integrate packageManager into servers
diff --git a/request-server.go b/request-server.go
index 95fdf3f..4d70373 100644
--- a/request-server.go
+++ b/request-server.go
@@ -1,6 +1,7 @@
 package sftp
 
 import (
+	"encoding"
 	"io"
 	"os"
 	"path/filepath"
@@ -28,6 +29,7 @@
 	serverConn
 	Handlers        Handlers
 	pktChan         chan requestPacket
+	pktMgr          packetManager
 	openRequests    map[string]Request
 	openRequestLock sync.RWMutex
 	handleCount     int
@@ -36,15 +38,17 @@
 // NewRequestServer creates/allocates/returns new RequestServer.
 // Normally there there will be one server per user-session.
 func NewRequestServer(rwc io.ReadWriteCloser, h Handlers) *RequestServer {
-	return &RequestServer{
-		serverConn: serverConn{
-			conn: conn{
-				Reader:      rwc,
-				WriteCloser: rwc,
-			},
+	svrConn := serverConn{
+		conn: conn{
+			Reader:      rwc,
+			WriteCloser: rwc,
 		},
+	}
+	return &RequestServer{
+		serverConn:   svrConn,
 		Handlers:     h,
 		pktChan:      make(chan requestPacket, sftpServerWorkerCount),
+		pktMgr:       newPktMgr(&svrConn),
 		openRequests: make(map[string]Request),
 	}
 }
@@ -91,6 +95,7 @@
 	}
 
 	var err error
+	var pkt requestPacket
 	var pktType uint8
 	var pktBytes []byte
 	for {
@@ -98,15 +103,19 @@
 		if err != nil {
 			break
 		}
-		pkt, err := makePacket(rxPacket{fxp(pktType), pktBytes})
+		pkt, err = makePacket(rxPacket{fxp(pktType), pktBytes})
 		if err != nil {
+			debug("makePacket err: %v", err)
+			rs.conn.Close() // shuts down recvPacket
 			break
 		}
+		rs.pktMgr.incomingPacket(pkt)
 		rs.pktChan <- pkt
 	}
 
 	close(rs.pktChan) // shuts down sftpServerWorkers
 	wg.Wait()         // wait for all workers to exit
+	rs.pktMgr.close() // shuts down packetManager
 	return err
 }
 
@@ -176,6 +185,20 @@
 	return rpkt
 }
 
+// Wrap underlying connection methods to use packetManager
+func (rs RequestServer) sendPacket(m encoding.BinaryMarshaler) error {
+	if pkt, ok := m.(responsePacket); ok {
+		rs.pktMgr.readyPacket(pkt)
+	} else {
+		return errors.Errorf("unexpected packet type %T", m)
+	}
+	return nil
+}
+
+func (rs RequestServer) sendError(p ider, err error) error {
+	return rs.sendPacket(statusFromError(p, err))
+}
+
 // os.ErrNotExist should convert to ssh_FX_NO_SUCH_FILE, but is not recognized
 // by statusFromError. So we convert to syscall.ENOENT which it does.
 func errorAdapter(err error) error {
diff --git a/server.go b/server.go
index f0bbb8b..cf200b1 100644
--- a/server.go
+++ b/server.go
@@ -30,6 +30,7 @@
 	debugStream   io.Writer
 	readOnly      bool
 	pktChan       chan requestPacket
+	pktMgr        packetManager
 	openFiles     map[string]*os.File
 	openFilesLock sync.RWMutex
 	handleCount   int
@@ -75,15 +76,17 @@
 //
 // A subsequent call to Serve() is required to begin serving files over SFTP.
 func NewServer(rwc io.ReadWriteCloser, options ...ServerOption) (*Server, error) {
-	s := &Server{
-		serverConn: serverConn{
-			conn: conn{
-				Reader:      rwc,
-				WriteCloser: rwc,
-			},
+	svrConn := serverConn{
+		conn: conn{
+			Reader:      rwc,
+			WriteCloser: rwc,
 		},
+	}
+	s := &Server{
+		serverConn:  svrConn,
 		debugStream: ioutil.Discard,
 		pktChan:     make(chan requestPacket, sftpServerWorkerCount),
+		pktMgr:      newPktMgr(&svrConn),
 		openFiles:   make(map[string]*os.File),
 		maxTxPacket: 1 << 15,
 	}
@@ -303,15 +306,18 @@
 
 		pkt, err = makePacket(rxPacket{fxp(pktType), pktBytes})
 		if err != nil {
+			debug("makePacket err: %v", err)
 			svr.conn.Close() // shuts down recvPacket
 			break
 		}
 
+		svr.pktMgr.incomingPacket(pkt)
 		svr.pktChan <- pkt
 	}
 
 	close(svr.pktChan) // shuts down sftpServerWorkers
 	wg.Wait()          // wait for all workers to exit
+	svr.pktMgr.close() // shuts down packetManager
 
 	// close any still-open files
 	for handle, file := range svr.openFiles {
@@ -321,6 +327,20 @@
 	return err // error from recvPacket
 }
 
+// Wrap underlying connection methods to use packetManager
+func (svr Server) sendPacket(m encoding.BinaryMarshaler) error {
+	if pkt, ok := m.(responsePacket); ok {
+		svr.pktMgr.readyPacket(pkt)
+	} else {
+		return errors.Errorf("unexpected packet type %T", m)
+	}
+	return nil
+}
+
+func (svr Server) sendError(p ider, err error) error {
+	return svr.sendPacket(statusFromError(p, err))
+}
+
 type ider interface {
 	id() uint32
 }