explicitly close files
authorDan Villiom Podlaski Christiansen <danchr@gmail.com>
Fri, 24 Dec 2010 15:23:01 +0100
changeset 13400 14f3795a5ed7
parent 13399 eff102facb15
child 13401 12773f1b7728
explicitly close files Add missing calls to close() to many places where files are opened. Relying on reference counting to catch them soon-ish is not portable and fails in environments with a proper GC, such as PyPy.
contrib/check-code.py
hgext/gpg.py
hgext/inotify/linux/__init__.py
hgext/mq.py
hgext/patchbomb.py
mercurial/archival.py
mercurial/cmdutil.py
mercurial/commands.py
mercurial/dirstate.py
mercurial/hgweb/common.py
mercurial/localrepo.py
mercurial/merge.py
mercurial/posix.py
mercurial/revlog.py
mercurial/statichttprepo.py
mercurial/transaction.py
mercurial/util.py
setup.py
tests/run-tests.py
--- a/contrib/check-code.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/contrib/check-code.py	Fri Dec 24 15:23:01 2010 +0100
@@ -248,7 +248,9 @@
         fc = 0
         if not re.match(match, f):
             continue
-        pre = post = open(f).read()
+        fp = open(f)
+        pre = post = fp.read()
+        fp.close()
         if "no-" + "check-code" in pre:
             break
         for p, r in filters:
--- a/hgext/gpg.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/hgext/gpg.py	Fri Dec 24 15:23:01 2010 +0100
@@ -244,7 +244,9 @@
                            "(please commit .hgsigs manually "
                            "or use --force)"))
 
-    repo.wfile(".hgsigs", "ab").write(sigmessage)
+    sigsfile = repo.wfile(".hgsigs", "ab")
+    sigsfile.write(sigmessage)
+    sigsfile.close()
 
     if '.hgsigs' not in repo.dirstate:
         repo[None].add([".hgsigs"])
--- a/hgext/inotify/linux/__init__.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/hgext/inotify/linux/__init__.py	Fri Dec 24 15:23:01 2010 +0100
@@ -26,7 +26,10 @@
 def _read_procfs_value(name):
     def read_value():
         try:
-            return int(open(procfs_path + '/' + name).read())
+            fp = open(procfs_path + '/' + name)
+            r = int(fp.read())
+            fp.close()
+            return r
         except OSError:
             return None
 
--- a/hgext/mq.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/hgext/mq.py	Fri Dec 24 15:23:01 2010 +0100
@@ -251,6 +251,7 @@
         try:
             fh = open(os.path.join(path, 'patches.queue'))
             cur = fh.read().rstrip()
+            fh.close()
             if not cur:
                 curpath = os.path.join(path, 'patches')
             else:
@@ -1781,7 +1782,9 @@
                                 _('need --name to import a patch from -'))
                         text = sys.stdin.read()
                     else:
-                        text = url.open(self.ui, filename).read()
+                        fp = url.open(self.ui, filename)
+                        text = fp.read()
+                        fp.close()
                 except (OSError, IOError):
                     raise util.Abort(_("unable to read file %s") % filename)
                 if not patchname:
@@ -1790,6 +1793,7 @@
                 checkfile(patchname)
                 patchf = self.opener(patchname, "w")
                 patchf.write(text)
+                patchf.close()
             if not force:
                 checkseries(patchname)
             if patchname not in self.series:
@@ -2787,6 +2791,7 @@
         try:
             fh = repo.opener(_allqueues, 'r')
             queues = [queue.strip() for queue in fh if queue.strip()]
+            fh.close()
             if current not in queues:
                 queues.append(current)
         except IOError:
--- a/hgext/patchbomb.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/hgext/patchbomb.py	Fri Dec 24 15:23:01 2010 +0100
@@ -261,7 +261,10 @@
         tmpfn = os.path.join(tmpdir, 'bundle')
         try:
             commands.bundle(ui, repo, tmpfn, dest, **opts)
-            return open(tmpfn, 'rb').read()
+            fp = open(tmpfn, 'rb')
+            data = fp.read()
+            fp.close()
+            return data
         finally:
             try:
                 os.unlink(tmpfn)
--- a/mercurial/archival.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/archival.py	Fri Dec 24 15:23:01 2010 +0100
@@ -84,6 +84,7 @@
 
     def __init__(self, dest, mtime, kind=''):
         self.mtime = mtime
+        self.fileobj = None
 
         def taropen(name, mode, fileobj=None):
             if kind == 'gz':
@@ -93,8 +94,10 @@
                 gzfileobj = self.GzipFileWithTime(name, mode + 'b',
                                                   zlib.Z_BEST_COMPRESSION,
                                                   fileobj, timestamp=mtime)
+                self.fileobj = gzfileobj
                 return tarfile.TarFile.taropen(name, mode, gzfileobj)
             else:
