4 Copyright 2008, 2009 Michel Pollet <buserror@gmail.com>
6 This file is part of simavr.
8 simavr is free software: you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation, either version 3 of the License, or
11 (at your option) any later version.
13 simavr is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with simavr. If not, see <http://www.gnu.org/licenses/>.
22 #ifndef __SIM_REGBIT_H__
23 #define __SIM_REGBIT_H__
31 #define ARRAY_SIZE(_aa) (sizeof(_aa) / sizeof((_aa)[0]))
35 * These accessors are inlined and are used to perform the operations on
36 * avr_regbit_t definitions. This is the "official" way to access bits into registers
37 * The small footprint costs brings much better versatility for functions/bits that are
38 * not always defined in the same place on real AVR cores
41 * set/get/clear io register bits in one operation
43 static inline uint8_t avr_regbit_set(avr_t * avr, avr_regbit_t rb)
48 uint8_t m = rb.mask << rb.bit;
49 avr_core_watch_write(avr, a, avr->data[a] | m);
50 return (avr->data[a] >> rb.bit) & rb.mask;
53 static inline uint8_t avr_regbit_setto(avr_t * avr, avr_regbit_t rb, uint8_t v)
58 uint8_t m = rb.mask << rb.bit;
59 avr_core_watch_write(avr, a, (avr->data[a] & ~(m)) | ((v << rb.bit) & m));
60 return (avr->data[a] >> rb.bit) & rb.mask;
64 * Set the 'raw' bits, if 'v' is the unshifted value of the bits
66 static inline uint8_t avr_regbit_setto_raw(avr_t * avr, avr_regbit_t rb, uint8_t v)
71 uint8_t m = rb.mask << rb.bit;
72 avr_core_watch_write(avr, a, (avr->data[a] & ~(m)) | ((v) & m));
73 return (avr->data[a]) & (rb.mask << rb.bit);
76 static inline uint8_t avr_regbit_get(avr_t * avr, avr_regbit_t rb)
81 //uint8_t m = rb.mask << rb.bit;
82 return (avr->data[a] >> rb.bit) & rb.mask;
86 * Return the bit(s) 'in position' instead of zero based
88 static inline uint8_t avr_regbit_get_raw(avr_t * avr, avr_regbit_t rb)
93 //uint8_t m = rb.mask << rb.bit;
94 return (avr->data[a]) & (rb.mask << rb.bit);
97 static inline uint8_t avr_regbit_clear(avr_t * avr, avr_regbit_t rb)
100 uint8_t m = rb.mask << rb.bit;
101 avr_core_watch_write(avr, a, avr->data[a] & ~m);
107 * This reads the bits for an array of avr_regbit_t, make up a "byte" with them.
108 * This allows reading bits like CS0, CS1, CS2 etc even if they are not in the same
109 * physical IO register.
111 static inline uint8_t avr_regbit_get_array(avr_t * avr, avr_regbit_t *rb, int count)
115 for (int i = 0; i < count; i++, rb++) if (rb->reg) {
116 uint8_t a = (rb->reg);
117 res |= ((avr->data[a] >> rb->bit) & rb->mask) << i;
122 #define AVR_IO_REGBIT(_io, _bit) { . reg = (_io), .bit = (_bit), .mask = 1 }
123 #define AVR_IO_REGBITS(_io, _bit, _mask) { . reg = (_io), .bit = (_bit), .mask = (_mask) }
129 #endif /* __SIM_REGBIT_H__ */