Internal RC Oscillator

Hey all!

I’m kind of new to this so please bear with me.

I’ve made a board that is running an ATMeag328p, same as the UNO.

The thingamabob is battery powered so I want to draw as little power as possible, one of the easiest ways to save power is to run of a lower voltage and reduce the clock speed.

I’m running of 3v3 and I want to run of the internal RC oscillator at 1MHz, luckily according to the datasheet it comes with the "CKDIV8" fuse set, so it will be running at the right speed from the factory.

I won’t be using the Optiboot bootloader since I’ll be programming it directly with my programmer. What setting do I have to change to the "boards.txt" to not override this and program it normally but running the internal clock at 1MHz. I’m assuming that boards.txt is a substitute for a full sized Makefile.

I posted the added board instance below.

Thanks in advanced

uno1mhz.name=ATMega328P_1MHz

uno1mhz.vid.0=0x2341
uno1mhz.pid.0=0x0043
uno1mhz.vid.1=0x2341
uno1mhz.pid.1=0x0001
uno1mhz.vid.2=0x2A03
uno1mhz.pid.2=0x0043
uno1mhz.vid.3=0x2341
uno1mhz.pid.3=0x0243

uno1mhz.upload.tool=avrdude
uno1mhz.upload.protocol=arduino
uno1mhz.upload.maximum_size=32256
uno1mhz.upload.maximum_data_size=2048
uno1mhz.upload.speed=115200

uno1mhz.bootloader.tool=avrdude
uno1mhz.bootloader.low_fuses=0xFF
uno1mhz.bootloader.high_fuses=0xDE
uno1mhz.bootloader.extended_fuses=0xFD
uno1mhz.bootloader.unlock_bits=0x3F
uno1mhz.bootloader.lock_bits=0x0F
uno1mhz.bootloader.file=optiboot/optiboot_atmega328.hex

uno1mhz.build.mcu=atmega328p
uno1mhz.build.f_cpu=1000000L
uno1mhz.build.board=AVR_UNO
uno1mhz.build.core=arduino
uno1mhz.build.variant=standard

http://www.engbedded.com/fusecalc/?P=ATmega328P

I suggest adding "Preserve EEPROM memory through the Chip Erase cycle; [EESAVE=0]".

With no brown-out your gadget will run the battery very dead and will very likely stop working correctly if the voltage drops below 1.6 V. However, the brown-out consumes energy.

You can very likely reduce the startup time.

one of the easiest ways to save power is to run of a lower voltage

Absolutely!

reduce the clock speed

Maybe. A theory is that a fast clock gets the processor back to sleep eight times faster resulting in a tiny bit less energy consumed.

Turning off unused peripherals is effective and easy. That includes the oscillator. If your gadget can tolerate running at ~ 128 kHz the watchdog makes a good processor clock.

Yeah I forgot to mention that disabling peripherals is an easy way to. Sadly I’ll be needing to use the ADC to sample and process the data and then send it through I2C every ~1s. So I’m not sure if I can use the WDT to go into sleep and wake up in that time. I am however going to use a push button hooked up to a pin with an external interrupt to wake it up

