1 1.12 rillig /* $NetBSD: d_alignof.c,v 1.12 2023/07/07 19:45:22 rillig Exp $ */ 2 1.2 rillig # 3 "d_alignof.c" 3 1.2 rillig 4 1.3 rillig /* https://gcc.gnu.org/onlinedocs/gcc/Alignment.html */ 5 1.3 rillig 6 1.12 rillig /* lint1-extra-flags: -X 351 */ 7 1.12 rillig 8 1.3 rillig unsigned long 9 1.3 rillig leading_and_trailing_alignof_type(void) 10 1.1 jruoho { 11 1.1 jruoho return __alignof__(short); 12 1.1 jruoho } 13 1.3 rillig 14 1.3 rillig unsigned long 15 1.3 rillig leading_alignof_type(void) 16 1.3 rillig { 17 1.3 rillig return __alignof(short); 18 1.3 rillig } 19 1.3 rillig 20 1.3 rillig unsigned long 21 1.3 rillig plain_alignof_type(void) 22 1.3 rillig { 23 1.3 rillig /* The plain word 'alignof' is not recognized by GCC. */ 24 1.4 rillig /* expect+2: error: function 'alignof' implicitly declared to return int [215] */ 25 1.4 rillig /* expect+1: error: syntax error 'short' [249] */ 26 1.3 rillig return alignof(short); 27 1.3 rillig } 28 1.8 rillig /* expect-1: warning: function 'plain_alignof_type' falls off bottom without returning value [217] */ 29 1.3 rillig 30 1.3 rillig unsigned long 31 1.3 rillig leading_and_trailing_alignof_expr(void) 32 1.3 rillig { 33 1.3 rillig return __alignof__ 3; 34 1.3 rillig } 35 1.3 rillig 36 1.3 rillig unsigned long 37 1.3 rillig leading_alignof_expr(void) 38 1.3 rillig { 39 1.3 rillig return __alignof 3; 40 1.3 rillig } 41 1.3 rillig 42 1.3 rillig unsigned long 43 1.3 rillig plain_alignof_expr(void) 44 1.3 rillig { 45 1.3 rillig /* The plain word 'alignof' is not recognized by GCC. */ 46 1.4 rillig /* expect+2: error: 'alignof' undefined [99] */ 47 1.3 rillig /* expect+1: error: syntax error '3' [249] */ 48 1.3 rillig return alignof 3; 49 1.3 rillig } 50 1.8 rillig /* expect-1: warning: function 'plain_alignof_expr' falls off bottom without returning value [217] */ 51 1.6 rillig 52 1.6 rillig 53 1.6 rillig /* 54 1.6 rillig * As with 'sizeof', the keyword '__alignof__' doesn't require parentheses 55 1.6 rillig * when followed by an expression. This allows for the seemingly strange 56 1.6 rillig * '->' after the parentheses, which in fact is perfectly fine. 57 1.6 rillig * 58 1.6 rillig * The NetBSD style guide says "We parenthesize sizeof expressions", even 59 1.6 rillig * though it is misleading in edge cases like this. The GCC manual says that 60 1.6 rillig * '__alignof__' and 'sizeof' are syntactically the same, therefore the same 61 1.6 rillig * reasoning applies to '__alignof__'. 62 1.6 rillig */ 63 1.6 rillig unsigned long 64 1.6 rillig alignof_pointer_to_member(void) 65 1.6 rillig { 66 1.6 rillig struct s { 67 1.6 rillig unsigned long member; 68 1.6 rillig } var = { 0 }, *ptr = &var; 69 1.6 rillig 70 1.6 rillig return __alignof__(ptr)->member + ptr->member; 71 1.6 rillig } 72 1.9 rillig 73 1.9 rillig void 74 1.9 rillig alignof_variants(void) 75 1.9 rillig { 76 1.9 rillig /* expect+1: error: negative array dimension (-4) [20] */ 77 1.9 rillig typedef int array_int[-(int)__alignof(int[3])]; 78 1.9 rillig 79 1.9 rillig /* expect+1: error: negative array dimension (-8) [20] */ 80 1.9 rillig typedef int array_double[-(int)__alignof(double[3])]; 81 1.9 rillig 82 1.9 rillig /* expect+1: error: cannot take size/alignment of function type 'function(int) returning int' [144] */ 83 1.9 rillig typedef int func[-(int)__alignof(int(int))]; 84 1.9 rillig 85 1.9 rillig struct int_double { 86 1.9 rillig int i; 87 1.9 rillig double d; 88 1.9 rillig }; 89 1.9 rillig /* expect+1: error: negative array dimension (-8) [20] */ 90 1.9 rillig typedef int struct_int_double[-(int)__alignof(struct int_double)]; 91 1.9 rillig 92 1.9 rillig struct chars { 93 1.9 rillig char name[20]; 94 1.9 rillig }; 95 1.9 rillig /* expect+1: error: negative array dimension (-1) [20] */ 96 1.9 rillig typedef int struct_chars[-(int)__alignof(struct chars)]; 97 1.9 rillig 98 1.9 rillig /* expect+1: warning: struct 'incomplete_struct' never defined [233] */ 99 1.9 rillig struct incomplete_struct; 100 1.9 rillig /* expect+1: error: cannot take size/alignment of incomplete type [143] */ 101 1.9 rillig typedef int incomplete_struct[-(int)__alignof(struct incomplete_struct)]; 102 1.9 rillig 103 1.9 rillig /* expect+1: warning: union 'incomplete_union' never defined [234] */ 104 1.9 rillig union incomplete_union; 105 1.9 rillig /* expect+1: error: cannot take size/alignment of incomplete type [143] */ 106 1.9 rillig typedef int incomplete_union[-(int)__alignof(union incomplete_union)]; 107 1.9 rillig 108 1.9 rillig /* expect+1: warning: enum 'incomplete_enum' never defined [235] */ 109 1.9 rillig enum incomplete_enum; 110 1.10 rillig /* expect+1: error: cannot take size/alignment of incomplete type [143] */ 111 1.9 rillig typedef int incomplete_enum[-(int)__alignof(enum incomplete_enum)]; 112 1.9 rillig 113 1.11 rillig /* expect+1: error: cannot take size/alignment of incomplete type [143] */ 114 1.11 rillig typedef int incomplete_array[-(int)__alignof(int[])]; 115 1.11 rillig 116 1.9 rillig struct bit_fields { 117 1.9 rillig _Bool bit_field:1; 118 1.9 rillig }; 119 1.9 rillig /* 120 1.9 rillig * FIXME: This is not an attempt to initialize the typedef, it's the 121 1.9 rillig * initialization of a nested expression. 122 1.9 rillig */ 123 1.9 rillig /* expect+2: error: cannot initialize typedef '00000000_tmp' [25] */ 124 1.9 rillig /* expect+1: error: cannot take size/alignment of bit-field [145] */ 125 1.11 rillig typedef int bit_field_1[-(int)__alignof((struct bit_fields){0}.bit_field)]; 126 1.11 rillig 127 1.11 rillig struct bit_fields bit_fields; 128 1.11 rillig /* expect+1: error: cannot take size/alignment of bit-field [145] */ 129 1.11 rillig typedef int bit_field_2[-(int)__alignof(bit_fields.bit_field)]; 130 1.9 rillig 131 1.9 rillig /* expect+1: error: cannot take size/alignment of void [146] */ 132 1.9 rillig typedef int plain_void[-(int)__alignof(void)]; 133 1.9 rillig } 134