FastLED 3.9.15
Loading...
Searching...
No Matches

◆ vorbis_search_for_page_pushdata()

static int32_t fl::third_party::vorbis::vorbis_search_for_page_pushdata ( vorb * f,
uint8 * data,
int32_t data_len )
static

Definition at line 4111 of file stb_vorbis.cpp.hpp.

4112{
4113 int32_t i,n;
4114 for (i=0; i < f->page_crc_tests; ++i)
4115 f->scan[i].bytes_done = 0;
4116
4117 // if we have room for more scans, search for them first, because
4118 // they may cause us to stop early if their header is incomplete
4120 if (data_len < 4) return 0;
4121 data_len -= 3; // need to look for 4-byte sequence, so don't miss
4122 // one that straddles a boundary
4123 for (i=0; i < data_len; ++i) {
4124 if (data[i] == 0x4f) {
4125 if (0==memcmp(data+i, ogg_page_header, 4)) {
4126 int32_t j,len;
4127 uint32 crc;
4128 // make sure we have the whole page header
4129 if (i+26 >= data_len || i+27+data[i+26] >= data_len) {
4130 // only read up to this page start, so hopefully we'll
4131 // have the whole page header start next time
4132 data_len = i;
4133 break;
4134 }
4135 // ok, we have it all; compute the length of the page
4136 len = 27 + data[i+26];
4137 for (j=0; j < data[i+26]; ++j)
4138 len += data[i+27+j];
4139 // scan everything up to the embedded crc (which we must 0)
4140 crc = 0;
4141 for (j=0; j < 22; ++j)
4142 crc = crc32_update(crc, data[i+j]);
4143 // now process 4 0-bytes
4144 for ( ; j < 26; ++j)
4145 crc = crc32_update(crc, 0);
4146 // len is the total number of bytes we need to scan
4147 n = f->page_crc_tests++;
4148 f->scan[n].bytes_left = len-j;
4149 f->scan[n].crc_so_far = crc;
4150 f->scan[n].goal_crc = data[i+22] + (data[i+23] << 8) + ((uint32)data[i+24]<<16) + ((uint32)data[i+25]<<24);
4151 // if the last frame on a page is continued to the next, then
4152 // we can't recover the sample_loc immediately
4153 if (data[i+27+data[i+26]-1] == 255)
4154 f->scan[n].sample_loc = ~0;
4155 else
4156 f->scan[n].sample_loc = data[i+6] + (data[i+7] << 8) + ((uint32)data[i+ 8]<<16) + ((uint32)data[i+ 9]<<24);
4157 f->scan[n].bytes_done = i+j;
4159 break;
4160 // keep going if we still have room for more
4161 }
4162 }
4163 }
4164 }
4165
4166 for (i=0; i < f->page_crc_tests;) {
4167 uint32 crc;
4168 int32_t j;
4169 int32_t n = f->scan[i].bytes_done;
4170 int32_t m = f->scan[i].bytes_left;
4171 if (m > data_len - n) m = data_len - n;
4172 // m is the bytes to scan in the current chunk
4173 crc = f->scan[i].crc_so_far;
4174 for (j=0; j < m; ++j)
4175 crc = crc32_update(crc, data[n+j]);
4176 f->scan[i].bytes_left -= m;
4177 f->scan[i].crc_so_far = crc;
4178 if (f->scan[i].bytes_left == 0) {
4179 // does it match?
4180 if (f->scan[i].crc_so_far == f->scan[i].goal_crc) {
4181 // Houston, we have page
4182 data_len = n+m; // consumption amount is wherever that scan ended
4183 f->page_crc_tests = -1; // drop out of page scan mode
4184 f->previous_length = 0; // decode-but-don't-output one frame
4185 f->next_seg = -1; // start a new page
4186 f->current_loc = f->scan[i].sample_loc; // set the current sample location
4187 // to the amount we'd have decoded had we decoded this page
4188 f->current_loc_valid = f->current_loc != ~0U;
4189 return data_len;
4190 }
4191 // delete entry
4192 f->scan[i] = f->scan[--f->page_crc_tests];
4193 } else {
4194 ++i;
4195 }
4196 }
4197
4198 return data_len;
4199}
static uint8 ogg_page_header[4]
int memcmp(const void *s1, const void *s2, size_t n) FL_NOEXCEPT
FL_ALWAYS_INLINE uint32 crc32_update(uint32 crc, uint8 byte) FL_NOEXCEPT
CRCscan scan[FL_STB_VORBIS_PUSHDATA_CRC_COUNT]
fl::i32 int32_t
Definition coder.h:220
#define FL_STB_VORBIS_PUSHDATA_CRC_COUNT

References crc32_update(), FL_NOEXCEPT, FL_STB_VORBIS_PUSHDATA_CRC_COUNT, memcmp(), and ogg_page_header.

Referenced by stb_vorbis_decode_frame_pushdata().

+ Here is the call graph for this function:
+ Here is the caller graph for this function: