--- /dev/null
+Texas Instruments TWL family
+
+The TWLs are Integrated Power Management Chips.
+Some version might contain much more analog function like
+USB transceiver or Audio amplifier.
+These chips are connected to an i2c bus.
+
+
+Required properties:
+- compatible : Must be "ti,twl4030";
+  For Integrated power-management/audio CODEC device used in OMAP3
+  based boards
+- compatible : Must be "ti,twl6030";
+  For Integrated power-management used in OMAP4 based boards
+- interrupts : This i2c device has an IRQ line connected to the main SoC
+- interrupt-controller : Since the twl support several interrupts internally,
+  it is considered as an interrupt controller cascaded to the SoC one.
+- #interrupt-cells = <1>;
+- interrupt-parent : The parent interrupt controller.
+
+Optional node:
+- Child nodes contain in the twl. The twl family is made of several variants
+  that support a different number of features.
+  The children nodes will thus depend of the capability of the variant.
+
+
+Example:
+/*
+ * Integrated Power Management Chip
+ * http://www.ti.com/lit/ds/symlink/twl6030.pdf
+ */
+twl@48 {
+    compatible = "ti,twl6030";
+    reg = <0x48>;
+    interrupts = <39>; /* IRQ_SYS_1N cascaded to gic */
+    interrupt-controller;
+    #interrupt-cells = <1>;
+    interrupt-parent = <&gic>;
+    #address-cells = <1>;
+    #size-cells = <0>;
+
+    twl_rtc {
+        compatible = "ti,twl_rtc";
+        interrupts = <11>;
+        reg = <0>;
+    };
+};
 
 #include <linux/platform_device.h>
 #include <linux/clk.h>
 #include <linux/err.h>
+#include <linux/device.h>
+#include <linux/of.h>
+#include <linux/of_irq.h>
+#include <linux/of_platform.h>
+#include <linux/irqdomain.h>
 
 #include <linux/regulator/machine.h>
 
 
 #define TWL_MODULE_LAST TWL4030_MODULE_LAST
 
+#define TWL4030_NR_IRQS    8
+#define TWL6030_NR_IRQS    20
+
 /* Base Address defns for twl4030_map[] */
 
 /* subchip/slave 0 - USB ID */
 
 static struct twl_client twl_modules[TWL_NUM_SLAVES];
 
+static struct irq_domain domain;
 
 /* mapping the module id to slave id and base address */
 struct twl_mapping {
        int                             status;
        unsigned                        i;
        struct twl4030_platform_data    *pdata = client->dev.platform_data;
+       struct device_node              *node = client->dev.of_node;
        u8 temp;
        int ret = 0;
+       int nr_irqs = TWL4030_NR_IRQS;
+
+       if ((id->driver_data) & TWL6030_CLASS)
+               nr_irqs = TWL6030_NR_IRQS;
+
+       if (node && !pdata) {
+               /*
+                * XXX: Temporary pdata until the information is correctly
+                * retrieved by every TWL modules from DT.
+                */
+               pdata = devm_kzalloc(&client->dev,
+                                    sizeof(struct twl4030_platform_data),
+                                    GFP_KERNEL);
+               if (!pdata)
+                       return -ENOMEM;
+       }
 
        if (!pdata) {
                dev_dbg(&client->dev, "no platform data?\n");
                return -EINVAL;
        }
 
+       status = irq_alloc_descs(-1, pdata->irq_base, nr_irqs, 0);
+       if (IS_ERR_VALUE(status)) {
+               dev_err(&client->dev, "Fail to allocate IRQ descs\n");
+               return status;
+       }
+
+       pdata->irq_base = status;
+       pdata->irq_end = pdata->irq_base + nr_irqs;
+
+       domain.irq_base = pdata->irq_base;
+       domain.nr_irq = nr_irqs;
+#ifdef CONFIG_OF_IRQ
+       domain.of_node = of_node_get(node);
+       domain.ops = &irq_domain_simple_ops;
+#endif
+       irq_domain_add(&domain);
+
        if (i2c_check_functionality(client->adapter, I2C_FUNC_I2C) == 0) {
                dev_dbg(&client->dev, "can't talk I2C?\n");
                return -EIO;
                twl_i2c_write_u8(TWL4030_MODULE_INTBR, temp, REG_GPPUPDCTR1);
        }
 
-       status = add_children(pdata, id->driver_data);
+#ifdef CONFIG_OF_DEVICE
+       if (node)
+               status = of_platform_populate(node, NULL, NULL, &client->dev);
+       else
+#endif
+               status = add_children(pdata, id->driver_data);
+
 fail:
        if (status < 0)
                twl_remove(client);