From 802d9a3349faf5a96ef8968f1c92a0d21a9b11b7 Mon Sep 17 00:00:00 2001 From: quamrulmina Date: Wed, 27 Jan 2016 18:20:11 -0600 Subject: [PATCH 01/12] Fix #71; Env vars like APPDATA, LOCALAPPDATA etc in sshd are set correctly now. APPDATA, LOCALAPPDATA, HOMEDRIVE, HOMEPATH set correctly in sshd server --- contrib/win32/win32compat/pwd.c | 15 ++++++++++++++- session.c | 26 ++++++++++++++++++-------- 2 files changed, 32 insertions(+), 9 deletions(-) diff --git a/contrib/win32/win32compat/pwd.c b/contrib/win32/win32compat/pwd.c index 336dc1c..17cfcf2 100644 --- a/contrib/win32/win32compat/pwd.c +++ b/contrib/win32/win32compat/pwd.c @@ -129,6 +129,7 @@ int GetDomainFromToken ( HANDLE *hAccessToken, UCHAR *domain, DWORD dwSize) char *GetHomeDirFromToken(char *userName, HANDLE token) { UCHAR domain[200]; + wchar_t pw_buf[MAX_PATH] = { L'\0' }; debug("-> GetHomeDirFromToken()..."); @@ -172,7 +173,19 @@ char *GetHomeDirFromToken(char *userName, HANDLE token) return NULL; } - + + // update APPDATA user's env variable + if (SUCCEEDED(SHGetFolderPathW(NULL, CSIDL_APPDATA, token, 0, pw_buf))) + { + SetEnvironmentVariableW(L"APPDATA", pw_buf); + } + + // update LOCALAPPDATA user's env variable + if (SUCCEEDED(SHGetFolderPathW(NULL, CSIDL_LOCAL_APPDATA, token, 0, pw_buf))) + { + SetEnvironmentVariableW(L"LOCALAPPDATA", pw_buf); + } + /* * Unload user profile. */ diff --git a/session.c b/session.c index 57b963a..af08490 100644 --- a/session.c +++ b/session.c @@ -804,25 +804,25 @@ do_exec_no_pty(Session *s, const char *command) * Get user homedir if needed. */ - if (s -> pw -> pw_dir == NULL || s -> pw -> pw_dir[0] == '\0') + if (1) // (s -> pw -> pw_dir == NULL || s -> pw -> pw_dir[0] == '\0') { /* * If there is homedir from LSA use it. */ - if (HomeDirLsaW[0] != '\0') - { - s -> pw -> pw_dir = HomeDirLsaW; - } + //if (HomeDirLsaW[0] != '\0') + //{ + //s -> pw -> pw_dir = HomeDirLsaW; + //} /* * If not get homedir from token. */ - else - { + //else + //{ s -> pw -> pw_dir = GetHomeDirFromToken(s -> pw -> pw_name, hToken); - } + //} } /* @@ -832,6 +832,16 @@ do_exec_no_pty(Session *s, const char *command) _wchdir(s -> pw -> pw_dir); SetEnvironmentVariableW(L"HOME", s -> pw -> pw_dir); + wchar_t *wstr, wchr; + wstr = wcschr(s->pw->pw_dir, ':'); + if (wstr) { + wchr = *(wstr + 1); + *(wstr + 1) = '\0'; + SetEnvironmentVariableW(L"HOMEDRIVE", s->pw->pw_dir); + *(wstr + 1) = wchr; + SetEnvironmentVariableW(L"HOMEPATH", (wstr+1)); + } + SetEnvironmentVariableW(L"USERPROFILE", s -> pw -> pw_dir); // find the server name of the domain controller which created this token From f43f33da8bb93a5c0804e6e2a71fe2f80aed4bc8 Mon Sep 17 00:00:00 2001 From: quamrulmina Date: Fri, 29 Jan 2016 02:53:53 -0600 Subject: [PATCH 02/12] Fix sshd.log file to be created in the correct place sshd.log of child was created in root / directory. It should be in the directory where sshd.exe binary is located. Otherwise logged data were not being found in the central sshd.log file where user's expect. --- sshd.c | 2 ++ 1 file changed, 2 insertions(+) diff --git a/sshd.c b/sshd.c index 250b973..cf99125 100644 --- a/sshd.c +++ b/sshd.c @@ -2750,8 +2750,10 @@ main(int ac, char **av) /* Chdir to the root directory so that the current disk can be unmounted if desired. */ + #ifndef WIN32_FIXME if (chdir("/") == -1) error("chdir(\"/\"): %s", strerror(errno)); + #endif /* ignore SIGPIPE */ signal(SIGPIPE, SIG_IGN); From 829f799ad9374cfbf105b79aef45e7500ce3504b Mon Sep 17 00:00:00 2001 From: quamrulmina Date: Mon, 1 Feb 2016 04:10:36 -0600 Subject: [PATCH 03/12] Add pluggable access to shell session so that cmd & powershell runs like natively #define WIN32_PRAGMA_REMCON in config.h.vs or in channels.c, session.c and sshpty.c files . cmdserver.exe runtime in Pragma Fortress SSH package needed to access shell session. --- channels.c | 7 +++- contrib/win32/openssh/config.h.vs | 4 +- session.c | 65 +++++++++++++++++++++++++------ sshpty.c | 32 +++++++++++++++ 4 files changed, 94 insertions(+), 14 deletions(-) diff --git a/channels.c b/channels.c index 408dee7..e7d2a51 100644 --- a/channels.c +++ b/channels.c @@ -42,6 +42,7 @@ #include "includes.h" #ifdef WIN32_FIXME +//#define WIN32_PRAGMA_REMCON #ifdef ECONNABORTED #undef ECONNABORTED #endif @@ -2482,6 +2483,9 @@ channel_input_data(int type, u_int32_t seq, void *ctxt) if ( c->client_tty ) telProcessNetwork ( data, data_len ); // run it by ANSI engine if it is the ssh client else { + #ifdef WIN32_PRAGMA_REMCON + buffer_append(&c->output, data, data_len); // it is the sshd server, so pass it on + #else if ( ( c->isatty) && (data_len ==1) && (data[0] == '\003') ) { /* send control-c to the shell process */ if ( GenerateConsoleCtrlEvent ( CTRL_C_EVENT, 0 ) ) { @@ -2492,7 +2496,7 @@ channel_input_data(int type, u_int32_t seq, void *ctxt) } else { // avoid sending the 4 arrow keys out to remote for now "ESC[A" .. - if ( (c->isatty) && (data_len ==3) && (data[0] == '\033') && (data[1] == '[')) { + if ( (c->isatty) && (data_len ==3) && (data[0] == '\033') && (data[1] == '[')) { if ( ( data[2] == 'A') || (data[2] == 'B') || (data[2] == 'C') || (data[2] == 'D')) packet_check_eom(); return 0; @@ -2515,6 +2519,7 @@ channel_input_data(int type, u_int32_t seq, void *ctxt) charinline = 0; // a line has ended, begin char in line count again } } + #endif // WIN32_PRAGMA_REMCON } #endif diff --git a/contrib/win32/openssh/config.h.vs b/contrib/win32/openssh/config.h.vs index b673805..5035572 100644 --- a/contrib/win32/openssh/config.h.vs +++ b/contrib/win32/openssh/config.h.vs @@ -1707,5 +1707,7 @@ struct iovec // define building with MS Visual Studio Compiler and runtime and not with MingW/gcc compiler #define WIN32_VS 1 - +// Use Pragma Systems Remote Console modules for shell sessions so that cmd/powershell fully +// works remotely over SSH like they operate in a local machine +//#define WIN32_PRAGMA_REMCON diff --git a/session.c b/session.c index af08490..a01b7eb 100644 --- a/session.c +++ b/session.c @@ -42,6 +42,7 @@ #undef GSSAPI #undef KRB5 #define WIN32_USER_AUTH 1 + //#define WIN32_PRAGMA_REMCON #endif #include @@ -589,11 +590,20 @@ do_exec_no_pty(Session *s, const char *command) char buf[256]; int prot_scr_width = 80; int prot_scr_height = 25; + #ifdef WIN32_PRAGMA_REMCON + char exec_command_str[512]; + #endif if (!command) { + #ifndef WIN32_PRAGMA_REMCON exec_command = s->pw->pw_shell; - //exec_command = "c:\\tools\\echoit.exe"; // temp + #else + snprintf(exec_command_str, sizeof(exec_command_str), + "\\program files\\pragma\\shared files\\cmdserver.exe SSHD %d %d", + s->row, s->col ); + exec_command = exec_command_str; + #endif } else { @@ -606,28 +616,42 @@ do_exec_no_pty(Session *s, const char *command) * Create three socket pairs for stdin, stdout and stderr */ - HANDLE wfdtocmd = -1; + #ifdef WIN32_PRAGMA_REMCON + int retcode = -1; if ( (!s -> is_subsystem) && (s ->ttyfd != -1)) { - //FreeConsole(); - //AllocConsole(); - MakeNewConsole(); prot_scr_width = s->col; prot_scr_height = s->row; extern HANDLE hConsole ; hConsole = GetStdHandle (STD_OUTPUT_HANDLE); ConSetScreenSize( s->col, s->row ); - s->ptyfd = hConsole ; // the pty is the Windows console output handle in our Win32 port - - wfdtocmd = GetStdHandle (STD_INPUT_HANDLE) ; // we use this console handle to feed input to Windows shell cmd.exe - sockin[1] = allocate_sfd((int)wfdtocmd); // put the std input handle in our global general handle table - //if (sockin[1] >= 0) - // sfd_set_to_console(sockin[1]); // mark it as Console type - + socketpair(sockin); + s->ptyfd = sockin[1]; // hConsole; // the pty is the Windows console output handle in our Win32 port } else socketpair(sockin); + #else + HANDLE wfdtocmd = -1; + int retcode = -1; + if ((!s->is_subsystem) && (s->ttyfd != -1)) + { + //FreeConsole(); + //AllocConsole(); + MakeNewConsole(); + prot_scr_width = s->col; + prot_scr_height = s->row; + extern HANDLE hConsole; + hConsole = GetStdHandle(STD_OUTPUT_HANDLE); + ConSetScreenSize(s->col, s->row); + s->ptyfd = hConsole; // the pty is the Windows console output handle in our Win32 port + + wfdtocmd = GetStdHandle(STD_INPUT_HANDLE); // we use this console handle to feed input to Windows shell cmd.exe + sockin[1] = allocate_sfd((int)wfdtocmd); // put the std input handle in our global general handle table + } + else + socketpair(sockin); + #endif socketpair(sockout); socketpair(sockerr); @@ -636,12 +660,14 @@ do_exec_no_pty(Session *s, const char *command) debug3("sockout[0]: %d sockout[1]: %d", sockout[0], sockout[1]); debug3("sockerr[0]: %d sockerr[1]: %d", sockerr[0], sockerr[1]); + #ifndef WIN32_PRAGMA_REMCON if ( (s -> is_subsystem) || (s ->ttyfd == -1)) crlf_sfd(sockin[1]); crlf_sfd(sockout[1]); if ( (s -> is_subsystem) || (s ->ttyfd == -1)) + #endif SetHandleInformation(sfd_to_handle(sockin[1]), HANDLE_FLAG_INHERIT, 0); SetHandleInformation(sfd_to_handle(sockout[1]), HANDLE_FLAG_INHERIT, 0); @@ -668,11 +694,16 @@ do_exec_no_pty(Session *s, const char *command) si.cbReserved2 = 0; si.lpReserved2 = 0; + #ifdef WIN32_PRAGMA_REMCON + if (0) { + #else if ( (!s -> is_subsystem) && (s ->ttyfd != -1) ) { + si.hStdInput = GetStdHandle (STD_INPUT_HANDLE) ; // shell tty interactive session gets a console input for Win32 si.hStdOutput = (HANDLE) sfd_to_handle(sockout[0]); si.hStdError = (HANDLE) sfd_to_handle(sockerr[0]); si.lpDesktop = NULL ; //winstadtname_w ; + #endif } else { si.hStdInput = (HANDLE) sfd_to_handle(sockin[0]); @@ -889,6 +920,7 @@ do_exec_no_pty(Session *s, const char *command) GetUserName(name, &size); +#ifndef WIN32_PRAGMA_REMCON if ( (!s -> is_subsystem) && (s ->ttyfd != -1)) { // Send to the remote client ANSI/VT Sequence so that they send us CRLF in place of LF char *inittermseq = "\033[20h\033[?7h\0" ; // LFtoCRLF AUTOWRAPON @@ -896,6 +928,7 @@ do_exec_no_pty(Session *s, const char *command) buffer_append(&c->input, inittermseq, strlen(inittermseq)); channel_output_poll(); } +#endif //if (s ->ttyfd != -1) { // set the channel to tty interactive type @@ -975,8 +1008,12 @@ do_exec_no_pty(Session *s, const char *command) /* * We are the parent. Close the child sides of the socket pairs. */ + #ifndef WIN32_PRAGMA_REMCON if ( (s -> is_subsystem) || (s ->ttyfd == -1)) close(sockin[0]); + #else + close(sockin[0]); + #endif close(sockout[0]); close(sockerr[0]); @@ -2734,7 +2771,9 @@ session_pty_req(Session *s) /* for SSH1 the tty modes length is not given */ if (!compat20) n_bytes = packet_remaining(); + #ifndef WIN32_PRAGMA_REMCON tty_parse_modes(s->ttyfd, &n_bytes); + #endif if (!use_privsep) pty_setowner(s->pw, s->tty); @@ -2744,7 +2783,9 @@ session_pty_req(Session *s) pty_change_window_size(s->ptyfd, s->row, s->col, s->xpixel, s->ypixel); #endif + #ifndef WIN32_PRAGMA_REMCON packet_check_eom(); + #endif session_proctitle(s); return 1; } diff --git a/sshpty.c b/sshpty.c index 8f8b5d6..2e15ac8 100644 --- a/sshpty.c +++ b/sshpty.c @@ -21,6 +21,7 @@ #ifdef WIN32_FIXME #undef GSSAPI #undef KRB5 +//#define WIN32_PRAGMA_REMCON #endif #include @@ -196,6 +197,32 @@ pty_make_controlling_tty(int *ttyfd, const char *tty) #endif } +#ifdef WIN32_PRAGMA_REMCON +/* Changes the window size associated with the pty. */ + +void pty_change_window_size_oob(int ptyfd, u_int row, u_int col, u_int xpixel, u_int ypixel) +{ + int rc; + char unsigned data[16]; + size_t data_len; + + // IAC SB NAWS <16-bit value width> <16-bit value height> IAC + //sprintf (data,"%c%c%c%c%c%c%c%c", 255, 250, 31, 0, col, 0, row, 255 ); + data[0] = 255; // IAC; + data[1] = 250; // SB + data[2] = 31; // NAWS + data[3] = 0; + data[4] = (unsigned char)col; + data[5] = 0; + data[6] = (unsigned char)row; + data[7] = 255; // IAC + data[8] = 240; // iac end + data_len = 9; //strlen (data); + rc = write(ptyfd, data, (DWORD)data_len); + //rc = AsyncWrite(c->hInputHandle, (char *)data, (DWORD)data_len); +} + +#endif /* Changes the window size associated with the pty. */ void @@ -214,7 +241,12 @@ pty_change_window_size(int ptyfd, u_int row, u_int col, #else extern HANDLE hConsole ; hConsole = ptyfd; + #ifndef WIN32_PRAGMA_REMCON ConSetScreenSize( col, row ); + #else + if (ptyfd > 0 ) + pty_change_window_size_oob(ptyfd, row, col, xpixel, ypixel); + #endif #endif } From 384cd18b563caff33a6487d80637db3025215607 Mon Sep 17 00:00:00 2001 From: dkulwin Date: Mon, 25 Jan 2016 14:52:21 -0600 Subject: [PATCH 04/12] Add abstraction interface for elliptic points and elliptic diffie hellman --- contrib/win32/openssh/libssh.vcxproj | 1 + contrib/win32/openssh/libssh.vcxproj.filters | 9 +- crypto-wrap.h | 25 +++ openssl-epoint.c | 151 +++++++++++++++++++ 4 files changed, 183 insertions(+), 3 deletions(-) create mode 100644 openssl-epoint.c diff --git a/contrib/win32/openssh/libssh.vcxproj b/contrib/win32/openssh/libssh.vcxproj index 061950b..131093f 100644 --- a/contrib/win32/openssh/libssh.vcxproj +++ b/contrib/win32/openssh/libssh.vcxproj @@ -262,6 +262,7 @@ true + diff --git a/contrib/win32/openssh/libssh.vcxproj.filters b/contrib/win32/openssh/libssh.vcxproj.filters index 87cba0c..b07b7ef 100644 --- a/contrib/win32/openssh/libssh.vcxproj.filters +++ b/contrib/win32/openssh/libssh.vcxproj.filters @@ -288,15 +288,18 @@ Source Files - + Source Files - + + Source Files + + Source Files - + Header Files diff --git a/crypto-wrap.h b/crypto-wrap.h index f1e4934..6ed12df 100644 --- a/crypto-wrap.h +++ b/crypto-wrap.h @@ -6,6 +6,10 @@ struct sshdh; struct sshbn; struct sshbuf; struct ssh; +struct sshedh; +struct sshepoint; +struct sshecurve; + struct sshdh *sshdh_new(void); void sshdh_free(struct sshdh *dh); @@ -21,6 +25,27 @@ int sshdh_new_group_hex(const char *gen, const char *modulus, struct sshdh **dhp); struct sshdh *sshdh_new_group(struct sshbn *gen, struct sshbn *modulus); +struct sshedh *sshedh_new(void); +void sshedh_free(struct sshdh *dh); +struct sshepoint *sshedh_pubkey(struct sshedh *dh); +void sshedh_dump(struct sshedh *dh); +size_t sshedh_shared_key_size(struct sshedh *dh); +int sshedh_compute_key(struct sshedh *dh, struct sshepoint *pubkey, +struct sshbn **shared_secretp); +int sshedh_generate(struct sshedh *dh, size_t len); +struct sshedh *sshedh_new_curve(int nid); + +struct sshepoint * sshepoint_new(void); +int sshepoint_from(struct sshbn * x, struct sshbn * y, struct sshecurve * sshecurve, struct sshepoint **retp); +int sshepoint_to(struct sshepoint * pt, struct sshbn **retx, struct sshbn **rety, struct sshecurve ** retcurve); +void sshepoint_free(struct sshepoint * pt); + +struct sshecurve * sshecurve_new(void); +void sshecurve_free(struct sshecurve * curve); +struct sshecurve * sshecurve_new_curve(int nid); + + + struct sshbn *sshbn_new(void); void sshbn_free(struct sshbn *bn); int sshbn_from(const void *d, size_t l, struct sshbn **retp); diff --git a/openssl-epoint.c b/openssl-epoint.c new file mode 100644 index 0000000..62f7fdb --- /dev/null +++ b/openssl-epoint.c @@ -0,0 +1,151 @@ +/* +* Copyright (c) 2015 Damien Miller +* +* Permission to use, copy, modify, and distribute this software for any +* purpose with or without fee is hereby granted, provided that the above +* copyright notice and this permission notice appear in all copies. +* +* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES +* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF +* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR +* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES +* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN +* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF +* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. +*/ + +#include + + +#include +#include +#include +#include +#include + + +#include +#include + + +#include "sshbuf.h" +#include "packet.h" +#include "ssherr.h" +#include "crypto-wrap.h" + +struct sshepoint { + EC_POINT *pt; + EC_GROUP *gp; +}; + +struct sshecurve { + EC_GROUP *gp; +}; + + +struct sshepoint * + sshepoint_new(void) +{ + return malloc(sizeof(struct sshepoint)); +} + +void +sshepoint_free(struct sshepoint *pt) +{ + if (pt != NULL) { + if (pt->pt != NULL) + EC_POINT_free(pt->pt); + if (pt->gp != NULL) + EC_GROUP_free(pt->gp); + explicit_bzero(pt, sizeof(*pt)); + free(pt); + } +} + + +int sshepoint_from(struct sshbn * x, struct sshbn * y, struct sshecurve * curve, struct sshepoint **retp) +{ + struct sshepoint *ret = NULL; + + + *retp = NULL; + if ((ret = sshepoint_new()) == NULL) + { + return SSH_ERR_ALLOC_FAIL; + } + if ((ret->pt = EC_POINT_new(curve->gp)) == NULL) + { + sshepoint_free(ret); + return SSH_ERR_LIBCRYPTO_ERROR; + } + ret->gp = curve->gp; + if (EC_POINT_set_affine_corrdinates_GFp(curve->gp, ret->pt, x, y)) { + sshepoint_free(ret); + return SSH_ERR_LIBCRYPTO_ERROR; + } + *retp = ret; + return 0; +} +int sshepoint_to(struct sshepoint * pt, struct sshbn **retx, struct sshbn **rety, struct sshecurve ** retcurve) +{ + struct sshbn * x = NULL; + struct sshbn * y = NULL; + struct sshecurve * curve = NULL; + + if (((x = sshbn_new()) == NULL) || + ((y = sshbn_new()) == NULL) || + ((curve = sshecurve_new()) == NULL)) + { + sshbn_free(x); + sshbn_free(y); + sshecurve_free(curve); + return SSH_ERR_ALLOC_FAIL; + } + + curve->gp = pt->gp; + if (EC_POINT_get_affine_coordinates_GFp(pt->gp, pt->pt, sshbn_bignum(x), sshbn_bignum(y), NULL)) + { + sshecurve_free(curve); + sshbn_free(x); + sshbn_free(y); + return SSH_ERR_LIBCRYPTO_ERROR; + } + *retcurve = curve; + *retx = x; + *rety = y; + + return 0; +} + +struct sshecurve * sshecurve_new(void) +{ + struct sshecurve * curve = NULL; + + curve = (struct sshecurve *)malloc(sizeof(struct sshecurve)); + memset(curve, 0, sizeof(struct sshecurve)); + + return curve; +} + +void sshecurve_free(struct sshecurve * curve) +{ + if (curve != NULL) { + if (curve->gp != NULL) + EC_GROUP_free(curve->gp); + explicit_bzero(curve, sizeof(*curve)); + free(curve); + } +} + +struct sshecurve * sshecurve_new_curve(int nid) +{ + struct sshecurve * ret; + + if ((ret = sshecurve_new()) == NULL) + return NULL; + ret->gp = EC_GROUP_new_by_curve_name(nid); + + return ret; + + +} \ No newline at end of file From 9f47848ee6feab23d02d1180fa5a57eff7b8aaf3 Mon Sep 17 00:00:00 2001 From: arif-pragmasys Date: Mon, 1 Feb 2016 16:49:53 -0600 Subject: [PATCH 05/12] Fix linux build by adding new crypto files --- Makefile.in | 2 +- kex.h | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/Makefile.in b/Makefile.in index 40cc7aa..12176f8 100644 --- a/Makefile.in +++ b/Makefile.in @@ -91,7 +91,7 @@ LIBSSH_OBJS=${LIBOPENSSH_OBJS} \ sc25519.o ge25519.o fe25519.o ed25519.o verify.o hash.o blocks.o \ kex.o kexdh.o kexgex.o kexecdh.o kexc25519.o \ kexdhc.o kexgexc.o kexecdhc.o kexc25519c.o \ - kexdhs.o kexgexs.o kexecdhs.o kexc25519s.o + kexdhs.o kexgexs.o kexecdhs.o kexc25519s.o openssl-dh.o openssl-bn.o SSHOBJS= ssh.o readconf.o clientloop.o sshtty.o \ sshconnect.o sshconnect1.o sshconnect2.o mux.o \ diff --git a/kex.h b/kex.h index 1c2be3e..43e8b9f 100644 --- a/kex.h +++ b/kex.h @@ -29,6 +29,7 @@ #include "mac.h" #include "buffer.h" /* XXX for typedef */ #include "key.h" /* XXX for typedef */ +#include "crypto-wrap.h" #ifdef WITH_LEAKMALLOC #include "leakmalloc.h" From f3c841824ed99e0ef9131cb3763c790da6030f94 Mon Sep 17 00:00:00 2001 From: quamrulmina Date: Tue, 2 Feb 2016 02:02:56 -0600 Subject: [PATCH 06/12] Improve sshd Pluggable remote console enhancements pluggable binaries are to reside in the same directory where sshd.exe is located --- session.c | 17 ++++++++++++++--- 1 file changed, 14 insertions(+), 3 deletions(-) diff --git a/session.c b/session.c index a01b7eb..e9378a4 100644 --- a/session.c +++ b/session.c @@ -117,6 +117,9 @@ FIXME: GFPZR: Function stat() may be undeclared. #include #include +#ifdef WIN32_PRAGMA_REMCON +#include +#endif extern char HomeDirLsaW[MAX_PATH]; #endif @@ -599,9 +602,17 @@ do_exec_no_pty(Session *s, const char *command) #ifndef WIN32_PRAGMA_REMCON exec_command = s->pw->pw_shell; #else - snprintf(exec_command_str, sizeof(exec_command_str), - "\\program files\\pragma\\shared files\\cmdserver.exe SSHD %d %d", - s->row, s->col ); + if ( PathFileExists("\\program files\\pragma\\shared files\\cmdserver.exe") ) + snprintf(exec_command_str, sizeof(exec_command_str), + "\\program files\\pragma\\shared files\\cmdserver.exe SSHD %d %d", s->row, s->col ); + else { + // find base path of our executable + char basepath[MAX_PATH]; + strcpy_s(basepath, MAX_PATH, __progname); + PathRemoveFileSpec(basepath); // get the full dir part of the name + snprintf(exec_command_str, sizeof(exec_command_str), + "%s\\cmdserver.exe SSHD %d %d", basepath,s->row, s->col); + } exec_command = exec_command_str; #endif } From 88f4c54f66457893431c2b93cfb05141faf50177 Mon Sep 17 00:00:00 2001 From: Manoj Ampalam Date: Tue, 9 Feb 2016 11:41:26 -0800 Subject: [PATCH 07/12] OpenSSL build script from David --- .../win32/openssh/OpenSSL-1.0.2d_build.cmd | 45 +++++++++++++++++++ 1 file changed, 45 insertions(+) create mode 100644 contrib/win32/openssh/OpenSSL-1.0.2d_build.cmd diff --git a/contrib/win32/openssh/OpenSSL-1.0.2d_build.cmd b/contrib/win32/openssh/OpenSSL-1.0.2d_build.cmd new file mode 100644 index 0000000..daca44b --- /dev/null +++ b/contrib/win32/openssh/OpenSSL-1.0.2d_build.cmd @@ -0,0 +1,45 @@ +set OPENSSL_VERSION=1.0.2d +set PerlPath=c:\perl\bin +set NASMPath=c:\nasm + +set VS2013="C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC\bin\vcvars32.bat" +set VS2013_AMD64="C:\Program Files (x86)\Microsoft Visual Studio 12.0\VC\bin\amd64\vcvars64.bat" +set VS2015="C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\bin\vcvars32.bat" +set VS2015_AMD64="C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\bin\amd64\vcvars64.bat" + +set path=%NASMPath%;%PerlPath%;%path% + + +CALL %VS2015% + +cd \Dev\OpenSSL\openssl-%OPENSSL_VERSION%-src-x86 +perl Configure VC-WIN32 --prefix=C:\dev\OpenSSL\%OPENSSL_VERSION%\VS2015\Win32\Release +call ms\do_ms.bat +call ms\do_nasm.bat +nmake -f ms\nt.mak clean +nmake -f ms\nt.mak +nmake -f ms\nt.mak install + +cd \Dev\OpenSSL\openssl-%OPENSSL_VERSION%-src-x86 +perl Configure debug-VC-WIN32 --prefix=C:\dev\OpenSSL\%OPENSSL_VERSION%\VS2015\Win32\Debug +call ms\do_ms.bat +call ms\do_nasm.bat +nmake -f ms\nt.mak clean +nmake -f ms\nt.mak +nmake -f ms\nt.mak install + +CALL %VS2015_AMD64% + +cd \Dev\OpenSSL\openssl-%OPENSSL_VERSION%-src-x64 +perl Configure VC-WIN64A --prefix=C:\dev\OpenSSL\%OPENSSL_VERSION%\VS2015\x64\Release +call ms\do_win64a.bat +nmake -f ms\nt.mak clean +nmake -f ms\nt.mak +nmake -f ms\nt.mak install + +cd \Dev\OpenSSL\openssl-%OPENSSL_VERSION%-src-x64 +perl Configure debug-VC-WIN64A --prefix=C:\dev\OpenSSL\%OPENSSL_VERSION%\VS2015\x64\Debug +call ms\do_win64a.bat +nmake -f ms\nt.mak clean +nmake -f ms\nt.mak +nmake -f ms\nt.mak install From 907848880eaeb1c76737532e4c2715a447a776d0 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Viktor=20Sz=C3=A9pe?= Date: Fri, 19 Feb 2016 11:26:53 +0100 Subject: [PATCH 08/12] Adding Chocolatey badges --- README.md | 3 +++ 1 file changed, 3 insertions(+) diff --git a/README.md b/README.md index 1548381..530d70f 100644 --- a/README.md +++ b/README.md @@ -8,3 +8,6 @@ See the [wiki](https://github.com/PowerShell/Win32-OpenSSH/wiki) for installatio [First release announcement](http://blogs.msdn.com/b/powershell/archive/2015/10/19/openssh-for-windows-update.aspx ) +### Chocolatey + +[![](http://img.shields.io/chocolatey/dt/win32-openssh.svg)](https://chocolatey.org/packages/win32-openssh) [![](http://img.shields.io/chocolatey/v/win32-openssh.svg)](https://chocolatey.org/packages/win32-openssh) From 1f825c7e3007b8a7b6117590f7086e88d1a5f8fe Mon Sep 17 00:00:00 2001 From: quamrulmina Date: Wed, 24 Feb 2016 23:23:23 -0600 Subject: [PATCH 09/12] sftp client lls did not work in Windows if cygwin or linux ls not available Now lls is mapped to "dir" in Windows port which is available in Windows shell (cmd or powershell ). Cygwin or Linux emulation tools which has "ls" are not needed. --- sftp.c | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/sftp.c b/sftp.c index 7d5e0e2..cef03cb 100644 --- a/sftp.c +++ b/sftp.c @@ -346,6 +346,10 @@ local_do_shell(const char *args) static void local_do_ls(const char *args) { +#ifdef WIN32_FIXME +#undef _PATH_LS +#define _PATH_LS "dir" +#endif if (!args || !*args) local_do_shell(_PATH_LS); else { From b1fb7477164c9d361276bbc0c3dbc4b3e78f0dc9 Mon Sep 17 00:00:00 2001 From: manojampalam Date: Fri, 26 Feb 2016 19:40:40 -0800 Subject: [PATCH 10/12] PS Script to analyze fork Vs original code diffs Intention is to see the % of original code being reused for Win32 port. Here are the number as of 2-26-2016 for various libs libssh 89.09911361805 % scp 85.2348993288591 % sftp 93.3269323091695 % sftp-server 76.2975778546713 % ssh 90.1238422312415 % ssh-add 99.6138996138996 % ssh-agent 85.7938718662953 % sshd 84.0249187432286 % --- contrib/win32/openssh/AnalyzeCodeDiff.ps1 | 200 ++++++++++++++++++++++ 1 file changed, 200 insertions(+) create mode 100644 contrib/win32/openssh/AnalyzeCodeDiff.ps1 diff --git a/contrib/win32/openssh/AnalyzeCodeDiff.ps1 b/contrib/win32/openssh/AnalyzeCodeDiff.ps1 new file mode 100644 index 0000000..560a67f --- /dev/null +++ b/contrib/win32/openssh/AnalyzeCodeDiff.ps1 @@ -0,0 +1,200 @@ +Set-StrictMode -Version Latest +$Win32Macro = 'WIN32_FIXME' +$sourceRoot = 'C:\openssh\Win32-OpenSSH' + +[int]$g_code = 0 +[int]$g_win32 = 0 +[int]$g_unix = 0 + +function AnalyzeFile($file, [bool]$log) +{ + $file = Join-Path $sourceRoot $file + if ($log) { Write-Host -ForegroundColor Gray $file } + $content = Get-Content $file + [int]$commentlines = 0 #comments + [int]$emptylines = 0 #emptylines + [int]$code = 0 #all code lines + [int]$win32 = 0 #win32 only lines + [int]$win32substituted = 0#lines in win32 block that have a corresponding Unix block (#ifdef with #else) + [int]$unix = 0; #unix only lines + [int]$unixsubstituted = 0 #lines in unix block that have a corresponding Win32 block (#ifdef with #else) + [int]$total = 0 + [int]$nestedmacros = 0 #tracks nested macro blocks inside a win32 or a unix block + [bool]$incommentblock = $false + [bool]$inWin32block = $false + [bool]$inUnixblock = $false + [int]$currentblockcode = 0 + [bool]$insubstitutedblock = $false + + + foreach ($linestr in $content) + { + $total++ + $line = [String]$linestr + $line = $line.Trim() + #skip if line is empty + if ($line.Length -gt 0) + { + if ($incommentblock) + { + $commentlines++ + if ($line.EndsWith('*/')) {$incommentblock = $false} + } + else + { + if ($line.StartsWith('//')) {$commentlines++} + elseif ($line.StartsWith('/*')) + { + if (!($line.EndsWith('*/'))) { $incommentblock = $true } + $commentlines++ + } + else + { + $code++ + if ($inWin32block) + { + $win32++ + $currentblockcode++ + #keep skipping inner #ifdefs + if ($line.StartsWith('#ifdef')) {$nestedmacros++} + + if ($line.EndsWith('#endif') -or $line.EndsWith('#else')) + { + if ($nestedmacros -eq 0) + { + $inWin32block = $false + if ($line.EndsWith('#else')) + { + $inUnixblock = $true + $insubstitutedblock = $true + $win32substituted += $currentblockcode + } + elseif ($insubstitutedblock) + { + $win32substituted += $currentblockcode + $insubstitutedblock = $false + } + $currentblockcode = 0 + } + else + { + if ($line.EndsWith('#endif')) {$nestedmacros--} + } + } + } + elseif ($inUnixblock) + { + $unix++ + $currentblockcode++ + #keep skipping inner #ifdefs + if ($line.StartsWith('#ifdef')) {$nestedmacros++} + + if ($line.EndsWith('#endif') -or $line.EndsWith('#else')) + { + if ($nestedmacros -eq 0) + { + $inUnixblock = $false + if ($line.EndsWith('#else')) + { + $inWin32block = $true + $insubstitutedblock = $true + $unixsubstituted += $currentblockcode + } + elseif ($insubstitutedblock) + { + $unixsubstituted += $currentblockcode + $insubstitutedblock = $false + } + + $currentblockcode = 0 + } + else + { + if ($line.EndsWith('#endif')) {$nestedmacros--} + } + } + } + else + { + if ($line.StartsWith('#ifdef') -and $line.Contains($Win32Macro)) + { + $inWin32block = $true + $currentblockcode = 0 + } + if ($line.StartsWith('#ifndef') -and $line.Contains($Win32Macro)) + { + $inUnixblock = $true + $currentblockcode = 0; + } + } + + } + } + } + else {$emptylines++} + } + + if ($log) + { + Write-Host -ForegroundColor Yellow " Comments " $commentlines + Write-Host -ForegroundColor Green " Blank " $emptylines + Write-Host -ForegroundColor Cyan " Code " $code + Write-Host -ForegroundColor DarkMagenta " Total " $total " check("($commentlines+$emptylines+$code)")" + Write-Host -ForegroundColor Cyan " Win32 " $win32 + Write-Host -ForegroundColor Cyan " Unix " $unix + Write-Host -ForegroundColor Cyan " Win32sub " $win32substituted + Write-Host -ForegroundColor Cyan " Unixsub " $unixsubstituted + } + + $global:g_code += $code + $global:g_win32 += $win32 + $global:g_unix += $unix + +} + + +function AnalyzeProject($project, [bool]$log) +{ + if ($log) { Write-Host "Project: " $project} + $projectName = $project + $projectroot = Join-Path $sourceRoot 'contrib\win32\openssh' + $project = Join-Path $projectroot $project + $project = $project + '.vcxproj' + + $global:g_code = 0 + $global:g_win32 = 0 + $global:g_unix = 0 + + $c = Get-Content $project + foreach ($ln in $c){ + $l = [String]$ln + $l = $l.Trim() + + if ($l.StartsWith(' Date: Sat, 27 Feb 2016 23:03:57 -0600 Subject: [PATCH 11/12] sshd fixed to now take domain\user format for domain user login domain\user form now works. user@domain format already worked but now fixd to allow local machine name as the domain name also. So all these formats now work: For a domain acct: user OR domain\user OR user@domain For a local acct: user OR localmachinename\user OR user@localmachinename Note: public key logon still only works for a local user acct and the localmachinename must not be given and only the username specified for public key logon to work. --- auth-passwd.c | 68 +++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 63 insertions(+), 5 deletions(-) diff --git a/auth-passwd.c b/auth-passwd.c index d846b01..0626fb3 100644 --- a/auth-passwd.c +++ b/auth-passwd.c @@ -223,8 +223,65 @@ int sys_auth_passwd(Authctxt *authctxt, const char *password) /* * Identify domain or local login. */ - - domain_UTF16 = strchr(authctxt -> user, '@') ? NULL : L"."; + + char *username = authctxt->user; + + char *domainslash = strchr(authctxt->user, '\\'); + if (domainslash) { + // domain\username format + char *domainname = authctxt->user; + *domainslash = '\0'; + username = ++domainslash; // username is past the domain \ is the username + + // Convert domainname from UTF-8 to UTF-16 + buffer_size = MultiByteToWideChar(CP_UTF8, 0, domainname, -1, NULL, 0); + + if (buffer_size > 0) + { + domain_UTF16 = xmalloc(4 * buffer_size); + } + else + { + return 0; + } + + if (0 == MultiByteToWideChar(CP_UTF8, 0, domainname, + -1, domain_UTF16, buffer_size)) + { + free(domain_UTF16); + + return 0; + } + } + else if (domainslash = strchr(authctxt->user, '@')) { + // username@domain format + username = authctxt->user; + *domainslash = '\0'; + char *domainname = ++domainslash; // domainname is past the user@ + + // Convert domainname from UTF-8 to UTF-16 + buffer_size = MultiByteToWideChar(CP_UTF8, 0, domainname, -1, NULL, 0); + + if (buffer_size > 0) + { + domain_UTF16 = xmalloc(4 * buffer_size); + } + else + { + return 0; + } + + if (0 == MultiByteToWideChar(CP_UTF8, 0, domainname, + -1, domain_UTF16, buffer_size)) + { + free(domain_UTF16); + + return 0; + } + } + else { + domain_UTF16 = strchr(authctxt->user, '@') ? NULL : L"."; + } authctxt -> methoddata = hToken; @@ -237,7 +294,7 @@ int sys_auth_passwd(Authctxt *authctxt, const char *password) * Convert username from UTF-8 to UTF-16 */ - buffer_size = MultiByteToWideChar(CP_UTF8, 0, authctxt -> user, -1, NULL, 0); + buffer_size = MultiByteToWideChar(CP_UTF8, 0, username, -1, NULL, 0); if (buffer_size > 0) { @@ -248,7 +305,7 @@ int sys_auth_passwd(Authctxt *authctxt, const char *password) return 0; } - if (0 == MultiByteToWideChar(CP_UTF8, 0, authctxt -> user, + if (0 == MultiByteToWideChar(CP_UTF8, 0, username, -1, user_UTF16, buffer_size)) { free(user_UTF16); @@ -296,7 +353,7 @@ int sys_auth_passwd(Authctxt *authctxt, const char *password) HANDLE weakToken = INVALID_HANDLE_VALUE; debug3("Netork login attemp [%s][%ls]...", - authctxt -> user, domain_UTF16); + username, domain_UTF16); worked = LogonUserW(user_UTF16, domain_UTF16, password_UTF16, LOGON32_LOGON_NETWORK, @@ -314,6 +371,7 @@ int sys_auth_passwd(Authctxt *authctxt, const char *password) free(user_UTF16); free(password_UTF16); + if (domainslash) free(domain_UTF16); /* * If login still fails, go out. From 9b054c011e138cf5fcdf53f0358d2d0ad2badeb6 Mon Sep 17 00:00:00 2001 From: quamrulmina Date: Sun, 28 Feb 2016 13:30:11 -0600 Subject: [PATCH 12/12] moduli file and primes file should be picked from current sshd directory they were being picked from root directory /moduli and /primes ; now they are to be where sshd package is installed. --- pathnames.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/pathnames.h b/pathnames.h index 27e8620..b5919ee 100644 --- a/pathnames.h +++ b/pathnames.h @@ -43,8 +43,8 @@ # define _PATH_HOST_ECDSA_KEY_FILE "ssh_host_ecdsa_key" # define _PATH_HOST_ED25519_KEY_FILE "ssh_host_ed25519_key" # define _PATH_HOST_RSA_KEY_FILE "ssh_host_rsa_key" -# define _PATH_DH_MODULI "/moduli" -# define _PATH_DH_PRIMES "/primes" +# define _PATH_DH_MODULI "moduli" +# define _PATH_DH_PRIMES "primes" # define _PATH_SSH_PROGRAM "ssh.exe" #else