Invalid Memory Address or Nil Pointer Dereference in Golang's c-shared Buildmode












0















I created a Node app that calls golang code for a resource-expensive operation. I use library called gosync and I use the option -buildmode=c-shared, which results two files, the .h file and .so file.



Here's the source I've written in Golang :



package main

import "C"

import (
"errors"
"os"
"personal.io/go-wrapper/util"
)

func main() {}

//export Diff
func Diff(localFilePath string, summaryFilePath string) {
util.Diff(localFilePath, summaryFilePath)
}


The util.Diff function is almost same with the sample provided by the gosync creator here https://github.com/Redundancy/gosync-cmd/blob/master/src/gosync/diff.go. Only slight modification on the function parameter :



I built it with this command :



go build -buildmode=c-shared -o gowrapper.so main.go


In case you're wondering what's the header output :



/* Created by "go tool cgo" - DO NOT EDIT. */

/* package command-line-arguments */


#line 1 "cgo-builtin-prolog"

#include <stddef.h> /* for ptrdiff_t below */

#ifndef GO_CGO_EXPORT_PROLOGUE_H
#define GO_CGO_EXPORT_PROLOGUE_H

typedef struct { const char *p; ptrdiff_t n; } _GoString_;

#endif

/* Start of preamble from import "C" comments. */
/* End of preamble from import "C" comments. */


/* Start of boilerplate cgo prologue. */
#line 1 "cgo-gcc-export-header-prolog"

#ifndef GO_CGO_PROLOGUE_H
#define GO_CGO_PROLOGUE_H

typedef signed char GoInt8;
typedef unsigned char GoUint8;
typedef short GoInt16;
typedef unsigned short GoUint16;
typedef int GoInt32;
typedef unsigned int GoUint32;
typedef long long GoInt64;
typedef unsigned long long GoUint64;
typedef GoInt64 GoInt;
typedef GoUint64 GoUint;
typedef __SIZE_TYPE__ GoUintptr;
typedef float GoFloat32;
typedef double GoFloat64;
typedef float _Complex GoComplex64;
typedef double _Complex GoComplex128;

/*
static assertion to make sure the file is being used on architecture
at least with matching size of GoInt.
*/
typedef char _check_for_64_bit_pointer_matching_GoInt[sizeof(void*)==64/8 ? 1:-1];

typedef _GoString_ GoString;
typedef void *GoMap;
typedef void *GoChan;
typedef struct { void *t; void *v; } GoInterface;
typedef struct { void *data; GoInt len; GoInt cap; } GoSlice;

#endif

/* End of boilerplate cgo prologue. */

#ifdef __cplusplus
extern "C" {
#endif

extern void Diff(GoString p0, GoString p1);

#ifdef __cplusplus
}
#endif


And then this is how I called the function in my Node app :



var ref = require("ref")
var ffi = require("ffi-napi")
var Struct = require("ref-struct")
var ArrayType = require("ref-array")
var LongArray = ArrayType(ref.types.longlong);

var GoSlice = Struct({
data: LongArray,
len: "longlong",
cap: "longlong"
});
var GoString = Struct({
p: "string",
n: "longlong"
});

var gozsync = ffi.Library("./gowrapper.so", {
Diff: ["void", [GoString, GoString]]
});

const originPath = "/home/ivan/Documents/testingground/crossfire/dummy.v1.txt"
let originGoString = new GoString();
originGoString["p"] = originPath;
originGoString["n"] = originPath.length;

const summaryPath = "/home/ivan/Documents/testingground/crossfire/dummy.v2.gosync"
let summaryGoString = new GoString();
summaryGoString["p"] = summaryPath;
summaryGoString["n"] = summaryPath.length;

console.log(gozsync.Diff(originGoString, summaryGoString));


Running that code (the js one) will achieve the main goal (calculating the diff). However I can't exit that successfully :



panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x17 pc=0x7fa1e56fe842]

