Create an account

Very important

  • To access the important data of the forums, you must be active in each forum and especially in the leaks and database leaks section, send data and after sending the data and activity, data and important content will be opened and visible for you.
  • You will only see chat messages from people who are at or below your level.
  • More than 500,000 database leaks and millions of account leaks are waiting for you, so access and view with more activity.
  • Many important data are inactive and inaccessible for you, so open them with activity. (This will be done automatically)


Thread Rating:
  • 306 Vote(s) - 3.69 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Specifying size of enum type in C

#1
Already read through [this related question][1], but was looking for something a little more specific.

- Is there a way to tell your compiler specifically how wide you want your enum to be?
- If so, how do you do it? I know how to specify it in C#; is it similarly done in C?
- Would it even be worth doing? When the enum value is passed to a function, will it be passed as an `int`-sized value regardless?



[1]:

[To see links please register here]

Reply

#2
I believe there is a flag if you are using GCC.

> -fshort-enums
Reply

#3
You can force it to be at least a certain size by defining an appropriate value. For example, if you want your enum to be stored as the same size as an `int`, even though all the values would fit in a `char`, you can do something like this:

typedef enum {
firstValue = 1,
secondValue = 2,

Internal_ForceMyEnumIntSize = MAX_INT
} MyEnum;

Note, however, that the behavior can be dependent on the implementation.

As you note, passing such a value to a function will cause it to be expanded to an int anyway, but if you are using your type in an array or a struct, then the size will matter. If you really care about element sizes, you should really use types like `int8_t`, `int32_t`, etc.
Reply

#4
> Is there a way to tell your compiler
> specifically how wide you want your
> enum to be?

In general case no. Not in standard C.

> Would it even be worth doing?

It depends on the context. If you are talking about passing parameters to functions, then no, it is not worth doing (see below). If it is about saving memory when building aggregates from enum types, then it might be worth doing. However, in C you can simply use a suitably-sized integer type instead of enum type in aggregates. In C (as opposed to C++) enum types and integer types are almost always interchangeable.

> When the enum value is passed to a function, will it be passed as an int-sized value regardless?

Many (most) compilers these days pass all parameters as values of natural word size for the given hardware platform. For example, on a 64-bit platform many compilers will pass all parameters as 64-bit values, regardless of their actual size, even if type `int` has 32 bits in it on that platform (so, it is not generally passed as "int-sized" value on such a platform). For this reason, it makes no sense to try to optimize enum sizes for parameter passing purposes.

Reply

#5
It depends on the values assigned for the enums.

Ex:
If the value greater than 2^32-1 is stored, the size allocated for the overall enum will change to the next size.

Store 0xFFFFFFFFFFFF value to a enum variable, it will give warning if tried to compile in a 32 bit environment (round off warning)
Where as in a 64 bit compilation, it will be successful and the size allocated will be 8 bytes.
Reply

#6
Even if you are writing strict `C` code, the results are going to be compiler dependent. Employing the strategies from this thread, I got some interesting results...

**enum_size.c**

```c
#include <stdio.h>

enum __attribute__((__packed__)) PackedFlags {
PACKED = 0b00000001,
};

enum UnpackedFlags {
UNPACKED = 0b00000001,
};

int main (int argc, char * argv[]) {
printf("packed:\t\t%lu\n", sizeof(PACKED));
printf("unpacked:\t%lu\n", sizeof(UNPACKED));
return 0;
}
```

```nano
$ gcc enum_size.c
$ ./a.out
packed: 4
unpacked: 4
```

```nano
$ gcc enum_size.c -fshort_enums
$ ./a.out
packed: 4
unpacked: 4
```

```nano
$ g++ enum_size.c
$ ./a.out
packed: 1
unpacked: 4
```

```nano
$ g++ enum_size.c -fshort_enums
$ ./a.out
packed: 1
unpacked: 1
```

In my example above, I did not realize any benefit from `__attribute__((__packed__))` modifier until I started using the C++ compiler.

**EDIT:**

@technosaurus's suspicion was correct.

By checking the size of `sizeof(enum PackedFlags)` instead of `sizeof(PACKED)` I see the results I had expected...

```c++
printf("packed:\t\t%lu\n", sizeof(enum PackedFlags));
printf("unpacked:\t%lu\n", sizeof(enum UnpackedFlags));
```

I now see the expected results from `gcc`:

```nano
$ gcc enum_size.c
$ ./a.out
packed: 1
unpacked: 4
```

```nano
$ gcc enum_size.c -fshort_enums
$ ./a.out
packed: 1
unpacked: 1
```
Reply



Forum Jump:


Users browsing this thread:
1 Guest(s)

©0Day  2016 - 2023 | All Rights Reserved.  Made with    for the community. Connected through