]> www.fi.muni.cz Git - tinyboard.git/blobdiff - projects/step-up/pwm.c
Experimental step-up driver for chain of 5630 LEDs.
[tinyboard.git] / projects / step-up / pwm.c
index f16aaa3175440cd44b84abafb3b477baa5d74e31..b93a4fab8502039d73d811c69b96592725c5bad5 100644 (file)
@@ -1,5 +1,6 @@
 #include <avr/io.h>
 #include <avr/interrupt.h>
+#include <avr/power.h>
 #include <util/delay.h>
 #include <util/atomic.h>
 
  * Counts from 0 to 0xFF, without OCR1C compare.
  */
 
+volatile unsigned char pwm_enabled;
+
 static void inline enable_pll()
 {
        /* Async clock */
-       PLLCSR = _BV(PLLE);
+       PLLCSR = _BV(PLLE) | _BV(LSM);
 
        /* Synchronize to the phase lock */
        _delay_us(100);
@@ -24,43 +27,48 @@ static void inline enable_pll()
 
 void init_pwm()
 {
-       enable_pll();
+       pwm_enabled = 0;
+       power_timer1_enable();
 
-       TCCR1 = _BV(CTC1) | _BV(CS10);  // no clock prescaling
+       TCCR1 = _BV(CTC1) | _BV(CS11);  // pll_clk/2
        GTCCR = _BV(COM1B1) | _BV(PWM1B);
 
        OCR1C = PWM_MAX;
        OCR1B = 0;              // initial stride is 0
 
-       DDRB  &= ~_BV(PB4); // tristate it
+       DDRB &= ~(_BV( PB4 ));
        PORTB &= ~_BV(PB4); // set to zero
 }
 
-#if 0
 void susp_pwm()
 {
-       unsigned char i;
-
-       for (i = 0; i < N_PWMLEDS; i++)
-               pwm[i] = 0;
-
-       DDRB &= ~(_BV( PB1 ) | _BV( PB3 ) | _BV( PB5 ));
-       TCCR1D = TCCR1C = TCCR1B = TCCR1A = 0;
+       DDRB &= ~(_BV( PB4 ));
+       PORTB &= ~(_BV( PB4 ));
+       TCCR1 = 0;
        TIMSK = 0;
        TIFR = 0;
 
        PLLCSR &= ~(_BV(PLLE) | _BV(PCKE));
 }
-#endif
 
 void pwm_off()
 {
        OCR1B = 0;
        DDRB &= ~_BV(PB4);
+
+       PLLCSR &= ~(_BV(PLLE) | _BV(PCKE));
+       power_timer1_disable();
+       pwm_enabled = 0;
 }
 
 void pwm_set(uint8_t stride)
 {
        OCR1B = stride;
-       DDRB |= _BV(PB4);
+
+       if (!pwm_enabled) {
+               power_timer1_enable();
+               enable_pll();
+               DDRB |= _BV(PB4);
+               pwm_enabled = 1;
+       }
 }