Решение 2038 года для встроенного Linux (32 бит)?
Как правильно обрабатывать времена в коде C для 32-битного встроенного Linux (ARMLinux), чтобы гарантировать, что код продолжает работать должным образом после 03:14:07 UTC 19 января 2038 г. (когда подписанный 32-битный time_t
Переполнение)? При условии time_t
подписан 32-битным в системе, которую я должен использовать, каковы альтернативы?
Значительное количество поисков в Google не обнаружило ничего полезного. Кажется, все предполагают, что к тому времени мы все будем использовать 64-битные ОС, но это явно не относится к встроенным системам.
В системе, которую я должен использовать, __kernel_time_t
определяется как long
, Что, вероятно, означает, что в течение 64-битного времени нет возможности ядра. Версия uClibc - 0.9.29.
Я не могу поверить, что я один с этой проблемой, и я не хочу изобретать велосипед.
3 ответа
Здесь нет серебряных пуль, хитростей или хитрых решений. Либо использовать операционную систему, которая имеет 64-битную time_t
или не использовать time_t
и любые средства ОС, которые зависят от него (включая файловые системы, таймеры, половину сети и т. д.) или планируют обновить программное обеспечение в течение следующих 20 лет.
Есть как минимум две unix-подобные системы с 64 битами time_t
на 32-битных машинах: OpenBSD и NetBSD. OpenBSD провела несколько бесед, объясняющих причины этого: http://www.openbsd.org/papers/eurobsdcon_2013_time_t/index.html
Подпрограммы преобразования времени "просто" должны будут использовать 2038-01-19:03:14:07Z в качестве основы для времени эпохи Unix, если отметка времени ниже определенного значения.
Т.е., если ваша система заработает в 2010-01-01, вы можете предположить, что никакая временная метка, которая не переполнена, находится ниже 1262300400 (что является временем эпохи unix для этой даты).
Если встречается более низкая временная метка, учтите, что она переполнилась, и используйте 2038-01-19:03:14:07Z в качестве базового времени. Сравнения также должны быть приняты во внимание.
Не чистое решение, но выполнимое с умеренными усилиями. Лучше переключиться на 64-битные метки времени (для которых абсолютно не нужна 64-битная система, кстати).
Я предполагаю, что ABI вашей встроенной системы определяет long
как 32 бита.
Там нет никаких требований для time_t
тип для подписи. Не могли бы вы сделать это unsigned long
и купить себе и своим потомкам дополнительные 68 лет спокойствия? Изменение этого потребовало бы перекомпиляции ядра, библиотеки C и всех программ и библиотек, которые используют time_t
... Не для слабонервных! Вы могли бы также определить это как long long
, но это изменит многие структурные макеты и будет еще более сложным.