User Tools

Site Tools


doc:appunti:hardware:raspberrypi_thermostat

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revisionPrevious revision
Next revision
Previous revision
doc:appunti:hardware:raspberrypi_thermostat [2016/11/27 08:45] – [Printing a 3D Case] niccolodoc:appunti:hardware:raspberrypi_thermostat [2022/01/12 17:11] (current) – [Installing the old Adafruit LCD library] niccolo
Line 33: Line 33:
  
 {{.:raspberrypi:protherm-lcd_image.png?direct&120|The LCD display}} {{.:raspberrypi:protherm-lcd_image.png?direct&120|The LCD display}}
 +
 ===== Printing a 3D Case ===== ===== Printing a 3D Case =====
  
Line 53: Line 54:
 {{.:raspberrypi:protherm-lasercut-cover.jpg?direct&240 |The cover, made from laser cut plexiglass}} {{.:raspberrypi:protherm-lasercut-cover.jpg?direct&240 |The cover, made from laser cut plexiglass}}
 The **cover** is made with a piece of **plexiglass**, 2 mm thick. I tried a **lasercut** service, which cutted two covers from a single A4 sheet of plexiglass for 18.60 €. The service required a 2D project in DXF format, so I used the export function from OpenSCAD. The screw holes are too near to the edge, if you want to replicate this object I suggest to modify the ''screw_flange()'' module of the OpenSCAD project. The **cover** is made with a piece of **plexiglass**, 2 mm thick. I tried a **lasercut** service, which cutted two covers from a single A4 sheet of plexiglass for 18.60 €. The service required a 2D project in DXF format, so I used the export function from OpenSCAD. The screw holes are too near to the edge, if you want to replicate this object I suggest to modify the ''screw_flange()'' module of the OpenSCAD project.
 +
 ===== Wiring Diagram ===== ===== Wiring Diagram =====
  
