initial checkin
authorEnrico Scholz <enrico.scholz@informatik.tu-chemnitz.de>
Fri, 26 Mar 2004 07:40:39 +0000 (07:40 +0000)
committerEnrico Scholz <enrico.scholz@informatik.tu-chemnitz.de>
Fri, 26 Mar 2004 07:40:39 +0000 (07:40 +0000)
git-svn-id: http://svn.linux-vserver.org/svn/util-vserver/trunk@1379 94cd875c-1c1d-0410-91d2-eb244daf1a30

util-vserver/scripts/vshelper [new file with mode: 0755]
util-vserver/src/vshelper-sync.c [new file with mode: 0644]

diff --git a/util-vserver/scripts/vshelper b/util-vserver/scripts/vshelper
new file mode 100755 (executable)
index 0000000..f642aa5
--- /dev/null
@@ -0,0 +1,182 @@
+#! /bin/bash
+
+# Copyright (C) 2004 Enrico Scholz <enrico.scholz@informatik.tu-chemnitz.de>
+#  
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; version 2 of the License.
+#  
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#  
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+
+## Usage: vshelper <xid> <action> <args>
+
+: ${UTIL_VSERVER_VARS:=/usr/lib/util-vserver/util-vserver-vars}
+test -e "$UTIL_VSERVER_VARS" || {
+    echo "Can not find util-vserver installation; aborting..." >&2
+    exit 1
+}
+. "$UTIL_VSERVER_VARS"
+. "$_LIB_FUNCTIONS"
+
+function showHelp
+{
+    echo $"\
+Usage: vshelper <xid> <event> <args>*
+
+Report bugs to <$PACKAGE_BUGREPORT>."
+    exit 0
+}
+
+function showVersion
+{
+    echo $"\
+vshelper $PACKAGE_VERSION -- userspace reboot helper
+This program is part of $PACKAGE_STRING
+
+Copyright (C) 2004 Enrico Scholz
+This program is free software; you may redistribute it under the terms of
+the GNU General Public License.  This program has absolutely no warranty."
+    exit 0
+}
+
+function doInternalMethod
+{
+    local method=$1
+    case "$method" in
+       (restart)
+           case "$ACTION" in
+               (restart*)
+                   logging $"Restarting vserver '$VSERVER'"
+                   execute $_VSERVER "$VSERVER" restart
+                   ;;
+               (halt|poweroff)
+                   logging $"Stopping vserver '$VSERVER'"
+                   execute $_VSERVER "$VSERVER" stop
+                   ;;
+               (swsusp)
+                   ## TODO: any senseful action here? Perhaps shutdown scheduler for it?
+                   exit 0
+               (*)
+                   warning $"Unknown action '$ACTION' for vserver '$VSERVER'"
+                   exit 1
+           esac
+           ;;
+           
+       (sync)
+           local f=${METHOD_ARGS[0]}
+           test "$f" ||
+               panic $"Insufficent arguments for method '$method' and vserver '$VSERVER'"
+
+           test -p "$f" ||
+               panic $"File '$f' which is required for synchronisation of vserver '$VSERVER' is not a pipe"
+
+           echo "$ACTION" >"$f"
+           ;;
+
+       (*)
+           local script
+           findObject -x script "$CONFDIR"/.defaults/apps/vshelper-methods/"$method" "$PKGLIBDIR"/vshelper-methods/"$method" ''
+           
+           test '$script' || {
+               warning $"No handler for internal method '$method' found"
+               exit 1
+           }
+
+           export VSERVER
+           execute "$script" "${ARGS[@]}"
+    esac
+}
+    
+function doDefaultMethod
+{
+    local handler
+
+    vshelper.getHandler handler "$VSERVER" "$ACTION" || {
+       warning $"No handler configured for action '$ACTION' on vserver '$VSERVER'"
+       exit 1
+    }
+
+    case "$handler" in
+       (/*)    execute "$handler" "${ARGS[@]}";;
+       (:*)    doInternalMethod "${handler##:}" "$@";;
+    esac
+}
+
+#===========
+
+
+test "$1" != '--version' || showVersion
+test "$1" != '--help'    || showHelp
+test "$#" -ge 2 ||
+    panic $"vshelper called with missing arguments; try '--help' for more information"
+
+vshelper.isEnabled || exit 0
+logging "$(date): vshelper $*"
+    
+set -eu
+
+declare -r XID=$1
+declare -r ACTION=$2
+
+
+this_xid=$($_VSERVER_INFO - XID)
+pxid=
+while true; do
+    pxid=$($_VSERVER_INFO "$XID" PXID) || break
+    test "$pxid" -ne "$this_xid"       || break
+    xid=$pxid
+done
+
+vserver_id=$($_VSERVER_INFO "$XID" ID) ||
+    panic $"No responsible vserver found for xid '$1' ($XID); aborting..."
+    
+test "$1" = "$XID" || {
+    logging "Giving 'vshelper' task for '$1' to parent vserver '$vserver_id' ($XID)"
+    execute $_VSERVER "$vserver_id" exec $_VSHELPER "$@"
+}
+
+#===========
+
+ARGS=( "$@" )
+
+declare -a state
+getFileArray state "$VSHELPERSTATEDIR/$XID" && test ${#state[@]} -ge 2 || {
+    logging "'vshelper' not configured for xid '$XID'"
+    exit 0
+}
+
+declare -r VSERVER=${state[0]}
+
+cfg_xid=$($_VSERVER_INFO "${state[0]}" CONTEXT false) ||
+    panic $"Configured vserver '$VSERVER' does not seem to run; aborting..."
+
+test "$cfg_xid" = "$XID" ||
+    panic $"Configured ($cfg_xid) and actual ($XID) xid for vserver '$VSERVER' are mismatching; aborting..."
+
+cur_xid=$($_VSERVER_INFO "$VSERVER" CONTEXT false) ||
+    panic $"Vserver '$VSERVER' with '$XID' does not seem to run; strange..."
+
+test "$cur_xid" = "$XID" ||
+    panic $"Expected ($XID) and actual ($cur_xid) xid for vserver '$VSERVER' are mismatching; strange..."
+
+
+method=${state[1]}
+if test "${#state[@]}" -gt 2; then
+    unset state[0] state[1]
+    declare -ra METHOD_ARGS=( "${state[@]}" )
+else
+    declare -ra METHOD_ARGS=()
+fi
+
+case "$method" in
+    (default)  doDefaultMethod "$@";;
+    (sync)     doInternalMethod "$method" "$@";;
+    (*)                panic $"Unknown method '$method' used by vserver '$VSERVER'";;
+esac
diff --git a/util-vserver/src/vshelper-sync.c b/util-vserver/src/vshelper-sync.c
new file mode 100644 (file)
index 0000000..cf987de
--- /dev/null
@@ -0,0 +1,99 @@
+// $Id$    --*- c -*--
+
+// Copyright (C) 2004 Enrico Scholz <enrico.scholz@informatik.tu-chemnitz.de>
+//  
+// This program is free software; you can redistribute it and/or modify
+// it under the terms of the GNU General Public License as published by
+// the Free Software Foundation; version 2 of the License.
+//  
+// This program is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+// GNU General Public License for more details.
+//  
+// You should have received a copy of the GNU General Public License
+// along with this program; if not, write to the Free Software
+// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+
+
+#ifdef HAVE_CONFIG_H
+#  include <config.h>
+#endif
+
+#include "util.h"
+
+#include <stdlib.h>
+#include <fcntl.h>
+#include <unistd.h>
+#include <signal.h>
+#include <stdio.h>
+
+static void
+showHelp(int fd, char const *cmd, int res)
+{
+  WRITE_MSG(fd, "Usage:  ");
+  WRITE_STR(fd, cmd);
+  WRITE_MSG(fd,
+           " [--] <pipe> <timeout>\n\n"
+           "Please report bugs to " PACKAGE_BUGREPORT "\n");
+  exit(res);
+}
+
+static void
+showVersion()
+{
+  WRITE_MSG(1,
+           "vshelper-sync " VERSION " -- waits for data from a pipe"
+           "This program is part of " PACKAGE_STRING "\n\n"
+           "Copyright (C) 2004 Enrico Scholz\n"
+           VERSION_COPYRIGHT_DISCLAIMER);
+  exit(0);
+}
+
+static volatile sig_atomic_t   timeout_flag = 0;
+
+void alarmHandler(int UNUSED sig)
+{
+  timeout_flag = 1;
+}
+
+int main(int argc, char *argv[])
+{
+  int          fd;
+  int          idx = 1;
+
+  if (argc>=2) {
+    if (strcmp(argv[1], "--help")   ==0) showHelp(1, argv[0], 0);
+    if (strcmp(argv[1], "--version")==0) showVersion();
+    if (strcmp(argv[1], "--")       ==0) ++idx;
+  }
+
+  if (argc<idx+2) {
+    WRITE_MSG(2, "Not enough parameters; use '--help' for more information\n");
+    return EXIT_FAILURE;
+  }
+
+
+  signal(SIGALRM, alarmHandler);
+  alarm(atoi(argv[idx+1]));
+  
+  fd = open(argv[idx], O_RDONLY,0);
+  if (timeout_flag) return EXIT_FAILURE;
+  if (fd==-1) {
+    perror("vshelper-sync: open()");
+    return EXIT_FAILURE;
+  }
+  
+  for (;;) {
+    char       buf[512];
+    ssize_t    len = read(fd,buf,sizeof buf);
+    if (len==0) break;
+    if (timeout_flag) return EXIT_FAILURE;
+    if (len==-1) {
+      perror("vshelper-sync: read()");
+      return EXIT_FAILURE;
+    }
+  }
+
+  return EXIT_SUCCESS;
+}