diff options
-rw-r--r-- | Documentation/devicetree/bindings/arm/altera.txt | 14 | ||||
-rw-r--r-- | Documentation/devicetree/bindings/arm/arch_timer.txt | 8 | ||||
-rw-r--r-- | Documentation/devicetree/bindings/common-properties.txt | 60 | ||||
-rw-r--r-- | Documentation/devicetree/bindings/vendor-prefixes.txt | 1 | ||||
-rw-r--r-- | arch/frv/include/asm/io.h | 5 | ||||
-rw-r--r-- | arch/mn10300/include/asm/io.h | 5 | ||||
-rw-r--r-- | drivers/of/Kconfig | 2 | ||||
-rw-r--r-- | drivers/of/base.c | 28 | ||||
-rw-r--r-- | drivers/of/fdt.c | 24 | ||||
-rw-r--r-- | drivers/of/unittest.c | 62 | ||||
-rw-r--r-- | drivers/tty/serial/8250/8250_core.c | 20 | ||||
-rw-r--r-- | drivers/tty/serial/8250/8250_early.c | 5 | ||||
-rw-r--r-- | drivers/tty/serial/of_serial.c | 3 | ||||
-rw-r--r-- | include/linux/of.h | 6 | ||||
-rw-r--r-- | include/linux/of_fdt.h | 2 | ||||
-rw-r--r-- | include/linux/of_irq.h | 9 |
16 files changed, 243 insertions, 11 deletions
diff --git a/Documentation/devicetree/bindings/arm/altera.txt b/Documentation/devicetree/bindings/arm/altera.txt new file mode 100644 index 000000000000..558735aacca8 --- /dev/null +++ b/Documentation/devicetree/bindings/arm/altera.txt | |||
@@ -0,0 +1,14 @@ | |||
1 | Altera's SoCFPGA platform device tree bindings | ||
2 | --------------------------------------------- | ||
3 | |||
4 | Boards with Cyclone 5 SoC: | ||
5 | Required root node properties: | ||
6 | compatible = "altr,socfpga-cyclone5", "altr,socfpga"; | ||
7 | |||
8 | Boards with Arria 5 SoC: | ||
9 | Required root node properties: | ||
10 | compatible = "altr,socfpga-arria5", "altr,socfpga"; | ||
11 | |||
12 | Boards with Arria 10 SoC: | ||
13 | Required root node properties: | ||
14 | compatible = "altr,socfpga-arria10", "altr,socfpga"; | ||
diff --git a/Documentation/devicetree/bindings/arm/arch_timer.txt b/Documentation/devicetree/bindings/arm/arch_timer.txt index 256b4d8bab7b..e774128935d5 100644 --- a/Documentation/devicetree/bindings/arm/arch_timer.txt +++ b/Documentation/devicetree/bindings/arm/arch_timer.txt | |||
@@ -17,7 +17,10 @@ to deliver its interrupts via SPIs. | |||
17 | - interrupts : Interrupt list for secure, non-secure, virtual and | 17 | - interrupts : Interrupt list for secure, non-secure, virtual and |
18 | hypervisor timers, in that order. | 18 | hypervisor timers, in that order. |
19 | 19 | ||
20 | - clock-frequency : The frequency of the main counter, in Hz. Optional. | 20 | - clock-frequency : The frequency of the main counter, in Hz. Should be present |
21 | only where necessary to work around broken firmware which does not configure | ||
22 | CNTFRQ on all CPUs to a uniform correct value. Use of this property is | ||
23 | strongly discouraged; fix your firmware unless absolutely impossible. | ||
21 | 24 | ||
22 | - always-on : a boolean property. If present, the timer is powered through an | 25 | - always-on : a boolean property. If present, the timer is powered through an |
23 | always-on power domain, therefore it never loses context. | 26 | always-on power domain, therefore it never loses context. |
@@ -46,7 +49,8 @@ Example: | |||
46 | 49 | ||
47 | - compatible : Should at least contain "arm,armv7-timer-mem". | 50 | - compatible : Should at least contain "arm,armv7-timer-mem". |
48 | 51 | ||
49 | - clock-frequency : The frequency of the main counter, in Hz. Optional. | 52 | - clock-frequency : The frequency of the main counter, in Hz. Should be present |
53 | only when firmware has not configured the MMIO CNTFRQ registers. | ||
50 | 54 | ||
51 | - reg : The control frame base address. | 55 | - reg : The control frame base address. |
52 | 56 | ||
diff --git a/Documentation/devicetree/bindings/common-properties.txt b/Documentation/devicetree/bindings/common-properties.txt new file mode 100644 index 000000000000..3193979b1d05 --- /dev/null +++ b/Documentation/devicetree/bindings/common-properties.txt | |||
@@ -0,0 +1,60 @@ | |||
1 | Common properties | ||
2 | |||
3 | The ePAPR specification does not define any properties related to hardware | ||
4 | byteswapping, but endianness issues show up frequently in porting Linux to | ||
5 | different machine types. This document attempts to provide a consistent | ||
6 | way of handling byteswapping across drivers. | ||
7 | |||
8 | Optional properties: | ||
9 | - big-endian: Boolean; force big endian register accesses | ||
10 | unconditionally (e.g. ioread32be/iowrite32be). Use this if you | ||
11 | know the peripheral always needs to be accessed in BE mode. | ||
12 | - little-endian: Boolean; force little endian register accesses | ||
13 | unconditionally (e.g. readl/writel). Use this if you know the | ||
14 | peripheral always needs to be accessed in LE mode. | ||
15 | - native-endian: Boolean; always use register accesses matched to the | ||
16 | endianness of the kernel binary (e.g. LE vmlinux -> readl/writel, | ||
17 | BE vmlinux -> ioread32be/iowrite32be). In this case no byteswaps | ||
18 | will ever be performed. Use this if the hardware "self-adjusts" | ||
19 | register endianness based on the CPU's configured endianness. | ||
20 | |||
21 | If a binding supports these properties, then the binding should also | ||
22 | specify the default behavior if none of these properties are present. | ||
23 | In such cases, little-endian is the preferred default, but it is not | ||
24 | a requirement. The of_device_is_big_endian() and of_fdt_is_big_endian() | ||
25 | helper functions do assume that little-endian is the default, because | ||
26 | most existing (PCI-based) drivers implicitly default to LE by using | ||
27 | readl/writel for MMIO accesses. | ||
28 | |||
29 | Examples: | ||
30 | Scenario 1 : CPU in LE mode & device in LE mode. | ||
31 | dev: dev@40031000 { | ||
32 | compatible = "name"; | ||
33 | reg = <0x40031000 0x1000>; | ||
34 | ... | ||
35 | native-endian; | ||
36 | }; | ||
37 | |||
38 | Scenario 2 : CPU in LE mode & device in BE mode. | ||
39 | dev: dev@40031000 { | ||
40 | compatible = "name"; | ||
41 | reg = <0x40031000 0x1000>; | ||
42 | ... | ||
43 | big-endian; | ||
44 | }; | ||
45 | |||
46 | Scenario 3 : CPU in BE mode & device in BE mode. | ||
47 | dev: dev@40031000 { | ||
48 | compatible = "name"; | ||
49 | reg = <0x40031000 0x1000>; | ||
50 | ... | ||
51 | native-endian; | ||
52 | }; | ||
53 | |||
54 | Scenario 4 : CPU in BE mode & device in LE mode. | ||
55 | dev: dev@40031000 { | ||
56 | compatible = "name"; | ||
57 | reg = <0x40031000 0x1000>; | ||
58 | ... | ||
59 | little-endian; | ||
60 | }; | ||
diff --git a/Documentation/devicetree/bindings/vendor-prefixes.txt b/Documentation/devicetree/bindings/vendor-prefixes.txt index 83737a3403d7..80339192c93e 100644 --- a/Documentation/devicetree/bindings/vendor-prefixes.txt +++ b/Documentation/devicetree/bindings/vendor-prefixes.txt | |||
@@ -26,6 +26,7 @@ aptina Aptina Imaging | |||
26 | arasan Arasan Chip Systems | 26 | arasan Arasan Chip Systems |
27 | arm ARM Ltd. | 27 | arm ARM Ltd. |
28 | armadeus ARMadeus Systems SARL | 28 | armadeus ARMadeus Systems SARL |
29 | artesyn Artesyn Embedded Technologies Inc. | ||
29 | asahi-kasei Asahi Kasei Corp. | 30 | asahi-kasei Asahi Kasei Corp. |
30 | atmel Atmel Corporation | 31 | atmel Atmel Corporation |
31 | auo AU Optronics Corporation | 32 | auo AU Optronics Corporation |
diff --git a/arch/frv/include/asm/io.h b/arch/frv/include/asm/io.h index 99bb7efaf9b7..0b78bc89e840 100644 --- a/arch/frv/include/asm/io.h +++ b/arch/frv/include/asm/io.h | |||
@@ -342,6 +342,11 @@ static inline void iowrite32(u32 val, void __iomem *p) | |||
342 | __flush_PCI_writes(); | 342 | __flush_PCI_writes(); |
343 | } | 343 | } |
344 | 344 | ||
345 | #define ioread16be(addr) be16_to_cpu(ioread16(addr)) | ||
346 | #define ioread32be(addr) be32_to_cpu(ioread32(addr)) | ||
347 | #define iowrite16be(v, addr) iowrite16(cpu_to_be16(v), (addr)) | ||
348 | #define iowrite32be(v, addr) iowrite32(cpu_to_be32(v), (addr)) | ||
349 | |||
345 | static inline void ioread8_rep(void __iomem *p, void *dst, unsigned long count) | 350 | static inline void ioread8_rep(void __iomem *p, void *dst, unsigned long count) |
346 | { | 351 | { |
347 | io_insb((unsigned long) p, dst, count); | 352 | io_insb((unsigned long) p, dst, count); |
diff --git a/arch/mn10300/include/asm/io.h b/arch/mn10300/include/asm/io.h index 897ba3c12b32..cc4a2ba9e228 100644 --- a/arch/mn10300/include/asm/io.h +++ b/arch/mn10300/include/asm/io.h | |||
@@ -197,6 +197,11 @@ static inline void outsl(unsigned long addr, const void *buffer, int count) | |||
197 | #define iowrite16(v, addr) writew((v), (addr)) | 197 | #define iowrite16(v, addr) writew((v), (addr)) |
198 | #define iowrite32(v, addr) writel((v), (addr)) | 198 | #define iowrite32(v, addr) writel((v), (addr)) |
199 | 199 | ||
200 | #define ioread16be(addr) be16_to_cpu(readw(addr)) | ||
201 | #define ioread32be(addr) be32_to_cpu(readl(addr)) | ||
202 | #define iowrite16be(v, addr) writew(cpu_to_be16(v), (addr)) | ||
203 | #define iowrite32be(v, addr) writel(cpu_to_be32(v), (addr)) | ||
204 | |||
200 | #define ioread8_rep(p, dst, count) \ | 205 | #define ioread8_rep(p, dst, count) \ |
201 | insb((unsigned long) (p), (dst), (count)) | 206 | insb((unsigned long) (p), (dst), (count)) |
202 | #define ioread16_rep(p, dst, count) \ | 207 | #define ioread16_rep(p, dst, count) \ |
diff --git a/drivers/of/Kconfig b/drivers/of/Kconfig index 1470b5227834..07bb3c8f191b 100644 --- a/drivers/of/Kconfig +++ b/drivers/of/Kconfig | |||
@@ -50,7 +50,7 @@ config OF_ADDRESS_PCI | |||
50 | 50 | ||
51 | config OF_IRQ | 51 | config OF_IRQ |
52 | def_bool y | 52 | def_bool y |
53 | depends on !SPARC | 53 | depends on !SPARC && IRQ_DOMAIN |
54 | 54 | ||
55 | config OF_NET | 55 | config OF_NET |
56 | depends on NETDEVICES | 56 | depends on NETDEVICES |
diff --git a/drivers/of/base.c b/drivers/of/base.c index a1aa0c7dee50..99764db0875a 100644 --- a/drivers/of/base.c +++ b/drivers/of/base.c | |||
@@ -568,6 +568,29 @@ bool of_device_is_available(const struct device_node *device) | |||
568 | EXPORT_SYMBOL(of_device_is_available); | 568 | EXPORT_SYMBOL(of_device_is_available); |
569 | 569 | ||
570 | /** | 570 | /** |
571 | * of_device_is_big_endian - check if a device has BE registers | ||
572 | * | ||
573 | * @device: Node to check for endianness | ||
574 | * | ||
575 | * Returns true if the device has a "big-endian" property, or if the kernel | ||
576 | * was compiled for BE *and* the device has a "native-endian" property. | ||
577 | * Returns false otherwise. | ||
578 | * | ||
579 | * Callers would nominally use ioread32be/iowrite32be if | ||
580 | * of_device_is_big_endian() == true, or readl/writel otherwise. | ||
581 | */ | ||
582 | bool of_device_is_big_endian(const struct device_node *device) | ||
583 | { | ||
584 | if (of_property_read_bool(device, "big-endian")) | ||
585 | return true; | ||
586 | if (IS_ENABLED(CONFIG_CPU_BIG_ENDIAN) && | ||
587 | of_property_read_bool(device, "native-endian")) | ||
588 | return true; | ||
589 | return false; | ||
590 | } | ||
591 | EXPORT_SYMBOL(of_device_is_big_endian); | ||
592 | |||
593 | /** | ||
571 | * of_get_parent - Get a node's parent if any | 594 | * of_get_parent - Get a node's parent if any |
572 | * @node: Node to get parent | 595 | * @node: Node to get parent |
573 | * | 596 | * |
@@ -640,8 +663,9 @@ static struct device_node *__of_get_next_child(const struct device_node *node, | |||
640 | * @node: parent node | 663 | * @node: parent node |
641 | * @prev: previous child of the parent node, or NULL to get first | 664 | * @prev: previous child of the parent node, or NULL to get first |
642 | * | 665 | * |
643 | * Returns a node pointer with refcount incremented, use | 666 | * Returns a node pointer with refcount incremented, use of_node_put() on |
644 | * of_node_put() on it when done. | 667 | * it when done. Returns NULL when prev is the last child. Decrements the |
668 | * refcount of prev. | ||
645 | */ | 669 | */ |
646 | struct device_node *of_get_next_child(const struct device_node *node, | 670 | struct device_node *of_get_next_child(const struct device_node *node, |
647 | struct device_node *prev) | 671 | struct device_node *prev) |
diff --git a/drivers/of/fdt.c b/drivers/of/fdt.c index 3a896c9aeb74..cde35c5d0191 100644 --- a/drivers/of/fdt.c +++ b/drivers/of/fdt.c | |||
@@ -109,6 +109,25 @@ int of_fdt_is_compatible(const void *blob, | |||
109 | } | 109 | } |
110 | 110 | ||
111 | /** | 111 | /** |
112 | * of_fdt_is_big_endian - Return true if given node needs BE MMIO accesses | ||
113 | * @blob: A device tree blob | ||
114 | * @node: node to test | ||
115 | * | ||
116 | * Returns true if the node has a "big-endian" property, or if the kernel | ||
117 | * was compiled for BE *and* the node has a "native-endian" property. | ||
118 | * Returns false otherwise. | ||
119 | */ | ||
120 | bool of_fdt_is_big_endian(const void *blob, unsigned long node) | ||
121 | { | ||
122 | if (fdt_getprop(blob, node, "big-endian", NULL)) | ||
123 | return true; | ||
124 | if (IS_ENABLED(CONFIG_CPU_BIG_ENDIAN) && | ||
125 | fdt_getprop(blob, node, "native-endian", NULL)) | ||
126 | return true; | ||
127 | return false; | ||
128 | } | ||
129 | |||
130 | /** | ||
112 | * of_fdt_match - Return true if node matches a list of compatible values | 131 | * of_fdt_match - Return true if node matches a list of compatible values |
113 | */ | 132 | */ |
114 | int of_fdt_match(const void *blob, unsigned long node, | 133 | int of_fdt_match(const void *blob, unsigned long node, |
@@ -172,7 +191,7 @@ static void * unflatten_dt_node(void *blob, | |||
172 | if (!pathp) | 191 | if (!pathp) |
173 | return mem; | 192 | return mem; |
174 | 193 | ||
175 | allocl = l++; | 194 | allocl = ++l; |
176 | 195 | ||
177 | /* version 0x10 has a more compact unit name here instead of the full | 196 | /* version 0x10 has a more compact unit name here instead of the full |
178 | * path. we accumulate the full path size using "fpsize", we'll rebuild | 197 | * path. we accumulate the full path size using "fpsize", we'll rebuild |
@@ -879,8 +898,7 @@ int __init early_init_dt_scan_memory(unsigned long node, const char *uname, | |||
879 | 898 | ||
880 | endp = reg + (l / sizeof(__be32)); | 899 | endp = reg + (l / sizeof(__be32)); |
881 | 900 | ||
882 | pr_debug("memory scan node %s, reg size %d, data: %x %x %x %x,\n", | 901 | pr_debug("memory scan node %s, reg size %d,\n", uname, l); |
883 | uname, l, reg[0], reg[1], reg[2], reg[3]); | ||
884 | 902 | ||
885 | while ((endp - reg) >= (dt_root_addr_cells + dt_root_size_cells)) { | 903 | while ((endp - reg) >= (dt_root_addr_cells + dt_root_size_cells)) { |
886 | u64 base, size; | 904 | u64 base, size; |
diff --git a/drivers/of/unittest.c b/drivers/of/unittest.c index e844907c9efa..18016341d5a9 100644 --- a/drivers/of/unittest.c +++ b/drivers/of/unittest.c | |||
@@ -23,6 +23,8 @@ | |||
23 | #include <linux/i2c.h> | 23 | #include <linux/i2c.h> |
24 | #include <linux/i2c-mux.h> | 24 | #include <linux/i2c-mux.h> |
25 | 25 | ||
26 | #include <linux/bitops.h> | ||
27 | |||
26 | #include "of_private.h" | 28 | #include "of_private.h" |
27 | 29 | ||
28 | static struct unittest_results { | 30 | static struct unittest_results { |
@@ -1109,6 +1111,59 @@ static const char *overlay_path(int nr) | |||
1109 | 1111 | ||
1110 | static const char *bus_path = "/testcase-data/overlay-node/test-bus"; | 1112 | static const char *bus_path = "/testcase-data/overlay-node/test-bus"; |
1111 | 1113 | ||
1114 | /* it is guaranteed that overlay ids are assigned in sequence */ | ||
1115 | #define MAX_UNITTEST_OVERLAYS 256 | ||
1116 | static unsigned long overlay_id_bits[BITS_TO_LONGS(MAX_UNITTEST_OVERLAYS)]; | ||
1117 | static int overlay_first_id = -1; | ||
1118 | |||
1119 | static void of_unittest_track_overlay(int id) | ||
1120 | { | ||
1121 | if (overlay_first_id < 0) | ||
1122 | overlay_first_id = id; | ||
1123 | id -= overlay_first_id; | ||
1124 | |||
1125 | /* we shouldn't need that many */ | ||
1126 | BUG_ON(id >= MAX_UNITTEST_OVERLAYS); | ||
1127 | overlay_id_bits[BIT_WORD(id)] |= BIT_MASK(id); | ||
1128 | } | ||
1129 | |||
1130 | static void of_unittest_untrack_overlay(int id) | ||
1131 | { | ||
1132 | if (overlay_first_id < 0) | ||
1133 | return; | ||
1134 | id -= overlay_first_id; | ||
1135 | BUG_ON(id >= MAX_UNITTEST_OVERLAYS); | ||
1136 | overlay_id_bits[BIT_WORD(id)] &= ~BIT_MASK(id); | ||
1137 | } | ||
1138 | |||
1139 | static void of_unittest_destroy_tracked_overlays(void) | ||
1140 | { | ||
1141 | int id, ret, defers; | ||
1142 | |||
1143 | if (overlay_first_id < 0) | ||
1144 | return; | ||
1145 | |||
1146 | /* try until no defers */ | ||
1147 | do { | ||
1148 | defers = 0; | ||
1149 | /* remove in reverse order */ | ||
1150 | for (id = MAX_UNITTEST_OVERLAYS - 1; id >= 0; id--) { | ||
1151 | if (!(overlay_id_bits[BIT_WORD(id)] & BIT_MASK(id))) | ||
1152 | continue; | ||
1153 | |||
1154 | ret = of_overlay_destroy(id + overlay_first_id); | ||
1155 | if (ret != 0) { | ||
1156 | defers++; | ||
1157 | pr_warn("%s: overlay destroy failed for #%d\n", | ||
1158 | __func__, id + overlay_first_id); | ||
1159 | continue; | ||
1160 | } | ||
1161 | |||
1162 | overlay_id_bits[BIT_WORD(id)] &= ~BIT_MASK(id); | ||
1163 | } | ||
1164 | } while (defers > 0); | ||
1165 | } | ||
1166 | |||
1112 | static int of_unittest_apply_overlay(int unittest_nr, int overlay_nr, | 1167 | static int of_unittest_apply_overlay(int unittest_nr, int overlay_nr, |
1113 | int *overlay_id) | 1168 | int *overlay_id) |
1114 | { | 1169 | { |
@@ -1130,6 +1185,7 @@ static int of_unittest_apply_overlay(int unittest_nr, int overlay_nr, | |||
1130 | goto out; | 1185 | goto out; |
1131 | } | 1186 | } |
1132 | id = ret; | 1187 | id = ret; |
1188 | of_unittest_track_overlay(id); | ||
1133 | 1189 | ||
1134 | ret = 0; | 1190 | ret = 0; |
1135 | 1191 | ||
@@ -1343,6 +1399,7 @@ static void of_unittest_overlay_6(void) | |||
1343 | return; | 1399 | return; |
1344 | } | 1400 | } |
1345 | ov_id[i] = ret; | 1401 | ov_id[i] = ret; |
1402 | of_unittest_track_overlay(ov_id[i]); | ||
1346 | } | 1403 | } |
1347 | 1404 | ||
1348 | for (i = 0; i < 2; i++) { | 1405 | for (i = 0; i < 2; i++) { |
@@ -1367,6 +1424,7 @@ static void of_unittest_overlay_6(void) | |||
1367 | PDEV_OVERLAY)); | 1424 | PDEV_OVERLAY)); |
1368 | return; | 1425 | return; |
1369 | } | 1426 | } |
1427 | of_unittest_untrack_overlay(ov_id[i]); | ||
1370 | } | 1428 | } |
1371 | 1429 | ||
1372 | for (i = 0; i < 2; i++) { | 1430 | for (i = 0; i < 2; i++) { |
@@ -1411,6 +1469,7 @@ static void of_unittest_overlay_8(void) | |||
1411 | return; | 1469 | return; |
1412 | } | 1470 | } |
1413 | ov_id[i] = ret; | 1471 | ov_id[i] = ret; |
1472 | of_unittest_track_overlay(ov_id[i]); | ||
1414 | } | 1473 | } |
1415 | 1474 | ||
1416 | /* now try to remove first overlay (it should fail) */ | 1475 | /* now try to remove first overlay (it should fail) */ |
@@ -1433,6 +1492,7 @@ static void of_unittest_overlay_8(void) | |||
1433 | PDEV_OVERLAY)); | 1492 | PDEV_OVERLAY)); |
1434 | return; | 1493 | return; |
1435 | } | 1494 | } |
1495 | of_unittest_untrack_overlay(ov_id[i]); | ||
1436 | } | 1496 | } |
1437 | 1497 | ||
1438 | unittest(1, "overlay test %d passed\n", 8); | 1498 | unittest(1, "overlay test %d passed\n", 8); |
@@ -1855,6 +1915,8 @@ static void __init of_unittest_overlay(void) | |||
1855 | of_unittest_overlay_i2c_cleanup(); | 1915 | of_unittest_overlay_i2c_cleanup(); |
1856 | #endif | 1916 | #endif |
1857 | 1917 | ||
1918 | of_unittest_destroy_tracked_overlays(); | ||
1919 | |||
1858 | out: | 1920 | out: |
1859 | of_node_put(bus_np); | 1921 | of_node_put(bus_np); |
1860 | } | 1922 | } |
diff --git a/drivers/tty/serial/8250/8250_core.c b/drivers/tty/serial/8250/8250_core.c index 422ebea96a64..4506e405c8f3 100644 --- a/drivers/tty/serial/8250/8250_core.c +++ b/drivers/tty/serial/8250/8250_core.c | |||
@@ -450,6 +450,18 @@ static unsigned int mem32_serial_in(struct uart_port *p, int offset) | |||
450 | return readl(p->membase + offset); | 450 | return readl(p->membase + offset); |
451 | } | 451 | } |
452 | 452 | ||
453 | static void mem32be_serial_out(struct uart_port *p, int offset, int value) | ||
454 | { | ||
455 | offset = offset << p->regshift; | ||
456 | iowrite32be(value, p->membase + offset); | ||
457 | } | ||
458 | |||
459 | static unsigned int mem32be_serial_in(struct uart_port *p, int offset) | ||
460 | { | ||
461 | offset = offset << p->regshift; | ||
462 | return ioread32be(p->membase + offset); | ||
463 | } | ||
464 | |||
453 | static unsigned int io_serial_in(struct uart_port *p, int offset) | 465 | static unsigned int io_serial_in(struct uart_port *p, int offset) |
454 | { | 466 | { |
455 | offset = offset << p->regshift; | 467 | offset = offset << p->regshift; |
@@ -488,6 +500,11 @@ static void set_io_from_upio(struct uart_port *p) | |||
488 | p->serial_out = mem32_serial_out; | 500 | p->serial_out = mem32_serial_out; |
489 | break; | 501 | break; |
490 | 502 | ||
503 | case UPIO_MEM32BE: | ||
504 | p->serial_in = mem32be_serial_in; | ||
505 | p->serial_out = mem32be_serial_out; | ||
506 | break; | ||
507 | |||
491 | #if defined(CONFIG_MIPS_ALCHEMY) || defined(CONFIG_SERIAL_8250_RT288X) | 508 | #if defined(CONFIG_MIPS_ALCHEMY) || defined(CONFIG_SERIAL_8250_RT288X) |
492 | case UPIO_AU: | 509 | case UPIO_AU: |
493 | p->serial_in = au_serial_in; | 510 | p->serial_in = au_serial_in; |
@@ -513,6 +530,7 @@ serial_port_out_sync(struct uart_port *p, int offset, int value) | |||
513 | switch (p->iotype) { | 530 | switch (p->iotype) { |
514 | case UPIO_MEM: | 531 | case UPIO_MEM: |
515 | case UPIO_MEM32: | 532 | case UPIO_MEM32: |
533 | case UPIO_MEM32BE: | ||
516 | case UPIO_AU: | 534 | case UPIO_AU: |
517 | p->serial_out(p, offset, value); | 535 | p->serial_out(p, offset, value); |
518 | p->serial_in(p, UART_LCR); /* safe, no side-effects */ | 536 | p->serial_in(p, UART_LCR); /* safe, no side-effects */ |
@@ -2748,6 +2766,7 @@ static int serial8250_request_std_resource(struct uart_8250_port *up) | |||
2748 | case UPIO_AU: | 2766 | case UPIO_AU: |
2749 | case UPIO_TSI: | 2767 | case UPIO_TSI: |
2750 | case UPIO_MEM32: | 2768 | case UPIO_MEM32: |
2769 | case UPIO_MEM32BE: | ||
2751 | case UPIO_MEM: | 2770 | case UPIO_MEM: |
2752 | if (!port->mapbase) | 2771 | if (!port->mapbase) |
2753 | break; | 2772 | break; |
@@ -2784,6 +2803,7 @@ static void serial8250_release_std_resource(struct uart_8250_port *up) | |||
2784 | case UPIO_AU: | 2803 | case UPIO_AU: |
2785 | case UPIO_TSI: | 2804 | case UPIO_TSI: |
2786 | case UPIO_MEM32: | 2805 | case UPIO_MEM32: |
2806 | case UPIO_MEM32BE: | ||
2787 | case UPIO_MEM: | 2807 | case UPIO_MEM: |
2788 | if (!port->mapbase) | 2808 | if (!port->mapbase) |
2789 | break; | 2809 | break; |
diff --git a/drivers/tty/serial/8250/8250_early.c b/drivers/tty/serial/8250/8250_early.c index 8e119682266a..6c0fd8b9d1c3 100644 --- a/drivers/tty/serial/8250/8250_early.c +++ b/drivers/tty/serial/8250/8250_early.c | |||
@@ -42,6 +42,8 @@ unsigned int __weak __init serial8250_early_in(struct uart_port *port, int offse | |||
42 | return readb(port->membase + offset); | 42 | return readb(port->membase + offset); |
43 | case UPIO_MEM32: | 43 | case UPIO_MEM32: |
44 | return readl(port->membase + (offset << 2)); | 44 | return readl(port->membase + (offset << 2)); |
45 | case UPIO_MEM32BE: | ||
46 | return ioread32be(port->membase + (offset << 2)); | ||
45 | case UPIO_PORT: | 47 | case UPIO_PORT: |
46 | return inb(port->iobase + offset); | 48 | return inb(port->iobase + offset); |
47 | default: | 49 | default: |
@@ -58,6 +60,9 @@ void __weak __init serial8250_early_out(struct uart_port *port, int offset, int | |||
58 | case UPIO_MEM32: | 60 | case UPIO_MEM32: |
59 | writel(value, port->membase + (offset << 2)); | 61 | writel(value, port->membase + (offset << 2)); |
60 | break; | 62 | break; |
63 | case UPIO_MEM32BE: | ||
64 | iowrite32be(value, port->membase + (offset << 2)); | ||
65 | break; | ||
61 | case UPIO_PORT: | 66 | case UPIO_PORT: |
62 | outb(value, port->iobase + offset); | 67 | outb(value, port->iobase + offset); |
63 | break; | 68 | break; |
diff --git a/drivers/tty/serial/of_serial.c b/drivers/tty/serial/of_serial.c index aa00154c4a6d..5b73afb9f9f3 100644 --- a/drivers/tty/serial/of_serial.c +++ b/drivers/tty/serial/of_serial.c | |||
@@ -116,7 +116,8 @@ static int of_platform_serial_setup(struct platform_device *ofdev, | |||
116 | port->iotype = UPIO_MEM; | 116 | port->iotype = UPIO_MEM; |
117 | break; | 117 | break; |
118 | case 4: | 118 | case 4: |
119 | port->iotype = UPIO_MEM32; | 119 | port->iotype = of_device_is_big_endian(np) ? |
120 | UPIO_MEM32BE : UPIO_MEM32; | ||
120 | break; | 121 | break; |
121 | default: | 122 | default: |
122 | dev_warn(&ofdev->dev, "unsupported reg-io-width (%d)\n", | 123 | dev_warn(&ofdev->dev, "unsupported reg-io-width (%d)\n", |
diff --git a/include/linux/of.h b/include/linux/of.h index 5f124f685e07..ddeaae6d2083 100644 --- a/include/linux/of.h +++ b/include/linux/of.h | |||
@@ -305,6 +305,7 @@ extern int of_property_read_string_helper(struct device_node *np, | |||
305 | extern int of_device_is_compatible(const struct device_node *device, | 305 | extern int of_device_is_compatible(const struct device_node *device, |
306 | const char *); | 306 | const char *); |
307 | extern bool of_device_is_available(const struct device_node *device); | 307 | extern bool of_device_is_available(const struct device_node *device); |
308 | extern bool of_device_is_big_endian(const struct device_node *device); | ||
308 | extern const void *of_get_property(const struct device_node *node, | 309 | extern const void *of_get_property(const struct device_node *node, |
309 | const char *name, | 310 | const char *name, |
310 | int *lenp); | 311 | int *lenp); |
@@ -467,6 +468,11 @@ static inline bool of_device_is_available(const struct device_node *device) | |||
467 | return false; | 468 | return false; |
468 | } | 469 | } |
469 | 470 | ||
471 | static inline bool of_device_is_big_endian(const struct device_node *device) | ||
472 | { | ||
473 | return false; | ||
474 | } | ||
475 | |||
470 | static inline struct property *of_find_property(const struct device_node *np, | 476 | static inline struct property *of_find_property(const struct device_node *np, |
471 | const char *name, | 477 | const char *name, |
472 | int *lenp) | 478 | int *lenp) |
diff --git a/include/linux/of_fdt.h b/include/linux/of_fdt.h index 0ff360d5b3b3..587ee507965d 100644 --- a/include/linux/of_fdt.h +++ b/include/linux/of_fdt.h | |||
@@ -33,6 +33,8 @@ extern void *of_fdt_get_property(const void *blob, | |||
33 | extern int of_fdt_is_compatible(const void *blob, | 33 | extern int of_fdt_is_compatible(const void *blob, |
34 | unsigned long node, | 34 | unsigned long node, |
35 | const char *compat); | 35 | const char *compat); |
36 | extern bool of_fdt_is_big_endian(const void *blob, | ||
37 | unsigned long node); | ||
36 | extern int of_fdt_match(const void *blob, unsigned long node, | 38 | extern int of_fdt_match(const void *blob, unsigned long node, |
37 | const char *const *compat); | 39 | const char *const *compat); |
38 | extern void of_fdt_unflatten_tree(unsigned long *blob, | 40 | extern void of_fdt_unflatten_tree(unsigned long *blob, |
diff --git a/include/linux/of_irq.h b/include/linux/of_irq.h index bfec136a6d1e..d884929a7747 100644 --- a/include/linux/of_irq.h +++ b/include/linux/of_irq.h | |||
@@ -37,8 +37,6 @@ extern int of_irq_parse_one(struct device_node *device, int index, | |||
37 | extern unsigned int irq_create_of_mapping(struct of_phandle_args *irq_data); | 37 | extern unsigned int irq_create_of_mapping(struct of_phandle_args *irq_data); |
38 | extern int of_irq_to_resource(struct device_node *dev, int index, | 38 | extern int of_irq_to_resource(struct device_node *dev, int index, |
39 | struct resource *r); | 39 | struct resource *r); |
40 | extern int of_irq_to_resource_table(struct device_node *dev, | ||
41 | struct resource *res, int nr_irqs); | ||
42 | 40 | ||
43 | extern void of_irq_init(const struct of_device_id *matches); | 41 | extern void of_irq_init(const struct of_device_id *matches); |
44 | 42 | ||
@@ -46,6 +44,8 @@ extern void of_irq_init(const struct of_device_id *matches); | |||
46 | extern int of_irq_count(struct device_node *dev); | 44 | extern int of_irq_count(struct device_node *dev); |
47 | extern int of_irq_get(struct device_node *dev, int index); | 45 | extern int of_irq_get(struct device_node *dev, int index); |
48 | extern int of_irq_get_byname(struct device_node *dev, const char *name); | 46 | extern int of_irq_get_byname(struct device_node *dev, const char *name); |
47 | extern int of_irq_to_resource_table(struct device_node *dev, | ||
48 | struct resource *res, int nr_irqs); | ||
49 | #else | 49 | #else |
50 | static inline int of_irq_count(struct device_node *dev) | 50 | static inline int of_irq_count(struct device_node *dev) |
51 | { | 51 | { |
@@ -59,6 +59,11 @@ static inline int of_irq_get_byname(struct device_node *dev, const char *name) | |||
59 | { | 59 | { |
60 | return 0; | 60 | return 0; |
61 | } | 61 | } |
62 | static inline int of_irq_to_resource_table(struct device_node *dev, | ||
63 | struct resource *res, int nr_irqs) | ||
64 | { | ||
65 | return 0; | ||
66 | } | ||
62 | #endif | 67 | #endif |
63 | 68 | ||
64 | #if defined(CONFIG_OF) | 69 | #if defined(CONFIG_OF) |