Affix

 view release on metacpan or  search on metacpan

infix/src/core/signature.c  view on Meta::CPAN

    case INFIX_TYPE_STRUCT:
    case INFIX_TYPE_UNION:
        if (type->name) {
            // Check for namespaced type (e.g. "Namespace::Class")
            // Itanium mangling for namespaces is N...E
            const char * p = type->name;
            int parts = 0;
            // Count parts
            while (*p) {
                if (p[0] == ':' && p[1] == ':') {
                    parts++;
                    p += 2;
                }
                else {
                    p++;
                }
            }
            parts++;  // Last part

            if (parts > 1) {
                _print(state, "N");
                p = type->name;
                while (*p) {
                    const char * end = strstr(p, "::");
                    size_t part_len = end ? (size_t)(end - p) : strlen(p);
                    _print(state, "%zu", part_len);
                    // Print part_len chars
                    for (size_t i = 0; i < part_len; i++)
                        _print(state, "%c", p[i]);
                    if (end)
                        p = end + 2;
                    else
                        break;
                }
                _print(state, "E");
            }
            else {
                // Simple name
                size_t len = strlen(type->name);
                _print(state, "%zu%s", len, type->name);
            }
            _add_itanium_sub(state, type);
        }
        else {
            // Mangling for anonymous structs isn't standardized.
            // Emitting 'void' as a safe placeholder for "unknown type".
            _print(state, "v");
        }
        break;
    case INFIX_TYPE_COMPLEX:
        _print(state, "C");
        _infix_type_print_itanium_recursive(state, type->meta.complex_info.base_type);
        _add_itanium_sub(state, type);
        break;
    case INFIX_TYPE_VECTOR:
        _print(state, "Dv%zu_", type->size / type->meta.vector_info.element_type->size);
        _infix_type_print_itanium_recursive(state, type->meta.vector_info.element_type);
        _add_itanium_sub(state, type);
        break;
    default:
        // Fallback for types that don't map cleanly to Itanium mangling
        _print(state, "v");
        break;
    }
}
/**
 * @internal
 * @brief Recursively prints the MSVC C++ mangling for a type.
 * @param state The printer state.
 * @param type The type to mangle.
 */
static void _infix_type_print_msvc_recursive(printer_state * state, const infix_type * type) {
    if (state->status != INFIX_SUCCESS || !type) {
        if (state->status == INFIX_SUCCESS)
            state->status = INFIX_ERROR_INVALID_ARGUMENT;
        return;
    }

    // Check for type back-references (0-9)
    // MSVC only back-references complex types or pointers to them.
    bool can_backref =
        (type->category == INFIX_TYPE_POINTER || type->category == INFIX_TYPE_STRUCT ||
         type->category == INFIX_TYPE_UNION || type->category == INFIX_TYPE_ENUM || type->name != nullptr);

    if (can_backref) {
        for (size_t i = 0; i < state->msvc_type_count; i++) {
            if (state->msvc_types[i] == type) {
                _print(state, "%zu", i);
                return;
            }
        }
    }

    // Handle named types (Struct/Union/Enum or aliases)
    if (type->name) {
        // MSVC encoding:
        // U = Struct
        // T = Union
        // W = Enum
        char prefix = 'U';
        if (type->category == INFIX_TYPE_UNION)
            prefix = 'T';
        else if (type->category == INFIX_TYPE_ENUM)
            prefix = 'W';

        // Check for namespaces (e.g. "Namespace::Class")
        // MSVC format: <Prefix><Name>@<Namespace>@@
        // Reverse order of namespaces!
        if (strstr(type->name, "::")) {
            _print(state, "%c", prefix);

            // We need to split and reverse. Since we can't allocate easily here,
            // we'll scan the string multiple times or use recursion.
            // Let's use a simple stack-based approach for small depth.
            const char * parts[MAX_RECURSION_DEPTH];
            size_t lens[MAX_RECURSION_DEPTH];
            int count = 0;

            const char * p = type->name;
            while (*p && count < MAX_RECURSION_DEPTH) {
                parts[count] = p;



( run in 3.374 seconds using v1.01-cache-2.11-cpan-5837b0d9d2c )