summaryrefslogtreecommitdiffstats
path: root/hyper
diff options
context:
space:
mode:
authormakefu <github@syntax-fehler.de>2011-09-20 17:19:25 +0200
committermakefu <github@syntax-fehler.de>2011-09-20 17:19:25 +0200
commit32ddd0b2dec60ac99e30e26819e4653ccc47690e (patch)
tree6745bd80ed8392f0165a026215268ca24d3ce5c5 /hyper
parentdfadcd3b21d838c9d1bb8fc37304cec71e7517d8 (diff)
parentfcbb481cbd888d6ab66b09e649c754a012198e53 (diff)
Merge branch 'master' of github.com:krebscode/painload
Diffstat (limited to 'hyper')
-rw-r--r--hyper/process/main.go92
-rwxr-xr-xhyper/process/spawn103
2 files changed, 149 insertions, 46 deletions
diff --git a/hyper/process/main.go b/hyper/process/main.go
index 5420f681..214dade9 100644
--- a/hyper/process/main.go
+++ b/hyper/process/main.go
@@ -10,68 +10,68 @@ import "bytes"
import "hyper/process"
-var proc = map[string] *hyper.Process{}
+var proc = map[string]*hyper.Process{}
// TODO Retrieve Process, Write, Kill [autokill], get exit code
func RespondJSON(res http.ResponseWriter, v interface{}) os.Error {
- content, err := json.Marshal(v)
- if err == nil {
- log.Printf("< %s", content)
- res.Header().Set("Content-Type", "application/json; charset=\"utf-8\"")
- res.WriteHeader(http.StatusOK)
- res.Write(content)
- } else {
- log.Printf("%s while json.Marshal(%s)", err, v)
- }
- return err
+ content, err := json.Marshal(v)
+ if err == nil {
+ log.Printf("< %s", content)
+ res.Header().Set("Content-Type", "application/json; charset=\"utf-8\"")
+ res.WriteHeader(http.StatusOK)
+ res.Write(content)
+ } else {
+ log.Printf("%s while json.Marshal(%s)", err, v)
+ }
+ return err
}
func CreateProcessHandler(res http.ResponseWriter, req *http.Request) {
- if p, err := hyper.NewProcess(req); err == nil {
- id := p.Id()
- proc[id] = p
- RespondJSON(res, &map[string]string{
- "path": fmt.Sprintf("/proc/%s", id),
- })
- } else {
- log.Printf("%s", err)
- res.WriteHeader(http.StatusInternalServerError)
- }
+ if p, err := hyper.NewProcess(req); err == nil {
+ id := p.Id()
+ proc[id] = p
+ RespondJSON(res, &map[string]string{
+ "path": fmt.Sprintf("/proc/%s", id),
+ })
+ } else {
+ log.Printf("%s", err)
+ res.WriteHeader(http.StatusInternalServerError)
+ }
}
func RetrieveProcess(res http.ResponseWriter, req *http.Request) {
- if p := proc[mux.Vars(req)["id"]]; p != nil {
- RespondJSON(res, p)
- } else {
- res.WriteHeader(http.StatusNotFound)
- }
+ if p := proc[mux.Vars(req)["id"]]; p != nil {
+ RespondJSON(res, p)
+ } else {
+ res.WriteHeader(http.StatusNotFound)
+ }
}
func FeedProcess(res http.ResponseWriter, req *http.Request) {
- if p := proc[mux.Vars(req)["id"]]; p != nil {
- body := make([]byte, 4096)
- if _, err := req.Body.Read(body); err == nil {
- body = bytes.TrimRight(body, string([]byte{0}))
- p.Write(body)
- //if err := p.Write(body); err == nil {
- RespondJSON(res, true)
- //}
- }
- } else {
- res.WriteHeader(http.StatusNotFound)
- }
+ if p := proc[mux.Vars(req)["id"]]; p != nil {
+ body := make([]byte, 4096)
+ if _, err := req.Body.Read(body); err == nil {
+ body = bytes.TrimRight(body, string([]byte{0}))
+ p.Write(body)
+ //if err := p.Write(body); err == nil {
+ RespondJSON(res, true)
+ //}
+ }
+ } else {
+ res.WriteHeader(http.StatusNotFound)
+ }
}
func main() {
- // Gorilla
- mux.HandleFunc("/proc", CreateProcessHandler).Methods("POST")
- mux.HandleFunc("/proc/{id}", RetrieveProcess).Methods("GET")
- mux.HandleFunc("/proc/{id}", FeedProcess).Methods("POST")
+ // Gorilla
+ mux.HandleFunc("/proc", CreateProcessHandler).Methods("POST")
+ mux.HandleFunc("/proc/{id}", RetrieveProcess).Methods("GET")
+ mux.HandleFunc("/proc/{id}", FeedProcess).Methods("POST")
- err := http.ListenAndServe("0.0.0.0:8888", mux.DefaultRouter)
- if err != nil {
- log.Fatal("ListenAndServe: ", err.String())
- }
+ err := http.ListenAndServe("0.0.0.0:8888", mux.DefaultRouter)
+ if err != nil {
+ log.Fatal("ListenAndServe: ", err.String())
+ }
}
diff --git a/hyper/process/spawn b/hyper/process/spawn
new file mode 100755
index 00000000..65e94d86
--- /dev/null
+++ b/hyper/process/spawn
@@ -0,0 +1,103 @@
+#! /bin/sh
+#
+# [sh -x] spawn [command [argument ...]]
+#
+# export id to create&destroy or reuse the working directory //proc/$id/.
+# this feature is for debug only and marked as deprecated, so don't rely
+# on it too hard.
+#
+spawn() {
+ set -euf
+
+ # establish working subdirectory in //proc. we're mking only
+ # transient dirs, i.e. if we mkdir, then we also defer rmdir.
+ if test -n "${id-}"; then
+ : "using id=$id from env"
+ wd=$pd/$id
+ if ! test -d $wd; then
+ : "make transient $wd/"
+ mkdir $wd
+ defer rmdir $wd
+ elif ! test `ls $wd | wc -l` = 0; then
+ : "$wd/ is not empty!"
+ exit 23
+ else
+ : "reuse existing $wd/"
+ fi
+ else
+ id=`cd $pd && mktemp -d XXXXXXXXXXXXXXXX`
+ wd=$pd/$id
+ defer rmdir $wd
+ : "made transient $wd/"
+ fi
+
+ # change to //proc working directory
+ cwd="$PWD"
+ cd $wd
+ defer cd $cwd
+
+ # create named pipes for the child process's stdio
+ mkfifo 0 1 2
+ defer rm 0 1 2
+
+ # spawn child process
+ ( : "in $PWD/ spawn ${*:-nothing}"
+ set +x # disable debug output so we don't clobber 2
+ exec 0>&- 1>&- 2>&- 0<>0 1<>1 2<>2
+ cd "$cwd"
+ exec "$@") &
+ pid=$!
+
+ # setup a trap to kill the child process if this (parent) process dies
+ defer kill $pid
+
+ # store misc. info.
+ ln -snf $cwd cwd
+ echo $id >id
+ echo $$ >ppid
+ echo $pid >pid
+ defer rm cwd id pid ppid
+
+ # wait for the child process's
+ set +e
+ wait $pid
+ code=$?
+ set -e
+
+ # the child is already dead
+ cancel kill $pid
+
+ # return the same way wait did
+ (exit $code)
+}
+
+#
+# defer [command [argument ...]]
+#
+# Defer execution of a command. Deferred commands are executed in LIFO
+# order immediately before the script terminates. See (golang's defer
+# statement for more information how this should work).
+#
+defer() {
+ defer="$*${defer+
+$defer}"
+}
+
+#
+# cancel [command [argument ...]]
+#
+# Cancel a deferred command. The arguments have to match exactly a
+# prior defer call or else chaos and mayhem shall haunt thee and shi-
+#
+cancel() {
+ defer="`echo "$defer" | grep -Fxv "$*"`"
+}
+
+# setup //proc directory
+pd=/tmp/krebs/proc
+mkdir -p $pd
+test -w $pd
+
+# setup deferred execution and spawn command
+trap 'eval "${defer-}"; defer=' EXIT INT TERM
+spawn "$@"