µracoli Manual Version foo

- µracoli
- User Guide
- Reference Guide

ioutil.h
1 /* Copyright (c) 2007 Axel Wachtler
2 All rights reserved.
3
4 Redistribution and use in source and binary forms, with or without
5 modification, are permitted provided that the following conditions
6 are met:
7
8 * Redistributions of source code must retain the above copyright
9 notice, this list of conditions and the following disclaimer.
10 * Redistributions in binary form must reproduce the above copyright
11 notice, this list of conditions and the following disclaimer in the
12 documentation and/or other materials provided with the distribution.
13 * Neither the name of the authors nor the names of its contributors
14 may be used to endorse or promote products derived from this software
15 without specific prior written permission.
16
17 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
18 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
21 LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22 CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23 SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24 INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25 CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26 ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27 POSSIBILITY OF SUCH DAMAGE. */
28
29 /* The function keys_debounced() use the code given in Peter Fleury's
30 avr-gcc examples. File: avrgcc-examples/debounce_keys.c */
31
32 /****************************************************************************
33 Title: Debouncing 8 Keys
34 Author: Peter Fleury <pfleury@gmx.ch> http://jump.to/fleury,
35 based on algorithm of Peter Dannegger <danni@specs.de>
36 Date: December 2003
37 Software: AVR-GCC 3.3
38 Hardware: AT90S8515 at 4 Mhz, STK200 compatible starter kit
39
40 *****************************************************************************/
41
42 /* $Id$ */
48 #ifndef IOUTIL_H
49 #define IOUTIL_H
50
51 /* === Includes ============================================================== */
52 #include <stdlib.h>
53 #include <stdio.h>
54 //#include <util/atomic.h>
55
56 #include "board.h"
57 #include "hif.h"
58 #include "timer.h"
59
60 /* === Externals ============================================================= */
61
62 /* === Types ================================================================= */
63
72 typedef struct
73 {
75 void * next;
77 uint8_t used;
79 uint8_t len;
81 uint8_t istart;
83 uint8_t iend;
85 uint8_t data[];
86 } buffer_t;
87
88
89 typedef struct
90 {
92 uint8_t nb;
94 uint8_t elsz;
96 uint8_t pool[];
97 } buffer_pool_t;
98
101 /* === Macros ================================================================ */
102
103 /* === LED Handling === */
104
108 #if defined(NO_LEDS) || defined (DOXYGEN)
109 # undef LED_NUMBER
110
111 # define LED_NUMBER (0)
112 #endif
113
114 #if defined(NO_LEDS) || defined (DOXYGEN)
115
116 # define LED_INIT() do{}while(0)
117 #elif !defined(LED_INIT)
118 # if LEDS_INVERSE == 0
119 # define LED_INIT() do{\
120 LED_DDR |= (LED_MASK); LED_PORT &= ~(LED_MASK);\
121 }while(0)
122 # else
123 # define LED_INIT() do{\
124 LED_DDR |= (LED_MASK); LED_PORT |= (LED_MASK);\
125 }while(0)
126 # endif
127 #endif /* !defined(LED_INIT)*/
128
129 #if defined(NO_LEDS) || defined (DOXYGEN)
130
135 # define LED_SET_VALUE(x) do{}while(0)
136 #elif !defined(LED_SET_VALUE)
137 # if LEDS_INVERSE == 0
138 # define LED_SET_VALUE(x) \
139 do {\
140 LED_PORT = (LED_PORT & ~LED_MASK) | ((x<<LED_SHIFT) & LED_MASK);\
141 }while(0)
142 # else
143 # define LED_SET_VALUE(x) do {\
144 LED_PORT = (LED_PORT & ~LED_MASK) | ((~x<<LED_SHIFT) & LED_MASK);\
145 }while(0)
146 # endif
147 #endif /* !defined(LED_SET_VALUE)*/
148
149 #if defined(NO_LEDS) || defined (DOXYGEN)
150
151 # define LED_GET_VALUE() 0
152 #elif !defined(LED_GET_VALUE)
153 # if LEDS_INVERSE == 0
154 # define LED_GET_VALUE() ((LED_PORT & LED_MASK) >> LED_SHIFT)
155 # else
156 # define LED_GET_VALUE() ((~LED_PORT & LED_MASK) >> LED_SHIFT)
157 # endif
158 #endif /* !defined(LED_GET_VALUE)*/
159
160
161 #if defined(NO_LEDS) || defined (DOXYGEN)
162
163 # define LED_SET(ln) do{}while(0)
164 #elif !defined(LED_SET)
165 # if LEDS_INVERSE == 0
166 # define LED_SET(ln) LED_PORT |= (_BV(ln+LED_SHIFT) & LED_MASK)
167 # else
168 # define LED_SET(ln) LED_PORT &= ~(_BV(ln+LED_SHIFT) & LED_MASK)
169 # endif
170 #endif /* !defined(LED_SET)*/
171
172
173 #if defined(NO_LEDS) || defined (DOXYGEN)
174
175 # define LED_CLR(ln) do{}while(0)
176 #elif !defined(LED_CLR)
177 # if LEDS_INVERSE == 0
178 # define LED_CLR(ln) LED_PORT &= ~(_BV(ln+LED_SHIFT) & LED_MASK)
179 # else
180 # define LED_CLR(ln) LED_PORT |= (_BV(ln+LED_SHIFT) & LED_MASK)
181 # endif
182 #endif /* !defined(LED_CLR)*/
183
184 #if defined(NO_LEDS) || defined (DOXYGEN)
185
186 # define LED_VAL(msk,val) do{}while(0)
187 #elif !defined(LED_VAL)
188 # if LEDS_INVERSE == 0
189 # define LED_VAL(msk,val) LED_PORT |= ((LED_MASK|msk) << LED_SHIFT); \
190 LED_PORT |= ~((val << LED_SHIFT)& (LED_MASK|(msk<<LED_SHIFT)) )
191 # else
192 # define LED_VAL(msk,val) LED_PORT &= ~(LED_MASK|(msk<<LED_SHIFT)); LED_PORT |= ~(val & (LED_MASK|msk))
193
194 # endif
195 #endif /* !defined(LED_VAL)*/
196
197 #if defined(NO_LEDS) || defined (DOXYGEN)
198
199 # define LED_TOGGLE(ln) do{}while(0)
200 #elif !defined(LED_TOGGLE)
201 # define LED_TOGGLE(ln) LED_PORT ^= (_BV(ln+LED_SHIFT) & LED_MASK)
202 #endif /* !defined(LED_TOGGLE)*/
203
205 #define LED_MAX_VALUE ((1<<LED_NUMBER)-1)
206
210 /* === KEY Handling === */
211
216 #if defined(NO_KEYS) || defined (DOXYGEN)
217
218 # define KEY_INIT()
219
221 # define KEY_GET() (0)
222
223 #else /* defined(NO_KEYS) || defined (DOXYGEN) */
224 # if PULLUP_KEYS != 0
225 # define PULL_MASK (MASK_KEY)
226 # else /* PULLUP_KEYS != 0 */
227 # define PULL_MASK (0)
228 # endif /* PULLUP_KEYS != 0 */
229 # if !defined KEY_INIT
230 # define KEY_INIT() do{PORT_KEY |= PULL_MASK; DDR_KEY &= ~(MASK_KEY); }while(0)
231 # endif
232 # if !defined KEY_GET
233 # if INVERSE_KEYS == 0
234 # define KEY_GET()\
235 ((PIN_KEY & MASK_KEY) >> SHIFT_KEY)
236 # else /* INVERSE_KEYS == 0 */
237 # define KEY_GET()\
238 ((~PIN_KEY & MASK_KEY) >> SHIFT_KEY)
239 # endif /* INVERSE_KEYS == 0 */
240 # endif /* !defined KEY_GET */
241 #endif /* defined(NO_KEYS) || defined (DOXYGEN) */
242
243
244
249 static inline uint8_t keys_debounced(void)
250 {
251 static uint8_t key_state; // debounced and inverted key state:
252 static uint8_t ct0, ct1; // holds two bit counter for each key
253 uint8_t i;
254
255
256 /*
257 * read current state of keys (active-low),
258 * clear corresponding bit in i when key has changed
259 */
260 i = key_state ^ KEY_GET(); // key changed ?
261
262 /*
263 * ct0 and ct1 form a two bit counter for each key,
264 * where ct0 holds LSB and ct1 holds MSB
265 * After a key is pressed longer than four times the
266 * sampling period, the corresponding bit in key_state is set
267 */
268 ct0 = ~( ct0 & i ); // reset or count ct0
269 ct1 = (ct0 ^ ct1) & i; // reset or count ct1
270 i &= ct0 & ct1; // count until roll over ?
271 key_state ^= i; // then toggle debounced state
272
273 /*
274 * To notify main program of pressed key, the correspondig bit
275 * in global variable key_press is set.
276 * The main loop needs to clear this bit
277 */
278 return key_state & i; // 0->1: key press detect
279
280 }
281
286 static inline void trap_if_key_pressed(void)
287 {
288
289 KEY_INIT();
290 DELAY_MS(10);
291 if (KEY_GET())
292 {
293 LED_INIT();
294 while(1)
295 {
296 DELAY_MS(400);
297 LED_SET(0);
298 DELAY_MS(10);
299 LED_CLR(0);
300 }
301 }
302 }
303
306 /* === Bootloader Interface === */
307 #if BOOTLOADER_ADDRESS != 0
308
309 #define JUMP_BOOT_LOADER() \
310 do {\
311 void (*funcptr)( uint8_t flag ) = BOOTLOADER_ADDRESS;\
312 funcptr(42);\
313 }while(0)
314 #else /* BOOTLOADER_ADDRESS != 0 */
315 #define JUMP_BOOT_LOADER()
316 #endif /* BOOTLOADER_ADDRESS != 0 */
317
318
319
320
321 /* === Prototypes ============================================================ */
322 #ifdef __cplusplus
323 extern "C" {
324 #endif
325
329 #if 0
330 #define BUFFER_SET_USED(b) do{ATOMIC_BLOCK(ATOMIC_FORCEON){b->used|=1}}while(0)
331 #define BUFFER_SET_UNUSED(b) do{ATOMIC_BLOCK(ATOMIC_FORCEON){b->used&=~1}}while(0)
332 #define BUFFER_IS_USED(b) ((b->used&1)!=0)
333
334 #define BUFFER_SET_LOCK(b) do{ATOMIC_BLOCK(ATOMIC_FORCEON){b->used|=2}}while(0)
335 #define BUFFER_SET_UNLOCK(b) do{ATOMIC_BLOCK(ATOMIC_FORCEON){b->used&=~2}}while(0)
336 #define BUFFER_IS_LOCKED(b) ((b->used&2)!=0)
337 #endif
338
339 #define BUFFER_SET_USED(b) do{b->used|=1;}while(0)
340 #define BUFFER_SET_UNUSED(b) do{b->used&=~1;}while(0)
341 #define BUFFER_IS_USED(b) ((b->used&1)!=0)
342
343 #define BUFFER_SET_LOCK(b) do{b->used|=2;}while(0)
344 #define BUFFER_SET_UNLOCK(b) do{b->used&=~2;}while(0)
345 #define BUFFER_IS_LOCKED(b) ((b->used&2)!=0)
346
347
348 #define BUFFER_SIZE(b) (b->iend - b->istart)
349 #define BUFFER_PDATA(b) (b->data + b->istart)
350 #define BUFFER_SEEK(b,offset) (b->data + (b->iend=offset))
351
352 #define BUFFER_GET_MEMBLOCK(b,pmem,size) \
353 do{\
354 b->used = 1;\
355 pmem = (b->data + b->iend);\
356 size = (b->len - b->iend);\
357 }while(0)
358
359 #define BUFFER_UPDATE_MEMBLOCK(b,end) \
360 do{\
361 b->iend = end;\
362 b->used = 0;\
363 }while(0);
364
365 #define BUFFER_LAST_CHAR(b) \
366 (b->iend <= b->istart) ? EOF : (char)b->data[b->iend-1]
367 #define BUFFER_FREE_AT_END(b) (b->len - b->iend)
368 #define BUFFER_FREE_AT_START(b) (b->istart)
369 #define BUFFER_ELSZ(x) (sizeof(buffer_t) + (x))
370 #define BUFFER_RESET(b,start) do{ b->iend = b->istart = start;}while(0)
371 #define BUFFER_ADVANCE(b,more) do{ b->istart += more;}while(0)
372
374 buffer_t * buffer_init(void * pmem, uint8_t size, uint8_t start);
376 int buffer_append_char(buffer_t *b, uint8_t c);
378 int buffer_prepend_char(buffer_t *b, int c);
380 int buffer_get_char(buffer_t *b);
382 uint8_t buffer_append_block(buffer_t *b, void *pdata, uint8_t size);
384 uint8_t buffer_prepend_block(buffer_t *b, void *pdata, uint8_t size);
386 uint8_t buffer_get_block(buffer_t *b, void *pdata, uint8_t size);
387
388
389 buffer_pool_t * buffer_pool_init(uint8_t *pmem, size_t memsz, uint8_t bsz);
390 buffer_t * buffer_alloc(buffer_pool_t *ppool, uint8_t istart);
391 void buffer_free(buffer_t * pbuf);
392
393
394
395 /* buffer stream function */
396 //typedef void (*incb)(buffer_t *pbuf) buffer_stream_incb_t;
397 //typedef void (*outcb)(buffer_t *pbuf) buffer_stream_outcb_t;
398
399 typedef struct
400 {
401 FILE bstream;
402 buffer_t *pbufin;
403 buffer_t *pbufout;
404 void (*incb)(buffer_t *pbuf);
405 void (*outcb)(buffer_t *pbuf);
406 } buffer_stream_t;
407
408
409
410 int buffer_stream_init( buffer_stream_t *pbs,
411 void (*incb)(buffer_t *pbuf),
412 void (*outcb)(buffer_t *pbuf));
413
414 int buffer_stream_putchar(char c,FILE *f);
415 int buffer_stream_getchar(FILE *f);
416
417
418
420 #ifdef __cplusplus
421 } /* extern "C" */
422 #endif
423
424 #endif /* #ifndef IOUTIL_H */
425 /* EOF */
KEY_GET
#define KEY_GET()
Definition: ioutil.h:221
LED_INIT
#define LED_INIT()
Definition: ioutil.h:116
buffer_get_char
int buffer_get_char(buffer_t *b)
buffer_append_char
int buffer_append_char(buffer_t *b, uint8_t c)
KEY_INIT
#define KEY_INIT()
Definition: ioutil.h:218
buffer_t::used
uint8_t used
Definition: ioutil.h:77
buffer_append_block
uint8_t buffer_append_block(buffer_t *b, void *pdata, uint8_t size)
buffer_t::next
void * next
Definition: ioutil.h:75
buffer_t
Definition: ioutil.h:72
LED_CLR
#define LED_CLR(ln)
Definition: ioutil.h:175
keys_debounced
static uint8_t keys_debounced(void)
Debounce Key values, returned from the macro KEY_GET()
Definition: ioutil.h:249
buffer_get_block
uint8_t buffer_get_block(buffer_t *b, void *pdata, uint8_t size)
buffer_t::istart
uint8_t istart
Definition: ioutil.h:81
buffer_t::len
uint8_t len
Definition: ioutil.h:79
buffer_prepend_block
uint8_t buffer_prepend_block(buffer_t *b, void *pdata, uint8_t size)
buffer_prepend_char
int buffer_prepend_char(buffer_t *b, int c)
buffer_init
buffer_t * buffer_init(void *pmem, uint8_t size, uint8_t start)
DELAY_MS
#define DELAY_MS(x)
Macro for delays with ms resolution.
Definition: board.h:93
trap_if_key_pressed
static void trap_if_key_pressed(void)
Debounce Key values, returned from the macro KEY_GET()
Definition: ioutil.h:286
buffer_t::iend
uint8_t iend
Definition: ioutil.h:83
LED_SET
#define LED_SET(ln)
Definition: ioutil.h:163