NDK makefile说明

[转自百度文库]


NDK makefile说明

提示事项:

1.Ndkmakefile log用法

__ndk_info  打印普通信息

__ndk_warning  打印警告信息,不会终止makefile

__ndk_error  打印错误信息,会终止makefile

使用时直接调用$(call __ndk_info,PARAM1,PARAM2,PARAM3,PARAM4,PARAM5)

应该是只支持5个参数。

 

如果在makefile中定义了NDK_NO_WARNINGS,NDK_NO_ERRORS,将不会提示上面的警告和错误信息。

 

NDK_LOG:定义这个宏后,会打印出一些系统信息。具体用法一个是在mk文件中定义这个变量,或者是makeAPP=XXX NDK_LOG=YYY, YYY可取任何值。

 

2.在Andorid.mk中include$(CLEAR_VARS)调用以后会清楚所有的LOCAL_变量的值,所以在定义LOCAL_CFLAGS等变量之后不要调用include$(CLEAR_VARS)

被CLEAR_VARS置空的变量有:

  LOCAL_MODULE \

  LOCAL_SRC_FILES \

  LOCAL_C_INCLUDES \

  LOCAL_CFLAGS \

  LOCAL_CXXFLAGS \

  LOCAL_CPPFLAGS \

  LOCAL_LDFLAGS \

  LOCAL_LDLIBS \

  LOCAL_ARFLAGS \

  LOCAL_CPP_EXTENSION \

  LOCAL_STATIC_LIBRARIES \

  LOCAL_STATIC_WHOLE_LIBRARIES \

  LOCAL_SHARED_LIBRARIES \

  LOCAL_MAKEFILE \

  LOCAL_NO_UNDEFINED_SYMBOLS \

  LOCAL_ARM_MODE \

 

3.类似include $(BUILD_EXECUTABLE)这种命令会调用其他mk生成执行文件了。

4.可以在mk文件中加入伪目标,例如:

gpsinclude:

  echo $(GPS_INCLUDE)/*

这样可以显示所有的文件,注意echo之前要用tab

 

5.编译时如果需要显示编译选项,可以使用

makeAPP=NF_Thread V=1

因为V=1会关闭hide变量置为空

 

6.LOCAL_C_INCLUDES这个选项会在definitions.mk被添加到编译选项中了

并且被替换为$$(LOCAL_C_INCLUDES:%=-I%),所以不需要手动在LOCAL_CFLAGS中自己添加。

本地目录页被添加到了编译选项中(-I$$(LOCAL_PATH))

 

7.ANDROID这个编译选项在build-binary.mk中已经有了,不需要自己加

LOCAL_CFLAGS:= -DANDROID $(LOCAL_CFLAGS)

我们在写程序时可以用ANDROID来判断是否为android程序。

 

main.mk 部分解析

 

definitions.mk这个mk文件中定义了很多其他mk要用到的函数。__ndk_info就定义在这里。

definitions.mk中定义了一系列的   makefile函数,其中也包括了c和c++的编译函数,ev-compile-cpp-source,ev-compile-c-source,这两个函数里编写了编译命令。

 

然后会去查找out/host/config.mk,如果没有这个文件,这个文件中定义了宿主机器的系统,体系结构等,后面会用到。就会提示无此文件,并调用build/host-setup.sh去创建这个文件

 

然后定义NDK_APP_OUT := $(NDK_OUT)/apps即out/app目录,定义NDK_HOST_OUT:= $(NDK_OUT)/host/$(HOST_TAG)即out\hostconfig.mk

 

并调用add-toolchain.mk,添加toolchain,在add-toolchain.mk中添加toolchain,在每个路径下都会去寻找build/toolchains/*/setup.mk文件,这个文件中包含了编译c,c++的方法,包括编译动态库,静态库,执行文件,以及编译选项,连接选项,还有系统目录等。

 

Application.mk中的APP_PROJECT_PATH 和APP_MODULES 被使用在definitions.mk

NDK_APP_VARS_REQUIRED中,最终被定义到NDK_APP_VARS中

在Application.mk中还可以定义APP_OPTIMAPP_CPPFLAGS APP_CFLAGS APP_CXXFLAGS APP_PLATFORM APP_BUILD_SCRIP这几个变量下面会讲解到。

 

然后main.mk开始搜索android平台,

