Browse Source

* moved assert handling from second to first pass, so that the code generator
knows that the frame pointer needs to be available (and the code is also
much simpler this way), fixes test/units/system/tassert7 after r21843

git-svn-id: trunk@21869 -

Jonas Maebe 13 years ago
parent
commit
89c230c035
2 changed files with 15 additions and 81 deletions
  1. 1 73
      compiler/ncginl.pas
  2. 14 8
      compiler/ninl.pas

+ 1 - 73
compiler/ncginl.pas

@@ -31,7 +31,6 @@ interface
     type
        tcginlinenode = class(tinlinenode)
           procedure pass_generate_code;override;
-          procedure second_assert;virtual;
           procedure second_sizeoftypeof;virtual;
           procedure second_length;virtual;
           procedure second_predsucc;virtual;
@@ -65,7 +64,7 @@ implementation
 
     uses
       globtype,systems,constexp,
-      cutils,verbose,globals,fmodule,
+      cutils,verbose,globals,
       symconst,symdef,defutil,symsym,
       aasmbase,aasmtai,aasmdata,aasmcpu,parabase,
       cgbase,pass_1,pass_2,
@@ -89,8 +88,6 @@ implementation
          location_reset(location,LOC_VOID,OS_NO);
 
          case inlinenumber of
-            in_assert_x_y:
-              second_Assert;
             in_sizeof_x,
             in_typeof_x :
               second_SizeofTypeOf;
@@ -185,75 +182,6 @@ implementation
       end;
 
 
-{*****************************************************************************
-                          ASSERT GENERIC HANDLING
-*****************************************************************************}
-    procedure tcginlinenode.second_Assert;
-     var
-       hp2,hp3 : tnode;
-       otlabel,oflabel : tasmlabel;
-       paraloc1,paraloc2,
-       paraloc3,paraloc4 : tcgpara;
-     begin
-       { the node should be removed in the firstpass }
-       if not (cs_do_assertion in current_settings.localswitches) then
-          internalerror(7123458);
-       paraloc1.init;
-       paraloc2.init;
-       paraloc3.init;
-       paraloc4.init;
-       paramanager.getintparaloc(pocall_default,1,getpointerdef(cshortstringtype),paraloc1);
-       paramanager.getintparaloc(pocall_default,2,getpointerdef(cshortstringtype),paraloc2);
-       paramanager.getintparaloc(pocall_default,3,s32inttype,paraloc3);
-       paramanager.getintparaloc(pocall_default,4,voidpointertype,paraloc4);
-       otlabel:=current_procinfo.CurrTrueLabel;
-       oflabel:=current_procinfo.CurrFalseLabel;
-       current_asmdata.getjumplabel(current_procinfo.CurrTrueLabel);
-       current_asmdata.getjumplabel(current_procinfo.CurrFalseLabel);
-       secondpass(tcallparanode(left).left);
-       maketojumpbool(current_asmdata.CurrAsmList,tcallparanode(left).left,lr_load_regvars);
-       cg.a_label(current_asmdata.CurrAsmList,current_procinfo.CurrFalseLabel);
-       { First call secondpass() before we can push the parameters, otherwise
-         parameters allocated in the registers can be destroyed }
-       { generate filename string parameter }
-       hp2:=ctypeconvnode.create(cstringconstnode.createstr(current_module.sourcefiles.get_file_name(current_filepos.fileindex)),cshortstringtype);
-       firstpass(hp2);
-       secondpass(hp2);
-       if codegenerror then
-          exit;
-       { message parameter }
-       hp3:=tcallparanode(tcallparanode(left).right).left;
-       secondpass(hp3);
-       if codegenerror then
-          exit;
-       { push erroraddr }
-       cg.a_load_reg_cgpara(current_asmdata.CurrAsmList,OS_ADDR,NR_FRAME_POINTER_REG,paraloc4);
-       { push lineno }
-       cg.a_load_const_cgpara(current_asmdata.CurrAsmList,OS_S32,current_filepos.line,paraloc3);
-       { push filename }
-       cg.a_loadaddr_ref_cgpara(current_asmdata.CurrAsmList,hp2.location.reference,paraloc2);
-       { push msg }
-       cg.a_loadaddr_ref_cgpara(current_asmdata.CurrAsmList,hp3.location.reference,paraloc1);
-       { call }
-       paramanager.freecgpara(current_asmdata.CurrAsmList,paraloc1);
-       paramanager.freecgpara(current_asmdata.CurrAsmList,paraloc2);
-       paramanager.freecgpara(current_asmdata.CurrAsmList,paraloc3);
-       paramanager.freecgpara(current_asmdata.CurrAsmList,paraloc4);
-       cg.allocallcpuregisters(current_asmdata.CurrAsmList);
-       cg.a_call_name(current_asmdata.CurrAsmList,'FPC_ASSERT',false);
-       cg.deallocallcpuregisters(current_asmdata.CurrAsmList);
-       location_freetemp(current_asmdata.CurrAsmList,hp3.location);
-       location_freetemp(current_asmdata.CurrAsmList,hp2.location);
-       cg.a_label(current_asmdata.CurrAsmList,current_procinfo.CurrTrueLabel);
-       current_procinfo.CurrTrueLabel:=otlabel;
-       current_procinfo.CurrFalseLabel:=oflabel;
-       paraloc1.done;
-       paraloc2.done;
-       paraloc3.done;
-       paraloc4.done;
-       hp2.free;
-     end;
-
 
 {*****************************************************************************
                           SIZEOF / TYPEOF GENERIC HANDLING

+ 14 - 8
compiler/ninl.pas

@@ -102,7 +102,7 @@ implementation
 
     uses
       verbose,globals,systems,constexp,
-      globtype, cutils,
+      globtype,cutils,fmodule,
       symconst,symdef,symsym,symtable,paramgr,defutil,symbase,
       pass_1,
       ncal,ncon,ncnv,nadd,nld,nbas,nflw,nmem,nmat,nutils,
@@ -3788,15 +3788,21 @@ implementation
 
 
      function tinlinenode.first_assert: tnode;
+       var
+         paras: tcallparanode;
        begin
-         result:=nil;
-         expectloc:=LOC_VOID;
-{$ifdef i386}
-         { hack: on i386, the fourth parameter is passed via memory ->
-           we have to allocate enough stack space for it on targets that
-           use a fixed stack }
-         current_procinfo.allocate_push_parasize(4);
+         paras:=tcallparanode(tcallparanode(left).right);
+         paras:=ccallparanode.create(cstringconstnode.createstr(current_module.sourcefiles.get_file_name(current_filepos.fileindex)),paras);
+         paras:=ccallparanode.create(genintconstnode(fileinfo.line),paras);
+{$if defined(x86) or defined(arm)}
+         paras:=ccallparanode.create(geninlinenode(in_get_frame,false,nil),paras);
+{$else}
+         paras:=ccallparanode.create(ccallnode.createinternfromunit('SYSTEM','GET_FRAME',nil),paras);
 {$endif}
+         result:=cifnode.create(cnotnode.create(tcallparanode(left).left),
+            ccallnode.createintern('fpc_assert',paras),nil);
+         tcallparanode(left).left:=nil;
+         tcallparanode(left).right:=nil;
        end;