|
@@ -58,6 +58,7 @@ interface
|
|
|
function assemble : tnode;
|
|
|
|
|
|
var
|
|
|
+ uhs,
|
|
|
retstr,s,hs : string;
|
|
|
c : char;
|
|
|
ende : boolean;
|
|
@@ -96,202 +97,242 @@ interface
|
|
|
retstr:=upper(tostr(current_procinfo.return_offset)+'('+gas_reg2str[framereg.enum]+')')
|
|
|
else
|
|
|
retstr:='';
|
|
|
- c:=current_scanner.asmgetchar;
|
|
|
- code:=TAAsmoutput.Create;
|
|
|
- while not(ende) do
|
|
|
- begin
|
|
|
- { wrong placement
|
|
|
- current_scanner.gettokenpos; }
|
|
|
- case c of
|
|
|
- 'A'..'Z','a'..'z','_' : begin
|
|
|
- current_scanner.gettokenpos;
|
|
|
- i:=0;
|
|
|
- hs:='';
|
|
|
- while ((ord(c)>=ord('A')) and (ord(c)<=ord('Z')))
|
|
|
- or ((ord(c)>=ord('a')) and (ord(c)<=ord('z')))
|
|
|
- or ((ord(c)>=ord('0')) and (ord(c)<=ord('9')))
|
|
|
- or (c='_') do
|
|
|
- begin
|
|
|
- inc(i);
|
|
|
- hs[i]:=c;
|
|
|
- c:=current_scanner.asmgetchar;
|
|
|
- end;
|
|
|
- hs[0]:=chr(i);
|
|
|
- if upper(hs)='END' then
|
|
|
- ende:=true
|
|
|
- else
|
|
|
- begin
|
|
|
- if c=':' then
|
|
|
- begin
|
|
|
- searchsym(upper(hs),srsym,srsymtable);
|
|
|
- if srsym<>nil then
|
|
|
- if (srsym.typ = labelsym) then
|
|
|
- Begin
|
|
|
- hs:=tlabelsym(srsym).lab.name;
|
|
|
- tlabelsym(srsym).lab.is_set:=true;
|
|
|
- end
|
|
|
- else
|
|
|
- Message(asmr_w_using_defined_as_local);
|
|
|
- end
|
|
|
- else if upper(hs)='FWAIT' then
|
|
|
- FwaitWarning
|
|
|
- else
|
|
|
- { access to local variables }
|
|
|
- if assigned(current_procdef) then
|
|
|
- begin
|
|
|
- { is the last written character an special }
|
|
|
- { char ? }
|
|
|
- if (s[length(s)]='%') and
|
|
|
- (not paramanager.ret_in_param(current_procdef.rettype.def,current_procdef.proccalloption)) and
|
|
|
- ((pos('AX',upper(hs))>0) or
|
|
|
- (pos('AL',upper(hs))>0)) then
|
|
|
- tvarsym(current_procdef.funcretsym).varstate:=vs_assigned;
|
|
|
- if (s[length(s)]<>'%') and
|
|
|
- (s[length(s)]<>'$') and
|
|
|
- (s[length(s)]<>'.') and
|
|
|
- ((s[length(s)]<>'0') or (hs[1]<>'x')) then
|
|
|
- begin
|
|
|
- if assigned(current_procdef.localst) and
|
|
|
- (current_procdef.localst.symtablelevel>=normal_function_level) then
|
|
|
- sym:=tsym(current_procdef.localst.search(upper(hs)))
|
|
|
- else
|
|
|
- sym:=nil;
|
|
|
- if assigned(sym) then
|
|
|
- begin
|
|
|
- if (sym.typ = labelsym) then
|
|
|
- Begin
|
|
|
- hs:=tlabelsym(sym).lab.name;
|
|
|
- end
|
|
|
- else if sym.typ=varsym then
|
|
|
- begin
|
|
|
- {variables set are after a comma }
|
|
|
- {like in movl %eax,I }
|
|
|
- if pos(',',s) > 0 then
|
|
|
- tvarsym(sym).varstate:=vs_used
|
|
|
- else
|
|
|
- if (pos('MOV',upper(s)) > 0) and (tvarsym(sym).varstate=vs_declared) then
|
|
|
- Message1(sym_n_uninitialized_local_variable,hs);
|
|
|
- if (vo_is_external in tvarsym(sym).varoptions) then
|
|
|
- hs:=tvarsym(sym).mangledname
|
|
|
- else
|
|
|
- hs:='-'+tostr(tvarsym(sym).address)+
|
|
|
- '('+gas_reg2str[framereg.enum]+')';
|
|
|
- end
|
|
|
+ c:=current_scanner.asmgetchar;
|
|
|
+ code:=TAAsmoutput.Create;
|
|
|
+ while not(ende) do
|
|
|
+ begin
|
|
|
+ { wrong placement
|
|
|
+ current_scanner.gettokenpos; }
|
|
|
+ case c of
|
|
|
+ 'A'..'Z','a'..'z','_' : begin
|
|
|
+ current_scanner.gettokenpos;
|
|
|
+ i:=0;
|
|
|
+ hs:='';
|
|
|
+ while ((ord(c)>=ord('A')) and (ord(c)<=ord('Z')))
|
|
|
+ or ((ord(c)>=ord('a')) and (ord(c)<=ord('z')))
|
|
|
+ or ((ord(c)>=ord('0')) and (ord(c)<=ord('9')))
|
|
|
+ or (c='_') do
|
|
|
+ begin
|
|
|
+ inc(i);
|
|
|
+ hs[i]:=c;
|
|
|
+ c:=current_scanner.asmgetchar;
|
|
|
+ end;
|
|
|
+ hs[0]:=chr(i);
|
|
|
+ if upper(hs)='END' then
|
|
|
+ ende:=true
|
|
|
+ else
|
|
|
+ begin
|
|
|
+ if c=':' then
|
|
|
+ begin
|
|
|
+ searchsym(upper(hs),srsym,srsymtable);
|
|
|
+ if srsym<>nil then
|
|
|
+ if (srsym.typ = labelsym) then
|
|
|
+ Begin
|
|
|
+ hs:=tlabelsym(srsym).lab.name;
|
|
|
+ tlabelsym(srsym).lab.is_set:=true;
|
|
|
+ end
|
|
|
+ else
|
|
|
+ Message(asmr_w_using_defined_as_local);
|
|
|
+ end
|
|
|
+ else if upper(hs)='FWAIT' then
|
|
|
+ FwaitWarning
|
|
|
+ else
|
|
|
+ { access to local variables }
|
|
|
+ if assigned(current_procdef) then
|
|
|
+ begin
|
|
|
+ { is the last written character an special }
|
|
|
+ { char ? }
|
|
|
+ if (s[length(s)]='%') and
|
|
|
+ (not paramanager.ret_in_param(current_procdef.rettype.def,current_procdef.proccalloption)) and
|
|
|
+ ((pos('AX',upper(hs))>0) or
|
|
|
+ (pos('AL',upper(hs))>0)) then
|
|
|
+ tvarsym(current_procdef.funcretsym).varstate:=vs_assigned;
|
|
|
+ if (s[length(s)]<>'%') and
|
|
|
+ (s[length(s)]<>'$') and
|
|
|
+ (s[length(s)]<>'.') and
|
|
|
+ ((s[length(s)]<>'0') or (hs[1]<>'x')) then
|
|
|
+ begin
|
|
|
+ if assigned(current_procdef.localst) and
|
|
|
+ (current_procdef.localst.symtablelevel>=normal_function_level) then
|
|
|
+ sym:=tsym(current_procdef.localst.search(upper(hs)))
|
|
|
+ else
|
|
|
+ sym:=nil;
|
|
|
+ if assigned(sym) then
|
|
|
+ begin
|
|
|
+ if (sym.typ = labelsym) then
|
|
|
+ Begin
|
|
|
+ hs:=tlabelsym(sym).lab.name;
|
|
|
+ end
|
|
|
+ else if sym.typ=varsym then
|
|
|
+ begin
|
|
|
+ {variables set are after a comma }
|
|
|
+ {like in movl %eax,I }
|
|
|
+ if pos(',',s) > 0 then
|
|
|
+ tvarsym(sym).varstate:=vs_used
|
|
|
else
|
|
|
- { call to local function }
|
|
|
- if (sym.typ=procsym) and ((pos('CALL',upper(s))>0) or
|
|
|
- (pos('LEA',upper(s))>0)) then
|
|
|
- begin
|
|
|
- hs:=tprocsym(sym).first_procdef.mangledname;
|
|
|
- end;
|
|
|
- end
|
|
|
- else
|
|
|
- begin
|
|
|
- if assigned(current_procdef.parast) then
|
|
|
- sym:=tsym(current_procdef.parast.search(upper(hs)))
|
|
|
+ if (pos('MOV',upper(s)) > 0) and (tvarsym(sym).varstate=vs_declared) then
|
|
|
+ Message1(sym_n_uninitialized_local_variable,hs);
|
|
|
+ if (vo_is_external in tvarsym(sym).varoptions) then
|
|
|
+ hs:=tvarsym(sym).mangledname
|
|
|
else
|
|
|
- sym:=nil;
|
|
|
- if assigned(sym) then
|
|
|
- begin
|
|
|
- if sym.typ=varsym then
|
|
|
- begin
|
|
|
- l:=tvarsym(sym).address;
|
|
|
- { set offset }
|
|
|
- inc(l,current_procdef.parast.address_fixup);
|
|
|
- hs:=tostr(l)+'('+gas_reg2str[framereg.enum]+')';
|
|
|
- if pos(',',s) > 0 then
|
|
|
- tvarsym(sym).varstate:=vs_used;
|
|
|
+ hs:='-'+tostr(tvarsym(sym).address)+
|
|
|
+ '('+gas_reg2str[framereg.enum]+')';
|
|
|
+ end
|
|
|
+ else
|
|
|
+ { call to local function }
|
|
|
+ if (sym.typ=procsym) and ((pos('CALL',upper(s))>0) or
|
|
|
+ (pos('LEA',upper(s))>0)) then
|
|
|
+ begin
|
|
|
+ hs:=tprocsym(sym).first_procdef.mangledname;
|
|
|
+ end;
|
|
|
+ end
|
|
|
+ else
|
|
|
+ begin
|
|
|
+ if assigned(current_procdef.parast) then
|
|
|
+ sym:=tsym(current_procdef.parast.search(upper(hs)))
|
|
|
+ else
|
|
|
+ sym:=nil;
|
|
|
+ if assigned(sym) then
|
|
|
+ begin
|
|
|
+ if sym.typ=varsym then
|
|
|
+ begin
|
|
|
+ l:=tvarsym(sym).address;
|
|
|
+ { set offset }
|
|
|
+ inc(l,current_procdef.parast.address_fixup);
|
|
|
+ hs:=tostr(l)+'('+gas_reg2str[framereg.enum]+')';
|
|
|
+ if pos(',',s) > 0 then
|
|
|
+ tvarsym(sym).varstate:=vs_used;
|
|
|
+ end;
|
|
|
+ end
|
|
|
+ { I added that but it creates a problem in line.ppi
|
|
|
+ because there is a local label wbuffer and
|
|
|
+ a static variable WBUFFER ...
|
|
|
+ what would you decide, florian ?}
|
|
|
+ else
|
|
|
+
|
|
|
+ begin
|
|
|
+ uhs:=upper(hs);
|
|
|
+ if (uhs='__SELF') then
|
|
|
+ begin
|
|
|
+ if assigned(current_procdef._class) then
|
|
|
+ uhs:='self'
|
|
|
+ else
|
|
|
+ begin
|
|
|
+ Message(asmr_e_cannot_use_SELF_outside_a_method);
|
|
|
+ uhs:='';
|
|
|
+ end;
|
|
|
+ end
|
|
|
+ else
|
|
|
+ if (uhs='__OLDEBP') then
|
|
|
+ begin
|
|
|
+ if current_procdef.parast.symtablelevel>normal_function_level then
|
|
|
+ uhs:='parentframe'
|
|
|
+ else
|
|
|
+ begin
|
|
|
+ Message(asmr_e_cannot_use_OLDEBP_outside_nested_procedure);
|
|
|
+ uhs:='';
|
|
|
+ end;
|
|
|
+ end
|
|
|
+ else
|
|
|
+ if uhs='__RESULT' then
|
|
|
+ begin
|
|
|
+ if (not is_void(current_procdef.rettype.def)) then
|
|
|
+ uhs:='result'
|
|
|
+ else
|
|
|
+ begin
|
|
|
+ Message(asmr_e_void_function);
|
|
|
+ uhs:='';
|
|
|
+ end;
|
|
|
+ end;
|
|
|
+
|
|
|
+ if uhs<>'' then
|
|
|
+ searchsym(uhs,sym,srsymtable)
|
|
|
+ else
|
|
|
+ sym:=nil;
|
|
|
+ if assigned(sym) then
|
|
|
+ begin
|
|
|
+ case sym.owner.symtabletype of
|
|
|
+ globalsymtable,
|
|
|
+ staticsymtable :
|
|
|
+ begin
|
|
|
+ case sym.typ of
|
|
|
+ varsym :
|
|
|
+ begin
|
|
|
+ Message2(asmr_h_direct_global_to_mangled,hs,tvarsym(sym).mangledname);
|
|
|
+ hs:=tvarsym(sym).mangledname;
|
|
|
+ inc(tvarsym(sym).refs);
|
|
|
+ end;
|
|
|
+ typedconstsym :
|
|
|
+ begin
|
|
|
+ Message2(asmr_h_direct_global_to_mangled,hs,ttypedconstsym(sym).mangledname);
|
|
|
+ hs:=ttypedconstsym(sym).mangledname;
|
|
|
+ end;
|
|
|
+ procsym :
|
|
|
+ begin
|
|
|
+ { procs can be called or the address can be loaded }
|
|
|
+ if ((pos('CALL',upper(s))>0) or (pos('LEA',upper(s))>0)) then
|
|
|
+ begin
|
|
|
+ if tprocsym(sym).procdef_count>1 then
|
|
|
+ Message1(asmr_w_direct_global_is_overloaded_func,hs);
|
|
|
+ Message2(asmr_h_direct_global_to_mangled,hs,tprocsym(sym).first_procdef.mangledname);
|
|
|
+ hs:=tprocsym(sym).first_procdef.mangledname;
|
|
|
+ end;
|
|
|
+ end;
|
|
|
+ else
|
|
|
+ Message(asmr_e_wrong_sym_type);
|
|
|
end;
|
|
|
- end
|
|
|
- { I added that but it creates a problem in line.ppi
|
|
|
- because there is a local label wbuffer and
|
|
|
- a static variable WBUFFER ...
|
|
|
- what would you decide, florian ?}
|
|
|
- else
|
|
|
-
|
|
|
- begin
|
|
|
- searchsym(upper(hs),sym,srsymtable);
|
|
|
- if assigned(sym) and (sym.owner.symtabletype in [globalsymtable,staticsymtable]) then
|
|
|
- begin
|
|
|
- case sym.typ of
|
|
|
- varsym :
|
|
|
- begin
|
|
|
- Message2(asmr_h_direct_global_to_mangled,hs,tvarsym(sym).mangledname);
|
|
|
- hs:=tvarsym(sym).mangledname;
|
|
|
- inc(tvarsym(sym).refs);
|
|
|
- end;
|
|
|
- typedconstsym :
|
|
|
- begin
|
|
|
- Message2(asmr_h_direct_global_to_mangled,hs,ttypedconstsym(sym).mangledname);
|
|
|
- hs:=ttypedconstsym(sym).mangledname;
|
|
|
- end;
|
|
|
- procsym :
|
|
|
- begin
|
|
|
- { procs can be called or the address can be loaded }
|
|
|
- if ((pos('CALL',upper(s))>0) or (pos('LEA',upper(s))>0)) then
|
|
|
+ end;
|
|
|
+ parasymtable,
|
|
|
+ localsymtable :
|
|
|
+ begin
|
|
|
+ case sym.typ of
|
|
|
+ varsym :
|
|
|
begin
|
|
|
- if tprocsym(sym).procdef_count>1 then
|
|
|
- Message1(asmr_w_direct_global_is_overloaded_func,hs);
|
|
|
- Message2(asmr_h_direct_global_to_mangled,hs,tprocsym(sym).first_procdef.mangledname);
|
|
|
- hs:=tprocsym(sym).first_procdef.mangledname;
|
|
|
+ hs:=tostr(tvarsym(sym).adjusted_address)+
|
|
|
+ '('+gas_reg2str[framereg.enum]+')';
|
|
|
+ inc(tvarsym(sym).refs);
|
|
|
end;
|
|
|
- end;
|
|
|
- else
|
|
|
- Message(asmr_e_wrong_sym_type);
|
|
|
- end;
|
|
|
- end
|
|
|
- else if upper(hs)='__SELF' then
|
|
|
- begin
|
|
|
- if assigned(current_procdef._class) then
|
|
|
- hs:=tostr(current_procinfo.selfpointer_offset)+
|
|
|
- '('+gas_reg2str[framereg.enum]+')'
|
|
|
- else
|
|
|
- Message(asmr_e_cannot_use_SELF_outside_a_method);
|
|
|
- end
|
|
|
- else if upper(hs)='__RESULT' then
|
|
|
- begin
|
|
|
- if (not is_void(current_procdef.rettype.def)) then
|
|
|
- hs:=retstr
|
|
|
- else
|
|
|
- Message(asmr_e_void_function);
|
|
|
- end
|
|
|
- else if upper(hs)='__OLDEBP' then
|
|
|
- begin
|
|
|
- { complicate to check there }
|
|
|
- { we do it: }
|
|
|
- if current_procdef.parast.symtablelevel>normal_function_level then
|
|
|
- hs:=tostr(current_procinfo.framepointer_offset)+
|
|
|
- '('+gas_reg2str[framereg.enum]+')'
|
|
|
- else
|
|
|
- Message(asmr_e_cannot_use_OLDEBP_outside_nested_procedure);
|
|
|
+ typedconstsym :
|
|
|
+ begin
|
|
|
+ Message2(asmr_h_direct_global_to_mangled,hs,ttypedconstsym(sym).mangledname);
|
|
|
+ hs:=ttypedconstsym(sym).mangledname;
|
|
|
+ end;
|
|
|
+ else
|
|
|
+ Message(asmr_e_wrong_sym_type);
|
|
|
+ end;
|
|
|
+ end;
|
|
|
end;
|
|
|
- end;
|
|
|
- end;
|
|
|
- end;
|
|
|
- end;
|
|
|
- s:=s+hs;
|
|
|
- end;
|
|
|
- end;
|
|
|
- '{',';',#10,#13 : begin
|
|
|
- if pos(retstr,s) > 0 then
|
|
|
- tvarsym(current_procdef.funcretsym).varstate:=vs_assigned;
|
|
|
- writeasmline;
|
|
|
- c:=current_scanner.asmgetchar;
|
|
|
- end;
|
|
|
- #26 : Message(scan_f_end_of_file);
|
|
|
- else
|
|
|
- begin
|
|
|
- current_scanner.gettokenpos;
|
|
|
- inc(byte(s[0]));
|
|
|
- s[length(s)]:=c;
|
|
|
- c:=current_scanner.asmgetchar;
|
|
|
- end;
|
|
|
- end;
|
|
|
+ end
|
|
|
+ end;
|
|
|
+ end;
|
|
|
+ end;
|
|
|
+ end;
|
|
|
+ s:=s+hs;
|
|
|
+ end;
|
|
|
+ end;
|
|
|
+ '{',';',#10,#13 :
|
|
|
+ begin
|
|
|
+ if pos(retstr,s) > 0 then
|
|
|
+ tvarsym(current_procdef.funcretsym).varstate:=vs_assigned;
|
|
|
+ writeasmline;
|
|
|
+ c:=current_scanner.asmgetchar;
|
|
|
+ end;
|
|
|
+ #26 :
|
|
|
+ Message(scan_f_end_of_file);
|
|
|
+ else
|
|
|
+ begin
|
|
|
+ current_scanner.gettokenpos;
|
|
|
+ inc(byte(s[0]));
|
|
|
+ s[length(s)]:=c;
|
|
|
+ c:=current_scanner.asmgetchar;
|
|
|
+ end;
|
|
|
+ end;
|
|
|
end;
|
|
|
writeasmline;
|
|
|
assemble:=casmnode.create(code);
|
|
|
end;
|
|
|
|
|
|
+
|
|
|
{*****************************************************************************
|
|
|
Initialize
|
|
|
*****************************************************************************}
|
|
@@ -320,7 +361,13 @@ initialization
|
|
|
end.
|
|
|
{
|
|
|
$Log$
|
|
|
- Revision 1.3 2003-05-13 19:15:28 peter
|
|
|
+ Revision 1.4 2003-05-15 18:58:54 peter
|
|
|
+ * removed selfpointer_offset, vmtpointer_offset
|
|
|
+ * tvarsym.adjusted_address
|
|
|
+ * address in localsymtable is now in the real direction
|
|
|
+ * removed some obsolete globals
|
|
|
+
|
|
|
+ Revision 1.3 2003/05/13 19:15:28 peter
|
|
|
* removed radirect
|
|
|
|
|
|
Revision 1.2 2003/05/01 07:59:43 florian
|