static SCM equal_p (SCM, SCM);
int print_smob (SCM, scm_print_state *);
static int print_trampoline (SCM, SCM, scm_print_state *);
+ static void smob_proc_init (scm_t_bits) { };
// type_p_name_ can be overriden in the Super class with a static
// const char [] string. This requires both a declaration in the
static const int type_p_name_ = 0;
// LY_DECLARE_SMOB_PROC is used in the Super class definition for
- // making a smob callable like a function. Declaration has to be
- // public. It may be either be completed with a semicolon in which
- // case a definition of the member function smob_proc has to be done
- // outside of the class body, or the semicolon is left off and an
- // inline function body is added immediately below. It would be
- // nice if this were a non-static member function but it would seem
- // tricky to do the required trampolining for unsmobbing the first
- // argument of the callback and using it as a this pointer.
-#define LY_DECLARE_SMOB_PROC(REQ, OPT, VAR, ARGLIST) \
- static const int smob_proc_signature_ = ((REQ)<<8)|((OPT)<<4)|(VAR); \
- static SCM smob_proc ARGLIST
-
- // a separate LY_DEFINE_SMOB_PROC seems sort of pointless as it
- // would just result in SCM CLASS::smob_proc ARGLIST
- //
- // The default case without function functionality is recognized by
- // smob_proc_signature being -1.
- static const int smob_proc = 0;
- static const int smob_proc_signature_ = -1;
+ // making a smob callable like a function. Its first argument is a
+ // function member pointer constant, to a function taking the
+ // correct number of SCM arguments and returning SCM. The function
+ // itself has to be defined separately.
+
+#define LY_DECLARE_SMOB_PROC(PMF, REQ, OPT, VAR) \
+ static void smob_proc_init (scm_t_bits smob_tag) \
+ { \
+ scm_set_smob_apply (smob_tag, \
+ (scm_t_subr)smob_trampoline<PMF>, \
+ REQ, OPT, VAR); \
+ }
+
+ // Well, function template argument packs are a C++11 feature. So
+ // we just define a bunch of trampolines manually.
+ template <SCM (Super::*pmf)(void)>
+ static SCM smob_trampoline (SCM self)
+ {
+ return (Super::unchecked_unsmob (self)->*pmf)();
+ }
+ template <SCM (Super::*pmf)(SCM)>
+ static SCM smob_trampoline (SCM self, SCM arg1)
+ {
+ return (Super::unchecked_unsmob (self)->*pmf)(arg1);
+ }
+ template <SCM (Super::*pmf)(SCM, SCM)>
+ static SCM smob_trampoline (SCM self, SCM arg1, SCM arg2)
+ {
+ return (Super::unchecked_unsmob (self)->*pmf)(arg1, arg2);
+ }
+ template <SCM (Super::*pmf)(SCM, SCM, SCM)>
+ static SCM smob_trampoline (SCM self, SCM arg1, SCM arg2, SCM arg3)
+ {
+ return (Super::unchecked_unsmob (self)->*pmf)(arg1, arg2, arg3);
+ }
public:
static bool is_smob (SCM s)