Mercurial > libavformat.hg
annotate aviobuf.c @ 5836:2997c88028cd libavformat
Move the probe loop from av_open_input_file() into its own method
av_probe_input_buffer() so that it can be reused. Here are a few
differences to the original way things were probed:
- maximum probe buffer size can be specified as a parameter.
- offset within the stream to probe from can be specified as a parameter.
- instead of seeking back to the start each time a probe fails, stream
data is appended to the reallocated buffer. This lowers the amount
of data read from the stream (there is no repetition) and results in
fewer closed and reopened streams (when seeking fails).
New attempt after r22296, which was revert in r22315 due to a FATE
failure.
See the thread:
Subject: [FFmpeg-devel] [PATCH] Move av_open_input_file probe loop to its own method
Date: 2010-03-05 03:23:57 GMT
Patch by Micah F. Galizia printf("%s%s@%s.%s", "micah", "galizia", "gmail", "com").
author | stefano |
---|---|
date | Sun, 14 Mar 2010 22:40:16 +0000 |
parents | 26c471598b2f |
children | a9a36b4f83a2 |
rev | line source |
---|---|
0 | 1 /* |
2 * Buffered I/O for ffmpeg system | |
3 * Copyright (c) 2000,2001 Fabrice Bellard | |
4 * | |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1326
diff
changeset
|
5 * This file is part of FFmpeg. |
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1326
diff
changeset
|
6 * |
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1326
diff
changeset
|
7 * FFmpeg is free software; you can redistribute it and/or |
0 | 8 * modify it under the terms of the GNU Lesser General Public |
9 * License as published by the Free Software Foundation; either | |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1326
diff
changeset
|
10 * version 2.1 of the License, or (at your option) any later version. |
0 | 11 * |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1326
diff
changeset
|
12 * FFmpeg is distributed in the hope that it will be useful, |
0 | 13 * but WITHOUT ANY WARRANTY; without even the implied warranty of |
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
15 * Lesser General Public License for more details. | |
16 * | |
17 * You should have received a copy of the GNU Lesser General Public | |
1358
0899bfe4105c
Change license headers to say 'FFmpeg' instead of 'this program/this library'
diego
parents:
1326
diff
changeset
|
18 * License along with FFmpeg; if not, write to the Free Software |
896
edbe5c3717f9
Update licensing information: The FSF changed postal address.
diego
parents:
887
diff
changeset
|
19 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA |
0 | 20 */ |
3286 | 21 |
22 #include "libavutil/crc.h" | |
4233 | 23 #include "libavutil/intreadwrite.h" |
0 | 24 #include "avformat.h" |
64 | 25 #include "avio.h" |
0 | 26 #include <stdarg.h> |
27 | |
28 #define IO_BUFFER_SIZE 32768 | |
29 | |
1326 | 30 static void fill_buffer(ByteIOContext *s); |
5320
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
31 #if LIBAVFORMAT_VERSION_MAJOR >= 53 |
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
32 static int url_resetbuf(ByteIOContext *s, int flags); |
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
33 #endif |
1326 | 34 |
0 | 35 int init_put_byte(ByteIOContext *s, |
36 unsigned char *buffer, | |
37 int buffer_size, | |
38 int write_flag, | |
39 void *opaque, | |
65 | 40 int (*read_packet)(void *opaque, uint8_t *buf, int buf_size), |
554 | 41 int (*write_packet)(void *opaque, uint8_t *buf, int buf_size), |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
42 int64_t (*seek)(void *opaque, int64_t offset, int whence)) |
0 | 43 { |
44 s->buffer = buffer; | |
45 s->buffer_size = buffer_size; | |
46 s->buf_ptr = buffer; | |
4127
6afa3d7c206e
Initialize s->opaque before calling url_resetbuf().
cehoyos
parents:
4091
diff
changeset
|
47 s->opaque = opaque; |
2598
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
48 url_resetbuf(s, write_flag ? URL_WRONLY : URL_RDONLY); |
0 | 49 s->write_packet = write_packet; |
50 s->read_packet = read_packet; | |
51 s->seek = seek; | |
52 s->pos = 0; | |
53 s->must_flush = 0; | |
54 s->eof_reached = 0; | |
554 | 55 s->error = 0; |
0 | 56 s->is_streamed = 0; |
57 s->max_packet_size = 0; | |
418
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
58 s->update_checksum= NULL; |
1403
1973528c6975
move memory reading ByteIOContext init from mov.c to avobuf.c
michael
parents:
1358
diff
changeset
|
59 if(!read_packet && !write_flag){ |
1973528c6975
move memory reading ByteIOContext init from mov.c to avobuf.c
michael
parents:
1358
diff
changeset
|
60 s->pos = buffer_size; |
1973528c6975
move memory reading ByteIOContext init from mov.c to avobuf.c
michael
parents:
1358
diff
changeset
|
61 s->buf_end = s->buffer + buffer_size; |
1973528c6975
move memory reading ByteIOContext init from mov.c to avobuf.c
michael
parents:
1358
diff
changeset
|
62 } |
2783
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
63 s->read_pause = NULL; |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
64 s->read_seek = NULL; |
0 | 65 return 0; |
66 } | |
885 | 67 |
2853 | 68 ByteIOContext *av_alloc_put_byte( |
69 unsigned char *buffer, | |
70 int buffer_size, | |
71 int write_flag, | |
72 void *opaque, | |
73 int (*read_packet)(void *opaque, uint8_t *buf, int buf_size), | |
74 int (*write_packet)(void *opaque, uint8_t *buf, int buf_size), | |
4091 | 75 int64_t (*seek)(void *opaque, int64_t offset, int whence)) |
76 { | |
2853 | 77 ByteIOContext *s = av_mallocz(sizeof(ByteIOContext)); |
78 init_put_byte(s, buffer, buffer_size, write_flag, opaque, | |
79 read_packet, write_packet, seek); | |
80 return s; | |
81 } | |
82 | |
0 | 83 static void flush_buffer(ByteIOContext *s) |
84 { | |
85 if (s->buf_ptr > s->buffer) { | |
554 | 86 if (s->write_packet && !s->error){ |
87 int ret= s->write_packet(s->opaque, s->buffer, s->buf_ptr - s->buffer); | |
88 if(ret < 0){ | |
89 s->error = ret; | |
90 } | |
91 } | |
421 | 92 if(s->update_checksum){ |
418
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
93 s->checksum= s->update_checksum(s->checksum, s->checksum_ptr, s->buf_ptr - s->checksum_ptr); |
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
94 s->checksum_ptr= s->buffer; |
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
95 } |
0 | 96 s->pos += s->buf_ptr - s->buffer; |
97 } | |
98 s->buf_ptr = s->buffer; | |
99 } | |
100 | |
101 void put_byte(ByteIOContext *s, int b) | |
102 { | |
103 *(s->buf_ptr)++ = b; | |
885 | 104 if (s->buf_ptr >= s->buf_end) |
0 | 105 flush_buffer(s); |
106 } | |
107 | |
108 void put_buffer(ByteIOContext *s, const unsigned char *buf, int size) | |
109 { | |
110 while (size > 0) { | |
5275 | 111 int len = FFMIN(s->buf_end - s->buf_ptr, size); |
0 | 112 memcpy(s->buf_ptr, buf, len); |
113 s->buf_ptr += len; | |
114 | |
885 | 115 if (s->buf_ptr >= s->buf_end) |
0 | 116 flush_buffer(s); |
117 | |
118 buf += len; | |
119 size -= len; | |
120 } | |
121 } | |
122 | |
123 void put_flush_packet(ByteIOContext *s) | |
124 { | |
125 flush_buffer(s); | |
126 s->must_flush = 0; | |
127 } | |
128 | |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
129 int64_t url_fseek(ByteIOContext *s, int64_t offset, int whence) |
0 | 130 { |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
131 int64_t offset1; |
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
132 int64_t pos; |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
133 |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
134 if(!s) |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
135 return AVERROR(EINVAL); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
136 |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
137 pos = s->pos - (s->write_flag ? 0 : (s->buf_end - s->buffer)); |
0 | 138 |
139 if (whence != SEEK_CUR && whence != SEEK_SET) | |
1787
eb16c64144ee
This fixes error handling for BeOS, removing the need for some ifdefs.
mmu_man
parents:
1747
diff
changeset
|
140 return AVERROR(EINVAL); |
885 | 141 |
1323 | 142 if (whence == SEEK_CUR) { |
143 offset1 = pos + (s->buf_ptr - s->buffer); | |
144 if (offset == 0) | |
145 return offset1; | |
146 offset += offset1; | |
147 } | |
148 offset1 = offset - pos; | |
149 if (!s->must_flush && | |
4871
37da30baa62d
seek inside buffer when offset is exactly at the end, fix seeking with memory ByteIOContext
bcoudurier
parents:
4236
diff
changeset
|
150 offset1 >= 0 && offset1 <= (s->buf_end - s->buffer)) { |
1323 | 151 /* can do the seek inside the buffer */ |
152 s->buf_ptr = s->buffer + offset1; | |
1326 | 153 } else if(s->is_streamed && !s->write_flag && |
154 offset1 >= 0 && offset1 < (s->buf_end - s->buffer) + (1<<16)){ | |
155 while(s->pos < offset && !s->eof_reached) | |
156 fill_buffer(s); | |
2816
1523342b58b3
return error when url_fseek could not read until desired offset in streamed mode
bcoudurier
parents:
2783
diff
changeset
|
157 if (s->eof_reached) |
1523342b58b3
return error when url_fseek could not read until desired offset in streamed mode
bcoudurier
parents:
2783
diff
changeset
|
158 return AVERROR(EPIPE); |
1326 | 159 s->buf_ptr = s->buf_end + offset - s->pos; |
1323 | 160 } else { |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
161 int64_t res = AVERROR(EPIPE); |
1747
fa70e732d2db
Fix misbehaviour in url_fseek() when seeking fails.
gpoirier
parents:
1741
diff
changeset
|
162 |
4206 | 163 #if CONFIG_MUXERS || CONFIG_NETWORK |
1323 | 164 if (s->write_flag) { |
0 | 165 flush_buffer(s); |
166 s->must_flush = 1; | |
3614
71fdc3f7c771
Only reset buffer state if seeking is successful; update seek reg ref.
bcoudurier
parents:
3286
diff
changeset
|
167 } |
4206 | 168 #endif /* CONFIG_MUXERS || CONFIG_NETWORK */ |
1747
fa70e732d2db
Fix misbehaviour in url_fseek() when seeking fails.
gpoirier
parents:
1741
diff
changeset
|
169 if (!s->seek || (res = s->seek(s->opaque, offset, SEEK_SET)) < 0) |
fa70e732d2db
Fix misbehaviour in url_fseek() when seeking fails.
gpoirier
parents:
1741
diff
changeset
|
170 return res; |
3614
71fdc3f7c771
Only reset buffer state if seeking is successful; update seek reg ref.
bcoudurier
parents:
3286
diff
changeset
|
171 if (!s->write_flag) |
71fdc3f7c771
Only reset buffer state if seeking is successful; update seek reg ref.
bcoudurier
parents:
3286
diff
changeset
|
172 s->buf_end = s->buffer; |
71fdc3f7c771
Only reset buffer state if seeking is successful; update seek reg ref.
bcoudurier
parents:
3286
diff
changeset
|
173 s->buf_ptr = s->buffer; |
1323 | 174 s->pos = offset; |
0 | 175 } |
1323 | 176 s->eof_reached = 0; |
0 | 177 return offset; |
178 } | |
179 | |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
180 void url_fskip(ByteIOContext *s, int64_t offset) |
0 | 181 { |
182 url_fseek(s, offset, SEEK_CUR); | |
183 } | |
184 | |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
185 int64_t url_ftell(ByteIOContext *s) |
0 | 186 { |
187 return url_fseek(s, 0, SEEK_CUR); | |
188 } | |
189 | |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
190 int64_t url_fsize(ByteIOContext *s) |
764
cdb845a57ae4
drop most url_fileno() calls (allows to use ByteIOContext directly in caller apps instead of URLProtocol)
aurel
parents:
719
diff
changeset
|
191 { |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
192 int64_t size; |
885 | 193 |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
194 if(!s) |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
195 return AVERROR(EINVAL); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
196 |
764
cdb845a57ae4
drop most url_fileno() calls (allows to use ByteIOContext directly in caller apps instead of URLProtocol)
aurel
parents:
719
diff
changeset
|
197 if (!s->seek) |
1787
eb16c64144ee
This fixes error handling for BeOS, removing the need for some ifdefs.
mmu_man
parents:
1747
diff
changeset
|
198 return AVERROR(EPIPE); |
1612
a6eaa0762191
seekless filesize retrieving support in 7 lines of code, also doesnt break compatibility
michael
parents:
1592
diff
changeset
|
199 size = s->seek(s->opaque, 0, AVSEEK_SIZE); |
a6eaa0762191
seekless filesize retrieving support in 7 lines of code, also doesnt break compatibility
michael
parents:
1592
diff
changeset
|
200 if(size<0){ |
1741
e9c7714b1c34
proper error handling in file size retrieval, patch by Ronald S. Bultje rbultje at ronald bitfreak net
bcoudurier
parents:
1613
diff
changeset
|
201 if ((size = s->seek(s->opaque, -1, SEEK_END)) < 0) |
e9c7714b1c34
proper error handling in file size retrieval, patch by Ronald S. Bultje rbultje at ronald bitfreak net
bcoudurier
parents:
1613
diff
changeset
|
202 return size; |
e9c7714b1c34
proper error handling in file size retrieval, patch by Ronald S. Bultje rbultje at ronald bitfreak net
bcoudurier
parents:
1613
diff
changeset
|
203 size++; |
1613 | 204 s->seek(s->opaque, s->pos, SEEK_SET); |
1612
a6eaa0762191
seekless filesize retrieving support in 7 lines of code, also doesnt break compatibility
michael
parents:
1592
diff
changeset
|
205 } |
764
cdb845a57ae4
drop most url_fileno() calls (allows to use ByteIOContext directly in caller apps instead of URLProtocol)
aurel
parents:
719
diff
changeset
|
206 return size; |
cdb845a57ae4
drop most url_fileno() calls (allows to use ByteIOContext directly in caller apps instead of URLProtocol)
aurel
parents:
719
diff
changeset
|
207 } |
cdb845a57ae4
drop most url_fileno() calls (allows to use ByteIOContext directly in caller apps instead of URLProtocol)
aurel
parents:
719
diff
changeset
|
208 |
0 | 209 int url_feof(ByteIOContext *s) |
210 { | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
211 if(!s) |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
212 return 0; |
0 | 213 return s->eof_reached; |
214 } | |
215 | |
554 | 216 int url_ferror(ByteIOContext *s) |
217 { | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
218 if(!s) |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
219 return 0; |
554 | 220 return s->error; |
221 } | |
222 | |
0 | 223 void put_le32(ByteIOContext *s, unsigned int val) |
224 { | |
225 put_byte(s, val); | |
226 put_byte(s, val >> 8); | |
227 put_byte(s, val >> 16); | |
228 put_byte(s, val >> 24); | |
229 } | |
230 | |
231 void put_be32(ByteIOContext *s, unsigned int val) | |
232 { | |
233 put_byte(s, val >> 24); | |
234 put_byte(s, val >> 16); | |
235 put_byte(s, val >> 8); | |
236 put_byte(s, val); | |
237 } | |
238 | |
239 void put_strz(ByteIOContext *s, const char *str) | |
240 { | |
241 if (str) | |
242 put_buffer(s, (const unsigned char *) str, strlen(str) + 1); | |
243 else | |
244 put_byte(s, 0); | |
245 } | |
246 | |
65 | 247 void put_le64(ByteIOContext *s, uint64_t val) |
0 | 248 { |
65 | 249 put_le32(s, (uint32_t)(val & 0xffffffff)); |
250 put_le32(s, (uint32_t)(val >> 32)); | |
0 | 251 } |
252 | |
65 | 253 void put_be64(ByteIOContext *s, uint64_t val) |
0 | 254 { |
65 | 255 put_be32(s, (uint32_t)(val >> 32)); |
256 put_be32(s, (uint32_t)(val & 0xffffffff)); | |
0 | 257 } |
258 | |
259 void put_le16(ByteIOContext *s, unsigned int val) | |
260 { | |
261 put_byte(s, val); | |
262 put_byte(s, val >> 8); | |
263 } | |
264 | |
265 void put_be16(ByteIOContext *s, unsigned int val) | |
266 { | |
267 put_byte(s, val >> 8); | |
268 put_byte(s, val); | |
269 } | |
270 | |
937 | 271 void put_le24(ByteIOContext *s, unsigned int val) |
272 { | |
273 put_le16(s, val & 0xffff); | |
274 put_byte(s, val >> 16); | |
275 } | |
276 | |
822 | 277 void put_be24(ByteIOContext *s, unsigned int val) |
278 { | |
279 put_be16(s, val >> 8); | |
280 put_byte(s, val); | |
281 } | |
282 | |
0 | 283 void put_tag(ByteIOContext *s, const char *tag) |
284 { | |
285 while (*tag) { | |
286 put_byte(s, *tag++); | |
287 } | |
288 } | |
289 | |
290 /* Input stream */ | |
291 | |
292 static void fill_buffer(ByteIOContext *s) | |
293 { | |
4020
9d94163ca066
always use the whole buffer for reading w/ packetized sources to avoid packet truncation
henry
parents:
3998
diff
changeset
|
294 uint8_t *dst= !s->max_packet_size && s->buf_end - s->buffer < s->buffer_size ? s->buf_ptr : s->buffer; |
3998
692e5298a27a
Append read data onto the buffer instead of overwriting, this ensures
michael
parents:
3982
diff
changeset
|
295 int len= s->buffer_size - (dst - s->buffer); |
692e5298a27a
Append read data onto the buffer instead of overwriting, this ensures
michael
parents:
3982
diff
changeset
|
296 |
692e5298a27a
Append read data onto the buffer instead of overwriting, this ensures
michael
parents:
3982
diff
changeset
|
297 assert(s->buf_ptr == s->buf_end); |
0 | 298 |
299 /* no need to do anything if EOF already reached */ | |
300 if (s->eof_reached) | |
301 return; | |
418
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
302 |
3998
692e5298a27a
Append read data onto the buffer instead of overwriting, this ensures
michael
parents:
3982
diff
changeset
|
303 if(s->update_checksum && dst == s->buffer){ |
780 | 304 if(s->buf_end > s->checksum_ptr) |
305 s->checksum= s->update_checksum(s->checksum, s->checksum_ptr, s->buf_end - s->checksum_ptr); | |
418
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
306 s->checksum_ptr= s->buffer; |
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
307 } |
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
308 |
2576 | 309 if(s->read_packet) |
3998
692e5298a27a
Append read data onto the buffer instead of overwriting, this ensures
michael
parents:
3982
diff
changeset
|
310 len = s->read_packet(s->opaque, dst, len); |
692e5298a27a
Append read data onto the buffer instead of overwriting, this ensures
michael
parents:
3982
diff
changeset
|
311 else |
692e5298a27a
Append read data onto the buffer instead of overwriting, this ensures
michael
parents:
3982
diff
changeset
|
312 len = 0; |
0 | 313 if (len <= 0) { |
314 /* do not modify buffer if EOF reached so that a seek back can | |
315 be done without rereading data */ | |
316 s->eof_reached = 1; | |
2082 | 317 if(len<0) |
318 s->error= len; | |
0 | 319 } else { |
320 s->pos += len; | |
3998
692e5298a27a
Append read data onto the buffer instead of overwriting, this ensures
michael
parents:
3982
diff
changeset
|
321 s->buf_ptr = dst; |
692e5298a27a
Append read data onto the buffer instead of overwriting, this ensures
michael
parents:
3982
diff
changeset
|
322 s->buf_end = dst + len; |
0 | 323 } |
324 } | |
325 | |
4091 | 326 unsigned long ff_crc04C11DB7_update(unsigned long checksum, const uint8_t *buf, |
327 unsigned int len) | |
328 { | |
2893 | 329 return av_crc(av_crc_get_table(AV_CRC_32_IEEE), checksum, buf, len); |
2683
153d6efc05b8
rename av_crc04C11DB7_update to ff_crc04C11DB7_update and move it to aviobuf.c so it can be reused by other (de)muxers
bcoudurier
parents:
2598
diff
changeset
|
330 } |
153d6efc05b8
rename av_crc04C11DB7_update to ff_crc04C11DB7_update and move it to aviobuf.c so it can be reused by other (de)muxers
bcoudurier
parents:
2598
diff
changeset
|
331 |
4091 | 332 unsigned long get_checksum(ByteIOContext *s) |
333 { | |
418
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
334 s->checksum= s->update_checksum(s->checksum, s->checksum_ptr, s->buf_ptr - s->checksum_ptr); |
421 | 335 s->update_checksum= NULL; |
418
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
336 return s->checksum; |
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
337 } |
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
338 |
4091 | 339 void init_checksum(ByteIOContext *s, |
340 unsigned long (*update_checksum)(unsigned long c, const uint8_t *p, unsigned int len), | |
341 unsigned long checksum) | |
342 { | |
418
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
343 s->update_checksum= update_checksum; |
421 | 344 if(s->update_checksum){ |
1184 | 345 s->checksum= checksum; |
421 | 346 s->checksum_ptr= s->buf_ptr; |
347 } | |
418
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
348 } |
41da3366d341
checksuming for nut & nice checksum API for libavformat
michael
parents:
389
diff
changeset
|
349 |
0 | 350 /* XXX: put an inline version */ |
351 int get_byte(ByteIOContext *s) | |
352 { | |
353 if (s->buf_ptr < s->buf_end) { | |
354 return *s->buf_ptr++; | |
355 } else { | |
356 fill_buffer(s); | |
357 if (s->buf_ptr < s->buf_end) | |
358 return *s->buf_ptr++; | |
359 else | |
360 return 0; | |
361 } | |
362 } | |
363 | |
364 int url_fgetc(ByteIOContext *s) | |
365 { | |
366 if (s->buf_ptr < s->buf_end) { | |
367 return *s->buf_ptr++; | |
368 } else { | |
369 fill_buffer(s); | |
370 if (s->buf_ptr < s->buf_end) | |
371 return *s->buf_ptr++; | |
372 else | |
373 return URL_EOF; | |
374 } | |
375 } | |
376 | |
377 int get_buffer(ByteIOContext *s, unsigned char *buf, int size) | |
378 { | |
379 int len, size1; | |
380 | |
381 size1 = size; | |
382 while (size > 0) { | |
383 len = s->buf_end - s->buf_ptr; | |
384 if (len > size) | |
385 len = size; | |
386 if (len == 0) { | |
719 | 387 if(size > s->buffer_size && !s->update_checksum){ |
2576 | 388 if(s->read_packet) |
2577 | 389 len = s->read_packet(s->opaque, buf, size); |
719 | 390 if (len <= 0) { |
391 /* do not modify buffer if EOF reached so that a seek back can | |
392 be done without rereading data */ | |
393 s->eof_reached = 1; | |
394 if(len<0) | |
395 s->error= len; | |
396 break; | |
397 } else { | |
398 s->pos += len; | |
399 size -= len; | |
400 buf += len; | |
401 s->buf_ptr = s->buffer; | |
402 s->buf_end = s->buffer/* + len*/; | |
403 } | |
404 }else{ | |
405 fill_buffer(s); | |
406 len = s->buf_end - s->buf_ptr; | |
407 if (len == 0) | |
408 break; | |
409 } | |
0 | 410 } else { |
411 memcpy(buf, s->buf_ptr, len); | |
412 buf += len; | |
413 s->buf_ptr += len; | |
414 size -= len; | |
415 } | |
416 } | |
5253
a2289b41a9f2
Make get_buffer and get_partial_buffer return url_ferror or AVERROR_EOF as
reimar
parents:
4871
diff
changeset
|
417 if (size1 == size) { |
a2289b41a9f2
Make get_buffer and get_partial_buffer return url_ferror or AVERROR_EOF as
reimar
parents:
4871
diff
changeset
|
418 if (url_ferror(s)) return url_ferror(s); |
a2289b41a9f2
Make get_buffer and get_partial_buffer return url_ferror or AVERROR_EOF as
reimar
parents:
4871
diff
changeset
|
419 if (url_feof(s)) return AVERROR_EOF; |
a2289b41a9f2
Make get_buffer and get_partial_buffer return url_ferror or AVERROR_EOF as
reimar
parents:
4871
diff
changeset
|
420 } |
0 | 421 return size1 - size; |
422 } | |
423 | |
389
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
424 int get_partial_buffer(ByteIOContext *s, unsigned char *buf, int size) |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
425 { |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
426 int len; |
885 | 427 |
643 | 428 if(size<0) |
429 return -1; | |
389
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
430 |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
431 len = s->buf_end - s->buf_ptr; |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
432 if (len == 0) { |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
433 fill_buffer(s); |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
434 len = s->buf_end - s->buf_ptr; |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
435 } |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
436 if (len > size) |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
437 len = size; |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
438 memcpy(buf, s->buf_ptr, len); |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
439 s->buf_ptr += len; |
5253
a2289b41a9f2
Make get_buffer and get_partial_buffer return url_ferror or AVERROR_EOF as
reimar
parents:
4871
diff
changeset
|
440 if (!len) { |
a2289b41a9f2
Make get_buffer and get_partial_buffer return url_ferror or AVERROR_EOF as
reimar
parents:
4871
diff
changeset
|
441 if (url_ferror(s)) return url_ferror(s); |
a2289b41a9f2
Make get_buffer and get_partial_buffer return url_ferror or AVERROR_EOF as
reimar
parents:
4871
diff
changeset
|
442 if (url_feof(s)) return AVERROR_EOF; |
a2289b41a9f2
Make get_buffer and get_partial_buffer return url_ferror or AVERROR_EOF as
reimar
parents:
4871
diff
changeset
|
443 } |
389
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
444 return len; |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
445 } |
e14fcd57ad2f
decode latency patch by (Leon van Stuivenberg <l dot vanstuivenberg at chello dot nl>)
michael
parents:
364
diff
changeset
|
446 |
0 | 447 unsigned int get_le16(ByteIOContext *s) |
448 { | |
449 unsigned int val; | |
450 val = get_byte(s); | |
451 val |= get_byte(s) << 8; | |
452 return val; | |
453 } | |
454 | |
937 | 455 unsigned int get_le24(ByteIOContext *s) |
456 { | |
457 unsigned int val; | |
458 val = get_le16(s); | |
459 val |= get_byte(s) << 16; | |
460 return val; | |
461 } | |
462 | |
0 | 463 unsigned int get_le32(ByteIOContext *s) |
464 { | |
465 unsigned int val; | |
822 | 466 val = get_le16(s); |
467 val |= get_le16(s) << 16; | |
0 | 468 return val; |
469 } | |
470 | |
65 | 471 uint64_t get_le64(ByteIOContext *s) |
0 | 472 { |
65 | 473 uint64_t val; |
474 val = (uint64_t)get_le32(s); | |
475 val |= (uint64_t)get_le32(s) << 32; | |
0 | 476 return val; |
477 } | |
478 | |
479 unsigned int get_be16(ByteIOContext *s) | |
480 { | |
481 unsigned int val; | |
482 val = get_byte(s) << 8; | |
483 val |= get_byte(s); | |
484 return val; | |
485 } | |
486 | |
822 | 487 unsigned int get_be24(ByteIOContext *s) |
488 { | |
489 unsigned int val; | |
490 val = get_be16(s) << 8; | |
491 val |= get_byte(s); | |
492 return val; | |
493 } | |
0 | 494 unsigned int get_be32(ByteIOContext *s) |
495 { | |
496 unsigned int val; | |
822 | 497 val = get_be16(s) << 16; |
498 val |= get_be16(s); | |
0 | 499 return val; |
500 } | |
501 | |
502 char *get_strz(ByteIOContext *s, char *buf, int maxlen) | |
503 { | |
504 int i = 0; | |
505 char c; | |
506 | |
507 while ((c = get_byte(s))) { | |
508 if (i < maxlen-1) | |
509 buf[i++] = c; | |
510 } | |
885 | 511 |
0 | 512 buf[i] = 0; /* Ensure null terminated, but may be truncated */ |
513 | |
514 return buf; | |
515 } | |
516 | |
65 | 517 uint64_t get_be64(ByteIOContext *s) |
0 | 518 { |
65 | 519 uint64_t val; |
520 val = (uint64_t)get_be32(s) << 32; | |
521 val |= (uint64_t)get_be32(s); | |
0 | 522 return val; |
523 } | |
524 | |
2700 | 525 uint64_t ff_get_v(ByteIOContext *bc){ |
2699 | 526 uint64_t val = 0; |
527 int tmp; | |
528 | |
529 do{ | |
530 tmp = get_byte(bc); | |
531 val= (val<<7) + (tmp&127); | |
532 }while(tmp&128); | |
533 return val; | |
534 } | |
535 | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
536 int url_fdopen(ByteIOContext **s, URLContext *h) |
0 | 537 { |
65 | 538 uint8_t *buffer; |
0 | 539 int buffer_size, max_packet_size; |
540 | |
541 max_packet_size = url_get_max_packet_size(h); | |
542 if (max_packet_size) { | |
543 buffer_size = max_packet_size; /* no need to bufferize more than one packet */ | |
544 } else { | |
545 buffer_size = IO_BUFFER_SIZE; | |
546 } | |
547 buffer = av_malloc(buffer_size); | |
548 if (!buffer) | |
1787
eb16c64144ee
This fixes error handling for BeOS, removing the need for some ifdefs.
mmu_man
parents:
1747
diff
changeset
|
549 return AVERROR(ENOMEM); |
0 | 550 |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
551 *s = av_mallocz(sizeof(ByteIOContext)); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
552 if(!*s) { |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
553 av_free(buffer); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
554 return AVERROR(ENOMEM); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
555 } |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
556 |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
557 if (init_put_byte(*s, buffer, buffer_size, |
364
0d74e8abcb3d
avio patch by (Gildas Bazin <gbazin at altern dot org>)
michael
parents:
277
diff
changeset
|
558 (h->flags & URL_WRONLY || h->flags & URL_RDWR), h, |
2831 | 559 url_read, url_write, url_seek) < 0) { |
0 | 560 av_free(buffer); |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
561 av_freep(s); |
2274
b21c2af60bc9
Replace all occurrences of AVERROR_IO with AVERROR(EIO).
takis
parents:
2082
diff
changeset
|
562 return AVERROR(EIO); |
0 | 563 } |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
564 (*s)->is_streamed = h->is_streamed; |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
565 (*s)->max_packet_size = max_packet_size; |
2783
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
566 if(h->prot) { |
2839
b51319dd86e5
Merge recently added and still unused play and pause functions.
michael
parents:
2831
diff
changeset
|
567 (*s)->read_pause = (int (*)(void *, int))h->prot->url_read_pause; |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
568 (*s)->read_seek = (int64_t (*)(void *, int, int64_t, int))h->prot->url_read_seek; |
2783
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
569 } |
0 | 570 return 0; |
571 } | |
572 | |
573 int url_setbufsize(ByteIOContext *s, int buf_size) | |
574 { | |
65 | 575 uint8_t *buffer; |
0 | 576 buffer = av_malloc(buf_size); |
577 if (!buffer) | |
1787
eb16c64144ee
This fixes error handling for BeOS, removing the need for some ifdefs.
mmu_man
parents:
1747
diff
changeset
|
578 return AVERROR(ENOMEM); |
0 | 579 |
580 av_free(s->buffer); | |
581 s->buffer = buffer; | |
582 s->buffer_size = buf_size; | |
583 s->buf_ptr = buffer; | |
2598
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
584 url_resetbuf(s, s->write_flag ? URL_WRONLY : URL_RDONLY); |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
585 return 0; |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
586 } |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
587 |
5320
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
588 #if LIBAVFORMAT_VERSION_MAJOR < 53 |
2598
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
589 int url_resetbuf(ByteIOContext *s, int flags) |
5320
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
590 #else |
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
591 static int url_resetbuf(ByteIOContext *s, int flags) |
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
592 #endif |
2598
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
593 { |
5320
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
594 #if LIBAVFORMAT_VERSION_MAJOR < 53 |
2598
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
595 URLContext *h = s->opaque; |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
596 if ((flags & URL_RDWR) || (h && h->flags != flags && !h->flags & URL_RDWR)) |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
597 return AVERROR(EINVAL); |
5320
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
598 #else |
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
599 assert(flags == URL_WRONLY || flags == URL_RDONLY); |
db1e4c61789a
Make url_resetbuf() assert on wrong flags passed and make it static on next
benoit
parents:
5275
diff
changeset
|
600 #endif |
2598
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
601 |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
602 if (flags & URL_WRONLY) { |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
603 s->buf_end = s->buffer + s->buffer_size; |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
604 s->write_flag = 1; |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
605 } else { |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
606 s->buf_end = s->buffer; |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
607 s->write_flag = 0; |
fc7f8ee4700b
Add functionality to set the direction of a ByteIOContext buffer.
benoit
parents:
2577
diff
changeset
|
608 } |
0 | 609 return 0; |
610 } | |
611 | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
612 int url_fopen(ByteIOContext **s, const char *filename, int flags) |
0 | 613 { |
614 URLContext *h; | |
615 int err; | |
616 | |
617 err = url_open(&h, filename, flags); | |
618 if (err < 0) | |
619 return err; | |
620 err = url_fdopen(s, h); | |
621 if (err < 0) { | |
622 url_close(h); | |
623 return err; | |
624 } | |
625 return 0; | |
626 } | |
627 | |
628 int url_fclose(ByteIOContext *s) | |
629 { | |
630 URLContext *h = s->opaque; | |
885 | 631 |
0 | 632 av_free(s->buffer); |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
633 av_free(s); |
0 | 634 return url_close(h); |
635 } | |
636 | |
637 URLContext *url_fileno(ByteIOContext *s) | |
638 { | |
639 return s->opaque; | |
640 } | |
641 | |
4206 | 642 #if CONFIG_MUXERS |
0 | 643 int url_fprintf(ByteIOContext *s, const char *fmt, ...) |
644 { | |
645 va_list ap; | |
646 char buf[4096]; | |
647 int ret; | |
648 | |
649 va_start(ap, fmt); | |
650 ret = vsnprintf(buf, sizeof(buf), fmt, ap); | |
651 va_end(ap); | |
652 put_buffer(s, buf, strlen(buf)); | |
653 return ret; | |
654 } | |
858
66cc656ea404
Replace CONFIG_ENCODERS/CONFIG_DECODERS with CONFIG_MUXERS/CONFIG_DEMUXERS
diego
parents:
823
diff
changeset
|
655 #endif //CONFIG_MUXERS |
0 | 656 |
657 char *url_fgets(ByteIOContext *s, char *buf, int buf_size) | |
658 { | |
659 int c; | |
660 char *q; | |
661 | |
662 c = url_fgetc(s); | |
663 if (c == EOF) | |
664 return NULL; | |
665 q = buf; | |
666 for(;;) { | |
667 if (c == EOF || c == '\n') | |
668 break; | |
669 if ((q - buf) < buf_size - 1) | |
670 *q++ = c; | |
671 c = url_fgetc(s); | |
672 } | |
673 if (buf_size > 0) | |
674 *q = '\0'; | |
675 return buf; | |
676 } | |
677 | |
678 int url_fget_max_packet_size(ByteIOContext *s) | |
679 { | |
680 return s->max_packet_size; | |
681 } | |
682 | |
2839
b51319dd86e5
Merge recently added and still unused play and pause functions.
michael
parents:
2831
diff
changeset
|
683 int av_url_read_fpause(ByteIOContext *s, int pause) |
2783
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
684 { |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
685 if (!s->read_pause) |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
686 return AVERROR(ENOSYS); |
2839
b51319dd86e5
Merge recently added and still unused play and pause functions.
michael
parents:
2831
diff
changeset
|
687 return s->read_pause(s->opaque, pause); |
2783
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
688 } |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
689 |
4091 | 690 int64_t av_url_read_fseek(ByteIOContext *s, int stream_index, |
691 int64_t timestamp, int flags) | |
2783
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
692 { |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
693 URLContext *h = s->opaque; |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
694 int64_t ret; |
2783
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
695 if (!s->read_seek) |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
696 return AVERROR(ENOSYS); |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
697 ret = s->read_seek(h, stream_index, timestamp, flags); |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
698 if(ret >= 0) { |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
699 s->buf_ptr = s->buf_end; // Flush buffer |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
700 s->pos = s->seek(h, 0, SEEK_CUR); |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
701 } |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
702 return ret; |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
703 } |
1a9db30c1d1c
Extend ByteIOContext and add the buffered IO functions:
andoma
parents:
2771
diff
changeset
|
704 |
1546
41356096b2d0
Fix compile with --disable-muxers, patch by Lo«Ác Le Loarer, lll+ffmpeg m4x org.
diego
parents:
1403
diff
changeset
|
705 /* url_open_dyn_buf and url_close_dyn_buf are used in rtp.c to send a response |
4206 | 706 * back to the server even if CONFIG_MUXERS is false. */ |
707 #if CONFIG_MUXERS || CONFIG_NETWORK | |
0 | 708 /* buffer handling */ |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
709 int url_open_buf(ByteIOContext **s, uint8_t *buf, int buf_size, int flags) |
0 | 710 { |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
711 int ret; |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
712 *s = av_mallocz(sizeof(ByteIOContext)); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
713 if(!*s) |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
714 return AVERROR(ENOMEM); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
715 ret = init_put_byte(*s, buf, buf_size, |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
716 (flags & URL_WRONLY || flags & URL_RDWR), |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
717 NULL, NULL, NULL, NULL); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
718 if(ret != 0) |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
719 av_freep(s); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
720 return ret; |
0 | 721 } |
722 | |
723 int url_close_buf(ByteIOContext *s) | |
724 { | |
725 put_flush_packet(s); | |
726 return s->buf_ptr - s->buffer; | |
727 } | |
728 | |
729 /* output in a dynamic buffer */ | |
730 | |
731 typedef struct DynBuffer { | |
732 int pos, size, allocated_size; | |
65 | 733 uint8_t *buffer; |
0 | 734 int io_buffer_size; |
65 | 735 uint8_t io_buffer[1]; |
0 | 736 } DynBuffer; |
737 | |
554 | 738 static int dyn_buf_write(void *opaque, uint8_t *buf, int buf_size) |
0 | 739 { |
740 DynBuffer *d = opaque; | |
3982
1505b1ddab11
Make size variables in dyn_buf_write unsigned so gcc will not optimize the
reimar
parents:
3973
diff
changeset
|
741 unsigned new_size, new_allocated_size; |
885 | 742 |
0 | 743 /* reallocate buffer if needed */ |
744 new_size = d->pos + buf_size; | |
745 new_allocated_size = d->allocated_size; | |
639 | 746 if(new_size < d->pos || new_size > INT_MAX/2) |
747 return -1; | |
0 | 748 while (new_size > new_allocated_size) { |
749 if (!new_allocated_size) | |
750 new_allocated_size = new_size; | |
751 else | |
885 | 752 new_allocated_size += new_allocated_size / 2 + 1; |
0 | 753 } |
885 | 754 |
0 | 755 if (new_allocated_size > d->allocated_size) { |
93
69ed49c151bf
ffserver deallocate ctx->streams on closing patch by (Mark Hills <mark at pogo dot org dot uk>)
michaelni
parents:
65
diff
changeset
|
756 d->buffer = av_realloc(d->buffer, new_allocated_size); |
69ed49c151bf
ffserver deallocate ctx->streams on closing patch by (Mark Hills <mark at pogo dot org dot uk>)
michaelni
parents:
65
diff
changeset
|
757 if(d->buffer == NULL) |
4231
07ea426be9a3
Replace nonsense -1234 return value in dyn_buf_write by proper AVERROR(ENOMEM)
reimar
parents:
4206
diff
changeset
|
758 return AVERROR(ENOMEM); |
0 | 759 d->allocated_size = new_allocated_size; |
760 } | |
761 memcpy(d->buffer + d->pos, buf, buf_size); | |
762 d->pos = new_size; | |
763 if (d->pos > d->size) | |
764 d->size = d->pos; | |
554 | 765 return buf_size; |
0 | 766 } |
767 | |
554 | 768 static int dyn_packet_buf_write(void *opaque, uint8_t *buf, int buf_size) |
0 | 769 { |
770 unsigned char buf1[4]; | |
554 | 771 int ret; |
0 | 772 |
773 /* packetized write: output the header */ | |
4233 | 774 AV_WB32(buf1, buf_size); |
554 | 775 ret= dyn_buf_write(opaque, buf1, 4); |
776 if(ret < 0) | |
777 return ret; | |
0 | 778 |
779 /* then the data */ | |
554 | 780 return dyn_buf_write(opaque, buf, buf_size); |
0 | 781 } |
782 | |
3973
549a09cf23fe
Remove offset_t typedef and use int64_t directly instead.
diego
parents:
3614
diff
changeset
|
783 static int64_t dyn_buf_seek(void *opaque, int64_t offset, int whence) |
0 | 784 { |
785 DynBuffer *d = opaque; | |
786 | |
787 if (whence == SEEK_CUR) | |
788 offset += d->pos; | |
789 else if (whence == SEEK_END) | |
790 offset += d->size; | |
791 if (offset < 0 || offset > 0x7fffffffLL) | |
792 return -1; | |
793 d->pos = offset; | |
794 return 0; | |
795 } | |
796 | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
797 static int url_open_dyn_buf_internal(ByteIOContext **s, int max_packet_size) |
0 | 798 { |
799 DynBuffer *d; | |
4235
ce71070e447d
Make io_buffer_size unsigned to avoid a warning about comparing
reimar
parents:
4234
diff
changeset
|
800 int ret; |
4236
63c721da20e5
Merge declaration and initialization of io_buffer_size
reimar
parents:
4235
diff
changeset
|
801 unsigned io_buffer_size = max_packet_size ? max_packet_size : 1024; |
885 | 802 |
639 | 803 if(sizeof(DynBuffer) + io_buffer_size < io_buffer_size) |
804 return -1; | |
4232
5defcf4194fb
Use av_mallocz instead of explicitly zeroing in url_open_dyn_buf_internal.
reimar
parents:
4231
diff
changeset
|
805 d = av_mallocz(sizeof(DynBuffer) + io_buffer_size); |
0 | 806 if (!d) |
4234
3d57729868a9
Return AVERROR(ENOMEM) instead of -1 when malloc fails in url_open_dyn_buf_internal
reimar
parents:
4233
diff
changeset
|
807 return AVERROR(ENOMEM); |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
808 *s = av_mallocz(sizeof(ByteIOContext)); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
809 if(!*s) { |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
810 av_free(d); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
811 return AVERROR(ENOMEM); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
812 } |
0 | 813 d->io_buffer_size = io_buffer_size; |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
814 ret = init_put_byte(*s, d->io_buffer, io_buffer_size, |
885 | 815 1, d, NULL, |
816 max_packet_size ? dyn_packet_buf_write : dyn_buf_write, | |
0 | 817 max_packet_size ? NULL : dyn_buf_seek); |
818 if (ret == 0) { | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
819 (*s)->max_packet_size = max_packet_size; |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
820 } else { |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
821 av_free(d); |
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
822 av_freep(s); |
0 | 823 } |
824 return ret; | |
825 } | |
826 | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
827 int url_open_dyn_buf(ByteIOContext **s) |
0 | 828 { |
829 return url_open_dyn_buf_internal(s, 0); | |
830 } | |
831 | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
832 int url_open_dyn_packet_buf(ByteIOContext **s, int max_packet_size) |
0 | 833 { |
834 if (max_packet_size <= 0) | |
835 return -1; | |
836 return url_open_dyn_buf_internal(s, max_packet_size); | |
837 } | |
838 | |
65 | 839 int url_close_dyn_buf(ByteIOContext *s, uint8_t **pbuffer) |
0 | 840 { |
841 DynBuffer *d = s->opaque; | |
842 int size; | |
843 | |
844 put_flush_packet(s); | |
845 | |
846 *pbuffer = d->buffer; | |
847 size = d->size; | |
848 av_free(d); | |
2771
d52c718e83f9
Use dynamically allocated ByteIOContext in AVFormatContext
andoma
parents:
2700
diff
changeset
|
849 av_free(s); |
0 | 850 return size; |
851 } | |
1546
41356096b2d0
Fix compile with --disable-muxers, patch by Lo«Ác Le Loarer, lll+ffmpeg m4x org.
diego
parents:
1403
diff
changeset
|
852 #endif /* CONFIG_MUXERS || CONFIG_NETWORK */ |