如何将 Golang 的 cgo 与 link 到 math.h 的 C 库一起使用?
How do you use Golang's cgo with C libraries that link to math.h?
我目前正在尝试使用 cgo
为 NOVAS C package (an astrometry/astronomy package) 构建一个 Golang 包装器。 NOVAS 本质上是 'installed' 通过将源文件放在您碰巧在其中工作的任何目录中(不存在编译的库文件),因此我相信我需要包含我将使用的 .c 文件(在.go
文件下一个目录的文件夹。
因此,我试图通过创建一个测试 .go 程序来测试它,该程序本身调用 novas.c
中的一个函数。但是,程序无法编译,显然是因为 math.h
中存在多个未定义的函数引用;这很奇怪,因为 math.h
包含在我的 .go 文件和我打算使用的 C 文件中。
go run novasTest.go
# command-line-arguments
/tmp/go-build681583835/b001/_x002.o: In function `equ2gal':
./Cdist/novas.c:1995: undefined reference to `sincos'
./Cdist/novas.c:1996: undefined reference to `sincos'
./Cdist/novas.c:2033: undefined reference to `atan2'
./Cdist/novas.c:2025: undefined reference to `atan2'
./Cdist/novas.c:2022: undefined reference to `sqrt'
/tmp/go-build681583835/b001/_x002.o: In function `era':
./Cdist/novas.c:3242: undefined reference to `fmod'
./Cdist/novas.c:3242: undefined reference to `fmod'
...(etcetera)
我 运行 在 VirtualBox VM 实例中的 Ubuntu 18.04 (x64) 上。我在这里漏掉了特定的一行吗?
我的 go 程序 看起来像这样:
package main
/*
#include "Cdist/novas.h"
#include "Cdist/novas.c"
#include "Cdist/novascon.c"
#include "Cdist/nutation.c"
#include <math.h>
*/
import "C"
import "log"
func main() {
log.Println("Test of NOVAS function")
var JulianHigh C.double
var JulianLow C.double
...
var Z C.double
// Test values
JulianHigh = 2458953.5
JulianLow = 1.0
...
Z = -1.437110810486059E+03
vCel := make([]C.double,0) //Create the array to pass to the function.
vCel = append(vCel, X)
...
vTerFirst := &(vTer[0])
C.cel2ter(JulianHigh,JulianLow,DeltaT,Method,Accuracy,Option,PolarX,PolarY,vCelFirst,vTerFirst)
log.Println("C function completed processing.")
}
C 程序太大,无法包含,所以我将改为显示 novas.h 文件和 novas.c 文件的相关部分。
C 文件:
/*
...
novas.c: Main library
...
*/
#ifndef _NOVAS_
#include "novas.h"
#endif
#include <math.h>
... //(other functions follow until the necessary one)
/********cel2ter */
short int cel2ter (double jd_ut_high, double jd_ut_low, double delta_t,
short int method, short int accuracy, short int option,
double xp, double yp, double *vec1,
double *vec2)
/*
------------------------------------------------------------------------
PURPOSE:
This function...
请注意,该函数本身依赖于从我包含的其他文件进行调用的函数。
.h 文件:
/*
...
novas.h: Header file for novas.c
...
*/
#ifndef _NOVAS_
#define _NOVAS_
#ifndef __STDIO__
#include <stdio.h>
#endif
#ifndef __MATH__
#include <math.h>
#endif
#ifndef __STRING__
#include <string.h>
#endif
...
你需要一个指令来告诉 go linker 到 link 使用 c 的数学库。 header math.h
不包含数学函数的实现:只有它们的声明(第一次近似)。
无论如何,您需要在您的 go 文件的注释中添加这一行:
#cgo LDFLAGS: -lm
-l
表示"link with this library",m
是C的数学库名称。
我目前正在尝试使用 cgo
为 NOVAS C package (an astrometry/astronomy package) 构建一个 Golang 包装器。 NOVAS 本质上是 'installed' 通过将源文件放在您碰巧在其中工作的任何目录中(不存在编译的库文件),因此我相信我需要包含我将使用的 .c 文件(在.go
文件下一个目录的文件夹。
因此,我试图通过创建一个测试 .go 程序来测试它,该程序本身调用 novas.c
中的一个函数。但是,程序无法编译,显然是因为 math.h
中存在多个未定义的函数引用;这很奇怪,因为 math.h
包含在我的 .go 文件和我打算使用的 C 文件中。
go run novasTest.go
# command-line-arguments
/tmp/go-build681583835/b001/_x002.o: In function `equ2gal':
./Cdist/novas.c:1995: undefined reference to `sincos'
./Cdist/novas.c:1996: undefined reference to `sincos'
./Cdist/novas.c:2033: undefined reference to `atan2'
./Cdist/novas.c:2025: undefined reference to `atan2'
./Cdist/novas.c:2022: undefined reference to `sqrt'
/tmp/go-build681583835/b001/_x002.o: In function `era':
./Cdist/novas.c:3242: undefined reference to `fmod'
./Cdist/novas.c:3242: undefined reference to `fmod'
...(etcetera)
我 运行 在 VirtualBox VM 实例中的 Ubuntu 18.04 (x64) 上。我在这里漏掉了特定的一行吗?
我的 go 程序 看起来像这样:
package main
/*
#include "Cdist/novas.h"
#include "Cdist/novas.c"
#include "Cdist/novascon.c"
#include "Cdist/nutation.c"
#include <math.h>
*/
import "C"
import "log"
func main() {
log.Println("Test of NOVAS function")
var JulianHigh C.double
var JulianLow C.double
...
var Z C.double
// Test values
JulianHigh = 2458953.5
JulianLow = 1.0
...
Z = -1.437110810486059E+03
vCel := make([]C.double,0) //Create the array to pass to the function.
vCel = append(vCel, X)
...
vTerFirst := &(vTer[0])
C.cel2ter(JulianHigh,JulianLow,DeltaT,Method,Accuracy,Option,PolarX,PolarY,vCelFirst,vTerFirst)
log.Println("C function completed processing.")
}
C 程序太大,无法包含,所以我将改为显示 novas.h 文件和 novas.c 文件的相关部分。
C 文件:
/*
...
novas.c: Main library
...
*/
#ifndef _NOVAS_
#include "novas.h"
#endif
#include <math.h>
... //(other functions follow until the necessary one)
/********cel2ter */
short int cel2ter (double jd_ut_high, double jd_ut_low, double delta_t,
short int method, short int accuracy, short int option,
double xp, double yp, double *vec1,
double *vec2)
/*
------------------------------------------------------------------------
PURPOSE:
This function...
请注意,该函数本身依赖于从我包含的其他文件进行调用的函数。
.h 文件:
/*
...
novas.h: Header file for novas.c
...
*/
#ifndef _NOVAS_
#define _NOVAS_
#ifndef __STDIO__
#include <stdio.h>
#endif
#ifndef __MATH__
#include <math.h>
#endif
#ifndef __STRING__
#include <string.h>
#endif
...
你需要一个指令来告诉 go linker 到 link 使用 c 的数学库。 header math.h
不包含数学函数的实现:只有它们的声明(第一次近似)。
无论如何,您需要在您的 go 文件的注释中添加这一行:
#cgo LDFLAGS: -lm
-l
表示"link with this library",m
是C的数学库名称。