Interrupt with timing and repeat

After many googlings and going through forum posts and test sketches, I need to ask for help! Thank you to anyone that takes the time to read this.
I have a working sketch that takes ADC data and sends it out on a serial port with a delay (yeah, I know) between each transmission.
I need to incorporate code that takes a 1pps pulse (inverted) that starts a routine every 46mS 20 times then reverts back to waiting for the next pulse.
Before I incorporate the code into the larger sketch, I’ve been trying to get a functional code. The below code is supposed to:
After pulse (falling edge), trigger routine
Take current millis
When millis equals 46, serial print x
Increment x
Repeat until x equals 20.
Wait for next pulse.

What it currently gives is an incrementing value of x every second.
What have I done wrong?

int period = 46;
//int trigger = 0;
int x = 0;
//int i;
//int n=20;
int previousMillis = 0;

void setup()

{

  Serial.begin(115200);

  attachInterrupt(0, blink, FALLING);

}

void loop()
{

}

void blink() {

  unsigned long currentMillis = millis();
  //x=x+1;
  if (currentMillis - previousMillis > period) {
    previousMillis = currentMillis;
    x = x + 1;
    Serial.println(x);

  }
  if (x < 20) {
    (blink);
  } else {
    x = 0;
  }
}

What do you think this does?

    (blink);

Because it's not a function call...

You probably should read up on state machines, this is a classic example of something that's straight forward
to code up from a state-machine design.

I tweaked the code related to your suggestion as below:

 if (x < 20) {
    blink();
  } else {
    x = 0;
  }

and now I get a single digit “1”!

The state machine approach is what you want as MarkT suggests.

A possible example implementation (compiles, not tested.)

/*
 * Sketch: sketch_nov06d.ino
 */
#define NUM_EVENTS          20      //#     number of events after 1PPS pulse
#define EVENT_INTERVAL      46000ul //uS    time between successive event actions

const uint8_t pinLED = LED_BUILTIN;
const uint8_t pin1PPS = 2;

enum statesEvents
{
    ST_WAIT_1PPS=0,
    ST_RUN_EVENTS    
};

volatile bool
    beventFlag = false;
volatile uint32_t
    isrTimeEdge;
    
void setup()
{
    Serial.begin( 115200 );
    pinMode( pinLED, OUTPUT );
    pinMode( pin1PPS, INPUT_PULLUP );    
    attachInterrupt( digitalPinToInterrupt(pin1PPS), isrEvent, FALLING );

}//setup

void loop()
{
    EventSM();
    
    /*
     * do other stuff
     * .
     * .
     * .
     */
    
}//loop

void EventSM( void )
{
    static uint8_t
        evtCounter,
        stateSM = ST_WAIT_1PPS;
    static uint32_t
        timeSM;
    uint32_t 
        timeNow = micros();
        
    switch( stateSM )
    {
        case    ST_WAIT_1PPS:
            //here we wait for the 1PPS pulse
            if( beventFlag == true )
            {
                //happened; copy the time logged at the 1PPS edge 
                //into a local variable timeSM and clear the flag
                noInterrupts();
                timeSM = isrTimeEdge;
                beventFlag = false;
                interrupts();
                
                //set the event counter (i.e. 20)
                evtCounter = NUM_EVENTS;         
                
                //move to the state where we run those events       
                stateSM = ST_RUN_EVENTS;
                
            }//if
                
        break;

        case    ST_RUN_EVENTS:
            //is it time for the next event?
            if( (timeNow - timeSM) >= EVENT_INTERVAL )
            {
                //yes; save the time for the next event
                timeSM = timeNow;
                
                //do the routine
                Routine();

                //after each event, decrement the event counter
                //when it reaches zero we're done; go back to
                //the state where we look for the next 1PPS pulse
                if( --evtCounter == 0 )
                    stateSM = ST_WAIT_1PPS;
                    
            }//if
            
        break;
        
    }//switch
    
}//EventSM

