MochiLibraries / Biohazrd

A framework for automatically generating binding wrappers for C/C++ libraries
MIT License
60 stars 9 forks source link

Instead of erroring when an implicitly instantiated template is incomplete, make it undefined #195

Open PathogenDavid opened 3 years ago

PathogenDavid commented 3 years ago

This issue effectively covers this TODO:

https://github.com/InfectedLibraries/Biohazrd/blob/357faf9a59ed39864325d58c9a2d92315fa3e5a6/Biohazrd/TranslationUnitParser.cs#L527-L531


This situation was discovered during the fix for https://github.com/InfectedLibraries/Biohazrd/issues/134 and is now more annoying because of it.

Implicitly-instantiated templates cause an error to be attached to the library when they cannot be instantiated due to an involved type being incomplete. For example, consider the following C++ code from FunctionAbiTests.FunctionIsUncallableWithIncompleteTemplateReturn/FunctionAbiTests.FunctionIsCallableWithPointerToIncompleteTemplateReturn:

struct UndefinedType;

template<typename T> struct SomeTemplate
{
    T Field;
};

// Note: The issue happens if only one of either of these are present
SomeTemplate<UndefinedType> Test1();
SomeTemplate<UndefinedType>* Test2();

results in a parsing diagnostic:

error: field has incomplete type 'UndefinedType'

This isn't ideal since the Test function is still callable. And even if it wasn't, we could easily just strip it out.

When the same situation happens with a non-template (IE: UndefinedType Test3();) the UndefinedType becomes a TranslatedUndefinedRecord and Test3 becomes an uncallable TranslatedFunction. (This is effectively the same as what a C++ compiler does.)

We should translate these templates as TranslatedUndefinedRecord instead of emitting the error. (Maybe emit it as a warning instead.)

Unfortunately this might end up involving some heavy modification to pathogen_InstantiateAllFullySpecializedClassTemplates. Right now the diagnostics are actually being emitted to the translation unit by Clang directly. We'd need to add a mechanism to intercept them like we do with pathogen_IsFunctionTypeCallable.

Note that pathogen_IsFunctionTypeCallable is sort-of affected by this as well since as a side-effect it also caused templates to be implicitly instantiated, it's just hidden by pathogen_InstantiateAllFullySpecializedClassTemplates. We might need to modify it too...

PathogenDavid commented 3 years ago

Once this is fixed make sure to re-enable the broken tests in FunctionAbiTests.