Linux-2.6.12-rc2

Initial git repository build. I'm not bothering with the full history,
even though we have it. We can create a separate "historical" git
archive of that later if we want to, and in the meantime it's about
3.2GB when imported into git - space that would just make the early
git days unnecessarily complicated, when we don't have a lot of good
infrastructure for it.

Let it rip!
diff --git a/include/asm-frv/unaligned.h b/include/asm-frv/unaligned.h
new file mode 100644
index 0000000..a0d199b
--- /dev/null
+++ b/include/asm-frv/unaligned.h
@@ -0,0 +1,203 @@
+/* unaligned.h: unaligned access handler
+ *
+ * Copyright (C) 2004 Red Hat, Inc. All Rights Reserved.
+ * Written by David Howells (dhowells@redhat.com)
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ */
+
+#ifndef _ASM_UNALIGNED_H
+#define _ASM_UNALIGNED_H
+
+#include <linux/config.h>
+
+/*
+ * Unaligned accesses on uClinux can't be performed in a fault handler - the
+ * CPU detects them as imprecise exceptions making this impossible.
+ *
+ * With the FR451, however, they are precise, and so we used to fix them up in
+ * the memory access fault handler.  However, instruction bundling make this
+ * impractical.  So, now we fall back to using memcpy.
+ */
+#ifdef CONFIG_MMU
+
+/*
+ * The asm statement in the macros below is a way to get GCC to copy a
+ * value from one variable to another without having any clue it's
+ * actually doing so, so that it won't have any idea that the values
+ * in the two variables are related.
+ */
+
+#define get_unaligned(ptr) ({				\
+	typeof((*(ptr))) __x;				\
+	void *__ptrcopy;				\
+	asm("" : "=r" (__ptrcopy) : "0" (ptr));		\
+	memcpy(&__x, __ptrcopy, sizeof(*(ptr)));	\
+	__x;						\
+})
+
+#define put_unaligned(val, ptr) ({			\
+	typeof((*(ptr))) __x = (val);			\
+	void *__ptrcopy;				\
+	asm("" : "=r" (__ptrcopy) : "0" (ptr));		\
+	memcpy(__ptrcopy, &__x, sizeof(*(ptr)));	\
+})
+
+extern int handle_misalignment(unsigned long esr0, unsigned long ear0, unsigned long epcr0);
+
+#else
+
+#define get_unaligned(ptr)							\
+({										\
+	typeof(*(ptr)) x;							\
+	const char *__p = (const char *) (ptr);					\
+										\
+	switch (sizeof(x)) {							\
+	case 1:									\
+		x = *(ptr);							\
+		break;								\
+	case 2:									\
+	{									\
+		uint8_t a;							\
+		asm("	ldub%I2		%M2,%0		\n"			\
+		    "	ldub%I3.p	%M3,%1		\n"			\
+		    "	slli		%0,#8,%0	\n"			\
+		    "	or		%0,%1,%0	\n"			\
+		    : "=&r"(x), "=&r"(a)					\
+		    : "m"(__p[0]),  "m"(__p[1])					\
+		    );								\
+		break;								\
+	}									\
+										\
+	case 4:									\
+	{									\
+		uint8_t a;							\
+		asm("	ldub%I2		%M2,%0		\n"			\
+		    "	ldub%I3.p	%M3,%1		\n"			\
+		    "	slli		%0,#8,%0	\n"			\
+		    "	or		%0,%1,%0	\n"			\
+		    "	ldub%I4.p	%M4,%1		\n"			\
+		    "	slli		%0,#8,%0	\n"			\
+		    "	or		%0,%1,%0	\n"			\
+		    "	ldub%I5.p	%M5,%1		\n"			\
+		    "	slli		%0,#8,%0	\n"			\
+		    "	or		%0,%1,%0	\n"			\
+		    : "=&r"(x), "=&r"(a)					\
+		    : "m"(__p[0]),  "m"(__p[1]), "m"(__p[2]), "m"(__p[3])	\
+		    );								\
+		break;								\
+	}									\
+										\
+	case 8:									\
+	{									\
+		union { uint64_t x; u32 y[2]; } z;				\
+		uint8_t a;							\
+		asm("	ldub%I3		%M3,%0		\n"			\
+		    "	ldub%I4.p	%M4,%2		\n"			\
+		    "	slli		%0,#8,%0	\n"			\
+		    "	or		%0,%2,%0	\n"			\
+		    "	ldub%I5.p	%M5,%2		\n"			\
+		    "	slli		%0,#8,%0	\n"			\
+		    "	or		%0,%2,%0	\n"			\
+		    "	ldub%I6.p	%M6,%2		\n"			\
+		    "	slli		%0,#8,%0	\n"			\
+		    "	or		%0,%2,%0	\n"			\
+		    "	ldub%I7		%M7,%1		\n"			\
+		    "	ldub%I8.p	%M8,%2		\n"			\
+		    "	slli		%1,#8,%1	\n"			\
+		    "	or		%1,%2,%1	\n"			\
+		    "	ldub%I9.p	%M9,%2		\n"			\
+		    "	slli		%1,#8,%1	\n"			\
+		    "	or		%1,%2,%1	\n"			\
+		    "	ldub%I10.p	%M10,%2		\n"			\
+		    "	slli		%1,#8,%1	\n"			\
+		    "	or		%1,%2,%1	\n"			\
+		    : "=&r"(z.y[0]), "=&r"(z.y[1]), "=&r"(a)			\
+		    : "m"(__p[0]), "m"(__p[1]), "m"(__p[2]), "m"(__p[3]),	\
+		      "m"(__p[4]), "m"(__p[5]), "m"(__p[6]), "m"(__p[7])	\
+		    );								\
+		x = z.x;							\
+		break;								\
+	}									\
+										\
+	default:								\
+		x = 0;								\
+		BUG();								\
+		break;								\
+	}									\
+										\
+	x;									\
+})
+
+#define put_unaligned(val, ptr)								\
+do {											\
+	char *__p = (char *) (ptr);							\
+	int x;										\
+											\
+	switch (sizeof(*ptr)) {								\
+	case 2:										\
+	{										\
+		asm("	stb%I1.p	%0,%M1		\n"				\
+		    "	srli		%0,#8,%0	\n"				\
+		    "	stb%I2		%0,%M2		\n"				\
+		    : "=r"(x), "=m"(__p[1]),  "=m"(__p[0])				\
+		    : "0"(val)								\
+		    );									\
+		break;									\
+	}										\
+											\
+	case 4:										\
+	{										\
+		asm("	stb%I1.p	%0,%M1		\n"				\
+		    "	srli		%0,#8,%0	\n"				\
+		    "	stb%I2.p	%0,%M2		\n"				\
+		    "	srli		%0,#8,%0	\n"				\
+		    "	stb%I3.p	%0,%M3		\n"				\
+		    "	srli		%0,#8,%0	\n"				\
+		    "	stb%I4		%0,%M4		\n"				\
+		    : "=r"(x), "=m"(__p[3]),  "=m"(__p[2]), "=m"(__p[1]), "=m"(__p[0])	\
+		    : "0"(val)								\
+		    );									\
+		break;									\
+	}										\
+											\
+	case 8:										\
+	{										\
+		uint32_t __high, __low;							\
+		__high = (uint64_t)val >> 32;						\
+		__low = val & 0xffffffff;						\
+		asm("	stb%I2.p	%0,%M2		\n"				\
+		    "	srli		%0,#8,%0	\n"				\
+		    "	stb%I3.p	%0,%M3		\n"				\
+		    "	srli		%0,#8,%0	\n"				\
+		    "	stb%I4.p	%0,%M4		\n"				\
+		    "	srli		%0,#8,%0	\n"				\
+		    "	stb%I5.p	%0,%M5		\n"				\
+		    "	srli		%0,#8,%0	\n"				\
+		    "	stb%I6.p	%1,%M6		\n"				\
+		    "	srli		%1,#8,%1	\n"				\
+		    "	stb%I7.p	%1,%M7		\n"				\
+		    "	srli		%1,#8,%1	\n"				\
+		    "	stb%I8.p	%1,%M8		\n"				\
+		    "	srli		%1,#8,%1	\n"				\
+		    "	stb%I9		%1,%M9		\n"				\
+		    : "=&r"(__low), "=&r"(__high), "=m"(__p[7]), "=m"(__p[6]), 		\
+		      "=m"(__p[5]), "=m"(__p[4]), "=m"(__p[3]), "=m"(__p[2]), 		\
+		      "=m"(__p[1]), "=m"(__p[0])					\
+		    : "0"(__low), "1"(__high)						\
+		    );									\
+		break;									\
+	}										\
+											\
+        default:									\
+		*(ptr) = (val);								\
+		break;									\
+	}										\
+} while(0)
+
+#endif
+
+#endif