extern int dma_set_mask(struct device *dev, u64 dma_mask);
 extern int __dma_set_mask(struct device *dev, u64 dma_mask);
+extern u64 __dma_get_required_mask(struct device *dev);
 
 #define dma_alloc_coherent(d,s,h,f)    dma_alloc_attrs(d,s,h,f,NULL)
 
 
        *dev->dma_mask = dma_mask;
        return 0;
 }
+
 int dma_set_mask(struct device *dev, u64 dma_mask)
 {
        if (ppc_md.dma_set_mask)
 }
 EXPORT_SYMBOL(dma_set_mask);
 
-u64 dma_get_required_mask(struct device *dev)
+u64 __dma_get_required_mask(struct device *dev)
 {
        struct dma_map_ops *dma_ops = get_dma_ops(dev);
 
-       if (ppc_md.dma_get_required_mask)
-               return ppc_md.dma_get_required_mask(dev);
-
        if (unlikely(dma_ops == NULL))
                return 0;
 
 
        return DMA_BIT_MASK(8 * sizeof(dma_addr_t));
 }
+
+u64 dma_get_required_mask(struct device *dev)
+{
+       if (ppc_md.dma_get_required_mask)
+               return ppc_md.dma_get_required_mask(dev);
+
+       return __dma_get_required_mask(dev);
+}
 EXPORT_SYMBOL_GPL(dma_get_required_mask);
 
 static int __init dma_init(void)
 
        return 0;
 }
 
+static u64 pnv_pci_ioda_dma_get_required_mask(struct pnv_phb *phb,
+                                             struct pci_dev *pdev)
+{
+       struct pci_dn *pdn = pci_get_pdn(pdev);
+       struct pnv_ioda_pe *pe;
+       u64 end, mask;
+
+       if (WARN_ON(!pdn || pdn->pe_number == IODA_INVALID_PE))
+               return 0;
+
+       pe = &phb->ioda.pe_array[pdn->pe_number];
+       if (!pe->tce_bypass_enabled)
+               return __dma_get_required_mask(&pdev->dev);
+
+
+       end = pe->tce_bypass_base + memblock_end_of_DRAM();
+       mask = 1ULL << (fls64(end) - 1);
+       mask += mask - 1;
+
+       return mask;
+}
+
 static void pnv_ioda_setup_bus_dma(struct pnv_ioda_pe *pe,
                                   struct pci_bus *bus,
                                   bool add_to_iommu_group)
        /* Setup TCEs */
        phb->dma_dev_setup = pnv_pci_ioda_dma_dev_setup;
        phb->dma_set_mask = pnv_pci_ioda_dma_set_mask;
+       phb->dma_get_required_mask = pnv_pci_ioda_dma_get_required_mask;
 
        /* Setup shutdown function for kexec */
        phb->shutdown = pnv_pci_ioda_shutdown;
 
        return __dma_set_mask(&pdev->dev, dma_mask);
 }
 
+u64 pnv_pci_dma_get_required_mask(struct pci_dev *pdev)
+{
+       struct pci_controller *hose = pci_bus_to_host(pdev->bus);
+       struct pnv_phb *phb = hose->private_data;
+
+       if (phb && phb->dma_get_required_mask)
+               return phb->dma_get_required_mask(phb, pdev);
+
+       return __dma_get_required_mask(&pdev->dev);
+}
+
 void pnv_pci_shutdown(void)
 {
        struct pci_controller *hose;
 
        void (*dma_dev_setup)(struct pnv_phb *phb, struct pci_dev *pdev);
        int (*dma_set_mask)(struct pnv_phb *phb, struct pci_dev *pdev,
                            u64 dma_mask);
+       u64 (*dma_get_required_mask)(struct pnv_phb *phb,
+                                    struct pci_dev *pdev);
        void (*fixup_phb)(struct pci_controller *hose);
        u32 (*bdfn_to_pe)(struct pnv_phb *phb, struct pci_bus *bus, u32 devfn);
        void (*shutdown)(struct pnv_phb *phb);
 
 extern void pnv_pci_init(void);
 extern void pnv_pci_shutdown(void);
 extern int pnv_pci_dma_set_mask(struct pci_dev *pdev, u64 dma_mask);
+extern u64 pnv_pci_dma_get_required_mask(struct pci_dev *pdev);
 #else
 static inline void pnv_pci_init(void) { }
 static inline void pnv_pci_shutdown(void) { }
 {
        return -ENODEV;
 }
+
+static inline u64 pnv_pci_dma_get_required_mask(struct pci_dev *pdev)
+{
+       return 0;
+}
 #endif
 
 extern void pnv_lpc_init(void);
 
        return __dma_set_mask(dev, dma_mask);
 }
 
+static u64 pnv_dma_get_required_mask(struct device *dev)
+{
+       if (dev_is_pci(dev))
+               return pnv_pci_dma_get_required_mask(to_pci_dev(dev));
+
+       return __dma_get_required_mask(dev);
+}
+
 static void pnv_shutdown(void)
 {
        /* Let the PCI code clear up IODA tables */
        .power_save             = power7_idle,
        .calibrate_decr         = generic_calibrate_decr,
        .dma_set_mask           = pnv_dma_set_mask,
+       .dma_get_required_mask  = pnv_dma_get_required_mask,
 #ifdef CONFIG_KEXEC
        .kexec_cpu_down         = pnv_kexec_cpu_down,
 #endif