Archive for the ‘Hardware testing’ Category

Battery Life of an ESP8266 design

January 11, 2016 1 comment


The use of the relatively “new” and absolutely  “cheap” ESP8266 IC generates a rush in the apparition of new IoT  applications.

Lately I’m looking for devices that can run on batteries for months.

A device inside my mailbox twittering when the door was opened.

A moisture sensor reporting every hour from a spot in the garden, sending the data to ThingSpeak .

A tank level sensor reporting when low critical level is reached.


Working with Energía and the Texas Intrument’s Launchpads found the EnergyTrace tool.

How EnergyTrace measure power?
A software controlled DC-DC converter generates the target power supply (1.2 V-3.6 V).
The time density of the DC-DC converter charge pulses equals the energy consumption of the target microcontroller.
A built-in calibration circuit defines the energy equivalent for a single charge pulse.
The width of pulses remains constant. By counting  the charge pulses during a period of timed the average current is calculated.


By removing the jumper of 3.3V to the development section and connecting my ESP8266 based device the EnergyTrace can be used to estimate the battery life.



My  approach for the battery  power is to use a LDO regulator with very low quiescent current and 3 AA alkaline batteries.


To reduce power the power-on LED and the light sensor LDR were removed.

The RGB led and some other resistors were also removed.


This post is in construction….


ESP-201 an ESP8266 breadboard friend

December 31, 2015 Leave a comment

To plug the ESP-201 in the breadboard is necessary to remove the 4 pin connector from the botton of the board and install it in the component side.




A quick pinout reference to start the wiring:


Note: GPIO9 and GPIO10 are connected to the FLASH memory (may be unusable). Here is a “surgery” procedure to use them: ESP-201 board modification

First experiment sending the analog value from A0 to ThingSpeak:



Experimenting with different antennas:


Best results with the external antenna (the metal one):




Experimenting with Deep Sleep:

In progress….SEP-201_DS_Wiring

Boot Modes

NodeMCU Breathing LED with Arduino IDE

August 20, 2015 18 comments


The first sketch used to test an Arduino compatible board is Blink.
After run Blink in my new NodeMCU Development Kit,
Started experiments with the WiFi connection:
-Mini servers to control leds, servos, etc..
-Send light intensity and temperature to ThingSpeak, Xively, Plotly etc..
-Serial data bridges

The blue led in the board was used to signal the execution of a particular procedure.
Because the GPIO16 (DO) limitation to use the analogWrite() and looking to see my LED doing something else…

Inspired by the Apple’s “breathing” pattern used for the sleep indicator.
Here is the code to generate a “breathing LED”.

The Arduino code runs inside a multitasking application, the ESP8266 is running at the same time TCP and WiFi stacks.
The sketch can breake the multitasking execution if your code runs in a blocking section.
The delayMicroseconds() is one of those blocking functions, delay(0)  was used to prevent watchdog reset inside the PWM loops.

/*LED_Breathing.ino  20 AUG 2015
Using NodeMCU Development Kit V1.0
Going beyond Blink sketch to see the blue LED breathing.
A PWM modulation is made in software because GPIO16 can't
be used with analogWrite().

#define LED     D0        // Led in NodeMCU at pin GPIO16 (D0).
#define BRIGHT    350     //max led intensity (1-500)
#define INHALE    1250    //Inhalation time in milliseconds.
#define PULSE     INHALE*1000/BRIGHT
#define REST      1000    //Rest Between Inhalations.

//----- Setup function. ------------------------
void setup() {                
  pinMode(LED, OUTPUT);   // LED pin as output.    

//----- Loop routine. --------------------------
void loop() {
  //ramp increasing intensity, Inhalation: 
  for (int i=1;i<BRIGHT;i++){
    digitalWrite(LED, LOW);          // turn the LED on.
    delayMicroseconds(i*10);         // wait
    digitalWrite(LED, HIGH);         // turn the LED off.
    delayMicroseconds(PULSE-i*10);   // wait
    delay(0);                        //to prevent watchdog firing.
  //ramp decreasing intensity, Exhalation (half time):
  for (int i=BRIGHT-1;i>0;i--){
    digitalWrite(LED, LOW);          // turn the LED on.
    delayMicroseconds(i*10);          // wait
    digitalWrite(LED, HIGH);         // turn the LED off.
    delayMicroseconds(PULSE-i*10);  // wait
    delay(0);                        //to prevent watchdog firing.
  delay(REST);                       //take a rest...

NodeMCU ESP-12 Development Kit V1.0

August 15, 2015 Leave a comment

Here is my Pinout Diagram of this wonderful board for IoT development:


With added circuitry to manage the RESET and FLASH from the USB Serial Port, this board is  great for development.

After some LUA scripts and trying the Arduino IDE with it…  This Board is awesome!


I’ll continue experimenting with this one for a while…

Interrupts with the TRINKET analog comparator

July 12, 2015 Leave a comment

Here I’m sharing a working example using the analog comparator of the Adafruit’s  TRINKET (ATtiny85).



/*Trinket_comp_ISR.ino 12 JUL 2015
  Sketch to test interrupts fron the analog comparator.
  2.5 Volt in ANI0 (voltage divider).
  Potentiometer input in ANI1  An interrupt is generated in every change of the comparator output (toggle).
  The interrupt set the flag  "triggered".
  The main loop program checks for the flag, if the flag is set, test the output value  of the comparator
  and modify the state of the LED according.*/

