using System; using System.Runtime.InteropServices; namespace Misaki.HighPerformance.Image.Runtime; internal static unsafe class CRuntime { private static readonly string s_numbers = "0123456789"; public static void* malloc(ulong size) { return malloc((long)size); } public static void* malloc(long size) { var ptr = NativeMemory.Alloc((nuint)size); MemoryStats.Allocated(); return ptr; } public static void free(void* ptr) { if (ptr == null) { return; } NativeMemory.Free(ptr); MemoryStats.Freed(); } public static void memcpy(void* a, void* b, long size) { NativeMemory.Copy(b, a, (nuint)size); } public static void memcpy(void* a, void* b, ulong size) { memcpy(a, b, (long)size); } public static void memmove(void* a, void* b, long size) { void* temp = null; try { temp = malloc(size); memcpy(temp, b, size); memcpy(a, temp, size); } finally { if (temp != null) { free(temp); } } } public static int memcmp(void* a, void* b, long size) { var result = 0; var ap = (byte*)a; var bp = (byte*)b; for (long i = 0; i < size; ++i) { if (*ap != *bp) { result += 1; } ap++; bp++; } return result; } public static void memset(void* ptr, int value, long size) { var bptr = (byte*)ptr; var bval = (byte)value; for (long i = 0; i < size; ++i) { *bptr++ = bval; } } public static void memset(void* ptr, int value, ulong size) { memset(ptr, value, (long)size); } public static uint _lrotl(uint x, int y) { return (x << y) | (x >> (32 - y)); } public static void* realloc(void* ptr, long newSize) { if (ptr == null) { return malloc(newSize); } var result = NativeMemory.Realloc(ptr, (nuint)newSize); return result; } public static void* realloc(void* a, ulong newSize) { return realloc(a, (long)newSize); } public static int abs(int v) { return Math.Abs(v); } public static double pow(double a, double b) { return Math.Pow(a, b); } public static double ldexp(double number, int exponent) { return number * Math.Pow(2, exponent); } public static int strcmp(sbyte* src, string token) { var result = 0; for (var i = 0; i < token.Length; ++i) { if (src[i] != token[i]) { ++result; } } return result; } public static int strncmp(sbyte* src, string token, ulong size) { var result = 0; for (var i = 0; i < Math.Min(token.Length, (int)size); ++i) { if (src[i] != token[i]) { ++result; } } return result; } public static long strtol(sbyte* start, sbyte** end, int radix) { // First step - determine length var length = 0; var ptr = start; while (s_numbers.IndexOf((char)*ptr) != -1) { ++ptr; ++length; } long result = 0; // Now build up the number ptr = start; while (length > 0) { long num = s_numbers.IndexOf((char)*ptr); var pow = (long)Math.Pow(10, length - 1); result += num * pow; ++ptr; --length; } if (end != null) { *end = ptr; } return result; } }