/*** Copyright (C) 2022 J Reece Wilson (a/k/a "Reece"). All rights reserved. File: auTypeUtils.hpp Date: 2022-2-10 Author: Reece ***/ #pragma once #include "auEndianness.hpp" #if defined(AURORA_ARCH_X64) || defined(AURORA_ARCH_X86) || defined(AURORA_ARCH_ARM) #define AURORA_PERMIT_ARBITRARY_REF #endif template static auline T AuReadGenericLE(const void *ptr, int offset) { #if defined(AURORA_PERMIT_ARBITRARY_REF) T temp = *reinterpret_cast(reinterpret_cast(ptr) + offset); #else T temp; AuMemcpy(&temp, reinterpret_cast(ptr) + offset, sizeof(temp)); #endif if constexpr (sizeof(T) != 1) { #if !defined(AU_CPU_ENDIAN_LITTLE) temp = AuFlipEndian(temp); #endif } return temp; } template static auline T AuReadGenericBE(const void *ptr, int offset) { #if defined(AURORA_PERMIT_ARBITRARY_REF) T temp = *reinterpret_cast(reinterpret_cast(ptr) + offset); #else T temp; AuMemcpy(&temp, reinterpret_cast(ptr) + offset, sizeof(temp)); #endif if constexpr (sizeof(T) != 1) { #if defined(AU_CPU_ENDIAN_LITTLE) temp = AuFlipEndian(temp); #endif } return temp; } static auline AuUInt64 AuReadU64LE(const void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuUInt32 AuReadU32LE(const void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuUInt16 AuReadU16LE(const void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuUInt8 AuReadU8LE(const void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuInt64 AuReadS64LE(const void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuInt32 AuReadS32LE(const void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuInt16 AuReadS16LE(const void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuInt8 AuReadS8LE(const void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuUInt64 AuReadU64BE(const void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuUInt32 AuReadU32BE(const void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuUInt16 AuReadU16BE(const void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuUInt8 AuReadU8BE(const void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuInt64 AuReadS64BE(const void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuInt32 AuReadS32BE(const void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuInt16 AuReadS16BE(const void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuInt8 AuReadS8BE(const void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuUInt64 AuReadU64(const void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadU64LE(ptr, offset); #else return AuReadU64BE(ptr, offset); #endif } static auline AuUInt32 AuReadU32(const void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadU32LE(ptr, offset); #else return AuReadU32BE(ptr, offset); #endif } static auline AuUInt16 AuReadU16(const void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadU16LE(ptr, offset); #else return AuReadU16BE(ptr, offset); #endif } static auline AuUInt8 AuReadU8(const void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadU8LE(ptr, offset); #else return AuReadU8BE(ptr, offset); #endif } static auline AuInt64 AuReadS64(const void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadS64LE(ptr, offset); #else return AuReadS64BE(ptr, offset); #endif } static auline AuInt32 AuReadS32(const void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadS32LE(ptr, offset); #else return AuReadS32BE(ptr, offset); #endif } static auline AuInt16 AuReadS16(const void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadS16LE(ptr, offset); #else return AuReadS16BE(ptr, offset); #endif } static auline AuInt8 AuReadS8(const void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadS8LE(ptr, offset); #else return AuReadS8BE(ptr, offset); #endif } template static auline void AuWriteGenericLE(void *ptr, int offset, T value) { #if !defined(AU_CPU_ENDIAN_LITTLE) value = AuFlipEndian(value); #endif #if defined(AURORA_PERMIT_ARBITRARY_REF) *reinterpret_cast(reinterpret_cast(ptr) + offset) = value; #else AuMemcpy(reinterpret_cast(ptr) + offset, &value, sizeof(value)); #endif } template static auline void AuWriteGenericBE(void *ptr, int offset, T value) { #if defined(AU_CPU_ENDIAN_LITTLE) value = AuFlipEndian(value); #endif #if defined(AURORA_PERMIT_ARBITRARY_REF) *reinterpret_cast(reinterpret_cast(ptr) + offset) = value; #else AuMemcpy(reinterpret_cast(ptr) + offset, &value, sizeof(value)); #endif } static auline void AuWriteU64LE(void *ptr, int offset, AuUInt64 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteU32LE(void *ptr, int offset, AuUInt32 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteU16LE(void *ptr, int offset, AuUInt16 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteU8LE(void *ptr, int offset, AuUInt8 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteS64LE(void *ptr, int offset, AuInt64 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteS32LE(void *ptr, int offset, AuInt32 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteS16LE(void *ptr, int offset, AuInt16 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteS8LE(void *ptr, int offset, AuInt8 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteU64BE(void *ptr, int offset, AuUInt64 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteU32BE(void *ptr, int offset, AuUInt32 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteU16BE(void *ptr, int offset, AuUInt16 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteU8BE(void *ptr, int offset, AuUInt8 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteS64BE(void *ptr, int offset, AuInt64 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteS32BE(void *ptr, int offset, AuInt32 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteS16BE(void *ptr, int offset, AuInt16 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteS8BE(void *ptr, int offset, AuInt8 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteU64(void *ptr, int offset, AuUInt64 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteU64LE(ptr, offset, value); #else AuWriteU64BE(ptr, offset, value); #endif } static auline void AuWriteU32(void *ptr, int offset, AuUInt32 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteU32LE(ptr, offset, value); #else AuWriteU32BE(ptr, offset, value); #endif } static auline void AuWriteU16(void *ptr, int offset, AuUInt16 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteU16LE(ptr, offset, value); #else AuWriteU16BE(ptr, offset, value); #endif } static auline void AuWriteU8(void *ptr, int offset, AuUInt8 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteU8LE(ptr, offset, value); #else AuWriteU8BE(ptr, offset, value); #endif } static auline void AuWriteS64(void *ptr, int offset, AuInt64 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteS64LE(ptr, offset, value); #else AuWriteS64BE(ptr, offset, value); #endif } static auline void AuWriteS32(void *ptr, int offset, AuInt32 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteS32LE(ptr, offset, value); #else AuWriteS32BE(ptr, offset, value); #endif } static auline void AuWriteS16(void *ptr, int offset, AuInt16 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteS16LE(ptr, offset, value); #else AuWriteS16BE(ptr, offset, value); #endif } static auline void AuWriteS8(void *ptr, int offset, AuInt8 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteS8LE(ptr, offset, value); #else AuWriteS8BE(ptr, offset, value); #endif } template static auline T AuReadGenericLE(const volatile void *ptr, int offset) { #if defined(AURORA_PERMIT_ARBITRARY_REF) && ((defined(AURORA_COMPILER_CLANG) && !defined(CLANG_NOT_X86_AND_NOT_VOLATILEMS)) || defined(AURORA_COMPILER_MSVC)) T temp = *reinterpret_cast(reinterpret_cast(ptr) + offset); #else AURORA_COMPILER_VOLATILE_BARRIER(); T temp; AuMemcpy(&temp, ((const AuUInt8 *)ptr) + offset, sizeof(temp)); #endif if constexpr (sizeof(T) != 1) { #if !defined(AU_CPU_ENDIAN_LITTLE) temp = AuFlipEndian(temp); #endif } return temp; } template static auline T AuReadGenericBE(const volatile void *ptr, int offset) { #if defined(AURORA_PERMIT_ARBITRARY_REF) && ((defined(AURORA_COMPILER_CLANG) && !defined(CLANG_NOT_X86_AND_NOT_VOLATILEMS)) || defined(AURORA_COMPILER_MSVC)) T temp = *reinterpret_cast(reinterpret_cast(ptr) + offset); #else AURORA_COMPILER_VOLATILE_BARRIER(); T temp; AuMemcpy(&temp, ((const AuUInt8 *)ptr) + offset, sizeof(temp)); #endif if constexpr (sizeof(T) != 1) { #if defined(AU_CPU_ENDIAN_LITTLE) temp = AuFlipEndian(temp); #endif } return temp; } static auline AuUInt64 AuReadU64LE(const volatile void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuUInt32 AuReadU32LE(const volatile void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuUInt16 AuReadU16LE(const volatile void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuUInt8 AuReadU8LE(const volatile void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuInt64 AuReadS64LE(const volatile void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuInt32 AuReadS32LE(const volatile void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuInt16 AuReadS16LE(const volatile void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuInt8 AuReadS8LE(const volatile void *ptr, int offset) { return AuReadGenericLE(ptr, offset); } static auline AuUInt64 AuReadU64BE(const volatile void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuUInt32 AuReadU32BE(const volatile void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuUInt16 AuReadU16BE(const volatile void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuUInt8 AuReadU8BE(const volatile void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuInt64 AuReadS64BE(const volatile void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuInt32 AuReadS32BE(const volatile void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuInt16 AuReadS16BE(const volatile void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuInt8 AuReadS8BE(const volatile void *ptr, int offset) { return AuReadGenericBE(ptr, offset); } static auline AuUInt64 AuReadU64(const volatile void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadU64LE(ptr, offset); #else return AuReadU64BE(ptr, offset); #endif } static auline AuUInt32 AuReadU32(const volatile void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadU32LE(ptr, offset); #else return AuReadU32BE(ptr, offset); #endif } static auline AuUInt16 AuReadU16(const volatile void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadU16LE(ptr, offset); #else return AuReadU16BE(ptr, offset); #endif } static auline AuUInt8 AuReadU8(const volatile void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadU8LE(ptr, offset); #else return AuReadU8BE(ptr, offset); #endif } static auline AuInt64 AuReadS64(const volatile void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadS64LE(ptr, offset); #else return AuReadS64BE(ptr, offset); #endif } static auline AuInt32 AuReadS32(const volatile void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadS32LE(ptr, offset); #else return AuReadS32BE(ptr, offset); #endif } static auline AuInt16 AuReadS16(const volatile void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadS16LE(ptr, offset); #else return AuReadS16BE(ptr, offset); #endif } static auline AuInt8 AuReadS8(const volatile void *ptr, int offset) { #if defined(AU_CPU_ENDIAN_LITTLE) return AuReadS8LE(ptr, offset); #else return AuReadS8BE(ptr, offset); #endif } template static auline void AuWriteGenericLE(volatile void *ptr, int offset, T value) { #if !defined(AU_CPU_ENDIAN_LITTLE) value = AuFlipEndian(value); #endif #if defined(AURORA_PERMIT_ARBITRARY_REF) *reinterpret_cast(reinterpret_cast(ptr) + offset) = value; #else AuMemcpy(reinterpret_cast(ptr) + offset, &value, sizeof(value)); #endif } template static auline void AuWriteGenericBE(volatile void *ptr, int offset, T value) { #if defined(AU_CPU_ENDIAN_LITTLE) value = AuFlipEndian(value); #endif #if defined(AURORA_PERMIT_ARBITRARY_REF) *reinterpret_cast(reinterpret_cast(ptr) + offset) = value; #else AuMemcpy(reinterpret_cast(ptr) + offset, &value, sizeof(value)); #endif } static auline void AuWriteU64LE(volatile void *ptr, int offset, AuUInt64 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteU32LE(volatile void *ptr, int offset, AuUInt32 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteU16LE(volatile void *ptr, int offset, AuUInt16 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteU8LE(volatile void *ptr, int offset, AuUInt8 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteS64LE(volatile void *ptr, int offset, AuInt64 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteS32LE(volatile void *ptr, int offset, AuInt32 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteS16LE(volatile void *ptr, int offset, AuInt16 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteS8LE(volatile void *ptr, int offset, AuInt8 value) { AuWriteGenericLE(ptr, offset, value); } static auline void AuWriteU64BE(volatile void *ptr, int offset, AuUInt64 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteU32BE(volatile void *ptr, int offset, AuUInt32 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteU16BE(volatile void *ptr, int offset, AuUInt16 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteU8BE(volatile void *ptr, int offset, AuUInt8 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteS64BE(volatile void *ptr, int offset, AuInt64 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteS32BE(volatile void *ptr, int offset, AuInt32 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteS16BE(volatile void *ptr, int offset, AuInt16 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteS8BE(volatile void *ptr, int offset, AuInt8 value) { AuWriteGenericBE(ptr, offset, value); } static auline void AuWriteU64(volatile void *ptr, int offset, AuUInt64 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteU64LE(ptr, offset, value); #else AuWriteU64BE(ptr, offset, value); #endif } static auline void AuWriteU32(volatile void *ptr, int offset, AuUInt32 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteU32LE(ptr, offset, value); #else AuWriteU32BE(ptr, offset, value); #endif } static auline void AuWriteU16(volatile void *ptr, int offset, AuUInt16 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteU16LE(ptr, offset, value); #else AuWriteU16BE(ptr, offset, value); #endif } static auline void AuWriteU8(volatile void *ptr, int offset, AuUInt8 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteU8LE(ptr, offset, value); #else AuWriteU8BE(ptr, offset, value); #endif } static auline void AuWriteS64(volatile void *ptr, int offset, AuInt64 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteS64LE(ptr, offset, value); #else AuWriteS64BE(ptr, offset, value); #endif } static auline void AuWriteS32(volatile void *ptr, int offset, AuInt32 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteS32LE(ptr, offset, value); #else AuWriteS32BE(ptr, offset, value); #endif } static auline void AuWriteS16(volatile void *ptr, int offset, AuInt16 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteS16LE(ptr, offset, value); #else AuWriteS16BE(ptr, offset, value); #endif } static auline void AuWriteS8(volatile void *ptr, int offset, AuInt8 value) { #if defined(AU_CPU_ENDIAN_LITTLE) AuWriteS8LE(ptr, offset, value); #else AuWriteS8BE(ptr, offset, value); #endif }