Blame bindings/utils.py

Packit 228f82
# Lasso - A free implementation of the Liberty Alliance specifications.
Packit 228f82
#
Packit 228f82
# Copyright (C) 2004-2007 Entr'ouvert
Packit 228f82
# http://lasso.entrouvert.org
Packit 228f82
#
Packit 228f82
# Authors: See AUTHORS file in top-level directory.
Packit 228f82
#
Packit 228f82
# This program is free software; you can redistribute it and/or modify
Packit 228f82
# it under the terms of the GNU General Public License as published by
Packit 228f82
# the Free Software Foundation; either version 2 of the License, or
Packit 228f82
# (at your option) any later version.
Packit 228f82
#
Packit 228f82
# This program is distributed in the hope that it will be useful,
Packit 228f82
# but WITHOUT ANY WARRANTY; without even the implied warranty of
Packit 228f82
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
Packit 228f82
# GNU General Public License for more details.
Packit 228f82
#
Packit 228f82
# You should have received a copy of the GNU General Public License
Packit 228f82
# along with this program; if not, see <http://www.gnu.org/licenses/>.
Packit 228f82
Packit 228f82
import re
Packit 228f82
import string
Packit 228f82
Packit 228f82
_mapping_convert_type_from_gobject_annotation = {
Packit 228f82
        'utf8': 'char*'
Packit 228f82
}
Packit 228f82
Packit 228f82
def convert_type_from_gobject_annotation(type):
Packit 228f82
    return _mapping_convert_type_from_gobject_annotation.get(type, type)
Packit 228f82
Packit 228f82
def clean_type(type):
Packit 228f82
    '''Convert struct references to their typedef counterpart'''
Packit 228f82
    if not type:
Packit 228f82
        return type
Packit 228f82
    type = type.strip()
Packit 228f82
    type = re.sub('\s+', ' ', type)
Packit 228f82
    m = re.match('\s*struct\s+_(\w+)\s*\*', type)
Packit 228f82
    if m:
Packit 228f82
        type = '%s*' % m.group(1)
Packit 228f82
    return re.sub('\s*\*\s*', '*', type)
Packit 228f82
Packit 228f82
Packit 228f82
def camelcase_to_list(varname):
Packit 228f82
    ''' convert 'camlCaseISTheThing' to ['caml', 'Case', 'IS', 'The', 'Thing']'''
Packit 228f82
    l = [[]]
Packit 228f82
    last = None
Packit 228f82
    for x in varname:
Packit 228f82
        if last:
Packit 228f82
            if last.isupper() and x.isupper():
Packit 228f82
                pass
Packit 228f82
            elif not last.isupper() and x.isupper():
Packit 228f82
                l.append([])
Packit 228f82
            elif last.isupper() and x.islower():
Packit 228f82
                y = l[-1][-1]
Packit 228f82
                del l[-1][-1]
Packit 228f82
                if not l[-1]:
Packit 228f82
                    del l[-1]
Packit 228f82
                l.append([y])
Packit 228f82
            l[-1].append(x)
Packit 228f82
        else:
Packit 228f82
            l[-1].append(x)
Packit 228f82
        last = x
Packit 228f82
    return list(map(str.lower,map(''.join,l)))
Packit 228f82
Packit 228f82
def old_format_as_camelcase(var):
Packit 228f82
    '''Format an identifier name into CamelCase'''
Packit 228f82
    if '_' in var:
Packit 228f82
        return format_underscore_as_camelcase(var)
Packit 228f82
    if var[0] in string.ascii_uppercase:
Packit 228f82
        var = var[0].lower() + var[1:]
Packit 228f82
    var = re.sub(r'([a-z])(ID)([A-Z]|$)', r'\1Id\3', var) # replace standing ID by Id
Packit 228f82
    return var
Packit 228f82
Packit 228f82
def format_as_camelcase(var):
Packit 228f82
    '''Format an identifier name into CamelCase'''
Packit 228f82
    if var[0].isupper():
Packit 228f82
        l = camelcase_to_list(var)
Packit 228f82
        return l[0] + ''.join(list(map(str.capitalize, l[1:])))
Packit 228f82
    if '_' in var:
Packit 228f82
        return format_underscore_as_camelcase(var)
Packit 228f82
    if var[0] in string.ascii_uppercase:
Packit 228f82
        var = var[0].lower() + var[1:]
Packit 228f82
    var = re.sub(r'([a-z])(ID)([A-Z]|$)', r'\1Id\3', var) # replace standing ID by Id
Packit 228f82
    return var
Packit 228f82
Packit 228f82
def format_as_underscored(var):
Packit 228f82
    '''Format an identifier name into underscored_name'''
Packit 228f82
    var = '_'.join(camelcase_to_list(var))
Packit 228f82
    var = var.replace('id_wsf2_', 'idwsf2_')
Packit 228f82
    var = var.replace('_saslresponse', '_sasl_response')
Packit 228f82
    var = var.replace('ws_addr_', 'wsa_')
Packit 228f82
    return var
Packit 228f82
Packit 228f82
def format_underscore_as_camelcase(var):
Packit 228f82
    '''Format an underscored identifier name into CamelCase'''
Packit 228f82
    def rep(s):
Packit 228f82
        return s.group(1)[0].upper() + s.group(1)[1:]
Packit 228f82
    var = re.sub(r'_([A-Za-z0-9]+)', rep, var)
Packit 228f82
    var = re.sub(r'([a-z])(ID)([A-Z]|$)', r'\1Id\3', var) # replace standing ID by Id
Packit 228f82
    return var
Packit 228f82
Packit 228f82
Packit 228f82
Packit 228f82
def last(x):
Packit 228f82
    return x[len(x)-1]
Packit 228f82
Packit 228f82
def common_prefix(x,y):
Packit 228f82
    max = min(len(x),len(y))
Packit 228f82
    last = 0
Packit 228f82
    for i in range(max):
Packit 228f82
        if x[i] != y[i]:
Packit 228f82
            return min(i,last+1)
Packit 228f82
        if x[i] == '_':
Packit 228f82
            last = i
Packit 228f82
    return max
Packit 228f82
Packit 228f82
def pgroup(group,prev):
Packit 228f82
    level, l = group
Packit 228f82
    i = 0
Packit 228f82
    for x in l:
Packit 228f82
        if i == 0:
Packit 228f82
            prefix = prev
Packit 228f82
        else:
Packit 228f82
            prefix = level
Packit 228f82
        if isinstance(x,tuple):
Packit 228f82
            pgroup(x,prefix)
Packit 228f82
        else:
Packit 228f82
            print(prefix * ' ' + x[prefix:])
Packit 228f82
        i = i + 1
Packit 228f82
Packit 228f82
def group(list):
Packit 228f82
    list.sort()
Packit 228f82
    pile = [(0,[])]
Packit 228f82
    prev = ""
Packit 228f82
    for x in list:
Packit 228f82
        l, g = last(pile)
Packit 228f82
        u = common_prefix(x,prev)
Packit 228f82
        # Find the good level of insertion
Packit 228f82
        while u < l:
Packit 228f82
            pile.pop()
Packit 228f82
            l, g = last(pile)
Packit 228f82
        # Insert here
Packit 228f82
        if u == l:
Packit 228f82
            g.append(x)
Packit 228f82
        elif u > l:
Packit 228f82
            t = (u, [g.pop(),x])
Packit 228f82
            g.append(t)
Packit 228f82
            pile.append(t)
Packit 228f82
        prev = x
Packit 228f82
    return pile[0]
Packit 228f82
Packit 228f82
def _test_arg(arg, what):
Packit 228f82
    if isinstance(arg, tuple) or isinstance(arg, list):
Packit 228f82
        return bool(arg[2].get(what))
Packit 228f82
    return False
Packit 228f82
Packit 228f82
def is_optional(arg):
Packit 228f82
    return _test_arg(arg, 'optional')
Packit 228f82
Packit 228f82
def element_type(arg):
Packit 228f82
    return arg[2].get('element-type')
Packit 228f82
Packit 228f82
def key_type(arg):
Packit 228f82
    return arg[2].get('key-type')
Packit 228f82
Packit 228f82
def value_type(arg):
Packit 228f82
    return arg[2].get('value-type')
Packit 228f82
Packit 228f82
def is_out(arg):
Packit 228f82
    return _test_arg(arg, 'out') or (arg_type(arg).endswith('**') and not _test_arg(arg, 'in'))
Packit 228f82
Packit 228f82
Packit 228f82
def is_glist(arg):
Packit 228f82
    return re.match('GList', unconstify(var_type(arg)))
Packit 228f82
Packit 228f82
def is_hashtable(arg):
Packit 228f82
    return re.match('GHashTable', unconstify(var_type(arg)))
Packit 228f82
Packit 228f82
def var_type(arg):
Packit 228f82
    '''Return the type of variable to store content'''
Packit 228f82
    arg = arg_type(arg)
Packit 228f82
    if is_out(arg):
Packit 228f82
        return arg[:-1]
Packit 228f82
    else:
Packit 228f82
        return arg
Packit 228f82
Packit 228f82
def unref_type(arg):
Packit 228f82
    return (var_type(arg), arg[1], arg[2])
Packit 228f82
Packit 228f82
def ref_name(arg):
Packit 228f82
    if is_out(arg):
Packit 228f82
        return '&%s' % arg[1]
Packit 228f82
    else:
Packit 228f82
        return arg[1]
Packit 228f82
Packit 228f82
def arg_type(arg):
Packit 228f82
    if isinstance(arg, tuple) or isinstance(arg, list):
Packit 228f82
        return arg[0]
Packit 228f82
    else:
Packit 228f82
        return arg
Packit 228f82
Packit 228f82
def arg_name(arg):
Packit 228f82
    return arg[1]
Packit 228f82
Packit 228f82
def unconstify(type):
Packit 228f82
    type = arg_type(type)
Packit 228f82
    if isinstance(type, str):
Packit 228f82
        return re.sub(r'\bconst\b\s*', '', type).strip()
Packit 228f82
    else:
Packit 228f82
        return type
Packit 228f82
Packit 228f82
def make_arg(type):
Packit 228f82
    return (type,'',{})
Packit 228f82
Packit 228f82
def arg_default(arg):
Packit 228f82
    return arg[2].get('default')
Packit 228f82
Packit 228f82
def remove_modifiers(type):
Packit 228f82
    if isinstance(type, str):
Packit 228f82
        type = re.sub(r'\s*\bunsigned\b\s*', ' ', type).strip()
Packit 228f82
        type = re.sub(r'\s*\bconst\b\s*', ' ', type).strip()
Packit 228f82
        type = re.sub(r'\s*\bsigned\b\s*', ' ', type).strip()
Packit 228f82
        type = re.sub(r'\s*\bvolatile\b\s*', ' ', type).strip()
Packit 228f82
        return clean_type(type)
Packit 228f82
    else:
Packit 228f82
        return type
Packit 228f82
Packit 228f82
def is_const(arg):
Packit 228f82
    return bool(re.search(r'\bconst\b', arg_type(arg)))
Packit 228f82
Packit 228f82
def is_cstring(arg):
Packit 228f82
    arg = arg_type(arg)
Packit 228f82
    return clean_type(unconstify(arg)) in ('char*','gchar*','guchar*','string','utf8','strings')
Packit 228f82
Packit 228f82
def is_xml_node(arg):
Packit 228f82
    arg = unconstify(arg_type(arg))
Packit 228f82
    return arg and arg.startswith('xmlNode')
Packit 228f82
Packit 228f82
def is_boolean(arg):
Packit 228f82
    return arg_type(arg) in ('gboolean','bool')
Packit 228f82
Packit 228f82
def is_pointer(arg):
Packit 228f82
    return arg_type(arg).endswith('*')
Packit 228f82
Packit 228f82
def unpointerize(arg):
Packit 228f82
    return arg_type(arg).replace('*','')
Packit 228f82
Packit 228f82
def is_list(arg):
Packit 228f82
    return unconstify(arg_type(arg)).startswith('GList')
Packit 228f82
Packit 228f82
def is_rc(arg):
Packit 228f82
    return arg_type(arg) in [ 'lasso_error_t' ]
Packit 228f82
Packit 228f82
def is_int(arg, binding_data):
Packit 228f82
    return remove_modifiers(arg_type(arg)) in [ 'time_t', 'int', 'gint', 'long', 'glong', 'lasso_error_t'] + binding_data.enums
Packit 228f82
Packit 228f82
def is_time_t_pointer(arg):
Packit 228f82
    return re.match(r'\btime_t\*', unconstify(arg_type(arg)))
Packit 228f82
Packit 228f82
def is_transfer_full(arg, default=False):
Packit 228f82
    if not isinstance(arg, tuple):
Packit 228f82
        return default
Packit 228f82
    transfer = arg[2].get('transfer')
Packit 228f82
    if transfer:
Packit 228f82
        return transfer == 'full'
Packit 228f82
    if is_cstring(arg) and is_const(arg):
Packit 228f82
        return False
Packit 228f82
    return default or is_out(arg) or is_object(arg)
Packit 228f82
Packit 228f82
_not_objects = ( 'GHashTable', 'GList', 'GType' )
Packit 228f82
Packit 228f82
def is_object(arg):
Packit 228f82
    t = clean_type(unconstify(arg_type(arg)))
Packit 228f82
    return t and t[0] in string.ascii_uppercase and not [ x for x in _not_objects if x in t ]
Packit 228f82
Packit 228f82
if __name__ == '__main__':
Packit 228f82
    print(camelcase_to_list('Samlp2IDPList'))