root/trunk/src/callint.c

Revision 4220, 29.5 kB (checked in by miyoshi, 6 months ago)

Sync up with Emacs22.2.

  • Property svn:eol-style set to native
Line 
1 /* Call a Lisp function interactively.
2    Copyright (C) 1985, 1986, 1993, 1994, 1995, 1997, 2000, 2001, 2002,
3                  2003, 2004, 2005, 2006, 2007, 2008
4                  Free Software Foundation, Inc.
5
6 This file is part of GNU Emacs.
7
8 GNU Emacs is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 3, or (at your option)
11 any later version.
12
13 GNU Emacs is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 GNU General Public License for more details.
17
18 You should have received a copy of the GNU General Public License
19 along with GNU Emacs; see the file COPYING.  If not, write to
20 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
21 Boston, MA 02110-1301, USA.  */
22
23
24 #include <config.h>
25
26 #include "lisp.h"
27 #include "buffer.h"
28 #include "commands.h"
29 #include "keyboard.h"
30 #include "window.h"
31 #include "keymap.h"
32
33 #ifdef HAVE_INDEX
34 extern char *index P_ ((const char *, int));
35 #endif
36
37 extern Lisp_Object Qcursor_in_echo_area;
38 extern Lisp_Object Qfile_directory_p;
39
40 Lisp_Object Vcurrent_prefix_arg, Qminus, Qplus;
41 Lisp_Object Qcall_interactively;
42 Lisp_Object Vcommand_history;
43
44 extern Lisp_Object Vhistory_length;
45 extern Lisp_Object Vthis_original_command, real_this_command;
46
47 Lisp_Object Vcommand_debug_status, Qcommand_debug_status;
48 Lisp_Object Qenable_recursive_minibuffers;
49
50 /* Non-nil means treat the mark as active
51    even if mark_active is 0.  */
52 Lisp_Object Vmark_even_if_inactive;
53
54 Lisp_Object Vmouse_leave_buffer_hook, Qmouse_leave_buffer_hook;
55
56 Lisp_Object Qlist, Qlet, Qletx, Qsave_excursion, Qprogn, Qif, Qwhen;
57 static Lisp_Object preserved_fns;
58
59 /* Marker used within call-interactively to refer to point.  */
60 static Lisp_Object point_marker;
61
62 /* String for the prompt text used in Fcall_interactively.  */
63 static Lisp_Object callint_message;
64
65 /* ARGSUSED */
66 DEFUN ("interactive", Finteractive, Sinteractive, 0, UNEVALLED, 0,
67        doc: /* Specify a way of parsing arguments for interactive use of a function.
68 For example, write
69   (defun foo (arg) "Doc string" (interactive "p") ...use arg...)
70 to make ARG be the prefix argument when `foo' is called as a command.
71 The "call" to `interactive' is actually a declaration rather than a function;
72  it tells `call-interactively' how to read arguments
73  to pass to the function.
74 When actually called, `interactive' just returns nil.
75
76 The argument of `interactive' is usually a string containing a code letter
77  followed by a prompt.  (Some code letters do not use I/O to get
78  the argument and do not need prompts.)  To prompt for multiple arguments,
79  give a code letter, its prompt, a newline, and another code letter, etc.
80  Prompts are passed to format, and may use % escapes to print the
81  arguments that have already been read.
82 If the argument is not a string, it is evaluated to get a list of
83  arguments to pass to the function.
84 Just `(interactive)' means pass no args when calling interactively.
85
86 Code letters available are:
87 a -- Function name: symbol with a function definition.
88 b -- Name of existing buffer.
89 B -- Name of buffer, possibly nonexistent.
90 c -- Character (no input method is used).
91 C -- Command name: symbol with interactive function definition.
92 d -- Value of point as number.  Does not do I/O.
93 D -- Directory name.
94 e -- Parametrized event (i.e., one that's a list) that invoked this command.
95      If used more than once, the Nth `e' returns the Nth parameterized event.
96      This skips events that are integers or symbols.
97 f -- Existing file name.
98 F -- Possibly nonexistent file name.
99 G -- Possibly nonexistent file name, defaulting to just directory name.
100 i -- Ignored, i.e. always nil.  Does not do I/O.
101 k -- Key sequence (downcase the last event if needed to get a definition).
102 K -- Key sequence to be redefined (do not downcase the last event).
103 m -- Value of mark as number.  Does not do I/O.
104 M -- Any string.  Inherits the current input method.
105 n -- Number read using minibuffer.
106 N -- Numeric prefix arg, or if none, do like code `n'.
107 p -- Prefix arg converted to number.  Does not do I/O.
108 P -- Prefix arg in raw form.  Does not do I/O.
109 r -- Region: point and mark as 2 numeric args, smallest first.  Does no I/O.
110 s -- Any string.  Does not inherit the current input method.
111 S -- Any symbol.
112 U -- Mouse up event discarded by a previous k or K argument.
113 v -- Variable name: symbol that is user-variable-p.
114 x -- Lisp expression read but not evaluated.
115 X -- Lisp expression read and evaluated.
116 z -- Coding system.
117 Z -- Coding system, nil if no prefix arg.
118 In addition, if the string begins with `*'
119  then an error is signaled if the buffer is read-only.
120  This happens before reading any arguments.
121 If the string begins with `@', then Emacs searches the key sequence
122  which invoked the command for its first mouse click (or any other
123  event which specifies a window), and selects that window before
124  reading any arguments.  You may use both `@' and `*'; they are
125  processed in the order that they appear.
126 usage: (interactive ARGS)  */)
127      (args)
128      Lisp_Object args;
129 {
130   return Qnil;
131 }
132
133 /* Quotify EXP: if EXP is constant, return it.
134    If EXP is not constant, return (quote EXP).  */
135 Lisp_Object
136 quotify_arg (exp)
137      register Lisp_Object exp;
138 {
139   if (!INTEGERP (exp) && !STRINGP (exp)
140       && !NILP (exp) && !EQ (exp, Qt))
141     return Fcons (Qquote, Fcons (exp, Qnil));
142
143   return exp;
144 }
145
146 /* Modify EXP by quotifying each element (except the first).  */
147 Lisp_Object
148 quotify_args (exp)
149      Lisp_Object exp;
150 {
151   register Lisp_Object tail;
152   Lisp_Object next;
153   for (tail = exp; CONSP (tail); tail = next)
154     {
155       next = XCDR (tail);
156       XSETCAR (tail, quotify_arg (XCAR (tail)));
157     }
158   return exp;
159 }
160
161 char *callint_argfuns[]
162     = {"", "point", "mark", "region-beginning", "region-end"};
163
164 static void
165 check_mark (for_region)
166      int for_region;
167 {
168   Lisp_Object tem;
169   tem = Fmarker_buffer (current_buffer->mark);
170   if (NILP (tem) || (XBUFFER (tem) != current_buffer))
171     error (for_region ? "The mark is not set now, so there is no region"
172            : "The mark is not set now");
173   if (!NILP (Vtransient_mark_mode) && NILP (Vmark_even_if_inactive)
174       && NILP (current_buffer->mark_active))
175     xsignal0 (Qmark_inactive);
176 }
177
178 /* If the list of args INPUT was produced with an explicit call to
179    `list', look for elements that were computed with
180    (region-beginning) or (region-end), and put those expressions into
181    VALUES instead of the present values.
182
183    This function doesn't return a value because it modifies elements
184    of VALUES to do its job.  */
185
186 static void
187 fix_command (input, values)
188      Lisp_Object input, values;
189 {
190   if (CONSP (input))
191     {
192       Lisp_Object car;
193
194       car = XCAR (input);
195       /* Skip through certain special forms.  */
196       while (EQ (car, Qlet) || EQ (car, Qletx)
197              || EQ (car, Qsave_excursion)
198              || EQ (car, Qprogn))
199         {
200           while (CONSP (XCDR (input)))
201             input = XCDR (input);
202           input = XCAR (input);
203           if (!CONSP (input))
204             break;
205           car = XCAR (input);
206         }
207       if (EQ (car, Qlist))
208         {
209           Lisp_Object intail, valtail;
210           for (intail = Fcdr (input), valtail = values;
211                CONSP (valtail);
212                intail = Fcdr (intail), valtail = XCDR (valtail))
213             {
214               Lisp_Object elt;
215               elt = Fcar (intail);
216               if (CONSP (elt))
217                 {
218                   Lisp_Object presflag, carelt;
219                   carelt = Fcar (elt);
220                   /* If it is (if X Y), look at Y.  */
221                   if (EQ (carelt, Qif)
222                       && EQ (Fnthcdr (make_number (3), elt), Qnil))
223                     elt = Fnth (make_number (2), elt);
224                   /* If it is (when ... Y), look at Y.  */
225                   else if (EQ (carelt, Qwhen))
226                     {
227                       while (CONSP (XCDR (elt)))
228                         elt = XCDR (elt);
229                       elt = Fcar (elt);
230                     }
231
232                   /* If the function call we're looking at
233                      is a special preserved one, copy the
234                      whole expression for this argument.  */
235                   if (CONSP (elt))
236                     {
237                       presflag = Fmemq (Fcar (elt), preserved_fns);
238                       if (!NILP (presflag))
239                         Fsetcar (valtail, Fcar (intail));
240                     }
241                 }
242             }
243         }
244     }
245 }
246
247 DEFUN ("call-interactively", Fcall_interactively, Scall_interactively, 1, 3, 0,
248        doc: /* Call FUNCTION, reading args according to its interactive calling specs.
249 Return the value FUNCTION returns.
250 The function contains a specification of how to do the argument reading.
251 In the case of user-defined functions, this is specified by placing a call
252 to the function `interactive' at the top level of the function body.
253 See `interactive'.
254
255 Optional second arg RECORD-FLAG non-nil
256 means unconditionally put this command in the command-history.
257 Otherwise, this is done only if an arg is read using the minibuffer.
258
259 Optional third arg KEYS, if given, specifies the sequence of events to
260 supply, as a vector, if the command inquires which events were used to
261 invoke it.  If KEYS is omitted or nil, the return value of
262 `this-command-keys-vector' is used.  */)
263      (function, record_flag, keys)
264      Lisp_Object function, record_flag, keys;
265 {
266   Lisp_Object *args, *visargs;
267   Lisp_Object fun;
268   Lisp_Object specs;
269   Lisp_Object filter_specs;
270   Lisp_Object teml;
271   Lisp_Object up_event;
272   Lisp_Object enable;
273   int speccount = SPECPDL_INDEX ();
274
275   /* The index of the next element of this_command_keys to examine for
276      the 'e' interactive code.  */
277   int next_event;
278
279   Lisp_Object prefix_arg;
280   unsigned char *string;
281   unsigned char *tem;
282
283   /* If varies[i] > 0, the i'th argument shouldn't just have its value
284      in this call quoted in the command history.  It should be
285      recorded as a call to the function named callint_argfuns[varies[i]].  */
286   int *varies;
287
288   register int i, j;
289   int count, foo;
290   char prompt1[100];
291   char *tem1;
292   int arg_from_tty = 0;
293   struct gcpro gcpro1, gcpro2, gcpro3, gcpro4, gcpro5;
294   int key_count;
295   int record_then_fail = 0;
296
297   Lisp_Object save_this_command, save_last_command;
298   Lisp_Object save_this_original_command, save_real_this_command;
299
300   save_this_command = Vthis_command;
301   save_this_original_command = Vthis_original_command;
302   save_real_this_command = real_this_command;
303   save_last_command = current_kboard->Vlast_command;
304
305   if (NILP (keys))
306     keys = this_command_keys, key_count = this_command_key_count;
307   else
308     {
309       CHECK_VECTOR (keys);
310       key_count = XVECTOR (keys)->size;
311     }
312
313   /* Save this now, since use of minibuffer will clobber it. */
314   prefix_arg = Vcurrent_prefix_arg;
315
316   if (SYMBOLP (function))
317     enable = Fget (function, Qenable_recursive_minibuffers);
318   else
319     enable = Qnil;
320
321   fun = indirect_function (function);
322
323   specs = Qnil;
324   string = 0;
325   /* The idea of FILTER_SPECS is to provide away to
326      specify how to represent the arguments in command history.
327      The feature is not fully implemented.  */
328   filter_specs = Qnil;
329
330   /* If k or K discard an up-event, save it here so it can be retrieved with U */
331   up_event = Qnil;
332
333   /* Decode the kind of function.  Either handle it and return,
334      or go to `lose' if not interactive, or set either STRING or SPECS.  */
335
336   if (SUBRP (fun))
337     {
338       string = (unsigned char *) XSUBR (fun)->prompt;
339       if (!string)
340         {
341         lose:
342           wrong_type_argument (Qcommandp, function);
343         }
344     }
345   else if (COMPILEDP (fun))
346     {
347       if ((XVECTOR (fun)->size & PSEUDOVECTOR_SIZE_MASK) <= COMPILED_INTERACTIVE)
348         goto lose;
349       specs = XVECTOR (fun)->contents[COMPILED_INTERACTIVE];
350     }
351   else
352     {
353       Lisp_Object form;
354       GCPRO2 (function, prefix_arg);
355       form = Finteractive_form (function);
356       UNGCPRO;
357       if (CONSP (form))
358         specs = filter_specs = Fcar (XCDR (form));
359       else
360         goto lose;
361     }
362
363   /* If either SPECS or STRING is set to a string, use it.  */
364   if (STRINGP (specs))
365     {
366       /* Make a copy of string so that if a GC relocates specs,
367          `string' will still be valid.  */
368       string = (unsigned char *) alloca (SBYTES (specs) + 1);
369       bcopy (SDATA (specs), string,
370              SBYTES (specs) + 1);
371     }
372   else if (string == 0)
373     {
374       Lisp_Object input;
375       i = num_input_events;
376       input = specs;
377       /* Compute the arg values using the user's expression.  */
378       GCPRO2 (input, filter_specs);
379       specs = Feval (specs);
380       UNGCPRO;
381       if (i != num_input_events || !NILP (record_flag))
382         {
383           /* We should record this command on the command history.  */
384           Lisp_Object values;
385           /* Make a copy of the list of values, for the command history,
386              and turn them into things we can eval.  */
387           values = quotify_args (Fcopy_sequence (specs));
388           fix_command (input, values);
389           Vcommand_history
390             = Fcons (Fcons (function, values), Vcommand_history);
391
392           /* Don't keep command history around forever.  */
393           if (INTEGERP (Vhistory_length) && XINT (Vhistory_length) > 0)
394             {
395               teml = Fnthcdr (Vhistory_length, Vcommand_history);
396               if (CONSP (teml))
397                 XSETCDR (teml, Qnil);
398             }
399         }
400
401       Vthis_command = save_this_command;
402       Vthis_original_command = save_this_original_command;
403       real_this_command= save_real_this_command;
404       current_kboard->Vlast_command = save_last_command;
405
406       single_kboard_state ();
407       return apply1 (function, specs);
408     }
409
410   /* Here if function specifies a string to control parsing the defaults */
411
412   /* Set next_event to point to the first event with parameters.  */
413   for (next_event = 0; next_event < key_count; next_event++)
414     if (EVENT_HAS_PARAMETERS (XVECTOR (keys)->contents[next_event]))
415       break;
416
417   /* Handle special starting chars `*' and `@'.  Also `-'.  */
418   /* Note that `+' is reserved for user extensions.  */
419   while (1)
420     {
421       if (*string == '+')
422         error ("`+' is not used in `interactive' for ordinary commands");
423       else if (*string == '*')
424         {
425           string++;
426           if (!NILP (current_buffer->read_only))
427             {
428               if (!NILP (record_flag))
429                 {
430                   unsigned char *p = string;
431                   while (*p)
432                     {
433                       if (! (*p == 'r' || *p == 'p' || *p == 'P'
434                              || *p == '\n'))
435                         Fbarf_if_buffer_read_only ();
436                       p++;
437                     }
438                   record_then_fail = 1;
439                 }
440               else
441                 Fbarf_if_buffer_read_only ();
442             }
443         }
444       /* Ignore this for semi-compatibility with Lucid.  */
445       else if (*string == '-')
446         string++;
447       else if (*string == '@')
448         {
449           Lisp_Object event, tem;
450
451           event = (next_event < key_count
452                    ? XVECTOR (keys)->contents[next_event]
453                    : Qnil);
454           if (EVENT_HAS_PARAMETERS (event)
455               && (tem = XCDR (event), CONSP (tem))
456               && (tem = XCAR (tem), CONSP (tem))
457               && (tem = XCAR (tem), WINDOWP (tem)))
458             {
459               if (MINI_WINDOW_P (XWINDOW (tem))
460                   && ! (minibuf_level > 0 && EQ (tem, minibuf_window)))
461                 error ("Attempt to select inactive minibuffer window");
462
463               /* If the current buffer wants to clean up, let it.  */
464               if (!NILP (Vmouse_leave_buffer_hook))
465                 call1 (Vrun_hooks, Qmouse_leave_buffer_hook);
466
467               Fselect_window (tem, Qnil);
468             }
469           string++;
470         }
471       else break;
472     }
473
474   /* Count the number of arguments the interactive spec would have
475      us give to the function.  */
476   tem = string;
477   for (j = 0; *tem; j++)
478     {
479       /* 'r' specifications ("point and mark as 2 numeric args")
480          produce *two* arguments.  */
481       if (*tem == 'r') j++;
482       tem = (unsigned char *) index (tem, '\n');
483       if (tem)
484         tem++;
485       else
486         tem = (unsigned char *) "";
487     }
488   count = j;
489
490   args = (Lisp_Object *) alloca ((count + 1) * sizeof (Lisp_Object));
491   visargs = (Lisp_Object *) alloca ((count + 1) * sizeof (Lisp_Object));
492   varies = (int *) alloca ((count + 1) * sizeof (int));
493
494   for (i = 0; i < (count + 1); i++)
495     {
496       args[i] = Qnil;
497       visargs[i] = Qnil;
498       varies[i] = 0;
499     }
500
501   GCPRO5 (prefix_arg, function, *args, *visargs, up_event);
502   gcpro3.nvars = (count + 1);
503   gcpro4.nvars = (count + 1);
504
505   if (!NILP (enable))
506     specbind (Qenable_recursive_minibuffers, Qt);
507
508   tem = string;
509   for (i = 1; *tem; i++)
510     {
511       strncpy (prompt1, tem + 1, sizeof prompt1 - 1);
512       prompt1[sizeof prompt1 - 1] = 0;
513       tem1 = (char *) index (prompt1, '\n');
514       if (tem1) *tem1 = 0;
515
516       visargs[0] = build_string (prompt1);
517       if (index (prompt1, '%'))
518         callint_message = Fformat (i, visargs);
519       else
520         callint_message = visargs[0];
521
522       switch (*tem)
523         {
524         case 'a':               /* Symbol defined as a function */
525           visargs[i] = Fcompleting_read (callint_message,
526                                          Vobarray, Qfboundp, Qt,
527                                          Qnil, Qnil, Qnil, Qnil);
528           /* Passing args[i] directly stimulates compiler bug */
529           teml = visargs[i];
530           args[i] = Fintern (teml, Qnil);
531           break;
532
533         case 'b':               /* Name of existing buffer */
534           args[i] = Fcurrent_buffer ();
535           if (EQ (selected_window, minibuf_window))
536             args[i] = Fother_buffer (args[i], Qnil, Qnil);
537           args[i] = Fread_buffer (callint_message, args[i], Qt);
538           break;
539
540         case 'B':               /* Name of buffer, possibly nonexistent */
541           args[i] = Fread_buffer (callint_message,
542                                   Fother_buffer (Fcurrent_buffer (), Qnil, Qnil),
543                                   Qnil);
544           break;
545
546         case 'c':               /* Character */
547           args[i] = Fread_char (callint_message, Qnil, Qnil);
548           message1_nolog ((char *) 0);
549           /* Passing args[i] directly stimulates compiler bug */
550           teml = args[i];
551           visargs[i] = Fchar_to_string (teml);
552           break;
553
554         case 'C':               /* Command: symbol with interactive function */
555           visargs[i] = Fcompleting_read (callint_message,
556                                          Vobarray, Qcommandp,
557                                          Qt, Qnil, Qnil, Qnil, Qnil);
558