Mercurial > mplayer.hg
diff playtreeparser.c @ 22242:4cabf7499fef
Add support for smil playlist served over realrtsp
(audio and video playback only, not full smil support)
author | rtogni |
---|---|
date | Sun, 18 Feb 2007 15:57:50 +0000 |
parents | 36a474903e8a |
children | e305132d083b |
line wrap: on
line diff
--- a/playtreeparser.c Sun Feb 18 15:06:54 2007 +0000 +++ b/playtreeparser.c Sun Feb 18 15:57:50 2007 +0000 @@ -76,6 +76,8 @@ 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 @@ 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 @@ 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 @@ 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 @@ } } + if (line) + free(line); + if(!list) return NULL; // Nothing found entry = play_tree_new();