Error al verificar una función que devuelve un int

Si tengo una función que devuelve algún tipo de puntero, compruebo los errores configurando el retorno a NULL en caso de error.

char *foo(void) {
  //If stuff doesn't go okay
  return NULL;
}

char *bar = foo();
if(!bar) return 1;

Esto funciona muy bien porque sé que en tales casos nunca tendré la intención de devolver NULL.

Sin embargo, a veces tendré funciones que devuelven enteros (en este caso, estoy leyendo entradas de un archivo de configuración). Sin embargo, el problema es que ahora no hay forma de verificar el valor devuelto en busca de errores porque cualquier valor (incluido 0) podría ser genuino.

Un par de soluciones:

Incluir un parámetro de código de error en la funciónDevuelve un código de error e incluye un puntero int como parámetro

El problema con ambos es que tengo un conjunto de funciones que hacen lo mismo pero para diferentes tipos y quiero mantener una interfaz regular para que puedan usarse de la misma manera.

¿Hay otra solución que no implique cambiar la interfaz a la función? ¿Cuál es la forma más común de lidiar con esta situación?

SOLUCIÓN ELEGIDA

Gracias por todos sus pensamientos y respuestas sobre esto.

Al final decidí que si una función está destinada a devolver algunos datos, un error solo se puede devolver a través de un parámetro de error. De lo contrario, el error se devuelve directamente.

Elegí esta raíz porque generalmente descubrí que al devolver formas de datos más complejas, la cantidad de errores potenciales era casi siempre mayor que 1. Esto significaba que usar NULL como la única fuente de datos de error no era práctico de todos modos, ya que significaba que no había manera de determinar cuál fue realmente el error. Con las funciones que devuelven datos como int, también se hizo imposible distinguir múltiples códigos de error diferentes de datos válidos.

Lo mismo no es cierto, por supuesto, para las funciones que realmente no devuelven ningún dato, en cuyo caso soy libre de usar el valor de retorno como un código de error.

También me gusta el hecho de que el patrón anterior hace una clara distinción entre funciones que devuelven datos y funciones que no lo hacen.

Respuestas a la pregunta(7)

Su respuesta a la pregunta