Subprocesos vs procesos (bifurcados)

9

Las aplicaciones de Linux generalmente se bifurcan y luego se ejecutan (con execve ()), pero las aplicaciones de Java y ciertos MPM de Apache usan subprocesos. Si se bifurca, utiliza fork + exec para generar un proceso, ¿cuál es la versión de alto nivel para subprocesos? ¿Cómo genera JVM o Worker MPM hilos?

Gregg Leventhal
fuente
2
Echa un vistazo a Stackoverflow. Hay varias preguntas y respuestas que explicaron parte de esto.
Henk Langeveld

Respuestas:

13

La idea detrás de los hilos y procesos es casi la misma: bifurca la ruta de ejecución. De lo contrario, los hilos y procesos difieren en cosas como la memoria. Es decir, los procesos tienen un espacio de VM diferente, mientras que los hilos comparten lo que existía antes de la división.

Subyacente al trabajo de subprocesamiento y bifurcación mediante el uso de la llamada clone () (clon man 2):

A diferencia de fork (2), clone () permite que el proceso hijo comparta partes de su contexto de ejecución con el proceso de llamada, como el espacio de memoria, la tabla de descriptores de archivos y la tabla de manejadores de señales. (Tenga en cuenta que en esta página del manual, "proceso de llamada" normalmente corresponde al "proceso padre". Pero consulte la descripción de CLONE_PARENT a continuación).

El uso principal de clone () es implementar hilos: múltiples hilos de control en un programa que se ejecuta simultáneamente en un espacio de memoria compartida.

Las diferencias provienen de las banderas que se pasan a clone (). Como puede ver en la página de manual, fork y threading son solo un conjunto de parámetros predefinidos para clonar (). Sin embargo, uno también puede hacer cosas personalizadas con él.

V13
fuente
1
Uhm? ¿Qué? Vuelva a leer casi todos los libros sobre el tema, porque el espacio de memoria separado para los procesos es un gran problema. También ayuda a "atrapar" el código que se bloquea, mientras que el núcleo simplemente matará un proceso en el que un hilo individual se vuelve loco / traspasa.
0xC0000022L
3
@ 0xC0000022L su argumento no contradice la respuesta, como me parece a mí.
Ruslan
1
@Ruslan: Ruego diferir: "¿La idea [...] es casi la misma"? La idea detrás de los hilos es de hecho concurrencia, pero para los procesos esta es una historia completamente diferente.
0xC0000022L
44
@ 0xC0000022L Se perdió la parte importante de la respuesta de V13: "Bifurca la ruta de ejecución" - la pregunta es sobre cómo se
generan los
@Izkata: en absoluto. Solo sostengo que este no es un reclamo correcto.
0xC0000022L
8

La mayoría de los sistemas operativos (SO) de multiprocesamiento no Unix utilizan una llamada "spawn ()" o algo similar para generar un nuevo proceso de OS o flujo de control. Spawn () tiende a ser una llamada muy compleja, con muchas opciones y muchos gastos generales. Una de las innovaciones de Unix fue proporcionar una forma general mucho más baja de crear procesos: fork (). Unix se encargó de las muchas opciones necesarias para generar () al permitir cantidades arbitrarias de procesamiento antes de la otra mitad de spawn (), con exec ().

Como Unix y sus variantes se usaban cada vez más, se descubrió que la creación de procesos de baja sobrecarga era útil y se usó. De hecho, se usó tanto que la gente quería formas más bajas de crear procesos, y así nació la idea de "hilos". Originalmente, los subprocesos fueron manejados completamente por el proceso de origen (y programas como la JVM pueden hacer esto con "subprocesos verdes"); pero manejar la programación de subprocesos múltiples es complicado y con frecuencia se realizó incorrectamente. Por lo tanto, hay una forma más fácil e intermedia de hacer subprocesos, donde el sistema operativo maneja la programación pero se ahorra algo de sobrecarga al compartir (típicamente) el espacio de direcciones entre subprocesos.

Su pregunta es difícil de responder porque hay varios conceptos diferentes pero relacionados que son todos "hilos", y para detalles necesita un adjetivo para describir a cuál se refiere. Por otro lado, comprender las diferencias probablemente lo llevará a la respuesta específica que desea. Busque cosas como "procesos livianos", "hilos de usuario" y "rfork ()" para obtener más información.

mpez0
fuente
1
"manejar la programación de subprocesos múltiples es complicado y con frecuencia se hizo incorrectamente", se necesita una cita. Implementar hilos de espacio de usuario no es un problema. El problema con los subprocesos de espacio de usuario es que si un subproceso realiza una llamada de bloqueo, todos los subprocesos se bloquean. La única forma de evitar esto es mediante el uso de subprocesos a nivel del sistema.
Bakuriu 05 de
1
Curiosamente, Windows no incluyó esta innovación de Unix: no tiene CreateProcess()nada parecido fork().
Ruslan
2
@Bakuriu: busque cualquiera de los muchos artículos sobre cómo crear programadores de multiprocesamiento, mantener la imparcialidad, evitar el hambre, manejar las prioridades, etc. Implementar hilos de espacio de usuario no es, como usted dice, un problema. Programar ejemplos no triviales es difícil.
mpez0
@Ruslan: uno puede bifurcar en Windows, simplemente no es parte de la API Win32. Lea "La API nativa de Windows NT / 2000" de Nebbett. Él tiene una implementación que imita fork().
0xC0000022L
3

