linuxc一站式编程答案_第1页
linuxc一站式编程答案_第2页
linuxc一站式编程答案_第3页
免费预览已结束,剩余6页可下载查看

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、linuxc一站式编程答案【篇一:linux下c语言编程基础知识】在linux下进行c语言编程所需要的基础知识.在这篇文章当中,我们将会学到以下内容:源程序编译makefile的编写程序库的链接程序的调试头文件和系统求助源程序的编译在linux下面,如果要编译一个c语言源程序,我们要使用gnu的gcc编译器.下面我们以一个实例来说明如何使用gcc编译器.假设我们有下面一个非常简单的源程序(hello.c):intmain(intargc,char*argv)(printf(hellolinuxn);要编译这个程序,我们只要在命令行下执行:gcc-ohellohello.cgcc编译器就会为我们

2、生成一个hello的可执行文件.执行./hello就可以看到程序的输出结果了.命令行中gcc表示我们是用gcc来编译我们的源程序,-o选项表示我们要求编译器给我们输出的可执行文件名为hello而hello.c是我们的源程序文件.gcc编译器有许多选项,一般来说我们只要知道其中的几个就够了.-o选项我们已经知道了,表示我们要求输出的可执行文件名.-c选项表示我们只要求编译器输出目标代码,而不必要输出可执行文件.-g选项表示我们要求编译器在编译的时候提供我们以后对程序进行调试的信息.知道了这三个选项,我们就可以编译我们自己所写的简单的源程序了,如果你想要知道更多的选项,可以查看gcc的帮助文档,那

3、里有着许多对其它选项的详细说明.gcc编译器还有2个非常有用的选项(-o2-wall),几乎在所有用gcc编译的程序中都可以看到这2个选项.-o2选项表示我们希望编译器在编译的时候对我们的程序进行一定程度的优化.2表示我们优化的级别是2.当然你也可以不使用2,而是使用1-3的中的任何一个,不过习惯上我们都使用2的优化级别.关于优化的详细情况可以参考gcc的帮助手册.-wall是警告选项,表示我们希望gcc在编译的时候,让gcc输出她认为的一些程序中可能会出问题的一些警告信息,比如指针没有初始化就进行赋值等等一些警告信息.1. makefile的编写假设我们有下面这样的一个程序,源代码如下:#

4、/*main.c*/includeincludeintmain(intargc,char*argv)mytool1_print(hello);mytool2_print(hello);/*mytool1.h*/#ifndef_mytool_1_h#define_mytool_1_hvoidmytool1_print(char*print_str);#endif/*mytool1.c*/includevoidmytool1_print(char*print_str)printf(thisismytool1print%sn,print_str);/*mytool2.h*/#ifndef_mytoo

5、l_2_h#define_mytool_2_hvoidmytool2_print(char*print_str);#endif/*mytool2.c*/includevoidmytool2_print(char*print_str)(一一printf(thisismytool2print%sn,print_str);_当然由于这个程序是很短的我们可以这样来编译gcc-cmain.c-i.gcc-cmytool1.c-i.gcc-cmytool2.c-i.gcc-omainmain.omytool1.omytool2.o因为我们在程序中使用了我们自己的2个头文件,而在包含这2个头文件的时候,我们

6、使用的是这样编译器在编译的时候会去系统默认的头文件路径找我们的2个头文件,由于我们的2个头文件不在系统能够的缺省路径下面,所以我们自己扩展系统的缺省路径,为此我们使用了-i.选项,表示将系统缺省的头文件路径扩展到当前路径.这样的话我们也可以产生main程序,而且也不是很麻烦.但是考虑一下如果有一天我们修改了其中的一个文件(比如说mytool1.c)那么我们难道还要重新输入上面的命令?也许你会说,这个很容易解决啊,我写一个shell脚本,让她帮我去完成不就可以了.是的对于这个程序来说,是可以起到作用的.但是当我们把事情想的更复杂一点,如果我们的程序有几百个源程序的时候,难道也要编译器重新一个一个

7、的去编译?为此,聪明的程序员们想出了一个很好的工具来做这件事情,这就是make.我们只要执行一下make,就可以把上面的问题解决掉.在我们执行make之前,我们要先编写一个非常重要的文件.-makefile.对于上面的那个程序来说,可能的一个makefile的文件是:#这是上面那个程序的makefile文件main:main.omytool1.omytool2.ogcc-omainmain.omytool1.omytool2.omain.o:main.cmytool1.hmytool2.hgcc-cmain.c-i.mytool1.o:mytool1.cmytool1.hgcc-cmytool

8、1.c-i.mytool2.o:mytool2.cmytool2.hgcc-cmytool2.c-i.有了这个makefile文件,不管我们什么时候修改了源程序当中的什么文件,我们只要执行make命令,我们的编译器都只会去编译和我们修改的文件有关的文件,其它的文件她连理都不想去理的.下面我们学习makefile是如何编写的.在makefile中也#开始的行都是注释行.makefile中最重要的是描述文件的依赖关系的说明.一般的格式是:target:componentstabrule第一行表示的是依赖关系.第二行是规则.main:main.omytooll.omytool2.o表示我们的目标(t

9、arget)main的依赖对象(components)是main.omytool1.omytool2.o当倚赖的对象在目标修改后修改的话,就要去执行规则一行所指定的命令.就象我们的上面那个makefile第三行所说的一样要执行gcc-omainmain.omytool1.omytool2.o注意规则一行中的tab表示那里是一个tab键makefile有三个非常有用的变量.分另U是email=$,$%5e,$,$A,$/emailintmain(intargc,char*argv)(doublevalue=15;printf(value:%fn,log(value);这个程序相当简单,但是当我们

10、用gcc-otemptemp.c编译时会出现下面所示的错误./tmp/cc33kydu.o:infunction'main:/tmp/cc33kydu.o(.text+0xe):undefinedreferenceto'logcollect2:ldreturned1exitstatus出现这个错误是因为编译器找不到log的具体实现.虽然我们包括了正确的头文件,但是我们在编译的时候还是要连接确定的库.在linux下,为了使用数学函数,我们必须和数学库连接,为此我们要加入-lm选项.gcc-otemptemp.c-lm这样才能够正确的编译.也许有人要问,前面我们用printf函数的

11、时候怎么没有连接库呢?是这样的,对于一些常用的函数的实现,gcc编译器会自动去连接一些常用库,这样我们就没有必要自己去指定了.有时候我们在编译程序的时候还要指定库的路径,这个时候我们要用到编译器的-l选项指定路径.比如说我们有一个库在/home/hoyt/mylib下,这样我们编译的时候还要加上-l/home/hoyt/mylib.对于一些标准库来说,我们没有必要指出路径.只要它们在起缺省库的路径下就可以了.系统的缺省库的路径/lib/usr/lib/usr/local/lib(你可以查看你的/etc/ld.conf文件来看看你的系统指定了那几个缺省的路径)在这三个路径下面的库,我们可以不指定

12、路径.还有一个问题,有时候我们使用了某个函数,但是我们不知道库的名字,这个时候怎么办呢?很抱歉,对于这个问题我也不知道答案,我只有一个傻办法.首先,我到标准库路径下面去找看看有没有和我用的函数相关的库,我就这样找到了线程(thread)函数的库文件(libpthread.a).当然,如果找不到,只有一个笨方法.比如我要找sin这个函数所在的库.就只好用nm-o/lib/*.so|grepsin/sin命令,然后看/sin文件,到那里面去找了.在sin文件当中,我会找到这样的一行libm-2.1.2.so:00009fa0wsin这样我就知道了sin在libm-2.1.2.so库里面,我用-lm

13、选项就可以了(去掉前面的lib和后面的版本标志,就剩下m了所以是-lm).如果你知道怎么找,请赶快告诉我,我回非常感激的.谢谢!4. 程序的调试我们编写的程序不太可能一次性就会成功的,在我们的程序当中,会出现许许多多我们想不到的错误,这个时候我们就要对我们的程序进行调试了.最常用的调试软件是gdb.如果你想在图形界面下调试程序,那么你现在可以选择xxgdb.记得要在编译的时候加入-g选项.关于gdb的使用可以看gdb的帮助文件.由于我很少使用这个软件,所以我也不能够详细的说出如何使用.不过我不喜欢用gdb.跟踪一个程序是很烦的事情,我一般用在程序当中输出中间变量的值来调试程序的.当然你可以选择

14、自己的办法,没有必要去学别人的.现在有了许多ide环境,里面已经自己带了调试器了.你可以选择几个试一试找出自己喜欢的一个用.5. 头文件和系统求助有时候我们只知道一个函数的大概形式,不记得确切的表达式,或者是不记得着函数在那个头文件进行了说明.这个时候我们可以求助系统.比如说我们想知道fread这个函数的确切形式,我们只要执行manfread系统就会输出着函数的详细解释的.和这个函数所在的头文件说明了.如果我们要write这个函数的说明,当我们执行manwrite时,输出的结果却不是我们所需要的.因为我们要的是write这个函数的说明,可是出来的却是write这个命令的说明.为了得到write

15、的函数说明我们要用man2write.2表示我们用的write这个函数是系统调用函数,还有一个我们常用的是3表示函数是c的库函数.记住,man永远是最好的求助工具。linux下进程的创建(第二章)刖曰:这篇文章是用来介绍在linux下和进程相关的各个概念.我们将会学到:进程的概念进程的标志进程的创建守护进程的创建1。进程的概念linux操作系统是面向多用户的.在同一时间可以有许多用户向操作系统发出各种命令.那么操作系统是怎么实现多用户的环境呢?在现代的操作系统里面,都有程序和进程的概念.那么什么是程序,什么是进程呢?通俗的讲程序是一个包含可以执行代码的文件,是一个静态的文件.而进程是一个开始执

16、行但是还没有结束的程序的实例.就是可执行文件的具体实现.一个程序可能有许多进程,而每一个进程又可以有许多子进程.依次循环下去,而产生子孙进程.当程序被系统调用到内存以后,系统会给程序分配一定的资源(内存,设备等等)然后进行一系列的复杂操作,使程序变成进程以供系统调用.在系统里面只有进程没有程序,为了区分各个不同的进程,系统给每一个进程分配了一个id(就象我们的身份证)以便识别.为了充分的利用资源,系统还对进程区分了不同的状态.将进程分为新建,运行,阻塞,就绪和完成五个状态.新建表示进程正在被创建,运行是进程正在运行,阻塞是进程正在等待某一个事件发生,就绪是表示系统正在等待cpu来执行命令,而完

17、成表示进程已经结束了系统正在回收资源.关于进程五个状态的详细解说我们可以看操作系统上面有详细的解说。【篇二:实验一-linuxc编程工具gcc和gdbxt实验报告书课程名:linux程序设计题目:实验一班级:软件131学号:姓名:王裕一、实验目的与要求1. 掌握linuxc开发过程中的基本概念;2. 掌握如gcc,gdb等开发工具的使用。二、实验内容1. 将参考代码录入到testl.c文件中,编译执行后发现结果与预期不一致,请使用gdb调试,完成字符串反序输出功能。三、参考源代码#includestdio.h#includestdlib.h#includestring.hintreverse_

18、str(char*string);intmain(void)charstring=linuxctools:gccandgdb;printf(theoriginalstringis%sn,string);reverse_str(string);intreverse_str(char*str)char*new_str;inti,size;size=strlen(str);if(new_str=(char*)malloc(size+1)=null)return-1;for(i=0;isize;i+)new_strsize-i=stri;new_strsize+1=;printf(thereverse

19、dstringis%sn,new_str);free(new_str);return0;四、实验步骤步骤1.编辑源代码testl.cmkdirtestlcdtestlgedittestl.c(1)使用gedit编辑器,建议课外学习vim;(2)分析代码中语句功能。(1) 步骤2.编译源代码testl.cgcctestl.c-otestl-g复习gcc常用选项;帮助学生排查编译时错误。(1) 分析输出结果步骤3.调试testlgdbtestl回顾调试的基本方法:跟踪语句执彳了过程,观察执行结果;设置断点的三种基本方法:(2) bline_numberbline_numberifcondition

20、_expressionbfunction_name查看中间扁出结果:pvarsetprintelement0parray_name或pointer说明:gdb中查看字符串变量值可通过“setprintelement0”命令,一次性显示字符串所有内容。分析中间结果,修改28行语句为new_strsize-i-1=stri;五、实验结果与截图编写test1.c文件并编译设置断点,进行gdb测试跟踪变量。执行到i=27时size-i=0,str27已经超过str字符串限制,于是new_str0=10'。输出new_str时,由于超过限制无法输出。所以修改程序第28行语句为new_strsiz

21、e-i-1=stri;正确的程序运行结果如下图所示。1. 六、思考题分析以下代码,完成指定范围内数值累加功能:#includestdio.h/*函数功能:将low到high之间的数值累加求和*/intadd_range(intlow,inthigh)(inti,sum;for(i=low;i=high;i+)sum=sum+i;returnsum;intmain(void)(intresult2;result0=add_range(1,10);result1=add_range(1,100);printf(result0=%desult1=%dn,result0,result1);return

22、0;答:进行累加时,局部变量sum的值会被内存保存下来,会导致数值错误,要对其初始化为0。把inti,sum;改为inti;intsum=0;结构化编程经常将相近功能编译成库形式,方便调用。请查阅资料,使用gcc将一组功能相关的源文件编译成静态库或动态库?建立库文件的源文件print1.c和print2.c如下所示:/*print1.c*/#includestdio.hvoidprint1(intarg)(printf(%dn,arg);/*print2.c*/#includestdio.hvoidprint2(char*arg)(printf(%sn,arg);【篇三:linuxc网络网络编

23、程面试题收集】基础部份:1.下列程序在32位linux或unix中的结果是什么?func(char*str)(printf(%d,sizeof(str);printf(%d,strlen(str);main()(chara=123456789;printf(%d,sizeof(a);func(a);答:1049网络/网络编程部份:1、connect方法会阻塞,请问有什么方法可以避免其长时间阻塞?答:最通常的方法最有效的是加定时器;也可以采用非阻塞模式。2、网络中,如果客户端突然掉线或者重启,服务器端怎么样才能立刻知道?答:若客户端掉线或者重新启动,服务器端会收到复位信号,每一种tcp/ip得实

24、现不一样,控制机制也不一样。2. 在子网210.27.48.21/30种有多少个可用地址?分别是什么?答:简:30表示的是网络号(networknumber)是30位,剩下2位中11是广播(broadcast)地址,00是multicast地址,只有01和10可以作为hostaddress。详:210.27.48.21/30代表的子网的网络号是30位,即网络号是210.27.48.21255.255.255.251=210.27.48.20,此子网的地址空间是2位,即可以有4个地址:210.27.48.20,210.27.48.21,210.27.48.22,210.27.48.23。第一个地

25、址的主机号(hostnumber/id)是0,而主机号0代表的是multicast地址。最后一个地址的最后两位是11,主机号每一位都为1代表的是广播(broadcast)地址。所以只有中间两个地址可以给host使用。其实那个问题本身不准确,广播或multicast地止也是可以使用的地址,所以回答4也应该正确,当然问的人也可能是想要你回答2。我个人觉得最好的回答是一个广播地址,一个multicast地址,2个unicast地址。3. ttl是什么?有什么用处,通常那些工具会用到它?(ping?traceroute?ifconfig?netstat?)答:简:ttl是timetolive,一般是h

26、upcount,每经过一个路由就会被减去一,如果它变成0,包会被丢掉。它的主要目的是防止包在有回路的网络上死转,浪费网络资源。ping和traceroute用到它。4. 详:ttl是timetolive,目前是hupcount,当包每经过一个路由器它就会被减去一,如果它变成0,路由器就会把包丢掉。ip网络往往带有环(loop),比如子网a和子网b有两个路由器相连,它就是一个loop。ttl的主要目的是防止包在有回路的网络上死转,因为包的ttl最终后变成0而使得此包从网上消失(此时往往路由器会送一个icmp包回来,traceroute就是根据这个做的)。ping会送包出去,所以里面有它,但是ping不一定非要不可它。traceroute则是完全因为有它才能成的。ifconfig是用来配置网卡的,netstat-rn是用来列路由表的,所以都用不着它路由表示做什么用的?在linux环境中怎么来配置一条默认路由?答:简:路由表是用来决定如何将包从一个子网传送到另一个子网的,换局话说就是用来决定从一个网卡接收到的包应该送的哪一张网卡上的。在linux上可以用“routeadddefaultgw默认路由器ip”来配置一条默认路由。详:路由表是用来决定如何将包从一个子网传送到另一个子网的,换局话说就是用来决定从一个网卡接收到

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论