Analog Pin Power Consumption Question

Hey all...

I've designed and built simple temperature data logger using a standalone ATMega328P (32-TQFP running at 1 MHz) an MCP9808 temp sensor, a DS3231 RTC, and a CAT24C512 (512Kb EEPROM) which all communicate via I2C. Power supply is a single AAA battery via a TPS61221 boost converter to give 3.3V. Since this is just a prototype, I added a single LED through a 130 ohm resistor as a status indicator. The intent would be to occasionally blink this LED as proof of life/low battery/malfunction indications while hiking the Catskill Mountains this summer.

I just completed a few initial power consumption measurements while supplying a nominal 1.25V and found the total circuit draws ~2.7 mA with everything awake (LED off, of course)...which seemed reasonable for an initial starting point before employing any low power modes for any devices. This also meets my goal of logging data for at least 5 days.

Next, I turned the LED on via a digitalWrite command and the current jumped to a whopping 43 mA?! :astonished:

With a 3.3V supply and ~2V of drop across the LED, I selected a 130 Ohm resistor for a target of ~10 mA when in use. I measured the pin output to be ~3.1V and the LED drop is right at the 2V as per its datasheet...so I would expect to see only about an additional 8.5 mA with the 130 Ohm resistor.

What's going on here?!?

In case it matters...and I suspect it may...

The LED is connected to pin 24 of the ATMega328P in the 32-TQFP package which is the A1 pin. I used an analog pin as a digital output simply due to board layout considerations (the pin was easy to route to).

Thanks in advance for any insight. This is my first attempt at any low power battery design and this has stumped me.

-Dave

So what was the actual measured current threough the LED ?

srnet:
So what was the actual measured current threough the LED ?

Fair question...

My project is all SMD and on the board already, so I was unable to easily remove a component to do a proper series current measurement. I checked voltages at the pin (3.1V), across LED (2.0V), and at the 130 Ohm resistor (1.1V) and applied Ohm's law at the resistor to find the series current (1.1V /130 Ohms = ~.0085A).

Pin 24 (A1)------------------>LED-------------------->130Ohm------------>GND
(3.1V) (3.1V) (1.1V) (1.1V) (0.0V)

Is there a better way with the SMD circuit already constructed?

GarageGeek:
Is there a better way with the SMD circuit already constructed?

Yes, remove the resistor and replace with only one end solderd to the pads. Then you can measure the current flow.

GarageGeek:
Next, I turned the LED on via a digitalWrite command and the current jumped to a whopping 43 mA?!

Post your code.

srnet:
Yes, remove the resistor and replace with only one end solderd to the pads. Then you can measure the current flow.

Soooo...I did this and found 9 mA...pretty much as expected. That LED or micro pin wouldn't have survived 40+ mA for long.

Ok…but it’s a work in progress. I put this together the other day just for testing purposes. It simply prints a menu to the serial terminal which I use to interact. I use it to run an I2C address scanner, read/write a few bits of data to the EEPROM, toggle the LED, and read from the RTC. (I cant get the MCP9808 temp sensor to respond…but that’s a problem for another thread)

I’m simply toggling a digitalWrite on pin A1 whenever I send a ‘L’ via the serial monitor. Please note I’ve omitted the functions from the code below due to posting limits.

When I toggle the LED off…I’m at 2.7 mA. Toggle LED on and it’s 43 mA.

/*
 * Hiking Data Logger - v1.0
*/

/* To-Do List:
 * Add Barometric Pressure/Altitude Sensor
 * Communicate with Temp Sensor 
 * Output EEPROM to CSV file
 * Include Low Power Mode Options
 * 
*/

//---------------------------------------------------------------- LIBRARIES
#include <Wire.h>
#include <RTClib.h>
//---------------------------------------------------------------- DEFINITIONS
#define EEPROM_I2C_ADDRESS 80
#define switchOne 7
#define switchTwo 8
#define ledPin A1

RTC_DS3231 rtc; //#define RTC_ADDRESS 104
char daysOfTheWeek[7][12] = {"Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"};

//---------------------------------------------------------------- VARIABLES

bool awaitingCommand = false;
bool ledOn = true;

unsigned long time1;
unsigned long time2;

int blinkDelay = 100;

