curl: never invoke callbacks with s->mutex held
All curl callbacks go through curl_multi_do, and hence are called with s->mutex held. Note that with comments, and make curl_read_cb drop the lock before invoking the callback. Likewise for curl_find_buf, where the callback can be invoked by the caller. Cc: qemu-stable@nongnu.org Reviewed-by: Jeff Cody <jcody@redhat.com> Signed-off-by: Paolo Bonzini <pbonzini@redhat.com> Reviewed-by: Max Reitz <mreitz@redhat.com> Message-id: 20170515100059.15795-3-pbonzini@redhat.com Signed-off-by: Jeff Cody <jcody@redhat.com>
This commit is contained in:
parent
675a775633
commit
34db05e7ff
12
block/curl.c
12
block/curl.c
@ -148,6 +148,7 @@ static void curl_multi_do(void *arg);
|
|||||||
static void curl_multi_read(void *arg);
|
static void curl_multi_read(void *arg);
|
||||||
|
|
||||||
#ifdef NEED_CURL_TIMER_CALLBACK
|
#ifdef NEED_CURL_TIMER_CALLBACK
|
||||||
|
/* Called from curl_multi_do_locked, with s->mutex held. */
|
||||||
static int curl_timer_cb(CURLM *multi, long timeout_ms, void *opaque)
|
static int curl_timer_cb(CURLM *multi, long timeout_ms, void *opaque)
|
||||||
{
|
{
|
||||||
BDRVCURLState *s = opaque;
|
BDRVCURLState *s = opaque;
|
||||||
@ -164,6 +165,7 @@ static int curl_timer_cb(CURLM *multi, long timeout_ms, void *opaque)
|
|||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
/* Called from curl_multi_do_locked, with s->mutex held. */
|
||||||
static int curl_sock_cb(CURL *curl, curl_socket_t fd, int action,
|
static int curl_sock_cb(CURL *curl, curl_socket_t fd, int action,
|
||||||
void *userp, void *sp)
|
void *userp, void *sp)
|
||||||
{
|
{
|
||||||
@ -213,6 +215,7 @@ static int curl_sock_cb(CURL *curl, curl_socket_t fd, int action,
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Called from curl_multi_do_locked, with s->mutex held. */
|
||||||
static size_t curl_header_cb(void *ptr, size_t size, size_t nmemb, void *opaque)
|
static size_t curl_header_cb(void *ptr, size_t size, size_t nmemb, void *opaque)
|
||||||
{
|
{
|
||||||
BDRVCURLState *s = opaque;
|
BDRVCURLState *s = opaque;
|
||||||
@ -227,6 +230,7 @@ static size_t curl_header_cb(void *ptr, size_t size, size_t nmemb, void *opaque)
|
|||||||
return realsize;
|
return realsize;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Called from curl_multi_do_locked, with s->mutex held. */
|
||||||
static size_t curl_read_cb(void *ptr, size_t size, size_t nmemb, void *opaque)
|
static size_t curl_read_cb(void *ptr, size_t size, size_t nmemb, void *opaque)
|
||||||
{
|
{
|
||||||
CURLState *s = ((CURLState*)opaque);
|
CURLState *s = ((CURLState*)opaque);
|
||||||
@ -265,7 +269,9 @@ static size_t curl_read_cb(void *ptr, size_t size, size_t nmemb, void *opaque)
|
|||||||
request_length - offset);
|
request_length - offset);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
qemu_mutex_unlock(&s->s->mutex);
|
||||||
acb->common.cb(acb->common.opaque, 0);
|
acb->common.cb(acb->common.opaque, 0);
|
||||||
|
qemu_mutex_lock(&s->s->mutex);
|
||||||
qemu_aio_unref(acb);
|
qemu_aio_unref(acb);
|
||||||
s->acb[i] = NULL;
|
s->acb[i] = NULL;
|
||||||
}
|
}
|
||||||
@ -306,8 +312,6 @@ static int curl_find_buf(BDRVCURLState *s, size_t start, size_t len,
|
|||||||
if (clamped_len < len) {
|
if (clamped_len < len) {
|
||||||
qemu_iovec_memset(acb->qiov, clamped_len, 0, len - clamped_len);
|
qemu_iovec_memset(acb->qiov, clamped_len, 0, len - clamped_len);
|
||||||
}
|
}
|
||||||
acb->common.cb(acb->common.opaque, 0);
|
|
||||||
|
|
||||||
return FIND_RET_OK;
|
return FIND_RET_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -854,8 +858,8 @@ static void curl_readv_bh_cb(void *p)
|
|||||||
// we can just call the callback and be done.
|
// we can just call the callback and be done.
|
||||||
switch (curl_find_buf(s, start, acb->nb_sectors * BDRV_SECTOR_SIZE, acb)) {
|
switch (curl_find_buf(s, start, acb->nb_sectors * BDRV_SECTOR_SIZE, acb)) {
|
||||||
case FIND_RET_OK:
|
case FIND_RET_OK:
|
||||||
qemu_aio_unref(acb);
|
ret = 0;
|
||||||
// fall through
|
goto out;
|
||||||
case FIND_RET_WAIT:
|
case FIND_RET_WAIT:
|
||||||
goto out;
|
goto out;
|
||||||
default:
|
default:
|
||||||
|
Loading…
Reference in New Issue
Block a user