aboutsummaryrefslogtreecommitdiffstats
path: root/src/data.c
diff options
context:
space:
mode:
authorPhilipp Stephani2017-05-13 16:29:40 +0200
committerPhilipp Stephani2017-05-20 15:32:52 +0200
commit31fded0370c3aa6d2c4370cae21cdb7475873483 (patch)
treeacf2a7fda2d1b801b3aaf4cc9f168d3b6da77ec0 /src/data.c
parent6c7bf039e9c2e6daf548a95204740eeaf4c61abd (diff)
downloademacs-31fded0370c3aa6d2c4370cae21cdb7475873483.tar.gz
emacs-31fded0370c3aa6d2c4370cae21cdb7475873483.zip
Reimplement module functions
Instead of a lambda, create a new type containing all data required to call the function, and support it in the evaluator. Because this type now also needs to store the function documentation, it is too big for Lisp_Misc; use a pseudovector instead. That also has the nice benefit that we don't have to add special support to the garbage collector. Since the new type is user-visible, give it a predicate. Now we can easily support 'help-function-args' and 'func-arity'; add unit tests for these. * src/lisp.h (allocate_module_function, MODULE_FUNCTIONP) (XMODULE_FUNCTION): New pseudovector type 'module function'. * src/eval.c (FUNCTIONP): Also treat module functions as functions. (funcall_lambda, Ffuncall, eval_sub): Add support for calling module functions. (Ffunc_arity): Add support for detecting the arity of module functions. * src/emacs-module.c (module_make_function): Adapt to new structure. Return module function object directly instead of wrapping it in a lambda; remove FIXME. (funcall_module): New function to call module functions. Replaces `internal--module-call' and is called directly from eval.c. (syms_of_module): Remove internal helper function, which is no longer needed. (module_function_arity): New helper function. * src/data.c (Ftype_of): Adapt to new implementation. (Fmodule_function_p, syms_of_data): New user-visible function. Now that module functions are first-class objects, they deserve a predicate. Define it even if not compiled with --enable-modules so that Lisp code doesn't have to check for the function's existence. * src/doc.c (Fdocumentation): Support module functions. * src/print.c (print_object): Adapt to new implementation. * src/alloc.c (mark_object): Specialized garbage collector support is no longer needed. * lisp/help.el (help-function-arglist): Support module functions. While there, simplify the arity calculation by using `func-arity', which does the right thing for all kinds of functions. * test/data/emacs-module/mod-test.c: Amend docstring so we can test the argument list. * test/src/emacs-module-tests.el (mod-test-sum-docstring): Adapt to new docstring. (mod-test-non-local-exit-signal-test): Because `internal--module-call' is gone, the backtrace has changed and no longer leaks the implementation. (module--func-arity): New test for `func-arity'. (module--help-function-arglist): New test for `help-function-arglist'.
Diffstat (limited to 'src/data.c')
-rw-r--r--src/data.c13
1 files changed, 11 insertions, 2 deletions
diff --git a/src/data.c b/src/data.c
index 4242b90e628..25859105ee0 100644
--- a/src/data.c
+++ b/src/data.c
@@ -233,8 +233,6 @@ for example, (type-of 1) returns `integer'. */)
233 case Lisp_Misc_Finalizer: 233 case Lisp_Misc_Finalizer:
234 return Qfinalizer; 234 return Qfinalizer;
235#ifdef HAVE_MODULES 235#ifdef HAVE_MODULES
236 case Lisp_Misc_Module_Function:
237 return Qmodule_function;
238 case Lisp_Misc_User_Ptr: 236 case Lisp_Misc_User_Ptr:
239 return Quser_ptr; 237 return Quser_ptr;
240#endif 238#endif
@@ -278,6 +276,8 @@ for example, (type-of 1) returns `integer'. */)
278 else 276 else
279 return t; 277 return t;
280 } 278 }
279 case PVEC_MODULE_FUNCTION:
280 return Qmodule_function;
281 /* "Impossible" cases. */ 281 /* "Impossible" cases. */
282 case PVEC_XWIDGET: 282 case PVEC_XWIDGET:
283 case PVEC_OTHER: 283 case PVEC_OTHER:
@@ -494,6 +494,14 @@ DEFUN ("byte-code-function-p", Fbyte_code_function_p, Sbyte_code_function_p,
494 return Qnil; 494 return Qnil;
495} 495}
496 496
497DEFUN ("module-function-p", Fmodule_function_p, Smodule_function_p, 1, 1, NULL,
498 doc: /* Return t if OBJECT is a function loaded from a dynamic module. */
499 attributes: const)
500 (Lisp_Object object)
501{
502 return MODULE_FUNCTIONP (object) ? Qt : Qnil;
503}
504
497DEFUN ("char-or-string-p", Fchar_or_string_p, Schar_or_string_p, 1, 1, 0, 505DEFUN ("char-or-string-p", Fchar_or_string_p, Schar_or_string_p, 1, 1, 0,
498 doc: /* Return t if OBJECT is a character or a string. */ 506 doc: /* Return t if OBJECT is a character or a string. */
499 attributes: const) 507 attributes: const)
@@ -3793,6 +3801,7 @@ syms_of_data (void)
3793 defsubr (&Smarkerp); 3801 defsubr (&Smarkerp);
3794 defsubr (&Ssubrp); 3802 defsubr (&Ssubrp);
3795 defsubr (&Sbyte_code_function_p); 3803 defsubr (&Sbyte_code_function_p);
3804 defsubr (&Smodule_function_p);
3796 defsubr (&Schar_or_string_p); 3805 defsubr (&Schar_or_string_p);
3797 defsubr (&Sthreadp); 3806 defsubr (&Sthreadp);
3798 defsubr (&Smutexp); 3807 defsubr (&Smutexp);