00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include "StreamParser.hh"
00022
00023 #include <string.h>
00024 #include <stdlib.h>
00025
00026 #define BANK_SIZE 150000
00027
00028 StreamParser::StreamParser(FramedSource* inputSource,
00029 FramedSource::onCloseFunc* onInputCloseFunc,
00030 void* onInputCloseClientData,
00031 clientContinueFunc* clientContinueFunc,
00032 void* clientContinueClientData)
00033 : fInputSource(inputSource), fOnInputCloseFunc(onInputCloseFunc),
00034 fOnInputCloseClientData(onInputCloseClientData),
00035 fClientContinueFunc(clientContinueFunc),
00036 fClientContinueClientData(clientContinueClientData),
00037 fSavedParserIndex(0), fSavedRemainingUnparsedBits(0),
00038 fCurParserIndex(0), fRemainingUnparsedBits(0),
00039 fTotNumValidBytes(0) {
00040 fBank[0] = new unsigned char[BANK_SIZE];
00041 fBank[1] = new unsigned char[BANK_SIZE];
00042 fCurBankNum = 0;
00043 fCurBank = fBank[fCurBankNum];
00044 }
00045
00046 StreamParser::~StreamParser() {
00047 delete[] fBank[0]; delete[] fBank[1];
00048 }
00049
00050 #define NO_MORE_BUFFERED_INPUT 1
00051
00052 void StreamParser::ensureValidBytes1(unsigned numBytesNeeded) {
00053
00054
00055 unsigned maxInputFrameSize = fInputSource->maxFrameSize();
00056 if (maxInputFrameSize > numBytesNeeded) numBytesNeeded = maxInputFrameSize;
00057
00058
00059
00060 if (fCurParserIndex + numBytesNeeded > BANK_SIZE) {
00061
00062 unsigned numBytesToSave = fTotNumValidBytes - fSavedParserIndex;
00063 unsigned char const* from = &curBank()[fSavedParserIndex];
00064
00065 fCurBankNum = (fCurBankNum + 1)%2;
00066 fCurBank = fBank[fCurBankNum];
00067 memmove(curBank(), from, numBytesToSave);
00068 fCurParserIndex = fCurParserIndex - fSavedParserIndex;
00069 fSavedParserIndex = 0;
00070 fTotNumValidBytes = numBytesToSave;
00071 }
00072
00073
00074
00075 if (fCurParserIndex + numBytesNeeded > BANK_SIZE) {
00076
00077
00078 fInputSource->envir() << "StreamParser internal error ("
00079 << fCurParserIndex << "+ "
00080 << numBytesNeeded << " > "
00081 << BANK_SIZE << ")\n";
00082 exit(1);
00083 }
00084
00085
00086 unsigned maxNumBytesToRead = BANK_SIZE - fTotNumValidBytes;
00087 fInputSource->getNextFrame(&curBank()[fTotNumValidBytes],
00088 maxNumBytesToRead,
00089 afterGettingBytes, this,
00090 fOnInputCloseFunc, fOnInputCloseClientData);
00091
00092 throw NO_MORE_BUFFERED_INPUT;
00093 }
00094
00095 void StreamParser::afterGettingBytes(void* clientData,
00096 unsigned numBytesRead,
00097 unsigned ,
00098 struct timeval presentationTime,
00099 unsigned ){
00100 StreamParser* buffer = (StreamParser*)clientData;
00101
00102
00103 if (buffer->fTotNumValidBytes + numBytesRead > BANK_SIZE) {
00104 buffer->fInputSource->envir()
00105 << "StreamParser::afterGettingBytes() warning: read "
00106 << numBytesRead << " bytes; expected no more than "
00107 << BANK_SIZE - buffer->fTotNumValidBytes << "\n";
00108 }
00109
00110 unsigned char* ptr = &buffer->curBank()[buffer->fTotNumValidBytes];
00111 buffer->fTotNumValidBytes += numBytesRead;
00112
00113
00114 buffer->restoreSavedParserState();
00115
00116
00117 buffer->fClientContinueFunc(buffer->fClientContinueClientData,
00118 ptr, numBytesRead, presentationTime);
00119 }
00120
00121 void StreamParser::saveParserState() {
00122 fSavedParserIndex = fCurParserIndex;
00123 fSavedRemainingUnparsedBits = fRemainingUnparsedBits;
00124 }
00125
00126 void StreamParser::restoreSavedParserState() {
00127 fCurParserIndex = fSavedParserIndex;
00128 fRemainingUnparsedBits = fSavedRemainingUnparsedBits;
00129 }
00130
00131 void StreamParser::skipBits(unsigned numBits) {
00132 if (numBits <= fRemainingUnparsedBits) {
00133 fRemainingUnparsedBits -= numBits;
00134 } else {
00135 numBits -= fRemainingUnparsedBits;
00136
00137 unsigned numBytesToExamine = (numBits+7)/8;
00138 ensureValidBytes(numBytesToExamine);
00139 fCurParserIndex += numBytesToExamine;
00140
00141 fRemainingUnparsedBits = 8*numBytesToExamine - numBits;
00142 }
00143 }
00144
00145 unsigned StreamParser::getBits(unsigned numBits) {
00146 if (numBits <= fRemainingUnparsedBits) {
00147 unsigned char lastByte = *lastParsed();
00148 lastByte >>= (fRemainingUnparsedBits - numBits);
00149 fRemainingUnparsedBits -= numBits;
00150
00151 return (unsigned)lastByte &~ ((~0)<<numBits);
00152 } else {
00153 unsigned char lastByte;
00154 if (fRemainingUnparsedBits > 0) {
00155 lastByte = *lastParsed();
00156 } else {
00157 lastByte = 0;
00158 }
00159
00160 unsigned remainingBits = numBits - fRemainingUnparsedBits;
00161
00162
00163
00164 unsigned result = test4Bytes();
00165
00166 result >>= (32 - remainingBits);
00167 result |= (lastByte << remainingBits);
00168 if (numBits < 32) result &=~ ((~0)<<numBits);
00169
00170 unsigned const numRemainingBytes = (remainingBits+7)/8;
00171 fCurParserIndex += numRemainingBytes;
00172 fRemainingUnparsedBits = 8*numRemainingBytes - remainingBits;
00173
00174 return result;
00175 }
00176 }
00177
00178 void StreamParser::flushInput() {
00179 fCurParserIndex = fSavedParserIndex = 0;
00180 fSavedRemainingUnparsedBits = fRemainingUnparsedBits = 0;
00181 fTotNumValidBytes = 0;
00182 }