From 68526933a835f4a4984769083aebb47405af6086 Mon Sep 17 00:00:00 2001 From: Sean Whitton Date: Fri, 21 Oct 2022 09:47:16 -0700 Subject: have gdbmacs start up Emacs rather than attach to it Additionally, either re-use or kill the GUD interaction buffer rather than calling `gdb-reset' ourselves: killing it is the documented way to reset. --- bin/emacsclient | 82 ++++++++++++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 78 insertions(+), 4 deletions(-) (limited to 'bin/emacsclient') diff --git a/bin/emacsclient b/bin/emacsclient index fe08427d..920c0102 100755 --- a/bin/emacsclient +++ b/bin/emacsclient @@ -24,8 +24,11 @@ min_arg=0 may_start=true want_update=false want_installed=false +want_eval=false +want_version=false devel_running=false installed_running=false +pass_to_gdbmacs=false socket_dir="/run/user/$(id -u)/emacs/" get_listener () { @@ -40,12 +43,34 @@ get_listener () { fi } +maybe_notify () { + echo >&2 "$1" + [ -n "$XDG_RUNTIME_DIR" ] \ + && notify-send --urgency=low --expire-time=10000 "$1" +} + +die_wedged () { + maybe_notify "in-tree Emacs appears to be wedged" + # Only exit non-zero if we were expected to start the daemon. + ! $may_start; exit +} + +egrep_negate () { + echo -n "^([^${1:0:1}]" + for (( i=1; i < ${#1}; i++ )); do + echo -n "|(${1:0:$i}([^${1:$i:1}]|$))" + done + echo -n "|($1.+))" +} + for arg do shift case "$arg" in '--spw/installed') want_installed=true ;; '--spw/no-start') may_start=false ;; '--spw/update-environment') want_update=true ;; + '-V'|'--version') want_version=true ;;& + '-e'|'--eval') want_eval=true ;;& '-s'|'--socket-name') min_arg=2; daemon_name="$1" ;;& '-s'?*) min_arg=1; daemon_name="${arg:2}" ;;& '--socket-name='?*) min_arg=1; daemon_name="${arg:14}" ;;& @@ -81,10 +106,11 @@ if [ -z "$daemon_name" ] && $devel_running && $want_installed; then # Detach gdb so that Emacs can handle the SIGTERM. # We also have to quit gdb so that `gdb-inferior-status' is reset from - # "signal-received"; see `spw/gdbmacs-attach' command. - [ -n "$(get_listener ${socket_dir}gdbmacs)" ] \ - && emacsclient -sgdbmacs --eval '(gud-basic-call "detach")' \ - --eval '(gud-basic-call "quit")' + # "signal-received"; see `spw/gdbmacs-attach' function. + [ -n "${gdbmacs:=$(get_listener ${socket_dir}gdbmacs)}" ] \ + && "$installed_emacsclient" -sgdbmacs \ + --eval '(gud-basic-call "detach")' \ + --eval '(gud-basic-call "quit")' wait $inotifywait devel_running=false @@ -106,6 +132,54 @@ if ! $want_installed && ! $installed_running \ | xargs pwdx | grep -q "$HOME/src/emacs" ); then emacs="$devel_emacs" emacsclient="$devel_emacsclient" + + # ---- Two special cases for primary session that's always under gdb + if [ -z "$daemon_name" ] && ! $want_version; then + # If devel Emacs is stopped or gdbmacs can't start it, ask gdbmacs to + # handle the request: it's probs. C-i e or editing a file via EDITOR. + + [ -n "${gdbmacs:=$(get_listener ${socket_dir}gdbmacs)}" ] \ + && status=$("$installed_emacsclient" \ + -sgdbmacs \ + --eval \ + '(and (boundp '"'"'gud-comint-buffer) + (get-buffer-process gud-comint-buffer) + (string= "signal-received" + gdb-inferior-status))') + + if [ "$status" = t ]; then + if $want_eval || $want_update; then + die_wedged + else + pass_to_gdbmacs=true + fi + elif [ -z "$listener" ]; then + # inotifywait(1) in Debian "bullseye" doesn't have --include. + inotifywait -qq -e create "${socket_dir}" \ + --exclude "$(egrep_negate ${socket_dir}server)" & + inotifywait=$! + + if "$installed_emacsclient" -a '' -sgdbmacs \ + --eval '(spw/gdbmacs-attach)'; then + wait $inotifywait + listener=true + elif $want_eval || $want_update; then + kill $inotifywait + die_wedged + else + kill $inotifywait + pass_to_gdbmacs=true + fi + fi + + if $pass_to_gdbmacs; then + emacs="$installed_emacs" + emacsclient="$installed_emacsclient" + listener="$gdbmacs" + set -- "$@" -sgdbmacs + fi + fi + # ---- End two special cases for primary session that's always under gdb else emacs="$installed_emacs" emacsclient="$installed_emacsclient" -- cgit v1.2.3