PHWinfo banniere

Titres
PORTAIL ANNUAIRE ARTICLES COMPARATEUR HÉBERGEURS DEVIS FORUMS RÉDUCTEUR D'URL
Précédent   PHWinfo > Autres forums > Forum Programmation & Conception > comp.lang.c > Finding number of bits of integer
S'inscrire FAQ Membres Recherche Messages du jour Marquer les forums comme lus
Finding number of bits of integer

Réponse
 
LinkBack Outils de la discussion
Vieux 18/10/2007, 14h37   #1
Richard Heathfield
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Daniel Kraft said:

> Hi,
>
> I do need to implement something similar to C++'s std::bitset in C; for
> this, I use an array of int's to get together any desired number of
> bits, possibly larger than 32/64 or anything like this.
>
> So of course it does not matter how many bits a single int has, but I do
> need a reliable way to find it out.
>
> I think of something like
> CHAR_BITS*sizeof(int)
> will do the trick, am I right here?


Well, you mean CHAR_BIT, but yes, that will give you the total number of
bits occupied by the int - including the sign bit, at least (but possibly
more than) 15 value bits, and at least (but possibly more than) no padding
bits.

> I'm just confused that it is *CHAR*_BITS; in reference to the usual
> example, there are some machines where char's have 9 bits--but is in
> this case int required to have some multiple of 9 bits, too?


Yes, CHAR_BIT gives the number of bits in a char, and a char is exactly one
byte wide, and every object must be a whole number of bytes wide. If
CHAR_BIT is 9, then objects must be a multiple of 9 bits wide.

The usual way to implement a "bit array", though, is as follows:

1) decide how many bits, B, you want your array to have (if you decide this
at runtime, you'll need to allocate the memory in step 2 dynamically,
check that you've got it, and release it when you're done);
2) allocate (B + CHAR_BIT - 1) / CHAR_BIT bytes (unsigned char foo[N] = {0}
or unsigned char *foo = calloc((B + CHAR_BIT - 1) / CHAR_BIT, 1),
initialising it all to 0 (you can use = {0} unless you allocate
dynamically, in which case use calloc - one of the rare occasions where
this is a good idea);
3) use macros to get, set, and test individual bits.

http://www.snippets.org has some macros that can be used for this purpose.

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
  Réponse avec citation
Vieux 18/10/2007, 14h38   #2
vipvipvipvip.ru@gmail.com
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

It is CHAR_BIT and not CHAR_BITS, ignoring that, if sizeof(anything)
== 2
we know that it's twice the size of a `char'.

  Réponse avec citation
Vieux 18/10/2007, 14h55   #3
Ben Bacarisse
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Richard Heathfield <rjh@see.sig.invalid> writes:

> Daniel Kraft said:
>
>> I do need to implement something similar to C++'s std::bitset in C;

<snip>
> The usual way to implement a "bit array", though, is as follows:

