From d141ba49f3bb21048ab7249f72878d4575af5e7b Mon Sep 17 00:00:00 2001
From: James Housley <jim@thehousleys.net>
Date: Wed, 6 Jun 2007 19:52:11 +0000
Subject: [PATCH] Make libssh2_sftp_write() be fully non-blocking.  The state
 of the socket is fully honored.  LIBSSH2SFTP_EAGAIN is returned when the call
 would block.

---
 example/simple/sftp_RW_nonblock.c    |   4 +-
 example/simple/sftp_write_nonblock.c |   4 +-
 include/libssh2_sftp.h               |   5 +-
 src/libssh2_priv.h                   |  37 +-----
 src/sftp.c                           | 185 +++++++++------------------
 5 files changed, 70 insertions(+), 165 deletions(-)

diff --git a/example/simple/sftp_RW_nonblock.c b/example/simple/sftp_RW_nonblock.c
index df87ccc..377c2ec 100644
--- a/example/simple/sftp_RW_nonblock.c
+++ b/example/simple/sftp_RW_nonblock.c
@@ -1,5 +1,5 @@
 /*
- * $Id: sftp_RW_nonblock.c,v 1.4 2007/06/06 12:34:08 jehousley Exp $
+ * $Id: sftp_RW_nonblock.c,v 1.5 2007/06/06 19:52:11 jehousley Exp $
  *
  * Sample showing how to do SFTP transfers in a non-blocking manner.
  *
@@ -241,7 +241,7 @@ int main(int argc, char *argv[])
 
                         do {
                                 /* write data in a loop until we block */
-                                rc = libssh2_sftp_writenb(sftp_handle, ptr,
+                                rc = libssh2_sftp_write(sftp_handle, ptr,
 							  nread);
 				ptr += rc;
 				nread -= nread;
diff --git a/example/simple/sftp_write_nonblock.c b/example/simple/sftp_write_nonblock.c
index 647607d..a009e94 100644
--- a/example/simple/sftp_write_nonblock.c
+++ b/example/simple/sftp_write_nonblock.c
@@ -1,5 +1,5 @@
 /*
- * $Id: sftp_write_nonblock.c,v 1.4 2007/06/06 12:34:09 jehousley Exp $
+ * $Id: sftp_write_nonblock.c,v 1.5 2007/06/06 19:52:11 jehousley Exp $
  *
  * Sample showing how to do SFTP non-blocking write transfers.
  *
@@ -196,7 +196,7 @@ int main(int argc, char *argv[])
         
         do {
             /* write data in a loop until we block */
-            while ((rc = libssh2_sftp_writenb(sftp_handle, ptr, nread)) == LIBSSH2SFTP_EAGAIN) {
+            while ((rc = libssh2_sftp_write(sftp_handle, ptr, nread)) == LIBSSH2SFTP_EAGAIN) {
                 ;
             }
             ptr += rc;
diff --git a/include/libssh2_sftp.h b/include/libssh2_sftp.h
index 633d92f..cb5d220 100644
--- a/include/libssh2_sftp.h
+++ b/include/libssh2_sftp.h
@@ -198,10 +198,7 @@ LIBSSH2_API int libssh2_sftp_readdir(LIBSSH2_SFTP_HANDLE *handle, char *buffer,
 LIBSSH2_API int libssh2_sftp_readdirnb(LIBSSH2_SFTP_HANDLE *handle, char *buffer, 
                                        size_t buffer_maxlen, LIBSSH2_SFTP_ATTRIBUTES *attrs);
 
-LIBSSH2_API ssize_t libssh2_sftp_write(LIBSSH2_SFTP_HANDLE *handle,
-                       const char *buffer, size_t count);
-LIBSSH2_API ssize_t libssh2_sftp_writenb(LIBSSH2_SFTP_HANDLE *handle,
-                     const char *buffer, size_t count);
+LIBSSH2_API ssize_t libssh2_sftp_write(LIBSSH2_SFTP_HANDLE *handle, const char *buffer, size_t count);
 
 LIBSSH2_API int libssh2_sftp_close_handle(LIBSSH2_SFTP_HANDLE *handle);
 #define libssh2_sftp_close(handle)                  libssh2_sftp_close_handle(handle)
diff --git a/src/libssh2_priv.h b/src/libssh2_priv.h
index d02cba6..56a73c9 100644
--- a/src/libssh2_priv.h
+++ b/src/libssh2_priv.h
@@ -447,31 +447,6 @@ struct _LIBSSH2_PUBLICKEY {
     unsigned long               listFetch_data_len;
 };
 
-typedef enum {
-    sftp_read_idle = 0,
-    sftp_read_packet_allocated,
-    sftp_read_packet_created,
-    sftp_read_packet_sent
-} libssh2_sftp_read_state;
-
-typedef enum {
-    sftp_readdir_idle = 0,
-    sftp_readdir_packet_created,
-    sftp_readdir_packet_sent
-} libssh2_sftp_readdir_state;
-
-typedef enum {
-    sftp_write_idle = 0,
-    sftp_write_packet_created,
-    sftp_write_packet_sent
-} libssh2_sftp_write_state;
-
-typedef enum {
-    sftp_mkdir_idle = 0,
-    sftp_mkdir_packet_created,
-    sftp_mkdir_packet_sent
-} libssh2_sftp_mkdir_state;
-
 struct _LIBSSH2_SFTP_HANDLE {
     LIBSSH2_SFTP *sftp;
     LIBSSH2_SFTP_HANDLE *prev, *next;
@@ -513,23 +488,23 @@ struct _LIBSSH2_SFTP {
     time_t requirev_start;
     
     /* State variables used in _libssh2_sftp_read() */
-    libssh2_sftp_read_state read_state;
-    unsigned char           *read_packet;
-    unsigned long           read_request_id;
+    libssh2_nonblocking_states  read_state;
+    unsigned char               *read_packet;
+    unsigned long                   read_request_id;
     size_t                  read_total_read;
     
     /* State variables used in _libssh2_sftp_readdir() */
-    libssh2_sftp_readdir_state  readdir_state;
+    libssh2_nonblocking_states  readdir_state;
     unsigned char               *readdir_packet;
     unsigned long               readdir_request_id;
     
     /* State variables used in _libssh2_sftp_write() */
-    libssh2_sftp_write_state    write_state;
+    libssh2_nonblocking_states  write_state;
     unsigned char               *write_packet;
     unsigned long               write_request_id;
     
     /* State variables used in _libssh2_sftp_mkdir() */
-    libssh2_sftp_mkdir_state    mkdir_state;
+    libssh2_nonblocking_states  mkdir_state;
     unsigned char               *mkdir_packet;
     unsigned long               mkdir_request_id;
     
diff --git a/src/sftp.c b/src/sftp.c
index 6494159..a1cd3a3 100644
--- a/src/sftp.c
+++ b/src/sftp.c
@@ -793,14 +793,14 @@ static ssize_t _libssh2_sftp_read(LIBSSH2_SFTP_HANDLE *handle, char *buffer,
     size_t total_read = 0;
     int retcode;
     
-    if (sftp->read_state == sftp_read_idle) {
+    if (sftp->read_state == libssh2_NB_state_idle) {
         _libssh2_debug(session, LIBSSH2_DBG_SFTP, "Reading %lu bytes from SFTP handle", (unsigned long)buffer_maxlen);
         packet = LIBSSH2_ALLOC(session, packet_len);
         if (!packet) {
             libssh2_error(session, LIBSSH2_ERROR_ALLOC, "Unable to allocate memory for FXP_CLOSE packet", 0);
             return -1;
         }
-        sftp->read_state = sftp_read_packet_allocated;
+        sftp->read_state = libssh2_NB_state_allocated;
     } else {
         packet = sftp->read_packet;
         request_id = sftp->read_request_id;
@@ -824,7 +824,7 @@ static ssize_t _libssh2_sftp_read(LIBSSH2_SFTP_HANDLE *handle, char *buffer,
         _libssh2_debug(session, LIBSSH2_DBG_SFTP, "Requesting %lu bytes from SFTP handle", (unsigned long)bytes_requested);
 #endif
         
-        if (sftp->read_state == sftp_read_packet_allocated) {
+        if (sftp->read_state == libssh2_NB_state_allocated) {
             libssh2_htonu32(s, packet_len - 4);
             s += 4;
             *(s++) = SSH_FXP_READ;
@@ -843,17 +843,17 @@ static ssize_t _libssh2_sftp_read(LIBSSH2_SFTP_HANDLE *handle, char *buffer,
             libssh2_htonu32(s, buffer_maxlen);
             s += 4;
             
-            sftp->read_state = sftp_read_packet_created;
+            sftp->read_state = libssh2_NB_state_created;
         }
         
-        if (sftp->read_state != sftp_read_packet_sent) {
+        if (sftp->read_state != libssh2_NB_state_sent) {
             if (libssh2_session_get_blocking(channel->session)) {
                 while ((retcode = libssh2_channel_write_ex(channel, 0, (char *)packet, packet_len)) == PACKET_EAGAIN);
                 if (packet_len != retcode) {
                     libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send FXP_READ command", 0);
                     LIBSSH2_FREE(session, packet);
                     sftp->read_packet = NULL;
-                    sftp->read_state = sftp_read_idle;
+                    sftp->read_state = libssh2_NB_state_idle;
                     return -1;
                 }
             } else {
@@ -867,14 +867,14 @@ static ssize_t _libssh2_sftp_read(LIBSSH2_SFTP_HANDLE *handle, char *buffer,
                     libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send FXP_READ command", 0);
                     LIBSSH2_FREE(session, packet);
                     sftp->read_packet = NULL;
-                    sftp->read_state = sftp_read_idle;
+                    sftp->read_state = libssh2_NB_state_idle;
                     return -1;
                 }
             }
             sftp->read_packet = packet;
             sftp->read_request_id = request_id;
             sftp->read_total_read = total_read;
-            sftp->read_state = sftp_read_packet_sent;
+            sftp->read_state = libssh2_NB_state_sent;
         }
         
         retcode = libssh2_sftp_packet_requirev(sftp, 2, read_responses, request_id, &data, &data_len);
@@ -885,7 +885,7 @@ static ssize_t _libssh2_sftp_read(LIBSSH2_SFTP_HANDLE *handle, char *buffer,
             libssh2_error(session, LIBSSH2_ERROR_SOCKET_TIMEOUT, "Timeout waiting for status message", 0);
             LIBSSH2_FREE(session, packet);
             sftp->read_packet = NULL;
-            sftp->read_state = sftp_read_idle;
+            sftp->read_state = libssh2_NB_state_idle;
             return -1;
         }
         
@@ -895,7 +895,7 @@ static ssize_t _libssh2_sftp_read(LIBSSH2_SFTP_HANDLE *handle, char *buffer,
                 LIBSSH2_FREE(session, packet);
                 LIBSSH2_FREE(session, data);
                 sftp->read_packet = NULL;
-                sftp->read_state = sftp_read_idle;
+                sftp->read_state = libssh2_NB_state_idle;
                 
                 if (retcode == LIBSSH2_FX_EOF) {
                     return total_read;
@@ -910,7 +910,7 @@ static ssize_t _libssh2_sftp_read(LIBSSH2_SFTP_HANDLE *handle, char *buffer,
                 if (bytes_read > (data_len - 9)) {
                     LIBSSH2_FREE(session, packet);
                     sftp->read_packet = NULL;
-                    sftp->read_state = sftp_read_idle;
+                    sftp->read_state = libssh2_NB_state_idle;
                     return -1;
                 }
 #ifdef LIBSSH2_DEBUG_SFTP
@@ -924,13 +924,13 @@ static ssize_t _libssh2_sftp_read(LIBSSH2_SFTP_HANDLE *handle, char *buffer,
                  * Set the state back to allocated, so a new one will be
                  * created to either request more data or get EOF
                  */
-                sftp->read_state = sftp_read_packet_allocated;
+                sftp->read_state = libssh2_NB_state_allocated;
         }
     }
     
     LIBSSH2_FREE(session, packet);
     sftp->read_packet = NULL;
-    sftp->read_state = sftp_read_idle;
+    sftp->read_state = libssh2_NB_state_idle;
     return total_read;
 }
 /* {{{ libssh2_sftp_read
@@ -1003,7 +1003,7 @@ static int _libssh2_sftp_readdir(LIBSSH2_SFTP_HANDLE *handle, char *buffer, size
     unsigned char read_responses[2] = { SSH_FXP_NAME, SSH_FXP_STATUS };
     int retcode;
     
-    if (sftp->readdir_state == sftp_readdir_idle) {
+    if (sftp->readdir_state == libssh2_NB_state_idle) {
         if (handle->u.dir.names_left) {
             /*
              * A prior request returned more than one directory entry, 
@@ -1062,23 +1062,23 @@ static int _libssh2_sftp_readdir(LIBSSH2_SFTP_HANDLE *handle, char *buffer, size
         memcpy(s, handle->handle, handle->handle_len);
         s += handle->handle_len;
         
-        sftp->readdir_state = sftp_readdir_packet_created;
+        sftp->readdir_state = libssh2_NB_state_created;
     }
-    else if (sftp->readdir_state == sftp_readdir_packet_created) {
+    else if (sftp->readdir_state == libssh2_NB_state_created) {
         packet = sftp->readdir_packet;
         request_id = sftp->readdir_request_id;
         sftp->readdir_packet = NULL;
     }
         
     
-    if (sftp->readdir_state != sftp_readdir_packet_sent) {
+    if (sftp->readdir_state != libssh2_NB_state_sent) {
         _libssh2_debug(session, LIBSSH2_DBG_SFTP, "Reading entries from directory handle");
         if (libssh2_session_get_blocking(channel->session)) {
             while ((retcode = libssh2_channel_write_ex(channel, 0, (char *)packet, packet_len)) == PACKET_EAGAIN);
             if (packet_len != retcode) {
                 libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send FXP_READ command", 0);
                 LIBSSH2_FREE(session, packet);
-                sftp->readdir_state = sftp_readdir_idle;
+                sftp->readdir_state = libssh2_NB_state_idle;
                 return -1;
             }
         } else {
@@ -1090,13 +1090,13 @@ static int _libssh2_sftp_readdir(LIBSSH2_SFTP_HANDLE *handle, char *buffer, size
             else if (packet_len != retcode) {
                 libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send FXP_READ command", 0);
                 LIBSSH2_FREE(session, packet);
-                sftp->readdir_state = sftp_readdir_idle;
+                sftp->readdir_state = libssh2_NB_state_idle;
                 return -1;
             }
         }
         
         LIBSSH2_FREE(session, packet);
-        sftp->readdir_state = sftp_readdir_packet_sent;
+        sftp->readdir_state = libssh2_NB_state_sent;
         sftp->readdir_packet = NULL;
     }
 
@@ -1106,7 +1106,7 @@ static int _libssh2_sftp_readdir(LIBSSH2_SFTP_HANDLE *handle, char *buffer, size
     }
     else if (retcode) {
         libssh2_error(session, LIBSSH2_ERROR_SOCKET_TIMEOUT, "Timeout waiting for status message", 0);
-        sftp->readdir_state = sftp_readdir_idle;
+        sftp->readdir_state = libssh2_NB_state_idle;
         return -1;
     }
 
@@ -1114,12 +1114,12 @@ static int _libssh2_sftp_readdir(LIBSSH2_SFTP_HANDLE *handle, char *buffer, size
         retcode = libssh2_ntohu32(data + 5);
         LIBSSH2_FREE(session, data);
         if (retcode == LIBSSH2_FX_EOF) {
-            sftp->readdir_state = sftp_readdir_idle;
+            sftp->readdir_state = libssh2_NB_state_idle;
             return 0;
         } else {
             sftp->last_errno = retcode;
             libssh2_error(session, LIBSSH2_ERROR_SFTP_PROTOCOL, "SFTP Protocol Error", 0);
-            sftp->readdir_state = sftp_readdir_idle;
+            sftp->readdir_state = libssh2_NB_state_idle;
             return -1;
         }
     }
@@ -1128,7 +1128,7 @@ static int _libssh2_sftp_readdir(LIBSSH2_SFTP_HANDLE *handle, char *buffer, size
     _libssh2_debug(session, LIBSSH2_DBG_SFTP, "%lu entries returned", num_names);
     if (num_names <= 0) {
         LIBSSH2_FREE(session, data);
-        sftp->readdir_state = sftp_readdir_idle;
+        sftp->readdir_state = libssh2_NB_state_idle;
         return (num_names == 0) ? 0 : -1;
     }
 
@@ -1153,7 +1153,7 @@ static int _libssh2_sftp_readdir(LIBSSH2_SFTP_HANDLE *handle, char *buffer, size
         }
         LIBSSH2_FREE(session, data);
 
-        sftp->readdir_state = sftp_readdir_idle;
+        sftp->readdir_state = libssh2_NB_state_idle;
         return filename_len;
     }
 
@@ -1161,7 +1161,7 @@ static int _libssh2_sftp_readdir(LIBSSH2_SFTP_HANDLE *handle, char *buffer, size
     handle->u.dir.names_packet = data;
     handle->u.dir.next_name = (char *)data + 9;
 
-    sftp->readdir_state = sftp_readdir_idle;
+    sftp->readdir_state = libssh2_NB_state_idle;
     
     /* Be lazy, just use the name popping mechanism from the start of the function */
     return libssh2_sftp_readdir(handle, buffer, buffer_maxlen, attrs);
@@ -1220,83 +1220,68 @@ LIBSSH2_API int libssh2_sftp_readdirnb(LIBSSH2_SFTP_HANDLE *handle, char *buffer
 }
 /* }}} */
 
-/* {{{ _libssh2_sftp_write
+/* {{{ libssh2_sftp_write
  * Write data to a file handle
  */
-/* _libssh2_sftp_write - NB-SAFE */
-static ssize_t _libssh2_sftp_write(LIBSSH2_SFTP_HANDLE *handle, const char *buffer, size_t count)
+LIBSSH2_API ssize_t libssh2_sftp_write(LIBSSH2_SFTP_HANDLE *handle, const char *buffer, size_t count)
 {
     LIBSSH2_SFTP    *sftp    = handle->sftp;
     LIBSSH2_CHANNEL *channel = sftp->channel;
     LIBSSH2_SESSION *session = channel->session;
-    unsigned long data_len, request_id, retcode;
+    unsigned long data_len, retcode;
     /* 25 = packet_len(4) + packet_type(1) + request_id(4) + handle_len(4) + offset(8) + count(4) */
     ssize_t packet_len = handle->handle_len + count + 25;
-    unsigned char *packet, *s, *data;
+    unsigned char *s, *data;
     int rc;
     
-    if (sftp->write_state == sftp_write_idle) {
+    if (sftp->write_state == libssh2_NB_state_idle) {
         _libssh2_debug(session, LIBSSH2_DBG_SFTP, "Writing %lu bytes", (unsigned long)count);
-        s = packet = LIBSSH2_ALLOC(session, packet_len);
-        if (!packet) {
+        s = sftp->write_packet = LIBSSH2_ALLOC(session, packet_len);
+        if (!sftp->write_packet) {
             libssh2_error(session, LIBSSH2_ERROR_ALLOC, "Unable to allocate memory for FXP_WRITE packet", 0);
             return -1;
         }
         
         libssh2_htonu32(s, packet_len - 4);             s += 4;
         *(s++) = SSH_FXP_WRITE;
-        request_id = sftp->request_id++;
-        libssh2_htonu32(s, request_id);                 s += 4;
+        sftp->write_request_id = sftp->request_id++;
+        libssh2_htonu32(s, sftp->write_request_id);     s += 4;
         libssh2_htonu32(s, handle->handle_len);         s += 4;
         memcpy(s, handle->handle, handle->handle_len);  s += handle->handle_len;
         libssh2_htonu64(s, handle->u.file.offset);      s += 8;
         libssh2_htonu32(s, count);                      s += 4;
         memcpy(s, buffer, count);                       s += count;
         
-        sftp->write_state = sftp_write_packet_created;
-    } else {
-        packet = sftp->write_packet;
-        request_id = sftp->write_request_id;
+        sftp->write_state = libssh2_NB_state_created;
     }
     
-    if (sftp->write_state != sftp_write_packet_sent) {
-        if (libssh2_session_get_blocking(channel->session)) {
-            while ((rc = libssh2_channel_write_ex(channel, 0, (char *)packet, packet_len)) == PACKET_EAGAIN);
-            if (packet_len != rc) {
-                libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send FXP_READ command", 0);
-                LIBSSH2_FREE(session, packet);
-                sftp->write_state = sftp_write_idle;
-                return -1;
-            }
-        } else {
-            if ((rc = libssh2_channel_write_ex(channel, 0, (char *)packet, packet_len)) == PACKET_EAGAIN) {
-                sftp->write_packet = packet;
-                sftp->write_request_id = request_id;
-                return PACKET_EAGAIN;
-            }
-            if (packet_len != rc) {
-                libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send FXP_READ command", 0);
-                LIBSSH2_FREE(session, packet);
-                sftp->write_state = sftp_write_idle;
-                return -1;
-            }
+    if (sftp->write_state == libssh2_NB_state_created) {
+        if ((rc = libssh2_channel_write_ex(channel, 0, (char *)sftp->write_packet, packet_len)) == PACKET_EAGAIN) {
+            return PACKET_EAGAIN;
         }
-        LIBSSH2_FREE(session, packet);
-        sftp->write_state = sftp_write_packet_sent;
+        if (packet_len != rc) {
+            libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send FXP_READ command", 0);
+            LIBSSH2_FREE(session, sftp->write_packet);
+            sftp->write_packet = NULL;
+            sftp->write_state = libssh2_NB_state_idle;
+            return -1;
+        }
+        LIBSSH2_FREE(session, sftp->write_packet);
         sftp->write_packet = NULL;
+        sftp->write_state = libssh2_NB_state_sent;
     }
     
-    rc = libssh2_sftp_packet_require(sftp, SSH_FXP_STATUS, request_id, &data, &data_len);
+    rc = libssh2_sftp_packet_require(sftp, SSH_FXP_STATUS, sftp->write_request_id, &data, &data_len);
     if (rc == PACKET_EAGAIN) {
         return PACKET_EAGAIN;
     }
     else if (rc) {
         libssh2_error(session, LIBSSH2_ERROR_SOCKET_TIMEOUT, "Timeout waiting for status message", 0);
-        sftp->write_state = sftp_write_idle;
+        sftp->write_state = libssh2_NB_state_idle;
         return -1;
     }
     
-    sftp->write_state = sftp_write_idle;
+    sftp->write_state = libssh2_NB_state_idle;
     
     retcode = libssh2_ntohu32(data + 5);
     LIBSSH2_FREE(session, data);
@@ -1312,58 +1297,6 @@ static ssize_t _libssh2_sftp_write(LIBSSH2_SFTP_HANDLE *handle, const char *buff
 }
 /* }}} */
 
-/* {{{ libssh2_sftp_write
- * Write data to a SFTP handle blocking
- */
-/* libssh2_sftp_write - NB-UNSAFE */
-LIBSSH2_API ssize_t libssh2_sftp_write(LIBSSH2_SFTP_HANDLE *handle,
-                                       const char *buffer, size_t count)
-{
-    ssize_t rc;
-    LIBSSH2_CHANNEL *ch = handle->sftp->channel;
-    int bl = libssh2_session_get_blocking(ch->session);
-    
-    /* set blocking */
-    libssh2_channel_set_blocking(ch, 1);
-    
-    rc = _libssh2_sftp_write(handle, buffer, count);
-    
-    /* restore state */
-    libssh2_channel_set_blocking(ch, bl);
-    
-    if (rc < 0) {
-        /* precent accidental returning of other return codes since
-        this API does not support/provide those */
-        return -1;
-    }
-    
-    return rc;
-}
-/* }}} */
-
-/* {{{ libssh2_sftp_write
- * Write data to a SFTP handle non-blocking
- */
-/* libssh2_sftp_writenb - NB-SAFE */
-LIBSSH2_API ssize_t libssh2_sftp_writenb(LIBSSH2_SFTP_HANDLE *handle,
-                                         const char *buffer, size_t count)
-{
-    ssize_t rc;
-    LIBSSH2_CHANNEL *ch = handle->sftp->channel;
-    int bl = libssh2_session_get_blocking(ch->session);
-    
-    /* set non-blocking */
-    libssh2_channel_set_blocking(ch, 0);
-    
-    rc = _libssh2_sftp_write(handle, buffer, count);
-    
-    /* restore state */
-    libssh2_channel_set_blocking(ch, bl);
-    
-    return rc;
-}
-/* }}} */
-
 /* {{{ libssh2_sftp_fstat_ex
  * Get or Set stat on a file
  */
@@ -1681,7 +1614,7 @@ static int _libssh2_sftp_mkdir_ex(LIBSSH2_SFTP *sftp, const char *path, unsigned
     unsigned char *packet, *s, *data;
     int rc;
     
-    if (sftp->mkdir_state == sftp_mkdir_idle) {
+    if (sftp->mkdir_state == libssh2_NB_state_idle) {
         _libssh2_debug(session, LIBSSH2_DBG_SFTP, "Creating directory %s with mode 0%lo", path, mode);
         s = packet = LIBSSH2_ALLOC(session, packet_len);
         if (!packet) {
@@ -1699,19 +1632,19 @@ static int _libssh2_sftp_mkdir_ex(LIBSSH2_SFTP *sftp, const char *path, unsigned
         memcpy(s, path, path_len);                  s += path_len;
         s += libssh2_sftp_attr2bin(s, &attrs);
         
-        sftp->mkdir_state = sftp_mkdir_packet_created;
+        sftp->mkdir_state = libssh2_NB_state_created;
     } else {
         packet = sftp->mkdir_packet;
         request_id = sftp->mkdir_request_id;
     }
     
-    if (sftp->mkdir_state != sftp_mkdir_packet_sent) {
+    if (sftp->mkdir_state != libssh2_NB_state_created) {
         if (libssh2_session_get_blocking(channel->session)) {
             while ((rc = libssh2_channel_write_ex(channel, 0, (char *)packet, packet_len)) == PACKET_EAGAIN);
             if (packet_len != rc) {
                 libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send FXP_READ command", 0);
                 LIBSSH2_FREE(session, packet);
-                sftp->mkdir_state = sftp_mkdir_idle;
+                sftp->mkdir_state = libssh2_NB_state_idle;
                 return -1;
             }
         } else {
@@ -1723,12 +1656,12 @@ static int _libssh2_sftp_mkdir_ex(LIBSSH2_SFTP *sftp, const char *path, unsigned
             if (packet_len != rc) {
                 libssh2_error(session, LIBSSH2_ERROR_SOCKET_SEND, "Unable to send FXP_READ command", 0);
                 LIBSSH2_FREE(session, packet);
-                sftp->mkdir_state = sftp_mkdir_idle;
+                sftp->mkdir_state = libssh2_NB_state_idle;
                 return -1;
             }
         }
         LIBSSH2_FREE(session, packet);
-        sftp->mkdir_state = sftp_mkdir_packet_sent;
+        sftp->mkdir_state = libssh2_NB_state_sent;
         sftp->mkdir_packet = NULL;
     }
     
@@ -1738,11 +1671,11 @@ static int _libssh2_sftp_mkdir_ex(LIBSSH2_SFTP *sftp, const char *path, unsigned
     }
     else if (rc) {
         libssh2_error(session, LIBSSH2_ERROR_SOCKET_TIMEOUT, "Timeout waiting for status message", 0);
-        sftp->mkdir_state = sftp_mkdir_idle;
+        sftp->mkdir_state = libssh2_NB_state_idle;
         return -1;
     }
     
-    sftp->mkdir_state = sftp_mkdir_idle;
+    sftp->mkdir_state = libssh2_NB_state_idle;
     
     retcode = libssh2_ntohu32(data + 5);
     LIBSSH2_FREE(session, data);