aboutsummaryrefslogtreecommitdiff
path: root/callback.go
diff options
context:
space:
mode:
authormattn <mattn.jp@gmail.com>2020-08-26 09:36:43 +0900
committerGitHub <noreply@github.com>2020-08-26 09:36:43 +0900
commit6a8b30186d28277f09a0ba6df3d3fa3859c5c499 (patch)
tree99068cf0d123b5c63476eed68f49f273a2a4e98b /callback.go
parenttreat vtable C arrays as Go slices rather than giant Go arrays (#840) (diff)
downloadgolite-6a8b30186d28277f09a0ba6df3d3fa3859c5c499.tar.gz
golite-6a8b30186d28277f09a0ba6df3d3fa3859c5c499.tar.xz
Use go-pointer instead of uintptr hacks. (#814)
* Use go-pointer instead of uintptr hacks. Fixes #791 * Do same of go-pointer * Drop older verion of Go * Fix build * Fix build
Diffstat (limited to 'callback.go')
-rw-r--r--callback.go50
1 files changed, 22 insertions, 28 deletions
diff --git a/callback.go b/callback.go
index 6450575..c3ce752 100644
--- a/callback.go
+++ b/callback.go
@@ -35,56 +35,55 @@ import (
//export callbackTrampoline
func callbackTrampoline(ctx *C.sqlite3_context, argc int, argv **C.sqlite3_value) {
args := (*[(math.MaxInt32 - 1) / unsafe.Sizeof((*C.sqlite3_value)(nil))]*C.sqlite3_value)(unsafe.Pointer(argv))[:argc:argc]
- fi := lookupHandle(uintptr(C.sqlite3_user_data(ctx))).(*functionInfo)
+ fi := lookupHandle(C.sqlite3_user_data(ctx)).(*functionInfo)
fi.Call(ctx, args)
}
//export stepTrampoline
func stepTrampoline(ctx *C.sqlite3_context, argc C.int, argv **C.sqlite3_value) {
args := (*[(math.MaxInt32 - 1) / unsafe.Sizeof((*C.sqlite3_value)(nil))]*C.sqlite3_value)(unsafe.Pointer(argv))[:int(argc):int(argc)]
- ai := lookupHandle(uintptr(C.sqlite3_user_data(ctx))).(*aggInfo)
+ ai := lookupHandle(C.sqlite3_user_data(ctx)).(*aggInfo)
ai.Step(ctx, args)
}
//export doneTrampoline
func doneTrampoline(ctx *C.sqlite3_context) {
- handle := uintptr(C.sqlite3_user_data(ctx))
- ai := lookupHandle(handle).(*aggInfo)
+ ai := lookupHandle(C.sqlite3_user_data(ctx)).(*aggInfo)
ai.Done(ctx)
}
//export compareTrampoline
-func compareTrampoline(handlePtr uintptr, la C.int, a *C.char, lb C.int, b *C.char) C.int {
+func compareTrampoline(handlePtr unsafe.Pointer, la C.int, a *C.char, lb C.int, b *C.char) C.int {
cmp := lookupHandle(handlePtr).(func(string, string) int)
return C.int(cmp(C.GoStringN(a, la), C.GoStringN(b, lb)))
}
//export commitHookTrampoline
-func commitHookTrampoline(handle uintptr) int {
+func commitHookTrampoline(handle unsafe.Pointer) int {
callback := lookupHandle(handle).(func() int)
return callback()
}
//export rollbackHookTrampoline
-func rollbackHookTrampoline(handle uintptr) {
+func rollbackHookTrampoline(handle unsafe.Pointer) {
callback := lookupHandle(handle).(func())
callback()
}
//export updateHookTrampoline
-func updateHookTrampoline(handle uintptr, op int, db *C.char, table *C.char, rowid int64) {
+func updateHookTrampoline(handle unsafe.Pointer, op int, db *C.char, table *C.char, rowid int64) {
callback := lookupHandle(handle).(func(int, string, string, int64))
callback(op, C.GoString(db), C.GoString(table), rowid)
}
//export authorizerTrampoline
-func authorizerTrampoline(handle uintptr, op int, arg1 *C.char, arg2 *C.char, arg3 *C.char) int {
+func authorizerTrampoline(handle unsafe.Pointer, op int, arg1 *C.char, arg2 *C.char, arg3 *C.char) int {
callback := lookupHandle(handle).(func(int, string, string, string) int)
return callback(op, C.GoString(arg1), C.GoString(arg2), C.GoString(arg3))
}
//export preUpdateHookTrampoline
-func preUpdateHookTrampoline(handle uintptr, dbHandle uintptr, op int, db *C.char, table *C.char, oldrowid int64, newrowid int64) {
+func preUpdateHookTrampoline(handle unsafe.Pointer, dbHandle uintptr, op int, db *C.char, table *C.char, oldrowid int64, newrowid int64) {
hval := lookupHandleVal(handle)
data := SQLitePreUpdateData{
Conn: hval.db,
@@ -105,33 +104,27 @@ type handleVal struct {
}
var handleLock sync.Mutex
-var handleVals = make(map[uintptr]handleVal)
-var handleIndex uintptr = 100
+var handleVals = make(map[unsafe.Pointer]handleVal)
-func newHandle(db *SQLiteConn, v interface{}) uintptr {
+func newHandle(db *SQLiteConn, v interface{}) unsafe.Pointer {
handleLock.Lock()
defer handleLock.Unlock()
- i := handleIndex
- handleIndex++
- handleVals[i] = handleVal{db, v}
- return i
+ val := handleVal{db: db, val: v}
+ var p unsafe.Pointer = C.malloc(C.size_t(1))
+ if p == nil {
+ panic("can't allocate 'cgo-pointer hack index pointer': ptr == nil")
+ }
+ handleVals[p] = val
+ return p
}
-func lookupHandleVal(handle uintptr) handleVal {
+func lookupHandleVal(handle unsafe.Pointer) handleVal {
handleLock.Lock()
defer handleLock.Unlock()
- r, ok := handleVals[handle]
- if !ok {
- if handle >= 100 && handle < handleIndex {
- panic("deleted handle")
- } else {
- panic("invalid handle")
- }
- }
- return r
+ return handleVals[handle]
}
-func lookupHandle(handle uintptr) interface{} {
+func lookupHandle(handle unsafe.Pointer) interface{} {
return lookupHandleVal(handle).val
}
@@ -141,6 +134,7 @@ func deleteHandles(db *SQLiteConn) {
for handle, val := range handleVals {
if val.db == db {
delete(handleVals, handle)
+ C.free(handle)
}
}
}