Commit 572c6a38 authored by Ronald S. Bultje's avatar Ronald S. Bultje

Allow subscription to any of the streams, not just the first, available in

this RTSP/RDT session. This basically implies full RDT support, including
stream selection in ffmpeg and multi-stream backupping in ffmpeg (by mapping
each stream to an output). See "[PATCH] RTSP/RDT: subscriptions" thread on
mailinglist.

Originally committed as revision 16469 to svn://svn.ffmpeg.org/ffmpeg/trunk
parent 7c68a177
......@@ -75,6 +75,8 @@ typedef struct RTSPState {
char last_reply[2048]; /* XXX: allocate ? */
void *cur_tx;
int need_subscription;
enum AVDiscard real_setup_cache[MAX_STREAMS];
char last_subscription[1024];
} RTSPState;
typedef struct RTSPStream {
......@@ -1352,27 +1354,66 @@ static int rtsp_read_packet(AVFormatContext *s,
int ret, len;
uint8_t buf[RTP_MAX_PACKET_LENGTH];
if (rt->server_type == RTSP_SERVER_REAL && rt->need_subscription) {
if (rt->server_type == RTSP_SERVER_REAL) {
int i;
RTSPHeader reply1, *reply = &reply1;
enum AVDiscard cache[MAX_STREAMS];
char cmd[1024];
snprintf(cmd, sizeof(cmd),
"SET_PARAMETER %s RTSP/1.0\r\n"
"Subscribe: ",
s->filename);
for (i = 0; i < rt->nb_rtsp_streams; i++) {
if (i != 0) av_strlcat(cmd, ",", sizeof(cmd));
ff_rdt_subscribe_rule(cmd, sizeof(cmd), i, 0);
for (i = 0; i < s->nb_streams; i++)
cache[i] = s->streams[i]->discard;
if (!rt->need_subscription) {
if (memcmp (cache, rt->real_setup_cache,
sizeof(enum AVDiscard) * s->nb_streams)) {
av_strlcatf(cmd, sizeof(cmd),
"SET_PARAMETER %s RTSP/1.0\r\n"
"Unsubscribe: %s\r\n",
s->filename, rt->last_subscription);
rtsp_send_cmd(s, cmd, reply, NULL);
if (reply->status_code != RTSP_STATUS_OK)
return AVERROR_INVALIDDATA;
rt->need_subscription = 1;
}
}
av_strlcat(cmd, "\r\n", sizeof(cmd));
rtsp_send_cmd(s, cmd, reply, NULL);
if (reply->status_code != RTSP_STATUS_OK)
return AVERROR_INVALIDDATA;
rt->need_subscription = 0;
if (rt->state == RTSP_STATE_PLAYING)
rtsp_read_play (s);
if (rt->need_subscription) {
int r, rule_nr, first = 1;
memcpy(rt->real_setup_cache, cache,
sizeof(enum AVDiscard) * s->nb_streams);
rt->last_subscription[0] = 0;
snprintf(cmd, sizeof(cmd),
"SET_PARAMETER %s RTSP/1.0\r\n"
"Subscribe: ",
s->filename);
for (i = 0; i < rt->nb_rtsp_streams; i++) {
rule_nr = 0;
for (r = 0; r < s->nb_streams; r++) {
if (s->streams[r]->priv_data == rt->rtsp_streams[i]) {
if (s->streams[r]->discard != AVDISCARD_ALL) {
if (!first)
av_strlcat(rt->last_subscription, ",",
sizeof(rt->last_subscription));
ff_rdt_subscribe_rule(
rt->last_subscription,
sizeof(rt->last_subscription), i, rule_nr);
first = 0;
}
rule_nr++;
}
}
}
av_strlcatf(cmd, sizeof(cmd), "%s\r\n", rt->last_subscription);
rtsp_send_cmd(s, cmd, reply, NULL);
if (reply->status_code != RTSP_STATUS_OK)
return AVERROR_INVALIDDATA;
rt->need_subscription = 0;
if (rt->state == RTSP_STATE_PLAYING)
rtsp_read_play (s);
}
}
/* get next frames from the same RTP packet */
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment