~morphis/aethercast/audio-streaming

« back to all changes in this revision

Viewing changes to tools/raw_streamer.cpp

Rework part of the streaming framework and add further unit tests

This reworks the streaming framework to be better testable which wasn't the case before
for all parts. Most critical parts are covered with tests now.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/*
2
 
 *  Copyright (C) 2016 Canonical, Ltd.
3
 
 *
4
 
 *  This program is free software; you can redistribute it and/or modify
5
 
 *  it under the terms of the GNU General Public License as published by
6
 
 *  the Free Software Foundation; either version 2 of the License, or
7
 
 *  (at your option) any later version.
8
 
 *
9
 
 *  This program is distributed in the hope that it will be useful,
10
 
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
11
 
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
 
 *  GNU General Public License for more details.
13
 
 *
14
 
 *  You should have received a copy of the GNU General Public License
15
 
 *  along with this program; if not, write to the Free Software
16
 
 *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
17
 
 *
18
 
 */
19
 
 
20
 
#include <sys/types.h>
21
 
#include <sys/stat.h>
22
 
#include <fcntl.h>
23
 
#include <memory.h>
24
 
 
25
 
#include <memory>
26
 
#include <chrono>
27
 
#include <thread>
28
 
#include <iostream>
29
 
#include <string>
30
 
 
31
 
#include <mcs/logger.h>
32
 
 
33
 
#include <mcs/report/reportfactory.h>
34
 
 
35
 
#include <mcs/streaming/mpegtspacketizer.h>
36
 
#include <mcs/streaming/rtpsender.h>
37
 
 
38
 
namespace {
39
 
static constexpr unsigned int kBufferSize = 2048;
40
 
}
41
 
 
42
 
int main(int argc, char **argv) {
43
 
 
44
 
    if (argc != 2 || argv[1] == nullptr) {
45
 
        std::cout << "Usage: " << std::endl
46
 
                  << " " << argv[0] << " <input>" << std::endl;
47
 
        return -EINVAL;
48
 
    }
49
 
 
50
 
    int fin = ::open(argv[1], O_RDONLY);
51
 
    if (fin < 0) {
52
 
        MCS_ERROR("Failed to open input file %s", argv[1]);
53
 
        return -EINVAL;
54
 
    }
55
 
 
56
 
    auto report_factory = mcs::report::ReportFactory::Create();
57
 
 
58
 
    auto packetizer = mcs::streaming::MPEGTSPacketizer::Create(report_factory->CreatePacketizerReport());
59
 
    auto sender = mcs::streaming::RTPSender::Create("192.168.178.1", 5000, report_factory->CreateSenderReport());
60
 
 
61
 
    if (!sender)
62
 
        return -EIO;
63
 
 
64
 
    int track_index = packetizer->AddTrack(mcs::streaming::MPEGTSPacketizer::TrackFormat{"video/avc"});
65
 
 
66
 
    int counter = 0;
67
 
 
68
 
    while (true) {
69
 
        uint8_t inbuf[kBufferSize];
70
 
 
71
 
        auto bytes_read = ::read(fin, inbuf, kBufferSize);
72
 
        if (bytes_read < 0) {
73
 
            MCS_ERROR("Failed to read input data");
74
 
            break;
75
 
        }
76
 
        else if (bytes_read == 0)
77
 
            break;
78
 
 
79
 
        auto buffer = mcs::video::Buffer::Create(bytes_read, mcs::Utils::GetNowUs());
80
 
        ::memcpy(buffer->Data(), inbuf, bytes_read);
81
 
 
82
 
        mcs::video::Buffer::Ptr outbuf;
83
 
 
84
 
        int flags = 0;
85
 
        if (!(counter % 100))
86
 
            flags = mcs::streaming::MPEGTSPacketizer::kEmitPCR |
87
 
                    mcs::streaming::MPEGTSPacketizer::kEmitPATandPMT;
88
 
 
89
 
        packetizer->Packetize(track_index, buffer, &outbuf, flags);
90
 
        sender->Queue(outbuf);
91
 
 
92
 
        counter++;
93
 
        std::this_thread::sleep_for(std::chrono::milliseconds{1});
94
 
    }
95
 
 
96
 
    ::close(fin);
97
 
 
98
 
    return 0;
99
 
}