OK, saya akan mencoba jawaban yang diperluas. Masalahnya, Emacs Lisp adalah single-threaded. Anda dapat memutar lebih banyak proses, tetapi tidak di dalam interpreter Emacs Lisp. Namun, input keyboard yang perlu Anda baca dari pengguna untuk mengganggu fungsi Anda perlu diproses oleh penerjemah Emacs Lisp yang sama. Ini berarti bahwa jika juru bahasa Anda macet menafsirkan beberapa kode Lisp mungkin tidak ada cara bagi Anda untuk menyela dari dalam. Inilah tempat di manual yang menggambarkan situasi ini:
Pada level kode C, berhenti tidak bisa terjadi di mana saja; hanya di tempat-tempat khusus yang memeriksa tanda berhenti. Alasan untuk ini adalah bahwa berhenti di tempat lain mungkin meninggalkan ketidakkonsistenan dalam kondisi internal Emacs. Karena berhenti ditunda sampai tempat yang aman, berhenti tidak dapat membuat Emacs crash.
https://www.gnu.org/software/emacs/manual/html_node/elisp/Quitting.html
Jadi, bagaimana Emacs masih memiliki fungsi C-g/ pembatalan? - Ada penghitung waktu dan fungsi yang dilakukan I / O (tunggu acara di loop perintah). Pengatur waktu dapat mengatur agar perhitungan Anda dilakukan dalam potongan, sehingga Anda memiliki poin dalam perhitungan Anda di mana Anda dapat melihat-lihat dan, jika perlu, mencegah semua perhitungan lebih lanjut. Fungsi I / O dapat mengirim quit
sinyal. Makro with-keyboard-quit
menunggu sinyal ini dan setelah diterima akan keluar dengan anggun. Namun, fungsi Anda perlu tahu untuk mengirim sinyal ini. Ini berarti bahwa jika fungsi Anda mencegah pengguna mengirim input keyboard, maka Anda tidak akan dapat memanfaatkan interupsi keyboard.
Intinya: coba masukkan kode fungsi Anda while-no-input
. Jika ini tidak berhasil, cobalah menulis ulang fungsi Anda dengan cara yang memungkinkan Emacs memproses acara papan ketik.
while-no-input
makro. Tampaknya melakukan apa yang Anda inginkan: yaitu membatalkan eksekusi tubuhnya ketika input baru muncul.