mirror of
https://github.com/mpv-player/mpv
synced 2024-10-26 07:22:17 +02:00
Add support for smil playlist served over realrtsp
(audio and video playback only, not full smil support) git-svn-id: svn://svn.mplayerhq.hu/mplayer/trunk@22260 b3059339-0415-0410-9bf9-f77b7e298cf2
This commit is contained in:
parent
56d17cef02
commit
ef4a45551b
@ -76,6 +76,8 @@ play_tree_parser_get_line(play_tree_parser_t* p) {
|
||||
if(r > 0) {
|
||||
p->buffer_end += r;
|
||||
p->buffer[p->buffer_end] = '\0';
|
||||
while(strlen(p->buffer + p->buffer_end - r) != r)
|
||||
p->buffer[p->buffer_end - r + strlen(p->buffer + p->buffer_end - r)] = '\n';
|
||||
}
|
||||
}
|
||||
|
||||
@ -433,8 +435,10 @@ parse_m3u(play_tree_parser_t* p) {
|
||||
static play_tree_t*
|
||||
parse_smil(play_tree_parser_t* p) {
|
||||
int entrymode=0;
|
||||
char* line,source[512],*pos,*s_start,*s_end;
|
||||
char* line,source[512],*pos,*s_start,*s_end,*src_line;
|
||||
play_tree_t *list = NULL, *entry = NULL, *last_entry = NULL;
|
||||
int is_rmsmil = 0;
|
||||
unsigned int npkt, ttlpkt;
|
||||
|
||||
mp_msg(MSGT_PLAYTREE,MSGL_V,"Trying smil playlist...\n");
|
||||
|
||||
@ -443,7 +447,8 @@ parse_smil(play_tree_parser_t* p) {
|
||||
strstrip(line);
|
||||
if(line[0] == '\0') // Ignore empties
|
||||
continue;
|
||||
if (strncasecmp(line,"<smil",5)==0 || strncasecmp(line,"<?wpl",5)==0)
|
||||
if (strncasecmp(line,"<smil",5)==0 || strncasecmp(line,"<?wpl",5)==0 ||
|
||||
strncasecmp(line,"(smil-document",14)==0)
|
||||
break; // smil header found
|
||||
else
|
||||
return NULL; //line not smil exit
|
||||
@ -452,10 +457,63 @@ parse_smil(play_tree_parser_t* p) {
|
||||
mp_msg(MSGT_PLAYTREE,MSGL_V,"Detected smil playlist format\n");
|
||||
play_tree_parser_stop_keeping(p);
|
||||
|
||||
if (strncasecmp(line,"(smil-document",14)==0) {
|
||||
mp_msg(MSGT_PLAYTREE,MSGL_V,"Special smil-over-realrtsp playlist header\n");
|
||||
is_rmsmil = 1;
|
||||
if (sscanf(line, "(smil-document (ver 1.0)(npkt %u)(ttlpkt %u", &npkt, &ttlpkt) != 2) {
|
||||
mp_msg(MSGT_PLAYTREE,MSGL_WARN,"smil-over-realrtsp: header parsing failure, assuming single packet.\n");
|
||||
npkt = ttlpkt = 1;
|
||||
}
|
||||
if (ttlpkt == 0 || npkt > ttlpkt) {
|
||||
mp_msg(MSGT_PLAYTREE,MSGL_WARN,"smil-over-realrtsp: bad packet counters (npkk = %u, ttlpkt = %u), assuming single packet.\n",
|
||||
npkt, ttlpkt);
|
||||
npkt = ttlpkt = 1;
|
||||
}
|
||||
}
|
||||
|
||||
//Get entries from smil
|
||||
while((line = play_tree_parser_get_line(p)) != NULL) {
|
||||
strstrip(line);
|
||||
line = NULL;
|
||||
while((src_line = play_tree_parser_get_line(p)) != NULL) {
|
||||
strstrip(src_line);
|
||||
if (line) {
|
||||
free(line);
|
||||
line = NULL;
|
||||
}
|
||||
/* If we're parsing smil over realrtsp and this is not the last packet and
|
||||
* this is the last line in the packet (terminating with ") ) we must get
|
||||
* the next line, strip the header, and concatenate it to the current line.
|
||||
*/
|
||||
if (is_rmsmil && npkt != ttlpkt && strstr(src_line,"\")")) {
|
||||
char *payload;
|
||||
|
||||
line = strdup(src_line);
|
||||
if(!(src_line = play_tree_parser_get_line(p))) {
|
||||
mp_msg(MSGT_PLAYTREE,MSGL_WARN,"smil-over-realrtsp: can't get line from packet %u/%u.\n", npkt, ttlpkt);
|
||||
break;
|
||||
}
|
||||
strstrip(src_line);
|
||||
// Skip header, packet starts after "
|
||||
if(!(payload = strchr(src_line,'\"'))) {
|
||||
mp_msg(MSGT_PLAYTREE,MSGL_WARN,"smil-over-realrtsp: can't find start of packet, using complete line.\n");
|
||||
payload = src_line;
|
||||
} else
|
||||
payload++;
|
||||
// Skip ") at the end of the last line from the current packet
|
||||
line[strlen(line)-2] = 0;
|
||||
line = realloc(line, strlen(line)+strlen(payload));
|
||||
strcat (line, payload);
|
||||
npkt++;
|
||||
} else
|
||||
line = strdup(src_line);
|
||||
/* Unescape \" to " for smil-over-rtsp */
|
||||
if (is_rmsmil && line[0] != '\0') {
|
||||
int i, j;
|
||||
|
||||
for (i = 0; i < strlen(line); i++)
|
||||
if (line[i] == '\\' && line[i+1] == '"')
|
||||
for (j = i; line[j]; j++)
|
||||
line[j] = line[j+1];
|
||||
}
|
||||
if (line[0]=='\0')
|
||||
continue;
|
||||
if (!entrymode) { // all entries filled so far
|
||||
@ -512,6 +570,9 @@ parse_smil(play_tree_parser_t* p) {
|
||||
}
|
||||
}
|
||||
|
||||
if (line)
|
||||
free(line);
|
||||
|
||||
if(!list) return NULL; // Nothing found
|
||||
|
||||
entry = play_tree_new();
|
||||
|
@ -140,6 +140,12 @@ rtsp_session_t *rtsp_session_start(int fd, char **mrl, char *path, char *host,
|
||||
}
|
||||
|
||||
rtsp_session->real_session = init_real_rtsp_session ();
|
||||
if(!strncmp(h->streams[0]->mime_type, "application/vnd.rn-rmadriver", h->streams[0]->mime_type_size)) {
|
||||
rtsp_session->real_session->header_len = 0;
|
||||
rtsp_session->real_session->recv_size = 0;
|
||||
rtsp_session->real_session->rdt_rawdata = 1;
|
||||
mp_msg(MSGT_OPEN, MSGL_V, "smil-over-realrtsp playlist, switching to raw rdt mode\n");
|
||||
} else {
|
||||
rtsp_session->real_session->header_len =
|
||||
rmff_dump_header (h, (char *) rtsp_session->real_session->header, 1024);
|
||||
|
||||
@ -150,6 +156,7 @@ rtsp_session_t *rtsp_session_start(int fd, char **mrl, char *path, char *host,
|
||||
|
||||
rtsp_session->real_session->recv_size =
|
||||
rtsp_session->real_session->header_len;
|
||||
}
|
||||
rtsp_session->real_session->recv_read = 0;
|
||||
} else /* not a Real server : try RTP instead */
|
||||
{
|
||||
@ -219,7 +226,7 @@ int rtsp_session_read (rtsp_session_t *this, char *data, int len) {
|
||||
dest += fill;
|
||||
this->real_session->recv_read = 0;
|
||||
this->real_session->recv_size =
|
||||
real_get_rdt_chunk (this->s, (char **)&(this->real_session->recv));
|
||||
real_get_rdt_chunk (this->s, (char **)&(this->real_session->recv), this->real_session->rdt_rawdata);
|
||||
if (this->real_session->recv_size < 0) {
|
||||
this->real_session->rdteof = 1;
|
||||
this->real_session->recv_size = 0;
|
||||
|
@ -342,7 +342,7 @@ static rmff_header_t *real_parse_sdp(char *data, char **stream_rules, uint32_t b
|
||||
return header;
|
||||
}
|
||||
|
||||
int real_get_rdt_chunk(rtsp_t *rtsp_session, char **buffer) {
|
||||
int real_get_rdt_chunk(rtsp_t *rtsp_session, char **buffer, int rdt_rawdata) {
|
||||
|
||||
int n=1;
|
||||
uint8_t header[8];
|
||||
@ -414,6 +414,10 @@ int real_get_rdt_chunk(rtsp_t *rtsp_session, char **buffer) {
|
||||
else
|
||||
ph.flags=0;
|
||||
*buffer = xbuffer_ensure_size(*buffer, 12+size);
|
||||
if(rdt_rawdata) {
|
||||
n=rtsp_read_data(rtsp_session, *buffer, size-12);
|
||||
return (n <= 0) ? 0 : n;
|
||||
}
|
||||
rmff_dump_pheader(&ph, *buffer);
|
||||
size-=12;
|
||||
n=rtsp_read_data(rtsp_session, (*buffer)+12, size);
|
||||
@ -650,6 +654,7 @@ init_real_rtsp_session (void)
|
||||
real_rtsp_session = malloc (sizeof (struct real_rtsp_session_t));
|
||||
real_rtsp_session->recv = xbuffer_init (BUF_SIZE);
|
||||
real_rtsp_session->rdteof = 0;
|
||||
real_rtsp_session->rdt_rawdata = 0;
|
||||
|
||||
return real_rtsp_session;
|
||||
}
|
||||
|
@ -47,9 +47,11 @@ struct real_rtsp_session_t {
|
||||
int header_read;
|
||||
|
||||
int rdteof;
|
||||
|
||||
int rdt_rawdata;
|
||||
};
|
||||
|
||||
int real_get_rdt_chunk(rtsp_t *rtsp_session, char **buffer);
|
||||
int real_get_rdt_chunk(rtsp_t *rtsp_session, char **buffer, int rdt_rawdata);
|
||||
rmff_header_t *real_setup_and_get_header(rtsp_t *rtsp_session, uint32_t bandwidth,
|
||||
char *username, char *password);
|
||||
struct real_rtsp_session_t *init_real_rtsp_session (void);
|
||||
|
Loading…
Reference in New Issue
Block a user