Example #1
0
func (rcv *TCP) handleConnection(conn net.Conn) {
	atomic.AddInt32(&rcv.active, 1)
	defer atomic.AddInt32(&rcv.active, -1)

	defer conn.Close()
	reader := bufio.NewReader(conn)

	for {
		conn.SetReadDeadline(time.Now().Add(2 * time.Minute))

		line, err := reader.ReadBytes('\n')

		if err != nil {
			if err == io.EOF {
				if len(line) > 0 {
					logrus.Warningf("[tcp] Unfinished line: %#v", line)
				}
			} else {
				atomic.AddUint32(&rcv.errors, 1)
				logrus.Error(err)
			}
			break
		}
		if len(line) > 0 { // skip empty lines
			if msg, err := points.ParseText(string(line)); err != nil {
				atomic.AddUint32(&rcv.errors, 1)
				logrus.Info(err)
			} else {
				atomic.AddUint32(&rcv.metricsReceived, 1)
				rcv.out <- msg
			}
		}
	}
}
Example #2
0
// Listen bind port. Receive messages and send to out channel
func (rcv *UDP) Listen(addr *net.UDPAddr) error {
	var err error
	rcv.conn, err = net.ListenUDP("udp", addr)
	if err != nil {
		return err
	}

	go func() {
		ticker := time.NewTicker(rcv.metricInterval)
		defer ticker.Stop()

		for {
			select {
			case <-ticker.C:
				metricsReceived := atomic.LoadUint32(&rcv.metricsReceived)
				atomic.AddUint32(&rcv.metricsReceived, -metricsReceived)
				rcv.Stat("udp.metricsReceived", float64(metricsReceived))

				incompleteReceived := atomic.LoadUint32(&rcv.incompleteReceived)
				atomic.AddUint32(&rcv.incompleteReceived, -incompleteReceived)
				rcv.Stat("udp.incompleteReceived", float64(incompleteReceived))

				errors := atomic.LoadUint32(&rcv.errors)
				atomic.AddUint32(&rcv.errors, -errors)
				rcv.Stat("udp.errors", float64(errors))

				logrus.WithFields(logrus.Fields{
					"metricsReceived":    int(metricsReceived),
					"incompleteReceived": int(incompleteReceived),
					"errors":             int(errors),
				}).Info("[udp] doCheckpoint()")

			case <-rcv.exit:
				rcv.conn.Close()
				return
			}
		}
	}()

	go func() {
		defer rcv.conn.Close()

		var buf [2048]byte

		var data *bytes.Buffer

		lines := newIncompleteStorage()

		for {
			rlen, peer, err := rcv.conn.ReadFromUDP(buf[:])
			if err != nil {
				if strings.Contains(err.Error(), "use of closed network connection") {
					break
				}
				atomic.AddUint32(&rcv.errors, 1)
				logrus.Error(err)
				continue
			}

			prev := lines.pop(peer.String())

			if prev != nil {
				data = bytes.NewBuffer(prev)
				data.Write(buf[:rlen])
			} else {
				data = bytes.NewBuffer(buf[:rlen])
			}

			for {
				line, err := data.ReadBytes('\n')

				if err != nil {
					if err == io.EOF {
						if len(line) > 0 { // incomplete line received

							if rcv.logIncomplete {
								logIncomplete(peer, buf[:rlen], line)
							}

							lines.store(peer.String(), line)
							atomic.AddUint32(&rcv.incompleteReceived, 1)
						}
					} else {
						atomic.AddUint32(&rcv.errors, 1)
						logrus.Error(err)
					}
					break
				}
				if len(line) > 0 { // skip empty lines
					if msg, err := points.ParseText(string(line)); err != nil {
						atomic.AddUint32(&rcv.errors, 1)
						logrus.Info(err)
					} else {
						atomic.AddUint32(&rcv.metricsReceived, 1)
						rcv.out <- msg
					}
				}
			}
		}

		close(rcv.finished)

	}()

	return nil
}
Example #3
0
func (rcv *UDP) receiveWorker(exit chan bool) {
	defer rcv.conn.Close()

	var buf [65535]byte

	var data *bytes.Buffer

	lines := newIncompleteStorage()

	for {
		rlen, peer, err := rcv.conn.ReadFromUDP(buf[:])
		if err != nil {
			if strings.Contains(err.Error(), "use of closed network connection") {
				break
			}
			atomic.AddUint32(&rcv.errors, 1)
			logrus.Error(err)
			continue
		}

		prev := lines.pop(peer.String())

		if prev != nil {
			data = bytes.NewBuffer(prev)
			data.Write(buf[:rlen])
		} else {
			data = bytes.NewBuffer(buf[:rlen])
		}

		for {
			line, err := data.ReadBytes('\n')

			if err != nil {
				if err == io.EOF {
					if len(line) > 0 { // incomplete line received

						if rcv.logIncomplete {
							logIncomplete(peer, buf[:rlen], line)
						}

						lines.store(peer.String(), line)
						atomic.AddUint32(&rcv.incompleteReceived, 1)
					}
				} else {
					atomic.AddUint32(&rcv.errors, 1)
					logrus.Error(err)
				}
				break
			}
			if len(line) > 0 { // skip empty lines
				if msg, err := points.ParseText(string(line)); err != nil {
					atomic.AddUint32(&rcv.errors, 1)
					logrus.Info(err)
				} else {
					atomic.AddUint32(&rcv.metricsReceived, 1)
					rcv.out <- msg
				}
			}
		}
	}
}