diff options
| author | Xavier ASUS <xavi92psx@gmail.com> | 2019-10-18 00:31:54 +0200 |
|---|---|---|
| committer | Xavier ASUS <xavi92psx@gmail.com> | 2019-10-18 00:31:54 +0200 |
| commit | 268a53de823a6750d6256ee1fb1e7707b4b45740 (patch) | |
| tree | 42c1799a9a82b2f7d9790ee9fe181d72a7274751 /support/regression/tests/bitfields.c | |
| download | sdcc-gas-268a53de823a6750d6256ee1fb1e7707b4b45740.tar.gz | |
sdcc-3.9.0 fork implementing GNU assembler syntax
This fork aims to provide better support for stm8-binutils
Diffstat (limited to 'support/regression/tests/bitfields.c')
| -rw-r--r-- | support/regression/tests/bitfields.c | 515 |
1 files changed, 515 insertions, 0 deletions
diff --git a/support/regression/tests/bitfields.c b/support/regression/tests/bitfields.c new file mode 100644 index 0000000..89fb7d0 --- /dev/null +++ b/support/regression/tests/bitfields.c @@ -0,0 +1,515 @@ +/** Bitfield tests. + + SDCC pic16 port currently does not support bitfields of size > 8, + so they are ifdefed out. +*/ +#include <testfwk.h> + +struct { + char c0_3 : 3; + char c3_5 : 5; +} c_bf; + +#ifndef __SDCC_pdk14 // Lack of memory +#if !defined(__SDCC_pic16) +struct { + int i0_7 : 7; + int i7_9 : 9; +} i_bf; + +struct { + long l0_7 : 7; + long l7_10 : 10; + long l17_15 : 15; +} l_bf; + +struct { + unsigned int b0 : 1; + unsigned int b1 : 1; + unsigned int b2 : 1; + unsigned int b3 : 1; + unsigned int b4 : 1; + unsigned int b5 : 1; + unsigned int b6 : 1; + unsigned int b7 : 1; + unsigned int b8 : 1; + unsigned int b9 : 1; +} sb_bf; +#endif /* !__SDCC_pic16 */ +#endif + +struct { + unsigned int b0 : 1; + unsigned int b2 : 1; +} size1a_bf; + +struct { + unsigned int b0 : 1; + unsigned int b1 : 1; + unsigned int : 0; +} size1b_bf; + +struct { + unsigned int b0 : 1; + unsigned int b1 : 1; + unsigned int b2 : 6; +} size1c_bf; + +struct { + unsigned int b0 : 1; + unsigned int : 0; + unsigned int b1 : 1; +} size2a_bf; + +#if !defined(__SDCC_pic16) +struct { + unsigned int b0 : 1; + unsigned int b1 : 1; + unsigned int b2 : 1; + unsigned int b3 : 1; + unsigned int b4 : 1; + unsigned int b5 : 1; + unsigned int b6 : 1; + unsigned int b7 : 1; + unsigned int b8 : 1; + unsigned int b9 : 1; +} size2b_bf; + +struct { + unsigned int b0 : 4; + unsigned int b1 : 5; +} size2c_bf; + +struct { + unsigned int b0 : 12; + unsigned int b1 : 3; +} size2d_bf; + +struct { /* Bit-fields that end on byte boundary */ + unsigned int b0 : 3; + unsigned int b1 : 5; + unsigned int b2 : 5; + unsigned int b3 : 3; +} size2e_bf; + +struct { + unsigned int b0 : 3; + unsigned int b1 : 12; +} size3a_bf; + +struct { + signed int s0_7 : 7; + signed int s7_1 : 1; + signed int s8_9 : 9; +} s_bf; +#endif /* !__SDCC_pic16 */ + +void +testBitfieldSizeof(void) +{ + /* Although bitfields are extremely implementation dependant, these + assertions should hold for all implementations with storage units + of 8 bits or larger (nearly universal). + */ + ASSERT( sizeof(size1a_bf) >= 1); + ASSERT( sizeof(size1b_bf) >= 1); + ASSERT( sizeof(size1c_bf) >= 1); +#if !defined(__SDCC_pic16) + ASSERT( sizeof(size2b_bf) >= 2); + ASSERT( sizeof(size2c_bf) >= 2); + ASSERT( sizeof(size2d_bf) >= 2); + ASSERT( sizeof(size3a_bf) >= 2); + ASSERT( sizeof(size1a_bf) <= sizeof(size1b_bf)); +#endif /* !__SDCC_pic16 */ + /* Some SDCC specific assertions. SDCC uses 8 bit storage units. + Bitfields that are less than 8 bits, but would (due to earlier + bitfield declarations) span a storage unit boundary are + realigned to the next storage unit boundary. Bitfields of + 8 or greater bits are always aligned to start on a storage + unit boundary. + */ +#ifdef __SDCC + ASSERT( sizeof(size1a_bf) == 1); + ASSERT( sizeof(size1b_bf) == 1); + ASSERT( sizeof(size1c_bf) == 1); + ASSERT( sizeof(size2a_bf) == 2); +#if !defined(__SDCC_pic16) + ASSERT( sizeof(size2b_bf) == 2); + ASSERT( sizeof(size2c_bf) == 2); + ASSERT( sizeof(size2d_bf) == 2); + ASSERT( sizeof(size3a_bf) == 3); +#endif /* !__SDCC_pic16 */ +#endif +} + + +void +testBitfieldsSingleBitLiteral(void) +{ +#ifndef __SDCC_pdk14 // Lack of memory +#if !defined(__SDCC_pic16) + size2b_bf.b0 = 0; + size2b_bf.b1 = 0; + size2b_bf.b2 = 0; + size2b_bf.b3 = 0; + size2b_bf.b4 = 0; + size2b_bf.b5 = 0; + size2b_bf.b6 = 0; + size2b_bf.b7 = 0; + size2b_bf.b8 = 0; + size2b_bf.b9 = 0; + + /* make sure modulo 2 truncation works */ + size2b_bf.b0 = 0x3fe; + ASSERT(size2b_bf.b0==0); + ASSERT(size2b_bf.b1==0); + ASSERT(size2b_bf.b2==0); + ASSERT(size2b_bf.b3==0); + ASSERT(size2b_bf.b4==0); + ASSERT(size2b_bf.b5==0); + ASSERT(size2b_bf.b6==0); + ASSERT(size2b_bf.b7==0); + ASSERT(size2b_bf.b8==0); + ASSERT(size2b_bf.b9==0); + size2b_bf.b0 = 0x3ff; + ASSERT(size2b_bf.b0==1); + ASSERT(size2b_bf.b1==0); + ASSERT(size2b_bf.b2==0); + ASSERT(size2b_bf.b3==0); + ASSERT(size2b_bf.b4==0); + ASSERT(size2b_bf.b5==0); + ASSERT(size2b_bf.b6==0); + ASSERT(size2b_bf.b7==0); + ASSERT(size2b_bf.b8==0); + ASSERT(size2b_bf.b9==0); + + /* make sure both bytes work */ + size2b_bf.b9 = 0x3ff; + ASSERT(size2b_bf.b0==1); + ASSERT(size2b_bf.b1==0); + ASSERT(size2b_bf.b2==0); + ASSERT(size2b_bf.b3==0); + ASSERT(size2b_bf.b4==0); + ASSERT(size2b_bf.b5==0); + ASSERT(size2b_bf.b6==0); + ASSERT(size2b_bf.b7==0); + ASSERT(size2b_bf.b8==0); + ASSERT(size2b_bf.b9==1); +#endif /* !__SDCC_pic16 */ +#endif +} + +void +testBitfieldsSingleBit(void) +{ +#ifndef __SDCC_pdk14 // Lack of memory +#if !defined(__SDCC_pic16) + volatile unsigned char c; + + c = 0; + size2b_bf.b0 = c; + size2b_bf.b1 = c; + size2b_bf.b2 = c; + size2b_bf.b3 = c; + size2b_bf.b4 = c; + size2b_bf.b5 = c; + size2b_bf.b6 = c; + size2b_bf.b7 = c; + size2b_bf.b8 = c; + size2b_bf.b9 = c; + + /* make sure modulo 2 truncation works */ + c = 0xfe; + size2b_bf.b0 = c; + ASSERT(size2b_bf.b0==0); + ASSERT(size2b_bf.b1==0); + ASSERT(size2b_bf.b2==0); + ASSERT(size2b_bf.b3==0); + ASSERT(size2b_bf.b4==0); + ASSERT(size2b_bf.b5==0); + ASSERT(size2b_bf.b6==0); + ASSERT(size2b_bf.b7==0); + ASSERT(size2b_bf.b8==0); + ASSERT(size2b_bf.b9==0); + c++; + size2b_bf.b0 = c; + ASSERT(size2b_bf.b0==1); + ASSERT(size2b_bf.b1==0); + ASSERT(size2b_bf.b2==0); + ASSERT(size2b_bf.b3==0); + ASSERT(size2b_bf.b4==0); + ASSERT(size2b_bf.b5==0); + ASSERT(size2b_bf.b6==0); + ASSERT(size2b_bf.b7==0); + ASSERT(size2b_bf.b8==0); + ASSERT(size2b_bf.b9==0); + + /* make sure both bytes work */ + size2b_bf.b9 = c; + ASSERT(size2b_bf.b0==1); + ASSERT(size2b_bf.b1==0); + ASSERT(size2b_bf.b2==0); + ASSERT(size2b_bf.b3==0); + ASSERT(size2b_bf.b4==0); + ASSERT(size2b_bf.b5==0); + ASSERT(size2b_bf.b6==0); + ASSERT(size2b_bf.b7==0); + ASSERT(size2b_bf.b8==0); + ASSERT(size2b_bf.b9==1); +#endif /* !__SDCC_pic16 */ +#endif +} + +void +testBitfieldsMultibitLiteral(void) +{ +#if !defined( __SDCC_pdk14) && !defined( __SDCC_pdk15) // Lack of memory +#if !defined(__SDCC_pic16) + size2c_bf.b0 = 0xff; /* should truncate to 0x0f */ + size2c_bf.b1 = 0; + ASSERT(size2c_bf.b0==0x0f); + ASSERT(size2c_bf.b1==0); + + size2c_bf.b1 = 0xff; /* should truncate to 0x1f */ + size2c_bf.b0 = 0; + ASSERT(size2c_bf.b0==0); + ASSERT(size2c_bf.b1==0x1f); + + size2c_bf.b0 = 0xff; /* should truncate to 0x0f */ + size2c_bf.b1 = 0xff; /* should truncate to 0x1f */ + ASSERT(size2c_bf.b0==0x0f); + ASSERT(size2c_bf.b1==0x1f); + + size2d_bf.b0 = 0xffff; /* should truncate to 0x0fff */ + size2d_bf.b1 = 0; + ASSERT(size2d_bf.b0==0x0fff); + ASSERT(size2d_bf.b1==0); + + size2d_bf.b1 = 0xffff; /* should truncate to 0x07 */ + size2d_bf.b0 = 0; + ASSERT(size2d_bf.b0==0); + ASSERT(size2d_bf.b1==0x07); + + size2d_bf.b0 = 0xffff; /* should truncate to 0x0fff */ + size2d_bf.b1 = 0xffff; /* should truncate to 0x07 */ + ASSERT(size2d_bf.b0==0x0fff); + ASSERT(size2d_bf.b1==0x07); + + size2d_bf.b0 = 0x0321; + size2d_bf.b1 = 1; + ASSERT(size2d_bf.b0==0x0321); + ASSERT(size2d_bf.b1==1); + + size2d_bf.b0 = 0x0a46; + size2d_bf.b1 = 5; + ASSERT(size2d_bf.b0==0x0a46); + ASSERT(size2d_bf.b1==5); + + size2e_bf.b0 = 2; + size2e_bf.b1 = 2; + size2e_bf.b2 = 2; + size2e_bf.b3 = 2; + + ASSERT(size2e_bf.b0==2); + ASSERT(size2e_bf.b1==2); + ASSERT(size2e_bf.b2==2); + ASSERT(size2e_bf.b3==2); +#endif /* !__SDCC_pic16 */ +#endif +} + +void +testBitfieldsMultibit(void) +{ +#if !defined( __SDCC_pdk14) && !defined( __SDCC_pdk15) // Lack of memory +#if !defined(__SDCC_pic16) + volatile int allones = 0xffff; + volatile int zero = 0; + volatile int x; + + size2c_bf.b0 = allones; /* should truncate to 0x0f */ + size2c_bf.b1 = zero; + ASSERT(size2c_bf.b0==0x0f); + ASSERT(size2c_bf.b1==0); + + size2c_bf.b1 = allones; /* should truncate to 0x1f */ + size2c_bf.b0 = zero; + ASSERT(size2c_bf.b0==0); + ASSERT(size2c_bf.b1==0x1f); + + size2d_bf.b0 = allones; /* should truncate to 0x0fff */ + size2d_bf.b1 = zero; + ASSERT(size2d_bf.b0==0x0fff); + ASSERT(size2d_bf.b1==0); + + size2d_bf.b1 = allones; /* should truncate to 0x07 */ + size2d_bf.b0 = zero; + ASSERT(size2d_bf.b0==0); + ASSERT(size2d_bf.b1==0x07); + + x = 0x0321; + size2d_bf.b0 = x; + x = 1; + size2d_bf.b1 = x; + ASSERT(size2d_bf.b0==0x0321); + ASSERT(size2d_bf.b1==1); + + x = 0x0a46; + size2d_bf.b0 = x; + x = 5; + size2d_bf.b1 = x; + ASSERT(size2d_bf.b0==0x0a46); + ASSERT(size2d_bf.b1==5); + + x = 2; + size2e_bf.b0 = x; + size2e_bf.b1 = x; + size2e_bf.b2 = x; + size2e_bf.b3 = x; + + ASSERT(size2e_bf.b0==2); + ASSERT(size2e_bf.b1==2); + ASSERT(size2e_bf.b2==2); + ASSERT(size2e_bf.b3==2); +#endif /* !__SDCC_pic16 */ +#endif +} + +void +testBitfields(void) +{ + c_bf.c0_3 = 2; + c_bf.c3_5 = 3; +#if defined(PORT_HOST) && (defined(__ppc__) || defined(__PPC__) || defined(__sparc) || defined(__sparc64__)) + /* bitfields on powerpc and sparc architectures are allocated from left to right */ + ASSERT(*(char *)(&c_bf) == ((2<<(8-3)) + 3) ); +#else + ASSERT(*(char *)(&c_bf) == (2 + (3<<3)) ); +#endif + +#if 0 // not yet + i_bf.i0_7 = 23; + i_bf.i7_9 = 234; + ASSERT(*(int *)(&i_bf) == (23 + (234<<7)) ); + + l_bitfield.l0_7 = 23; + l_bitfield.l7_10 = 234; + l_bitfield.l17_15 = 2345; + ASSERT(*(long *)(&l_bf) == (23 + (234<<7) + (2345<<17)) ); +#endif +} + +void +testSignedBitfields(void) +{ +#if !defined( __SDCC_pdk14) && !defined( __SDCC_pdk15) // Lack of memory +#if !defined(__SDCC_pic16) + s_bf.s0_7 = 0xf0; + s_bf.s7_1 = 1; + s_bf.s8_9 = 0xfff8; + ASSERT(s_bf.s0_7 == -16); + ASSERT(s_bf.s7_1 == - 1); + ASSERT(s_bf.s8_9 == - 8); + ASSERT(s_bf.s0_7 < 0); + ASSERT(s_bf.s7_1 < 0); + ASSERT(s_bf.s8_9 < 0); + + s_bf.s0_7 = 0x3f; + s_bf.s7_1 = 2; + s_bf.s8_9 = 0x00ff; + ASSERT(s_bf.s0_7 == 0x3f); + ASSERT(s_bf.s7_1 == 0); + ASSERT(s_bf.s8_9 == 0xff); + ASSERT(s_bf.s0_7 > 0); + ASSERT(s_bf.s8_9 > 0); +#endif /* !__SDCC_pic16 */ +#endif +} + +/* test case for enhancement request #2291335 : Unnamed bit-field initialization */ + +struct s2291335_1 { + int a : 2; + char : 2; + int b : 2; +}; + +struct s2291335_2 { + int a : 2; + char : 0; + int b : 2; +}; + +struct s2291335_1 gs2291335_1 = {1, 2}; +struct s2291335_2 gs2291335_2 = {1, 2}; + +void +__test2291335(void) +{ + struct s2291335_1 ls2291335_1 = {1, 2}; + struct s2291335_2 ls2291335_2 = {1, 2}; + + ASSERT(gs2291335_1.a == 1); + ASSERT(gs2291335_1.b == 2); + ASSERT(gs2291335_2.a == 1); + ASSERT(gs2291335_2.b == 2); + + ASSERT(ls2291335_1.a == 1); + ASSERT(ls2291335_1.b == 2); + ASSERT(ls2291335_2.a == 1); + ASSERT(ls2291335_2.b == 2); +} + +/* test case for bug #2366757: segfault when initializing structure with bitfield */ + +struct +{ + char a : 1; + char b : 1; +} s2366757 = {0}; + +/* test case for const struct with bitfields */ + +#if !defined( __SDCC_pdk14) && !defined( __SDCC_pdk15) // Lack of memory +#ifndef __SDCC_pic16 // TODO: enable when the pic16 ports supports bitfields of size greater than 8 bits! +const struct +{ + unsigned int a : 4; + unsigned int b : 3; + unsigned int c : 12; + unsigned int d : 3; + unsigned int e : 2; + unsigned int : 4; + unsigned int f : 2; + unsigned int g; +} cs = { 1, 2, 345, 6, 2, 1, 54321}; +#endif +#endif + +#if defined(PORT_HOST) && (defined(__x86_64__) || defined(__i386__)) && defined(__GNUC__) && (__GNUC__ == 4 && __GNUC_MINOR__ == 6) +/* Workaround to fix the (cs.f == 1) test failure, which appeared in svn build 6665, when -O2 gcc option was included. + * The failure only occurs on i386 and x86_64 host architectures with gcc 4.6 if -O2 is set. + * This seems like a gcc bug to me. (Borut) + */ +#pragma GCC push_options +#pragma GCC optimize ("O0") +#endif +void +testCS(void) +{ +#if !defined( __SDCC_pdk14) && !defined( __SDCC_pdk15) // Lack of memory +#ifndef __SDCC_pic16 // TODO: enable when the pic16 ports supports bitfields of size greater than 8 bits! + ASSERT(cs.a == 1); + ASSERT(cs.b == 2); + ASSERT(cs.c == 345); + ASSERT(cs.d == 6); + ASSERT(cs.e == 2); + ASSERT(cs.f == 1); + ASSERT(cs.g == 54321U); +#endif +#endif +} +#if defined(PORT_HOST) && defined(__sun) && defined(__i386__) && defined(__GNUC__) && (__GNUC__ == 4 && __GNUC_MINOR__ == 6) +#pragma GCC pop_options +#endif + |
