Skip to article frontmatterSkip to article content
Site not loading correctly?

This may be due to an incorrect BASE_URL configuration. See the MyST Documentation for reference.

Regla 0x2012h: Tipo de retorno obligatorio 'int' en la función main()

Funciones, contratos y modularizacion (0x20XX)

Universidad Nacional de Río Negro

0x2012h: Tipo de retorno obligatorio ‘int’ en la función main()

Enunciado normativo

DEBE declararse main con tipo de retorno int. NO DEBE usarse void main, main() sin tipo ni ninguna variante no estándar. El retorno DEBE informar el estado de terminación del programa.

¿Por qué existe esta regla?

El problema

main no es una función cualquiera: es el punto de entrada cuyo retorno se convierte en el código de salida del proceso. void main miente sobre ese canal: el sistema operativo y las herramientas que encadenan programas (make, scripts, el runner de la cátedra) esperan un entero. Además compila en algunos compiladores viejos por permisividad, lo que da falsa sensación de validez, pero GCC moderno advierte y otros entornos no lo aceptan.

Consecuencias de violarla

Tipo de consecuenciaEfecto concreto
No portabilidadvoid main es inválido fuera del dialecto que lo toleraba.
IntegraciónEl código de salida del proceso queda indeterminado para scripts.
ContratoLa función de entrada no cumple el modelo arranque/terminación.

Fundamento en el estándar y en la cátedra

C11 §5.1.2.2.1 define las formas válidas de main: int main(void) e int main(int argc, char *argv[]). El retorno es int, y si el control llega al final sin return, el estándar garantiza un 0 implícito (§5.1.2.2.3). La cátedra exige la forma estándar para evaluar automáticamente; el runner usa el código de salida para distinguir éxito de fallo (0x2007h: Los valores de retorno numéricos deben definirse como constantes de preprocesador o enums).

Alcance y excepciones

Aplica solo a main. Las demás funciones pueden devolver void, tipos escalares, punteros o estructuras, según su contrato. No se admiten variantes como int32_t main, long main ni static int main.

Excepción: implementaciones freestanding pueden definir su propio punto de entrada, pero el marco de la materia usa siempre un entorno hosted con int main.

Ejemplos exhaustivos

❌ Contraejemplo 1 — void main

#include <stdio.h>

void main(void)
{
    printf("Hola, mundo\n");
}

Por qué falla: declarar void en main es inválido según C11. El compilador puede aceptarlo con advertencia, pero el programa no informa su estado de terminación y no es portable.

❌ Contraejemplo 2 — main sin tipo de retorno

#include <stdio.h>

main()
{
    printf("Hola\n");
}

Por qué falla: en C moderno, omitir el tipo de retorno ya no implica int (el estilo implícito fue eliminado). Además, () deja la lista de parámetros indeterminada, en contra de 0x200Eh: Uso obligatorio de ‘void’ explícito en funciones sin parámetros.

✅ Ejemplo conforme 1 — Forma canónica sin argumentos

#include <stdio.h>

int main(void)
{
    printf("Hola, mundo\n");
    return 0;
}

int main(void) es la forma estándar para programas que no leen argumentos. El retorno 0 señala éxito y coincide con EXIT_SUCCESS de <stdlib.h>.

✅ Ejemplo conforme 2 — Entrada con argumentos y código de error

#include <stdio.h>

int main(int argc, char *argv[])
{
    if (argc != 2) {
        fprintf(stderr, "Uso: %s <archivo>\n", argv[0]);
        return ERROR_ARGUMENTOS;
    }
    FILE *f = fopen(argv[1], "r");
    if (f == NULL) {
        perror("fopen");
        return ERROR_APERTURA;
    }
    fclose(f);
    return 0;
}

El uso de argc/argv sigue la firma exacta del estándar y los códigos de error con nombre respetan 0x2007h: Los valores de retorno numéricos deben definirse como constantes de preprocesador o enums.

⚠️ Casos límite

Cómo detectarla

HerramientaComandoSeñal
gaffgaff check archivo.cmain sin int o con void.
gaffgaff fix archivo.cReescribe la firma a int main(void).
gcc / clanggcc -Wall -Wextra -std=c11 ...“return type of ‘main’ is not ‘int’”.

Checklist de autocontrol

Reglas relacionadas