Discussion:
MSDOS 3.2 COM ports
(too old to reply)
muta...@gmail.com
2021-04-23 23:19:00 UTC
Permalink
What support does MSDOS have for COM ports?

I believe you can copy a file with a destination of
COM1: and it will write to the COM port, but I don't
know what speed/parity/bits it uses when you do
that, and I've never heard of facilities to set those
things.

Thanks. Paul.
Grant Taylor
2021-04-24 00:26:53 UTC
Permalink
Post by ***@gmail.com
What support does MSDOS have for COM ports?
The ports are supported as devices.
Post by ***@gmail.com
I believe you can copy a file with a destination of COM1: and it
will write to the COM port, but I don't know what speed/parity/bits
it uses when you do that, and I've never heard of facilities to set
those things.
Utilities to manage the ports are a different matter.

I think I was always using some other program to configure / manage the
port as well as do the requisite communications.

Though, from a very deep dark and difficult to access memory, which
could easily be wrong, I want to say that mode had the capability to
configure ports.

I would say check the help command, but I think that was introduced in
6.<something> and you've listed 3.2 in the subject. That's way before I
started messing with DOS.
--
Grant. . . .
unix || die
muta...@gmail.com
2021-04-24 01:47:56 UTC
Permalink
Post by Grant Taylor
Post by ***@gmail.com
What support does MSDOS have for COM ports?
The ports are supported as devices.
Could you please explain what this means? A program
wishing to open a COM port is meant to do a special
"device open" or something?
Post by Grant Taylor
Post by ***@gmail.com
I believe you can copy a file with a destination of COM1: and it
will write to the COM port, but I don't know what speed/parity/bits
it uses when you do that, and I've never heard of facilities to set
those things.
Utilities to manage the ports are a different matter.
I think I was always using some other program to configure / manage the
port as well as do the requisite communications.
Though, from a very deep dark and difficult to access memory, which
could easily be wrong, I want to say that mode had the capability to
configure ports.
I would say check the help command, but I think that was introduced in
6.<something> and you've listed 3.2 in the subject. That's way before I
started messing with DOS.
Thanks for the pointer to the "mode" command. I found that here:

https://web.csulb.edu/~murdock/mode.html

So is there a DOS interrupt to do the equivalent of the
mode command?

Note that although I'm interested in DOS 3.2 (which is when
I started), if there is a solution in a more recent version of
DOS, I'm interested in that too, because I can backport it
to PDOS/86:

http://pdos.sourceforge.net/

I can remember when I wrote a comms program for MSDOS,
I bought a comms package, can't remember the name, from
the guy who created "Texas Zmodem", and he mentioned to
me that there shouldn't be a need for a comms package like
his, it should be built into MSDOS. And I'd like to understand
what the issue was.

BFN. Paul.
Grant Taylor
2021-04-24 02:08:57 UTC
Permalink
Could you please explain what this means? A program wishing to open
a COM port is meant to do a special "device open" or something?
Well, NUL, CON, COM1, COM2, COM3, COM4, LPT1, LPT2, and LPT3 are special
reserved device names in DOS. (I think COM goes up to 4.)

You could do something crude like "COPY CON MYFILE.TXT" start typing,
and copy would copy from the CONsole into MYFILE.TXT. I think you use
Control-D to indicate end of file.

Similarly, you can use "COPY MYFILE.TXT CON" as an alternative to TYPE.
DOS dutifully copies MYFILE.TXT to the CONsole.

There may be more such device names. I don't remember any more particulars.
Thanks for the pointer to the "mode" command.
You're welcome.
So is there a DOS interrupt to do the equivalent of the mode command?
I have no idea.
Note that although I'm interested in DOS 3.2 (which is when I started),
if there is a solution in a more recent version of DOS, I'm interested
ACK
I can remember when I wrote a comms program for MSDOS, I bought
a comms package, can't remember the name, from the guy who created
"Texas Zmodem", and he mentioned to me that there shouldn't be a need
for a comms package like his, it should be built into MSDOS. And I'd
like to understand what the issue was.
I wonder if he was implying that the MS-DOS was missing some
functionality or what.

Technically speaking, I suspect that you /can/ interact with a modem, a
la. a serial device, via the COM# port. But copy, as outlined above is
inherently uni-directional.

Then there's the fact that most communications programs included things
like address books, configuration wizards, and associated utility
functionality like xmodem / ymodem / zmodem.

These are all functions that are part of typical modem communications
programs from the '90s. MS-DOS simply did not include that functionality.
--
Grant. . . .
unix || die
muta...@gmail.com
2021-04-24 03:40:06 UTC
Permalink
Post by Grant Taylor
Could you please explain what this means? A program wishing to open
a COM port is meant to do a special "device open" or something?
Well, NUL, CON, COM1, COM2, COM3, COM4, LPT1, LPT2, and LPT3 are special
reserved device names in DOS. (I think COM goes up to 4.)
You could do something crude like "COPY CON MYFILE.TXT" start typing,
and copy would copy from the CONsole into MYFILE.TXT. I think you use
Control-D to indicate end of file.
Similarly, you can use "COPY MYFILE.TXT CON" as an alternative to TYPE.
DOS dutifully copies MYFILE.TXT to the CONsole.
Ok, which means a normal call to fopen() thus open()
would accept that name.
Post by Grant Taylor
So is there a DOS interrupt to do the equivalent of the mode command?
I have no idea.
I think there would have to be, as I assume "mode" is a
separate executable meaning it has to do an interrupt
to do its work.
Post by Grant Taylor
I can remember when I wrote a comms program for MSDOS, I bought
a comms package, can't remember the name, from the guy who created
"Texas Zmodem", and he mentioned to me that there shouldn't be a need
for a comms package like his, it should be built into MSDOS. And I'd
like to understand what the issue was.
I wonder if he was implying that the MS-DOS was missing some
functionality or what.
Sorry, maybe I should have said "comms library". It was an
API to interact with the serial port, because MSDOS
supposedly didn't have that ability.

