mirror of
https://github.com/python/cpython.git
synced 2024-11-30 21:34:17 +08:00
If a resource file cannot be decoded because the directory is readonly
create a temporary file. This fixes #688011. Got rid of the install() method in macresource, and replaced it with a resource_filename() method which will optionally decode a given resourcefile (which may be applesingle-encoded) and return the real resourcefile. Use this new method in buildtools to copy the correct resource file to the bundle. This fixes #688007.
This commit is contained in:
parent
ade626464d
commit
cba861e5e3
@ -299,7 +299,9 @@ def process_common_macho(template, progress, code, rsrcname, destname, is_update
|
||||
builder.builddir = destdir
|
||||
builder.name = shortname
|
||||
if rsrcname:
|
||||
builder.resources.append(rsrcname)
|
||||
realrsrcname = macresource.resource_pathname(rsrcname)
|
||||
builder.files.append((realrsrcname,
|
||||
os.path.join('Contents/Resources', os.path.basename(rsrcname))))
|
||||
for o in others:
|
||||
if type(o) == str:
|
||||
builder.resources.append(o)
|
||||
|
@ -96,56 +96,51 @@ def open_pathname(pathname, verbose=0):
|
||||
raise
|
||||
return refno
|
||||
|
||||
def open_error_resource():
|
||||
"""Open the resource file containing the error code to error message
|
||||
mapping."""
|
||||
need('Estr', 1, filename="errors.rsrc", modname=__name__)
|
||||
|
||||
def _decode(pathname, verbose=0, newpathname=None):
|
||||
# Decode an AppleSingle resource file, return the new pathname.
|
||||
if not newpathname:
|
||||
newpathname = pathname + '.df.rsrc'
|
||||
if os.path.exists(newpathname) and \
|
||||
os.stat(newpathname).st_mtime >= os.stat(pathname).st_mtime:
|
||||
return newpathname
|
||||
if verbose:
|
||||
print 'Decoding', pathname
|
||||
import applesingle
|
||||
applesingle.decode(pathname, newpathname, resonly=1)
|
||||
return newpathname
|
||||
|
||||
def install(src, dst, mkdirs=0):
|
||||
"""Copy a resource file. The result will always be a datafork-based
|
||||
resource file, whether the source is datafork-based, resource-fork
|
||||
based or AppleSingle-encoded."""
|
||||
if mkdirs:
|
||||
macostools.mkdirs(os.path.split(dst)[0])
|
||||
def resource_pathname(pathname, verbose=0):
|
||||
"""Return the pathname for a resource file (either DF or RF based).
|
||||
If the pathname given already refers to such a file simply return it,
|
||||
otherwise first decode it."""
|
||||
try:
|
||||
refno = Res.FSOpenResourceFile(src, u'', 1)
|
||||
refno = Res.FSpOpenResFile(pathname, 1)
|
||||
Res.CloseResFile(refno)
|
||||
except Res.Error, arg:
|
||||
if arg[0] in (-37, -39):
|
||||
# No resource fork. We may be on OSX, and this may be either
|
||||
# a data-fork based resource file or a AppleSingle file
|
||||
# from the CVS repository.
|
||||
try:
|
||||
refno = Res.FSOpenResourceFile(pathname, u'', 1)
|
||||
except Res.Error, arg:
|
||||
if arg[0] != -199:
|
||||
# -199 is "bad resource map"
|
||||
raise
|
||||
else:
|
||||
# Resource-fork based. Simply copy.
|
||||
Res.CloseResFile(refno)
|
||||
macostools.copy(src, dst)
|
||||
|
||||
try:
|
||||
refno = Res.FSpOpenResFile(src, 1)
|
||||
except Res.Error, arg:
|
||||
if not arg[0] in (-37, -39):
|
||||
raise
|
||||
return refno
|
||||
# Finally try decoding an AppleSingle file
|
||||
pathname = _decode(pathname, verbose=verbose)
|
||||
else:
|
||||
Res.CloseResFile(refno)
|
||||
BUFSIZ=0x80000 # Copy in 0.5Mb chunks
|
||||
ifp = MacOS.openrf(src, '*rb')
|
||||
ofp = open(dst, 'wb')
|
||||
d = ifp.read(BUFSIZ)
|
||||
while d:
|
||||
ofp.write(d)
|
||||
d = ifp.read(BUFSIZ)
|
||||
ifp.close()
|
||||
ofp.close()
|
||||
raise
|
||||
return pathname
|
||||
|
||||
_decode(src, newpathname=dst)
|
||||
def open_error_resource():
|
||||
"""Open the resource file containing the error code to error message
|
||||
mapping."""
|
||||
need('Estr', 1, filename="errors.rsrc", modname=__name__)
|
||||
|
||||
def _decode(pathname, verbose=0):
|
||||
# Decode an AppleSingle resource file, return the new pathname.
|
||||
newpathname = pathname + '.df.rsrc'
|
||||
if os.path.exists(newpathname) and \
|
||||
os.stat(newpathname).st_mtime >= os.stat(pathname).st_mtime:
|
||||
return newpathname
|
||||
if hasattr(os, 'access') and not \
|
||||
os.access(os.path.dirname(pathname), os.W_OK|os.X_OK):
|
||||
# The destination directory isn't writeable. Create the file in
|
||||
# a temporary directory
|
||||
import tempfile
|
||||
fd, newpathname = tempfile.mkstemp(".rsrc")
|
||||
if verbose:
|
||||
print 'Decoding', pathname, 'to', newpathname
|
||||
import applesingle
|
||||
applesingle.decode(pathname, newpathname, resonly=1)
|
||||
return newpathname
|
||||
|
Loading…
Reference in New Issue
Block a user