6

On a test server I purposefully deleted ????? in / - I was expecting the symlink /lib64 and the /media directory to be deleted. All went well (everything broke), but then I was curious about the output below:

[root@testserver /]# ls
bin  boot  dev  etc  home  lib  lib64  media  mnt  opt  proc  rh_share3  root  run  sbin  srv  sys  tmp  usr  var
[root@testserver /]# rm -rf ?????
bash: /usr/bin/sed: No such file or directory
[root@testserver /]# ls
bash: /usr/bin/ls: No such file or directory
bash: /usr/bin/sed: No such file or directory

I see that some packages have sed as a dependency, but I'm not understanding why it's calling sed for something as simple as pressing Enter

[root@testserver bin]# rpm -q --whatrequires sed
krb5-libs-1.17-18.el8.x86_64
ca-certificates-2019.2.32-80.0.el8_1.noarch
dracut-049-70.git20200228.el8.x86_64
crypto-policies-20191128-2.git23e1bf1.el8.noarch
policycoreutils-2.9-9.el8.x86_64
authselect-libs-1.1-2.el8.x86_64
cups-filters-1.20.0-19.el8.x86_64
open-vm-tools-11.0.0-4.el8.x86_64
authselect-compat-1.1-2.el8.x86_64
dhcp-client-4.3.6-40.el8.x86_64
nfs-utils-2.3.3-31.el8.x86_64
autofs-5.1.4-40.el8.x86_64

Why does the line bash: /usr/bin/sed: No such file or directory show up? Obviously sed is considered missing, but why is it being called at all? It is also not mentioned if I just run a strace -o bash bash. I know sed stands for stream editor - is every bash command run through sed, or what else could be going on?

The OS is an OOTB RHEL 8.2 (Oopta) with a GUI.

EDIT

Below is the output of set | grep sed:

