diff --git a/Lib/test/test_cmd_line.py b/Lib/test/test_cmd_line.py index fc0e3a728a6..d63dfa19f9d 100644 --- a/Lib/test/test_cmd_line.py +++ b/Lib/test/test_cmd_line.py @@ -135,12 +135,6 @@ class CmdLineTest(unittest.TestCase): self.exit_code('-c', 'pass'), 0) - # Test handling of non-ascii data - command = "assert(ord('\xe9') == 0xe9)" - self.assertEqual( - self.exit_code('-c', command), - 0) - def test_main(): test.support.run_unittest(CmdLineTest) diff --git a/Misc/NEWS b/Misc/NEWS index 5eaf640633a..1dd15d6cf25 100644 --- a/Misc/NEWS +++ b/Misc/NEWS @@ -13,7 +13,8 @@ Core and Builtins ----------------- - Issue #3705: fix crash when given a non-ascii value on the command line for - the "-c" and "-m" parameters. + the "-c" and "-m" parameters. Now the behaviour is as expected under Linux, + although under Windows it fails at a later point. - Issue #3279: Importing site at interpreter was failing silently because the site module uses the open builtin which was not initialized at the time. diff --git a/Modules/main.c b/Modules/main.c index 2148ccca477..5a84cc22bcc 100644 --- a/Modules/main.c +++ b/Modules/main.c @@ -287,7 +287,7 @@ Py_Main(int argc, wchar_t **argv) { int c; int sts; - wchar_t *command = NULL; + char *command = NULL; wchar_t *filename = NULL; wchar_t *module = NULL; FILE *fp = stdin; @@ -299,6 +299,7 @@ Py_Main(int argc, wchar_t **argv) int version = 0; int saw_unbuffered_flag = 0; PyCompilerFlags cf; + char *oldloc; cf.cf_flags = 0; @@ -309,19 +310,30 @@ Py_Main(int argc, wchar_t **argv) while ((c = _PyOS_GetOpt(argc, argv, PROGRAM_OPTS)) != EOF) { if (c == 'c') { - size_t len; + size_t r1, r2; + oldloc = setlocale(LC_ALL, NULL); + setlocale(LC_ALL, ""); + r1 = wcslen(_PyOS_optarg); + r2 = wcstombs(NULL, _PyOS_optarg, r1); + if (r2 == (size_t) -1) + Py_FatalError( + "cannot convert character encoding of -c argument"); + if (r2 > r1) + r1 = r2; + r1 += 2; /* -c is the last option; following arguments that look like options are left for the command to interpret. */ - - len = wcslen(_PyOS_optarg) + 1 + 1; - command = (wchar_t *)malloc(sizeof(wchar_t) * len); + command = (char *)malloc(r1); if (command == NULL) Py_FatalError( "not enough memory to copy -c argument"); - wcscpy(command, _PyOS_optarg); - command[len - 2] = '\n'; - command[len - 1] = 0; + r2 = wcstombs(command, _PyOS_optarg, r1); + if (r2 > r1-1) + Py_FatalError( + "not enough memory to copy -c argument"); + strcat(command, "\n"); + setlocale(LC_ALL, oldloc); break; } @@ -531,18 +543,8 @@ Py_Main(int argc, wchar_t **argv) } if (command) { - PyObject *commandObj = PyUnicode_FromUnicode( - command, wcslen(command)); + sts = PyRun_SimpleStringFlags(command, &cf) != 0; free(command); - if (commandObj != NULL) { - sts = PyRun_SimpleStringFlags( - _PyUnicode_AsString(commandObj), &cf) != 0; - } - else { - PyErr_Print(); - sts = 1; - } - Py_DECREF(commandObj); } else if (module) { sts = RunModule(module, 1); } diff --git a/Python/import.c b/Python/import.c index 13e46ad9a95..9c077fe8a66 100644 --- a/Python/import.c +++ b/Python/import.c @@ -2804,7 +2804,6 @@ call_find_module(char *name, PyObject *path) { extern int fclose(FILE *); PyObject *fob, *ret; - PyObject *pathobj; struct filedescr *fdp; char pathname[MAXPATHLEN+1]; FILE *fp = NULL; @@ -2848,9 +2847,9 @@ call_find_module(char *name, PyObject *path) fob = Py_None; Py_INCREF(fob); } - pathobj = PyUnicode_DecodeFSDefault(pathname); - ret = Py_BuildValue("NN(ssi)", - fob, pathobj, fdp->suffix, fdp->mode, fdp->type); + ret = Py_BuildValue("Os(ssi)", + fob, pathname, fdp->suffix, fdp->mode, fdp->type); + Py_DECREF(fob); PyMem_FREE(found_encoding); return ret; @@ -2861,9 +2860,7 @@ imp_find_module(PyObject *self, PyObject *args) { char *name; PyObject *path = NULL; - if (!PyArg_ParseTuple(args, "es|O:find_module", - Py_FileSystemDefaultEncoding, &name, - &path)) + if (!PyArg_ParseTuple(args, "s|O:find_module", &name, &path)) return NULL; return call_find_module(name, path); }