changeset 1399:a0c328bc2c14 draft

Little endian and big endian versions of peek (for host.c).
author Rob Landley <rob@landley.net>
date Mon, 21 Jul 2014 19:56:53 -0500
parents 7402cae7889f
children 31cb9ba1815c
files lib/lib.c lib/lib.h
diffstat 2 files changed, 27 insertions(+), 15 deletions(-) [+]
line wrap: on
line diff
--- a/lib/lib.c	Mon Jul 21 19:55:06 2014 -0500
+++ b/lib/lib.c	Mon Jul 21 19:56:53 2014 -0500
@@ -372,21 +372,31 @@
   nanosleep(&ts, &ts);
 }
 
-int64_t peek(void *ptr, int size)
+// Inefficient, but deals with unaligned access
+int64_t peek_le(void *ptr, unsigned size)
 {
-  if (size & 8) {
-    volatile int64_t *p = (int64_t *)ptr;
-    return *p;
-  } else if (size & 4) {
-    volatile int *p = (int *)ptr;
-    return *p;
-  } else if (size & 2) {
-    volatile short *p = (short *)ptr;
-    return *p;
-  } else {
-    volatile char *p = (char *)ptr;
-    return *p;
-  }
+  int64_t ret = 0;
+  char *c = ptr;
+  int i;
+
+  for (i=0; i<size; i++) ret |= ((int64_t)c[i])<<i;
+
+  return ret;
+}
+
+int64_t peek_be(void *ptr, unsigned size)
+{
+  int64_t ret = 0;
+  char *c = ptr;
+
+  while (size--) ret = (ret<<8)|c[size];
+
+  return ret;
+}
+
+int64_t peek(void *ptr, unsigned size)
+{
+  return IS_BIG_ENDIAN ? peek_be(ptr, size) : peek_le(ptr, size);
 }
 
 void poke(void *ptr, uint64_t val, int size)
--- a/lib/lib.h	Mon Jul 21 19:55:06 2014 -0500
+++ b/lib/lib.h	Mon Jul 21 19:56:53 2014 -0500
@@ -138,7 +138,9 @@
 struct string_list **splitpath(char *path, struct string_list **list);
 char *readfile(char *name, char *buf, off_t len);
 void msleep(long miliseconds);
-int64_t peek(void *ptr, int size);
+int64_t peek_le(void *ptr, unsigned size);
+int64_t peek_be(void *ptr, unsigned size);
+int64_t peek(void *ptr, unsigned size);
 void poke(void *ptr, uint64_t val, int size);
 struct string_list *find_in_path(char *path, char *filename);
 long atolx(char *c);