mirror of
https://github.com/owntone/owntone-server.git
synced 2025-01-15 08:45:02 -05:00
Revert "Fix 30 minute iTunes/DAAP time-out problem"
This reverts commit 7a021b2332402a32ad92494db910344f3a428e0a.
This commit is contained in:
parent
4eb416a3b3
commit
e9cdf88102
363
src/httpd_daap.c
363
src/httpd_daap.c
@ -59,17 +59,7 @@ extern struct event_base *evbase_httpd;
|
|||||||
|
|
||||||
/* Session timeout in seconds */
|
/* Session timeout in seconds */
|
||||||
#define DAAP_SESSION_TIMEOUT 1800
|
#define DAAP_SESSION_TIMEOUT 1800
|
||||||
/* Amount of time update request can pending before we
|
|
||||||
send a forced response to keep the channel alive */
|
|
||||||
#define DAAP_UPDATE_TIMEOUT 1500
|
|
||||||
/* How often we poll for database changes */
|
|
||||||
#define DAAP_UPDATE_MONITOR_TIMEOUT 10
|
|
||||||
|
|
||||||
/* XXX Workaround before adding revision support in db.c;
|
|
||||||
Client will not get dynamic updates. The state of the
|
|
||||||
database at the time of connection is all the client
|
|
||||||
gets. */
|
|
||||||
#define db_revision_number() (2)
|
|
||||||
|
|
||||||
struct uri_map {
|
struct uri_map {
|
||||||
regex_t preg;
|
regex_t preg;
|
||||||
@ -77,27 +67,14 @@ struct uri_map {
|
|||||||
void (*handler)(struct evhttp_request *req, struct evbuffer *evbuf, char **uri, struct evkeyvalq *query);
|
void (*handler)(struct evhttp_request *req, struct evbuffer *evbuf, char **uri, struct evkeyvalq *query);
|
||||||
};
|
};
|
||||||
|
|
||||||
struct daap_update_request; /* Forward */
|
|
||||||
struct daap_session {
|
struct daap_session {
|
||||||
int id;
|
int id;
|
||||||
|
|
||||||
struct event timeout;
|
struct event timeout;
|
||||||
/* A pending request, if active */
|
|
||||||
struct daap_update_request *update_request;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
struct daap_update_request {
|
struct daap_update_request {
|
||||||
|
|
||||||
/* Currently pending request */
|
|
||||||
struct evhttp_request *req;
|
struct evhttp_request *req;
|
||||||
/* Time-out when an update *must* be sent */
|
|
||||||
struct event timeout;
|
|
||||||
/* Session that this request belongs to */
|
|
||||||
struct daap_session *session;
|
|
||||||
|
|
||||||
/* Current revision number client is reporting */
|
|
||||||
int revision_number;
|
|
||||||
int session_id;
|
|
||||||
|
|
||||||
struct daap_update_request *next;
|
struct daap_update_request *next;
|
||||||
};
|
};
|
||||||
@ -122,16 +99,6 @@ static int next_session_id;
|
|||||||
|
|
||||||
/* Update requests */
|
/* Update requests */
|
||||||
static struct daap_update_request *update_requests;
|
static struct daap_update_request *update_requests;
|
||||||
/* Global persistent timer that triggers periodically (10 secs).
|
|
||||||
Checks the database to see if it has changed, and if so,
|
|
||||||
pushes a response to all outstanding client update requests. */
|
|
||||||
static struct event update_monitor_timer;
|
|
||||||
|
|
||||||
/* Forward declaration */
|
|
||||||
static void
|
|
||||||
daap_update_timeout_cb(int fd, short what, void *arg);
|
|
||||||
static void
|
|
||||||
update_request_free(struct daap_update_request *ur, int free_conn);
|
|
||||||
|
|
||||||
|
|
||||||
/* Session handling */
|
/* Session handling */
|
||||||
@ -150,9 +117,6 @@ daap_session_compare(const void *aa, const void *bb)
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* daap_session_free - called by avl_delete()
|
|
||||||
*/
|
|
||||||
static void
|
static void
|
||||||
daap_session_free(void *item)
|
daap_session_free(void *item)
|
||||||
{
|
{
|
||||||
@ -160,37 +124,16 @@ daap_session_free(void *item)
|
|||||||
|
|
||||||
s = (struct daap_session *)item;
|
s = (struct daap_session *)item;
|
||||||
|
|
||||||
/* If there is a pending request, then close it out */
|
|
||||||
if (s->update_request)
|
|
||||||
update_request_free(s->update_request, 1 /* Close connection */);
|
|
||||||
evtimer_del(&s->timeout);
|
evtimer_del(&s->timeout);
|
||||||
free(s);
|
free(s);
|
||||||
|
|
||||||
/* XXX does not handle the case the connection being open but no
|
|
||||||
pending request. The connection stays silently open but
|
|
||||||
httpd_daapd refuses to acknowledge stale requests on the
|
|
||||||
connection.
|
|
||||||
*/
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
* daap_session_kill - recover when connection dies
|
|
||||||
*/
|
|
||||||
static void
|
static void
|
||||||
daap_session_kill(struct daap_session *s)
|
daap_session_kill(struct daap_session *s)
|
||||||
{
|
{
|
||||||
/* NOTE: automatically calls daap_session_free() */
|
|
||||||
avl_delete(daap_sessions, s);
|
avl_delete(daap_sessions, s);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* daap_session_timeout_cb - event callback when session inactivity timeout is triggered
|
|
||||||
*
|
|
||||||
* fd - dummy
|
|
||||||
* what - time event fired
|
|
||||||
* arg - session pointer
|
|
||||||
*/
|
|
||||||
static void
|
static void
|
||||||
daap_session_timeout_cb(int fd, short what, void *arg)
|
daap_session_timeout_cb(int fd, short what, void *arg)
|
||||||
{
|
{
|
||||||
@ -206,10 +149,14 @@ daap_session_timeout_cb(int fd, short what, void *arg)
|
|||||||
static struct daap_session *
|
static struct daap_session *
|
||||||
daap_session_register(void)
|
daap_session_register(void)
|
||||||
{
|
{
|
||||||
|
#if 0
|
||||||
struct timeval tv;
|
struct timeval tv;
|
||||||
|
#endif
|
||||||
struct daap_session *s;
|
struct daap_session *s;
|
||||||
avl_node_t *node;
|
avl_node_t *node;
|
||||||
|
#if 0
|
||||||
int ret;
|
int ret;
|
||||||
|
#endif
|
||||||
|
|
||||||
s = (struct daap_session *)malloc(sizeof(struct daap_session));
|
s = (struct daap_session *)malloc(sizeof(struct daap_session));
|
||||||
if (!s)
|
if (!s)
|
||||||
@ -221,6 +168,7 @@ daap_session_register(void)
|
|||||||
memset(s, 0, sizeof(struct daap_session));
|
memset(s, 0, sizeof(struct daap_session));
|
||||||
|
|
||||||
s->id = next_session_id;
|
s->id = next_session_id;
|
||||||
|
|
||||||
next_session_id++;
|
next_session_id++;
|
||||||
|
|
||||||
evtimer_set(&s->timeout, daap_session_timeout_cb, s);
|
evtimer_set(&s->timeout, daap_session_timeout_cb, s);
|
||||||
@ -235,12 +183,14 @@ daap_session_register(void)
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#if 0
|
||||||
evutil_timerclear(&tv);
|
evutil_timerclear(&tv);
|
||||||
tv.tv_sec = DAAP_SESSION_TIMEOUT;
|
tv.tv_sec = DAAP_SESSION_TIMEOUT;
|
||||||
|
|
||||||
ret = evtimer_add(&s->timeout, &tv);
|
ret = evtimer_add(&s->timeout, &tv);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
DPRINTF(E_LOG, L_DAAP, "Could not add session timeout event for session %d\n", s->id);
|
DPRINTF(E_LOG, L_DAAP, "Could not add session timeout event for session %d\n", s->id);
|
||||||
|
#endif /* 0 */
|
||||||
|
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
@ -249,7 +199,9 @@ struct daap_session *
|
|||||||
daap_session_find(struct evhttp_request *req, struct evkeyvalq *query, struct evbuffer *evbuf)
|
daap_session_find(struct evhttp_request *req, struct evkeyvalq *query, struct evbuffer *evbuf)
|
||||||
{
|
{
|
||||||
struct daap_session needle;
|
struct daap_session needle;
|
||||||
|
#if 0
|
||||||
struct timeval tv;
|
struct timeval tv;
|
||||||
|
#endif
|
||||||
struct daap_session *s;
|
struct daap_session *s;
|
||||||
avl_node_t *node;
|
avl_node_t *node;
|
||||||
const char *param;
|
const char *param;
|
||||||
@ -275,6 +227,7 @@ daap_session_find(struct evhttp_request *req, struct evkeyvalq *query, struct ev
|
|||||||
|
|
||||||
s = (struct daap_session *)node->item;
|
s = (struct daap_session *)node->item;
|
||||||
|
|
||||||
|
#if 0
|
||||||
event_del(&s->timeout);
|
event_del(&s->timeout);
|
||||||
|
|
||||||
evutil_timerclear(&tv);
|
evutil_timerclear(&tv);
|
||||||
@ -283,6 +236,7 @@ daap_session_find(struct evhttp_request *req, struct evkeyvalq *query, struct ev
|
|||||||
ret = evtimer_add(&s->timeout, &tv);
|
ret = evtimer_add(&s->timeout, &tv);
|
||||||
if (ret < 0)
|
if (ret < 0)
|
||||||
DPRINTF(E_LOG, L_DAAP, "Could not add session timeout event for session %d\n", s->id);
|
DPRINTF(E_LOG, L_DAAP, "Could not add session timeout event for session %d\n", s->id);
|
||||||
|
#endif /* 0 */
|
||||||
|
|
||||||
return s;
|
return s;
|
||||||
|
|
||||||
@ -291,19 +245,21 @@ daap_session_find(struct evhttp_request *req, struct evkeyvalq *query, struct ev
|
|||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* update_request_free - delete update request and remove from list of pending updates
|
/* Update requests helpers */
|
||||||
*
|
|
||||||
* ur - pointer to update request to remove
|
|
||||||
* free_con - if set, then close the associated HTTP connection
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
static void
|
static void
|
||||||
update_request_free(struct daap_update_request *ur, int free_conn)
|
update_fail_cb(struct evhttp_connection *evcon, void *arg)
|
||||||
{
|
{
|
||||||
|
struct daap_update_request *ur;
|
||||||
struct daap_update_request *p;
|
struct daap_update_request *p;
|
||||||
|
|
||||||
if (ur == 0) return;
|
ur = (struct daap_update_request *)arg;
|
||||||
|
|
||||||
|
DPRINTF(E_DBG, L_DAAP, "Update request: client closed connection\n");
|
||||||
|
|
||||||
|
if (ur->req->evcon)
|
||||||
|
evhttp_connection_set_closecb(ur->req->evcon, NULL, NULL);
|
||||||
|
|
||||||
if (ur == update_requests)
|
if (ur == update_requests)
|
||||||
update_requests = ur->next;
|
update_requests = ur->next;
|
||||||
else
|
else
|
||||||
@ -320,34 +276,10 @@ update_request_free(struct daap_update_request *ur, int free_conn)
|
|||||||
p->next = ur->next;
|
p->next = ur->next;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ur->session)
|
|
||||||
ur->session->update_request = 0;
|
|
||||||
|
|
||||||
evtimer_del(&ur->timeout);
|
|
||||||
if (ur->req && ur->req->evcon)
|
|
||||||
{
|
|
||||||
evhttp_connection_set_closecb(ur->req->evcon, NULL, NULL);
|
|
||||||
if (free_conn) evhttp_connection_free(ur->req->evcon);
|
|
||||||
}
|
|
||||||
|
|
||||||
free(ur);
|
free(ur);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/* Update requests helpers */
|
|
||||||
static void
|
|
||||||
update_fail_cb(struct evhttp_connection *evcon, void *arg)
|
|
||||||
{
|
|
||||||
struct daap_update_request *ur;
|
|
||||||
|
|
||||||
ur = (struct daap_update_request *)arg;
|
|
||||||
|
|
||||||
DPRINTF(E_DBG, L_DAAP, "Update request: client closed connection\n");
|
|
||||||
|
|
||||||
update_request_free(ur, 1 /* Close connection */);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/* DAAP sort headers helpers */
|
/* DAAP sort headers helpers */
|
||||||
static struct sort_ctx *
|
static struct sort_ctx *
|
||||||
daap_sort_context_new(void)
|
daap_sort_context_new(void)
|
||||||
@ -700,12 +632,12 @@ daap_reply_server_info(struct evhttp_request *req, struct evbuffer *evbuf, char
|
|||||||
dmap_add_int(evbuf, "mpro", mpro); /* 12 */
|
dmap_add_int(evbuf, "mpro", mpro); /* 12 */
|
||||||
dmap_add_int(evbuf, "apro", apro); /* 12 */
|
dmap_add_int(evbuf, "apro", apro); /* 12 */
|
||||||
dmap_add_string(evbuf, "minm", name); /* 8 + strlen(name) */
|
dmap_add_string(evbuf, "minm", name); /* 8 + strlen(name) */
|
||||||
|
|
||||||
#if 0
|
#if 0
|
||||||
/* XXX Strangely, if these are enabled, then the client does
|
|
||||||
not poll for updates, even if msup == 1 */
|
|
||||||
dmap_add_int(evbuf, "mstm", DAAP_SESSION_TIMEOUT); /* 12 */
|
dmap_add_int(evbuf, "mstm", DAAP_SESSION_TIMEOUT); /* 12 */
|
||||||
dmap_add_char(evbuf, "msal", 1); /* 9 */
|
dmap_add_char(evbuf, "msal", 1); /* 9 */
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
dmap_add_char(evbuf, "mslr", 1); /* 9 */
|
dmap_add_char(evbuf, "mslr", 1); /* 9 */
|
||||||
dmap_add_char(evbuf, "msau", (passwd) ? 2 : 0); /* 9 */
|
dmap_add_char(evbuf, "msau", (passwd) ? 2 : 0); /* 9 */
|
||||||
dmap_add_char(evbuf, "msex", 1); /* 9 */
|
dmap_add_char(evbuf, "msex", 1); /* 9 */
|
||||||
@ -716,6 +648,7 @@ daap_reply_server_info(struct evhttp_request *req, struct evbuffer *evbuf, char
|
|||||||
dmap_add_char(evbuf, "mspi", 1); /* 9 */
|
dmap_add_char(evbuf, "mspi", 1); /* 9 */
|
||||||
dmap_add_int(evbuf, "msdc", 1); /* 12 */
|
dmap_add_int(evbuf, "msdc", 1); /* 12 */
|
||||||
|
|
||||||
|
/* Advertise updates support even though we don't send updates */
|
||||||
dmap_add_char(evbuf, "msup", 1); /* 9 */
|
dmap_add_char(evbuf, "msup", 1); /* 9 */
|
||||||
|
|
||||||
httpd_send_reply(req, HTTP_OK, "OK", evbuf);
|
httpd_send_reply(req, HTTP_OK, "OK", evbuf);
|
||||||
@ -844,144 +777,13 @@ daap_reply_logout(struct evhttp_request *req, struct evbuffer *evbuf, char **uri
|
|||||||
httpd_send_reply(req, 204, "Logout Successful", evbuf);
|
httpd_send_reply(req, 204, "Logout Successful", evbuf);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* Send update response
|
|
||||||
* s - current DAAP session
|
|
||||||
* req - evhttp_request we are responding to
|
|
||||||
* force - whether we are forcing a reply even if the database is unchanged
|
|
||||||
* Return value:
|
|
||||||
* -1: error
|
|
||||||
* 0: did not send
|
|
||||||
* 1: reply sent OK
|
|
||||||
*/
|
|
||||||
static int
|
|
||||||
daap_update_response(struct daap_update_request *ur, int force)
|
|
||||||
{
|
|
||||||
int db_rev = db_revision_number();
|
|
||||||
struct evbuffer *evbuf;
|
|
||||||
|
|
||||||
DPRINTF(E_DBG, L_DAAP, " (update, session-id=%d, old_rev=%d, current_rev=%d, force=%d)\n",
|
|
||||||
ur->session_id, ur->revision_number, db_rev, force);
|
|
||||||
if (!force && ur->revision_number == db_rev) return 0;
|
|
||||||
|
|
||||||
evbuf = evbuffer_new();
|
|
||||||
if (evbuffer_expand(evbuf, 32) < 0)
|
|
||||||
{
|
|
||||||
DPRINTF(E_LOG, L_DAAP, "Could not expand evbuffer for DAAP update reply\n");
|
|
||||||
|
|
||||||
dmap_send_error(ur->req, "mupd", "Out of memory");
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Send back current revision */
|
|
||||||
dmap_add_container(evbuf, "mupd", 24);
|
|
||||||
dmap_add_int(evbuf, "mstt", 200); /* 12 */
|
|
||||||
dmap_add_int(evbuf, "musr", db_rev); /* 12 */
|
|
||||||
|
|
||||||
httpd_send_reply(ur->req, HTTP_OK, "OK", evbuf);
|
|
||||||
evbuffer_free(evbuf);
|
|
||||||
DPRINTF(E_DBG, L_DAAP, " (reply OK, session-id=%d, old_rev=%d, current_rev=%d)\n",
|
|
||||||
ur->session_id, ur->revision_number, db_rev);
|
|
||||||
|
|
||||||
ur->revision_number = db_rev;
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* daap_update_monitor_cb - global database monitor callback
|
|
||||||
*
|
|
||||||
* This function is called periodically, to monitor for database updates
|
|
||||||
* that need to be sent out.
|
|
||||||
*
|
|
||||||
* fd - dummy
|
|
||||||
* what - timer event
|
|
||||||
* arg - dummy
|
|
||||||
*/
|
|
||||||
static void
|
|
||||||
daap_update_monitor_cb(int fd, short what, void *arg)
|
|
||||||
{
|
|
||||||
struct timeval tv;
|
|
||||||
int db_rev = db_revision_number();
|
|
||||||
int ret;
|
|
||||||
struct daap_update_request *ur = 0, *next = 0;
|
|
||||||
|
|
||||||
DPRINTF(E_DBG, L_DAAP, "Periodic update monitor event (db-rev=%d)\n", db_rev);
|
|
||||||
ur = update_requests;
|
|
||||||
while (ur)
|
|
||||||
{
|
|
||||||
next = ur->next; /* Cache a local copy of "next" */
|
|
||||||
DPRINTF(E_DBG, L_DAAP,
|
|
||||||
" (session-id=%d, request=%d, rev=%d)\n",
|
|
||||||
ur->session_id, ur->req ? 1 : 0, ur->revision_number);
|
|
||||||
if (! ur->req ) continue;
|
|
||||||
|
|
||||||
/* Send update to client now */
|
|
||||||
ret = 0;
|
|
||||||
if (db_rev != ur->revision_number)
|
|
||||||
ret = daap_update_response(ur, 1);
|
|
||||||
|
|
||||||
/* If we sent a reply, remove this update request from the linked list */
|
|
||||||
if (ret > 0) update_request_free(ur, 0);
|
|
||||||
|
|
||||||
ur = next; /* Advance to next request */
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Reset the timer for next monitor cycle */
|
|
||||||
evutil_timerclear(&tv);
|
|
||||||
tv.tv_sec = DAAP_UPDATE_MONITOR_TIMEOUT;
|
|
||||||
evtimer_add(&update_monitor_timer, &tv);
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
* daap_update_timeout_cb - single update timeout callback
|
|
||||||
*
|
|
||||||
* Called when an individual session update has timed out
|
|
||||||
*
|
|
||||||
* fd - dummy
|
|
||||||
* what - timer event
|
|
||||||
* arg - pointer to update request
|
|
||||||
*/
|
|
||||||
static void
|
|
||||||
daap_update_timeout_cb(int fd, short what, void *arg)
|
|
||||||
{
|
|
||||||
struct daap_update_request *ur;
|
|
||||||
|
|
||||||
ur = (struct daap_update_request *) arg;
|
|
||||||
|
|
||||||
if (ur && ur->req)
|
|
||||||
{
|
|
||||||
DPRINTF(E_DBG, L_DAAP, "Session update timeout (session-id=%d)\n", ur->session_id);
|
|
||||||
daap_update_response(ur, 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Remove update_request from list */
|
|
||||||
update_request_free(ur, 0);
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
* daap_reply_update - accept DAAP update request and respond or queue response
|
|
||||||
*
|
|
||||||
* Is passed an update request from HTTP server. If an update is available
|
|
||||||
* already, then it is responded to immediately, otherwise the request is
|
|
||||||
* queued with other update_requests for later response.
|
|
||||||
*
|
|
||||||
* req - HTTP request
|
|
||||||
* evbuf - response buffer
|
|
||||||
* uri - parsed URI
|
|
||||||
* query - parsed query parameters
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
static void
|
static void
|
||||||
daap_reply_update(struct evhttp_request *req, struct evbuffer *evbuf, char **uri, struct evkeyvalq *query)
|
daap_reply_update(struct evhttp_request *req, struct evbuffer *evbuf, char **uri, struct evkeyvalq *query)
|
||||||
{
|
{
|
||||||
struct daap_session *s;
|
struct daap_session *s;
|
||||||
struct daap_update_request *ur, update;
|
struct daap_update_request *ur;
|
||||||
const char *param;
|
const char *param;
|
||||||
|
int current_rev = 2;
|
||||||
int reqd_rev;
|
int reqd_rev;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
@ -1007,64 +809,47 @@ daap_reply_update(struct evhttp_request *req, struct evbuffer *evbuf, char **uri
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
DPRINTF(E_DBG, L_DAAP, "DAAP update request (revision=%d)\n", reqd_rev);
|
if (reqd_rev == 1) /* Or revision is not valid */
|
||||||
|
|
||||||
memset(&update, 0, sizeof(update));
|
|
||||||
update.revision_number = reqd_rev;
|
|
||||||
update.session_id = s->id;
|
|
||||||
update.req = req;
|
|
||||||
|
|
||||||
ret = daap_update_response(&update, 0);
|
|
||||||
if (ret < 0)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (ret == 0)
|
|
||||||
{
|
{
|
||||||
struct timeval tv;
|
ret = evbuffer_expand(evbuf, 32);
|
||||||
/* We did not send a reply immediately because the database is unchanged,
|
if (ret < 0)
|
||||||
so queue this request for pushing later. */
|
|
||||||
|
|
||||||
DPRINTF(E_DBG, L_DAAP, "Queuing update request for session-id=%d\n", s->id);
|
|
||||||
|
|
||||||
/* Create daap_update_request structure */
|
|
||||||
ur = (struct daap_update_request *)malloc(sizeof(struct daap_update_request));
|
|
||||||
if (!ur)
|
|
||||||
{
|
{
|
||||||
DPRINTF(E_LOG, L_DAAP, "Out of memory for update request\n");
|
DPRINTF(E_LOG, L_DAAP, "Could not expand evbuffer for DAAP update reply\n");
|
||||||
|
|
||||||
dmap_send_error(req, "mupd", "Out of memory");
|
dmap_send_error(req, "mupd", "Out of memory");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
*ur = update; /* Copy temporary request info into malloc'd structure */
|
|
||||||
ur->req = req;
|
|
||||||
ur->next = update_requests;
|
|
||||||
update_requests = ur; /* Add to master list */
|
|
||||||
|
|
||||||
/* Link the session and the request */
|
/* Send back current revision */
|
||||||
ur->session = s;
|
dmap_add_container(evbuf, "mupd", 24);
|
||||||
s->update_request = ur;
|
dmap_add_int(evbuf, "mstt", 200); /* 12 */
|
||||||
|
dmap_add_int(evbuf, "musr", current_rev); /* 12 */
|
||||||
|
|
||||||
/* Set the time-out timer */
|
httpd_send_reply(req, HTTP_OK, "OK", evbuf);
|
||||||
evtimer_set(&ur->timeout, daap_update_timeout_cb, ur);
|
|
||||||
event_base_set(evbase_httpd, &ur->timeout);
|
return;
|
||||||
evutil_timerclear(&tv);
|
|
||||||
tv.tv_sec = DAAP_UPDATE_TIMEOUT;
|
|
||||||
|
|
||||||
ret = evtimer_add(&ur->timeout, &tv);
|
|
||||||
if (ret < 0)
|
|
||||||
{
|
|
||||||
DPRINTF(E_LOG, L_DAAP, "Could not add update timeout event for session %d\n", s->id);
|
|
||||||
dmap_send_error(req, "mupd", "Timer setting failed");
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* If the connection fails before we have an update to push out
|
|
||||||
* to the client, we need to know.
|
|
||||||
*/
|
|
||||||
evhttp_connection_set_closecb(req->evcon, update_fail_cb, ur);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return;
|
/* Else, just let the request hang until we have changes to push back */
|
||||||
|
ur = (struct daap_update_request *)malloc(sizeof(struct daap_update_request));
|
||||||
|
if (!ur)
|
||||||
|
{
|
||||||
|
DPRINTF(E_LOG, L_DAAP, "Out of memory for update request\n");
|
||||||
|
|
||||||
|
dmap_send_error(req, "mupd", "Out of memory");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* NOTE: we may need to keep reqd_rev in there too */
|
||||||
|
ur->req = req;
|
||||||
|
|
||||||
|
ur->next = update_requests;
|
||||||
|
update_requests = ur;
|
||||||
|
|
||||||
|
/* If the connection fails before we have an update to push out
|
||||||
|
* to the client, we need to know.
|
||||||
|
*/
|
||||||
|
evhttp_connection_set_closecb(req->evcon, update_fail_cb, ur);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
@ -2641,25 +2426,10 @@ daap_init(void)
|
|||||||
char buf[64];
|
char buf[64];
|
||||||
int i;
|
int i;
|
||||||
int ret;
|
int ret;
|
||||||
struct timeval tv;
|
|
||||||
|
|
||||||
next_session_id = 100; /* gotta start somewhere, right? */
|
next_session_id = 100; /* gotta start somewhere, right? */
|
||||||
update_requests = NULL;
|
update_requests = NULL;
|
||||||
|
|
||||||
/* Add a monitor timer which periodically polls the database revision number */
|
|
||||||
evtimer_set(&update_monitor_timer, daap_update_monitor_cb, 0);
|
|
||||||
event_base_set(evbase_httpd, &update_monitor_timer);
|
|
||||||
|
|
||||||
evutil_timerclear(&tv);
|
|
||||||
tv.tv_sec = DAAP_UPDATE_MONITOR_TIMEOUT;
|
|
||||||
ret = evtimer_add(&update_monitor_timer, &tv);
|
|
||||||
if (ret < 0)
|
|
||||||
{
|
|
||||||
DPRINTF(E_FATAL, L_DAAP, "Could not add update monitor timer\n");
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Initialize handlers */
|
|
||||||
for (i = 0; daap_handlers[i].handler; i++)
|
for (i = 0; daap_handlers[i].handler; i++)
|
||||||
{
|
{
|
||||||
ret = regcomp(&daap_handlers[i].preg, daap_handlers[i].regexp, REG_EXTENDED | REG_NOSUB);
|
ret = regcomp(&daap_handlers[i].preg, daap_handlers[i].regexp, REG_EXTENDED | REG_NOSUB);
|
||||||
@ -2672,7 +2442,6 @@ daap_init(void)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Initialize session tree */
|
|
||||||
daap_sessions = avl_alloc_tree(daap_session_compare, daap_session_free);
|
daap_sessions = avl_alloc_tree(daap_session_compare, daap_session_free);
|
||||||
if (!daap_sessions)
|
if (!daap_sessions)
|
||||||
{
|
{
|
||||||
@ -2701,10 +2470,16 @@ daap_deinit(void)
|
|||||||
|
|
||||||
avl_free_tree(daap_sessions);
|
avl_free_tree(daap_sessions);
|
||||||
|
|
||||||
/* Free any update requests, starting at the beginning */
|
for (ur = update_requests; update_requests; ur = update_requests)
|
||||||
while ( (ur = update_requests) )
|
|
||||||
{
|
{
|
||||||
update_request_free(ur, 1 /* Close connection */);
|
update_requests = ur->next;
|
||||||
/* Note: update_requests changes */
|
|
||||||
|
if (ur->req->evcon)
|
||||||
|
{
|
||||||
|
evhttp_connection_set_closecb(ur->req->evcon, NULL, NULL);
|
||||||
|
evhttp_connection_free(ur->req->evcon);
|
||||||
|
}
|
||||||
|
|
||||||
|
free(ur);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user