Accessing /sys/class/leds/xxx from Toradex Python Container

I am using an LP5521 led driver with a kernel driver to indicate status. I have written a python script that I’ve tested running on the system with root privileges without a container and it works well.

#!python

import os
from enum import Enum

BASE_URL = "/sys/class/leds/lp5521_pri:channel0/device/"

class LED_CHANNEL(int, Enum):
    RED = 1
    GREEN = 2
    BLUE = 3

class ENGINE_MODE(str, Enum):
    RUN = "run"
    LOAD = "load"
    DISABLED = "disabled"

def write_sysfs(filepath:str, payload:str):
    if os.path.exists(filepath):
        try:
            with open(filepath, 'w') as fl:
                fl.write(payload)
        except IOError as e:
            raise RuntimeError(e)
    else:
        raise RuntimeError(f"No driver found at {filepath}, check if module is properly loaded")

def set_sequence(channel:LED_CHANNEL, sequence:str):
    engine_mode_str = f"engine{channel}_mode"
    engine_load_str = f"engine{channel}_load"
    write_sysfs(os.path.join(BASE_URL, engine_mode_str), ENGINE_MODE.LOAD)
    write_sysfs(os.path.join(BASE_URL, engine_load_str), sequence)

def run_sequence(channel:LED_CHANNEL):
    engine_mode_str = f"engine{channel}_mode"
    write_sysfs(os.path.join(BASE_URL, engine_mode_str), ENGINE_MODE.RUN)

def stop_sequence(channel:LED_CHANNEL):
    engine_mode_str = f"engine{channel}_mode"
    write_sysfs(os.path.join(BASE_URL, engine_mode_str), ENGINE_MODE.DISABLED)


for led_color in LED_CHANNEL:
    stop_sequence(led_color)
    set_sequence(led_color,"037f4d0003ff6000")
    
for led_color in LED_CHANNEL:
    run_sequence(led_color)

I attempted to add this into a simple Torizon python project and debug/run it via the Visual Studio Code extension, and I get the following error:

OSError: [Errno 30] Read-only file system: '/sys/class/leds/lp5521_pri:channel0/device/engine1_mode'

Is there a way to allow for writes to /sys/class/leds/XXX from a container? I’d eventually like to do this without root privileges, so I’d like to avoid running in the container as root.

Greetings @Ivan_I,

Other than the code itself, what other configurations/changes did you do in the Visual Studio Code project?

Best Regards,
Jeremias

Hi Jeremias - at the moment it is a stock project, made by following the instructions here:
https://developer.toradex.com/torizon/working-with-torizon/application-development/python-development-and-debugging-on-torizoncore-using-visual-studio-code

In that case you probably need to bind-mount /sys into your container. Since you’re running your code in a container now you need to give it access to any files you’re using from the host.

There’s details how to do this with the VSCode extension here: Torizon Best Practices Guide | Toradex Developer Center

You can probably just pass /sys as both the key and value here.

Best Regards,
Jeremias

Hi Jeremias,

I’ve mapped the /sys volume to /sys in my container using the VSCode extension:

I’m still getting the same error:

Exception has occurred: RuntimeError
[Errno 13] Permission denied: '/sys/class/leds/lp5521_pri:channel0/device/engine1_mode'
  File "C:\Users\iiakimenko\Desktop\ledtest\ledtest\main.py", line 30, in write_sysfs
    with open(filepath, 'w') as fl:

Do I need to map the full path to the device? Edit: mapping the full path doesn’t work very well:

("invalid volume specification: '/sys/class/leds/lp5521_pri:channel0:/sys/class/leds/lp5521_pri:channel0:rw'")

I’m still getting the same error:

Actually it appears you’re getting a different error now. Before you were getting Read-only file system but now it’s a Permission denied error.

In your previous post you stated:

I’ve tested running on the system with root privileges

So I guess this device requires root privileges in order to be accessed. You can try running as root in the container by changing the username configuration. Though you said:

I’d eventually like to do this without root privileges, so I’d like to avoid running in the container as root.

However, I’m not familiar with this particular LED driver. Do you know how permissions/access can be given to this device so that root privileges isn’t needed? There’s multiple ways to give hardware access in a container as documented here: Torizon Best Practices Guide | Toradex Developer Center

But this still requires knowledge of what kind of access to give. Which depends on the peripheral. Do you know what kind of device the Linux kernel classifies this LED driver as? Maybe that can help narrow down what kind of permissions are needed.

Best Regards,
Jeremias

Right - I’ve done this and this seems to work well enough for development purposes so I’m not blocked by it at the moment.

Yep, my mistake - though I’m not entirely sure if this signifies progress.

I’ve had a look and the driver appears to be an i2c device:

verdin-imx8mm-06827378:/$ cd /sys/class/leds/lp5521_pri\:channel0
verdin-imx8mm-06827378:/sys/class/leds/lp5521_pri:channel0$ sudo su
verdin-imx8mm-06827378:/sys/devices/platform/soc@0/soc@0:bus@30800000/30a50000.i2c/i2c-3/3-0032/leds/lp5521_pri:channel0#

Based on the documentation, the torizon user should have access to i2cdev - is there a more specific way to give access to the led driver files? I’ve had a look at adding it as a device, but I don’t see anything resembling the driver in the /dev folder.
As you may have guessed by my questions, I’m still quite new to Linux drivers/permissions so I appreciate the help.

The issue I see is that i2cdev won’t give you access to these files in /sys/class/leds/*. Probably you’d need to do something similar to what we did here for backlight devices: meta-toradex-torizon/93-toradex-backlight.rules at kirkstone-6.x.y · toradex/meta-toradex-torizon · GitHub

We created a udev rule that adds backlight files/devices to the video group. That way in a container if you add your user to the video group you’d be able to use these files. In particular notice the last 2 lines of that file where we change the group and permissions for /sys/class/leds/%k/brightness which is a similar file path/sub-system to your /sys/class/leds/lp5521_pri:channel0.

Try making a udev rule for your device here that changes the group and permission for the relevant files in /sys. You can either add them to an existing group in TorizonCore like i2cdev or create your own group if that makes more sense.

Best Regards,
Jeremias