diff options
author | Patrick DeVivo <patrick.devivo@gmail.com> | 2021-10-25 17:13:24 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2021-10-26 00:13:24 +0900 |
commit | 2b780b4a7fb3a4a06eb341184933d7c5691f4dda (patch) | |
tree | bd20b98453031ea88b189906409a2a5ae9d7a039 | |
parent | Use single-quotes around string literals. (#934) (diff) | |
download | golite-2b780b4a7fb3a4a06eb341184933d7c5691f4dda.tar.gz golite-2b780b4a7fb3a4a06eb341184933d7c5691f4dda.tar.xz |
fix idxStr freeing issue (#898)
uses snippet suggested by @rittneje https://github.com/mattn/go-sqlite3/issues/897#issuecomment-752162125
-rw-r--r-- | sqlite3_opt_vtable.go | 19 |
1 files changed, 15 insertions, 4 deletions
diff --git a/sqlite3_opt_vtable.go b/sqlite3_opt_vtable.go index 8fd6cdf..4aae1d1 100644 --- a/sqlite3_opt_vtable.go +++ b/sqlite3_opt_vtable.go @@ -472,10 +472,21 @@ func goVBestIndex(pVTab unsafe.Pointer, icp unsafe.Pointer) *C.char { } info.idxNum = C.int(res.IdxNum) - idxStr := C.CString(res.IdxStr) - defer C.free(unsafe.Pointer(idxStr)) - info.idxStr = idxStr - info.needToFreeIdxStr = C.int(0) + info.idxStr = (*C.char)(C.sqlite3_malloc(C.int(len(res.IdxStr) + 1))) + if info.idxStr == nil { + // C.malloc and C.CString ordinarily do this for you. See https://golang.org/cmd/cgo/ + panic("out of memory") + } + info.needToFreeIdxStr = C.int(1) + + idxStr := *(*[]byte)(unsafe.Pointer(&reflect.SliceHeader{ + Data: uintptr(unsafe.Pointer(info.idxStr)), + Len: len(res.IdxStr) + 1, + Cap: len(res.IdxStr) + 1, + })) + copy(idxStr, res.IdxStr) + idxStr[len(idxStr)-1] = 0 // null-terminated string + if res.AlreadyOrdered { info.orderByConsumed = C.int(1) } |