Saturday, March 6, 2010

Current status - 20% ish

My initial plan was to simply convert everything in place and avoid anything that would change how the code worked.  I would start one C file at a time, starting with main.c, and stub out all missing functions.  The first files I had to pull in were larncons.c and data.c (constants and data structures).

That's when I decided my original plan was not going to work.  Version 12.4 is likely pretty close to the original source, and that's a big problem.  I'm pretty sure that the version of C this was written for originally didn't support enumerations and possibly didn't support structs (if it did, I'll cry.  There are 3 structs so far -- cel (dungeon cell, 5 fields, sphere of annihilation (5 fields), monster (11 fields).  The core character data (20+ fields) is just a byte* with a ton of #defines that identify what field lives where.  And the only appropriate name for this pointer is of course "c", which is obviously short for character.  You couldn't shorten that to char since that's a type, so it's just c.  c[HP] c[GOLD], etc.  Monsters are also a giant list of #defines.  It's enough to make a person cry.

So I started refactoring while converting.  It took several hours to convert the data and constants file, then 2 evenings to finish converting main and stubbing out functions.  I tried starting the game, but was immediately hit by not having the save files/scoreboard functions done, so I started converting those (scores.c).  That took another evening.  I'd estimate that I'm about 20% done.  So far the conversion looks like:

CURRENT: 8 File(s) 128,537 bytes
OLD : 43 File(s) 458,630 bytes

Some of my notes from the conversion:

1) Scroll names all begin with \0.  I wondered about this for awhile and eventually found out that that entry is being used as the number of scrolls the player has.  I don't even think modern C allows true compiled in string entries to be modified.  That's right out.

2) I had to change all file serialization.  Larn does it in classic C style.  lwrite( pointer, sizeof( pointer type ) );  I'm using readers and writers and actually explicitly writing out each field.  For the moment, that means I am no longer backwards compatible.  That's fine, I'm going to tag files with a header to differentiate between these new saves and old saves.  I'll implementreading of old save files later.

3) I remember in college saying how stupid it was to even have a boolean type.  It's just an int under the hood anyway.  I regret that.  I'm converting many implicit booleans into true booleans.  It wouldn't be so nice except the code sometimes expects 1 to be true and other times expects 0 to be true (-1 being false).

4) The core data objects are now a LarnData object.  Encapsulation, heaven forbid!  Of course, that means most functions now need this object passed into them.  Honestly, I'm not sure if this was a bad idea yet or not.  It was this or make everything (EVERYTHING) static.

5) I changed many longs to UInt64's since it was obvious that you can't carry negative gold.  Unfortunately, this has introduced a lot of casting issues.  This may have been a mistake.

No comments:

Post a Comment