• Please review our updated Terms and Rules here

What makes a CP/M program a CP/M program (and not just, say, a z80 program)?

cj7hawk

Veteran Member
Joined
Jan 25, 2022
Messages
2,347
Location
Perth, Western Australia.
So here's an interesting, and already contentious question.

What makes a CP/M program a CP/M program?

It is 8080 opcodes only?

Is it loads at $0100?

Is it "can be loaded by CP/M 1.0"?

Is it "recognizes the BDOS and stays clear?

Would a microsoft basic (original) that runs under CP/M be a CP/M program?

At what point would a program no longer be reasonably recognized by the community as a CP/M program and it suddenly becomes a non-CP/M program?

What are reasonable boundaries of terminology here?

This is a contentious issue, I understand. Please keep responses polite and respectful - Play the ball, not the man.
 
Previous conversational considerations:
 
Some people think CP/M means "Should run on an Altair" and I think there's a reasonable basis for that
Since the Altair did not ship with CP/M, that point is moot.

So here's an interesting, and already contentious question.
The question is contentious because there is no correct answer. It's another one of those things to discuss in circles until the end of time.

There are roughly four major categories based on timeline: CP/M 1.4 (8080), CP/M 2.2 (8080), CP/M 2.2 (Z80) and CP/M 3 (Z80).

My base expectation is that applications which need CP/M 3 also need a Z80, and that all other applications are either 8080-compatible or properly labelled. Which seems to match the majority of applications.

Most of my CP/M code is 8080, since that is what my emulation does; ports to Z80-based machines freely use Z80 instructions.
 
  • Like
Reactions: cjs
This is an amorphous target at best. Obviously the design must be compliant with the CP/M environment and use the CP/M system calls.
Technically, CP/M is for the 8080 and to be truly compliant it needs to run on one. The reality is that the Z80 nearly completely subsumed the 8080 in the market place. So you have Z80 only programs running under CP/M in later days.

Personally, try to keep my code 8080, so it will run on my Altairs with 8080 processors, as well as my Z80 machines.

That horse should be a thin paste by now...
 
Since CP/M is an operating system, what makes a CP/M program a CP/M program would need to be specific to CP/M and not necessarily the CPU, since CP/M ran on more than one CPU.

So, what makes early operating systems unique? There are several items. The first is the system call interface. Interrupt based interfaces are how services are called in these systems (and really today as well, though we often use optimized versions of those instructions that are not just generic interrupts). So, the OS would have a specific interrupt number (or several) for that would be used to trigger those services. The total services provided by the OS would be specific to the OS. Additionally, any constraints or format needed for their binaries, such as code originating/referenced to start at 0x100, etc. All of these details differentiate CP/M programs from other programs.

If you had a binary in 8080 code that makes no system calls, you could make a case is not a CP/M program since you couldn't tell it apart from any other 8080 binary that might be on the same type of system but not run CP/M. BASIC programs, then, would not be CP/M specific if they are just using BASIC commands.

Just a thought...
 
  • Like
Reactions: cjs
Point of order! Your thread title says "What makes a CP/M program a CP/M program (and not just, say, a z80 program)?"... shouldn't have you said "CP/M-80 program"? CP/M-86 and CP/M-68000 exist, you know. ;)

Anyway... I find it a bit odd that your list of criteria doesn't actually include "uses documented CP/M API calls and accesses them via the standard: "LD DE,parameter; LD C,function; CALL 5"" calling routine? Is that what you meant by "recognizes the BDOS and stays clear?", because it's not actually clear to me what "stays clear" means there? Because, well, it seems to me like that's the basic definition of a CP/M program, that is uses the CP/M API verses, I dunno, TRS-DOS's roughly equivilant set of functionality that was called via completely different conventions?

The question is contentious because there is no correct answer. It's another one of those things to discuss in circles until the end of time.

Totally. This is "is the glass half empty, or half full?" on steroids. A "soft" glass-half-empty answer is probably going to be that the program:

a: uses *only* the documented CP/M API for everything it does; no directly poking hardware addresses or calling proprietary firmware extensions
b: loads at 100h and access the CP/M API via the "Call 5" address

