problem using do pin 6to13 to control relays

I need to control a 8 relay module using arduino uno pins from 6 to 13.
I connected the rely module to +5 pin each relay input pin to a arduino pin.
Each relay should stay excited for 15 millis.
Then I wrote a test program, which is a portion of my real program.
To avoid to stack cpu waiting for each relay timing I read the starting time and then I check if the current time value is bigger then starting time plus the 15 millis. To achieve this I used subroutines.

Now what happens is the I can see the 3 first relay that are turned on and off but not the other 5.
To check if the pins and the relay card are ok I have inserted a direct write to to the pins and I could see that the electronic is ok.
From the serial print it seems that the logic works, but …
I cannot understand the behavior of my program.
Any idea from this great forum?

thanks in advance

const int rele_eject = 6;              // arduino pin
const int rele_ball_counter = 7;
const int rele_ball_counter_reset = 8;
const int rele_dieci_plus = 9;
const int rele_cento_plus = 10;
const int rele_nuova_partita = 11;
const int rele_bandierine_giu = 12;
const int rele_dummy = 13;

int test = 0;
int cnt = 0;

unsigned long rele_timing = 15;
unsigned long tempi [16] = {0};

unsigned long starting_timing [16] = {0};
unsigned long currentMillis = 0;




void setup() {
  // put your setup code here, to run once:
  pinMode (rele_eject, OUTPUT);                 // espelle pallina
  pinMode (rele_ball_counter, OUTPUT);
  pinMode (rele_ball_counter_reset, OUTPUT);
  pinMode (rele_dieci_plus, OUTPUT);
  pinMode (rele_cento_plus, OUTPUT);
  pinMode (rele_nuova_partita, OUTPUT);
  pinMode (rele_bandierine_giu, OUTPUT);         // ripristina le bandierine
  pinMode (rele_dummy, OUTPUT);
  Serial.begin(9600);
  // resetta i rele
  digitalWrite(rele_eject, HIGH);
  digitalWrite(rele_ball_counter, HIGH);
  digitalWrite(rele_ball_counter_reset, HIGH);
  digitalWrite(rele_dieci_plus, HIGH);
  digitalWrite(rele_cento_plus, HIGH);
  digitalWrite(rele_nuova_partita, HIGH);
  digitalWrite(rele_bandierine_giu, HIGH);
  digitalWrite(rele_dummy, HIGH);
}

void loop() {
  // put your main code here, to run repeatedly:
  for (cnt = 0; cnt < 9; cnt ++)
  { eccita_rele (cnt);
    delay (1000);
  }
  // delay (1000);

  /*
    digitalWrite(rele_eject, LOW);
    delay (500);

    digitalWrite(rele_ball_counter, LOW);
    delay (500);
    digitalWrite(rele_ball_counter_reset, LOW);
    digitalWrite(rele_dieci_plus, LOW);
    delay (500);
    digitalWrite(rele_cento_plus, LOW);
    delay (500);
    digitalWrite(rele_nuova_partita, LOW);
    delay (500);
    digitalWrite(rele_bandierine_giu, LOW);
    delay (500);
    digitalWrite(rele_ball_counter, LOW);
    delay (500);
    digitalWrite(rele_dummy, LOW);

    delay (500);
  */

  spegni_rele ();

}
void  eccita_rele(int rele) {
  digitalWrite(rele, LOW);  //aziona il rele di in chiamata
  tempi[rele] = millis  ();
  Serial.print ("rele  ");
  Serial.print (rele);
  Serial.print (" ");
  Serial.println (tempi [rele]);
  //scrive il tempo di inizio

}


// *****************************

void spegni_rele () {
  currentMillis = millis ();
  Serial.print (" tempo ");
  Serial.println (currentMillis);

  for (cnt = 0; cnt < 15; cnt++)
  {

    if (tempi[cnt] > 0)     // determina se spegnere
    { if ((currentMillis - tempi[cnt]) >= rele_timing)     // determina se spegnere
      { digitalWrite(cnt, HIGH);  //spegne il rele
        tempi [cnt] = 0;
        Serial.print (cnt);
        delay (1000);
      }
    }
  }
}
// *****************************

Now what happens is the I can see the 3 first relay that are turned on and off but not the other 5.

There is confusion between pin numbers and index numbers.

Your relays are on pins 6 through 13. When your turn on “for” loop iterates from 0 to 8, you only are turning on 6,7,8.

There are several ways of fixing this. Here’s one suggestion.

For the turn on, try changing

for (cnt = 0; cnt < 8; cnt ++)
  { eccita_rele (cnt);
    delay (1000);
  }
void  eccita_rele(int rele) {
  digitalWrite(rele + 6, LOW);  //aziona il rele di in chiamata
  tempi[rele] = millis  ();
  Serial.print ("rele  ");
  Serial.print (rele);
  Serial.print (" ");
  Serial.println (tempi [rele]);
  //scrive il tempo di inizio

}

For the turn off, I don’t understand the use of 15 indexes.

//unsigned long tempi [16] = {0};
unsigned long tempi [8] = {0};

Try

void spegni_rele () {
  currentMillis = millis ();
  Serial.print (" tempo ");
  Serial.println (currentMillis);

  for (cnt = 0; cnt < 8; cnt++)
  {

    if (tempi[cnt] > 0)     // determina se spegnere
    { if ((currentMillis - tempi[cnt]) >= rele_timing)     // determina se spegnere
      { digitalWrite(cnt + 6, HIGH);  //spegne il rele
        tempi [cnt] = 0;
        Serial.print (cnt);
        delay (1000);
      }
    }
  }
}

many thanks!
When you see the solution you discover that it always a stupid mistake but you were blind!

the reason for the 15 is because in the full program I will control more relays and I just copied a part of it.

Bravo e grazie
:slight_smile: :slight_smile: :slight_smile: