У четырех потоков будет один и тот же PID, но только если смотреть сверху. То, что вы (как пользователь) называете PID, не является тем, что ядро (если смотреть снизу) называет PID.
В ядре каждый поток имеет свой собственный идентификатор, называемый PID (хотя, возможно, было бы разумнее называть его TID или идентификатором потока), и у них также есть TGID (идентификатор группы потоков), который является PID потока. с этого начался весь процесс.
Проще говоря, когда создается новый процесс , он отображается как поток, в котором PID и TGID имеют одинаковый (новый) номер.
Когда поток запускает другой поток, этот запущенный поток получает свой собственный PID (поэтому планировщик может планировать его независимо), но наследует TGID от исходного потока.
Таким образом, ядро может легко планировать потоки независимо от того, к какому процессу они принадлежат, в то время как процессы (идентификаторы групп потоков) сообщаются вам.
Следующая иерархия потоков может помочь (а) :
USER VIEW
<-- PID 43 --> <----------------- PID 42 ----------------->
+---------+
| process |
_| pid=42 |_
_/ | tgid=42 | \_ (new thread) _
_ (fork) _/ +---------+ \
/ +---------+
+---------+ | process |
| process | | pid=44 |
| pid=43 | | tgid=42 |
| tgid=43 | +---------+
+---------+
<-- PID 43 --> <--------- PID 42 --------> <--- PID 44 --->
KERNEL VIEW
Вы можете видеть, что запуск нового процесса (слева) дает вам новый PID и новый TGID (оба имеют одно и то же значение), а запуск нового потока (справа) дает вам новый PID при сохранении того же TGID как поток, который его запустил.
(а) Трепет перед моими впечатляющими графическими навыками :-)
getpid()
возвращает tgid:,asmlinkage long sys_getpid(void) { return current->tgid;}
как показано на www.makelinux.com/