¿Qué tan grande (en bits) es un UID de Unix?

18

Entiendo que las ID de usuario (UID) de Unix suelen ser enteros sin signo de 16 o 32 bits, pero ¿cómo puedo encontrar un sistema determinado (en un shell)?

Josef
fuente

Respuestas:

12

Usted tendrá que buscar en <limits.h>(o uno de los archivos que incluye, por ejemplo, sys/syslimits.hen OS X) para el #definede UID_MAX.

Los sistemas operativos más recientes (Solaris 2.x, OS X, BSD, Linux, HP-UX 11i, AIX 6) pueden manejar hasta dos mil millones ( 2^31-2), por lo que asumiría eso y haría una solución para los sistemas más oscuros que no 't.

DM.
fuente
1
Lamentablemente, no existe tal cosa UID_MAX. Por ejemplo, herramientas de shadow-utilsuso (uid_t)-1para averiguar el valor máximo para UID.
kirelagin
55
La mayoría de los sistemas usan /etc/login.defs, que tiene UID_MAX configurado para el valor UID más alto, 60000 en cualquier sistema que haya comprobado.
Ryaner
66
La página de manual para login.defsindica que, en ese contexto, UID_MAXsolo controla el uid más alto que se asignará automáticamente a los nuevos usuarios creados con useradd.
Stephen Touset
2
Probablemente sea 2 ^ 32 (4 mil millones en lugar de 2). En RHEL UID 4.294.967.295 (2 ^ 32-1) a menudo está reservado para un UID de "valor no válido", y 4.294.967.294 (2 ^ 32-2) está reservado para el usuario nfsnobody en algunos sistemas operativos. Por lo tanto, el valor máximo no reservado es 4.294.967.293 (2 ^ 32-3)
tehnicaorg
4

glibc proporciona definiciones para todos esos tipos de sistemas.

Puedes consultar /usr/include/bits/typesizes.h:

% grep UID_T /usr/include/bits/typesizes.h
#define __UID_T_TYPE            __U32_TYPE

A continuación te fijas en /usr/include/bits/types.h:

% grep '#define __U32_TYPE' /usr/include/bits/types.h
#define __U32_TYPE              unsigned int

Esto le permite descubrir el tipo C. Como necesita el tamaño en bytes, su mejor opción es analizar el nombre typedef de acuerdo con la especificación en types.h:

We define __S<SIZE>_TYPE and __U<SIZE>_TYPE for the signed and unsigned
variants of each of the following integer types on this machine.

 16      -- "natural" 16-bit type (always short)
 32      -- "natural" 32-bit type (always int)
 64      -- "natural" 64-bit type (long or long long)
 LONG32      -- 32-bit type, traditionally long
 QUAD        -- 64-bit type, always long long
 WORD        -- natural type of __WORDSIZE bits (int or long)
 LONGWORD    -- type of __WORDSIZE bits, traditionally long

Entonces, aquí hay una frase:

% grep '#define __UID_T_TYPE' /usr/include/bits/typesizes.h | cut -f 3 | sed -r 's/__([US])([^_]*)_.*/\1 \2/'
U 32

Aquí Usignifica unsigned(esto también puede ser Spara signed) y 32es el tamaño (búsquelo en la lista anterior; creo que, la mayoría de las veces, puede suponer que ya es tamaño en bytes, pero si desea que su script sea totalmente portátil, podría ser mejor hacer casecambiar este valor).

kirelagin
fuente
1
En mi sistema (Ubuntu 12.04) y otros sistemas basados ​​en Debian, el archivo de encabezado es: /usr/include/$(gcc -print-multiarch)/bits/typesizes.ho alternativamente:/usr/include/$(dpkg-architecture -qDEB_HOST_MULTIARCH)/bits/typesizes.h
pabouk
1
Tener esos archivos glibc probablemente significaría que hay un compilador disponible. Por lo tanto, se puede #incluir <sys / types.h> para tener acceso a uid_t e imprimir el resultado ( printf ("uid_t:% d bytes (% d bits) \ n", sizeof (uid_t), sizeof (uid_t) * 8 ); )
tehnicaorg
3

Esa es una pregunta interesante. Me sorprendería si hubiera un método estándar y portátil para determinar esto.

No tengo un cuadro de Linux a mano, pero el idcomando en FreeBSD 8.0 vuelve a cero:

# id 4294967296
uid=0(root) gid=0(wheel) groups=0(wheel),5(operator)

Estoy seguro de que este es un comportamiento indefinido, pero apostaría a que la mayoría de las versiones idse ajustarán a cero con 65'536(si es un UID de 16 bits) 4'294'967'296o se producirán errores si supera el límite del sistema.

Geoff Fritz
fuente
3

En este enlace, se hace la pregunta y un respondedor usa un método de prueba y error para determinar que el sistema en cuestión usa un int largo firmado, dejando 31 bits para almacenar el valor, con un máximo de 2,147,483,647.

# groupadd -g 42949672950 testgrp
# more /etc/group
testgrp:*:2147483647:
Donald Byrd
fuente