Skip to content

Investigate extending /ALTERNATENAME to the entire multiverse #2469

@StephanTLavavej

Description

@StephanTLavavej

Currently, the /ALTERNATENAME technique introduced in #2381 isn't used for Clang and ARM64EC:

STL/stl/inc/mutex

Lines 498 to 505 in 0dc93fc

#if defined(_M_CEE) || defined(_M_ARM64EC) || defined(_M_HYBRID) \
|| defined(__clang__) // TRANSITION, Clang doesn't recognize /ALTERNATENAME, not yet reported
#define _WINDOWS_API __stdcall
#define _RENAME_WINDOWS_API(_Api) _Api##_clr
#else // ^^^ use forwarders / use /ALTERNATENAME vvv
#define _WINDOWS_API __declspec(dllimport) __stdcall
#define _RENAME_WINDOWS_API(_Api) _Api
#endif // ^^^ use /ALTERNATENAME ^^^

STL/stl/src/xonce2.cpp

Lines 33 to 43 in 0dc93fc

#if defined(_M_ARM64EC) || defined(_M_HYBRID)
// <mutex> uses the forwarder fallbacks for ARM64EC and CHPE.
#elif defined(_M_IX86)
#pragma comment(linker, "/ALTERNATENAME:__imp____std_init_once_begin_initialize@16=__imp__InitOnceBeginInitialize@16")
#pragma comment(linker, "/ALTERNATENAME:__imp____std_init_once_complete@12=__imp__InitOnceComplete@12")
#elif defined(_M_X64) || defined(_M_ARM) || defined(_M_ARM64)
#pragma comment(linker, "/ALTERNATENAME:__imp___std_init_once_begin_initialize=__imp_InitOnceBeginInitialize")
#pragma comment(linker, "/ALTERNATENAME:__imp___std_init_once_complete=__imp_InitOnceComplete")
#else // ^^^ known architecture / unknown architecture vvv
#error Unknown architecture
#endif // ^^^ unknown architecture ^^^

We should investigate extending this technique to them. We'll need to:

  • File an internal issue to get this highly useful linker option documented.
  • Report an issue upstream to Clang so they can handle it correctly (according to my vague understanding, they just need to pass it along to link.exe, as we aren't using their lld-link.exe here).

We also don't use it for CHPE and /clr, but we don't need to extend it to them.

Finally, as @AlexGuteniev noted in #2381 (comment) , we could begin using this technique for shared_mutex and possibly elsewhere:

void __cdecl _Smtx_lock_exclusive(_Smtx_t* smtx) { // lock shared mutex exclusively
AcquireSRWLockExclusive(reinterpret_cast<PSRWLOCK>(smtx));
}
void __cdecl _Smtx_lock_shared(_Smtx_t* smtx) { // lock shared mutex non-exclusively
AcquireSRWLockShared(reinterpret_cast<PSRWLOCK>(smtx));
}
int __cdecl _Smtx_try_lock_exclusive(_Smtx_t* smtx) { // try to lock shared mutex exclusively
return TryAcquireSRWLockExclusive(reinterpret_cast<PSRWLOCK>(smtx));
}
int __cdecl _Smtx_try_lock_shared(_Smtx_t* smtx) { // try to lock shared mutex non-exclusively
return TryAcquireSRWLockShared(reinterpret_cast<PSRWLOCK>(smtx));
}
void __cdecl _Smtx_unlock_exclusive(_Smtx_t* smtx) { // unlock exclusive shared mutex
ReleaseSRWLockExclusive(reinterpret_cast<PSRWLOCK>(smtx));
}
void __cdecl _Smtx_unlock_shared(_Smtx_t* smtx) { // unlock non-exclusive shared mutex
ReleaseSRWLockShared(reinterpret_cast<PSRWLOCK>(smtx));
}

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions