1816 lines
69 KiB
Python
1816 lines
69 KiB
Python
#! /usr/bin/env python
|
|
|
|
import os
|
|
import re
|
|
import xml.dom.minidom
|
|
import string
|
|
import sys
|
|
|
|
full_constructors = {
|
|
'disco_svc_metadata': (
|
|
'''LASSO_EXPORT LassoIdWsf2DiscoSvcMetadata* lasso_idwsf2_disco_svc_metadata_new_full(
|
|
\t\tconst gchar *service_type, const gchar *abstract,
|
|
\t\tconst gchar *provider_id, const gchar *soap_endpoint);''',
|
|
'''
|
|
LassoIdWsf2DiscoSvcMetadata*
|
|
lasso_idwsf2_disco_svc_metadata_new_full(const gchar *service_type, const gchar *abstract,
|
|
\t\tconst gchar *provider_id, const gchar *soap_endpoint)
|
|
{
|
|
\tLassoIdWsf2DiscoSvcMetadata *metadata;
|
|
\tLassoIdWsf2DiscoEndpointContext *endpoint_context;
|
|
|
|
\tmetadata = lasso_idwsf2_disco_svc_metadata_new();
|
|
|
|
\tmetadata->Abstract = g_strdup(abstract);
|
|
\tmetadata->ProviderID = g_strdup(provider_id);
|
|
|
|
\tendpoint_context = lasso_idwsf2_disco_endpoint_context_new_full(soap_endpoint);
|
|
\tmetadata->ServiceContext = g_list_append(NULL,
|
|
\t\tlasso_idwsf2_disco_service_context_new_full(service_type, endpoint_context));
|
|
|
|
\treturn metadata;
|
|
}
|
|
'''),
|
|
|
|
'disco_svc_md_register' : (
|
|
'''LASSO_EXPORT LassoIdWsf2DiscoSvcMDRegister* lasso_idwsf2_disco_svc_md_register_new_full(
|
|
\t\tconst gchar *service_type, const gchar *abstract,
|
|
\t\tconst gchar *provider_id, const gchar *soap_endpoint);''',
|
|
'''
|
|
LassoIdWsf2DiscoSvcMDRegister*
|
|
lasso_idwsf2_disco_svc_md_register_new_full(const gchar *service_type, const gchar *abstract,
|
|
\t\tconst gchar *provider_id, const gchar *soap_endpoint)
|
|
{
|
|
\tLassoIdWsf2DiscoSvcMDRegister *metadata_register;
|
|
\tLassoIdWsf2DiscoSvcMetadata *metadata;
|
|
|
|
\tmetadata_register = lasso_idwsf2_disco_svc_md_register_new();
|
|
\tmetadata = lasso_idwsf2_disco_svc_metadata_new_full(service_type, abstract, provider_id,
|
|
\t\t\tsoap_endpoint);
|
|
\tmetadata_register->SvcMD = g_list_append(
|
|
\t\t\tmetadata_register->SvcMD, metadata);
|
|
|
|
\treturn metadata_register;
|
|
}'''),
|
|
|
|
'dstref_query_item': (
|
|
'''LASSO_EXPORT LassoIdWsf2DstRefQueryItem* lasso_idwsf2_dstref_query_item_new_full(
|
|
\t\tconst gchar *item_xpath, const gchar *item_id);''',
|
|
'''
|
|
LassoIdWsf2DstRefQueryItem*
|
|
lasso_idwsf2_dstref_query_item_new_full(const gchar *item_xpath, const gchar *item_id)
|
|
{
|
|
\tLassoIdWsf2DstRefResultQuery *item_result_query = LASSO_IDWSF2_DSTREF_RESULT_QUERY(
|
|
\t\tlasso_idwsf2_dstref_query_item_new());
|
|
\tLassoIdWsf2DstResultQueryBase *item_result_query_base = LASSO_IDWSF2_DST_RESULT_QUERY_BASE(
|
|
\t\titem_result_query);
|
|
|
|
\titem_result_query->Select = g_strdup(item_xpath);
|
|
\titem_result_query_base->itemID = g_strdup(item_id);
|
|
|
|
\treturn LASSO_IDWSF2_DSTREF_QUERY_ITEM(item_result_query);
|
|
}'''),
|
|
|
|
'sb2_redirect_request': (
|
|
'''LASSO_EXPORT LassoIdWsf2Sb2RedirectRequest* lasso_idwsf2_sb2_redirect_request_new_full(
|
|
\t\tconst gchar *redirect_url);''',
|
|
'''
|
|
LassoIdWsf2Sb2RedirectRequest*
|
|
lasso_idwsf2_sb2_redirect_request_new_full(const gchar *redirect_url)
|
|
{
|
|
\tLassoIdWsf2Sb2RedirectRequest *request;
|
|
|
|
\trequest = lasso_idwsf2_sb2_redirect_request_new();
|
|
\trequest->redirectURL = g_strdup(redirect_url);
|
|
|
|
\treturn request;
|
|
}'''),
|
|
|
|
'disco_endpoint_context': (
|
|
'''LASSO_EXPORT LassoIdWsf2DiscoEndpointContext* lasso_idwsf2_disco_endpoint_context_new_full(
|
|
\t\tconst gchar *address);''',
|
|
'''
|
|
LassoIdWsf2DiscoEndpointContext*
|
|
lasso_idwsf2_disco_endpoint_context_new_full(const gchar *address)
|
|
{
|
|
\tLassoIdWsf2DiscoEndpointContext *context;
|
|
\tLassoIdWsf2SbfFramework *sbf_framework;
|
|
|
|
\tcontext = lasso_idwsf2_disco_endpoint_context_new();
|
|
|
|
\tcontext->Address = g_list_append(NULL, g_strdup(address));
|
|
\tsbf_framework = lasso_idwsf2_sbf_framework_new();
|
|
\tsbf_framework->version = g_strdup("2.0");
|
|
\tcontext->Framework = g_list_append(NULL, sbf_framework);
|
|
|
|
\treturn context;
|
|
}'''),
|
|
|
|
'disco_service_context': (
|
|
'''LASSO_EXPORT LassoIdWsf2DiscoServiceContext* lasso_idwsf2_disco_service_context_new_full(
|
|
\t\tconst gchar *serviceType, LassoIdWsf2DiscoEndpointContext *endpointContext);''',
|
|
'''
|
|
LassoIdWsf2DiscoServiceContext*
|
|
lasso_idwsf2_disco_service_context_new_full(
|
|
\t\tconst gchar *serviceType, LassoIdWsf2DiscoEndpointContext *endpointContext)
|
|
{
|
|
\tLassoIdWsf2DiscoServiceContext *context;
|
|
|
|
\tcontext = lasso_idwsf2_disco_service_context_new();
|
|
|
|
\tcontext->ServiceType = g_list_append(NULL, g_strdup(serviceType));
|
|
\tcontext->EndpointContext = g_list_append(NULL, g_object_ref(endpointContext));
|
|
|
|
\treturn context;
|
|
}'''),
|
|
|
|
}
|
|
|
|
for d in ('id-wsf-2.0', 'ws', 'swig-id-wsf-2.0', 'swig-ws'):
|
|
if not os.path.exists(d):
|
|
os.mkdir(d)
|
|
|
|
def rep(s):
|
|
return s.group(0)[0] + '_' + s.group(1).lower()
|
|
|
|
|
|
def get_by_name_and_attribute(dom, name, attribute_name, attribute_value):
|
|
elems = dom.getElementsByTagName(name)
|
|
result = []
|
|
for elem in elems:
|
|
if not elem.attributes.has_key(attribute_name):
|
|
continue
|
|
if elem.attributes.get(attribute_name).value == attribute_value:
|
|
result.append(elem)
|
|
|
|
return result
|
|
|
|
|
|
def get_str_classes():
|
|
str_classes = ['ID', 'string', 'anyURI', 'dateTime', 'NCName', 'text-child',
|
|
'NMTOKEN', 'NMTOKENS', 'token', 'normalizedString', 'IDREF', 'QName']
|
|
str_classes += ['xs:'+x for x in str_classes]
|
|
str_classes += ['saml:' + x for x in string_classes] + string_classes[:]
|
|
lu_classes = ['IDType', 'IDReferenceType']
|
|
str_classes += lu_classes + ['lu:'+x for x in lu_classes] + ['util:'+x for x in lu_classes]
|
|
str_classes += ['tns:RelationshipTypeOpenEnum']
|
|
str_classes += ['wsu:AttributedDateTime']
|
|
return str_classes
|
|
|
|
|
|
class LassoClass:
|
|
has_ds_signature = False
|
|
has_custom_ns = False
|
|
node_set_name = None
|
|
|
|
def generate_header(self):
|
|
s = []
|
|
s.append("""/* $Id: %(file_name)s.h,v 1.0 2005/10/14 15:17:55 fpeters Exp $
|
|
*
|
|
* Lasso - A free implementation of the Liberty Alliance specifications.
|
|
*
|
|
* Copyright (C) 2004-2007 Entr'ouvert
|
|
* http://lasso.entrouvert.org
|
|
*
|
|
* Authors: See AUTHORS file in top-level directory.
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation; either version 2 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program; if not, write to the Free Software
|
|
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
|
*/
|
|
|
|
#ifndef __LASSO_%(category_upper)s%(file_name_upper)s_H__
|
|
#define __LASSO_%(category_upper)s%(file_name_upper)s_H__
|
|
|
|
#ifdef __cplusplus
|
|
extern "C" {
|
|
#endif /* __cplusplus */
|
|
""" % self.__dict__)
|
|
includes = {}
|
|
for elem in self.elements:
|
|
if elem[1] in string_classes:
|
|
continue
|
|
includes[elem[1]] = True
|
|
|
|
if self.base_class_name != 'Node':
|
|
if self.prefix == 'samlp2':
|
|
includes['samlp:' + self.base_class_name[6:]] = True
|
|
elif self.prefix == 'saml2':
|
|
includes['saml:' + self.base_class_name[5:]] = True
|
|
else:
|
|
b_pref = self.base_prefix
|
|
if not b_pref:
|
|
b_pref = self.prefix
|
|
|
|
if b_pref in ('lu', 'util'):
|
|
includes['util:' + self.base_class_name[10:]] = True
|
|
elif b_pref == 'ps':
|
|
includes['ps:' + self.base_class_name[8:]] = True
|
|
elif b_pref == 'is':
|
|
includes['is:' + self.base_class_name[8:]] = True
|
|
elif b_pref == 'subs':
|
|
includes['subs:' + self.base_class_name[10:]] = True
|
|
elif b_pref == 'ims':
|
|
includes['ims:' + self.base_class_name[9:]] = True
|
|
elif b_pref == 'dst':
|
|
includes['dst:' + self.base_class_name[9:]] = True
|
|
elif b_pref == 'subsref':
|
|
includes['subsref:' + self.base_class_name[13:]] = True
|
|
elif b_pref == 'dstref':
|
|
includes['dstref:' + self.base_class_name[12:]] = True
|
|
elif b_pref == 'wsa':
|
|
includes['wsa:' + self.base_class_name[6:]] = True
|
|
elif b_pref == 'tns':
|
|
includes['wsa:' + self.base_class_name[6:]] = True
|
|
else:
|
|
print b_pref, self.base_prefix, self.base_class_name
|
|
raise 'XXX'
|
|
|
|
s.append('#include <lasso/xml/xml.h>')
|
|
|
|
for inc in includes.keys():
|
|
if ':' in inc:
|
|
ns, name = inc.split(':')[-2:]
|
|
if ns == 'xs':
|
|
continue
|
|
if ns == 'lu':
|
|
ns = 'util'
|
|
if ns == 'tns':
|
|
ns = 'wsa'
|
|
try:
|
|
if ns.startswith('ws') and not self.prefix.startswith('ws'):
|
|
s.append('#include <lasso/xml/ws/%s.h>' % classes[ns][name].file_name)
|
|
elif ns == 'samlp':
|
|
samlp_header = 'samlp2_' + re.sub(r'[a-z]([A-Z])', rep, name).lower()
|
|
s.append('#include <lasso/xml/saml-2.0/%s.h>' % samlp_header)
|
|
else:
|
|
s.append('#include "%s.h"' % classes[ns][name].file_name)
|
|
except KeyError:
|
|
print >> sys.stderr, 'W: missing', ns, name
|
|
if self.name == 'DataResponseBase':
|
|
print classes[ns].keys()
|
|
raise 'toot'
|
|
pass
|
|
else:
|
|
try:
|
|
s.append('#include "%s.h"' % classes[self.prefix][inc].file_name)
|
|
except KeyError:
|
|
pass
|
|
|
|
# extra headers
|
|
if self.name == 'ServiceContext':
|
|
s.append('#include "disco_endpoint_context.h"')
|
|
|
|
if self.name in ('Advice', 'Evidence'):
|
|
s.append("""
|
|
#ifndef __LASSO_SAML2_ASSERTION_H__
|
|
/* to avoid circular inclusion of saml2_assertion.h */
|
|
typedef struct _LassoSaml2Assertion LassoSaml2Assertion;
|
|
#endif
|
|
""")
|
|
|
|
if len(self.prefix_cap) + len(self.file_name_upper) < 33:
|
|
s.append("""\n#define LASSO_TYPE_%(category_upper)s%(file_name_upper)s (lasso_%(category)s%(file_name)s_get_type())""" % self.__dict__)
|
|
else:
|
|
s.append("""\n#define LASSO_TYPE_%(category_upper)s%(file_name_upper)s \\\n\t(lasso_%(category)s%(file_name)s_get_type())""" % self.__dict__)
|
|
|
|
s.append("""#define LASSO_%(category_upper)s%(file_name_upper)s(obj) \\
|
|
\t(G_TYPE_CHECK_INSTANCE_CAST((obj), \\
|
|
\t\tLASSO_TYPE_%(category_upper)s%(file_name_upper)s, \\
|
|
\t\tLasso%(prefix_cap)s%(name)s))
|
|
#define LASSO_%(category_upper)s%(file_name_upper)s_CLASS(klass) \\
|
|
\t(G_TYPE_CHECK_CLASS_CAST((klass), \\
|
|
\t\tLASSO_TYPE_%(category_upper)s%(file_name_upper)s, \\
|
|
\t\tLasso%(prefix_cap)s%(name)sClass))
|
|
#define LASSO_IS_%(category_upper)s%(file_name_upper)s(obj) \\
|
|
\t(G_TYPE_CHECK_INSTANCE_TYPE((obj), \\
|
|
\t\tLASSO_TYPE_%(category_upper)s%(file_name_upper)s))
|
|
#define LASSO_IS_%(category_upper)s%(file_name_upper)s_CLASS(klass) \\
|
|
\t(G_TYPE_CHECK_CLASS_TYPE ((klass), \\
|
|
\t\tLASSO_TYPE_%(category_upper)s%(file_name_upper)s))
|
|
#define LASSO_%(category_upper)s%(file_name_upper)s_GET_CLASS(o) \\
|
|
\t(G_TYPE_INSTANCE_GET_CLASS ((o), \\
|
|
\t\tLASSO_TYPE_%(category_upper)s%(file_name_upper)s, \\
|
|
\t\tLasso%(prefix_cap)s%(name)sClass))
|
|
""" % self.__dict__)
|
|
|
|
if len(self.prefix_cap) + len(self.name) > 30:
|
|
s.append("""
|
|
typedef struct _Lasso%(prefix_cap)s%(name)s \\
|
|
\tLasso%(prefix_cap)s%(name)s;
|
|
typedef struct _Lasso%(prefix_cap)s%(name)sClass \\
|
|
\tLasso%(prefix_cap)s%(name)sClass;
|
|
""" % self.__dict__)
|
|
else:
|
|
s.append("""
|
|
typedef struct _Lasso%(prefix_cap)s%(name)s Lasso%(prefix_cap)s%(name)s;
|
|
typedef struct _Lasso%(prefix_cap)s%(name)sClass Lasso%(prefix_cap)s%(name)sClass;
|
|
""" % self.__dict__)
|
|
|
|
|
|
|
|
s.append("""
|
|
struct _Lasso%(prefix_cap)s%(name)s {""" % self.__dict__)
|
|
s.append("\tLasso%s parent;\n" % self.base_class_name)
|
|
|
|
s.append('\t/*< public >*/')
|
|
if self.elements:
|
|
s.append('\t/* elements */')
|
|
for elem in self.elements:
|
|
name, type = elem[:2]
|
|
if type in get_str_classes():
|
|
type = 'char'
|
|
name = '*'+name
|
|
elif type in ['text-child-int']:
|
|
type = 'int'
|
|
elif type == 'GList':
|
|
name = '*'+name
|
|
else:
|
|
type = ref_to_class_name(type)
|
|
name = '*'+name
|
|
s.append('\t%s %s;' % (type, name))
|
|
|
|
if type == 'GList':
|
|
if elem[2] == 'xmlNode':
|
|
s[-1] = s[-1] + ' /* of xmlNode */'
|
|
else:
|
|
t = ref_to_class_name(elem[2])
|
|
if not 'XXX' in t:
|
|
s[-1] = s[-1] + ' /* of %s */' % t
|
|
|
|
if self.attributes:
|
|
s.append('\t/* attributes */')
|
|
for elem in self.attributes:
|
|
name, type = elem[:2]
|
|
if type.startswith('xs:'):
|
|
type = type[3:]
|
|
if name in ('signed', ): # reserved keywords
|
|
name = name + '_'
|
|
if type == 'boolean':
|
|
type = 'gboolean'
|
|
elif type in ('unsignedShort', 'integer', 'nonNegativeInteger'):
|
|
type = 'int'
|
|
elif type == 'any':
|
|
type = 'GHashTable'
|
|
name = '*attributes'
|
|
else:
|
|
type = 'char'
|
|
name = '*'+name
|
|
s.append('\t%s %s;' % (type, name))
|
|
|
|
if self.has_ds_signature:
|
|
s.append('\t/*< private >*/')
|
|
s.append("""\t/* ds:Signature stuffs */
|
|
\tLassoSignatureType sign_type;
|
|
\tLassoSignatureMethod sign_method;
|
|
\tchar *private_key_file;
|
|
\tchar *certificate_file;
|
|
""")
|
|
if self.has_custom_ns:
|
|
s.append('''
|
|
\t/*< private >*/
|
|
\tchar *prefixServiceType;
|
|
\tchar *hrefServiceType;''')
|
|
|
|
s.append('};\n')
|
|
|
|
s.append("""
|
|
struct _Lasso%(prefix_cap)s%(name)sClass {
|
|
\tLasso%(base_class_name)sClass parent;
|
|
};
|
|
|
|
LASSO_EXPORT GType lasso_%(category)s%(file_name)s_get_type(void);
|
|
LASSO_EXPORT Lasso%(prefix_cap)s%(name)s* lasso_%(category)s%(file_name)s_new(void);
|
|
""" % self.__dict__)
|
|
|
|
if ('content', 'text-child') in self.elements:
|
|
s.append('LASSO_EXPORT Lasso%(prefix_cap)s%(name)s* lasso_%(category)s%(file_name)s_new_with_string(const char *content);' % self.__dict__)
|
|
|
|
if ('text-child-int',) in self.elements:
|
|
s.append('LASSO_EXPORT Lasso%(prefix_cap)s%(name)s* lasso_%(category)s%(file_name)s_new_with_int(int content);' % self.__dict__)
|
|
|
|
if full_constructors.has_key(self.file_name):
|
|
s.append(full_constructors.get(self.file_name)[0])
|
|
|
|
s.append("""
|
|
|
|
#ifdef __cplusplus
|
|
}
|
|
#endif /* __cplusplus */
|
|
|
|
#endif /* __LASSO_%(category_upper)s%(file_name_upper)s_H__ */
|
|
""" % self.__dict__)
|
|
|
|
return '\n'.join(s)
|
|
|
|
def generate_source(self):
|
|
s = []
|
|
s.append("""/* $Id: %(file_name)s.c,v 1.0 2005/10/14 15:17:55 fpeters Exp $
|
|
*
|
|
* Lasso - A free implementation of the Liberty Alliance specifications.
|
|
*
|
|
* Copyright (C) 2004-2007 Entr'ouvert
|
|
* http://lasso.entrouvert.org
|
|
*
|
|
* Authors: See AUTHORS file in top-level directory.
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation; either version 2 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program; if not, write to the Free Software
|
|
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
|
*/
|
|
""" % self.__dict__)
|
|
|
|
if self.has_ds_signature:
|
|
s.append("""
|
|
#include <xmlsec/xmldsig.h>
|
|
#include <xmlsec/templates.h>
|
|
""")
|
|
|
|
s.append('#include "%s.h"' % self.file_name)
|
|
|
|
# extra headers
|
|
if self.name == 'EndpointContext':
|
|
s.append('#include "sbf_framework.h"');
|
|
elif self.name == 'SvcMDRegister':
|
|
s.append('#include "disco_svc_metadata.h"')
|
|
elif self.name == 'SvcMetadata':
|
|
s.append('#include "disco_endpoint_context.h"')
|
|
s.append('#include "disco_service_context.h"')
|
|
|
|
|
|
s.append("""
|
|
/*
|
|
* Schema fragment (%s):
|
|
*
|
|
%s
|
|
*/""" % (self.schema_filename, self.schema_fragment))
|
|
|
|
s.append("""
|
|
/*****************************************************************************/
|
|
/* private methods */
|
|
/*****************************************************************************/
|
|
|
|
""")
|
|
|
|
s.append("static struct XmlSnippet schema_snippets[] = {")
|
|
|
|
for elem in self.elements:
|
|
name, type = elem[:2]
|
|
if type == 'text-child':
|
|
snippet_type = 'SNIPPET_TEXT_CHILD'
|
|
elif type == 'text-child-int':
|
|
snippet_type = 'SNIPPET_TEXT_CHILD | SNIPPET_INTEGER'
|
|
elif type in get_str_classes():
|
|
snippet_type = 'SNIPPET_CONTENT'
|
|
elif type == 'GList':
|
|
if elem[2] == 'xmlNode':
|
|
snippet_type = 'SNIPPET_LIST_XMLNODES'
|
|
elif elem[2] in get_str_classes():
|
|
snippet_type = 'SNIPPET_LIST_CONTENT'
|
|
else:
|
|
snippet_type = 'SNIPPET_LIST_NODES'
|
|
else:
|
|
snippet_type = 'SNIPPET_NODE'
|
|
if name == 'any':
|
|
snippet_type += ' | SNIPPET_ANY'
|
|
|
|
varname = name
|
|
|
|
if type in get_str_classes():
|
|
auto_detect = True
|
|
else:
|
|
if type == 'GList':
|
|
type = elem[2]
|
|
if type == 'xmlNode':
|
|
name = ''
|
|
auto_detect = True
|
|
else:
|
|
type = ref_to_class_name(type)
|
|
if type == 'LassoNode':
|
|
name = ''
|
|
snippet_type += ' | SNIPPET_ANY'
|
|
auto_detect = True
|
|
elif classes.has_key(name):
|
|
auto_detect = True
|
|
else:
|
|
if 'XXX' in type or type.endswith('Abstract') or name == 'any':
|
|
auto_detect = True
|
|
else:
|
|
auto_detect = False
|
|
|
|
if auto_detect:
|
|
s.append('\t{ "%s", %s,\n\t\tG_STRUCT_OFFSET(Lasso%s%s, %s) },' % (
|
|
name, snippet_type, self.prefix_cap, self.name, varname))
|
|
else:
|
|
s.append('\t{ "%s", %s,\n\t\tG_STRUCT_OFFSET(Lasso%s%s, %s),\n\t\t"%s" },' % (
|
|
name, snippet_type, self.prefix_cap, self.name, name, type))
|
|
|
|
id_name = 'XXX'
|
|
for elem in self.attributes:
|
|
name, type = elem[:2]
|
|
if type.startswith('xs:'):
|
|
type = type[3:]
|
|
if type == 'ID':
|
|
id_name = name
|
|
if type in get_str_classes():
|
|
snippet_type = 'SNIPPET_ATTRIBUTE'
|
|
elif type in ('unsignedShort', 'nonNegativeInteger', 'integer'):
|
|
snippet_type = 'SNIPPET_ATTRIBUTE | SNIPPET_INTEGER'
|
|
elif type == 'boolean':
|
|
snippet_type = 'SNIPPET_ATTRIBUTE | SNIPPET_BOOLEAN'
|
|
elif type == 'any':
|
|
snippet_type = 'SNIPPET_ATTRIBUTE | SNIPPET_ANY'
|
|
else:
|
|
raise 'unknown type: %r' % type
|
|
if len(elem) == 3:
|
|
optional = elem[2]
|
|
if optional:
|
|
if type == 'nonNegativeInteger':
|
|
snippet_type += ' | SNIPPET_OPTIONAL_NEG'
|
|
else:
|
|
snippet_type += ' | SNIPPET_OPTIONAL'
|
|
varname = name
|
|
if type == 'any':
|
|
varname = 'attributes'
|
|
if varname in ('signed', ): # reserved keywords
|
|
varname = varname + '_'
|
|
s.append('\t{ "%s", %s,\n\t\tG_STRUCT_OFFSET(Lasso%s%s, %s) },' % (
|
|
name, snippet_type, self.prefix_cap, self.name, varname))
|
|
|
|
if self.has_ds_signature:
|
|
if id_name == 'XXX':
|
|
s.append('\t{ "Signature", SNIPPET_SIGNATURE },')
|
|
else:
|
|
s.append('\t{ "Signature", SNIPPET_SIGNATURE,\n\t\tG_STRUCT_OFFSET(Lasso%s%s, %s) },' % (
|
|
self.prefix_cap, self.name, id_name))
|
|
|
|
s.append("""
|
|
\t/* hidden fields; used in lasso dumps */
|
|
\t{ "SignType", SNIPPET_ATTRIBUTE | SNIPPET_INTEGER | SNIPPET_LASSO_DUMP,
|
|
\t\tG_STRUCT_OFFSET(Lasso%(prefix_cap)s%(name)s, sign_type) },
|
|
\t{ "SignMethod", SNIPPET_ATTRIBUTE | SNIPPET_INTEGER | SNIPPET_LASSO_DUMP,
|
|
\t\tG_STRUCT_OFFSET(Lasso%(prefix_cap)s%(name)s, sign_method) },
|
|
\t{ "PrivateKeyFile", SNIPPET_CONTENT | SNIPPET_LASSO_DUMP,
|
|
\t\tG_STRUCT_OFFSET(Lasso%(prefix_cap)s%(name)s, private_key_file) },
|
|
\t{ "CertificateFile", SNIPPET_CONTENT | SNIPPET_LASSO_DUMP,
|
|
\t\tG_STRUCT_OFFSET(Lasso%(prefix_cap)s%(name)s, certificate_file) },
|
|
""" % self.__dict__)
|
|
|
|
s.append("\t{NULL, 0, 0}\n};")
|
|
|
|
s.append("""
|
|
static LassoNodeClass *parent_class = NULL;
|
|
""")
|
|
|
|
if self.has_custom_ns:
|
|
s.append('''
|
|
static xmlNode*
|
|
get_xmlNode(LassoNode *node, gboolean lasso_dump)
|
|
{
|
|
xmlNode *xmlnode;
|
|
|
|
xmlnode = parent_class->get_xmlNode(node, lasso_dump);
|
|
xml_insure_namespace(xmlnode, NULL, TRUE,
|
|
LASSO_%(category_upper)s%(file_name_upper)s(node)->hrefServiceType,
|
|
LASSO_%(category_upper)s%(file_name_upper)s(node)->prefixServiceType);
|
|
|
|
return xmlnode;
|
|
}
|
|
|
|
static int
|
|
init_from_xml(LassoNode *node, xmlNode *xmlnode)
|
|
{
|
|
Lasso%(prefix_cap)s%(name)s *object = LASSO_%(category_upper)s%(file_name_upper)s(node);
|
|
int res;
|
|
|
|
res = parent_class->init_from_xml(node, xmlnode);
|
|
if (res != 0) {
|
|
return res;
|
|
}
|
|
|
|
object->hrefServiceType = g_strdup((char*)xmlnode->ns->href);
|
|
object->prefixServiceType = lasso_get_prefix_for_idwsf2_dst_service_href(
|
|
object->hrefServiceType);
|
|
if (object->prefixServiceType == NULL) {
|
|
/* XXX: what to do here ? */
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
''' % self.__dict__)
|
|
|
|
has_build_query = False
|
|
if self.base_class_name == 'Samlp2RequestAbstract' or ( # two levels deep
|
|
classes.has_key(self.base_class_name) and \
|
|
classes[self.base_class_name].base_class_name == 'Samlp2RequestAbstract'):
|
|
has_build_query = True
|
|
qs_name = 'SAMLRequest'
|
|
elif self.prefix == 'samlp2' and self.name.endswith('Response'):
|
|
has_build_query = True
|
|
qs_name = 'SAMLResponse'
|
|
elif self.base_class_name == 'Samlp2StatusResponse':
|
|
has_build_query = True
|
|
qs_name = 'SAMLResponse'
|
|
|
|
if self.name in ('ArtifactResolve', 'ArtifactResponse'):
|
|
has_build_query = False
|
|
|
|
if has_build_query:
|
|
s.append("""
|
|
static gchar*
|
|
build_query(LassoNode *node)
|
|
{
|
|
\tchar *ret, *deflated_message;
|
|
|
|
\tdeflated_message = lasso_node_build_deflated_query(node);
|
|
\tret = g_strdup_printf("%s=%%s", deflated_message);
|
|
\t/* XXX: must support RelayState (which profiles?) */
|
|
\tg_free(deflated_message);
|
|
\treturn ret;
|
|
}
|
|
""" % qs_name)
|
|
has_init_from_query = False
|
|
if has_build_query:
|
|
has_init_from_query = True
|
|
s.append("""
|
|
static gboolean
|
|
init_from_query(LassoNode *node, char **query_fields)
|
|
{
|
|
\tgboolean rc;
|
|
\tchar *relay_state = NULL;
|
|
\trc = lasso_node_init_from_saml2_query_fields(node, query_fields, &relay_state);
|
|
\tif (rc && relay_state != NULL) {
|
|
\t\t/* XXX: support RelayState? */
|
|
\t}
|
|
\treturn rc;
|
|
}
|
|
""")
|
|
|
|
has_get_xml_node = False
|
|
if self.has_ds_signature and id_name != 'XXX':
|
|
# XXX: no id name for InteractionStatement -> no signature possible ?
|
|
has_get_xml_node = True
|
|
self.id_name = id_name
|
|
s.append("""
|
|
|
|
static xmlNode*
|
|
get_xmlNode(LassoNode *node, gboolean lasso_dump)
|
|
{
|
|
\tLasso%(prefix_cap)s%(name)s *request = LASSO_%(category_upper)s%(file_name_upper)s(node);
|
|
\txmlNode *xmlnode;
|
|
\tint rc;
|
|
\t
|
|
\txmlnode = parent_class->get_xmlNode(node, lasso_dump);
|
|
|
|
\tif (lasso_dump == FALSE && request->sign_type) {
|
|
\t\trc = lasso_sign_node(xmlnode, "%(id_name)s", request->%(id_name)s,
|
|
\t\t\t\trequest->private_key_file, request->certificate_file);
|
|
\t\t/* signature may have failed; what to do ? */
|
|
\t}
|
|
|
|
\treturn xmlnode;
|
|
}
|
|
""" % self.__dict__)
|
|
|
|
|
|
s.append("""
|
|
/*****************************************************************************/
|
|
/* instance and class init functions */
|
|
/*****************************************************************************/
|
|
|
|
static void
|
|
instance_init(Lasso%s%s *node)
|
|
{""" % (self.prefix_cap, self.name))
|
|
|
|
for elem in self.elements + self.attributes:
|
|
name, type = elem[:2]
|
|
if name in ('signed', ): # reserved keywords
|
|
name = name + '_'
|
|
if type.startswith('xs:'):
|
|
type = type[3:]
|
|
|
|
if type in ('unsignedShort', 'integer', 'text-child-int'):
|
|
s.append('\tnode->%s = 0;' % name)
|
|
elif type == 'nonNegativeInteger':
|
|
s.append('\tnode->%s = -1;' % name)
|
|
elif type == 'boolean':
|
|
s.append('\tnode->%s = FALSE;' % name)
|
|
elif type == 'any' and elem in self.attributes:
|
|
s.append('''\tnode->attributes = g_hash_table_new_full(
|
|
\t\tg_str_hash, g_str_equal, g_free, g_free);''')
|
|
else:
|
|
s.append('\tnode->%s = NULL;' % name)
|
|
|
|
if self.has_ds_signature:
|
|
s.append('\tnode->sign_type = LASSO_SIGNATURE_TYPE_NONE;')
|
|
|
|
if self.has_custom_ns:
|
|
s.append('\tnode->prefixServiceType = NULL;')
|
|
s.append('\tnode->hrefServiceType = NULL;')
|
|
|
|
s.append("""}
|
|
|
|
static void
|
|
class_init(Lasso%s%sClass *klass)
|
|
{
|
|
\tLassoNodeClass *nclass = LASSO_NODE_CLASS(klass);
|
|
|
|
\tparent_class = g_type_class_peek_parent(klass);""" % (self.prefix_cap, self.name))
|
|
if self.has_custom_ns:
|
|
s.append('\tnclass->get_xmlNode = get_xmlNode;')
|
|
s.append('\tnclass->init_from_xml = init_from_xml;')
|
|
if has_build_query:
|
|
s.append('\tnclass->build_query = build_query;')
|
|
if has_init_from_query:
|
|
s.append('\tnclass->init_from_query = init_from_query;')
|
|
if has_get_xml_node:
|
|
s.append('\tnclass->get_xmlNode = get_xmlNode;')
|
|
if self.prefix == 'saml2':
|
|
string_constant = 'SAML2_ASSERTION'
|
|
elif self.prefix == 'samlp2':
|
|
string_constant = 'SAML2_PROTOCOL'
|
|
elif self.prefix == 'disco':
|
|
string_constant = 'IDWSF2_DISCO'
|
|
elif self.prefix == 'util':
|
|
string_constant = 'IDWSF2_UTIL'
|
|
elif self.prefix == 'dst':
|
|
string_constant = 'IDWSF2_DST'
|
|
elif self.prefix == 'dstref':
|
|
string_constant = 'IDWSF2_DSTREF'
|
|
elif self.prefix == 'sec':
|
|
string_constant = 'IDWSF2_SEC'
|
|
elif self.prefix == 'ims':
|
|
string_constant = 'IDWSF2_IMS'
|
|
elif self.prefix == 'subs':
|
|
string_constant = 'IDWSF2_SUBS'
|
|
elif self.prefix == 'subsref':
|
|
string_constant = 'IDWSF2_SUBSREF'
|
|
elif self.prefix == 'ps':
|
|
string_constant = 'IDWSF2_PS'
|
|
elif self.prefix == 'is':
|
|
string_constant = 'IDWSF2_IS'
|
|
elif self.prefix == 'sbf':
|
|
string_constant = 'IDWSF2_SBF'
|
|
elif self.prefix == 'sb2':
|
|
string_constant = 'IDWSF2_SB2'
|
|
elif self.prefix == 'wsa':
|
|
string_constant = 'WSA'
|
|
elif self.prefix == 'wsu':
|
|
string_constant = 'WSUTIL1'
|
|
elif self.prefix == 'wsse':
|
|
string_constant = 'WSSE1'
|
|
else:
|
|
raise 'missing constant for %s' % self.prefix
|
|
|
|
if not self.node_set_name:
|
|
self.node_set_name = self.name
|
|
s.append("""\tnclass->node_data = g_new0(LassoNodeClassData, 1);
|
|
\tlasso_node_class_set_nodename(nclass, "%s");
|
|
\tlasso_node_class_set_ns(nclass, LASSO_%s_HREF, LASSO_%s_PREFIX);
|
|
\tlasso_node_class_add_snippets(nclass, schema_snippets);""" % (
|
|
self.node_set_name, string_constant, string_constant))
|
|
|
|
if self.has_ds_signature:
|
|
s.append("""
|
|
\tnclass->node_data->sign_type_offset = G_STRUCT_OFFSET(
|
|
\t\t\tLasso%(prefix_cap)s%(name)s, sign_type);
|
|
\tnclass->node_data->sign_method_offset = G_STRUCT_OFFSET(
|
|
\t\t\tLasso%(prefix_cap)s%(name)s, sign_method);""" % self.__dict__)
|
|
|
|
s.append("""}
|
|
|
|
GType
|
|
lasso_%(category)s%(file_name)s_get_type()
|
|
{
|
|
\tstatic GType this_type = 0;
|
|
|
|
\tif (!this_type) {
|
|
\t\tstatic const GTypeInfo this_info = {
|
|
\t\t\tsizeof (Lasso%(prefix_cap)s%(name)sClass),
|
|
\t\t\tNULL,
|
|
\t\t\tNULL,
|
|
\t\t\t(GClassInitFunc) class_init,
|
|
\t\t\tNULL,
|
|
\t\t\tNULL,
|
|
\t\t\tsizeof(Lasso%(prefix_cap)s%(name)s),
|
|
\t\t\t0,
|
|
\t\t\t(GInstanceInitFunc) instance_init,
|
|
\t\t};
|
|
|
|
\t\tthis_type = g_type_register_static(%(base_class_type)s,
|
|
\t\t\t\t"Lasso%(prefix_cap)s%(name)s", &this_info, 0);
|
|
\t}
|
|
\treturn this_type;
|
|
}
|
|
|
|
/**
|
|
* lasso_%(category)s%(file_name)s_new:
|
|
*
|
|
* Creates a new #Lasso%(prefix_cap)s%(name)s object.
|
|
*
|
|
* Return value: a newly created #Lasso%(prefix_cap)s%(name)s object
|
|
**/
|
|
Lasso%(prefix_cap)s%(name)s*
|
|
lasso_%(category)s%(file_name)s_new()
|
|
{
|
|
\treturn g_object_new(LASSO_TYPE_%(category_upper)s%(file_name_upper)s, NULL);
|
|
}
|
|
""" % self.__dict__)
|
|
|
|
if ('content', 'text-child') in self.elements:
|
|
s.append("""
|
|
/**
|
|
* lasso_%(category)s%(file_name)s_new_with_string:
|
|
* @content:
|
|
*
|
|
* Creates a new #Lasso%(prefix_cap)s%(name)s object and initializes it
|
|
* with @content.
|
|
*
|
|
* Return value: a newly created #Lasso%(prefix_cap)s%(name)s object
|
|
**/
|
|
Lasso%(prefix_cap)s%(name)s*
|
|
lasso_%(category)s%(file_name)s_new_with_string(const char *content)
|
|
{
|
|
\tLasso%(prefix_cap)s%(name)s *object;
|
|
\tobject = g_object_new(LASSO_TYPE_%(category_upper)s%(file_name_upper)s, NULL);
|
|
\tobject->content = g_strdup(content);
|
|
\treturn object;
|
|
}
|
|
""" % self.__dict__)
|
|
|
|
|
|
if ('text-child-int') in self.elements:
|
|
s.append("""
|
|
/**
|
|
* lasso_%(category)s%(file_name)s_new_with_int:
|
|
* @content:
|
|
*
|
|
* Creates a new #Lasso%(prefix_cap)s%(name)s object and initializes it
|
|
* with @content.
|
|
*
|
|
* Return value: a newly created #Lasso%(prefix_cap)s%(name)s object
|
|
**/
|
|
Lasso%(prefix_cap)s%(name)s*
|
|
lasso_%(category)s%(file_name)s_new_with_int(int content)
|
|
{
|
|
\tLasso%(prefix_cap)s%(name)s *object;
|
|
\tobject = g_object_new(LASSO_TYPE_%(category_upper)s%(file_name_upper)s, NULL);
|
|
\tobject->content = content;
|
|
\treturn object;
|
|
}
|
|
""" % self.__dict__)
|
|
|
|
if full_constructors.has_key(self.file_name):
|
|
s.append(full_constructors.get(self.file_name)[1] + '\n')
|
|
|
|
return '\n'.join(s)
|
|
|
|
|
|
def generate_swig(self):
|
|
s = []
|
|
s.append("""/* $Id: %(file_name)s.i,v 1.0 2005/10/14 15:17:55 fpeters Exp $
|
|
*
|
|
* Lasso - A free implementation of the Liberty Alliance specifications.
|
|
*
|
|
* Copyright (C) 2004-2007 Entr'ouvert
|
|
* http://lasso.entrouvert.org
|
|
*
|
|
* Authors: See AUTHORS file in top-level directory.
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation; either version 2 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program; if not, write to the Free Software
|
|
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
|
*/
|
|
|
|
#ifndef SWIGPHP4
|
|
%%rename(%(prefix_cap)s%(name)s) Lasso%(prefix_cap)s%(name)s;
|
|
#endif
|
|
typedef struct {""" % self.__dict__)
|
|
|
|
any_attribute = False
|
|
for elem in self.elements + self.attributes:
|
|
oname, type = elem[:2]
|
|
if oname in ('signed', ): # reserved keywords
|
|
oname = oname + '_'
|
|
if type.startswith('xs:'):
|
|
type = type[3:]
|
|
if type == 'boolean':
|
|
type = 'gboolean'
|
|
name = oname
|
|
elif type in ('unsignedShort', 'nonNegativeInteger', 'integer'):
|
|
type = 'int'
|
|
name = oname
|
|
elif type in get_str_classes():
|
|
type = 'char'
|
|
name = '*'+oname
|
|
elif type == 'any':
|
|
any_attribute = True
|
|
name = None # skip it here
|
|
elif elem in self.attributes:
|
|
# fallback for other attributes
|
|
type = 'char'
|
|
name = '*'+oname
|
|
else:
|
|
name = None
|
|
if 'XXX' in ref_to_class_name(type):
|
|
continue
|
|
if name:
|
|
if oname[0] in string.uppercase:
|
|
lname = oname[0].lower() + oname[1:]
|
|
s.append("""#ifndef SWIGPHP4
|
|
\t%%rename(%s) %s;
|
|
#endif""" % (lname, oname))
|
|
s.append('\t%s %s;' % (type, name))
|
|
|
|
s.append('} Lasso%(prefix_cap)s%(name)s;' % self.__dict__)
|
|
s.append('%%extend Lasso%(prefix_cap)s%(name)s {\n' % self.__dict__)
|
|
|
|
swig_elems = []
|
|
|
|
for elem in self.elements + self.attributes:
|
|
name, type = elem[:2]
|
|
if type.startswith('xs:'):
|
|
type = type[3:]
|
|
oname = name
|
|
if type in ['GList', 'boolean', 'unsignedShort', 'nonNegativeInteger',
|
|
'integer'] + get_str_classes():
|
|
continue
|
|
else:
|
|
type = ref_to_class_name(type)
|
|
if 'XXX' in type:
|
|
continue
|
|
|
|
name = '*'+name
|
|
|
|
if oname[0] in string.uppercase:
|
|
lname = oname[0].lower() + oname[1:]
|
|
s.append("""#ifndef SWIGPHP4
|
|
\t%%rename(%s) %s;
|
|
#endif""" % (lname, oname))
|
|
swig_elems.append((None, type, oname))
|
|
if type.startswith('Lasso'):
|
|
s.append('\t%%newobject %s_get;' % name)
|
|
s.append('\t%s %s;\n' % (type, name))
|
|
|
|
base_class_name = self.base_class_name
|
|
while base_class_name:
|
|
base_class = classes.get(base_class_name.replace('Saml2', '').replace('Samlp2', ''))
|
|
if not base_class:
|
|
break
|
|
s.append('\t/* inherited from %s */' % base_class_name)
|
|
|
|
for elem in base_class.elements + base_class.attributes:
|
|
name, type = elem[:2]
|
|
if type.startswith('xs:'):
|
|
type = type[3:]
|
|
oname = name
|
|
if type == 'boolean':
|
|
type = 'gboolean'
|
|
elif type in ('unsignedShort', 'nonNegativeInteger', 'integer'):
|
|
type = 'int'
|
|
elif type in get_str_classes():
|
|
type = 'char'
|
|
name = '*'+name
|
|
elif type == 'GList':
|
|
name = None
|
|
else:
|
|
type = ref_to_class_name(type)
|
|
name = '*'+name
|
|
if not name:
|
|
continue
|
|
if oname[0] in string.uppercase:
|
|
lname = oname[0].lower() + oname[1:]
|
|
s.append("""#ifndef SWIGPHP4
|
|
\t%%rename(%s) %s;
|
|
#endif""" % (lname, name))
|
|
|
|
swig_elems.append((base_class, type, oname))
|
|
if type.startswith('Lasso'):
|
|
s.append('\t%%newobject %s_get;' % name)
|
|
s.append('\t%s %s;' % (type, name))
|
|
if type.startswith('Lasso'):
|
|
s.append('')
|
|
|
|
base_class_name = base_class.base_class_name
|
|
|
|
if any_attribute:
|
|
s.append("""\
|
|
\t/* any attribute */
|
|
\t%%immutable attributes;
|
|
\t%%newobject attributes_get;
|
|
\tLassoStringDict *attributes;
|
|
""" % self.__dict__)
|
|
|
|
s.append("""\
|
|
\t/* Constructor, Destructor & Static Methods */
|
|
\tLasso%(prefix_cap)s%(name)s();
|
|
\t~Lasso%(prefix_cap)s%(name)s();
|
|
|
|
\t/* Method inherited from LassoNode */
|
|
\t%%newobject dump;
|
|
\tchar* dump();
|
|
}""" % self.__dict__)
|
|
|
|
s.append("""
|
|
%{
|
|
""")
|
|
if swig_elems:
|
|
base_class = swig_elems[0][0]
|
|
if base_class is not self:
|
|
base_class = None
|
|
|
|
for elem in swig_elems:
|
|
bclass, type, name = elem[:3]
|
|
if bclass != base_class:
|
|
s.append('/* inherited from %s */\n' % bclass.name)
|
|
base_class = bclass
|
|
|
|
s.append('/* %s */' % name)
|
|
|
|
if bclass is None:
|
|
if type.startswith('Lasso'):
|
|
s.append("""
|
|
#define Lasso%(prefix_cap)s%(name)s_get_%(elem_name)s(self) get_node((self)->%(elem_name)s)
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_get(self) get_node((self)->%(elem_name)s)
|
|
#define Lasso%(prefix_cap)s%(name)s_set_%(elem_name)s(self,value) set_node((gpointer*)&(self)->%(elem_name)s, (value))
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_set(self,value) set_node((gpointer*)&(self)->%(elem_name)s, (value))
|
|
""" % {
|
|
'prefix_cap': self.prefix_cap,
|
|
'name': self.name,
|
|
'elem_name': name,
|
|
})
|
|
else:
|
|
s.append("""
|
|
#define Lasso%(prefix_cap)s%(name)s_get_%(elem_name)s(self) self->%(elem_name)s
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_get(self) self->%(elem_name)s""" % {
|
|
'prefix_cap': self.prefix_cap,
|
|
'name': self.name,
|
|
'elem_name': name,
|
|
})
|
|
if type in ('boolean', 'unsignedShort'):
|
|
s.append("""
|
|
#define Lasso%(prefix_cap)s%(name)s_set_%(elem_name)s(self,value) (self)->%(elem_name)s = (value)
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_set(self,value) (self)->%(elem_name)s = (value)""" % {
|
|
'prefix_cap': self.prefix_cap,
|
|
'name': self.name,
|
|
'elem_name': name,
|
|
})
|
|
else: # string
|
|
s.append("""
|
|
#define Lasso%(prefix_cap)s%(name)s_set_%(elem_name)s(self,value) set_string(&(self)->%(elem_name)s, (value))
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_set(self,value) set_string(&(self)->%(elem_name)s, (value))""" % {
|
|
'prefix_cap': self.prefix_cap,
|
|
'name': self.name,
|
|
'elem_name': name,
|
|
})
|
|
else:
|
|
parent_upper = bclass.file_name_upper
|
|
if self.prefix.startswith('ws'):
|
|
parent_upper = 'WS_' + bclass.file_name_upper
|
|
else:
|
|
parent_upper = 'IDWSF2_' + bclass.file_name_upper
|
|
if type.startswith('Lasso'):
|
|
s.append("""
|
|
#define Lasso%(prefix_cap)s%(name)s_get_%(elem_name)s(self) get_node(LASSO_%(parent_upper)s(self)->%(elem_name)s)
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_get(self) get_node(LASSO_%(parent_upper)s(self)->%(elem_name)s)
|
|
#define Lasso%(prefix_cap)s%(name)s_set_%(elem_name)s(self,value) set_node((gpointer*)&LASSO_%(parent_upper)s(self)->%(elem_name)s, (value))
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_set(self,value) set_node((gpointer*)&LASSO_%(parent_upper)s(self)->%(elem_name)s, (value))
|
|
""" % {
|
|
'prefix_cap': self.prefix_cap,
|
|
'name': self.name,
|
|
'elem_name': name,
|
|
'parent_upper': parent_upper
|
|
})
|
|
else:
|
|
s.append("""
|
|
#define Lasso%(prefix_cap)s%(name)s_get_%(elem_name)s(self) LASSO_%(parent_upper)s(self)->%(elem_name)s
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_get(self) LASSO_%(parent_upper)s(self)->%(elem_name)s""" % {
|
|
'prefix_cap': self.prefix_cap,
|
|
'name': self.name,
|
|
'elem_name': name,
|
|
'parent_upper': parent_upper
|
|
})
|
|
if type in ('boolean', 'unsignedShort', 'nonNegativeInteger', 'integer'):
|
|
s.append("""
|
|
#define Lasso%(prefix_cap)s%(name)s_set_%(elem_name)s(self,value) LASSO_%(parent_upper)s(self)->%(elem_name)s = (value)
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_set(self,value) LASSO_%(parent_upper)s(self)->%(elem_name)s = (value)""" % {
|
|
'prefix_cap': self.prefix_cap,
|
|
'name': self.name,
|
|
'elem_name': name,
|
|
'parent_upper': parent_upper
|
|
})
|
|
else: # string
|
|
s.append("""
|
|
#define Lasso%(prefix_cap)s%(name)s_set_%(elem_name)s(self,value) set_string(&LASSO_%(parent_upper)s(self)->%(elem_name)s, (value))
|
|
#define Lasso%(prefix_cap)s%(name)s_%(elem_name)s_set(self,value) set_string(&LASSO_%(parent_upper)s(self)->%(elem_name)s, (value))""" % {
|
|
'prefix_cap': self.prefix_cap,
|
|
'name': self.name,
|
|
'elem_name': name,
|
|
'parent_upper': parent_upper
|
|
})
|
|
s.append('')
|
|
|
|
if any_attribute:
|
|
s.append("""\
|
|
/* any attribute */
|
|
LassoStringDict* Lasso%(prefix_cap)s%(name)s_attributes_get(Lasso%(prefix_cap)s%(name)s *self);
|
|
#define Lasso%(prefix_cap)s%(name)s_get_attributes Lasso%(prefix_cap)s%(name)s_attributes_get
|
|
LassoStringDict* Lasso%(prefix_cap)s%(name)s_attributes_get(Lasso%(prefix_cap)s%(name)s *self) {
|
|
return self->attributes;
|
|
}
|
|
/* TODO: implement attributes_set */
|
|
""" % self.__dict__)
|
|
|
|
|
|
s.append("""
|
|
/* Constructors, destructors & static methods implementations */
|
|
|
|
#define new_Lasso%(prefix_cap)s%(name)s lasso_%(category)s%(file_name)s_new
|
|
#define delete_Lasso%(prefix_cap)s%(name)s(self) lasso_node_destroy(LASSO_NODE(self))
|
|
|
|
/* Implementations of methods inherited from LassoNode */
|
|
|
|
#define Lasso%(prefix_cap)s%(name)s_dump(self) lasso_node_dump(LASSO_NODE(self))
|
|
|
|
%%}
|
|
|
|
""" % self.__dict__)
|
|
|
|
|
|
return '\n'.join(s)
|
|
|
|
|
|
|
|
def ref_to_class_name(s):
|
|
if s == 'LassoNode':
|
|
return s
|
|
|
|
if ':' in s:
|
|
ns = s.split(':')[0]
|
|
else:
|
|
ns = None
|
|
|
|
if ns in ('saml', 'samlp'):
|
|
return 'Lasso' + s.replace(':', '').replace('saml', 'Saml2').replace('Saml2p', 'Samlp2')
|
|
|
|
if ns == 'util':
|
|
return 'Lasso' + s.replace(':', '').replace('util', 'IdWsf2Util')
|
|
|
|
if ns == 'tns':
|
|
return 'Lasso' + s.replace(':', '').replace('tns', 'WsAddr')
|
|
|
|
if ns == 'disco':
|
|
return 'Lasso' + s.replace(':', '').replace('disco', 'IdWsf2Disco')
|
|
|
|
if ns == 'dstref':
|
|
return 'Lasso' + s.replace(':', '').replace('dstref', 'IdWsf2DstRef')
|
|
|
|
return '/* XXX */ void'
|
|
|
|
|
|
classes = {}
|
|
string_classes = []
|
|
|
|
doms = {}
|
|
|
|
def get_prefixes_by_filename(filename):
|
|
if filename == 'liberty-idwsf-disco-svc-v2.0.xsd':
|
|
prefix = 'disco'
|
|
prefix_cap = 'IdWsf2Disco'
|
|
elif filename == 'liberty-idwsf-utility-v2.0.xsd':
|
|
prefix = 'util'
|
|
prefix_cap = 'IdWsf2Util'
|
|
elif filename == 'liberty-idwsf-dst-v2.1.xsd':
|
|
prefix = 'dst'
|
|
prefix_cap = 'IdWsf2Dst'
|
|
elif filename == 'liberty-idwsf-dst-ref-v2.1.xsd':
|
|
prefix = 'dstref'
|
|
prefix_cap = 'IdWsf2DstRef'
|
|
elif filename == 'liberty-idwsf-security-mechanisms-v2.0.xsd':
|
|
prefix = 'sec'
|
|
prefix_cap = 'IdWsf2Sec'
|
|
elif filename == 'liberty-idwsf-idmapping-svc-v2.0.xsd':
|
|
prefix = 'ims'
|
|
prefix_cap = 'IdWsf2Ims'
|
|
elif filename == 'liberty-idwsf-subs-v1.0.xsd':
|
|
prefix = 'subs'
|
|
prefix_cap = 'IdWsf2Subs'
|
|
elif filename == 'liberty-idwsf-subs-ref-v1.0.xsd':
|
|
prefix = 'subsref'
|
|
prefix_cap = 'IdWsf2SubsRef'
|
|
elif filename == 'liberty-idwsf-people-service-v1.0.xsd':
|
|
prefix = 'ps'
|
|
prefix_cap = 'IdWsf2Ps'
|
|
elif filename == 'liberty-idwsf-interaction-svc-v2.0.xsd':
|
|
prefix = 'is'
|
|
prefix_cap = 'IdWsf2Is'
|
|
elif filename == 'liberty-idwsf-soap-binding.xsd':
|
|
prefix = 'sbf'
|
|
prefix_cap = 'IdWsf2Sbf'
|
|
elif filename == 'liberty-idwsf-soap-binding-v2.0.xsd':
|
|
prefix = 'sb2'
|
|
prefix_cap = 'IdWsf2Sb2'
|
|
elif filename == 'ws-addr.xsd':
|
|
prefix = 'wsa'
|
|
prefix_cap = 'WsAddr'
|
|
elif filename == 'oasis-200401-wss-wssecurity-secext-1.0.xsd':
|
|
prefix = 'wsse'
|
|
prefix_cap = 'WsSec1'
|
|
elif filename == 'oasis-200401-wss-wssecurity-utility-1.0.xsd':
|
|
prefix = 'wsu'
|
|
prefix_cap = 'WsUtil1'
|
|
else:
|
|
raise 'missing def for %s' % filename
|
|
return prefix, prefix_cap
|
|
|
|
xsd_filenames = ['liberty-idwsf-utility-v2.0.xsd',
|
|
'liberty-idwsf-disco-svc-v2.0.xsd',
|
|
'liberty-idwsf-dst-v2.1.xsd',
|
|
'liberty-idwsf-dst-ref-v2.1.xsd',
|
|
'liberty-idwsf-security-mechanisms-v2.0.xsd',
|
|
'liberty-idwsf-idmapping-svc-v2.0.xsd',
|
|
'liberty-idwsf-subs-ref-v1.0.xsd',
|
|
'liberty-idwsf-subs-v1.0.xsd',
|
|
'liberty-idwsf-people-service-v1.0.xsd',
|
|
'liberty-idwsf-interaction-svc-v2.0.xsd',
|
|
'liberty-idwsf-soap-binding.xsd',
|
|
'liberty-idwsf-soap-binding-v2.0.xsd',
|
|
'ws-addr.xsd',
|
|
'oasis-200401-wss-wssecurity-utility-1.0.xsd',
|
|
'oasis-200401-wss-wssecurity-secext-1.0.xsd',
|
|
]
|
|
|
|
for filename in xsd_filenames:
|
|
if filename.startswith('oasis-'):
|
|
dom = xml.dom.minidom.parseString(file(filename).read().replace(
|
|
'xsd:', 'xs:').replace('xmlns:xsd=', 'xmlns:xs='))
|
|
else:
|
|
dom = xml.dom.minidom.parse(filename)
|
|
prefix, prefix_cap = get_prefixes_by_filename(filename)
|
|
doms[prefix] = dom
|
|
classes[prefix] = {}
|
|
|
|
for filename in xsd_filenames:
|
|
xsd_content = file(filename).read()
|
|
if filename.startswith('oasis-'):
|
|
xsd_content = xsd_content.replace('xsd:', 'xs:').replace('xmlns:xsd=', 'xmlns:xs=')
|
|
prefix, prefix_cap = get_prefixes_by_filename(filename)
|
|
dom = doms[prefix]
|
|
|
|
for element in dom.getElementsByTagName('xs:complexType') + dom.getElementsByTagName('xs:element'):
|
|
|
|
string_wrapper = False
|
|
|
|
if not element.attributes.has_key('name'):
|
|
continue
|
|
|
|
if element.nodeName == 'xs:element':
|
|
if element.getElementsByTagName('xs:complexType'):
|
|
pass
|
|
else:
|
|
if not element.attributes.get('type'):
|
|
continue
|
|
if not element.attributes.get('type').value == 'samlp:StatusResponseType':
|
|
if element.attributes.get('name').value not in (
|
|
'Abstract', 'ProviderID', 'ServiceType'):
|
|
continue
|
|
string_wrapper = True
|
|
|
|
if element.nodeName == 'xs:complexType' and element.getElementsByTagName('xs:simpleContent'):
|
|
force_class_generation = False
|
|
if filename == 'liberty-idwsf-dst-ref-v2.1.xsd':
|
|
n = element.attributes['name'].value[:-4] # strip "Type"
|
|
if n in ('Select', 'TestOp', 'Sort'):
|
|
string_classes.append('dstref:%s' % n)
|
|
continue
|
|
force_class_generation = True
|
|
elif not filename.startswith('ws'):
|
|
continue
|
|
|
|
if element.nodeName == 'xs:element':
|
|
class_name = element.attributes['name'].value
|
|
else:
|
|
full_type_name = element.attributes['name'].value
|
|
class_name = full_type_name
|
|
if class_name.endswith('Type'):
|
|
class_name = class_name[:-4]
|
|
file_name = prefix + '_' + re.sub(r'[a-z]([A-Z])', rep, class_name).lower()
|
|
file_name = file_name.replace( '_name_id', '_name_id_').replace(
|
|
'_idp', '_idp_').replace('_md', '_md_')
|
|
if file_name.endswith('_'):
|
|
file_name = file_name[:-1]
|
|
|
|
klass = LassoClass()
|
|
klass.prefix = prefix
|
|
if klass.prefix.startswith('ws'):
|
|
klass.category = ''
|
|
klass.category_upper = ''
|
|
else:
|
|
klass.category = 'idwsf2_'
|
|
klass.category_upper = 'IDWSF2_'
|
|
klass.prefix_cap = prefix_cap
|
|
klass.schema_filename = filename
|
|
klass.name = class_name
|
|
klass.file_name = file_name
|
|
klass.file_name_upper = file_name.upper()
|
|
klass.elements = []
|
|
klass.attributes = []
|
|
|
|
t = [x for x in dom.getElementsByTagName('xs:element') + dom.getElementsByTagName('xsd:element') if x.attributes.has_key('type') and x.attributes['type'].value.split(':')[-1] == '%sType' % klass.name]
|
|
if len(t) == 1 and t[0].attributes['name'].value.lower() != klass.name.lower():
|
|
# if there is only one reference to this type and this reference uses another name,
|
|
# also use that other name
|
|
klass.node_set_name = t[0].attributes['name'].value
|
|
|
|
if klass.prefix == 'dstref' and klass.name in \
|
|
('Query', 'QueryResponse', 'Modify', 'ModifyResponse'):
|
|
klass.has_custom_ns = True
|
|
|
|
if element.nodeName == 'element':
|
|
schema_fragment = '<xs:element name="%s" type="samlp:StatusResponseType"/>' % class_name
|
|
elif element.nodeName == 'xs:element':
|
|
lookup_fragment_re = re.compile(
|
|
'(<xs:element name="%s")(.*?)(</xs:element>)' % klass.name, re.DOTALL)
|
|
try:
|
|
schema_fragment = ''.join(lookup_fragment_re.findall(xsd_content)[0])
|
|
except IndexError:
|
|
schema_fragment = ''
|
|
if string_wrapper:
|
|
lookup_fragment_re = re.compile(
|
|
'(<xs:element name="%s")(.*?)(/>)' % klass.name, re.DOTALL)
|
|
schema_fragment = ''.join(lookup_fragment_re.findall(xsd_content)[0])
|
|
else:
|
|
lookup_fragment_re = re.compile('(<xs:complexType name="%s")(.*?)(</xs:complexType>)' % full_type_name, re.DOTALL)
|
|
try:
|
|
schema_fragment = ''.join(lookup_fragment_re.findall(xsd_content)[0])
|
|
except IndexError:
|
|
if klass.file_name == 'wsu_timestamp':
|
|
raise 'xXX'
|
|
schema_fragment = ''
|
|
if '<xs:complexType name="%s"/>' % full_type_name in schema_fragment:
|
|
# special casing ultra simple complexType (samlp:Terminate)
|
|
schema_fragment = '<xs:complexType name="%s"/>' % full_type_name
|
|
indent = 0
|
|
schema_lines = []
|
|
for s in [x.strip() for x in schema_fragment.splitlines()]:
|
|
if s.startswith('</'):
|
|
indent -= 1
|
|
s = s.replace('\t', ' ')
|
|
if len(s) < 90:
|
|
schema_lines.append(' '*indent + s)
|
|
else:
|
|
for idx in range(70, 50, -5):
|
|
try:
|
|
s_i = s[idx:].index(' ')
|
|
except ValueError:
|
|
continue
|
|
schema_lines.append(' '*indent + s[:idx+s_i])
|
|
if len(s[idx+1+s_i:]) < 90:
|
|
schema_lines.append(' '*indent + ' '*8 + s[idx+1+s_i:])
|
|
else:
|
|
s2 = s[idx+1+s_i:]
|
|
idx = 50
|
|
s_i2 = s2[idx:].index(' ')
|
|
schema_lines.append(' '*indent + ' '*8 + s2[:idx+s_i2])
|
|
schema_lines.append(' '*indent + ' '*8 + s2[s_i2+idx+1:])
|
|
break
|
|
if not s:
|
|
continue
|
|
if s[0] == '<' and not s.startswith('</') and not s.endswith('/>'):
|
|
indent += 1
|
|
klass.schema_fragment = '\n'.join([' * ' + x for x in schema_lines])
|
|
|
|
for attr in element.getElementsByTagName('xs:attribute'):
|
|
if attr.attributes.has_key('ref'):
|
|
ref = attr.attributes['ref'].value
|
|
if ':' in ref:
|
|
ns, name = ref.split(':')
|
|
else:
|
|
name = ref
|
|
ns = prefix
|
|
if ns == 'lu':
|
|
ns = 'util'
|
|
elif ns not in doms.keys():
|
|
print 'ref:', ref
|
|
raise 'NS: %s' % ns
|
|
typ = [x for x in doms[ns].getElementsByTagName('xs:attribute') \
|
|
if x.attributes.get('name') and x.attributes['name'].value == name][0]
|
|
name = typ.attributes['name'].value
|
|
elem_type = '%s:%s' % (ns, typ.attributes['type'].value)
|
|
else:
|
|
name = attr.attributes['name'].value
|
|
if attr.attributes.has_key('type'):
|
|
type = attr.attributes['type'].value
|
|
elif attr.getElementsByTagName('xs:simpleType') and \
|
|
attr.getElementsByTagName('xs:restriction'):
|
|
restrict = attr.getElementsByTagName('xs:restriction')[0]
|
|
type = restrict.attributes['base'].value
|
|
# TODO: if present, list xs:enumeration value in comment
|
|
if attr.attributes.has_key('use') and attr.attributes['use'].value == 'optional':
|
|
optional = True
|
|
else:
|
|
optional = False
|
|
klass.attributes.append((name, type, optional))
|
|
|
|
for attr_group in element.getElementsByTagName('xs:attributeGroup'):
|
|
ref = attr_group.attributes['ref'].value.replace('saml:', '')
|
|
if ':' in ref:
|
|
ns, ref = ref.split(':', 2)
|
|
if ns == klass.prefix:
|
|
ns = None
|
|
else:
|
|
ns = None
|
|
if ns is None:
|
|
group_dom = dom
|
|
else:
|
|
group_dom = doms[ns]
|
|
|
|
attr_gr = [x for x in group_dom.getElementsByTagName('xs:attributeGroup') \
|
|
if x.attributes.get('name') and x.attributes.get('name').value == ref][0]
|
|
for attr in attr_gr.getElementsByTagName('xs:attribute'):
|
|
if attr.attributes.has_key('ref'):
|
|
ref = attr.attributes['ref'].value
|
|
if ':' in ref:
|
|
ns, name = ref.split(':')
|
|
else:
|
|
name = ref
|
|
ns = prefix
|
|
if ns == 'lu':
|
|
ns = 'util'
|
|
elif ns not in doms.keys():
|
|
print 'ref:', ref
|
|
raise 'NS: %s' % ns
|
|
typ = [x for x in doms[ns].getElementsByTagName('xs:attribute') \
|
|
if x.attributes.get('name') and x.attributes['name'].value == name][0]
|
|
name = typ.attributes['name'].value
|
|
if typ.attributes.has_key('type'):
|
|
if ':' in typ.attributes['type'].value:
|
|
elem_type = typ.attributes['type'].value
|
|
else:
|
|
elem_type = '%s:%s' % (ns, typ.attributes['type'].value)
|
|
|
|
else:
|
|
elem_type = 'xs:string'
|
|
|
|
if attr.attributes.has_key('name'):
|
|
klass.attributes.append((attr.attributes['name'].value, elem_type))
|
|
else:
|
|
klass.attributes.append((name, elem_type))
|
|
else:
|
|
if attr.attributes.has_key('type'):
|
|
if attr.attributes.has_key('use') and \
|
|
attr.attributes['use'].value == 'optional':
|
|
optional = True
|
|
else:
|
|
optional = False
|
|
klass.attributes.append(
|
|
(attr.attributes['name'].value, attr.attributes['type'].value, optional))
|
|
else:
|
|
# should actually look down, probably a simple type
|
|
if attr.attributes['name'].value in ['setReq', 'notSorted']:
|
|
klass.attributes.append(
|
|
(attr.attributes['name'].value, 'string'))
|
|
else:
|
|
raise str('No type for attr %s in attributeGroup' % attr.attributes['name'].value)
|
|
if attr_gr.getElementsByTagName('xs:anyAttribute'):
|
|
klass.attributes.append(('attributes', 'any'))
|
|
|
|
|
|
if element.getElementsByTagName('xs:anyAttribute'):
|
|
klass.attributes.append(('attributes', 'any'))
|
|
|
|
extension = element.getElementsByTagName('extension') + \
|
|
element.getElementsByTagName('xs:extension')
|
|
if string_wrapper:
|
|
klass.base_prefix = None
|
|
klass.base_class_name = 'Node'
|
|
klass.elements.append( ('content', 'text-child') )
|
|
elif extension:
|
|
base = extension[0].attributes['base'].value
|
|
klass.base_prefix = None
|
|
if base in get_str_classes() + ['xs:unsignedLong']:
|
|
if not extension[0].getElementsByTagName('attribute') and ( \
|
|
not extension[0].getElementsByTagName('xs:attribute') and ( \
|
|
not extension[0].getElementsByTagName('xs:anyAttribute'))) and (
|
|
not force_class_generation):
|
|
string_classes.append(klass.name)
|
|
else:
|
|
klass.base_class_name = 'Node'
|
|
if base in ['xs:unsignedLong']:
|
|
klass.elements.append( ('content', 'text-child-int') )
|
|
else:
|
|
klass.elements.append( ('content', 'text-child') )
|
|
else:
|
|
if ':' in base:
|
|
ns, name = base[:-4].split(':')
|
|
if ns == 'xs':
|
|
raise 'base class is %r:!' % base
|
|
if ns != prefix:
|
|
klass.base_class_name = name
|
|
klass.base_prefix = ns
|
|
else:
|
|
base_ext = get_by_name_and_attribute(dom, 'xs:complexType',
|
|
'name', name + 'Type')
|
|
if base_ext and base_ext[0].getElementsByTagName('xs:simpleContent'):
|
|
klass.base_class_name = 'Node'
|
|
if base in ('dstref:AppDataType',):
|
|
# AppDataType in schema is just an example; schemas
|
|
# derived from dstref will have random xml nodes here
|
|
klass.base_class_name = name
|
|
#klass.elements.append( ('any', 'GList', 'xmlNode'))
|
|
else:
|
|
klass.elements.append( ('content', 'text-child') )
|
|
else:
|
|
klass.base_class_name = name
|
|
else:
|
|
klass.base_class_name = base[:-4]
|
|
|
|
else:
|
|
klass.base_class_name = 'Node'
|
|
if element.nodeName == 'element':
|
|
klass.base_class_name = 'StatusResponse'
|
|
|
|
if klass.name == 'AppData':
|
|
# AppData is just a template in Data Service, replace the base
|
|
# definition (xs:string) to allow everything...
|
|
klass.elements = [['any', 'GList', 'xmlNode']]
|
|
|
|
classes[prefix][klass.name] = klass
|
|
|
|
for elem in element.getElementsByTagName('xs:element'):
|
|
if elem.attributes.has_key('ref'):
|
|
ref = elem.attributes['ref'].value
|
|
if not ':' in ref:
|
|
refered = get_by_name_and_attribute(dom, 'xs:element', 'name', ref)
|
|
if refered:
|
|
if len(refered) >= 1:
|
|
print >> sys.stderr, 'W: more than one refered'
|
|
refered = refered[0]
|
|
if refered.attributes.has_key('type'):
|
|
elem_type = refered.attributes['type'].value
|
|
name = refered.attributes['name'].value
|
|
if not ':' in elem_type:
|
|
if klass.prefix == 'util':
|
|
elem_type = 'util:%s' % elem_type
|
|
else:
|
|
elem_type = 'xs:string' # XXX
|
|
name = refered.attributes['name'].value
|
|
else:
|
|
ns, name = ref.split(':')
|
|
if ns == 'lu':
|
|
ns = 'util'
|
|
if ns == 'tns':
|
|
ns = 'wsa'
|
|
#if name in [x[0] for x in klass.elements]:
|
|
# continue
|
|
|
|
if ns == 'ds':
|
|
if name == 'Signature':
|
|
klass.has_ds_signature = True
|
|
elem_type = 'ds:Signature'
|
|
else:
|
|
print >> sys.stderr, 'W: missing xmldsig support for %s' % ref
|
|
elif not doms.has_key(ns):
|
|
print >> sys.stderr, 'W: missing dom for', ns
|
|
elem_type = 'XXX'
|
|
if ns == 'samlp':
|
|
elem_type = ref
|
|
else:
|
|
typ = [x for x in doms[ns].getElementsByTagName('xs:element') \
|
|
if x.attributes.get('name') and x.attributes['name'].value == name][0]
|
|
if typ.getElementsByTagName('xs:simpleType'):
|
|
elem_type = 'xs:string'
|
|
elif ':' in typ.attributes['type'].value:
|
|
elem_type = typ.attributes['type'].value
|
|
else:
|
|
elem_type = '%s:%s' % (ns, typ.attributes['type'].value)
|
|
else:
|
|
typ = elem
|
|
if typ.attributes.has_key('type'):
|
|
elem_type = elem.attributes['type'].value
|
|
name = elem.attributes['name'].value
|
|
elif typ.getElementsByTagName('xs:complexType'):
|
|
name = elem.attributes['name'].value
|
|
if name == 'Item':
|
|
# special case: interaction svc, SelectType/Item
|
|
klass.elements = [('Item', 'GList', 'SelectItem')]
|
|
klass.attributes = []
|
|
break
|
|
else:
|
|
raise 'XXX'
|
|
else:
|
|
raise 'XXX'
|
|
|
|
if elem_type.endswith('Type'):
|
|
elem_type = elem_type[:-4]
|
|
|
|
if elem_type == 'ds:Signature':
|
|
pass
|
|
else:
|
|
klass.elements.append( [name, elem_type] )
|
|
if elem.attributes.has_key('maxOccurs') and \
|
|
elem.attributes.get('maxOccurs').value == 'unbounded':
|
|
klass.elements[-1].insert(1, 'GList')
|
|
if not ':' in klass.elements[-1][2]:
|
|
klass.elements[-1][2] = '%s:%s' % (klass.prefix, klass.elements[-1][2])
|
|
|
|
#elif ns == 'ds' and name == 'Signature':
|
|
# klass.has_ds_signature = True
|
|
#else:
|
|
# elem_type = ref
|
|
# klass.elements.append( (name, elem_type) )
|
|
for elem in element.getElementsByTagName('any') + element.getElementsByTagName('xs:any'):
|
|
if klass.name in ('ArtifactResponse', # saml
|
|
'RequestedService', # disco
|
|
'TokenPolicy', 'Token', # sec
|
|
#'Framework', # sbf
|
|
#'TargetIdentity', 'UsageDirective', # sb2
|
|
#'Timestamp', # wsu
|
|
#'UsernameToken', 'Embedded', 'SecurityTokenReference', 'SecurityHeader',
|
|
#'TransformationParameters', # wsse
|
|
#'extension', # util
|
|
):
|
|
klass.elements.append( ('any', 'LassoNode'))
|
|
elif klass.name in (
|
|
'EndpointReference', 'ReferenceParameters', 'Metadata', 'AttributedAny', # wsa
|
|
'SecurityHeader', # wsse
|
|
):
|
|
klass.elements.append( ('any', 'GList', 'LassoNode'))
|
|
else:
|
|
print >> sys.stderr, 'W: any occurence for %s (prefix: %s)' % (klass.name, prefix)
|
|
# XXX... other occurences of <any>
|
|
|
|
print klass.name
|
|
for elem in klass.elements:
|
|
print ' ', elem
|
|
print '-'*40
|
|
|
|
def get_ordered_classes():
|
|
all_classes = []
|
|
for k in classes.keys():
|
|
all_classes.extend(classes[k].values())
|
|
clsses = []
|
|
while all_classes:
|
|
for c in all_classes:
|
|
if c.base_class_name == 'Node' or c.base_class_name in [
|
|
'%s%s' % (x.prefix_cap, x.name) for x in clsses]:
|
|
all_classes.remove(c)
|
|
clsses.append(c)
|
|
break
|
|
return clsses
|
|
|
|
|
|
def generate_swig_inheritance(prefix):
|
|
s = []
|
|
clsses = get_ordered_classes()
|
|
|
|
for klass in clsses:
|
|
if prefix == 'ws' and not klass.prefix.startswith('ws'):
|
|
continue
|
|
if prefix != 'ws' and klass.prefix.startswith('ws'):
|
|
continue
|
|
s.append('SET_NODE_INFO(%s%s, %s)' % (
|
|
klass.prefix_cap, klass.name, klass.base_class_name))
|
|
s.append('')
|
|
return '\n'.join(s) + '\n'
|
|
|
|
def generate_swig_main(prefix):
|
|
s = []
|
|
s.append('%{')
|
|
|
|
clsses = get_ordered_classes()
|
|
|
|
for klass in clsses:
|
|
if prefix == 'ws' and not klass.prefix.startswith('ws'):
|
|
continue
|
|
if prefix != 'ws' and klass.prefix.startswith('ws'):
|
|
continue
|
|
if prefix == 'ws':
|
|
s.append('#include <lasso/xml/ws/%(file_name)s.h>' % klass.__dict__)
|
|
else:
|
|
s.append('#include <lasso/xml/id-wsf-2.0/%(file_name)s.h>' % klass.__dict__)
|
|
s.append('%}')
|
|
|
|
for klass in clsses:
|
|
if prefix == 'ws' and not klass.prefix.startswith('ws'):
|
|
continue
|
|
if prefix != 'ws' and klass.prefix.startswith('ws'):
|
|
continue
|
|
s.append('%%include %(file_name)s.i' % klass.__dict__)
|
|
|
|
return '\n'.join(s)
|
|
|
|
|
|
#import pprint
|
|
#pprint.pprint(classes)
|
|
|
|
for klass_p in classes.keys():
|
|
for klass in classes[klass_p].values():
|
|
#print klass_p, klass.name
|
|
if klass.base_class_name != 'Node':
|
|
#print ' <-', klass.base_prefix, ':', klass.base_class_name
|
|
if klass.base_prefix:
|
|
prefix = klass.base_prefix
|
|
else:
|
|
prefix = klass.prefix
|
|
if prefix == 'lu':
|
|
prefix = 'util'
|
|
k = classes[prefix][klass.base_class_name]
|
|
klass.base_class_type = 'LASSO_TYPE_' + k.category_upper + k.file_name_upper
|
|
klass.base_class_name = '%s%s' % (
|
|
classes[prefix][klass.base_class_name].prefix_cap, klass.base_class_name)
|
|
else:
|
|
klass.base_class_type = 'LASSO_TYPE_NODE'
|
|
if klass.prefix.startswith('ws'):
|
|
file('ws/%s.h' % klass.file_name, 'w').write(klass.generate_header())
|
|
file('ws/%s.c' % klass.file_name, 'w').write(klass.generate_source())
|
|
file('swig-ws/%s.i' % klass.file_name, 'w').write(klass.generate_swig())
|
|
else:
|
|
file('id-wsf-2.0/%s.h' % klass.file_name, 'w').write(klass.generate_header())
|
|
file('id-wsf-2.0/%s.c' % klass.file_name, 'w').write(klass.generate_source())
|
|
file('swig-id-wsf-2.0/%s.i' % klass.file_name, 'w').write(klass.generate_swig())
|
|
|
|
file('swig-ws/inheritance.h', 'w').write(generate_swig_inheritance('ws'))
|
|
file('swig-ws/main.h', 'w').write(generate_swig_main('ws'))
|
|
|
|
file('swig-id-wsf-2.0/inheritance.h', 'w').write(generate_swig_inheritance('id-wsf-2.0'))
|
|
file('swig-id-wsf-2.0/main.h', 'w').write(generate_swig_main('id-wsf-2.0'))
|
|
|
|
def generate_makefile_am(dir):
|
|
makefile_am = file('%s/Makefile.am' % dir, 'w')
|
|
if dir == 'id-wsf-2.0':
|
|
lib_suffix = 'id-wsf-2'
|
|
else:
|
|
lib_suffix = dir
|
|
makefile_am.write('''\
|
|
liblassoincludedir = $(includedir)/lasso/xml/%s
|
|
|
|
INCLUDES = \\
|
|
\t-I$(top_srcdir) \\
|
|
\t-I$(top_srcdir)/lasso \\
|
|
\t$(LASSO_CORE_CFLAGS) \\
|
|
\t-DG_LOG_DOMAIN=\\"lasso\\"
|
|
|
|
noinst_LTLIBRARIES = liblasso-xml-%s.la
|
|
|
|
liblasso_xml_%s_la_SOURCES = \\
|
|
%s
|
|
|
|
liblassoinclude_HEADERS = \\
|
|
%s
|
|
|
|
''' % ( dir,
|
|
lib_suffix,
|
|
lib_suffix.replace('-', '_'),
|
|
'\n'.join(['\t%s \\' % x for x in sorted(os.listdir(dir)) if x.endswith('.c')])[:-2],
|
|
'\n'.join(['\t%s \\' % x for x in sorted(os.listdir(dir)) if x.endswith('.h')])[:-2]))
|
|
|
|
|
|
def generate_swig_makefile_am(dir):
|
|
makefile_am = file('%s/Makefile.am' % dir, 'w')
|
|
makefile_am.write('''\
|
|
EXTRA_DIST = \\
|
|
\tinheritance.h \\
|
|
\tmain.h \\
|
|
\tMakefile.am \\
|
|
%s
|
|
''' % '\n'.join(['\t%s \\' % x for x in sorted(os.listdir(dir)) if x.endswith('.i')])[:-2])
|
|
|
|
|
|
|
|
generate_makefile_am('id-wsf-2.0')
|
|
generate_makefile_am('ws')
|
|
|
|
generate_swig_makefile_am('swig-id-wsf-2.0')
|
|
generate_swig_makefile_am('swig-ws')
|