make how español edition 4th linux linux-kernel linux-device-driver

how - linux device drivers español



Usando linux/types.h en programas de usuario, o stdint.h en el código del módulo de controlador... ¿Importa? (2)

Estoy desarrollando un módulo de controlador de dispositivo y bibliotecas de usuario asociadas para manejar las llamadas ioctl (). La biblioteca toma la información pertinente y la coloca en una estructura, que se pasa al módulo del controlador y se desempaqueta allí y luego se resuelve (estoy omitiendo muchos pasos, pero esa es la idea general).

Algunos de los datos que se pasan a través de la estructura a través de ioctl () son del tipo uint32_t. Descubrí que ese tipo está definido en stdint.h AND linux / types.h. Hasta ahora he estado usando linux / types.h para definir ese valor, incluso en las bibliotecas de usuario. Pero entiendo que es una mala forma usar las bibliotecas linux / *. H en el espacio de usuario, así que si las elimino y uso stdint.h, cuando mi módulo de controlador incluya la definición de estructura, tendrá que incluir stdint.h además.

Me parece que el objetivo de linux / types.h es definir los tipos en los archivos kernel, por lo que no estoy seguro si eso significa que usar stdint.h es una mala idea. También descubrí que al INTENTAR usar stdint.h en mi módulo de controlador, obtengo errores de compilación sobre las redefiniciones que no desaparecerán, incluso si reemplazo todas las instancias de linux / types.h con stdint.h (y lo puse en la parte superior del orden de inclusión).

Soo ....

  1. ¿Es una mala idea usar linux / *. H incluye código de espacio de usuario?
  2. ¿Es una mala idea usar stdint.h en el código kernel-space?
  3. Si las respuestas a ambas son sí, ¿cómo manejo la situación en la que una estructura que contiene uint32_t es compartida tanto por la biblioteca del usuario como por el módulo del controlador?

Gracias.


  1. ¿Es una mala idea usar linux / *. H incluye código de espacio de usuario?

Sí, por lo general. La situación típica es que debe usar los encabezados de la biblioteca C (en este caso, stdint.h y amigos) e interactuar con la biblioteca C a través de esos tipos de espacio de usuario, y dejar que la biblioteca maneje hablando con el núcleo a través del kernel tipos.

Aunque no estás en una situación típica. En tu caso, estás escribiendo la biblioteca del controlador . Por lo tanto, debe presentar una interfaz al espacio de usuario utilizando stdint.h , pero utilizando los encabezados linux/*.h cuando se conecte con su controlador de kernel.

Entonces la respuesta es no, en tu caso.

  1. ¿Es una mala idea usar stdint.h en el código kernel-space?

Definitivamente sí.

Ver también: http://lwn.net/Articles/113349/


Enteros de longitud fija en el kernel de Linux

El kernel de Linux ya tiene enteros de longitud fija que pueden interesarle. En v4.9 en include/asm-generic/int-ll64.h :

typedef signed char s8; typedef unsigned char u8; typedef signed short s16; typedef unsigned short u16; typedef signed int s32; typedef unsigned int u32; typedef signed long long s64; typedef unsigned long long u64;

LDD3 también tiene un capítulo sobre tamaños de datos: https://static.lwn.net/images/pdf/LDD3/ch11.pdf

LDD3 menciona allí que la mejor estrategia de printk es convertir para simplemente lanzar al mayor entero posible con la firma correcta: %lld o %llu . %ju no está disponible en la pieza central de formato de printk lib/linux/vsprintf.c .