<table border="1" cellspacing="0" cellpadding="8">
<tr>
<th>Issue</th>
<td>
<a href=https://github.com/llvm/llvm-project/issues/225032>225032</a>
</td>
</tr>
<tr>
<th>Summary</th>
<td>
[clang] #pragma weak with a prototype-less target creates a second declaration; using the alias asserts in castAs<FunctionProtoType>
</td>
</tr>
<tr>
<th>Labels</th>
<td>
clang
</td>
</tr>
<tr>
<th>Assignees</th>
<td>
</td>
</tr>
<tr>
<th>Reporter</th>
<td>
captainnemo9292
</td>
</tr>
</table>
<pre>
When `a` is already declared and `#pragma weak a = b` is applied, the weak alias for `a` is created as a *new* `FunctionDecl` cloned from `b` instead of being merged with the existing declaration of `a`. Name lookup for `a` then yields two declarations, which the C code paths treat like an overload set, and the overload machinery assumes every candidate has a prototype. If `b` is declared without one, the clone is a `FunctionNoProtoType` and the `castAs<FunctionProtoType>()` fails.
https://godbolt.org/z/78j6c3zeY (`-O0`)
```c
int a();
#pragma weak a = b
int b() { return a; }
```
```
clang: include/clang/AST/TypeBase.h:9336: const T* clang::Type::castAs() const [with T = clang::FunctionProtoType]: Assertion `isa<T>(CanonicalType)' failed.
#11 completeFunctionType(clang::Sema&, clang::FunctionDecl*, clang::SourceLocation, bool) SemaOverload.cpp
#12 clang::Sema::ResolveAddressOfOverloadedFunction(...)
#13 clang::Sema::CheckSingleAssignmentConstraints(...)
#14 clang::InitializationSequence::Perform(...)
#17 clang::Sema::BuildReturnStmt(...)
```
Self-alias with a K&R definition hits the same thing from a different entry point (https://godbolt.org/z/8fTEe4dsY):
```c
#pragma weak a = a
int a() { a; }
```
```
Casting.h:572: llvm::cast(From*) [To = clang::FunctionProtoType; From = const clang::FunctionType]: Assertion `isa<To>(Val) && "cast<Ty>() argument of incompatible type!"' failed.
#10 clang::Sema::FunctionNonObjectParamTypesAreEqual(...)
#11 sameFunctionParameterTypeLists(...) SemaOverload.cpp
#12 clang::Sema::resolveAddressOfSingleOverloadCandidate(...)
```
With `int b(void)` / `int a(void)` there is no crash, only the odd (for C) diagnostics `address of overloaded function 'a' is ambiguous` / `reference to overloaded function could not be resolved`, which show the duplicate declaration is there in that case too. Clang trunk, assertions build.
Possibly related: #35478 (`#pragma weak A = B` when A is already declared) and #173674 (same assertion with a weak alias between a function and a variable).
</pre>
<img width="1" height="1" alt="" src="http://email.email.llvm.org/o/eJyUVlGP2zgO_jXKCzGBI02c5CEPTqYBFrfYFp3BLfZRlphYO7LkleTJpb_-QNmeSdOgvQMK1BORFEl930fKGM3JIW7ZcseWTzPZp8aHrZJdksY5bP2Gb_is9vqy_bNBB6wsJCsLMBGkDSj1BTQqKwNqkE7TOeOiC_LUSjijfAUJTDxBPTl1nTWoGd9DanC0sEZGOPpwHV0FlImCRorAK4dnxiuyOPROJePdEypLxsp6hxqOwbd0PNzkYkKpwR-hRuNO0GI4oYazSU2-GP9jYqKDIXtJAcl6zGAOf8gWwXr_2nffpZaoCxeDVkdIZ3_tH6mqc2PUcMUelNcInUxNhETlgDWvCNKBf8NgvdQQMZETdY5c3n9vpWqMw3ABGWPfYgR8o7-UdNpomRCa3Jgu-OTTpcM5_Hb8qD5-PApV7PsE3uHU9Nyw_BjX7fzDf6FgL5cOKcaUEisLJWOqIhP7yfTDUHxifM34hjyO0tg4Z0XFiqpJqYtMVIwfGD-cvK69TXMfTowfvjF-WK3_LpX4hn8B-ZfFw-ciI2czuNN3_qdYURmXQI7XiB2d3gfYYFkPlsBWOwiY-uBAMrEDtnq6Dnzzrax0JyYqME7ZXiPjh-EnfqieXxg_ULU7GXHeMFFthCjJWHkXE7wQLqcATFRDY-hrbNyQ0GDMlruMwZec9JXXj71dPtEdVYwYMjpZWZgomdi_DG3fS-edUdJma75hfJXfADU9AjAuFgtQvu0sJpzCD7brq4ufsZWMlwSOO-lkkvHq5vTZ90Hh715l3NNh7b2lKina5xHFc9V1UyYcbq_MX18xevuGldYBY_x8nFxRTwkwvp7P5wMyciRxP9K-QfX6bNzJYpVFrUWX9tTzII1L8Yc4j9dxfnMmGWnNt1zQM_7To1PjK37BcPSh_SHA6n4iu95Y_TUj7zm16drtO_QV1TPa48MgfhkTEv7FePkVNB4N5eMdNCbFTMNIcpQaUqwsdBK0OR4xoEuALoULdJ7gz_j6V9xbH18-4aOOf2VCVXcYd5dg8nsqZoL9D8zay6yzmTfLFSdIW_vWfhCE8fUh-DaDbEP8ePG_5obYwSHrPRlmYt0x_wWL_ECjf8sM3EyBEhjnOSmxf7m8qxvIcOoJTzQhjCNOyWRqi5AynRaM8zvsK-4D5ENw3ef6b1TpiwyypWRjFfDTPz0ldIO1RQbAex_IARMGcvrdxCt0_78EDDcEHBg0BdhP4-YnKP6ToEtdHcX3zRs9TgTGD9OJ_P4kNRjyCHIeVJCxIQ3xzl6GMag1AZnG7p5q0kaenI_JqJjn8JAsPYZ_1ws4js0BxleSXoMGXFubU-_7eJVNwEwbhZD8XX_le6vB-QQ1wtgfnafTNN1j4885Ud131igax9drhIlTfQ5SIxMoGek2P4c9vQGk0LvXPPcnWEaoSTbG6fnFx2hqe4GAlpYgQjDjQiwfV-txYN5QtMpM2FGZZ1pQqnsLWkYy7WgkXqJcPVKsLCzveUxCdLWX1ZjOiA7kR4coiIQ3GYysLY2e-Uxvhd6IjZzhdrFabzbrolyJWbN9LDblcalKJVf1UWjOS6VWi1UhxEJIrfnMbHnBy2LDF8V6uViIuSoLsS6E0IiLxXKF7LHAVho7J9kgGZuZGHvccr4sBJ9ZWaONeX_lfJzZnFbZsCWHh7o_RfZYWGLJR4hkks1L7-CxfIKbho59eN-vHiwhLslwwjTuprQ_RVTe6evXJ2nqI-k0AWRo4dDeSHj46S4164Pd3si3SU1fzxUJ5CEL5_DfQxc8aQfjh9yOyPhh7Mjblv83AAD___JXuCs">