unofficial mirror of emacs-devel@gnu.org 
 help / color / mirror / code / Atom feed
* Declarations in macro definitions
@ 2002-03-17 12:34 Gerd Moellmann
  2002-03-18  9:05 ` Richard Stallman
  0 siblings, 1 reply; 8+ messages in thread
From: Gerd Moellmann @ 2002-03-17 12:34 UTC (permalink / raw)


Reading some Lisp code today which contained declarations for ZWEI
inspired me to the following simple hack.  It let's one declare
indentation and Edebug specs in a defmacro, like

        (defmacro foo ()
           (declare (indent INDENT) (debug DEBUG))
           ...)

where INDENT is used for `lisp-indent-function', and DEBUG is used for
`edebug-form-spec'.

What do people think?



*** eval.c	2002/03/17 11:10:24	1.182
--- eval.c	2002/03/17 12:17:12
***************
*** 91,96 ****
--- 91,97 ----
  Lisp_Object Qinhibit_quit, Vinhibit_quit, Vquit_flag;
  Lisp_Object Qand_rest, Qand_optional;
  Lisp_Object Qdebug_on_error;
+ Lisp_Object Qdeclare;
  
  /* This holds either the symbol `run-hooks' or nil.
     It is nil at an early stage of startup, and when Emacs
***************
*** 189,194 ****
--- 190,200 ----
  
  int handling_signal;
  
+ /* Function to process declarations in defmacro forms.  */
+ 
+ Lisp_Object Vmacro_declaration_function;
+ 
+ 
  static Lisp_Object funcall_lambda P_ ((Lisp_Object, int, Lisp_Object*));
  
  void
