diff --git a/tests/README b/tests/README index ef00705712..0cb526c3b4 100644 --- a/tests/README +++ b/tests/README @@ -2,3 +2,7 @@ This directory contains tests for various functionality areas of MicroPython. To run all stable tests, run "run-tests" script in this directory. Note that bytecode tests are not yet stable and should be run separately in "bytecode" subdirectory. + +When creating new tests, anything that relies on float support should go in the +float/ subdirectory. Anything that relies on import x, where x is not a built-in +module, should go in the import/ subdirectory. diff --git a/tests/basics/int-divzero.py b/tests/basics/int-divzero.py index d1fc579321..28ec2a6995 100644 --- a/tests/basics/int-divzero.py +++ b/tests/basics/int-divzero.py @@ -1,8 +1,3 @@ -try: - 1 / 0 -except ZeroDivisionError: - print("ZeroDivisionError") - try: 1 // 0 except ZeroDivisionError: diff --git a/tests/basics/list1.py b/tests/basics/list1.py index a0c8afc4f8..c8317baa3d 100644 --- a/tests/basics/list1.py +++ b/tests/basics/list1.py @@ -22,8 +22,3 @@ print(x) print(x[1:]) print(x[:-1]) print(x[2:3]) - -try: - print(x[1.0]) -except TypeError: - print("TypeError") diff --git a/tests/basics/modulo.py b/tests/basics/modulo.py index 4d83db6ec8..c95305d13d 100644 --- a/tests/basics/modulo.py +++ b/tests/basics/modulo.py @@ -1,5 +1,6 @@ # check modulo matches python definition -# This test compiler version + +# this tests compiler constant folding print(123 % 7) print(-123 % 7) print(123 % -7) @@ -20,17 +21,3 @@ print(a % b) print(a % -b) print(-a % b) print(-a % -b) - -if False: - print(1.23456 % 0.7) - print(-1.23456 % 0.7) - print(1.23456 % -0.7) - print(-1.23456 % -0.7) - - a = 1.23456 - b = 0.7 - print(a % b) - print(a % -b) - print(-a % b) - print(-a % -b) - diff --git a/tests/basics/string-format-modulo.py b/tests/basics/string-format-modulo.py index 8e58be18c8..0e2c1d1096 100644 --- a/tests/basics/string-format-modulo.py +++ b/tests/basics/string-format-modulo.py @@ -23,11 +23,9 @@ except TypeError: print("%s" % True) print("%s" % 1) -print("%s" % 1.0) print("%r" % True) print("%r" % 1) -print("%r" % 1.0) print("%c" % 48) print("%c" % 'a') @@ -37,28 +35,16 @@ print("%d" % 10) print("%+d" % 10) print("% d" % 10) print("%d" % -10) -print("%d" % 1.0) print("%d" % True) print("%i" % -10) -print("%i" % 1.0) print("%i" % True) print("%u" % -10) -print("%u" % 1.0) print("%u" % True) print("%x" % 18) -print("%x" % 18.0) print("%o" % 18) -print("%o" % 18.0) print("%X" % 18) -print("%X" % 18.0) print("%#x" % 18) print("%#X" % 18) print("%#6o" % 18) print("%#6x" % 18) print("%#06x" % 18) -print("%e" % 1.23456) -print("%E" % 1.23456) -print("%f" % 1.23456) -print("%F" % 1.23456) -print("%g" % 1.23456) -print("%G" % 1.23456) diff --git a/tests/basics/string-format.py b/tests/basics/string-format.py index 2d6d0cc721..84ea054758 100644 --- a/tests/basics/string-format.py +++ b/tests/basics/string-format.py @@ -60,26 +60,6 @@ test("{:@<6d}", -123) test("{:@=6d}", -123) test("{:06d}", -123) -test("{:10.4e}", 123.456) -test("{:10.4e}", -123.456) -test("{:10.4f}", 123.456) -test("{:10.4f}", -123.456) -test("{:10.4g}", 123.456) -test("{:10.4g}", -123.456) -test("{:e}", 100) -test("{:f}", 200) -test("{:g}", 300) - -test("{:10.4E}", 123.456) -test("{:10.4E}", -123.456) -test("{:10.4F}", 123.456) -test("{:10.4F}", -123.456) -test("{:10.4G}", 123.456) -test("{:10.4G}", -123.456) - -# The following fails right now -#test("{:10.1}", 0.0) - def test_fmt(conv, fill, alignment, sign, prefix, width, precision, type, arg): fmt = '{' if conv: @@ -137,71 +117,4 @@ if full_tests: for str in ('', 'a', 'bcd', 'This is a test with a longer string'): test_fmt(conv, fill, alignment, '', '', width, '', 's', str) -eg_nums = (0.0, -0.0, 0.1, 1.234, 12.3459, 1.23456789, 123456789.0, -0.0, - -0.1, -1.234, -12.3459, 1e4, 1e-4, 1e5, 1e-5, 1e6, 1e-6, 1e10, - 1e37, -1e37, 1e-37, -1e-37, - 1.23456e8, 1.23456e7, 1.23456e6, 1.23456e5, 1.23456e4, 1.23456e3, 1.23456e2, 1.23456e1, 1.23456e0, - 1.23456e-1, 1.23456e-2, 1.23456e-3, 1.23456e-4, 1.23456e-5, 1.23456e-6, 1.23456e-7, 1.23456e-8, - -1.23456e8, -1.23456e7, -1.23456e6, -1.23456e5, -1.23456e4, -1.23456e3, -1.23456e2, -1.23456e1, -1.23456e0, - -1.23456e-1, -1.23456e-2, -1.23456e-3, -1.23456e-4, -1.23456e-5, -1.23456e-6, -1.23456e-7, -1.23456e-8) - -if full_tests: - for type in ('e', 'E', 'g', 'G', 'n'): - for width in ('', '4', '6', '8', '10'): - for alignment in ('', '<', '>', '=', '^'): - for fill in ('', '@', '0', ' '): - for sign in ('', '+', '-', ' '): - for prec in ('', '1', '3', '6'): - for num in eg_nums: - test_fmt('', fill, alignment, sign, '', width, prec, type, num) - -# Note: We use 1.23459 rather than 1.2345 because '{:3f}'.format(1.2345) -# rounds differently than print("%.3f", 1.2345); - -f_nums = (0.0, -0.0, 0.0001, 0.001, 0.01, 0.1, 1.0, 10.0, - 0.0012, 0.0123, 0.1234, 1.23459, 12.3456, - -0.0001, -0.001, -0.01, -0.1, -1.0, -10.0, - -0.0012, -0.0123, -0.1234, -1.23459, -12.3456) - -if full_tests: - for type in ('f', 'F'): - for width in ('', '4', '6', '8', '10'): - for alignment in ('', '<', '>', '=', '^'): - for fill in ('', ' ', '0', '@'): - for sign in ('', '+', '-', ' '): - # An empty precision defaults to 6, but when uPy is - # configured to use a float, we can only use a - # precision of 6 with numbers less than 10 and still - # get results that compare to CPython (which uses - # long doubles). - for prec in ('1', '2', '3'): - for num in f_nums: - test_fmt('', fill, alignment, sign, '', width, prec, type, num) - for num in int_nums2: - test_fmt('', fill, alignment, sign, '', width, '', type, num) - -pct_nums1 = (0.1, 0.58, 0.99, -0.1, -0.58, -0.99) -pct_nums2 = (True, False, 1, 0, -1) - -if full_tests: - type = '%' - for width in ('', '4', '6', '8', '10'): - for alignment in ('', '<', '>', '=', '^'): - for fill in ('', ' ', '0', '@'): - for sign in ('', '+', '-', ' '): - # An empty precision defaults to 6, but when uPy is - # configured to use a float, we can only use a - # precision of 6 with numbers less than 10 and still - # get results that compare to CPython (which uses - # long doubles). - for prec in ('1', '2', '3'): - for num in pct_nums1: - test_fmt('', fill, alignment, sign, '', width, prec, type, num) - for num in pct_nums2: - test_fmt('', fill, alignment, sign, '', width, '', type, num) - -# We don't currently test a type of '' with floats (see the detailed comment -# in objstr.c) - # TODO Add tests for erroneous format strings. - diff --git a/tests/basics/true-value.py b/tests/basics/true-value.py index 1dd547f326..9ec209fe82 100644 --- a/tests/basics/true-value.py +++ b/tests/basics/true-value.py @@ -9,12 +9,6 @@ if not None: if not 0: print("0") -if not 0.0: - print("float 0") - -if not 0+0j: - print("complex 0") - if not "": print("Empty string") if "foo": diff --git a/tests/basics/types1.py b/tests/basics/types1.py index 57b33b842b..38a20d6803 100644 --- a/tests/basics/types1.py +++ b/tests/basics/types1.py @@ -2,8 +2,6 @@ print(bool) print(int) -print(float) -print(complex) print(tuple) print(list) print(set) @@ -11,8 +9,6 @@ print(dict) print(type(bool()) == bool) print(type(int()) == int) -print(type(float()) == float) -print(type(complex()) == complex) print(type(tuple()) == tuple) print(type(list()) == list) print(type(set()) == set) @@ -20,8 +16,6 @@ print(type(dict()) == dict) print(type(False) == bool) print(type(0) == int) -print(type(0.0) == float) -print(type(1j) == complex) print(type(()) == tuple) print(type([]) == list) print(type({None}) == set) diff --git a/tests/basics/types2.py b/tests/basics/types2.py index 83a69c918f..ba7be6b154 100644 --- a/tests/basics/types2.py +++ b/tests/basics/types2.py @@ -9,4 +9,6 @@ print(int == int) print(int != list) d = {} -d[int] = float +d[int] = list +d[list] = int +print(len(d)) diff --git a/tests/basics/float1.py b/tests/float/float1.py similarity index 100% rename from tests/basics/float1.py rename to tests/float/float1.py diff --git a/tests/float/int-divzero.py b/tests/float/int-divzero.py new file mode 100644 index 0000000000..b037dd8c7b --- /dev/null +++ b/tests/float/int-divzero.py @@ -0,0 +1,4 @@ +try: + 1 / 0 +except ZeroDivisionError: + print("ZeroDivisionError") diff --git a/tests/float/list-index.py b/tests/float/list-index.py new file mode 100644 index 0000000000..13e4557af7 --- /dev/null +++ b/tests/float/list-index.py @@ -0,0 +1,8 @@ +x = [1, 2] + +print(x[1]) + +try: + print(x[1.0]) +except TypeError: + print("TypeError") diff --git a/tests/basics/math-fun-bool.py b/tests/float/math-fun-bool.py similarity index 100% rename from tests/basics/math-fun-bool.py rename to tests/float/math-fun-bool.py diff --git a/tests/basics/math-fun.py b/tests/float/math-fun.py similarity index 100% rename from tests/basics/math-fun.py rename to tests/float/math-fun.py diff --git a/tests/float/modulo.py b/tests/float/modulo.py new file mode 100644 index 0000000000..911268513a --- /dev/null +++ b/tests/float/modulo.py @@ -0,0 +1,14 @@ +# check modulo matches python definition +# TODO we currenty fail with this +if False: + print(1.23456 % 0.7) + print(-1.23456 % 0.7) + print(1.23456 % -0.7) + print(-1.23456 % -0.7) + + a = 1.23456 + b = 0.7 + print(a % b) + print(a % -b) + print(-a % b) + print(-a % -b) diff --git a/tests/float/string-format-modulo.py b/tests/float/string-format-modulo.py new file mode 100644 index 0000000000..f2117f3565 --- /dev/null +++ b/tests/float/string-format-modulo.py @@ -0,0 +1,16 @@ +print("%s" % 1.0) +print("%r" % 1.0) + +print("%d" % 1.0) +print("%i" % 1.0) +print("%u" % 1.0) +print("%x" % 18.0) +print("%o" % 18.0) +print("%X" % 18.0) + +print("%e" % 1.23456) +print("%E" % 1.23456) +print("%f" % 1.23456) +print("%F" % 1.23456) +print("%g" % 1.23456) +print("%G" % 1.23456) diff --git a/tests/float/string-format.py b/tests/float/string-format.py new file mode 100644 index 0000000000..b5ff68b8ca --- /dev/null +++ b/tests/float/string-format.py @@ -0,0 +1,123 @@ +# Change the following to True to get a much more comprehensive set of tests +# to run, albeit, which take considerably longer. + +full_tests = False + +def test(fmt, *args): + print('{:8s}'.format(fmt) + '>' + fmt.format(*args) + '<') + +test("{:10.4e}", 123.456) +test("{:10.4e}", -123.456) +test("{:10.4f}", 123.456) +test("{:10.4f}", -123.456) +test("{:10.4g}", 123.456) +test("{:10.4g}", -123.456) +test("{:e}", 100) +test("{:f}", 200) +test("{:g}", 300) + +test("{:10.4E}", 123.456) +test("{:10.4E}", -123.456) +test("{:10.4F}", 123.456) +test("{:10.4F}", -123.456) +test("{:10.4G}", 123.456) +test("{:10.4G}", -123.456) + +# The following fails right now +#test("{:10.1}", 0.0) + +def test_fmt(conv, fill, alignment, sign, prefix, width, precision, type, arg): + fmt = '{' + if conv: + fmt += '!' + fmt += conv + fmt += ':' + if alignment: + fmt += fill + fmt += alignment + fmt += sign + fmt += prefix + fmt += width + if precision: + fmt += '.' + fmt += precision + fmt += type + fmt += '}' + test(fmt, arg) + if fill == '0' and alignment == '=': + fmt = '{:' + fmt += sign + fmt += prefix + fmt += width + if precision: + fmt += '.' + fmt += precision + fmt += type + fmt += '}' + test(fmt, arg) + +eg_nums = (0.0, -0.0, 0.1, 1.234, 12.3459, 1.23456789, 123456789.0, -0.0, + -0.1, -1.234, -12.3459, 1e4, 1e-4, 1e5, 1e-5, 1e6, 1e-6, 1e10, + 1e37, -1e37, 1e-37, -1e-37, + 1.23456e8, 1.23456e7, 1.23456e6, 1.23456e5, 1.23456e4, 1.23456e3, 1.23456e2, 1.23456e1, 1.23456e0, + 1.23456e-1, 1.23456e-2, 1.23456e-3, 1.23456e-4, 1.23456e-5, 1.23456e-6, 1.23456e-7, 1.23456e-8, + -1.23456e8, -1.23456e7, -1.23456e6, -1.23456e5, -1.23456e4, -1.23456e3, -1.23456e2, -1.23456e1, -1.23456e0, + -1.23456e-1, -1.23456e-2, -1.23456e-3, -1.23456e-4, -1.23456e-5, -1.23456e-6, -1.23456e-7, -1.23456e-8) + +if full_tests: + for type in ('e', 'E', 'g', 'G', 'n'): + for width in ('', '4', '6', '8', '10'): + for alignment in ('', '<', '>', '=', '^'): + for fill in ('', '@', '0', ' '): + for sign in ('', '+', '-', ' '): + for prec in ('', '1', '3', '6'): + for num in eg_nums: + test_fmt('', fill, alignment, sign, '', width, prec, type, num) + +# Note: We use 1.23459 rather than 1.2345 because '{:3f}'.format(1.2345) +# rounds differently than print("%.3f", 1.2345); + +f_nums = (0.0, -0.0, 0.0001, 0.001, 0.01, 0.1, 1.0, 10.0, + 0.0012, 0.0123, 0.1234, 1.23459, 12.3456, + -0.0001, -0.001, -0.01, -0.1, -1.0, -10.0, + -0.0012, -0.0123, -0.1234, -1.23459, -12.3456) + +if full_tests: + for type in ('f', 'F'): + for width in ('', '4', '6', '8', '10'): + for alignment in ('', '<', '>', '=', '^'): + for fill in ('', ' ', '0', '@'): + for sign in ('', '+', '-', ' '): + # An empty precision defaults to 6, but when uPy is + # configured to use a float, we can only use a + # precision of 6 with numbers less than 10 and still + # get results that compare to CPython (which uses + # long doubles). + for prec in ('1', '2', '3'): + for num in f_nums: + test_fmt('', fill, alignment, sign, '', width, prec, type, num) + for num in int_nums2: + test_fmt('', fill, alignment, sign, '', width, '', type, num) + +pct_nums1 = (0.1, 0.58, 0.99, -0.1, -0.58, -0.99) +pct_nums2 = (True, False, 1, 0, -1) + +if full_tests: + type = '%' + for width in ('', '4', '6', '8', '10'): + for alignment in ('', '<', '>', '=', '^'): + for fill in ('', ' ', '0', '@'): + for sign in ('', '+', '-', ' '): + # An empty precision defaults to 6, but when uPy is + # configured to use a float, we can only use a + # precision of 6 with numbers less than 10 and still + # get results that compare to CPython (which uses + # long doubles). + for prec in ('1', '2', '3'): + for num in pct_nums1: + test_fmt('', fill, alignment, sign, '', width, prec, type, num) + for num in pct_nums2: + test_fmt('', fill, alignment, sign, '', width, '', type, num) + +# We don't currently test a type of '' with floats (see the detailed comment +# in objstr.c) diff --git a/tests/float/true-value.py b/tests/float/true-value.py new file mode 100644 index 0000000000..df415f0031 --- /dev/null +++ b/tests/float/true-value.py @@ -0,0 +1,7 @@ +# Test true-ish value handling + +if not 0.0: + print("float 0") + +if not 0+0j: + print("complex 0") diff --git a/tests/float/types.py b/tests/float/types.py new file mode 100644 index 0000000000..75674c9246 --- /dev/null +++ b/tests/float/types.py @@ -0,0 +1,17 @@ +# float types + +print(float) +print(complex) + +print(type(float()) == float) +print(type(complex()) == complex) + +print(type(0.0) == float) +print(type(1j) == complex) + +# hashing float types + +d = dict() +d[float] = complex +d[complex] = float +print(len(d)) diff --git a/tests/basics/import-pkg1.py b/tests/import/import-pkg1.py similarity index 100% rename from tests/basics/import-pkg1.py rename to tests/import/import-pkg1.py diff --git a/tests/basics/import-pkg2.py b/tests/import/import-pkg2.py similarity index 100% rename from tests/basics/import-pkg2.py rename to tests/import/import-pkg2.py diff --git a/tests/basics/import-pkg3.py b/tests/import/import-pkg3.py similarity index 100% rename from tests/basics/import-pkg3.py rename to tests/import/import-pkg3.py diff --git a/tests/basics/import-pkg4.py b/tests/import/import-pkg4.py similarity index 100% rename from tests/basics/import-pkg4.py rename to tests/import/import-pkg4.py diff --git a/tests/basics/import-pkg5.py b/tests/import/import-pkg5.py similarity index 100% rename from tests/basics/import-pkg5.py rename to tests/import/import-pkg5.py diff --git a/tests/basics/import1a.py b/tests/import/import1a.py similarity index 100% rename from tests/basics/import1a.py rename to tests/import/import1a.py diff --git a/tests/basics/import1b.py b/tests/import/import1b.py similarity index 100% rename from tests/basics/import1b.py rename to tests/import/import1b.py diff --git a/tests/basics/import2a.py b/tests/import/import2a.py similarity index 100% rename from tests/basics/import2a.py rename to tests/import/import2a.py diff --git a/tests/basics/import3a.py b/tests/import/import3a.py similarity index 100% rename from tests/basics/import3a.py rename to tests/import/import3a.py diff --git a/tests/basics/pkg/__init__.py b/tests/import/pkg/__init__.py similarity index 100% rename from tests/basics/pkg/__init__.py rename to tests/import/pkg/__init__.py diff --git a/tests/basics/pkg/mod.py b/tests/import/pkg/mod.py similarity index 100% rename from tests/basics/pkg/mod.py rename to tests/import/pkg/mod.py diff --git a/tests/basics/pkg2/__init__.py b/tests/import/pkg2/__init__.py similarity index 100% rename from tests/basics/pkg2/__init__.py rename to tests/import/pkg2/__init__.py diff --git a/tests/basics/pkg2/mod1.py b/tests/import/pkg2/mod1.py similarity index 100% rename from tests/basics/pkg2/mod1.py rename to tests/import/pkg2/mod1.py diff --git a/tests/basics/pkg2/mod2.py b/tests/import/pkg2/mod2.py similarity index 100% rename from tests/basics/pkg2/mod2.py rename to tests/import/pkg2/mod2.py diff --git a/tests/basics/pkg3/__init__.py b/tests/import/pkg3/__init__.py similarity index 100% rename from tests/basics/pkg3/__init__.py rename to tests/import/pkg3/__init__.py diff --git a/tests/basics/pkg3/mod1.py b/tests/import/pkg3/mod1.py similarity index 100% rename from tests/basics/pkg3/mod1.py rename to tests/import/pkg3/mod1.py diff --git a/tests/basics/pkg3/mod2.py b/tests/import/pkg3/mod2.py similarity index 100% rename from tests/basics/pkg3/mod2.py rename to tests/import/pkg3/mod2.py diff --git a/tests/basics/pkg3/subpkg1/__init__.py b/tests/import/pkg3/subpkg1/__init__.py similarity index 100% rename from tests/basics/pkg3/subpkg1/__init__.py rename to tests/import/pkg3/subpkg1/__init__.py diff --git a/tests/basics/pkg3/subpkg1/mod1.py b/tests/import/pkg3/subpkg1/mod1.py similarity index 100% rename from tests/basics/pkg3/subpkg1/mod1.py rename to tests/import/pkg3/subpkg1/mod1.py diff --git a/tests/basics/try-module.py b/tests/import/try-module.py similarity index 100% rename from tests/basics/try-module.py rename to tests/import/try-module.py diff --git a/tests/run-tests b/tests/run-tests index bd6e50bbd2..da18c6c765 100755 --- a/tests/run-tests +++ b/tests/run-tests @@ -29,7 +29,8 @@ failed_tests = [] tests = [] if not sys.argv[1:]: - tests = sorted(glob('basics/*.py') + glob('io/*.py') + glob('misc/*.py')) + test_dirs = ('basics', 'float', 'import', 'io', 'misc') + tests = sorted(test_file for test_files in (glob('{}/*.py'.format(dir)) for dir in test_dirs) for test_file in test_files) else: tests = sys.argv[1:] @@ -56,13 +57,9 @@ for test_file in tests: if test_on_pyboard: pyb.enter_raw_repl() try: - if test_file == 'basics/memoryerror.py': - # this test crashes the pyboard - output_mupy = b'CRASH' - else: - output_mupy = pyb.execfile(test_file).replace(b'\r\n', b'\n') + output_mupy = pyb.execfile(test_file).replace(b'\r\n', b'\n') except pyboard.PyboardError: - output_mupy = b'CRASH\n' + output_mupy + output_mupy = b'CRASH' else: try: output_mupy = subprocess.check_output([MP_PY, '-X', 'emit=bytecode', test_file])