Skip to content

Commit

Permalink
support go 1.13
Browse files Browse the repository at this point in the history
  • Loading branch information
vedhavyas committed Jan 5, 2020
1 parent a3327b9 commit 90853f7
Show file tree
Hide file tree
Showing 7 changed files with 87 additions and 142 deletions.
134 changes: 30 additions & 104 deletions bridge.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,6 @@ import (
"github.com/wasmerio/go-ext-wasm/wasmer"
)

const release_call = "_release_"

var (
undefined = &struct{}{}
bridges = map[string]*Bridge{}
Expand Down Expand Up @@ -60,30 +58,6 @@ type Bridge struct {
cancF context.CancelFunc
}

// releaseRef removes the ref from the refs.
// Returns the idx and true if remove was successful.
func (b *Bridge) releaseRef(v interface{}) (int, bool) {
idx, ok := b.refs[v]
if !ok {
return 0, false
}

delete(b.refs, v)
return idx, true
}

// releaseVal removes val from the valueMap
// Returns the value and true if remove was successful
func (b *Bridge) releaseVal(idx int) (interface{}, bool) {
v, ok := b.valueMap[idx]
if !ok {
return nil, false
}

delete(b.valueMap, idx)
return v, true
}

func BridgeFromBytes(name string, bytes []byte, imports *wasmer.Imports) (*Bridge, error) {
b := new(Bridge)
if imports == nil {
Expand Down Expand Up @@ -142,16 +116,9 @@ func (b *Bridge) addValues() {
"Object": &object{name: "Object", new: func(args []interface{}) interface{} {
return &object{name: "ObjectInner", props: map[string]interface{}{}}
}},
"Array": propObject("Array", nil),
"Int8Array": typedArray,
"Int16Array": typedArray,
"Int32Array": typedArray,
"Uint8Array": typedArray,
"Uint16Array": typedArray,
"Uint32Array": typedArray,
"Float32Array": typedArray,
"Float64Array": typedArray,
"process": propObject("process", nil),
"Array": propObject("Array", nil),
"Uint8Array": typedArray,
"process": propObject("process", nil),
"Date": &object{name: "Date", new: func(args []interface{}) interface{} {
t := time.Now()
return &object{name: "DateInner", props: map[string]interface{}{
Expand All @@ -168,7 +135,7 @@ func (b *Bridge) addValues() {
"crypto": propObject("crypto", map[string]interface{}{
"getRandomValues": Func(func(args []interface{}) (interface{}, error) {
arr := args[0].(*array)
return rand.Read(arr.data())
return rand.Read(arr.buf)
}),
}),
"AbortController": &object{name: "AbortController", new: func(args []interface{}) interface{} {
Expand All @@ -189,7 +156,7 @@ func (b *Bridge) addValues() {
return obj
}},
"fetch": Func(func(args []interface{}) (interface{}, error) {
// TODO(ved): implement fetch
// Fixme(ved): implement fetch
log.Fatalln(args)
return nil, nil
}),
Expand All @@ -207,7 +174,7 @@ func (b *Bridge) addValues() {
fd := int(args[0].(float64))
offset := int(args[2].(float64))
length := int(args[3].(float64))
buf := args[1].(*array).data()[offset : offset+length]
buf := args[1].(*array).buf[offset : offset+length]
pos := args[4]
callback := args[5].(*funcWrapper)
var err error
Expand All @@ -228,10 +195,7 @@ func (b *Bridge) addValues() {
}),
},
}, //global
6: propObject("mem", map[string]interface{}{
"buffer": &buffer{data: b.mem()}},
),
7: goObj, // jsGo
6: goObj, // jsGo
}
}

Expand Down Expand Up @@ -421,35 +385,34 @@ func (b *Bridge) storeValue(addr int32, v interface{}) {
return
}

rv := reflect.TypeOf(v)
if !rv.Comparable() {
panic(fmt.Sprintf("%T is not comparable", v))
rt := reflect.TypeOf(v)
if rt.Kind() == reflect.Ptr {
rt = rt.Elem()
}

if rv.Kind() == reflect.Ptr {
rv = rv.Elem()
rv := v
if !rt.Comparable() {
// since some types like Func cant be set as key, we will use their reflect value
// as key to insert for refs[key] so that we can avoid any duplicates
rv = reflect.ValueOf(v)
}

ref, ok := b.refs[v]
ref, ok := b.refs[rv]
if !ok {
b.valuesMu.RLock()
b.valueMap[b.valueIDX] = v
ref = b.valueIDX
b.refs[v] = ref
b.refs[rv] = ref
b.valueIDX++
b.valuesMu.RUnlock()
}

typeFlag := 0
switch rv.Kind() {
switch rt.Kind() {
case reflect.String:
typeFlag = 1
case reflect.Struct, reflect.Slice:
typeFlag = 2
case reflect.Func:
typeFlag = 3
default:
panic(fmt.Sprintf("unknown type: %T", v))
}
b.setUint32(addr+4, uint32(nanHead|typeFlag))
b.setUint32(addr, uint32(ref))
Expand All @@ -466,30 +429,20 @@ func propObject(name string, prop map[string]interface{}) *object {
}

type array struct {
buf *buffer
offset int
length int
}

func (a *array) data() []byte {
return a.buf.data[a.offset : a.offset+a.length]
buf []byte
}

var typedArray = &object{
name: "TypedArray",
new: func(args []interface{}) interface{} {
l := int(args[0].(float64))
return &array{
buf: args[0].(*buffer),
offset: int(args[1].(float64)),
length: int(args[2].(float64)),
buf: make([]byte, l, l),
}
},
}

type buffer struct {
data []byte
}

// TODO make this a wrapper that takes an inner `this` js object
type Func func(args []interface{}) (interface{}, error)

func (b *Bridge) resume() error {
Expand All @@ -503,9 +456,7 @@ type funcWrapper struct {
}

func (b *Bridge) makeFuncWrapper(id, this interface{}, args *[]interface{}) (interface{}, error) {
b.valuesMu.RLock()
goObj := b.valueMap[7].(*object)
b.valuesMu.RUnlock()
goObj := this.(*object)
event := propObject("_pendingEvent", map[string]interface{}{
"id": id,
"this": goObj,
Expand All @@ -528,10 +479,8 @@ func (b *Bridge) CallFunc(fn string, args []interface{}) (interface{}, error) {
if !ok {
return nil, fmt.Errorf("missing function: %v", fn)
}

this := b.valueMap[7]
this := b.valueMap[6]
b.valuesMu.RUnlock()

return b.makeFuncWrapper(fw.(*funcWrapper).id, this, &args)
}

Expand All @@ -542,28 +491,13 @@ func (b *Bridge) SetFunc(fname string, fn Func) error {
return nil
}

func (b *Bridge) releaseFunc(v interface{}) Func {
return Func(func(args []interface{}) (interface{}, error) {
b.valuesMu.Lock()
defer b.valuesMu.Unlock()

idx, ok := b.releaseRef(v)
if !ok {
return nil, nil
}

b.releaseVal(idx)
return nil, nil
})
}

func Bytes(v interface{}) ([]byte, error) {
arr, ok := v.(*array)
if !ok {
return nil, fmt.Errorf("got %T instead of bytes", v)
}

return arr.data(), nil
return arr.buf, nil
}

func String(v interface{}) (string, error) {
Expand All @@ -575,7 +509,7 @@ func String(v interface{}) (string, error) {
return str, nil
}

func Error(v interface{}) (errVal error, err error) {
func Error(v interface{}) (errVal, err error) {
str, ok := v.(string)
if !ok {
return nil, fmt.Errorf("got %T instead of error", v)
Expand All @@ -584,16 +518,8 @@ func Error(v interface{}) (errVal error, err error) {
return errors.New(str), nil
}

func UintArray(v interface{}) *[]uint {
rv := reflect.ValueOf(v)
if rv.Kind() != reflect.Slice {
panic("not a slice")
}

buf := make([]uint, rv.Len(), rv.Len())
for i := 0; i < rv.Len(); i++ {
buf[i] = uint(rv.Index(i).Uint())
}

return &buf
func FromBytes(v []byte) interface{} {
buf := make([]byte, len(v), len(v))
copy(buf, v)
return &array{buf: buf}
}
2 changes: 1 addition & 1 deletion examples/function-caller/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@ func main() {
}
log.Println(bytes)

res, err = b.CallFunc("bytes", []interface{}{wasm.UintArray(bytes)})
res, err = b.CallFunc("bytes", []interface{}{wasm.FromBytes(bytes)})
if err != nil {
panic(err)
}
Expand Down
14 changes: 9 additions & 5 deletions examples/function-wasm/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,6 @@ import (
"errors"
"log"
"syscall/js"

"github.com/vedhavyas/go-wasm/go-converts"
)

func addition(this js.Value, args []js.Value) interface{} {
Expand All @@ -27,7 +25,10 @@ func getBytes(this js.Value, args []js.Value) interface{} {
if err != nil {
panic(err)
}
return js.TypedArrayOf(r)

v := js.Global().Get("Uint8Array").New(len(r))
js.CopyBytesToJS(v, r)
return v
}

func getError(this js.Value, args []js.Value) interface{} {
Expand All @@ -37,8 +38,11 @@ func getError(this js.Value, args []js.Value) interface{} {

func receiveSendBytes(this js.Value, args []js.Value) interface{} {
b := args[0]
buf := converts.ToBytes(b)
return js.TypedArrayOf(buf)
buf := make([]byte, b.Length(), b.Length())
js.CopyBytesToGo(buf, b)
v := js.Global().Get("Uint8Array").New(len(buf))
js.CopyBytesToJS(v, buf)
return v
}

func main() {
Expand Down
Binary file modified examples/function-wasm/main.wasm
Binary file not shown.
Binary file modified examples/http-wasm/main.wasm
Binary file not shown.
20 changes: 0 additions & 20 deletions go-converts/wasm.go

This file was deleted.

Loading

0 comments on commit 90853f7

Please sign in to comment.