Color BASIC String Theory, part 2

See also: Part 1

I had no intention of turning this in to another rambling multi-part article series, so maybe I can wrap this up in just two posts…

But first, in a comment to the first part, William “Lost Wizard” Astle said:

String manipulation is, in fact, entirely predictable, and logical. I think I’ll do an article on the internals of string evaluation and manipulation in Color Basic. It’s actually fairly straight forward, but the whys and hows of it get a bit complex. – William Astle

His article explains how the string handling really works (unlike my random speculation), and includes some interesting tips about how to make things faster by allocating extra string space if memory allows. Check it out here:

http://lost.l-w.ca/0x05/color-basic-and-string-handling/

…and then read the rest of my speculative fiction about how strings work.

Speculative Fiction About How Strings Work

My original purpose was to talk about making sure you CLEAR enough string memory to keep your program from crashing if a user types in a big string or maxes out all the variables. This will become important when I get to designing the new version of the *ALLRAM* BBS I plan to write.

Today, let’s look at why this mattered when I created the original version back in 1983.

When I first created *ALLRAM*, I decided I would make the message board work on 64-character lines. That would fit nicely on two lines of the CoCo’s 32-column screen, or one line on the 64-column TRS-80 Model I and III screens. Isn’t it weird thinking back to the early days before 80 columns became standard?

On a cassette based CoCo, after a PCLEAR 0 (no graphics pages), I could get 31015 bytes of memory to use for storing the userlog and message base.

Somehow, I decided that I would let each message be up to 10 lines long (640 bytes max), and I used an extra line to store the TO, FROM and SUBJECT of the message. From looking at the old source code, I see that usernames were limited to 20 characters, and the subject was 18 for some reason. They were combined using backslash delimiters like this:

TO\FROM\SUBJECT

At max size (20+1+20+1+18) that is 60 bytes. Ah, now I understand why the subject must have been 18. This makes each message take up to 700 bytes total (640+60).

I used a two-dimensional array to hold the 11 lines for each of the 20 messages:

DIM MS$(19,10)

Twenty messages at 700 bytes each is 14000 bytes. I had to make sure I CLEARed that much plus anything else needed for operation.

I also decided I would store the userlog as an array of strings that contained the username, password and access level, separated by a delimiter:

USERNAME\PASSWORD\LEVEL

A username could be up to 20 characters long and a password 8 characters. The level was supposed to be from 0-9, so it could be 1 character. Thus, the maximum userlog string could be 31 bytes (20+1+8+1+1).

I decided I would allow up to 201 users. I suppose I expected user 0 to be the SysOp (system operator) account.

DIMNM$(200)

This meant the userlog could take up to 6231 bytes (201*31).

Now the RAM storage used by the BBS was 20231 bytes, assuming every byte of every user and message entry was full.

I knew I would need some extra storage for temporary strings and such, so I just rounded up:

CLEAR 21000

And that’s how *ALLRAM* came to exist on a 32K Radio Shack Color Computer. (I had 64K, but Color BASIC did not make use of anything past 32K, and I didn’t know assembly language yet which would have been needed to access the upper 64K. See this article for details.)

You may be able to see that this was a “safe” approach, but probably had a TON of memory that just wasn’t being used. Consider a message like this:

----------------------------------------------------------------
TO: ALLEN HUFFMAN
FR: SYSOP
SB: COOL!

THIS SIMULATES WHAT A MESSAGE MIGHT HAVE LOOKED LIKE ON THE 1983
*ALLRAM* BBS, USING UP TO TEN TEXT LINES OF 64 CHARACTERS. IF I
DIDN'T USE IT ALL, THE REMAINING MEMORY WAS JUST WASTED.

-<>- ALLEN HUFFMAN -<>-
----------------------------------------------------------------

The array that contained this message would look like this:

            ----------------------------------------------------------------
MS$(0,0) = "ALLEN HUFFMAN\SYSOP\COOL!"
MS$(0,1) = "THIS SIMULATES WHAT A MESSAGE MIGHT HAVE LOOKED LIKE ON THE 1983"
MS$(0,2) = "*ALLRAM* BBS, USING UP TO TEN TEXT LINES OF 64 CHARACTERS. IF I"
MS$(0,3) = "DIDN'T USE IT ALL, THE REMAINING MEMORY WAS JUST WASTED."
MS$(0,4) = ""
MS$(0,5) = "-<>- ALLEN HUFFMAN -<>-"
MS$(0,6) = ""
MS$(0,7) = ""
MS$(0,8) = ""
MS$(0,9) = ""
MS$(0,10)= ""

The row of dashes (“—“) represents the 64 character line size. As you can see, this small message is wasting much space because of unused lines, and even leftover space on the lines that are used.

If I were going to redesign this today (which I am), I have several ideas that would probably make it far more efficient, allowing for much larger message bases using the same memory (or, worst case, the same size if every message was maxed out).

Any thoughts?

I’ll share mine in a future installment.

Leave a Reply