termux / termux-packages

A package build system for Termux.
https://termux.dev
Other
13.15k stars 3.02k forks source link

[Bug]: OpenSSH as root stopped working because of "Privilege separation user sshd does not exist" on client connect #20774

Closed andreas1288 closed 3 months ago

andreas1288 commented 3 months ago

Problem description

See also https://github.com/termux/termux-packages/issues/20769. Thank you for the fast reaction! Unfortunately it seams that the error occurs on multiple places.

After updating to openssh_9.8p1-3_aarch64.deb the openssh daemon starts under root. However, on connection of a client the fork exits with

Privilege separation user sshd does not exist

the client gets the error

kex_exchange_identification: read: Connection reset by peer

What steps will reproduce the bug?

Start ssh with as root.

sudo sshd

user@Pixel8:/data/data/com.termux> su
:/data/data/com.termux # /data/data/com.termux/files/usr/bin/sshd -D -d
debug1: sshd version OpenSSH_9.8, OpenSSL 3.2.1 30 Jan 2024
debug1: private host key #0: ssh-rsa ...
debug1: private host key #1: ecdsa-sha2-nistp256 ...
debug1: private host key #2: ssh-ed25519 SHA256:...
debug1: rexec_argv[1]='-D'
debug1: rexec_argv[2]='-d'
debug1: Bind to port 11111 on ::.
Server listening on :: port 11111.
debug1: Bind to port 11111 on 0.0.0.0.
Server listening on 0.0.0.0 port 11111.
debug1: Server will not fork when running in debugging mode.
debug1: rexec start in 9 out 9 newsock 9 pipe -1 sock 12/13
debug1: sshd version OpenSSH_9.8, OpenSSL 3.2.1 30 Jan 2024
Privilege separation user sshd does not exist
255|:/data/data/com.termux # 

Use the following config file:

StrictModes no
Port 11111
PrintMotd no
PasswordAuthentication no
Subsystem sftp /data/data/com.termux/files/usr/libexec/sftp-server

What is the expected behavior?

No response

System information

Termux Variables:
TERMUX_API_VERSION=0.50.1
TERMUX_APK_RELEASE=F_DROID
TERMUX_APP_PACKAGE_MANAGER=apt
TERMUX_APP_PID=4825
TERMUX_IS_DEBUGGABLE_BUILD=0
TERMUX_MAIN_PACKAGE_FORMAT=debian
TERMUX_VERSION=0.118.0
TERMUX__USER_ID=0
Packages CPU architecture:
aarch64
Subscribed repositories:
# sources.list
deb https://mirrors.sahilister.in/termux/termux-main stable main
# root-repo (sources.list.d/root.list)
deb https://mirrors.sahilister.in/termux/termux-root root stable
Updatable packages:
All packages up to date
termux-tools version:
1.42.4
Android version:
14
Kernel build information:
Linux localhost 5.15.153-android14-11-gb1050d6a1731 #1 SMP PREEMPT Wed Jun 19 13:09:59 UTC 2024 aarch64 Android
Device manufacturer:
Google
Device model:
Pixel 8
LD Variables:
LD_LIBRARY_PATH=
LD_PRELOAD=/data/data/com.termux/files/usr/lib/libtermux-exec.so
Installed termux plugins:
com.termux.api versionCode:51
com.termux.boot versionCode:7
com.termux.tasker versionCode:5
licy183 commented 3 months ago

TL;DR It is not recommended to start sshd as the root user, as this will cause potential problems.

When there is a connection, sshd will start a child process sshd-session. If sshd is not started as the root user, the child process will inherit the status (uid/gid/selinux context and etc.) from the parent process; otherwise, sshd will call set(e)uid, set(e)gid, initgroups and a series of selinux function calls to set the child process to the same status as the logged-in user.

However, the situation is very different on Termux.

  1. Termux is almost considered to be a single user. The provided login username will be ignored, so the logged-in user should always be com.termux (unless the requested username is root).
  2. Android's initgroups implementation will only set AID_APP_TERMUX (1xxxx) to the child process, and will not set other group ids that com.termux has, such as AID_INET (3003), AID_EVERYBODY (9999), AID_SHARED_GID_TERMUX (5xxxx) and so on, to the child process, which will at least cause network connection issues.
  3. Termux is designed to execute commands as a normal user AID_APP_TERMUX, so selinux support is not enabled when building sshd, which will result in the child process not having the security context of com.termux, causing many programs not working properly.

I think it is better to prohibit sshd from starting with root user. When the user really needs to log in as the root user, the user should start sshd with a non-root user, log in to Termux as a normal user, and use su or sudo to switch the user to root.

CC: @agnostic-apollo @sylirre @twaik @truboxl

twaik commented 3 months ago

I agree. Starting sshd as root should be disabled.

andreas1288 commented 3 months ago

For me the main use case for running sshd as root is the export of the filesystem for an sshfs client. Without root the access is very limited, outside from termux of course. Could it be an option to run only the sshfs subsystem as root?

agnostic-apollo commented 3 months ago

I only run ssh client as root, and not the sshd server, so don't have experience with its issues.

  1. will not set other group ids that com.termux has, such as AID_INET (3003), AID_EVERYBODY (9999), AID_SHARED_GID_TERMUX (5xxxx) and so on, to the child process, which will at least cause network connection issues.

Root user processes started by Magisk and AOSP provided su, etc don't have users set either, as root user already has full access and doesn't need any users in its groups. Internet works fine.

  1. which will result in the child process not having the security context of com.termux, causing many programs not working properly.

That would also be a problem if users run commands directly with su/sudo su too instead of through sshd.

For Termux, if sshd is run with root user, it should act just the same as if running with termux user. The uid:gid, groups and selinux context should all be inherited from parent process, whatever they are for the parent root user process. Ideally, uid:gid would be root:root, groups won't be set, and selinux context would be u:r:magisk:s0 or u:r:su:s0. I haven't looked at sshd sources, but I assume they can be automatically inherited as you said.

Since normally, sshd won't be run as root, so incoming clients would only get termux user access, so not a security issue for them. If someone is rooted, and runs sshd with root, they should be well aware of the risks. A check in auth.c.patch could be added where if current process is root owned, then root user must be passed for authentication. as well.

licy183 commented 3 months ago

Root user processes started by Magisk and AOSP provided su, etc don't have users set either, as root user already has full access and doesn't need any users in its groups. Internet works fine.

There will indeed be no network connection problems under the root user, but if a program starting as root user executes set(e)uid, set(e)gid and initgroups to the uid of com.termux, initgroups will not automatically set INET group to this program so network issues will occur.

Since normally, sshd won't be run as root, so incoming clients would only get termux user access, so not a security issue for them. If someone is rooted, and runs sshd with root, they should be well aware of the risks. A check in auth.c.patch could be added where if current process is root owned, then root user must be passed for authentication. as well.

I think this is more reasonable than disabling sshd from starting as root. I'll submit a patch to implement it.

agnostic-apollo commented 3 months ago

but if a program starting as root user executes set(e)uid, set(e)gid and initgroups to the uid of com.termux, initgroups will not automatically set INET group to this program so network issues will occur.

Oh, that transition would be a far more complex issue than just groups and would require patching sepolicies. It is certainly doable, I have a local implementation but would be out of scope. If a user is running sshd as root, then they should run all processes as root too, but if they really want to run as termux user, they can send a RUN_COMMAND intent from the root process and intent commands would run as the normal termux user when Temux app starts a new shell for them by forking from the main app process itself.

https://android.stackexchange.com/a/217104

I think this is more reasonable than disabling sshd from starting as root. I'll submit a patch to implement it.

Great. Thanks.

andreas1288 commented 3 months ago

I have been running sshd as root for a long time, most recently on Android 14 with GrapheneOS, with a quite recent patch level. Until I updated from openssh_9.7p1_aarch64.deb to openssh_9.8p1-2_aarch64.deb, I never encountered any problems. It is unclear to me why this change is causing such issues. Was the update from openssh 9.7 to 9.8 so significant? Or is this in preparation for new Android versions? The solution doesn't have to be perfect. If some edge cases result in a program crash, it is totally acceptable in such an environment. However, due to this regression, I really don't want to stay on the old version for too long. I am also running another sshd under the "normal" Termux user on a different port.

Could you please ensure that sshd continues to work under root?

Thank you very much for your assistance.

TomJo2000 commented 3 months ago

Was the update from openssh 9.7 to 9.8 so significant? Or is this in preparation for new Android versions?

It was significant in so far as that it fixed a recoccuring security vulnerability dubbed "Regresshion" reoccuring as far back as openssh-8.5p1. Which can allow unauthenticated remote code execution. Android/Termux isn't currently known to be vulnerable to the CVE, but the suggested remediation is still to update OpenSSH.

Grimler91 commented 3 months ago

Probably the changes that are relevant to issues with "sshd as root" is the work to "separate sshd into a listener and a session binary", which removed the use_privsep option that we were previously setting to OFF

licy183 commented 3 months ago

Please test the debs in https://github.com/termux/termux-packages/actions/runs/9829064472/job/27133707099. Thanks!

TomJo2000 commented 3 months ago

(This is a pre-written, saved reply.) If you want to test this PR please download the appropriate DEB package(s) from the build artifacts of the associated PR's latest CI run. Screenshot_20240619_232413

After downloading the build artifact, make sure to unzip and un-tar it.

Detailed instructions, if needed.

```bash # finding out what architecture you need # architecture is just below the TERMUX_VERSION termux-info # e.g. # [...] # TERMUX_MAIN_PACKAGE_FORMAT=debian # TERMUX_VERSION=0.118.0 # TERMUX__USER_ID=0 # Packages CPU architecture: # aarch64 # [...] # ======================= # make sure `unzip` and `tar` are installed using pkg install unzip tar # unzip the artifact (if you have a different architecture this might be arm, i686 or x86_64 instead) unzip debs-aarch64-*.zip # untar the artifact tar xf debs-aarch64-*.tar # You should now have a debs/ directory in your current working directory # Install the packages from the local source using pkg install -- ./debs/*.deb # to clean up, you can remove the debs/ directory, .tar file and .zip file rm -rfi debs debs-aarch64-*.zip debs-aarch64-*.tar ```

Grimler91 commented 3 months ago

If you want to test this PR please download the appropriate DEB package(s)

If users have github-cli (gh) set up they can also download the deb tar with something like gh run download 9829064472 --pattern "debs-$(dpkg --print-architecture)-*" (where 9829064472 is the job id same as in the url: https://github.com/termux/termux-packages/actions/runs/9829064472).

Maybe we should create a termux-devel package with this type of wrapper script, and for example a script for simplifying rebasing and merging PRs from the command line.

andreas1288 commented 3 months ago

Everything works perfect. Login as root, exporting fs with sshfs under root. Files can be uploaded and downloaded correctly. uids and gids seams to be right. Thanks a lot! That was a nice birthday present, sorry party yesterday...