Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 27332002 authored by Linux Build Service Account's avatar Linux Build Service Account Committed by Gerrit - the friendly Code Review server
Browse files

Merge "sound: usb: Send explicit device disconnect to clients"

parents d2afad6a b73866cd
Loading
Loading
Loading
Loading
+3 −2
Original line number Diff line number Diff line
@@ -673,6 +673,9 @@ static void usb_audio_disconnect(struct usb_interface *intf)

	card = chip->card;

	if (chip->disconnect_cb)
		chip->disconnect_cb(chip);

	mutex_lock(&register_mutex);
	if (atomic_inc_return(&chip->shutdown) == 1) {
		struct snd_usb_stream *as;
@@ -707,8 +710,6 @@ static void usb_audio_disconnect(struct usb_interface *intf)
	if (chip->num_interfaces <= 0) {
		usb_chip[chip->index] = NULL;
		mutex_unlock(&register_mutex);
		if (chip->disconnect_cb)
			chip->disconnect_cb(chip);
		snd_card_free_when_closed(card);
	} else {
		mutex_unlock(&register_mutex);
+33 −9
Original line number Diff line number Diff line
@@ -134,6 +134,12 @@ static struct msg_desc uaudio_stream_resp_desc = {
	.ei_array = qmi_uaudio_stream_resp_msg_v01_ei,
};

static struct msg_desc uaudio_stream_ind_desc = {
	.max_msg_len = QMI_UAUDIO_STREAM_IND_MSG_V01_MAX_MSG_LEN,
	.msg_id = QMI_UADUIO_STREAM_IND_V01,
	.ei_array = qmi_uaudio_stream_ind_msg_v01_ei,
};

enum mem_type {
	MEM_EVENT_RING,
	MEM_DCBA,
@@ -643,29 +649,47 @@ void uaudio_disconnect_cb(struct snd_usb_audio *chip)
	int ret, if_idx;
	struct uaudio_dev *dev;
	int card_num = chip->card_num;
	struct uaudio_qmi_svc *svc = uaudio_svc;
	struct qmi_uaudio_stream_ind_msg_v01 disconnect_ind = {0};

	pr_debug("%s: for card# %d\n", __func__, card_num);

	mutex_lock(&chip->dev_lock);
	if (card_num >=  SNDRV_CARDS) {
		pr_err("%s: invalid card number\n", __func__);
		goto done;
		return;
	}

	mutex_lock(&chip->dev_lock);
	dev = &uadev[card_num];

	/* clean up */
	if (!dev->udev) {
		pr_debug("%s: no clean up required\n", __func__);
		goto done;
	}

	if (atomic_read(&dev->in_use)) {
		mutex_unlock(&chip->dev_lock);

		pr_debug("%s: sending qmi indication disconnect\n", __func__);
		disconnect_ind.dev_event = USB_AUDIO_DEV_DISCONNECT_V01;
		disconnect_ind.slot_id = dev->udev->slot_id;
		ret = qmi_send_ind(svc->uaudio_svc_hdl, svc->curr_conn,
				&uaudio_stream_ind_desc, &disconnect_ind,
				sizeof(disconnect_ind));
		if (ret < 0) {
			pr_err("%s: qmi send failed wiht err: %d\n",
					__func__, ret);
			return;
		}

		ret = wait_event_interruptible(dev->disconnect_wq,
				!atomic_read(&dev->in_use));
		if (ret < 0) {
			pr_debug("%s: failed with ret %d\n", __func__, ret);
			goto done;
		}
			return;
		}

	/* clean up */
	if (!dev->udev) {
		pr_debug("%s: no clean up required\n", __func__);
		goto done;
		mutex_lock(&chip->dev_lock);
	}

	/* free xfer buffer and unmap xfer ring and buf per interface */