Пример #1
0
func (h *Handler) daemonSyncMaster() {
	var last *conn
	wait := make(chan int, 0)
	for exit := false; !exit; {
		var c *conn
		select {
		case <-wait:
			last = nil
		case <-h.signal:
			exit = true
		case c = <-h.master:
		}
		if last != nil {
			last.Close()
			<-wait
		}
		last = c
		if c != nil {
			go func() {
				defer func() {
					wait <- 0
				}()
				defer c.Close()
				err := h.doSyncTo(c)
				log.InfoErrorf(err, "stop sync: %s", c.summ)
			}()
			h.syncto = c.nc.RemoteAddr().String()
			log.Infof("sync to %s", h.syncto)
		} else {
			h.syncto = ""
			log.Infof("sync to no one")
		}
	}
}
Пример #2
0
func putSockConn(addr string, c *conn) {
	if c.err != nil {
		c.sock.Close()
		log.InfoErrorf(c.err, "close error connection %s : %s", addr, c.summ)
	} else {
		poolmap.Lock()
		pool := poolmap.m[addr]
		if pool == nil {
			pool = list.New()
			poolmap.m[addr] = pool
		}
		pool.PushFront(c)
		poolmap.Unlock()
	}
}
Пример #3
0
func Serve(config *Config, bl *rpdb.Rpdb) error {
	h := &Handler{
		config: config,
		master: make(chan *conn, 0),
		signal: make(chan int, 0),
	}
	defer func() {
		close(h.signal)
	}()

	l, err := net.Listen("tcp", config.Listen)
	if err != nil {
		return errors.Trace(err)
	}
	defer l.Close()

	if h.htable, err = redis.NewHandlerTable(h); err != nil {
		return err
	} else {
		go h.daemonSyncMaster()
	}

	log.Infof("open listen address '%s' and start service", l.Addr())

	for {
		if nc, err := l.Accept(); err != nil {
			return errors.Trace(err)
		} else {
			h.counters.clientsAccepted.Add(1)
			go func() {
				h.counters.clients.Add(1)
				defer h.counters.clients.Sub(1)
				c := newConn(nc, bl, h.config.ConnTimeout)
				defer c.Close()
				log.Infof("new connection: %s", c.summ)
				if err := c.serve(h); err != nil {
					if errors.Equal(err, io.EOF) {
						log.Infof("connection lost: %s [io.EOF]", c.summ)
					} else {
						log.InfoErrorf(err, "connection lost: %s", c.summ)
					}
				} else {
					log.Infof("connection exit: %s", c.summ)
				}
			}()
		}
	}
}