Allow char bit-fields
These are not required to be supported (only int, signed int, and unsigned int are required), but most compilers support it. https://port70.net/~nsz/c/c89/c89-draft.html#3.5.2.1 https://port70.net/~nsz/c/c89/c89-draft.html#A.6.5.8 For consistency with other integral types, plain `char` bit-fields are unsigned, regardless of the `--signed-chars` option. Fixes #1047
This commit is contained in:
committed by
Oliver Schmidt
parent
41cee0eb44
commit
4e4e4c2d21
@@ -764,9 +764,9 @@ static int ParseFieldWidth (Declaration* Decl)
|
||||
/* TODO: This can be relaxed to be any integral type, but
|
||||
** ParseStructInit currently only supports up to int.
|
||||
*/
|
||||
if (SizeOf (Decl->Type) != SizeOf (type_uint)) {
|
||||
/* Only int sized types may be used for bit-fields for now */
|
||||
Error ("cc65 currently only supports unsigned int bit-fields");
|
||||
if (SizeOf (Decl->Type) > SizeOf (type_uint)) {
|
||||
/* Only int-sized or smaller types may be used for bit-fields for now */
|
||||
Error ("cc65 currently only supports char-sized and int-sized bit-fields");
|
||||
return -1;
|
||||
}
|
||||
|
||||
|
||||
@@ -870,9 +870,13 @@ SymEntry* AddBitField (const char* Name, const Type* T, unsigned Offs,
|
||||
if (!SignednessSpecified) {
|
||||
/* int is treated as signed int everywhere except bit-fields; switch it to unsigned,
|
||||
** since this is allowed for bit-fields and avoids sign-extension, so is much faster.
|
||||
** enums set SignednessSpecified to 1 to avoid this adjustment.
|
||||
** enums set SignednessSpecified to 1 to avoid this adjustment. Character types
|
||||
** actually distinguish 3 types of char; char may either be signed or unsigned, which
|
||||
** is controlled by `--signed-chars`. In bit-fields, however, we perform the same
|
||||
** `char -> unsigned char` adjustment that is performed with other integral types.
|
||||
*/
|
||||
CHECK ((Entry->Type->C & T_MASK_SIGN) == T_SIGN_SIGNED);
|
||||
CHECK ((Entry->Type->C & T_MASK_SIGN) == T_SIGN_SIGNED ||
|
||||
IsTypeChar (Entry->Type));
|
||||
Entry->Type->C &= ~T_MASK_SIGN;
|
||||
Entry->Type->C |= T_SIGN_UNSIGNED;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user