add support for options in rename/namewarn and central methods to access the rename/warning hashs

git-svn-id: https://swig.svn.sourceforge.net/svnroot/swig/trunk/SWIG@8150 626c5289-ae23-0410-ae9c-e8d60b6d4f22
This commit is contained in:
Marcelo Matus 2005-12-31 10:41:54 +00:00
commit b034e6c266
8 changed files with 211 additions and 67 deletions

View file

@ -1,6 +1,56 @@
Version 1.3.28 (unreleased).
===========================
12/30/2005: mmatus
- Add option/format support to %rename and %namewarn.
Now %namewarn can force renaming, for example:
%namewarn("314: import is a keyword",rename="_%s") "import";
and rename can also support format forms:
%rename("swig_%s") import;
Now, since the format is processed via swig Printf, you
can use encoder as follows:
%rename("%(title)s") import; -> Import
%rename("%(upper)s") import; -> IMPORT
%rename("%(lower)s") Import; -> import
This will allow us to add more encoders, as the next
expected 'regexp'.
- In the meantime, add the 'command' encoder, you can use it as follows
%rename(%(command:sed -e 's/\([a-z]\)/\U\\1/' <<< %s)s) import; -> Import
where swig executes the command defined as %(command:<command here>)s.
Note that swig pass the name and the prefix as parameters
that can capture via '%s'. Another example
#define awk_cmd "%(command:awk '{if (NF==2) {print $2_$1} else {print _$1}}' <<< %s %s)s"
%rename(awk_cmd) ns1::import; -> ns1_import;
%rename(awk_cmd) import; -> _import
Just remember, first parameter is the name, the second is
the prefix. If you don't need the prefix, just put one '%s'
argument in your command.
Note that the 'command' encoder requires popen in your platform.
- The rename directive has its first option 'match', to
match the node type, for example:
%rename(%(title)s,match="enumitem") *;
enum Hello {
hi, hello -> Hi, Hello
};
12/30/2005: mmatus
- Add initial support for gcj and Java -> <target language> mechanism.

View file

@ -43,9 +43,9 @@ extern int yylex();
/* parser.y */
extern SwigType *Swig_cparse_type(String *);
extern Node *Swig_cparse(File *);
extern Hash *Swig_cparse_namewarn();
extern String *Swig_cparse_name_warning(Node *n, String *prefix, String *name,SwigType *decl);
extern String *Swig_cparse_symbol_name(Node *n,String *prefix, String *name, SwigType *decl, String *oldname);
extern Hash *Swig_cparse_features();
extern Hash *Swig_cparse_rename();
extern void SWIG_cparse_set_compact_default_args(int defargs);
extern int SWIG_cparse_template_reduce(int treduce);

View file

@ -240,24 +240,24 @@ static String *feature_identifier_fix(String *s) {
}
}
static void single_rename_add(const char *name, SwigType *decl, const char *cnewname) {
static void single_rename_add(const char *name, SwigType *decl, Hash *newname) {
String *nname;
String *newname = NewString(cnewname);
if (Namespaceprefix) {
nname = NewStringf("%s::%s",Namespaceprefix, name);
} else {
nname = NewString(name);
}
Swig_name_object_set(Swig_cparse_rename(),nname,decl,newname);
Delete(newname);
Delete(nname);
}
/* Add a new rename. Works much like new_feature including default argument handling. */
static void rename_add(const char *name, SwigType *decl, const char *newname, ParmList *declaratorparms) {
static void rename_add(const char *name, SwigType *decl, Hash *kwargs, ParmList *declaratorparms) {
ParmList *declparms = declaratorparms;
String *newname = kwargs;
/* Add the name */
single_rename_add(name, decl, newname);
@ -288,7 +288,7 @@ static void rename_add(const char *name, SwigType *decl, const char *newname, Pa
}
}
static void namewarn_add(const char *name, SwigType *decl, const char *warning) {
static void namewarn_add(const char *name, SwigType *decl, Hash *warning) {
String *nname;
if (Namespaceprefix) {
nname = NewStringf("%s::%s",Namespaceprefix, name);
@ -296,7 +296,7 @@ static void namewarn_add(const char *name, SwigType *decl, const char *warning)
nname = NewString(name);
}
Swig_name_object_set(Swig_cparse_namewarn(),nname,decl,NewString(warning));
Swig_name_object_set(Swig_cparse_namewarn(),nname,decl,warning);
Delete(nname);
}
@ -311,14 +311,123 @@ static void rename_inherit(String *base, String *derived) {
/* This is a bit of a mess. Need to clean up */
static String *add_oldname = 0;
static String *make_name(String *name,SwigType *decl) {
String *rn = 0;
String *origname = name;
int destructor = 0;
if (name && (*(Char(name)) == '~')) {
destructor = 1;
/* Return the node name when it requires to emit a name warning */
String *Swig_cparse_name_warning(Node *n, String *prefix, String *name,SwigType *decl) {
if (n) {
/* Return in the obvious cases */
if (!Swig_cparse_namewarn() || !name || !need_name_warning(n)) {
return 0;
} else {
String *access = Getattr(n,"access");
int is_public = !access || (Strcmp(access,"public") == 0);
if (!is_public && !need_protected(n,dirprot_mode)) {
return 0;
}
}
}
if (name) {
/* Check to see if the name is in the hash */
Hash *res = Swig_name_object_get(Swig_cparse_namewarn(),prefix,name,decl);
return res ? Getattr(res,"name"): 0;
} else {
return 0;
}
}
/* Create a name applying rename/namewarn if needed */
String *Swig_cparse_symbol_name(Node *n, String *prefix, String *name, SwigType *decl, String *oldname) {
String *rn = 0;
Hash *wrn;
int destructor = name && (*(Char(name)) == '~');
int need_wrn = 1;
if (n) {
/* Return in the obvious cases */
if (!Swig_cparse_namewarn() || !name || !need_name_warning(n)) {
need_wrn = 0;
} else {
String *access = Getattr(n,"access");
int is_public = !access || (Strcmp(access,"public") == 0);
if (!is_public && !need_protected(n,dirprot_mode)) {
need_wrn = 0;
}
}
}
wrn = need_wrn ? Swig_name_object_get(Swig_cparse_namewarn(),prefix,name,decl) : 0;
if (wrn) {
String *fmt = 0;
Hash *kw = nextSibling(wrn);
while (kw) {
String *kname = Getattr(kw,"name");
if (kname && (Cmp(kname,"rename") == 0)) {
fmt = Getattr(kw,"value");
break;
}
kw = nextSibling(kw);
}
if (fmt) {
char *cprefix = prefix ? Char(prefix) : "";
if ((wrn) && (Len(wrn))) {
if (n) {
SWIG_WARN_NODE_BEGIN(n);
Swig_warning(0,Getfile(n),Getline(n), "%s\n", Getattr(wrn,"name"));
SWIG_WARN_NODE_END(n);
} else {
Swig_warning(0,Getfile(name),Getline(name), "%s\n", Getattr(wrn,"name"));
}
}
return NewStringf(fmt,name,cprefix);
}
}
rn = Swig_name_object_get(Swig_cparse_rename(), prefix, name, decl);
if (!rn) {
return oldname ? Copy(oldname): Copy(name);
} else {
String *type = 0;
String *newname = Getattr(rn,"name");
Hash *kw = nextSibling(rn);
while (kw) {
String *kname = Getattr(kw,"name");
if (kname && (Cmp(kname,"match") == 0)) {
type = Getattr(kw,"value");
break;
}
kw = nextSibling(kw);
}
if (type){
int match = 0;
if (n) {
String *ntype = Getattr(n,"nodeType");
if (ntype && Equal(ntype,type)) {
match = 1;
}
}
if (!match) {
return oldname ? Copy(oldname): Copy(name);
}
}
if (Strcmp(newname,"$ignore") == 0) {
return Copy(newname);
} else {
char *cprefix = prefix ? Char(prefix) : "";
if (destructor && (*(Char(newname)) != '~')) {
String *fmt = NewStringf("~%s", newname);
String *res = NewStringf(fmt,name,cprefix);
Delete(fmt);
return res;
} else {
String *res = NewStringf(newname,name,cprefix);
return res;
}
}
}
}
static String *make_name(Node *n, String *name,SwigType *decl) {
String *origname = name;
int destructor = name && (*(Char(name)) == '~');
if (yyrename) {
String *s = (yyrename);
yyrename = 0;
@ -334,18 +443,7 @@ static String *make_name(String *name,SwigType *decl) {
if (add_oldname) return Copy(add_oldname);
return Copy(origname);
}
rn = Swig_name_object_get(Swig_cparse_rename(), Namespaceprefix, name, decl);
if (!rn) {
if (add_oldname) return Copy(add_oldname);
return Copy(name);
}
if (destructor) {
if (Strcmp(rn,"$ignore") != 0) {
String *s = NewStringf("~%s", rn);
return s;
}
}
return Copy(rn);
return Swig_cparse_symbol_name(n,Namespaceprefix,name,decl,add_oldname);
}
/* Generate an unnamed identifier */
@ -354,23 +452,6 @@ static String *make_unnamed() {
return NewStringf("$unnamed%d$",unnamed);
}
/* Return the node name when it requires to emit a name warning */
static String *name_warning(Node *n,String *name,SwigType *decl) {
/* Return in the obvious cases */
if (!Swig_cparse_namewarn() || !name || !need_name_warning(n)) {
return 0;
} else {
String *access = Getattr(n,"access");
int is_public = !access || (Strcmp(access,"public") == 0);
if (!is_public && !need_protected(n,dirprot_mode)) {
return 0;
}
}
/* Check to see if the name is in the hash */
return Swig_name_object_get(Swig_cparse_namewarn(),Namespaceprefix,name,decl);
}
/* Return if the node is a friend declaration */
static int is_friend(Node *n) {
return Cmp(Getattr(n,"storage"),"friend") == 0;
@ -469,26 +550,26 @@ static void add_symbols(Node *n) {
if (!SwigType_isfunction(decl)) {
String *makename = Getattr(n,"parser:makename");
if (makename) {
symname = make_name(makename,0);
symname = make_name(n, makename,0);
Delattr(n,"parser:makename"); /* temporary information, don't leave it hanging around */
} else {
makename = Getattr(n,"name");
symname = make_name(makename,0);
symname = make_name(n, makename,0);
}
if (!symname) {
symname = Copy(Getattr(n,"unnamed"));
}
if (symname) {
wrn = name_warning(n,symname,0);
wrn = Swig_cparse_name_warning(n, Namespaceprefix, symname,0);
Swig_features_get(features_hash, Namespaceprefix, Getattr(n,"name"), 0, n);
}
} else {
SwigType *fdecl = Copy(decl);
SwigType *fun = SwigType_pop_function(fdecl);
symname = make_name(Getattr(n,"name"),fun);
wrn = name_warning(n,symname,fun);
symname = make_name(n, Getattr(n,"name"),fun);
wrn = Swig_cparse_name_warning(n, Namespaceprefix,symname,fun);
Swig_features_get(features_hash,Namespaceprefix,Getattr(n,"name"),fun,n);
Delete(fdecl);
@ -2163,16 +2244,19 @@ pragma_lang : LPAREN ID RPAREN { $$ = $2; }
rename_directive : rename_namewarn declarator idstring SEMI {
SwigType *t = $2.type;
Hash *kws = NewHash();
Setattr(kws,"name",$3);
if (!Len(t)) t = 0;
if ($1) {
rename_add($2.id,t,$3,$2.parms);
rename_add($2.id,t,kws,$2.parms);
} else {
namewarn_add($2.id,t,$3);
namewarn_add($2.id,t,kws);
}
$$ = 0;
scanner_clear_rename();
}
| rename_namewarn LPAREN idstring RPAREN declarator cpp_const SEMI {
| rename_namewarn LPAREN kwargs RPAREN declarator cpp_const SEMI {
String *fixname;
SwigType *t = $5.type;
fixname = feature_identifier_fix($5.id);
@ -2217,7 +2301,7 @@ rename_directive : rename_namewarn declarator idstring SEMI {
$$ = 0;
scanner_clear_rename();
}
| rename_namewarn LPAREN idstring RPAREN string SEMI {
| rename_namewarn LPAREN kwargs RPAREN string SEMI {
if ($1) {
rename_add($5,0,$3,0);
} else {
@ -3145,7 +3229,7 @@ cpp_class_decl :
}
Delete(class_rename);
class_rename = make_name($3,0);
class_rename = make_name(0,$3,0);
Classprefix = NewString($3);
/* Deal with inheritance */
if ($4) {
@ -3330,7 +3414,7 @@ cpp_class_decl :
| storage_class cpptype LBRACE {
Delete(class_rename);
class_rename = make_name(0,0);
class_rename = make_name(0,0,0);
if (strcmp($2,"class") == 0) {
cplus_mode = CPLUS_PRIVATE;
} else {
@ -3925,7 +4009,7 @@ cpp_member : c_declaration { $$ = $1; }
$$ = $1;
if (extendmode) {
String *symname;
symname= make_name(Getattr($$,"name"), Getattr($$,"decl"));
symname= make_name(0,Getattr($$,"name"), Getattr($$,"decl"));
if (Strcmp(symname,Getattr($$,"name")) == 0) {
/* No renaming operation. Set name to class name */
Delete(yyrename);

View file

@ -2392,7 +2392,7 @@ class CSHARP : public Language {
count++;
plist = nextSibling(plist);
}
String *wrn = pn ? Swig_name_object_get(Swig_cparse_namewarn(),0,pn,0) : 0;
String *wrn = pn ? Swig_cparse_name_warning(0,0,pn,0) : 0;
arg = (!pn || (count > 1) || wrn) ? NewStringf("arg%d",arg_num) : Copy(pn);
}

View file

@ -2546,7 +2546,7 @@ class JAVA : public Language {
count++;
plist = nextSibling(plist);
}
String *wrn = pn ? Swig_name_object_get(Swig_cparse_namewarn(),0,pn,0) : 0;
String *wrn = pn ? Swig_cparse_name_warning(0, 0, pn, 0) : 0;
arg = (!pn || (count > 1) || wrn) ? NewStringf("arg%d",arg_num) : Copy(pn);
}

View file

@ -1970,6 +1970,10 @@ int Language::classDirector(Node *n) {
* ---------------------------------------------------------------------- */
static void addCopyConstructor(Node *n)
{
Node *cn = NewHash();
set_nodeType(cn,"constructor");
Setattr(cn,"access","public");
String *cname = Getattr(n,"name");
SwigType *type = Copy(cname);
String *last = Swig_scopename_last(cname);
@ -1977,14 +1981,12 @@ static void addCopyConstructor(Node *n)
String *cc = NewStringf("r.q(const).%s", type);
String *decl = NewStringf("f(%s).",cc);
String *csymname = Getattr(n,"sym:name");
String *symname = Swig_name_object_get(Swig_cparse_rename(), cname, last, decl);
String *symname = Swig_cparse_symbol_name(cn, cname, last, decl, 0);
if (!symname) {
symname = Copy(csymname);
}
Parm *p = NewParm(cc,"_swig_self");
Node *cn = NewHash();
set_nodeType(cn,"constructor");
Setattr(cn,"name",name);
Setattr(cn,"sym:name",symname);
SetFlag(cn,"feature:new");
@ -2018,18 +2020,20 @@ static void addCopyConstructor(Node *n)
static void addDefaultConstructor(Node *n)
{
Node *cn = NewHash();
set_nodeType(cn,"constructor");
Setattr(cn,"access","public");
String *cname = Getattr(n,"name");
String *last = Swig_scopename_last(cname);
String *name = NewStringf("%s::%s",cname,last);
String *decl = NewString("f().");
String *csymname = Getattr(n,"sym:name");
String *symname = Swig_name_object_get(Swig_cparse_rename(), cname, last, decl);
String *symname = Swig_cparse_symbol_name(cn, cname, last, decl, 0);
if (!symname) {
symname = Copy(csymname);
}
Node *cn = NewHash();
set_nodeType(cn,"constructor");
Setattr(cn,"name",name);
Setattr(cn,"sym:name",symname);
SetFlag(cn,"feature:new");
@ -2061,18 +2065,20 @@ static void addDefaultConstructor(Node *n)
static void addDestructor(Node *n)
{
Node *cn = NewHash();
set_nodeType(cn,"destructor");
Setattr(cn,"access","public");
String *cname = Getattr(n,"name");
String *last = Swig_scopename_last(cname);
Insert(last,0,"~");
String *name = NewStringf("%s::%s",cname,last);
String *decl = NewString("f().");
String *symname = Swig_name_object_get(Swig_cparse_rename(), cname, last, decl);
String *symname = Swig_cparse_symbol_name(cn, cname, last, decl, 0);
if (!symname) {
symname = NewStringf("~%s",Getattr(n,"sym:name"));
}
Node *cn = NewHash();
set_nodeType(cn,"destructor");
Setattr(cn,"name",name);
Setattr(cn,"sym:name",symname);
Setattr(cn,"decl","f().");

View file

@ -1575,7 +1575,7 @@ public:
if (i == num_required) Putc('|', parse_args); /* Optional argument separator */
/* Keyword argument handling */
String *wrn = (allow_kwargs && pn) ? Swig_name_object_get(Swig_cparse_namewarn(),0,pn,0) : 0;
String *wrn = (allow_kwargs && pn) ? Swig_cparse_name_warning(0,0,pn,0) : 0;
if (!wrn && Len(pn)) {
Printf(kwargs,"(char *) \"%s\",", pn);
} else {

View file

@ -51,6 +51,9 @@ AC_CHECK_TYPES([bool])
AC_LANG_POP([C++])
# Check for popen
AC_CHECK_FUNC(popen, AC_DEFINE(HAVE_POPEN, 1, [Define if popen is available]))
# Set info about shared libraries.
AC_SUBST(SO)
AC_SUBST(LDSHARED)
@ -1837,4 +1840,5 @@ AC_CONFIG_FILES([ \
AC_CONFIG_FILES([preinst-swig], [chmod +x preinst-swig])
AC_OUTPUT
dnl configure.in ends here