github.com/olivere/camlistore@v0.0.0-20140121221811-1b7ac2da0199/third_party/code.google.com/p/go.crypto/ssh/server_terminal.go (about) 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 default 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 }