ARM: dts: Don't use legacy clock defines for dra7 clkctrl
[linux-2.6-microblaze.git] / kernel / resource.c
index ca9f519..5ad3eba 100644 (file)
@@ -73,6 +73,18 @@ static struct resource *next_resource(struct resource *p)
        return p->sibling;
 }
 
+static struct resource *next_resource_skip_children(struct resource *p)
+{
+       while (!p->sibling && p->parent)
+               p = p->parent;
+       return p->sibling;
+}
+
+#define for_each_resource(_root, _p, _skip_children) \
+       for ((_p) = (_root)->child; (_p); \
+            (_p) = (_skip_children) ? next_resource_skip_children(_p) : \
+                                      next_resource(_p))
+
 static void *r_next(struct seq_file *m, void *v, loff_t *pos)
 {
        struct resource *p = v;
@@ -1707,37 +1719,49 @@ static int strict_iomem_checks;
 #endif
 
 /*
- * check if an address is reserved in the iomem resource tree
- * returns true if reserved, false if not reserved.
+ * Check if an address is exclusive to the kernel and must not be mapped to
+ * user space, for example, via /dev/mem.
+ *
+ * Returns true if exclusive to the kernel, otherwise returns false.
  */
 bool iomem_is_exclusive(u64 addr)
 {
-       struct resource *p = &iomem_resource;
-       bool err = false;
-       loff_t l;
+       const unsigned int exclusive_system_ram = IORESOURCE_SYSTEM_RAM |
+                                                 IORESOURCE_EXCLUSIVE;
+       bool skip_children = false, err = false;
        int size = PAGE_SIZE;
-
-       if (!strict_iomem_checks)
-               return false;
+       struct resource *p;
 
        addr = addr & PAGE_MASK;
 
        read_lock(&resource_lock);
-       for (p = p->child; p ; p = r_next(NULL, p, &l)) {
-               /*
-                * We can probably skip the resources without
-                * IORESOURCE_IO attribute?
-                */
+       for_each_resource(&iomem_resource, p, skip_children) {
                if (p->start >= addr + size)
                        break;
-               if (p->end < addr)
+               if (p->end < addr) {
+                       skip_children = true;
                        continue;
+               }
+               skip_children = false;
+
+               /*
+                * IORESOURCE_SYSTEM_RAM resources are exclusive if
+                * IORESOURCE_EXCLUSIVE is set, even if they
+                * are not busy and even if "iomem=relaxed" is set. The
+                * responsible driver dynamically adds/removes system RAM within
+                * such an area and uncontrolled access is dangerous.
+                */
+               if ((p->flags & exclusive_system_ram) == exclusive_system_ram) {
+                       err = true;
+                       break;
+               }
+
                /*
                 * A resource is exclusive if IORESOURCE_EXCLUSIVE is set
                 * or CONFIG_IO_STRICT_DEVMEM is enabled and the
                 * resource is busy.
                 */
-               if ((p->flags & IORESOURCE_BUSY) == 0)
+               if (!strict_iomem_checks || !(p->flags & IORESOURCE_BUSY))
                        continue;
                if (IS_ENABLED(CONFIG_IO_STRICT_DEVMEM)
                                || p->flags & IORESOURCE_EXCLUSIVE) {