[NUT-devel] [nut]: r246 - in trunk/libnut: demuxer.c priv.h

ods15 subversion at mplayerhq.hu
Sat Nov 18 18:34:18 CET 2006


Author: ods15
Date: Sat Nov 18 18:34:18 2006
New Revision: 246

Modified:
   trunk/libnut/demuxer.c
   trunk/libnut/priv.h

Log:
add smart_find_syncpoint(), find syncpoint by index entries


Modified: trunk/libnut/demuxer.c
==============================================================================
--- trunk/libnut/demuxer.c	(original)
+++ trunk/libnut/demuxer.c	Sat Nov 18 18:34:18 2006
@@ -47,7 +47,7 @@
 	if (whence != SEEK_END) {
 		// don't do anything when already in seeked position. but still flush_buf
 		off_t req = pos + (whence == SEEK_CUR ? bctello(bc) : 0);
-		if (req >= bc->file_pos && req < bc->file_pos + bc->read_len) {
+		if (req >= bc->file_pos && req <= bc->file_pos + bc->read_len) {
 			bc->buf_ptr = bc->buf + (req - bc->file_pos);
 			flush_buf(bc);
 			return;
@@ -837,11 +837,66 @@
 	return err;
 }
 
-static int smart_find_syncpoint(nut_context_t * nut, syncpoint_t * res) {
-	int err = 0;
-	if (!(nut->dopts.cache_syncpoints & 1)) return find_syncpoint(nut, 0, res, 0);
+static int smart_find_syncpoint(nut_context_t * nut, syncpoint_t * sp) {
+	struct find_syncpoint_state_s * fss = &nut->find_syncpoint_state;
+	syncpoint_list_t * sl = &nut->syncpoints;
+	int i = fss->i, err = 0;
+	off_t pos = i ? fss->pos : bctello(nut->i);
+
+	if (!(nut->dopts.cache_syncpoints & 1) || !sl->len) return find_syncpoint(nut, 0, sp, 0);
+
+	if (!i) {
+		for (i = 0; i < sl->len; i++) if (sl->s[i].pos+15 > pos) break;
+		if (i && !sl->s[i-1].seen_next) return find_syncpoint(nut, 0, sp, 0);
+
+		seek_buf(nut->i, sl->s[i].pos, SEEK_SET);
+	}
+	fss->i = i + 1;
+	fss->pos = pos;
+
+	if (!fss->begin) CHECK(find_syncpoint(nut, 0, sp, sl->s[i].pos + 15 + 8));
+	else sp->seen_next = 1;
+
+	if (sp->seen_next) { // failure
+		int j, begin = fss->begin ? fss->begin - 1 : i;
+		fss->begin = begin + 1;
+		while (sl->s[i].seen_next) {
+			if (!fss->seeked) seek_buf(nut->i, sl->s[i+1].pos, SEEK_SET);
+			fss->seeked = 1;
+			CHECK(find_syncpoint(nut, 0, sp, sl->s[i+1].pos + 15 + 8));
+			fss->seeked = 0;
+			fss->i = ++i + 1;
+			if (!sp->seen_next) break;
+		}
+		if (sp->seen_next) { // still nothing! let's linear search the whole area
+			if (!fss->seeked) seek_buf(nut->i, begin > 0 ? sl->s[begin-1].pos+15 : 0, SEEK_SET);
+			fss->seeked = 1;
+			CHECK(find_syncpoint(nut, 0, sp, 0));
+			fss->seeked = 0;
+		}
+		CHECK(add_syncpoint(nut, *sp, NULL, NULL, &i));
+		assert(i >= begin);
+
+		sl->s[i].pts_valid = 0;
+		sl->s[i].seen_next = 0;
+		for (j = 0; j < nut->stream_count; j++) {
+			sl->pts[i * nut->stream_count + j] = 0;
+			sl->eor[i * nut->stream_count + j] = 0;
+		}
+
+		memmove(sl->s + begin, sl->s + i, (sl->len - i) * sizeof(syncpoint_t));
+		memmove(sl->pts + begin * nut->stream_count, sl->pts + i * nut->stream_count, (sl->len - i) * nut->stream_count * sizeof(uint64_t));
+		memmove(sl->eor + begin * nut->stream_count, sl->eor + i * nut->stream_count, (sl->len - i) * nut->stream_count * sizeof(uint64_t));
 
-	return find_syncpoint(nut, 0, res, 0);
+		sl->len -= i-begin;
+
+		if (sp->pos < pos) { // wow, how silly!
+			fss->pos = fss->i = fss->begin = fss->seeked = 0;
+			seek_buf(nut->i, pos, SEEK_SET);
+			return smart_find_syncpoint(nut, sp);
+		}
+	}
+	fss->pos = fss->i = fss->begin = fss->seeked = 0;
 
 err_out:
 	return err;
@@ -1380,6 +1435,7 @@
 	nut->seek_status = 0;
 	nut->before_seek = 0;
 	nut->last_syncpoint = 0;
+	nut->find_syncpoint_state = (struct find_syncpoint_state_s){0,0,0,0};
 
 	nut->alloc = &nut->dopts.alloc;
 

Modified: trunk/libnut/priv.h
==============================================================================
--- trunk/libnut/priv.h	(original)
+++ trunk/libnut/priv.h	Sat Nov 18 18:34:18 2006
@@ -149,6 +149,10 @@
 	double seek_time_pos;
 
 	syncpoint_list_t syncpoints;
+	struct find_syncpoint_state_s {
+		int i, begin, seeked;
+		off_t pos;
+	} find_syncpoint_state;
 
 	// debug
 	int sync_overhead;



More information about the NUT-devel mailing list