ソースを参照

Disallow the usage of the inline assembler inside generics, because there are currently two problems:
1. At least on x86 the assembler reader initializes the parameter location informations which results in InternalError 200301231
2. Assembler tokens are not stored in the token stream and thus won't be reproduced during specialization

x86/rax86int.pas, tx86intreader.Assemble:
* check for "parse_generic" before calling generate_parameter_info
pstatmnt.pas, assembler_block & statement:
* generate an error message if an asm statement should be parsed inside a generic

+ added test

git-svn-id: trunk@24892 -

svenbarth 12 年 前
コミット
b6bfa864d4

+ 1 - 0
.gitattributes

@@ -12354,6 +12354,7 @@ tests/webtbf/tw24184.pp svneol=native#text/plain
 tests/webtbf/tw24428.pp svneol=native#text/plain
 tests/webtbf/tw24428a.pp svneol=native#text/plain
 tests/webtbf/tw24495.pp svneol=native#text/pascal
+tests/webtbf/tw24588.pp svneol=native#text/pascal
 tests/webtbf/tw2478.pp svneol=native#text/plain
 tests/webtbf/tw2562.pp svneol=native#text/plain
 tests/webtbf/tw2657.pp svneol=native#text/plain

+ 3 - 1
compiler/msg/errore.msg

@@ -398,7 +398,7 @@ scan_e_illegal_peoptflag=02094_E_Illegal argument for SETPEOPTFLAGS
 #
 # Parser
 #
-# 03333 is the last used one
+# 03334 is the last used one
 #
 % \section{Parser messages}
 % This section lists all parser messages. The parser takes care of the
@@ -1496,6 +1496,8 @@ parser_e_not_allowed_in_record=03332_E_Visibility section "$1" not allowed in re
 parser_e_proc_dir_not_allowed=03333_E_Procedure directive "$1" not allowed here
 % This procedure directive is not allowed in the given context. E.g. "static"
 % is not allowed for instance methods or class operators.
+parser_e_no_assembler_in_generic=03334_E_Assembler blocks not allowed inside generics
+% The use of assembler blocks/routines is not allowed inside generics.
 %
 %
 % \end{description}

+ 3 - 2
compiler/msgidx.inc

@@ -431,6 +431,7 @@ const
   parser_e_no_class_in_local_anonymous_records=03331;
   parser_e_not_allowed_in_record=03332;
   parser_e_proc_dir_not_allowed=03333;
+  parser_e_no_assembler_in_generic=03334;
   type_e_mismatch=04000;
   type_e_incompatible_types=04001;
   type_e_not_equal_types=04002;
@@ -975,9 +976,9 @@ const
   option_info=11024;
   option_help_pages=11025;
 
-  MsgTxtSize = 69070;
+  MsgTxtSize = 69135;
 
   MsgIdxMax : array[1..20] of longint=(
-    26,95,334,121,88,56,126,27,202,63,
+    26,95,335,121,88,56,126,27,202,63,
     54,20,1,1,1,1,1,1,1,1
   );

ファイルの差分が大きいため隠しています
+ 392 - 392
compiler/msgtxt.inc


+ 8 - 1
compiler/pstatmnt.pas

@@ -1187,7 +1187,11 @@ implementation
                 code:=cnodeutils.call_fail_node;
              end;
            _ASM :
-             code:=_asm_statement;
+             begin
+               if parse_generic then
+                 Message(parser_e_no_assembler_in_generic);
+               code:=_asm_statement;
+             end;
            _EOF :
              Message(scan_f_end_of_file);
          else
@@ -1365,6 +1369,9 @@ implementation
 {$endif arm}
         srsym : tsym;
       begin
+         if parse_generic then
+           message(parser_e_no_assembler_in_generic);
+
          { Rename the funcret so that recursive calls are possible }
          if not is_void(current_procinfo.procdef.returndef) then
            begin

+ 3 - 2
compiler/x86/rax86int.pas

@@ -86,7 +86,7 @@ Unit Rax86int;
        { symtable }
        symconst,symbase,symtype,symsym,symdef,symtable,
        { parser }
-       scanner,
+       scanner,pbase,
        { register allocator }
        rabase,rautils,itx86int,
        { codegen }
@@ -2222,7 +2222,8 @@ Unit Rax86int;
       { setup label linked list }
       LocalLabelList:=TLocalLabelList.Create;
       { we might need to know which parameters are passed in registers }
-      current_procinfo.generate_parameter_info;
+      if not parse_generic then
+        current_procinfo.generate_parameter_info;
       { start tokenizer }
       c:=current_scanner.asmgetcharstart;
       gettoken;

+ 19 - 0
tests/webtbf/tw24588.pp

@@ -0,0 +1,19 @@
+{ %FAIL }
+program tw24588;
+{$mode objfpc}
+{$asmmode intel}
+type
+generic TFoo<T>=class
+procedure CrashMe(_val: T);
+end;
+
+procedure TFoo.CrashMe(_val: T);
+begin
+asm
+mov edi,edi
+end;
+end;
+
+begin
+end.
+

この差分においてかなりの量のファイルが変更されているため、一部のファイルを表示していません