Receiver reader

Hi
I have the following code which prints 500-530 all the time. I checked with oscilloscope and the width between the first falling edge and the next rising edge varies between 1.0ms and 2,0ms. Does anyone see the error in my code?

Cheers Kim


| | | | | | |
| | | | | | |
|| || |___| |

there is 8 spaces where width varies. ) tops with constant width and then there is a sync pause which is about 11ms

The illustration above is for the first 3 channels....

#define icpPin 8    // this interrupt handler must use pin 8
#define TICKS_PER_uS 2    // number of timer ticks per microsecond
#define MAX_CHANNELS    8   // maximum number of channels we can store 
#define SYNC_GAP_LEN (3000 * TICKS_PER_uS) // we assume a space at least 3000us is sync (note clock counts in 0.5 us ticks)
volatile unsigned int Pulses[ MAX_CHANNELS + 1]; // array holding channel pulses width value in microseconds
volatile uint8_t  Channel; // number of channels detected so far in the frame (first channel is 1)
volatile uint8_t State;   // this will be one of the following states:
#define NOT_SYNCHED_state  0    // the system is not synched so the data is random
#define ACQUIRING_state  1 // one sync pulse detected but not all channels have been received
#define READY_state     2 // synched and all channel data is valid
boolean stateChanged1 =  true;
boolean stateChanged2 =  true;
boolean stateChanged3 =  true;
boolean stateChanged4 =  true;





 
ISR(TIMER1_CAPT_vect){
   if(! bit_is_set(TCCR1B ,ICES1)){ // was falling edge detected ?  
      TCNT1 = 0;   // reset the counter
    if(Channel <= MAX_CHANNELS) {
        Pulses[Channel++] = ICR1/ TICKS_PER_uS;  // store pulse length as microsoeconds
     }
   }
  
   else {  // rising  edge was detected  
     TCNT1 = 0;   // reset the counter
     if(ICR1 >= SYNC_GAP_LEN){   // is the space between pulses big enough to be the SYNC
        Channel = 1; // if so, reset the channel counter to 1 
        if(State == NOT_SYNCHED_state)
            State = ACQUIRING_state;  // this is the first sync pulse, we need one more to fill the channel data array
        else if( State == ACQUIRING_state)    
          State = READY_state;     // this is the second sync so flag that channel data is valid
     }   
   }
  
   TCCR1B ^= _BV(ICES1);     // toggle bit value to trigger on the other edge   
}

void setup()
{
  delay(5000);
  Serial.begin(9600);     // initialize serial communication with computer
  Serial.println("No startet serieporten");
 
 
  pinMode(icpPin,INPUT);
  Channel = 1; 
  State = NOT_SYNCHED_state;
  TCCR1A = 0x00;   // COM1A1=0, COM1A0=0 => Disconnect Pin OC1 from Timer/Counter 1 -- PWM11=0,PWM10=0 => PWM Operation disabled
  TCCR1B = 0x02;   // 16MHz clock with prescaler means TCNT1 increments every .5 uS (cs11 bit set
  TIMSK1 = _BV(ICIE1);   // enable input capture interrupt for timer 1
 
 
 
  
}

int getChannelPulseWidth( uint8_t channel) {
  // this is the access function for channel data
  int result; 
  if( (State == READY_state)  && (channel > 0) && (channel <=  MAX_CHANNELS)  ) {
     cli(); //disable interrupts
     result =  Pulses[channel] ;
     sei(); // enable interrupts
  }
  else
     result = 0;  // return 0 if no valid pulse is available 

  return result;
 
}

