Search by Tags

Using PWM in a Container

 
Applicable for

Article updated at 07 Aug 2020
Subscribe for this article updates

Introduction

This article will explain how to use PWM in a Container. Learn how to enable a PWM channel on the device tree and access it using sysfs in a container.

This article complies to the Typographic Conventions for Torizon Documentation.

Prerequisites

In order to take full advantage of this article, the following read is proposed:

PWM Accessibility in User Space

Linux provide PWM functionality to userspace via a class accessed via sysfs(/sys/class/pwm/). Any PWM channel registered for use by a driver is not available for export (request access) to userspace control. The following command can be used to find which PWM channels are available for userspace control.

$ cat /sys/kernel/debug/pwm

Those shown as null are either not exported(can be exported) or in use by a driver and those shown as sysfs are exported to userspace control.

Sample Application

Toradex has provided a sample code written in C. Toradex provides a repository which contains all the sample code related to TorizonCore project, clone it to your PC:

$ git clone https://github.com/toradex/torizon-samples

The sample code sets the settings of the PWM channel at the pwmchip0 controller interface. If required, set controller and settings according to the needs in samples/pwm/pwm/pwm.c.

Move to the PWM directory:

$ cd toradex/torizon-samples/pwm/

Select your architecture below and execute the command to build an image:

$ docker build . -t pwm-sample
$ docker build . --build-arg IMAGE_ARCH=arm64v8 --build-arg CROSS_TC_IMAGE_ARCH=arm64 -t pwm-sample 

Note: The command above builds the Dockerfile.

In the first stage of the build process, the image is based on debian-cross-toolchain-$CROSS_TC_IMAGE_ARCH to cross-compile the sample application on the host machine.

Dockerfile
ARG IMAGE_ARCH=arm32v7
ARG CROSS_TC_IMAGE_ARCH=armhf
 
# First stage, x86_64 build container
FROM torizon/debian-cross-toolchain-$CROSS_TC_IMAGE_ARCH AS cross-container

In the second stage, the binary is copied from the first stage image to the /usr/local/bin of the final image (second stage). This will produce the final application container in a small and deployable image with the tag pwm-sample:

Dockerfile
# Second stage, container for target
FROM torizon/$IMAGE_ARCH-debian-base AS deploy-container
 
# get the compiled program from the Build stage
COPY --from=cross-container /project/build/* /usr/local/bin/
 
CMD pwm

To deploy the image on a portable tar archive file, execute the following command:

$ docker save -o pwm-image.tar pwm-sample

Now copy it to the target machine:

$ scp pwm-image.tar torizon@<board-ip>:/home/torizon/

If you don't know your board IP, it's possible to:

Running the sample

In the last steps, the image was deployed to a tar archive. Now load it to the target:

# docker load -i pwm-image.tar

Now the image can be run but the container needs access to the pwm sysfs interface. Access can be granted either by mounting the /sys or if access is needed to be tightly controlled, sub-directory of /sys containing the required interface can only be mounted.

Mounting /sys:

# docker run -it --rm -v /sys:/sys pwm-sample

In a case that a restricted control to a desired interface is required:

# docker run -it --rm -v /sys/class/pwm/pwmchip0:/sys/class/pwm/pwmchip0 pwm-sample

Note: In case of PWM, mounting the /sys/class/pwm/and trying to write to the files will result in a read-only filesystem issue, because its contents are symbolic links to the actual device in /sys/devices/soc/xxx/xxx/pwm/. Therefore, use absolute paths of symbolic links like /sys/class/pwm/pwmchip0.

Enable PWM Channel

Toradex modules have all PWM channels enabled by default, some modules have dedicated a PWM channel for backlight control. You can use that channel for a different purpose if the backlight is not required.

It is possible to disable the Backlight of a PWM channel by either modifying the device tree or creating a device tree overlay.

Modify Device Tree

Backlight support can be removed to free up the PWM channel by deleting the backlight node in the device tree file.

/delete-node/backlight;

For more information about this, please refer to Device Tree Customization.

Device Tree Overlay

As the device tree overlay does not support deleting a node, it can be set to disabled to mark it powered off/ not plugged in.

/dts-v1/;
/plugin/;

/ {
    fragment@0 {
        target = <&backlight>;
        __overlay__ {
            status = "disabled";
        };
    };
};

A tool named dtconf can be used to apply the overlay, please refer to Device Tree Overlays for more information.