mirror of
https://gitlab.com/freepascal.org/fpc/source.git
synced 2025-08-28 19:02:05 +02:00
+ LLVM support for library init/fini routines
git-svn-id: branches/debug_eh@42108 -
This commit is contained in:
parent
9f18cbf5d6
commit
5473f4fc44
@ -151,6 +151,8 @@ interface
|
||||
llvmdefs : THashSet; { defs added for llvm-specific reasons (not saved/restored) }
|
||||
llvmusedsyms : TFPObjectList; { a list of asmsymbols and their defs that need to be added to llvm.used (so they're not removed by llvm optimisation passes nor by the linker) }
|
||||
llvmcompilerusedsyms : TFPObjectList; { a list of asmsymbols and their defs that need to be added to llvm.compiler.used (so they're not removed by llvm optimisation passes) }
|
||||
llvminitprocs,
|
||||
llvmfiniprocs : TFPList;
|
||||
{$endif llvm}
|
||||
ansistrdef : tobject; { an ansistring def redefined for the current module }
|
||||
wpoinfo : tunitwpoinfobase; { whole program optimization-related information that is generated during the current run for this unit }
|
||||
@ -598,6 +600,8 @@ implementation
|
||||
llvmdefs:=THashSet.Create(64,true,false);
|
||||
llvmusedsyms:=TFPObjectList.Create(true);
|
||||
llvmcompilerusedsyms:=TFPObjectList.Create(true);
|
||||
llvminitprocs:=TFPList.Create;
|
||||
llvmfiniprocs:=TFPList.Create;
|
||||
{$endif llvm}
|
||||
ansistrdef:=nil;
|
||||
wpoinfo:=nil;
|
||||
@ -727,6 +731,8 @@ implementation
|
||||
llvmdefs.free;
|
||||
llvmusedsyms.free;
|
||||
llvmcompilerusedsyms.free;
|
||||
llvminitprocs.free;
|
||||
llvmfiniprocs.free;
|
||||
{$endif llvm}
|
||||
ansistrdef:=nil;
|
||||
wpoinfo.free;
|
||||
@ -801,6 +807,10 @@ implementation
|
||||
llvmusedsyms:=TFPObjectList.Create(true);
|
||||
llvmcompilerusedsyms.free;
|
||||
llvmcompilerusedsyms:=TFPObjectList.Create(true);
|
||||
llvminitprocs.free;
|
||||
llvminitprocs:=TFPList.Create;
|
||||
llvmfiniprocs.free;
|
||||
llvmfiniprocs:=TFPList.Create;
|
||||
{$endif llvm}
|
||||
wpoinfo.free;
|
||||
wpoinfo:=nil;
|
||||
|
@ -35,11 +35,14 @@ interface
|
||||
tllvmnodeutils = class(tnodeutils)
|
||||
strict protected
|
||||
class procedure insertbsssym(list: tasmlist; sym: tstaticvarsym; size: asizeint; varalign: shortint); override;
|
||||
class procedure InsertUsedList(var usedsyms: tfpobjectlist; const usedsymsname: TSymstr);
|
||||
class procedure InsertUsedList(var usedsyms: tfpobjectlist; const usedsymsname: TSymStr);
|
||||
class procedure InsertInitFiniList(var procdefs: tfplist; const initfinisymsname: TSymStr);
|
||||
public
|
||||
class procedure InsertObjectInfo; override;
|
||||
class procedure RegisterUsedAsmSym(sym: TAsmSymbol; def: tdef; compileronly: boolean); override;
|
||||
class procedure GenerateObjCImageInfo; override;
|
||||
class procedure RegisterModuleInitFunction(pd: tprocdef); override;
|
||||
class procedure RegisterModuleFiniFunction(pd: tprocdef); override;
|
||||
end;
|
||||
|
||||
|
||||
@ -50,7 +53,7 @@ implementation
|
||||
aasmtai,cpubase,llvmbase,aasmllvm,
|
||||
aasmcnst,nllvmtcon,
|
||||
symbase,symtable,defutil,
|
||||
llvmtype,
|
||||
llvmtype,llvmdef,
|
||||
objcasm;
|
||||
|
||||
class procedure tllvmnodeutils.insertbsssym(list: tasmlist; sym: tstaticvarsym; size: asizeint; varalign: shortint);
|
||||
@ -156,6 +159,50 @@ implementation
|
||||
end;
|
||||
|
||||
|
||||
class procedure tllvmnodeutils.InsertInitFiniList(var procdefs: tfplist; const initfinisymsname: TSymStr);
|
||||
var
|
||||
itemdef: trecorddef;
|
||||
arraydef: tarraydef;
|
||||
pd: tprocdef;
|
||||
fields: array[0..2] of tdef;
|
||||
tcb: ttai_typedconstbuilder;
|
||||
i: longint;
|
||||
begin
|
||||
if procdefs.count<>0 then
|
||||
begin
|
||||
pd:=tprocdef(procdefs[0]);
|
||||
fields[0]:=s32inttype;
|
||||
fields[1]:=pd.getcopyas(procvardef,pc_address_only,'');
|
||||
fields[2]:=voidpointertype;
|
||||
itemdef:=llvmgettemprecorddef(fields,C_alignment,
|
||||
targetinfos[target_info.system]^.alignment.recordalignmin,
|
||||
targetinfos[target_info.system]^.alignment.maxCrecordalign);
|
||||
include(itemdef.defoptions,df_llvm_no_struct_packing);
|
||||
tcb:=ctai_typedconstbuilder.create([tcalo_new_section]);
|
||||
tllvmtai_typedconstbuilder(tcb).appendingdef:=true;
|
||||
arraydef:=carraydef.getreusable(itemdef,procdefs.Count);
|
||||
tcb.maybe_begin_aggregate(arraydef);
|
||||
for i:=0 to procdefs.count-1 do
|
||||
begin
|
||||
tcb.maybe_begin_aggregate(itemdef);
|
||||
tcb.emit_ord_const(65535,s32inttype);
|
||||
tcb.emit_procdef_const(tprocdef(procdefs[i]));
|
||||
tcb.emit_tai(Tai_const.Create_sym(nil),voidpointertype);
|
||||
tcb.maybe_end_aggregate(itemdef);
|
||||
end;
|
||||
tcb.maybe_end_aggregate(arraydef);
|
||||
current_asmdata.AsmLists[al_globals].concatlist(
|
||||
tcb.get_final_asmlist(
|
||||
current_asmdata.DefineAsmSymbol(
|
||||
initfinisymsname,AB_GLOBAL,AT_DATA,arraydef),arraydef,sec_data,
|
||||
initfinisymsname,voidpointertype.alignment
|
||||
)
|
||||
);
|
||||
tcb.free;
|
||||
end;
|
||||
end;
|
||||
|
||||
|
||||
class procedure tllvmnodeutils.InsertObjectInfo;
|
||||
begin
|
||||
inherited;
|
||||
@ -164,6 +211,10 @@ implementation
|
||||
InsertUsedList(current_module.llvmcompilerusedsyms,'llvm.compiler.used');
|
||||
{ add the llvm.used array }
|
||||
InsertUsedList(current_module.llvmusedsyms,'llvm.used');
|
||||
{ add the llvm.global_ctors array }
|
||||
InsertInitFiniList(current_module.llvminitprocs,'llvm.global_ctors');
|
||||
{ add the llvm.global_dtors array }
|
||||
InsertInitFiniList(current_module.llvmfiniprocs,'llvm.global_dtors');
|
||||
|
||||
{ add "type xx = .." statements for all used recorddefs }
|
||||
with TLLVMTypeInfo.Create do
|
||||
@ -244,6 +295,18 @@ implementation
|
||||
end;
|
||||
|
||||
|
||||
class procedure tllvmnodeutils.RegisterModuleInitFunction(pd: tprocdef);
|
||||
begin
|
||||
current_module.llvminitprocs.add(pd);
|
||||
end;
|
||||
|
||||
|
||||
class procedure tllvmnodeutils.RegisterModuleFiniFunction(pd: tprocdef);
|
||||
begin
|
||||
current_module.llvmfiniprocs.add(pd);
|
||||
end;
|
||||
|
||||
|
||||
begin
|
||||
cnodeutils:=tllvmnodeutils;
|
||||
end.
|
||||
|
Loading…
Reference in New Issue
Block a user