Merge branch 'master' into doxygen

The way Python docstrings are indented has changed on master, so use the
standard inspect module in Python autodoc unit test to ignore the differences
in their indentation level between -builtin and non-builtin cases to make the
test still pass with the branch version, which avoids the use of different
(but almost identical) values in the test itself.
This commit is contained in:
Vadim Zeitlin 2016-12-05 02:14:51 +01:00
commit e668c47b70
1094 changed files with 39390 additions and 11483 deletions

View file

@ -58,6 +58,7 @@ extern "C" {
/* util.c */
extern void Swig_cparse_replace_descriptor(String *s);
extern SwigType *Swig_cparse_smartptr(Node *n);
extern void cparse_normalize_void(Node *);
extern Parm *Swig_cparse_parm(String *s);
extern ParmList *Swig_cparse_parms(String *s, Node *file_line_node);
@ -77,4 +78,7 @@ extern "C" {
#define SWIG_WARN_NODE_END(Node) \
if (wrnfilter) Swig_warnfilter(wrnfilter,0); \
}
#define COMPOUND_EXPR_VAL(dtype) \
((dtype).type == T_CHAR || (dtype).type == T_WCHAR ? (dtype).rawval : (dtype).val)
#endif

View file

@ -13,11 +13,14 @@
* some point. Beware.
* ----------------------------------------------------------------------------- */
/*
Removed until we know more about the min versions of Bison and Yacc required for this
to work, see Byacc man page: http://invisible-island.net/byacc/manpage/yacc.html
/* There are 6 known shift-reduce conflicts in this file, fail compilation if any
more are introduced.
Please don't increase the number of the conflicts if at all possible. And if
you really have no choice but to do it, make sure you clearly document each
new conflict in this file.
*/
%expect 6
*/
%{
#define yylex yylex
@ -160,6 +163,11 @@ static Node *copy_node(Node *n) {
Setattr(nn, key, k.item);
continue;
}
/* defaultargs will be patched back in later in update_defaultargs() */
if (strcmp(ckey,"defaultargs") == 0) {
Setattr(nn, "needs_defaultargs", "1");
continue;
}
/* Looks okay. Just copy the data using Copy */
ci = Copy(k.item);
Setattr(nn, key, ci);
@ -511,18 +519,24 @@ static void add_symbols(Node *n) {
SetFlag(n,"feature:ignore");
}
}
if (only_csymbol || GetFlag(n,"feature:ignore")) {
if (only_csymbol || GetFlag(n,"feature:ignore") || strncmp(Char(symname),"$ignore",7) == 0) {
/* Only add to C symbol table and continue */
Swig_symbol_add(0, n);
} else if (strncmp(Char(symname),"$ignore",7) == 0) {
char *c = Char(symname)+7;
SetFlag(n,"feature:ignore");
if (strlen(c)) {
SWIG_WARN_NODE_BEGIN(n);
Swig_warning(0,Getfile(n), Getline(n), "%s\n",c+1);
SWIG_WARN_NODE_END(n);
if (!only_csymbol && !GetFlag(n, "feature:ignore")) {
/* Print the warning attached to $ignore name, if any */
char *c = Char(symname) + 7;
if (strlen(c)) {
SWIG_WARN_NODE_BEGIN(n);
Swig_warning(0,Getfile(n), Getline(n), "%s\n",c+1);
SWIG_WARN_NODE_END(n);
}
/* If the symbol was ignored via "rename" and is visible, set also feature:ignore*/
SetFlag(n, "feature:ignore");
}
if (!GetFlag(n, "feature:ignore") && Strcmp(symname,"$ignore") == 0) {
/* Add feature:ignore if the symbol was explicitely ignored, regardless of visibility */
SetFlag(n, "feature:ignore");
}
Swig_symbol_add(0, n);
} else {
Node *c;
if ((wrn) && (Len(wrn))) {
@ -694,6 +708,32 @@ static void add_symbols_copy(Node *n) {
}
}
/* Add in the "defaultargs" attribute for functions in instantiated templates.
* n should be any instantiated template (class or start of linked list of functions). */
static void update_defaultargs(Node *n) {
if (n) {
Node *firstdefaultargs = n;
update_defaultargs(firstChild(n));
n = nextSibling(n);
/* recursively loop through nodes of all types, but all we really need are the overloaded functions */
while (n) {
update_defaultargs(firstChild(n));
if (!Getattr(n, "defaultargs")) {
if (Getattr(n, "needs_defaultargs")) {
Setattr(n, "defaultargs", firstdefaultargs);
Delattr(n, "needs_defaultargs");
} else {
firstdefaultargs = n;
}
} else {
/* Functions added in with %extend (for specialized template classes) will already have default args patched up */
assert(Getattr(n, "defaultargs") == firstdefaultargs);
}
n = nextSibling(n);
}
}
}
/* Check a set of declarations to see if any are pure-abstract */
static List *pure_abstracts(Node *n) {
@ -2632,6 +2672,7 @@ template_directive: SWIGTEMPLATE LPAREN idstringopt RPAREN idcolonnt LESSTHAN va
{
Node *nn = n;
Node *linklistend = 0;
Node *linkliststart = 0;
while (nn) {
Node *templnode = 0;
if (Strcmp(nodeType(nn),"template") == 0) {
@ -2713,7 +2754,7 @@ template_directive: SWIGTEMPLATE LPAREN idstringopt RPAREN idcolonnt LESSTHAN va
}
templnode = copy_node(nn);
update_nested_classes(templnode); /* update classes nested withing template */
update_nested_classes(templnode); /* update classes nested within template */
/* We need to set the node name based on name used to instantiate */
Setattr(templnode,"name",tname);
Delete(tname);
@ -2787,7 +2828,11 @@ template_directive: SWIGTEMPLATE LPAREN idstringopt RPAREN idcolonnt LESSTHAN va
Swig_symbol_setscope(csyms);
}
/* Merge in %extend methods for this class */
/* Merge in %extend methods for this class.
This only merges methods within %extend for a template specialized class such as
template<typename T> class K {}; %extend K<int> { ... }
The copy_node() call above has already added in the generic %extend methods such as
template<typename T> class K {}; %extend K { ... } */
/* !!! This may be broken. We may have to add the
%extend methods at the beginning of the class */
@ -2830,6 +2875,8 @@ template_directive: SWIGTEMPLATE LPAREN idstringopt RPAREN idcolonnt LESSTHAN va
}
/* all the overloaded templated functions are added into a linked list */
if (!linkliststart)
linkliststart = templnode;
if (nscope_inner) {
/* non-global namespace */
if (templnode) {
@ -2850,6 +2897,7 @@ template_directive: SWIGTEMPLATE LPAREN idstringopt RPAREN idcolonnt LESSTHAN va
}
nn = Getattr(nn,"sym:nextSibling"); /* repeat for overloaded templated functions. If a templated class there will never be a sibling. */
}
update_defaultargs(linkliststart);
}
Swig_symbol_setscope(tscope);
Delete(Namespaceprefix);
@ -2916,28 +2964,26 @@ c_declaration : c_decl {
SWIG_WARN_NODE_END($$);
}
| USING idcolon EQUAL type plain_declarator SEMI {
$$ = new_node("using");
/* Convert using statement to a typedef statement */
$$ = new_node("cdecl");
Setattr($$,"type",$4);
Setattr($$,"storage","typedef");
Setattr($$,"name",$2);
SwigType_push($4,$5.type);
Setattr($$,"uname",$4);
Setattr($$,"decl",$5.type);
SetFlag($$,"typealias");
add_symbols($$);
SWIG_WARN_NODE_BEGIN($$);
Swig_warning(WARN_CPP11_ALIAS_DECLARATION, cparse_file, cparse_line, "The 'using' keyword in type aliasing is not fully supported yet.\n");
SWIG_WARN_NODE_END($$);
$$ = 0; /* TODO - ignored for now */
}
| TEMPLATE LESSTHAN template_parms GREATERTHAN USING idcolon EQUAL type plain_declarator SEMI {
$$ = new_node("using");
/* Convert alias template to a "template" typedef statement */
$$ = new_node("template");
Setattr($$,"type",$8);
Setattr($$,"storage","typedef");
Setattr($$,"name",$6);
SwigType_push($8,$9.type);
Setattr($$,"uname",$8);
Setattr($$,"decl",$9.type);
Setattr($$,"templateparms",$3);
Setattr($$,"templatetype","cdecl");
SetFlag($$,"aliastemplate");
add_symbols($$);
SWIG_WARN_NODE_BEGIN($$);
Swig_warning(WARN_CPP11_ALIAS_TEMPLATE, cparse_file, cparse_line, "The 'using' keyword in template aliasing is not fully supported yet.\n");
SWIG_WARN_NODE_END($$);
$$ = 0; /* TODO - ignored for now */
}
;
@ -2957,6 +3003,14 @@ c_decl : storage_class type declarator initializer c_decl_tail {
Setattr($$,"throws",$4.throws);
Setattr($$,"throw",$4.throwf);
Setattr($$,"noexcept",$4.nexcept);
if ($4.val && $4.type) {
/* store initializer type as it might be different to the declared type */
SwigType *valuetype = NewSwigType($4.type);
if (Len(valuetype) > 0)
Setattr($$,"valuetype",valuetype);
else
Delete(valuetype);
}
if (!$5) {
if (Len(scanner_ccode)) {
String *code = Copy(scanner_ccode);
@ -2984,8 +3038,8 @@ c_decl : storage_class type declarator initializer c_decl_tail {
matches that of the declaration, then we will allow it. Otherwise, delete. */
String *p = Swig_scopename_prefix($3.id);
if (p) {
if ((Namespaceprefix && Strcmp(p,Namespaceprefix) == 0) ||
(inclass && Strcmp(p,Classprefix) == 0)) {
if ((Namespaceprefix && Strcmp(p, Namespaceprefix) == 0) ||
(Classprefix && Strcmp(p, Classprefix) == 0)) {
String *lstr = Swig_scopename_last($3.id);
Setattr($$,"name",lstr);
Delete(lstr);
@ -3040,8 +3094,8 @@ c_decl : storage_class type declarator initializer c_decl_tail {
if (Strstr($3.id,"::")) {
String *p = Swig_scopename_prefix($3.id);
if (p) {
if ((Namespaceprefix && Strcmp(p,Namespaceprefix) == 0) ||
(inclass && Strcmp(p,Classprefix) == 0)) {
if ((Namespaceprefix && Strcmp(p, Namespaceprefix) == 0) ||
(Classprefix && Strcmp(p, Classprefix) == 0)) {
String *lstr = Swig_scopename_last($3.id);
Setattr($$,"name",lstr);
Delete(lstr);
@ -3677,6 +3731,7 @@ cpp_class_decl : storage_class cpptype idcolon inherit LBRACE {
Swig_symbol_setscope(cscope);
Delete(Namespaceprefix);
Namespaceprefix = Swig_symbol_qualifiedscopename(0);
Classprefix = currentOuterClass ? Getattr(currentOuterClass, "Classprefix") : 0;
}
/* An unnamed struct, possibly with a typedef */
@ -3713,7 +3768,7 @@ cpp_class_decl : storage_class cpptype idcolon inherit LBRACE {
cparse_start_line = cparse_line;
currentOuterClass = $<node>$;
inclass = 1;
Classprefix = NewStringEmpty();
Classprefix = 0;
Delete(Namespaceprefix);
Namespaceprefix = Swig_symbol_qualifiedscopename(0);
/* save the structure declaration to make a typedef for it later*/
@ -3726,6 +3781,7 @@ cpp_class_decl : storage_class cpptype idcolon inherit LBRACE {
String *name = 0;
Node *n;
Classprefix = 0;
(void)$<node>5;
$$ = currentOuterClass;
currentOuterClass = Getattr($$, "nested:outer");
if (!currentOuterClass)
@ -3823,6 +3879,7 @@ cpp_class_decl : storage_class cpptype idcolon inherit LBRACE {
Delete($$);
$$ = $6; /* pass member list to outer class/namespace (instead of self)*/
}
Classprefix = currentOuterClass ? Getattr(currentOuterClass, "Classprefix") : 0;
}
;
@ -5871,7 +5928,7 @@ definetype : { /* scanner_check_typedef(); */ } expr {
if ($$.type == T_STRING) {
$$.rawval = NewStringf("\"%(escape)s\"",$$.val);
} else if ($$.type != T_CHAR && $$.type != T_WSTRING && $$.type != T_WCHAR) {
$$.rawval = 0;
$$.rawval = NewStringf("%s", $$.val);
}
$$.qualifier = 0;
$$.bitfield = 0;
@ -6180,81 +6237,81 @@ exprnum : NUM_INT { $$ = $1; }
;
exprcompound : expr PLUS expr {
$$.val = NewStringf("%s+%s",$1.val,$3.val);
$$.val = NewStringf("%s+%s", COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote($1.type,$3.type);
}
| expr MINUS expr {
$$.val = NewStringf("%s-%s",$1.val,$3.val);
$$.val = NewStringf("%s-%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote($1.type,$3.type);
}
| expr STAR expr {
$$.val = NewStringf("%s*%s",$1.val,$3.val);
$$.val = NewStringf("%s*%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote($1.type,$3.type);
}
| expr SLASH expr {
$$.val = NewStringf("%s/%s",$1.val,$3.val);
$$.val = NewStringf("%s/%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote($1.type,$3.type);
}
| expr MODULO expr {
$$.val = NewStringf("%s%%%s",$1.val,$3.val);
$$.val = NewStringf("%s%%%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote($1.type,$3.type);
}
| expr AND expr {
$$.val = NewStringf("%s&%s",$1.val,$3.val);
$$.val = NewStringf("%s&%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote($1.type,$3.type);
}
| expr OR expr {
$$.val = NewStringf("%s|%s",$1.val,$3.val);
$$.val = NewStringf("%s|%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote($1.type,$3.type);
}
| expr XOR expr {
$$.val = NewStringf("%s^%s",$1.val,$3.val);
$$.val = NewStringf("%s^%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote($1.type,$3.type);
}
| expr LSHIFT expr {
$$.val = NewStringf("%s << %s",$1.val,$3.val);
$$.val = NewStringf("%s << %s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote_type($1.type);
}
| expr RSHIFT expr {
$$.val = NewStringf("%s >> %s",$1.val,$3.val);
$$.val = NewStringf("%s >> %s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = promote_type($1.type);
}
| expr LAND expr {
$$.val = NewStringf("%s&&%s",$1.val,$3.val);
$$.val = NewStringf("%s&&%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = cparse_cplusplus ? T_BOOL : T_INT;
}
| expr LOR expr {
$$.val = NewStringf("%s||%s",$1.val,$3.val);
$$.val = NewStringf("%s||%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = cparse_cplusplus ? T_BOOL : T_INT;
}
| expr EQUALTO expr {
$$.val = NewStringf("%s==%s",$1.val,$3.val);
$$.val = NewStringf("%s==%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = cparse_cplusplus ? T_BOOL : T_INT;
}
| expr NOTEQUALTO expr {
$$.val = NewStringf("%s!=%s",$1.val,$3.val);
$$.val = NewStringf("%s!=%s",COMPOUND_EXPR_VAL($1),COMPOUND_EXPR_VAL($3));
$$.type = cparse_cplusplus ? T_BOOL : T_INT;
}
/* Sadly this causes 2 reduce-reduce conflicts with templates. FIXME resolve these.
| expr GREATERTHAN expr {
$$.val = NewStringf("%s < %s", $1.val, $3.val);
$$.val = NewStringf("%s > %s", COMPOUND_EXPR_VAL($1), COMPOUND_EXPR_VAL($3));
$$.type = cparse_cplusplus ? T_BOOL : T_INT;
}
| expr LESSTHAN expr {
$$.val = NewStringf("%s > %s", $1.val, $3.val);
$$.val = NewStringf("%s < %s", COMPOUND_EXPR_VAL($1), COMPOUND_EXPR_VAL($3));
$$.type = cparse_cplusplus ? T_BOOL : T_INT;
}
*/
| expr GREATERTHANOREQUALTO expr {
$$.val = NewStringf("%s >= %s", $1.val, $3.val);
$$.val = NewStringf("%s >= %s", COMPOUND_EXPR_VAL($1), COMPOUND_EXPR_VAL($3));
$$.type = cparse_cplusplus ? T_BOOL : T_INT;
}
| expr LESSTHANOREQUALTO expr {
$$.val = NewStringf("%s <= %s", $1.val, $3.val);
$$.val = NewStringf("%s <= %s", COMPOUND_EXPR_VAL($1), COMPOUND_EXPR_VAL($3));
$$.type = cparse_cplusplus ? T_BOOL : T_INT;
}
| expr QUESTIONMARK expr COLON expr %prec QUESTIONMARK {
$$.val = NewStringf("%s?%s:%s", $1.val, $3.val, $5.val);
$$.val = NewStringf("%s?%s:%s", COMPOUND_EXPR_VAL($1), COMPOUND_EXPR_VAL($3), COMPOUND_EXPR_VAL($5));
/* This may not be exactly right, but is probably good enough
* for the purposes of parsing constant expressions. */
$$.type = promote($3.type, $5.type);
@ -6272,7 +6329,7 @@ exprcompound : expr PLUS expr {
$$.type = $2.type;
}
| LNOT expr {
$$.val = NewStringf("!%s",$2.val);
$$.val = NewStringf("!%s",COMPOUND_EXPR_VAL($2));
$$.type = T_INT;
}
| type LPAREN {

View file

@ -70,6 +70,28 @@ void Swig_cparse_replace_descriptor(String *s) {
}
}
/* -----------------------------------------------------------------------------
* Swig_cparse_smartptr()
*
* Parse the type in smartptr feature and convert into a SwigType.
* Error out if the parsing fails as this is like a parser syntax error.
* ----------------------------------------------------------------------------- */
SwigType *Swig_cparse_smartptr(Node *n) {
SwigType *smart = 0;
String *smartptr = Getattr(n, "feature:smartptr");
if (smartptr) {
SwigType *cpt = Swig_cparse_type(smartptr);
if (cpt) {
smart = SwigType_typedef_resolve_all(cpt);
Delete(cpt);
} else {
Swig_error(Getfile(n), Getline(n), "Invalid type (%s) in 'smartptr' feature for class %s.\n", smartptr, SwigType_namestr(Getattr(n, "name")));
}
}
return smart;
}
/* -----------------------------------------------------------------------------
* cparse_normalize_void()
*

View file

@ -93,8 +93,8 @@
#define WARN_PARSE_EXTEND_NAME 326
#define WARN_CPP11_LAMBDA 340
#define WARN_CPP11_ALIAS_DECLARATION 341
#define WARN_CPP11_ALIAS_TEMPLATE 342
#define WARN_CPP11_ALIAS_DECLARATION 341 /* redundant now */
#define WARN_CPP11_ALIAS_TEMPLATE 342 /* redundant now */
#define WARN_CPP11_VARIADIC_TEMPLATE 343
#define WARN_IGNORE_OPERATOR_NEW 350 /* new */
@ -215,9 +215,9 @@
/* Feel free to claim any number in this space that's not currently being used. Just make sure you
add an entry here */
#define WARN_D_TYPEMAP_CTYPE_UNDEF 700
#define WARN_D_TYPEMAP_CTYPE_UNDEF 700
#define WARN_D_TYPEMAP_IMTYPE_UNDEF 701
#define WARN_D_TYPEMAP_DTYPE_UNDEF 702
#define WARN_D_TYPEMAP_DTYPE_UNDEF 702
#define WARN_D_MULTIPLE_INHERITANCE 703
#define WARN_D_TYPEMAP_CLASSMOD_UNDEF 704
#define WARN_D_TYPEMAP_DBODY_UNDEF 705
@ -264,6 +264,7 @@
#define WARN_JAVA_TYPEMAP_JAVAIN_UNDEF 818
#define WARN_JAVA_TYPEMAP_JAVADIRECTORIN_UNDEF 819
#define WARN_JAVA_TYPEMAP_JAVADIRECTOROUT_UNDEF 820
#define WARN_JAVA_TYPEMAP_INTERFACECODE_UNDEF 821
#define WARN_JAVA_COVARIANT_RET 822
#define WARN_JAVA_TYPEMAP_JAVACONSTRUCT_UNDEF 823
#define WARN_JAVA_TYPEMAP_DIRECTORIN_NODESC 824
@ -283,6 +284,7 @@
#define WARN_CSHARP_TYPEMAP_CSIN_UNDEF 838
#define WARN_CSHARP_TYPEMAP_CSDIRECTORIN_UNDEF 839
#define WARN_CSHARP_TYPEMAP_CSDIRECTOROUT_UNDEF 840
#define WARN_CSHARP_TYPEMAP_INTERFACECODE_UNDEF 841
#define WARN_CSHARP_COVARIANT_RET 842
#define WARN_CSHARP_TYPEMAP_CSCONSTRUCT_UNDEF 843
#define WARN_CSHARP_EXCODE 844

View file

@ -47,6 +47,7 @@ eswig_SOURCES = CParse/cscanner.c \
Modules/emit.cxx \
Modules/go.cxx \
Modules/guile.cxx \
Modules/interface.cxx \
Modules/java.cxx \
Modules/javascript.cxx \
Modules/lang.cxx \
@ -61,6 +62,7 @@ eswig_SOURCES = CParse/cscanner.c \
Modules/overload.cxx \
Modules/perl5.cxx \
Modules/php.cxx \
Modules/php5.cxx \
Modules/pike.cxx \
Modules/python.cxx \
Modules/r.cxx \

View file

@ -1635,9 +1635,7 @@ int ALLEGROCL::top(Node *n) {
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGALLEGROCL\n");
Printf(f_runtime, "\n");
Printf(f_runtime, "\n\n#ifndef SWIGALLEGROCL\n#define SWIGALLEGROCL\n#endif\n\n");
Swig_banner_target_lang(f_cl, ";;");
@ -1895,11 +1893,12 @@ static List *Swig_overload_rank(Node *n, bool script_lang_wrapping) {
Swig_warning(WARN_LANG_OVERLOAD_CONST, Getfile(nodes[i].n), Getline(nodes[i].n),
"using non-const method %s instead.\n", Swig_name_decl(nodes[i].n));
} else {
if (!Getattr(nodes[j].n, "overload:ignore"))
if (!Getattr(nodes[j].n, "overload:ignore")) {
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[j].n), Getline(nodes[j].n),
"Overloaded method %s ignored,\n", Swig_name_decl(nodes[j].n));
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[i].n), Getline(nodes[i].n),
"using %s instead.\n", Swig_name_decl(nodes[i].n));
}
}
}
nodes[j].error = 1;
@ -1912,11 +1911,12 @@ static List *Swig_overload_rank(Node *n, bool script_lang_wrapping) {
Swig_warning(WARN_LANG_OVERLOAD_CONST, Getfile(nodes[i].n), Getline(nodes[i].n),
"using non-const method %s instead.\n", Swig_name_decl(nodes[i].n));
} else {
if (!Getattr(nodes[j].n, "overload:ignore"))
if (!Getattr(nodes[j].n, "overload:ignore")) {
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[j].n), Getline(nodes[j].n),
"Overloaded method %s ignored,\n", Swig_name_decl(nodes[j].n));
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[i].n), Getline(nodes[i].n),
"using %s instead.\n", Swig_name_decl(nodes[i].n));
}
}
}
nodes[j].error = 1;
@ -1934,11 +1934,12 @@ static List *Swig_overload_rank(Node *n, bool script_lang_wrapping) {
Swig_warning(WARN_LANG_OVERLOAD_SHADOW, Getfile(nodes[i].n), Getline(nodes[i].n),
"as it is shadowed by %s.\n", Swig_name_decl(nodes[i].n));
} else {
if (!Getattr(nodes[j].n, "overload:ignore"))
if (!Getattr(nodes[j].n, "overload:ignore")) {
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[j].n), Getline(nodes[j].n),
"Overloaded method %s ignored,\n", Swig_name_decl(nodes[j].n));
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[i].n), Getline(nodes[i].n),
"using %s instead.\n", Swig_name_decl(nodes[i].n));
}
}
nodes[j].error = 1;
}
@ -2721,6 +2722,13 @@ int ALLEGROCL::functionWrapper(Node *n) {
}
}
/* See if there is any return cleanup code */
if ((tm = Swig_typemap_lookup("ret", n, Swig_cresult_name(), 0))) {
Replaceall(tm, "$source", Swig_cresult_name());
Printf(f->code, "%s\n", tm);
Delete(tm);
}
emit_return_variable(n, t, f);
if (CPlusPlus) {
@ -3168,6 +3176,9 @@ int ALLEGROCL::enumDeclaration(Node *n) {
Printf(stderr, "enumDeclaration %s\n", Getattr(n, "name"));
#endif
if (getCurrentClass() && (cplus_mode != PUBLIC))
return SWIG_NOWRAP;
if (Getattr(n, "sym:name")) {
add_defined_foreign_type(n);
}

View file

@ -729,6 +729,8 @@ Allocate():
}
}
Swig_interface_propagate_methods(n);
/* Only care about default behavior. Remove temporary values */
Setattr(n, "allocate:visit", "1");
Swig_symbol_setscope(symtab);

View file

@ -61,6 +61,11 @@ public:
virtual int classHandler(Node *n);
private:
static void checkConstraints(ParmList *parms, Wrapper *f);
static void argout(ParmList *parms, Wrapper *f);
static String *freearg(ParmList *parms);
static void cleanupFunction(Node *n, Wrapper *f, ParmList *parms);
void emit_defun(Node *n, String *name);
void emit_defmethod(Node *n);
void emit_initialize_instance(Node *n);
@ -169,9 +174,7 @@ int CFFI::top(Node *n) {
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGCFFI\n");
Printf(f_runtime, "\n");
Printf(f_runtime, "\n\n#ifndef SWIGCFFI\n#define SWIGCFFI\n#endif\n\n");
Swig_banner_target_lang(f_lisp, ";;;");
@ -364,6 +367,77 @@ int CFFI::membervariableHandler(Node *n) {
return Language::membervariableHandler(n);
}
void CFFI::checkConstraints(ParmList *parms, Wrapper *f) {
Parm *p = parms;
while (p) {
String *tm = Getattr(p, "tmap:check");
if (!tm) {
p = nextSibling(p);
} else {
tm = Copy(tm);
Replaceall(tm, "$input", Getattr(p, "emit:input"));
Printv(f->code, tm, "\n\n", NULL);
Delete(tm);
p = Getattr(p, "tmap:check:next");
}
}
}
void CFFI::argout(ParmList *parms, Wrapper *f) {
Parm *p = parms;
while (p) {
String *tm = Getattr(p, "tmap:argout");
if (!tm) {
p = nextSibling(p);
} else {
tm = Copy(tm);
Replaceall(tm, "$result", Swig_cresult_name());
Replaceall(tm, "$input", Getattr(p, "emit:input"));
Printv(f->code, tm, "\n", NULL);
Delete(tm);
p = Getattr(p, "tmap:argout:next");
}
}
}
String *CFFI::freearg(ParmList *parms) {
String *ret = NewString("");
Parm *p = parms;
while (p) {
String *tm = Getattr(p, "tmap:freearg");
if (!tm) {
p = nextSibling(p);
} else {
tm = Copy(tm);
Replaceall(tm, "$input", Getattr(p, "emit:input"));
Printv(ret, tm, "\n", NULL);
Delete(tm);
p = Getattr(p, "tmap:freearg:next");
}
}
return ret;
}
void CFFI::cleanupFunction(Node *n, Wrapper *f, ParmList *parms) {
String *cleanup = freearg(parms);
Printv(f->code, cleanup, NULL);
if (GetFlag(n, "feature:new")) {
String *tm = Swig_typemap_lookup("newfree", n, Swig_cresult_name(), 0);
if (tm) {
Replaceall(tm, "$source", Swig_cresult_name());
Printv(f->code, tm, "\n", NULL);
Delete(tm);
}
}
Replaceall(f->code, "$cleanup", cleanup);
Delete(cleanup);
Replaceall(f->code, "$symname", Getattr(n, "sym:name"));
}
int CFFI::functionWrapper(Node *n) {
ParmList *parms = Getattr(n, "parms");
@ -451,6 +525,9 @@ int CFFI::functionWrapper(Node *n) {
// Emit the function definition
String *signature = SwigType_str(return_type, name_and_parms);
Printf(f->def, "EXPORT %s {", signature);
checkConstraints(parms, f);
Printf(f->code, " try {\n");
String *actioncode = emit_action(n);
@ -459,9 +536,25 @@ int CFFI::functionWrapper(Node *n) {
if (result_convert) {
Replaceall(result_convert, "$result", "lresult");
Printf(f->code, "%s\n", result_convert);
if(!is_void_return) Printf(f->code, " return lresult;\n");
Delete(result_convert);
}
Delete(result_convert);
argout(parms, f);
cleanupFunction(n, f, parms);
/* See if there is any return cleanup code */
String *tm = 0;
if ((tm = Swig_typemap_lookup("ret", n, Swig_cresult_name(), 0))) {
Replaceall(tm, "$source", Swig_cresult_name());
Printf(f->code, "%s\n", tm);
Delete(tm);
}
if (!is_void_return) {
Printf(f->code, " return lresult;\n");
}
emit_return_variable(n, Getattr(n, "type"), f);
Printf(f->code, " } catch (...) {\n");
@ -603,6 +696,9 @@ int CFFI::typedefHandler(Node *n) {
}
int CFFI::enumDeclaration(Node *n) {
if (getCurrentClass() && (cplus_mode != PUBLIC))
return SWIG_NOWRAP;
String *name = Getattr(n, "sym:name");
bool slot_name_keywords;
String *lisp_name = 0;
@ -860,8 +956,11 @@ void CFFI::emit_struct_union(Node *n, bool un = false) {
}
void CFFI::emit_export(Node *n, String *name) {
if (GetInt(n, "feature:export"))
Printf(f_cl, "\n(cl:export '%s)\n", name);
if (GetInt(n, "feature:export")) {
String* package = Getattr(n, "feature:export:package");
Printf(f_cl, "\n(cl:export '%s%s%s)\n", name, package ? " " : "",
package ? package : "");
}
}
void CFFI::emit_inline(Node *n, String *name) {
@ -1019,7 +1118,7 @@ String *CFFI::convert_literal(String *literal, String *type, bool try_to_split)
return num;
} else if (SwigType_type(type) == T_CHAR) {
/* Use CL syntax for character literals */
String* result = NewStringf("#\\%c", s[0]);
String* result = NewStringf("#\\%s", s);
Delete(num);
return result;
} else if (SwigType_type(type) == T_STRING) {

View file

@ -222,8 +222,7 @@ int CHICKEN::top(Node *n) {
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGCHICKEN\n");
Printf(f_runtime, "\n\n#ifndef SWIGCHICKEN\n#define SWIGCHICKEN\n#endif\n\n");
if (no_collection)
Printf(f_runtime, "#define SWIG_CHICKEN_NO_COLLECTION 1\n");

View file

@ -242,6 +242,9 @@ int CLISP::typedefHandler(Node *n) {
}
int CLISP::enumDeclaration(Node *n) {
if (getCurrentClass() && (cplus_mode != PUBLIC))
return SWIG_NOWRAP;
is_function = 0;
String *name = Getattr(n, "sym:name");

View file

@ -52,6 +52,7 @@ class CSHARP:public Language {
String *imclass_class_code; // intermediary class code
String *proxy_class_def;
String *proxy_class_code;
String *interface_class_code; // if %feature("interface") was declared for a class, here goes the interface declaration
String *module_class_code;
String *proxy_class_name; // proxy class name
String *full_imclass_name; // fully qualified intermediary class name when using nspace feature, otherwise same as imclass_name
@ -126,6 +127,7 @@ public:
imclass_class_code(NULL),
proxy_class_def(NULL),
proxy_class_code(NULL),
interface_class_code(NULL),
module_class_code(NULL),
proxy_class_name(NULL),
full_imclass_name(NULL),
@ -186,8 +188,12 @@ public:
String *symname = Copy(Getattr(n, "sym:name"));
if (symname && !GetFlag(n, "feature:flatnested")) {
for (Node *outer_class = Getattr(n, "nested:outer"); outer_class; outer_class = Getattr(outer_class, "nested:outer")) {
Push(symname, ".");
Push(symname, Getattr(outer_class, "sym:name"));
if (String* name = Getattr(outer_class, "sym:name")) {
Push(symname, ".");
Push(symname, name);
}
else
return NULL;
}
}
if (nspace) {
@ -272,6 +278,7 @@ public:
SWIG_config_file("csharp.swg");
allow_overloading();
Swig_interface_feature_enable();
}
/* ---------------------------------------------------------------------
@ -392,8 +399,7 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGCSHARP\n");
Printf(f_runtime, "\n\n#ifndef SWIGCSHARP\n#define SWIGCSHARP\n#endif\n\n");
if (directorsEnabled()) {
Printf(f_runtime, "#define SWIG_DIRECTORS\n");
@ -416,8 +422,16 @@ public:
}
Printf(f_runtime, "\n");
if (namespce) {
String *wrapper_name = NewStringf("");
Printf(wrapper_name, "CSharp_%s_%%f", namespce);
Swig_name_register("wrapper", wrapper_name);
Delete(wrapper_name);
}
else {
Swig_name_register("wrapper", "CSharp_%f");
}
Swig_name_register("wrapper", "CSharp_%f");
if (old_variable_names) {
Swig_name_register("set", "set_%n%v");
Swig_name_register("get", "get_%n%v");
@ -1310,7 +1324,7 @@ public:
const char *val = Equal(Getattr(n, "enumvalue"), "true") ? "1" : "0";
Setattr(n, "enumvalue", val);
} else if (swigtype == T_CHAR) {
String *val = NewStringf("'%s'", Getattr(n, "enumvalue"));
String *val = NewStringf("'%(hexescape)s'", Getattr(n, "enumvalue"));
Setattr(n, "enumvalue", val);
Delete(val);
}
@ -1434,6 +1448,7 @@ public:
virtual int constantWrapper(Node *n) {
String *symname = Getattr(n, "sym:name");
SwigType *t = Getattr(n, "type");
SwigType *valuetype = Getattr(n, "valuetype");
ParmList *l = Getattr(n, "parms");
String *tm;
String *return_type = NewString("");
@ -1486,13 +1501,15 @@ public:
Swig_warning(WARN_CSHARP_TYPEMAP_CSWTYPE_UNDEF, input_file, line_number, "No cstype typemap defined for %s\n", SwigType_str(t, 0));
}
// Default (octal) escaping is no good - change to hex escaped value
String *hexescaped_value = Getattr(n, "rawvalue") ? NewStringf("%(hexescape)s", Getattr(n, "rawvalue")) : 0;
// Add the stripped quotes back in
String *new_value = NewString("");
if (SwigType_type(t) == T_STRING) {
Printf(new_value, "\"%s\"", Copy(Getattr(n, "value")));
Printf(new_value, "\"%s\"", hexescaped_value ? hexescaped_value : Copy(Getattr(n, "value")));
Setattr(n, "value", new_value);
} else if (SwigType_type(t) == T_CHAR) {
Printf(new_value, "\'%s\'", Copy(Getattr(n, "value")));
Printf(new_value, "\'%s\'", hexescaped_value ? hexescaped_value : Copy(Getattr(n, "value")));
Setattr(n, "value", new_value);
}
@ -1533,10 +1550,14 @@ public:
} else {
// Alternative constant handling will use the C syntax to make a true C# constant and hope that it compiles as C# code
if (Getattr(n, "wrappedasconstant")) {
if (SwigType_type(t) == T_CHAR)
Printf(constants_code, "\'%s\';\n", Getattr(n, "staticmembervariableHandler:value"));
else
if (SwigType_type(t) == T_CHAR) {
if (SwigType_type(valuetype) == T_CHAR)
Printf(constants_code, "\'%(hexescape)s\';\n", Getattr(n, "staticmembervariableHandler:value"));
else
Printf(constants_code, "(char)%s;\n", Getattr(n, "staticmembervariableHandler:value"));
} else {
Printf(constants_code, "%s;\n", Getattr(n, "staticmembervariableHandler:value"));
}
} else {
Printf(constants_code, "%s;\n", Getattr(n, "value"));
}
@ -1636,6 +1657,119 @@ public:
return Language::pragmaDirective(n);
}
/* -----------------------------------------------------------------------------
* getQualifiedInterfaceName()
* ----------------------------------------------------------------------------- */
String *getQualifiedInterfaceName(Node *n) {
String *ret = Getattr(n, "interface:qname");
if (!ret) {
String *nspace = Getattr(n, "sym:nspace");
String *interface_name = Getattr(n, "interface:name");
if (nspace) {
if (namespce)
ret = NewStringf("%s.%s.%s", namespce, nspace, interface_name);
else
ret = NewStringf("%s.%s", nspace, interface_name);
} else {
ret = Copy(interface_name);
}
Setattr(n, "interface:qname", ret);
}
return ret;
}
/* -----------------------------------------------------------------------------
* getInterfaceName()
* ----------------------------------------------------------------------------- */
String *getInterfaceName(SwigType *t, bool qualified) {
String *interface_name = NULL;
if (proxy_flag) {
Node *n = classLookup(t);
if (n && Getattr(n, "interface:name"))
interface_name = qualified ? getQualifiedInterfaceName(n) : Getattr(n, "interface:name");
}
return interface_name;
}
/* -----------------------------------------------------------------------------
* addInterfaceNameAndUpcasts()
* ----------------------------------------------------------------------------- */
void addInterfaceNameAndUpcasts(SwigType *smart, String *interface_list, String *interface_upcasts, Hash *base_list, String *c_classname) {
List *keys = Keys(base_list);
for (Iterator it = First(keys); it.item; it = Next(it)) {
Node *base = Getattr(base_list, it.item);
String *c_baseclass = SwigType_namestr(Getattr(base, "name"));
String *interface_name = Getattr(base, "interface:name");
if (Len(interface_list))
Append(interface_list, ", ");
Append(interface_list, interface_name);
Node *attributes = NewHash();
String *interface_code = Copy(typemapLookup(base, "csinterfacecode", Getattr(base, "classtypeobj"), WARN_CSHARP_TYPEMAP_INTERFACECODE_UNDEF, attributes));
String *cptr_method_name = 0;
if (interface_code) {
Replaceall(interface_code, "$interfacename", interface_name);
Printv(interface_upcasts, interface_code, NIL);
cptr_method_name = Copy(Getattr(attributes, "tmap:csinterfacecode:cptrmethod"));
}
if (!cptr_method_name)
cptr_method_name = NewStringf("%s_GetInterfaceCPtr", interface_name);
Replaceall(cptr_method_name, ".", "_");
Replaceall(cptr_method_name, "$interfacename", interface_name);
String *upcast_method_name = Swig_name_member(getNSpace(), proxy_class_name, cptr_method_name);
upcastsCode(smart, upcast_method_name, c_classname, c_baseclass);
Delete(upcast_method_name);
Delete(cptr_method_name);
Delete(interface_code);
Delete(c_baseclass);
}
Delete(keys);
}
/* -----------------------------------------------------------------------------
* upcastsCode()
*
* Add code for C++ casting to base class
* ----------------------------------------------------------------------------- */
void upcastsCode(SwigType *smart, String *upcast_method_name, String *c_classname, String *c_baseclass) {
String *wname = Swig_name_wrapper(upcast_method_name);
Printv(imclass_cppcasts_code, "\n [global::System.Runtime.InteropServices.DllImport(\"", dllimport, "\", EntryPoint=\"", wname, "\")]\n", NIL);
Printf(imclass_cppcasts_code, " public static extern global::System.IntPtr %s(global::System.IntPtr jarg1);\n", upcast_method_name);
Replaceall(imclass_cppcasts_code, "$csclassname", proxy_class_name);
if (smart) {
SwigType *bsmart = Copy(smart);
SwigType *rclassname = SwigType_typedef_resolve_all(c_classname);
SwigType *rbaseclass = SwigType_typedef_resolve_all(c_baseclass);
Replaceall(bsmart, rclassname, rbaseclass);
Delete(rclassname);
Delete(rbaseclass);
String *smartnamestr = SwigType_namestr(smart);
String *bsmartnamestr = SwigType_namestr(bsmart);
Printv(upcasts_code,
"SWIGEXPORT ", bsmartnamestr, " * SWIGSTDCALL ", wname, "(", smartnamestr, " *jarg1) {\n",
" return jarg1 ? new ", bsmartnamestr, "(*jarg1) : 0;\n"
"}\n", "\n", NIL);
Delete(bsmartnamestr);
Delete(smartnamestr);
Delete(bsmart);
} else {
Printv(upcasts_code,
"SWIGEXPORT ", c_baseclass, " * SWIGSTDCALL ", wname, "(", c_classname, " *jarg1) {\n",
" return (", c_baseclass, " *)jarg1;\n"
"}\n", "\n", NIL);
}
Delete(wname);
}
/* -----------------------------------------------------------------------------
* emitProxyClassDefAndCPPCasts()
* ----------------------------------------------------------------------------- */
@ -1645,9 +1779,12 @@ public:
String *c_baseclass = NULL;
String *baseclass = NULL;
String *c_baseclassname = NULL;
String *interface_list = NewStringEmpty();
String *interface_upcasts = NewStringEmpty();
SwigType *typemap_lookup_type = Getattr(n, "classtypeobj");
bool feature_director = Swig_directorclass(n) ? true : false;
bool has_outerclass = Getattr(n, "nested:outer") != 0 && !GetFlag(n, "feature:flatnested");
SwigType *smart = Swig_cparse_smartptr(n);
// Inheritance from pure C# classes
Node *attributes = NewHash();
@ -1660,31 +1797,29 @@ public:
if (!purebase_replace) {
List *baselist = Getattr(n, "bases");
if (baselist) {
Iterator base = First(baselist);
while (base.item && GetFlag(base.item, "feature:ignore")) {
base = Next(base);
}
if (base.item) {
c_baseclassname = Getattr(base.item, "name");
baseclass = Copy(getProxyName(c_baseclassname));
if (baseclass)
c_baseclass = SwigType_namestr(Getattr(base.item, "name"));
base = Next(base);
/* Warn about multiple inheritance for additional base class(es) */
while (base.item) {
if (GetFlag(base.item, "feature:ignore")) {
base = Next(base);
continue;
}
String *proxyclassname = Getattr(n, "classtypeobj");
String *baseclassname = Getattr(base.item, "name");
Swig_warning(WARN_CSHARP_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s proxy: Base %s ignored. Multiple inheritance is not supported in C#.\n", SwigType_namestr(proxyclassname), SwigType_namestr(baseclassname));
base = Next(base);
}
}
Iterator base = First(baselist);
while (base.item) {
if (!(GetFlag(base.item, "feature:ignore") || Getattr(base.item, "feature:interface"))) {
String *baseclassname = Getattr(base.item, "name");
if (!c_baseclassname) {
c_baseclassname = baseclassname;
baseclass = Copy(getProxyName(baseclassname));
if (baseclass)
c_baseclass = SwigType_namestr(baseclassname);
} else {
/* Warn about multiple inheritance for additional base class(es) */
String *proxyclassname = Getattr(n, "classtypeobj");
Swig_warning(WARN_CSHARP_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s, base %s ignored. Multiple inheritance is not supported in C#.\n", SwigType_namestr(proxyclassname), SwigType_namestr(baseclassname));
}
}
base = Next(base);
}
}
}
Hash *interface_bases = Getattr(n, "interface:bases");
if (interface_bases)
addInterfaceNameAndUpcasts(smart, interface_list, interface_upcasts, interface_bases, c_classname);
bool derived = baseclass && getProxyName(c_baseclassname);
if (derived && purebase_notderived)
@ -1700,12 +1835,15 @@ public:
Swig_error(Getfile(n), Getline(n), "The csbase typemap for proxy %s must contain just one of the 'replace' or 'notderived' attributes.\n", typemap_lookup_type);
} else if (Len(pure_baseclass) > 0 && Len(baseclass) > 0) {
Swig_warning(WARN_CSHARP_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s proxy: Base %s ignored. Multiple inheritance is not supported in C#. "
"Warning for %s, base %s ignored. Multiple inheritance is not supported in C#. "
"Perhaps you need one of the 'replace' or 'notderived' attributes in the csbase typemap?\n", typemap_lookup_type, pure_baseclass);
}
// Pure C# interfaces
const String *pure_interfaces = typemapLookup(n, derived ? "csinterfaces_derived" : "csinterfaces", typemap_lookup_type, WARN_NONE);
if (*Char(interface_list) && *Char(pure_interfaces))
Append(interface_list, ", ");
Append(interface_list, pure_interfaces);
// Start writing the proxy class
if (!has_outerclass)
Printv(proxy_class_def, typemapLookup(n, "csimports", typemap_lookup_type, WARN_NONE), // Import statements
@ -1718,8 +1856,8 @@ public:
Printv(proxy_class_def, typemapLookup(n, "csclassmodifiers", typemap_lookup_type, WARN_CSHARP_TYPEMAP_CLASSMOD_UNDEF), // Class modifiers
" $csclassname", // Class name and base class
(*Char(wanted_base) || *Char(pure_interfaces)) ? " : " : "", wanted_base, (*Char(wanted_base) && *Char(pure_interfaces)) ? // Interfaces
", " : "", pure_interfaces, " {", derived ? typemapLookup(n, "csbody_derived", typemap_lookup_type, WARN_CSHARP_TYPEMAP_CSBODY_UNDEF) : // main body of class
(*Char(wanted_base) || *Char(interface_list)) ? " : " : "", wanted_base, (*Char(wanted_base) && *Char(interface_list)) ? // Interfaces
", " : "", interface_list, " {", derived ? typemapLookup(n, "csbody_derived", typemap_lookup_type, WARN_CSHARP_TYPEMAP_CSBODY_UNDEF) : // main body of class
typemapLookup(n, "csbody", typemap_lookup_type, WARN_CSHARP_TYPEMAP_CSBODY_UNDEF), // main body of class
NIL);
@ -1764,6 +1902,8 @@ public:
Printv(proxy_class_def, "\n ", destruct_methodmodifiers, " ", derived ? "override" : "virtual", " void ", destruct_methodname, "() ", destruct, "\n",
NIL);
}
if (*Char(interface_upcasts))
Printv(proxy_class_def, interface_upcasts, NIL);
if (feature_director) {
// Generate director connect method
@ -1845,6 +1985,8 @@ public:
Delete(director_connect_method_name);
}
Delete(interface_upcasts);
Delete(interface_list);
Delete(attributes);
Delete(destruct);
@ -1852,60 +1994,92 @@ public:
Printv(proxy_class_def, typemapLookup(n, "cscode", typemap_lookup_type, WARN_NONE), // extra C# code
"\n", NIL);
// Add code to do C++ casting to base class (only for classes in an inheritance hierarchy)
if (derived) {
String *smartptr = Getattr(n, "feature:smartptr");
String *upcast_method = Swig_name_member(getNSpace(), getClassPrefix(), smartptr != 0 ? "SWIGSmartPtrUpcast" : "SWIGUpcast");
String *wname = Swig_name_wrapper(upcast_method);
Printv(imclass_cppcasts_code, "\n [global::System.Runtime.InteropServices.DllImport(\"", dllimport, "\", EntryPoint=\"", wname, "\")]\n", NIL);
Printf(imclass_cppcasts_code, " public static extern global::System.IntPtr %s(global::System.IntPtr jarg1);\n", upcast_method);
Replaceall(imclass_cppcasts_code, "$csclassname", proxy_class_name);
if (smartptr) {
SwigType *spt = Swig_cparse_type(smartptr);
if (spt) {
SwigType *smart = SwigType_typedef_resolve_all(spt);
Delete(spt);
SwigType *bsmart = Copy(smart);
SwigType *rclassname = SwigType_typedef_resolve_all(c_classname);
SwigType *rbaseclass = SwigType_typedef_resolve_all(c_baseclass);
Replaceall(bsmart, rclassname, rbaseclass);
Delete(rclassname);
Delete(rbaseclass);
String *smartnamestr = SwigType_namestr(smart);
String *bsmartnamestr = SwigType_namestr(bsmart);
Printv(upcasts_code,
"SWIGEXPORT ", bsmartnamestr, " * SWIGSTDCALL ", wname, "(", smartnamestr, " *jarg1) {\n",
" return jarg1 ? new ", bsmartnamestr, "(*jarg1) : 0;\n"
"}\n", "\n", NIL);
Delete(bsmartnamestr);
Delete(smartnamestr);
Delete(bsmart);
} else {
Swig_error(Getfile(n), Getline(n), "Invalid type (%s) in 'smartptr' feature for class %s.\n", smartptr, c_classname);
}
} else {
Printv(upcasts_code,
"SWIGEXPORT ", c_baseclass, " * SWIGSTDCALL ", wname, "(", c_classname, " *jarg1) {\n",
" return (", c_baseclass, " *)jarg1;\n"
"}\n", "\n", NIL);
}
Delete(wname);
Delete(upcast_method);
String *upcast_method_name = Swig_name_member(getNSpace(), getClassPrefix(), smart != 0 ? "SWIGSmartPtrUpcast" : "SWIGUpcast");
upcastsCode(smart, upcast_method_name, c_classname, c_baseclass);
Delete(upcast_method_name);
}
Delete(smart);
Delete(baseclass);
}
/* ----------------------------------------------------------------------
* emitInterfaceDeclaration()
* ---------------------------------------------------------------------- */
void emitInterfaceDeclaration(Node *n, String *interface_name, File *f_interface) {
Printv(f_interface, typemapLookup(n, "csimports", Getattr(n, "classtypeobj"), WARN_NONE), "\n", NIL);
Printf(f_interface, "public interface %s", interface_name);
if (List *baselist = Getattr(n, "bases")) {
String *bases = 0;
for (Iterator base = First(baselist); base.item; base = Next(base)) {
if (GetFlag(base.item, "feature:ignore") || !Getattr(base.item, "feature:interface"))
continue; // TODO: warn about skipped non-interface bases
String *base_iname = Getattr(base.item, "interface:name");
if (!bases)
bases = NewStringf(" : %s", base_iname);
else {
Append(bases, ", ");
Append(bases, base_iname);
}
}
if (bases) {
Printv(f_interface, bases, NIL);
Delete(bases);
}
}
Printf(f_interface, " {\n");
Node *attributes = NewHash();
String *interface_code = Copy(typemapLookup(n, "csinterfacecode", Getattr(n, "classtypeobj"), WARN_CSHARP_TYPEMAP_INTERFACECODE_UNDEF, attributes));
if (interface_code) {
String *interface_declaration = Copy(Getattr(attributes, "tmap:csinterfacecode:declaration"));
if (interface_declaration) {
Replaceall(interface_declaration, "$interfacename", interface_name);
Printv(f_interface, interface_declaration, NIL);
Delete(interface_declaration);
}
Delete(interface_code);
}
}
/* ----------------------------------------------------------------------
* calculateDirectBase()
* ---------------------------------------------------------------------- */
void calculateDirectBase(Node* n) {
Node* direct_base = 0;
// C++ inheritance
Node *attributes = NewHash();
SwigType *typemap_lookup_type = Getattr(n, "classtypeobj");
const String *pure_baseclass = typemapLookup(n, "csbase", typemap_lookup_type, WARN_NONE, attributes);
bool purebase_replace = GetFlag(attributes, "tmap:csbase:replace") ? true : false;
bool purebase_notderived = GetFlag(attributes, "tmap:csbase:notderived") ? true : false;
Delete(attributes);
if (!purebase_replace) {
if (List *baselist = Getattr(n, "bases")) {
Iterator base = First(baselist);
while (base.item && (GetFlag(base.item, "feature:ignore") || Getattr(base.item, "feature:interface")))
base = Next(base);
direct_base = base.item;
}
if (!direct_base && purebase_notderived)
direct_base = symbolLookup(const_cast<String*>(pure_baseclass));
} else {
direct_base = symbolLookup(const_cast<String*>(pure_baseclass));
}
Setattr(n, "direct_base", direct_base);
}
/* ----------------------------------------------------------------------
* classHandler()
* ---------------------------------------------------------------------- */
virtual int classHandler(Node *n) {
String *nspace = getNSpace();
File *f_proxy = NULL;
File *f_interface = NULL;
// save class local variables
String *old_proxy_class_name = proxy_class_name;
String *old_full_imclass_name = full_imclass_name;
@ -1914,9 +2088,12 @@ public:
String *old_proxy_class_def = proxy_class_def;
String *old_proxy_class_code = proxy_class_code;
bool has_outerclass = Getattr(n, "nested:outer") && !GetFlag(n, "feature:flatnested");
String *old_interface_class_code = interface_class_code;
interface_class_code = 0;
if (proxy_flag) {
proxy_class_name = NewString(Getattr(n, "sym:name"));
String *interface_name = Getattr(n, "feature:interface") ? Getattr(n, "interface:name") : 0;
if (Node *outer = Getattr(n, "nested:outer")) {
String *outerClassesPrefix = Copy(Getattr(outer, "sym:name"));
for (outer = Getattr(outer, "nested:outer"); outer != 0; outer = Getattr(outer, "nested:outer")) {
@ -1926,13 +2103,16 @@ public:
String *fnspace = nspace ? NewStringf("%s.%s", nspace, outerClassesPrefix) : outerClassesPrefix;
if (!addSymbol(proxy_class_name, n, fnspace))
return SWIG_ERROR;
if (interface_name && !addInterfaceSymbol(interface_name, n, fnspace))
return SWIG_ERROR;
if (nspace)
Delete(fnspace);
Delete(outerClassesPrefix);
}
else {
} else {
if (!addSymbol(proxy_class_name, n, nspace))
return SWIG_ERROR;
if (interface_name && !addInterfaceSymbol(interface_name, n, nspace))
return SWIG_ERROR;
}
if (!nspace) {
@ -1959,13 +2139,25 @@ public:
f_proxy = getOutputFile(output_directory, proxy_class_name);
addOpenNamespace(nspace, f_proxy);
Delete(output_directory);
}
else
++nesting_depth;
proxy_class_def = NewString("");
proxy_class_code = NewString("");
destructor_call = NewString("");
proxy_class_constants_code = NewString("");
if (Getattr(n, "feature:interface")) {
interface_class_code = NewString("");
String *output_directory = outputDirectory(nspace);
f_interface = getOutputFile(output_directory, interface_name);
addOpenNamespace(nspace, f_interface);
emitInterfaceDeclaration(n, interface_name, interface_class_code);
Delete(output_directory);
}
calculateDirectBase(n);
}
Language::classHandler(n);
@ -1979,22 +2171,28 @@ public:
Replaceall(proxy_class_def, "$csclassname", proxy_class_name);
Replaceall(proxy_class_code, "$csclassname", proxy_class_name);
Replaceall(proxy_class_constants_code, "$csclassname", proxy_class_name);
Replaceall(interface_class_code, "$csclassname", proxy_class_name);
Replaceall(proxy_class_def, "$csclazzname", csclazzname);
Replaceall(proxy_class_code, "$csclazzname", csclazzname);
Replaceall(proxy_class_constants_code, "$csclazzname", csclazzname);
Replaceall(interface_class_code, "$csclazzname", csclazzname);
Replaceall(proxy_class_def, "$module", module_class_name);
Replaceall(proxy_class_code, "$module", module_class_name);
Replaceall(proxy_class_constants_code, "$module", module_class_name);
Replaceall(interface_class_code, "$module", module_class_name);
Replaceall(proxy_class_def, "$imclassname", full_imclass_name);
Replaceall(proxy_class_code, "$imclassname", full_imclass_name);
Replaceall(proxy_class_constants_code, "$imclassname", full_imclass_name);
Replaceall(interface_class_code, "$imclassname", full_imclass_name);
Replaceall(proxy_class_def, "$dllimport", dllimport);
Replaceall(proxy_class_code, "$dllimport", dllimport);
Replaceall(proxy_class_constants_code, "$dllimport", dllimport);
Replaceall(interface_class_code, "$dllimport", dllimport);
if (!has_outerclass)
Printv(f_proxy, proxy_class_def, proxy_class_code, NIL);
else {
@ -2057,8 +2255,18 @@ public:
Delete(downcast_method);
}
if (f_interface) {
Printv(f_interface, interface_class_code, "}\n", NIL);
addCloseNamespace(nspace, f_interface);
if (f_interface != f_single_out)
Delete(f_interface);
f_interface = 0;
}
emitDirectorExtraMethods(n);
Delete(interface_class_code);
interface_class_code = old_interface_class_code;
Delete(csclazzname);
Delete(proxy_class_name);
proxy_class_name = old_proxy_class_name;
@ -2144,6 +2352,8 @@ public:
String *pre_code = NewString("");
String *post_code = NewString("");
String *terminator_code = NewString("");
bool is_interface = Getattr(parentNode(n), "feature:interface") != 0
&& !static_flag && Getattr(n, "interface:owner") == 0;
if (!proxy_flag)
return;
@ -2216,8 +2426,21 @@ public:
Printf(function_code, " %s ", methodmods);
if (!is_smart_pointer()) {
// Smart pointer classes do not mirror the inheritance hierarchy of the underlying pointer type, so no virtual/override/new required.
if (Getattr(n, "override"))
Printf(function_code, "override ");
if (Node *base_ovr = Getattr(n, "override")) {
if (GetFlag(n, "isextendmember"))
Printf(function_code, "override ");
else {
Node* base = parentNode(base_ovr);
bool ovr = false;
for (Node* direct_base = Getattr(parentNode(n), "direct_base"); direct_base; direct_base = Getattr(direct_base, "direct_base")) {
if (direct_base == base) { // "override" only applies if the base was not discarded (e.g. in case of multiple inheritance or via "ignore")
ovr = true;
break;
}
}
Printf(function_code, ovr ? "override " : "virtual ");
}
}
else if (checkAttribute(n, "storage", "virtual"))
Printf(function_code, "virtual ");
if (Getattr(n, "hides"))
@ -2227,6 +2450,9 @@ public:
if (static_flag)
Printf(function_code, "static ");
Printf(function_code, "%s %s(", return_type, proxy_function_name);
if (is_interface)
Printf(interface_class_code, " %s %s(", return_type, proxy_function_name);
Printv(imcall, full_imclass_name, ".$imfuncname(", NIL);
if (!static_flag)
@ -2306,10 +2532,15 @@ public:
}
/* Add parameter to proxy function */
if (gencomma >= 2)
if (gencomma >= 2) {
Printf(function_code, ", ");
if (is_interface)
Printf(interface_class_code, ", ");
}
gencomma = 2;
Printf(function_code, "%s %s", param_type, arg);
if (is_interface)
Printf(interface_class_code, "%s %s", param_type, arg);
Delete(arg);
Delete(param_type);
@ -2319,6 +2550,8 @@ public:
Printf(imcall, ")");
Printf(function_code, ")");
if (is_interface)
Printf(interface_class_code, ");\n");
// Transform return type used in PInvoke function (in intermediary class) to type used in C# wrapper function (in proxy class)
if ((tm = Swig_typemap_lookup("csout", n, "", 0))) {
@ -3187,6 +3420,50 @@ public:
substitution_performed = true;
Delete(classnametype);
}
if (Strstr(tm, "$csinterfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$csinterfacename", true);
substitution_performed = true;
Delete(interfacenametype);
}
if (Strstr(tm, "$*csinterfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
Delete(SwigType_pop(interfacenametype));
if (Len(interfacenametype) > 0) {
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$*csinterfacename", true);
substitution_performed = true;
}
Delete(interfacenametype);
}
if (Strstr(tm, "$&csinterfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
SwigType_add_pointer(interfacenametype);
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$&csinterfacename", true);
substitution_performed = true;
Delete(interfacenametype);
}
if (Strstr(tm, "$interfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$interfacename", false);
substitution_performed = true;
Delete(interfacenametype);
}
if (Strstr(tm, "$*interfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
Delete(SwigType_pop(interfacenametype));
if (Len(interfacenametype) > 0) {
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$*interfacename", false);
substitution_performed = true;
}
Delete(interfacenametype);
}
if (Strstr(tm, "$&interfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
SwigType_add_pointer(interfacenametype);
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$&interfacename", false);
substitution_performed = true;
Delete(interfacenametype);
}
Delete(strippedtype);
Delete(type);
@ -3232,6 +3509,20 @@ public:
Delete(replacementname);
}
/* -----------------------------------------------------------------------------
* substituteInterfacenameSpecialVariable()
* ----------------------------------------------------------------------------- */
void substituteInterfacenameSpecialVariable(SwigType *interfacenametype, String *tm, const char *interfacenamespecialvariable, bool qualified) {
String *interfacename = getInterfaceName(interfacenametype, qualified);
if (interfacename) {
String *replacementname = Copy(interfacename);
Replaceall(tm, interfacenamespecialvariable, replacementname);
Delete(replacementname);
}
}
/* -----------------------------------------------------------------------------
* emitTypeWrapperClass()
* ----------------------------------------------------------------------------- */
@ -3469,7 +3760,7 @@ public:
Wrapper *code_wrap = NewWrapper();
Printf(code_wrap->def, "SWIGEXPORT void SWIGSTDCALL %s(void *objarg", wname);
if (Len(smartptr)) {
if (smartptr) {
Printf(code_wrap->code, " %s *obj = (%s *)objarg;\n", smartptr, smartptr);
Printf(code_wrap->code, " // Keep a local instance of the smart pointer around while we are using the raw pointer\n");
Printf(code_wrap->code, " // Avoids using smart pointer specific API.\n");

View file

@ -472,8 +472,7 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGD\n");
Printf(f_runtime, "\n\n#ifndef SWIGD\n#define SWIGD\n#endif\n\n");
if (directorsEnabled()) {
Printf(f_runtime, "#define SWIG_DIRECTORS\n");
@ -911,7 +910,7 @@ public:
const char *val = Equal(Getattr(n, "enumvalue"), "true") ? "1" : "0";
Setattr(n, "enumvalue", val);
} else if (swigtype == T_CHAR) {
String *val = NewStringf("'%s'", Getattr(n, "enumvalue"));
String *val = NewStringf("'%(escape)s'", Getattr(n, "enumvalue"));
Setattr(n, "enumvalue", val);
Delete(val);
}
@ -1424,6 +1423,7 @@ public:
String *constants_code = NewString("");
SwigType *t = Getattr(n, "type");
SwigType *valuetype = Getattr(n, "valuetype");
ParmList *l = Getattr(n, "parms");
// Attach the non-standard typemaps to the parameter list.
@ -1471,16 +1471,21 @@ public:
Printf(constants_code, "%s;\n", override_value);
} else {
// Just take the value from the C definition and hope it compiles in D.
String* value = Getattr(n, "wrappedasconstant") ?
Getattr(n, "staticmembervariableHandler:value") : Getattr(n, "value");
// Add the stripped quotes back in.
if (SwigType_type(t) == T_STRING) {
Printf(constants_code, "\"%s\";\n", value);
} else if (SwigType_type(t) == T_CHAR) {
Printf(constants_code, "\'%s\';\n", value);
if (Getattr(n, "wrappedasconstant")) {
if (SwigType_type(valuetype) == T_CHAR)
Printf(constants_code, "\'%(escape)s\';\n", Getattr(n, "staticmembervariableHandler:value"));
else
Printf(constants_code, "%s;\n", Getattr(n, "staticmembervariableHandler:value"));
} else {
Printf(constants_code, "%s;\n", value);
// Add the stripped quotes back in.
String* value = Getattr(n, "value");
if (SwigType_type(t) == T_STRING) {
Printf(constants_code, "\"%s\";\n", value);
} else if (SwigType_type(t) == T_CHAR) {
Printf(constants_code, "\'%s\';\n", value);
} else {
Printf(constants_code, "%s;\n", value);
}
}
}
@ -3124,28 +3129,23 @@ private:
List *baselist = Getattr(n, "bases");
if (baselist) {
Iterator base = First(baselist);
while (base.item && GetFlag(base.item, "feature:ignore")) {
base = Next(base);
}
if (base.item) {
basenode = base.item;
c_baseclassname = Getattr(base.item, "name");
basename = createProxyName(c_baseclassname);
if (basename)
c_baseclass = SwigType_namestr(Getattr(base.item, "name"));
base = Next(base);
/* Warn about multiple inheritance for additional base class(es) */
while (base.item) {
if (GetFlag(base.item, "feature:ignore")) {
base = Next(base);
continue;
while (base.item) {
if (!GetFlag(base.item, "feature:ignore")) {
String *baseclassname = Getattr(base.item, "name");
if (!c_baseclassname) {
basenode = base.item;
c_baseclassname = baseclassname;
basename = createProxyName(c_baseclassname);
if (basename)
c_baseclass = SwigType_namestr(baseclassname);
} else {
/* Warn about multiple inheritance for additional base class(es) */
String *proxyclassname = Getattr(n, "classtypeobj");
Swig_warning(WARN_D_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Base %s of class %s ignored: multiple inheritance is not supported in D.\n", SwigType_namestr(baseclassname), SwigType_namestr(proxyclassname));
}
String *proxyclassname = SwigType_str(Getattr(n, "classtypeobj"), 0);
String *baseclassname = SwigType_str(Getattr(base.item, "name"), 0);
Swig_warning(WARN_D_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Base %s of class %s ignored: multiple inheritance is not supported in D.\n", baseclassname, proxyclassname);
base = Next(base);
}
base = Next(base);
}
}
}
@ -3170,7 +3170,7 @@ private:
}
} else if (basename && Len(pure_baseclass) > 0) {
Swig_warning(WARN_D_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s proxy: Base class %s ignored. Multiple inheritance is not supported in D. "
"Warning for %s, base class %s ignored. Multiple inheritance is not supported in D. "
"Perhaps you need one of the 'replace' or 'notderived' attributes in the dbase typemap?\n", typemap_lookup_type, pure_baseclass);
}
@ -3329,45 +3329,33 @@ private:
/* ---------------------------------------------------------------------------
* D::writeClassUpcast()
* --------------------------------------------------------------------------- */
void writeClassUpcast(Node *n, const String* d_class_name,
String* c_class_name, String* c_base_name) {
String *smartptr = Getattr(n, "feature:smartptr");
String *upcast_name = Swig_name_member(getNSpace(), d_class_name,
(smartptr != 0 ? "SmartPtrUpcast" : "Upcast"));
void writeClassUpcast(Node *n, const String* d_class_name, String* c_class_name, String* c_base_name) {
SwigType *smart = Swig_cparse_smartptr(n);
String *upcast_name = Swig_name_member(getNSpace(), d_class_name, (smart != 0 ? "SmartPtrUpcast" : "Upcast"));
String *upcast_wrapper_name = Swig_name_wrapper(upcast_name);
writeImDModuleFunction(upcast_name, "void*", "(void* objectRef)",
upcast_wrapper_name);
if (smartptr) {
SwigType *spt = Swig_cparse_type(smartptr);
if (spt) {
SwigType *smart = SwigType_typedef_resolve_all(spt);
Delete(spt);
SwigType *bsmart = Copy(smart);
SwigType *rclassname = SwigType_typedef_resolve_all(c_class_name);
SwigType *rbaseclass = SwigType_typedef_resolve_all(c_base_name);
Replaceall(bsmart, rclassname, rbaseclass);
Delete(rclassname);
Delete(rbaseclass);
String *smartnamestr = SwigType_namestr(smart);
String *bsmartnamestr = SwigType_namestr(bsmart);
Printv(upcasts_code,
"SWIGEXPORT ", bsmartnamestr, " * ", upcast_wrapper_name,
"(", smartnamestr, " *objectRef) {\n",
" return objectRef ? new ", bsmartnamestr, "(*objectRef) : 0;\n"
"}\n",
"\n", NIL);
Delete(bsmartnamestr);
Delete(smartnamestr);
Delete(bsmart);
} else {
Swig_error(Getfile(n), Getline(n),
"Invalid type (%s) in 'smartptr' feature for class %s.\n",
smartptr, c_class_name);
}
if (smart) {
SwigType *bsmart = Copy(smart);
SwigType *rclassname = SwigType_typedef_resolve_all(c_class_name);
SwigType *rbaseclass = SwigType_typedef_resolve_all(c_base_name);
Replaceall(bsmart, rclassname, rbaseclass);
Delete(rclassname);
Delete(rbaseclass);
String *smartnamestr = SwigType_namestr(smart);
String *bsmartnamestr = SwigType_namestr(bsmart);
Printv(upcasts_code,
"SWIGEXPORT ", bsmartnamestr, " * ", upcast_wrapper_name,
"(", smartnamestr, " *objectRef) {\n",
" return objectRef ? new ", bsmartnamestr, "(*objectRef) : 0;\n"
"}\n",
"\n", NIL);
Delete(bsmartnamestr);
Delete(smartnamestr);
Delete(bsmart);
} else {
Printv(upcasts_code,
"SWIGEXPORT ", c_base_name, " * ", upcast_wrapper_name,
@ -3382,6 +3370,7 @@ private:
Delete(upcast_name);
Delete(upcast_wrapper_name);
Delete(smart);
}
/* ---------------------------------------------------------------------------

View file

@ -785,6 +785,13 @@ private:
return SWIG_OK;
}
// Don't emit constructors for abstract director classes. They
// will never succeed anyhow.
if (Swig_methodclass(n) && Swig_directorclass(n)
&& Strcmp(Char(Getattr(n, "wrap:action")), director_prot_ctor_code) == 0) {
return SWIG_OK;
}
String *name = Getattr(n, "sym:name");
String *nodetype = Getattr(n, "nodeType");
bool is_static = is_static_member_function || isStatic(n);
@ -848,8 +855,7 @@ private:
Delete(c2);
Delete(c1);
if (Swig_methodclass(n) && Swig_directorclass(n)
&& Strcmp(Char(Getattr(n, "wrap:action")), director_prot_ctor_code) != 0) {
if (Swig_methodclass(n) && Swig_directorclass(n)) {
// The core SWIG code skips the first parameter when
// generating the $nondirector_new string. Recreate the
// action in this case. But don't it if we are using the
@ -1356,6 +1362,10 @@ private:
goargout(info->parms);
if (SwigType_type(info->result) != T_VOID) {
Swig_save("cgoGoWrapper", info->n, "type", "tmap:goout", NULL);
Setattr(info->n, "type", info->result);
String *goout = goTypemapLookup("goout", info->n, "swig_r");
if (goout == NULL) {
Printv(f_go_wrappers, "\treturn swig_r\n", NULL);
@ -1368,6 +1378,8 @@ private:
Printv(f_go_wrappers, goout, "\n", NULL);
Printv(f_go_wrappers, "\treturn swig_r_1\n", NULL);
}
Swig_restore(info->n);
}
Printv(f_go_wrappers, "}\n\n", NULL);
@ -1612,8 +1624,13 @@ private:
receiver = NULL;
}
Swig_save("cgoGoWrapper", n, "type", "tmap:goout", NULL);
Setattr(n, "type", result);
String *goout = goTypemapLookup("goout", n, "swig_r");
Swig_restore(n);
bool add_to_interface = (interfaces && !is_constructor && !is_destructor && !is_static && !overname && checkFunctionVisibility(n, NULL));
bool needs_wrapper = (gccgo_flag || receiver || is_constructor || is_destructor || parm_count > required_count);
@ -2106,6 +2123,7 @@ private:
emit_attach_parmmaps(parms, f);
int parm_count = emit_num_arguments(parms);
int required_count = emit_num_required(parms);
bool needs_swigargs = false;
emit_return_variable(n, result, f);
@ -2119,6 +2137,7 @@ private:
String *swigargs = NewString("\tstruct swigargs {\n");
if (parm_count > required_count) {
needs_swigargs = true;
Printv(swigargs, "\t\tintgo _swig_optargc;\n", NULL);
}
@ -2130,6 +2149,7 @@ private:
SwigType *pt = Getattr(p, "type");
String *ct = gcCTypeForGoValue(p, pt, ln);
Printv(swigargs, "\t\t\t", ct, ";\n", NULL);
needs_swigargs = true;
Delete(ct);
String *gn = NewStringf("_swig_go_%d", i);
@ -2146,6 +2166,7 @@ private:
String *ct = gcCTypeForGoValue(n, result, ln);
Delete(ln);
Printv(swigargs, "\t\t", ct, ";\n", NULL);
needs_swigargs = true;
Delete(ct);
ln = NewString("_swig_go_result");
@ -2154,7 +2175,7 @@ private:
Delete(ct);
Delete(ln);
}
Printv(swigargs, "\t} *swig_a = (struct swigargs *) swig_v;\n", NULL);
Printv(swigargs, "\t} SWIGSTRUCTPACKED *swig_a = (struct swigargs *) swig_v;\n", NULL);
// Copy the input arguments out of the structure into the Go local
// variables.
@ -2202,7 +2223,10 @@ private:
cleanupFunction(n, f, parms);
Printv(f->locals, swigargs, NULL);
if (needs_swigargs)
{
Printv(f->locals, swigargs, NULL);
}
Printv(f->code, "}\n", NULL);
@ -2421,7 +2445,8 @@ private:
}
String *code = Copy(Getattr(n, "wrap:action"));
Replaceall(code, Getattr(parms, "lname"), current);
Replace(code, Getattr(parms, "lname"), current, DOH_REPLACE_ANY | DOH_REPLACE_ID);
Delete(current);
Printv(actioncode, code, "\n", NULL);
}
@ -2574,6 +2599,14 @@ private:
Replaceall(f->code, "$cleanup", cleanup);
Delete(cleanup);
/* See if there is any return cleanup code */
String *tm;
if ((tm = Swig_typemap_lookup("ret", n, Swig_cresult_name(), 0))) {
Replaceall(tm, "$source", Swig_cresult_name());
Printf(f->code, "%s\n", tm);
Delete(tm);
}
Replaceall(f->code, "$symname", Getattr(n, "sym:name"));
}
@ -2699,6 +2732,9 @@ private:
* ---------------------------------------------------------------------- */
virtual int enumDeclaration(Node *n) {
if (getCurrentClass() && (cplus_mode != PUBLIC))
return SWIG_NOWRAP;
String *name = goEnumName(n);
if (Strcmp(name, "int") != 0) {
if (!ImportMode || !imported_package) {
@ -2773,28 +2809,39 @@ private:
String *get = NewString("");
Printv(get, Swig_cresult_name(), " = ", NULL);
char quote;
if (Getattr(n, "wrappedasconstant")) {
quote = '\0';
} else if (SwigType_type(type) == T_CHAR) {
quote = '\'';
} else if (SwigType_type(type) == T_STRING) {
quote = '"';
String *rawval = Getattr(n, "rawval");
if (rawval && Len(rawval)) {
if (SwigType_type(type) == T_STRING) {
Printv(get, "(char *)", NULL);
}
Printv(get, rawval, NULL);
} else {
quote = '\0';
}
char quote;
if (Getattr(n, "wrappedasconstant")) {
quote = '\0';
} else if (SwigType_type(type) == T_CHAR) {
quote = '\'';
} else if (SwigType_type(type) == T_STRING) {
Printv(get, "(char *)", NULL);
quote = '"';
} else {
quote = '\0';
}
if (quote != '\0') {
Printf(get, "%c", quote);
}
if (quote != '\0') {
Printf(get, "%c", quote);
}
Printv(get, Getattr(n, "value"), NULL);
Printv(get, Getattr(n, "value"), NULL);
if (quote != '\0') {
Printf(get, "%c", quote);
if (quote != '\0') {
Printf(get, "%c", quote);
}
}
Printv(get, ";\n", NULL);
Setattr(n, "wrap:action", get);
String *sname = Copy(symname);
@ -3976,7 +4023,7 @@ private:
Printv(f_c_directors, director_sig, NULL);
if (!gccgo_flag) {
Printv(f_c_directors, " struct { intgo p; } a;\n", NULL);
Printv(f_c_directors, " struct { intgo p; } SWIGSTRUCTPACKED a;\n", NULL);
Printv(f_c_directors, " a.p = go_val;\n", NULL);
Printv(f_c_directors, " crosscall2(", wname, ", &a, (int) sizeof a);\n", NULL);
@ -4148,7 +4195,6 @@ private:
Wrapper *dummy = NewWrapper();
emit_attach_parmmaps(parms, dummy);
DelWrapper(dummy);
Swig_typemap_attach_parms("gotype", parms, NULL);
Swig_typemap_attach_parms("imtype", parms, NULL);
@ -4205,6 +4251,8 @@ private:
Swig_typemap_attach_parms("goin", parms, dummy);
Swig_typemap_attach_parms("goargout", parms, dummy);
DelWrapper(dummy);
if (!is_ignored) {
// We use an interface to see if this method is defined in Go.
Printv(f_go_wrappers, "type ", interface_name, " interface {\n", NULL);
@ -5110,7 +5158,7 @@ private:
Delete(rname);
}
Printv(w->code, " } swig_a;\n", NULL);
Printv(w->code, " } SWIGSTRUCTPACKED swig_a;\n", NULL);
Printv(w->code, " swig_a.go_val = go_val;\n", NULL);
p = parms;

View file

@ -322,8 +322,7 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGGUILE\n");
Printf(f_runtime, "\n\n#ifndef SWIGGUILE\n#define SWIGGUILE\n#endif\n\n");
/* Write out directives and declarations */

View file

@ -0,0 +1,183 @@
/* -----------------------------------------------------------------------------
* This file is part of SWIG, which is licensed as a whole under version 3
* (or any later version) of the GNU General Public License. Some additional
* terms also apply to certain portions of SWIG. The full details of the SWIG
* license and copyrights can be found in the LICENSE and COPYRIGHT files
* included with the SWIG source code as distributed by the SWIG developers
* and at http://www.swig.org/legal.html.
*
* interface.cxx
*
* This module contains support for the interface feature.
* This feature is used in language modules where the target language does not
* naturally support C++ style multiple inheritance, but does support inheritance
* from multiple interfaces.
* ----------------------------------------------------------------------------- */
#include "swigmod.h"
static bool interface_feature_enabled = false;
/* -----------------------------------------------------------------------------
* collect_interface_methods()
*
* Create a list of all the methods from the base classes of class n that are
* marked as an interface. The resulting list is thus the list of methods that
* need to be implemented in order for n to be non-abstract.
* ----------------------------------------------------------------------------- */
static List *collect_interface_methods(Node *n) {
List *methods = NewList();
if (Hash *bases = Getattr(n, "interface:bases")) {
List *keys = Keys(bases);
for (Iterator base = First(keys); base.item; base = Next(base)) {
Node *cls = Getattr(bases, base.item);
if (cls == n)
continue;
for (Node *child = firstChild(cls); child; child = nextSibling(child)) {
if (Cmp(nodeType(child), "cdecl") == 0) {
if (GetFlag(child, "feature:ignore") || Getattr(child, "interface:owner"))
continue; // skip methods propagated to bases
Node *m = Copy(child);
set_nextSibling(m, NIL);
set_previousSibling(m, NIL);
Setattr(m, "interface:owner", cls);
Append(methods, m);
}
}
}
Delete(keys);
}
return methods;
}
/* -----------------------------------------------------------------------------
* collect_interface_bases
* ----------------------------------------------------------------------------- */
static void collect_interface_bases(Hash *bases, Node *n) {
if (Getattr(n, "feature:interface")) {
String *name = Getattr(n, "interface:name");
if (!Getattr(bases, name))
Setattr(bases, name, n);
}
if (List *baselist = Getattr(n, "bases")) {
for (Iterator base = First(baselist); base.item; base = Next(base)) {
if (!GetFlag(base.item, "feature:ignore")) {
if (Getattr(base.item, "feature:interface"))
collect_interface_bases(bases, base.item);
}
}
}
}
/* -----------------------------------------------------------------------------
* collect_interface_base_classes()
*
* Create a hash containing all the classes up the inheritance hierarchy
* marked with feature:interface (including this class n).
* Stops going up the inheritance chain as soon as a class is found without
* feature:interface.
* The idea is to find all the base interfaces that a class must implement.
* ----------------------------------------------------------------------------- */
static void collect_interface_base_classes(Node *n) {
if (Getattr(n, "feature:interface")) {
// check all bases are also interfaces
if (List *baselist = Getattr(n, "bases")) {
for (Iterator base = First(baselist); base.item; base = Next(base)) {
if (!GetFlag(base.item, "feature:ignore")) {
if (!Getattr(base.item, "feature:interface")) {
Swig_error(Getfile(n), Getline(n), "Base class '%s' of '%s' is not similarly marked as an interface.\n", SwigType_namestr(Getattr(base.item, "name")), SwigType_namestr(Getattr(n, "name")));
SWIG_exit(EXIT_FAILURE);
}
}
}
}
}
Hash *interface_bases = NewHash();
collect_interface_bases(interface_bases, n);
if (Len(interface_bases) == 0)
Delete(interface_bases);
else
Setattr(n, "interface:bases", interface_bases);
}
/* -----------------------------------------------------------------------------
* process_interface_name()
* ----------------------------------------------------------------------------- */
static void process_interface_name(Node *n) {
if (Getattr(n, "feature:interface")) {
String *interface_name = Getattr(n, "feature:interface:name");
if (!Len(interface_name)) {
Swig_error(Getfile(n), Getline(n), "The interface feature for '%s' is missing the name attribute.\n", SwigType_namestr(Getattr(n, "name")));
SWIG_exit(EXIT_FAILURE);
}
if (Strchr(interface_name, '%')) {
String *name = NewStringf(interface_name, Getattr(n, "sym:name"));
Setattr(n, "interface:name", name);
} else {
Setattr(n, "interface:name", interface_name);
}
}
}
/* -----------------------------------------------------------------------------
* Swig_interface_propagate_methods()
*
* Find all the base classes marked as an interface (with feature:interface) for
* class node n. For each of these, add all of its methods as methods of n so that
* n is not abstract. If class n is also marked as an interface, it will remain
* abstract and not have any methods added.
* ----------------------------------------------------------------------------- */
void Swig_interface_propagate_methods(Node *n) {
if (interface_feature_enabled) {
process_interface_name(n);
collect_interface_base_classes(n);
List *methods = collect_interface_methods(n);
bool is_interface = Getattr(n, "feature:interface") != 0;
for (Iterator mi = First(methods); mi.item; mi = Next(mi)) {
if (!is_interface && GetFlag(mi.item, "abstract"))
continue;
String *this_decl = Getattr(mi.item, "decl");
String *this_decl_resolved = SwigType_typedef_resolve_all(this_decl);
bool identically_overloaded_method = false; // true when a base class' method is implemented in n
if (SwigType_isfunction(this_decl_resolved)) {
String *name = Getattr(mi.item, "name");
for (Node *child = firstChild(n); child; child = nextSibling(child)) {
if (Getattr(child, "interface:owner"))
break; // at the end of the list are newly appended methods
if (checkAttribute(child, "name", name)) {
String *decl = SwigType_typedef_resolve_all(Getattr(child, "decl"));
identically_overloaded_method = Strcmp(decl, this_decl_resolved) == 0;
Delete(decl);
if (identically_overloaded_method)
break;
}
}
}
Delete(this_decl_resolved);
if (!identically_overloaded_method) {
// TODO: Fix if the method is overloaded with different arguments / has default args
appendChild(n, mi.item);
} else {
Delete(mi.item);
}
}
Delete(methods);
}
}
/* -----------------------------------------------------------------------------
* Swig_interface_feature_enable()
*
* Turn on interface feature support
* ----------------------------------------------------------------------------- */
void Swig_interface_feature_enable() {
interface_feature_enabled = true;
}

View file

@ -56,6 +56,7 @@ class JAVA:public Language {
String *imclass_class_code; // intermediary class code
String *proxy_class_def;
String *proxy_class_code;
String *interface_class_code; // if %feature("interface") was declared for a class, here goes the interface declaration
String *module_class_code;
String *proxy_class_name; // proxy class name
String *full_proxy_class_name;// fully qualified proxy class name when using nspace feature, otherwise same as proxy_class_name
@ -131,6 +132,7 @@ public:
imclass_class_code(NULL),
proxy_class_def(NULL),
proxy_class_code(NULL),
interface_class_code(NULL),
module_class_code(NULL),
proxy_class_name(NULL),
full_proxy_class_name(NULL),
@ -219,10 +221,14 @@ public:
String *nspace = Getattr(n, "sym:nspace");
String *symname = Copy(Getattr(n, "sym:name"));
if (symname && !GetFlag(n, "feature:flatnested")) {
for (Node *outer_class = Getattr(n, "nested:outer"); outer_class; outer_class = Getattr(outer_class, "nested:outer")) {
Push(symname, jnidescriptor ? "$" : ".");
Push(symname, Getattr(outer_class, "sym:name"));
}
for (Node *outer_class = Getattr(n, "nested:outer"); outer_class; outer_class = Getattr(outer_class, "nested:outer")) {
if (String* name = Getattr(outer_class, "sym:name")) {
Push(symname, jnidescriptor ? "$" : ".");
Push(symname, name);
}
else
return NULL;
}
}
if (nspace) {
if (package && !jnidescriptor)
@ -329,6 +335,7 @@ public:
SWIG_config_file("java.swg");
allow_overloading();
Swig_interface_feature_enable();
}
/* ---------------------------------------------------------------------
@ -452,7 +459,7 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n#define SWIGJAVA\n");
Printf(f_runtime, "\n\n#ifndef SWIGJAVA\n#define SWIGJAVA\n#endif\n\n");
if (directorsEnabled()) {
Printf(f_runtime, "#define SWIG_DIRECTORS\n");
@ -1347,8 +1354,10 @@ public:
// Add extra indentation
Replaceall(enum_code, "\n", "\n ");
Replaceall(enum_code, " \n", "\n");
Printv(proxy_class_constants_code, " ", enum_code, "\n\n", NIL);
if (GetFlag(getCurrentClass(), "feature:interface"))
Printv(interface_class_code, " ", enum_code, "\n\n", NIL);
else
Printv(proxy_class_constants_code, " ", enum_code, "\n\n", NIL);
} else {
// Global enums are defined in their own file
String *output_directory = outputDirectory(nspace);
@ -1436,7 +1445,7 @@ public:
const char *val = Equal(Getattr(n, "enumvalue"), "true") ? "1" : "0";
Setattr(n, "enumvalue", val);
} else if (swigtype == T_CHAR) {
String *val = NewStringf("'%s'", Getattr(n, "enumvalue"));
String *val = NewStringf("'%(escape)s'", Getattr(n, "enumvalue"));
Setattr(n, "enumvalue", val);
Delete(val);
}
@ -1567,6 +1576,7 @@ public:
virtual int constantWrapper(Node *n) {
String *symname = Getattr(n, "sym:name");
SwigType *t = Getattr(n, "type");
SwigType *valuetype = Getattr(n, "valuetype");
ParmList *l = Getattr(n, "parms");
String *tm;
String *return_type = NewString("");
@ -1668,8 +1678,8 @@ public:
} else {
// Alternative constant handling will use the C syntax to make a true Java constant and hope that it compiles as Java code
if (Getattr(n, "wrappedasconstant")) {
if (SwigType_type(t) == T_CHAR)
Printf(constants_code, "\'%s\';\n", Getattr(n, "staticmembervariableHandler:value"));
if (SwigType_type(valuetype) == T_CHAR)
Printf(constants_code, "\'%(escape)s\';\n", Getattr(n, "staticmembervariableHandler:value"));
else
Printf(constants_code, "%s;\n", Getattr(n, "staticmembervariableHandler:value"));
} else {
@ -1819,6 +1829,125 @@ public:
return Language::pragmaDirective(n);
}
/* -----------------------------------------------------------------------------
* getQualifiedInterfaceName()
* ----------------------------------------------------------------------------- */
String *getQualifiedInterfaceName(Node *n) {
String *ret = Getattr(n, "interface:qname");
if (!ret) {
String *nspace = Getattr(n, "sym:nspace");
String *symname = Getattr(n, "interface:name");
if (nspace) {
if (package)
ret = NewStringf("%s.%s.%s", package, nspace, symname);
else
ret = NewStringf("%s.%s", nspace, symname);
} else {
ret = Copy(symname);
}
Setattr(n, "interface:qname", ret);
}
return ret;
}
/* -----------------------------------------------------------------------------
* getInterfaceName()
* ----------------------------------------------------------------------------- */
String *getInterfaceName(SwigType *t, bool qualified) {
String *interface_name = NULL;
if (proxy_flag) {
Node *n = classLookup(t);
if (n && Getattr(n, "interface:name"))
interface_name = qualified ? getQualifiedInterfaceName(n) : Getattr(n, "interface:name");
}
return interface_name;
}
/* -----------------------------------------------------------------------------
* addInterfaceNameAndUpcasts()
* ----------------------------------------------------------------------------- */
void addInterfaceNameAndUpcasts(SwigType *smart, String *interface_list, String *interface_upcasts, Hash *base_list, String *c_classname) {
List *keys = Keys(base_list);
for (Iterator it = First(keys); it.item; it = Next(it)) {
Node *base = Getattr(base_list, it.item);
String *c_baseclass = SwigType_namestr(Getattr(base, "name"));
String *interface_name = Getattr(base, "interface:name");
if (Len(interface_list))
Append(interface_list, ", ");
Append(interface_list, interface_name);
Node *attributes = NewHash();
String *interface_code = Copy(typemapLookup(base, "javainterfacecode", Getattr(base, "classtypeobj"), WARN_JAVA_TYPEMAP_INTERFACECODE_UNDEF, attributes));
String *cptr_method_name = 0;
if (interface_code) {
Replaceall(interface_code, "$interfacename", interface_name);
Printv(interface_upcasts, interface_code, NIL);
cptr_method_name = Copy(Getattr(attributes, "tmap:javainterfacecode:cptrmethod"));
}
if (!cptr_method_name)
cptr_method_name = NewStringf("%s_GetInterfaceCPtr", interface_name);
Replaceall(cptr_method_name, ".", "_");
Replaceall(cptr_method_name, "$interfacename", interface_name);
String *upcast_method_name = Swig_name_member(getNSpace(), proxy_class_name, cptr_method_name);
upcastsCode(smart, upcast_method_name, c_classname, c_baseclass);
Delete(upcast_method_name);
Delete(cptr_method_name);
Delete(interface_code);
Delete(c_baseclass);
}
Delete(keys);
}
/* -----------------------------------------------------------------------------
* upcastsCode()
*
* Add code for C++ casting to base class
* ----------------------------------------------------------------------------- */
void upcastsCode(SwigType *smart, String *upcast_method_name, String *c_classname, String *c_baseclass) {
String *jniname = makeValidJniName(upcast_method_name);
String *wname = Swig_name_wrapper(jniname);
Printf(imclass_cppcasts_code, " public final static native long %s(long jarg1);\n", upcast_method_name);
if (smart) {
SwigType *bsmart = Copy(smart);
SwigType *rclassname = SwigType_typedef_resolve_all(c_classname);
SwigType *rbaseclass = SwigType_typedef_resolve_all(c_baseclass);
Replaceall(bsmart, rclassname, rbaseclass);
Delete(rclassname);
Delete(rbaseclass);
String *smartnamestr = SwigType_namestr(smart);
String *bsmartnamestr = SwigType_namestr(bsmart);
Printv(upcasts_code,
"SWIGEXPORT jlong JNICALL ", wname, "(JNIEnv *jenv, jclass jcls, jlong jarg1) {\n",
" jlong baseptr = 0;\n"
" ", smartnamestr, " *argp1;\n"
" (void)jenv;\n"
" (void)jcls;\n"
" argp1 = *(", smartnamestr, " **)&jarg1;\n"
" *(", bsmartnamestr, " **)&baseptr = argp1 ? new ", bsmartnamestr, "(*argp1) : 0;\n"
" return baseptr;\n"
"}\n", "\n", NIL);
Delete(bsmartnamestr);
Delete(smartnamestr);
Delete(bsmart);
} else {
Printv(upcasts_code,
"SWIGEXPORT jlong JNICALL ", wname, "(JNIEnv *jenv, jclass jcls, jlong jarg1) {\n",
" jlong baseptr = 0;\n"
" (void)jenv;\n"
" (void)jcls;\n"
" *(", c_baseclass, " **)&baseptr = *(", c_classname, " **)&jarg1;\n"
" return baseptr;\n"
"}\n", "\n", NIL);
}
Delete(wname);
Delete(jniname);
}
/* -----------------------------------------------------------------------------
* emitProxyClassDefAndCPPCasts()
* ----------------------------------------------------------------------------- */
@ -1828,9 +1957,12 @@ public:
String *c_baseclass = NULL;
String *baseclass = NULL;
String *c_baseclassname = NULL;
String *interface_list = NewStringEmpty();
String *interface_upcasts = NewStringEmpty();
SwigType *typemap_lookup_type = Getattr(n, "classtypeobj");
bool feature_director = Swig_directorclass(n) ? true : false;
bool has_outerclass = Getattr(n, "nested:outer") != 0 && !GetFlag(n, "feature:flatnested");
SwigType *smart = Swig_cparse_smartptr(n);
// Inheritance from pure Java classes
Node *attributes = NewHash();
@ -1843,32 +1975,31 @@ public:
if (!purebase_replace) {
List *baselist = Getattr(n, "bases");
if (baselist) {
Iterator base = First(baselist);
while (base.item && GetFlag(base.item, "feature:ignore")) {
base = Next(base);
}
if (base.item) {
c_baseclassname = Getattr(base.item, "name");
baseclass = Copy(getProxyName(c_baseclassname));
if (baseclass)
c_baseclass = SwigType_namestr(Getattr(base.item, "name"));
base = Next(base);
/* Warn about multiple inheritance for additional base class(es) */
while (base.item) {
if (GetFlag(base.item, "feature:ignore")) {
base = Next(base);
continue;
}
String *proxyclassname = Getattr(n, "classtypeobj");
String *baseclassname = Getattr(base.item, "name");
Swig_warning(WARN_JAVA_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s proxy: Base %s ignored. Multiple inheritance is not supported in Java.\n", SwigType_namestr(proxyclassname), SwigType_namestr(baseclassname));
base = Next(base);
}
}
Iterator base = First(baselist);
while (base.item) {
if (!(GetFlag(base.item, "feature:ignore") || Getattr(base.item, "feature:interface"))) {
String *baseclassname = Getattr(base.item, "name");
if (!c_baseclassname) {
c_baseclassname = baseclassname;
baseclass = Copy(getProxyName(baseclassname));
if (baseclass)
c_baseclass = SwigType_namestr(baseclassname);
} else {
/* Warn about multiple inheritance for additional base class(es) */
String *proxyclassname = Getattr(n, "classtypeobj");
Swig_warning(WARN_JAVA_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s, base %s ignored. Multiple inheritance is not supported in Java.\n", SwigType_namestr(proxyclassname), SwigType_namestr(baseclassname));
}
}
base = Next(base);
}
}
}
Hash *interface_bases = Getattr(n, "interface:bases");
if (interface_bases)
addInterfaceNameAndUpcasts(smart, interface_list, interface_upcasts, interface_bases, c_classname);
bool derived = baseclass && getProxyName(c_baseclassname);
if (derived && purebase_notderived)
pure_baseclass = empty_string;
@ -1883,7 +2014,7 @@ public:
Swig_error(Getfile(n), Getline(n), "The javabase typemap for proxy %s must contain just one of the 'replace' or 'notderived' attributes.\n", typemap_lookup_type);
} else if (Len(pure_baseclass) > 0 && Len(baseclass) > 0) {
Swig_warning(WARN_JAVA_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s proxy: Base %s ignored. Multiple inheritance is not supported in Java. "
"Warning for %s, base %s ignored. Multiple inheritance is not supported in Java. "
"Perhaps you need one of the 'replace' or 'notderived' attributes in the javabase typemap?\n", typemap_lookup_type, pure_baseclass);
}
@ -1899,6 +2030,10 @@ public:
Delete(doxygen_comments);
}
if (*Char(interface_list) && *Char(pure_interfaces))
Append(interface_list, ", ");
Append(interface_list, pure_interfaces);
// Start writing the proxy class
if (!has_outerclass) // Import statements
Printv(proxy_class_def, typemapLookup(n, "javaimports", typemap_lookup_type, WARN_NONE),"\n", NIL);
@ -1906,8 +2041,8 @@ public:
Printv(proxy_class_def, "static ", NIL); // C++ nested classes correspond to static java classes
Printv(proxy_class_def, typemapLookup(n, "javaclassmodifiers", typemap_lookup_type, WARN_JAVA_TYPEMAP_CLASSMOD_UNDEF), // Class modifiers
" $javaclassname", // Class name and bases
(*Char(wanted_base)) ? " extends " : "", wanted_base, *Char(pure_interfaces) ? // Pure Java interfaces
" implements " : "", pure_interfaces, " {", derived ? typemapLookup(n, "javabody_derived", typemap_lookup_type, WARN_JAVA_TYPEMAP_JAVABODY_UNDEF) : // main body of class
(*Char(wanted_base)) ? " extends " : "", wanted_base, *Char(interface_list) ? // Pure Java interfaces
" implements " : "", interface_list, " {", derived ? typemapLookup(n, "javabody_derived", typemap_lookup_type, WARN_JAVA_TYPEMAP_JAVABODY_UNDEF) : // main body of class
typemapLookup(n, "javabody", typemap_lookup_type, WARN_JAVA_TYPEMAP_JAVABODY_UNDEF), // main body of class
NIL);
@ -1950,6 +2085,8 @@ public:
if (*Char(destruct))
Printv(proxy_class_def, "\n ", destruct_methodmodifiers, " void ", destruct_methodname, "()", destructor_throws_clause, " ", destruct, "\n", NIL);
}
if (*Char(interface_upcasts))
Printv(proxy_class_def, interface_upcasts, NIL);
/* Insert directordisconnect typemap, if this class has directors enabled */
/* Also insert the swigTakeOwnership and swigReleaseOwnership methods */
@ -1971,6 +2108,8 @@ public:
Delete(take_jnicall);
}
Delete(interface_upcasts);
Delete(interface_list);
Delete(attributes);
Delete(destruct);
@ -1978,66 +2117,80 @@ public:
Printv(proxy_class_def, typemapLookup(n, "javacode", typemap_lookup_type, WARN_NONE), // extra Java code
"\n", NIL);
// Add code to do C++ casting to base class (only for classes in an inheritance hierarchy)
if (derived) {
String *smartptr = Getattr(n, "feature:smartptr");
String *upcast_method = Swig_name_member(getNSpace(), getClassPrefix(), smartptr != 0 ? "SWIGSmartPtrUpcast" : "SWIGUpcast");
String *jniname = makeValidJniName(upcast_method);
String *wname = Swig_name_wrapper(jniname);
Printf(imclass_cppcasts_code, " public final static native long %s(long jarg1);\n", upcast_method);
if (smartptr) {
SwigType *spt = Swig_cparse_type(smartptr);
if (spt) {
SwigType *smart = SwigType_typedef_resolve_all(spt);
Delete(spt);
SwigType *bsmart = Copy(smart);
SwigType *rclassname = SwigType_typedef_resolve_all(c_classname);
SwigType *rbaseclass = SwigType_typedef_resolve_all(c_baseclass);
Replaceall(bsmart, rclassname, rbaseclass);
Delete(rclassname);
Delete(rbaseclass);
String *smartnamestr = SwigType_namestr(smart);
String *bsmartnamestr = SwigType_namestr(bsmart);
Printv(upcasts_code,
"SWIGEXPORT jlong JNICALL ", wname, "(JNIEnv *jenv, jclass jcls, jlong jarg1) {\n",
" jlong baseptr = 0;\n"
" ", smartnamestr, " *argp1;\n"
" (void)jenv;\n"
" (void)jcls;\n"
" argp1 = *(", smartnamestr, " **)&jarg1;\n"
" *(", bsmartnamestr, " **)&baseptr = argp1 ? new ", bsmartnamestr, "(*argp1) : 0;\n"
" return baseptr;\n"
"}\n", "\n", NIL);
Delete(bsmartnamestr);
Delete(smartnamestr);
Delete(bsmart);
} else {
Swig_error(Getfile(n), Getline(n), "Invalid type (%s) in 'smartptr' feature for class %s.\n", smartptr, c_classname);
}
} else {
Printv(upcasts_code,
"SWIGEXPORT jlong JNICALL ", wname, "(JNIEnv *jenv, jclass jcls, jlong jarg1) {\n",
" jlong baseptr = 0;\n"
" (void)jenv;\n"
" (void)jcls;\n"
" *(", c_baseclass, " **)&baseptr = *(", c_classname, " **)&jarg1;\n"
" return baseptr;\n"
"}\n", "\n", NIL);
}
Delete(wname);
Delete(jniname);
Delete(upcast_method);
String *upcast_method_name = Swig_name_member(getNSpace(), getClassPrefix(), smart != 0 ? "SWIGSmartPtrUpcast" : "SWIGUpcast");
upcastsCode(smart, upcast_method_name, c_classname, c_baseclass);
Delete(upcast_method_name);
}
Delete(smart);
Delete(baseclass);
}
/* ----------------------------------------------------------------------
* classHandler()
* emitInterfaceDeclaration()
* ---------------------------------------------------------------------- */
virtual int classHandler(Node *n) {
void emitInterfaceDeclaration(Node *n, String *interface_name, File *f_interface, String *nspace) {
if (package || nspace) {
Printf(f_interface, "package ");
if (package)
Printv(f_interface, package, nspace ? "." : "", NIL);
if (nspace)
Printv(f_interface, nspace, NIL);
Printf(f_interface, ";\n");
}
Printv(f_interface, typemapLookup(n, "javaimports", Getattr(n, "classtypeobj"), WARN_NONE), "\n", NIL);
Printf(f_interface, "public interface %s", interface_name);
if (List *baselist = Getattr(n, "bases")) {
String *bases = 0;
for (Iterator base = First(baselist); base.item; base = Next(base)) {
if (GetFlag(base.item, "feature:ignore") || !Getattr(base.item, "feature:interface"))
continue; // TODO: warn about skipped non-interface bases
String *base_iname = Getattr(base.item, "interface:name");
if (!bases)
bases = Copy(base_iname);
else {
Append(bases, ", ");
Append(bases, base_iname);
}
}
if (bases) {
Printv(f_interface, " extends ", bases, NIL);
Delete(bases);
}
}
Printf(f_interface, " {\n");
Node *attributes = NewHash();
String *interface_code = Copy(typemapLookup(n, "javainterfacecode", Getattr(n, "classtypeobj"), WARN_JAVA_TYPEMAP_INTERFACECODE_UNDEF, attributes));
if (interface_code) {
String *interface_declaration = Copy(Getattr(attributes, "tmap:javainterfacecode:declaration"));
if (interface_declaration) {
Replaceall(interface_declaration, "$interfacename", interface_name);
Printv(f_interface, interface_declaration, NIL);
Delete(interface_declaration);
}
Delete(interface_code);
}
}
/* ----------------------------------------------------------------------
* classDeclaration()
* ---------------------------------------------------------------------- */
int classDeclaration(Node *n) {
return Language::classDeclaration(n);
}
/* ----------------------------------------------------------------------
* classHandler()
* ---------------------------------------------------------------------- */
virtual int classHandler(Node *n) {
File *f_proxy = NULL;
File *f_interface = NULL;
String *old_proxy_class_name = proxy_class_name;
String *old_full_proxy_class_name = full_proxy_class_name;
String *old_full_imclass_name = full_imclass_name;
@ -2047,6 +2200,8 @@ public:
String *old_proxy_class_def = proxy_class_def;
String *old_proxy_class_code = proxy_class_code;
bool has_outerclass = Getattr(n, "nested:outer") && !GetFlag(n, "feature:flatnested");
String *old_interface_class_code = interface_class_code;
interface_class_code = 0;
if (proxy_flag) {
proxy_class_name = NewString(Getattr(n, "sym:name"));
@ -2087,17 +2242,21 @@ public:
}
}
String *interface_name = Getattr(n, "feature:interface") ? Getattr(n, "interface:name") : 0;
if (outerClassesPrefix) {
String *fnspace = nspace ? NewStringf("%s.%s", nspace, outerClassesPrefix) : outerClassesPrefix;
if (!addSymbol(proxy_class_name, n, fnspace))
return SWIG_ERROR;
if (interface_name && !addInterfaceSymbol(interface_name, n, fnspace))
return SWIG_ERROR;
if (nspace)
Delete(fnspace);
Delete(outerClassesPrefix);
}
else {
} else {
if (!addSymbol(proxy_class_name, n, nspace))
return SWIG_ERROR;
if (interface_name && !addInterfaceSymbol(interface_name, n, nspace))
return SWIG_ERROR;
}
// Each outer proxy class goes into a separate file
@ -2133,11 +2292,27 @@ public:
destructor_call = NewString("");
destructor_throws_clause = NewString("");
proxy_class_constants_code = NewString("");
if (Getattr(n, "feature:interface")) {
interface_class_code = NewString("");
String *output_directory = outputDirectory(nspace);
String *filen = NewStringf("%s%s.java", output_directory, interface_name);
f_interface = NewFile(filen, "w", SWIG_output_files());
if (!f_interface) {
FileErrorDisplay(filen);
SWIG_exit(EXIT_FAILURE);
}
Append(filenames_list, filen); // file name ownership goes to the list
emitBanner(f_interface);
emitInterfaceDeclaration(n, interface_name, interface_class_code, nspace);
Delete(filen);
Delete(output_directory);
}
}
Language::classHandler(n);
if (proxy_flag) {
emitProxyClassDefAndCPPCasts(n);
String *javaclazzname = Swig_name_member(getNSpace(), getClassPrefix(), ""); // mangled full proxy class name
@ -2145,18 +2320,22 @@ public:
Replaceall(proxy_class_def, "$javaclassname", proxy_class_name);
Replaceall(proxy_class_code, "$javaclassname", proxy_class_name);
Replaceall(proxy_class_constants_code, "$javaclassname", proxy_class_name);
Replaceall(interface_class_code, "$javaclassname", proxy_class_name);
Replaceall(proxy_class_def, "$javaclazzname", javaclazzname);
Replaceall(proxy_class_code, "$javaclazzname", javaclazzname);
Replaceall(proxy_class_constants_code, "$javaclazzname", javaclazzname);
Replaceall(interface_class_code, "$javaclazzname", javaclazzname);
Replaceall(proxy_class_def, "$module", module_class_name);
Replaceall(proxy_class_code, "$module", module_class_name);
Replaceall(proxy_class_constants_code, "$module", module_class_name);
Replaceall(interface_class_code, "$module", module_class_name);
Replaceall(proxy_class_def, "$imclassname", full_imclass_name);
Replaceall(proxy_class_code, "$imclassname", full_imclass_name);
Replaceall(proxy_class_constants_code, "$imclassname", full_imclass_name);
Replaceall(interface_class_code, "$imclassname", full_imclass_name);
if (!has_outerclass)
Printv(f_proxy, proxy_class_def, proxy_class_code, NIL);
@ -2221,8 +2400,16 @@ public:
Delete(downcast_method);
}
if (f_interface) {
Printv(f_interface, interface_class_code, "}\n", NIL);
Delete(f_interface);
f_interface = 0;
}
emitDirectorExtraMethods(n);
Delete(interface_class_code);
interface_class_code = old_interface_class_code;
Delete(javaclazzname);
Delete(proxy_class_name);
proxy_class_name = old_proxy_class_name;
@ -2314,6 +2501,8 @@ public:
bool setter_flag = false;
String *pre_code = NewString("");
String *post_code = NewString("");
bool is_interface = Getattr(parentNode(n), "feature:interface") != 0
&& !static_flag && Getattr(n, "interface:owner") == 0;
if (!proxy_flag)
return;
@ -2372,6 +2561,9 @@ public:
if (static_flag)
Printf(function_code, "static ");
Printf(function_code, "%s %s(", return_type, proxy_function_name);
if (is_interface)
Printf(interface_class_code, " %s %s(", return_type, proxy_function_name);
Printv(imcall, full_imclass_name, ".$imfuncname(", NIL);
if (!static_flag) {
@ -2459,10 +2651,15 @@ public:
}
/* Add parameter to proxy function */
if (gencomma >= 2)
if (gencomma >= 2) {
Printf(function_code, ", ");
if (is_interface)
Printf(interface_class_code, ", ");
}
gencomma = 2;
Printf(function_code, "%s %s", param_type, arg);
if (is_interface)
Printf(interface_class_code, "%s %s", param_type, arg);
if (prematureGarbageCollectionPreventionParameter(pt, p)) {
String *pgcppname = Getattr(p, "tmap:javain:pgcppname");
@ -2484,6 +2681,8 @@ public:
Printf(imcall, ")");
Printf(function_code, ")");
if (is_interface)
Printf(interface_class_code, ");\n");
// Transform return type used in JNI function (in intermediary class) to type used in Java wrapper function (in proxy class)
if ((tm = Swig_typemap_lookup("javaout", n, "", 0))) {
@ -3206,6 +3405,50 @@ public:
substitution_performed = true;
Delete(classnametype);
}
if (Strstr(tm, "$javainterfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$javainterfacename", jnidescriptor, true);
substitution_performed = true;
Delete(interfacenametype);
}
if (Strstr(tm, "$*javainterfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
Delete(SwigType_pop(interfacenametype));
if (Len(interfacenametype) > 0) {
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$*javainterfacename", jnidescriptor, true);
substitution_performed = true;
}
Delete(interfacenametype);
}
if (Strstr(tm, "$&javainterfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
SwigType_add_pointer(interfacenametype);
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$&javainterfacename", jnidescriptor, true);
substitution_performed = true;
Delete(interfacenametype);
}
if (Strstr(tm, "$interfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$interfacename", jnidescriptor, false);
substitution_performed = true;
Delete(interfacenametype);
}
if (Strstr(tm, "$*interfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
Delete(SwigType_pop(interfacenametype));
if (Len(interfacenametype) > 0) {
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$*interfacename", jnidescriptor, false);
substitution_performed = true;
}
Delete(interfacenametype);
}
if (Strstr(tm, "$&interfacename")) {
SwigType *interfacenametype = Copy(strippedtype);
SwigType_add_pointer(interfacenametype);
substituteInterfacenameSpecialVariable(interfacenametype, tm, "$&interfacename", jnidescriptor, false);
substitution_performed = true;
Delete(interfacenametype);
}
Delete(strippedtype);
Delete(type);
@ -3254,6 +3497,24 @@ public:
Delete(replacementname);
}
/* -----------------------------------------------------------------------------
* substituteInterfacenameSpecialVariable()
* ----------------------------------------------------------------------------- */
void substituteInterfacenameSpecialVariable(SwigType *interfacenametype, String *tm, const char *interfacenamespecialvariable, bool jnidescriptor, bool qualified) {
String *interfacename = getInterfaceName(interfacenametype/*, jnidescriptor*/, qualified);
if (interfacename) {
String *replacementname = Copy(interfacename);
if (jnidescriptor)
Replaceall(replacementname,".","/");
Replaceall(tm, interfacenamespecialvariable, replacementname);
Delete(replacementname);
}
}
/* -----------------------------------------------------------------------------
* emitTypeWrapperClass()
* ----------------------------------------------------------------------------- */
@ -3412,7 +3673,7 @@ public:
* ----------------------------------------------------------------------------- */
String *prematureGarbageCollectionPreventionParameter(SwigType *t, Parm *p) {
String *proxyClassName = 0;
String *pgcpp_java_type = 0;
String *jtype = NewString(Getattr(p, "tmap:jtype"));
// Strip C comments
@ -3429,11 +3690,9 @@ public:
if (Cmp(jtype, "long") == 0) {
if (proxy_flag) {
if (!GetFlag(p, "tmap:jtype:nopgcpp") && !nopgcpp_flag) {
String *proxyname = getProxyName(t);
if (proxyname) {
// Found a struct/class parameter passed by value, reference, pointer, or pointer reference
proxyClassName = proxyname;
} else {
String *interface_name = getInterfaceName(t, true);
pgcpp_java_type = interface_name ? interface_name : getProxyName(t);
if (!pgcpp_java_type) {
// Look for proxy class parameters passed to C++ layer using non-default typemaps, ie not one of above types
String *jstype = NewString(Getattr(p, "tmap:jstype"));
if (jstype) {
@ -3455,7 +3714,7 @@ public:
if (cls && !Getattr(cls, "feature:ignore")) {
String *symname = Getattr(cls, "sym:name");
if (symname && Strcmp(symname, jstype) == 0) {
proxyClassName = symname;
pgcpp_java_type = symname;
}
}
}
@ -3467,7 +3726,7 @@ public:
}
}
Delete(jtype);
return proxyClassName;
return pgcpp_java_type;
}
/* -----------------------------------------------------------------------------
@ -3619,7 +3878,7 @@ public:
"SWIGEXPORT void JNICALL Java_%s%s_%s(JNIEnv *jenv, jclass jcls, jobject jself, jlong objarg, jboolean jswig_mem_own, "
"jboolean jweak_global) {\n", jnipackage, jni_imclass_name, swig_director_connect_jni);
if (Len(smartptr)) {
if (smartptr) {
Printf(code_wrap->code, " %s *obj = *((%s **)&objarg);\n", smartptr, smartptr);
Printf(code_wrap->code, " (void)jcls;\n");
Printf(code_wrap->code, " // Keep a local instance of the smart pointer around while we are using the raw pointer\n");

View file

@ -1100,7 +1100,7 @@ int JSEmitter::emitSetter(Node *n, bool is_member, bool is_static) {
* ----------------------------------------------------------------------------- */
int JSEmitter::emitConstant(Node *n) {
// HACK: somehow it happened under OSX that before everything started
// HACK: somehow it happened under Mac OS X that before everything started
// a lot of SWIG internal constants were emitted
// This didn't happen on other platforms yet...
// we ignore those premature definitions
@ -1354,6 +1354,11 @@ void JSEmitter::emitCleanupCode(Node *n, Wrapper *wrapper, ParmList *params) {
}
}
/* See if there is any return cleanup code */
if ((tm = Swig_typemap_lookup("ret", n, Swig_cresult_name(), 0))) {
Printf(wrapper->code, "%s\n", tm);
Delete(tm);
}
}
int JSEmitter::switchNamespace(Node *n) {

View file

@ -873,7 +873,7 @@ int Language::cDeclaration(Node *n) {
} else {
// Found an unignored templated method that has an empty template instantiation (%template())
// Ignore it unless it has been %rename'd
if (Strncmp(symname, "__dummy_", 8) == 0) {
if (Strncmp(symname, "__dummy_", 8) == 0 && Cmp(storage, "typedef") != 0) {
SetFlag(n, "feature:ignore");
Swig_warning(WARN_LANG_TEMPLATE_METHOD_IGNORE, input_file, line_number,
"%%template() contains no name. Template method ignored: %s\n", Swig_name_decl(n));
@ -1652,6 +1652,9 @@ int Language::externDeclaration(Node *n) {
* ---------------------------------------------------------------------- */
int Language::enumDeclaration(Node *n) {
if (CurrentClass && (cplus_mode != PUBLIC))
return SWIG_NOWRAP;
String *oldNSpace = NSpace;
NSpace = Getattr(n, "sym:nspace");
@ -3133,6 +3136,31 @@ int Language::addSymbol(const String *s, const Node *n, const_String_or_char_ptr
return 1;
}
/* -----------------------------------------------------------------------------
* Language::addInterfaceSymbol()
*
* Adds a symbol entry into the target language symbol tables - for the interface
* feature only.
* Returns 1 if the symbol is added successfully.
* The scope is as per addSymbol.
* ----------------------------------------------------------------------------- */
int Language::addInterfaceSymbol(const String *interface_name, Node *n, const_String_or_char_ptr scope) {
if (interface_name) {
Node *existing_symbol = symbolLookup(interface_name, scope);
if (existing_symbol) {
String *proxy_class_name = Getattr(n, "sym:name");
Swig_error(input_file, line_number, "The interface feature name '%s' for proxy class '%s' is already defined in the generated target language module in scope '%s'.\n",
interface_name, proxy_class_name, scope);
Swig_error(Getfile(existing_symbol), Getline(existing_symbol), "Previous declaration of '%s'\n", interface_name);
return 0;
}
if (!addSymbol(interface_name, n, scope))
return 0;
}
return 1;
}
/* -----------------------------------------------------------------------------
* Language::symbolAddScope()
*
@ -3229,7 +3257,7 @@ void Language::dumpSymbols() {
* Language::symbolLookup()
* ----------------------------------------------------------------------------- */
Node *Language::symbolLookup(String *s, const_String_or_char_ptr scope) {
Node *Language::symbolLookup(const String *s, const_String_or_char_ptr scope) {
Hash *symbols = Getattr(symtabs, scope ? scope : "");
if (!symbols) {
return NULL;
@ -3820,6 +3848,7 @@ String *Language::defaultExternalRuntimeFilename() {
/* -----------------------------------------------------------------------------
* Language::replaceSpecialVariables()
*
* Language modules should implement this if special variables are to be handled
* correctly in the $typemap(...) special variable macro.
* method - typemap method name
@ -3839,3 +3868,4 @@ Language *Language::instance() {
Hash *Language::getClassHash() const {
return classhash;
}

View file

@ -329,8 +329,7 @@ public:
/* Standard stuff for the SWIG runtime section */
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGLUA\n");
Printf(f_runtime, "\n\n#ifndef SWIGLUA\n#define SWIGLUA\n#endif\n\n");
emitLuaFlavor(f_runtime);
@ -857,6 +856,9 @@ public:
//Printf(stdout,"Swig_overload_dispatch %s %s '%s' %d\n",symname,wname,dispatch,maxargs);
if (!luaAddSymbol(lua_name, n)) {
DelWrapper(f);
Delete(dispatch);
Delete(tmp);
return SWIG_ERROR;
}
@ -1158,6 +1160,9 @@ public:
* ------------------------------------------------------------ */
virtual int enumDeclaration(Node *n) {
if (getCurrentClass() && (cplus_mode != PUBLIC))
return SWIG_NOWRAP;
current[STATIC_CONST] = true;
current[ENUM_CONST] = true;
// There is some slightly specific behaviour with enums. Basically,

View file

@ -64,7 +64,7 @@ static const char *usage1 = (const char *) "\
-copyctor - Automatically generate copy constructors wherever possible\n\
-cpperraswarn - Treat the preprocessor #error statement as #warning (default)\n\
-cppext <ext> - Change file extension of generated C++ files to <ext>\n\
(default is cxx, except for PHP which uses cpp)\n\
(default is cxx, except for PHP5 which uses cpp)\n\
-copyright - Display copyright notices\n\
-debug-classes - Display information about the classes found in the interface\n\
-debug-module <n>- Display module parse tree at stages 1-4, <n> is a csv list of stages\n\

View file

@ -958,9 +958,7 @@ MODULA3():
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGMODULA3\n");
Printf(f_runtime, "\n");
Printf(f_runtime, "\n\n#ifndef SWIGMODULA3\n#define SWIGMODULA3\n#endif\n\n");
Swig_name_register("wrapper", "Modula3_%f");
if (old_variable_names) {
@ -2178,20 +2176,24 @@ MODULA3():
/* Deal with inheritance */
List *baselist = Getattr(n, "bases");
if (baselist != NIL) {
if (baselist) {
Iterator base = First(baselist);
if (base.item) {
c_baseclassname = Getattr(base.item, "name");
baseclass = Copy(getProxyName(c_baseclassname));
if (baseclass) {
c_baseclass = SwigType_namestr(Getattr(base.item, "name"));
while (base.item) {
if (!GetFlag(base.item, "feature:ignore")) {
String *baseclassname = Getattr(base.item, "name");
if (!c_baseclassname) {
c_baseclassname = baseclassname;
baseclass = Copy(getProxyName(baseclassname));
if (baseclass)
c_baseclass = SwigType_namestr(baseclassname);
} else {
/* Warn about multiple inheritance for additional base class(es) */
String *proxyclassname = Getattr(n, "classtypeobj");
Swig_warning(WARN_MODULA3_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s, base %s ignored. Multiple inheritance is not supported in Modula 3.\n", SwigType_namestr(proxyclassname), SwigType_namestr(baseclassname));
}
}
base = Next(base);
if (base.item != NIL) {
Swig_warning(WARN_MODULA3_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s proxy: Base %s ignored. Multiple inheritance is not supported in Modula 3.\n",
name, Getattr(base.item, "name"));
}
}
}
@ -2203,7 +2205,7 @@ MODULA3():
const String *pure_baseclass = typemapLookup(n, "m3base", name, WARN_NONE);
if (hasContent(pure_baseclass) && hasContent(baseclass)) {
Swig_warning(WARN_MODULA3_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s proxy: Base %s ignored. Multiple inheritance is not supported in Modula 3.\n", name, pure_baseclass);
"Warning for %s, base %s ignored. Multiple inheritance is not supported in Modula 3.\n", name, pure_baseclass);
}
// Pure Modula 3 interfaces
const String *pure_interfaces = typemapLookup(n, derived ? "m3interfaces_derived" : "m3interfaces",
@ -2433,7 +2435,7 @@ MODULA3():
base = Next(base);
if (base.item) {
Swig_warning(WARN_MODULA3_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s proxy: Base %s ignored. Multiple inheritance is not supported in Modula 3.\n",
"Warning for %s, base %s ignored. Multiple inheritance is not supported in Modula 3.\n",
proxy_class_name, Getattr(base.item, "name"));
}
}

View file

@ -150,9 +150,7 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGMZSCHEME\n");
Printf(f_runtime, "\n");
Printf(f_runtime, "\n\n#ifndef SWIGMZSCHEME\n#define SWIGMZSCHEME\n#endif\n\n");
module = Getattr(n, "name");

View file

@ -269,8 +269,8 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGOCAML\n");
Printf(f_runtime, "\n\n#ifndef SWIGOCAML\n#define SWIGOCAML\n#endif\n\n");
Printf(f_runtime, "#define SWIG_MODULE \"%s\"\n", module);
/* Module name */
Printf(f_mlbody, "let module_name = \"%s\"\n", module);
@ -676,6 +676,14 @@ public:
Printv(f->code, tm, "\n", NIL);
}
}
/* See if there is any return cleanup code */
if ((tm = Swig_typemap_lookup("ret", n, Swig_cresult_name(), 0))) {
Replaceall(tm, "$source", Swig_cresult_name());
Printf(f->code, "%s\n", tm);
Delete(tm);
}
// Free any memory allocated by the function being wrapped..
if ((tm = Swig_typemap_lookup("swig_result", n, Swig_cresult_name(), 0))) {
@ -1287,6 +1295,9 @@ public:
* typedef enum and enum are handled. I need to produce consistent names,
* which means looking up and registering by typedef and enum name. */
int enumDeclaration(Node *n) {
if (getCurrentClass() && (cplus_mode != PUBLIC))
return SWIG_NOWRAP;
String *name = Getattr(n, "name");
if (name) {
String *oname = NewString(name);

View file

@ -194,8 +194,8 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGOCTAVE\n");
Printf(f_runtime, "\n\n#ifndef SWIGOCTAVE\n#define SWIGOCTAVE\n#endif\n\n");
Printf(f_runtime, "#define SWIG_name_d \"%s\"\n", module);
Printf(f_runtime, "#define SWIG_name %s\n", module);
@ -234,7 +234,7 @@ public:
}
Printf(f_init, "return true;\n}\n");
Printf(s_global_tab, "{0,0,0,0,0}\n};\n");
Printf(s_global_tab, "{0,0,0,0,0,0}\n};\n");
Printv(f_wrappers, s_global_tab, NIL);
SwigType_emit_type_table(f_runtime, f_wrappers);
@ -469,7 +469,6 @@ public:
value = Getattr(p, "tmap:doc:value");
}
// Note: the generated name should be consistent with that in kwnames[]
name = name ? name : Getattr(p, "name");
name = name ? name : Getattr(p, "lname");
name = Swig_name_make(p, 0, name, 0, 0); // rename parameter if a keyword
@ -966,25 +965,13 @@ public:
SwigType *t = Copy(Getattr(n, "name"));
SwigType_add_pointer(t);
String *smartptr = Getattr(n, "feature:smartptr"); // Replace storing a pointer to underlying class with a smart pointer (intended for use with non-intrusive smart pointers)
SwigType *smart = 0;
if (smartptr) {
SwigType *cpt = Swig_cparse_type(smartptr);
if (cpt) {
smart = SwigType_typedef_resolve_all(cpt);
Delete(cpt);
} else {
// TODO: report line number of where the feature comes from
Swig_error(Getfile(n), Getline(n), "Invalid type (%s) in 'smartptr' feature for class %s.\n", smartptr, class_name);
}
}
// Replace storing a pointer to underlying class with a smart pointer (intended for use with non-intrusive smart pointers)
SwigType *smart = Swig_cparse_smartptr(n);
String *wrap_class = NewStringf("&_wrap_class_%s", class_name);
if(smart){
if (smart) {
SwigType_add_pointer(smart);
SwigType_remember_clientdata(smart, wrap_class);
}
Delete(smart);
Delete(smartptr);
//String *wrap_class = NewStringf("&_wrap_class_%s", class_name);
SwigType_remember_clientdata(t, wrap_class);
@ -1010,7 +997,7 @@ public:
Delete(cnameshdw);
}
Printf(s_members_tab, "{0,0,0,0}\n};\n");
Printf(s_members_tab, "{0,0,0,0,0,0}\n};\n");
Printv(f_wrappers, s_members_tab, NIL);
String *base_class_names = NewString("");
@ -1064,6 +1051,7 @@ public:
Delete(base_class);
Delete(base_class_names);
Delete(smart);
Delete(t);
Delete(s_members_tab);
s_members_tab = 0;

View file

@ -433,6 +433,7 @@ String *Swig_overload_dispatch_cast(Node *n, const_String_or_char_ptr fmt, int *
int fn = 0;
Node *ni = Getitem(dispatch, i);
Parm *pi = Getattr(ni, "wrap:parms");
bool implicitconvtypecheckoff = GetFlag(ni, "implicitconvtypecheckoff") != 0;
int num_required = emit_num_required(pi);
int num_arguments = emit_num_arguments(pi);
if (num_arguments > *maxargs)
@ -476,6 +477,7 @@ String *Swig_overload_dispatch_cast(Node *n, const_String_or_char_ptr fmt, int *
String *tm = Getattr(pj, "tmap:typecheck");
if (tm) {
tm = Copy(tm);
/* normalise for comparison later */
Replaceid(tm, Getattr(pj, "lname"), "_v");
@ -528,13 +530,14 @@ String *Swig_overload_dispatch_cast(Node *n, const_String_or_char_ptr fmt, int *
String *tmp = NewStringf(argv_template_string, j);
String *conv = Getattr(pj, "implicitconv");
if (conv) {
if (conv && !implicitconvtypecheckoff) {
Replaceall(tm, "$implicitconv", conv);
} else {
Replaceall(tm, "$implicitconv", "0");
}
Replaceall(tm, "$input", tmp);
Printv(f, "{\n", tm, "}\n", NIL);
Delete(tm);
fn = i + 1;
Printf(f, "if (!_v) goto check_%d;\n", fn);
Printf(f, "_ranki += _v*_pi;\n");
@ -574,6 +577,9 @@ String *Swig_overload_dispatch_cast(Node *n, const_String_or_char_ptr fmt, int *
if (fn)
Printf(f, "check_%d:\n\n", fn);
if (implicitconvtypecheckoff)
Delattr(ni, "implicitconvtypecheckoff");
Delete(lfmt);
Delete(coll);
}
@ -607,6 +613,7 @@ String *Swig_overload_dispatch_fast(Node *n, const_String_or_char_ptr fmt, int *
int fn = 0;
Node *ni = Getitem(dispatch, i);
Parm *pi = Getattr(ni, "wrap:parms");
bool implicitconvtypecheckoff = GetFlag(ni, "implicitconvtypecheckoff") != 0;
int num_required = emit_num_required(pi);
int num_arguments = emit_num_arguments(pi);
if (num_arguments > *maxargs)
@ -646,6 +653,7 @@ String *Swig_overload_dispatch_fast(Node *n, const_String_or_char_ptr fmt, int *
String *tm = Getattr(pj, "tmap:typecheck");
if (tm) {
tm = Copy(tm);
/* normalise for comparison later */
Replaceid(tm, Getattr(pj, "lname"), "_v");
@ -699,13 +707,14 @@ String *Swig_overload_dispatch_fast(Node *n, const_String_or_char_ptr fmt, int *
String *tmp = NewStringf(argv_template_string, j);
String *conv = Getattr(pj, "implicitconv");
if (conv) {
if (conv && !implicitconvtypecheckoff) {
Replaceall(tm, "$implicitconv", conv);
} else {
Replaceall(tm, "$implicitconv", "0");
}
Replaceall(tm, "$input", tmp);
Printv(f, "{\n", tm, "}\n", NIL);
Delete(tm);
fn = i + 1;
Printf(f, "if (!_v) goto check_%d;\n", fn);
}
@ -737,6 +746,9 @@ String *Swig_overload_dispatch_fast(Node *n, const_String_or_char_ptr fmt, int *
if (fn)
Printf(f, "check_%d:\n\n", fn);
if (implicitconvtypecheckoff)
Delattr(ni, "implicitconvtypecheckoff");
Delete(lfmt);
Delete(coll);
}

View file

@ -325,8 +325,8 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGPERL\n");
Printf(f_runtime, "\n\n#ifndef SWIGPERL\n#define SWIGPERL\n#endif\n\n");
if (directorsEnabled()) {
Printf(f_runtime, "#define SWIG_DIRECTORS\n");
}
@ -1045,21 +1045,9 @@ public:
String *tt = Getattr(n, "tmap:varout:type");
if (tt) {
String *tm = NewStringf("&SWIGTYPE%s", SwigType_manglestr(t));
if (Replaceall(tt, "$1_descriptor", tm)) {
SwigType_remember(t);
}
Delete(tm);
SwigType *st = Copy(t);
SwigType_add_pointer(st);
tm = NewStringf("&SWIGTYPE%s", SwigType_manglestr(st));
if (Replaceall(tt, "$&1_descriptor", tm)) {
SwigType_remember(st);
}
Delete(tm);
Delete(st);
tt = NewStringf("&%s", tt);
} else {
tt = (String *) "0";
tt = NewString("0");
}
/* Now add symbol to the PERL interpreter */
if (GetFlag(n, "feature:immutable")) {
@ -1087,6 +1075,7 @@ public:
if (export_all)
Printf(exported, "$%s ", iname);
Delete(tt);
DelWrapper(setf);
DelWrapper(getf);
Delete(getname);
@ -2141,6 +2130,8 @@ public:
String *cres = SwigType_lstr(returntype, "c_result");
Printf(w->code, "%s;\n", cres);
Delete(cres);
}
if (!ignored_method) {
String *pres = NewStringf("SV *%s", Swig_cresult_name());
Wrapper_add_local(w, Swig_cresult_name(), pres);
Delete(pres);

View file

@ -43,7 +43,7 @@
#include <errno.h>
static const char *usage = "\
PHP Options (available with -php)\n\
PHP Options (available with -php7)\n\
-noproxy - Don't generate proxy classes.\n\
-prefix <prefix> - Prepend <prefix> to all class names in PHP wrappers\n\
\n";
@ -100,6 +100,11 @@ static String *s_oowrappers;
static String *s_fakeoowrappers;
static String *s_phpclasses;
/* To reduce code size (generated and compiled) we only want to emit each
* different arginfo once, so we need to track which have been used.
*/
static Hash *arginfo_used;
/* Variables for using PHP classes */
static Node *current_class = 0;
@ -129,6 +134,7 @@ extern "C" {
static void SwigPHP_emit_resource_registrations() {
Iterator ki;
bool emitted_default_dtor = false;
if (!zend_types)
return;
@ -140,9 +146,7 @@ static void SwigPHP_emit_resource_registrations() {
DOH *key = ki.key;
Node *class_node = ki.item;
String *human_name = key;
// Write out destructor function header
Printf(s_wrappers, "static ZEND_RSRC_DTOR_FUNC(_wrap_destroy%s) {\n", key);
String *rsrc_dtor_name = NULL;
// write out body
if (class_node != NOTCLASS) {
@ -152,51 +156,42 @@ static void SwigPHP_emit_resource_registrations() {
human_name = Getattr(class_node, "name");
// Do we have a known destructor for this type?
if (destructor) {
Printf(s_wrappers, " %s(rsrc, SWIGTYPE%s->name TSRMLS_CC);\n", destructor, key);
} else {
Printf(s_wrappers, " /* No destructor for class %s */\n", human_name);
Printf(s_wrappers, " efree(rsrc->ptr);\n");
rsrc_dtor_name = NewStringf("_wrap_destroy%s", key);
// Write out custom destructor function
Printf(s_wrappers, "static ZEND_RSRC_DTOR_FUNC(%s) {\n", rsrc_dtor_name);
Printf(s_wrappers, " %s(res, SWIGTYPE%s->name);\n", destructor, key);
Printf(s_wrappers, "}\n");
}
} else {
Printf(s_wrappers, " /* No destructor for simple type %s */\n", key);
Printf(s_wrappers, " efree(rsrc->ptr);\n");
}
// close function
Printf(s_wrappers, "}\n");
if (!rsrc_dtor_name) {
rsrc_dtor_name = NewString("_swig_default_rsrc_destroy");
if (!emitted_default_dtor) {
// Write out custom destructor function
Printf(s_wrappers, "static ZEND_RSRC_DTOR_FUNC(%s) {\n", rsrc_dtor_name);
Printf(s_wrappers, " efree(res->ptr);\n");
Printf(s_wrappers, "}\n");
emitted_default_dtor = true;
}
}
// declare le_swig_<mangled> to store php registration
Printf(s_vdecl, "static int le_swig_%s=0; /* handle for %s */\n", key, human_name);
// register with php
Printf(s_oinit, "le_swig_%s=zend_register_list_destructors_ex"
"(_wrap_destroy%s,NULL,(char *)(SWIGTYPE%s->name),module_number);\n", key, key, key);
"(%s, NULL, SWIGTYPE%s->name, module_number);\n", key, rsrc_dtor_name, key);
// store php type in class struct
Printf(s_oinit, "SWIG_TypeClientData(SWIGTYPE%s,&le_swig_%s);\n", key, key);
Delete(rsrc_dtor_name);
ki = Next(ki);
}
}
class PHP : public Language {
String *emit_action(Node *n) {
// Adjust wrap:action to add TSRMLS_CC.
String * action = Getattr(n, "wrap:action");
if (action) {
char * p = Strstr(action, "Swig::DirectorPureVirtualException::raise(\"");
if (p) {
p += strlen("Swig::DirectorPureVirtualException::raise(\"");
p = strchr(p, '"');
if (p) {
++p;
Insert(action, (int)(p - Char(action)), " TSRMLS_CC");
}
}
}
return ::emit_action(n);
}
public:
PHP() {
director_language = 1;
@ -208,7 +203,6 @@ public:
virtual void main(int argc, char *argv[]) {
SWIG_library_directory("php");
SWIG_config_cppext("cpp");
for (int i = 1; i < argc; i++) {
if (strcmp(argv[i], "-prefix") == 0) {
@ -225,25 +219,11 @@ public:
Swig_mark_arg(i);
} else if (strcmp(argv[i], "-help") == 0) {
fputs(usage, stdout);
} else if (strcmp(argv[i], "-make") == 0 ||
strcmp(argv[i], "-withc") == 0 ||
strcmp(argv[i], "-withcxx") == 0) {
Printf(stderr, "*** %s is no longer supported.\n", argv[i]);
SWIG_exit(EXIT_FAILURE);
} else if (strcmp(argv[i], "-phpfull") == 0 ||
strcmp(argv[i], "-withlibs") == 0 ||
strcmp(argv[i], "-withincs") == 0) {
Printf(stderr, "*** %s is no longer supported.\n*** We recommend building as a dynamically loadable module.\n", argv[i]);
SWIG_exit(EXIT_FAILURE);
} else if (strcmp(argv[i], "-dlname") == 0) {
Printf(stderr, "*** -dlname is no longer supported.\n*** If you want to change the module name, use -module instead.\n");
SWIG_exit(EXIT_FAILURE);
}
}
Preprocessor_define("SWIGPHP 1", 0);
// SWIGPHP5 is deprecated, and no longer documented.
Preprocessor_define("SWIGPHP5 1", 0);
Preprocessor_define("SWIGPHP7 1", 0);
SWIG_typemap_lang("php");
SWIG_config_file("php.swg");
allow_overloading();
@ -267,7 +247,7 @@ public:
}
/* Set comparison with null for ConstructorToFunction */
setSubclassInstanceCheck(NewString("$arg->type != IS_NULL"));
setSubclassInstanceCheck(NewString("Z_TYPE_P($arg) != IS_NULL"));
/* Initialize all of the output files */
String *outfile = Getattr(n, "outfile");
@ -320,9 +300,7 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGPHP\n");
Printf(f_runtime, "\n");
Printf(f_runtime, "\n\n#ifndef SWIGPHP\n#define SWIGPHP\n#endif\n\n");
if (directorsEnabled()) {
Printf(f_runtime, "#define SWIG_DIRECTORS\n");
@ -404,9 +382,9 @@ public:
* which has to be dynamically generated as it depends on the module name.
*/
Append(s_header, "#ifdef __GNUC__\n");
Append(s_header, "static void SWIG_FAIL(TSRMLS_D) __attribute__ ((__noreturn__));\n");
Append(s_header, "static void SWIG_FAIL(void) __attribute__ ((__noreturn__));\n");
Append(s_header, "#endif\n\n");
Append(s_header, "static void SWIG_FAIL(TSRMLS_D) {\n");
Append(s_header, "static void SWIG_FAIL(void) {\n");
Append(s_header, " zend_error(SWIG_ErrorCode(), \"%s\", SWIG_ErrorMsg());\n");
// zend_error() should never return with the parameters we pass, but if it
// does, we really don't want to let SWIG_FAIL() return. This also avoids
@ -422,38 +400,36 @@ public:
Printf(s_header, "static void %s_destroy_globals(zend_%s_globals * globals) { (void)globals; }\n", module, module);
Printf(s_header, "\n");
Printf(s_header, "static void SWIG_ResetError(TSRMLS_D) {\n");
Printf(s_header, "static void SWIG_ResetError(void) {\n");
Printf(s_header, " SWIG_ErrorMsg() = default_error_msg;\n");
Printf(s_header, " SWIG_ErrorCode() = default_error_code;\n");
Printf(s_header, "}\n");
Append(s_header, "\n");
Printf(s_header, "ZEND_NAMED_FUNCTION(_wrap_swig_%s_alter_newobject) {\n", module);
Append(s_header, " zval **args[2];\n");
Append(s_header, " zval args[2];\n");
Append(s_header, " swig_object_wrapper *value;\n");
Append(s_header, " int type;\n");
Append(s_header, "\n");
Append(s_header, " SWIG_ResetError(TSRMLS_C);\n");
Append(s_header, " SWIG_ResetError();\n");
Append(s_header, " if(ZEND_NUM_ARGS() != 2 || zend_get_parameters_array_ex(2, args) != SUCCESS) {\n");
Append(s_header, " WRONG_PARAM_COUNT;\n");
Append(s_header, " }\n");
Append(s_header, "\n");
Append(s_header, " value = (swig_object_wrapper *) zend_list_find((*args[0])->value.lval, &type);\n");
Append(s_header, " value->newobject = zval_is_true(*args[1]);\n");
Append(s_header, " value = (swig_object_wrapper *) Z_RES_VAL(args[0]);\n");
Append(s_header, " value->newobject = zval_is_true(&args[1]);\n");
Append(s_header, "\n");
Append(s_header, " return;\n");
Append(s_header, "}\n");
Printf(s_header, "ZEND_NAMED_FUNCTION(_wrap_swig_%s_get_newobject) {\n", module);
Append(s_header, " zval **args[1];\n");
Append(s_header, " zval args[1];\n");
Append(s_header, " swig_object_wrapper *value;\n");
Append(s_header, " int type;\n");
Append(s_header, "\n");
Append(s_header, " SWIG_ResetError(TSRMLS_C);\n");
Append(s_header, " SWIG_ResetError();\n");
Append(s_header, " if(ZEND_NUM_ARGS() != 1 || zend_get_parameters_array_ex(1, args) != SUCCESS) {\n");
Append(s_header, " WRONG_PARAM_COUNT;\n");
Append(s_header, " }\n");
Append(s_header, "\n");
Append(s_header, " value = (swig_object_wrapper *) zend_list_find((*args[0])->value.lval, &type);\n");
Append(s_header, " value = (swig_object_wrapper *) Z_RES_VAL(args[0]);\n");
Append(s_header, " RETVAL_LONG(value->newobject);\n");
Append(s_header, "\n");
Append(s_header, " return;\n");
@ -509,6 +485,7 @@ public:
/* start the arginfo section */
s_arginfo = NewString("/* arginfo subsection */\n");
arginfo_used = NewHash();
/* start the function entry section */
s_entry = NewString("/* entry subsection */\n");
@ -527,7 +504,7 @@ public:
Append(s_init, "#endif\n");
Printv(s_init, "zend_module_entry ", module, "_module_entry = {\n", NIL);
Printf(s_init, " STANDARD_MODULE_HEADER,\n");
Printf(s_init, " (char*)\"%s\",\n", module);
Printf(s_init, " \"%s\",\n", module);
Printf(s_init, " %s_functions,\n", module);
Printf(s_init, " PHP_MINIT(%s),\n", module);
Printf(s_init, " PHP_MSHUTDOWN(%s),\n", module);
@ -639,7 +616,7 @@ public:
Printv(f_begin, all_cs_entry, "\n\n", s_arginfo, "\n\n", s_entry,
" SWIG_ZEND_NAMED_FE(swig_", module, "_alter_newobject,_wrap_swig_", module, "_alter_newobject,NULL)\n"
" SWIG_ZEND_NAMED_FE(swig_", module, "_get_newobject,_wrap_swig_", module, "_get_newobject,NULL)\n"
"{NULL, NULL, NULL}\n};\n\n", NIL);
" ZEND_FE_END\n};\n\n", NIL);
Printv(f_begin, s_init, NIL);
Delete(s_header);
Delete(s_wrappers);
@ -650,6 +627,7 @@ public:
Delete(s_arginfo);
Delete(f_runtime);
Delete(f_begin);
Delete(arginfo_used);
Printf(f_phpcode, "%s\n%s\n", pragma_incl, pragma_code);
if (s_fakeoowrappers) {
@ -669,22 +647,36 @@ public:
void create_command(String *cname, String *iname, Node *n) {
// This is for the single main zend_function_entry record
Printf(f_h, "ZEND_NAMED_FUNCTION(%s);\n", iname);
String * s = cs_entry;
if (!s) s = s_entry;
Printf(s, " SWIG_ZEND_NAMED_FE(%(lower)s,%s,swig_arginfo_%(lower)s)\n", cname, iname, cname);
// This is the above referenced arginfo structure.
// We want to only emit each different arginfo once, as that reduces the
// size of both the generated source code and the compiled extension
// module. To do this, we name the arginfo to encode the number of
// parameters and which (if any) are passed by reference by using a
// sequence of 0s (for non-reference) and 1s (for by references).
ParmList *l = Getattr(n, "parms");
Printf(s_arginfo, "ZEND_BEGIN_ARG_INFO_EX(swig_arginfo_%(lower)s, 0, 0, 0)\n", cname);
String * arginfo_code = NewStringEmpty();
for (Parm *p = l; p; p = Getattr(p, "tmap:in:next")) {
/* Ignored parameters */
if (checkAttribute(p, "tmap:in:numinputs", "0")) {
continue;
}
int byref = GetFlag(p, "tmap:in:byref");
Printf(s_arginfo, " ZEND_ARG_PASS_INFO(%d)\n", byref);
Append(arginfo_code, GetFlag(p, "tmap:in:byref") ? "1" : "0");
}
Printf(s_arginfo, "ZEND_END_ARG_INFO()\n");
if (!GetFlag(arginfo_used, arginfo_code)) {
// Not had this one before, so emit it.
SetFlag(arginfo_used, arginfo_code);
Printf(s_arginfo, "ZEND_BEGIN_ARG_INFO_EX(swig_arginfo_%s, 0, 0, 0)\n", arginfo_code);
for (const char * p = Char(arginfo_code); *p; ++p) {
Printf(s_arginfo, " ZEND_ARG_PASS_INFO(%c)\n", *p);
}
Printf(s_arginfo, "ZEND_END_ARG_INFO()\n");
}
String * s = cs_entry;
if (!s) s = s_entry;
Printf(s, " SWIG_ZEND_NAMED_FE(%(lower)s,%s,swig_arginfo_%s)\n", cname, iname, arginfo_code);
Delete(arginfo_code);
}
/* ------------------------------------------------------------
@ -712,12 +704,12 @@ public:
Wrapper_add_local(f, "argc", "int argc");
Printf(tmp, "zval **argv[%d]", maxargs);
Printf(tmp, "zval argv[%d]", maxargs);
Wrapper_add_local(f, "argv", tmp);
Printf(f->code, "argc = ZEND_NUM_ARGS();\n");
Printf(f->code, "zend_get_parameters_array_ex(argc,argv);\n");
Printf(f->code, "zend_get_parameters_array_ex(argc, argv);\n");
Replaceall(dispatch, "$args", "self,args");
@ -725,7 +717,7 @@ public:
Printf(f->code, "SWIG_ErrorCode() = E_ERROR;\n");
Printf(f->code, "SWIG_ErrorMsg() = \"No matching function for overloaded '%s'\";\n", symname);
Printv(f->code, "SWIG_FAIL(TSRMLS_C);\n", NIL);
Printv(f->code, "SWIG_FAIL();\n", NIL);
Printv(f->code, "}\n", NIL);
Wrapper_print(f, s_wrappers);
@ -821,8 +813,8 @@ public:
if (num_arguments > 0) {
String *args = NewStringEmpty();
if (wrapperType == directorconstructor)
Wrapper_add_local(f, "arg0", "zval *arg0");
Printf(args, "zval **args[%d]", num_arguments);
Wrapper_add_local(f, "arg0", "zval * arg0");
Printf(args, "zval args[%d]", num_arguments);
Wrapper_add_local(f, "args", args);
Delete(args);
args = NULL;
@ -836,7 +828,7 @@ public:
// NOTE: possible we ignore this_ptr as a param for native constructor
Printf(f->code, "SWIG_ResetError(TSRMLS_C);\n");
Printf(f->code, "SWIG_ResetError();\n");
if (numopt > 0) { // membervariable wrappers do not have optional args
Wrapper_add_local(f, "arg_count", "int arg_count");
@ -853,7 +845,7 @@ public:
Printf(f->code, "WRONG_PARAM_COUNT;\n}\n\n");
}
if (wrapperType == directorconstructor)
Printf(f->code, "arg0 = *args[0];\n \n");
Printf(f->code, "arg0 = &args[0];\n \n");
/* Now convert from PHP to C variables */
// At this point, argcount if used is the number of deliberately passed args
@ -893,7 +885,7 @@ public:
}
if ((tm = Getattr(p, "tmap:in"))) {
Replaceall(tm, "$source", source);
Replaceall(tm, "$source", &source);
Replaceall(tm, "$target", ln);
Replaceall(tm, "$input", source);
Setattr(p, "emit:input", source);
@ -917,7 +909,7 @@ public:
if (is_member_director(n)) {
Wrapper_add_local(f, "upcall", "bool upcall = false");
Printf(f->code, "upcall = !Swig::Director::swig_is_overridden_method((char *)\"%s%s\", (char *)\"%s\" TSRMLS_CC);\n",
Printf(f->code, "upcall = !Swig::Director::swig_is_overridden_method(\"%s%s\", \"%s\");\n",
prefix, Swig_class_name(Swig_methodclass(n)), name);
}
@ -1002,12 +994,13 @@ public:
Delete(tm);
}
Printf(f->code, "thrown:\n");
Printf(f->code, "return;\n");
/* Error handling code */
Printf(f->code, "fail:\n");
Printv(f->code, cleanup, NIL);
Append(f->code, "SWIG_FAIL(TSRMLS_C);\n");
Append(f->code, "SWIG_FAIL();\n");
Printf(f->code, "}\n");
@ -1057,6 +1050,7 @@ public:
bool handle_as_overload = false;
String **arg_names;
String **arg_values;
unsigned char * byref;
// Method or static method or plain function.
const char *methodname = 0;
String *output = s_oowrappers;
@ -1197,7 +1191,8 @@ public:
}
arg_values = (String **) malloc(max_num_of_arguments * sizeof(String *));
if (!arg_values) {
byref = (unsigned char *) malloc(max_num_of_arguments);
if (!arg_values || !byref) {
/* FIXME: How should this be handled? The rest of SWIG just seems
* to not bother checking for malloc failing! */
fprintf(stderr, "Malloc failed!\n");
@ -1205,6 +1200,7 @@ public:
}
for (i = 0; i < max_num_of_arguments; ++i) {
arg_values[i] = NULL;
byref[i] = false;
}
Node *o;
@ -1224,6 +1220,7 @@ public:
continue;
}
assert(0 <= argno && argno < max_num_of_arguments);
byref[argno] = GetFlag(p, "tmap:in:byref");
String *&pname = arg_names[argno];
const char *pname_cstr = GetChar(p, "name");
// Just get rid of the C++ namespace part for now.
@ -1472,6 +1469,7 @@ public:
Printf(args, ",");
if (i || wrapperType == memberfn)
Printf(invoke, ",");
if (byref[i]) Printf(args, "&");
String *value = arg_values[i];
if (value) {
const char *v = Char(value);
@ -1906,7 +1904,7 @@ done:
enumvalue = GetChar(n, "enumvalueex");
}
if (enumvalue) {
if (enumvalue && *Char(enumvalue)) {
// Check for a simple constant expression which is valid in PHP.
// If we find one, initialise the const member with it; otherwise
// we initialise it using the C/C++ wrapped constant.
@ -1918,7 +1916,8 @@ done:
break;
}
}
if (!*p) set_to = enumvalue;
if (!*p)
set_to = enumvalue;
}
if (wrapping_member_constant) {
@ -2020,7 +2019,7 @@ done:
String *proxyclassname = SwigType_str(Getattr(n, "classtypeobj"), 0);
String *baseclassname = SwigType_str(Getattr(base.item, "name"), 0);
Swig_warning(WARN_PHP_MULTIPLE_INHERITANCE, input_file, line_number,
"Warning for %s proxy: Base %s ignored. Multiple inheritance is not supported in PHP.\n", proxyclassname, baseclassname);
"Warning for %s, base %s ignored. Multiple inheritance is not supported in PHP.\n", proxyclassname, baseclassname);
base = Next(base);
}
}
@ -2290,15 +2289,15 @@ done:
Delete(director_ctor_code);
director_ctor_code = NewStringEmpty();
director_prot_ctor_code = NewStringEmpty();
Printf(director_ctor_code, "if ( arg0->type == IS_NULL ) { /* not subclassed */\n");
Printf(director_prot_ctor_code, "if ( arg0->type == IS_NULL ) { /* not subclassed */\n");
Printf(director_ctor_code, "if (Z_TYPE_P(arg0) == IS_NULL) { /* not subclassed */\n");
Printf(director_prot_ctor_code, "if (Z_TYPE_P(arg0) == IS_NULL) { /* not subclassed */\n");
Printf(director_ctor_code, " %s = (%s *)new %s(%s);\n", Swig_cresult_name(), ctype, ctype, args);
Printf(director_prot_ctor_code, " SWIG_PHP_Error(E_ERROR, \"accessing abstract class or protected constructor\");\n", name, name, args);
if (i) {
Insert(args, 0, ", ");
}
Printf(director_ctor_code, "} else {\n %s = (%s *)new SwigDirector_%s(arg0 TSRMLS_CC%s);\n}\n", Swig_cresult_name(), ctype, sname, args);
Printf(director_prot_ctor_code, "} else {\n %s = (%s *)new SwigDirector_%s(arg0 TSRMLS_CC%s);\n}\n", Swig_cresult_name(), ctype, sname, args);
Printf(director_ctor_code, "} else {\n %s = (%s *)new SwigDirector_%s(arg0%s);\n}\n", Swig_cresult_name(), ctype, sname, args);
Printf(director_prot_ctor_code, "} else {\n %s = (%s *)new SwigDirector_%s(arg0%s);\n}\n", Swig_cresult_name(), ctype, sname, args);
Delete(args);
wrapperType = directorconstructor;
@ -2328,9 +2327,9 @@ done:
Wrapper *f = NewWrapper();
Printf(f->def, "/* This function is designed to be called by the zend list destructors */\n");
Printf(f->def, "/* to typecast and do the actual destruction */\n");
Printf(f->def, "static void %s(zend_rsrc_list_entry *rsrc, const char *type_name TSRMLS_DC) {\n", destructorname);
Printf(f->def, "static void %s(zend_resource *res, const char *type_name) {\n", destructorname);
Wrapper_add_localv(f, "value", "swig_object_wrapper *value=(swig_object_wrapper *) rsrc->ptr", NIL);
Wrapper_add_localv(f, "value", "swig_object_wrapper *value=(swig_object_wrapper *) res->ptr", NIL);
Wrapper_add_localv(f, "ptr", "void *ptr=value->ptr", NIL);
Wrapper_add_localv(f, "newobject", "int newobject=value->newobject", NIL);
@ -2348,7 +2347,7 @@ done:
Printf(f->code, " efree(value);\n");
Printf(f->code, " if (! newobject) return; /* can't delete it! */\n");
Printf(f->code, " arg1 = (%s)SWIG_ZTS_ConvertResourceData(ptr,type_name,SWIGTYPE%s TSRMLS_CC);\n", SwigType_lstr(pt, 0), SwigType_manglestr(pt));
Printf(f->code, " arg1 = (%s)SWIG_ConvertResourceData(ptr, type_name, SWIGTYPE%s);\n", SwigType_lstr(pt, 0), SwigType_manglestr(pt));
Printf(f->code, " if (! arg1) zend_error(E_ERROR, \"%s resource already free'd\");\n", Char(name));
Setattr(n, "wrap:name", destructorname);
@ -2357,9 +2356,10 @@ done:
Append(f->code, actioncode);
Delete(actioncode);
Printf(f->code, "thrown:\n");
Append(f->code, "return;\n");
Append(f->code, "fail:\n");
Append(f->code, "SWIG_FAIL(TSRMLS_C);\n");
Append(f->code, "SWIG_FAIL();\n");
Printf(f->code, "}\n");
Wrapper_print(f, s_wrappers);
@ -2419,16 +2419,9 @@ done:
String *call;
String *basetype = Getattr(parent, "classtype");
// We put TSRMLS_DC after the self parameter in order to cope with
// any default parameters.
String *target = Swig_method_decl(0, decl, classname, parms, 0, 0);
const char * p = Char(target);
const char * comma = strchr(p, ',');
int ins = comma ? (int)(comma - p) : Len(target) - 1;
Insert(target, ins, " TSRMLS_DC");
call = Swig_csuperclass_call(0, basetype, superparms);
Printf(w->def, "%s::%s: %s, Swig::Director(self TSRMLS_CC) {", classname, target, call);
Printf(w->def, "%s::%s: %s, Swig::Director(self) {", classname, target, call);
Append(w->def, "}");
Delete(target);
Wrapper_print(w, f_directors);
@ -2438,14 +2431,7 @@ done:
/* constructor header */
{
// We put TSRMLS_DC after the self parameter in order to cope with
// any default parameters.
String *target = Swig_method_decl(0, decl, classname, parms, 0, 1);
const char * p = Char(target);
const char * comma = strchr(p, ',');
int ins = comma ? (int)(comma - p) : Len(target) - 1;
Insert(target, ins, " TSRMLS_DC");
Printf(f_directors_h, " %s;\n", target);
Delete(target);
}
@ -2530,8 +2516,6 @@ done:
Append(w->def, " {");
Append(declaration, ";\n");
Printf(w->code, "TSRMLS_FETCH_FROM_CTX(swig_zts_ctx);\n");
/* declare method return value
* if the return value is a reference or const reference, a specialized typemap must
* handle it, including declaration of c_result ($result).
@ -2552,7 +2536,7 @@ done:
Printf(w->code, "%s;\n", super_call);
Delete(super_call);
} else {
Printf(w->code, "Swig::DirectorPureVirtualException::raise(\"Attempted to invoke pure virtual method %s::%s\" TSRMLS_CC);\n", SwigType_namestr(c_classname),
Printf(w->code, "Swig::DirectorPureVirtualException::raise(\"Attempted to invoke pure virtual method %s::%s\");\n", SwigType_namestr(c_classname),
SwigType_namestr(name));
}
} else {
@ -2567,7 +2551,6 @@ done:
Swig_typemap_attach_parms("directorargout", l, w);
Parm *p;
char source[256];
int outputs = 0;
if (!is_void)
@ -2591,16 +2574,11 @@ done:
if ((tm = Getattr(p, "tmap:directorin")) != 0) {
String *parse = Getattr(p, "tmap:directorin:parse");
if (!parse) {
sprintf(source, "obj%d", idx++);
String *input = NewStringf("&%s", source);
String *input = NewStringf("&args[%d]", idx++);
Setattr(p, "emit:directorinput", input);
Replaceall(tm, "$input", input);
Delete(input);
Replaceall(tm, "$owner", "0");
Printv(wrap_args, "zval ", source, ";\n", NIL);
Printf(wrap_args, "args[%d] = &%s;\n", idx - 1, source);
Printv(wrap_args, "INIT_ZVAL(", source, ");\n", NIL);
Printv(wrap_args, tm, "\n", NIL);
Putc('O', parse_args);
} else {
@ -2624,6 +2602,7 @@ done:
}
/* exception handling */
bool error_used_in_typemap = false;
tm = Swig_typemap_lookup("director:except", n, Swig_cresult_name(), 0);
if (!tm) {
tm = Getattr(n, "feature:director:except");
@ -2633,6 +2612,7 @@ done:
if ((tm) && Len(tm) && (Strcmp(tm, "1") != 0)) {
if (Replaceall(tm, "$error", "error")) {
/* Only declare error if it is used by the typemap. */
error_used_in_typemap = true;
Append(w->code, "int error;\n");
}
} else {
@ -2641,23 +2621,26 @@ done:
}
if (!idx) {
Printf(w->code, "zval **args = NULL;\n");
Printf(w->code, "zval *args = NULL;\n");
} else {
Printf(w->code, "zval *args[%d];\n", idx);
Printf(w->code, "zval args[%d];\n", idx);
}
Printf(w->code, "zval *%s, funcname;\n", Swig_cresult_name());
Append(w->code, "if (!swig_self) {\n");
Append(w->code, " SWIG_PHP_Error(E_ERROR, \"this pointer is NULL\");");
Append(w->code, "}\n\n");
Printf(w->code, "MAKE_STD_ZVAL(%s);\n", Swig_cresult_name());
// typemap_directorout testcase requires that 0 can be assigned to the
// variable named after the result of Swig_cresult_name(), so that can't
// be a zval - make it a pointer to one instead.
Printf(w->code, "zval swig_zval_result, swig_funcname;\n", Swig_cresult_name());
Printf(w->code, "zval *%s = &swig_zval_result;\n", Swig_cresult_name());
const char * funcname = GetChar(n, "sym:name");
Printf(w->code, "ZVAL_STRINGL(&funcname, (char *)\"%s\", %d, 0);\n", funcname, strlen(funcname));
Printf(w->code, "ZVAL_STRINGL(&swig_funcname, \"%s\", %d);\n", funcname, strlen(funcname));
/* wrap complex arguments to zvals */
Printv(w->code, wrap_args, NIL);
Append(w->code, "call_user_function(EG(function_table), (zval**)&swig_self, &funcname,");
Printf(w->code, " %s, %d, args TSRMLS_CC);\n", Swig_cresult_name(), idx);
if (error_used_in_typemap) {
Append(w->code, "error = ");
}
Append(w->code, "call_user_function(EG(function_table), &swig_self, &swig_funcname,");
Printf(w->code, " &swig_zval_result, %d, args);\n", idx);
if (tm) {
Printv(w->code, Str(tm), "\n", NIL);
@ -2709,13 +2692,12 @@ done:
}
}
Printf(w->code, "FREE_ZVAL(%s);\n", Swig_cresult_name());
Delete(parse_args);
Delete(cleanup);
Delete(outarg);
}
Append(w->code, "thrown:\n");
if (!is_void) {
if (!(ignored_method && !pure_virtual)) {
String *rettype = SwigType_str(returntype, 0);
@ -2731,7 +2713,7 @@ done:
}
Append(w->code, "fail:\n");
Append(w->code, "SWIG_FAIL(TSRMLS_C);\n");
Append(w->code, "SWIG_FAIL();\n");
Append(w->code, "}\n");
// We expose protected methods via an extra public inline method which makes a straight call to the wrapped class' method
@ -2776,7 +2758,8 @@ static PHP *maininstance = 0;
// We use this function to be able to write out zend_register_list_destructor_ex
// lines for most things in the type table
// NOTE: it's a function NOT A PHP::METHOD
extern "C" void typetrace(const SwigType *ty, String *mangled, String *clientdata) {
extern "C" {
static void typetrace(const SwigType *ty, String *mangled, String *clientdata) {
Node *class_node;
if (!zend_types) {
zend_types = NewHash();
@ -2796,6 +2779,7 @@ extern "C" void typetrace(const SwigType *ty, String *mangled, String *clientdat
if (r_prevtracefunc)
(*r_prevtracefunc) (ty, mangled, (String *) clientdata);
}
}
/* -----------------------------------------------------------------------------
* new_swig_php() - Instantiate module
@ -2812,13 +2796,6 @@ static Language *new_swig_php() {
return maininstance;
}
extern "C" Language *swig_php4(void) {
Printf(stderr, "*** -php4 is no longer supported.\n"
"*** Either upgrade to PHP5 or use SWIG 1.3.36 or earlier.\n");
SWIG_exit(EXIT_FAILURE);
return NULL; // To avoid compiler warnings.
}
extern "C" Language *swig_php(void) {
return new_swig_php();
}

2861
Source/Modules/php5.cxx Normal file

File diff suppressed because it is too large Load diff

View file

@ -149,9 +149,7 @@ public:
/* Standard stuff for the SWIG runtime section */
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGPIKE\n");
Printf(f_runtime, "\n");
Printf(f_runtime, "\n\n#ifndef SWIGPIKE\n#define SWIGPIKE\n#endif\n\n");
Printf(f_header, "#define SWIG_init pike_module_init\n");
Printf(f_header, "#define SWIG_name \"%s\"\n\n", module);

File diff suppressed because it is too large Load diff

View file

@ -793,9 +793,7 @@ int R::top(Node *n) {
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGR\n");
Printf(f_runtime, "\n");
Printf(f_runtime, "\n\n#ifndef SWIGR\n#define SWIGR\n#endif\n\n");
Swig_banner_target_lang(s_init, "#");
@ -1066,7 +1064,7 @@ int R::OutputMemberReferenceMethod(String *className, int isSet,
if (!isSet && varaccessor > 0) {
Printf(f->code, "%svaccessors = c(", tab8);
int vcount = 0;
int first = 1;
for(j = 0; j < numMems; j+=3) {
String *item = Getitem(el, j);
String *dup = Getitem(el, j + 1);
@ -1074,8 +1072,8 @@ int R::OutputMemberReferenceMethod(String *className, int isSet,
ptr = &ptr[Len(dup) - 3];
if (!strcmp(ptr, "get")) {
vcount++;
Printf(f->code, "'%s'%s", item, vcount < varaccessor ? ", " : "");
Printf(f->code, "%s'%s'", first ? "" : ", ", item);
first = 0;
}
}
Printf(f->code, ");\n");
@ -1181,6 +1179,9 @@ int R::OutputArrayMethod(String *className, List *el, File *out) {
tdname is the typedef of the enumeration, i.e. giving its name.
*************************************************************/
int R::enumDeclaration(Node *n) {
if (getCurrentClass() && (cplus_mode != PUBLIC))
return SWIG_NOWRAP;
String *name = Getattr(n, "name");
String *tdname = Getattr(n, "tdname");
@ -1481,11 +1482,12 @@ List * R::Swig_overload_rank(Node *n,
Swig_warning(WARN_LANG_OVERLOAD_CONST, Getfile(nodes[i].n), Getline(nodes[i].n),
"using non-const method %s instead.\n", Swig_name_decl(nodes[i].n));
} else {
if (!Getattr(nodes[j].n, "overload:ignore"))
if (!Getattr(nodes[j].n, "overload:ignore")) {
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[j].n), Getline(nodes[j].n),
"Overloaded method %s ignored,\n", Swig_name_decl(nodes[j].n));
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[i].n), Getline(nodes[i].n),
"using %s instead.\n", Swig_name_decl(nodes[i].n));
}
}
}
nodes[j].error = 1;
@ -1498,11 +1500,12 @@ List * R::Swig_overload_rank(Node *n,
Swig_warning(WARN_LANG_OVERLOAD_CONST, Getfile(nodes[i].n), Getline(nodes[i].n),
"using non-const method %s instead.\n", Swig_name_decl(nodes[i].n));
} else {
if (!Getattr(nodes[j].n, "overload:ignore"))
if (!Getattr(nodes[j].n, "overload:ignore")) {
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[j].n), Getline(nodes[j].n),
"Overloaded method %s ignored,\n", Swig_name_decl(nodes[j].n));
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[i].n), Getline(nodes[i].n),
"using %s instead.\n", Swig_name_decl(nodes[i].n));
}
}
}
nodes[j].error = 1;
@ -1520,11 +1523,12 @@ List * R::Swig_overload_rank(Node *n,
Swig_warning(WARN_LANG_OVERLOAD_SHADOW, Getfile(nodes[i].n), Getline(nodes[i].n),
"as it is shadowed by %s.\n", Swig_name_decl(nodes[i].n));
} else {
if (!Getattr(nodes[j].n, "overload:ignore"))
if (!Getattr(nodes[j].n, "overload:ignore")) {
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[j].n), Getline(nodes[j].n),
"Overloaded method %s ignored,\n", Swig_name_decl(nodes[j].n));
Swig_warning(WARN_LANG_OVERLOAD_IGNORED, Getfile(nodes[i].n), Getline(nodes[i].n),
"using %s instead.\n", Swig_name_decl(nodes[i].n));
}
}
nodes[j].error = 1;
}
@ -2093,6 +2097,13 @@ int R::functionWrapper(Node *n) {
}
}
/* See if there is any return cleanup code */
if ((tm = Swig_typemap_lookup("ret", n, Swig_cresult_name(), 0))) {
Replaceall(tm, "$source", Swig_cresult_name());
Printf(f->code, "%s\n", tm);
Delete(tm);
}
Printv(f->code, UnProtectWrapupCode, NIL);
/*If the user gave us something to convert the result in */

View file

@ -232,7 +232,7 @@ private:
/* ------------------------------------------------------------
* docstring()
* Get the docstring text, stripping off {} if neccessary,
* Get the docstring text, stripping off {} if necessary,
* and enclose in triple double quotes. If autodoc is also
* set then it will build a combined docstring.
* ------------------------------------------------------------ */
@ -1011,6 +1011,8 @@ public:
virtual int top(Node *n) {
String *mod_docstring = NULL;
/**
* See if any Ruby module options have been specified as options
* to the %module directive.
@ -1032,6 +1034,7 @@ public:
multipleInheritance = true;
director_multiple_inheritance = 1;
}
mod_docstring = Getattr(options, "docstring");
}
}
@ -1097,8 +1100,7 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGRUBY\n");
Printf(f_runtime, "\n\n#ifndef SWIGRUBY\n#define SWIGRUBY\n#endif\n\n");
if (directorsEnabled()) {
Printf(f_runtime, "#define SWIG_DIRECTORS\n");
@ -1147,6 +1149,15 @@ public:
Printf(f_header, "#define SWIG_init Init_%s\n", feature);
Printf(f_header, "#define SWIG_name \"%s\"\n\n", module);
if (mod_docstring) {
if (Len(mod_docstring)) {
Printf(f_header, "/*\n Document-module: %s\n\n%s\n*/\n", module, mod_docstring);
}
Delete(mod_docstring);
mod_docstring = NULL;
}
Printf(f_header, "static VALUE %s;\n", modvar);
/* Start generating the initialization function */
@ -1535,7 +1546,8 @@ public:
/* Finish argument marshalling */
Printf(kwargs, " NULL }");
if (allow_kwargs) {
Printv(f->locals, tab4, "const char *kwnames[] = ", kwargs, ";\n", NIL);
// kwarg support not implemented
// Printv(f->locals, tab4, "const char *kwnames[] = ", kwargs, ";\n", NIL);
}
/* Trailing varargs */
@ -1740,11 +1752,13 @@ public:
/* Now write the wrapper function itself */
if (current == CONSTRUCTOR_ALLOCATE) {
Printv(f->def, "SWIGINTERN VALUE\n", NIL);
Printf(f->def, "#ifdef HAVE_RB_DEFINE_ALLOC_FUNC\n");
Printv(f->def, "SWIGINTERN VALUE\n", wname, "(VALUE self) {", NIL);
Printv(f->def, wname, "(VALUE self)\n", NIL);
Printf(f->def, "#else\n");
Printv(f->def, "SWIGINTERN VALUE\n", wname, "(int argc, VALUE *argv, VALUE self) {", NIL);
Printv(f->def, wname, "(int argc, VALUE *argv, VALUE self)\n", NIL);
Printf(f->def, "#endif\n");
Printv(f->def, "{\n", NIL);
} else if (current == CONSTRUCTOR_INITIALIZE) {
Printv(f->def, "SWIGINTERN VALUE\n", wname, "(int argc, VALUE *argv, VALUE self) {", NIL);
if (!varargs) {
@ -1830,10 +1844,19 @@ public:
Wrapper_add_local(f, "classname", classname);
}
if (action) {
Printf(action, "\nDATA_PTR(self) = %s;", Swig_cresult_name());
if (GetFlag(pn, "feature:trackobjects")) {
Printf(action, "\nSWIG_RubyAddTracking(%s, self);", Swig_cresult_name());
SwigType *smart = Swig_cparse_smartptr(pn);
String *result_name = NewStringf("%s%s", smart ? "smart" : "", Swig_cresult_name());
if (smart) {
String *result_var = NewStringf("%s *%s = 0", SwigType_namestr(smart), result_name);
Wrapper_add_local(f, result_name, result_var);
Printf(action, "\n%s = new %s(%s);", result_name, SwigType_namestr(smart), Swig_cresult_name());
}
Printf(action, "\nDATA_PTR(self) = %s;", result_name);
if (GetFlag(pn, "feature:trackobjects")) {
Printf(action, "\nSWIG_RubyAddTracking(%s, self);", result_name);
}
Delete(result_name);
Delete(smart);
}
}
@ -1921,11 +1944,17 @@ public:
/* Extra code needed for new and initialize methods */
if (current == CONSTRUCTOR_ALLOCATE) {
Node *pn = Swig_methodclass(n);
SwigType *smart = Swig_cparse_smartptr(pn);
if (smart)
SwigType_add_pointer(smart);
String *classtype = smart ? smart : t;
need_result = 1;
Printf(f->code, "VALUE vresult = SWIG_NewClassInstance(self, SWIGTYPE%s);\n", Char(SwigType_manglestr(t)));
Printf(f->code, "VALUE vresult = SWIG_NewClassInstance(self, SWIGTYPE%s);\n", Char(SwigType_manglestr(classtype)));
Printf(f->code, "#ifndef HAVE_RB_DEFINE_ALLOC_FUNC\n");
Printf(f->code, "rb_obj_call_init(vresult, argc, argv);\n");
Printf(f->code, "#endif\n");
Delete(smart);
} else if (current == CONSTRUCTOR_INITIALIZE) {
need_result = 1;
}
@ -2094,13 +2123,11 @@ public:
// Generate prototype list, go to first node
Node *sibl = n;
String* type = SwigType_str(Getattr(sibl,"type"),NULL);
while (Getattr(sibl, "sym:previousSibling"))
sibl = Getattr(sibl, "sym:previousSibling"); // go all the way up
// Constructors will be treated specially
const bool isCtor = Cmp(Getattr(sibl,"feature:new"), "1") == 0;
const bool isCtor = (!Cmp(Getattr(sibl, "nodeType"), "constructor"));
const bool isMethod = ( Cmp(Getattr(sibl, "ismember"), "1") == 0 &&
(!isCtor) );
@ -2122,7 +2149,11 @@ public:
String *protoTypes = NewString("");
do {
Append( protoTypes, "\n\" ");
if ( !isCtor ) Printv( protoTypes, type, " ", NIL );
if (!isCtor) {
SwigType *type = SwigType_str(Getattr(sibl, "type"), NULL);
Printv(protoTypes, type, " ", NIL);
Delete(type);
}
Printv(protoTypes, methodName, NIL );
Parm* p = Getattr(sibl, "wrap:parms");
if (p && (current == MEMBER_FUNC || current == MEMBER_VAR ||
@ -2143,7 +2174,6 @@ public:
Append(f->code, "\nreturn Qnil;\n");
Delete(methodName);
Delete(type);
Delete(protoTypes);
Printv(f->code, "}\n", NIL);
@ -2424,19 +2454,23 @@ public:
SwigType *btype = NewString(basename);
SwigType_add_pointer(btype);
SwigType_remember(btype);
SwigType *smart = Swig_cparse_smartptr(base.item);
if (smart) {
SwigType_add_pointer(smart);
SwigType_remember(smart);
}
String *bmangle = SwigType_manglestr(smart ? smart : btype);
if (multipleInheritance) {
String *bmangle = SwigType_manglestr(btype);
Insert(bmangle, 0, "((swig_class *) SWIGTYPE");
Append(bmangle, "->clientdata)->mImpl");
Printv(klass->init, "rb_include_module(", klass->mImpl, ", ", bmangle, ");\n", NIL);
Delete(bmangle);
} else {
String *bmangle = SwigType_manglestr(btype);
Insert(bmangle, 0, "((swig_class *) SWIGTYPE");
Append(bmangle, "->clientdata)->klass");
Replaceall(klass->init, "$super", bmangle);
Delete(bmangle);
}
Delete(bmangle);
Delete(smart);
Delete(btype);
}
base = Next(base);
@ -2453,7 +2487,7 @@ public:
String *proxyclassname = SwigType_str(Getattr(n, "classtypeobj"), 0);
String *baseclassname = SwigType_str(Getattr(base.item, "name"), 0);
Swig_warning(WARN_RUBY_MULTIPLE_INHERITANCE, Getfile(n), Getline(n),
"Warning for %s proxy: Base %s ignored. Multiple inheritance is not supported in Ruby.\n", proxyclassname, baseclassname);
"Warning for %s, base %s ignored. Multiple inheritance is not supported in Ruby.\n", proxyclassname, baseclassname);
base = Next(base);
}
}
@ -2537,9 +2571,15 @@ public:
SwigType *tt = NewString(name);
SwigType_add_pointer(tt);
SwigType_remember(tt);
String *tm = SwigType_manglestr(tt);
SwigType *smart = Swig_cparse_smartptr(n);
if (smart) {
SwigType_add_pointer(smart);
SwigType_remember(smart);
}
String *tm = SwigType_manglestr(smart ? smart : tt);
Printf(klass->init, "SWIG_TypeClientData(SWIGTYPE%s, (void *) &SwigClass%s);\n", tm, valid_name);
Delete(tm);
Delete(smart);
Delete(tt);
Delete(valid_name);
@ -2718,7 +2758,9 @@ public:
String *pname0 = Swig_cparm_name(0, 0);
Printv(freefunc, "free_", klass->mname, NIL);
Printv(freebody, "SWIGINTERN void\n", freefunc, "(", klass->type, " *", pname0, ") {\n", tab4, NIL);
Printv(freebody, "SWIGINTERN void\n", freefunc, "(void *self) {\n", NIL);
Printv(freebody, tab4, klass->type, " *", pname0, " = (", klass->type, " *)self;\n", NIL);
Printv(freebody, tab4, NIL);
/* Check to see if object tracking is activated for the class
that owns this destructor. */
@ -2971,6 +3013,7 @@ public:
Printf(rescue->code, "if (%s == 0) ", depthCountName);
Printv(rescue->code, Str(tm), "\n", NIL);
Printv(rescue->code, "rb_exc_raise(error);\n", NIL);
Printv(rescue->code, "return Qnil;\n", NIL);
Printv(rescue->code, "}", NIL);
}
@ -3431,6 +3474,7 @@ public:
*--------------------------------------------------------------------*/
bool kwargsSupport() const {
// kwargs support isn't actually implemented, but changing to return false may break something now as it turns on compactdefaultargs
return true;
}
}; /* class RUBY */

View file

@ -195,8 +195,7 @@ public:
/* Output module initialization code */
Swig_banner(beginSection);
Printf(runtimeSection, "\n#define SWIGSCILAB\n");
Printf(runtimeSection, "\n");
Printf(runtimeSection, "\n\n#ifndef SWIGSCILAB\n#define SWIGSCILAB\n#endif\n\n");
// Gateway header source merged with wrapper source in nobuilder mode
if (!generateBuilder)
@ -327,6 +326,7 @@ public:
bool isLastOverloaded = isOverloaded && !Getattr(node, "sym:nextSibling");
if (!isOverloaded && !addSymbol(functionName, node)) {
DelWrapper(wrapper);
return SWIG_ERROR;
}
@ -412,7 +412,7 @@ public:
emit_return_variable(node, functionReturnType, wrapper);
/* Return the function value if necessary */
String *functionReturnTypemap = Swig_typemap_lookup_out("out", node, "result", wrapper, functionActionCode);
String *functionReturnTypemap = Swig_typemap_lookup_out("out", node, Swig_cresult_name(), wrapper, functionActionCode);
if (functionReturnTypemap) {
// Result is actually the position of output value on stack
if (Len(functionReturnTypemap) > 0) {
@ -471,6 +471,13 @@ public:
}
}
/* See if there is any return cleanup code */
String *tm;
if ((tm = Swig_typemap_lookup("ret", node, Swig_cresult_name(), 0))) {
Replaceall(tm, "$source", Swig_cresult_name());
Printf(wrapper->code, "%s\n", tm);
Delete(tm);
}
/* Close the function(ok) */
Printv(wrapper->code, "return SWIG_OK;\n", NIL);
@ -634,7 +641,10 @@ public:
/* Add function to builder table */
addFunctionToScilab(scilabSetFunctionName, setFunctionName);
DelWrapper(setFunctionWrapper);
}
DelWrapper(getFunctionWrapper);
return SWIG_OK;
}
@ -661,7 +671,7 @@ public:
if (isConstant || isEnum) {
if (isEnum) {
Setattr(node, "type", "double");
constantValue = Getattr(node, "enumvalue");
constantValue = Getattr(node, "value");
}
constantTypemap = Swig_typemap_lookup("scilabconstcode", node, nodeName, 0);
@ -885,7 +895,7 @@ public:
Printf(builderCode, "libs = [];\n");
// Flags from command line arguments
Printf(builderCode, "cflags = [];\n");
Printf(builderCode, "cflags = \"\";\n");
for (int i = 0; i < Len(cflags); i++) {
String *cflag = Getitem(cflags, i);
Printf(builderCode, "cflags = cflags + \" %s\";\n", cflag);
@ -901,7 +911,7 @@ public:
}
}
} else {
Printf(builderCode, "ldflags = [];\n");
Printf(builderCode, "ldflags = \"\";\n");
}
// External script to set flags
@ -1027,7 +1037,7 @@ public:
Printf(gatewayHeaderV5, ",\n");
Printf(gatewayHeaderV5, " {(Myinterfun)sci_gateway, (GT)%s, (char *)\"%s\"}", wrapperFunctionName, scilabFunctionName);
Printf(gatewayHeaderV6, "if (wcscmp(pwstFuncName, L\"%s\") == 0) { addCFunction((wchar_t *)L\"%s\", &%s, (wchar_t *)MODULE_NAME); }\n", scilabFunctionName, scilabFunctionName, wrapperFunctionName);
Printf(gatewayHeaderV6, "if (wcscmp(pwstFuncName, L\"%s\") == 0) { addCStackFunction((wchar_t *)L\"%s\", &%s, (wchar_t *)MODULE_NAME); }\n", scilabFunctionName, scilabFunctionName, wrapperFunctionName);
}
/* -----------------------------------------------------------------------

View file

@ -36,6 +36,7 @@ extern "C" {
Language *swig_java(void);
Language *swig_php(void);
Language *swig_php4(void);
Language *swig_php5(void);
Language *swig_ocaml(void);
Language *swig_octave(void);
Language *swig_pike(void);
@ -83,9 +84,10 @@ static swig_module modules[] = {
{"-octave", swig_octave, "Octave"},
{"-perl", swig_perl5, "Perl"},
{"-perl5", swig_perl5, 0},
{"-php", swig_php, "PHP"},
{"-php", swig_php5, 0},
{"-php4", swig_php4, 0},
{"-php5", swig_php, 0},
{"-php5", swig_php5, "PHP5"},
{"-php7", swig_php, "PHP7"},
{"-pike", swig_pike, "Pike"},
{"-python", swig_python, "Python"},
{"-r", swig_r, "R (aka GNU S)"},

View file

@ -18,12 +18,6 @@
#include "preprocessor.h"
#include "swigwarn.h"
#if !defined(HAVE_BOOL)
typedef int bool;
#define true ((bool)1)
#define false ((bool)0)
#endif
#define NOT_VIRTUAL 0
#define PLAIN_VIRTUAL 1
#define PURE_VIRTUAL 2
@ -220,8 +214,9 @@ public:
/* Miscellaneous */
virtual int validIdentifier(String *s); /* valid identifier? */
virtual int addSymbol(const String *s, const Node *n, const_String_or_char_ptr scope = ""); /* Add symbol */
virtual int addInterfaceSymbol(const String *interface_name, Node *n, const_String_or_char_ptr scope = "");
virtual void dumpSymbols();
virtual Node *symbolLookup(String *s, const_String_or_char_ptr scope = ""); /* Symbol lookup */
virtual Node *symbolLookup(const String *s, const_String_or_char_ptr scope = ""); /* Symbol lookup */
virtual Hash* symbolAddScope(const_String_or_char_ptr scope);
virtual Hash* symbolScopeLookup(const_String_or_char_ptr scope);
virtual Hash* symbolScopePseudoSymbolLookup(const_String_or_char_ptr scope);
@ -435,19 +430,24 @@ extern "C" {
}
/* Contracts */
void Swig_contracts(Node *n);
void Swig_contract_mode_set(int flag);
int Swig_contract_mode_get();
/* Browser */
void Swig_browser(Node *n, int);
void Swig_default_allocators(Node *n);
void Swig_process_types(Node *n);
/* Nested classes */
void Swig_nested_process_classes(Node *n);
void Swig_nested_name_unnamed_c_structs(Node *n);
/* Interface feature */
void Swig_interface_feature_enable();
void Swig_interface_propagate_methods(Node *n);
/* Miscellaneous */
template <class T> class save_value {
T _value;
T& _value_ptr;

View file

@ -165,9 +165,7 @@ public:
Swig_banner(f_begin);
Printf(f_runtime, "\n");
Printf(f_runtime, "#define SWIGTCL\n");
Printf(f_runtime, "\n");
Printf(f_runtime, "\n\n#ifndef SWIGTCL\n#define SWIGTCL\n#endif\n\n");
/* Set the module name, namespace, and prefix */
@ -968,7 +966,7 @@ public:
Printf(f_wrappers, ",0");
}
Printv(f_wrappers, ", swig_", mangled_classname, "_methods, swig_", mangled_classname, "_attributes, swig_", mangled_classname, "_bases,",
"swig_", mangled_classname, "_base_names, &swig_module };\n", NIL);
"swig_", mangled_classname, "_base_names, &swig_module, SWIG_TCL_HASHTABLE_INIT };\n", NIL);
if (!itcl) {
Printv(cmd_tab, tab4, "{ SWIG_prefix \"", class_name, "\", (swig_wrapper_func) SWIG_ObjectConstructor, (ClientData)&_wrap_class_", mangled_classname,

View file

@ -224,7 +224,7 @@ class TypePass:private Dispatcher {
if (tname)
Delete(tname);
if (!bcls) {
if (!clsforward) {
if (!clsforward && !GetFlag(cls, "feature:ignore")) {
if (ispublic && !Getmeta(bname, "already_warned")) {
Swig_warning(WARN_TYPE_UNDEFINED_CLASS, Getfile(bname), Getline(bname), "Nothing known about base class '%s'. Ignored.\n", SwigType_namestr(bname));
if (Strchr(bname, '<')) {
@ -254,41 +254,44 @@ class TypePass:private Dispatcher {
Node *bclass = n; /* Getattr(n,"class"); */
Hash *scopes = Getattr(bclass, "typescope");
SwigType_inherit(clsname, bname, cast, 0);
String *smartptr = Getattr(first, "feature:smartptr");
if (smartptr) {
SwigType *smart = 0;
SwigType *spt = Swig_cparse_type(smartptr);
if (spt) {
smart = SwigType_typedef_resolve_all(spt);
Delete(spt);
/* Record a (fake) inheritance relationship between smart pointer
and smart pointer to base class, so that smart pointer upcasts
are automatically generated. */
SwigType *bsmart = Copy(smart);
SwigType *rclsname = SwigType_typedef_resolve_all(clsname);
SwigType *rbname = SwigType_typedef_resolve_all(bname);
Replaceall(bsmart, rclsname, rbname);
Delete(rclsname);
Delete(rbname);
String *smartnamestr = SwigType_namestr(smart);
String *bsmartnamestr = SwigType_namestr(bsmart);
/* construct casting code */
String *convcode = NewStringf("\n *newmemory = SWIG_CAST_NEW_MEMORY;\n return (void *) new %s(*(%s *)$from);\n", bsmartnamestr, smartnamestr);
Delete(bsmartnamestr);
Delete(smartnamestr);
/* setup inheritance relationship between smart pointer templates */
SwigType_inherit(smart, bsmart, 0, convcode);
if (!GetFlag(bclass, "feature:smartptr"))
Swig_warning(WARN_LANG_SMARTPTR_MISSING, Getfile(first), Getline(first), "Base class '%s' of '%s' is not similarly marked as a smart pointer.\n", SwigType_namestr(Getattr(bclass, "name")), SwigType_namestr(Getattr(first, "name")));
Delete(convcode);
Delete(bsmart);
if (ispublic && !GetFlag(bclass, "feature:ignore")) {
String *smartptr = Getattr(first, "feature:smartptr");
if (smartptr) {
SwigType *smart = Swig_cparse_smartptr(first);
if (smart) {
/* Record a (fake) inheritance relationship between smart pointer
and smart pointer to base class, so that smart pointer upcasts
are automatically generated. */
SwigType *bsmart = Copy(smart);
SwigType *rclsname = SwigType_typedef_resolve_all(clsname);
SwigType *rbname = SwigType_typedef_resolve_all(bname);
int replace_count = Replaceall(bsmart, rclsname, rbname);
if (replace_count == 0) {
// If no replacement made, it will be because rclsname is fully resolved, but the
// type in the smartptr feature used a typedef or not fully resolved name.
String *firstname = Getattr(first, "name");
Replaceall(bsmart, firstname, rbname);
}
Delete(rclsname);
Delete(rbname);
String *smartnamestr = SwigType_namestr(smart);
String *bsmartnamestr = SwigType_namestr(bsmart);
/* construct casting code */
String *convcode = NewStringf("\n *newmemory = SWIG_CAST_NEW_MEMORY;\n return (void *) new %s(*(%s *)$from);\n", bsmartnamestr, smartnamestr);
Delete(bsmartnamestr);
Delete(smartnamestr);
/* setup inheritance relationship between smart pointer templates */
SwigType_inherit(smart, bsmart, 0, convcode);
if (!GetFlag(bclass, "feature:smartptr"))
Swig_warning(WARN_LANG_SMARTPTR_MISSING, Getfile(first), Getline(first), "Base class '%s' of '%s' is not similarly marked as a smart pointer.\n", SwigType_namestr(Getattr(bclass, "name")), SwigType_namestr(Getattr(first, "name")));
Delete(convcode);
Delete(bsmart);
}
Delete(smart);
} else {
Swig_error(Getfile(first), Getline(first), "Invalid type (%s) in 'smartptr' feature for class %s.\n", SwigType_namestr(smartptr), SwigType_namestr(clsname));
if (GetFlag(bclass, "feature:smartptr"))
Swig_warning(WARN_LANG_SMARTPTR_MISSING, Getfile(first), Getline(first), "Derived class '%s' of '%s' is not similarly marked as a smart pointer.\n", SwigType_namestr(Getattr(first, "name")), SwigType_namestr(Getattr(bclass, "name")));
}
} else {
if (GetFlag(bclass, "feature:smartptr"))
Swig_warning(WARN_LANG_SMARTPTR_MISSING, Getfile(first), Getline(first), "Derived class '%s' of '%s' is not similarly marked as a smart pointer.\n", SwigType_namestr(Getattr(first, "name")), SwigType_namestr(Getattr(bclass, "name")));
}
if (!importmode) {
String *btype = Copy(bname);
@ -563,6 +566,10 @@ class TypePass:private Dispatcher {
SwigType_typedef_class(rname);
Delete(rname);
/* SwigType_typedef_class(name); */
} else if (Strcmp(ttype, "cdecl") == 0) {
String *rname = SwigType_typedef_resolve_all(name);
SwigType_typedef_class(rname);
Delete(rname);
}
return SWIG_OK;
}

View file

@ -81,9 +81,11 @@ public:
virtual int top(Node *n) {
if (out == 0) {
String *outfile = Getattr(n, "outfile");
Replaceall(outfile, ".cxx", ".xml");
Replaceall(outfile, ".cpp", ".xml");
Replaceall(outfile, ".c", ".xml");
String *ext = Swig_file_extension(outfile);
// If there's an extension, ext will include the ".".
Delslice(outfile, Len(outfile) - Len(ext), DOH_END);
Delete(ext);
Append(outfile, ".xml");
out = NewFile(outfile, "w", SWIG_output_files());
if (!out) {
FileErrorDisplay(outfile);
@ -142,8 +144,8 @@ public:
Xml_print_kwargs(Getattr(obj, k));
} else if (Cmp(k, "parms") == 0 || Cmp(k, "pattern") == 0) {
Xml_print_parmlist(Getattr(obj, k));
} else if (Cmp(k, "catchlist") == 0) {
Xml_print_parmlist(Getattr(obj, k), "catchlist");
} else if (Cmp(k, "catchlist") == 0 || Cmp(k, "templateparms") == 0) {
Xml_print_parmlist(Getattr(obj, k), Char(k));
} else {
DOH *o;
print_indent(0);

View file

@ -291,6 +291,7 @@ int Swig_insert_file(const_String_or_char_ptr filename, File *outfile) {
while ((nbytes = Read(f, buffer, 4096)) > 0) {
Write(outfile, buffer, nbytes);
}
fclose(f);
return 0;
}

View file

@ -309,6 +309,7 @@ int Swig_storage_isstatic(Node *n) {
* Swig_string_escape()
*
* Takes a string object and produces a string with escape codes added to it.
* Octal escaping is used.
* ----------------------------------------------------------------------------- */
String *Swig_string_escape(String *s) {
@ -342,6 +343,43 @@ String *Swig_string_escape(String *s) {
return ns;
}
/* -----------------------------------------------------------------------------
* Swig_string_hexescape()
*
* Takes a string object and produces a string with escape codes added to it.
* Hex escaping is used.
* ----------------------------------------------------------------------------- */
String *Swig_string_hexescape(String *s) {
String *ns;
int c;
ns = NewStringEmpty();
while ((c = Getc(s)) != EOF) {
if (c == '\n') {
Printf(ns, "\\n");
} else if (c == '\r') {
Printf(ns, "\\r");
} else if (c == '\t') {
Printf(ns, "\\t");
} else if (c == '\\') {
Printf(ns, "\\\\");
} else if (c == '\'') {
Printf(ns, "\\'");
} else if (c == '\"') {
Printf(ns, "\\\"");
} else if (c == ' ') {
Putc(c, ns);
} else if (!isgraph(c)) {
if (c < 0)
c += UCHAR_MAX + 1;
Printf(ns, "\\x%X", c);
} else {
Putc(c, ns);
}
}
return ns;
}
/* -----------------------------------------------------------------------------
* Swig_string_upper()
@ -1147,6 +1185,39 @@ String *Swig_string_strip(String *s) {
return ns;
}
/* -----------------------------------------------------------------------------
* Swig_string_rstrip()
*
* Strip given suffix from identifiers
*
* Printf(stderr,"%(rstrip:[Cls])s","HelloCls") -> Hello
* ----------------------------------------------------------------------------- */
String *Swig_string_rstrip(String *s) {
String *ns;
int len = Len(s);
if (!len) {
ns = NewString(s);
} else {
const char *cs = Char(s);
const char *ce = Strchr(cs, ']');
if (*cs != '[' || !ce) {
ns = NewString(s);
} else {
String *fmt = NewStringf("%%.%ds", ce-cs-1);
String *suffix = NewStringf(fmt, cs+1);
int suffix_len = Len(suffix);
if (0 == Strncmp(cs+len-suffix_len, suffix, suffix_len)) {
int copy_len = len-suffix_len-(ce+1-cs);
ns = NewStringWithSize(ce+1, copy_len);
} else {
ns = NewString(ce+1);
}
}
}
return ns;
}
/* -----------------------------------------------------------------------------
* Swig_offset_string()
*
@ -1328,7 +1399,7 @@ String *replace_captures(int num_captures, const char *input, String *subst, int
*
* Executes a regular expression substitution. For example:
*
* Printf(stderr,"gsl%(regex:/GSL_.*_/\\1/)s","GSL_Hello_") -> gslHello
* Printf(stderr,"gsl%(regex:/GSL_(.*)_/\\1/)s", "GSL_Hello_") -> gslHello
* ----------------------------------------------------------------------------- */
String *Swig_string_regex(String *s) {
const int pcre_options = 0;
@ -1403,6 +1474,7 @@ int Swig_is_generated_overload(Node *n) {
void Swig_init() {
/* Set some useful string encoding methods */
DohEncoding("escape", Swig_string_escape);
DohEncoding("hexescape", Swig_string_hexescape);
DohEncoding("upper", Swig_string_upper);
DohEncoding("lower", Swig_string_lower);
DohEncoding("title", Swig_string_title);
@ -1414,6 +1486,7 @@ void Swig_init() {
DohEncoding("command", Swig_string_command);
DohEncoding("schemify", Swig_string_schemify);
DohEncoding("strip", Swig_string_strip);
DohEncoding("rstrip", Swig_string_rstrip);
DohEncoding("regex", Swig_string_regex);
/* aliases for the case encoders */

View file

@ -50,6 +50,13 @@ void Swig_name_unregister(const_String_or_char_ptr method) {
}
}
/* Return naming format for the specified method or the default format if none was explicitly registered */
static String* get_naming_format_for(const char *method, const char *def_format) {
String* f = naming_hash ? Getattr(naming_hash, method) : NULL;
return f ? Copy(f) : NewString(def_format);
}
static int name_mangle(String *r) {
char *c;
int special;
@ -172,18 +179,8 @@ String *Swig_name_mangle(const_String_or_char_ptr s) {
* ----------------------------------------------------------------------------- */
String *Swig_name_wrapper(const_String_or_char_ptr fname) {
String *r;
String *f;
String *r = get_naming_format_for("wrapper", "_wrap_%f");
r = NewStringEmpty();
if (!naming_hash)
naming_hash = NewHash();
f = Getattr(naming_hash, "wrapper");
if (!f) {
Append(r, "_wrap_%f");
} else {
Append(r, f);
}
Replace(r, "%f", fname, DOH_REPLACE_ANY);
name_mangle(r);
return r;
@ -198,20 +195,11 @@ String *Swig_name_wrapper(const_String_or_char_ptr fname) {
String *Swig_name_member(const_String_or_char_ptr nspace, const_String_or_char_ptr classname, const_String_or_char_ptr membername) {
String *r;
String *f;
String *rclassname;
char *cname;
rclassname = SwigType_namestr(classname);
r = NewStringEmpty();
if (!naming_hash)
naming_hash = NewHash();
f = Getattr(naming_hash, "member");
if (!f) {
Append(r, "%n%c_%m");
} else {
Append(r, f);
}
r = get_naming_format_for("member", "%n%c_%m");
cname = Char(rclassname);
if ((strncmp(cname, "struct ", 7) == 0) || ((strncmp(cname, "class ", 6) == 0)) || ((strncmp(cname, "union ", 6) == 0))) {
cname = strchr(cname, ' ') + 1;
@ -231,23 +219,12 @@ String *Swig_name_member(const_String_or_char_ptr nspace, const_String_or_char_p
* ----------------------------------------------------------------------------- */
String *Swig_name_get(const_String_or_char_ptr nspace, const_String_or_char_ptr vname) {
String *r;
String *f;
String *r = get_naming_format_for("get", "%n%v_get");
#ifdef SWIG_DEBUG
Printf(stdout, "Swig_name_get: '%s'\n", vname);
#endif
r = NewStringEmpty();
if (!naming_hash)
naming_hash = NewHash();
f = Getattr(naming_hash, "get");
if (!f) {
Append(r, "%n%v_get");
} else {
Append(r, f);
}
replace_nspace(r, nspace);
Replace(r, "%v", vname, DOH_REPLACE_ANY);
/* name_mangle(r); */
@ -261,18 +238,7 @@ String *Swig_name_get(const_String_or_char_ptr nspace, const_String_or_char_ptr
* ----------------------------------------------------------------------------- */
String *Swig_name_set(const_String_or_char_ptr nspace, const_String_or_char_ptr vname) {
String *r;
String *f;
r = NewStringEmpty();
if (!naming_hash)
naming_hash = NewHash();
f = Getattr(naming_hash, "set");
if (!f) {
Append(r, "%n%v_set");
} else {
Append(r, f);
}
String *r = get_naming_format_for("set", "%n%v_set");
replace_nspace(r, nspace);
Replace(r, "%v", vname, DOH_REPLACE_ANY);
@ -280,6 +246,26 @@ String *Swig_name_set(const_String_or_char_ptr nspace, const_String_or_char_ptr
return r;
}
/* Common implementation of all Swig_name_<special-method>() functions below. */
static String *make_full_name_for(const char *method, const char *def_format, const_String_or_char_ptr nspace, const_String_or_char_ptr classname) {
String *r;
String *rclassname;
char *cname;
rclassname = SwigType_namestr(classname);
r = get_naming_format_for(method, def_format);
cname = Char(rclassname);
if ((strncmp(cname, "struct ", 7) == 0) || ((strncmp(cname, "class ", 6) == 0)) || ((strncmp(cname, "union ", 6) == 0))) {
cname = strchr(cname, ' ') + 1;
}
replace_nspace(r, nspace);
Replace(r, "%c", cname, DOH_REPLACE_ANY);
Delete(rclassname);
return r;
}
/* -----------------------------------------------------------------------------
* Swig_name_construct()
*
@ -287,31 +273,7 @@ String *Swig_name_set(const_String_or_char_ptr nspace, const_String_or_char_ptr
* ----------------------------------------------------------------------------- */
String *Swig_name_construct(const_String_or_char_ptr nspace, const_String_or_char_ptr classname) {
String *r;
String *f;
String *rclassname;
char *cname;
rclassname = SwigType_namestr(classname);
r = NewStringEmpty();
if (!naming_hash)
naming_hash = NewHash();
f = Getattr(naming_hash, "construct");
if (!f) {
Append(r, "new_%n%c");
} else {
Append(r, f);
}
cname = Char(rclassname);
if ((strncmp(cname, "struct ", 7) == 0) || ((strncmp(cname, "class ", 6) == 0)) || ((strncmp(cname, "union ", 6) == 0))) {
cname = strchr(cname, ' ') + 1;
}
replace_nspace(r, nspace);
Replace(r, "%c", cname, DOH_REPLACE_ANY);
Delete(rclassname);
return r;
return make_full_name_for("construct", "new_%n%c", nspace, classname);
}
@ -322,31 +284,7 @@ String *Swig_name_construct(const_String_or_char_ptr nspace, const_String_or_cha
* ----------------------------------------------------------------------------- */
String *Swig_name_copyconstructor(const_String_or_char_ptr nspace, const_String_or_char_ptr classname) {
String *r;
String *f;
String *rclassname;
char *cname;
rclassname = SwigType_namestr(classname);
r = NewStringEmpty();
if (!naming_hash)
naming_hash = NewHash();
f = Getattr(naming_hash, "copy");
if (!f) {
Append(r, "copy_%n%c");
} else {
Append(r, f);
}
cname = Char(rclassname);
if ((strncmp(cname, "struct ", 7) == 0) || ((strncmp(cname, "class ", 6) == 0)) || ((strncmp(cname, "union ", 6) == 0))) {
cname = strchr(cname, ' ') + 1;
}
replace_nspace(r, nspace);
Replace(r, "%c", cname, DOH_REPLACE_ANY);
Delete(rclassname);
return r;
return make_full_name_for("copy", "copy_%n%c", nspace, classname);
}
/* -----------------------------------------------------------------------------
@ -356,30 +294,7 @@ String *Swig_name_copyconstructor(const_String_or_char_ptr nspace, const_String_
* ----------------------------------------------------------------------------- */
String *Swig_name_destroy(const_String_or_char_ptr nspace, const_String_or_char_ptr classname) {
String *r;
String *f;
String *rclassname;
char *cname;
rclassname = SwigType_namestr(classname);
r = NewStringEmpty();
if (!naming_hash)
naming_hash = NewHash();
f = Getattr(naming_hash, "destroy");
if (!f) {
Append(r, "delete_%n%c");
} else {
Append(r, f);
}
cname = Char(rclassname);
if ((strncmp(cname, "struct ", 7) == 0) || ((strncmp(cname, "class ", 6) == 0)) || ((strncmp(cname, "union ", 6) == 0))) {
cname = strchr(cname, ' ') + 1;
}
replace_nspace(r, nspace);
Replace(r, "%c", cname, DOH_REPLACE_ANY);
Delete(rclassname);
return r;
return make_full_name_for("destroy", "delete_%n%c", nspace, classname);
}
@ -390,30 +305,7 @@ String *Swig_name_destroy(const_String_or_char_ptr nspace, const_String_or_char_
* ----------------------------------------------------------------------------- */
String *Swig_name_disown(const_String_or_char_ptr nspace, const_String_or_char_ptr classname) {
String *r;
String *f;
String *rclassname;
char *cname;
rclassname = SwigType_namestr(classname);
r = NewStringEmpty();
if (!naming_hash)
naming_hash = NewHash();
f = Getattr(naming_hash, "disown");
if (!f) {
Append(r, "disown_%n%c");
} else {
Append(r, f);
}
cname = Char(rclassname);
if ((strncmp(cname, "struct ", 7) == 0) || ((strncmp(cname, "class ", 6) == 0)) || ((strncmp(cname, "union ", 6) == 0))) {
cname = strchr(cname, ' ') + 1;
}
replace_nspace(r, nspace);
Replace(r, "%c", cname, DOH_REPLACE_ANY);
Delete(rclassname);
return r;
return make_full_name_for("disown", "disown_%n%c", nspace, classname);
}
@ -466,8 +358,7 @@ static DOH *get_object(Hash *n, String *decl) {
return rn;
}
static
DOH *name_object_get(Hash *namehash, String *tname, SwigType *decl, SwigType *ncdecl) {
static DOH *name_object_get(Hash *namehash, String *tname, SwigType *decl, SwigType *ncdecl) {
DOH *rn = 0;
Hash *n = Getattr(namehash, tname);
if (n) {
@ -513,7 +404,17 @@ DOH *Swig_name_object_get(Hash *namehash, String *prefix, String *name, SwigType
}
Delete(cls);
}
/* A template-based class lookup, check name first */
/* Lookup a name within a templated-based class */
if (!rn) {
String *t_name = SwigType_istemplate_templateprefix(prefix);
if (t_name) {
Clear(tname);
Printf(tname, "%s::%s", t_name, name);
rn = name_object_get(namehash, tname, decl, ncdecl);
Delete(t_name);
}
}
/* Lookup a template-based name within a class */
if (!rn) {
String *t_name = SwigType_istemplate_templateprefix(name);
if (t_name)
@ -646,8 +547,7 @@ static void merge_features(Hash *features, Node *n) {
* the declaration, decl.
* ----------------------------------------------------------------------------- */
static
void features_get(Hash *features, const String *tname, SwigType *decl, SwigType *ncdecl, Node *node) {
static void features_get(Hash *features, const String *tname, SwigType *decl, SwigType *ncdecl, Node *node) {
Node *n = Getattr(features, tname);
#ifdef SWIG_DEBUG
Printf(stdout, " features_get: %s\n", tname);
@ -844,41 +744,41 @@ void Swig_feature_set(Hash *features, const_String_or_char_ptr name, SwigType *d
* ----------------------------------------------------------------------------- */
static Hash *namewarn_hash = 0;
Hash *Swig_name_namewarn_hash() {
static Hash *name_namewarn_hash() {
if (!namewarn_hash)
namewarn_hash = NewHash();
return namewarn_hash;
}
static Hash *rename_hash = 0;
Hash *Swig_name_rename_hash() {
static Hash *name_rename_hash() {
if (!rename_hash)
rename_hash = NewHash();
return rename_hash;
}
static List *namewarn_list = 0;
List *Swig_name_namewarn_list() {
static List *name_namewarn_list() {
if (!namewarn_list)
namewarn_list = NewList();
return namewarn_list;
}
static List *rename_list = 0;
List *Swig_name_rename_list() {
static List *name_rename_list() {
if (!rename_list)
rename_list = NewList();
return rename_list;
}
/* -----------------------------------------------------------------------------
* int Swig_need_name_warning(Node *n)
* int need_name_warning(Node *n)
*
* Detects if a node needs name warnings
*
* ----------------------------------------------------------------------------- */
int Swig_need_name_warning(Node *n) {
static int need_name_warning(Node *n) {
int need = 1;
/*
We don't use name warnings for:
@ -1061,13 +961,13 @@ int Swig_need_protected(Node *n) {
}
/* -----------------------------------------------------------------------------
* void Swig_name_nameobj_add()
* void name_nameobj_add()
*
* Add nameobj (rename/namewarn)
*
* ----------------------------------------------------------------------------- */
static List *Swig_make_attrlist(const char *ckey) {
static List *make_attrlist(const char *ckey) {
List *list = NewList();
const char *cattr = strchr(ckey, '$');
if (cattr) {
@ -1089,7 +989,7 @@ static List *Swig_make_attrlist(const char *ckey) {
return list;
}
static void Swig_name_object_attach_keys(const char *keys[], Hash *nameobj) {
static void name_object_attach_keys(const char *keys[], Hash *nameobj) {
Node *kw = nextSibling(nameobj);
List *matchlist = 0;
while (kw) {
@ -1105,7 +1005,7 @@ static void Swig_name_object_attach_keys(const char *keys[], Hash *nameobj) {
|| (isregexmatch = (strncmp(ckey, "regexmatch", 10) == 0))
|| (isnotmatch = isregexmatch = (strncmp(ckey, "notregexmatch", 13) == 0))) {
Hash *mi = NewHash();
List *attrlist = Swig_make_attrlist(ckey);
List *attrlist = make_attrlist(ckey);
if (!matchlist)
matchlist = NewList();
Setattr(mi, "value", Getattr(kw, "value"));
@ -1135,7 +1035,7 @@ static void Swig_name_object_attach_keys(const char *keys[], Hash *nameobj) {
}
}
void Swig_name_nameobj_add(Hash *name_hash, List *name_list, String *prefix, String *name, SwigType *decl, Hash *nameobj) {
static void name_nameobj_add(Hash *name_hash, List *name_list, String *prefix, String *name, SwigType *decl, Hash *nameobj) {
String *nname = 0;
if (name && Len(name)) {
String *target_fmt = Getattr(nameobj, "targetfmt");
@ -1164,13 +1064,13 @@ void Swig_name_nameobj_add(Hash *name_hash, List *name_list, String *prefix, Str
}
/* -----------------------------------------------------------------------------
* int Swig_name_match_nameobj()
* int name_match_nameobj()
*
* Apply and check the nameobj's math list to the node
*
* ----------------------------------------------------------------------------- */
static DOH *Swig_get_lattr(Node *n, List *lattr) {
static DOH *get_lattr(Node *n, List *lattr) {
DOH *res = 0;
int ilen = Len(lattr);
int i;
@ -1192,7 +1092,7 @@ static DOH *Swig_get_lattr(Node *n, List *lattr) {
#ifdef HAVE_PCRE
#include <pcre.h>
int Swig_name_regexmatch_value(Node *n, String *pattern, String *s) {
static int name_regexmatch_value(Node *n, String *pattern, String *s) {
pcre *compiled_pat;
const char *err;
int errpos;
@ -1224,7 +1124,7 @@ int Swig_name_regexmatch_value(Node *n, String *pattern, String *s) {
#else /* !HAVE_PCRE */
int Swig_name_regexmatch_value(Node *n, String *pattern, String *s) {
static int name_regexmatch_value(Node *n, String *pattern, String *s) {
(void)pattern;
(void)s;
Swig_error("SWIG", Getline(n),
@ -1234,7 +1134,7 @@ int Swig_name_regexmatch_value(Node *n, String *pattern, String *s) {
#endif /* HAVE_PCRE/!HAVE_PCRE */
int Swig_name_match_value(String *mvalue, String *value) {
static int name_match_value(String *mvalue, String *value) {
#if defined(SWIG_USE_SIMPLE_MATCHOR)
int match = 0;
char *cvalue = Char(value);
@ -1260,12 +1160,11 @@ int Swig_name_match_value(String *mvalue, String *value) {
#endif
}
int Swig_name_match_nameobj(Hash *rn, Node *n) {
static int name_match_nameobj(Hash *rn, Node *n) {
int match = 1;
List *matchlist = Getattr(rn, "matchlist");
#ifdef SWIG_DEBUG
Printf(stdout, "Swig_name_match_nameobj: %s\n", Getattr(n, "name"));
Printf(stdout, "name_match_nameobj: %s\n", Getattr(n, "name"));
#endif
if (matchlist) {
int ilen = Len(matchlist);
@ -1273,14 +1172,14 @@ int Swig_name_match_nameobj(Hash *rn, Node *n) {
for (i = 0; match && (i < ilen); ++i) {
Node *mi = Getitem(matchlist, i);
List *lattr = Getattr(mi, "attrlist");
String *nval = Swig_get_lattr(n, lattr);
String *nval = get_lattr(n, lattr);
int notmatch = GetFlag(mi, "notmatch");
int regexmatch = GetFlag(mi, "regexmatch");
match = 0;
if (nval) {
String *kwval = Getattr(mi, "value");
match = regexmatch ? Swig_name_regexmatch_value(n, kwval, nval)
: Swig_name_match_value(kwval, nval);
match = regexmatch ? name_regexmatch_value(n, kwval, nval)
: name_match_value(kwval, nval);
#ifdef SWIG_DEBUG
Printf(stdout, "val %s %s %d %d \n", nval, kwval, match, ilen);
#endif
@ -1290,19 +1189,19 @@ int Swig_name_match_nameobj(Hash *rn, Node *n) {
}
}
#ifdef SWIG_DEBUG
Printf(stdout, "Swig_name_match_nameobj: %d\n", match);
Printf(stdout, "name_match_nameobj: %d\n", match);
#endif
return match;
}
/* -----------------------------------------------------------------------------
* Hash *Swig_name_nameobj_lget()
* Hash *name_nameobj_lget()
*
* Get a nameobj (rename/namewarn) from the list of filters
*
* ----------------------------------------------------------------------------- */
Hash *Swig_name_nameobj_lget(List *namelist, Node *n, String *prefix, String *name, String *decl) {
static Hash *name_nameobj_lget(List *namelist, Node *n, String *prefix, String *name, String *decl) {
Hash *res = 0;
if (namelist) {
int len = Len(namelist);
@ -1313,7 +1212,7 @@ Hash *Swig_name_nameobj_lget(List *namelist, Node *n, String *prefix, String *na
String *rdecl = Getattr(rn, "decl");
if (rdecl && (!decl || !Equal(rdecl, decl))) {
continue;
} else if (Swig_name_match_nameobj(rn, n)) {
} else if (name_match_nameobj(rn, n)) {
String *tname = Getattr(rn, "targetname");
if (tname) {
String *sfmt = Getattr(rn, "sourcefmt");
@ -1336,8 +1235,8 @@ Hash *Swig_name_nameobj_lget(List *namelist, Node *n, String *prefix, String *na
DohIncref(name);
}
}
match = regextarget ? Swig_name_regexmatch_value(n, tname, sname)
: Swig_name_match_value(tname, sname);
match = regextarget ? name_regexmatch_value(n, tname, sname)
: name_match_value(tname, sname);
Delete(sname);
} else {
/* Applying the renaming rule may fail if it contains a %(regex)s expression that doesn't match the given name. */
@ -1367,23 +1266,23 @@ Hash *Swig_name_nameobj_lget(List *namelist, Node *n, String *prefix, String *na
void Swig_name_namewarn_add(String *prefix, String *name, SwigType *decl, Hash *namewrn) {
const char *namewrn_keys[] = { "rename", "error", "fullname", "sourcefmt", "targetfmt", 0 };
Swig_name_object_attach_keys(namewrn_keys, namewrn);
Swig_name_nameobj_add(Swig_name_namewarn_hash(), Swig_name_namewarn_list(), prefix, name, decl, namewrn);
name_object_attach_keys(namewrn_keys, namewrn);
name_nameobj_add(name_namewarn_hash(), name_namewarn_list(), prefix, name, decl, namewrn);
}
/* -----------------------------------------------------------------------------
* Hash *Swig_name_namewarn_get()
* Hash *name_namewarn_get()
*
* Return the namewarn object, if there is one.
*
* ----------------------------------------------------------------------------- */
Hash *Swig_name_namewarn_get(Node *n, String *prefix, String *name, SwigType *decl) {
static Hash *name_namewarn_get(Node *n, String *prefix, String *name, SwigType *decl) {
if (!namewarn_hash && !namewarn_list)
return 0;
if (n) {
/* Return in the obvious cases */
if (!name || !Swig_need_name_warning(n)) {
if (!name || !need_name_warning(n)) {
return 0;
} else {
String *access = Getattr(n, "access");
@ -1395,11 +1294,11 @@ Hash *Swig_name_namewarn_get(Node *n, String *prefix, String *name, SwigType *de
}
if (name) {
/* Check to see if the name is in the hash */
Hash *wrn = Swig_name_object_get(Swig_name_namewarn_hash(), prefix, name, decl);
if (wrn && !Swig_name_match_nameobj(wrn, n))
Hash *wrn = Swig_name_object_get(name_namewarn_hash(), prefix, name, decl);
if (wrn && !name_match_nameobj(wrn, n))
wrn = 0;
if (!wrn) {
wrn = Swig_name_nameobj_lget(Swig_name_namewarn_list(), n, prefix, name, decl);
wrn = name_nameobj_lget(name_namewarn_list(), n, prefix, name, decl);
}
if (wrn && Getattr(wrn, "error")) {
if (n) {
@ -1422,7 +1321,7 @@ Hash *Swig_name_namewarn_get(Node *n, String *prefix, String *name, SwigType *de
* ----------------------------------------------------------------------------- */
String *Swig_name_warning(Node *n, String *prefix, String *name, SwigType *decl) {
Hash *wrn = Swig_name_namewarn_get(n, prefix, name, decl);
Hash *wrn = name_namewarn_get(n, prefix, name, decl);
return (name && wrn) ? Getattr(wrn, "name") : 0;
}
@ -1434,7 +1333,7 @@ String *Swig_name_warning(Node *n, String *prefix, String *name, SwigType *decl)
* ----------------------------------------------------------------------------- */
static void single_rename_add(String *prefix, String *name, SwigType *decl, Hash *newname) {
Swig_name_nameobj_add(Swig_name_rename_hash(), Swig_name_rename_list(), prefix, name, decl, newname);
name_nameobj_add(name_rename_hash(), name_rename_list(), prefix, name, decl, newname);
}
/* Add a new rename. Works much like new_feature including default argument handling. */
@ -1443,7 +1342,7 @@ void Swig_name_rename_add(String *prefix, String *name, SwigType *decl, Hash *ne
ParmList *declparms = declaratorparms;
const char *rename_keys[] = { "fullname", "sourcefmt", "targetfmt", "continue", "regextarget", 0 };
Swig_name_object_attach_keys(rename_keys, newname);
name_object_attach_keys(rename_keys, newname);
/* Add the name */
single_rename_add(prefix, name, decl, newname);
@ -1556,11 +1455,10 @@ String *Swig_name_make(Node *n, String *prefix, const_String_or_char_ptr cname,
}
}
if (rename_hash || rename_list || namewarn_hash || namewarn_list) {
Hash *rn = Swig_name_object_get(Swig_name_rename_hash(), prefix, name, decl);
if (!rn || !Swig_name_match_nameobj(rn, n)) {
rn = Swig_name_nameobj_lget(Swig_name_rename_list(), n, prefix, name, decl);
Hash *rn = Swig_name_object_get(name_rename_hash(), prefix, name, decl);
if (!rn || !name_match_nameobj(rn, n)) {
rn = name_nameobj_lget(name_rename_list(), n, prefix, name, decl);
if (rn) {
String *sfmt = Getattr(rn, "sourcefmt");
int fullname = GetFlag(rn, "fullname");
@ -1596,7 +1494,7 @@ String *Swig_name_make(Node *n, String *prefix, const_String_or_char_ptr cname,
}
}
nname = result ? result : name;
wrn = Swig_name_namewarn_get(n, prefix, nname, decl);
wrn = name_namewarn_get(n, prefix, nname, decl);
if (wrn) {
String *rename = Getattr(wrn, "rename");
if (rename) {
@ -1641,14 +1539,14 @@ String *Swig_name_make(Node *n, String *prefix, const_String_or_char_ptr cname,
/* -----------------------------------------------------------------------------
* void Swig_name_inherit()
*
* Inherit namewarn,rename, and feature objects
* Inherit namewarn, rename, and feature objects
*
* ----------------------------------------------------------------------------- */
void Swig_name_inherit(String *base, String *derived) {
/* Printf(stdout,"base = '%s', derived = '%s'\n", base, derived); */
Swig_name_object_inherit(Swig_name_rename_hash(), base, derived);
Swig_name_object_inherit(Swig_name_namewarn_hash(), base, derived);
Swig_name_object_inherit(name_rename_hash(), base, derived);
Swig_name_object_inherit(name_namewarn_hash(), base, derived);
Swig_name_object_inherit(Swig_cparse_features(), base, derived);
}

View file

@ -283,13 +283,11 @@ extern int ParmList_is_compactdefargs(ParmList *p);
extern void Swig_naming_init(void);
extern void Swig_name_namewarn_add(String *prefix, String *name, SwigType *decl, Hash *namewrn);
extern Hash *Swig_name_namewarn_get(Node *n, String *prefix, String *name, SwigType *decl);
extern void Swig_name_rename_add(String *prefix, String *name, SwigType *decl, Hash *namewrn, ParmList *declaratorparms);
extern void Swig_name_inherit(String *base, String *derived);
extern List *Swig_make_inherit_list(String *clsname, List *names, String *Namespaceprefix);
extern void Swig_inherit_base_symbols(List *bases);
extern int Swig_need_protected(Node *n);
extern int Swig_need_name_warning(Node *n);
extern int Swig_need_redefined_warn(Node *a, Node *b, int InClass);
extern String *Swig_name_make(Node *n, String *prefix, const_String_or_char_ptr cname, SwigType *decl, String *oldname);
@ -411,8 +409,6 @@ extern int ParmList_is_compactdefargs(ParmList *p);
extern String *Swig_typemap_lookup(const_String_or_char_ptr tmap_method, Node *n, const_String_or_char_ptr lname, Wrapper *f);
extern String *Swig_typemap_lookup_out(const_String_or_char_ptr tmap_method, Node *n, const_String_or_char_ptr lname, Wrapper *f, String *actioncode);
extern void Swig_typemap_new_scope(void);
extern Hash *Swig_typemap_pop_scope(void);
extern void Swig_typemap_attach_parms(const_String_or_char_ptr tmap_method, ParmList *parms, Wrapper *f);

View file

@ -68,7 +68,7 @@ void Swig_print_node(Node *obj) {
Node *cobj;
print_indent(0);
Printf(stdout, "+++ %s ----------------------------------------\n", nodeType(obj));
Printf(stdout, "+++ %s - %p ----------------------------------------\n", nodeType(obj), obj);
ki = First(obj);
while (ki.key) {
String *k = ki.key;

View file

@ -59,13 +59,9 @@ static void replace_embedded_typemap(String *s, ParmList *parm_sublist, Wrapper
*
* ----------------------------------------------------------------------------- */
#define MAX_SCOPE 32
static Hash *typemaps;
static Hash *typemaps[MAX_SCOPE];
static int tm_scope = 0;
static Hash *get_typemap(int tm_scope, const SwigType *type) {
static Hash *get_typemap(const SwigType *type) {
Hash *tm = 0;
SwigType *dtype = 0;
SwigType *hashtype;
@ -79,7 +75,7 @@ static Hash *get_typemap(int tm_scope, const SwigType *type) {
/* remove unary scope operator (::) prefix indicating global scope for looking up in the hashmap */
hashtype = SwigType_remove_global_scope_prefix(type);
tm = Getattr(typemaps[tm_scope], hashtype);
tm = Getattr(typemaps, hashtype);
Delete(dtype);
Delete(hashtype);
@ -87,7 +83,7 @@ static Hash *get_typemap(int tm_scope, const SwigType *type) {
return tm;
}
static void set_typemap(int tm_scope, const SwigType *type, Hash **tmhash) {
static void set_typemap(const SwigType *type, Hash **tmhash) {
SwigType *hashtype = 0;
Hash *new_tm = 0;
assert(*tmhash == 0);
@ -96,7 +92,7 @@ static void set_typemap(int tm_scope, const SwigType *type, Hash **tmhash) {
String *ty = Swig_symbol_template_deftype(rty, 0);
String *tyq = Swig_symbol_type_qualify(ty, 0);
hashtype = SwigType_remove_global_scope_prefix(tyq);
*tmhash = Getattr(typemaps[tm_scope], hashtype);
*tmhash = Getattr(typemaps, hashtype);
Delete(rty);
Delete(tyq);
Delete(ty);
@ -111,7 +107,7 @@ static void set_typemap(int tm_scope, const SwigType *type, Hash **tmhash) {
}
/* note that the unary scope operator (::) prefix indicating global scope has been removed from the type */
Setattr(typemaps[tm_scope], hashtype, *tmhash);
Setattr(typemaps, hashtype, *tmhash);
Delete(hashtype);
Delete(new_tm);
@ -125,12 +121,7 @@ static void set_typemap(int tm_scope, const SwigType *type, Hash **tmhash) {
* ----------------------------------------------------------------------------- */
void Swig_typemap_init() {
int i;
for (i = 0; i < MAX_SCOPE; i++) {
typemaps[i] = 0;
}
typemaps[0] = NewHash();
tm_scope = 0;
typemaps = NewHash();
}
static String *typemap_method_name(const_String_or_char_ptr tmap_method) {
@ -160,32 +151,6 @@ static String *typemap_method_name(const_String_or_char_ptr tmap_method) {
return s;
}
#if 0
/* -----------------------------------------------------------------------------
* Swig_typemap_new_scope()
*
* Create a new typemap scope
* ----------------------------------------------------------------------------- */
void Swig_typemap_new_scope() {
tm_scope++;
typemaps[tm_scope] = NewHash();
}
/* -----------------------------------------------------------------------------
* Swig_typemap_pop_scope()
*
* Pop the last typemap scope off
* ----------------------------------------------------------------------------- */
Hash *Swig_typemap_pop_scope() {
if (tm_scope > 0) {
return typemaps[tm_scope--];
}
return 0;
}
#endif
/* -----------------------------------------------------------------------------
* typemap_register()
*
@ -216,9 +181,9 @@ static void typemap_register(const_String_or_char_ptr tmap_method, ParmList *par
pname = Getattr(parms, "name");
/* See if this type has been seen before */
tm = get_typemap(tm_scope, type);
tm = get_typemap(type);
if (!tm) {
set_typemap(tm_scope, type, &tm);
set_typemap(type, &tm);
}
if (pname) {
/* See if parameter has been seen before */
@ -311,15 +276,12 @@ void Swig_typemap_register(const_String_or_char_ptr tmap_method, ParmList *parms
/* -----------------------------------------------------------------------------
* typemap_get()
*
* Retrieve typemap information from current scope.
* Retrieve typemap information.
* ----------------------------------------------------------------------------- */
static Hash *typemap_get(SwigType *type, const_String_or_char_ptr name, int scope) {
static Hash *typemap_get(SwigType *type, const_String_or_char_ptr name) {
Hash *tm, *tm1;
/* See if this type has been seen before */
if ((scope < 0) || (scope > tm_scope))
return 0;
tm = get_typemap(scope, type);
tm = get_typemap(type);
if (!tm) {
return 0;
}
@ -342,51 +304,48 @@ int Swig_typemap_copy(const_String_or_char_ptr tmap_method, ParmList *srcparms,
Parm *p;
String *pname;
SwigType *ptype;
int ts = tm_scope;
String *tm_methods, *multi_tmap_method;
if (ParmList_len(parms) != ParmList_len(srcparms))
return -1;
tm_method = typemap_method_name(tmap_method);
while (ts >= 0) {
p = srcparms;
tm_methods = NewString(tm_method);
while (p) {
ptype = Getattr(p, "type");
pname = Getattr(p, "name");
p = srcparms;
tm_methods = NewString(tm_method);
while (p) {
ptype = Getattr(p, "type");
pname = Getattr(p, "name");
/* Lookup the type */
tm = typemap_get(ptype, pname, ts);
if (!tm)
break;
/* Lookup the type */
tm = typemap_get(ptype, pname);
if (!tm)
break;
tm = Getattr(tm, tm_methods);
if (!tm)
break;
tm = Getattr(tm, tm_methods);
if (!tm)
break;
/* Got a match. Look for next typemap */
multi_tmap_method = NewStringf("%s-%s+%s:", tm_methods, ptype, pname);
Delete(tm_methods);
tm_methods = multi_tmap_method;
p = nextSibling(p);
}
/* Got a match. Look for next typemap */
multi_tmap_method = NewStringf("%s-%s+%s:", tm_methods, ptype, pname);
Delete(tm_methods);
if (!p && tm) {
/* Got some kind of match */
String *parms_str = ParmList_str_multibrackets(parms);
String *srcparms_str = ParmList_str_multibrackets(srcparms);
String *source_directive = NewStringf("typemap(%s) %s = %s", tmap_method, parms_str, srcparms_str);
typemap_register(tmap_method, parms, Getattr(tm, "code"), Getattr(tm, "locals"), Getattr(tm, "kwargs"), source_directive);
Delete(source_directive);
Delete(srcparms_str);
Delete(parms_str);
return 0;
}
ts--;
tm_methods = multi_tmap_method;
p = nextSibling(p);
}
Delete(tm_methods);
if (!p && tm) {
/* Got some kind of match */
String *parms_str = ParmList_str_multibrackets(parms);
String *srcparms_str = ParmList_str_multibrackets(srcparms);
String *source_directive = NewStringf("typemap(%s) %s = %s", tmap_method, parms_str, srcparms_str);
typemap_register(tmap_method, parms, Getattr(tm, "code"), Getattr(tm, "locals"), Getattr(tm, "kwargs"), source_directive);
Delete(source_directive);
Delete(srcparms_str);
Delete(parms_str);
return 0;
}
/* Not found */
return -1;
@ -411,7 +370,7 @@ void Swig_typemap_clear(const_String_or_char_ptr tmap_method, ParmList *parms) {
while (p) {
type = Getattr(p, "type");
name = Getattr(p, "name");
tm = typemap_get(type, name, tm_scope);
tm = typemap_get(type, name);
if (!tm)
return;
p = nextSibling(p);
@ -452,7 +411,6 @@ int Swig_typemap_apply(ParmList *src, ParmList *dest) {
String *ssig, *dsig;
Parm *p, *np, *lastp, *dp, *lastdp = 0;
int narg = 0;
int ts = tm_scope;
SwigType *type = 0, *name;
Hash *tm, *sm;
int match = 0;
@ -480,9 +438,9 @@ int Swig_typemap_apply(ParmList *src, ParmList *dest) {
/* make sure a typemap node exists for the last destination node */
type = Getattr(lastdp, "type");
tm = get_typemap(tm_scope, type);
tm = get_typemap(type);
if (!tm) {
set_typemap(tm_scope, type, &tm);
set_typemap(type, &tm);
}
name = Getattr(lastdp, "name");
if (name) {
@ -501,69 +459,65 @@ int Swig_typemap_apply(ParmList *src, ParmList *dest) {
type = Getattr(lastp, "type");
name = Getattr(lastp, "name");
while (ts >= 0) {
/* See if there is a matching typemap in this scope */
sm = typemap_get(type, name);
/* See if there is a matching typemap in this scope */
sm = typemap_get(type, name, ts);
/* if there is not matching, look for a typemap in the
original typedef, if any, like in:
/* if there is not matching, look for a typemap in the
original typedef, if any, like in:
typedef unsigned long size_t;
...
%apply(size_t) {my_size}; ==> %apply(unsigned long) {my_size};
*/
if (!sm) {
SwigType *ntype = SwigType_typedef_resolve(type);
if (ntype && (Cmp(ntype, type) != 0)) {
sm = typemap_get(ntype, name, ts);
}
Delete(ntype);
typedef unsigned long size_t;
...
%apply(size_t) {my_size}; ==> %apply(unsigned long) {my_size};
*/
if (!sm) {
SwigType *ntype = SwigType_typedef_resolve(type);
if (ntype && (Cmp(ntype, type) != 0)) {
sm = typemap_get(ntype, name);
}
Delete(ntype);
}
if (sm) {
/* Got a typemap. Need to only merge attributes for methods that match our signature */
Iterator ki;
match = 1;
for (ki = First(sm); ki.key; ki = Next(ki)) {
/* Check for a signature match with the source signature */
if ((count_args(ki.key) == narg) && (Strstr(ki.key, ssig))) {
String *oldm;
/* A typemap we have to copy */
String *nkey = Copy(ki.key);
Replace(nkey, ssig, dsig, DOH_REPLACE_ANY);
if (sm) {
/* Got a typemap. Need to only merge attributes for methods that match our signature */
Iterator ki;
match = 1;
for (ki = First(sm); ki.key; ki = Next(ki)) {
/* Check for a signature match with the source signature */
if ((count_args(ki.key) == narg) && (Strstr(ki.key, ssig))) {
String *oldm;
/* A typemap we have to copy */
String *nkey = Copy(ki.key);
Replace(nkey, ssig, dsig, DOH_REPLACE_ANY);
/* Make sure the typemap doesn't already exist in the target map */
/* Make sure the typemap doesn't already exist in the target map */
oldm = Getattr(tm, nkey);
if (!oldm || (!Getattr(tm, "code"))) {
String *code;
ParmList *locals;
ParmList *kwargs;
Hash *sm1 = ki.item;
oldm = Getattr(tm, nkey);
if (!oldm || (!Getattr(tm, "code"))) {
String *code;
ParmList *locals;
ParmList *kwargs;
Hash *sm1 = ki.item;
code = Getattr(sm1, "code");
locals = Getattr(sm1, "locals");
kwargs = Getattr(sm1, "kwargs");
if (code) {
String *src_str = ParmList_str_multibrackets(src);
String *dest_str = ParmList_str_multibrackets(dest);
String *source_directive = NewStringf("apply %s { %s }", src_str, dest_str);
code = Getattr(sm1, "code");
locals = Getattr(sm1, "locals");
kwargs = Getattr(sm1, "kwargs");
if (code) {
String *src_str = ParmList_str_multibrackets(src);
String *dest_str = ParmList_str_multibrackets(dest);
String *source_directive = NewStringf("apply %s { %s }", src_str, dest_str);
Replace(nkey, dsig, "", DOH_REPLACE_ANY);
Replace(nkey, "tmap:", "", DOH_REPLACE_ANY);
typemap_register(nkey, dest, code, locals, kwargs, source_directive);
Replace(nkey, dsig, "", DOH_REPLACE_ANY);
Replace(nkey, "tmap:", "", DOH_REPLACE_ANY);
typemap_register(nkey, dest, code, locals, kwargs, source_directive);
Delete(source_directive);
Delete(dest_str);
Delete(src_str);
}
Delete(source_directive);
Delete(dest_str);
Delete(src_str);
}
Delete(nkey);
}
Delete(nkey);
}
}
ts--;
}
Delete(ssig);
Delete(dsig);
@ -597,7 +551,7 @@ void Swig_typemap_clear_apply(Parm *parms) {
}
p = np;
}
tm = get_typemap(tm_scope, Getattr(lastp, "type"));
tm = get_typemap(Getattr(lastp, "type"));
if (!tm) {
Delete(tsig);
return;
@ -711,7 +665,6 @@ static Hash *typemap_search(const_String_or_char_ptr tmap_method, SwigType *type
SwigType *primitive = 0;
SwigType *ctype = 0;
SwigType *ctype_unstripped = 0;
int ts;
int isarray;
const String *cname = 0;
const String *cqualifiedname = 0;
@ -722,90 +675,86 @@ static Hash *typemap_search(const_String_or_char_ptr tmap_method, SwigType *type
cname = name;
if ((qualifiedname) && Len(qualifiedname))
cqualifiedname = qualifiedname;
ts = tm_scope;
if (debug_display) {
String *typestr = SwigType_str(type, cqualifiedname ? cqualifiedname : cname);
Swig_diagnostic(Getfile(node), Getline(node), "Searching for a suitable '%s' typemap for: %s\n", tmap_method, typestr);
Delete(typestr);
}
while (ts >= 0) {
ctype = Copy(type);
ctype_unstripped = Copy(ctype);
while (ctype) {
/* Try to get an exact type-match */
tm = get_typemap(ts, ctype);
result = typemap_search_helper(debug_display, tm, tm_method, ctype, cqualifiedname, cname, &backup);
if (result && Getattr(result, "code"))
goto ret_result;
ctype = Copy(type);
ctype_unstripped = Copy(ctype);
while (ctype) {
/* Try to get an exact type-match */
tm = get_typemap(ctype);
result = typemap_search_helper(debug_display, tm, tm_method, ctype, cqualifiedname, cname, &backup);
if (result && Getattr(result, "code"))
goto ret_result;
{
/* Look for the type reduced to just the template prefix - for templated types without the template parameter list being specified */
SwigType *template_prefix = SwigType_istemplate_only_templateprefix(ctype);
if (template_prefix) {
tm = get_typemap(ts, template_prefix);
result = typemap_search_helper(debug_display, tm, tm_method, template_prefix, cqualifiedname, cname, &backup);
Delete(template_prefix);
if (result && Getattr(result, "code"))
goto ret_result;
}
}
/* look for [ANY] arrays */
isarray = SwigType_isarray(ctype);
if (isarray) {
/* If working with arrays, strip away all of the dimensions and replace with "ANY".
See if that generates a match */
SwigType *noarrays = strip_arrays(ctype);
tm = get_typemap(ts, noarrays);
result = typemap_search_helper(debug_display, tm, tm_method, noarrays, cqualifiedname, cname, &backup);
Delete(noarrays);
{
/* Look for the type reduced to just the template prefix - for templated types without the template parameter list being specified */
SwigType *template_prefix = SwigType_istemplate_only_templateprefix(ctype);
if (template_prefix) {
tm = get_typemap(template_prefix);
result = typemap_search_helper(debug_display, tm, tm_method, template_prefix, cqualifiedname, cname, &backup);
Delete(template_prefix);
if (result && Getattr(result, "code"))
goto ret_result;
}
/* No match so far - try with a qualifier stripped (strip one qualifier at a time until none remain)
* The order of stripping in SwigType_strip_single_qualifier is used to provide some sort of consistency
* with the default (SWIGTYPE) typemap matching rules for the first qualifier to be stripped. */
{
SwigType *oldctype = ctype;
ctype = SwigType_strip_single_qualifier(oldctype);
if (!Equal(ctype, oldctype)) {
Delete(oldctype);
continue;
}
Delete(oldctype);
}
/* Once all qualifiers are stripped try resolve a typedef */
{
SwigType *oldctype = ctype;
ctype = SwigType_typedef_resolve(ctype_unstripped);
Delete(oldctype);
ctype_unstripped = Copy(ctype);
}
}
/* Hmmm. Well, no match seems to be found at all. See if there is some kind of default (SWIGTYPE) mapping */
primitive = SwigType_default_create(type);
while (primitive) {
tm = get_typemap(ts, primitive);
result = typemap_search_helper(debug_display, tm, tm_method, primitive, cqualifiedname, cname, &backup);
/* look for [ANY] arrays */
isarray = SwigType_isarray(ctype);
if (isarray) {
/* If working with arrays, strip away all of the dimensions and replace with "ANY".
See if that generates a match */
SwigType *noarrays = strip_arrays(ctype);
tm = get_typemap(noarrays);
result = typemap_search_helper(debug_display, tm, tm_method, noarrays, cqualifiedname, cname, &backup);
Delete(noarrays);
if (result && Getattr(result, "code"))
goto ret_result;
}
{
SwigType *nprim = SwigType_default_deduce(primitive);
Delete(primitive);
primitive = nprim;
/* No match so far - try with a qualifier stripped (strip one qualifier at a time until none remain)
* The order of stripping in SwigType_strip_single_qualifier is used to provide some sort of consistency
* with the default (SWIGTYPE) typemap matching rules for the first qualifier to be stripped. */
{
SwigType *oldctype = ctype;
ctype = SwigType_strip_single_qualifier(oldctype);
if (!Equal(ctype, oldctype)) {
Delete(oldctype);
continue;
}
Delete(oldctype);
}
if (ctype != type) {
Delete(ctype);
ctype = 0;
/* Once all qualifiers are stripped try resolve a typedef */
{
SwigType *oldctype = ctype;
ctype = SwigType_typedef_resolve(ctype_unstripped);
Delete(oldctype);
ctype_unstripped = Copy(ctype);
}
ts--; /* Hmmm. Nothing found in this scope. Guess we'll go try another scope */
}
/* Hmmm. Well, no match seems to be found at all. See if there is some kind of default (SWIGTYPE) mapping */
primitive = SwigType_default_create(type);
while (primitive) {
tm = get_typemap(primitive);
result = typemap_search_helper(debug_display, tm, tm_method, primitive, cqualifiedname, cname, &backup);
if (result && Getattr(result, "code"))
goto ret_result;
{
SwigType *nprim = SwigType_default_deduce(primitive);
Delete(primitive);
primitive = nprim;
}
}
if (ctype != type) {
Delete(ctype);
ctype = 0;
}
result = backup;
@ -1318,6 +1267,7 @@ static String *Swig_typemap_lookup_impl(const_String_or_char_ptr tmap_method, No
char *cmethod = Char(tmap_method);
int optimal_attribute = 0;
int optimal_substitution = 0;
int delete_optimal_attribute = 0;
int num_substitutions = 0;
SwigType *matchtype = 0;
@ -1372,7 +1322,6 @@ static String *Swig_typemap_lookup_impl(const_String_or_char_ptr tmap_method, No
Delete(typestr);
}
Delete(qpname);
qpname = 0;
Delete(noscope_pname);
@ -1391,23 +1340,16 @@ static String *Swig_typemap_lookup_impl(const_String_or_char_ptr tmap_method, No
s = Copy(s); /* Make a local copy of the typemap code */
/* Attach kwargs - ie the typemap attributes */
kw = Getattr(tm, "kwargs");
while (kw) {
String *value = Copy(Getattr(kw, "value"));
String *kwtype = Getattr(kw, "type");
char *ckwname = Char(Getattr(kw, "name"));
if (kwtype) {
String *mangle = Swig_string_mangle(kwtype);
Append(value, mangle);
Delete(mangle);
/* Look in the "out" typemap for the "optimal" attribute */
if (Cmp(cmethod, "out") == 0) {
kw = Getattr(tm, "kwargs");
while (kw) {
if (Cmp(Getattr(kw, "name"), "optimal") == 0) {
optimal_attribute = GetFlag(kw, "value");
break;
}
kw = nextSibling(kw);
}
sprintf(temp, "%s:%s", cmethod, ckwname);
Setattr(node, typemap_method_name(temp), value);
if (Cmp(temp, "out:optimal") == 0)
optimal_attribute = (Cmp(value, "0") != 0) ? 1 : 0;
Delete(value);
kw = nextSibling(kw);
}
if (optimal_attribute) {
@ -1438,14 +1380,15 @@ static String *Swig_typemap_lookup_impl(const_String_or_char_ptr tmap_method, No
}
}
if (!optimal_substitution) {
Swig_warning(WARN_TYPEMAP_OUT_OPTIMAL_IGNORED, Getfile(node), Getline(node), "Method %s usage of the optimal attribute ignored\n", Swig_name_decl(node));
Swig_warning(WARN_TYPEMAP_OUT_OPTIMAL_IGNORED, Getfile(s), Getline(s), "in the out typemap as the following cannot be used to generate optimal code: %s\n", clname);
Delattr(node, "tmap:out:optimal");
Swig_warning(WARN_TYPEMAP_OUT_OPTIMAL_IGNORED, Getfile(node), Getline(node), "Method %s usage of the optimal attribute ignored\n", Swig_name_decl(node));
Swig_warning(WARN_TYPEMAP_OUT_OPTIMAL_IGNORED, Getfile(s), Getline(s), "in the out typemap as the following cannot be used to generate optimal code: %s\n", clname);
delete_optimal_attribute = 1;
}
} else {
assert(!f);
}
}
if (actioncode) {
assert(f);
Append(f->code, actioncode);
@ -1486,6 +1429,41 @@ static String *Swig_typemap_lookup_impl(const_String_or_char_ptr tmap_method, No
Delete(parm_sublist);
}
/* Attach kwargs - ie the typemap attributes */
kw = Getattr(tm, "kwargs");
while (kw) {
String *value = Copy(Getattr(kw, "value"));
String *kwtype = Getattr(kw, "type");
char *ckwname = Char(Getattr(kw, "name"));
{
/* Expand special variables in typemap attributes. */
SwigType *ptype = Getattr(node, "type");
String *pname = Getattr(node, "name");
SwigType *mtype = Getattr(node, "tmap:match");
SwigType *matchtype = mtype ? mtype : ptype;
ParmList *parm_sublist;
typemap_replace_vars(value, NULL, matchtype, ptype, pname, (char *)lname, 1);
/* Expand special variable macros (embedded typemaps) in typemap attributes. */
parm_sublist = NewParmWithoutFileLineInfo(ptype, pname);
Setattr(parm_sublist, "lname", lname);
replace_embedded_typemap(value, parm_sublist, NULL, tm);
Delete(parm_sublist);
}
if (kwtype) {
String *mangle = Swig_string_mangle(kwtype);
Append(value, mangle);
Delete(mangle);
}
sprintf(temp, "%s:%s", cmethod, ckwname);
Setattr(node, typemap_method_name(temp), value);
Delete(value);
kw = nextSibling(kw);
}
if (delete_optimal_attribute)
Delattr(node, "tmap:out:optimal");
Replace(s, "$name", pname, DOH_REPLACE_ANY);
symname = Getattr(node, "sym:name");
@ -1558,17 +1536,44 @@ String *Swig_typemap_lookup(const_String_or_char_ptr tmap_method, Node *node, co
* If this hash (tm) contains a linked list of parameters under its "kwargs"
* attribute, add keys for each of those named keyword arguments to this
* parameter for later use.
* For example, attach the typemap attributes to p:
* For example, attach the typemap attributes to firstp (first parameter in parameter list):
* %typemap(in, foo="xyz") ...
* A new attribute called "tmap:in:foo" with value "xyz" is attached to p.
* A new attribute called "tmap:in:foo" with value "xyz" is attached to firstp.
* Also expands special variables and special variable macros in the typemap attributes.
* ----------------------------------------------------------------------------- */
static void typemap_attach_kwargs(Hash *tm, const_String_or_char_ptr tmap_method, Parm *p) {
static void typemap_attach_kwargs(Hash *tm, const_String_or_char_ptr tmap_method, Parm *firstp, int nmatch) {
String *temp = NewStringEmpty();
Parm *kw = Getattr(tm, "kwargs");
while (kw) {
String *value = Copy(Getattr(kw, "value"));
String *type = Getattr(kw, "type");
int i;
Parm *p = firstp;
/* Expand special variables */
for (i = 0; i < nmatch; i++) {
SwigType *type = Getattr(p, "type");
String *pname = Getattr(p, "name");
String *lname = Getattr(p, "lname");
SwigType *mtype = Getattr(p, "tmap:match");
SwigType *matchtype = mtype ? mtype : type;
typemap_replace_vars(value, NULL, matchtype, type, pname, lname, i + 1);
p = nextSibling(p);
}
/* Expand special variable macros (embedded typemaps).
* Special variable are expanded first above as they might be used in the special variable macros.
* For example: $typemap(imtype, $2_type). */
p = firstp;
for (i = 0; i < nmatch; i++) {
SwigType *type = Getattr(p, "type");
String *pname = Getattr(p, "name");
String *lname = Getattr(p, "lname");
ParmList *parm_sublist = NewParmWithoutFileLineInfo(type, pname);
Setattr(parm_sublist, "lname", lname);
replace_embedded_typemap(value, parm_sublist, NULL, tm);
p = nextSibling(p);
}
if (type) {
Hash *v = NewHash();
Setattr(v, "type", type);
@ -1578,13 +1583,13 @@ static void typemap_attach_kwargs(Hash *tm, const_String_or_char_ptr tmap_method
}
Clear(temp);
Printf(temp, "%s:%s", tmap_method, Getattr(kw, "name"));
Setattr(p, typemap_method_name(temp), value);
Setattr(firstp, typemap_method_name(temp), value);
Delete(value);
kw = nextSibling(kw);
}
Clear(temp);
Printf(temp, "%s:match_type", tmap_method);
Setattr(p, typemap_method_name(temp), Getattr(tm, "type"));
Setattr(firstp, typemap_method_name(temp), Getattr(tm, "type"));
Delete(temp);
}
@ -1779,7 +1784,7 @@ void Swig_typemap_attach_parms(const_String_or_char_ptr tmap_method, ParmList *p
Setattr(firstp, typemap_method_name(temp), p);
/* Attach kwargs */
typemap_attach_kwargs(tm, tmap_method, firstp);
typemap_attach_kwargs(tm, tmap_method, firstp, nmatch);
/* Replace the argument number */
sprintf(temp, "%d", argnum);
@ -2054,16 +2059,9 @@ static void replace_embedded_typemap(String *s, ParmList *parm_sublist, Wrapper
* ----------------------------------------------------------------------------- */
void Swig_typemap_debug() {
int ts;
int nesting_level = 2;
Printf(stdout, "---[ typemaps ]--------------------------------------------------------------\n");
ts = tm_scope;
while (ts >= 0) {
Printf(stdout, "::: scope %d\n\n", ts);
Swig_print(typemaps[ts], nesting_level);
ts--;
}
Swig_print(typemaps, nesting_level);
Printf(stdout, "-----------------------------------------------------------------------------\n");
}