mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-19 06:19:32 +02:00
* Always use RIP relative symbol addressing for x86_64 Windows targets. Bug #13657.
* Support for simple form of RIP relative addressing by x86_64 assembler writer. Example: movl rax,SomeSymbol(%rip) git-svn-id: trunk@13135 -
This commit is contained in:
parent
4eef2b87a1
commit
92ad06f1e8
@ -1298,6 +1298,9 @@ implementation
|
||||
begin
|
||||
result:=(oper[opidx]^.typ=top_ref) and
|
||||
(oper[opidx]^.ref^.refaddr=addr_no) and
|
||||
{$ifdef x86_64}
|
||||
(oper[opidx]^.ref^.base<>NR_RIP) and
|
||||
{$endif x86_64}
|
||||
(
|
||||
(
|
||||
(oper[opidx]^.ref^.index<>NR_NO) and
|
||||
@ -2279,13 +2282,28 @@ implementation
|
||||
2,4 :
|
||||
begin
|
||||
currsym:=objdata.symbolref(oper[opidx]^.ref^.symbol);
|
||||
currval:=oper[opidx]^.ref^.offset;
|
||||
{$ifdef x86_64}
|
||||
if oper[opidx]^.ref^.refaddr=addr_pic then
|
||||
currabsreloc:=RELOC_GOTPCREL
|
||||
else
|
||||
if oper[opidx]^.ref^.base=NR_RIP then
|
||||
begin
|
||||
currabsreloc:=RELOC_RELATIVE;
|
||||
{ Adjust reloc value depending of immediate operand size }
|
||||
case Ord(codes^) of
|
||||
12,13,14,16,17,18,20,21,22:
|
||||
Dec(currval, 1);
|
||||
24,25,26:
|
||||
Dec(currval, 2);
|
||||
32,33,34:
|
||||
Dec(currval, 4);
|
||||
end;
|
||||
end
|
||||
else
|
||||
{$endif x86_64}
|
||||
currabsreloc:=RELOC_ABSOLUTE32;
|
||||
objdata.writereloc(oper[opidx]^.ref^.offset,ea_data.bytes,currsym,currabsreloc);
|
||||
currabsreloc:=RELOC_ABSOLUTE32;
|
||||
objdata.writereloc(currval,ea_data.bytes,currsym,currabsreloc);
|
||||
inc(s,ea_data.bytes);
|
||||
end;
|
||||
end;
|
||||
|
@ -381,29 +381,62 @@ unit cgx86;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
if (cs_create_pic in current_settings.moduleswitches) and
|
||||
assigned(ref.symbol) and not((ref.symbol.bind=AB_LOCAL) and (ref.symbol.typ in [AT_LABEL,AT_FUNCTION])) then
|
||||
|
||||
if assigned(ref.symbol) and not((ref.symbol.bind=AB_LOCAL) and (ref.symbol.typ in [AT_LABEL,AT_FUNCTION])) then
|
||||
begin
|
||||
reference_reset_symbol(href,ref.symbol,0,sizeof(pint));
|
||||
hreg:=getaddressregister(list);
|
||||
href.refaddr:=addr_pic;
|
||||
href.base:=NR_RIP;
|
||||
list.concat(taicpu.op_ref_reg(A_MOV,S_Q,href,hreg));
|
||||
|
||||
ref.symbol:=nil;
|
||||
|
||||
if ref.base=NR_NO then
|
||||
ref.base:=hreg
|
||||
else if ref.index=NR_NO then
|
||||
if cs_create_pic in current_settings.moduleswitches then
|
||||
begin
|
||||
ref.index:=hreg;
|
||||
ref.scalefactor:=1;
|
||||
reference_reset_symbol(href,ref.symbol,0,sizeof(pint));
|
||||
hreg:=getaddressregister(list);
|
||||
href.refaddr:=addr_pic;
|
||||
href.base:=NR_RIP;
|
||||
list.concat(taicpu.op_ref_reg(A_MOV,S_Q,href,hreg));
|
||||
|
||||
ref.symbol:=nil;
|
||||
|
||||
if ref.base=NR_NO then
|
||||
ref.base:=hreg
|
||||
else if ref.index=NR_NO then
|
||||
begin
|
||||
ref.index:=hreg;
|
||||
ref.scalefactor:=1;
|
||||
end
|
||||
else
|
||||
begin
|
||||
list.concat(taicpu.op_reg_reg(A_ADD,S_Q,ref.base,hreg));
|
||||
ref.base:=hreg;
|
||||
end;
|
||||
end
|
||||
else
|
||||
begin
|
||||
list.concat(taicpu.op_reg_reg(A_ADD,S_Q,ref.base,hreg));
|
||||
ref.base:=hreg;
|
||||
end;
|
||||
{ Always use RIP relative symbol addressing for Windows targets. }
|
||||
if (target_info.system in system_all_windows) and (ref.base<>NR_RIP) then
|
||||
begin
|
||||
if (ref.refaddr=addr_no) and (ref.base=NR_NO) and (ref.index=NR_NO) then
|
||||
{ Set RIP relative addressing for simple symbol references }
|
||||
ref.base:=NR_RIP
|
||||
else
|
||||
begin
|
||||
{ Use temp register to load calculated 64-bit symbol address for complex references }
|
||||
reference_reset_symbol(href,ref.symbol,0,sizeof(pint));
|
||||
href.base:=NR_RIP;
|
||||
hreg:=GetAddressRegister(list);
|
||||
list.concat(taicpu.op_ref_reg(A_LEA,S_Q,href,hreg));
|
||||
ref.symbol:=nil;
|
||||
if ref.base=NR_NO then
|
||||
ref.base:=hreg
|
||||
else if ref.index=NR_NO then
|
||||
begin
|
||||
ref.index:=hreg;
|
||||
ref.scalefactor:=0;
|
||||
end
|
||||
else
|
||||
begin
|
||||
list.concat(taicpu.op_reg_reg(A_ADD,S_Q,ref.base,hreg));
|
||||
ref.base:=hreg;
|
||||
end;
|
||||
end;
|
||||
|
||||
end;
|
||||
end;
|
||||
{$else x86_64}
|
||||
add_hreg:=false;
|
||||
|
@ -235,6 +235,7 @@ implementation
|
||||
else
|
||||
internalerror(200506081);
|
||||
end;
|
||||
tcgx86(cg).make_simple_ref(current_asmdata.CurrAsmList, href);
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_ref_reg(A_ANDPS,S_XMM,href,location.register))
|
||||
end
|
||||
else
|
||||
|
Loading…
Reference in New Issue
Block a user