// file: $isip/class/sp/FtrBuffer/ftrb_05.cc // version: $Id: // // isip include files // #include "FtrBuffer.h" // method: resetBuffer // // arguments: none // // return: a bool8 value indicating status // bool8 FtrBuffer::resetBuffer() { length_d.clear(Integral::RELEASE); Vector keys; hash_d.keys(keys); for (int32 i = keys.length() - 1; i >= 0; i--) { Vector< CircularBuffer >* cbuf = hash_d.get(keys(i)); if (cbuf == (Vector< CircularBuffer >*)NULL) { return Error::handle(name(), L"resetBuffer", Error::MEM, __FILE__, __LINE__); } cbuf->clear(Integral::RELEASE); // pull the CircularBuffer out of the HashTable and delete it // Vector< CircularBuffer >* cbuf0 = (Vector< CircularBuffer >*)NULL; hash_d.remove(keys(i), cbuf0); if (cbuf != cbuf0) { return Error::handle(name(), L"resetBuffer", Error::MEM, __FILE__, __LINE__); } delete cbuf; } // reset time index // frame_index_d = -1; last_index_d = -1; leftover_samps_d = 0; // exit gracefully // return true; } // method: addOrInitBuffer // // arguments: // const String& cname: (input) coefficient name // int32 num_chan: (input) number of channels // int32 buf_cap: (input) buffer capacity // // return: a bool8 value indicating status // // ensure that the named buffer exists. if it already exists, // reinitialize it. if it does not exist, add it. // bool8 FtrBuffer::addOrInitBuffer(const String& cname_a, int32 num_chan_a, int32 buf_cap_a) { // check arguments // if (num_chan_a < 1) { return Error::handle(name(), L"addOrInitBuffer", Error::ARG, __FILE__, __LINE__); } // if the coefficient is currently in the buffer hash, initialize // the buffer // if (hash_d.containsKey(cname_a)) { Vector< CircularBuffer >* ptr = &(getBuffer(cname_a)); // clear out the existing elements // int32 nc = ptr->length(); for (int32 i = 0; i < nc; i++) { (*ptr)(i).clear(Integral::RETAIN); } ptr->setLength(num_chan_a); // clear any new elements // for (int32 i = nc; i < num_chan_a; i++) { (*ptr)(i).clear(Integral::RETAIN); } // set the capacity // for (int32 i = 0; i < num_chan_a; i++) { (*ptr)(i).setCapacity(buf_cap_a); } } // if the coefficient is not currently in the buffer hash, add it // else { Vector< CircularBuffer >* ptr = new Vector< CircularBuffer >(num_chan_a); for (int32 i = 0; i < num_chan_a; i++) { (*ptr)(i).setCapacity(buf_cap_a); } hash_d.insert(cname_a, ptr); } // make sure the length hash also contains an entry for this // coefficient // if (!length_d.containsKey(cname_a)) { Long obj(-1); length_d.insert(cname_a, &obj); } else { length_d.get(cname_a)->assign((int32)-1); } // exit gracefully // return true; } // method: ensureChannels // // arguments: // const String& cname: (input) coefficient name // int32 num_chan: (input) number of channels // // return: a bool8 value indicating status // // ensure that the given buffer has the given channel capacity. if // there are not enough channels, increase the number of channels // within the buffer. // bool8 FtrBuffer::ensureChannels(const String& cname_a, int32 num_chan_a) { Vector< CircularBuffer >* ptr = &(getBuffer(cname_a)); if (ptr == (Vector< CircularBuffer >*)NULL) { return Error::handle(name(), L"ensureChannels", ERR, __FILE__, __LINE__); } int32 old_len = ptr->length(); if (old_len < num_chan_a) { // if we are increasing the number of channels, the old length // had better be 1 (i.e., not set before). // if (old_len != 1) { return Error::handle(name(), L"ensureChannels", ERR, __FILE__, __LINE__); } // add the additional channels we need // ptr->setLength(num_chan_a); for (int32 i = old_len; i < num_chan_a; i++) { (*ptr)(i).clear(Integral::RETAIN); } // set the capacity for each channel to what channel 0 has, // since channel 0's capacity was set in the // RecipePool::delayRecipe method. // int32 buf_cap = (*ptr)(0).getCapacity(); for (int32 i = 0; i < num_chan_a; i++) { (*ptr)(i).setCapacity(buf_cap); } } // exit gracefully // return true; } // method: ensureBufferTrailingPad // // arguments: // const String& cname: (input) coefficient name // int32 req_pad: (input) required trailing pad (in frames) // // return: a bool8 value indicating status // // make sure that the given buffer has the required number of trailing // frames. if enough frames do not currently exist, add them. // bool8 FtrBuffer::ensureBufferTrailingPad(const String& cname_a, int32 req_pad_a) { int32 nchan = getBuffer(cname_a).length(); AlgorithmData obj; obj.make(getBuffer(cname_a)(0)(0)); obj.clear(Integral::RETAIN); for (int32 i = 0; i < nchan; i++) { while (getBuffer(cname_a)(i).getNumBackward() < req_pad_a) { getBuffer(cname_a)(i).prepend(obj); } } // exit gracefully // return true; } // method: ensureBufferLeadingPad // // arguments: // const String& cname: (input) coefficient name // int32 req_pad: (input) required leading pad (in frames) // // return: a bool8 value indicating status // // make sure that the given buffer has the required number of leading // frames. if enough frames do not currently exist, add them. // bool8 FtrBuffer::ensureBufferLeadingPad(const String& cname_a, int32 req_pad_a) { int32 nchan = getBuffer(cname_a).length(); AlgorithmData obj; obj.make(getBuffer(cname_a)(0)(0)); obj.clear(Integral::RETAIN); for (int32 i = 0; i < nchan; i++) { while (getBuffer(cname_a)(i).getNumForward() < req_pad_a) { getBuffer(cname_a)(i).append(obj); } } // exit gracefully // return true; } // method: advanceRead // // arguments: none // // return: a bool8 value indicating status // // this method gets the frame duration // bool8 FtrBuffer::advanceRead() { Vector ckeys; length_d.keys(ckeys); for (int32 i = ckeys.length() - 1; i >= 0; i--) { Vector< CircularBuffer >* ptr = hash_d.get(ckeys(i)); int32 len = ptr->length(); int32 num = (int32)(*(length_d.get(ckeys(i)))); for (int32 c = 0; c < len; c++) { if ((*ptr)(c).getNumElements() > num) { (*ptr)(c).setRead(1); } } } // exit gracefully // return true; } // method: advanceCurr // // arguments: none // // return: a bool8 value indicating status // // this method gets the frame duration // bool8 FtrBuffer::advanceCurr() { if (getBuffer()(0).getNumElements() > 1) { Vector keys; hash_d.keys(keys); for (int32 i = keys.length() - 1; i >= 0; i--) { if ((*hash_d.get(keys(i)))(0).getNumForward() < 1) { keys(i).debug(L"end of coeff buffer"); printf("this has %d coeffs\n", (*hash_d.get(keys(i)))(0).getNumElements()); printf("this needs %d coeffs\n", (int32)(*length_d.get(keys(i)))); return Error::handle(name(), L"advanceCurr", ERR, __FILE__, __LINE__); } int32 nchan = hash_d.get(keys(i))->length(); for (int32 c = 0; c < nchan; c++) { (*hash_d.get(keys(i)))(c).seekCurr(1); } } } // advance the frame index pointer // frame_index_d += 1; // exit gracefully // return true; }