rc_receive.c File Reference

This file decodes the values coming from the RC module on the UI board from 4 channels. More...

Go to the source code of this file.

Functions

float rcx_get_chan (RCX_CHAN chan)
 Returns the current pulse width of the given channel.
float rcx_get_chan_0 (void)
 Gets the pulse width of channel 0.
float rcx_get_chan_1 (void)
 Gets the pulse width of channel 1.
float rcx_get_chan_2 (void)
 Gets the pulse width of channel 2.
float rcx_get_chan_3 (void)
 Gets the pulse width of channel 3.
void rcx_init (int chan_0, int chan_1, int chan_2, int chan_3)
 Initializes the rc channels.
void rcx_isr (void)
 The interrupt service routine for the rc module.
void rcx_update (RCX_CHAN chan, int curr, int cap_value, int flag_overflow)
 Updates the given channel from a capture register.

Variables

static volatile RCX_DATA rcx_chans [RCX_LAST]
 An array of the rc channels.
static int rcx_is_init = 0
 Whether or not this module has been initialized with rcx_init yet.
static int rcx_read [RCX_LAST]
 Array indicating whether we are using a given channel.

Detailed Description

This file decodes the values coming from the RC module on the UI board from 4 channels.

To use:

Example hardware setup of Timer:

  // *******************************************************************************
  // RC Receive Setup
  // *******************************************************************************
  PINSEL1 &= ~(3<<12); //p0.22 clear
  PINSEL1 &= ~(3<<22); //p0.27 clear
//  PINSEL1 &= ~(3<<0); //p0.16  clear
//  PINSEL1 &= ~(3<<26); //p0.29 clear
  PINSEL1 |= (2<<12); //p0.22 cap0
  PINSEL1 |= (2<<22); //p0.27 cap1
//  PINSEL1 |= (3<<0); //p0.16 cap2
//  PINSEL1 |= (2<<26); //p0.29 cap3
  T0IR = 0xFF;
  T0CCR |= (1<<0)|(1<<1)|(1<<2); //cap0 interrupt on RE (rising edge) and FE (falling edge)
  T0CCR |= (1<<3)|(1<<4)|(1<<5); //cap1 interrupt on RE (rising edge) and FE (falling edge)
//  T0CCR |= (1<<6)|(1<<7)|(1<<8); //cap2 interrupt on RE (rising edge) and FE (falling edge)
//  T0CCR |= (1<<9)|(1<<10)|(1<<11); //cap3 interrupt on RE (rising edge) and FE (falling edge)
  T0MR0 = (60000000/100)-1; //10ms       
  T0MCR = (1<<0)|(1<<1); // Match Control Reg: Interrupt(b0) and Reset(b1) on MR0;
  T0TCR = 1;   // Timer0 Enable
Author:
Nicolas Williamson
Jason Cortell
Date:
April 12, 2010

Definition in file rc_receive.c.


Function Documentation

float rcx_get_chan ( RCX_CHAN  chan  ) 

Returns the current pulse width of the given channel.

Parameters:
chan The RCX_CHAN to read from.
Returns:
Pulse width as a floating point number, or 0.0 if the module hasn't been initialized or we aren't using that channel.

Definition at line 82 of file rc_receive.c.

References error_occurred(), rcx_is_init, rcx_read, and RCX_DATA::value.

Referenced by rcx_get_chan_0(), rcx_get_chan_1(), rcx_get_chan_2(), and rcx_get_chan_3().

00083 {
00084   if (rcx_is_init){
00085     if (rcx_read[chan]){
00086       return (float)(rcx_chans[chan].value>>14);
00087     } else {
00088       error_occurred(ERROR_RCX_BAD_CHAN);
00089       return 0.0;
00090     }
00091   } else {
00092     error_occurred(ERROR_RCX_NINIT);
00093     return 0.0;
00094   }
00095 }

float rcx_get_chan_0 ( void   ) 

Gets the pulse width of channel 0.

Returns:
The pulse with of channel 0 as a floating point number, or 0.0 if the module hasn't been initialized.

Definition at line 102 of file rc_receive.c.

References rcx_get_chan().

00102 {return rcx_get_chan(RCX_CHAN_0);} 

float rcx_get_chan_1 ( void   ) 

Gets the pulse width of channel 1.

Returns:
The pulse with of channel 1 as a floating point number, or 0.0 if the module hasn't been initialized.

Definition at line 108 of file rc_receive.c.

References rcx_get_chan().

00108 {return rcx_get_chan(RCX_CHAN_1);}

float rcx_get_chan_2 ( void   ) 

Gets the pulse width of channel 2.

Returns:
The pulse with of channel 2 as a floating point number, or 0.0 if the module hasn't been initialized.

Definition at line 114 of file rc_receive.c.

References rcx_get_chan().

00114 {return rcx_get_chan(RCX_CHAN_2);}

float rcx_get_chan_3 ( void   ) 

Gets the pulse width of channel 3.

Returns:
The pulse with of channel 3 as a floating point number, or 0.0 if the module hasn't been initialized.

Definition at line 120 of file rc_receive.c.

References rcx_get_chan().

00120 {return rcx_get_chan(RCX_CHAN_3);}

void rcx_init ( int  chan_0,
int  chan_1,
int  chan_2,
int  chan_3 
)

Initializes the rc channels.

Must call this function before any others for proper operation.