goroutine 17 [running, locked to thread]:
main._cgoexpwrap_dc7530d6a4e5_Diff.func1(0xc420245ea8)
_cgo_gotypes.go:59 +0x42
main._cgoexpwrap_dc7530d6a4e5_Diff(0x2d775c0, 0x3d, 0x2d67860, 0x40, 0x0, 0x0)
_cgo_gotypes.go:61 +0x92
Aborted (core dumped)


My hypothesis is that the memory that holds the value needed deferred operation (such as file instance on closing it) has been removed somehow by garbage collector mechanism (which seems like also ported in .so file). However I'm not sure as I can't find the reference to that statement.



Any idea regarding to that problem?










share|improve this question

























  • stackoverflow.com/help/mcve , you can't expect others to read your whole program.

    – nilsocket
    Nov 22 '18 at 2:47
















0















I created a Node app that calls golang code for a resource-expensive operation. I use library called gosync and I use the option -buildmode=c-shared, which results two files, the .h file and .so file.



Here's the source I've written in Golang :



package main

import "C"

import (
"errors"
"os"
"personal.io/go-wrapper/util"
)

func main() {}

//export Diff
func Diff(localFilePath string, summaryFilePath string) {
util.Diff(localFilePath, summaryFilePath)
}


The util.Diff function is almost same with the sample provided by the gosync creator here https://github.com/Redundancy/gosync-cmd/blob/master/src/gosync/diff.go. Only slight modification on the function parameter :



I built it with this command :



go build -buildmode=c-shared -o gowrapper.so main.go


In case you're wondering what's the header output :



/* Created by "go tool cgo" - DO NOT EDIT. */

/* package command-line-arguments */


#line 1 "cgo-builtin-prolog"

#include <stddef.h> /* for ptrdiff_t below */

#ifndef GO_CGO_EXPORT_PROLOGUE_H
#define GO_CGO_EXPORT_PROLOGUE_H

typedef struct { const char *p; ptrdiff_t n; } _GoString_;

#endif

/* Start of preamble from import "C" comments. */
/* End of preamble from import "C" comments. */


/* Start of boilerplate cgo prologue. */
#line 1 "cgo-gcc-export-header-prolog"

#ifndef GO_CGO_PROLOGUE_H
#define GO_CGO_PROLOGUE_H

typedef signed char GoInt8;
typedef unsigned char GoUint8;
typedef short GoInt16;
typedef unsigned short GoUint16;
typedef int GoInt32;
typedef unsigned int GoUint32;
typedef long long GoInt64;
typedef unsigned long long GoUint64;
typedef GoInt64 GoInt;
typedef GoUint64 GoUint;
typedef __SIZE_TYPE__ GoUintptr;
typedef float GoFloat32;
typedef double GoFloat64;
typedef float _Complex GoComplex64;
typedef double _Complex GoComplex128;

/*
static assertion to make sure the file is being used on architecture
at least with matching size of GoInt.
*/
typedef char _check_for_64_bit_pointer_matching_GoInt[sizeof(void*)==64/8 ? 1:-1];

typedef _GoString_ GoString;
typedef void *GoMap;
typedef void *GoChan;
typedef struct { void *t; void *v; } GoInterface;
typedef struct { void *data; GoInt len; GoInt cap; } GoSlice;

#endif

/* End of boilerplate cgo prologue. */

#ifdef __cplusplus
extern "C" {
#endif

extern void Diff(GoString p0, GoString p1);

#ifdef __cplusplus
}
#endif


And then this is how I called the function in my Node app :



var ref = require("ref")
var ffi = require("ffi-napi")
var Struct = require("ref-struct")
var ArrayType = require("ref-array")
var LongArray = ArrayType(ref.types.longlong);

var GoSlice = Struct({
data: LongArray,
len: "longlong",
cap: "longlong"
});
var GoString = Struct({
p: "string",
n: "longlong"
});

var gozsync = ffi.Library("./gowrapper.so", {
Diff: ["void", [GoString, GoString]]
});

const originPath = "/home/ivan/Documents/testingground/crossfire/dummy.v1.txt"
let originGoString = new GoString();
originGoString["p"] = originPath;
originGoString["n"] = originPath.length;

