2 This file is part of LilyPond, the GNU music typesetter.
4 Copyright (C) 1999--2014 Han-Wen Nienhuys <hanwen@xs4all.nl>
6 LilyPond is free software: you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation, either version 3 of the License, or
9 (at your option) any later version.
11 LilyPond is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with LilyPond. If not, see <http://www.gnu.org/licenses/>.
23 #include "lily-guile.hh"
28 Smobs are GUILEs mechanism of exporting C(++) objects to the Scheme
29 world. They are documented in the GUILE manual.
32 In LilyPond, C++ objects can be placed under the control of GUILE's
33 type system and garbage collection mechanism by inheriting from one
34 of several Smob base classes.
36 There are two types of smob objects.
38 1. Simple smobs are intended for simple objects like numbers:
39 immutable objects that can be copied without change of meaning.
41 To obtain an SCM version of a simple smob, use the member function
44 Simple smobs are created by deriving from Simple_smob<Classname>.
46 A simple smob is only optionally under the reign of the GUILE
47 garbage collector: its usual life time is that of a normal C++
48 object. While a smobbed_copy () is fully under control of the
49 garbage collector and will have its mark_smob function called during
50 garbage collection, an automatic variable of this type will not have
51 mark_smob called, but rather have its memory image in the call stack
52 scanned for contained non-immediate SCM values. Anything requiring
53 more complex mark_smob behavior is not suitable for a simple smob.
55 When you create a smobbed_copy, the _copy_ is fully managed by the
56 GUILE memory system. As a corollary, multiple smobbed_copy calls
57 yield multiple GUILE objects generally not eq? to each other.
59 2. Complex smobs are objects that have an identity. These objects
60 carry this identity in the form of a self_scm () method, which is a
61 SCM pointer to the object itself. Complex smobs are always under
62 control of the GUILE memory system.
64 The constructor for a complex smob should have 3 steps:
66 * initialize all SCM members to an immediate value (like SCM_EOL)
68 * call smobify_self ()
70 * initialize SCM members
74 Complex_smob::Complex_smob : public Smob<Complex_smob> () {
75 scm_member_ = SCM_EOL;
77 scm_member_ = <..what you want to store..>
80 after construction, the self_scm () field of a complex smob is
81 protected from Garbage Collection. This protection should be
82 removed once the object is put into another (reachable) Scheme data
85 Complex_smob *p = new Complex_smob;
86 list = scm_cons (p->self_scm (), list);
89 Since unprotect returns the SCM object itself, this particular case
92 Complex_smob *p = new Complex_smob;
93 list = scm_cons (p->unprotect (), list);
95 Complex smobs are created by deriving from Smob<Classname>.
99 Common public methods to C++ smob objects:
101 - unsmob (SCM x) - unpacks X and returns pointer to the C++ object,
102 or 0 if it has the wrong type. This can be used as a boolean
103 condition at C++ level.
104 - smob_p (SCM x) returns #t or #f at Scheme level.
108 For implementating a class, the following public members can be
109 provided in the top class itself:
111 - SCM equal_p (SCM a, SCM b) - compare A and B. Returns a Scheme
112 boolean. If the class does not define this function, equal? will
113 be equivalent to eq?. The function will only be called when both
114 objects are of the respective type and not eq? to each other.
116 - mark_smob () function, that calls scm_gc_mark () on all Scheme
117 objects in the class. If the class does not define this function,
118 it must not contain non-immediate Scheme values.
120 - a print_smob () function, that displays a representation for
121 debugging purposes. If the class does not define this function,
122 the output will be #<Classname> when printing.
124 - a static const type_p_name_[] string set to something like
125 "ly:grob?". When provided, an accordingly named function for
126 checking for the given smob type will be available in Scheme.
130 // Initialization class. Create a variable or static data member of
131 // this type at global scope (or creation will happen too late for
132 // Scheme initialization), initialising with a function to be called.
133 // Reference somewhere (like in the constructor of the containing
134 // class) to make sure the variable is actually instantiated.
139 Scm_init (void (*fun) (void))
141 add_scm_init_func (fun);
145 template <class Super>
148 static scm_t_bits smob_tag_;
149 static Scm_init scm_init_;
150 static void init (void);
151 static string smob_name_;
152 static Super *unchecked_unsmob (SCM s)
154 return reinterpret_cast<Super *> (SCM_SMOB_DATA (s));
157 // reference scm_init_ in smob_tag which is sure to be called. The
158 // constructor, in contrast, may not be called at all in classes
160 static scm_t_bits smob_tag () { (void) scm_init_; return smob_tag_; }
162 static SCM register_ptr (Super *p);
163 static Super *unregister_ptr (SCM obj);
165 // Those fallbacks are _only_ for internal use by Smob_base. They
166 // are characterized by no knowledge about the implemented type
167 // apart from the type's name. Overriding them as a template
168 // specialization is _not_ intended since a type-dependent
169 // implementation will in general need access to possibly private
170 // parts of the Super class. So any class-dependent override should
171 // be done by redefining the respective function in the Super class
172 // (where it will mask the private template member) rather than
173 // specializing a different template function/pointer.
175 // Since we consider those internal-only, two of them are actually
176 // implemented as literal zero constant. That allows us to fall
177 // back to GUILE's default implementation. Arguably the same could
178 // be done for print_smob, but the resulting default output of, say,
179 // #<Context_mod 0x7352414> would depend on memory layout, thus
180 // being unsuitable for regtest comparisons unless filtered.
182 static const int mark_smob = 0;
183 static const int equal_p = 0;
184 static const int smob_proc = 0;
185 static const int smob_proc_signature_ = 0;
186 static int print_smob (SCM, SCM, scm_print_state *);
187 static size_t free_smob (SCM obj)
189 delete Smob_base<Super>::unregister_ptr (obj);
192 // type_p_name_ can be overriden in the Super class with a static
193 // const char [] string. This requires both a declaration in the
194 // class as well as a single instantiation outside. Using a
195 // template specialization for supplying a different string name
196 // right in Smob_base<Super> itself seems tempting, but the C++
197 // rules would then require a specialization declaration at the
198 // class definition site as well as a specialization instantiation
199 // in a single compilation unit. That requires just as much source
200 // code maintenance while being harder to understand and quite
201 // trickier in its failure symptoms when things go wrong. So we
202 // just do things like with the other specializations.
203 static const int type_p_name_ = 0;
204 // This macro is used in the Super class definition for making a
205 // smob callable like a function. Declaration has to be public. It
206 // may be either be completed with a semicolon in which case a
207 // definition of the member function smob_proc has to be done
208 // outside of the class body, or the semicolon is left off and an
209 // inline function body is added immediately below. It would be
210 // nice if this were a non-static member function but it would seem
211 // tricky to do the required trampolining for unsmobbing the first
212 // argument of the callback and using it as a this pointer.
213 #define LY_DECLARE_SMOB_PROC(REQ, OPT, VAR, ARGLIST) \
214 static const int smob_proc_signature_ = ((REQ)<<8)|((OPT)<<4)|(VAR); \
215 static SCM smob_proc ARGLIST
216 // a separate LY_DEFINE_SMOB_PROC seems sort of pointless as it
217 // would just result in SCM CLASS::smob_proc ARGLIST
219 static bool is_smob (SCM s)
221 return SCM_SMOB_PREDICATE (smob_tag (), s);
223 static SCM smob_p (SCM s)
225 return is_smob (s) ? SCM_BOOL_T : SCM_BOOL_F;
227 static Super *unsmob (SCM s)
229 return is_smob (s) ? Super::unchecked_unsmob (s) : 0;
234 template <class Super>
235 class Simple_smob : public Smob_base<Super> {
237 SCM smobbed_copy () const
239 Super *p = new Super(*static_cast<const Super *> (this));
240 return Smob_base<Super>::register_ptr (p);
244 void protect_smob (SCM smob, SCM *prot_cons);
245 void unprotect_smob (SCM smob, SCM *prot_cons);
247 template <class Super>
248 class Smob : public Smob_base<Super> {
251 SCM protection_cons_;
253 SCM unprotected_smobify_self ()
255 self_scm_ = SCM_UNDEFINED;
256 self_scm_ = Smob_base<Super>::register_ptr (static_cast<Super *> (this));
261 protect_smob (self_scm_, &protection_cons_);
265 unprotect_smob (self_scm_, &protection_cons_);
268 void smobify_self () {
269 protection_cons_ = SCM_EOL;
270 self_scm_ = unprotected_smobify_self ();
273 SCM self_scm () const { return self_scm_; }
276 extern bool parsed_objects_should_be_dead;
279 static vector<parsed_dead *> elements;
284 data = SCM_UNDEFINED;
288 parsed_dead () : data (SCM_UNDEFINED)
290 elements.push_back (this);
292 void checkin (SCM arg) { data = arg; }
293 static SCM readout ();
297 #define ASSERT_LIVE_IS_ALLOWED(arg) \
299 static parsed_dead pass_here; \
300 if (parsed_objects_should_be_dead) \
301 pass_here.checkin (arg); \
304 #define ASSERT_LIVE_IS_ALLOWED(arg) do { (void)(arg); } \
309 #endif /* SMOBS_HH */