Membaca input dari keyboard dengan syscalls linux x64 (perakitan)

Saya mencoba mempelajari cara menggunakan syscall linux 64bits di perakitan.

Saya sedang menulis beberapa kode untuk membaca keyboard dan cukup mencetaknya di layar dengan tombol yang ditekan: saya menggunakan sys_read.

Kode:

section .text

global _start

_start:
;write startmsg
mov rax, 1
mov rdi, 1
mov rsi, startmsg
mov rdx, sizestart
syscall
;using sys_read
mov ax, 0
mov rdi, 0
mov rsi, key
mov rdx, 2
syscall
;trying to see if esc is pressed then exit
mov rbx, 0x1b
cmp rbx, key
je _exit

_exit:  
mov rax, 60
mov rdi, 0
syscall

section .bss
key resw 1

section .data
startmsg db 'Press a key', 10
sizestart equ $-startmsg

Sekarang ada dua hal yang terjadi: 1) secara otomatis mencetak tombol di layar (D:) 2) tidak keluar ketika saya menekan esc


person vMind    schedule 25.06.2014    source sumber


Jawaban (1)


secara otomatis mencetak tombol di layar

Ini adalah pengaturan default di Linux (terlepas dari bahasa pemrogramannya):

  • Input keyboard dicetak ke layar
  • sys_read akan menunggu hingga tombol return (enter) ditekan

Untuk mengubah perilaku ini, fungsi tcsetattr() (di C) harus dipanggil. Anda harus memanggil fungsi tcgetattr() sebelumnya untuk menyimpan pengaturan saat ini dan memulihkannya sebelum keluar dari program.

Jika Anda ingin menggunakan panggilan sistem secara langsung: tcsetattr dan tcgetattr keduanya menggunakan beberapa sys_ioctl. Untuk mengetahui kode ioctl() mana yang digunakan, Anda dapat menulis program C dengan melakukan tcsetattr dan tcgetattr dan menggunakan "strace" untuk mengetahui syscall mana yang dipanggil.

itu tidak keluar ketika saya menekan esc

Ada tiga masalah dalam file:

  1. Sejauh yang saya pahami dengan benar, Anda membaca dua byte - yang berarti dua penekanan tombol - setiap kali Anda memanggil sys_read
  2. sys_read akan menunggu sampai tombol return ditekan (lihat di atas)
  3. Anda membandingkan nilai 64-bit dengan sepotong memori yang panjangnya hanya satu (atau dua) byte.

Anda harus membaca hanya satu byte menggunakan sys_read. Maka Anda harus melakukan perbandingan bytewise alih-alih perbandingan 64-bit:

cmp bl,key

alih-alih:

cmp rbx,key
person Martin Rosenau    schedule 26.06.2014