While a *strict* "half-empty" is going to add:

c: only uses 8080 instructions for universal compatibility

Bullet point A: seems pretty reasonable, although you have to add an asterisk specifying which *version* of the CP/M API the program is targeting. (IE, you can't disqualify a program meant for MP/M or CP/M Plus because it doesn't run on CP/M 1.4.) And bullet point B: is also pretty reasonable; yes, there were those oddball versions of CP/M to run on TRS-80s and Zenith machines, but they're not directly binary compatible with "standard" CP/M-80 programs. You could trivially run programs for those oddball systems (usually ORG'ed to start at 4200H) on a generic CP/M system by using a special loader, I suppose, but the reverse is not true, so, yeah, I'd say they're disqualified. Bullet point C:... well, yes, it's "reasonable" in the sense that while Z80 machines vastly outnumber 8080 boxes CP/M itself is 8080-only, and, well, there *were* still companies churning out 8085 computers well into the 1980's; the point of the "half empty" position is you're defining a "CP/M Program" as compatible with "any machine that runs standard CP/M-80". Z80 programs fail that test.

On the flip side, the expansive answer is simply "the program runs on a computer that boots CP/M and uses it to load the binary". Almost *any* program designed for a computer that has anything remotely like graphics capability breaks rule "A" for the strict criteria; even standard fare like Wordstar, which *can* abide by rule A, usually doesn't when it's configured for computers that have memory mapped video because doing fancy terminal handling is such a massive PITA when all you have to work with is a serial punch API call.

But yeah, who cares. If you want to start calling video games shipped on floppy disks for MSX computers "CP/M programs" go with your heart, they do probably make at least a few CP/M compatible calls before going straight off into ColecoVision-ville with the direct register pounding. Just don't expect that designation to help anyone trying to run them on their Osborne.
 
This is an amorphous target at best. Obviously the design must be compliant with the CP/M environment and use the CP/M system calls.

This seems a pretty reasonable starting point - how should it translate to software that requires hardware or APIs as a baseline that are not included or supported by any CP/M?

Would they be CP/M software or machine-specific software - eg, Osborne 1 software is Osborne 1 software as it requires an Osborne 1, and doesn't interact via the CP/M API so can't be addressed in software by the BIOS?

That horse should be a thin paste by now...

Should be... But it seems the horse is a self-regenerating zombie. We'll still be flogging it until the end of time.
 
Should be... But it seems the horse is a self-regenerating zombie. We'll still be flogging it until the end of time.

"We" could just all stop, I suppose? Seems like it's an option.

I mean... why is this bothering you so much? It seems like the question is kind of without practical meaning. Anyone with much experience with CP/M machines knows that even "pure" CP/M software usually can't just be willy-nilly moved between machines because of all the random hassle with things like disk formats and terminal handling garbage. (Even *if* the program plays nice and just uses the CP/M console API to send terminal escape codes instead of cheating and poking at a memory mapped console that still leaves you having to patch it unless you have the *same* terminal that it's set up to use.) Being at least a little machine-specific just comes with the territory.
 
Point of order! Your thread title says "What makes a CP/M program a CP/M program (and not just, say, a z80 program)?"... shouldn't have you said "CP/M-80 program"? CP/M-86 and CP/M-68000 exist, you know. ;)

If it's DRI and has DRI in the title, I figure it's CP/M, but I like your definition more. Otherwise it will take me down rabbit holes I don't want to explore.

Anyway... I find it a bit odd that your list of criteria doesn't actually include "uses documented CP/M API calls and accesses them via the standard: "LD DE,parameter; LD C,function; CALL 5"" calling routine?
Totally. This is "is the glass half empty, or half full?" on steroids. A "soft" glass-half-empty answer is probably going to be that the program:

a: uses *only* the documented CP/M API for everything it does; no directly poking hardware addresses or calling proprietary firmware extensions
b: loads at 100h and access the CP/M API via the "Call 5" address

While a *strict* "half-empty" is going to add:

c: only uses 8080 instructions for universal compatibility

