Как установить часы реального времени (RTC) на Raspbian?

9

Я имею:

  • Raspberry Pi с малиной 2015-05-05
  • ds1307 подключен (это плата Adafruit, подтягивающие резисторы не установлены).

Как я:

  • настроить драйверы
  • убедиться, что Pi на самом деле использует время RTC при запуске?

На самом деле, я сделал первую часть, насколько я могу судить, но со второй не повезло. Большая часть информации, включая инструкции Adafruit, устарела из-за этого: https://www.raspberrypi.org/forums/viewtopic.php?t=97314

Итак, первый шаг: вы включаете I2c и драйверы в raspi-config, добавляете dtoverlay=i2c-rtc,ds1307в конец /boot/config.txt, и у вас есть драйверы, и hwclock, очевидно , работает на меня (не могу запустить i2cdetect, более об этом позже).

Теперь вам нужно удалить fake-hwclock и настроить его так, чтобы он действительно читал rtc при запуске. Я пытался следовать этому совету - который в значительной степени согласуется с другими вещами, которые я видел, и очень недавно - https://www.raspberrypi.org/forums/viewtopic.php?p=842661#p842661

(это для другого RTC, но я только следую второй части об удалении fake-hwclock и так далее).

Но не повезло, и на моем пи не существует «строк, которые нужно закомментировать». Мой пи приходит с 1 января 1970 г. 00:00 и hwclock -rговорит, что RTC поврежден. Даже если я не выключил питание после установки RTC и перезагрузки pi, похоже, он был поврежден при запуске.

Я также не смог запустить i2cdetect вообще. Он жалуется, что устройства / dev / i2c (что-то) не существуют - и действительно они не ...


Промежуточное обновление

Хорошо, я установил, что:

  • коррупция только из информации о времени / дате. Если я использую i2cset для заполнения nvram шаблоном, эта информация не изменяется при перезагрузке, но год переходит к 0x66
  • Если я удалю ,ds1307из строки dtoverlay=i2c-rtc,ds1307в config.txt, то система будет работать без повреждения RTC! Который поддерживает идею, что сам драйвер портит данные. Я посмотрел на код драйвера, и он проходит через время и меняет вещи, которые ему не нравятся (например, он меняет 12-часовой формат на 24-часовой). Итак, возможно, проблема в том, что драйвер установлен в то время, когда порт I2C фактически не готов к работе (возможно, из-за того, что часы не готовы?)
  • Если я сделаю это после запуска: sudo sh -c 'echo ds1307 0x68 > /sys/class/i2c-adapter/i2c-1/new_device'это приведет к загрузке драйвера rtc_ds1307 и появлению / dev / rtc0. И время все еще в порядке. И так, что может быть использовано в качестве основы для модификации сценариев инициализации
  • Еще одна забавная деталь: если я использую hwclock -sв скрипте сразу после записи в /sys/..../new_device, он не работает. Там должно быть sleep 0.5или что-то между.

Так что, похоже, у меня теперь есть система, которую можно выключить и запустить, и у нее будет правильное время - я скоро напишу это правильно.

greggo
источник
Коррупция может (или не может) быть связана с запуском ntpdate ... raspberrypi.org/forums/viewtopic.php?p=690492#p690492
greggo
Я добавил dtparam=i2c1=onв config.txt, как работал для micksulley в январе raspberrypi.org/forums/viewtopic.php?f=28&t=97639 - Перезагрузка. Все еще нет / dev / i2c *, все еще нет i2cdetect.
Грегго
@goldilocks - спасибо, важная часть головоломки. i2cdetect теперь работает и 1: 0x68 отображается как UU. Попробую другие вещи позже сегодня.
Грегго
1
примечание sudo invoke-rc.d hwclock.sh startничего не делает, оно выходит, потому что /run/udevсуществует. Но sudo invoke-rc.d hwclock.sh showчитает часы и sudo invoke-rc.d hwclock.sh stopкопирует системные часы на аппаратные часы.
Грегго

Ответы:

6

Вот как я это сделал.

Почти все здесь должно быть сделано как суперпользователь, так что используйте sudo bash или ставьте sudo перед всем (если это еще не показано).

Следующие основные шаги необходимы:

  • Позаботьтесь о том, чтобы драйверы i2c присутствовали, если еще нет;
  • есть дополнительный драйвер для rtc_ds1307
  • удалить поддельные часы Это подсистема, которая обычно используется, когда у вас нет сети для предоставления времени; он сохраняет системное время в файле, когда система выключается, и загружает его из того же файла при запуске. Так что время не подходит, но, по крайней мере, оно не возвращается к нулю (1 января 1970 г.) при каждом перезапуске. С установленным временем RTC время начнется достаточно корректно даже без сети.
  • организуйте, чтобы система считывала время из RTC при запуске.