#define LED 4 

volatile boolean triggered=false;

//------------ Analog Comparator Interrupt Routine ----------------------------
  triggered = true;
void setup(){
  ADCSRB &= ~(1<<ACME);             //Set AIN1 as the negative input (Potentiometer).
  DIDR0 |= (1<<AIN1D)|(1<<AIN0D);   // disable digital inputs.
//ACSR – Analog Comparator Control and Status Register   
  ACSR = B00001000; // comparator interrupt enabled and tripped on toggle. (compare with AN1)
      //  ||||||||_ ACIS0 ACIS1, ACIS0: Analog Comparator Interrupt Mode Select
      //  |||||||__ ACIS1 10= falling edge; 11= raising edge; 00= toggle.
      //  ||||||___ ACIC  Reserved Bit
      //  |||||____ ACIE  Interrupt Enable
      //  ||||_____ ACI   Analog Comparator Interrupt Flag (R/W), write 1 to clear it.
      //  |||______ ACO   Analog Comparator Output (read only)
      //  ||_______ ACBG  1= Bandgap Select (1.1V); 0= compare with AIN0 (pin 6)
      //  |________ ACD   Analog Comparator Disable

  digitalWrite(LED, HIGH);//LED on for 100 milliseconds.
  //Put the LED status as the analog comparator output (inverted)
  if(ACSR & (1<<ACO))digitalWrite(LED, LOW);
  else digitalWrite(LED, HIGH);

void loop(){
    if(ACSR & (1<<ACO))digitalWrite(LED, LOW);
    else digitalWrite(LED, HIGH);
    triggered= false;

Arduino and Two Stepper Motors

May 30, 2015 16 comments



This project consist in moving two stepper motors “simultaneously”.
Really there is a loop where both motors are moved “one step at a time” to reach their final position.
5 Volts steppers with external power source are used.


Here is the video in YouTube:

Here is the Sketch:


Two_Steppers.ino  30 MAY 2015

Driving two steppers concurrently with the Arduino Nano.
stepperX follows potentiometer on analog input 0.
stepperY follows potentiometer on analog input 1.
A timeout is used to turn off coils and save energy in battery
operated applications.

Arduino NANO.
Drivers: ULN2003A
Stepper Motors: 28BYJ48, 5VDC, step angle 5.625 °
                Gear reduction 64:1
                No-load starting frequency:> = 500PPS (4 rpm)
                Coil resistance 60 Ohms.               

#include <Stepper.h>

#define  STEPSREV    4096    // 64(fullsteps) * 64 (reduction ratio)
#define  SPEED       4       // motor speed (RPM)

#define  COIL_1X     11
#define  COIL_2X     9
#define  COIL_3X     10
#define  COIL_4X     8

#define  COIL_1Y     7
#define  COIL_2Y     5
#define  COIL_3Y     6
#define  COIL_4Y     4

#define  POT_X       0
#define  POT_Y       1                
#define  TIMEOUT     1000    //Turns off after 1 sec of inactivity.
#define  NOISE       8       //inmunity in steps because analog noisy readings.

// create the instances of the stepper class.
Stepper stepperX(STEPSREV, COIL_1X, COIL_2X, COIL_3X, COIL_4X);
Stepper stepperY(STEPSREV, COIL_1Y, COIL_2Y, COIL_3Y, COIL_4Y);

int potValX,potValY;           // potentiometers analog readings
int Xpos,Ypos;                 // Actual steppers positions(0-4096)->(0-360°)
int newXpos, newYpos;          // New steppers positions
unsigned long stampX, stampY;  // last move time stamped.

//============== functions ====================================================

//Read the potentiometers and map the reading to mach 360 degrees.
void readPots(){
  potValX = analogRead(POT_X);          // read POT_X value (0-1023).
  potValY = analogRead(POT_Y);          // read POT_Y value (0-1023).
  newXpos= map(potValX,0,1023,0,2047);  // Map pot X range to one stepper turn.
  newYpos= map(potValY,0,1023,0,2047);  // Map pot Y range to the stepper turn.
// Aproach stepperX to the newX position.
void aproachX(int newX){
  int Xdir = Xpos<newX ? 1 : -1;
  stepperX.step(Xdir);        // move one step in the Xdir direction.
  Xpos += Xdir;               // update Xpos.
  stampX = millis();          // stamp actual time.

// Aproach stepperY to the newY position.
void aproachY(int newY){
  int Ydir = Ypos<newY ? 1 : -1;
  stepperY.step(Ydir);        // move one step in the Ydir direction.
  Ypos += Ydir;               // update Ypos.
  stampY = millis();          // stamp actual time.

//Check for inactivity and turn off the steppers coils to save battery.
void CheckTimeout(){
  if((millis() - stampX) > TIMEOUT){   //Turn Off StepperX coils.
    digitalWrite(COIL_1X, LOW);
    digitalWrite(COIL_2X, LOW);
    digitalWrite(COIL_3X, LOW);
    digitalWrite(COIL_4X, LOW);
  if((millis() - stampY) > TIMEOUT){   //Turn Off StepperY coils.
    digitalWrite(COIL_1Y, LOW);
    digitalWrite(COIL_2Y, LOW);
    digitalWrite(COIL_3Y, LOW);
    digitalWrite(COIL_4Y, LOW);

//=================== setup ===================================================
void setup(){
  stepperX.setSpeed(SPEED);  // set the X motor speed.
  stepperY.setSpeed(SPEED);  // set the Y motor speed.
  Xpos = newXpos;
  Ypos = newYpos;

//================= main loop =================================================
void loop(){
//if diference is greater than NOISE move steppers.
  if(abs(newXpos - Xpos)> NOISE) aproachX(newXpos);
  if(abs(newYpos - Ypos)> NOISE) aproachY(newYpos);

  CheckTimeout();   //check for inactivity.









Digital To Analog with Tiva C Launchpad and Energía

April 17, 2015 1 comment


There are nice Energía diagrams for this LaunchPad in the Web.

Nevertheless, to become familiar with the board functionality and pin layout (and because enjoy drawing) decided to make a diagram. Tiva C Launchpad Pinout Diagram :


Since my first contact with Arduino always wanted to generate waveforms and see them in an oscilloscope. Almost three years ago made some projects with the MSP430 LaunchPad, can be seen at the SeuPay’s YouTube channel. Then also did some test with the Stellaris LaunchPad.

After more than a year with a couple of unboxed Tiva C LaunchPads, decided to try some waveforms generation with the inexpensive 32 bit, 80 MHz ARM platform. Using Energía, began some experiments with the Tiva C :

-Generating waves with the MCP4725, I2C 12-Bits DAC .

-Generating waves with the AD7801 Parallel 8-Bit DAC.

Direct Port Manipulation was used to reach higher data updates (samples/second).


Tiva C Launchpad and MCP4725

The first experiment generates wave shapes using an external DAC (Digital-To-Analog Converter).

The first choice was to use the MCP4725 from Adafruit’s (SparkFun also has a version with different address).


The following sketch fills an array with the values of a sine wave and feeds the  DAC continuously with those values.

The “Fast Mode Write Command” of the MCP4725 is used.

/*MCP4725_Sin_01.ino   Arduining 17 APR 2015

-Energia Sketch to be used with Tiva C Launchpad and the Adafruit's MCP4725.
-I2C Fast Mode Write Command is used.
-120 samples are producing a 3.62Hz sine wave  => 434 samples/second.

Based in the code at:

#include <Wire.h>
#include <math.h>

//The MCP4725 from Adafruit:
//  I2C address is 0x62 ( by default A0 has a 10k pull-down resistor ).
//  I2C address is 0x63 if A0 is connected to VCC. 
#define MCP4725_ADDR 0x62           //I2c address..

int ch[ 360 ] , cl[ 360 ];          //Arrays to load the sine wave.

void setup() {

  Wire.begin();           // SCL(3) and SDA(3) by default in Tiva C.
  Wire.setModule(0);      // Changing to SCL(0)and SDA(0),(PB_2 and PB_3). 

  analogWrite(GREEN_LED,25);        //led 10% on.
// Create a sine table of 360 points:
  for ( int i = 0; i <= 360; i++ ) {
    int c = sin( i * 3.141592 / 180 ) * 2047 + 2048;
    ch[ i ] = int( c / 256 );      // the 4 most significant bits.
    cl[ i ] = c - ch[ i ] * 256;   // the 8 least significant bits.

void loop() {
  for ( int i = 0; i < 360; i=i+3 ) {     //Only 120 points are used.
    //Fast Mode Write Command.
    Wire.write( ch[ i ] );        // the 4 most significant bits.
    Wire.write( cl[ i ] );        // the 8 least significant bits.

This is the final result.


The DSO Nano is very handy because fits anywhere close to my desktop computer and

has become an excellent and inexpensive monitor for debugging.

DSO Nano screen capture of a  simulated ECG wave (using the same hardware):



Working with C and Direct Registers (and Ports) Manipulation

Thanks to the page:

Where the professor Valvano, from University of Texas at Austin, teach how to Develop Embedded Systems with the ARM M 4 Processor (Tiva C LaunchPad).

The chapters are mainly designed to work in C but, with some adjusts, the Energía environment does pretty good.

To enable Direct Register Manipulation we need to include in Energía the hardware register definitions.

Just write at the beginning of your code:

#include     <tm4c123gh6pm.h>

This file is located in: C:\energia-0101E0015\hardware\lm4f\cores\lm4f\inc

I just made a copy and put it in: C:\energia-0101E0015\hardware\lm4f\libraries\tm4c123gh6pm

Notice that the file was copied inside a folder created with the same name.

(Surely there is a path to be included in Enegía to do this in a more elegant way).

Now you can use the Valvano’s examples in the Energía IDE, just remember to split the code appearing inside the main() function in two parts:

  – The configuration code goes inside the setup() function of Energía.

  – And the code running continuously is located inside the loop() function of Energía.

Is also possible to include Assembly code in Energía, but it needs another post.


Wiring the AD7801 8-Bits Parallel Digital to Analog Converter

A parallel DAC with 8 Bits is chosen to make the data transfer very fast.

Found the AD7801  at Mouser, the problem: (No DIP Package).

OK, let’s do some SMT work. With the DAC ordered and a  20 contact SOIC-to-DIP adapter.

…some SMT manual soldering…Breadboard-adapter-AD7801_02

A wiring diagram to connect the AD7801 to the Tiva C LaunchPad:


The AD7801, once soldered and wired, is very easy to operate. Simply put a new data in the PORTB and toggle PORTA bit 2 to produce a low pulse in the WR signal.

Did a A Quick-Ref of the chip:


Then I had to study  Valvano’s code to understand how to deal with the Direct Register (and Ports) Manipulation.

First began to do the I/O Ports setup using the Direct Register manipulation, this part is not necessary, you can use Arduino code in Energía to do it. But was a good opportunity to learn  some details of the the ARM  Cortex M 4.

Finally, the code used to generate the fast data transfer between Tiva C launchpad and the AD7801:

/*AD7801_FastDAC.ino 18 APR 2015

Testing the Tiva C LaunchPad and the AD7801 (Parallel Input 8-Bit DAC).
Using the PORTB to write the 8-Bit data.
Using PORTA bit 2 for the write signal (WR).

6 kHz    POINTS=256   ==>  1,536 Mega-samples/sec.
96 kHz   POINTS=16    ==>  1,536 Mega-samples/sec.
Note: faster if offset is a char.( 1,9 Mega-samples/sec.)

#include  <tm4c123gh6pm.h>    // TM4C123GE6PM Register Definitions.
#include  <math.h>            // To calculate the sine table.

// bits 7-0 of port B address (Data).
#define ldata     (*((volatile unsigned long *)0x400053FC))
// bit 2 of port A address (WR signal).
#define wrsignal  (*((volatile unsigned long *)0x40004010))

#define POINTS    256    // Wave points.(256 max. to keep offset as char type)
#define PEAKVAL   128    // Wave Amplitud (128 max, inside 8-Bits range)
#define OFFSET    128    // Center of the wave (128 for full 8-Bits span).

int sintable[POINTS];    // Array to load the sin table data.
int offset=0;           // index to point the data inside sintable[].

void setup(){


  // Fill the sin table with POINTS samples:
  for ( int i = 0; i <= POINTS; i++ ) {
    sintable[i] = sin( i * 3.141592 * 2 / POINTS ) * (PEAKVAL-1) + OFFSET ;


void loop(){
    //Write data to the AD7801

    ldata= sintable[offset];        // Load value in the port B.
    wrsignal= 0;                    // WR signal to low.
    wrsignal= 4;                    // WR signal to high
    if((POINTS-offset)<=0)offset=0; // Keep offset in range.

  //  delayMicroseconds(2);           // To experiment different frequencies.

Subroutine to initialize port B all pins output.
Port B is used to output the data.
void PortB_Init(void){
  volatile unsigned long delay;
  SYSCTL_RCGC2_R |= 0x02;          // 1) activate Port B clock
  delay = SYSCTL_RCGC2_R;          // allow time for clock to stabilize
                                   // 2) no need to unlock PB7-0
  GPIO_PORTB_AMSEL_R &= ~0xFF;     // 3) disable analog functionality on PB7-0
  GPIO_PORTB_PCTL_R = 0x00000000;  // 4) configure PB7-0 as GPIO
  GPIO_PORTB_DIR_R |= 0xFF;        // 5) set PB7-0 as outputs
  GPIO_PORTB_AFSEL_R &= ~0xFF;     // 6) disable alt funct on PB7-0
  GPIO_PORTB_DR8R_R |= 0xFF;       // enable 8 mA drive on PB7-0
  GPIO_PORTB_DEN_R |= 0xFF;        // 7) enable digital I/O on PB7-0

Subroutine to initialize port A pin 2 as output.
PA2 is used to drive the WR signal of the DAC.
void PortA_Init(void){
  volatile unsigned long delay;
  SYSCTL_RCGC2_R |= 0x01;           // 1) activate clock for Port A
  delay = SYSCTL_RCGC2_R;           // allow time for clock to start
                                    // 2) no need to unlock PA2 
  GPIO_PORTA_PCTL_R &= ~0x00000F00; // 3) regular GPIO 
  GPIO_PORTA_AMSEL_R &= ~0x04;      // 4) disable analog function on PA2 
  GPIO_PORTA_DIR_R |= 0x04;         // 5) set direction to output 
  GPIO_PORTA_AFSEL_R &= ~0x04;      // 6) regular port function 
  GPIO_PORTA_DEN_R |= 0x04;         // 7) enable digital port PA2
//End of code.

The complete assembly:


Two screenshots, thanks to the DSO Nano’s image capture function:

 A 6  kHz sine wave using POINTS= 256

and  a 95 kHz sine wave with POINTS= 16 .

The transfer speed is 1.536.000 samples/second.



Next steps:

Now we have a Sine Wave Generator, but the microcontroller is busy with this simple task.

If we need to do additional tasks like:

  • Change the frequency and (or) the amplitude on the fly.
  • Show  those values in a display.
  • Receive commands or transmit parameters serially.

 We need to use interruptions…

Thanks for reading Arduining blog.