Parameters:
chan_0 1 to read from channel 0 (RCIN0) or 0.
chan_1 1 to read from channel 1 (RCIN1) or 0.
chan_2 1 to read from channel 2 (RCIN2) or 0.
chan_3 1 to read from channel 3 (RCIN3) or 0.

Definition at line 58 of file rc_receive.c.

References RCX_DATA::overflows, RCX_DATA::prev, rcx_is_init, rcx_read, RCX_DATA::start, and RCX_DATA::value.

00059 {
00060   int i = 0;
00061   volatile RCX_DATA* data;
00062   for (i = 0; i < RCX_LAST; i++){
00063     data = &rcx_chans[i];
00064     data->prev = -1;
00065     data->start = 0;
00066     data->value = 0;
00067     data->overflows = 0;
00068   }
00069   rcx_read[0] = chan_0;
00070   rcx_read[1] = chan_1;
00071   rcx_read[2] = chan_2;
00072   rcx_read[3] = chan_3;
00073   rcx_is_init = 1;
00074 }

void rcx_isr ( void   ) 

The interrupt service routine for the rc module.

This function is called when timer0 causes an interrupt, either from a capture or a match. If it is a capture event, that channel's data is updated.

Definition at line 128 of file rc_receive.c.

References RCX_DATA::overflows, rcx_read, and rcx_update().

00129 {
00130   int i;
00131   int interrupts = T0IR;
00132   int cap_0 = T0CR0;
00133   int cap_1 = T0CR1;
00134   int cap_2 = T0CR2;
00135   int cap_3 = T0CR3;
00136   int pins = FIO0PIN;
00137   int lvl_0 = pins & (1<<22);
00138   int lvl_1 = pins & (1<<27);
00139   int lvl_2 = pins & (1<<16);
00140   int lvl_3 = pins & (1<<29);
00141   int flag_cap_0 = interrupts & (1<<4);
00142   int flag_cap_1 = interrupts & (1<<5);
00143   int flag_cap_2 = interrupts & (1<<6);
00144   int flag_cap_3 = interrupts & (1<<7);
00145   int flag_overflow = interrupts & (1<<0);
00146   T0IR = flag_overflow | flag_cap_0 | flag_cap_1 | flag_cap_2 | flag_cap_3; //clear interrupts
00147   
00148   if (flag_overflow){
00149     for (i = 0; i < RCX_LAST; i++){
00150       rcx_chans[i].overflows++;
00151     }
00152   }
00153   if (flag_cap_0 && rcx_read[0]){
00154     rcx_update(RCX_CHAN_0, lvl_0, cap_0, flag_overflow);
00155   }
00156   if (flag_cap_1 && rcx_read[1]){
00157     rcx_update(RCX_CHAN_1, lvl_1, cap_1, flag_overflow);
00158   }
00159   if (flag_cap_2 && rcx_read[2]){
00160     rcx_update(RCX_CHAN_2, lvl_2, cap_2, flag_overflow);
00161   }
00162   if (flag_cap_3 && rcx_read[3]){
00163     rcx_update(RCX_CHAN_3, lvl_3, cap_3, flag_overflow);
00164   } 
00165   
00166 //  VICVectAddr = 0; //for __irq
00167   
00168 }

void rcx_update ( RCX_CHAN  chan,
int  curr,
int  cap_value,
int  flag_overflow 
)

Updates the given channel from a capture register.

Parameters:
chan The channel to update.
curr The level (0 = low, >0 = high) of the signal
cap_value The value of the timer's capture register.
flag_overflow The timer overflow flag.

Definition at line 177 of file rc_receive.c.

References error_occurred(), RCX_DATA::overflows, RCX_DATA::prev, RCX_DATA::start, and RCX_DATA::value.

Referenced by rcx_isr().

00178 {
00179   static int coeff = 4;
00180   int new_value;
00181   volatile RCX_DATA* data = &rcx_chans[chan];
00182 
00183   if (flag_overflow){
00184     if (cap_value > T0MR0 / 2){ //overflow happened after capture
00185       data->overflows--;
00186     }
00187   }
00188 
00189   if (!data->prev && curr){ //Capture channel has gone from low to high
00190     data->start = cap_value; //rcx_initial_time_0 = T0CR0;
00191   } else if (data->prev && !curr){ //Capture channel has gone from high to low
00192     //find pulse width
00193     new_value = (data->overflows * T0MR0) + cap_value - data->start;    
00194     //add pulse width to average
00195     if (data->value == 0){ //init average
00196       data->value = new_value<<14; 
00197     } else if (new_value > 0) { //average new data
00198       data->value = data->value - (data->value >> coeff) + (new_value << (14-coeff));
00199     }
00200 
00201   } else { //undefined operation - either both low or both high <- BAD
00202     error_occurred(ERROR_RCX_BAD_LVLS);
00203   }
00204   data->overflows = 0;
00205   data->prev = curr;//actual current pin level.
00206 }


Variable Documentation

volatile RCX_DATA rcx_chans[RCX_LAST] [static]

An array of the rc channels.

Definition at line 46 of file rc_receive.c.

int rcx_is_init = 0 [static]

Whether or not this module has been initialized with rcx_init yet.

Definition at line 47 of file rc_receive.c.

Referenced by rcx_get_chan(), and rcx_init().

int rcx_read[RCX_LAST] [static]

Array indicating whether we are using a given channel.

0 = no, 1 = yes.

Definition at line 45 of file rc_receive.c.

Referenced by rcx_get_chan(), rcx_init(), and rcx_isr().

Generated on Tue Jun 29 16:36:15 2010 by  doxygen 1.6.3