1 /* -----------------------------------------------------------------------------
2 * See the LICENSE file for information on copyright, usage and redistribution
3 * of SWIG, and the README file for authors - http://www.swig.org/release.html.
7 * This file manages named code fragments. Code fragments are typically
8 * used to hold helper-code that may or may not be included in the wrapper
9 * file (depending on what features are actually used in the interface).
11 * By using fragments, it's possible to greatly reduce the amount of
12 * wrapper code and to generate cleaner wrapper files.
13 * ----------------------------------------------------------------------------- */
15 char cvsroot_fragment_c[] = "$Id: fragment.c 9632 2007-01-03 20:58:19Z beazley $";
20 static Hash *fragments = 0;
21 static Hash *looking_fragments = 0;
25 /* -----------------------------------------------------------------------------
26 * Swig_fragment_register()
28 * Add a fragment. Use the original Node*, so, if something needs to be
29 * changed, lang.cxx doesn't nedd to be touched again.
30 * ----------------------------------------------------------------------------- */
32 void Swig_fragment_register(Node *fragment) {
33 if (Getattr(fragment, "emitonly")) {
34 Swig_fragment_emit(fragment);
37 String *name = Copy(Getattr(fragment, "value"));
38 String *type = Getattr(fragment, "type");
40 SwigType *rtype = SwigType_typedef_resolve_all(type);
41 String *mangle = Swig_string_mangle(type);
46 Printf(stdout, "register fragment %s %s\n", name, type);
49 fragments = NewHash();
51 if (!Getattr(fragments, name)) {
52 String *section = Copy(Getattr(fragment, "section"));
53 String *ccode = Copy(Getattr(fragment, "code"));
54 Hash *kwargs = Getattr(fragment, "kwargs");
55 Setmeta(ccode, "section", section);
57 Setmeta(ccode, "kwargs", kwargs);
59 Setattr(fragments, name, ccode);
61 Printf(stdout, "registering fragment %s %s\n", name, section);
69 /* -----------------------------------------------------------------------------
70 * Swig_fragment_emit()
73 * ----------------------------------------------------------------------------- */
76 char *char_index(char *str, char c) {
77 while (*str && (c != *str))
79 return (c == *str) ? str : 0;
82 void Swig_fragment_emit(Node *n) {
91 Swig_warning(WARN_FRAGMENT_NOT_FOUND, Getfile(n), Getline(n), "Fragment '%s' not found.\n", name);
96 name = Getattr(n, "value");
100 type = Getattr(n, "type");
102 mangle = Swig_string_mangle(type);
106 Printf(stdout, "looking fragment %s %s\n", name, type);
109 pc = char_index(tok, ',');
113 String *name = NewString(tok);
115 Append(name, mangle);
116 if (looking_fragments && Getattr(looking_fragments, name)) {
119 code = Getattr(fragments, name);
121 Printf(stdout, "looking subfragment %s\n", name);
122 if (code && (Strcmp(code, "ignore") != 0)) {
123 String *section = Getmeta(code, "section");
124 Hash *nn = Getmeta(code, "kwargs");
125 if (!looking_fragments)
126 looking_fragments = NewHash();
127 Setattr(looking_fragments, name, "1");
129 if (Equal(Getattr(nn, "name"), "fragment")) {
131 Printf(stdout, "emitting fragment %s %s\n", nn, type);
132 Setfile(nn, Getfile(n));
133 Setline(nn, Getline(n));
134 Swig_fragment_emit(nn);
136 nn = nextSibling(nn);
139 File *f = Swig_filebyname(section);
141 Swig_error(Getfile(code), Getline(code), "Bad section '%s' for code fragment '%s'\n", section, name);
144 Printf(stdout, "emitting subfragment %s %s\n", name, section);
146 Printf(f, "/* begin fragment %s */\n", name);
147 Printf(f, "%s\n", code);
149 Printf(f, "/* end fragment %s */\n\n", name);
150 Setattr(fragments, name, "ignore");
151 Delattr(looking_fragments, name);
154 } else if (!code && type) {
155 SwigType *rtype = SwigType_typedef_resolve_all(type);
156 if (!Equal(type, rtype)) {
157 String *name = Copy(Getattr(n, "value"));
158 String *mangle = Swig_string_mangle(type);
159 Append(name, mangle);
160 Setfile(name, Getfile(n));
161 Setline(name, Getline(n));
162 Swig_fragment_emit(name);
170 Swig_warning(WARN_FRAGMENT_NOT_FOUND, Getfile(n), Getline(n), "Fragment '%s' not found.\n", name);
172 tok = pc ? pc + 1 : 0;
174 pc = char_index(tok, ',');