summaryrefslogtreecommitdiffstats
path: root/recipes-demo/agl-vss-helper
diff options
context:
space:
mode:
Diffstat (limited to 'recipes-demo/agl-vss-helper')
-rw-r--r--recipes-demo/agl-vss-helper/agl-vss-helper.bb35
-rw-r--r--recipes-demo/agl-vss-helper/files/agl-vss-helper.py96
-rw-r--r--recipes-demo/agl-vss-helper/files/agl-vss-helper.service11
-rw-r--r--recipes-demo/agl-vss-helper/files/agl-vss-helper.token1
-rw-r--r--recipes-demo/agl-vss-helper/files/agl-vss-helper.yaml108
5 files changed, 251 insertions, 0 deletions
diff --git a/recipes-demo/agl-vss-helper/agl-vss-helper.bb b/recipes-demo/agl-vss-helper/agl-vss-helper.bb
new file mode 100644
index 000000000..88e14511a
--- /dev/null
+++ b/recipes-demo/agl-vss-helper/agl-vss-helper.bb
@@ -0,0 +1,35 @@
+DESCRIPTION = "AGL VSS helper daemon"
+LICENSE = "MIT"
+LIC_FILES_CHKSUM = "file://${COMMON_LICENSE_DIR}/MIT;md5=0835ade698e0bcf8506ecda2f7b4f302"
+
+SRC_URI = "file://agl-vss-helper.py \
+ file://agl-vss-helper.yaml \
+ file://agl-vss-helper.token \
+ file://agl-vss-helper.service \
+"
+
+inherit systemd
+
+SYSTEMD_SERVICE:${PN} = "${BPN}.service"
+
+do_configure[noexec] = "1"
+do_compile[noexec] = "1"
+
+do_install() {
+ install -d ${D}${sbindir}
+ install -m 0755 ${WORKDIR}/${BPN}.py ${D}${sbindir}
+ install -d ${D}${sysconfdir}/xdg/AGL/${BPN}
+ install -m 0644 ${WORKDIR}/${BPN}.yaml ${D}${sysconfdir}/xdg/AGL/
+ install -m 0644 ${WORKDIR}/${BPN}.token ${D}${sysconfdir}/xdg/AGL/${BPN}/
+ install -D -m 0644 ${WORKDIR}/${BPN}.service ${D}${systemd_system_unitdir}/${BPN}.service
+}
+
+RDEPENDS:${PN} = " \
+ python3 \
+ python3-asyncio \
+ python3-systemd \
+ kuksa-databroker \
+ kuksa-databroker-agl \
+ kuksa-client \
+ kuksa-certificates-agl-ca \
+"
diff --git a/recipes-demo/agl-vss-helper/files/agl-vss-helper.py b/recipes-demo/agl-vss-helper/files/agl-vss-helper.py
new file mode 100644
index 000000000..73ac6b9df
--- /dev/null
+++ b/recipes-demo/agl-vss-helper/files/agl-vss-helper.py
@@ -0,0 +1,96 @@
+#!/usr/bin/env python3
+# Copyright (c) 2022 Aakash Solanki, tech2aks@gmail.com
+# Copyright (c) 2024 Scott Murray <scott.murray@konsulko.com>
+#
+# SPDX-License-Identifier: MIT
+
+import sys
+from pathlib import Path
+import yaml
+import asyncio
+import concurrent.futures
+from kuksa_client.grpc.aio import VSSClient
+from kuksa_client.grpc import Datapoint
+from systemd.daemon import notify
+
+# Defaults
+hostname = "localhost"
+port = 55555
+config_filename = "/etc/xdg/AGL/agl-vss-helper.yaml"
+token_filename = "/etc/xdg/AGL/agl-vss-helper/agl-vss-helper.token"
+ca_cert_filename = "/etc/kuksa-val/CA.pem"
+tls_server_name = "localhost"
+verbose = False
+
+async def main():
+ client = VSSClient(hostname,
+ port,
+ root_certificates=Path(ca_cert_filename),
+ tls_server_name=tls_server_name,
+ token=token,
+ ensure_startup_connection=True)
+ await client.connect()
+ print(f"Connected to KUKSA.val databroker at {hostname}:{port}")
+ if "initialize" in config and isinstance(config["initialize"], list):
+ for entry in config["initialize"]:
+ if "signal" in entry and "value" in entry:
+ if verbose:
+ print(f"Setting {entry['signal']} to {entry['value']}")
+ await client.set_current_values({ entry["signal"] : Datapoint(entry["value"]) })
+
+ notify("READY=1")
+
+ if "mock" in config and isinstance(config["mock"], list):
+ if len(config["mock"]) != 0:
+ print(f"Mocking actuators:")
+ for signal in config["mock"]:
+ print(f" {signal}")
+ async for updates in client.subscribe_target_values(config["mock"]):
+ for signal in updates:
+ if updates[signal] is not None:
+ if verbose:
+ print(f"Actuating {signal} to {updates[signal].value}")
+ await client.set_current_values({ signal : Datapoint(updates[signal].value) })
+
+
+#
+# Initialization
+#
+
+try:
+ config_file = open(config_filename, "r")
+ config = yaml.safe_load(config_file)
+except yaml.YAMLError as exc:
+ print(f"Could not parse configuration: ${exc}")
+except:
+ print(f"Could not read configuration")
+
+if "verbose" in config and isinstance(config["verbose"], bool):
+ verbose = config["verbose"]
+if "hostname" in config and isinstance(config["hostname"], string):
+ hostname = config["hostname"]
+if "port" in config and isinstance(config["port"], int):
+ port = config["port"]
+if "use-tls" in config and isinstance(config["use-tls"], bool):
+ use_tls = config["use-tls"]
+if "token-file" in config and isinstance(config["token-file"], string):
+ token_filename = config["token-file"]
+if "ca-certificate" in config and isinstance(config["ca-certificate"], string):
+ ca_cert_filename = config["ca-certificate"]
+
+if token_filename != "":
+ if verbose:
+ print(f"Reading authorization token {token_filename}")
+ token_file = open(token_filename, "r")
+ token = token_file.read()
+else:
+ token = ""
+
+print("Starting")
+try:
+ asyncio.run(main())
+except KeyboardInterrupt:
+ print("Exiting")
+
+notify("STOPPING=1")
+sys.exit(0)
diff --git a/recipes-demo/agl-vss-helper/files/agl-vss-helper.service b/recipes-demo/agl-vss-helper/files/agl-vss-helper.service
new file mode 100644
index 000000000..0199b6cde
--- /dev/null
+++ b/recipes-demo/agl-vss-helper/files/agl-vss-helper.service
@@ -0,0 +1,11 @@
+[Unit]
+Wants=network.target kuksa-databroker.service
+After=network.target kuksa-databroker.service
+
+[Service]
+Type=notify
+ExecStart=/usr/bin/python3 -u /usr/sbin/agl-vss-helper.py
+Restart=on-failure
+
+[Install]
+WantedBy=multi-user.target
diff --git a/recipes-demo/agl-vss-helper/files/agl-vss-helper.token b/recipes-demo/agl-vss-helper/files/agl-vss-helper.token
new file mode 100644
index 000000000..110d3c413
--- /dev/null
+++ b/recipes-demo/agl-vss-helper/files/agl-vss-helper.token
@@ -0,0 +1 @@
+eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJzdWIiOiJsb2NhbCBkZXYiLCJpc3MiOiJjcmVhdGVUb2tlbi5weSIsImF1ZCI6WyJrdWtzYS52YWwiXSwiaWF0IjoxNTE2MjM5MDIyLCJleHAiOjE3NjcyMjU1OTksInNjb3BlIjoiYWN0dWF0ZSBwcm92aWRlIn0.x-bUZwDCC663wGYrWCYjQZwQWhN1CMuKgxuIN5dUF_izwMutiqF6Xc-tnXgZa93BbT3I74WOMk4awKHBUSTWekGs3-qF6gajorbat6n5180TOqvNu4CXuIPZN5zpngf4id3smMkKOT699tPnSEbmlkj4vk-mIjeOAU-FcYA-VbkKBTsjvfFgKa2OdB5h9uZARBg5Rx7uBN3JsH1I6j9zoLid184Ewa6bhU2qniFt5iPsGJniNsKsRrrndN1KzthO13My44s56yvwSHIOrgDGbXdja_eLuOVOq9pHCjCtorPScgEuUUE4aldIuML-_j397taNP9Y3VZYVvofEK7AuiePTbzwxrZ1RAjK74h1-4ued3A2gUTjr5BsRlc9b7eLZzxLJkrqdfGAzBh_rtrB7p32TbvpjeFP30NW6bB9JS43XACUUm_S_RcyI7BLuUdnFyQDQr6l6sRz9XayYXceilHdCxbAVN0HVnBeui5Bb0mUZYIRZeY8k6zcssmokANTD8ZviDMpKlOU3t5AlXJ0nLkgyMhV9IUTwPUv6F8BTPc-CquJCUNbTyo4ywTSoODWbm3PmQ3Y46gWF06xqnB4wehLscBdVk3iAihQp3tckGhMnx5PI_Oy7utIncr4pRCMos63TnBkfrl7d43cHQTuK0kO76EWtv4ODEHgLvEAv4HA \ No newline at end of file
diff --git a/recipes-demo/agl-vss-helper/files/agl-vss-helper.yaml b/recipes-demo/agl-vss-helper/files/agl-vss-helper.yaml
new file mode 100644
index 000000000..21b5ce9a0
--- /dev/null
+++ b/recipes-demo/agl-vss-helper/files/agl-vss-helper.yaml
@@ -0,0 +1,108 @@
+initialize:
+- signal: Vehicle.Speed
+ value: 0
+- signal: Vehicle.Powertrain.CombustionEngine.Speed
+ value: 600
+- signal: Vehicle.Powertrain.FuelSystem.RelativeLevel
+ value: 70
+- signal: Vehicle.Powertrain.FuelSystem.Range
+ value: 300000
+- signal: Vehicle.Powertrain.CombustionEngine.ECT
+ value: 70
+- signal: Vehicle.Body.Lights.DirectionIndicator.Left.IsSignaling
+ value: false
+- signal: Vehicle.Body.Lights.DirectionIndicator.Right.IsSignaling
+ value: false
+- signal: Vehicle.Powertrain.Transmission.SelectedGear
+ value: 127
+- signal: Vehicle.Body.Lights.Beam.Low.IsOn
+ value: true
+- signal: Vehicle.Body.Lights.Beam.High.IsOn
+ value: false
+- signal: Vehicle.Body.Lights.Parking.IsOn
+ value: false
+- signal: Vehicle.Body.Lights.Hazard.IsSignaling
+ value: false
+- signal: Vehicle.TraveledDistance
+ value: 1763
+- signal: Vehicle.TraveledDistanceSinceStart
+ value: 0
+- signal: Vehicle.Body.Trunk.Rear.IsLocked
+ value: true
+- signal: Vehicle.Body.Trunk.Rear.IsOpen
+ value: false
+- signal: Vehicle.Powertrain.Transmission.PerformanceMode
+ value: "NORMAL"
+- signal: Vehicle.Cabin.HVAC.AmbientAirTemperature
+ value: 22
+- signal: Vehicle.Exterior.AirTemperature
+ value: 24
+- signal: Vehicle.Chassis.Axle.Row1.Wheel.Left.Tire.Pressure
+ value: 220
+- signal: Vehicle.Chassis.Axle.Row1.Wheel.Right.Tire.Pressure
+ value: 216
+- signal: Vehicle.Chassis.Axle.Row2.Wheel.Left.Tire.Pressure
+ value: 217
+- signal: Vehicle.Chassis.Axle.Row2.Wheel.Right.Tire.Pressure
+ value: 222
+- signal: Vehicle.OBD.Status.IsMILOn
+ value: false
+- signal: Vehicle.Cabin.Infotainment.HMI.DistanceUnit
+ value: "KILOMETERS"
+- signal: Vehicle.Cabin.Infotainment.HMI.TemperatureUnit
+ value: "C"
+- signal: Vehicle.Cabin.Infotainment.HMI.TirePressureUnit
+ value: "KPA"
+- signal: Vehicle.ADAS.CruiseControl.IsEnabled
+ value: false
+- signal: Vehicle.ADAS.CruiseControl.IsActive
+ value: false
+- signal: Vehicle.ADAS.CruiseControl.SpeedSet
+ value: false
+- signal: Vehicle.ADAS.CruiseControl.IsError
+ value: false
+- signal: Vehicle.Powertrain.TractionBattery.Charging.IsCharging
+ value: false
+- signal: Vehicle.Powertrain.TractionBattery.Charging.IsChargingCableConnected
+ value: false
+- signal: Vehicle.Powertrain.TractionBattery.Charging.IsChargingCableLocked
+ value: false
+- signal: Vehicle.Powertrain.TractionBattery.Charging.IsDischarging
+ value: false
+#- signal: Vehicle.CurrentLocation.Latitude
+# value:
+#- signal: Vehicle.CurrentLocation.Longitude
+# value:
+#
+# AGL specific signals
+#
+- signal: Vehicle.Cabin.Infotainment.Navigation.State
+ value: "STOPPED"
+- signal: Vehicle.Cabin.Infotainment.Navigation.ElapsedDistance
+ value: 0.0
+#- signal: Vehicle.Cabin.Infotainment.Navigation.DestinationSet.Latitude
+# value:
+#- signal: Vehicle.Cabin.Infotainment.Navigation.DestinationSet.Longitude
+# value:
+- signal: Vehicle.Cabin.SteeringWheel.Switches.Info
+ value: false
+- signal: Vehicle.Cabin.SteeringWheel.Switches.VolumeUp
+ value: false
+- signal: Vehicle.Cabin.SteeringWheel.Switches.VolumeDown
+ value: false
+- signal: Vehicle.Cabin.SteeringWheel.Switches.VolumeMute
+ value: false
+- signal: Vehicle.Cabin.SteeringWheel.Switches.Next
+ value: false
+- signal: Vehicle.Cabin.SteeringWheel.Switches.Previous
+ value: false
+- signal: Vehicle.Cabin.SteeringWheel.Switches.Mode
+ value: false
+
+mock:
+- Vehicle.Cabin.Infotainment.HMI.DistanceUnit
+- Vehicle.Cabin.Infotainment.HMI.TemperatureUnit
+- Vehicle.Cabin.Infotainment.HMI.TirePressureUnit
+- Vehicle.ADAS.CruiseControl.IsEnabled
+- Vehicle.ADAS.CruiseControl.IsActive
+- Vehicle.ADAS.CruiseControl.SpeedSet