From: Frank Kotler on 28 Nov 2009 15:12 carlos wrote: > Hello, I'm trying to make a little program that do the following: > > Check if a key was pressed. If so, return the ascii value of the key. > Otherwise, returns 0. Hi again Carlos, Due to some wind, the power went out, so I took the opportunity to boot to dos and refresh my memory. Your program does what you say... since no key has been pressed, it returns zero. > I made this code, but I'm can't capturing the ascii value of the > arrows. .... or any other ascii value, that I can see... > org 100h > > mov ah, 11h > int 16h > je pre_quit Since no key has been pressed, this goes right to "pre_quit" and returns zero, as described. The rest of it never gets to run. This probably isn't what you really want to do. > mov ah,8h > int 21h > cmp al,0 ; if not extended key > jnz quit > int 21h > jmp quit This would work, if it got to run. > pre_quit: > mov al,0 > quit: > mov ah,4ch > int 21h Rod gave an example of this using ah=6 instead of 8 - which is not the problem, I don't think. Steve gave an example with int 16h/0 - int 16h/10h is the same thing, but for "103-key" keyboards, it catches a few "exotic" keys that int 16h/0 misses. Here's still another example... using int 21h/7 (same as int 21h/8, but it ignores control-c... so we can see its code). This prints out a hex value and goes back for more (hit "ESC" to quit). Best, Frank ; nasm -f bin -o wotkey.com wotkey.asm org 100h top: mov ah, 7 ; no echo - change to 1 if you want int 21h ; get a key call byte2ha ; show it or al, al ; if it was 0 jz top ; call again call newline cmp al, 1Bh ; was it escape? jnz top ; no? do more. ret ;--------------------------- ;------------------------ ; thanks Ben ; thanks TAD byte2ha: push ax aam 16 ; 2 hex: xchg ah,al ; 2 cmp al,0Ah ; 2 sbb al,69h ; 2 das ; 1 int 29h mov al,89h ; 2 (thanks Ruud) jc short hex ; 2 pop ax ret ;------------------------ ;---------------------- newline: push ax mov al, 13 int 29h mov al, 10 int 29h pop ax ret ;-------------------
From: Rod Pemberton on 28 Nov 2009 18:31 "Frank Kotler" <fbkotler(a)myfairpoint.net> wrote in message news:hervvv$jde$2(a)aioe.org... > > Rod gave an example of this using ah=6 instead of 8 RBIL doesn't document that 8h returns extended. That may be reason enough to avoid 8h. But, I rechecked. 8h does return extended, at least for arrow keys, on this machine. > - which is not the > problem, I don't think. I think the real problem was that he had no keypresses in the keyboard input buffer and no wait for a keypress... He was missing a loop on ZF for a wait, or he needed to fill the keyboard buffer. Rod Pemberton
From: carlos on 30 Nov 2009 00:45 Thanks for the help. I think it's impossible to do what I want with 16-bit assembler. In the end I did but at c using the Windows API calling to functions _kbhit and _getch of msvcrt.dll If anyone thinks that can be done with 16-bit assembler, please show me how to. This is c source code: int main() { int c = 0; if (_kbhit()) //if key was pressed. { c = _getch(); //get key if (c == 0 || c == 0xE0) //if is extended key { c = _getch();//get extended key } } return c;//return 0 o value of key. }
From: Rod Pemberton on 30 Nov 2009 04:49 "carlos" <cmontiers(a)gmail.com> wrote in message news:9a32662f-d83b-46f6-9ebf-2bc788ffcf49(a)d21g2000yqn.googlegroups.com... > ... with 16-bit assembler. When you asked for 16-bit assembler, you're asking for an environment that supports 16-bit x86 cpu mode. These are real-mode DOS, v86 mode emulated DOS environments like a Windows "console" application (or dosbox) or DOS running under Linux's DOSEMU, DOSBox application, or your own 16-bit bootloader or a 16-bit operating system, etc. If you used a DOS compiler, e.g., DJGPP, you could see what BIOS and DOS function calls are used. > If anyone thinks [example C code] can be done with 16-bit assembler, > please show me how to. We already showed you that. *Where* are you trying to use the 16-bit code? By "where", I mean what OS, what cpu mode, what environment? You can only use it in 16-bit mode, on x86, in an environment that supports 16-bit x86 cpu mode. You can't be asking for 16-bit code that works with an existing modern OS like Windows 7, Vista, XP or Linux. These OSes limit or prohibit use of 16-bit code, like BIOS calls, and don't support DOS calls. Supposedly, x86 64-bit mode doesn't support 16-bit code natively, so a 64-bit OS might not have support for 16-bit mode. > In the end I did but at c using the Windows API calling to functions > _kbhit and _getch of msvcrt.dll You can't use DOS and BIOS calls in pure Windows. You can use DOS and BIOS calls in real-mode DOS or a Windows "console" application (or dosbox). A Windows "console" is supported in Windows 95, 98, SE, ME, NT, 2K. AFAIK, a Windows "console" is *not* supported in Windows 7 or Vista. Windows XP "console" has limited support. > ... Windows API ... msvcrt.dll It seems you're using a Windows C compiler which calls Windows C functions. It's very likely Windows functions are *not* using BIOS or DOS. You might be able to produce Windows "console" applications with your Windows C compiler, but these won't use DOS or BIOS calls either. The last version that supported DOS was MSVC 1.52c. This version hasn't been available for many years. > int main() > { > int c = 0; > if (_kbhit()) //if key was pressed. > { > c = _getch(); //get key > if (c == 0 || c == 0xE0) //if is extended key > { > c = _getch();//get extended key > } > } > return c;//return 0 o value of key. > } DJGPP (a DOS compiler using GCC and custom C library) calls: bioskey() - int 16h, ah=00h, 01h, 02h, 10h, 11h, or 12h kbhit() - int 16h, ah=11h - after comparing memory 40:1Ah (pointer to first character in BIOS keyboard buffer) and 40:1Ch (pointer to first free character slot in BIOS keyboard buffer) getch() - int 21h, ax=0700h *or* buffered character - after checking isatty and line buffering on stdout & stderr and flushing output You could also look at the OpenWatcom code for the DOS versions of these functions. OW will also have Windows versions. > This is c source code: I understand what the C code you posted is supposed to do. It does what I expect. But, I want you to explain to me what this actually does do with your compiler. Did you run it? Does it immediately exit? Does it ever return a letter or extended key? You posted C code to demonstrate the issue. But, it's unlikely I'm using the same C compiler in the same environment. So, I may be experiencing different results. E.g., I'm not using a Windows C compiler. Functions like getch, kbhit, bioskey, are non-portable and can be implemented differently from compiler to compiler. When I change _kbhit() and _getch() to kbhit() and getch() and compile with *multiple* DOS compilers, this has the exact same problem as your assembly code in real mode DOS and Windows "console". There are *NO* keys in the keyboard buffer. There is *NO* wait for someone to press a key to put a key in the keyboard buffer. This causes the code to immediately exit because if(kbhit()) fails (is false). You can wrap the if(_kbhit()) in a while(1) loop, adding a break statement inside to get it to wait for a keypress. Rod Pemberton
From: Frank Kotler on 30 Nov 2009 09:52 carlos wrote: > Thanks for the help. > I think it's impossible to do what I want with 16-bit assembler. Horsefeathers! As Rod points out, your OS may not support 16-bit code, but that's not your code's fault. ( http://www.dosbox.com/ may help?) > In the end I did but at c using the Windows API calling to functions > _kbhit and _getch of msvcrt.dll Sure. But that's 32-bit code (or 64-bit code, perhaps?). (we can do this in asm, too, of course!) > If anyone thinks that can be done with 16-bit assembler, please show > me how to. Something like... org 100h mov ah, 11h int 16h je pre_quit mov ah,8h int 21h cmp al,0 ; if not extended key jnz quit int 21h jmp quit pre_quit: mov al,0 quit: mov ah,4ch int 21h Oh, wait! That's your original code! In what way does it not do what you want? > This is c source code: > int main() > { > int c = 0; > if (_kbhit()) //if key was pressed. > { > c = _getch(); //get key > if (c == 0 || c == 0xE0) //if is extended key Anyone ever actually seen 0xE0 at this level? I don't recall. > { > c = _getch();//get extended key > } > } > return c;//return 0 o value of key. > } Or, put another way, what does an executable made from this C code do different from your asm code? What does (either program) do if you feed it some input - "myprog<some.txt"? Do you have a convenient way to see the return value in dos? IIRC, we need to run the thing from a batch file and check "errorlevel". PITA. (in Linux, we can do "echo $?" to see the exit code from the last program!) We could arrange to "instrument" your code so you could more easily see what it's doing, if that would help... What might be more "useful" is to wrap the first three lines of your code in a "timer" so we could "return zero if no key is hit within ten seconds" or something... Honestly, Carlos, I don't see anything wrong with your original code... except that it isn't very useful to return zero immediately if^H^H since no key is hit... Best, Frank
First
|
Prev
|
Next
|
Last
Pages: 1 2 3 Prev: Embedding assembler in a language Next: Function BB of Int 1Ah |