Makefile构建Golang项目

Posted 刘贤松handler

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Makefile构建Golang项目相关的知识,希望对你有一定的参考价值。

GNU_make手册.pdf - 豆丁网

Documentation of the GNU Project- GNU Project - Free Software Foundation

make命令是GNU的工程化编译工具,用以实现工程化的管理,提高开发效率。

Make解释Makefile 中的指令(应该说是规则)。在Makefile文件中描述了整个工程所有文件的编译顺序、编译规则。Makefile 有自己的书写格式、关键字、函数。像C 语言有自己的格式、关键字和函数一样。而且在Makefile 中可以使用系统shell所提供的任何命令来完成想要的工作。

Makefile文件
构建规则都写在Makefile文件里面,要学会如何Make命令,就必须学会如何编写Makefile文件。

文件格式

Makefile文件由一系列规则(rules)构成。

每条规则要说明构建的依赖条件,及怎么样去构建。那么格式如下,

# rule
<target> : <prerequisites> 
[tab]  <commands>

target: 目标

prerequisites: 先决条件,或者说依赖条件

tab: 使用tab来缩进

command: 要执行的命令

 

target目标
一个目标,可以是文件名,也可以是某个操作的名字(伪目标),这个名字由自己定义,用来指明要构建的对象。

create:
    touch demo.txt


比如上面这条规则,伪目标为create,命令作用为创建一个文件。要想构建这个操作,调用make create即可。

但是如果目录下,存在一个文件名为create,那么构建命令就不会去执行。为了解决这个问题,当使用伪目标时,可以明确声明create是“伪目标“,告诉make跳过文件检查。

.PHONY: create
create:
        touch a.txt

如果Make命令运行时没有指定目标,默认会执行Makefile文件的第一个目标。

prerequisites先决条件

先决条件,通常是文件名,多个名字用空格分隔。

它定义了一个是否进行重新构建的判断标准: 如果有任何一个先决文件发生改变(时间戳更新),就要重新构建。

result.txt: abc.txt
        cp abc.txt result.txt

abc.txt:
        echo "this is the sbc.txt file" > abc.txt


Makefile例子演示
1. 执行多个目标

.PHONY: cleanall cleanobj cleandiff

cleanall: cleanobj cleandiff
        rm all

cleanobj:
        rm *.o

cleandiff:
        rm *.diff


上面代码可以调用不同目标,删除不同后缀名的文件,也可以调用一个目标(cleanall),删除所有指定类型的文件。2. 构建golang项目

BUILD_NAME:=GoAppName
BUILD_VERSION:=1.0
SOURCE:=*.go
LDFLAGS:=-ldflags "-X main.Version=$BUILD_VERSION"

all: deps build install

deps:
    #安装依赖
    [ -x glide ] && glide install || yum install glide

test: 
    go test

build: test
    go build -o $BUILD_NAME $SOURCE

build_linux: test
    CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build -o $BUILD_NAME $SOURCE

build_win: test
    CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build -o $BUILD_NAME $SOURCE

install: deps build
    go install
    #生成配置文件等
    #cp app.conf.example /etc/app.conf

clean:
    go clean

.PHONY: all deps test build build_linux build_win install clean

这样就很方便地通过一个make命令完成对项目的构建。

Makefile missing separator. Stop.如何解决
Makefile:1: *** missing separator.  Stop.

第一:makefile的命令行,开头必须用tab键,目前没有发现tabstop的设定值的不同,会引起error。例如:

 set tabstop=3(默认)  OR   set tabstop=4等,均可以。

第二:编码方式引起的原因。这个原因不多见,不容易发现。查看/etc/vimrc文件以及~/.vimrc,查看是否有set fileencodings的选项,是否设定了utf-8。没有的话加上。

                                makefile                  missing?separator?                  stop                  makefile常见错误              
[解决办法]
这个makefile里不要乱用TAB,只有命令所在的行才能且只能以TAB开头!
 
其他的如,make变量的定义、赋值,make内定函数如$(error "strings")都不能以TAB开头,不然make会将其作为命令来处理!
[解决办法]
1.第一行ifnep这个符号是做什么的?大概是ifneq吧?
2.很多地方你打的是空格,你最好尝试习惯去用tab键
3.第八行和第十行必须用tab开头
ifneq ($(KERNELRELEASE),)
    obj-m += module.o
else
    PWD := $(shell pwd)
    KVER := $(shell uname -r)
    KDIR := /lib/modules/$(KVER)/build
all:
        $(MAKE)    -C $(KDIR) M= $(PWD)
clean:
        rm -rf *.o *.mod.c *.ko *.symvers *.order *.makers
endif
[解决办法]
如果排除了TAB用空格代替的问题后、以及由中文“:”等问题后,问题还存在
那么很可能是文件编码格式的问题
查看一下Makefile 文件编码格式是不是utf-8的,还带有BOM标记在文件头 
$ xxd -l 16 Makefile
0000000: efbb bf61 6c6c 3a0a 2020 6563 686f 2068  ...all:.
 
去掉红色字体部分就OK了 

参考:

使用makefile构建golang项目_Tiny鹏的博客-CSDN博客_golang makefile

Makefile missing separator. Stop.怎么解决_limanjihe的博客-CSDN博客_makefile missing separator

Makefile 语法入门_阿飞__的博客-CSDN博客_makefile语法 

Makefile的语法_【ql君】qlexcel的博客-CSDN博客_makefile语法

以上是关于Makefile构建Golang项目的主要内容,如果未能解决你的问题,请参考以下文章

golang 构建工具之 Makefile

Golang:无惧makefile

使用 Makefile.am/Makefile.in 在 Ubuntu Linux 中构建 c++ 项目

Linux项目自动化构建工具-make/Makefile

从命令行构建 Eclipse Makefile 项目

如何为使用 makefile 构建的整个项目生成一个大型依赖映射?