15
15
License along with this library; if not, write to the Free Software
16
16
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
17
17
*/
18
+ #include < abi.h>
19
+ #include < stdint.h>
20
+ #include < exception>
18
21
19
- #include < stdlib.h>
22
+ #include < avr/io.h>
23
+ #include < avr/interrupt.h>
20
24
21
- extern " C" void __cxa_pure_virtual (void ) __attribute__ ((__noreturn__));
22
- extern " C" void __cxa_deleted_virtual (void ) __attribute__ ((__noreturn__));
25
+ namespace {
26
+ // guard is an integer type big enough to hold flag and a mutex.
27
+ // By default gcc uses long long int and avr ABI does not change it
28
+ // So we have 32 or 64 bits available. Actually, we need 16.
23
29
24
- void __cxa_pure_virtual (void ) {
25
- // We might want to write some diagnostics to uart in this case
26
- // std::terminate();
27
- abort ();
30
+ inline char & flag_part (__guard *g) {
31
+ return *(reinterpret_cast <char *>(g));
28
32
}
29
33
30
- void __cxa_deleted_virtual (void ) {
31
- // We might want to write some diagnostics to uart in this case
32
- // std::terminate();
33
- abort ();
34
+ inline uint8_t & sreg_part (__guard *g) {
35
+ return *(reinterpret_cast <uint8_t *>(g) + sizeof (char ));
36
+ }
37
+ }
38
+
39
+ int __cxa_guard_acquire (__guard *g) {
40
+ uint8_t oldSREG = SREG;
41
+ cli ();
42
+ // Initialization of static variable has to be done with blocked interrupts
43
+ // because if this function is called from interrupt and sees that somebody
44
+ // else is already doing initialization it MUST wait until initializations
45
+ // is complete. That's impossible.
46
+ // If you don't want this overhead compile with -fno-threadsafe-statics
47
+ if (flag_part (g)) {
48
+ SREG = oldSREG;
49
+ return false ;
50
+ } else {
51
+ sreg_part (g) = oldSREG;
52
+ return true ;
53
+ }
54
+ }
55
+
56
+ void __cxa_guard_release (__guard *g) {
57
+ flag_part (g) = 1 ;
58
+ SREG = sreg_part (g);
34
59
}
35
60
61
+ void __cxa_guard_abort (__guard *g) {
62
+ SREG = sreg_part (g);
63
+ }
64
+
65
+ void __cxa_pure_virtual (void ) {
66
+ // We might want to write some diagnostics to uart in this case
67
+ std::terminate ();
68
+ }
69
+
70
+ void __cxa_deleted_virtual (void ) {
71
+ // We might want to write some diagnostics to uart in this case
72
+ std::terminate ();
73
+ }
0 commit comments