Getting Input from the Console

In order to get input from the console, we first need to get a handle for the standard input device (basically the keyboard). To do this we invoke the GetStdHandle function (another Win32 API function) with STD_INPUT_HANDLE as the only parameter.

When the function returns, the EAX register contains the handle that we are after. Our first task is to store it away in a variable so that it can be used later, whenever we need it.

Now we are ready to obtain input from the console. To do so, we call the Win32 ReadConsole function. It takes five parameters.

The first parameter is the handle of the standard input device, which we just obtained using GetStdHandle.

The second parameter is a pointer to a memory buffer (an array of bytes) large enough to hold the characters that we want to read from the input device.

The third parameter is the number of characters that we would like to read from the input device (this should be less than or equal to the number of bytes the buffer can hold).

The fourth parameter is a pointer to a double word that will hold the number of characters actually read from the input device (perhaps the user doesn't enter as many characters as we would like them to).

Finally, the fifth parameter is reserved and we can just set it to zero.

By default, ReadConsole will wait until the user enters something at the keyboard, and will not return until the user has pressed the enter key.

Here is a simple program which makes use of this functionality, to wait until the user has pressed the enter key before exiting. This is an extension of the example from an earlier section, but now we actually get to see the console that is opened, because it will stay there until the enter key is pressed.

include '%fasminc%/win32ax.inc'

.data

  inchar     DB ?
  numread    DD ?
  inhandle   DD ?

.code

  start:
        invoke  AllocConsole
        invoke  GetStdHandle,STD_INPUT_HANDLE
        mov [inhandle],eax
        invoke  ReadConsole,[inhandle],inchar,1,numread,0
        invoke  ExitProcess,0

.end start