|
@@ -26,7 +26,8 @@ unit nwasmset;
|
|
|
interface
|
|
|
|
|
|
uses
|
|
|
- node,nset,ncgset;
|
|
|
+ node,nset,ncgset,
|
|
|
+ aasmbase;
|
|
|
|
|
|
type
|
|
|
|
|
@@ -41,12 +42,8 @@ interface
|
|
|
|
|
|
twasmcasenode = class(tcgcasenode)
|
|
|
private
|
|
|
- ElseBr: Integer;
|
|
|
- EndBr: Integer;
|
|
|
-
|
|
|
- function GetBranchBr(Block: TNode; out _Br: Integer): Boolean;
|
|
|
+ function GetBranchLabel(Block: TNode; out _Label: TAsmLabel): Boolean;
|
|
|
protected
|
|
|
- function BlockBr(id:longint):Integer;
|
|
|
procedure genlinearlist(hp : pcaselabel);override;
|
|
|
procedure genlinearcmplist(hp : pcaselabel);override;
|
|
|
public
|
|
@@ -80,14 +77,14 @@ implementation
|
|
|
TWASMCASENODE
|
|
|
*****************************************************************************}
|
|
|
|
|
|
- function twasmcasenode.GetBranchBr(Block: TNode; out _Br: Integer): Boolean;
|
|
|
+ function twasmcasenode.GetBranchLabel(Block: TNode; out _Label: TAsmLabel): Boolean;
|
|
|
begin
|
|
|
Result := True;
|
|
|
|
|
|
if not Assigned(Block) then
|
|
|
begin
|
|
|
{ Block doesn't exist / is empty }
|
|
|
- _Br := EndBr;
|
|
|
+ _Label := endlabel;
|
|
|
Exit;
|
|
|
end;
|
|
|
|
|
@@ -95,9 +92,9 @@ implementation
|
|
|
if not (cs_opt_level2 in current_settings.optimizerswitches) then
|
|
|
begin
|
|
|
Result := False;
|
|
|
+ current_asmdata.getjumplabel(_Label);
|
|
|
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_block));
|
|
|
thlcgwasm(hlcg).incblock;
|
|
|
- _Br:=thlcgwasm(hlcg).br_blocks;
|
|
|
Exit;
|
|
|
end;
|
|
|
|
|
@@ -106,7 +103,7 @@ implementation
|
|
|
case Block.nodetype of
|
|
|
nothingn:
|
|
|
begin
|
|
|
- _Br := EndBr;
|
|
|
+ _Label := endlabel;
|
|
|
Exit;
|
|
|
end;
|
|
|
goton:
|
|
@@ -139,15 +136,7 @@ implementation
|
|
|
Result := False;
|
|
|
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_block));
|
|
|
thlcgwasm(hlcg).incblock;
|
|
|
- _Br:=thlcgwasm(hlcg).br_blocks;
|
|
|
- end;
|
|
|
-
|
|
|
-
|
|
|
- function twasmcasenode.BlockBr(id: longint): Integer;
|
|
|
- begin
|
|
|
- if not assigned(blocks[id]) then
|
|
|
- internalerror(200411301);
|
|
|
- result:=pcaseblock(blocks[id])^.BlockBr;
|
|
|
+ current_asmdata.getjumplabel(_Label);
|
|
|
end;
|
|
|
|
|
|
|
|
@@ -177,16 +166,16 @@ implementation
|
|
|
genitem(t^.less);
|
|
|
{ do we need to test the first value? }
|
|
|
if first and (t^._low>get_min_value(left.resultdef)) then
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList,opsize,jmp_lt,tcgint(t^._low.svalue),hregister,thlcgwasm(hlcg).br_blocks-ElseBr);
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList,opsize,jmp_lt,tcgint(t^._low.svalue),hregister,elselabel);
|
|
|
if t^._low=t^._high then
|
|
|
begin
|
|
|
if t^._low-last=0 then
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList,opsize,OC_EQ,0,hregister,thlcgwasm(hlcg).br_blocks-BlockBr(t^.blockid))
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList,opsize,OC_EQ,0,hregister,blocklabel(t^.blockid))
|
|
|
else
|
|
|
begin
|
|
|
gensub(tcgint(t^._low.svalue-last.svalue));
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList,opsize,
|
|
|
- OC_EQ,tcgint(t^._low.svalue-last.svalue),scratch_reg,thlcgwasm(hlcg).br_blocks-BlockBr(t^.blockid));
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList,opsize,
|
|
|
+ OC_EQ,tcgint(t^._low.svalue-last.svalue),scratch_reg,blocklabel(t^.blockid));
|
|
|
end;
|
|
|
last:=t^._low;
|
|
|
end
|
|
@@ -207,10 +196,10 @@ implementation
|
|
|
{ present label then the lower limit can be checked }
|
|
|
{ immediately. else check the range in between: }
|
|
|
gensub(tcgint(t^._low.svalue-last.svalue));
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList, opsize,jmp_lt,tcgint(t^._low.svalue-last.svalue),scratch_reg,thlcgwasm(hlcg).br_blocks-ElseBr);
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList, opsize,jmp_lt,tcgint(t^._low.svalue-last.svalue),scratch_reg,elselabel);
|
|
|
end;
|
|
|
gensub(tcgint(t^._high.svalue-t^._low.svalue));
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList,opsize,jmp_le,tcgint(t^._high.svalue-t^._low.svalue),scratch_reg,thlcgwasm(hlcg).br_blocks-BlockBr(t^.blockid));
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList,opsize,jmp_le,tcgint(t^._high.svalue-t^._low.svalue),scratch_reg,blocklabel(t^.blockid));
|
|
|
last:=t^._high;
|
|
|
end;
|
|
|
first:=false;
|
|
@@ -252,15 +241,15 @@ implementation
|
|
|
begin
|
|
|
{ If only one label exists, we can greatly simplify the checks to a simple comparison }
|
|
|
if hp^._low=hp^._high then
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList, opsize, OC_EQ, tcgint(hp^._low.svalue), hregister, thlcgwasm(hlcg).br_blocks-BlockBr(hp^.blockid))
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList, opsize, OC_EQ, tcgint(hp^._low.svalue), hregister,blocklabel(hp^.blockid))
|
|
|
else
|
|
|
begin
|
|
|
scratch_reg:=hlcg.getintregister(current_asmdata.CurrAsmList,opsize);
|
|
|
gensub(tcgint(hp^._low.svalue));
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList, opsize, OC_BE, tcgint(hp^._high.svalue-hp^._low.svalue), hregister, thlcgwasm(hlcg).br_blocks-BlockBr(hp^.blockid))
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList, opsize, OC_BE, tcgint(hp^._high.svalue-hp^._low.svalue), hregister,blocklabel(hp^.blockid))
|
|
|
end;
|
|
|
end;
|
|
|
- current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,thlcgwasm(hlcg).br_blocks-ElseBr));
|
|
|
+ current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br,elselabel));
|
|
|
end;
|
|
|
end;
|
|
|
|
|
@@ -277,7 +266,7 @@ implementation
|
|
|
genitem(t^.less);
|
|
|
if t^._low=t^._high then
|
|
|
begin
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList, opsize, OC_EQ, tcgint(t^._low.svalue),hregister, thlcgwasm(hlcg).br_blocks-BlockBr(t^.blockid));
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList, opsize, OC_EQ, tcgint(t^._low.svalue),hregister, blocklabel(t^.blockid));
|
|
|
{ Reset last here, because we've only checked for one value and need to compare
|
|
|
for the next range both the lower and upper bound }
|
|
|
lastwasrange := false;
|
|
@@ -288,8 +277,8 @@ implementation
|
|
|
{ is even smaller then jump immediately to the }
|
|
|
{ ELSE-label }
|
|
|
if not lastwasrange or (t^._low-last>1) then
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList, opsize, jmp_lt, tcgint(t^._low.svalue), hregister, thlcgwasm(hlcg).br_blocks-ElseBr);
|
|
|
- thlcgwasm(hlcg).a_cmp_const_reg_br(current_asmdata.CurrAsmList, opsize, jmp_le, tcgint(t^._high.svalue), hregister, thlcgwasm(hlcg).br_blocks-BlockBr(t^.blockid));
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList, opsize, jmp_lt, tcgint(t^._low.svalue), hregister, elselabel);
|
|
|
+ thlcgwasm(hlcg).a_cmp_const_reg_label(current_asmdata.CurrAsmList, opsize, jmp_le, tcgint(t^._high.svalue), hregister, blocklabel(t^.blockid));
|
|
|
|
|
|
last:=t^._high;
|
|
|
lastwasrange := true;
|
|
@@ -302,7 +291,7 @@ implementation
|
|
|
last:=0;
|
|
|
lastwasrange:=false;
|
|
|
genitem(hp);
|
|
|
- current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,thlcgwasm(hlcg).br_blocks-ElseBr));
|
|
|
+ current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br,elselabel));
|
|
|
end;
|
|
|
|
|
|
|
|
@@ -317,16 +306,17 @@ implementation
|
|
|
oldflowcontrol := flowcontrol;
|
|
|
include(flowcontrol,fc_inflowcontrol);
|
|
|
|
|
|
+ current_asmdata.getjumplabel(endlabel);
|
|
|
+
|
|
|
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_block));
|
|
|
thlcgwasm(hlcg).incblock;
|
|
|
- EndBr:=thlcgwasm(hlcg).br_blocks;
|
|
|
|
|
|
{ Do some optimisation to deal with empty else blocks }
|
|
|
- ShortcutElse := GetBranchBr(elseblock, ElseBr);
|
|
|
+ ShortcutElse := GetBranchLabel(elseblock, elselabel);
|
|
|
|
|
|
for i:=blocks.count-1 downto 0 do
|
|
|
with pcaseblock(blocks[i])^ do
|
|
|
- shortcut := GetBranchBr(statement, BlockBr);
|
|
|
+ shortcut := GetBranchLabel(statement, blocklabel);
|
|
|
|
|
|
with_sign:=is_signed(left.resultdef);
|
|
|
if with_sign then
|
|
@@ -466,13 +456,15 @@ implementation
|
|
|
begin
|
|
|
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
|
|
thlcgwasm(hlcg).decblock;
|
|
|
+ hlcg.a_label(current_asmdata.CurrAsmList,blocklabel);
|
|
|
+
|
|
|
secondpass(statement);
|
|
|
{ don't come back to case line }
|
|
|
current_filepos:=current_asmdata.CurrAsmList.getlasttaifilepos^;
|
|
|
{$ifdef OLDREGVARS}
|
|
|
load_all_regvars(current_asmdata.CurrAsmList);
|
|
|
{$endif OLDREGVARS}
|
|
|
- current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,thlcgwasm(hlcg).br_blocks-EndBr));
|
|
|
+ current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br,endlabel));
|
|
|
end;
|
|
|
end;
|
|
|
|
|
@@ -481,6 +473,7 @@ implementation
|
|
|
begin
|
|
|
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
|
|
thlcgwasm(hlcg).decblock;
|
|
|
+ hlcg.a_label(current_asmdata.CurrAsmList,elselabel);
|
|
|
end;
|
|
|
|
|
|
if Assigned(elseblock) then
|
|
@@ -494,6 +487,7 @@ implementation
|
|
|
|
|
|
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
|
|
thlcgwasm(hlcg).decblock;
|
|
|
+ hlcg.a_label(current_asmdata.CurrAsmList,endlabel);
|
|
|
|
|
|
flowcontrol := oldflowcontrol + (flowcontrol - [fc_inflowcontrol]);
|
|
|
end;
|