+ tcgllvm.a_label() and tcgllvm.a_jmp_always(). Special for llvm: every

basic block must end with a terminator instruciton (such as a branch) ->
    when emitting a label, check whether the previous instruction is a
    terminator instruction and if not, add an unconditional branch to the
    label we are adding.
   o Implemented at the tcg instead of at the thlcgobj level because
    a) these methods don't need any high level type information
    b) implementing them in thlcgobj would require making thlcg.a_label()
       virtual and ensuring that no-one ever calls cg.a_label() in any
       generic code

git-svn-id: branches/hlcgllvm@26038 -
This commit is contained in:
Jonas Maebe 2013-11-11 11:15:20 +00:00
parent 7db9d4c7e9
commit d245228ba6
2 changed files with 28 additions and 1 deletions

View File

@ -28,11 +28,13 @@ interface
uses
globtype,parabase,
cgbase,cgutils,cgobj,cghlcpu,
llvmbase,llvminfo,aasmtai,aasmdata,aasmllvm;
llvmbase,llvminfo,aasmbase,aasmtai,aasmdata,aasmllvm;
type
tcgllvm=class(thlbasecgcpu)
public
procedure a_label(list : TAsmList;l : tasmlabel);override;
procedure a_jmp_always(list: TAsmList; l: tasmlabel); override;
procedure init_register_allocators;override;
procedure done_register_allocators;override;
function getintregister(list:TAsmList;size:Tcgsize):Tregister;override;
@ -54,6 +56,26 @@ implementation
Assembler code
****************************************************************************}
procedure tcgllvm.a_label(list: TAsmList; l: tasmlabel);
begin
{ in llvm, every block must end with a terminator instruction, such as
a branch -> if the previous instruction is not a terminator instruction,
add an unconditional branch to the next block (= the one starting with
this label) }
if not assigned(list.last) or
(tai(list.Last).typ<>ait_llvmins) or
not(taillvm(list.Last).llvmopcode in llvmterminatoropcodes) then
a_jmp_always(list,l);
inherited;
end;
procedure tcgllvm.a_jmp_always(list: TAsmList; l: tasmlabel);
begin
list.concat(taillvm.op_lab(la_br,l));
end;
procedure tcgllvm.init_register_allocators;
begin
inherited init_register_allocators;

View File

@ -69,6 +69,11 @@ interface
la_type { type definition }
);
const
llvmterminatoropcodes = [la_ret, la_br, la_switch, la_indirectbr,
la_invoke, la_resume,
la_unreachable];
type
tllvmfpcmp = (
lfc_false,