- ·上一篇文章:Linux下的C编程实战之文件系统编程
- ·下一篇文章:资深Linux程序员的开发经验谈(下)
Linux下的C编程实战之开发平台搭建
1.引言
Linux操作系统在服务器领域的应用和普及已经有较长的历史,这源于它的开源特点以及其超越Windows的安全性和稳定性。而近年来,Linux操作系统在嵌入式系统领域的延伸也可谓是如日中天,许多版本的嵌入式Linux系统被开发出来,如ucLinux、RTLinux、ARM-Linux等等。在嵌入式操作系统方面,Linux的地位是不容怀疑的,它开源、它包含TCP/IP协议栈、它易集成GUI。
鉴于Linux操作系统在服务器和嵌入式系统领域愈来愈广泛的应用,社会上越来越需要基于Linux操作系统进行编程的开发人员。
浏览许多论坛,经常碰到这样的提问:“现在是不是很流行unix/linux下的c编程?所以想学习一下!但是不知道该从何学起,如何下手!有什么好的建议吗?各位高手!哪些书籍比较合适初学者?在深入浅出的过程中应该看哪些不同层次的书?比如好的网站、论坛请大家赐教!不慎感激!”
鉴于读者的需求,在本文中,笔者将对Linux平台下C编程的几个方面进行实例讲解,并力求回答读者们关心的问题,以与读者朋友们进行交流,共同提高。在本文的连载过程中,有任何问题或建议,您可以给笔者发送email:21cnbao@21cn.com,您也可以进入笔者的博客参与讨论:http://blog.donews.com/21cnbao。
笔者建议在PC内存足够大的情况下,不要直接安装Linux操作系统,最好把它安装在运行VMWare虚拟机软件的Windows平台上,如下图:
在Linux平台下,可用任意一个文本编辑工具编辑源代码,但笔者建议使用emacs软件,它具备语法高亮、版本控制等附带功能,如下图:
2.GCC编译器
GCC是Linux平台下最重要的开发工具,它是GNU的C和C++编译器,其基本用法为:
gcc [options] [filenames]
options为编译选项,GCC总共提供的编译选项超过100个,但只有少数几个会被频繁使用,我们仅对几个常用选项进行介绍。
假设我们编译一输出“Hello World”的程序:
最简单的编译方法是不指定任何编译选项:
gcc helloworld.c
它会为目标程序生成默认的文件名a.out,我们可用-o编译选项来为将产生的可执行文件指定一个文件名来代替a.out。例如,将上述名为helloworld.c的C程序编译为名叫helloworld的可执行文件,需要输入如下命令:
gcc –o helloworld helloworld.c
-c选项告诉GCC仅把源代码编译为目标代码而跳过汇编和连接的步骤;
-S 编译选项告诉GCC 在为 C代码产生了汇编语言文件后停止编译。GCC 产生的汇编语言文件的缺省扩展名是.s,上述程序运行如下命令:
gcc –S helloworld.c
将生成helloworld.c的汇编代码,使用的是AT&T汇编。用emacs打开汇编代码如下图:
-E选项指示编译器仅对输入文件进行预处理。当这个选项被使用时,预处理器的输出被送到标准输出(默认为屏幕)而不是储存在文件里。
-O选项告诉GCC对源代码进行基本优化从而使得程序执行地更快;而-O2选项告诉GCC产生尽可能小和尽可能快的代码。使用-O2选项编译的速度比使用-O时慢,但产生的代码执行速度会更快。
-g选项告诉GCC产生能被GNU调试器使用的调试信息以便调试你的程序,可喜的是,在GCC里,我们能联用-g和-O (产生优化代码)。
-pg选项告诉GCC在你的程序里加入额外的代码,执行时,产生gprof用的剖析信息以显示你的程序的耗时情况。
3.GDB调试器
GCC用于编译程序,而Linux的另一个GNU工具gdb则用于调试程序。gdb是一个用来调试C和C++程序的强力调试器,我们能通过它进行一系列调试工作,包括设置断点、观查变量、单步等。
其最常用的命令如下:
file:装入想要调试的可执行文件。
kill:终止正在调试的程序。
list:列表显示源代码。
next:执行一行源代码但不进入函数内部。
step:执行一行源代码而且进入函数内部。
run:执行当前被调试的程序
quit:终止gdb
watch:监视一个变量的值
break:在代码里设置断点,程序执行到这里时挂起
make:不退出gdb而重新产生可执行文件
shell:不离开gdb而执行shell
下面我们来演示怎样用GDB来调试一个求0+1+2+3+…+99的程序:
执行如下命令编译sum.c(加-g选项产生debug信息):
gcc –g –o sum sum.c
在命令行上键入gdb sum并按回车键就可以开始调试sum了,再运行run命令执行sum,屏幕上将看到如下内容:

list命令:
list命令用于列出源代码,对上述程序两次运行list,将出现如下画面(源代码被标行号):

根据列出的源程序,如果我们将断点设置在第5行,只需在gdb 命令行提示符下键入如下命令设置断点:(gdb) break 5,执行情况如下图:

这个时候我们再run,程序会停止在第5行,如下图:

设置断点的另一种语法是 break <function>,它在进入指定函数(function)时停住。
相反的,clear用于清除所有的已定义的断点,clear <function>清除设置在函数上的断点, clear <linenum>则清除设置在指定行上的断点。
watch命令:
watch命令用于观查变量或表达式的值,我们观查sum变量只需要运行watch sum:

watch <expr>为表达式(变量)expr设置一个观察点,一量表达式值有变化时,程序会停止执行。
要观查当前设置的watch,可以使用info watchpoints命令。
next、step命令:
next、step用于单步执行,在执行的过程中,被watch变量的变化情况将实时呈现(分别显示Old value和New value),如下图:

next、step命令的区别在于step遇到函数调用,会跳转到到该函数定义的开始行去执行,而next则不进入到函数内部,它把函数调用语句当作一条普通语句执行。
4.Make
make是所有想在Linux系统上编程的用户必须掌握的工具,对于任何稍具规模的程序,我们都会使用到make,几乎可以说不使用make的程序不具备任何实用价值。
在此,我们有必要解释编译和连接的区别。编译器使用源码文件来产生某种形式的目标文件(object files),在编译
Linux操作系统在服务器领域的应用和普及已经有较长的历史,这源于它的开源特点以及其超越Windows的安全性和稳定性。而近年来,Linux操作系统在嵌入式系统领域的延伸也可谓是如日中天,许多版本的嵌入式Linux系统被开发出来,如ucLinux、RTLinux、ARM-Linux等等。在嵌入式操作系统方面,Linux的地位是不容怀疑的,它开源、它包含TCP/IP协议栈、它易集成GUI。
鉴于Linux操作系统在服务器和嵌入式系统领域愈来愈广泛的应用,社会上越来越需要基于Linux操作系统进行编程的开发人员。
浏览许多论坛,经常碰到这样的提问:“现在是不是很流行unix/linux下的c编程?所以想学习一下!但是不知道该从何学起,如何下手!有什么好的建议吗?各位高手!哪些书籍比较合适初学者?在深入浅出的过程中应该看哪些不同层次的书?比如好的网站、论坛请大家赐教!不慎感激!”
鉴于读者的需求,在本文中,笔者将对Linux平台下C编程的几个方面进行实例讲解,并力求回答读者们关心的问题,以与读者朋友们进行交流,共同提高。在本文的连载过程中,有任何问题或建议,您可以给笔者发送email:21cnbao@21cn.com,您也可以进入笔者的博客参与讨论:http://blog.donews.com/21cnbao。
笔者建议在PC内存足够大的情况下,不要直接安装Linux操作系统,最好把它安装在运行VMWare虚拟机软件的Windows平台上,如下图:
![]() |
在Linux平台下,可用任意一个文本编辑工具编辑源代码,但笔者建议使用emacs软件,它具备语法高亮、版本控制等附带功能,如下图:
![]() |
2.GCC编译器
GCC是Linux平台下最重要的开发工具,它是GNU的C和C++编译器,其基本用法为:
gcc [options] [filenames]
options为编译选项,GCC总共提供的编译选项超过100个,但只有少数几个会被频繁使用,我们仅对几个常用选项进行介绍。
假设我们编译一输出“Hello World”的程序:
| /* Filename:helloworld.c */ main() { printf("Hello World\n"); } |
最简单的编译方法是不指定任何编译选项:
gcc helloworld.c
它会为目标程序生成默认的文件名a.out,我们可用-o编译选项来为将产生的可执行文件指定一个文件名来代替a.out。例如,将上述名为helloworld.c的C程序编译为名叫helloworld的可执行文件,需要输入如下命令:
gcc –o helloworld helloworld.c
-c选项告诉GCC仅把源代码编译为目标代码而跳过汇编和连接的步骤;
-S 编译选项告诉GCC 在为 C代码产生了汇编语言文件后停止编译。GCC 产生的汇编语言文件的缺省扩展名是.s,上述程序运行如下命令:
gcc –S helloworld.c
将生成helloworld.c的汇编代码,使用的是AT&T汇编。用emacs打开汇编代码如下图:

-E选项指示编译器仅对输入文件进行预处理。当这个选项被使用时,预处理器的输出被送到标准输出(默认为屏幕)而不是储存在文件里。
-O选项告诉GCC对源代码进行基本优化从而使得程序执行地更快;而-O2选项告诉GCC产生尽可能小和尽可能快的代码。使用-O2选项编译的速度比使用-O时慢,但产生的代码执行速度会更快。
-g选项告诉GCC产生能被GNU调试器使用的调试信息以便调试你的程序,可喜的是,在GCC里,我们能联用-g和-O (产生优化代码)。
-pg选项告诉GCC在你的程序里加入额外的代码,执行时,产生gprof用的剖析信息以显示你的程序的耗时情况。
3.GDB调试器
GCC用于编译程序,而Linux的另一个GNU工具gdb则用于调试程序。gdb是一个用来调试C和C++程序的强力调试器,我们能通过它进行一系列调试工作,包括设置断点、观查变量、单步等。
其最常用的命令如下:
file:装入想要调试的可执行文件。
kill:终止正在调试的程序。
list:列表显示源代码。
next:执行一行源代码但不进入函数内部。
step:执行一行源代码而且进入函数内部。
run:执行当前被调试的程序
quit:终止gdb
watch:监视一个变量的值
break:在代码里设置断点,程序执行到这里时挂起
make:不退出gdb而重新产生可执行文件
shell:不离开gdb而执行shell
下面我们来演示怎样用GDB来调试一个求0+1+2+3+…+99的程序:
| /* Filename:sum.c */ main() { int i, sum; sum = 0; for (i = 0; i < 100; i++) { sum + = i; } printf("the sum of 1+2+...+ is %d", sum); } |
执行如下命令编译sum.c(加-g选项产生debug信息):
gcc –g –o sum sum.c
在命令行上键入gdb sum并按回车键就可以开始调试sum了,再运行run命令执行sum,屏幕上将看到如下内容:

list命令:
list命令用于列出源代码,对上述程序两次运行list,将出现如下画面(源代码被标行号):

根据列出的源程序,如果我们将断点设置在第5行,只需在gdb 命令行提示符下键入如下命令设置断点:(gdb) break 5,执行情况如下图:

这个时候我们再run,程序会停止在第5行,如下图:

设置断点的另一种语法是 break <function>,它在进入指定函数(function)时停住。
相反的,clear用于清除所有的已定义的断点,clear <function>清除设置在函数上的断点, clear <linenum>则清除设置在指定行上的断点。
watch命令:
watch命令用于观查变量或表达式的值,我们观查sum变量只需要运行watch sum:

watch <expr>为表达式(变量)expr设置一个观察点,一量表达式值有变化时,程序会停止执行。
要观查当前设置的watch,可以使用info watchpoints命令。
next、step命令:
next、step用于单步执行,在执行的过程中,被watch变量的变化情况将实时呈现(分别显示Old value和New value),如下图:

next、step命令的区别在于step遇到函数调用,会跳转到到该函数定义的开始行去执行,而next则不进入到函数内部,它把函数调用语句当作一条普通语句执行。
4.Make
make是所有想在Linux系统上编程的用户必须掌握的工具,对于任何稍具规模的程序,我们都会使用到make,几乎可以说不使用make的程序不具备任何实用价值。
在此,我们有必要解释编译和连接的区别。编译器使用源码文件来产生某种形式的目标文件(object files),在编译



