标签:
对于跨平台编译,网上有很多教程和解释,但零零碎碎总感觉不完整,所以想集中整理一下。但跨平台编译是一个很宽泛的问题,如果要全部说清楚,涉及到的问题会有很多,多番查证文献也会拖慢进度,所以决定隐藏不必要的技术细节,从“不求甚解”的角度,解释一下跨平台遇到的各种问题。
1.举例子。比如文章中提到,有一条(1101 0010)的机器码指令,但其实并没有这条指令,只是为了举例子方便而构造出这么一条指令。
2.简化结构。文章中说"可执行程序 = 操作系统头 + 完成任务的机器码",事实上的可执行程序肯定不是这么分块,也不是这么简单,但从宏观来看,笔者认为这么划分可以反映一定的问题,也是合理的。
跨平台编译入门级玩家。
可以熟练使用shell脚本。
简化现实世界的计算机模型,从一种不同的角度描述遇到的问题。
程序源码 = C/C++内置操作 + 各种库调用
int main(int argc, char const *argv[]) { int prices[] = {7, 3, 8, 4, 5}; //c/c++内置操作 std::sort(prices, prices+5); //调用stl库 return 0; }
可执行程序 = 操作系统头 + 完成任务的机器码
计算机 = 操作系统 + 处理器
具体描述:
为什么在windows上编译出来的.exe文件,不能放到linux上直接运行。
android是基于linux的系统,为什么在linux上编译出的可执行程序,在android上不能直接运行。
答:
可执行程序要想被成功执行,需要满足两个基本要求(操作系统头+完成任务的机器码)。
一是操作系统层面,你必须通知操作系统说:这个程序可不是一般的程序,它是可以被执行的!对于Windows来说,需要在[操作系统头]里面写上"windows is great"的字样;对于linux来说,需要写上"linux is the best"的字样,对于android来说,则要写上“android i love you”等等。所以,一个用vs编译出来的程序,只有windows会认为它是可执行的,但对于linux和android来说,“这是什么?我不知道。”
二是处理器层面的,主要由两大处理器厂商(Intel和AMD)所控制。CXX源码编译出的可执行程序,内部存储的是机器码,直接执行机器码的,就是处理器。但不同的处理器对同一条机器码的解释是不一样的。比如说(1101 0010)这条机器码,在Intel看来,这是一条mov ax,ex指令;但在AMD看来,这是一条pop指令。所以,在Intel处理器上编译出的程序,是不能直接跑在AMD处理器上的。
所以,一个程序要正确执行,必须保证:操作系统头信息正确 + 对应处理器的机器码正确。
上面说到,在win上编译的程序只能跑在win的机器上,在linux上编译的程序只能跑在linux上,那想要编译出一个能跑在手机端的程序该怎么做?用跨平台编译器。
跨平台编译器是怎么工作的
从源码到可执行程序,可以分为2个步骤(下面的说法与大多数教程不同)。
第一个步骤是把你自己写的代码,编译成.obj文件;
第二个步骤是把你用到的库文件(比如说stl),与你自己代码生成的.obj文件进行链接,生成最终的可执行文件。
其中,你自己写的代码,本身就是跨平台的,这个是由c++标准委员会规定给各个编译器看的,无须你操心;
你用到的库文件,相当一部分是用汇编实现,不具有跨平台性,所以每个平台都有自己的实现,这个也不用你操心。
你的工作是:写自己的代码,找到对应平台的库文件,把它们的位置都告诉编译器,编译器会生成一个跨平台的可执行文件给你。
到哪里找库文件
Windows上,下载了vs,你只需要在vs里写自己的代码,寻找库文件的任务vs会替你完成。
Linux上,下载了gcc/g++,你只需要写自己的代码,寻找库文件的任务gcc/g++会替你完成。
Mac上,下载了xcode,你只需要写自己的代码,寻找库文件的任务xcode会替你完成。
但由于你不可能在Android上跑一个vs/gcc/xcode,所以这个时候你要去google的官网上下载一个android专用的编译器,也就是ndk。然后,你只需要写自己的代码,寻找库文件的任务ndk会替你完成。
基础概念就这么多,下面是一些跨平台编译的例子。继续看下去之前,请确保电脑上已经正确配置了ndk开发环境。
标签:
原文地址:http://www.cnblogs.com/zzrom/p/5097513.html