View previous topic - View next topic |
Author |
Message |
RuneLancer Mage
Joined: 17 Jun 2005 Posts: 441
|
Posted: Wed Aug 24, 2005 11:48 pm Post subject: Nifty obscure code |
[quote] |
|
We've all run into and used obscure code. Particularly when dealing with low-level languages (the lower-level, the easier to write obscure stuff :P ) So, how about we share obscure yet useful code? :)
My favorite, though hardly obscure, is this little nifty trick to count how many bits are set in an integer.
Code: | int countBits(int p_value)
{
int counter = x & 1;
while(p_value)
counter += (p_value >>= 1) & 1;
return counter;
} |
Why would anyone want to know how many bits are set in a value? This was written as part of a 65816 ROM hacking utility I wrote which would parse some 65816 code and show what happened in memory. But it has many in-game uses, particularly when you need to count how many flags are set (for instance, to know how many statuses are affecting a character in an RPG; dunno, first thing that came to mind...)
So hey. There's mine. Let's see some more. :P While I'm at it, is there anyone here who programs on very old platforms for fun, like pre-CD console systems or pre-HD computers? _________________ Endless Saga
An OpenGL RPG in the making. Now with new hosting!
|
|
Back to top |
|
|
DeveloperX 202192397
Joined: 04 May 2003 Posts: 1626 Location: Decatur, IL, USA
|
Posted: Thu Aug 25, 2005 12:06 am Post subject: Re: Nifty obscure code |
[quote] |
|
RuneLancer wrote: | While I'm at it, is there anyone here who programs on very old platforms for fun, like pre-CD console systems or pre-HD computers? |
Yes. I still use my Commodore 64 to this day.
I started with this monster 17 years ago, and not once has it ever let me down.
As for obscure code.....I don't have anything that would be useful to anyone offhand. :) Another time perhaps. _________________ Principal Software Architect
Rambling Indie Games, LLC
See my professional portfolio
|
|
Back to top |
|
|
biggerUniverse Mage
Joined: 18 Nov 2003 Posts: 326 Location: A small, b/g planet in the unfashionable arm of the galaxy
|
Posted: Thu Aug 25, 2005 2:05 am Post subject: |
[quote] |
|
Actually, the oldest online contest in the world happens to be about this topic: http://www0.us.ioccc.org/years.html _________________ We are on the outer reaches of someone else's universe.
|
|
Back to top |
|
|
LeoDraco Demon Hunter
Joined: 24 Jun 2003 Posts: 584 Location: Riverside, South Cali
|
Posted: Thu Aug 25, 2005 5:11 am Post subject: |
[quote] |
|
While obscure for the fact that I hardly ever see method pointers (but not obscure otherwise), I submit a hack I made that simplified the logistics for mapping an object method to an interpreter operator call:
Code: | ret = (c1->ret)->*decode[c2](c3->ret) |
where decode is
Code: | map< int, BinOp > decode |
(BinOp was declared as:
Code: | typedef Type * (Type::*BinOp) ( Type * ); |
and is filled something like
Code: | decode['*'] = &Type::operator* |
(with all binary operators thrown in).
While I never really cared for the way the heirarchy was set up, that one method was really sexy: depending upon whatever c2 was, the appropriate C++ operator would be called on object c1->ret (which subclasses Type somewhere), with passing c3->ret along as argument.
The neat thing is, all conditional operations are pushed to the decode container, which means there was little code that I had to write to get that running. And, assuming no new operators were ever added, everything was perfectly extensible. _________________ "...LeoDraco is a pompus git..." -- Mandrake
|
|
Back to top |
|
|
DrunkenCoder Demon Hunter
Joined: 29 May 2002 Posts: 559
|
Posted: Thu Aug 25, 2005 6:14 am Post subject: |
[quote] |
|
um, that bit count is linear in the position of the highest set bit.
Code: |
inline size_t bits(int n)
{
size_t c = !!n;
while( n &= n - 1)
++c;
return c;
}
|
this variant is linar in the number of set bits.
if you done any hardcore optimnizations on the pentium you know how dreaded branches are so I came up with theese
Code: |
//non branching
inline int max(int a, int b){ return a + ((b - a) & ((b - a) < 0) - 1);}
inline int min(int a, int b){ return a + ((b - a) & (0 < (b - a)) - 1);}
|
oh, and finally when dealing with textures etc knowing if a number is a power of two or getting the next power of two thats greater or equal is usefull, that can be done like this:
Code: |
inline bool ispow2(unsigned u){ return !(u & u - 1);}
inline unsigned nextpow2(unsigned x)
{
--x;
x |= x >> 1;
x |= x >> 2;
x |= x >> 4;
x |= x >> 8;
x |= x >> 16;
return x + 1;
}
|
ispow2 will report that 0 is a power of two, and while not mathematicly correct I like it that way.
that's from my bitwise.hpp utility header :) _________________ If there's life after death there is no death, if there's no death we never live. | ENTP
|
|
Back to top |
|
|
Mandrake elementry school minded asshole
Joined: 28 May 2002 Posts: 1341 Location: GNARR!
|
Posted: Fri Aug 26, 2005 2:54 pm Post subject: |
[quote] |
|
Quote: |
So hey. There's mine. Let's see some more. :P While I'm at it, is there anyone here who programs on very old platforms for fun, like pre-CD console systems or pre-HD computers?
|
Off and on. I still code on TRS-180 CoCo for fun (I still have one, heh, hooked up to my television). I used to work at a company that used an ICE-4000 system to power an ATM. It was powered by a z80 chip, with an included chip for hardware encryption on the keypad.
That was fun. And talk about obscure code- since the code itself couldn't be anymore than 12k to fit into memory we had to do all sorts of fun tricks to get shit to work. But, I can't post any of that without being sued by violating my NDA I signed (bastards).
I think they use a Windows XP on the latest ATM's. Fun while it lasted.
Funny you should mention this. Even though the GBA is still *new* I consider it a retro machine, and I've been doing an assload of coding on it in the last month. _________________ "Well, last time I flicked on a lighter, I'm pretty sure I didn't create a black hole."-
Xmark
http://pauljessup.com
|
|
Back to top |
|
|
RuneLancer Mage
Joined: 17 Jun 2005 Posts: 441
|
Posted: Fri Aug 26, 2005 8:37 pm Post subject: |
[quote] |
|
[quote="Mandrake"] Quote: | Funny you should mention this. Even though the GBA is still *new* I consider it a retro machine, and I've been doing an assload of coding on it in the last month. |
In response to that, I consider all forms of non-CD-based console developement to be retro-programming (even though, as you've said, some of the cartridge-based systems on the market are still quite recent.)
Most of what I do is SNES-based, mainly because working with assembly is a thrill that makes funny things happen in my pants. ;) I like having to work under tightly restrictive environments and having code be as low level as it gets (for some reason, high-level code is a terrible pain for me to work with, and low-level code reads just like plain english to me..) _________________ Endless Saga
An OpenGL RPG in the making. Now with new hosting!
|
|
Back to top |
|
|
janus Mage
Joined: 29 Jun 2002 Posts: 464 Location: Issaquah, WA
|
Posted: Sat Aug 27, 2005 1:11 pm Post subject: |
[quote] |
|
DrunkenCoder wrote: | if you done any hardcore optimnizations on the pentium you know how dreaded branches are so I came up with theese
Code: |
//non branching
inline int max(int a, int b){ return a + ((b - a) & ((b - a) < 0) - 1);}
inline int min(int a, int b){ return a + ((b - a) & (0 < (b - a)) - 1);}
|
|
While we're on the topic of branching...
Code: | inline int ClipValue(int value, int minimum, int maximum) {
int iClipped;
iClipped = -(int)(value < minimum);
value = (minimum & iClipped) | (value & ~iClipped);
iClipped = -(int)(value > maximum);
return (maximum & iClipped) | (value & ~iClipped);
} |
Code: | inline Byte ClipByte(int value) {
value &= (-(int)!(value < 0));
return ((255 & (-(int)(value > 255))) | (value)) & 0xFF;
} |
|
|
Back to top |
|
|
Xegnma Monkey-Butler
Joined: 03 Apr 2003 Posts: 53 Location: Trapped in Middle Earth
|
Posted: Thu Sep 08, 2005 9:12 pm Post subject: |
[quote] |
|
I found this a while back: Bit Twiddling Hacks. Might be of some use to you. You're gonna flip when you see how to count bits set using a Look-up table(LUT). :)
[EDIT]
And if you're interested try to get your hands on a few books by Micheal Abrash. Here are a few of his more popular titles (some of which are available online for free):
- Zen of Code Optimization: The Ultimate Guide to Writing Software That Pushes PCs to the Limit
- Graphics Programming Black Book (PDF format)
- Zen of Graphics Programming (2nd Edition)
|
|
Back to top |
|
|
Nodtveidt Demon Hunter
Joined: 11 Nov 2002 Posts: 786 Location: Camuy, PR
|
Posted: Sat Sep 24, 2005 2:08 pm Post subject: |
[quote] |
|
My team works with the TurboGrafx 16 console...it's a CD-based system when upgraded but it's certainly retro. Unfortunately for the sake of this thread, there's really not much obfuscation possible unless you really suck at C... ;) ...then again, you could really hack a bunch of shit together in assembly and confuse the hell out of everyone...but most TG game developers use HuC, a specialized C compiler developed exclusively for the console which is pretty advanced and has an excellent "runtime library", so to speak. Of course, the hardware hackers still write in assembly and do some really funky shit... _________________ If you play a Microsoft CD backwards you can hear demonic voices. The scary part is that if you play it forwards it installs Windows. - wallace
|
|
Back to top |
|
|
omega_alpha Fluffy Bunny of Doom
Joined: 07 Jun 2003 Posts: 16 Location: California
|
Posted: Sun Oct 23, 2005 3:54 pm Post subject: |
[quote] |
|
I wrote a generic templated version before, but this one was for a very specific purpose:
Code: |
typedef unsigned long u32;
...
template<typename T>
u32 countBits()
{
T value = ~0;
u32 bits = 0;
while(value != 0) {
value >>= 1;
bits++;
}
return bits;
}
...
std::cout << "Unsigned Long: " << countBits<u32>() << std::endl;
|
now, of course you have to set T to a valid integer data type, but thats the only hangup. I used this to ensure that datatypes I was working with were of the specific size I required.
|
|
Back to top |
|
|
DrunkenCoder Demon Hunter
Joined: 29 May 2002 Posts: 559
|
Posted: Sun Oct 23, 2005 6:19 pm Post subject: |
[quote] |
|
omega_alpha wrote: | I wrote a generic templated version before, but this one was for a very specific purpose:
Code: |
typedef unsigned long u32;
...
template<typename T>
u32 countBits()
{
T value = ~0;
u32 bits = 0;
while(value != 0) {
value >>= 1;
bits++;
}
return bits;
}
...
std::cout << "Unsigned Long: " << countBits<u32>() << std::endl;
|
now, of course you have to set T to a valid integer data type, but thats the only hangup. I used this to ensure that datatypes I was working with were of the specific size I required. |
or you could simply use the standard library...
Code: |
template <typename T>
int bits(){ return std::numeric_limits<T>::digits + std::numeric_limits<T>::is_signed;}
|
works for any integer type... _________________ If there's life after death there is no death, if there's no death we never live. | ENTP
|
|
Back to top |
|
|