Обратите внимание, что это изображение 2015-05-05-raspian-wheezy, на версии 2.0 «Pi 1» и RTC ds1307, подключенном к разъему расширения. Некоторая или большая часть этого должна применяться к другим ситуациям (но, вероятно, не к более старым распианам). Возможно, что проблема с повреждением RTC связана с драйвером ds1307, поэтому для других чипов это может быть проще. И эта проблема может быть исправлена ​​в будущем выпуске.

Также эти инструкции написаны для печатной платы модели 2, где используется шина I2C № 1. Если у вас есть печатная плата rev1 (у которой нет 8-контактного разъема «P5» рядом с P1), вы будете подключать RTC к шине I2C № 0. Поэтому всякий раз, когда вы видите /i2c-1/ниже, используйте /i2c-0/вместо этого.

Сначала запустите raspi-config, и в разделе «Дополнительные параметры» вы найдете параметр, позволяющий включить I2C и загрузку драйверов I2C. Включить их.

Теперь вы можете в принципе добавить строку внизу /boot/config.txt:, dtoverlay=i2c-rtc,ds1307которая загрузит диск ds1307; но, как выяснили некоторые, загрузка драйвера повредит содержимое часов, нанося ущерб их назначению. Я понятия не имею, почему, но я посмотрел на источник драйвера и обнаружил, что при запуске он читает часы, а затем, если находит вещи, которые ему не нравятся (например, 12-часовой формат вместо 24), он «исправляет» эти настройки с записью. Итак, я подозреваю, что может случиться так, что драйвер загружается слишком рано после запуска I2C, и, возможно, часы не настроены должным образом или что-то в этом роде, и связь нарушена. В любом случае, это не работает с имеющейся у меня конфигурацией, поэтому мы будем загружать драйвер позже.

На этом этапе вы можете перезагрузить компьютер, и с lsmod | grep i2cего помощью вы должны увидеть i2c_bcm2708загруженный драйвер (как это требуется в raspi-config).

Далее выполните эту команду:

echo ds1307 0x68 > /sys/class/i2c-adapter/i2c-1/new_device

или (если еще не суперпользователь):

sudo sh -c 'echo ds1307 0x68 > /sys/class/i2c-adapter/i2c-1/new_device'

( sudo echoне будет работать, так как >это то, что должно быть суперпользователем).

Это должно привести rtc_ds1307к загрузке драйвера и создаст устройство /dev/rtc0. Теперь вы должны быть в состоянии выполнить hwclock:

sudo hwclock -r

... Это показывает время с RTC. Это может привести к ошибке, потому что ваши часы еще не инициализированы должным образом. В любом случае мы сейчас его установим.

(1) убедитесь, что системные часы установлены с помощью date. Если вы находитесь в сети, это должно быть уже установлено; если нет, достаньте свой телефон или карманные часы и попробуйте что-то вроде

sudo date -s '18 nov 2015 22:20:24'

если вы правильно настроили системное время - соблюдая правильную настройку часового пояса - вы можете сделать

sudo hwclock -w

который копирует это в RTC.

И тогда hwclock -rдолжно сработать и показать время в RTC, и вы должны увидеть, что оно увеличивается, если вы прочитаете его более одного раза.

Wed 18 Nov 2015 22:48:41 EST  -0.181329 seconds
Wed 18 Nov 2015 22:48:53 EST  -0.013721 seconds

Примечание. Значение часов сохраняется относительно часового пояса UTC, но отображается по местному времени.

Следующий шаг: удалите fake-hwclock. Сначала отключите его и убедитесь, что hwclock.sh включен:

sudo update-rc.d hwclock.sh enable
sudo update-rc.d fake-hwclock remove

sudo apt-get remove fake-hwclock
sudo rm /etc/cron.hourly/fake-hwclock
sudo rm /etc/init.d/fake-hwclock

hwclock.shничего не делает при запуске - он обнаруживает присутствие udev и предполагает, что udev выполнил работу по запуску - но он делает что-то полезное, что приводит к записи системного времени в RTC при включении питания. Таким образом, когда вы подключаетесь к сети, время Pi будет синхронизироваться с сетью, и ваш дрейф RTC будет исправлен после выключения.

Осталось одно - нам нужно организовать чтение RTC при включении, чтобы было установлено системное время. В udev есть что-то, что пытается это сделать, но не удастся или будет обойдено, потому что драйвер RTC не загружен.

Способ, которым я настроил это, состоит в том, чтобы добавить эти четыре строки вверху /etc/rc.local(справа вверху, под комментариями):

echo 'setting up RTC'
echo ds1307 0x68 > /sys/class/i2c-adapter/i2c-1/new_device
sleep 0.5
hwclock -s