Maybe it was just interrupt-driven capability that was missing.
Post by Grant Taylor
Technically speaking, I suspect that you /can/ interact with a modem, a
la. a serial device, via the COM# port. But copy, as outlined above is
inherently uni-directional.
I wonder if that was the limitation, and all that is required
is to extend MSDOS (via PDOS/86 or whatever) to allow
a COM port to be opened read/write, and you just need
to do a rewind() when switching between the two modes.

I think I can devise a strategy based on that.

With the assumption that the remote is more sophisticated
than PDOS/86 and will coddle PDOS/86 communication.

My plan is to basically run a "BBS" on my Windows box
for PDOS/86 to communicate with via the serial port.

BFN. Paul.
Grant Taylor
2021-04-24 02:14:48 UTC
Permalink
So is there a DOS interrupt to do the equivalent of the mode command?
I suspect that there is an answer to your question in the MS-DOS
Encyclopedia.

Link - MS-DOS Encyclopedia
- https://www.amazon.com/dp/1556151748
Note that although I'm interested in DOS 3.2 (which is when I started),
if there is a solution in a more recent version of DOS, I'm interested
I suspect that you would find the MS-DOS Encyclopedia to be quite
valuable in answering a lot of questions about the internals of MS-DOS.

You might also be interested in the copies of the MS-DOS source code
that can be found various places on the Internet. Though, once you look
at it, it will probably forever taint your view and you will never be
able to say that you weren't influenced by it.
--
Grant. . . .
unix || die
R.Wieser
2021-04-24 08:07:22 UTC
Permalink
Muta,
Post by ***@gmail.com
So is there a DOS interrupt to do the equivalent
of the mode command?
No, as the "mode" program has bundled up a slew of different settings.
*One* of them being the serial port

Question : Do you already have a copy of Ralf Brown's Inerrup List ? If
not, I strongly advice you to get yourself one.

In it you can find, among /lots/ more, this :

Notice that the second set allows higher baudrates by sacrificing some of
the lower ones. Which of the four below sets works for you is dependant on
your hardware and BIOS.

