mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-04-13 06:29:32 +02:00
+ introduced the use of asm labels for WebAssembly. Resolve them in
tcpuprocinfo.postprocess_code. Use them when generating code for the 'continue' label jumps.
This commit is contained in:
parent
e1698a5969
commit
01dc62b127
@ -196,6 +196,9 @@ interface
|
||||
TAsmList with loadsym/loadref/const_symbol (PFV) }
|
||||
refs : longint;
|
||||
public
|
||||
{$ifdef wasm}
|
||||
nestingdepth : longint;
|
||||
{$endif wasm}
|
||||
{ on avr the compiler needs to replace cond. jumps with too large offsets
|
||||
so we have to store an offset somewhere to calculate jump distances }
|
||||
{$ifdef AVR}
|
||||
@ -337,6 +340,9 @@ implementation
|
||||
typ:=_typ;
|
||||
{ used to remove unused labels from the al_procedures }
|
||||
refs:=0;
|
||||
{$ifdef wasm}
|
||||
nestingdepth:=-1;
|
||||
{$endif wasm}
|
||||
end;
|
||||
|
||||
|
||||
|
@ -379,6 +379,123 @@ implementation
|
||||
end;
|
||||
end;
|
||||
|
||||
procedure resolve_labels_pass1(asmlist: TAsmList);
|
||||
var
|
||||
hp: tai;
|
||||
lastinstr: taicpu;
|
||||
cur_nesting_depth: longint;
|
||||
lbl: tai_label;
|
||||
begin
|
||||
cur_nesting_depth:=0;
|
||||
lastinstr:=nil;
|
||||
hp:=tai(asmlist.first);
|
||||
while assigned(hp) do
|
||||
begin
|
||||
case hp.typ of
|
||||
ait_instruction:
|
||||
begin
|
||||
lastinstr:=taicpu(hp);
|
||||
case lastinstr.opcode of
|
||||
a_block,
|
||||
a_loop,
|
||||
a_if,
|
||||
a_try:
|
||||
inc(cur_nesting_depth);
|
||||
|
||||
a_end_block,
|
||||
a_end_loop,
|
||||
a_end_if,
|
||||
a_end_try:
|
||||
begin
|
||||
dec(cur_nesting_depth);
|
||||
if cur_nesting_depth<0 then
|
||||
internalerror(2021102001);
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
ait_label:
|
||||
begin
|
||||
lbl:=tai_label(hp);
|
||||
lbl.labsym.nestingdepth:=-1;
|
||||
if assigned(lastinstr) then
|
||||
begin
|
||||
if lastinstr.opcode=a_loop then
|
||||
lbl.labsym.nestingdepth:=cur_nesting_depth
|
||||
else if lastinstr.opcode in [a_end_block,a_end_try,a_end_if] then
|
||||
lbl.labsym.nestingdepth:=cur_nesting_depth+1;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
hp:=tai(hp.Next);
|
||||
end;
|
||||
if cur_nesting_depth<>0 then
|
||||
internalerror(2021102002);
|
||||
end;
|
||||
|
||||
procedure resolve_labels_pass2(asmlist: TAsmList);
|
||||
var
|
||||
hp: tai;
|
||||
instr: taicpu;
|
||||
cur_nesting_depth: longint;
|
||||
begin
|
||||
cur_nesting_depth:=0;
|
||||
hp:=tai(asmlist.first);
|
||||
while assigned(hp) do
|
||||
begin
|
||||
if hp.typ=ait_instruction then
|
||||
begin
|
||||
instr:=taicpu(hp);
|
||||
case instr.opcode of
|
||||
a_block,
|
||||
a_loop,
|
||||
a_if,
|
||||
a_try:
|
||||
inc(cur_nesting_depth);
|
||||
|
||||
a_end_block,
|
||||
a_end_loop,
|
||||
a_end_if,
|
||||
a_end_try:
|
||||
begin
|
||||
dec(cur_nesting_depth);
|
||||
if cur_nesting_depth<0 then
|
||||
internalerror(2021102003);
|
||||
end;
|
||||
|
||||
a_br,
|
||||
a_br_if:
|
||||
begin
|
||||
if instr.ops<>1 then
|
||||
internalerror(2021102004);
|
||||
if instr.oper[0]^.typ=top_ref then
|
||||
begin
|
||||
if not assigned(instr.oper[0]^.ref^.symbol) then
|
||||
internalerror(2021102005);
|
||||
if (instr.oper[0]^.ref^.base<>NR_NO) or
|
||||
(instr.oper[0]^.ref^.index<>NR_NO) or
|
||||
(instr.oper[0]^.ref^.offset<>0) then
|
||||
internalerror(2021102006);
|
||||
if instr.oper[0]^.ref^.symbol.nestingdepth=-1 then
|
||||
internalerror(2021102007);
|
||||
instr.loadconst(0,cur_nesting_depth-instr.oper[0]^.ref^.symbol.nestingdepth);
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
hp:=tai(hp.Next);
|
||||
end;
|
||||
if cur_nesting_depth<>0 then
|
||||
internalerror(2021102008);
|
||||
end;
|
||||
|
||||
procedure resolve_labels(asmlist: TAsmList);
|
||||
begin
|
||||
if not assigned(asmlist) then
|
||||
exit;
|
||||
resolve_labels_pass1(asmlist);
|
||||
resolve_labels_pass2(asmlist);
|
||||
end;
|
||||
|
||||
var
|
||||
templist : TAsmList;
|
||||
l : TWasmLocal;
|
||||
@ -404,6 +521,8 @@ implementation
|
||||
|
||||
replace_local_frame_pointer(aktproccode);
|
||||
|
||||
resolve_labels(aktproccode);
|
||||
|
||||
inherited postprocess_code;
|
||||
end;
|
||||
|
||||
|
@ -56,9 +56,6 @@ uses
|
||||
function is_methodptr_like_type(d:tdef): boolean;
|
||||
public
|
||||
br_blocks: integer;
|
||||
loopContBr: integer; // the value is different depending of the condition test
|
||||
// if it's in the beggning the jump should be done to the loop (1)
|
||||
// if the condition at the end, the jump should done to the end of block (0)
|
||||
loopBreakBr: integer;
|
||||
exitBr: integer;
|
||||
raiseBr: integer; // raiseBr is only used in branchful exceptions mode (ts_wasm_bf_exceptions)
|
||||
@ -1804,7 +1801,7 @@ implementation
|
||||
if l=current_procinfo.CurrBreakLabel then
|
||||
list.concat(taicpu.op_const(a_br,br_blocks-loopBreakBr))
|
||||
else if l=current_procinfo.CurrContinueLabel then
|
||||
list.concat(taicpu.op_const(a_br,br_blocks-loopContBr))
|
||||
list.concat(taicpu.op_sym(a_br,l))
|
||||
else if l=current_procinfo.CurrExitLabel then
|
||||
list.concat(taicpu.op_const(a_br,br_blocks-exitBr))
|
||||
else
|
||||
|
@ -131,7 +131,6 @@ implementation
|
||||
oldclabel,oldblabel : tasmlabel;
|
||||
truelabel,falselabel : tasmlabel;
|
||||
oldflowcontrol : tflowcontrol;
|
||||
oldloopcontbroffset: Integer;
|
||||
oldloopbreakbroffset: Integer;
|
||||
begin
|
||||
location_reset(location,LOC_VOID,OS_NO);
|
||||
@ -142,7 +141,6 @@ implementation
|
||||
|
||||
oldflowcontrol:=flowcontrol;
|
||||
|
||||
oldloopcontbroffset:=thlcgwasm(hlcg).loopContBr;
|
||||
oldloopbreakbroffset:=thlcgwasm(hlcg).loopBreakBr;
|
||||
oldclabel:=current_procinfo.CurrContinueLabel;
|
||||
oldblabel:=current_procinfo.CurrBreakLabel;
|
||||
@ -158,10 +156,9 @@ implementation
|
||||
|
||||
if lnf_testatbegin in loopflags then
|
||||
begin
|
||||
hlcg.a_label(current_asmdata.CurrAsmList,lcont);
|
||||
pass_generate_code_condition;
|
||||
thlcgwasm(hlcg).loopContBr:=thlcgwasm(hlcg).br_blocks;
|
||||
end else
|
||||
thlcgwasm(hlcg).loopContBr:=thlcgwasm(hlcg).br_blocks+1;
|
||||
end;
|
||||
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_block));
|
||||
thlcgwasm(hlcg).incblock;
|
||||
@ -176,9 +173,11 @@ implementation
|
||||
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
||||
thlcgwasm(hlcg).decblock;
|
||||
if not (lnf_testatbegin in loopflags) then begin
|
||||
pass_generate_code_condition;
|
||||
end;
|
||||
if not (lnf_testatbegin in loopflags) then
|
||||
begin
|
||||
hlcg.a_label(current_asmdata.CurrAsmList,lcont);
|
||||
pass_generate_code_condition;
|
||||
end;
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,0) ); // jump back to loop
|
||||
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_loop));
|
||||
@ -188,7 +187,6 @@ implementation
|
||||
|
||||
current_procinfo.CurrContinueLabel:=oldclabel;
|
||||
current_procinfo.CurrBreakLabel:=oldblabel;
|
||||
thlcgwasm(hlcg).loopContBr:=oldloopcontbroffset;
|
||||
thlcgwasm(hlcg).loopBreakBr:=oldloopbreakbroffset;
|
||||
|
||||
{ a break/continue in a while/repeat block can't be seen outside }
|
||||
@ -453,8 +451,7 @@ implementation
|
||||
afteronflowcontrol: tflowcontrol;
|
||||
oldCurrExitLabel,
|
||||
oldContinueLabel,
|
||||
oldBreakLabel: tasmlabel;
|
||||
oldLoopContBr: integer;
|
||||
oldBreakLabel, NewContinueLabel: tasmlabel;
|
||||
oldLoopBreakBr: integer;
|
||||
oldExitBr: integer;
|
||||
in_loop: Boolean;
|
||||
@ -464,7 +461,6 @@ implementation
|
||||
oldCurrExitLabel:=nil;
|
||||
oldContinueLabel:=nil;
|
||||
oldBreakLabel:=nil;
|
||||
oldLoopContBr:=0;
|
||||
oldLoopBreakBr:=0;
|
||||
oldExitBr:=0;
|
||||
location_reset(location,LOC_VOID,OS_NO);
|
||||
@ -560,9 +556,8 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
oldContinueLabel:=current_procinfo.CurrContinueLabel;
|
||||
oldLoopContBr:=thlcgwasm(hlcg).loopContBr;
|
||||
current_asmdata.getjumplabel(current_procinfo.CurrContinueLabel);
|
||||
thlcgwasm(hlcg).loopContBr:=thlcgwasm(hlcg).br_blocks;
|
||||
current_asmdata.getjumplabel(NewContinueLabel);
|
||||
current_procinfo.CurrContinueLabel:=NewContinueLabel;
|
||||
end;
|
||||
|
||||
secondpass(t1);
|
||||
@ -575,10 +570,12 @@ implementation
|
||||
{ exit the 'continue' block }
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
||||
thlcgwasm(hlcg).decblock;
|
||||
if in_loop then
|
||||
hlcg.a_label(current_asmdata.CurrAsmList,NewContinueLabel);
|
||||
if fc_continue in doobjectdestroyandreraisestate.newflowcontrol then
|
||||
begin
|
||||
hlcg.g_call_system_proc(current_asmdata.CurrAsmList,'fpc_doneexception',[],nil).resetiftemp;
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,thlcgwasm(hlcg).br_blocks-oldLoopContBr));
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br,oldContinueLabel));
|
||||
end;
|
||||
|
||||
{ exit the 'break' block }
|
||||
@ -604,7 +601,6 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
current_procinfo.CurrContinueLabel:=oldContinueLabel;
|
||||
thlcgwasm(hlcg).loopContBr:=oldLoopContBr;
|
||||
current_procinfo.CurrBreakLabel:=oldBreakLabel;
|
||||
thlcgwasm(hlcg).loopBreakBr:=oldLoopBreakBr;
|
||||
end;
|
||||
@ -645,8 +641,7 @@ implementation
|
||||
afteronflowcontrol: tflowcontrol;
|
||||
oldCurrExitLabel,
|
||||
oldContinueLabel,
|
||||
oldBreakLabel: tasmlabel;
|
||||
oldLoopContBr: integer;
|
||||
oldBreakLabel, NewContinueLabel: tasmlabel;
|
||||
oldLoopBreakBr: integer;
|
||||
oldExitBr: integer;
|
||||
oldRaiseBr: Integer;
|
||||
@ -657,7 +652,6 @@ implementation
|
||||
oldCurrExitLabel:=nil;
|
||||
oldContinueLabel:=nil;
|
||||
oldBreakLabel:=nil;
|
||||
oldLoopContBr:=0;
|
||||
oldLoopBreakBr:=0;
|
||||
oldExitBr:=0;
|
||||
oldRaiseBr:=0;
|
||||
@ -769,9 +763,8 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
oldContinueLabel:=current_procinfo.CurrContinueLabel;
|
||||
oldLoopContBr:=thlcgwasm(hlcg).loopContBr;
|
||||
current_asmdata.getjumplabel(current_procinfo.CurrContinueLabel);
|
||||
thlcgwasm(hlcg).loopContBr:=thlcgwasm(hlcg).br_blocks;
|
||||
current_asmdata.getjumplabel(NewContinueLabel);
|
||||
current_procinfo.CurrContinueLabel:=NewContinueLabel;
|
||||
end;
|
||||
|
||||
secondpass(t1);
|
||||
@ -784,10 +777,12 @@ implementation
|
||||
{ exit the 'continue' block }
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
||||
thlcgwasm(hlcg).decblock;
|
||||
if in_loop then
|
||||
hlcg.a_label(current_asmdata.CurrAsmList,NewContinueLabel);
|
||||
if fc_continue in doobjectdestroyandreraisestate.newflowcontrol then
|
||||
begin
|
||||
hlcg.g_call_system_proc(current_asmdata.CurrAsmList,'fpc_doneexception',[],nil).resetiftemp;
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,thlcgwasm(hlcg).br_blocks-oldLoopContBr));
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br,OldContinueLabel));
|
||||
end;
|
||||
|
||||
{ exit the 'break' block }
|
||||
@ -816,7 +811,6 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
current_procinfo.CurrContinueLabel:=oldContinueLabel;
|
||||
thlcgwasm(hlcg).loopContBr:=oldLoopContBr;
|
||||
current_procinfo.CurrBreakLabel:=oldBreakLabel;
|
||||
thlcgwasm(hlcg).loopBreakBr:=oldLoopBreakBr;
|
||||
end;
|
||||
@ -878,7 +872,6 @@ implementation
|
||||
oldCurrExitLabel,
|
||||
oldContinueLabel,
|
||||
oldBreakLabel: tasmlabel;
|
||||
oldLoopContBr: integer;
|
||||
oldLoopBreakBr: integer;
|
||||
oldExitBr: integer;
|
||||
finallyexceptionstate: tcgexceptionstatehandler.texceptionstate;
|
||||
@ -897,6 +890,17 @@ implementation
|
||||
thlcgwasm(hlcg).decstack(current_asmdata.CurrAsmList,1);
|
||||
end;
|
||||
|
||||
procedure generate_exceptreason_check_br(reason: tcgint; l: TAsmLabel);
|
||||
var
|
||||
reasonreg : tregister;
|
||||
begin
|
||||
reasonreg:=hlcg.getintregister(current_asmdata.CurrAsmList,exceptionreasontype);
|
||||
hlcg.g_exception_reason_load(current_asmdata.CurrAsmList,exceptionreasontype,exceptionreasontype,excepttemps.reasonbuf,reasonreg);
|
||||
thlcgwasm(hlcg).a_cmp_const_reg_stack(current_asmdata.CurrAsmList,exceptionreasontype,OC_EQ,reason,reasonreg);
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br_if,l));
|
||||
thlcgwasm(hlcg).decstack(current_asmdata.CurrAsmList,1);
|
||||
end;
|
||||
|
||||
begin
|
||||
location_reset(location,LOC_VOID,OS_NO);
|
||||
oldBreakLabel:=nil;
|
||||
@ -904,7 +908,6 @@ implementation
|
||||
continuefinallylabel:=nil;
|
||||
breakfinallylabel:=nil;
|
||||
oldLoopBreakBr:=0;
|
||||
oldLoopContBr:=0;
|
||||
|
||||
in_loop:=assigned(current_procinfo.CurrBreakLabel);
|
||||
|
||||
@ -957,10 +960,8 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
oldContinueLabel:=current_procinfo.CurrContinueLabel;
|
||||
oldLoopContBr:=thlcgwasm(hlcg).loopContBr;
|
||||
continuefinallylabel:=get_jump_out_of_try_finally_frame_label(finallyexceptionstate);
|
||||
current_procinfo.CurrContinueLabel:=continuefinallylabel;
|
||||
thlcgwasm(hlcg).loopContBr:=thlcgwasm(hlcg).br_blocks;
|
||||
end;
|
||||
|
||||
{ try code }
|
||||
@ -983,6 +984,8 @@ implementation
|
||||
{ exit the 'continue' block }
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
||||
thlcgwasm(hlcg).decblock;
|
||||
if in_loop then
|
||||
hlcg.a_label(current_asmdata.CurrAsmList,continuefinallylabel);
|
||||
{ exceptionreason:=4 (continue) }
|
||||
hlcg.g_exception_reason_save_const(current_asmdata.CurrAsmList,exceptionreasontype,4,excepttemps.reasonbuf);
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,2)); // jump to the 'finally' section
|
||||
@ -1029,7 +1032,7 @@ implementation
|
||||
if fc_break in finallyexceptionstate.newflowcontrol then
|
||||
generate_exceptreason_check_br(3,thlcgwasm(hlcg).br_blocks-oldLoopBreakBr);
|
||||
if fc_continue in finallyexceptionstate.newflowcontrol then
|
||||
generate_exceptreason_check_br(4,thlcgwasm(hlcg).br_blocks-oldLoopContBr);
|
||||
generate_exceptreason_check_br(4,oldContinueLabel);
|
||||
|
||||
cexceptionstatehandler.unget_exception_temps(current_asmdata.CurrAsmList,excepttemps);
|
||||
|
||||
@ -1041,7 +1044,6 @@ implementation
|
||||
if assigned(current_procinfo.CurrBreakLabel) then
|
||||
begin
|
||||
current_procinfo.CurrContinueLabel:=oldContinueLabel;
|
||||
thlcgwasm(hlcg).loopContBr:=oldLoopContBr;
|
||||
current_procinfo.CurrBreakLabel:=oldBreakLabel;
|
||||
thlcgwasm(hlcg).loopBreakBr:=oldLoopBreakBr;
|
||||
end;
|
||||
@ -1061,7 +1063,6 @@ implementation
|
||||
oldCurrExitLabel,
|
||||
oldContinueLabel,
|
||||
oldBreakLabel: tasmlabel;
|
||||
oldLoopContBr: integer;
|
||||
oldLoopBreakBr: integer;
|
||||
oldExitBr: integer;
|
||||
finallyexceptionstate: tcgexceptionstatehandler.texceptionstate;
|
||||
@ -1080,6 +1081,17 @@ implementation
|
||||
thlcgwasm(hlcg).decstack(current_asmdata.CurrAsmList,1);
|
||||
end;
|
||||
|
||||
procedure generate_exceptreason_check_br(reason: tcgint; l: tasmlabel);
|
||||
var
|
||||
reasonreg : tregister;
|
||||
begin
|
||||
reasonreg:=hlcg.getintregister(current_asmdata.CurrAsmList,exceptionreasontype);
|
||||
hlcg.g_exception_reason_load(current_asmdata.CurrAsmList,exceptionreasontype,exceptionreasontype,excepttemps.reasonbuf,reasonreg);
|
||||
thlcgwasm(hlcg).a_cmp_const_reg_stack(current_asmdata.CurrAsmList,exceptionreasontype,OC_EQ,reason,reasonreg);
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br_if,l));
|
||||
thlcgwasm(hlcg).decstack(current_asmdata.CurrAsmList,1);
|
||||
end;
|
||||
|
||||
procedure generate_exceptreason_throw(reason: tcgint);
|
||||
var
|
||||
reasonreg : tregister;
|
||||
@ -1102,7 +1114,6 @@ implementation
|
||||
continuefinallylabel:=nil;
|
||||
breakfinallylabel:=nil;
|
||||
oldLoopBreakBr:=0;
|
||||
oldLoopContBr:=0;
|
||||
|
||||
in_loop:=assigned(current_procinfo.CurrBreakLabel);
|
||||
|
||||
@ -1155,10 +1166,8 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
oldContinueLabel:=current_procinfo.CurrContinueLabel;
|
||||
oldLoopContBr:=thlcgwasm(hlcg).loopContBr;
|
||||
continuefinallylabel:=get_jump_out_of_try_finally_frame_label(finallyexceptionstate);
|
||||
current_procinfo.CurrContinueLabel:=continuefinallylabel;
|
||||
thlcgwasm(hlcg).loopContBr:=thlcgwasm(hlcg).br_blocks;
|
||||
end;
|
||||
|
||||
{ the inner 'try..end_try' block }
|
||||
@ -1194,6 +1203,8 @@ implementation
|
||||
{ exit the 'continue' block }
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
||||
thlcgwasm(hlcg).decblock;
|
||||
if in_loop then
|
||||
hlcg.a_label(current_asmdata.CurrAsmList,continuefinallylabel);
|
||||
{ exceptionreason:=4 (continue) }
|
||||
hlcg.g_exception_reason_save_const(current_asmdata.CurrAsmList,exceptionreasontype,4,excepttemps.reasonbuf);
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,2)); // jump to the 'finally' section
|
||||
@ -1240,7 +1251,7 @@ implementation
|
||||
if fc_break in finallyexceptionstate.newflowcontrol then
|
||||
generate_exceptreason_check_br(3,thlcgwasm(hlcg).br_blocks-oldLoopBreakBr);
|
||||
if fc_continue in finallyexceptionstate.newflowcontrol then
|
||||
generate_exceptreason_check_br(4,thlcgwasm(hlcg).br_blocks-oldLoopContBr);
|
||||
generate_exceptreason_check_br(4,oldContinueLabel);
|
||||
generate_exceptreason_throw(1);
|
||||
|
||||
cexceptionstatehandler.unget_exception_temps(current_asmdata.CurrAsmList,excepttemps);
|
||||
@ -1253,7 +1264,6 @@ implementation
|
||||
if assigned(current_procinfo.CurrBreakLabel) then
|
||||
begin
|
||||
current_procinfo.CurrContinueLabel:=oldContinueLabel;
|
||||
thlcgwasm(hlcg).loopContBr:=oldLoopContBr;
|
||||
current_procinfo.CurrBreakLabel:=oldBreakLabel;
|
||||
thlcgwasm(hlcg).loopBreakBr:=oldLoopBreakBr;
|
||||
end;
|
||||
@ -1268,7 +1278,6 @@ implementation
|
||||
oldCurrExitLabel,
|
||||
oldContinueLabel,
|
||||
oldBreakLabel: tasmlabel;
|
||||
oldLoopContBr: integer;
|
||||
oldLoopBreakBr: integer;
|
||||
oldExitBr: integer;
|
||||
oldRaiseBr: integer;
|
||||
@ -1288,6 +1297,17 @@ implementation
|
||||
thlcgwasm(hlcg).decstack(current_asmdata.CurrAsmList,1);
|
||||
end;
|
||||
|
||||
procedure generate_exceptreason_check_br(reason: tcgint; l: tasmsymbol);
|
||||
var
|
||||
reasonreg : tregister;
|
||||
begin
|
||||
reasonreg:=hlcg.getintregister(current_asmdata.CurrAsmList,exceptionreasontype);
|
||||
hlcg.g_exception_reason_load(current_asmdata.CurrAsmList,exceptionreasontype,exceptionreasontype,excepttemps.reasonbuf,reasonreg);
|
||||
thlcgwasm(hlcg).a_cmp_const_reg_stack(current_asmdata.CurrAsmList,exceptionreasontype,OC_EQ,reason,reasonreg);
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br_if,l));
|
||||
thlcgwasm(hlcg).decstack(current_asmdata.CurrAsmList,1);
|
||||
end;
|
||||
|
||||
procedure generate_exceptreason_reraise(reason: tcgint);
|
||||
var
|
||||
reasonreg : tregister;
|
||||
@ -1311,7 +1331,6 @@ implementation
|
||||
continuefinallylabel:=nil;
|
||||
breakfinallylabel:=nil;
|
||||
oldLoopBreakBr:=0;
|
||||
oldLoopContBr:=0;
|
||||
oldRaiseBr:=0;
|
||||
|
||||
in_loop:=assigned(current_procinfo.CurrBreakLabel);
|
||||
@ -1365,10 +1384,8 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
oldContinueLabel:=current_procinfo.CurrContinueLabel;
|
||||
oldLoopContBr:=thlcgwasm(hlcg).loopContBr;
|
||||
continuefinallylabel:=get_jump_out_of_try_finally_frame_label(finallyexceptionstate);
|
||||
current_procinfo.CurrContinueLabel:=continuefinallylabel;
|
||||
thlcgwasm(hlcg).loopContBr:=thlcgwasm(hlcg).br_blocks;
|
||||
end;
|
||||
|
||||
{ the inner 'try..end_try' block }
|
||||
@ -1406,6 +1423,8 @@ implementation
|
||||
{ exit the 'continue' block }
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
||||
thlcgwasm(hlcg).decblock;
|
||||
if in_loop then
|
||||
hlcg.a_label(current_asmdata.CurrAsmList,continuefinallylabel);
|
||||
{ exceptionreason:=4 (continue) }
|
||||
hlcg.g_exception_reason_save_const(current_asmdata.CurrAsmList,exceptionreasontype,4,excepttemps.reasonbuf);
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,2)); // jump to the 'finally' section
|
||||
@ -1455,7 +1474,7 @@ implementation
|
||||
if fc_break in finallyexceptionstate.newflowcontrol then
|
||||
generate_exceptreason_check_br(3,thlcgwasm(hlcg).br_blocks-oldLoopBreakBr);
|
||||
if fc_continue in finallyexceptionstate.newflowcontrol then
|
||||
generate_exceptreason_check_br(4,thlcgwasm(hlcg).br_blocks-oldLoopContBr);
|
||||
generate_exceptreason_check_br(4,oldContinueLabel);
|
||||
generate_exceptreason_reraise(1);
|
||||
|
||||
cexceptionstatehandler.unget_exception_temps(current_asmdata.CurrAsmList,excepttemps);
|
||||
@ -1468,7 +1487,6 @@ implementation
|
||||
if assigned(current_procinfo.CurrBreakLabel) then
|
||||
begin
|
||||
current_procinfo.CurrContinueLabel:=oldContinueLabel;
|
||||
thlcgwasm(hlcg).loopContBr:=oldLoopContBr;
|
||||
current_procinfo.CurrBreakLabel:=oldBreakLabel;
|
||||
thlcgwasm(hlcg).loopBreakBr:=oldLoopBreakBr;
|
||||
end;
|
||||
@ -1512,8 +1530,7 @@ implementation
|
||||
exceptlocreg: tregister;
|
||||
oldCurrExitLabel,
|
||||
oldContinueLabel,
|
||||
oldBreakLabel: tasmlabel;
|
||||
oldLoopContBr: integer;
|
||||
oldBreakLabel, NewContinueLabel: tasmlabel;
|
||||
oldLoopBreakBr: integer;
|
||||
oldExitBr: integer;
|
||||
in_loop: Boolean;
|
||||
@ -1523,7 +1540,6 @@ implementation
|
||||
oldCurrExitLabel:=nil;
|
||||
oldContinueLabel:=nil;
|
||||
oldBreakLabel:=nil;
|
||||
oldLoopContBr:=0;
|
||||
oldLoopBreakBr:=0;
|
||||
oldExitBr:=0;
|
||||
location_reset(location,LOC_VOID,OS_NO);
|
||||
@ -1587,9 +1603,8 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
oldContinueLabel:=current_procinfo.CurrContinueLabel;
|
||||
oldLoopContBr:=thlcgwasm(hlcg).loopContBr;
|
||||
current_asmdata.getjumplabel(current_procinfo.CurrContinueLabel);
|
||||
thlcgwasm(hlcg).loopContBr:=thlcgwasm(hlcg).br_blocks;
|
||||
current_asmdata.getjumplabel(NewContinueLabel);
|
||||
current_procinfo.CurrContinueLabel:=NewContinueLabel;
|
||||
end;
|
||||
|
||||
if assigned(right) then
|
||||
@ -1603,10 +1618,12 @@ implementation
|
||||
{ exit the 'continue' block }
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
||||
thlcgwasm(hlcg).decblock;
|
||||
if in_loop then
|
||||
hlcg.a_label(current_asmdata.CurrAsmList,NewContinueLabel);
|
||||
if fc_continue in doobjectdestroyandreraisestate.newflowcontrol then
|
||||
begin
|
||||
hlcg.g_call_system_proc(current_asmdata.CurrAsmList,'fpc_doneexception',[],nil).resetiftemp;
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,thlcgwasm(hlcg).br_blocks-oldLoopContBr));
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br,oldContinueLabel));
|
||||
end;
|
||||
|
||||
{ exit the 'break' block }
|
||||
@ -1632,7 +1649,6 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
current_procinfo.CurrContinueLabel:=oldContinueLabel;
|
||||
thlcgwasm(hlcg).loopContBr:=oldLoopContBr;
|
||||
current_procinfo.CurrBreakLabel:=oldBreakLabel;
|
||||
thlcgwasm(hlcg).loopBreakBr:=oldLoopBreakBr;
|
||||
end;
|
||||
@ -1667,8 +1683,7 @@ implementation
|
||||
exceptlocreg: tregister;
|
||||
oldCurrExitLabel,
|
||||
oldContinueLabel,
|
||||
oldBreakLabel: tasmlabel;
|
||||
oldLoopContBr: integer;
|
||||
oldBreakLabel, NewContinueLabel: tasmlabel;
|
||||
oldLoopBreakBr: integer;
|
||||
oldExitBr: integer;
|
||||
oldRaiseBr: Integer;
|
||||
@ -1679,7 +1694,6 @@ implementation
|
||||
oldCurrExitLabel:=nil;
|
||||
oldContinueLabel:=nil;
|
||||
oldBreakLabel:=nil;
|
||||
oldLoopContBr:=0;
|
||||
oldLoopBreakBr:=0;
|
||||
oldExitBr:=0;
|
||||
oldRaiseBr:=0;
|
||||
@ -1749,9 +1763,8 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
oldContinueLabel:=current_procinfo.CurrContinueLabel;
|
||||
oldLoopContBr:=thlcgwasm(hlcg).loopContBr;
|
||||
current_asmdata.getjumplabel(current_procinfo.CurrContinueLabel);
|
||||
thlcgwasm(hlcg).loopContBr:=thlcgwasm(hlcg).br_blocks;
|
||||
current_asmdata.getjumplabel(NewContinueLabel);
|
||||
current_procinfo.CurrContinueLabel:=NewContinueLabel;
|
||||
end;
|
||||
|
||||
if assigned(right) then
|
||||
@ -1765,10 +1778,12 @@ implementation
|
||||
{ exit the 'continue' block }
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_none(a_end_block));
|
||||
thlcgwasm(hlcg).decblock;
|
||||
if in_loop then
|
||||
hlcg.a_label(current_asmdata.CurrAsmList,NewContinueLabel);
|
||||
if fc_continue in doobjectdestroyandreraisestate.newflowcontrol then
|
||||
begin
|
||||
hlcg.g_call_system_proc(current_asmdata.CurrAsmList,'fpc_doneexception',[],nil).resetiftemp;
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_const(a_br,thlcgwasm(hlcg).br_blocks-oldLoopContBr));
|
||||
current_asmdata.CurrAsmList.concat(taicpu.op_sym(a_br,oldContinueLabel));
|
||||
end;
|
||||
|
||||
{ exit the 'break' block }
|
||||
@ -1797,7 +1812,6 @@ implementation
|
||||
if in_loop then
|
||||
begin
|
||||
current_procinfo.CurrContinueLabel:=oldContinueLabel;
|
||||
thlcgwasm(hlcg).loopContBr:=oldLoopContBr;
|
||||
current_procinfo.CurrBreakLabel:=oldBreakLabel;
|
||||
thlcgwasm(hlcg).loopBreakBr:=oldLoopBreakBr;
|
||||
end;
|
||||
|
Loading…
Reference in New Issue
Block a user