MCPcopy
hub / github.com/tinygo-org/tinygo / createConvert

Method createConvert

compiler/compiler.go:3187–3392  ·  view source on GitHub ↗

createConvert creates a Go type conversion instruction.

(typeFrom, typeTo types.Type, value llvm.Value, pos token.Pos)

Source from the content-addressed store, hash-verified

3185
3186// createConvert creates a Go type conversion instruction.
3187func (b *builder) createConvert(typeFrom, typeTo types.Type, value llvm.Value, pos token.Pos) (llvm.Value, error) {
3188 llvmTypeFrom := value.Type()
3189 llvmTypeTo := b.getLLVMType(typeTo)
3190
3191 // Conversion between unsafe.Pointer and uintptr.
3192 isPtrFrom := isPointer(typeFrom.Underlying())
3193 isPtrTo := isPointer(typeTo.Underlying())
3194 if isPtrFrom && !isPtrTo {
3195 return b.CreatePtrToInt(value, llvmTypeTo, ""), nil
3196 } else if !isPtrFrom && isPtrTo {
3197 return b.CreateIntToPtr(value, llvmTypeTo, ""), nil
3198 }
3199
3200 // Conversion between pointers and unsafe.Pointer.
3201 if isPtrFrom && isPtrTo {
3202 return value, nil
3203 }
3204
3205 switch typeTo := typeTo.Underlying().(type) {
3206 case *types.Basic:
3207 sizeFrom := b.targetData.TypeAllocSize(llvmTypeFrom)
3208
3209 if typeTo.Info()&types.IsString != 0 {
3210 switch typeFrom := typeFrom.Underlying().(type) {
3211 case *types.Basic:
3212 // Assume a Unicode code point, as that is the only possible
3213 // value here.
3214 // Cast to an i32 value as expected by
3215 // runtime.stringFromUnicode.
3216 if sizeFrom > 4 {
3217 value = b.CreateTrunc(value, b.ctx.Int32Type(), "")
3218 } else if sizeFrom < 4 && typeTo.Info()&types.IsUnsigned != 0 {
3219 value = b.CreateZExt(value, b.ctx.Int32Type(), "")
3220 } else if sizeFrom < 4 {
3221 value = b.CreateSExt(value, b.ctx.Int32Type(), "")
3222 }
3223 return b.createRuntimeCall("stringFromUnicode", []llvm.Value{value}, ""), nil
3224 case *types.Slice:
3225 switch typeFrom.Elem().(*types.Basic).Kind() {
3226 case types.Byte:
3227 return b.createRuntimeCall("stringFromBytes", []llvm.Value{value}, ""), nil
3228 case types.Rune:
3229 return b.createRuntimeCall("stringFromRunes", []llvm.Value{value}, ""), nil
3230 default:
3231 return llvm.Value{}, b.makeError(pos, "todo: convert to string: "+typeFrom.String())
3232 }
3233 default:
3234 return llvm.Value{}, b.makeError(pos, "todo: convert to string: "+typeFrom.String())
3235 }
3236 }
3237
3238 typeFrom := typeFrom.Underlying().(*types.Basic)
3239 sizeTo := b.targetData.TypeAllocSize(llvmTypeTo)
3240
3241 if typeFrom.Info()&types.IsInteger != 0 && typeTo.Info()&types.IsInteger != 0 {
3242 // Conversion between two integers.
3243 if sizeFrom > sizeTo {
3244 return b.CreateTrunc(value, llvmTypeTo, ""), nil

Callers 2

createMakeMapMethod · 0.95
createExprMethod · 0.95

Calls 9

createRuntimeCallMethod · 0.95
isPointerFunction · 0.85
getLLVMTypeMethod · 0.80
InfoMethod · 0.80
makeErrorMethod · 0.80
KindMethod · 0.65
ElemMethod · 0.65
StringMethod · 0.65
TypeMethod · 0.45

Tested by

no test coverage detected