Need faster timers, maybe interrupts

A project log for /dev/analog0

Primitive analog output device for a Raspberry Pi.

Steven ClarkSteven Clark 04/17/2016 at 01:493 Comments

Audio...might be difficult.

So the thing, is ideally I want to run the update function on this at a decent audio frequency, say 22050hz. But the Linux Kernel doesn't really have features for timing with that kind of frequency. If the kernel calls your function it's once every n "jiffies" and those jiffies only come about 100 to 1000 per second. It looks like some work has been done on maybe putting a high-frequency or high-resolution timer system into the kernel, but I can't seem to find documentation or support on it in official kernels so I'm not even sure any of those would be available in a release kernel and I don't trust my knowledge of the system enough to patch things.

There is hope though, the Broadcom SOC keeps a 1mhz high-accuracy running timer and there's 4 counter registers attached to it. The problem is all I can find documentation of it from is bare-metal programming wikis, and even then 2 out of 4 counters are in use just for the GPU. So, to do audio I'd need to verify that counters 1 and 3 aren't used by the kernel, then learn how to set one of those to 45, and put an interrupt vector to my own top-half code in the right spot, and hopefully it would run.

I've never done something even remotely like any of that. The most likely of my teammates to contribute has already backed out and I haven't heard from the other in about a week. Most of the class is choosing to do stuff like multi-threaded sudoku solvers and other things that sound more impressive than they are. It appears I am going to venture all alone into the terra icognita of kernel space, on an SOC by a company who believes documentation is something that happens to other people.

Maybe it's best to just focus on the variable DC output, given the hardware already has an audio jack.


Greg Kennedy wrote 04/17/2016 at 03:46 point

What about going the other way, like hooking up an ADC and reading input levels off a thermistor or something?

  Are you sure? yes | no

Steven Clark wrote 04/17/2016 at 16:51 point

Possible, but I'd have to learn how to talk to it.  And buy one. And maybe toss out the parts I already have.  My intent is mostly to confine the difficult parts of the assignment to the topic of the course: OS level stuff, not hardware interfacing. I like this idea because it maximizes sounding insanely difficult while only being just hard.

I would be in a better mood about a change like that if I wasn't having to teach myself TCL and AWK for a one-off assignment in networking too.

  Are you sure? yes | no

Steven Clark wrote 04/19/2016 at 06:54 point

On later consideration, you could use this as part of an ADC, but it would run much faster with it's own kernel module.  You feed the dc output of the resistor network (before the capacitor, or better yet with it removed) and your signal into an analog comparator and then read that off another pin.  You then iterate through the values of the output until the analog comparator goes low, and read that as your input.  If you do it with direct access to the output register (hence as root at least, if not in the kernel) you could do it as fast as you could bitbang the port.

  Are you sure? yes | no