github.com/HaHadaxigua/yaegi@v1.0.1/stdlib/unsafe/unsafe.go (about) 1 //go:build go1.16 2 // +build go1.16 3 4 // Package unsafe provides wrapper of standard library unsafe package to be imported natively in Yaegi. 5 package unsafe 6 7 import ( 8 "reflect" 9 "unsafe" 10 ) 11 12 // Symbols stores the map of unsafe package symbols. 13 var Symbols = map[string]map[string]reflect.Value{} 14 15 func init() { 16 Symbols["github.com/traefik/yaegi/stdlib/unsafe/unsafe"] = map[string]reflect.Value{ 17 "Symbols": reflect.ValueOf(Symbols), 18 } 19 Symbols["github.com/traefik/yaegi/yaegi"] = map[string]reflect.Value{ 20 "convert": reflect.ValueOf(convert), 21 } 22 23 // Add builtin functions to unsafe. 24 Symbols["unsafe/unsafe"]["Sizeof"] = reflect.ValueOf(sizeof) 25 Symbols["unsafe/unsafe"]["Alignof"] = reflect.ValueOf(alignof) 26 Symbols["unsafe/unsafe"]["Offsetof"] = reflect.ValueOf("Offsetof") // This symbol is handled directly in interpreter. 27 } 28 29 func convert(from, to reflect.Type) func(src, dest reflect.Value) { 30 switch { 31 case to.Kind() == reflect.UnsafePointer && from.Kind() == reflect.Uintptr: 32 return uintptrToUnsafePtr 33 case to.Kind() == reflect.UnsafePointer: 34 return func(src, dest reflect.Value) { 35 dest.SetPointer(unsafe.Pointer(src.Pointer())) 36 } 37 case to.Kind() == reflect.Uintptr && from.Kind() == reflect.UnsafePointer: 38 return func(src, dest reflect.Value) { 39 ptr := src.Interface().(unsafe.Pointer) 40 dest.Set(reflect.ValueOf(uintptr(ptr))) 41 } 42 case from.Kind() == reflect.UnsafePointer: 43 return func(src, dest reflect.Value) { 44 ptr := src.Interface().(unsafe.Pointer) 45 v := reflect.NewAt(dest.Type().Elem(), ptr) 46 dest.Set(v) 47 } 48 default: 49 return nil 50 } 51 } 52 53 func sizeof(i interface{}) uintptr { 54 return reflect.ValueOf(i).Type().Size() 55 } 56 57 func alignof(i interface{}) uintptr { 58 return uintptr(reflect.ValueOf(i).Type().Align()) 59 } 60 61 //go:nocheckptr 62 func uintptrToUnsafePtr(src, dest reflect.Value) { 63 dest.SetPointer(unsafe.Pointer(src.Interface().(uintptr))) //nolint:govet 64 } 65 66 //go:generate ../../internal/cmd/extract/extract unsafe