Re: [RFC PATCH] m68k: GENERIC_IOMAP support (take #2)

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi Geert,

Note that both 16 and 32 bit accesses will return 8 bit results only, due
to the way the address and data bus are wired on the ROM ISA adapter. I
hope this is the correct behavior.

I don't think that's correct. Shouldn't 16-bit resp. 32-bit accesses be
emulated using 2 resp. 4 8-bit accesses instead?

OK, this emulates word and longword access by multiple byte accesses.
Goes on top of my previous patch (and should be included in the Debian
package).

	Michael

--- include/asm-m68k/raw_io.h.ms-submitted	2006-11-07 13:07:43.000000000 +0100
+++ include/asm-m68k/raw_io.h	2007-05-31 15:31:25.000000000 +0200
@@ -62,28 +62,74 @@
  *
  * Data lines D8-D15 are connected to ISA data lines D0-D7 for reading.
  * For writes, address lines A1-A8 are latched to ISA data lines D0-D7
- * (meaning the bit pattern on A1-A8 can be read back as byte).
+ * (meaning the bit pattern on A1-A8 can be read back as byte on D8-D15).
+ *
+ * Proper conversion of addr (i.e., shifting address bits 0-4 up by 9 bits)
+ * has to be taken care of by ISA address translation code in caller. The
+ * offset of 0x10000 in the write functions is the offset between read and
+ * write ROM base address (/ROM3 vs /ROM4)
+ *
+ * Reads and writes are byte only. Data arrive in the high byte of a word,
+ * hence the shifts.
  *
- * Reads and writes are byte only.
+ * For word and longword accesses, emulate by byte-wise reads and shifts.
  */

 #if defined(CONFIG_ATARI_ROM_ISA)
 #define rom_in_8(addr) \
     ({ u16 __v = (*(__force volatile u16 *) (addr)); __v >>= 8; __v; })
 #define rom_in_be16(addr) \
-    ({ u16 __v = (*(__force volatile u16 *) (addr)); __v >>= 8; __v; })
+    ({ u16 __w = (*(__force volatile u16 *) (addr)); \
+       u16 __v = (*(__force volatile u16 *) (addr)); __w &= __v >> 8; __w; })
 #define rom_in_be32(addr) \
-    ({ u32 __v = (*(__force volatile u32 *) (addr)); __v >>= 8; __v; })
+    ({ u32 __y = (*(__force volatile u32 *) (addr)); \
+       u32 __x = (*(__force volatile u32 *) (addr)); \
+       u32 __w = (*(__force volatile u32 *) (addr)); \
+       u32 __v = (*(__force volatile u32 *) (addr)); __y &= __x >> 8; __w &= __v >> 8; __w &= __y << 16; __w; })
 #define rom_in_le16(addr) \
-    ({ u16 __v = le16_to_cpu(*(__force volatile u16 *) (addr)); __v >>= 8; __v; })
+    ({ u16 __v = (*(__force volatile u16 *) (addr)); \
+       u16 __w = (*(__force volatile u16 *) (addr)); __w &= __v >> 8; __w; })
 #define rom_in_le32(addr) \
-    ({ u32 __v = le32_to_cpu(*(__force volatile u32 *) (addr)); __v >>= 8; __v; })
-
-#define rom_out_8(addr,b)     ({u8 __w, __v = (b);            __w = ((*(__force volatile u8 *)  ((addr) + 0x10000 + (__v<<1)))); })
-#define rom_out_be16(addr,w) ({u16 __w, __v = (w);            __w = ((*(__force volatile u16 *) ((addr) + 0x10000 + (__v<<1)))); })
-#define rom_out_be32(addr,l) ({u32 __w, __v = (l);            __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); })
-#define rom_out_le16(addr,w) ({u16 __w, __v = cpu_to_le16(w); __w = ((*(__force volatile u16 *) ((addr) + 0x10000 + (__v<<1)))); })
-#define rom_out_le32(addr,l) ({u32 __w, __v = cpu_to_le32(l); __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); })
+    ({ u32 __v = (*(__force volatile u32 *) (addr)); \
+       u32 __w = (*(__force volatile u32 *) (addr)); \
+       u32 __x = (*(__force volatile u32 *) (addr)); \
+       u32 __y = (*(__force volatile u32 *) (addr)); __y &= __x >> 8; __w &= __v >> 8; __w &= __y << 16; __w; })
+
+#define rom_out_8(addr,b) \
+    ({u8 __w, __v = (b);  \
+	 __w = ((*(__force volatile u8 *)  ((addr) + 0x10000 + (__v<<1)))); })
+#define rom_out_be16(addr,w)                                                 \
+    ({u16 __w, __v;                                                          \
+	  __v = (w) >> 8;                                                    \
+	  __w = ((*(__force volatile u16 *) ((addr) + 0x10000 + (__v<<1)))); \
+	  __v = (w) & 0x0f;                                                  \
+	  __w = ((*(__force volatile u16 *) ((addr) + 0x10000 + (__v<<1)))); })
+#define rom_out_be32(addr,l)                                                 \
+    ({u32 __w, __v;                                                          \
+	  __v =  (l) >> 24;                                                  \
+    	  __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); \
+	  __v = ((l) >> 16) & 0x0f;                                          \
+    	  __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); \
+	  __v = ((l) >> 8)  & 0x0f;                                          \
+    	  __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); \
+	  __v =  (l) & 0x0f;                                                 \
+    	  __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); })
+#define rom_out_le16(addr,w)                                                 \
+    ({u16 __w, __v;                                                          \
+	  __v = (w) & 0x0f;                                                  \
+	  __w = ((*(__force volatile u16 *) ((addr) + 0x10000 + (__v<<1)))); \
+	  __v = (w) >> 8;                                                    \
+	  __w = ((*(__force volatile u16 *) ((addr) + 0x10000 + (__v<<1)))); })
+#define rom_out_le32(addr,l)                                                 \
+    ({u32 __w, __v;                                                          \
+	  __v =  (l) & 0x0f;                                                 \
+    	  __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); \
+	  __v = ((l) >> 8)  & 0x0f;                                          \
+    	  __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); \
+	  __v = ((l) >> 16) & 0x0f;                                          \
+    	  __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); \
+	  __v =  (l) >> 24;                                                  \
+    	  __w = ((*(__force volatile u32 *) ((addr) + 0x10000 + (__v<<1)))); })

 #define raw_rom_inb rom_in_8
 #define raw_rom_inw rom_in_be16

-
To unsubscribe from this list: send the line "unsubscribe linux-m68k" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at  http://vger.kernel.org/majordomo-info.html

[Index of Archives]     [Video for Linux]     [Yosemite News]     [Linux S/390]     [Linux Kernel]     [Linux SCSI]

  Powered by Linux