Implementando Funções de Callback em C

CBeginner
Pratique Agora

Introdução

Neste projeto, você aprenderá como implementar uma função de callback na linguagem C. Funções de callback são uma técnica poderosa na programação C, especialmente no contexto do desenvolvimento de sistemas Linux, onde são comumente usadas.

👀 Visualização

$ gcc test_callback.c callback.c -o test_callback
$ ./test_callback
Alarm1:0
Alarm2:1
Alarm3:2

🎯 Tarefas

Neste projeto, você aprenderá:

  • Como definir e usar funções de callback em C
  • Como registrar e acionar alarmes usando uma função de callback
  • Como lidar com casos extremos (edge cases) e erros na implementação da função de callback

🏆 Conquistas

Após concluir este projeto, você será capaz de:

  • Compreender o conceito de funções de callback e seu uso na programação C
  • Implementar um sistema de alarme baseado em callback, incluindo o registro e acionamento de alarmes
  • Escrever código robusto e defensivo para lidar com possíveis problemas na função de callback
  • Aplicar seu conhecimento de funções de callback a outras áreas da programação C, como sistemas orientados a eventos ou operações assíncronas

Entenda a Função de Callback

Nesta etapa, você aprenderá sobre o conceito de funções de callback na linguagem C e como elas são usadas no desenvolvimento de programas C para Linux.

Funções de callback são uma maneira de passar uma função como um argumento para outra função, que pode então chamar a função passada em um momento posterior. Esta é uma técnica poderosa que permite um código mais flexível e modular.

No código fornecido no arquivo callback.c, a função de callback é usada para implementar um sistema de alarme. A struct alarm representa um alarme, e a função register_alarm é usada para registrar um alarme. A função hit_alarm é então usada para acionar os alarmes registrados.

✨ Verificar Solução e Praticar

Identificar e Corrigir os Defeitos

Agora, vamos dar uma olhada no código fornecido no arquivo callback.c e corrigir os defeitos.

  1. Segmentation Fault (Falha de Segmentação): Isso provavelmente ocorre porque a alarm_list não está sendo corretamente preenchida ou acessada, levando a um acesso ilegal à memória.
  2. Manipulação Incorreta do Índice em register_alarm: A variável index é local à função register_alarm e é reinicializada para 0 toda vez que a função é chamada. Isso faz com que todos os alarmes sejam registrados no índice 1, sobrescrevendo uns aos outros.

Atualize o arquivo callback.c da seguinte forma:

#include "callback.h"

alarm alarm_list[MAX_ALARMS];
int current_index = 0; // Global index tracker

void register_alarm(alarm a) {
    if (current_index < MAX_ALARMS) {
        alarm_list[current_index] = a;
        current_index++;
    }
    // If the number of registered alarms exceeds MAX_ALARMS, do nothing (don't report an error)
}

int hit_alarm(int index) {
    if (index < 0 || index >= MAX_ALARMS || !alarm_list[index])
        return 1;
    (*alarm_list[index])(index);
    return 0;
}

As principais mudanças são:

  1. Adicionada uma variável global current_index para rastrear o índice atual para registrar alarmes.
  2. Em register_alarm, verificamos se current_index é menor que MAX_ALARMS antes de registrar o alarme. Se o número de alarmes registrados exceder MAX_ALARMS, não relatamos um erro e simplesmente continuamos.
  3. Em hit_alarm, adicionamos verificações adicionais para garantir que o índice esteja dentro do intervalo válido e que um alarme esteja realmente registrado nesse índice. Caso contrário, retornamos 1 para indicar que nenhum alarme foi acionado.
✨ Verificar Solução e Praticar

Testar a Função de Callback

Agora que corrigimos os defeitos no arquivo callback.c, vamos testar a função de callback executando o programa test_callback.c fornecido.

Compile o programa:

gcc test_callback.c callback.c -o test_callback

Execute o programa:

./test_callback

Saída:

Alarm1:0
Alarm2:1
Alarm3:2

A saída agora deve corresponder à saída esperada, e o programa deve ser executado sem nenhuma falha de segmentação ou outros erros.

Parabéns! Você depurou e corrigiu com sucesso a implementação da função de callback.

✨ Verificar Solução e Praticar

Resumo

Parabéns! Você concluiu este projeto. Você pode praticar mais laboratórios no LabEx para aprimorar suas habilidades.