summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAnders Kaseorg <andersk@mit.edu>2012-04-17 02:50:29 -0400
committerKeith Winstein <keithw@mit.edu>2012-04-22 16:14:28 -0400
commitb6736eb0a5db212a536e10bca241ea9a09ec56c3 (patch)
tree75634b92bebc05c15bd55dc3dc1cafb7717a1808
parent76f5b593d9123f04721426f5759ba305b8ee970b (diff)
Use protobuf’s Gzip{Input,Output}Stream wrapper around zlib
This removes our direct zlib dependency (although of course protobuf still uses it internally), removes a fixed 4 MiB buffer and its corresponding limit on the terminal size, reduces some string copying, and deletes some code. Signed-off-by: Anders Kaseorg <andersk@mit.edu> (Closes #230.)
-rw-r--r--configure.ac2
-rw-r--r--debian/control2
-rw-r--r--fedora/mosh.spec1
-rw-r--r--src/network/Makefile.am2
-rw-r--r--src/network/compressor.cc32
-rw-r--r--src/network/compressor.h28
-rw-r--r--src/network/transportfragment.cc34
7 files changed, 30 insertions, 71 deletions
diff --git a/configure.ac b/configure.ac
index e734cc9..ce59f2a 100644
--- a/configure.ac
+++ b/configure.ac
@@ -155,8 +155,6 @@ AS_IF([test x"$with_utempter" != xno],
[AC_MSG_WARN([Unable to find libutempter; utmp entries will not be made.])],
[AC_MSG_ERROR([--with-utempter was given but libutempter was not found.])])])])
-AC_SEARCH_LIBS([compress], [z], , [AC_MSG_ERROR([Unable to find zlib.])])
-
AC_ARG_WITH([skalibs],
[AS_HELP_STRING([--with-skalibs[=DIR]],
[root directory of skalibs installation])],
diff --git a/debian/control b/debian/control
index c3c20f3..8f34ff3 100644
--- a/debian/control
+++ b/debian/control
@@ -2,7 +2,7 @@ Source: mosh
Section: net
Priority: optional
Maintainer: Keith Winstein <keithw@mit.edu>
-Build-Depends: debhelper (>= 7.0.50), autotools-dev, protobuf-compiler, libprotobuf-dev, dh-autoreconf, pkg-config, libutempter-dev, zlib1g-dev, libncurses5-dev
+Build-Depends: debhelper (>= 7.0.50), autotools-dev, protobuf-compiler, libprotobuf-dev, dh-autoreconf, pkg-config, libutempter-dev, libncurses5-dev
Standards-Version: 3.9.3
Homepage: http://mosh.mit.edu
Vcs-Git: git://github.com/keithw/mosh.git
diff --git a/fedora/mosh.spec b/fedora/mosh.spec
index 6d92689..9b8a48d 100644
--- a/fedora/mosh.spec
+++ b/fedora/mosh.spec
@@ -11,7 +11,6 @@ Source0: https://github.com/downloads/keithw/mosh/mosh-%{version}.tar.gz
BuildRequires: protobuf-compiler
BuildRequires: protobuf-devel
BuildRequires: libutempter-devel
-BuildRequires: zlib-devel
BuildRequires: ncurses-devel
Requires: openssh-clients
Requires: perl-IO-Tty
diff --git a/src/network/Makefile.am b/src/network/Makefile.am
index 3143cc4..2768e6e 100644
--- a/src/network/Makefile.am
+++ b/src/network/Makefile.am
@@ -3,4 +3,4 @@ AM_CXXFLAGS = $(WARNING_CXXFLAGS) $(PICKY_CXXFLAGS) $(HARDEN_CFLAGS) $(MISC_CXXF
noinst_LIBRARIES = libmoshnetwork.a
-libmoshnetwork_a_SOURCES = network.cc network.h networktransport.cc networktransport.h transportfragment.cc transportfragment.h transportsender.cc transportsender.h transportstate.h compressor.cc compressor.h
+libmoshnetwork_a_SOURCES = network.cc network.h networktransport.cc networktransport.h transportfragment.cc transportfragment.h transportsender.cc transportsender.h transportstate.h
diff --git a/src/network/compressor.cc b/src/network/compressor.cc
deleted file mode 100644
index 37c95c5..0000000
--- a/src/network/compressor.cc
+++ /dev/null
@@ -1,32 +0,0 @@
-#include <zlib.h>
-
-#include "compressor.h"
-#include "dos_assert.h"
-
-using namespace Network;
-using namespace std;
-
-string Compressor::compress_str( const string &input )
-{
- long unsigned int len = BUFFER_SIZE;
- dos_assert( Z_OK == compress( buffer, &len,
- reinterpret_cast<const unsigned char *>( input.data() ),
- input.size() ) );
- return string( reinterpret_cast<char *>( buffer ), len );
-}
-
-string Compressor::uncompress_str( const string &input )
-{
- long unsigned int len = BUFFER_SIZE;
- dos_assert( Z_OK == uncompress( buffer, &len,
- reinterpret_cast<const unsigned char *>( input.data() ),
- input.size() ) );
- return string( reinterpret_cast<char *>( buffer ), len );
-}
-
-/* construct on first use */
-Compressor & Network::get_compressor( void )
-{
- static Compressor the_compressor;
- return the_compressor;
-}
diff --git a/src/network/compressor.h b/src/network/compressor.h
deleted file mode 100644
index ffeca99..0000000
--- a/src/network/compressor.h
+++ /dev/null
@@ -1,28 +0,0 @@
-#ifndef COMPRESSOR_H
-#define COMPRESSOR_H
-
-#include <string>
-
-namespace Network {
- class Compressor {
- private:
- static const int BUFFER_SIZE = 2048 * 2048; /* effective limit on terminal size */
-
- unsigned char *buffer;
-
- public:
- Compressor() : buffer( NULL ) { buffer = new unsigned char[ BUFFER_SIZE ]; }
- ~Compressor() { if ( buffer ) { delete[] buffer; } }
-
- std::string compress_str( const std::string &input );
- std::string uncompress_str( const std::string &input );
-
- /* unused */
- Compressor( const Compressor & );
- Compressor & operator=( const Compressor & );
- };
-
- Compressor & get_compressor( void );
-}
-
-#endif
diff --git a/src/network/transportfragment.cc b/src/network/transportfragment.cc
index 2aeffd5..53eae91 100644
--- a/src/network/transportfragment.cc
+++ b/src/network/transportfragment.cc
@@ -17,13 +17,15 @@
*/
#include <assert.h>
+#include <google/protobuf/io/gzip_stream.h>
+#include <google/protobuf/io/zero_copy_stream_impl.h>
#include "byteorder.h"
#include "transportfragment.h"
#include "transportinstruction.pb.h"
-#include "compressor.h"
#include "fatal_assert.h"
+using namespace google::protobuf::io;
using namespace Network;
using namespace TransportBuffers;
@@ -115,15 +117,24 @@ Instruction FragmentAssembly::get_assembly( void )
{
assert( fragments_arrived == fragments_total );
- string encoded;
-
+ ZeroCopyInputStream **streams = new ZeroCopyInputStream *[fragments_total];
for ( int i = 0; i < fragments_total; i++ ) {
assert( fragments.at( i ).initialized );
- encoded += fragments.at( i ).contents;
+ streams[i] = new ArrayInputStream( fragments.at( i ).contents.data(),
+ fragments.at( i ).contents.size() );
}
Instruction ret;
- fatal_assert( ret.ParseFromString( get_compressor().uncompress_str( encoded ) ) );
+ {
+ ConcatenatingInputStream stream( streams, fragments_total );
+ GzipInputStream gzip_stream( &stream, GzipInputStream::ZLIB );
+ fatal_assert( ret.ParseFromZeroCopyStream( &gzip_stream ) );
+ }
+
+ for ( int i = 0; i < fragments_total; i++ ) {
+ delete streams[i];
+ }
+ delete[] streams;
fragments.clear();
fragments_arrived = 0;
@@ -158,7 +169,18 @@ vector<Fragment> Fragmenter::make_fragments( const Instruction &inst, int MTU )
last_instruction = inst;
last_MTU = MTU;
- string payload = get_compressor().compress_str( inst.SerializeAsString() );
+ string payload;
+ {
+ StringOutputStream stream( &payload );
+ GzipOutputStream::Options gzip_options;
+ gzip_options.format = GzipOutputStream::ZLIB;
+ GzipOutputStream gzip_stream( &stream, gzip_options );
+ fatal_assert( inst.SerializeToZeroCopyStream( &gzip_stream ) );
+ if ( !gzip_stream.Close() ) {
+ throw std::string( "zlib error: " ) + gzip_stream.ZlibErrorMessage();
+ }
+ }
+
uint16_t fragment_num = 0;
vector<Fragment> ret;