How to Enable and Control PWM on AML-S905X-CC

AML-S905X-CC Le Potato has 5 available hardware PWM multiplex over 6 pins. The hardware PWMs are grouped in chip pairs accessible via pwm0 and pwm1.

  • AO_A AO_B on c8100550
  • A on c1108550
  • E F on c11086c0

You cannot enable overlapping overlays within the grouped pair. This means you can not individually enable pwm-e and pwm-f. You have to enable pwm-ef to have both running at the same time.

In terms of pin routing:

  • AO_A on Pin 11 controlled via c8100550 pwm0
  • AO_B on Pin 12 or 13 controlled via c8100550 pwm1
  • E on Pin 32 controlled via c11086c0 pwm0
  • A on Pin 33 controlled via c1108550 pwm0
  • F on Pin 35 controlled via c11086c0 pwm1

For AO_A on pin 11, you must move the jumper for 2J1 to the edge of the board from the stock jumper position to connect the GPIO to the 40 pin header pin 11.

There are 9 dto combinations to select from:

  • pwm-ao-6 on Pin 11 and 12
  • pwm-ao-9 on Pin 11 and 13
  • pwm-ao-a on Pin 11
  • pwm-ao-b-6 on Pin 12
  • pwm-ao-b-9 on Pin 13
  • pwm-a on Pin 33
  • pwm-e on Pin 32
  • pwm-ef on Pin 32 and 35
  • pwm-f on Pin 35

The Linux kernel interface can be accessed via sysfs.

sudo ldto enable pwm-{x} # replace x with one of the dtos in list above
ls -al /sys/class/pwm # see the pwmchip{n} to hardware mapping
echo {0,1} | sudo tee /sys/class/pwm/pwmchip{n}/export
echo 1000000 | sudo tee /sys/class/pwm/pwmchip{n}/pwm{n}/period
echo 500000 | sudo tee /sys/class/pwm/pwmchip{n}/pwm{n}/duty_cycle
echo 1 | sudo tee /sys/class/pwm/pwmchip{n}/pwm{n}/enable
1 Like

Can you give an example for how to control a servo motor plugged into pin 11?

I assume pin 11 will have {n} = 0. How do we:

  1. enable pin 11
  2. set frequency to 50hz
  3. change duty cycle
  4. turn off pin (so there aren’t fluctuations) until we enable it again

Check the updated post. Please run sudo apt update && sudo apt dist-upgrade before trying the dtos. They were just added.

  1. sudo ldto enable pwm-ao-a
  2. The period is in nanoseconds per the kernel interface. So if you want a 1KHz signal, you need to put 1000000.
  3. Duty cycle is also in nanoseconds so if you want a certain %, multiply it by the period.
  4. echo 1 > enable

I moved the jumper over one pin to the edge, updated my board, ran commands below and wasnt able to get anything from my servo. i am connected to gpio pin 11, power on pin 4, and ground on pin 6. i used multiple brand new servos to rule out defected hardware. any thoughts?

sudo ./ldto enable pwm-ao-a
sudo ./ldto active
ls -al /sys/class/pwm
echo 1 > /sys/class/pwm/pwmchip0/export
echo 1000000 > /sys/class/pwm/pwmchip0/pwm1/period
echo 500000 > /sys/class/pwm/pwmchip0/pwm1/duty_cycle
echo 1 > /sys/class/pwm/pwmchip0/pwm1/enable

update: Just kidding i looked over the " AO_A on Pin 11 controlled via c8100550 pwm0" part. after echoing 0 instead of 1 to /sys/class/pwm/pwmchip0/export, that took care of the problem. Any thoughts on how to reverse the direction?

1 Like

There should be a file called polarity and you can echo a 0 or 1 and it should work.

I am trying to follow the steps from minitacoslayer. However, I do not see the /sys/class/pwm folder:

ubuntu@lepotato:~$ sudo ldto enable pwm-ao-a
Overlay pwm-ao-a: applied
ubuntu@lepotato:~$ sudo ldto active 
#Overlays active:
ubuntu@lepotato:~$ ls -al /sys/class/pwm
ls: cannot access '/sys/class/pwm': No such file or directory

Any idea on why this is happening?

1 Like

This was a bug on our part. Please update the kernel and try again.

1 Like

I was trying to enable pwm on pin 33:

sudo ldto enable pwm-a
echo 0 > pwmchip0/export 
echo 100000000 > pwmchip0/pwm0/period 
echo 10000000 > pwmchip0/pwm0/duty_cycle
echo 1 > pwmchip0/pwm0/enable 

But I get an error: “-bash: echo: write error: Invalid argument” on this last line. What could this be?

I am encountering the same issue as @Samuel
As additional information, these are the active DTOs I have:

#Overlays active:

Note that the error is not uniform across chips/lines:

  • pwmchip0/pwm0: I can set duty_cycle and period but cannot set enable.
  • pwmchip0/pwm1: I cannot set duty_cycle
  • pwmchip2/pwm0 and pmwchip2/pwm1: works, I can set duty_cycle, period and enable.

Again, by “cannot set” I mean I get “write error: Invalid argument”.

You don’t have permission as you are not the root user. You need to add yourself to the gpio group via sudo adduser USERNAME gpio or run sudo su.

I try both solutions. And still, I wasn´t able to set enable on pins 32, 33 and 35. After rebooting the system I was able to write to pmw0/enable (for pin33 and 32). However, for some reason, I still cannot write (write error: Invalid argument) to pmw1/enable for pin35.

Aditional info

  • Like @technoryt, I was always able to set period and duty_cycle for all pins. I only had issues while setting enable (echo 1 > /sys/class/pwm/pwmchip{x}/pwm[n}/enable ) for pins 32, 33 and 35.

  • I only have one active DTO each time. And I’m using rasbian.

Actually, I rebooted after using ldto merge (so that I do not need to use ldto activate, I don’t think I changed anything else). Now I can successfully use all four PWM lines. I started from the Ubuntu 22.04 Desktop image.

@Samuel: did you manage to use the PWM lines from a non-root user? If I try to add my user to the gpio group as mentioned by @librecomputer, I have the error that the group does not exist. All the directories under /sys/class/pwm are all owned by root:root.

ubuntu@lepotato:~$ sudo adduser ubuntu gpio
[sudo] password for ubuntu: 
adduser: The group `gpio' does not exist.

Check the group ownership of the files under /sys/class/pwm. Different OSes use different groups based on udev rules.

@librecomputer: Regarding your last post. All the files under sys/class/pwm/pwmchip{X} belong to the gpio group. Except for the pwmchip{X}, which are owned by root group. So, I tried to change the group of these directories (assuming that it should be gpio) but nothing changed:

inl@raspberrypi:~ $ sudo chgrp gpio /sys/class/pwm/pwmchip0
inl@raspberrypi:~ $ ls -l /sys/class/pwm/
total 0
lrwxrwxrwx 1 root root 0 Jan 18 16:43 pwmchip0 → …/…/devices/platform/soc/c1100000.bus/c11086c0.pwm/pwm/pwmchip0

By way, it is not very clear to me which group should own these directories. Should It be gpio?

For some reason, now I can control pin35, but cannot control pin33 anymore (refer to my previous post). Why could this be?

@technoryt: Regarding your question, I believe so, at least for pins 12 and 13. Relative to your comment, my user was already a member of gpio group.

Permissions are setup by udev and can be arbitrarily customized.

You need to enable pwm-ef rather than pwm-e or pwm-f. They’re a combo pair.

Once you add yourself to a group. You need to logout and log back in to have it take effect. Also the permission should have group write.