//---------------------------------------------------------------- SETUP
void setup()
{
  //Pin 0 - Serial RX
  //Pin 1 - Serial TX
  pinMode(2, INPUT_PULLUP);
  pinMode(3, INPUT_PULLUP);
  pinMode(4, INPUT_PULLUP);
  pinMode(5, INPUT_PULLUP);
  pinMode(6, INPUT_PULLUP);
  pinMode(switchOne, INPUT_PULLUP); //7
  pinMode(switchTwo, INPUT_PULLUP); //8
  pinMode(9, INPUT_PULLUP);
  pinMode(10, INPUT_PULLUP);
  //Pin 11 - SPI MOSI
  //Pin 12 - SPI MISO
  //Pin 13 - SPI SCK
  pinMode(A0, INPUT_PULLUP);
  pinMode(ledPin, OUTPUT);
  pinMode(A2, INPUT_PULLUP);
  pinMode(A3, INPUT_PULLUP);
  //Pin A4 - I2C SDA
  //Pin A5 - I2C SCL

  Serial.begin(9600);
  
  Wire.begin();  
  
  rtc.begin();
  rtc.adjust(DateTime(F(__DATE__), F(__TIME__)));  //Set to sketch compile time
  //rtc.adjust(DateTime(2018, 5, 12, 12, 0, 0));  //Set to specific day/time  (Y, M, D, H, M, S)
   
  digitalWrite(ledPin, HIGH);
  delay(1500);
  digitalWrite(ledPin, LOW);  

  time1 = millis();
  
  Serial.println();
  Serial.println("***************************************************");
  Serial.println("Dave's Hiking Data Logger - v1.0");
  Serial.println("***************************************************");

  delay(2500);

  Serial.println();
  Serial.print("Current Date/Time: ");
  getTime();
  delay(1500);
}

//---------------------------------------------------------------- LOOP
void loop()
{
  if (awaitingCommand == false)
  {
    Serial.println("Available Commands:");
    Serial.println("R = Read EEPROM");
    Serial.println("E = Erase EEPROM");
    Serial.println("I = Run I2C Scanner");
    Serial.println("L = Toggle LED");
    Serial.println("T = Print Current Time");
    Serial.println("***************************************************");
    delay(1500);
    Serial.print("Awaiting Command...");
    awaitingCommand = true;
  }

  else
  {
    if (Serial.available())
    {
      Serial.println("Command Received!");
      delay(1500);
      byte command = Serial.read();
      if (command == 'E')
      {
        Serial.println("Eraseing EEPROM...please wait...");
        delay(1500);
        Serial.println("***************************************************");

        for (unsigned long writeAddress = 0; writeAddress <= 10; writeAddress++)  //65535
        {
          eepromWrite(writeAddress, 123);
          Serial.print("EEPROM Write Address: ");
          Serial.println(writeAddress);
        }

        Serial.println("***************************************************");
        delay(1500);
        Serial.println("EEPROM Write Complete!");
        Serial.println("***************************************************");
        Serial.println();
      }

      else if (command == 'R')
      {
        Serial.println("Reading from EEPROM...please wait...");
        delay(1500);
        Serial.println("***************************************************");

        for (unsigned long readAddress = 0; readAddress <= 10; readAddress++)  //65535
        {
          int readVal = eepromRead(readAddress);
          Serial.print("EEPROM Read Address: ");
          Serial.print(readAddress);
          Serial.print(" / Value: ");
          Serial.println(readVal);
        }

        Serial.println("***************************************************");
        delay(1500);
        Serial.println("EEPROM Read Complete!");
        Serial.println("***************************************************");
        Serial.println();
      }

      else if (command == 'I')
      {
        I2CScanner();
      }

      else if (command == 'L')
      {
        if (ledOn == true)
        {
          digitalWrite(ledPin, LOW);
          Serial.println();
          Serial.println("LED is OFF");
          Serial.println("***************************************************");
          delay(1500);
          ledOn = false;
        }

        else
        {
          digitalWrite(ledPin, HIGH);
          Serial.println();
          Serial.println("LED is ON");
          Serial.println("***************************************************");
          delay(1500);
          ledOn = true;
        }
      }

      else if (command == 'T')
      {
        delay(1000);
        getTime();
      }


      else
      {
        Serial.println("Unknown Command. :-(");
        Serial.println();
        Serial.println();
      }

      awaitingCommand = false;
    }
  }

 time2 = millis();
 if ((time2-time1) >= 60000)
 {
  ledBlink();
  time1 = millis();
 }
}

