Yesterday’s post was nice, but it stepped over one teeny weeny little detail: the ATmega’s ADC isn’t sensitive enough to measure AC signals in the millivolts range. With a 3.3V reference, each step is ≈ 3.3 mV, while the signals at low power levels are close to a single ADC step. I could bump the sensitivity slightly by using the 1.1V bandgap as ADC reference voltage, but that still only gets me to 1.1 mV steps. Hardly enough to apply filtering to and set thresholds.
Ah, but there’s a way out… (there always is!)
The ATtiny85 is the smaller brother of the ATmega with a frighteningly low pin count of 8. The key is that it has a differential ADC option, i.e. it’s able to measure the voltage between two points (within 0..VCC) and that it has an optional 20 x analog signal amplifier built-in, when used in differential mode. As reference voltage, there is 1.1V, 2.56V, and VCC – providing a couple of ways to tweak the actual range and sensitivity.
Since I had the right ATtiny85 lying around, as well as TinkerLog’s prototyping board, I thought I’d give it a go:
The problem with an 8-pin chip, of course, is that it only has 5 I/O pins (6 if you’re willing to use the RESET line and lose the ISP programming mode – which I wasn’t). That’s not much to interface with. The ATtiny85 I used has 8 Kb flash and 512 bytes of RAM, so that in itself should be sufficient for all the code I need.
There’s no boot loader. There’s no ready-to-use serial port. And it’s not an Arduino-compatible system, so you can’t just write sketches for it, right?
Not so fast. First of all, there’s the LCD Plug which needs only 2 I/O lines. That leaves me 3 pins: 2 for the differential analog input, and 1 for a debug LED. Plenty!
The LCD needs the Ports library. Which needs the Arduino IDE and runtime. Ah, but there’s more good news: there’s an arduino-tiny project which defines some boards and a set of “core” runtime source files which are intended to run on ATtiny85’s and other non-mega AVR chips. That’s quite a feat, btw, once you consider just how limited an ATtiny85 is (ASCII art by the arduino-tiny project):
+-\/-+
Ain0 (D 5) PB5 1| |8 VCC
Ain3 (D 3) PB3 2| |7 PB2 (D 2) INT0 Ain1
Ain2 (D 4) PB4 3| |6 PB1 (D 1) pwm1
GND 4| |5 PB0 (D 0) pwm0
+----+
Still, they managed to support a couple of digital and analog I/O pins, with support for the millis() timer, analog in and out, and more. With this installed, I can write sketches and upload them via the AVR-ISP. Pretty amazing!
Sooo… just had to make a few small and obvious tweaks, and the Ports library works. There’s exactly one port (AIO1 = PB2, DIO1 = PB0, IRQ = PB1). Note that I’m using the new Arduino IDE 1.0 (beta).
That leaves me a whopping two pins for the differential analog input, which is what this is all about, after all.
Here’s my setup (hooked up to the safe 20 VAC brick):
I was too excited to tidy up once the LCD hookup worked. It would all have fitted on a single (mini) breadboard.
Tomorrow, I’ll show you how this crazy little setup measures up…
With a very low aref voltage, would the ATmega’s ADC Measure the values you’re going for?
The ATtiny85 can measure with a resolution down to about 0.05 mV due to its built-in PGA. For ATmega’s, AREF needs to be at least 1V (only marginally less than the internal 1.1V bandgap), which translates to 1 mV resolution.
Amazing “crazy little setup” using only 8 pins!.