There is this neat "secret volt meter" (edit: fixed link) trick (security certificate of that site recently expired - the page itself is still there, though, and a summery can be found a.o. here) which allows you to read the battery voltage. Should not use any significant current but allows you to start flashing an LED or so when the battery runs low (of course that takes extra power but at least you know it's time to replace the batteries).

UNI-T:
I’ll be needing to use the ADC to sample and process the data and then send it through I2C every ~1s. So I’m not sure if I can use the WDT to go into sleep and wake up in that time.

Why not? Every time no matter how short in sleep is helping to cut down on power use.

To make a 1 MHz clock and I2C work together you will have to keep your I2C speed low. That clock speed also slows down your ADC sampling, the speed of which is related to the clock speed. Normally about 100 µs at 16 MHz, this would become 1.6 ms on 1 MHz unless you start changing the ADC clock prescaler as well, and there I really don't know what effect it has on the ADC's accuracy (at 16 MHz clock it goes down).

Doing an ADC conversion, processing, and sending a few bytes over I2C shouldn't take more than 10-20 ms. Probably less. That leaves you with 99% or so idle time, and that's an opportunity to sleep and save power.

wvmarle:
There is this neat "secret volt meter" trick (security certificate of that site recently expired - the page itself is still there, though, and a summery can be found a.o. here) which allows you to read the battery voltage. Should not use any significant current but allows you to start flashing an LED or so when the battery runs low (of course that takes extra power but at least you know it's time to replace the batteries).

Why not? Every time no matter how short in sleep is helping to cut down on power use.

To make a 1 MHz clock and I2C work together you will have to keep your I2C speed low. That clock speed also slows down your ADC sampling, the speed of which is related to the clock speed. Normally about 100 µs at 16 MHz, this would become 1.6 ms on 1 MHz unless you start changing the ADC clock prescaler as well, and there I really don't know what effect it has on the ADC's accuracy (at 16 MHz clock it goes down).

Doing an ADC conversion, processing, and sending a few bytes over I2C shouldn't take more than 10-20 ms. Probably less. That leaves you with 99% or so idle time, and that's an opportunity to sleep and save power.

Thanks for the cool trick, I’m not sure why you linked to a coin sorter, I know they are handy but you don’t need to shove it down my thought :stuck_out_tongue:

I was thinking of going into "ADC noise reduction mode" during the sampling, I’m also averaging 10 samples and ten sending the sampled data through an IIR filter. I’m not sure if this is over kill for a little AVR ADC but why not. Maybe it’s worth going into "Power Save Mode" or even "Power down Mode" during each time it’s sampled and sends the data.

Oops... Link corrected and correct link here/ That was still in the copy/paste buffer apparently.

You can save yourself quite some processing by using a nice and round number like 8 or 16 samples. Then you can calculate the average by a simple bit shift (one instruction) instead of a floating point calculation (hundreds of instructions).

I don't think you can go in any sleep mode while sampling the ADC or sending I2C data.

wvmarle:
Oops... Link corrected and correct link here/ That was still in the copy/paste buffer apparently.

You can save yourself quite some processing by using a nice and round number like 8 or 16 samples. Then you can calculate the average by a simple bit shift (one instruction) instead of a floating point calculation (hundreds of instructions).

I don't think you can go in any sleep mode while sampling the ADC or sending I2C data.

Thanks for the tip!
But I’ve got a bit of track.
I’m looking for a proper way to program the AVR in one go to run at 1MHz and still work with I2C. Are the fuses set automatically when programming it with a programmer? And have I set the fuses properly?

ATMega328P Datasheet: 14.5
ADC noise reduction mode
When the SM[2:0] bits are written to '001', the SLEEP instruction makes the MCU enter ADC Noise Reduction mode, stopping the CPU but allowing the ADC, the external interrupts, the 2-wire Serial Interface address watch, Timer/Counter2(1), and the Watchdog to continue operating (if enabled). This sleep mode basically halts clkI/O, clkCPU, and clkFLASH, while allowing the other clocks to run. This improves the noise environment for the ADC, enabling higher resolution measurements. If the ADC is enabled, a conversion starts automatically when this mode is entered. Apart from the ADC Conversion Complete interrupt, only these events can wake up the MCU from ADC Noise Reduction mode:

wvmarle:
There is this neat...

A version that includes the correct divisor, a technical explanation, an easy calibration method, and a way to increase the performance by using a sleep mode...

...plus, the security certificate is valid.

UNI-T:
Sadly I’ll be needing to use the ADC to sample and process the data and then send it through I2C every ~1s.

The ADC can be powered at will. Discard the first reading after power-up.

UNI-T:
Are the fuses set automatically when programming it with a programmer?

No.

UNI-T:
I was thinking of going into “ADC noise reduction mode” during the sampling…

Follow the link in post #7 for an example.