]> git.xonotic.org Git - xonotic/gmqcc.git/blobdiff - util.c
Fix util_endianswap; and endianswap the LNO data as well
[xonotic/gmqcc.git] / util.c
diff --git a/util.c b/util.c
index d7e325dbde1bad4842063837ac9d17fc3dec0ab1..03cf40efda956590f2c8c97a0c545b3e6e4e1c1f 100644 (file)
--- a/util.c
+++ b/util.c
@@ -135,7 +135,7 @@ void *util_memory_r(void *ptrn, size_t byte, unsigned int line, const char *file
 void util_meminfo() {
     struct memblock_t *info;
 
-    if (!opts_memchk)
+    if (!opts.memchk)
         return;
 
     for (info = mem_start; info; info = info->next) {
@@ -246,10 +246,10 @@ bool util_strncmpexact(const char *src, const char *ned, size_t len) {
 
 void util_debug(const char *area, const char *ms, ...) {
     va_list  va;
-    if (!opts_debug)
+    if (!opts.debug)
         return;
 
-    if (!strcmp(area, "MEM") && !opts_memchk)
+    if (!strcmp(area, "MEM") && !opts.memchk)
         return;
 
     va_start(va, ms);
@@ -263,6 +263,7 @@ void util_debug(const char *area, const char *ms, ...) {
  * reorders by stride and length, much nicer than other functions for
  * certian-sized types like short or int.
  */
+#if 0
 void util_endianswap(void *m, int s, int l) {
     size_t w = 0;
     size_t i = 0;
@@ -280,6 +281,64 @@ void util_endianswap(void *m, int s, int l) {
         }
     }
 }
+#endif
+
+static void util_swap16(uint16_t *d, size_t l) {
+    while (l--) {
+        d[l] = (d[l] << 8) | (d[l] >> 8);
+    }
+}
+
+static void util_swap32(uint32_t *d, size_t l) {
+    while (l--) {
+        uint32_t v;
+        v = ((d[l] << 8) & 0xFF00FF00) | ((d[l] >> 8) & 0x00FF00FF);
+        d[l] = (v << 16) | (v >> 16);
+    }
+}
+
+/* Some strange system doesn't like constants that big, AND doesn't recognize an ULL suffix
+ * so let's go the safe way
+ */
+static void util_swap64(uint32_t *d, size_t l) {
+    /*
+    while (l--) {
+        uint64_t v;
+        v = ((d[l] << 8) & 0xFF00FF00FF00FF00) | ((d[l] >> 8) & 0x00FF00FF00FF00FF);
+        v = ((v << 16) & 0xFFFF0000FFFF0000) | ((v >> 16) & 0x0000FFFF0000FFFF);
+        d[l] = (v << 32) | (v >> 32);
+    }
+    */
+    size_t i;
+    for (i = 0; i < l; i += 2) {
+        uint32_t v1 = d[i];
+        d[i] = d[i+1];
+        d[i+1] = v1;
+        util_swap32(d+i, 2);
+    }
+}
+
+void util_endianswap(void *_data, size_t length, unsigned int typesize) {
+    /* I'm guessing there's no GOOD way to do this at compile time:
+     * FIXME:
+     */
+    if (*((char*)&typesize))
+        return;
+    if (typesize == 1)
+        return;
+    if (typesize == 2) {
+        util_swap16((uint16_t*)_data, length>>1);
+        return;
+    }
+    if (typesize == 4) {
+        util_swap32((uint32_t*)_data, length>>2);
+        return;
+    }
+    if (typesize == 4) {
+        util_swap64((uint32_t*)_data, length>>3);
+        return;
+    }
+}
 
 /*
  * CRC algorithms vary in the width of the polynomial, the value of said polynomial,
@@ -495,7 +554,7 @@ size_t util_strtononcmd(const char *in, char *out, size_t outsz) {
 
 FILE *util_fopen(const char *filename, const char *mode)
 {
-#ifdef WIN32
+#ifdef _MSC_VER
     FILE *out;
     if (fopen_s(&out, filename, mode) != 0)
         return NULL;
@@ -533,7 +592,7 @@ typedef struct hash_node_t {
  * below.  These should be autovectorized by gcc.
  */
 #ifdef __x86_64__
-GMQCC_INLINE uint32_t util_hthashfunc(hash_table_t *ht, const char *key, register size_t seed) {
+GMQCC_INLINE uint32_t util_hthashfunc(hash_table_t *ht, const char *key, size_t seed) {
     const uint64_t       mix   = 0xC6A4A7935BD1E995;
     const int            rot   = 47;
     size_t               size  = strlen(key);
@@ -575,13 +634,13 @@ GMQCC_INLINE uint32_t util_hthashfunc(hash_table_t *ht, const char *key, registe
 }
 
 #else
-GMQCC_INLINE uint32_t util_hthashfunc(hash_table_t *ht, const char *key, register size_t seed) {
+GMQCC_INLINE uint32_t util_hthashfunc(hash_table_t *ht, const char *key, size_t seed) {
     const uint32_t       mix   = 0x5BD1E995;
     const uint32_t       rot   = 24;
     size_t               size  = strlen(key);
     uint32_t             hash  = seed ^ size;
     uint32_t             alias = 0;
-    const unsigned char *data  = (const unsigned char*)ket;
+    const unsigned char *data  = (const unsigned char*)key;
 
     while (size >= 4) {
         alias = *(uint32_t*)data;