3.2 gcc编译器windows平台下移植工作原理
可执行程序从源码到可执行的二进制程序主要步骤如下:
1) 预编译(Pre-Processing):完成对预编译代码的处理;
2) 编译(Compiling):将源代码编译成汇编代码;
3) 汇编(Assembling):将汇编代码会变成目标文件;
4)链接(Linking):将目标代码和所需要库链成一个完整的应用程序。
本文通过IDE环境实现gcc的上述各个功能的自动链接执行。首先,下载安装Sourcery G++ Lite for ARM装程序,获取相应的编译器、连接器、以及运行库文件等文件信息。然后,将这些文件打包到开发环境安装包中,通过IDE应用程序 NaBuild.exe调用相应的gcc 命令,执行当前程序的编译,以及编译信息的输出等工作。Gcc工具链的各个执行文件都是基于控制台的执行程序,而IDE是图形用户界面(GUI)程序,通过VC6.0编程软件编程实现将他们执行的各种输出信息收集并放到IDE的输出窗口中显示。实现IDE的输出窗口中编译信息的方法如下:
1) 用户点击菜单-编译后,建立一个后台线程OperateBuildThread;
2) 后台线程创建一个匿名管道,发起一个命令子进程以执行编译整个工程的make命令,并将该命令子进程的标准输出和错误输出均定向到由父进程创建的匿名管道的写端,IDE后台线程通过该匿名管道读取编译信息;
3) 后台线程再将所有通过管道获取的编译信息,传送给界面线程显示输出。
伪代码信息表示如下:
//创建匿名管道,用来获取编译信息
if (!CreatePipe(&hRead,&hWrite,&sa,0))
{
MessageBox( "Error On CreatePipe() ");
return “create error”;
}
//建立子进程用来,调用执行相应的gcc程序,发送执行命令
if (!CreateProcess(NULL, strCommand.GetBuffer(0)
,NULL,NULL,TRUE,NULL,NULL,makefilefileaddr,&si,&pi)) {
m_Edit1="Error On CreateProcess() ";
MessageBox( "Error on CreateProcess() ");
return m_Edit1;
}
CloseHandle(hWrite); //关闭写句柄
//循环从匿名管道读取编译信息,如果出错直接退出循环
while (true)
{
if (ReadFile(hRead,buffer,1023,&bytesRead,NULL) == NULL)
break;
strBuf = buffer;
if (strBuf.Find("reserved") != -1)
{
strBuf = strBuf.Mid(strBuf.Find("reserved") +8);
strcpy(buffer, strBuf.GetBuffer(0));
strBuf.ReleaseBuffer();
}
m_Edit1 += buffer;
Sleep(200);
}
return m_Edit1;
4 hex程序下载
该系统通过基于FlashMagic所提供的Command Line方法,将.hex程序通过串口线下载到嵌入式系统中。首先将FlashMagic库文件以及Command Line命令文件打包到集成环境目录下,通过IDE应用程序 NaBuile.exe调用相应的命令信息,实现程序的烧写功能。
例如:FM DEVICE(LPC1758,11.0592) COM(3,19200) HARDWARE(BOOTEXEC,25,250) ERASE(DEVICE, PROTECTISP) HEXFILE(TEST.HEX, NOCHECKSUMS, NOFILL, NOPROTECTISP) VERIFY(TEST.HEX, NOCHECKSUMS),表示以擦除程序的方式将hex程序TEST.HEX执行下载。
通过VC6.0编程实现了hex程序下载功能,主要方法步骤如下(程序流程图如图4所示):
1) 用户点击下载按钮会弹出下载配置界面,用来配置波特率、串口号、擦除模式等,如图2所示;
2) 启动后台线程实现具体下载功能;
3) 获取界面配置信息,根据获取的配置信息组包下载命令行参数;
4) 创建匿名管道,用来截获下载时返回的信息以及错误记录;
5) 通过函数CreateProcess()创建子进程,调用FM命令行程序,并传递步骤3所组包的命令行参数,实现HEX文件的下载;
6) 通过匿名管道读取下载信息,并传送到界面线程显示,如图3所示。
图 2 下载配置界面