У меня есть этот простой тест:
int main() {
int res = fork();
if (res == 0) { // child
printf("Son running now, pid = %d\n", getpid());
}
else { // parent
printf("Parent running now, pid = %d\n", getpid());
wait(NULL);
}
return 0;
}
Когда я запускаю его сто раз, т.е. запускаю эту команду,
for ((i=0;i<100;i++)); do echo ${i}:; ./test; done
Я получаю:
0:
Parent running now, pid = 1775
Son running now, pid = 1776
1:
Parent running now, pid = 1777
Son running now, pid = 1778
2:
Parent running now, pid = 1779
Son running now, pid = 1780
и т. Д .;тогда как, когда я сначала записываю в файл и затем читаю файл, т.е. запускаю эту команду,
for ((i=0;i<100;i++)); do echo ${i}:; ./test; done > forout
cat forout
я получаю его перевёрнутым!То есть
0:
Son running now, pid = 1776
Parent running now, pid = 1775
1:
Son running now, pid = 1778
Parent running now, pid = 1777
2:
Son running now, pid = 1780
Parent running now, pid = 1779
Я знаю о планировщике.Что не означает этот результат с точки зрения того, кто бежит первым после разветвления?Функция разветвления, do_fork()
(в kernel/fork.c
) заканчивается установкой флага need_resched
в 1 с комментарием разработчиков ядра, который говорит: «Пусть дочерний процесс запускается первым».
Я догадался, чтоэто как-то связано с буферами, в которые printf пишет.
Также верно ли, что перенаправление ввода (>
) сначала записывает все в буфер, а только потом копирует в файл?И даже в этом случае, почему это изменит порядок печати?
Примечание: Я запускаю тест на одноядерной виртуальной машине с ядром Linux v2.4.14 .
Спасибо за ваше время.