mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-24 22:39:11 +02:00
* x86 and SPARC: fixed handling 64-bit (qwordbool) values in tcgnotnode (partial fix for Mantis #25255).
* Moved handling LOC_JUMP locations to helper method of base class, it appears to be the same for all targets. git-svn-id: trunk@26353 -
This commit is contained in:
parent
e1332304ef
commit
36d0c8a5a7
compiler
@ -109,6 +109,7 @@ interface
|
||||
|
||||
tcgnotnode = class(tnotnode)
|
||||
protected
|
||||
function handle_locjump: boolean;
|
||||
procedure second_boolean;virtual;abstract;
|
||||
{$ifdef SUPPORT_MMX}
|
||||
procedure second_mmx;virtual;abstract;
|
||||
@ -131,7 +132,7 @@ implementation
|
||||
parabase,
|
||||
pass_2,
|
||||
ncon,
|
||||
tgobj,ncgutil,cgobj,cgutils,paramgr,hlcgobj
|
||||
tgobj,ncgutil,cgobj,cgutils,paramgr,hlcgobj,procinfo
|
||||
{$ifndef cpu64bitalu}
|
||||
,cg64f32
|
||||
{$endif not cpu64bitalu}
|
||||
@ -557,6 +558,33 @@ implementation
|
||||
end;
|
||||
|
||||
|
||||
function tcgnotnode.handle_locjump: boolean;
|
||||
var
|
||||
hl: tasmlabel;
|
||||
begin
|
||||
result:=(left.expectloc=LOC_JUMP);
|
||||
if result then
|
||||
begin
|
||||
hl:=current_procinfo.CurrTrueLabel;
|
||||
current_procinfo.CurrTrueLabel:=current_procinfo.CurrFalseLabel;
|
||||
current_procinfo.CurrFalseLabel:=hl;
|
||||
secondpass(left);
|
||||
|
||||
if is_constboolnode(left) then
|
||||
internalerror(2014010101);
|
||||
if left.location.loc<>LOC_JUMP then
|
||||
internalerror(2012081306);
|
||||
|
||||
{ This does nothing for LOC_JUMP }
|
||||
//maketojumpbool(current_asmdata.CurrAsmList,left,lr_load_regvars);
|
||||
hl:=current_procinfo.CurrTrueLabel;
|
||||
current_procinfo.CurrTrueLabel:=current_procinfo.CurrFalseLabel;
|
||||
current_procinfo.CurrFalseLabel:=hl;
|
||||
location_reset(location,LOC_JUMP,OS_NO);
|
||||
end;
|
||||
end;
|
||||
|
||||
|
||||
procedure tcgnotnode.pass_generate_code;
|
||||
begin
|
||||
if is_boolean(resultdef) then
|
||||
|
@ -253,29 +253,8 @@ implementation
|
||||
*****************************************************************************}
|
||||
|
||||
procedure tsparcnotnode.second_boolean;
|
||||
var
|
||||
hl : tasmlabel;
|
||||
begin
|
||||
{ if the location is LOC_JUMP, we do the secondpass after the
|
||||
labels are allocated
|
||||
}
|
||||
if left.expectloc=LOC_JUMP then
|
||||
begin
|
||||
hl:=current_procinfo.CurrTrueLabel;
|
||||
current_procinfo.CurrTrueLabel:=current_procinfo.CurrFalseLabel;
|
||||
current_procinfo.CurrFalseLabel:=hl;
|
||||
secondpass(left);
|
||||
|
||||
if left.location.loc<>LOC_JUMP then
|
||||
internalerror(2012081306);
|
||||
|
||||
maketojumpbool(current_asmdata.CurrAsmList,left,lr_load_regvars);
|
||||
hl:=current_procinfo.CurrTrueLabel;
|
||||
current_procinfo.CurrTrueLabel:=current_procinfo.CurrFalseLabel;
|
||||
current_procinfo.CurrFalseLabel:=hl;
|
||||
location.loc:=LOC_JUMP;
|
||||
end
|
||||
else
|
||||
if not handle_locjump then
|
||||
begin
|
||||
secondpass(left);
|
||||
case left.location.loc of
|
||||
@ -290,7 +269,11 @@ implementation
|
||||
LOC_SUBSETREF, LOC_CSUBSETREF:
|
||||
begin
|
||||
hlcg.location_force_reg(current_asmdata.CurrAsmList,left.location,left.resultdef,left.resultdef,true);
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_reg_const_reg(A_SUBcc,left.location.register,0,NR_G0));
|
||||
if is_64bit(left.resultdef) then
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_reg_reg_reg(A_ORcc,
|
||||
left.location.register64.reglo,left.location.register64.reghi,NR_G0))
|
||||
else
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_reg_const_reg(A_SUBcc,left.location.register,0,NR_G0));
|
||||
location_reset(location,LOC_FLAGS,OS_NO);
|
||||
location.resflags:=F_E;
|
||||
end;
|
||||
|
@ -221,28 +221,12 @@ interface
|
||||
|
||||
procedure tx86notnode.second_boolean;
|
||||
var
|
||||
hl : tasmlabel;
|
||||
opsize : tcgsize;
|
||||
hreg: tregister;
|
||||
begin
|
||||
opsize:=def_cgsize(resultdef);
|
||||
|
||||
if left.expectloc=LOC_JUMP then
|
||||
begin
|
||||
location_reset(location,LOC_JUMP,OS_NO);
|
||||
hl:=current_procinfo.CurrTrueLabel;
|
||||
current_procinfo.CurrTrueLabel:=current_procinfo.CurrFalseLabel;
|
||||
current_procinfo.CurrFalseLabel:=hl;
|
||||
secondpass(left);
|
||||
|
||||
if left.location.loc<>LOC_JUMP then
|
||||
internalerror(2012081307);
|
||||
|
||||
maketojumpbool(current_asmdata.CurrAsmList,left,lr_load_regvars);
|
||||
hl:=current_procinfo.CurrTrueLabel;
|
||||
current_procinfo.CurrTrueLabel:=current_procinfo.CurrFalseLabel;
|
||||
current_procinfo.CurrFalseLabel:=hl;
|
||||
end
|
||||
else
|
||||
if not handle_locjump then
|
||||
begin
|
||||
{ the second pass could change the location of left }
|
||||
{ if it is a register variable, so we've to do }
|
||||
@ -255,18 +239,44 @@ interface
|
||||
location.resflags:=left.location.resflags;
|
||||
inverse_flags(location.resflags);
|
||||
end;
|
||||
LOC_CREFERENCE,
|
||||
LOC_REFERENCE:
|
||||
begin
|
||||
{$ifndef cpu64bitalu}
|
||||
if is_64bit(resultdef) then
|
||||
begin
|
||||
hreg:=cg.GetIntRegister(current_asmdata.CurrAsmList,OS_32);
|
||||
tcgx86(cg).make_simple_ref(current_asmdata.CurrAsmList,left.location.reference);
|
||||
cg.a_load_ref_reg(current_asmdata.CurrAsmList,OS_32,OS_32,left.location.reference,hreg);
|
||||
inc(left.location.reference.offset,4);
|
||||
cg.a_op_ref_reg(current_asmdata.CurrAsmList,OP_OR,OS_32,left.location.reference,hreg);
|
||||
end
|
||||
else
|
||||
{$endif cpu64bitalu}
|
||||
emit_const_ref(A_CMP, TCGSize2Opsize[opsize], 0, left.location.reference);
|
||||
location_reset(location,LOC_FLAGS,OS_NO);
|
||||
location.resflags:=F_E;
|
||||
end;
|
||||
LOC_CONSTANT,
|
||||
LOC_REGISTER,
|
||||
LOC_CREGISTER,
|
||||
LOC_REFERENCE,
|
||||
LOC_CREFERENCE,
|
||||
LOC_SUBSETREG,
|
||||
LOC_CSUBSETREG,
|
||||
LOC_SUBSETREF,
|
||||
LOC_CSUBSETREF :
|
||||
begin
|
||||
hlcg.location_force_reg(current_asmdata.CurrAsmList,left.location,left.resultdef,resultdef,true);
|
||||
emit_reg_reg(A_TEST,TCGSize2Opsize[opsize],left.location.register,left.location.register);
|
||||
{$ifndef cpu64bitalu}
|
||||
if is_64bit(resultdef) then
|
||||
begin
|
||||
hlcg.location_force_reg(current_asmdata.CurrAsmList,left.location,left.resultdef,resultdef,false);
|
||||
emit_reg_reg(A_OR,S_L,left.location.register64.reghi,left.location.register64.reglo);
|
||||
end
|
||||
else
|
||||
{$endif cpu64bitalu}
|
||||
begin
|
||||
hlcg.location_force_reg(current_asmdata.CurrAsmList,left.location,left.resultdef,resultdef,true);
|
||||
emit_reg_reg(A_TEST,TCGSize2Opsize[opsize],left.location.register,left.location.register);
|
||||
end;
|
||||
location_reset(location,LOC_FLAGS,OS_NO);
|
||||
location.resflags:=F_E;
|
||||
end;
|
||||
|
Loading…
Reference in New Issue
Block a user