--------S-1400-------------------------------
INT 14 - SERIAL - INITIALIZE PORT
AH = 00h
AL = port parameters (see #00300)
DX = port number (00h-03h) (04h-43h for Digiboard XAPCM232.SYS)
Return: AH = line status (see #00304)
FFh if error on Digiboard XAPCM232.SYS
AL = modem status (see #00305)
Notes: default handler is at F000h:E739h in IBM PC and 100% compatible
BIOSes
since the PCjr supports a maximum of 4800 bps, attempting to set 9600
bps will result in 4800 bps
various network and serial-port drivers support the standard BIOS
functions with interrupt-driven I/O instead of the BIOS's polled I/O
the 1993/04/08 Compaq system ROM uses only the low two bits of DX
the default setting used by DOS (MS-DOS 6, DR-DOS 7.03, PTS-DOS) when
(re-)initializing the serial devices is AL=A3h (2400 bps, no parity,
1 stop bit, 8 data bits).
SeeAlso: AH=04h"SERIAL",AH=04h"MultiDOS",AH=05h"SERIAL",AH=57h
SeeAlso: AX=8000h"ARTICOM",AH=81h"COMM-DRV",AH=82h"COURIERS",AH=8Ch
SeeAlso: MEM 0040h:0000h,PORT 03F8h"Serial"

Bitfields for serial port parameters:
Bit(s) Description (Table 00300)
7-5 data rate (110,150,300,600,1200,2400,4800,9600 bps)
4-3 parity (00 or 10 = none, 01 = odd, 11 = even)
2 stop bits (set = 2, clear = 1)
1-0 data bits (00 = 5, 01 = 6, 10 = 7, 11 = 8)
SeeAlso: #00302,#00307,#00308,#00309
--------S-1400-------------------------------
INT 14 - FOSSIL (Fido/Opus/Seadog Standard Interface Level) - INITIALIZE
AH = 00h
AL = initializing parameters
7 - 6 - 5 4 - 3 2 1 - 0
-BAUD RATE- PARITY STOP WORD
BITS LENGTH
000 19200 bd 00 none 0: 1 00: 5
001 38400 bd 01 odd 1: 2 01: 6
010 300 bd 11 even 10: 7
011 600 bd 11: 8
100 1200 bd
101 2400 bd
110 4800 bd
111 9600 bd (4800 on PCjr)
DX = port number (0-3 or FFh if only performing non-I/O setup)
Return: AH = RS-232 status code bits (see #00301)
AL = modem status bits
bit 3: always 1
bit 7: DCD - carrier detect
SeeAlso: #00300,AH=05h"FOSSIL",AH=81h"COMM-DRV",AH=82h"COURIERS"

Bitfields for FOSSIL RS-232 status:
Bit(s) Description (Table 00301)
0 RDA - input data is available in buffer
1 OVRN - data has been lost
5 THRE - room is available in output buffer
6 TSRE - output buffer empty
--------S-1400-------------------------------
INT 14 - Tandy 2000 - SERIAL - RESET COMM PORT
AH = 00h
AL = RS-232C parameters (see #00302)
DL = port number
DH = protocol
bit 0: use XON/XOFF on received data
bit 1: use XON/XOFF when transmitting
Return: AH = line status (see #00304)
AL = modem status (see #00305)
Note: this interrupt is identical to INT 53 on the Tandy 2000
SeeAlso: AH=04h"Tandy 2000",INT 53"Tandy 2000"
--------S-1400-------------------------------
INT 14 - MBBIOS - INITIALIZE PORT
AH = 00h
AL = port parameters (see #00302)
DX = port number
Return: AH = line status (see #00304)
AL = modem status (see #00305)
Note: MBBIOS was written by H. Roy Engehausen
SeeAlso: AH=04h"MBBIOS",AH=05h"MBBIOS",AH=09h"MBBIOS"

Bitfields for MBBIOS port parameters:
Bit(s) Description (Table 00302)
7-5 data rate
(normally 110,150,300,600,1200,2400,4800,9600 bps;
9600,14400,19200,28800,38400,57600,115200,330400 bps
if the high-speed option is set)
4-3 parity (00 or 10 = none, 01 = odd, 11 = even)
2 stop bits (set = 2, clear = 1)
1-0 data bits (00 = 5, 01 = 6, 10 = 7, 11 = 8)
SeeAlso: #00300
---------------------------------------------

Regards,
Rudy Wieser
muta...@gmail.com
2021-04-24 22:04:50 UTC
Permalink
Post by R.Wieser
Muta,
Post by ***@gmail.com
So is there a DOS interrupt to do the equivalent
of the mode command?
No, as the "mode" program has bundled up a slew of different settings.
*One* of them being the serial port
Question : Do you already have a copy of Ralf Brown's Inerrup List ? If
not, I strongly advice you to get yourself one.
I normally read it online, but that requires me to know
what I need to do.
Post by R.Wieser
INT 14 - SERIAL - INITIALIZE PORT
AH = 00h
AL = port parameters (see #00300)
DX = port number (00h-03h) (04h-43h for Digiboard XAPCM232.SYS)
Return: AH = line status (see #00304)
Interestingly I couldn't find this table online:

http://www.ctyme.com/intr/rb-0811.htm

But it is in the disk files:

Bitfields for serial line status:
Bit(s) Description (Table 00304)
7 timeout
6 transmit shift register empty
5 transmit holding register empty
4 break detected
3 framing error
2 parity error
1 overrun error
0 receive data ready
Note: for COMM-DRV, if bit 7 is set, an error occurred, and may be retrieved
through a separate call (see AX=8000h"COMM-DRV")
Post by R.Wieser
various network and serial-port drivers support the standard BIOS
functions with interrupt-driven I/O instead of the BIOS's polled I/O
This is one of the things that interests me - how were
MSDOS programs ideally meant to be written that would
benefit from replacing polled I/O with interrupt-driven I/O?

Note that my original question was about MSDOS. This is
a BIOS function.

I tried doing an fopen() of "COM1:" for "w" on Freedos and
I was surprised to find that it failed.

But:
copy temp.txt com1:
worked, and I saw temp.txt.

I'm surprised that a copy would work, but not an
fopen.

I'm in a position to start extending MSDOS (basically
picking up where Microsoft left off) with PDOS/86
and PDOS/386.

I was thinking that I should be able to do fopen
of "COM1:" as "w+b" and switch between reading
and writing by doing an fseek() SEEK_CUR, 0.

Furthermore, this would involve blocking reads,
so what I would like is to posit the existence of
a sophisticated BBS (in reality it will just be my
Windows box), that would coddle my comms
program that uses fopen(). It would know that
there might be line noise so I might have missed
a CR that I was waiting on, so it will resend text
after an appropriate timeout, and will expect my
comms program to send an acknowledgement.

I think I just want to inherit whatever parameters
were set by the MODE command rather than
attempting to manipulate that myself.

I'm also happy to replace/front-end the BIOS so
that a more useful BIOS is available to PDOS/86
to support the above.

BFN. Paul.
R.Wieser
2021-04-25 08:32:50 UTC
Permalink
Muta,
Post by ***@gmail.com
http://www.ctyme.com/intr/rb-0811.htm
Uhhh.... whut ? <confused>

On the page you linked to : "AL = modem status (see #00305)". I just
clicked the "(see #00305)" link and got what you posted (as part of the "get
port status" (int 14/AH=03h) page). :-)
Post by ***@gmail.com
This is one of the things that interests me - how were
MSDOS programs ideally meant to be written that
would benefit from replacing polled I/O with interrupt-
driven I/O?
The moment you write an interactive program (read: non-commandline) you most
always need to have stuff happening "in the background" to keep the
user-facing side (the "gui") responsive.
Post by ***@gmail.com
Note that my original question was about MSDOS.
This is a BIOS function.
Thats true. The problem is that MSDOS does not have an int 0x21 API call
available to initialize the serial port. And as you are posting in the
"programmer" newsgroup I gave you the next-best thing ...

Having said that, you can ofcourse always just shell the "mode" command
(similar to how you executed "cmd.exe" in the "programmer.win32" newsgroup).
Post by ***@gmail.com
I tried doing an fopen() of "COM1:" for "w" on Freedos
and I was surprised to find that it failed.
Try removing the ":" at the end of the device name.

Also, COM1 is not actually a file, so what you can do with it is limited
(you can't "seek" it).
Post by ***@gmail.com
Furthermore, this would involve blocking reads,
so what I would like is to posit the existence of
a sophisticated BBS (in reality it will just be my
Windows box), that would coddle my comms
program that uses fopen().
You asked about when interrupt-driven I/O would be called for ? Well,
there you go. :-)

And not to be a party-pooper, but depending on the C environment you work in
you still might be, in regard to the serial port, working with simple,
blocking I/O ...

In that regard it would not be a bad idea to search for drivers which will
give you interrupt-based serial-port handling. IIRC "Fossil" is one of
those drivers (its named it Ralf Browns Interrup List).
Post by ***@gmail.com
I think I just want to inherit whatever parameters
were set by the MODE command rather than
attempting to manipulate that myself.
:-) That will certainly be the easiest way to go.

Regards,
Rudy Wieser
muta...@gmail.com
2021-04-26 08:32:05 UTC
Permalink
On the page you linked to : "AL = modem status (see #00305)". I just
clicked the "(see #00305)" link and got what you posted (as part of the "get
port status" (int 14/AH=03h) page). :-)
Ok, 304 was difficult to see.
Post by ***@gmail.com
This is one of the things that interests me - how were
MSDOS programs ideally meant to be written that
would benefit from replacing polled I/O with interrupt-
driven I/O?
The moment you write an interactive program (read: non-commandline) you most
always need to have stuff happening "in the background" to keep the
user-facing side (the "gui") responsive.
Isn't this more a function of multitasking? Given that
MSDOS wasn't multitasking, was there a problem?
Post by ***@gmail.com
I tried doing an fopen() of "COM1:" for "w" on Freedos
and I was surprised to find that it failed.
Try removing the ":" at the end of the device name.
I was surprised - that actually worked!

So I was able to output a character to the COM port.
Also, COM1 is not actually a file, so what you can do with it is limited
(you can't "seek" it).
My intention is to do an fopen("news.eternal-september.org:119", "r+b");

and then read and write the COM port as if it is a normal
file. The C standard requires you to do a seek before
switching modes.

And my intention is to run this under PDOS/386, so
all levels are under my control. I will get the OS to
do the polling so that my application blocks.

Then I will finally be able to get access to this newsgroup
and others by a better interface than google. Namely
micro-emacs.
Post by ***@gmail.com
Furthermore, this would involve blocking reads,
so what I would like is to posit the existence of
a sophisticated BBS (in reality it will just be my
Windows box), that would coddle my comms
program that uses fopen().
You asked about when interrupt-driven I/O would be called for ? Well,
there you go. :-)
And not to be a party-pooper, but depending on the C environment you work in
you still might be, in regard to the serial port, working with simple,
blocking I/O ...
I want blocking I/O. I want the external "BBS" to deal
with timeouts etc and provide a clean data stream
to my applications running on PDOS/x86.
In that regard it would not be a bad idea to search for drivers which will
give you interrupt-based serial-port handling. IIRC "Fossil" is one of
those drivers (its named it Ralf Browns Interrup List).
Actually I wrote my own already (PDCOMM). But I've
never been happy with the interface. It's not C90.
And when I needed to reimplement something for
PDOS/386 I wondered what would be clean.

BFN. Paul.
R.Wieser
2021-04-26 09:42:10 UTC
Permalink
Muta,
Post by ***@gmail.com
Ok, 304 was difficult to see.
My apologies, I goofed up. You said 304, and I blabbered about 305. :-(
Post by ***@gmail.com
Isn't this more a function of multitasking? Given that
MSDOS wasn't multitasking, was there a problem?
No, its not multitasking. Its just, as the method says, interrupting the
program for a short(!) while. So, no problem for DOS.

And although DOS itself isn't multitasking, there where several programs dat
did do a nice job at faking it. IIRC DoubleDesk is one of them. I also
remember a helpfile program that would, inside the (flat text) editor of
your choice, pop up a window with searchable help context.
Post by ***@gmail.com
The C standard requires you to do a seek before
switching modes.
Than you should at least try if it works that way. :-)

Full disclosure : my language-of-choice is Assembly. Although I can do some
C{something}, my knowledge about it is meager.
Post by ***@gmail.com
I want blocking I/O. I want the external "BBS" to
deal with timeouts etc and provide a clean data
stream to my applications running on PDOS/x86.
The problem with blocking I/O is, as you have probably already noticed, that
if you are waiting for something (to arrive or be (fully) send) you cannot
do anything else. And for some reason when humans press a key they
normally expect a direct response. :-)

Regards,
Rudy Wieser
muta...@gmail.com
2021-04-26 11:42:44 UTC
Permalink
Post by R.Wieser
Post by ***@gmail.com
The C standard requires you to do a seek before
switching modes.
Than you should at least try if it works that way. :-)
I have control of both the C library (PDPCLIB) and
the OS (PDOS) so I can make it behave however I
want, at least within the limits of the BIOS.
Post by R.Wieser
Post by ***@gmail.com
I want blocking I/O. I want the external "BBS" to
deal with timeouts etc and provide a clean data
stream to my applications running on PDOS/x86.
The problem with blocking I/O is, as you have probably already noticed, that
if you are waiting for something (to arrive or be (fully) send) you cannot
do anything else. And for some reason when humans press a key they
normally expect a direct response. :-)
Any reason why I shouldn't expect a direct response from
the BBS running on my Windows machine?

And if my BBS is in turn waiting on the news server on
the internet, I don't see that there is much choice but to
wait for that.

BFN. Paul.
R.Wieser
2021-04-26 12:54:48 UTC
Permalink
Muta,
Post by ***@gmail.com
Any reason why I shouldn't expect a direct response
from the BBS running on my Windows machine?
Apart from the one you already named ? :-)

Even on your own 'puter you can do stuff that takes a while to complete.
Just take searching for a certain file (dir filemask.ext /s/b) - or worse :
searching for a file with certain contents (grep -idl "some text"
filemask.ext)
Post by ***@gmail.com
And if my BBS is in turn waiting on the news server
on the internet, I don't see that there is much choice
but to wait for that.
For either of the above examples I gave I can press ctrl-c to abort. I
can easily imagine that a BBS would accept a key stroke or command to do the
same. But as your client program is using blocking I/O you could be
pressing keys all you want, but those won't be send until after you got your
response back from the BBS ...

Granted, blocking I/O is much easier to work with. But keep the downside of
it in mind.

Regards,
Rudy Wieser
muta...@gmail.com
2021-04-26 21:10:01 UTC
Permalink
Post by ***@gmail.com
And if my BBS is in turn waiting on the news server
on the internet, I don't see that there is much choice
but to wait for that.
For either of the above examples I gave I can press ctrl-c to abort. I
can easily imagine that a BBS would accept a key stroke or command to do the
same. But as your client program is using blocking I/O you could be
pressing keys all you want, but those won't be send until after you got your
response back from the BBS ...
A long-running "grep -R" running within PDOS, forget
about the BBS, would be considered to be using
blocking I/O (on the disk, not the BBS), wouldn't it?

Interrupting either the disk or the BBS is an independent
activity, isn't it?
Granted, blocking I/O is much easier to work with
Are you talking about from an application programmer's
perspective, a user's perspective, or something else?

You're now touching on the heart of PDOS design.

PDOS wasn't really designed up front. It was just
"use C90 and look like MSDOS and be 32-bit instead
of 16-bit".
But keep the downside of it in mind.
Can you list those? It might be possible to
overcome them.

I guess it depends on what we're trying to achieve.

What would be a sensible achievement in your eyes?

BTW, I started this project in 1994.

BFN. Paul.
R.Wieser
2021-04-27 09:40:07 UTC
Permalink
Muta,
Post by ***@gmail.com
A long-running "grep -R" running within PDOS, forget
about the BBS, would be considered to be using
blocking I/O (on the disk, not the BBS), wouldn't it?
Yes, and no.

No : As mentioned, on your own *local* machine you can most always use
ctrl-c to abort (force-closing the program).

Yes : As long as your program doesn't output anything you cannot stop it
(the ctrl-c checking is done inside (some of) the character output BIOS
INTs)
Post by ***@gmail.com
Interrupting either the disk or the BBS is an independent
activity, isn't it?
And I'm not even going to try to answer this. You're throwing apples and
eggs together and expect a single explanation.

What happens on your local machine is one thing.
Your (client programs) communication with a server (the BBS) is another
How the server (your BBS) responds to your clients communication is a third.

Don't throw them all on a heap. You're just end up confusing
yourself.(and me for that matter)

And just ask yourself : Your BBS listens to your client-programs
communications and does whatever it says. How's that independant ?
Post by ***@gmail.com
Are you talking about from an application programmer's
perspective, a user's perspective, or something else?
both (though for different, opposite reasons), and what else is there ?
Post by ***@gmail.com
But keep the downside of it in mind.
Can you list those? It might be possible to
overcome them.
Whut ? What didn't you understand from what I already said :

[quote=me, parent post]
But as your client program is using blocking I/O you could be pressing keys
all you want, but those won't be send until after you got your response back
from the BBS ...
[/quote]

Again: as long as you are in a blocking wait (for data to come in) *you
can't do anything else*. Your 'puter is effectivily frozen. How do you
think you can overcome that ?

Remark: if you can find a "wait for data *but use a time-out*" method you
can mitigate /some/ of it - even though the user will still have the
"pleasure" of experiencing freeze-stutter. Not funny when you try to use
the keyboard...
Post by ***@gmail.com
I guess it depends on what we're trying to achieve.
What would be a sensible achievement in your eyes?
And as far as I'm concerned ? Anything. As long as you learn from it it
doesn't even matter if you can / will actually finish the program. IOW,
I consider the road traveled more important that arriving at the
destination.

So yes, you can definitily create a client that uses blocking I/O to talk
with a BBS. No doubt about it. And it will work well too. It just has
a certain behaviour not everyone might like ...
Post by ***@gmail.com
BTW, I started this project in 1994.
I got my first PC a few years later : a 286 with turbo button (8 -> 12 MHz)
:-)

Regards,
Rudy Wieser
muta...@gmail.com
2021-04-27 10:56:38 UTC
Permalink
Post by R.Wieser
Post by ***@gmail.com
A long-running "grep -R" running within PDOS, forget
about the BBS, would be considered to be using
blocking I/O (on the disk, not the BBS), wouldn't it?
Yes, and no.
No : As mentioned, on your own *local* machine you can most always use
ctrl-c to abort (force-closing the program).
Yes : As long as your program doesn't output anything you cannot stop it
(the ctrl-c checking is done inside (some of) the character output BIOS
INTs)
Wow. I didn't know that. I didn't actually believe it,
so I tried writing a program that just went into a
loop, and confirmed that I could ctrl-C out of it
on Windows (which screws up my keyboard
because it is left in ANSI terminal mode and
Windows doesn't fix that).

Then I ran the same program on MSDOS and it
didn't allow me to ctrl-c out of it.

I did one more test which was to run my Windows
program on MSDOS using HX under Freedos. It
also couldn't be aborted.

I thought all keyboard strokes resulted in an
interrupt?

Isn't it a simple matter of hooking into that interrupt
and doing the ctrl-c checking?

Note that I haven't implemented ctrl-c checking in
PDOS at all yet. Neither PDOS/86 nor PDOS/386,
not even on output.

I guess now is the time to find out what options are
available. :-)
Post by R.Wieser
Post by ***@gmail.com
Interrupting either the disk or the BBS is an independent
activity, isn't it?
And just ask yourself : Your BBS listens to your client-programs
communications and does whatever it says. How's that independant ?
ctrl-c checking is independent of the application
being run.
Post by R.Wieser
Post by ***@gmail.com
Are you talking about from an application programmer's
perspective, a user's perspective, or something else?
both (though for different, opposite reasons), and what else is there ?
Hardware design, C library design. Language design.
Post by R.Wieser
Post by ***@gmail.com
But keep the downside of it in mind.
Can you list those? It might be possible to
overcome them.
[quote=me, parent post]
But as your client program is using blocking I/O you could be pressing keys
all you want, but those won't be send until after you got your response back
from the BBS ...
[/quote]
It was all based on a misunderstanding.

By "blocking mode" I thought you meant that the
application waited until data arrived instead of
going into a polling loop to check multiple devices
at the same time. I didn't know you meant
ctrl-c checking.
Post by R.Wieser
Again: as long as you are in a blocking wait (for data to come in) *you
can't do anything else*. Your 'puter is effectivily frozen. How do you
think you can overcome that ?
By getting the OS, even Freedos, to check the keyboard
every timer interrupt to see if there are any pending
characters? That won't work on an application that
disables interrupts, but I don't care about that, I only
care about normal programs that have a bug (or are
long-running) and go into a loop without printing
anything.

I wasn't aware that that wasn't already in place.

What's the technical barrier?

Thanks. Paul.
R.Wieser
2021-05-01 19:56:44 UTC
Permalink
Muta,
Post by ***@gmail.com
I thought all keyboard strokes resulted in
an interrupt?
Yeah, they do. A *hardware* one. Which dumps the keystroke into a small
buffer which you than read from with a few of the BIOS INTs.
Post by ***@gmail.com
Isn't it a simple matter of hooking into that interrupt
and doing the ctrl-c checking?
Yeah, thats a good idea : you just, somewhere in the middle of whatever your
'puter is busy with - even harddisk writing ! - hard-abort it. Nope, I
would not suggest doing that.
Post by ***@gmail.com
Post by R.Wieser
And just ask yourself : Your BBS listens to your client-programs
communications and does whatever it says. How's that independant ?
ctrl-c checking is independent of the application
being run.
I don't think you understood the question ...
Post by ***@gmail.com
What's the technical barrier?
I already mentioned that : while you can just have your client program
crash-and-burn by pressing ctrl-c, it won't stop the server (the BBS) from
continuing what its busy with.

IOW, you need to figure out a "soft" method to stop whatever your client is
doing (*not* aborting the program or interrupting it in the middle of
something important), and than *ask* the server to stop what it busy with -
'cause thats the only thing you can do : ask..

Regards,
Rudy Wieser
muta...@gmail.com
2021-05-01 21:36:05 UTC
Permalink
Post by ***@gmail.com
I thought all keyboard strokes resulted in
an interrupt?
Yeah, they do. A *hardware* one. Which dumps the keystroke into a small
buffer which you than read from with a few of the BIOS INTs.
Post by ***@gmail.com
Isn't it a simple matter of hooking into that interrupt
and doing the ctrl-c checking?
Yeah, thats a good idea : you just, somewhere in the middle of whatever your
'puter is busy with - even harddisk writing ! - hard-abort it. Nope, I
would not suggest doing that.
Ok, great! Now I'm learning something.
I already mentioned that : while you can just have your client program
crash-and-burn by pressing ctrl-c, it won't stop the server (the BBS) from
continuing what its busy with.
IOW, you need to figure out a "soft" method to stop whatever your client is
doing (*not* aborting the program or interrupting it in the middle of
something important), and than *ask* the server to stop what it busy with -
'cause thats the only thing you can do : ask..
Ok, let's do one thing at a time.

The first thing I'd like to know is if my program goes
into a hard loop, with:

for (;;) ;

ie no input or output I/O to any device, is there a technical
barrier on either 8086 or 80386 to allowing the hardware
interrupt of ctrl-c being pressed aborting the application?

Or at least letting the timer interrupt detect that ctrl-c has
been pressed and waiting two more timer interrupts and then
actioning the abort.

You mentioned that you shouldn't be aborting a hard disk
write. The OS will always be the one who initiates that. So
the OS can mark that operation as "do not interrupt until
complete".

Or alternatively, the OS will know whether it is in the middle
of doing any OS work at all, or whether it is an application
being run. If it is in application code, then it can be safely
aborted. OS work should not be aborted, at least by default.

When doing a blocked read from a COM port (assuming
such a BIOS call exists, which doesn't seem to be the
case), the specific BIOS call to read from a COM port
could be marked as interruptable, meaning whenever
a ctrl-c comes in, the OS can forget about the COM port
read and abort the application that ultimately requested
the operation in the first place. The OS can have further
knowledge that that interruptable operation needs to be
followed up with a reset of the COM port if required.

And then finally moving on to the BBS - remembering
that it is a cooperative BBS - the OS can be set to send
the ctrl-c out the COM port as part of aborting the
application.

Would that work?

Thanks. Paul.
R.Wieser
2021-05-02 08:29:00 UTC
Permalink
Muta,
Post by ***@gmail.com
The first thing I'd like to know is if my program goes
for (;;) ;
ie no input or output I/O to any device, is there a technical
barrier on either 8086 or 80386 to allowing the hardware
interrupt of ctrl-c being pressed aborting the application?
That fully depends on how you define "technical". Using it that way and
leaving your (and perhaps another) machine in an unstable state is what I
would definitily call a technical barrier.
Post by ***@gmail.com
Or at least letting the timer interrupt detect that ctrl-c has
been pressed and waiting two more timer interrupts and
then actioning the abort.
Sigh. You do *NOT* leave it up to some random factor to force your program
to abort whatever it is busy with. Doing so is simply asking for trouble.
Post by ***@gmail.com
You mentioned that you shouldn't be aborting a hard \
disk write.
As an example, yes. Same goes for your connection to that BBS of yours too
though
Post by ***@gmail.com
The OS will always be the one who initiates that.
No. *Your program* initiates it. It also holds the to-be-written data.
Just imagine what happens when the OS-based disk-write routine is reading
whatever you want to have written, and you just yank that buffer away from
under it.

Have you ever heard about how a use-after-free is something that should
/never/ happen ? You would be opening up yourself to the same. Bonus
points if some other program allocates that same buffer space and overwrites
it.
Post by ***@gmail.com
Or alternatively, the OS will know whether it is in the
middle of doing any OS work at all, or whether it is an
application being run.
:-) Now you are trying to offload the problem to an imaginary (future)
(D)OS. Thats not the way to go I'm afraid. For one, further
development of your client would need to stop until those OS features are
available ...
Post by ***@gmail.com
When doing a blocked read from a COM port (assuming
such a BIOS call exists, which doesn't seem to be the
case),
Actually, its the opposite. Blocking calls are the default. The
non-blocking ones - or the ones that have a timeout - are, especially under
BIOS / DOS, the exception of the rule.

You might not directly notice a COM port blocking I/O effect, but thats most
likely either because most of todays UARTs have a (small) internal buffer,
or your C{something} function-library is buffering it for you (yes, your
C{something} programming environment might actually already carry an
interrupt-driven COM library).

But yes, there is a possibility that your C{something} based COM access will
(be configured to) return immediatily - regardless of if all the data has
been received or not. And that ofcourse means that you (again) need to
poll to get all the transmitted-to-you data ...
Post by ***@gmail.com
And then finally moving on to the BBS - remembering
that it is a cooperative BBS - the OS can be set to
send the ctrl-c out the COM port as part of aborting
the application.
:-) You *say* you're "moving on to the BBS", but directly mock those words
by only talking about something the OS your client is running on is supposed
to be doing.

Also, how would that OS know that there is a serial connection active, or
what exactly to say (and when!) to that BBS ?

No, you're fantasizing about OS capabilities I'm afraid. *You* have to
write it. Either as part of your client, or as part of your future OS.
I suggest you keep focussed on your client.

Regards,
Rudy Wieser
muta...@gmail.com
2021-05-02 09:14:11 UTC
Permalink
Post by ***@gmail.com
The first thing I'd like to know is if my program goes
for (;;) ;
ie no input or output I/O to any device, is there a technical
barrier on either 8086 or 80386 to allowing the hardware
interrupt of ctrl-c being pressed aborting the application?
That fully depends on how you define "technical". Using it that way and
leaving your (and perhaps another) machine in an unstable state is what I
would definitily call a technical barrier.
The current alternative is to hang the PC requiring a reboot.

ie that is how Freedos is currently behaving.
Post by ***@gmail.com
Or at least letting the timer interrupt detect that ctrl-c has
been pressed and waiting two more timer interrupts and
then actioning the abort.
Sigh. You do *NOT* leave it up to some random factor to force your program
to abort whatever it is busy with. Doing so is simply asking for trouble.
I'm trying to improve on Freedos/MSDOS, not solve
all the world's problems in one release.
Post by ***@gmail.com
You mentioned that you shouldn't be aborting a hard \
disk write.
As an example, yes. Same goes for your connection to that BBS of yours too
though
BBSes are quite used to remotes dropping carrier.

My BBS in particular, running on Windows, will be
designed around the fact that the caller is primitive.
Post by ***@gmail.com
The OS will always be the one who initiates that.
No. *Your program* initiates it. It also holds the to-be-written data.
Just imagine what happens when the OS-based disk-write routine is reading
whatever you want to have written, and you just yank that buffer away from
under it.
Not sure what you're talking about here. That's
exactly what ctrl-c means, isn't it?
Have you ever heard about how a use-after-free is something that should
/never/ happen ? You would be opening up yourself to the same. Bonus
points if some other program allocates that same buffer space and overwrites
it.
Not sure what the issue is here either. The application
will be dead. That's the whole point of ctrl-c.
Post by ***@gmail.com
Or alternatively, the OS will know whether it is in the
middle of doing any OS work at all, or whether it is an
application being run.
:-) Now you are trying to offload the problem to an imaginary (future)
(D)OS. Thats not the way to go I'm afraid. For one, further
development of your client would need to stop until those OS features are
available ...
I'm not sure if we're talking cross-purposes or what.

Here is my project:

http://pdos.sourceforge.net/

I have a 16-bit and 32-bit version of MSDOS. And 32-bit
Windows too. And the mainframe hardware as well. This
isn't future, it's current.

I also have my own C library for both of the above
environments. And many more environments too.

I've been working on it off and on for more than
25 years.

I provide my own version of GCC 3.2.3 to target all
of those platforms.

I don't control the BIOS, except, sort of, in 32-bit mode.

I don't control the hardware either, except, sort of, on
the mainframe.

Other than that, every byte of code that is executed
when you boot PDOS, on either 8086 or 80386, is
part of my project. At least if you boot from floppy.
Booting from hard disk uses an MBR put in by
someone else. I have a public domain MBR (not
written by me) standing by though.
Post by ***@gmail.com
When doing a blocked read from a COM port (assuming
such a BIOS call exists, which doesn't seem to be the
case),
Actually, its the opposite. Blocking calls are the default. The
non-blocking ones - or the ones that have a timeout - are, especially under
BIOS / DOS, the exception of the rule.
All I know is that under Freedos I tried to do a read from
COM1 and it returned immediately with a timeout and
I had to put my application into a loop for me to get
any data. Here is the code that I used:

static int testBosSerialReadChar(void)
{
unsigned int x;

while (1)
{
x = BosSerialReadChar(0);
if ((x & 0x8000U) == 0)
{
printf("%c", (x & 0xff));
fflush(stdout);
}
}
printf("received %x\n", x);
return (0);
}

That BiosSerialReadChar() function is my own, which
you can see here:

/* BosSerialReadChar BIOS Int 14h Function 02h */

unsigned int BosSerialReadChar(unsigned int port)
{
union REGS regsin;
union REGS regsout;

regsin.h.ah = 0x02;
regsin.h.al = 0;
regsin.x.dx = port;

int86(0x14 + BIOS_INT_OFFSET, &regsin, &regsout);
return (regsout.x.ax);
}
You might not directly notice a COM port blocking I/O effect, but thats most
likely either because most of todays UARTs have a (small) internal buffer,
or your C{something} function-library is buffering it for you (yes, your
C{something} programming environment might actually already carry an
interrupt-driven COM library).
Not unless I write it myself. I didn't.
But yes, there is a possibility that your C{something} based COM access will
(be configured to) return immediatily - regardless of if all the data has
been received or not. And that ofcourse means that you (again) need to
poll to get all the transmitted-to-you data ...
The BIOS does.
Post by ***@gmail.com
And then finally moving on to the BBS - remembering
that it is a cooperative BBS - the OS can be set to
send the ctrl-c out the COM port as part of aborting
the application.
:-) You *say* you're "moving on to the BBS", but directly mock those words
by only talking about something the OS your client is running on is supposed
to be doing.
I don't understand.
Also, how would that OS know that there is a serial connection active, or
Because it would have been fopen'ed as "COM1".
what exactly to say (and when!) to that BBS ?
The BBS and the OS will have an agreed protocol
that allows the OS to do a blocked read and the
BBS is expecting that and will coddle the OS (PDOS).
No, you're fantasizing about OS capabilities I'm afraid.
It's not a fantasy. I'm trying to add it to existing PDOS.
*You* have to write it.
Yes, of course. That's what I'm doing right now. Adding
ctrl-c handling after understanding why Freedos and
MSDOS don't do this already and require the user to
reboot the machine, when both keyboard and timer
interrupts are available to the OS, even in 8086 mode.
Either as part of your client, or as part of your future OS.
I suggest you keep focussed on your client.
They are all growing together, and have been doing so
for over 25 years. Just today I made changes to both
the C library and the OS, as I found issues in both.
This is not abnormal. It's a near-daily occurrence.

It is the BBS that is the future, and the comms program
that is sort of in the future. I'm just going through the
motions of understanding what is required to support
that so that I don't paint myself into a corner in either
PDPCLIB or PDOS.

BFN. Paul.

Peter 'Shaggy' Haywood
2021-04-28 04:15:17 UTC
Permalink
Groovy hepcat Grant Taylor was jivin' in comp.os.msdos.programmer on
Sat, 24 Apr 2021 10:26 am. It's a cool scene! Dig it.
Post by Grant Taylor
Post by ***@gmail.com
What support does MSDOS have for COM ports?
The ports are supported as devices.
Post by ***@gmail.com
I believe you can copy a file with a destination of COM1: and it
will write to the COM port, but I don't know what speed/parity/bits
it uses when you do that, and I've never heard of facilities to set
those things.
Utilities to manage the ports are a different matter.
I think I was always using some other program to configure / manage
the port as well as do the requisite communications.
Though, from a very deep dark and difficult to access memory, which
could easily be wrong, I want to say that mode had the capability to
configure ports.
I would say check the help command, but I think that was introduced in
6.<something> and you've listed 3.2 in the subject. That's way before
I started messing with DOS.
MODE (Configure Serial Port)

Configures a serial communications port.

This version of the MODE command sets the parameters for a serial port
(COM1, COM2, COM3, or COM4).

Syntax

MODE COMm[:] [b[,p[,d[,s[,r]]]]]

MODE COMm[:] [BAUD=b] [PARITY=p] [DATA=d] [STOP=s] [RETRY=r]

Parameters

COMm
Specifies the number of the serial (COM) port. Valid values for m
are in
the range 1 through 4.

If you omit any of the following five parameters, MODE uses the most
recent setting for the omitted parameter. If you are using the
shorter
form of the syntax (without the words BAUD=, PARITY=, DATA=, and so
on),
the MODE command "recognizes" the parameters by their positions.
Thus,
if you do not specify a value for a parameter, you must still type
the
comma that precedes the next parameter.

BAUD=b
Specifies the first two digits of the transmission rate in bits per
second. The following list shows each valid value for b and its
related
rate:

11 110 baud

15 150 baud

30 300 baud

60 600 baud

12 1200 baud

24 2400 baud

48 4800 baud

96 9600 baud

19 19,200 baud

The b value of 19 is not supported on all computers (check your
hardware
manual). You can abbreviate this parameter by omitting BAUD= and
specifying a value for b.

PARITY=p
Specifies how the system uses the parity bit to check for
transmission
errors. The p value can be one of the following: N (none), E (even),
O
(odd), M (mark), or S (space). The default value is E. Not all
computers
support the values M and S. You can abbreviate this parameter by
omitting PARITY= and specifying a value for p.

DATA=d
Specifies the number of data bits in a character. Valid values for d
are
in the range 5 through 8. The default value is 7. Not all computers
support the values 5 and 6. You can abbreviate this parameter by
omitting DATA= and specifying a value for d.

STOP=s
Specifies the number of stop bits that define the end of a
character: 1,
1.5, or 2. If the baud rate is 110, the default value is 2;
otherwise,
the default value is 1. Not all computers support the value 1.5. You
can
abbreviate this parameter by omitting STOP= and specifying a value
for
s.

RETRY=r
Specifies the retry action to take if a time-out error occurs when
MODE
attempts to send output to a serial printer. This parameter causes
part
of MODE to remain resident in memory. The following list shows each
valid value for r and a brief description of its meaning:

E Return an error from a status check of a busy port.

B Return "busy" from a status check of a busy port.

P Continue retrying until printer accepts output.

R Return "ready" from a status check of a busy port.

N Take no retry action (default value). You can also specify none
for
this value.

If you are using the MODE command over a network, do not use any of
the
r values. You can abbreviate this parameter by simply omitting
RETRY=
and specifying a value for r.
--
----- Dig the NEW and IMPROVED news sig!! -----


-------------- Shaggy was here! ---------------
Ain't I'm a dawg!!
Loading...