diff -r d489394a73de Lib/test/test_csv.py --- a/Lib/test/test_csv.py Tue Dec 17 15:12:46 2013 +0200 +++ b/Lib/test/test_csv.py Thu Dec 19 11:05:16 2013 +0100 @@ -803,6 +803,20 @@ class TestDialectValidity(unittest.TestC mydialect.lineterminator = 4 self.assertRaises(csv.Error, mydialect) + def test_invalid_chars(self): + def create_invalid(field_name, value): + class mydialect(csv.Dialect): + pass + setattr(mydialect, field_name, value) + d = mydialect() + + for field_name in ("delimiter", "escapechar", "quotechar"): + with self.subTest(field_name=field_name): + self.assertRaises(csv.Error, create_invalid, field_name, "") + self.assertRaises(csv.Error, create_invalid, field_name, "abc") + self.assertRaises(csv.Error, create_invalid, field_name, b'x') + self.assertRaises(csv.Error, create_invalid, field_name, 5) + class TestSniffer(unittest.TestCase): sample1 = """\ diff -r d489394a73de Modules/_csv.c --- a/Modules/_csv.c Tue Dec 17 15:12:46 2013 +0200 +++ b/Modules/_csv.c Thu Dec 19 11:05:16 2013 +0100 @@ -240,15 +240,14 @@ static int if (src != Py_None) { Py_ssize_t len; len = PyUnicode_GetLength(src); - if (len > 1) { + if (len != 1) { PyErr_Format(PyExc_TypeError, "\"%s\" must be an 1-character string", name); return -1; } /* PyUnicode_READY() is called in PyUnicode_GetLength() */ - if (len > 0) - *target = PyUnicode_READ_CHAR(src, 0); + *target = PyUnicode_READ_CHAR(src, 0); } } return 0;