aboutsummaryrefslogtreecommitdiff
path: root/include/exec/tswap.h
diff options
context:
space:
mode:
Diffstat (limited to 'include/exec/tswap.h')
-rw-r--r--include/exec/tswap.h72
1 files changed, 72 insertions, 0 deletions
diff --git a/include/exec/tswap.h b/include/exec/tswap.h
new file mode 100644
index 0000000000..68944a880b
--- /dev/null
+++ b/include/exec/tswap.h
@@ -0,0 +1,72 @@
+/*
+ * Macros for swapping a value if the endianness is different
+ * between the target and the host.
+ *
+ * SPDX-License-Identifier: LGPL-2.1-or-later
+ */
+
+#ifndef TSWAP_H
+#define TSWAP_H
+
+#include "hw/core/cpu.h"
+#include "qemu/bswap.h"
+
+/*
+ * If we're in target-specific code, we can hard-code the swapping
+ * condition, otherwise we have to do (slower) run-time checks.
+ */
+#ifdef NEED_CPU_H
+#define target_needs_bswap() (HOST_BIG_ENDIAN != TARGET_BIG_ENDIAN)
+#else
+#define target_needs_bswap() (target_words_bigendian() != HOST_BIG_ENDIAN)
+#endif
+
+static inline uint16_t tswap16(uint16_t s)
+{
+ if (target_needs_bswap()) {
+ return bswap16(s);
+ } else {
+ return s;
+ }
+}
+
+static inline uint32_t tswap32(uint32_t s)
+{
+ if (target_needs_bswap()) {
+ return bswap32(s);
+ } else {
+ return s;
+ }
+}
+
+static inline uint64_t tswap64(uint64_t s)
+{
+ if (target_needs_bswap()) {
+ return bswap64(s);
+ } else {
+ return s;
+ }
+}
+
+static inline void tswap16s(uint16_t *s)
+{
+ if (target_needs_bswap()) {
+ *s = bswap16(*s);
+ }
+}
+
+static inline void tswap32s(uint32_t *s)
+{
+ if (target_needs_bswap()) {
+ *s = bswap32(*s);
+ }
+}
+
+static inline void tswap64s(uint64_t *s)
+{
+ if (target_needs_bswap()) {
+ *s = bswap64(*s);
+ }
+}
+
+#endif /* TSWAP_H */