{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "<link rel=\"preconnect\" href=\"https://fonts.gstatic.com\">\n",
    "<link href=\"https://fonts.googleapis.com/css2?family=Fira+Code&display=swap\" rel=\"stylesheet\">\n",
    "\n",
    "### License\n",
    "\n",
    "<p style=\"font-family: 'Fira Code', monospace; font-size: 1.2rem\">\n",
    "Copyright 2021 Xilinx, Inc.<br><br>\n",
    "Licensed under the Apache License, Version 2.0 (the \"License\");<br>\n",
    "you may not use this file except in compliance with the License.<br><br>\n",
    "You may obtain a copy of the License at <a href=\"http://www.apache.org/licenses/LICENSE-2.0\"?>http://www.apache.org/licenses/LICENSE-2.0</a><br><br>\n",
    "Unless required by applicable law or agreed to in writing, software<br>\n",
    "distributed under the License is distributed on an \"AS IS\" BASIS,<br>\n",
    "WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.<br>\n",
    "See the License for the specific language governing permissions and<br>\n",
    "limitations under the License.<br>\n",
    "</p>\n"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# ChipScoPy System Monitor Example\n",
    "\n",
    "\n",
    "<img src=\"../img/api_overview.png\" width=\"500\" align=\"left\">"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## Description\n",
    "\n",
    "\n",
    "This demo shows how to take and display measurements with the System Monitor.\n",
    "\n",
    "\n",
    "## Requirements\n",
    "- Local or remote Xilinx Versal board, such as a VCK190\n",
    "- Xilinx hw_server 2022.1 installed and running\n",
    "- Xilinx cs_server 2022.1 installed and running\n",
    "- Python 3.8 or greater installed\n",
    "- ChipScoPy 2022.1 installed\n",
    "- Jupyter notebook support installed - Please do so, using the command `pip install chipscopy[jupyter]`"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 1 - Initialization: Imports and File Paths\n",
    "\n",
    "After this step,\n",
    "- Required functions and classes are imported\n",
    "- URL paths are set correctly\n",
    "- File paths to example files are set correctly"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 1,
   "metadata": {},
   "outputs": [],
   "source": [
    "import os\n",
    "import time\n",
    "from chipscopy import get_design_files\n",
    "from chipscopy import __version__, dm\n",
    "from chipscopy import create_session, report_versions"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "HW_URL: TCP:localhost:3121\n",
      "CS_URL: TCP:localhost:3042\n",
      "PROGRAMMING_FILE: C:\\wrk\\chipscopy\\chipscopy-venv\\Lib\\site-packages\\chipscopy\\examples\\designs\\vck190\\production\\chipscopy_ced\\chipscopy_wrapper.pdi\n",
      "PROBES_FILE:C:\\wrk\\chipscopy\\chipscopy-venv\\Lib\\site-packages\\chipscopy\\examples\\designs\\vck190\\production\\chipscopy_ced\\chipscopy_wrapper.ltx\n"
     ]
    }
   ],
   "source": [
    "# Make sure to start the hw_server and cs_server prior to running.\n",
    "# Specify locations of the running hw_server and cs_server below.\n",
    "# The default is localhost - but can be other locations on the network.\n",
    "CS_URL = os.getenv(\"CS_SERVER_URL\", \"TCP:localhost:3042\")\n",
    "HW_URL = os.getenv(\"HW_SERVER_URL\", \"TCP:localhost:3121\")\n",
    "\n",
    "# The get_design_files() function tries to find the PDI and LTX files. In non-standard\n",
    "# configurations, you can put the path for PROGRAMMING_FILE and PROBES_FILE below.\n",
    "design_files = get_design_files(\"vck190/production/chipscopy_ced\")\n",
    "\n",
    "PROGRAMMING_FILE = design_files.programming_file\n",
    "PROBES_FILE = design_files.probes_file\n",
    "\n",
    "print(f\"HW_URL: {HW_URL}\")\n",
    "print(f\"CS_URL: {CS_URL}\")\n",
    "print(f\"PROGRAMMING_FILE: {PROGRAMMING_FILE}\")\n",
    "print(f\"PROBES_FILE:{PROBES_FILE}\")"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 2 - Create a session and connect to the hw_server and cs_server\n",
    "\n",
    "The session is a container that keeps track of devices and debug cores.\n",
    "After this step,\n",
    "- Session is initialized and connected to server(s)\n",
    "- Versions are detected and reported to stdout"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/html": [
       "<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\">\n",
       "\n",
       "</pre>\n"
      ],
      "text/plain": [
       "<rich.jupyter.JupyterRenderable at 0x24c15408df0>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\"><span style=\"font-style: italic\">                         ChipScoPy Version Information                          </span>\n",
       "┌────────────────────────────┬─────────────────────────────────────────────────┐\n",
       "│<span style=\"font-weight: bold\">                     Entity </span>│<span style=\"font-weight: bold\"> Version                                         </span>│\n",
       "├────────────────────────────┼─────────────────────────────────────────────────┤\n",
       "│                  ChipScoPy │ ┌───────────┬──────────────────────┐            │\n",
       "│                            │ │<span style=\"font-weight: bold\"> Attribute </span>│<span style=\"font-weight: bold\"> Value                </span>│            │\n",
       "│                            │ ├───────────┼──────────────────────┤            │\n",
       "│                            │ │     Build │ 2022.1.1654231490    │            │\n",
       "│                            │ │ Timestamp │ Jun 02 2022-22:44:50 │            │\n",
       "│                            │ └───────────┴──────────────────────┘            │\n",
       "│                            │                                                 │\n",
       "│ hw_server @ localhost:3121 │ ┌───────────┬─────────────────────────────────┐ │\n",
       "│                            │ │<span style=\"font-weight: bold\"> Attribute </span>│<span style=\"font-weight: bold\"> Value                           </span>│ │\n",
       "│                            │ ├───────────┼─────────────────────────────────┤ │\n",
       "│                            │ │    Status │ Connected                       │ │\n",
       "│                            │ │     Build │ 1641456835                      │ │\n",
       "│                            │ │   Version │ 2022.1                          │ │\n",
       "│                            │ │ Timestamp │ Thu 06 Jan 2022 08:13:55 AM UTC │ │\n",
       "│                            │ └───────────┴─────────────────────────────────┘ │\n",
       "│                            │                                                 │\n",
       "│ cs_server @ localhost:3042 │ ┌───────────────┬──────────────────────┐        │\n",
       "│                            │ │<span style=\"font-weight: bold\">     Attribute </span>│<span style=\"font-weight: bold\"> Value                </span>│        │\n",
       "│                            │ ├───────────────┼──────────────────────┤        │\n",
       "│                            │ │        Status │ Connected            │        │\n",
       "│                            │ │         Build │ 1649790728           │        │\n",
       "│                            │ │       Version │ 2022.1.0             │        │\n",
       "│                            │ │     Timestamp │ Apr 12 2022-13:12:08 │        │\n",
       "│                            │ │       Package │ 2022.1.1649790728    │        │\n",
       "│                            │ │ Artifact type │ pyinstaller          │        │\n",
       "│                            │ └───────────────┴──────────────────────┘        │\n",
       "└────────────────────────────┴─────────────────────────────────────────────────┘\n",
       "</pre>\n"
      ],
      "text/plain": [
       "<rich.jupyter.JupyterRenderable at 0x24c154087c0>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "text/html": [
       "<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\">\n",
       "\n",
       "</pre>\n"
      ],
      "text/plain": [
       "<rich.jupyter.JupyterRenderable at 0x24c15408e50>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "session = create_session(cs_server_url=CS_URL, hw_server_url=HW_URL)\n",
    "report_versions(session)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 3 - Program the device with the example design\n",
    "\n",
    "After this step,\n",
    "- Device is programmed with the example programming file"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {},
   "outputs": [
    {
     "data": {
      "text/html": [
       "<pre style=\"white-space:pre;overflow-x:auto;line-height:normal;font-family:Menlo,'DejaVu Sans Mono',consolas,'Courier New',monospace\">\n",
       "<span style=\"font-weight: bold\">--&gt; INFO: </span>Programming device with: C:\\wrk\\chipscopy\\chipscopy-venv\\Lib\\site-packages\\chipscop\n",
       "y\\examples\\designs\\vck190\\production\\chipscopy_ced\\chipscopy_wrapper.pdi\n",
       "    \n",
       "</pre>\n"
      ],
      "text/plain": [
       "<rich.jupyter.JupyterRenderable at 0x24c154d2fd0>"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    },
    {
     "data": {
      "application/vnd.jupyter.widget-view+json": {
       "model_id": "be20018231f24c62b161f26d562e051a",
       "version_major": 2,
       "version_minor": 0
      },
      "text/plain": [
       "Output()"
      ]
     },
     "metadata": {},
     "output_type": "display_data"
    }
   ],
   "source": [
    "# Typical case - one device on the board - get it.\n",
    "device = session.devices.filter_by(family=\"versal\").get()\n",
    "device.program(PROGRAMMING_FILE)"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 4 - Discover Debug Cores\n",
    "\n",
    "Debug core discovery initializes the chipscope server debug cores. This brings debug cores in the chipscope server online.\n",
    "\n",
    "After this step,\n",
    "\n",
    "- The cs_server is initialized and ready for use"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "System monitor setup and ready for use.\n"
     ]
    }
   ],
   "source": [
    "device.discover_and_setup_cores(sysmon_scan=True)\n",
    "print(f\"System monitor setup and ready for use.\")"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 5 - Initialize System Monitor\n",
    "\n",
    "Get reference to the system monitor and initialize all sensors."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Initializing sensors\n",
      "Refresh measurement schedule\n",
      "Sensors:\n",
      "  VCCAUX\n",
      "  VCCAUX_PMC\n",
      "  VCC_PMC\n",
      "  VCC_PSFP\n",
      "  VCC_PSLP\n",
      "  VCC_SOC\n",
      "  VP_VN\n",
      "Done.\n"
     ]
    }
   ],
   "source": [
    "sysmon = device.sysmon_root.get()\n",
    "\n",
    "print(\"Initializing sensors\")\n",
    "active_nodes = sysmon.initialize_sensors()\n",
    "\n",
    "print(\"Refresh measurement schedule\")\n",
    "schedule = sysmon.refresh_measurement_schedule()\n",
    "\n",
    "print(\"Sensors:\")\n",
    "for sensor in schedule.values():\n",
    "    print(f\"  {sensor}\")\n",
    "\n",
    "print(\"Done.\")"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 6 - Register a listener for System Monitor Events\n",
    "\n",
    "The SysMonNodeListener node_changed() will be called every 1000ms with updated system monitor values."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Node listener added.\n"
     ]
    }
   ],
   "source": [
    "class SysMonNodeListener(dm.NodeListener):\n",
    "    def node_changed(self, node, updated_keys):\n",
    "        if \"device_temp\" in node.props:\n",
    "            print(f\"Device Temp: {node.props['device_temp']}\")\n",
    "        for supply_idx, named_sensor in schedule.items():\n",
    "            supply = f\"supply{supply_idx}\"\n",
    "            if supply in node.props:\n",
    "                print(f\"{named_sensor}: {node.props[supply]}\")\n",
    "        print()\n",
    "\n",
    "\n",
    "node_listener = SysMonNodeListener()\n",
    "session.chipscope_view.add_node_listener(node_listener)\n",
    "\n",
    "sysmon.stream_sensor_data(1000)\n",
    "print(\"Node listener added.\")"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "## 7 - Run measurement for 5 seconds\n",
    "\n",
    "System Monitor will report results for 5 seconds then exit."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "metadata": {},
   "outputs": [
    {
     "name": "stdout",
     "output_type": "stream",
     "text": [
      "Device Temp: 47.5859375\n",
      "VCCAUX: 1.498077392578125\n",
      "VCCAUX_PMC: 1.490966796875\n",
      "VCC_PMC: 0.800872802734375\n",
      "VCC_PSFP: 0.80169677734375\n",
      "VCC_PSLP: 0.8040771484375\n",
      "VCC_SOC: 0.80218505859375\n",
      "VP_VN: 0.1318359375\n",
      "\n",
      "Device Temp: 47.5859375\n",
      "VCCAUX: 1.49859619140625\n",
      "VCCAUX_PMC: 1.492431640625\n",
      "VCC_PMC: 0.8018798828125\n",
      "VCC_PSFP: 0.80169677734375\n",
      "VCC_PSLP: 0.803558349609375\n",
      "VCC_SOC: 0.80853271484375\n",
      "VP_VN: 0.13232421875\n",
      "\n",
      "Device Temp: 47.828125\n",
      "VCCAUX: 1.498382568359375\n",
      "VCCAUX_PMC: 1.4920654296875\n",
      "VCC_PMC: 0.80108642578125\n",
      "VCC_PSFP: 0.802734375\n",
      "VCC_PSLP: 0.8033447265625\n",
      "VCC_SOC: 0.817535400390625\n",
      "VP_VN: 0.132232666015625\n",
      "\n",
      "Device Temp: 47.703125\n",
      "VCCAUX: 1.497314453125\n",
      "VCCAUX_PMC: 1.491546630859375\n",
      "VCC_PMC: 0.80108642578125\n",
      "VCC_PSFP: 0.803131103515625\n",
      "VCC_PSLP: 0.804168701171875\n",
      "VCC_SOC: 0.815093994140625\n",
      "VP_VN: 0.131988525390625\n",
      "\n",
      "Device Temp: 47.6875\n",
      "VCCAUX: 1.498291015625\n",
      "VCCAUX_PMC: 1.491363525390625\n",
      "VCC_PMC: 0.800445556640625\n",
      "VCC_PSFP: 0.802032470703125\n",
      "VCC_PSLP: 0.80419921875\n",
      "VCC_SOC: 0.817108154296875\n",
      "VP_VN: 0.1319580078125\n",
      "\n",
      "Measurement done.\n"
     ]
    }
   ],
   "source": [
    "# Take measurements for 5 seconds then exit.\n",
    "\n",
    "time_end = time.time() + 5\n",
    "\n",
    "while time.time() < time_end:\n",
    "    session.chipscope_view.run_events()\n",
    "    time.sleep(0.1)\n",
    "\n",
    "print(\"Measurement done.\")"
   ]
  }
 ],
 "metadata": {
  "jupytext": {
   "cell_metadata_filter": "-all",
   "main_language": "python",
   "notebook_metadata_filter": "-all"
  },
  "kernelspec": {
   "display_name": "Python 3 (ipykernel)",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.8.10"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 4
}