+                self.fileobj = fileobj
                 return tarfile.open(name, mode + kind, fileobj)
 
         if isinstance(dest, str):
@@ -120,6 +123,8 @@
 
     def done(self):
         self.z.close()
+        if self.fileobj:
+            self.fileobj.close()
 
 class tellable(object):
     '''provide tell method for zipfile.ZipFile when writing to http
--- a/mercurial/cmdutil.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/cmdutil.py	Fri Dec 24 15:23:01 2010 +0100
@@ -679,7 +679,9 @@
             parents.reverse()
         prev = (parents and parents[0]) or nullid
 
+        shouldclose = False
         if not fp:
+            shouldclose = True
             fp = make_file(repo, template, node, total=total, seqno=seqno,
                            revwidth=revwidth, mode='ab')
         if fp != sys.stdout and hasattr(fp, 'name'):
@@ -700,7 +702,8 @@
         for chunk in patch.diff(repo, prev, node, opts=opts):
             fp.write(chunk)
 
-        fp.flush()
+        if shouldclose:
+            fp.close()
 
     for seqno, rev in enumerate(revs):
         single(rev, seqno + 1, fp)
--- a/mercurial/commands.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/commands.py	Fri Dec 24 15:23:01 2010 +0100
@@ -750,6 +750,7 @@
         if opts.get('decode'):
             data = repo.wwritedata(abs, data)
         fp.write(data)
+        fp.close()
         err = 0
     return err
 
--- a/mercurial/dirstate.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/dirstate.py	Fri Dec 24 15:23:01 2010 +0100
@@ -80,7 +80,9 @@
     @propertycache
     def _pl(self):
         try:
-            st = self._opener("dirstate").read(40)
+            fp = self._opener("dirstate")
+            st = fp.read(40)
+            fp.close()
             l = len(st)
             if l == 40:
                 return st[:20], st[20:40]
--- a/mercurial/hgweb/common.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/hgweb/common.py	Fri Dec 24 15:23:01 2010 +0100
@@ -119,7 +119,10 @@
         os.stat(path)
         ct = mimetypes.guess_type(path)[0] or "text/plain"
         req.respond(HTTP_OK, ct, length = os.path.getsize(path))
-        return open(path, 'rb').read()
+        fp = open(path, 'rb')
+        data = fp.read()
+        fp.close()
+        return data
     except TypeError:
         raise ErrorResponse(HTTP_SERVER_ERROR, 'illegal filename')
     except OSError, err:
--- a/mercurial/localrepo.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/localrepo.py	Fri Dec 24 15:23:01 2010 +0100
@@ -283,6 +283,8 @@
         # committed tags are stored in UTF-8
         writetags(fp, names, encoding.fromlocal, prevtags)
 
+        fp.close()
+
         if '.hgtags' not in self.dirstate:
             self[None].add(['.hgtags'])
 
--- a/mercurial/merge.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/merge.py	Fri Dec 24 15:23:01 2010 +0100
@@ -32,6 +32,7 @@
                 else:
                     bits = l[:-1].split("\0")
                     self._state[bits[0]] = bits[1:]
+            f.close()
         except IOError, err:
             if err.errno != errno.ENOENT:
                 raise
@@ -42,6 +43,7 @@
             f.write(hex(self._local) + "\n")
             for d, v in self._state.iteritems():
                 f.write("\0".join([d] + v) + "\n")
+            f.close()
             self._dirty = False
     def add(self, fcl, fco, fca, fd, flags):
         hash = util.sha1(fcl.path()).hexdigest()
@@ -67,6 +69,7 @@
         state, hash, lfile, afile, anode, ofile, flags = self._state[dfile]
         f = self._repo.opener("merge/" + hash)
         self._repo.wwrite(dfile, f.read(), flags)
+        f.close()
         fcd = wctx[dfile]
         fco = octx[ofile]
         fca = self._repo.filectx(afile, fileid=anode)
--- a/mercurial/posix.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/posix.py	Fri Dec 24 15:23:01 2010 +0100
@@ -77,20 +77,26 @@
     if l:
         if not stat.S_ISLNK(s):
             # switch file to link
-            data = open(f).read()
+            fp = open(f)
+            data = fp.read()
+            fp.close()
             os.unlink(f)
             try:
                 os.symlink(data, f)
             except:
                 # failed to make a link, rewrite file
-                open(f, "w").write(data)
+                fp = open(f, "w")
+                fp.write(data)
+                fp.close()
         # no chmod needed at this point
         return
     if stat.S_ISLNK(s):
         # switch link to file
         data = os.readlink(f)
         os.unlink(f)
-        open(f, "w").write(data)
+        fp = open(f, "w")
+        fp.write(data)
+        fp.close()
         s = 0666 & ~umask # avoid restatting for chmod
 
     sx = s & 0100
--- a/mercurial/revlog.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/revlog.py	Fri Dec 24 15:23:01 2010 +0100
@@ -243,6 +243,7 @@
         try:
             f = self.opener(self.indexfile)
             i = f.read()
+            f.close()
             if len(i) > 0:
                 v = struct.unpack(versionformat, i[:4])[0]
         except IOError, inst:
@@ -1167,6 +1168,7 @@
                 if not dfh and not self._inline:
                     # addrevision switched from inline to conventional
                     # reopen the index
+                    ifh.close()
                     dfh = self.opener(self.datafile, "a")
                     ifh = self.opener(self.indexfile, "a")
         finally:
@@ -1226,6 +1228,7 @@
             f = self.opener(self.datafile)
             f.seek(0, 2)
             actual = f.tell()
+            f.close()
             dd = actual - expected
         except IOError, inst:
             if inst.errno != errno.ENOENT:
@@ -1236,6 +1239,7 @@
             f = self.opener(self.indexfile)
             f.seek(0, 2)
             actual = f.tell()
+            f.close()
             s = self._io.size
             i = max(0, actual // s)
             di = actual - (i * s)
--- a/mercurial/statichttprepo.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/statichttprepo.py	Fri Dec 24 15:23:01 2010 +0100
@@ -98,7 +98,9 @@
                 raise
             # check if it is a non-empty old-style repository
             try:
-                self.opener("00changelog.i").read(1)
+                fp = self.opener("00changelog.i")
+                fp.read(1)
+                fp.close()
             except IOError, inst:
                 if inst.errno != errno.ENOENT:
                     raise
--- a/mercurial/transaction.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/transaction.py	Fri Dec 24 15:23:01 2010 +0100
@@ -27,13 +27,17 @@
     for f, o, ignore in entries:
         if o or not unlink:
             try:
-                opener(f, 'a').truncate(o)
+                fp = opener(f, 'a')
+                fp.truncate(o)
+                fp.close()
             except IOError:
                 report(_("failed to truncate %s\n") % f)
                 raise
         else:
             try:
-                fn = opener(f).name
+                fp = opener(f)
+                fn = fp.name
+                fp.close()
                 os.unlink(fn)
             except (IOError, OSError), inst:
                 if inst.errno != errno.ENOENT:
@@ -169,7 +173,10 @@
 def rollback(opener, file, report):
     entries = []
 
-    for l in open(file).readlines():
+    fp = open(file)
+    lines = fp.readlines()
+    fp.close()
+    for l in lines:
         f, o = l.split('\0')
         entries.append((f, int(o), None))
 
--- a/mercurial/util.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/mercurial/util.py	Fri Dec 24 15:23:01 2010 +0100
@@ -198,7 +198,10 @@
         if code:
             raise Abort(_("command '%s' failed: %s") %
                         (cmd, explain_exit(code)))
-        return open(outname, 'rb').read()
+        fp = open(outname, 'rb')
+        r = fp.read()
+        fp.close()
+        return r
     finally:
         try:
             if inname:
@@ -591,7 +594,10 @@
             raise
     except AttributeError: # no symlink in os
         pass
-    return posixfile(pathname).read()
+    fp = posixfile(pathname)
+    r = fp.read()
+    fp.close()
+    return r
 
 def fstat(fp):
     '''stat file object that may not have fileno method.'''
--- a/setup.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/setup.py	Fri Dec 24 15:23:01 2010 +0100
@@ -294,14 +294,18 @@
             libdir =  uplevel * ('..' + os.sep) + self.install_lib[len(common):]
 
         for outfile in self.outfiles:
-            data = open(outfile, 'rb').read()
+            fp = open(outfile, 'rb')
+            data = fp.read()
+            fp.close()
 
             # skip binary files
             if '\0' in data:
                 continue
 
             data = data.replace('@LIBDIR@', libdir.encode('string_escape'))
-            open(outfile, 'wb').write(data)
+            fp = open(outfile, 'wb')
+            fp.write(data)
+            fp.close()
 
 cmdclass = {'build_mo': hgbuildmo,
             'build_ext': hgbuildext,
--- a/tests/run-tests.py	Fri Feb 11 22:24:10 2011 +0800
+++ b/tests/run-tests.py	Fri Dec 24 15:23:01 2010 +0100
@@ -231,6 +231,8 @@
                 if line and not line.startswith('#'):
                     blacklist[line] = filename
 
+            f.close()
+
         options.blacklist = blacklist
 
     return (options, args)
@@ -491,6 +493,8 @@
             # non-command/result - queue up for merged output
             after.setdefault(pos, []).append(l)
 
+    t.close()
+
     script.append('echo %s %s $?\n' % (salt, n + 1))
 
     fd, name = tempfile.mkstemp(suffix='hg-tst')
@@ -927,7 +931,9 @@
                 continue
 
             if options.keywords:
-                t = open(test).read().lower() + test.lower()
+                fp = open(test)
+                t = fp.read().lower() + test.lower()
+                fp.close()
                 for k in options.keywords.lower().split():
                     if k in t:
                         break