Благодаря обновлению Win 10 октября 2018 года Windows стала второстепенной.DateTime .NET тоже сейчас? - PullRequest
2 голосов
/ 03 мая 2019

В 2012 году у SO возник вопрос: способны ли DateTime .NET распознавать високосные секунды. [1] Ответ был нет.

В документации все еще явно говорится, что это не так. [2]

Однако, Windows Server 2019 и обновление Windows 10 октября 2018 года сделали саму Windows осведомленной о скачке секунды. [3]

В связи с этим возникает вопрос: является ли .NET по сути своей второстепенной? Точнее говоря, можно ли сделать так, чтобы мои DateTime структуры были также осведомлены с помощью скачка секунды?

Изменить:

Из документа MS Word, озаглавленного «Квест: напишите второе прыжковое приложение для Windows» [4] (выделено мной):

Известные проблемы: Известно, что некоторые фреймворки неправильно рассчитывают время после високосной секунды происходит. Например, .NET Framework использует его Собственная внутренняя логика, чтобы определить, который час. Его логика не приходится високосные секунды. Таким образом, после високосной секунды вводится Операционная система выводит «System.DateTime.Now.ToString ()» быть впереди на одну секунду местного системного времени. (мы работаем с об этом .NET Framework Team.)

А из [5]:

Известно, что некоторые приложения неправильно рассчитывают время, предполагая, что всегда есть 60 секунд в минуту. С високосными секундами изменить это поведение, они будут неправильно записывать время в течение этого событие. Например (на момент написания):

.NET Framework использует свою внутреннюю логику, чтобы определить, который час и нет приходится високосные секунды. В результате PowerShell, который опирается на .NET Framework, не будет сообщать о 61-й секунде (номер 60) при использовании Get-Date

Просмотр событий: дата события будет неверной записано. Тем не менее, метаданные события будут правильно записывать систему время (показывает 60-ую секунду).

Примечание: эти команды работают над обновлением своего программного обеспечения для использования более подходящая математика при обработке високосных секунд .

Похоже, что в будущем .NET будет на секунду осведомлен. Поэтому я не буду публиковать это как решение.

[1] Способны ли методы .Net DateTime распознавать дополнительную секунду?

[2] https://docs.microsoft.com/en-us/dotnet/api/system.datetime.ticks?redirectedfrom=MSDN&view=netframework-4.8#System_DateTime_Ticks

[3] https://support.microsoft.com/en-us/help/2722715/support-for-the-leap-second

[4] https://aka.ms/Dev-LeapSecond (MS Word)

[5] https://aka.ms/ITPro-LeapSecond (MS Word)

Ответы [ 2 ]

2 голосов
/ 04 мая 2019

[H] Вот некоторые пояснения о том, как .NET (версия 4.7.2) работает в версии Windows, поддерживающей високосные секунды (т.е. выпуск Windows 10 RS5):

DateTime (DT) и DateTimeOffset (DTO) не изменяются в том, как он хранит единицы времени и как работают с такими единицами.Эти типы просто хранят тики, и тик составляет 100 наносекунд.При преобразовании между тиками и датой / временем (например, год, месяц, день, час, минута, секунда, миллисекунда) всегда принимается, что минута равна 60 секундам и не может быть 61 секунде.т. е. не учитываются никакие високосные секунды в тиках или в конверсии.

При вызове свойства Now для DT и DTO мы в конечном итоге вызовем Windows API (например, GetSystemTimeAsFileTime).GetSystemTimeAsFileTime имеет подсчитанные там дополнительные секунды.Таким образом, .NET делает дополнительный шаг при работе в системе с поддержкой високосных секунд, чтобы получить точное время, вызывая больше Windows API, который может сообщать системное время, чтобы гарантировать, что сообщаемое время .NET синхронизируется с системой..NET по-прежнему вызывает GetSystemTimeAsFileTime для получения более точного времени (с точностью до 100 наносекунд).

В случае, если Windows сообщит нам второе число 60 (что является високосной секундой), .NET примет это за последнюю секунду в этой минуте и использует ее в качестве секунды 59, чтобы она работала без проблем с DTи DTO, поскольку эти типы не знают о високосных секундах.

