getch and putc C functions

Does anyone can tell me if this is the better code to do these functions:
[code]
void putChar(char parChar)
{
asm{
mov dl, parChar
mov ah, 2
int 0x21
}
}
char getChar()
{
char read;
asm{
mov ah, 0
int 0x16
mov read,al
}
return read;
}
[/code]

Comments

  • [b][red]This message was edited by AsmGuru62 at 2003-8-30 15:59:44[/red][/b][hr]
    : Does anyone can tell me if this is the better code to do these functions:
    : [code]
    : void putChar(char parChar)
    : {
    : asm{
    : mov dl, parChar
    : mov ah, 2
    : int 0x21
    : }
    : }
    : char getChar()
    : {
    : char read;
    : asm{
    : mov ah, 0
    : int 0x16
    : mov read,al
    : }
    : return read;
    : }
    : [/code]
    :
    [blue]Should be fine... just test the getChar() when pressing arrows or Fx keys.[/blue]


  • Thanks for the reply!

    : [blue]Should be fine... just test the getChar() when pressing arrows or Fx keys.[/blue]

    And how can I do it?

    : : Does anyone can tell me if this is the better code to do these functions:
    : : [code]
    : : void putChar(char parChar)
    : : {
    : : asm{
    : : mov dl, parChar
    : : mov ah, 2
    : : int 0x21
    : : }
    : : }
    : : char getChar()
    : : {
    : : char read;
    : : asm{
    : : mov ah, 0
    : : int 0x16
    : : mov read,al
    : : }
    : : return read;
    : : }
    : : [/code]
    : :
  • : Thanks for the reply!
    :
    : : [blue]Should be fine... just test the getChar() when pressing arrows or Fx keys.[/blue]
    :
    : And how can I do it?
    :
    : : : Does anyone can tell me if this is the better code to do these functions:
    : : : [code]
    : : : void putChar(char parChar)
    : : : {
    : : : asm{
    : : : mov dl, parChar
    : : : mov ah, 2
    : : : int 0x21
    : : : }
    : : : }
    : : : char getChar()
    : : : {
    : : : char read;
    : : : asm{
    : : : mov ah, 0
    : : : int 0x16
    : : : mov read,al
    : : : }
    : : : return read;
    : : : }
    : : : [/code]
    : : :
    :
    [code]
    putChar (getChar ()); // Press F1 here and see what will be printed
    [/code]
  • It printed white spaces! But they have different values (integers for example, as char have) dont they? So I must verify each Fx and arrow key, correct?
    : [code]
    : putChar (getChar ()); // Press F1 here and see what will be printed
    : [/code]

  • : It printed white spaces! But they have different values (integers for example, as char have) dont they? So I must verify each Fx and arrow key, correct?
    [code]
    putChar (getChar ()); // Press F1 here and see what will be printed
    [/code]
    [green]
    Extended keys return AL=0 with the key in AH.
    Printing a 0 looks like a space on the screen.
    Enhanced key board interrupts handle F11 & F12 also.
    There are alternate ways of KBD input & here's some.
    You convert & test it for your C program.
    More info is available in Ralf Browns interrupt list. (an internet freebee)

    INT 16h AH=0 pauses for a key press, & returns AL=character/value. On return
    if AL=0 an extended key was pressed (F# arrows) & the character/value is in AH.
    INT 16h AH=10h is the same as above except it gets enhanced keys F11 & F12?

    You can check the key board & get the key/scan code with out removing
    the key from the keyboard buffer or pausing with this code.[/green]
    [code]
    MOV AH,1 ;get KBD key & status, (MOV AH,11h = enhanced KBD)
    INT 16h ;BIOS interrupt
    JNZ NOKEY ;continue on

    ;& it can be followed with this code to remove the key from the buffer.
    MOV AH,0 ;a key is waiting so it doesn't pause (AH=10h enhanced)
    INT 16h ;get/remove key from buffer
    OR AL,AL ;check for AL=0 , if so extended key is in AH
    JZ isEXTENDED
    ;process regular key in AL here, & jump
    isEXTENDED:
    ;process extended key in AH here

    ;DOS interrupts have some of the same functions as BIOS interrupts.
    MOV AH,1 ; function, pause get key with echo (AH=8 no echo)
    INT 21h ; DOS int, return key in AL
    OR AL,AL ; if AL=0 an extended key is waiting in buffer
    JNZ notEXTENDED
    INT 21h ; get extended key in AL (no pause), process & jump
    notEXTENDED: ;process normal key here
    ;See R.B. int list for INT 21h AH=0Ah buffered input strings.
    ;or INT 21h AH=0Ch flush buffer & execute AL as function. AL=1 get key w/echo
    ;or INT 21h AH=0Bh kbd status, returns AL=0 no key waiting


    ;The key board interrupts can be turned off with by disabling IRQ 1
    ;so flushing key board buffer is not required since the buffer is not filled.
    ;But interrupts will not get a key for you, IN AL,60h will though.
    ;Be sure to turn IRQ 1 back on at the end of your program. (TEST it first !)
    PUSHF ;; save flags
    CLI ;; disable interrupts (clears int flag bit 9)
    IN AL,21h ;; port 21h
    OR AL,00000010b ;; set bit 1, disable IRQ 1 & KBD int's
    ; AND AL,11111101b ;; clear bit 1, enable IRQ 1 & KBD int's
    ; JMP SHORT $+2 ;; kill time for 286 & 386 port I/O recovery
    OUT 21h,AL ;; write the value
    POPF ;; restore flags including the previous interrupt flag state

    ;with IRQ 1 off, you might try this, but mouse packets are a whole nuther wurld
    IN AL,64h ;; Get port 60h status byte from port 64h
    TEST AL,00000001b ;; TEST bit 0, if =0 jump & move on
    JZ KBDbye ;; no KEY or MOUSE packet waiting
    TEST AL,00100000b ;; check for mouse packet ready
    JNZ isMOUSE ;; JMP & deal with mouse packet (& die there)
    IN AL,60h ;; get port 60h last key byte
    OR AL,AL ;; check AL
    JS RELEASED ;; bit 7 set = signed, last key was a release
    JZ ESCpressed ;; exit program or some function here?
    ;process the key that is pressed here, & jump KBDbye
    RELEASED:
    AND AL,01111111b ;; clear bit 7, AL = released key in bits 6-0
    ;process the key that was released here.
    KBDbye:

    ;if your in line assembler won't do CLI or STI you can try this.
    PUSHF
    POP AX
    AND AH,11111101b ; clear bit 9 of AX = CLI
    ; OR AH,00000010b ; set bit 9 of AX = STI
    PUSH AX ; CLI & STI = one byte each. Size in C :-)
    POPF ; 16 bit default assembles this to 7 bytes, 32 bit = 11 bytes

    [/code]
    Disreguard any errors above :-)
    Bitdog



  • Thanks SO much! Altough the second part became to complex to my experience Im really grateful! ;)
    You gave me an excelent explanation!

    : : It printed white spaces! But they have different values (integers for example, as char have) dont they? So I must verify each Fx and arrow key, correct?
    : [code]
    : putChar (getChar ()); // Press F1 here and see what will be printed
    : [/code]
    : [green]
    : Extended keys return AL=0 with the key in AH.
    : Printing a 0 looks like a space on the screen.
    : Enhanced key board interrupts handle F11 & F12 also.
    : There are alternate ways of KBD input & here's some.
    : You convert & test it for your C program.
    : More info is available in Ralf Browns interrupt list. (an internet freebee)
    :
    : INT 16h AH=0 pauses for a key press, & returns AL=character/value. On return
    : if AL=0 an extended key was pressed (F# arrows) & the character/value is in AH.
    : INT 16h AH=10h is the same as above except it gets enhanced keys F11 & F12?
    :
    : You can check the key board & get the key/scan code with out removing
    : the key from the keyboard buffer or pausing with this code.[/green]
    : [code]
    : MOV AH,1 ;get KBD key & status, (MOV AH,11h = enhanced KBD)
    : INT 16h ;BIOS interrupt
    : JNZ NOKEY ;continue on
    :
    : ;& it can be followed with this code to remove the key from the buffer.
    : MOV AH,0 ;a key is waiting so it doesn't pause (AH=10h enhanced)
    : INT 16h ;get/remove key from buffer
    : OR AL,AL ;check for AL=0 , if so extended key is in AH
    : JZ isEXTENDED
    : ;process regular key in AL here, & jump
    : isEXTENDED:
    : ;process extended key in AH here
    :
    : ;DOS interrupts have some of the same functions as BIOS interrupts.
    : MOV AH,1 ; function, pause get key with echo (AH=8 no echo)
    : INT 21h ; DOS int, return key in AL
    : OR AL,AL ; if AL=0 an extended key is waiting in buffer
    : JNZ notEXTENDED
    : INT 21h ; get extended key in AL (no pause), process & jump
    : notEXTENDED: ;process normal key here
    : ;See R.B. int list for INT 21h AH=0Ah buffered input strings.
    : ;or INT 21h AH=0Ch flush buffer & execute AL as function. AL=1 get key w/echo
    : ;or INT 21h AH=0Bh kbd status, returns AL=0 no key waiting
    :
    :
    : ;The key board interrupts can be turned off with by disabling IRQ 1
    : ;so flushing key board buffer is not required since the buffer is not filled.
    : ;But interrupts will not get a key for you, IN AL,60h will though.
    : ;Be sure to turn IRQ 1 back on at the end of your program. (TEST it first !)
    : PUSHF ;; save flags
    : CLI ;; disable interrupts (clears int flag bit 9)
    : IN AL,21h ;; port 21h
    : OR AL,00000010b ;; set bit 1, disable IRQ 1 & KBD int's
    : ; AND AL,11111101b ;; clear bit 1, enable IRQ 1 & KBD int's
    : ; JMP SHORT $+2 ;; kill time for 286 & 386 port I/O recovery
    : OUT 21h,AL ;; write the value
    : POPF ;; restore flags including the previous interrupt flag state
    :
    : ;with IRQ 1 off, you might try this, but mouse packets are a whole nuther wurld
    : IN AL,64h ;; Get port 60h status byte from port 64h
    : TEST AL,00000001b ;; TEST bit 0, if =0 jump & move on
    : JZ KBDbye ;; no KEY or MOUSE packet waiting
    : TEST AL,00100000b ;; check for mouse packet ready
    : JNZ isMOUSE ;; JMP & deal with mouse packet (& die there)
    : IN AL,60h ;; get port 60h last key byte
    : OR AL,AL ;; check AL
    : JS RELEASED ;; bit 7 set = signed, last key was a release
    : JZ ESCpressed ;; exit program or some function here?
    : ;process the key that is pressed here, & jump KBDbye
    : RELEASED:
    : AND AL,01111111b ;; clear bit 7, AL = released key in bits 6-0
    : ;process the key that was released here.
    : KBDbye:
    :
    : ;if your in line assembler won't do CLI or STI you can try this.
    : PUSHF
    : POP AX
    : AND AH,11111101b ; clear bit 9 of AX = CLI
    : ; OR AH,00000010b ; set bit 9 of AX = STI
    : PUSH AX ; CLI & STI = one byte each. Size in C :-)
    : POPF ; 16 bit default assembles this to 7 bytes, 32 bit = 11 bytes
    :
    : [/code]
    : Disreguard any errors above :-)
    : Bitdog
    :
    :
    :
    :

  • : Thanks, Altough the second part became to complex.
    [green]
    I don't understand it either !
    But, now ya got some new stuff to try anyway.

    Bitdog
    [/green]

  • I believe I'm reading this correctly:

    Mind you this is FPC [Pascal/Delphi] syntax, YMMV.



    keyboardhandler(var r:regs);

    scancode:byte;
    c:char;

    begin

    if readportb($64) and 32=0 then begin
    handleMouse;
    end;

    scancode=ReadPortb($60);
    if scancode and $80)=0 then begin //keypressed
    case scancode of
    .
    .
    .
    end; //case
    while readportb($64) and 1=0 do begin //wait to clear buffer
    DisableInterrupts;
    toggleLEDs;
    EnableInterrupts;
    end;
    c:=keymap[scancode]; //keymap has to be set, you can look online for these

    case c of
    #0:begin // function keys
    doSomething;
    end;
    end else begin //not a function key
    writechar(ch);
    end; //case
    end; //if we get here, key is released
    //put the released keycode info here


    end;




    I'm not an expert in assembler, but I have half of it written for me already.We had a '2' where the '1' was supposed to be.

    Pascal is a lot simpler to understand than C, but assembler sometimes a bit more complex than C to read, easy as it may be to code for.

    You don't need int21.Whatever that does, it calls DOS to do it.I have irq 1 already hooked in the kernel's isr, you may need to hook int33[irq 1] to do this correctly.

    By that, I mean setIntVec(33,@YourCustom33); and restoreIntVec(33,@OltInt33); or similar when done.I don't need to do this.


    You have to define your own keymap for this to work, of course.Basically, its a list of char[#,then number] and a displayed char, 'f', for example.We use three sets of these to get the numpad working. Well, I did, anyway, it was a quick shortcut.

    Thanks for the help on the mouse.Was wondering how we got that on int33[irq1] and still handled the keyboard.



Sign In or Register to comment.

Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

Categories