c2rust-refactor 0.15.0

C2Rust refactoring tool implementation
import functools
import re


def linewise(f):
    @functools.wraps(f)
    def g(*args, **kwargs):
        return '\n'.join(f(*args, **kwargs))
    return g

def comma_sep(f):
    @functools.wraps(f)
    def g(*args, **kwargs):
        return ', '.join(f(*args, **kwargs))
    return g

def wordwise(f):
    @functools.wraps(f)
    def g(*args, **kwargs):
        return ' '.join(f(*args, **kwargs))
    return g


@comma_sep
def struct_fields(fields, suffix, bind_mode):
    for f in fields:
        yield '%s: %s%s%s' % (f.name, bind_mode, f.name, suffix)

@comma_sep
def tuple_fields(fields, suffix, bind_mode):
    for f in fields:
        yield '%s%s%s' % (bind_mode, f.name, suffix)

def struct_pattern(s, path, suffix='', bind_mode='ref '):
    if not s.is_tuple:
        return '%s { %s }' % (path, struct_fields(s.fields, suffix, bind_mode))
    else:
        if len(s.fields) == 0:
            return path
        else:
            return '%s(%s)' % (path, tuple_fields(s.fields, suffix, bind_mode))


CAPS_RE = re.compile(r'[A-Z]')

def snake(s):
    s = CAPS_RE.sub(lambda m: '_' + m.group().lower(), s)
    if s.startswith('_'):
        s = s[1:]
    return s

def find_kind_field(s):
    if 'no_kind' in s.attrs:
        return None

    marked_fields = []
    for f in s.fields:
        if 'kind' in f.attrs:
            marked_fields.append(f.name)
    if len(marked_fields) == 1:
        return marked_fields[0]
    elif len(marked_fields) > 1:
        raise ValueError('struct %s has %d fields marked #[kind] (expected 0 or 1)' %
                (s.name, len(marked_fields)))

    for f in s.fields:
        if f.name == 'kind':
            return f.name

    return None