LEFT | RIGHT |
(no file at all) | |
| 1 // Copyright 2011 The Go Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style |
| 3 // license that can be found in the LICENSE file. |
| 4 |
| 5 package ssh |
| 6 |
| 7 // A Terminal is capable of parsing and generating virtual terminal |
| 8 // data from an SSH client. |
| 9 type Terminal interface { |
| 10 ReadLine() (line string, err error) |
| 11 SetSize(x, y int) |
| 12 Write([]byte) (int, error) |
| 13 } |
| 14 |
| 15 // ServerTerminal contains the state for running a terminal that is capable of |
| 16 // reading lines of input. |
| 17 type ServerTerminal struct { |
| 18 Term Terminal |
| 19 Channel Channel |
| 20 } |
| 21 |
| 22 // parsePtyRequest parses the payload of the pty-req message and extracts the |
| 23 // dimensions of the terminal. See RFC 4254, section 6.2. |
| 24 func parsePtyRequest(s []byte) (width, height int, ok bool) { |
| 25 _, s, ok = parseString(s) |
| 26 if !ok { |
| 27 return |
| 28 } |
| 29 width32, s, ok := parseUint32(s) |
| 30 if !ok { |
| 31 return |
| 32 } |
| 33 height32, _, ok := parseUint32(s) |
| 34 width = int(width32) |
| 35 height = int(height32) |
| 36 if width < 1 { |
| 37 ok = false |
| 38 } |
| 39 if height < 1 { |
| 40 ok = false |
| 41 } |
| 42 return |
| 43 } |
| 44 |
| 45 func (ss *ServerTerminal) Write(buf []byte) (n int, err error) { |
| 46 return ss.Term.Write(buf) |
| 47 } |
| 48 |
| 49 // ReadLine returns a line of input from the terminal. |
| 50 func (ss *ServerTerminal) ReadLine() (line string, err error) { |
| 51 for { |
| 52 if line, err = ss.Term.ReadLine(); err == nil { |
| 53 return |
| 54 } |
| 55 |
| 56 req, ok := err.(ChannelRequest) |
| 57 if !ok { |
| 58 return |
| 59 } |
| 60 |
| 61 ok = false |
| 62 switch req.Request { |
| 63 case "pty-req": |
| 64 var width, height int |
| 65 width, height, ok = parsePtyRequest(req.Payload) |
| 66 ss.Term.SetSize(width, height) |
| 67 case "shell": |
| 68 ok = true |
| 69 if len(req.Payload) > 0 { |
| 70 // We don't accept any commands, only the defaul
t shell. |
| 71 ok = false |
| 72 } |
| 73 case "env": |
| 74 ok = true |
| 75 } |
| 76 if req.WantReply { |
| 77 ss.Channel.AckRequest(ok) |
| 78 } |
| 79 } |
| 80 panic("unreachable") |
| 81 } |
LEFT | RIGHT |