Advertisement
Guest User

Untitled

a guest
Oct 26th, 2022
295
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 1.91 KB | None | 0 0
  1. package main
  2.  
  3. import (
  4. "bytes"
  5. "errors"
  6. "fmt"
  7. "io"
  8. "os"
  9. "runtime"
  10. "sync"
  11. "time"
  12.  
  13. "github.com/valyala/bytebufferpool"
  14. )
  15.  
  16. var bufferPool = sync.Pool{
  17. New: func() interface{} {
  18. b := make([]byte, 4096)
  19. return &b
  20. },
  21. }
  22.  
  23. func main() {
  24. //print infinite current number of goroutines
  25. go func() {
  26. for {
  27. time.Sleep(time.Second * 2)
  28. fmt.Println(runtime.NumGoroutine())
  29. }
  30. }()
  31. //spawn infinite goroutines of receive
  32. for {
  33. go func() {
  34. bb := bytebufferpool.Get()
  35. defer bytebufferpool.Put(bb)
  36. err := Receive(bb, []byte("#"), time.Second*2)
  37. if err != nil {
  38. fmt.Println(err)
  39. }
  40. }()
  41. time.Sleep(time.Second * 4)
  42. }
  43. runtime.Goexit()
  44.  
  45. }
  46. func Receive(bb *bytebufferpool.ByteBuffer, delimiter []byte, timeout time.Duration) (err error) {
  47. rx := os.Stdin
  48. rx.SetDeadline(time.Now().Add(time.Second * 4))
  49. donec := make(chan error, 1)
  50. cancelc := make(chan struct{}, 1)
  51. go func() {
  52. donec <- receive(cancelc, rx, bb, delimiter)
  53. }()
  54.  
  55. select {
  56. case err = <-donec:
  57. break
  58. case <-time.After(timeout):
  59. cancelc <- struct{}{}
  60. return errors.New("timeout")
  61. }
  62. return err
  63. }
  64.  
  65. //receive reads from s till the delimiter is reached
  66. func receive(cancelc chan struct{}, s io.Reader, bb *bytebufferpool.ByteBuffer, delimiter []byte) error {
  67.  
  68. buf := bufferPool.Get().(*[]byte)
  69. defer bufferPool.Put(buf)
  70. b := *buf
  71. for {
  72. select {
  73. case <-cancelc:
  74. return errors.New("timeout")
  75. default:
  76. n, err := s.Read(b) // read block infinite if no data is ever send
  77. //How to stop it?
  78.  
  79. if n > 0 {
  80. bb.Write(b[:n])
  81. if err != nil {
  82. if err == io.EOF {
  83. if i := bytes.Index(bb.Bytes(), delimiter); i != -1 {
  84. bb.Set(bb.Bytes()[:i])
  85. return nil
  86. }
  87. }
  88. return err
  89. }
  90.  
  91. if i := bytes.Index(bb.Bytes(), delimiter); i != -1 {
  92. bb.Set(bb.Bytes()[:i])
  93. return nil
  94. }
  95. }
  96. }
  97. }
  98. }
  99.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement