44#include <wchar.h>
55#include "../strbuf.h"
66#include "../run-command.h"
7+ #include "../cache.h"
78
89static const int delay [] = { 0 , 1 , 10 , 20 , 40 };
910
@@ -919,9 +920,9 @@ static pid_t mingw_spawnve_fd(const char *cmd, const char **argv, char **env,
919920{
920921 STARTUPINFOW si ;
921922 PROCESS_INFORMATION pi ;
922- struct strbuf envblk , args ;
923- wchar_t wcmd [MAX_PATH ], wdir [MAX_PATH ], * wargs ;
924- unsigned flags ;
923+ struct strbuf args ;
924+ wchar_t wcmd [MAX_PATH ], wdir [MAX_PATH ], * wargs , * wenvblk = NULL ;
925+ unsigned flags = CREATE_UNICODE_ENVIRONMENT ;
925926 BOOL ret ;
926927
927928 /* Determine whether or not we are associated to a console */
@@ -938,15 +939,14 @@ static pid_t mingw_spawnve_fd(const char *cmd, const char **argv, char **env,
938939 * instead of CREATE_NO_WINDOW to make ssh
939940 * recognize that it has no console.
940941 */
941- flags = DETACHED_PROCESS ;
942+ flags | = DETACHED_PROCESS ;
942943 } else {
943944 /* There is already a console. If we specified
944945 * DETACHED_PROCESS here, too, Windows would
945946 * disassociate the child from the console.
946947 * The same is true for CREATE_NO_WINDOW.
947948 * Go figure!
948949 */
949- flags = 0 ;
950950 CloseHandle (cons );
951951 }
952952 memset (& si , 0 , sizeof (si ));
@@ -985,6 +985,7 @@ static pid_t mingw_spawnve_fd(const char *cmd, const char **argv, char **env,
985985 if (env ) {
986986 int count = 0 ;
987987 char * * e , * * sorted_env ;
988+ int size = 0 , wenvsz = 0 , wenvpos = 0 ;
988989
989990 for (e = env ; * e ; e ++ )
990991 count ++ ;
@@ -994,20 +995,22 @@ static pid_t mingw_spawnve_fd(const char *cmd, const char **argv, char **env,
994995 memcpy (sorted_env , env , sizeof (* sorted_env ) * (count + 1 ));
995996 qsort (sorted_env , count , sizeof (* sorted_env ), env_compare );
996997
997- strbuf_init ( & envblk , 0 );
998+ /* create environment block from temporary environment */
998999 for (e = sorted_env ; * e ; e ++ ) {
999- strbuf_addstr (& envblk , * e );
1000- strbuf_addch (& envblk , '\0' );
1000+ size = 2 * strlen (* e ) + 2 ; /* +2 for final \0 */
1001+ ALLOC_GROW (wenvblk , (wenvpos + size ) * sizeof (wchar_t ), wenvsz );
1002+ wenvpos += xutftowcs (& wenvblk [wenvpos ], * e , size ) + 1 ;
10011003 }
1004+ /* add final \0 terminator */
1005+ wenvblk [wenvpos ] = 0 ;
10021006 free (sorted_env );
10031007 }
10041008
10051009 memset (& pi , 0 , sizeof (pi ));
10061010 ret = CreateProcessW (wcmd , wargs , NULL , NULL , TRUE, flags ,
1007- env ? envblk . buf : NULL , dir ? wdir : NULL , & si , & pi );
1011+ wenvblk , dir ? wdir : NULL , & si , & pi );
10081012
1009- if (env )
1010- strbuf_release (& envblk );
1013+ free (wenvblk );
10111014 free (wargs );
10121015
10131016 if (!ret ) {
0 commit comments