@zip.js/zip.js 2.8.29 → 2.8.30
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/BENCHMARKS.md +35 -0
- package/deno.json +1 -1
- package/dist/zip-core.js +527 -48
- package/dist/zip-core.min.js +1 -1
- package/dist/zip-fs-core.js +413 -48
- package/dist/zip-fs-core.min.js +1 -1
- package/dist/zip-fs-native.js +589 -52
- package/dist/zip-fs-native.min.js +1 -1
- package/dist/zip-fs.js +587 -50
- package/dist/zip-fs.min.js +1 -1
- package/dist/zip-legacy.js +528 -49
- package/dist/zip-legacy.min.js +1 -1
- package/dist/zip-module.wasm +0 -0
- package/dist/zip-native.js +531 -52
- package/dist/zip-native.min.js +1 -1
- package/dist/zip-web-worker-native.js +1 -1
- package/dist/zip-web-worker.js +1 -1
- package/dist/zip.js +529 -50
- package/dist/zip.min.js +1 -1
- package/index-native.cjs +589 -52
- package/index-native.min.js +1 -1
- package/index.cjs +587 -50
- package/index.d.ts +126 -1
- package/index.min.js +1 -1
- package/lib/core/options.js +11 -1
- package/lib/core/streams/codecs/crc32.js +39 -11
- package/lib/core/streams/zip-entry-stream.js +85 -5
- package/lib/core/streams/zlib-js/zlib-streams.min.js +1 -1
- package/lib/core/streams/zlib-wasm/zlib-streams.wasm +0 -0
- package/lib/core/util/opfs-temp-stream.js +175 -0
- package/lib/core/web-worker-inline-native.js +1 -1
- package/lib/core/web-worker-inline-wasm.js +1 -1
- package/lib/core/zip-fs.js +58 -0
- package/lib/core/zip-reader.js +219 -31
- package/lib/core/zip-writer.js +11 -0
- package/lib/core/zlib-streams-inline.js +1 -1
- package/lib/zip-core-base.js +4 -1
- package/package.json +1 -1
package/index.cjs
CHANGED
|
@@ -205,7 +205,7 @@ function setIfDefined(propertyName, propertyValue) {
|
|
|
205
205
|
}
|
|
206
206
|
}
|
|
207
207
|
|
|
208
|
-
function t(t){const e='(t=>{"function"==typeof define&&define.amd?define(t):t()})(function(){"use strict";const{Array:t,Object:e,Number:n,Math:s,Error:r,Uint8Array:o,Uint16Array:i,Uint32Array:a,Int32Array:c,Map:l,DataView:w,Promise:f,TextEncoder:h,crypto:u,postMessage:p,TransformStream:d,ReadableStream:y,WritableStream:m,CompressionStream:g,DecompressionStream:S}=self,b=void 0,k="undefined",v="function",z=[];for(let t=0;256>t;t++){let e=t;for(let t=0;8>t;t++)1&e?e=e>>>1^3988292384:e>>>=1;z[t]=e}class C{constructor(t){this.t=t||-1}append(t){let e=0|this.t;for(let n=0,s=0|t.length;s>n;n++)e=e>>>8^z[255&(e^t[n])];this.t=e}get(){return~this.t}}class I extends d{constructor(){let t;const e=new C;super({transform(t,n){e.append(t),n.enqueue(t)},flush(){const n=new o(4);new w(n.buffer).setUint32(0,e.get()),t.value=n}}),t=this}}const A={concat(t,e){if(0===t.length||0===e.length)return t.concat(e);const n=t[t.length-1],s=A.o(n);return 32===s?t.concat(e):A.i(e,s,0|n,t.slice(0,t.length-1))},l(t){const e=t.length;if(0===e)return 0;const n=t[e-1];return 32*(e-1)+A.o(n)},h(t,e){if(32*t.length<e)return t;const n=(t=t.slice(0,s.ceil(e/32))).length;return e&=31,n>0&&e&&(t[n-1]=A.u(e,t[n-1]&2147483648>>e-1,1)),t},u:(t,e,n)=>32===t?e:(n?0|e:e<<32-t)+1099511627776*t,o:t=>s.round(t/1099511627776)||32,i(t,e,n,s){for(void 0===s&&(s=[]);e>=32;e-=32)s.push(n),n=0;if(0===e)return s.concat(t);for(let r=0;r<t.length;r++)s.push(n|t[r]>>>e),n=t[r]<<32-e;const r=t.length?t[t.length-1]:0,o=A.o(r);return s.push(A.u(e+o&31,e+o>32?n:s.pop(),1)),s}},P={bytes:{p(t){const e=A.l(t)/8,n=new o(e);let s;for(let r=0;e>r;r++)3&r||(s=t[r/4]),n[r]=s>>>24,s<<=8;return n},m(t){const e=[];let n,s=0;for(n=0;n<t.length;n++)s=s<<8|t[n],3&~n||(e.push(s),s=0);return 3&n&&e.push(A.u(8*(3&n),s)),e}}},x=class{constructor(t){const e=this;e.blockSize=512,e.S=[1732584193,4023233417,2562383102,271733878,3285377520],e.k=[1518500249,1859775393,2400959708,3395469782],t?(e.v=t.v.slice(0),e.C=t.C.slice(0),e.I=t.I):e.reset()}reset(){const t=this;return t.v=t.S.slice(0),t.C=[],t.I=0,t}update(t){const e=this;"string"==typeof t&&(t=P.A.m(t));const n=e.C=A.concat(e.C,t),s=e.I,o=e.I=s+A.l(t);if(o>9007199254740991)throw new r("Cannot hash more than 2^53 - 1 bits");const i=new a(n);let c=0;for(let t=e.blockSize+s-(e.blockSize+s&e.blockSize-1);o>=t;t+=e.blockSize)e.P(i.subarray(16*c,16*(c+1))),c+=1;return n.splice(0,16*c),e}R(){const t=this;let e=t.C;const n=t.v;e=A.concat(e,[A.u(1,1)]);for(let t=e.length+2;15&t;t++)e.push(0);for(e.push(s.floor(t.I/4294967296)),e.push(0|t.I);e.length;)t.P(e.splice(0,16));return t.reset(),n}U(t,e,n,s){return t>19?t>39?t>59?t>79?void 0:e^n^s:e&n|e&s|n&s:e^n^s:e&n|~e&s}W(t,e){return e<<t|e>>>32-t}P(e){const n=this,r=n.v,o=t(80);for(let t=0;16>t;t++)o[t]=e[t];let i=r[0],a=r[1],c=r[2],l=r[3],w=r[4];for(let t=0;79>=t;t++){16>t||(o[t]=n.W(1,o[t-3]^o[t-8]^o[t-14]^o[t-16]));const e=n.W(5,i)+n.U(t,a,c,l)+w+o[t]+n.k[s.floor(t/20)]|0;w=l,l=c,c=n.W(30,a),a=i,i=e}r[0]=r[0]+i|0,r[1]=r[1]+a|0,r[2]=r[2]+c|0,r[3]=r[3]+l|0,r[4]=r[4]+w|0}},R={importKey:t=>new R.D(P.bytes.m(t)),M(t,e,n,s){if(n=n||1e4,0>s||0>n)throw new r("invalid params to pbkdf2");const o=1+(s>>5)<<2;let i,a,c,l,f;const h=new ArrayBuffer(o),u=new w(h);let p=0;const d=A;for(e=P.bytes.m(e),f=1;(o||1)>p;f++){for(i=a=t.encrypt(d.concat(e,[f])),c=1;n>c;c++)for(a=t.encrypt(a),l=0;l<a.length;l++)i[l]^=a[l];for(c=0;(o||1)>p&&c<i.length;c++)u.setInt32(p,i[c]),p+=4}return h.slice(0,s/8)},D:class{constructor(t){const e=this,n=e.V=x,s=[[],[]];e._=[new n,new n];const r=e._[0].blockSize/32;t.length>r&&(t=(new n).update(t).R());for(let e=0;r>e;e++)s[0][e]=909522486^t[e],s[1][e]=1549556828^t[e];e._[0].update(s[0]),e._[1].update(s[1]),e.B=new n(e._[0])}reset(){const t=this;t.B=new t.V(t._[0]),t.T=!1}update(t){this.T=!0,this.B.update(t)}digest(){const t=this,e=t.B.R(),n=new t.V(t._[1]).update(e).R();return t.reset(),n}encrypt(t){if(this.T)throw new r("encrypt on already updated hmac called!");return this.update(t),this.digest(t)}}},U=typeof u!=k&&typeof u.getRandomValues==v,W="Invalid password",D="Invalid signature",M="zipjs-abort-check-password";function V(t){if(U)return u.getRandomValues(t);throw new r("Crypto API not supported")}const _=16,B={name:"PBKDF2"},T=e.assign({hash:{name:"HMAC"}},B),K=e.assign({iterations:1e3,hash:{name:"SHA-1"}},B),j=["deriveBits"],E=[8,12,16],L=[16,24,32],O=10,H=[0,0,0,0],Z=typeof u!=k,F=Z&&u.subtle,N=Z&&typeof F!=k,q=P.bytes,G=class{constructor(t){const e=this;e.K=[[[],[],[],[],[]],[[],[],[],[],[]]],e.K[0][0][0]||e.j();const n=e.K[0][4],s=e.K[1],o=t.length;let i,a,c,l=1;if(4!==o&&6!==o&&8!==o)throw new r("invalid aes key size");for(e.k=[a=t.slice(0),c=[]],i=o;4*o+28>i;i++){let t=a[i-1];(i%o===0||8===o&&i%o===4)&&(t=n[t>>>24]<<24^n[t>>16&255]<<16^n[t>>8&255]<<8^n[255&t],i%o===0&&(t=t<<8^t>>>24^l<<24,l=l<<1^283*(l>>7))),a[i]=a[i-o]^t}for(let t=0;i;t++,i--){const e=a[3&t?i:i-4];c[t]=4>=i||4>t?e:s[0][n[e>>>24]]^s[1][n[e>>16&255]]^s[2][n[e>>8&255]]^s[3][n[255&e]]}}encrypt(t){return this.L(t,0)}decrypt(t){return this.L(t,1)}j(){const t=this.K[0],e=this.K[1],n=t[4],s=e[4],r=[],o=[];let i,a,c,l;for(let t=0;256>t;t++)o[(r[t]=t<<1^283*(t>>7))^t]=t;for(let w=i=0;!n[w];w^=a||1,i=o[i]||1){let o=i^i<<1^i<<2^i<<3^i<<4;o=o>>8^255&o^99,n[w]=o,s[o]=w,l=r[c=r[a=r[w]]];let f=16843009*l^65537*c^257*a^16843008*w,h=257*r[o]^16843008*o;for(let n=0;4>n;n++)t[n][w]=h=h<<24^h>>>8,e[n][o]=f=f<<24^f>>>8}for(let n=0;5>n;n++)t[n]=t[n].slice(0),e[n]=e[n].slice(0)}L(t,e){if(4!==t.length)throw new r("invalid aes block size");const n=this.k[e],s=n.length/4-2,o=[0,0,0,0],i=this.K[e],a=i[0],c=i[1],l=i[2],w=i[3],f=i[4];let h,u,p,d=t[0]^n[0],y=t[e?3:1]^n[1],m=t[2]^n[2],g=t[e?1:3]^n[3],S=4;for(let t=0;s>t;t++)h=a[d>>>24]^c[y>>16&255]^l[m>>8&255]^w[255&g]^n[S],u=a[y>>>24]^c[m>>16&255]^l[g>>8&255]^w[255&d]^n[S+1],p=a[m>>>24]^c[g>>16&255]^l[d>>8&255]^w[255&y]^n[S+2],g=a[g>>>24]^c[d>>16&255]^l[y>>8&255]^w[255&m]^n[S+3],S+=4,d=h,y=u,m=p;for(let t=0;4>t;t++)o[e?3&-t:t]=f[d>>>24]<<24^f[y>>16&255]<<16^f[m>>8&255]<<8^f[255&g]^n[S++],h=d,d=y,y=m,m=g,g=h;return o}},J=class{constructor(t,e){this.O=t,this.H=e,this.Z=e}reset(){this.Z=this.H}update(t){return this.F(this.O,t,this.Z)}N(t){if(255&~(t>>24))t+=1<<24;else{let e=t>>16&255,n=t>>8&255,s=255&t;255===e?(e=0,255===n?(n=0,255===s?s=0:++s):++n):++e,t=0,t+=e<<16,t+=n<<8,t+=s}return t}q(t){0===(t[0]=this.N(t[0]))&&(t[1]=this.N(t[1]))}F(t,e,n){let s;if(!(s=e.length))return[];const r=A.l(e);for(let r=0;s>r;r+=4){this.q(n);const s=t.encrypt(n);e[r]^=s[0],e[r+1]^=s[1],e[r+2]^=s[2],e[r+3]^=s[3]}return A.h(e,r)}},Q=R.D;let X=Z&&N&&typeof F.importKey==v,Y=Z&&N&&typeof F.deriveBits==v;class $ extends d{constructor({password:t,rawPassword:n,encryptionStrength:s,checkPasswordOnly:i}){super({start(){e.assign(this,{ready:new f(t=>this.G=t),password:st(t,n),J:s-1,pending:new o})},async transform(t,e){const n=this,{password:s,J:a,G:c,ready:l}=n;s?(await(async(t,e,n,s)=>{const o=await nt(t,e,n,ot(s,0,E[e])),i=ot(s,E[e]);if(o[0]!=i[0]||o[1]!=i[1])throw new r(W)})(n,a,s,ot(t,0,E[a]+2)),t=ot(t,E[a]+2),i?e.error(new r(M)):c()):await l;const w=new o(t.length-O-(t.length-O)%_);e.enqueue(et(n,t,w,0,O,!0))},async flush(t){const{X:e,Y:n,pending:s,ready:i}=this;if(n&&e){await i;const a=ot(s,0,s.length-O),c=ot(s,s.length-O);let l=new o;if(a.length){const t=at(q,a);n.update(t);const s=e.update(t);l=it(q,s)}const w=ot(it(q,n.digest()),0,O);let f=s.length<O?1:0;for(let t=0;O>t;t++)f|=w[t]^c[t];if(f)throw new r(D);t.enqueue(l)}}})}}class tt extends d{constructor({password:t,rawPassword:n,encryptionStrength:s}){let r;super({start(){e.assign(this,{ready:new f(t=>this.G=t),password:st(t,n),J:s-1,pending:new o})},async transform(t,e){const n=this,{password:s,J:r,G:i,ready:a}=n;let c=new o;s?(c=await(async(t,e,n)=>{const s=V(new o(E[e]));return rt(s,await nt(t,e,n,s))})(n,r,s),i()):await a;const l=new o(c.length+t.length-t.length%_);l.set(c,0),e.enqueue(et(n,t,l,c.length,0))},async flush(t){const{X:e,Y:n,pending:s,ready:i}=this;if(n&&e){await i;let a=new o;if(s.length){const t=e.update(at(q,s));n.update(t),a=it(q,t)}r.signature=it(q,n.digest()).slice(0,O),t.enqueue(rt(a,r.signature))}}}),r=this}}function et(t,e,n,s,r,i){const{X:a,Y:c,pending:l}=t;l.length&&(e=rt(l,e));const w=e.length-r;let f;for(n=((t,e)=>{if(e&&e>t.length){const n=t;(t=new o(e)).set(n,0)}return t})(n,s+(w-w%_)),f=0;w-_>=f;f+=_){const t=at(q,ot(e,f,f+_));i&&c.update(t);const r=a.update(t);i||c.update(r),n.set(it(q,r),f+s)}return t.pending=ot(e,f),n}async function nt(n,s,r,i){n.password=null;const a=await(async(t,e,n,s,r)=>{if(!X)return R.importKey(e);try{return await F.importKey("raw",e,n,!1,r)}catch{return X=!1,R.importKey(e)}})(0,r,T,0,j),c=await(async(t,e,n)=>{if(!Y)return R.M(e,t.salt,K.iterations,n);try{return await F.deriveBits(t,e,n)}catch{return Y=!1,R.M(e,t.salt,K.iterations,n)}})(e.assign({salt:i},K),a,8*(2*L[s]+2)),l=new o(c),w=at(q,ot(l,0,L[s])),f=at(q,ot(l,L[s],2*L[s])),h=ot(l,2*L[s]);return e.assign(n,{keys:{key:w,$:f,passwordVerification:h},X:new J(new G(w),t.from(H)),Y:new Q(f)}),h}function st(t,e){return e===b?(t=>{if(typeof h==k){const e=new o((t=unescape(encodeURIComponent(t))).length);for(let n=0;n<e.length;n++)e[n]=t.charCodeAt(n);return e}return(new h).encode(t)})(t):e}function rt(t,e){let n=t;return t.length+e.length&&(n=new o(t.length+e.length),n.set(t,0),n.set(e,t.length)),n}function ot(t,e,n){return t.subarray(e,n)}function it(t,e){return t.p(e)}function at(t,e){return t.m(e)}class ct extends d{constructor({password:t,rawPassword:n,passwordVerification:s,checkPasswordOnly:o}){super({start(){e.assign(this,{password:t,rawPassword:n,passwordVerification:s}),ht(this,t,n)},transform(t,e){const n=this;if(n.password||n.rawPassword){const e=wt(n,t.subarray(0,12));if(n.password=n.rawPassword=null,0!=(e.at(-1)^n.passwordVerification))throw new r(W);t=t.subarray(12)}o?e.error(new r(M)):e.enqueue(wt(n,t))}})}}class lt extends d{constructor({password:t,rawPassword:n,passwordVerification:s}){super({start(){e.assign(this,{password:t,rawPassword:n,passwordVerification:s}),ht(this,t,n)},transform(t,e){const n=this;let s,r;if(n.password||n.rawPassword){n.password=n.rawPassword=null;const e=V(new o(12));e[11]=n.passwordVerification,s=new o(t.length+e.length),s.set(ft(n,e),0),r=12}else s=new o(t.length),r=0;s.set(ft(n,t),r),e.enqueue(s)}})}}function wt(t,e){const n=new o(e.length);for(let s=0;s<e.length;s++)n[s]=pt(t)^e[s],ut(t,n[s]);return n}function ft(t,e){const n=new o(e.length);for(let s=0;s<e.length;s++)n[s]=pt(t)^e[s],ut(t,e[s]);return n}function ht(t,n,s){const r=[305419896,591751049,878082192];if(e.assign(t,{keys:r,tt:new C(r[0]),et:new C(r[2])}),s)for(let e=0;e<s.length;e++)ut(t,s[e]);else for(let e=0;e<n.length;e++)ut(t,n.charCodeAt(e))}function ut(t,e){let[,n]=t.keys;t.tt.append([e]);const r=~t.tt.get();n=yt(s.imul(yt(n+dt(r)),134775813)+1),t.et.append([n>>>24]);const o=~t.et.get();t.keys=[r,n,o]}function pt(t){const e=2|t.keys[2];return dt(s.imul(e,1^e)>>>8)}function dt(t){return 255&t}function yt(t){return 4294967295&t}class mt extends d{constructor(t,{chunkSize:e,nt:n,CompressionStream:s}){super({});const{compressed:r,encrypted:o,useCompressionStream:i,zipCrypto:a,signed:c,level:l}=t,f=this;let h,u,p=super.readable;o&&!a||!c||(h=new I,p=kt(p,h)),r&&(p=bt(p,i,{level:l,chunkSize:e},s,n,s)),o&&(a?p=kt(p,new lt(t)):(u=new tt(t),p=kt(p,u))),St(f,p,()=>{let t;o&&!a&&(t=u.signature),o&&!a||!c||(t=new w(h.value.buffer).getUint32(0)),f.signature=t})}}class gt extends d{constructor(t,{chunkSize:e,st:n,DecompressionStream:s}){super({});const{zipCrypto:o,encrypted:i,signed:a,signature:c,compressed:l,useCompressionStream:f,deflate64:h}=t;let u,p,d=super.readable;i&&(o?d=kt(d,new ct(t)):(p=new $(t),d=kt(d,p))),l&&(d=bt(d,f,{chunkSize:e,deflate64:h},s,n,s),d=(t=>{const e=t.getReader();return new y({async pull(t){let n;try{n=await e.read()}catch(t){if(t&&t.message)throw t;const e=new r("Invalid compressed data");throw e.cause=t,e}const{value:s,done:o}=n;o?t.close():t.enqueue(s)},cancel:t=>e.cancel(t)})})(d)),i&&!o||!a||(u=new I,d=kt(d,u)),St(this,d,()=>{if((!i||o)&&a){const t=new w(u.value.buffer);if(c!=t.getUint32(0,!1))throw new r(D)}})}}function St(t,n,s){n=kt(n,new d({flush:s})),e.defineProperty(t,"readable",{get:()=>n})}function bt(t,e,n,s,r,o){const i=e&&s?s:r||o,a=n.deflate64?"deflate64-raw":"deflate-raw";let c;try{c=new i(a,n)}catch(t){if(!e)throw t;if(r)c=new r(a,n);else{if(!o)throw t;c=new o(a,n)}}return((t,e)=>{const n=e.writable.getWriter(),s=t.getReader();return(async()=>{try{for(;;){await n.ready;const t=await s.read();if(t.done){await n.close();break}await n.write(t.value)}}catch(t){await(async(t,e)=>{try{await t.abort(e)}catch{}})(n,t),await(async(t,e)=>{try{await t.cancel(e)}catch{}})(s,t)}})(),e.readable})(t,c)}function kt(t,e){return t.pipeThrough(e)}const vt="data",zt="close";class Ct extends d{constructor(t,n){super({});const s=this,{codecType:o}=t;let i;o.startsWith("deflate")?i=mt:o.startsWith("inflate")&&(i=gt),s.outputSize=0;let a=0;const c=new i(t,n),l=super.readable,w=new d({transform(t,e){t&&t.length&&(a+=t.length,e.enqueue(t))},flush(){e.assign(s,{inputSize:a})}}),f=new d({transform(e,n){if(e&&e.length&&(n.enqueue(e),s.outputSize+=e.length,t.outputSize!==b&&s.outputSize>t.outputSize))throw new r("Invalid uncompressed size")},flush(){const{signature:t}=c;e.assign(s,{signature:t,inputSize:a})}});e.defineProperty(s,"readable",{get:()=>l.pipeThrough(w).pipeThrough(c).pipeThrough(f)})}}class It extends d{constructor(t){let e;1>t&&(t=65536),super({transform:(n,s)=>{if(e){const t=new o(e.length+n.length);t.set(e),t.set(n,e.length),n=t,e=null}let r=0;for(;n.length-r>t;)s.enqueue(n.slice(r,r+t)),r+=t;e=r?n.slice(r):n},flush(t){e&&e.length&&t.enqueue(e)}})}}let At=2;try{typeof navigator!=k&&navigator.hardwareConcurrency&&(At=navigator.hardwareConcurrency)}catch{}const Pt={rt:"./core/web-worker-wasm.js",wasmURI:"./core/streams/zlib-wasm/zlib-streams.wasm",chunkSize:65536,ot:At,it:5e3,ct:5e3,lt:!0,useCompressionStream:!0,CompressionStream:typeof g!=k&&g,DecompressionStream:typeof S!=k&&S};e.assign({},Pt);const xt=new l,Rt=new l;let Ut,Wt,Dt,Mt,Vt,_t=0;async function Bt(t){let e,r;try{const{options:o,config:i}=t;if(!o.useCompressionStream)try{await self.initModule(t.config)}catch{o.useCompressionStream=!0}i.CompressionStream=self.CompressionStream,i.DecompressionStream=self.DecompressionStream;const a={highWaterMark:1},c=t.readable||new y({async pull(t){const e=new f(t=>xt.set(_t,t));Tt({type:"pull",messageId:_t}),_t=(_t+1)%n.MAX_SAFE_INTEGER;const{value:s,done:r}=await e;t.enqueue(s),r&&t.close()}},a);r=t.writable||new m({async write(t){let e;const s=new f(t=>e=t);Rt.set(_t,e),Tt({type:vt,value:t,messageId:_t}),_t=(_t+1)%n.MAX_SAFE_INTEGER,await s}},a),e=new Ct(o,i),Ut=new AbortController;const{signal:l}=Ut;await c.pipeThrough(e).pipeThrough(new It((t=>s.max(t.chunkSize,64))(i))).pipeTo(r,{signal:l,preventClose:!0,preventAbort:!0}),await r.getWriter().close();const{signature:w,inputSize:h,outputSize:u}=e;Tt({type:zt,result:{signature:w,inputSize:h,outputSize:u}})}catch(t){if(t.outputSize=e?e.outputSize:0,r&&!r.locked)try{await r.getWriter().close()}catch{}Kt(t)}}function Tt(t){let{value:e}=t;if(e)if(e.length)try{e=new o(e),t.value=e.buffer,p(t,[t.value])}catch{p(t)}else p(t);else p(t)}function Kt(t=new r("Unknown error")){const{message:e,stack:n,code:s,name:o,outputSize:i}=t;p({error:{message:e,stack:n,code:s,name:o,outputSize:i}})}function jt(t,e,n={}){const i="number"==typeof n.level?n.level:-1,a="number"==typeof n.wt?n.wt:65536,c="number"==typeof n.ft?n.ft:65536;return new d({start(){try{let n;if(this.ht=Dt(a),this.in=Dt(c),this.ft=c,!this.ht||!this.in)throw new r("allocation failed");if(this.ut=new o(a),t?(this.dt=Wt.deflate_process,this.yt=Wt.deflate_last_consumed,this.gt=Wt.deflate_end,this.St=Wt.deflate_new(),n="gzip"===e?Wt.deflate_init_gzip(this.St,i):"deflate-raw"===e?Wt.deflate_init_raw(this.St,i):Wt.deflate_init(this.St,i)):"deflate64-raw"===e?(this.dt=Wt.inflate9_process,this.yt=Wt.inflate9_last_consumed,this.gt=Wt.inflate9_end,this.St=Wt.inflate9_new(),n=Wt.inflate9_init_raw(this.St)):(this.dt=Wt.inflate_process,this.yt=Wt.inflate_last_consumed,this.gt=Wt.inflate_end,this.St=Wt.inflate_new(),n="deflate-raw"===e?Wt.inflate_init_raw(this.St):"gzip"===e?Wt.inflate_init_gzip(this.St):Wt.inflate_init(this.St)),0!==n)throw new r("init failed:"+n)}catch(t){throw l(this),t}},transform(e,n){try{const i=e,c=new o(Vt.buffer),l=this.dt,w=this.yt,f=this.ht,h=this.ut;let u=0;for(;u<i.length;){const e=s.min(i.length-u,32768);if((!this.in||this.ft<e)&&(this.in&&Mt&&(Mt(this.in),this.in=0),this.in=Dt(e),this.ft=e,!this.in))throw new r("allocation failed");c.set(i.subarray(u,u+e),this.in);const o=l(this.St,this.in,e,f,a,0),p=16777215&o;if(p&&(h.set(c.subarray(f,f+p),0),n.enqueue(h.slice(0,p))),!t){const t=o>>24&255,e=128&t?t-256:t;if(0>e)throw new r("process error:"+e)}const d=w(this.St);if(0===d)break;u+=d}}catch(t){l(this),n.error(t)}},flush(e){try{const n=new o(Vt.buffer),s=this.dt,i=this.ht,c=this.ut;for(;;){const o=s(this.St,0,0,i,a,4),l=16777215&o,w=o>>24&255;if(!t){const t=128&w?w-256:w;if(0>t)throw new r("process error:"+t)}if(l&&(c.set(n.subarray(i,i+l),0),e.enqueue(c.slice(0,l))),1===w||0===l)break}}catch(t){e.error(t)}finally{const t=l(this);0!==t&&e.error(new r("end error:"+t))}},cancel(){l(this)}});function l(t){let e=0;return t.St&&t.gt&&(e=t.gt(t.St)),t.St=0,t.in&&Mt&&Mt(t.in),t.in=0,t.ht&&Mt&&Mt(t.ht),t.ht=0,e}}addEventListener("message",({data:t})=>{const{type:e,messageId:n,value:s,done:r}=t;try{if("start"==e&&Bt(t),e==vt){const t=xt.get(n);xt.delete(n),t({value:new o(s),done:r})}if("ack"==e){const t=Rt.get(n);Rt.delete(n),t()}e==zt&&Ut.abort()}catch(t){Kt(t)}});class Et{constructor(t="deflate",e){return jt(!0,t,e)}}class Lt{constructor(t="deflate",e){return jt(!1,t,e)}}Et.bt=!0,Lt.bt=!0;let Ot=!1;self.initModule=async t=>{try{const e=await(async(t,{baseURI:e})=>{if(!Ot){let n,s;try{try{s=new URL(t,e)}catch{}const r=await fetch(s);n=await r.arrayBuffer()}catch(e){if(!t.startsWith("data:application/wasm;base64,"))throw e;n=(t=>{const e=t.split(",")[1],n=atob(e),s=n.length,r=new o(s);for(let t=0;s>t;++t)r[t]=n.charCodeAt(t);return r.buffer})(t)}(t=>{if(Wt=t,({malloc:Dt,free:Mt,memory:Vt}=Wt),"function"!=typeof Dt||"function"!=typeof Mt||!Vt)throw Wt=Dt=Mt=Vt=null,new r("Invalid WASM module")})((await WebAssembly.instantiate(n)).instance.exports),Ot=!0}})(t.wasmURI,t);return t.nt=Et,t.st=Lt,e}catch{}}});\n';t({workerURI:t=>{const n="text/javascript";if(t){const t=new Blob([e],{type:n});return URL.createObjectURL(t)}return "data:"+n+","+encodeURIComponent(e)}});}
|
|
208
|
+
function t(t){const e='(t=>{"function"==typeof define&&define.amd?define(t):t()})(function(){"use strict";const{Array:t,Object:e,Number:n,Math:s,Error:r,Uint8Array:o,Uint16Array:i,Uint32Array:a,Int32Array:c,Map:w,DataView:f,Promise:l,TextEncoder:u,crypto:h,postMessage:p,TransformStream:d,ReadableStream:y,WritableStream:m,CompressionStream:g,DecompressionStream:S}=self,b=void 0,k="undefined",v="function",z=[[],[],[],[],[],[],[],[]];for(let t=0;256>t;t++){let e=t;for(let t=0;8>t;t++)e=1&e?e>>>1^3988292384:e>>>1;z[0][t]=e}for(let t=0;256>t;t++)for(let e=1;8>e;e++){const n=z[e-1][t];z[e][t]=n>>>8^z[0][255&n]}const[C,I,A,x,P,R,U,W]=z;class D{constructor(t){this.t=t||-1}append(t){let e=0|this.t;const n=0|t.length;let s=0;if(n>=8&&t.buffer){const r=new f(t.buffer,t.byteOffset,n),o=n-8;for(;o>=s;s+=8){const t=e^r.getInt32(s,!0),n=r.getInt32(s+4,!0);e=W[255&t]^U[t>>>8&255]^R[t>>>16&255]^P[t>>>24&255]^x[255&n]^A[n>>>8&255]^I[n>>>16&255]^C[n>>>24&255]}}for(;n>s;s++)e=e>>>8^C[255&(e^t[s])];this.t=e}get(){return~this.t}}class M extends d{constructor(){let t;const e=new D;super({transform(t,n){e.append(t),n.enqueue(t)},flush(){const n=new o(4);new f(n.buffer).setUint32(0,e.get()),t.value=n}}),t=this}}const V={concat(t,e){if(0===t.length||0===e.length)return t.concat(e);const n=t[t.length-1],s=V.o(n);return 32===s?t.concat(e):V.i(e,s,0|n,t.slice(0,t.length-1))},l(t){const e=t.length;if(0===e)return 0;const n=t[e-1];return 32*(e-1)+V.o(n)},u(t,e){if(32*t.length<e)return t;const n=(t=t.slice(0,s.ceil(e/32))).length;return e&=31,n>0&&e&&(t[n-1]=V.h(e,t[n-1]&2147483648>>e-1,1)),t},h:(t,e,n)=>32===t?e:(n?0|e:e<<32-t)+1099511627776*t,o:t=>s.round(t/1099511627776)||32,i(t,e,n,s){for(void 0===s&&(s=[]);e>=32;e-=32)s.push(n),n=0;if(0===e)return s.concat(t);for(let r=0;r<t.length;r++)s.push(n|t[r]>>>e),n=t[r]<<32-e;const r=t.length?t[t.length-1]:0,o=V.o(r);return s.push(V.h(e+o&31,e+o>32?n:s.pop(),1)),s}},_={bytes:{p(t){const e=V.l(t)/8,n=new o(e);let s;for(let r=0;e>r;r++)3&r||(s=t[r/4]),n[r]=s>>>24,s<<=8;return n},m(t){const e=[];let n,s=0;for(n=0;n<t.length;n++)s=s<<8|t[n],3&~n||(e.push(s),s=0);return 3&n&&e.push(V.h(8*(3&n),s)),e}}},B=class{constructor(t){const e=this;e.blockSize=512,e.S=[1732584193,4023233417,2562383102,271733878,3285377520],e.k=[1518500249,1859775393,2400959708,3395469782],t?(e.v=t.v.slice(0),e.C=t.C.slice(0),e.I=t.I):e.reset()}reset(){const t=this;return t.v=t.S.slice(0),t.C=[],t.I=0,t}update(t){const e=this;"string"==typeof t&&(t=_.A.m(t));const n=e.C=V.concat(e.C,t),s=e.I,o=e.I=s+V.l(t);if(o>9007199254740991)throw new r("Cannot hash more than 2^53 - 1 bits");const i=new a(n);let c=0;for(let t=e.blockSize+s-(e.blockSize+s&e.blockSize-1);o>=t;t+=e.blockSize)e.P(i.subarray(16*c,16*(c+1))),c+=1;return n.splice(0,16*c),e}R(){const t=this;let e=t.C;const n=t.v;e=V.concat(e,[V.h(1,1)]);for(let t=e.length+2;15&t;t++)e.push(0);for(e.push(s.floor(t.I/4294967296)),e.push(0|t.I);e.length;)t.P(e.splice(0,16));return t.reset(),n}U(t,e,n,s){return t>19?t>39?t>59?t>79?void 0:e^n^s:e&n|e&s|n&s:e^n^s:e&n|~e&s}W(t,e){return e<<t|e>>>32-t}P(e){const n=this,r=n.v,o=t(80);for(let t=0;16>t;t++)o[t]=e[t];let i=r[0],a=r[1],c=r[2],w=r[3],f=r[4];for(let t=0;79>=t;t++){16>t||(o[t]=n.W(1,o[t-3]^o[t-8]^o[t-14]^o[t-16]));const e=n.W(5,i)+n.U(t,a,c,w)+f+o[t]+n.k[s.floor(t/20)]|0;f=w,w=c,c=n.W(30,a),a=i,i=e}r[0]=r[0]+i|0,r[1]=r[1]+a|0,r[2]=r[2]+c|0,r[3]=r[3]+w|0,r[4]=r[4]+f|0}},T={importKey:t=>new T.D(_.bytes.m(t)),M(t,e,n,s){if(n=n||1e4,0>s||0>n)throw new r("invalid params to pbkdf2");const o=1+(s>>5)<<2;let i,a,c,w,l;const u=new ArrayBuffer(o),h=new f(u);let p=0;const d=V;for(e=_.bytes.m(e),l=1;(o||1)>p;l++){for(i=a=t.encrypt(d.concat(e,[l])),c=1;n>c;c++)for(a=t.encrypt(a),w=0;w<a.length;w++)i[w]^=a[w];for(c=0;(o||1)>p&&c<i.length;c++)h.setInt32(p,i[c]),p+=4}return u.slice(0,s/8)},D:class{constructor(t){const e=this,n=e.V=B,s=[[],[]];e._=[new n,new n];const r=e._[0].blockSize/32;t.length>r&&(t=(new n).update(t).R());for(let e=0;r>e;e++)s[0][e]=909522486^t[e],s[1][e]=1549556828^t[e];e._[0].update(s[0]),e._[1].update(s[1]),e.B=new n(e._[0])}reset(){const t=this;t.B=new t.V(t._[0]),t.T=!1}update(t){this.T=!0,this.B.update(t)}digest(){const t=this,e=t.B.R(),n=new t.V(t._[1]).update(e).R();return t.reset(),n}encrypt(t){if(this.T)throw new r("encrypt on already updated hmac called!");return this.update(t),this.digest(t)}}},K=typeof h!=k&&typeof h.getRandomValues==v,j="Invalid password",E="Invalid signature",L="zipjs-abort-check-password";function O(t){if(K)return h.getRandomValues(t);throw new r("Crypto API not supported")}const H=16,Z={name:"PBKDF2"},F=e.assign({hash:{name:"HMAC"}},Z),N=e.assign({iterations:1e3,hash:{name:"SHA-1"}},Z),q=["deriveBits"],G=[8,12,16],J=[16,24,32],Q=10,X=[0,0,0,0],Y=typeof h!=k,$=Y&&h.subtle,tt=Y&&typeof $!=k,et=_.bytes,nt=class{constructor(t){const e=this;e.K=[[[],[],[],[],[]],[[],[],[],[],[]]],e.K[0][0][0]||e.j();const n=e.K[0][4],s=e.K[1],o=t.length;let i,a,c,w=1;if(4!==o&&6!==o&&8!==o)throw new r("invalid aes key size");for(e.k=[a=t.slice(0),c=[]],i=o;4*o+28>i;i++){let t=a[i-1];(i%o===0||8===o&&i%o===4)&&(t=n[t>>>24]<<24^n[t>>16&255]<<16^n[t>>8&255]<<8^n[255&t],i%o===0&&(t=t<<8^t>>>24^w<<24,w=w<<1^283*(w>>7))),a[i]=a[i-o]^t}for(let t=0;i;t++,i--){const e=a[3&t?i:i-4];c[t]=4>=i||4>t?e:s[0][n[e>>>24]]^s[1][n[e>>16&255]]^s[2][n[e>>8&255]]^s[3][n[255&e]]}}encrypt(t){return this.L(t,0)}decrypt(t){return this.L(t,1)}j(){const t=this.K[0],e=this.K[1],n=t[4],s=e[4],r=[],o=[];let i,a,c,w;for(let t=0;256>t;t++)o[(r[t]=t<<1^283*(t>>7))^t]=t;for(let f=i=0;!n[f];f^=a||1,i=o[i]||1){let o=i^i<<1^i<<2^i<<3^i<<4;o=o>>8^255&o^99,n[f]=o,s[o]=f,w=r[c=r[a=r[f]]];let l=16843009*w^65537*c^257*a^16843008*f,u=257*r[o]^16843008*o;for(let n=0;4>n;n++)t[n][f]=u=u<<24^u>>>8,e[n][o]=l=l<<24^l>>>8}for(let n=0;5>n;n++)t[n]=t[n].slice(0),e[n]=e[n].slice(0)}L(t,e){if(4!==t.length)throw new r("invalid aes block size");const n=this.k[e],s=n.length/4-2,o=[0,0,0,0],i=this.K[e],a=i[0],c=i[1],w=i[2],f=i[3],l=i[4];let u,h,p,d=t[0]^n[0],y=t[e?3:1]^n[1],m=t[2]^n[2],g=t[e?1:3]^n[3],S=4;for(let t=0;s>t;t++)u=a[d>>>24]^c[y>>16&255]^w[m>>8&255]^f[255&g]^n[S],h=a[y>>>24]^c[m>>16&255]^w[g>>8&255]^f[255&d]^n[S+1],p=a[m>>>24]^c[g>>16&255]^w[d>>8&255]^f[255&y]^n[S+2],g=a[g>>>24]^c[d>>16&255]^w[y>>8&255]^f[255&m]^n[S+3],S+=4,d=u,y=h,m=p;for(let t=0;4>t;t++)o[e?3&-t:t]=l[d>>>24]<<24^l[y>>16&255]<<16^l[m>>8&255]<<8^l[255&g]^n[S++],u=d,d=y,y=m,m=g,g=u;return o}},st=class{constructor(t,e){this.O=t,this.H=e,this.Z=e}reset(){this.Z=this.H}update(t){return this.F(this.O,t,this.Z)}N(t){if(255&~(t>>24))t+=1<<24;else{let e=t>>16&255,n=t>>8&255,s=255&t;255===e?(e=0,255===n?(n=0,255===s?s=0:++s):++n):++e,t=0,t+=e<<16,t+=n<<8,t+=s}return t}q(t){0===(t[0]=this.N(t[0]))&&(t[1]=this.N(t[1]))}F(t,e,n){let s;if(!(s=e.length))return[];const r=V.l(e);for(let r=0;s>r;r+=4){this.q(n);const s=t.encrypt(n);e[r]^=s[0],e[r+1]^=s[1],e[r+2]^=s[2],e[r+3]^=s[3]}return V.u(e,r)}},rt=T.D;let ot=Y&&tt&&typeof $.importKey==v,it=Y&&tt&&typeof $.deriveBits==v;class at extends d{constructor({password:t,rawPassword:n,encryptionStrength:s,checkPasswordOnly:i}){super({start(){e.assign(this,{ready:new l(t=>this.G=t),password:lt(t,n),J:s-1,pending:new o})},async transform(t,e){const n=this,{password:s,J:a,G:c,ready:w}=n;s?(await(async(t,e,n,s)=>{const o=await ft(t,e,n,ht(s,0,G[e])),i=ht(s,G[e]);if(o[0]!=i[0]||o[1]!=i[1])throw new r(j)})(n,a,s,ht(t,0,G[a]+2)),t=ht(t,G[a]+2),i?e.error(new r(L)):c()):await w;const f=new o(t.length-Q-(t.length-Q)%H);e.enqueue(wt(n,t,f,0,Q,!0))},async flush(t){const{X:e,Y:n,pending:s,ready:i}=this;if(n&&e){await i;const a=ht(s,0,s.length-Q),c=ht(s,s.length-Q);let w=new o;if(a.length){const t=dt(et,a);n.update(t);const s=e.update(t);w=pt(et,s)}const f=ht(pt(et,n.digest()),0,Q);let l=s.length<Q?1:0;for(let t=0;Q>t;t++)l|=f[t]^c[t];if(l)throw new r(E);t.enqueue(w)}}})}}class ct extends d{constructor({password:t,rawPassword:n,encryptionStrength:s}){let r;super({start(){e.assign(this,{ready:new l(t=>this.G=t),password:lt(t,n),J:s-1,pending:new o})},async transform(t,e){const n=this,{password:s,J:r,G:i,ready:a}=n;let c=new o;s?(c=await(async(t,e,n)=>{const s=O(new o(G[e]));return ut(s,await ft(t,e,n,s))})(n,r,s),i()):await a;const w=new o(c.length+t.length-t.length%H);w.set(c,0),e.enqueue(wt(n,t,w,c.length,0))},async flush(t){const{X:e,Y:n,pending:s,ready:i}=this;if(n&&e){await i;let a=new o;if(s.length){const t=e.update(dt(et,s));n.update(t),a=pt(et,t)}r.signature=pt(et,n.digest()).slice(0,Q),t.enqueue(ut(a,r.signature))}}}),r=this}}function wt(t,e,n,s,r,i){const{X:a,Y:c,pending:w}=t;w.length&&(e=ut(w,e));const f=e.length-r;let l;for(n=((t,e)=>{if(e&&e>t.length){const n=t;(t=new o(e)).set(n,0)}return t})(n,s+(f-f%H)),l=0;f-H>=l;l+=H){const t=dt(et,ht(e,l,l+H));i&&c.update(t);const r=a.update(t);i||c.update(r),n.set(pt(et,r),l+s)}return t.pending=ht(e,l),n}async function ft(n,s,r,i){n.password=null;const a=await(async(t,e,n,s,r)=>{if(!ot)return T.importKey(e);try{return await $.importKey("raw",e,n,!1,r)}catch{return ot=!1,T.importKey(e)}})(0,r,F,0,q),c=await(async(t,e,n)=>{if(!it)return T.M(e,t.salt,N.iterations,n);try{return await $.deriveBits(t,e,n)}catch{return it=!1,T.M(e,t.salt,N.iterations,n)}})(e.assign({salt:i},N),a,8*(2*J[s]+2)),w=new o(c),f=dt(et,ht(w,0,J[s])),l=dt(et,ht(w,J[s],2*J[s])),u=ht(w,2*J[s]);return e.assign(n,{keys:{key:f,$:l,passwordVerification:u},X:new st(new nt(f),t.from(X)),Y:new rt(l)}),u}function lt(t,e){return e===b?(t=>{if(typeof u==k){const e=new o((t=unescape(encodeURIComponent(t))).length);for(let n=0;n<e.length;n++)e[n]=t.charCodeAt(n);return e}return(new u).encode(t)})(t):e}function ut(t,e){let n=t;return t.length+e.length&&(n=new o(t.length+e.length),n.set(t,0),n.set(e,t.length)),n}function ht(t,e,n){return t.subarray(e,n)}function pt(t,e){return t.p(e)}function dt(t,e){return t.m(e)}class yt extends d{constructor({password:t,rawPassword:n,passwordVerification:s,checkPasswordOnly:o}){super({start(){e.assign(this,{password:t,rawPassword:n,passwordVerification:s}),bt(this,t,n)},transform(t,e){const n=this;if(n.password||n.rawPassword){const e=gt(n,t.subarray(0,12));if(n.password=n.rawPassword=null,0!=(e.at(-1)^n.passwordVerification))throw new r(j);t=t.subarray(12)}o?e.error(new r(L)):e.enqueue(gt(n,t))}})}}class mt extends d{constructor({password:t,rawPassword:n,passwordVerification:s}){super({start(){e.assign(this,{password:t,rawPassword:n,passwordVerification:s}),bt(this,t,n)},transform(t,e){const n=this;let s,r;if(n.password||n.rawPassword){n.password=n.rawPassword=null;const e=O(new o(12));e[11]=n.passwordVerification,s=new o(t.length+e.length),s.set(St(n,e),0),r=12}else s=new o(t.length),r=0;s.set(St(n,t),r),e.enqueue(s)}})}}function gt(t,e){const n=new o(e.length);for(let s=0;s<e.length;s++)n[s]=vt(t)^e[s],kt(t,n[s]);return n}function St(t,e){const n=new o(e.length);for(let s=0;s<e.length;s++)n[s]=vt(t)^e[s],kt(t,e[s]);return n}function bt(t,n,s){const r=[305419896,591751049,878082192];if(e.assign(t,{keys:r,tt:new D(r[0]),et:new D(r[2])}),s)for(let e=0;e<s.length;e++)kt(t,s[e]);else for(let e=0;e<n.length;e++)kt(t,n.charCodeAt(e))}function kt(t,e){let[,n]=t.keys;t.tt.append([e]);const r=~t.tt.get();n=Ct(s.imul(Ct(n+zt(r)),134775813)+1),t.et.append([n>>>24]);const o=~t.et.get();t.keys=[r,n,o]}function vt(t){const e=2|t.keys[2];return zt(s.imul(e,1^e)>>>8)}function zt(t){return 255&t}function Ct(t){return 4294967295&t}class It extends d{constructor(t,{chunkSize:e,nt:n,CompressionStream:s}){super({});const{compressed:r,encrypted:o,useCompressionStream:i,zipCrypto:a,signed:c,level:w,deflate64:l}=t,u=this;let h,p,d,y=super.readable;const m=c&&r&&!l&&(!o||a)&&!(!i||!s);o&&!a||!c||m||(h=new M,y=Ut(y,h)),r&&(m?(d=new At,y=Wt(y,new s("gzip")),y=Ut(y,d)):y=Rt(y,i,{level:w,chunkSize:e},s,n,s)),o&&(a?y=Ut(y,new mt(t)):(p=new ct(t),y=Ut(y,p))),Pt(u,y,()=>{let t;o&&!a&&(t=p.signature),o&&!a||!c||(t=m?d.signature:new f(h.value.buffer).getUint32(0)),u.signature=t})}}class At extends d{constructor(){let t,e=10,n=new o(0);super({transform(t,r){if(e){const n=s.min(e,t.length);if(e-=n,!(t=t.subarray(n)).length)return}const i=n.length+t.length;if(8>=i){const e=new o(i);return e.set(n),e.set(t,n.length),void(n=e)}const a=i-8,c=new o(a),w=s.min(a,n.length);c.set(n.subarray(0,w),0),a>w&&c.set(t.subarray(0,a-w),w),r.enqueue(c);const f=new o(8),l=n.length-w;l&&f.set(n.subarray(w),0),f.set(t.subarray(a-w),l),n=f},flush(){const e=new f(n.buffer,n.byteOffset,n.byteLength);t.signature=e.getUint32(0,!0),t.st=e.getUint32(4,!0)}}),t=this}}class xt extends d{constructor(t,{chunkSize:e,rt:n,DecompressionStream:s}){super({});const{zipCrypto:o,encrypted:i,signed:a,signature:c,compressed:w,useCompressionStream:l,deflate64:u}=t;let h,p,d=super.readable;i&&(o?d=Ut(d,new yt(t)):(p=new at(t),d=Ut(d,p))),w&&(d=Rt(d,l,{chunkSize:e,deflate64:u},s,n,s),d=(t=>{const e=t.getReader();return new y({async pull(t){let n;try{n=await e.read()}catch(t){if(t&&t.message)throw t;const e=new r("Invalid compressed data");throw e.cause=t,e}const{value:s,done:o}=n;o?t.close():t.enqueue(s)},cancel:t=>e.cancel(t)})})(d)),i&&!o||!a||(h=new M,d=Ut(d,h)),Pt(this,d,()=>{if((!i||o)&&a){const t=new f(h.value.buffer);if(c!=t.getUint32(0,!1))throw new r(E)}})}}function Pt(t,n,s){n=Ut(n,new d({flush:s})),e.defineProperty(t,"readable",{get:()=>n})}function Rt(t,e,n,s,r,o){const i=e&&s?s:r||o,a=n.deflate64?"deflate64-raw":"deflate-raw";let c;try{c=new i(a,n)}catch(t){if(!e)throw t;if(r)c=new r(a,n);else{if(!o)throw t;c=new o(a,n)}}return Wt(t,c)}function Ut(t,e){return t.pipeThrough(e)}function Wt(t,e){const n=e.writable.getWriter(),s=t.getReader();return(async()=>{try{for(;;){await n.ready;const t=await s.read();if(t.done){await n.close();break}await n.write(t.value)}}catch(t){await(async(t,e)=>{try{await t.abort(e)}catch{}})(n,t),await(async(t,e)=>{try{await t.cancel(e)}catch{}})(s,t)}})(),e.readable}const Dt="data",Mt="close";class Vt extends d{constructor(t,n){super({});const s=this,{codecType:o}=t;let i;o.startsWith("deflate")?i=It:o.startsWith("inflate")&&(i=xt),s.outputSize=0;let a=0;const c=new i(t,n),w=super.readable,f=new d({transform(t,e){t&&t.length&&(a+=t.length,e.enqueue(t))},flush(){e.assign(s,{inputSize:a})}}),l=new d({transform(e,n){if(e&&e.length&&(n.enqueue(e),s.outputSize+=e.length,t.outputSize!==b&&s.outputSize>t.outputSize))throw new r("Invalid uncompressed size")},flush(){const{signature:t}=c;e.assign(s,{signature:t,inputSize:a})}});e.defineProperty(s,"readable",{get:()=>w.pipeThrough(f).pipeThrough(c).pipeThrough(l)})}}class _t extends d{constructor(t){let e;1>t&&(t=65536),super({transform:(n,s)=>{if(e){const t=new o(e.length+n.length);t.set(e),t.set(n,e.length),n=t,e=null}let r=0;for(;n.length-r>t;)s.enqueue(n.slice(r,r+t)),r+=t;e=r?n.slice(r):n},flush(t){e&&e.length&&t.enqueue(e)}})}}let Bt=2;try{typeof navigator!=k&&navigator.hardwareConcurrency&&(Bt=navigator.hardwareConcurrency)}catch{}const Tt={ot:"./core/web-worker-wasm.js",wasmURI:"./core/streams/zlib-wasm/zlib-streams.wasm",chunkSize:65536,it:Bt,ct:5e3,wt:5e3,ft:!0,useCompressionStream:!0,CompressionStream:typeof g!=k&&g,DecompressionStream:typeof S!=k&&S};e.assign({},Tt);const Kt=new w,jt=new w;let Et,Lt,Ot,Ht,Zt,Ft=0;async function Nt(t){let e,r;try{const{options:o,config:i}=t;if(!o.useCompressionStream)try{await self.initModule(t.config)}catch{o.useCompressionStream=!0}i.CompressionStream=self.CompressionStream,i.DecompressionStream=self.DecompressionStream;const a={highWaterMark:1},c=t.readable||new y({async pull(t){const e=new l(t=>Kt.set(Ft,t));qt({type:"pull",messageId:Ft}),Ft=(Ft+1)%n.MAX_SAFE_INTEGER;const{value:s,done:r}=await e;t.enqueue(s),r&&t.close()}},a);r=t.writable||new m({async write(t){let e;const s=new l(t=>e=t);jt.set(Ft,e),qt({type:Dt,value:t,messageId:Ft}),Ft=(Ft+1)%n.MAX_SAFE_INTEGER,await s}},a),e=new Vt(o,i),Et=new AbortController;const{signal:w}=Et;await c.pipeThrough(e).pipeThrough(new _t((t=>s.max(t.chunkSize,64))(i))).pipeTo(r,{signal:w,preventClose:!0,preventAbort:!0}),await r.getWriter().close();const{signature:f,inputSize:u,outputSize:h}=e;qt({type:Mt,result:{signature:f,inputSize:u,outputSize:h}})}catch(t){if(t.outputSize=e?e.outputSize:0,r&&!r.locked)try{await r.getWriter().close()}catch{}Gt(t)}}function qt(t){let{value:e}=t;if(e)if(e.length)try{e=new o(e),t.value=e.buffer,p(t,[t.value])}catch{p(t)}else p(t);else p(t)}function Gt(t=new r("Unknown error")){const{message:e,stack:n,code:s,name:o,outputSize:i}=t;p({error:{message:e,stack:n,code:s,name:o,outputSize:i}})}function Jt(t,e,n={}){const i="number"==typeof n.level?n.level:-1,a="number"==typeof n.lt?n.lt:65536,c="number"==typeof n.ut?n.ut:65536;return new d({start(){try{let n;if(this.ht=Ot(a),this.in=Ot(c),this.ut=c,!this.ht||!this.in)throw new r("allocation failed");if(this.dt=new o(a),t?(this.yt=Lt.deflate_process,this.gt=Lt.deflate_last_consumed,this.St=Lt.deflate_end,this.bt=Lt.deflate_new(),n="gzip"===e?Lt.deflate_init_gzip(this.bt,i):"deflate-raw"===e?Lt.deflate_init_raw(this.bt,i):Lt.deflate_init(this.bt,i)):"deflate64-raw"===e?(this.yt=Lt.inflate9_process,this.gt=Lt.inflate9_last_consumed,this.St=Lt.inflate9_end,this.bt=Lt.inflate9_new(),n=Lt.inflate9_init_raw(this.bt)):(this.yt=Lt.inflate_process,this.gt=Lt.inflate_last_consumed,this.St=Lt.inflate_end,this.bt=Lt.inflate_new(),n="deflate-raw"===e?Lt.inflate_init_raw(this.bt):"gzip"===e?Lt.inflate_init_gzip(this.bt):Lt.inflate_init(this.bt)),0!==n)throw new r("init failed:"+n)}catch(t){throw w(this),t}},transform(e,n){try{const i=e,c=new o(Zt.buffer),w=this.yt,f=this.gt,l=this.ht,u=this.dt;let h=0;for(;h<i.length;){const e=s.min(i.length-h,32768);if((!this.in||this.ut<e)&&(this.in&&Ht&&(Ht(this.in),this.in=0),this.in=Ot(e),this.ut=e,!this.in))throw new r("allocation failed");c.set(i.subarray(h,h+e),this.in);const o=w(this.bt,this.in,e,l,a,0),p=16777215&o;if(p&&(u.set(c.subarray(l,l+p),0),n.enqueue(u.slice(0,p))),!t){const t=o>>24&255,e=128&t?t-256:t;if(0>e)throw new r("process error:"+e)}const d=f(this.bt);if(0===d)break;h+=d}}catch(t){w(this),n.error(t)}},flush(e){try{const n=new o(Zt.buffer),s=this.yt,i=this.ht,c=this.dt;for(;;){const o=s(this.bt,0,0,i,a,4),w=16777215&o,f=o>>24&255;if(!t){const t=128&f?f-256:f;if(0>t)throw new r("process error:"+t)}if(w&&(c.set(n.subarray(i,i+w),0),e.enqueue(c.slice(0,w))),1===f||0===w)break}}catch(t){e.error(t)}finally{const t=w(this);0!==t&&e.error(new r("end error:"+t))}},cancel(){w(this)}});function w(t){let e=0;return t.bt&&t.St&&(e=t.St(t.bt)),t.bt=0,t.in&&Ht&&Ht(t.in),t.in=0,t.ht&&Ht&&Ht(t.ht),t.ht=0,e}}addEventListener("message",({data:t})=>{const{type:e,messageId:n,value:s,done:r}=t;try{if("start"==e&&Nt(t),e==Dt){const t=Kt.get(n);Kt.delete(n),t({value:new o(s),done:r})}if("ack"==e){const t=jt.get(n);jt.delete(n),t()}e==Mt&&Et.abort()}catch(t){Gt(t)}});class Qt{constructor(t="deflate",e){return Jt(!0,t,e)}}class Xt{constructor(t="deflate",e){return Jt(!1,t,e)}}Qt.kt=!0,Xt.kt=!0;let Yt=!1;self.initModule=async t=>{try{const e=await(async(t,{baseURI:e})=>{if(!Yt){let n,s;try{try{s=new URL(t,e)}catch{}const r=await fetch(s);n=await r.arrayBuffer()}catch(e){if(!t.startsWith("data:application/wasm;base64,"))throw e;n=(t=>{const e=t.split(",")[1],n=atob(e),s=n.length,r=new o(s);for(let t=0;s>t;++t)r[t]=n.charCodeAt(t);return r.buffer})(t)}(t=>{if(Lt=t,({malloc:Ot,free:Ht,memory:Zt}=Lt),"function"!=typeof Ot||"function"!=typeof Ht||!Zt)throw Lt=Ot=Ht=Zt=null,new r("Invalid WASM module")})((await WebAssembly.instantiate(n)).instance.exports),Yt=!0}})(t.wasmURI,t);return t.nt=Qt,t.rt=Xt,e}catch{}}});\n';t({workerURI:t=>{const n="text/javascript";if(t){const t=new Blob([e],{type:n});return URL.createObjectURL(t)}return "data:"+n+","+encodeURIComponent(e)}});}
|
|
209
209
|
|
|
210
210
|
/*
|
|
211
211
|
Copyright (c) 2022 Gildas Lormeau. All rights reserved.
|
|
@@ -235,18 +235,30 @@ function t(t){const e='(t=>{"function"==typeof define&&define.amd?define(t):t()}
|
|
|
235
235
|
EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
236
236
|
*/
|
|
237
237
|
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
238
|
+
// Slicing-by-8 CRC-32 (Intel / zlib). The eight 256-entry tables let the inner loop
|
|
239
|
+
// consume 8 bytes per iteration with a shorter dependency chain, ~4x the byte-at-a-time
|
|
240
|
+
// rate (measured ~320 -> ~1400 MB/s on 64KB chunks).
|
|
241
|
+
//
|
|
242
|
+
// Every table MUST stay a PACKED_SMI array: build with array literals (not `new Array(n)`,
|
|
243
|
+
// which is HOLEY) and store the signed int32 XOR result (no `>>> 0`). An unsigned or holey
|
|
244
|
+
// table becomes a V8 FixedDoubleArray whose every hot-loop lookup unboxes a double (~1.6x
|
|
245
|
+
// slower). Signedness is irrelevant to the result — the reads mask/shift it and the final
|
|
246
|
+
// `~crc` normalizes it. Do NOT reintroduce `>>> 0` here or switch to `new Array(256)`.
|
|
247
|
+
const T = [[], [], [], [], [], [], [], []];
|
|
248
|
+
for (let n = 0; n < 256; n++) {
|
|
249
|
+
let t = n;
|
|
241
250
|
for (let j = 0; j < 8; j++) {
|
|
242
|
-
|
|
243
|
-
t = (t >>> 1) ^ 0xEDB88320;
|
|
244
|
-
} else {
|
|
245
|
-
t = t >>> 1;
|
|
246
|
-
}
|
|
251
|
+
t = (t & 1) ? (t >>> 1) ^ 0xEDB88320 : t >>> 1;
|
|
247
252
|
}
|
|
248
|
-
|
|
253
|
+
T[0][n] = t;
|
|
249
254
|
}
|
|
255
|
+
for (let n = 0; n < 256; n++) {
|
|
256
|
+
for (let k = 1; k < 8; k++) {
|
|
257
|
+
const previous = T[k - 1][n];
|
|
258
|
+
T[k][n] = (previous >>> 8) ^ T[0][previous & 0xFF];
|
|
259
|
+
}
|
|
260
|
+
}
|
|
261
|
+
const [T0, T1, T2, T3, T4, T5, T6, T7] = T;
|
|
250
262
|
|
|
251
263
|
class Crc32 {
|
|
252
264
|
|
|
@@ -256,8 +268,24 @@ class Crc32 {
|
|
|
256
268
|
|
|
257
269
|
append(data) {
|
|
258
270
|
let crc = this.crc | 0;
|
|
259
|
-
|
|
260
|
-
|
|
271
|
+
const length = data.length | 0;
|
|
272
|
+
let offset = 0;
|
|
273
|
+
// Process 8 bytes per iteration over the typed-array body. DataView.getInt32(le)
|
|
274
|
+
// reads an unaligned little-endian word as a signed int32 (no double boxing), so no
|
|
275
|
+
// alignment or endianness handling is needed; data.buffer guards non-typed inputs.
|
|
276
|
+
if (length >= 8 && data.buffer) {
|
|
277
|
+
const view = new DataView(data.buffer, data.byteOffset, length);
|
|
278
|
+
const end = length - 8;
|
|
279
|
+
for (; offset <= end; offset += 8) {
|
|
280
|
+
const a = crc ^ view.getInt32(offset, true);
|
|
281
|
+
const b = view.getInt32(offset + 4, true);
|
|
282
|
+
crc = T7[a & 0xFF] ^ T6[(a >>> 8) & 0xFF] ^ T5[(a >>> 16) & 0xFF] ^ T4[(a >>> 24) & 0xFF] ^
|
|
283
|
+
T3[b & 0xFF] ^ T2[(b >>> 8) & 0xFF] ^ T1[(b >>> 16) & 0xFF] ^ T0[(b >>> 24) & 0xFF];
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
// Remaining tail (and non-typed inputs) byte-at-a-time with the base table.
|
|
287
|
+
for (; offset < length; offset++) {
|
|
288
|
+
crc = (crc >>> 8) ^ T0[(crc ^ data[offset]) & 0xFF];
|
|
261
289
|
}
|
|
262
290
|
this.crc = crc;
|
|
263
291
|
}
|
|
@@ -1691,21 +1719,40 @@ const ERR_INVALID_UNCOMPRESSED_SIZE = "Invalid uncompressed size";
|
|
|
1691
1719
|
const ERR_INVALID_COMPRESSED_DATA = "Invalid compressed data";
|
|
1692
1720
|
const FORMAT_DEFLATE_RAW = "deflate-raw";
|
|
1693
1721
|
const FORMAT_DEFLATE64_RAW = "deflate64-raw";
|
|
1722
|
+
const FORMAT_GZIP = "gzip";
|
|
1723
|
+
const GZIP_HEADER_LENGTH = 10;
|
|
1724
|
+
const GZIP_TRAILER_LENGTH = 8;
|
|
1694
1725
|
|
|
1695
1726
|
class DeflateStream extends TransformStream {
|
|
1696
1727
|
|
|
1697
1728
|
constructor(options, { chunkSize, CompressionStreamZlib, CompressionStream }) {
|
|
1698
1729
|
super({});
|
|
1699
|
-
const { compressed, encrypted, useCompressionStream, zipCrypto, signed, level } = options;
|
|
1730
|
+
const { compressed, encrypted, useCompressionStream, zipCrypto, signed, level, deflate64 } = options;
|
|
1700
1731
|
const stream = this;
|
|
1701
|
-
let crc32Stream, encryptionStream;
|
|
1732
|
+
let crc32Stream, encryptionStream, gzipCrc32Stream;
|
|
1702
1733
|
let readable = super.readable;
|
|
1703
|
-
|
|
1734
|
+
// The gzip trailer carries a CRC-32 of the uncompressed data (same polynomial as zip),
|
|
1735
|
+
// computed in native code for free during compression. On the native CompressionStream,
|
|
1736
|
+
// harvest it instead of running a separate CRC pass: compress as gzip, then strip the
|
|
1737
|
+
// fixed 10-byte header and 8-byte trailer to recover the exact raw-deflate payload
|
|
1738
|
+
// (byte-identical to a deflate-raw compression) while capturing the CRC. The CRC becomes
|
|
1739
|
+
// available at end-of-stream, exactly like Crc32Stream, so nothing downstream (data
|
|
1740
|
+
// descriptor, central directory, ZipCrypto) needs it any earlier. Not applied for the
|
|
1741
|
+
// pure-JS/WASM ports (a separate slice-by-8 CRC pass is as fast or faster there).
|
|
1742
|
+
const useGzipCrc32 = signed && compressed && !deflate64 && (!encrypted || zipCrypto) &&
|
|
1743
|
+
Boolean(useCompressionStream && CompressionStream);
|
|
1744
|
+
if ((!encrypted || zipCrypto) && signed && !useGzipCrc32) {
|
|
1704
1745
|
crc32Stream = new Crc32Stream();
|
|
1705
1746
|
readable = pipeThrough(readable, crc32Stream);
|
|
1706
1747
|
}
|
|
1707
1748
|
if (compressed) {
|
|
1708
|
-
|
|
1749
|
+
if (useGzipCrc32) {
|
|
1750
|
+
gzipCrc32Stream = new GzipToRawDeflateStream();
|
|
1751
|
+
readable = pipeThroughBackpressured(readable, new CompressionStream(FORMAT_GZIP));
|
|
1752
|
+
readable = pipeThrough(readable, gzipCrc32Stream);
|
|
1753
|
+
} else {
|
|
1754
|
+
readable = pipeThroughCommpressionStream(readable, useCompressionStream, { level, chunkSize }, CompressionStream, CompressionStreamZlib, CompressionStream);
|
|
1755
|
+
}
|
|
1709
1756
|
}
|
|
1710
1757
|
if (encrypted) {
|
|
1711
1758
|
if (zipCrypto) {
|
|
@@ -1721,13 +1768,74 @@ class DeflateStream extends TransformStream {
|
|
|
1721
1768
|
signature = encryptionStream.signature;
|
|
1722
1769
|
}
|
|
1723
1770
|
if ((!encrypted || zipCrypto) && signed) {
|
|
1724
|
-
signature = new DataView(crc32Stream.value.buffer).getUint32(0);
|
|
1771
|
+
signature = useGzipCrc32 ? gzipCrc32Stream.signature : new DataView(crc32Stream.value.buffer).getUint32(0);
|
|
1725
1772
|
}
|
|
1726
1773
|
stream.signature = signature;
|
|
1727
1774
|
});
|
|
1728
1775
|
}
|
|
1729
1776
|
}
|
|
1730
1777
|
|
|
1778
|
+
// Converts a gzip stream into its raw-deflate payload while capturing the CRC-32 from the gzip
|
|
1779
|
+
// trailer. The CompressionStream gzip header is always the fixed 10-byte form (FLG=0, no optional
|
|
1780
|
+
// fields) per the Compression Streams spec, so it is stripped by length; the trailer is the last
|
|
1781
|
+
// 8 bytes (CRC-32 LE, then ISIZE LE). Bounded memory: at most GZIP_TRAILER_LENGTH bytes are held
|
|
1782
|
+
// back across chunks. The signature is read big-endian-agnostically as a number, matching the
|
|
1783
|
+
// value Crc32Stream produces, so the writer path is unchanged.
|
|
1784
|
+
class GzipToRawDeflateStream extends TransformStream {
|
|
1785
|
+
|
|
1786
|
+
constructor() {
|
|
1787
|
+
// deno-lint-ignore prefer-const
|
|
1788
|
+
let stream;
|
|
1789
|
+
let headerLeft = GZIP_HEADER_LENGTH;
|
|
1790
|
+
let tail = new Uint8Array(0);
|
|
1791
|
+
super({
|
|
1792
|
+
transform(chunk, controller) {
|
|
1793
|
+
if (headerLeft) {
|
|
1794
|
+
const dropped = Math.min(headerLeft, chunk.length);
|
|
1795
|
+
headerLeft -= dropped;
|
|
1796
|
+
chunk = chunk.subarray(dropped);
|
|
1797
|
+
if (!chunk.length) {
|
|
1798
|
+
return;
|
|
1799
|
+
}
|
|
1800
|
+
}
|
|
1801
|
+
const available = tail.length + chunk.length;
|
|
1802
|
+
if (available <= GZIP_TRAILER_LENGTH) {
|
|
1803
|
+
const pending = new Uint8Array(available);
|
|
1804
|
+
pending.set(tail);
|
|
1805
|
+
pending.set(chunk, tail.length);
|
|
1806
|
+
tail = pending;
|
|
1807
|
+
return;
|
|
1808
|
+
}
|
|
1809
|
+
// Emit everything except the trailing GZIP_TRAILER_LENGTH bytes as a standalone,
|
|
1810
|
+
// right-sized Uint8Array. Consumers may read chunk.buffer directly (e.g. custom
|
|
1811
|
+
// writers), so an aliased subarray of a larger buffer would leak the held-back
|
|
1812
|
+
// trailer bytes. Bytes are copied exactly once, into `output` or `tail`.
|
|
1813
|
+
const emitLength = available - GZIP_TRAILER_LENGTH;
|
|
1814
|
+
const output = new Uint8Array(emitLength);
|
|
1815
|
+
const fromTail = Math.min(emitLength, tail.length);
|
|
1816
|
+
output.set(tail.subarray(0, fromTail), 0);
|
|
1817
|
+
if (emitLength > fromTail) {
|
|
1818
|
+
output.set(chunk.subarray(0, emitLength - fromTail), fromTail);
|
|
1819
|
+
}
|
|
1820
|
+
controller.enqueue(output);
|
|
1821
|
+
const nextTail = new Uint8Array(GZIP_TRAILER_LENGTH);
|
|
1822
|
+
const tailRemaining = tail.length - fromTail;
|
|
1823
|
+
if (tailRemaining) {
|
|
1824
|
+
nextTail.set(tail.subarray(fromTail), 0);
|
|
1825
|
+
}
|
|
1826
|
+
nextTail.set(chunk.subarray(emitLength - fromTail), tailRemaining);
|
|
1827
|
+
tail = nextTail;
|
|
1828
|
+
},
|
|
1829
|
+
flush() {
|
|
1830
|
+
const dataView = new DataView(tail.buffer, tail.byteOffset, tail.byteLength);
|
|
1831
|
+
stream.signature = dataView.getUint32(0, true);
|
|
1832
|
+
stream.uncompressedSize = dataView.getUint32(4, true);
|
|
1833
|
+
}
|
|
1834
|
+
});
|
|
1835
|
+
stream = this;
|
|
1836
|
+
}
|
|
1837
|
+
}
|
|
1838
|
+
|
|
1731
1839
|
class InflateStream extends TransformStream {
|
|
1732
1840
|
|
|
1733
1841
|
constructor(options, { chunkSize, DecompressionStreamZlib, DecompressionStream }) {
|
|
@@ -3693,6 +3801,11 @@ const OPTION_ENCODE_TEXT = "encodeText";
|
|
|
3693
3801
|
const OPTION_OFFSET = "offset";
|
|
3694
3802
|
const OPTION_USDZ = "usdz";
|
|
3695
3803
|
const OPTION_UNIX_EXTRA_FIELD_TYPE = "unixExtraFieldType";
|
|
3804
|
+
const OPTION_STRICTNESS = "strictness";
|
|
3805
|
+
const OPTION_MAX_APPENDED_DATA_SIZE = "maxAppendedDataSize";
|
|
3806
|
+
const STRICTNESS_STRICT = "strict";
|
|
3807
|
+
const STRICTNESS_BALANCED = "balanced";
|
|
3808
|
+
const STRICTNESS_TOLERANT = "tolerant";
|
|
3696
3809
|
|
|
3697
3810
|
/*
|
|
3698
3811
|
Copyright (c) 2025 Gildas Lormeau. All rights reserved.
|
|
@@ -3782,7 +3895,11 @@ class ZipReader {
|
|
|
3782
3895
|
throw new Error(ERR_BAD_FORMAT);
|
|
3783
3896
|
}
|
|
3784
3897
|
reader.chunkSize = getChunkSize(config);
|
|
3785
|
-
const
|
|
3898
|
+
const strictness = getStrictness(getOptionValue$1(zipReader, options, OPTION_STRICTNESS), getOptionValue$1(zipReader, options, OPTION_CHECK_AMBIGUITY));
|
|
3899
|
+
const checkAmbiguity = strictness == STRICTNESS_STRICT;
|
|
3900
|
+
const rejectAmbiguousEndOfDirectory = strictness != STRICTNESS_TOLERANT;
|
|
3901
|
+
const maxAppendedDataSize = getMaxAppendedDataSize(getOptionValue$1(zipReader, options, OPTION_MAX_APPENDED_DATA_SIZE), strictness);
|
|
3902
|
+
const { endOfDirectoryInfo, endOfDirectoryReachingEndCount } = await findEndOfCentralDirectory(reader, rejectAmbiguousEndOfDirectory, maxAppendedDataSize);
|
|
3786
3903
|
if (!endOfDirectoryInfo) {
|
|
3787
3904
|
const signatureArray = await readUint8Array(reader, 0, 4);
|
|
3788
3905
|
const signatureView = getDataView$1(signatureArray);
|
|
@@ -3792,14 +3909,18 @@ class ZipReader {
|
|
|
3792
3909
|
throw new Error(ERR_EOCDR_NOT_FOUND);
|
|
3793
3910
|
}
|
|
3794
3911
|
}
|
|
3912
|
+
// two or more end-anchored records that each dereference to a valid central directory cannot be told
|
|
3913
|
+
// apart (see comment_length ⟺ EOF): the archive is genuinely ambiguous, so refuse rather than guess
|
|
3914
|
+
if (rejectAmbiguousEndOfDirectory && endOfDirectoryReachingEndCount > 1) {
|
|
3915
|
+
throwAmbiguousArchive("multiple end of central directory records");
|
|
3916
|
+
}
|
|
3795
3917
|
const endOfDirectoryView = getDataView$1(endOfDirectoryInfo);
|
|
3796
3918
|
let directoryDataLength = getUint32(endOfDirectoryView, 12);
|
|
3797
3919
|
let directoryDataOffset = getUint32(endOfDirectoryView, 16);
|
|
3798
3920
|
const commentOffset = endOfDirectoryInfo.offset;
|
|
3799
3921
|
const commentLength = getUint16(endOfDirectoryView, 20);
|
|
3800
3922
|
const appendedDataOffset = commentOffset + END_OF_CENTRAL_DIR_LENGTH + commentLength;
|
|
3801
|
-
|
|
3802
|
-
if (checkAmbiguity && appendedDataOffset != reader.size) {
|
|
3923
|
+
if (reader.size - appendedDataOffset > maxAppendedDataSize) {
|
|
3803
3924
|
throwAmbiguousArchive("appended data");
|
|
3804
3925
|
}
|
|
3805
3926
|
let lastDiskNumber = getUint16(endOfDirectoryView, 4);
|
|
@@ -3878,14 +3999,28 @@ class ZipReader {
|
|
|
3878
3999
|
throw new Error(ERR_BAD_FORMAT);
|
|
3879
4000
|
}
|
|
3880
4001
|
const expectedDirectoryDataOffset = centralDirectoryEndOffset - directoryDataLength - (reader.lastDiskOffset || 0);
|
|
3881
|
-
if (
|
|
3882
|
-
|
|
3883
|
-
|
|
3884
|
-
|
|
3885
|
-
|
|
4002
|
+
if (directoryDataOffset != expectedDirectoryDataOffset && diskNumber == lastDiskNumber) {
|
|
4003
|
+
// the reconciled offset (the directory ends exactly where the canonical record begins) is anchored
|
|
4004
|
+
// to the unforgeable end of the archive; the stored offset is not. Prefer the reconciled offset
|
|
4005
|
+
// unless the stored one points at a directory and the reconciled one does not — that exception
|
|
4006
|
+
// keeps a corrupt declared directory length from sending the read astray, while still moving off a
|
|
4007
|
+
// stored offset that only looks valid because an append remnant left the previous (identically
|
|
4008
|
+
// laid out) directory sitting there.
|
|
4009
|
+
const storedPointsAtDirectory = getUint32(directoryView, offset) == CENTRAL_FILE_HEADER_SIGNATURE;
|
|
4010
|
+
let reconcile = !storedPointsAtDirectory;
|
|
4011
|
+
if (!reconcile && expectedDirectoryDataOffset >= 0 && expectedDirectoryDataOffset + 4 <= reader.size) {
|
|
4012
|
+
const expectedSignatureArray = await readUint8Array(reader, expectedDirectoryDataOffset, 4, diskNumber);
|
|
4013
|
+
reconcile = getUint32(getDataView$1(expectedSignatureArray), 0) == CENTRAL_FILE_HEADER_SIGNATURE;
|
|
4014
|
+
}
|
|
4015
|
+
if (reconcile) {
|
|
4016
|
+
const originalDirectoryDataOffset = directoryDataOffset;
|
|
4017
|
+
directoryDataOffset = expectedDirectoryDataOffset;
|
|
4018
|
+
if (directoryDataOffset > originalDirectoryDataOffset) {
|
|
4019
|
+
prependedDataLength += directoryDataOffset - originalDirectoryDataOffset;
|
|
4020
|
+
}
|
|
4021
|
+
directoryArray = await readUint8Array(reader, directoryDataOffset, directoryDataLength, diskNumber);
|
|
4022
|
+
directoryView = getDataView$1(directoryArray);
|
|
3886
4023
|
}
|
|
3887
|
-
directoryArray = await readUint8Array(reader, directoryDataOffset, directoryDataLength, diskNumber);
|
|
3888
|
-
directoryView = getDataView$1(directoryArray);
|
|
3889
4024
|
}
|
|
3890
4025
|
}
|
|
3891
4026
|
const expectedDirectoryDataLength = centralDirectoryEndOffset - directoryDataOffset - (reader.lastDiskOffset || 0);
|
|
@@ -4142,7 +4277,7 @@ let ZipEntry$1 = class ZipEntry {
|
|
|
4142
4277
|
extraFieldLength,
|
|
4143
4278
|
filenameLength
|
|
4144
4279
|
} = localDirectory;
|
|
4145
|
-
const checkAmbiguity = getOptionValue$1(zipEntry, options, OPTION_CHECK_AMBIGUITY);
|
|
4280
|
+
const checkAmbiguity = getStrictness(getOptionValue$1(zipEntry, options, OPTION_STRICTNESS), getOptionValue$1(zipEntry, options, OPTION_CHECK_AMBIGUITY)) == STRICTNESS_STRICT;
|
|
4146
4281
|
let rawLocalFilename = new Uint8Array();
|
|
4147
4282
|
if (checkAmbiguity && (filenameLength || extraFieldLength)) {
|
|
4148
4283
|
const trailingDataArray = await readUint8Array(reader, offset + HEADER_SIZE, filenameLength + extraFieldLength, diskNumberStart);
|
|
@@ -4592,26 +4727,191 @@ async function detectOverlappingEntry({
|
|
|
4592
4727
|
readRanges.set(index, range);
|
|
4593
4728
|
}
|
|
4594
4729
|
|
|
4595
|
-
|
|
4596
|
-
|
|
4597
|
-
|
|
4598
|
-
|
|
4599
|
-
|
|
4600
|
-
return
|
|
4601
|
-
|
|
4602
|
-
|
|
4603
|
-
|
|
4604
|
-
|
|
4605
|
-
|
|
4606
|
-
|
|
4607
|
-
|
|
4608
|
-
|
|
4609
|
-
|
|
4610
|
-
|
|
4611
|
-
|
|
4730
|
+
function getStrictness(strictness, checkAmbiguity) {
|
|
4731
|
+
if (strictness === UNDEFINED_VALUE) {
|
|
4732
|
+
// `checkAmbiguity: true` is kept as a backward-compatible alias for the strictest mode
|
|
4733
|
+
return checkAmbiguity ? STRICTNESS_STRICT : STRICTNESS_BALANCED;
|
|
4734
|
+
}
|
|
4735
|
+
return strictness;
|
|
4736
|
+
}
|
|
4737
|
+
|
|
4738
|
+
function getMaxAppendedDataSize(maxAppendedDataSize, strictness) {
|
|
4739
|
+
if (maxAppendedDataSize !== UNDEFINED_VALUE) {
|
|
4740
|
+
return maxAppendedDataSize;
|
|
4741
|
+
}
|
|
4742
|
+
if (strictness == STRICTNESS_STRICT) {
|
|
4743
|
+
// the comment must reach the end of the file: no trailing data tolerated
|
|
4744
|
+
return 0;
|
|
4745
|
+
}
|
|
4746
|
+
if (strictness == STRICTNESS_TOLERANT) {
|
|
4747
|
+
return Infinity;
|
|
4748
|
+
}
|
|
4749
|
+
// balanced: tolerate up to a legal comment's worth of trailing data (a 16-bit length); beyond that the
|
|
4750
|
+
// trailing bytes cannot hide inside a comment, so they are treated as a second thing bolted onto the file
|
|
4751
|
+
return MAX_16_BITS;
|
|
4752
|
+
}
|
|
4753
|
+
|
|
4754
|
+
// cap on how many out-of-window central directory probes the scan below may issue. A legitimate archive needs
|
|
4755
|
+
// at most a couple (the canonical record, plus one more to detect genuine ambiguity); every other reachability
|
|
4756
|
+
// check is served from the tail window already in memory. The cap keeps an archive whose comment is stuffed
|
|
4757
|
+
// with unreachable end-anchored records from forcing an unbounded number of (potentially remote) reads.
|
|
4758
|
+
const MAX_END_OF_CENTRAL_DIR_PROBES = 64;
|
|
4759
|
+
|
|
4760
|
+
// reachability rankings for an end-anchored candidate record (see getCentralDirectoryReachability)
|
|
4761
|
+
const CENTRAL_DIRECTORY_UNREACHABLE = 0;
|
|
4762
|
+
const CENTRAL_DIRECTORY_PLAUSIBLE = 1;
|
|
4763
|
+
const CENTRAL_DIRECTORY_REACHABLE = 2;
|
|
4764
|
+
|
|
4765
|
+
// Locates the authoritative end of central directory record. The canonical record is the last one whose
|
|
4766
|
+
// declared comment reaches exactly the end of the file ("end-anchored") and that points to a central directory
|
|
4767
|
+
// ("reachable"); earlier signatures (stale append remnants, bytes embedded in a comment) are ignored. When two
|
|
4768
|
+
// or more end-anchored records point to a central directory the archive is ambiguous, and the count is returned
|
|
4769
|
+
// so the caller can refuse it. A record that reaches the end of the file but points to no central directory (an
|
|
4770
|
+
// empty archive) is only "plausible": it cannot be corroborated, so it never counts towards ambiguity and is
|
|
4771
|
+
// chosen only when no reachable record exists — otherwise an empty record forged in a comment could outrank the
|
|
4772
|
+
// genuine directory. When no record is end-anchored (appended data or an oversized comment), falls back to the
|
|
4773
|
+
// last record within the tolerated window that points to a directory (see seekEndOfCentralDirectory).
|
|
4774
|
+
async function findEndOfCentralDirectory(reader, rejectAmbiguous, maxAppendedDataSize) {
|
|
4775
|
+
const { size } = reader;
|
|
4776
|
+
// an end-anchored record can only live within the last END_OF_CENTRAL_DIR_LENGTH + MAX_16_BITS bytes,
|
|
4777
|
+
// since the comment length that ties it to the end of the file is a 16-bit field
|
|
4778
|
+
const anchoredLength = Math.min(size, END_OF_CENTRAL_DIR_LENGTH + MAX_16_BITS);
|
|
4779
|
+
const anchoredOffset = size - anchoredLength;
|
|
4780
|
+
const anchoredArray = await readUint8Array(reader, anchoredOffset, anchoredLength);
|
|
4781
|
+
const anchoredView = getDataView$1(anchoredArray);
|
|
4782
|
+
const remoteProbeBudget = { count: MAX_END_OF_CENTRAL_DIR_PROBES };
|
|
4783
|
+
let endOfDirectoryInfo;
|
|
4784
|
+
let plausibleEndOfDirectoryInfo;
|
|
4785
|
+
let endOfDirectoryReachingEndCount = 0;
|
|
4786
|
+
for (let indexByte = anchoredArray.length - END_OF_CENTRAL_DIR_LENGTH; indexByte >= 0; indexByte--) {
|
|
4787
|
+
if (getUint32(anchoredView, indexByte) == END_OF_CENTRAL_DIR_SIGNATURE) {
|
|
4788
|
+
const offset = anchoredOffset + indexByte;
|
|
4789
|
+
const commentLength = getUint16(anchoredView, indexByte + 20);
|
|
4790
|
+
// end-anchored: the declared comment extends exactly to the end of the file. The comment length is
|
|
4791
|
+
// attacker-controlled, but the reconciliation against the (unforgeable) end of file is not.
|
|
4792
|
+
if (offset + END_OF_CENTRAL_DIR_LENGTH + commentLength == size) {
|
|
4793
|
+
const reachability = await getCentralDirectoryReachability(reader, anchoredView, anchoredOffset, indexByte, offset, size, remoteProbeBudget);
|
|
4794
|
+
if (reachability == CENTRAL_DIRECTORY_REACHABLE) {
|
|
4795
|
+
if (!endOfDirectoryInfo) {
|
|
4796
|
+
endOfDirectoryInfo = {
|
|
4797
|
+
offset,
|
|
4798
|
+
buffer: anchoredArray.slice(indexByte, indexByte + END_OF_CENTRAL_DIR_LENGTH).buffer
|
|
4799
|
+
};
|
|
4800
|
+
}
|
|
4801
|
+
endOfDirectoryReachingEndCount++;
|
|
4802
|
+
// the canonical record (highest offset) is found first; a second one is enough to flag ambiguity
|
|
4803
|
+
if (!rejectAmbiguous || endOfDirectoryReachingEndCount > 1) {
|
|
4804
|
+
break;
|
|
4805
|
+
}
|
|
4806
|
+
} else if (reachability == CENTRAL_DIRECTORY_PLAUSIBLE && !plausibleEndOfDirectoryInfo) {
|
|
4807
|
+
plausibleEndOfDirectoryInfo = {
|
|
4808
|
+
offset,
|
|
4809
|
+
buffer: anchoredArray.slice(indexByte, indexByte + END_OF_CENTRAL_DIR_LENGTH).buffer
|
|
4810
|
+
};
|
|
4811
|
+
}
|
|
4612
4812
|
}
|
|
4613
4813
|
}
|
|
4614
4814
|
}
|
|
4815
|
+
if (!endOfDirectoryInfo) {
|
|
4816
|
+
// no record points to a directory: prefer a plausible (empty) end-anchored record before scanning the
|
|
4817
|
+
// tolerated window for a bare signature
|
|
4818
|
+
endOfDirectoryInfo = plausibleEndOfDirectoryInfo;
|
|
4819
|
+
}
|
|
4820
|
+
if (!endOfDirectoryInfo) {
|
|
4821
|
+
endOfDirectoryInfo = await seekEndOfCentralDirectory(reader, maxAppendedDataSize, remoteProbeBudget);
|
|
4822
|
+
}
|
|
4823
|
+
return { endOfDirectoryInfo, endOfDirectoryReachingEndCount };
|
|
4824
|
+
}
|
|
4825
|
+
|
|
4826
|
+
// Fallback for findEndOfCentralDirectory when no record is end-anchored: appended data or an oversized comment
|
|
4827
|
+
// pushed the record's declared comment past the end of the file, so its position can no longer be reconciled
|
|
4828
|
+
// against the end of the file. Scans the tolerated window from the end and returns the first record that points
|
|
4829
|
+
// to a central directory, so a stray signature embedded in appended data cannot hijack discovery (which the
|
|
4830
|
+
// anchored scan already prevents for anchored records). Falls back to the first plausible (empty) record, then
|
|
4831
|
+
// to the last bare signature, so a degenerate archive still opens as before. The window ends at the file, so the
|
|
4832
|
+
// same in-window / metered reads as the anchored scan apply.
|
|
4833
|
+
async function seekEndOfCentralDirectory(reader, maxAppendedDataSize, remoteProbeBudget) {
|
|
4834
|
+
const { size } = reader;
|
|
4835
|
+
const searchLength = Math.min(size, maxAppendedDataSize == Infinity ? size :
|
|
4836
|
+
END_OF_CENTRAL_DIR_LENGTH + MAX_16_BITS + maxAppendedDataSize);
|
|
4837
|
+
const searchOffset = size - searchLength;
|
|
4838
|
+
const searchArray = await readUint8Array(reader, searchOffset, searchLength);
|
|
4839
|
+
const searchView = getDataView$1(searchArray);
|
|
4840
|
+
let firstSignatureInfo, plausibleInfo;
|
|
4841
|
+
for (let indexByte = searchArray.length - END_OF_CENTRAL_DIR_LENGTH; indexByte >= 0; indexByte--) {
|
|
4842
|
+
if (getUint32(searchView, indexByte) == END_OF_CENTRAL_DIR_SIGNATURE) {
|
|
4843
|
+
const offset = searchOffset + indexByte;
|
|
4844
|
+
const record = { offset, buffer: searchArray.slice(indexByte, indexByte + END_OF_CENTRAL_DIR_LENGTH).buffer };
|
|
4845
|
+
if (!firstSignatureInfo) {
|
|
4846
|
+
firstSignatureInfo = record;
|
|
4847
|
+
}
|
|
4848
|
+
const reachability = await getCentralDirectoryReachability(reader, searchView, searchOffset, indexByte, offset, size, remoteProbeBudget);
|
|
4849
|
+
if (reachability == CENTRAL_DIRECTORY_REACHABLE) {
|
|
4850
|
+
return record;
|
|
4851
|
+
}
|
|
4852
|
+
if (reachability == CENTRAL_DIRECTORY_PLAUSIBLE && !plausibleInfo) {
|
|
4853
|
+
plausibleInfo = record;
|
|
4854
|
+
}
|
|
4855
|
+
}
|
|
4856
|
+
}
|
|
4857
|
+
return plausibleInfo || firstSignatureInfo;
|
|
4858
|
+
}
|
|
4859
|
+
|
|
4860
|
+
// Ranks how strongly an end-anchored candidate record is backed by an actual central directory, used to decide
|
|
4861
|
+
// which record is canonical and which count towards ambiguity. It is intentionally conservative and does not
|
|
4862
|
+
// fully parse the directory (the caller does that for the canonical record):
|
|
4863
|
+
// - REACHABLE: the record dereferences a central directory (a central file header signature at the
|
|
4864
|
+
// reconciled offset), or, for a zip64 record, the zip64 locator that a genuine zip64 archive places
|
|
4865
|
+
// immediately before it. Only these count towards ambiguity.
|
|
4866
|
+
// - PLAUSIBLE: the record describes an empty archive, which has no central directory to dereference. Its
|
|
4867
|
+
// fields are indistinguishable from an empty end of central directory record forged inside a comment, so it
|
|
4868
|
+
// is accepted only as a last resort and never inflates the ambiguity count.
|
|
4869
|
+
// - UNREACHABLE: neither — stale append remnant or signature bytes embedded in a comment.
|
|
4870
|
+
// Signatures are read from the tail window (`view`, spanning `[anchoredOffset, size)`) when they fall inside it;
|
|
4871
|
+
// only a target below the window costs a (possibly remote) read, metered by `remoteProbeBudget` so a stuffed
|
|
4872
|
+
// comment cannot amplify into an unbounded number of requests.
|
|
4873
|
+
async function getCentralDirectoryReachability(reader, view, anchoredOffset, indexByte, offset, size, remoteProbeBudget) {
|
|
4874
|
+
const filesLength = getUint16(view, indexByte + 10);
|
|
4875
|
+
const directoryDataLength = getUint32(view, indexByte + 12);
|
|
4876
|
+
const directoryDataOffset = getUint32(view, indexByte + 16);
|
|
4877
|
+
if (filesLength == MAX_16_BITS || directoryDataLength == MAX_32_BITS || directoryDataOffset == MAX_32_BITS) {
|
|
4878
|
+
// saturated fields imply a zip64 record; corroborate it with the zip64 end of central directory locator
|
|
4879
|
+
// that sits immediately before it, so saturated bytes inside a comment cannot masquerade as one
|
|
4880
|
+
const locatorSignature = await readSignature(reader, view, anchoredOffset, offset - ZIP64_END_OF_CENTRAL_DIR_LOCATOR_LENGTH, size, remoteProbeBudget);
|
|
4881
|
+
return locatorSignature == ZIP64_END_OF_CENTRAL_DIR_LOCATOR_SIGNATURE ? CENTRAL_DIRECTORY_REACHABLE : CENTRAL_DIRECTORY_UNREACHABLE;
|
|
4882
|
+
}
|
|
4883
|
+
if (!filesLength && !directoryDataLength) {
|
|
4884
|
+
// a valid empty archive has no central directory to dereference
|
|
4885
|
+
return CENTRAL_DIRECTORY_PLAUSIBLE;
|
|
4886
|
+
}
|
|
4887
|
+
// the central directory ends where this record starts; reconcile the stored offset against that actual
|
|
4888
|
+
// position (see stored_cd_offset ⟺ eocd_pos − cd_size) so prepended data does not hide the directory
|
|
4889
|
+
for (const centralDirectoryOffset of [offset - directoryDataLength, directoryDataOffset]) {
|
|
4890
|
+
if (await readSignature(reader, view, anchoredOffset, centralDirectoryOffset, size, remoteProbeBudget) == CENTRAL_FILE_HEADER_SIGNATURE) {
|
|
4891
|
+
return CENTRAL_DIRECTORY_REACHABLE;
|
|
4892
|
+
}
|
|
4893
|
+
}
|
|
4894
|
+
return CENTRAL_DIRECTORY_UNREACHABLE;
|
|
4895
|
+
}
|
|
4896
|
+
|
|
4897
|
+
// Reads a 4-byte little-endian signature at `signatureOffset`, served from the tail window (`view`, spanning
|
|
4898
|
+
// `[anchoredOffset, size)`) when it falls inside it and otherwise from a metered (possibly remote) read. Returns
|
|
4899
|
+
// UNDEFINED_VALUE when the position is out of range or the out-of-window read budget is exhausted.
|
|
4900
|
+
async function readSignature(reader, view, anchoredOffset, signatureOffset, size, remoteProbeBudget) {
|
|
4901
|
+
if (signatureOffset < 0 || signatureOffset + 4 > size) {
|
|
4902
|
+
return UNDEFINED_VALUE;
|
|
4903
|
+
}
|
|
4904
|
+
if (signatureOffset >= anchoredOffset) {
|
|
4905
|
+
// the target sits inside the tail window already in memory: no extra read needed
|
|
4906
|
+
return getUint32(view, signatureOffset - anchoredOffset);
|
|
4907
|
+
}
|
|
4908
|
+
if (remoteProbeBudget.count > 0) {
|
|
4909
|
+
remoteProbeBudget.count--;
|
|
4910
|
+
const signatureArray = await readUint8Array(reader, signatureOffset, 4);
|
|
4911
|
+
return getUint32(getDataView$1(signatureArray), 0);
|
|
4912
|
+
}
|
|
4913
|
+
// out of budget: leave this candidate unverified rather than issue another read
|
|
4914
|
+
return UNDEFINED_VALUE;
|
|
4615
4915
|
}
|
|
4616
4916
|
|
|
4617
4917
|
function checkLocalDirectory(zipEntry, localDirectory, rawLocalFilename) {
|
|
@@ -4676,10 +4976,6 @@ function getBigUint64(view, offset) {
|
|
|
4676
4976
|
return Number(view.getBigUint64(offset, true));
|
|
4677
4977
|
}
|
|
4678
4978
|
|
|
4679
|
-
function setUint32$1(view, offset, value) {
|
|
4680
|
-
view.setUint32(offset, value, true);
|
|
4681
|
-
}
|
|
4682
|
-
|
|
4683
4979
|
function getDataView$1(array) {
|
|
4684
4980
|
return new DataView(array.buffer, array.byteOffset, array.byteLength);
|
|
4685
4981
|
}
|
|
@@ -5469,6 +5765,17 @@ async function getFileEntry(zipWriter, name, reader, entryInfo, options) {
|
|
|
5469
5765
|
if (releaseLockWriter) {
|
|
5470
5766
|
releaseLockWriter();
|
|
5471
5767
|
}
|
|
5768
|
+
// A buffered entry uses a temporary stream (see `createTempStream`). When that stream is
|
|
5769
|
+
// backed by a resource (a file, an OPFS handle, ...) it must be released on every exit path,
|
|
5770
|
+
// including the error path where the stream is otherwise abandoned without being closed or
|
|
5771
|
+
// cancelled. `dispose()` is optional and best-effort so it never masks the original outcome.
|
|
5772
|
+
if (bufferedWrite && fileWriter && fileWriter.dispose) {
|
|
5773
|
+
try {
|
|
5774
|
+
await fileWriter.dispose();
|
|
5775
|
+
} catch {
|
|
5776
|
+
// ignored
|
|
5777
|
+
}
|
|
5778
|
+
}
|
|
5472
5779
|
}
|
|
5473
5780
|
|
|
5474
5781
|
function requestLockCurrentFileEntry() {
|
|
@@ -6506,13 +6813,184 @@ function getMimeType$1() {
|
|
|
6506
6813
|
*/
|
|
6507
6814
|
|
|
6508
6815
|
|
|
6816
|
+
const DEFAULT_THRESHOLD = 1024 * 1024;
|
|
6817
|
+
const DEFAULT_DIRECTORY_NAME = ".zip.js-temp";
|
|
6818
|
+
|
|
6819
|
+
// Builds a `createTempStream` factory (see `ZipWriter`'s option of the same name) that spills the
|
|
6820
|
+
// data of a buffered entry to the Origin Private File System (OPFS) instead of keeping it in memory.
|
|
6821
|
+
//
|
|
6822
|
+
// It is meant for the buffered-write path (keep-order concurrent `add()`, non-seekable output, ...),
|
|
6823
|
+
// where the compressed data of an entry has to be held until the writer is free. In memory that data
|
|
6824
|
+
// grows with the entry size; here it is written to an OPFS file and streamed back, so peak memory
|
|
6825
|
+
// stays bounded.
|
|
6826
|
+
//
|
|
6827
|
+
// It is hybrid on purpose: an entry stays fully in memory until it exceeds `thresholdBytes`, and only
|
|
6828
|
+
// then spills to a file. Small entries never touch the disk, so a workload made of many tiny entries
|
|
6829
|
+
// keeps the speed of the in-memory default; only genuinely large entries pay for (and benefit from)
|
|
6830
|
+
// the file round-trip.
|
|
6831
|
+
//
|
|
6832
|
+
// OPFS is a browser/worker feature; there is no fallback here. Feature-detect
|
|
6833
|
+
// `navigator.storage.getDirectory` (or inject `getDirectory`) before using it, and let the writer use
|
|
6834
|
+
// its in-memory default elsewhere.
|
|
6835
|
+
//
|
|
6836
|
+
// Options:
|
|
6837
|
+
// thresholdBytes spill to a file once a buffered entry exceeds this size (default 1 MiB).
|
|
6838
|
+
// directoryName name of the OPFS sub-directory holding the temp files (default ".zip.js-temp").
|
|
6839
|
+
// getDirectory returns (or resolves to) the root `FileSystemDirectoryHandle`. Defaults to
|
|
6840
|
+
// `navigator.storage.getDirectory()`. Inject it to run inside a worker with a
|
|
6841
|
+
// pre-obtained handle, or to test against a mock.
|
|
6842
|
+
function createOPFSTempStream(options = {}) {
|
|
6843
|
+
const {
|
|
6844
|
+
thresholdBytes = DEFAULT_THRESHOLD,
|
|
6845
|
+
directoryName = DEFAULT_DIRECTORY_NAME,
|
|
6846
|
+
getDirectory = () => navigator.storage.getDirectory()
|
|
6847
|
+
} = options;
|
|
6848
|
+
// The temp directory is resolved once and shared by every entry of this factory.
|
|
6849
|
+
let directoryHandlePromise;
|
|
6850
|
+
function getTempDirectory() {
|
|
6851
|
+
if (!directoryHandlePromise) {
|
|
6852
|
+
directoryHandlePromise = Promise.resolve(getDirectory())
|
|
6853
|
+
.then(root => root.getDirectoryHandle(directoryName, { create: true }));
|
|
6854
|
+
}
|
|
6855
|
+
return directoryHandlePromise;
|
|
6856
|
+
}
|
|
6857
|
+
return async function () {
|
|
6858
|
+
const memoryChunks = [];
|
|
6859
|
+
let bufferedSize = 0;
|
|
6860
|
+
let spilled = false;
|
|
6861
|
+
let fileName, fileHandle, fileWriter, fileReader;
|
|
6862
|
+
|
|
6863
|
+
// Move whatever is buffered in memory to a fresh OPFS file, then keep writing to that file.
|
|
6864
|
+
// `FileSystemWritableFileStream` is a `WritableStream`, so it is driven through the standard
|
|
6865
|
+
// writer API rather than its non-standard `write()`/`seek()` convenience methods.
|
|
6866
|
+
async function spillToFile() {
|
|
6867
|
+
const directoryHandle = await getTempDirectory();
|
|
6868
|
+
fileName = crypto.randomUUID();
|
|
6869
|
+
fileHandle = await directoryHandle.getFileHandle(fileName, { create: true });
|
|
6870
|
+
fileWriter = (await fileHandle.createWritable()).getWriter();
|
|
6871
|
+
spilled = true;
|
|
6872
|
+
for (const chunk of memoryChunks) {
|
|
6873
|
+
await fileWriter.write(chunk);
|
|
6874
|
+
}
|
|
6875
|
+
// Release the in-memory copy; from now on data lives in the file.
|
|
6876
|
+
memoryChunks.length = 0;
|
|
6877
|
+
}
|
|
6878
|
+
|
|
6879
|
+
const writable = new WritableStream({
|
|
6880
|
+
async write(chunk) {
|
|
6881
|
+
if (spilled) {
|
|
6882
|
+
await fileWriter.write(chunk);
|
|
6883
|
+
} else {
|
|
6884
|
+
memoryChunks.push(chunk);
|
|
6885
|
+
bufferedSize += chunk.length;
|
|
6886
|
+
if (bufferedSize > thresholdBytes) {
|
|
6887
|
+
await spillToFile();
|
|
6888
|
+
}
|
|
6889
|
+
}
|
|
6890
|
+
},
|
|
6891
|
+
async close() {
|
|
6892
|
+
if (fileWriter) {
|
|
6893
|
+
await fileWriter.close();
|
|
6894
|
+
fileWriter = null;
|
|
6895
|
+
}
|
|
6896
|
+
}
|
|
6897
|
+
});
|
|
6898
|
+
|
|
6899
|
+
// The writer always closes `writable` before reading `readable`, so `spilled` is final by the
|
|
6900
|
+
// time `pull` runs. It is read lazily here (not in `start`, which runs at construction time,
|
|
6901
|
+
// before anything is written and before `spilled` is known).
|
|
6902
|
+
let memoryIndex = 0;
|
|
6903
|
+
const readable = new ReadableStream({
|
|
6904
|
+
async pull(controller) {
|
|
6905
|
+
if (spilled) {
|
|
6906
|
+
if (!fileReader) {
|
|
6907
|
+
const file = await fileHandle.getFile();
|
|
6908
|
+
fileReader = file.stream().getReader();
|
|
6909
|
+
}
|
|
6910
|
+
const { value, done } = await fileReader.read();
|
|
6911
|
+
if (done) {
|
|
6912
|
+
controller.close();
|
|
6913
|
+
} else {
|
|
6914
|
+
controller.enqueue(value);
|
|
6915
|
+
}
|
|
6916
|
+
} else if (memoryIndex < memoryChunks.length) {
|
|
6917
|
+
controller.enqueue(memoryChunks[memoryIndex++]);
|
|
6918
|
+
} else {
|
|
6919
|
+
controller.close();
|
|
6920
|
+
}
|
|
6921
|
+
},
|
|
6922
|
+
async cancel(reason) {
|
|
6923
|
+
if (fileReader) {
|
|
6924
|
+
await fileReader.cancel(reason);
|
|
6925
|
+
}
|
|
6926
|
+
}
|
|
6927
|
+
}, { highWaterMark: 0 });
|
|
6928
|
+
// highWaterMark 0: do not pull (and possibly close on an empty buffer) until the consumer
|
|
6929
|
+
// actually reads, which the writer only does once the data has been fully written.
|
|
6930
|
+
|
|
6931
|
+
// Called by the writer on every exit path (success, error, abort). Best-effort: it must never
|
|
6932
|
+
// throw. Closes any still-open file writer, then deletes the temp file.
|
|
6933
|
+
async function dispose() {
|
|
6934
|
+
if (fileWriter) {
|
|
6935
|
+
try {
|
|
6936
|
+
await fileWriter.close();
|
|
6937
|
+
} catch {
|
|
6938
|
+
// ignored
|
|
6939
|
+
}
|
|
6940
|
+
fileWriter = null;
|
|
6941
|
+
}
|
|
6942
|
+
if (fileName) {
|
|
6943
|
+
try {
|
|
6944
|
+
const directoryHandle = await getTempDirectory();
|
|
6945
|
+
await directoryHandle.removeEntry(fileName);
|
|
6946
|
+
} catch {
|
|
6947
|
+
// ignored
|
|
6948
|
+
}
|
|
6949
|
+
fileHandle = fileName = null;
|
|
6950
|
+
}
|
|
6951
|
+
memoryChunks.length = 0;
|
|
6952
|
+
}
|
|
6953
|
+
|
|
6954
|
+
return { writable, readable, dispose };
|
|
6955
|
+
};
|
|
6956
|
+
}
|
|
6957
|
+
|
|
6958
|
+
/*
|
|
6959
|
+
Copyright (c) 2025 Gildas Lormeau. All rights reserved.
|
|
6960
|
+
|
|
6961
|
+
Redistribution and use in source and binary forms, with or without
|
|
6962
|
+
modification, are permitted provided that the following conditions are met:
|
|
6963
|
+
|
|
6964
|
+
1. Redistributions of source code must retain the above copyright notice,
|
|
6965
|
+
this list of conditions and the following disclaimer.
|
|
6966
|
+
|
|
6967
|
+
2. Redistributions in binary form must reproduce the above copyright
|
|
6968
|
+
notice, this list of conditions and the following disclaimer in
|
|
6969
|
+
the documentation and/or other materials provided with the distribution.
|
|
6970
|
+
|
|
6971
|
+
3. The names of the authors may not be used to endorse or promote products
|
|
6972
|
+
derived from this software without specific prior written permission.
|
|
6973
|
+
|
|
6974
|
+
THIS SOFTWARE IS PROVIDED ''AS IS'' AND ANY EXPRESSED OR IMPLIED WARRANTIES,
|
|
6975
|
+
INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
|
|
6976
|
+
FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JCRAFT,
|
|
6977
|
+
INC. OR ANY CONTRIBUTORS TO THIS SOFTWARE BE LIABLE FOR ANY DIRECT, INDIRECT,
|
|
6978
|
+
INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
|
|
6979
|
+
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
|
|
6980
|
+
OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
|
|
6981
|
+
LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
|
|
6982
|
+
NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE,
|
|
6983
|
+
EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
6984
|
+
*/
|
|
6985
|
+
|
|
6986
|
+
|
|
6509
6987
|
try {
|
|
6510
6988
|
configure({ baseURI: (typeof document === 'undefined' ? require('u' + 'rl').pathToFileURL(__filename).href : (_documentCurrentScript && _documentCurrentScript.tagName.toUpperCase() === 'SCRIPT' && _documentCurrentScript.src || new URL('index.cjs', document.baseURI).href)) });
|
|
6511
6989
|
} catch {
|
|
6512
6990
|
// ignored
|
|
6513
6991
|
}
|
|
6514
6992
|
|
|
6515
|
-
const A="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";function g(g){let B;g({wasmURI:()=>(B||(B="data:application/wasm;base64,"+(g=>{g=(g=>{const B=(g=(g+"").replace(/[^A-Za-z0-9+/=]/g,"")).length,E=[];for(let I=0;B>I;I+=4){const B=A.indexOf(g[I])<<18|A.indexOf(g[I+1])<<12|(63&A.indexOf(g[I+2]))<<6|63&A.indexOf(g[I+3]);E.push(B>>16&255),"="!==g[I+2]&&E.push(B>>8&255),"="!==g[I+3]&&E.push(255&B);}return new Uint8Array(E)})(g);let B=new Uint8Array(1024),E=0;for(let A=0;A<g.length;){const C=g[A++];if(128&C){const Q=3+(127&C),Y=g[A++]<<8|g[A++],D=E-Y;I(E+Q);for(let A=0;Q>A;A++)B[E++]=B[D+A];}else {const Q=C;I(E+Q);for(let I=0;Q>I&&A<g.length;I++)B[E++]=g[A++];}}return (g=>{let B="";const E=g.length;let I=0;for(;E>I+2;I+=3){const E=g[I]<<16|g[I+1]<<8|g[I+2];B+=A[E>>18&63]+A[E>>12&63]+A[E>>6&63]+A[63&E];}const C=E-I;if(1===C){const E=g[I]<<16;B+=A[E>>18&63]+A[E>>12&63]+"==";}else if(2===C){const E=g[I]<<16|g[I+1]<<8;B+=A[E>>18&63]+A[E>>12&63]+A[E>>6&63]+"=";}return B})(new Uint8Array(B.buffer.slice(0,E)));function I(A){if(B.length<A){let g=2*B.length;for(;A>g;)g*=2;const I=new Uint8Array(g);I.set(B.subarray(0,E)),B=I;}}})("FABhc20BAAAAAUULYAF/AX9gA39/gQAHBAJ/fwCBAAWAAAsBAYAACgEGgAAWgwAZgQAgAwBgAIAAA4AADQEEgQAVAwBgB4MAHoAAHxIDQ0IHAAQCAAQICAADAAUDCgCAAAeBAAMBBYEABwMBAwOBAAgQAgEABQYAAQEFBAkEBAkCBoAAAR4AAwQBAwQDAwIEBwEBBAUBcAENDQUGAQGCAoICBgiAAJkiQdDVBAsHigQcBm1lbW9yeQIADGluZmxhdGU5X25ldwAHDYYADwdpbml0AAgRigAQB19yYXcAChCGABQJcHJvY2VzcwALhwBGBmVuZAAOFoYADxBsYXN0X2NvbnN1bWVkABELhAAZgwBthQA2gwBsARKFAFiHAGsBFIUAf4MAEwdnemlwABUPhQAUhQB+ARaGAFaBAH0CGBWFAA6NAHwCZGWJAHyFAA6CAHwCGhCJAA+CAHwCHBGKABOCAHwCHQ+FABSFAHwBHoYAVoEAfAkgBGZyZWUAAhWFABWMAIMKBm1hbGxvYwABC4IAVQppYWxpemUAABlfgAAPFmRpcmVjdF9mdW5jdGlvbl90YWJsZQGAABwbZW1zY3JpcHRlbl9zdGFja19yZXN0b3JlAAUcjgAbAmdlgABvDnVycmVudAAGIl9fY3hhgABbBGNyZW2AABIGX2V4Y2VwggBdBnJlZmNvdYAAJR4+CRIBAEEBCwwAIiMMDxcZHz82OTwMAQsK9eYCQgOAAKkQwycBC38jAEEQayIKJAACQI8AAhIgAEH0AU0EQEGkJygCACIEQRCAABIGC2pB+ANxgQAJEEkbIgZBA3YiAHYiAUEDcQSBADIGAUF/c0EBgAAfBmoiAkEDdIAAGQzMJ2oiACABKALUJyKAAAYECCIFRoIAUgkgBEF+IAJ3cTaAAqoRAQsgBSAANgIMIAAgBTYCCAuAAEgDCGohgAA3ASCCAEaAAAUEcjYCBIEADwNqIgGBAE0DBEEBgQASBwwLCyAGQayCAJ8DCE0NgAAbgQCGBEECIACBADUFACACa3KAADUEAHRxaIEAowN0IgCCAI+AAB+CAI+AAAaLAI8FAXdxIgSGAJEBAoEAkQEChACRAQCAAGiDAIWAAAoDaiIHgACigQDfBSAGayIFgwCMgAAZAgFqgQAuCgAgCARAIAhBeHGBAG4EIQFBuIEAoAQhAgJ/gABlAQGAABkHA3Z0IgNxRYMAeAMDIASAAD6AADyBAHWBASEDCyEDgQDpgAB2gAAchACEAQGDAAcBA4MAi4IBHIAAVgIgB4AAOYAA/oIAdYABCwJBqIIBCQILRYABCQULaEECdIAA5gMpIgKBAS4CeHGAAKqAAFkEAiEBA4IBqAUoAhAiAIAAg4EACgEUgAAKAQ2AAH6AARCEACqAANmBAIUFA0kiARuAADaAAUkBIIAACYABOAEhgQCnAgsggABUAxghCYAAFoAACQQMIgBHgABIgAAKAQiAADeEAcaAALEDCAwKggApBRQiAQR/gAHIAhRqgAFTgQB3AwFFDYAAiQtBEGoLIQUDQCAFIYABTYABmgMUaiGAAgWCADACDQCAAOUBEIQAEIAAMQYNAAsgB0GAAFsIAAwJC0F/IQaAAB8Dv39LggAnAQuAAhKAALUCIQaEAP4IB0UNAEEfIQiAAf6CAPKAAsQD//8HgALGgAHBASaBAlgGdmciAGt2ggKlCkEBdGtBPmohCAuEAvEBCIUBNQEBgQGeAgAhgQIKgQAHgAA8ARmAAB0DAXZrgABXCAhBH0cbdCEChQFJhQE0BAQgA0+AAJMBAYAAtwMEIgOAAIYBAIEByoAARAEDgQI/ggFoAgQgggLFB0EddkEEcWqCANwCRhuAAB0CBBuAAGQBAoAAj4ABZIEA7oEAMQIFcoMAhAEFgALPAQiBAruAAO6AAs8CB3GBAa6AANiFAeEBIYABHYIBwIABTIgBwoACLgJJIYAAbIEByYMBxAEFgQAJhQFTgAGTAQGDAW8DCyIAggByAQWAATkCIAODA02AAEGBAMsBBYEB5wEIgAA5gAAJhAHngAAKjQHngAKTgAAWgwHnAQWCAeeAAA+EAecBBYIB54ABK4ACeoAA+4MB54IDgIgB54IAEIQB5wEEgwHnAQeHA9gBBYEEgoMDQ4AEpoAAjYECnwNBEE+AAI2CA4uAATKGA4ECBWqBAJOAAFeFA66BA1WAABeGA7sBBYsEQIABX4AEJwEhgAHlgANGgQA6gQNWgAN0gQCZgQNlgAJvgABKAbCCAIgCAkmAAIgBsIAAH4IAgYEALAK8J4AAA4EAG4MAiIEAN4kAjYYEMYUAS4QCSgkvaiIDAn9B/CqAADuAAFMChCuAAAiBAmgFiCtCfzeAAFcGgCtCgKCAgAABAQSBAA4R/CogCkEMakFwcUHYqtWqBXOBAHoCkCuCAScDQeAqgwAIBoAgCyIBaoAFooABkwJrIoACI4AEmQVNDQhB3IEAZAIiBYAAZgHUggAKAQiABKMFIgkgCE2AAUcFCUlyDQmAAvmAAEUDLQAAgAKQgAJvhQX6hADYgQA5BOQqIQCDAlqBAD+BAY2AADwBCIICagNqSQ2BAtuBAhKCAkMEQQAQBIAFdwJ/RoAB+QMBIQSAAMmCAR0BQYAAk4AD+4AGIYEC/AFrgQVTAWqCAs0EcWohBIAB8oEAqwEDhACrgQERgwCrgANFgQVnAgVNgAFKAQeAAKuBACqAAF+AAWMFRw0BDAWBADiAAEyAAOuBABaCAkKAAFOBAJUBRoAE/gECggMVgQCKgAEJBUEwaiAEgQC4gAHtAwwEC4MBcYEDIAMgBGuBAIkHAmtxIgIQBIMALgECgAB3gAKqgQArgADcgADNBEcNAguBAWgB4IEAlgFBggWsgAWohADpggDygQBoAXKBBSQDTXINgANTgABQgAPoCAZBKGpNDQULgADOgwDRgQDPggGsAdiCAA4BAIECTgLYKoEDSQEAgQGFgwFxAQOHAXGDANOBA2uAANUCIgWAANeCABKDAWuBAMcBtIMCe4EBSoAAewEbgQQtAbSDAr2CAmkEQegqIIEGzIAAUIIAFQVBxCdBf4EACALIJ4MCe4EADAHwgwJAgQHggwbPgwewgAZQAdSAAxCBBlgC2CeBBSeAALsDQSBHgAB5gQMBBARBKGuAABABeIAA6QFBgQJrgAHegwMOhAegggbOgAN0hQMIBAJqQSiBA2wEwCdBjIEBe4ED4IABzoABgQFNgQZkAktygwDaBAxBCHGBAAqAAdkCBWqBADCAAFEBA4AAZgEDggBmgAhRggN0ArAngwOPgQFPgAAtgACJgwBvgAClggBvgABWkABvAQOCARMCDAaDAAeFAT0DIAJLiAE1gwH7AQWCAYACAkCBBpmEAYKBBPeEAXoDAQwCgQWcAi0AgQCtgATgAQuEAa6BCSyDAa4BA4ECaYEHPIICjAMiBUmEB1kBCIIGTJQBQIIHyIwBQAEHmQFAgABiAgVBgAf4gQBBA2pBL4AAT4AAKAEDgAVMgAmUAwFBG4IJLAlB7CopAgA3AhCAAAsB5IMACwEIgAAUgglbgQBwjQIghAIMgAAgARiABK+CAhOAAJiEBL+AAWsBQYABHoEE4YAA04EDAgMgA0aBBu2DBU0BfoAJx4AG/4EAFoAGeoQAuoIIxQEAgAj2AwJB/4EKR4AACIQJE4AAFYQKVIAFLoEJ44AJEQEChQkRgAARggkRggmGgQE6AQuABseAAN6BCRGAAGCABnkCQQyABbYBCIEFMwEfggc3Af+EB+EBAoAH4YAAGZAH4YAAsYAHAgY2AhwgA0KCARMBAIAHPQNB1CmACZ6CBO+DCDuAArOBCjmCBQqAABOBAomDCZuBAHaCAI8BAoAIB4AAVYIIB4AIZoEIB4IH2oAHpoECMYEK4YIHgAECggOugAfngQdwgQfXgwMSgAf0AiIEgQbrAQWCBuuBAFcBEIEAmoAB8wMYQQiAAWUCAyKACDACQQyFCguAAdeBAPCDAIGBCg+AAMOACNmAACMBGIABAgEMgAA7hAbwgQL2gwRLhAatgAZoAU2ACIKAAm6BB8yxBq+AAyUEoCdBMIEAOYEDNIIIxIMHGoIC24ADLIIDb4UCxwFqgAYdhQBCgAmQgAaHggAVgAUJAiAIgAbwA2shB4UE5QIgBIELcoED3YoD0AEHgwUfgQDlhAvcgAHgggf3gwAxgAeZggAxAqwnhAijjgAxgQIlgwEGgQFAgAFogQWbBANxQQGAAD+AACSACiQBCYEAFoACPYIM24MClIAAEYEI0AECgwwGgwKWgAwKgAA5AXaDDJwBAoEC7IcLh4ECd4EANQMYIQaAAEaABDOBBB6CAEWCAR+BACaBAaWAACaAAB+AABiAC1yACRcBBIIJF4IB+4EJq4AAEIEJF4ALi4IKLoAGjYEJF4IENIAAMIADV4ELHoEJvYIAMYECLAEFgwkXggqOgACSAQaACayDAGABHIAA5AECgAW6gQoKggEpgAF+gALYgwGrAwINAYACyIMC3oEA1YUA0oEAOwIgBoAAXYEAMAEGgQAsARCBANeCAAoBFIAC5oIMDoAI6IACl4QAtYEDXoEA2YADOoEAJQEYggEEggw4gQJFgAAZARSGABkEByAJaoAL0wEEgAAHgQLtAQSBA32BAlaFBCSFBNmAAAoBaoIMwoAAEoMBjAEHkwQgAQetBCCDAymBAAeEAbGABCgBAoEAZoQEKAEHgAQoAQeSBCiAAVuCDXSGBCgBAoUEKIIPIYQEKIIEtQN0IgWFBCiAA9uDAJKGBCgBB4AEKIAFB4IEKAEChAwvggYigwH0gQ56ggQoAQeBBCiBDA+BAe2DC/+BBYGBBCiDC0SCAfyGBCiAANYBGIAAB4QA5IEA8oUBBIEGeoMLk4MEKoECL4EAK4gBCAELgAy5ggPaggIAAQiDAkKAAGYBHIAA0IAAzoACbIACQoEPDoAAioECQoIDXYAG84EA4gEHhA8dgQGvgwBAgAoEhAJAgAoMhAJAggAKgAJAhA5OAiAIgQCEgwDIggutgACGgAaNggDGhQwzgQJAggAZARSFABmAAFwDA0EPgwpnAQOBBKmAA4uHC72DBH2GBCGBDA6EAB+AAAqBBG8BA4YCXgIEaoIBj4AAEoMCXoAITJECXgEDogJegAcqgQJegAAHAQyBAs2DAAeHAl6CAGaEAl4BA4ACXgEDlQaGggA8AxwgBJEGhoEDGoIQuYUCWIACtIQGgIEHqYMAcQEYgQCYAQOWBoeDAl+FD/OAB6OEBoeCCSGBACaBBfKBAl8BB4cPWYEAXgEQgQtPgwPYhQDlgQDzggb0gwTdggAWgATwgQEJgg2lgAQbgwTyggDUgQ4FgwJfggT6AQmDAl+AADyEAl+AAe+AAl+BBWeAACiNAl8BC4MCX4YCXQMCIAmEAl0BCYYCXYIACogCXQEJgQCCgxBQjwJdgxB3mQJdgQv/igJdgAl6jQJdgAUChAAfgAAKgAOSiAJdgA5pggJdihHqgQ4+ggGFgAJhhRHogAFehQJbAQSEAc+IAluCEjWCAVKDEeOED1mCAfEBCIEG/4IR24EOnYEAboEIgIEBYwELgA4SAxBqJIAASgYL3gsBCH+BBs+CAOwEQQhrIoEHDwIEa4IM4oAAmIALOAIhBYEBUoACiYIGWIACXYAGgIAEPYIT0oAAL4MLC4AKp4EC5oQE6IAE6oMHegEDgQbegAArAQyAAkEBBIQDSIAAPoECEoANhwECiQcyAQSGBzKADZyAACIBGIER14YAQYAAMIUA4oES2oEMAIAAFgMUIgKABx0BA4IHHYAADwIQIoAGeoAAm4IHHQEEgALKAQSAEeoBAoACQIAHHYABIYIAMIEKdIEHHYIAEIAAMYECwgEGgwcdgAijgAJmgQ2ZgAf1AgNHgA5UgAE4ggJngA5+hgZ/hQgtghRxAgAPgQHmiQCZgA3tgRAQASCBEkeBAi6BAsEBBIcFIAEDhwUggwuoiwdiAQSIAsWABuCEAsWAAQmEAsWCAAqAAsWAApuBCeOBBv+ABaaCAMmDDx6BAsWCAJGAAsWDASGBAdmCABkBFIcAGQIgBYQRngEEgACcAQGAAdKGFb+AAYeDBD+DCWuCFN2OCWuADUyMCToBA4MB8AJHDYERdYMQUwG4gwAIAQ+ECYWBD4uSCYePAE2GCYeAAV2CBIeAAoSCAK6JAkaCEkiAANGMCXiKAkaOAjOEEpCAB3CGEouLACSDAgODAleIEouAAUWADLi0AleACBSACbuOAkCHCm2CDl2BBv+IB1OIAjOIB1OdAjOJB1WFAjOCAAqIAjOHB1WQAjODAP2SAjOOALiBAqGAD9OFAyWAAa2FCxSBCyyCBNGAFrOGF/yBBkKBBNEBAIUEz4AEL4IEzwEChQYlAQuCBl+CCICEDLiEFsCDDLiAAkoBH4IGiIUHKQEAgAcpgASzgAcpAQKDBymBCQKCBymBBuOBALmGCYeBBkOCBykCBAKABO6AAJaDCYkBBoAAlgEBigcxAQaCAJOCDVqBDSWADuyCBW2ABzCAB+yCBzABAYMHMIACioEFq4ICD4YHMAEAgQcwAQGBBzCBDMWABzCCEhCCBzCBCy4CIgSCAheCCY+BAF2BFNQBQYIA9wIDIoYBBoEIhIcXroAAJ4AA44AAiAIAC4ACdYAFEIASi4MBfIIBGoIBjYALZ4IRngHEggISgBAPgBJRAiAAgA/FgBNTBIwLAQeAAA2AE7eBBceDEGeBBOKKBc6CEHuAALmECEiBACaBEoWEBo+EEL8BDIEX/oUJC4MKNAEEjAXDgQ+JhgN9gAAigAzkgQCihhEAggDThAHWggOQggywAQSAA2yBFdeEFloBBIIWnYgV94AHAoAGZoIV94IE0oABRYIF44MAEIQBVYQX3pIFw4IDNocFw4EBw4UFw4EAG4EEZoUAmYIItIIFw4AASoQNJYAAlgEcgABRgAOQgAHygAOQAQCBA2ABBIIDkIMKIIsDkIQak4IDkIAPFYYNJYEB9YMNJYAACoADkAEDggOQgAhFgQOQggD6gQOQggEcgQOQgAAlgAN3ggEhggOQggAZgQOQggAZhgWvhADukQW0ggWGhgW0gBODhBbahg+ynwW0gBWwhAW0ggAfhgW0kABNgRq8hAFOgQg4ggJNgwW0hwI3ggVxgAFsjAW0igI3iwGLhQW0gAE1igW0iQJIhQW0gQJIiAW0gAJIhQW0rwJIggW0jwIxhgDmgwW0hwIkggW0iAIkggW0owIkgAx4owIkhgW0jAIkhwW0iwIkkQC4gQ1VhAW0hAGtAQGFCZaPBbSACq6BHKaABbSACCOFDN6BCtCKBbSBBOOBBZ+FCnyEEMeDCpiCBbSABYuGBbQBAYYbRI0FtIISIYAAuQMcIACDBbQBA4UFtIARb4YPO4EGSIAWaQEHhxNjgwsUggCEghbKhAzjAQGABbOAAMGCBbMBA4MFs4ABH4EFs4ICDoIQWoICqIEFswEDgQWzgQAHgAWzgAJ6gACVhgzjggfKAQeFELuAApWCAVmEAOqDBpeFEgSEDdaCAQ2AEvWCA9iDDPeDAQ0DCwtJgQvaAZCDDjuBFR8BaoELYgECggs1gAB0ggNQgheJAyAAP4AFAgF0gB6RhxNFAX+AAUwBkIQKkAMBCwaAAC0GJAALBAAjgBOzAgEBgAbVBEHEABCAEBmDC8gCBGuBGZOAHiSCAA6ABh4DAPwLgRjSggVrgAEjASSBB40FNgIgIACAEhkDCwsRgAAmgQFRAX6CB8ULEBAJC9kCAQN/QXqABzAEQEGUCIEATQExgQI4AX6BDHKEAFWEBLgBIIMCfIAACgEkhAAICihBAUHYNyACEQGABlaBAFcBfIEAV4MRF4AA5gM2AjiFAa8EAkG//oAACYAAZQQgABAkgxYPBkEfdSIDc4EWCIABj4AUBYAWLoMC0gEogw58AnZBghn+gAcSAU6AHl0BIoMQtoIAPYIAXAM0IAKBAj8BLIkAFIAA54EAB4ABloEAG4ANzYIN8YAAX4ADhgEwgALIgQAWATyDACsBJIAAB4AbOYIOHAFCgRtEAXCCEcYBQoAAqAE3gQ3IAkKBgwAUAcyAAOCAACsCtAqCCr4BcIMA0QFUgwAHAlBBggkNgAEJgxmFAiQRghwQgQ+5gAIsjAFtAXCAAW0BEoIB+oIOU4AGlQlBBBANC4YlASKEIV0CFCSBAXgBGYYBJIEHjAIiEoQBbAMEIROEG1uBAjcBE4AEZwMAIROCAH2BBJAB3IALOgEfgACnBfQFaiEVgAAIAdiAABABG4AACAHwgAAIARqDAL8CIRaBACCAABADEUGcgRgdBCEcQZiCAAgEHUGUK4AB+AIhHoEDNgNAIQqBAAcBPIENlAFBgBg2CAJJISBBfSENgAAOBgZHISEgE4ECGIEDLwMXIRCBGPyRIg6UAAKBCZCRIjyBCVSACaGAAXkXaw4TBAUGBwgJAwIMDQEaABwPIyMVIiOCBIEFTCEGDBqGAAqAFtKAAAoBbIEeUoEACAEigAlGAygCYIAO0wUDIAxJG4AAIQQGCyAggR/ggABWgAZUBQ4hDQwdgwTIAg0QgA8UAghygBXiAQiBBAKCF48DCkECgga2A0UNDoEajgFrgBVqAQOAARIDIAp0gBR6gAEKgAJBgAS3BCAJIQqDINSBEYCAAlIDCEHBgABegALUhgDLgAAYAXaCFkkCaw6AIzkBAoAE6gEegQ12gh+eBQgDQEGQgBztgA/vA5ABRoEBxQERgSApBnRqQQg7AYEgLIAAZIEKhIAfngNBgAKADL2AHRcBAoQAKIAFDYAAKAEJgQAogAALgArdhAAoAZiBHywBCIAAB4oAUAEHjQBQgAA1AaCLAEuCAHOHAEuAAJ8BBIACDgNBoCuBBIECoDyDAAkDIBRBgBE8AQyABYkBEYAAQIAAF4AAEQcMaiAVECUaggBUASCKAFMBBYwAUwGcgABPATyBArEBHIMAS4AQoAEMgCChAxFBIIoASoACfQNBATqABHcDoCshgQGjAiAdgANYgAN/AYmAA38B0IADiwFYgAATgABCgANyAkHHggRDAkEBgAKqASGACjsCCkGAGC0BCoIV9QIhB4EAHYEIPYEghYABFIEB8YASLQHEgQGggwvYAsILgRk7AdGBABGCG8GAAEqBER6IAEOFAD0CDBuBABmAGAUBBYAGDwEKgBidgAAcgRm0AkEfghgHggfwgAIkgAF5gQIkAQWEAiSDAXCDEtsDBQwCgAVugAFTgQIgAQaAAFQBCoIAkQEegAWagQh5BP//A3GAAqsBB4ElAgIQdoILNQJB3YMSpoEAoYIKsYACawQbC0HCggBAAQKBAAiEHLMDNgJEgABagAi9gABUgQOTgAQdgQBbgACzAwJBw4IAJoIC5wFEgR4hggRmgAAEgBvrAgMggAdnAiAQgQAKgQKOgAAqhAMWgAA5ARKADjoCAxCAGxGCADmABZCAAGSAAC0EEmohEoEANgJrIYEAO4AA1oESfIAADgMEDBmBAG2DBdABDIEKooIDQgINS4EYrowBHYUDQYQBHYADeQFqgwNEggEegQGegwCGgQBSgAEQAR+AARcDQYECgBowAWSCABACBXaAABOAADsDNgJoggAQBQp2QQ9xgBxeASKACScBYIAATgEOgwG9AQ6CAb0CQR6CIekCQaGKAUqAAKGAAAwBxYMCOgIAIYAEKIEFnwFsgAMVgAOvAwYgDIEKogETgAAJBwZBE00bIQmAAMsDBiAJghdsgAATgAr+gAFxAWyAAuOAAAwFdC8BsA6CAuoBAIEC6gEDgARlAQCBB2uYBE4BCqMEToADYoAWkYMAaYAADIYAaYAA2wIHcYEAbIsCpwEEgADGhQKrgwBBARaDBpKAAAeABqCBHYyBAzWAAA6ABqCAA3AFEyAaIBuBA2wCIg6CASEBv4IQGYYBIQEXgQEhAcaEAmGCAR2AASgBDoEOh4ICSgNkIg+BAAcEaGohDIAA3AELgAVfgAEygB2qBCgCWHSAAsEBIYIVWwNQISKAAQGAGzWAANgBCoIBBQEigAM8AhhxgAnZB2oiIy0AASKAAwaAH0OBCuiBGHSAARWAAQGJAz8BCYEBFQEJhQM/gADXgAGfBiMvAQIiCIUVhoAI/oYBJoAADIABH4IExYEj5oEBHAIgBoMBHAELgRZXAX+FBm2AAnoEEGsOAoAFjIERpoAJgYIPx4YAjAEdowCMigBlAwUgC4IJuQJBh4sDswEJgAGTAQOAAvmAJqaBBmyAAgaBADOAJZSBAJiAJFiADqeBJqiBALsDIBFqgAAeAi8Bgg7HgBY6jQCXgBDOpgCXhAIbgACagAszgwIggAI2gABUggxfgAp6jABcARupAFwBB4gAXAEHgwBcA/8AcYAnSoAnkYECIgMEIAyAACkCC2qAAhSWARGAA92BBT6CBiqDAbgBBIEBuIEBz4ACYoMDIYQCyIAFowFsgBfAhAA4ggAUBC8B9ASDAW8ClAqKArcBFoECt4AAcYUC64QDAIEGrQIgD4wC8gGjiwLyggA7gARDAVyDBPMBcIADPoEGmYIC7oIAoYEC8IAAQwEfiABDAfGNAEOEBnGGBpaAAzSEBZGAAAsBDYMAZAHIhQWRgQNXAtA3iQM3ggNVAVCAA8qLAzcBDIABboAE44EDNwELiwM3gAP0ogG4AQuAAzUCIQ+AAvqAAECAKeKBC1oF/wFxQQ6BAEcDBiEMgACdAQaBAhoDDCAPgQBmAiEYgACVAQaAAcKCAJWCAakCIBiAAIQBC4AoGgF2ggCHAQ+BAIcBDIAY1oEB5IAAiAENqQMzgQdCggOYgABGAQCAAe4BD4IAnYEB6wEPgQZlgAVkAiAMgAXeAtA3gAAvAQyDAmwBDIEALwELgQC0gA/ZghUQAc2DAXMBEoEWJAEggSYchQZ9gAAJgCSoAtA3gwAbAsAAgQAcAwBB1YEH6YcBqoAAHAMCQcmFB0ABBIEGZIAB+wFMhQJmgg/ZAQiMAYaAALyEAO6ACFKiAO6CAkmAAMcBBoMAzoQHS4AH4gIgBoEBWoAOZAEMgQDxiwSthQLpgCr+ARCDCiQBEIEA7YQHFIAL3QESggBHgAkdhgJMAiAQgQCPAxAgEoEAggMSDBGBEUeCB5sBCoEXEYAB0AEKggdagAXPhABGhgAiggAYgAcIhAAYgB4mhwAYggASghMekABMgAE8hAA0AQ6ABu+ACX4BDYILfgJB0IMAkYYJI4MJNAEKhCvMAkQhgiKckgBSgADLhABSgCk1AwJByoUBnYABIwLUN4ArtoEAQAFcgwKRgQALAVSSAyYBC4MDJoICn4cDJoIbeqABsIICiYEGZIECmQIiD4MqJYIBw4IHloAAYgELiAMfAQ+DAx8BD4YDHwEPhgMfggOmiAMfpQIxiwMfhQI9gAIcgQO3gAQeggPHgACIASGADMmBAycBCoUDJ4kCQQEPhgL1AfGKAvWGAlqAKx0DAkHLhQFgAQ+ACT6DAv2CBWsBSIcDBIgBXwMgBgSDJtOFAwOCHyq0AwMBSIkDA4EAcpIDAYEApQHMhAUrhgMJgAARhAIlAQaAB9CCAE2ACsYCFyCADygBCYAB7YIbNwEJgRzFgAAaATCAJMKBAAgCzDeDELIB/IsGKwEHhABBATSAKtEBA4EA1oAADIAQmgEogBA8gwBEAWuCBy2CABaAACIBa4EG3oETY4ELR4EUkAMGSRuBACABEoEK/oIumoAAF4EvfIEBmIcLWQEJggs4AwkhA4ABPgMSIAWAAS2BA7mDA6mBBueBB/2BAUqBLfGAAOiAAHmAA8iBAE2AAWKFA9+BFQeSAzOAAcSEAQ6BDLaFABuJA9uAA0aEACKACFSIB0OIBBCBABaEDIyBEacBEIMS6gESgxK4gQ0RgyGKgRGGgAFBgQl0gApLATyHD6YBLIABXQQQIBdGgAhXgAP9gCmOgRHFgBgbgSYSgAARgCsVhBCQgBVmATiDBb6CGECAEieBFXkCKHSBGhuAEkiBEi+AAG8COCCBFbqCHL4DLCIFggAugRGgATCBASaDADCBKi8CLAuDAfWAALuBA6QBBIEBXANrIAWADLCCIrsBNIMeogEsgBHggwRwgAANgAHoAWqBDNaAACeBAd+AC5yAAAIFCUsiCRuALAMDJiAJgQBqgQHsgQz5gB7ZAgRrgCwwgABPgQEDjABPggANATSBKkKBMCaAAVSBAKsCCUeAGXKAACmAAniAAJYBCYEdYYENaYEpLIASZIIRrQIIIIIRrYAddQFrgAAWgRrmAReDETaAEu2CLRIBFIAAF4EVwIABVgEgggA6gBK6ghF/gAPSgSQKgABDBBtqQYCAEeWDER+CEMkBRoEAE4AStoIUQYEOFIEwEoEIgIAAGYABKQcgDUF7IA0bginigAemgAGpARuAAAgDBCATgAAIgAGoBEYbIRmDKJoB0oMIsgJ8IYANdwEUgyAgBhkLlAkBDIAUNIYSsIABIYAI0oAAB4ATMIADNIADQgEOggePARCCMn8DAkFAgAGOhyf4ggt1gDP2AQKBM/aBKNeBM/WABMABDoEgaYAhowEEgAVkgAYeAQ2BBXKBFK6AAEoBC4AAyYEgTQELgA3RAiANgQvkAQmABBMEDSALa4MteIAJigFNgS1SghekAwkgDYAMgYEI1oMAK4EAJ4ABlAEQgQBBAQmAABUBD4ARZwJyQYEjkYAE/YAIz4AehYAhVoIADwMMIAyGIayABHkDCBADgSOKgxlCgg3/gxk3Aw1qIoAAVYAAcpMAUAEIgwBzhCaTgSkvhSuLgQMygQBSgyEIggBSgxk8gABSBQggC0kNgShFgAAJgQA9ggZnkgBgAQ2GJu6AAlOBADmCJvCAArmGKzWDItuBADkCIAiFADuCACwBB4EgP4cwp4EQHAENgiISAQ2EIhKCJYyBBtWBAYiAMrkBcYABNYEii4EAooALlIEBRIAABwFrgASngAAiAwwhCoINN4MYLYAAEQEIgABhAQqMGcmBIrKGKPWAAB+BBEOABdaEJAiAADUBGIEUHoAAEwEMgRDehQBFigAmgAAfgAAYAxQiB4AWqgEMghnNgAAPARCBM5UBAYAAEIEZzQENgAVJAQ2ABLMDByIKgRnNgAEiggAwgANvgSLVgAAQAQqCADGBBU6AA56EAYaAERiBBkWCGayAAFEBHIEA8IAYRoIZrIEBnIABZ4EZrIAAjIAAR4sZrAEIiBmsAwwgEIQZrIAUL4QZrIIACoAZrAEKghmsAQqBBUABGIQAtYAAKIIA2QEQgwENgBB0gwDcgQaPggAZARSGABkBEoMO0IQBygERhwIFARGLAcqDAe+SAooBEoQC2o4ANIACEAISEIIF/4AH+QIHC4IAmIAov4EG3oEESYAYNoElbgMaQXyAK3cBDoQj/IAQVQJxG4IpUYEATIEQ+AMHSxuCADoGCSAOIAf8gDp4gAPHARCAAxcCCyKBBAKHF+QBPIAABwEOgAXHgAQOgAAugAz+AiACgwAuggZNgQZbhChpgAAsgQZbgQRTgxm7gAgGAhEDgCEKgQAcggUogAc7gQXbgQUjgAyvgBpCgBmvBkEYdHILCIEE6gUFEBALT4EZUQF+gQAzAxAkBIAACoIeRIAmMoEGaoEAf40XhYAAHYEgHYIAF4IGdogXnIEZCYAfi4cE7AMgARGACXWCACcBOIAA6gEAgAAEAwELEIQAIoQX4wFAjBfPBQ8QEwvSgRk8hyVUmxkpgQkUoRkpAbSHGSkBJ4EOTYAtIYABDYAKcoAGDQNIIgSAE8IDQQ9LghsdA0GB/oAFSwFyiBk3ghkvghk5gDYphRkygABGjhkyhgAUjhkygBlunRk1gRt6ixk1gAC0ihk1AcS0GTUCQX6MAWYBcYABZosAEgEfgAASjBlHAQaAGUcEs0QBI4QZRwEQghlHAReFAUKDGUcBDIQBioQZQIECdYYIr4IHYgEDggdigg5eAcCDByCAAAeBHKyBGQcCIR2AABeBGWSAGSSjGWSDGUyAECCDGUyCCA0BHIUZPAMOIRKJGQKBFIyAGWSCIbelGTbDAAKAAeaAAbsDaw4fghl2GzM0NTYKCwwNDg8QEQMCFBUBJAAmFxgEPj9AQYQZeQMLDCSGAAqBLf+AGXuDDkyCGYWCGjqDGYUBCoEH/oAOMYEAEgEMgAwhATKDAAqCFn6GAWICDDOBEHEBBoMFEYAKDAE3ihY8AQaLFjwBBoEMaoEQu4Eq1YAhBoAEswSflgJHgTj7gQBbASiDAFmAEFcBKIEGBYAEyoAdDYAAAgIQKIEDBwEcgA84gAAuAjsBgTEbARCAAEoEQQIQKIIgsAG1iBdagAQZgABiATOCAKsBJIE204ACXIAQYYADBIAFRQN0QYCAA26CLg4FakEfcEWCAyGCCMkDAEG5iwxwgABCAQeBFqkBCIMX2wGHgA7YjQAeAgR2gDJEgA2OghcSgRjLAgdNggDGAiIJgAcPAQmADGWDA9GAAn8EA09xDYAWoYAFroI6zQGuiw3pgRRtATKLAUYBNqQBRoIL3oAGmIISH5MAq4ABtgQHQYDAgT2ygAAdAdiLEwODAdMBJIQYaYEBGIIEMoE2pIEANoAqzYEEZIE1AYMAC4ABdwM6AAiAB0aBACsCOgCEPBSBAZqDAY+CHTUDAkG2hRNPgQjIAQaDANuDGXkDRQ01pQDbiACYgQ5WgQy/Ay0AFYIlBYsAlIIIjooAigEEhgCKAbeQAIqFAWWADBSuAIqAAPeDIs2CAXOBICeZAJiBAqyTASIBuIsAmIEAJAEUgAS/AoAIgQGnAQeCESGFAKmBAASLAKiABLyAKDyKAKiDGqyCAksBNoIaooI+yoATnoEAvIENLYAP54EI+YIDV4AAaIEAo4AFvIUArgEogACugBv8kQCuAgwohQECgQAngg2wARCAABSKAdQBMqcCr4AIEoECWoADh4ADj4A84IECc4QDlQQYdnJygwPpggh2ATCAAScBvo8BJ4EQXYMItYEInoAC7I8O+YARH4UO+QRBAiEXgAEShgRKASmMAGGDFIUDCyAdgB8lAg0vhB5egRorjBoQgBh4hBoQAQ+KGhCFAOyGGhCHAOmkHl6BHlaABjsCpDyAAE+BDHeBHW+CD/b/HmubHmsFqDxBsDyCJrYBzYAABIEACoACN4kebIAAGIAAEoIeIwEqoR5tAayAAFEBzYIH34IpNQEQiR5uigBMgAEtgh5vgQHXAaiBATCPHm6AAEKHHm6DF9SAEgSBGWgBBo0eKgEynx5jkwA5ASqBABmEHmOAGaW3HmOAAE4DBgwwqR5ZAQaBAH2THlOAKniCGMICDC2eHk8BDoAACgEOgh5PAg0sgA0ukh5CAQyAD7OBACkBa4AQSYseQoEEGIUeQgEngwQQgg/XgAQQASuoBBCSHjCBOZ2PHjKAAZsBYIAAP4AeMoEBjIIeMgQFQR5JgSYRAU2FB8aLHjkBJ4oeOYAI3IgeOYAVp4MeOYAZcIIeOYMYNgELgx45ghyqhB45gRryjR45gEVqgR45mAQpgBtWoQQpAQqBAGmABLmBAGmAAAyPHjmLAn0BCIAAxqYeOQIhDYoePQMqIhSCASWMHj0BJpEePYMKGoceOYEB4YARuIE9Q4gbAgETgxsCARiGFn0BBoIBBYEXXwETgxfcARmBF1yAHUOEF9yAAL2kHjkBGYEeOQEEhR45AQ2IASaAAAyFHIEDBSAKggEcAiAKgwEcAQ2LHjmAOXmFHjmAHcuAAn2CAeIBCIQXFQElphfnhwBlAwUgDZ4eOYAU7oACBoEAM4weOQEEggC7ih45gCAWjQCXASSoAJeEAhuAAJqAESSDAiCHHjmACpGNAFwBI6kAXIAeOYYAXIIeOYASUYQeOYADTgELgADygRWsAQ2bHjmCCCqBBQ2FAbiCBkuBAc+AEf2DBCaEAsiAEuqmHjkBJaAeOYUC7oweOYIAO6AeOQEeiABDjB45ggBDhh4zgQ9whB4zAwUMK4keMwQEQQZJgBGkA4ICSYIM4qYItYAFjAIOaoAFFAFrgBpEgQV9AhJrgSgZgRaegQ7HghaWAxwiDYEXJIADkoEWzgQgaiEhgAOXgAAMgxtzASKDAA2DA6QBI4EACwFUgAOkgAAHA1AhGYEABwFAgQLIgQ7VAQOBAAeBFiSAAAcDMCEkgga/AQ6BA3KFBrSAMLGAAAuBPs4CCGqAGK6CReMBcoIKfoEDTwILIIArtwIgI4ID6oE9IoRBSQEGgQP0gAzsgRmBAgR2gQQWgRuhggHKgBtmAy0AAoEZVYEjMYAcYIADBIADpoEK9gEGgRsuAQmCSTeADVWCAC6CBO2CA9OBECSCAJiBIY+BAt2CBk0BCogAqIIAnAIIaoAAT4IAeYABAgEEghqzgTyggBoRgACJAQuCA4uCAN8BCoYC/4EAC4YA34EdAIAA2IEh8oEA5gELggTJASKEAN+HANsBCIMb9gEIgQMUggDbgBbFgUsRAX+AAJaBALuERTiBDhSCA4iJA2yBBe+CEPGBPyiAGvMBGoMAgQEDhAAfgS8Dgg5MAQKAA2aBDumCAM6AIbSCAUeAASKCG42DANoBaoAFWAMMIB+AGP2DG0yAGkuBRIwBJIEbSYAB0AHEgRtJgBtHgAZqgR0mgRd4gQFUAw4gIIFFCoAD2wEEgBQsgBj6gS1iggGXghrsgwGXgiU4ggZ1gUKwgUSDghmYAQuBBcYDDiAhhQBBgRcRAQSDPf6kAEiAGriAGsSBAKmAFQgCIgeAF6uiADaAFnSBBI2AADQDayEJgRawAQ6BBHyJAMaBOwueAEiIAEmAAVgBCYEEmwQJQQNJhgKZgwA8ggHlATqAAZWFAq2AFTiBBWkBCYAAV4ACaIEAV4AAB4MHwIAVjIAg/4YAPAIJQYBCDIAXBoMC3IAMsYIAcIEjvQEMgByGgACrhAAogAAMhABkggAKggBkggBWgC6TgwYqgQByASKAAE+ASveCAGaAAnuBACqAAD6ABb0CQQKBChiAEFCEAGaAAOMFLQAEOgCBRomADh0BDIExmwEIgx5YgB5WgQECgh4YAwgMH4Ee+4ECR4EC04ICS4ARFIACS4MC4oAA0oII1YIhiIEBFQEZhwAshwNRhgAsAQuBCf6CIdADDRwagCGzgAAVgCiKiAE/gQNMgCBngBtJAU+AJLOAIq6BREyCLAGBCGYByJEjTIAD0ooISoEeZ4QjTAENgQN7gAabqwhKAiANhSNMgABAAgAigAZ5iCNMAQuCHZqCAt0BCoQjTAETgACVgAA1gyAtgRi+AQWAHAeAGtMDcSALiCNMgAo8hSAtpQCIgApagwPLAQuGI0wBDY8jTIEAWYEBG4wI2gENgiNMghT2hiNMgCf0AQiRI0wCyDeDABuUI0yCKCuGI0yCBLGAACGII0yATlGBCtGJAYaAALyEAO6CCsGlIEmAAMeEAM6II0wBC4UEvIMjTIABFYEA5oIBFYUH/IACNAEOgQ9pgi4RiyM7gAsbgQyKhANhgAGqghSSgR55ggd/AQqLEJgBJKQMiIAfQQIgDoI9TYwd1gEDgh3WgUXLgBl2gQeKAUaCB8qAEgGBIQKBESuCIoGBEb6BAk+AAb8BA4MUlIIAloAAN4AEroACXYMAGQEpgRaKgxSlhBCBggPagBF1gRFzgBoEnBEcggBnAhtGgAAxAwBB54oJEIAFVgMSDB+BD5eBJs2AABKAAMGAEA6AKq6DACaTEPwCvf6CHpKCFB8CAHGBSEeBDkOALOKFIL+ABHKCIKQBBoEBaYMAFIAAZo8AHpEAMoApPo4AFIIS+gHOhSRzhA8zgw9EAQaCK+SBJHMBCoM30oMOy4AA2IEANAHPgwK7gQyUhyRqgAECAcyLJGqCAZIBVIADV4sCvoAcdQIgCogkaocERKQqx4MDp4EdU4wkagLIN4MniYAcx4gEPYokaoEEPYAZ+IQEPYEH7IEeo4UEPaUAgYsEPYUDW4ABIYEIXIAFPAEKggChgB1qggN7gSgMhARFiQNfniRqggFgiyRqggQbgQ6lgRCXkiRvgAFkAiALhCRvhQQmqidyjAQmgyRvhAQmgyRviQDFgQ1lgACEiSRvAQ6BNXmAKbuAAMCHJGWCA9GBAeiCJGUBBYwkZYIJHI8kZQEShiRlgApCjSRlgQBEiCRlgAAiiiRlgSJpgCEwgyZ5hyRlgBymgSRlgQAehRFviSRlgBAliwizjiRlAQ6BJGUBDoIATYAFE4YkZYcn6ocDYIcoSocAFIYoJIgAFIAAPIUB84IE/YE4sYEBA4EIKgENgQAOgTvthQymgRKsAgN2gCGpgx33gAWWAWuBEa8BIoQMzAETgCOjgAh0gROzgA4MgAAsgEzkgBO4gQN2gQgzAQWCAciBDNSLG0yAAAcBBIEEfQFHgQT/hAa2gEMDgRMNgyTiAQaBVOKDFfQCQbmHEsUBFIAJFIMXJYIBXoA/q4ItF4ASxIIB6oIWqYAf3IAfsoEbpAENhAAKARiAAZ6AAAcBFIEBxAEFgQIDgAz/gAzZgAGWgCSHgRrrgB1sAwtLG4ES/oAAJoAKGYFE1JAY/4QXHoETKYQXyYUTLYEA9AFEhBMahBMogABdgFFygAC/AbqIEVsBRIYYMIEAxYEGtIEGqIQPpQFqgQPNAQOFAMeBH+eBRRoBHIFV44ICtgFEgAh4gAARASCBJK6DEjmBAHWBCDMCIAOCFQ+AF56CAkGBARgCSRuAAj6WGJ2GAMoBBYQAyoEAf4IT3IAOYoAAwoAhH4Ip2YQX+YEeS4Id3YAAxgG7kgDPgQ0BhQDPghUHlQDPASSNAM8BKOQAz4M2Z4kAz4EdCAJBvIkCXQEFgQH1ggTNhxongS8xoAhFgwCchQCRgALiAy8BHIFPNAMAQZqLCYGCF/OHGNCEGlsBQYA6dIAnNoAA8AEJgxuEgBJGjBz/jBi1gQRqgBRnggRoARSAAAiKCPqBQsShCPqBCKSBI66CA5IBIIFTEwMAQdCKBRWCAKWABemEF/iCALmDB6OAABsBFIEWxIEAqYMsSYEsWoFATaUQ6YQTp4EFYYE1BIAJX4FTlIMk4oEonoconQEIgQr2gAAQiSidggsPliidgABuATiBQ6WFKJ2DKMuNKJ2AAJsBLIEBu4IGL4AG0YEH2QEIgAWWhShQkCifgihCBDQiBmqAACcBCYAAJ4NYDYAAPIBVZIEh2wEIgAA4gRLxgiifgAAjgAUhgBAygCa0gSifgACWkyifgBAPgVXQgij8iyifgg9diyifgATcgyfYAQSBAYWEKK6ASmiFKKmCAM6VKKSFAqaHCs+BIV2AAKaDCrgBHIFZ6oMHB4EK1IEROwMIECiDJMqBAAsCKQuBLH+BAo6AAAeCKSyBBdq5KPMBBYAo8wEFgyjzAQWCAJUBG4FFgwIgHIYo8wEXgwJkgyjzAQuAKPSADMQBEIMo9AEXgyReAQeLJF4BJ8EkXgEKg0EyCA8QQAvyBgEFgQBcgQTNjiQogUBVhSQoAUGBQ/aAXRaAALUBBYEWiIEDwwFIgQUZgEOigylzARCBNXuBVy+BJqWAHJ6BBUkCEGuAQPaAXb2CThcCCEaBXG+BKX4CCEmBBA4CS3KAJB2AAPSFAukDQcgtgCV6gALhh0rxARyBI/KCAAeCPvOAAA4BKoIa9oQ+fwRC//+BghsZAVSAAAwHgICCgPABN4AJ1gIBQYEfvwIHG4FSHAEwgUB9gU7mgAAMASyCWrQBAYAIpQE0gwEYgSSUggE4gQNYgQNWhAAWgAFaASyJABmEAWOAABcBTIcAF4Fa44EAnQLELYNGpQFEgAAPAoCAgAC1AZyBABGCANOAAA8BQYIjVYIDuIJdC4JUaQKcLYAaGgECgAzDgCo0gABdgQHJgkbsgAJvhAAIAUSCBfyCRyoCQZqAB4KBQycBgIIVrAMAECGAJyOCQTKAAH0BiIAAUIEfAAGEgQGdgCDCASSDJHmAAn4BmIEAhoBOFQFsgBFvBDYCpC2BAeWAAD0BNYIB5IIBDYslW4MCU4MNY4IApYAAboBGsYEIY4AELIAB64EAcYI/D4IoKQUBQTlBKoEi7ANGIgKCVaiCVSGBAhGDBdmCJ9WDDZ2ABiWAAYaBAGYCvC2BQq6BAEkDOwG4gACgB0GIETYCuBaCAloB/IED0QGwgAAMAkH0gCi7AayDABUCiBOAABUBpIEAFQHggAAVAaCDABUBlIEHTwGYgQAVAX6BIoYDARArgwC9ggKsASyAFuqCJ/2BAawCAXSAGJCDWHsBRIBA4IMa4oE/doImi4NAi4EA8gK0LYABBoEmMQQgNwJ0gwERAWiHABIBXIMAJQFIgwSPBYQBQQxsgAEpA5QgaoAY6gM2ApCBKCgDAUGQhAAPAYyDAA8BkoQADwGAgwAPAZaEAA8BfIAFFoUDfwFxgAN/hAALAR+AAAuMJjYBCIAmNgL2JIAs9YElZYFS9AIQNYEl7IAu1wIAGoICNYEE24QDoAEcg1GVgFlegwQNg05bgQRigwSsAQSAAkMBR4AvEIEA7gGHgQcDhS1EgSByggSCgAKtggvNgAK+gAKEhwa9ghglAhA3ggAsgwqagAWYgwS0gAraASiDRKCBAGmAYJ+BAW4Bd4Mn4wJLG4ETV4QAEAcDQQRKG2pKgAC5gBO9mCXtAwRBKoJUhIEArYNIDYAH7gELgjUigAKFgxIhAfGCCB+DM8QDMEEMgCT2AfCBHImBB7ODALEBiIAAhwFKgwmFAoQBgQNlAUiABGMBwIELfQEDgBizgAAMgAOSAcCBAxgBBoAEyYMfCIBS9YAAKQIgcoMM7wFsgSjCAh9wgERgBUEfcxA9ggATghuoBAAvATKBABCBAAkDMBA9ggI6gwLggwi7ggCbggEtgQE4hAfuglwYAkE5g1W5hAMaggAvgwmVgR0zgQNwggB6gBkEAR+CEhKTABwBi4EgGJUAHYAD+oZQp4MmxZMAKIINkOwAHIMGC4QBkAEJgAHjAUGASoqDB0eCAa6BOfMCAkiEAY6RAEYBIIAWAJYAYoELUI4BfoEJ+IQCooAC6YAIbAEkgQ55gQMpgA/AgSKGgA9ugAQrgQ4qgQhxgQL6hA2CggBdggCygAZDggB9gAoXAkdBgQQwAwgbcoIAuAEDgAAIgmGWgAAIARCBC8gCG3KCAISAAF+CCk+FAE2DH+mADZqEAEmDAKqeACaCJn+DACkDLwEGoABPAi0AgRcEnAAmvQF9ggC3gklEnACOgloYgVgqgQ5voQEMmQAmiAEMgAk4AQuAAbOCHG2ABBuAA0OBChqBADeCA1KCIQ6HDb4BIIJe9YMDgYIEWwHFgCpHBgUCCQkJA4IYBgHbgDQPgAVoAkHngQ+ngl3FggIugiv8gwNFgwTxAwMvAYAKZIAHwIERqIEAbYEEaIFHuIIqLoELIgFqgBmhgwCMgDIogwDSgjU4ASCAAL+BGg2GInmAFTaCCrGCACMCLEWBBHgBT4QdPYcA0IAARIAA6QFrhQDTggBJhBWrhgLcgRkggQ+OgE/XhR5OgwLrg0R2kACJAQaFAIQBFIFT/4FJ04cAh4AApQFNkQCHgQC9hgFagQFSghddhg03gAA9ARyDBhEBFIIkHIEAE4QBI4AL14EA74JKSoQA6gEHjwBjgByggAAYhQBjhgU3ggH7gABKhA2QgSSigQAQhAIjASCEAiOAARSAENmCD4WBBcKEAjeGALuBAjSBEmKEBRKBAIWDBhOAAt6AAIyCCl2KAIqAABaPAO0B24IA7YYARIIvLeMA8AEktADwsQDuAeeJAdOBA1+BAMyEANiAGuaCIQKFAK2BF0aDTy4BMJcAiYYAHpoD04kHDoEAh40FwIEs/YIC1YI6JIIACoITMYIACoFTU4MACoMAjoIvLIAAOAF0gQs8gU1vgQP6gAhHgTfzhAhfgg32gQUFgwcdAwEQNoIz5YUI6IAFDAEChSNQAQKBCmGBF1+FAB2BAFcDAhA6iABiggN7gwIrgAo7gg/JgQm6gAAhAVyBCy0BToFoKIEPJAIDaoFAiIEADAFsgWH/AwEQL4MAJgFsgiGlgAaJAxA3QYAFgIIAC4ADrwEbgwDagABWAWCDAECBACuGAfeAAA0CoC2BTHmAAVECoC2BTB4BKIAL5YkHgLAAH4MBtIEVloEXxYAPsoAKp4AAJIELKIIANIAQeIAMPgF0hAC3gRKygkLkggBOgQAGAqQtgAD7gxmelgD/gRQ8gAHrjwD8hQD4gmUIggEnAqAtghH3ngFKmQBOgAI9gwFIgQHHgicRgyU2ggDPgEnKAoMCghjkhgFnAWyDKSGBAeICAUWHACUCSXGAEyCAPG6LACqBJQCBEb2BAJWAGlKDEi6JAgqCMaTAAgqBAviDARCELou4ARABB4QU8YAAsoATQoIUzoIA84AEkYAZuYAB4oIh6oIZcoISkoIhuYYACoBZIYE21AGCgR7zgAkagBAqiQACgAUMgB+BgBTJgSHsAQiDVfOAAAyBWVaDAAqBUv6DAAqAAyaBNgSAAAqAC+GBZ3yAAAqAJF+AYVmBAAqAVcSAE8eBHE+BIkGAF3iBGWKBF0UFA0H6AUmAGvuBInYBDYIU7oJDmIAZcYEEE4AmiYEACoAB8YAXzYEACoFRq4EgPwEJglGRgSA1giFXgDOIgQAKgRRagSY9gQERgAnjgBfygADYgAL4hD1JgQcdggHrgAMsgRnrAQOAOH6AMz2CIW+CAziCAzaAB0aCK6aGA1eDBOaAAB+CBOeOA3aOAB+BAFqACBuCBbiBHwAELQCQIYADgYAWIAJBhIEjPooDh4AytYIyDIMChoEVfgKIE4IAHAGIgCikggKwgirTgQOkgwzCgwOkhA3YAqAtgRj8gQHqhQRIjwDMmwCtngDMgQAfgjL3qARChACchQRDgSZjuwRDgCF/gQDxghD0BQxsQZgggGyWAQCAN8cBC4AE9AF+gB0jgzU8ghFLgQoBAX2AOmaBOHaCADwBBoE1IIYKAIAFJIAE1IUGHYALJYAKOoByxQIBAoJdSoABfwK4LYMDqQG8gBHGBHRyIgaCEMyBFFkDA0EOgTaelAtJAQaXDMaBFLoCuS2DDMqAEzWFAF0Ca3aEAF0DA0ENghNlgAI3AWqAANEBNoAAHoIAcQMEQQq/AHGDEYyCAHMCQQmCAGeAR04BaoARtYEAZQIQLoMT3YMHroATQYFWzoIClYURXoQcJYFRDYIsQIEmIIENJoIRXoECAIU3zIAFIIIACIABu4MsrIYQWoIAIoIH0IMQt4ECEIIFY4ISewRMDQMagwhWgQHcgWs2lQDVggOUhAAqlQAjhQiAgA/OmAAmggAjAy0AM50AI4AAC7sAI4cAjwEKnwCPg1TllgAjggaOg14JgC9gixCsgwMqARiBa2cBSoQTAAEAgAOXhGBjAkULgji9AfqBKukCQXuAAYQBAYk/bAIQIY06fQK/AYFTloMWkgE1ixaSgQ7bgmfzmBaZgRTgnAAgAUCcACCwFvkBfYISjAHxgBecAQuBVLcFARACCwmCE3ICbBCBdF6AACcBbYEXiQcQQQu9CQEVgTmuAUCACECCBuICBkGBPW2DDfqAZOyDQCCADVmCat4BdIET24EAB4AGMoAmVYUE/YAAGoAamYINoIJbooAbd4AllAN/IQ6BJfyBRLiCAEKBLxiBAECBAFOBB4qETXaAIP+BAASBUiyAF1OBTfgBCYIAgwJBEIMGzoIAPIAQroIAPIFAZYMHEIEm5IFLxIEN9Icv04MoLIQAWAEJgQAEA0sbIYA9uYAMcgEBgin9gD/6gRN6gQDMgT7RggC5ggBBgR5JgABNgQBlAWuACRUCAE6EbDmAAAuAAiCBALECR3KAHL6CNXuAAnwBO4AnUoMAUoAA7YAAroMBL4EAW4cBKQEigQlTgQBChwExgVz/ggEzgWUFgjAggAANgTIxhQFBAkETgUSkBCIVIRaEBZUDAA4CgAusgUGjDCESQe4IIRZBrgghFYEWcwF/gAARAvANgAARBLANIRWBG7UBDoAh7oBDXYFkPwIBRoFkxAECgG7tAyACG4BtrYAEZAMPdCKAB0wDayEXgxIXgC1jgkSwgASOgScigWL9A3QhGIAKQwF/gRHogEKOhADEgEjigBRYARqANlsCEkyERhEB4IJAxAEVgUkCgApAgQAmgEVAAwYgFoEHd4Aq8IAgMYEIbgMiDnSALKiALZOASkmCI1gCGiCAYmCAASgBGoAcqAEZgD7jggdFAwYgEIABS4AAPgEOgylIgRPeASCBKeaAAJGAAeoCa3SDAWSAHEsCAXaCBzeAbnGAATGHAhWGAoqAAbaENQOAcK+AQZqBVrIBCIF1AYAAywFqgC3gAQaCIv6BAn0BCYJBRoEBsoIgbwEMgwongkkmAwIgF4BBjYEd8oMBJYEAGAUgDyIKIYA7QYcAy4EEW4EAtoAc7oEAtoEVdoET/QEBggLXhQCygWXtgl2NgEHmghd9gwCYAQCCcUiAAJiCAqWDY9UCIBOBAFaDXwaAKEOBAmUBDoEJ8YAY74YBiYQAB4MJzgEXgGfXgACngUC8gHDBgSpcgANFgAAEAUuCKaEEIAwbIoBLxAEIgACyARiCAXoBEYEBTYEBkwQGdCEQhDM3gUvwASKBMgqAAdqCAU6CL9mCAv6AMnABSoFxhYAg/oICVoECT4ICIAMgE2qAAkQD0wZLgwJdgAC3BNEES3GBcUKCZJuBQzqDAdQBD4gBzQEGgTA1gFa/AXaBATIBB4Ax3YAD1IEAbIECNIMDroEDywEAgwMRgjCPglHvgwMfhwOVgQALgQAIgQM+hSrjAw4LK4ABX4IBy4AE3oQjg4EElYFnW4EAB4MbBIJaUQELgwT4A2BB1IIE+ALKA4J1T4RAV4FZywHVgRhOgRdCAdWABn+BdcOAAAmDCvuACgiBIRiDACKDT8WAEHeBKnGAAziBCmmANDWGN7mBDCWAG/+BAmiAADiACNYHQaCG4u1+c4ABCIEASIF1zoM0PoMFL4ELC4AJqQLATYk3RIAAaoEgSoNzEAFzgCRjgRyDgDH+AX+DArSCAOsDIANzgisDgXZRgAA+gRBtgAAqiQD3hQJjgABDgBi5lAAzgAKnAgh2gQAegALHiQAehwAZgALnkwAZgBtjkwAZgBDdkwAZgAc7kwAZgAMnkwAZgD+wigAZggDigCD4gh1khADiAwvCBYAHo4ABK4ED4IEb+YAIEoAdm4BvloEBB4ELDYAANYAA/4EDtwTx/wNrgRIkBEHw/wOAJHCCcpOACEKBenoDgIA8gAosgABfggAbAyAAcoEceIJ5BoEiRIQBeoMBWIYAUYFqsoNieIAAk4QB0YAAYwFwgABSgQeAgQBtgWccggBSgABQgAIvAtsCgSZUA0GwK4IusIAApIIOVYECcoMAToMADYE2toQAC4ENs4QACwEDhwALgAC3hQALgA4/hQALgRTyhAALgA7uhQALgQ1mhAALgEakhQALgA7IhQALgETLhQALgAQUhQALgEaThQALAQ6HAAsBD4EAC4FBPoEw44IDG4AlNoN4BYEA+YIafYIACYEBqQKwK4MBqgKwK4UCjYBl5YICzYAfQYUCzaQBU4YAWoEnrIQBz4EBMIID+YF07YQAC4FqFIQAC4ABMIUAC4F1yYQAC4FskoQAC4FqTYQAC4FwmoQAC4ABMIUAC4ABMIUAC4FDQYQAC4ABMIUAC4ABMIUAC4ABMIUAC4ABMIUAC4UBMIJmqoEBDAEQhAELgADHgjM1AnRygAFEAQuBSfWHCYiAEcTJCYqDWBiFAD+FCYeAELWICYaEal6BdDKCKCMEQcACNoEM45IAF4ADXAEMgRB9kAm7ggdbgDCmxAm7gClQgwm7ggDEgAm9gSRcoQm9gAhBgF++gRLVgWWZhAnAAw0CGoM/PJAJwYUBaMAJwwEUgAbbBQUiFCEVjAnDAoECgAk9CaAPIRVB4A4hFIIgNoEAEQEQgQARAQ+AOayAB2QBDJQJwQIEGoEAHQJ0IoBOxQFrgDYFhAnCAQyPCcIBFoQJwoAAgoAHn4QAxYAvcAFqgDKDARqAI5iCIrqBWFaDCcUBFIEAE4ATpIUJyAEOgAF4ARWJCcgED2siF4UJyAEPhQnIARaRCcgBDoMJyAEX1gnIgRIKgDc4iwnIgXq3iADrigkmARiGCSYBDI0JJoEwlwQPGyIPgwkmARaICSaAAPGACSaADLqECSaAA8GCCSaANKyYCSaICSQCEmqAAaYB1IYJJAMSQdCCCSQCBxqNCSUBDKEJJYABkYgJJYADN6oJJoEFcYE5tYIz/ocKtoIBpIQKtoYKhAEShAqEgRKCgCfzgAAtAwsLq4ASC4EHWoEWX4E15AMBQZ6CEl4BAIEiroN9h4IAFgEegwAVgCLYiAAVAROCBLOBB1KAAFmEIpCHBdaAATEDOwGUgHAigQ6yAbCBIpWAIooBqIAACIEAEAKgLYEXGpIAOZYAGQMLrwKCAK2BEAmBEkiBDxSAEloBBIASt4BApIAAEoEjtgEEgxK3gg9AgRn2gxBagiS4gBBaAQWCCkCTAByABvyDEkaCZsKEAF2AEreKErWBNfeDEk4CABCAAASDAEqHEMCDAEqCOTmVAByFESWVAB+AAvwBc4MVTpQAqIYeSYMQNIQoQIEP/AEQgD4jgwA1gHE5gURHAaeAE+qCSzWCAMyAJkqIARuBAViEcYWFAP8BuIQA/5UAIIIBH4MS14ASyZkAKoIASoIiVoMBmYEAgIJsZ4AB+4EBPIIUioE9A4EAOgTALQumhQCpgQHghACtgk4TvACthQCCglE2gQpZAUiCcVOeAFSBAD+HALqAComCAfQDCwuBgWv6gAZWgEQLhQX7giVFghKIgQw9ASKALsCAJ26BGCeDA1UHCUH/gP+ff4IMVQEFgH2vgiQVgQxugUXrgQLmgQc5ghXGgAU3gSUsgRuvggZlgniFgALqAQGBdC8DLwG8hAAIAciAAAgCQSCDDKWBDJKAABaBDGSBFxiCDGCBB1iCEYWFFkaBGDaELM+AGFmAOzWCLLWBARsFmBZqEDCCAAoBpIYACoAAtIEAyQScFhAxggAQgAQHgQAQAaiFABABsIMAKgJB/oAECgMGQRKDHFuBGK+BBneACvuBAWiADQkDLQDwgEWsgwDegwpFhDJMggF9gAQGgAAygBfcAwZBEYABhIEEFQYoAqwtQQqAIwOAXQCABPqAKoyAAAqBey+BABuAHNIBBIAPs4FFhIAFj4IeyIEa3oFSzgIES4QenoImbgIQLIEAgIIEIIMT54ACd4AZp4QAIYAVcYAW4oA5IAJyIoBKoJIEMY0CFYkDy5cCZYEJyoUCuIQEMQEBjwQxAkGggEVwAxoQMoICi4EmSoQAjYJ6+4YAh4QAmrkAj4QDQQENgS5ZgQCagACUggqThDq1hFA2gQCTgQHpgTGrAf6BOyqDAeiAAWODARcBDIQAkIEykocBMrgAmIMH2IkBKoIqdgELgytzgwBngAASAQSAArGAPHSDAKGAAIoBB4cAioAKE8IAioBBIpkAioIAZ4J6nYEAioMBKwQFQf3/gwElggEdAQ3NAR2RAR8BIoAKeYICSwEMggCZhwBvgwAYgCT9iACfgj9ohQOYhH77gAk/gwMdgAtFigOUgAqChwBInwMGAQejAMKBGe6PAL2IAwiJAK2GBA+BBHOAAJADCRAzhQRxgCrlAQiCAA6BINyATPwBAIArFYEZi4AHcwYLC6ELARKBDUgEIGsiD4AuWoJ5YYBloIIXpoINEYEYBYEl3YMq8wLQx4AIdgHQgksSgQAEAUqCh20DQdgogw7jAtwWgVnUAX+CIq+CbMOCbmWFgjsC0CiBcdWBKYKCEGmCf5+AAEuBNQuDPZiBMvSAAFiACfABSIFY8oJ934FGvoAfdoCGHYAI/4EAwwEEhBx1hAT6ghxCgQUBgX2UARuBDN+Cci6DBQKCE7WAOCWAACMCrC2CCQ2CCqWDCd4BCYABuYUBpAHQgC5jgAuahACQggpxhH5ehgBwgG+dgjAPggoUgQYIgQnjggF1gnbjgR/pgAZzggD2gAfPgwbAAtAoggARggDvgACEgABdgAAVAuAWghTmhAD3gknIAuAWgAARgA1yAhA0gwCPAdSAAI+CNV0B1IUAMoIfMYIAl4FzSo8AJoUAHoQBNIIdcYYA6gEFgQrpgAuchgD3gg2PghE+gSamgR/igQxiAQSCAAqAGkWBHu6AAN+EIf6BCwOAMQWDCwqAHwSIAK2ER9eJAdyEBpODAJyAAI6CAJyDAeGCAMqDDxYBvIACKYAwNYEaE4B22IECaAEJhgJ0ARCDgBUBCINfQwEEg1KRgkfVgjg8gApNggOGgjluhkiahhQigjWOgVs4gwCFgwFihQr/gDT4ggn3AdSAAK6AAJUGvARMGyESggKfggHPgR8CgDONgDWxgTLvhAA8g3bngANGgVYngFZZhEAbgUeogQA1gQcpAUyALucBIoIXl4GH94EUsYEFeAIgDIIM74IX9ose/YMVBAIgC4EEI4BMF4FaOIMAbINwYYMH0oAAaYAAfIABpgMQamyDB9WAN9iHAtqAIPCAFl6AAIaAAcSBACCDAuCBCDyBJeKBSw+AAHaCSMABAYIChIF4DoE1HYEAtYFAV4IO54EI1YAASIE+X4IQUoNMo4EBHIEArAECggIngmOYgQ5ngg/DA0ECSoAA3IAAB4I564AAP4EAYYEAmIQAcoEOTIIDBIIUAoM76YIw0IMBS4EBFIIOWIEBVYAf7oEBRoAVbIJL8IQA+IAAFIEIXQIFa4QA9oASC4UDcYUTFYEK7oAMxIIW0wMAQbqAAkyBAVOBEJ+FAiGCEMaBPlwCAEiBAsqCBJGCDWWDELCBaoGGAICBBQsBD4MCTYEwJ4IFz4YBqIKGJIEAfAJxcoEPi4F+XoAAKgFLgj5ygQPvhTvzAQaDhO2BR+eCAKCFDbYBD4AOaAEkgBXIgwBhgIrAgRyTgHLqgQOFgQARgAbqiQK+gYlbgAO2gANbhwDvBQu2AgEJgBd7gTztg41agQLOgAbdAjsBgEMMAUGAAkqABPcEQQdBioAzCAEbgQhvgg5XAQmABYeAVASBHhSFAQWBQfaBAZyAHYeBIVODEzSBA2aBEBeDjw2DBZeFAuCAMCSBNzeBDzcBS4EQfoAG2YA8koEn94AEEIMEWgEgggRcAQaDBFGCIIeCFj+CdQiLACWDAVOCAuCAC34BFYIADwK8FYNG6YETagEJgnkvgQAdAcCDAB0BwIEbtYMAEgHEgwASAcSAG7aAEWmAI68BQYAtpYCECgMiAxuFAPeAJSKAAy0BG4QBD4IBOALZCIABOIMGe4AlLIEAXoIKyYQO6YRQboEADYAi6oEV6YAVDIJ+SIEHwQIDL4AFCwEHghZzgwVaASKAA7+BFouCAJCBDsKCEtqEB6CBB/2AAY+ADRmAEkeANx2BMxKVDm+YDq6SCwIBBIAH/IIAXIEsFgFqgBUPgQyGgQALgwr4gAiHApAhgCWpgASkgTdNAy8BhoFNloUApoAAEAKECIA8B4MASwEGgACngExBgwikgABhgBduAQaIAKuDI/2AG/mEAI+CLd6UAMeIAKsBC4YAqwEGgACrgwBggYB4gQCrgjfqAQaACKqABjgCvC2BB30FQRxrQWyCPzGDDN2CfA8CkB6CViOCAJWAAA8DoBsigTyigwCbgQ2CgSNLgwEEuQFWjAoSgBCMgjy2gwFVgibzggBqhAAVAQuBB1qCD12CANOBAyeCR1KAXtmATBiADiuBCLIEgQJJG4ABgQEjgwGBgRhEgQImgQffgABFgQIigADhhwC8ggDgAQaAYdyIAXWHKwWqAiCHAXUBBYYCIIGEHoQAy4EAC4UKHwMKQQSBXyiACNeAAWkBH4EzEoBVpIABZQEcgAGwhQKrgADxggrCvwFlgQYkigFnkgCgjQBygQiHhACwgQljgBiJgBLpgQO3gUc8gALnAy8BgoGKO4EAN4AADAGAgXbKiACvg2HAiwN4tAFYgBEohwt0gwtygYycgwC2gQkjgxC6BbMLAQp/gwV0gQWYAiIHgDEmggWMgAAJgRCrgQWCgCHRiQV+gSCAgAxGgQWEgxc7g0nagQV6gxfpgUj4gwV4gAGrAUaBK4aCBY2DBXqBC0yCQZyBb0yBFX2AAGaCBM6CAZ2ABM6BFi6GBKOEAn2ASJWMA/KAA1elA/KNAByIASWAYOWOA/KOAn2ACqiBJiWFHk+BV9+HEE2GBYSBDpGCIFWAC8CCJ4eDRFuEAOaBCroBAoQB+IEGRIE/E4UB94Aeg44B9bICsoIkJIEEEIEAwIISNIEFGoBMeoUB84gP44KAZYEGv4MAioEq8YEBDAQvAb4VgHothgNOvgNGiwCUgnwkjACUgAYFgAAnggFkAQaDD0yBHScBD4RfAoEpgo0PSI0B0YkPSIECa4Ivrp4Dz4B7E4MoFIFUkYAFE4EGjoYAcYQAGoArdoEAGoJOwgEGgwfZggE3AcCOATcBwvoBNwH+hQE3hA+t4gE3gA/AkAEzg1K8ggEmAcSOASYBxvoBJgH2hQEmgipQ5AEmgyptjQEmgCp7gRkwgUaAhACgAQuCCgyALh2BPGuBBY+AGvqABYiACgyAAA+ALlyBBY8BCIQKEAL/AYCcDYMQroEJuoEQroGVtIUMnYBRMoAMGIFOZ4MNOYMOFoCaxoEAnYAO4AEEgAy7gkdXAQSAHS6CG0WAAWKABV+FAECCBLKBBKWChb2HDkCALxmDABgBDYNBZwENgSqmgAtIgQ9ughChgAAIgkHkgAuYgw1tgT8LiQBCggBjggBagXxpgQDtgQYJgQA/hA+/gX2FgQEpgg9ng4N8hA0rhQAVgCm+AwALg4EanoANJoKQHIQ8IIF6a4EACIVj8IApqYQ+Z4AAD4ArbYM+g4FA1AHbgBvEBAFBFk2AK+6BhJIGQYGggAJxgCfigQBNgzdEAwECAoCf14ENlAIqRoAABYAzZYFj4gMAQTmBLTSBBvmAAl8DC9wJggGGgZUMgEaYggIUASyBLCmABt+AdsaBAA+AAAOBJCGBK+2DH4yBHniCABmDklmEAsACQSqAFtUCdSKAfX2BAbWAAkiBABcBbIMK7QFcgCXQgAGIgX9BgQ97gASOgQBrgABkgWYhg1pvAU+AEmEBS4EW+IAGbAFFgEB5gIQEAnJygWhggizPhD0igIIIgG54gCzcgQK6ggLOgF9ngB1nhBYYhQATgAtJhhqJhwAWgZgHgCRMhBp+hwAYgB2ohjTrgy6pgEk9hISBgQEYgQAIATiCAMaBHKqBALcBCIFH64A3qYMBBIKR4YI3+oKMw4E3zIEv5YGM34E5WoIAGoGQq4EAQoIADYFV9YA4FYEBf4UZWIIcxIA1zAIQOIItQIcAEYIAVoIADYEHXoEAVoIADYUbA4KCTYIBY4FdDYFFzoEXbYKD4YOCUYEBhIICfIIH1IIuBIIB4oIzWYJAXYEcvIEA4YEhcIKZK4EA2YQAJYM/b4ED2wFsgwBDgAAXgj+wAWyBbOwBA4KdDoEJGoBEfIE0a4EASIEDw4FIyoFEuYAAEAGwgARGAUGDh+KCCUGBAHCCALCAAEKBAAcCtC2BRFeCB88BtIMAGYAAioISnIEAA4ENE4IBaYIAMoABPYEAk4AAaIMFRYICBwG0gQ2TgUsqgJYlARuClCKCAEiBALQBXIEFP4AAIwLELYEfAYIAEwLELYEAxgIGBIM0ZgEBgAMkgaNohAFCgTaegSIcgQKhgQGtgBp9hgD0hQE6gQAlggCygQLVggrNgEXVgCphgQBfgTpEhACggToagQHphAESgQ4ggwFZmAESgEvfhBO+AWyDA1SFARyCAYeCBo6EA3SAQD6DAPCCES2CAUiANoGABm+CAj+tASyQASSEAQGAClCAC7mEA8uCAwiFA+eBAQ6BkH+BA7eCAICBBDSABYsCSxuDIaCADBgBRYUDtAEGgGVbhJlwggFjg4csgwCoATiABTGCRWiDS0ABCIIh/IMwVwEagzHzgwGWARqCO4QBC4CbNIAAyYMDSoFGSIIBYYIvMYAS9AFBgF7IAQOBTOmAJ32CHXeAJKIBi4Eu/oEAJYBnnAIQLoRBKYNCZoBvQ4EaqIGYvoQFbII5TIAaUIUCcYAVC4IDf4IvyIAAGIAADYFIUIEENoIADYQD1YEagoOFXYIAXYFpZ4MAHII1mIIAFoFDoAMLC4SBHgeBADKAaCSCBEiBBP+CBAOAATuBA92CRS6CA4cCECaHHYGAOe0BGIEy2oM484IAc4BDpIAAJIFAzoQRlIUAE4Q6s4QARoAApIQH9oAEuIAADYFKfQULkAkBD4EHd4EhAoEZU4Edx4CXKYWBgYEALgN0QYWCXkABAIE3aIIAEYACswKGAoI9BIMwt4M59oE1c4QAbgFUiAPUATiABwSCAe+AQ4eBVVoBc4CEsYJDlIAwLIMCrgE0gB8bgxaCgFRvgxTkgQdQgAlMggNHghK+hAGVASyAAHmBSOACA2uBB22BAAIDAxA7gjX8ggD7gjVyg5FkAQODn5+AABOANPyDA1qBNLaBABGBNPyCAxaAAAUBcIAErYYJDpIAKoCLYYcgxZIAIoI2FIIGdoGIqIY2FICFnYE2FIQVsIMlZoFzY4FV7oFhUYEOf4QQrIFIioAX1gKQI4EIMIINXIoANoIAe4BE34JpBoIEVoIADQKkLYEUUYEAlYFJIIABgIMD3QKAAYUeJ4IV4IARKQFgggGIgR0QggEkAUiDB7EBbIMEXwE0gBflgQGMgDepgQGCg0nFAVSAUcGBAa6BLWGBAEmCAPaDYHyBAZQBC4QJHwMQdHOAUkqBDk4BSIJyGwEMgwHKgiPngxXCghgBgAGwgwDHgylhgQCRgilmgjU2hABXgHBzgDhmggt+gzcxhwS6hAB3ggQhgAAPgVhzhAJDgwJsgVi4gwGOgQJegQAZggBNggsyggA1gQBJhDdGlgHGiBq4sAAfgwvcgVaKlAG9hDdMgwDVhwFMgjdLggHLgp/mhAe3hATVgaZBgTdQggDEAQKDN1CBBBuCN1CDAEqIBPWBAAeDO5OCniKDSO+BBjyAAWQBT4BH6YY65oIZhYQAYoJtl4QAYgEBhDqagZs6gTrnjQBigjrnhABmARuDRocCoC2DOpShAFOZALWBRveBSoKBht4CvgWAEb6CA+yAC7WAA+6DCneAiVeDFg8BPIMC5YAEXQFqgRjmggAdASyFoV+BB2CBEbKBmdiAEU+FBbsBcIAKYoFii4QCU4AKb4MIoYIAsYIAHAFcgwSKArQtgj83iAiAAUSBAAUBTIEeCYAMeIMLEIIAioABVYIKtYMWaYF1f4FEWQQgCE8bhCXIgAuPhAmMgk9KggA+AQOCGOelADuAEXWADduECHSAS1yCR1eBAlCDBYWDAWICBGqABzIBEIIC44EXB4ACZIMAMIEH3YGgiYAFlYQCg4EIeoIA/4EImIAed4IcWYcDRoENGYEDSIIEGwFYgBaOgAWogC+2gFTsgRAygR9igAB+g3FagkDRgACGgAAkgCj5gwAmggDogAAFgBkciAXOggE3ASKAVgqCBAeAGTyDAxGCGuuCAWSEHaqCHO+DXFmBL+MBhYEACoQCHIFAI4UJeIMJdQHEgAOAgiMsgyVAggEJgCNfgAQDgWQKAYKCLX2CAWGAAAyBDEiACHuADCqFTlaBApWBKoeCOOaBFD+DJS2BPE2AAA6CqcKBCd+BGXKCCeaECBWBMV+FAEGBSpCFSoWBAI+ACuSAAEOBFH2ACS0DC68EgB+0gQAZAXyBGVyAKQWBAAwBeIMBfQKMAYUNRwFshAt7AWuAAuOBGdWBAVgBA4Bl8YIFjAGQgJlBggDbgAGVgAxggAA0ggWcATiAHOaABQCBFtkBaoAFoAEHgj3agSsbgRbbgQTfg1v4gQAKggCaATSAHZ6BAZiDHUaBCuKAYcSBDAuDAC8CIAqBCJKEADICIAuCCJ+BAAqBXhGEAA2AA0qDPlGBPj+DEjyIajmGPkaAAICCAC2BBYmBPheAAA2AB7iCPkyAARyBMVyAAA2AOn+ADByBMVCAAA2ACdOAAFCBMUSAAA2APlWAAa6BMTiAAA2APliAAYGBMSyAAA2CFHaBBVaBB0iAEBiCD1aALtSBPl6AB5iBINiDPmWAPVGAAKGAir6CPmWBEIyDiayAY1eBAAqCQFaAHf0BBoNGMoARRQEGg6Vdgl81ghzAgADbghTdggKRgl7AgHHzgQJDgQ6jAQWDKAKAAuqASmABIIIjEIEZIoKdrYM9oIAC3IArXYMBe4AAG4FXcQESgAFwARGCAw2BA+oBAYELvoEsPAIiCYEC0oEZW4EABAVJGwu4C4EcQoMJg4EqQoEJg4RiuZIJgwFFgwIbgQmEgEDrgAFhgEM5ggtEkQmDggJIkAmDgAQqhAO1ggAZiQmDgx1tgQe8gwmDgAG2hRwcgQiBgAd6AXiEBVeAaSCCSXKCDjoBYIEcXoUAUAGAggDvgQLhggmxggR4iwm0gAP/AWCBJP+EA+qBSNSDKDCAAiiAPKyDFzuECaMDQYEggQDZiABsggLgAXiCDzWBCPiAAm6FZNCAABiAB6GDE1+DB1wBdIJZEYAACYUJ+IAQZYAABwFkgA/+gAHciQfXiENlhAAvhhALlgAigACAkQn9gBdwjgn9gR1ztAn9AXiBHfiCBTSEAXyAP5eAB6aAAIyANXGBCmqCWd6BAN2DBqWAChuCAOWAChsBCoMfJYIBE4MOBYAEAoQdz4QCJ4EJV4I1AokCIoAMppUF14JtpAIiCIQF14AEpIQCIIUF2AJ4IIKTC4QCF4IJ0IBPloEJHYKn2oAHgoEEfIECtYEABIR3xIZAP4QAkYIIOoFa0psI74KpJoAACgFohQWeggYOhAUHgRidjAIRhQIKiwnRrQAfgxJlgSBojwGwhwnUgwlthACFkgDghAMZkgDjhANygQouhgiuhgpIhgD+AQSCpeCDAWGUAC6ABKiCrdH/ASWHASWCAhSICqeBEEGOCqeGAhqQClSBB+WsCqeKAm2VAFOgCqeBBHaAk0wDAAs/gg/CgQAejxdIhkAhlAAfgAAcglJFBARAED+AAZ6AtXUCCxuAAA+HeJGACHGBLnwBSIB4CwQQGwtDgxYdh1XukRYdggogghO6ggfBgRIcgRPEgAcggXXxBQsL4x0LgVSNBAuhBGmAtDcFZmZpY2mAs7wBIIO1sBMAMS4zLjEuMS1tb3RsZXkAaW52gLREFWQgbGl0ZXJhbC9sZW5ndGhzIHNldIYAHAVjb2RlIIkAGQ91bmtub3duIGhlYWRlciCAtKoBZ4sAMgJkaYC0TgFugLTgigAWA2JpdIQARxAgcmVwZWF0AHRvbyBtYW55hQAXB3N5bWJvbHOOABgCb3KGAFOGACSFAFaCtMuAAF2AtRcBa4UApgIAYoAA+IAAmgxlcnJvcgBzdHJlYW2EAA2KANULLS0gbWlzc2luZyCAtX4ELW9mLYIAR4AAJQJjb4C1BAJjdIUA4wNjaGWKABeEAJiNABcEZGF0YYYAFYsBCwEggQDUBWZhciBigLVnAQCFAFcCcmOBAIEFbWF0Y2iGADIBd4C1ywRvdyBzgbXahgE7ggDeA3R5cIcAE4sBsoIA0I8AdYIAFoUBrwRjb21wgLX7AXOAtcCAAg4EdGhvZIAu/RMMC6UCAwAEAAUABgAHAAgACQAKgCXVDQ0ADwARABMAFwAbAB+Alj0VKwAzADsAQwBTAGMAcwCDAKMAwwDjgbhQggABAYCMAAIBgYQAAgGChAACAYOEAAIBhIQAAgGFhAACBZAASQDIghWNgK4cggCEAQeAAIABDYAAegEZgCX3ATGABD8BYYAARgHBgEXeAYGBReCAPP8EAQYBCIAl1gMQARiAAzcJMAFAAWABgAHAiQB4hQBwhQBoAYaAAAIBh4AAAgGIgAACAYmAAAIBioAAAgGLgAACAYyAAAIBjYAAAgGOgAACARCAAHIBEoAAiAEIggCAAQaAAQIBBYABBAMEAAyAAJaAGV0CAA6AAKIBD4CxBgQOC7cMtQEsgBmWggABARCMAAIBEYQAAgEShAACAROEAAIBFIQAAgEVhAACARDAASyJAICFAHSFAGyBAGQBFoAAAgEXgAACARiAAAIBGYAAAgEagAACARuAAAIBHIAAAgEdgAACAUCAAAIGoAgAAKANgACIgADQAR6AAAQBD4AAVAEggAAQAiAOgwDgAR6AAASBABSBAAEBoIQAFAETgAAEAQeEABQBDIABOAGMgAAEAUyAAAQBzIAABAEsgAAEAayAAAQBbIAABAHsgAAEARyAAAQBnIAABAFcgAAEAdyAAAQBPIAABAG8gAAEAXyAAAQB/IAABAECgAAEAYKAAAQBQoAABAHCgAAEASKAAAQBooAABAFigAAEAeKAAAQBEoAABAGSgAAEAVKAAAQB0oAABAEygAAEAbKAAAQBcoAABAHygAAEAQqAAAQBioAABAFKgAAEAcqAAAQBKoAABAGqgAAEAWqAAAQB6oAABAEagAAEAZqAAAQBWoAABAHagAAEgHp2AgC6gAAEAXqAAAQB+oAABAEGgAAEAYaAAAQBRoAABAHGgAAEASaAAAQBpoAABAFmgAAEAeaAAAQBFoAABAGWgAAEAVaAAAQB1oAABAE2gAAEAbaAAAQBdoAABAH2gAAEAQ6AAAQBjoAABAFOgAAEAc6AAAQBLoAABAGugAAEAW6AAAQB7oAABAEegAAEAZ6AAAQBXoAABAHegAAEAT6AAAQBvoAABAF+gAAEAf6AAAQBAYAABAGBgAAEAUGAAAQBwYAABAEhgAAEAaGAAAQBYYAABAHhgAAEARGAAAQBkYAABAFRgAAEAdGAAAQBMYAABAGxgAAEAXGAAAQB8YAABAEJgAAEAYmAAAQBSYAABAHJgAAEASmAAAQBqYAABAFpgAAEAemAAAQBGYAABAGZgAAEAVmAAAQB2YAABAE5gAAEAbmAAAQBeYAABAH5gAAEAQWAAAQBhYAABAFFgAAEAcWAAAQBJYAABAGlgAAEAWWAAAQB5YAABAEVgAAEAZWAAAQBVYAABAHVgAAEATWAAAQBtYAABAF1gAAEAfWAAAQBDYAABAGNgAAEAU2AAAQBzYAABIAN6AIArYAABAFtgAAEAe2AAAQBHYAABAGdgAAEAV2AAAQB3YAABAE9gAAEAb2AAAQBfYAABAH9gAAEAROAAMIFEwEJAJOAAAgBk4AACAFTgAAIAVOAAAgB04AACAHTgAAIATOAAAgBM4AACAGzgAAIAbOAAAgBc4AACAFzgAAIAfOAAAgB84AACAELgAAIgA2LgAQCgAAEgAAIAUuAAAgBS4AACAHLgAAIAcuAAAgBK4AACAErgAAIAauAAAgBq4AACAFrgAAIAWuAAAgB64AACAHrgAAIARuAAAgBG4AACAGbgAAIAZuAAAgBW4AACAFbgAAIAduAAAgB24AACAE7gAAIATuAAAgBu4AACAG7gAAIAXuAAAgBe4AACAH7gAAIAfuAAAiBA7YBB4AACAGHgAAIAYeAAAgBR4AACAFHgAAIAceAAAgBx4AACAEngAAIASeAAAgBp4AACAGngAAIAWeAAAgBZ4AACAHngAAIAeeAAAgBF4AACAEXgAAIAZeAAAgBl4AACAFXgAAIAVeAAAgB14AACAHXgAAIATeAAAgBN4AACAG3gAAIAbeAAAgBd4AACAF3gAAIAfeAAAgB94AACAEPgAAIAQ+AAAgBj4AACAGPgAAIAU+AAAgBT4AACAHPgAAIAc+AAAgBL4AACAEvgAAIAa+AAAgBr4AACAFvgAAIAW+AAAgB74AACAHvgAAIAR+AAAgBH4AACAGfgAAIAZ+AAAgBX4AACAFfgAAIAd+AAAgB34AACAE/gAAIAT+AAAgBv4AACAG/gAAIAX+AAAgBf4AACAH/gAAIAf+AAAiBBAoBQIAABAEggAAEAWCAAAQBEIAABAFQgAAEATCAAAQBcIIFVgMHAEiAAAQBKIAABAFogAAEARiAAAQBWIAABAE4gAAEAXiAAAQBBIAABAFEgAAEASSAAAQBZIAABAEUgAAEAVSAAAQBNIAABAF0gAAEAQOAAEIBg4AABAFDgAAEAcOAAAQBI4AABAGjgAAEAWOAAAQB44AABIC/A4AAdIECxgEFgABcAQWCBUoBFIAABAEMgAAEARyAAAQBAoAABAESgAAEgQYEARqCBeoBBYAD1AEFgAO4AQWAA5yATGqAAAQBEYAABAEJgAAEARmAAASBAAIBFYAABAENgAAEAR2AAASAv26AAqSBBkABBYACLIEFpgEFgAG0AQWAOroDGwtNgxx6hwAEAQKMAASBB1GJAAQBBIwABAEFigAEBEGwHAuAveGLAEuNADuFAC8BBoQABIEFiIEABIEBCoEABIEBkoEABICFfIIABAELhAAEAQyEAASABduBRGIE4B0LI4UAX4UFywIQEYAFbQYHCQYKBQuAN44EDQIOAYAHJQSUHgtphQCQhQCIhQCAhQB4gQBogQBcgQYfARCAAAQBFIAABAEYgAAEARyAAAQBIIAABAEogAAEATCAAAQBOIAABAFAgAAEAVCAAASBBr0BcIAABAGAgAAEAaCAAAQBwIAABAHggABvAx8Lco0Ab4EAa4EAZ4EAY4EAX4EAW4EAV4EAU4EAT4EAS4EAR4EAQ4EBPAGArwBBgE7BAgttgQDHAQSAAAIBCIAABIEBM4ECSwEQgAAOgwAMgZ97gKs6hAAkgQdzgQBPAQiAAAiBABiFAAyBCLeDAAwBIIEAlIAvUoEAawGAgQgvAQSDAAyAPCIKAQAQDABBkSEL/4Ah4AEDgpzlBQgJCQoKgEYggAABAQ2AAAEBDoAAAQEPgAABARCEAAEBEYQAAQEShAABAROEAAEBFIwAAQEVjAABARaMAAEBF4wAAQEYnAABARmcAAEBGpwAAQEbmwABARyBfrkEBAQFBYHCrAEHgAABAQiEAAGAWjqCAAEBCowAAYAkc4oAAYEBMJkAAYEBTJkAAYEBaLkAAYEBpLkAAYIDdYABzoUBvI0BqJ0BkLwBgAIbHLwAAQEdvAABgLyTgH3yA9AqAQ==")),B)});}
|
|
6993
|
+
const A="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";function g(g){let B;g({wasmURI:()=>(B||(B="data:application/wasm;base64,"+(g=>{g=(g=>{const B=(g=(g+"").replace(/[^A-Za-z0-9+/=]/g,"")).length,E=[];for(let C=0;B>C;C+=4){const B=A.indexOf(g[C])<<18|A.indexOf(g[C+1])<<12|(63&A.indexOf(g[C+2]))<<6|63&A.indexOf(g[C+3]);E.push(B>>16&255),"="!==g[C+2]&&E.push(B>>8&255),"="!==g[C+3]&&E.push(255&B);}return new Uint8Array(E)})(g);let B=new Uint8Array(1024),E=0;for(let A=0;A<g.length;){const I=g[A++];if(128&I){const Q=3+(127&I),D=g[A++]<<8|g[A++],Y=E-D;C(E+Q);for(let A=0;Q>A;A++)B[E++]=B[Y+A];}else {const Q=I;C(E+Q);for(let C=0;Q>C&&A<g.length;C++)B[E++]=g[A++];}}return (g=>{let B="";const E=g.length;let C=0;for(;E>C+2;C+=3){const E=g[C]<<16|g[C+1]<<8|g[C+2];B+=A[E>>18&63]+A[E>>12&63]+A[E>>6&63]+A[63&E];}const I=E-C;if(1===I){const E=g[C]<<16;B+=A[E>>18&63]+A[E>>12&63]+"==";}else if(2===I){const E=g[C]<<16|g[C+1]<<8;B+=A[E>>18&63]+A[E>>12&63]+A[E>>6&63]+"=";}return B})(new Uint8Array(B.buffer.slice(0,E)));function C(A){if(B.length<A){let g=2*B.length;for(;A>g;)g*=2;const C=new Uint8Array(g);C.set(B.subarray(0,E)),B=C;}}})("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EAIgDoMA4AEegAAEgQAUgQABAaCEABQBE4AABAEHhAAUAQyAATgBjIAABAFMgAAEAcyAAAQBLIAABAGsgAAEAWyAAAQB7IAABAEcgAAEAZyAAAQBXIAABAHcgAAEATyAAAQBvIAABAF8gAAEAfyAAAQBAoAABAGCgAAEAUKAAAQBwoAABAEigAAEAaKAAAQBYoAABAHigAAEARKAAAQBkoAABAFSgAAEAdKAAAQBMoAABAGygAAEAXKAAAQB8oAABAEKgAAEAYqAAAQBSoAABAHKgAAEASqAAAQBqoAABAFqgAAEAeqAAAQBGoAABAGagAAEAVqAAAQB2oAABIB91wIAuoAABAF6gAAEAfqAAAQBBoAABAGGgAAEAUaAAAQBxoAABAEmgAAEAaaAAAQBZoAABAHmgAAEARaAAAQBloAABAFWgAAEAdaAAAQBNoAABAG2gAAEAXaAAAQB9oAABAEOgAAEAY6AAAQBToAABAHOgAAEAS6AAAQBroAABAFugAAEAe6AAAQBHoAABAGegAAEAV6AAAQB3oAABAE+gAAEAb6AAAQBfoAABAH+gAAEAQGAAAQBgYAABAFBgAAEAcGAAAQBIYAABAGhgAAEAWGAAAQB4YAABAERgAAEAZGAAAQBUYAABAHRgAAEATGAAAQBsYAABAFxgAAEAfGAAAQBCYAABAGJgAAEAUmAAAQByYAABAEpgAAEAamAAAQBaYAABAHpgAAEARmAAAQBmYAABAFZgAAEAdmAAAQBOYAABAG5gAAEAXmAAAQB+YAABAEFgAAEAYWAAAQBRYAABAHFgAAEASWAAAQBpYAABAFlgAAEAeWAAAQBFYAABAGVgAAEAVWAAAQB1YAABAE1gAAEAbWAAAQBdYAABAH1gAAEAQ2AAAQBjYAABAFNgAAEAc2AAASADegCAK2AAAQBbYAABAHtgAAEAR2AAAQBnYAABAFdgAAEAd2AAAQBPYAABAG9gAAEAX2AAAQB/YAABAETgADCBRMBCQCTgAAIAZOAAAgBU4AACAFTgAAIAdOAAAgB04AACAEzgAAIATOAAAgBs4AACAGzgAAIAXOAAAgBc4AACAHzgAAIAfOAAAgBC4AACIANi4AEAoAABIAACAFLgAAIAUuAAAgBy4AACAHLgAAIASuAAAgBK4AACAGrgAAIAauAAAgBa4AACAFrgAAIAeuAAAgB64AACAEbgAAIARuAAAgBm4AACAGbgAAIAVuAAAgBW4AACAHbgAAIAduAAAgBO4AACAE7gAAIAbuAAAgBu4AACAF7gAAIAXuAAAgB+4AACAH7gAAIgQO2AQeAAAgBh4AACAGHgAAIAUeAAAgBR4AACAHHgAAIAceAAAgBJ4AACAEngAAIAaeAAAgBp4AACAFngAAIAWeAAAgB54AACAHngAAIAReAAAgBF4AACAGXgAAIAZeAAAgBV4AACAFXgAAIAdeAAAgB14AACAE3gAAIATeAAAgBt4AACAG3gAAIAXeAAAgBd4AACAH3gAAIAfeAAAgBD4AACAEPgAAIAY+AAAgBj4AACAFPgAAIAU+AAAgBz4AACAHPgAAIAS+AAAgBL4AACAGvgAAIAa+AAAgBb4AACAFvgAAIAe+AAAgB74AACAEfgAAIAR+AAAgBn4AACAGfgAAIAV+AAAgBX4AACAHfgAAIAd+AAAgBP4AACAE/gAAIAb+AAAgBv4AACAF/gAAIAX+AAAgB/4AACAH/gAAIgQQKAUCAAAQBIIAABAFggAAEARCAAAQBUIAABAEwgAAEAXCCBVYDBwBIgAAEASiAAAQBaIAABAEYgAAEAViAAAQBOIAABAF4gAAEAQSAAAQBRIAABAEkgAAEAWSAAAQBFIAABAFUgAAEATSAAAQBdIAABAEDgABCAYOAAAQBQ4AABAHDgAAEASOAAAQBo4AABAFjgAAEAeOAAASAwmaAAHSBAsYBBYAAXAEFggVKARSAAAQBDIAABAEcgAAEgEVZgAREAQWCBgQBGoIF6gEFgAPUAQWAA7gBBYADnIBPy4AABAERgAAEAQmAAAQBGYAABIEAAgEVgAAEAQ2AAAQBHYAABAEDgAAEAROCBkABBYACLIEFpgEFgAG0AQWAOz0DGwtNgxx6hwAEAQKMAASBB1GJAAQBBIwABAEFigAEBEGwHAuAwUKLAEuNADuFAC8BBoQABIEFiIEABIEBCoEABIEBkoEABICI3YIABAELhAAEAQyEAASABduBR8EE4B0LI4UAX4UFywIQEYAFbQYHCQYKBQuAN44EDQIOAYAHJQSUHgtphQCQhQCIhQCAhQB4gQBogQBcgQYfARCAAAQBFIAABAEYgAAEARyAAAQBIIAABAEogAAEATCAAAQBOIAABAFAgAAEAVCAAASBBr0BcIAABAGAgAAEAaCAAAQBwIAABAHggABvAx8Lco0Ab4EAa4EAZ4EAY4EAX4EAW4EAV4EAU4EAT4EAS4EAR4EAQ4EBPAGArwBBgFIiAgttgQDHAQSAAAIBCIAABIEBM4ECSwEQgAAOgwAMgaLcgK6bhAAkgQdzgQBPAQiAAAiBABiFAAyBCLeDAAwBIIEAlIAvUoEAawGAgQgvAQSDAAyAPCIKAQAQDABBkSEL/4Ah4AEDgqBGBQgJCQoKgEmBgAABAQ2AAAEBDoAAAQEPgAABARCEAAEBEYQAAQEShAABAROEAAEBFIwAAQEVjAABARaMAAEBF4wAAQEYnAABARmcAAEBGpwAAQEbmwABARyBghoEBAQFBYHGDQEHgAABAQiEAAGAXZuCAAEBCowAAYAkc4oAAYEBMJkAAYEBTJkAAYEBaLkAAYEBpLkAAYIDdYABzoUBvI0BqJ0BkLwBgAIbHLwAAQEdvAABgL/0gIFTA1BLAQ==")),B)});}
|
|
6516
6994
|
|
|
6517
6995
|
/*
|
|
6518
6996
|
Copyright (c) 2025 Gildas Lormeau. All rights reserved.
|
|
@@ -7249,6 +7727,10 @@ class ZipDirectoryEntry extends ZipEntry {
|
|
|
7249
7727
|
return writable;
|
|
7250
7728
|
}
|
|
7251
7729
|
|
|
7730
|
+
exportFileSystemHandle(handle, options = {}) {
|
|
7731
|
+
return exportFileSystemHandle(this, handle, options);
|
|
7732
|
+
}
|
|
7733
|
+
|
|
7252
7734
|
async importZip(reader, options = {}) {
|
|
7253
7735
|
await initStream(reader);
|
|
7254
7736
|
const zipReader = new ZipReader(reader, options);
|
|
@@ -7514,6 +7996,10 @@ class FS {
|
|
|
7514
7996
|
return this.root.exportWritable(writable, options);
|
|
7515
7997
|
}
|
|
7516
7998
|
|
|
7999
|
+
exportFileSystemHandle(handle, options) {
|
|
8000
|
+
return this.root.exportFileSystemHandle(handle, options);
|
|
8001
|
+
}
|
|
8002
|
+
|
|
7517
8003
|
exportZip(writer, options) {
|
|
7518
8004
|
return this.root.exportZip(writer, options);
|
|
7519
8005
|
}
|
|
@@ -7751,6 +8237,56 @@ function addFileSystemHandle(zipEntry, handle, options) {
|
|
|
7751
8237
|
}
|
|
7752
8238
|
}
|
|
7753
8239
|
|
|
8240
|
+
async function exportFileSystemHandle(zipEntry, directoryHandle, options) {
|
|
8241
|
+
const totalSize = getTotalSize([zipEntry], "uncompressedSize");
|
|
8242
|
+
const writtenSizes = new Map();
|
|
8243
|
+
await exportChildren(zipEntry, directoryHandle);
|
|
8244
|
+
return directoryHandle;
|
|
8245
|
+
|
|
8246
|
+
async function exportChildren(entry, parentHandle) {
|
|
8247
|
+
// Separate files have no ordering constraint, so they can be written concurrently on demand.
|
|
8248
|
+
if (options.concurrent) {
|
|
8249
|
+
const results = await Promise.allSettled(entry.children.map(child => exportChild(child, parentHandle)));
|
|
8250
|
+
const failedResult = results.find(result => result.status == "rejected");
|
|
8251
|
+
if (failedResult) {
|
|
8252
|
+
throw failedResult.reason;
|
|
8253
|
+
}
|
|
8254
|
+
} else {
|
|
8255
|
+
for (const child of entry.children) {
|
|
8256
|
+
await exportChild(child, parentHandle);
|
|
8257
|
+
}
|
|
8258
|
+
}
|
|
8259
|
+
}
|
|
8260
|
+
|
|
8261
|
+
async function exportChild(child, parentHandle) {
|
|
8262
|
+
try {
|
|
8263
|
+
if (child.directory) {
|
|
8264
|
+
const childDirectoryHandle = await parentHandle.getDirectoryHandle(child.name, { create: true });
|
|
8265
|
+
await exportChildren(child, childDirectoryHandle);
|
|
8266
|
+
} else {
|
|
8267
|
+
const fileHandle = await parentHandle.getFileHandle(child.name, { create: true });
|
|
8268
|
+
const writable = await fileHandle.createWritable();
|
|
8269
|
+
// getData() streams the entry's data into `writable` and closes it (a FileSystemWritableFileStream
|
|
8270
|
+
// only commits the file on close), applying options such as password, signal and onprogress.
|
|
8271
|
+
await child.getData({ writable }, Object.assign({}, options, {
|
|
8272
|
+
onprogress: async progress => {
|
|
8273
|
+
if (options.onprogress) {
|
|
8274
|
+
writtenSizes.set(child.id, progress);
|
|
8275
|
+
try {
|
|
8276
|
+
await options.onprogress(Array.from(writtenSizes.values()).reduce((previousValue, currentValue) => previousValue + currentValue, 0), totalSize);
|
|
8277
|
+
} catch {
|
|
8278
|
+
// ignored
|
|
8279
|
+
}
|
|
8280
|
+
}
|
|
8281
|
+
}
|
|
8282
|
+
}));
|
|
8283
|
+
}
|
|
8284
|
+
} catch (error) {
|
|
8285
|
+
throw new Error(error.message + (child ? " (" + child.name + ")" : ""), { cause: error });
|
|
8286
|
+
}
|
|
8287
|
+
}
|
|
8288
|
+
}
|
|
8289
|
+
|
|
7754
8290
|
async function transformToFileSystemhandle(entry) {
|
|
7755
8291
|
const handle = {
|
|
7756
8292
|
name: entry.name
|
|
@@ -9538,6 +10074,7 @@ exports.ZipReaderStream = ZipReaderStream;
|
|
|
9538
10074
|
exports.ZipWriter = ZipWriter;
|
|
9539
10075
|
exports.ZipWriterStream = ZipWriterStream;
|
|
9540
10076
|
exports.configure = configure;
|
|
10077
|
+
exports.createOPFSTempStream = createOPFSTempStream;
|
|
9541
10078
|
exports.fs = fs;
|
|
9542
10079
|
exports.getMimeType = getMimeType;
|
|
9543
10080
|
exports.terminateWorkers = terminateWorkersAndModule;
|