<snip>
> 2) allocate (B + CHAR_BIT - 1) / CHAR_BIT bytes (unsigned char
> foo[N] = {0}

<snip>

It is probably worth adding the reason one uses an unsigned integer
type is that shift operations are well-defined on these, and the
reason one uses unsigned char in particular is that it is guaranteed
not to have any padding bits.

--
Ben.
  Réponse avec citation
Vieux 18/10/2007, 15h50   #4
Richard Heathfield
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Ben Bacarisse said:

<snip>

> It is probably worth adding the reason one uses an unsigned integer
> type is that shift operations are well-defined on these, and the
> reason one uses unsigned char in particular is that it is guaranteed
> not to have any padding bits.


It is indeed worth adding. Thank you.

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
  Réponse avec citation
Vieux 18/10/2007, 16h06   #5
Erik Trulsson
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

vipvipvipvip.ru@gmail.com wrote:
> It is CHAR_BIT and not CHAR_BITS, ignoring that, if sizeof(anything)
> == 2
> we know that it's twice the size of a `char'.


Yes, but we do not know that it contains twice as many 'usable' bits.

E.g. one could have

CHAR_BIT == 9
sizeof(int) == 2
INT_MIN == -32767
INT_MAX == 32767

and it would be perfactly fine as far as the C standard is concerned.
In this case an int would occupy 18 bits, but 2 of those bits would
be padding and such an int would not be able to hold than a 16-bit wide
int without padding would.




--
<Insert your favourite quote here.>
Erik Trulsson
ertr1013@student.uu.se
  Réponse avec citation
Vieux 18/10/2007, 16h18   #6
Daniel Kraft
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Finding number of bits of integer

Hi,

I do need to implement something similar to C++'s std::bitset in C; for
this, I use an array of int's to get together any desired number of
bits, possibly larger than 32/64 or anything like this.

So of course it does not matter how many bits a single int has, but I do
need a reliable way to find it out.

I think of something like
CHAR_BITS*sizeof(int)
will do the trick, am I right here?

I'm just confused that it is *CHAR*_BITS; in reference to the usual
example, there are some machines where char's have 9 bits--but is in
this case int required to have some multiple of 9 bits, too? I.e., does
sizeof(something) always give the size of this as multiples of
sizeof(char) or could such a 9 bit char be paired with 16/32 bit integers?

Thank you very much,
Daniel

--
Got two Dear-Daniel-Instant Messages
by MSN, associate ICQ with stress--so
please use good, old E-MAIL!
  Réponse avec citation
Vieux 18/10/2007, 18h36   #7
Martin Wells
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Daniel:

> I think of something like
> CHAR_BITS*sizeof(int)
> will do the trick, am I right here?



What you're looking for is the quantity of "value representational
bits". These are the bits that actually take place in arithmetic and
bit-shifting, and they are distinct from the other two varieties of
bits that can be present in an int type (i.e. the single sign bit and
the padding bits). On most systems, integer types don't have
padding... but the Standard permits that they may, which is why in
fully-portable programming you should shy away from
sizeof(unsigned)*CHAR_BIT for getting the VR bits.

The C Standard doesn't provide an operator or macro or anything for
determing the quantity of VR bits, but such a macro can be "own-
rolled". Of course, you can use a simple loop to work it out, but it's
a little trickier to get the figure as a compile-time constant (e.g.
for use in array dimensions).

A chap called Hallvard B Furuseth, (a genius if you ask me), devised a
macro called IMAX_BITS that's used for determing the amount of bits
you need to represent a given number, and he has it as a compile time
constant. (The only restriction is that the "given number" must be all
one's in binary: e.g. 1111, or 11111, or 111111). Given that the
highest number for any unsigned integer type will always be all-one's,
we can use this macro. Here's an example:

Quantity of value bits in unsigned short = IMAX_BITS(USHRT_MAX)

I've reshaped Hallvard's macro so that it can be used in the following
form:

Quantity of value bits in unsigned short = VALUE_BITS_UINT(unsigned
short)

The macro is a follows:

#define VALUE_BITS_UINT(my_type) (((my_type)-1) /
(((my_type)-1)%0x3fffffffL+1) \
/0x3fffffffL %0x3fffffffL *30 \
+ ((my_type)-1)%0x3fffffffL \
/(((my_type)-1)%31+1)/31%31*5 + 4-12/(((my_type)-1)%31+3))

Don't ask me how it works coz I haven't a clue. What I do know is that
it's tried and tested and definitely does work.

There's probably a way of getting the VR bits for a signed type also
but to be honest I've no interest in it because I shudder at the
thought of using signed types for bit manipulation.

Best of luck.

Martin

  Réponse avec citation
Vieux 18/10/2007, 18h37   #8
Martin Wells
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Daniel:

> I think of something like
> CHAR_BITS*sizeof(int)
> will do the trick, am I right here?



What you're looking for is the quantity of "value representational
bits". These are the bits that actually take place in arithmetic and
bit-shifting, and they are distinct from the other two varieties of
bits that can be present in an int type (i.e. the single sign bit and
the padding bits). On most systems, integer types don't have
padding... but the Standard permits that they may, which is why in
fully-portable programming you should shy away from
sizeof(unsigned)*CHAR_BIT for getting the VR bits.

The C Standard doesn't provide an operator or macro or anything for
determing the quantity of VR bits, but such a macro can be "own-
rolled". Of course, you can use a simple loop to work it out, but it's
a little trickier to get the figure as a compile-time constant (e.g.
for use in array dimensions).

A chap called Hallvard B Furuseth, (a genius if you ask me), devised a
macro called IMAX_BITS that's used for determing the amount of bits
you need to represent a given number, and he has it as a compile time
constant. (The only restriction is that the "given number" must be all
one's in binary: e.g. 1111, or 11111, or 111111). Given that the
highest number for any unsigned integer type will always be all-one's,
we can use this macro. Here's an example:

Quantity of value bits in unsigned short = IMAX_BITS(USHRT_MAX)

I've reshaped Hallvard's macro so that it can be used in the following
form:

Quantity of value bits in unsigned short = VALUE_BITS_UINT(unsigned
short)

The macro is a follows:

#define VALUE_BITS_UINT(my_type) (((my_type)-1) /
(((my_type)-1)%0x3fffffffL+1) \
/0x3fffffffL %0x3fffffffL *30 \
+ ((my_type)-1)%0x3fffffffL \
/(((my_type)-1)%31+1)/31%31*5 + 4-12/(((my_type)-1)%31+3))

Don't ask me how it works coz I haven't a clue. What I do know is that
it's tried and tested and definitely does work.

There's probably a way of getting the VR bits for a signed type also
but to be honest I've no interest in it because I shudder at the
thought of using signed types for bit manipulation.

Best of luck.

Martin

  Réponse avec citation
Vieux 18/10/2007, 18h39   #9
Martin Wells
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Daniel:

> I think of something like
> CHAR_BITS*sizeof(int)
> will do the trick, am I right here?



What you're looking for is the quantity of "value representational
bits". These are the bits that actually take place in arithmetic and
bit-shifting, and they are distinct from the other two varieties of
bits that can be present in an int type (i.e. the single sign bit and
the padding bits). On most systems, integer types don't have
padding... but the Standard permits that they may, which is why in
fully-portable programming you should shy away from
sizeof(unsigned)*CHAR_BIT for getting the VR bits.

The C Standard doesn't provide an operator or macro or anything for
determing the quantity of VR bits, but such a macro can be "own-
rolled". Of course, you can use a simple loop to work it out, but it's
a little trickier to get the figure as a compile-time constant (e.g.
for use in array dimensions).

A chap called Hallvard B Furuseth, (a genius if you ask me), devised a
macro called IMAX_BITS that's used for determing the amount of bits
you need to represent a given number, and he has it as a compile time
constant. (The only restriction is that the "given number" must be all
one's in binary: e.g. 1111, or 11111, or 111111). Given that the
highest number for any unsigned integer type will always be all-one's,
we can use this macro. Here's an example:

Quantity of value bits in unsigned short = IMAX_BITS(USHRT_MAX)

I've reshaped Hallvard's macro so that it can be used in the following
form:

Quantity of value bits in unsigned short = VALUE_BITS_UINT(unsigned
short)

The macro is a follows:

#define VALUE_BITS_UINT(my_type) (((my_type)-1) /
(((my_type)-1)%0x3fffffffL+1) \
/0x3fffffffL %0x3fffffffL *30 \
+ ((my_type)-1)%0x3fffffffL \
/(((my_type)-1)%31+1)/31%31*5 + 4-12/(((my_type)-1)%31+3))

Don't ask me how it works coz I haven't a clue. What I do know is that
it's tried and tested and definitely does work.

There's probably a way of getting the VR bits for a signed type also
but to be honest I've no interest in it because I shudder at the
thought of using signed types for bit manipulation.

Best of luck.

Martin

  Réponse avec citation
Vieux 18/10/2007, 19h17   #10
Daniel Kraft
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

>>> I do need to implement something similar to C++'s std::bitset in C;
> <snip>
>> The usual way to implement a "bit array", though, is as follows:

> <snip>
>> 2) allocate (B + CHAR_BIT - 1) / CHAR_BIT bytes (unsigned char
>> foo[N] = {0}

> <snip>
>
> It is probably worth adding the reason one uses an unsigned integer
> type is that shift operations are well-defined on these, and the
> reason one uses unsigned char in particular is that it is guaranteed
> not to have any padding bits.


Hm... Actually I was thinking of using int's, as the main operations in
my case are not accessing individual bits but rather doing binary and's
and or's on the whole bitset--I know, premature optimization... but it
seems to me to be much cleaner and probably "faster" to use ints for
this instead of chars (always unsigned, of course).

So is there a way to get the number of *usable* bits of a single
unsigned? Or should I use unsigned chars and do the binary operations
per-char instead of per-int?

Cheers,
Daniel

--
Got two Dear-Daniel-Instant Messages
by MSN, associate ICQ with stress--so
please use good, old E-MAIL!
  Réponse avec citation
Vieux 18/10/2007, 21h12   #11
Daniel Kraft
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

>> I think of something like
>> CHAR_BITS*sizeof(int)
>> will do the trick, am I right here?

>
>
> What you're looking for is the quantity of "value representational
> bits". These are the bits that actually take place in arithmetic and
> bit-shifting, and they are distinct from the other two varieties of
> bits that can be present in an int type (i.e. the single sign bit and
> the padding bits). On most systems, integer types don't have
> padding... but the Standard permits that they may, which is why in
> fully-portable programming you should shy away from
> sizeof(unsigned)*CHAR_BIT for getting the VR bits.
>
> The C Standard doesn't provide an operator or macro or anything for
> determing the quantity of VR bits, but such a macro can be "own-
> rolled". Of course, you can use a simple loop to work it out, but it's
> a little trickier to get the figure as a compile-time constant (e.g.
> for use in array dimensions).


Of course, I also thought about calculating this once at runtime (which
is easy and should not cost much), but of course a compile-time constant
is much better--with C++ template meta-programming this shouldn't be
hard to solve, but with the C preprocessor it could get a bit trickier...

However, thanks for this nice macro! I think I can put it into
something I can use (because I do have some restrictions on which bits
are really usable for me).

Cheers,
Daniel
  Réponse avec citation
Vieux 18/10/2007, 22h21   #12
Richard Heathfield
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Daniel Kraft said:

<snip>

> So is there a way to get the number of *usable* bits of a single
> unsigned?


Sure. UINT_MAX has to be one less than a power of 2, so you can do this
(once only will do):

#include <limits.h>

int count_value_bits_in_unsigned_int(void)
{
int rv = 0;
unsigned int n = UINT_MAX;
while(n > 0)
{
++rv;
n >>= 1;
}
return rv;
}

> Or should I use unsigned chars and do the binary operations
> per-char instead of per-int?


Well, I would, but it's up to you.

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
  Réponse avec citation
Vieux 18/10/2007, 23h44   #13
pete
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Richard Heathfield wrote:
>
> Daniel Kraft said:
>
> <snip>
>
> > So is there a way to get the number of *usable* bits of a single
> > unsigned?

>
> Sure. UINT_MAX has to be one less than a power of 2,
> so you can do this (once only will do):
>
> #include <limits.h>
>
> int count_value_bits_in_unsigned_int(void)
> {
> int rv = 0;
> unsigned int n = UINT_MAX;
> while(n > 0)
> {
> ++rv;
> n >>= 1;
> }
> return rv;
> }


rv should be type unsigned, instead of type int.
The number of value bits in type unsigned isn't
guaranteed to be representable as an int type value.

--
pete
  Réponse avec citation
Vieux 18/10/2007, 23h54   #14
Peter Pichler
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

pete wrote:
> Richard Heathfield wrote:
>
>>int count_value_bits_in_unsigned_int(void)
>>{
>> int rv = 0;

<snip>
>> return rv;
>>}

>
> rv should be type unsigned, instead of type int.
> The number of value bits in type unsigned isn't
> guaranteed to be representable as an int type value.


Can you name one architecture with more than 32767 value bit
in unsigned?
  Réponse avec citation
Vieux 19/10/2007, 00h40   #15
pete
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Peter Pichler wrote:
>
> pete wrote:


> > The number of value bits in type unsigned isn't
> > guaranteed to be representable as an int type value.

>
> Can you name one architecture with more than 32767 value bit
> in unsigned?


I've never even seen a padding bit.

--
pete
  Réponse avec citation
Vieux 19/10/2007, 00h43   #16
Keith Thompson
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Daniel Kraft <d@domob.eu> writes:
[...]
> Of course, I also thought about calculating this once at runtime
> (which is easy and should not cost much), but of course a compile-time
> constant is much better--with C++ template meta-programming this
> shouldn't be hard to solve, but with the C preprocessor it could get a
> bit trickier...
>
> However, thanks for this nice macro! I think I can put it into
> something I can use (because I do have some restrictions on which bits
> are really usable for me).


Another possibility is to write a small C program that computes the
number of value bits and writes out a valid C header file that
declares it as a macro. You can then include this generated header
file in your program.

You'll have to have some mechanism for compiling and executing this
small program as part of your build procedure. Doing so is beyond the
scope of C, but shouldn't be difficult for a "make"-like tool -- *if*
you're compiling on the same system where you're going to run the
program. If you're cross-compiling, things get a bit trickier.

Or you can maintain it manually, but that's error-prone.

--
Keith Thompson (The_Other_Keith) kst-u@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <*> <http://users.sdsc.edu/~kst>
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"
  Réponse avec citation
Vieux 19/10/2007, 07h35   #17
Richard Heathfield
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

pete said:

> Richard Heathfield wrote:
>>
>> Daniel Kraft said:
>>
>> <snip>
>>
>> > So is there a way to get the number of *usable* bits of a single
>> > unsigned?

>>
>> Sure. UINT_MAX has to be one less than a power of 2,
>> so you can do this (once only will do):
>>
>> #include <limits.h>
>>
>> int count_value_bits_in_unsigned_int(void)
>> {
>> int rv = 0;
>> unsigned int n = UINT_MAX;
>> while(n > 0)
>> {
>> ++rv;
>> n >>= 1;
>> }
>> return rv;
>> }

>
> rv should be type unsigned, instead of type int.
> The number of value bits in type unsigned isn't
> guaranteed to be representable as an int type value.


We can deduce from the standard that it is representable as an int type
value. The int type uses the same amount of storage as the unsigned int
type, and has the same alignment requirements. Given that UINT_MAX must be
representable as an unsigned int, and given that it must be at least 65535
(at which point rv can be at most 16), and given that n grows very much
faster than log2(n), it follows that rv will grow very slowly.

Since int must be capable of storing the value 32767, my little function
will work on any system with unsigned ints containing 32767 value bits -
that is, even if there were a disparity between the number of the value
bits in the two types so great that INT_MAX were 32767 and UINT_MAX were 1
less than 2 to the power 32767 (a number so large I hesitate to post it
here!), my function would still cope.

And with each extra value bit in an int, you more than double the UINT_MAX
it can cope with.

An implementation on which my function did not work would not merely be
run-of-the-mill clc-style pathological. It would be psychopathological.

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
  Réponse avec citation
Vieux 19/10/2007, 13h48   #18
Martin Wells
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

pete:

> > #include <limits.h>

>
> > int count_value_bits_in_unsigned_int(void)
> > {
> > int rv = 0;
> > unsigned int n = UINT_MAX;
> > while(n > 0)
> > {
> > ++rv;
> > n >>= 1;
> > }
> > return rv;
> > }

>
> rv should be type unsigned, instead of type int.
> The number of value bits in type unsigned isn't
> guaranteed to be representable as an int type value.



While we're making ridiculous critiques, the most blatantly obvious
flaw if you ask me is the use of a "while" instead of a "do".

As for signed integer types Vs unsigned integer types, I default to
unsigned rather than signed.

My own function would've been something like:

unsigned VRbitsInUInt(void)
{
unsigned vr = 16;

unsigned x = 0x8000u;

while (x <<= 1) ++vr;

return vr;
}

Or a more generic one (if we pretend we can pass a type):

template <typename UIntType>
unsigned VRbitsUIntType(void)
{
unsigned vr = 8;

UIntType x = 0x80u;
while (x <<= 1) ++vr;

return vr;
}

Martin

  Réponse avec citation
Vieux 19/10/2007, 22h54   #19
pete
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

Richard Heathfield wrote:
>
> pete said:
>
> > Richard Heathfield wrote:
> >>
> >> Daniel Kraft said:
> >>
> >> <snip>
> >>
> >> > So is there a way to get the number of *usable* bits of a single
> >> > unsigned?
> >>
> >> Sure. UINT_MAX has to be one less than a power of 2,
> >> so you can do this (once only will do):
> >>
> >> #include <limits.h>
> >>
> >> int count_value_bits_in_unsigned_int(void)
> >> {
> >> int rv = 0;
> >> unsigned int n = UINT_MAX;
> >> while(n > 0)
> >> {
> >> ++rv;
> >> n >>= 1;
> >> }
> >> return rv;
> >> }

> >
> > rv should be type unsigned, instead of type int.
> > The number of value bits in type unsigned isn't
> > guaranteed to be representable as an int type value.

>
> We can deduce from the standard
> that it is representable as an int type value.


> An implementation on which my function
> did not work would not merely be
> run-of-the-mill clc-style pathological.
> It would be psychopathological.


You can't have it both ways.

If you can deduce from the standard that it
is representable as an int type value,
then there can't be an implementation,
psychopathological or otherwise,
where your function won't work.

--
pete
  Réponse avec citation
Vieux 20/10/2007, 00h54   #20
$)CHarald van D)&k
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

On Fri, 19 Oct 2007 17:54:00 -0400, pete wrote:
> Richard Heathfield wrote:
>>
>> pete said:
>>
>> > Richard Heathfield wrote:
>> >>
>> >> Daniel Kraft said:
>> >>
>> >> <snip>
>> >>
>> >> > So is there a way to get the number of *usable* bits of a single
>> >> > unsigned?
>> >>
>> >> Sure. UINT_MAX has to be one less than a power of 2, so you can do
>> >> this (once only will do):
>> >>
>> >> #include <limits.h>
>> >>
>> >> int count_value_bits_in_unsigned_int(void) {
>> >> int rv = 0;
>> >> unsigned int n = UINT_MAX;
>> >> while(n > 0)
>> >> {
>> >> ++rv;
>> >> n >>= 1;
>> >> }
>> >> return rv;
>> >> }
>> >
>> > rv should be type unsigned, instead of type int. The number of value
>> > bits in type unsigned isn't guaranteed to be representable as an int
>> > type value.

>>
>> We can deduce from the standard
>> that it is representable as an int type value.

>
>> An implementation on which my function did not work would not merely be
>> run-of-the-mill clc-style pathological. It would be psychopathological.

>
> You can't have it both ways.
>
> If you can deduce from the standard that it is representable as an int
> type value, then there can't be an implementation, psychopathological or
> otherwise,
> where your function won't work.


The standard doesn't guarantee that

int main(int argc, char *argv[])
{
return 0;
}

will work, since it declares two objects whose size is allowed to be
greater than 65535 bytes. This is already taking the environmental limits
to the extreme. A hosted implementation on which
UINT_MAX > (1 << INT_MAX) - 1
would require sizeof(int) to not only simply equal or exceed 2^16, but to
equal or exceed 2^32752. A freestanding implementation might be able to
get it done with a lower number of bytes, by using excessively large
bytes, but it would still require such an utterly insane implementation
that you're better off worrying about clowns breaking into your house,
doing a silly dance, and leaving with your toilet paper.
  Réponse avec citation
Vieux 20/10/2007, 04h37   #21
Richard Heathfield
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

pete said:

> Richard Heathfield wrote:


<snip>

>
>> An implementation on which my function
>> did not work would not merely be
>> run-of-the-mill clc-style pathological.
>> It would be psychopathological.

>
> You can't have it both ways.
>
> If you can deduce from the standard that it
> is representable as an int type value,
> then there can't be an implementation,
> psychopathological or otherwise,
> where your function won't work.


Yes, I think I wrote that one as I was going along, and forgot to go back
to edit out the claim that it is deducible. (It might yet be, but in fact
I failed to do it.)

Let's just say that I would certainly worry about the possibility of a
non-ASCII character set, I have been known to worry about the number of
bits in a byte being greater than 8, I might worry about the endianness of
a machine being different to the endianness of data in a file on that
machine, and I could even conceivably worry about the result of
right-shifting a negative value - but I would not be even slightly
concerned about the possibility of an implementation using more than
INT_MAX value bits in an unsigned int.

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
  Réponse avec citation
Vieux 20/10/2007, 05h16   #22
DiAvOl
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

My question is probably off-topic, but can someone please explain me
what are padding bits in an unsigned integer? (and how can affect the
code)

One more question:

This code

#include <limits.h>

int count_value_bits_in_unsigned_int(void)
{
int rv = 0;
unsigned int n = UINT_MAX;
while(n > 0)
{
++rv;
n >>= 1;
}
return rv;

}

should always give 32 on a 4 byte int system, is this correct?

Thanks for your time

  Réponse avec citation
Vieux 20/10/2007, 06h07   #23
Richard Heathfield
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

DiAvOl said:

> My question is probably off-topic, but can someone please explain me
> what are padding bits in an unsigned integer?


They are bits that do not contribute to the value of the object, but which
are there for the convenience of the implementor (or, perhaps they are
inconveniently there, and are ignored for the convenience of the
implementor!).

Let's just say, for the sake of argument, that you wanted to write a C
compiler on a system with 8-bit bytes, and that you wanted to give a
*guarantee* to your users that any legal pointer could be converted to a
legal unsigned int and vice versa - but you only had a 28-bit address
space, i.e. 256 MB of RAM. It would be sensible to keep your byte size at
the natural size for the machine, 8 bits, and it's clear you're going to
need four bytes for an unsigned int on this system. But if *any* unsigned
int value translates to a valid pointer value and you only have 2^28
addresses, then it's clear that you're not going to be able to use the top
four bits of your unsigned int. So you'd probably define UINT_MAX as
268435455 and ignore the top four bits completely. They'd still be there,
of course, but they would not contribute to the value of the unsigned int.
In fact, you'd probably have to mask them out during calcs, just in case
some bright spark managed to set them anyway.

> One more question:
>
> This code
>
> #include <limits.h>
>
> int count_value_bits_in_unsigned_int(void)
> {
> int rv = 0;
> unsigned int n = UINT_MAX;
> while(n > 0)
> {
> ++rv;
> n >>= 1;
> }
> return rv;
>
> }
>
> should always give 32 on a 4 byte int system, is this correct?


No, it isn't correct. Consider a "4 byte int" system with bytes that are
117 bits in size, and no padding bits. On such a system, the function will
return 468.

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
  Réponse avec citation
Vieux 20/10/2007, 09h10   #24
DiAvOl
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

> Let's just say, for the sake of argument, that you wanted to write a C
> compiler on a system with 8-bit bytes, and that you wanted to give a
> *guarantee* to your users that any legal pointer could be converted to a
> legal unsigned int and vice versa - but you only had a 28-bit address
> space, i.e. 256 MB of RAM. It would be sensible to keep your byte size at
> the natural size for the machine, 8 bits, and it's clear you're going to
> need four bytes for an unsigned int on this system. But if *any* unsigned
> int value translates to a valid pointer value and you only have 2^28
> addresses, then it's clear that you're not going to be able to use the top
> four bits of your unsigned int. So you'd probably define UINT_MAX as
> 268435455 and ignore the top four bits completely. They'd still be there,
> of course, but they would not contribute to the value of the unsigned int.
> In fact, you'd probably have to mask them out during calcs, just in case
> some bright spark managed to set them anyway.


What values would those 4 top "padded bits" contain? 0 or 1?
I'm trying to figure out if padding bits affects the code in any way,
for example what if the user wanted to use those 4 top bits for
bitwise operations?

Can someone give an example how would the code be affected when
running on a system without padding bit ints and when running on one
with padding bit ?

Thanks for the above example & sorry for my bad english.



  Réponse avec citation
Vieux 20/10/2007, 09h44   #25
Richard Heathfield
Aucun Avatar
 
Messages: n/a
Hébergeur:
Par défaut Re: Finding number of bits of integer

DiAvOl said:

<snip>

>> So you'd probably define
>> UINT_MAX as 268435455 and ignore the top four bits completely. They'd
>> still be there, of course, but they would not contribute to the value of
>> the unsigned int. In fact, you'd probably have to mask them out during
>> calcs, just in case some bright spark managed to set them anyway.

>
> What values would those 4 top "padded bits" contain? 0 or 1?


One or other of those, yes.

> I'm trying to figure out if padding bits affects the code in any way,
> for example what if the user wanted to use those 4 top bits for
> bitwise operations?


The user could actually do this, of course, simply by accessing the object
representation via type punning:

unsigned int n = some_value;
unsigned char *p = (unsigned char *)&n;
/* can now write to n's object representation via p[0] through p[(sizeof n)
- 1] */

If the user chooses to bitshift via a series of p[i] hacks, he could, and
the padding bits would then muddy the waters. But if the user instead
shifted the unsigned int itself, well, that's a value-based operation, so
the padding bits would have no effect on the value of the shifted unsigned
int (and the implementation would have to ensure that this was the case).

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
Google users: <http://www.cpax.org.uk/prg/writings/googly.php>
"Usenet is a strange place" - dmr 29 July 1999
  Réponse avec citation
Réponse