summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorCarl Hetherington <cth@carlh.net>2012-07-27 21:12:53 +0100
committerCarl Hetherington <cth@carlh.net>2012-07-27 21:12:53 +0100
commit480a14fd2fd9937e2450c652f2953d5835f56239 (patch)
tree15bd9adfaa764aed0c06f868b2fa3cff9260c36e /src
parent8b07c8131e535579f39c1899f063ccedc425eeb8 (diff)
Compiles.
Diffstat (limited to 'src')
-rw-r--r--src/lib/dcp_video_frame.cc73
-rw-r--r--src/lib/dcp_video_frame.h4
-rw-r--r--src/lib/util.cc36
-rw-r--r--src/lib/util.h10
-rw-r--r--src/tools/servomatic.cc64
5 files changed, 42 insertions, 145 deletions
diff --git a/src/lib/dcp_video_frame.cc b/src/lib/dcp_video_frame.cc
index 8a4c845d9..9addb3b25 100644
--- a/src/lib/dcp_video_frame.cc
+++ b/src/lib/dcp_video_frame.cc
@@ -38,11 +38,10 @@
#include <iostream>
#include <unistd.h>
#include <errno.h>
-#ifdef DVDOMATIC_POSIX
-#include <netinet/in.h>
-#include <netdb.h>
-#endif
+#include <boost/array.hpp>
+#include <boost/asio.hpp>
#include <boost/filesystem.hpp>
+#include <boost/lexical_cast.hpp>
#include "film.h"
#include "dcp_video_frame.h"
#include "lut.h"
@@ -292,43 +291,13 @@ DCPVideoFrame::encode_locally ()
shared_ptr<EncodedData>
DCPVideoFrame::encode_remotely (Server const * serv)
{
-#ifdef DVDOMATIC_POSIX
- int const fd = socket (AF_INET, SOCK_STREAM, 0);
- if (fd < 0) {
- throw NetworkError ("could not create socket");
- }
-
- struct timeval tv;
- tv.tv_sec = 20;
- tv.tv_usec = 0;
-
- if (setsockopt (fd, SOL_SOCKET, SO_RCVTIMEO, (void *) &tv, sizeof (tv)) < 0) {
- close (fd);
- throw NetworkError ("setsockopt failed");
- }
+ asio::io_service io_service;
+ asio::ip::tcp::resolver resolver (io_service);
+ asio::ip::tcp::resolver::query query (serv->host_name(), boost::lexical_cast<string> (Config::instance()->server_port ()));
+ asio::ip::tcp::resolver::iterator endpoint_iterator = resolver.resolve (query);
- if (setsockopt (fd, SOL_SOCKET, SO_SNDTIMEO, (void *) &tv, sizeof (tv)) < 0) {
- close (fd);
- throw NetworkError ("setsockopt failed");
- }
-
- struct hostent* server = gethostbyname (serv->host_name().c_str ());
- if (server == 0) {
- close (fd);
- throw NetworkError ("gethostbyname failed");
- }
-
- struct sockaddr_in server_address;
- memset (&server_address, 0, sizeof (server_address));
- server_address.sin_family = AF_INET;
- memcpy (&server_address.sin_addr.s_addr, server->h_addr, server->h_length);
- server_address.sin_port = htons (Config::instance()->server_port ());
- if (connect (fd, (struct sockaddr *) &server_address, sizeof (server_address)) < 0) {
- close (fd);
- stringstream s;
- s << "could not connect (" << strerror (errno) << ")";
- throw NetworkError (s.str());
- }
+ shared_ptr<asio::ip::tcp::socket> socket (new asio::ip::tcp::socket (io_service));
+ socket->connect (*endpoint_iterator);
#ifdef DEBUG_HASH
_input->hash ("Input for remote encoding (before sending)");
@@ -351,13 +320,13 @@ DCPVideoFrame::encode_remotely (Server const * serv)
s << _input->line_size()[i] << " ";
}
- socket_write (fd, (uint8_t *) s.str().c_str(), s.str().length() + 1);
+ asio::write (*socket, asio::buffer (s.str().c_str(), s.str().length() + 1));
for (int i = 0; i < _input->components(); ++i) {
- socket_write (fd, _input->data()[i], _input->line_size()[i] * _input->lines(i));
+ asio::write (*socket, asio::buffer (_input->data()[i], _input->line_size()[i] * _input->lines(i)));
}
- SocketReader reader (fd);
+ SocketReader reader (socket);
char buffer[32];
reader.read_indefinite ((uint8_t *) buffer, sizeof (buffer));
@@ -377,13 +346,7 @@ DCPVideoFrame::encode_remotely (Server const * serv)
_log->log (s.str ());
}
- close (fd);
return e;
-#endif
-
-#ifdef DVDOMATIC_WINDOWS
- return shared_ptr<EncodedData> ();
-#endif
}
/** Write this data to a J2K file.
@@ -408,19 +371,17 @@ EncodedData::write (shared_ptr<const Options> opt, int frame)
filesystem::rename (tmp_j2k, opt->frame_out_path (frame, false));
}
-#ifdef DVDOMATIC_POSIX
-/** Send this data to a file descriptor.
- * @param fd File descriptor.
+/** Send this data to a socket.
+ * @param socket Socket
*/
void
-EncodedData::send (int fd)
+EncodedData::send (shared_ptr<asio::ip::tcp::socket> socket)
{
stringstream s;
s << _size;
- socket_write (fd, (uint8_t *) s.str().c_str(), s.str().length() + 1);
- socket_write (fd, _data, _size);
+ asio::write (*socket, asio::buffer (s.str().c_str(), s.str().length() + 1));
+ asio::write (*socket, asio::buffer (_data, _size));
}
-#endif
#ifdef DEBUG_HASH
void
diff --git a/src/lib/dcp_video_frame.h b/src/lib/dcp_video_frame.h
index 9acf50692..464d48515 100644
--- a/src/lib/dcp_video_frame.h
+++ b/src/lib/dcp_video_frame.h
@@ -48,9 +48,7 @@ public:
virtual ~EncodedData () {}
-#ifdef DVDOMATIC_POSIX
- void send (int);
-#endif
+ void send (boost::shared_ptr<boost::asio::ip::tcp::socket>);
void write (boost::shared_ptr<const Options>, int);
#ifdef DEBUG_HASH
diff --git a/src/lib/util.cc b/src/lib/util.cc
index 9896bff60..1bd8f4318 100644
--- a/src/lib/util.cc
+++ b/src/lib/util.cc
@@ -281,40 +281,15 @@ dependency_version_summary ()
return s.str ();
}
-#ifdef DVDOMATIC_POSIX
-/** Write some data to a socket.
- * @param fd Socket file descriptor.
- * @param data Data.
- * @param size Amount to write, in bytes.
- */
-void
-socket_write (int fd, uint8_t const * data, int size)
-{
- uint8_t const * p = data;
- while (size) {
- int const n = send (fd, p, size, MSG_NOSIGNAL);
- if (n < 0) {
- stringstream s;
- s << "could not write (" << strerror (errno) << ")";
- throw NetworkError (s.str ());
- }
-
- size -= n;
- p += n;
- }
-}
-#endif
-
double
seconds (struct timeval t)
{
return t.tv_sec + (double (t.tv_usec) / 1e6);
}
-#ifdef DVDOMATIC_POSIX
-/** @param fd File descriptor to read from */
-SocketReader::SocketReader (int fd)
- : _fd (fd)
+/** @param socket Socket to read from */
+SocketReader::SocketReader (shared_ptr<asio::ip::tcp::socket> socket)
+ : _socket (socket)
, _buffer_data (0)
{
@@ -356,7 +331,7 @@ SocketReader::read_definite_and_consume (uint8_t* data, int size)
/* read() the rest */
while (size > 0) {
- int const n = ::read (_fd, data, size);
+ int const n = asio::read (*_socket, asio::buffer (data, size));
if (n <= 0) {
throw NetworkError ("could not read");
}
@@ -379,7 +354,7 @@ SocketReader::read_indefinite (uint8_t* data, int size)
int to_read = size - _buffer_data;
while (to_read > 0) {
/* read as much of it as we can (into our buffer) */
- int const n = ::read (_fd, _buffer + _buffer_data, to_read);
+ int const n = asio::read (*_socket, asio::buffer (_buffer + _buffer_data, to_read));
if (n <= 0) {
throw NetworkError ("could not read");
}
@@ -394,7 +369,6 @@ SocketReader::read_indefinite (uint8_t* data, int size)
assert (size >= _buffer_data);
memcpy (data, _buffer, size);
}
-#endif
#ifdef DVDOMATIC_POSIX
void
diff --git a/src/lib/util.h b/src/lib/util.h
index b3c1ebc05..1faef0cd3 100644
--- a/src/lib/util.h
+++ b/src/lib/util.h
@@ -28,6 +28,7 @@
#include <string>
#include <vector>
#include <boost/shared_ptr.hpp>
+#include <boost/asio.hpp>
extern "C" {
#include <libavcodec/avcodec.h>
#include <libavfilter/avfilter.h>
@@ -41,7 +42,6 @@ extern void stacktrace (std::ostream &, int);
extern std::string audio_sample_format_to_string (AVSampleFormat);
extern AVSampleFormat audio_sample_format_from_string (std::string);
extern std::string dependency_version_summary ();
-extern void socket_write (int, uint8_t const *, int);
extern double seconds (struct timeval);
extern void dvdomatic_setup ();
extern std::vector<std::string> split_at_spaces_considering_quotes (std::string);
@@ -58,19 +58,21 @@ extern void md5_data (std::string, void const *, int);
/** @class SocketReader
* @brief A helper class from reading from sockets.
+ *
+ * You can probably do this stuff directly in boost, but I'm not sure how.
*/
class SocketReader
{
public:
- SocketReader (int);
+ SocketReader (boost::shared_ptr<boost::asio::ip::tcp::socket>);
void read_definite_and_consume (uint8_t *, int);
void read_indefinite (uint8_t *, int);
void consume (int);
private:
- /** file descriptor we are reading from */
- int _fd;
+ /** socket we are reading from */
+ boost::shared_ptr<boost::asio::ip::tcp::socket> _socket;
/** a buffer for small reads */
uint8_t _buffer[256];
/** amount of valid data in the buffer */
diff --git a/src/tools/servomatic.cc b/src/tools/servomatic.cc
index 74be41e39..a802665c8 100644
--- a/src/tools/servomatic.cc
+++ b/src/tools/servomatic.cc
@@ -24,11 +24,8 @@
#include <vector>
#include <unistd.h>
#include <errno.h>
-#ifdef DVDOMATIC_POSIX
-#include <sys/types.h>
-#include <sys/socket.h>
-#include <netinet/in.h>
-#endif
+#include <boost/array.hpp>
+#include <boost/asio.hpp>
#include <boost/algorithm/string.hpp>
#include <boost/thread.hpp>
#include <boost/thread/mutex.hpp>
@@ -49,15 +46,15 @@ using namespace boost;
static vector<thread *> worker_threads;
-static std::list<int> queue;
+static std::list<shared_ptr<asio::ip::tcp::socket> > queue;
static mutex worker_mutex;
static condition worker_condition;
static Log log_ ("servomatic.log");
int
-process (int fd)
+process (shared_ptr<asio::ip::tcp::socket> socket)
{
- SocketReader reader (fd);
+ SocketReader reader (socket);
char buffer[128];
reader.read_indefinite ((uint8_t *) buffer, sizeof (buffer));
@@ -68,7 +65,6 @@ process (int fd)
string command;
s >> command;
if (command != "encode") {
- close (fd);
return -1;
}
@@ -123,7 +119,6 @@ process (int fd)
#ifdef DEBUG_HASH
encoded->hash ("Encoded image (as made by server and as sent back)");
#endif
-
return frame;
}
@@ -137,7 +132,7 @@ worker_thread ()
worker_condition.wait (lock);
}
- int fd = queue.front ();
+ shared_ptr<asio::ip::tcp::socket> socket = queue.front ();
queue.pop_front ();
lock.unlock ();
@@ -148,12 +143,12 @@ worker_thread ()
gettimeofday (&start, 0);
try {
- frame = process (fd);
+ frame = process (socket);
} catch (std::exception& e) {
cerr << "Error: " << e.what() << "\n";
}
- close (fd);
+ socket.reset ();
lock.lock ();
@@ -178,44 +173,11 @@ main ()
worker_threads.push_back (new thread (worker_thread));
}
- int fd = socket (AF_INET, SOCK_STREAM, 0);
- if (fd < 0) {
- throw NetworkError ("could not open socket");
- }
-
- int const o = 1;
- setsockopt (fd, SOL_SOCKET, SO_REUSEADDR, &o, sizeof (o));
-
- struct timeval tv;
- tv.tv_sec = 20;
- tv.tv_usec = 0;
- setsockopt (fd, SOL_SOCKET, SO_RCVTIMEO, (void *) &tv, sizeof (tv));
- setsockopt (fd, SOL_SOCKET, SO_SNDTIMEO, (void *) &tv, sizeof (tv));
-
- struct sockaddr_in server_address;
- memset (&server_address, 0, sizeof (server_address));
- server_address.sin_family = AF_INET;
- server_address.sin_addr.s_addr = INADDR_ANY;
- server_address.sin_port = htons (Config::instance()->server_port ());
- if (::bind (fd, (struct sockaddr *) &server_address, sizeof (server_address)) < 0) {
- stringstream s;
- s << "could not bind to port " << Config::instance()->server_port() << " (" << strerror (errno) << ")";
- throw NetworkError (s.str());
- }
-
- listen (fd, BACKLOG);
-
+ asio::io_service io_service;
+ asio::ip::tcp::acceptor acceptor (io_service, asio::ip::tcp::endpoint (asio::ip::tcp::v4(), Config::instance()->server_port ()));
while (1) {
- struct sockaddr_in client_address;
- socklen_t client_length = sizeof (client_address);
- int new_fd = accept (fd, (struct sockaddr *) &client_address, &client_length);
- if (new_fd < 0) {
- if (errno != EAGAIN && errno != EWOULDBLOCK) {
- throw NetworkError ("accept failed");
- }
-
- continue;
- }
+ shared_ptr<asio::ip::tcp::socket> socket (new asio::ip::tcp::socket (io_service));
+ acceptor.accept (*socket);
mutex::scoped_lock lock (worker_mutex);
@@ -230,7 +192,7 @@ main ()
setsockopt (new_fd, SOL_SOCKET, SO_RCVTIMEO, (void *) &tv, sizeof (tv));
setsockopt (new_fd, SOL_SOCKET, SO_SNDTIMEO, (void *) &tv, sizeof (tv));
- queue.push_back (new_fd);
+ queue.push_back (socket);
worker_condition.notify_all ();
}