I am trying to create a low power device, which would work off a LIR2450 or similar coin cell battery. athe device has long periods of sleep with short periods when it performs operation (e.g. reading sensor and/or sending LoRa data).

For this purpose, I am using an atmega328p. The idea is to have a stable 3.3V out of a voltage regulator and correct battery reading over the voltage divider R9/R10.

Here is the relevant part of the diagram:

atmega328p battery power

I have selected high resistance values for the voltage divider in order to reduce current (this might have been a bad idea).

I am getting readings of Vmeas, but depending on the battery voltage they are somehow - not consistent. When I have approx. 3.5V I seem to get around expected measurement of ADC, however, with around 3V or 4V the readings are strange - either lower than expected or sometimes higher, as if the ADC is not linear in its readings.

How do I measure:

// calculate Vbat from adc value, assuming Vbat:Vmeas is over the resistor-devider 1M:2M
float adcVbat(int adcV) {
  // first calculate adc measurement (10 bit adc - reference 3.3V)
  double meas = ((double)3.3) * ((double)adcV) / 1023;
  // calculate Vbat from voltage devider
  double result = meas * (R1M + R2M) / R2M;
  return result;
// read Vcc in miliVolts
long readVcc() {
  int adc = analogRead(A6); // read ADC
  return (adcVbat(adc) * 1000);

Do you see anything wrong with my concept and should it, in general, work as I expect?

  • \$\begingroup\$ Try putting a 100 nF capacitor across R10. \$\endgroup\$
    – Andy aka
    Jan 16, 2021 at 10:06
  • \$\begingroup\$ that voltage regulator stops working correctly at about 3.6V in. \$\endgroup\$ Jan 16, 2021 at 12:16

2 Answers 2


The problem is that the ADC input works best with impedances below 10k which reads in the datasheet.

The divider has an impedance much greater than that, above 500k.

It has no chance to charge the internal ADC sampling capacitance in the given sampling time.

If you don't plan to sample very often, put something like a 100nF capacitor at the ADC input pin.

If you sample too often, the ADC sampling discharges the 100nF capacitor faster than the resistors charge it so it results into lower voltage result.

  • \$\begingroup\$ Thanks, I don't sample often, actually it is when the device "wakes up", and that is not expected to occur more than 2-3 times per hour. I will try to reduce resistance in divider circuit, at the expense of more battery consumption, it might still be acceptable. \$\endgroup\$
    – Marko
    Jan 16, 2021 at 12:05
  • \$\begingroup\$ The resistances would have to be around 15k and 30k to get source impedance for ADC down to 10k. If that is too much, then simply use the capacitor which allows for higher resistances. Note that the 100nF cap value was a random large enough value you already use. In reality, even a 10nF would hugely improve the reading. \$\endgroup\$
    – Justme
    Jan 16, 2021 at 12:24

LIR2450 has a voltage output from 4.2 to 2.75V,

ATMEGA328P will operate from 2.7 to 5.5V so you don't need to waste energy running a voltage regulator.

so to measure voltage you need to compare the supply voltage with a known voltage. you can use the internal 1.1V reference.

So use a 4:1 divider from a GPIO pin to ground and set the GPIO high and measure the voltage. then set the GPIO low to save energy.


simulate this circuit – Schematic created using CircuitLab

  • \$\begingroup\$ Thanks, my issue there is that I need to communicate over SPI with modules that are 3.3V only. My understanding is that atmega would output on pins the voltages that it is supplied with, therefore it would kill 3.3V modules. \$\endgroup\$
    – Marko
    Jan 16, 2021 at 12:01
  • \$\begingroup\$ well you could use transistors instead of the GPIO to turn on the top end of the voltage divider. \$\endgroup\$ Jan 16, 2021 at 12:18

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.