summaryrefslogtreecommitdiff
path: root/clientloop.c
diff options
context:
space:
mode:
authordjm@openbsd.org <djm@openbsd.org>2019-01-19 21:33:57 +0000
committerDamien Miller <djm@mindrot.org>2019-01-20 09:02:36 +1100
commit23f22a4aaa923c61ec49a99ebaa383656e87fa40 (patch)
treeea5b6c7935eb2c910886e6f646f93f728bbd29c3 /clientloop.c
parentad60b1179c9682ca5aef0b346f99ef68cbbbc4e5 (diff)
upstream: convert clientloop.c to new packet API
with & ok markus@ OpenBSD-Commit-ID: 497b36500191f452a22abf283aa8d4a9abaee7fa
Diffstat (limited to 'clientloop.c')
-rw-r--r--clientloop.c287
1 files changed, 166 insertions, 121 deletions
diff --git a/clientloop.c b/clientloop.c
index d29ec00bc..5f87b24a2 100644
--- a/clientloop.c
+++ b/clientloop.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: clientloop.c,v 1.319 2019/01/19 21:31:32 djm Exp $ */ 1/* $OpenBSD: clientloop.c,v 1.320 2019/01/19 21:33:57 djm Exp $ */
2/* 2/*
3 * Author: Tatu Ylonen <ylo@cs.hut.fi> 3 * Author: Tatu Ylonen <ylo@cs.hut.fi>
4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland 4 * Copyright (c) 1995 Tatu Ylonen <ylo@cs.hut.fi>, Espoo, Finland
@@ -478,21 +478,24 @@ client_global_request_reply(int type, u_int32_t seq, struct ssh *ssh)
478 free(gc); 478 free(gc);
479 } 479 }
480 480
481 packet_set_alive_timeouts(0); 481 ssh_packet_set_alive_timeouts(ssh, 0);
482 return 0; 482 return 0;
483} 483}
484 484
485static void 485static void
486server_alive_check(void) 486server_alive_check(struct ssh *ssh)
487{ 487{
488 if (packet_inc_alive_timeouts() > options.server_alive_count_max) { 488 int r;
489
490 if (ssh_packet_inc_alive_timeouts(ssh) > options.server_alive_count_max) {
489 logit("Timeout, server %s not responding.", host); 491 logit("Timeout, server %s not responding.", host);
490 cleanup_exit(255); 492 cleanup_exit(255);
491 } 493 }
492 packet_start(SSH2_MSG_GLOBAL_REQUEST); 494 if ((r = sshpkt_start(ssh, SSH2_MSG_GLOBAL_REQUEST)) != 0 ||
493 packet_put_cstring("keepalive@openssh.com"); 495 (r = sshpkt_put_cstring(ssh, "keepalive@openssh.com")) != 0 ||
494 packet_put_char(1); /* boolean: want reply */ 496 (r = sshpkt_put_u8(ssh, 1)) != 0 || /* boolean: want reply */
495 packet_send(); 497 (r = sshpkt_send(ssh)) != 0)
498 fatal("%s: %s", __func__, ssh_err(r));
496 /* Insert an empty placeholder to maintain ordering */ 499 /* Insert an empty placeholder to maintain ordering */
497 client_register_global_confirm(NULL, NULL); 500 client_register_global_confirm(NULL, NULL);
498} 501}
@@ -517,7 +520,7 @@ client_wait_until_can_do_something(struct ssh *ssh,
517 520
518 /* channel_prepare_select could have closed the last channel */ 521 /* channel_prepare_select could have closed the last channel */
519 if (session_closed && !channel_still_open(ssh) && 522 if (session_closed && !channel_still_open(ssh) &&
520 !packet_have_data_to_write()) { 523 !ssh_packet_have_data_to_write(ssh)) {
521 /* clear mask since we did not call select() */ 524 /* clear mask since we did not call select() */
522 memset(*readsetp, 0, *nallocp); 525 memset(*readsetp, 0, *nallocp);
523 memset(*writesetp, 0, *nallocp); 526 memset(*writesetp, 0, *nallocp);
@@ -527,7 +530,7 @@ client_wait_until_can_do_something(struct ssh *ssh,
527 FD_SET(connection_in, *readsetp); 530 FD_SET(connection_in, *readsetp);
528 531
529 /* Select server connection if have data to write to the server. */ 532 /* Select server connection if have data to write to the server. */
530 if (packet_have_data_to_write()) 533 if (ssh_packet_have_data_to_write(ssh))
531 FD_SET(connection_out, *writesetp); 534 FD_SET(connection_out, *writesetp);
532 535
533 /* 536 /*
@@ -542,7 +545,8 @@ client_wait_until_can_do_something(struct ssh *ssh,
542 server_alive_time = now + options.server_alive_interval; 545 server_alive_time = now + options.server_alive_interval;
543 } 546 }
544 if (options.rekey_interval > 0 && !rekeying) 547 if (options.rekey_interval > 0 && !rekeying)
545 timeout_secs = MINIMUM(timeout_secs, packet_get_rekey_timeout()); 548 timeout_secs = MINIMUM(timeout_secs,
549 ssh_packet_get_rekey_timeout(ssh));
546 set_control_persist_exit_time(ssh); 550 set_control_persist_exit_time(ssh);
547 if (control_persist_exit_time > 0) { 551 if (control_persist_exit_time > 0) {
548 timeout_secs = MINIMUM(timeout_secs, 552 timeout_secs = MINIMUM(timeout_secs,
@@ -583,7 +587,7 @@ client_wait_until_can_do_something(struct ssh *ssh,
583 * Keepalive we check here, rekeying is checked in clientloop. 587 * Keepalive we check here, rekeying is checked in clientloop.
584 */ 588 */
585 if (server_alive_time != 0 && server_alive_time <= monotime()) 589 if (server_alive_time != 0 && server_alive_time <= monotime())
586 server_alive_check(); 590 server_alive_check(ssh);
587 } 591 }
588 592
589} 593}
@@ -615,7 +619,7 @@ client_suspend_self(struct sshbuf *bin, struct sshbuf *bout, struct sshbuf *berr
615} 619}
616 620
617static void 621static void
618client_process_net_input(fd_set *readset) 622client_process_net_input(struct ssh *ssh, fd_set *readset)
619{ 623{
620 char buf[SSH_IOBUFSZ]; 624 char buf[SSH_IOBUFSZ];
621 int r, len; 625 int r, len;
@@ -661,7 +665,7 @@ client_process_net_input(fd_set *readset)
661 quit_pending = 1; 665 quit_pending = 1;
662 return; 666 return;
663 } 667 }
664 packet_process_incoming(buf, len); 668 ssh_packet_process_incoming(ssh, buf, len);
665 } 669 }
666} 670}
667 671
@@ -1284,8 +1288,8 @@ client_loop(struct ssh *ssh, int have_pty, int escape_char_arg,
1284 /* Initialize variables. */ 1288 /* Initialize variables. */
1285 last_was_cr = 1; 1289 last_was_cr = 1;
1286 exit_status = -1; 1290 exit_status = -1;
1287 connection_in = packet_get_connection_in(); 1291 connection_in = ssh_packet_get_connection_in(ssh);
1288 connection_out = packet_get_connection_out(); 1292 connection_out = ssh_packet_get_connection_out(ssh);
1289 max_fd = MAXIMUM(connection_in, connection_out); 1293 max_fd = MAXIMUM(connection_in, connection_out);
1290 1294
1291 quit_pending = 0; 1295 quit_pending = 0;
@@ -1349,7 +1353,7 @@ client_loop(struct ssh *ssh, int have_pty, int escape_char_arg,
1349 * Make packets from buffered channel data, and 1353 * Make packets from buffered channel data, and
1350 * enqueue them for sending to the server. 1354 * enqueue them for sending to the server.
1351 */ 1355 */
1352 if (packet_not_very_much_data_to_write()) 1356 if (ssh_packet_not_very_much_data_to_write(ssh))
1353 channel_output_poll(ssh); 1357 channel_output_poll(ssh);
1354 1358
1355 /* 1359 /*
@@ -1377,7 +1381,7 @@ client_loop(struct ssh *ssh, int have_pty, int escape_char_arg,
1377 channel_after_select(ssh, readset, writeset); 1381 channel_after_select(ssh, readset, writeset);
1378 1382
1379 /* Buffer input from the connection. */ 1383 /* Buffer input from the connection. */
1380 client_process_net_input(readset); 1384 client_process_net_input(ssh, readset);
1381 1385
1382 if (quit_pending) 1386 if (quit_pending)
1383 break; 1387 break;
@@ -1387,7 +1391,7 @@ client_loop(struct ssh *ssh, int have_pty, int escape_char_arg,
1387 * sender. 1391 * sender.
1388 */ 1392 */
1389 if (FD_ISSET(connection_out, writeset)) 1393 if (FD_ISSET(connection_out, writeset))
1390 packet_write_poll(); 1394 ssh_packet_write_poll(ssh);
1391 1395
1392 /* 1396 /*
1393 * If we are a backgrounded control master, and the 1397 * If we are a backgrounded control master, and the
@@ -1409,12 +1413,13 @@ client_loop(struct ssh *ssh, int have_pty, int escape_char_arg,
1409 /* Stop watching for window change. */ 1413 /* Stop watching for window change. */
1410 signal(SIGWINCH, SIG_DFL); 1414 signal(SIGWINCH, SIG_DFL);
1411 1415
1412 packet_start(SSH2_MSG_DISCONNECT); 1416 if ((r = sshpkt_start(ssh, SSH2_MSG_DISCONNECT)) != 0 ||
1413 packet_put_int(SSH2_DISCONNECT_BY_APPLICATION); 1417 (r = sshpkt_put_u32(ssh, SSH2_DISCONNECT_BY_APPLICATION)) != 0 ||
1414 packet_put_cstring("disconnected by user"); 1418 (r = sshpkt_put_cstring(ssh, "disconnected by user")) != 0 ||
1415 packet_put_cstring(""); /* language tag */ 1419 (r = sshpkt_put_cstring(ssh, "")) != 0 || /* language tag */
1416 packet_send(); 1420 (r = sshpkt_send(ssh)) != 0 ||
1417 packet_write_wait(); 1421 (r = ssh_packet_write_wait(ssh)) != 0)
1422 fatal("%s: %s", __func__, ssh_err(r));
1418 1423
1419 channel_free_all(ssh); 1424 channel_free_all(ssh);
1420 1425
@@ -1471,7 +1476,7 @@ client_loop(struct ssh *ssh, int have_pty, int escape_char_arg,
1471 1476
1472 /* Report bytes transferred, and transfer rates. */ 1477 /* Report bytes transferred, and transfer rates. */
1473 total_time = monotime_double() - start_time; 1478 total_time = monotime_double() - start_time;
1474 packet_get_bytes(&ibytes, &obytes); 1479 ssh_packet_get_bytes(ssh, &ibytes, &obytes);
1475 verbose("Transferred: sent %llu, received %llu bytes, in %.1f seconds", 1480 verbose("Transferred: sent %llu, received %llu bytes, in %.1f seconds",
1476 (unsigned long long)obytes, (unsigned long long)ibytes, total_time); 1481 (unsigned long long)obytes, (unsigned long long)ibytes, total_time);
1477 if (total_time > 0) 1482 if (total_time > 0)
@@ -1491,21 +1496,29 @@ client_request_forwarded_tcpip(struct ssh *ssh, const char *request_type,
1491 Channel *c = NULL; 1496 Channel *c = NULL;
1492 struct sshbuf *b = NULL; 1497 struct sshbuf *b = NULL;
1493 char *listen_address, *originator_address; 1498 char *listen_address, *originator_address;
1494 u_short listen_port, originator_port; 1499 u_int listen_port, originator_port;
1495 int r; 1500 int r;
1496 1501
1497 /* Get rest of the packet */ 1502 /* Get rest of the packet */
1498 listen_address = packet_get_string(NULL); 1503 if ((r = sshpkt_get_cstring(ssh, &listen_address, NULL)) != 0 ||
1499 listen_port = packet_get_int(); 1504 (r = sshpkt_get_u32(ssh, &listen_port)) != 0 ||
1500 originator_address = packet_get_string(NULL); 1505 (r = sshpkt_get_cstring(ssh, &originator_address, NULL)) != 0 ||
1501 originator_port = packet_get_int(); 1506 (r = sshpkt_get_u32(ssh, &originator_port)) != 0 ||
1502 packet_check_eom(); 1507 (r = sshpkt_get_end(ssh)) != 0)
1508 fatal("%s: %s", __func__, ssh_err(r));
1503 1509
1504 debug("%s: listen %s port %d, originator %s port %d", __func__, 1510 debug("%s: listen %s port %d, originator %s port %d", __func__,
1505 listen_address, listen_port, originator_address, originator_port); 1511 listen_address, listen_port, originator_address, originator_port);
1506 1512
1507 c = channel_connect_by_listen_address(ssh, listen_address, listen_port, 1513 if (listen_port > 0xffff)
1508 "forwarded-tcpip", originator_address); 1514 error("%s: invalid listen port", __func__);
1515 else if (originator_port > 0xffff)
1516 error("%s: invalid originator port", __func__);
1517 else {
1518 c = channel_connect_by_listen_address(ssh,
1519 listen_address, listen_port, "forwarded-tcpip",
1520 originator_address);
1521 }
1509 1522
1510 if (c != NULL && c->type == SSH_CHANNEL_MUX_CLIENT) { 1523 if (c != NULL && c->type == SSH_CHANNEL_MUX_CLIENT) {
1511 if ((b = sshbuf_new()) == NULL) { 1524 if ((b = sshbuf_new()) == NULL) {
@@ -1543,13 +1556,13 @@ client_request_forwarded_streamlocal(struct ssh *ssh,
1543{ 1556{
1544 Channel *c = NULL; 1557 Channel *c = NULL;
1545 char *listen_path; 1558 char *listen_path;
1559 int r;
1546 1560
1547 /* Get the remote path. */ 1561 /* Get the remote path. */
1548 listen_path = packet_get_string(NULL); 1562 if ((r = sshpkt_get_cstring(ssh, &listen_path, NULL)) != 0 ||
1549 /* XXX: Skip reserved field for now. */ 1563 (r = sshpkt_get_string(ssh, NULL, NULL)) != 0 || /* reserved */
1550 if (packet_get_string_ptr(NULL) == NULL) 1564 (r = sshpkt_get_end(ssh)) != 0)
1551 fatal("%s: packet_get_string_ptr failed", __func__); 1565 fatal("%s: %s", __func__, ssh_err(r));
1552 packet_check_eom();
1553 1566
1554 debug("%s: %s", __func__, listen_path); 1567 debug("%s: %s", __func__, listen_path);
1555 1568
@@ -1564,8 +1577,8 @@ client_request_x11(struct ssh *ssh, const char *request_type, int rchan)
1564{ 1577{
1565 Channel *c = NULL; 1578 Channel *c = NULL;
1566 char *originator; 1579 char *originator;
1567 u_short originator_port; 1580 int originator_port;
1568 int sock; 1581 int r, sock;
1569 1582
1570 if (!options.forward_x11) { 1583 if (!options.forward_x11) {
1571 error("Warning: ssh server tried X11 forwarding."); 1584 error("Warning: ssh server tried X11 forwarding.");
@@ -1578,9 +1591,10 @@ client_request_x11(struct ssh *ssh, const char *request_type, int rchan)
1578 "expired"); 1591 "expired");
1579 return NULL; 1592 return NULL;
1580 } 1593 }
1581 originator = packet_get_string(NULL); 1594 if ((r = sshpkt_get_cstring(ssh, &originator, NULL)) != 0 ||
1582 originator_port = packet_get_int(); 1595 (r = sshpkt_get_u32(ssh, (u_int *)&originator_port)) != 0 ||
1583 packet_check_eom(); 1596 (r = sshpkt_get_end(ssh)) != 0)
1597 fatal("%s: %s", __func__, ssh_err(r));
1584 /* XXX check permission */ 1598 /* XXX check permission */
1585 debug("client_request_x11: request from %s %d", originator, 1599 debug("client_request_x11: request from %s %d", originator,
1586 originator_port); 1600 originator_port);
@@ -1626,7 +1640,7 @@ client_request_tun_fwd(struct ssh *ssh, int tun_mode,
1626 int local_tun, int remote_tun) 1640 int local_tun, int remote_tun)
1627{ 1641{
1628 Channel *c; 1642 Channel *c;
1629 int fd; 1643 int r, fd;
1630 char *ifname = NULL; 1644 char *ifname = NULL;
1631 1645
1632 if (tun_mode == SSH_TUNMODE_NO) 1646 if (tun_mode == SSH_TUNMODE_NO)
@@ -1651,14 +1665,15 @@ client_request_tun_fwd(struct ssh *ssh, int tun_mode,
1651 sys_tun_outfilter, NULL, NULL); 1665 sys_tun_outfilter, NULL, NULL);
1652#endif 1666#endif
1653 1667
1654 packet_start(SSH2_MSG_CHANNEL_OPEN); 1668 if ((r = sshpkt_start(ssh, SSH2_MSG_CHANNEL_OPEN)) != 0 ||
1655 packet_put_cstring("tun@openssh.com"); 1669 (r = sshpkt_put_cstring(ssh, "tun@openssh.com")) != 0 ||
1656 packet_put_int(c->self); 1670 (r = sshpkt_put_u32(ssh, c->self)) != 0 ||
1657 packet_put_int(c->local_window_max); 1671 (r = sshpkt_put_u32(ssh, c->local_window_max)) != 0 ||
1658 packet_put_int(c->local_maxpacket); 1672 (r = sshpkt_put_u32(ssh, c->local_maxpacket)) != 0 ||
1659 packet_put_int(tun_mode); 1673 (r = sshpkt_put_u32(ssh, tun_mode)) != 0 ||
1660 packet_put_int(remote_tun); 1674 (r = sshpkt_put_u32(ssh, remote_tun)) != 0 ||
1661 packet_send(); 1675 (r = sshpkt_send(ssh)) != 0)
1676 fatal("%s: %s", __func__, ssh_err(r));
1662 1677
1663 return ifname; 1678 return ifname;
1664} 1679}
@@ -1668,14 +1683,17 @@ static int
1668client_input_channel_open(int type, u_int32_t seq, struct ssh *ssh) 1683client_input_channel_open(int type, u_int32_t seq, struct ssh *ssh)
1669{ 1684{
1670 Channel *c = NULL; 1685 Channel *c = NULL;
1671 char *ctype; 1686 char *ctype = NULL;
1672 int rchan; 1687 int r;
1673 u_int rmaxpack, rwindow, len; 1688 u_int rchan;
1674 1689 size_t len;
1675 ctype = packet_get_string(&len); 1690 u_int rmaxpack, rwindow;
1676 rchan = packet_get_int(); 1691
1677 rwindow = packet_get_int(); 1692 if ((r = sshpkt_get_cstring(ssh, &ctype, &len)) != 0 ||
1678 rmaxpack = packet_get_int(); 1693 (r = sshpkt_get_u32(ssh, &rchan)) != 0 ||
1694 (r = sshpkt_get_u32(ssh, &rwindow)) != 0 ||
1695 (r = sshpkt_get_u32(ssh, &rmaxpack)) != 0)
1696 goto out;
1679 1697
1680 debug("client_input_channel_open: ctype %s rchan %d win %d max %d", 1698 debug("client_input_channel_open: ctype %s rchan %d win %d max %d",
1681 ctype, rchan, rwindow, rmaxpack); 1699 ctype, rchan, rwindow, rmaxpack);
@@ -1699,57 +1717,66 @@ client_input_channel_open(int type, u_int32_t seq, struct ssh *ssh)
1699 c->remote_window = rwindow; 1717 c->remote_window = rwindow;
1700 c->remote_maxpacket = rmaxpack; 1718 c->remote_maxpacket = rmaxpack;
1701 if (c->type != SSH_CHANNEL_CONNECTING) { 1719 if (c->type != SSH_CHANNEL_CONNECTING) {
1702 packet_start(SSH2_MSG_CHANNEL_OPEN_CONFIRMATION); 1720 if ((r = sshpkt_start(ssh, SSH2_MSG_CHANNEL_OPEN_CONFIRMATION)) != 0 ||
1703 packet_put_int(c->remote_id); 1721 (r = sshpkt_put_u32(ssh, c->remote_id)) != 0 ||
1704 packet_put_int(c->self); 1722 (r = sshpkt_put_u32(ssh, c->self)) != 0 ||
1705 packet_put_int(c->local_window); 1723 (r = sshpkt_put_u32(ssh, c->local_window)) != 0 ||
1706 packet_put_int(c->local_maxpacket); 1724 (r = sshpkt_put_u32(ssh, c->local_maxpacket)) != 0 ||
1707 packet_send(); 1725 (r = sshpkt_send(ssh)) != 0)
1726 sshpkt_fatal(ssh, r, "%s: send reply", __func__);
1708 } 1727 }
1709 } else { 1728 } else {
1710 debug("failure %s", ctype); 1729 debug("failure %s", ctype);
1711 packet_start(SSH2_MSG_CHANNEL_OPEN_FAILURE); 1730 if ((r = sshpkt_start(ssh, SSH2_MSG_CHANNEL_OPEN_FAILURE)) != 0 ||
1712 packet_put_int(rchan); 1731 (r = sshpkt_put_u32(ssh, rchan)) != 0 ||
1713 packet_put_int(SSH2_OPEN_ADMINISTRATIVELY_PROHIBITED); 1732 (r = sshpkt_put_u32(ssh, SSH2_OPEN_ADMINISTRATIVELY_PROHIBITED)) != 0 ||
1714 packet_put_cstring("open failed"); 1733 (r = sshpkt_put_cstring(ssh, "open failed")) != 0 ||
1715 packet_put_cstring(""); 1734 (r = sshpkt_put_cstring(ssh, "")) != 0 ||
1716 packet_send(); 1735 (r = sshpkt_send(ssh)) != 0)
1736 sshpkt_fatal(ssh, r, "%s: send failure", __func__);
1717 } 1737 }
1738 r = 0;
1739 out:
1718 free(ctype); 1740 free(ctype);
1719 return 0; 1741 return r;
1720} 1742}
1721 1743
1722static int 1744static int
1723client_input_channel_req(int type, u_int32_t seq, struct ssh *ssh) 1745client_input_channel_req(int type, u_int32_t seq, struct ssh *ssh)
1724{ 1746{
1725 Channel *c = NULL; 1747 Channel *c = NULL;
1726 int exitval, id, reply, success = 0; 1748 char *rtype = NULL;
1727 char *rtype; 1749 u_char reply;
1728 1750 u_int id, exitval;
1729 id = packet_get_int(); 1751 int r, success = 0;
1730 c = channel_lookup(ssh, id); 1752
1753 if ((r = sshpkt_get_u32(ssh, &id)) != 0)
1754 return r;
1755 if (id <= INT_MAX)
1756 c = channel_lookup(ssh, id);
1731 if (channel_proxy_upstream(c, type, seq, ssh)) 1757 if (channel_proxy_upstream(c, type, seq, ssh))
1732 return 0; 1758 return 0;
1733 rtype = packet_get_string(NULL); 1759 if ((r = sshpkt_get_cstring(ssh, &rtype, NULL)) != 0 ||
1734 reply = packet_get_char(); 1760 (r = sshpkt_get_u8(ssh, &reply)) != 0)
1761 goto out;
1735 1762
1736 debug("client_input_channel_req: channel %d rtype %s reply %d", 1763 debug("client_input_channel_req: channel %u rtype %s reply %d",
1737 id, rtype, reply); 1764 id, rtype, reply);
1738 1765
1739 if (id == -1) { 1766 if (c == NULL) {
1740 error("client_input_channel_req: request for channel -1");
1741 } else if (c == NULL) {
1742 error("client_input_channel_req: channel %d: " 1767 error("client_input_channel_req: channel %d: "
1743 "unknown channel", id); 1768 "unknown channel", id);
1744 } else if (strcmp(rtype, "eow@openssh.com") == 0) { 1769 } else if (strcmp(rtype, "eow@openssh.com") == 0) {
1745 packet_check_eom(); 1770 if ((r = sshpkt_get_end(ssh)) != 0)
1771 goto out;
1746 chan_rcvd_eow(ssh, c); 1772 chan_rcvd_eow(ssh, c);
1747 } else if (strcmp(rtype, "exit-status") == 0) { 1773 } else if (strcmp(rtype, "exit-status") == 0) {
1748 exitval = packet_get_int(); 1774 if ((r = sshpkt_get_u32(ssh, &exitval)) != 0)
1775 goto out;
1749 if (c->ctl_chan != -1) { 1776 if (c->ctl_chan != -1) {
1750 mux_exit_message(ssh, c, exitval); 1777 mux_exit_message(ssh, c, exitval);
1751 success = 1; 1778 success = 1;
1752 } else if (id == session_ident) { 1779 } else if ((int)id == session_ident) {
1753 /* Record exit value of local session */ 1780 /* Record exit value of local session */
1754 success = 1; 1781 success = 1;
1755 exit_status = exitval; 1782 exit_status = exitval;
@@ -1758,19 +1785,23 @@ client_input_channel_req(int type, u_int32_t seq, struct ssh *ssh)
1758 debug("%s: no sink for exit-status on channel %d", 1785 debug("%s: no sink for exit-status on channel %d",
1759 __func__, id); 1786 __func__, id);
1760 } 1787 }
1761 packet_check_eom(); 1788 if ((r = sshpkt_get_end(ssh)) != 0)
1789 goto out;
1762 } 1790 }
1763 if (reply && c != NULL && !(c->flags & CHAN_CLOSE_SENT)) { 1791 if (reply && c != NULL && !(c->flags & CHAN_CLOSE_SENT)) {
1764 if (!c->have_remote_id) 1792 if (!c->have_remote_id)
1765 fatal("%s: channel %d: no remote_id", 1793 fatal("%s: channel %d: no remote_id",
1766 __func__, c->self); 1794 __func__, c->self);
1767 packet_start(success ? 1795 if ((r = sshpkt_start(ssh, success ?
1768 SSH2_MSG_CHANNEL_SUCCESS : SSH2_MSG_CHANNEL_FAILURE); 1796 SSH2_MSG_CHANNEL_SUCCESS : SSH2_MSG_CHANNEL_FAILURE)) != 0 ||
1769 packet_put_int(c->remote_id); 1797 (r = sshpkt_put_u32(ssh, c->remote_id)) != 0 ||
1770 packet_send(); 1798 (r = sshpkt_send(ssh)) != 0)
1799 sshpkt_fatal(ssh, r, "%s: send failure", __func__);
1771 } 1800 }
1801 r = 0;
1802 out:
1772 free(rtype); 1803 free(rtype);
1773 return 0; 1804 return r;
1774} 1805}
1775 1806
1776struct hostkeys_update_ctx { 1807struct hostkeys_update_ctx {
@@ -1987,7 +2018,10 @@ client_global_hostkeys_private_confirm(struct ssh *ssh, int type,
1987 if (ndone != ctx->nnew) 2018 if (ndone != ctx->nnew)
1988 fatal("%s: ndone != ctx->nnew (%zu / %zu)", __func__, 2019 fatal("%s: ndone != ctx->nnew (%zu / %zu)", __func__,
1989 ndone, ctx->nnew); /* Shouldn't happen */ 2020 ndone, ctx->nnew); /* Shouldn't happen */
1990 ssh_packet_check_eom(ssh); 2021 if ((r = sshpkt_get_end(ssh)) != 0) {
2022 error("%s: protocol error", __func__);
2023 goto out;
2024 }
1991 2025
1992 /* Make the edits to known_hosts */ 2026 /* Make the edits to known_hosts */
1993 update_known_hosts(ctx); 2027 update_known_hosts(ctx);
@@ -2174,23 +2208,27 @@ static int
2174client_input_global_request(int type, u_int32_t seq, struct ssh *ssh) 2208client_input_global_request(int type, u_int32_t seq, struct ssh *ssh)
2175{ 2209{
2176 char *rtype; 2210 char *rtype;
2177 int want_reply; 2211 u_char want_reply;
2178 int success = 0; 2212 int r, success = 0;
2179 2213
2180 rtype = packet_get_cstring(NULL); 2214 if ((r = sshpkt_get_cstring(ssh, &rtype, NULL)) != 0 ||
2181 want_reply = packet_get_char(); 2215 (r = sshpkt_get_u8(ssh, &want_reply)) != 0)
2216 goto out;
2182 debug("client_input_global_request: rtype %s want_reply %d", 2217 debug("client_input_global_request: rtype %s want_reply %d",
2183 rtype, want_reply); 2218 rtype, want_reply);
2184 if (strcmp(rtype, "hostkeys-00@openssh.com") == 0) 2219 if (strcmp(rtype, "hostkeys-00@openssh.com") == 0)
2185 success = client_input_hostkeys(); 2220 success = client_input_hostkeys();
2186 if (want_reply) { 2221 if (want_reply) {
2187 packet_start(success ? 2222 if ((r = sshpkt_start(ssh, success ? SSH2_MSG_REQUEST_SUCCESS :
2188 SSH2_MSG_REQUEST_SUCCESS : SSH2_MSG_REQUEST_FAILURE); 2223 SSH2_MSG_REQUEST_FAILURE)) != 0 ||
2189 packet_send(); 2224 (r = sshpkt_send(ssh)) != 0 ||
2190 packet_write_wait(); 2225 (r = ssh_packet_write_wait(ssh)) != 0)
2226 goto out;
2191 } 2227 }
2228 r = 0;
2229 out:
2192 free(rtype); 2230 free(rtype);
2193 return 0; 2231 return r;
2194} 2232}
2195 2233
2196void 2234void
@@ -2198,7 +2236,7 @@ client_session2_setup(struct ssh *ssh, int id, int want_tty, int want_subsystem,
2198 const char *term, struct termios *tiop, int in_fd, struct sshbuf *cmd, 2236 const char *term, struct termios *tiop, int in_fd, struct sshbuf *cmd,
2199 char **env) 2237 char **env)
2200{ 2238{
2201 int i, j, matched, len; 2239 int i, j, matched, len, r;
2202 char *name, *val; 2240 char *name, *val;
2203 Channel *c = NULL; 2241 Channel *c = NULL;
2204 2242
@@ -2207,7 +2245,7 @@ client_session2_setup(struct ssh *ssh, int id, int want_tty, int want_subsystem,
2207 if ((c = channel_lookup(ssh, id)) == NULL) 2245 if ((c = channel_lookup(ssh, id)) == NULL)
2208 fatal("%s: channel %d: unknown channel", __func__, id); 2246 fatal("%s: channel %d: unknown channel", __func__, id);
2209 2247
2210 packet_set_interactive(want_tty, 2248 ssh_packet_set_interactive(ssh, want_tty,
2211 options.ip_qos_interactive, options.ip_qos_bulk); 2249 options.ip_qos_interactive, options.ip_qos_bulk);
2212 2250
2213 if (want_tty) { 2251 if (want_tty) {
@@ -2219,15 +2257,18 @@ client_session2_setup(struct ssh *ssh, int id, int want_tty, int want_subsystem,
2219 2257
2220 channel_request_start(ssh, id, "pty-req", 1); 2258 channel_request_start(ssh, id, "pty-req", 1);
2221 client_expect_confirm(ssh, id, "PTY allocation", CONFIRM_TTY); 2259 client_expect_confirm(ssh, id, "PTY allocation", CONFIRM_TTY);
2222 packet_put_cstring(term != NULL ? term : ""); 2260 if ((r = sshpkt_put_cstring(ssh, term != NULL ? term : ""))
2223 packet_put_int((u_int)ws.ws_col); 2261 != 0 ||
2224 packet_put_int((u_int)ws.ws_row); 2262 (r = sshpkt_put_u32(ssh, (u_int)ws.ws_col)) != 0 ||
2225 packet_put_int((u_int)ws.ws_xpixel); 2263 (r = sshpkt_put_u32(ssh, (u_int)ws.ws_row)) != 0 ||
2226 packet_put_int((u_int)ws.ws_ypixel); 2264 (r = sshpkt_put_u32(ssh, (u_int)ws.ws_xpixel)) != 0 ||
2265 (r = sshpkt_put_u32(ssh, (u_int)ws.ws_ypixel)) != 0)
2266 fatal("%s: %s", __func__, ssh_err(r));
2227 if (tiop == NULL) 2267 if (tiop == NULL)
2228 tiop = get_saved_tio(); 2268 tiop = get_saved_tio();
2229 ssh_tty_make_modes(ssh, -1, tiop); 2269 ssh_tty_make_modes(ssh, -1, tiop);
2230 packet_send(); 2270 if ((r = sshpkt_send(ssh)) != 0)
2271 fatal("%s: %s", __func__, ssh_err(r));
2231 /* XXX wait for reply */ 2272 /* XXX wait for reply */
2232 c->client_tty = 1; 2273 c->client_tty = 1;
2233 } 2274 }
@@ -2259,9 +2300,10 @@ client_session2_setup(struct ssh *ssh, int id, int want_tty, int want_subsystem,
2259 2300
2260 debug("Sending env %s = %s", name, val); 2301 debug("Sending env %s = %s", name, val);
2261 channel_request_start(ssh, id, "env", 0); 2302 channel_request_start(ssh, id, "env", 0);
2262 packet_put_cstring(name); 2303 if ((r = sshpkt_put_cstring(ssh, name)) != 0 ||
2263 packet_put_cstring(val); 2304 (r = sshpkt_put_cstring(ssh, val)) != 0 ||
2264 packet_send(); 2305 (r = sshpkt_send(ssh)) != 0)
2306 fatal("%s: %s", __func__, ssh_err(r));
2265 free(name); 2307 free(name);
2266 } 2308 }
2267 } 2309 }
@@ -2276,9 +2318,10 @@ client_session2_setup(struct ssh *ssh, int id, int want_tty, int want_subsystem,
2276 2318
2277 debug("Setting env %s = %s", name, val); 2319 debug("Setting env %s = %s", name, val);
2278 channel_request_start(ssh, id, "env", 0); 2320 channel_request_start(ssh, id, "env", 0);
2279 packet_put_cstring(name); 2321 if ((r = sshpkt_put_cstring(ssh, name)) != 0 ||
2280 packet_put_cstring(val); 2322 (r = sshpkt_put_cstring(ssh, val)) != 0 ||
2281 packet_send(); 2323 (r = sshpkt_send(ssh)) != 0)
2324 fatal("%s: %s", __func__, ssh_err(r));
2282 free(name); 2325 free(name);
2283 } 2326 }
2284 2327
@@ -2298,12 +2341,14 @@ client_session2_setup(struct ssh *ssh, int id, int want_tty, int want_subsystem,
2298 channel_request_start(ssh, id, "exec", 1); 2341 channel_request_start(ssh, id, "exec", 1);
2299 client_expect_confirm(ssh, id, "exec", CONFIRM_CLOSE); 2342 client_expect_confirm(ssh, id, "exec", CONFIRM_CLOSE);
2300 } 2343 }
2301 packet_put_string(sshbuf_ptr(cmd), sshbuf_len(cmd)); 2344 if ((r = sshpkt_put_stringb(ssh, cmd)) != 0 ||
2302 packet_send(); 2345 (r = sshpkt_send(ssh)) != 0)
2346 fatal("%s: %s", __func__, ssh_err(r));
2303 } else { 2347 } else {
2304 channel_request_start(ssh, id, "shell", 1); 2348 channel_request_start(ssh, id, "shell", 1);
2305 client_expect_confirm(ssh, id, "shell", CONFIRM_CLOSE); 2349 client_expect_confirm(ssh, id, "shell", CONFIRM_CLOSE);
2306 packet_send(); 2350 if ((r = sshpkt_send(ssh)) != 0)
2351 fatal("%s: %s", __func__, ssh_err(r));
2307 } 2352 }
2308} 2353}
2309 2354