in my previous post I’ve described my first rust project. when i finally got everything working I went on to deploy my app on the raspberry pi zero host. and it wasn’t easy at all.
for reasons I didn’t quite understand it’s impossible to compile rust on the zero. the rust toolchain only support the new arm7 architecture and not the older arm6 used on the zero.
I found plenty of articles describing how to perform the cross compilation, and after a couple of days downloading linkers and building virtual machines, I gave cross a try. while it requires docker to be installed, I found it as a small price to pay considering the ease of use.
as per the instructions, I’ve typed the following line and watch the magic happen
cross build --target arm-unknown-linux-gnueabihf
after a few minutes I had an executable. i’ve uploaded it into my pi and started it, just to find out it stops immediately with a segmentation fault. this was very frustrating. so I thought I’ll give the other target architectures a try. I was very happy to find that arm-unknown-linux-gnueabi
does a better job, and my software respondes.
so I filled in all the required parameters, and let it do its job. after a few minutes, I had my wave audio file ready. but when listening to it, it was clear all was not well. i’ve opened it in audiosity and compared it to the original output I had on my mac.
the frequencies looked ok, but the waveform was definitely not a sine wave. i’ve check the other architectures (arm-unknown-linux-musleabihf
& arm-unknown-linux-musleabi
) and they seemed to work ok and generate the wanted sine. but it got me thinking.
the arm6 is a much weaker and lack even floating point operations that needs to be emulated. what if I used only integers and a Look Up Table for the Sin() function ? luckily I had the code written by Dave Akerman for the arduino, which is even weaker than the PiZero. so I re-wrote the needed function, and measured the results.
looking at the numbers, It was clear that arm-unknown-linux-musleabihf
is a clear winner. with even better results for the LUT method.
i’ve also tried adding the --release
flag, but with marginal improvements to the running time
was it worth all the trouble ? we’ll to check it out, I’ve measured the original python code both on my mac mini and on the pi zero.
while surprisingly the python code it actually faster than rust on the mac by 1 second (6.3s for rust, 5.9s for python, which I suspect is actually a measuring error), rust actually beats python running 4.5 times faster on the pi.
job well done.