17

When I want to ask for a password in a bash script, I do that :

read -s

...but when I run bash in POSIX mode, with sh, the -s option is rejected:

$ read -s
sh: 1: read: Illegal option -s

How do I securely ask for an input with a POSIX-compliant command ?

24
read_password() {
  REPLY="$(
    # always read from the tty even when redirected:
    exec < /dev/tty || exit # || exit only needed for bash

    # save current tty settings:
    tty_settings=$(stty -g) || exit

    # schedule restore of the settings on exit of that subshell
    # or on receiving SIGINT or SIGTERM:
    trap 'stty "$tty_settings"' EXIT INT TERM

    # disable terminal local echo
    stty -echo || exit

    # prompt on tty
    printf "Password: " > /dev/tty

    # read password as one line, record exit status
    IFS= read -r password; ret=$?

    # display a newline to visually acknowledge the entered password
    echo > /dev/tty

    # return the password for $REPLY
    printf '%s\n' "$password"
    exit "$ret"
  )"
}

Note that for those shells (mksh) where printf is not builtin, the password will appear in clear in the ps output (for a few microseconds) or may show up in some audit logs if all command invocations with their parameters are audited.

20

read -s is not in POSIX. If you want to be POSIX-compliant use the stty -echo. stty and its echo parameter are defined in POSIX.

#!/bin/bash
stty -echo
printf "Password: "
read PASSWORD
stty echo
printf "\n"

This will work on all shells that conform to POSIX.

Source

  • 7
    to highlight a point from the answer in @arkadiusz-drabczyk's comment, it'd be a good idea to trap all the signals you can in order to turn stty echo back on -- in case the user gets confused and hits control-C during the read PASSWORD section. – Jeff Schaller Aug 13 '15 at 12:36
  • read the linked answer or see Stephane's answer in this thread – Jeff Schaller Aug 13 '15 at 15:00
  • You shouldn't turn on echoing unconditionally, you should save and restore the old setting. Many people work in Emacs shell buffers, and this normally has echoing disabled because Emacs is doing the echoing itself. The other answer shows how to do this. – Barmar Aug 19 '15 at 19:37

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.