What is connected to A0 (physical pin 23)?

What is connected to A7 (physical pin 22)?

Enable the internal pullup on A1 / physical pin 24 / the LED pin. What voltage do you measure on that pin?

Nothing is connected here. Pin is configured as - pinMode(A0, INPUT_PULLUP);

Hmmm...good question. I overlooked that pin on the 32-TQFP version.

I have nothing connected to it...but I also didn't do anything with it in setup. Do I need to? And how would I go about that, if necessary?

Not entirely sure of the configuration you're looking for here. Ordinarily this is an output pin for the LED. So apologies if I've not done what you're asking.

Configured it as an input with the pull up enabled, measured voltage on the pin 1.75V. I expect this is due to the basically making a voltage divider since my LED/130Ohm resistor are still connected here.

Is that what you were looking for?

Thanks again for the help.

GarageGeek:
Is that what you were looking for?

Solder bridge. None found.

GarageGeek:
Next, I turned the LED on via a digitalWrite command and the current jumped to a whopping 43 mA?!

Using the ‘L’ command?

I send various commands via the serial window for different tests. When an L is sent, it toggles the LED on/off.

When you test the current consumption of the LED circuit are you or are you not using just the 'L" command?

Yes. Using the L command to turn the LED on/off for each current measurement. Powering the device with a bench supply through a bench meter for current measurement.

There is nothing left. The problem cannot be anything associated with A1 / ledPin. I suggest you test with a sketch that only touches the A1 pin (no Serial).

Makes sense...

Simple sketch toggling the LED on a 20 second delay.

LED Off = 2.7 mA
LED On = 32.5 mA

This really makes no sense. :neutral_face:

#define switchOne 7
#define switchTwo 8
#define ledPin A1

void setup()
{
  pinMode(0, INPUT);  //Pin 0 - Serial RX
  pinMode(1, INPUT);  //Pin 1 - Serial TX
  pinMode(2, INPUT_PULLUP);
  pinMode(3, INPUT_PULLUP);
  pinMode(4, INPUT_PULLUP);
  pinMode(5, INPUT_PULLUP);
  pinMode(6, INPUT_PULLUP);
  pinMode(switchOne, INPUT_PULLUP); //7
  pinMode(switchTwo, INPUT_PULLUP); //8
  pinMode(9, INPUT_PULLUP);
  pinMode(10, INPUT_PULLUP);
  pinMode(11, INPUT);  //Pin 11 - SPI MOSI
  pinMode(12, INPUT);  //Pin 12 - SPI MISO
  pinMode(13, INPUT);  //Pin 13 - SPI SCK
  pinMode(A0, INPUT_PULLUP);
  pinMode(ledPin, OUTPUT);
  pinMode(A2, INPUT_PULLUP);
  pinMode(A3, INPUT_PULLUP);
  pinMode(A4, INPUT);
  pinMode(A5, INPUT);
}


void loop()
{
  digitalWrite(ledPin, HIGH);
  delay(20000);
  digitalWrite(ledPin, LOW);
  delay(20000);
}

Are the voltages at the pin and at the resistor + LED connection the same? What are those voltages?

Yes. Here are the measured voltages:

Micro Pin - 3.1V

LED Andode - 3.1V
LED Cathode - 1.1V

Resistor In - 1.1V
Resistor Out - GND

One thing interesting is that all of the other pins that I have pulled up internally are at 3.3V. This is the only pin that is at 3.1V when written high. And current is going somewhere else (internally or otherwise) whenever it is written high.

GarageGeek:
One thing interesting is that all of the other pins that I have pulled up internally are at 3.3V. This is the only pin that is at 3.1V when written high.

The section of interest is "Pin Driver Strength". At 9 mA sourced there is about a 0.25 volt drop at the pin. The difference heats the die. An observation that perfectly matches expectations.

What do you have connected to AREF?

Do all VCC / GND pairs have a bypass capacitor?

Are all VCC / GND pairs connected to power?

GarageGeek:
And current is going somewhere else (internally or otherwise) whenever it is written high.

And going back to the question posed in post #1 ?