AppImage packaging

Disabled by default. To kick the the tires:

wget https://github.com/linuxdeploy/linuxdeploy/releases/download/continuous/linuxdeploy-x86_64.AppImage
sudo mv linuxdeploy-x86_64.AppImage /usr/local/bin/linuxdeploy
sudo chmod +x linuxdeploy-x86_64.AppImage

Enable VPP_BUILD_APPIMAGE e.g. in ccmake
make build | make build-release

The vpp AppImage lands in .../install-xxx-native/VPP-x86_64.AppImage. To run it:

./VPP-x86_64.AppImage vpp unix interactive

To run it (as root) and inhale the usual startup.conf:

sudo ./VPP-x86_64.AppImage \${HERE}/bin/vpp -c \${HERE}/etc/vpp/startup.conf

To run vppctl, or any of the usual vpp binaries:

./VPP-x86_64.AppImage vppctl [etc]

Change-Id: Ide8cf4658cbb56f1d36a1ce7fc8f7338f8d38278
Signed-off-by: Dave Barach <dave@barachs.net>
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index d467da7..248d7b8 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -98,6 +98,7 @@
   set(SUBDIRS
     vppinfra svm vlib vlibmemory vlibapi vnet vpp vat vcl plugins
     vpp-api tools/vppapigen tools/g2 tools/elftool tools/perftool cmake pkg
+    tools/appimage
   )
 elseif("${CMAKE_SYSTEM_NAME}" STREQUAL "Darwin")
   set(SUBDIRS vppinfra)
@@ -141,4 +142,3 @@
 pr("Target processor" "${CMAKE_SYSTEM_PROCESSOR}")
 pr("Prefix path" "${CMAKE_PREFIX_PATH}")
 pr("Install prefix" "${CMAKE_INSTALL_PREFIX}")
