/**********
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.
// RTP sink for a common kind of payload format: Those which pack multiple,
// complete codec frames (as many as possible) into each RTP packet.
// C++ header

#ifndef _MULTI_FRAMED_RTP_SINK_HH
#define _MULTI_FRAMED_RTP_SINK_HH

#ifndef _RTP_SINK_HH
#include "RTPSink.hh"
#endif

class MultiFramedRTPSink: public RTPSink {
public:
  void setPacketSizes(unsigned preferredPacketSize, unsigned maxPacketSize);

  typedef void (onSendErrorFunc)(void* clientData);
  void setOnSendErrorFunc(onSendErrorFunc* onSendErrorFunc, void* onSendErrorFuncData) {
    // Can be used to set a callback function to be called if there's an error sending RTP packets on our socket.
    fOnSendErrorFunc = onSendErrorFunc;
    fOnSendErrorData = onSendErrorFuncData;
  }

protected:
  MultiFramedRTPSink(UsageEnvironment& env,
		     Groupsock* rtpgs, unsigned char rtpPayloadType,
		     unsigned rtpTimestampFrequency,
		     char const* rtpPayloadFormatName,
		     unsigned numChannels = 1);
	// we're a virtual base class

  virtual ~MultiFramedRTPSink();

  virtual void doSpecialFrameHandling(unsigned fragmentationOffset,
				      unsigned char* frameStart,
				      unsigned numBytesInFrame,
				      struct timeval framePresentationTime,
				      unsigned numRemainingBytes);
      // perform any processing specific to the particular payload format
  virtual Boolean allowFragmentationAfterStart() const;
      // whether a frame can be fragmented if other frame(s) appear earlier
      // in the packet (by default: False)
  virtual Boolean allowOtherFramesAfterLastFragment() const;
      // whether other frames can be packed into a packet following the
      // final fragment of a previous, fragmented frame (by default: False)
  virtual Boolean frameCanAppearAfterPacketStart(unsigned char const* frameStart,
						 unsigned numBytesInFrame) const;
      // whether this frame can appear in position >1 in a pkt (default: True)
  virtual unsigned specialHeaderSize() const;
      // returns the size of any special header used (following the RTP header) (default: 0)
  virtual unsigned frameSpecificHeaderSize() const;
      // returns the size of any frame-specific header used (before each frame
      // within the packet) (default: 0)
  virtual unsigned computeOverflowForNewFrame(unsigned newFrameSize) const;
      // returns the number of overflow bytes that would be produced by adding a new
      // frame of size "newFrameSize" to the current RTP packet.
      // (By default, this just calls "numOverflowBytes()", but subclasses can redefine
      // this to (e.g.) impose a granularity upon RTP payload fragments.)

  // Functions that might be called by doSpecialFrameHandling(), or other subclass virtual functions:
  Boolean isFirstPacket() const { return fIsFirstPacket; }
  Boolean isFirstFrameInPacket() const { return fNumFramesUsedSoFar == 0; }
  unsigned curFragmentationOffset() const { return fCurFragmentationOffset; }
  void setMarkerBit();
  void setTimestamp(struct timeval framePresentationTime);
  void setSpecialHeaderWord(unsigned word, /* 32 bits, in host order */
			    unsigned wordPosition = 0);
  void setSpecialHeaderBytes(unsigned char const* bytes, unsigned numBytes,
			     unsigned bytePosition = 0);
  void setFrameSpecificHeaderWord(unsigned word, /* 32 bits, in host order */
				  unsigned wordPosition = 0);
  void setFrameSpecificHeaderBytes(unsigned char const* bytes, unsigned numBytes,
				   unsigned bytePosition = 0);
  void setFramePadding(unsigned numPaddingBytes);
  unsigned numFramesUsedSoFar() const { return fNumFramesUsedSoFar; }
  unsigned ourMaxPacketSize() const { return fOurMaxPacketSize; }

public: // redefined virtual functions:
  virtual void stopPlaying();

protected: // redefined virtual functions:
  virtual Boolean continuePlaying();

private:
  void buildAndSendPacket(Boolean isFirstPacket);
  void packFrame();
  void sendPacketIfNecessary();
  static void sendNext(void* firstArg);
  friend void sendNext(void*);

  static void afterGettingFrame(void* clientData,
				unsigned numBytesRead, unsigned numTruncatedBytes,
				struct timeval presentationTime,
				unsigned durationInMicroseconds);
  void afterGettingFrame1(unsigned numBytesRead, unsigned numTruncatedBytes,
			  struct timeval presentationTime,
			  unsigned durationInMicroseconds);
  Boolean isTooBigForAPacket(unsigned numBytes) const;

  static void ourHandleClosure(void* clientData);

private:
  OutPacketBuffer* fOutBuf;

  Boolean fNoFramesLeft;
  unsigned fNumFramesUsedSoFar;
  unsigned fCurFragmentationOffset;
  Boolean fPreviousFrameEndedFragmentation;

  Boolean fIsFirstPacket;
  struct timeval fNextSendTime;
  unsigned fTimestampPosition;
  unsigned fSpecialHeaderPosition;
  unsigned fSpecialHeaderSize; // size in bytes of any special header used
  unsigned fCurFrameSpecificHeaderPosition;
  unsigned fCurFrameSpecificHeaderSize; // size in bytes of cur frame-specific header
  unsigned fTotalFrameSpecificHeaderSizes; // size of all frame-specific hdrs in pkt
  unsigned fOurMaxPacketSize;

  onSendErrorFunc* fOnSendErrorFunc;
  void* fOnSendErrorData;
};

#endif
