From: Karoly Lorentey Date: Sun, 25 Dec 2005 20:06:58 +0000 (+0000) Subject: Reimplement terminal parameters in C; clean up term.c, create terminal.c. X-Git-Url: http://git.hcoop.net/bpt/emacs.git/commitdiff_plain/ed8dad6b616204b4dd4e853801f41da6f4c3b0a7?hp=4beb2d71ea5cbd7f451b8958c3cd21b3cd4d6edc Reimplement terminal parameters in C; clean up term.c, create terminal.c. * lisp/termdev.el (terminal-parameter-alist, terminal-parameters, terminal-parameter-p) (terminal-parameter, set-terminal-parameter, terminal-handle-delete-frame): Remove. * src/term.c (Vring_bell_function, device_list, initial_device) (next_device_id, ring_bell, update_begin, update_end) (set_terminal_window, cursor_to, raw_cursor_to) (clear_to_end, clear_frame, clear_end_of_line) (write_glyphs, insert_glyphs, delete_glyphs, ins_del_lines) (get_device, Fdisplay_name, create_device, delete_device) (Fdelete_display, Fdisplay_live_p, Fdisplay_list) Move to terminal.c. (syms_of_term): Move their initialization to terminal.c. * src/terminal.c: New file. (device_list, next_device_id, initial_device, Vring_bell_function) (ring_bell, update_begin, update_end, set_terminal_window) (cursor_to, raw_cursor_to, clear_to_end, clear_frame) (clear_end_of_line, write_glyphs, insert_glyphs, delete_glyphs) (ins_del_lines, get_device, create_device, delete_device) (Fdelete_display, Fdisplay_live_p, Fdisplay_list, Fdisplay_name): Move here. (mark_devices, get_terminal_param, store_terminal_param) (Fterminal_parameters, Fterminal_parameter) (Fmodify_terminal_parameters, Fset_terminal_parameter) (init_initial_device, delete_initial_device) (syms_of_terminal): New functions. * lisp/simple.el (normal-erase-is-backspace-setup-frame) (normal-erase-is-backspace-mode): Rephrase things without terminal-parameter-p. * lisp/termdev.el (terminal-getenv, terminal-setenv) (with-terminal-environment): Ditto. * mac/makefile.MPW (EmacsObjects): Add terminal.c.x. ({Src}terminal.c.x): Add dependencies. * src/Makefile.in (obj): Add terminal.o. (terminal.o): Add dependencies. [HAVE_CARBON]: Make terminal.o depend on macgui.h. * src/alloc.c (mark_devices): Declare. (Fgarbage_collect): Call `mark_devices'. * src/dispextern.h (set_scroll_region, turn_off_insert) (turn_off_highlight, background_highlight, clear_end_of_line_raw) (tty_clear_end_of_line, tty_setup_colors, delete_tty): Remove. (raw_cursor_to, clear_to_end, tty_turn_off_insert) (tty_turn_off_highlight): Add declaration. * src/emacs.c (main): Call `syms_of_terminal'. * src/frame.c (get_future_frame_param): New function. (Fmake_terminal_frame): Use it. * src/keyboard.c (pop_kboard): Remove unused variable. (Fset_output_flow_control): Return nil. * src/keymap.h (Fset_keymap_parent): Add EXFUN. * src/lisp.h (syms_of_terminal): Declare it. * src/sysdep.c (reset_sys_modes): Update for renames. * src/term.c (set_scroll_region): Rename to `tty_set_scroll_region'. (turn_on_insert): Rename to `tty_turn_on_insert'. (turn_off_insert): Rename to `tty_turn_off_insert'. (turn_off_highlight): Rename to `tty_turn_off_highlight'. (turn_on_highlight): Rename to `tty_turn_on_highlight'. (toggle_highligh): Rename to `tty_toggle_highlight'. (background_highlight): Rename to `tty_background_highlight'. (highlight_if_desired): Rename to `tty_highlight_if_desired'. (tty_ring_bell, tty_update_end, tty_set_terminal_window) (tty_set_scroll_region, tty_background_highlight) (tty_cursor_to, tty_raw_cursor_to, tty_clear_to_end) (tty_clear_frame, tty_clear_end_of_line, tty_write_glyphs) (tty_insert_glyphs, tty_delete_glyphs, tty_ins_del_lines) (term_get_fkeys, tty_setup_colors, dissociate_if_controlling_tty) (delete_tty): Add static modifier. (tty_reset_terminal_modes, tty_set_terminal_window) (tty_set_scroll_region, tty_background_highlight) (tty_highlight_if_desired, tty_cursor_to) (tty_raw_cursor_to, tty_clear_to_end, tty_clear_frame) (tty_clear_end_of_line, tty_write_glyphs, tty_insert_glyphs) (tty_delete_glyphs, tty_ins_del_lines, turn_on_face): Update for renames. * src/termhooks.h (param_alist): New member to struct device. * src/xterm.h (x_delete_device): Declare. git-archimport-id: lorentey@elte.hu--2004/emacs--multi-tty--0--patch-460 --- diff --git a/README.multi-tty b/README.multi-tty index c4e990e5b8..ebe064c2fc 100644 --- a/README.multi-tty +++ b/README.multi-tty @@ -401,6 +401,41 @@ is probably not very interesting for anyone else.) THINGS TO DO ------------ +** Implement automatic forwarding of client environment variables to + forked processes, as discussed on the multi-tty list. Terminal + parameters are now accessible in C code, so the biggest obstacle is + gone. The `getenv_internal' and `child_setup' functions in + callproc.c must be changed to support the following variable: + + terminal-local-environment-variables is a variable defined in ... + + Enable or disable terminal-local environment variables. + + If set to t, `getenv', `setenv' and subprocess creation + functions use the environment variables of the emacsclient + process that created the selected frame, ignoring + `process-environment'. + + If set to nil, Emacs uses `process-environment' and ignores + the client environment. + + Otherwise, `terminal-local-environment-variables' should be a + list of variable names (represented by Lisp strings) to look + up in the client environment. The rest will come from + `process-environment'. + +** (Possibly) create hooks in struct device for creating frames on a + specific terminal, and eliminate the hackish terminal-related frame + parameters (display, tty, tty-type). + + make_terminal_frame + create_tty_output + + +** Move Fsend_string_to_terminal to term.c, and declare get_named_tty + as static, removing it from dispextern.h. + Move fatal to emacs.c and declare it somewhere. + ** Search for `suspend-emacs' references and replace them with `suspend-frame', if necessary. Ditto for `save-buffers-kill-emacs' vs. `save-buffers-kill-display'. @@ -450,6 +485,11 @@ THINGS TO DO ** I think `(set-)terminal-local-value' and the terminal parameter mechanism should be integrated into a single framework. + (Update: `(set-)terminal-local-value' is now eliminated, but the + terminal-local variables should still be accessible as terminal + parameters. This also applies to `display-name' and similar + functions.) + ** Add the following hooks: after-delete-frame-hook (for server.el, instead of delete-frame-functions), after-delete-terminal-functions, after-create-terminal-functions. diff --git a/lisp/simple.el b/lisp/simple.el index bfbdaf14d2..99487430c8 100644 --- a/lisp/simple.el +++ b/lisp/simple.el @@ -5323,10 +5323,8 @@ call `normal-erase-is-backspace-mode' (which see) instead." "Set up `normal-erase-is-backspace-mode' on FRAME, if necessary." (unless frame (setq frame (selected-frame))) (with-selected-frame frame - (unless (terminal-parameter-p nil 'normal-erase-is-backspace) - (if (cond ((terminal-parameter-p nil 'normal-erase-is-backspace) - (terminal-parameter nil 'normal-erase-is-backspace)) - ((eq normal-erase-is-backspace 'maybe) + (unless (terminal-parameter nil 'normal-erase-is-backspace) + (if (cond ((eq normal-erase-is-backspace 'maybe) (and (not noninteractive) (or (memq system-type '(ms-dos windows-nt)) (eq window-system 'mac) @@ -5376,9 +5374,10 @@ See also `normal-erase-is-backspace'." (interactive "P") (set-terminal-parameter nil 'normal-erase-is-backspace - (if arg - (> (prefix-numeric-value arg) 0) - (not (terminal-parameter nil 'normal-erase-is-backspace)))) + (if (or (and arg (> (prefix-numeric-value arg) 0)) + (not (eq 1 (terminal-parameter nil 'normal-erase-is-backspace)))) + 0 + 1)) (cond ((or (memq window-system '(x w32 mac pc)) (memq system-type '(ms-dos windows-nt))) @@ -5390,7 +5389,7 @@ See also `normal-erase-is-backspace'." [C-delete] [C-backspace]))) (old-state (lookup-key local-function-key-map [delete]))) - (if (terminal-parameter nil 'normal-erase-is-backspace) + (if (eq 1 (terminal-parameter nil 'normal-erase-is-backspace)) (progn (define-key local-function-key-map [delete] [?\C-d]) (define-key local-function-key-map [kp-delete] [?\C-d]) @@ -5412,7 +5411,7 @@ See also `normal-erase-is-backspace'." (define-key map key1 binding2) (define-key map key2 binding1))))))) (t - (if (terminal-parameter nil 'normal-erase-is-backspace) + (if (eq 1 (terminal-parameter nil 'normal-erase-is-backspace)) (progn (keyboard-translate ?\C-h ?\C-?) (keyboard-translate ?\C-? ?\C-d)) @@ -5422,7 +5421,8 @@ See also `normal-erase-is-backspace'." (run-hooks 'normal-erase-is-backspace-hook) (if (interactive-p) (message "Delete key deletes %s" - (if normal-erase-is-backspace "forward" "backward")))) + (if (terminal-parameter nil 'normal-erase-is-backspace) + "forward" "backward")))) (defvar vis-mode-saved-buffer-invisibility-spec nil "Saved value of `buffer-invisibility-spec' when Visible mode is on.") diff --git a/lisp/termdev.el b/lisp/termdev.el index 667975b9b8..f413067d54 100644 --- a/lisp/termdev.el +++ b/lisp/termdev.el @@ -48,66 +48,6 @@ device (HOST.SERVER.SCREEN) or a tty device file." (t (error "Invalid argument %s in `terminal-id'" terminal)))) -(defvar terminal-parameter-alist nil - "An alist of terminal parameter alists.") - -(defun terminal-parameters (&optional terminal) - "Return the paramater-alist of terminal TERMINAL. -It is a list of elements of the form (PARM . VALUE), where PARM is a symbol. - -TERMINAL can be a terminal id, a frame, or nil (meaning the -selected frame's terminal)." - (cdr (assq (terminal-id terminal) terminal-parameter-alist))) - -(defun terminal-parameter-p (terminal parameter) - "Return non-nil if PARAMETER is a terminal parameter on TERMINAL. - -The actual value returned in that case is a cell (PARAMETER . VALUE), -where VALUE is the current value of PARAMETER. - -TERMINAL can be a terminal id, a frame, or nil (meaning the -selected frame's terminal)." - (assq parameter (cdr (assq (terminal-id terminal) terminal-parameter-alist)))) - -(defun terminal-parameter (terminal parameter) - "Return TERMINAL's value for parameter PARAMETER. - -TERMINAL can be a terminal id, a frame, or nil (meaning the -selected frame's terminal)." - (cdr (terminal-parameter-p terminal parameter))) - -(defun set-terminal-parameter (terminal parameter value) - "Set TERMINAL's value for parameter PARAMETER to VALUE. -Returns the previous value of PARAMETER. - -TERMINAL can be a terminal id, a frame, or nil (meaning the -selected frame's terminal)." - (setq terminal (terminal-id terminal)) - (let* ((alist (assq terminal terminal-parameter-alist)) - (pair (assq parameter (cdr alist))) - (result (cdr pair))) - (cond - (pair (setcdr pair value)) - (alist (setcdr alist (cons (cons parameter value) (cdr alist)))) - (t (setq terminal-parameter-alist - (cons (cons terminal - (cons (cons parameter value) - nil)) - terminal-parameter-alist)))) - result)) - -(defun terminal-handle-delete-frame (frame) - "Clean up terminal parameters of FRAME, if it's the last frame on its terminal." - ;; XXX We assume that the display is closed immediately after the - ;; last frame is deleted on it. It would be better to create a hook - ;; called `delete-display-functions', and use it instead. - (when (and (frame-live-p frame) - (= 1 (length (frames-on-display-list (frame-display frame))))) - (setq terminal-parameter-alist - (assq-delete-all (frame-display frame) terminal-parameter-alist)))) - -(add-hook 'delete-frame-functions 'terminal-handle-delete-frame) - (defun terminal-getenv (variable &optional terminal global-ok) "Get the value of VARIABLE in the client environment of TERMINAL. VARIABLE should be a string. Value is nil if VARIABLE is undefined in @@ -125,7 +65,7 @@ its value in the global environment instead. TERMINAL can be a terminal id, a frame, or nil (meaning the selected frame's terminal)." (setq terminal (terminal-id terminal)) - (if (not (terminal-parameter-p terminal 'environment)) + (if (null (terminal-parameter terminal 'environment)) (getenv variable) (if (multibyte-string-p variable) (setq variable (encode-coding-string variable locale-coding-system))) @@ -156,7 +96,7 @@ process itself. TERMINAL can be a terminal id, a frame, or nil (meaning the selected frame's terminal)." - (if (not (terminal-parameter-p terminal 'environment)) + (if (null (terminal-parameter terminal 'environment)) (setenv variable value) (with-terminal-environment terminal variable (setenv variable value)))) @@ -222,7 +162,7 @@ then the new variable values will be remembered for TERMINAL, and (if (stringp ,v) (setq ,v (list ,v))) (cond - ((not (terminal-parameter-p ,term 'environment)) + ((null (terminal-parameter ,term 'environment)) ;; Not a remote terminal; nothing to do. (progn ,@body)) ((eq ,v t) diff --git a/mac/makefile.MPW b/mac/makefile.MPW index d63ef5bcde..031a2dddb0 100644 --- a/mac/makefile.MPW +++ b/mac/makefile.MPW @@ -118,6 +118,7 @@ EmacsObjects = "{Src}sysdep.c.x" ¶ "{Src}term.c.x" ¶ "{Src}termcap.c.x" ¶ + "{Src}terminal.c.x" ¶ "{Src}textprop.c.x" ¶ "{Src}tparam.c.x" ¶ "{Src}undo.c.x" ¶ @@ -792,6 +793,16 @@ buildobj.lst "{Src}lisp.h" ¶ "{Includes}sys:file.h" +{Src}terminal.c.x Ä ¶ + {CONFIG_H_GROUP} ¶ + "{Src}lisp.h" ¶ + "{Src}frame.h" ¶ + "{Src}termchar.h" ¶ + "{Src}termhooks.h" ¶ + "{Src}charset.h" ¶ + "{Src}coding.h" ¶ + "{Src}keyboard.h" + {Src}textproc.c.x Ä ¶ {CONFIG_H_GROUP} ¶ "{Src}lisp.h" ¶ diff --git a/src/Makefile.in b/src/Makefile.in index e0ba8a25b6..f8029d5e24 100644 --- a/src/Makefile.in +++ b/src/Makefile.in @@ -577,7 +577,7 @@ emacsappsrc = ${srcdir}/../mac/Emacs.app/ whose initialized data areas should be dumped as pure by dump-emacs. */ obj= dispnew.o frame.o scroll.o xdisp.o $(XMENU_OBJ) window.o \ charset.o coding.o category.o ccl.o \ - cm.o term.o xfaces.o $(XOBJ) $(GTK_OBJ)\ + cm.o term.o terminal.o xfaces.o $(XOBJ) $(GTK_OBJ)\ emacs.o keyboard.o macros.o keymap.o sysdep.o \ buffer.o filelock.o insdel.o marker.o \ minibuf.o fileio.o dired.o filemode.o \ @@ -1171,6 +1171,8 @@ term.o: term.c termchar.h termhooks.h termopts.h $(config_h) cm.h frame.h \ disptab.h dispextern.h keyboard.h charset.h coding.h ccl.h msdos.h \ window.h keymap.h termcap.o: termcap.c $(config_h) +terminal.o: terminal.c frame.h termchar.h termhooks.h charset.h coding.h \ + keyboard.h $(config_h) terminfo.o: terminfo.c $(config_h) tparam.o: tparam.c $(config_h) undo.o: undo.c buffer.h commands.h $(config_h) @@ -1250,7 +1252,7 @@ sunfns.o: sunfns.c buffer.h window.h dispextern.h termhooks.h $(config_h) #ifdef HAVE_CARBON abbrev.o buffer.o callint.o cmds.o dispnew.o editfns.o fileio.o frame.o \ fontset.o indent.o insdel.o keyboard.o macros.o minibuf.o msdos.o process.o \ - scroll.o sysdep.o term.o widget.o window.o xdisp.o xfaces.o xfns.o xmenu.o \ + scroll.o sysdep.o term.o terminal.o widget.o window.o xdisp.o xfaces.o xfns.o xmenu.o \ xterm.o xselect.o sound.o: macgui.h mac.o: mac.c process.h sysselect.h blockinput.h atimer.h systime.h charset.h \ coding.h ccl.h $(config_h) diff --git a/src/alloc.c b/src/alloc.c index 83ba06277f..f8ba5f480a 100644 --- a/src/alloc.c +++ b/src/alloc.c @@ -324,6 +324,7 @@ Lisp_Object Vgc_elapsed; /* accumulated elapsed time in GC */ EMACS_INT gcs_done; /* accumulated GCs */ static void mark_buffer P_ ((Lisp_Object)); +extern void mark_devices P_ ((void)); extern void mark_kboards P_ ((void)); extern void mark_ttys P_ ((void)); extern void mark_backtrace P_ ((void)); @@ -4937,6 +4938,7 @@ returns nil, because real GC can't be done. */) mark_object (bind->symbol); mark_object (bind->old_value); } + mark_devices (); mark_kboards (); mark_ttys (); diff --git a/src/dispextern.h b/src/dispextern.h index f5573efdcc..b473f9cb16 100644 --- a/src/dispextern.h +++ b/src/dispextern.h @@ -2622,8 +2622,6 @@ void init_iterator_to_row_start P_ ((struct it *, struct window *, struct glyph_row *)); int get_next_display_element P_ ((struct it *)); void set_iterator_to_next P_ ((struct it *, int)); -void produce_glyphs P_ ((struct it *)); -void produce_special_glyphs P_ ((struct it *, enum display_element_type)); void start_display P_ ((struct it *, struct window *, struct text_pos)); void move_it_to P_ ((struct it *, int, int, int, int, int)); void move_it_vertically P_ ((struct it *, int)); @@ -2905,8 +2903,6 @@ void clear_glyph_row P_ ((struct glyph_row *)); void prepare_desired_row P_ ((struct glyph_row *)); int line_hash_code P_ ((struct glyph_row *)); void set_window_update_flags P_ ((struct window *, int)); -void write_glyphs P_ ((struct frame *, struct glyph *, int)); -void insert_glyphs P_ ((struct frame *, struct glyph *, int)); void redraw_frame P_ ((struct frame *)); void redraw_garbaged_frames P_ ((void)); int scroll_cost P_ ((struct frame *, int, int, int)); @@ -2924,39 +2920,48 @@ void syms_of_display P_ ((void)); extern Lisp_Object Qredisplay_dont_pause; GLYPH spec_glyph_lookup_face P_ ((struct window *, GLYPH)); -/* Defined in term.c */ +/* Defined in terminal.c */ extern void ring_bell P_ ((struct frame *)); extern void update_begin P_ ((struct frame *)); extern void update_end P_ ((struct frame *)); extern void set_terminal_window P_ ((struct frame *, int)); -extern void set_scroll_region P_ ((struct frame *, int, int)); -extern void turn_off_insert P_ ((struct tty_display_info *)); -extern void turn_off_highlight P_ ((struct tty_display_info *)); -extern void background_highlight P_ ((struct tty_display_info *)); +extern void cursor_to P_ ((struct frame *, int, int)); + +/* Was not declared before: */ +extern void raw_cursor_to P_ ((struct frame *, int, int)); +extern void clear_to_end P_ ((struct frame *)); + extern void clear_frame P_ ((struct frame *)); extern void clear_end_of_line P_ ((struct frame *, int)); -extern void clear_end_of_line_raw P_ ((struct frame *, int)); -extern void tty_clear_end_of_line P_ ((struct frame *, int)); +extern void write_glyphs P_ ((struct frame *, struct glyph *, int)); +extern void insert_glyphs P_ ((struct frame *, struct glyph *, int)); extern void delete_glyphs P_ ((struct frame *, int)); extern void ins_del_lines P_ ((struct frame *, int, int)); + +extern struct device *get_device P_ ((Lisp_Object display, int)); + +extern struct device *init_initial_device P_ ((void)); + + +/* Defined in term.c */ + +extern void tty_set_terminal_modes P_ ((struct device *)); +extern void tty_reset_terminal_modes P_ ((struct device *)); +extern void tty_turn_off_insert P_ ((struct tty_display_info *)); +extern void tty_turn_off_highlight P_ ((struct tty_display_info *)); extern int string_cost P_ ((char *)); extern int per_line_cost P_ ((char *)); extern void calculate_costs P_ ((struct frame *)); +extern void produce_glyphs P_ ((struct it *)); +extern void produce_special_glyphs P_ ((struct it *, enum display_element_type)); +extern int tty_capable_p P_ ((struct tty_display_info *, unsigned, unsigned long, unsigned long)); extern void set_tty_color_mode P_ ((struct frame *, Lisp_Object)); -extern void tty_setup_colors P_ ((struct tty_display_info *, int)); -extern struct device *get_device P_ ((Lisp_Object display, int)); extern struct device *get_tty_device P_ ((Lisp_Object terminal)); extern struct device *get_named_tty P_ ((char *)); EXFUN (Fdisplay_tty_type, 1); -extern struct device *init_initial_device P_ ((void)); -extern struct device *init_tty P_ ((char *, char *, int)); -extern void delete_tty P_ ((struct device *)); -extern void cursor_to P_ ((struct frame *, int, int)); -extern int tty_capable_p P_ ((struct tty_display_info *, unsigned, unsigned long, unsigned long)); -extern void tty_set_terminal_modes P_ ((struct device *)); -extern void tty_reset_terminal_modes P_ ((struct device *)); extern void create_tty_output P_ ((struct frame *)); +extern struct device *init_tty P_ ((char *, char *, int)); /* Defined in scroll.c */ diff --git a/src/emacs.c b/src/emacs.c index ff1a40283f..28b5f374cc 100644 --- a/src/emacs.c +++ b/src/emacs.c @@ -1600,6 +1600,7 @@ main (argc, argv syms_of_frame (); #endif syms_of_syntax (); + syms_of_terminal (); syms_of_term (); syms_of_undo (); #ifdef HAVE_SOUND diff --git a/src/frame.c b/src/frame.c index 9c83f96126..c3140628ce 100644 --- a/src/frame.c +++ b/src/frame.c @@ -638,6 +638,33 @@ make_terminal_frame (struct device *device) return f; } +/* Get a suitable value for frame parameter PARAMETER for a newly + created frame, based on (1) the user-supplied frame parameter + alist SUPPLIED_PARMS, (2) CURRENT_VALUE, and finally, if all else + fails, (3) Vdefault_frame_alist. */ + +static Lisp_Object +get_future_frame_param (Lisp_Object parameter, + Lisp_Object supplied_parms, + char *current_value) +{ + Lisp_Object result; + + result = Fassq (parameter, supplied_parms); + if (NILP (result)) + result = Fassq (parameter, XFRAME (selected_frame)->param_alist); + if (NILP (result) && current_value != NULL) + result = build_string (current_value); + if (NILP (result)) + result = Fassq (parameter, Vdefault_frame_alist); + if (!NILP (result) && !STRINGP (result)) + result = XCDR (result); + if (NILP (result) || !STRINGP (result)) + result = Qnil; + + return result; +} + DEFUN ("make-terminal-frame", Fmake_terminal_frame, Smake_terminal_frame, 1, 1, 0, doc: /* Create an additional terminal frame, possibly on another terminal. @@ -662,8 +689,6 @@ affects all frames on the same terminal device. */) struct device *d = NULL; Lisp_Object frame, tem; struct frame *sf = SELECTED_FRAME (); - Lisp_Object tty, tty_type; - struct gcpro gcpro1, gcpro2; #ifdef MSDOS if (sf->output_method != output_msdos_raw @@ -697,41 +722,24 @@ affects all frames on the same terminal device. */) if (!d) { char *name = 0, *type = 0; + Lisp_Object tty, tty_type; - tty = Fassq (Qtty, parms); - if (EQ (tty, Qnil)) - tty = Fassq (Qtty, XFRAME (selected_frame)->param_alist); - if (EQ (tty, Qnil) && FRAME_TERMCAP_P (XFRAME (selected_frame)) - && FRAME_TTY (XFRAME (selected_frame))->name) - tty = build_string (FRAME_TTY (XFRAME (selected_frame))->name); - if (EQ (tty, Qnil)) - tty = Fassq (Qtty, Vdefault_frame_alist); - if (! EQ (tty, Qnil) && ! STRINGP (tty)) - tty = XCDR (tty); - if (EQ (tty, Qnil) || !STRINGP (tty)) - tty = Qnil; - - tty_type = Fassq (Qtty_type, parms); - if (EQ (tty_type, Qnil)) - tty_type = Fassq (Qtty_type, XFRAME (selected_frame)->param_alist); - if (EQ (tty_type, Qnil) && FRAME_TERMCAP_P (XFRAME (selected_frame)) - && FRAME_TTY (XFRAME (selected_frame))->type) - tty_type = build_string (FRAME_TTY (XFRAME (selected_frame))->type); - if (EQ (tty_type, Qnil)) - tty_type = Fassq (Qtty_type, Vdefault_frame_alist); - if (! EQ (tty_type, Qnil) && ! STRINGP (tty_type)) - tty_type = XCDR (tty_type); - if (EQ (tty_type, Qnil) || !STRINGP (tty_type)) - tty_type = Qnil; - - if (! EQ (tty, Qnil)) + tty = get_future_frame_param + (Qtty, parms, (FRAME_TERMCAP_P (XFRAME (selected_frame)) + ? FRAME_TTY (XFRAME (selected_frame))->name + : NULL)); + if (!NILP (tty)) { name = (char *) alloca (SBYTES (tty) + 1); strncpy (name, SDATA (tty), SBYTES (tty)); name[SBYTES (tty)] = 0; } - if (! EQ (tty_type, Qnil)) + tty_type = get_future_frame_param + (Qtty_type, parms, (FRAME_TERMCAP_P (XFRAME (selected_frame)) + ? FRAME_TTY (XFRAME (selected_frame))->type + : NULL)); + if (!NILP (tty_type)) { type = (char *) alloca (SBYTES (tty_type) + 1); strncpy (type, SDATA (tty_type), SBYTES (tty_type)); @@ -752,13 +760,15 @@ affects all frames on the same terminal device. */) adjust_glyphs (f); calculate_costs (f); XSETFRAME (frame, f); - GCPRO2 (tty_type, tty); Fmodify_frame_parameters (frame, Vdefault_frame_alist); Fmodify_frame_parameters (frame, parms); Fmodify_frame_parameters (frame, Fcons (Fcons (Qwindow_system, Qnil), Qnil)); - Fmodify_frame_parameters (frame, Fcons (Fcons (Qtty_type, tty_type), Qnil)); - Fmodify_frame_parameters (frame, Fcons (Fcons (Qtty, tty), Qnil)); - UNGCPRO; + Fmodify_frame_parameters (frame, Fcons (Fcons (Qtty_type, + build_string (d->display_info.tty->type)), + Qnil)); + Fmodify_frame_parameters (frame, Fcons (Fcons (Qtty, + build_string (d->display_info.tty->name)), + Qnil)); /* Make the frame face alist be frame-specific, so that each frame could change its face definitions independently. */ diff --git a/src/keyboard.c b/src/keyboard.c index edce75d774..95f2daf78a 100644 --- a/src/keyboard.c +++ b/src/keyboard.c @@ -1136,7 +1136,6 @@ pop_kboard () #ifdef MULTI_KBOARD struct device *d; struct kboard_stack *p = kboard_stack; - int ok = 0; current_kboard = NULL; for (d = device_list; d; d = d->next_device) { @@ -10739,6 +10738,7 @@ See also `current-input-mode'. */) init_sys_modes (tty); #endif } + return Qnil; } DEFUN ("set-input-meta-mode", Fset_input_meta_mode, Sset_input_meta_mode, 1, 2, 0, diff --git a/src/keymap.h b/src/keymap.h index bcf14abcd8..a6598558a7 100644 --- a/src/keymap.h +++ b/src/keymap.h @@ -37,6 +37,7 @@ EXFUN (Fcurrent_active_maps, 1); extern Lisp_Object access_keymap P_ ((Lisp_Object, Lisp_Object, int, int, int)); extern Lisp_Object get_keyelt P_ ((Lisp_Object, int)); extern Lisp_Object get_keymap P_ ((Lisp_Object, int, int)); +EXFUN (Fset_keymap_parent, 2); extern void describe_map_tree P_ ((Lisp_Object, int, Lisp_Object, Lisp_Object, char *, int, int, int, int)); extern int current_minor_maps P_ ((Lisp_Object **, Lisp_Object **)); diff --git a/src/lisp.h b/src/lisp.h index a18408bd1a..4b71cd67e9 100644 --- a/src/lisp.h +++ b/src/lisp.h @@ -3184,6 +3184,9 @@ extern void syms_of_dired P_ ((void)); extern void syms_of_term P_ ((void)); extern void fatal () NO_RETURN; +/* Defined in terminal.c */ +extern void syms_of_terminal P_ ((void)); + #ifdef HAVE_X_WINDOWS /* Defined in fontset.c */ extern void syms_of_fontset P_ ((void)); diff --git a/src/sysdep.c b/src/sysdep.c index 0cf6ecb1f3..7f9d189d79 100644 --- a/src/sysdep.c +++ b/src/sysdep.c @@ -1972,7 +1972,7 @@ reset_sys_modes (tty_out) else { /* have to do it the hard way */ int i; - turn_off_insert (tty_out); + tty_turn_off_insert (tty_out); for (i = curX (tty_out); i < FrameCols (tty_out) - 1; i++) { diff --git a/src/term.c b/src/term.c index 679def93c7..b599e1b97f 100644 --- a/src/term.c +++ b/src/term.c @@ -80,14 +80,14 @@ extern int tgetnum P_ ((char *id)); #define O_NOCTTY 0 #endif +static void tty_set_scroll_region P_ ((struct frame *f, int start, int stop)); static void turn_on_face P_ ((struct frame *, int face_id)); static void turn_off_face P_ ((struct frame *, int face_id)); static void tty_show_cursor P_ ((struct tty_display_info *)); static void tty_hide_cursor P_ ((struct tty_display_info *)); - -void delete_initial_device P_ ((struct device *)); -void create_tty_output P_ ((struct frame *)); -void delete_tty_output P_ ((struct frame *)); +static void tty_background_highlight P_ ((struct tty_display_info *tty)); +static void dissociate_if_controlling_tty P_ ((int fd)); +static void delete_tty P_ ((struct device *)); #define OUTPUT(tty, a) \ emacs_tputs ((tty), a, \ @@ -113,22 +113,12 @@ void delete_tty_output P_ ((struct frame *)); extern Lisp_Object Qspace, QCalign_to, QCwidth; -/* Function to use to ring the bell. */ - -Lisp_Object Vring_bell_function; - /* Functions to call after suspending a tty. */ Lisp_Object Vsuspend_tty_functions; /* Functions to call after resuming a tty. */ Lisp_Object Vresume_tty_functions; -/* Chain of all displays currently in use. */ -struct device *device_list; - -/* The initial display device, created by initial_term_init. */ -struct device *initial_device; - /* Chain of all tty device parameters. */ struct tty_display_info *tty_list; @@ -138,7 +128,6 @@ struct tty_display_info *tty_list; else. */ int no_redraw_on_reenter; - /* Meaning of bits in no_color_video. Each bit set means that the corresponding attribute cannot be combined with colors. */ @@ -169,9 +158,6 @@ int max_frame_lines; should not open a frame on stdout. */ static int no_controlling_tty; -/* The first unallocated display id. */ -static int next_device_id; - /* Provided for lisp packages. */ static int system_uses_terminfo; @@ -192,35 +178,10 @@ extern char *tgetstr (); #define FRAME_TERMCAP_P(_f_) 0 #endif /* WINDOWSNT */ -void -ring_bell (struct frame *f) -{ - if (!NILP (Vring_bell_function)) - { - Lisp_Object function; - - /* Temporarily set the global variable to nil - so that if we get an error, it stays nil - and we don't call it over and over. - - We don't specbind it, because that would carefully - restore the bad value if there's an error - and make the loop of errors happen anyway. */ - - function = Vring_bell_function; - Vring_bell_function = Qnil; - - call0 (function); - - Vring_bell_function = function; - } - else if (FRAME_DEVICE (f)->ring_bell_hook) - (*FRAME_DEVICE (f)->ring_bell_hook) (f); -} /* Ring the bell on a tty. */ -void +static void tty_ring_bell (struct frame *f) { struct tty_display_info *tty = FRAME_TTY (f); @@ -272,8 +233,8 @@ tty_reset_terminal_modes (struct device *display) if (tty->output) { - turn_off_highlight (tty); - turn_off_insert (tty); + tty_turn_off_highlight (tty); + tty_turn_off_insert (tty); OUTPUT_IF (tty, tty->TS_end_keypad_mode); OUTPUT_IF (tty, tty->TS_cursor_normal); OUTPUT_IF (tty, tty->TS_end_termcap_modes); @@ -285,59 +246,33 @@ tty_reset_terminal_modes (struct device *display) } } -void -update_begin (struct frame *f) -{ - if (FRAME_DEVICE (f)->update_begin_hook) - (*FRAME_DEVICE (f)->update_begin_hook) (f); -} - -void -update_end (struct frame *f) -{ - if (FRAME_DEVICE (f)->update_end_hook) - (*FRAME_DEVICE (f)->update_end_hook) (f); -} - /* Flag the end of a display update on a termcap display. */ -void +static void tty_update_end (struct frame *f) { struct tty_display_info *tty = FRAME_TTY (f); if (!XWINDOW (selected_window)->cursor_off_p) tty_show_cursor (tty); - turn_off_insert (tty); - background_highlight (tty); -} - -/* Specify how many text lines, from the top of the window, - should be affected by insert-lines and delete-lines operations. - This, and those operations, are used only within an update - that is bounded by calls to update_begin and update_end. */ - -void -set_terminal_window (struct frame *f, int size) -{ - if (FRAME_DEVICE (f)->set_terminal_window_hook) - (*FRAME_DEVICE (f)->set_terminal_window_hook) (f, size); + tty_turn_off_insert (tty); + tty_background_highlight (tty); } /* The implementation of set_terminal_window for termcap frames. */ -void +static void tty_set_terminal_window (struct frame *f, int size) { struct tty_display_info *tty = FRAME_TTY (f); tty->specified_window = size ? size : FRAME_LINES (f); if (FRAME_SCROLL_REGION_OK (f)) - set_scroll_region (f, 0, tty->specified_window); + tty_set_scroll_region (f, 0, tty->specified_window); } -void -set_scroll_region (struct frame *f, int start, int stop) +static void +tty_set_scroll_region (struct frame *f, int start, int stop) { char *buf; struct tty_display_info *tty = FRAME_TTY (f); @@ -359,7 +294,7 @@ set_scroll_region (struct frame *f, int start, int stop) static void -turn_on_insert (struct tty_display_info *tty) +tty_turn_on_insert (struct tty_display_info *tty) { if (!tty->insert_mode) OUTPUT (tty, tty->TS_insert_mode); @@ -367,7 +302,7 @@ turn_on_insert (struct tty_display_info *tty) } void -turn_off_insert (struct tty_display_info *tty) +tty_turn_off_insert (struct tty_display_info *tty) { if (tty->insert_mode) OUTPUT (tty, tty->TS_end_insert_mode); @@ -377,7 +312,7 @@ turn_off_insert (struct tty_display_info *tty) /* Handle highlighting. */ void -turn_off_highlight (struct tty_display_info *tty) +tty_turn_off_highlight (struct tty_display_info *tty) { if (tty->standout_mode) OUTPUT_IF (tty, tty->TS_end_standout_mode); @@ -385,7 +320,7 @@ turn_off_highlight (struct tty_display_info *tty) } static void -turn_on_highlight (struct tty_display_info *tty) +tty_turn_on_highlight (struct tty_display_info *tty) { if (!tty->standout_mode) OUTPUT_IF (tty, tty->TS_standout_mode); @@ -393,12 +328,12 @@ turn_on_highlight (struct tty_display_info *tty) } static void -toggle_highlight (struct tty_display_info *tty) +tty_toggle_highlight (struct tty_display_info *tty) { if (tty->standout_mode) - turn_off_highlight (tty); + tty_turn_off_highlight (tty); else - turn_on_highlight (tty); + tty_turn_on_highlight (tty); } @@ -433,38 +368,31 @@ tty_show_cursor (struct tty_display_info *tty) empty space inside windows. What this is, depends on the user option inverse-video. */ -void -background_highlight (struct tty_display_info *tty) +static void +tty_background_highlight (struct tty_display_info *tty) { if (inverse_video) - turn_on_highlight (tty); + tty_turn_on_highlight (tty); else - turn_off_highlight (tty); + tty_turn_off_highlight (tty); } /* Set standout mode to the mode specified for the text to be output. */ static void -highlight_if_desired (struct tty_display_info *tty) +tty_highlight_if_desired (struct tty_display_info *tty) { if (inverse_video) - turn_on_highlight (tty); + tty_turn_on_highlight (tty); else - turn_off_highlight (tty); + tty_turn_off_highlight (tty); } /* Move cursor to row/column position VPOS/HPOS. HPOS/VPOS are frame-relative coordinates. */ -void -cursor_to (struct frame *f, int vpos, int hpos) -{ - if (FRAME_DEVICE (f)->cursor_to_hook) - (*FRAME_DEVICE (f)->cursor_to_hook) (f, vpos, hpos); -} - -void +static void tty_cursor_to (struct frame *f, int vpos, int hpos) { struct tty_display_info *tty = FRAME_TTY (f); @@ -478,22 +406,15 @@ tty_cursor_to (struct frame *f, int vpos, int hpos) && curX (tty) == hpos) return; if (!tty->TF_standout_motion) - background_highlight (tty); + tty_background_highlight (tty); if (!tty->TF_insmode_motion) - turn_off_insert (tty); + tty_turn_off_insert (tty); cmgoto (tty, vpos, hpos); } /* Similar but don't take any account of the wasted characters. */ -void -raw_cursor_to (struct frame *f, int row, int col) -{ - if (FRAME_DEVICE (f)->raw_cursor_to_hook) - (*FRAME_DEVICE (f)->raw_cursor_to_hook) (f, row, col); -} - -void +static void tty_raw_cursor_to (struct frame *f, int row, int col) { struct tty_display_info *tty = FRAME_TTY (f); @@ -502,25 +423,17 @@ tty_raw_cursor_to (struct frame *f, int row, int col) && curX (tty) == col) return; if (!tty->TF_standout_motion) - background_highlight (tty); + tty_background_highlight (tty); if (!tty->TF_insmode_motion) - turn_off_insert (tty); + tty_turn_off_insert (tty); cmgoto (tty, row, col); } /* Erase operations */ -/* Clear from cursor to end of frame. */ -void -clear_to_end (struct frame *f) -{ - if (FRAME_DEVICE (f)->clear_to_end_hook) - (*FRAME_DEVICE (f)->clear_to_end_hook) (f); -} - /* Clear from cursor to end of frame on a termcap device. */ -void +static void tty_clear_to_end (struct frame *f) { register int i; @@ -528,7 +441,7 @@ tty_clear_to_end (struct frame *f) if (tty->TS_clr_to_bottom) { - background_highlight (tty); + tty_background_highlight (tty); OUTPUT (tty, tty->TS_clr_to_bottom); } else @@ -541,25 +454,16 @@ tty_clear_to_end (struct frame *f) } } -/* Clear entire frame */ - -void -clear_frame (struct frame *f) -{ - if (FRAME_DEVICE (f)->clear_frame_hook) - (*FRAME_DEVICE (f)->clear_frame_hook) (f); -} - /* Clear an entire termcap frame. */ -void +static void tty_clear_frame (struct frame *f) { struct tty_display_info *tty = FRAME_TTY (f); if (tty->TS_clr_frame) { - background_highlight (tty); + tty_background_highlight (tty); OUTPUT (tty, tty->TS_clr_frame); cmat (tty, 0, 0); } @@ -570,23 +474,11 @@ tty_clear_frame (struct frame *f) } } -/* Clear from cursor to end of line. - Assume that the line is already clear starting at column first_unused_hpos. - - Note that the cursor may be moved, on terminals lacking a `ce' string. */ - -void -clear_end_of_line (struct frame *f, int first_unused_hpos) -{ - if (FRAME_DEVICE (f)->clear_end_of_line_hook) - (*FRAME_DEVICE (f)->clear_end_of_line_hook) (f, first_unused_hpos); -} - /* An implementation of clear_end_of_line for termcap frames. Note that the cursor may be moved, on terminals lacking a `ce' string. */ -void +static void tty_clear_end_of_line (struct frame *f, int first_unused_hpos) { register int i; @@ -599,14 +491,14 @@ tty_clear_end_of_line (struct frame *f, int first_unused_hpos) if (curX (tty) >= first_unused_hpos) return; - background_highlight (tty); + tty_background_highlight (tty); if (tty->TS_clr_line) { OUTPUT1 (tty, tty->TS_clr_line); } else { /* have to do it the hard way */ - turn_off_insert (tty); + tty_turn_off_insert (tty); /* Do not write in last row last col with Auto-wrap on. */ if (AutoWrap (tty) @@ -743,19 +635,9 @@ encode_terminal_code (src, src_len, coding) } -/* Output LEN glyphs starting at STRING at the nominal cursor position. - Advance the nominal cursor over the text. */ - -void -write_glyphs (struct frame *f, struct glyph *string, int len) -{ - if (FRAME_DEVICE (f)->write_glyphs_hook) - (*FRAME_DEVICE (f)->write_glyphs_hook) (f, string, len); -} - /* An implementation of write_glyphs for termcap frames. */ -void +static void tty_write_glyphs (struct frame *f, struct glyph *string, int len) { unsigned char *conversion_buffer; @@ -763,7 +645,7 @@ tty_write_glyphs (struct frame *f, struct glyph *string, int len) struct tty_display_info *tty = FRAME_TTY (f); - turn_off_insert (tty); + tty_turn_off_insert (tty); tty_hide_cursor (tty); /* Don't dare write in last column of bottom line, if Auto-Wrap, @@ -798,7 +680,7 @@ tty_write_glyphs (struct frame *f, struct glyph *string, int len) break; /* Turn appearance modes of the face of the run on. */ - highlight_if_desired (tty); + tty_highlight_if_desired (tty); turn_on_face (f, face_id); if (n == len) @@ -818,29 +700,15 @@ tty_write_glyphs (struct frame *f, struct glyph *string, int len) /* Turn appearance modes off. */ turn_off_face (f, face_id); - turn_off_highlight (tty); + tty_turn_off_highlight (tty); } cmcheckmagic (tty); } -/* Insert LEN glyphs from START at the nominal cursor position. - - If start is zero, insert blanks instead of a string at start */ - -void -insert_glyphs (struct frame *f, struct glyph *start, int len) -{ - if (len <= 0) - return; - - if (FRAME_DEVICE (f)->insert_glyphs_hook) - (*FRAME_DEVICE (f)->insert_glyphs_hook) (f, start, len); -} - /* An implementation of insert_glyphs for termcap frames. */ -void +static void tty_insert_glyphs (struct frame *f, struct glyph *start, int len) { char *buf; @@ -861,7 +729,7 @@ tty_insert_glyphs (struct frame *f, struct glyph *start, int len) return; } - turn_on_insert (tty); + tty_turn_on_insert (tty); cmplus (tty, len); if (! start) @@ -886,7 +754,7 @@ tty_insert_glyphs (struct frame *f, struct glyph *start, int len) } else { - highlight_if_desired (tty); + tty_highlight_if_desired (tty); turn_on_face (f, start->face_id); glyph = start; ++start; @@ -918,25 +786,16 @@ tty_insert_glyphs (struct frame *f, struct glyph *start, int len) if (start) { turn_off_face (f, glyph->face_id); - turn_off_highlight (tty); + tty_turn_off_highlight (tty); } } cmcheckmagic (tty); } -/* Delete N glyphs at the nominal cursor position. */ - -void -delete_glyphs (struct frame *f, int n) -{ - if (FRAME_DEVICE (f)->delete_glyphs_hook) - (*FRAME_DEVICE (f)->delete_glyphs_hook) (f, n); -} - /* An implementation of delete_glyphs for termcap frames. */ -void +static void tty_delete_glyphs (struct frame *f, int n) { char *buf; @@ -946,11 +805,11 @@ tty_delete_glyphs (struct frame *f, int n) if (tty->delete_in_insert_mode) { - turn_on_insert (tty); + tty_turn_on_insert (tty); } else { - turn_off_insert (tty); + tty_turn_off_insert (tty); OUTPUT_IF (tty, tty->TS_delete_mode); } @@ -967,18 +826,9 @@ tty_delete_glyphs (struct frame *f, int n) OUTPUT_IF (tty, tty->TS_end_delete_mode); } -/* Insert N lines at vpos VPOS. If N is negative, delete -N lines. */ - -void -ins_del_lines (struct frame *f, int vpos, int n) -{ - if (FRAME_DEVICE (f)->ins_del_lines_hook) - (*FRAME_DEVICE (f)->ins_del_lines_hook) (f, vpos, n); -} - /* An implementation of ins_del_lines for termcap frames. */ -void +static void tty_ins_del_lines (struct frame *f, int vpos, int n) { struct tty_display_info *tty = FRAME_TTY (f); @@ -1006,7 +856,7 @@ tty_ins_del_lines (struct frame *f, int vpos, int n) if (multi) { raw_cursor_to (f, vpos, 0); - background_highlight (tty); + tty_background_highlight (tty); buf = tparam (multi, 0, 0, i); OUTPUT (tty, buf); xfree (buf); @@ -1014,7 +864,7 @@ tty_ins_del_lines (struct frame *f, int vpos, int n) else if (single) { raw_cursor_to (f, vpos, 0); - background_highlight (tty); + tty_background_highlight (tty); while (--i >= 0) OUTPUT (tty, single); if (tty->TF_teleray) @@ -1022,15 +872,15 @@ tty_ins_del_lines (struct frame *f, int vpos, int n) } else { - set_scroll_region (f, vpos, tty->specified_window); + tty_set_scroll_region (f, vpos, tty->specified_window); if (n < 0) raw_cursor_to (f, tty->specified_window - 1, 0); else raw_cursor_to (f, vpos, 0); - background_highlight (tty); + tty_background_highlight (tty); while (--i >= 0) OUTPUTL (tty, scroll, tty->specified_window - vpos); - set_scroll_region (f, 0, tty->specified_window); + tty_set_scroll_region (f, 0, tty->specified_window); } if (!FRAME_SCROLL_REGION_OK (f) @@ -1331,7 +1181,7 @@ static Lisp_Object term_get_fkeys_1 (); This function scans the termcap function key sequence entries, and adds entries to Vfunction_key_map for each function key it finds. */ -void +static void term_get_fkeys (address, kboard) char **address; KBOARD *kboard; @@ -1805,13 +1655,13 @@ turn_on_face (f, face_id) { if (fg == FACE_TTY_DEFAULT_FG_COLOR || bg == FACE_TTY_DEFAULT_BG_COLOR) - toggle_highlight (tty); + tty_toggle_highlight (tty); } else { if (fg == FACE_TTY_DEFAULT_BG_COLOR || bg == FACE_TTY_DEFAULT_FG_COLOR) - toggle_highlight (tty); + tty_toggle_highlight (tty); } } else @@ -1822,13 +1672,13 @@ turn_on_face (f, face_id) { if (fg == FACE_TTY_DEFAULT_FG_COLOR || bg == FACE_TTY_DEFAULT_BG_COLOR) - toggle_highlight (tty); + tty_toggle_highlight (tty); } else { if (fg == FACE_TTY_DEFAULT_BG_COLOR || bg == FACE_TTY_DEFAULT_FG_COLOR) - toggle_highlight (tty); + tty_toggle_highlight (tty); } } } @@ -2031,7 +1881,7 @@ tty_default_color_capabilities (struct tty_display_info *tty, int save) MODE's value is generally the number of colors which we want to support; zero means set up for the default capabilities, the ones we saw at init_tty time; -1 means turn off color support. */ -void +static void tty_setup_colors (struct tty_display_info *tty, int mode) { /* Canonicalize all negative values of MODE. */ @@ -2124,43 +1974,6 @@ set_tty_color_mode (f, val) -/* Return the display object specified by DEVICE. DEVICE may be a - display id, a frame, or nil for the display device of the current - frame. If THROW is zero, return NULL for failure, otherwise throw - an error. */ - -struct device * -get_device (Lisp_Object device, int throw) -{ - struct device *result = NULL; - - if (NILP (device)) - device = selected_frame; - - if (INTEGERP (device)) - { - struct device *d; - - for (d = device_list; d; d = d->next_device) - { - if (d->id == XINT (device)) - { - result = d; - break; - } - } - } - else if (FRAMEP (device)) - { - result = FRAME_DEVICE (XFRAME (device)); - } - - if (result == NULL && throw) - wrong_type_argument (Qdisplay_live_p, device); - - return result; -} - /* Return the tty display object specified by DEVICE. */ struct device * @@ -2204,24 +2017,6 @@ get_named_tty (name) } - -DEFUN ("display-name", Fdisplay_name, Sdisplay_name, 0, 1, 0, - doc: /* Return the name of the display device DEVICE. -It is not guaranteed that the returned value is unique among opened devices. - -DEVICE may be a display device id, a frame, or nil (meaning the -selected frame's display device). */) - (device) - Lisp_Object device; -{ - struct device *d = get_device (device, 1); - - if (d->name) - return build_string (d->name); - else - return Qnil; -} - DEFUN ("display-tty-type", Fdisplay_tty_type, Sdisplay_tty_type, 0, 1, 0, doc: /* Return the type of the tty device that DEVICE uses. @@ -2275,47 +2070,166 @@ selected frame's display device). */) return Qnil; } + + +DEFUN ("suspend-tty", Fsuspend_tty, Ssuspend_tty, 0, 1, 0, + doc: /* Suspend the terminal device TTY. + +The device is restored to its default state, and Emacs ceases all +access to the tty device. Frames that use the device are not deleted, +but input is not read from them and if they change, their display is +not updated. + +TTY may be a terminal id, a frame, or nil for the terminal device of +the currently selected frame. + +This function runs `suspend-tty-functions' after suspending the +device. The functions are run with one arg, the id of the suspended +terminal device. + +`suspend-tty' does nothing if it is called on a device that is already +suspended. + +A suspended tty may be resumed by calling `resume-tty' on it. */) + (tty) + Lisp_Object tty; +{ + struct device *d = get_tty_device (tty); + FILE *f; + + if (!d) + error ("Unknown tty device"); + + f = d->display_info.tty->input; + + if (f) + { + reset_sys_modes (d->display_info.tty); + + delete_keyboard_wait_descriptor (fileno (f)); + + fclose (f); + if (f != d->display_info.tty->output) + fclose (d->display_info.tty->output); + + d->display_info.tty->input = 0; + d->display_info.tty->output = 0; + + if (FRAMEP (d->display_info.tty->top_frame)) + FRAME_SET_VISIBLE (XFRAME (d->display_info.tty->top_frame), 0); + + /* Run `suspend-tty-functions'. */ + if (!NILP (Vrun_hooks)) + { + Lisp_Object args[2]; + args[0] = intern ("suspend-tty-functions"); + args[1] = make_number (d->id); + Frun_hook_with_args (2, args); + } + } + + return Qnil; +} + +DEFUN ("resume-tty", Fresume_tty, Sresume_tty, 0, 1, 0, + doc: /* Resume the previously suspended terminal device TTY. +The terminal is opened and reinitialized. Frames that are on the +suspended display are revived. + +It is an error to resume a display while another display is active on +the same device. + +This function runs `resume-tty-functions' after resuming the device. +The functions are run with one arg, the id of the resumed display +device. + +`resume-tty' does nothing if it is called on a device that is not +suspended. + +TTY may be a display device id, a frame, or nil for the display device +of the currently selected frame. */) + (tty) + Lisp_Object tty; +{ + struct device *d = get_tty_device (tty); + int fd; + + if (!d) + error ("Unknown tty device"); + + if (!d->display_info.tty->input) + { + if (get_named_tty (d->display_info.tty->name)) + error ("Cannot resume display while another display is active on the same device"); + + fd = emacs_open (d->display_info.tty->name, O_RDWR | O_NOCTTY, 0); + + /* XXX What if open fails? */ + + dissociate_if_controlling_tty (fd); + + d->display_info.tty->output = fdopen (fd, "w+"); + d->display_info.tty->input = d->display_info.tty->output; + + add_keyboard_wait_descriptor (fd); + + if (FRAMEP (d->display_info.tty->top_frame)) + FRAME_SET_VISIBLE (XFRAME (d->display_info.tty->top_frame), 1); + + init_sys_modes (d->display_info.tty); + + /* Run `suspend-tty-functions'. */ + if (!NILP (Vrun_hooks)) + { + Lisp_Object args[2]; + args[0] = intern ("resume-tty-functions"); + args[1] = make_number (d->id); + Frun_hook_with_args (2, args); + } + } + + return Qnil; +} /*********************************************************************** Initialization ***********************************************************************/ -/* Create the bootstrap display device for the initial frame. - Returns a device of type output_initial. */ +/* Initialize the tty-dependent part of frame F. The frame must + already have its device initialized. */ -struct device * -init_initial_device (void) +void +create_tty_output (struct frame *f) { - if (initialized || device_list || tty_list) + struct tty_output *t; + + if (! FRAME_TERMCAP_P (f)) abort (); - initial_device = create_device (); - initial_device->type = output_initial; - initial_device->name = xstrdup ("initial_device"); - initial_device->kboard = initial_kboard; + t = xmalloc (sizeof (struct tty_output)); + bzero (t, sizeof (struct tty_output)); - initial_device->delete_device_hook = &delete_initial_device; - /* All other hooks are NULL. */ + t->display_info = FRAME_DEVICE (f)->display_info.tty; - return initial_device; + f->output_data.tty = t; } -/* Deletes the bootstrap display device. - Called through delete_device_hook. */ +/* Delete the tty-dependent part of frame F. */ -void -delete_initial_device (struct device *device) +static void +delete_tty_output (struct frame *f) { - if (device != initial_device) + if (! FRAME_TERMCAP_P (f)) abort (); - delete_device (device); - initial_device = NULL; + xfree (f->output_data.tty); } + + /* Drop the controlling terminal if fd is the same device. */ -void +static void dissociate_if_controlling_tty (int fd) { int pgid; @@ -2974,7 +2888,7 @@ static int deleting_tty = 0; /* Delete the given terminal device, closing all frames on it. */ -void +static void delete_tty (struct device *device) { struct tty_display_info *tty; @@ -3066,44 +2980,11 @@ delete_tty (struct device *device) -/* Initialize the tty-dependent part of frame F. The frame must - already have its device initialized. */ - -void -create_tty_output (struct frame *f) -{ - struct tty_output *t; - - if (! FRAME_TERMCAP_P (f)) - abort (); - - t = xmalloc (sizeof (struct tty_output)); - bzero (t, sizeof (struct tty_output)); - - t->display_info = FRAME_DEVICE (f)->display_info.tty; - - f->output_data.tty = t; -} - -/* Delete the tty-dependent part of frame F. */ - -void -delete_tty_output (struct frame *f) -{ - if (! FRAME_TERMCAP_P (f)) - abort (); - - xfree (f->output_data.tty); -} - - - - /* Mark the pointers in the tty_display_info objects. Called by the Fgarbage_collector. */ void -mark_ttys () +mark_ttys (void) { struct tty_display_info *tty; @@ -3116,279 +2997,6 @@ mark_ttys () -/* Create a new device object and add it to the device list. */ - -struct device * -create_device (void) -{ - struct device *device = (struct device *) xmalloc (sizeof (struct device)); - - bzero (device, sizeof (struct device)); - device->next_device = device_list; - device_list = device; - - device->id = next_device_id++; - - device->keyboard_coding = - (struct coding_system *) xmalloc (sizeof (struct coding_system)); - device->terminal_coding = - (struct coding_system *) xmalloc (sizeof (struct coding_system)); - - setup_coding_system (Qnil, device->keyboard_coding); - setup_coding_system (Qnil, device->terminal_coding); - - return device; -} - -/* Remove a device from the device list and free its memory. */ - -void -delete_device (struct device *device) -{ - struct device **dp; - Lisp_Object tail, frame; - - /* Check for and close live frames that are still on this - device. */ - FOR_EACH_FRAME (tail, frame) - { - struct frame *f = XFRAME (frame); - if (FRAME_LIVE_P (f) && f->device == device) - { - Fdelete_frame (frame, Qt); - } - } - - for (dp = &device_list; *dp != device; dp = &(*dp)->next_device) - if (! *dp) - abort (); - *dp = device->next_device; - - if (device->keyboard_coding) - xfree (device->keyboard_coding); - if (device->terminal_coding) - xfree (device->terminal_coding); - if (device->name) - xfree (device->name); - -#ifdef MULTI_KBOARD - if (device->kboard && --device->kboard->reference_count == 0) - delete_kboard (device->kboard); -#endif - - bzero (device, sizeof (struct device)); - xfree (device); -} - -DEFUN ("delete-display", Fdelete_display, Sdelete_display, 0, 2, 0, - doc: /* Delete DEVICE by deleting all frames on it and closing the device. -DEVICE may be a display device id, a frame, or nil (meaning the -selected frame's display device). - -Normally, you may not delete a display if all other displays are suspended, -but if the second argument FORCE is non-nil, you may do so. */) - (device, force) - Lisp_Object device, force; -{ - struct device *d, *p; - - d = get_device (device, 0); - - if (!d) - return Qnil; - - p = device_list; - while (p && (p == d || !DEVICE_ACTIVE_P (p))) - p = p->next_device; - - if (NILP (force) && !p) - error ("Attempt to delete the sole active display device"); - - if (d->delete_device_hook) - (*d->delete_device_hook) (d); - else - delete_device (d); - - return Qnil; -} - -DEFUN ("display-live-p", Fdisplay_live_p, Sdisplay_live_p, 1, 1, 0, - doc: /* Return non-nil if OBJECT is a device which has not been deleted. -Value is nil if OBJECT is not a live display device. -If object is a live display device, the return value indicates what -sort of output device it uses. See the documentation of `framep' for -possible return values. - -Display devices are represented by their integer identifiers. */) - (object) - Lisp_Object object; -{ - struct device *d; - - if (!INTEGERP (object)) - return Qnil; - - d = get_device (object, 0); - - if (!d) - return Qnil; - - switch (d->type) - { - case output_initial: /* The initial frame is like a termcap frame. */ - case output_termcap: - return Qt; - case output_x_window: - return Qx; - case output_w32: - return Qw32; - case output_msdos_raw: - return Qpc; - case output_mac: - return Qmac; - default: - abort (); - } -} - -DEFUN ("display-list", Fdisplay_list, Sdisplay_list, 0, 0, 0, - doc: /* Return a list of all display devices. -Display devices are represented by their integer identifiers. */) - () -{ - Lisp_Object devices = Qnil; - struct device *d; - - for (d = device_list; d; d = d->next_device) - devices = Fcons (make_number (d->id), devices); - - return devices; -} - - - - -DEFUN ("suspend-tty", Fsuspend_tty, Ssuspend_tty, 0, 1, 0, - doc: /* Suspend the terminal device TTY. - -The device is restored to its default state, and Emacs ceases all -access to the tty device. Frames that use the device are not deleted, -but input is not read from them and if they change, their display is -not updated. - -TTY may be a terminal id, a frame, or nil for the terminal device of -the currently selected frame. - -This function runs `suspend-tty-functions' after suspending the -device. The functions are run with one arg, the id of the suspended -terminal device. - -`suspend-tty' does nothing if it is called on a device that is already -suspended. - -A suspended tty may be resumed by calling `resume-tty' on it. */) - (tty) - Lisp_Object tty; -{ - struct device *d = get_tty_device (tty); - FILE *f; - - if (!d) - error ("Unknown tty device"); - - f = d->display_info.tty->input; - - if (f) - { - reset_sys_modes (d->display_info.tty); - - delete_keyboard_wait_descriptor (fileno (f)); - - fclose (f); - if (f != d->display_info.tty->output) - fclose (d->display_info.tty->output); - - d->display_info.tty->input = 0; - d->display_info.tty->output = 0; - - if (FRAMEP (d->display_info.tty->top_frame)) - FRAME_SET_VISIBLE (XFRAME (d->display_info.tty->top_frame), 0); - - /* Run `suspend-tty-functions'. */ - if (!NILP (Vrun_hooks)) - { - Lisp_Object args[2]; - args[0] = intern ("suspend-tty-functions"); - args[1] = make_number (d->id); - Frun_hook_with_args (2, args); - } - } - - return Qnil; -} - - -DEFUN ("resume-tty", Fresume_tty, Sresume_tty, 0, 1, 0, - doc: /* Resume the previously suspended terminal device TTY. -The terminal is opened and reinitialized. Frames that are on the -suspended display are revived. - -It is an error to resume a display while another display is active on -the same device. - -This function runs `resume-tty-functions' after resuming the device. -The functions are run with one arg, the id of the resumed display -device. - -`resume-tty' does nothing if it is called on a device that is not -suspended. - -TTY may be a display device id, a frame, or nil for the display device -of the currently selected frame. */) - (tty) - Lisp_Object tty; -{ - struct device *d = get_tty_device (tty); - int fd; - - if (!d) - error ("Unknown tty device"); - - if (!d->display_info.tty->input) - { - if (get_named_tty (d->display_info.tty->name)) - error ("Cannot resume display while another display is active on the same device"); - - fd = emacs_open (d->display_info.tty->name, O_RDWR | O_NOCTTY, 0); - - /* XXX What if open fails? */ - - dissociate_if_controlling_tty (fd); - - d->display_info.tty->output = fdopen (fd, "w+"); - d->display_info.tty->input = d->display_info.tty->output; - - add_keyboard_wait_descriptor (fd); - - if (FRAMEP (d->display_info.tty->top_frame)) - FRAME_SET_VISIBLE (XFRAME (d->display_info.tty->top_frame), 1); - - init_sys_modes (d->display_info.tty); - - /* Run `suspend-tty-functions'. */ - if (!NILP (Vrun_hooks)) - { - Lisp_Object args[2]; - args[0] = intern ("resume-tty-functions"); - args[1] = make_number (d->id); - Frun_hook_with_args (2, args); - } - } - - return Qnil; -} - - void syms_of_term () { @@ -3401,11 +3009,6 @@ This variable can be used by terminal emulator packages. */); system_uses_terminfo = 0; #endif - DEFVAR_LISP ("ring-bell-function", &Vring_bell_function, - doc: /* Non-nil means call this function to ring the bell. -The function should accept no arguments. */); - Vring_bell_function = Qnil; - DEFVAR_LISP ("suspend-tty-functions", &Vsuspend_tty_functions, doc: /* Functions to be run after suspending a tty. The functions are run with one argument, the name of the tty to be suspended. @@ -3422,17 +3025,10 @@ See `resume-tty'. */); defsubr (&Stty_display_color_p); defsubr (&Stty_display_color_cells); defsubr (&Stty_no_underline); - defsubr (&Sdisplay_name); defsubr (&Sdisplay_tty_type); defsubr (&Sdisplay_controlling_tty_p); - defsubr (&Sdelete_display); - defsubr (&Sdisplay_live_p); - defsubr (&Sdisplay_list); defsubr (&Ssuspend_tty); defsubr (&Sresume_tty); - - Fprovide (intern ("multi-tty"), Qnil); - } diff --git a/src/termhooks.h b/src/termhooks.h index cb68c9e2c2..824cef6035 100644 --- a/src/termhooks.h +++ b/src/termhooks.h @@ -330,6 +330,9 @@ struct device the function `set-keyboard-coding-system'. */ struct coding_system *keyboard_coding; + /* Parameter alist of this terminal. */ + Lisp_Object param_alist; + /* Terminal characteristics. */ /* XXX Are these really used on non-termcap displays? */ diff --git a/src/terminal.c b/src/terminal.c new file mode 100644 index 0000000000..83879a43af --- /dev/null +++ b/src/terminal.c @@ -0,0 +1,596 @@ +/* Functions related to terminal devices. + Copyright (C) 2005 Free Software Foundation, Inc. + +This file is part of GNU Emacs. + +GNU Emacs is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2, or (at your option) +any later version. + +GNU Emacs is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with GNU Emacs; see the file COPYING. If not, write to +the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, +Boston, MA 02110-1301, USA. */ + +#include + +#include "lisp.h" +#include "frame.h" +#include "termchar.h" +#include "termhooks.h" +#include "charset.h" +#include "coding.h" +#include "keyboard.h" + +/* Chain of all displays currently in use. */ +struct device *device_list; + +/* The first unallocated display id. */ +static int next_device_id; + +/* The initial display device, created by initial_term_init. */ +struct device *initial_device; + +/* Function to use to ring the bell. */ +Lisp_Object Vring_bell_function; + +void delete_initial_device P_ ((struct device *)); + + + +void +ring_bell (struct frame *f) +{ + if (!NILP (Vring_bell_function)) + { + Lisp_Object function; + + /* Temporarily set the global variable to nil + so that if we get an error, it stays nil + and we don't call it over and over. + + We don't specbind it, because that would carefully + restore the bad value if there's an error + and make the loop of errors happen anyway. */ + + function = Vring_bell_function; + Vring_bell_function = Qnil; + + call0 (function); + + Vring_bell_function = function; + } + else if (FRAME_DEVICE (f)->ring_bell_hook) + (*FRAME_DEVICE (f)->ring_bell_hook) (f); +} + +void +update_begin (struct frame *f) +{ + if (FRAME_DEVICE (f)->update_begin_hook) + (*FRAME_DEVICE (f)->update_begin_hook) (f); +} + +void +update_end (struct frame *f) +{ + if (FRAME_DEVICE (f)->update_end_hook) + (*FRAME_DEVICE (f)->update_end_hook) (f); +} + +/* Specify how many text lines, from the top of the window, + should be affected by insert-lines and delete-lines operations. + This, and those operations, are used only within an update + that is bounded by calls to update_begin and update_end. */ + +void +set_terminal_window (struct frame *f, int size) +{ + if (FRAME_DEVICE (f)->set_terminal_window_hook) + (*FRAME_DEVICE (f)->set_terminal_window_hook) (f, size); +} + +/* Move cursor to row/column position VPOS/HPOS. HPOS/VPOS are + frame-relative coordinates. */ + +void +cursor_to (struct frame *f, int vpos, int hpos) +{ + if (FRAME_DEVICE (f)->cursor_to_hook) + (*FRAME_DEVICE (f)->cursor_to_hook) (f, vpos, hpos); +} + +/* Similar but don't take any account of the wasted characters. */ + +void +raw_cursor_to (struct frame *f, int row, int col) +{ + if (FRAME_DEVICE (f)->raw_cursor_to_hook) + (*FRAME_DEVICE (f)->raw_cursor_to_hook) (f, row, col); +} + +/* Erase operations */ + +/* Clear from cursor to end of frame. */ +void +clear_to_end (struct frame *f) +{ + if (FRAME_DEVICE (f)->clear_to_end_hook) + (*FRAME_DEVICE (f)->clear_to_end_hook) (f); +} + +/* Clear entire frame */ + +void +clear_frame (struct frame *f) +{ + if (FRAME_DEVICE (f)->clear_frame_hook) + (*FRAME_DEVICE (f)->clear_frame_hook) (f); +} + +/* Clear from cursor to end of line. + Assume that the line is already clear starting at column first_unused_hpos. + + Note that the cursor may be moved, on terminals lacking a `ce' string. */ + +void +clear_end_of_line (struct frame *f, int first_unused_hpos) +{ + if (FRAME_DEVICE (f)->clear_end_of_line_hook) + (*FRAME_DEVICE (f)->clear_end_of_line_hook) (f, first_unused_hpos); +} + +/* Output LEN glyphs starting at STRING at the nominal cursor position. + Advance the nominal cursor over the text. */ + +void +write_glyphs (struct frame *f, struct glyph *string, int len) +{ + if (FRAME_DEVICE (f)->write_glyphs_hook) + (*FRAME_DEVICE (f)->write_glyphs_hook) (f, string, len); +} + +/* Insert LEN glyphs from START at the nominal cursor position. + + If start is zero, insert blanks instead of a string at start */ + +void +insert_glyphs (struct frame *f, struct glyph *start, int len) +{ + if (len <= 0) + return; + + if (FRAME_DEVICE (f)->insert_glyphs_hook) + (*FRAME_DEVICE (f)->insert_glyphs_hook) (f, start, len); +} + +/* Delete N glyphs at the nominal cursor position. */ + +void +delete_glyphs (struct frame *f, int n) +{ + if (FRAME_DEVICE (f)->delete_glyphs_hook) + (*FRAME_DEVICE (f)->delete_glyphs_hook) (f, n); +} + +/* Insert N lines at vpos VPOS. If N is negative, delete -N lines. */ + +void +ins_del_lines (struct frame *f, int vpos, int n) +{ + if (FRAME_DEVICE (f)->ins_del_lines_hook) + (*FRAME_DEVICE (f)->ins_del_lines_hook) (f, vpos, n); +} + + + + +/* Return the display object specified by DEVICE. DEVICE may be a + display id, a frame, or nil for the display device of the current + frame. If THROW is zero, return NULL for failure, otherwise throw + an error. */ + +struct device * +get_device (Lisp_Object device, int throw) +{ + struct device *result = NULL; + + if (NILP (device)) + device = selected_frame; + + if (INTEGERP (device)) + { + struct device *d; + + for (d = device_list; d; d = d->next_device) + { + if (d->id == XINT (device)) + { + result = d; + break; + } + } + } + else if (FRAMEP (device)) + { + result = FRAME_DEVICE (XFRAME (device)); + } + + if (result == NULL && throw) + wrong_type_argument (Qdisplay_live_p, device); + + return result; +} + + + +/* Create a new device object and add it to the device list. */ + +struct device * +create_device (void) +{ + struct device *device = (struct device *) xmalloc (sizeof (struct device)); + + bzero (device, sizeof (struct device)); + device->next_device = device_list; + device_list = device; + + device->id = next_device_id++; + + device->keyboard_coding = + (struct coding_system *) xmalloc (sizeof (struct coding_system)); + device->terminal_coding = + (struct coding_system *) xmalloc (sizeof (struct coding_system)); + + setup_coding_system (Qnil, device->keyboard_coding); + setup_coding_system (Qnil, device->terminal_coding); + + device->param_alist = Qnil; + return device; +} + +/* Mark the Lisp pointers in the terminal objects. + Called by the Fgarbage_collector. */ + +void +mark_devices (void) +{ + struct device *d; + for (d = device_list; d; d = d->next_device) + { + mark_object (d->param_alist); + } +} + + +/* Remove a device from the device list and free its memory. */ + +void +delete_device (struct device *device) +{ + struct device **dp; + Lisp_Object tail, frame; + + /* Check for and close live frames that are still on this + device. */ + FOR_EACH_FRAME (tail, frame) + { + struct frame *f = XFRAME (frame); + if (FRAME_LIVE_P (f) && f->device == device) + { + Fdelete_frame (frame, Qt); + } + } + + for (dp = &device_list; *dp != device; dp = &(*dp)->next_device) + if (! *dp) + abort (); + *dp = device->next_device; + + if (device->keyboard_coding) + xfree (device->keyboard_coding); + if (device->terminal_coding) + xfree (device->terminal_coding); + if (device->name) + xfree (device->name); + +#ifdef MULTI_KBOARD + if (device->kboard && --device->kboard->reference_count == 0) + delete_kboard (device->kboard); +#endif + + bzero (device, sizeof (struct device)); + xfree (device); +} + +DEFUN ("delete-display", Fdelete_display, Sdelete_display, 0, 2, 0, + doc: /* Delete DEVICE by deleting all frames on it and closing the device. +DEVICE may be a display device id, a frame, or nil (meaning the +selected frame's display device). + +Normally, you may not delete a display if all other displays are suspended, +but if the second argument FORCE is non-nil, you may do so. */) + (device, force) + Lisp_Object device, force; +{ + struct device *d, *p; + + d = get_device (device, 0); + + if (!d) + return Qnil; + + p = device_list; + while (p && (p == d || !DEVICE_ACTIVE_P (p))) + p = p->next_device; + + if (NILP (force) && !p) + error ("Attempt to delete the sole active display device"); + + if (d->delete_device_hook) + (*d->delete_device_hook) (d); + else + delete_device (d); + + return Qnil; +} + +DEFUN ("display-live-p", Fdisplay_live_p, Sdisplay_live_p, 1, 1, 0, + doc: /* Return non-nil if OBJECT is a device which has not been deleted. +Value is nil if OBJECT is not a live display device. +If object is a live display device, the return value indicates what +sort of output device it uses. See the documentation of `framep' for +possible return values. + +Display devices are represented by their integer identifiers. */) + (object) + Lisp_Object object; +{ + struct device *d; + + if (!INTEGERP (object)) + return Qnil; + + d = get_device (object, 0); + + if (!d) + return Qnil; + + switch (d->type) + { + case output_initial: /* The initial frame is like a termcap frame. */ + case output_termcap: + return Qt; + case output_x_window: + return Qx; + case output_w32: + return Qw32; + case output_msdos_raw: + return Qpc; + case output_mac: + return Qmac; + default: + abort (); + } +} + +DEFUN ("display-list", Fdisplay_list, Sdisplay_list, 0, 0, 0, + doc: /* Return a list of all display devices. +Display devices are represented by their integer identifiers. */) + () +{ + Lisp_Object devices = Qnil; + struct device *d; + + for (d = device_list; d; d = d->next_device) + devices = Fcons (make_number (d->id), devices); + + return devices; +} + +DEFUN ("display-name", Fdisplay_name, Sdisplay_name, 0, 1, 0, + doc: /* Return the name of the display device DEVICE. +It is not guaranteed that the returned value is unique among opened devices. + +DEVICE may be a display device id, a frame, or nil (meaning the +selected frame's display device). */) + (device) + Lisp_Object device; +{ + struct device *d = get_device (device, 1); + + if (d->name) + return build_string (d->name); + else + return Qnil; +} + + + +/* Return the value of terminal parameter PARAM in device D. */ +Lisp_Object +get_terminal_param (d, param) + struct device *d; + Lisp_Object param; +{ + Lisp_Object tem = Fassq (param, d->param_alist); + if (EQ (tem, Qnil)) + return tem; + return Fcdr (tem); +} + +/* Set the value of terminal parameter PARAMETER in device D to VALUE. + Return the previous value. */ + +Lisp_Object +store_terminal_param (d, parameter, value) + struct device *d; + Lisp_Object parameter; + Lisp_Object value; +{ + Lisp_Object old_alist_elt = Fassq (parameter, d->param_alist); + if (EQ (old_alist_elt, Qnil)) + { + d->param_alist = Fcons (Fcons (parameter, value), d->param_alist); + return Qnil; + } + else + { + Lisp_Object result = Fcdr (old_alist_elt); + Fsetcdr (old_alist_elt, value); + return result; + } +} + + +DEFUN ("terminal-parameters", Fterminal_parameters, Sterminal_parameters, 0, 1, 0, + doc: /* Return the parameter-alist of terminal TERMINAL. +The value is a list of elements of the form (PARM . VALUE), where PARM +is a symbol. + +TERMINAL can be a terminal if, a frame or nil (meaning the selected +frame's terminal). */) + (terminal) + Lisp_Object terminal; +{ + struct device *d = get_device (terminal, 1); + return Fcopy_alist (d->param_alist); +} + +DEFUN ("terminal-parameter", Fterminal_parameter, Sterminal_parameter, 2, 2, 0, + doc: /* Return TERMINAL's value for parameter PARAMETER. +TERMINAL can be a terminal if, a frame or nil (meaning the selected +frame's terminal). */) + (terminal, parameter) + Lisp_Object terminal; + Lisp_Object parameter; +{ + Lisp_Object value; + struct device *d = get_device (terminal, 1); + CHECK_SYMBOL (parameter); + value = Fcdr (Fassq (parameter, d->param_alist)); + return value; +} + +DEFUN ("modify-terminal-parameters", Fmodify_terminal_parameters, + Smodify_terminal_parameters, 2, 2, 0, + doc: /* Modify the parameters of terminal TERMINAL according to ALIST. +ALIST is an alist of parameters to change and their new values. +Each element of ALIST has the form (PARM . VALUE), where PARM is a symbol. + +TERMINAL can be a terminal if, a frame or nil (meaning the selected +frame's terminal). */) + (terminal, alist) + Lisp_Object terminal; + Lisp_Object alist; +{ + Lisp_Object tail, prop, val; + struct device *d = get_device (terminal, 1); + int length = XINT (Fsafe_length (alist)); + int i; + Lisp_Object *parms = (Lisp_Object *) alloca (length * sizeof (Lisp_Object)); + Lisp_Object *values = (Lisp_Object *) alloca (length * sizeof (Lisp_Object)); + + /* Extract parm names and values into those vectors. */ + + i = 0; + for (tail = alist; CONSP (tail); tail = Fcdr (tail)) + { + Lisp_Object elt; + + elt = Fcar (tail); + parms[i] = Fcar (elt); + values[i] = Fcdr (elt); + i++; + } + + /* Now process them in reverse of specified order. */ + for (i--; i >= 0; i--) + { + prop = parms[i]; + val = values[i]; + store_terminal_param (d, prop, val); + } + return Qnil; +} + +DEFUN ("set-terminal-parameter", Fset_terminal_parameter, + Sset_terminal_parameter, 3, 3, 0, + doc: /* Set TERMINAL's value for parameter PARAMETER to VALUE. +Return the previous value of PARAMETER. + +TERMINAL can be a terminal if, a frame or nil (meaning the selected +frame's terminal). */) + (terminal, parameter, value) + Lisp_Object terminal; + Lisp_Object parameter; + Lisp_Object value; +{ + struct device *d = get_device (terminal, 1); + return store_terminal_param (d, parameter, value); +} + + + +/* Create the bootstrap display device for the initial frame. + Returns a device of type output_initial. */ + +struct device * +init_initial_device (void) +{ + if (initialized || device_list || tty_list) + abort (); + + initial_device = create_device (); + initial_device->type = output_initial; + initial_device->name = xstrdup ("initial_device"); + initial_device->kboard = initial_kboard; + + initial_device->delete_device_hook = &delete_initial_device; + /* All other hooks are NULL. */ + + return initial_device; +} + +/* Deletes the bootstrap display device. + Called through delete_device_hook. */ + +void +delete_initial_device (struct device *device) +{ + if (device != initial_device) + abort (); + + delete_device (device); + initial_device = NULL; +} + +void +syms_of_terminal () +{ + + DEFVAR_LISP ("ring-bell-function", &Vring_bell_function, + doc: /* Non-nil means call this function to ring the bell. +The function should accept no arguments. */); + Vring_bell_function = Qnil; + + defsubr (&Sdelete_display); + defsubr (&Sdisplay_live_p); + defsubr (&Sdisplay_list); + defsubr (&Sdisplay_name); + defsubr (&Sterminal_parameters); + defsubr (&Sterminal_parameter); + defsubr (&Smodify_terminal_parameters); + defsubr (&Sset_terminal_parameter); + + Fprovide (intern ("multi-tty"), Qnil); +} + +/* arch-tag: e9af6f27-b483-47dc-bb1a-730c1c5cab03 + (do not change this comment) */ diff --git a/src/xterm.h b/src/xterm.h index c96d015be4..b0464b6cbf 100644 --- a/src/xterm.h +++ b/src/xterm.h @@ -995,6 +995,7 @@ extern void x_wm_set_size_hint P_ ((struct frame *, long, int)); extern void x_wm_set_window_state P_ ((struct frame *, int)); extern void x_wm_set_icon_pixmap P_ ((struct frame *, int)); extern void x_delete_display P_ ((struct x_display_info *)); +extern void x_delete_device P_ ((struct device *device)); extern void x_initialize P_ ((void)); extern unsigned long x_copy_color P_ ((struct frame *, unsigned long)); #ifdef USE_X_TOOLKIT