diff -r 18d927fb8671 Objects/fileobject.c --- a/Objects/fileobject.c Wed Oct 03 13:48:17 2012 +0530 +++ b/Objects/fileobject.c Thu Oct 04 14:47:33 2012 +0530 @@ -273,6 +273,8 @@ _PyFile_SanitizeMode(char *mode) { char *upos; + char *s; + int rwa = 0, plus = 0, text_mode = 0, binary = 0; size_t len = strlen(mode); if (!len) { @@ -280,6 +282,62 @@ return -1; } + s = mode; + while (*s) { + switch (*s++) { + case 'x': + if (rwa) { + bad_mode: + PyErr_SetString(PyExc_ValueError, + "Must have exactly one of create/read/write/append " + "mode and at most one plus"); + return -1; + } + rwa = 1; + break; + case 'r': + if (rwa) + goto bad_mode; + rwa = 1; + break; + case 'w': + if (rwa) + goto bad_mode; + rwa = 1; + break; + case 'a': + if (rwa) + goto bad_mode; + rwa = 1; + break; + case 'b': + binary = 1; + if (binary && text_mode) { + bad_mix_mode: + PyErr_SetString(PyExc_ValueError, + "Can't have text and binary mode at once"); + return -1; + } + break; + case '+': + if (plus) + goto bad_mode; + plus = 1; + break; + case 'U': + break; + case 't': + text_mode = 1; + if (binary && text_mode) + goto bad_mix_mode; + break; + default: + PyErr_Format(PyExc_ValueError, + "invalid mode: %.200s", mode); + return -1; + } + } + upos = strchr(mode, 'U'); if (upos) { memmove(upos, upos+1, len-(upos-mode)); /* incl null char */