Either would seem a reasonable approach. "No Poking" would also be a reasonable way to describe it.

On the flip side, the expansive answer is simply "the program runs on a computer that boots CP/M and uses it to load the binary". Almost *any* program designed for a computer that has anything remotely like graphics capability breaks rule "A" for the strict criteria; even standard fare like Wordstar, which *can* abide by rule A, usually doesn't when it's configured for computers that have memory mapped video because doing fancy terminal handling is such a massive PITA when all you have to work with is a serial punch API call.

This is the reasonable flip site. But Wordstar pretty much runs on CP/M... Choice of terminals isn't a CP/M thing and disk handling by wordstar might be non-standard but it's entirely CP/M in it's approach.

But yeah, who cares. If you want to start calling video games shipped on floppy disks for MSX computers "CP/M programs" go with your heart, they do probably make at least a few CP/M compatible calls before going straight off into ColecoVision-ville with the direct register pounding. Just don't expect that designation to help anyone trying to run them on their Osborne.

They never called MSX games CP/M games. They called them MSX games for a reason.
 
"We" could just all stop, I suppose? Seems like it's an option.

I mean... why is this bothering you so much? It seems like the question is kind of without practical meaning. Anyone with much experience with CP/M machines knows that even "pure" CP/M software usually can't just be willy-nilly moved between machines because of all the random hassle with things like disk formats and terminal handling garbage. (Even *if* the program plays nice and just uses the CP/M console API to send terminal escape codes instead of cheating and poking at a memory mapped console that still leaves you having to patch it unless you have the *same* terminal that it's set up to use.) Being at least a little machine-specific just comes with the territory.

It comes up from time to time, and now I can move it out of my other thread :)

And terminal choice was never a CP/M limitation. And disk formats are related to the hardware of a machine - but the underlying software is generally remarkably transferrable, as is the disk if your hardware manages to access it.
 
They never called MSX games CP/M games. They called them MSX games for a reason.

A proper devil’s advocate has to ask “why not?”.

If I have Wordstar set up to use direct screen access (see the docs in the porting guide) it’s going to wreak havoc on *any other machine” that doesn’t have the same video hardware *unless* it’s patched. If you have an MSX game that plays by the CP/M API rules when doing disk access (because disk access is almost the only functionality CP/M provides) it seems to me it’s legitimately just as much a “CP/M program” as Wordstar is according to the most expansive definition.

To be clear, I’m fine with expansive definitions, the few other examples of early DOSes that were cross-vendor (including MS-DOS) also were usually only directly binary compatible across machines for programs that restricted themselves to a really limited least-common-denominator set of functionality… but if you call the programs that go outside that common denominator “X-dos compatible” instead of “IBM PC compatible” or “Mindset compatible” or whatever you are kind of kidding yourself.
 
Obviously there's no strict definition. Typically what people are trying to do when calling a program a "CP/M" program is communicate to users of "CP/M systems" that the program will run on their system. But due to the number of different CP/M systems and configurations out there, there are always caveats that the user must watch out for; some of these are well known and commonly taken into account, and others not.

So how do you figure out if you're communicating the requirements of your program without enumerating every last requirement every time you mention it?

You can get a rough idea of what these known caveats are by looking at the set of all system models sold that in their base configurations were clearly intended to run CP/M. If a feature is available on most of these, then it's reasonable not to mention it because the owners of that minority of systems without it will generally be aware. If you require some feature that few of these systems have, and you fail to mention that requirement, you're likely to get a lot of returns from people whom you told, "It runs on CP/M" and found out that "It doesn't run on my CP/M machine."

