tomadas tiene son sistemas seguir que procesos proceso por pasos para operativos lugar los hilos estados entre diferencia debe cuando cuales contexto cambio acciones multithreading process context-switch

multithreading - tiene - procesos e hilos



Pasos en el cambio de contexto (3)

  1. En un conmutador, el estado del proceso que se está ejecutando actualmente debe guardarse de alguna manera, de modo que cuando se reprograme, este estado se puede restaurar.
  2. El estado del proceso incluye todos los registros que el proceso puede estar usando, especialmente el contador del programa, más cualquier otro dato específico del sistema operativo que pueda ser necesario. Esto generalmente se almacena en una estructura de datos llamada bloque de control de proceso (PCB) o switchframe.
  3. La PCB puede almacenarse en una pila por proceso en la memoria del kernel (a diferencia de la pila de llamadas en modo de usuario), o puede haber alguna estructura de datos definida por el sistema operativo específico para esta información. Se agrega un identificador a la PCB a una cola de procesos que están listos para ejecutarse, a menudo llamada la cola lista.
  4. Dado que el sistema operativo ha suspendido efectivamente la ejecución de un proceso, puede cambiar el contexto eligiendo un proceso de la cola de espera y restaurando su PCB. Al hacerlo, se carga el contador del programa desde el PCB y, por lo tanto, la ejecución puede continuar en el proceso elegido. El proceso y la prioridad del hilo pueden influir en qué proceso se elige de la cola lista (es decir, puede ser una cola de prioridad).

(Fuente: cambio de contexto )

Se me pide que describa los pasos involucrados en un cambio de contexto (1) entre dos procesos diferentes y (2) entre dos hilos diferentes en el mismo proceso.

  1. Durante un cambio de contexto, el kernel guardará el contexto del proceso anterior en su PCB y luego cargará el contexto guardado del nuevo proceso programado para ejecutarse.
  2. El sistema operativo puede programar el cambio de contexto entre dos subprocesos diferentes en el mismo proceso para que parezcan ejecutarse en paralelo y, por lo tanto, generalmente es más rápido que los cambios de contexto entre dos procesos diferentes.

¿Es esto demasiado general o qué agregaría para explicar el proceso con mayor claridad?


Es mucho más fácil explicarlos en orden inverso porque un cambio de proceso siempre implica un cambio de hilo.

Un conmutador de contexto de subproceso típico en una CPU de un solo núcleo sucede así:

  1. Todos los cambios de contexto son iniciados por una ''interrupción''. Esto podría ser una interrupción de hardware real que ejecuta un controlador (por ejemplo, desde una tarjeta de red, teclado, administración de memoria o hardware con temporizador), o una llamada de software (llamada del sistema), que realiza una secuencia de llamada similar a una interrupción de hardware para entrar en el sistema operativo. En el caso de una interrupción del controlador, el sistema operativo proporciona un punto de entrada al que el controlador puede llamar en lugar de realizar la "interrupción-retorno directo" normal y así permite que un controlador salga a través del programador del sistema operativo si necesita que el sistema operativo establezca un hilo. listo, (por ejemplo, ha señalado un semáforo).

  2. Los sistemas no triviales deberán iniciar un cambio de nivel de protección de hardware para ingresar un estado de kernel para que se pueda acceder al código / datos del kernel, etc.

  3. El estado del núcleo para el hilo interrumpido tiene que ser guardado. En un sistema integrado simple, esto podría ser simplemente empujar todos los registros en la pila de hilos y guardar el puntero de pila en su Bloque de control de hilos (TCB).

  4. Muchos sistemas cambian a una pila dedicada al sistema operativo en esta etapa para que la mayor parte de los requisitos de la pila interna del sistema operativo no se inflijan en la pila de cada subproceso.

  5. Puede ser necesario marcar la posición de la pila de hilos donde ocurrió el cambio al estado de interrupción para permitir interrupciones anidadas.

  6. La llamada del controlador / sistema se ejecuta y puede cambiar el conjunto de subprocesos listos agregando / eliminando TCB de las colas internas para las diferentes prioridades de subprocesos, por ejemplo. el controlador de la tarjeta de red puede haber establecido un evento o haber señalado un semáforo que otro hilo estaba esperando, por lo que ese hilo se agregará al conjunto preparado, o un hilo en ejecución puede haber llamado a sleep () y, por lo tanto, se eligió para retirarse del conjunto preparado .

  7. El algoritmo del planificador del sistema operativo se ejecuta para decidir qué subproceso se ejecutará a continuación, normalmente el subproceso preparado con la prioridad más alta que está en la parte delantera de la cola para esa prioridad. Si el subproceso próximo a ejecutar pertenece a un proceso diferente al subproceso ejecutado anteriormente, se necesitan algunas cosas adicionales aquí (ver más adelante).

  8. El puntero de pila guardado del TCB para ese hilo se recupera y se carga en el puntero de pila de hardware.

  9. El estado del núcleo para el hilo seleccionado se restaura. En mi sistema simple, los registros serían extraídos de la pila del hilo seleccionado. Los sistemas más complejos tendrán que manejar un retorno a la protección a nivel de usuario.

  10. Se realiza una interrupción-retorno, por lo que se transfiere la ejecución al hilo seleccionado.

