├── .github └── workflows │ └── github_release_build.yml ├── .gitignore ├── LICENSE ├── Makefile ├── README.md ├── licenses └── agnostic-apollo__sudo__MIT.md ├── packaging └── debian │ └── sudo-package.json.in ├── site └── pages │ └── en │ └── projects │ ├── docs │ ├── developer │ │ ├── build │ │ │ └── index.md │ │ ├── contribute │ │ │ └── index.md │ │ ├── guides │ │ │ ├── index.md │ │ │ └── su-sub-process-communication │ │ │ │ └── index.md │ │ ├── index.md │ │ └── test │ │ │ └── index.md │ ├── index.md │ ├── install │ │ └── index.md │ └── usage │ │ └── index.md │ ├── index.md │ └── releases │ ├── 0 │ ├── v0.1.0.md │ └── v0.2.0.md │ ├── 1 │ ├── v1.0.0.md │ ├── v1.1.0.md │ └── v1.2.0.md │ └── index.md ├── sudo ├── sudo.config ├── templates └── plugin_hosts │ └── tasker │ ├── Termux_RUN_COMMAND_Intent_Sudo_Templates.tsk.md │ ├── Termux_RUN_COMMAND_Intent_Sudo_Templates.tsk.sha256sums │ ├── Termux_RUN_COMMAND_Intent_Sudo_Templates.tsk.xml │ ├── Termux_Tasker_Plugin_Sudo_Templates.tsk.md │ ├── Termux_Tasker_Plugin_Sudo_Templates.tsk.sha256sums │ └── Termux_Tasker_Plugin_Sudo_Templates.tsk.xml └── tests └── sudo_tests /.github/workflows/github_release_build.yml: -------------------------------------------------------------------------------- 1 | name: GitHub Release Build 2 | 3 | on: 4 | release: 5 | types: 6 | - published 7 | 8 | jobs: 9 | build: 10 | runs-on: ubuntu-latest 11 | env: 12 | GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} 13 | steps: 14 | - name: Clone repository 15 | uses: actions/checkout@v4 16 | with: 17 | ref: ${{ env.GITHUB_REF }} 18 | 19 | - name: Build and upload files to release 20 | shell: bash {0} 21 | run: | 22 | exit_on_error() { 23 | echo "$1" 24 | echo "Deleting '$RELEASE_VERSION_NAME' release and '$GITHUB_REF' tag" 25 | gh release delete --cleanup-tag --yes "$RELEASE_VERSION_NAME" 26 | git push --delete origin "$GITHUB_REF" 27 | exit 1 28 | } 29 | 30 | echo "Setting vars" 31 | RELEASE_VERSION_NAME="${GITHUB_REF/refs\/tags\//}" 32 | if ! printf "%s" "${RELEASE_VERSION_NAME/v/}" | grep -qP '^(0|[1-9]\d*)\.(0|[1-9]\d*)\.(0|[1-9]\d*)(?:-((?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*)(?:\.(?:0|[1-9]\d*|\d*[a-zA-Z-][0-9a-zA-Z-]*))*))?(?:\+([0-9a-zA-Z-]+(?:\.[0-9a-zA-Z-]+)*))?$'; then 33 | exit_on_error "The release version '${RELEASE_VERSION_NAME/v/}' is not a valid version as per semantic version '2.0.0' spec in the format 'major.minor.patch(-prerelease)(+buildmetadata)'. https://semver.org/spec/v2.0.0.html." 34 | fi 35 | 36 | echo "Validating sudo file for '$RELEASE_VERSION_NAME' release" 37 | if ! test -f "sudo"; then 38 | files_found="$(ls -a)" 39 | exit_on_error "Failed to find sudo file. Files found: "$'\n'"$files_found" 40 | fi 41 | 42 | echo "Generating checksums-sha256.txt file" 43 | if ! (sha256sum "sudo" > checksums-sha256.txt); then 44 | exit_on_error "Generate checksums-sha256.txt file failed for '$RELEASE_VERSION_NAME' release." 45 | fi 46 | echo "checksums-sha256.txt:"$'\n```\n'"$(cat checksums-sha256.txt)"$'\n```' 47 | 48 | echo "Uploading files to release" 49 | if ! gh release upload "$RELEASE_VERSION_NAME" \ 50 | "sudo" \ 51 | "checksums-sha256.txt" \ 52 | ; then 53 | exit_on_error "Upload files to release failed for '$RELEASE_VERSION_NAME' release." 54 | fi 55 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | /build/install/* 2 | /build/output/* 3 | *.deb 4 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | Format: https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ 2 | 3 | 4 | 5 | Files: 6 | * 7 | Comment: 8 | The `sudo` repository is released under the `MIT` license, unless specified 9 | differently in a file/directory or in any additional `Files` sections below. 10 | License: [MIT](licenses/agnostic-apollo__sudo__MIT.md) 11 | -------------------------------------------------------------------------------- /Makefile: -------------------------------------------------------------------------------- 1 | export SUDO_PKG__VERSION := 1.2.0 2 | export SUDO_PKG__ARCH 3 | export SUDO__INSTALL_PREFIX 4 | 5 | export TERMUX__NAME := Termux# Default value: `Termux` 6 | export TERMUX__LNAME := termux# Default value: `termux` 7 | 8 | export TERMUX_APP__NAME := Termux# Default value: `Termux` 9 | export TERMUX_APP__PACKAGE_NAME := com.termux# Default value: `com.termux` 10 | export TERMUX_APP__DATA_DIR := /data/data/$(TERMUX_APP__PACKAGE_NAME)# Default value: `/data/data/com.termux` 11 | 12 | export TERMUX__ROOTFS := $(TERMUX_APP__DATA_DIR)/files# Default value: `/data/data/com.termux/files` 13 | export TERMUX__HOME := $(TERMUX__ROOTFS)/home# Default value: `/data/data/com.termux/files/home` 14 | export TERMUX__PREFIX := $(TERMUX__ROOTFS)/usr# Default value: `/data/data/com.termux/files/usr` 15 | 16 | export TERMUX_ENV__S_ROOT := TERMUX_# Default value: `TERMUX_` 17 | export TERMUX_ENV__SS_TERMUX := _# Default value: `_` 18 | export TERMUX_ENV__S_TERMUX := $(TERMUX_ENV__S_ROOT)$(TERMUX_ENV__SS_TERMUX)# Default value: `TERMUX__` 19 | export TERMUX_ENV__SS_TERMUX_APP := APP__# Default value: `APP__` 20 | export TERMUX_ENV__S_TERMUX_APP := $(TERMUX_ENV__S_ROOT)$(TERMUX_ENV__SS_TERMUX_APP)# Default value: `TERMUX_APP__` 21 | 22 | 23 | # If architecture not set, find it for the compiler based on which 24 | # predefined architecture macro is defined. The `shell` function 25 | # replaces newlines with a space and a literal space cannot be entered 26 | # in a makefile as its used as a splitter, hence $(SPACE) variable is 27 | # created and used for matching. 28 | ifeq ($(SUDO_PKG__ARCH),) 29 | export override PREDEFINED_MACROS := $(shell $(CC) -x c /dev/null -dM -E) 30 | override EMPTY := 31 | override SPACE := $(EMPTY) $(EMPTY) 32 | ifneq (,$(findstring $(SPACE)#define __i686__ 1$(SPACE),$(SPACE)$(PREDEFINED_MACROS)$(SPACE))) 33 | override SUDO_PKG__ARCH := i686 34 | else ifneq (,$(findstring $(SPACE)#define __x86_64__ 1$(SPACE),$(SPACE)$(PREDEFINED_MACROS)$(SPACE))) 35 | override SUDO_PKG__ARCH := x86_64 36 | else ifneq (,$(findstring $(SPACE)#define __aarch64__ 1$(SPACE),$(SPACE)$(PREDEFINED_MACROS)$(SPACE))) 37 | override SUDO_PKG__ARCH := aarch64 38 | else ifneq (,$(findstring $(SPACE)#define __arm__ 1$(SPACE),$(SPACE)$(PREDEFINED_MACROS)$(SPACE))) 39 | override SUDO_PKG__ARCH := arm 40 | else ifneq (,$(findstring $(SPACE)#define __riscv 1$(SPACE),$(SPACE)$(PREDEFINED_MACROS)$(SPACE))) 41 | override SUDO_PKG__ARCH := riscv64 42 | else 43 | $(error Unsupported package arch) 44 | endif 45 | endif 46 | 47 | 48 | 49 | export override BUILD_DIR := build# Default value: `build` 50 | 51 | export override BUILD_OUTPUT_DIR := $(BUILD_DIR)/output# Default value: `build/output` 52 | 53 | export override PREFIX_BUILD_OUTPUT_DIR := $(BUILD_OUTPUT_DIR)/usr# Default value: `build/output/usr` 54 | export override BIN_BUILD_OUTPUT_DIR := $(PREFIX_BUILD_OUTPUT_DIR)/bin# Default value: `build/output/usr/bin` 55 | export override LIBEXEC_BUILD_OUTPUT_DIR := $(PREFIX_BUILD_OUTPUT_DIR)/libexec# Default value: `build/output/usr/libexec` 56 | export override TESTS_BUILD_OUTPUT_DIR := $(LIBEXEC_BUILD_OUTPUT_DIR)/installed-tests/sudo# Default value: `build/output/usr/libexec/installed-tests/sudo` 57 | export override SHARE_BUILD_OUTPUT_DIR := $(PREFIX_BUILD_OUTPUT_DIR)/share# Default value: `build/output/usr/share` 58 | export override EXAMPLES_BUILD_OUTPUT_DIR := $(SHARE_BUILD_OUTPUT_DIR)/doc/sudo/examples# Default value: `build/output/usr/share/doc/sudo/examples` 59 | 60 | export override PACKAGING_BUILD_OUTPUT_DIR := $(BUILD_OUTPUT_DIR)/packaging# Default value: `build/output/packaging` 61 | export override DEBIAN_PACKAGING_BUILD_OUTPUT_DIR := $(PACKAGING_BUILD_OUTPUT_DIR)/debian# Default value: `build/output/packaging/debian` 62 | 63 | 64 | 65 | export override BUILD_INSTALL_DIR := $(BUILD_DIR)/install# Default value: `build/install` 66 | export override PREFIX_BUILD_INSTALL_DIR := $(BUILD_INSTALL_DIR)/usr# Default value: `build/install/usr` 67 | 68 | ifeq ($(SUDO__INSTALL_PREFIX),) 69 | ifeq ($(DESTDIR)$(PREFIX),) 70 | override SUDO__INSTALL_PREFIX := $(TERMUX__PREFIX) 71 | else 72 | override SUDO__INSTALL_PREFIX := $(DESTDIR)$(PREFIX) 73 | endif 74 | endif 75 | export SUDO__INSTALL_PREFIX 76 | 77 | 78 | 79 | export override TERMUX__CONSTANTS__SED_ARGS := \ 80 | -e "s%[@]SUDO_PKG__VERSION[@]%$(SUDO_PKG__VERSION)%g" \ 81 | -e "s%[@]SUDO_PKG__ARCH[@]%$(SUDO_PKG__ARCH)%g" \ 82 | -e "s%[@]TERMUX__LNAME[@]%$(TERMUX__LNAME)%g" \ 83 | -e "s%[@]TERMUX_APP__NAME[@]%$(TERMUX_APP__NAME)%g" \ 84 | -e "s%[@]TERMUX_APP__PACKAGE_NAME[@]%$(TERMUX_APP__PACKAGE_NAME)%g" \ 85 | -e "s%[@]TERMUX__ROOTFS[@]%$(TERMUX__ROOTFS)%g" \ 86 | -e "s%[@]TERMUX__HOME[@]%$(TERMUX__HOME)%g" \ 87 | -e "s%[@]TERMUX__PREFIX[@]%$(TERMUX__PREFIX)%g" \ 88 | -e "s%[@]TERMUX_ENV__S_ROOT[@]%$(TERMUX_ENV__S_ROOT)%g" \ 89 | -e "s%[@]TERMUX_ENV__SS_TERMUX[@]%$(TERMUX_ENV__SS_TERMUX)%g" \ 90 | -e "s%[@]TERMUX_ENV__S_TERMUX[@]%$(TERMUX_ENV__S_TERMUX)%g" \ 91 | -e "s%[@]TERMUX_ENV__SS_TERMUX_APP[@]%$(TERMUX_ENV__SS_TERMUX_APP)%g" 92 | 93 | define replace-termux-constants 94 | sed $(TERMUX__CONSTANTS__SED_ARGS) "$1.in" > "$2/$$(basename "$1")" 95 | endef 96 | 97 | 98 | 99 | # - https://www.gnu.org/software/make/manual/html_node/Parallel-Disable.html 100 | .NOTPARALLEL: 101 | 102 | all: | pre-build 103 | @mkdir -p $(BIN_BUILD_OUTPUT_DIR) 104 | sed $(TERMUX__CONSTANTS__SED_ARGS) "sudo" > "$(BIN_BUILD_OUTPUT_DIR)/sudo" 105 | chmod 700 "$(BIN_BUILD_OUTPUT_DIR)/sudo" 106 | 107 | 108 | @printf "\nsudo: %s\n" "Building sudo.config" 109 | @mkdir -p $(EXAMPLES_BUILD_OUTPUT_DIR) 110 | sed $(TERMUX__CONSTANTS__SED_ARGS) "sudo.config" > "$(EXAMPLES_BUILD_OUTPUT_DIR)/sudo.config" 111 | 112 | 113 | @printf "\nsudo: %s\n" "Building sudo_tests" 114 | @mkdir -p $(TESTS_BUILD_OUTPUT_DIR) 115 | sed $(TERMUX__CONSTANTS__SED_ARGS) "tests/sudo_tests" > "$(TESTS_BUILD_OUTPUT_DIR)/sudo_tests" 116 | chmod 700 "$(TESTS_BUILD_OUTPUT_DIR)/sudo_tests" 117 | 118 | 119 | @printf "\nsudo: %s\n" "Building packaging/debian/*" 120 | @mkdir -p $(DEBIAN_PACKAGING_BUILD_OUTPUT_DIR) 121 | find packaging/debian -mindepth 1 -maxdepth 1 -type f -name "*.in" -exec sh -c \ 122 | 'sed $(TERMUX__CONSTANTS__SED_ARGS) "$$1" > $(DEBIAN_PACKAGING_BUILD_OUTPUT_DIR)/"$$(basename "$$1" | sed "s/\.in$$//")"' sh "{}" \; 123 | find $(DEBIAN_PACKAGING_BUILD_OUTPUT_DIR) -mindepth 1 -maxdepth 1 -type f \ 124 | -regextype posix-extended -regex "^.*/(postinst|postrm|preinst|prerm)$$" \ 125 | -exec chmod 700 {} \; 126 | find $(DEBIAN_PACKAGING_BUILD_OUTPUT_DIR) -mindepth 1 -maxdepth 1 -type f \ 127 | -regextype posix-extended -regex "^.*/(config|conffiles|templates|triggers|clilibs|fortran_mod|runit|shlibs|starlibs|symbols)$$" \ 128 | -exec chmod 600 {} \; 129 | 130 | 131 | @printf "\nsudo: %s\n\n" "Build sudo successful" 132 | 133 | 134 | 135 | pre-build: | clean 136 | @printf "sudo: %s\n" "Building sudo" 137 | @mkdir -p $(BUILD_OUTPUT_DIR) 138 | 139 | clean: 140 | rm -rf $(BUILD_OUTPUT_DIR) 141 | 142 | install: 143 | @printf "sudo: %s\n" "Installing sudo in $(SUDO__INSTALL_PREFIX)" 144 | 145 | install -d $(SUDO__INSTALL_PREFIX)/bin 146 | cp -a $(BIN_BUILD_OUTPUT_DIR)/sudo $(SUDO__INSTALL_PREFIX)/bin/ 147 | 148 | 149 | install -d $(SUDO__INSTALL_PREFIX)/share/doc/sudo/examples 150 | cp -a $(EXAMPLES_BUILD_OUTPUT_DIR)/sudo.config $(SUDO__INSTALL_PREFIX)/share/doc/sudo/examples/ 151 | 152 | 153 | install -d $(SUDO__INSTALL_PREFIX)/libexec/installed-tests/sudo 154 | cp -a $(TESTS_BUILD_OUTPUT_DIR)/sudo_tests $(SUDO__INSTALL_PREFIX)/libexec/installed-tests/sudo/ 155 | 156 | @printf "\nsudo: %s\n\n" "Install sudo successful" 157 | 158 | uninstall: 159 | @printf "sudo: %s\n" "Uninstalling sudo from $(SUDO__INSTALL_PREFIX)" 160 | 161 | rm -f $(SUDO__INSTALL_PREFIX)/bin/sudo 162 | rm -f $(SUDO__INSTALL_PREFIX)/share/doc/sudo/examples/sudo.config 163 | rm -f $(SUDO__INSTALL_PREFIX)/libexec/installed-tests/sudo/sudo_tests 164 | 165 | @printf "\nsudo: %s\n\n" "Uninstall sudo successful" 166 | 167 | 168 | 169 | packaging-debian-build: all 170 | termux-create-package $(DEBIAN_PACKAGING_BUILD_OUTPUT_DIR)/sudo-package.json 171 | 172 | 173 | 174 | .PHONY: all pre-build clean install uninstall packaging-debian-build 175 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # sudo 2 | 3 | [`sudo`](https://github.com/agnostic-apollo/sudo) stands for *superuser do*. It is a wrapper script to execute commands as the `root (superuser)` user in the [Termux](https://github.com/termux/termux-app) app, like to drop to an interactive shell for any of the supported shells, or to execute shell script files or their text passed as an argument. 4 | 5 | ### Contents 6 | 7 | - [Project](#project) 8 | 9 | --- 10 | 11 |   12 | 13 | 14 | 15 | 16 | 17 | ## Project 18 | 19 | **Check the `sudo` project info [here](site/pages/en/projects/index.md), including `docs` and `releases` info.** 20 | 21 | --- 22 | 23 |   24 | -------------------------------------------------------------------------------- /licenses/agnostic-apollo__sudo__MIT.md: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2019, agnostic-apollo, auth={ type=`scrypt-kdf`, key=`xY%I5l>AxK+n@o.]cjUp8&s2.NyFBr=&]PoMxQ5B-W(T)e+d(lDT*I7u=jjFK-UA-IA-BA` } 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | 23 | - https://opensource.org/licenses/MIT 24 | -------------------------------------------------------------------------------- /packaging/debian/sudo-package.json.in: -------------------------------------------------------------------------------- 1 | { 2 | "control": { 3 | "Package": "sudo", 4 | "Version": "@SUDO_PKG__VERSION@", 5 | "Architecture": "@SUDO_PKG__ARCH@", 6 | "Maintainer": "@agnostic-apollo", 7 | "Depends": "bash", 8 | "Conflicts": "tsu", 9 | "Replaces": "tsu", 10 | "Homepage": "https://github.com/agnostic-apollo/sudo", 11 | "Description": "A wrapper script to execute commands as the 'root (superuser)' user in the @TERMUX_APP__NAME@ app, like to drop to an interactive shell for any of the supported shells, or to execute shell script files or their text passed as an argument." 12 | }, 13 | 14 | "installation_prefix": "@TERMUX__PREFIX@", 15 | "control_files_dir": "build/output/packaging/debian", 16 | 17 | "data_files": { 18 | "": { 19 | "source": "build/output/usr", 20 | "source_recurse": true 21 | } 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /site/pages/en/projects/docs/developer/build/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/docs/@ARK_DOC__VERSION@/developer/build/index.md" 3 | --- 4 | 5 | # sudo Build Docs 6 | 7 | 8 | 9 | The [`sudo`](https://github.com/agnostic-apollo/sudo) build instructions are available below. For install instructions, check [`install`](../../install/index.md) docs. 10 | 11 | ### Contents 12 | 13 | - [Build Methods](#build-methods) 14 | 15 | --- 16 | 17 |   18 | 19 | 20 | 21 | 22 | 23 | ## Build Methods 24 | 25 | The `sudo` package provided by Termux is built from the [`agnostic-apollo/sudo`](https://github.com/agnostic-apollo/sudo) repository. It can be built with the following methods. 26 | 27 | - [Termux Packages Build Infrastructure](#termux-packages-build-infrastructure) 28 | - [On Device With `make`](#on-device-with-make) 29 | 30 | **The [Termux Packages Build Infrastructure](#termux-packages-build-infrastructure) is the recommended way to build `sudo`.** If the `sudo` package is built with the [Termux Packages Infrastructure](#termux-packages-build-infrastructure), then the Termux variable values in the `Makefile` are dynamically set to the values defined in the [`properties.sh`] file of the build infrastructure by passing them to `make` via the `$TERMUX_PKG_EXTRA_MAKE_ARGS` variable set in the [`packages/sudo/build.sh`] file. If `sudo` is built with `make` instead, then the hardcoded fallback/default Termux variable values in the `Makefile` will get used during build time, which may affect or break `sudo` at runtime if current app/environment is different from the Termux default one (`TERMUX_APP__PACKAGE_NAME=com.termux` and `TERMUX__ROOTFS=/data/data/com.termux/files`). However, if `make` must be used for some reason, and building for a different app/environment than the Termux default, like for a Termux fork or alternate package name/rootfs, then manually update the hardcoded values in the `Makefile` or manually pass the alternate values to the `make` command. 31 | 32 | ##   33 | 34 |   35 | 36 | 37 | 38 | ### Termux Packages Infrastructure 39 | 40 | To build the `sudo` package with the [`termux-packages`](https://github.com/termux/termux-packages) build infrastructure, the provided [`build-package.sh`](https://github.com/termux/termux-packages/blob/master/build-package.sh) script can be used. Check the [Build environment](https://github.com/termux/termux-packages/wiki/Build-environment) and [Building packages](https://github.com/termux/termux-packages/wiki/Building-packages) docs for how to build packages. 41 | 42 | #### Default Sources 43 | 44 | To build the `sudo` package from its default repository release tag or git branch sources that are used for building the package provided in Termux repositories, just clone the `termux-packages` repository and build. 45 | 46 | ```shell 47 | # Clone `termux-packages` repo and switch current working directory to it. 48 | git clone https://github.com/termux/termux-packages.git 49 | cd termux-packages 50 | 51 | # (OPTIONAL) Run termux-packages docker container if running off-device. 52 | ./scripts/run-docker.sh 53 | 54 | # Force build package and download dependencies from Termux packages repositories. 55 | ./build-package.sh -f -I sudo 56 | ``` 57 | 58 | #### Local Sources 59 | 60 | To build the `sudo` package from its local sources or a pull request branch, clone the `termux-packages` repository, clone/create the `sudo` repository locally, make required changes to the [`packages/sudo/build.sh`] file to update the source url and then build. 61 | 62 | Check [Build Local Package](https://github.com/termux/termux-packages/wiki/Building-packages#build-local-package) and [Package Build Local Source URLs](https://github.com/termux/termux-packages/wiki/Creating-new-package#package-build-local-source-urls) docs for more info on how to building packages from local sources.* 63 | 64 | ```shell 65 | # Clone `termux-packages` repo and switch current working directory to it. 66 | git clone https://github.com/termux/termux-packages.git 67 | cd termux-packages 68 | 69 | # Update `$TERMUX_PKG_SRCURL` variable in `packages/sudo/build.sh`. 70 | # We use `file:///path/to/source/dir` format for the local source URL. 71 | TERMUX_PKG_SRCURL=file:///home/builder/termux-packages/sources/sudo 72 | TERMUX_PKG_SHA256=SKIP_CHECKSUM 73 | 74 | # Clone/copy `sudo` repo at `termux-packages/sources/sudo` 75 | # directory. Make sure current working directory is root directory of 76 | # termux-packages repo when cloning. 77 | git clone https://github.com/agnostic-apollo/sudo.git sources/sudo 78 | 79 | # (OPTIONAL) Manually switch to different (pull) branch that exists on 80 | # origin if required, or to the one defined in $TERMUX_PKG_GIT_BRANCH 81 | # variable of build.sh file, as it will not be automatically checked out. 82 | # By default, the repo default/current branch that's cloned 83 | # will get built, which is usually `master` or `main`. 84 | # Whatever is the current state of the source directory will 85 | # be built as is, including any uncommitted changes to current 86 | # branch. 87 | (cd sources/sudo; git checkout ) 88 | 89 | # (OPTIONAL) Run termux-packages docker container if running off-device. 90 | ./scripts/run-docker.sh 91 | 92 | # Force build package and download dependencies from Termux packages repositories. 93 | ./build-package.sh -f -I sudo 94 | ``` 95 | 96 | ##   97 | 98 |   99 | 100 | 101 | 102 | ### On Device With `make` 103 | 104 | To build `sudo` package on the device inside the Termux app with [`make`](https://www.gnu.org/software/make), check below. Do not use a PC to build the package as PC architecture may be different from target device architecture and the `clang` compiler wouldn't have been patched like Termux provided one is so that built packages are compatible with Termux, like patches done for `DT_RUNPATH`. 105 | 106 | ```shell 107 | # Install dependencies. 108 | pkg install clang git make termux-create-package 109 | 110 | # Clone/copy `sudo` repo at `sudo` directory and switch current 111 | # working directory to it. 112 | git clone https://github.com/agnostic-apollo/sudo.git sudo 113 | cd sudo 114 | 115 | # Whatever is the current state of the `sudo` directory will be built. 116 | # If required, manually switch to different (pull) branch that exists on origin. 117 | git checkout 118 | 119 | # Remove any existing deb files in current directory. 120 | rm -f sudo_*.deb 121 | 122 | # Build deb file for the architecture of the host device/clang compiler. 123 | make packaging-debian-build 124 | 125 | # Install. 126 | # We use shell * glob expansion to automatically select the deb file 127 | # regardless of `__.deb` suffix, that's why existing 128 | # deb files were deleted earlier in case any existed with the wrong version. 129 | dpkg -i sudo_*.deb 130 | ``` 131 | 132 | --- 133 | 134 |   135 | 136 | 137 | 138 | 139 | 140 | [`packages/sudo/build.sh`]: https://github.com/termux/termux-packages/blob/master/packages/sudo/build.sh 141 | [`properties.sh`]: https://github.com/termux/termux-packages/blob/master/scripts/properties.sh 142 | -------------------------------------------------------------------------------- /site/pages/en/projects/docs/developer/contribute/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/docs/@ARK_DOC__VERSION@/developer/contribute/index.md" 3 | --- 4 | 5 | # sudo Contribute Docs 6 | 7 | 8 | 9 | These docs are meant for you if you want to contribute to the [`agnostic-apollo/sudo`](https://github.com/agnostic-apollo/sudo) repository. 10 | 11 | ### Contents 12 | 13 | - [Commit Messages Guidelines](#commit-messages-guidelines) 14 | 15 | --- 16 | 17 |   18 | 19 | 20 | 21 | 22 | 23 | ## Commit Messages Guidelines 24 | 25 | Commit messages **must** use the [Conventional Commits](https://www.conventionalcommits.org) spec so that changelogs can be automatically generated when [releases](../../../releases/index.md) are made as per the [Keep a Changelog](https://github.com/olivierlacan/keep-a-changelog) spec by the [`create-conventional-changelog`](https://github.com/termux/create-conventional-changelog) script, check its repository for further details on the spec. 26 | 27 | **The first letter for `type` and `description` must be capital and description should be in the present tense.** The space after the colon `:` is necessary. For a breaking change, add an exclamation mark `!` before the colon `:` as an indicator, and it will also cause the change to be automatically highlighted in the changelog. 28 | 29 | ``` 30 | [optional scope]: 31 | 32 | [optional body] 33 | 34 | [optional footer(s)] 35 | ``` 36 | 37 | **Only the `types` listed below must be used exactly as they are used in the changelog headings.** For example, `Added: Add foo`, `Added|Fixed: Add foo and fix bar`, `Changed!: Change baz as a breaking change`, etc. You can optionally add a scope as well, like `Fixed(docs): Fix some bug`. **Do not use anything else as type, like `add` instead of `Added`, or `chore`, etc.** 38 | 39 | - **Added** for new additions or features. 40 | - **Changed** for changes in existing functionality. 41 | - **Deprecated** for soon-to-be removed features. 42 | - **Fixed** for any bug fixes. 43 | - **Removed** for now removed features. 44 | - **Reverted** for changes that were reverted. 45 | - **Patched** for patches done for specific builds. 46 | - **Security** in case of vulnerabilities. 47 | - **Release** for when a new release is made. 48 | 49 | --- 50 | 51 |   52 | -------------------------------------------------------------------------------- /site/pages/en/projects/docs/developer/guides/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/docs/@ARK_DOC__VERSION@/developer/guides/index.md" 3 | --- 4 | 5 | # sudo Developer Guides 6 | 7 | 8 | 9 | These guides are meant for the developers, maintainers and contributors of the [`agnostic-apollo/sudo`](https://github.com/agnostic-apollo/sudo) repository and its forks. 10 | 11 | ### Contents 12 | 13 | - [`su` Sub Process Communication](su-sub-process-communication/index.md) 14 | 15 | --- 16 | 17 |   18 | -------------------------------------------------------------------------------- /site/pages/en/projects/docs/developer/guides/su-sub-process-communication/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/docs/@ARK_DOC__VERSION@/developer/guides/su-sub-process-communication/index.md" 3 | --- 4 | 5 | # `su` Sub Process Communication Guide 6 | 7 | 8 | 9 | The following guide details how the communication between `su` sub processes and the main `sudo` script process happens and related issues. 10 | 11 | ### Contents 12 | 13 | - [Send Data To `su` process](#send-data-to-su-process) 14 | - [Receive Data From `su` process](#receive-data-from-su-process) 15 | - [Send And Receive Data From `su` process](#send-and-receive-data-from-su-process) 16 | - [Additional Rationale](#additional-rationale) 17 | 18 | --- 19 | 20 |   21 | 22 | 23 | 24 | 25 | 26 | # Send Data To `su` process 27 | 28 | Data like `sudo -s ` (`$SUDO_SCRIPT_COMMAND_TO_RUN`) cannot be passed to the bash shell inside `su` using process substitution directly since the `self` in `proc/self/fd/#` passed by process substitution is for the `sudo` script process and not for the `bash` process inside `su`. So when bash shell inside `su` tries to read from it, then there will be errors like `/proc/self/fd/63: No such file or directory`. 29 | 30 | ```shell 31 | /sbin/su --shell="${TERMUX__PREFIX:-$PREFIX}/bin/bash" --preserve-environment -c "bash --noprofile --norc" <(echo 'echo 1')` 32 | bash: /proc/self/fd/63: No such file or directory 33 | ``` 34 | 35 | Hence, we manually create a file descriptor and pass its path to `su` or to be more specific to the `bash` shell for the `path` and `script` commands. The method that is used for passing data to `su` using file descriptors in `sudo` script is the following. 36 | 37 | 1. Get an unsed file descriptor for the current `sudo` script process and `fd` path by calling `sudo_get_unsed_file_descriptor_and_path()`. The fd path is manually set to `/proc/$BASHPID/fd/` since that is where the `fd` are created in Android. `$$` returns pid of current process, but preferable `$BASHPID` should be used as `$$` will give wrong results in subshells. Normally unused fd number start at `3`, and its path will be `/proc/$BASHPID/fd/3`. 38 | 2. Then run something like `eval "exec $fd<" <(printf "%s" "string")`, where `$fd` expands to `3`. 39 | 3. This will create a pseudo pipe file descriptor and attach `stdout` of `printf` to the file descriptor `3`. This basically creates the file descriptor and "saves" the output of `printf` before `su` is started so `/proc/self/fd` issues do not occur. 40 | 4. We pass this path to whatever requires it inside `su`, like `bash` or `cat` for it to read. This is done by hardcoding path in the command run with `su` or exporting a variable for the path. The path will of course be for current `sudo` script `bash` process and not for the `bash` process inside `su` because of `$$`/`$BASHPID`, but since `bash` is being run with root it will be able to read from it. The file descriptor will be a read only stream like in pipes. seeking forward/backward is not a possibility and once data has been read by another process, it is gone and cannot be read again from the start. 41 | 42 | Credits and details: https://stackoverflow.com/a/20018118/14686958 by Jo So 43 | 44 | A basic version not dependent on `sudo` script functions/variables is the following. Errors and `trap` are not handled. 45 | 46 | ```shell 47 | ( 48 | get_unsed_file_descriptor() { 49 | local __fd=2 max=256; while ((++__fd < max)); do ! true <&"$__fd" && break; done 2>/dev/null || return $?; printf -v "$1" "%s" "$__fd" 50 | } 51 | 52 | # Get first unsued file descriptor and export its path for `su`. 53 | get_unsed_file_descriptor "SUDO_SU_SUB_PROCESS__SEND_COMM__FD" 54 | export SUDO_SU_SUB_PROCESS__SEND_COMM__FD_PATH="/proc/$BASHPID/fd/$SUDO_SU_SUB_PROCESS__SEND_COMM__FD" 55 | 56 | send_data="I think, therefore I am" 57 | 58 | # Use process substitution to start a process that writes send_data to 59 | # `SUDO_SU_SUB_PROCESS__SEND_COMM__FD` and then exits. 60 | eval "exec $SUDO_SU_SUB_PROCESS__SEND_COMM__FD<" <(printf '%s' "$send_data") 61 | 62 | # Start an `su` process in a subshell and read send_data from 63 | # `SUDO_SU_SUB_PROCESS__SEND_COMM__FD` with `cat` 64 | # and process it, like writing to a file or optionally printing 65 | # processed data back to stdout. 66 | su_output=$(unset LD_PRELOAD; su --preserve-environment -c 'send_data="$(cat "$SUDO_SU_SUB_PROCESS__SEND_COMM__FD_PATH")" && echo "${send_data%,*}"' 2>&1 < /dev/null) 67 | echo "PROCESSED_DATA:'$su_output'" 68 | #I think 69 | 70 | # Close send fd. 71 | exec {SUDO_SU_SUB_PROCESS__SEND_COMM__FD}<&- 72 | ) 73 | ``` 74 | 75 | An advance version dependent on `sudo` script functions/variables is the following. Errors and trap are handled. 76 | 77 | ```shell 78 | sudo_get_unsed_file_descriptor_and_path SUDO_SU_SUB_PROCESS__SEND_COMM__FD SUDO_SU_SUB_PROCESS__SEND_COMM__FD_PATH "to write data" || return $? 79 | export SUDO_SU_SUB_PROCESS__SEND_COMM__FD_PATH 80 | 81 | send_data="I think, therefore I am" 82 | 83 | # Use process substitution to start a process that writes send_data to 84 | # `SUDO_SU_SUB_PROCESS__SEND_COMM__FD` and then exits. 85 | eval "exec $SUDO_SU_SUB_PROCESS__SEND_COMM__FD<" <(printf '%s' "$send_data") 86 | 87 | # Start an `su` process in a subshell and read send_data from 88 | # `SUDO_SU_SUB_PROCESS__SEND_COMM__FD` with `cat` 89 | # and process it, like writing to a file or optionally printing 90 | # processed data back to stdout. 91 | sudo_unset_pre_su_variables 92 | su_output=$($SU_ENV_COMMAND 'send_data="$(cat "$SUDO_SU_SUB_PROCESS__SEND_COMM__FD_PATH")" && echo "${send_data%,*}"' 2>&1 < /dev/null) 93 | sudo_set_post_su_variables 94 | echo "PROCESSED_DATA:'$su_output'" 95 | #I think 96 | 97 | # Close send fd. 98 | exec {SUDO_SU_SUB_PROCESS__SEND_COMM__FD}<&- 99 | ``` 100 | 101 | --- 102 | 103 |   104 | 105 | 106 | 107 | 108 | 109 | # Receive Data From `su` process 110 | 111 | To receive data from `su` process, the `sudo_su_sub_process__receive_comm__start()` function can be used, like it is for `sudo_setup_sudo_shell_home_and_working_environment_wrapper()` that gets `$SUDO_TEMP_DIRECTORY` from `su` process. The same process of using process substitution is used to open a `fd` as detailed in [Send Data To `su` process](#send-data-to-su-process), however, inside the process substitution referred as the relay process, instead of `printf`, we start a `sleep` process in background and wait on it to keep the current process substitution process alive until it is manually killed after `su` process ends and communication is no longer required by calling the `sudo_su_sub_process__receive_comm__stop()` function. A trap is also setup inside the process substitution to also kill the background `sleep` process when the process substitution process is sent a kill signal by `sudo_su_sub_process__receive_comm__stop()`. 112 | 113 | The following procedure needs to be used. 114 | 1. Call `set_sudo_traps` to setup a trap for `sudo_trap` that calls `sudo_su_sub_process__receive_comm__stop` and `sudo_su_sub_process__receive_comm__cleanup()` if `sudo` script exits early on errors or receives a kill signal. 115 | 2. Call `sudo_su_sub_process__receive_comm__start` to start the receive communication by setting up the process substitution and fds. 116 | 3. Run `su` command that writes to the `$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH` variable exported by `sudo_su_sub_process__receive_comm__start()`. 117 | 4. Call `sudo_su_sub_process__receive_comm__stop` after `su` process exits to kill the process substitution process. 118 | 5. Read data from `$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH` with `cat`, etc sent by `su` command. 119 | 6. Call `sudo_su_sub_process__receive_comm__cleanup()` to close the `$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD` opened for process substitution. 120 | 121 | The `sudo_su_sub_process__receive_comm__stop()` function must be called before reading data from `$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH`, otherwise script will hang indefinitely. 122 | 123 | If the process substitution process is not kept alive with a background `sleep` process and waiting on it, then older devices like below Android `6` and `7`, possibly depending on kernel version, will fail with errors like `/proc/6026/fd/3: Text file busy` when `su` process attempts to write to `$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH`. So the process substitution process must only be killed after `su` process has exited and sent all its data. 124 | 125 | An advance version dependent on `sudo` script functions/variables is the following. Errors and trap are handled. 126 | 127 | ```shell 128 | # Set traps to run commands before exiting sudo. 129 | set_sudo_traps "sudo_trap" || return $? 130 | 131 | # Start relay process. 132 | sudo_su_sub_process__receive_comm__start || return $? 133 | 134 | sudo_unset_pre_su_variables 135 | su_output=$($SU_ENV_COMMAND 'receive_data="I think, therefore I am"; echo "$receive_data" > "$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH"' 2>&1 < /dev/null) 136 | return_value=$? 137 | sudo_set_post_su_variables 138 | [ -n "$su_output" ] && echo "$su_output" 139 | if [ $return_value -ne 0 ]; then 140 | sudo_log_errors "Failure while running su sub process" 141 | return $return_value 142 | fi 143 | 144 | # Stop relay process. 145 | sudo_su_sub_process__receive_comm__stop || return $? 146 | 147 | if [ ! -e "$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH" ]; then 148 | sudo_log_errors "The SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH '$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH' does not exist that needs to be used to read RECEIVE_DATA" 149 | return 1 150 | fi 151 | 152 | RECEIVE_DATA="$(cat "$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH")" 153 | return_value=$? 154 | if [ $return_value -ne 0 ]; then 155 | sudo_log_errors "Failure to read RECEIVE_DATA from SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH '$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH'" 156 | return $return_value 157 | fi 158 | 159 | echo "RECEIVE_DATA='$RECEIVE_DATA'" 160 | #I think, therefore I am 161 | 162 | # Close receive fd. 163 | sudo_su_sub_process__receive_comm__cleanup || return $? 164 | ``` 165 | 166 | --- 167 | 168 |   169 | 170 | 171 | 172 | 173 | 174 | # Send And Receive Data From `su` process 175 | 176 | This is a combination of [Send Data To `su` process](#send-data-to-su-process) and [Receive Data From `su` process](#receive-data-from-su-process). 177 | 178 | An advance version dependent on `sudo` script functions/variables is the following. Errors and trap are handled. 179 | 180 | ```shell 181 | # Set traps to run commands before exiting sudo. 182 | set_sudo_traps "sudo_trap" || return $? 183 | 184 | # Get first unsued file descriptor and export its path for `su`. 185 | sudo_get_unsed_file_descriptor_and_path SUDO_SU_SUB_PROCESS__SEND_COMM__FD \ 186 | SUDO_SU_SUB_PROCESS__SEND_COMM__FD_PATH "to send data" || return $? 187 | export SUDO_SU_SUB_PROCESS__SEND_COMM__FD_PATH 188 | 189 | send_data="I think, therefore I am" 190 | 191 | # Use process substitution to start a process that writes send_data to 192 | # `SUDO_SU_SUB_PROCESS__SEND_COMM__FD` and then exits. 193 | eval "exec $SUDO_SU_SUB_PROCESS__SEND_COMM__FD<" <(printf '%s' "$send_data") 194 | 195 | 196 | # Start relay process. 197 | sudo_su_sub_process__receive_comm__start || return $? 198 | 199 | 200 | sudo_unset_pre_su_variables 201 | su_output=$($SU_ENV_COMMAND 'send_data="$(cat "$SUDO_SU_SUB_PROCESS__SEND_COMM__FD_PATH")" && receive_data="${send_data%,*}" && echo "$receive_data" > "$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH"' 2>&1 < /dev/null) 202 | return_value=$? 203 | sudo_set_post_su_variables 204 | [ -n "$su_output" ] && echo "$su_output" 205 | if [ $return_value -ne 0 ]; then 206 | sudo_log_errors "Failure while running su sub process" 207 | return $return_value 208 | fi 209 | 210 | # Stop relay process. 211 | sudo_su_sub_process__receive_comm__stop || return $? 212 | 213 | if [ ! -e "$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH" ]; then 214 | sudo_log_errors "The SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH '$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH' does not exist that needs to be used to read PROCESSED_DATA" 215 | return 1 216 | fi 217 | 218 | PROCESSED_DATA="$(cat "$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH")" 219 | return_value=$? 220 | if [ $return_value -ne 0 ]; then 221 | sudo_log_errors "Failure to read PROCESSED_DATA from SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH '$SUDO_SU_SUB_PROCESS__RECEIVE_COMM__FD_PATH'" 222 | return $return_value 223 | fi 224 | 225 | echo "PROCESSED_DATA='$PROCESSED_DATA'" 226 | #I think 227 | 228 | # Close receive fd. 229 | sudo_su_sub_process__receive_comm__cleanup || return $? 230 | 231 | # Close send fd. 232 | exec {SUDO_SU_SUB_PROCESS__SEND_COMM__FD}<&- 233 | ``` 234 | 235 | --- 236 | 237 |   238 | 239 | 240 | 241 | 242 | 243 | # Additional Rationale 244 | 245 | There are other reasons as well why the above method is being used other than the `/proc/self/fd` issues. 246 | 247 | 1. The above method is faster than `heredocs` and `herestrings` since data is processed only in memory and does not create temp files on the disk increasing execution time like the later. The data is of course buffered with a likely limit of `64KB` but that's still large enough not to cause problems for average script text passing. 248 | 249 | 2. The temp files created by `heredocs` and `herestrings` are in `$TMPDIR` which in termux's case is `$TERMUX__PREFIX/tmp`. The `$TMPDIR` is relatively less secure since non-root processes can access it and ideally shouldn't be used due to potential risk of privilege escalation or private data leakage. Although any process in Termux context could get `su` access if termux app has been granted root access but other apps granted SAF access can by default only access `$TERMUX__HOME` and not `$TERMUX__PREFIX` by default, and cannot access any root owned directories as Termux app process cannot access them in its `ContentProvider`. You can confirm usage of `$TMPDIR` by running: 250 | ```shell 251 | # For herestrings. 252 | sleep 3 <<<"here string" & lsof -w -p $! | grep 0r 253 | 254 | # For heredocs. 255 | sleep 3 <` path to `bash` directly that the `<(echo 'echo 1')` process substitution will create. The `$su_shell_pid` is inside single quotes so it expands inside the `su` shell and `$fd_number` is inside double quotes so it expands locally. Despite the `/proc/self/fd/63` argument passed due to process substitution, bash will read from the path manually passed. Note that we cannot create the path using `$PPID` variable because multiple processes are created by the `su` shell and `$PPID` will not match `$su_shell_pid`. If the `$TERMUX__PREFIX/bin/su` is directly used by running `su --shell...` instead of full path, then another process is created because `su` in Termux `bin` directory is actually a wrapper script and process substitution path will be created for it instead, it may even give errors while executing commands. This method is however not used because its a bit hacky but could work, but would require multiple device and multiple `su` implementation testing. Another reason this isn't used is because normally, the `sudo` binary of linux distros will close all open file descriptors other than standard input, standard output and standard error when its called for security reasons to prevent child processes from getting access to file descriptors of the parent processes that were not intended for it. Some `su` binaries behave in the same way. There are however not closed by SuperSU `v2.82` as shown by the above test and neither by Magisk `v21.1` but other android `su` implementations may close the file descriptors, breaking this method. 273 | 274 | To monitor the file descriptors `63` opened by child processes, run the following commands: 275 | ```shell 276 | # Drop to a root shell so that root processes can also be monitored. 277 | sudo su 278 | # Run a background infinite loop that passes a comma separated list of 279 | # pids returned by ps to ls using brace expansion that will list all 280 | # files in `/proc/{pids}/fd` paths and then grep only fds matching `63` 281 | # and output their pid to stdout which is captured by `$pid`. 282 | # If $pid is set, then ps is used to display pid,ppid,cmd of all pids stored in the $pid variable 283 | (while true; do pid="$(eval "ls --color=never -d -1 /proc/{$(ps --no-headers -o pid -g | sed -z -e 's/\n/,/g' -e 's/ //g' -e 's/,$//')}/fd/* 2>/dev/null" | grep "/fd/63" | sed -E 's|/proc/([0-9]+)/fd/.*|\1|g')"; [ -n "$pid" ] && ps -wwo pid,ppid,cmd $(echo "$pid" | sed -z -E 's/[ \n\t]+/ /'); done) & 284 | # Store the pid of the background process so that it can be killed later. 285 | while_pid=$! 286 | # Then drop to another root shell. 287 | sudo su 288 | # Then run the su command with an added sleep command for background 289 | # monitoring to work, you may want to increase the sleep time. 290 | # Ideally two commands would be shown by ps that created fd `63`, one 291 | # for the local bash interactive shell of the sudo su command and the 292 | # other for the newly created su shell since the fd will be copied 293 | # during the fork. 294 | fd_number="$(echo <(echo "") | sed -E 's|/proc/self/fd/([0-9]+)|\1|')" 295 | /sbin/su --shell="${TERMUX__PREFIX:-$PREFIX}/bin/bash" --preserve-environment -c "bash_shell_pid=$$; "'su_shell_pid=$(pgrep -P $bash_shell_pid); sleep 0.3; bash /proc/$su_shell_pid/fd/'"$fd_number" <(echo 'echo 1') 296 | # Exit the second root shell once done. 297 | exit 298 | # Kill background process, do not leave it running since it will 299 | # consume lots of resources and may slow down the system. 300 | kill $while_pid 301 | ``` 302 | There are probably other methods using `lsof` etc. 303 | 304 | --- 305 | 306 |   307 | -------------------------------------------------------------------------------- /site/pages/en/projects/docs/developer/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/docs/@ARK_DOC__VERSION@/developer/index.md" 3 | --- 4 | 5 | # sudo Developer Docs 6 | 7 | 8 | 9 | These docs are meant for the developers, maintainers and contributors of the [`agnostic-apollo/sudo`](https://github.com/agnostic-apollo/sudo) repository and its forks. 10 | 11 | ### Contents 12 | 13 | - [Build](build/index.md) 14 | - [Test](test/index.md) 15 | - [Contribute](contribute/index.md) 16 | - [Guides](guides/index.md) 17 | 18 | --- 19 | 20 |   21 | -------------------------------------------------------------------------------- /site/pages/en/projects/docs/developer/test/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/docs/@ARK_DOC__VERSION@/developer/test/index.md" 3 | --- 4 | 5 | # sudo Test Docs 6 | 7 | 8 | 9 | [`sudo_tests`](https://github.com/agnostic-apollo/sudo/blob/master/tests/sudo_tests) can be used to run tests for [`sudo`](https://github.com/agnostic-apollo/sudo). 10 | 11 | Check the `sudo_tests` file for setup instructions, or run it with the `--help-extra` option. 12 | 13 | If `sudo` is installed with a Termux package manager, then `sudo_tests` gets installed at `$TERMUX__PREFIX/libexec/installed-tests/sudo/sudo_tests`. 14 | 15 | To show help, run `${TERMUX__PREFIX:-$PREFIX}/libexec/installed-tests/sudo/sudo_tests --help-extra`. 16 | 17 | To run all tests, run `${TERMUX__PREFIX:-$PREFIX}/libexec/installed-tests/sudo/sudo_tests -vv`. Tests will only be run for whatever shells are currently installed. The `--only-bash-tests` option can be passed to only test `bash` shell. Additionally, the `su`, `asu`, `path`, or `script` can be passed to only run tests for specific command types. 18 | 19 | --- 20 | 21 |   22 | 23 | 24 | 25 | 26 | 27 | ## Help 28 | 29 | ``` 30 | sudo_tests is a script that run tests for the sudo script. 31 | 32 | 33 | Usage: 34 | sudo_tests [command_options] 35 | sudo_tests [command_options] 36 | sudo_tests [command_options] 37 | 38 | 39 | Available command_options: 40 | [ -h | --help ] Display this help screen. 41 | [ --help-extra ] Display more help about how sudo_tests command 42 | works. 43 | [ -q | --quiet ] Set log level to 'OFF'. 44 | [ -v | -vv ] Set log level to 'DEBUG', 'VERBOSE', `VVERBOSE'. 45 | [ --only-bash-tests ] Run only bash shell tests. 46 | 47 | 48 | Setting log level '>= DEBUG' will fail test validation for tests that 49 | match the output, its mainly for debugging. 50 | ``` 51 | 52 | --- 53 | 54 |   55 | -------------------------------------------------------------------------------- /site/pages/en/projects/docs/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/docs/@ARK_DOC__VERSION@/index.html" 3 | ark__replacement_strings: 4 | - target: "../releases/index.md" 5 | replacement: "@ARK_PAGE__URL@/../../../releases/index.html" 6 | --- 7 | 8 | # sudo Docs 9 | 10 | 11 | 12 | [`sudo`](https://github.com/agnostic-apollo/sudo) stands for *superuser do*. It is a wrapper script to execute commands as the `root (superuser)` user in the [Termux](https://github.com/termux/termux-app) app, like to drop to an interactive shell for any of the [supported shells](usage/index.md#supported-shells), or to execute shell script files or their text passed as an argument. 13 | 14 | ### Contents 15 | 16 | - [Releases](../releases/index.md) 17 | - [Install](install/index.md) 18 | - [Usage](usage/index.md) 19 | - [Developer](developer/index.md) 20 | - [Build](developer/build/index.md) 21 | - [Test](developer/test/index.md) 22 | - [Contribute](developer/contribute/index.md) 23 | - [License](https://github.com/agnostic-apollo/sudo/blob/master/LICENSE) 24 | 25 | --- 26 | 27 |   28 | -------------------------------------------------------------------------------- /site/pages/en/projects/docs/install/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/docs/@ARK_DOC__VERSION@/install/index.md" 3 | --- 4 | 5 | # sudo Install Docs 6 | 7 | 8 | 9 | The [`sudo`](https://github.com/agnostic-apollo/sudo) install instructions are available below. For build instructions, check [`build`](../developer/build/index.md) docs. 10 | 11 | ### Contents 12 | 13 | - [Install Dependencies](#install-dependencies) 14 | - [Install Sources](#install-sources) 15 | 16 | --- 17 | 18 |   19 | 20 | 21 | 22 | 23 | 24 | ## Install Dependencies 25 | 26 | Using `sudo` in Termux shells only has the following dependencies. 27 | 28 | - [Termux](https://github.com/termux/termux-app) app version: minimum `>= 0.100`, **recommended `>= 0.119.0`**. 29 | - [`bash`](https://www.gnu.org/software/bash/manual/bash.html) version: `>= 4.1`. 30 | - A `su` binary that supports the `-c`, `--shell`, `--preserve-environment` and `--mount-master` options. [Magisk](https://github.com/topjohnwu/Magisk) and [SuperSU](https://su.chainfire.eu/) are recommended and their `su` binaries support the required options. Note that the [limited `su` provided by Android debug builds](https://cs.android.com/android/platform/superproject/+/master:system/extras/su/su.cpp) for `adb root` does not support these options. Check [`su` search paths](../usage/index.md#su-search-paths) for more info. 31 | 32 | However, to use `sudo` with [Termux:Tasker](https://github.com/termux/termux-tasker) plugin app and [RUN_COMMAND Intent](https://github.com/termux/termux-app/wiki/RUN_COMMAND-Intent) requires the following app versions to be installed. Check [Passing Arguments](../usage/index.md#passing-arguments) section and [Termux:Tasker `Setup Instructions`](https://github.com/termux/termux-tasker#setup-instructions) section for details. 33 | 34 | - [Tasker](https://play.google.com/store/apps/details?id=net.dinglisch.android.taskerm) app version: `>= 5.9.4.beta` 35 | - [Termux:Tasker](https://github.com/termux/termux-tasker) app version: `>= 0.5` 36 | 37 | --- 38 | 39 |   40 | 41 | 42 | 43 | 44 | 45 | ## Install Sources 46 | 47 | `sudo` can be installed from the following sources. 48 | 49 | - [Termux Packages Repository](#termux-packages-repository) 50 | - [GitHub](#github) 51 | 52 | **The [Termux Packages Repository](#termux-packages-repository) is the recommended way to install `sudo`.** 53 | 54 | The Termux app version `>= v0.119.0` exports path environment variables like `$TERMUX_ROOTFS`, `$TERMUX_HOME` and `$TERMUX_PREFIX` under the `TERMUX_` env root scope (`$TERMUX_ENV__S_ROOT`). `sudo` version `>= 1.0.0` uses these dynamic paths instead of relying on hardcoded `com.termux` paths, which will not work if Termux is built for a different rootfs or for a fork. In future, multiple rootfs support may be added in Termux app as well. The hardcoded `com.termux` paths refers to `/data/data/com.termux/*` paths for the [upstream Termux app](https://github.com/termux/termux-app) with the `com.termux` app package name. 55 | 56 | - If running in Termux app version `< 0.119.0` where environment variables are not exported: 57 | - If `sudo` is built with [Termux Packages Build Infrastructure](../developer/build/index.md#termux-packages-build-infrastructure), then placeholder path values that are replaced during build time are used. 58 | - If `sudo` is built [On Device With `make`](../developer/build/index.md#on-device-with-make) or downloaded from [`master` branch](https://github.com/agnostic-apollo/sudo/blob/master/sudo) or [GitHub Releases](https://github.com/agnostic-apollo/sudo/releases), then hardcoded `/data/data/com.termux/*` paths are used. 59 | - If running in Termux app version `>= 0.119.0` where environment variables are exported: 60 | - If `sudo` is built with [Termux Packages Build Infrastructure](../developer/build/index.md#termux-packages-build-infrastructure), then environment variables are used if set, with a fallback to placeholder path values that are replaced during build time. 61 | - If `sudo` is built [On Device With `make`](../developer/build/index.md#on-device-with-make) or downloaded from [`master` branch](https://github.com/agnostic-apollo/sudo/blob/master/sudo) or [GitHub Releases](https://github.com/agnostic-apollo/sudo/releases), then environment variables are used if set, with a fallback to hardcoded `/data/data/com.termux/*` paths. 62 | 63 | Hence, if `sudo` is not built with the [Termux Packages Build Infrastructure](../developer/build/index.md#termux-packages-build-infrastructure), then it will not work in Termux app forks that have not merged the changes done in Termux app version `>= 0.119.0` for exporting path environment variables into their own apps. 64 | 65 | Termux variables are set in the `sudo_set_termux_env_variables` function of the `sudo` script, which internally calls the [`termux_gtsev_bash__get_termux_scoped_env_variable()`](https://github.com/termux/termux-packages//blob/master/packages/termux-core/src/scripts/termux_gtsev_bash__get_termux_scoped_env_variable) function that is used by the [`termux-get-termux-scoped-env-variable.bash`](https://github.com/termux/termux-core-package/blob/v0.1.0/src/scripts/termux-get-termux-scoped-env-variable.bash.in) util provided by the `termux-core` package. The `@*@` placeholders (like `@TERMUX__ROOTFS@`) in the `sudo_set_termux_env_variables` function exist so that they are replaced during build time by the Termux build infrastructure through the `Makefile`. Check [`termux-get-termux-scoped-env-variable` usage docs](https://github.com/termux/termux-core-package/blob/master/site/pages/en/projects/docs/usage/utils/.md) for more info. 66 | 67 | ##   68 | 69 |   70 | 71 | 72 | 73 | ### Termux Packages Repository 74 | 75 | To install `sudo` package from the [`main` channel](https://github.com/termux/termux-packages/blob/master/packages/sudo/build.sh) of the [Termux packages repository](https://packages.termux.dev), run the following commands. 76 | 77 | ```shell 78 | pkg install sudo 79 | ``` 80 | 81 | ##   82 | 83 |   84 | 85 | 86 | 87 | ### GitHub 88 | 89 | The `sudo` file should be installed in termux `bin` directory `${TERMUX__PREFIX:-$PREFIX}/bin`. It should have `Termux app (u_a)` user (like `u0_a100`) `uid:gid` ownership and have executable (`700`/`rwx------`) permission before it can be executed. 90 | 91 |   92 | 93 | #### Basic 94 | 95 | **The Basic way is the recommended way to install `sudo` from GitHub, especially if you have limited understanding of shell commands.** 96 | 97 | [`curl`](https://curl.se) will automatically be installed to download `sudo`. 98 | 99 | Download `sudo` from the **`latest` [GitHub Releases](https://github.com/agnostic-apollo/sudo/releases)** and convert it into an executable. Copy all the commands and run them together in the shell. 100 | 101 | ```shell 102 | pkg install curl && \ 103 | install_dir="${TERMUX__PREFIX:-$PREFIX}/bin" && \ 104 | mkdir -p "$install_dir" && \ 105 | rm -f "$install_dir/sudo" && \ 106 | curl -L 'https://github.com/agnostic-apollo/sudo/releases/latest/download/sudo' -o "$install_dir/sudo" 107 | owner="$(stat -c "%u" "$install_dir")" && chown "$owner:$owner" "$install_dir/sudo" && \ 108 | chmod 700 "$install_dir/sudo" && \ 109 | termux-fix-shebang "$install_dir/sudo" 110 | ``` 111 | 112 |   113 | 114 | #### Advance 115 | 116 | 1. Set install directory path and create it and delete any existing `sudo` file. 117 | 118 | ```shell 119 | install_dir="${TERMUX__PREFIX:-$PREFIX}/bin" && \ 120 | mkdir -p "$install_dir" && \ 121 | rm -f "$install_dir/sudo" 122 | ``` 123 | 124 | 2. Download the `sudo` file. If using [`curl`](https://curl.se), then it must be installed to download `sudo`. Run `pkg install curl` to install `curl`. 125 | 126 | - **Using `curl` from [GitHub Releases](https://github.com/agnostic-apollo/sudo/releases)** with a non-root shell. 127 | - Latest release: 128 | 129 | `curl -L 'https://github.com/agnostic-apollo/sudo/releases/latest/download/sudo' -o "$install_dir/sudo"` 130 | 131 | - Specific release: 132 | 133 | `curl -L 'https://github.com/agnostic-apollo/sudo/releases/download/v0.1.0/sudo' -o "$install_dir/sudo"` 134 | 135 | - **Manually from [GitHub Releases](https://github.com/agnostic-apollo/sudo/releases)** listed under the `Assets` dropdown menu to the android download directory and then copy it to install directory using `cat` command or a root file browser. Termux app must have `storage` permission if running `cat` command. 136 | 137 | `cat "/storage/emulated/0/Download/sudo" > "$install_dir/sudo"` 138 | 139 | - **Using `curl` from [`master` branch](https://github.com/agnostic-apollo/sudo/tree/master)** (*may be unstable*) with a non-root shell. 140 | 141 | `curl -L 'https://github.com/agnostic-apollo/sudo/raw/master/sudo' -o "$install_dir/sudo"` 142 | 143 | 3. Set `Termux app (u_a)` user ownership and executable (`700`/`rwx------`) permission. 144 | 145 | - If you used `curl` or `cat` to copy the file, then use a non-root shell to set ownership and permissions with `chown` and `chmod` commands respectively: 146 | 147 | `owner="$(stat -c "%u" "$install_dir")" && chown "$owner:$owner" "$install_dir/sudo" && chmod 700 "$install_dir/sudo";` 148 | 149 | - If you used a root file browser to copy the file, then use `su` to start a root shell to set ownership, permissions and SeLinux context ([1](https://github.com/agnostic-apollo/Android-Docs/blob/master/site/pages/en/projects/docs/os/selinux/security-context.md), [2](https://github.com/agnostic-apollo/Android-Docs/blob/master/site/pages/en/projects/docs/os/selinux/context-types.md)) for Termux user with `chown`, `chmod` and `restorecon` commands respectively: 150 | 151 | `owner="$(stat -c "%u" "$install_dir")" && su -c "chown \"$owner:$owner\" \"$install_dir/sudo\" && chmod 700 \"$install_dir/sudo\" && restorecon \"$install_dir/sudo\"";` 152 | 153 | 4. Replace `#!/usr/bin/bash` shebang in `sudo` script with path to `bash` under the current Termux rootfs `bin` path by running [`termux-fix-shebang`](https://github.com/termux/termux-tools/blob/master/scripts/termux-fix-shebang.in) on it so that `sudo` works properly even if `libtermux-exec.so` is not set in `$LD_PRELOAD`. Check [`termux-exec` `Linux vs Termux `bin` paths`](https://github.com/termux/termux-exec-package/blob/master/site/pages/en/projects/docs/technical/index.md#linux-vs-termux-bin-paths) and [`termux-tasker` `Termux Environment`](https://github.com/termux/termux-tasker#termux-environment) docs for more info. 154 | 155 | `termux-fix-shebang "$install_dir/sudo"` 156 | 157 | 158 | --- 159 | 160 |   161 | -------------------------------------------------------------------------------- /site/pages/en/projects/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/index.html" 3 | ark__replacement_strings: 4 | - target: "docs/index.md" 5 | replacement: "@ARK_PAGE__URL@/../docs/latest/index.html" 6 | - target: "docs/developer/contribute/index.md" 7 | replacement: "@ARK_PAGE__URL@/../docs/latest/developer/contribute/index.html" 8 | --- 9 | 10 | # sudo 11 | 12 | [`sudo`](https://github.com/agnostic-apollo/sudo) stands for *superuser do*. It is a wrapper script to execute commands as the `root (superuser)` user in the [Termux](https://github.com/termux/termux-app) app, like to drop to an interactive shell for any of the supported shells, or to execute shell script files or their text passed as an argument. 13 | 14 | ### Contents 15 | 16 | - [Releases](#releases) 17 | - [Docs](#docs) 18 | - [Donations](#donations) 19 | - [Credits](#credits) 20 | 21 | --- 22 | 23 |   24 | 25 | 26 | 27 | 28 | 29 | ## Releases 30 | 31 | Check `releases` [here](releases/index.md). 32 | 33 | --- 34 | 35 |   36 | 37 | 38 | 39 | 40 | 41 | ## Docs 42 | 43 | Check `docs` [here](docs/index.md). If you intend to contribute to this repository, then also check `contribute` docs [here](docs/developer/contribute/index.md). 44 | 45 | --- 46 | 47 |   48 | 49 | 50 | 51 | 52 | 53 | ## Donations 54 | 55 | - To donate money to support me, you can visit [here](https://github.com/agnostic-apollo/agnostic-apollo/blob/main/Donations.md) for more info. 56 | 57 | --- 58 | 59 |   60 | 61 | 62 | 63 | 64 | 65 | ## Credits 66 | 67 | - [`termux-sudo` by `st42`] 68 | - [`tsu` by `cswl`] 69 | 70 | --- 71 | 72 |   73 | -------------------------------------------------------------------------------- /site/pages/en/projects/releases/0/v0.1.0.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/releases/0/v0.1.0.html" 3 | --- 4 | 5 | # sudo v0.1.0 - 2020-12-14 6 | 7 | ## Changelog 8 | 9 | **Commit history:** [`v0.1.0`](https://github.com/agnostic-apollo/sudo/releases/tag/v0.1) 10 | 11 |   12 | 13 | 14 | 15 | Initial release. 16 | 17 | --- 18 | 19 |   20 | -------------------------------------------------------------------------------- /site/pages/en/projects/releases/0/v0.2.0.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/releases/0/v0.2.0.html" 3 | --- 4 | 5 | # sudo v0.2.0 - 2021-04-11 6 | 7 | ## Changelog 8 | 9 | **Commit history:** [`v0.1.0...v0.2.0`](https://github.com/agnostic-apollo/sudo/compare/v0.1.0...v0.2.0) 10 | 11 |   12 | 13 | 14 | 15 | ### Changed 16 | 17 | - Made `$PS1` replacement commands more generic. ([`a10efd95f`](https://github.com/agnostic-apollo/sudo/commit/a10efd95f)) 18 | 19 | ##   20 | 21 |   22 | 23 | 24 | 25 | ### Fixed 26 | 27 | - Fixed wrong architecture detection causing `CANNOT LINK EXECUTABLE` errors. ([`c01cb241`](https://github.com/agnostic-apollo/sudo/commit/c01cb241)) 28 | 29 | - Fixed template download links. ([`d3f3e673`](https://github.com/agnostic-apollo/sudo/commit/d3f3e673)) 30 | 31 | --- 32 | 33 |   34 | -------------------------------------------------------------------------------- /site/pages/en/projects/releases/1/v1.0.0.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/releases/1/v1.0.0.html" 3 | --- 4 | 5 | # sudo v1.0.0 - 2025-03-21 6 | 7 | ## Changelog 8 | 9 | **Commit history:** [`v0.2.0...v1.0.0`](https://github.com/agnostic-apollo/sudo/compare/v0.2.0...v1.0.0) 10 | 11 |   12 | 13 | 14 | 15 | ### Added 16 | 17 | - Add log level `VVVERBOSE` for tests and change log level and format for entries. 18 | 19 | - Add homepage and SPDX-License-Identifier to scripts. 20 | 21 | - Add release docs and move changelogs to dedicated version release files. 22 | 23 | - Add developer docs for building, contribute and test. 24 | 25 | - Add install docs 26 | 27 | The `#!/data/data/com.termux/files/usr/bin/bash` shebang for `com.termux` package has been replaced with the linux `#!/usr/bin/bash` shebang so that `sudo` from `master` branch and GitHub releases works for termux forks or a different rootfs path. The install docs have been updated with the instructions to run `termux-fix-shebang` on installation so that required shebang gets replaced as per Termux environment of the running device. 28 | 29 | - Init new site design for project, docs and release info 30 | 31 | `README.md` has also been added back that was previously move to usage docs. 32 | 33 | - Add `github_release_build` workflow to automatically upload `sudo` and its checksum file to a release when its published. 34 | 35 | - **!** Set `SUDO__TERMUX_ROOTFS`, `SUDO__TERMUX_HOME` and `SUDO__TERMUX_PREFIX` to be used by `sudo.config` 36 | 37 | Previously, `$TERMUX_HOME` was used by `sudo.config`, which should be replaced with `$SUDO__TERMUX_HOME` in user config files as it may not be set in future versions. 38 | 39 | Also added check to abort if sourcing `sudo.config` failed. 40 | 41 | - Export `$TERMUX__ROOTFS`, `$TERMUX__HOME` and `$TERMUX__PREFIX` environment variable as per paths found with `termux_bash__get_termux_scoped_env_variable` and only export `$PREFIX` if its already exported to an absolute path. 42 | 43 | Termux app will deprecate `$PREFIX` from version `>= 0.119.0` and will add an option to not export it all in future. Users and external programs should rely on `$TERMUX__PREFIX` instead of `$PREFIX` as that may conflict with other programs. 44 | 45 | - Do not use hardcoded `com.termux` paths and use `TERMUX_` scoped environment variables for getting termux paths under rootfs, add support termux-packages build infrastructure and replace `TERMUX_FILES` references with `TERMUX_ROOTFS` 46 | 47 | The Termux app version `>= v0.119.0` (yet to be released) will export path environment variables like `$TERMUX_ROOTFS`, `$TERMUX_HOME` and `$TERMUX_PREFIX` under the `TERMUX_` env root scope (`$TERMUX_ENV__S_ROOT`). We use these dynamic paths instead of relying of hardcoded `com.termux` paths, which will not work if Termux is compiled for a different rootfs or for a fork. In future, multiple rootfs support may be added in Termux app as well. 48 | 49 | If running in Termux app version `< 0.119.0` where env variables are not exported: 50 | - If using `sudo` compiled with termux-packages build infrastructure, then use placeholder values replaced during build time, with a fallback to hardcoded `/data/data/com.termux/*` paths. 51 | - If using `sudo` compiled on-device with `make` or downloaded from `master` branch or GitHub releases, then use hardcoded `/data/data/com.termux/*` paths. 52 | If running in Termux app version `>= 0.119.0` where env variables are exported: 53 | - If using `sudo` compiled with termux-packages build infrastructure, then use env variables, with a fallback to placeholder values replaced during build time. 54 | - If using `sudo` compiled on-device with `make` or downloaded from `master` branch or GitHub releases, then use env variables, with a fallback to hardcoded `/data/data/com.termux/*` paths. 55 | 56 | The hardcoded `com.termux` paths refers to `/data/data/com.termux/*` paths for the current Termux app (https://github.com/termux/termux-app) for the `com.termux` app package name, but such paths will not work for termux forks or for multiple rootfs. 57 | 58 | Settings variables is handled by the `termux_bash__get_termux_scoped_env_variable` function, which is taken from the `termux-get-termux-scoped-env-variable` util provided by the `termux-core-package` package. The `@*@` placeholders like `@TERMUX__ROOTFS@` have been added so that they are replaced during build time by the build infrastructure through the `Makefile`. Check https://github.com/termux/termux-core-package/blob/master/site/pages/en/projects/docs/usage/utils/termux-get-termux-scoped-env-variable.md for more info. 59 | 60 | Termux files/base directory is also now referred as the rootfs by the Termux app and build infrastructure. 61 | 62 | - Add support of Android 5/6 and the `-A`, `-AA`, `-t` `-T`, `-TT` priority flags and change `path` command and fix `$LD_LIBRARY_PATH` behaviour 63 | 64 | - On android `6`, possibly `5` as well, writing to fd path `$SUDO_TEMP_DIRECTORY_FD` in `sudo_setup_sudo_temp_directory()` with `printf` fails with `text file busy` error inside the the root user `su` shell (`$SU_ENV_COMMAND`), where the fd path was opened in the termux user shell in `sudo_setup_sudo_shell_home_and_working_environment_wrapper()` before starting the `su` shell. So passing data with a fd is not possible between termux and root user, so a temp file is used under `$TMPDIR` for Android `< 7` with the name `.sudo.temp.path.XXXXXX`. 65 | - The `-A`, `-AA`, `-t` `-T`, `-TT` priority flags have been added, in addition to the already existing `-a` flag. This allows easily running commands specific to termux or android bin paths to have a consistent experience with them. Check the updated docs for each command type for their behaviour and the https://github.com/agnostic-apollo/sudo#path-and-ld_library_path-priorities and https://github.com/termux/termux-packages/wiki/Termux-execution-environment docs for more info. 66 | - To ensure only binaries under `$TERMUX__PREFIX/bin` directory are executed, pass the `-T` flag. This will have consistent behaviour with shells starts by the Termux app. 67 | - To ensure only binaries under any `termux` directory (`$TERMUX__PREFIX/bin` or `$TERMUX__PREFIX/bin/applets`) are executed, pass the `-TT` flag. 68 | - To ensure only binaries under `/system/bin` directory are executed, pass the `-A` flag. 69 | - To ensure only binaries under any `android` bin directory are executed, pass the `-AA` flag. This will have consistent behaviour with shells starts by android `adb` (https://developer.android.com/tools/adb). 70 | - While running in a shell as the `termux` user, to run a single `android` system command as the `root` user, use the `path` command with the `-A` or `-AA` flag as `sudo -A `, like `sudo -A ls -lhdZ .` to execute `/system/bin/ls`. 71 | - The `path` command previously set priority automatically if command path was under `/system` partition, but there are other system paths under which system/non-termux binaries may exist, like `/apex`, `/vendor`, `/product` paths or under `/sbin` and `/system/xbin` directories, and their dynamic linking may fail if `$LD_LIBRARY_PATH` contains `$TERMUX__PREFIX/lib`, as they rely on linker using default system library paths instead. So now, for `path` command, if priority flags are not passed, then priority is given to `termux` paths followed `android` paths if executable `canonical` path is under `$TERMUX__ROOTFS` directory (like `-t` flag), otherwise to `android` paths followed `termux` paths (like `-a` flag). 72 | - The android `bin` paths are exported as per AOSP for each android version to have a consistent experience with normal app environment and `adb` shell. 73 | - The `$LD_LIBRARY_PATH` variable is no longer exported for Android `>= 7` as Termux uses `DT_RUNPATH` and it causes the linker error `CANNOT LINK EXECUTABLE` for certain commands, like `ffmpeg`. However, it is exported for Android `< 7` for priority flags for which termux bin paths exist in `$PATH`. 74 | 75 | - Add docs to advise against piping `su` and `sudo` output to other commands and using script `-s` command type instead. 76 | 77 | - Add support for `--only-bash-tests` to run only bash tests for `sudo_tests` 78 | 79 | Bash tests cover most of the logical tests and does not require installing packages of additional shells and utilities that are tested. 80 | 81 | - Add `/debug_ramdisk/su` to `su` search paths, and ensure `su` binary selected after searching supports the `-c` option, and add support for custom path with `$SUDO_SU_PATH` env variable and `--su-path` option 82 | 83 | The order for `su` search paths has been changed too. Check docs added in `README` for more info. 84 | 85 | The `/debug_ramdisk/su` path is required as its the source path for the `tmpfs` mount done at `/system/bin/sh` by `Magisk`. Other Magisk forks may not do the `tmpfs` mount, like it was removed for `Kitsune Mask` `vR65976974` and then reverted in `vR65C33E4F`. 86 | 87 | - https://web.archive.org/web/20240109161543/https://github.com/HuskyDG/magisk-files/releases/tag/R65976974-kitsune 88 | - https://web.archive.org/web/20240220115005/https://github.com/HuskyDG/magisk-files/releases/tag/1707294287 89 | 90 | ##   91 | 92 |   93 | 94 | 95 | 96 | ### Changed 97 | 98 | - **!** Use `SUDO__` scoped environment variables for `sudo.config`, and `SUDO_SCRIPT__` scoped environment variables and `sudo_script__` scoped files/functions for `script` command 99 | 100 | Following environment variable scopes have been renamed that may be defined in `sudo.config` file or exported before running `sudo`. 101 | 102 | - `$SUDO_SHELL_HOME` to `$SUDO__SHELL_HOME` 103 | - `$SUDO_POST_SHELL_HOME` to `$SUDO__POST_SHELL_HOME` 104 | - `$SUDO_SHELL_PS1` to `$SUDO__SHELL_PS1` 105 | - `$SUDO_POST_SHELL_PS1` to `$SUDO__POST_SHELL_PS1` 106 | - `$SUDO_ADDITIONAL_PATHS_TO_EXPORT` to `$SUDO__ADDITIONAL_PATHS_TO_EXPORT` 107 | - `$SUDO_EXPORT_ALL_EXISTING_PATHS_IN_PATH_VARIABLE` to `$SUDO__EXPORT_ALL_EXISTING_PATHS_IN_PATH_VARIABLE` 108 | - `$SUDO_ADDITIONAL_LD_LIBRARY_PATHS_TO_EXPORT` to `$SUDO__ADDITIONAL_LD_LIBRARY_PATHS_TO_EXPORT` 109 | - `$SUDO_EXPORT_ALL_EXISTING_PATHS_IN_LD_LIBRARY_PATH_VARIABLE` to `$SUDO__EXPORT_ALL_EXISTING_PATHS_IN_LD_LIBRARY_PATH_VARIABLE` 110 | - `$SUDO_SHELLS_AUTOMATICALLY_CREATE_RC_FILES` to `$SUDO__SHELLS_AUTOMATICALLY_CREATE_RC_FILES` 111 | - `$SUDO_SHELLS_AUTOMATICALLY_CREATE_HISTORY_FILES` to `$SUDO__SHELLS_AUTOMATICALLY_CREATE_HISTORY_FILES` 112 | - `$SUDO_SHELLS_HISTORY_ENABLED` to `$SUDO__SHELLS_HISTORY_ENABLED` 113 | - `$SUDO_SU_PATH` to `$SUDO__SU_PATH` 114 | - `$SUDO_LOG_LEVEL` to `$SUDO__LOG_LEVEL` 115 | 116 | Following environment variable scopes have been renamed that are exported for the `sudo -s` `script` command. Their names have been changed as well for clarity of their function, like exit code and pid is for the `core_script` passed, and not for the `script` command as a whole. 117 | 118 | - `$SUDO_SCRIPT_DIR` to `$SUDO_SCRIPT__TEMP_DIR` 119 | - `$SUDO_SCRIPT_EXIT_CODE` to `$SUDO_SCRIPT__CORE_SCRIPT_EXIT_CODE` 120 | - `$SUDO_SCRIPT_PID` to `$SUDO_SCRIPT__CORE_SCRIPT_PID` 121 | 122 | Following file name scopes have been renamed that are created for the `sudo -s` `script` command. 123 | 124 | - `sudo_core_script` to `sudo_script__core_script` 125 | 126 | Following function name scopes have been renamed that are exported for the `sudo -s` `script` command for exit traps. 127 | 128 | - `sudo_script_trap` to `sudo_script__trap` 129 | - `sudo_script_custom_trap` to `sudo_script__custom_trap` 130 | - `sudo_remove_temp_directory` to `sudo_script__remove_temp_directory` 131 | 132 | - Move license text to licenses/agnostic-apollo__sudo__MIT.md file and update LICENSE to debian copyright format 133 | 134 | - https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ 135 | 136 | - **!** Use `SUDO__` scoped environment variable for `tpath` and `apath` functions instead of hardcoded paths 137 | 138 | Previously, `LD_PRELOAD` set in `rc` files was hardcoded to `/data/data/com.termux` paths, which wouldn't work for a different rootfs. 139 | 140 | We use `SUDO__` scoped environment variables instead of just `TERMUX_PRIORITY_PATH`, `ANDROID_PRIORITY_PATH`, `TERMUX_PRIORITY_LD_LIBRARY_PATH` and `ANDROID_PRIORITY_LD_LIBRARY_PATH` variables so that they do not conflict with variables set by something else and in the `sudo` environment it is explicitly clear who exported the variables. 141 | 142 | - Do no use `herestring` for command option arrays generated from strings with `xargs` as it creates temp files in `$TMPDIR` which has a performance impact and pass them with a `printf` pipe instead. 143 | 144 | - Prepend default rc and history file options passed to interactive shells to the ones passed by `--shell-options` and `--post-shell-options` arguments in case user wants to override them. 145 | 146 | - Replace hardcoded `/data/data/com.termux/files/{usr,home}` paths with `$TERMUX__PREFIX` and `~/` and replace `/storage/emulated/0` with `/sdcard` 147 | 148 | The `/sdcard` should be a symlink to `/storage/self/primary`, which would be a symlink to `/storage/emulated/` depending on current user id. This would allow running commands in secondary users. 149 | 150 | - Use `ANDROID__BUILD_VERSION_SDK` exported by Termux app `>= v0.119.0` instead of running `getprop "ro.build.version.sdk"` 151 | 152 | This will have a performance impact for older versions where variable is not exported 153 | 154 | - Update donation link. 155 | 156 | - **!** Refactor to change conventions for variables, comments, indentation and log levels and update tests 157 | 158 | - All global variables in `sudo` are now uppercase including all the variables in `sudo.config`. The `ADDITIONAL_PATHS_TO_EXPORT`, `EXPORT_ALL_EXISTING_PATHS_IN_PATH_VARIABLE`, `ADDITIONAL_LD_LIBRARY_PATHS_TO_EXPORT` and `EXPORT_ALL_EXISTING_PATHS_IN_LD_LIBRARY_PATH_VARIABLE` variables in `sudo.config` now have the `SUDO_` scope prefix to prevent conflicts, like `SUDO_ADDITIONAL_PATHS_TO_EXPORT`. **Users using `sudo.config` file must update their variables.** 159 | - Comments now have a space after the hash `#` character and first letter is uppercase, like `# Comment`. 160 | - Indentation has been converted from tabs to 4 spaces. 161 | - Log levels are used instead of verbose mode. Log level can also be set by exporting an `int` in `$SUDO_LOG_LEVEL` between `0-3` in addition to increasing it with `-v` flags or setting it to `0` with `-q|--quiet` flags, like `SUDO_LOG_LEVEL=3` to set log level to `VERBOSE=3`. 162 | - Tests have been updated to pass, mainly required switching `youtube-dl` to `yt-dlp`. 163 | - Fix printing of empty line at start of `sudo --help` output. 164 | 165 | ##   166 | 167 |   168 | 169 | 170 | 171 | ### Fixed 172 | 173 | - Use `/system/bin/sh` shell on Android `< 7` if running `asu`/`script` commands with `-A` or `-AA` flags as Termux shells will have linker errors as `LD_LIBRARY_PATH` will not be set. 174 | 175 | - Disable calling `tudo_script__killtree` for Android `< 6` as `pgrep` is not available. 176 | 177 | - Do not use quiet mode for `funcsave` for `fish` shell on Android `< 7` as `-q` option is not available. 178 | 179 | - Use `/proc/self/mounts` to check for magisk system mirror instead of `mount` command in case it is not available in `$PATH` 180 | 181 | Termux provides `mount` command with `mount-utils` package, which isn't installed by default. 182 | 183 | - Fix conversion of command string to command array by using `bash___shell__set_shell_command_args_array()` function from `libalteran-sh` 184 | 185 | Current `printf | xargs` pipe will remove empty arguments `''` and globs `*` will expand when output from `xargs` is assigned to the array unless `set -f` (`shopt -so noglob`) has been set before hand, which then needs to be restored if not already set by checking output of `shopt -o noglob` first, which obviously gets complicated. 186 | 187 | Note that `/system/bin/xargs` does not parse arguments properly and single and double quotes around arguments remain, nor do backslash escapes work, so do not use such characters when calling `sudo` if current shell has `/system/bin` in `$PATH` instead of or before Termux bin path. 188 | 189 | - Use `$TERMUX__PREFIX/lib/libtermux-exec.so` for `LD_PRELOAD` when writing `tpath` function instead of hardcoded `com.termux` absolute path. 190 | 191 | - Redirect `stderr` to `stdout`, `stdin` to `/dev/null` for `su` shells (`$SU_ENV_COMMAND`) and put all commands inside a subshell as sometimes exit code is `0` even if last command fails with a non zero exit code and command/output is out of order or stderr is not completely flushed before command exits 192 | 193 | The reason is unknown at this time, can be tested with `sudo -vv --shell-home=$HOME/.. su`, which should always fail when `sudo_setup_sudo_shell_home_and_working_environment` returns an error and exits with exit code `1`, but doesn't. 194 | 195 | The issue with this is that since `stderr` is redirected to `stdout`, the `su_output` that's manually logged with `echo` afterwards to `stdout` will contain both normal log entries and the errors, instead of the errors being sent to `stderr`. But this is not too big an issue as an additional error is still logged with `sudo_log_errors` to `stderr` if a command fails. 196 | 197 | - Do not attempt to remount `/system` partition as `rw` for shell home if magisk overlay is being used as it would be `ro` and cannot be remounted. 198 | 199 | - Manually `cd` to current working directory in case `su` changes it. 200 | 201 | - Fix validation if rootfs `/` is passed as `--work-dir` and do not spend time on setup for it as a working directory and fix already existing rootfs `/` or `/system` subdirectories not allowed on android `>= 10` if passed as `--work-dir` 202 | 203 | Validation failure was caused because regex being used for validation didn't allow allow rootfs `/` itself and only absolute paths under it. 204 | 205 | - Fix `path` command executing executable symlink target instead of symlink itself and do no execute file relative to current working directory if path does not start with `./` or `../` 206 | 207 | For `coreutils` and `toybox`, etc, the symlink itself must be executed, like `/system/bin/ls` instead of the executable target, like `/system/bin/toybox`. 208 | 209 | Previously, if `sudo stat` was executed and a file with the name `stat` existed in current working directory, then it would be executed instead of the one in `$PATH`, which causes nondeterministic behaviour depending on state of current directory. So we do not allow this anymore, if user wants to execute a file in current directory, it must start with `./` or `../`, like `sudo ./stat`. This behaviour is consistent with normal shell behaviour as well. 210 | 211 | - Disable logging of `funcsave: wrote $HOME/.config/fish/functions/[export|unset].sh` by using quiet mode. 212 | 213 | --- 214 | 215 |   216 | -------------------------------------------------------------------------------- /site/pages/en/projects/releases/1/v1.1.0.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/releases/1/v1.1.0.html" 3 | --- 4 | 5 | # sudo v1.1.0 - 2025-03-25 6 | 7 | ## Changelog 8 | 9 | **Commit history:** [`v1.0.0...v1.1.0`](https://github.com/agnostic-apollo/sudo/compare/v1.0.0...v1.1.0) 10 | 11 |   12 | 13 | 14 | 15 | ### Added 16 | 17 | - Add `riscv64` support. ([`18c755cd`](https://github.com/agnostic-apollo/sudo/commit/18c755cd)) 18 | 19 | ##   20 | 21 |   22 | 23 | 24 | 25 | ### Changed 26 | 27 | - Use standardized format for version string output as per the ` version= org= project=` format. ([`fb98e958`](https://github.com/agnostic-apollo/sudo/commit/fb98e958)) 28 | - Only disable calling `sudo_script__killtree` for Android `< 6` if `pgrep` is not in `$PATH` like if it is set to `/system/bin` instead of always disabling it as per `7396ca78`. ([`4699500e`](https://github.com/agnostic-apollo/sudo/commit/4699500e)) 29 | 30 | ##   31 | 32 |   33 | 34 | 35 | 36 | ### Fixed 37 | 38 | - Fix sdk level typo for Android `< 6` used for trimming environment and trap `pgrep` check. ([`47cf5ee1`](https://github.com/agnostic-apollo/sudo/commit/47cf5ee1)) 39 | - Exit early from su env command shells if failed to source `sudo` script. ([`04e8412f`](https://github.com/agnostic-apollo/sudo/commit/04e8412f)) 40 | - Fix `Text file busy` error when root user `su` shell attempts to write data in `sudo_setup_sudo_temp_directory()` to the fd opened by the termux user `sudo` script `bash` shell to receive `$SUDO_TEMP_DIRECTORY` in `sudo_setup_sudo_shell_home_and_working_environment_wrapper()` and add `su` Sub Process Communication Guide. ([`3eaec348`](https://github.com/agnostic-apollo/sudo/commit/3eaec348)) 41 | 42 | --- 43 | 44 |   45 | -------------------------------------------------------------------------------- /site/pages/en/projects/releases/1/v1.2.0.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/releases/1/v1.2.0.html" 3 | --- 4 | 5 | # sudo v1.2.0 - 2025-05-12 6 | 7 | ## Changelog 8 | 9 | **Commit history:** [`v1.1.0...v1.2.0`](https://github.com/agnostic-apollo/sudo/compare/v1.1.0...v1.2.0) 10 | 11 |   12 | 13 | 14 | 15 | ### Fixed 16 | 17 | - Pass the new `--interactive` flag along with `-c` to force open a tty as required by Magisk now. Related pull https://github.com/topjohnwu/Magisk/pull/8927. Related pull https://github.com/termux/termux-packages/pull/24684. ([`746ba74b`](https://github.com/agnostic-apollo/sudo/commit/746ba74b)) 18 | - Call `sudo_set_su_variables()` before running tests to properly set `ANDROID_PATH`. ([`5e34ad65`](https://github.com/agnostic-apollo/sudo/commit/5e34ad65)) 19 | 20 | --- 21 | 22 |   23 | -------------------------------------------------------------------------------- /site/pages/en/projects/releases/index.md: -------------------------------------------------------------------------------- 1 | --- 2 | page_ref: "@ARK_PROJECT__VARIANT@/agnostic-apollo/sudo/releases/index.html" 3 | --- 4 | 5 | # sudo Releases 6 | 7 | This page lists the releases info for [`sudo`](https://github.com/agnostic-apollo/sudo). 8 | 9 | **The currently latest release of `sudo` is [`v1.2.0`](1/v1.2.0.md).** 10 | 11 | --- 12 | 13 |   14 | 15 | 16 | 17 | 18 | 19 | ## Release Sources 20 | 21 | The `sudo` is released on the following sources. 22 | 23 | - [GitHub releases](https://github.com/agnostic-apollo/sudo/releases). 24 | 25 | --- 26 | 27 |   28 | 29 | 30 | 31 | 32 | 33 | ## Release Versions 34 | 35 | Open a release to view its release notes and/or changelogs. Changelogs are generated as per the [Keep a Changelog](https://github.com/olivierlacan/keep-a-changelog) spec. 36 | 37 | ### `v0` 38 | 39 | - [`v0.1.0`](0/v0.1.0.md) 40 | - [`v0.2.0`](0/v0.2.0.md) 41 | 42 | ### `v1` 43 | 44 | - [`v1.0.0`](1/v1.0.0.md) 45 | - [`v1.1.0`](1/v1.1.0.md) 46 | - [`v1.2.0`](1/v1.2.0.md) 47 | 48 | --- 49 | 50 |   51 | -------------------------------------------------------------------------------- /sudo.config: -------------------------------------------------------------------------------- 1 | # .sudo.config 2 | 3 | # Set SUDO__SHELL_HOME which will be used as sudo shell home directory 4 | #SUDO__SHELL_HOME="$SUDO__TERMUX_HOME/.suroot" # Default: `$SUDO__TERMUX_HOME/.suroot` 5 | #SUDO__SHELL_HOME="$SUDO__TERMUX_HOME" # Use '$SUDO__TERMUX_HOME' as sudo shell home 6 | 7 | # Set SUDO__POST_SHELL_HOME which will be used as sudo post shell home directory 8 | #SUDO__POST_SHELL_HOME="$SUDO__TERMUX_HOME/.suroot" # Default: `$SUDO__TERMUX_HOME/.suroot` 9 | #SUDO__POST_SHELL_HOME="$SUDO__TERMUX_HOME" # Use '$SUDO__TERMUX_HOME' as sudo post shell home 10 | 11 | # Set the prompt string 1 for the sudo shell 12 | #SUDO__SHELL_PS1="# " # Default: `# ` 13 | 14 | # Set the prompt string 1 for the sudo post shell 15 | #SUDO__POST_SHELL_PS1="# " # Default: `# ` 16 | 17 | # Set any additional paths you want to export other than termux bin, android bin and su bin paths, 18 | # separated with colons `:` 19 | # The string must not start or end with or contain two consecutive colons ':' 20 | # The `--export-paths` option will override this value 21 | #SUDO__ADDITIONAL_PATHS_TO_EXPORT="" # Default: `` 22 | 23 | # Set to "1" or pass "-L" as argument if you want to automatically export all the paths that already exist 24 | # in the PATH variable at the moment the sudo command is run 25 | # The default paths mentioned above and any path in SUDO__ADDITIONAL_PATHS_TO_EXPORT are always exported 26 | #SUDO__EXPORT_ALL_EXISTING_PATHS_IN_PATH_VARIABLE=0 # Default: `0` 27 | 28 | # Set any additional ld library paths you want to export other than termux lib and android lib paths, 29 | # separated with colons `:` 30 | # The string must not start or end with or contain two consecutive colons ':' 31 | # The `--export-ld-lib-paths` option will override this value 32 | #SUDO__ADDITIONAL_LD_LIBRARY_PATHS_TO_EXPORT="" # Default: `` 33 | 34 | # Set to "1" or pass "-P" as argument if you want to automatically export all the paths that already exist 35 | # in the LD_LIBRARY_PATH variable at the moment the sudo command is run 36 | # The default paths mentioned above and any path in SUDO__ADDITIONAL_LD_LIBRARY_PATHS_TO_EXPORT are always exported 37 | #SUDO__EXPORT_ALL_EXISTING_PATHS_IN_LD_LIBRARY_PATH_VARIABLE=0 # Default: `0` 38 | 39 | # Set to 1 if you want to automatically create rc files for interactive shells, otherwise 0 40 | #SUDO__SHELLS_AUTOMATICALLY_CREATE_RC_FILES=1 # Default: `1` 41 | 42 | # Set to 1 if you want to automatically create history files for interactive shells, otherwise 0 43 | #SUDO__SHELLS_AUTOMATICALLY_CREATE_HISTORY_FILES=1 # Default: `1` 44 | 45 | # Set to 1 if you want to store command history for interactive shells, otherwise 0 46 | #SUDO__SHELLS_HISTORY_ENABLED=1 # Default: `1` 47 | 48 | # Set absolute path for su binary to use instead of searching for it in default search paths. 49 | # This can be used if path is not in search paths or all paths in it should not be checked. 50 | #SUDO__SU_PATH="" # Default: `` 51 | -------------------------------------------------------------------------------- /templates/plugin_hosts/tasker/Termux_RUN_COMMAND_Intent_Sudo_Templates.tsk.md: -------------------------------------------------------------------------------- 1 | # Termux RUN COMMAND Intent Sudo Templates 2 | 3 |   4 | ## Export Info: 5 | **Tasker Version:** `5.11.7.beta` 6 | **Timestamp:** `2020-12-14 15.54.33` 7 |   8 | 9 | 10 | 11 |   12 | ## Profile Names: 13 | **Count:** `0` 14 | 15 | 16 | 17 | 18 | ## Scene Names: 19 | **Count:** `0` 20 | 21 | 22 | 23 | 24 | ## Task Names: 25 | **Count:** `1` 26 | 27 | - `Termux RUN_COMMAND Intent Sudo Templates` 28 | ## 29 |   30 | 31 | 32 | 33 |   34 | ## Profiles Info: 35 |   36 | 37 | 38 | 39 |   40 | ## Tasks Info: 41 |   42 | 43 | ### Task 1 44 | **Name:** `Termux RUN_COMMAND Intent Sudo Templates` 45 | **ID:** `999` 46 | **Collision Handling:** `Abort New Task` 47 | **Keep Device Awake:** `false` 48 | 49 | #### Help: 50 | 51 | A task that provides templates for running `sudo` script commands with the `RUN_COMMAND` intent as the `root (superuser)` user in Termux. The commands are run using the Tasker `TermuxCommand()` function of the `Tasker Function` action and with the `am` command with the `Run Shell` action and are referred as intent actions in this task. This task requires Termux:Tasker version `>= 0.5`. Tasker must be granted `com.termux.permission.RUN_COMMAND` permission. The `sudo` script must be installed at `$PREFIX/bin/sudo`. The `allow-external-apps` property must also be set to `true` in `~/.termux/termux.properties` file, otherwise any commands received via the `RUN_COMMAND` intent will not be executed by Termux. For android `>= 10`, Termux must also be granted `Draw Over Apps` permissions so that foreground commands automatically start executing without the user having to manually click the `Termux` notification in the status bar dropdown notifications list for the commands to start. The device must be rooted and ideally `Termux` must have been granted root permissions by your root manager app like `SuperSU` or `Magisk` for the `sudo` script to work. 52 | 53 | Check [Termux:Tasker Github](https://github.com/termux/termux-tasker) and [RunCommand Intent](https://github.com/termux/termux-app/wiki/RUN_COMMAND-Intent) for more details on `RUN_COMMAND` intent configuration. 54 | 55 | Check [sudo](https://github.com/agnostic-apollo/sudo) for more details for the `sudo` script. 56 | 57 | 58 | The result of commands is not received back when commands are run with the `RUN_COMMAND` intent, hence all templates run their commands in the foreground terminal session so that the results can be viewed. The `--sleep=3` command option is also passed to `sudo` so that it sleeps for `3` seconds before exiting. If this is not passed, the terminal would immediately close after `sudo` executes its commands without giving the user a chance to view the results in the terminal session. Moreover, a `Wait` action of `2` seconds is also added to the task after each template so that the templates execute in order and don't start until the previous one has at least ideally started executing. 59 | 60 | The default value of the `%comma_alternative` variable in this task is set to `‚` (`#U+201A`, `‚`, `‚`, `single low-9 quotation mark`). This is the same character that is replaced with the simple comma `,` (`U+002C`, `,`, `,`, `comma`) by the `sudo` script by default when the `-r` option is passed. You can use a different character that should be replaced using the `--comma-alternative` option. 61 | 62 | 63 | Template 1 runs the `$PREFIX/bin/sudo --sleep=3 dumpsys -l` command in the foreground using `TermuxCommand()` function as a template for the `path` `command_type` to list all android services. The arguments do not contain any simple comma characters and hence can be passed directly without having to replace them with `%comma_alternative` characters. 64 | 65 | 66 | Template 2 runs the `$PREFIX/bin/sudo -sr --sleep=3 '%core_script' '%argument_1' '%argument_2'` command in the foreground using `TermuxCommand()` function as a template for the `script` `command_type` with `bash` as the `sudo shell`, which would be chosen automatically by default without having to pass the `--shell` option. The `termux_tasker_basic_bash_test` `bash` script text is passed as the `core_script` argument with 2 complex dynamic args that may contain simple comma characters. The `-s` command option is passed to set `command_type` to `script`. The `-r` command option is passed so that `sudo` parses the arguments as per `RUN_COMMAND` intent rules. The `sudo` executable is passed to the intent using the `%executable` variable. The `%core_script`, `%argument_1` and `%argument_2` variables are used to store the dynamic values to be sent as `$1`, `$2` and `$3` respectively to `sudo`. They are first all set in the `%arguments` variable separated by simple comma characters, which is passed to the intent. The `%core_script`, `%argument_1` and `%argument_2` variables may contain any type of characters, even a simple comma, but simple commas must be replaced with the `%comma_alternative` characters before the intent action is run so that their values are not split into multiple arguments by the intent. To replace the simple commas, `Variable Search Replace` action is run to replace all simple commas `,` with the `%comma_alternative` variable value. The `Variable Search Replace` action must be used separately for each argument variable before adding it to the `%arguments` variable. Do not set multiple arguments in the same variable and use `Variable Search Replace` action on it since that will result in incorrect argument splitting. This template shows how you can dynamically create intent commands at runtime using variables and send them via the `RUN_COMMAND` intent to Termux for execution, including passing the script text itself without having to create a physical file in `~/.termux/tasker/` directory. 67 | 68 | 69 | Template 3 is almost the same as Template 2, but it runs the `$PREFIX/bin/sudo -sr --shell=python --sleep=3 '%core_script' '%argument_1' '%argument_2'` command in the foreground using `am` command as a template for the `script` `command_type` with `python` as the `sudo shell`. The `termux_tasker_basic_python_test` `python` script text is passed as the `core_script` argument with 2 complex dynamic args that may contain simple comma characters. However, as already mentioned that this template uses the `am` command, the `%arguments` variable is passed to the `com.termux.RUN_COMMAND_ARGUMENTS` string array extra surrounded with single quotes inside a shell and hence any single quotes inside the `%arguments` variable also need to be escaped before running the intent command to prevent incorrect quoting. To escape the single quotes, `Variable Search Replace` action is run to replace all single quotes `'` with one single quote, followed by one backslash, followed by two single quotes `'\''`. So `%arguments` surrounded with single quotes that would have been passed like `'some arg with single quote ' in it'` will be passed as `'some arg with single quote '\'' in it'`. This is basically 3 parts `'some arg with single quote '`, `\'` and `' in it'` but when processed, it will be considered as one single argument with the value `some arg with single quote ' in it` that is passed as the `com.termux.RUN_COMMAND_ARGUMENTS` string array extra value. The `Variable Search Replace` action does not need to be used separately for each argument variable before adding it to the `%arguments` variable, running it on only the final `%arguments` variable would be fine, unlike how its done on individual argument variables like `%argument_1`, etc for usage with `Termux:Tasker` plugin app. 70 | 71 | 72 | Template 4 runs `$PREFIX/bin/sudo --shell-pre-commands="echo 'starting sudo shell';" --title='sudo' su` in the foreground using `TermuxCommand()` function as a template for the `su` `command_type` to start an interactive `bash` shell with priority to termux binaries and libraries. The `--shell-pre-commands` option is passed to run some commands before starting the interactive `bash` shell and its argument is **not** passed surrounded with single or double quotes to prevent whitespace splitting in the intent action, like done for usage with `Termux:Tasker` plugin app since splitting will occur on simple comma characters instead. If there are going to be simple comma characters in arguments to the command options or in the main arguments to `sudo`, you must replace them with `%comma_alternative` variable value and pass the `-r` option. The `--title` option is passed to set the title of the terminal. 73 | 74 | 75 | The `$PREFIX/` is a shortcut for the termux prefix directory `/data/data/com.termux/files/usr/`. The `~/` is a shortcut for the termux home directory `/data/data/com.termux/files/home/`. These shortcuts can be used in any path arguments to the `sudo` command. 76 | 77 | 78 | The `%command_failed` variable will be set if the intent action failed, this is detected by whether `%err` or `%errmsg` is set by the intent action. If you run multiple intent actions in the same task or are using `Local Variable Passthrough`, then you must clear the `%command_failed` variable and optionally the `%errmsg` variable with the `Variable Clear` action before running each intent action, in case they were already set, like by a previously failed intent action after which the task was not stopped. 79 | ## 80 | 81 | 82 | **Parameters:** `-` 83 | 84 | 85 | **Returns:** `-` 86 | 87 | 88 | **Control:** 89 | 90 | ``` 91 | version_name: 0.1.0 92 | ``` 93 | ## 94 |   95 | 96 | 97 | 98 |   99 | ## Code Description: 100 |   101 | 102 | `````` 103 | Task Name: Termux RUN_COMMAND Intent Sudo Templates 104 | 105 | Actions: 106 | = 0.5`. Tasker must be granted `com.termux.permission.RUN_COMMAND` permission. The `sudo` script must be installed at `$PREFIX/bin/sudo`. The `allow-external-apps` property must also be set to `true` in `~/.termux/termux.properties` file, otherwise any commands received via the `RUN_COMMAND` intent will not be executed by Termux. For android `>= 10`, Termux must also be granted `Draw Over Apps` permissions so that foreground commands automatically start executing without the user having to manually click the `Termux` notification in the status bar dropdown notifications list for the commands to start. The device must be rooted and ideally `Termux` must have been granted root permissions by your root manager app like `SuperSU` or `Magisk` for the `sudo` script to work. 107 | 108 | Check [Termux:Tasker Github](https://github.com/termux/termux-tasker) and [RunCommand Intent](https://github.com/termux/termux-app/wiki/RUN_COMMAND-Intent) for more details on `RUN_COMMAND` intent configuration. 109 | 110 | Check [sudo](https://github.com/agnostic-apollo/sudo) for more details for the `sudo` script. 111 | 112 | 113 | The result of commands is not received back when commands are run with the `RUN_COMMAND` intent, hence all templates run their commands in the foreground terminal session so that the results can be viewed. The `--sleep=3` command option is also passed to `sudo` so that it sleeps for `3` seconds before exiting. If this is not passed, the terminal would immediately close after `sudo` executes its commands without giving the user a chance to view the results in the terminal session. Moreover, a `Wait` action of `2` seconds is also added to the task after each template so that the templates execute in order and don't start until the previous one has at least ideally started executing. 114 | 115 | The default value of the `%comma_alternative` variable in this task is set to `‚` (`#U+201A`, `‚`, `‚`, `single low-9 quotation mark`). This is the same character that is replaced with the simple comma `,` (`U+002C`, `,`, `,`, `comma`) by the `sudo` script by default when the `-r` option is passed. You can use a different character that should be replaced using the `--comma-alternative` option. 116 | 117 | 118 | Template 1 runs the `$PREFIX/bin/sudo --sleep=3 dumpsys -l` command in the foreground using `TermuxCommand()` function as a template for the `path` `command_type` to list all android services. The arguments do not contain any simple comma characters and hence can be passed directly without having to replace them with `%comma_alternative` characters. 119 | 120 | 121 | Template 2 runs the `$PREFIX/bin/sudo -sr --sleep=3 '%core_script' '%argument_1' '%argument_2'` command in the foreground using `TermuxCommand()` function as a template for the `script` `command_type` with `bash` as the `sudo shell`, which would be chosen automatically by default without having to pass the `--shell` option. The `termux_tasker_basic_bash_test` `bash` script text is passed as the `core_script` argument with 2 complex dynamic args that may contain simple comma characters. The `-s` command option is passed to set `command_type` to `script`. The `-r` command option is passed so that `sudo` parses the arguments as per `RUN_COMMAND` intent rules. The `sudo` executable is passed to the intent using the `%executable` variable. The `%core_script`, `%argument_1` and `%argument_2` variables are used to store the dynamic values to be sent as `$1`, `$2` and `$3` respectively to `sudo`. They are first all set in the `%arguments` variable separated by simple comma characters, which is passed to the intent. The `%core_script`, `%argument_1` and `%argument_2` variables may contain any type of characters, even a simple comma, but simple commas must be replaced with the `%comma_alternative` characters before the intent action is run so that their values are not split into multiple arguments by the intent. To replace the simple commas, `Variable Search Replace` action is run to replace all simple commas `,` with the `%comma_alternative` variable value. The `Variable Search Replace` action must be used separately for each argument variable before adding it to the `%arguments` variable. Do not set multiple arguments in the same variable and use `Variable Search Replace` action on it since that will result in incorrect argument splitting. This template shows how you can dynamically create intent commands at runtime using variables and send them via the `RUN_COMMAND` intent to Termux for execution, including passing the script text itself without having to create a physical file in `~/.termux/tasker/` directory. 122 | 123 | 124 | Template 3 is almost the same as Template 2, but it runs the `$PREFIX/bin/sudo -sr --shell=python --sleep=3 '%core_script' '%argument_1' '%argument_2'` command in the foreground using `am` command as a template for the `script` `command_type` with `python` as the `sudo shell`. The `termux_tasker_basic_python_test` `python` script text is passed as the `core_script` argument with 2 complex dynamic args that may contain simple comma characters. However, as already mentioned that this template uses the `am` command, the `%arguments` variable is passed to the `com.termux.RUN_COMMAND_ARGUMENTS` string array extra surrounded with single quotes inside a shell and hence any single quotes inside the `%arguments` variable also need to be escaped before running the intent command to prevent incorrect quoting. To escape the single quotes, `Variable Search Replace` action is run to replace all single quotes `'` with one single quote, followed by one backslash, followed by two single quotes `'\''`. So `%arguments` surrounded with single quotes that would have been passed like `'some arg with single quote ' in it'` will be passed as `'some arg with single quote '\'' in it'`. This is basically 3 parts `'some arg with single quote '`, `\'` and `' in it'` but when processed, it will be considered as one single argument with the value `some arg with single quote ' in it` that is passed as the `com.termux.RUN_COMMAND_ARGUMENTS` string array extra value. The `Variable Search Replace` action does not need to be used separately for each argument variable before adding it to the `%arguments` variable, running it on only the final `%arguments` variable would be fine, unlike how its done on individual argument variables like `%argument_1`, etc for usage with `Termux:Tasker` plugin app. 125 | 126 | 127 | Template 4 runs `$PREFIX/bin/sudo --shell-pre-commands="echo 'starting sudo shell';" --title='sudo' su` in the foreground using `TermuxCommand()` function as a template for the `su` `command_type` to start an interactive `bash` shell with priority to termux binaries and libraries. The `--shell-pre-commands` option is passed to run some commands before starting the interactive `bash` shell and its argument is **not** passed surrounded with single or double quotes to prevent whitespace splitting in the intent action, like done for usage with `Termux:Tasker` plugin app since splitting will occur on simple comma characters instead. If there are going to be simple comma characters in arguments to the command options or in the main arguments to `sudo`, you must replace them with `%comma_alternative` variable value and pass the `-r` option. The `--title` option is passed to set the title of the terminal. 128 | 129 | 130 | The `$PREFIX/` is a shortcut for the termux prefix directory `/data/data/com.termux/files/usr/`. The `~/` is a shortcut for the termux home directory `/data/data/com.termux/files/home/`. These shortcuts can be used in any path arguments to the `sudo` command. 131 | 132 | 133 | The `%command_failed` variable will be set if the intent action failed, this is detected by whether `%err` or `%errmsg` is set by the intent action. If you run multiple intent actions in the same task or are using `Local Variable Passthrough`, then you must clear the `%command_failed` variable and optionally the `%errmsg` variable with the `Variable Clear` action before running each intent action, in case they were already set, like by a previously failed intent action after which the task was not stopped. 134 | ## 135 | 136 | 137 | **Parameters:** `-` 138 | 139 | 140 | **Returns:** `-` 141 | 142 | 143 | **Control:** 144 | 145 | ``` 146 | version_name: 0.1.0 147 | ```> 148 | A1: Anchor 149 | 150 | A2: Variable Set [ 151 | Name:%task_name 152 | To:Termux RUN_COMMAND Intent Sudo Templates 153 | Recurse Variables:Off 154 | Do Maths:Off 155 | Append:Off 156 | Max Rounding Digits:3 ] 157 | 158 |