diff --git a/notebooks/FCLayer_graph.onnx b/notebooks/FCLayer_graph.onnx
index 3f29f902b0d98e55af7955a99965642db9621e2e..950c78a9de7224b83ff46da4920da1baa5d80d61 100644
Binary files a/notebooks/FCLayer_graph.onnx and b/notebooks/FCLayer_graph.onnx differ
diff --git a/notebooks/FINN-CodeGenerationAndCompilation.ipynb b/notebooks/FINN-CodeGenerationAndCompilation.ipynb
index e3f0f03e8c10d6c9c53c2e58d0b7418ddab5d70a..f73b0f5610af51a9a178cb986e1ac9d6e9bcfa56 100644
--- a/notebooks/FINN-CodeGenerationAndCompilation.ipynb
+++ b/notebooks/FINN-CodeGenerationAndCompilation.ipynb
@@ -245,7 +245,7 @@
   },
   {
    "cell_type": "code",
-   "execution_count": 12,
+   "execution_count": 11,
    "metadata": {},
    "outputs": [
     {
@@ -283,7 +283,7 @@
   },
   {
    "cell_type": "code",
-   "execution_count": 13,
+   "execution_count": 12,
    "metadata": {},
    "outputs": [
     {
@@ -547,6 +547,101 @@
     "### Compilation"
    ]
   },
+  {
+   "cell_type": "markdown",
+   "metadata": {},
+   "source": [
+    "<font size=\"3\">The compilation is a transformation pass like the code generation. The code of this transformation is shown below. </font>"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 16,
+   "metadata": {},
+   "outputs": [
+    {
+     "name": "stdout",
+     "output_type": "stream",
+     "text": [
+      "class Compile(Transformation):\n",
+      "    \"\"\"Compile for all nodes in model\"\"\"\n",
+      "\n",
+      "    def __init__(self):\n",
+      "        super().__init__()\n",
+      "\n",
+      "    def apply(self, model):\n",
+      "        for node in model.graph.node:\n",
+      "            op_type = node.op_type\n",
+      "            if node.domain == \"finn\":\n",
+      "                backend_attribute = util.get_by_name(node.attribute, \"backend\")\n",
+      "                if backend_attribute is None:\n",
+      "                    continue\n",
+      "                backend_value = backend_attribute.s.decode(\"UTF-8\")\n",
+      "                if backend_value == \"fpgadataflow\":\n",
+      "                    try:\n",
+      "                        # lookup op_type in registry of CustomOps\n",
+      "                        inst = registry.custom_op[op_type](node)\n",
+      "                        # ensure that code is generated\n",
+      "                        assert inst.get_nodeattr(\"code_gen_dir\") != \"\"\n",
+      "                        # call the compilation function for this node\n",
+      "                        inst.compile_singlenode_code()\n",
+      "                        # ensure that executable path is now set\n",
+      "                        assert inst.get_nodeattr(\"executable_path\") != \"\"\n",
+      "                    except KeyError:\n",
+      "                        # exception if op_type is not supported\n",
+      "                        raise Exception(\n",
+      "                            \"Custom op_type %s is currently not supported.\" % op_type\n",
+      "                        )\n",
+      "        return (model, False)\n",
+      "\n"
+     ]
+    }
+   ],
+   "source": [
+    "from finn.transformation.fpgadataflow.compile import Compile\n",
+    "showSrc(Compile)"
+   ]
+  },
+  {
+   "cell_type": "markdown",
+   "metadata": {},
+   "source": [
+    "<font size=\"3\">The scheme resembles that of the code generation transformation pass. The pass iterates over all nodes in the model and if `domain=\"finn\"` and `backend=\"fpgadataflow\"` is True, the compilation is activated for that node. First an instance of the node is created and checked whether the code was generated. For this the node attribute `code_gen_dir` is checked. If it exists, the function `compile_singlenode_code()` can be executed. Then it is checked whether the path to the executable has been set. There is an exception if the custom op_type is not supported. \n",
+    "\n",
+    "The actual compilation is done with the function `compile_singlenode_code()`. What happens inside the function is shown below.</font>"
+   ]
+  },
+  {
+   "cell_type": "code",
+   "execution_count": 17,
+   "metadata": {},
+   "outputs": [
+    {
+     "name": "stdout",
+     "output_type": "stream",
+     "text": [
+      "    def compile_singlenode_code(self):\n",
+      "        code_gen_dir = self.get_nodeattr(\"code_gen_dir\")\n",
+      "        builder = CppBuilder()\n",
+      "        builder.append_includes(\"-I/workspace/finn/src/finn/data/cpp\")\n",
+      "        builder.append_includes(\"-I/workspace/cnpy/\")\n",
+      "        builder.append_includes(\"-I/workspace/finn-hlslib\")\n",
+      "        builder.append_includes(\"-I/workspace/vivado-hlslib\")\n",
+      "        builder.append_includes(\"--std=c++11\")\n",
+      "        builder.append_sources(code_gen_dir + \"/*.cpp\")\n",
+      "        builder.append_sources(\"/workspace/cnpy/cnpy.cpp\")\n",
+      "        builder.append_includes(\"-lz\")\n",
+      "        builder.set_executable_path(code_gen_dir + \"/node_model\")\n",
+      "        builder.build(code_gen_dir)\n",
+      "        self.set_nodeattr(\"executable_path\", builder.executable_path)\n",
+      "\n"
+     ]
+    }
+   ],
+   "source": [
+    "showSrc(StreamingFCLayer_Batch.compile_singlenode_code)"
+   ]
+  },
   {
    "cell_type": "code",
    "execution_count": null,