Есть ли способ запустить любую функцию семейства exec как поток в c - PullRequest
3 голосов
/ 17 ноября 2010

Я думаю, что вопрос не требует пояснений.

Я знаю, что exec запускается на другом процессе, поэтому, если бы я захотел открыть каталог, я бы сделал что-то подобное.

int pid;
if((pid = fork()) != -1) {
     if(!pid) {
         execl("/bin/ls", "-a", "-l", (char *) 0);
     } else {
         wait(&status);
     }
} else //error

Хорошо, если вы хотите создать процесс, но чтоо темах?Я хотел бы сначала создать поток, а затем функцию exec, но это сделало бы, что у только что созданного потока было два процесса

Ответы [ 4 ]

6 голосов
/ 17 ноября 2010

Это не имеет смысла.Потоки используют одно и то же адресное пространство (включая программный код);невозможно, чтобы два отдельных исполняемых файла сосуществовали в одном и том же процессе, поскольку они просто уничтожали бы друг друга.

4 голосов
/ 17 ноября 2010

Это невозможно, exec просто заменит текущий процесс указанным исполняемым файлом, поэтому ваш исходный процесс больше не существует.Кроме того, процесс является более высокой единицей выполнения, чем поток, поэтому нет смысла «запускать процесс внутри другого потока».

3 голосов
/ 17 ноября 2010

Вы должны сделать шаг назад и сообщить нам реальные требования. Вы должны спрашивать, как добиться того, чего вы хотите, а не как этого добиться определенным образом. Делая последнее, вы ограничиваете возможности, что редко бывает разумным.

Для чего стоит, этот код будет работать под POSIX, так как только вызывающий поток приостанавливается до завершения дочернего процесса.

Если вы хотите, чтобы подпроцесс выполнялся как поток в текущем процессе, это не сработает. Вы пытаетесь смешать два разных уровня абстракции, и в тот момент, когда вы exec, текущий процесс загружает всю новую программу. Это не повлияет на родителя (поскольку вы разветвлены), но вы не можете запустить ls (или любую другую программу) в потоке существующего процесса.


Основано на ваших комментариях:

... because my main process has a lot of variables and stuff and I didn't want to duplicate that memory space because of the fork.

Современные операционные системы не будут дублировать все на fork, они намного умнее этого.

Например, Linux будет только копировать таблицы страниц и создавать новую структуру задач. Вся остальная память помечена как копируемая при записи, поэтому ее можно разбивать только при необходимости.

Кроме того, в Linux есть vfork, который даже не будет дублировать таблицы страниц, по крайней мере, до тех пор, пока вы не вызовете exec, но родительский элемент будет приостановлен до этой точки (или _exit), чтобы предотвратить межпроцессное повреждение и вы очень ограничены в том, что ребенку разрешено делать.

0 голосов
/ 22 марта 2019

Когда какой-либо поток вызывает одну из функций exec (), вызывающая программа полностью заменяется. Все потоки, кроме той, которая вызывает exec (), немедленно исчезают. Ни один из потоков не выполняет деструкторы для данных, специфичных для потока, или вызывает обработчики очистки. Все (приватные) мьютексы и условные переменные, принадлежащие процессу, также исчезают. После exec () идентификатор оставшегося потока не указан. Майкл КеррисК "Интерфейс программирования Linux"

...