lima-vm / sshocker Goto Github PK
View Code? Open in Web Editor NEWssh + reverse sshfs + port forwarder, in Docker-like CLI (predecessor of Lima)
License: Apache License 2.0
ssh + reverse sshfs + port forwarder, in Docker-like CLI (predecessor of Lima)
License: Apache License 2.0
Currently a shell can start before the mounts are ready
This issue was automatically created by Allstar.
Security Policy Violation
Security policy not enabled.
A SECURITY.md file can give users information about what constitutes a vulnerability and how to report one securely so that information about a bug is not publicly visible. Examples of secure reporting methods include using an issue tracker with private issue support, or encrypted email with a published key.
To fix this, add a SECURITY.md file that explains how to handle vulnerabilities found in your repository. Go to https://github.com/lima-vm/sshocker/security/policy to enable.
For more information, see https://docs.github.com/en/code-security/getting-started/adding-a-security-policy-to-your-repository.
This issue will auto resolve when the policy is in compliance.
Issue created by Allstar. See https://github.com/ossf/allstar/ for more information. For questions specific to the repository, please contact the owner or maintainer.
It needs to resolve the target, before waiting for it to appear in mount...
For instance when /mnt
is a symbolic link to /var/mnt
like in CoreOS
The sftp server provided by github.com/pkg/sftp.NewServer(...)
permits running arbitrary commands, like so:
sftp> ! bash
bash-5.1$ whoami
protosam
As far as I can tell, I don't see anything preventing sftp.NewServer(...) from doing this?
This widens the surface area of an attack from inside the vm if a container is escaped and an attacker has access to the sshfs process. Debugging tools can be used from arbitrarily ran containers to attach to the sshfs pid. From there the sshfs pid can be exploited to run arbitrary commands at the host level.
OpenSSH sftp server might be more robust than github.com/pkg/sftp
.
Performance seems almost same, though.
alternative Title: exec.Command with ssh doesn't work when there are spaces in args
(I'm pondering how to best fix this for one of my apps too :) )
sven@x1carbon:/tmp/space path$ ./sshocker --debug -p 8080:80 -v .:/tmp/sshfs xeon
DEBU[0000] executing ssh for preparing sshfs: /usr/bin/ssh [ssh -o ControlMaster=auto -o ControlPath=~/.ssh/sshocker-%r@%h:%p-232029 -o ControlPersist=yes xeon -- mkdir -p /tmp/sshfs]
DEBU[0000] executing ssh for remote sshfs: /usr/bin/ssh [ssh -o ControlMaster=auto -o ControlPath=~/.ssh/sshocker-%r@%h:%p-232029 -o ControlPersist=yes xeon -- sshfs :/tmp/space path /tmp/sshfs -o slave]
DEBU[0000] starting sftp server for /tmp/space path
DEBU[0000] generated script "wait-for-remote-ready" with map map[Dir:/tmp/sshfs MaxTrial:30]: "#!/bin/sh\nset -eu\ndir=\"/tmp/sshfs\"\nmax_trial=\"30\"\nLANG=C\nLC_ALL=C\nexport LANG LC_ALL\ni=0\nwhile : ; do\n # FIXME: not really robust\n if mount | grep \"on ${dir}\" | egrep -qw \"fuse.sshfs|osxfuse\"; then\n echo '{\"return\":{}}'\n exit 0\n fi\n sleep 1\n if [ $i -ge ${max_trial} ]; then\n echo >&2 \"sshfs does not seem to be mounted on ${dir}\"\n exit 1\n fi\n i=$((i + 1))\ndone\n"
DEBU[0000] executing ssh for script "wait-for-remote-ready": /usr/bin/ssh [ssh -o ControlMaster=auto -o ControlPath=~/.ssh/sshocker-%r@%h:%p-232029 -o ControlPersist=yes xeon -- /bin/sh]
fuse: bad mount point `path': No such file or directory
DEBU[0000] sftp server for /tmp/space path exited with EOF (negligible) error=EOF
DEBU[0031] executed script "wait-for-remote-ready", stdout="", stderr="sshfs does not seem to be mounted on /tmp/sshfs\n", err=failed to execute script "wait-for-remote-ready": stdout="", stderr="sshfs does not seem to be mounted on /tmp/sshfs\n": exit status 1
WARN[0031] failed to confirm whether /tmp/sshfs [remote] is successfully mounted error="failed to execute script \"wait-for-remote-ready\": stdout=\"\", stderr=\"sshfs does not seem to be mounted on /tmp/sshfs\\n\": exit status 1"
DEBU[0031] executing main SSH: /usr/bin/ssh [ssh -o ControlMaster=auto -o ControlPath=~/.ssh/sshocker-%r@%h:%p-232029 -o ControlPersist=yes -L 0.0.0.0:8080:localhost:80 xeon --]
Last login: Thu Oct 8 10:03:54 2020 from 10.10.10.146
sven@xeon:~$
This issue was automatically created by Allstar.
Security Policy Violation
PR Approvals not configured for branch master
This issue will auto resolve when the policy is in compliance.
Issue created by Allstar. See https://github.com/ossf/allstar/ for more information. For questions specific to the repository, please contact the owner or maintainer.
We should use https://pkg.go.dev/github.com/pkg/[email protected]#NewRequestServer to prevent the remote host from accessing unexpected local directories (if sshfs
had a bug)
Like using the -N
option to ssh
?
Current workaround is running sleep
It can be convenient to address the host by name (in config)
But currently this doesn't work, since port is hardcoded (to 22)
atm, it waits for a timeout
sven@x1carbon:/tmp/space path$ ./sshocker -p 8080:80 -v .:/tmp/sshfs xeon
bash: sshfs: command not found
WARN[0031] failed to confirm whether /tmp/sshfs [remote] is successfully mounted error="failed to execute script \"wait-for-remote-ready\": stdout=\"\", stderr=\"sshfs does not seem to be mounted on /tmp/sshfs\\n\": exit status 1"
Last login: Thu Oct 8 10:00:37 2020 from 10.10.10.146
It might be useful if multiple remote hosts can be connected to an ad-hoc VPN like this:
(terminal1)$ sshocker network create foo
(terminal1)$ sshocker run --network foo --ip 192.168.42.101/24 host1
(terminal2)$ sshocker run --network foo --ip 192.168.42.102/24 host2
This could be easily implemented using vdeplug4, though it requires the root privileges (in NS at least) for creating TAP devices, and is not apt-gettable.
For unprivileged cases (#7) I'm currently thinking forwarding connections to a loopback address like 127.0.42.101 on remote to a user-space multiplexer via socat-over-stdio.
sshocker needs to be aware of the app's port numbers to implement this.
Connecting to Azure ACI and Kubernetes could be supported using az container exec
and kubectl exec
.
-v can be implemented using sshfs-over-stdio (without ssh), but it requires the container to be privileged. So maybe we should just sync directories with tar (and sync back from the remote to the client on exit) or maybe with mutagen.io .
-p can be implemented using socat-over-stdio without privilege.
Amazon ECS can be supported in future but requires aws/containers-roadmap#1050 to be implemented.
Not sure about Google Cloud Run (currently lacking "exec" capability)
Currently I just made a copy/paste version, that was called sudoExecuteScript
It would be nice if this feature was available through the regular functions?
@@ -1,8 +1,8 @@
-// ExecuteScript executes the given script on the remote host via stdin.
+// sudoExecuteScript executes the given script (as root) on the remote host via stdin.
// Returns stdout and stderr.
//
// scriptName is used only for readability of error strings.
-func ExecuteScript(host string, port int, c *SSHConfig, script, scriptName string) (string, string, error) {
+func sudoExecuteScript(host string, port int, c *ssh.SSHConfig, script, scriptName string) (stdout, stderr string, err error) {
if c == nil {
return "", "", errors.New("got nil SSHConfig")
}
@@ -15,15 +15,15 @@
if port != 0 {
sshArgs = append(sshArgs, "-p", strconv.Itoa(port))
}
- sshArgs = append(sshArgs, host, "--", interpreter)
+ sshArgs = append(sshArgs, host, "--", "sudo", interpreter)
sshCmd := exec.Command(sshBinary, sshArgs...)
sshCmd.Stdin = strings.NewReader(script)
- var stderr bytes.Buffer
- sshCmd.Stderr = &stderr
+ var buf bytes.Buffer
+ sshCmd.Stderr = &buf
logrus.Debugf("executing ssh for script %q: %s %v", scriptName, sshCmd.Path, sshCmd.Args)
out, err := sshCmd.Output()
if err != nil {
- return string(out), stderr.String(), fmt.Errorf("failed to execute script %q: stdout=%q, stderr=%q: %w", scriptName, string(out), stderr.String(), err)
+ return string(out), buf.String(), fmt.Errorf("failed to execute script %q: stdout=%q, stderr=%q: %w", scriptName, string(out), buf.String(), err)
}
- return string(out), stderr.String(), nil
+ return string(out), buf.String(), nil
}
(renamed the "stderr" variable due to go-critic, feel free to ignore)
unnamedResult: consider giving a name to these results (gocritic)
Currently AFAIK sshocker
is only looking for the sftp-server
provided by cygwin, which means it won't work if we don't have cygwin installed, since windows also provides an openSSH server, maybe that can be used, which would require users to just enable it from the optional features, once enabled the binary is present at: C:/Windows/System32/OpenSSH/sftp-server.exe
A declarative, efficient, and flexible JavaScript library for building user interfaces.
๐ Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
An Open Source Machine Learning Framework for Everyone
The Web framework for perfectionists with deadlines.
A PHP framework for web artisans
Bring data to life with SVG, Canvas and HTML. ๐๐๐
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
Some thing interesting about web. New door for the world.
A server is a program made to process requests and deliver data to clients.
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
Some thing interesting about visualization, use data art
Some thing interesting about game, make everyone happy.
We are working to build community through open source technology. NB: members must have two-factor auth.
Open source projects and samples from Microsoft.
Google โค๏ธ Open Source for everyone.
Alibaba Open Source for everyone
Data-Driven Documents codes.
China tencent open source team.