fix: Guard pty window resize after close (#3270)

Could help alleviate #3236.
This commit is contained in:
Mathias Fredriksson
2022-07-28 22:07:11 +03:00
committed by GitHub
parent 43b8cf04f0
commit 29d44b6283
2 changed files with 19 additions and 6 deletions

View File

@ -457,7 +457,7 @@ func (a *agent) handleSSHSession(session ssh.Session) (retErr error) {
for win := range windowSize { for win := range windowSize {
resizeErr := ptty.Resize(uint16(win.Height), uint16(win.Width)) resizeErr := ptty.Resize(uint16(win.Height), uint16(win.Width))
if resizeErr != nil { if resizeErr != nil {
a.logger.Warn(context.Background(), "failed to resize tty", slog.Error(err)) a.logger.Warn(context.Background(), "failed to resize tty", slog.Error(resizeErr))
} }
} }
}() }()

View File

@ -10,6 +10,7 @@ import (
"sync" "sync"
"github.com/creack/pty" "github.com/creack/pty"
"golang.org/x/xerrors"
) )
func newPty() (PTY, error) { func newPty() (PTY, error) {
@ -26,6 +27,8 @@ func newPty() (PTY, error) {
type otherPty struct { type otherPty struct {
mutex sync.Mutex mutex sync.Mutex
closed bool
err error
pty, tty *os.File pty, tty *os.File
} }
@ -55,6 +58,9 @@ func (p *otherPty) Output() ReadWriter {
func (p *otherPty) Resize(height uint16, width uint16) error { func (p *otherPty) Resize(height uint16, width uint16) error {
p.mutex.Lock() p.mutex.Lock()
defer p.mutex.Unlock() defer p.mutex.Unlock()
if p.closed {
return p.err
}
return pty.Setsize(p.pty, &pty.Winsize{ return pty.Setsize(p.pty, &pty.Winsize{
Rows: height, Rows: height,
Cols: width, Cols: width,
@ -65,17 +71,24 @@ func (p *otherPty) Close() error {
p.mutex.Lock() p.mutex.Lock()
defer p.mutex.Unlock() defer p.mutex.Unlock()
if p.closed {
return p.err
}
p.closed = true
err := p.pty.Close() err := p.pty.Close()
err2 := p.tty.Close()
if err != nil { if err != nil {
_ = p.tty.Close() err = err2
return err
} }
err = p.tty.Close()
if err != nil { if err != nil {
return err p.err = err
} else {
p.err = xerrors.New("pty: closed")
} }
return nil
return err
} }
func (p *otherProcess) Wait() error { func (p *otherProcess) Wait() error {