UNIX环境高级编程——学习笔记(1)
2015-10-23 20:03
302 查看
10.15节的实例程序
对应书中的源码为~/apue.3e/signals/mask.c
自己编译出的程序和书中的输出怎么也对应不上.
编译:
$ cd ~/apue.3e/signals
$ gcc -o mask_d mask.c -I../include ../lib/error.o ../lib/prmask.o
运行结果:
$ ./mask_d &
[6] 24152
starting main:
$ kill -USR1 24152
starting sig_usr1:
in sig_alrm:
finishing sig_usr1:
ending main:
正确结果:
$ ./mask_d &
[6] 24152
starting main:
$ kill -USR1 `ps aux | grep mask_d | grep -v grep | awk ‘{print $2}’`
starting sig_usr1: SIGUSR1
in sig_alrm: SIGUSR1 SIGALRM
finishing sig_usr1: SIGUSR1
ending main:
明显没有对任何信号进行屏蔽。
经过调试,发现:
__sysv_signal (sig=10, handler=0x400b42 ) at ../sysdeps/posix/sysv_signal.c:41
调用的是系统的api。
应该是编译的时候没有指定书中提供的signal实现。
修改编译命令:
$ gcc -o mask_d mask.c -I../include ../lib/error.o ../lib/prmask.o ../lib/signal.o
运行程序还是不行,效果一样的。
经gdbtui调试调用的还是__sysv_signal。
使用readelf查看mask_d:
$ readelf mask_d -a | grep signal
000000601b40 000100000007 R_X86_64_JUMP_SLO 0000000000000000 __sysv_signal + 0
1: 0000000000000000 0 FUNC GLOBAL DEFAULT UND __sysv_signal@GLIBC_2.2.5 (2)
27: 0000000000401484 149 FUNC GLOBAL DEFAULT 13 signal
56: 0000000000000000 0 FILE LOCAL DEFAULT ABS signal.c
63: 0000000000000000 0 FUNC GLOBAL DEFAULT UND __sysv_signal@@GLIBC_2.2.
104: 0000000000401484 149 FUNC GLOBAL DEFAULT 13 signal
符号表有signal,但是调用的还是系统的__sysv_signal,重定位段.rela.plt有__sysv_signal的重定位信息。
既然没调用signal,为什么会有signal的符号表,连接的时候难道不优化掉吗???
(gdb) info address signal
Symbol “signal” is a function at address 0x401484.
(gdb) x/i 0x401484
0x401484 < signal> : push %rbp
(gdb) disassemble signal
Dump of assembler code for function signal:
0x0000000000401484 <+0>: push %rbp
0x0000000000401485 <+1>: mov %rsp,%rbp
0x0000000000401488 <+4>: sub $0x150,%rsp
0x000000000040148f <+11>: mov %edi,-0x144(%rbp)
再次修改:
$ gcc -I../include -g mask.c -o mask_d -L../lib -lapue
运行readelf:
$ readelf mask_d -a | grep signal
0000006019c8 000100000007 R_X86_64_JUMP_SLO 0000000000000000 __sysv_signal + 0
1: 0000000000000000 0 FUNC GLOBAL DEFAULT UND __sysv_signal@GLIBC_2.2.5 (2)
62: 0000000000000000 0 FUNC GLOBAL DEFAULT UND __sysv_signal@@GLIBC_2.2.
signal符号与实现没有了。
看来以后一些库函数,能把它放到静态库里,就尽量放到静态库里,编译器会根据使用情况,对最终的二进制执行文件进行优化的。
查找源码中的Makefile,发现Make.defines.linux中定义的
CFLAGS=-ansi -I$(ROOT)/include -Wall -DLINUX -D_GNU_SOURCE -g $(EXTRA)
挨个添加选项最后发现,原来是_GNU_SOURCE搞的鬼。
$ gcc -I../include -g mask.c -o mask_d -L../lib -lapue -D_GNU_SOURCE
26: 0000000000401444 149 FUNC GLOBAL DEFAULT 13 signal
56: 0000000000000000 0 FILE LOCAL DEFAULT ABS signal.c
103: 0000000000401444 149 FUNC GLOBAL DEFAULT 13 signal
一切正常。
对应书中的源码为~/apue.3e/signals/mask.c
自己编译出的程序和书中的输出怎么也对应不上.
编译:
$ cd ~/apue.3e/signals
$ gcc -o mask_d mask.c -I../include ../lib/error.o ../lib/prmask.o
运行结果:
$ ./mask_d &
[6] 24152
starting main:
$ kill -USR1 24152
starting sig_usr1:
in sig_alrm:
finishing sig_usr1:
ending main:
正确结果:
$ ./mask_d &
[6] 24152
starting main:
$ kill -USR1 `ps aux | grep mask_d | grep -v grep | awk ‘{print $2}’`
starting sig_usr1: SIGUSR1
in sig_alrm: SIGUSR1 SIGALRM
finishing sig_usr1: SIGUSR1
ending main:
明显没有对任何信号进行屏蔽。
经过调试,发现:
__sysv_signal (sig=10, handler=0x400b42 ) at ../sysdeps/posix/sysv_signal.c:41
调用的是系统的api。
应该是编译的时候没有指定书中提供的signal实现。
修改编译命令:
$ gcc -o mask_d mask.c -I../include ../lib/error.o ../lib/prmask.o ../lib/signal.o
运行程序还是不行,效果一样的。
经gdbtui调试调用的还是__sysv_signal。
使用readelf查看mask_d:
$ readelf mask_d -a | grep signal
000000601b40 000100000007 R_X86_64_JUMP_SLO 0000000000000000 __sysv_signal + 0
1: 0000000000000000 0 FUNC GLOBAL DEFAULT UND __sysv_signal@GLIBC_2.2.5 (2)
27: 0000000000401484 149 FUNC GLOBAL DEFAULT 13 signal
56: 0000000000000000 0 FILE LOCAL DEFAULT ABS signal.c
63: 0000000000000000 0 FUNC GLOBAL DEFAULT UND __sysv_signal@@GLIBC_2.2.
104: 0000000000401484 149 FUNC GLOBAL DEFAULT 13 signal
符号表有signal,但是调用的还是系统的__sysv_signal,重定位段.rela.plt有__sysv_signal的重定位信息。
既然没调用signal,为什么会有signal的符号表,连接的时候难道不优化掉吗???
(gdb) info address signal
Symbol “signal” is a function at address 0x401484.
(gdb) x/i 0x401484
0x401484 < signal> : push %rbp
(gdb) disassemble signal
Dump of assembler code for function signal:
0x0000000000401484 <+0>: push %rbp
0x0000000000401485 <+1>: mov %rsp,%rbp
0x0000000000401488 <+4>: sub $0x150,%rsp
0x000000000040148f <+11>: mov %edi,-0x144(%rbp)
再次修改:
$ gcc -I../include -g mask.c -o mask_d -L../lib -lapue
运行readelf:
$ readelf mask_d -a | grep signal
0000006019c8 000100000007 R_X86_64_JUMP_SLO 0000000000000000 __sysv_signal + 0
1: 0000000000000000 0 FUNC GLOBAL DEFAULT UND __sysv_signal@GLIBC_2.2.5 (2)
62: 0000000000000000 0 FUNC GLOBAL DEFAULT UND __sysv_signal@@GLIBC_2.2.
signal符号与实现没有了。
看来以后一些库函数,能把它放到静态库里,就尽量放到静态库里,编译器会根据使用情况,对最终的二进制执行文件进行优化的。
查找源码中的Makefile,发现Make.defines.linux中定义的
CFLAGS=-ansi -I$(ROOT)/include -Wall -DLINUX -D_GNU_SOURCE -g $(EXTRA)
挨个添加选项最后发现,原来是_GNU_SOURCE搞的鬼。
$ gcc -I../include -g mask.c -o mask_d -L../lib -lapue -D_GNU_SOURCE
26: 0000000000401444 149 FUNC GLOBAL DEFAULT 13 signal
56: 0000000000000000 0 FILE LOCAL DEFAULT ABS signal.c
103: 0000000000401444 149 FUNC GLOBAL DEFAULT 13 signal
一切正常。
相关文章推荐
- Linux编译mssql扩展使用php连接sqlserver2008的使用步骤
- unix环境高级编程代码编译方法
- apue第16章习题16.3:支持多个端点的服务
- 信号量函数知多少
- Linux - Unix环境高级编程(第三版) 代码编译
- Linux守护进程的编程实现
- Linux进程间通信——使用共享内存
- 学习unix高级编程之我见(持续更新中)
- apue.h头文件(UNIX环境高级编程)
- APUE读书笔记(0.2) ——APUE源代码中的awk脚本文件
- APUE读书笔记(2.0) ——第二章 Unix 标准化及实现
- APUE读书笔记(3.0) ——第三章 文件I/O
- 三)Unix文件I/O(2)
- 三)Unix文件I/O(1)
- pthread_cleanup_push和pthread_cleanup_pop学习
- 线程的学习(一)
- 《Unix环境高级编程》学习之Unix标准
- 《Unix环境高级编程》学习之用户
- openat函数的用法示例
- 《Unix环境高级编程》学习之编写守护进程