dan@srs.UUCP (Dan Kegel) (02/03/87)
> > The question is, "WHAT MS-DOS FUNCTION CALL DID COPY MAKE TO CAUSE THE FILE > > TO PRINT?" It sounds like the handle must be placed in raw mode, or > > something synonymous. Unfortunately, I do not know how to do this, and > > the programmer's manual for MS-DOS is not too helpful. Any help would > > be appreciated. COPY /b probably uses DOS function 40h to do the reads and writes. At the end of this article is a shell archive of a Microsoft C file containing the routine SetHandleRaw(handle), which should answer your other question. When using raw mode, you may notice a speed increase when writing blocks of data; this is because DOS passes I/O requests straight to the device driver in raw mode, with very little overhead. The difference is most noticable with CON: and NANSI.SYS (plug, plug). By the way, in older versions of Aztec C, it might help to avoid using the colon in the device name when opening the file. I think there is also something called 'raw mode' in Aztec's I/O library; this should also be set, but it has nothing to do with the DOS raw mode described above. Also by the way, here's what the manual says about raw mode: IOCTL Data (Function 44H, Codes 0 and 1) Function 44H, Codes 0 and 1 either gets or sets the data MS-DOS uses to control the device. AL must contain 0 to get the data or 1 to set it. BX must contain the handle. If AL is 1, DH must contain 0. The device data word is specified or returned in DX. If bit 7 of the data is 1, the handle refers to a device and the other bits have the following meanings: ... Bit 5: 1=Don't check for control chars. 0=Check for control chars. ... The control characters referred to in the description of bit 5 are ^C, ^P, ^S, and ^Z. To read these characters as data, rather than having them interpreted as control characters, bit 5 must be set. If bit 7 of the data is 0, the handle refers to a file and the other bits mean: Bit 6: 0=the file has been written. Bits 0-5: Driver number (0=A, 1=B...) - Daniel Kegel (...rochester!srs!dan)
dan@srs.UUCP (Dan Kegel) (02/03/87)
Here is the subroutine promised in my last posting: #!/bin/sh # # shar archiver, delete everything above the #!/bin/sh line # and run through sh (not csh) # echo 'shar: extracting "rawmode.c" (3326 characters)' sed 's/^XX //' > rawmode.c << 'XXX_EOF_XXX' XX /*--- rawmode.c ------------------------------------------------- XX Routines to set and reset raw mode for Microsoft C. XX Stolen from the sources to the mighty game Hack. XX Thanks to Mark Zbikowski (markz@microsoft.UUCP). XX XX Applications should set stdout to raw mode when they start up, and set XX it back to the old mode when terminating. XX Programs which rely on cooked mode will appear to hang in raw mode because, XX in raw mode, keyboard reads don't terminate when the user hits ENTER; they XX continue until the line buffer is full. XX ------------------------------------------------------------------*/ XX #include <dos.h> XX #include <stdio.h> XX XX #define DEVICE 0x80 XX #define RAW 0x20 XX #define IOCTL 0x44 XX #define STDIN fileno(stdin) XX #define STDOUT fileno(stdout) XX #define GETBITS 0 XX #define SETBITS 1 XX XX static unsigned old_stdin, old_stdout, ioctl(); XX XX #define BREAKCHECK 0x33 XX XX static unsigned old_breakchk, breakctl(); XX XX /*---- SetHandleRaw ----------------------------------------------------- XX Given any file handle, sets it into raw mode. Useful when opening handles XX to printers, COM ports, etc., as it lets you output ^Z chars without fear. XX -------------------------------------------------------------------------*/ XX void XX SetHandleRaw(handle) XX short handle; XX { XX int temp; XX temp = ioctl(handle, GETBITS, 0); XX if (temp & DEVICE) XX ioctl(handle, SETBITS, temp | RAW); XX } XX XX /*---- rawgetchar --------------------------------------------------- XX Read a character from keyboard with neither echo nor ^C-checking. XX Used by editors, etc., which can't afford to let themselves be killed by the XX user, or who want to use ^C for a function key. XX ----------------------------------------------------------------------*/ XX int XX rawgetchar() XX { XX return (0xff & bdos(7, 0, 0)); XX } XX XX /*--- set_raw --------------------------------------------------------- XX Call this to set raw mode; call restore_raw() later to restore XX console to old rawness state. (Don't strand user in RAW mode!) XX Not only sets raw mode, but also turns off ^C trapping on random DOS calls. XX All character input from stdin should be done with rawgetchar() to XX avoid ^C trapping on input. XX -----------------------------------------------------------------------*/ XX set_raw() XX { XX old_stdin = ioctl(STDIN, GETBITS, 0); XX old_stdout = ioctl(STDOUT, GETBITS, 0); XX old_breakchk = breakctl(GETBITS, 0); XX if (old_stdin & DEVICE) XX ioctl(STDIN, SETBITS, old_stdin | RAW); XX if (old_stdout & DEVICE) XX ioctl(STDOUT, SETBITS, old_stdout | RAW); XX (void) breakctl(SETBITS, 0); XX } XX XX restore_raw() XX { XX if (old_stdin) XX (void) ioctl(STDIN, SETBITS, old_stdin); XX if (old_stdout) XX (void) ioctl(STDOUT, SETBITS, old_stdout); XX if (old_breakchk) XX (void) breakctl(SETBITS, old_breakchk); XX } XX XX static unsigned XX ioctl(handle, mode, setvalue) XX unsigned setvalue; XX { XX union REGS regs; XX XX regs.h.ah = IOCTL; XX regs.h.al = mode; XX regs.x.bx = handle; XX regs.h.dl = setvalue; XX regs.h.dh = 0; /* Zero out dh */ XX intdos(®s, ®s); XX return (regs.x.dx); XX } XX XX /* Controls ^C - checking during everything except keyboard reads */ XX static unsigned XX breakctl(mode, setvalue) XX unsigned setvalue; XX { XX union REGS regs; XX XX regs.h.ah = BREAKCHECK; XX regs.h.al = mode; XX regs.h.dl = setvalue; XX intdos(®s, ®s); XX return (regs.x.dx & 0xff); XX } XX XX /*------ end of rawmode.c ----------------------------------------------*/ XXX_EOF_XXX if test 3326 -ne "`wc -c < rawmode.c`" then echo 'shar: transmission error on "rawmode.c"' fi