Common code used to the buildtools module (Just)
This commit is contained in:
parent
b5ae378c84
commit
015b70ec93
|
@ -6,64 +6,32 @@ It is created by copying an applet template and then adding a 'PYC '
|
|||
resource named __main__ containing the compiled, marshalled script.
|
||||
"""
|
||||
|
||||
DEBUG=0
|
||||
|
||||
import sys
|
||||
sys.stdout = sys.stderr
|
||||
|
||||
import string
|
||||
import os
|
||||
import marshal
|
||||
import imp
|
||||
import macfs
|
||||
import MACFS
|
||||
import MacOS
|
||||
from Res import *
|
||||
import macostools
|
||||
import EasyDialogs
|
||||
import buildtools
|
||||
|
||||
# .pyc file (and 'PYC ' resource magic number)
|
||||
MAGIC = imp.get_magic()
|
||||
|
||||
# Template file (searched on sys.path)
|
||||
TEMPLATE = "PythonApplet"
|
||||
|
||||
# Specification of our resource
|
||||
RESTYPE = 'PYC '
|
||||
RESNAME = '__main__'
|
||||
|
||||
# A resource with this name sets the "owner" (creator) of the destination
|
||||
# XXXX Should look for id=0
|
||||
OWNERNAME = "owner resource"
|
||||
|
||||
# OpenResFile mode parameters
|
||||
READ = 1
|
||||
WRITE = 2
|
||||
|
||||
def findtemplate():
|
||||
"""Locate the applet template along sys.path"""
|
||||
for p in sys.path:
|
||||
template = os.path.join(p, TEMPLATE)
|
||||
try:
|
||||
template, d1, d2 = macfs.ResolveAliasFile(template)
|
||||
break
|
||||
except (macfs.error, ValueError):
|
||||
continue
|
||||
else:
|
||||
die("Template %s not found on sys.path" % `TEMPLATE`)
|
||||
return
|
||||
template = template.as_pathname()
|
||||
return template
|
||||
|
||||
def main():
|
||||
global DEBUG
|
||||
DEBUG=1
|
||||
try:
|
||||
buildapplet()
|
||||
except buildtools.BuildError, detail:
|
||||
EasyDialogs.Message(detail)
|
||||
|
||||
|
||||
def buildapplet():
|
||||
buildtools.DEBUG=1
|
||||
|
||||
# Find the template
|
||||
# (there's no point in proceeding if we can't find it)
|
||||
|
||||
template = findtemplate()
|
||||
|
||||
template = buildtools.findtemplate()
|
||||
|
||||
# Ask for source text if not specified in sys.argv[1:]
|
||||
|
||||
if not sys.argv[1:]:
|
||||
|
@ -75,267 +43,24 @@ def main():
|
|||
if tf[-3:] == '.py':
|
||||
tf = tf[:-3]
|
||||
else:
|
||||
tf = tf + '.out'
|
||||
tf = tf + '.applet'
|
||||
dstfss, ok = macfs.StandardPutFile('Save application as:', tf)
|
||||
if not ok: return
|
||||
dstfilename = dstfss.as_pathname()
|
||||
cr, tp = MacOS.GetCreatorAndType(filename)
|
||||
if tp == 'APPL':
|
||||
update(template, filename, dstfilename)
|
||||
buildtools.update(template, filename, dstfilename)
|
||||
else:
|
||||
process(template, filename, dstfilename)
|
||||
buildtools.process(template, filename, dstfilename, 1)
|
||||
else:
|
||||
|
||||
# Loop over all files to be processed
|
||||
for filename in sys.argv[1:]:
|
||||
cr, tp = MacOS.GetCreatorAndType(filename)
|
||||
if tp == 'APPL':
|
||||
update(template, filename, '')
|
||||
buildtools.update(template, filename, '')
|
||||
else:
|
||||
process(template, filename, '')
|
||||
|
||||
def process(template, filename, output):
|
||||
|
||||
if DEBUG:
|
||||
progress = EasyDialogs.ProgressBar("Processing %s..."%os.path.split(filename)[1], 120)
|
||||
progress.label("Compiling...")
|
||||
else:
|
||||
progress = None
|
||||
|
||||
# Read the source and compile it
|
||||
# (there's no point overwriting the destination if it has a syntax error)
|
||||
|
||||
fp = open(filename)
|
||||
text = fp.read()
|
||||
fp.close()
|
||||
try:
|
||||
code = compile(text, filename, "exec")
|
||||
except (SyntaxError, EOFError):
|
||||
die("Syntax error in script %s" % `filename`)
|
||||
return
|
||||
|
||||
# Set the destination file name
|
||||
|
||||
if string.lower(filename[-3:]) == ".py":
|
||||
destname = filename[:-3]
|
||||
rsrcname = destname + '.rsrc'
|
||||
else:
|
||||
destname = filename + ".applet"
|
||||
rsrcname = filename + '.rsrc'
|
||||
|
||||
if output:
|
||||
destname = output
|
||||
|
||||
process_common(template, progress, code, rsrcname, destname, 0)
|
||||
|
||||
def update(template, filename, output):
|
||||
if DEBUG:
|
||||
progress = EasyDialogs.ProgressBar("Updating %s..."%os.path.split(filename)[1], 120)
|
||||
else:
|
||||
progress = None
|
||||
if not output:
|
||||
output = filename + ' (updated)'
|
||||
process_common(template, progress, None, filename, output, 1)
|
||||
|
||||
|
||||
def process_common(template, progress, code, rsrcname, destname, is_update):
|
||||
# Try removing the output file
|
||||
try:
|
||||
os.unlink(destname)
|
||||
except os.error:
|
||||
pass
|
||||
|
||||
|
||||
# Create FSSpecs for the various files
|
||||
|
||||
template_fss = macfs.FSSpec(template)
|
||||
template_fss, d1, d2 = macfs.ResolveAliasFile(template_fss)
|
||||
dest_fss = macfs.FSSpec(destname)
|
||||
|
||||
# Copy data (not resources, yet) from the template
|
||||
if DEBUG:
|
||||
progress.label("Copy data fork...")
|
||||
progress.set(10)
|
||||
|
||||
tmpl = open(template, "rb")
|
||||
dest = open(destname, "wb")
|
||||
data = tmpl.read()
|
||||
if data:
|
||||
dest.write(data)
|
||||
dest.close()
|
||||
tmpl.close()
|
||||
del dest
|
||||
del tmpl
|
||||
|
||||
# Open the output resource fork
|
||||
|
||||
if DEBUG:
|
||||
progress.label("Copy resources...")
|
||||
progress.set(20)
|
||||
try:
|
||||
output = FSpOpenResFile(dest_fss, WRITE)
|
||||
except MacOS.Error:
|
||||
CreateResFile(destname)
|
||||
output = FSpOpenResFile(dest_fss, WRITE)
|
||||
|
||||
# Copy the resources from the target specific resource template, if any
|
||||
typesfound, ownertype = [], None
|
||||
try:
|
||||
input = FSpOpenResFile(rsrcname, READ)
|
||||
except (MacOS.Error, ValueError):
|
||||
pass
|
||||
if DEBUG:
|
||||
progress.inc(50)
|
||||
else:
|
||||
if is_update:
|
||||
skip_oldfile = ['cfrg']
|
||||
else:
|
||||
skip_oldfile = []
|
||||
typesfound, ownertype = copyres(input, output, skip_oldfile, 0, progress)
|
||||
CloseResFile(input)
|
||||
|
||||
# Check which resource-types we should not copy from the template
|
||||
skiptypes = []
|
||||
if 'SIZE' in typesfound: skiptypes.append('SIZE')
|
||||
if 'BNDL' in typesfound: skiptypes = skiptypes + ['BNDL', 'FREF', 'icl4',
|
||||
'icl8', 'ics4', 'ics8', 'ICN#', 'ics#']
|
||||
skipowner = (ownertype <> None)
|
||||
|
||||
# Copy the resources from the template
|
||||
|
||||
input = FSpOpenResFile(template_fss, READ)
|
||||
dummy, tmplowner = copyres(input, output, skiptypes, skipowner, progress)
|
||||
if ownertype == None:
|
||||
ownertype = tmplowner
|
||||
CloseResFile(input)
|
||||
if ownertype == None:
|
||||
die("No owner resource found in either resource file or template")
|
||||
|
||||
# Make sure we're manipulating the output resource file now
|
||||
|
||||
UseResFile(output)
|
||||
|
||||
if code:
|
||||
# Delete any existing 'PYC ' resource named __main__
|
||||
|
||||
try:
|
||||
res = Get1NamedResource(RESTYPE, RESNAME)
|
||||
res.RemoveResource()
|
||||
except Error:
|
||||
pass
|
||||
|
||||
# Create the raw data for the resource from the code object
|
||||
if DEBUG:
|
||||
progress.label("Write PYC resource...")
|
||||
progress.set(120)
|
||||
|
||||
data = marshal.dumps(code)
|
||||
del code
|
||||
data = (MAGIC + '\0\0\0\0') + data
|
||||
|
||||
# Create the resource and write it
|
||||
|
||||
id = 0
|
||||
while id < 128:
|
||||
id = Unique1ID(RESTYPE)
|
||||
res = Resource(data)
|
||||
res.AddResource(RESTYPE, id, RESNAME)
|
||||
res.WriteResource()
|
||||
res.ReleaseResource()
|
||||
|
||||
# Close the output file
|
||||
|
||||
CloseResFile(output)
|
||||
|
||||
# Now set the creator, type and bundle bit of the destination
|
||||
dest_finfo = dest_fss.GetFInfo()
|
||||
dest_finfo.Creator = ownertype
|
||||
dest_finfo.Type = 'APPL'
|
||||
dest_finfo.Flags = dest_finfo.Flags | MACFS.kHasBundle
|
||||
dest_finfo.Flags = dest_finfo.Flags & ~MACFS.kHasBeenInited
|
||||
dest_fss.SetFInfo(dest_finfo)
|
||||
|
||||
macostools.touched(dest_fss)
|
||||
if DEBUG:
|
||||
progress.label("Done.")
|
||||
|
||||
|
||||
# Copy resources between two resource file descriptors.
|
||||
# skip a resource named '__main__' or (if skipowner is set) 'Owner resource'.
|
||||
# Also skip resources with a type listed in skiptypes.
|
||||
#
|
||||
def copyres(input, output, skiptypes, skipowner, progress=None):
|
||||
ctor = None
|
||||
alltypes = []
|
||||
UseResFile(input)
|
||||
ntypes = Count1Types()
|
||||
progress_type_inc = 50/ntypes
|
||||
for itype in range(1, 1+ntypes):
|
||||
type = Get1IndType(itype)
|
||||
if type in skiptypes:
|
||||
continue
|
||||
alltypes.append(type)
|
||||
nresources = Count1Resources(type)
|
||||
progress_cur_inc = progress_type_inc/nresources
|
||||
for ires in range(1, 1+nresources):
|
||||
res = Get1IndResource(type, ires)
|
||||
id, type, name = res.GetResInfo()
|
||||
lcname = string.lower(name)
|
||||
## if (type, lcname) == (RESTYPE, RESNAME):
|
||||
## continue # Don't copy __main__ from template
|
||||
# XXXX should look for id=0
|
||||
if lcname == OWNERNAME:
|
||||
if skipowner:
|
||||
continue # Skip this one
|
||||
else:
|
||||
ctor = type
|
||||
size = res.size
|
||||
attrs = res.GetResAttrs()
|
||||
if DEBUG and progress:
|
||||
progress.label("Copy %s %d %s"%(type, id, name))
|
||||
progress.inc(progress_cur_inc)
|
||||
res.LoadResource()
|
||||
res.DetachResource()
|
||||
UseResFile(output)
|
||||
try:
|
||||
res2 = Get1Resource(type, id)
|
||||
except MacOS.Error:
|
||||
res2 = None
|
||||
if res2:
|
||||
if DEBUG and progress:
|
||||
progress.label("Overwrite %s %d %s"%(type, id, name))
|
||||
res2.RemoveResource()
|
||||
res.AddResource(type, id, name)
|
||||
res.WriteResource()
|
||||
attrs = attrs | res.GetResAttrs()
|
||||
res.SetResAttrs(attrs)
|
||||
UseResFile(input)
|
||||
return alltypes, ctor
|
||||
|
||||
|
||||
# Show a message and exit
|
||||
|
||||
def die(str):
|
||||
message(str)
|
||||
sys.exit(1)
|
||||
|
||||
|
||||
# Show a message
|
||||
|
||||
def message(str, id = 256):
|
||||
from Dlg import *
|
||||
d = GetNewDialog(id, -1)
|
||||
if not d:
|
||||
print "Error:", `str`
|
||||
print "DLOG id =", id, "not found."
|
||||
return
|
||||
tp, h, rect = d.GetDialogItem(2)
|
||||
SetDialogItemText(h, str)
|
||||
d.SetDialogDefaultItem(1)
|
||||
while 1:
|
||||
n = ModalDialog(None)
|
||||
if n == 1: break
|
||||
del d
|
||||
buildtools.process(template, filename, '', 1)
|
||||
|
||||
|
||||
if __name__ == '__main__':
|
||||
|
|
|
@ -1,38 +1,38 @@
|
|||
(This file must be converted with BinHex 4.0)
|
||||
|
||||
:%%*eD@aN3A"`E'9d,R*cFQ-!FR0bBe*6483"!*!(#dPr5J#3"!%!!!!+2!!!#6`
|
||||
!!!%00K3J9#"S!"3J8(d4X'J4!$S"CbB5,`a1ZJ)-$$S!@RN33R9TE'4"F("XCA3
|
||||
ZFR0bBf-ZD(&iBbjSFAJZ1'*`H3!!FR0bBe*6483"!!"!!!%!N!m"Al1`(eFK!*!
|
||||
'#dRr%F#SD3%G3"(rma0`!"!Zrr1pdK&Q%&%f[P9V!3,fK[P9V!3%`86)"Caj
|
||||
%&3`!!"aP%R!!%#j$&3`!!"pL"R!"B!!"!3)X@P3Y,N5p!3!E2!&Q-#G92KT+J#"
|
||||
6!LJ![`!Z)J$Y#3)"!%#$+0Xd%kRA,`a1ZJ%*5QGV!3#Q9d-k!!!"!*!,3!!!!+!
|
||||
!!!&3!!!#U!!!"&3!!!NN!!!5P!!$rrm!"!!!J!2rr`!"!!)!!3!#!!%!!`!"!!2
|
||||
J!3!$)!%!!L!"!!)J!rrr,J3!!,i$rrm1!+`%!!'Z#!!"rK!!!"!J!!!)3!!!")!
|
||||
!!!-!N"K!!!!!i!!!!I!!!!2i!!!(r!!!$r`!!"rm!!2rr`!(rrq!!rrr!!(rrJ!
|
||||
"rri!!Irr!!(rrq!"rrmJ!Irq)!(rrL!$rrmZ"rrr[J2rr`i!rr`!!Iri!!(rm!!
|
||||
!(q!!!!r!!!!(J!!!!`#3%3T3i!!HK)!!"k%J!!!!"d&38%`!N!C!!!!"!!+!"8!
|
||||
)3$ri%"!3(K!5%"-rq`iJ$N!#J!%!N!8"!!1!"m!2`$ri(r!IrKrb(r-rq`rJ$m!
|
||||
$J!%!N!8%!*"5r`#3([m!r`#3(2m!X!$r!*!Dr`#`!,!!r`#3'2m!!!#`!2m&r`#
|
||||
3&[m!!,!!!2m&"Im!N"Ar!!#`!,!!!2m&r`#3%2q3%J#3$Im!!#X!+j!+q5[jqIm
|
||||
!N!hrN")!N!rr!!!VN!VjqIm!N"$r!!!!+j!)qIRjr`#3%2m!!#Z3#[Rjrrm!N!r
|
||||
r!!!!+j!)qIRjrj!&!*!-r`!!+j!+qIRrr`!!r`#3$2m!!!!VN!MjqIRr!!!!r`#
|
||||
3$2m!!#Z3#[Rjr`!!!2m!N![rN")!!2m!APjH!*!'r`!!+`!VN!Vj+rRjr`$rrej
|
||||
HAJ#3"rq3%J#3"&jHAJ#3#E!&X!@`X2NVN!Ajr`#3%E#`"E!&X,#`q5XV+rRr!*!
|
||||
5X*!)q5XVqIm!N"IrqC!%+rRr!*!CrrNV+rRr!*!ErrRjr`#3(Irr!*"b!J#3+3m
|
||||
!N!r`m!#3$3m&$`#3$I"382!!N!X2!!82(`#3#r!&!2%I!*!+$`"38!mI!*!)rj!
|
||||
*!*!'$`$!c*!&h0h`!*!'rj!*!*!($`$-N!AGm!#3"`m!$-c-c-hGm!#3"`m!c*!
|
||||
&hIm!N!F2!!c-c-c0hIrrm!#3"3m!c*!&hIm!m!#3"3m!$-c-c-hGm!$`!*!&$`$
|
||||
-N!AGm!$`!*!&rj!*!2#lX!!!$`$!c*!&h0h`rlZ`!!!!rj!*!!#lX!#3"&&49Gc
|
||||
-c0m!N!J&89&9AFc0m!#3#!99999Gc0m!N!X2hGh0m!#3$2h-h`#3$3rGm!#3$[m
|
||||
!N$S"!*!Br`#3$[m!r`#3$2m!X!$r!*!+r`#3"2m&!*!(rj!,!*!'r`!VN!Ajr`#
|
||||
3"rm!+j!&qIq3"!#3"2m!+j!&qIm!!2m!N!6r!#Z3"IRr!!"HAJ!!rj!,!&jH!*!
|
||||
%X,#`+b[jr`#3#E#`X#[jr`#3$2rjr`#3$[m!N"Z!!*!,$`#3"r$`!*!&$`82!*!
|
||||
&m!!2%!!!!2q3"I!!!!m-c-cI!!!!$`c-c0rrm!!2$-c-h`$`!!m-c-cI!,X!rj!
|
||||
&m,X!!&9FcI!!N!49A0m!N!Epm!#3"Jm!N!m(9%9B9!!"!*!%!3#3"!FUN!3!!J#
|
||||
3"#a3HA3a!!!!!8C548B!!J!!!)!!!3#"!!)!JNP$6L-!!J!!!5`!!3!!!!)!N!3
|
||||
"!!!!#M`!!!Nm!!!"$3FdRi3RUJ!!!"`!rJ!*3Nj%6!!!!&**3diM!!!!AP0*@N8
|
||||
!!!"U4P*&4J!#!(CTBh-M!!!!QQPME$J!!!#QD@0X0!!!!,*TBh-i!!!![QPMFc3
|
||||
!!!$+8(Pd-3!!!0B!J2rr!!!*$!FdR-!",2rr!*!%"c5G$2q3"!!!!33!N!@!rrm
|
||||
!!!%5"c5G#!#"rrm!!!Ma"c5G"!##rrm!!!N""c5FV!%Xrrm!!!%G"c5FZ!%Xrrm
|
||||
!!!&K"c5F[!%Xrrm!!!9P"c5Fb!%Xrrm!!!GT"c5FY!%Xrrm!!!KY"c5Fa!#3"JM
|
||||
m"c5G!!j2GfjPFL"bCA0[GA*MC@-!:
|
||||
:%%*eD@aN3A"`E'9d,R*cFQ-!FR0bBe*6483"!*!(#h()%3#3"!%!!!!+8!!!#9!
|
||||
!!!%K0K3J9#"S!"3J8(d4X'J4!$S"CbB5,`a1ZJ)-$$S!@RN33R9TE'4"F("XCA3
|
||||
ZFR0bBh3#!!!!8'&bG&0*9#%!N!43BA*d8dP8)3#3',(QTJ%!N!B,FIm4`+KT!4e
|
||||
!%Irc%h!!%#lrmlh5%@B386Dq9@X"!8*%[D'q9@X"!6"4-J&R(N39$!!!('85F!!
|
||||
3,N-9$!!!(f)'F!&J!!%"!LaD9#dZ4,d"!"Xm!@B`*e8q'NU!)&-#+!#r!#iL!1d
|
||||
*!J%!3)-Sfc36UGF[$%kk!3P+CfX"!+CA3cS!!!%!N!Y!!!!!S!!!!9!!!!+S!!!
|
||||
%9!!!#53!!"+8!!2rr`!%!!#!!rrr!!%!!J!"!!)!!3!$!!%!!q!"!!-J!3!#)!%
|
||||
!!L!$rrmZ"!!![J2rr`i!V!3!!Di)!!(q%!!!%#!!!!K!!!!%J!!!!`#3'%!!!!$
|
||||
J!!!"m!!!!rJ!!!Im!!!2r!!!(r`!!rrr!!Irri!$rrm!!Irq!!(rrJ!"rrm!!Ir
|
||||
ri!(rrb!"rriJ!Irq)!2rrbi(rrqq!rrr$J$rr!!"rrJ!!Ir`!!!Ii!!!$m!!!!H
|
||||
!!!!$!*!4#P$J!"k%J!!(S5!!!!!(39"36!#3"N!!!!%!!S!&3!K!2rJ3%"!H%")
|
||||
3%crl$L!13!+!!3#3"3%!!i!(`!r!2rJIm"rq(r)Imcrl$q!2`!1!!3#3"33!N&,
|
||||
r!*!Hr`$r!*!Fr`#`!2m!N"Vr!,!!X!$r!*!Br`!!!,!!r`Ar!*!@r`!!X!!!r`8
|
||||
&r`#3&Im!!,!!X!!!r`Ar!*!3rj!5!*!0r`!!+`!VN!Vj+rRjr`#3$Iq3%J#3$rm
|
||||
!!#Z3#[Rjr`#3%2m!!!!VN!MjqIRr!*!3r`!!+j!+qIRrr`#3$rm!!!!VN!MjqIR
|
||||
rN!8!N!cr!!!VN!VjqIrr!!$r!*!-r`!!!#Z3#2RjqIm!!!$r!*!-r`!!+j!+qIR
|
||||
r!!!!r`#3#rq3%J!!r`"HAPi!N!Er!!!V!#Z3#[NVqIRr!2rrAPjH!*!(rj!5!*!
|
||||
%APjH!*!*X!@`"E#`q5Z3"IRr!*!4X,!&X!@`X,$j+bXVqIm!N"+`N!Mj+b[jr`#
|
||||
3&rrjN!3VqIm!N"Rrq5XVqIm!N"[rqIRr!*!Grrm!N()#!*!T$`#3$r$`!*!0$`8
|
||||
2!*!0m&"3m!#3#`m!"3mI!*!,m!8!m4m!N!S2!&"3$am!N!MrN!N!N!B2!-$-N!A
|
||||
FhI!!N!ErN!N!N!F2!-b3"Gh`!*!($`!-c-c-cGh`!*!($`$-N!AGr`#3"`m!$-c
|
||||
-c-hGrrr`!*!&$`$-N!AGr`$`!*!&$`!-c-c-cGh`!2!!N!82!-b3"Gh`!2!!N!A
|
||||
rN!N!m,Z`!!!2!-$-N!AFhI$rZl!!!!$rN!N!!,Z`!*!%89&9h-c-h`#3#!94899
|
||||
Gc-h`!*!)"99999h-h`#3#`rGhFh`!*!-rFcI!*!0$ph`!*!1r`#31J%!N"Mr!*!
|
||||
1r`$r!*!-r`#`!2m!N!Vr!*!%r`8!N!IrN!X!N!Er!#Z3"IRr!*!(r`!VN!Ajrj!
|
||||
%!*!%r`!VN!Ajr`!!r`#3"2m!+j!&qIm!!&jH!!$rN!X!APi!N!5`X,!V+rRr!*!
|
||||
*X,#`+rRr!*!-rrRr!*!1r`#3'i!!N!X2!*!(m2!!N!82"3m!N!A`!!m3!!!!rj!
|
||||
&m!!!$`c-c0m!!!!2$-c-hrr`!!m-c-cI!2!!$`c-c0m!Z`$rN!A`Z`!!99c0m!#
|
||||
3"&9Fh`#3"[h`!*!'$`#3$`G849K8!!%!N!3"!*!%"bU3"!!#!*!%,&"jG$%!!!!
|
||||
"4P*&4J!#!!!!J!!"!)%!!J##5801)`!#!!!",!!"!!!!!J#3"4"849K8G(4iG!#
|
||||
S-$%i-3#3"!%!!!!+8!!!#9!!!!%K"Hr&G#kN!!!!(!%5!!T#6N4-!!!!@NP$6L-
|
||||
!!!"Q8dPD43!!!(*'8N9'!!)!IQPMFb-!!!#LD@0X1!!!!+jTBf`d!!!!ZQPMFcJ
|
||||
!!!$'D@0c0!!!!0*3HA3a!!!!hNG9YdN!!!$U!)$rr`!!#3`!N!3",2rr!*!)rj!
|
||||
%!!!""!A[aI3!J2rr!!!"%J#3"B(rr`!!#2%!N!@#rrm!!!N"!*!%!5crr`!!!4d
|
||||
!N!3",2rr!!!"B3#3"!%Xrrm!!!9P!*!%!5crr`!!"fN!N!3",2rr!!!)E3#3#JM
|
||||
m!*!%+!(rr`!!#6`!N!316hGZCA)JFQ9cEh9bBf8%j!:
|
||||
|
|
Loading…
Reference in New Issue