Example:
  • The owner of an Altair with only 20K of memory (the minimum memory configuration for CP/M 1.4 and, I think, 2.2 as well) is going to well aware of this limitation and is going to be keeping that well in mind when selecting software. She will not be buying "CP/M" software without carefully checking the memory requirements.
  • As of the late '70s (or perhaps early '80s?), the owner of one of the many machines that gives a TPA of about 56K or more (I'm not sure what the most common figures from that era were) is not going to be worried about memory usage, so if your program needs a minimum 40K TPA, you can put that in the fine print where most users won't notice it, but the 20K Altair owner will go look for it.
As you can see, these issues could arise long before the Z80 existed, and they continued on through the years and into today.
  • By about 1980, if someone said in a forum that Turbo Pascal was a "CP/M program," even though it doesn't run on 8080 machines, this would be fine. Everybody knew at that point that use of a Z80 instead of an 8080 in CP/M systems was virtually ubiquitous, and that 8080 owners should check the vendor specs before buying a CP/M program.
  • In the modern day, many, perhaps most, new systems intended to run CP/M support more than 64K of RAM and a fairly standard bank switching scheme such as RomWBW. But if your software requires this, it's not reasonable to call it just a "CP/M" program without mentioning that requirement because there's still a huge active community of users on vintage systems such as Kaypros and whatnot, who (correctly) consider themselves CP/M users, and who will be (correctly) surprised when the "CP/M program" doesn't work on their very average CP/M system.
This is all not that hard, we do it intuitively. Or most of us, anyway.
 
I would argue that CP/M sensu stricto means CP/M-80, although I don't see "it works on an 8080 or 8085, doesn't need a Z80" as a necessary since a lot of CP/M platforms were Z80-based. Otherwise, it usually gets modified, "CP/M-86", "CP/M-68K" etc. YMMV.

But I think to be a "CP/M program" would mean that it never directly hits the hardware, and does everything strictly through CP/M interfaces.
 
While the requirements for the binaries were already discussed here, another aspect is the distribution media (floppies). Basically, each manufacturer had its own proprietary floppy format. Even Altair 8800 and IMSAI 8080, both using 8" floppies, used incompatible formats. The same is true for 5.25" floppies: Kaypro, Osborne, and Apple II with SoftCard all used different formats. Even for Apple II, there were multiple Z80 CP/M cards not fully compatible with each other. This forced software publishers to make computer-specific releases. There was no easy way to take, for example, IMSAI disk and transfer contents to the Kaypro.
 
I've always considered it bit like MS-DOS and POSIX in position.

It's a thing for which can write general purposes tools to an API and those programs will run (or should) on CP/M or any other OS implementing those calls - whether the Soviet ones, MP/M, TurboDOS or even emulation libraries under another OS. Like DOS and POSIX though it's only useful for a subset of things that the user is doing so you'll always have some stuff where it allows most of the app to be portable but there are niggles.

Not sure media ever had much to do with it. That was in many cases the nature of the hardware improving and shifting as much as anything else and not a uniquely CP/M problem - although the broken CP/M BIOS table model of disks didn't help when things like FLEX or OS/9 didn't have that problem.
 
  • By about 1980, if someone said in a forum that Turbo Pascal was a "CP/M program," even though it doesn't run on 8080 machines, this would be fine. Everybody knew at that point that use of a Z80 instead of an 8080 in CP/M systems was virtually ubiquitous, and that 8080 owners should check the vendor specs before buying a CP/M program.
Although there was also a brief period when people with V.20 and V.30 processors cursed everyone writing "unclean" Z80 software that didn't run in the emulation mode on their x86 processor.

Alan
 
Although there was also a brief period when people with V.20 and V.30 processors cursed everyone writing "unclean" Z80 software that didn't run in the emulation mode on their x86 processor.
Well, sure, but it's not as if they weren't aware that they, being effectively on 8080s (though long after the 8080 itself, or even the 8085, had virtually vanished from the CP/M community), were going to have to live with being a small minority with hardware that wouldn't run some major programs.

Not sure media ever had much to do with it.
Right. From the very start it was known and accepted that there were a huge variety of media formats, and you could certainly not expect any random CP/M diskette from one machine to be readable on another without something to convert the lower levels of the format. I didn't feel it was worth bringing up in my earlier comment because it seemed to me like a very well known thing.
 
For CP/M-80 only programs that;

- use 8080 code
- BDOS calls thru page zero address
- no direct BIOS calls
- no direct ROM calls

are guaranteed to work!
Any thing else should state the CPU, and/or machine to use.

Tom
KE6JAG
 
Back
Top