diff --git a/hw/usb/dev-mtp.c b/hw/usb/dev-mtp.c index 9846e4b513..7c07295519 100644 --- a/hw/usb/dev-mtp.c +++ b/hw/usb/dev-mtp.c @@ -2038,26 +2038,36 @@ static void usb_mtp_realize(USBDevice *dev, Error **errp) { MTPState *s = USB_MTP(dev); - usb_desc_create_serial(dev); - usb_desc_init(dev); - QTAILQ_INIT(&s->objects); - if (s->desc == NULL) { - if (s->root == NULL) { - error_setg(errp, "usb-mtp: rootdir property must be configured"); - return; - } - s->desc = strrchr(s->root, '/'); - if (s->desc && s->desc[0]) { - s->desc = g_strdup(s->desc + 1); - } else { - s->desc = g_strdup("none"); - } + if ((s->root == NULL) || !g_path_is_absolute(s->root)) { + error_setg(errp, "usb-mtp: rootdir must be configured and be an absolute path"); + return; } + + if (access(s->root, R_OK) != 0) { + error_setg(errp, "usb-mtp: rootdir does not exist/not readable"); + return; + } else if (!s->readonly && access(s->root, W_OK) != 0) { + error_setg(errp, "usb-mtp: rootdir does not have write permissions"); + return; + } + /* Mark store as RW */ if (!s->readonly) { s->flags |= (1 << MTP_FLAG_WRITABLE); } + if (s->desc == NULL) { + /* + * This does not check if path exists + * but we have the checks above + */ + s->desc = g_path_get_basename(s->root); + } + + usb_desc_create_serial(dev); + usb_desc_init(dev); + QTAILQ_INIT(&s->objects); + } static const VMStateDescription vmstate_usb_mtp = { diff --git a/hw/usb/hcd-xhci.c b/hw/usb/hcd-xhci.c index f578264948..80988bb305 100644 --- a/hw/usb/hcd-xhci.c +++ b/hw/usb/hcd-xhci.c @@ -1914,6 +1914,7 @@ static void xhci_kick_epctx(XHCIEPContext *epctx, unsigned int streamid) } usb_handle_packet(xfer->packet.ep->dev, &xfer->packet); if (xfer->packet.status == USB_RET_NAK) { + xhci_xfer_unmap(xfer); return; } xhci_try_complete_packet(xfer); @@ -2161,6 +2162,7 @@ static TRBCCode xhci_address_slot(XHCIState *xhci, unsigned int slotid, DeviceOutRequest | USB_REQ_SET_ADDRESS, slotid, 0, 0, NULL); assert(p.status != USB_RET_ASYNC); + usb_packet_cleanup(&p); } res = xhci_enable_ep(xhci, slotid, 1, octx+32, ep0_ctx);