-
diff --git a/src/tools/appimage/AppRun b/src/tools/appimage/AppRun
new file mode 100755
index 0000000..b4c243c
--- /dev/null
+++ b/src/tools/appimage/AppRun
@@ -0,0 +1,14 @@
+#!/bin/sh
+SELF=$(readlink -f "$0")
+HERE=${SELF%/*}
+export PATH="${HERE}/usr/bin/:${HERE}/usr/sbin/:${HERE}/usr/games/:${HERE}/bin/:${HERE}/sbin/${PATH:+:$PATH}"
+export LD_LIBRARY_PATH="${HERE}/usr/lib/:${HERE}/usr/lib/i386-linux-gnu/:${HERE}/usr/lib/x86_64-linux-gnu/:${HERE}/usr/lib32/:${HERE}/usr/lib64/:${HERE}/lib/:${HERE}/lib/i386-linux-gnu/:${HERE}/lib/x86_64-linux-gnu/:${HERE}/lib32/:${HERE}/lib64/${LD_LIBRARY_PATH:+:$LD_LIBRARY_PATH}"
+export PYTHONPATH="${HERE}/usr/share/pyshared/${PYTHONPATH:+:$PYTHONPATH}"
+export XDG_DATA_DIRS="${HERE}/usr/share/${XDG_DATA_DIRS:+:$XDG_DATA_DIRS}"
+export PERLLIB="${HERE}/usr/share/perl5/:${HERE}/usr/lib/perl5/${PERLLIB:+:$PERLLIB}"
+export GSETTINGS_SCHEMA_DIR="${HERE}/usr/share/glib-2.0/schemas/${GSETTINGS_SCHEMA_DIR:+:$GSETTINGS_SCHEMA_DIR}"
+export QT_PLUGIN_PATH="${HERE}/usr/lib/qt4/plugins/:${HERE}/usr/lib/i386-linux-gnu/qt4/plugins/:${HERE}/usr/lib/x86_64-linux-gnu/qt4/plugins/:${HERE}/usr/lib32/qt4/plugins/:${HERE}/usr/lib64/qt4/plugins/:${HERE}/usr/lib/qt5/plugins/:${HERE}/usr/lib/i386-linux-gnu/qt5/plugins/:${HERE}/usr/lib/x86_64-linux-gnu/qt5/plugins/:${HERE}/usr/lib32/qt5/plugins/:${HERE}/usr/lib64/qt5/plugins/${QT_PLUGIN_PATH:+:$QT_PLUGIN_PATH}"
+# EXEC=$(grep -e '^Exec=.*' "${HERE}"/*.desktop | head -n 1 | cut -d "=" -f 2 | cut -d " " -f 1)
+# exec "${EXEC}" "$@"
+# So you can run vppctl, etc.
+eval exec $*
diff --git a/src/tools/appimage/CMakeLists.txt b/src/tools/appimage/CMakeLists.txt
new file mode 100644
index 0000000..1b83656
--- /dev/null
+++ b/src/tools/appimage/CMakeLists.txt
@@ -0,0 +1,27 @@
+# Copyright (c) 2018 Cisco and/or its affiliates.
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at:
+#
+#     http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+option(VPP_BUILD_APPIMAGE "Build VPP AppImage" OFF)
+if(VPP_BUILD_APPIMAGE)
+  install(FILES AppRun DESTINATION .
+    PERMISSIONS OWNER_READ OWNER_WRITE OWNER_EXECUTE
+                GROUP_READ GROUP_WRITE GROUP_EXECUTE
+                WORLD_READ WORLD_EXECUTE)
+  install(FILES vpp.desktop DESTINATION .)
+  install(FILES vpp.png DESTINATION .)
+  install(FILES vpp.svg DESTINATION share/icons/hicolor/scalable/vpp.svg)
+  install(CODE "EXECUTE_PROCESS(COMMAND ln -s . ./usr
+                WORKING_DIRECTORY ${CMAKE_INSTALL_PREFIX})")
+  install(CODE "EXECUTE_PROCESS(
+          COMMAND linuxdeploy --appdir vpp --output appimage
+          WORKING_DIRECTORY ${CMAKE_INSTALL_PREFIX}/..)")
+endif()
diff --git a/src/tools/appimage/vpp.desktop b/src/tools/appimage/vpp.desktop
new file mode 100644
index 0000000..008965c
--- /dev/null
+++ b/src/tools/appimage/vpp.desktop
@@ -0,0 +1,11 @@
+[Desktop Entry]
+Name=VPP
+Exec=vpp %F
+Icon=vpp
+Type=Application
+Categories=Network;
+Comment=Vector Packet Processor
+Name[en]=VPP
+Terminal=false
+StartupNotify=true
+NoDisplay=false
diff --git a/src/tools/appimage/vpp.png b/src/tools/appimage/vpp.png
new file mode 100644
index 0000000..ef78981
--- /dev/null
+++ b/src/tools/appimage/vpp.png
Binary files differ
diff --git a/src/tools/appimage/vpp.svg b/src/tools/appimage/vpp.svg
new file mode 100644
index 0000000..58b901e
--- /dev/null
+++ b/src/tools/appimage/vpp.svg
@@ -0,0 +1,112 @@
+<?xml version="1.0" encoding="UTF-8" standalone="no"?>
+<!-- Created with Inkscape (http://www.inkscape.org/) -->
+
+<svg
+   xmlns:dc="http://purl.org/dc/elements/1.1/"
+   xmlns:cc="http://creativecommons.org/ns#"
+   xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
+   xmlns:svg="http://www.w3.org/2000/svg"
+   xmlns="http://www.w3.org/2000/svg"
+   xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
+   xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
+   width="210mm"
+   height="297mm"
+   viewBox="0 0 210 297"
+   version="1.1"
+   id="svg8"
+   inkscape:version="0.92.4 (unknown)"
+   sodipodi:docname="vpp.svg">
+  <defs
+     id="defs2" />
+  <sodipodi:namedview
+     id="base"
+     pagecolor="#ffffff"
+     bordercolor="#666666"
+     borderopacity="1.0"
+     inkscape:pageopacity="0.0"
+     inkscape:pageshadow="2"
+     inkscape:zoom="0.35"
+     inkscape:cx="400"
+     inkscape:cy="560"
+     inkscape:document-units="mm"
+     inkscape:current-layer="layer1"
+     showgrid="false"
+     inkscape:window-width="1248"
+     inkscape:window-height="1044"
+     inkscape:window-x="511"
+     inkscape:window-y="283"
+     inkscape:window-maximized="0" />
+  <metadata
+     id="metadata5">
+    <rdf:RDF>
+      <cc:Work
+         rdf:about="">
+        <dc:format>image/svg+xml</dc:format>
+        <dc:type
+           rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
+        <dc:title></dc:title>
+      </cc:Work>
+    </rdf:RDF>
+  </metadata>
+  <g
+     inkscape:label="Layer 1"
+     inkscape:groupmode="layer"
+     id="layer1">
+    <flowRoot
+       xml:space="preserve"
+       id="flowRoot3713"
+       style="fill:black;fill-opacity:1;stroke:none;font-family:OpenSymbol;font-style:normal;font-weight:normal;font-size:40px;line-height:1.25;letter-spacing:0px;word-spacing:0px;-inkscape-font-specification:OpenSymbol;font-stretch:normal;font-variant:normal;"><flowRegion
+         id="flowRegion3715"
+         style="-inkscape-font-specification:OpenSymbol;font-family:OpenSymbol;font-weight:normal;font-style:normal;font-stretch:normal;font-variant:normal;"><rect
+           id="rect3717"
+           width="280"
+           height="200"
+           x="85.714287"
+           y="153.94826"
+           style="-inkscape-font-specification:OpenSymbol;font-family:OpenSymbol;font-weight:normal;font-style:normal;font-stretch:normal;font-variant:normal;" /></flowRegion><flowPara
+         id="flowPara3719"></flowPara></flowRoot>    <flowRoot
+       xml:space="preserve"
+       id="flowRoot3721"
+       style="font-style:normal;font-weight:normal;font-size:40px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none"
+       transform="scale(0.26458333)"><flowRegion
+         id="flowRegion3723"><rect
+           id="rect3725"
+           width="560"
+           height="420"
+           x="51.42857"
+           y="111.09111" /></flowRegion><flowPara
+         id="flowPara3727" /></flowRoot>    <flowRoot
+       xml:space="preserve"
+       id="flowRoot3729"
+       style="font-style:normal;font-weight:normal;font-size:40px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none"
+       transform="matrix(2.4431409,0,0,2.5199848,-134.77294,-217.23292)"><flowRegion
+         id="flowRegion3731"><rect
+           id="rect3733"
+           width="251.42857"
+           height="360"
+           x="65.714287"
+           y="91.09111" /></flowRegion><flowPara
+         id="flowPara3735">V</flowPara></flowRoot>    <flowRoot
+       xml:space="preserve"
+       id="flowRoot3749"
+       style="font-style:normal;font-weight:normal;font-size:40px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none"
+       transform="matrix(2.7137436,0,0,2.5199847,-334.37256,-931.00484)"><flowRegion
+         id="flowRegion3751"><rect
+           id="rect3753"
+           width="62.857136"
+           height="74.285683"
+           x="151.42857"
+           y="408.23398" /></flowRegion><flowPara
+         id="flowPara3755">P</flowPara></flowRoot>    <flowRoot
+       xml:space="preserve"
+       id="flowRoot3749-7"
+       style="font-style:normal;font-weight:normal;font-size:40px;line-height:1.25;font-family:sans-serif;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none"
+       transform="matrix(2.7137437,0,0,2.5199847,-289.14292,-853.73425)"><flowRegion
+         id="flowRegion3751-6"><rect
+           id="rect3753-9"
+           width="62.857136"
+           height="74.285683"
+           x="151.42857"
+           y="408.23398" /></flowRegion><flowPara
+         id="flowPara3755-1">P</flowPara></flowRoot>  </g>
+</svg>