diff options
Diffstat (limited to 'main.go')
-rw-r--r-- | main.go | 116 |
1 files changed, 116 insertions, 0 deletions
diff --git a/main.go b/main.go new file mode 100644 index 0000000..2928196 --- /dev/null +++ b/main.go @@ -0,0 +1,116 @@ +package main + +import ( + "bytes" + "fmt" + "github.com/gliderlabs/ssh" + "github.com/kr/pty" + "io" + "log" + "net/http" + "os/exec" +) + +var ( + metrics_num_passwords int +) + +func main() { + log.Println("Starting SSH listener") + + //// start the ssh server + //go func() { + // listenErr := ssh.ListenAndServe(":2222", nil, ssh.PasswordAuth(handlePass)) + // if listenErr != nil { + // log.Fatalln(listenErr.Error()) + // } + //}() + + go func() { + // star the metrics listener + log.Println("Starting HTTP metrics listener") + http.HandleFunc("/metrics", metricsHandler) + listenErr := http.ListenAndServe(":8080", nil) + if listenErr != nil { + log.Fatalln(listenErr.Error()) + } + }() + + ssh.Handle(handleConnection) + log.Fatal(ssh.ListenAndServe(":2222", nil, ssh.PasswordAuth(handlePass))) +} + +func handleConnection(s ssh.Session) { + cmd := exec.Command("bash") + p, _ := pty.Start(cmd) + + go func() { + var readErr error + for readErr == nil { + // create two buffers, one for storing the char input (buf) + // and the other for storing complete commands (commandBuffer) + buf := make([]byte, 1024) + commandBuffer := make([]byte, 0) + + // the current char + var char string + + // read until ENTER is pressed + for char != "\x0d"{ + + // read the char inserted by the user into the buffer + _, readErr = s.Read(buf) + + // trim the char and append it to the commandBuffer + char1 := bytes.Trim(buf, "\x00")[0] + if char1 == []byte("\x03")[0] { + s.Close() + return + } + commandBuffer = append(commandBuffer, char1) + + // write the char to stdout + char = string(bytes.Trim(buf, "\x00")) + input := string(bytes.Trim(buf, "\x00")) + io.WriteString(s, input) + } + + // prepare the command for execution + input := string(bytes.Trim(commandBuffer, "\x00")) + + // filter out unwanted commands + filteredInput := filter(input) + + // write the string to the commandHandler + io.WriteString(p, filteredInput) + s.Close() + return + } + }() + + io.Copy(s, p) + s.Close() +} + +func filter(buffer string) string { + //if strings.Contains(buffer, "wget") == false { + // return "\n" + //} + //return buffer + + // all ways return a newline -> track what is input + log.Printf("%s", buffer) + return "\n" +} + +func handlePass(ctx ssh.Context, pass string) bool { + metrics_num_passwords++ + log.Printf("%s@%s: '%s'", ctx.User(), ctx.RemoteAddr().String(), pass) + return true +} + +// Handle HTTP /metrics requests +func metricsHandler(w http.ResponseWriter, req *http.Request) { + fmt.Fprintf(w, "num_passwords %d\n", metrics_num_passwords) +} + |