Network Working Group Tatu Ylonen INTERNET-DRAFT SSH Communications Security draft-ietf-secsh-connect-00.txt March 22, 1997 Expires: September 1, 1997 Status of This memo This document is an Internet-Draft. Internet-Drafts are working documents of the Internet Engineering Task Force (IETF), its areas, and its working groups. Note that other groups may also distribute working documents as Internet-Drafts. Internet-Drafts are draft documents valid for a maximum of six months and may be updated, replaced, or obsoleted by other documents at any time. It is inappropriate to use Internet-Drafts as reference material or to cite them other than as ``work in progress.'' To learn the current status of any Internet-Draft, please check the ``1id-abstracts.txt'' listing contained in the Internet-Drafts Shadow Directories on ftp.is.co.za (Africa), nic.nordu.net (Europe), munnari.oz.au (Pacific Rim), ds.internic.net (US East Coast), or ftp.isi.edu (US West Coast). Abstract This document describes the SSH connection protocol. It runs over the SSH user authentication layer, and performs management of forwarded con- nections and the terminal session(s). Tatu Ylonen [page 1] INTERNET-DRAFT March 22, 1997 Table of Contents 1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . 2 2. Channel Mechanism . . . . . . . . . . . . . . . . . . . . . . . 2 2.1. Opening a Channel . . . . . . . . . . . . . . . . . . . . . 3 2.2. Data Transfer . . . . . . . . . . . . . . . . . . . . . . . 3 2.3. Closing a Channel . . . . . . . . . . . . . . . . . . . . . 4 3. Sessions . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4 3.1. Opening a Session . . . . . . . . . . . . . . . . . . . . . 4 3.2. Requesting a Pseudo-Terminal . . . . . . . . . . . . . . . . 5 3.3. Environment Variable Passing . . . . . . . . . . . . . . . . 5 3.4. Requesting X11 Forwarding . . . . . . . . . . . . . . . . . 6 3.5. Requesting Athentication Agent Forwarding . . . . . . . . . 6 3.6. Starting Shell or Command . . . . . . . . . . . . . . . . . 6 3.7. Session Data Transfer . . . . . . . . . . . . . . . . . . . 7 3.8. Additional Control Messages . . . . . . . . . . . . . . . . 7 3.8.1. Window Change Message . . . . . . . . . . . . . . . . . 7 3.8.2. Local Flow Control . . . . . . . . . . . . . . . . . . . 7 3.9. Terminating a Session . . . . . . . . . . . . . . . . . . . 8 4. X11 Forwarding . . . . . . . . . . . . . . . . . . . . . . . . . 8 5. Authentication Agent Forwarding . . . . . . . . . . . . . . . . 8 6. TCP/IP Port Forwarding . . . . . . . . . . . . . . . . . . . . . 9 6.1. Requesting Port Forwarding . . . . . . . . . . . . . . . . . 9 6.2. Opening a Forwarded Connection . . . . . . . . . . . . . . . 9 7. FTP Forwarding . . . . . . . . . . . . . . . . . . . . . . . . . 10 8. Encoding of Terminal Modes . . . . . . . . . . . . . . . . . . . 10 9. Summary of Message Numbers . . . . . . . . . . . . . . . . . . . 14 10. Address of Author . . . . . . . . . . . . . . . . . . . . . . . 15 1. Introduction This protocol has been designed to run over the SSH transport layer and user authentication protocols. The service name for this protocol (after user authentication) is "ssh-connection". It provides interactive login sessions, remote execution of commands, forwarded TCP/IP connections, and forwarded X11 connections. 2. Channel Mechanism All terminal sessions, forwarded connections, etc. are channels. Either side may open a channel. Multiple channels are multiplexed on the single connection. There are several ways to open a channel; typically the method used depends on the intended use of the channel. After opening, however, different channels use the same mechanisms for communication. Channels are identified by numbers at each end. The number referring to a channel may be different on each side. Requests to open a channel contain the sender's channel number. Any other channel-related messages contain the recipient's channel number for the channel. Tatu Ylonen [page 2] INTERNET-DRAFT March 22, 1997 All channel-related messages contain the number of the channel they refer to. Channels are flow-controlled. No data may be sent to a channel until a message is received to indicate that window space is available. 2.1. Opening a Channel Regardless of the method used to open a channel, when a side wishes to open a channel, it allocates a local number for the channel. It then sends a method-specific message to the other side, and includes the local channel number and initial window size in the message. The remote side then decides whether it can open the channel, and responds with either vlint32 SSH_MSG_CHANNEL_OPEN_CONFIRMATION vlint32 recipient_channel vlint32 sender_channel vlint32 initial_window_size where recipient_channel is the channel number given in the original open request, and sender_channel is the channel number allocated by the other side, or vlint32 SSH_MSG_CHANNEL_OPEN_FAILURE vlint32 recipient_channel The window size specifies how many characters the other party can send before it must wait for the window to be adjusted. Both parties use the following message to adjust the window. vlint32 SSH_MSG_CHANNEL_WINDOW_ADJUST vlint32 recipient_channel vlint32 bytes_to_add Upon receiving this message, the recipient increases the number of bytes it is allowed to send by the given amount. 2.2. Data Transfer Data transfer is done with messages of the following type. vlint32 SSH_MSG_CHANNEL_DATA vlint32 recipient_channel string data The maximum amount of data allowed is the current window size. The window size is decremented by the amount of data sent. Additionally, some channels can transfer several types of data. An example of this is stderr data from interactive sessions. Such data can be passed with SSH_MSG_CHANNEL_EXTENDED_DATA messages, where a separate integer specifies the type of the data. The available types and their Tatu Ylonen [page 3] INTERNET-DRAFT March 22, 1997 interpretation depend on the type of the channel. vlint32 SSH_MSG_CHANNEL_EXTENDED_DATA vlint32 recipient_channel vlint32 data_type_code string data Data sent with these messages consumes the same window as ordinary data. Currently, only the following type is defined. #define SSH_EXTENDED_DATA_STDERR 1 2.3. Closing a Channel When a party will no longer send more data to a channel, it should send SSH_MSG_CHANNEL_EOF. vlint32 SSH_MSG_CHANNEL_EOF vlint32 recipient_channel No explicit response is sent to this message; however, the application may send EOF to whatever is at the other end of the channel. Note that the channel remains open after this message, and more data may still be sent in the other direction. When either party wishes to terminate the channel, it sends SSH_MSG_CHANNEL_CLOSE. Upon receiving this message, a party must send back an SSH_MSG_CHANNEL_CLOSE unless it has already sent this message for the channel. The channel is considered closed for a party when it has both sent and received SSH_MSG_CHANNEL_CLOSE, and the party may then reuse the channel number. It is legal to send SSH_MSG_CHANNEL_CLOSE without having sent or received SSH_MSG_EOF. vlint32 SSH_MSG_CHANNEL_CLOSE vlint32 recipient_channel 3. Sessions A session is a remote execution of a command. The command may be an shell, a program, or some built-in subsystem. It may or may not have a tty, and may or may not involve X11 forwarding. Multiple sessions can be active simultaneously. A session is created by SSH_MSG_CHANNEL_CREATE_SESSION. Then, the client may send preparatory requests for the session, such as starting X11 forwarding or allocating a pseudo-terminal. Finally, the client requests to execute a command or to start an interactive shell. 3.1. Opening a Session A session is started by sending the following message. While this message can be sent by either side, it is normally recommended for Tatu Ylonen [page 4] INTERNET-DRAFT March 22, 1997 clients not to permit opening new sessions to avoid a corrupt server from attacking clients. vlint32 SSH_MSG_CHANNEL_CREATE_SESSION vlint32 sender_channel The server allocates a channel number and responds with open confirmation or open failure. 3.2. Requesting a Pseudo-Terminal A pseudo-terminal can be allocated for the session by sending the following message. vlint32 SSH_MSG_SESSION_REQUEST_PTY vlint32 recipient_channel (session) string TERM environment variable value (e.g., vt100) vlint32 terminal width, characters (e.g., 80) vlint32 terminal height, rows (e.g., 24) vlint32 terminal width, pixels (e.g., 480) vlint32 terminal height, pixels (e.g., 640) string encoded terminal modes The encoding of terminal modes is described in Section ``Encoding of Terminal Modes''. The server responds with either SSH_MSG_CHANNEL_SUCCESS or SSH_MSG_CHANNEL_FAILURE. The client is allowed to send further messages without waiting for the response to this message. vlint32 SSH_MSG_CHANNEL_SUCCESS vlint32 recipient_channel vlint32 SSH_MSG_CHANNEL_FAILURE vlint32 recipient_channel 3.3. Environment Variable Passing Environment variables may be passed to the shell/command to be started later. Typically, each machine will have a preconfigured set of variables that it will allow. Since uncontrolled setting of environment variables can be very dangerous, it is recommended that implementations allow setting only variables whose names have been explicitly configured to be allowed. vlint32 SSH_MSG_SESSION_ENVIRONMENT_VARIABLE vlint32 recipient_channel string variable_name string variable_value The server responds with either SSH_MSG_CHANNEL_SUCCESS or SSH_MSG_CHANNEL_FAILURE. The client is allowed to send further messages without waiting for the response to this message. Tatu Ylonen [page 5] INTERNET-DRAFT March 22, 1997 3.4. Requesting X11 Forwarding X11 forwarding may be requested for a session by sending vlint32 SSH_MSG_SESSION_REQUEST_X11_FORWARDING vlint32 recipient_channel (session) string x11_authentication_protocol string x11_authentication_cookie vlint32 x11_screen_number It is recommended that the authentication cookie that is sent be a fake, random cookie, and that the cookie is checked and replaced by the real cookie when a connection request is received. The server responds with either SSH_MSG_CHANNEL_SUCCESS or SSH_MSG_CHANNEL_FAILURE. The client is allowed to send futher messages without waiting for the reponse to this message. 3.5. Requesting Athentication Agent Forwarding Authentication agent forwarding may be requested for a session by sending vlint32 SSH_MSG_SESSION_REQUEST_AGENT_FORWARDING vlint32 recipient_channel (session) The server responds with either SSH_MSG_CHANNEL_SUCCESS or SSH_MSG_CHANNEL_FAILURE. The client is allowed to send futher messages without waiting for the reponse to this message. 3.6. Starting Shell or Command Once the session has been set up, a shell or command is started at the remote end. This can happen in any of a number of ways. vlint32 SSH_MSG_SESSION_EXEC_SHELL vlint32 recipient_channel vlint32 SSH_MSG_SESSION_EXEC_COMMAND vlint32 recipient_channel string command vlint32 SSH_MSG_SESSION_EXEC_PREDEFINED vlint32 recipient_channel vlint32 subsystem_name This last form executes a predefined subsystem. It expected that these will include a general file transfer mechanism, and possibly other features. Implementations may also allow configuring more such mechanisms. Having a special message for them avoids the need to have their paths and command names be supplied by the other side. This also makes it easier to implement them in the same executable as the rest of the protocol on platforms where that is desirable. Tatu Ylonen [page 6] INTERNET-DRAFT March 22, 1997 3.7. Session Data Transfer Data transfer for a session is done using SSH_MSG_CHANNEL_DATA and SSH_MSG_CHANNEL_EXTENDED_DATA packets and the window mechanism. The extended data type SSH_EXTENDED_DATA_STDERR has been defined for stderr data. 3.8. Additional Control Messages Smooth operation sometimes requires extra messages to be passed to notify the other side of some event or change. A single message type, SSH_MSG_SESSION_NOTIFICATION has been defined for all of these notifications. Implementations should ignore all notifications that they cannot interpret, and are free to ignore any notifications. vlint32 SSH_MSG_SESSION_NOTIFICATION vlint32 recipient_channel string notification_type ... Currently, the following notification types have been defined: window_change Window size changed xon_xoff_flow_control Local flow control 3.8.1. Window Change Message When the window (terminal) size changes on the client side (client here means the party who sent the create message for the session), it may send a message to the other side to inform it of the new size. vlint32 SSH_MSG_SESSION_NOTIFICATION vlint32 recipient_channel string "window_change" vlint32 terminal width, columns vlint32 terminal height, rows vlint32 terminal width, pixels vlint32 terminal height, pixels 3.8.2. Local Flow Control On many systems it is possible to determine if a pseudo-terminal is using control-S control-Q flow control. When this is the case, it is often desirable to do the flow control at the client end to speed up responses to user requests. This is facilitated by the following two notifications. Initially, the server is responsible for flow control. (Here, again, client means the side originating the session, and server the other side.) vlint32 SSH_MSG_SESSION_NOTIFICATION vlint32 recipient_channel Tatu Ylonen [page 7] INTERNET-DRAFT March 22, 1997 string "xon_xoff_flow_control" boolean client_can_do If client_can_do is true, the client (originator) can do control-S control-Q flow control locally. 3.9. Terminating a Session When the command running at the other end terminates, SSH_MSG_SESSION_EXIT_STATUS may be sent to return the exit status of the command. Returning the status is optional, but recommended. No acknowledgement is sent for this message. The channel needs to be closed with SSH_MSG_CHANNEL_CLOSE after this message. vlint32 SSH_MSG_SESSION_EXIT_STATUS vlint32 recipient_channel vlint32 exit_status 4. X11 Forwarding X11 forwarding is requested with respect to a session. However, forwarded connections are independent of the session. The request to forward X11 connections opens a fake X11 display on the server. No connections are opened at this time. When an X11 client connects the fake X11 server, a request is sent to the originator of the session. vlint32 SSH_MSG_X11_OPEN vlint32 sender_channel vlint32 initial_window_size string originator_string The recipient should respond with open confirmation or open failure. Originator_string is a free-form implementation-dependent description of the X11 client that made the connection. It should typically contain the IP address and port of the client, and may also contain user name or other information if available. It should be in a format that is understandable by a user. 5. Authentication Agent Forwarding Authentication agent forwarding is requested with respect to a session. However, forwarded connections are independent of the session. When an application requests a connection to the authentication agent, the following message is sent to the originator of the session. vlint32 SSH_MSG_AGENT_OPEN vlint32 sender_channel vlint32 initial_window_size string originator_string Tatu Ylonen [page 8] INTERNET-DRAFT March 22, 1997 string host_chain The recipient should respond with open confirmation or open failure. Originator_string is a free-form implementation-dependent description of the application that made the connection, or empty if no description is available. host_chain is a comma-separated list of hosts this request has passed through. (Receiver of the message appends the sender's name, if the message will be passed on (i.e. receiver is not the actual agent).) Because only one application can use a forwarded agent channel at a time, multiple channels cannot be multiplexed in a ssh daemon. Instead, ssh daemon must pass the request, and forward the reply all the way from the agent to the requesting application. This results in creation of a private channel for application using the agent. Agent stores the host chain for every channel and uses it to determine which operations are permitted. 6. TCP/IP Port Forwarding 6.1. Requesting Port Forwarding A party need not explicitly request forwardings from its own end to the other direction. However, it if wishes to have connections to a port on the other side be forwarded to the local side, it must explicitly request this. vlint32 SSH_MSG_REQUEST_TCPIP_PORT_FORWARDING string address_to_bind vlint32 port_number_to_bind Address_to_bind and port_number_to_bind specify the IP address and port to which the socket to be listened is bound. The address should be "0.0.0.0" if connections are allowed from anywhere. (Note that the client can still filter connections based on information passed in the open request.) Implementations should only allow forwarding privileged ports if the user has been authenticated as a privileged user. The recipient will respond to this message with either SSH_MSG_REQUEST_SUCCESS or SSH_MSG_REQUEST_FAILURE. vlint32 SSH_MSG_REQUEST_SUCCESS vlint32 SSH_MSG_REQUEST_FAILURE 6.2. Opening a Forwarded Connection When a connection comes to a port for which forwarding was requested with SSH_MSG_REQUEST_TCPIP_PORT_FORWARDING, the following message is sent to the other side. Tatu Ylonen [page 9] INTERNET-DRAFT March 22, 1997 vlint32 SSH_MSG_TCPIP_REMOTE_PORT_OPEN vlint32 sender_channel vlint32 initial_window_size vlint32 port_that_was_connected string originator_ip_address vlint32 originator_port string originator_string When a connection comes to a locally forwarded TCP/IP port, the following packet is sent to the other side. Note that these messages may be sent also for ports for which no forwarding has been explicitly requested. The receiving side must decide whether to allow the forwarding. vlint32 SSH_MSG_TCPIP_PORT_OPEN vlint32 sender_channel vlint32 initial_window_size string host_to_connect vlint32 port_to_connect string originator_ip_address vlint32 originator_port string originator_string Host_to_connect and port_to_connect specify the TCP/IP host and port where the recipient should connect the channel. Host_to_connect may be either a domain name or a numeric IP address. Originator_ip_address is the numeric IP address of the machine where the connection request comes from, and originator_port is the port on the originator host from where the connection came from. Originator_string is a free-form description of where the connection came in a form that can be displayed to the user. 7. FTP Forwarding XXX 8. Encoding of Terminal Modes Terminal modes (as passed in SSH_MSG_SESSION_REQUEST_PTY) are encoded into a byte stream. It is intended that the coding be portable across different environments. The tty mode description is a stream of bytes. The stream consists of opcode-argument pairs. It is terminated by opcode TTY_OP_END (0). Opcodes 1-127 have one-byte arguments. Opcodes 128-159 have 32-bit integer arguments (stored msb first). Opcodes 160-255 are not yet defined, and cause parsing to stop (they should only be used after any other data). The client puts in the stream any modes it knows about, and the server ignores any modes it does not know about. This allows some degree of machine-independence, at least between systems that use a POSIX-like tty Tatu Ylonen [page 10] INTERNET-DRAFT March 22, 1997 interface. The protocol can support other systems as well, but the client may need to fill reasonable values for a number of parameters so the server pty gets set to a reasonable mode (the server leaves all unspecified mode bits in their default values, and only some combinations make sense). The following opcodes have been defined. The naming of opcodes mostly follows the POSIX terminal mode flags. 0 TTY_OP_END Indicates end of options. 1 VINTR Interrupt character; 255 if none. Similarly for the other characters. Not all of these characters are supported on all systems. 2 VQUIT The quit character (sends SIGQUIT signal on UNIX systems). 3 VERASE Erase the character to left of the cursor. 4 VKILL Kill the current input line. 5 VEOF End-of-file character (sends EOF from the terminal). 6 VEOL End-of-line character in addition to carriage return and/or linefeed. 7 VEOL2 Additional end-of-line character. 8 VSTART Continues paused output (normally control-Q). 9 VSTOP Pauses output (normally control-S). 10 VSUSP Suspends the current program. 11 VDSUSP Another suspend character. 12 VREPRINT Reprints the current input line. 13 VWERASE Erases a word left of cursor. Tatu Ylonen [page 11] INTERNET-DRAFT March 22, 1997 14 VLNEXT More special input characters; these are probably not supported on most systems. 15 VFLUSH Character to flush output. 16 VSWTCH ??? 17 VSTATUS ??? 18 VDISCARD ??? 30 IGNPAR The ignore parity flag. The next byte should be 0 if this flag is not set, and 1 if it is set. 31 PARMRK Mark parity and framing errors. 32 INPCK Enable checking of parity errors. 33 ISTRIP Strip 8th bit off chars. 34 INLCR Map NL into CR on input. 35 IGNCR Ignore CR on input. 36 ICRNL Map CR to NL on input. 37 IUCLC ??? 38 IXON Enable output flow control. 39 IXANY Any char will restart after stop. 40 IXOFF Enable input flow control. 41 IMAXBEL Ring bell on input queue full. 50 ISIG Tatu Ylonen [page 12] INTERNET-DRAFT March 22, 1997 Enable signals INTR, QUIT, DSUSP. 51 ICANON Canonicalize input lines. 52 XCASE ??? 53 ECHO Enable echoing. 54 ECHOE Visually erase chars. 55 ECHOK Kill character discards current line. 56 ECHONL Echo NL even if ECHO is off. 57 NOFLSH Don't flush after interrupt. 58 TOSTOP Stop background jobs from output. 59 IEXTEN Enable extensions. 60 ECHOCTL Echo control characters as ^(Char). 61 ECHOKE Visual erase for line kill. 62 PENDIN Retype pending input. 70 OPOST Enable output processing. 71 OLCUC Convert lowercase to uppercase. 72 ONLCR Map NL to CR-NL. 73 OCRNL ??? 74 ONOCR ??? 75 ONLRET Tatu Ylonen [page 13] INTERNET-DRAFT March 22, 1997 ??? 90 CS7 7 bits. 91 CS8 8 bits. 92 PARENB Parity enable. 93 PARODD Odd parity, else even. 192 TTY_OP_ISPEED Specifies the input baud rate in bits per second (as a 32-bit int, msb first). 193 TTY_OP_OSPEED Specifies the output baud rate in bits per second (as a 32-bt int, msb first). 9. Summary of Message Numbers The following message numbers are used by this protocol. If an unrecognized message is received, SSH_MSG_REQUEST_FAILURE should be sent in response. #define SSH_MSG_CHANNEL_OPEN_CONFIRMATION 40 #define SSH_MSG_CHANNEL_OPEN_FAILURE 41 #define SSH_MSG_CHANNEL_WINDOW_ADJUST 42 #define SSH_MSG_CHANNEL_DATA 43 #define SSH_MSG_CHANNEL_EOF 44 #define SSH_MSG_CHANNEL_CLOSE 45 #define SSH_MSG_CHANNEL_CREATE_SESSION 46 #define SSH_MSG_SESSION_REQUEST_PTY 47 #define SSH_MSG_CHANNEL_SUCCESS 48 #define SSH_MSG_CHANNEL_FAILURE 49 #define SSH_MSG_SESSION_ENVIRONMENT_VARIABLE 50 #define SSH_MSG_SESSION_REQUEST_X11_FORWARDING 51 #define SSH_MSG_SESSION_REQUEST_AGENT_FORWARDING 52 #define SSH_MSG_SESSION_EXEC_SHELL 53 #define SSH_MSG_SESSION_EXEC_COMMAND 54 #define SSH_MSG_SESSION_EXEC_PREDEFINED 55 #define SSH_MSG_SESSION_NOTIFICATION 56 #define SSH_MSG_SESSION_EXIT_STATUS 57 #define SSH_MSG_X11_OPEN 58 #define SSH_MSG_AGENT_OPEN 59 #define SSH_MSG_REQUEST_TCPIP_PORT_FORWARDING 60 #define SSH_MSG_REQUEST_SUCCESS 61 #define SSH_MSG_REQUEST_FAILURE 62 #define SSH_MSG_TCPIP_REMOTE_PORT_OPEN 63 #define SSH_MSG_TCPIP_PORT_OPEN 64 Tatu Ylonen [page 14] INTERNET-DRAFT March 22, 1997 10. Address of Author Tatu Ylonen SSH Communications Security Ltd. Tekniikantie 12 FIN-02150 ESPOO Finland E-mail: ylo@ssh.fi Tatu Ylonen [page 15]