Gpio pin toggle loop speed

Hello, I have a radxa rock pro, anyone know any way to speed up the gpio? it currently takes like 5 seconds to toggle a pin (low to high) 384.000 times in a loop, this is to latch some tft screen pixels. I have an arduino due 54mhz which does this in 104ms.

Manuel recompile the kernel without some not used peripherals? Like lvds, spi, i2c, maybe helps to focus rk3188 clock at gpio?

A lot of things can impact the rate of toggling a pin in a loop. Or just running a loop by itself. Having additional peripherals enabled isn’t one of them.

Let me ask you this; where is this loop you are running?

You see, the thing about arduino, is that a sketch is compiled into binary that runs directly on the bare metal. There is no kernel, there is no userspace, there is no security, no access controls, and no cpu scheduler. So your loop() basically represents everything its doing (yeah I know, its a bit more than that, but for the purpose of this discussion, its adequate).

But if you’re running it on a generic computer with a full blown operating system, like Linux, then there is a huge range of things that can impact it.

For instance, if you want to make a really SLOW loop, you might run this;

#!/bin/bash

for i in {1..384000}; do
  echo $(($i % 2)) > direction
done

Just to give you an idea about the performance of that loop, even running on my laptop, if I put “/dev/null” in place of “direction”, it takes over 5 seconds to run that.

If I run the same thing on my rk3399, it takes 9 seconds! If I write out to an led brightness, it jumps up to 21 seconds. Note that while an LED is technically a gpio, there is more overhead with the led driver and with interfacing with it like that.

If you write a similar program in C, it will be much faster than that.
If you take it another step and keep the file descriptor open, it will again be faster.
If you write it as a kernel module, which is the closest you’ll get to the hardware and the closest you’ll get to running “like an arduino”, then it will knock the socks off the arduino.

Also there is another thing you might want to look at. You say that you are working with interfacing to a TFT display… aren’t those usually SPI? If so, you will get much better performance out of that than mucking around with gpio’s directly.

Hello, thank you for reply.

Yes, I first tried using /sys/class/gpio (from radxa nodejs), totally slow for my case, then I changed to radxa wiringX and the total time was from 20 to 30 seconds which made me look into the wiringx radxa.c code to check why still slow.

I saw many places in the code which reads data from the pin/banks/etc many times, for example setting a pin to low/or high makes the code set the pin mode to output even if it was previous set.

I copied the code and changed it to be more like arduino (pin mask, port registers pointers, etc), im now able to get the pointers and just set the bit related to the operation (pinMode, pinStatus, etc). It dropped the total time to 5 seconds which is still slow for me.

Im trying to use some tft lcd I have, I tried with arduino due (84mhz) and was slow, I moved to test with particle photon (120mhz), still not good, then I took my old radxa to test, installed the ubuntu server nand image and got this 30 seconds time.

Im not sure what more I can do with radxa to improve this time, you can check my code here https://gist.github.com/bymaximus/17d84afea20acc7ccd0f7810b26cfc8a

I tried to check many status related to the process, the loop drives some of the cores to 100% usage, I saw no problems related to memory/disk, I dont know how to check the chip clocks. I checked the http://rockchip.fr/Rockchip%20RK3188%20TRM%20V1.3.pdf (1.5.4Recommended Operating Frequency) for the clocks but im not sure which ‘symbol’ the ports are connected to.

No, the pcb I have is 16bit parallel, which im driving with 8 bits only. This board https://www.itead.cc/wiki/ITDB02-5.0 and this shield https://www.itead.cc/wiki/ITDB02_Arduino_MEGA_Shield

1 Like

Yeah, just got 0.3 seconds right now after disabled VMAC which seems to limited the peripheral clocks to 50mhz. Going to do more changes and tests.

1 Like

I was able to get it drop to 100ms but was a hard job and still not enough, is there any way to make use of the LCD output pins of J15 extension header? The lcd clocks are really better than the gpio