This tutorial walks you through how to run PXL-based C++ applications interactively in a Jupyter + xeus-cling environment. By the end of this guide, you’ll be able to build and run example applications directly from a Jupyter Notebook.

The XCENA SDK supports running Jupyter in multiple environments:

  • Native: Run directly on your host system with XCENA SDK installed
  • Docker: Run inside a Docker container (requires XCENA CXL hardware)
  • Docker + QEMU: Run inside a QEMU VM within Docker (for development/testing without physical hardware)

Prerequisites

Depending on your deployment method, you will need:

  • For Native environment:
    • XCENA SDK installed on your host system
  • For Docker environment:
    • Docker installed and configured on your system
  • For Docker + QEMU environment:
    • Docker installed and configured on your system
    • Port forwarding configured from host → Docker → QEMU
    • KVM support enabled on the host system

Note: For installation instructions, see Install Guide.


How to Run

1. Launch Environment

You can run the Jupyter environment in one of the following setups:

1.1. Native Environment

If you have the XCENA SDK installed directly on your host machine, you can run Jupyter natively.

Prerequisites
  • XCENA SDK installed on the host system
  • Jupyter and xeus-cling installed via the provided installation script
Setup
  1. Install Jupyter and xeus-cling (if not already installed):

     cd <sdk>/jupyter
     ./install_jupyter.sh
    
  2. Start the Jupyter server:

     cd <sdk>/jupyter
     ./run_jupyter.sh
    
  3. Access Jupyter from your browser at:

     http://localhost:8888
    

1.2. Docker Environment

You can run Jupyter directly inside a Docker container without QEMU virtualization.

Prerequisites
  • Docker installed on the host system
  • Access to a XCENA CXL device (for actual hardware acceleration)
Setup
  1. Launch the Docker container with Jupyter port forwarding:

     docker run -dit --name xcena_sdk \
       -p 8888:8888 \
       --privileged \
       xcenadev/sdk:latest
    

    Note: The --privileged flag is required for the driver to access the XCENA CXL device.

  2. Access the Docker container:

     docker exec -it xcena_sdk bash
    
  3. Start the Jupyter server inside Docker:

     jupyter/run_jupyter.sh
    
  4. Access Jupyter from your host browser at:

     http://localhost:8888
    

1.3. Docker + QEMU Environment

This setup is useful for development and testing when you don’t have access to physical XCENA CXL hardware. The Jupyter server runs inside a QEMU virtual machine, which itself runs inside a Docker container.

Required Port Mapping
  • SSH: host:<any_available_port> → Docker:<any_port> → QEMU:22
  • Jupyter: host:<any_available_port> → Docker:<any_port> → QEMU:8888
Example Setup
  1. Launch the Docker container with port forwarding:

     docker run -dit --name xcena_sdk \
       -p 10022:10022 \
       -p 20088:20088 \
       --device=/dev/kvm \
       --cap-add=SYS_ADMIN \
       -e USER=$USER \
       xcenadev/sdk:latest
    

    Note: The --device=/dev/kvm and --cap-add=SYS_ADMIN flags are required to run QEMU with KVM acceleration.

  2. Access the Docker container:

     docker exec -it xcena_sdk bash
    
  3. Inside the Docker container, run the QEMU virtual machine with the following command:

     ./run.sh -f 10022:22 20088:8888
    

    This command will start the QEMU VM and forward the SSH and Jupyter ports. For more information on the run.sh script, refer to the Documentation/Emulator Section.

  4. Start the Jupyter server inside QEMU:

     ~/run_jupyter.sh
    
  5. Access Jupyter from your host browser at:

     http://localhost:20088
    

2. Access Jupyter from the Browser

Once the Jupyter server is running, access it from your browser:

  • Native environment: http://localhost:8888
  • Docker environment: http://localhost:8888
  • Docker + QEMU environment: http://localhost:<host_jupyter_port> (e.g., http://localhost:20088)

If you are running in a headless environment, replace localhost with the server’s IP address:

http://<server_ip>:<port>

Important: Make sure to use http:// not https:// when accessing Jupyter.


3. Load PXL in Jupyter Notebook

Currently, the SDK release only supports C++17 with xeus-cling.

Creating a C++17 Notebook

When creating a new notebook, you must select the C++17 kernel:

  1. In the Jupyter Launcher, locate and click on C++17 under the “Notebook” section.
  2. Alternatively, if you open an existing notebook, verify that the kernel is set to C++17 in the top-right corner of the notebook interface.
  3. If the kernel is not set to C++17, click on the kernel name and select C++17 from the dropdown menu.

Once you have a C++17 notebook open, load the PXL library with:

#pragma cling add_include_path("/usr/local/include")
#pragma cling add_library_path("/usr/local/lib")
#pragma cling load("pxl")

#include "pxl/pxl.hpp"

Important: Ensure you select C++17 as the kernel version in Jupyter.


4. Try the Sort Example

We provide a sorting example to demonstrate how to offload a simple computation using PXL.

Location

<sdk>/example/sort/

This example consists of:

  • build.sh: Compiles the MU Kernel for the sort example.
  • mu_kernel/: MU kernel source code for the sort example
  • sort.ipynb: A Jupyter notebook demonstrating sorting with the PXL library.

To run the example

  1. Run the build script(before open the notebook) to compile the MU Kernel:

     cd <sdk>/example/sort
     ./build.sh
    

    Note: The example directory location may vary depending on your setup:

    • Native: <sdk>/example/sort
    • Docker: /work/example/sort
    • QEMU: ~/sdk/example/sort
  2. Open the notebook in Jupyter:

    Navigate to example/sort/sort.ipynb in the Jupyter file browser.

  3. Execute cells in the notebook to see the sorting example in action.


Troubleshooting

Port Forwarding Issues

If you cannot access Jupyter, verify the following:

  1. Ensure the ports are correctly forwarded:
    • For QEMU: Check the -f option in run.sh.
    • For Docker: Verify the -p flags in the docker run command.
  2. Test connectivity:

     curl http://localhost:<host_jupyter_port>
    
  3. Make sure the ports aren’t used by other services. You can check which ports are currently in use on your host with:

     netstat -tuln
    

    or

     lsof -i -P -n | grep LISTEN
    

Jupyter Kernel Errors

If you encounter errors related to the kernel:

  • Ensure you selected C++17 as the kernel version.
  • Check that #pragma cling commands complete successfully.
  • Verify that the Jupyter server is running and accessible.

Additional Help

Refer to the Troubleshooting for further assistance.