4 Handles the 8 bits and 16 bits AVR timer.
9 Copyright 2008, 2009 Michel Pollet <buserror@gmail.com>
11 This file is part of simavr.
13 simavr is free software: you can redistribute it and/or modify
14 it under the terms of the GNU General Public License as published by
15 the Free Software Foundation, either version 3 of the License, or
16 (at your option) any later version.
18 simavr is distributed in the hope that it will be useful,
19 but WITHOUT ANY WARRANTY; without even the implied warranty of
20 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 GNU General Public License for more details.
23 You should have received a copy of the GNU General Public License
24 along with simavr. If not, see <http://www.gnu.org/licenses/>.
28 #include "avr_timer.h"
30 static avr_cycle_count_t avr_timer_compa(struct avr_t * avr, avr_cycle_count_t when, void * param)
32 avr_timer_t * p = (avr_timer_t *)param;
33 avr_raise_interrupt(avr, &p->compa);
34 return p->tov_cycles ? 0 : p->compa_cycles ? when + p->compa_cycles : 0;
37 static avr_cycle_count_t avr_timer_compb(struct avr_t * avr, avr_cycle_count_t when, void * param)
39 avr_timer_t * p = (avr_timer_t *)param;
40 avr_raise_interrupt(avr, &p->compb);
41 return p->tov_cycles ? 0 : p->compb_cycles ? when + p->compb_cycles : 0;
44 static avr_cycle_count_t avr_timer_tov(struct avr_t * avr, avr_cycle_count_t when, void * param)
46 avr_timer_t * p = (avr_timer_t *)param;
47 avr_raise_interrupt(avr, &p->overflow);
49 if (p->compa_cycles && p->tov_cycles > p->compa_cycles)
50 avr_cycle_timer_register(avr, p->compa_cycles, avr_timer_compa, p);
51 if (p->compb_cycles && p->tov_cycles > p->compb_cycles)
52 avr_cycle_timer_register(avr, p->compb_cycles, avr_timer_compb, p);
53 return when + p->tov_cycles;
56 static uint8_t avr_timer_tcnt_read(struct avr_t * avr, avr_io_addr_t addr, void * param)
58 //avr_timer_t * p = (avr_timer_t *)param;
59 // made to trigger potential watchpoints
60 return avr_core_watch_read(avr, addr);
64 * The timers are /always/ 16 bits here, if the higher byte register
65 * is specified it's just added.
67 static uint16_t _timer_get_ocra(avr_timer_t * p)
69 return p->io.avr->data[p->r_ocra] |
70 (p->r_ocrah ? (p->io.avr->data[p->r_ocrah] << 8) : 0);
72 static uint16_t _timer_get_ocrb(avr_timer_t * p)
74 return p->io.avr->data[p->r_ocrb] |
75 (p->r_ocrbh ? (p->io.avr->data[p->r_ocrbh] << 8) : 0);
78 static void avr_timer_configure(avr_timer_t * p, uint32_t clock, uint32_t top)
80 uint32_t ocra = _timer_get_ocra(p);
81 uint32_t ocrb = _timer_get_ocrb(p);
82 float fa = clock / (float)(ocra+1), fb = clock / (float)(ocrb+1);
83 float t = clock / (float)(top+1);
84 float frequency = p->io.avr->frequency;
86 p->compa_cycles = p->compb_cycles = p->tov_cycles = 0;
88 printf("%s-%c clock %d top %d a %d b %d\n", __FUNCTION__, p->name, clock, top, ocra, ocrb);
90 p->tov_cycles = frequency / t; // avr_hz_to_cycles(frequency, t);
91 printf("%s-%c TOP %.2fHz = cycles = %d\n", __FUNCTION__, p->name, t, (int)p->tov_cycles);
93 if (ocra && ocra <= top) {
94 p->compa_cycles = frequency / fa; // avr_hz_to_cycles(p->io.avr, fa);
95 printf("%s-%c A %.2fHz = cycles = %d\n", __FUNCTION__, p->name, fa, (int)p->compa_cycles);
97 if (ocrb && ocrb <= top) {
98 p->compb_cycles = frequency / fb; // avr_hz_to_cycles(p->io.avr, fb);
99 printf("%s-%c B %.2fHz = cycles = %d\n", __FUNCTION__, p->name, fb, (int)p->compb_cycles);
102 if (p->tov_cycles > 1)
103 avr_cycle_timer_register(p->io.avr, p->tov_cycles, avr_timer_tov, p);
105 if (p->compa_cycles > 1)
106 avr_cycle_timer_register(p->io.avr, p->compa_cycles, avr_timer_compa, p);
107 if (p->compb_cycles > 1)
108 avr_cycle_timer_register(p->io.avr, p->compb_cycles, avr_timer_compb, p);
112 static void avr_timer_write(struct avr_t * avr, avr_io_addr_t addr, uint8_t v, void * param)
114 avr_timer_t * p = (avr_timer_t *)param;
119 avr_core_watch_write(avr, addr, v);
120 long clock = avr->frequency;
122 // only can exists on "asynchronous" 8 bits timers
123 if (avr_regbit_get(avr, p->as2))
126 uint8_t cs = avr_regbit_get_array(avr, p->cs, ARRAY_SIZE(p->cs));
128 printf("%s-%c clock turned off\n", __FUNCTION__, p->name);
129 avr_cycle_timer_cancel(avr, avr_timer_tov, p);
130 avr_cycle_timer_cancel(avr, avr_timer_compa, p);
131 avr_cycle_timer_cancel(avr, avr_timer_compb, p);
135 uint8_t mode = avr_regbit_get_array(avr, p->wgm, ARRAY_SIZE(p->wgm));
136 uint8_t cs_div = p->cs_div[cs];
137 uint32_t f = clock >> cs_div;
139 printf("%s-%c clock %d, div %d(/%d) = %d ; mode %d\n", __FUNCTION__, p->name, clock, cs, 1 << cs_div, f, mode);
140 switch (p->wgm_op[mode].kind) {
141 case avr_timer_wgm_normal:
142 avr_timer_configure(p, f, (1 << p->wgm_op[mode].size) - 1);
144 case avr_timer_wgm_ctc: {
145 avr_timer_configure(p, f, _timer_get_ocra(p));
147 case avr_timer_wgm_fast_pwm: {
148 avr_raise_irq(p->io.irq + TIMER_IRQ_OUT_PWM0, _timer_get_ocra(p));
149 avr_raise_irq(p->io.irq + TIMER_IRQ_OUT_PWM1, _timer_get_ocra(p));
152 printf("%s-%c unsupported timer mode wgm=%d (%d)\n", __FUNCTION__, p->name, mode, p->wgm_op[mode].kind);
156 static void avr_timer_reset(avr_io_t * port)
158 avr_timer_t * p = (avr_timer_t *)port;
159 avr_cycle_timer_cancel(p->io.avr, avr_timer_tov, p);
160 avr_cycle_timer_cancel(p->io.avr, avr_timer_compa, p);
161 avr_cycle_timer_cancel(p->io.avr, avr_timer_compb, p);
166 static avr_io_t _io = {
168 .reset = avr_timer_reset,
171 void avr_timer_init(avr_t * avr, avr_timer_t * p)
174 printf("%s timer%c created OCRA %02x OCRAH %02x\n", __FUNCTION__, p->name, p->r_ocra, p->r_ocrah);
176 // allocate this module's IRQ
177 p->io.irq_count = TIMER_IRQ_COUNT;
178 p->io.irq = avr_alloc_irq(0, p->io.irq_count);
179 p->io.irq_ioctl_get = AVR_IOCTL_TIMER_GETIRQ(p->name);
180 p->io.irq[TIMER_IRQ_OUT_PWM0].flags |= IRQ_FLAG_FILTERED;
181 p->io.irq[TIMER_IRQ_OUT_PWM1].flags |= IRQ_FLAG_FILTERED;
183 avr_register_io(avr, &p->io);
184 avr_register_vector(avr, &p->compa);
185 avr_register_vector(avr, &p->compb);
187 avr_register_io_write(avr, p->cs[0].reg, avr_timer_write, p);
190 * Even if the timer is 16 bits, we don't care to have watches on the
191 * high bytes because the datasheet says that the low address is always
194 avr_register_io_write(avr, p->r_ocra, avr_timer_write, p);
195 avr_register_io_write(avr, p->r_ocrb, avr_timer_write, p);
197 avr_register_io_read(avr, p->r_tcnt, avr_timer_tcnt_read, p);