void loop()   // run over and over again
{
// print the decoder state
   if(State == NOT_SYNCHED_state){
     //stateChanged = true;
     if (stateChanged1){
        Serial.println("The decoder has not detected a synch pulse ");  
        // receiver.setTxReception(false);
        stateChanged1 = false;
        }
   } 
   else if ( State == ACQUIRING_state){
     //stateChanged = true;
      if (stateChanged2){
        Serial.println("The decoder has detected one synch pulse and has started filling channel data"); 
         //receiver.setTxReception(false); 
         stateChanged2 = false;
         }
   }
   else if( State == READY_state){
     //stateChanged = true;
      if (stateChanged3){
         Serial.println("The decoder is synched and the channel data is valid"); 
          stateChanged3 = false;
     }
     Serial.print("Channel 1 pulsewidt is: ");
     Serial.println(getChannelPulseWidth(1));
    
    // Serial.print("Channel 2 pulsewidt is: ");
     // Serial.println(getChannelPulseWidth(2));
    
     //receiver.setTxReception(true);
   } 
   else{
     //stateChanged = true;
     if (stateChanged4){
       Serial.println("Unknown decoder state, this should never happen!");
       //receiver.setTxReception(false);
       stateChanged4 = false;
     }
    
   } 
   delay(1000);
}

Hi Kim :slight_smile:

try changing:
if(! bit_is_set(TCCR1B ,ICES1)){ // was falling edge detected ?
to
if( bit_is_set(TCCR1B ,ICES1)){ // was rising edge detected ?

removing the ! before bit_is_set allows the code measures time from falling up to the rising edges

Hmm
That didn't work for some reason, need to do some more debugging I guess....

What output pulse widths you are seeing printed to the serial port?

Will get back to u monday avro... Then I will have my whole thing up running again...

Cheers Kim

Tx on:
Channel1 pulsewidt is: 123
Channel2 pulsewidt is: 36
Channel1 pulsewidt is: 143
Channel2 pulsewidt is: 293
Channel1 pulsewidt is: 71
Channel2 pulsewidt is: 167
Channel1 pulsewidt is: 391
Channel2 pulsewidt is: 234
Channel1 pulsewidt is: 137
Channel2 pulsewidt is: 54
Channel1 pulsewidt is: 170
Channel2 pulsewidt is: 133
Channel1 pulsewidt is: 296
Channel2 pulsewidt is: 60

Tx off:
Channel2 pulsewidt is: 237
Channel1 pulsewidt is: 262
Channel2 pulsewidt is: 550
Channel1 pulsewidt is: 89
Channel2 pulsewidt is: 348
Channel1 pulsewidt is: 136
Channel2 pulsewidt is: 206
Channel1 pulsewidt is: 158
Channel2 pulsewidt is: 344
Channel1 pulsewidt is: 246
Channel2 pulsewidt is: 110
Channel1 pulsewidt is: 513
Channel2 pulsewidt is: 286

bit_is_set(TCCR1B ,ICES1):
The decoder has not detected a synch pulse
The decoder has not detected a synch pulse
The decoder has not detected a synch pulse
The decoder has not detected a synch pulse
The decoder has not detected a synch pulse
The decoder has not detected a synch pulse
The decoder has not detected a synch pulse
The decoder has not detected a synch pulse

Well this doesnt make sence to me at all...

You could try a test using an arduino pin to drive the input. Write a sketch that pulses a pin at a know rate, say a sequence of pulses of alternating 1ms and 2ms pulses with a delay in between of sat 500 us. Connect the output to the pin 8 through a 1k resistor and see if you get more sensible results.

did that...

#define icpPin 8    // this interrupt handler must use pin 8
#define TICKS_PER_uS 2    // number of timer ticks per microsecond
#define MAX_CHANNELS    8   // maximum number of channels we can store  
#define SYNC_GAP_LEN (3000 * TICKS_PER_uS) // we assume a space at least 3000us is sync (note clock counts in 0.5 us ticks) 
volatile unsigned int Pulses[ MAX_CHANNELS + 1]; // array holding channel pulses width value in microseconds 
volatile uint8_t  Channel; // number of channels detected so far in the frame (first channel is 1)
volatile uint8_t State;   // this will be one of the following states:
#define NOT_SYNCHED_state  0    // the system is not synched so the data is random
#define ACQUIRING_state  1 // one sync pulse detected but not all channels have been received 
#define READY_state     2 // synched and all channel data is valid 

#define outPin 7 

long previousMillis = 0;        // will store last time LED was updated
long interval = 3000;           // interval at which to blink (milliseconds)

ISR(TIMER1_CAPT_vect){ 
  if(bit_is_set(TCCR1B ,ICES1)){ // was falling edge detected ?   
    TCNT1 = 0;   // reset the counter
    if(Channel <= MAX_CHANNELS) {
      Pulses[Channel++] = ICR1 / TICKS_PER_uS;  // store pulse length as microsoeconds
    }
  }

  else {  // rising  edge was detected   
    TCNT1 = 0;   // reset the counter
    if(ICR1 >= SYNC_GAP_LEN){   // is the space between pulses big enough to be the SYNC
      Channel = 1; // if so, reset the channel counter to 1  
      if(State == NOT_SYNCHED_state)
        State = ACQUIRING_state;  // this is the first sync pulse, we need one more to fill the channel data array
      else if( State == ACQUIRING_state)     
        State = READY_state;     // this is the second sync so flag that channel data is valid
    }    
  } 

  TCCR1B ^= _BV(ICES1);     // toggle bit value to trigger on the other edge    
}

void setup()
{
  delay(2000);
  Serial.begin(9600);     // initialize serial communication with computer
  Serial.println("No startet serieporten"); 

  pinMode(outPin, OUTPUT);      // sets the digital pin as output
  pinMode(icpPin,INPUT);
  Channel = 1;  
  State = NOT_SYNCHED_state;
  TCCR1A = 0x00;   // COM1A1=0, COM1A0=0 => Disconnect Pin OC1 from Timer/Counter 1 -- PWM11=0,PWM10=0 => PWM Operation disabled 
  TCCR1B = 0x02;   // 16MHz clock with prescaler means TCNT1 increments every .5 uS (cs11 bit set
  TIMSK1 = _BV(ICIE1);   // enable input capture interrupt for timer 1




}

int getChannelPulseWidth( uint8_t channel) {
  // this is the access function for channel data
  int result;  
  if( (State == READY_state)  && (channel > 0) && (channel <=  MAX_CHANNELS)  ) {
    cli(); //disable interrupts
    result =  Pulses[channel] ;
    sei(); // enable interrupts
  }
  else
    result = 0;  // return 0 if no valid pulse is available  

  return result; 

}


void generateTx(){
 



    for (int ii=0; ii++;ii<9){
    digitalWrite(outPin, HIGH);   // sets the pin on
    delayMicroseconds(500);        // pauses for 50 microseconds      
    digitalWrite(outPin, LOW);    // sets the pin off
    delayMicroseconds(1000+ii*60);        // pauses for 50 microseconds 
  }  
}




void loop()   // run over and over again
{
  generateTx();
  // print the decoder state
  if(State == NOT_SYNCHED_state){
    Serial.println("The decoder has not detected a synch pulse ");   
    // receiver.setTxReception(false); 
  }  
  else if ( State == ACQUIRING_state){
    Serial.println("The decoder has detected one synch pulse and has started filling channel data");  
    //receiver.setTxReception(false);  
  } 
  else if( State == READY_state){
    // Serial.println("The decoder is synched and the channel data is valid");  
    if (millis() - previousMillis > interval) {
      previousMillis = millis();             // remember the last time we blinked the LED
      Serial.print("Channel1 pulsewidt is: "); 
      Serial.println(getChannelPulseWidth(1));

      Serial.print("Channel2 pulsewidt is: "); 
      Serial.println(getChannelPulseWidth(2));
    }

    //receiver.setTxReception(true); 
  }  
  else{
    Serial.println("Unknown decoder state, this should never happen!"); 
    //receiver.setTxReception(false);
    delay(1000); 
  }  
  delay(5);
}

But maybe sth is wrong in this code.... cant detect sync pulse

Kim , try changing
for (int ii=0; ii++;ii<9){
to
for (int ii=0; ii < 9; ii++){

still the same, decode has not deteced sync pulse, do u read ur emails? Do u have a dual crystallaying around?

Cheers Kim

try this:
void generateTx(){
for (int ii=0; ii< MAX_CHANNELS; ii++) {
digitalWrite(outPin, HIGH); // sets the pin on
delayMicroseconds(1000 + (ii*100) );
digitalWrite(outPin, LOW); // sets the pin off
delayMicroseconds(50); // pauses for 50 microseconds
}
delay(4); 4000 us sync gap
}

I will be logging off shortly, back on tomorrow morning, good luck