return hci->cmd->perform_daa(hci);
 }
 
+static int i3c_hci_alloc_safe_xfer_buf(struct i3c_hci *hci,
+                                      struct hci_xfer *xfer)
+{
+       if (hci->io != &mipi_i3c_hci_dma ||
+           xfer->data == NULL || !is_vmalloc_addr(xfer->data))
+               return 0;
+
+       if (xfer->rnw)
+               xfer->bounce_buf = kzalloc(xfer->data_len, GFP_KERNEL);
+       else
+               xfer->bounce_buf = kmemdup(xfer->data,
+                                          xfer->data_len, GFP_KERNEL);
+
+       return xfer->bounce_buf == NULL ? -ENOMEM : 0;
+}
+
+static void i3c_hci_free_safe_xfer_buf(struct i3c_hci *hci,
+                                      struct hci_xfer *xfer)
+{
+       if (hci->io != &mipi_i3c_hci_dma || xfer->bounce_buf == NULL)
+               return;
+
+       if (xfer->rnw)
+               memcpy(xfer->data, xfer->bounce_buf, xfer->data_len);
+
+       kfree(xfer->bounce_buf);
+}
+
 static int i3c_hci_priv_xfers(struct i3c_dev_desc *dev,
                              struct i3c_priv_xfer *i3c_xfers,
                              int nxfers)
                }
                hci->cmd->prep_i3c_xfer(hci, dev, &xfer[i]);
                xfer[i].cmd_desc[0] |= CMD_0_ROC;
+               ret = i3c_hci_alloc_safe_xfer_buf(hci, &xfer[i]);
+               if (ret)
+                       goto out;
        }
        last = i - 1;
        xfer[last].cmd_desc[0] |= CMD_0_TOC;
        }
 
 out:
+       for (i = 0; i < nxfers; i++)
+               i3c_hci_free_safe_xfer_buf(hci, &xfer[i]);
+
        hci_free_xfer(xfer, nxfers);
        return ret;
 }
                xfer[i].rnw = i2c_xfers[i].flags & I2C_M_RD;
                hci->cmd->prep_i2c_xfer(hci, dev, &xfer[i]);
                xfer[i].cmd_desc[0] |= CMD_0_ROC;
+               ret = i3c_hci_alloc_safe_xfer_buf(hci, &xfer[i]);
+               if (ret)
+                       goto out;
        }
        last = i - 1;
        xfer[last].cmd_desc[0] |= CMD_0_TOC;
        }
 
 out:
+       for (i = 0; i < nxfers; i++)
+               i3c_hci_free_safe_xfer_buf(hci, &xfer[i]);
+
        hci_free_xfer(xfer, nxfers);
        return ret;
 }