From 3c316c0b38b4a54c7201483203eebae672ede2e0 Mon Sep 17 00:00:00 2001 From: Alistair Buxton Date: Sun, 5 Mar 2023 01:41:07 +0000 Subject: [PATCH 01/11] Use pytest instead of py.test Apparently `py.test` is no longer a supported way of referring to the pytest module. --- src/tox.ini | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/tox.ini b/src/tox.ini index 6ab42f2..df4bb57 100644 --- a/src/tox.ini +++ b/src/tox.ini @@ -5,7 +5,7 @@ skip_missing_interpreters = True [testenv] commands = python setup.py install - coverage run -m py.test -v -r wsx + coverage run -m pytest -v -r wsx coverage report deps = mock From e2e3ecfb6b6c336c7006527794f8950d58eeee62 Mon Sep 17 00:00:00 2001 From: Alistair Buxton Date: Mon, 6 Mar 2023 20:41:46 +0000 Subject: [PATCH 02/11] Test all extant Python versions "3.10" needs quotes, otherwise it becomes 3.1. --- .github/workflows/test.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index 4bae59c..aee538e 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -11,7 +11,7 @@ jobs: runs-on: ubuntu-latest strategy: matrix: - python: [3.7, 3.8] + python: ["3.7", "3.8", "3.9", "3.10", "3.11"] steps: # Linux deps From 78513797676875773d880f8b1ab55726d755670c Mon Sep 17 00:00:00 2001 From: Alistair Buxton Date: Sun, 5 Mar 2023 01:06:33 +0000 Subject: [PATCH 03/11] Fix bug when deleting from flash The terminating null should be sent after the offset. Sending it before causes the offset to be 256x too big, because it is little endian. Also adds a log message, not shown by default. --- src/ttblit/core/blitserial.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/ttblit/core/blitserial.py b/src/ttblit/core/blitserial.py index cad3cd1..ef990e0 100644 --- a/src/ttblit/core/blitserial.py +++ b/src/ttblit/core/blitserial.py @@ -122,8 +122,10 @@ def send_file(self, file, drive, directory=pathlib.PurePosixPath('/'), auto_laun raise RuntimeError(f"Failed to save/flash {file_name}: {response.decode()}") def erase(self, offset): - self.write(b'32BLERSE\x00') + logging.info(f'Deleting at offset {offset}') + self.write(b'32BLERSE') self.write(struct.pack(" Date: Mon, 6 Mar 2023 22:25:29 +0000 Subject: [PATCH 04/11] Use "self.port" instead of "serial.port" in error message --- src/ttblit/core/blitserial.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ttblit/core/blitserial.py b/src/ttblit/core/blitserial.py index ef990e0..87df8d7 100644 --- a/src/ttblit/core/blitserial.py +++ b/src/ttblit/core/blitserial.py @@ -69,7 +69,7 @@ def reset(self, timeout=5.0): return except BlitSerialException: time.sleep(0.1) - raise RuntimeError(f"Failed to connect to 32Blit on {serial.port} after reset") + raise RuntimeError(f"Failed to connect to 32Blit on {self.port} after reset") def send_file(self, file, drive, directory=pathlib.PurePosixPath('/'), auto_launch=False): sent_byte_count = 0 From 2d46a29e486f6585245372f923f3112c884b5ec8 Mon Sep 17 00:00:00 2001 From: Alistair Buxton Date: Tue, 7 Mar 2023 00:36:34 +0000 Subject: [PATCH 05/11] Add unit tests for BlitSerial --- src/tests/test_blitserial.py | 185 +++++++++++++++++++++++++++++++++++ 1 file changed, 185 insertions(+) create mode 100644 src/tests/test_blitserial.py diff --git a/src/tests/test_blitserial.py b/src/tests/test_blitserial.py new file mode 100644 index 0000000..e3fc752 --- /dev/null +++ b/src/tests/test_blitserial.py @@ -0,0 +1,185 @@ +import io +import pathlib + +import mock +import pytest +from ttblit.core.blitserial import BlitSerial, BlitSerialException + + +def test_comport(): + """Test serial port discovery.""" + def comports(): + class Comport: + def __init__(self, vid, pid, device): + self.vid = vid + self.pid = pid + self.device = device + + for c in ((0, 0, "notblit"), (0, 0, "notblit"), (0x0483, 0x5740, "_fakeserial_"), (None, None, "_noidserial_")): + yield Comport(*c) + + with mock.patch("serial.tools.list_ports.comports", return_value=comports()): + BlitSerial.validate_comport("auto") + + with mock.patch("serial.tools.list_ports.comports", return_value=comports()): + BlitSerial.validate_comport("all") + + with mock.patch("serial.tools.list_ports.comports", return_value=comports()): + BlitSerial.validate_comport("_fakeserial_") + + with mock.patch("serial.tools.list_ports.comports", return_value=comports()): + BlitSerial.validate_comport("_noidserial_") + + with pytest.raises(RuntimeError): + # Without the mock, no blit should be connected. + BlitSerial.validate_comport("auto") + + with pytest.raises(RuntimeError): + # Without the mock, no blit should be connected. + BlitSerial.validate_comport("_fakeserial_") + + +class BlitSerialTester(BlitSerial): + """Mock wrapper around BlitSerial that uses BytesIO to simulate the hardware port.""" + def __init__(self, output): + self.__reader = io.BytesIO(output) + self.__writer = io.BytesIO() + + def read(self, n): + return self.__reader.read(n) + + def write(self, b): + return self.__writer.write(b) + + def sent_bytes(self): + return bytes(self.__writer.getbuffer()) + + def open(self): + raise BlitSerialException() + + @property + def in_waiting(self): + return 0 + + def flush(self): + pass + + def reset_output_buffer(self): + pass + + def close(self): + pass + + @property + def port(self): + return "_fakeserial_" + + +def test_status(): + b = BlitSerialTester(b"32BL_EXT") + + assert b.status == 'game' + assert b.sent_bytes() == b'32BLINFO\x00' + + +def test_reset(): + b = BlitSerialTester(b"") + with pytest.raises(RuntimeError): + b.reset() + assert b.sent_bytes() == b"32BL_RST\x00" + + +def test_send_file(test_resources): + f = pathlib.Path(test_resources / "doom-fire.blit") + f_data = f.read_bytes() + + b = BlitSerialTester(b'32BL__OK\x00\x00') + b.send_file(f, "flash", auto_launch=True) + assert b.sent_bytes() == b'32BLPROGdoom-fire.blit\x0026322\x00' + f_data + b'32BLLNCHflash:/0\x00' + + b = BlitSerialTester(b'32BL__OK\x00\x00') + b.send_file(f, "flash", auto_launch=False) + assert b.sent_bytes() == b'32BLPROGdoom-fire.blit\x0026322\x00' + f_data + + b = BlitSerialTester(b'32BL__OK\x00\x00') + b.send_file(f, "sd", auto_launch=True) + assert b.sent_bytes() == b'32BLSAVE//doom-fire.blit\x0026322\x00' + f_data + b'32BLLNCH//doom-fire.blit\x00' + + b = BlitSerialTester(b'32BL__OK\x00\x00') + b.send_file(f, "sd", auto_launch=False) + assert b.sent_bytes() == b'32BLSAVE//doom-fire.blit\x0026322\x00' + f_data + + with pytest.raises(TypeError): + b = BlitSerialTester(b'32BL__OK\x00\x00') + b.send_file(f, "no_such_drive") + + +def test_erase(): + b = BlitSerialTester(b"") + b.erase(0x12345678) + assert b.sent_bytes() == b'32BLERSE\x78\x56\x34\x12\x00' + + +def test_list(): + import struct + from ttblit.core.struct import struct_blit_meta_standalone + from ttblit.core.palette import Palette + + palette = Palette() + palette.get_entry(255, 255, 255, 255) + + # TODO: This should be a fixture or something + metadata = { + 'checksum': 0x12345678, + 'date': "date", + 'title': "title", + 'description': "description", + 'version': "version", + 'author': "author", + 'category': "category", + 'filetypes': "", + 'url': "", + 'icon': { + 'data': { + 'width': 8, + 'height': 8, + 'palette': palette.tostruct(), + 'pixels': b'\x00' * 8 * 8, + }, + }, + 'splash': { + 'data': { + 'width': 128, + 'height': 96, + 'palette': palette.tostruct(), + 'pixels': b'\x00' * 128 * 96, + }, + }, + } + + test_meta = struct_blit_meta_standalone.build({'data': metadata}) + + fake_offs = 0x50000 + fake_size = 0x15000 + + test_data = b''.join([ + struct.pack(" Date: Fri, 10 Mar 2023 14:37:58 +0000 Subject: [PATCH 06/11] Fix the build badge --- src/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/README.md b/src/README.md index 279ed51..3399d21 100644 --- a/src/README.md +++ b/src/README.md @@ -1,6 +1,6 @@ # 32blit Tools -[![Build Status](https://shields.io/github/workflow/status/32blit/32blit-tools/Python%20Tests.svg)](https://github.com/32blit/32blit-tools/actions/workflows/test.yml) +[![Build Status](https://img.shields.io/github/actions/workflow/status/32blit/32blit-tools/test.yml?branch=master)](https://github.com/32blit/32blit-tools/actions/workflows/test.yml) [![Coverage Status](https://coveralls.io/repos/github/32blit/32blit-tools/badge.svg?branch=master)](https://coveralls.io/github/32blit/32blit-tools?branch=master) [![PyPi Package](https://img.shields.io/pypi/v/32blit.svg)](https://pypi.python.org/pypi/32blit) [![Python Versions](https://img.shields.io/pypi/pyversions/32blit.svg)](https://pypi.python.org/pypi/32blit) From 87857a27d57cf0bd898c81ea4a17cdf08c3fa181 Mon Sep 17 00:00:00 2001 From: Phil Howard Date: Wed, 17 May 2023 14:02:34 +0100 Subject: [PATCH 07/11] Fix README build badge. --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 43e1ef5..69fedd5 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # 32blit Tools -[![Build Status](https://shields.io/github/workflow/status/32blit/32blit-tools/Python%20Tests.svg)](https://github.com/32blit/32blit-tools/actions/workflows/test.yml) +[![Build Status](https://img.shields.io/github/actions/workflow/status/32blit/32blit-tools/test.yml?branch=master)](https://github.com/32blit/32blit-tools/actions/workflows/test.yml) [![Coverage Status](https://coveralls.io/repos/github/32blit/32blit-tools/badge.svg?branch=master)](https://coveralls.io/github/32blit/32blit-tools?branch=master) [![PyPi Package](https://img.shields.io/pypi/v/32blit.svg)](https://pypi.python.org/pypi/32blit) [![Python Versions](https://img.shields.io/pypi/pyversions/32blit.svg)](https://pypi.python.org/pypi/32blit) From 2eeb6438f0a850469100ef98a0bca8a76257b5d4 Mon Sep 17 00:00:00 2001 From: Charlie Birks Date: Thu, 16 May 2024 12:35:20 +0100 Subject: [PATCH 08/11] Use a real image in test_image_struct --- src/tests/resources/no_image.raw | Bin 0 -> 12288 bytes src/tests/test_image_struct.py | 22 ++++++++++++++++------ 2 files changed, 16 insertions(+), 6 deletions(-) create mode 100644 src/tests/resources/no_image.raw diff --git a/src/tests/resources/no_image.raw b/src/tests/resources/no_image.raw new file mode 100644 index 0000000000000000000000000000000000000000..b4a7514fb1c98e379ddae6ab2b371db76f676ad5 GIT binary patch literal 12288 zcmeH~(Uz+q3`K3N+S~vC;G2^G2}p3N?aWKET0sPMast>+Q&=bv3WNfoKqwFjgaV;J zC=d#S0)L>u?RLN2v&~eY?|h$)J?6)C^CG($kgYEE=8gKp>HBaTs3J9E!C&7s8k6`W z7$!>vYKQ!V3}eKY?~L)9R~mYj4?3*F-!=~@?dACye)3n~#sL%mRsdZ;^s(XRFiLr# zzw$8&nc+`L=r~{=j`(wDD4G&Y`6&aIKXSm}r<#8wliB(DW4;Jb@qGs@zUBjO9Psp) z{G0HX9^Z4I!VmeL{y*gR9jNg`{y6?w1z5ZBPdx`3e9d1Wzsxnt|8D=KA$9({i>Jlc zd_FyO{Vm-orYZ4@04aRkf6wRir0;|)mwBQcUis)LXzH{{Ee~tT%%4}JfDZiRa)}>v zkqO>7u*Vm^jKD;|ivtJwM`yfkP_kJ*V#kNe+ROXpE} z3J1Qzr+GQdbkTDl#hw~={1x)UBeCQ7Uu2q%M*np5aJcMI+py!CO#lzR$!BTEflB`r zcP>87*8`dJfbcKy@&AhTFMk+%`fr?TEWlC$91Xl9&c_dSHc_nbIWoEI-#D`Pa+mM& zcc&g2RQyZ&=h#s?@$c{~`LFSJc$4?*`Xgq<-r4^t_0B6Nqq#hv|08}U`i@_QpMFW{ z531Aq9~>87KT>{r?U%Rzh4XKWuN=6>mvx`7X8#YOuf!8=kY4i5qgr7cN kvE@p+G1Q3WNfoKqwFj{H6l`0mN!KF8}}l literal 0 HcmV?d00001 diff --git a/src/tests/test_image_struct.py b/src/tests/test_image_struct.py index 3c56805..2113b0e 100644 --- a/src/tests/test_image_struct.py +++ b/src/tests/test_image_struct.py @@ -1,4 +1,4 @@ -def test_image_struct(): +def test_image_struct(test_resources): from ttblit.core.struct import struct_blit_image from ttblit.core.palette import Palette @@ -13,16 +13,26 @@ def check_image(i, t): b1 = struct_blit_image.build(p) assert b1 == b - # TODO: Use a real image to test? + # default splash image palette = Palette() - palette.get_entry(255, 255, 255, 255) + palette.get_entry( 0, 0, 0, 255) + palette.get_entry( 99, 175, 227, 255) + palette.get_entry( 45, 100, 143, 255) + palette.get_entry( 56, 66, 67, 255) + palette.get_entry( 52, 62, 59, 255) + palette.get_entry( 37, 55, 60, 255) + palette.get_entry( 12, 29, 33, 255) + palette.get_entry(234, 92, 181, 255) + palette.get_entry(100, 246, 178, 255) + palette.get_entry(234, 226, 81, 255) + palette.get_entry(140, 139, 144, 255) image_dict = { 'data': { - 'width': 0x10, - 'height': 0x4, + 'width': 128, + 'height': 96, 'palette': palette.tostruct(), - 'pixels': b'\x00' * 0x40, + 'pixels': open(test_resources / 'no_image.raw', 'rb').read(), } } From ae11b9bcbd69dafb2b9926ba0577636b291110c8 Mon Sep 17 00:00:00 2001 From: Charlie Birks Date: Thu, 16 May 2024 12:59:06 +0100 Subject: [PATCH 09/11] Fix RLE decompress with bitstring 4.1+ --- src/ttblit/core/compression.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/ttblit/core/compression.py b/src/ttblit/core/compression.py index 8ed1a27..909109a 100644 --- a/src/ttblit/core/compression.py +++ b/src/ttblit/core/compression.py @@ -47,7 +47,7 @@ def decompress(data, bit_length, output_length): stream = ConstBitStream(bytes=data) result = [] while len(result) < output_length: - t = stream.read(1) + t = stream.read(1).uint if t: count = stream.read(8).uint + 1 else: From 68a3a206a9f3be9d064606736332d8c86543914d Mon Sep 17 00:00:00 2001 From: Phil Howard Date: Mon, 17 Jun 2024 13:41:31 +0100 Subject: [PATCH 10/11] CI: Fix deprecation warnings, rename branch prep. --- .github/workflows/test-setup.yml | 4 ++-- .github/workflows/test.yml | 6 +++--- README.md | 4 ++-- src/README.md | 4 ++-- 4 files changed, 9 insertions(+), 9 deletions(-) diff --git a/.github/workflows/test-setup.yml b/.github/workflows/test-setup.yml index 94581e4..a00668c 100644 --- a/.github/workflows/test-setup.yml +++ b/.github/workflows/test-setup.yml @@ -28,9 +28,9 @@ jobs: run: | sudo apt update && sudo apt install ${{matrix.apt-packages}} - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 - name: Grab the SDK - uses: actions/checkout@v2 + uses: actions/checkout@v4 with: repository: 32blit/32blit-sdk path: 32blit-sdk diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml index aee538e..0cd8ba8 100644 --- a/.github/workflows/test.yml +++ b/.github/workflows/test.yml @@ -4,7 +4,7 @@ on: pull_request: push: branches: - - master + - main jobs: test: @@ -19,9 +19,9 @@ jobs: if: runner.os == 'Linux' run: | sudo apt update && sudo apt install gcc-arm-none-eabi - - uses: actions/checkout@v2 + - uses: actions/checkout@v4 - name: Set up Python ${{ matrix.python }} - uses: actions/setup-python@v2 + uses: actions/setup-python@v5 with: python-version: ${{ matrix.python }} - name: Install Dependencies diff --git a/README.md b/README.md index 69fedd5..50b6964 100644 --- a/README.md +++ b/README.md @@ -1,7 +1,7 @@ # 32blit Tools -[![Build Status](https://img.shields.io/github/actions/workflow/status/32blit/32blit-tools/test.yml?branch=master)](https://github.com/32blit/32blit-tools/actions/workflows/test.yml) -[![Coverage Status](https://coveralls.io/repos/github/32blit/32blit-tools/badge.svg?branch=master)](https://coveralls.io/github/32blit/32blit-tools?branch=master) +[![Build Status](https://img.shields.io/github/actions/workflow/status/32blit/32blit-tools/test.yml?branch=main)](https://github.com/32blit/32blit-tools/actions/workflows/test.yml) +[![Coverage Status](https://coveralls.io/repos/github/32blit/32blit-tools/badge.svg?branch=main)](https://coveralls.io/github/32blit/32blit-tools?branch=main) [![PyPi Package](https://img.shields.io/pypi/v/32blit.svg)](https://pypi.python.org/pypi/32blit) [![Python Versions](https://img.shields.io/pypi/pyversions/32blit.svg)](https://pypi.python.org/pypi/32blit) diff --git a/src/README.md b/src/README.md index 3399d21..c668065 100644 --- a/src/README.md +++ b/src/README.md @@ -1,7 +1,7 @@ # 32blit Tools -[![Build Status](https://img.shields.io/github/actions/workflow/status/32blit/32blit-tools/test.yml?branch=master)](https://github.com/32blit/32blit-tools/actions/workflows/test.yml) -[![Coverage Status](https://coveralls.io/repos/github/32blit/32blit-tools/badge.svg?branch=master)](https://coveralls.io/github/32blit/32blit-tools?branch=master) +[![Build Status](https://img.shields.io/github/actions/workflow/status/32blit/32blit-tools/test.yml?branch=main)](https://github.com/32blit/32blit-tools/actions/workflows/test.yml) +[![Coverage Status](https://coveralls.io/repos/github/32blit/32blit-tools/badge.svg?branch=main)](https://coveralls.io/github/32blit/32blit-tools?branch=main) [![PyPi Package](https://img.shields.io/pypi/v/32blit.svg)](https://pypi.python.org/pypi/32blit) [![Python Versions](https://img.shields.io/pypi/pyversions/32blit.svg)](https://pypi.python.org/pypi/32blit) From bce129050583550b6296be31d5455c715e9d3b09 Mon Sep 17 00:00:00 2001 From: Phil Howard Date: Mon, 17 Jun 2024 15:10:44 +0100 Subject: [PATCH 11/11] Prep for v0.7.4. --- Makefile | 2 +- src/CHANGELOG.txt | 7 +++++++ src/README.md | 7 +++++++ src/setup.cfg | 2 +- src/ttblit/__init__.py | 2 +- 5 files changed, 17 insertions(+), 3 deletions(-) diff --git a/Makefile b/Makefile index afa1c14..1f32359 100644 --- a/Makefile +++ b/Makefile @@ -64,7 +64,7 @@ python-dist: python-clean python-wheels python-sdist -python3 -m twine check src/dist/* python-testdeploy: python-dist - twine upload --repository-url https://test.pypi.org/legacy/ src/dist/* + twine upload --repository testpypi src/dist/* python-deploy: check python-dist twine upload src/dist/* diff --git a/src/CHANGELOG.txt b/src/CHANGELOG.txt index a959a3f..85cd6c6 100644 --- a/src/CHANGELOG.txt +++ b/src/CHANGELOG.txt @@ -1,3 +1,10 @@ +0.7.4 +----- + +* Fix bug when deleting from flash - thanks @ali1234 +* Fix serial port in error message - thanks @ali1234 +* Fix image encoding - thanks @Daft-Freak + 0.7.3 ----- diff --git a/src/README.md b/src/README.md index c668065..bc1532a 100644 --- a/src/README.md +++ b/src/README.md @@ -118,6 +118,13 @@ Supported formats: # Changelog +0.7.4 +----- + +* Fix bug when deleting from flash - thanks @ali1234 +* Fix serial port in error message - thanks @ali1234 +* Fix image encoding - thanks @Daft-Freak + 0.7.3 ----- diff --git a/src/setup.cfg b/src/setup.cfg index d58ec57..aff3d79 100644 --- a/src/setup.cfg +++ b/src/setup.cfg @@ -1,7 +1,7 @@ # -*- coding: utf-8 -*- [metadata] name = 32blit -version = 0.7.3 +version = 0.7.4 author = Philip Howard author_email = phil@pimoroni.com description = 32Blit asset preparation and upload tools diff --git a/src/ttblit/__init__.py b/src/ttblit/__init__.py index 4d09cc4..60bb6a3 100644 --- a/src/ttblit/__init__.py +++ b/src/ttblit/__init__.py @@ -1,5 +1,5 @@ -__version__ = '0.7.3' +__version__ = '0.7.4' import logging