|
Lines 266-285
ssh_packet_set_connection(struct ssh *ssh, int fd_in, int fd_out)
Link Here
|
| 266 |
const struct sshcipher *none = cipher_by_name("none"); |
266 |
const struct sshcipher *none = cipher_by_name("none"); |
| 267 |
int r; |
267 |
int r; |
| 268 |
|
268 |
|
| 269 |
if (none == NULL) |
269 |
if (none == NULL) { |
| 270 |
fatal("%s: cannot load cipher 'none'", __func__); |
270 |
error("%s: cannot load cipher 'none'", __func__); |
|
|
271 |
return NULL; |
| 272 |
} |
| 271 |
if (ssh == NULL) |
273 |
if (ssh == NULL) |
| 272 |
ssh = ssh_alloc_session_state(); |
274 |
ssh = ssh_alloc_session_state(); |
| 273 |
if (ssh == NULL) |
275 |
if (ssh == NULL) { |
| 274 |
fatal("%s: cound not allocate state", __func__); |
276 |
error("%s: cound not allocate state", __func__); |
|
|
277 |
return NULL; |
| 278 |
} |
| 275 |
state = ssh->state; |
279 |
state = ssh->state; |
| 276 |
state->connection_in = fd_in; |
280 |
state->connection_in = fd_in; |
| 277 |
state->connection_out = fd_out; |
281 |
state->connection_out = fd_out; |
| 278 |
if ((r = cipher_init(&state->send_context, none, |
282 |
if ((r = cipher_init(&state->send_context, none, |
| 279 |
(const u_char *)"", 0, NULL, 0, CIPHER_ENCRYPT)) != 0 || |
283 |
(const u_char *)"", 0, NULL, 0, CIPHER_ENCRYPT)) != 0 || |
| 280 |
(r = cipher_init(&state->receive_context, none, |
284 |
(r = cipher_init(&state->receive_context, none, |
| 281 |
(const u_char *)"", 0, NULL, 0, CIPHER_DECRYPT)) != 0) |
285 |
(const u_char *)"", 0, NULL, 0, CIPHER_DECRYPT)) != 0) { |
| 282 |
fatal("%s: cipher_init failed: %s", __func__, ssh_err(r)); |
286 |
error("%s: cipher_init failed: %s", __func__, ssh_err(r)); |
|
|
287 |
return NULL; |
| 288 |
} |
| 283 |
state->newkeys[MODE_IN] = state->newkeys[MODE_OUT] = NULL; |
289 |
state->newkeys[MODE_IN] = state->newkeys[MODE_OUT] = NULL; |
| 284 |
deattack_init(&state->deattack); |
290 |
deattack_init(&state->deattack); |
| 285 |
return ssh; |
291 |
return ssh; |
|
Lines 882-889
ssh_packet_send1(struct ssh *ssh)
Link Here
|
| 882 |
|
888 |
|
| 883 |
/* |
889 |
/* |
| 884 |
* Note that the packet is now only buffered in output. It won't be |
890 |
* Note that the packet is now only buffered in output. It won't be |
| 885 |
* actually sent until packet_write_wait or packet_write_poll is |
891 |
* actually sent until ssh_packet_write_wait or ssh_packet_write_poll |
| 886 |
* called. |
892 |
* is called. |
| 887 |
*/ |
893 |
*/ |
| 888 |
r = 0; |
894 |
r = 0; |
| 889 |
out: |
895 |
out: |
|
Lines 1252-1259
ssh_packet_read_seqnr(struct ssh *ssh, u_char *typep, u_int32_t *seqnr_p)
Link Here
|
| 1252 |
if (setp == NULL) |
1258 |
if (setp == NULL) |
| 1253 |
return SSH_ERR_ALLOC_FAIL; |
1259 |
return SSH_ERR_ALLOC_FAIL; |
| 1254 |
|
1260 |
|
| 1255 |
/* Since we are blocking, ensure that all written packets have been sent. */ |
1261 |
/* |
| 1256 |
ssh_packet_write_wait(ssh); |
1262 |
* Since we are blocking, ensure that all written packets have |
|
|
1263 |
* been sent. |
| 1264 |
*/ |
| 1265 |
if ((r = ssh_packet_write_wait(ssh)) != 0) |
| 1266 |
return r; |
| 1257 |
|
1267 |
|
| 1258 |
/* Stay in the loop until we have received a complete packet. */ |
1268 |
/* Stay in the loop until we have received a complete packet. */ |
| 1259 |
for (;;) { |
1269 |
for (;;) { |
|
Lines 1339-1354
ssh_packet_read(struct ssh *ssh)
Link Here
|
| 1339 |
* that given, and gives a fatal error and exits if there is a mismatch. |
1349 |
* that given, and gives a fatal error and exits if there is a mismatch. |
| 1340 |
*/ |
1350 |
*/ |
| 1341 |
|
1351 |
|
| 1342 |
void |
1352 |
int |
| 1343 |
ssh_packet_read_expect(struct ssh *ssh, int expected_type) |
1353 |
ssh_packet_read_expect(struct ssh *ssh, u_int expected_type) |
| 1344 |
{ |
1354 |
{ |
| 1345 |
int type; |
1355 |
int r; |
|
|
1356 |
u_char type; |
| 1346 |
|
1357 |
|
| 1347 |
type = ssh_packet_read(ssh); |
1358 |
if ((r = ssh_packet_read_seqnr(ssh, &type, NULL)) != 0) |
| 1348 |
if (type != expected_type) |
1359 |
return r; |
| 1349 |
ssh_packet_disconnect(ssh, |
1360 |
if (type != expected_type) { |
|
|
1361 |
if ((r = sshpkt_disconnect(ssh, |
| 1350 |
"Protocol error: expected packet type %d, got %d", |
1362 |
"Protocol error: expected packet type %d, got %d", |
| 1351 |
expected_type, type); |
1363 |
expected_type, type)) != 0) |
|
|
1364 |
return r; |
| 1365 |
return SSH_ERR_PROTOCOL_ERROR; |
| 1366 |
} |
| 1367 |
return 0; |
| 1352 |
} |
1368 |
} |
| 1353 |
|
1369 |
|
| 1354 |
/* Checks if a full packet is available in the data received so far via |
1370 |
/* Checks if a full packet is available in the data received so far via |
|
Lines 1365-1370
ssh_packet_read_poll1(struct ssh *ssh, u_char *typep)
Link Here
|
| 1365 |
{ |
1381 |
{ |
| 1366 |
struct session_state *state = ssh->state; |
1382 |
struct session_state *state = ssh->state; |
| 1367 |
u_int len, padded_len; |
1383 |
u_int len, padded_len; |
|
|
1384 |
const char *emsg; |
| 1368 |
const u_char *cp; |
1385 |
const u_char *cp; |
| 1369 |
u_char *p; |
1386 |
u_char *p; |
| 1370 |
u_int checksum, stored_checksum; |
1387 |
u_int checksum, stored_checksum; |
|
Lines 1377-1385
ssh_packet_read_poll1(struct ssh *ssh, u_char *typep)
Link Here
|
| 1377 |
return 0; |
1394 |
return 0; |
| 1378 |
/* Get length of incoming packet. */ |
1395 |
/* Get length of incoming packet. */ |
| 1379 |
len = PEEK_U32(sshbuf_ptr(state->input)); |
1396 |
len = PEEK_U32(sshbuf_ptr(state->input)); |
| 1380 |
if (len < 1 + 2 + 2 || len > 256 * 1024) |
1397 |
if (len < 1 + 2 + 2 || len > 256 * 1024) { |
| 1381 |
ssh_packet_disconnect(ssh, "Bad packet length %u.", |
1398 |
if ((r = sshpkt_disconnect(ssh, "Bad packet length %u", |
| 1382 |
len); |
1399 |
len)) != 0) |
|
|
1400 |
return r; |
| 1401 |
return SSH_ERR_CONN_CORRUPT; |
| 1402 |
} |
| 1383 |
padded_len = (len + 8) & ~7; |
1403 |
padded_len = (len + 8) & ~7; |
| 1384 |
|
1404 |
|
| 1385 |
/* Check if the packet has been entirely received. */ |
1405 |
/* Check if the packet has been entirely received. */ |
|
Lines 1398-1416
ssh_packet_read_poll1(struct ssh *ssh, u_char *typep)
Link Here
|
| 1398 |
* Ariel Futoransky(futo@core-sdi.com) |
1418 |
* Ariel Futoransky(futo@core-sdi.com) |
| 1399 |
*/ |
1419 |
*/ |
| 1400 |
if (!state->receive_context.plaintext) { |
1420 |
if (!state->receive_context.plaintext) { |
|
|
1421 |
emsg = NULL; |
| 1401 |
switch (detect_attack(&state->deattack, |
1422 |
switch (detect_attack(&state->deattack, |
| 1402 |
sshbuf_ptr(state->input), padded_len)) { |
1423 |
sshbuf_ptr(state->input), padded_len)) { |
| 1403 |
case DEATTACK_OK: |
1424 |
case DEATTACK_OK: |
| 1404 |
break; |
1425 |
break; |
| 1405 |
case DEATTACK_DETECTED: |
1426 |
case DEATTACK_DETECTED: |
| 1406 |
ssh_packet_disconnect(ssh, |
1427 |
emsg = "crc32 compensation attack detected"; |
| 1407 |
"crc32 compensation attack: network attack detected" |
1428 |
break; |
| 1408 |
); |
|
|
| 1409 |
case DEATTACK_DOS_DETECTED: |
1429 |
case DEATTACK_DOS_DETECTED: |
| 1410 |
ssh_packet_disconnect(ssh, |
1430 |
emsg = "deattack denial of service detected"; |
| 1411 |
"deattack denial of service detected"); |
1431 |
break; |
| 1412 |
default: |
1432 |
default: |
| 1413 |
ssh_packet_disconnect(ssh, "deattack error"); |
1433 |
emsg = "deattack error"; |
|
|
1434 |
break; |
| 1435 |
} |
| 1436 |
if (emsg != NULL) { |
| 1437 |
error("%s", emsg); |
| 1438 |
if ((r = sshpkt_disconnect(ssh, "%s", emsg)) != 0 || |
| 1439 |
(r = ssh_packet_write_wait(ssh)) != 0) |
| 1440 |
return r; |
| 1441 |
return SSH_ERR_CONN_CORRUPT; |
| 1414 |
} |
1442 |
} |
| 1415 |
} |
1443 |
} |
| 1416 |
|
1444 |
|
|
Lines 1439-1454
ssh_packet_read_poll1(struct ssh *ssh, u_char *typep)
Link Here
|
| 1439 |
goto out; |
1467 |
goto out; |
| 1440 |
|
1468 |
|
| 1441 |
/* Test check bytes. */ |
1469 |
/* Test check bytes. */ |
| 1442 |
if (len != sshbuf_len(state->incoming_packet)) |
1470 |
if (len != sshbuf_len(state->incoming_packet)) { |
| 1443 |
ssh_packet_disconnect(ssh, |
1471 |
error("%s: len %d != sshbuf_len %zd", __func__, |
| 1444 |
"packet_read_poll1: len %d != sshbuf_len %zd.", |
|
|
| 1445 |
len, sshbuf_len(state->incoming_packet)); |
1472 |
len, sshbuf_len(state->incoming_packet)); |
|
|
1473 |
if ((r = sshpkt_disconnect(ssh, "invalid packet length")) != 0 || |
| 1474 |
(r = ssh_packet_write_wait(ssh)) != 0) |
| 1475 |
return r; |
| 1476 |
return SSH_ERR_CONN_CORRUPT; |
| 1477 |
} |
| 1446 |
|
1478 |
|
| 1447 |
cp = sshbuf_ptr(state->incoming_packet) + len - 4; |
1479 |
cp = sshbuf_ptr(state->incoming_packet) + len - 4; |
| 1448 |
stored_checksum = PEEK_U32(cp); |
1480 |
stored_checksum = PEEK_U32(cp); |
| 1449 |
if (checksum != stored_checksum) |
1481 |
if (checksum != stored_checksum) { |
| 1450 |
ssh_packet_disconnect(ssh, |
1482 |
error("Corrupted check bytes on input"); |
| 1451 |
"Corrupted check bytes on input."); |
1483 |
if ((r = sshpkt_disconnect(ssh, "connection corrupted")) != 0 || |
|
|
1484 |
(r = ssh_packet_write_wait(ssh)) != 0) |
| 1485 |
return r; |
| 1486 |
return SSH_ERR_CONN_CORRUPT; |
| 1487 |
} |
| 1452 |
if ((r = sshbuf_consume_end(state->incoming_packet, 4)) < 0) |
1488 |
if ((r = sshbuf_consume_end(state->incoming_packet, 4)) < 0) |
| 1453 |
goto out; |
1489 |
goto out; |
| 1454 |
|
1490 |
|
|
Lines 1466-1474
ssh_packet_read_poll1(struct ssh *ssh, u_char *typep)
Link Here
|
| 1466 |
state->p_read.bytes += padded_len + 4; |
1502 |
state->p_read.bytes += padded_len + 4; |
| 1467 |
if ((r = sshbuf_get_u8(state->incoming_packet, typep)) != 0) |
1503 |
if ((r = sshbuf_get_u8(state->incoming_packet, typep)) != 0) |
| 1468 |
goto out; |
1504 |
goto out; |
| 1469 |
if (*typep < SSH_MSG_MIN || *typep > SSH_MSG_MAX) |
1505 |
if (*typep < SSH_MSG_MIN || *typep > SSH_MSG_MAX) { |
| 1470 |
ssh_packet_disconnect(ssh, |
1506 |
error("Invalid ssh1 packet type: %d", *typep); |
| 1471 |
"Invalid ssh1 packet type: %d", *typep); |
1507 |
if ((r = sshpkt_disconnect(ssh, "invalid packet type")) != 0 || |
|
|
1508 |
(r = ssh_packet_write_wait(ssh)) != 0) |
| 1509 |
return r; |
| 1510 |
return SSH_ERR_PROTOCOL_ERROR; |
| 1511 |
} |
| 1472 |
r = 0; |
1512 |
r = 0; |
| 1473 |
out: |
1513 |
out: |
| 1474 |
return r; |
1514 |
return r; |
|
Lines 1622-1628
ssh_packet_read_poll2(struct ssh *ssh, u_char *typep, u_int32_t *seqnr_p)
Link Here
|
| 1622 |
if ((r = sshbuf_consume(state->input, mac->mac_len)) != 0) |
1662 |
if ((r = sshbuf_consume(state->input, mac->mac_len)) != 0) |
| 1623 |
goto out; |
1663 |
goto out; |
| 1624 |
} |
1664 |
} |
| 1625 |
/* XXX now it's safe to use fatal/packet_disconnect */ |
|
|
| 1626 |
if (seqnr_p != NULL) |
1665 |
if (seqnr_p != NULL) |
| 1627 |
*seqnr_p = state->p_read.seqnr; |
1666 |
*seqnr_p = state->p_read.seqnr; |
| 1628 |
if (++state->p_read.seqnr == 0) |
1667 |
if (++state->p_read.seqnr == 0) |
|
Lines 1636-1644
ssh_packet_read_poll2(struct ssh *ssh, u_char *typep, u_int32_t *seqnr_p)
Link Here
|
| 1636 |
/* get padlen */ |
1675 |
/* get padlen */ |
| 1637 |
padlen = sshbuf_ptr(state->incoming_packet)[4]; |
1676 |
padlen = sshbuf_ptr(state->incoming_packet)[4]; |
| 1638 |
DBG(debug("input: padlen %d", padlen)); |
1677 |
DBG(debug("input: padlen %d", padlen)); |
| 1639 |
if (padlen < 4) |
1678 |
if (padlen < 4) { |
| 1640 |
ssh_packet_disconnect(ssh, |
1679 |
if ((r = sshpkt_disconnect(ssh, |
| 1641 |
"Corrupted padlen %d on input.", padlen); |
1680 |
"Corrupted padlen %d on input.", padlen)) != 0 || |
|
|
1681 |
(r = ssh_packet_write_wait(ssh)) != 0) |
| 1682 |
return r; |
| 1683 |
return SSH_ERR_CONN_CORRUPT; |
| 1684 |
} |
| 1642 |
|
1685 |
|
| 1643 |
/* skip packet size + padlen, discard padding */ |
1686 |
/* skip packet size + padlen, discard padding */ |
| 1644 |
if ((r = sshbuf_consume(state->incoming_packet, 4 + 1)) != 0 || |
1687 |
if ((r = sshbuf_consume(state->incoming_packet, 4 + 1)) != 0 || |
|
Lines 1665-1673
ssh_packet_read_poll2(struct ssh *ssh, u_char *typep, u_int32_t *seqnr_p)
Link Here
|
| 1665 |
*/ |
1708 |
*/ |
| 1666 |
if ((r = sshbuf_get_u8(state->incoming_packet, typep)) != 0) |
1709 |
if ((r = sshbuf_get_u8(state->incoming_packet, typep)) != 0) |
| 1667 |
goto out; |
1710 |
goto out; |
| 1668 |
if (*typep < SSH2_MSG_MIN || *typep >= SSH2_MSG_LOCAL_MIN) |
1711 |
if (*typep < SSH2_MSG_MIN || *typep >= SSH2_MSG_LOCAL_MIN) { |
| 1669 |
ssh_packet_disconnect(ssh, |
1712 |
if ((r = sshpkt_disconnect(ssh, |
| 1670 |
"Invalid ssh2 packet type: %d", *typep); |
1713 |
"Invalid ssh2 packet type: %d", *typep)) != 0 || |
|
|
1714 |
(r = ssh_packet_write_wait(ssh)) != 0) |
| 1715 |
return r; |
| 1716 |
return SSH_ERR_PROTOCOL_ERROR; |
| 1717 |
} |
| 1671 |
if (*typep == SSH2_MSG_NEWKEYS) |
1718 |
if (*typep == SSH2_MSG_NEWKEYS) |
| 1672 |
r = ssh_set_newkeys(ssh, MODE_IN); |
1719 |
r = ssh_set_newkeys(ssh, MODE_IN); |
| 1673 |
else if (*typep == SSH2_MSG_USERAUTH_SUCCESS && !state->server_side) |
1720 |
else if (*typep == SSH2_MSG_USERAUTH_SUCCESS && !state->server_side) |
|
Lines 1804-1812
ssh_packet_remaining(struct ssh *ssh)
Link Here
|
| 1804 |
* message is printed immediately, but only if the client is being executed |
1851 |
* message is printed immediately, but only if the client is being executed |
| 1805 |
* in verbose mode. These messages are primarily intended to ease debugging |
1852 |
* in verbose mode. These messages are primarily intended to ease debugging |
| 1806 |
* authentication problems. The length of the formatted message must not |
1853 |
* authentication problems. The length of the formatted message must not |
| 1807 |
* exceed 1024 bytes. This will automatically call packet_write_wait. |
1854 |
* exceed 1024 bytes. This will automatically call ssh_packet_write_wait. |
| 1808 |
*/ |
1855 |
*/ |
| 1809 |
|
|
|
| 1810 |
void |
1856 |
void |
| 1811 |
ssh_packet_send_debug(struct ssh *ssh, const char *fmt,...) |
1857 |
ssh_packet_send_debug(struct ssh *ssh, const char *fmt,...) |
| 1812 |
{ |
1858 |
{ |
|
Lines 1834-1840
ssh_packet_send_debug(struct ssh *ssh, const char *fmt,...)
Link Here
|
| 1834 |
(r = sshpkt_send(ssh)) != 0) |
1880 |
(r = sshpkt_send(ssh)) != 0) |
| 1835 |
fatal("%s: %s", __func__, ssh_err(r)); |
1881 |
fatal("%s: %s", __func__, ssh_err(r)); |
| 1836 |
} |
1882 |
} |
| 1837 |
ssh_packet_write_wait(ssh); |
1883 |
if ((r = ssh_packet_write_wait(ssh)) != 0) |
|
|
1884 |
fatal("%s: %s", __func__, ssh_err(r)); |
| 1885 |
} |
| 1886 |
|
| 1887 |
/* |
| 1888 |
* Pretty-print connection-terminating errors and exit. |
| 1889 |
*/ |
| 1890 |
void |
| 1891 |
sshpkt_fatal(struct ssh *ssh, const char *tag, int r) |
| 1892 |
{ |
| 1893 |
switch (r) { |
| 1894 |
case SSH_ERR_CONN_CLOSED: |
| 1895 |
logit("Connection closed by %.200s", ssh_remote_ipaddr(ssh)); |
| 1896 |
cleanup_exit(255); |
| 1897 |
case SSH_ERR_CONN_TIMEOUT: |
| 1898 |
logit("Connection to %.200s timed out while " |
| 1899 |
"waiting to write", ssh_remote_ipaddr(ssh)); |
| 1900 |
cleanup_exit(255); |
| 1901 |
default: |
| 1902 |
fatal("%s: Connection to %.200s: %s", |
| 1903 |
tag != NULL ? tag : "", tag != NULL ? ": " : "", |
| 1904 |
ssh_err(r)); |
| 1905 |
} |
| 1838 |
} |
1906 |
} |
| 1839 |
|
1907 |
|
| 1840 |
/* |
1908 |
/* |
|
Lines 1843-1849
ssh_packet_send_debug(struct ssh *ssh, const char *fmt,...)
Link Here
|
| 1843 |
* should not contain a newline. The length of the formatted message must |
1911 |
* should not contain a newline. The length of the formatted message must |
| 1844 |
* not exceed 1024 bytes. |
1912 |
* not exceed 1024 bytes. |
| 1845 |
*/ |
1913 |
*/ |
| 1846 |
|
|
|
| 1847 |
void |
1914 |
void |
| 1848 |
ssh_packet_disconnect(struct ssh *ssh, const char *fmt,...) |
1915 |
ssh_packet_disconnect(struct ssh *ssh, const char *fmt,...) |
| 1849 |
{ |
1916 |
{ |
|
Lines 1867-1896
ssh_packet_disconnect(struct ssh *ssh, const char *fmt,...)
Link Here
|
| 1867 |
/* Display the error locally */ |
1934 |
/* Display the error locally */ |
| 1868 |
logit("Disconnecting: %.100s", buf); |
1935 |
logit("Disconnecting: %.100s", buf); |
| 1869 |
|
1936 |
|
| 1870 |
/* Send the disconnect message to the other side, and wait for it to get sent. */ |
1937 |
/* |
| 1871 |
if (compat20) { |
1938 |
* Send the disconnect message to the other side, and wait |
| 1872 |
if ((r = sshpkt_start(ssh, SSH2_MSG_DISCONNECT)) != 0 || |
1939 |
* for it to get sent. |
| 1873 |
(r = sshpkt_put_u32(ssh, SSH2_DISCONNECT_PROTOCOL_ERROR)) != 0 || |
1940 |
*/ |
| 1874 |
(r = sshpkt_put_cstring(ssh, buf)) != 0 || |
1941 |
if ((r = sshpkt_disconnect(ssh, "%s", buf)) != 0) |
| 1875 |
(r = sshpkt_put_cstring(ssh, "")) != 0 || |
1942 |
sshpkt_fatal(ssh, __func__, r); |
| 1876 |
(r = sshpkt_send(ssh)) != 0) |
1943 |
|
| 1877 |
fatal("%s: %s", __func__, ssh_err(r)); |
1944 |
if ((r = ssh_packet_write_wait(ssh)) != 0) |
| 1878 |
} else { |
1945 |
sshpkt_fatal(ssh, __func__, r); |
| 1879 |
if ((r = sshpkt_start(ssh, SSH_MSG_DISCONNECT)) != 0 || |
|
|
| 1880 |
(r = sshpkt_put_cstring(ssh, buf)) != 0 || |
| 1881 |
(r = sshpkt_send(ssh)) != 0) |
| 1882 |
fatal("%s: %s", __func__, ssh_err(r)); |
| 1883 |
} |
| 1884 |
ssh_packet_write_wait(ssh); |
| 1885 |
|
1946 |
|
| 1886 |
/* Close the connection. */ |
1947 |
/* Close the connection. */ |
| 1887 |
ssh_packet_close(ssh); |
1948 |
ssh_packet_close(ssh); |
| 1888 |
cleanup_exit(255); |
1949 |
cleanup_exit(255); |
| 1889 |
} |
1950 |
} |
| 1890 |
|
1951 |
|
| 1891 |
/* Checks if there is any buffered output, and tries to write some of the output. */ |
1952 |
/* |
| 1892 |
|
1953 |
* Checks if there is any buffered output, and tries to write some of |
| 1893 |
void |
1954 |
* the output. |
|
|
1955 |
*/ |
| 1956 |
int |
| 1894 |
ssh_packet_write_poll(struct ssh *ssh) |
1957 |
ssh_packet_write_poll(struct ssh *ssh) |
| 1895 |
{ |
1958 |
{ |
| 1896 |
struct session_state *state = ssh->state; |
1959 |
struct session_state *state = ssh->state; |
|
Lines 1903-1935
ssh_packet_write_poll(struct ssh *ssh)
Link Here
|
| 1903 |
sshbuf_ptr(state->output), len, &cont); |
1966 |
sshbuf_ptr(state->output), len, &cont); |
| 1904 |
if (len == -1) { |
1967 |
if (len == -1) { |
| 1905 |
if (errno == EINTR || errno == EAGAIN) |
1968 |
if (errno == EINTR || errno == EAGAIN) |
| 1906 |
return; |
1969 |
return 0; |
| 1907 |
fatal("Write failed: %.100s", strerror(errno)); |
1970 |
return SSH_ERR_SYSTEM_ERROR; |
| 1908 |
} |
1971 |
} |
| 1909 |
if (len == 0 && !cont) |
1972 |
if (len == 0 && !cont) |
| 1910 |
fatal("Write connection closed"); |
1973 |
return SSH_ERR_CONN_CLOSED; |
| 1911 |
if ((r = sshbuf_consume(state->output, len)) != 0) |
1974 |
if ((r = sshbuf_consume(state->output, len)) != 0) |
| 1912 |
fatal("%s: %s", __func__, ssh_err(r)); |
1975 |
return r; |
| 1913 |
} |
1976 |
} |
|
|
1977 |
return 0; |
| 1914 |
} |
1978 |
} |
| 1915 |
|
1979 |
|
| 1916 |
/* |
1980 |
/* |
| 1917 |
* Calls packet_write_poll repeatedly until all pending output data has been |
1981 |
* Calls packet_write_poll repeatedly until all pending output data has been |
| 1918 |
* written. |
1982 |
* written. |
| 1919 |
*/ |
1983 |
*/ |
| 1920 |
|
1984 |
int |
| 1921 |
void |
|
|
| 1922 |
ssh_packet_write_wait(struct ssh *ssh) |
1985 |
ssh_packet_write_wait(struct ssh *ssh) |
| 1923 |
{ |
1986 |
{ |
| 1924 |
fd_set *setp; |
1987 |
fd_set *setp; |
| 1925 |
int ret, ms_remain = 0; |
1988 |
int ret, r, ms_remain = 0; |
| 1926 |
struct timeval start, timeout, *timeoutp = NULL; |
1989 |
struct timeval start, timeout, *timeoutp = NULL; |
| 1927 |
struct session_state *state = ssh->state; |
1990 |
struct session_state *state = ssh->state; |
| 1928 |
|
1991 |
|
| 1929 |
setp = (fd_set *)calloc(howmany(state->connection_out + 1, |
1992 |
setp = (fd_set *)calloc(howmany(state->connection_out + 1, |
| 1930 |
NFDBITS), sizeof(fd_mask)); |
1993 |
NFDBITS), sizeof(fd_mask)); |
| 1931 |
if (setp == NULL) |
1994 |
if (setp == NULL) |
| 1932 |
fatal("%s: calloc failed", __func__); |
1995 |
return SSH_ERR_ALLOC_FAIL; |
| 1933 |
ssh_packet_write_poll(ssh); |
1996 |
ssh_packet_write_poll(ssh); |
| 1934 |
while (ssh_packet_have_data_to_write(ssh)) { |
1997 |
while (ssh_packet_have_data_to_write(ssh)) { |
| 1935 |
memset(setp, 0, howmany(state->connection_out + 1, |
1998 |
memset(setp, 0, howmany(state->connection_out + 1, |
|
Lines 1959-1971
ssh_packet_write_wait(struct ssh *ssh)
Link Here
|
| 1959 |
} |
2022 |
} |
| 1960 |
} |
2023 |
} |
| 1961 |
if (ret == 0) { |
2024 |
if (ret == 0) { |
| 1962 |
logit("Connection to %.200s timed out while " |
2025 |
free(setp); |
| 1963 |
"waiting to write", ssh_remote_ipaddr(ssh)); |
2026 |
return SSH_ERR_CONN_TIMEOUT; |
| 1964 |
cleanup_exit(255); |
2027 |
} |
|
|
2028 |
if ((r = ssh_packet_write_poll(ssh)) != 0) { |
| 2029 |
free(setp); |
| 2030 |
return r; |
| 1965 |
} |
2031 |
} |
| 1966 |
ssh_packet_write_poll(ssh); |
|
|
| 1967 |
} |
2032 |
} |
| 1968 |
free(setp); |
2033 |
free(setp); |
|
|
2034 |
return 0; |
| 1969 |
} |
2035 |
} |
| 1970 |
|
2036 |
|
| 1971 |
/* Returns true if there is buffered data to write to the connection. */ |
2037 |
/* Returns true if there is buffered data to write to the connection. */ |