const summaryPath = "/home/ivan/Documents/testingground/crossfire/dummy.v2.gosync"
let summaryGoString = new GoString();
summaryGoString["p"] = summaryPath;
summaryGoString["n"] = summaryPath.length;

console.log(gozsync.Diff(originGoString, summaryGoString));


Running that code (the js one) will achieve the main goal (calculating the diff). However I can't exit that successfully :



panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x17 pc=0x7fa1e56fe842]

goroutine 17 [running, locked to thread]:
main._cgoexpwrap_dc7530d6a4e5_Diff.func1(0xc420245ea8)
_cgo_gotypes.go:59 +0x42
main._cgoexpwrap_dc7530d6a4e5_Diff(0x2d775c0, 0x3d, 0x2d67860, 0x40, 0x0, 0x0)
_cgo_gotypes.go:61 +0x92
Aborted (core dumped)


My hypothesis is that the memory that holds the value needed deferred operation (such as file instance on closing it) has been removed somehow by garbage collector mechanism (which seems like also ported in .so file). However I'm not sure as I can't find the reference to that statement.



Any idea regarding to that problem?










share|improve this question

























  • stackoverflow.com/help/mcve , you can't expect others to read your whole program.

    – nilsocket
    Nov 22 '18 at 2:47














0












0








0








I created a Node app that calls golang code for a resource-expensive operation. I use library called gosync and I use the option -buildmode=c-shared, which results two files, the .h file and .so file.



Here's the source I've written in Golang :



package main

import "C"

import (
"errors"
"os"
"personal.io/go-wrapper/util"
)

func main() {}

//export Diff
func Diff(localFilePath string, summaryFilePath string) {
util.Diff(localFilePath, summaryFilePath)
}


The util.Diff function is almost same with the sample provided by the gosync creator here https://github.com/Redundancy/gosync-cmd/blob/master/src/gosync/diff.go. Only slight modification on the function parameter :



I built it with this command :



go build -buildmode=c-shared -o gowrapper.so main.go


In case you're wondering what's the header output :



/* Created by "go tool cgo" - DO NOT EDIT. */

/* package command-line-arguments */


#line 1 "cgo-builtin-prolog"

#include <stddef.h> /* for ptrdiff_t below */

#ifndef GO_CGO_EXPORT_PROLOGUE_H
#define GO_CGO_EXPORT_PROLOGUE_H

typedef struct { const char *p; ptrdiff_t n; } _GoString_;

#endif

/* Start of preamble from import "C" comments. */
/* End of preamble from import "C" comments. */


/* Start of boilerplate cgo prologue. */
#line 1 "cgo-gcc-export-header-prolog"

#ifndef GO_CGO_PROLOGUE_H
#define GO_CGO_PROLOGUE_H

typedef signed char GoInt8;
typedef unsigned char GoUint8;
typedef short GoInt16;
typedef unsigned short GoUint16;
typedef int GoInt32;
typedef unsigned int GoUint32;
typedef long long GoInt64;
typedef unsigned long long GoUint64;
typedef GoInt64 GoInt;
typedef GoUint64 GoUint;
typedef __SIZE_TYPE__ GoUintptr;
typedef float GoFloat32;
typedef double GoFloat64;
typedef float _Complex GoComplex64;
typedef double _Complex GoComplex128;

/*
static assertion to make sure the file is being used on architecture
at least with matching size of GoInt.
*/
typedef char _check_for_64_bit_pointer_matching_GoInt[sizeof(void*)==64/8 ? 1:-1];

typedef _GoString_ GoString;
typedef void *GoMap;
typedef void *GoChan;
typedef struct { void *t; void *v; } GoInterface;
typedef struct { void *data; GoInt len; GoInt cap; } GoSlice;

#endif

/* End of boilerplate cgo prologue. */

#ifdef __cplusplus
extern "C" {
#endif

extern void Diff(GoString p0, GoString p1);

#ifdef __cplusplus
}
#endif


And then this is how I called the function in my Node app :



var ref = require("ref")
var ffi = require("ffi-napi")
var Struct = require("ref-struct")
var ArrayType = require("ref-array")
var LongArray = ArrayType(ref.types.longlong);

