473,322 Members | 1,522 Online
Bytes | Software Development & Data Engineering Community
Post Job

Home Posts Topics Members FAQ

Join Bytes to post your question to a community of 473,322 software developers and data experts.

Binary set - how to calculate offset?

Hello C programmers,

I have a small web game with the server part written in C
which runs on OpenBSD (Linux and Cygwin work too).

I've found out, that for me it's most comfortable to
make the different player states to be of power of 2:

typedef enum user_phase {
CONNECTING = 0,
CHAT_LOBBY = 1,
CHAT_TABLE = 2,
KIBITZING = 4,
BIDDING_1 = 8,
TAKING_TALON_1 = 16,
TAKING_TALON_2 = 32,
DISCARDING_1 = 64,
DISCARDING_2 = 128,
DECLARING = 256,
BIDDING_2 = 512,
ALL_PASSED = 1024,
PLAYING = 2048,
PHASE_MAX = 4096
} user_phase;

/* all phases from above except CONNECTING */
#define ALL_PHASES ((uint32_t) 0xFFFFFFFF)

That way I can check quickly for several phases
at once, for example here in event handling table:

static const EVENT_ENTRY EVENT_TABLE[] = {
/* valid phases args table turn */
{ ALL_PHASES, NO, ANY, ANY, handle_alive },
{ ALL_PHASES, YES, ANY, ANY, handle_chat },
{ ALL_PHASES ^ KIBITZING, NO, ANY, NO, handle_kuku },
{ CHAT_LOBBY, YES, NO, ANY, handle_join },
{ ALL_PHASES ^ CHAT_LOBBY, NO, YES, ANY, handle_lobby },
{ BIDDING_1 | BIDDING_2, YES, YES, YES, handle_bid },
{ ALL_PASSED | PLAYING, YES, YES, YES, handle_card }
};

However my problem is to perform the backward
mapping: given a user_phase, how do I found out,
which power of 2 is it (sorry for my awkward language)?

For example here how I find phase names currently:

static const char* PHASE_NAMES[] = {
"CONNECTING",
"CHAT_LOBBY",
"CHAT_TABLE",
"KIBITZING",
"BIDDING_1",
"TAKING_TALON_1",
"TAKING_TALON_2",
"DISCARDING_1",
"DISCARDING_2",
"DECLARING",
"BIDDING_2",
"ALL_PASSED",
"PLAYING"
};

const char*
phase_name(user_phase phase)
{
unsigned i;

for (i = 0; i < sizeof(PHASE_NAMES) / sizeof(char*); i++)
if ((uint32_t)(1 << i) == phase)
return PHASE_NAMES[i];

return "UNKNOWN";
}

Is there a better way maybe?

Thank you
Alex

May 4 '07 #1
3 3932
A. Farber wrote On 05/04/07 10:26,:
[...]

However my problem is to perform the backward
mapping: given a user_phase, how do I found out,
which power of 2 is it (sorry for my awkward language)?
(The snipped material makes clear that user_phase
is an enum value equal to a positive integral power of 2.)

Stripped to its essentials, you are looking for the
binary logarithm of a value. There are many ways to do
this, some of which are described at

http://graphics.stanford.edu/~seander/bithacks.html

WARNING: Some of the hacks on this page rely on non-portable
assumptions, not always mentioned explicitly. Be alert!
Also, the claims about operation count, branch counts, and
so on are strongly platform-dependent.

--
Er*********@sun.com
May 4 '07 #2
On May 5, 2:26 am, "A. Farber" <Alexander.Far...@gmail.comwrote:
I've found out, that for me it's most comfortable to
make the different player states to be of power of 2:

