On Thu, 7 May 2026 at 16:59, Arsen Arsenović via Gcc <[email protected]> wrote: > > Thomas Schwinge <[email protected]> writes: > > > Hi! > > > > On 2026-05-07T13:16:59+0200, I wrote: > >> As much as possible, I'd like to implemented and upstream the necessary > >> changes already in the current C implementation (for example, make 'enum' > >> usage compatible for both C and C++), but that won't be possible for all > >> changes, obviously. I'll reach out in separate emails for any cases > >> where it's not obvious which way is best to address certain C vs. C++ > >> incompatibilities. > > > > So, first item: what do we do with the untyped 'gomp_malloc' etc.? > > 'libgomp/libgomp.h': > > > > extern void *gomp_malloc (size_t) __attribute__((malloc)); > > > > ..., and a good number of similar others. > > > > My current assumption is that we leave these untyped, do not templatize > > them? > > > > In other words, we'll need some kind of type casting at each call site: > > > > gomp_mutex_t *plock; > > [...] > > plock = gomp_malloc (sizeof (gomp_mutex_t)); > > > > I could already in the C implementation make that: > > > > plock = (gomp_mutex_t *) gomp_malloc (sizeof (gomp_mutex_t)); > > > > ..., or (preferably?): > > > > plock = (typeof (plock)) gomp_malloc (sizeof (gomp_mutex_t)); > > > > Such changes could go in already now, in the C code. However, I assume > > that we'd eventually like this to be proper C++: > > > > plock = static_cast<decltype(plock)>(gomp_malloc (sizeof > > (gomp_mutex_t))); > > > > ..., or not? If yes, then all those numerous changes have to be part of > > the C++ switch commit. > > No, we can implement an 'operator new' overload for it: > > struct gomp_malloc_tag {}; > gomp_malloc_tag use_gomp_malloc; > > void * > operator new (std::size_t sz, gomp_malloc_tag)
If you declare this as noexcept then that means that it signals failure to allocate by returning null, instead of throwing an exception. And then callers (including the compiler when invoking it for a new-expression) check for a null pointer, instead of having to handle a std::bad_alloc exception. But since gomp_malloc never fails anyway (it either returns non-null or aborts the process with a diagnostic?) there's no need to worry about exceptions here. So the operator above would allow: auto ptr = new (use_gomp_malloc) SomeType(args); and you'd get a call to gomp_malloc with the right size, followed by a call to the SomeType constructor.
