diff --git a/flang/include/flang/Decimal/binary-floating-point.h b/flang/include/flang/Decimal/binary-floating-point.h index 1e0cde97d98e61..cbeaaf02a67ea5 100644 --- a/flang/include/flang/Decimal/binary-floating-point.h +++ b/flang/include/flang/Decimal/binary-floating-point.h @@ -32,6 +32,7 @@ enum FortranRounding { template class BinaryFloatingPointNumber { public: + RT_OFFLOAD_VAR_GROUP_BEGIN static constexpr common::RealCharacteristics realChars{BINARY_PRECISION}; static constexpr int binaryPrecision{BINARY_PRECISION}; static constexpr int bits{realChars.bits}; @@ -47,7 +48,6 @@ template class BinaryFloatingPointNumber { using RawType = common::HostUnsignedIntType; static_assert(CHAR_BIT * sizeof(RawType) >= bits); - RT_OFFLOAD_VAR_GROUP_BEGIN static constexpr RawType significandMask{(RawType{1} << significandBits) - 1}; constexpr RT_API_ATTRS BinaryFloatingPointNumber() {} // zero diff --git a/flang/include/flang/Runtime/allocator-registry.h b/flang/include/flang/Runtime/allocator-registry.h index acfada506fafc6..fdbd47412528b7 100644 --- a/flang/include/flang/Runtime/allocator-registry.h +++ b/flang/include/flang/Runtime/allocator-registry.h @@ -13,6 +13,8 @@ #include #include +RT_OFFLOAD_VAR_GROUP_BEGIN + static constexpr unsigned kDefaultAllocator = 0; // Allocator used for CUF @@ -21,6 +23,8 @@ static constexpr unsigned kDeviceAllocatorPos = 2; static constexpr unsigned kManagedAllocatorPos = 3; static constexpr unsigned kUnifiedAllocatorPos = 4; +RT_OFFLOAD_VAR_GROUP_END + #define MAX_ALLOCATOR 7 // 3 bits are reserved in the descriptor. namespace Fortran::runtime { diff --git a/flang/include/flang/Runtime/freestanding-tools.h b/flang/include/flang/Runtime/freestanding-tools.h index e94cb0a6c938cd..6326be211616cb 100644 --- a/flang/include/flang/Runtime/freestanding-tools.h +++ b/flang/include/flang/Runtime/freestanding-tools.h @@ -63,6 +63,26 @@ #define STD_TOUPPER_UNSUPPORTED 1 #endif +#if defined(OMP_OFFLOAD_BUILD) || defined(OMP_NOHOST_BUILD) +// #pragma message "OMP_OFFLOAD_BUILD or OMP_NOHOST_BUILD is defined" +#define STD_LIBC_UNSUPPORTED 1 +#define STD_FILL_N_UNSUPPORTED 1 +#define STD_MEMSET_BUILTIN 1 +#define STD_MEMSET_UNSUPPORTED 1 +#define STD_MEMCPY_BUILTIN 1 +#define STD_MEMCPY_UNSUPPORTED 1 +#define STD_MEMMOVE_BUILTIN 1 +#define STD_MEMMOVE_UNSUPPORTED 1 +// #define STD_STRLEN_BUILTIN 1 // still resolves to strlen +#define STD_STRLEN_UNSUPPORTED 1 +#define STD_MEMCMP_UNSUPPORTED 1 +#define STD_REALLOC_UNSUPPORTED 1 +#define STD_MEMCHR_UNSUPPORTED 1 +#define STD_STRCPY_UNSUPPORTED 1 +#define STD_STRCMP_UNSUPPORTED 1 +#define STD_TOUPPER_UNSUPPORTED 1 +#endif + namespace Fortran::runtime { #if STD_FILL_N_UNSUPPORTED @@ -79,7 +99,52 @@ fill_n(A *start, std::size_t count, const B &value) { using std::fill_n; #endif // !STD_FILL_N_UNSUPPORTED -#if STD_MEMMOVE_UNSUPPORTED +#if STD_MEMSET_BUILTIN +static inline RT_API_ATTRS void memset( + void *dest, uint8_t value, std::size_t count) { + __builtin_memset(dest, value, count); +} +#elif STD_MEMSET_UNSUPPORTED +static inline RT_API_ATTRS void memset( + void *dest, uint8_t value, std::size_t count) { + char *to{reinterpret_cast(dest)}; + while (count--) { + *to++ = value; + } + return; +} +#else +using std::memset; +#endif + +#if STD_MEMCPY_BUILTIN +static inline RT_API_ATTRS void memcpy( + void *dest, const void *src, std::size_t count) { + __builtin_memcpy(dest, src, count); +} +#elif STD_MEMCPY_UNSUPPORTED +static inline RT_API_ATTRS void memcpy( + void *dest, const void *src, std::size_t count) { + char *to{reinterpret_cast(dest)}; + const char *from{reinterpret_cast(src)}; + if (to == from) { + return; + } + while (count--) { + *to++ = *from++; + } + return; +} +#else +using std::memcpy; +#endif + +#if STD_MEMMOVE_BUILTIN +static inline RT_API_ATTRS void memmove( + void *dest, const void *src, std::size_t count) { + __builtin_memmove(dest, src, count); +} +#elif STD_MEMMOVE_UNSUPPORTED // Provides alternative implementation for std::memmove(), if // it is not supported. static inline RT_API_ATTRS void memmove( @@ -91,7 +156,7 @@ static inline RT_API_ATTRS void memmove( return; } if (to + count <= from || from + count <= to) { - std::memcpy(dest, src, count); + memcpy(dest, src, count); } else if (to < from) { while (count--) { *to++ = *from++; @@ -108,7 +173,11 @@ static inline RT_API_ATTRS void memmove( using std::memmove; #endif // !STD_MEMMOVE_UNSUPPORTED -#if STD_STRLEN_UNSUPPORTED +#if STD_STRLEN_BUILTIN +static inline RT_API_ATTRS std::size_t strlen(const char *str) { + return __builtin_strlen(str); +} +#elif STD_STRLEN_UNSUPPORTED // Provides alternative implementation for std::strlen(), if // it is not supported. static inline RT_API_ATTRS std::size_t strlen(const char *str) { diff --git a/flang/runtime/assign.cpp b/flang/runtime/assign.cpp index d558ada51cd21a..b6076533d7ba58 100644 --- a/flang/runtime/assign.cpp +++ b/flang/runtime/assign.cpp @@ -274,7 +274,7 @@ RT_API_ATTRS static void Assign( if (MayAlias(to, from)) { if (mustDeallocateLHS) { deferDeallocation = &deferredDeallocStatDesc.descriptor(); - std::memcpy(deferDeallocation, &to, to.SizeInBytes()); + Fortran::runtime::memcpy(deferDeallocation, &to, to.SizeInBytes()); to.set_base_addr(nullptr); } else if (!isSimpleMemmove()) { // Handle LHS/RHS aliasing by copying RHS into a temp, then @@ -282,7 +282,7 @@ RT_API_ATTRS static void Assign( auto descBytes{from.SizeInBytes()}; StaticDescriptor staticDesc; Descriptor &newFrom{staticDesc.descriptor()}; - std::memcpy(&newFrom, &from, descBytes); + Fortran::runtime::memcpy(&newFrom, &from, descBytes); // Pretend the temporary descriptor is for an ALLOCATABLE // entity, otherwise, the Deallocate() below will not // free the descriptor memory. diff --git a/flang/runtime/derived.cpp b/flang/runtime/derived.cpp index 659f54fa344bb0..18344e948c7c82 100644 --- a/flang/runtime/derived.cpp +++ b/flang/runtime/derived.cpp @@ -73,7 +73,8 @@ RT_API_ATTRS int Initialize(const Descriptor &instance, std::size_t bytes{comp.SizeInBytes(instance)}; for (std::size_t j{0}; j++ < elements; instance.IncrementSubscripts(at)) { char *ptr{instance.ElementComponent(at, comp.offset())}; - std::memcpy(ptr, init, bytes); + // std::memcpy(ptr, init, bytes); + Fortran::runtime::memcpy(ptr, init, bytes); } } else if (comp.genre() == typeInfo::Component::Genre::Pointer) { // Data pointers without explicit initialization are established diff --git a/flang/runtime/descriptor.cpp b/flang/runtime/descriptor.cpp index 32f43e89dc7a36..eaf6331ef8e84c 100644 --- a/flang/runtime/descriptor.cpp +++ b/flang/runtime/descriptor.cpp @@ -26,7 +26,7 @@ RT_OFFLOAD_API_GROUP_BEGIN RT_API_ATTRS Descriptor::Descriptor(const Descriptor &that) { *this = that; } RT_API_ATTRS Descriptor &Descriptor::operator=(const Descriptor &that) { - std::memcpy(this, &that, that.SizeInBytes()); + Fortran::runtime::memcpy(this, &that, that.SizeInBytes()); return *this; } diff --git a/flang/runtime/stat.cpp b/flang/runtime/stat.cpp index 525a4e36cdc773..694bbd77451bbb 100644 --- a/flang/runtime/stat.cpp +++ b/flang/runtime/stat.cpp @@ -84,10 +84,10 @@ RT_API_ATTRS int ToErrmsg(const Descriptor *errmsg, int stat) { std::size_t bufferLength{errmsg->ElementBytes()}; std::size_t msgLength{Fortran::runtime::strlen(msg)}; if (msgLength >= bufferLength) { - std::memcpy(buffer, msg, bufferLength); + Fortran::runtime::memcpy(buffer, msg, bufferLength); } else { - std::memcpy(buffer, msg, msgLength); - std::memset(buffer + msgLength, ' ', bufferLength - msgLength); + Fortran::runtime::memcpy(buffer, msg, msgLength); + Fortran::runtime::memset(buffer + msgLength, ' ', bufferLength - msgLength); } } } diff --git a/flang/runtime/tools.cpp b/flang/runtime/tools.cpp index 73d6c2cf7e1d2b..0ee4f6058ac419 100644 --- a/flang/runtime/tools.cpp +++ b/flang/runtime/tools.cpp @@ -28,7 +28,7 @@ RT_API_ATTRS OwningPtr SaveDefaultCharacter( const char *s, std::size_t length, const Terminator &terminator) { if (s) { auto *p{static_cast(AllocateMemoryOrCrash(terminator, length + 1))}; - std::memcpy(p, s, length); + Fortran::runtime::memcpy(p, s, length); p[length] = '\0'; return OwningPtr{p}; } else { @@ -75,10 +75,10 @@ RT_API_ATTRS void ToFortranDefaultCharacter( char *to, std::size_t toLength, const char *from) { std::size_t len{Fortran::runtime::strlen(from)}; if (len < toLength) { - std::memcpy(to, from, len); - std::memset(to + len, ' ', toLength - len); + Fortran::runtime::memcpy(to, from, len); + Fortran::runtime::memset(to + len, ' ', toLength - len); } else { - std::memcpy(to, from, toLength); + Fortran::runtime::memcpy(to, from, toLength); } } @@ -122,7 +122,7 @@ RT_API_ATTRS void ShallowCopyDiscontiguousToDiscontiguous( std::size_t elementBytes{to.ElementBytes()}; for (std::size_t n{to.Elements()}; n-- > 0; to.IncrementSubscripts(toAt), from.IncrementSubscripts(fromAt)) { - std::memcpy( + Fortran::runtime::memcpy( to.Element(toAt), from.Element(fromAt), elementBytes); } } @@ -135,7 +135,7 @@ RT_API_ATTRS void ShallowCopyDiscontiguousToContiguous( std::size_t elementBytes{to.ElementBytes()}; for (std::size_t n{to.Elements()}; n-- > 0; toAt += elementBytes, from.IncrementSubscripts(fromAt)) { - std::memcpy(toAt, from.Element(fromAt), elementBytes); + Fortran::runtime::memcpy(toAt, from.Element(fromAt), elementBytes); } } @@ -147,7 +147,7 @@ RT_API_ATTRS void ShallowCopyContiguousToDiscontiguous( std::size_t elementBytes{to.ElementBytes()}; for (std::size_t n{to.Elements()}; n-- > 0; to.IncrementSubscripts(toAt), fromAt += elementBytes) { - std::memcpy(to.Element(toAt), fromAt, elementBytes); + Fortran::runtime::memcpy(to.Element(toAt), fromAt, elementBytes); } } @@ -155,7 +155,7 @@ RT_API_ATTRS void ShallowCopy(const Descriptor &to, const Descriptor &from, bool toIsContiguous, bool fromIsContiguous) { if (toIsContiguous) { if (fromIsContiguous) { - std::memcpy(to.OffsetElement(), from.OffsetElement(), + Fortran::runtime::memcpy(to.OffsetElement(), from.OffsetElement(), to.Elements() * to.ElementBytes()); } else { ShallowCopyDiscontiguousToContiguous(to, from); @@ -177,7 +177,7 @@ RT_API_ATTRS char *EnsureNullTerminated( char *str, std::size_t length, Terminator &terminator) { if (runtime::memchr(str, '\0', length) == nullptr) { char *newCmd{(char *)AllocateMemoryOrCrash(terminator, length + 1)}; - std::memcpy(newCmd, str, length); + Fortran::runtime::memcpy(newCmd, str, length); newCmd[length] = '\0'; return newCmd; } else { @@ -209,7 +209,7 @@ RT_API_ATTRS std::int32_t CopyCharsToDescriptor(const Descriptor &value, return ToErrmsg(errmsg, StatValueTooShort); } - std::memcpy(value.OffsetElement(offset), rawValue, toCopy); + Fortran::runtime::memcpy(value.OffsetElement(offset), rawValue, toCopy); if (static_cast(rawValueLength) > toCopy) { return ToErrmsg(errmsg, StatValueTooShort);