var GoSlice = Struct({
data: LongArray,
len: "longlong",
cap: "longlong"
});
var GoString = Struct({
p: "string",
n: "longlong"
});

var gozsync = ffi.Library("./gowrapper.so", {
Diff: ["void", [GoString, GoString]]
});

const originPath = "/home/ivan/Documents/testingground/crossfire/dummy.v1.txt"
let originGoString = new GoString();
originGoString["p"] = originPath;
originGoString["n"] = originPath.length;

const summaryPath = "/home/ivan/Documents/testingground/crossfire/dummy.v2.gosync"
let summaryGoString = new GoString();
summaryGoString["p"] = summaryPath;
summaryGoString["n"] = summaryPath.length;

console.log(gozsync.Diff(originGoString, summaryGoString));


Running that code (the js one) will achieve the main goal (calculating the diff). However I can't exit that successfully :



panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x17 pc=0x7fa1e56fe842]

goroutine 17 [running, locked to thread]:
main._cgoexpwrap_dc7530d6a4e5_Diff.func1(0xc420245ea8)
_cgo_gotypes.go:59 +0x42
main._cgoexpwrap_dc7530d6a4e5_Diff(0x2d775c0, 0x3d, 0x2d67860, 0x40, 0x0, 0x0)
_cgo_gotypes.go:61 +0x92
Aborted (core dumped)


My hypothesis is that the memory that holds the value needed deferred operation (such as file instance on closing it) has been removed somehow by garbage collector mechanism (which seems like also ported in .so file). However I'm not sure as I can't find the reference to that statement.



Any idea regarding to that problem?










share|improve this question
















I created a Node app that calls golang code for a resource-expensive operation. I use library called gosync and I use the option -buildmode=c-shared, which results two files, the .h file and .so file.



Here's the source I've written in Golang :



package main

import "C"

import (
"errors"
"os"
"personal.io/go-wrapper/util"
)

func main() {}

//export Diff
func Diff(localFilePath string, summaryFilePath string) {
util.Diff(localFilePath, summaryFilePath)
}


The util.Diff function is almost same with the sample provided by the gosync creator here https://github.com/Redundancy/gosync-cmd/blob/master/src/gosync/diff.go. Only slight modification on the function parameter :



I built it with this command :



go build -buildmode=c-shared -o gowrapper.so main.go


In case you're wondering what's the header output :



/* Created by "go tool cgo" - DO NOT EDIT. */

/* package command-line-arguments */


#line 1 "cgo-builtin-prolog"

#include <stddef.h> /* for ptrdiff_t below */

#ifndef GO_CGO_EXPORT_PROLOGUE_H
#define GO_CGO_EXPORT_PROLOGUE_H

typedef struct { const char *p; ptrdiff_t n; } _GoString_;

#endif

/* Start of preamble from import "C" comments. */
/* End of preamble from import "C" comments. */


/* Start of boilerplate cgo prologue. */
#line 1 "cgo-gcc-export-header-prolog"

#ifndef GO_CGO_PROLOGUE_H
#define GO_CGO_PROLOGUE_H

typedef signed char GoInt8;
typedef unsigned char GoUint8;
typedef short GoInt16;
typedef unsigned short GoUint16;
typedef int GoInt32;
typedef unsigned int GoUint32;
typedef long long GoInt64;
typedef unsigned long long GoUint64;
typedef GoInt64 GoInt;
typedef GoUint64 GoUint;
typedef __SIZE_TYPE__ GoUintptr;
typedef float GoFloat32;
typedef double GoFloat64;
typedef float _Complex GoComplex64;
typedef double _Complex GoComplex128;

/*
static assertion to make sure the file is being used on architecture
at least with matching size of GoInt.
*/
typedef char _check_for_64_bit_pointer_matching_GoInt[sizeof(void*)==64/8 ? 1:-1];

typedef _GoString_ GoString;
typedef void *GoMap;
typedef void *GoChan;
typedef struct { void *t; void *v; } GoInterface;
typedef struct { void *data; GoInt len; GoInt cap; } GoSlice;

#endif

/* End of boilerplate cgo prologue. */

#ifdef __cplusplus
extern "C" {
#endif

extern void Diff(GoString p0, GoString p1);

#ifdef __cplusplus
}
#endif


And then this is how I called the function in my Node app :



var ref = require("ref")
var ffi = require("ffi-napi")
var Struct = require("ref-struct")
var ArrayType = require("ref-array")
var LongArray = ArrayType(ref.types.longlong);

var GoSlice = Struct({
data: LongArray,
len: "longlong",
cap: "longlong"
});
var GoString = Struct({
p: "string",
n: "longlong"
});

var gozsync = ffi.Library("./gowrapper.so", {
Diff: ["void", [GoString, GoString]]
});

const originPath = "/home/ivan/Documents/testingground/crossfire/dummy.v1.txt"
let originGoString = new GoString();
originGoString["p"] = originPath;
originGoString["n"] = originPath.length;

const summaryPath = "/home/ivan/Documents/testingground/crossfire/dummy.v2.gosync"
let summaryGoString = new GoString();
summaryGoString["p"] = summaryPath;
summaryGoString["n"] = summaryPath.length;

console.log(gozsync.Diff(originGoString, summaryGoString));


Running that code (the js one) will achieve the main goal (calculating the diff). However I can't exit that successfully :



panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x1 addr=0x17 pc=0x7fa1e56fe842]

goroutine 17 [running, locked to thread]:
main._cgoexpwrap_dc7530d6a4e5_Diff.func1(0xc420245ea8)
_cgo_gotypes.go:59 +0x42
main._cgoexpwrap_dc7530d6a4e5_Diff(0x2d775c0, 0x3d, 0x2d67860, 0x40, 0x0, 0x0)
_cgo_gotypes.go:61 +0x92
Aborted (core dumped)


My hypothesis is that the memory that holds the value needed deferred operation (such as file instance on closing it) has been removed somehow by garbage collector mechanism (which seems like also ported in .so file). However I'm not sure as I can't find the reference to that statement.



Any idea regarding to that problem?







node.js go






share|improve this question















share|improve this question













share|improve this question




share|improve this question








edited Nov 22 '18 at 3:13







imeluntuk

















asked Nov 22 '18 at 2:43









imeluntukimeluntuk

84113




84113













  • stackoverflow.com/help/mcve , you can't expect others to read your whole program.

    – nilsocket
    Nov 22 '18 at 2:47



















  • stackoverflow.com/help/mcve , you can't expect others to read your whole program.

    – nilsocket
    Nov 22 '18 at 2:47

















stackoverflow.com/help/mcve , you can't expect others to read your whole program.

– nilsocket
Nov 22 '18 at 2:47





stackoverflow.com/help/mcve , you can't expect others to read your whole program.

– nilsocket
Nov 22 '18 at 2:47












0






active

oldest

votes











Your Answer






StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");

StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "1"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);

StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});

function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});


}
});














draft saved

draft discarded


















StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53423157%2finvalid-memory-address-or-nil-pointer-dereference-in-golangs-c-shared-buildmode%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown

























0






active

oldest

votes








0






active

oldest

votes









active

oldest

votes






active

oldest

votes
















draft saved

draft discarded




















































Thanks for contributing an answer to Stack Overflow!


  • Please be sure to answer the question. Provide details and share your research!

But avoid



  • Asking for help, clarification, or responding to other answers.

  • Making statements based on opinion; back them up with references or personal experience.


To learn more, see our tips on writing great answers.




draft saved


draft discarded














StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53423157%2finvalid-memory-address-or-nil-pointer-dereference-in-golangs-c-shared-buildmode%23new-answer', 'question_page');
}
);

Post as a guest















Required, but never shown





















































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown

































Required, but never shown














Required, but never shown












Required, but never shown







Required, but never shown







這個網誌中的熱門文章

Tangent Lines Diagram Along Smooth Curve

Yusuf al-Mu'taman ibn Hud

Zucchini