From 4959298886e8ed2f779c2372a3fd23172fcf0799 Mon Sep 17 00:00:00 2001 From: Provan Date: Fri, 14 Aug 2026 11:39:43 +0100 Subject: [PATCH 1/2] Updating register_map_intro.ipynb to describe correct number of push buttons on VCK190 board. --- .../notebooks/board/register_map_intro.ipynb | 267 ++++++++++++++++-- 1 file changed, 251 insertions(+), 16 deletions(-) diff --git a/boards/VCK190/notebooks/board/register_map_intro.ipynb b/boards/VCK190/notebooks/board/register_map_intro.ipynb index 080b12846..78fc81958 100644 --- a/boards/VCK190/notebooks/board/register_map_intro.ipynb +++ b/boards/VCK190/notebooks/board/register_map_intro.ipynb @@ -11,7 +11,7 @@ "In this example we'll be looking at the AXI GPIO IP exposed by the VCK190 base overlay:\n", "\n", "* `axi_gpio_led` -- the 4 board LEDs (output)\n", - "* `axi_gpio_pb` -- the 4 push-buttons (input)\n", + "* `axi_gpio_pb` -- the 2 push-buttons (input)\n", "* `axi_gpio_dip_sw` -- the 4 DIP switches (input)\n", "\n", "The convenience aliases `base.leds` / `base.buttons` / `base.switches` on the `BaseOverlay` wrap the default channel of each respective AXI GPIO." @@ -19,9 +19,48 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 1, "metadata": {}, - "outputs": [], + "outputs": [ + { + "data": { + "application/javascript": [ + "\n", + "try {\n", + "require(['notebook/js/codecell'], function(codecell) {\n", + " codecell.CodeCell.options_default.highlight_modes[\n", + " 'magic_text/x-csrc'] = {'reg':[/^%%microblaze/]};\n", + " Jupyter.notebook.events.one('kernel_ready.Kernel', function(){\n", + " Jupyter.notebook.get_cells().map(function(cell){\n", + " if (cell.cell_type == 'code'){ cell.auto_highlight(); } }) ;\n", + " });\n", + "});\n", + "} catch (e) {};\n" + ] + }, + "metadata": {}, + "output_type": "display_data" + }, + { + "data": { + "application/javascript": [ + "\n", + "try {\n", + "require(['notebook/js/codecell'], function(codecell) {\n", + " codecell.CodeCell.options_default.highlight_modes[\n", + " 'magic_text/x-csrc'] = {'reg':[/^%%pybind11/]};\n", + " Jupyter.notebook.events.one('kernel_ready.Kernel', function(){\n", + " Jupyter.notebook.get_cells().map(function(cell){\n", + " if (cell.cell_type == 'code'){ cell.auto_highlight(); } }) ;\n", + " });\n", + "});\n", + "} catch (e) {};\n" + ] + }, + "metadata": {}, + "output_type": "display_data" + } + ], "source": [ "from pynq.overlays.base import BaseOverlay\n", "\n", @@ -37,7 +76,7 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 2, "metadata": {}, "outputs": [], "source": [ @@ -55,9 +94,28 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 3, "metadata": {}, - "outputs": [], + "outputs": [ + { + "data": { + "text/plain": [ + "RegisterMap {\n", + " GPIO_DATA = Register(CH1_DATA=0),\n", + " GPIO_TRI = Register(CH1_TRI=3),\n", + " GPIO2_DATA = Register(CH2_DATA=0),\n", + " GPIO2_TRI = Register(CH2_TRI=4294967295),\n", + " GIER = Register(INT_EN=0),\n", + " IP_ISR = Register(CH1_INT_S=0, CH2_INT_S=0),\n", + " IP_IER = Register(CH1_INT_EN=0, CH2_INT_EN=0)\n", + "}" + ] + }, + "execution_count": 3, + "metadata": {}, + "output_type": "execute_result" + } + ], "source": [ "btns.register_map" ] @@ -71,9 +129,20 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 16, "metadata": {}, - "outputs": [], + "outputs": [ + { + "data": { + "text/plain": [ + "3" + ] + }, + "execution_count": 16, + "metadata": {}, + "output_type": "execute_result" + } + ], "source": [ "btns.register_map.GPIO_DATA.CH1_DATA" ] @@ -87,9 +156,160 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 17, "metadata": {}, - "outputs": [], + "outputs": [ + { + "name": "stdout", + "output_type": "stream", + "text": [ + "Help on RegisterIP_IER in module pynq.registers object:\n", + "\n", + "class RegisterIP_IER(Register)\n", + " | RegisterIP_IER(address, width=32, debug=False, buffer=None, access='read-write', device=None)\n", + " |\n", + " | IP Interrupt Enable register\n", + " |\n", + " | Method resolution order:\n", + " | RegisterIP_IER\n", + " | Register\n", + " | builtins.object\n", + " |\n", + " | Data descriptors defined here:\n", + " |\n", + " | CH1_INT_EN\n", + " | Enable Channel 1 Interrupt\n", + " | 0 - Disabled (masked)\n", + " | 1 - Enabled\n", + " |\n", + " | CH2_INT_EN\n", + " | Enable Channel 2 Interrupt\n", + " | 0 - Disabled (masked)\n", + " | 1 - Enabled\n", + " |\n", + " | ----------------------------------------------------------------------\n", + " | Data and other attributes defined here:\n", + " |\n", + " | _fields = {'CH1_INT_EN': {'access': 'read-write', 'bit_offset': 0, 'bi...\n", + " |\n", + " | ----------------------------------------------------------------------\n", + " | Methods inherited from Register:\n", + " |\n", + " | __getitem__(self, index)\n", + " | Get the register value.\n", + " |\n", + " | This method accepts both integer index, or slice as input parameters.\n", + " |\n", + " | Parameters\n", + " | ----------\n", + " | index : int | slice\n", + " | The integer index, or slice to access the register value.\n", + " |\n", + " | __index__(self)\n", + " | Return an index containing the value of the register\n", + " |\n", + " | __init__(self, address, width=32, debug=False, buffer=None, access='read-write', device=None)\n", + " | Instantiate a register object.\n", + " |\n", + " | Parameters\n", + " | ----------\n", + " | address : int\n", + " | The address of the register.\n", + " | width : int\n", + " | The width of the register, e.g., 32 (default) or 64.\n", + " | debug : bool\n", + " | Turn on debug mode if True; default is False.\n", + " | buffer : Buffer\n", + " | Buffer object to use for reading and writing the value\n", + " | of the register. If None the address is assumed to be\n", + " | an absolute physical address\n", + " |\n", + " | __int__(self)\n", + " | Return an integer of the value of the register\n", + " |\n", + " | __repr__(self)\n", + " | Print a representation of the Register and all its fields\n", + " |\n", + " | If the Register has been subclassed with fields then these\n", + " | will be printed otherwise the return string will contain the\n", + " | value of the entire register\n", + " |\n", + " | __setitem__(self, index, value)\n", + " | Set the register value.\n", + " |\n", + " | This method accepts both integer index, or slice as input parameters.\n", + " |\n", + " | Parameters\n", + " | ----------\n", + " | index : int | slice\n", + " | The integer index, or slice to access the register value.\n", + " |\n", + " | __str__(self)\n", + " | Print the register value.\n", + " |\n", + " | This method is overloaded to print the register value. The output\n", + " | is a string in hex format.\n", + " |\n", + " | _debug(self, s, *args)\n", + " | The method provides debug capabilities for this class.\n", + " |\n", + " | Parameters\n", + " | ----------\n", + " | s : str\n", + " | The debug information format string\n", + " | *args : any\n", + " | The arguments to be formatted\n", + " | Returns\n", + " | -------\n", + " | None\n", + " |\n", + " | _reordered_setitem(self, value, index)\n", + " | Wrapped version of __setitem__ for better use with\n", + " | functools.partial\n", + " |\n", + " | ----------------------------------------------------------------------\n", + " | Class methods inherited from Register:\n", + " |\n", + " | count(index, width=32)\n", + " | Provide the number of bits accessed by an index or slice\n", + " |\n", + " | This method accepts both integer index, or slice as input parameters.\n", + " |\n", + " | Parameters\n", + " | ----------\n", + " | index : int | slice\n", + " | The integer index, or slice to access the register value.\n", + " | width : int\n", + " | The number of bits accessed.\n", + " |\n", + " | create_subclass(name, fields, doc=None)\n", + " | Create a subclass of Register that has properties for the\n", + " | specified fields\n", + " |\n", + " | The fields should be in the form used by `ip_dict`, namely::\n", + " |\n", + " | {name: {'access': \"read-only\" | \"read-write\" | \"write-only\",\n", + " | 'bit_offset': int, 'bit_width': int, 'description': str}}\n", + " |\n", + " | Parameters\n", + " | ----------\n", + " | name : str\n", + " | A suffix for the name of the subclass\n", + " | fields : dict\n", + " | A Dictionary containing the fields to add to the subclass\n", + " |\n", + " | ----------------------------------------------------------------------\n", + " | Data descriptors inherited from Register:\n", + " |\n", + " | __dict__\n", + " | dictionary for instance variables\n", + " |\n", + " | __weakref__\n", + " | list of weak references to the object\n", + "\n" + ] + } + ], "source": [ "help(btns.register_map.IP_IER)" ] @@ -103,7 +323,7 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 13, "metadata": {}, "outputs": [], "source": [ @@ -120,9 +340,20 @@ }, { "cell_type": "code", - "execution_count": null, + "execution_count": 26, "metadata": {}, - "outputs": [], + "outputs": [ + { + "data": { + "text/plain": [ + "7" + ] + }, + "execution_count": 26, + "metadata": {}, + "output_type": "execute_result" + } + ], "source": [ "switches.register_map.GPIO_DATA.CH1_DATA" ] @@ -146,10 +377,14 @@ "language_info": { "codemirror_mode": { "name": "ipython", - "mimetype": "text/x-python", - "file_extension": ".py" + "version": 3 }, - "name": "python" + "file_extension": ".py", + "mimetype": "text/x-python", + "name": "python", + "nbconvert_exporter": "python", + "pygments_lexer": "ipython3", + "version": "3.12.3" } }, "nbformat": 4, From cc0ce45d15f9a94ad250731961c6c7590f182de9 Mon Sep 17 00:00:00 2001 From: Provan Date: Fri, 14 Aug 2026 11:44:02 +0100 Subject: [PATCH 2/2] Fix Jupyter Notebook crash when the display device cannot be initialised --- pynq/lib/video/drm.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/pynq/lib/video/drm.py b/pynq/lib/video/drm.py index f6c72e38d..aa042f367 100644 --- a/pynq/lib/video/drm.py +++ b/pynq/lib/video/drm.py @@ -58,7 +58,7 @@ def __init__(self, device_path, event_loop=None): self._video_file = os.fdopen(self._video_fd, "r+b", buffering=0) self._device = self._videolib.pynqvideo_device_init(self._video_fd) - if self._device == 0: + if self._device == self._ffi.NULL: raise RuntimeError("Unable to create DRM device") if event_loop: