The little set of $PS* variables that are hiding on standard linux machines are one of those hidden nuggets of awesome that, once you discover, lead to numerous kinds of fun! Give it a try on your machine, and see how each are set: ## PS1 This is the primary prompt string. The default on my machine is quite spectacular:  echo$PS1
$\e]0;\u@\h: \w\a$${debian_chroot:+($debian_chroot)}$\033[01;32m$\u@\h$\033[00m$:$\033[01;34m$\w$\033[00m$\$ and this results in the expected path to my present working directory, for example:  ~/Documents/Dropbox/Website/vsoch.github.io/vsoch.github.io.new$



Now we can try changing it, and seeing what happens! All you have to do is set PS1 in a terminal, and press enter.


PS1="pancakes> "
pancakes>



This is one of those “my world is rocked” moments. I’ve always wanted pancakes in my prompt! If you export the variable in your .bash_profile or .profile or similar, you can have pancakes all the time.

## PS2

This is the prompt that you see when you press enter during a command (newline) but you forget a quote or something like that. The default is a little carrot, and it’s easiest to just show you. First, here is the default:


$echo$PS2
>

car="I once was riding in a red velvet car and>
>
>



and it goes away when I complete the statement with the second quote. Now, let’s try changing it to something else.


PS2='keepgoing>'
$car="this is a car keepgoing> keepgoing> keepgoing>  and there you have it! You could use a motivational message, or something more appropriate…  car="I once was.. taco! taco! taco!  ## PS3 This is what gets shown when there is a select command. Take a look at this example:  #!/bin/bash # favorite-color.sh # chmod u+x favorite-color.sh select color in blue green orange red exit do case$color in
blue) echo "Blue!";;
green) echo "Green!";;
orange) echo "Orange!";;
red) echo "Red!";;
exit) exit;;
esac
done



Let’s look at the default $PS3, it’s not set. $ echo $PS3  When we run it without that set, we get this.  ./favorite-color.sh 1) blue 2) green 3) orange 4) red 5) exit #? 1 Blue! #? 5  I entered 1 and it selected blue, and I entered 5 and exit. Now let’s try setting it:  PS3="What is your favorite color? " ./favorite-color.sh 1) blue 2) green 3) orange 4) red 5) exit What is your favorite color? 3 Orange! What is your favorite color? 5  That’s super cool! It’s such an easy way of giving a prompt. ## PS4 And here is the most mysterious (at least to me). This is what gets printed before a trace, and so if you set the calling /bin/bash to have -x it’s going to do this. You can look at the bash man pages for some interesting snippets about how this works, and I have a feeling hidden in these pages is going to be the answer to this riddle, if not a good starting point for solving it. First, here is the default on my machine: $ echo $PS4 +  and so if I use a small example script and run it:  #!/bin/sh -x printenv | grep HOME echo hello world!  I get the expected output, with a little + before the trace of each line.  ./hello-world.sh +printenv +grep HOME HOME=/home/vanessa +echo hello world! hello world!  # Riddle Me This… And herein lies the challenge for us to think about today! This example comes from a recent pull request discussion, I noticed this (bug?) that appeared to be inconsistent output between (the same!) calls:  ./hello-world.sh ++printenv grep HOME HOME=/home/vanessa +echo hello world! hello world!  We isolated it to Ubuntu and the case of using -x, but didn’t go beyond that. Later as I was developing something else that warranted changing the prompt, I realized that this mysterious PS4 existed, period, and that the repeated + character in the bug was in fact, exactly that. How do we know? If we change it to something else, it changes appropriately.  PS4='pancakes' ./hello-world.sh pancakesprintenv pancakesgrep HOME HOME=/home/vanessa pancakesecho hello world! hello world!  (and yes, this lovely discovery turned into this huge sidetrack of a post to talk about it, I’m ok with this. And so herein lies the puzzle, please help to solve it, because I haven’t yet! Why do we sometimes see a double print of $PS4?

I think likely it has to do with the fact that we are doing this trace and print relative to a pipe. But I don’t know the answer. I’m hoping the rest of the internet (you!) can help!