[3.7] bpo-31446: Copy command line that should be passed to CreateProcessW(). (GH-11141). (GH-11149)

(cherry picked from commit 7b36016a15aeed0d76a4c05a66203e6d7723aace)

Co-authored-by: Vladimir Matveev <v2matveev@outlook.com>
diff --git a/Modules/_winapi.c b/Modules/_winapi.c
index 9ea5a92..127f888 100644
--- a/Modules/_winapi.c
+++ b/Modules/_winapi.c
@@ -974,7 +974,8 @@
 _winapi.CreateProcess
 
     application_name: Py_UNICODE(accept={str, NoneType})
-    command_line: Py_UNICODE(accept={str, NoneType})
+    command_line: object
+        Can be str or None
     proc_attrs: object
         Ignored internally, can be None.
     thread_attrs: object
@@ -994,12 +995,12 @@
 
 static PyObject *
 _winapi_CreateProcess_impl(PyObject *module, Py_UNICODE *application_name,
-                           Py_UNICODE *command_line, PyObject *proc_attrs,
+                           PyObject *command_line, PyObject *proc_attrs,
                            PyObject *thread_attrs, BOOL inherit_handles,
                            DWORD creation_flags, PyObject *env_mapping,
                            Py_UNICODE *current_directory,
                            PyObject *startup_info)
-/*[clinic end generated code: output=4652a33aff4b0ae1 input=4a43b05038d639bb]*/
+/*[clinic end generated code: output=2ecaab46a05e3123 input=42ac293eaea03fc4]*/
 {
     PyObject *ret = NULL;
     BOOL result;
@@ -1007,6 +1008,7 @@
     STARTUPINFOEXW si;
     PyObject *environment = NULL;
     wchar_t *wenvironment;
+    wchar_t *command_line_copy = NULL;
     AttributeList attribute_list = {0};
 
     ZeroMemory(&si, sizeof(si));
@@ -1041,10 +1043,23 @@
         goto cleanup;
 
     si.lpAttributeList = attribute_list.attribute_list;
+    if (PyUnicode_Check(command_line)) {
+        command_line_copy = PyUnicode_AsWideCharString(command_line, NULL);
+        if (command_line_copy == NULL) {
+            goto cleanup;
+        }
+    }
+    else if (command_line != Py_None) {
+        PyErr_Format(PyExc_TypeError, 
+                     "CreateProcess() argument 2 must be str or None, not %s", 
+                     Py_TYPE(command_line)->tp_name);
+        goto cleanup;
+    }
+
 
     Py_BEGIN_ALLOW_THREADS
     result = CreateProcessW(application_name,
-                           command_line,
+                           command_line_copy,
                            NULL,
                            NULL,
                            inherit_handles,
@@ -1068,6 +1083,7 @@
                         pi.dwThreadId);
 
 cleanup:
+    PyMem_Free(command_line_copy);
     Py_XDECREF(environment);
     freeattributelist(&attribute_list);