Если кто-то попытается создать DT или DTO с високосной секундой (60), .NET сначала проверит, вызвав Windows API, является ли это допустимой високосной секундой, а затем преобразует ее во второе число 59. Если этоне действует високосная секунда, тогда мы скинем исключение.

.NET не изменил, как работают DT и DTO ради совместимости приложений, так как мы знаем, что многие пользователи делают те же предположения в своем коде, что тики всегда имеют время, равное 60 секундам.А галочки в другой системе не могут означать разное время.Дайте мне знать, если у вас есть еще вопросы или вам нужно больше разъяснений

Источник: https://github.com/dotnet/dotnet-api-docs/issues/966#issuecomment-434440807

0 голосов
/ 05 мая 2019

Расширение принятого ответа путем предоставления более подробной информации, возможно, представляющей интерес.

Хотя UTC знает о случайном (и оспариваемом [1]) введении високосной секунды, структура DateTime .NET до Windows Server 2019 и обновления Windows 10 за октябрь 2018 - нет, [2] потому что сама Windows не был ни. [3] [4]

Но даже несмотря на то, что ядро ​​Window теперь знает о високосных секундах, приложения все равно не узнают, если не предпринимаются конкретные действия. [5] Платформа .NET сама по себе еще не поддерживает високосные секунды. [6]

Тем не менее, системы Windows обновляют свое время через NTP (используя UTC), что позволяет учитывать дополнительные секунды. [7] Это может привести к разрывам во времени в системах Windows, поскольку служба времени Windows, работающая в качестве NTP-клиента, может захотеть синхронизировать время системы сразу после следующей синхронизации через некоторое время после високосной секунды, что может привести к тому, что часы переместятся назад на 1 секунду. [8]

Конечно, возникновение отрицательного значения времени может (и в системах Linux [9] [10]) привело к нежелательному или непредсказуемому поведению, поэтому Windows не допустит этого.

При вызове методов DateTime.Now вызывается функция Windows 101 с поддержкой високосной функции GetSystemTimeAsFileTime. При получении високосной секунды 23:59:60 UTC она обрабатывается как второе вхождение в 23:59:59 UTC без повторного подсчета тиков 100 нс, но с сохранением всех 10 миллионов тиков этой секунды при максимально возможном количестве тиков. вместо этого, т. е. хронометраж фактически останавливается на секунду. [11]

Обратите внимание, что ввод 23:59:60 как времени в структуре DateTime приводит к тому, что .Net выполняет проверки в соответствии с уже имеющимися високосными секундами. Если это действительно так, оно будет принято (но преобразовано в 23:59:59). [11]


[1] Международная служба вращения Земли и системы отсчета (IERS); Всемирное координированное время (UTC) для сохранения «високосной секунды» - https://www.iers.org/SharedDocs/Publikationen/EN/IERS/Publications/messages/IERS_Message_No_282.html

[2] Microsoft; Свойство DateTime.Ticks - https://docs.microsoft.com/en-us/dotnet/api/system.datetime.ticks?redirectedfrom=MSDN&view=netframework-4.8#System_DateTime_Ticks

[3] Microsoft; Как служба Windows Time относится к високосной секунде - https://support.microsoft.com/en-us/help/909614/how-the-windows-time-service-treats-a-leap-second

[4] Microsoft; Поддержка високосной секунды - https://support.microsoft.com/en-us/help/2722715/support-for-the-leap-second

[5] Microsoft; Вторичная проверка для разработчиков - https://aka.ms/Dev-LeapSecond

[6] Microsoft; Вторичная проверка для ИТ-специалистов - https://aka.ms/ITPro-LeapSecond

[7] Д. Миллс (Университет штата Делавэр); Обработка второго прыжка - https://www.eecis.udel.edu/~mills/ntp/html/leap.html

[8] Microsoft; Как служба Windows Time относится к високосной секунде - https://support.microsoft.com/en-us/help/909614/how-the-windows-time-service-treats-a-leap-second

[9] Проводной; Ошибка «Прыжок второй» привела к хаосу в сети - https://www.wired.com/2012/07/leap-second-bug-wreaks-havoc-with-java-linux/

[10] /root.in; Ошибка второго прыжка в ядре Linux - https://www.slashroot.in/leap-second-bug-linux-kernel

[11] Github; Второе утверждение сбивает с толку - https://github.com/dotnet/dotnet-api-docs/issues/966#issuecomment-434440807

...