Issue #5604: non-ASCII characters in module name passed to

imp.find_module() were converted to UTF-8 while the path is
converted to the default filesystem encoding, causing nonsense.
Thanks to Andrew Svetlov.

(This time to the right branch.  Will block duplicate merge to 3.0.2.)
This commit is contained in:
Guido van Rossum 2009-03-30 22:01:35 +00:00
parent eaaec27b6e
commit 0ad59d467d
4 changed files with 117 additions and 16 deletions

View file

@ -1,4 +1,7 @@
import imp
import locale
import os
import os.path
import sys
import unittest
from test import support
@ -75,6 +78,74 @@ class ImportTests(unittest.TestCase):
support.unlink(temp_mod_name + '.pyc')
support.unlink(temp_mod_name + '.pyo')
def test_issue5604(self):
# Test cannot cover imp.load_compiled function.
# Martin von Loewis note what shared library cannot have non-ascii
# character because init_xxx function cannot be compiled
# and issue never happens for dynamic modules.
# But sources modified to follow generic way for processing pathes.
locale_encoding = locale.getpreferredencoding()
# covers utf-8 and Windows ANSI code pages
# one non-space symbol from every page
# (http://en.wikipedia.org/wiki/Code_page)
known_locales = {
'utf-8' : b'\xe4',
'cp1250' : b'\x8C',
'cp1251' : b'\xc0',
'cp1252' : b'\xc0',
'cp1253' : b'\xc1',
'cp1254' : b'\xc0',
'cp1255' : b'\xe0',
'cp1256' : b'\xe0',
'cp1257' : b'\xc0',
'cp1258' : b'\xc0',
}
special_char = known_locales.get(locale_encoding)
if special_char:
encoded_char = special_char.decode(locale_encoding)
temp_mod_name = 'test_imp_helper_' + encoded_char
test_package_name = 'test_imp_helper_package_' + encoded_char
init_file_name = os.path.join(test_package_name, '__init__.py')
try:
with open(temp_mod_name + '.py', 'w') as file:
file.write('a = 1\n')
file, filename, info = imp.find_module(temp_mod_name)
self.assertNotEquals(None, file)
self.assertTrue(filename[:-3].endswith(temp_mod_name))
self.assertEquals('.py', info[0])
self.assertEquals('U', info[1])
self.assertEquals(imp.PY_SOURCE, info[2])
mod = imp.load_module(temp_mod_name, file, filename, info)
self.assertEquals(1, mod.a)
file.close()
mod = imp.load_source(temp_mod_name, temp_mod_name + '.py')
self.assertEquals(1, mod.a)
mod = imp.load_compiled(temp_mod_name, temp_mod_name + '.pyc')
self.assertEquals(1, mod.a)
if not os.path.exists(test_package_name):
os.mkdir(test_package_name)
with open(init_file_name, 'w') as file:
file.write('b = 2\n')
package = imp.load_package(test_package_name, test_package_name)
self.assertEquals(2, package.b)
finally:
support.unlink(temp_mod_name + '.py')
support.unlink(temp_mod_name + '.pyc')
support.unlink(temp_mod_name + '.pyo')
support.unlink(init_file_name + '.py')
support.unlink(init_file_name + '.pyc')
support.unlink(init_file_name + '.pyo')
support.rmtree(test_package_name)
def test_reload(self):
import marshal
imp.reload(marshal)