aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
-rw-r--r--builder/build.go2
-rw-r--r--compiler/channel.go8
-rw-r--r--compiler/compiler.go46
-rw-r--r--compiler/defer.go19
-rw-r--r--compiler/interface.go16
-rw-r--r--compiler/llvm.go6
-rw-r--r--compiler/llvmutil/wordpack.go6
-rw-r--r--go.mod2
-rw-r--r--go.sum4
-rw-r--r--interp/memory.go4
-rw-r--r--transform/gc.go4
-rw-r--r--transform/llvm.go10
-rw-r--r--transform/stacksize.go2
13 files changed, 69 insertions, 60 deletions
diff --git a/builder/build.go b/builder/build.go
index bb2d634a9..7a6b9dbb9 100644
--- a/builder/build.go
+++ b/builder/build.go
@@ -1146,7 +1146,7 @@ func setGlobalValues(mod llvm.Module, globals map[string]map[string]string) erro
// Create the string value, which is a {ptr, len} pair.
zero := llvm.ConstInt(mod.Context().Int32Type(), 0, false)
- ptr := llvm.ConstGEP(buf, []llvm.Value{zero, zero})
+ ptr := llvm.ConstGEP(bufInitializer.Type(), buf, []llvm.Value{zero, zero})
if ptr.Type() != elementTypes[0] {
return fmt.Errorf("%s: not a string", globalName)
}
diff --git a/compiler/channel.go b/compiler/channel.go
index 5c3b6c596..81f845657 100644
--- a/compiler/channel.go
+++ b/compiler/channel.go
@@ -173,7 +173,7 @@ func (b *builder) createSelect(expr *ssa.Select) llvm.Value {
allocaType := llvm.ArrayType(b.ctx.Int8Type(), int(recvbufSize))
recvbufAlloca, _, _ := b.createTemporaryAlloca(allocaType, "select.recvbuf.alloca")
recvbufAlloca.SetAlignment(recvbufAlign)
- recvbuf = b.CreateGEP(recvbufAlloca, []llvm.Value{
+ recvbuf = b.CreateGEP(allocaType, recvbufAlloca, []llvm.Value{
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
}, "select.recvbuf")
@@ -184,13 +184,13 @@ func (b *builder) createSelect(expr *ssa.Select) llvm.Value {
statesAlloca, statesI8, statesSize := b.createTemporaryAlloca(statesAllocaType, "select.states.alloca")
for i, state := range selectStates {
// Set each slice element to the appropriate channel.
- gep := b.CreateGEP(statesAlloca, []llvm.Value{
+ gep := b.CreateGEP(statesAllocaType, statesAlloca, []llvm.Value{
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
llvm.ConstInt(b.ctx.Int32Type(), uint64(i), false),
}, "")
b.CreateStore(state, gep)
}
- statesPtr := b.CreateGEP(statesAlloca, []llvm.Value{
+ statesPtr := b.CreateGEP(statesAllocaType, statesAlloca, []llvm.Value{
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
}, "select.states")
@@ -204,7 +204,7 @@ func (b *builder) createSelect(expr *ssa.Select) llvm.Value {
chBlockAllocaType := llvm.ArrayType(b.getLLVMRuntimeType("channelBlockedList"), len(selectStates))
chBlockAlloca, chBlockAllocaPtr, chBlockSize := b.createTemporaryAlloca(chBlockAllocaType, "select.block.alloca")
chBlockLen := llvm.ConstInt(b.uintptrType, uint64(len(selectStates)), false)
- chBlockPtr := b.CreateGEP(chBlockAlloca, []llvm.Value{
+ chBlockPtr := b.CreateGEP(chBlockAllocaType, chBlockAlloca, []llvm.Value{
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
}, "select.block")
diff --git a/compiler/compiler.go b/compiler/compiler.go
index 7ab2fe4e9..c93b2e563 100644
--- a/compiler/compiler.go
+++ b/compiler/compiler.go
@@ -918,7 +918,7 @@ func (c *compilerContext) createEmbedGlobal(member *ssa.Global, global llvm.Valu
bufferGlobal.SetInitializer(bufferValue)
bufferGlobal.SetLinkage(llvm.InternalLinkage)
bufferGlobal.SetAlignment(1)
- slicePtr := llvm.ConstInBoundsGEP(bufferGlobal, []llvm.Value{
+ slicePtr := llvm.ConstInBoundsGEP(bufferValue.Type(), bufferGlobal, []llvm.Value{
llvm.ConstInt(c.uintptrType, 0, false),
llvm.ConstInt(c.uintptrType, 0, false),
})
@@ -990,7 +990,7 @@ func (c *compilerContext) createEmbedGlobal(member *ssa.Global, global llvm.Valu
// Create the slice object itself.
// Because embed.FS refers to it as *[]embed.file instead of a plain
// []embed.file, we have to store this as a global.
- slicePtr := llvm.ConstInBoundsGEP(sliceDataGlobal, []llvm.Value{
+ slicePtr := llvm.ConstInBoundsGEP(sliceDataInitializer.Type(), sliceDataGlobal, []llvm.Value{
llvm.ConstInt(c.uintptrType, 0, false),
llvm.ConstInt(c.uintptrType, 0, false),
})
@@ -1018,11 +1018,11 @@ func (c *compilerContext) createEmbedGlobal(member *ssa.Global, global llvm.Valu
func (c *compilerContext) getEmbedFileString(file *loader.EmbedFile) llvm.Value {
dataGlobalName := "embed/file_" + file.Hash
dataGlobal := c.mod.NamedGlobal(dataGlobalName)
+ dataGlobalType := llvm.ArrayType(c.ctx.Int8Type(), int(file.Size))
if dataGlobal.IsNil() {
- dataGlobalType := llvm.ArrayType(c.ctx.Int8Type(), int(file.Size))
dataGlobal = llvm.AddGlobal(c.mod, dataGlobalType, dataGlobalName)
}
- strPtr := llvm.ConstInBoundsGEP(dataGlobal, []llvm.Value{
+ strPtr := llvm.ConstInBoundsGEP(dataGlobalType, dataGlobal, []llvm.Value{
llvm.ConstInt(c.uintptrType, 0, false),
llvm.ConstInt(c.uintptrType, 0, false),
})
@@ -1601,7 +1601,7 @@ func (b *builder) createBuiltin(argTypes []types.Type, argValues []llvm.Value, c
// Note: the pointer is always of type *i8.
ptr := argValues[0]
len := argValues[1]
- return b.CreateGEP(ptr, []llvm.Value{len}, ""), nil
+ return b.CreateGEP(b.ctx.Int8Type(), ptr, []llvm.Value{len}, ""), nil
case "Alignof": // unsafe.Alignof
align := b.targetData.ABITypeAlignment(argValues[0].Type())
return llvm.ConstInt(b.uintptrType, uint64(align), false), nil
@@ -1911,7 +1911,8 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
llvm.ConstInt(b.ctx.Int32Type(), uint64(expr.Field), false),
}
- return b.CreateInBoundsGEP(val, indices, ""), nil
+ elementType := b.getLLVMType(expr.X.Type().Underlying().(*types.Pointer).Elem())
+ return b.CreateInBoundsGEP(elementType, val, indices, ""), nil
case *ssa.Function:
panic("function is not an expression")
case *ssa.Global:
@@ -1935,7 +1936,7 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
alloca, allocaPtr, allocaSize := b.createTemporaryAlloca(arrayType, "index.alloca")
b.CreateStore(array, alloca)
zero := llvm.ConstInt(b.ctx.Int32Type(), 0, false)
- ptr := b.CreateInBoundsGEP(alloca, []llvm.Value{zero, index}, "index.gep")
+ ptr := b.CreateInBoundsGEP(arrayType, alloca, []llvm.Value{zero, index}, "index.gep")
result := b.CreateLoad(arrayType.ElementType(), ptr, "index.load")
b.emitLifetimeEnd(allocaPtr, allocaSize)
return result, nil
@@ -1945,13 +1946,15 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
// Get buffer pointer and length
var bufptr, buflen llvm.Value
+ var bufType llvm.Type
switch ptrTyp := expr.X.Type().Underlying().(type) {
case *types.Pointer:
- typ := expr.X.Type().Underlying().(*types.Pointer).Elem().Underlying()
+ typ := ptrTyp.Elem().Underlying()
switch typ := typ.(type) {
case *types.Array:
bufptr = val
buflen = llvm.ConstInt(b.uintptrType, uint64(typ.Len()), false)
+ bufType = b.getLLVMType(typ)
// Check for nil pointer before calculating the address, from
// the spec:
// > For an operand x of type T, the address operation &x
@@ -1965,6 +1968,7 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
case *types.Slice:
bufptr = b.CreateExtractValue(val, 0, "indexaddr.ptr")
buflen = b.CreateExtractValue(val, 1, "indexaddr.len")
+ bufType = b.getLLVMType(ptrTyp.Elem())
default:
return llvm.Value{}, b.makeError(expr.Pos(), "todo: indexaddr: "+ptrTyp.String())
}
@@ -1982,9 +1986,9 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
index,
}
- return b.CreateInBoundsGEP(bufptr, indices, ""), nil
+ return b.CreateInBoundsGEP(bufType, bufptr, indices, ""), nil
case *types.Slice:
- return b.CreateInBoundsGEP(bufptr, []llvm.Value{index}, ""), nil
+ return b.CreateInBoundsGEP(bufType, bufptr, []llvm.Value{index}, ""), nil
default:
panic("unreachable")
}
@@ -2012,8 +2016,9 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
// Lookup byte
buf := b.CreateExtractValue(value, 0, "")
- bufPtr := b.CreateInBoundsGEP(buf, []llvm.Value{index}, "")
- return b.CreateLoad(b.ctx.Int8Type(), bufPtr, ""), nil
+ bufElemType := b.ctx.Int8Type()
+ bufPtr := b.CreateInBoundsGEP(bufElemType, buf, []llvm.Value{index}, "")
+ return b.CreateLoad(bufElemType, bufPtr, ""), nil
case *types.Map:
valueType := expr.Type()
if expr.CommaOk {
@@ -2146,7 +2151,8 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
switch typ := expr.X.Type().Underlying().(type) {
case *types.Pointer: // pointer to array
// slice an array
- length := typ.Elem().Underlying().(*types.Array).Len()
+ arrayType := typ.Elem().Underlying().(*types.Array)
+ length := arrayType.Len()
llvmLen := llvm.ConstInt(b.uintptrType, uint64(length), false)
if high.IsNil() {
high = llvmLen
@@ -2175,7 +2181,7 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
}
sliceLen := b.CreateSub(high, low, "slice.len")
- slicePtr := b.CreateInBoundsGEP(value, indices, "slice.ptr")
+ slicePtr := b.CreateInBoundsGEP(b.getLLVMType(arrayType), value, indices, "slice.ptr")
sliceCap := b.CreateSub(max, low, "slice.cap")
slice := b.ctx.ConstStruct([]llvm.Value{
@@ -2214,7 +2220,8 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
max = b.CreateTrunc(max, b.uintptrType, "")
}
- newPtr := b.CreateInBoundsGEP(oldPtr, []llvm.Value{low}, "")
+ ptrElemType := b.getLLVMType(typ.Elem())
+ newPtr := b.CreateInBoundsGEP(ptrElemType, oldPtr, []llvm.Value{low}, "")
newLen := b.CreateSub(high, low, "")
newCap := b.CreateSub(max, low, "")
slice := b.ctx.ConstStruct([]llvm.Value{
@@ -2254,7 +2261,7 @@ func (b *builder) createExpr(expr ssa.Value) (llvm.Value, error) {
high = b.CreateTrunc(high, b.uintptrType, "")
}
- newPtr := b.CreateInBoundsGEP(oldPtr, []llvm.Value{low}, "")
+ newPtr := b.CreateInBoundsGEP(b.ctx.Int8Type(), oldPtr, []llvm.Value{low}, "")
newLen := b.CreateSub(high, low, "")
str := llvm.Undef(b.getLLVMRuntimeType("_string"))
str = b.CreateInsertValue(str, newPtr, 0, "")
@@ -2717,14 +2724,15 @@ func (c *compilerContext) createConst(expr *ssa.Const) llvm.Value {
var strPtr llvm.Value
if str != "" {
objname := c.pkg.Path() + "$string"
- global := llvm.AddGlobal(c.mod, llvm.ArrayType(c.ctx.Int8Type(), len(str)), objname)
+ globalType := llvm.ArrayType(c.ctx.Int8Type(), len(str))
+ global := llvm.AddGlobal(c.mod, globalType, objname)
global.SetInitializer(c.ctx.ConstString(str, false))
global.SetLinkage(llvm.InternalLinkage)
global.SetGlobalConstant(true)
global.SetUnnamedAddr(true)
global.SetAlignment(1)
zero := llvm.ConstInt(c.ctx.Int32Type(), 0, false)
- strPtr = llvm.ConstInBoundsGEP(global, []llvm.Value{zero, zero})
+ strPtr = llvm.ConstInBoundsGEP(globalType, global, []llvm.Value{zero, zero})
} else {
strPtr = llvm.ConstNull(c.i8ptrType)
}
@@ -2844,7 +2852,7 @@ func (b *builder) createConvert(typeFrom, typeTo types.Type, value llvm.Value, p
// create a GEP that is not in bounds. However, we're
// talking about unsafe code here so the programmer has to
// be careful anyway.
- return b.CreateInBoundsGEP(origptr, []llvm.Value{index}, ""), nil
+ return b.CreateInBoundsGEP(b.ctx.Int8Type(), origptr, []llvm.Value{index}, ""), nil
}
}
}
diff --git a/compiler/defer.go b/compiler/defer.go
index 1f892e5ba..27e903319 100644
--- a/compiler/defer.go
+++ b/compiler/defer.go
@@ -407,7 +407,8 @@ func (b *builder) createDefer(instr *ssa.Defer) {
// createRunDefers emits code to run all deferred functions.
func (b *builder) createRunDefers() {
- deferType := llvm.PointerType(b.getLLVMRuntimeType("_defer"), 0)
+ deferType := b.getLLVMRuntimeType("_defer")
+ deferPtrType := llvm.PointerType(deferType, 0)
// Add a loop like the following:
// for stack != nil {
@@ -434,7 +435,7 @@ func (b *builder) createRunDefers() {
// Create loop head:
// for stack != nil {
b.SetInsertPointAtEnd(loophead)
- deferData := b.CreateLoad(deferType, b.deferPtr, "")
+ deferData := b.CreateLoad(deferPtrType, b.deferPtr, "")
stackIsNil := b.CreateICmp(llvm.IntEQ, deferData, llvm.ConstPointerNull(deferData.Type()), "stackIsNil")
b.CreateCondBr(stackIsNil, end, loop)
@@ -443,13 +444,13 @@ func (b *builder) createRunDefers() {
// stack = stack.next
// switch stack.callback {
b.SetInsertPointAtEnd(loop)
- nextStackGEP := b.CreateInBoundsGEP(deferData, []llvm.Value{
+ nextStackGEP := b.CreateInBoundsGEP(deferType, deferData, []llvm.Value{
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
llvm.ConstInt(b.ctx.Int32Type(), 1, false), // .next field
}, "stack.next.gep")
- nextStack := b.CreateLoad(deferType, nextStackGEP, "stack.next")
+ nextStack := b.CreateLoad(deferPtrType, nextStackGEP, "stack.next")
b.CreateStore(nextStack, b.deferPtr)
- gep := b.CreateInBoundsGEP(deferData, []llvm.Value{
+ gep := b.CreateInBoundsGEP(deferType, deferData, []llvm.Value{
llvm.ConstInt(b.ctx.Int32Type(), 0, false),
llvm.ConstInt(b.ctx.Int32Type(), 0, false), // .callback field
}, "callback.gep")
@@ -489,7 +490,7 @@ func (b *builder) createRunDefers() {
forwardParams := []llvm.Value{}
zero := llvm.ConstInt(b.ctx.Int32Type(), 0, false)
for i := 2; i < len(valueTypes); i++ {
- gep := b.CreateInBoundsGEP(deferredCallPtr, []llvm.Value{zero, llvm.ConstInt(b.ctx.Int32Type(), uint64(i), false)}, "gep")
+ gep := b.CreateInBoundsGEP(deferredCallType, deferredCallPtr, []llvm.Value{zero, llvm.ConstInt(b.ctx.Int32Type(), uint64(i), false)}, "gep")
forwardParam := b.CreateLoad(valueTypes[i], gep, "param")
forwardParams = append(forwardParams, forwardParam)
}
@@ -538,7 +539,7 @@ func (b *builder) createRunDefers() {
forwardParams := []llvm.Value{}
zero := llvm.ConstInt(b.ctx.Int32Type(), 0, false)
for i := range getParams(callback.Signature) {
- gep := b.CreateInBoundsGEP(deferredCallPtr, []llvm.Value{zero, llvm.ConstInt(b.ctx.Int32Type(), uint64(i+2), false)}, "gep")
+ gep := b.CreateInBoundsGEP(deferredCallType, deferredCallPtr, []llvm.Value{zero, llvm.ConstInt(b.ctx.Int32Type(), uint64(i+2), false)}, "gep")
forwardParam := b.CreateLoad(valueTypes[i+2], gep, "param")
forwardParams = append(forwardParams, forwardParam)
}
@@ -571,7 +572,7 @@ func (b *builder) createRunDefers() {
forwardParams := []llvm.Value{}
zero := llvm.ConstInt(b.ctx.Int32Type(), 0, false)
for i := 2; i < len(valueTypes); i++ {
- gep := b.CreateInBoundsGEP(deferredCallPtr, []llvm.Value{zero, llvm.ConstInt(b.ctx.Int32Type(), uint64(i), false)}, "")
+ gep := b.CreateInBoundsGEP(deferredCallType, deferredCallPtr, []llvm.Value{zero, llvm.ConstInt(b.ctx.Int32Type(), uint64(i), false)}, "")
forwardParam := b.CreateLoad(valueTypes[i], gep, "param")
forwardParams = append(forwardParams, forwardParam)
}
@@ -598,7 +599,7 @@ func (b *builder) createRunDefers() {
var argValues []llvm.Value
zero := llvm.ConstInt(b.ctx.Int32Type(), 0, false)
for i := 0; i < params.Len(); i++ {
- gep := b.CreateInBoundsGEP(deferredCallPtr, []llvm.Value{zero, llvm.ConstInt(b.ctx.Int32Type(), uint64(i+2), false)}, "gep")
+ gep := b.CreateInBoundsGEP(deferredCallType, deferredCallPtr, []llvm.Value{zero, llvm.ConstInt(b.ctx.Int32Type(), uint64(i+2), false)}, "gep")
forwardParam := b.CreateLoad(valueTypes[i+2], gep, "param")
argValues = append(argValues, forwardParam)
}
diff --git a/compiler/interface.go b/compiler/interface.go
index 72f8952d0..acb474f5c 100644
--- a/compiler/interface.go
+++ b/compiler/interface.go
@@ -122,19 +122,19 @@ func (c *compilerContext) makeStructTypeFields(typ *types.Struct) llvm.Value {
for i := 0; i < typ.NumFields(); i++ {
fieldGlobalValue := llvm.ConstNull(runtimeStructField)
fieldGlobalValue = llvm.ConstInsertValue(fieldGlobalValue, c.getTypeCode(typ.Field(i).Type()), []uint32{0})
- fieldName := c.makeGlobalArray([]byte(typ.Field(i).Name()), "reflect/types.structFieldName", c.ctx.Int8Type())
+ fieldNameType, fieldName := c.makeGlobalArray([]byte(typ.Field(i).Name()), "reflect/types.structFieldName", c.ctx.Int8Type())
fieldName.SetLinkage(llvm.PrivateLinkage)
fieldName.SetUnnamedAddr(true)
- fieldName = llvm.ConstGEP(fieldName, []llvm.Value{
+ fieldName = llvm.ConstGEP(fieldNameType, fieldName, []llvm.Value{
llvm.ConstInt(c.ctx.Int32Type(), 0, false),
llvm.ConstInt(c.ctx.Int32Type(), 0, false),
})
fieldGlobalValue = llvm.ConstInsertValue(fieldGlobalValue, fieldName, []uint32{1})
if typ.Tag(i) != "" {
- fieldTag := c.makeGlobalArray([]byte(typ.Tag(i)), "reflect/types.structFieldTag", c.ctx.Int8Type())
+ fieldTagType, fieldTag := c.makeGlobalArray([]byte(typ.Tag(i)), "reflect/types.structFieldTag", c.ctx.Int8Type())
fieldTag.SetLinkage(llvm.PrivateLinkage)
fieldTag.SetUnnamedAddr(true)
- fieldTag = llvm.ConstGEP(fieldTag, []llvm.Value{
+ fieldTag = llvm.ConstGEP(fieldTagType, fieldTag, []llvm.Value{
llvm.ConstInt(c.ctx.Int32Type(), 0, false),
llvm.ConstInt(c.ctx.Int32Type(), 0, false),
})
@@ -239,7 +239,7 @@ func (c *compilerContext) getTypeMethodSet(typ types.Type) llvm.Value {
zero := llvm.ConstInt(c.ctx.Int32Type(), 0, false)
if !global.IsNil() {
// the method set already exists
- return llvm.ConstGEP(global, []llvm.Value{zero, zero})
+ return llvm.ConstGEP(global.GlobalValueType(), global, []llvm.Value{zero, zero})
}
ms := c.program.MethodSets.MethodSet(typ)
@@ -272,7 +272,7 @@ func (c *compilerContext) getTypeMethodSet(typ types.Type) llvm.Value {
global.SetInitializer(value)
global.SetGlobalConstant(true)
global.SetLinkage(llvm.LinkOnceODRLinkage)
- return llvm.ConstGEP(global, []llvm.Value{zero, zero})
+ return llvm.ConstGEP(arrayType, global, []llvm.Value{zero, zero})
}
// getInterfaceMethodSet returns a global variable with the method set of the
@@ -288,7 +288,7 @@ func (c *compilerContext) getInterfaceMethodSet(typ types.Type) llvm.Value {
zero := llvm.ConstInt(c.ctx.Int32Type(), 0, false)
if !global.IsNil() {
// method set already exist, return it
- return llvm.ConstGEP(global, []llvm.Value{zero, zero})
+ return llvm.ConstGEP(global.GlobalValueType(), global, []llvm.Value{zero, zero})
}
// Every method is a *i8 reference indicating the signature of this method.
@@ -303,7 +303,7 @@ func (c *compilerContext) getInterfaceMethodSet(typ types.Type) llvm.Value {
global.SetInitializer(value)
global.SetGlobalConstant(true)
global.SetLinkage(llvm.LinkOnceODRLinkage)
- return llvm.ConstGEP(global, []llvm.Value{zero, zero})
+ return llvm.ConstGEP(value.Type(), global, []llvm.Value{zero, zero})
}
// getMethodSignatureName returns a unique name (that can be used as the name of
diff --git a/compiler/llvm.go b/compiler/llvm.go
index 9540bcc63..686d4d2b3 100644
--- a/compiler/llvm.go
+++ b/compiler/llvm.go
@@ -61,10 +61,10 @@ func (b *builder) emitPointerUnpack(ptr llvm.Value, valueTypes []llvm.Type) []ll
}
// makeGlobalArray creates a new LLVM global with the given name and integers as
-// contents, and returns the global.
+// contents, and returns the global and initializer type.
// Note that it is left with the default linkage etc., you should set
// linkage/constant/etc properties yourself.
-func (c *compilerContext) makeGlobalArray(buf []byte, name string, elementType llvm.Type) llvm.Value {
+func (c *compilerContext) makeGlobalArray(buf []byte, name string, elementType llvm.Type) (llvm.Type, llvm.Value) {
globalType := llvm.ArrayType(elementType, len(buf))
global := llvm.AddGlobal(c.mod, globalType, name)
value := llvm.Undef(globalType)
@@ -73,7 +73,7 @@ func (c *compilerContext) makeGlobalArray(buf []byte, name string, elementType l
value = llvm.ConstInsertValue(value, llvm.ConstInt(elementType, ch, false), []uint32{uint32(i)})
}
global.SetInitializer(value)
- return global
+ return globalType, global
}
// createObjectLayout returns a LLVM value (of type i8*) that describes where
diff --git a/compiler/llvmutil/wordpack.go b/compiler/llvmutil/wordpack.go
index 97b860457..2a4607c87 100644
--- a/compiler/llvmutil/wordpack.go
+++ b/compiler/llvmutil/wordpack.go
@@ -58,7 +58,7 @@ func EmitPointerPack(builder llvm.Builder, mod llvm.Module, prefix string, needs
llvm.ConstInt(ctx.Int32Type(), 0, false),
llvm.ConstInt(ctx.Int32Type(), uint64(i), false),
}
- gep := builder.CreateInBoundsGEP(packedAllocCast, indices, "")
+ gep := builder.CreateInBoundsGEP(packedType, packedAllocCast, indices, "")
builder.CreateStore(value, gep)
}
@@ -115,7 +115,7 @@ func EmitPointerPack(builder llvm.Builder, mod llvm.Module, prefix string, needs
llvm.ConstInt(ctx.Int32Type(), 0, false),
llvm.ConstInt(ctx.Int32Type(), uint64(i), false),
}
- gep := builder.CreateInBoundsGEP(packedAlloc, indices, "")
+ gep := builder.CreateInBoundsGEP(packedType, packedAlloc, indices, "")
builder.CreateStore(value, gep)
}
@@ -170,7 +170,7 @@ func EmitPointerUnpack(builder llvm.Builder, mod llvm.Module, ptr llvm.Value, va
llvm.ConstInt(ctx.Int32Type(), 0, false),
llvm.ConstInt(ctx.Int32Type(), uint64(i), false),
}
- gep := builder.CreateInBoundsGEP(packedAlloc, indices, "")
+ gep := builder.CreateInBoundsGEP(packedType, packedAlloc, indices, "")
values[i] = builder.CreateLoad(valueType, gep, "")
}
if !packedRawAlloc.IsNil() {
diff --git a/go.mod b/go.mod
index 26707a963..feb4e0d61 100644
--- a/go.mod
+++ b/go.mod
@@ -17,7 +17,7 @@ require (
golang.org/x/sys v0.0.0-20220829200755-d48e67d00261
golang.org/x/tools v0.1.11
gopkg.in/yaml.v2 v2.4.0
- tinygo.org/x/go-llvm v0.0.0-20220921144624-6c125b0aeda6
+ tinygo.org/x/go-llvm v0.0.0-20220921144624-dabbe3f30634
)
require (
diff --git a/go.sum b/go.sum
index e5c734cd4..907364f98 100644
--- a/go.sum
+++ b/go.sum
@@ -64,5 +64,5 @@ gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8
gopkg.in/yaml.v2 v2.4.0 h1:D8xgwECY7CYvx+Y2n4sBz93Jn9JRvxdiyyo8CTfuKaY=
gopkg.in/yaml.v2 v2.4.0/go.mod h1:RDklbk79AGWmwhnvt/jBztapEOGDOx6ZbXqjP6csGnQ=
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c h1:dUUwHk2QECo/6vqA44rthZ8ie2QXMNeKRTHCNY2nXvo=
-tinygo.org/x/go-llvm v0.0.0-20220921144624-6c125b0aeda6 h1:bJYUpmJrVm7Uluxh80qSivfeU3d9D4JNg5oJ+h9U+xc=
-tinygo.org/x/go-llvm v0.0.0-20220921144624-6c125b0aeda6/go.mod h1:GFbusT2VTA4I+l4j80b17KFK+6whv69Wtny5U+T8RR0=
+tinygo.org/x/go-llvm v0.0.0-20220921144624-dabbe3f30634 h1:hihbmHkJjalV4kGshoCF03P/G4IjoXcNAbzLblXLa/M=
+tinygo.org/x/go-llvm v0.0.0-20220921144624-dabbe3f30634/go.mod h1:GFbusT2VTA4I+l4j80b17KFK+6whv69Wtny5U+T8RR0=
diff --git a/interp/memory.go b/interp/memory.go
index 3a16b875e..2fa6f5cbc 100644
--- a/interp/memory.go
+++ b/interp/memory.go
@@ -646,8 +646,8 @@ func (v pointerValue) toLLVMValue(llvmType llvm.Type, mem *memoryView) (llvm.Val
if llvmValue.Type() != mem.r.i8ptrType {
llvmValue = llvm.ConstBitCast(llvmValue, mem.r.i8ptrType)
}
- llvmValue = llvm.ConstInBoundsGEP(llvmValue, []llvm.Value{
- llvm.ConstInt(llvmValue.Type().Context().Int32Type(), uint64(v.offset()), false),
+ llvmValue = llvm.ConstInBoundsGEP(mem.r.mod.Context().Int8Type(), llvmValue, []llvm.Value{
+ llvm.ConstInt(mem.r.mod.Context().Int32Type(), uint64(v.offset()), false),
})
}
diff --git a/transform/gc.go b/transform/gc.go
index 7a4e99aca..3870a6b60 100644
--- a/transform/gc.go
+++ b/transform/gc.go
@@ -223,7 +223,7 @@ func MakeGCStackSlots(mod llvm.Module) bool {
// Update stack start.
parent := builder.CreateLoad(stackChainStartType, stackChainStart, "")
- gep := builder.CreateGEP(stackObject, []llvm.Value{
+ gep := builder.CreateGEP(stackObjectType, stackObject, []llvm.Value{
llvm.ConstInt(ctx.Int32Type(), 0, false),
llvm.ConstInt(ctx.Int32Type(), 0, false),
}, "")
@@ -244,7 +244,7 @@ func MakeGCStackSlots(mod llvm.Module) bool {
builder.SetInsertPointBefore(insertionPoint)
// Extract a pointer to the appropriate section of the stack object.
- gep := builder.CreateGEP(stackObject, []llvm.Value{
+ gep := builder.CreateGEP(stackObjectType, stackObject, []llvm.Value{
llvm.ConstInt(ctx.Int32Type(), 0, false),
llvm.ConstInt(ctx.Int32Type(), uint64(2+i), false),
}, "")
diff --git a/transform/llvm.go b/transform/llvm.go
index 32ee95604..6716dd633 100644
--- a/transform/llvm.go
+++ b/transform/llvm.go
@@ -31,10 +31,10 @@ func hasUses(value llvm.Value) bool {
}
// makeGlobalArray creates a new LLVM global with the given name and integers as
-// contents, and returns the global.
+// contents, and returns the global and initializer type.
// Note that it is left with the default linkage etc., you should set
// linkage/constant/etc properties yourself.
-func makeGlobalArray(mod llvm.Module, bufItf interface{}, name string, elementType llvm.Type) llvm.Value {
+func makeGlobalArray(mod llvm.Module, bufItf interface{}, name string, elementType llvm.Type) (llvm.Type, llvm.Value) {
buf := reflect.ValueOf(bufItf)
globalType := llvm.ArrayType(elementType, buf.Len())
global := llvm.AddGlobal(mod, globalType, name)
@@ -44,7 +44,7 @@ func makeGlobalArray(mod llvm.Module, bufItf interface{}, name string, elementTy
value = llvm.ConstInsertValue(value, llvm.ConstInt(elementType, ch, false), []uint32{uint32(i)})
}
global.SetInitializer(value)
- return global
+ return globalType, global
}
// getGlobalBytes returns the slice contained in the array of the provided
@@ -64,8 +64,8 @@ func getGlobalBytes(global llvm.Value) []byte {
// function used for creating reflection sidetables, for example.
func replaceGlobalIntWithArray(mod llvm.Module, name string, buf interface{}) llvm.Value {
oldGlobal := mod.NamedGlobal(name)
- global := makeGlobalArray(mod, buf, name+".tmp", oldGlobal.Type().ElementType())
- gep := llvm.ConstGEP(global, []llvm.Value{
+ globalType, global := makeGlobalArray(mod, buf, name+".tmp", oldGlobal.Type().ElementType())
+ gep := llvm.ConstGEP(globalType, global, []llvm.Value{
llvm.ConstInt(mod.Context().Int32Type(), 0, false),
llvm.ConstInt(mod.Context().Int32Type(), 0, false),
})
diff --git a/transform/stacksize.go b/transform/stacksize.go
index f1a3c93d7..169f1454c 100644
--- a/transform/stacksize.go
+++ b/transform/stacksize.go
@@ -59,7 +59,7 @@ func CreateStackSizeLoads(mod llvm.Module, config *compileopts.Config) []string
defer irbuilder.Dispose()
for i, function := range functions {
for _, use := range functionMap[function] {
- ptr := llvm.ConstGEP(stackSizesGlobal, []llvm.Value{
+ ptr := llvm.ConstGEP(stackSizesGlobalType, stackSizesGlobal, []llvm.Value{
llvm.ConstInt(ctx.Int32Type(), 0, false),
llvm.ConstInt(ctx.Int32Type(), uint64(i), false),
})