***************
*** 651,659 ****
  {
    register Lisp_Object fn_name;
    register Lisp_Object defn;
  
    fn_name = Fcar (args);
!   defn = Fcons (Qmacro, Fcons (Qlambda, Fcdr (args)));
    if (!NILP (Vpurify_flag))
      defn = Fpurecopy (defn);
    Ffset (fn_name, defn);
--- 657,695 ----
  {
    register Lisp_Object fn_name;
    register Lisp_Object defn;
+   Lisp_Object lambda_list, doc, tail;
  
    fn_name = Fcar (args);
!   lambda_list = Fcar (Fcdr (args));
!   tail = Fcdr (Fcdr (args));
! 
!   doc = Qnil;
!   if (STRINGP (Fcar (tail)))
!     {
!       doc = Fcar (tail);
!       tail = Fcdr (tail);
!     }
! 
!   while (CONSP (Fcar (tail))
! 	 && EQ (Fcar (Fcar (tail)), Qdeclare))
!     {
!       if (!NILP (Vmacro_declaration_function))
! 	{
! 	  struct gcpro gcpro1;
! 	  GCPRO1 (args);
! 	  call2 (Vmacro_declaration_function, fn_name, Fcar (tail));
! 	  UNGCPRO;
! 	}
!       
!       tail = Fcdr (tail);
!     }
! 
!   if (NILP (doc))
!     tail = Fcons (lambda_list, tail);
!   else
!     tail = Fcons (lambda_list, Fcons (doc, tail));
!   defn = Fcons (Qmacro, Fcons (Qlambda, tail));
!   
    if (!NILP (Vpurify_flag))
      defn = Fpurecopy (defn);
    Ffset (fn_name, defn);
***************
*** 3229,3234 ****
--- 3265,3273 ----
    Qmacro = intern ("macro");
    staticpro (&Qmacro);
  
+   Qdeclare = intern ("declare");
+   staticpro (&Qdeclare);
+   
    /* Note that the process handling also uses Qexit, but we don't want
       to staticpro it twice, so we just do it here.  */
    Qexit = intern ("exit");
***************
*** 3313,3318 ****
--- 3352,3365 ----
  Note that `debug-on-error', `debug-on-quit' and friends
  still determine whether to handle the particular condition.  */);
    Vdebug_on_signal = Qnil;
+ 
+   DEFVAR_LISP ("macro-declaration-function", &Vmacro_declaration_function,
+ 	       doc: /* Function to process declarations in a macro definition.
+ The function will be called with two args MACRO and DECL.
+ MACRO is the name of the macro being defined.
+ DECL is a list '(declare ...)' containing the declarations.
+ The value the function returns is not used.  */);
+   Vmacro_declaration_function = Qnil;
  
    Vrun_hooks = intern ("run-hooks");
    staticpro (&Vrun_hooks);



*** subr.el	2002/03/17 11:58:18	1.291
--- subr.el	2002/03/17 12:14:14
***************
*** 32,37 ****
--- 32,55 ----
  (defun custom-declare-variable-early (&rest arguments)
    (setq custom-declare-variable-list
  	(cons arguments custom-declare-variable-list)))
+ 
+ \f
+ (defun macro-declaration-function (macro decl)
+   "Process a declaration found in a macro definition.
+ This is set as the value of the variable `macro-declaration-function'.
+ MACRO is the name of the macro being defined.
+ DECL is a list `(declare ...)' containing the declarations.
+ The return value of this function is not used."
+   (dolist (d (cdr decl))
+     (cond ((and (consp d) (eq (car d) 'indent))
+ 	   (put macro 'lisp-indent-function (cadr d)))
+ 	  ((and (consp d) (eq (car d) 'debug))
+ 	   (put macro 'edebug-form-spec (cadr d)))
+ 	  (t
+ 	   (message "Unknown declaration %s" d)))))
+ 
+ (setq macro-declaration-function 'macro-declaration-function)
+ 
  \f
  ;;;; Lisp language features.
  

_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://mail.gnu.org/mailman/listinfo/emacs-devel


^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: Declarations in macro definitions
  2002-03-17 12:34 Declarations in macro definitions Gerd Moellmann
@ 2002-03-18  9:05 ` Richard Stallman
  2002-03-19 21:53   ` Gerd Moellmann
  0 siblings, 1 reply; 8+ messages in thread
From: Richard Stallman @ 2002-03-18  9:05 UTC (permalink / raw)
  Cc: emacs-devel

I like the the idea of putting this info in a macro definition, but I
don't think `declare' is a good name for it.  That name is too general
to fit this rather specific meaning.

I would rather imitate `interactive' and define separate no-op
functions for these purposes.  The things that want to use them
can search the macro definition for them.

(ISTR that someone was implementing this for edebug a few months
ago--in fact, I thought it had been installed already.

_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://mail.gnu.org/mailman/listinfo/emacs-devel


^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: Declarations in macro definitions
  2002-03-18  9:05 ` Richard Stallman
@ 2002-03-19 21:53   ` Gerd Moellmann
  2002-03-19 22:18     ` Stefan Monnier
                       ` (2 more replies)
  0 siblings, 3 replies; 8+ messages in thread
From: Gerd Moellmann @ 2002-03-19 21:53 UTC (permalink / raw)
  Cc: emacs-devel

Richard Stallman <rms@gnu.org> writes:

> I like the the idea of putting this info in a macro definition, but I
> don't think `declare' is a good name for it.  That name is too general
> to fit this rather specific meaning.

(But it's familiar to Lisp programmers for a long time...)

> I would rather imitate `interactive' and define separate no-op
> functions for these purposes.  The things that want to use them
> can search the macro definition for them.
> 
> (ISTR that someone was implementing this for edebug a few months
> ago--in fact, I thought it had been installed already.

In that case I guess my patch won't be needed.

_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://mail.gnu.org/mailman/listinfo/emacs-devel


^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: Declarations in macro definitions
  2002-03-19 21:53   ` Gerd Moellmann
@ 2002-03-19 22:18     ` Stefan Monnier
  2002-03-20 12:11       ` Gerd Moellmann
  2002-03-20 13:44     ` Juanma Barranquero
  2002-03-21  9:04     ` Richard Stallman
  2 siblings, 1 reply; 8+ messages in thread
From: Stefan Monnier @ 2002-03-19 22:18 UTC (permalink / raw)
  Cc: rms, emacs-devel

> > I like the the idea of putting this info in a macro definition, but I
> > don't think `declare' is a good name for it.  That name is too general
> > to fit this rather specific meaning.
> 
> (But it's familiar to Lisp programmers for a long time...)

Agreed.

> > I would rather imitate `interactive' and define separate no-op
> > functions for these purposes.  The things that want to use them
> > can search the macro definition for them.
> > 
> > (ISTR that someone was implementing this for edebug a few months
> > ago--in fact, I thought it had been installed already.
> 
> In that case I guess my patch won't be needed.

I don't think that there is anything already installed that does what
you patch does.  Maybe someone has been working on this, but at least
I haven't heard anything conclusive.


	Stefan


_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://mail.gnu.org/mailman/listinfo/emacs-devel


^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: Declarations in macro definitions
  2002-03-19 22:18     ` Stefan Monnier
@ 2002-03-20 12:11       ` Gerd Moellmann
  0 siblings, 0 replies; 8+ messages in thread
From: Gerd Moellmann @ 2002-03-20 12:11 UTC (permalink / raw)
  Cc: rms, emacs-devel

> > In that case I guess my patch won't be needed.
> 
> I don't think that there is anything already installed that does what
> you patch does.  Maybe someone has been working on this, but at least
> I haven't heard anything conclusive.

In case the patch might be useful anyway---I see that I forgot to send
the diff for bytecomp.el (the thing would be pretty useless if it
didn't work with compiled code :-).  Here it is:

*** bytecomp.el	2002/03/13 23:05:30	2.94
--- bytecomp.el	2002/03/20 12:06:35
***************
*** 1980,1985 ****
--- 1980,2001 ----
  	       (stringp (car-safe (cdr-safe (cdr-safe body)))))
  	  (byte-compile-warn "probable `\"' without `\\' in doc string of %s"
  			     (nth 1 form))))
+ 
+     ;; Generate code for declarations in macro definitions.
+     ;; Remove declarations from the body of the macro definition.
+     (when macrop
+       (let ((tail (nthcdr 2 form)))
+ 	(when (stringp (car (cdr tail)))
+ 	  (setq tail (cdr tail)))
+ 	(while (and (consp (car (cdr tail)))
+ 		    (eq (car (car (cdr tail))) 'declare))
+ 	  (let ((declaration (car (cdr tail))))
+ 	    (setcdr tail (cdr (cdr tail)))
+ 	    (princ `(if macro-declaration-function
+ 			(funcall macro-declaration-function
+ 				 ',name ',declaration))
+ 		   outbuffer)))))
+       
      (let* ((new-one (byte-compile-lambda (cons 'lambda (nthcdr 2 form))))
  	   (code (byte-compile-byte-code-maker new-one)))
        (if this-one

_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://mail.gnu.org/mailman/listinfo/emacs-devel


^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: Declarations in macro definitions
  2002-03-19 21:53   ` Gerd Moellmann
  2002-03-19 22:18     ` Stefan Monnier
@ 2002-03-20 13:44     ` Juanma Barranquero
  2002-03-21  9:04     ` Richard Stallman
  2 siblings, 0 replies; 8+ messages in thread
From: Juanma Barranquero @ 2002-03-20 13:44 UTC (permalink / raw)
  Cc: emacs-devel


On 19 Mar 2002 22:53:14 +0100, gerd.moellmann@t-online.de (Gerd Moellmann) wrote:

> (But it's familiar to Lisp programmers for a long time...)

Certainly, and it is always posible that (declare ...) be expanded in
the future to support other kinds of declarations...

> In that case I guess my patch won't be needed.

Yours (or equivalent) would be very welcome. And yours is already here.


                                                           /L/e/k/t/u


_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://mail.gnu.org/mailman/listinfo/emacs-devel


^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: Declarations in macro definitions
  2002-03-19 21:53   ` Gerd Moellmann
  2002-03-19 22:18     ` Stefan Monnier
  2002-03-20 13:44     ` Juanma Barranquero
@ 2002-03-21  9:04     ` Richard Stallman
  2002-03-21 11:12       ` Gerd Moellmann
  2 siblings, 1 reply; 8+ messages in thread
From: Richard Stallman @ 2002-03-21  9:04 UTC (permalink / raw)
  Cc: emacs-devel

    > I like the the idea of putting this info in a macro definition, but I
    > don't think `declare' is a good name for it.  That name is too general
    > to fit this rather specific meaning.

    (But it's familiar to Lisp programmers for a long time...)

My memory of `declare' is different (and probably comes from Maclisp
in the 70s).  Could you tell me how you have seen it used?

    > (ISTR that someone was implementing this for edebug a few months
    > ago--in fact, I thought it had been installed already.

    In that case I guess my patch won't be needed.

That code has not been installed--I checked that after I saw your
message.  I think we never got papers for it.


That code is more elegant in some ways, because the edebug form spec
is stored in the macro definition itself and never goes in any other
data base.  However, your code is much simpler.  Given that anonymous
macros are not useful, perhaps your simple approach is better.


_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://mail.gnu.org/mailman/listinfo/emacs-devel


^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: Declarations in macro definitions
  2002-03-21  9:04     ` Richard Stallman
@ 2002-03-21 11:12       ` Gerd Moellmann
  0 siblings, 0 replies; 8+ messages in thread
From: Gerd Moellmann @ 2002-03-21 11:12 UTC (permalink / raw)
  Cc: emacs-devel

Richard Stallman <rms@gnu.org> writes:

>     > I like the the idea of putting this info in a macro definition, but I
>     > don't think `declare' is a good name for it.  That name is too general
>     > to fit this rather specific meaning.
> 
>     (But it's familiar to Lisp programmers for a long time...)
> 
> My memory of `declare' is different (and probably comes from Maclisp
> in the 70s).  Could you tell me how you have seen it used?

This is an excerpt from some actual CL code:

  (defmacro mlet (vars value &body body)
    #+lispm(declare (compiler:do-not-record-macroexpansions)
                    (zwei:indentation 1 3 2 1))
    `(multiple-value-bind ,vars ,value ,@body))

I haven't seen anything for the debugger yet.

[What I meant by ``familiar'' is not that (contemporary Common:-) Lisp
programmers are specifically used to using `declare' for specifying
indentation (I'm not aware that/if they are), but that CL programmers
are used to `declare' in general, and to implementation-defined
declaration specifiers in particular.]

>     > (ISTR that someone was implementing this for edebug a few months
>     > ago--in fact, I thought it had been installed already.
> 
>     In that case I guess my patch won't be needed.
> 
> That code has not been installed--I checked that after I saw your
> message.  I think we never got papers for it.
> 
> 
> That code is more elegant in some ways, because the edebug form spec
> is stored in the macro definition itself and never goes in any other
> data base.  However, your code is much simpler.  Given that anonymous
> macros are not useful, perhaps your simple approach is better.

I haven't seen the other code, so I cannot compare the two.  The
simplicity of the declare approach you mentioned yourself, which made
it easy to handle both Edebug specs and indentation without touching
Edebug or the Lisp indentation code.

I like that simplicity, but on the other hand, I don't have strong
feelings about this.  Just tell me if you want it installed at some
point.

_______________________________________________
Emacs-devel mailing list
Emacs-devel@gnu.org
http://mail.gnu.org/mailman/listinfo/emacs-devel


^ permalink raw reply	[flat|nested] 8+ messages in thread

end of thread, other threads:[~2002-03-21 11:12 UTC | newest]

Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2002-03-17 12:34 Declarations in macro definitions Gerd Moellmann
2002-03-18  9:05 ` Richard Stallman
2002-03-19 21:53   ` Gerd Moellmann
2002-03-19 22:18     ` Stefan Monnier
2002-03-20 12:11       ` Gerd Moellmann
2002-03-20 13:44     ` Juanma Barranquero
2002-03-21  9:04     ` Richard Stallman
2002-03-21 11:12       ` Gerd Moellmann

Code repositories for project(s) associated with this public inbox

	https://git.savannah.gnu.org/cgit/emacs.git

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).