Вот такая головоломка. Хотя для кого-то головоломка, а для кого-то уже семечки.
На x86 машинах вторым системным вызовом идет fork(), а на x86_64 - sys_open(). Однако этот код запускает fork() на обеих платформах:
Код: Выделить всё
#include <stdio.h>
#include <unistd.h>
int main ()
{
printf("--------------------\n");
__asm__("movl $2, %eax; int $0x80");
printf("[i am %d]\n", getpid());
}
Однако... если мы посмотрим вывод strace, то увидим, что на x86_64 действительно запускается open(), а на x86 fork():
x86_64:
Код: Выделить всё
> gcc asm.c -o asm && ./asm
--------------------
[i am 4628]
[i am 4629]
> strace ./asm
execve("./asm", ["./asm"], [/* 41 vars */]) = 0
brk(0) = 0x823000
access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory)
mmap(NULL, 8192, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fa5bbfa2000
access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY) = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=111792, ...}) = 0
mmap(NULL, 111792, PROT_READ, MAP_PRIVATE, 3, 0) = 0x7fa5bbf86000
close(3) = 0
access("/etc/ld.so.nohwcap", F_OK) = -1 ENOENT (No such file or directory)
open("/lib/libc.so.6", O_RDONLY) = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0`\355\1\0\0\0\0\0"..., 832) = 832
fstat(3, {st_mode=S_IFREG|0755, st_size=1432968, ...}) = 0
mmap(NULL, 3541032, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x7fa5bba26000
mprotect(0x7fa5bbb7e000, 2093056, PROT_NONE) = 0
mmap(0x7fa5bbd7d000, 20480, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x157000) = 0x7fa5bbd7d000
mmap(0x7fa5bbd82000, 18472, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x7fa5bbd82000
close(3) = 0
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fa5bbf85000
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fa5bbf84000
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fa5bbf83000
arch_prctl(ARCH_SET_FS, 0x7fa5bbf84700) = 0
mprotect(0x7fa5bbd7d000, 16384, PROT_READ) = 0
mprotect(0x7fa5bbfa4000, 4096, PROT_READ) = 0
munmap(0x7fa5bbf86000, 111792) = 0
fstat(1, {st_mode=S_IFCHR|0600, st_rdev=makedev(136, 5), ...}) = 0
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7fa5bbfa1000
write(1, "--------------------\n", 21--------------------
) = 21
open(0xffffffff, O_RDONLY|O_SYNC|O_NOFOLLOW|O_CLOEXEC|0xbbf00000) = 4635
getpid() = 4634
[i am 4635]
write(1, "[i am 4634]\n", 12) = ? ERESTARTSYS (To be restarted)
--- SIGCHLD (Child exited) @ 0 (0) ---
write(1, "[i am 4634]\n", 12[i am 4634]
) = 12
exit_group(12) = ?
x86:
Код: Выделить всё
> gcc asm.c -o asm && ./asm
--------------------
[i am 5163]
[i am 5162]
> strace ./asm
execve("./asm", ["./asm"], [/* 22 vars */]) = 0
brk(0) = 0x9a32000
access("/etc/ld.so.preload", R_OK) = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY) = 3
fstat64(3, {st_mode=S_IFREG|0644, st_size=40948, ...}) = 0
mmap2(NULL, 40948, PROT_READ, MAP_PRIVATE, 3, 0) = 0xb7ef8000
close(3) = 0
open("/lib/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\340_\1\0004\0\0\0"..., 512) = 512
fstat64(3, {st_mode=S_IFREG|0755, st_size=1686224, ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb7ef7000
mmap2(NULL, 1410500, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x110000
mmap2(0x263000, 12288, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x152) = 0x263000
mmap2(0x266000, 9668, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x266000
close(3) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb7ef6000
set_thread_area({entry_number:-1 -> 6, base_addr:0xb7ef66c0, limit:1048575, seg_32bit:1, contents:0, read_exec_only:0, limit_in_pages:1, seg_not_present:0, useable:1}) = 0
mprotect(0x263000, 8192, PROT_READ) = 0
mprotect(0x79e000, 4096, PROT_READ) = 0
munmap(0xb7ef8000, 40948) = 0
fstat64(1, {st_mode=S_IFCHR|0620, st_rdev=makedev(136, 0), ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0xb7f01000
write(1, "--------------------\n", 21--------------------
) = 21
fork() = 5192
[i am 5192]
getpid() = 5191
write(1, "[i am 5191]\n", 12[i am 5191]
) = 12
exit_group(12)
Вопрос: почему strace показывает не то, что выполняется на самом деле?
![:tongue:](./images/smilies/tongue.gif)