Line 66: Line 68:
 **GPIO2** is not generally used for INPUT/OUTPUT because it has a strong PULL-UP resistor (1.8 kΩ) in addition to the software controlled one. Infact GPIO2 and GPIO3 are generally used for I2C communication, e.g. to add a realtime clock module. Neverthless we used it for the **push button** because it is near the three pins used by the temperature sensor, so we arranged a 5 pin **doughter board** which also accomodates two resistors and a capacitor. The 4.7 kΩ resistor is required by the DS18B20, the capacitor should help in debouncing (see notes about [[#Push Button|push button]]). To avoid problems remember to blacklist the **i2c-bcm2708** module as stated in [[#Kernel modules|this paragraph]]. **GPIO2** is not generally used for INPUT/OUTPUT because it has a strong PULL-UP resistor (1.8 kΩ) in addition to the software controlled one. Infact GPIO2 and GPIO3 are generally used for I2C communication, e.g. to add a realtime clock module. Neverthless we used it for the **push button** because it is near the three pins used by the temperature sensor, so we arranged a 5 pin **doughter board** which also accomodates two resistors and a capacitor. The 4.7 kΩ resistor is required by the DS18B20, the capacitor should help in debouncing (see notes about [[#Push Button|push button]]). To avoid problems remember to blacklist the **i2c-bcm2708** module as stated in [[#Kernel modules|this paragraph]].
  
-===== Unsolved Problems =====+===== The Custom Software ===== 
 + 
 +The ProTherm software I wrote is mantained into the **[[https://github.com/RigacciOrg/ProTherm|ProTherm GitHub repository]]**. It is a collection of software: 
 + 
 +  * **protherm**: a Python daemon which polls the temperature sensors and starts or stops the relay accordingly a program. It also updates the LCD contents. 
 +  * **protherm-tbot**: a Python daemon which acts as a [[https://telegram.org/|Telegram]] [[https://core.telegram.org/bots|Bot]]. It is used to control the thermostat from remote. 
 +  * Some **cron-job scripts** used to update an [[http://oss.oetiker.ch/rrdtool/index.en.html|RRA]] archive, which is needed to plot temperature graphs. 
 +  * There are also some **PHP scripts**, to give a simple web interface. 
 + 
 +Something is still missing in the repo, eventually I will upload everything in near future. 
 + 
 +===== The System Software ===== 
 + 
 +The overall system uses several pieces of software, most of them from the Raspbian distribution, others are installed via PIP packaging system. 
 + 
 +  * **Python**: protherm and protherm-tbot daemons are written in Python. 
 +  * **python-rpi.gpio** library used to access the GPIO lines for button and relay operations. 
 +  * **python-imaging** library used to create the LCD display image. 
 +  * **PIP** Python package installer, to get libraries which are not available as Debian packages. 
 +  * **Adafruit LCD library** Python library to drive the LCD via the SPI interface. 
 +  * **Telepot**: Python framework for Telegram Bot API. 
 +  * **rrdtool** used to store statistical data and to create nice graphs. 
 +  * **Nginx**: a lighweight web server. 
 +  * **php5-fpm** PHP server side language, for a simple web interface. 
 +  * **php5-gd** and **php5-imagick** PHP library for creating graphs. 
 +  * **SNMPD**: daemon for remote logging of thermostat data. 
 +  * **busybox-syslogd** syslog daemon replacement to log in RAM. 
 + 
 +===== Solved Problems =====
  
 === Fake (erratic) button keypresses === === Fake (erratic) button keypresses ===
  
-This problem is described in [[#Push Button]] paragraph. It seems solved simply by wiring far apart the GPIO wires and the boiler controlling cable, where 220 v A/C flows. +This problem is described in [[#Push Button]] paragraph. It seems solved simply by keeping the button wires as short as possible and by wiring far apart the GPIO wires and the boiler controlling cable, where 220 v A/C flows.
-===== The Software =====+
  
-The ProTherm software I wrote is mantained into the **[[https://github.com/RigacciOrg/ProTherm|ProTherm GitHub repository]]**. It is a collection of software:+=== LCD goes blank after some time ===
  
-  * A Python daemon which polls the temperature sensors and starts or stops the relay accordingly a program. It also updates the LCD contents. +This problem is described in [[#the_nokia_51103310_lcd|Nokia LCD]] paragraphThe Adafruit LCD library is not thread safeit is necessary to add a semaphore to avoid conflicting updates of LCD content.
-  * A Python daemon which acts as a [[https://telegram.org/|Telegram]] [[https://core.telegram.org/bots|Bot]]. It is used to control the thermostat from remote. +
-  * Some cron-job scripts used to update an [[http://oss.oetiker.ch/rrdtool/index.en.html|RRA]] archivewhich is needed to plot temperature graphs. +
-  * There are also some PHP scripts, to give a simple web interface.+
  
-Something is still missing in the repoeventually I will upload everything in near future.+===== Adafruit LCD library ===== 
 + 
 +To drive the PCD8544 LCD module we used the **Adafruit_Nokia_LCD** Python libraryversion 0.1.0 (this was in 2016, in 2021 we used version 0.2.0, which proved to work well and uses the same dependencies). It depends upon other Python libraries: 
 + 
 +  * **Adafruit_Nokia_LCD 0.1.0** 
 +  * **Adafruit_Python_GPIO 1.0.4** 
 +  * **Adafruit_PureIO 0.2.1 ** 
 +  * **RPi.GPIO 0.6.3**
  
 ==== System software and libraries ==== ==== System software and libraries ====
  
-Some packages are required from the standard Raspbian repository. Git is required to download the Adafruit LCD library and python-dev is required to compile it. The Adafruit library uses python-imaging to draw LCD images.+Some packages are installed from the standard Raspbian repository. Git is required to download the Adafruit LCD library, **python-dev**, **spidev** and **python-setuptools** are required to compile it. The Adafruit library uses **python-imaging** to draw LCD images.
  
 <code> <code>
-apt-get install python-rpi.gpio python-imaging python-dev git+apt-get install git python-dev python-imaging python-rpi.gpio python-setuptools spidev 
 +</code> 
 + 
 +We used version **0.2.1** of the **Adafruit-PureIO** library, more recent versions may have requirements which are not easy to satisfy on Debian 8 Jessie environment. 
 + 
 +<code> 
 +pip install --download /usr/local/src adafruit-pureio==0.2.1 
 +pip install /usr/local/src/Adafruit_PureIO-0.2.1-py2-none-any.whl
 </code> </code>
  
-Then download and install the **[[https://github.com/adafruit/Adafruit_Nokia_LCD|Adafruit Nokia LCD]]** for the Raspberry Pi:+Download and install the **[[https://github.com/adafruit/Adafruit_Nokia_LCD|Adafruit Nokia LCD]]** for the Raspberry Pi:
  
 <code> <code>
Line 101: Line 141:
 We also used **[[http://www.dafont.com/it/pf-tempesta-seven.font|PF Tempesta Seven]]**, a free TrueType font for the LCD display. TrueType files were saved into **''/usr/local/share/fonts/''** directory. We also used **[[http://www.dafont.com/it/pf-tempesta-seven.font|PF Tempesta Seven]]**, a free TrueType font for the LCD display. TrueType files were saved into **''/usr/local/share/fonts/''** directory.
  
-==== Disabling the serial console ====+==== The RPi.GPIO library is now a Debian package ====
  
-We decided to use GPIO 14 and 15 to drive the relays board, so we had to **prevent the use of the serial line** which uses that pins, otherwise there was an annoying flickering of the realys at boot time. Following the instructions of this [[http://raspberrypihobbyist.blogspot.it/2012/08/raspberry-pi-serial-port.html|post]], we changed **''/boot/cmdline.txt''** removing the options referring to **ttyAMA0**:+Before python-rpi.gpio became available as a Debian package, the library was installed using the alternative package manager PIP. 
 + 
 +So now **you don't need the following steps!** In the old days you ''apt-get install python-pip'' and then ''pip install RPi.GPIO''. PIP uses the [[https://pypi.python.org/pypi/|Python Package Index]] repository. The **[[https://pypi.python.org/pypi/RPi.GPIO/0.5.11|RPi.GPIO]]** package installed by PIP will go into ''/usr/local/lib/python2.7/dist-packages/''
 + 
 +===== Configuration Optimization ===== 
 + 
 +==== Disabling console and login shell from the serial line ==== 
 + 
 +We decided to use GPIO 14 and 15 to drive the relays board, so we had to **prevent the use of the serial line** by the kernel console output and by the login shell which is spawned on it by the system, otherwise there is an annoying flickering of the realys at boot time caused by data written on the serial line. 
 + 
 +We found some relevant info on this [[http://raspberrypihobbyist.blogspot.it/2012/08/raspberry-pi-serial-port.html|post]]
 + 
 +The **kernel console** on serial line is activated by some **''/boot/cmdline.txt''** options. Depending on Debian version (7 Wheezy or 8 Jessie) we have to remove:
  
 <file> <file>
 console=ttyAMA0,115200 kgdboc=ttyAMA0,115200 console=ttyAMA0,115200 kgdboc=ttyAMA0,115200
 </file> </file>
- 
-In Debian 8 Jessie we have the following part to remove: 
  
 <file> <file>
 console=serial0,115200 console=serial0,115200
 </file> </file>
 +
 +Also **removing the login shell** is different upon the version of the operating system.
  
 in **Debian 7 Wheezy** (running **sysvinit**) we commented out the line which spawns a login process from **''/etc/inittab''**: in **Debian 7 Wheezy** (running **sysvinit**) we commented out the line which spawns a login process from **''/etc/inittab''**:
Line 128: Line 180:
 </code> </code>
  
 +Do not use the **raspi-config** option to diasble the serial line, because it disables the serial device **''/dev/ttyAMA0''** entirely, adding an **enable_uart=0** option in **''/boot/config.txt''**.
 ==== Kernel modules ==== ==== Kernel modules ====
  
Line 138: Line 191:
 </file> </file>
  
 +Starting with Raspbian based upon Debian 8 Jessie, the I2C interface is disabled using the [[https://www.raspberrypi.org/documentation/configuration/device-tree.md|Device Tree]]. You can use the **raspi-config** tool, or just add to **''/boot/config.txt''** the following line:
  
-==== Obsolete: RPi.GPIO from PIP repository ==== +<file
- +dtparam=i2c_arm=off 
-**NOTICE: This step is no longer required!** The python-rpi.gpio package is entered into the Raspbian repository in recent days, before that we had to install the library from the alternative package manager PIP. First of all install the PIP package manager: +</file
- +==== Headless Configuration ====
-<code+
-apt-get install python-pip +
-</code> +
- +
-From PIP (which uses the [[https://pypi.python.org/pypi/|Python Package Index]] repository) we install the **[[https://pypi.python.org/pypi/RPi.GPIO/0.5.11|RPi.GPIO]]** package (PIP installed packages will go into ''/usr/local/lib/python2.7/dist-packages/''): +
- +
-<code> +
-pip install RPi.GPIO +
-</code> +
- +
-====Configuration Optimization ===== +
- +
-=== Headless Configuration ===+
  
 The Raspberry Pi is used without a monitor attached (headless configuration), so we can set the **minimum for GPU memory**, in **''/boot/config.txt''** we set: The Raspberry Pi is used without a monitor attached (headless configuration), so we can set the **minimum for GPU memory**, in **''/boot/config.txt''** we set:
Line 527: Line 568:
   * **bot.notifyOnMessage(handle)** => **bot.message_loop(handle)**   * **bot.notifyOnMessage(handle)** => **bot.message_loop(handle)**
   * **telepot.glance2(msg)** => **telepot.glance(msg)**   * **telepot.glance2(msg)** => **telepot.glance(msg)**
 +===== Installing on Raspberry Pi OS 2021-10-30 Bullseye =====
 +
 +The latest version of the ProTherm software should work on Debian 11 Bullseye, this means using **Python 3.9** both for the **ProTherm** package and for the **Telegram bot** daemon. Also the **Adafruit libraries** used to drive the LCD should run on Python 3.
 +
 +I copied the **Raspberry Pi OS Lite** image onto the SD card, before the first bootstrap I enabled remote ssh and WiFi by creating two files into the boot partitions:
 +
 +  * **/boot/ssh** - Just create an empty file.
 +  * **/boot/wpa_supplicant.conf** - Create a suitable file with your home ESSID and PSK.
 +
 +==== Debian Packages ====
 +
 +The extra Debian packages required by the ProTherm software are:
 +
 +  * **busybox-syslogd**
 +  * **ntp**
 +  * **snmpd**, **rrdtool**
 +  * **nginx**, **php-fpm**, **php-gd**, **php-imagick**
 +  * **python3-pip**
 +  * **python3-daemon**, **python3-lockfile**, **python3-netifaces**, **python3-ntplib**, **python3-pil**
 +  * **python3-python-telegram-bot**
 +  * **python3-rpi.gpio**
 +  * Required by the adafruit-circuitpython-pcd8544 library:
 +    * **python3-serial**
 +    * **python3-usb**
 +
 +==== Operating System Customization ====
 +
 +This is a brief check-out list of customizations required by the operating system. See above for more details.
 +
 +  * Disabled the **serial line console** from **/boot/cmdline.txt**, removing ''console=serial0,115200''.
 +  * Disabled **login on serial console** with ''systemctl disable serial-getty@ttyAMA0.service''.
 +  * Using **raspi-config**:
 +    * Interface Options => I2C => No (this will insert ''dtparam=i2c_arm=off'' into **/boot/config.txt**).
 +    * Interface Options => SPI => Yes (this will insert ''dtparam=spi=on'' into **/boot/config.txt**).
 +    * Localisation Options => Timezone => **Europe/Rome**
 +    * Localisation Options => Locale => **en_US.UTF-8**
 +  * Copied **PF Tempesta Seven** TTF fonts into ''/usr/local/share/fonts/''.
 +
 +=== CPU overload and kworker ===
 +
 +There is a problem with the old **Raspberry Pi model B** and the new Debian Bullseye, with **top** you can view several processes takin about 10% od the CPU during idle time:
 +
 +<code>
 +kworker/0:0+events_power_efficient
 +kworker/0:5-events
 +</code>
 +
 +I turned out that an idle eth0 causes that, just disable eth0 to restore the CPU to 0.3%:
 +
 +<code>
 +ifconfig eth0 down
 +</code>
 +
 +To leave the interface down at bootstrap you must configure the **dhcpcd** daemon, which is repsponsible for network configuration in Raspberry Pi OS. Edit the file **/etc/dhcpcd.conf** and add the following line:
 +
 +<file>
 +denyinterfaces eth0
 +</file>
 +
 +  * **[[https://forums.raspberrypi.com/viewtopic.php?t=317429|kworker processes consume CPU with the latest Raspberry Pi OS]]**
 +  * **[[https://forums.raspberrypi.com/viewtopic.php?t=293974#p1775552|kworker processes consume CPU with kernel 5.4.79]]**
 +
 +=== Nginx and PHP ===
 +
 +You can verify that the web server and PHP are running:
 +
 +<code>
 +systemctl status nginx.service
 +systemctl status php7.4-fpm.service
 +</code>
 +
 +Check also if the socket **/run/php/php7.4-fpm.sock** exists. Enable PHP by editing **/etc/nginx/sites-available/default**:
 +
 +<file>
 +    index index.php index.html index.htm index.nginx-debian.html;
 +
 +    location ~ \.php$ {
 +        include snippets/fastcgi-php.conf;
 +        # With php-fpm (or other unix sockets):
 +        fastcgi_pass unix:/run/php/php7.4-fpm.sock;
 +    }
 +</file>
 +
 +If you want Nginx to log to syslog instead that into a file, edit **/etc/nginx/nginx.conf**:
 +
 +<file>
 +    access_log syslog:server=unix:/dev/log;
 +    error_log syslog:server=unix:/dev/log;
 +</file>
 +
 +==== Installing the new Adafruit LCD library ====
 +
 +**WARNING**: Do not use this library on the old Raspberry Pi model B, it is too CPU intensive! Use the old one.
 +
 +**WARNING**: The new library is more CPU intensive than the old one. I opened an **[[https://github.com/adafruit/Adafruit_CircuitPython_PCD8544/issues/16|issue on GitHub]]**. So I decided to give-up with the new library and use the old one (see below for installation tips). Here you can see a CPU utilization graph, the first half is using the old library, the second half is using the new one:
 +
 +{{.:raspberrypi:protherm-cpu-percent.png?direct&640|CPU usage with different Adafruit Python libraries}}
 +
 +
 +Nowdays (2021), to operate the Nokia LCD, we should use the **[[https://github.com/adafruit/Adafruit_CircuitPython_PCD8544|Adafruit CircuitPython PCD8544]]** Python library. Detailed instructions can be found on the page **[[https://learn.adafruit.com/nokia-5110-3310-monochrome-lcd|Nokia 5110/3310 Monochrome LCD]]**. In the past (2016) it was used the **[[https://github.com/adafruit/Adafruit_Nokia_LCD|Adafruit Nokia LCD]]** library, which is now phased-out.
 +
 +To download the library **adafruit-circuitpython-pcd8544** and its dependencies without installing them:
 +
 +<code>
 +mkdir -p /usr/local/download/pcd8544
 +cd /usr/local/download/pcd8544
 +pip3 download adafruit-circuitpython-pcd8544
 +</code> 
 +
 +Some dependencies (libraries) exist as Debian Bullseye packages, but the version does not meet the requirements, so I uninstalled the Debian packages to install the PIP downloaded ones:
 +
 +<code>
 +dpkg --purge python3-sysv-ipc
 +dpkg --purge python3-ftdi1
 +</code>
 +
 +To avoid automatic dependency resolution (and related download/installation), I used the **%%--no-deps%%** option for each installation, checking manually the proper installation order (see the **Requires-Dist** entries into each packages METADATA):
 +
 +<code>
 +pip3 install --no-deps adafruit_circuitpython_pcd8544-1.2.6-py3-none-any.whl
 +pip3 install --no-deps Adafruit_Blinka-6.18.0-py3-none-any.whl
 +pip3 install --no-deps adafruit_circuitpython_busdevice-5.1.1-py3-none-any.whl
 +pip3 install --no-deps adafruit_circuitpython_framebuf-1.4.8-py3-none-any.whl
 +pip3 install --no-deps Adafruit_PlatformDetect-3.19.1-py3-none-any.whl
 +pip3 install --no-deps Adafruit_PureIO-1.1.9-py3-none-any.whl
 +pip3 install --no-deps pyftdi-0.53.3-py3-none-any.whl
 +pip3 install --no-deps rpi_ws281x-4.3.1-cp39-cp39-linux_armv6l.whl
 +pip3 install --no-deps sysv_ipc-1.1.0-cp39-cp39-linux_armv6l.whl
 +</code>
 +
 +We can test the library using the **[[https://github.com/adafruit/Adafruit_CircuitPython_PCD8544/blob/main/examples/pcd8544_simpletest.py|pcd8544_simpletest.py]]** example. Beware to modify the source code, because the **GPIOs** used to communicate to the SPI device do not fit our model **RASPBERRY_PI_B_REV2**. Here are the values needed by our hardware wiring:
 +
 +<code python>
 +dc = digitalio.DigitalInOut(board.D23)  # data/command
 +cs = digitalio.DigitalInOut(board.D8)  # Chip select
 +reset = digitalio.DigitalInOut(board.D24)  # reset
 +</code>
 +
 +Our LCD hardware works at best with **display.bias = 5** and **display.contrast = 57**.
 +
 +==== Installing the old Adafruit LCD library ====
 +
 +As reported above, the old and discontinued library **[[https://github.com/adafruit/Adafruit_Nokia_LCD|Adafruit Nokia LCD]]** is less CPU intensive than the new **Adafruit CircuitPython PCD8544**. Fortunately enough, the old library does run with Python 3, and I was able to use it on my old Raspberry Pi model B over the operating system derived from Debian 11 Bullseye. So the average CPU usage is **lower than 10%**, instead than **above 30%**!
 +
 +The library is not available from the **[[https://pypi.org/|PyPI]]** repository, so it must be downloaded from the GitHub repository. The library depends upon **Adafruit_GPIO**, which in turn requires **Adafruit_PureIO** and **spidev**. The two Adafruit libraries are available from PyPI, for **spidev** we installed the Debian packaged version.
 +
 +<code>
 +apt install python3-spidev
 +mkdir -p /usr/local/download/Adafruit-GPIO
 +cd /usr/local/download/Adafruit-GPIO
 +pip3 download Adafruit-GPIO
 +pip3 install Adafruit_PureIO-1.1.9-py3-none-any.whl
 +pip3 install Adafruit_GPIO-1.0.3-py3-none-any.whl
 +</code>
 +
 +We download the library from its **GitHub repository** and install it using **pip3**:
 +
 +<code>
 +cd /usr/local/download
 +git clone https://github.com/adafruit/Adafruit_Nokia_LCD.git
 +cd Adafruit_Nokia_LCD/
 +pip3 install .
 +</code>
 +
 +The dependencies tree is the following:
 +
 +  * Adafruit_Nokia_LCD
 +    * Adafruit_GPIO
 +      * Adafruit_PureIO
 +      * spidev
 +
 +==== Installing the Telegram Bot Python library ====
 +
 +FIXME: Into the Debian 11 Bullseye distribution there is the **python3-python-telegram-bot** package, which is a Telegram Bot Python library actively mantained, whereas the old Telepot library was abandoned. So we need to port our program to the new library and update these instruction.
 +
 +We wish to save locally the Telegram client library **telepot**, so we can redo the installation in the future, even if the library will not be longer available in the current version. So into a directory e.g. called **/usr/local/download/telepot/** we execute:
 +
 +<code>
 +pip3 download telepot
 +...
 +Successfully downloaded telepot aiohttp urllib3 typing-extensions
 +    attrs async-timeout multidict chardet yarl idna
 +</code>
 +
 +The **library** and its **dependencies** will be downloaded (not installed) in current directory. Now we install the dependencies from the Debian respository, if they are available (we prefer the Debian packaging over the Pip repository)
 +
 +<code>
 +apt-get install python3-aiohttp python3-urllib3 python3-chardet python3-idna
 +</code>
 +
 +Finally we install the telepot package from the local copy:
 +
 +<code>
 +pip3 install telepot-12.7-py3-none-any.whl
 +</code>
 +
 +==== Starting the protherm service at bootstrap ====
 +
 +Raspberry Pi OS based on **Debian 11 Bullseye** uses **systemd** to start services on bootstrap. The **protherm** service requires the **/dev/spidev0.0** device to be available on start, otherwise it starts with the LCD disabled. Unfortunately the timing at which the kernel enables the device cannot be predicted, so we have to take some precautions to let systemd wait for the spidev device before starting protherm.
 +
 +First of all we create an //udev// rule; the rule will force //systemd// to create a "systemd device" when the kernel device becomes available. The rule is created into a file named **/etc/udev/rules.d/protherm-spidev.rules**:
 +
 +<file>
 +# Inform systemd when the kernel device /dev/spidev0.0 becomes available.
 +# Systemd will create a systemd device named "dev-spidev0.0.device", which
 +# can be used to trigger the start of a service.
 +ACTION=="add", SUBSYSTEM=="spidev", KERNEL=="spidev0.0", TAG+="systemd"
 +</file>
 +
 +We use three keywords that must matched (because of the **%%==%%** sign) during an udev event. If the event is of type device **add**, the device belongs to the **spidev** subsystem and the kernel device name is **spidev0.0**, //udev// adds the string **systemd** to the **TAG** key associated to the device itself. 
 +
 +Systemd includes the **systemd-udevd.service** which will notice every device tagged witht the string **systemd** and dynamically creates a **device unit**. In this case the unit will be called **dev-spidev0.0.device**. You can ask systemd to list all the existing device units (because of the **%%--all%%** option, also the short name is listed):
 +
 +<code>
 +systemctl list-units --all --type=device
 +...
 +  dev-spidev0.0.device   loaded active   plugged /dev/spidev0.0
 +...
 +</code>
 +
 +If the systemd device does not exist, it probably means that the udev rule did not worked as expected. Thanks to this systemd device unit, we can write a protherm systemd unit that will start the service only after the device is instantiated by the kernel. The systemd unit will be **/etc/systemd/system/protherm.service**:
 +
 +<file>
 +[Unit]
 +Description=Programmable Thermostat Service
 +After=syslog.target
 +# Wait for spidev0.0 systemd device to be available.
 +After=dev-spidev0.0.device
 +Requires=dev-spidev0.0.device
 +
 +[Service]
 +Type=simple
 +WorkingDirectory=/tmp/
 +ExecStart=/usr/local/sbin/protherm -f
 +
 +[Install]
 +WantedBy=multi-user.target
 +</file>
 +
 ===== Web references ===== ===== Web references =====
  
doc/appunti/hardware/raspberrypi_thermostat.1480232705.txt.gz · Last modified: 2016/11/27 08:45 by niccolo