Pages: 1 [2]   Go Down
Author Topic: Arduino due / ppm  (Read 2887 times)
0 Members and 1 Guest are viewing this topic.
Offline Offline
Newbie
*
Karma: 5
Posts: 29
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Ok, you really wants the same code back? Please test it, i dont have an Due now. But hope this problem isnt one, when i have my own.
Get the Lib from ivanseidel/DueTimer
and test this:

Code:
#include <DueTimer.h>

#define chanel_number 8
#define default_servo_value 1500
#define PPM_FrLen 22500
#define PPM_PulseLen 300
#define sigPin 10
#define onState 1

int ppm[chanel_number];

void doit(){
  static boolean state = true;
  if(state){
    digitalWrite(sigPin, onState);
    Timer3.attachInterrupt(doit).setPeriod(PPM_PulseLen);
    state = false;
  } else {
    static byte cur_chan_numb;
    static unsigned int calc_rest;
   
    digitalWrite(sigPin, !onState);
    state = true;
 
    if(cur_chan_numb >= chanel_number){
      cur_chan_numb = 0;
      calc_rest = calc_rest + PPM_PulseLen;
      Timer3.attachInterrupt(doit).setPeriod(PPM_FrLen - calc_rest);
      calc_rest = 0;
    } else {
      Timer3.attachInterrupt(doit).setPeriod(ppm[cur_chan_numb] - PPM_PulseLen);
      calc_rest = calc_rest + ppm[cur_chan_numb];
      cur_chan_numb++;
    }
  }     
}

void setup(){
  for (int i = 0; i < chanel_number; i++){
    ppm[i] = default_servo_value;
  }
  pinMode(sigPin, OUTPUT);
  digitalWrite(sigPin, !onState);
  Timer3.attachInterrupt(doit).start(1000);
}

void loop(){
  while(1){ }
}
Logged

USA
Offline Offline
Newbie
*
Karma: 0
Posts: 13
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

Thank you very much for your help, I will be able to check the code on Friday (I do not have an osciloscope at home  smiley-cry ).

Here is what i would like to learn to do on the arduino due ( in green is the equivalent code for the arduino uno):

1. Setup a timer on the due & Start a timer  
  cli();
  TCCR1A = 0;                        // set entire TCCR1 register to 0
  TCCR1B = 0;
  OCR1A = 100;                     // compare match register
  TCCR1B |= (1 << WGM12);   // turn on CTC mode
  TIMSK1 |= (1 << OCIE1A);    // enable timer compare interrupt
  sei();


2. Set a presacaler
  TCCR1B |= (1 << CS11);    // 8 prescaler: 0,5 microseconds at 16mhz

3. Change the match register (trigger)
  OCR1A = XXX // what every value i decide

4. Run into a loop every time the match register is reached
  ISR(TIMER1_COMPA_vect){ code }

Is it possible to do ?
« Last Edit: December 11, 2013, 09:03:56 pm by Francois » Logged

Offline Offline
Newbie
*
Karma: 5
Posts: 29
View Profile
 Bigger Bigger  Smaller Smaller  Reset Reset

First, if u have an other Arduino, i use this sketch on a Uno for fast bugfixing:

Code:
#define channumber 7 //How many channels have your radio?
int value[channumber];

void setup()
{
Serial.begin(57600); //Serial Begin
pinMode(3, INPUT); //Pin 3 as input
}
void loop()
{
while(pulseIn(3, LOW) < 5000){} //Wait for the beginning of the frame
// while(pulseIn(3, HIGH) < 5000){} //alt for invert signal
for(int x=0; x<=channumber-1; x++)//Loop to store all the channel position
{
value[x]=pulseIn(3, LOW);
// value[x]=pulseIn(3, HIGH); //alt for invert signal
}
for(int x=0; x<=channumber-1; x++)//Loop to print and clear all the channel readings
{
Serial.print(value[x]); //Print the value
Serial.print(" ");
value[x]=0; //Clear the value afeter is printed
}
Serial.println(""); //Start a new line
}
Just hang pin 3 from this one to ppm-out on Due an connect ground together.

and the other points, look to stimmers code too:

Quote
1. Setup a timer on the due & Start a timer  
Code:
REG_PIOB_PDR = 1<<25; // disable PIO, enable peripheral
  REG_PIOB_ABSR= 1<<25; // select peripheral B
  REG_TC0_WPMR=0x54494D00; // enable write to registers
//REG_TC0_CMR0=0b00000000000010011100010000000000; // set channel mode register (see datasheet)
  REG_TC0_CMR0=0b00000000000001101100010000000000; // alternative CMR for inverted output
  REG_TC0_RC0=100000000; // counter period
  REG_TC0_CCR0=0b101;    // start counter
  REG_TC0_IER0=0b00010000; // enable interrupt on counter=rc
  REG_TC0_IDR0=0b11101111; // disable other interrupts

Quote
2. Set a presacaler
not sure, think its inside this part, the TCCLKS, look in datasheet at page 869, Table 37-1 and page 904
Code:
REG_TC0_CMR0=0b00000000000001101100010000000000;

Quote
3. Change the match register (trigger)
Code:
REG_TC0_RC0= XXX

Quote
4. Run into a loop every time the match register is reached
Code:
void TC0_Handler() { code }

greetings
« Last Edit: December 12, 2013, 04:03:57 am by Sijjim » Logged

Pages: 1 [2]   Go Up
Jump to: