Millis() affect my other code

Hello

So i have a piece of code and i find out some strange things

In one project(with several .cpp and .h file), the second millis() could impact my result while if i delete that duration=millis(); the result is what i want.
in another project(with no .cpp and .h file), the second millis() will not have any impact on my result.

Can anyone give me some hint on it?
get me crazy to find out that BUG

   while(1){
      if(testStage==1){
        testStage = 2;
        duration = millis();  //start the record the time.
      }else if(testStage==2){
          testStage = 3; 
          duration = millis();  //delete or not delete this sentence will have a impact for checkRelayStatus()
                                       //in one of my sketch while no impact in another one
      }else if(testStage==3){
        val = checkRelayStatus(relayNum);
        Serial.println(val,BIN);
        delay(100);
        if(millis()-duration>=2000){
          testStage = 2;
          relayNum++;
        }
      }
  }

some other strange things
seems that i cannot add any other code in that if(testStage==2)
otherwise the result is't what i want

else if(testStage==2){
          testStage = 3;
          testStage = 3;    //I cannot add this
          testStage = 3;    //i canot add this too
        //  duration = millis();    
          Serial.println("There is a bug");  //and this too
      }

right now I don't think it's a bug in that part, I think it's a bug from some where else.
But just cannot target where it is.
I use mega2560 and i only use up 8% of the program storage space and 7% of dynamic memory

What is the undesired impact?

Hey

Thanks for your reply,

I had more items in that case, but i just delete them,when debug
That's the reason why you can see no need the if(testStage==2).

basically, it will impact the result of checkRelayStatus(relayNum);

the reuslt of that function will not behave as expected if i add one more sentence in that part.

Trying to post all my project. it just include some other .cpp and .h file

Attached is my complete code for that sketch

I use mega2560

And i tested that bug part in setup code.

Basically, i think it's somewhere else that have a impact on that code.

But it's kind of hard for me to target that problem.

Much appreciate if you guys can give me some hint on it

Kevin

display.cpp (7.68 KB)

display.h (7.62 KB)

font.h (40.8 KB)

hal.cpp (6.51 KB)

hal.h (1.84 KB)

pinMap.h (2.54 KB)

remoteControl.ino (9.63 KB)

test.cpp (3.49 KB)

test.h (515 Bytes)

VEML6040.cpp (2.54 KB)

VEML6040.h (1.39 KB)

Thanks Delta_G

I hope that attached code is OK

as i said, add more line is just for test

And i find out if i add more than one line
then the result will not be what i want

ledStatus:0
relayStatus:1

while if i only have one line here, the result would be

led Relay Status:1

since both ledStaus and relayStatus should be the same

below is another sketch that i test those function separately and they works as i expected with the same test condition

#define LED_1 A12

#define LED_2 A7
#define LED_3 A8
#define LED_4 A10
#define LED_5 A6
#define LED_6 A5
#define LED_7 A11
#define LED_8 A9

#define RD_RELAY1 36
#define RD_RELAY2 31
#define RD_RELAY3 33
#define RD_RELAY4 30
#define RD_RELAY5 37
#define RD_RELAY6 34
#define RD_RELAY7 35
#define RD_RELAY8 32 


#define LED_ON  1
#define LED_OFF 0
#define LED_SENSOR_ACTIVE 100
#define LED_SENSOR_DEACTIVE 1000
#define SENSOR_ACTIVE_THRESHOLD   60
#define SENSOR_DEACTIVE_THRESHOLD 500


#define READ_RELAY_FAIL   0X01
#define CHECK_RELAY_FAIL  0X02

#define RELAY_TEST_FAIL   0X01
#define RELAY_TEST_PASS   0x02

#define DISABLE           0X01
#define ENABLE            0X02

#define LED_GREEN 0x01
#define LED_RED   0x02

uint8_t checkRelayResult[9]={0x00,0x01,0x03,0x05,0x09,0x11,0x21,0x41,0x81};
uint8_t ledBuf[]={LED_1,LED_2,LED_3,LED_4,LED_5,LED_6,LED_7,LED_8};
uint8_t relayBuf[8]={RD_RELAY1,RD_RELAY2,RD_RELAY3,RD_RELAY4,RD_RELAY5,RD_RELAY6,RD_RELAY7,RD_RELAY8};
void setup() {
  // put your setup code here, to run once:
  pinMode(45,OUTPUT);
  digitalWrite(45,HIGH);
  Serial.begin(115200);
}

uint16_t readADC(uint16_t analogPort){
  uint16_t temp=0,sum,maxVal=0,minVal=1024;
  for(char i=0;i<10;i++){
    temp=analogRead(analogPort);
    sum+=temp;
    if(maxVal<temp)
      maxVal=temp;
    if(minVal>temp)
      minVal= temp;
    delay(2);
  }
  sum-=(minVal+maxVal);
  sum>>=3;
  return sum;
}

boolean LEDStateJudge(uint16_t ledValue){
  uint16_t value_H,value_L;
  value_H = LED_SENSOR_ACTIVE+SENSOR_ACTIVE_THRESHOLD;
  value_L = LED_SENSOR_ACTIVE-SENSOR_ACTIVE_THRESHOLD;
  if((ledValue<=LED_SENSOR_ACTIVE))
    return LED_ON;
  value_H = LED_SENSOR_DEACTIVE+SENSOR_DEACTIVE_THRESHOLD;
  value_L = LED_SENSOR_DEACTIVE-SENSOR_DEACTIVE_THRESHOLD;
  if((ledValue>=value_L)&&(ledValue<=value_H))
    return LED_OFF;
  return LED_OFF;
}
boolean readLEDStatus(uint16_t whichLED){  
  uint16_t temp;
  boolean result=0;
  temp = readADC(whichLED);
  result = LEDStateJudge(temp);
  return result;
}


boolean readRelay(uint8_t whichRelay){
    return digitalRead(whichRelay);
}
//check all the relay status together
uint8_t checkAllRelayStatus(void){
  uint8_t ledStatus=0;
  uint8_t relayStatus=0;
  
  for(char i=0;i<8;i++){
    ledStatus>>=1;
    relayStatus>>=1;
    if(readLEDStatus(ledBuf[i])!=0){
      ledStatus|=0x80;
    }
    if(readRelay(relayBuf[i])!=0)
      relayStatus|=0x80;
  }
  //Serial.println(ledStatus,BIN);
 // Serial.println(relayStatus,BIN);

  
  if(relayStatus!=ledStatus){
    Serial.print("Fail: ALL the LED status is:");
    Serial.println(ledStatus,BIN);
    Serial.print("Fail: ALL the relay status is:");
    Serial.println(relayStatus,BIN);
    return READ_RELAY_FAIL;
  }
  Serial.print("PASS: ALL the relay status is:");
  Serial.println(relayStatus,BIN);
  
  return relayStatus;
}


uint8_t checkRelayStatus(uint8_t whichRelay){
  uint8_t ledStatus=0;
  uint8_t relayStatus=0;
  uint8_t temp=0;
  for(char i=0;i<8;i++){
    ledStatus>>=1;
    relayStatus>>=1;
    if(readLEDStatus(ledBuf[i])!=0){
      ledStatus|=0x80;
    }
    if(readRelay(relayBuf[i])!=0)
      relayStatus|=0x80;
  }
  if(ledStatus==relayStatus){
      Serial.print("led Relay Status:");
      Serial.println(ledStatus,BIN);
      return relayStatus;
  }else{
     Serial.print("ledStatus:");
     Serial.println(ledStatus,BIN);
     Serial.print("relayStatus:");
     Serial.println(relayStatus,BIN);
  }
}

void loop() {
  // put your main code here, to run repeatedly:
  uint16_t adc=0;
  uint8_t val = 0;
  uint8_t testStage = 1;
  uint8_t relayNum=0;
  unsigned long duration = millis();
   while(1){
      if(testStage==1){
        testStage = 2;
        //some other code here
        duration = millis();  //start the record the time.
      }else if(testStage==2){
          testStage = 3;
          //some other code here
          duration = millis();
      }else if(testStage==3){
        val = checkRelayStatus(relayNum);
        Serial.println(val,BIN);
        delay(100);
        if(millis()-duration>=2000){
          testStage = 2;
          relayNum++;
        }
      }
  }

  checkRelayStatus(1);
  delay(500);
  Serial.println("---");
}

Behaviour where adding or removing code unexpectedly affects how the application behaves is usually due to memory issues.

Writing outside the boundaries of an array is one, extensive use of String (capital S) another one; there might be more

Can't look at your code at the moment.

yuan2017:
But it's kind of hard for me to target that problem.

IMHO it is rather unreasonable to expect someone to find a needle in your 40k haystack of code.

Presumably you were testing your code as you developed each piece of it and you had a recent version of the program that worked properly and then you made some small change that broke it?

What is the difference between the last working version and the first non-working version?

...R

So in that piece of code.

void loop() {
  // put your main code here, to run repeatedly:
  uint16_t adc=0;
  uint8_t val = 0;
  uint8_t testStage = 1;
  uint8_t relayNum=0;
  unsigned long duration = millis();
   while(1){
      if(testStage==1){
        testStage = 2;
        //some other code here
        duration = millis();  //start the record the time.
      }else if(testStage==2){
          testStage = 3;
          //some other code here
          duration = millis();
      }else if(testStage==3){
        val = checkRelayStatus(relayNum);
        Serial.println(val,BIN);
        delay(100);
        if(millis()-duration>=2000){
          testStage = 2;
          relayNum++;
        }
      }
  }

  checkRelayStatus(1);
  delay(500);
  Serial.println("---");
}

I'm trying to do some thing in step 1 and step2 and then, I will try to read out the relayStatus in step3.
Normally, the result should be pass from Srial port and if i test it individually in another sketch the result is Pass while if i add this piece of code into my project, it just simply failed the relayStatus check.

Hey

Thanks you all
I had figured out the problem.

I defined below code in one place

#define LED_2 2
#define LED_3 3
#define LED_4 4
#define LED_5 5
#define LED_6 6
#define LED_7 7
#define LED_8 8

while i also defined it in another place with different value

#define LED_2 A7
#define LED_3 A8
#define LED_4 A10
#define LED_5 A6
#define LED_6 A5
#define LED_7 A11
#define LED_8 A9

that makes conflict and probably this is why if add one more line, the result is totally different
Seems that it will use another defined value

Would be great if someone can explain the theory a little bit

#define name value

locks the value to that name so the code cannot change it later.

when you then use
#define name different_value
you have violated the rule.

@CrossRoads

In that case the compiler will complain. If it did not complain, it was in different files and it is allowed.

I think that you should understand state machines better. It's not required to put another for loop into loop(), because loop() is already called forever. If you increment the state variable unconditionally, all state code will be performed without any delay, making the state variable and handling superfluous and useless.

yes it's in different .h file

Really takes me quite a lot of time to figure out this problem -:frowning:

put a while into loop is just for debug, I should add some comment on it so that you will not misunderstanding it