For anyone browsing Catakig's source code, hoping to make some sense of it, here's a brief summary . . .

FILE (DIS-)ORGANIZATION

The source code is grouped into three major parts:

  1. the MacOS X Cocoa application (in Source/Cocoa)
  2. the Apple II emulation library (in Source/LibAppleII)
  3. generally useful C and Objective-C stuff, not specific to this project (in Source/Misc)

Part 1 depends on parts 2 & 3. Part 2 depends on part 3. Part 1 is allowed to have Cocoa-specific code, whereas the other two are meant to be portable, and should rely only on FoundationKit, AppKit, and standard Unix APIs.

File Prefix.pch is the project's pre-compiled header file. Its content is implicitly included by every source file.

The LibAppleII emulation library is driven from the outside. (You call it -- it doesn't call you.) The client of the library, the surrounding application, is expected to pass along all relevant user input, to call the 65c02 interpreter, and to call the video frame renderer, whenever these tasks are needed. The library doesn't initiate any action on its own.

Documentation of the source code is pretty scant right now. Most methods do have a brief summary at their beginning, and most files have a few comments at the top describing the contents. But there isn't anything right now to document how the whole thing hangs together.

DESIGN GOALS

Adhere as much as possible to POSIX, OpenGL, and the common subset of Cocoa and GNUStep. Maybe port someday to generic Linux/BSD + GNUStep platforms. OpenAL might be a another good standard, for audio output.

Target MacOS X 10.3, and avoid 10.4+ features. (Occasionally review this decision though.) It would be nice to support 10.2 as well, as I was trying to do initially, but it seems time to move on. Note that MacOS X on Intel must always at least version 10.4.

For now, don't bother supporting arbitrary Apple II peripherals in arbitrary slot configurations. Rather, aim for a "canonical" Apple II with the same feature set across all models. These features are:

NAMING CONVENTIONS IN THE SOURCE

In general, identifiers are in mixed-case form (e.g. "doItNow") -- except C pre-processor macros, which follow the ancient C tradition of being all uppercase, with words separated by underscores ("DO_IT_NOW").

All LibAppleII identifiers in the publicly visible scope, except enum constants, begin with "A2".

Enumeration constants begin with "kf" when they're flags (integers having a single 1 bit, e.g. 0x400), "ks" when bit-shift values (0 to 31), "km" when bit-masks (e.g. 0x3FF), and just "k" otherwise. Public enumeration constants also have "A2" in their prefix. Flag and shift enum values are often defined in pairs: e.g. "kfALTZP" and "ksALTZP".

Names of object instance variables begin with "m" and are mixed-case ("mFavoriteColor"). This convention seems to go against popular Objective-C practice, but I don't care. It helps me.

Methods supplied by the author that don't exist in the standard class libraries have capitalized names. For example: "InputChar" and not "inputChar" -- but on the other hand "keyDown" and not "KeyDown". In other words, lower-cased methods will have some pre-defined purpose in the system libraries, because of class inheritance, whereas the upper-cased methods are entirely new additions. Again, this is a personal convention that helps me.

Methods begining with an underscore ( _ ) are considered private to the class, for internal use only. Objective-C has no "private" attribute like C++ does to enforce this behavior however. Any Objective-C message can be sent to any object at any time. But the underscore alerts the reader that the method isn't supposed to be called from just anywhere.

CODING HABITS OF THE AUTHOR THAT WILL ANNOY YOU

Hard tabs are used in the source, and are expected to be 4 spaces wide. Might switch to soft tabs (all spaces) at some point.

The author often exploits the fact that C literal strings are arrays of constant characters, that C characters can also serve as small integers, and that therefore short literal strings make handy little in-line lookup tables of small integers. For example:

  number_of_one_bits = "\0\1\1\2\1\2\2\3"[n]
You're probably entitled to be outraged at this practice.

Comments ending with "??" or "!!" are considered temporary, and not part of the settled in-line documentation -- if such a thing will ever exist. These annotations usually mark code that is volatile, experimental, or whose need is questionable.

There are some C99 (and non-C89) features used pretty frequently: (1) declaring for-loop variables in-line; (2) initializing structure fields by name instead of by position. The first one is pretty well known, but use of the second feature doesn't seem very widespread and might be a surprise to some.

The author prefers using "and", "or", and "not" over "&&", "||" and "!". Macros defining these pseudo-keywords are in the header Prefix.pch.

Colin K.
Oct. 2006