func reorderGlobalConstructors(m llvm.Module) error { ctors := m.NamedGlobal("llvm.global_ctors") if ctors.IsNil() { // No global constructors. return nil } init := ctors.Initializer() arraylength := init.Type().ArrayLength() zeroindex := []uint32{0} // The constructors are ordered within each package, but the packages // are in reverse order. We must go backwards through the constructors, // reassigning priorities. ceiling, npackagectors := -1, -1 for i := arraylength - 1; i >= 0; i-- { indices := []uint32{uint32(i)} ctor := llvm.ConstExtractValue(init, indices) priority := int(llvm.ConstExtractValue(ctor, zeroindex).ZExtValue()) if npackagectors == -1 { ceiling = arraylength - (i + 1) + priority npackagectors = priority } newpriority := ceiling - (npackagectors - priority) newpriorityvalue := llvm.ConstInt(llvm.Int32Type(), uint64(newpriority), false) ctor = llvm.ConstInsertValue(ctor, newpriorityvalue, zeroindex) if priority == 1 { npackagectors = -1 } init = llvm.ConstInsertValue(init, ctor, indices) } ctors.SetInitializer(init) return nil }
func getFflush(module llvm.Module) llvm.Value { fflush := module.NamedFunction("fflush") if fflush.IsNil() { voidPtr := llvm.PointerType(llvm.Int8Type(), 0) ftyp := llvm.FunctionType(llvm.Int32Type(), []llvm.Type{voidPtr}, false) fflush = llvm.AddFunction(module, "fflush", ftyp) fflush.SetFunctionCallConv(llvm.CCallConv) } return fflush }
func getPrintf(module llvm.Module) llvm.Value { printf := module.NamedFunction("printf") if printf.IsNil() { charPtr := llvm.PointerType(llvm.Int8Type(), 0) ftyp := llvm.FunctionType(llvm.Int32Type(), []llvm.Type{charPtr}, true) printf = llvm.AddFunction(module, "printf", ftyp) printf.SetFunctionCallConv(llvm.CCallConv) } return printf }
func getnewgoroutine(module llvm.Module) llvm.Value { fn := module.NamedFunction("llgo_newgoroutine") if fn.IsNil() { i8Ptr := llvm.PointerType(llvm.Int8Type(), 0) VoidFnPtr := llvm.PointerType(llvm.FunctionType( llvm.VoidType(), []llvm.Type{i8Ptr}, false), 0) i32 := llvm.Int32Type() fn_type := llvm.FunctionType( llvm.VoidType(), []llvm.Type{VoidFnPtr, i8Ptr, i32}, true) fn = llvm.AddFunction(module, "llgo_newgoroutine", fn_type) fn.SetFunctionCallConv(llvm.CCallConv) } return fn }