YARP
Yet Another Robot Platform
MjpegCarrier.h
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2006-2020 Istituto Italiano di Tecnologia (IIT)
3  * Copyright (C) 2006-2010 RobotCub Consortium
4  * All rights reserved.
5  *
6  * This software may be modified and distributed under the terms of the
7  * BSD-3-Clause license. See the accompanying LICENSE file for details.
8  */
9 
10 #ifndef MJPEGCARRIER_INC
11 #define MJPEGCARRIER_INC
12 
13 #include <yarp/os/Carrier.h>
14 #include <yarp/os/NetType.h>
16 #include "MjpegStream.h"
17 #include "MjpegLogComponent.h"
18 
19 #include <cstring>
20 
39 class MjpegCarrier :
40  public yarp::os::Carrier
41 {
42 private:
43  bool firstRound;
44  bool sender;
45  std::string envelope;
46 public:
48  firstRound = true;
49  sender = false;
50  }
51 
52  Carrier *create() const override {
53  return new MjpegCarrier();
54  }
55 
56  std::string getName() const override {
57  return "mjpeg";
58  }
59 
60  bool isConnectionless() const override {
61  return false;
62  }
63 
64  bool canAccept() const override {
65  return true;
66  }
67 
68  bool canOffer() const override {
69  return true;
70  }
71 
72  bool isTextMode() const override {
73  return false;
74  }
75 
76  bool canEscape() const override {
77  return false;
78  }
79 
80  void handleEnvelope(const std::string& envelope) override {
81  this->envelope = envelope;
82  }
83 
84  bool requireAck() const override {
85  return false;
86  }
87 
88  bool supportReply() const override {
89  return false;
90  }
91 
92  bool isLocal() const override {
93  return false;
94  }
95 
96  // this is important - flips expected flow of messages
97  bool isPush() const override {
98  return false;
99  }
100 
101  std::string toString() const override {
102  return "mjpeg_carrier";
103  }
104 
105  void getHeader(yarp::os::Bytes& header) const override {
106  // GET /?action=stream HTTP/1.1
107  const char *target = "GET /?ac";
108  for (size_t i=0; i<8 && i<header.length(); i++) {
109  header.get()[i] = target[i];
110  }
111  }
112 
113  bool checkHeader(const yarp::os::Bytes& header) override {
114  if (header.length()!=8) {
115  return false;
116  }
117  const char *target = "GET /?ac";
118  for (int i=0; i<8; i++) {
119  if (header.get()[i] != target[i]) {
120  return false;
121  }
122  }
123  yCTrace(MJPEGCARRIER, "Got header");
124  return true;
125  }
126 
127  void setParameters(const yarp::os::Bytes& header) override {
128  // no parameters - no carrier variants
129  }
130 
131 
132  // Now, the initial hand-shaking
133 
134  bool prepareSend(yarp::os::ConnectionState& proto) override {
135  // nothing special to do
136  return true;
137  }
138 
139  bool sendHeader(yarp::os::ConnectionState& proto) override;
140 
142  return true;
143  }
144 
146  std::string txt;
147  do {
148  txt = proto.is().readLine();
149  } while (txt!="");
150  return true;
151  }
152 
154  std::string target = "HTTP/1.0 200 OK\r\n\
155 Connection: close\r\n\
156 Server: yarp/mjpeg_carrier/0.1\r\n\
157 Cache-Control: no-store, no-cache, must-revalidate, pre-check=0, post-check=0, max-age=0\r\n\
158 Pragma: no-cache\r\n\
159 Expires: Mon, 3 Jan 2000 12:34:56 GMT\r\n\
160 Content-Type: multipart/x-mixed-replace;boundary=boundarydonotcross\r\n\
161 \r\n\
162 --boundarydonotcross\r\n";
163  yarp::os::Bytes b((char*)target.c_str(),strlen(target.c_str()));
164  proto.os().write(b);
165  sender = true; // this is a pull connection, not a push
166  //MjpegStream *stream = new MjpegStream(proto.giveStreams(),sender);
167  //if (stream==NULL) { return false; }
168  //proto.takeStreams(stream);
169  return true;
170  }
171 
173  std::string txt;
174  do {
175  txt = proto.is().readLine();
176  } while (txt!="");
177 
178  sender = false;
179  MjpegStream *stream = new MjpegStream(proto.giveStreams(),
180  autoCompression());
181  if (stream==NULL) { return false; }
182  proto.takeStreams(stream);
183  return true;
184  }
185 
186  bool isActive() const override {
187  return true;
188  }
189 
190 
191  // Payload time!
192 
193  bool write(yarp::os::ConnectionState& proto, yarp::os::SizedWriter& writer) override;
194 
195  bool reply(yarp::os::ConnectionState& proto, yarp::os::SizedWriter& writer) override;
196 
198  return true;
199  }
200 
201  bool expectIndex(yarp::os::ConnectionState& proto) override {
202  return true;
203  }
204 
205  bool sendAck(yarp::os::ConnectionState& proto) override {
206  return true;
207  }
208 
209  bool expectAck(yarp::os::ConnectionState& proto) override {
210  return true;
211  }
212 
213  std::string getBootstrapCarrierName() const override { return {}; }
214 
215  virtual bool autoCompression() const;
216 };
217 
218 #endif
yarp::os::Carrier
A base class for connection types (tcp, mcast, shmem, ...) which are called carriers in YARP.
Definition: Carrier.h:48
MjpegCarrier::setParameters
void setParameters(const yarp::os::Bytes &header) override
Configure this carrier based on the first 8 bytes of the connection.
Definition: MjpegCarrier.h:127
yarp::os::ConnectionState::giveStreams
virtual TwoWayStream * giveStreams()=0
Take ownership of the streams associated with the connection.
yarp::os::OutputStream::write
virtual void write(char ch)
Write a single byte to the stream.
Definition: OutputStream.cpp:17
MjpegCarrier::sendAck
bool sendAck(yarp::os::ConnectionState &proto) override
Send an acknowledgement, if needed for this carrier.
Definition: MjpegCarrier.h:205
MjpegCarrier
A carrier for sending/receiving images via mjpeg over http.
Definition: MjpegCarrier.h:41
MjpegCarrier::sendHeader
bool sendHeader(yarp::os::ConnectionState &proto) override
Write a header appropriate to the carrier to the connection, followed by any carrier-specific data.
Definition: MjpegCarrier.cpp:207
MjpegCarrier::write
bool write(yarp::os::ConnectionState &proto, yarp::os::SizedWriter &writer) override
Write a message.
Definition: MjpegCarrier.cpp:160
MjpegCarrier::sendIndex
virtual bool sendIndex(yarp::os::ConnectionState &proto, yarp::os::SizedWriter &writer)
Definition: MjpegCarrier.h:197
MjpegCarrier::expectSenderSpecifier
bool expectSenderSpecifier(yarp::os::ConnectionState &proto) override
Expect the name of the sending port.
Definition: MjpegCarrier.h:141
MjpegCarrier::expectIndex
bool expectIndex(yarp::os::ConnectionState &proto) override
Expect a message header, if there is one for this carrier.
Definition: MjpegCarrier.h:201
MjpegCarrier::canEscape
bool canEscape() const override
Check if carrier can encode administrative messages, as opposed to just user data.
Definition: MjpegCarrier.h:76
MjpegCarrier::requireAck
bool requireAck() const override
Check if carrier has flow control, requiring sent messages to be acknowledged by recipient.
Definition: MjpegCarrier.h:84
MjpegCarrier::getHeader
void getHeader(yarp::os::Bytes &header) const override
Provide 8 bytes describing this connection sufficiently to allow the other side of a connection to se...
Definition: MjpegCarrier.h:105
NetType.h
MjpegCarrier::expectAck
bool expectAck(yarp::os::ConnectionState &proto) override
Receive an acknowledgement, if expected for this carrier.
Definition: MjpegCarrier.h:209
MjpegCarrier::isActive
bool isActive() const override
Check if carrier is alive and error free.
Definition: MjpegCarrier.h:186
MjpegCarrier::isLocal
bool isLocal() const override
Check if carrier operates within a single process.
Definition: MjpegCarrier.h:92
MjpegCarrier::isPush
bool isPush() const override
Check if carrier is "push" or "pull" style.
Definition: MjpegCarrier.h:97
yarp::os::ConnectionState::takeStreams
virtual void takeStreams(TwoWayStream *streams)=0
Provide streams to be used with the connection.
yarp::os::ConnectionState::os
OutputStream & os()
Shorthand for getOutputStream()
Definition: ConnectionState.h:117
ConnectionState.h
MJPEGCARRIER
const yarp::os::LogComponent & MJPEGCARRIER()
Definition: MjpegLogComponent.cpp:16
MjpegStream
Definition: MjpegStream.h:29
MjpegCarrier::expectExtraHeader
bool expectExtraHeader(yarp::os::ConnectionState &proto) override
Receive any carrier-specific header.
Definition: MjpegCarrier.h:145
yarp::os::Bytes::get
const char * get() const
Definition: Bytes.cpp:30
MjpegCarrier::getBootstrapCarrierName
std::string getBootstrapCarrierName() const override
Get the name of the carrier that should be used prior to handshaking, if a port is registered with th...
Definition: MjpegCarrier.h:213
yarp::os::Bytes::length
size_t length() const
Definition: Bytes.cpp:25
yarp::os::InputStream::readLine
std::string readLine(const char terminal='\n', bool *success=nullptr)
Read a block of text terminated with a specific marker (or EOF).
Definition: InputStream.cpp:57
MjpegCarrier::isConnectionless
bool isConnectionless() const override
Check if this carrier is connectionless (like udp, mcast) or connection based (like tcp).
Definition: MjpegCarrier.h:60
MjpegCarrier::canOffer
bool canOffer() const override
Check if writing is implemented for this carrier.
Definition: MjpegCarrier.h:68
MjpegCarrier::respondToHeader
bool respondToHeader(yarp::os::ConnectionState &proto) override
Respond to the header.
Definition: MjpegCarrier.h:153
yarp::os::Bytes
A simple abstraction for a block of bytes.
Definition: Bytes.h:28
MjpegCarrier::autoCompression
virtual bool autoCompression() const
Definition: MjpegCarrier.cpp:228
MjpegCarrier::prepareSend
bool prepareSend(yarp::os::ConnectionState &proto) override
Perform any initialization needed before writing on a connection.
Definition: MjpegCarrier.h:134
MjpegCarrier::reply
bool reply(yarp::os::ConnectionState &proto, yarp::os::SizedWriter &writer) override
Definition: MjpegCarrier.cpp:202
MjpegCarrier::canAccept
bool canAccept() const override
Check if reading is implemented for this carrier.
Definition: MjpegCarrier.h:64
MjpegCarrier::getName
std::string getName() const override
Get the name of this connection type ("tcp", "mcast", "shmem", ...)
Definition: MjpegCarrier.h:56
yarp::os::ConnectionState
The basic state of a connection - route, streams in use, etc.
Definition: ConnectionState.h:31
Carrier.h
MjpegCarrier::handleEnvelope
void handleEnvelope(const std::string &envelope) override
Carriers that do not distinguish data from administrative headers (i.e.
Definition: MjpegCarrier.h:80
MjpegLogComponent.h
MjpegCarrier::isTextMode
bool isTextMode() const override
Check if carrier is textual in nature.
Definition: MjpegCarrier.h:72
MjpegStream.h
MjpegCarrier::toString
std::string toString() const override
Get name of carrier.
Definition: MjpegCarrier.h:101
yarp::os::ConnectionState::is
InputStream & is()
Shorthand for getInputStream()
Definition: ConnectionState.h:125
MjpegCarrier::create
Carrier * create() const override
Factory method.
Definition: MjpegCarrier.h:52
MjpegCarrier::supportReply
bool supportReply() const override
This flag is used by YARP to determine whether the connection can carry RPC traffic,...
Definition: MjpegCarrier.h:88
MjpegCarrier::expectReplyToHeader
bool expectReplyToHeader(yarp::os::ConnectionState &proto) override
Process reply to header, if one is expected for this carrier.
Definition: MjpegCarrier.h:172
yCTrace
#define yCTrace(component,...)
Definition: LogComponent.h:88
MjpegCarrier::checkHeader
bool checkHeader(const yarp::os::Bytes &header) override
Given the first 8 bytes received on a connection, decide if this is the right carrier type to use for...
Definition: MjpegCarrier.h:113
MjpegCarrier::MjpegCarrier
MjpegCarrier()
Definition: MjpegCarrier.h:47
yarp::os::SizedWriter
Minimal requirements for an efficient Writer.
Definition: SizedWriter.h:36