搜索路径在build\platforms下,然后列出所有支持的平台,也就是文件夹名。如果在编译模块的时候调用加上NDK_LOG=1,会看到类似Foundsupported platforms:这个字样,然后列出可用平台。代码为:

NDK_PLATFORMS_ROOT:= $(BUILD_SYSTEM)/../platforms

NDK_ALL_PLATFORMS:= $(strip $(notdir $(wildcard $(NDK_PLATFORMS_ROOT)/android-*)))

$(callndk_log,Found supported platforms: $(NDK_ALL_PLATFORMS))

 

根据所有平台,会调用add-platform.mk文件,代码为:

$(foreach_platform,$(NDK_ALL_PLATFORMS),\

  $(eval include$(BUILD_SYSTEM)/add-platform.mk)\

)

 

在add-platform.mk中会通过字符查找找到所有支持的体系结构(arm,x86等),然后为每个构架添加变量并显示每个构架的目录(NDK_LOG可以看到)。

 

然后开始读取应用的信息。搜索所有的Application.mk文件,并为每一个mk文件调用add-application.mk

Add-application.mk文件会找到模块的文件名,如果APP_MODILES中有lib作为前缀,会被去掉,然后判断你需要编译的版本是debug还是release,变量名为APP_OPTIM,如果没定义,默认为release(我们写的文件一般都没定义,所以都是release版本),如果想定义debug版本在Application.mk文件中加入:

APP_OPTIM:= debug

然后回去判断APP_PLATFORM是否定义,如果没有定义,就是用默认的定义,默认的定义在$(APP_PROJECT_PATH)/default.properties)路径中,如果找到这个文件,就按照这个文件定义平台,否则按照android-3定义,也就是说默认为android-3这个平台。

 

然后判断APP_BUILD_SCRIPT是否存在,这个变量可以定义我们自己的编译文件,也就是Android.mk文件,如果没有定义,就是用jni中默认的Android.mk文件,如果自己定义了,就是用自己的文件。

 

NDK_ALL_APPS变量会存储所有的APP

 

退出add-application.mk

 

然后会查找APP是否被定义,如果不定义,列出所有的APP,并abort。

 

接下来就开始编译程序了,首先为每一个APP调用setup-app.mk代码为:

$(foreach_app,$(NDK_APPS),\

  $(eval include $(BUILD_SYSTEM)/setup-app.mk)\

)

 

setup-app.mk中会检查目标平台,为debug/release版本加入编译选项

 

然后调用setup-toolchain.mk文件

这个文件会准备好编译连接库等文件,比如crtbegin_static.o,crtbegin_dynamic.o,crtend_android.o,libc libstdc++libm等文件,然后再最后会调用我们自己写的Android.mk文件,根据我们设置好的编译头文件,库文件,源文件,然后再我们的mk文件里看是include什么类型的文件,以决定编译成执行文件,静态库还是动态库。

 

然后跳回到main.mk中。

根据选择的include文件,进入到相应的mk中。

BUILD_STATIC_LIBRARY      :=$(BUILD_SYSTEM)/build-static-library.mk

BUILD_SHARED_LIBRARY      :=$(BUILD_SYSTEM)/build-shared-library.mk

BUILD_EXECUTABLE          :=$(BUILD_SYSTEM)/build-executable.mk

 

具体编译的东西也没有详细看,

比如BUILD_EXECUTABLE通过调用build-executable.mk,然后调用

$(LOCAL_BUILT_MODULE):$(LOCAL_OBJECTS)

  @ mkdir -p $(dir $@)

  @ echo "Executable     : $(PRIVATE_NAME)"

  $(hide) $(cmd-build-executable)

 

cmd-build-executable为真正的编译

这个变量在build\toolchains\arm-eabi-4.2.1中

definecmd-build-executable

$(TARGET_CC)\

    -nostdlib -Bdynamic \

    -Wl,-dynamic-linker,/system/bin/linker \

    -Wl,--gc-sections \

    -Wl,-z,nocopyreloc \

    $(PRIVATE_SHARED_LIBRARIES) \

    $(TARGET_CRTBEGIN_DYNAMIC_O) \

    $(PRIVATE_OBJECTS) \

    $(PRIVATE_STATIC_LIBRARIES) \

    $(PRIVATE_LDFLAGS) \

    $(PRIVATE_LDLIBS) \

    $(TARGET_CRTEND_O) \

    -o $@

endif

 

 

 

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值