X-Git-Url: https://git.sesse.net/?a=blobdiff_plain;f=httpd.h;h=e8efc030b4706d92b64e89e7ea748c056d8f7c85;hb=c667195e19ec9898b21cc5ebfa29dc8804ec96ad;hp=0a092aaadd3e7c3a926c2920925277764958a858;hpb=b4f16ea9f8969a3ba14be8cd9c88cfe00d19533b;p=nageru diff --git a/httpd.h b/httpd.h index 0a092aa..e8efc03 100644 --- a/httpd.h +++ b/httpd.h @@ -1,22 +1,41 @@ #ifndef _HTTPD_H #define _HTTPD_H +// A class dealing with stream output, both to HTTP (thus the class name) +// and to local output files. Since we generally have very few outputs +// (end clients are not meant to connect directly to our stream; it should be +// transcoded by something else and then sent to a reflector), we don't need to +// care a lot about performance. Thus, we solve this by the simplest possible +// way, namely having one ffmpeg mux per output. + #include +#include +#include +#include +#include #include -#include +#include #include -#include +#include #include +struct MHD_Connection; + extern "C" { +#include #include +#include } class HTTPD { public: - HTTPD(); + HTTPD(int width, int height); void start(int port); - void add_packet(const AVPacket &pkt); + void add_packet(const AVPacket &pkt, int64_t pts, int64_t dts); + + // You can only have one going at the same time. + void open_output_file(const std::string &filename); + void close_output_file(); private: static int answer_to_connection_thunk(void *cls, MHD_Connection *connection, @@ -31,23 +50,31 @@ private: static void free_stream(void *cls); + class Mux { + public: + Mux(AVFormatContext *avctx, int width, int height); // Takes ownership of avctx. + ~Mux(); + void add_packet(const AVPacket &pkt, int64_t pts, int64_t dts); + + private: + AVFormatContext *avctx; + AVStream *avstream_video, *avstream_audio; + }; + class Stream { public: - Stream(AVOutputFormat *oformat); - ~Stream(); + Stream(AVOutputFormat *oformat, int width, int height); static ssize_t reader_callback_thunk(void *cls, uint64_t pos, char *buf, size_t max); ssize_t reader_callback(uint64_t pos, char *buf, size_t max); - void add_packet(const AVPacket &pkt); + void add_packet(const AVPacket &pkt, int64_t pts, int64_t dts); private: static int write_packet_thunk(void *opaque, uint8_t *buf, int buf_size); int write_packet(uint8_t *buf, int buf_size); - AVIOContext *avio; - AVFormatContext *avctx; - AVStream *avstream_video, *avstream_audio; + std::unique_ptr mux; std::mutex buffer_mutex; std::condition_variable has_buffered_data; @@ -56,6 +83,9 @@ private: }; std::vector streams; // Not owned. + + int width, height; + std::unique_ptr file_mux; // To local disk. }; #endif // !defined(_HTTPD_H)