void Routine( void )
{
    static bool
        bLEDState=false;

    //each time this is called it toggles the state of the 
    //built-in LED
    bLEDState ^= HIGH;
    digitalWrite( pinLED, bLEDState );

    Serial.println( "Toggle" );
    
}//Routine

void isrEvent( void )
{
    //got the 1PPS pulse; log the time and...
    isrTimeEdge = micros();
        
    //...set the flag indicating it happened
    beventFlag = true;

}//isrEvent

Blackfin,

That code is quite comprehensive. No wonder I couldn't figure it out!
The code I am going to integrate this into is quite long (by my standards) so I'll be having fun!
Thank you for your assistance

Colin

Just a quick question...
My main sketch has an interrupt that runs a calibrate routine. When this is running, will the 1pps override the routine?
Is there a way of stopping an interrupt temporarily while another routine is running?

aqcolin:
Just a quick question...
My main sketch has an interrupt that runs a calibrate routine. When this is running, will the 1pps override the routine?
Is there a way of stopping an interrupt temporarily while another routine is running?

Interrupts have priority levels and the processor will choose which to execute based on that level if more than one interrupt is pending.

You can stop interrupts or stop selected interrupts by disabling global interrupts (e.g. noInterrupts()) or by disabling individual interrupts by clearing their enable bits as appropriate.

But in order to really help we'd need to see your code.

This is the data acquisition code that I intend to combine with the 20Hz/1pps sketch you kindly provided.
I know it’s probably a mess in comparison to how an experienced coder would produce it!

//Test MCP41010 V1.08

#include <SPI.h> 
#include <Wire.h>
#include <Adafruit_ADS1015.h>

Adafruit_ADS1115 ads1(0x48); 
const int CSI = 10; // chip select pin for MCP41010Input
const int CSO = 11; // chip select pin for MCP41010Output
const int gain1 = 12;
int PotWiperVoltage = 1;
int RawVoltage = 0;
float Voltage = 0;
int centrevalue = 0;
int offsetvalue = 0;
int perstep = 0;
int shift = 0;
int offset = 128;
int upper = 27000;
int lower = 2600;
int level = 128;
int ADCread = 0;
int flag = 0;
int residual = 0; //set residual calculation value to 0
const int  buttonPin = 18; //trigger calibrate pin
int buttonState = 0; //trigger related

void setup() {
  pinMode (CSI, OUTPUT);   //set chip select pin as output
  pinMode (CSO, OUTPUT);   //set chip select pin as output
  pinMode (gain1, OUTPUT); //set gain pin as output
  digitalWrite(gain1, HIGH); // set gain high
  pinMode(buttonPin, INPUT); //set trigger as input
  Serial.begin(57600);
  SPI.begin();    
  ads1.begin();
  ads1.setGain(GAIN_TWO);
  int level = 128; //set pot halfway
  MCP41010Input(level);
  MCP41010Output(level);
}
 
void loop() {
    
 buttonState = digitalRead(buttonPin);//names the button press
   if (buttonState == HIGH) {  // if trigger is high
      calibrate(); //run calibrate routine
   } else { //otherwise run ADC
    ADCread = ads1.readADC_Differential_0_1(); // - residual;
    if (gain1 == LOW) {
      ADCread = (ads1.readADC_Differential_0_1() * 10);
    }
    Serial.print("ADS1_1 = "); 
    Serial.print(ADCread);
    Serial.println();  
    if ((ADCread > 27000 || ADCread < -27000) && gain1 == HIGH) { // if ADC goes over 27000 and gain is high
    digitalWrite(gain1, LOW); //set gain low
    }
    else if ((ADCread < 2600 && ADCread > -2600) && gain1 == LOW) { // if ADC is less than 2600 and gain is LOW
      digitalWrite(gain1, HIGH); // set gain high
    }
    }
    delay(10);  // wait a couple seconds
  }

 void calibrate(){
 Serial.println("calibrate Front");
 digitalWrite(gain1, LOW); //set gain pin LOW
 delay (200);//delay for settling
 int level = 128;
  MCP41010Input(128); // set input pot to 128
  MCP41010Output(128); // set output pot to 128
  delay(200);
  centrevalue = ads1.readADC_Differential_0_1();
  Serial.print("Centre value: \t");
  Serial.println(centrevalue);
  level = 128-50;
  MCP41010Input(78);
  delay(200);
  offsetvalue = ads1.readADC_Differential_0_1();
  Serial.print("Offset value: \t");
  Serial.println(offsetvalue);
  perstep = ((offsetvalue - centrevalue)/ 50);
  Serial.print("Step value: \t");
  Serial.println(perstep);
  delay(200);
  shift = (centrevalue / perstep);
  Serial.print("Number of pot steps required to centre output: \t");
  Serial.println(shift);
  offset = 128 + shift;
  Serial.print("Pot final value: \t");
  Serial.println(offset);
  delay(2000);
  MCP41010Input(offset);
  digitalWrite(gain1, HIGH); //set gain pin HIGH
  delay(1000);

 Serial.println("calibrate Back");
  centrevalue = ads1.readADC_Differential_0_1();
  Serial.print("Centre value: \t");
  Serial.println(centrevalue);
  level = 128-50;
  MCP41010Output(78);
  delay(200);
  offsetvalue = ads1.readADC_Differential_0_1();
  Serial.print("Offset value: \t");
  Serial.println(offsetvalue);
  perstep = ((offsetvalue - centrevalue)/ 50);
  Serial.print("Step value: \t");
  Serial.println(perstep);
  delay(200);
  shift = (centrevalue / perstep);
  Serial.print("Number of pot steps required to centre output: \t");
  Serial.println(shift);
  offset = 128 + shift;
  Serial.print("Pot final value: \t");
  Serial.println(offset);
  delay(2000);
  MCP41010Output(offset);  
 /* centrevalue = ads1.readADC_Differential_0_1();
  level = 128-50;
  MCP41010Output(128 - 50);
  delay(200);
  offsetvalue = ads1.readADC_Differential_0_1();
  perstep = ((offsetvalue - centrevalue)/ 50);
  shift = (centrevalue / perstep);
  Serial.print("Number of pot steps required to centre output: ");
  Serial.println(shift);
  offset = 128 + shift;
  MCP41010Output(offset);
  */
  delay (200);

  residual = ads1.readADC_Differential_0_1();
  Serial.print("Residual ");
  Serial.println(residual);
  if (residual <-28000 || residual >28000){
    Serial.println("*CALIBRATION FAULT*");
 // delay(5000);
  }
 
  delay(1000);

}



void MCP41010Input(byte value) 
{
  // Note that the integer vale passed to this subroutine
  // is cast to a byte
  
  digitalWrite(CSI,LOW);
  SPI.transfer(B00010001); // This tells the chip to set the pot
  SPI.transfer(value);     // This tells it the pot position
  digitalWrite(CSI,HIGH); 
}

void MCP41010Output(byte value) 
{
  // Note that the integer vale passed to this subroutine
  // is cast to a byte
  
  digitalWrite(CSO,LOW);
  SPI.transfer(B00010001); // This tells the chip to set the pot
  SPI.transfer(value);     // This tells it the pot position
  digitalWrite(CSO,HIGH); 
}

OK, so I tried to combine the 2 sketches and pretty much got nothing to work! The serial output gets “ca” and that’s the lot.
I have a calibration routine and I think I need to stop the 1PPS interrupt while it is running, but I don’t think that is the main issue.
Could someone point me in the right direction please?
I added my existing code in between //MCP41410 … //\MCP41010

/*
   Sketch: sketch_nov06d.ino
*/
#define NUM_EVENTS          20      //#     number of events after 1PPS pulse
#define EVENT_INTERVAL      47000ul //uS    time between successive event actions
int x = 0;

//MCP41410

#include <SPI.h>
#include <Wire.h>
#include <Adafruit_ADS1015.h>

