Nesta aula, vamos explorar os conceitos fundamentais sobre processos e escalonamento em sistemas operacionais. Entender como o sistema gerencia múltiplos programas concorrentes é essencial para a ciência da computação. Vamos abordar desde a definição de processo até os principais algoritmos de escalonamento.

O que é um Processo?

Um processo é um programa em execução. Ele inclui o código do programa, o contador de programa, as variáveis, os registradores e o contexto de hardware. Diferente de um programa, que é uma entidade passiva armazenada em disco, o processo é uma entidade ativa que possui um estado em um determinado instante.

Em sistemas operacionais modernos, cada processo possui seu próprio espaço de endereçamento, garantindo isolamento e proteção. O sistema operacional mantém uma tabela de processos, onde cada entrada (chamada de Process Control Block - PCB) armazena as informações necessárias para gerenciar o processo.

Estados de um Processo

  • Novo (New): O processo está sendo criado.
  • Pronto (Ready): O processo está carregado na memória e aguardando para ser executado pela CPU.
  • Executando (Running): O processo está utilizando a CPU.
  • Bloqueado (Waiting/Blocked): O processo está aguardando por um evento (como E/S ou um sinal).
  • Terminado (Terminated): O processo terminou sua execução.

Escalonamento de Processos

O escalonamento é a atividade do sistema operacional que decide qual processo, na fila de prontos, receberá a CPU. O módulo responsável por essa decisão é chamado de escalonador (scheduler). Existem diferentes tipos de escalonamento: de longo prazo, médio prazo e curto prazo.

O escalonador de curto prazo (ou CPU scheduler) seleciona um processo da fila de prontos e aloca a CPU para ele. A frequência desse escalonamento é alta (a cada dezenas de milissegundos), sendo crucial para o desempenho do sistema.

Algoritmos de Escalonamento

Diversos algoritmos foram propostos para atender a diferentes critérios, como maximizar a utilização da CPU, minimizar o tempo de resposta e garantir equidade. Os principais incluem:

  1. First-Come, First-Served (FCFS): O primeiro processo a chegar é o primeiro a ser executado. Simples, mas pode causar o efeito convoy (processos curtos esperam por um longo processo).
  2. Shortest Job First (SJF): Seleciona o processo com o menor tempo de execução estimado. Pode ser preemptivo ou não. Ótimo em termos de tempo médio de espera, mas sofre de starvation para processos longos.
  3. Round Robin (RR): Cada processo recebe um quantum de tempo (time slice) e é executado em modo circular. Ideal para sistemas interativos, mas o desempenho depende do tamanho do quantum.
  4. Escalonamento por Prioridades: Cada processo recebe uma prioridade e a CPU é alocada para o processo de maior prioridade. Pode causar starvation para processos de baixa prioridade, resolvido com envelhecimento (aging).
  5. Múltiplas Filas (Multilevel Queue): Processos são divididos em diferentes filas com base em características, e cada fila pode usar seu próprio algoritmo.

Pontos Importantes sobre Escalonamento

  • A troca de contexto (context switch) ocorre quando a CPU alterna de um processo para outro; ela consome tempo e overhead.
  • O escalonamento pode ser preemptivo (o scheduler pode interromper um processo em execução) ou não preemptivo (o processo executa até terminar ou bloquear).
  • Sistemas em tempo real requerem escalonamento com garantias de deadlines.

Exemplo Simples de Algoritmo Round Robin em Python

def round_robin(processos, quantum):
    fila = processos[:]
    tempo = 0
    while fila:
        processo = fila.pop(0)
        if processo['tempo'] > quantum:
            tempo += quantum
            processo['tempo'] -= quantum
            fila.append(processo)
            print(f"Processo {processo['id']} executou por {quantum} unidades, tempo restante: {processo['tempo']}")
        else:
            tempo += processo['tempo']
            print(f"Processo {processo['id']} finalizado no tempo {tempo}")
    print(f"Tempo total de simulação: {tempo}")

# Exemplo de uso
processos = [{'id': 1, 'tempo': 10}, {'id': 2, 'tempo': 5}, {'id': 3, 'tempo': 8}]
round_robin(processos, 3)

Troca de Contexto

Quando o escalonador decide interromper um processo e iniciar outro, o sistema deve salvar o estado do processo atual (contexto) e carregar o estado do novo processo. Esse mecanismo é chamado de troca de contexto. O contexto inclui registradores, contador de programa, ponteiro de pilha, etc. A troca de contexto é um overhead puro, pois a CPU não realiza trabalho útil durante esse período.

Processos vs. Threads

Uma thread é a unidade básica de utilização da CPU, composta por um ID de thread, contador de programa, registradores e pilha. Threads de um mesmo processo compartilham o espaço de endereçamento e recursos, tornando a comunicação mais eficiente que entre processos. No entanto, a falta de proteção entre threads exige sincronização cuidadosa.

Sistemas operacionais modernos suportam threads em nível de usuário (ULT) e threads em nível de kernel (KLT). A maioria dos sistemas atuais utiliza threads nativas do kernel.

Perguntas Frequentes (FAQ)

O que é um processo?
É um programa em execução, incluindo código, dados, estado e contexto.
Qual a diferença entre escalonamento preemptivo e não preemptivo?
No preemptivo, o sistema pode interromper o processo em execução para alocar a CPU a outro. No não preemptivo, o processo mantém a CPU até terminar ou bloquear.
O que é starvation?
É quando um processo nunca recebe a CPU por existirem processos de maior prioridade sempre prontos. A técnica de aging aumenta a prioridade de processos que esperam muito tempo.
O que é quantum no Round Robin?
É o intervalo de tempo máximo que cada processo pode usar a CPU antes de ser interrompido. Deve ser balanceado: muito pequeno causa muitas trocas de contexto; muito grande degrada a interatividade.

Conclusão

Nesta aula, vimos os conceitos essenciais sobre processos e escalonamento em sistemas operacionais. Compreender esses tópicos é fundamental para projetar e analisar o desempenho de sistemas computacionais. Nos próximos dias, aprofundaremos em mecanismos de sincronização e comunicação entre processos.