(Fix): replaced unsafe.Pointer(&h) (Go stack pointer passed to C) with storeHandle/loadHandle helpers that keep the cgo.Handle in C-heap memory.
This commit is contained in:
@@ -10,12 +10,22 @@ package auth
|
||||
#cgo LDFLAGS: -lpam
|
||||
#include <security/pam_appl.h>
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
|
||||
// Match the //export-generated signature.
|
||||
extern int latchd_pam_conv(int, struct pam_message **,
|
||||
struct pam_response **, void *);
|
||||
|
||||
// Helper to create the conv struct with the proper cast.
|
||||
// Store a uintptr_t handle in C heap so the Go GC never sees a Go pointer.
|
||||
static void *storeHandle(uintptr_t h) {
|
||||
uintptr_t *p = malloc(sizeof(uintptr_t));
|
||||
if (p) *p = h;
|
||||
return p;
|
||||
}
|
||||
static uintptr_t loadHandle(void *p) {
|
||||
return *(uintptr_t *)p;
|
||||
}
|
||||
|
||||
static struct pam_conv makePAMConv(void *data) {
|
||||
struct pam_conv c;
|
||||
c.conv = (int (*)(int, const struct pam_message **,
|
||||
@@ -61,7 +71,7 @@ type Credentials struct {
|
||||
|
||||
//export latchd_pam_conv
|
||||
func latchd_pam_conv(numMsg C.int, msg **C.struct_pam_message, resp **C.struct_pam_response, data unsafe.Pointer) C.int {
|
||||
h := *(*cgo.Handle)(data)
|
||||
h := cgo.Handle(C.loadHandle(data))
|
||||
pw := h.Value().(string)
|
||||
|
||||
r := (*C.struct_pam_response)(C.calloc(C.ulong(numMsg), C.sizeof_struct_pam_response))
|
||||
@@ -93,7 +103,10 @@ func Validate(user, pass, service string) (*Credentials, error) {
|
||||
h := cgo.NewHandle(pass)
|
||||
defer h.Delete()
|
||||
|
||||
conv := C.makePAMConv(unsafe.Pointer(&h))
|
||||
cData := C.storeHandle(C.uintptr_t(h))
|
||||
defer C.free(cData)
|
||||
|
||||
conv := C.makePAMConv(cData)
|
||||
|
||||
var pamh *C.pam_handle_t
|
||||
ret := C.pam_start(cSvc, cUser, &conv, &pamh)
|
||||
|
||||
Reference in New Issue
Block a user