Advertisement
Guest User

HDD clock

a guest
Mar 22nd, 2013
80
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C 4.98 KB | None | 0 0
  1.  
  2.  
  3.  
  4.  
  5. //___________________ Librairies & defines __________________//
  6. #include <avr/io.h>
  7. #include <util/delay.h>
  8. #include <stdlib.h>
  9. #include <avr/interrupt.h>
  10. #include <stdio.h>
  11. //RTC libs
  12. #include <Wire.h>
  13. #include <RTClib.h>
  14.  
  15.  
  16. #ifndef F_CPU
  17. #define F_CPU           16000000UL  // 16 MHz
  18. #endif
  19.  
  20.  
  21. // frequencion division
  22. #define FREQ_DIV_8      (F_CPU / 8)
  23. // #of ticks / millisec
  24. #define MILLITICK       (FREQ_DIV_8 * .001)
  25.  
  26.  
  27. //______________________ Constants and global variables_______________//
  28. const int  divisions = 180;  //a multiple of 60 to simplyfy the positioning
  29.  
  30. volatile byte LED [divisions+1]; //Array with positions where the leds should light up. in bytes so we can clock it directly in the portB register
  31.  
  32. // _____________period of the rotation of the disk
  33. int period;
  34. // ______________volatile so it will be accessible in the IRS routine
  35. volatile int positionCounter = 0;
  36.  
  37. //____________RTC declareren
  38. RTC_DS1307 RTC;
  39.  
  40. volatile boolean update; //variable to trigger update
  41.  
  42. void setup()
  43. {
  44.  
  45.   Serial.begin(115200);
  46.   Serial.println("serial is set");
  47.   //______________ RTC opzetten_____________//
  48.  // Wire.begin();
  49.   //RTC.begin();
  50.  
  51.  delay(50);
  52.   Serial.println("rtc is set");
  53. delay(50);
  54.   //________________    Set I/O ports   ______________//
  55.  
  56.   DDRL=255 ;   //PL4 pin 45 as output for servo
  57.   DDRB=255;      // pin 51 - 52 - 53 as ooutput for portb
  58.   DDRD=0;
  59.   Serial.println("IO is set");
  60. delay(50);
  61.   //___________________Init Timers_______________________//
  62.  cli(); //disable timers
  63.  
  64.  
  65.   //**********          PWM for Servo (ESC)     ****************//
  66.  
  67.   TCCR5A = (1 << COM5B1); // timer5: phase & frequency correct - pwm Clear OC1B on Compare Match
  68.   TCCR5B = (1 << WGM53)  | (1 << CS51); //prescaler 8
  69.  
  70.   ICR5 = 20000; // 20ms
  71.   OCR5B= 1500; // 1.5ms
  72.   Serial.println("servo is set");
  73.   delay(50);
  74.   //***************      Timers for disk position     *****************//
  75.  
  76.   // setup timer0 - 8bit, --> to drive the leds
  77.   TCCR2A = 0;
  78.   TCCR2B = 0;
  79.   // select CTC mode:  clear timer on compare match mode
  80.   TCCR2A = (1<< WGM21);
  81.   // select prescaler clk / 8
  82.   TCCR2B= (1<< CS21);
  83.   // enable compare interrupt
  84.   TIMSK2 = (1<<OCIE2A);
  85.  
  86.   // setup timer1 - 16bit to count the rotations and calculate the period
  87.   TCCR3B = 0;
  88.   TCCR3A = 0; // A1 registering p134
  89.   // select prescaler clk / 8
  90.   TCCR3B=(1<< CS31);
  91.   // reset timer
  92.   TCNT3 = 0;
  93.   // enable overflow interrupt
  94.   TIMSK3=(1<< TOIE3);
  95.   Serial.println("timer1 is set");
  96.   delay(50);
  97.   // stel PIN2( arduino D-input) falling edge interrupt
  98.   EICRA |= _BV(ISC21);  
  99.   EIMSK |= _BV(INT2);
  100.   Serial.println("int2 is set");
  101.   delay(50);
  102.   // set the rotational period to 0
  103.  
  104.   period = 0;
  105.  
  106.   // setup timer3 - 16bit, --> to drive time keeping function
  107.   TCCR4A = 0;
  108.   TCCR4B = 0;
  109.   // select CTC mode:  clear timer on compare match mode
  110.   TCCR4A = (1<< WGM41);
  111.   // select prescaler clk / 1024
  112.   TCCR4B= (1<< CS40)|(1<<CS42);
  113.   // enable compare interrupt
  114.   TIMSK4 = (1<<OCIE4A);
  115.  
  116.   OCR4A=6250; //400ms
  117.   Serial.println("timer4 is set");
  118.   delay(50);
  119.  sei(); //reenable interrupts
  120.   Serial.begin(9600);
  121. Serial.println("timers are set");
  122. delay(50);
  123.  
  124.  
  125.   for(int i =0; i<divisions;i++){  //Set all bytes in the array to zero
  126.     LED[positionCounter]=0;
  127.   }
  128.   Serial.println("array is empty");
  129.   //Getting out of settings mode of the ESC & Testing leds
  130.   PORTB=0b00000001;
  131.   _delay_ms(5000);
  132.   PORTB=0b00000010;
  133.   OCR5B = 2000;
  134.   _delay_ms(2000);
  135.   PORTB=0b00000100;
  136.   OCR5B = 1000;
  137.   _delay_ms(2000);
  138.   OCR5B = 2000;
  139.   PORTB=0b00000000;
  140.  
  141.  
  142.  
  143. }
  144. void loop()
  145.   {
  146.  
  147.    
  148.     if(update){
  149.       DateTime now = RTC.now();
  150.       int hours=now.hour()%12; //getting the time from 0 to 11 instead of 24 hours
  151.       int minutes= now.minute();
  152.       int seconds= now.second();
  153.  
  154.       for(int i =0; i<divisions;i++){  //clear the whole array
  155.         LED[positionCounter]=0;
  156.       }
  157.         LED[hours*15] |= 4;
  158.         LED[minutes*3] |= 2;
  159.         LED[seconds*3] |= 1;
  160.  
  161.       }
  162.       update=false;
  163.    
  164.  
  165.   }
  166.  
  167.  
  168.  
  169. ISR(INT2_vect)   //Sensor interrupt routine
  170. {
  171.   // period = nuber of ticks since last interrupt
  172.   period = TCNT3;
  173.   // if period < than to millis no rotation is possible --> discard value
  174.   // disk 7500 rpm --> 125rps -->8 millis /rotation
  175.   if(period <(2 * MILLITICK))  
  176.   {
  177.     return;
  178.   }
  179.   //reset timer to zero
  180.   TCNT3 = 0;
  181.   //8bit timer0 generates an interrupt / division --> time between interrupts = period/divisions
  182.   TCNT2 = 0;  
  183.   OCR2A = (period / divisions);
  184.   positionCounter = 25;  // set position to 25. sensor is rotated 37° to the length axis of the disk.
  185. }
  186.  
  187.  
  188.  
  189.  
  190. ISR(TIMER2_COMPA_vect) { //timer interrupt routine
  191.   positionCounter = ((positionCounter + 1) % divisions); //position with modulo division
  192.   PORTB=LED[positionCounter]; //getting the led values of the current position and clocking them in the portB output register.
  193. }
  194.  
  195. ISR(TIMER4_COMPA_vect) { //timer interrupt routine
  196.  update=true;
  197. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement