Tech Info & FAQs

From: lti@earthlink.net
Newsgroups: rec.games.video.classic
Subject: Action Pack Techie Info
Date: 23 Mar 1995 09:21:35 GMT
Organization: LTI
Lines: 126
Message-ID: <3kreiv$6tu@mars.earthlink.net>
NNTP-Posting-Host: lti.earthlink.net
X-Newsreader: AIR News 3.X (SPRY, Inc.)

Hello, everyone!


It seems that there are a number opinions floating around out there
about the Atari 2600 Action Pack that I thought I should clear up.

If you're not a techie, please accept my appologies for littering the
group with this post.


By way of introduction, I'm Mike Livesay, a game developer/programmer
for the past 15 years.  Past work includes Miner2049er, Arcade Game
Construction Set, The Heist, It Came From The Desert, etc, etc.  Other
software-related interests include video compression, color
quantization, and image processing.

I began development on Action Pack in June '94, just shipped Volume I
(as you know), and am in the process of finishing additional volumes. 
Action Pack, while certainly not huge project like DOOM, was a fun
technology project and a nice detour into my youth and the early days
of video gaming, when the 6502 was king and cart ROMs were measured in
1,000 (not millions) of bits.

Action Pack was not only my first commercial PC/Windows product, but
also my first experience with 486 assembly coding.  I've spent most of
my time on game console programming, usually in 68K, 6502, or Z80 ASM.
The last time I had done x86 programming was when the 8088 was first
released and before the IBM PC hit the market (back when the Apple II
was king)!

The Pack was written almost entirely in 486 assembly using Borland's
Turbo Assembler.  The GUI stuff was written in C++ (no OOP extensions
used, though - not really necessary) using Borland Turbo C++ 4.0.  All
of the emulation stuff was written in 486ASM.  I didn't want to have
to rely on Win32 DLLs, so everything was written assuming a 486 Win16
target system.  However, 32-bit 486 instructions are used all over the
place in the emulator, especially in the line rendering code.

There have been some comments that the Pack may have written in BASIC
(wince).  Sorry, but even C would be too slow to implement a 2600
emulator.  Assembly was the only realistic option.  I've heard some
folks discussing the possibility of writing an 2600 emulator in a high
level language - forget it, not possible.

Action Pack makes use of the Micro$ofts's WinG DLL, which actually
works fairly well.  However, due to the fact that I wanted the games
to run in both normal (320x200) and maximized (640x400) windows, it
was necessary to write some pretty tricky code that makes WinG only
update regions that have changed from frame to frame.  The original
2600 screen resolution was 160x200 (the number of active lines depends
on the game), so even in the normal window size, the emulator is
doubling the pixels horizontally.  Even at 15fps, Action Pack pumps a
whole lot of pixels to the screen, especially in a maximized window. 
However, when I last profiled the emulator, WinG updates were only
eating up 10% of the CPU on each displayed frame on a P90.

In order to keep game play responsive, the emulator must emulate each
frame (actually, NTSC field) in 1/60th of a second or less (16ms). 
Unfortunately, on all but the highest end, PCI/VLB video cards, it is
impossible to update even a 320x200 window at 60 frames/sec.  So the
emulator runs the game code at full speed, while refreshing the
display at some user assignable interval (usuall every 4th frame, or
15fps).

The emulator consists of two major pieces of code:  a TIA emulator and
a 6507 (6502) CPU emulator.  The two are pretty intimate with one
another, since it is necessary to count the number of CPU cycles that
have executed between TIA register writes to keep everything in sync. 
The TIA emulator ended up working as sort of a state machine and only
gets activated when a TIA register is accessed and changes, and at the
end of each line, when the pixels are actually created.  Mid-scanline
register changes and collision register reads are supported, which was
a major programming pain.  Many games do things like change the color
registers.

VCS sound emulation was a painful exercise, mainly due to the fact
that Windows doesn't support the Adlib very well (there is no support
for loading custom timbres) and the multimedia low level audio API is
not supported robustly by all sound card drivers.  The sound API was
designed mainly to play back short samples in a linear fashion with a
known duration.  Since the emulator knows nothing about the sound
effects in an emulated game, it needs to play back very short, looped
waveforms.  I experimented with sampling all waveforms at all
frequencies, and wrote something similar to WAVEMIX.DLL, which worked,
but not fast enough, due to the fact that the loop rate had to be kept
down to 250ms or less (otherwise, one would need a huge amount of
memory to store all the samples).  The final workable solution I came
up with is that all VCS waveforms, except noise, are emulated using
FM.  The noise sample are played back using PCM, and only once noise
sample at a time can play.  The noise samples were created by actually
sampling the output of a VCS, at each frequency setting.  Note that
VCS games that use noise extensively, like River Raid and Kaboom!,
tend to run a bit slower, depending on the PCM sound driver being
used.  All FM access was done at the register level - I had to bypass
the MIDI interface stuff.

Since Activision had no source code to any of the games, I had to
design and breadboard a cart reader/emulator, so I could upload
commerical carts and also write and download test code to an actual
VCS.  Activision only supplied me with a bunch of store-bought carts,
some of which were PAL versions (which made things interesting).

I am currently negotiating a contract to do additional volumes with
Activision (assume we can agree on a price).  They are obtaining the
rights to non-Activision carts, so expect to see more classics in
coming volumes.  Also expect foriegn versions (French, German, among
them).

Anyway, Action Pack, while not being the most complicated thing I've
worked on in my career, was a kick to write nevertheless.  I hope you
have as much fun playing with it as I did writing it.

Please feel free to mail me any questions you might have about Action
Pack - I'll try to answer what I can.  I welcome all comments, so
flame me, ignore me, or pat me on the back, as you see fit!

Best Regards,

Mike.
-------------------
Answers to some common Pack-related questions:

WHY DOES THE EMULATOR NEED A 486?

Two reasons:  Speed and the BSWAP instruction.  Most 486 instructions
execute in one cycle (assuming no cache hits), which was a saving
grace for the emulator.  The BSWAP instruction, which executes in one
cycle, was a life saver during pixel rendering in the TIA emulator.  I
won'y bore you with details, but it really came in handy.


WHY DOES A 1MHz 6502-BASED VCS EMULATOR NEED A 486/33 MINIMUM SYSTEM?

There are a number of reasons, but I'll name the two main ones. 
First, the emulator has to do much more than just emulate a 6507 CPU. 
It also has to emulate VCS sound and graphics hardware, which is quite
involved.  Not to mention that, in order to run at full speed, it has
to emulate the 6507 code, along with the sound/graphics functions, at
a very high rate, like 320,000 emulated instructions per second!

Secondly, the line-oriented nature of the VCS graphics hardware causes
a whole lot of processing to be done on every scan line.  On emulaters
with sprite-oriented displays, like the the Genesis or the C64, when a
sprite is plotted very little processing has to be done to render each
line of the sprite.  On the VCS, collision detection, graphics, color,
etc are modified on at line, sometimes even multiple time during a
line.  This creates a whole lot of overhead for the emulator.

Not to mention the fact that there are no X/Y position registers; the
position of a single line sprite is determined by position the TV beam
is currently at when a write to a certain TIA register occurs, in REAL
TIME.  This creates the necessity to count the actual number of cycles
each CPU instruction takes as the game code is executing. (side note: 
very few VCSgames do a WSYNC at each line - this would have made life
much easier, but life in game programmer is seldon easy!)


DOES THE EMULATOR REALLY USE 4 MEG?

No.  The code and data take up less than 500K and the PCM sound
samples take up 1200K.  But, adding in Windows, WinG, etc, and to keep
things from swapping out during game play, 4MB seemed a reasonable
requirement.


WHAT WAS THE EMULATOR WRITTEN IN?

90% 486 assembly and 10% C, using Borland Turbo C++ and Turbo ASM.


WHY WINDOWS INSTEAD OF DOS?

Wasn't really my decision, but I think it was the correct one on
Activision's part.  There is a lot of demand for Windows-based games
at this time.  The only real competition is MS Arcade, which has been
out for a while.  Under DOS, Action Pack would be competing with
raycasting-based games like Doom, Dark Forces, etc, which are
certainly much flashier and are at the leading edge of the industry,
technically speaking.  Action Pack was never intended to push the
envelope (although, it certainly was not a walk in the park to code)
or compete with such games.  Its a retro/nostalgia kind of thing. 
Also, going to DOS would only have speed things up by 10..20%, not a
real major gain.  I definately agree that Windows has its downside,
but Action Pack was well suited for the platform.


WHAT IS THE IDEAL SYSTEM FOR ACTION PACK?

A 486/66 with a fast (VLB/PCI) video card, reasonable amount of cache
memory (256K) and a Pro Audio Spectum 16 (or compatible) with the
latest sound drivers.  Best display mode is 640x480, 256 colors. 
NOTE:  you must run Action Pack in 256-color mode, or things will look
wierd and run slow.

Return to Atari 2600 Action Pack information.
lkseitz@hiwaay.net
Moved to HiWAAY: 1 Jul 1996; Last Modified: 1 Jul 1996