Mercurial > dropbear
comparison svr-chansession.c @ 1804:f0cd000f3bca
Prevent multiple shells being spawned
Existing shells would be leaked.
The old check only caught multiple commands, not shells.
author | Matt Johnston <matt@ucc.asn.au> |
---|---|
date | Sat, 06 Mar 2021 23:06:43 +0800 |
parents | 837cc354b388 |
children | 5120e22882de eaa2d7240a5d |
comparison
equal
deleted
inserted
replaced
1803:837cc354b388 | 1804:f0cd000f3bca |
---|---|
656 int iscmd, int issubsys) { | 656 int iscmd, int issubsys) { |
657 | 657 |
658 unsigned int cmdlen = 0; | 658 unsigned int cmdlen = 0; |
659 int ret; | 659 int ret; |
660 | 660 |
661 TRACE(("enter sessioncommand")) | 661 TRACE(("enter sessioncommand %d", channel->index)) |
662 | 662 |
663 if (chansess->cmd != NULL) { | 663 if (chansess->pid != 0) { |
664 /* Note that only one command can _succeed_. The client might try | 664 /* Note that only one command can _succeed_. The client might try |
665 * one command (which fails), then try another. Ie fallback | 665 * one command (which fails), then try another. Ie fallback |
666 * from sftp to scp */ | 666 * from sftp to scp */ |
667 TRACE(("leave sessioncommand, already have a command")) | |
667 return DROPBEAR_FAILURE; | 668 return DROPBEAR_FAILURE; |
668 } | 669 } |
669 | 670 |
670 if (iscmd) { | 671 if (iscmd) { |
671 /* "exec" */ | 672 /* "exec" */ |
673 chansess->cmd = buf_getstring(ses.payload, &cmdlen); | 674 chansess->cmd = buf_getstring(ses.payload, &cmdlen); |
674 | 675 |
675 if (cmdlen > MAX_CMD_LEN) { | 676 if (cmdlen > MAX_CMD_LEN) { |
676 m_free(chansess->cmd); | 677 m_free(chansess->cmd); |
677 /* TODO - send error - too long ? */ | 678 /* TODO - send error - too long ? */ |
679 TRACE(("leave sessioncommand, command too long %d", cmdlen)) | |
678 return DROPBEAR_FAILURE; | 680 return DROPBEAR_FAILURE; |
679 } | 681 } |
680 } | 682 } |
681 if (issubsys) { | 683 if (issubsys) { |
682 #if DROPBEAR_SFTPSERVER | 684 #if DROPBEAR_SFTPSERVER |
685 chansess->cmd = m_strdup(SFTPSERVER_PATH); | 687 chansess->cmd = m_strdup(SFTPSERVER_PATH); |
686 } else | 688 } else |
687 #endif | 689 #endif |
688 { | 690 { |
689 m_free(chansess->cmd); | 691 m_free(chansess->cmd); |
692 TRACE(("leave sessioncommand, unknown subsystem")) | |
690 return DROPBEAR_FAILURE; | 693 return DROPBEAR_FAILURE; |
691 } | 694 } |
692 } | 695 } |
693 } | 696 } |
694 | 697 |
741 #endif | 744 #endif |
742 | 745 |
743 if (ret == DROPBEAR_FAILURE) { | 746 if (ret == DROPBEAR_FAILURE) { |
744 m_free(chansess->cmd); | 747 m_free(chansess->cmd); |
745 } | 748 } |
749 TRACE(("leave sessioncommand, ret %d", ret)) | |
746 return ret; | 750 return ret; |
747 } | 751 } |
748 | 752 |
749 /* Execute a command and set up redirection of stdin/stdout/stderr without a | 753 /* Execute a command and set up redirection of stdin/stdout/stderr without a |
750 * pty. | 754 * pty. |
914 svr_ses.childpids = (struct ChildPid*)m_realloc(svr_ses.childpids, | 918 svr_ses.childpids = (struct ChildPid*)m_realloc(svr_ses.childpids, |
915 sizeof(struct ChildPid) * (svr_ses.childpidsize+1)); | 919 sizeof(struct ChildPid) * (svr_ses.childpidsize+1)); |
916 svr_ses.childpidsize++; | 920 svr_ses.childpidsize++; |
917 } | 921 } |
918 | 922 |
923 TRACE(("addchildpid %d pid %d for chansess %p", i, pid, chansess)) | |
919 svr_ses.childpids[i].pid = pid; | 924 svr_ses.childpids[i].pid = pid; |
920 svr_ses.childpids[i].chansess = chansess; | 925 svr_ses.childpids[i].chansess = chansess; |
921 | 926 |
922 } | 927 } |
923 | 928 |