Skip to content

Commit

Permalink
Use a select to monitor stdout
Browse files Browse the repository at this point in the history
  • Loading branch information
muesli committed Jan 29, 2022
1 parent 9ff991c commit ad04dd0
Show file tree
Hide file tree
Showing 4 changed files with 17 additions and 37 deletions.
24 changes: 7 additions & 17 deletions ioctl_linux.go
Expand Up @@ -4,7 +4,7 @@
package termenv

import (
"fmt"
"syscall"
"time"

"golang.org/x/sys/unix"
Expand All @@ -14,22 +14,12 @@ func tcFlush(fd int, selector uintptr) error {
return unix.IoctlSetInt(fd, unix.TCFLSH, int(selector))
}

func waitForData(fd uintptr) error {
var avail int
var err error
func waitForData(fd uintptr, timeout time.Duration) error {
tv := syscall.NsecToTimeval(int64(timeout))

for i := 1; i < 10; i++ {
avail, err = unix.IoctlGetInt(int(fd), unix.TIOCINQ)
if err != nil || avail > 0 {
break
}
var fds syscall.FdSet
fds.Bits[0] = 1 << uint(fd)

time.Sleep(time.Duration(i*i) * time.Millisecond)
}

if avail == 0 || err != nil {
return fmt.Errorf("timeout")
}

return nil
_, err := syscall.Select(int(fd)+1, &fds, nil, nil, &tv)
return err
}
4 changes: 3 additions & 1 deletion ioctl_other.go
Expand Up @@ -4,13 +4,15 @@
package termenv

import (
"time"

"golang.org/x/sys/unix"
)

func tcFlush(fd int, selector uintptr) error {
return unix.IoctlSetInt(fd, unix.TCFLSH, int(selector))
}

func waitForData(fd uintptr) error {
func waitForData(fd uintptr, timeout time.Duration) error {
return nil
}
23 changes: 5 additions & 18 deletions ioctl_unix.go
Expand Up @@ -7,10 +7,8 @@
package termenv

import (
"fmt"
"syscall"
"time"
"unsafe"

"golang.org/x/sys/unix"
)
Expand All @@ -24,22 +22,11 @@ func tcFlush(fd int, selector uintptr) error {
return unix.IoctlSetPointerInt(fd, unix.TIOCFLUSH, int(selector))
}

func waitForData(fd uintptr) error {
var avail int
var err syscall.Errno
func waitForData(fd uintptr, timeout time.Duration) error {
tv := syscall.NsecToTimeval(int64(timeout))

for i := 1; i < 10; i++ {
_, _, err = syscall.Syscall(syscall.SYS_IOCTL, fd, _FIONREAD, uintptr(unsafe.Pointer(&avail)))
if err != 0 || avail > 0 {
break
}
var fds syscall.FdSet
fds.Bits[0] = 1 << uint(fd)

time.Sleep(time.Duration(i*i) * time.Millisecond)
}

if avail == 0 || err != 0 {
return fmt.Errorf("timeout")
}

return nil
return syscall.Select(int(fd)+1, &fds, nil, nil, &tv)
}
3 changes: 2 additions & 1 deletion termenv_unix.go
Expand Up @@ -8,6 +8,7 @@ import (
"os"
"strconv"
"strings"
"time"

"golang.org/x/sys/unix"
)
Expand Down Expand Up @@ -85,7 +86,7 @@ func backgroundColor() Color {
}

func readNextByte(f *os.File) (byte, error) {
if err := waitForData(f.Fd()); err != nil {
if err := waitForData(f.Fd(), 100*time.Millisecond); err != nil {
return 0, err
}

Expand Down

0 comments on commit ad04dd0

Please sign in to comment.