protected override void DoMergeWith(NVorbis.DataPacket continuation) { var op = continuation as Packet; if (op == null) throw new ArgumentException("Incorrect packet type!"); Length += continuation.Length; if (_mergedPacket == null) { _mergedPacket = op; } else { _mergedPacket.DoMergeWith(continuation); } // per the spec, a partial packet goes with the next page's granulepos. we'll go ahead and assign it to the next page as well PageGranulePosition = continuation.PageGranulePosition; PageSequenceNumber = continuation.PageSequenceNumber; }
internal int pack(NVorbis.Ogg.BBuffer opb) { int i; bool ordered = false; opb.Write(0x564342, 24); opb.Write(dim, 16); opb.Write(entries, 24); // pack the codewords. There are two packings; length ordered and // length random. Decide between the two now. for (i = 1; i < entries; i++) { if (lengthlist[i] < lengthlist[i - 1]) break; } if (i == entries) ordered = true; if (ordered) { // length ordered. We only need to say how many codewords of // each length. The actual codewords are generated // deterministically int count = 0; opb.Write(1, 1); // ordered opb.Write(lengthlist[0] - 1, 5); // 1 to 32 for (i = 1; i < entries; i++) { int _this = lengthlist[i]; int _last = lengthlist[i - 1]; if (_this > _last) { for (int j = _last; j < _this; j++) { opb.Write(i - count, Util.ilog(entries - count)); count = i; } } } opb.Write(i - count, Util.ilog(entries - count)); } else { // length random. Again, we don't code the codeword itself, just // the length. This time, though, we have to encode each length opb.Write(0, 1); // unordered // algortihmic mapping has use for 'unused entries', which we tag // here. The algorithmic mapping happens as usual, but the unused // entry has no codeword. for (i = 0; i < entries; i++) { if (lengthlist[i] == 0) break; } if (i == entries) { opb.Write(0, 1); // no unused entries for (i = 0; i < entries; i++) { opb.Write(lengthlist[i] - 1, 5); } } else { opb.Write(1, 1); // we have unused entries; thus we tag for (i = 0; i < entries; i++) { if (lengthlist[i] == 0) { opb.Write(0, 1); } else { opb.Write(1, 1); opb.Write(lengthlist[i] - 1, 5); } } } } // is the entry number the desired return value, or do we have a // mapping? If we have a mapping, what type? opb.Write(maptype, 4); switch (maptype) { case 0: // no mapping break; case 1: case 2: // implicitly populated value mapping // explicitly populated value mapping if (quantlist == null) { // no quantlist? error return (-1); } // values that define the dequantization opb.Write(q_min, 32); opb.Write(q_delta, 32); opb.Write(q_quant - 1, 4); opb.Write(q_sequencep, 1); { int quantvals = 0; switch (maptype) { case 1: // a single column of (c->entries/c->dim) quantized values for // building a full value list algorithmically (square lattice) quantvals = maptype1_quantvals(); break; case 2: // every value (c->entries*c->dim total) specified explicitly quantvals = entries * dim; break; } // quantized values for (i = 0; i < quantvals; i++) { opb.Write(Math.Abs(quantlist[i]), q_quant); } } break; default: // error case; we don't have any other map types now return (-1); } return (0); }
internal override void pack(Info vi, Object imap, NVorbis.Ogg.BBuffer opb) { InfoMapping0 info = (InfoMapping0)imap; /* another 'we meant to do it this way' hack... up to beta 4, we packed 4 binary zeros here to signify one submapping in use. We now redefine that to mean four bitflags that indicate use of deeper features; bit0:submappings, bit1:coupling, bit2,3:reserved. This is backward compatable with all actual uses of the beta code. */ if (info.submaps > 1) { opb.Write(1, 1); opb.Write(info.submaps - 1, 4); } else { opb.Write(0, 1); } if (info.coupling_steps > 0) { opb.Write(1, 1); opb.Write(info.coupling_steps - 1, 8); for (int i = 0; i < info.coupling_steps; i++) { opb.Write(info.coupling_mag[i], Util.ilog2(vi.Channels)); opb.Write(info.coupling_ang[i], Util.ilog2(vi.Channels)); } } else { opb.Write(0, 1); } opb.Write(0, 2); /* 2,3:reserved */ /* we don't write the channel submappings if we only have one... */ if (info.submaps > 1) { for (int i = 0; i < vi.Channels; i++) opb.Write(info.chmuxlist[i], 4); } for (int i = 0; i < info.submaps; i++) { opb.Write(info.timesubmap[i], 8); opb.Write(info.floorsubmap[i], 8); opb.Write(info.residuesubmap[i], 8); } }
internal abstract void pack(Object vr, NVorbis.Ogg.BBuffer opb);
internal int unpack(NVorbis.Ogg.BBuffer opb) { int vendorlen = opb.Read(32); if (vendorlen < 0) { Clear(); return (-1); } vendor = new byte[vendorlen + 1]; opb.Read(vendor, vendorlen); comments = opb.Read(32); if (comments < 0) { Clear(); return (-1); } user_comments = new byte[comments + 1][]; comment_lengths = new int[comments + 1]; for (int i = 0; i < comments; i++) { int len = opb.Read(32); if (len < 0) { Clear(); return (-1); } comment_lengths[i] = len; user_comments[i] = new byte[len + 1]; opb.Read(user_comments[i], len); } if (opb.Read(1) != 1) { Clear(); return (-1); } return (0); }
public int HeaderOut(NVorbis.Ogg.Packet op) { NVorbis.Ogg.BBuffer opb = new NVorbis.Ogg.BBuffer(); opb.WriteInit(); if (Pack(opb) != 0) return OV_EIMPL; op.packet_base = new byte[opb.bytes()]; op.packet = 0; op.bytes = opb.bytes(); Array.Copy(opb.buffer(), 0, op.packet_base, 0, op.bytes); op.b_o_s = 0; op.e_o_s = 0; op.granulepos = 0; return 0; }
/// <summary> /// All of the real encoding details are here. The modes, books, everything. /// </summary> /// <param name="Buffer"></param> /// <returns></returns> int UnpackBooks(NVorbis.Ogg.BBuffer Buffer) { Books = Buffer.Read(8) + 1; if (BookParam == null || BookParam.Length != Books) BookParam = new StaticCodeBook[Books]; for (int i = 0; i < Books; i++) { BookParam[i] = new StaticCodeBook(); if (BookParam[i].unpack(Buffer) != 0) { Clear(); return (-1); } } // time backend settings Times = Buffer.Read(6) + 1; if (TimeType == null || TimeType.Length != Times) TimeType = new int[Times]; if (TimeParam == null || TimeParam.Length != Times) TimeParam = new Object[Times]; for (int i = 0; i < Times; i++) { TimeType[i] = Buffer.Read(16); if (TimeType[i] < 0 || TimeType[i] >= VI_TIMEB) { Clear(); return (-1); } TimeParam[i] = FuncTime.time_P[TimeType[i]].unpack(this, Buffer); if (TimeParam[i] == null) { Clear(); return (-1); } } // floor backend settings floors = Buffer.Read(6) + 1; if (FloorType == null || FloorType.Length != floors) FloorType = new int[floors]; if (FloorParam == null || FloorParam.Length != floors) FloorParam = new Object[floors]; for (int i = 0; i < floors; i++) { FloorType[i] = Buffer.Read(16); if (FloorType[i] < 0 || FloorType[i] >= VI_FLOORB) { Clear(); return (-1); } FloorParam[i] = FuncFloor.floor_P[FloorType[i]].unpack(this, Buffer); if (FloorParam[i] == null) { Clear(); return (-1); } } // residue backend settings residues = Buffer.Read(6) + 1; if (residue_type == null || residue_type.Length != residues) residue_type = new int[residues]; if (ResidueParam == null || ResidueParam.Length != residues) ResidueParam = new Object[residues]; for (int i = 0; i < residues; i++) { residue_type[i] = Buffer.Read(16); if (residue_type[i] < 0 || residue_type[i] >= VI_RESB) { Clear(); return (-1); } ResidueParam[i] = FuncResidue.residue_P[residue_type[i]].unpack(this, Buffer); if (ResidueParam[i] == null) { Clear(); return (-1); } } // map backend settings maps = Buffer.Read(6) + 1; if (map_type == null || map_type.Length != maps) map_type = new int[maps]; if (MapParam == null || MapParam.Length != maps) MapParam = new Object[maps]; for (int i = 0; i < maps; i++) { map_type[i] = Buffer.Read(16); if (map_type[i] < 0 || map_type[i] >= VI_MAPB) { Clear(); return (-1); } MapParam[i] = FuncMapping.mapping_P[map_type[i]].unpack(this, Buffer); if (MapParam[i] == null) { Clear(); return (-1); } } // mode settings Modes = Buffer.Read(6) + 1; if (ModeParam == null || ModeParam.Length != Modes) ModeParam = new InfoMode[Modes]; for (int i = 0; i < Modes; i++) { ModeParam[i] = new InfoMode(); ModeParam[i].blockflag = Buffer.Read(1); ModeParam[i].windowtype = Buffer.Read(16); ModeParam[i].transformtype = Buffer.Read(16); ModeParam[i].mapping = Buffer.Read(8); if ((ModeParam[i].windowtype >= VI_WINDOWB) || (ModeParam[i].transformtype >= VI_WINDOWB) || (ModeParam[i].mapping >= maps)) { Clear(); return (-1); } } if (Buffer.Read(1) != 1) { Clear(); return (-1); } return (0); }
int PackBooks(NVorbis.Ogg.BBuffer Buffer) { Buffer.Write(0x05, 8); Buffer.Write(_vorbis); // books Buffer.Write(Books - 1, 8); for (int i = 0; i < Books; i++) { if (BookParam[i].pack(Buffer) != 0) { //goto err_out; return (-1); } } // times Buffer.Write(Times - 1, 6); for (int i = 0; i < Times; i++) { Buffer.Write(TimeType[i], 16); FuncTime.time_P[TimeType[i]].pack(this.TimeParam[i], Buffer); } // floors Buffer.Write(floors - 1, 6); for (int i = 0; i < floors; i++) { Buffer.Write(FloorType[i], 16); FuncFloor.floor_P[FloorType[i]].pack(FloorParam[i], Buffer); } // residues Buffer.Write(residues - 1, 6); for (int i = 0; i < residues; i++) { Buffer.Write(residue_type[i], 16); FuncResidue.residue_P[residue_type[i]].pack(ResidueParam[i], Buffer); } // maps Buffer.Write(maps - 1, 6); for (int i = 0; i < maps; i++) { Buffer.Write(map_type[i], 16); FuncMapping.mapping_P[map_type[i]].pack(this, MapParam[i], Buffer); } // modes Buffer.Write(Modes - 1, 6); for (int i = 0; i < Modes; i++) { Buffer.Write(ModeParam[i].blockflag, 1); Buffer.Write(ModeParam[i].windowtype, 16); Buffer.Write(ModeParam[i].transformtype, 16); Buffer.Write(ModeParam[i].mapping, 8); } Buffer.Write(1, 1); return (0); }
internal override void pack(Object i, NVorbis.Ogg.BBuffer opb) { }
internal override Object unpack(Info vi, NVorbis.Ogg.BBuffer opb) { int count = 0, maxclass = -1, rangebits; InfoFloor1 info = new InfoFloor1(); /* read partitions */ info.Partitions = opb.Read(5); /* only 0 to 31 legal */ for (int j = 0; j < info.Partitions; j++) { info.Partitionclass[j] = opb.Read(4); /* only 0 to 15 legal */ if (maxclass < info.Partitionclass[j]) maxclass = info.Partitionclass[j]; } /* read partition classes */ for (int j = 0; j < maxclass + 1; j++) { info.class_dim[j] = opb.Read(3) + 1; /* 1 to 8 */ info.class_subs[j] = opb.Read(2); /* 0,1,2,3 bits */ if (info.class_subs[j] < 0) { info.free(); return (null); } if (info.class_subs[j] != 0) { info.class_book[j] = opb.Read(8); } if (info.class_book[j] < 0 || info.class_book[j] >= vi.Books) { info.free(); return (null); } for (int k = 0; k < (1 << info.class_subs[j]); k++) { info.class_subbook[j][k] = opb.Read(8) - 1; if (info.class_subbook[j][k] < -1 || info.class_subbook[j][k] >= vi.Books) { info.free(); return (null); } } } /* read the post list */ info.mult = opb.Read(2) + 1; /* only 1,2,3,4 legal now */ rangebits = opb.Read(4); for (int j = 0, k = 0; j < info.Partitions; j++) { count += info.class_dim[info.Partitionclass[j]]; for (; k < count; k++) { int t = info.postlist[k + 2] = opb.Read(rangebits); if (t < 0 || t >= (1 << rangebits)) { info.free(); return (null); } } } info.postlist[0] = 0; info.postlist[1] = 1 << rangebits; return (info); }
internal override void pack(Object i, NVorbis.Ogg.BBuffer opb) { InfoFloor1 info = (InfoFloor1)i; int count = 0; int rangebits; int maxposit = info.postlist[1]; int maxclass = -1; /* save out partitions */ opb.Write(info.Partitions, 5); /* only 0 to 31 legal */ for (int j = 0; j < info.Partitions; j++) { opb.Write(info.Partitionclass[j], 4); /* only 0 to 15 legal */ if (maxclass < info.Partitionclass[j]) maxclass = info.Partitionclass[j]; } /* save out partition classes */ for (int j = 0; j < maxclass + 1; j++) { opb.Write(info.class_dim[j] - 1, 3); /* 1 to 8 */ opb.Write(info.class_subs[j], 2); /* 0 to 3 */ if (info.class_subs[j] != 0) { opb.Write(info.class_book[j], 8); } for (int k = 0; k < (1 << info.class_subs[j]); k++) { opb.Write(info.class_subbook[j][k] + 1, 8); } } /* save out the post list */ opb.Write(info.mult - 1, 2); /* only 1,2,3,4 legal now */ opb.Write(Util.ilog2(maxposit), 4); rangebits = Util.ilog2(maxposit); for (int j = 0, k = 0; j < info.Partitions; j++) { count += info.class_dim[info.Partitionclass[j]]; for (; k < count; k++) { opb.Write(info.postlist[k + 2], rangebits); } } }
internal override Object unpack(Info vi, NVorbis.Ogg.BBuffer opb) { InfoFloor0 info = new InfoFloor0(); info.order = opb.Read(8); info.rate = opb.Read(16); info.barkmap = opb.Read(16); info.ampbits = opb.Read(6); info.ampdB = opb.Read(8); info.numbooks = opb.Read(4) + 1; if ((info.order < 1) || (info.rate < 1) || (info.barkmap < 1) || (info.numbooks < 1)) { return (null); } for (int j = 0; j < info.numbooks; j++) { info.books[j] = opb.Read(8); if (info.books[j] < 0 || info.books[j] >= vi.Books) { return (null); } } return (info); }
internal override void pack(Object i, NVorbis.Ogg.BBuffer opb) { InfoFloor0 info = (InfoFloor0)i; opb.Write(info.order, 8); opb.Write(info.rate, 16); opb.Write(info.barkmap, 16); opb.Write(info.ampbits, 6); opb.Write(info.ampdB, 8); opb.Write(info.numbooks - 1, 4); for (int j = 0; j < info.numbooks; j++) opb.Write(info.books[j], 8); }
internal abstract Object unpack(Info info, NVorbis.Ogg.BBuffer buffer);
internal abstract void pack(Info info, Object imap, NVorbis.Ogg.BBuffer buffer);
internal override void pack(Object vr, NVorbis.Ogg.BBuffer opb) { InfoResidue0 info = (InfoResidue0)vr; int acc = 0; opb.Write(info.begin, 24); opb.Write(info.end, 24); opb.Write(info.grouping - 1, 24); /* residue vectors to group and code with a partitioned book */ opb.Write(info.partitions - 1, 6); /* possible partition choices */ opb.Write(info.groupbook, 8); /* group huffman book */ /* secondstages is a bitmask; as encoding progresses pass by pass, a bitmask of one indicates this partition class has bits to write this pass */ for (int j = 0; j < info.partitions; j++) { int i = info.secondstages[j]; if (Util.ilog(i) > 3) { /* yes, this is a minor hack due to not thinking ahead */ opb.Write(i, 3); opb.Write(1, 1); opb.Write((int)(((uint)i) >> 3), 5); } else { opb.Write(i, 4); /* trailing zero */ } acc += Util.icount(i); } for (int j = 0; j < acc; j++) { opb.Write(info.booklist[j], 8); } }
internal override Object unpack(Info vi, NVorbis.Ogg.BBuffer opb) { int acc = 0; InfoResidue0 info = new InfoResidue0(); info.begin = opb.Read(24); info.end = opb.Read(24); info.grouping = opb.Read(24) + 1; info.partitions = opb.Read(6) + 1; info.groupbook = opb.Read(8); for (int j = 0; j < info.partitions; j++) { int cascade = opb.Read(3); if (opb.Read(1) != 0) { cascade |= (opb.Read(5) << 3); } info.secondstages[j] = cascade; acc += Util.icount(cascade); } for (int j = 0; j < acc; j++) { info.booklist[j] = opb.Read(8); } if (info.groupbook >= vi.Books) { free_info(info); return (null); } for (int j = 0; j < acc; j++) { if (info.booklist[j] >= vi.Books) { free_info(info); return (null); } } return (info); }
internal override Object unpack(Info vi, NVorbis.Ogg.BBuffer opb) { return ""; }
// pack side int PackInfo(NVorbis.Ogg.BBuffer Buffer) { // preamble Buffer.Write(0x01, 8); Buffer.Write(_vorbis); // basic information about the stream Buffer.Write(0x00, 32); Buffer.Write(Channels, 8); Buffer.Write(Rate, 32); Buffer.Write(bitrate_upper, 32); Buffer.Write(bitrate_nominal, 32); Buffer.Write(bitrate_lower, 32); Buffer.Write(Util.ilog2(blocksizes[0]), 4); Buffer.Write(Util.ilog2(blocksizes[1]), 4); Buffer.Write(1, 1); return (0); }
// Decode side is specced and easier, because we don't need to find // matches using different criteria; we simply read and map. There are // two things we need to do 'depending': // // We may need to support interleave. We don't really, but it's // convenient to do it here rather than rebuild the vector later. // // Cascades may be additive or multiplicitive; this is not inherent in // the codebook, but set in the code using the codebook. Like // interleaving, it's easiest to do it here. // stage==0 -> declarative (set the value) // stage==1 -> additive // stage==2 -> multiplicitive // returns the entry number or -1 on eof internal int decode(NVorbis.Ogg.BBuffer b) { int ptr = 0; DecodeAux t = decode_tree; int lok = b.Look(t.tabn); if (lok >= 0) { ptr = t.tab[lok]; b.adv(t.tabl[lok]); if (ptr <= 0) { return -ptr; } } do { switch (b.Read1()) { case 0: ptr = t.ptr0[ptr]; break; case 1: ptr = t.ptr1[ptr]; break; case -1: default: return (-1); } } while (ptr > 0); return (-ptr); }
/// <summary> /// Header packing/unpacking /// </summary> /// <param name="Buffer"></param> /// <returns></returns> int UnpackInfo(NVorbis.Ogg.BBuffer Buffer) { version = Buffer.Read(32); if (version != 0) return (-1); Channels = Buffer.Read(8); Rate = Buffer.Read(32); bitrate_upper = Buffer.Read(32); bitrate_nominal = Buffer.Read(32); bitrate_lower = Buffer.Read(32); blocksizes[0] = 1 << Buffer.Read(4); blocksizes[1] = 1 << Buffer.Read(4); if ((Rate < 1) || (Channels < 1) || (blocksizes[0] < 8) || (blocksizes[1] < blocksizes[0]) || (Buffer.Read(1) != 1)) { Clear(); return (-1); } return (0); }
// returns the entry number or -1 on eof internal int decodevs(float[] a, int index, NVorbis.Ogg.BBuffer b, int step, int addmul) { int entry = decode(b); if (entry == -1) return (-1); switch (addmul) { case -1: for (int i = 0, o = 0; i < dim; i++, o += step) a[index + o] = valuelist[entry * dim + i]; break; case 0: for (int i = 0, o = 0; i < dim; i++, o += step) a[index + o] += valuelist[entry * dim + i]; break; case 1: for (int i = 0, o = 0; i < dim; i++, o += step) a[index + o] *= valuelist[entry * dim + i]; break; default: //System.err.println("CodeBook.decodeves: addmul="+addmul); break; } return (entry); }
internal int Pack(NVorbis.Ogg.BBuffer Buffer) { // preamble Buffer.Write(0x03, 8); Buffer.Write(_vorbis); // vendor Buffer.Write(_vendor.Length, 32); Buffer.Write(_vendor); // comments Buffer.Write(comments, 32); if (comments != 0) { for (int i = 0; i < comments; i++) { if (user_comments[i] != null) { Buffer.Write(comment_lengths[i], 32); Buffer.Write(user_comments[i]); } else { Buffer.Write(0, 32); } } } Buffer.Write(1, 1); return (0); }
internal int decodevs_add(float[] a, int offset, NVorbis.Ogg.BBuffer b, int n) { lock (this) { int step = n / dim; int entry; int i, j, o; if (t.Length < step) { t = new int[step]; } for (i = 0; i < step; i++) { entry = decode(b); if (entry == -1) return (-1); t[i] = entry * dim; } for (i = 0, o = 0; i < dim; i++, o += step) { for (j = 0; j < step; j++) { a[offset + o + j] += valuelist[t[j] + i]; } } return (0); } }
internal int decodevv_add(float[][] a, int offset, int ch, NVorbis.Ogg.BBuffer b, int n) { int i, j, entry; int chptr = 0; for (i = offset / ch; i < (offset + n) / ch; ) { entry = decode(b); if (entry == -1) return (-1); int t = entry * dim; for (j = 0; j < dim; j++) { a[chptr++][i] += valuelist[t + j]; if (chptr == ch) { chptr = 0; i++; } } } return (0); }
internal int decodev_add(float[] a, int offset, NVorbis.Ogg.BBuffer b, int n) { int i, j, entry; int t; if (dim > 8) { for (i = 0; i < n; ) { entry = decode(b); if (entry == -1) return (-1); t = entry * dim; for (j = 0; j < dim; ) { a[offset + (i++)] += valuelist[t + (j++)]; } } } else { for (i = 0; i < n; ) { entry = decode(b); if (entry == -1) return (-1); t = entry * dim; j = 0; switch (dim) { case 8: a[offset + (i++)] += valuelist[t + (j++)]; goto case 7; case 7: a[offset + (i++)] += valuelist[t + (j++)]; goto case 6; case 6: a[offset + (i++)] += valuelist[t + (j++)]; goto case 5; case 5: a[offset + (i++)] += valuelist[t + (j++)]; goto case 4; case 4: a[offset + (i++)] += valuelist[t + (j++)]; goto case 3; case 3: a[offset + (i++)] += valuelist[t + (j++)]; goto case 2; case 2: a[offset + (i++)] += valuelist[t + (j++)]; goto case 1; case 1: a[offset + (i++)] += valuelist[t + (j++)]; goto case 0; case 0: break; } } } return (0); }
internal abstract Object unpack(Info vi, NVorbis.Ogg.BBuffer opb);
internal int decodev_set(float[] a, int offset, NVorbis.Ogg.BBuffer b, int n) { int i, j, entry; int t; for (i = 0; i < n; ) { entry = decode(b); if (entry == -1) return (-1); t = entry * dim; for (j = 0; j < dim; ) { a[offset + i++] = valuelist[t + (j++)]; } } return (0); }
// also responsible for range checking internal override Object unpack(Info vi, NVorbis.Ogg.BBuffer opb) { InfoMapping0 info = new InfoMapping0(); if (opb.Read(1) != 0) { info.submaps = opb.Read(4) + 1; } else { info.submaps = 1; } if (opb.Read(1) != 0) { info.coupling_steps = opb.Read(8) + 1; for (int i = 0; i < info.coupling_steps; i++) { int testM = info.coupling_mag[i] = opb.Read(Util.ilog2(vi.Channels)); int testA = info.coupling_ang[i] = opb.Read(Util.ilog2(vi.Channels)); if (testM < 0 || testA < 0 || testM == testA || testM >= vi.Channels || testA >= vi.Channels) { //goto err_out; info.free(); return (null); } } } if (opb.Read(2) > 0) { /* 2,3:reserved */ info.free(); return (null); } if (info.submaps > 1) { for (int i = 0; i < vi.Channels; i++) { info.chmuxlist[i] = opb.Read(4); if (info.chmuxlist[i] >= info.submaps) { info.free(); return (null); } } } for (int i = 0; i < info.submaps; i++) { info.timesubmap[i] = opb.Read(8); if (info.timesubmap[i] >= vi.Times) { info.free(); return (null); } info.floorsubmap[i] = opb.Read(8); if (info.floorsubmap[i] >= vi.floors) { info.free(); return (null); } info.residuesubmap[i] = opb.Read(8); if (info.residuesubmap[i] >= vi.residues) { info.free(); return (null); } } return info; }
// unpacks a codebook from the packet buffer into the codebook struct, // readies the codebook auxiliary structures for decode internal int unpack(NVorbis.Ogg.BBuffer opb) { int i; //memset(s,0,sizeof(static_codebook)); // make sure alignment is correct if (opb.Read(24) != 0x564342) { // goto _eofout; clear(); return (-1); } // first the basic parameters dim = opb.Read(16); entries = opb.Read(24); if (entries == -1) { // goto _eofout; clear(); return (-1); } // codeword ordering.... length ordered or unordered? switch (opb.Read(1)) { case 0: // unordered lengthlist = new int[entries]; // allocated but unused entries? if (opb.Read(1) != 0) { // yes, unused entries for (i = 0; i < entries; i++) { if (opb.Read(1) != 0) { int num = opb.Read(5); if (num == -1) { // goto _eofout; clear(); return (-1); } lengthlist[i] = num + 1; } else { lengthlist[i] = 0; } } } else { // all entries used; no tagging for (i = 0; i < entries; i++) { int num = opb.Read(5); if (num == -1) { // goto _eofout; clear(); return (-1); } lengthlist[i] = num + 1; } } break; case 1: // ordered { int length = opb.Read(5) + 1; lengthlist = new int[entries]; for (i = 0; i < entries; ) { int num = opb.Read(Util.ilog(entries - i)); if (num == -1) { // goto _eofout; clear(); return (-1); } for (int j = 0; j < num; j++, i++) { lengthlist[i] = length; } length++; } } break; default: // EOF return (-1); } // Do we have a mapping to unpack? switch ((maptype = opb.Read(4))) { case 0: // no mapping break; case 1: case 2: // implicitly populated value mapping // explicitly populated value mapping q_min = opb.Read(32); q_delta = opb.Read(32); q_quant = opb.Read(4) + 1; q_sequencep = opb.Read(1); { int quantvals = 0; switch (maptype) { case 1: quantvals = maptype1_quantvals(); break; case 2: quantvals = entries * dim; break; } // quantized values quantlist = new int[quantvals]; for (i = 0; i < quantvals; i++) { quantlist[i] = opb.Read(q_quant); } if (quantlist[quantvals - 1] == -1) { // goto _eofout; clear(); return (-1); } } break; default: // goto _eofout; clear(); return (-1); } // all set return (0); // _errout: // _eofout: // vorbis_staticbook_clear(s); // return(-1); }