typedef enum user_phase {
CONNECTING = 0,
CHAT_LOBBY = 1,
CHAT_TABLE = 2,
[...]
PLAYING = 2048,
PHASE_MAX = 4096
I find it is clearer to use hexadecimal constants in this
situation; it also helps to reduce typoes, sign, and
out-of-range constant problems.
/* all phases from above except CONNECTING */
#define ALL_PHASES ((uint32_t) 0xFFFFFFFF)
What is the purpose of that cast?

NB. 0xFFFFFFFF is already an unsigned int (unless you
are on a system where int is less than 32 bits, in which
the code is still correct but it will be a long or an unsigned
long).
That way I can check quickly for several phases
at once, for example here in event handling table:

static const EVENT_ENTRY EVENT_TABLE[] = {
A minor point; uppercase identifiers starting with E are
reserved for implementation use whenever <errno.his
included. Suppose you were coding on an embedded
air conditioning system, the system vendor might have
defined an error condition where the entry to an air vent
was malfunctioning: E VENT_ENTRY !
/* valid phases args table turn */
{ CHAT_LOBBY, YES, NO, ANY, handle_join },
{ ALL_PHASES ^ CHAT_LOBBY, NO, YES, ANY, handle_lobby },
{ BIDDING_1 | BIDDING_2, YES, YES, YES, handle_bid },
{ ALL_PASSED | PLAYING, YES, YES, YES, handle_card }

However my problem is to perform the backward
mapping: given a user_phase, how do I found out,
which power of 2 is it (sorry for my awkward language)?
They way I do such things is (note, I like to always
prefix my enums to avoid unexpected clashes and
avoid causing undefind behaviour if one starts with E):

enum
{ PHASE_NONE
, PHASE_FOO
, PHASE_BAR
, PHASE_QUX
, NUM_PHASES
};

char const *phase_names[] =
{ "(none)"
, "foo"
, "bar"
, "qux"
};

STATIC_ASSERT( NUM_PHASES == dimof(phase_names) );

Note, this can be hard to keep in sync if the tables are
large. So it is possible to combine those two into one file, eg.
MAGIC( PHASE_FOO, "foo" )
MAGIC( PHASE_BAR, "bar" )
and then include this file in both your .h and .c files but
with MAGIC defined to produce the enum if it is a .h, and
produce the string table if it is a .c .

For the flags table, assuming your goal is compactness:
#define FT(X) P_##X = 1UL << PHASE_##X
enum
{ FT(FOO)
, FT(BAR)
, FT(QUX)
};
#undef FT

then the table will look like:
{ P_ALL_PASSED | P_PLAYING, YES, YES, YES, handle_card }
etc.
May 6 '07 #3
On 6 May 2007 16:03:28 -0700, Old Wolf <ol*****@inspire.net.nzwrote:
<snip>
#define ALL_PHASES ((uint32_t) 0xFFFFFFFF)
NB. 0xFFFFFFFF is already an unsigned int (unless you
are on a system where int is less than 32 bits, in which
the code is still correct but it will be a long or an unsigned
long).
Or int is more than 32 (nonpadding) bits in which case that fits in,
and is, signed int. (Although it would then safely promote to unsigned
int where needed in an expression, which is probably enough.)
enum
{ PHASE_NONE
, PHASE_FOO
, PHASE_BAR
, PHASE_QUX
BTW the canonical metaname is quux with two u's. Not to be confused
with two yous, two ewes, you toos, U-2s, yoohoos, tutus, or youse. <G>

- formerly david.thompson1 || achar(64) || worldnet.att.net
May 21 '07 #4

This thread has been closed and replies have been disabled. Please start a new discussion.

Similar topics

2
by: Albert Tu | last post by:
Hi, I am learning and pretty new to Python and I hope your guys can give me a quick start. I have an about 1G-byte binary file from a flat panel x-ray detector; I know at the beggining there...
13
by: E-Star | last post by:
I have a binary file that I want to read some numbers out of. However the numbers are 32bit floats. How can I get the numbers into a C program to use? I can do the calculations manually....but...
9
by: Ching-Lung | last post by:
Hi all, I try to create a tool to check the delta (diff) of 2 binaries and create the delta binary. I use binary formatter (serialization) to create the delta binary. It works fine but the...
9
by: Hemang Shah | last post by:
Hello fellow Coders! ok, I"m trying to write a very simple application in C#. (Yes its my first program) What I want to do is : 1) Open a binary file 2) Search this file for a particular...
8
by: Gordon Knote | last post by:
Hi can anyone tell me what's the best way to search in binary content? Best if someone could post or link me to some source code (in C/C++). The search should be as fast as possible and it would...
12
by: jamie | last post by:
I wish to create an array that points to, say, the middle section of a different array. eg Original array > second array-------------^ Is this at all possible?? I think that it...
6
by: | last post by:
Hi all, is there a better way to stream binary data stored in a table in sql 2005 to a browser in .net 2.0? Or is the code same as in .net 1.1? We noticed that in certain heavy load scenarios,...
6
by: al jones | last post by:
I picked a good project to try to learn to use VS - and up till now everything has worked the way I expect. The code is from a VS.net class, which I picked up on the web, from which I've extracted...
4
by: dondigitech | last post by:
I want to convert hex to binary without losing bits. I want to preserve the 8-bits because I ultimately need a 24-bit string to grab information from. I am just using this line of code for the...
0
by: ryjfgjl | last post by:
ExcelToDatabase: batch import excel into database automatically...
0
isladogs
by: isladogs | last post by:
The next Access Europe meeting will be on Wednesday 6 Mar 2024 starting at 18:00 UK time (6PM UTC) and finishing at about 19:15 (7.15PM). In this month's session, we are pleased to welcome back...
0
by: Vimpel783 | last post by:
Hello! Guys, I found this code on the Internet, but I need to modify it a little. It works well, the problem is this: Data is sent from only one cell, in this case B5, but it is necessary that data...
0
by: ArrayDB | last post by:
The error message I've encountered is; ERROR:root:Error generating model response: exception: access violation writing 0x0000000000005140, which seems to be indicative of an access violation...
1
by: CloudSolutions | last post by:
Introduction: For many beginners and individual users, requiring a credit card and email registration may pose a barrier when starting to use cloud servers. However, some cloud server providers now...
1
by: Shællîpôpï 09 | last post by:
If u are using a keypad phone, how do u turn on JavaScript, to access features like WhatsApp, Facebook, Instagram....
0
by: af34tf | last post by:
Hi Guys, I have a domain whose name is BytesLimited.com, and I want to sell it. Does anyone know about platforms that allow me to list my domain in auction for free. Thank you
0
by: Faith0G | last post by:
I am starting a new it consulting business and it's been a while since I setup a new website. Is wordpress still the best web based software for hosting a 5 page website? The webpages will be...
0
isladogs
by: isladogs | last post by:
The next Access Europe User Group meeting will be on Wednesday 3 Apr 2024 starting at 18:00 UK time (6PM UTC+1) and finishing by 19:30 (7.30PM). In this session, we are pleased to welcome former...

By using Bytes.com and it's services, you agree to our Privacy Policy and Terms of Use.

To disable or enable advertisements and analytics tracking please visit the manage ads & tracking page.