c - que - ¿Hay alguna manera de obtener time_t de 64 bits en el programa de 32 bits en Linux
instalar paquetes i386 en arquitectura 64 bits ubuntu (3)
Aparentemente, no, no es posible. Para empezar, solo hay una función de time()
en Linux, sin time32()
o time64()
.
Después de buscar por un tiempo, puedo ver que no es culpa de libc, pero el culpable es en realidad el kernel.
Para que libc busque la hora actual, necesita ejecutar una llamada al sistema para ello: ( Fuente )
time_t time (t) time_t *t;
{
// ...
INTERNAL_SYSCALL_DECL (err);
time_t res = INTERNAL_SYSCALL (time, err, 1, NULL);
// ...
return res;
}
La llamada al sistema se define como: ( Fuente )
SYSCALL_DEFINE1(time, time_t __user *, tloc)
{
time_t i = get_seconds();
// ...
return i;
}
La función get_seconds()
devuelve unsigned long
, así: ( Fuente )
unsigned long get_seconds(void)
{
struct timekeeper *tk = &timekeeper;
return tk->xtime_sec;
}
Y timekeeper.xtime_sec
es en realidad de 64 bits: ( Fuente )
struct timekeeper {
// ...
/* Current CLOCK_REALTIME time in seconds */
u64 xtime_sec;
// ...
}
Ahora, si conoce su C, sabe que el tamaño de la unsigned long
depende de la implementación. En mi máquina de 64 bits aquí, es de 64 bits; pero en mi máquina de 32 bits aquí, es de 32 bits. Posiblemente podría ser de 64 bits en alguna implementación de 32 bits, pero no hay garantía.
Por otro lado, u64
siempre es de 64 bits, por lo que en la base, el kernel realiza un seguimiento de la hora en un tipo de 64 bits. Por qué procede a devolver esto como un unsigned long
, que no está garantizado para ser de 64 bits de largo, está más allá de mí.
Al final, incluso si libc obligaría a time_t
a mantener un valor de 64 bits, no cambiaría nada.
Podría vincular su aplicación profundamente con el kernel, pero no creo que valga la pena.
En Windows puedo llamar:
_time32(__time32_t); // to get 32bit time_t
_time64(__time64_t); // to get 64bit time_t
(ambos en programas de 32 y 64 bits)
¿Hay alguna forma de hacer esto en Linux (compilando con GCC)?
No se incluye la función time64()/time32()
en las bibliotecas estándar.
No time32_t/time64_t
define se contemplan en los encabezados estándar.
time_t
se define en time.h
como typedef __time_t time_t
;
Después de una larga cadena de redefiniciones, descubrirá que __time_t
se define como 32 bits en máquinas de 32 bits y máquinas de 64 bits en 64 bits.
Si realmente necesitas esto, ¿por qué no haces tu propio?
typedef int32_t my_time32;
typedef int64_t my_time64;
my_time32 get_mytime32() {
if (sizeof(time_t) == sizeof(my_time32))
return time(NULL);
else {
/* Check for overflow etc. here... */
return (my_time32)(time(NULL));
}
}
Y de manera similar para get_mytime64()
.
Si no le importa el desbordamiento, un return time(NULL);
simple return time(NULL);
funcionaría para ambas funciones gracias a las conversiones numéricas implícitas de C.