Ignore:
Timestamp:
Apr 26, 2026, 5:46:08 PM (2 days ago)
Author:
Matthew Au-Yeung <mw2auyeu@…>
Branches:
stuck-waitfor-destruct
Parents:
88bb0b4
git-author:
Matthew Au-Yeung <mw2auyeu@…> (04/26/26 17:44:48)
git-committer:
Matthew Au-Yeung <mw2auyeu@…> (04/26/26 17:46:08)
Message:

Set top level autogen cfa_linkonce

  • Remove default static and inline
  • Add pass to autogen functions in lib to have default visibility
  • Add fix for union ctor with array constructor passing pointer to array instead of array itself. Previous changes brought light the compilation error.
  • Note: found compilation trying to invoke union operator with array in cfa
File:
1 edited

Legend:

Unmodified
Added
Removed
  • src/CodeGen/LinkOnce.cpp

    r88bb0b4 rd8a3073  
    2222#include "AST/Expr.hpp"
    2323#include "AST/Pass.hpp"
     24#include "CompilationState.hpp"
     25#include "InitTweak/InitTweak.hpp"
    2426
    2527namespace CodeGen {
     
    3335bool is_section_attribute( ast::Attribute const * attr ) {
    3436        return "section" == attr->name;
     37}
     38
     39bool is_visibility_attribute( ast::Attribute const * attr ) {
     40        return "visibility" == attr->name;
    3541}
    3642
     
    6066                ast::Attribute * attribute = found->get_and_mutate();
    6167                assert( attribute->params.empty() );
    62                 assert( !decl->mangleName.empty() );
    6368
    6469                attribute->name = "section";
     
    6974                );
    7075
    71                 // Unconditionnaly add "visibility(default)" to anything with
    72                 // .gnu.linkonce visibility is a mess otherwise.
    7376                attributes.push_back( new ast::Attribute( "visibility", {
     77                        ast::ConstantExpr::from_string( mutDecl->location, "default" )
     78                } ) );
     79
     80                // Mark as used so GCC does not warn about unused definitions
     81                // in translation units that include but don't call the function.
     82                attributes.push_back( new ast::Attribute( "used" ) );
     83
     84                return mutDecl;
     85        }
     86};
     87
     88/// Adds visibility("default") to autogen CFA autogen function definitions so they
     89/// are exported from shared libraries compiled with -fvisibility=hidden.
     90struct AutogenDefaultVisibility {
     91        int funcDepth = 0;
     92
     93        void previsit( ast::FunctionDecl const * ) {
     94                funcDepth++;
     95        }
     96
     97        ast::FunctionDecl const * postvisit( ast::FunctionDecl const * decl ) {
     98                funcDepth--;
     99                // Only top-level function definitions (not nested).
     100                if ( funcDepth > 0 ) return decl;
     101                // Only CFA-mangled, non-builtin, non-static, non-inline functions.
     102                if ( !decl->linkage.is_mangled ) return decl;
     103                if ( decl->linkage.is_builtin ) return decl;
     104                if ( decl->storage.is_static || decl->funcSpec.is_inline ) return decl;
     105
     106                // Only definitions (functions with bodies).
     107                if ( !decl->stmts ) return decl;
     108
     109                // Only constructors, destructors, and assignment operators —
     110                // the functions that cfa_linkonce autogen functions call on member types.
     111                if ( !InitTweak::isDefaultConstructor( decl )
     112                                && !InitTweak::isCopyConstructor( decl )
     113                                && !InitTweak::isDestructor( decl )
     114                                && !InitTweak::isAssignment( decl ) ) return decl;
     115
     116                // Skip if already has a visibility attribute.
     117                auto & attributes = decl->attributes;
     118                auto found = std::find_if( attributes.begin(), attributes.end(),
     119                                is_visibility_attribute );
     120                if ( attributes.end() != found ) return decl;
     121
     122                auto mutDecl = mutate( decl );
     123                mutDecl->attributes.push_back( new ast::Attribute( "visibility", {
    74124                        ast::ConstantExpr::from_string( mutDecl->location, "default" )
    75125                } ) );
     
    82132void translateLinkOnce( ast::TranslationUnit & translationUnit ) {
    83133        ast::Pass<LinkOnceCore>::run( translationUnit );
     134
     135        // When building libcfa (-cfalib), add visibility("default") to CFA
     136        // function definitions so they are exported despite -fvisibility=hidden.
     137        if ( buildingLibrary() ) {
     138                ast::Pass<AutogenDefaultVisibility>::run( translationUnit );
     139        }
    84140}
    85141
Note: See TracChangeset for help on using the changeset viewer.