comparison mercurial/posix.py @ 30445:1ce4c2062ab0

posix: simplify checkexec check Use a slightly simpler logic that in some cases can avoid an unnecessary chmod and stat. Instead of flipping the X bits, make it more clear that we rely on no X bits being set on initial file creation, and that at least some of them stick after they all have been set.
author Mads Kiilerich <madski@unity3d.com>
date Wed, 14 Jan 2015 01:15:26 +0100
parents b1ce25a40826
children b324b4e431e5
comparison
equal deleted inserted replaced
30444:b1ce25a40826 30445:1ce4c2062ab0
164 if not os.path.isdir(cachedir): 164 if not os.path.isdir(cachedir):
165 cachedir = path 165 cachedir = path
166 fh, fn = tempfile.mkstemp(dir=cachedir, prefix='hg-checkexec-') 166 fh, fn = tempfile.mkstemp(dir=cachedir, prefix='hg-checkexec-')
167 try: 167 try:
168 os.close(fh) 168 os.close(fh)
169 m = os.stat(fn).st_mode & 0o777 169 m = os.stat(fn).st_mode
170 new_file_has_exec = m & EXECFLAGS 170 if m & EXECFLAGS:
171 os.chmod(fn, m ^ EXECFLAGS) 171 return False
172 exec_flags_cannot_flip = ((os.stat(fn).st_mode & 0o777) == m) 172 os.chmod(fn, m & 0o777 | EXECFLAGS)
173 return os.stat(fn).st_mode & EXECFLAGS
173 finally: 174 finally:
174 os.unlink(fn) 175 os.unlink(fn)
175 except (IOError, OSError): 176 except (IOError, OSError):
176 # we don't care, the user probably won't be able to commit anyway 177 # we don't care, the user probably won't be able to commit anyway
177 return False 178 return False
178 return not (new_file_has_exec or exec_flags_cannot_flip)
179 179
180 def checklink(path): 180 def checklink(path):
181 """check whether the given path is on a symlink-capable filesystem""" 181 """check whether the given path is on a symlink-capable filesystem"""
182 # mktemp is not racy because symlink creation will fail if the 182 # mktemp is not racy because symlink creation will fail if the
183 # file already exists 183 # file already exists