Commit 0d3332a6 authored by Léo-Paul Géneau's avatar Léo-Paul Géneau 👾

software/tsn-demo: add TSN demo SR

Add Software Release to provide scripts to run Time-Sensitive Networking
motor demo.
parent 38aebe2f
tsn-demo
========
Software release to provide required scripts to run `Time-Sensitive Networking`_ motor demo.
This is an automation of `this demo`_.
setup
=====
To allow SlapOS to setup gpio pins, you need to add the following configuration
in ``/etc/udev/rules.d/99-gpio.rules`` :
.. code-block:: shell
SUBSYSTEM=="gpio", KERNEL=="gpiochip*", ACTION=="add", PROGRAM="/bin/sh -c 'chown root:slapsoft /sys/class/gpio/export /sys/class/gpio/unexport ; chmod 220 /sys/class/gpio/export /sys/class/gpio/unexport'"
SUBSYSTEM=="gpio", KERNEL=="gpio*", ACTION=="add", PROGRAM="/bin/sh -c 'chown root:slapsoft /sys%p/direction /sys%p/value ; chmod 660 /sys%p/direction /sys%p/value'"
tutorial
========
`A tutorial`_ describing how to use this SR is available.
.. _Time-Sensitive Networking: https://1.ieee802.org/tsn/
.. _this demo: https://www.osie-project.eu/P-OSIE.Blog.TSN.Motor.Control.Demo
.. _A tutorial: https://www.osie-project.eu/P-OSIE.Blog.TSN.Motor.Control.Demo.Software.Release
\ No newline at end of file
# THIS IS NOT A BUILDOUT FILE, despite purposedly using a compatible syntax.
# The only allowed lines here are (regexes):
# - "^#" comments, copied verbatim
# - "^[" section beginings, copied verbatim
# - lines containing an "=" sign which must fit in the following categorie.
# - "^\s*filename\s*=\s*path\s*$" where "path" is relative to this file
# Copied verbatim.
# - "^\s*hashtype\s*=.*" where "hashtype" is one of the values supported
# by the re-generation script.
# Re-generated.
# - other lines are copied verbatim
# Substitution (${...:...}), extension ([buildout] extends = ...) and
# section inheritance (< = ...) are NOT supported (but you should really
# not need these here).
[template]
filename = instance.cfg
md5sum = cad8d9c7c17808f23eee936f149183a9
[template-tsn-client]
filename = instance-tsn-client.cfg
md5sum = 829e50492ef9adb0037b82c814f76afd
[template-tsn-server]
filename = instance-tsn-server.cfg
md5sum = 5ce17649f54faf2a9e2a05774d643041
{% set hardware_timestamps = slapparameter_dict.get('hardware-timestamps', 'n') -%}
{% set interface_ip_string_list = [] -%}
{% set interface_list = slapparameter_dict.get('interface-list', '').split() -%}
{% set ip_list = slapparameter_dict.get('ip-list', '').split() -%}
{% set part_list = [] -%}
{% set server_guid_list = slapparameter_dict.get('server-guid-list', '').split() -%}
{% set server_interface_list = slapparameter_dict.get('server-interface-list', '').split() -%}
{% set server_list = [] -%}
{% set script_list = [] -%}
[directory]
recipe = slapos.cookbook:mkdirectory
etc = $${buildout:directory}/etc
scripts = $${:etc}/tsn
run = $${:etc}/run
[tsn-script-template]
recipe = slapos.recipe.template:jinja2
rendered= $${directory:scripts}/$${:_buildout_section_name_}
mode = 755
{% for server_nb, server_guid in enumerate(server_guid_list) -%}
{% set request_tsn_server_section_title = 'request-tsn-server' ~ server_nb -%}
{% do interface_ip_string_list.extend([interface_list[server_nb], '$${' ~ request_tsn_server_section_title ~ ':connection-ip}']) -%}
{% do part_list.append(request_tsn_server_section_title) -%}
[{{ request_tsn_server_section_title }}]
<= slap-connection
recipe = slapos.cookbook:request
name = TSNMeasurementsServer{{ server_nb }}
software-url = $${:software-release-url}
software-type = tsn-server
return = ip
sla-computer_guid = {{ server_guid }}
config-ip = {{ ip_list[server_nb] }}
{% if 'gpio-port' in slapparameter_dict -%}
config-gpio-port = {{ slapparameter_dict.get('gpio-port') }}
{% endif -%}
{% if server_nb < len(server_interface_list) -%}
config-interface = {{ server_interface_list[server_nb] }}
{% endif %}
{% if hardware_timestamps == 'y' -%}
{% set phc2sys_launcher_section_title = 'phc2sys-launcher-' ~ interface_list[server_nb] -%}
{% do part_list.append(phc2sys_launcher_section_title) -%}
{% do script_list.append(phc2sys_launcher_section_title) -%}
[{{ phc2sys_launcher_section_title }}]
<= tsn-script-template
template= inline:
#!/bin/sh
${linuxptp:location}/sbin/pmc -u -b 0 -i {{ interface_list[server_nb] }} "SET GRANDMASTER_SETTINGS_NP clockClass 248 clockAccuracy 0xfe offsetScaledLogVariance 0xffff currentUtcOffset 37 leap61 0 leap59 0 currentUtcOffsetValid 1 ptpTimescale 1 timeTraceable 1 frequencyTraceable 0 timeSource 0xa0"
exec {{ chrt }} -f 95 ${linuxptp:location}/sbin/phc2sys -s CLOCK_REALTIME -c {{ interface_list[server_nb] }} --step_threshold=1 -m -w
{% endif %}
{% set ptp4l_launcher_section_title = 'ptp4l-launcher-' ~ interface_list[server_nb] -%}
{% do part_list.append(ptp4l_launcher_section_title) -%}
{% do script_list.append(ptp4l_launcher_section_title) -%}
[{{ ptp4l_launcher_section_title }}]
<= tsn-script-template
template= inline:
#!/bin/sh
exec {{ chrt }} -f 97 ${linuxptp:location}/sbin/ptp4l {{ '-H' if hardware_timestamps=='y' else '-S' }} -i {{ interface_list[server_nb] }} --step_threshold=1 -m
{% endfor -%}
[tsn-script]
<= tsn-script-template
template= inline:
#!/bin/sh
exec ${tsn-rt-measures:location}/bin/master -a1 -p97 -t4000 {{ interface_ip_string_list | join(' ') }}
[buildout]
parts =
{% for part in part_list -%}
{{ ' ' ~ part }}
{% endfor %}
tsn-script
publish-connection-information
[publish-connection-information]
recipe = slapos.cookbook:publish
{% for script in script_list -%}
{{ script }} = {{ '$${' ~ script ~ ':rendered}' }}
{% endfor -%}
tsn-script = $${tsn-script:rendered}
{% set interface = slapparameter_dict.get('interface', 'eth0') -%}
{% set ip = slapparameter_dict.get('ip', '') -%}
{% set gpio_direction_pin = slapparameter_dict.get('gpio-direction-pin', '192') -%}
{% set gpio_pulse_pin = slapparameter_dict.get('gpio-pulse-pin', '193') -%}
[buildout]
parts =
gpio_setup
ptp4l-launcher-{{ interface }}
tsn-script
publish-connection-information
[directory]
recipe = slapos.cookbook:mkdirectory
etc = $${buildout:directory}/etc
scripts = $${:etc}/tsn
[gpio_setup]
recipe = slapos.recipe.build
gpio-direction-pin = {{ gpio_direction_pin }}
gpio-pulse-pin = {{ gpio_pulse_pin }}
init =
import os
def setup_gpio(pin_number):
gpio_dir = "/sys/class/gpio/gpio" + pin_number
if not os.path.exists(gpio_dir):
with open("/sys/class/gpio/export", "w") as fd:
fd.write(pin_number)
with open(os.path.join(gpio_dir, "direction"), "w") as fd:
fd.write("out")
with open(os.path.join(gpio_dir, "value"), "w") as fd:
fd.write("0")
setup_gpio(options["gpio-direction-pin"])
setup_gpio(options["gpio-pulse-pin"])
[tsn-script-template]
recipe = slapos.recipe.template:jinja2
rendered= $${directory:scripts}/$${:_buildout_section_name_}
mode = 755
[ptp4l-launcher-{{ interface }}]
<= tsn-script-template
template= inline:
#!/bin/sh
exec {{ chrt }} -f 97 ${linuxptp:location}/sbin/ptp4l -s -S -i {{ interface }} --step_threshold=1 -m
[tsn-script]
<= tsn-script-template
template= inline:
#!/bin/sh
exec ${tsn-rt-measures:location}/bin/slave -f {{ interface }} -a1 -p98 -d {{ gpio_direction_pin }} -u {{ gpio_pulse_pin }}
[publish-connection-information]
recipe = slapos.cookbook:publish
ip = {{ ip }}
ptp4l-launcher-{{ interface }} = $${ptp4l-launcher-{{ interface }}:rendered}
tsn-script = $${tsn-script:rendered}
[buildout]
parts =
switch-softwaretype
eggs-directory = ${buildout:eggs-directory}
develop-eggs-directory = ${buildout:develop-eggs-directory}
offline = true
[switch-softwaretype]
recipe = slapos.cookbook:switch-softwaretype
default = tsn-client-dynamic-template:rendered
tsn-server = tsn-server-dynamic-template:rendered
RootSoftwareInstance = $${:default}
[dynamic-template-base]
recipe = slapos.recipe.template:jinja2
rendered = $${buildout:directory}/$${:filename}
context =
raw chrt ${util-linux:location}/bin/chrt
key slapparameter_dict slap-configuration:configuration
key ipv4 slap-configuration:ipv4-random
[tsn-client-dynamic-template]
<= dynamic-template-base
extensions = jinja2.ext.do
template = ${template-tsn-client:output}
filename = instance-tsn-client.cfg
[tsn-server-dynamic-template]
<= dynamic-template-base
template = ${template-tsn-server:output}
filename = instance-tsn-server.cfg
[slap-configuration]
recipe = slapos.cookbook:slapconfiguration
computer = $${slap-connection:computer-id}
partition = $${slap-connection:partition-id}
url = $${slap-connection:server-url}
key = $${slap-connection:key-file}
cert = $${slap-connection:cert-file}
[buildout]
extends =
buildout.hash.cfg
../../stack/slapos.cfg
../../component/linuxptp/buildout.cfg
../../component/tsn-rt-measures/buildout.cfg
../../component/util-linux/buildout.cfg
parts =
slapos-cookbook
eggs
util-linux
template
# eggs for instance-rsn-client.cfg
[eggs]
recipe = zc.recipe.egg
eggs =
plone.recipe.command
[template-base]
recipe = slapos.recipe.template
url = ${:_profile_base_location_}/${:filename}
mode = 0644
[template]
< = template-base
output = ${buildout:directory}/template.cfg
[template-tsn-client]
< = template-base
output = ${buildout:directory}/template-tsn-client.cfg
[template-tsn-server]
< = template-base
output = ${buildout:directory}/template-tsn-server.cfg
[util-linux]
configure-options -=
--disable-schedutils
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment