浏览代码

Fix connection leak. Use net.Addr.String() as freeconn map key. When the function SetServers is called the ServerList is replaced by a new set of net.Addr interfaces which no longer match those used as keys for the freeconn map. The underlying data structure is usually a TCPaddr or UnixAddr pointer. Go's equality operation on the map keys looks at the underlying pointer and thinks they are not the same so continues to create new connections assuming it does not have any free.

Asim Aslam 12 年之前
父节点
当前提交
e7a12e6eb5
共有 1 个文件被更改,包括 6 次插入6 次删除
  1. 6 6
      memcache/memcache.go

+ 6 - 6
memcache/memcache.go

@@ -133,7 +133,7 @@ type Client struct {
 	selector ServerSelector
 
 	lk       sync.Mutex
-	freeconn map[net.Addr][]*conn
+	freeconn map[string][]*conn
 }
 
 // Item is an item to be got or stored in a memcached server.
@@ -193,14 +193,14 @@ func (c *Client) putFreeConn(addr net.Addr, cn *conn) {
 	c.lk.Lock()
 	defer c.lk.Unlock()
 	if c.freeconn == nil {
-		c.freeconn = make(map[net.Addr][]*conn)
+		c.freeconn = make(map[string][]*conn)
 	}
-	freelist := c.freeconn[addr]
+	freelist := c.freeconn[addr.String()]
 	if len(freelist) >= maxIdleConnsPerAddr {
 		cn.nc.Close()
 		return
 	}
-	c.freeconn[addr] = append(freelist, cn)
+	c.freeconn[addr.String()] = append(freelist, cn)
 }
 
 func (c *Client) getFreeConn(addr net.Addr) (cn *conn, ok bool) {
@@ -209,12 +209,12 @@ func (c *Client) getFreeConn(addr net.Addr) (cn *conn, ok bool) {
 	if c.freeconn == nil {
 		return nil, false
 	}
-	freelist, ok := c.freeconn[addr]
+	freelist, ok := c.freeconn[addr.String()]
 	if !ok || len(freelist) == 0 {
 		return nil, false
 	}
 	cn = freelist[len(freelist)-1]
-	c.freeconn[addr] = freelist[:len(freelist)-1]
+	c.freeconn[addr.String()] = freelist[:len(freelist)-1]
 	return cn, true
 }