Los subprocesos y la bifurcación son en realidad dos conceptos diferentes, los cuales existen en los sistemas Unix / Linux (y ambos se pueden usar en C / C ++).

La idea de un fork () es (muy básicamente) una creación de un proceso separado que tiene el mismo código de ejecución que el proceso padre, y que comienza la ejecución en la línea fork. El propósito de usar horquillas con funciones ejecutivas es que las funciones ejecutivas cierran el proceso que las llamó cuando finalizan. Por lo tanto, generalmente se bifurca, obtiene el PID de cada proceso (el niño siempre es 0) y hace que el padre espere hasta que el niño termine de ejecutar la función exec.

Los hilos se usan para el paralelismo (recuerde que el padre espera al hijo, generalmente, en un programa bifurcado). Un hilo, como pthread en C / C ++ (hacer una búsqueda en Google), se ejecutará en paralelo al proceso principal y puede compartir variables globales y funciones globales con el programa original. Dado que los hilos de Java se comportan de manera similar, me imagino que actúan más como estos hilos que como un proceso de bifurcación.

Básicamente, hay una diferencia entre bifurcación y roscado. Hacen cosas claramente diferentes (aunque parezcan similares). Estos conceptos pueden ser difíciles de entender, pero puede aprenderlos a través de una investigación (extensa) si tiene un sincero deseo de comprenderlos.

EDITAR # 1

Vea estos ejemplos de cómo se pueden llamar y utilizar los tenedores y los hilos. Tenga en cuenta el comportamiento de las funciones ejecutivas y sus efectos en el programa principal.

http://www.jdembrun.com:4352/computerScience/forkVSthread.zip

jaredad7
fuente
2
Fork (con o sin exec) también se puede usar para paralelismo. No estoy seguro de lo que quiere decir con "las funciones ejecutivas cierran el proceso que las llamó cuando finalizan", exec hace tiempo que terminó de ejecutarse cuando finaliza el proceso. También pthreades una API, no una implementación de subprocesos.
Mat
En cuanto a la bifurcación, estoy citando a mi maestro de SO. De acuerdo con lo que nos ha dicho, sí, la bifurcación podría usarse para ejecutarse en paralelo, pero, si usara una función ejecutiva, esa sería la última. En cuanto a pthread, se entiende como un ejemplo.
jaredad7
Exec sería la última llamada en el código de la persona que llama, no la última instrucción del proceso bifurcado. El proceso bifurcado viviría al ejecutar el código ejecutado.
Mat
Sus comentarios me han llevado a probar estas cosas. He escrito algunos programas en c ++ que demuestran el comportamiento de las funciones ejecutivas y sus efectos en los programas cuando se usan en bifurcaciones frente a hilos. Por favor vea la edición de arriba.
jaredad7
Me temo que la mayoría de la gente no se molestará en descargar eso. Además, sus ejemplos no ilustran las diferencias interesantes entre los modelos, que están relacionados principalmente con compartir (o no) el espacio de direcciones.
Mat
1

Tanto JVM como Apache MPM confían en el núcleo para hilos nativos. Es decir, usan el sistema operativo para programarlos. Por supuesto, ambos necesitan su propia API para realizar un seguimiento de las cosas.

Stackoverflow ya tiene varias preguntas relacionadas con esto:

  1. Hilos nativos de JVM , consulte esta respuesta para obtener más detalles.

  2. Apache tiene dos tipos de MPM: Prefork, con un proceso por subproceso, y Worker, que maneja varios subprocesos: Apache MPM . Mira la referencia acodebucket

Henk Langeveld
fuente
1

Si se bifurca, utiliza fork + exec para generar un proceso, ¿cuál es la versión de alto nivel para subprocesos? ¿Cómo genera JVM o Worker MPM hilos?

Eso es específico de la plataforma, pero en Linux y supongo que muchos otros sistemas compatibles con POSIX utilizan la implementación local de pthreads , una API de subprocesos de usuario y tierra. P.ej:

#include <pthread.h>

pthread_t tid;
pthread_create(&tid, NULL, somefunc, NULL);

Inicia un nuevo hilo llamando somefunccomo su primer punto de ejecución.

También puede crear hilos - distinto de bifurcaciones en que comparten el mismo mundial montón de espacio de memoria del proceso padre, en lugar de obtener un duplicado de la misma (pero roscas nota cada Ejecutar con una organización independiente pila de memoria de los suyos) - con la clone()llamada al sistema, que es sobre lo que se construye pthreads.

encerrada dorada
fuente