Это обеспечит загрузку драйвера и системное время, установленное с аппаратных часов, при каждом запуске системы. «Sleep 0.5» существует, потому что я обнаружил, что hwclockкоманда не будет работать без него - действие, инициируемое записью /sys/class/i2c-adapter/i2c-1/new_device(включая создание / dev / rtc0, существует), по-видимому, занимает немного времени (вероятно, чуть менее 0,5 с).

И это все. Я не очень доволен этим использованием /etc/rc.local- я бы предпочел, чтобы оно было настроено намного раньше, так как многое происходит до того, как rc.localбудет выполнено, и было бы гораздо лучше установить часы до того, как эти вещи запустятся. Но это работает для меня. Я обновлю этот ответ, если найду лучший способ.

Ссылки https://www.raspberrypi.org/forums/viewtopic.php?t=97314 https://www.raspberrypi.org/forums/viewtopic.php?p=842661 https://www.raspberrypi.org/forums /viewtopic.php?t=85683 https://www.raspberrypi.org/blog/upcoming-board-revision/

greggo
источник
У меня был RTC на заказ, и я читал сообщения RTC. Это один из немногих на этом сайте, который упоминает RTC. Мой RTC прибыл, я добавил dtoverlay=i2c-rtc,ds3231к config.txtпо последнему Raspbian (Jessie). Кажется, все работает хорошо. Никаких специальных настроек не требуется. По общему признанию, это другая микросхема (хотя технические характеристики выглядят очень похоже, кроме встроенного чипа Xtal и работает от 3,3 В). PS hwclockнужноsudo
Milliways
1
@Milliways /etc/rc.localработает от имени пользователя root. Я не помню, использует ли ds3231 тот же драйвер, и я все равно не знаю, что вызывает повреждение, просто это происходит при загрузке драйвера. Кроме того, как я упоминал в комментарии выше, я подозреваю, что некоторые из этих проблем могут быть вызваны условиями гонки во время инициализации (например, драйвер rtc может загружаться до правильной настройки i2c), и скорость работы может значительно повлиять SD-карта. Когда я впервые побежал Джесси, это было на карточке класса 4, и это было серьезно сломано; странные ошибки, и это игнорируется shutdown. Было хорошо в классе 10
Грегго
@Milliways, но да, я настоятельно рекомендую использовать ds3231, он работает на 3.3v, он намного точнее. Если это также спасает вас от этих неприятностей, это огромный бонус.
Грегго
2

Дополнительный ответ - Устранение неполадок с помощью инструментов I2C

Пытаясь заставить его работать, я нашел полезным использовать i2c-tools для просмотра RTC, и вы найдете много ссылок на это в других дискуссиях. Я добавил некоторую информацию к вопросу о том, что я нашел с ним; Я переместил это к этому ответу на случай, если это будет полезно.

Вам понадобится I2C (raspi-config) и загруженный модуль i2c-dev - вы можете принудительно сделать это с помощью sudo modprobe i2c-dev. i2c-devне требуется для работы RTC, но необходимо использовать i2c-tools.

Вы можете установить i2c-tools используя sudo apt-get install i2c-tools, если 'i2cdetect' отсутствует.

Если у вас есть Rev. 1 PCB: Изменение i2cdetect -y 1к i2cdetect -y 0, и изменить все , 1 0x68чтобы 0 0x68в i2cdumpкомандах.

Ты можешь сделать i2cdetect -y 1

     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f
00:          -- -- -- -- -- -- -- -- -- -- -- -- -- 
10: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- 
20: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- 
30: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- 
40: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- 
50: -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- 
60: -- -- -- -- -- -- -- -- 68 -- -- -- -- -- -- -- 
70: -- -- -- -- -- -- -- --

... '68' показывает, что устройство по адресу 0x68 ответило на адрес в шине I2C. Если вы загрузили драйвер rtc_ds1307, он будет отображаться как «UU», поскольку он зарезервирован драйвером.

Команда i2cdump -y -f -r 0-6 1 0x68 cможет быть использована для создания дампа первых 7 регистров DS1307 , которые содержат время ( «-f» необходима , только если установлен драйвер РОК, он отменяет резервирование).

Ниже описано, что происходит после включения питания, когда RTC поврежден из-за загрузки драйвера dtoverlay=i2c-rtc,ds307.

hwclock -r Первоначально сообщает, что установка часов повреждена, и, действительно, год равен «66».

