comparison lisp/progmodes/idlw-shell.el @ 27607:527d42ebb15e

(idlwave-shell-print): Fixed bug with idlwave-shell-expression-overlay. Implemented printing of expressions on higher levels of the calling stack. (idlwave-shell-display-level-in-calling-stack): Restore stack level. (idlwave-retrieve-expression-from-level): New function. (idlwave-shell-last-calling-stack): Variable removed. (idlwave-shell-reset): Argument action reversed (`visible' to `hidden'). Also remove stop-line overlay. (idlwave-shell-calling-stack-routine): New variable. (idlwave-shell-parse-stack-and-display): Messages now display negative level numbers. (idlwave-shell-mode): Set `modeline-format'. (idlwave-shell-display-line): Set `idlwave-shell-mode-line-info'. (idlwave-shell-make-new-bp-overlay): Fixed glyph display for Emacs 21. (idlwave-shell-print-expression-function): New option.
author Carsten Dominik <dominik@science.uva.nl>
date Fri, 04 Feb 2000 10:10:40 +0000
parents ae5b17b9c403
children 8eff9cc9cbae
comparison
equal deleted inserted replaced
27606:0396e9e8d57b 27607:527d42ebb15e
3 ;; Copyright (c) 1999 Carsten Dominik 3 ;; Copyright (c) 1999 Carsten Dominik
4 ;; Copyright (c) 1999 Free Software Foundation 4 ;; Copyright (c) 1999 Free Software Foundation
5 5
6 ;; Author: Chris Chase <chase@att.com> 6 ;; Author: Chris Chase <chase@att.com>
7 ;; Maintainer: Carsten Dominik <dominik@strw.leidenuniv.nl> 7 ;; Maintainer: Carsten Dominik <dominik@strw.leidenuniv.nl>
8 ;; Version: 3.12 8 ;; Version: 3.15
9 ;; Date: $Date: 2000/01/05 12:38:46 $ 9 ;; Date: $Date: 2000/02/04 09:20:21 $
10 ;; Keywords: processes 10 ;; Keywords: processes
11 11
12 ;; This file is part of GNU Emacs. 12 ;; This file is part of GNU Emacs.
13 13
14 ;; GNU Emacs is free software; you can redistribute it and/or modify 14 ;; GNU Emacs is free software; you can redistribute it and/or modify
67 ;; 67 ;;
68 ;; 68 ;;
69 ;; KNOWN PROBLEMS 69 ;; KNOWN PROBLEMS
70 ;; ============== 70 ;; ==============
71 ;; 71 ;;
72 ;; The idlwave-shell buffer seems to occasionally lose output from the IDL
73 ;; process. I have not been able to consistently observe this. I
74 ;; do not know if it is a problem with idlwave-shell, comint, or Emacs
75 ;; handling of subprocesses.
76 ;;
77 ;; I don't plan on implementing directory tracking by watching the IDL 72 ;; I don't plan on implementing directory tracking by watching the IDL
78 ;; commands entered at the prompt, since too often an IDL procedure 73 ;; commands entered at the prompt, since too often an IDL procedure
79 ;; will change the current directory. If you want the the idl process 74 ;; will change the current directory. If you want the the idl process
80 ;; buffer to match the IDL current working just execute `M-x 75 ;; buffer to match the IDL current working just execute `M-x
81 ;; idlwave-shell-resync-dirs' (bound to "\C-c\C-d\C-w" by default.) 76 ;; idlwave-shell-resync-dirs' (bound to "\C-c\C-d\C-w" by default.)
82 ;; 77 ;;
83 ;; The stack motion commands `idlwave-shell-stack-up' and
84 ;; `idlwave-shell-stack-down' only display the calling frame but
85 ;; cannot show the values of variables in higher frames correctly. I
86 ;; just don't know how to get these values from IDL. Anyone knows the
87 ;; magic word to do this?
88 ;; Also, the stack pointer stays at the level where is was and is not
89 ;; reset correctly when you type executive commands in the shell buffer
90 ;; yourself. However, using the executive commands bound to key sequences
91 ;; does the reset correctly. As a workaround, just jump down when needed.
92 ;;
93 ;; Under XEmacs the Debug menu in the shell does not display the 78 ;; Under XEmacs the Debug menu in the shell does not display the
94 ;; keybindings in the prefix map. There bindings are available anyway - so 79 ;; keybindings in the prefix map. There bindings are available anyway - so
95 ;; it is a bug in XEmacs. 80 ;; it is a bug in XEmacs.
96 ;; The Debug menu in source buffers does display the bindings correctly. 81 ;; The Debug menu in source buffers *does* display the bindings correctly.
97 ;; 82 ;;
98 ;; 83 ;;
99 ;; CUSTOMIZATION VARIABLES 84 ;; CUSTOMIZATION VARIABLES
100 ;; ======================= 85 ;; =======================
101 ;; 86 ;;
180 :type '(repeat 165 :type '(repeat
181 (cons symbol sexp))) 166 (cons symbol sexp)))
182 167
183 (defcustom idlwave-shell-use-toolbar t 168 (defcustom idlwave-shell-use-toolbar t
184 "Non-nil means, use the debugging toolbar in all IDL related buffers. 169 "Non-nil means, use the debugging toolbar in all IDL related buffers.
170 Starting the shell will then add the toolbar to all idlwave-mode buffers.
171 Exiting the shell will removed everywhere.
185 Available on XEmacs and on Emacs 21.x or later. 172 Available on XEmacs and on Emacs 21.x or later.
186 Needs to be set at load-time, so don't try to do this in the hook." 173 At any time you can toggle the display of the toolbar with
174 `C-c C-d C-t' (`idlwave-shell-toggle-toolbar')."
187 :group 'idlwave-shell-general-setup 175 :group 'idlwave-shell-general-setup
188 :type 'boolean) 176 :type 'boolean)
189 177
190 (defcustom idlwave-shell-temp-pro-prefix "/tmp/idltemp" 178 (defcustom idlwave-shell-temp-pro-prefix "/tmp/idltemp"
191 "*The prefix for temporary IDL files used when compiling regions. 179 "*The prefix for temporary IDL files used when compiling regions.
243 231
244 (defcustom idlwave-shell-mode-hook '() 232 (defcustom idlwave-shell-mode-hook '()
245 "*Hook for customising `idlwave-shell-mode'." 233 "*Hook for customising `idlwave-shell-mode'."
246 :group 'idlwave-shell-general-setup 234 :group 'idlwave-shell-general-setup
247 :type 'hook) 235 :type 'hook)
236
237 (defcustom idlwave-shell-print-expression-function nil
238 "When non-nil, a function to handle display of evaluated expressions.
239 This can be used to arrange for displaying the value of an expression
240 in (e.g.) a special frame. The function must accept one argument:
241 the expression which was evaluated. The output from IDL will be
242 available in the variable `idlwave-shell-command-output'."
243 :group 'idlwave-shell-highlighting-and-faces
244 :type 'symbol)
248 245
249 ;;; Breakpoint Overlays etc 246 ;;; Breakpoint Overlays etc
250 247
251 (defgroup idlwave-shell-highlighting-and-faces nil 248 (defgroup idlwave-shell-highlighting-and-faces nil
252 "Indentation options for IDL/WAVE mode." 249 "Indentation options for IDL/WAVE mode."
289 Allows you to choose the font, color and other properties for 286 Allows you to choose the font, color and other properties for
290 line where IDL is stopped. See also `idlwave-shell-mark-stop-line'." 287 line where IDL is stopped. See also `idlwave-shell-mark-stop-line'."
291 :group 'idlwave-shell-highlighting-and-faces 288 :group 'idlwave-shell-highlighting-and-faces
292 :type 'symbol) 289 :type 'symbol)
293 290
294 (defcustom idlwave-shell-expression-face 'secondary-selection
295 "*The face for `idlwave-shell-expression-overlay'.
296 Allows you to choose the font, color and other properties for
297 the expression printed by IDL."
298 :group 'idlwave-shell-highlighting-and-faces
299 :type 'symbol)
300
301 (defcustom idlwave-shell-mark-breakpoints t 291 (defcustom idlwave-shell-mark-breakpoints t
302 "*Non-nil means, mark breakpoints in the source files. 292 "*Non-nil means, mark breakpoints in the source files.
303 Legal values are: 293 Legal values are:
304 nil Do not mark breakpoints. 294 nil Do not mark breakpoints.
305 'face Highlight line with `idlwave-shell-breakpoint-face'. 295 'face Highlight line with `idlwave-shell-breakpoint-face'.
331 "Face for highlighting lines-with-breakpoints." 321 "Face for highlighting lines-with-breakpoints."
332 :group 'idlwave-shell-highlighting-and-faces) 322 :group 'idlwave-shell-highlighting-and-faces)
333 ;; Just copy the underline face to be on the safe side. 323 ;; Just copy the underline face to be on the safe side.
334 (copy-face 'underline 'idlwave-shell-bp-face)) 324 (copy-face 'underline 'idlwave-shell-bp-face))
335 325
326 (defcustom idlwave-shell-expression-face 'secondary-selection
327 "*The face for `idlwave-shell-expression-overlay'.
328 Allows you to choose the font, color and other properties for
329 the expression printed by IDL."
330 :group 'idlwave-shell-highlighting-and-faces
331 :type 'symbol)
332
336 ;;; End user customization variables 333 ;;; End user customization variables
337 334
338 ;;; External variables 335 ;;; External variables
339 (defvar comint-last-input-start) 336 (defvar comint-last-input-start)
340 (defvar comint-last-input-end) 337 (defvar comint-last-input-end)
345 "Absolute pathname for temporary IDL file for compiling regions") 342 "Absolute pathname for temporary IDL file for compiling regions")
346 343
347 (defvar idlwave-shell-dirstack-query "printd" 344 (defvar idlwave-shell-dirstack-query "printd"
348 "Command used by `idlwave-shell-resync-dirs' to query IDL for 345 "Command used by `idlwave-shell-resync-dirs' to query IDL for
349 the directory stack.") 346 the directory stack.")
347
348 (defvar idlwave-shell-mode-line-info nil
349 "Additional info displayed in the mode line")
350 350
351 (defvar idlwave-shell-default-directory nil 351 (defvar idlwave-shell-default-directory nil
352 "The default directory in the idlwave-shell buffer, of outside use.") 352 "The default directory in the idlwave-shell buffer, of outside use.")
353 353
354 (defvar idlwave-shell-last-save-and-action-file nil 354 (defvar idlwave-shell-last-save-and-action-file nil
402 402
403 ;; Now the expression overlay 403 ;; Now the expression overlay
404 (setq idlwave-shell-expression-overlay (make-overlay 1 1)) 404 (setq idlwave-shell-expression-overlay (make-overlay 1 1))
405 (overlay-put idlwave-shell-expression-overlay 405 (overlay-put idlwave-shell-expression-overlay
406 'face idlwave-shell-expression-face) 406 'face idlwave-shell-expression-face)
407
408 (defvar idlwave-shell-bp-query "help,/breakpoints" 407 (defvar idlwave-shell-bp-query "help,/breakpoints"
409 "Command to obtain list of breakpoints") 408 "Command to obtain list of breakpoints")
410 409
411 (defvar idlwave-shell-command-output nil 410 (defvar idlwave-shell-command-output nil
412 "String for accumulating current command output.") 411 "String for accumulating current command output.")
500 (defvar idlwave-shell-error-buffer) 499 (defvar idlwave-shell-error-buffer)
501 (defvar idlwave-shell-error-last) 500 (defvar idlwave-shell-error-last)
502 (defvar idlwave-shell-bp-buffer) 501 (defvar idlwave-shell-bp-buffer)
503 (defvar idlwave-shell-sources-query) 502 (defvar idlwave-shell-sources-query)
504 (defvar idlwave-shell-mode-map) 503 (defvar idlwave-shell-mode-map)
504 (defvar idlwave-shell-calling-stack-index)
505 505
506 (defun idlwave-shell-mode () 506 (defun idlwave-shell-mode ()
507 "Major mode for interacting with an inferior IDL process. 507 "Major mode for interacting with an inferior IDL process.
508 508
509 1. Shell Interaction 509 1. Shell Interaction
579 (set (make-local-variable 'completion-ignore-case) t) 579 (set (make-local-variable 'completion-ignore-case) t)
580 (setq comint-completion-addsuffix '("/" . "")) 580 (setq comint-completion-addsuffix '("/" . ""))
581 (setq comint-input-ignoredups t) 581 (setq comint-input-ignoredups t)
582 (setq major-mode 'idlwave-shell-mode) 582 (setq major-mode 'idlwave-shell-mode)
583 (setq mode-name "IDL-Shell") 583 (setq mode-name "IDL-Shell")
584 (setq idlwave-shell-mode-line-info nil)
585 (setq mode-line-format
586 '(""
587 mode-line-modified
588 mode-line-buffer-identification
589 " "
590 global-mode-string
591 " %[("
592 mode-name
593 mode-line-process
594 minor-mode-alist
595 "%n"
596 ")%]-"
597 idlwave-shell-mode-line-info
598 "---"
599 (line-number-mode "L%l--")
600 (column-number-mode "C%c--")
601 (-3 . "%p")
602 "-%-"))
584 ;; (make-local-variable 'idlwave-shell-bp-alist) 603 ;; (make-local-variable 'idlwave-shell-bp-alist)
585 (setq idlwave-shell-halt-frame nil 604 (setq idlwave-shell-halt-frame nil
586 idlwave-shell-trace-frame nil 605 idlwave-shell-trace-frame nil
587 idlwave-shell-command-output nil 606 idlwave-shell-command-output nil
588 idlwave-shell-step-frame nil) 607 idlwave-shell-step-frame nil)
589 (idlwave-shell-display-line nil) 608 (idlwave-shell-display-line nil)
609 (setq idlwave-shell-calling-stack-index 0)
590 ;; Make sure comint-last-input-end does not go to beginning of 610 ;; Make sure comint-last-input-end does not go to beginning of
591 ;; buffer (in case there were other processes already in this buffer). 611 ;; buffer (in case there were other processes already in this buffer).
592 (set-marker comint-last-input-end (point)) 612 (set-marker comint-last-input-end (point))
593 (setq idlwave-shell-ready nil) 613 (setq idlwave-shell-ready nil)
594 (setq idlwave-shell-bp-alist nil) 614 (setq idlwave-shell-bp-alist nil)
614 (defvar idlwave-shell-idl-wframe nil 634 (defvar idlwave-shell-idl-wframe nil
615 "Frame for displaying the idl shell window.") 635 "Frame for displaying the idl shell window.")
616 (defvar idlwave-shell-display-wframe nil 636 (defvar idlwave-shell-display-wframe nil
617 "Frame for displaying the idl source files.") 637 "Frame for displaying the idl source files.")
618 638
619 (defvar idlwave-shell-last-calling-stack nil
620 "Caches the last calling stack, so that we can compare.")
621 (defvar idlwave-shell-calling-stack-index 0) 639 (defvar idlwave-shell-calling-stack-index 0)
640 (defvar idlwave-shell-calling-stack-routine nil)
622 641
623 (defun idlwave-shell-source-frame () 642 (defun idlwave-shell-source-frame ()
624 "Return the frame to be used for source display." 643 "Return the frame to be used for source display."
625 (if idlwave-shell-use-dedicated-frame 644 (if idlwave-shell-use-dedicated-frame
626 ;; We want separate frames for source and shell 645 ;; We want separate frames for source and shell
921 940
922 ;; Various types of HALT messages. 941 ;; Various types of HALT messages.
923 ((string-match idlwave-shell-halt-messages-re 942 ((string-match idlwave-shell-halt-messages-re
924 idlwave-shell-command-output) 943 idlwave-shell-command-output)
925 ;; Grab the file and line state info. 944 ;; Grab the file and line state info.
945 (setq idlwave-shell-calling-stack-index 0)
926 (setq idlwave-shell-halt-frame 946 (setq idlwave-shell-halt-frame
927 (idlwave-shell-parse-line 947 (idlwave-shell-parse-line
928 (substring idlwave-shell-command-output (match-end 0))) 948 (substring idlwave-shell-command-output (match-end 0)))
929 update t)) 949 update t))
930 950
931 ;; Handle breakpoints separately 951 ;; Handle breakpoints separately
932 ((string-match idlwave-shell-break-message 952 ((string-match idlwave-shell-break-message
933 idlwave-shell-command-output) 953 idlwave-shell-command-output)
954 (setq idlwave-shell-calling-stack-index 0)
934 (setq idlwave-shell-halt-frame 955 (setq idlwave-shell-halt-frame
935 (idlwave-shell-parse-line 956 (idlwave-shell-parse-line
936 (substring idlwave-shell-command-output (match-end 0))) 957 (substring idlwave-shell-command-output (match-end 0)))
937 update t) 958 update t)
938 ;; We used to to counting hits on breakpoints 959 ;; We used to to counting hits on breakpoints
1150 (if (or arg (y-or-n-p "Exit the IDLWAVE Shell? ")) 1171 (if (or arg (y-or-n-p "Exit the IDLWAVE Shell? "))
1151 (condition-case nil 1172 (condition-case nil
1152 (idlwave-shell-send-command "exit") 1173 (idlwave-shell-send-command "exit")
1153 (error nil))))) 1174 (error nil)))))
1154 1175
1155 (defun idlwave-shell-reset (&optional visible) 1176 (defun idlwave-shell-reset (&optional hidden)
1156 "Reset IDL. Return to main level and destroy the leaftover variables. 1177 "Reset IDL. Return to main level and destroy the leaftover variables.
1157 This issues the following commands: 1178 This issues the following commands:
1158 RETALL 1179 RETALL
1159 WIDGET_CONTROL,/RESET 1180 WIDGET_CONTROL,/RESET
1160 CLOSE, /ALL 1181 CLOSE, /ALL
1161 HEAP_GC, /VERBOSE" 1182 HEAP_GC, /VERBOSE"
1162 ;; OBJ_DESTROY, OBJ_VALID() FIXME: should this be added? 1183 ;; OBJ_DESTROY, OBJ_VALID() FIXME: should this be added?
1163 (interactive "P") 1184 (interactive "P")
1164 (message "Resetting IDL") 1185 (message "Resetting IDL")
1165 (idlwave-shell-send-command "retall" nil (not visible)) 1186 (setq idlwave-shell-calling-stack-index 0)
1166 (idlwave-shell-send-command "widget_control,/reset" nil (not visible)) 1187 (idlwave-shell-send-command "retall" nil hidden)
1167 (idlwave-shell-send-command "close,/all" nil (not visible)) 1188 (idlwave-shell-send-command "widget_control,/reset" nil hidden)
1168 ;; (idlwave-shell-send-command "obj_destroy, obj_valid()" nil (not visible)) 1189 (idlwave-shell-send-command "close,/all" nil hidden)
1169 (idlwave-shell-send-command "heap_gc,/verbose" nil (not visible)) 1190 ;; (idlwave-shell-send-command "obj_destroy, obj_valid()" nil hidden)
1170 (setq idlwave-shell-calling-stack-index 0)) 1191 (idlwave-shell-send-command "heap_gc,/verbose" nil hidden)
1192 (idlwave-shell-display-line nil))
1171 1193
1172 (defun idlwave-shell-filter-directory () 1194 (defun idlwave-shell-filter-directory ()
1173 "Get the current directory from `idlwave-shell-command-output'. 1195 "Get the current directory from `idlwave-shell-command-output'.
1174 Change the default directory for the process buffer to concur." 1196 Change the default directory for the process buffer to concur."
1175 (save-excursion 1197 (save-excursion
1239 "Tries to resync the display with where execution has stopped. 1261 "Tries to resync the display with where execution has stopped.
1240 Issues a \"help,/trace\" command followed by a call to 1262 Issues a \"help,/trace\" command followed by a call to
1241 `idlwave-shell-display-line'. Also updates the breakpoint 1263 `idlwave-shell-display-line'. Also updates the breakpoint
1242 overlays." 1264 overlays."
1243 (interactive) 1265 (interactive)
1266 (setq idlwave-shell-calling-stack-index 0)
1244 (idlwave-shell-send-command 1267 (idlwave-shell-send-command
1245 "help,/trace" 1268 "help,/trace"
1246 '(idlwave-shell-display-line 1269 '(idlwave-shell-display-line
1247 (idlwave-shell-pc-frame)) 1270 (idlwave-shell-pc-frame))
1248 hide) 1271 hide)
1249 (idlwave-shell-bp-query)) 1272 (idlwave-shell-bp-query))
1250 1273
1251 (defun idlwave-shell-display-level-in-calling-stack (&optional hide) 1274 (defun idlwave-shell-display-level-in-calling-stack (&optional hide)
1252 (idlwave-shell-send-command 1275 (idlwave-shell-send-command
1253 "help,/trace" 1276 "help,/trace"
1254 'idlwave-shell-parse-stack-and-display 1277 `(progn
1278 ;; scanning for the state will reset the stack level - restore it
1279 (setq idlwave-shell-calling-stack-index
1280 ,idlwave-shell-calling-stack-index)
1281 ;; parse the stack and visit the selected frame
1282 (idlwave-shell-parse-stack-and-display))
1255 hide)) 1283 hide))
1256 1284
1257 (defun idlwave-shell-parse-stack-and-display () 1285 (defun idlwave-shell-parse-stack-and-display ()
1258 (let* ((lines (delete "" (idlwave-split-string 1286 (let* ((lines (delete "" (idlwave-split-string
1259 idlwave-shell-command-output "^%"))) 1287 idlwave-shell-command-output "^%")))
1260 (stack (delq nil (mapcar 'idlwave-shell-parse-line lines))) 1288 (stack (delq nil (mapcar 'idlwave-shell-parse-line lines)))
1261 (nmax (1- (length stack))) 1289 (nmax (1- (length stack)))
1262 (nmin 0) message) 1290 (nmin 0) message)
1263 ; ;; Reset the stack to zero if it is a new stack.
1264 ; (if (not (equal stack idlwave-shell-last-calling-stack))
1265 ; (setq idlwave-shell-calling-stack-index 0))
1266 ; (setq idlwave-shell-last-calling-stack stack)
1267 (cond 1291 (cond
1268 ((< nmax nmin) 1292 ((< nmax nmin)
1269 (setq idlwave-shell-calling-stack-index 0) 1293 (setq idlwave-shell-calling-stack-index 0)
1270 (error "Problem with calling stack")) 1294 (error "Problem with calling stack"))
1271 ((> idlwave-shell-calling-stack-index nmax) 1295 ((> idlwave-shell-calling-stack-index nmax)
1296 (ding)
1272 (setq idlwave-shell-calling-stack-index nmax 1297 (setq idlwave-shell-calling-stack-index nmax
1273 message (format "%d is the highest level on the calling stack" 1298 message (format "%d is the highest calling stack level - can't go further up"
1274 nmax))) 1299 (- nmax))))
1275 ((< idlwave-shell-calling-stack-index nmin) 1300 ((< idlwave-shell-calling-stack-index nmin)
1301 (ding)
1276 (setq idlwave-shell-calling-stack-index nmin 1302 (setq idlwave-shell-calling-stack-index nmin
1277 message (format "%d is the lowest level on the calling stack" 1303 message (format "%d is the current calling stack level - can't go further down"
1278 nmin)))) 1304 (- nmin)))))
1305 (setq idlwave-shell-calling-stack-routine
1306 (nth 2 (nth idlwave-shell-calling-stack-index stack)))
1279 (idlwave-shell-display-line 1307 (idlwave-shell-display-line
1280 (nth idlwave-shell-calling-stack-index stack)) 1308 (nth idlwave-shell-calling-stack-index stack))
1281 (message (or message 1309 (message (or message
1282 (format "On stack level %d" 1310 (format "In routine %s (stack level %d)"
1283 idlwave-shell-calling-stack-index))))) 1311 idlwave-shell-calling-stack-routine
1312 (- idlwave-shell-calling-stack-index))))))
1284 1313
1285 (defun idlwave-shell-stack-up () 1314 (defun idlwave-shell-stack-up ()
1286 "Display the source code one step up the calling stack." 1315 "Display the source code one step up the calling stack."
1287 (interactive) 1316 (interactive)
1288 (incf idlwave-shell-calling-stack-index) 1317 (incf idlwave-shell-calling-stack-index)
1307 1336
1308 (defun idlwave-shell-pc-frame () 1337 (defun idlwave-shell-pc-frame ()
1309 "Returns the frame for IDL execution." 1338 "Returns the frame for IDL execution."
1310 (and idlwave-shell-halt-frame 1339 (and idlwave-shell-halt-frame
1311 (list (nth 0 idlwave-shell-halt-frame) 1340 (list (nth 0 idlwave-shell-halt-frame)
1312 (nth 1 idlwave-shell-halt-frame)))) 1341 (nth 1 idlwave-shell-halt-frame)
1342 (nth 2 idlwave-shell-halt-frame))))
1313 1343
1314 (defun idlwave-shell-valid-frame (frame) 1344 (defun idlwave-shell-valid-frame (frame)
1315 "Check that frame is for an existing file." 1345 "Check that frame is for an existing file."
1316 (file-readable-p (car frame))) 1346 (file-readable-p (car frame)))
1317 1347
1322 If FRAME is nil then remove overlay." 1352 If FRAME is nil then remove overlay."
1323 (if (not frame) 1353 (if (not frame)
1324 ;; Remove stop-line overlay from old position 1354 ;; Remove stop-line overlay from old position
1325 (progn 1355 (progn
1326 (setq overlay-arrow-string nil) 1356 (setq overlay-arrow-string nil)
1357 (setq idlwave-shell-mode-line-info nil)
1327 (if idlwave-shell-stop-line-overlay 1358 (if idlwave-shell-stop-line-overlay
1328 (delete-overlay idlwave-shell-stop-line-overlay))) 1359 (delete-overlay idlwave-shell-stop-line-overlay)))
1329 (if (not (idlwave-shell-valid-frame frame)) 1360 (if (not (idlwave-shell-valid-frame frame))
1330 (error (concat "Invalid frame - unable to access file: " (car frame))) 1361 (error (concat "Invalid frame - unable to access file: " (car frame)))
1331 ;;; 1362 ;;;
1332 ;;; buffer : the buffer to display a line in. 1363 ;;; buffer : the buffer to display a line in.
1333 ;;; select-shell: current buffer is the shell. 1364 ;;; select-shell: current buffer is the shell.
1334 ;;; 1365 ;;;
1366 (setq idlwave-shell-mode-line-info
1367 (if (nth 2 frame)
1368 (format "[%d:%s]"
1369 (- idlwave-shell-calling-stack-index)
1370 (nth 2 frame))))
1335 (let* ((buffer (idlwave-find-file-noselect (car frame))) 1371 (let* ((buffer (idlwave-find-file-noselect (car frame)))
1336 (select-shell (equal (buffer-name) (idlwave-shell-buffer))) 1372 (select-shell (equal (buffer-name) (idlwave-shell-buffer)))
1337 window pos) 1373 window pos)
1338 1374
1339 ;; First make sure the shell window is visible 1375 ;; First make sure the shell window is visible
1647 "Call `idlwave-shell-print' at the mouse position." 1683 "Call `idlwave-shell-print' at the mouse position."
1648 (interactive "e") 1684 (interactive "e")
1649 (mouse-set-point event) 1685 (mouse-set-point event)
1650 (idlwave-shell-help-expression)) 1686 (idlwave-shell-help-expression))
1651 1687
1652 (defun idlwave-shell-print (&optional help special) 1688 (defun idlwave-shell-print (&optional help)
1653 "Print current expression. With are HELP, show help on expression. 1689 "Print current expression. With HELP, show help on expression.
1654 An expression is an identifier plus 1 pair of matched parentheses 1690 An expression is an identifier plus 1 pair of matched parentheses
1655 directly following the identifier - an array or function 1691 directly following the identifier - an array or function
1656 call. Alternatively, an expression is the contents of any matched 1692 call. Alternatively, an expression is the contents of any matched
1657 parentheses when the open parentheses is not directly preceded by an 1693 parentheses when the open parentheses is not directly preceded by an
1658 identifier. If point is at the beginning or within an expression 1694 identifier. If point is at the beginning or within an expression
1659 return the inner-most containing expression, otherwise, return the 1695 return the inner-most containing expression, otherwise, return the
1660 preceding expression." 1696 preceding expression."
1661 (interactive "P") 1697 (interactive)
1662 (save-excursion 1698 (save-excursion
1663 (let (beg end) 1699 (let (expr beg end cmd)
1664 ;; Move to beginning of current or previous expression 1700 (if current-prefix-arg
1665 (if (looking-at "\\<\\|(") 1701 (setq expr (read-string "Expression: "))
1666 ;; At beginning of expression, don't move backwards unless 1702 ;; Move to beginning of current or previous expression
1667 ;; this is at the end of an indentifier. 1703 (if (looking-at "\\<\\|(")
1668 (if (looking-at "\\>") 1704 ;; At beginning of expression, don't move backwards unless
1669 (backward-sexp)) 1705 ;; this is at the end of an indentifier.
1670 (backward-sexp)) 1706 (if (looking-at "\\>")
1671 (if (looking-at "\\>") 1707 (backward-sexp))
1672 ;; Move to beginning of identifier - must be an array or 1708 (backward-sexp))
1673 ;; function expression. 1709 (if (looking-at "\\>")
1674 (backward-sexp)) 1710 ;; Move to beginning of identifier - must be an array or
1675 ;; Move to end of expression 1711 ;; function expression.
1676 (setq beg (point)) 1712 (backward-sexp))
1677 (forward-sexp) 1713 ;; Move to end of expression
1678 (while (looking-at "\\>(\\|\\.") 1714 (setq beg (point))
1679 ;; an array 1715 (forward-sexp)
1680 (forward-sexp)) 1716 (while (looking-at "\\>[[(]\\|\\.")
1681 (setq end (point)) 1717 ;; an array
1682 (when idlwave-shell-expression-overlay 1718 (forward-sexp))
1683 (move-overlay idlwave-shell-expression-overlay beg end) 1719 (setq end (point))
1720 (setq expr (buffer-substring beg end)))
1721 (when (and beg end idlwave-shell-expression-overlay)
1722 (move-overlay idlwave-shell-expression-overlay beg end
1723 (current-buffer))
1684 (add-hook 'pre-command-hook 'idlwave-shell-delete-expression-overlay)) 1724 (add-hook 'pre-command-hook 'idlwave-shell-delete-expression-overlay))
1685 (if special 1725 (if (and (integerp idlwave-shell-calling-stack-index)
1726 (> idlwave-shell-calling-stack-index 0))
1727 (setq cmd (idlwave-retrieve-expression-from-level
1728 expr
1729 idlwave-shell-calling-stack-index
1730 idlwave-shell-calling-stack-routine
1731 help))
1732 (setq cmd (concat (if help "help," "print,") expr)))
1733 (if idlwave-shell-print-expression-function
1686 (idlwave-shell-send-command 1734 (idlwave-shell-send-command
1687 (concat (if help "help," "print,") (buffer-substring beg end)) 1735 cmd
1688 `(idlwave-shell-process-print-output ,(buffer-substring beg end) 1736 (list idlwave-shell-print-expression-function expr)
1689 idlwave-shell-command-output
1690 ,special)
1691 'hide) 1737 'hide)
1692 (idlwave-shell-recenter-shell-window) 1738 (idlwave-shell-recenter-shell-window)
1693 (idlwave-shell-send-command 1739 (idlwave-shell-send-command cmd)))))
1694 (concat (if help "help," "print,") (buffer-substring beg end))))))) 1740
1741 (defun idlwave-retrieve-expression-from-level (expr level routine help)
1742 "Return IDL command to print the expression EXPR from stack level LEVEL.
1743
1744 It does not seem possible to evaluate an expression on a differnt
1745 level than the current. Therefore, this function retrieves *copies* of
1746 the variables involved in the expression from the desired level in the
1747 calling stack. The copies are given some unlikely names on the
1748 *current* level, and the expression is then evaluated on the *current*
1749 level.
1750
1751 Since this function depends upon the undocumented IDL routine routine_names,
1752 there is no guarantie that this will work with future versions of IDL."
1753 (let ((prefix "___") ;; No real variables should starts with this.
1754 (fetch (- 0 level))
1755 (start 0)
1756 var tvar fetch-vars pre post)
1757
1758 ;; FIXME: In the following we try to find the variables in expression
1759 ;; This is quite empirical - I don't know in what situations this will
1760 ;; break. We will look for identifiers and exclude cases where we
1761 ;; know it is not a variable. To distinguish array references from
1762 ;; function calls, we require that arrays use [] instead of ()
1763
1764 (while (string-match
1765 "\\(\\`\\|[^a-zA-Z0-9$_]\\)\\([a-zA-Z][a-zA-Z0-9$_]*\\)\\([^a-zA-Z0-9$_]\\|\\'\\)" expr start)
1766 (setq var (match-string 2 expr)
1767 tvar (concat prefix var)
1768 start (match-beginning 2)
1769 pre (substring expr 0 (match-beginning 2))
1770 post (substring expr (match-end 2)))
1771 (cond
1772 ;; Exclude identifiers which are not variables
1773 ((string-match ",[ \t]*/\\'" pre)) ;; a `/' KEYWORD
1774 ((and (string-match "[,(][ \t]*\\'" pre)
1775 (string-match "\\`[ \t]*=" post))) ;; a `=' KEYWORD
1776 ((string-match "\\`(" post)) ;; a function
1777 ((string-match "->[ \t]*\\'" pre)) ;; a method
1778 ((string-match "\\.\\'" pre)) ;; structure member
1779 (t ;; seems to be a variable - arrange to get it and replace
1780 ;; its name in the expression with the temproary name.
1781 (push (cons var tvar) fetch-vars)
1782 (setq expr (concat pre tvar post)))))
1783 ;; Make a command line that first copies the relevant variables
1784 ;; and then prints the expression.
1785 (concat
1786 (mapconcat
1787 (lambda (x)
1788 (format "%s = routine_names('%s',fetch=%d)" (cdr x) (car x) fetch))
1789 (nreverse fetch-vars)
1790 " & ")
1791 (if idlwave-shell-print-expression-function " & " "\n")
1792 (if help "help, " "print, ")
1793 expr
1794 (format " ; [-%d:%s]" level routine))))
1695 1795
1696 (defun idlwave-shell-delete-expression-overlay () 1796 (defun idlwave-shell-delete-expression-overlay ()
1697 (condition-case nil 1797 (condition-case nil
1698 (if idlwave-shell-expression-overlay 1798 (if idlwave-shell-expression-overlay
1699 (delete-overlay idlwave-shell-expression-overlay)) 1799 (delete-overlay idlwave-shell-expression-overlay))
2032 (if (and (memq idlwave-shell-mark-breakpoints '(t glyph)) 2132 (if (and (memq idlwave-shell-mark-breakpoints '(t glyph))
2033 idlwave-shell-bp-glyph) ; this var knows if glyph's possible 2133 idlwave-shell-bp-glyph) ; this var knows if glyph's possible
2034 ;; use a glyph 2134 ;; use a glyph
2035 (let ((string "@")) 2135 (let ((string "@"))
2036 (put-text-property 0 1 2136 (put-text-property 0 1
2037 'display (cons nil idlwave-shell-bp-glyph) 2137 'display idlwave-shell-bp-glyph
2038 string) 2138 string)
2039 (overlay-put ov 'before-string string)) 2139 (overlay-put ov 'before-string string))
2040 (overlay-put ov 'face 'idlwave-shell-bp-face))) 2140 (overlay-put ov 'face 'idlwave-shell-bp-face)))
2041 (idlwave-shell-mark-breakpoints 2141 (idlwave-shell-mark-breakpoints
2042 ;; use a face 2142 ;; use a face
2059 (interactive "P") 2159 (interactive "P")
2060 (if (or (not idlwave-shell-command-line-to-execute) 2160 (if (or (not idlwave-shell-command-line-to-execute)
2061 arg) 2161 arg)
2062 (setq idlwave-shell-command-line-to-execute 2162 (setq idlwave-shell-command-line-to-execute
2063 (read-string "IDL> " idlwave-shell-command-line-to-execute))) 2163 (read-string "IDL> " idlwave-shell-command-line-to-execute)))
2064 (idlwave-shell-reset nil) 2164 (idlwave-shell-reset 'hidden)
2065 (idlwave-shell-send-command idlwave-shell-command-line-to-execute 2165 (idlwave-shell-send-command idlwave-shell-command-line-to-execute
2066 '(idlwave-shell-redisplay 'hide))) 2166 '(idlwave-shell-redisplay 'hide)))
2067 2167
2068 (defun idlwave-shell-save-and-run () 2168 (defun idlwave-shell-save-and-run ()
2069 "Save file and run it in IDL. 2169 "Save file and run it in IDL.
2434 (provide 'idlw-shell) 2534 (provide 'idlw-shell)
2435 (provide 'idlwave-shell) 2535 (provide 'idlwave-shell)
2436 2536
2437 ;;; Load the toolbar when wanted by the user. 2537 ;;; Load the toolbar when wanted by the user.
2438 2538
2539 (autoload 'idlwave-toolbar-toggle "idlw-toolbar"
2540 "Toggle the IDLWAVE toolbar")
2541 (autoload 'idlwave-toolbar-add-everywhere "idlw-toolbar"
2542 "Add IDLWAVE toolbar")
2439 (defun idlwave-shell-toggle-toolbar () 2543 (defun idlwave-shell-toggle-toolbar ()
2440 "Toggle the display of the debugging toolbar." 2544 "Toggle the display of the debugging toolbar."
2441 (interactive) 2545 (interactive)
2442 (if (featurep 'idlw-toolbar) 2546 (idlwave-toolbar-toggle))
2443 (idlwave-toolbar-toggle) 2547
2444 (require 'idlw-toolbar) 2548 (if idlwave-shell-use-toolbar
2445 (idlwave-toolbar-toggle))) 2549 (add-hook 'idlwave-shell-mode-hook 'idlwave-toolbar-add-everywhere))
2446
2447
2448 (when idlwave-shell-use-toolbar
2449 (or (load "idlw-toolbar" t)
2450 (message
2451 "Tried to load file `idlw-toolbar.el', but file does not exist")))
2452 2550
2453 ;;; idlw-shell.el ends here 2551 ;;; idlw-shell.el ends here
2454 2552
2455