Adafruit_ADS1115 ads1(0x48);
const int CSI = 10; // chip select pin for MCP41010Input
const int CSO = 11; // chip select pin for MCP41010Output
const int gain1 = 12;
int PotWiperVoltage = 1;
int RawVoltage = 0;
float Voltage = 0;
int centrevalue = 0;
int offsetvalue = 0;
int perstep = 0;
int shift = 0;
int offset = 128;
int upper = 27000;
int lower = 2600;
int level = 128;
int ADCread = 0;
int flag = 0;
int residual = 0; //set residual calculation value to 0
//const int  buttonPin = 18; //trigger calibrate pin
//int buttonState = 0; //trigger related
const uint8_t buttonPin = 18;
//\mcp41010

const uint8_t pinLED = LED_BUILTIN;
const uint8_t pin1PPS = 2;

enum statesEvents
{
  ST_WAIT_1PPS = 0,
  ST_RUN_EVENTS
};

volatile bool
beventFlag = false;
volatile uint32_t
isrTimeEdge;

void setup()
{
  Serial.begin( 115200 );
  pinMode( pinLED, OUTPUT );
  pinMode( pin1PPS, INPUT_PULLUP );
  pinMode( buttonPin, INPUT_PULLUP);
  attachInterrupt( digitalPinToInterrupt(pin1PPS), isrEvent, FALLING );
  attachInterrupt(digitalPinToInterrupt(buttonPin), calibration, LOW);

  //MCP41010

  pinMode (CSI, OUTPUT);   //set chip select pin as output
  pinMode (CSO, OUTPUT);   //set chip select pin as output
  pinMode (gain1, OUTPUT); //set gain pin as output
  digitalWrite(gain1, HIGH); // set gain high
  pinMode(buttonPin, INPUT); //set trigger as input
  //Serial.begin(57600);
  SPI.begin();
  ads1.begin();
  ads1.setGain(GAIN_TWO);
  int level = 128; //set pot halfway
  MCP41010Input(level);
  MCP41010Output(level);

  //\MCP41010

}//setup

void loop()
{
  EventSM();

  //MCP41010

  //buttonState = digitalRead(buttonPin);//names the button press
  //if (buttonState == HIGH) {  // if trigger is high
  //  calibrate(); //run calibrate routine
  //} else { //otherwise run ADC
    ADCread = ads1.readADC_Differential_0_1(); // - residual;
    if (gain1 == LOW) {
      ADCread = (ads1.readADC_Differential_0_1() * 10);
  //  }
    Serial.print("ADS1 = ");
    Serial.print(ADCread);
    Serial.println();
    if ((ADCread > 27000 || ADCread < -27000) && gain1 == HIGH) { // if ADC goes over 27000 and gain is high
      digitalWrite(gain1, LOW); //set gain low
    }
    else if ((ADCread < 2600 && ADCread > -2600) && gain1 == LOW) { // if ADC is less than 2600 and gain is LOW
      digitalWrite(gain1, HIGH); // set gain high
    }
  }

  //\MCP41010

}//loop

void EventSM( void )
{
  static uint8_t
  evtCounter,
  stateSM = ST_WAIT_1PPS;
  static uint32_t
  timeSM;
  uint32_t
  timeNow = micros();

  switch ( stateSM )
  {
    case    ST_WAIT_1PPS:
      //here we wait for the 1PPS pulse
      if ( beventFlag == true )
      {
        //happened; copy the time logged at the 1PPS edge
        //into a local variable timeSM and clear the flag
        noInterrupts();
        timeSM = isrTimeEdge;
        beventFlag = false;
        interrupts();

        //set the event counter (i.e. 20)
        evtCounter = NUM_EVENTS;

        //move to the state where we run those events
        stateSM = ST_RUN_EVENTS;

      }//if

      break;

    case    ST_RUN_EVENTS:
      //is it time for the next event?
      if ( (timeNow - timeSM) >= EVENT_INTERVAL )
      {
        //yes; save the time for the next event
        timeSM = timeNow;
        x = timeSM;
        //do the routine
        Routine();

        //after each event, decrement the event counter
        //when it reaches zero we're done; go back to
        //the state where we look for the next 1PPS pulse
        if ( --evtCounter == 0 )
          stateSM = ST_WAIT_1PPS;

      }//if

      break;

  }//switch

}//EventSM

void Routine( void )
{
  static bool
  bLEDState = false;

  //each time this is called it toggles the state of the
  //built-in LED
  bLEDState ^= HIGH;
  digitalWrite( pinLED, bLEDState );

  // Serial.println( micros() );

}//Routine

void isrEvent( void )
{
  //got the 1PPS pulse; log the time and...
  isrTimeEdge = micros();

  //...set the flag indicating it happened
  beventFlag = true;

}//isrEvent

//MCP41010

void calibration() {
  Serial.println("calibrate Front");
  digitalWrite(gain1, LOW); //set gain pin LOW
  delay (200);//delay for settling
  int level = 128;
  MCP41010Input(128); // set input pot to 128
  MCP41010Output(128); // set output pot to 128
  delay(200);
  centrevalue = ads1.readADC_Differential_0_1();
  Serial.print("Centre value: \t");
  Serial.println(centrevalue);
  level = 128 - 50;
  MCP41010Input(78);
  delay(200);
  offsetvalue = ads1.readADC_Differential_0_1();
  Serial.print("Offset value: \t");
  Serial.println(offsetvalue);
  perstep = ((offsetvalue - centrevalue) / 50);
  Serial.print("Step value: \t");
  Serial.println(perstep);
  delay(200);
  shift = (centrevalue / perstep);
  Serial.print("Number of pot steps required to centre output: \t");
  Serial.println(shift);
  offset = 128 + shift;
  Serial.print("Pot final value: \t");
  Serial.println(offset);
  delay(2000);
  MCP41010Input(offset);
  digitalWrite(gain1, HIGH); //set gain pin HIGH
  delay(1000);

  Serial.println("calibrate Back");
  centrevalue = ads1.readADC_Differential_0_1();
  Serial.print("Centre value: \t");
  Serial.println(centrevalue);
  level = 128 - 50;
  MCP41010Output(78);
  delay(200);
  offsetvalue = ads1.readADC_Differential_0_1();
  Serial.print("Offset value: \t");
  Serial.println(offsetvalue);
  perstep = ((offsetvalue - centrevalue) / 50);
  Serial.print("Step value: \t");
  Serial.println(perstep);
  delay(200);
  shift = (centrevalue / perstep);
  Serial.print("Number of pot steps required to centre output: \t");
  Serial.println(shift);
  offset = 128 + shift;
  Serial.print("Pot final value: \t");
  Serial.println(offset);
  delay(2000);
  MCP41010Output(offset);
  /* centrevalue = ads1.readADC_Differential_0_1();
    level = 128-50;
    MCP41010Output(128 - 50);
    delay(200);
    offsetvalue = ads1.readADC_Differential_0_1();
    perstep = ((offsetvalue - centrevalue)/ 50);
    shift = (centrevalue / perstep);
    Serial.print("Number of pot steps required to centre output: ");
    Serial.println(shift);
    offset = 128 + shift;
    MCP41010Output(offset);
  */
  delay (200);

  residual = ads1.readADC_Differential_0_1();
  Serial.print("Residual ");
  Serial.println(residual);
  if (residual < -28000 || residual > 28000) {
    Serial.println("*CALIBRATION FAULT*");
    // delay(5000);
  }

  delay(1000);

}



void MCP41010Input(byte value)
{
  // Note that the integer vale passed to this subroutine
  // is cast to a byte

  digitalWrite(CSI, LOW);
  SPI.transfer(B00010001); // This tells the chip to set the pot
  SPI.transfer(value);     // This tells it the pot position
  digitalWrite(CSI, HIGH);
}

void MCP41010Output(byte value)
{
  // Note that the integer vale passed to this subroutine
  // is cast to a byte

  digitalWrite(CSO, LOW);
  SPI.transfer(B00010001); // This tells the chip to set the pot
  SPI.transfer(value);     // This tells it the pot position
  digitalWrite(CSO, HIGH);
}

