Well, it's not pretty, but...
#include <TinyGPS.h>
TinyGPS gps;
static void gpsdump(TinyGPS &gps);
static bool feedgps();
static void print_float(float val, float invalid, int len, int prec);
static void print_int(unsigned long val, unsigned long invalid, int len);
static void print_date(TinyGPS &gps);
static void print_str(const char *str, int len);
volatile int datcol=0, val=0, sum = 0;
volatile long tim=0, bigsum=0, bigind=0, bigsum1=0, oldbigsum1=0, resvalsum=0, ckint1=0, holdcons0=0;
long cons0=0, tmptim=0, llong=0, llat=0;
volatile long rtc=0, gpsc=0, savrtc=0, savgps=0;
int ar0=0, ar1=0;
long deadtime=0;
int agewarn=0, GPSPWR=7, EQINT=8, RTCINT=9, GPSINT=10, CS=2, CLK=3, UD=4, EQINTLED=32;
int x=0, inByte0='0', inByte1='0', inByte2='0', sval=0;
volatile int inByteTot=0, newinByteTot=0;
unsigned long evArray[4]={0,0,0,0};
int evarraycount=0;
void setup() {
Serial.begin(115200);
Serial2.begin(9600);
pinMode(GPSPWR,OUTPUT);
pinMode(EQINT,INPUT);
pinMode(EQINTLED,OUTPUT);
pinMode(CS,OUTPUT);
pinMode(UD,OUTPUT);
pinMode(CLK,OUTPUT);
inByteTot=40;
chgpot();
digitalWrite(GPSPWR,HIGH);
digitalWrite(EQINTLED,LOW);
attachInterrupt(EQINT,eq,CHANGE);
digitalWrite(EQINT,HIGH);
attachInterrupt(RTCINT,rtcsub,RISING);
attachInterrupt(GPSINT,gpssub,RISING);
analogReadResolution(12);
}
void loop()
{
int incomingByte=0;
int ii=0;
bool newdata = false;
unsigned long start = millis();
// Every minute we print an update
bigsum=0;
bigind=0;
bigsum1=0;
cons0=0;
holdcons0=0;
while (millis() - start < 60000)
{
if (datcol>0){goto checkeq;} //break out of loop searching for gps data if EQ interrupt triggered
if (Serial.available()){ //Need to change potentiometer setting
digitalWrite(EQINTLED,LOW);
inByte0=Serial.read();
if (Serial.available()) {
inByte1=Serial.read();
if (Serial.available()){
inByte2=Serial.read();
}
}
newinByteTot=(inByte2-'0')+ (10*(inByte1-'0')) + (100*(inByte0-'0'));
inByte0='0';
inByte1='0';
inByte2='0';
if(newinByteTot>10 && newinByteTot<110){
inByteTot=newinByteTot; //only make change if sent a reasonable input
}
chgpot();
} //End of loop changing pot setting
if (feedgps()){
newdata = true;
}
ar0=analogRead(0);
delay(4);
ar1=analogRead(1);
bigsum+= ar0;
bigsum1+= ar1;
if(ar0==0)
{
cons0++;
if(cons0>holdcons0)
{
holdcons0=cons0;
}
}
else
{
cons0=0;
}
delay(1);
bigind++;
} //end of while loop that completes every minute
gpsdump(gps);
checkeq:
if (datcol>0)
{ ckint1=analogRead(1); // check to see if interrupt was random spike or
delay(2); // if amplified signal is actually significantly larger than
ckint1=analogRead(1); // previous background
if(abs((8*ckint1)-oldbigsum1)<100) goto cancel; // get out if not real EQ
detachInterrupt(EQINT);
digitalWrite(EQINTLED,HIGH);
Serial.print("< EQ start ");
Serial.print(savgps);
Serial.print(" gps and ");
Serial.print(savrtc);
Serial.println(" rtc >");
while(ii<1000)
{
ii++;
Serial.print("< ");
sum = 0;
for (int j = 0; j < 8; j++)
{
sum += analogRead(0);
delay(2);
}
Serial.print(sum);
Serial.print(" ");
tmptim=millis();
Serial.print(tmptim);
Serial.print(" ");
Serial.print(rtc);
Serial.print(" ");
sum=analogRead(1);
delay(10);
sum = 0;
for (int j = 0; j < 8; j++)
{
sum += analogRead(1);
delay(2);
}
Serial.print(sum);
Serial.print(" ");
tmptim=millis();
Serial.print(tmptim);
Serial.print(" ");
Serial.print(rtc);
Serial.print(" ");
Serial.print(gpsc);
Serial.println(" >");
} //End of while ii<1000 loop
Serial.println("< xxx xxx EQ Data Ended xxx xxx >"); // Last
evArray[evarraycount & 3] = millis(); //update time of most recent EQ int
evarraycount++; //move pointer to next array element
if (((millis() - evArray[evarraycount & 3] ) < 1800000) && (inByteTot<110)){//if oldest EQ int < 30 m old and pot not near its limit, change pot
inByteTot++;
chgpot();
}
datcol=0;
digitalWrite(EQINTLED,LOW);
//attachInterrupt(EQINT,eq,HIGH); Replace this line by next two for
attachInterrupt(EQINT,eq,CHANGE); //less touchy interrupts
digitalWrite(EQINT,HIGH);
/* flag++;
if(flag<4){
attachInterrupt(EQINT,eq,HIGH);
}*/
} //end datcol>0 loop
cancel:
if(agewarn>0 && (millis()-deadtime)>600000) //GPS down AND down >10 min
{
digitalWrite(GPSPWR,LOW); //power cycle
delay(10000);
digitalWrite(GPSPWR,HIGH);
agewarn=0; //reset alarm trip
}
} //main loop
static void gpsdump(TinyGPS &gps)
{
float flat, flon;
unsigned long age, date, time, chars = 0;
unsigned short sentences = 0, failed = 0;
gps.f_get_position(&flat, &flon, &age);
Serial.print("< ");
if (datcol > 0){ return;}
llat=100000*flat;
print_int(llat,TinyGPS::GPS_INVALID_F_ANGLE,8);
if (datcol > 0){ return;}
llong=100000*flon;
print_int(llong,TinyGPS::GPS_INVALID_F_ANGLE,9);
if (datcol > 0){ return;}
Serial.print(age);
Serial.print(" ");
if (datcol > 0){ return;}
if(age<10000)
{
agewarn=0;
}
if(age>10000 && agewarn==0)
{
deadtime=millis(); //get time of first noticing dead gps
agewarn=1;
}
print_date(gps);
gps.stats(&chars, &sentences, &failed);
Serial.println(" >");
}
static void print_int(unsigned long val, unsigned long invalid, int len)
{
char sz[32];
if (val == invalid)
strcpy(sz, "*******");
else
sprintf(sz, "%ld", val);
sz[len] = 0;
for (int i=strlen(sz); i<len; ++i)
sz[i] = ' ';
if (len > 0)
sz[len-1] = ' ';
Serial.print(sz);
feedgps();
}
static void print_date(TinyGPS &gps)
{
int year;
int loopi;
byte month, day, hour, minute, second, hundredths;
unsigned long age;
gps.crack_datetime(&year, &month, &day, &hour, &minute, &second, &hundredths, &age);
if (age == TinyGPS::GPS_INVALID_AGE)
Serial.print("******* ******* ");
else
{
char sz[32];
sprintf(sz, "%02d%02d%02d %02d %02d %02d %02d ",
month, day, year, hour, minute, second,hundredths);
Serial.print(sz);
}
Serial.print(age);
Serial.print(" ");
Serial.print(rtc);
Serial.print(" ");
Serial.print(gpsc);
resvalsum=analogRead(2);
resvalsum=0;
delay(20);
for (int jjj = 0; jjj < 10; jjj++)
{
resvalsum+=analogRead(2); //Pot wiper
delay(2);
}
Serial.print(" ");
Serial.print(resvalsum);
Serial.print(" ");
Serial.print(holdcons0);
Serial.print(" ");
Serial.print(bigsum/bigind);
Serial.print(" ");
Serial.print(bigsum1/bigind);
Serial.print(" ");
Serial.print(inByteTot);
feedgps();
oldbigsum1=bigsum1;
}
static void print_str(const char *str, int len)
{
int slen = strlen(str);
for (int i=0; i<len; ++i)
Serial.print(i<slen ? str[i] : ' ');
feedgps();
}
static bool feedgps()
{
while (Serial2.available())
{
if (gps.encode(Serial2.read()))
return true;
}
return false;
}
void chgpot()
{
x=0;
detachInterrupt(EQINT);
digitalWrite(CS,LOW); //Low to change resistance, high otherwise
digitalWrite(UD,LOW); //UD Low = Decrement = lower voltage, High = Increment
digitalWrite(CLK,LOW); //CLK->High, CLK->Low as fast as possible = change resistance 1 unit
while(x<140){ //Run Vout of Pot all the way to 0 V min to ensure known starting pos
digitalWrite(CLK,HIGH);
digitalWrite(CLK,LOW);
x++;
delay(1);
}
digitalWrite(EQINTLED,HIGH);
x=0;
digitalWrite(UD,HIGH);
digitalWrite(CLK,LOW);
while(x<inByteTot){
digitalWrite(CLK,HIGH);
digitalWrite(CLK,LOW);
x++;
delay(1);
}
attachInterrupt(EQINT,eq,CHANGE); //less touchy interrupts
digitalWrite(EQINT,HIGH);
digitalWrite(EQINTLED,LOW);
digitalWrite(CS,HIGH); // No more writes to dig pot for now
}
void eq()
{
savrtc=rtc;
savgps=gpsc;
tim = millis();
val=digitalRead(EQINT);
if(val==1){
datcol=1;
}
}
void gpssub()
{
gpsc++;
rtc=0;
}
void rtcsub()
{
rtc++;
}
Again, it will work fine for a few minutes ( = a few loops) and then report zeros for the A2 read, called resvalsum in the code. After one to several loops of that, it will return to normal for a minute or a few, and then back to zeros, alternating like that as long as I leave it running. When I program the MEGA with this, it's fine.