text必须带unicode中点·,否则go编译器无法识别函数;汇编文件名需为xxx_架构.s、同包go文件须声明原型、fp偏移需手算(如a+0(fp))、跨平台须分文件且路径严格匹配。

TEXT 必须带 Unicode 中点 ·,否则函数根本不会被 Go 编译器识别——这是最常卡住新手的第一步。
汇编文件名和函数名必须严格匹配 Go 声明
Go 不会自动发现你写了 .s 文件,它只在满足三个条件时才去链接汇编实现:
• 同一包、同一目录下存在 Go 源文件,且其中声明了对应函数原型(如 func Add(a, b int64) int64)
• 汇编文件名以 .s 结尾(不是 .asm 或 .S)
• 函数符号用 TEXT ·Add(SB) 形式定义,其中 · 是 U+00B7,不是 ASCII 点号 . 或全角中点
FP 偏移必须手算,不能靠猜
参数和返回值都通过帧指针 FP 加偏移访问,规则固定:
• 64 位平台下每个参数/返回值占 8 字节
• a+0(FP) 是第一个参数,b+8(FP) 是第二个,ret+16(FP) 是返回值地址(两个 int64 输入 + 一个 int64 输出 = 16 字节)
• 错写成 a+0(SP) 可能暂时跑通,但实际读的是栈顶附近随机内存,行为不可预测
• 局部变量要用 SP,例如 MOVQ , -8(SP),但前提是函数签名后声明了栈帧大小,比如 -16 表示分配 16 字节本地空间
验证汇编是否真正生效,别信构建日志
构建成功 ≠ 汇编代码被使用。唯一可靠方式是反汇编:
• 先执行 go build -o myapp .
• 再运行 go tool objdump -s "main\.Add" ./myapp(注意转义点号)
• 如果输出里出现你写的 MOVQ、ADDQ,说明接入成功;如果看到 CALL runtime.morestack_noctxt,说明 Go 还在用自己生成的版本
• go tool compile -S 输出的是 Go 编译器中间汇编,不是你的手写代码,不能用来验证
跨平台必须分文件,GOOS/GOARCH 不匹配就静默失效
Go 汇编没有条件编译指令,不同平台需物理隔离:
• add_amd64.s 只在 GOARCH=amd64 时参与构建
• add_arm64.s 只在 GOARCH=arm64 时生效
• 放错目录(比如塞进 internal/ 或子包)会导致文件被忽略,且不报错
• 在 macOS 上用 amd64 文件构建 Linux 二进制,汇编不会被加载——交叉编译时仍需匹配目标平台的 .s 文件
MOVQ,而是让 Go 运行时准确找到、正确调用、完全信任那段手写的字节序列。每一个 ·、每一处 FP 偏移、每一个文件路径,都得严丝合缝。golang免费学习笔记(深入):立即使用
在学习笔记中,你将探索golang的核心概念和高级技巧!