En el caso de una CPU multinúcleo, las cosas son más complejas. El programador puede decidir que un subproceso que se está ejecutando actualmente en otro núcleo debe ser detenido y reemplazado por un subproceso que acaba de estar listo. Puede hacer esto utilizando su controlador interprocessor para interrumpir por hardware el núcleo que ejecuta el subproceso que debe detenerse. La complejidad de esta operación, además de todas las demás cosas, es una buena razón para evitar escribir kernels del sistema operativo :)

Un cambio de contexto de proceso típico ocurre así:

  1. Los cambios de contexto de proceso se inician mediante un cambio de contexto de subproceso, por lo que todo lo anterior, 1-9, deberá suceder.

  2. En el paso 5 anterior, el programador decide ejecutar un subproceso que pertenece a un proceso diferente del que era propietario del subproceso que se estaba ejecutando anteriormente.

  3. El hardware de administración de la memoria debe cargarse con el espacio de direcciones para el nuevo proceso, es decir, los selectores / segmentos / indicadores / lo que permita que los subprocesos del nuevo proceso accedan a su memoria.

  4. El contexto de cualquier hardware de FPU debe guardarse / restaurarse desde la PCB.

  5. Puede haber otro hardware dedicado al proceso que deba guardarse / restaurarse.

En cualquier sistema real, los mecanismos dependen de la arquitectura y lo anterior es una guía aproximada e incompleta de las implicaciones de cada cambio de contexto. Hay otros gastos generales generados por un cambio de proceso que no son estrictamente parte del cambio; puede haber vacíos de caché adicionales y fallos de página después de un cambio de proceso, ya que parte de su memoria puede haber sido paginada a favor de las páginas que pertenecen. al proceso que posee el hilo que se estaba ejecutando antes.


Espero poder proporcionar una imagen más detallada / clara.

