[精华] strace, anti-strace, anti anti-strace
时间:2007-03-07 来源:loughsky
|=----------------=[ strace, anti-strace, anti anti-strace ]=---------------=|
|=--------------------------------------------------------------------------=|
|=-----------------=[ CoolQ <[email protected]> ]=----------------=|
|=--------------------------------------------------------------------------=|
--[ 内容
0 - 前言
1 - strace的原理
2 - strace死循环的分析
3 - anti-strace
3.1 方法一
3.2 方法二
3.3 方法三
4 - anti anti-strace
4.1 int3的情况
4.2 kill的情况
5 - 参考
6 - strace.4.5.8.patch
--[ 0 - 前言
前面在介绍Burneye加密文件的时候,遇到了两个问题,一个是GDB中无法设置断点,另一个
问题是strace时死循环。GDB的问题已经找到,无法设置断点是GDB的一个Bug,具体的结
论见[1].至于strace的问题,一直没有解决,如果真能写出一个让strace死循环的程序,
也算是一种anti-strace的技术。但是一直没有将死循环的现象用程序重现。
后来经Grip2的指点,发现了问题的原因,经过对内核和strace源代码的研究,写了一个
防止strace死循环的patch,之后更进一步的patch,使得strace更加健壮,能够跟踪anti-
strace程序的系统调用。
在这里感谢Grip2的帮助和测试程序。
本文的环境是Redhat Fedora Core 2, Linux 2.6.5/2.6.8.1,
gcc 3.3.1, strace 4.5.8
文章选项:
coolq
(member)
04-12-31 01:13
[精华] Re: strace, anti-strace, anti anti-strace [re: coolq]
--[ 1 - strace的原理
要想了解strace的原理,首先得谈谈ptrace。
ptrace是操作系统为了调试为用户程序提供的系统接口。先来看看ptrace的用法:[2]
long ptrace(enum __ptrace_request request, pid_t pid, void *addr, void
*data)
strace需要使用的__ptrace_request主要有以下几个:
被调试的进程)
PTRACE_TRACEME 自己主动提供被跟踪的请求,当被跟踪的进程收到信号时,会先被
父进程截获.同样,execve时也是如此.
监视进程strace)
PTRACE_GETREGS 获得被跟踪进程的寄存器状况,详细的结构请参见asm/user.h的
user_regs_struct
PTRACE_PEEKDATA 获得系统堆栈中的参数
PTRACE_SYSCALL 这是最重要的,每次本跟踪的进程在系统调用时,ptrace会返回
两次,一次是系统调用之前,会调用PTRACE_PEEKDATA获得参数
值,另一次是系统调用之后,会调用PTRACE_GETREGS获得返回值
ENTRY(system_call)
...
# system call tracing in operation
testb $(_TIF_SYSCALL_TRACE|_TIF_SYSCALL_AUDIT),TI_flags(%ebp)
jnz syscall_trace_entry
...
syscall_trace_entry:
movl $-ENOSYS,EAX(%esp)
movl %esp, %eax
xorl %edx,%edx
call do_syscall_trace <-- ptrace的第一次sysycall跟踪
movl ORIG_EAX(%esp), %eax
cmpl $(nr_syscalls), %eax
jnae syscall_call <-- 系统调用
jmp syscall_exit
# perform syscall exit tracing
ALIGN
syscall_exit_work:
testb $(_TIF_SYSCALL_TRACE|_TIF_SYSCALL_AUDIT), %cl
jz work_pending
sti # could let do_syscall_trace() call
# schedule() instead
movl %esp, %eax
movl $1, %edx
call do_syscall_trace <-- ptrace的第二次sysycall跟踪
jmp resume_userspace
接下来简单的说一下strace的流程:
strace首先fork,然后子进程先自动PTRACE_TRACEME,然后execve被调试的文件,等待父
进程的调试。父进程进入一个循环,用wait4等待子进程,并判断子进程的状态,退出状
态有几种 - 子进程的信号被截获、子进程系统调用之前与之后、子进程退出。然后按照
情况将截获的信息打印在屏幕上。之后,继续调用PTRACE_SYSCALL使程序继续执行。
--[ 2 - strace死循环的分析
我们先来看看死循环的提示
signal(SIGTRAP, 0x5371991) = ? ERESTARTNOINTR (To be restarted)
signal(SIGTRAP, 0x5371991) = ? ERESTARTNOINTR (To be restarted)
似乎是signal系统调用的不断重启,一开始没有搞清楚到底是内核重启系统调用还是
strace重启系统调用。搜索一下sys_signal系统调用和ERESTARTNOINTR的定义,
sys_signal->do_sigaction()
2298 if (signal_pending(current)) {
2299 /*
2300 * If there might be a fatal signal pending on multiple
2301 * threads, make sure we take it before changing the action.
2302 */
2303 spin_unlock_irq(¤t->sighand->siglock);
2304 return -ERESTARTNOINTR;
2305 }
也就是说当程序执行sys_signal时,如果有信号还未处理,就直接返回-ERESTARTNOINTR
接下来当系统调用返回时,会依次调用
resume_userspace->work_pending->work_notify_sig->do_notify_resume->do_signal
590 no_signal:
591 /* Did we come from a system call? */
592 if (regs->orig_eax >= 0) {
593 /* Restart the system call - no handlers present */
594 if (regs->eax == -ERESTARTNOHAND ||
595 regs->eax == -ERESTARTSYS ||
596 regs->eax == -ERESTARTNOINTR) {
597 regs->eax = regs->orig_eax;
598 regs->eip -= 2;
599 }
600 if (regs->eax == -ERESTART_RESTARTBLOCK){
601 regs->eax = __NR_restart_syscall;
602 regs->eip -= 2;
603 }
604 }
605 return 0;
606 }
此时, regs->eip -= 2;正好代表int $0x80 (0xcd 0x80)两个字节,可见,内核重启
系统调用。
那么,究竟什么时候signal_pending(current)为真呢?经过GDB调试,发现strace在处理
sys_signal系统调用时,syscall.c:trace_syscall会调用signal的sys_signal函数
sys_res = (*sysent[tcp->scno].sys_func)(tcp)
signal.c::sys_signal()
...
#ifndef USE_PROCFS
if (tcp->u_arg[0] == SIGTRAP) {
tcp->flags |= TCB_SIGTRAPPED;
kill(tcp->pid, SIGSTOP);
}
#endif /* !USE_PROCFS */
死循环的问题就在这个kill(tcp->pid, SIGSTOP)上,当程序被处于跟踪的时刻,向已经
停止的进程发送SIGSTOP本来是没有必要的,不知道strace的作者为什么还要单独来上这
么一句?Linux 2.4和2.6内核又出现了差异,在2.6内核的do_sigaction判断了是否有信
号pending,而2.4却没有,因此在2.4的机器上,运行strace不会出现死循环的情况,在
2.6上,我们只须将改行注释掉即可。
我们可以认为这是strace和2.6内核不兼容的一个Bug!
注意:如果你在程序里用的是C库的signal,实际上使用的是sys_rt_sigaction而不是
sys_signal,而strace在处理sys_rt_sigaction时,并没有kill(tcp->pid, SIGSTOP);
也许strace的作者认为用C写的程序不会用到sys_signal?
接下来让我们试一试新的strace来跟踪burneye加密的程序
#./strace /tmp/ls.new (ls.new是burneye加密的程序)
execve("/tmp/ls.new", ["/tmp/ls.new"], [/* 20 vars */]) = 0
signal(SIGTRAP, 0x5371991) = 0 (SIG_DFL)
--- SIGSEGV (Segmentation fault) @ 0 (0) ---
+++ killed by SIGSEGV ++
OK,不死循环了,但是我们现在还无法继续跟踪,因为burneye加密的时候使用了某些anti-
strace的技术。
文章选项:
coolq
(member)
04-12-31 01:14
[精华] Re: strace, anti-strace, anti anti-strace [re: coolq]
--[ 3 - anti-strace的原理
了解了strace的工作原理,就可以有针对的使用anti-strace的技术
--[ 3.1 方法一
利用上边介绍的strace与2.6内核的不兼容,造成死循环.对上边打过patch的strace不适用
测试程序(Grip2提供)
#include <stdio.h>
#include <string.h>
#include <signal.h>
#include <unistd.h>
#include <sys/ptrace.h>
#include <sys/wait.h>
#include <sys/types.h>
void sig_handler(int sig)
{
printf("signal trap\n");
return;
}
static inline int my_signal(int num, void *func)
{
int ret;
__asm__ __volatile__ ( "int $0x80"
:"=a"(ret)
:"0" (48), "b" ((long)num),
"c" ((int)func));
return ret;
}
int main(int argc, char *argv[])
{
my_signal(SIGTRAP, sig_handler);
return 0;
}
注意一定不能使用C库的signal,原因在前边已经提过
--[ 3.2 方法二
自己发送int3
这种方法是Silvio Cesare在[3]中介绍的方法,由程序自己执行int3,这样会产生一个
陷阱,内核会向程序发送一个SIGTRAP信号,由于程序被跟踪,因此信号由strace截获,
根据strace的源代码,if (ptrace(PTRACE_SYSCALL, pid, (char *) 1, 0) < 0)
可见ptrace并没有返回该信号(0),因此,程序可以设置自己的SIGTRAP处理函数,看有
没有截获信号。burneye就使用了这种方法
例子:
#include <stdio.h>
#include <string.h>
#include <signal.h>
#include <unistd.h>
#include <sys/ptrace.h>
#include <sys/wait.h>
#include <sys/types.h>
static int not_trace
void sig_handler(int sig)
{
not_trace++;
return;
}
int main(int argc, char *argv[])
{
signal(SIGTRAP, sig_handler);
__asm__ __volatile__ ( "int3" );
if(!not_trace){
printf("TRACING...\n");
exit(-1);
}
return 0;
}
--[ 3.3 方法三
程序使用kill向自己发送SIGTRAP,跟方法二类似,这里就不赘述了
kill(getpid(), SIGTRAP);
文章选项:
coolq
(member)
04-12-31 01:18
[精华] Re: strace, anti-strace, anti anti-strace [re: coolq]
--[ 4 - anti anti-strace
现在我们来进一步完善strace,让它也能对付方法二和方法三,其实问题的关键就是看
strace在ptrace退出之后,下次使用ptrace能不能将SIGTRAP信号返回给被跟踪程序。
根据ptrace的手册页对PTRACE_CONT和PTRACE_SYSCALL的描述
PTRACE_CONT ... If data is non-zero and not SIGSTOP, it is interpreted as a
signal to be delivered to the child ...
PTRACE_SYSCALL ... Restarts the stopped child as for PTRACE_CONT
看来我们只须在下一次调用ptrace时指定返回的信号是SIGTRAP即可,不过不能胡乱发送,
只有在发现int3和kill(pid, SIGTRAP)的情况下才适用。
--[ 4.1 int3的情况
首先,我们需要判断int3的情况,因此,需要在strace.c::trace()最后添加以下几行
tracing:
if(ptrace(PTRACE_GETREGS, pid, NULL, (int)®s) < 0)
SHOW_PTRACE_ERROR;
else{
unsigned int code;
code = ptrace(PTRACE_PEEKTEXT, pid,
(void *)(regs.eip - 4), 0);
if((code & 0xff000000) == 0xcc000000){
tprintf("\n!! INT3 FOUND !!\n");
if(ptrace(PTRACE_SYSCALL,
pid,
(char *)1,
SIGTRAP) < 0)
SHOW_PTRACE_ERROR;
else
continue;
}
}
...
这段程序,会在每次被跟踪程序停止时用ptrace读取程序的寄存器,判断当前的字节是不
是0xcc(int 3),如果是,就在下一次的PTRACE_SYSCALL时返回SIGTRAP信号,实际的结果
是什么样的呢?我们就以方法二的程序作实验
#./strace /tmp/test.c
...
rt_sigaction(SIGTRAP, {0x80484dc, [TRAP], SA_RESTART}, {SIG_DFL}, 8) = 0
!! INT3 FOUND !!
fstat64(1, {st_mode=S_IFREG|0644, st_size=1463, ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) =0xf70a6000
sigreturn() = ? (mask now [])
!! INT3 FOUND !!
!! INT3 FOUND !!
sigreturn() = ? (mask now [])
!! INT3 FOUND !!
!! INT3 FOUND !!
sigreturn() = ? (mask now [])
!! INT3 FOUND !!
!! INT3 FOUND !!
sigreturn() = ? (mask now [])
!! INT3 FOUND !!
...
又是死循环,这时sigreturn引起了我的注意,似乎sigreturn也在不断的重启,这是为什
么呢?
首先得弄明白sigreturn是干什么的:一个程序调用signal时,会在内核中注册一个信号
处理函数,当进程收到信号需要处理的时候,需要从内核中直接切换到用户的处理函数
中,切换点是进程在系统调用、中断、异常返回时,另一种情况是进程刚被唤醒时。由于
返回的并不是进入内核之前的代码中,因此,内核需要在进入用户态之前设置一个栈帧,
目的地就是信号处理函数,处理完信号之后,会调用sigreturn返回内核,再由内核返回
到原来进入内核的代码中。
因此,系统调用sigreturn时当前的字节也是0xcc,因此,PTRACE又会发送SIGTRAP信号,
形成了SIGTRAP处理的嵌套。这次的不断重启是strace的问题,与内核无关。
解决的方法是将sigreturn和rt_sigreturn的情况跳过:
加上这么一行:
if(tcp->scno != __NR_sigreturn && tcp->scno != __NR_rt_sigreturn)
--[ 4.2 kill的情况
kill情况比较简单,只须在sys_kill调用的第二次ptrace返回时,将返回值设定为SIGTRAP
if(tcp->scno == __NR_kill){
if(!(tcp->flags & TCB_INSYSCALL)){
tprintf("\n!! Self SIGTRAP !!\n");
if(ptrace(PTRACE_SYSCALL,
pid,
(char *)1,
SIGTRAP) < 0)
SHOW_PTRACE_ERROR;
else
continue;
}
}
文章选项:
coolq
(member)
04-12-31 01:27
附加档案
[精华] Re: strace, anti-strace, anti anti-strace [re: coolq]
--[ 5 - 参考
[1][http://www.linuxforum.net/forum/showthreaded.php?Cat=&Board=security&Number=532461&page=0&view=collapsed&sb=5&o=31]
[http://www.linuxforum.net/forum/showflat.php?Cat=&Board=security&Number=532460&page=0&view=collapsed&sb=5&o=31&fpart=]
[2] ptrace手册页
[3] [http://vx.netlux.org/lib/vsc04.html]
[4] strace source code
[5] burneye source code
[6] linux kernel source code
--[ 6 - strace.4.5.8.patch
begin 644 strace-4.5.8.patch
M9&EF9B`M=7).('-T<F%C92TT+C4N."]S:6=N86PN8R!S=')A8V4M-"XU+C@N
M;F5W+W-I9VYA;"YC"BTM+2!S=')A8V4M-"XU+C@O<VEG;F%L+F,),C`P-"TQ
M,"TP-B`Q.#HQ,3HU-"XP,#`P,#`P,#`@+3`T,#`**RLK('-T<F%C92TT+C4N
M."YN97<O<VEG;F%L+F,),C`P-"TQ,BTR.2`Q.3HS-SHQ-2XU.#$Y.#,X-S(@
M+3`U,#`*0$`@+3$Q-S,L-R`K,3$W,RPW($!`"B`C:69N9&5F(%5315]04D]#
M1E,*(`D)"6EF("AT8W`M/G5?87)G6S!=(#T](%-)1U1205`I('L*(`D)"0ET
M8W`M/F9L86=S('P](%1#0E]324=44D%04$5$.PHM"0D)"6MI;&PH=&-P+3YP
M:60L(%-)1U-43U`I.PHK"0D)"2\O:VEL;"AT8W`M/G!I9"P@4TE'4U1/4"D[
M"B`)"0E]"B`C96YD:68@+RH@(55315]04D]#1E,@*B\*(`D)"71P<FEN=&8H
M(B4C;'@B+"!T8W`M/G5?87)G6S%=*3L*9&EF9B`M=7).('-T<F%C92TT+C4N
M."]S=')A8V4N8R!S=')A8V4M-"XU+C@N;F5W+W-T<F%C92YC"BTM+2!S=')A
M8V4M-"XU+C@O<W1R86-E+F,),C`P-"TQ,"TQ.2`R,CHP-#HQ-2XP,#`P,#`P
M,#`@+3`T,#`**RLK('-T<F%C92TT+C4N."YN97<O<W1R86-E+F,),C`P-"TQ
M,BTR.2`Q.3HS-SHP-BXQ.#4T,3(S-C@@+3`U,#`*0$`@+30V+#8@*S0V+#@@
M0$`*("-I;F-L=61E(#QL:6UI=',N:#X*("-I;F-L=61E(#QD:7)E;G0N:#X*
M(`HK(VEN8VQU9&4@/&%S;2]U<V5R+F@^"BL*("-I9B!D969I;F5D*$E!-C0I
M("8F(&1E9FEN960H3$E.55@I"B`C(&EN8VQU9&4@/&%S;2]P=')A8V5?;V9F
M<V5T<RYH/@H@(V5N9&EF"D!`("TV,RPV("LV-2PQ,R!`0`H@(V5N9&EF"B`C
M96YD:68*(`HK(V1E9FEN92!32$]77U!44D%#15]%4E)/4B`)7`HK"61O>PD)
M"5P**PD)<&5R<F]R*"(B*3L@"5P**PD)8VQE86YU<"@I.PE<"BL)"7)E='5R
M;B`M,3L)7`HK"7UW:&EL92@P*0HK"B!I;G0@9&5B=6<@/2`P+"!F;VQL;W=F
M;W)K(#T@,"P@9F]L;&]W=F9O<FL@/2`P+"!I;G1E<F%C=&EV92`](#`["B!I
M;G0@<F9L86<@/2`P+"!T9FQA9R`](#`L(&1T:6UE(#T@,"P@8V9L86<@/2`P
href="mailto:M.PH@:6YT(&EF;&%G(#T@">M.PH@:6YT(&EF;&%G(#T@,"P@>&9L86<@/2`P+"!Q9FQA9R`](#`["D!`("TQ
M.3DP+#8@*S$Y.3DL-R!`0`H@"6EN="!W86ET7V5R<FYO.PH@"6EN="!S=&%T
M=7,["B`)<W1R=6-T('1C8B`J=&-P.PHK"7-T<G5C="!U<V5R7W)E9W-?<W1R
M=6-T(')E9W,["B`C:69D968@3$E.55@*(`ES=')U8W0@<G5S86=E(')U.PH@
M(VEF9&5F(%]?5T%,3`I`0"`M,C(Y-RPV("LR,S`W+#,W($!`"B`)"0EC;VYT
M:6YU93L*(`D)?0H@"71R86-I;F<Z"BL)"6EF*'!T<F%C92A05%)!0T5?1T54
M4D5'4RP@<&ED+"!.54Q,+"`H:6YT*29R96=S*2`\(#`I"BL)"0E32$]77U!4
M4D%#15]%4E)/4CL**PD)96QS97L**PD)"75N<VEG;F5D(&EN="!C;V1E.PHK
M"0D)8V]D92`]('!T<F%C92A05%)!0T5?4$5%2U1%6%0L('!I9"P@"BL)"0D)
M"2AV;VED("HI*')E9W,N96EP("T@-"DL(#`I.PHK"0D):68H*&-O9&4@)B`P
M>&9F,#`P,#`P*2`]/2`P>&-C,#`P,#`P*7L**PD)"0EI9BAT8W`M/G-C;F\@
M(3T@7U].4E]S:6=R971U<FX@)B8**PD)"0D)=&-P+3YS8VYO("$](%]?3E)?
M<G1?<VEG<F5T=7)N*7L**PD)"0D)='!R:6YT9B@B7&XA(2!)3E0S($9/54Y$
M("$A7&XB*3L**PD)"0D):68H<'1R86-E*%!44D%#15]365-#04Q,+`HK"0D)
M"0D)<&ED+`HK"0D)"0D)*&-H87(@*BDQ+`HK"0D)"0D)4TE'5%)!4"D@/"`P
M*0HK"0D)"0D)4TA/5U]05%)!0T5?15)23U(["BL)"0D)"65L<V4**PD)"0D)
M"6-O;G1I;G5E.PHK"0D)"7T**PD)"7UE;'-E(&EF*'1C<"T^<V-N;R`]/2!?
M7TY27VMI;&PI>PHK"0D)"6EF*"$H=&-P+3YF;&%G<R`F(%1#0E])3E-94T-!
M3$PI*7L**PD)"0D)='!R:6YT9B@B7&XA(2!396QF(%-)1U1205`@(2%<;B(I
M.PHK"0D)"0EI9BAP=')A8V4H4%1204-%7U-94T-!3$PL"BL)"0D)"0EP:60L
M"BL)"0D)"0DH8VAA<B`J*3$L"BL)"0D)"0E324=44D%0*2`\(#`I"BL)"0D)
M"0E32$]77U!44D%#15]%4E)/4CL**PD)"0D)96QS90HK"0D)"0D)8V]N=&EN
M=64["BL)"0D)?0HK"0D)?0HK"0E]"B`)"6EF("AP=')A8V4H4%1204-%7U-9
M4T-!3$PL('!I9"P@*&-H87(@*BD@,2P@,"D@/"`P*2!["B`)"0EP97)R;W(H
M(G1R86-E.B!P=')A8V4H4%1204-%7U-94T-!3$PL("XN+BDB*3L*(`D)"6-L
)96%N=7`H*3L*
`
end
文章选项:
coolq
(member)
04-12-31 09:22
附:用修改后的strace跟踪burneye加密的ls [re: coolq]
#./strace /tmp/ls.new
execve("/tmp/ls.new", ["/tmp/ls.new"], [/* 32 vars */]) = 0
signal(SIGTRAP, 0x5371990) = 0 (SIG_DFL)
!! INT3 FOUND !!
sigreturn() = ? (mask now [])
open("/dev/tty", O_RDWR) = 3
ioctl(3, SNDCTL_TMR_TIMEBASE or TCGETS, {B38400 opost isig icanon echo ...}) = 0
ioctl(3, SNDCTL_TMR_CONTINUE or TCSETSF, {B38400 opost -isig icanon -echo ...}) = 0
write(3, "password: ", 10) = 10
read(3, "1234\n", 64) = 5
write(3, "\n", 1) = 1
ioctl(3, SNDCTL_TMR_CONTINUE or TCSETSF, {B38400 opost isig icanon echo ...}) = 0
close(3) = 0
brk(0x805aba4) = 0x805aba4
old_mmap(0x8048000, 74660, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, 0, 0) = 0x8048000
mprotect(0x8048000, 74660, PROT_READ|PROT_EXEC) = 0
brk(0x805a3a4) = 0x805a3a4
brk(0x805c7f3) = 0x805c7f3
old_mmap(0x805b000, 4083, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, 0, 0) = 0x805b000
mprotect(0x805b000, 3151, PROT_READ|PROT_WRITE) = 0
brk(0x805bff3) = 0x805bff3
open("/lib/ld-linux.so.2", O_RDONLY) = 3
lseek(3, 0, SEEK_SET) = 0
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0\300\307"..., 52) = 52
lseek(3, 52, SEEK_SET) = 52
read(3, "\1\0\0\0\0\0\0\0\0\300Q\0\0\300Q\0PA\1\0PA\1\0\5\0\0\0"..., 192) = 192
old_mmap(0x4051c000, 82256, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED, 3, 0) = 0x4051c000
mprotect(0x4051c000, 82256, PROT_READ|PROT_EXEC) = 0
old_mmap(0x40531000, 4840, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED, 3, 0x14000) = 0x40531000
close(3) = 0
uname({sys="Linux", node="CoolQ", ...}) = 0
brk(0) = 0x805bff3
open("/etc/ld.so.preload", O_RDONLY) = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY) = 3
fstat64(3, {st_mode=S_IFREG|0644, st_size=76211, ...}) = 0
old_mmap(NULL, 76211, PROT_READ, MAP_PRIVATE, 3, 0) = 0x40000000
close(3) = 0
open("/lib/tls/librt.so.1", O_RDONLY) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0\300\200"..., 512) = 512
fstat64(3, {st_mode=S_IFREG|0755, st_size=50940, ...}) = 0
old_mmap(0x4ee96000, 81880, PROT_READ|PROT_EXEC, MAP_PRIVATE, 3, 0) = 0x4ee96000
old_mmap(0x4ee9e000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED, 3, 0x7000) = 0x4ee9e000
old_mmap(0x4eea0000, 40920, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x4eea0000
close(3) = 0
open("/lib/libacl.so.1", O_RDONLY) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0\220\302"..., 512) = 512
fstat64(3, {st_mode=S_IFREG|0644, st_size=23572, ...}) = 0
old_mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x40013000
old_mmap(0x87b000, 20940, PROT_READ|PROT_EXEC, MAP_PRIVATE, 3, 0) = 0x87b000
old_mmap(0x880000, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED, 3, 0x5000) = 0x880000
close(3) = 0
open("/lib/libselinux.so.1", O_RDONLY) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0\350\1\246"..., 512) = 512
fstat64(3, {st_mode=S_IFREG|0755, st_size=60776, ...}) = 0
old_mmap(0xa5d000, 64532, PROT_READ|PROT_EXEC, MAP_PRIVATE, 3, 0) = 0xa5d000
old_mmap(0xa6b000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED, 3, 0xd000) = 0xa6b000
close(3) = 0
open("/lib/tls/libc.so.6", O_RDONLY) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0\300\233"..., 512) = 512
fstat64(3, {st_mode=S_IFREG|0755, st_size=1455084, ...}) = 0
old_mmap(0x535000, 1158124, PROT_READ|PROT_EXEC, MAP_PRIVATE, 3, 0) = 0x535000
old_mmap(0x64a000, 16384, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED, 3, 0x115000) = 0x64a000
old_mmap(0x64e000, 7148, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x64e000
close(3) = 0
open("/lib/tls/libpthread.so.0", O_RDONLY) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0`\27y\000"..., 512) = 512
fstat64(3, {st_mode=S_IFREG|0755, st_size=106212, ...}) = 0
old_mmap(0x78d000, 70128, PROT_READ|PROT_EXEC, MAP_PRIVATE, 3, 0) = 0x78d000
old_mmap(0x79b000, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED, 3, 0xd000) = 0x79b000
old_mmap(0x79d000, 4592, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x79d000
close(3) = 0
open("/lib/libattr.so.1", O_RDONLY) = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0\3\0\1\0\0\0\320[\207"..., 512) = 512
fstat64(3, {st_mode=S_IFREG|0644, st_size=12260, ...}) = 0
old_mmap(0x875000, 13756, PROT_READ|PROT_EXEC, MAP_PRIVATE, 3, 0) = 0x875000
old_mmap(0x878000, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED, 3, 0x2000) = 0x878000
close(3) = 0
old_mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x40014000
mprotect(0x79b000, 4096, PROT_READ) = 0
mprotect(0x64a000, 8192, PROT_READ) = 0
mprotect(0x4ee9e000, 4096, PROT_READ) = 0
mprotect(0x40531000, 4096, PROT_READ) = 0
set_thread_area({entry_number:-1 -> 6, base_addr:0x40014660, limit:1048575, seg_32bit:1, contents:0, read_exec_only:0, limit_in_pages:1, seg_not_present:0, useable:1}) = 0
munmap(0x40000000, 76211) = 0
set_tid_address(0x400146a8) = 2423
rt_sigaction(SIGRTMIN, {0x7916d0, [], SA_RESTORER|SA_SIGINFO, 0x798450}, NULL, 8) = 0
rt_sigprocmask(SIG_UNBLOCK, [RTMIN], NULL, 8) = 0
getrlimit(RLIMIT_STACK, {rlim_cur=8192*1024, rlim_max=RLIM_INFINITY}) = 0
_sysctl({{CTL_KERN, KERN_VERSION}, 2, 0xbfffdb08, 35, (nil), 0}) = 0
brk(0) = 0x805bff3
brk(0x807cff3) = 0x807cff3
brk(0x807d000) = 0x807d000
open("/proc/mounts", O_RDONLY) = 3
fstat64(3, {st_mode=S_IFREG|0444, st_size=0, ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x40000000
read(3, "rootfs / rootfs rw 0 0\n/dev/root"..., 1024) = 365
read(3, "", 1024) = 0
close(3) = 0
munmap(0x40000000, 4096) = 0
open("/usr/lib/locale/locale-archive", O_RDONLY|O_LARGEFILE) = 3
fstat64(3, {st_mode=S_IFREG|0644, st_size=40263072, ...}) = 0
mmap2(NULL, 2097152, PROT_READ, MAP_PRIVATE, 3, 0) = 0x40015000
mmap2(NULL, 614400, PROT_READ, MAP_PRIVATE, 3, 0x13b2) = 0x40215000
close(3) = 0
open("/proc/filesystems", O_RDONLY) = 3
read(3, "nodev\tsysfs\nnodev\trootfs\nnodev\tb"..., 4095) = 253
close(3) = 0
ioctl(1, SNDCTL_TMR_TIMEBASE or TCGETS, 0xbfffdaa8) = -1 ENOTTY (Inappropriate ioctl for device)
ioctl(1, TIOCGWINSZ, 0xbfffdb78) = -1 ENOTTY (Inappropriate ioctl for device)
open(".", O_RDONLY|O_NONBLOCK|O_LARGEFILE|O_DIRECTORY) = 3
fstat64(3, {st_mode=S_IFDIR|0777, st_size=4096, ...}) = 0
fcntl64(3, F_SETFD, FD_CLOEXEC) = 0
getdents64(3, /* 95 entries */, 4096) = 3008
getdents64(3, /* 0 entries */, 4096) = 0
close(3) = 0
open("/etc/mtab", O_RDONLY) = 3
fstat64(3, {st_mode=S_IFREG|0644, st_size=281, ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x402ab000
read(3, "/dev/hda2 / ext3 rw 0 0\nnone /pr"..., 4096) = 281
close(3) = 0
munmap(0x402ab000, 4096) = 0
open("/proc/meminfo", O_RDONLY) = 3
fstat64(3, {st_mode=S_IFREG|0444, st_size=0, ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x402ab000
read(3, "MemTotal: 237460 kB\nMemFre"..., 1024) = 644
close(3) = 0
munmap(0x402ab000, 4096) = 0
fstat64(1, {st_mode=S_IFREG|0644, st_size=7972, ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x402ab000
write(1, "acinclude.m4\naclocal.m4\nAUTHORS\n"..., 816acinclude.m4
aclocal.m4
AUTHORS
bjm.c
bjm.o
ChangeLog
...
) = 816
close(1) = 0
munmap(0x402ab000, 4096) = 0
exit_group(0) = ?