The standard input package provides functions that read characters, strings, numeric values, and other types of data. You may specify raw or buffered formats for string and character inputs, numeric inputs always use the buffered format.
include stdin.a or include ucrlib.aThe stdin.a include file exports several symbols. The UCR Standard Library prefaces all "private" names with a dollar sign ("$"). You should not call any routine in this package that begins with this symbol unless otherwise advised. To avoid name conflicts, you should not define any symbols in your programs that begin with a dollar sign ("$"). Note that future versions of the stdlib (that remain compatible with this release) may change "private" names. To remain compatible with future releases, you must not refer to these "private" names within your programs.
Source code appearing in this chapter is current as of Version Two, Release 40. There may be minor changes between this source code and the current release.
IsAlNum ;Passed in AL register. IsAlNumCS dword chrPtr ;Passed by reference in code stream. push 'a' ;Passed by value on the stack. IsAlNumTOS push seg chrVar ;Passed by reference on the stack. push offset chrVar IsAlNumStkIn addition to the above forms there are two other suffixes generally applied to stdlib routine names: "m" and "x". The "m" suffix stands for "malloc". Routines with the "m" suffix typically generate a string result and malloc storage for the string on the heap, returning a pointer to this string in the ES:DI register pair. The routines with an "x" suffix also process strings. Most stdlib routines preserve the value of the ES:DI registers when processing strings; typically, they leave the ES:DI register pair pointing at the start of the string. The routines with an "x" suffix do not preserve ES:DI, they generally leave ES:DI pointing at the zero byte of the string they processed or generated.
To make it easier to use all these different variants, the standard library typically defines a macro for each routine that lets you specify various operands using stdlib "addressing modes." The allowable addressing modes vary by routines, but they typically take one of the following forms:
name ;If operand field is blank, use "plain" version. name var ;Generally passes address of var in code stream (CS). name const ;Pushes const onto TOS and uses nameTOS routine. name [wvar] ;Pushes DS followed by value of wVar variable ; (assumed to be a word) and calls nameSTK name [dVar] ;Pushes dword value of dVar onto stk, calls nameStk.Since not all of these "addressing modes" are applicable to all instructions, and some instructions allow different sets of operands (including multiple operands), there are lots of special cases. Such cases are noted after the explaination for each particular routine.
The rawGetc routine is the basic character input routine in the Standard Input package. This routine jumps to the procedure that reads a character from the current input device (typically the DOS standard input device). The rawGets and rawGetsm (get a string) routines call rawGetc to read a line of data directly from the standard input device.
The buffered input routines, on the other hand, read entire lines of data from the standard input device into an internal buffer and then extract characters from this buffer. When these routines exhaust the characters in the buffer, they read another line of text from the standard input device and reset the buffer pointers to the beginning of the buffer and start over.
Buffered input allows the user to type an entire line and edit that line (e.g., using the backspace or ESC keys) before committing that data to the program. The rawGetc routine, on the other hand, simply returns the backspace character like any other key and relies upon the user program to perform any necessary editing.
There is one detail you must consider when using buffered and raw I/O in a program: if you intermix calls to the raw and buffered routines, you may get strange results. For example, if you call the Getc (buffered) function to read a character from the standard input, this will force the system to read an entire line of text. Subsequent calls to Getc read characters from that same line. However, if you intermix calls to rawGetc with calls to Getc, the rawGetc calls will read directly from the standard input ignoring the characters in the internal buffer. This will appear to the user as though the data is being read out of order.
Because buffered I/O is somewhat "safer," the numeric input routines all use buffered I/O. Therefore, as a general rule, you should attempt to use buffered I/O for all your input operations. Reserve raw input for the situations where you have to guarantee that the input is coming directly from the standard input device.
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| Getc | X | X | - | X | - | - |
The getc macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| Getc | X | X | - | X | X | - |
cvar byte ? wvar word cvar dvar dword cvar . . . print "Enter Y or N:" getc toupper cmp al, 'Y' je EnteredYes . . . print "Enter a character: " getcCS dword cvar printf "You entered %c\n", cvar . . . print "Enter a character: " pshadrs cvar getcStk printf "You entered %c\n", cvar . . . getc ;Leaves character in AL getc cvar ;Leaves character in byte var cvar. getc [wvar] ;ds:wvar is near ptr to dest location. getc [dvar] ;dvar contains far ptr to dest location. . . . print "Enter a character:" getc cvar printf "You entered %c\n", cvar . . . print "Enter a character:" getc [wvar] print "You entered " putc cvar putcr . . . print "Enter a character:" getc [dvar] print "You entered " putc cvar putcr
If the buffer is empty when you call Peekc, the system will read a new line of text from the standard input and then return a copy of the first character in the buffer without removing that character from the buffer.
Peekc returns the carry flag clear if no error occurs. Assuming exceptions are not active, Peekc will return the carry flag set if an error occurs (while reading the buffered line of text from the standard input). If exceptions are active, Peekc (actually the call to rawGets that reads the line of text into the buffer) will raise an appropriate exception. See the rawGets routine for more details on the possible exceptions.
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| Peekc | X | X | - | X | - | - |
The peekc macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| Peekc | X | X | - | X | X | - |
print "Enter Y or N:" peekc toupper cmp al, 'Y' je EnteredYes . . . print "Enter Y or N:" peekcCS byte YorNChar cmp YorNChar, 'Y' je EnteredYes . . . pshadrs YorNChar peekcStk cmp YorNChar, 'Y' je EnteredYes . . . getc ;Returns character in AL getc CharVar ;Puts char in CharVar getc [wVar] ;Stores char where wVar points in DS getc [dVar] ;Stores char where dVar points
GetsCS works like Gets except a pointer to the destination string follows the call in the code stream; it does not use the value in ES:DI.
GetsStk is very similar to Gets except it expects the address of the destination string on the stack rather than in the ES:DI register pair.
Getsm allocates storage on the heap and copies the contents of the internal buffer to the storage allocated on the heap. Getsm returns the address of this heap object in the ES:DI register pair.
These routines all return the error status in the carry flag. If the carry is set on return, then some sort of error occured while attempting to input the line of text. If exceptions are enabled, these calls will raise an appropriate exception. This is typically an EOF, file I/O error, or memory allocation (getsm) exception.
If you use Getc to read all of the characters from the input buffer except the terminating carriage return, a call to Gets, GetsStk, or Getsm will ignore this last "character" in the buffer and read a new line of text from the user. The next buffered get* call will force the system to read a new line of text from the standard input device.
| Name | Plain | CS | TOS | Stk | X | CSi | M |
|---|---|---|---|---|---|---|---|
| Gets | X | X | - | X | - | - | X |
The gets macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| Gets | X | X | - | X | X | - |
Name byte 256 dup (0) . . . print "Enter your name:" lesi Name gets printf "Hello %s\n", Name . . .Gets calls GetcCS with the address of "byteVar" following in the code stream.
Gets assumes the word variable contains a DS-relative near pointer. It pushes the value of DS onto the stack followed by the value of the word variable. Then it calls GetsStk.
Gets assumes the dword variable contains a far pointer. It pushes the value of the dword variable onto the stack and calls GetsStk.
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| GetcLen | X | X | - | X | - |
The GetcLen macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| GetcLen | X | X | - | X | X | - |
getc mov Char1, al getc mov Char2, al GetcLen print "There are " puti print " characters left in the buffer." . . .
getc mov Char1, al getc mov Char2, al GetcLenCS dword BufLen printf "There are %d characters left in the buffer.\n",BufLen . . . getc mov Char1, al getc mov Char2, al pshAdrs BufLen GetcLenStk printf "There are %d characters left in the buffer.\n",BufLen . . . The GetcLen macro also allows an extended syntax with operands specifying the particular "addressing mode" for the destination value: getcLen ;Returns length in CX. getcLen wVar ;Stores length into wVar (word variable) getcLen [wVar] ;Stores length where wVar points in DS. getcLen [dvar] ;Stores length where dVar points.
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| FlushGetc | X | - | - | - | - | - |
The FlushGetc macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| FlushGetc | X | - | - | - | - | - |
print "Enter a line of text:" FlushGetc getsm print "You entered: " puts free . . .
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| RawGetc | X | - | - | - | - | - |
The RawGetc macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| RawGetc | X | - | - | - | - | - |
print "Enter Y or N:" rawgetc tolower cmp al, 'y' je EnteredYes . . .
These routines ignore any non-ASCII characters. If you press a cursor control key or a function key, that key is not placed in the destination string. Since the buffered input routines read data from the standard input device via calls to rawGets, this also means that you cannot read non-ASCII characters using buffered I/O routines like Getc, PeekC, Gets, etc.
| Name | Plain | CS | TOS | Stk | X | CSi | M |
|---|---|---|---|---|---|---|---|
| RawGets | X | X | - | X | - | - | X |
The RawGets macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| RawGets | X | X | - | X | X | - |
Name byte 256 dup (0) . . . print "Enter your name:" lesi Name rawgets printf "Hello %s\n", Name . . . print "Enter your name again:" rawGetsCS dword Name printf "Hi again, %s\n", Name . . . print "Enter your name again:" push seg Name push offset Name rawGetsStk printf "Hi again, %s\n", Name . . . print "Enter your name yet a third time:" rawgetsm print "Are you sure you're " puts putc '?' putcr free rawGets ;Stores string at ES:DI rawGets bVar ;Stores string starting at location bVar rawGets [wVar] ;Stores string at address pointed at by wVar. rawGets [dVar] ;Stores string at far address in dVar.
GetcStdIn begins by checking to see if it is reading data directly from some device (e.g., the keyboard) or from a file. The behavior of the system changes somewhat if you are reading data from a file (via input redirection) rather than a device. GetcStdIn processes the input stream differently so that any routines calling GetcStdIn (e.g., rawGetc) see a unified view of the system and don't have to do any special handling of their own. One difference, for example, concerns end of line sequences. GetcStdIn assumes that data coming from a hardware device terminates each line with a CR (but no corresponding LF); it assumes that data coming from a file terminates each line with a CR/LF sequence. GetcStdIn eats the line feed in a CR/LF sequence if reading data from a file. It simply passes line feeds read from a device (like the keyboard).
GetcStdIn checks for device/file I/O errors and end of file (control-Z on a device, true end of file when reading from a file). If a device or file I/O error occurs, GetcStdIn will raise the $FileIO exception if exceptions are active. Otherwise, it will set the carry flag and return the appropriate DOS error code in the AX register. If end of file occurs, GetcStdIn will raise the $EndOfFile exception, if exceptions are active; otherwise it will return with the carry flag clear and AH=0. If no error occurs, GetcStdIn returns with the carry flag clear, the ASCII code in AL, and AH=1.
GetcStdIn call DOS to read a character from the standard input device. Therefore, it inherits all the properties of the DOS standard input device. In particular, if the current input device is the keyboard and the user presses a non-ASCII key (e.g., a function or cursor control key), then GetcStdIn returns two characters: a zero byte followed by the scan code for that particular key. GetcStdIn does not do any special handling on non-ASCII characters. That is still the application program's responsibility to manage.
| Name | Plain | CS | TOS | Stk | X | CSi | M |
|---|---|---|---|---|---|---|---|
| GetcStdIn | X | - | - | - | - | - | - |
The GetcStdIn macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| GetcStdIn | X | - | - | - | - | - |
print "If inputing data from the keyboard, " print "press control-Z to stop.",nl GCLoop: getcStdIn jc IOError cmp ah, 0 je EOFError cmp al, 0 je NonASCIIChar print "You pressed: " putc putcr jmp GCLoop NonASCIIChar: GetcStdIn jc IOError cmp ah, 0 je EOFError print "You pressed a non-ASCII character whose " print "scan code is " puth putcr jmp GCLoop IOError: print "I/O error #" puti print " occured during read.",nl jmp Done EOFError: print "End of file encountered.",nl Done:
Unlike the PC BIOS int 16h functions, GetcBIOS does not return the scan code in AH and a zero in AL if the user presses a non-ASCII character. GetcBIOS preprocesses such keystrokes and returns the same two-character sequences that GetcStdIn returns.
Note that GetcBIOS does not check for end of file, therefore it always returns a one in the AH register. If you press the control-Z key, GetcBIOS will return the ASCII code for control-Z. Likewise, GetcBIOS does not handle control-C any differently than other keys. It just returns the ASCII code for control-C (03).
| Name | Plain | CS | TOS | Stk | X | CSi | M |
|---|---|---|---|---|---|---|---|
| GetcBIOS | X | X | - | X | - | - | X |
The GetcBIOS macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| GetcBIOS | X | - | - | - | - | - |
controlZ = 26 print "If inputing data from the keyboard, " print "press control-Z to stop.",nl GCLoop: getcStdIn cmp al, controlZ je Done cmp al, 0 je NonASCIIChar print "You pressed: " putc putcr jmp GCLoop NonASCIIChar: GetcStdIn print "You pressed a non-ASCII character whose " print "scan code is " puth putcr jmp GCLoop Done:
Thet GetInAdrs and GetInAdrs (along with the PushInAdrs and PopInAdrs) functions provide you with the ability to maintain the GetcAdrs pointer. GetInAdrs returns the current value of this (far) pointer in the ES:DI register pair. This allows you to save the current value so you can restore it later after you are done redirecting the standard input. The SetInAdrs copies the value in the ES:DI register pair to the GetcAdrs pointer. Presumably, you would load the address of an appropriate input device handler into ES:DI before calling SetInAdrs.
An input device handler should read a single character from it associated device and return the ASCII code (or whatever code you want to use) in the AL register. It should also return an error status in the carry flag (C=1 for error, C=0 for success). If an error occurs, you can return a DOS error code in the AX register. The character device handler should return the EOF status in AH (AH=0 for end of file, AH=1 for not end of file). Note that when returning end of file, you should clear the carry flag.
If exceptions are active, you can raise an appropriate exception when EOF or an input error occurs. Your device handler should explicitly check to see if exceptions are active (using the GetXEnabled call) before raising any exceptions.
Input handlers must be far procedures and must preserve all registers except AX.
| Name | Plain | CS | TOS | Stk | X | CSi | M |
|---|---|---|---|---|---|---|---|
| GetInAdrs | X | - | - | - | - | - | - |
| SetInAdrs | X | - | - | - | - | - | - |
The GetInAdrs and SetInAdrs macros allow the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| GetInAdrs | X | - | - | - | - | - |
| SetInAdrs | X | - | - | - | - | - |
DOSInput proc far mov ah, 7 ;DOS char read w/o ^c chk int 21h mov ah, 1 ;Cannot detect EOF. ret DOSInput endp ASCIIOnly proc far AOLoop: GetcStdIn jc Done ;Bail if error. cmp ah, 0 je Done ;Bail if EOF. cmp al, 0 ;Non-ASCII character? jne Done GetcStdIn ;Eat scan code jmp AOLoop ; and get the next char. Done: ret ASCIIOnly endpThe following example demonstrates how to use the SetInAdrs and GetInAdrs functions to redirect the standard input device:
GetcAdrsSave dword ? . . . GetInAdrs mov word ptr GetcAdrsSave, di mov word ptr GetcAdrsSave+2, es lesi DOSInput SetInAdrs . . ;Input statements in this section . ; read their data using the DOSInput . ; character handler (no ctrl-C checking). . lesi ASCIIOnly SetInAdrs . . ;Input statements in this section . ; read their data using the ASCIIOnly . ; character handler. Therefore, the . ; input routines will only see ASCII . ; characters, all other keypresses . ; are ignored. . les di, GetcAdrsSave ;Restore the address SetInAdrs ; of the original . ; input handler. . .
The PushInAdrs function pushes the current GetcAdrs pointer onto an internal stack. It then copies the pointer in ES:DI to GetcAdrs. Therefore, PushInAdrs roughly corresonds to the SetInAdrs routine with the added benefit of automatically preserving the previous pointer value. The internal GetcAdrs stack contains enough storage to hold 16 (nested) addresses you've pushed on the stack. This should be far more than any one program will ever need (most programs would need only one or two positions) assuming there isn't a programming error like forgetting to pop values you've pushed. If a stack overflow occurs and exceptions are active, PushInAdrs will raise the $GetcStkErr exception. If exceptions are not active, then PushInAdrs returns with the carry flag set and it does not change the current value of the GetcAdrs pointer nor does it change any value on the stack (in other words, the call is ignored).
The PopInAdrs pops an address off the internal stack and stores this address into the GetcAdrs pointer. This restores GetcAdrs with the address of the previous character input device handler. PopInAdrs returns with the carry flag clear if it sucessfully restored the GetcAdrs pointer. If stack underflow occurs (i.e., you call PopInAdrs when there is no data on the internal stack), PopInAdrs will raise a $GetcStkErr exception if exceptions are active. It will return with the carry flag set and store the address of the GetcStdIn routine into GetcAdrs if exceptions are not active.
| Name | Plain | CS | TOS | Stk | X | CSi | M |
|---|---|---|---|---|---|---|---|
| PushInAdrs | X | ||||||
| PopInAdrs | X |
The PushInAdrs and PopInAdrs macros allow the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| PushInAdrs | X | - | - | - | - | - |
| PopInAdrs | X | - | - | - | - | - |
. . . lesi DOSInput PushInAdrs . . ;Input statements in this section . ; read their data using the DOSInput . ; character handler (no ctrl-C checking). . lesi ASCIIOnly SetInAdrs . . ;Input statements in this section . ; read their data using the ASCIIOnly . ; character handler. Therefore, the . ; input routines will only see ASCII . ; characters, all other keypresses . ; are ignored. . PopInAdrs ;Restore the address . ; of the original . ; input handler. .
| Name | Plain | CS | TOS | Stk | X | CSi | M |
|---|---|---|---|---|---|---|---|
| ResetStdIn | X |
The ResetStdIn macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| ResetStdIn | X | - | - | - | - | - |
. . . ResetStdIn . . ;Standard input behaves just as it did on program startup . ; at this point.
Note that many routines in the standard input package, including all buffered I/O routines, throw out any non-ASCII characters. Therefore, although tstKbd might claim keystrokes are available, a call to one of these routines that throw away non-ASCII characters may have to wait until the user presses an actual ASCII character at the keyboard. GetcBIOS, GetcStdIn and rawGetc (assuming GetcAdrs points at GetcStdIn or GetcBIOS) are the only routines in the standard input package that will return non-ASCII characters like function keys or cursor control keys. Therefore, you would typically call one of these three routines after testing the system status with a tstKbd call, assuming you did not want a delay if tstKbd returns true. See the tstASCII function for additional details.
| Name | Plain | CS | TOS | Stk | X | CSi | M |
|---|---|---|---|---|---|---|---|
| TstKbd | X |
The TestKbd macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| TestKbd | X | - | - | - | - | - |
; The following loop continuously checks the keyboard to ; see if a key is available. If not, it executes the ; "Background" procedure on each iteration of the loop. ; ; This allows background processing to commence as long ; as the user does not press a key on the keyboard. TstLoop: tstKbd jne GotAKey call Background jmp TstLoop GotAKey: rawgetc ;Read the key pressed from the user . . .
| Name | Plain | CS | TOS | Stk | X | CSi | M |
|---|---|---|---|---|---|---|---|
| TstInput | X |
The TestInput macro allows the following operands:
| Name | byteVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| TestInput | X | - | - | - | - | - |
; The following loop continuously checks the keyboard to ; see if a key is available. If not, it executes the ; "Background" procedure on each iteration of the loop. ; ; This allows background processing to commence as long ; as the user does not press a key on the keyboard. TstLoop: tstInput jne GotAKey call Background jmp TstLoop GotAKey: gets ;Read a line of text from the user. . . .
If exceptions are enabled, these routines will raise an overflow exception if the value will not fit into 16 bits (Geth) or 32 bits (Gethl). These routines will raise a $Conversion exception if there are any illegal characters in the number. The regular expression that defines a legal hexadecimal value is:
ws* ["0"-"9","A"-"F","a"-"f"] [["0"-"9", "A"-"F", "a"-"f", "_"]* ["0"-"9", "A"-"F", "a"-"f"]]? [ws | ","]In English, this regular expression says that a hexadecimal value may begin with zero or more whitespace characters, followed by a single hexadecimal digit (0-0, A-F, a-f), followed by zero or more hexadecimal characters and underscores (although an underscore cannot end the value), followed by whitespace or a comma.
Other possible exceptions include $EndOfFile and $FileIO. These exceptions, of course, assume that the standard input is redirected from a file.
If exceptions are not enabled, Geth and Gethl return the carry flag set if an error occurs.
If the hexadecimal value ends with the comma character, the Geth and Gethl routines will remove the comma from the standard input stream. However, if the hexadecimal value ends with a whitespace character, Geth and Gethl will not remove the whitespace character from the standard input stream.
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| Geth | X | X | - | X | - | - |
| Gethl | X | X | - | X | - | - |
The Geth and Gethl macros allow the following operands:
| Name | Var | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| Geth | X | word | - | X | X | - |
| Gethl | X | dword | - | X | X | - |
cout "Enter a 16-bit hex value:" geth cout "You entered: ",ax,nl gethCS dword wVar pshAdrs wVar gethStk cout "Enter a 32-bit hex value: " gethl cout "You entered: ",eax,nl getlhcs dword dVar pshadrs dVar getlhStk
ws* ["-"]? ["0"-"9"] [["0"-"9","_"]* ["0"-"9"]]? [ws | ","]
In English, this means that a valid integer value can be preceeded by zero or more whitespace characters, followed by an optional minus sign, followed by at least one decimal digit, followed by zero or more decimal digits or underscores (although the number must end with a digit), followed by a comma or whitespace.
Geti can raise the following exceptions:
$Conversion- If the decimal string contains illegal characters. $Overflow- If the value is outside the range -32768..+32767. $EndOfFile- If end of file occurs while reading the input. $FileIO- If a file I/O error occurs while reading the input. $Break- If the user presses control-C while inputting the data.Geti will only raise an exception if exceptions are enabled. It will return the carry flag set if an error occurs and exceptions are not active.
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| Geti | X | X | - | X | - | - |
The Geti macro allows the following operands:
| Name | wordVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| Geti | X | X | - | X | X | - |
print "Enter an integer: " geti print "You entered: " puti putc getiCS dword wVar pshadrs wVar getiStk geti wVar geti [wVar] geti [dVar]
ws* ["0"-"9"] [["0"-"9","_"]* ["0"-"9"]]? [ws | ","]See the description of Geti for more details about Getu.
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| Getu | X | X | - | X | - | - |
The Getu macro allows the following operands:
| Name | wordVar | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| Getu | X | X | - | X | X | - |
print "Enter an unsigned 16-bit integer: " getu print "You entered: " putu putcr getuCS dword wVar pshadrs wVar getuStk getu wVar getu [wVar] getu [dVar]
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| Getl | X | X | - | X | - | - |
The Getl macro allows the following operands:
| Name | dword Var | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| Getl | X | X | - | X | X | - |
print "Enter a signed 32-bit integer: " getl print "You entered: " putl putcr getlCS dword dVar pshadrs dVar getlStk getl dVar getl [wVar] getl [dVar]
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| Getul | X | X | - | X | - | - |
The Getul macro allows the following operands:
| Name | dword Var | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| Getul | X | X | - | X | X | - |
print "Enter a signed 32-bit unsigned integer: " getul print "You entered: " putul putcr getulCS dword dVar pshadrs dVar getulStk getul dVar getul [wVar] getul [dVar]
Getf can raise the following exceptions:
$Conversion- If the decimal string contains illegal characters. $Overflow- If the value is outside the range 10**-4930..10**+4930 $EndOfFile- If end of file occurs while reading the input. $FileIO- If a file I/O error occurs while reading the input. $Break- If the user presses control-C while inputting the data.Getf will only raise an exception if exceptions are enabled. It will return the carry flag set if an error occurs and exceptions are not active.
| Name | Plain | CS | TOS | Stk | X | CSi |
|---|---|---|---|---|---|---|
| Getul | X | - | - | - | - | - |
The Getf macro allows the following operands:
| Name | Var | Num const | [word Var] | [dword Var] | String Const | |
|---|---|---|---|---|---|---|
| Getf | X | - | - | - | - | - |
print "Enter a floating point value: " getf print "You entered: " mov ax, 15 pute putcr
scanf byte "format string", 0 dword <Parameter list>The format string consists of a list of format items. A format item takes one of the following forms:
%i Input an integer %^i Input a *integer %d Input an integer %^d Input a *integer %u Input an unsigned integer %^u Input an unsigned *integer %li Input a 32-bit integer %^li Input a 32-bit *integer %ld Input a 32-bit integer %^ld Input a 32-bit *integer %lu Input a 32-bit unsigned integer %^lu Input a 32-bit unsigned *integer %x Input a 16-bit hex value %^x Input a 16-bit hex value and store it through a pointer %lx Input a 32-bit hex value %^lx Input a 32-bit hex value and store it through a pointer %h Input an 8-bit hex value %^h Input an 8-bit hex value and store it through a pointer %c Input a character %^c Input a ^character %s Input a string %^s Input a *string %f Input a float %^f Input a *float %g Input a double %^g Input a *doubleThere must be at least one character following each format item in the scanf format string. Typically, this would be a space or the string's zero terminating byte. This character is know as the terminating character. Scanf will allow this character (along with whitespace, a comma, or an end of line) to terminate any given input. If the terminating character is a space or a zero byte, then Scanf only allows whitespace as a termination value.
For each format item in the format string, there must be a corresponding double word address following the format string. Consider the following example:
scanf byte "%d %d %c",0 dword IntVar1, IntVar2, CharVarIf a space appears in the format string, then Scanf will automatically skip all whitespace characters before inputting the next value. This is the normal condition for numeric input (via calls to geti, getu, getf, etc). Note, however, that Scanf extends this behavior to characters and strings as well. In the example above, if the user had typed "1 2 c" then Scanf would have place the character "c" into CharVar rather than a space. If you want to read the space as a character, you would need to call Getc.
The character immediately following a format item is special. Scanf will allow the input value corresponding to that format item to end on that character even if that would normally be illegal. For example, consider the following Scanf call:
scanf byte "%i: %i)",0 dword i,jIf any other character appears in the format string, Scanf will remove that character from the standard input if it is the next character to be read from the standard input. Otherwise, Scanf ignores that character in the format string. Note that anywhere a space appears in the format string, Scanf will remove zero or more white space values (rather than just one) from the standard input. Consider the following example:
scanf byte " -%d (%d)",0 dword i,jIn this example, the first character of the format string is a blank. Therefore, Scanf will skip any number of whitespace characters that appear at the beginning of the line. The "-" symbol tells Scanf to eat a minus sign, if that's the next character on the input. Then Scanf reads an integer value into variable I. Next, it skips any amount of whitespace and eats a possible open parenthesis. Then it reads an integer variable into J and (possibly) eats a closing parenthesis. Note that this code attempts to prevent the user from entering negative numbers for variable I (although if the user presses "--1" s/he would still succeed in entering a negative value).
If the "^" symbol appears between the "%" and the type specification then the corresponding parameter specifies the address of a pointer to the destination object rather than the address of the object itself. This lets you read data into strings and other objects you've allocated on the heap or in a local activation record. The pointer itself must be a static variable (typically in the data segment, though this is not required).
Scanf calls Gets to read strings. Therefore, Scanf can read as many as 255 characters from the user when you specify string input. You must ensure that your string variables have sufficient storage to hold any input.
Given Scanf's nature, it is difficult for Scanf to report an error on a specific input element. Therefore, Scanf does not return with the carry denoting an error state. However, Scanf will raise an appropriate exception if an error occurs. If you enable exceptions you can trap errors that occur within Scanf.
Since Scanff duplicates all the features found in Scanf (in addition to adding floating point support), you should never use both Scanff and Scanf in the same program; doing so would waste memory. MASM will generate a warning message if you call both functions in your program.
print "Enter an integer, a character, and a string:" scanf byte "%d %c %s",0 dword IntVar, CharVar, StrVar printf byte "You entered int=%d, char=%c, string=%s\n",0 dword IntVar, CharVar, StrVar
scanf "%d %c %s",IntVar,CharVar,StrVarYou may also specify the dword parameters separately, as follows:
scanf "%d %c %s" dword IntVar, CharVar, StrVar
GetTermChar returns in AL the current special termination character. If this value is zero, then this feature is currently disabled. You can use GetTermChar to preserve the current value if you need to change it for a short time period.
SetTermChar sets the special termination character to the value found in the AL register.
SaveChar byte ? . . . GetTermChar ;Save current value mov SaveChar, al mov al, ":" ;Allow #s to end with SetTermChar ; a ":" character. . . ;Numeric input routines . ; that allow values to . ; end with a ":" . mov al, SaveChar ;Restore the special SetTermChar ; termination char to ; its previous value.