I think I may have found it - does my code go in the routine() subroutine?

Edit: That doesn't work either!

After a quick look, the function calibration() is an ISR and you have this:

void calibration() {
  Serial.println("calibrate Front");
.
.
.

and a whole bunch more. Note that Serial print stuff requires interrupts and interrupts are turned off while in an ISR.

You need to aim to keep the ISR short and sweet: Unless you need something done in "realtime" setting a flag that the event occurred (e.g. a falling edge on the button input) and let the mainline code see that flag and do the calibration and all its prints.

Another question: Why do you need an interrupt to process the calibration button? There's no need for the immediacy of an interrupt for a button press.

I'll have another proper look at this tomorrow. Thank you for the information.

Are you suggesting:
If button = high, set flag.
If flag, do this calibrate routine (included in main loop)
Set flag false

While calibrate is running, 1PPS ISR should be disabled/ignored. Do I need to write this in or will the calibrate routine cause it to be ignored anyway.

Hello my friend, I personally would cut the code down in to minimum blocks. First of all this practice will help you understand the processes involved inside the code. This will save you hours, if not weeks of debugging code that you don't fully comprehend at the moment. Believe me this is better than smacking your head on the keyboard in frustration.

Gates,

Thank you for that suggestion. I have had each section of code running on their own successfully. It is the combining of the codes and their interaction I'm fighting.

Colin

Thanks for your help guys. I am learning!
Whilst I haven’t integrated the calibrate routine yet, I have used a flag to perform a calculation as my original code “if (gain == LOW)” wasn’t working. This is OK now. My current issue is to do with the calculation.
I have a 16 bit ADC running in differential mode. The output goes -32767 to +32768 and works perfectly. When the low gain is triggered (the circuit reduces the output to 10%), the flag adds in a x10 multiplier to the ADC data. This in theory should allow for reading larger voltages on the same ADC. However, when low gain is triggered the value will only reach the 16 bit limit before actually reducing the value.
I have tried changing the “ADCvalue” calculation to long, unsigned long, and I’m sure another type, but it still does the same. What am I doing wrong?
ADCread is the raw ADC data
ADCvalue is the ADC data x10

/*
   Sketch: 20Hz_ADC_1.02.ino
*/
#define NUM_EVENTS          20      //#     number of events after 1PPS pulse
#define EVENT_INTERVAL      47000ul //uS    time between successive event actions
int x = 0;

#include <SPI.h>
#include <Wire.h>
#include <Adafruit_ADS1015.h>
Adafruit_ADS1115 ads1(0x48);
const int CSI = 10; // chip select pin for MCP41010Input
const int CSO = 11; // chip select pin for MCP41010Output
const int gain1 = 12;
int PotWiperVoltage = 1;
int RawVoltage = 0;
float Voltage = 0;
int centrevalue = 0;
int offsetvalue = 0;
int perstep = 0;
int shift = 0;
int offset = 128;
int upper = 27000;
int lower = 2600;
int level = 128;
int ADCread = 0;
long ADCvalue = 0;
int flag = 0;
int residual = 0; //set residual calculation value to 0
const int  buttonPin = 18; //trigger calibrate pin
int buttonState = 0; //trigger related

const uint8_t pinLED = LED_BUILTIN;
const uint8_t pin1PPS = 2;

enum statesEvents
{
  ST_WAIT_1PPS = 0,
  ST_RUN_EVENTS
};

volatile bool gainlow = false;
volatile bool
beventFlag = false;
volatile uint32_t
isrTimeEdge;

void setup()
{
  Serial.begin( 115200 );
  pinMode( pinLED, OUTPUT );
  pinMode( pin1PPS, INPUT_PULLUP );
  attachInterrupt( digitalPinToInterrupt(pin1PPS), isrEvent, FALLING );

  pinMode (CSI, OUTPUT);   //set chip select pin as output
  pinMode (CSO, OUTPUT);   //set chip select pin as output
  pinMode (gain1, OUTPUT); //set gain pin as output
  digitalWrite(gain1, HIGH); // set gain high
  pinMode(buttonPin, INPUT); //set trigger as input
  // Serial.begin(57600);
  SPI.begin();
  ads1.begin();
  ads1.setGain(GAIN_TWO);
  int level = 128; //set pot halfway
  MCP41010Input(level);
  MCP41010Output(level);

}//setup

void loop()
{
  EventSM();



  /*
     do other stuff
     .
     .
     .
  */

}//loop

void EventSM( void )
{
  static uint8_t
  evtCounter,
  stateSM = ST_WAIT_1PPS;
  static uint32_t
  timeSM;
  uint32_t
  timeNow = micros();

  switch ( stateSM )
  {
    case    ST_WAIT_1PPS:
      //here we wait for the 1PPS pulse
      if ( beventFlag == true )
      {
        //happened; copy the time logged at the 1PPS edge
        //into a local variable timeSM and clear the flag
        noInterrupts();
        timeSM = isrTimeEdge;
        beventFlag = false;
        interrupts();

        //set the event counter (i.e. 20)
        evtCounter = NUM_EVENTS;

        //move to the state where we run those events
        stateSM = ST_RUN_EVENTS;

      }//if

      break;

    case    ST_RUN_EVENTS:
      //is it time for the next event?
      if ( (timeNow - timeSM) >= EVENT_INTERVAL )
      {
        //yes; save the time for the next event
        timeSM = timeNow;
        x = timeSM;
        //do the routine
        Routine();

        //after each event, decrement the event counter
        //when it reaches zero we're done; go back to
        //the state where we look for the next 1PPS pulse
        if ( --evtCounter == 0 )
          stateSM = ST_WAIT_1PPS;

      }//if

      break;

  }//switch

}//EventSM

void Routine( void )
{
  static bool
  bLEDState = false;

  //each time this is called it toggles the state of the
  //built-in LED
  bLEDState ^= HIGH;
  digitalWrite( pinLED, bLEDState );

  // Serial.println( micros() );

  ADCread = ads1.readADC_Differential_0_1();
  /*  if (gain1 == LOW) {
      ADCread = (ads1.readADC_Differential_0_1() * 10);
    }
    Serial.print("ADC = ");
    Serial.println(ADCread);
    //  Serial.println();*/
  if (ADCread > 27000 || ADCread < -27000 ) { // if ADC goes over 27000 and gain is high
    digitalWrite(gain1, LOW); //set gain low
    // Serial.println("gain LOW");
    gainlow = true;
  }
  else if ( ADCread < 2500 && ADCread > -2500 ) { // if ADC is less than 2600 and gain is LOW
    digitalWrite(gain1, HIGH); // set gain high
    //   Serial.println("gain HIGH");
    gainlow = false;
  }
  Serial.print("ADC = ");
  ADCvalue = ADCread * 10;
  if (gainlow) {
    Serial.print("low");
    Serial.println(ADCvalue);
  } else {
    Serial.println(ADCread);
  }
  // Serial.print("ADC = ");
  // Serial.println(ADCvalue);
}//Routine

void isrEvent( void )
{
  //got the 1PPS pulse; log the time and...
  isrTimeEdge = micros();

  //...set the flag indicating it happened
  beventFlag = true;

}//isrEvent

void MCP41010Input(byte value)
{
  // Note that the integer vale passed to this subroutine
  // is cast to a byte

  digitalWrite(CSI, LOW);
  SPI.transfer(B00010001); // This tells the chip to set the pot
  SPI.transfer(value);     // This tells it the pot position
  digitalWrite(CSI, HIGH);
}

void MCP41010Output(byte value)
{
  // Note that the integer vale passed to this subroutine
  // is cast to a byte

  digitalWrite(CSO, LOW);
  SPI.transfer(B00010001); // This tells the chip to set the pot
  SPI.transfer(value);     // This tells it the pot position
  digitalWrite(CSO, HIGH);
}