/**********
This library is free software; you can redistribute it and/or modify it under
the terms of the GNU Lesser General Public License as published by the
Free Software Foundation; either version 3 of the License, or (at your
option) any later version. (See <http://www.gnu.org/copyleft/lesser.html>.)

This library is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public License for
more details.

You should have received a copy of the GNU Lesser General Public License
along with this library; if not, write to the Free Software Foundation, Inc.,
51 Franklin Street, Fifth Floor, Boston, MA 02110-1301  USA
**********/
// "liveMedia"
// Copyright (c) 1996-2020 Live Networks, Inc.  All rights reserved.
// Abstract class for parsing a byte stream
// C++ header

#ifndef _STREAM_PARSER_HH
#define _STREAM_PARSER_HH

#ifndef _FRAMED_SOURCE_HH
#include "FramedSource.hh"
#endif

class StreamParser {
public:
  virtual void flushInput();

protected: // we're a virtual base class
  typedef void (clientContinueFunc)(void* clientData,
				    unsigned char* ptr, unsigned size,
				    struct timeval presentationTime);
  StreamParser(FramedSource* inputSource,
	       FramedSource::onCloseFunc* onInputCloseFunc,
	       void* onInputCloseClientData,
	       clientContinueFunc* clientContinueFunc,
	       void* clientContinueClientData);
  virtual ~StreamParser();

  void saveParserState();
  virtual void restoreSavedParserState();

  u_int32_t get4Bytes() { // byte-aligned; returned in big-endian order
    u_int32_t result = test4Bytes();
    fCurParserIndex += 4;
    fRemainingUnparsedBits = 0;

    return result;
  }
  u_int32_t test4Bytes() { // as above, but doesn't advance ptr
    ensureValidBytes(4);

    unsigned char const* ptr = nextToParse();
    return (ptr[0]<<24)|(ptr[1]<<16)|(ptr[2]<<8)|ptr[3];
  }

  u_int16_t get2Bytes() {
    ensureValidBytes(2);

    unsigned char const* ptr = nextToParse();
    u_int16_t result = (ptr[0]<<8)|ptr[1];

    fCurParserIndex += 2;
    fRemainingUnparsedBits = 0;

    return result;
  }
  u_int16_t test2Bytes() {
    ensureValidBytes(2);

    unsigned char const* ptr = nextToParse();
    return (ptr[0]<<8)|ptr[1];
  }


  u_int8_t get1Byte() { // byte-aligned
    ensureValidBytes(1);
    fRemainingUnparsedBits = 0;
    return curBank()[fCurParserIndex++];
  }
  u_int8_t test1Byte() { // as above, but doesn't advance ptr
    ensureValidBytes(1);
    return nextToParse()[0];
  }

  void getBytes(u_int8_t* to, unsigned numBytes) {
    testBytes(to, numBytes);
    fCurParserIndex += numBytes;
    fRemainingUnparsedBits = 0;
  }
  void testBytes(u_int8_t* to, unsigned numBytes) { // as above, but doesn't advance ptr
    ensureValidBytes(numBytes);
    memmove(to, nextToParse(), numBytes);
  }
  void skipBytes(unsigned numBytes) {
    ensureValidBytes(numBytes);
    fCurParserIndex += numBytes;
  }

  void skipBits(unsigned numBits);
  unsigned getBits(unsigned numBits);
      // numBits <= 32; returns data into low-order bits of result

  unsigned curOffset() const { return fCurParserIndex; }

  unsigned& totNumValidBytes() { return fTotNumValidBytes; }

  Boolean haveSeenEOF() const { return fHaveSeenEOF; }

  unsigned bankSize() const;

private:
  unsigned char* curBank() { return fCurBank; }
  unsigned char* nextToParse() { return &curBank()[fCurParserIndex]; }
  unsigned char* lastParsed() { return &curBank()[fCurParserIndex-1]; }

  // makes sure that at least "numBytes" valid bytes remain:
  void ensureValidBytes(unsigned numBytesNeeded) {
    // common case: inlined:
    if (fCurParserIndex + numBytesNeeded <= fTotNumValidBytes) return;

    ensureValidBytes1(numBytesNeeded);
  }
  void ensureValidBytes1(unsigned numBytesNeeded);

  static void afterGettingBytes(void* clientData, unsigned numBytesRead,
				unsigned numTruncatedBytes,
				struct timeval presentationTime,
				unsigned durationInMicroseconds);
  void afterGettingBytes1(unsigned numBytesRead, struct timeval presentationTime);

  static void onInputClosure(void* clientData);
  void onInputClosure1();

private:
  FramedSource* fInputSource; // should be a byte-stream source??
  FramedSource::onCloseFunc* fClientOnInputCloseFunc;
  void* fClientOnInputCloseClientData;
  clientContinueFunc* fClientContinueFunc;
  void* fClientContinueClientData;

  // Use a pair of 'banks', and swap between them as they fill up:
  unsigned char* fBank[2];
  unsigned char fCurBankNum;
  unsigned char* fCurBank;

  // The most recent 'saved' parse position:
  unsigned fSavedParserIndex; // <= fCurParserIndex
  unsigned char fSavedRemainingUnparsedBits;

  // The current position of the parser within the current bank:
  unsigned fCurParserIndex; // <= fTotNumValidBytes
  unsigned char fRemainingUnparsedBits; // in previous byte: [0,7]

  // The total number of valid bytes stored in the current bank:
  unsigned fTotNumValidBytes; // <= BANK_SIZE

  // Whether we have seen EOF on the input source:
  Boolean fHaveSeenEOF;

  struct timeval fLastSeenPresentationTime; // hack used for EOF handling
};

#endif
