The scheme for textual representation of keystrokes in screen

gnu-screenkey mappingkeyboard shortcuts

How can I derive the character sequence that represents a certain keystroke in screen? I mean, what bind takes as input. For instance, 's' represents the obvious keystroke on the 's' key. 'S' represents 'shift+s'. But the representation of other more complex combinations are unclear to me and the scheme that is followed seems quite obscure.

I have searched all around and asked before what the representation would be for the particular case 'tab' and 'shift+tab', but I couldn't find the answer. So I guess the best is to try to understand the general scheme. I have also seen this, but it's now working for me.

Can someone explain what scheme/rules screen follows for this? What are the rules to derive the representation of any arbitrary key combination? And are they screen specific, or shared with other software? Other GNU software maybe? Where is this documented?

Best Answer

There is no scheme, screen, like any terminal application, doesn't deal with keystrokes, but with characters or sequences of characters which it reads from a terminal device.

It's the terminal (or terminal emulator like xterm) that transforms a keystroke into a character or sequence of characters which it sends over a wire (the wire being virtual in the case of a terminal emulator) to the system. The line discipline of the terminal device may do some modification on that (for instance, CRs turned into LFs).

To know what character or character sequence screen receives when you type something on your terminal, you can use for instance od to display them for you.

For instance, if I enter od -tc in a terminal, od -tc will read characters from the terminal device, and display them on stdout (the terminal device as well if you've not redirected the output) in a printable way.

For instance, here's the output when I type: Up Enter Ctrl+D (the latter to signify od the end of input):

0000000 033   [   A  \n
0000004

Up has sent the 3 characters ESC, [ and A, and the \r has been changed to a \n.

screen will actually set its host terminal in raw mode so that no transformation is done by the line discipline and no characters are treated specially (like the 004 character sent upon Ctrl+D above for instance).

To see what the terminal sends in that mode, you'd do:

$ stty raw; stty min 1 time 10; dd count=1 2> /dev/null | od -tc; stty sane
0000000 033   [   A
                   0000003

Notice how the \n output by od has not been converted to \r\n for output (\n is line-feed, when output to a terminal, it only moved the cursor down, not to the beginning of the line for which your need a carriage return (\r)).

Above, we're setting the terminal in raw mode, but also set it so that a read on the terminal device times out after 10 hundredths of second as soon as 1 character has been received (because otherwise, we'd have to type a lot of characters before the read done by od returns).

Pressing Tab on all terminals sends the TAB ASCII character also known as \t or ^I or C-I or \011. For Shift+Tab, not all terminals send the same thing (some send ESC [ Z, some send \t as well and some send nothing for instance).

The terminfo database can tell you what that character is for a given terminal (based on the $TERM variable) via the kcbt capability (back tab, not necessarily sent upon Shift-Tab though).

For the current terminal:

$ tput kcbt | od -tc
0000000 033   [   Z
0000003