[user1@testserver ~]$ set | grep sed
    local command=$(HISTTIMEFORMAT= history 1 | sed 's/^ *[0-9]\+ *//');
                COMPREPLY=($( compgen -W "$( bpftool help 2>&1 |                     command sed                     -e '/OBJECT := /!d'                     -e 's/.*{//'                     -e 's/}.*//'                     -e 's/|//g' )" -- "$cur" ));
    COMPREPLY+=($( compgen -W "$( bpftool -jp btf 2>&1 |         command sed -n 's/.*"id": \(.*\),$/\1/p' )" -- "$cur" ))
    COMPREPLY+=($( compgen -W "$( bpftool -jp map  2>&1 |         command sed -n 's/.*"id": \(.*\),$/\1/p' )" -- "$cur" ))
    COMPREPLY+=($( compgen -W "$( bpftool -jp map  2>&1 |         command grep -C2 "$type" |         command sed -n 's/.*"id": \(.*\),$/\1/p' )" -- "$cur" ))
    COMPREPLY+=($( compgen -W "$( bpftool -jp prog 2>&1 |         command sed -n 's/.*"id": \(.*\),$/\1/p' )" -- "$cur" ))
    COMPREPLY+=($( compgen -W "$( bpftool -jp prog 2>&1 |         command sed -n 's/.*"tag": "\(.*\)",$/\1/p' )" -- "$cur" ))
    type=$(bpftool -jp map show $keyword $ref |         command sed -n 's/.*"type": "\(.*\)",$/\1/p');
        COMPREPLY=($( compgen -W "$( command sed -ne 's|^iface \([^ ]\{1,\}\).*$|\1|p'            /etc/network/interfaces /etc/network/interfaces.d/* 2>/dev/null )"             -- "$cur" ));
            COMPREPLY=($( compgen -W "$( printf '%s\n'             /etc/sysconfig/network/ifcfg-* |             command sed -ne 's|.*ifcfg-\([^*].*\)$|\1|p' )" -- "$cur" ));
                COMPREPLY=($( compgen -W "$( command ls -B             /etc/sysconfig/interfaces |             command sed -ne 's|.*ifcfg-\([^*].*\)$|\1|p' )" -- "$cur" ));
                COMPREPLY=($( compgen -W "$( printf '%s\n'             /etc/sysconfig/network-scripts/ifcfg-* |             command sed -ne 's|.*ifcfg-\([^*].*\)$|\1|p' )" -- "$cur" ));
    local included=$( command sed -ne 's/^[[:blank:]]*[Ii][Nn][Cc][Ll][Uu][Dd][Ee][[:blank:]]\{1,\}\([^#%]*\)\(#.*\)\{0,1\}$/\1/p' "${configfile}" );
    COMPREPLY+=($( compgen -W         "$( { LC_ALL=C ifconfig -a || ip addr show; } 2>/dev/null | command sed -ne             's/.*addr:\([^[:space:]]*\).*/\1/p' -ne             's|.*inet[[:space:]]\{1,\}\([^[:space:]/]*\).*|\1|p' )"         -- "$cur" ))
    [[ $# -ge $OPTIND ]] && echo "error: $FUNCNAME("$@"): unprocessed arguments:" $(while [[ $# -ge $OPTIND ]]; do printf '%s\n' ${!OPTIND}; shift; done);
        local hosts=$( command sed -ne 's/^[[:blank:]]*[Hh][Oo][Ss][Tt][[:blank:]]\{1,\}\([^#*?%]*\)\(#.*\)\{0,1\}$/\1/p' "${config[@]}" );
            local argtype=$( LC_ALL=C $1 --help 2>&1 | command sed -ne                 "s|.*$prev\[\{0,1\}=[<[]\{0,1\}\([-A-Za-z0-9_]\{1,\}\).*|\1|p" );
        COMPREPLY=($( compgen -W "$( LC_ALL=C $1 --help 2>&1 |             command sed -ne 's/.*\(--[-A-Za-z0-9]\{1,\}=\{0,1\}\).*/\1/p' | sort -u )"             -- "$cur" ));
    COMPREPLY+=($(         { LC_ALL=C ifconfig -a || ip link show; } 2>/dev/null | command sed -ne         "s/.*[[:space:]]HWaddr[[:space:]]\{1,\}\($re\)[[:space:]].*/\1/p" -ne         "s/.*[[:space:]]HWaddr[[:space:]]\{1,\}\($re\)[[:space:]]*$/\1/p" -ne         "s|.*[[:space:]]\(link/\)\{0,1\}ether[[:space:]]\{1,\}\($re\)[[:space:]].*|\2|p" -ne         "s|.*[[:space:]]\(link/\)\{0,1\}ether[[:space:]]\{1,\}\($re\)[[:space:]]*$|\2|p"
    COMPREPLY+=($( { arp -an || ip neigh show; } 2>/dev/null | command sed -ne         "s/.*[[:space:]]\($re\)[[:space:]].*/\1/p" -ne         "s/.*[[:space:]]\($re\)[[:space:]]*$/\1/p" ));
    COMPREPLY+=($( command sed -ne         "s/^[[:space:]]*\($re\)[[:space:]].*/\1/p" /etc/ethers 2>/dev/null ));
    COMPREPLY=($( compgen -W "$( command ls -RL $modpath 2>/dev/null |         command sed -ne 's/^\(.*\)\.k\{0,1\}o\(\.[gx]z\)\{0,1\}$/\1/p' )" -- "$cur" ))
        COMPREPLY=($( compgen -X '<defunct>'             -W '$( command ps axo comm | command sed -e 1d )' -- "$cur" ));
        COMPREPLY=($( compgen -X '<defunct>' -W '$( command ps axo command= | command sed -e \
        COMPREPLY=($( compgen -W '`command sed -e "y/|/ /" \
    COMPREPLY+=($( compgen -W         "$( command sed -ne 's/^\([^[:space:]#|]\{2,\}\)|.*/\1/p' /etc/termcap             2>/dev/null )" -- "$cur" ));
7
  • 2
    set|grep sed should show you where set is used in shell option suggestions/filename completions etc.
    – stoney
    Sep 19, 2020 at 7:01
  • 3
    And that's it. Filename completion. simple as that. bash tries to look up comletions with sed and this triggers the error.
    – stoney
    Sep 19, 2020 at 8:00
  • 2
    @stoney, how does filename completion come into it if you just typed ls and hit enter, without tabbing?
    – ilkkachu
    Sep 19, 2020 at 10:31
  • 1
    I would rather say that editing history file need a bit of sed
    – Archemar
    Sep 19, 2020 at 13:11
  • 1
    You may have PROMPT_COMMAND set to something that calls sed. Or calls some non-existing command, which in turn triggers the command_not_found_handle() function which in turn may be calling sed. Or something completely different. If you have fun trashing your system by removing essential files and directories, keep the fun on until you get to the bottom of it, rather than trying to collect wildly innacurate guesses about what that could mean.
    – user414777
    Sep 19, 2020 at 23:46

4 Answers 4

2

The file that is causing this behavior is vte.sh in /etc/profile.d/:

One aspect of VTE configuration is the use of /etc/profile.d/vte.sh. The VTE uses this script to override the PROMPT_COMMAND in order to feed itself additional information via terminal control codes. In particular, this script is used to tell the VTE the current directory of the shell. Previously the VTE component used to read this from /proc/<pid>/cwd however according to VTE upstream there were a number of issues with this approach and hence the change to /etc/profile.d/vte.sh.

Source

This behavior does not occur over SSH, only when using the GNOME Terminal. If anyone with a better understanding of window systems would like to write a more detailed answer, I would be glad to accept as my understanding of GNOME is limited at the moment.

0

I think the problem is that you've overridden command, a builtin:

$ help command | head --lines=2
command: command [-pVv] command [arg ...]
    Execute a simple command or display information about commands.

command is commonly used to ignore aliases and functions to explicitly run the builtin or executable directly. This is useful to avoid infinite loops. For example:

ls() {
    command ls --color=auto
}

This calls the ls executable instead of calling itself recursively forever.

unset command and look for any uses of command in your Bash profile.

0

This is just speculation, but sed is probably a dynamically-linked 64-bit binary. By deleting lib64, the kernel can no longer locate the dynamic linker needed to execute sed (and probably just about everything else). The no such file or directory isn't for sed, it's for the linker.

0

it's due to /etc/profile.d/vte.sh

case "$TERM" in
  xterm*|vte*)
    [ -n "$BASH_VERSION" ] && PROMPT_COMMAND="__vte_prompt_command"
    [ -n "$ZSH_VERSION"  ] && precmd_functions+=(__vte_osc7)
    ;;
esac
vte_prompt_command() {
  ######### HERE : bash tries to look up comletions with sed ###
  local command=$(HISTTIMEFORMAT= history 1 | sed 's/^ *[0-9]\+ *//')
  ############################################################
  command="${command//;/ }"
  local pwd='~'
  [ "$PWD" != "$HOME" ] && pwd=${PWD/#$HOME\//\~\/}
  printf "\033]777;notify;Command completed;%s\007\033]0;%s@%s:%s\007%s" "${command}" "${USER}" "${HOSTNAME%%.*}" "${pwd}" "$(__vte_osc7)"
}

just delete this(then you must use correct filename)

sed 's/^ *[0-9]\+ *//'

fixed!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.