|
|
@@ -387,11 +387,11 @@ req_thread(void *arg __unused) |
|
|
|
buf = NULL; |
|
|
|
break; |
|
|
|
|
|
|
|
case BIO_DELETE: |
|
|
|
case BIO_FLUSH: |
|
|
|
greq->r_ggio.gctl_data = NULL; |
|
|
|
break; |
|
|
|
|
|
|
|
case BIO_DELETE: |
|
|
|
default: |
|
|
|
greq->r_ggio.gctl_error = EOPNOTSUPP; |
|
|
|
g_gate_ioctl(G_GATE_CMD_DONE, &greq->r_ggio); |
|
|
@@ -426,6 +426,27 @@ req_thread(void *arg __unused) |
|
|
|
return (NULL); |
|
|
|
} |
|
|
|
|
|
|
|
static const char * |
|
|
|
sftperrno_str(int err) |
|
|
|
{ |
|
|
|
const char *strs[] = { |
|
|
|
[0] = "ok", |
|
|
|
[1] = "eof", |
|
|
|
[2] = "no such file", |
|
|
|
[3] = "permission denied", |
|
|
|
[4] = "failure", |
|
|
|
[5] = "bad message", |
|
|
|
[6] = "no connection", |
|
|
|
[7] = "connection lost", |
|
|
|
[8] = "op unsupported", |
|
|
|
}; |
|
|
|
|
|
|
|
if (err < 0 || err >= (int)nitems(strs)) |
|
|
|
return "invalid errno"; |
|
|
|
|
|
|
|
return strs[err]; |
|
|
|
} |
|
|
|
|
|
|
|
static int |
|
|
|
process_pending(struct ggs_reqqueue *req_pending, |
|
|
|
struct ggs_sessqueue *sessqueue) |
|
|
@@ -433,6 +454,7 @@ process_pending(struct ggs_reqqueue *req_pending, |
|
|
|
struct ggs_req *greq, *greq2; |
|
|
|
char *errmsg; |
|
|
|
int rc; |
|
|
|
int sftperrno; |
|
|
|
int didwork; |
|
|
|
|
|
|
|
didwork = 0; |
|
|
@@ -505,6 +527,38 @@ again: |
|
|
|
/* NOTREACHABLE */ |
|
|
|
break; |
|
|
|
|
|
|
|
case BIO_DELETE: |
|
|
|
g_gate_log(LOG_DEBUG, "sftp_punchhole(%p)", greq); |
|
|
|
rc = libssh2_sftp_punchhole(greq->r_handle, |
|
|
|
greq->r_ggio.gctl_offset, greq->r_ggio.gctl_length); |
|
|
|
|
|
|
|
didwork = 1; /* assume this always does work */ |
|
|
|
switch (rc) { |
|
|
|
case LIBSSH2_ERROR_SFTP_PROTOCOL: |
|
|
|
greq->r_ggio.gctl_error = EOPNOTSUPP; |
|
|
|
sftperrno = libssh2_sftp_last_error( |
|
|
|
greq->r_session); |
|
|
|
g_gate_log(LOG_DEBUG, "sftp_punchhole(%p) errno: %s(%d)", greq, |
|
|
|
sftperrno_str(sftperrno), sftperrno); |
|
|
|
goto completeio; |
|
|
|
|
|
|
|
case LIBSSH2_ERROR_EAGAIN: |
|
|
|
continue; |
|
|
|
|
|
|
|
case 0: /* success */ |
|
|
|
goto completeio; |
|
|
|
|
|
|
|
default: |
|
|
|
libssh2_session_last_error(greq->r_ssh_session, |
|
|
|
&errmsg, NULL, 0); |
|
|
|
g_gate_log(LOG_ERR, "sftp_punchhole(%p) ret %d: %s", |
|
|
|
greq, rc, errmsg); |
|
|
|
greq->r_ggio.gctl_error = EIO; |
|
|
|
goto completeio; |
|
|
|
} |
|
|
|
/* NOTREACHABLE */ |
|
|
|
break; |
|
|
|
|
|
|
|
default: |
|
|
|
rc = 0; |
|
|
|
g_gate_log(LOG_ERR, "unhandled op: %d", |
|
|
|