lengthlimit_reader.go raw

   1  package smtp
   2  
   3  import (
   4  	"errors"
   5  	"io"
   6  )
   7  
   8  var ErrTooLongLine = errors.New("smtp: too long a line in input stream")
   9  
  10  // lineLimitReader reads from the underlying Reader but restricts
  11  // line length of lines in input stream to a certain length.
  12  //
  13  // If line length exceeds the limit - Read returns ErrTooLongLine
  14  type lineLimitReader struct {
  15  	R         io.Reader
  16  	LineLimit int
  17  
  18  	curLineLength int
  19  }
  20  
  21  func (r *lineLimitReader) Read(b []byte) (int, error) {
  22  	if r.curLineLength > r.LineLimit && r.LineLimit > 0 {
  23  		return 0, ErrTooLongLine
  24  	}
  25  
  26  	n, err := r.R.Read(b)
  27  	if err != nil {
  28  		return n, err
  29  	}
  30  
  31  	if r.LineLimit == 0 {
  32  		return n, nil
  33  	}
  34  
  35  	for _, chr := range b[:n] {
  36  		if chr == '\n' {
  37  			r.curLineLength = 0
  38  		}
  39  		r.curLineLength++
  40  
  41  		if r.curLineLength > r.LineLimit {
  42  			return 0, ErrTooLongLine
  43  		}
  44  	}
  45  
  46  	return n, nil
  47  }
  48