diff options
Diffstat (limited to 'songdbj/com/jcraft/jogg')
-rw-r--r-- | songdbj/com/jcraft/jogg/Buffer.java | 541 | ||||
-rw-r--r-- | songdbj/com/jcraft/jogg/Packet.java | 82 | ||||
-rw-r--r-- | songdbj/com/jcraft/jogg/Page.java | 973 | ||||
-rw-r--r-- | songdbj/com/jcraft/jogg/StreamState.java | 657 | ||||
-rw-r--r-- | songdbj/com/jcraft/jogg/SyncState.java | 275 |
5 files changed, 2528 insertions, 0 deletions
diff --git a/songdbj/com/jcraft/jogg/Buffer.java b/songdbj/com/jcraft/jogg/Buffer.java new file mode 100644 index 0000000000..a40a9def9c --- /dev/null +++ b/songdbj/com/jcraft/jogg/Buffer.java | |||
@@ -0,0 +1,541 @@ | |||
1 | /* -*-mode:java; c-basic-offset:2; -*- */ | ||
2 | /* JOrbis | ||
3 | * Copyright (C) 2000 ymnk, JCraft,Inc. | ||
4 | * | ||
5 | * Written by: 2000 ymnk<ymnk@jcraft.com> | ||
6 | * | ||
7 | * Many thanks to | ||
8 | * Monty <monty@xiph.org> and | ||
9 | * The XIPHOPHORUS Company http://www.xiph.org/ . | ||
10 | * JOrbis has been based on their awesome works, Vorbis codec. | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU Library General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 of | ||
15 | * the License, or (at your option) any later version. | ||
16 | |||
17 | * This program is distributed in the hope that it will be useful, | ||
18 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
19 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
20 | * GNU Library General Public License for more details. | ||
21 | * | ||
22 | * You should have received a copy of the GNU Library General Public | ||
23 | * License along with this program; if not, write to the Free Software | ||
24 | * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | ||
25 | */ | ||
26 | |||
27 | package com.jcraft.jogg; | ||
28 | |||
29 | public class Buffer{ | ||
30 | private static final int BUFFER_INCREMENT=256; | ||
31 | |||
32 | private static final int[] mask={ | ||
33 | 0x00000000,0x00000001,0x00000003,0x00000007,0x0000000f, | ||
34 | 0x0000001f,0x0000003f,0x0000007f,0x000000ff,0x000001ff, | ||
35 | 0x000003ff,0x000007ff,0x00000fff,0x00001fff,0x00003fff, | ||
36 | 0x00007fff,0x0000ffff,0x0001ffff,0x0003ffff,0x0007ffff, | ||
37 | 0x000fffff,0x001fffff,0x003fffff,0x007fffff,0x00ffffff, | ||
38 | 0x01ffffff,0x03ffffff,0x07ffffff,0x0fffffff,0x1fffffff, | ||
39 | 0x3fffffff,0x7fffffff,0xffffffff | ||
40 | }; | ||
41 | |||
42 | int ptr=0; | ||
43 | byte[] buffer=null; | ||
44 | int endbit=0; | ||
45 | int endbyte=0; | ||
46 | int storage=0; | ||
47 | |||
48 | public void writeinit(){ | ||
49 | buffer=new byte[BUFFER_INCREMENT]; | ||
50 | ptr=0; | ||
51 | buffer[0]=(byte)'\0'; | ||
52 | storage=BUFFER_INCREMENT; | ||
53 | } | ||
54 | |||
55 | public void write(byte[] s){ | ||
56 | for(int i=0; i<s.length; i++){ | ||
57 | if(s[i]==0)break; | ||
58 | write(s[i],8); | ||
59 | } | ||
60 | } | ||
61 | |||
62 | public void read(byte[] s, int bytes){ | ||
63 | int i=0; | ||
64 | while(bytes--!=0){ | ||
65 | s[i++]=(byte)(read(8)); | ||
66 | } | ||
67 | } | ||
68 | |||
69 | void reset(){ | ||
70 | ptr=0; | ||
71 | buffer[0]=(byte)'\0'; | ||
72 | endbit=endbyte=0; | ||
73 | } | ||
74 | |||
75 | public void writeclear(){ | ||
76 | buffer=null; | ||
77 | } | ||
78 | |||
79 | public void readinit(byte[] buf, int bytes){ | ||
80 | readinit(buf, 0, bytes); | ||
81 | } | ||
82 | |||
83 | public void readinit(byte[] buf, int start, int bytes){ | ||
84 | //System.err.println("readinit: start="+start+", bytes="+bytes); | ||
85 | //for(int i=0;i<bytes; i++){ | ||
86 | //System.err.println(i+": "+Integer.toHexString(buf[i+start])); | ||
87 | //} | ||
88 | ptr=start; | ||
89 | buffer=buf; | ||
90 | endbit=endbyte=0; | ||
91 | storage=bytes; | ||
92 | } | ||
93 | |||
94 | public void write(int value, int bits){ | ||
95 | //System.err.println("write: "+Integer.toHexString(value)+", bits="+bits+" ptr="+ptr+", storage="+storage+", endbyte="+endbyte); | ||
96 | if(endbyte+4>=storage){ | ||
97 | byte[] foo=new byte[storage+BUFFER_INCREMENT]; | ||
98 | System.arraycopy(buffer, 0, foo, 0, storage); | ||
99 | buffer=foo; | ||
100 | storage+=BUFFER_INCREMENT; | ||
101 | } | ||
102 | |||
103 | value&=mask[bits]; | ||
104 | bits+=endbit; | ||
105 | buffer[ptr]|=(byte)(value<<endbit); | ||
106 | |||
107 | if(bits>=8){ | ||
108 | buffer[ptr+1]=(byte)(value>>>(8-endbit)); | ||
109 | if(bits>=16){ | ||
110 | buffer[ptr+2]=(byte)(value>>>(16-endbit)); | ||
111 | if(bits>=24){ | ||
112 | buffer[ptr+3]=(byte)(value>>>(24-endbit)); | ||
113 | if(bits>=32){ | ||
114 | if(endbit>0) | ||
115 | buffer[ptr+4]=(byte)(value>>>(32-endbit)); | ||
116 | else | ||
117 | buffer[ptr+4]=0; | ||
118 | } | ||
119 | } | ||
120 | } | ||
121 | } | ||
122 | |||
123 | endbyte+=bits/8; | ||
124 | ptr+=bits/8; | ||
125 | endbit=bits&7; | ||
126 | } | ||
127 | |||
128 | public int look(int bits){ | ||
129 | int ret; | ||
130 | int m=mask[bits]; | ||
131 | |||
132 | bits+=endbit; | ||
133 | |||
134 | //System.err.println("look ptr:"+ptr+", bits="+bits+", endbit="+endbit+", storage="+storage); | ||
135 | |||
136 | if(endbyte+4>=storage){ | ||
137 | if(endbyte+(bits-1)/8>=storage)return(-1); | ||
138 | } | ||
139 | |||
140 | ret=((buffer[ptr])&0xff)>>>endbit; | ||
141 | // ret=((byte)(buffer[ptr]))>>>endbit; | ||
142 | if(bits>8){ | ||
143 | ret|=((buffer[ptr+1])&0xff)<<(8-endbit); | ||
144 | // ret|=((byte)(buffer[ptr+1]))<<(8-endbit); | ||
145 | if(bits>16){ | ||
146 | ret|=((buffer[ptr+2])&0xff)<<(16-endbit); | ||
147 | // ret|=((byte)(buffer[ptr+2]))<<(16-endbit); | ||
148 | if(bits>24){ | ||
149 | ret|=((buffer[ptr+3])&0xff)<<(24-endbit); | ||
150 | //System.err.print("ret="+Integer.toHexString(ret)+", ((byte)(buffer[ptr+3]))="+Integer.toHexString(((buffer[ptr+3])&0xff))); | ||
151 | // ret|=((byte)(buffer[ptr+3]))<<(24-endbit); | ||
152 | //System.err.println(" ->ret="+Integer.toHexString(ret)); | ||
153 | if(bits>32 && endbit!=0){ | ||
154 | ret|=((buffer[ptr+4])&0xff)<<(32-endbit); | ||
155 | // ret|=((byte)(buffer[ptr+4]))<<(32-endbit); | ||
156 | } | ||
157 | } | ||
158 | } | ||
159 | } | ||
160 | return(m&ret); | ||
161 | } | ||
162 | |||
163 | public int look1(){ | ||
164 | if(endbyte>=storage)return(-1); | ||
165 | return((buffer[ptr]>>endbit)&1); | ||
166 | } | ||
167 | |||
168 | public void adv(int bits){ | ||
169 | bits+=endbit; | ||
170 | ptr+=bits/8; | ||
171 | endbyte+=bits/8; | ||
172 | endbit=bits&7; | ||
173 | } | ||
174 | |||
175 | public void adv1(){ | ||
176 | ++endbit; | ||
177 | if(endbit>7){ | ||
178 | endbit=0; | ||
179 | ptr++; | ||
180 | endbyte++; | ||
181 | } | ||
182 | } | ||
183 | |||
184 | public int read(int bits){ | ||
185 | //System.err.println(this+" read: bits="+bits+", storage="+storage+", endbyte="+endbyte); | ||
186 | //System.err.println(this+" read: bits="+bits+", storage="+storage+", endbyte="+endbyte+ | ||
187 | // ", ptr="+ptr+", endbit="+endbit+", buf[ptr]="+buffer[ptr]); | ||
188 | |||
189 | int ret; | ||
190 | int m=mask[bits]; | ||
191 | |||
192 | bits+=endbit; | ||
193 | |||
194 | if(endbyte+4>=storage){ | ||
195 | ret=-1; | ||
196 | if(endbyte+(bits-1)/8>=storage){ | ||
197 | ptr+=bits/8; | ||
198 | endbyte+=bits/8; | ||
199 | endbit=bits&7; | ||
200 | return(ret); | ||
201 | } | ||
202 | } | ||
203 | |||
204 | /* | ||
205 | ret=(byte)(buffer[ptr]>>>endbit); | ||
206 | if(bits>8){ | ||
207 | ret|=(buffer[ptr+1]<<(8-endbit)); | ||
208 | if(bits>16){ | ||
209 | ret|=(buffer[ptr+2]<<(16-endbit)); | ||
210 | if(bits>24){ | ||
211 | ret|=(buffer[ptr+3]<<(24-endbit)); | ||
212 | if(bits>32 && endbit>0){ | ||
213 | ret|=(buffer[ptr+4]<<(32-endbit)); | ||
214 | } | ||
215 | } | ||
216 | } | ||
217 | } | ||
218 | */ | ||
219 | ret=((buffer[ptr])&0xff)>>>endbit; | ||
220 | if(bits>8){ | ||
221 | ret|=((buffer[ptr+1])&0xff)<<(8-endbit); | ||
222 | // ret|=((byte)(buffer[ptr+1]))<<(8-endbit); | ||
223 | if(bits>16){ | ||
224 | ret|=((buffer[ptr+2])&0xff)<<(16-endbit); | ||
225 | // ret|=((byte)(buffer[ptr+2]))<<(16-endbit); | ||
226 | if(bits>24){ | ||
227 | ret|=((buffer[ptr+3])&0xff)<<(24-endbit); | ||
228 | // ret|=((byte)(buffer[ptr+3]))<<(24-endbit); | ||
229 | if(bits>32 && endbit!=0){ | ||
230 | ret|=((buffer[ptr+4])&0xff)<<(32-endbit); | ||
231 | // ret|=((byte)(buffer[ptr+4]))<<(32-endbit); | ||
232 | } | ||
233 | } | ||
234 | } | ||
235 | } | ||
236 | |||
237 | ret&=m; | ||
238 | |||
239 | ptr+=bits/8; | ||
240 | // ptr=bits/8; | ||
241 | endbyte+=bits/8; | ||
242 | // endbyte=bits/8; | ||
243 | endbit=bits&7; | ||
244 | return(ret); | ||
245 | } | ||
246 | |||
247 | public int readB(int bits){ | ||
248 | //System.err.println(this+" read: bits="+bits+", storage="+storage+", endbyte="+endbyte+ | ||
249 | // ", ptr="+ptr+", endbit="+endbit+", buf[ptr]="+buffer[ptr]); | ||
250 | int ret; | ||
251 | int m=32-bits; | ||
252 | |||
253 | bits+=endbit; | ||
254 | |||
255 | if(endbyte+4>=storage){ | ||
256 | /* not the main path */ | ||
257 | ret=-1; | ||
258 | if(endbyte*8+bits>storage*8) { | ||
259 | ptr+=bits/8; | ||
260 | endbyte+=bits/8; | ||
261 | endbit=bits&7; | ||
262 | return(ret); | ||
263 | } | ||
264 | } | ||
265 | |||
266 | ret=(buffer[ptr]&0xff)<<(24+endbit); | ||
267 | if(bits>8){ | ||
268 | ret|=(buffer[ptr+1]&0xff)<<(16+endbit); | ||
269 | if(bits>16){ | ||
270 | ret|=(buffer[ptr+2]&0xff)<<(8+endbit); | ||
271 | if(bits>24){ | ||
272 | ret|=(buffer[ptr+3]&0xff)<<(endbit); | ||
273 | if(bits>32 && (endbit != 0)) | ||
274 | ret|=(buffer[ptr+4]&0xff)>>(8-endbit); | ||
275 | } | ||
276 | } | ||
277 | } | ||
278 | ret=(ret>>>(m>>1))>>>((m+1)>>1); | ||
279 | |||
280 | ptr+=bits/8; | ||
281 | endbyte+=bits/8; | ||
282 | endbit=bits&7; | ||
283 | return(ret); | ||
284 | } | ||
285 | |||
286 | public int read1(){ | ||
287 | int ret; | ||
288 | if(endbyte>=storage){ | ||
289 | ret=-1; | ||
290 | endbit++; | ||
291 | if(endbit>7){ | ||
292 | endbit=0; | ||
293 | ptr++; | ||
294 | endbyte++; | ||
295 | } | ||
296 | return(ret); | ||
297 | } | ||
298 | |||
299 | ret=(buffer[ptr]>>endbit)&1; | ||
300 | |||
301 | endbit++; | ||
302 | if(endbit>7){ | ||
303 | endbit=0; | ||
304 | ptr++; | ||
305 | endbyte++; | ||
306 | } | ||
307 | return(ret); | ||
308 | } | ||
309 | |||
310 | public int bytes(){ | ||
311 | return(endbyte+(endbit+7)/8); | ||
312 | } | ||
313 | |||
314 | public int bits(){ | ||
315 | return(endbyte*8+endbit); | ||
316 | } | ||
317 | |||
318 | public byte[] buffer(){ | ||
319 | return(buffer); | ||
320 | } | ||
321 | |||
322 | public static int ilog(int v){ | ||
323 | int ret=0; | ||
324 | while(v>0){ | ||
325 | ret++; | ||
326 | v>>>=1; | ||
327 | } | ||
328 | return(ret); | ||
329 | } | ||
330 | |||
331 | public static void report(String in){ | ||
332 | System.err.println(in); | ||
333 | System.exit(1); | ||
334 | } | ||
335 | |||
336 | /* | ||
337 | static void cliptest(int[] b, int vals, int bits, int[] comp, int compsize){ | ||
338 | int bytes; | ||
339 | byte[] buffer; | ||
340 | |||
341 | o.reset(); | ||
342 | for(int i=0;i<vals;i++){ | ||
343 | o.write(b[i],((bits!=0)?bits:ilog(b[i]))); | ||
344 | } | ||
345 | buffer=o.buffer(); | ||
346 | bytes=o.bytes(); | ||
347 | System.err.println("cliptest: bytes="+bytes); | ||
348 | if(bytes!=compsize)report("wrong number of bytes!\n"); | ||
349 | for(int i=0;i<bytes;i++){ | ||
350 | if(buffer[i]!=(byte)comp[i]){ | ||
351 | for(int j=0;j<bytes;j++){ | ||
352 | System.err.println(j+": "+Integer.toHexString(buffer[j])+" "+ | ||
353 | Integer.toHexString(comp[j])); | ||
354 | } | ||
355 | report("wrote incorrect value!\n"); | ||
356 | } | ||
357 | } | ||
358 | System.err.println("bits: "+bits); | ||
359 | r.readinit(buffer,bytes); | ||
360 | for(int i=0;i<vals;i++){ | ||
361 | int tbit=(bits!=0)?bits:ilog(b[i]); | ||
362 | System.err.println(Integer.toHexString(b[i])+" tbit: "+tbit); | ||
363 | if(r.look(tbit)==-1){ | ||
364 | report("out of data!\n"); | ||
365 | } | ||
366 | if(r.look(tbit)!=(b[i]&mask[tbit])){ | ||
367 | report(i+" looked at incorrect value! "+Integer.toHexString(r.look(tbit))+", "+Integer.toHexString(b[i]&mask[tbit])+":"+b[i]+" bit="+tbit); | ||
368 | } | ||
369 | if(tbit==1){ | ||
370 | if(r.look1()!=(b[i]&mask[tbit])){ | ||
371 | report("looked at single bit incorrect value!\n"); | ||
372 | } | ||
373 | } | ||
374 | if(tbit==1){ | ||
375 | if(r.read1()!=(b[i]&mask[tbit])){ | ||
376 | report("read incorrect single bit value!\n"); | ||
377 | } | ||
378 | } | ||
379 | else{ | ||
380 | if(r.read(tbit)!=(b[i]&mask[tbit])){ | ||
381 | report("read incorrect value!\n"); | ||
382 | } | ||
383 | } | ||
384 | } | ||
385 | if(r.bytes()!=bytes){ | ||
386 | report("leftover bytes after read!\n"); | ||
387 | } | ||
388 | } | ||
389 | |||
390 | static int[] testbuffer1= | ||
391 | {18,12,103948,4325,543,76,432,52,3,65,4,56,32,42,34,21,1,23,32,546,456,7, | ||
392 | 567,56,8,8,55,3,52,342,341,4,265,7,67,86,2199,21,7,1,5,1,4}; | ||
393 | static int test1size=43; | ||
394 | |||
395 | static int[] testbuffer2= | ||
396 | {216531625,1237861823,56732452,131,3212421,12325343,34547562,12313212, | ||
397 | 1233432,534,5,346435231,14436467,7869299,76326614,167548585, | ||
398 | 85525151,0,12321,1,349528352}; | ||
399 | static int test2size=21; | ||
400 | |||
401 | static int[] large= | ||
402 | {2136531625,2137861823,56732452,131,3212421,12325343,34547562,12313212, | ||
403 | 1233432,534,5,2146435231,14436467,7869299,76326614,167548585, | ||
404 | 85525151,0,12321,1,2146528352}; | ||
405 | |||
406 | static int[] testbuffer3= | ||
407 | {1,0,14,0,1,0,12,0,1,0,0,0,1,1,0,1,0,1,0,1,0,1,0,1,0,1,0,0,1,1,1,1,1,0,0,1, | ||
408 | 0,1,30,1,1,1,0,0,1,0,0,0,12,0,11,0,1,0,0,1}; | ||
409 | static int test3size=56; | ||
410 | |||
411 | static int onesize=33; | ||
412 | static int[] one={146,25,44,151,195,15,153,176,233,131,196,65,85,172,47,40, | ||
413 | 34,242,223,136,35,222,211,86,171,50,225,135,214,75,172, | ||
414 | 223,4}; | ||
415 | |||
416 | static int twosize=6; | ||
417 | static int[] two={61,255,255,251,231,29}; | ||
418 | |||
419 | static int threesize=54; | ||
420 | static int[] three={169,2,232,252,91,132,156,36,89,13,123,176,144,32,254, | ||
421 | 142,224,85,59,121,144,79,124,23,67,90,90,216,79,23,83, | ||
422 | 58,135,196,61,55,129,183,54,101,100,170,37,127,126,10, | ||
423 | 100,52,4,14,18,86,77,1}; | ||
424 | |||
425 | static int foursize=38; | ||
426 | static int[] four={18,6,163,252,97,194,104,131,32,1,7,82,137,42,129,11,72, | ||
427 | 132,60,220,112,8,196,109,64,179,86,9,137,195,208,122,169, | ||
428 | 28,2,133,0,1}; | ||
429 | |||
430 | static int fivesize=45; | ||
431 | static int[] five={169,2,126,139,144,172,30,4,80,72,240,59,130,218,73,62, | ||
432 | 241,24,210,44,4,20,0,248,116,49,135,100,110,130,181,169, | ||
433 | 84,75,159,2,1,0,132,192,8,0,0,18,22}; | ||
434 | |||
435 | static int sixsize=7; | ||
436 | static int[] six={17,177,170,242,169,19,148}; | ||
437 | |||
438 | static Buffer o=new Buffer(); | ||
439 | static Buffer r=new Buffer(); | ||
440 | |||
441 | public static void main(String[] arg){ | ||
442 | byte[] buffer; | ||
443 | int bytes; | ||
444 | // o=new Buffer(); | ||
445 | // r=new Buffer(); | ||
446 | |||
447 | o.writeinit(); | ||
448 | |||
449 | System.err.print("\nSmall preclipped packing: "); | ||
450 | cliptest(testbuffer1,test1size,0,one,onesize); | ||
451 | System.err.print("ok."); | ||
452 | |||
453 | System.err.print("\nNull bit call: "); | ||
454 | cliptest(testbuffer3,test3size,0,two,twosize); | ||
455 | System.err.print("ok."); | ||
456 | |||
457 | System.err.print("\nLarge preclipped packing: "); | ||
458 | cliptest(testbuffer2,test2size,0,three,threesize); | ||
459 | System.err.print("ok."); | ||
460 | |||
461 | System.err.print("\n32 bit preclipped packing: "); | ||
462 | o.reset(); | ||
463 | for(int i=0;i<test2size;i++) | ||
464 | o.write(large[i],32); | ||
465 | buffer=o.buffer(); | ||
466 | bytes=o.bytes(); | ||
467 | |||
468 | |||
469 | r.readinit(buffer,bytes); | ||
470 | for(int i=0;i<test2size;i++){ | ||
471 | if(r.look(32)==-1){ | ||
472 | report("out of data. failed!"); | ||
473 | } | ||
474 | if(r.look(32)!=large[i]){ | ||
475 | System.err.print(r.look(32)+" != "+large[i]+" ("+ | ||
476 | Integer.toHexString(r.look(32))+"!="+ | ||
477 | Integer.toHexString(large[i])+")"); | ||
478 | report("read incorrect value!\n"); | ||
479 | } | ||
480 | r.adv(32); | ||
481 | } | ||
482 | if(r.bytes()!=bytes)report("leftover bytes after read!\n"); | ||
483 | System.err.print("ok."); | ||
484 | |||
485 | System.err.print("\nSmall unclipped packing: "); | ||
486 | cliptest(testbuffer1,test1size,7,four,foursize); | ||
487 | System.err.print("ok."); | ||
488 | |||
489 | System.err.print("\nLarge unclipped packing: "); | ||
490 | cliptest(testbuffer2,test2size,17,five,fivesize); | ||
491 | System.err.print("ok."); | ||
492 | |||
493 | System.err.print("\nSingle bit unclicpped packing: "); | ||
494 | cliptest(testbuffer3,test3size,1,six,sixsize); | ||
495 | System.err.print("ok."); | ||
496 | |||
497 | System.err.print("\nTesting read past end: "); | ||
498 | r.readinit("\0\0\0\0\0\0\0\0".getBytes(),8); | ||
499 | for(int i=0;i<64;i++){ | ||
500 | if(r.read(1)!=0){ | ||
501 | System.err.print("failed; got -1 prematurely.\n"); | ||
502 | System.exit(1); | ||
503 | } | ||
504 | } | ||
505 | |||
506 | if(r.look(1)!=-1 || | ||
507 | r.read(1)!=-1){ | ||
508 | System.err.print("failed; read past end without -1.\n"); | ||
509 | System.exit(1); | ||
510 | } | ||
511 | |||
512 | r.readinit("\0\0\0\0\0\0\0\0".getBytes(),8); | ||
513 | if(r.read(30)!=0 || r.read(16)!=0){ | ||
514 | System.err.print("failed 2; got -1 prematurely.\n"); | ||
515 | System.exit(1); | ||
516 | } | ||
517 | |||
518 | if(r.look(18)!=0 || | ||
519 | r.look(18)!=0){ | ||
520 | System.err.print("failed 3; got -1 prematurely.\n"); | ||
521 | System.exit(1); | ||
522 | } | ||
523 | if(r.look(19)!=-1 || | ||
524 | r.look(19)!=-1){ | ||
525 | System.err.print("failed; read past end without -1.\n"); | ||
526 | System.exit(1); | ||
527 | } | ||
528 | if(r.look(32)!=-1 || | ||
529 | r.look(32)!=-1){ | ||
530 | System.err.print("failed; read past end without -1.\n"); | ||
531 | System.exit(1); | ||
532 | } | ||
533 | System.err.print("ok.\n\n"); | ||
534 | } | ||
535 | */ | ||
536 | } | ||
537 | |||
538 | |||
539 | |||
540 | |||
541 | |||
diff --git a/songdbj/com/jcraft/jogg/Packet.java b/songdbj/com/jcraft/jogg/Packet.java new file mode 100644 index 0000000000..22a8a5439b --- /dev/null +++ b/songdbj/com/jcraft/jogg/Packet.java | |||
@@ -0,0 +1,82 @@ | |||
1 | /* JOrbis | ||
2 | * Copyright (C) 2000 ymnk, JCraft,Inc. | ||
3 | * | ||
4 | * Written by: 2000 ymnk<ymnk@jcraft.com> | ||
5 | * | ||
6 | * Many thanks to | ||
7 | * Monty <monty@xiph.org> and | ||
8 | * The XIPHOPHORUS Company http://www.xiph.org/ . | ||
9 | * JOrbis has been based on their awesome works, Vorbis codec. | ||
10 | * | ||
11 | * This program is free software; you can redistribute it and/or | ||
12 | * modify it under the terms of the GNU Library General Public License | ||
13 | * as published by the Free Software Foundation; either version 2 of | ||
14 | * the License, or (at your option) any later version. | ||
15 | |||
16 | * This program is distributed in the hope that it will be useful, | ||
17 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
18 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
19 | * GNU Library General Public License for more details. | ||
20 | * | ||
21 | * You should have received a copy of the GNU Library General Public | ||
22 | * License along with this program; if not, write to the Free Software | ||
23 | * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | ||
24 | */ | ||
25 | |||
26 | package com.jcraft.jogg; | ||
27 | |||
28 | public class Packet{ | ||
29 | public byte[] packet_base; | ||
30 | public int packet; | ||
31 | public int bytes; | ||
32 | public int b_o_s; | ||
33 | public int e_o_s; | ||
34 | |||
35 | public long granulepos; | ||
36 | |||
37 | public long packetno; // sequence number for decode; the framing | ||
38 | // knows where there's a hole in the data, | ||
39 | // but we need coupling so that the codec | ||
40 | // (which is in a seperate abstraction | ||
41 | // layer) also knows about the gap | ||
42 | |||
43 | /* | ||
44 | // TEST | ||
45 | static int sequence=0; | ||
46 | static int lastno=0; | ||
47 | void checkpacket(int len, int no, int pos){ | ||
48 | if(bytes!=len){ | ||
49 | System.err.println("incorrect packet length!"); | ||
50 | System.exit(1); | ||
51 | } | ||
52 | if(granulepos!=pos){ | ||
53 | System.err.println("incorrect packet position!"); | ||
54 | System.exit(1); | ||
55 | } | ||
56 | |||
57 | // packet number just follows sequence/gap; adjust the input number | ||
58 | // for that | ||
59 | if(no==0){ | ||
60 | sequence=0; | ||
61 | } | ||
62 | else{ | ||
63 | sequence++; | ||
64 | if(no>lastno+1) | ||
65 | sequence++; | ||
66 | } | ||
67 | lastno=no; | ||
68 | if(packetno!=sequence){ | ||
69 | System.err.println("incorrect packet sequence "+packetno+" != "+sequence); | ||
70 | System.exit(1); | ||
71 | } | ||
72 | |||
73 | // Test data | ||
74 | for(int j=0;j<bytes;j++){ | ||
75 | if((packet_base[packet+j]&0xff)!=((j+no)&0xff)){ | ||
76 | System.err.println("body data mismatch at pos "+ j+": "+(packet_base[packet+j]&0xff)+"!="+((j+no)&0xff)+"!\n"); | ||
77 | System.exit(1); | ||
78 | } | ||
79 | } | ||
80 | } | ||
81 | */ | ||
82 | } | ||
diff --git a/songdbj/com/jcraft/jogg/Page.java b/songdbj/com/jcraft/jogg/Page.java new file mode 100644 index 0000000000..fc1add010e --- /dev/null +++ b/songdbj/com/jcraft/jogg/Page.java | |||
@@ -0,0 +1,973 @@ | |||
1 | /* -*-mode:java; c-basic-offset:2; -*- */ | ||
2 | /* JOrbis | ||
3 | * Copyright (C) 2000 ymnk, JCraft,Inc. | ||
4 | * | ||
5 | * Written by: 2000 ymnk<ymnk@jcraft.com> | ||
6 | * | ||
7 | * Many thanks to | ||
8 | * Monty <monty@xiph.org> and | ||
9 | * The XIPHOPHORUS Company http://www.xiph.org/ . | ||
10 | * JOrbis has been based on their awesome works, Vorbis codec. | ||
11 | * | ||
12 | * This program is free software; you can redistribute it and/or | ||
13 | * modify it under the terms of the GNU Library General Public License | ||
14 | * as published by the Free Software Foundation; either version 2 of | ||
15 | * the License, or (at your option) any later version. | ||
16 | |||
17 | * This program is distributed in the hope that it will be useful, | ||
18 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
19 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
20 | * GNU Library General Public License for more details. | ||
21 | * | ||
22 | * You should have received a copy of the GNU Library General Public | ||
23 | * License along with this program; if not, write to the Free Software | ||
24 | * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | ||
25 | */ | ||
26 | |||
27 | package com.jcraft.jogg; | ||
28 | |||
29 | public class Page{ | ||
30 | private static int[] crc_lookup=new int[256]; | ||
31 | static { | ||
32 | for(int i=0; i<crc_lookup.length; i++){ | ||
33 | crc_lookup[i]=crc_entry(i); | ||
34 | } | ||
35 | } | ||
36 | |||
37 | private static int crc_entry(int index){ | ||
38 | int r=index<<24; | ||
39 | for(int i=0; i<8; i++){ | ||
40 | if((r& 0x80000000)!=0){ | ||
41 | r=(r << 1)^0x04c11db7; /* The same as the ethernet generator | ||
42 | polynomial, although we use an | ||
43 | unreflected alg and an init/final | ||
44 | of 0, not 0xffffffff */ | ||
45 | } | ||
46 | else{ | ||
47 | r<<=1; | ||
48 | } | ||
49 | } | ||
50 | return(r&0xffffffff); | ||
51 | } | ||
52 | |||
53 | public byte[] header_base; | ||
54 | public int header; | ||
55 | public int header_len; | ||
56 | public byte[] body_base; | ||
57 | public int body; | ||
58 | public int body_len; | ||
59 | |||
60 | int version(){ | ||
61 | return header_base[header+4]&0xff; | ||
62 | } | ||
63 | int continued(){ | ||
64 | return (header_base[header+5]&0x01); | ||
65 | } | ||
66 | public int bos(){ | ||
67 | return (header_base[header+5]&0x02); | ||
68 | } | ||
69 | public int eos(){ | ||
70 | return (header_base[header+5]&0x04); | ||
71 | } | ||
72 | public long granulepos(){ | ||
73 | long foo=header_base[header+13]&0xff; | ||
74 | foo=(foo<<8)|(header_base[header+12]&0xff); | ||
75 | foo=(foo<<8)|(header_base[header+11]&0xff); | ||
76 | foo=(foo<<8)|(header_base[header+10]&0xff); | ||
77 | foo=(foo<<8)|(header_base[header+9]&0xff); | ||
78 | foo=(foo<<8)|(header_base[header+8]&0xff); | ||
79 | foo=(foo<<8)|(header_base[header+7]&0xff); | ||
80 | foo=(foo<<8)|(header_base[header+6]&0xff); | ||
81 | return(foo); | ||
82 | } | ||
83 | public int serialno(){ | ||
84 | return (header_base[header+14]&0xff)| | ||
85 | ((header_base[header+15]&0xff)<<8)| | ||
86 | ((header_base[header+16]&0xff)<<16)| | ||
87 | ((header_base[header+17]&0xff)<<24); | ||
88 | } | ||
89 | int pageno(){ | ||
90 | return (header_base[header+18]&0xff)| | ||
91 | ((header_base[header+19]&0xff)<<8)| | ||
92 | ((header_base[header+20]&0xff)<<16)| | ||
93 | ((header_base[header+21]&0xff)<<24); | ||
94 | } | ||
95 | |||
96 | void checksum(){ | ||
97 | int crc_reg=0; | ||
98 | |||
99 | // for(int i=0;i<header_len;i++){ | ||
100 | // System.err.println("chksum: "+Integer.toHexString(header_base[header+i]&0xff)); | ||
101 | // } | ||
102 | |||
103 | for(int i=0;i<header_len;i++){ | ||
104 | crc_reg=(crc_reg<<8)^crc_lookup[((crc_reg>>>24)&0xff)^(header_base[header+i]&0xff)]; | ||
105 | } | ||
106 | for(int i=0;i<body_len;i++){ | ||
107 | crc_reg=(crc_reg<<8)^crc_lookup[((crc_reg>>>24)&0xff)^(body_base[body+i]&0xff)]; | ||
108 | } | ||
109 | header_base[header+22]=(byte)crc_reg/*&0xff*/; | ||
110 | header_base[header+23]=(byte)(crc_reg>>>8)/*&0xff*/; | ||
111 | header_base[header+24]=(byte)(crc_reg>>>16)/*&0xff*/; | ||
112 | header_base[header+25]=(byte)(crc_reg>>>24)/*&0xff*/; | ||
113 | } | ||
114 | public Page copy(){ | ||
115 | return copy(new Page()); | ||
116 | } | ||
117 | public Page copy(Page p){ | ||
118 | byte[] tmp=new byte[header_len]; | ||
119 | System.arraycopy(header_base, header, tmp, 0, header_len); | ||
120 | p.header_len=header_len; | ||
121 | p.header_base=tmp; | ||
122 | p.header=0; | ||
123 | tmp=new byte[body_len]; | ||
124 | System.arraycopy(body_base, body, tmp, 0, body_len); | ||
125 | p.body_len=body_len; | ||
126 | p.body_base=tmp; | ||
127 | p.body=0; | ||
128 | return p; | ||
129 | } | ||
130 | /* | ||
131 | // TEST | ||
132 | static StreamState os_en, os_de; | ||
133 | static SyncState oy; | ||
134 | void check_page(byte[] data_base, int data, int[] _header){ | ||
135 | // Test data | ||
136 | for(int j=0;j<body_len;j++) | ||
137 | if(body_base[body+j]!=data_base[data+j]){ | ||
138 | System.err.println("body data mismatch at pos "+j+": "+data_base[data+j]+"!="+body_base[body+j]+"!\n"); | ||
139 | System.exit(1); | ||
140 | } | ||
141 | |||
142 | // Test header | ||
143 | for(int j=0;j<header_len;j++){ | ||
144 | if((header_base[header+j]&0xff)!=_header[j]){ | ||
145 | System.err.println("header content mismatch at pos "+j); | ||
146 | for(int jj=0;jj<_header[26]+27;jj++) | ||
147 | System.err.print(" ("+jj+")"+Integer.toHexString(_header[jj])+":"+Integer.toHexString(header_base[header+jj])); | ||
148 | System.err.println(""); | ||
149 | System.exit(1); | ||
150 | } | ||
151 | } | ||
152 | if(header_len!=_header[26]+27){ | ||
153 | System.err.print("header length incorrect! ("+header_len+"!="+(_header[26]+27)+")"); | ||
154 | System.exit(1); | ||
155 | } | ||
156 | } | ||
157 | |||
158 | void print_header(){ | ||
159 | System.err.println("\nHEADER:"); | ||
160 | System.err.println(" capture: "+ | ||
161 | (header_base[header+0]&0xff)+" "+ | ||
162 | (header_base[header+1]&0xff)+" "+ | ||
163 | (header_base[header+2]&0xff)+" "+ | ||
164 | (header_base[header+3]&0xff)+" "+ | ||
165 | " version: "+(header_base[header+4]&0xff)+" flags: "+ | ||
166 | (header_base[header+5]&0xff)); | ||
167 | System.err.println(" pcmpos: "+ | ||
168 | (((header_base[header+9]&0xff)<<24)| | ||
169 | ((header_base[header+8]&0xff)<<16)| | ||
170 | ((header_base[header+7]&0xff)<<8)| | ||
171 | ((header_base[header+6]&0xff)))+ | ||
172 | " serialno: "+ | ||
173 | (((header_base[header+17]&0xff)<<24)| | ||
174 | ((header_base[header+16]&0xff)<<16)| | ||
175 | ((header_base[header+15]&0xff)<<8)| | ||
176 | ((header_base[header+14]&0xff)))+ | ||
177 | " pageno: "+ | ||
178 | (((header_base[header+21]&0xff)<<24)| | ||
179 | ((header_base[header+20]&0xff)<<16)| | ||
180 | ((header_base[header+19]&0xff)<<8)| | ||
181 | ((header_base[header+18]&0xff)))); | ||
182 | |||
183 | System.err.println(" checksum: "+ | ||
184 | (header_base[header+22]&0xff)+":"+ | ||
185 | (header_base[header+23]&0xff)+":"+ | ||
186 | (header_base[header+24]&0xff)+":"+ | ||
187 | (header_base[header+25]&0xff)+"\n segments: "+ | ||
188 | (header_base[header+26]&0xff)+" ("); | ||
189 | for(int j=27;j<header_len;j++){ | ||
190 | System.err.println((header_base[header+j]&0xff)+" "); | ||
191 | } | ||
192 | System.err.println(")\n"); | ||
193 | } | ||
194 | |||
195 | void copy_page(){ | ||
196 | byte[] tmp=new byte[header_len]; | ||
197 | System.arraycopy(header_base, header, tmp, 0, header_len); | ||
198 | header_base=tmp; | ||
199 | header=0; | ||
200 | tmp=new byte[body_len]; | ||
201 | System.arraycopy(body_base, body, tmp, 0, body_len); | ||
202 | body_base=tmp; | ||
203 | body=0; | ||
204 | } | ||
205 | |||
206 | static void test_pack(int[] pl, int[][] headers){ | ||
207 | byte[] data=new byte[1024*1024]; // for scripted test cases only | ||
208 | int inptr=0; | ||
209 | int outptr=0; | ||
210 | int deptr=0; | ||
211 | int depacket=0; | ||
212 | int pcm_pos=7; | ||
213 | int packets,pageno=0,pageout=0; | ||
214 | int eosflag=0; | ||
215 | int bosflag=0; | ||
216 | |||
217 | os_en.reset(); | ||
218 | os_de.reset(); | ||
219 | oy.reset(); | ||
220 | |||
221 | for(packets=0;;packets++){ | ||
222 | if(pl[packets]==-1)break; | ||
223 | } | ||
224 | |||
225 | for(int i=0;i<packets;i++){ | ||
226 | // construct a test packet | ||
227 | Packet op=new Packet(); | ||
228 | int len=pl[i]; | ||
229 | op.packet_base=data; | ||
230 | op.packet=inptr; | ||
231 | op.bytes=len; | ||
232 | op.e_o_s=(pl[i+1]<0?1:0); | ||
233 | op.granulepos=pcm_pos; | ||
234 | |||
235 | pcm_pos+=1024; | ||
236 | |||
237 | for(int j=0;j<len;j++){ | ||
238 | data[inptr++]=(byte)(i+j); | ||
239 | } | ||
240 | |||
241 | // submit the test packet | ||
242 | os_en.packetin(op); | ||
243 | |||
244 | // retrieve any finished pages | ||
245 | { | ||
246 | Page og=new Page(); | ||
247 | |||
248 | while(os_en.pageout(og)!=0){ | ||
249 | // We have a page. Check it carefully | ||
250 | //System.err.print(pageno+", "); | ||
251 | if(headers[pageno]==null){ | ||
252 | System.err.println("coded too many pages!"); | ||
253 | System.exit(1); | ||
254 | } | ||
255 | og.check_page(data, outptr, headers[pageno]); | ||
256 | |||
257 | outptr+=og.body_len; | ||
258 | pageno++; | ||
259 | |||
260 | //System.err.println("1# pageno="+pageno+", pageout="+pageout); | ||
261 | |||
262 | // have a complete page; submit it to sync/decode | ||
263 | |||
264 | { | ||
265 | Page og_de=new Page(); | ||
266 | Packet op_de=new Packet(); | ||
267 | int index=oy.buffer(og.header_len+og.body_len); | ||
268 | byte[] buf=oy.data; | ||
269 | System.arraycopy(og.header_base, og.header, buf, index, og.header_len); | ||
270 | System.arraycopy(og.body_base, og.body, buf, index+og.header_len, og.body_len); | ||
271 | oy.wrote(og.header_len+og.body_len); | ||
272 | |||
273 | //System.err.println("2# pageno="+pageno+", pageout="+pageout); | ||
274 | |||
275 | while(oy.pageout(og_de)>0){ | ||
276 | // got a page. Happy happy. Verify that it's good. | ||
277 | |||
278 | og_de.check_page(data, deptr, headers[pageout]); | ||
279 | deptr+=og_de.body_len; | ||
280 | pageout++; | ||
281 | |||
282 | // submit it to deconstitution | ||
283 | os_de.pagein(og_de); | ||
284 | |||
285 | // packets out? | ||
286 | while(os_de.packetout(op_de)>0){ | ||
287 | |||
288 | // verify the packet! | ||
289 | // check data | ||
290 | boolean check=false; | ||
291 | for(int ii=0; ii<op_de.bytes; ii++){ | ||
292 | if(data[depacket+ii]!=op_de.packet_base[op_de.packet+ii]){ | ||
293 | check=true; | ||
294 | break; | ||
295 | } | ||
296 | } | ||
297 | if(check){ | ||
298 | System.err.println("packet data mismatch in decode! pos="+ | ||
299 | depacket); | ||
300 | System.exit(1); | ||
301 | } | ||
302 | |||
303 | // check bos flag | ||
304 | if(bosflag==0 && op_de.b_o_s==0){ | ||
305 | System.err.println("b_o_s flag not set on packet!"); | ||
306 | System.exit(1); | ||
307 | } | ||
308 | if(bosflag!=0 && op_de.b_o_s!=0){ | ||
309 | System.err.println("b_o_s flag incorrectly set on packet!"); | ||
310 | System.exit(1); | ||
311 | } | ||
312 | |||
313 | bosflag=1; | ||
314 | depacket+=op_de.bytes; | ||
315 | |||
316 | // check eos flag | ||
317 | if(eosflag!=0){ | ||
318 | System.err.println("Multiple decoded packets with eos flag!"); | ||
319 | System.exit(1); | ||
320 | } | ||
321 | |||
322 | if(op_de.e_o_s!=0)eosflag=1; | ||
323 | |||
324 | // check pcmpos flag | ||
325 | if(op_de.granulepos!=-1){ | ||
326 | System.err.print(" pcm:"+op_de.granulepos+" "); | ||
327 | } | ||
328 | } | ||
329 | } | ||
330 | } | ||
331 | } | ||
332 | } | ||
333 | } | ||
334 | //free(data); | ||
335 | if(headers[pageno]!=null){ | ||
336 | System.err.println("did not write last page!"); | ||
337 | System.exit(1); | ||
338 | } | ||
339 | if(headers[pageout]!=null){ | ||
340 | System.err.println("did not decode last page!"); | ||
341 | System.exit(1); | ||
342 | } | ||
343 | if(inptr!=outptr){ | ||
344 | System.err.println("encoded page data incomplete!"); | ||
345 | System.exit(1); | ||
346 | } | ||
347 | if(inptr!=deptr){ | ||
348 | System.err.println("decoded page data incomplete!"); | ||
349 | System.exit(1); | ||
350 | } | ||
351 | if(inptr!=depacket){ | ||
352 | System.err.println("decoded packet data incomplete!"); | ||
353 | System.exit(1); | ||
354 | } | ||
355 | if(eosflag==0){ | ||
356 | System.err.println("Never got a packet with EOS set!"); | ||
357 | } | ||
358 | System.err.println("ok."); | ||
359 | } | ||
360 | |||
361 | static void error(){ | ||
362 | System.err.println("error!"); | ||
363 | System.exit(1); | ||
364 | } | ||
365 | public static void main(String[] arg){ | ||
366 | |||
367 | os_en=new StreamState(0x04030201); | ||
368 | os_de=new StreamState(0x04030201); | ||
369 | |||
370 | oy=new SyncState(); | ||
371 | |||
372 | // Exercise each code path in the framing code. Also verify that | ||
373 | // the checksums are working. | ||
374 | |||
375 | { | ||
376 | // 17 only | ||
377 | int[] packets={17, -1}; | ||
378 | int[] head1={0x4f,0x67,0x67,0x53,0,0x06, | ||
379 | 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||
380 | 0x01,0x02,0x03,0x04,0,0,0,0, | ||
381 | 0x15,0xed,0xec,0x91, | ||
382 | 1, | ||
383 | 17}; | ||
384 | int[][] headret={head1, null}; | ||
385 | |||
386 | System.err.print("testing single page encoding... "); | ||
387 | test_pack(packets,headret); | ||
388 | } | ||
389 | |||
390 | { | ||
391 | // 17, 254, 255, 256, 500, 510, 600 byte, pad | ||
392 | int[] packets={17, 254, 255, 256, 500, 510, 600, -1}; | ||
393 | int[] head1={0x4f,0x67,0x67,0x53,0,0x02, | ||
394 | 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||
395 | 0x01,0x02,0x03,0x04,0,0,0,0, | ||
396 | 0x59,0x10,0x6c,0x2c, | ||
397 | 1, | ||
398 | 17}; | ||
399 | int[] head2={0x4f,0x67,0x67,0x53,0,0x04, | ||
400 | 0x07,0x18,0x00,0x00,0x00,0x00,0x00,0x00, | ||
401 | 0x01,0x02,0x03,0x04,1,0,0,0, | ||
402 | 0x89,0x33,0x85,0xce, | ||
403 | 13, | ||
404 | 254,255,0,255,1,255,245,255,255,0, | ||
405 | 255,255,90}; | ||
406 | int[][] headret={head1,head2,null}; | ||
407 | |||
408 | System.err.print("testing basic page encoding... "); | ||
409 | test_pack(packets,headret); | ||
410 | } | ||
411 | |||
412 | { | ||
413 | // nil packets; beginning,middle,end | ||
414 | int[] packets={0,17, 254, 255, 0, 256, 0, 500, 510, 600, 0, -1}; | ||
415 | |||
416 | int[] head1={0x4f,0x67,0x67,0x53,0,0x02, | ||
417 | 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||
418 | 0x01,0x02,0x03,0x04,0,0,0,0, | ||
419 | 0xff,0x7b,0x23,0x17, | ||
420 | 1, | ||
421 | 0}; | ||
422 | int[] head2={0x4f,0x67,0x67,0x53,0,0x04, | ||
423 | 0x07,0x28,0x00,0x00,0x00,0x00,0x00,0x00, | ||
424 | 0x01,0x02,0x03,0x04,1,0,0,0, | ||
425 | 0x5c,0x3f,0x66,0xcb, | ||
426 | 17, | ||
427 | 17,254,255,0,0,255,1,0,255,245,255,255,0, | ||
428 | 255,255,90,0}; | ||
429 | int[][] headret={head1,head2,null}; | ||
430 | |||
431 | System.err.print("testing basic nil packets... "); | ||
432 | test_pack(packets,headret); | ||
433 | } | ||
434 | |||
435 | { | ||
436 | // large initial packet | ||
437 | int[] packets={4345,259,255,-1}; | ||
438 | |||
439 | int[] head1={0x4f,0x67,0x67,0x53,0,0x02, | ||
440 | 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||
441 | 0x01,0x02,0x03,0x04,0,0,0,0, | ||
442 | 0x01,0x27,0x31,0xaa, | ||
443 | 18, | ||
444 | 255,255,255,255,255,255,255,255, | ||
445 | 255,255,255,255,255,255,255,255,255,10}; | ||
446 | |||
447 | int[] head2={0x4f,0x67,0x67,0x53,0,0x04, | ||
448 | 0x07,0x08,0x00,0x00,0x00,0x00,0x00,0x00, | ||
449 | 0x01,0x02,0x03,0x04,1,0,0,0, | ||
450 | 0x7f,0x4e,0x8a,0xd2, | ||
451 | 4, | ||
452 | 255,4,255,0}; | ||
453 | int[][] headret={head1,head2,null}; | ||
454 | |||
455 | System.err.print("testing initial-packet lacing > 4k... "); | ||
456 | test_pack(packets,headret); | ||
457 | } | ||
458 | |||
459 | { | ||
460 | // continuing packet test | ||
461 | int[] packets={0,4345,259,255,-1}; | ||
462 | |||
463 | int[] head1={0x4f,0x67,0x67,0x53,0,0x02, | ||
464 | 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||
465 | 0x01,0x02,0x03,0x04,0,0,0,0, | ||
466 | 0xff,0x7b,0x23,0x17, | ||
467 | 1, | ||
468 | 0}; | ||
469 | |||
470 | int[] head2={0x4f,0x67,0x67,0x53,0,0x00, | ||
471 | 0x07,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||
472 | 0x01,0x02,0x03,0x04,1,0,0,0, | ||
473 | 0x34,0x24,0xd5,0x29, | ||
474 | 17, | ||
475 | 255,255,255,255,255,255,255,255, | ||
476 | 255,255,255,255,255,255,255,255,255}; | ||
477 | |||
478 | int[] head3={0x4f,0x67,0x67,0x53,0,0x05, | ||
479 | 0x07,0x0c,0x00,0x00,0x00,0x00,0x00,0x00, | ||
480 | 0x01,0x02,0x03,0x04,2,0,0,0, | ||
481 | 0xc8,0xc3,0xcb,0xed, | ||
482 | 5, | ||
483 | 10,255,4,255,0}; | ||
484 | int[][] headret={head1,head2,head3,null}; | ||
485 | |||
486 | System.err.print("testing single packet page span... "); | ||
487 | test_pack(packets,headret); | ||
488 | } | ||
489 | |||
490 | // page with the 255 segment limit | ||
491 | { | ||
492 | |||
493 | int[] packets={0,10,10,10,10,10,10,10,10, | ||
494 | 10,10,10,10,10,10,10,10, | ||
495 | 10,10,10,10,10,10,10,10, | ||
496 | 10,10,10,10,10,10,10,10, | ||
497 | 10,10,10,10,10,10,10,10, | ||
498 | 10,10,10,10,10,10,10,10, | ||
499 | 10,10,10,10,10,10,10,10, | ||
500 | 10,10,10,10,10,10,10,10, | ||
501 | 10,10,10,10,10,10,10,10, | ||
502 | 10,10,10,10,10,10,10,10, | ||
503 | 10,10,10,10,10,10,10,10, | ||
504 | 10,10,10,10,10,10,10,10, | ||
505 | 10,10,10,10,10,10,10,10, | ||
506 | 10,10,10,10,10,10,10,10, | ||
507 | 10,10,10,10,10,10,10,10, | ||
508 | 10,10,10,10,10,10,10,10, | ||
509 | 10,10,10,10,10,10,10,10, | ||
510 | 10,10,10,10,10,10,10,10, | ||
511 | 10,10,10,10,10,10,10,10, | ||
512 | 10,10,10,10,10,10,10,10, | ||
513 | 10,10,10,10,10,10,10,10, | ||
514 | 10,10,10,10,10,10,10,10, | ||
515 | 10,10,10,10,10,10,10,10, | ||
516 | 10,10,10,10,10,10,10,10, | ||
517 | 10,10,10,10,10,10,10,10, | ||
518 | 10,10,10,10,10,10,10,10, | ||
519 | 10,10,10,10,10,10,10,10, | ||
520 | 10,10,10,10,10,10,10,10, | ||
521 | 10,10,10,10,10,10,10,10, | ||
522 | 10,10,10,10,10,10,10,10, | ||
523 | 10,10,10,10,10,10,10,10, | ||
524 | 10,10,10,10,10,10,10,50,-1}; | ||
525 | |||
526 | int[] head1={0x4f,0x67,0x67,0x53,0,0x02, | ||
527 | 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||
528 | 0x01,0x02,0x03,0x04,0,0,0,0, | ||
529 | 0xff,0x7b,0x23,0x17, | ||
530 | 1, | ||
531 | 0}; | ||
532 | |||
533 | int[] head2={0x4f,0x67,0x67,0x53,0,0x00, | ||
534 | 0x07,0xfc,0x03,0x00,0x00,0x00,0x00,0x00, | ||
535 | 0x01,0x02,0x03,0x04,1,0,0,0, | ||
536 | 0xed,0x2a,0x2e,0xa7, | ||
537 | 255, | ||
538 | 10,10,10,10,10,10,10,10, | ||
539 | 10,10,10,10,10,10,10,10, | ||
540 | 10,10,10,10,10,10,10,10, | ||
541 | 10,10,10,10,10,10,10,10, | ||
542 | 10,10,10,10,10,10,10,10, | ||
543 | 10,10,10,10,10,10,10,10, | ||
544 | 10,10,10,10,10,10,10,10, | ||
545 | 10,10,10,10,10,10,10,10, | ||
546 | 10,10,10,10,10,10,10,10, | ||
547 | 10,10,10,10,10,10,10,10, | ||
548 | 10,10,10,10,10,10,10,10, | ||
549 | 10,10,10,10,10,10,10,10, | ||
550 | 10,10,10,10,10,10,10,10, | ||
551 | 10,10,10,10,10,10,10,10, | ||
552 | 10,10,10,10,10,10,10,10, | ||
553 | 10,10,10,10,10,10,10,10, | ||
554 | 10,10,10,10,10,10,10,10, | ||
555 | 10,10,10,10,10,10,10,10, | ||
556 | 10,10,10,10,10,10,10,10, | ||
557 | 10,10,10,10,10,10,10,10, | ||
558 | 10,10,10,10,10,10,10,10, | ||
559 | 10,10,10,10,10,10,10,10, | ||
560 | 10,10,10,10,10,10,10,10, | ||
561 | 10,10,10,10,10,10,10,10, | ||
562 | 10,10,10,10,10,10,10,10, | ||
563 | 10,10,10,10,10,10,10,10, | ||
564 | 10,10,10,10,10,10,10,10, | ||
565 | 10,10,10,10,10,10,10,10, | ||
566 | 10,10,10,10,10,10,10,10, | ||
567 | 10,10,10,10,10,10,10,10, | ||
568 | 10,10,10,10,10,10,10,10, | ||
569 | 10,10,10,10,10,10,10}; | ||
570 | |||
571 | int[] head3={0x4f,0x67,0x67,0x53,0,0x04, | ||
572 | 0x07,0x00,0x04,0x00,0x00,0x00,0x00,0x00, | ||
573 | 0x01,0x02,0x03,0x04,2,0,0,0, | ||
574 | 0x6c,0x3b,0x82,0x3d, | ||
575 | 1, | ||
576 | 50}; | ||
577 | int[][] headret={head1,head2,head3,null}; | ||
578 | |||
579 | System.err.print("testing max packet segments... "); | ||
580 | test_pack(packets,headret); | ||
581 | } | ||
582 | |||
583 | { | ||
584 | // packet that overspans over an entire page | ||
585 | |||
586 | int[] packets={0,100,9000,259,255,-1}; | ||
587 | |||
588 | int[] head1={0x4f,0x67,0x67,0x53,0,0x02, | ||
589 | 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||
590 | 0x01,0x02,0x03,0x04,0,0,0,0, | ||
591 | 0xff,0x7b,0x23,0x17, | ||
592 | 1, | ||
593 | 0}; | ||
594 | |||
595 | int[] head2={0x4f,0x67,0x67,0x53,0,0x00, | ||
596 | 0x07,0x04,0x00,0x00,0x00,0x00,0x00,0x00, | ||
597 | 0x01,0x02,0x03,0x04,1,0,0,0, | ||
598 | 0x3c,0xd9,0x4d,0x3f, | ||
599 | 17, | ||
600 | 100,255,255,255,255,255,255,255,255, | ||
601 | 255,255,255,255,255,255,255,255}; | ||
602 | |||
603 | int[] head3={0x4f,0x67,0x67,0x53,0,0x01, | ||
604 | 0x07,0x04,0x00,0x00,0x00,0x00,0x00,0x00, | ||
605 | 0x01,0x02,0x03,0x04,2,0,0,0, | ||
606 | 0xbd,0xd5,0xb5,0x8b, | ||
607 | 17, | ||
608 | 255,255,255,255,255,255,255,255, | ||
609 | 255,255,255,255,255,255,255,255,255}; | ||
610 | |||
611 | int[] head4={0x4f,0x67,0x67,0x53,0,0x05, | ||
612 | 0x07,0x10,0x00,0x00,0x00,0x00,0x00,0x00, | ||
613 | 0x01,0x02,0x03,0x04,3,0,0,0, | ||
614 | 0xef,0xdd,0x88,0xde, | ||
615 | 7, | ||
616 | 255,255,75,255,4,255,0}; | ||
617 | int[][] headret={head1,head2,head3,head4,null}; | ||
618 | |||
619 | System.err.print("testing very large packets... "); | ||
620 | test_pack(packets,headret); | ||
621 | } | ||
622 | |||
623 | { | ||
624 | // term only page. why not? | ||
625 | |||
626 | int[] packets={0,100,4080,-1}; | ||
627 | |||
628 | int[] head1={0x4f,0x67,0x67,0x53,0,0x02, | ||
629 | 0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00, | ||
630 | 0x01,0x02,0x03,0x04,0,0,0,0, | ||
631 | 0xff,0x7b,0x23,0x17, | ||
632 | 1, | ||
633 | 0}; | ||
634 | |||
635 | int[] head2={0x4f,0x67,0x67,0x53,0,0x00, | ||
636 | 0x07,0x04,0x00,0x00,0x00,0x00,0x00,0x00, | ||
637 | 0x01,0x02,0x03,0x04,1,0,0,0, | ||
638 | 0x3c,0xd9,0x4d,0x3f, | ||
639 | 17, | ||
640 | 100,255,255,255,255,255,255,255,255, | ||
641 | 255,255,255,255,255,255,255,255}; | ||
642 | |||
643 | int[] head3={0x4f,0x67,0x67,0x53,0,0x05, | ||
644 | 0x07,0x08,0x00,0x00,0x00,0x00,0x00,0x00, | ||
645 | 0x01,0x02,0x03,0x04,2,0,0,0, | ||
646 | 0xd4,0xe0,0x60,0xe5, | ||
647 | 1,0}; | ||
648 | |||
649 | int[][] headret={head1,head2,head3,null}; | ||
650 | |||
651 | System.err.print("testing zero data page (1 nil packet)... "); | ||
652 | test_pack(packets,headret); | ||
653 | } | ||
654 | |||
655 | { | ||
656 | // build a bunch of pages for testing | ||
657 | byte[] data=new byte[1024*1024]; | ||
658 | int[] pl={0,100,4079,2956,2057,76,34,912,0,234,1000,1000,1000,300,-1}; | ||
659 | int inptr=0; | ||
660 | Page[] og=new Page[5]; | ||
661 | for(int i=0; i<5; i++){ | ||
662 | og[i]=new Page(); | ||
663 | } | ||
664 | |||
665 | os_en.reset(); | ||
666 | |||
667 | for(int i=0;pl[i]!=-1;i++){ | ||
668 | Packet op=new Packet(); | ||
669 | int len=pl[i]; | ||
670 | |||
671 | op.packet_base=data; | ||
672 | op.packet=inptr; | ||
673 | op.bytes=len; | ||
674 | op.e_o_s=(pl[i+1]<0?1:0); | ||
675 | op.granulepos=(i+1)*1000; | ||
676 | |||
677 | for(int j=0;j<len;j++)data[inptr++]=(byte)(i+j); | ||
678 | os_en.packetin(op); | ||
679 | } | ||
680 | |||
681 | // free(data); | ||
682 | |||
683 | // retrieve finished pages | ||
684 | for(int i=0;i<5;i++){ | ||
685 | if(os_en.pageout(og[i])==0){ | ||
686 | System.err.print("Too few pages output building sync tests!\n"); | ||
687 | System.exit(1); | ||
688 | } | ||
689 | og[i].copy_page(); | ||
690 | } | ||
691 | |||
692 | // Test lost pages on pagein/packetout: no rollback | ||
693 | { | ||
694 | Page temp=new Page(); | ||
695 | Packet test=new Packet(); | ||
696 | |||
697 | System.err.print("Testing loss of pages... "); | ||
698 | |||
699 | oy.reset(); | ||
700 | os_de.reset(); | ||
701 | for(int i=0;i<5;i++){ | ||
702 | int index=oy.buffer(og[i].header_len); | ||
703 | System.arraycopy(og[i].header_base, og[i].header, | ||
704 | oy.data, index, og[i].header_len); | ||
705 | oy.wrote(og[i].header_len); | ||
706 | index=oy.buffer(og[i].body_len); | ||
707 | System.arraycopy(og[i].body_base, og[i].body, | ||
708 | oy.data, index, og[i].body_len); | ||
709 | oy.wrote(og[i].body_len); | ||
710 | } | ||
711 | |||
712 | oy.pageout(temp); | ||
713 | os_de.pagein(temp); | ||
714 | oy.pageout(temp); | ||
715 | os_de.pagein(temp); | ||
716 | oy.pageout(temp); | ||
717 | |||
718 | // skip | ||
719 | oy.pageout(temp); | ||
720 | os_de.pagein(temp); | ||
721 | |||
722 | // do we get the expected results/packets? | ||
723 | |||
724 | if(os_de.packetout(test)!=1)error(); | ||
725 | test.checkpacket(0,0,0); | ||
726 | if(os_de.packetout(test)!=1)error(); | ||
727 | test.checkpacket(100,1,-1); | ||
728 | if(os_de.packetout(test)!=1)error(); | ||
729 | test.checkpacket(4079,2,3000); | ||
730 | if(os_de.packetout(test)!=-1){ | ||
731 | System.err.println("Error: loss of page did not return error"); | ||
732 | System.exit(1); | ||
733 | } | ||
734 | if(os_de.packetout(test)!=1)error(); | ||
735 | test.checkpacket(76,5,-1); | ||
736 | if(os_de.packetout(test)!=1)error(); | ||
737 | test.checkpacket(34,6,-1); | ||
738 | System.err.println("ok."); | ||
739 | } | ||
740 | |||
741 | // Test lost pages on pagein/packetout: rollback with continuation | ||
742 | { | ||
743 | Page temp=new Page(); | ||
744 | Packet test=new Packet(); | ||
745 | |||
746 | System.err.print("Testing loss of pages (rollback required)... "); | ||
747 | |||
748 | oy.reset(); | ||
749 | os_de.reset(); | ||
750 | for(int i=0;i<5;i++){ | ||
751 | int index=oy.buffer(og[i].header_len); | ||
752 | System.arraycopy(og[i].header_base, og[i].header, | ||
753 | oy.data, index, og[i].header_len); | ||
754 | oy.wrote(og[i].header_len); | ||
755 | index=oy.buffer(og[i].body_len); | ||
756 | System.arraycopy(og[i].body_base, og[i].body, | ||
757 | oy.data, index, og[i].body_len); | ||
758 | oy.wrote(og[i].body_len); | ||
759 | } | ||
760 | |||
761 | oy.pageout(temp); | ||
762 | os_de.pagein(temp); | ||
763 | oy.pageout(temp); | ||
764 | os_de.pagein(temp); | ||
765 | oy.pageout(temp); | ||
766 | os_de.pagein(temp); | ||
767 | oy.pageout(temp); | ||
768 | // skip | ||
769 | oy.pageout(temp); | ||
770 | os_de.pagein(temp); | ||
771 | |||
772 | // do we get the expected results/packets? | ||
773 | |||
774 | if(os_de.packetout(test)!=1)error(); | ||
775 | test.checkpacket(0,0,0); | ||
776 | if(os_de.packetout(test)!=1)error(); | ||
777 | test.checkpacket(100,1,-1); | ||
778 | if(os_de.packetout(test)!=1)error(); | ||
779 | test.checkpacket(4079,2,3000); | ||
780 | if(os_de.packetout(test)!=1)error(); | ||
781 | test.checkpacket(2956,3,4000); | ||
782 | if(os_de.packetout(test)!=-1){ | ||
783 | System.err.println("Error: loss of page did not return error"); | ||
784 | System.exit(1); | ||
785 | } | ||
786 | if(os_de.packetout(test)!=1)error(); | ||
787 | test.checkpacket(300,13,14000); | ||
788 | System.err.println("ok."); | ||
789 | } | ||
790 | |||
791 | // the rest only test sync | ||
792 | { | ||
793 | Page og_de=new Page(); | ||
794 | // Test fractional page inputs: incomplete capture | ||
795 | System.err.print("Testing sync on partial inputs... "); | ||
796 | oy.reset(); | ||
797 | int index=oy.buffer(og[1].header_len); | ||
798 | System.arraycopy(og[1].header_base, og[1].header, | ||
799 | oy.data, index, 3); | ||
800 | oy.wrote(3); | ||
801 | if(oy.pageout(og_de)>0)error(); | ||
802 | |||
803 | // Test fractional page inputs: incomplete fixed header | ||
804 | index=oy.buffer(og[1].header_len); | ||
805 | System.arraycopy(og[1].header_base, og[1].header+3, | ||
806 | oy.data, index, 20); | ||
807 | |||
808 | oy.wrote(20); | ||
809 | if(oy.pageout(og_de)>0)error(); | ||
810 | |||
811 | // Test fractional page inputs: incomplete header | ||
812 | index=oy.buffer(og[1].header_len); | ||
813 | System.arraycopy(og[1].header_base, og[1].header+23, | ||
814 | oy.data, index, 5); | ||
815 | oy.wrote(5); | ||
816 | if(oy.pageout(og_de)>0)error(); | ||
817 | |||
818 | // Test fractional page inputs: incomplete body | ||
819 | index=oy.buffer(og[1].header_len); | ||
820 | System.arraycopy(og[1].header_base, og[1].header+28, | ||
821 | oy.data, index, og[1].header_len-28); | ||
822 | oy.wrote(og[1].header_len-28); | ||
823 | if(oy.pageout(og_de)>0)error(); | ||
824 | |||
825 | index=oy.buffer(og[1].body_len); | ||
826 | System.arraycopy(og[1].body_base, og[1].body, | ||
827 | oy.data, index, 1000); | ||
828 | oy.wrote(1000); | ||
829 | if(oy.pageout(og_de)>0)error(); | ||
830 | |||
831 | index=oy.buffer(og[1].body_len); | ||
832 | System.arraycopy(og[1].body_base, og[1].body+1000, | ||
833 | oy.data, index, og[1].body_len-1000); | ||
834 | oy.wrote(og[1].body_len-1000); | ||
835 | if(oy.pageout(og_de)<=0)error(); | ||
836 | System.err.println("ok."); | ||
837 | } | ||
838 | |||
839 | // Test fractional page inputs: page + incomplete capture | ||
840 | { | ||
841 | Page og_de=new Page(); | ||
842 | System.err.print("Testing sync on 1+partial inputs... "); | ||
843 | oy.reset(); | ||
844 | |||
845 | int index=oy.buffer(og[1].header_len); | ||
846 | System.arraycopy(og[1].header_base, og[1].header, | ||
847 | oy.data, index, og[1].header_len); | ||
848 | oy.wrote(og[1].header_len); | ||
849 | |||
850 | index=oy.buffer(og[1].body_len); | ||
851 | System.arraycopy(og[1].body_base, og[1].body, | ||
852 | oy.data, index, og[1].body_len); | ||
853 | oy.wrote(og[1].body_len); | ||
854 | |||
855 | index=oy.buffer(og[1].header_len); | ||
856 | System.arraycopy(og[1].header_base, og[1].header, | ||
857 | oy.data, index, 20); | ||
858 | oy.wrote(20); | ||
859 | if(oy.pageout(og_de)<=0)error(); | ||
860 | if(oy.pageout(og_de)>0)error(); | ||
861 | |||
862 | index=oy.buffer(og[1].header_len); | ||
863 | System.arraycopy(og[1].header_base, og[1].header+20, | ||
864 | oy.data, index, og[1].header_len-20); | ||
865 | oy.wrote(og[1].header_len-20); | ||
866 | index=oy.buffer(og[1].body_len); | ||
867 | System.arraycopy(og[1].body_base, og[1].body, | ||
868 | oy.data, index, og[1].body_len); | ||
869 | |||
870 | oy.wrote(og[1].body_len); | ||
871 | if(oy.pageout(og_de)<=0)error(); | ||
872 | |||
873 | System.err.println("ok."); | ||
874 | } | ||
875 | |||
876 | // // // // // // // // // | ||
877 | // Test recapture: garbage + page | ||
878 | { | ||
879 | Page og_de=new Page(); | ||
880 | System.err.print("Testing search for capture... "); | ||
881 | oy.reset(); | ||
882 | |||
883 | // 'garbage' | ||
884 | int index=oy.buffer(og[1].body_len); | ||
885 | System.arraycopy(og[1].body_base, og[1].body, | ||
886 | oy.data, index, og[1].body_len); | ||
887 | oy.wrote(og[1].body_len); | ||
888 | |||
889 | index=oy.buffer(og[1].header_len); | ||
890 | System.arraycopy(og[1].header_base, og[1].header, | ||
891 | oy.data, index, og[1].header_len); | ||
892 | oy.wrote(og[1].header_len); | ||
893 | |||
894 | index=oy.buffer(og[1].body_len); | ||
895 | System.arraycopy(og[1].body_base, og[1].body, | ||
896 | oy.data, index, og[1].body_len); | ||
897 | oy.wrote(og[1].body_len); | ||
898 | |||
899 | index=oy.buffer(og[2].header_len); | ||
900 | System.arraycopy(og[2].header_base, og[2].header, | ||
901 | oy.data, index, 20); | ||
902 | |||
903 | oy.wrote(20); | ||
904 | if(oy.pageout(og_de)>0)error(); | ||
905 | if(oy.pageout(og_de)<=0)error(); | ||
906 | if(oy.pageout(og_de)>0)error(); | ||
907 | |||
908 | index=oy.buffer(og[2].header_len); | ||
909 | System.arraycopy(og[2].header_base, og[2].header+20, | ||
910 | oy.data, index, og[2].header_len-20); | ||
911 | oy.wrote(og[2].header_len-20); | ||
912 | index=oy.buffer(og[2].body_len); | ||
913 | System.arraycopy(og[2].body_base, og[2].body, | ||
914 | oy.data, index, og[2].body_len); | ||
915 | oy.wrote(og[2].body_len); | ||
916 | if(oy.pageout(og_de)<=0)error(); | ||
917 | |||
918 | System.err.println("ok."); | ||
919 | } | ||
920 | |||
921 | // Test recapture: page + garbage + page | ||
922 | { | ||
923 | Page og_de=new Page(); | ||
924 | System.err.print("Testing recapture... "); | ||
925 | oy.reset(); | ||
926 | |||
927 | int index=oy.buffer(og[1].header_len); | ||
928 | System.arraycopy(og[1].header_base, og[1].header, | ||
929 | oy.data, index, og[1].header_len); | ||
930 | oy.wrote(og[1].header_len); | ||
931 | |||
932 | index=oy.buffer(og[1].body_len); | ||
933 | System.arraycopy(og[1].body_base, og[1].body, | ||
934 | oy.data, index, og[1].body_len); | ||
935 | oy.wrote(og[1].body_len); | ||
936 | |||
937 | index=oy.buffer(og[2].header_len); | ||
938 | System.arraycopy(og[2].header_base, og[2].header, | ||
939 | oy.data, index, og[2].header_len); | ||
940 | oy.wrote(og[2].header_len); | ||
941 | |||
942 | index=oy.buffer(og[2].header_len); | ||
943 | System.arraycopy(og[2].header_base, og[2].header, | ||
944 | oy.data, index, og[2].header_len); | ||
945 | oy.wrote(og[2].header_len); | ||
946 | |||
947 | if(oy.pageout(og_de)<=0)error(); | ||
948 | |||
949 | index=oy.buffer(og[2].body_len); | ||
950 | System.arraycopy(og[2].body_base, og[2].body, | ||
951 | oy.data, index, og[2].body_len-5); | ||
952 | oy.wrote(og[2].body_len-5); | ||
953 | |||
954 | index=oy.buffer(og[3].header_len); | ||
955 | System.arraycopy(og[3].header_base, og[3].header, | ||
956 | oy.data, index, og[3].header_len); | ||
957 | oy.wrote(og[3].header_len); | ||
958 | |||
959 | index=oy.buffer(og[3].body_len); | ||
960 | System.arraycopy(og[3].body_base, og[3].body, | ||
961 | oy.data, index, og[3].body_len); | ||
962 | oy.wrote(og[3].body_len); | ||
963 | |||
964 | if(oy.pageout(og_de)>0)error(); | ||
965 | if(oy.pageout(og_de)<=0)error(); | ||
966 | |||
967 | System.err.println("ok."); | ||
968 | } | ||
969 | } | ||
970 | //return(0); | ||
971 | } | ||
972 | */ | ||
973 | } | ||
diff --git a/songdbj/com/jcraft/jogg/StreamState.java b/songdbj/com/jcraft/jogg/StreamState.java new file mode 100644 index 0000000000..2f34b374f8 --- /dev/null +++ b/songdbj/com/jcraft/jogg/StreamState.java | |||
@@ -0,0 +1,657 @@ | |||
1 | /* JOrbis | ||
2 | * Copyright (C) 2000 ymnk, JCraft,Inc. | ||
3 | * | ||
4 | * Written by: 2000 ymnk<ymnk@jcraft.com> | ||
5 | * | ||
6 | * Many thanks to | ||
7 | * Monty <monty@xiph.org> and | ||
8 | * The XIPHOPHORUS Company http://www.xiph.org/ . | ||
9 | * JOrbis has been based on their awesome works, Vorbis codec. | ||
10 | * | ||
11 | * This program is free software; you can redistribute it and/or | ||
12 | * modify it under the terms of the GNU Library General Public License | ||
13 | * as published by the Free Software Foundation; either version 2 of | ||
14 | * the License, or (at your option) any later version. | ||
15 | |||
16 | * This program is distributed in the hope that it will be useful, | ||
17 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
18 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
19 | * GNU Library General Public License for more details. | ||
20 | * | ||
21 | * You should have received a copy of the GNU Library General Public | ||
22 | * License along with this program; if not, write to the Free Software | ||
23 | * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | ||
24 | */ | ||
25 | |||
26 | package com.jcraft.jogg; | ||
27 | |||
28 | public class StreamState{ | ||
29 | byte[] body_data; /* bytes from packet bodies */ | ||
30 | int body_storage; /* storage elements allocated */ | ||
31 | int body_fill; /* elements stored; fill mark */ | ||
32 | private int body_returned; /* elements of fill returned */ | ||
33 | |||
34 | |||
35 | int[] lacing_vals; /* The values that will go to the segment table */ | ||
36 | long[] granule_vals; /* pcm_pos values for headers. Not compact | ||
37 | this way, but it is simple coupled to the | ||
38 | lacing fifo */ | ||
39 | int lacing_storage; | ||
40 | int lacing_fill; | ||
41 | int lacing_packet; | ||
42 | int lacing_returned; | ||
43 | |||
44 | byte[] header=new byte[282]; /* working space for header encode */ | ||
45 | int header_fill; | ||
46 | |||
47 | public int e_o_s; /* set when we have buffered the last packet in the | ||
48 | logical bitstream */ | ||
49 | int b_o_s; /* set after we've written the initial page | ||
50 | of a logical bitstream */ | ||
51 | int serialno; | ||
52 | int pageno; | ||
53 | long packetno; /* sequence number for decode; the framing | ||
54 | knows where there's a hole in the data, | ||
55 | but we need coupling so that the codec | ||
56 | (which is in a seperate abstraction | ||
57 | layer) also knows about the gap */ | ||
58 | long granulepos; | ||
59 | |||
60 | public StreamState(){ | ||
61 | init(); | ||
62 | } | ||
63 | |||
64 | StreamState(int serialno){ | ||
65 | this(); | ||
66 | init(serialno); | ||
67 | } | ||
68 | void init(){ | ||
69 | body_storage=16*1024; | ||
70 | body_data=new byte[body_storage]; | ||
71 | lacing_storage=1024; | ||
72 | lacing_vals=new int[lacing_storage]; | ||
73 | granule_vals=new long[lacing_storage]; | ||
74 | } | ||
75 | public void init(int serialno){ | ||
76 | if(body_data==null){ init(); } | ||
77 | else{ | ||
78 | for(int i=0; i<body_data.length; i++) body_data[i]=0; | ||
79 | for(int i=0; i<lacing_vals.length; i++) lacing_vals[i]=0; | ||
80 | for(int i=0; i<granule_vals.length; i++) granule_vals[i]=0; | ||
81 | } | ||
82 | this.serialno=serialno; | ||
83 | } | ||
84 | public void clear(){ | ||
85 | body_data=null; | ||
86 | lacing_vals=null; | ||
87 | granule_vals=null; | ||
88 | //memset(os,0,sizeof(ogg_stream_state)); | ||
89 | } | ||
90 | void destroy(){ | ||
91 | clear(); | ||
92 | } | ||
93 | void body_expand(int needed){ | ||
94 | if(body_storage<=body_fill+needed){ | ||
95 | body_storage+=(needed+1024); | ||
96 | byte[] foo=new byte[body_storage]; | ||
97 | System.arraycopy(body_data, 0, foo, 0, body_data.length); | ||
98 | body_data=foo; | ||
99 | //System.out.println("expand: body_fill="+body_fill+", body_storage="+body_data.length); | ||
100 | } | ||
101 | } | ||
102 | void lacing_expand(int needed){ | ||
103 | if(lacing_storage<=lacing_fill+needed){ | ||
104 | lacing_storage+=(needed+32); | ||
105 | int[] foo=new int[lacing_storage]; | ||
106 | System.arraycopy(lacing_vals, 0, foo, 0, lacing_vals.length); | ||
107 | lacing_vals=foo; | ||
108 | |||
109 | long[] bar=new long[lacing_storage]; | ||
110 | System.arraycopy(granule_vals, 0, bar, 0, granule_vals.length); | ||
111 | granule_vals=bar; | ||
112 | } | ||
113 | } | ||
114 | |||
115 | /* submit data to the internal buffer of the framing engine */ | ||
116 | public int packetin(Packet op){ | ||
117 | int lacing_val=op.bytes/255+1; | ||
118 | |||
119 | if(body_returned!=0){ | ||
120 | /* advance packet data according to the body_returned pointer. We | ||
121 | had to keep it around to return a pointer into the buffer last | ||
122 | call */ | ||
123 | |||
124 | body_fill-=body_returned; | ||
125 | if(body_fill!=0){ | ||
126 | // memmove(os->body_data,os->body_data+os->body_returned, | ||
127 | // os->body_fill*sizeof(char)); | ||
128 | System.arraycopy(body_data, body_returned, body_data, 0, body_fill); | ||
129 | } | ||
130 | body_returned=0; | ||
131 | } | ||
132 | |||
133 | /* make sure we have the buffer storage */ | ||
134 | body_expand(op.bytes); | ||
135 | lacing_expand(lacing_val); | ||
136 | |||
137 | /* Copy in the submitted packet. Yes, the copy is a waste; this is | ||
138 | the liability of overly clean abstraction for the time being. It | ||
139 | will actually be fairly easy to eliminate the extra copy in the | ||
140 | future */ | ||
141 | |||
142 | System.arraycopy(op.packet_base, op.packet, body_data, body_fill, op.bytes); | ||
143 | body_fill+=op.bytes; | ||
144 | //System.out.println("add: "+body_fill); | ||
145 | |||
146 | /* Store lacing vals for this packet */ | ||
147 | int j; | ||
148 | for(j=0;j<lacing_val-1;j++){ | ||
149 | lacing_vals[lacing_fill+j]=255; | ||
150 | granule_vals[lacing_fill+j]=granulepos; | ||
151 | } | ||
152 | lacing_vals[lacing_fill+j]=(op.bytes)%255; | ||
153 | granulepos=granule_vals[lacing_fill+j]=op.granulepos; | ||
154 | |||
155 | /* flag the first segment as the beginning of the packet */ | ||
156 | lacing_vals[lacing_fill]|= 0x100; | ||
157 | |||
158 | lacing_fill+=lacing_val; | ||
159 | |||
160 | /* for the sake of completeness */ | ||
161 | packetno++; | ||
162 | |||
163 | if(op.e_o_s!=0)e_o_s=1; | ||
164 | return(0); | ||
165 | } | ||
166 | |||
167 | public int packetout(Packet op){ | ||
168 | |||
169 | /* The last part of decode. We have the stream broken into packet | ||
170 | segments. Now we need to group them into packets (or return the | ||
171 | out of sync markers) */ | ||
172 | |||
173 | int ptr=lacing_returned; | ||
174 | |||
175 | if(lacing_packet<=ptr){ | ||
176 | return(0); | ||
177 | } | ||
178 | |||
179 | if((lacing_vals[ptr]&0x400)!=0){ | ||
180 | /* We lost sync here; let the app know */ | ||
181 | lacing_returned++; | ||
182 | |||
183 | /* we need to tell the codec there's a gap; it might need to | ||
184 | handle previous packet dependencies. */ | ||
185 | packetno++; | ||
186 | return(-1); | ||
187 | } | ||
188 | |||
189 | /* Gather the whole packet. We'll have no holes or a partial packet */ | ||
190 | { | ||
191 | int size=lacing_vals[ptr]&0xff; | ||
192 | int bytes=0; | ||
193 | |||
194 | op.packet_base=body_data; | ||
195 | op.packet=body_returned; | ||
196 | op.e_o_s=lacing_vals[ptr]&0x200; /* last packet of the stream? */ | ||
197 | op.b_o_s=lacing_vals[ptr]&0x100; /* first packet of the stream? */ | ||
198 | bytes+=size; | ||
199 | |||
200 | while(size==255){ | ||
201 | int val=lacing_vals[++ptr]; | ||
202 | size=val&0xff; | ||
203 | if((val&0x200)!=0)op.e_o_s=0x200; | ||
204 | bytes+=size; | ||
205 | } | ||
206 | |||
207 | op.packetno=packetno; | ||
208 | op.granulepos=granule_vals[ptr]; | ||
209 | op.bytes=bytes; | ||
210 | |||
211 | //System.out.println(this+" # body_returned="+body_returned); | ||
212 | body_returned+=bytes; | ||
213 | //System.out.println(this+"## body_returned="+body_returned); | ||
214 | |||
215 | lacing_returned=ptr+1; | ||
216 | } | ||
217 | packetno++; | ||
218 | return(1); | ||
219 | } | ||
220 | |||
221 | |||
222 | // add the incoming page to the stream state; we decompose the page | ||
223 | // into packet segments here as well. | ||
224 | |||
225 | public int pagein(Page og){ | ||
226 | byte[] header_base=og.header_base; | ||
227 | int header=og.header; | ||
228 | byte[] body_base=og.body_base; | ||
229 | int body=og.body; | ||
230 | int bodysize=og.body_len; | ||
231 | int segptr=0; | ||
232 | |||
233 | int version=og.version(); | ||
234 | int continued=og.continued(); | ||
235 | int bos=og.bos(); | ||
236 | int eos=og.eos(); | ||
237 | long granulepos=og.granulepos(); | ||
238 | int _serialno=og.serialno(); | ||
239 | int _pageno=og.pageno(); | ||
240 | int segments=header_base[header+26]&0xff; | ||
241 | |||
242 | // clean up 'returned data' | ||
243 | { | ||
244 | int lr=lacing_returned; | ||
245 | int br=body_returned; | ||
246 | |||
247 | // body data | ||
248 | |||
249 | //System.out.println("br="+br+", body_fill="+body_fill); | ||
250 | |||
251 | if(br!=0){ | ||
252 | body_fill-=br; | ||
253 | if(body_fill!=0){ | ||
254 | System.arraycopy(body_data, br, body_data, 0, body_fill); | ||
255 | } | ||
256 | body_returned=0; | ||
257 | } | ||
258 | |||
259 | //System.out.println("?? br="+br+", body_fill="+body_fill+" body_returned="+body_returned); | ||
260 | |||
261 | if(lr!=0){ | ||
262 | // segment table | ||
263 | if((lacing_fill-lr)!=0){ | ||
264 | System.arraycopy(lacing_vals, lr, lacing_vals, 0, lacing_fill-lr); | ||
265 | System.arraycopy(granule_vals, lr, granule_vals, 0, lacing_fill-lr); | ||
266 | } | ||
267 | lacing_fill-=lr; | ||
268 | lacing_packet-=lr; | ||
269 | lacing_returned=0; | ||
270 | } | ||
271 | } | ||
272 | |||
273 | // check the serial number | ||
274 | if(_serialno!=serialno)return(-1); | ||
275 | if(version>0)return(-1); | ||
276 | |||
277 | lacing_expand(segments+1); | ||
278 | |||
279 | // are we in sequence? | ||
280 | if(_pageno!=pageno){ | ||
281 | int i; | ||
282 | |||
283 | // unroll previous partial packet (if any) | ||
284 | for(i=lacing_packet;i<lacing_fill;i++){ | ||
285 | body_fill-=lacing_vals[i]&0xff; | ||
286 | //System.out.println("??"); | ||
287 | } | ||
288 | lacing_fill=lacing_packet; | ||
289 | |||
290 | // make a note of dropped data in segment table | ||
291 | if(pageno!=-1){ | ||
292 | lacing_vals[lacing_fill++]=0x400; | ||
293 | lacing_packet++; | ||
294 | } | ||
295 | |||
296 | // are we a 'continued packet' page? If so, we'll need to skip | ||
297 | // some segments | ||
298 | if(continued!=0){ | ||
299 | bos=0; | ||
300 | for(;segptr<segments;segptr++){ | ||
301 | int val=(header_base[header+27+segptr]&0xff); | ||
302 | body+=val; | ||
303 | bodysize-=val; | ||
304 | if(val<255){ | ||
305 | segptr++; | ||
306 | break; | ||
307 | } | ||
308 | } | ||
309 | } | ||
310 | } | ||
311 | |||
312 | //System.out.println("bodysize="+bodysize); | ||
313 | |||
314 | if(bodysize!=0){ | ||
315 | body_expand(bodysize); | ||
316 | System.arraycopy(body_base, body, body_data, body_fill, bodysize); | ||
317 | body_fill+=bodysize; | ||
318 | } | ||
319 | |||
320 | //System.out.println("bodyfill="+body_fill); | ||
321 | |||
322 | { | ||
323 | int saved=-1; | ||
324 | while(segptr<segments){ | ||
325 | int val=(header_base[header+27+segptr]&0xff); | ||
326 | lacing_vals[lacing_fill]=val; | ||
327 | granule_vals[lacing_fill]=-1; | ||
328 | |||
329 | if(bos!=0){ | ||
330 | lacing_vals[lacing_fill]|=0x100; | ||
331 | bos=0; | ||
332 | } | ||
333 | |||
334 | if(val<255)saved=lacing_fill; | ||
335 | |||
336 | lacing_fill++; | ||
337 | segptr++; | ||
338 | |||
339 | if(val<255)lacing_packet=lacing_fill; | ||
340 | } | ||
341 | |||
342 | /* set the granulepos on the last pcmval of the last full packet */ | ||
343 | if(saved!=-1){ | ||
344 | granule_vals[saved]=granulepos; | ||
345 | } | ||
346 | } | ||
347 | |||
348 | if(eos!=0){ | ||
349 | e_o_s=1; | ||
350 | if(lacing_fill>0) | ||
351 | lacing_vals[lacing_fill-1]|=0x200; | ||
352 | } | ||
353 | |||
354 | pageno=_pageno+1; | ||
355 | return(0); | ||
356 | } | ||
357 | |||
358 | |||
359 | /* This will flush remaining packets into a page (returning nonzero), | ||
360 | even if there is not enough data to trigger a flush normally | ||
361 | (undersized page). If there are no packets or partial packets to | ||
362 | flush, ogg_stream_flush returns 0. Note that ogg_stream_flush will | ||
363 | try to flush a normal sized page like ogg_stream_pageout; a call to | ||
364 | ogg_stream_flush does not gurantee that all packets have flushed. | ||
365 | Only a return value of 0 from ogg_stream_flush indicates all packet | ||
366 | data is flushed into pages. | ||
367 | |||
368 | ogg_stream_page will flush the last page in a stream even if it's | ||
369 | undersized; you almost certainly want to use ogg_stream_pageout | ||
370 | (and *not* ogg_stream_flush) unless you need to flush an undersized | ||
371 | page in the middle of a stream for some reason. */ | ||
372 | |||
373 | public int flush(Page og){ | ||
374 | |||
375 | //System.out.println(this+" ---body_returned: "+body_returned); | ||
376 | |||
377 | int i; | ||
378 | int vals=0; | ||
379 | int maxvals=(lacing_fill>255?255:lacing_fill); | ||
380 | int bytes=0; | ||
381 | int acc=0; | ||
382 | long granule_pos=granule_vals[0]; | ||
383 | |||
384 | if(maxvals==0)return(0); | ||
385 | |||
386 | /* construct a page */ | ||
387 | /* decide how many segments to include */ | ||
388 | |||
389 | /* If this is the initial header case, the first page must only include | ||
390 | the initial header packet */ | ||
391 | if(b_o_s==0){ /* 'initial header page' case */ | ||
392 | granule_pos=0; | ||
393 | for(vals=0;vals<maxvals;vals++){ | ||
394 | if((lacing_vals[vals]&0x0ff)<255){ | ||
395 | vals++; | ||
396 | break; | ||
397 | } | ||
398 | } | ||
399 | } | ||
400 | else{ | ||
401 | for(vals=0;vals<maxvals;vals++){ | ||
402 | if(acc>4096)break; | ||
403 | acc+=(lacing_vals[vals]&0x0ff); | ||
404 | granule_pos=granule_vals[vals]; | ||
405 | } | ||
406 | } | ||
407 | |||
408 | /* construct the header in temp storage */ | ||
409 | System.arraycopy("OggS".getBytes(), 0, header, 0, 4); | ||
410 | |||
411 | /* stream structure version */ | ||
412 | header[4]=0x00; | ||
413 | |||
414 | /* continued packet flag? */ | ||
415 | header[5]=0x00; | ||
416 | if((lacing_vals[0]&0x100)==0)header[5]|=0x01; | ||
417 | /* first page flag? */ | ||
418 | if(b_o_s==0) header[5]|=0x02; | ||
419 | /* last page flag? */ | ||
420 | if(e_o_s!=0 && lacing_fill==vals) header[5]|=0x04; | ||
421 | b_o_s=1; | ||
422 | |||
423 | /* 64 bits of PCM position */ | ||
424 | for(i=6;i<14;i++){ | ||
425 | header[i]=(byte)granule_pos; | ||
426 | granule_pos>>>=8; | ||
427 | } | ||
428 | |||
429 | /* 32 bits of stream serial number */ | ||
430 | { | ||
431 | int _serialno=serialno; | ||
432 | for(i=14;i<18;i++){ | ||
433 | header[i]=(byte)_serialno; | ||
434 | _serialno>>>=8; | ||
435 | } | ||
436 | } | ||
437 | |||
438 | /* 32 bits of page counter (we have both counter and page header | ||
439 | because this val can roll over) */ | ||
440 | if(pageno==-1)pageno=0; /* because someone called | ||
441 | stream_reset; this would be a | ||
442 | strange thing to do in an | ||
443 | encode stream, but it has | ||
444 | plausible uses */ | ||
445 | { | ||
446 | int _pageno=pageno++; | ||
447 | for(i=18;i<22;i++){ | ||
448 | header[i]=(byte)_pageno; | ||
449 | _pageno>>>=8; | ||
450 | } | ||
451 | } | ||
452 | |||
453 | /* zero for computation; filled in later */ | ||
454 | header[22]=0; | ||
455 | header[23]=0; | ||
456 | header[24]=0; | ||
457 | header[25]=0; | ||
458 | |||
459 | /* segment table */ | ||
460 | header[26]=(byte)vals; | ||
461 | for(i=0;i<vals;i++){ | ||
462 | header[i+27]=(byte)lacing_vals[i]; | ||
463 | bytes+=(header[i+27]&0xff); | ||
464 | } | ||
465 | |||
466 | /* set pointers in the ogg_page struct */ | ||
467 | og.header_base=header; | ||
468 | og.header=0; | ||
469 | og.header_len=header_fill=vals+27; | ||
470 | og.body_base=body_data; | ||
471 | og.body=body_returned; | ||
472 | og.body_len=bytes; | ||
473 | |||
474 | /* advance the lacing data and set the body_returned pointer */ | ||
475 | |||
476 | //System.out.println("###body_returned: "+body_returned); | ||
477 | |||
478 | lacing_fill-=vals; | ||
479 | System.arraycopy(lacing_vals, vals, lacing_vals, 0, lacing_fill*4); | ||
480 | System.arraycopy(granule_vals, vals, granule_vals, 0, lacing_fill*8); | ||
481 | body_returned+=bytes; | ||
482 | |||
483 | //System.out.println("####body_returned: "+body_returned); | ||
484 | |||
485 | /* calculate the checksum */ | ||
486 | |||
487 | og.checksum(); | ||
488 | |||
489 | /* done */ | ||
490 | return(1); | ||
491 | } | ||
492 | |||
493 | |||
494 | /* This constructs pages from buffered packet segments. The pointers | ||
495 | returned are to static buffers; do not free. The returned buffers are | ||
496 | good only until the next call (using the same ogg_stream_state) */ | ||
497 | public int pageout(Page og){ | ||
498 | // if(body_returned!=0){ | ||
499 | // /* advance packet data according to the body_returned pointer. We | ||
500 | // had to keep it around to return a pointer into the buffer last | ||
501 | // call */ | ||
502 | // | ||
503 | // body_fill-=body_returned; | ||
504 | // if(body_fill!=0){ // overlap? | ||
505 | // System.arraycopy(body_data, body_returned, body_data, 0, body_fill); | ||
506 | // } | ||
507 | // body_returned=0; | ||
508 | // } | ||
509 | // | ||
510 | //System.out.println("pageout: e_o_s="+e_o_s+" lacing_fill="+lacing_fill+" body_fill="+body_fill+", lacing_fill="+lacing_fill+" b_o_s="+b_o_s); | ||
511 | // | ||
512 | // if((e_o_s!=0&&lacing_fill!=0) || /* 'were done, now flush' case */ | ||
513 | // body_fill > 4096 || /* 'page nominal size' case */ | ||
514 | // lacing_fill>=255 || /* 'segment table full' case */ | ||
515 | // (lacing_fill!=0&&b_o_s==0)){ /* 'initial header page' case */ | ||
516 | // int vals=0,bytes=0; | ||
517 | // int maxvals=(lacing_fill>255?255:lacing_fill); | ||
518 | // long acc=0; | ||
519 | // long pcm_pos=granule_vals[0]; | ||
520 | // | ||
521 | // /* construct a page */ | ||
522 | // /* decide how many segments to include */ | ||
523 | // | ||
524 | // /* If this is the initial header case, the first page must only include | ||
525 | // the initial header packet */ | ||
526 | // if(b_o_s==0){ /* 'initial header page' case */ | ||
527 | // pcm_pos=0; | ||
528 | // for(vals=0;vals<maxvals;vals++){ | ||
529 | // if((lacing_vals[vals]&0x0ff)<255){ | ||
530 | // vals++; | ||
531 | // break; | ||
532 | // } | ||
533 | // } | ||
534 | // } | ||
535 | // else{ | ||
536 | // for(vals=0;vals<maxvals;vals++){ | ||
537 | // if(acc>4096)break; | ||
538 | // acc+=lacing_vals[vals]&0x0ff; | ||
539 | // pcm_pos=granule_vals[vals]; | ||
540 | // } | ||
541 | // } | ||
542 | // | ||
543 | // /* construct the header in temp storage */ | ||
544 | // System.arraycopy("OggS".getBytes(), 0, header, 0, 4); | ||
545 | // | ||
546 | // /* stream structure version */ | ||
547 | // header[4]=0x00; | ||
548 | // | ||
549 | // /* continued packet flag? */ | ||
550 | // header[5]=0x00; | ||
551 | // if((lacing_vals[0]&0x100)==0)header[5]|=0x01; | ||
552 | // /* first page flag? */ | ||
553 | // if(b_o_s==0)header[5]|=0x02; | ||
554 | // /* last page flag? */ | ||
555 | // if(e_o_s!=0 && lacing_fill==vals)header[5]|=0x04; | ||
556 | // b_o_s=1; | ||
557 | // | ||
558 | // /* 64 bits of PCM position */ | ||
559 | // for(int i=6;i<14;i++){ | ||
560 | // header[i]=(byte)pcm_pos; | ||
561 | // pcm_pos>>>=8; | ||
562 | // } | ||
563 | // | ||
564 | // /* 32 bits of stream serial number */ | ||
565 | // { | ||
566 | // int serialn=serialno; | ||
567 | // for(int i=14;i<18;i++){ | ||
568 | // header[i]=(byte)serialn; | ||
569 | // serialn>>>=8; | ||
570 | // } | ||
571 | // } | ||
572 | // | ||
573 | // | ||
574 | ///* 32 bits of page counter (we have both counter and page header | ||
575 | // because this val can roll over) */ | ||
576 | // if(pageno==-1)pageno=0; /* because someone called | ||
577 | // stream_reset; this would be a | ||
578 | // strange thing to do in an | ||
579 | // encode stream, but it has | ||
580 | // plausible uses */ | ||
581 | // { | ||
582 | // int pagen=pageno++; | ||
583 | // for(int i=18;i<22;i++){ | ||
584 | // header[i]=(byte)pagen; | ||
585 | // pagen>>>=8; | ||
586 | // } | ||
587 | // } | ||
588 | // | ||
589 | // /* zero for computation; filled in later */ | ||
590 | // header[22]=0; | ||
591 | // header[23]=0; | ||
592 | // header[24]=0; | ||
593 | // header[25]=0; | ||
594 | // | ||
595 | // /* segment table */ | ||
596 | // header[26]=(byte)vals; | ||
597 | // for(int i=0;i<vals;i++){ | ||
598 | // header[i+27]=(byte)lacing_vals[i]; | ||
599 | // bytes+=header[i+27]&0xff; | ||
600 | //// bytes+=header[i+27]=(lacing_vals[i]&0xff); | ||
601 | // } | ||
602 | // | ||
603 | // /* advance the lacing data and set the body_returned pointer */ | ||
604 | // | ||
605 | // lacing_fill-=vals; | ||
606 | // System.arraycopy(lacing_vals, vals, lacing_vals, 0, lacing_fill); | ||
607 | // System.arraycopy(granule_vals, vals, granule_vals, 0, lacing_fill); | ||
608 | // body_returned=bytes; | ||
609 | // | ||
610 | // /* set pointers in the ogg_page struct */ | ||
611 | // og.header_base=header; | ||
612 | // og.header=0; | ||
613 | // og.header_len=header_fill=vals+27; | ||
614 | // | ||
615 | // og.body_base=body_data; | ||
616 | // og.body=0; | ||
617 | // og.body_len=bytes; | ||
618 | // | ||
619 | // /* calculate the checksum */ | ||
620 | // | ||
621 | // og.checksum(); | ||
622 | // return(1); | ||
623 | // } | ||
624 | // /* not enough data to construct a page and not end of stream */ | ||
625 | // return(0); | ||
626 | //System.out.println("pageout: "+body_returned); | ||
627 | if((e_o_s!=0&&lacing_fill!=0) || /* 'were done, now flush' case */ | ||
628 | body_fill-body_returned> 4096 || /* 'page nominal size' case */ | ||
629 | lacing_fill>=255 || /* 'segment table full' case */ | ||
630 | (lacing_fill!=0&&b_o_s==0)){ /* 'initial header page' case */ | ||
631 | return flush(og); | ||
632 | } | ||
633 | return 0; | ||
634 | } | ||
635 | |||
636 | public int eof(){ | ||
637 | return e_o_s; | ||
638 | } | ||
639 | |||
640 | public int reset(){ | ||
641 | body_fill=0; | ||
642 | body_returned=0; | ||
643 | |||
644 | lacing_fill=0; | ||
645 | lacing_packet=0; | ||
646 | lacing_returned=0; | ||
647 | |||
648 | header_fill=0; | ||
649 | |||
650 | e_o_s=0; | ||
651 | b_o_s=0; | ||
652 | pageno=-1; | ||
653 | packetno=0; | ||
654 | granulepos=0; | ||
655 | return(0); | ||
656 | } | ||
657 | } | ||
diff --git a/songdbj/com/jcraft/jogg/SyncState.java b/songdbj/com/jcraft/jogg/SyncState.java new file mode 100644 index 0000000000..b3705e54dd --- /dev/null +++ b/songdbj/com/jcraft/jogg/SyncState.java | |||
@@ -0,0 +1,275 @@ | |||
1 | /* JOrbis | ||
2 | * Copyright (C) 2000 ymnk, JCraft,Inc. | ||
3 | * | ||
4 | * Written by: 2000 ymnk<ymnk@jcraft.com> | ||
5 | * | ||
6 | * Many thanks to | ||
7 | * Monty <monty@xiph.org> and | ||
8 | * The XIPHOPHORUS Company http://www.xiph.org/ . | ||
9 | * JOrbis has been based on their awesome works, Vorbis codec. | ||
10 | * | ||
11 | * This program is free software; you can redistribute it and/or | ||
12 | * modify it under the terms of the GNU Library General Public License | ||
13 | * as published by the Free Software Foundation; either version 2 of | ||
14 | * the License, or (at your option) any later version. | ||
15 | |||
16 | * This program is distributed in the hope that it will be useful, | ||
17 | * but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
18 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | ||
19 | * GNU Library General Public License for more details. | ||
20 | * | ||
21 | * You should have received a copy of the GNU Library General Public | ||
22 | * License along with this program; if not, write to the Free Software | ||
23 | * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. | ||
24 | */ | ||
25 | |||
26 | package com.jcraft.jogg; | ||
27 | |||
28 | // DECODING PRIMITIVES: packet streaming layer | ||
29 | |||
30 | // This has two layers to place more of the multi-serialno and paging | ||
31 | // control in the application's hands. First, we expose a data buffer | ||
32 | // using ogg_decode_buffer(). The app either copies into the | ||
33 | // buffer, or passes it directly to read(), etc. We then call | ||
34 | // ogg_decode_wrote() to tell how many bytes we just added. | ||
35 | // | ||
36 | // Pages are returned (pointers into the buffer in ogg_sync_state) | ||
37 | // by ogg_decode_stream(). The page is then submitted to | ||
38 | // ogg_decode_page() along with the appropriate | ||
39 | // ogg_stream_state* (ie, matching serialno). We then get raw | ||
40 | // packets out calling ogg_stream_packet() with a | ||
41 | // ogg_stream_state. See the 'frame-prog.txt' docs for details and | ||
42 | // example code. | ||
43 | |||
44 | public class SyncState{ | ||
45 | |||
46 | public byte[] data; | ||
47 | int storage; | ||
48 | int fill; | ||
49 | int returned; | ||
50 | |||
51 | int unsynced; | ||
52 | int headerbytes; | ||
53 | int bodybytes; | ||
54 | |||
55 | public int clear(){ | ||
56 | data=null; | ||
57 | return(0); | ||
58 | } | ||
59 | |||
60 | // !!!!!!!!!!!! | ||
61 | // byte[] buffer(int size){ | ||
62 | public int buffer(int size){ | ||
63 | // first, clear out any space that has been previously returned | ||
64 | if(returned!=0){ | ||
65 | fill-=returned; | ||
66 | if(fill>0){ | ||
67 | System.arraycopy(data, returned, data, 0, fill); | ||
68 | } | ||
69 | returned=0; | ||
70 | } | ||
71 | |||
72 | if(size>storage-fill){ | ||
73 | // We need to extend the internal buffer | ||
74 | int newsize=size+fill+4096; // an extra page to be nice | ||
75 | if(data!=null){ | ||
76 | byte[] foo=new byte[newsize]; | ||
77 | System.arraycopy(data, 0, foo, 0, data.length); | ||
78 | data=foo; | ||
79 | } | ||
80 | else{ | ||
81 | data=new byte[newsize]; | ||
82 | } | ||
83 | storage=newsize; | ||
84 | } | ||
85 | |||
86 | // expose a segment at least as large as requested at the fill mark | ||
87 | // return((char *)oy->data+oy->fill); | ||
88 | // return(data); | ||
89 | return(fill); | ||
90 | } | ||
91 | |||
92 | public int wrote(int bytes){ | ||
93 | if(fill+bytes>storage)return(-1); | ||
94 | fill+=bytes; | ||
95 | return(0); | ||
96 | } | ||
97 | |||
98 | // sync the stream. This is meant to be useful for finding page | ||
99 | // boundaries. | ||
100 | // | ||
101 | // return values for this: | ||
102 | // -n) skipped n bytes | ||
103 | // 0) page not ready; more data (no bytes skipped) | ||
104 | // n) page synced at current location; page length n bytes | ||
105 | private Page pageseek=new Page(); | ||
106 | private byte[] chksum=new byte[4]; | ||
107 | public int pageseek(Page og){ | ||
108 | int page=returned; | ||
109 | int next; | ||
110 | int bytes=fill-returned; | ||
111 | |||
112 | if(headerbytes==0){ | ||
113 | int _headerbytes,i; | ||
114 | if(bytes<27)return(0); // not enough for a header | ||
115 | |||
116 | /* verify capture pattern */ | ||
117 | //!!!!!!!!!!! | ||
118 | if(data[page]!='O' || | ||
119 | data[page+1]!='g' || | ||
120 | data[page+2]!='g' || | ||
121 | data[page+3]!='S'){ | ||
122 | headerbytes=0; | ||
123 | bodybytes=0; | ||
124 | |||
125 | // search for possible capture | ||
126 | next=0; | ||
127 | for(int ii=0; ii<bytes-1; ii++){ | ||
128 | if(data[page+1+ii]=='O'){next=page+1+ii; break;} | ||
129 | } | ||
130 | //next=memchr(page+1,'O',bytes-1); | ||
131 | if(next==0) next=fill; | ||
132 | |||
133 | returned=next; | ||
134 | return(-(next-page)); | ||
135 | } | ||
136 | _headerbytes=(data[page+26]&0xff)+27; | ||
137 | if(bytes<_headerbytes)return(0); // not enough for header + seg table | ||
138 | |||
139 | // count up body length in the segment table | ||
140 | |||
141 | for(i=0;i<(data[page+26]&0xff);i++){ | ||
142 | bodybytes+=(data[page+27+i]&0xff); | ||
143 | } | ||
144 | headerbytes=_headerbytes; | ||
145 | } | ||
146 | |||
147 | if(bodybytes+headerbytes>bytes)return(0); | ||
148 | |||
149 | // The whole test page is buffered. Verify the checksum | ||
150 | synchronized(chksum){ | ||
151 | // Grab the checksum bytes, set the header field to zero | ||
152 | |||
153 | System.arraycopy(data, page+22, chksum, 0, 4); | ||
154 | data[page+22]=0; | ||
155 | data[page+23]=0; | ||
156 | data[page+24]=0; | ||
157 | data[page+25]=0; | ||
158 | |||
159 | // set up a temp page struct and recompute the checksum | ||
160 | Page log=pageseek; | ||
161 | log.header_base=data; | ||
162 | log.header=page; | ||
163 | log.header_len=headerbytes; | ||
164 | |||
165 | log.body_base=data; | ||
166 | log.body=page+headerbytes; | ||
167 | log.body_len=bodybytes; | ||
168 | log.checksum(); | ||
169 | |||
170 | // Compare | ||
171 | if(chksum[0]!=data[page+22] || | ||
172 | chksum[1]!=data[page+23] || | ||
173 | chksum[2]!=data[page+24] || | ||
174 | chksum[3]!=data[page+25]){ | ||
175 | // D'oh. Mismatch! Corrupt page (or miscapture and not a page at all) | ||
176 | // replace the computed checksum with the one actually read in | ||
177 | System.arraycopy(chksum, 0, data, page+22, 4); | ||
178 | // Bad checksum. Lose sync */ | ||
179 | |||
180 | headerbytes=0; | ||
181 | bodybytes=0; | ||
182 | // search for possible capture | ||
183 | next=0; | ||
184 | for(int ii=0; ii<bytes-1; ii++){ | ||
185 | if(data[page+1+ii]=='O'){next=page+1+ii; break;} | ||
186 | } | ||
187 | //next=memchr(page+1,'O',bytes-1); | ||
188 | if(next==0) next=fill; | ||
189 | returned=next; | ||
190 | return(-(next-page)); | ||
191 | } | ||
192 | } | ||
193 | |||
194 | // yes, have a whole page all ready to go | ||
195 | { | ||
196 | page=returned; | ||
197 | |||
198 | if(og!=null){ | ||
199 | og.header_base=data; | ||
200 | og.header=page; | ||
201 | og.header_len=headerbytes; | ||
202 | og.body_base=data; | ||
203 | og.body=page+headerbytes; | ||
204 | og.body_len=bodybytes; | ||
205 | } | ||
206 | |||
207 | unsynced=0; | ||
208 | returned+=(bytes=headerbytes+bodybytes); | ||
209 | headerbytes=0; | ||
210 | bodybytes=0; | ||
211 | return(bytes); | ||
212 | } | ||
213 | // headerbytes=0; | ||
214 | // bodybytes=0; | ||
215 | // next=0; | ||
216 | // for(int ii=0; ii<bytes-1; ii++){ | ||
217 | // if(data[page+1+ii]=='O'){next=page+1+ii;} | ||
218 | // } | ||
219 | // //next=memchr(page+1,'O',bytes-1); | ||
220 | // if(next==0) next=fill; | ||
221 | // returned=next; | ||
222 | // return(-(next-page)); | ||
223 | } | ||
224 | |||
225 | |||
226 | // sync the stream and get a page. Keep trying until we find a page. | ||
227 | // Supress 'sync errors' after reporting the first. | ||
228 | // | ||
229 | // return values: | ||
230 | // -1) recapture (hole in data) | ||
231 | // 0) need more data | ||
232 | // 1) page returned | ||
233 | // | ||
234 | // Returns pointers into buffered data; invalidated by next call to | ||
235 | // _stream, _clear, _init, or _buffer | ||
236 | |||
237 | public int pageout(Page og){ | ||
238 | // all we need to do is verify a page at the head of the stream | ||
239 | // buffer. If it doesn't verify, we look for the next potential | ||
240 | // frame | ||
241 | |||
242 | while(true){ | ||
243 | int ret=pageseek(og); | ||
244 | if(ret>0){ | ||
245 | // have a page | ||
246 | return(1); | ||
247 | } | ||
248 | if(ret==0){ | ||
249 | // need more data | ||
250 | return(0); | ||
251 | } | ||
252 | |||
253 | // head did not start a synced page... skipped some bytes | ||
254 | if(unsynced==0){ | ||
255 | unsynced=1; | ||
256 | return(-1); | ||
257 | } | ||
258 | // loop. keep looking | ||
259 | } | ||
260 | } | ||
261 | |||
262 | // clear things to an initial state. Good to call, eg, before seeking | ||
263 | public int reset(){ | ||
264 | fill=0; | ||
265 | returned=0; | ||
266 | unsynced=0; | ||
267 | headerbytes=0; | ||
268 | bodybytes=0; | ||
269 | return(0); | ||
270 | } | ||
271 | public void init(){} | ||
272 | |||
273 | public int getDataOffset(){ return returned; } | ||
274 | public int getBufferOffset(){ return fill; } | ||
275 | } | ||