From 3b6de5e847bb8bf12f2299e2026ebf35c2026463 Mon Sep 17 00:00:00 2001 From: Dmitriy Vyukov Date: Tue, 30 Jul 2013 19:47:16 +0400 Subject: [PATCH] net: fix memory leak on unix If netFD is closed by finalizer, runtime netpoll descriptor is not freed. R=golang-dev, dave, alex.brainman CC=golang-dev https://golang.org/cl/12037043 --- src/pkg/net/fd_unix.go | 14 +++++--------- 1 file changed, 5 insertions(+), 9 deletions(-) diff --git a/src/pkg/net/fd_unix.go b/src/pkg/net/fd_unix.go index 4012e36d37..5f8a6705df 100644 --- a/src/pkg/net/fd_unix.go +++ b/src/pkg/net/fd_unix.go @@ -9,6 +9,7 @@ package net import ( "io" "os" + "runtime" "sync" "syscall" "time" @@ -29,7 +30,6 @@ type netFD struct { family int sotype int isConnected bool - sysfile *os.File net string laddr Addr raddr Addr @@ -70,7 +70,7 @@ func newFD(fd, family, sotype int, net string) (*netFD, error) { func (fd *netFD) setAddr(laddr, raddr Addr) { fd.laddr = laddr fd.raddr = raddr - fd.sysfile = os.NewFile(uintptr(fd.sysfd), fd.net) + runtime.SetFinalizer(fd, (*netFD).Close) } func (fd *netFD) name() string { @@ -129,15 +129,11 @@ func (fd *netFD) decref() { fd.sysref-- if fd.closing && fd.sysref == 0 { // Poller may want to unregister fd in readiness notification mechanism, - // so this must be executed before sysfile.Close(). + // so this must be executed before closesocket. fd.pd.Close() - if fd.sysfile != nil { - fd.sysfile.Close() - fd.sysfile = nil - } else { - closesocket(fd.sysfd) - } + closesocket(fd.sysfd) fd.sysfd = -1 + runtime.SetFinalizer(fd, nil) } fd.sysmu.Unlock() }