gf框架使用sqlite3数据库后交叉编译cgo适配arm64-linux

2023-11-10

gf框架使用sqlite3数据库后交叉编译cgo适配arm64-linux


1. 前言

之前已经说过我们将使用openwrt+nginx+go+sqlite3的方式在openwrt上开发适配业务的web,而框架使用的go-frame,目前go语言操作sqlite3的相关库都使用了cgo,因此我们不得不面对交叉编译cgo的问题。

2. 解决方案

我们考虑了两个解决方案:1、openwrt下安装openwrt-go,然后在openwrt下编译工程;2、安装arm-linux交叉编译工具链,然后交叉编译基于cgo程序。

虽然我们的openwrt为19.07.1是支持go语言的,但是编译固件时没有添加openwrt-go,因此为了避免重新编译固件以及升级固件,暂时没有选择这种方案,其实添加一个go环境还是蛮不错的(https://openwrt.org/packages/pkgdata/golang-src)。

确实直接使用交叉编译工具链来编译cgo工程更合理一些,毕竟openwrt大多情况下还是嵌入式环境,尽量还是考虑这种交叉编译方案好一些,其实也没有那么复杂,安装交叉编译工具链,然后编译时指定对应环境变量即可。

3. wsl+Windows交叉编译cgo工程

3.1 简述cgo程序交叉编译

Windows安装相关交叉编译工具链很少,基本上都是在Ubuntu等类似的宿主机上搭建交叉编译环境,然后交叉编译适合目标机的程序,对于cgo也是如此,你可以简单理解cgo就是c程序套壳一层go接口,所以交叉编译cgo程序可以说就是交叉编译c/c++程序,因此我们搭建交叉编译环境,然后指定编译的CC、CXX环境变量即可,由于目前wsl已经足够成熟(wsl2和vmware强制而二选一,你能明白操作系统的重要性了吧),因此目前使用wsl+Windows的模式编译项目,项目在Windows下,但是交叉编译环境安装在wsl中,然后利用wsl中的交叉编译环境编译Windows下的项目。

3.2 安装交叉编译工具链

由于我们是交叉编译适配aar64+linux的程序,因此相对简单一些,直接安装现成的交叉编译工具链即可(如果是其它的系统和cpu架构,需要根据具体情况而定,但是思路都是安装相关系统和cpu架构的gcc和g++及对应依赖库,方便后续编译时使用):

sudo apt-get update
sudo apt install -y cpp-aarch64-linux-gnu g++-aarch64-linux-gnu

3.3 交叉编译包含cgo依赖的go项目

之后在wsl中编译时指定对应的环境变量即可(注意结合go的特性进行静态链接,这样虽然会导致程序大一些,但是避免了动态库的依赖,更方便移植):

CGO_ENABLED=1 CC=aarch64-linux-gnu-gcc CXX=aarch64-linux-gnu-g++ GOOS=linux GOARCH=arm64 go build -o ./bin/server main.go -ldflags '-s -w --extldflags "-static -fpic"'

-ldflags '-s -w’可以去掉一些符号表,这样不但可以减少程序的体积,实际发布后在一定程序上也可以避免程序被二进制逆向破解。static那部分则是静态链接方式,将相关库都静态链接,这样生成的程序就不必依赖可能的动态库了。

3.4 交叉编译依赖sqlite3的gf工程

交叉编译时使用gf建议只设置config.toml中的extra,当成go build命令来使用:

config.toml:

[gfcli]
    # 自定义DAO生成配置(默认是读取database配置)
    [[gfcli.gen.dao]]
        link   = "sqlite:./gateway.db"
        tables = "user, login_log, oper_log"
        descriptionTag = true
        noModelComment = true
    [gfcli.build]
        cgo      = 1
        extra    = "-ldflags '-s -w --extldflags \"-static -fpic\"'"

编译时:

CGO_ENABLED=1 CC=aarch64-linux-gnu-gcc CXX=aarch64-linux-gnu-g++ GOOS=linux GOARCH=arm64 gf build main.go -o ./bin/TSL-G10-SW-GATEWAY-WEB --pack public --swagger -v 1.0.0

至于gf框架如何使用sqlite3可以看这里:https://goframe.org/pages/viewpage.action?pageId=17203966

4. 最后

cgo的使用还是不错的,尽量根据go的特性使用静态库,这也是go使用起来体验不错的原因之一,太多的动态库依赖往往让编译过程变得比较麻烦,找依赖错误往往占编译的很大一部分。

参考:https://github.com/eyasliu/blog/issues/27

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

gf框架使用sqlite3数据库后交叉编译cgo适配arm64-linux 的相关文章

  • 如何在golang中创建一个充满“000000...”数据的10MB文件?

    我打算在日志或磁盘队列等系统中使用 fdatasync 首先是在 ext4 等文件系统中创建一个带有 000000 的 10MB 文件 但我不知道如何正确地做到这一点 jnml fsc r630 src tmp SO 16797380 ls
  • 如何使信号量超时

    Go 中的信号量是通过通道来实现的 一个例子是这样的 https sites google com site gopatterns concurrency semaphores https sites google com site gop
  • Golang中按长度分割字符串

    有谁知道如何在 Golang 中按长度分割字符串 例如 每 3 个字符分割 helloworld 那么理想情况下它应该返回一个 hel low orl d 数组 或者 一个可能的解决方案是在每 3 个字符后附加一个换行符 所有的想法都非常感
  • Golang:带有 JSON 负载的 http.NewRequest POST 返回错误 500

    我正在开发一个 API 库 有一个API端点 POST 当您发出curl命令时 它是 curl H X API TOKEN API TOKEN http interest graph getprismatic com text topic
  • Golang 正则表达式在字符串之间替换

    我有一些可能采用以下形式的字符串 MYSTRING MYSTRING n MYSTRING n MYSTRING randomstringwithvariablelength n 我希望能够将其正则表达式为MYSTRING foo 基本上替
  • os.Mkdir 和 os.MkdirAll 权限

    我正在尝试在程序开始时创建一个日志文件 我需要检查是否 log如果不创建目录 则目录存在 然后继续创建日志文件 好吧 我尝试使用os Mkdir 也os MkdirAll 但无论我在第二个参数中输入什么值 我都会得到一个没有权限的锁定文件夹
  • 如何同时使用 LoadHTMLGlob 和 LoadHTMLFiles

    我想要来自不同子目录的分隔符逻辑模板templates文件夹 下面是我的templates文件夹 templates authentication login gohtml logout gohtml index gohtml profil
  • 在 Visual Studio Code 中调试 Go 测试

    在我的 Windows 计算机上 我安装了 Visual Studio Code 要手动运行测试 我进入控制台到项目文件夹并输入 go test main test go 它工作完美 但我遇到一种情况 我需要调试我的测试以了解发生了什么 为
  • 如何确定 go 中当前运行的可执行文件的完整路径?

    我一直在 osx 上使用这个函数 Shortcut to get the path to the current executable func ExecPath string var here os Args 0 if strings H
  • golang无法启动调试,显示未找到框架CoreFoundation

    我使用的是 Macbook pro m1 在数据迁移或更新到 monterey 后 不确定是什么原因导致的 golang 似乎无法调试或 go list 编译 我尝试重新安装 更新 golang 结果是一样的 Go版本 1 17 3 dar
  • 使用 mgo 驱动程序进行 mongo 聚合查询

    我在 mongodb 中有以下查询 db devices aggregate match userId v73TuQqZykbxFXsWo state true project userId 1 categorySlug 1 weight
  • 如何在 Go 中填写 void* C 指针?

    我正在尝试与 Go 中的一些 C 代码交互 使用 cgo 这一直相对简单 直到我遇到这种 相当常见 的情况 需要将指针传递给本身包含指向某些数据的指针的结构 我似乎无法弄清楚如何从 Go 中做到这一点 而不诉诸于将结构的创建放入 C 代码本
  • 在复杂的文件夹结构中进行测试

    我正在 golang 中构建一个设计模式存储库 为了运行所有测试 我使用这个 bash 脚本 有用 bin bash go test creational abstract factory go go test creational bui
  • GoLang 中的 HTML 部分

    我刚刚开始使用 Go 我想用它创建一个网络应用程序 我现在尝试的是以handlebarsjs 式的方式使用模板 我想将页眉和页脚从主页中取出 以便可以将它们注入到每个网页上 我当前的设置应该是解析主页 页眉和页脚 HTML 文件并缓存它们
  • 为什么 DER ASN.1 大整数的解组在 Golang 中仅限于 SEQUENCE?

    我希望能够使用encoding asn1 包从 DER 文件中解组一个大整数 但它看起来只适用于整数序列 例如 这不起作用 这很奇怪 因为 Big Int 的编组效果很好 https play golang org p Wkj0jAA6bp
  • 如何使用 go1.6.2 构建 linux 32 位

    有没有任何组合GOARCH and GOOS我可以设置哪些值来构建 ELF 32 位二进制文 件 GOOS linux and GOARCH 386 更多示例 架构 32 bit gt GOARCH 386 64 bit gt GOARCH
  • 如何通过在切片上查找来从切片复制到数组

    我正在编写一个库来处理二进制格式 我有一个带有数组变量的结构 我想保留它以用于文档目的 我还需要从输入字节片中查找和判断 一些伪代码 type foo struct boo 5 byte coo 3 byte func main input
  • 子字符串和 Go 垃圾收集器

    在 Go 中获取字符串的子字符串时 不会分配新的内存 相反 子字符串的底层表示包含一个数据指针 该指针是原始字符串的数据指针的偏移量 这意味着 如果我有一个大字符串并希望跟踪一个小子字符串 则垃圾收集器将无法释放任何大字符串 直到我释放对较
  • Go 指针 - 通过指针将值附加到切片

    我有一个 struct ProductData 及其实例 p 它有一个切片属性 type ProductInfo struct TopAttributes map string interface 我想设置 TopAttributes 如下
  • 仅导出嵌入结构实现的方法子集

    是否可以仅导出嵌入结构实现的方法的子集 这是一种与减少代码复制和粘贴非常不同的方法吗 还有更惯用的方法吗 type A struct func a A Hello fmt Println Hello func a A World fmt P

随机推荐

  • 一文解释python中的实例方法,类方法和静态方法作用和区别是啥?该如何使用

    我们都知道 python类中有三种常见的方法 分别是实例方法 类方法和静态方法 那么这几个方法到底有什么作用 它们之间有什么区别 该如何使用 带着这些问题 下面我们就来了解下这三种方法 1 方法介绍 2 代码说明 若我们要实现一个学生的类
  • ==,Object.equals(), Objects.equals(), Objects.deepEquals 使用注意

    相等判断时需注意 基本数据类型之间 可使用 包装类型之间尽量不要使用 包装类数值超过 127 128 引用类型地址不同 在 127 128之间时 翻阅底层源码发现 使用的是缓存的值 使用Object equals 做内容比较时 把常量 或可
  • IM即时通讯实现原理

    即时通讯 Instant Messenger 简称IM 软件多是基于TCP IP和UDP进行通讯的 TCP IP和UDP都是建立在更低层的IP协议上的两种通讯传输协议 前 者是以数据流的形式 将传输数据经分割 打包后 通过两台机器之间建立起
  • Spyder 快捷键大全(转)

    主要介绍了Spyder常见的快捷键 从spyder的配置表中导出 中文名称为直译 常用快捷键 快捷键 中文名称 Ctrl R 替换文本 Ctrl 1 单行注释 单次注释 双次取消注释 Ctrl 4 块注释 单次注释 双次取消注释 F5 运行
  • Python之argparse.ArgumentParser

    一 介绍 argparse是python用于解析命令行参数和选项的标准模块 一方面可以接收运行代码时用户传入的各种参数 比如传入数据路径 另一方面也可以规范的定义程序中用到的参数 比如定义epoch及batch size等 二 使用 新建t
  • [javascript]canvas 热点区域图,框选区域并在区域显示热点

    需求 设置人员需要在图片上框选区域 并且后台针对区域读出数据后显示热点 做法 直接上代码 作者 jww dragon 163 com 依赖 jquery var goog function tag this hotpoint this sq
  • 时序预测

    时序预测 Python实现XGBoost极限梯度提升树股票价格预测 目录 时序预测 Python实现XGBoost极限梯度提升树股票价格预测 预测效果 基本描述 环境配置 模型描述 程序设计 参考资料 预测效果 基本描述 Python实现X
  • 【VBScript恶搞代码】关不掉的窗口

    前言 编写vbs脚本没有什么特定要求 只要有系统带了WSH环境就可以 千言万语汇成一句话 有手就行 效果图 操作步骤 先打开记事本 win R打开运行窗口 输入notepad 回车 在记事本上粘贴下列内容 WScript Echo 嘿 谢谢
  • 【算法

    Leetcode206 反转链表 给你单链表的头节点 head 请你反转链表 并返回反转后的链表 示例 1 输入 head 1 2 3 4 5 输出 5 4 3 2 1 示例 2 输入 head 1 2 输出 2 1 示例 3 输入 hea
  • 通过CPUID指令读取处理器信息

    一 CPUID简介 CPUID操作码是一个面向x86架构的处理器补充指令 它的名称派生自CPU识别 作用是允许软件通过CPUID指令读取处理器的详细信息 二 CPUID基本原理 CPUID有很多function号 每个号代表一个功能 CPU
  • nginx 之 Http 请求处理的11个阶段

    处理的11个阶段 POST HEAD realip SERVER REWRITE rewrite FIND CONFIG REWRITE rewrite POST REWRITE PREACCESS limit conn limit req
  • 通过使用Mybatis插件来实现数据的分页功能

    目录 背景 一 SpringBoot的后端 1 手动拼接SQL来实现 2 使用Mybatis插件来实现 二 Vue cli的前端 请求响应跟踪 三 在使用Mybatis插件进行多表查询 表数大于2 出现的问题 1 SQL解决 2 后端查询方
  • 毕设教学:Yolo v5 (v6.1)解析(二)

    Yolo v5 v6 1 解析 二 本文对YOLOv5模型的detect py文件内容进行了详细阐述 笔者以后会定期讲解关于模型的其他的模块与相关技术 笔者也建立了一个关于目标检测的交流群 781334731 大家也可扫描底部图片加入 欢迎
  • java软件官网下载汇总——JDK,eclipse,mysql,maven,idea,Git,oracle

    说明 最近换了一台电脑 所以很多软件都要重新安装 边安装边思考我不如把所有软件的下载官网记录下来 以后就不用到处找了 直接在这篇博文里看就行了 这篇博文没有具体的下载链接 只是官网 因为如果真的不记得进了官网怎么点 那确实也应该复习一下 就
  • 学习1(Linunx操作系统_前期安装)

    1 安装虚拟机 vm12 我下载的是这个版本 vmware workstation full 12 1 0 3272444 exe 下载地址 https www xinsaisai com vmware workstation full 1
  • keep-alive源码解析及实现原理

    keep alive源码 vue 2 6 10 在src core components keep alive js中 代码分析 export default name keep alive abstract true 抽象组件 props
  • 解决Mac应用程序软件不出现在Launchpad里面的方法

    新装了几个软件 可是打开Lauchpad之后却在里面找不到 尝试重置Launchpad方式 1 分别输入终端命令即可 rm Library Application Support Dock db killall Dock
  • ASP.NET 清除模式窗口数据缓存

    使用模式窗口showModalDialog 弹出页面在asp net中经常用到 用的最多的就是点击 修改 按钮 弹出修改页面 修改成功之后 关闭修改页面 刷新父页面 目前存在的一个问题是 刷新完父页面之后 再点击修改按钮弹出修改页面 修改页
  • Java 枚举

    枚举的每一个成员变量就是枚举类型自身的一个实例 枚举的实例在编译的时候就能确定枚举类型有多少个 实例对象 每一个枚举都继承自java lang Enum类 枚举的每个成员默认都是 public static final 的 当定义一个 枚举
  • gf框架使用sqlite3数据库后交叉编译cgo适配arm64-linux

    gf框架使用sqlite3数据库后交叉编译cgo适配arm64 linux 文章目录 gf框架使用sqlite3数据库后交叉编译cgo适配arm64 linux 1 前言 2 解决方案 3 wsl Windows交叉编译cgo工程 3 1