En primer lugar, el sistema operativo programa subprocesos, no procesos, porque los subprocesos son las únicas unidades ejecutables en el sistema. El interruptor de proceso es solo un interruptor de hilos donde los hilos pertenecen a procesos diferentes. Debido a esto en general el procedimiento de cambio es común.

  1. El programador debe ser invocado. Hay tres escenarios básicos:

    • Cambio involuntario. Han ocurrido algunos eventos externos a su hilo que han afectado la programación. Por ejemplo, el anillo del temporizador ha activado un hilo con alta prioridad, el controlador de HDD ha informado que parte del archivo solicitado ha sido leído en la memoria, y el hilo en espera puede continuar su ejecución, el temporizador del sistema le ha dicho al kernel que su hilo había Se acabó el tiempo cuántico, etc.
    • Voluntario. El hilo solicita explícitamente la reprogramación por llamada al sistema. Por ejemplo, solicitó un rendimiento, solicitó un sueño o solicitó esperar hasta que se libere el mutex.
    • Semi-voluntario Subprocesamiento desencadenó implícitamente la reprogramación realizando alguna llamada de sistema no relacionada. Por ejemplo, le pidió a un sistema que lea un archivo. El sistema operativo ha enrutado esta solicitud al controlador del disco y, para no perder el tiempo en espera, el resultado decidió cambiar a otro subproceso.
  2. En todos los casos, para poder realizar un cambio de hilo, el control debe pasarse al kernel. En el caso de interruptores involuntarios, dicho paso de control se realiza por interrupción, en el caso de un control voluntario (y semi-voluntario) se pasa a través de una llamada al sistema.

  3. En ambos casos, la entrada al kernel es asistida por la CPU. El procesador realiza la verificación de permisos, recuerda un punto en el que se reemplazó el subproceso (para poder reanudarlo en el futuro), cambia de la parte del usuario de la pila de subprocesos a su contraparte del kernel, y pasa un control a un punto predefinido y conocido en el código del kernel.

  4. La primera acción que realiza el kernel es guardar el contenido de los registros de la CPU, que el kernel reutilizará para sus propias tareas. Por lo general, el kernel usa solo registros de CPU de propósito general y los guarda empujando en la pila.
  5. Luego, el kernel maneja una solicitud primaria: controla la interrupción, prepara la solicitud de lectura del archivo o realiza la configuración del temporizador.
  6. En algún punto del manejo de solicitudes, el kernel realiza una acción que afecta el estado del subproceso actual (decidió que no hay nada que hacer en este subproceso y debemos esperar algo) o afecta el estado de otro (s) subproceso (nuevo hilo se convirtió en ejecutable como resultado de la interrupción recibida o debido al mutex liberado, etc.).
  7. Kernel invoca a un planificador. Programador tiene que tomar dos decisiones. El primero es sobre qué hacer con un hilo actual. ¿Debería estar bloqueado? Si es así, ¿en qué cola de espera se debe colocar? Si el hilo se cambia involuntariamente, se coloca en el final de la cola de ejecución, si el hilo se bloquea, porque espera algo, se coloca en una de las colas de espera. La segunda decisión es sobre qué hilo ejecutar a continuación.
  8. Una vez que se toman las dos decisiones, el programador realiza un intercambio de contexto y le pasa dos parámetros: el bloque de control de subprocesos de los subprocesos actuales y siguientes.
  9. El cambio de contexto en sí consta de tres pasos principales. En la primera, el kernel determina qué subprocesos de CPU utiliza realmente y guarda su contenido en la pila o en TCB de subproceso de salida. Si el subproceso no utiliza los registros FPU y SSE (por ejemplo, para la plataforma IA-32), su contenido no se guardará.
  10. El segundo paso es un cambio de contexto. El kernel empuja el puntero de instrucción actual a la pila y el valor del puntero de pila se guarda en TCB del hilo saliente. Luego carga en la CPU el nuevo puntero de pila de TCB del subproceso entrante y saca el puntero de instrucción desde su parte superior. Eso es todo! Nueva pila activa significa nuevo hilo activo. A partir de este punto, el resto del sistema pensará que funciona en el contexto del subproceso entrante.
  11. En el tercer paso, el núcleo se da cuenta de los registros realmente utilizados por el subproceso entrante y carga su contenido guardado previamente (mira el paso 1) de nuevo en la CPU.
  12. Luego, las comprobaciones del kernel pertenecen o no a los dos hilos (entrantes y salientes) en el mismo proceso. Si pertenecen a procesos diferentes (en el caso en el que la gente llama a switch de proceso), el núcleo restablece el espacio de direcciones actual apuntando a MMU al nuevo conjunto de tablas de traducción de direcciones virtuales a físicas. Como parte de este proceso, la CPU vacía el búfer de traducción (TLB), que almacena las reglas de traducción de direcciones virtuales a físicas. Nuevo espacio de direcciones virtuales significa que las reglas previamente almacenadas en caché ahora son incorrectas. Tenga en cuenta que este es el único paso en el conjunto completo de acciones de cambio de contexto que se preocupan por los procesos.
  13. Kernel prepara Thread Local Storage para el thread entrante. Por ejemplo, asigna las páginas de memoria respectivas a las direcciones especificadas o, por ejemplo, en el enfoque común IA-32 es cargar un nuevo segmento que apunte a los datos TLS del subproceso entrante.
  14. Finalmente, el kernel se carga en la dirección de la CPU de la parte del kernel del subproceso entrante. Después de esto, cada nueva invocación del kernel utilizará la parte del kernel de la pila del subproceso entrante y no dañará los datos almacenados en la pila del subproceso saliente.
  15. Otro paso que puede ser realizado por el kernel es la reprogramación del temporizador del sistema. Al hacer esto, el kernel le pide al temporizador que suene y pase el control al kernel después de que se pase algún tiempo. Este período de tiempo se llama cantidad de tiempo del hilo.
  16. Finalmente, a los kernels les gusta recopilar estadísticas durante los cambios de contexto, incluida la información de soch, ya que la cantidad de tiempo de CPU consume, cómo pueden ocurrir los cambios de contexto en el sistema en la unidad de tiempo real, cuántas veces se invocaron los hilos, cuántas veces se ha liberado el CPU voluntariamente e involuntario, cuántas veces se quedaron sin ellos cuánticos. Parte de esa estadística es utilizada por el planificador, que intenta tomar decisiones más óptimas. Otro propósito de las estadísticas es la entrega a los administradores y usuarios del sistema para mostrarles lo que sucede debajo del capó del sistema.
  17. El cambio de hilo se puede considerar como realizado en este punto y el kernel continúa las acciones del sistema previamente interrumpidas. Por ejemplo, el hilo que estaba esperando la lectura del archivo inspecciona el resultado de lectura en la memoria y lo maneja. O un hilo que fue bloqueado en el mutex en medio de una gran actividad del sistema continúa esa actividad.
  18. Finalmente, más tarde o más pronto, el hilo finaliza sus actividades de sistema y desea volver al modo de usuario para continuar con su tarea principal, para la cual fue empleado inicialmente. En este punto, el kernel hace estallar el contenido de la pila del kernel de los registros de propósito general que se guardaron previamente durante el ingreso al kernel y le pide a la CPU que realice el retorno al modo de usuario.
  19. La CPU captura los valores de puntero de instrucción y puntero de pila, que se guardaron previamente durante el ingreso al modo de núcleo y los restaura. Al hacer esto, también cambia el hilo de la parte del kernel de su pila a la parte del usuario de la pila. Finalmente, la CPU restablece los permisos del código que se ejecutará a un conjunto más limitado (por ejemplo, prohíbe el uso de instrucciones especiales del sistema o prohíbe el acceso al código y los datos de kerel). Finalmente, la CPU pasa el control de vuelta al punto donde el subproceso fue inicialmente reemplazado. En el caso de que el subproceso de la llamada al sistema proceda en el punto donde se invocó la llamada del sistema, capturando y manejando su resultado. En el caso de preferencia por interrupción, el subproceso continuará su ejecución exactamente en el mismo punto en el que estaba cuando ocurrió la interrupción. En ese caso, incluso será completamente inconsciente de que fue interrumpido.

Algunas notas de resumen:

  1. Kernel programa y ejecuta solo hilos, no procesos. Debido a este contexto swicth sucede entre los hilos.
  2. El procedimiento de cambio de contexto entre las bandas de rodadura que pertenecen a diferentes procesos es esencialmente el mismo que entre las cadenas que pertenecen al mismo proceso. En el primer caso, solo hay un paso adicional: cargar un nuevo espacio de direcciones virtuales (lo que lleva a la descarga TLB).
  3. El contexto de los hilos se almacena en la parte del núcleo de la pila de hilos o en el hilo TCB (¡no en PCB!).
  4. El interruptor de hilos introduce una penalización de rendimiento. Hay un costo directo significativo de cambio de hilos. E incluso un costo indirecto mucho mayor creado por la contaminación del caché y el vaciado TLB (si el espacio de direcciones virtuales se recargaba durante el cambio).