pi@raspberrypi ~ $ sudo hwclock -r
hwclock: The Hardware Clock registers contain values that are either invalid (e.g. 50th day of month) or beyond the range we can handle (e.g. Year 2095).
pi@raspberrypi ~ $ sudo i2cdump -y -f -r 0-6 1 0x68 c
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f    0123456789abcdef
00: 50 04 00 05 01 01 66                               P?.???f         
pi@raspberrypi ~ $ sudo i2cdump -y -f -r 0-6 1 0x68 c
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f    0123456789abcdef
00: 52 04 00 05 01 01 66                               R?.???f         
pi@raspberrypi ~ $ sudo hwclock -w
pi@raspberrypi ~ $ sudo i2cdump -y -f -r 0-6 1 0x68 c
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f    0123456789abcdef
00: 35 09 01 03 17 11 15                               5??????         
pi@raspberrypi ~ $ sudo i2cdump -y -f -r 0-6 1 0x68 c
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f    0123456789abcdef
00: 37 09 01 03 17 11 15                               7??????         
pi@raspberrypi ~ $ sudo hwclock -r
Tue 17 Nov 2015 01:09:42 UTC  -0.384866 seconds
pi@raspberrypi ~ $ sudo i2cdump -y -f -r 0-6 1 0x68 c
     0  1  2  3  4  5  6  7  8  9  a  b  c  d  e  f    0123456789abcdef
00: 46 09 01 03 17 11 15                               F??????         

Семь чисел из i2cdump: [сек, мин, час дня, день, месяц, год], все в bcd, поэтому последний раз 17 ноября 2015, 01:09:46 UTC.

«Поврежденное» время - 1 января 66 года, и я видел других, которые сообщали о том же значении.

greggo
источник
2

У меня была похожая проблема на двух Raspberry Pi 2 Model B с Arch Linux, одна с TinyRTC (с ds1307) и другая с конденсатором RTC (с ds3231).

Запуск NTPD в качестве демона повредил дату RTC и установил ее на 2066/01/01.

#hwclock --debug
hwclock from util-linux 2.27
Using the /dev interface to the clock.
Last drift adjustment done at 1420070400 seconds after 1969
Last calibration done at 1420070400 seconds after 1969
Hardware clock is on UTC time
Assuming hardware clock is kept in UTC time.
Waiting for clock tick...
/dev/rtc does not have interrupt functions. Waiting in loop for time from /dev/rtc to change
...got clock tick
Time read from Hardware Clock: 2066/01/01 00:01:12
Invalid values in hardware clock: 2066/01/01 00:01:12
Time since last adjustment is -1420070400 seconds
Calculated Hardware Clock drift is 0.000000 seconds
hwclock: The Hardware Clock registers contain values that are either invalid (e.g. 50th day of month) or beyond the range we can handle (e.g. Year 2095).

Настройка

Я добавил в /boot/config.txt

dtparam=i2c_arm=on
dtoverlay=i2c-rtc,ds1307

или

dtparam=i2c_arm=on
dtoverlay=i2c-rtc,ds3231

Я добавил в /etc/modules-load.d/raspberrypi.conf

i2c-bcm2708
i2c-dev

Я отключил systemd-timesyncd

# timedatectl set-ntp false

Я установил NTP

# pacman -S ntp

Как это решило

Я обнаружил, что при запуске одного экземпляра NTPD перед запуском службы обновляется системное время и не устанавливается RTC, но если после этого я запускаю службу NTPD, она обновляет дату RTC, не повреждая ее.

Я думал, что есть проблема с разрешением. Группа по умолчанию - аудио.

# ls -l /dev/rtc0
crw-rw---- 1 root audio 254, 0 Jan  1  1970 /dev/rtc0

Я создал /etc/udev/40-rtc-permissions.rules, чтобы протестировать его

KERNEL=="rtc0", GROUP="ntp", MODE="0666"

но это не помогло, поэтому я удалил его.

Я также должен был обновить системную дату при запуске, поскольку это не сделано автоматически.

Я добавил в файл /etc/ntpd.service

ExecStartPre=-/usr/bin/hwclock -s
ExecStartPre=/usr/bin/ntpd -gq

и включил службу NTPD

# systemctl enable ntpd

и дата обновляется и не портится при загрузке.

Я не выяснил, что заставляет демон NTPD повредить RTC, если он был запущен первым, и был бы рад, если бы кто-то улучшил мое решение, но это работает для меня.

iomihai
источник
Спасибо за пост. Я боролся с этим на Raspberry Pi 3 весь день, и ваш пост наконец собрал последние недостающие фрагменты. Я использую Fedberry для ОС и пытаюсь настроить устройство в качестве сервера IPA (почему? Потому что бесплатный IPA на 10 ватт - вкусный, менее насыщенный!) Теперь у меня есть работающий сервер IPA, который может выдерживать сбои питания без ручного вмешательства. Я использую RT1 DS1307, и столкнулся с некоторыми из тех же проблем при устранении неполадок часов, которые вы определили. Хуже всего было повреждение памяти RTC при загрузке. Я не уверен, была ли уловка dtparam = i2c_arm = on