《Linux权威指南》阅读笔记(3)
第十三章 程序设计语言
Linux共享函数库使用一种叫跳跃表格(jump table)的数据结构
gcc -o 执行链接,指定文件名,-c不执行链接,-O优化,-g调试信息放入目标文件,
建立和使用静态函数库的方法:
先gcc -c将含目标函数源码(多个文件也可以)编译为.o文件,然后用ar程序 ar -r 建立.a静态库,
然后用ranlib命令产生索引,然后为该函数库建立头文件
gcc -I../include -L../lib -o wibble wibble.c -lstuff 使用建立的函数库
其中-I参数要求gcc在搜寻头文件时,(除默认目录外)也到指定目录去找,-L要求搜寻函数库也要到指定目录去找。
函数库目录/usr/lib,其中.a结尾是静态函数库, .so结尾是共享函数库
建立和使用共享函数库的方法:
共享函数库程序代码与位置无关,gcc使用 -fPIC参数产生与位置无关的代码
gcc -c pfPIC square.c factorial.c
gcc -shared -o libstuff.so square.o factorial.o
共享函数库不需要制作索引,现在可以使用所建立的共享函数库了:
gcc -I../include -L../lib -o wibble wibble.c -lstuff -lm 其中-lm指定连接libm这个函数库(函数库默认lib开头,-lstuff 指定libstuff)
使用ldd可以查看执行文件使用了哪些共享函数库
Makefiles
通常以makefile或Makefile作为文件名,格式如下
edimh:main.o edit.o
gcc -o edimh mian.o edit.o
make可以定义宏,上面的范例可以修改为:
OBJECTS=main.o edit.o
edimh: $(OBJECTS)
gcc -o edimh mian.o edit.o
宏可以修改,比如用:= 在宏末尾添加drivers/scsi/scsi.a
DRIVERS :=$(DRIVERS) drivers/scsi/scsi.a
宏还可以在make的命令行进行定义和赋值
文件名后缀、模式匹配规则
%.o: %.c
gcc -c -o $@ $(CFLAGS) $<
输出文件%.o,输入文件 %.c,$<代表输入文件,$@代表输出文件,$*代表不含结尾字符串的输入文件名,如输入edit.c,则$*为edit。
行首加@,在执行该行命令不显示,加 - ,发生错误也不停。
可以用include引入其他makefile
使用Perl
CPAN(Comprehensive Perl Archive Network Perl综合典藏网、Perl程序库)存储了各式Perl模块一般存储在/usr/lib/perl5,用命令 perl -MCGI -e l
Shell脚本语言程序设计
Bourne shell的条件表达式是一个命令,其值取决于命令传回值(结束状态为0时会成立);C shell的条件表达式是数学表达式或逻辑运算式
《Learning the bash Shell》和《Using csh and tcsh》
Tcl(Tool Command Language)
Java编译器不针对cpu或操作系统产生目标代码,但会针对Java虚拟机产生目标代码
语言转换程序p2c将Pascal程序转换为C程序,而f2c将FORTRAN转换为C程序
第十四章 程序设计员的工具
gdb调试范例:
gdb trymh
list
break 19
run <> …
next next会执行经过的子程序而不告知,step可以进入子程序去侦错
step
until 27 直接执行到27行为止
print mask 打印参数mask
finish 继续执行知道目前的函数结束
quit 离开gdb
当程序导致内存错误时,程序会死机并产生core文件,文件名就叫core,目录为程序目前工作目录
attach命令告诉gdb拦截正在执行的程序(必要要有读取这个程序的权限),detach命令使gdb停止拦截程序
ptype会给出变量详细的类型信息,想进一步查看内存内容,而不管它的类型,可使用x命令,其后接的参数是内存位置
info命令可知目前调试程序的状态,info program、info locals、info address …、info frame
中断点和观察点的区别在于中断点在特定位置停,观察点在某个条件表达式成立时停住而不管程序执行到哪。中断点也可搭配条件式,如:break 184 if (status==0)
机器码的调试 nexti、stepi、disass(显示指定内存位置范围内的反汇编代码)
可在Emacs内使用gdb:M-x gdb加程序名启动、core-file命令载入core文件
gprof是一个效率分析程序,要使用它则在gcc编译时要加上-pg参数
calls可显示C语言源代码中函数调用的树状结构
strace这个工具用来显示程序执行时所用到的系统调用
imake是makefile的产生程序,它可以简化makefile的编写过程,用命令xmkmf将Imakefile转成makefile。
ICmake使用一种类似C的宏语言来产生makefile,另外两个提供的弹性与空间要大得多的程序有autoconf与automake
Cheaker是一套C语言内存管理的函数库,会取代原来的内存管理函数如malloc、realloc和free等。它会加些程序代码以检查内存的读写,比标准库慢,可以开发测试用Cheaker,没问题后再用标准函数库。编译时使用 -lcheaker选项来链接checker函数库。Checker也提供了garbage collector(垃圾收集)、garbage detector(垃圾检测)等功能,当然这些也可以在gdb手工执行
xaw3D也是元件库,修改字标准的Athena元件库
Qt是C++的GUI工具套件,用非常聪明的机制将用户的互动与程序码连接在一起。它还具有一个速度非常快的绘图引擎,以及一个功能强大又容易使用的API。它是KDE的基础。
gtk是C的GUI工具套件,原本是为了图像处理程序GIMP而开发的
版本控制工具RCS
Revision Control System 版本控制系统,靠一个RCS文件运作,源文件靠它“登录进入”及“登录退出”。一个源文件有一个对应的RCS文件。
ci命令登录进入RCS,co命令登录退出,what命令找寻@(#)开头字符串并显示,rcs命令也可以管理RCS文件。
版本控制工具CVS
Concurrent Version System 同步版本系统比RCS更复杂,使用文件格式与RCS相同,但使用另一套管理方针
Patch文件
patch这个程序可以根据文件内容来修改文件,将文件更新成另一个文件版本。当你的程序改版时,只需要推出对应这份源文件的patch文件,其他人就可以执行patch程序使用patch文件,得到最新的版本。
可以使用diff -c命令产生patch文件:
diff -c hello.c.old hello.c > hello.patch
然后,就可以使用patch执行更新了:
patch < hello.patch
patch会将原文件备份为filename~(原文件名加~)。
再次使用patch文件时,patch程序会产生警告信息,会问是否以-R方式执行,-R会将文件还原。
要更新整个目录结构中所有源文件,在diff命令加上-r参数:
diff -cr hello.old hello > hello.patch
缩排工具indent是一个精明的C语言程序排版工具