From b1f67dfc1a7372dd665246cf1c203528e5057e42 Mon Sep 17 00:00:00 2001 From: bellard <6490144+bellard@users.noreply.github.com> Date: Sun, 8 Nov 2020 14:30:56 +0100 Subject: [PATCH] 2020-11-08 release --- Changelog | 7 + Makefile | 15 +- TODO | 82 +- VERSION | 2 +- doc/jsbignum.html | 734 ------------ doc/jsbignum.pdf | Bin 153057 -> 0 bytes doc/quickjs.html | 1369 --------------------- doc/quickjs.pdf | Bin 165855 -> 0 bytes doc/quickjs.texi | 12 +- jscompress.c | 918 --------------- libbf.h | 2 +- libregexp.c | 26 +- qjscalc.js | 11 + quickjs-atom.h | 1 + quickjs-libc.c | 95 +- quickjs-opcode.h | 13 +- quickjs.c | 2549 ++++++++++++++++++++++------------------ quickjs.h | 9 +- release.sh | 77 +- test262.conf | 17 +- test262_errors.txt | 65 +- tests/test_builtin.js | 25 +- tests/test_language.js | 155 ++- 23 files changed, 1880 insertions(+), 4304 deletions(-) delete mode 100644 doc/jsbignum.html delete mode 100644 doc/jsbignum.pdf delete mode 100644 doc/quickjs.html delete mode 100644 doc/quickjs.pdf delete mode 100644 jscompress.c diff --git a/Changelog b/Changelog index 1a7533b..0c25b96 100644 --- a/Changelog +++ b/Changelog @@ -1,3 +1,10 @@ +2020-11-08: + +- improved function parameter initializers +- added std.setenv(), std.unsetenv() and std.getenviron() +- added JS_EvalThis() +- misc bug fixes + 2020-09-06: - added logical assignment operators diff --git a/Makefile b/Makefile index 94c8e31..766a7e1 100644 --- a/Makefile +++ b/Makefile @@ -28,9 +28,9 @@ endif # Windows cross compilation from Linux #CONFIG_WIN32=y # use link time optimization (smaller and faster executables but slower build) -CONFIG_LTO=y +#CONFIG_LTO=y # consider warnings as errors (for development) -#CONFIG_WERROR=y +CONFIG_WERROR=y # force 32 bit build for some utilities #CONFIG_M32=y @@ -53,7 +53,11 @@ CONFIG_BIGNUM=y OBJDIR=.obj ifdef CONFIG_WIN32 - CROSS_PREFIX=i686-w64-mingw32- + ifdef CONFIG_M32 + CROSS_PREFIX=i686-w64-mingw32- + else + CROSS_PREFIX=x86_64-w64-mingw32- + endif EXE=.exe else CROSS_PREFIX= @@ -281,15 +285,12 @@ $(OBJDIR)/%.check.o: %.c | $(OBJDIR) regexp_test: libregexp.c libunicode.c cutils.c $(CC) $(LDFLAGS) $(CFLAGS) -DTEST -o $@ libregexp.c libunicode.c cutils.c $(LIBS) -jscompress: jscompress.c - $(CC) $(LDFLAGS) $(CFLAGS) -o $@ jscompress.c - unicode_gen: $(OBJDIR)/unicode_gen.host.o $(OBJDIR)/cutils.host.o libunicode.c unicode_gen_def.h $(HOST_CC) $(LDFLAGS) $(CFLAGS) -o $@ $(OBJDIR)/unicode_gen.host.o $(OBJDIR)/cutils.host.o clean: rm -f repl.c qjscalc.c out.c - rm -f *.a *.o *.d *~ jscompress unicode_gen regexp_test $(PROGS) + rm -f *.a *.o *.d *~ unicode_gen regexp_test $(PROGS) rm -f hello.c test_fib.c rm -f examples/*.so tests/*.so rm -rf $(OBJDIR)/ *.dSYM/ qjs-debug diff --git a/TODO b/TODO index 0eec6d3..b5500c9 100644 --- a/TODO +++ b/TODO @@ -1,13 +1,11 @@ -Misc: -- use realpath in module name normalizer and put it in quickjs-libc -- use custom printf to avoid C library compatibility issues -- rename CONFIG_ALL_UNICODE, CONFIG_BIGNUM, CONFIG_ATOMICS, CONFIG_CHECK_JSVALUE ? +Bugs: +- modules: better error handling with cyclic module references + +Misc ideas: +- use custom printf to avoid compatibility issues with floating point numbers +- consistent naming for preprocessor defines - unify coding style and naming conventions - use names from the ECMA spec in library implementation -- modules: if no ".", use a well known module loading path ? -- use JSHoistedDef only for global variables (JSHoistedDef.var_name != JS_ATOM_NULL) -- add index in JSVarDef and is_arg flag to merge args and vars in JSFunctionDef -- replace most JSVarDef flags with var_type enumeration - use byte code emitters with typed arguments (for clarity) - use 2 bytecode DynBufs in JSFunctionDef, one for reading, one for writing and use the same wrappers in all phases @@ -15,48 +13,18 @@ Misc: - use custom timezone support to avoid C library compatibility issues Memory: +- use memory pools for objects, etc? - test border cases for max number of atoms, object properties, string length - add emergency malloc mode for out of memory exceptions. - test all DynBuf memory errors - test all js_realloc memory errors -- bignum: handle memory errors -- use memory pools for objects, etc? - improve JS_ComputeMemoryUsage() with more info -Optimizations: -- 64-bit atoms in 64-bit mode ? -- use auto-init properties for more global objects -- reuse stack slots for disjoint scopes, if strip -- optimize `for of` iterator for built-in array objects -- add heuristic to avoid some cycles in closures -- small String (0-2 charcodes) with immediate storage -- perform static string concatenation at compile time -- optimize string concatenation with ropes or miniropes? -- add implicit numeric strings for Uint32 numbers? -- optimize `s += a + b`, `s += a.b` and similar simple expressions -- ensure string canonical representation and optimise comparisons and hashes? -- remove JSObject.first_weak_ref, use bit+context based hashed array for weak references -- optimize function storage with length and name accessors? -- property access optimization on the global object, functions, - prototypes and special non extensible objects. -- create object literals with the correct length by backpatching length argument -- remove redundant set_loc_uninitialized/check_uninitialized opcodes -- peephole optim: push_atom_value, to_propkey -> push_atom_value -- peephole optim: put_loc x, get_loc_check x -> set_loc x -- comparative performance benchmark -- use variable name when throwing uninitialized exception if available -- convert slow array to fast array when all properties != length are numeric -- optimize destructuring assignments for global and local variables -- implement some form of tail-call-optimization -- optimize OP_apply -- optimize f(...b) - -Extensions: -- support more features in [features] section -- add built-in preprocessor in compiler, get rid of jscompress - handle #if, #ifdef, #line, limited support for #define -- get rid of __loadScript, use more common name +Built-in standard library: - BSD sockets +- modules: use realpath in module name normalizer and put it in quickjs-libc +- modules: if no ".", use a well known module loading path ? +- get rid of __loadScript, use more common name REPL: - debugger @@ -71,8 +39,32 @@ REPL: - save history - close all predefined methods in repl.js and jscalc.js +Optimization ideas: +- 64-bit atoms in 64-bit mode ? +- 64-bit small bigint in 64-bit mode ? +- reuse stack slots for disjoint scopes, if strip +- add heuristic to avoid some cycles in closures +- small String (0-2 charcodes) with immediate storage +- perform static string concatenation at compile time +- optimize string concatenation with ropes or miniropes? +- add implicit numeric strings for Uint32 numbers? +- optimize `s += a + b`, `s += a.b` and similar simple expressions +- ensure string canonical representation and optimise comparisons and hashes? +- remove JSObject.first_weak_ref, use bit+context based hashed array for weak references +- property access optimization on the global object, functions, + prototypes and special non extensible objects. +- create object literals with the correct length by backpatching length argument +- remove redundant set_loc_uninitialized/check_uninitialized opcodes +- peephole optim: push_atom_value, to_propkey -> push_atom_value +- peephole optim: put_loc x, get_loc_check x -> set_loc x +- convert slow array to fast array when all properties != length are numeric +- optimize destructuring assignments for global and local variables +- implement some form of tail-call-optimization +- optimize OP_apply +- optimize f(...b) + Test262o: 0/11262 errors, 463 excluded Test262o commit: 7da91bceb9ce7613f87db47ddd1292a2dda58b42 (es5-tests branch) -Test262: 30/71748 errors, 868 excluded, 474 skipped -Test262 commit: 24c67328062383079ada85f4d253eb0526fd209b +Result: 51/75119 errors, 899 excluded, 570 skipped +Test262 commit: 1c33fdb0ca60fb9d7392403be769ed0d26209132 diff --git a/VERSION b/VERSION index c67790a..78749b0 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -2020-09-06 +2020-11-08 diff --git a/doc/jsbignum.html b/doc/jsbignum.html deleted file mode 100644 index ab31612..0000000 --- a/doc/jsbignum.html +++ /dev/null @@ -1,734 +0,0 @@ - - - - -Javascript Bignum Extensions - - - - - - - - - - - - - - - -

Javascript Bignum Extensions

- - -

Table of Contents

- -
- -
- - - -

1 Introduction

- -

The Bignum extensions add the following features to the Javascript -language while being 100% backward compatible: -

- - -

The extensions are independent from each other except the math -mode which relies on BigFloat and operator overloading. -

- -

2 Operator overloading

- -

Operator overloading is inspired from the proposal available at -https://github.com/tc39/proposal-operator-overloading/. It -implements the same dispatch logic but finds the operator sets by -looking at the Symbol.operatorSet property in the objects. The -changes were done in order to simplify the implementation. -

-

More precisely, the following modifications were made: -

- - - -

3 BigInt extensions

- -

A few properties are added to the BigInt object: -

-
-
tdiv(a, b)
-

Return trunc(a/b). b = 0 raises a RangeError -exception. -

-
-
fdiv(a, b)
-

Return \lfloor a/b \rfloor. b = 0 raises a RangeError -exception. -

-
-
cdiv(a, b)
-

Return \lceil a/b \rceil. b = 0 raises a RangeError -exception. -

-
-
ediv(a, b)
-

Return sgn(b) \lfloor a/{|b|} \rfloor (Euclidian -division). b = 0 raises a RangeError exception. -

-
-
tdivrem(a, b)
-
fdivrem(a, b)
-
cdivrem(a, b)
-
edivrem(a, b)
-

Return an array of two elements. The first element is the quotient, -the second is the remainder. The same rounding is done as the -corresponding division operation. -

-
-
sqrt(a)
-

Return \lfloor \sqrt(a) \rfloor. A RangeError exception is -raised if a < 0. -

-
-
sqrtrem(a)
-

Return an array of two elements. The first element is \lfloor -\sqrt{a} \rfloor. The second element is a-\lfloor \sqrt{a} -\rfloor^2. A RangeError exception is raised if a < 0. -

-
-
floorLog2(a)
-

Return -1 if a \leq 0 otherwise return \lfloor \log2(a) \rfloor. -

-
-
ctz(a)
-

Return the number of trailing zeros in the two’s complement binary representation of a. Return -1 if a=0. -

-
-
- - -

4 BigFloat

- - -

4.1 Introduction

- -

This extension adds the BigFloat primitive type. The -BigFloat type represents floating point numbers in base 2 -with the IEEE 754 semantics. A floating -point number is represented as a sign, mantissa and exponent. The -special values NaN, +/-Infinity, +0 and -0 -are supported. The mantissa and exponent can have any bit length with -an implementation specific minimum and maximum. -

- -

4.2 Floating point rounding

- -

Each floating point operation operates with infinite precision and -then rounds the result according to the specified floating point -environment (BigFloatEnv object). The status flags of the -environment are also set according to the result of the operation. -

-

If no floating point environment is provided, the global floating -point environment is used. -

-

The rounding mode of the global floating point environment is always -RNDN (“round to nearest with ties to even”)1. The status flags of the global environment cannot be -read2. The precision of the global environment is -BigFloatEnv.prec. The number of exponent bits of the global -environment is BigFloatEnv.expBits. The global environment -subnormal flag is set to true. -

-

For example, prec = 53 and expBits = 11 exactly give -the same precision as the IEEE 754 64 bit floating point format. The -default precision is prec = 113 and expBits = 15 (IEEE -754 128 bit floating point format). -

-

The global floating point environment can only be modified temporarily -when calling a function (see BigFloatEnv.setPrec). Hence a -function can change the global floating point environment for its -callees but not for its caller. -

- -

4.3 Operators

- -

The builtin operators are extended so that a BigFloat is returned if -at least one operand is a BigFloat. The computations are always done -with infinite precision and rounded according to the global floating -point environment. -

-

typeof applied on a BigFloat returns bigfloat. -

-

BigFloat can be compared with all the other numeric types and the -result follows the expected mathematical relations. -

-

However, since BigFloat and Number are different types they are never -equal when using the strict comparison operators (e.g. 0.0 === -0.0l is false). -

- -

4.4 BigFloat literals

- -

BigFloat literals are floating point numbers with a trailing l -suffix. BigFloat literals have an infinite precision. They are rounded -according to the global floating point environment when they are -evaluated.3 -

- -

4.5 Builtin Object changes

- - -

4.5.1 BigFloat function

- -

The BigFloat function cannot be invoked as a constructor. When -invoked as a function: the parameter is converted to a primitive -type. If the result is a numeric type, it is converted to BigFloat -without rounding. If the result is a string, it is converted to -BigFloat using the precision of the global floating point environment. -

-

BigFloat properties: -

-
-
LN2
-
PI
-

Getter. Return the value of the corresponding mathematical constant -rounded to nearest, ties to even with the current global -precision. The constant values are cached for small precisions. -

-
-
MIN_VALUE
-
MAX_VALUE
-
EPSILON
-

Getter. Return the minimum, maximum and epsilon BigFloat values -(same definition as the corresponding Number constants). -

-
-
fpRound(a[, e])
-

Round the floating point number a according to the floating -point environment e or the global environment if e is -undefined. -

-
-
parseFloat(a[, radix[, e]])
-

Parse the string a as a floating point number in radix -radix. The radix is 0 (default) or from 2 to 36. The radix 0 -means radix 10 unless there is a hexadecimal or binary prefix. The -result is rounded according to the floating point environment e -or the global environment if e is undefined. -

-
-
isFinite(a)
-

Return true if a is a finite bigfloat. -

-
-
isNaN(a)
-

Return true if a is a NaN bigfloat. -

-
-
add(a, b[, e])
-
sub(a, b[, e])
-
mul(a, b[, e])
-
div(a, b[, e])
-

Perform the specified floating point operation and round the floating -point number a according to the floating point environment -e or the global environment if e is undefined. If -e is specified, the floating point status flags are updated. -

-
-
floor(x)
-
ceil(x)
-
round(x)
-
trunc(x)
-

Round to an integer. No additional rounding is performed. -

-
-
abs(x)
-

Return the absolute value of x. No additional rounding is performed. -

-
-
fmod(x, y[, e])
-
remainder(x, y[, e])
-

Floating point remainder. The quotient is truncated to zero (fmod) or -to the nearest integer with ties to even (remainder). e is an -optional floating point environment. -

-
-
sqrt(x[, e])
-

Square root. Return a rounded floating point number. e is an -optional floating point environment. -

-
-
sin(x[, e])
-
cos(x[, e])
-
tan(x[, e])
-
asin(x[, e])
-
acos(x[, e])
-
atan(x[, e])
-
atan2(x, y[, e])
-
exp(x[, e])
-
log(x[, e])
-
pow(x, y[, e])
-

Transcendental operations. Return a rounded floating point -number. e is an optional floating point environment. -

-
-
- - -

4.5.2 BigFloat.prototype

- -

The following properties are modified: -

-
-
valueOf()
-

Return the bigfloat primitive value corresponding to this. -

-
-
toString(radix)
-
-

For floating point numbers: -

- - -

The exponent letter is e for base 10, p for bases 2, 8, -16 with a binary exponent and @ for the other bases. -

-
-
toPrecision(p, rnd_mode = BigFloatEnv.RNDNA, radix = 10)
-
toFixed(p, rnd_mode = BigFloatEnv.RNDNA, radix = 10)
-
toExponential(p, rnd_mode = BigFloatEnv.RNDNA, radix = 10)
-

Same semantics as the corresponding Number functions with -BigFloats. There is no limit on the accepted precision p. The -rounding mode and radix can be optionally specified. The radix must be -between 2 and 36. -

-
-
- - -

4.5.3 BigFloatEnv constructor

- -

The BigFloatEnv([p, [,rndMode]] constructor cannot be invoked as a -function. The floating point environment contains: -

- - -

new BigFloatEnv([p, [,rndMode]] creates a new floating point -environment. The status flags are reset. If no parameter is given the -precision, exponent bits and subnormal flags are copied from the -global floating point environment. Otherwise, the precision is set to -p, the number of exponent bits is set to expBitsMax and the -subnormal flags is set to false. If rndMode is -undefined, the rounding mode is set to RNDN. -

-

BigFloatEnv properties: -

-
-
prec
-

Getter. Return the precision in bits of the global floating point -environment. The initial value is 113. -

-
-
expBits
-

Getter. Return the exponent size in bits of the global floating point -environment assuming an IEEE 754 representation. The initial value is -15. -

-
-
setPrec(f, p[, e])
-

Set the precision of the global floating point environment to p -and the exponent size to e then call the function -f. Then the Float precision and exponent size are reset to -their precious value and the return value of f is returned (or -an exception is raised if f raised an exception). If e -is undefined it is set to BigFloatEnv.expBitsMax. -

-
-
precMin
-

Read-only integer. Return the minimum allowed precision. Must be at least 2. -

-
-
precMax
-

Read-only integer. Return the maximum allowed precision. Must be at least 113. -

-
-
expBitsMin
-

Read-only integer. Return the minimum allowed exponent size in -bits. Must be at least 3. -

-
-
expBitsMax
-

Read-only integer. Return the maximum allowed exponent size in -bits. Must be at least 15. -

-
-
RNDN
-

Read-only integer. Round to nearest, with ties to even rounding mode. -

-
-
RNDZ
-

Read-only integer. Round to zero rounding mode. -

-
-
RNDD
-

Read-only integer. Round to -Infinity rounding mode. -

-
-
RNDU
-

Read-only integer. Round to +Infinity rounding mode. -

-
-
RNDNA
-

Read-only integer. Round to nearest, with ties away from zero rounding mode. -

-
-
RNDA
-

Read-only integer. Round away from zero rounding mode. -

-
-
RNDF4
-

Read-only integer. Faithful rounding mode. The result is -non-deterministically rounded to -Infinity or +Infinity. This rounding -mode usually gives a faster and deterministic running time for the -floating point operations. -

-
-
- -

BigFloatEnv.prototype properties: -

-
-
prec
-

Getter and setter (Integer). Return or set the precision in bits. -

-
-
expBits
-

Getter and setter (Integer). Return or set the exponent size in bits -assuming an IEEE 754 representation. -

-
-
rndMode
-

Getter and setter (Integer). Return or set the rounding mode. -

-
-
subnormal
-

Getter and setter (Boolean). subnormal flag. It is false when -expBits = expBitsMax. -

-
-
clearStatus()
-

Clear the status flags. -

-
-
invalidOperation
-
divideByZero
-
overflow
-
underflow
-
inexact
-

Getter and setter (Boolean). Status flags. -

-
-
- - -

5 BigDecimal

- -

This extension adds the BigDecimal primitive type. The -BigDecimal type represents floating point numbers in base -10. It is inspired from the proposal available at -https://github.com/littledan/proposal-bigdecimal. -

-

The BigDecimal floating point numbers are always normalized and -finite. There is no concept of -0, Infinity or -NaN. By default, all the computations are done with infinite -precision. -

- -

5.1 Operators

- -

The following builtin operators support BigDecimal: -

-
-
+
-
-
-
*
-

Both operands must be BigDecimal. The result is computed with infinite -precision. -

-
%
-

Both operands must be BigDecimal. The result is computed with infinite -precision. A range error is throws in case of division by zero. -

-
-
/
-

Both operands must be BigDecimal. A range error is throws in case of -division by zero or if the result cannot be represented with infinite -precision (use BigDecimal.div to specify the rounding). -

-
-
**
-

Both operands must be BigDecimal. The exponent must be a positive -integer. The result is computed with infinite precision. -

-
-
===
-

When one of the operand is a BigDecimal, return true if both operands -are a BigDecimal and if they are equal. -

-
-
==
-
!=
-
<=
-
>=
-
<
-
>
-
-

Numerical comparison. When one of the operand is not a BigDecimal, it is -converted to BigDecimal by using ToString(). Hence comparisons between -Number and BigDecimal do not use the exact mathematical value of the -Number value. -

-
-
- - -

5.2 BigDecimal literals

- -

BigDecimal literals are decimal floating point numbers with a trailing -m suffix. -

- -

5.3 Builtin Object changes

- - -

5.3.1 The BigDecimal function.

- -

It returns 0m if no parameter is provided. Otherwise the first -parameter is converted to a bigdecimal by using ToString(). Hence -Number values are not converted to their exact numerical value as -BigDecimal. -

- -

5.3.2 Properties of the BigDecimal object

- -
-
add(a, b[, e])
-
sub(a, b[, e])
-
mul(a, b[, e])
-
div(a, b[, e])
-
mod(a, b[, e])
-
sqrt(a, e)
-
round(a, e)
-

Perform the specified floating point operation and round the floating -point result according to the rounding object e. If the -rounding object is not present, the operation is executed with -infinite precision. -

-

For div, a RangeError exception is thrown in case of -division by zero or if the result cannot be represented with infinite -precision if no rounding object is present. -

-

For sqrt, a range error is thrown if a is less than -zero. -

-

The rounding object must contain the following properties: -roundingMode is a string specifying the rounding mode -("floor", "ceiling", "down", "up", -"half-even", "half-up"). Either -maximumSignificantDigits or maximumFractionDigits must -be present to specify respectively the number of significant digits -(must be >= 1) or the number of digits after the decimal point (must -be >= 0). -

-
-
- - -

5.3.3 Properties of the BigDecimal.prototype object

- -
-
valueOf()
-

Return the bigdecimal primitive value corresponding to this. -

-
-
toString()
-

Convert this to a string with infinite precision in base 10. -

-
-
toPrecision(p, rnd_mode = "half-up")
-
toFixed(p, rnd_mode = "half-up")
-
toExponential(p, rnd_mode = "half-up")
-

Convert the BigDecimal this to string with the specified -precision p. There is no limit on the accepted precision -p. The rounding mode can be optionally -specified. toPrecision outputs either in decimal fixed notation -or in decimal exponential notation with a p digits of -precision. toExponential outputs in decimal exponential -notation with p digits after the decimal point. toFixed -outputs in decimal notation with p digits after the decimal -point. -

-
-
- - -

6 Math mode

- -

A new math mode is enabled with the "use math" -directive. It propagates the same way as the strict mode. It is -designed so that arbitrarily large integers and floating point numbers -are available by default. In order to minimize the number of changes -in the Javascript semantics, integers are represented either as Number -or BigInt depending on their magnitude. Floating point numbers are -always represented as BigFloat. -

-

The following changes are made to the Javascript semantics: -

- - -
-
-

Footnotes

- -

(1)

-

The -rationale is that the rounding mode changes must always be -explicit.

-

(2)

-

The rationale is to avoid side effects for the built-in -operators.

-

(3)

-

Base 10 floating point literals cannot usually be -exactly represented as base 2 floating point number. In order to -ensure that the literal is represented accurately with the current -precision, it must be evaluated at runtime.

-

(4)

-

Could be removed in case a deterministic behavior for floating point operations is required.

-
-
- - - - - diff --git a/doc/jsbignum.pdf b/doc/jsbignum.pdf deleted file mode 100644 index 442a8c04d7e527dbb778a81f9d72795be4523313..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 153057 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 WEGl|m&il*_-WRWef`y~y(Z2!Yw+My+ diff --git a/doc/quickjs.html b/doc/quickjs.html deleted file mode 100644 index e8b3369..0000000 --- a/doc/quickjs.html +++ /dev/null @@ -1,1369 +0,0 @@ - - - - -QuickJS Javascript Engine - - - - - - - - - - - - - - - -

QuickJS Javascript Engine

- - -

Table of Contents

- - - - - -

1 Introduction

- -

QuickJS is a small and embeddable Javascript engine. It supports the -ES2020 specification -1 -including modules, asynchronous generators, proxies and BigInt. -

-

It supports mathematical extensions such as big decimal float float -numbers (BigDecimal), big binary floating point numbers (BigFloat), -and operator overloading. -

- -

1.1 Main Features

- -
    -
  • Small and easily embeddable: just a few C files, no external dependency, 210 KiB of x86 code for a simple “hello world” program. - -
  • Fast interpreter with very low startup time: runs the 69000 tests of the ECMAScript Test Suite2 in about 95 seconds on a single core of a desktop PC. The complete life cycle of a runtime instance completes in less than 300 microseconds. - -
  • Almost complete ES2020 support including modules, asynchronous -generators and full Annex B support (legacy web compatibility). Many -features from the upcoming ES2021 specification -3 are also supported. - -
  • Passes nearly 100% of the ECMAScript Test Suite tests when selecting the ES2020 features. - -
  • Compile Javascript sources to executables with no external dependency. - -
  • Garbage collection using reference counting (to reduce memory usage and have deterministic behavior) with cycle removal. - -
  • Mathematical extensions: BigDecimal, BigFloat, operator overloading, bigint mode, math mode. - -
  • Command line interpreter with contextual colorization and completion implemented in Javascript. - -
  • Small built-in standard library with C library wrappers. - -
- - -

2 Usage

- - -

2.1 Installation

- -

A Makefile is provided to compile the engine on Linux or MacOS/X. A -preliminary Windows support is available thru cross compilation on a -Linux host with the MingGW tools. -

-

Edit the top of the Makefile if you wish to select specific -options then run make. -

-

You can type make install as root if you wish to install the binaries and support files to -/usr/local (this is not necessary to use QuickJS). -

- -

2.2 Quick start

- -

qjs is the command line interpreter (Read-Eval-Print Loop). You can pass -Javascript files and/or expressions as arguments to execute them: -

-
-
./qjs examples/hello.js
-
- -

qjsc is the command line compiler: -

-
-
./qjsc -o hello examples/hello.js
-./hello
-
- -

generates a hello executable with no external dependency. -

- -

2.3 Command line options

- - -

2.3.1 qjs interpreter

- -
usage: qjs [options] [file [args]]
-
-

Options are: -

-
-h
-
--help
-

List options. -

-
-
-e EXPR
-
--eval EXPR
-

Evaluate EXPR. -

-
-
-i
-
--interactive
-

Go to interactive mode (it is not the default when files are provided on the command line). -

-
-
-m
-
--module
-

Load as ES6 module (default=autodetect). A module is autodetected if -the filename extension is .mjs or if the first keyword of the -source is import. -

-
-
--script
-

Load as ES6 script (default=autodetect). -

-
-
--bignum
-

Enable the bignum extensions: BigDecimal object, BigFloat object and -the "use math" directive. -

-
-
-I file
-
--include file
-

Include an additional file. -

-
-
- -

Advanced options are: -

-
-
--std
-

Make the std and os modules available to the loaded -script even if it is not a module. -

-
-
-d
-
--dump
-

Dump the memory usage stats. -

-
-
-q
-
--quit
-

just instantiate the interpreter and quit. -

-
-
- - -

2.3.2 qjsc compiler

- -
usage: qjsc [options] [files]
-
-

Options are: -

-
-c
-

Only output bytecode in a C file. The default is to output an executable file. -

-
-e
-

Output main() and bytecode in a C file. The default is to output an -executable file. -

-
-o output
-

Set the output filename (default = out.c or a.out). -

-
-
-N cname
-

Set the C name of the generated data. -

-
-
-m
-

Compile as Javascript module (default=autodetect). -

-
-
-D module_name
-

Compile a dynamically loaded module and its dependencies. This option -is needed when your code uses the import keyword or the -os.Worker constructor because the compiler cannot statically -find the name of the dynamically loaded modules. -

-
-
-M module_name[,cname]
-

Add initialization code for an external C module. See the -c_module example. -

-
-
-x
-

Byte swapped output (only used for cross compilation). -

-
-
-flto
-

Use link time optimization. The compilation is slower but the -executable is smaller and faster. This option is automatically set -when the -fno-x options are used. -

-
-
-fno-[eval|string-normalize|regexp|json|proxy|map|typedarray|promise|bigint]
-

Disable selected language features to produce a smaller executable file. -

-
-
-fbignum
-

Enable the bignum extensions: BigDecimal object, BigFloat object and -the "use math" directive. -

-
-
- - -

2.4 qjscalc application

- -

The qjscalc application is a superset of the qjs -command line interpreter implementing a Javascript calculator with -arbitrarily large integer and floating point numbers, fractions, -complex numbers, polynomials and matrices. The source code is in -qjscalc.js. More documentation and a web version are available at -http://numcalc.com. -

- -

2.5 Built-in tests

- -

Run make test to run the few built-in tests included in the -QuickJS archive. -

- -

2.6 Test262 (ECMAScript Test Suite)

- -

A test262 runner is included in the QuickJS archive. The test262 tests -can be installed in the QuickJS source directory with: -

-
-
git clone https://github.com/tc39/test262.git test262
-cd test262
-patch -p1 < ../tests/test262.patch
-cd ..
-
- -

The patch adds the implementation specific harness functions -and optimizes the inefficient RegExp character classes and Unicode -property escapes tests (the tests themselves are not modified, only a -slow string initialization function is optimized). -

-

The tests can be run with -

-
make test2
-
- -

The configuration files test262.conf -(resp. test262o.conf for the old ES5.1 tests4)) -contain the options to run the various tests. Tests can be excluded -based on features or filename. -

-

The file test262_errors.txt contains the current list of -errors. The runner displays a message when a new error appears or when -an existing error is corrected or modified. Use the -u option -to update the current list of errors (or make test2-update). -

-

The file test262_report.txt contains the logs of all the -tests. It is useful to have a clearer analysis of a particular -error. In case of crash, the last line corresponds to the failing -test. -

-

Use the syntax ./run-test262 -c test262.conf -f filename.js to -run a single test. Use the syntax ./run-test262 -c test262.conf -N to start testing at test number N. -

-

For more information, run ./run-test262 to see the command line -options of the test262 runner. -

-

run-test262 accepts the -N option to be invoked from -test262-harness5 -thru eshost. Unless you want to compare QuickJS with other -engines under the same conditions, we do not recommend to run the -tests this way as it is much slower (typically half an hour instead of -about 100 seconds). -

- -

3 Specifications

- - -

3.1 Language support

- - -

3.1.1 ES2020 support

- -

The ES2020 specification is almost fully supported including the Annex -B (legacy web compatibility) and the Unicode related features. -

-

The following features are not supported yet: -

-
    -
  • Tail calls6 - -
- - -

3.1.2 ECMA402

- -

ECMA402 (Internationalization API) is not supported. -

- -

3.1.3 Extensions

- -
    -
  • The directive "use strip" indicates that the debug information (including the source code of the functions) should not be retained to save memory. As "use strict", the directive can be global to a script or local to a function. - -
  • The first line of a script beginning with #! is ignored. - -
- - -

3.1.4 Mathematical extensions

- -

The mathematical extensions are fully backward compatible with -standard Javascript. See jsbignum.pdf for more information. -

-
    -
  • BigDecimal support: arbitrary large floating point numbers in base 10. - -
  • BigFloat support: arbitrary large floating point numbers in base 2. - -
  • Operator overloading. - -
  • The directive "use bigint" enables the bigint mode where integers are BigInt by default. - -
  • The directive "use math" enables the math mode where the division and power operators on integers produce fractions. Floating point literals are BigFloat by default and integers are BigInt by default. - -
- - -

3.2 Modules

- -

ES6 modules are fully supported. The default name resolution is the -following: -

-
    -
  • Module names with a leading . or .. are relative -to the current module path. - -
  • Module names without a leading . or .. are system -modules, such as std or os. - -
  • Module names ending with .so are native modules using the -QuickJS C API. - -
- - -

3.3 Standard library

- -

The standard library is included by default in the command line -interpreter. It contains the two modules std and os and -a few global objects. -

- -

3.3.1 Global objects

- -
-
scriptArgs
-

Provides the command line arguments. The first argument is the script name. -

-
print(...args)
-

Print the arguments separated by spaces and a trailing newline. -

-
console.log(...args)
-

Same as print(). -

-
-
- - -

3.3.2 std module

- -

The std module provides wrappers to the libc stdlib.h -and stdio.h and a few other utilities. -

-

Available exports: -

-
-
exit(n)
-

Exit the process. -

-
-
evalScript(str, options = undefined)
-

Evaluate the string str as a script (global -eval). options is an optional object containing the following -optional properties: -

-
-
backtrace_barrier
-

Boolean (default = false). If true, error backtraces do not list the - stack frames below the evalScript. -

-
- -
-
loadScript(filename)
-

Evaluate the file filename as a script (global eval). -

-
-
loadFile(filename)
-

Load the file filename and return it as a string assuming UTF-8 -encoding. Return null in case of I/O error. -

-
-
open(filename, flags, errorObj = undefined)
-

Open a file (wrapper to the libc fopen()). Return the FILE -object or null in case of I/O error. If errorObj is not -undefined, set its errno property to the error code or to 0 if -no error occured. -

-
-
popen(command, flags, errorObj = undefined)
-

Open a process by creating a pipe (wrapper to the libc -popen()). Return the FILE -object or null in case of I/O error. If errorObj is not -undefined, set its errno property to the error code or to 0 if -no error occured. -

-
-
fdopen(fd, flags, errorObj = undefined)
-

Open a file from a file handle (wrapper to the libc -fdopen()). Return the FILE -object or null in case of I/O error. If errorObj is not -undefined, set its errno property to the error code or to 0 if -no error occured. -

-
-
tmpfile(errorObj = undefined)
-

Open a temporary file. Return the FILE -object or null in case of I/O error. If errorObj is not -undefined, set its errno property to the error code or to 0 if -no error occured. -

-
-
puts(str)
-

Equivalent to std.out.puts(str). -

-
-
printf(fmt, ...args)
-

Equivalent to std.out.printf(fmt, ...args). -

-
-
sprintf(fmt, ...args)
-

Equivalent to the libc sprintf(). -

-
-
in
-
out
-
err
-

Wrappers to the libc file stdin, stdout, stderr. -

-
-
SEEK_SET
-
SEEK_CUR
-
SEEK_END
-

Constants for seek(). -

-
-
Error
-
-

Enumeration object containing the integer value of common errors -(additional error codes may be defined): -

-
-
EINVAL
-
EIO
-
EACCES
-
EEXIST
-
ENOSPC
-
ENOSYS
-
EBUSY
-
ENOENT
-
EPERM
-
EPIPE
-
- -
-
strerror(errno)
-

Return a string that describes the error errno. -

-
-
gc()
-

Manually invoke the cycle removal algorithm. The cycle removal -algorithm is automatically started when needed, so this function is -useful in case of specific memory constraints or for testing. -

-
-
getenv(name)
-

Return the value of the environment variable name or -undefined if it is not defined. -

-
-
urlGet(url, options = undefined)
-
-

Download url using the curl command line -utility. options is an optional object containing the following -optional properties: -

-
-
binary
-

Boolean (default = false). If true, the response is an ArrayBuffer - instead of a string. When a string is returned, the data is assumed - to be UTF-8 encoded. -

-
-
full
-
-

Boolean (default = false). If true, return the an object contains - the properties response (response content), - responseHeaders (headers separated by CRLF), status - (status code). response is null is case of protocol or - network error. If full is false, only the response is - returned if the status is between 200 and 299. Otherwise null - is returned. -

-
-
- -
-
parseExtJSON(str)
-
-

Parse str using a superset of JSON.parse. The - following extensions are accepted: -

-
    -
  • Single line and multiline comments -
  • unquoted properties (ASCII-only Javascript identifiers) -
  • trailing comma in array and object definitions -
  • single quoted strings -
  • \f and \v are accepted as space characters -
  • leading plus in numbers -
  • octal (0o prefix) and hexadecimal (0x prefix) numbers -
-
-
- -

FILE prototype: -

-
-
close()
-

Close the file. Return 0 if OK or -errno in case of I/O error. -

-
puts(str)
-

Outputs the string with the UTF-8 encoding. -

-
printf(fmt, ...args)
-

Formatted printf. -

-

The same formats as the standard C library printf are -supported. Integer format types (e.g. %d) truncate the Numbers -or BigInts to 32 bits. Use the l modifier (e.g. %ld) to -truncate to 64 bits. -

-
-
flush()
-

Flush the buffered file. -

-
seek(offset, whence)
-

Seek to a give file position (whence is -std.SEEK_*). offset can be a number or a bigint. Return -0 if OK or -errno in case of I/O error. -

-
tell()
-

Return the current file position. -

-
tello()
-

Return the current file position as a bigint. -

-
eof()
-

Return true if end of file. -

-
fileno()
-

Return the associated OS handle. -

-
error()
-

Return true if there was an error. -

-
clearerr()
-

Clear the error indication. -

-
-
read(buffer, position, length)
-

Read length bytes from the file to the ArrayBuffer buffer at byte -position position (wrapper to the libc fread). -

-
-
write(buffer, position, length)
-

Write length bytes to the file from the ArrayBuffer buffer at byte -position position (wrapper to the libc fread). -

-
-
getline()
-

Return the next line from the file, assuming UTF-8 encoding, excluding -the trailing line feed. -

-
-
readAsString(max_size = undefined)
-

Read max_size bytes from the file and return them as a string -assuming UTF-8 encoding. If max_size is not present, the file -is read up its end. -

-
-
getByte()
-

Return the next byte from the file. Return -1 if the end of file is reached. -

-
-
putByte(c)
-

Write one byte to the file. -

-
- - -

3.3.3 os module

- -

The os module provides Operating System specific functions: -

-
    -
  • low level file access -
  • signals -
  • timers -
  • asynchronous I/O -
  • workers (threads) -
- -

The OS functions usually return 0 if OK or an OS specific negative -error code. -

-

Available exports: -

-
-
open(filename, flags, mode = 0o666)
-

Open a file. Return a handle or < 0 if error. -

-
-
O_RDONLY
-
O_WRONLY
-
O_RDWR
-
O_APPEND
-
O_CREAT
-
O_EXCL
-
O_TRUNC
-

POSIX open flags. -

-
-
O_TEXT
-

(Windows specific). Open the file in text mode. The default is binary mode. -

-
-
close(fd)
-

Close the file handle fd. -

-
-
seek(fd, offset, whence)
-

Seek in the file. Use std.SEEK_* for -whence. offset is either a number or a bigint. If -offset is a bigint, a bigint is returned too. -

-
-
read(fd, buffer, offset, length)
-

Read length bytes from the file handle fd to the -ArrayBuffer buffer at byte position offset. -Return the number of read bytes or < 0 if error. -

-
-
write(fd, buffer, offset, length)
-

Write length bytes to the file handle fd from the -ArrayBuffer buffer at byte position offset. -Return the number of written bytes or < 0 if error. -

-
-
isatty(fd)
-

Return true is fd is a TTY (terminal) handle. -

-
-
ttyGetWinSize(fd)
-

Return the TTY size as [width, height] or null if not available. -

-
-
ttySetRaw(fd)
-

Set the TTY in raw mode. -

-
-
remove(filename)
-

Remove a file. Return 0 if OK or -errno. -

-
-
rename(oldname, newname)
-

Rename a file. Return 0 if OK or -errno. -

-
-
realpath(path)
-

Return [str, err] where str is the canonicalized absolute -pathname of path and err the error code. -

-
-
getcwd()
-

Return [str, err] where str is the current working directory -and err the error code. -

-
-
chdir(path)
-

Change the current directory. Return 0 if OK or -errno. -

-
-
mkdir(path, mode = 0o777)
-

Create a directory at path. Return 0 if OK or -errno. -

-
-
stat(path)
-
lstat(path)
-
-

Return [obj, err] where obj is an object containing the -file status of path. err is the error code. The -following fields are defined in obj: dev, ino, mode, nlink, -uid, gid, rdev, size, blocks, atime, mtime, ctime. The times are -specified in milliseconds since 1970. lstat() is the same as -stat() excepts that it returns information about the link -itself. -

-
-
S_IFMT
-
S_IFIFO
-
S_IFCHR
-
S_IFDIR
-
S_IFBLK
-
S_IFREG
-
S_IFSOCK
-
S_IFLNK
-
S_ISGID
-
S_ISUID
-

Constants to interpret the mode property returned by -stat(). They have the same value as in the C system header -sys/stat.h. -

-
-
utimes(path, atime, mtime)
-

Change the access and modification times of the file path. The -times are specified in milliseconds since 1970. Return 0 if OK or -errno. -

-
-
symlink(target, linkpath)
-

Create a link at linkpath containing the string target. Return 0 if OK or -errno. -

-
-
readlink(path)
-

Return [str, err] where str is the link target and err -the error code. -

-
-
readdir(path)
-

Return [array, err] where array is an array of strings -containing the filenames of the directory path. err is -the error code. -

-
-
setReadHandler(fd, func)
-

Add a read handler to the file handle fd. func is called -each time there is data pending for fd. A single read handler -per file handle is supported. Use func = null to remove the -handler. -

-
-
setWriteHandler(fd, func)
-

Add a write handler to the file handle fd. func is -called each time data can be written to fd. A single write -handler per file handle is supported. Use func = null to remove -the handler. -

-
-
signal(signal, func)
-

Call the function func when the signal signal -happens. Only a single handler per signal number is supported. Use -null to set the default handler or undefined to ignore -the signal. Signal handlers can only be defined in the main thread. -

-
-
SIGINT
-
SIGABRT
-
SIGFPE
-
SIGILL
-
SIGSEGV
-
SIGTERM
-

POSIX signal numbers. -

-
-
kill(pid, sig)
-

Send the signal sig to the process pid. -

-
-
exec(args[, options])
-

Execute a process with the arguments args. options is an -object containing optional parameters: -

-
-
block
-

Boolean (default = true). If true, wait until the process is - terminated. In this case, exec return the exit code if positive - or the negated signal number if the process was interrupted by a - signal. If false, do not block and return the process id of the child. -

-
-
usePath
-

Boolean (default = true). If true, the file is searched in the - PATH environment variable. -

-
-
file
-

String (default = args[0]). Set the file to be executed. -

-
-
cwd
-

String. If present, set the working directory of the new process. -

-
-
stdin
-
stdout
-
stderr
-

If present, set the handle in the child for stdin, stdout or stderr. -

-
-
env
-

Object. If present, set the process environment from the object - key-value pairs. Otherwise use the same environment as the current - process. -

-
-
uid
-

Integer. If present, the process uid with setuid. -

-
-
gid
-

Integer. If present, the process gid with setgid. -

-
-
- -
-
waitpid(pid, options)
-

waitpid Unix system call. Return the array [ret, -status]. ret contains -errno in case of error. -

-
-
WNOHANG
-

Constant for the options argument of waitpid. -

-
-
dup(fd)
-

dup Unix system call. -

-
-
dup2(oldfd, newfd)
-

dup2 Unix system call. -

-
-
pipe()
-

pipe Unix system call. Return two handles as [read_fd, -write_fd] or null in case of error. -

-
-
sleep(delay_ms)
-

Sleep during delay_ms milliseconds. -

-
-
setTimeout(func, delay)
-

Call the function func after delay ms. Return a handle -to the timer. -

-
-
clearTimeout(handle)
-

Cancel a timer. -

-
-
platform
-

Return a string representing the platform: "linux", "darwin", -"win32" or "js". -

-
-
Worker(module_filename)
-

Constructor to create a new thread (worker) with an API close to the -WebWorkers. module_filename is a string specifying the -module filename which is executed in the newly created thread. As for -dynamically imported module, it is relative to the current script or -module path. Threads normally don’t share any data and communicate -between each other with messages. Nested workers are not supported. An -example is available in tests/test_worker.js. -

-

The worker class has the following static properties: -

-
-
parent
-

In the created worker, Worker.parent represents the parent - worker and is used to send or receive messages. -

-
- -

The worker instances have the following properties: -

-
-
postMessage(msg)
-
-

Send a message to the corresponding worker. msg is cloned in - the destination worker using an algorithm similar to the HTML - structured clone algorithm. SharedArrayBuffer are shared - between workers. -

-

Current limitations: Map and Set are not supported - yet. -

-
-
onmessage
-
-

Getter and setter. Set a function which is called each time a - message is received. The function is called with a single - argument. It is an object with a data property containing the - received message. The thread is not terminated if there is at least - one non null onmessage handler. -

-
-
- -
-
- - -

3.4 QuickJS C API

- -

The C API was designed to be simple and efficient. The C API is -defined in the header quickjs.h. -

- -

3.4.1 Runtime and contexts

- -

JSRuntime represents a Javascript runtime corresponding to an -object heap. Several runtimes can exist at the same time but they -cannot exchange objects. Inside a given runtime, no multi-threading is -supported. -

-

JSContext represents a Javascript context (or Realm). Each -JSContext has its own global objects and system objects. There can be -several JSContexts per JSRuntime and they can share objects, similar -to frames of the same origin sharing Javascript objects in a -web browser. -

- -

3.4.2 JSValue

- -

JSValue represents a Javascript value which can be a primitive -type or an object. Reference counting is used, so it is important to -explicitly duplicate (JS_DupValue(), increment the reference -count) or free (JS_FreeValue(), decrement the reference count) -JSValues. -

- -

3.4.3 C functions

- -

C functions can be created with -JS_NewCFunction(). JS_SetPropertyFunctionList() is a -shortcut to easily add functions, setters and getters properties to a -given object. -

-

Unlike other embedded Javascript engines, there is no implicit stack, -so C functions get their parameters as normal C parameters. As a -general rule, C functions take constant JSValues as parameters -(so they don’t need to free them) and return a newly allocated (=live) -JSValue. -

- -

3.4.4 Exceptions

- -

Exceptions: most C functions can return a Javascript exception. It -must be explicitly tested and handled by the C code. The specific -JSValue JS_EXCEPTION indicates that an exception -occurred. The actual exception object is stored in the -JSContext and can be retrieved with JS_GetException(). -

- -

3.4.5 Script evaluation

- -

Use JS_Eval() to evaluate a script or module source. -

-

If the script or module was compiled to bytecode with qjsc, it -can be evaluated by calling js_std_eval_binary(). The advantage -is that no compilation is needed so it is faster and smaller because -the compiler can be removed from the executable if no eval is -required. -

-

Note: the bytecode format is linked to a given QuickJS -version. Moreover, no security check is done before its -execution. Hence the bytecode should not be loaded from untrusted -sources. That’s why there is no option to output the bytecode to a -binary file in qjsc. -

- -

3.4.6 JS Classes

- -

C opaque data can be attached to a Javascript object. The type of the -C opaque data is determined with the class ID (JSClassID) of -the object. Hence the first step is to register a new class ID and JS -class (JS_NewClassID(), JS_NewClass()). Then you can -create objects of this class with JS_NewObjectClass() and get or -set the C opaque point with -JS_GetOpaque()/JS_SetOpaque(). -

-

When defining a new JS class, it is possible to declare a finalizer -which is called when the object is destroyed. A gc_mark method -can be provided so that the cycle removal algorithm can find the other -objects referenced by this object. Other methods are available to -define exotic object behaviors. -

-

The Class ID are globally allocated (i.e. for all runtimes). The -JSClass are allocated per JSRuntime. JS_SetClassProto() -is used to define a prototype for a given class in a given -JSContext. JS_NewObjectClass() sets this prototype in the -created object. -

-

Examples are available in quickjs-libc.c. -

- -

3.4.7 C Modules

- -

Native ES6 modules are supported and can be dynamically or statically -linked. Look at the test_bjson and bjson.so -examples. The standard library quickjs-libc.c is also a good example -of a native module. -

- -

3.4.8 Memory handling

- -

Use JS_SetMemoryLimit() to set a global memory allocation limit -to a given JSRuntime. -

-

Custom memory allocation functions can be provided with -JS_NewRuntime2(). -

-

The maximum system stack size can be set with JS_SetMaxStackSize(). -

- -

3.4.9 Execution timeout and interrupts

- -

Use JS_SetInterruptHandler() to set a callback which is -regularly called by the engine when it is executing code. This -callback can be used to implement an execution timeout. -

-

It is used by the command line interpreter to implement a -Ctrl-C handler. -

- -

4 Internals

- - -

4.1 Bytecode

- -

The compiler generates bytecode directly with no intermediate -representation such as a parse tree, hence it is very fast. Several -optimizations passes are done over the generated bytecode. -

-

A stack-based bytecode was chosen because it is simple and generates -compact code. -

-

For each function, the maximum stack size is computed at compile time so that -no runtime stack overflow tests are needed. -

-

A separate compressed line number table is maintained for the debug -information. -

-

Access to closure variables is optimized and is almost as fast as local -variables. -

-

Direct eval in strict mode is optimized. -

- -

4.2 Executable generation

- - -

4.2.1 qjsc compiler

- -

The qjsc compiler generates C sources from Javascript files. By -default the C sources are compiled with the system compiler -(gcc or clang). -

-

The generated C source contains the bytecode of the compiled functions -or modules. If a full complete executable is needed, it also -contains a main() function with the necessary C code to initialize the -Javascript engine and to load and execute the compiled functions and -modules. -

-

Javascript code can be mixed with C modules. -

-

In order to have smaller executables, specific Javascript features can -be disabled, in particular eval or the regular expressions. The -code removal relies on the Link Time Optimization of the system -compiler. -

- -

4.2.2 Binary JSON

- -

qjsc works by compiling scripts or modules and then serializing -them to a binary format. A subset of this format (without functions or -modules) can be used as binary JSON. The example test_bjson.js -shows how to use it. -

-

Warning: the binary JSON format may change without notice, so it -should not be used to store persistent data. The test_bjson.js -example is only used to test the binary object format functions. -

- -

4.3 Runtime

- - -

4.3.1 Strings

- -

Strings are stored either as an 8 bit or a 16 bit array of -characters. Hence random access to characters is always fast. -

-

The C API provides functions to convert Javascript Strings to C UTF-8 encoded -strings. The most common case where the Javascript string contains -only ASCII characters involves no copying. -

- -

4.3.2 Objects

- -

The object shapes (object prototype, property names and flags) are shared -between objects to save memory. -

-

Arrays with no holes (except at the end of the array) are optimized. -

-

TypedArray accesses are optimized. -

- -

4.3.3 Atoms

- -

Object property names and some strings are stored as Atoms (unique -strings) to save memory and allow fast comparison. Atoms are -represented as a 32 bit integer. Half of the atom range is reserved for -immediate integer literals from 0 to 2^{31}-1. -

- -

4.3.4 Numbers

- -

Numbers are represented either as 32-bit signed integers or 64-bit IEEE-754 -floating point values. Most operations have fast paths for the 32-bit -integer case. -

- -

4.3.5 Garbage collection

- -

Reference counting is used to free objects automatically and -deterministically. A separate cycle removal pass is done when the allocated -memory becomes too large. The cycle removal algorithm only uses the -reference counts and the object content, so no explicit garbage -collection roots need to be manipulated in the C code. -

- -

4.3.6 JSValue

- -

It is a Javascript value which can be a primitive type (such as -Number, String, ...) or an Object. NaN boxing is used in the 32-bit version -to store 64-bit floating point numbers. The representation is -optimized so that 32-bit integers and reference counted values can be -efficiently tested. -

-

In 64-bit code, JSValue are 128-bit large and no NaN boxing is used. The -rationale is that in 64-bit code memory usage is less critical. -

-

In both cases (32 or 64 bits), JSValue exactly fits two CPU registers, -so it can be efficiently returned by C functions. -

- -

4.3.7 Function call

- -

The engine is optimized so that function calls are fast. The system -stack holds the Javascript parameters and local variables. -

- -

4.4 RegExp

- -

A specific regular expression engine was developed. It is both small -and efficient and supports all the ES2020 features including the -Unicode properties. As the Javascript compiler, it directly generates -bytecode without a parse tree. -

-

Backtracking with an explicit stack is used so that there is no -recursion on the system stack. Simple quantifiers are specifically -optimized to avoid recursions. -

-

Infinite recursions coming from quantifiers with empty terms are -avoided. -

-

The full regexp library weights about 15 KiB (x86 code), excluding the -Unicode library. -

- -

4.5 Unicode

- -

A specific Unicode library was developed so that there is no -dependency on an external large Unicode library such as ICU. All the -Unicode tables are compressed while keeping a reasonable access -speed. -

-

The library supports case conversion, Unicode normalization, Unicode -script queries, Unicode general category queries and all Unicode -binary properties. -

-

The full Unicode library weights about 45 KiB (x86 code). -

- -

4.6 BigInt, BigFloat, BigDecimal

- -

BigInt, BigFloat and BigDecimal are implemented with the libbf -library7. It weights about 90 -KiB (x86 code) and provides arbitrary precision IEEE 754 floating -point operations and transcendental functions with exact rounding. -

- -

5 License

- -

QuickJS is released under the MIT license. -

-

Unless otherwise specified, the QuickJS sources are copyright Fabrice -Bellard and Charlie Gordon. -

-
-
-

Footnotes

- -

(1)

-

https://tc39.es/ecma262/

-

(2)

-

https://github.com/tc39/test262

-

(3)

-

https://tc39.github.io/ecma262/

-

(4)

-

The old -ES5.1 tests can be extracted with git clone --single-branch ---branch es5-tests https://github.com/tc39/test262.git test262o

-

(5)

-

https://github.com/bterlson/test262-harness

-

(6)

-

We believe the current specification of tails calls is too complicated and presents limited practical interests.

-

(7)

-

https://bellard.org/libbf

-
-
- - - - - diff --git a/doc/quickjs.pdf b/doc/quickjs.pdf deleted file mode 100644 index 497964bc890c3963eb3ae986b30d3d05c4541fbf..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 165855 zcmbTdb8s);+U6bGww>(Q*s*Qfwr$&XvSZt}?H%(QoAY~So|>AebE@XNZ~wKbtGc^t z^{4x~?)zGcTtP(a7ZW`j4Eg->$T|!Y5hIbkkrfOtFARf>shzot1rZx32hsmJU>L+K zZCp&9h#16d3|&k`OpWbLOksZihH-XrGBvb?@z}Igk&Q1BKpk<9ea{V+bL4=hqp_-F2d+2!b)kGDNKe^+Bsf+= zjL01*KLUuGmqBMF1fKI?uska=5yG(p!04fQDl5OLU(u5Dc}Gb$8Nt67twSEKMA@T1 zSx z3)TT4VuL9vSkf>eidqr|YpJujEyPoF|BMMVOZN03x3h!5nA(~AH&y?P z{)tqjCXSE1#%*3`X;t3J$E&EST6{1 zqM00RMF&8zd5a_rjn^0p99`{YiQQjTJl>k=W0TP&Oy4fiwrf6##hCWpmQGt}$C7Xp ziN>vKoxinJFc-7uMD613NY}PLzKup+I}$$@ud7;xl&jZ8)s9cdM zDEsx8;8aM9Ws8OkFog)lS9Gbw#XY5w*T2mCpJQ1{Ht=X9hdiKp4Rb&~uGB#wV=6Ke z{z0>R8nWMp9qLvXkN*Js;0SpvVu{kXPSf|aK$%xI7y}(%H5*Bz3F8~>i6|Y_;Nl-N z3kh6;ext{G2O3r;yn)}QI7}>b<(IEWeJspTL$8zOMy)gi~vpVC~^1-HFwPI#&IO{t~(^z>J7!ILPZH zJPYqQO8haLTe2n828xLnfAek9XuZ_FCc==S2fHh&xcNa^TZN<$=_dQNG(A<4W7))A2Ykd!0@3>!+T7Om(B^Uh2B6_Mk- zeR-Njic<5Ic>FwxJ&olf_dy4_e3ml0 z`&#gITAwu_9qC5%f3Le;i^b^$-OXY)dt-QY(9=Y{;zDY|0`Qe9RK+bFgBhKF-QO|%-v5^-0p9;k{4kWbXI*u z8#ZK+R74`y=j#^%(Qu-RiC<<_6NiAlD9a6RuU3lZBJ+arrBp?d^qfPND zc$R`BIW91NaJf{K)tQe^>^P>VWQL;cxoA$)3G83pSxoRQL1enEXLj#1XI*E}mqZD3V?Yh2lE@^XKG4KED_KtfcYhti&u?%elytFSAZhCEUHOEqOmZ zf48@Q{(2BXk1VmSR`2uJo0_tjq>S0c>B*46Wues^W&==9v^xvuJkVOJ+Kj4W9M zCQjvP;ibfyt&q)7B}%XJN1su&^1Dv&$;xcFxkInD3080F{N(WV-K#0jksGkNZ@Q+x zHJ?JHL$%7GDoYPW?s}|M)C4P)nbV8=yK!ed?d;Kv{|2MAVd&IyWD$Z&HN?^mmz(uA z*H&OEZl^Wv1MA3D8yps(sgtZ#%0|5VY;O=bHUF{$^S0$<-!xIL+{>(mpyIFnKBd4HCgJM<1&6qxp)Yjt4Pw}I7wXC zr+w3D)?s7h>zFgjMm{+%uC1Hnee&hjv9ljC17O0N1c=9&IrAuOp1LV)b`>v%SOazj za(KRb^{35c`G~*IxvcRbUGaynt zO%kNghXZumna59NEmo@>!K!J|uKYMBMx7lzkH1{Fxn&A;P%5KM^A?ZIs9rRPsO1NN zC*w7z6ys9eQic|ri$t^$C1$S3mw}yyAOlLJin%D$+!1g6{hU(>IV^uzxRva}=Ue5^ zHvv1XE&O9P#5Dxy^43b_DZ2Ul=wleGv`l#SlgRa&bws5->H_C~(Mu!uX}m%UyO{~u zq8leC#b-FGx<;I~$%9ZHA|NS8$nz@_SfYbrt<$g&GReu)%x8j9p3Q(uec#B)D_n1* zu$*B~MPPHeOEu%NL~mWnDmuEf=}$HWx>ZWv5A;gWwB!FeIU_hq7~-Q05r>!LoZ$a+ zJpyoPk1!bNB!d?t$qvxrieJMO{U?aX+I8mwap-CYjV2X8KjHEAzQbTAX_)Y}1oli9 zC^cXQSjyX-Q8)x+7k{$j@S>im?J~nCSkSM+0M@EeN%g12QG-0PKi2Z+BeqFSazKSXwVrw%X~$8|d6 z^v6|e9#I8mFP>(;fa z^-XQ+$kUZz`>M%}XUJKULeavcpsvEX=%Bk@(Zukprh#0mMFS|N4VR2Wepc&WGK{B#3D0uih zv*9IOc;m^76Y}BS{$@0~wzrB_dcvIfyC8^)V8hcwcm&BeF(h7dzhq(G!si(XNQuV- zco|^_dQIf@v`~X31bAHjW50RI==fQ!oz%#Pd#~M@vClk=bddWqTKt5(=f{(=%R4@l zD@>TNTmYEyuo-l^z%5`S>>)}#<4fe~W6J*-mn!?%uerS<(-nrc;xmRjI)@xjP(ymy zVH|}zEr8r%a{#5ltscxYWO5i~fB7b1h5vf(fxa!kjE2NDQ^U(HJ==J%FvyfYO!%t& z6Zq<%M|>2tn&)E+S4N3Gi>`|?+23$m;DR5P`grE`PWInu3J&InfZh@UOEiVcCTtS; zY4G&dkuM~Py?$9%KWa#R>}96-YNqgcNmP8oaGNmq8dPwWLo^a?df?RiJ;65P%^z0LpP=1p0#yN0dye zmG<-A-tKSllUU;tLaj|TYrQ(g6#Ntb7H5{r`j!ByFgO5|;P6+UYA`kuV&3mmw`FWt-jRI_u466UG2?ChCRoX2wKbItwySZa^OblGbl8FPXe!GHph z$ngYt6#3pfa#X$UE1F$TzbzaBwg8=)afBbMVN_Cc7t1fGp3A%N?U}m{3`^yGv&{!Yj(79I=wzm71pP>ILgj2d%noTc0Kc09F@WjF3E+ zmMh8rB>W-bM&)jxM#s%S8-*?PDHT5 z_2CKxw26?_60XB6sMOGSpj}8k{nu{!l`}%>Qv!2uRnBUlc$KyLm%*-k^BC%E^1H zOdlSx=-ynWZNe;xE`ipLsg2~{1H}&u0x)h^u+!{=P~GITS>~H7DM4R*f^`b=)J_tovq*JF_L&gNLaQ9fSD&)`dGLKFdegDGv5R`D(rn z@N3?}{)47Y3o--Yai4nnZP(KKb!QsmTpS3=pZq`@`m+h1xj1Z`S~ zMra}kTiOJv8Ix|hTf67V)ph?^>7SDIfT)>m+^T2OI`#c$b7Z$V>)Da(J!1qDC14TYXO16DrZ`aFbGzg*C3C_}vlZWm z51z?;6Y!;o3-{koee--jJaeY^U~`s<=r=N{eO;IucN-)j;u2i=>nv9Orpo~?3#<9k zS5OQ8$`056QSzvGI+zkM$QxNHyV$}o$PqCyGX7Ub*2&q0h?DuB;eYpQnK(FD{?n4E zMRUszmjlUnP5pMklS&l9oRbU*ZG1*F5W>P5(<1v-P_eZ_NmHp5J>k1+)tC z{YK^=2dYj*;&f0gtXy#0VXOx<0|!l+S?qQotAUDnK8orz_l(S_aQr_gx7|bAa56Un zX}}i^j7&o&H-hQtg28J{pwq^&E2&fhKoy6JfzJrb1gudNsEBSA1el z&WtYc->Yi4bq{(mG!2`xxR}Z`NU6CFEOL??p3(6?B8SXQ0)Jd$4iqCiR7QcuI`T+C zNoZoNOVoX`mBl4(oUzuVR2jWpl96GyC!dJORK@M&wvDI8diJ+c|&RI*#SsY1dHN0|Sgm6bo!Bib~;)uX( zgjnOJ&L`5mqe;u>)GT%62Fq!mDsB4x;zi}1!&n^43|d%{>-UBh+;pVK!a8SV247Gi z#~ry6v3s_M={LP_GL!CNmup*5-F!4nb!G$V$Xq{u8HF1o#Sca1s*Xyg;kni3#q-eL z1G^!HAmxwA<$r5i^C7g*vC@}&;p(ctDp)9{ezxZ%Ro`S{PdVs_ecRVO4Gy(D>*N%g zNW~{NkQcJjQ(kmjq7%zcOs*?l4pW>vzAwgEQ=*V6#-nug4QSDx7K-SJ0H_>&C<)S$ z$6n@n0{0)U@7rUP?3&-x`Kdzh!DHrt6&ZfY`o5pL6oVQ!imYm%r;caRcTVLP5ZwVT z91#VG?qB!%z<%SU_MPtMRft`Wsb26jPdF--Oj_cVh<%6E*9v&@Y>%V`I!=>+hzl5V zz1tk4P%94^=_%v>aHhHC97kM;pNOR1_awI;#AF=+ne)!&kx;ZOcQuaM{X+2Bc}jj< ztdptp!^xFvnJZnchz3O8r~}---1zM=FIS3*3)7oME?SJ;H>NkgS~qqut0`lm_1z@a z2HN)O+yFKmIk_jDsPC4289%DyL|wL!BY8FU_U2V>q7EGzY^A#PFt_zi{(XDs4d7A} zZcVng-ukR~qNk#6y}dhhY5B-GzYrUnX3RP=5V71Tzg_w?TKASmY_fH|g*M)Gd)h~} zqg253^}9Wu?2;FG_5F>sWHM@ZQ)}gE$ zj_juj)xKn3N71-#Oi3YAH`dQ@P?+~?e{^py>mM7tLO!*21$KQ#@WO7Jus!{jh|G;= zdYfGv^R4*c#=T!__B40zGu|dY(92q~^lkv)+h+kk{Yt&EPtdQemH2 zw|cU&|EKC%qakg-&5qRjp$-KOV-ZL%8|8J9)-IWV2As6nMh2;MaNW3IEG^lvqrZoZ zP`cA{JW34*iou1K#IncRLGt&OGKdbQQKwPIOmHK|QM_d<0K&hQ4>ivoKIW2iR$blv z)INy}DF?k9X<&syf@Ic1Z~9bMb>LK?x>v7<-`kgsFhvAf+URXqoAMe`-Q1Fh86%Qx zv`R6W$`sGs<&s;{^wo}h(2ZP_bKR~b%$_YR_*^UHy!Vk;L!9d{lz)H8Vp26Fd~a93 zcGZzgXz4ILJgUsM_#!K;vc{qSciXWiC|F2W^`djN`Lst%RP)t0wWRPu+WI+oZ{AL} zYQrk`j@9Qh@~eHXin+gMxnwB}USj$m|F>fT$ zL^O#o^QiazGSU&g9!3wT%5uu9TBZy9u>>xAR#!8&<=US#>EcEUa(ULxmg89>cBsa# zMOE0GvXu`DD8nxH84rO~$J4a+MoR}5YZ5&o1Dz=l(^5NV1CUU1XDVtK=nCp^ji~Re)aa zFbSMmfO|L0iZQ|v%p9OQzl%!ipVU-38hDS0&EZEx7d7VSWK|3i6?)W5*VTR!xuP)3 zdPcIJ-4>wXsp4BY38`58Y6CXLv?OG}Qmk_;sNYj?J7WvZUom6B_f%g+oOOYg6r+nD zp=PvzWo6e0=bdggXl-3S%331-YL+mGz?a8%t1L})Sq&Z;O=*1q;%zJLtW32^tJU{SaU{3|VRu(o78hXt*63l|;i0r2@>*C&Q$Wm(H zzB+o~SJKrlxG0hE8Vn!yH%$%C#Yi%;oDCOxSUiV7JW(f(WFR@2N@->KIG2UMPzRxVHomfYx zo5I21{)}83>xFBLG|f$UxmWziokaF*Fu_dF#GFZvAru7 zf`;-(1xn#s^?YGOQ!dwOCH1k=iqAFPt=filizpI#r!!!F1P@p8EYS-DC#`zdqDq&B zbe4JrS@;?R3H`#time-!*SR7rb>}ob4Bi3(KA}DA3&kXEue75VS2@ECH*41Q{tgUUZRu zAHEnEg8Bd=kM(yU+&R@lN3YxrZ0(kHGkJRI=ZzMThA8+z zMkw0#FayUUWcaowc&bVM@tU8WLv!?=71oK0>>yDe_kNkL#|eR4{PS-c#9Y^J#xC5_ z{&eZAPC^{HIcN9lFvGn*PJTiuO~#%4%SJ^-oZLN3Q8e&zOnact_6SCT}C|?2Peo8t~7!E{az7d_WX?{vit5AaxEa@KylMF z!Y4dfA~NV?%R3Pygz5O8znTQxf#QQM@$W(ESAAsfm<6R*xBo^WS^rI<&BV_5-?8KW zdqGgF#*Y0mCzAh-e!~GZt!}qtukty;-&!IhsM<#`%Cq3?_O3vms}V`*A8#{Ww@zw3 zE!9eVZ{EDQy_obmkk`X1IvrEb;d?6WRDfiGdN?48;%@oR5BZ2W1}wuN_&<3e4E}79!vE&T?wCh53~w-G`gL_Prxzq@LSW zCrdO@Fu~p`{(XiYk|h7S_0$U?M?SVMU)#$>ncbxvoO|KcdiBNq zh81wt*IsOkqqcn4SLi3T?yhaVPZM;{WM;(~tDxPQ!%S4kjdU^+nN5`hm~``--lU^X zUkIM;e2+HB4Rmt@+*!yTDtg7vcuYu`bYTiCDJ_QH;Zje@s-l4F(osc8Rz=X!#pK0^ zit*>hY9==+(sP2?ax+IBBW{^o>02ZaW?2?mdDx_`5(MEKEgELxVevtyJY3SU=9fJj zV>mWyp*l2tS+V7t*@(*|(izPLq@bWklu2?$2<5y@QlSODV8;iE{LSu>LQlhm49wCC z%Pl?O=*<_#jzQKxr6f2Ds?DE7M~0y&>NC9f7jHo9Z~`WYyxEfQ*<}o&$^&TS&Jw=x zNe0^+M@3A}ox37Jl+qPwrT{#S1`cZDasRST5nLbt2V_pi6Ct*}?Xz(3DQ3HdnZJc6 zNTIv#1{vf8Sa8ek7VkiZ-#=w>!^)f=xGj-OIdt);@bJD{R@sL_#e(qWDc{9-Kox)a ze-$~-mj3x<0m>Ohjr}oX3=z3q4H?Nxd3k7WM^y18g`kmp7Q(jNg^KOYDx?Yb;@_Ma z-{JGizd07NTmp&oXCb?fPXd{$g<3VX= zVIovWqio$+E-U@WB}0lvEYwQFm(OZ%ObEs})v6#ECdYtNx4jb{69)bi1~Qr)b$%F` zTcc1^y3&K$QsTT14_4YFNT(me4cAyJ|ra`1@<1ju6Sm6Jfd)1`5*qbBy6&<>Dgy z5*iuabfS=$wJvUH#YS6A=djO7Zz;mN#C?lEqmb1nhN8r7F=CumsLedX$Y9qJx|H%S!`W$IS~5qA z?Yy-#;}KS!ux4U2ds1uT?5*vcZfo<@Yv9?hJlOL6?&D)LA_(w@<^MSI&HsZ-*$9TrY z@-w%(f#mVcb$=H>9+Pb3@X} zG^yGYmj1>e6gpDKDHaKy5%x0L*(uukD12|JC=b)(AV9svazP~Vr(_5>C%>94SiAn{ zAlJfx7Px2CVx8*?kxp^?0`o<}ExYqjvazsXnHk202wNR@q33i56X}JDpd4-RSGDh| z@Rg}-ilZ^aTVJIg=jE*=bogaEomhzUQaIvt9&Osm{tjoM%`iQ-{;kF#e<#(`7D>8?e!)$~TTZz5P55 zn>G|!ny;T6e3iWb-fGIC>LmHhdDQ!xmttC4K}8jQb+}Wcl#G31>gwhfKXA%YaP7Yn zCeDAY-Iy7<{(G&}|67=HHMZim+2MTW)ZyNbz`3J-O|;?_AkLKiLL&OLX|oW{O4ZzI zwyLR5(VDYE{d_2WaWFN!w1F`&YMe~9_NzG0ebjjm6U)i6J59|z5 zFBaIVV0+>vRz&$wpS6f(CK+T3X{26dT}YTu@GNZAR~;tCESA{`vL>MllX_Z}j6~RC zOik^s>AnFpLp~H+nFcBj@A>YgLdNzD3HWvtSr*`Ylx%OTD0O+8ms+-PnA0Z{sw0Qd z!i;-S5OtCS$|xkgUueF=z=Fm>KpA2+k;a2YoZe!Eb&IM2OB%Fm##;Bz1MkI5Qllv_-AW(T#! zgcw*~+e#f!HDOR2hG=b2$(#74f`qRMrJ978Cx|Uy z3RoJ!(UMjomE z+?PRln5dn?sGVDEx_f=As*sXNbehUp>J&MPxEo}fV!rS^CP|fu2 zXTBL)Wpbu1T*|vVR^mqq3D^Lh)XPUag3;L1z`Vftc+mgBk^ZBDGP0nKEAb09@Qt)v z|D>@|ghB@NWu~>Bx#eNmR^-(!N$BS~7sr+HLshmgt6PO{5Y@=ZS)ChNdi$EKZIvo? zDCjcMS)K5D`VUcnI8!fReqR@b4vHj{!teyu!@(>fs-VWuTiB*2@*45jJIOI^_W}RG#sTQj%+OQyC=udCT=_1f?7w&&Mz6egmMX- zE`{7j)o8kn3~ZPwc=2TFrZnSEJVuhy;7A_E8G_st2tsonZJ(u(SDT2Qk4guAAM5tN zhoKhkEtd%xke4otpO?-+;|T5@>d95A*|Ioo z#wx&RrbCxUq9Hxko_i3f)6ydE{13`?!MEK8PWKvGHPIkdH?|KM4DK4;tjEz?rsyfa zsK(^PZf#CdbQw)R)_Sdw>mZsT5bE8mTk+ozfN7(-EWh30UG4V0CPfc#yOa5rks3}l z=4@<6ZKj!UV@w5Zo>2UHZp_oReD<_xYc&KWVw4x%)|xLxfyfWuPE5L6-kEyLY2Z1j zz)Yv4goO#0F*W&sNmFP1wwiTgIhEyeH><{mmdbl=^AL1DJbWsT_azAtD-(1nHGkzASiX1Nm(V#MV=^OMhVzd13rWFQe6e{!;&~9gqS8_FV@-+5Ae9D z&1EleEzQ(u+~>RC8y`U&(^k(9pl8mOq$ke=mvG^q2R24X?@#0n!y#2jVH@+w4B%8V6w6xyu( zf+Td((8pK+nP$G-~8D>R|X zKm|igaMV#pug7_vujb-mq*8i1n^8$*Jq|p}Xdbq4i7QSw!K9S^OnNaZM9yO;|4##L z(Y5iKy|8oKN=QcU^7aQd=5lQsy5H2p!S|su2PEHMdwtur9;UE9;->Lq8;y-rmkJu6X z=k%H42@2Gz5x4FS^t?u%=Rw>Bvagi2@zAuB?`p=fny%~?`+8HT-i$A9@!-5F8OW&T{P=Wt{jkp=vXZK*Eesu6 z{<>)3`b_b0R$Eg<97}P|t9Kt$iQs)RSZVtGegFC;2qnp^8R##&;1oNEI7 zC;3G5ntxpb1Cj;`6Fi!|G03Dtpe6=wjFmy--lN*12rv!<0g>)`@0@0S)A#nWhWIqE zCtd=a>>$JGow2D1itC!T$4$yp(oB*fx%|N9qZDD1!-mF-UDo?@9T>VAw%2=ICdM(o z@VwvDG&+E&tWB6H^V{zy0F3SRt>bIu%K{{OU-UlW)29Y86_Tw5CMiFTnids5bxY9| z-wKl!Af9C~yv(&JSw`_99%2T(tWU4?#9~(n@6*nXOtv?q>VI5 zi}tY{6i!?qxs$1Pc*`57{&D?HusXYhS}}9%SMBLa=q7Pue~{)rU6akwsI#JxpGe!I zg!c*R4|O+rRgL1gCe&&LwE_B%r}_)rcNicPlWw5b6JMUaD8d#y63XP%oNist(CMyI zjHA6oTGb;&1`O=_;VdTFb7?W3Gr>%;tqI@L>NY0^OreC0Ew8N4Bg&4o!eJ5B5eF#! zlC_sD3BVnP(ORx)YLpSXAql`HS5m>1|N4`^*B7uaG+E--ZIE2)J9Aqir+GOHt68We z{x#p$a+ht(s#F^c-9;#NnyyY}tz9L6$SefWE}Fi(dw|P5Pp{^lA*c9+g!W{%4LU=f zaj09DU59jAb_4Q=P7wl#Nq(m;ndEH#Vu{=8#n)bG=^F_E;qbs;to>ca8YvQIIyiw) zYp?Tm$LK6ti(&++mNS<*XM6$*faVKEr4p4+yEZh3-^?h(d{V4KxnKy)6|A>j;tA)I z7hZ2A<(4W3)WT~D(u|VO8RG!$AQ!*-i0z!v3|cFos>0k;T2E? zdoa(EFPM6g-9^5&5Hmz>-l*wmUGDle+Jeg_yqMfJ)i8)4Zh!?6BPtn|U4x>r1)tDZ z&>uL#BzlQ!VYsBRO=^KN-eyli+5*qU|e!mhT@=Z#F(-zSmJ=Z$7-%oN_9HC29IHRq3 z+-%i@XEP`h?!MKMYWDoKkfw9`J1JZitRNJf7jH7uC;RRY+WGA=y*l z+I|@>wuIx-KSaV64upajImH1hJa>;MXe~*y~tBCU@pI(KwqH*T2R&;)XwIBy7fG_t;u2 z%dXn!R8QgZ>9j<5_XYk_;<7{&cWSuFw+xhbtfSk^huh^H-~db>wAZh3ggrsMC-x+~ z$F)QpOVb{~B`;%laLsqks3~WJec$MW)b-Ajmc89gEzzCyN)8%`m+)t&XIwWS4>(b9 zYnh`RZvoZ^V^U9Lk)vj;n)aK-`8kB5MG7bQstvO{fESP?&_!lodOc%S+7EILUAS{= zd=;L!t#$NRnX>gmi=txS7>{AM8`e?Bsq6#dkn*+|Av(VFxwGOPv(_4R$OXk$bsYj% ziHOD$D!;uHrv{%SYcjM($O724vP=tYtjN8&+U{-_@BEo#u%F*i!QRJqWw7J_O2Wq> z3T7On^?W_bq)(WmU+5ef+ChA!X@hXpMA1xvgkCG4+tUeH7fh<80yE-vo?+akY_eLR zSA@Vs_TLXmyyc+B`9qABcYQ;Vck!%4&OQG$b*7J(Ro}Vozkkq76}|}$&NH~z$L46^ zH~5jlgTI6}H}+_$;Ojg3Q=v}3#~Z?PK`1SPgGVlz zmtKX_;HQ-u%24NtAgSxSZ^(9A2HS-Aca%@t(;jeSxh!lh>))q*vbxHoiJUhzm-WK4 zyfClw@65-)39gx$*#18(`;vA(WJmcYxTcy2t&FM%gX%pwk<3XcceA3jwg(VT1d>o= zLleUM)4lNjaw`UoNcp3YxA{vwlL(5nv(Hc1=Xi)vf5Zr#5?DIOBXy0VHxKYki}U#~ zhHJNKYp`$Dc>i@cv*!mjg#My=QSS59t{pmP?w7>*j)2<1r0}NKO!|6cO?E8deT*DT@WZJ7m}c-L8Ieftf$Wi>tErIF1BJr%Ooe z|N6Ef1*HHnY-Nc93we2Y3iIB`@}BXVekNCl7Oo>ilu-Au<-m&spN1rYWBN-jsVqL7 z)FteMIEeXMDG4^^Bm#sSi5VtFC0>3UIKG=l8g!IT0qIUh?7hg#%S?6W88p`2SheTx zd=xPXZ#Ug^8b#fx5SzCa^E#+~cG+ig*vyejLdCUeA^K;c#zk*vVdvmqYPXh+z?Y3Vhzm@9KX#mJ4 zYPNBDw|FCCZasmF#*Z^q_V?MSGdh_8)V@v-EnC6N2&P_PCo|#lDO+dC2Bz$bD3WQ& z&hyhcZq<3X9Dc7JH`F8X=lZpRY+=86%gTV`kaF1H*FX*+)?pDK_CEZVW&yUY)~a8_ zjDb=aUKJEZ&rg8$W3hzdkAmm`*ms$T_1B_-)*VBvD7ZkZV&UXVEX!snaQ%@5d_Wz!uuhD#AIxJPWrUE4medI{9gL(`B4L+k^n zM}W)QuWI>&Vg>P3iabG5pi(kFPI1yX9B#|1M3%AZDz|J^3f>k9HLN(N`HluaYjH=E z!5qusbknaz;Asrdhz7|RB4*F7H!IBJ#!Gm4bc@ikmZEqaJZ$&DYt^L$!GY~2oV+xZ zA?1Po*{g~@pO$gWaR(E?4j6EY{pNMhm_68VC2Q(w9K*yN|0Z3v>tv5sJbEA;bO$dq zOdX|SCYb>Ec%ii=H?w59%OgxK>TU2u7H8Xx6KlzyYwuKN5Qf5_^48@1D%1tTSHMOr zVY=VA!|ACjRAk4TVh+OZ;NShUO4r_q$41+Cr=#!Mec%#fS@=;qN%Kq=G)`HYnh#)z zbQ2IR27$rWv4DWcyCh99;AGy8jP;@^w>LdNU-)1NL_qqs8X{oRlItF!API$WtFmya z6Z248vyEeW=#JP4E@sQc&Z)(U@fz!Jb;7FpuCL)?cC&awV{3X8)4)dYozuXOjDhP| zANEHW9FIPdUYVj$?MrDvTWMXzWxcw*SHa6s@F~cV|0^isF+P}!3AY;1V)EjJ;V|&| zs&edraY zy+Ijvc7GJ98_F$%nIBA%}@|2u-D{W7s~yB|Z?j zFx&Mc3)hNJ!a-t6-S(>w;Na3Se=*vJwO~WP3`Tu87?S?aHm4Ku;^vDIhLl?8(LwuF zE|#eET8L}|YGMdsw-v6{rv_i`*jCdn1TdFEz$^cmI{M?v9mD543r*$m-T2 zrG+5443IV&*AzXK+LR@wgkQNiLeK}*@QwW_nFd;AjL%+z=kG4Q#0I!6nl-j|$R+9V zy5fJF=0cA<(kwx&+R9-&s8Z=5F1@{(z2MK?@MVoiffLlLF>Oa!`sH_j% zFG%;a!skWrk{vVs-X1l1&%%w)efERRDeV)BbzK~0%fVMmm&4V`5B#gQ8mV<;y&4i> z&X~s<*V^ig9lHxAbt?ImAZxI^*Cx62UoD648O7b-zJ@@3KjR46@~_i}=;DPTp2jS5 z*w&a3*Eh~uA-wCQY+XCvz3Nv2QBbH`#Igb;jKl@}2mk!Ze=jR$m2MsXf{oQpDK&k> zqq964v&tQfa8mAcb@6sRlX{I$)GpcmGT>M^m0|mW?io;l(x8=LV3WPdtuPSWb1J*8 zk|FHSpM3VY5W%$ZzaElh>I)9)axlH$dWL=rTX*s*j+SX0^v4{+$ zCTgG}GQ!l-OkfLj5Op})irBL2qmqHD`M|r9$9F}ktbg`{dsPE)7j#}CTI7v(mP}Ui z%dR!iqP8s_{}0CAsYw&A4bm;!w!3T_UAAr8=(26wwr$(yQ?~8u={cB)eeg!??@z4E zm63Vfk;cCC^7cOC*BRddhlsCLqO|n~DGkH=G`>G8`sj@CVnczfntYd{Y-S4XYE@xb zd1sh0=cWu8oQlz=jB!aDwsrm6grbQ?y@X>(V;TopH2Z#aNfKk==XP$?s+|_Z*QUhY zqetP1rCLhqXR=dn55j@0YvS!3%AHs#FNs=+Y`@>obBI<_($GG{iWk*$!0AYP`Z4c% z0D?AdYL#ksJ3?s_E^VYC&YDnq^>Z2&gWvk-gRRK_;au4NV++B=#l-Z#R_?AfrQ^2# zRqjsJ-zY(uhRQ_#y_HmMQE0$QCT(X0R4_F%H7VnXG!q_Qp9oyZG9Jge_9#baR|9CG z@Td1aEW-5K3U9_y!3-#L;TRJnyZi-qtv$MXd)M~z>H2MfAyo#)Q84(r3xre!>P1SuALsAS zq^L_r^$~PMrR<7>`j6V&`-WUzauvyC=e1PVzp>O(P!pS52%*!|PBwW`65Se1Lg_|t z$AovsiI?T#xSuf%px6P)->Z972)nLkX)T)etL+D)y`KmA*NxjQKU1DDNg0?MW~QpE zZEq@B@^=Q|Yj#E}lT~Gsv|yEKLDpH5@s%Au*&c82s;z8#*mXO0^=pw$PTl0t79>#M zk^$s8NL=A4B1o~;*s_BoAghsB2dAs9-=1-O8N#KQ(C&6SwXh{WRWfq|VA@9LK5Hj`I zW+a=h{xiL-IY9$Pzxs1jwC89Fm16^a-`iCj!6;|#sO1qKv3r)9eO|pWreqRTCaE%K zP8auUdolakx@a6~c+!MUjMa3HZ9ANK{`h>Ng|K%K+Xw7na<)id z&dm{Go@H4fMhujWfwiPChYGf&zOY!8W|CEKgEi-j(2D$yU`ofAn(MYPN0!s}81TV-HWdY!ZX+$V0z`kplZx{Hf|sy+gZ#e-w?NbgxcB zc?d9&Wv&cdB2b=ZlU3t$fUKxy22Lw~7lG^sv*OGP%8E_sTJ*3ZGm*pkqX;>?liez~ zt43_{zznTvJVSxL+yi(vP<9BJ_ZV(k{v4^#e$fj~FMs5NCB?9U)JO*ZUNZg)5Kc?! zZX3Zw31pgc{I@99hxf6*>*w{`)9LfE)ZzScM_umSD(Mg1WNsKzviU%1=-Ovx=8QYj zldrKBt#!0)t}6kJYyeALZqL18Q+H-uT551WwPbr{PQ{SIyOe^;hVAR}8XL|1%#4@! zBf2T@AJ4<4WaoA<$V=i*-|Dk@lXaKSrgh^pV5H4gtceH$VIe#Iy&kM9o|4kyU;?L~ z^u|SE|D_rR{hr=_#q?Fj!W>m`r@}L=KCePr6ut=Na2Lf<46yuMC%%wqSUz+9r)-3R zuts6q(HunzMUgYbET;O$J5sHq+f1Pms(!&e))y zOEWv;0ccdxs-Xk+Y&rw4Fz9tyP|%=)%>J%`D1a-kp~A`%>Dv2YRuU*u*_(zZ^NOs$ zx4v^j&CF|!X5N6k+l^%&h7wzjbLNCu!BCtRa@oA%i~c&_5Iugw<)HEj1~vLSdym11 z%$2qbe|0r9tH&~5jj^aIs@z`8%iY{`nrB{)rr?XC487C*-Bv#)zU{smKcUMxBc8`A zf)M4DkY+n+xeg5QtoQQ4J^RAko1YV4AgP@=XQ^=hk{!x31EfcNyJ)@)4MW`@tnCPY zpD^8wkM#RC;oF%vzQE2B@6*<@5n4xmLjc2rUcFvvh3OuD@^LK8KFXkAPq8S#dS~Qg zxDC|;pcxz>kf%m#30O@jkYL$a3a?$=;zJ1f>C~5`;c&dR7mxh60&1+WG{BsXk>RT3 zUp%Q4W%#x)2Y~72ZqJ{u2-43IkvrV36wUP^$6Mk!bKdHVqIAkE0+z}lIis8kLo!KD zwYPeFcHcjn#kW(w+ZevV{d+X!N2OoQUWT*!19+hA_#~TdC$MqL;;9ZAs&d=Hoy(EW z6J%fVph9R;w*cx>V|wj=n5cwxkjj~N!oXaHO&B62o>nfewrT=+8+W1dU?I4-CI){5 zxqX%JzNHU@kW!!Bu`zNVUca|lfqn{bPy14}M8q-w3K^zz9Q0<Ng=G?(PwPp=?j{?fkndlAQW|1TZ?uU;Sr+yBhssL`;s|EJ?W z0R8iavL!uTYm!6~Y0HOQQ9(ETcHm!i@ zI4#U3f$XL(n>FZv7P9yDt?nd>2r6gAu6M72^x+|DERgqdveeEn;`F@&b?&cDpI?Ix zqLwg0r{SIeYN6&gmbpuKl6Wm9M6h#<&dA!n8tZVCFqB__kuo`CbS5NbKB>!QZBlGM77%xRz~y*z1; z3e|PnZ)%#L9pxKVjz>`}F2AU5QXv3RYjyS1N23+23B zosAnyt_Ilp!s_jmILZ$gvd z*u!Aup_Rw?0<}P&7WMm~g(XkLbd0aR&`$nHZaBeH=%^!Ir{1c`U34~3Sp|}i;-56v zQCwSk>FfN}X_!qCv3>4)B`vNTy)SkSk7xb&_XMY= zxk?!0m=W%?zL|j1%sOX$H=;7>0V2O~8a5d`s#f?KH4mY|>P}mejh&f{Cf9@)Uh{7Y zdtLzUMbCZxpQ?stt?fTEgNdx#64yGyklp>Pji}&09et>5F;;>gQv346k!h6D*{ua! z;K~&N3|YOi5j1yM2`@G4PbsMt9pe-C?bYZ{@E(HayNXyAZWQ|%H&le=dl`}*dtw51!gtP%W|>^g)7wTBbriU|9+Mr7b5W}&|F#zSx@edS=ENLoAzmHUT&ju{Y6QP z#A?45(>o^E;&%C|c*QJ`&6%IJ!n05SYVee(vwkI$0}0tjzTyA$&hJ_DaNJv)SzW&$ zKn)X$FGEaIC2I&p=dZbpQUad5n<@J$KP))AetjGi_F_xmQ3Y$ARPk%2?#bpUe zZqsX78L7iK9plp9mSe*TI$n!*oz#-?w3F;Ac65g(nWtnwuL5#A8lb?`OXS_WNQ(ucw0DZqy&XvGC^!pBopI3D9(h!Jh zpN2if6SY1)Kb$w;Toem>2xJnq7M7AEh}2K{iFdlOp!+~71k^;SA(7@+u|7p#SI?XzI>yUA#c?lGa@Eblw$S@H&jMDmUezuNH%44v2XJrL7o~Rv`zIe6(LK_U?n%vH_9SL%yvIdJ!LSuDVdI3PoVe8@g1v! zRYBwc-;d>yI!a|Nw&kFCItcr`!4M_B)cXmi)o5uxs0?%E6Oyw=9-oEH#YKR_`6{`) zNGzi{0%NfVhZ!;&@m$^!aw|sCq#<7PppxGOMNo&pUGn@b{Ef%Qet{L`)v0AA_j!Lu zFw3#e#^x4vUI*>|oWltv5Ili%4QY)WoDYUPIW3gOV&w7b&G*Ga;GhP7Uq;8E*CFs~ zRPo(S#A^jvoC`CwGy+e?f>+I&K&yYE9LL(K#b8^yz&s3KbSEYrUoZG}i{d)@85KY9 z4FTSx%l`Hj6ir3>E0&Q+a4I)2Cce5Us)v7HaFH{|NdYBkkY!p=eV9pe0K2?;RVi(+&t>2r?66D+3t0o zh@QcFq+Vrt+olDCxEC4VH#_1xe?xJ1O;`3rR^}7&r5}s@tzw=SSc_D4Fb(jXL#XVa zFh*UuF3j@=KZWJ&#pQOjx4$eFGW9Y3g69$`X#JN|{zq8P#KFw?zkYdlH2>eq?5f1S zb)30SqzB{)3D<4Ev^-#42vHV!T+2%RthPD7c>TQY7A`DNGz*so@kjwIT;ke-V3$|& zF$D4N8woUqBu*o%493XM@S6RKnNU<)U#^328_3{F@Wa!|(Xl8RUHcrfz+qID)8vI& z&)XEw)=8LLD&*Rp_`wS%; z3<*YrLun-FGb*1k(@IhpRlI1v{q&bad}F?B;Nn2}IthXXoY_ZcWLP1qN$T}KTqm=M zM~~Y*3@5BR6w(Mca(39?%7yV=JBhNZ>n( zcD4H;n4gu0%l1Rg^qOi9aY2~wZsK%hDF@r+&FkA=I!?~#SWAQUM2Lkni+PJ)(X?BM zBQJpmUCJd@GbeHzm@(_*!)#-n!>(t9YWl1+!Yekq@^5JQT zLq|d8%*CghxM`z$Sq#fDPdo1Sr0CYk7`&0oNp0%&6qpxf1BqczB?`?-QLFOoV3vZ; zAo+;`aAa{v&mWG_>HMXO(orLc0s|BJlbSduqQyUIMaeehd@!QX5jT+f)qTS9_y)l^ z{XMt0=3iM=6-u1BWW~o+SH#aYoNIDpkFS^FdcW5o$L=$vfs2yJ< zb;-e`njH{}&rAKmV-!GkD-rSd4q(n#G(d$grR|==QLaqF-ANG3k+l+yhjX+7HZDoD zQ;eAPp4k40_?>!hqi|Bz!t(y!ESO#l*_(4=eHOBK)oOM>b{JW?%O06qwsMmAW#W5= z;~5IfXJ3UdST}MILKK|vTALH@KulP&cgob|Mvu$f@6Bo`07i!aRFNwV4MJ;RnT=K6 zA!L0TN@K_iPcRSyy{xcEWMfc3KNk#mGd>#$45vlY!TA;ViztMd=9lI#m-g%JK=*** zxWvD$kRrb;LbGvTj=G2KO1>aVI7~MtiJNX)708aRhI=6h?hMh8NRVCFHtj0ou-Fpy z3XS~dW^H5-n$Z!=MB*ajZ8p_wn%v3)!GF%GTeX`mA0IggefbM*;x%GT#Y5{vqD{a? z6S$GyjCU!WirOb|H;+v6j1>xYaoOe-MaT2gAPewI+g3(Z#Ke}WZ(RKKWaVBb6y2Io z|E2UY|A;H3UHG$kjz*B46o0xp9Qm&=jq@>kloACq#5&K(mMlEk-zccr1SBX}ZZa&{ z%dVGa9v@WMkJYKFJuTg*PhQ8h_ZY9$Iamwk3sc7gf}5ut#cZXH4Mu ze0q(zY5NdG^3NT}I)y1>W~=gM{L5l#_H>H&qRdsZ)K*!(&X8@iDkcAV>Mjhp(R0Hf zsFx4e>ZdAYIQcOWe*}X08*}Wqg~oaVG5sO;Aa>$V-Sp*w0gW-u|1tNWIDze7`*^IR69YXPI~8aGIp3yuY#D{ zLc`vzyYT}C*@@$X8utdSuB;uqePtSWcu{8 zxqUC)z^)QUA};kBS(O-718Mss?7bBtOgJo~p;sdo(;XbyyV0X|jA&CwRl@JgwTZkm zLc@+4tkGh-7=LqRF=ABbp2Np96^5>-T5@GMgsQ#>ikLKTyn|%8(NpK4m6b@M@b)9xLUv5LJ|%$v@jgQ82GrA zaEf?H7E`z6c`Hww(_MZ6VzG9a?u6n92qo!5&Iq>6DJF^fbC5w_!U{;9Q@E$sw`~7e zXgKY?T?5K1od_BQF2yP!&`Q6UXLD%KJFl%dqQLyHo%Gf9|T%eC^t(s?xlaExP|2 z3Y$2l`K*oFIPx~!Wq)_M2lQGpeY$%rWMIG#hn;_2Q_QTnIT6tikO5+0{>46kqoo64 z=R`eq$<{&oN}fQg)9WHNW+~J{e(>UWx0*`p)vNXh`X;Hb>br>>4fgzqwUXKW32s1{ z7WIOj4uz)9_RiM3;1f6E6e~kWWsd5tQG2|X7Vy2AVCD;ZClA8?cRqw`PveV(RQnp< z#EW1#VM2e&wT2Y2uK{Hz@X@6!74;4X(`f#Qq7p|NEQ zD~!Y$yQ;Pt4Rf9hz~}Fj+18)%vCMt5odqgyr{n<*n@%i_t`PKYe=u=(WRfa!!6U2y zvMewmG9clAORW8IvHpi|IgC*@45I)BCuMq&Tst5scl~`!MmIh=&S%yuH25Cftq9UI zzH9{9uq?G{_`^9Zx{o)VypR$PnaGqYo?`&+lfOnnWzHp)AUrrK76wFUlicbR<~ zmhu>JnLQWqe3zQ1!Oak<(edbnD3(#L_WKBB%@&7ca1+~1c(468s%!fjtbA;@%&3Iq zC@%^`bxa%HnAbLbrzDm2qJ>3e8Q~bXFE0ifs=PEb54Mz)nk6^3-v2#6?!srj?kFRMonZo(g^FrNzC?3krl42xAD&a)Ndj1yPULgWpTH6CN*Q z*=fa<7yGq@*QC4M4FXixni7TK|CnFNj;cG)xrLeRwe$52TtF42Lh2&`&*d(M3x_$* zTkcs|0Z;#|nmJsG(-Winj$Dm>E$T>oxU7oE1*~W8SWyBbasjn;1z; zZG&IS`PFaLsMdB_xp6}fPY>_A4zOSZrv5rqs~ysYeB}n$3A;VGn0jZ85AQcF zP$eI+Cac(T5yAoQiI@&X^S~3``j_zHsH>lkxx|H*vYxFqR=qo1*wHixW?HTHTM^BK z8uJ0!fm6zj{+nlWuV%*R@fPOtqOHFJOX1i3#Yh#0P<w?6Q4Q;2aGDy9VFt-;j{yxZ9J>n22JoI(%ehbJg`d*%4@iml@9d)I zbg-x9MeKh?{Sp^$qY_sFX&OR{;;>G&<4jRKYlxc$-IX>Ek08*3wBr`3tx8|UN0!RM z1bLIXIWGK|xJAN&a;R~kU0@2G`iS0^%|gw8*fU%zx}AZ9ImQhDRSE|ND+b?z1UDlK z6zKth(A+QXmP?P_>Z!KU&-m=U*i{H=FeRG_7h15r(XxP_eCY!Eb?Y*|{!oaG47Z>NE$>p`O=< zvV5eLhGa8wWOQa^_~LVv7C4EV7;5v~O+CeYp?LKfP_+)oIm5@Oa=*ahID!)|J}%D{ zNQ!k(q|ympO#0nMcVMt(w$BnVKmR~Ap3Gs3(*0rb~KH~u=<9~z@NV;i+g?s3T zI;bP9;DOHp5@6$sNR{I_OVU!11Dnr<^xvkU`B`I?u;k7TbVu6XPVI8yt4pc)cQ28ayeSH9O); zyX1Yo9&8glm6zp%oMGIpre80uE(qL;EhK+pSg<=XIg+re}f2jOWcy>D-}Ow8N&(~XneN*p0zuBOxb z+s$sJEDp12ivR1y*KDJ#?bbIl>%*orSBi!qAIS>!PyqQ5PRHD|7s!kex4h)$Vs=_f zy21Iw4Mr0LUkWG(w!O)D;KSyowzisTg)aACz{XIa=o-dz&1@9=jSJei7pns+=$#BW z-{Q<|O*atNXUNa0z0%GCmKiAq8`_nbHSnyBEx5RtbN!0K(gs42;Fk|(=`Js8&1P0X zjui9pG%Y1(Ks%yX{RuiC?#e8AlFW;{%V5u%BnLRo-)a8lnlcX8yZG*9ou4%1(rKr^ zZ7ozRv9!|Crc0zI5-XcQaB@|)XmFdpMGiA_%tR_%-gLgg2L-a3vF372^6(??7r1G>B(E{Tq}YUSS`h!$!aIq~ zW^w4^^YLE7oLA48l6UBH?mJdnEoAmaPcqpaUuzd#jv-@c(JO{?HdbRT=Lm#KGw0b8 zRdR6ktMN(iR5x@nlI}>T*V{>u)Gz}zavzH;7!Hqix$sXjg6N(w+jJQ>*noKsO5XiQ z1jN-e1x07M9F$1=-b94lWpG2?bt5>SV!pjKg9DgSilgABgVADgCi8n?p0ddm9AadA4V6+yNd{9x)Kz!Q_D$ZsETyt9iN z=!Q>6hS1F-%rAE5)YRl~B6p=Lv|T7Kg9E;tz%-HJBy}rZgG{uLMs-!m$o{PjuVXK- z2)8xU0e1Y+fmor`=7!u73AV<0m}qX^nzvWqtWVkliPCI_YK zzh}hIdd(7sN4M41Gba;*d1)1$jG1>k0~{UDx$-(zxn=j+;dp9b2*%~hs2Cc$`wFpp zTtKO#9wZq~Ve=tTa*3>=UDe~ec((M|FaqbUqlFrn@TGTJ^FgS_%!FbV9qjcwzQQV0 z=ukT=)!u>vFoxa=DzNylVQ(l=_%rP2O~7deXF6;KPzbCD8w5oN9V8DO^b+15#b6bU zL?8^Sl|8Yc6JaEY1Gp%d)ePPVwj}G63PJO2F_N&tNm%qi1Y{MlH~Z|dtI4ll!GrMx z1sK%%35YZT;?8T`w(jsZB&wKu>cFP@@po2sx;>gZaZCTOD5rI2#?*@Xc>kRI0q{HspQHc!@eP?EN$D!k5al6g_e)FOoGl5sHAIt1R2BLsB26z)C1}(;dO^eSFu2oOQ!cdrcT>G&$ z(4o=r``5(+Awx>0W8N>{L38!Xdqwq)tEATh@|~8>T!vtzTz6)DiHh#29dBfjT)pEw zA9{7m|7#|SMIwd|y?>4`=EO18gEY`7ON%*`$8tZ#MTd+byNY zWvJ`AoWMnjmKtiPjrMH@zz-v}t(OY>eI~8#S^4&WE%Nvb3WaGiq|nN3*-6W!;Vdc! z^G`Q-&mJVesIE|uMrbA6`&9_vqo;tl=&77C`Tuoc&yP_w84aiO(<*9$gOBarvI^Yrgt#>^j~oe2VNgSu`*{blvZkH1#!{C z0ApfZ)yKr~6PoF82VE!# zx66r5_59r}iDLg<2m?s=s2$8lKWR_y$qvWLZZ9VL@1=w{1%GiKzvb`w3mIfcBgA3FL6Wz1 zfnfhj^>|DBtidz|YB**nE}N{(I|tJq@&5pqxztnuhWk|x;%u$M8|SugjT%xAx}Qt8 zKq^7>FPn46pkX1#1?h6^5bo~FPAF&(hPYOLuPG`q1LsUJqhJK){>u2bVWmFyS*l9K zP{V4QJhFlP1v@YEWYt#Bh!+|iwy>;E*)tZSt5v2AAJge^u=rWtS{r5M`l(>bR|nMw zYx|Vi5Jt?OPmPqjnAdv48j5{S8{2b?Gl7)nIol&=%wOKWRpe@E_s0#brn{aZU14yD z7(kwaTX^!qu--N^wal7Gz>MHyX}LT+NaPFsw&Cv{CXl}nPP~}jL-FBO4)JHX^ZG(4 zkR14f2OCU57BI=$b7E~&-%~fS^<`%lfSX#CnR+cWNb?LaLvjI3Zx)5c{pl#}$e}Ah zRKedi1`@E1{dx>4?e*kkrSBxgrMtEhTRfC&UA(j8Eae^M2JX<*{Cm}MA${+|z)kea zbY+pm1Pgj}$c|#5QLLCx3L*9zc?n{qp+ob<%4hi~Iy|eJv#ZNB#y1Zn{LAP^oZ>+s z^Tf~OF>jpw{nJ04w4L^evx*c;cQG?MA1u5g;Sic*mW#^280vkV4It3v=|k;@_!!OJ z&^tv}2vwWDXM~f~N!>QQmY8&VLJihEy>$6I?-JmucNXUDwXq83gw$7|9&oqJWkrKA za*s7A@UEXdf64Nfk@?kdfJwSdJc9)cl%=k4#JY21KB_dLS_X} zQCZ8^0OIfv51XpC1h_a`zd%OYlYraAd|_jVi`Ln9tM>ESuevf_q5SLaF6J{K9p*a! zq@#ZJa6?=KFw{ouvCpqQ*Q>%X!gI6=XI2nrN>w-;)zV>JMVfQp6Oz(z_i+@<-5~98 z)wPXtlP8BI+s-U??sFh!ME|oe01yp)J4m zO2FdPc`_wZKTk*|tRjC#VL%Ue42sGwm=jrgV)rBO%we9+!|eL_SqjrGL;2`xXmUvq zD$<@WV{hQLdc%MkyA`x^VgnrrZ+mB);a7Iw++nZPGxBpal&_I~PY&IUIF!A%%SZ-b zyht7;N#h}D=L{Y)&zEPMhpSI&)jhOPt``qJD7%R;6q6M@JdLO_bUJgZ8p0p+Kujz@ za~RMD`btT;Tn_OE)*MMX?;O+3t|+^Ph^?3%UGM|+dVODASA{jcgM)R+junl2&eFL| zDLX5|Z49q)t+5Og65+t3?zmh5Pi?1#3L+4HYWD6!JvbyhN@(tq4QIOYOnl4pp@G~Wa$%C+0FdcprV=R)lNO$h=LBm18D0r%xT=rfV_|{M2t!x`kRUqaneb+iQ znCMhiICXi4p|;A$Lbu<+PyE6QZ3MlFzXA$<&|~L+T_GS7ZXxX$fn$6viiCP%sx3%c z{x&5}u+e$9d~v-4^v-I-*Uf&M`VJbg9TAzaOBGb%`v#A;bzh;EB9ckocd*`1W&wmA_^P?DX1y71oT6( zFJNIUQuZHu&iNm8CT0$n|Ct1ugZ(d>7JK2-H#{<>$~WS|)B8*{%d(3u9p4oDtk(r& zWlKy~C{9h={Q1n?ik8Tb+71DBcIR}qbG}hh2mY$4V(pe9&33ThC(cAv| zlA7pcv(b@v`*DB0`26GOT>>J2=;Z3!mQ&cdrSm=J)x{7SbgpJy(^BTAQBy?uVi#BC zn(kRz{R5?pE`<=|mQv!2()rJO zXKm*F{WFTN;@+VYyKh@C?S0ZP)3>Lx3!-XMG|dZ3iVv##g#$1NK7G-mFHUF7bs_O! z&bbJWN#3WZjA6KRm-RaWDN)&wiJe$q+YaVZ0WkjNj7FCHRwcWv;~P&Z7_#}0RSAXxf*AVzcSH)Pwr1L2;)P-*FEh_OV@%6ysreqp3a=sV=kdBLiW$~?nyzay zTLaWw2RpC>Z7AP(QpI`~>Aq(u2U3yE$Ka~ zP>NJ;v+O`^-~TEBOQ2lke?1mNQwFOEXS~sv$%8w|#yC^ns1qBHW=l6ap5SOM3vV;N zeHP{#;~`LMFH>&>nbA%d8T%3i2)j~OOgamgzl~~PP7Gh6ChbD)k7r-qHzWt6_Xa(1 zd#8<$jYyQ@iCs_b9LpaWQ2$N)$LI@Yot*tfVTh6cc#gtz({CE1@Hp$!loKyW%+vrf zC)bNqRDzq~fID&Z6tw~va;V@vdH2Ty&#vFVRittAnm)gy*Rowvs0+ zUU=IA|K6T#`M&k%N@}+4_V6wN8s&^;QSXp2PcavDY@9)9Coz5#ScWT0Y}uqczqxhN zL*-A2>SIysiwQ0DQTf&f5x^7_^Hd)PTY^M9#>avPlJsRk;E%)~Whd|BEtA!T zCsPW{7HRssY|~Y8uKM0s`D@GIXL0DN^L}&Mwbe3YjCBF6b{u9Hv3J1Yn+f-v1{(Hv z@tMX%Ao^!ajcE5NIv$-$(gQ0?8*<2IxOYSBAZ#1aXL{xeTVA<;D&S$RV9Q*ZLnF@F ziMV_-pfk@&!+;m~P6$$&^~X)t&t#QoSn*e!y}J=aUr zlM>8Nl`C|#l+5%K!UDR%>#yyg87sE$S^{tR7#c#2KBXx_fDQ&Ru~WmT$wTYJ+>QVp|NF6)3&g zkLy+NnKCH*3ymr&~@j@oIL7YGD38!!tivMJeyDTzRMmePcV z`wDfEA!s^6wfey4V${?nA$7hri3!=DBc$K>FU)OPwzzJLZMy!_tgHuEMCzqt1)ga) z@!|x$9aqgq0HWRMA5;%#(VEL@-S>clWYMYi;)whyh+k6!9)c)AF(>!hhY_#E9V#Tx zzO%UD>&@^z^=s_|TyVVX-vfNML2M^74cR9Sn4TCMs3%K4hyFy`Yt-+c#c6hk4j=MMyhS(!v0c8j7E+vZ_1^>X=_ zE%EASe(wDhF0`;hMboxP+auD=V2hA+@G!r;AUwdATJV!KniJKS`GL;|&;3B9vR)!vs~1jX~N9$#^Y zXIh^Kfy48(Ye_l8X5Wb`)0Jl~rNnV_`>kGB5+HtkbQbJEy-ulmG!OK&BG!ubwJy0t zlPwE2Kx|!31jdNCExRh*q6hVXm#2eoEevZijjkTGlzXeG4&3q^O|m9ltH^ze-9iX6 znq-z?Q>0RY-F?~yWX0dD;XnjBkBZftxz?R`pdq%D9C($Zv>Z`G@o+}C?R$xej|BKA z(UEu3@a9D+n{l4xPOCBt$9H4pnhy&;LjvdR-eW=vGtE8ER<7(5R*~$fmN6vo3Hsv( zw61JT#+K_?>!NF)CIdIu6*+2F-WC&>h1fH6BD%bZ$F5W_n8;8(LR4-%gtL6K&a#5TFX`wxm0(^W~Y@pTiL}5_F+r2LDRTDWH9avat4{q>7~vk zV2cDR{hx6+*Sthy1C2;Kr_u|>W2jRM-P%>-+N%|REX;q~GCB30#C=cb#Y1s+vvt>z zhai``+vWx{DqFMEO*cm=HrTH=3q-xinM9g=j$MZf8uxR;t~=RK+0fWJgX4wO zLIIs&<_VH;Wgo&R3;Gff6S^DzA&`ZvsY#I^@`jZMt0f6mavSor z2{)sji*NHR_L_R`uKjcv%X-X_=fV_R>fV$cG)w-TjQO_MGSQt+GN|`EM`{*7Fa`eW7GR+F>-7D;xz2n+KLeN)J+EE2hSpm_GMJug z@T)noTgL7Pk2zvhxKse~OR3_20_^U2LrxyCz+qKy!s+7#zdmM z-tctRibx{JQ57PrKgQ95PrMh$MAx`K&sJyi1kvVV%uA|{X?ExOm9&} z<65?ACV(<0ew!YM?)gu>&2}yfE@+#}b;iSbtCW41?xN<(>o6Fub)f{UX`=Yg3j#M$ ze(&&|hVmD|Usi?~vQxdBJP2=eyF`;gtMY55#rdW_5=a?i65Ew~s~JoTAae%*c{w7D zqYQ50e@=$lgjK*CLKV5-Q0v~=)!q6tu^m`hqP#)*i)dk3c*Pbq(jxI6Tq_lV)>dv2 zTD|DMi5!5Ye6MdTn46xklp>W`LQQPb?618Fx0F)f6&ppirb9PzmgCpW2*tjcap@t`+;w0d_06+{Zg{$`SshJq1|qsbJNxHaI8bh1g8)FHL zLXW@&6llrYi&mp{>{xG1a4K&EGC2O4|4z^-nC=B@CK4e=0*Z1gc1R%eRUaz@eko8cQ3lafQIt3fPSC`|-C04SJR;<=sGzSB3QEtg7(o(T$#gx3=V$!gF2=nN- zzXkb}khn(8SL8U1ep?BR$FKqMl$il=c}Y^HjkpjjWjV1)lBKkR)QSEOLa?GEkBBf; zAu%L-+7NGSMLW_?zu_hwY$wlqGwLAalZ;XFF03vh&1%y~r5PePrCLQtF)PkOrz5>2 zxawG4-QVe5CgEz`YG&?f6{aC0PE50!0B|-$V;!{pP50IexCuDQLMu26p>4;35VbYZ z)Gy)MU`-yygQ+7dvz}Pa8#4=wS^~n2dQS z$*$eM287%Z)R?nPhSD!s++Tfz$=teYQ%^vB{N&71P7Rqae;WYb#jbkZhZb?!{FvG9 zgV9^p!tK^d6p(AE;j8O68p9;CXo#t4(1meR8x9jS+!5NqdcZV*;KMmX1xk~od%QoK4dTDJ#REi$RA9Qg3>Cpin>}6hK!^)D z33gi=(qjjtHi6cPfG0x{xEVkPjd}Y<)hbo0a(B%S0u$6#v&zkBoytgq>ej8j^9(W| zW}QiFEw`#Tz!?;lPAik#v@X$Z->J>GOyR42c|pwcVT-S1PDzT#-}w0YGmeBjHw3>f zRQQKm&8VNDL!I0Uxm5N$G~})LT3vdSZOy~^`LV(E8Q{xb6IKN%9OR8PUw|{hfc{k8 z?YJ2kClHEeeq0}{T2Xz zMPOn+HfPRVNpX+twad|V8}=+mA_$GoP`|3BOpCDOK8)L}#_3YEPYUx`A!Iw!U;lp? zd#4~#qGnyN?cKI*+qP}nwr$(iZriqP+qQf5xf3U5V$L6PZ#`73s>ruml~tMff%w73 zF$wbvu&U&vbe9ous$>+%dAd*WPrB|mEU=K2-jf~Jv3k@+griT z>dhm8MBa-(hK1bei86V&F5SmLS_d@w#B?)F907_&cwWnG95~yT zoG;_=JVxASM~X?W7+uqMlo%`h3|bGO7t81sRekBfiK_3N8I+m;hKfMF^P8bH;4WT4 zaA97I2`+{a_h$kA3k4q7*Dm-JzX}qUG}PTyliNjVxA1wKB8j-p^w$8DrvI~;h%WfnYciP`@|Jx7V*RR{%mlgKXK>vH(VzzN)f~f1tu2L zL1uGNxYRfiGw|<}3f`d(^e5o@QG~a~9f)ZWhPAjE%343Zn_(Gdp=dWemRuj7LfE4_ zW<)|A`}IHED>mO;HZr7n&CSIy@KxZ0Llw8h%ZDQ(P)Z|7FdQH%O zst0Bn><3z?`eHhTN3~(#HX71R7V!9d1VyPljjUcvP1HVpe^Nag*p!VgU$(~5Zz`Sv zvzK~A=!m?MkL+T5IOXxpB;Kj3|EC!|20)uX9iB)nK*2~ znvSvY!NK2X3im<(Ys|nKek2yyq zD1gx80P)>t*x@??O8|B!u{&tHoDR5@ORYOhepYC=>ELbb3cd=Verf5g@7Tm!znqcvj`|BU_&^2iS4raj<0g?>A zV=@@`9_%GjGZ<@^*3r2#Uq?64VgXOu2_Rbkl?kX69W%_@8-iRx=X7F!{J5#p16bn#cPK|md61UG!;@l$tMlilxPBGtgf**=O<4ma3c$B%35Q_s`INiFhY+bh@&~APvi#C1AD~_W`97V z7xq9cO2b#YPhjF?jDufwbsq9nM3%jV*gHcg|DhogK_^W(bdA)1pSezU;@YAaXgwJq z7e3rGQ&A5NzqCH3eoErj_Hx}`Hmb&&8J#2!bV$`3##oSXD;CmA!=&|M?(UI=sJgra zU14ah<1hhdYelIhLY8x4U88J2`9tK>BHiXZ1XUY0aIVp8M^%F;KV_=L1iF|HlSi<$ zWveJ@|KM>vUUM1sSdFk36}Mbwq$3-%8z4H>E~E5?61bx%kJ;WmEx*;`i`W?srSk6aSp`XHmMMfrEs* zAogRQin0U()V{u&xbNa-Ove>_pNI<3A>yy}{umX6F{f#ZDSmjmNWVN)b*=`p8{QT} z!E^|jI)@6!(m$Qsrq|}0GH@$;Rp8+fNPED6!#;_9RvY1u)mVZXfI_3}P`^;#oSj`p}_ zQeFp@Vag+AlOjhzwNamW#ka_*QHw07KUlTao@afAe1X6f%7w%x%`LvR^hTW9ParGMWXD0Sv%y4D8lU%DT_~enqvbW4AO916BptbbE@Xt=sAPIS>m*^SYTfO(C!mlw){jx*(kI;cA z+Tlg^J@C67`r4%(;D2ZB(Jo?NR+yH6%CX6WeF$2O&E?xcS`HNjJW!JUyuqc6j9s4a zD~|~59dG&I!v%`ozPYQHs2zHuXICDu2Y|;9n}F-Y?omPTI~;xM;HK$&1B72{ArQRk zWz)&JKmSuqYUzQw2;EC#BQW}6ce%9j$0vq;PedZ!+046b^TTD|Tt?9mA5cMwhB?!G zOR?12p%NvvMS&2{lL-RK0nzx-d&Pt0P~vB!eOKikTM;_k_x^p+f-*8hc6VHbgHEH@ znrWL`Rdvtpds;}Y(y`t-jqhJr5gE92+#JSh+41%D6Wi={!U8x!;^FKtqjeDcr&P4G z{dKm=RwbFRVZ$ZhM~XEV+e3FRMtko!U_!7}5V8Nmb3a5W1461807<--#M?PF>{q6>z#j8VA z2IOE4-4d7GTqglK^nu@Sey!eEX_;YZR}KWoLXh>{@0Aq<7||yMxGS;1{rq@{VmZm3 zR?P1vGxI!|1r^STJ^us4DdduYF9Ta78`9*81!Dv6pSc9b!VEMei7?Fm)!p{4t}_{pTvX2b*^oqcaeTwc zVnrDx5|dqmhw1Q$Hu{47;k*`>3}yy428S|)RR)QRYm5{kzcQ9Ftn?Q9gOH@aE1cuV zt>!FBh`c!lkyqJ96|IjD17rhErJ!H#{Z0M8;Ub4wcbOIshcrxqFRoMKRj&aUG0$(N zds-ml()sm?CPZ5|%7Zne-SZFwLOirn&6!`Eg%Rqu%+fb^N|0W&%ObPeIG(DA2MbikPTC4qhacfnth*kRr)dGZ!cV5SFlV#(2%}1qj*q!$GBt4gM4Y zaQTC60Az879)Js^$K#7#_^RcH3KpLvD^6h!BT3di*Rf?wgn@|1Q+7K>BjO@w>|5ba z;NuJfza2{}@D>ZiQn*4QP>59dLza*XGy~z7OA<<(gp*$tSCwLr4|}2~;eq1-)jp)E z8U^`-NP;KW8_No+Xu?OuXNBq_Mes9|$RySwn_xyRM*8=ct&E|qV+wMa!x97F2P#B= zaTZ1{o#NA-@6TZ6VlPkjww*kFbWt64AN}~G%4&Qx`D!&jrQ<+)#PPVtV}Ea;ypNtL zG5SdJ!R>NyT6=G(*f7Kyr>UGS9l0!zRJyi%Oh2C6X{_5s`*4R1~gLRUr zd1!l&nr5;M7m|eC<6UJYyqjL4Trq0V9-@}{_|tjewyJkWKX$xJm!|ENQddOT$Q$k` zSR2bmujq7&S^~;um1=ECR^n=N6J=3SwWf1_Y>jmB#%0ljvNvd~mpu`x)~^e%TMn1O zO?r=gdMhN?uQzxpm;mF=meuOnv}jpaHug8!@SmV&*P7uO`ckQx(z~y%JksRpxjbrE zx1e)RXKJ`2fNz;#JpRGXxTWwlv2Q^1x}~R@oK7vfKNw#&e0+6NsV5kG;eL4@8@xj0z?MgRmwYdpxriK}!xd)mJapg+Ru|zWB+n({pwN`IZ5@cT z3ZC5Juuhoy9mwFgkTy+_PSCW?p%J3I)T-z-HB z^8A^dkK5V*6-?Z4foQVo;~7_8hgsfp^a|W2xy$Ur8{-e*fty$NL~}7O)4sJ-txB|A zSa@5r$ugvg8;uT!QmN(>V1~n^1SfbtN`7rnrj(Tz7lPP}J8EX?;a zdlB?jVH^9&Sk`E-WWRAO_RD!{^|uZBBL;ik?v3_Isz~fB%*Sr6>G#GKgsH}O#f=b?(QvXp^494fJ#bLz6u| z^C%o|=4D{lqcbPZz}1m#dJc|(Y8a)99kW672u|e4ub%nW8|wW5KeO)6zDYY9Jr`Ih z9H^-;h`!PHyU+70T_3Ou^Z(56j2!=os>a0ne@s>T|5V6{ds6M|HS5#tD0UOLr--Ni z1^5vRdeHHg8Q;(6XylSYcBQ43YXF%1MR!sgemWhqdK{kCrwn4xbv zZ4|-gw$DfU<+DdW@n>3oJ>Kq4ZVYy4r5fm^mZ?l0x9C8qA7rWqAc&uUNIlR^D4^3r zDU~;MQpx%^t0RNz?QozRz3R*xqoU~57_V2w(vv`cS(aVFllI^(5MWyHS~`m%qH$X9 zJWg(8TSplFb^;^S*!@v7*%Q@r+hk|wu(h%ZHo2-saHVSrh1_lTSh6*)xY!if+<4Z3 zcu^)+IWHNAa0bG!!l-f(t-4No*8Wm}^ux2#=myhqc9wQxRCRsJvW?~5nsnn{Bz4F) zFj|*&BU^8GRU?afHz$uaA<3tw{1e;VX1d*SB7ZqAu4K$xe_1M^6x7+!I&e3?kjpQ^ zE$ta?-i%{xss}FU7P2T1+y7cn{nF1r z@Z5m>_|+5QzC3NL-FAZYdp6$PANq|i76ke!OYPeOi~j_8O$Ou1-HGLA_zE(Bha_g# zB?+41YP#$`FI8z`-K^L24-kDK0+z7GTq?+*XV4~hVqSGl35BrMna4hbza#EIDa&AM zZtsX)6UoCRn#LCD@qzIny1#-ngl}F6H0Ewf8WZoT|DliXy3tXYV@9#)57Y^AmXDGR zD7=3rG@n~JQUz`=6;IqEJV=`FD;8TQ?s>)Wl(V0EYj!7mK@_Bq){hzJTr$j;0xo2T zJPH=i)IePUupKdqWg`bx5|+gCCZb`8X@)Vc*5IA0z*e>+2;W5Izv))atPR_AlTK)% zBp=d^{^!%Ihy$0jPFGr8Qw&i_vISMx1pEuqB~K9cfWn-TV0v+GNrlJp^2jHqHPedwFoF4iv;b%^?ZwmPAnfHB2o`V#eSBQ116#Z_`JT z;WzTGZBz&ifdj#p#gEtAft|jTC`WTjKFEHyd|>+av_tTRiH&NTfdS9A{z3n;1=lK$ zVr^Juu+De{`L+}a+*ko*j(L{}9?jPRT6DUQ`AwR{pLu}(NHZUV0wL2r_htpgRcX#Y z$jk)Sdnuko8Do<6XiY8}m82319F%4veHwzuTJ$V^AI_Zjugj6((DEaI3a7MZwAe-w zCn^ZpO$Vs!710MNMZ_C=UL}3Qm_nuwCk5gN+}q0_MCp6b9AIWFH%_wS3eoFSJ2aWj zDb-m){t%>lIXipcm$15=eqTc7pT}th8{-2Kwfo2;F?M|LBVAyqiAv3x`6?8rB8NJ1 zvM%;NuNF{)pY)W(hBxzw>pz9A`KR%~WQrcR-v0EIB+=mkmz~^D2gO~|MB2z;lmr21 zo<9v(fcNC$P`^Vl`AJ(4sX}amgCvmXu`VIo*=E+AX4ywSQ1MtutC5(KA()_td+vuCtio7UKrYsXoY-bL=Sv=`>zfc7bbw4J)E zj(^^S`JFqwFnx=+eINp68tb$t^Bv=nRhG{pQQQK11w>o7`~`vVRr7h3(5(87ickK3dr1L<^lh{)l_8v#g5>qR&DpHaZ=a2{tntKWd1 z4_!KK$@?qGOF!$Qu`R7CT=w`fVCm>brV}7ThRtp9@3@kSzlm4TukDyt#_u3le&d`* zx$f`gEh*)CrqLklaBHTJ38a&0B&Dn!ypfUd=7@;~-2z$2+sK890BPPN!wEsD?K6ZC zin5#b(~}udJ*d?f+A`_b@>l&hfE*m~>co}ACldznh;~jpa4;oMdSx8tQ9u znSAXD>q+U;UD3^w!N*SrN<{{YlGXhAk|GvKGui}H}6B8>_Fh5LGKsrdn12-!nr;G8)9tr{vtZg zYB^%#A1TynYq%A6jTJrcYrr=dW*&^jBG%f)!1xe}WC-MnO8VAP_pvnxSw7vL1PCgM zt4J)nk0F zb`!1b)FOcZ7#%|V?5NNf7%{26_(n$41|^}B^RZkbi8h>(3S8AQE*|H?CiZ#Ek;5NK z8z|iITQqOQ93b=Mb7_Ly3#17JM`IEH&tF4*QnM@Gdc$s{e(!*su@y`4?Lug3Ns@St``?}I$GToK4@tuR?ACMN6r@Hi&B z0$%|n2@$`apN}_y?B78eG8sCJJ6cG1Xx=ew;6PyJ?a~beO97_O#8+M$depKYWOLkr ztlyj}Z$@&@wT>QeztKvRBr9)|{8h}f%_N?r2+k_J*%wFOFQ*?rd>J(C?oL_EFx4FY zU2+xqC78n`L{6G8Rtv~5(56BzPnS@%VeEhcpCbXq+3_c?G}`O2jmr3(N!wRmQaHW! zaY}?56;36hN*pF7&=PP{W4vq27f~t*D3+i!7YE@H0e(YR^k5!1*Zxcb=Y)1+CE*R( zN3V{Cjdy=aB4t`l<`@o+LSwe97_@Emlj%&3hGq(K5qSj;h(tfBni5kVX(LYLxQ3_D zB~p^sNSu+UmWXk5W@`RHwi^x`bg(YV^V}w(2;Q88ry$rCH|4m47!O7jKVtW9F2Eav zimBCpJl)DyY9SIiCZMDbZmpu>akCe*p?>30?#Yww)IlGS6?@(4xBr}DJ+oc8WYJWu zwBjf*2rS@`#wh35%VtENhmOM{gQ?udje5Y2@38;U6&;2vaa9O?@Z#PFrfkAdKlzje!qvYLX`Me-;W%^#4IoiRr(U1^-X>rh<&z5I%C(tD1eV zaJ*W6(<;l&NDS_hry^Xlk1du}XF(^!kC(x@?N=K*Y!};976w506Lh#t#B|D73dyq< zAzb-py!uu(V!Fo`(mUHpq4Z4J2z-2DJZStw3i=$O(nqlx>rq0W$?P#_JGGo7Da(NQ zv)m@pXI$$vgnB~Yd_R{q(R473P8~~hmh}8(&4_^^KSS{wjyhuQi6H9Z)OAm#M&@Gc zGtZ$U#fFT*>XJd+at56VaY9}hu;YmfbxF5YR!d19moS@YJ0TR6zHw=%gu4+(8 z5uO{~c5uP;d6NluGxFt)MBvED)L=z8Zom(bER8APoQ0 z6_Np;k&%_@zx!~E_zbM{jP(C~`Hyz=-%ET3HYOJK|CLt$_emxC1ymkKa{&~JsDB#= z_6B<^u=9T%!F%vqI{&ri0)fQc3go-l${5eN{jJ=gs@SXAt~7bR*#UPn1U2y#K=L9| zV({WZ^CSfmwe_#7`p0@;@=r(z2}nr5NX^zBUKk#E;ybN7vMiOINquqM`qhWv%E0XK z&W=Fu@P;?Jz6MaNVFe&X1wi6rLjq?bBJ$5jNVwz^_9C0nf#gpG#5b`syMU3R zwZ7duH@2|de@Hmx!vj5K4<$+Jc7>^T!5Y;$a$szQ+k{3aWOzAML#|!A!r+vls<;HdASHLvYmDJR4oZi6&pkhOVvm;Y7@+<4n z0p#;^YHJC!Z)9w2tbYcS-UTGx6I~17S2F+LT>pcPXi;wz57WCF=L!eF6pvBbhh|!u z@2Ag`3#%goNIP3w#;5z&;!O`^atMUJp4k-;JtI?VqyH!3$HCh2h3%)!k4y^ApY?F` zjR6q-_v8JRY&#B;slK)G{!8e06$My@MJ0J@*!-8~y;qcgzzfcwjRyl@ZB%VxW(v3O*{vPV=R!jBGuWzWxOeBDpFhQj}1 zHvf{ofdSL+%kblu`{vj2{g>_7PvqSX=jm4~A-ytYy7x-i59!D6Dzqh)HTT!lTe_xl zaujuJ!|y6^`?sVb>!-Uz@P(E1ca`+q@U0#?(Dj7%*QThXF})=0Z$w~8RQ>So;lpeD zg{;l=<>LO6SnW6C)UrXFIW6O^_Z#JLlgC6N(-0}Nva-r+U3#p$C1``%n z-`x2498&7NQF8kF8o-V;-le(W#eFRW7y!oAl@6~q0N#N&py`Wjo!>S&7Zw2d+v@yo zI1T{vM-V#z|2|(h5&-ghP#XaM{4XJ_D1iJGoFNdv@Gm|pfcyiTAt*q}Pkx*?qu-nu z?>gTZQQj8bQ-a)2Z}=lo-oSq?@8Jx=08;+NTuuCoaZTYn6Y9Lcds2wn@IzP?qY3?Y zlScHvP9wh}Rd@`1xLlijSG_j~<_~ah3VG*#`=cy?zqkc_!EuSxKYhLN$9TMxdUMx! zfIkhJot)o;zd?pS{~{BH^FDZ$HQhPYy}OS5(DBStfBo@DG`@j-&0BxKzu@g2;r>Bs zUf_&B=03<6H^VBoNB4dPe+YJd!;1BOczYwPO52?myMwYJR{M0jkd@i2& zY>d9kH}(%f>wm>6GkA-Cix{NwICFlHU(py{KE;UEc+Y0=;I8q);?n&Xy}8x+(V)o| z{hoe`_|e=x{n))BT))A;&Qdn{Y#)Mt;?Abg2%}B$ih) z1^KdXLzBk55ZGNsC~iYmA#{7@wXpJsw31M^@O^fjjZ#hDv<}ux>BGvPg%&eY@hpzn0@s>*YacZK!dVo2G?&QREfHsm3fo zQfuJPGEHa>kp?&ykolJibU*QHwsq!-O=tL$B}SHoJb$B1D;`xhPh&r}oi%F|3|wsm z356Dg$N>0;aWY8l(>NznhcsX5Xkt^LplVo)=C>|QtwtE1jcH14bx$bq@^&-D`c&bO zYsWURVWC=8wMo%3ds-J|FNVZqYRxJzzD^YD0bEwCxx7W5qiD3ppCeE48DBe=_F?C) zHYCKV=H!TZa!~M0T8+!F^ zzfwBX|6$?D4H5%%ue&x8OYvEaM@e$DSzJ$drn3F3+bMUrFsmn#k@9HO)SClq3W-th zAg4SQ2(})!IorWF~O^wV(}2vDv9D)#D(E>W}xp3Isu8>&6u zAo|MqZCifpy`YhH9id716?;x zq&>%nhMGJa9y;)AmGxt6rrV^!0BRcU*j|Sr*K{JcgiC5$bdx;k8%(#R%(f{s|MACAxglBh)}80!=@VwI>D2qXKk8B7@mg*x{mK$s;o=df^-#9gA(@p z=9M^dt3I&%1*N?oRjgnm0zS=^6r*R_5Z$XO#R#>{pe*@Nu>}0zyx`v3L{GvjNmoz2 z7Cfiy*;4@FcFG8(b(G+53;G*WeN$fL&rW7RanxM; zI14~QNs55}rBSpA9-=N58apQOUn4A1aKsa{w3ln+Uzi_Wv@iwm(`9Ke-of+5iG{M_ zSpN3_H@>sx>G8(&=m}h6`McSC0%fCQD{$ceif+^9eh9igLZjzo{e-1`wQNP%xxIR_ z5&}w`;)VDYil#3);7X_Mb2?+#H1midCSnjQHtlBxNdR5gYOCFbsTg*h4JEood21H( z>m~+tZShUf586yTFP_b+;WOjP-6i3sv&tl|$_3P=)#4-^%*y@QN3G0pKCXgGB+4a*USP>yQweQMux zp=^PTCL?U94S~^bdg)y|7|WitOAJxn9}D{a z6J-)4uR$IE@5UbcBa6-ks|CByX?8RhjTL}WXD*k4x&7h|G|j5ItDZzS!()6D zn!gk%mUx*g^+EoNlgQF2nW|8qFb4>un4sXfVR5npwUW1=5apD5&3I53sd&$1v{lCU z*q+Yc@EhkL_G8E=yEqOl=c(XvN*dDmvdt1Ey|&=*O+9&X*7tIw(vCNj<^dbH!vcvL znUUmMGo@+126lr{zb|7dS0h#g8%4DOEJqk z*k2HJh1h``M3dz&cu&04m>Om#0&7HZIbF3F4TMxiCM*8POb&qHwvzf1@!<6gl8^c* zMoDiv4chB@-Wv9dXptm>;vT?#GI7Gf6Mn;KD zW6h-$quVq(Q|d0SHAVFS3Vvlkz$`5$xSsBPq6}m!3nljMQGgIn1#AYP%vqQ^&@ib- z@dIXLHjh|GsO|^|{YFLM`O|1{sY*mej}of6Px3S;on2(82*6)wb%rRk_6`w6m6Y3w z%NMaKCS23ih7prQ?;3+V((P>&wpZ<#7XZWRO7cIC8VP%*zw{{z`ACEZjRhgOjoh^l!ne}M<;3%q?@V{Og6eKG6H+&F_x2ZY{zjm%o&7c z)*LwrQZ<35akqUmwJEkclXsG8y8q%|CE?SPT)12xl0!I!@ad)%bSTb9+^Kl%9nq3-uu}BRa^Gmgp^0vOKV&h zTOC6uvE2GqoxSZ;4D-4+P7tY7Dt^1%$U`Ffo}9%ZgX4rf*OCe}z6Lzq<;3^CSiu)W zDd5$S)`I=fC51seRR@y%mT-S8^(He6n9q;hy7vd8W&E51 zF8rydCzk4I+=VHh^vVbxa&XjaT#H9MkyL6xfQ~&-;u2u4{%y5{Y}SVJ)ht54*>0Aq zTZ|a>`7b^*s5JVjppV%P3Z69X+W|!((WZal6iL0~U-a$z^kZXJD&4}@!od;LT;Yz^ zi_ij`3XX057>96*Z>4r|xZeKR8kTBBRJFs5*rY=LL3o3);42yvCP>*?(DGQ!wgZms z>s=my9Uvd2{*6NNYnko|E=a@*+69AwRogf#&xX>J{kqIxD-1!qNaFl>{6|~lOC<-n z3jl$E9U7b%a-rgUhM&Pnh9yKq}mwAPT2!%T;C`w*6<&!XQS6fD;n!KDw+vj*T}s9HjV*W-TctL-0&s<|3k1hrA`=Gl4S35Vd}_KGlPTM&Ayj{o zFMCjYq}{88GSa6%WD!nm@U9`U+RnFKfzF)ujQEr-Jrsb8+3L`8ak301d6G#CXabC> z!&~2Cw9@P3M$Wb0SWTYDq>wnG{6?v1S&=yv?_$UYFhZgUrN)R9=l%C!24yh}@)JaC zxavbbQOf)duoR1{4~EyC;$ly4eTJuwY2;4lOq#r))}Yqm-#3nFDQXdws1B);IBG*y zR_+&nUP1#sV6T+dFD!dZY7_?}Y7?D)7|9ZNUbS$Qd@!K(4AN%x^D%$`o zStvzqQqw-msJ5{eIGL?Q#To#O@2Swsf4;o)rV`+e&Z>`a zTFdy93E|#6>ul1Z=}4A>>Ga(IK4xgg+_%i;gKCIJRFaAsKyGowQsfdmC0>Y_XY#zh zRtm9R_rGaXU$!ew;VYQIeL-*0JhIWzQ#HpvH_-045n501#eIQIZmyMVDU`rV3L;7s zig$lHwJ~-D3LQt;JecvCu0<6yDeb~q`wV3Z=1*HYT~h-&J4BqXE@%-j{wsv-9v zYNlGI1RoNOiX2DwE955wG51im?uD`1C2vZ{k2Zu>+#mF$c6;O1E%=+P*n@f}IQMI^ z!&TY7CNz^h2sj9TM2tdZvIJl%DA5u4c)-BqMrQ*z8c+KZyoY5YSHEq=y&qFvCvndq zHXferuU0w=A1UGC!#(lukdCN5S&Fl@e z#uqJ$JqB||i z-rbzYrX5wk*Og9$c8qKzqIfjw+5q zXhm1bmt|`0LzY$#|DH8Aga12jgJG1A$-!g6L$gnYagG7>d06$j3HmhoI=Edyio?*# zwXAmmV!sW@`mg=eiRs8y z<|4{4uR#R`OTjDMY9ji)M7Dv4Mq9YW!=Czu^FT-ysDCGj8ueVEgo8(D*`& za1vWy9!<46+L$FCRA=)$oWI#4{*C4Rbg0k2q7&BA34XFwbLotLmWc!>b zAnxk5*9YA7@FC+j4KRm&?(X0OQjnEx*?PQb3W)!XX<6ieTFg~7cOZG)v zL}kCmrk<1O;mtE~pEC@@b8D1u;jjaSEw%YtI9%a}zjk zELnVWkQl51vf^B&jQgyF6(F=BcSZf+@IQgcihWQ2SZs$IC1-RSj+fiZUSt8Vp=X6R zFsu4pLx;@(X<5*W$wIn+sfglC1J`sMgN!%m-46L+^i66{A(GqTM!89RJ1vqseXg4) zc2mqq$ghRHSz+A?WI$yeY%XfP_3)}8`9MqOdmp>>|;&0c0q&7Q<0Nm=$ zti)aiC0AsZq!D*eYm_Cj^EIE9OoB)aSb28x;&6YKNR0y$Nfd$y^cmC{{$Ftx#A4vnFqesEIzi)&2#i3+Kdsj zUsM|B6f?2(BPnDr@~5LtoGT=^Nq%hcgwFNQF{H92_Bjj&jAZCj2d_+};dCgGo7` z!(|gv53I61>>(oDBzrSoJYI->MJ`D77r$95LiwvKf5SiOMlFE`DYypAFr8$?Uni4) z6%YPWw^fv{-ZD_p>Q1(o%VH)MWp&)AdfbArH)EI~46GfuUu8MJF8yl&x0P_$#r?6V zJD+!0yRtR(n+q0sUaITk3RIsWjf?I1`+0e>N=ffM$2jFSqkn4;S1nxU3;xCBNSQq1 z&SXgVkh=!qo3>O%XbG*D^^uzSsZSZFS?8C0bVRfsCgvMuVWEeam|h^dj2AY|gy32P z`pd>iEf(8J3PEw!2g-|yy z=W=;?;*`L4pe{cb;OWyi-9kz~dDA+$z6w0n;uqo-QxF>j2w#dekVQ{wBk4R=+H}yx zwqyOeNNKhLP1Q42(?R5uU0?{UIpK5;ei~Df8x)A0xyflifk>brRz`lAVtum&L@ICi zw%8xd-q?2lgkk7UXHPqX7hs-o$>lysR&(2}lS79m!olIS&pcVh5b|S78&OITJyI45 zb#eiH8SKiIrrx3oH1(wbN3T(>4s+e*1&?=Ua`xG6xj2lg2vmuL+QIp^L-(ezWB)XO z?*&`R3sz>~1BZ390_X`=I7}|KT6Y^BUG=_lnE~#d1xHm*1>g%#3zoO_&vr!RR-uXK zk-vUxUyV~Nw(Lfnnb8)J%j)u?eC(6tJbIMV$V~#ZhE^|od2Pe>G!M0)N~hY&(cP7D zJ=L|%WEBCBW$Ap5ms656c7oumc+0gDm<*HG*Y;#huJvyAX=9tjWe$ulB$opYN5NC- zpewh|M{bS~9ce*yUI#>V++%t~2fLR_4jEGNyqh!mA5{p8`$Eoz0H@e>p;Qr1GHK%@ zcU45LV2Xa@zga5E++)Q!gweAwzWMcp3sL!pST6#a!%TV5TQS_WoU#l-5qg3jO93qs zK1SO@?i7WaIMTFe>1PA#wjFiU2@O$cO`cb9REuz^>p?n0e2wCETgsxvL*!Gzu#b)d~T{p5V!=B^d?U`w}_mu*ndj+ms$Qm)&Ss=(l6W3iG)M8Dq2`jMv2* z>2dTqT?I*Gx)r1S$p6g_weU-cTZYws;ins;)b&!V4+Kj|EzeCr!GaZdHJmpW*OkfQ zQU_knjgtUG?iw-Z1L28Sgp1*qOMin><y z3w7>&QYeF=j9%3VmCFQ%cm&xr*EPbDwNz%)Tj*i(TBNhQexy*{Mg;%$a3CTZc0(p4 zcjz&_>*0iR0PGkjox?|yqh7n-oauh54p`f*VSDM-tFK8X&P?omNV1st`Or4&HS+k# zHcB7t%r(yx&Q)RjRxh8XUdveblSKDAK+xgx9>AK}Z&E-mBQ=gJ^#R|e*PVgWgvYJh zT@aLI!|aNls&fkHbdfVHv%u`WE4JnO6wNL($G}LYXo|mhuvuj`4{x^DjsU|mPCK=S`paruF1pL>8j|!=jz!X zafoB6vwpO2WqNQ9OG(>w@wmsyL1K$DHInVt!^7~REi+=>kI+< zUkQ$><+EiF#UBj1bh~<`aH7A1Dr08UxB(KNz3LKRm4@?=CVrI3Iic-2Ese_QF#8FV z8=owXo$9NArqU=677k6HnyB(g74|>0B`1akcrEK=iu;#Qm2l=fG7}~1eIQ~JKamc- z;Obs-&KMINY#}=dq6+9Wf35q^&Hclq;^h~fm>xxz{gnf;LYaKB9giT9K3Ts->pGk# zu!Hzs=BqBQAEn)#e4W9BjEc*FZj$q{v0GtMHcbX1Bn9YX9+Zi$od;md(X8S$SGZHXu3Mz=rER0rGS)B{&!atMbnngw&tFjpt z{f#3)Kiyp-uqx~{eA0|>?eYU9v~41p7gxV;D`cF^@`Mq6Tjs4!o5Ec$ed11gJ1qrO zn!9tF{L4m2gfEV|qwB#-zj}R&BO`8QI;~tRQBT5E0jazjd2203H%GpeewDo(~(Q_uO0bhnGbh&Z3lU?fVfT-bro1TU?l zyfVcR^_P{wGRwY6dnWru?S4%;W!tV-2yoA)Db&Mlt{}yC&ByY1Z^cO4THkU-mj~c22E4J z%b;R;A?%XONzU8m7@*lm9!*aySPuUp4-kE`Tu~MoK1HdqV2CVjV*P8$~4CQO(8cmj` zV)b$fJR_!PaoC7LXj3d*TubwPjv!Ub?*AfpYQHi&`I%`S8o3_sXNVA5sMf!mSsiZ* z{uUb33&%bHDBYeXfHz+YQlMh~@!A0-P*D#6xqmU1UO6T=vnaQ;1Y?W@Rj&DQzGr3W zET?Kcr22>O|Mp;6`3XGq_mS#Ab$q{ZiXAZT69;P+?Z6e;#G7w&ia3i1hA>J|#xOJb zzi7LsUSYJTOVHc4ZQHhO+qP}J+qP}nwr$%s>Lit~(n(j+SADsD!Aj_t!Vs77Ix&7#a+w-F^H&;2s3Rlea00>L6rKl_!O6W z#t+Ehtms|HGD0Hn!7Sx1-gs;ibH6GiTSkKs50}!Snh$)8GHEw6 zBM2cSbE*8|I%ir6i>*OYB&400ndb^*WBX5NoQrwBs_RD4g@53dA$oQ9PI4Zav&ceQ*PdfR0IN;`m%@4qjl zSlP#b8VdI~vAY@(0hiNlO-s$IKzen#2*xuV`c40>>Y(RiC&KegeW^Hw576Ly5qPeE zg8DRAZS&s^RUJl|GeORGCPDW6W@>Brn88$wX_e5~0-BCCWZT>$cY_r^1@IEDzQlBl zPwtk)`h|VR7MaSAp5r*4!0R=r`Ue5S8PV3T`dn0KhAI$t^A zqK1qTe|#eK|2D^nI5^GrHu&Q_Wv3q>^n6E80xX~pmPq?A^RHhTJ(Cw=J=Z|oiGYZ^ zl^18t)f2x~ph4{_EuWYZA~6p?^45pa?YOk|Ni<1BgjOdUQ&=HyUPQj%fpp$suZIh* z=@u=wd0gDhu`~cLo%Or8KWX9rpg-I}+Vs&~ApgWmrHp#W1j13|6WY;_jbm%~Ju_d8 zr=ds+LYhcj+;H|_I)Xuz%dE$DhaRkg*!Ki|T!d8?4nG_S;#qSz-TTHDAR!eH8r3_- zF&kZ>xigMQ6O*2?H~&OJC}RdFzx2(K-=&PlK^~mV$ER*#UaLzp-mW)v_X*OQmqI(g zP9dGKE|z^(2T1V%r(S)2O!O3VM>}3$ta31=iobrx?OvwhPpb1Dkt!Q6(68Kk%i)GT z9P@KaTTM|A;a9UeH=6NNTyG7aNJ5mcQXB6)|9yYV1ykq>oN3aStz5C2@LQa06*LR? zp0d4&P||5aX%81)x=e$c7Ra*YBSqD4zDE^535b|6i>G%Y5o3Kr6m}Gk=rH35F?)SK z1Q1zOTngDn^ls1QYcDO*BW(B2kexbW7KSLkFV$!X?I48>9O;TSKAKf~l(uji_vWtJ z54y!K>^6fdCFQqMP)mmEs9E-qQ&n4Wc_oyD?N0Tp2Xrcvs%7%G7o2wY0mM7k!ncgr zIw#ehp9vc|A^uKRVMX(f=ECVfPCWXj;1=YV0+l}Z`T5;dn&D->Ym7l%aXwEh<^fV| zwvBnqdor9z5}beK?irQ!ABdoOPtuUGhbu&m!S0j0#HU-sGiZ5rUiz6hrv@2a=-6JI zkKx7JFA`B!*7_AuIMVrTQvH>SZd@R51e0LFx|S*q>Yi02X0ni%Mp~nU0VdeB+Gi`u zib!?YGt48j;FBQb_l!(4%lFv(?azvx>c64>)9PI}1vgJ4Tj%H=DsPb;kKX77j2p5^ z1o7Yl^=c98HyR1XHR3X$6WD8@3&3(`j{J8ei))EE%IqxeSUx8GL$O!;bD$_6!0u1- z_lYWrOMNEY^p23v^f&i=VKXqzU<2nvTy;?=37U#>DpMj?{e}==+2`HQ@8a)Utb!L% zJC01_kG4-l>j|HW6n=hF!&cn-=T7bAI(S_@KR6X}AhT>9mg%205twUx%F=ZL4 z2z)m<-UdFi93*sKEZ9`KW*SZz{RMu1A%54E%L`N{l_oI7ZJhfG? zJ|BNH4IHy9gP~3Gw4{1~OEzP6%AyEW9L<~PT{%L$+Q(ayUxCb3tDsCxCVz^zWonTW zRA>qoNl*4}+fq{ihf@hDtRYu3<8HVS>FDu?*3BM}BbbpA-h}{~LFB@I@RkmKn}>pk zQQ0+wO_&ZX1Fk?>InThOd@dQ$zwG`QO_AZNVh290Gnj?3F8t^*)=#x6*5r`>S)EGz z%5!Y7!A6Dr$h7X3uSwHH)&k+0Z6_gZel-NBjllm}qM<>?I2&E6_%FRPtk~`CAK)ex znL%Oy1IxnmmTmh%ayk&9`l|_&xlTryV()}8D)o82-%1(nep(qL7%CjEt^tbr(T?&$ zJHC@SWdL%E6%NySh9=9A%m6xhI(yh*gx5^}N*n9)F{o47^i4Y1zM(GzEwS4woben# z%y-TyQz;LU(bdwfR_b!*`vYJnMY0-3ixwEGqae*G;J2ftp<2Hgl8Sqw*vDIOHW~iY zl5KtTCUDs-%Ov7`#nZ8d3!oImB48T}9Ham7rW!Yjr_guXP-=W~4g@5BPDGwFGe^mz z?|~z=cvqT&of!FZ>5b+ANLjU86Cgh;7N#!?a1!qE*hwcSTInC)s2{u7r=K)3?faZ< z41Oyq-;V!R9&%;;&%B|rvi#NLB;3iPOZ+UMAJrb$!Pr^Czq-xz!MNtamuS(W5#K{X zB>k*C98fJrOwtY6cC%{GUEw}T>>$vIGGgU2GgS1Ly^7dVndqL{vl*~JWg2{P;6gAXjG z#o+wZ#|XLY%K)c(P8&11Pu0~B8=*~=;h!qw#&dUfDsM=LC<#8=0lbHUnd?2Y(yJK~ zUWKy=yv}=_tcxRRc!`59Hf_07x6ir$`n3O2Qo7`w31VW{7?QG9M(Y(9GEXZANvbc= z&h8cve{Y~NXS=K!NDZgpKitE5pXx2q3F*pPFe$r4%Mky@gO3p`ETN1_N@Un9n{C%b za<{O2hH$){9xpg%^do(iStHR}I2=xg)fY8g>yG^#^q-CRYv`wK4YGf>85p3yO>i0u zZ7Yekrr4JJ@-Qmu5b1<445H?|KSW~`Ts<6*MnAjzL6P*`g_#93jgssomR(NDIy=kE z{2*=b!Zao?Vrh3*>>WSN@5yu(hG;_f?hNPSuY?cq@!1v6ll4=nEOR zOSOQwdTL?bYHywEbHF)w=#Wy%kvmoj%|}Uka42PCUCxfP9)--V))ne}25D?(?VQ=E zho-;MATi&k6nlsk>m#r{>^-oebBIdH6J&TNREMU$B0aZ79F#jqbAvH~!}7#}iPuqM_5_TJ?>5(WOn0+o#uM_&rCtvT4hGquR=(h6-lKngkr_M7w=hHds6+ksB!!9>qF zLDU~M{}5x-St$b?>`X&59+C|5AKew^d$jDr3Ip^E7UP)>kKSuXI0oe4n-p|JFk5qO z2$_?eW*PyjvL)j&2(wECGu4gfUY2LnMus!z5SA{FH4p1#&AeMJEVropx7Ly7~IB;Zq4E36ceM2<1}&w>)ooRIpki; zI$1GNnU4S?9<|9?x~r4>VEuNpLGwI7aNKps)Uip|8aVsl3l{W=n$Z*d^y)5tGKW`^ zWas%ZZ1pMf)|zmy##TwYLnvh4M95OfBvwawaKc$3It`D2d(NH-M&TS)z`lq-kG0E= zK`I^ye!I!wxN`F;@k`%v(*VeJW0^*nyYA`nsdBt$42mj(lz#YpEOsVvb~ zU(0NJl-s{6yuKFsCQR>F!3TZ_^Oj)+j+T089Bi#hB2DL-zHd(~l zB$n|p;!3_%frv~EvnhWrp1-;VxfcqyzAz|$&xYnooO99Y;!Bdp`t*6_1QRH5PWp^@ z%#%8Y*rCn)bvQ;C&SgR<1nlK2q$>V3#}Epr>4K@Isb?I^w1AQ^DBe*TUIxH#ZkxH{ zPj^J)cFo-itkRoafoA-v9JnV*RYYJ;8%4iu)b~Y%n`2jfh?cK){blOO9Q;P(Yt)sK zGJ{IXh&lk1NC&EeoHbI>YN^^xbBV%YnMju*VgvRSn_raJ1Rz!jHt+AyZ(s@$?HbM| z+`=`K$n4=v$P^My)ynG6qcs02SK z+xbE3c^UxhY>*$_u6WBp*f{|;A$)ku5n0N6=-eq3fd+CDX#QS7#P=vq`_?KH;+H@T z9ctk{OwUn^)}L4}2~K%(q`0L9Uc$RbOw(peW-`pmLnJqU@J5r(`XO+AzrRPncVae~ zDWU1YFl)tu_BkGuzBSK)V~Un05N^DGG;}h~8GQ|4)zHH!y<&J1zFVS}hmg0Ujf3`~ z&!TcRy{;Z;jz7zbP9x82Rt|9%B8RQGatEWY(agOJF8&Ci!sEVxM~}mII8|3^T9-Vh zEP4QAcv`!MiMhYmR-x@!PWcrU#DaQ++&8!M(g~nYnuKPHCaGTSub-i47o~XV1+3#X zw2$-}_P^7I?Y~cI zpnwtUUkh=0N}i%31C|ECtjg~qjE6Y6>j~}6zE1B{uQoIy(l=fSzub|JnZHe+N}Q8{ zuT}12>9x)ywY^@o`XUF)HU?sT|0jkC8ZWrP%j8z?fhhygUC$2Ktm%GCm7I?6hZJbE z_y2K`PV4Z=r>{KNFR)kKMI==(N7mKE9^wzEgBnzK^CFf82bk!Jxs()&X@h>2!q>aA zteW@~{_BpSG<{$uff}A(-P037hR)I?q29x7XP!w6K$QvUTZx{=D)aMJ$zi7u;mt>< zKX}J!=lNasDjV&0&tg}vX^uGZg1kZs z^@isSLY_75W^D}E+Z>^2Eb&AFS*^$~mqr5bNKGJDlfRvRb)Ch#xG&${)7_>xP^Ve3 zB4fbAn7_J&9Bm3%r{9$nh?r2&8KUal*pze@UveU3g`Np}jQxm)?sJ zC~>7%0W&bMOVFzvRHNwR0jyTL)@DRst<&0BekT94 zOpzt(V=Xe?U*`^8xtOb)rv%jd{t8G)@JTL+%DZC9kDN8Ra#$p{;z{*j$&`+8zO-cHHXiPe z_ZfhX9X7F4L~y7R1ldJSB1ebNF>ApK6SJyPrSE#Cj|dYu(<@Bpv49cA9Ob|ciJu3Z$sf)z=h5DKLWM2O3 zS!~&jUUq&mRuz>FQs$4lY!-4jXUJzEI-h$52l+m%c)*)1d5hWZI2aiG1M$(`T4y%i zk!+FVP@22D>A$AeyP`2!a$U`=iRav*Vdtq~W6@hjr>!*yUoljaL$83?zK#tTtJLk4dh%cc{5pCTFqx)La-$Z9jqw%VBS ztj0l>3Q2MSRYvMZ(l;n)!{WX<6u!=AW-B6YzU?hDMojS~9c6#?$bE*uXwk8_^vgto z8)-7{voak#WHnYwaff@6@2s$`luXHxYqcALbd6V@U5ocP zQ~QX_(-keMsgks=9eq)ZMv!Ff*b~+A?A-5m8Usd!wAks9y|Z-5;BeHf<;2ceIk{Dz zIB|wxdK>Lqml*pa%n^MaIAv`VrFgH~yhN5g5Y<$Ca6JjyO``X)`O6EFv)zmfr2`uFdKKKNo z|Fx#xBn`MA-$h$BXI) z6)*nS1{=NA2f#t4dSIwAWyGieTUrntX9f>&I={mzHv6%;NQN9l$Zmd9=SdN1M^Mi? znFy`ANGl8-AYA_RE2w^;$BLCbqw7%|2^S?v?@jg)$y9zemEUF3KKYXM&NZQFqtTnjv|tWA=@MFoWjtPMPOlhU?>qJ}oH@!1={M9%YTx zta2n9R()uW?-lQy+aITsrQ@^Fj(>H&RYv5I9p^*tL6w#c7O2920M`}uka>*oQAB@L zkR8@Y@!wQM*Dy4-VA8P+liGcL^jLA@ZFrbJ=95ww$O&&;*4B2#sGGHD+ez16A?Z@) zh-YcGhnHVRFDu#qTcbsK{ujyaGz{60aQ5i_#B7j_vuAN12FwRd4AqA67*fZ><+Ocs z`_+%4`_{|#AXxv+g3{*vT0~YPYANWYJ$!`Y_G1^e+yc_$aJzj#H>IO1KQC3C|OAP;-RmbY){p*E_1& z+_R2l+d<9h!EXal8<``evP@gN2}y8gt(*3|@gmg!9W-Te%yM;2%v&_@%Z#}VtyrAF zoxMm17Y8?&!tM-Oj>v9dvX>^@pgW8pH(CJ6`YyJ1$d27u`|nc=;5^Q7m;*MB?y&~& z03muguR+8yd3~mBrZcqrmjvCb3Wz{yy+<2*mN7_y_E`5}pe56!)03!(eDNcP$vm&^ z1MYsuw8PD$u!uAy1`b!r7kON$urI2o-3~`nO*-vE0>U975 zq=<^;%CMJtQj9 zO!Fr!Hw zjXN+&GDokiX;qM;tJBD)$@107AKFHhV*7RsO#&Pbe_$;w_I_HvR^9Z?w4Zw*)TtAJ zZwtiMBM}2x!Lvn!8k2L=RN} zG?13^1I2qi1`S31Y<(lz52^8)~jboC?XOh3XQ-i-fpuCh?%+> ztMsY}tZ+^5=+gli*12nRuyf$nlh0`^BEgOTO|R2KPhWc#Ac@$Mlc1deCF8L6&;ENY zSpFqcnS1qeKDG^;{iwn?QXt}F>5^CQm9(VmxS_{NZPOK<=PBadK|2PP)!eyo&hiP$ zGBf=rPMoOD)BYe$g^q9i_0TBp2xTbgi;F$h_LIx&Uxdq}+Z5#h;GqyktSMp!)o zpy;sl31(r%NGxNA=$2s;U9j?GP*~s)gT=TxQ7}%eB3I0hiFK&SZA66;6O#fstGla` zisSW?bF0GIk8yZ7q!_*(xn_+*W9ET;kV5=j=&YYWWYMi%iTm&pVw&raltvk51ODXC zHosXMh6b@4C0lI2JBZ+hL5}8PI+!X{3RSLKcbJW-4^y2;-;iAg9!{9?*^C~vqWyl#y`ivkU4)Yo3qVrLWw*_lbA}`pBxic zsHP@q2Ez}?_w@s!_s-d{{!Xw~J}*v9_&5{+a^|RqQ;X;LsD5fT7AR5ybb5&dbOkfE z0?C-r$yZn`_iF$MY>P=NkqQ|O`cKcX7Fs~%3-4vxy^V!nOe2s~t3EtENlL11Mh_`6 z>*>Z(C8pGR+e~Zk|7K|~VFa7R9kbTzZA!eGvaSD&Nqw`G3IM|K5J!0eS-nRlPel;Z z8qfS_hh#J+ZXZ>dwIzrt7-fOVM0#>K@8o~nKcGJXJ)Fq{+%)sOF zTJ?RKOVl2Y`iSKUU17Que$5oy)8&e_(bq&P+%~y~~E; z^Ggw(UA6FQ?C~qw^grjaY@D3V$;tXAaO%?mdYqmVTD%4lT1@4QBGe!f&#vEdTDvJE zG$;w@qtGAli()0v_VH%RVS{yw>wjrYHgOSb5%p~lC@8R%)UpB74;YgpgAvs#mrcX5 z1j`daN^LV@zZSwuQ_`91vOTXe3WwoVa;!@-`)N4&33F4CNE_~`Z1_(AHCBbEhk zn&+Nuu2NT~4;@4&=j)^^N2h-DptAbqQs4i%(YCSI4)w0D&(skh!ext{Tqr((^Sa zs#bMvsUNH17vZx12gw68^utg(g*<}3eRwlLC>gw)=(D_a5$Xd3gJ9i{4q5C zVfH)vI-)q%o7zZR3Dp_-!(*18Ei&-k(#}ClZe;{68j7^12D@G8V&NX*{0BrWI!^S7 zV8hHumJDXj+ujhhDyeH*S!pfk%Dl?bR@u7!ZrKBS{@(6#sU;)ZAiV>>%&B%yj3~Y& zZB&dpj2wlQd$*~uQs6x6)aD(aEc3!C4nR%X1ek}m)SGWP!`;sLLnkPv;9i1vOdsIr zoH5UU3v&vgo!{b;;x6S0=ky@F6<0!ctzMx5@Wv(YnC5P=YV9moG+Pj2!CAM9?R0se zo9OlxM~{zSyCnyCW5Vb+G4EF|N$!3r?YE6Y-5t) zuD(?3gCxS4S-~^YepWFNSE(5`dg7wNC*bdcg{7(E53T;gU%~#JL^onEsWP7{oZwSD za8HPr32$ZWH zl69K$iO#*`!dlNuR!OQup)Y=Y+~WP;7?J-s0Le(e$jr&{KUfG80V@Z`|9SmC6%jTL z7UutL6a9ZHA~EjZDoIz3Y(dQgN+QKlA_hy67DPR7da42tk^u^d@gZoD1U-~J>=#r$ z!4MRx0?Cyw@kFAc7oz)Mu6fR{AAc>kx|-CU=BF92v&?&+gT6!aA`*~cjloq#@f?Kp z3=&x7g=J-+V1R-IjD`pjDE%|Gk^LS0f2+XlGY1$nK%vRM@F7rOa07@gl?XV1<>5j= zEjzja28;w6N?1P9SRg==K>}@mV1*2e0;&<&FhEd(KraLw;_cLg#3+YAEP{fF4%u(~LidwghYl8&h=}s? z@`e%AY8au8@n^^&UPKPD0>&I@u@3=50cW(pFNC%C{56ok?SZAS5ZCs>kpHQfkOTdJ zAfeDeP~t|Abhi>1IKU((;F%T|K(O-;$M*HN_5lRG}ihS}(H2oQpUvw;ZcG?Dx84*>)^1a2Vxb&G@ouB5~SA@c`$ zzx4_*Krus5#)x!hyph@AggQ-FNToqeuA#(^8vUNWl@KsEQtj^c3H(E@Vud^jeE!m} z5G2#T-LUE0TEj5^9Gt_gD}DzMR0903aP~R!K_o6y)006EZoxvl1#v}Zk<-134*H_^ zommUO`SDqxV4KOC0pEnzhamX@@M(sD;f4*j5B&K4vqQ>20D=Pky;L(=DwptDwFuKlH^+O_R~* z#U*4=C`hOPfr11NmHM?qg7^53FoY2NFW=$yX^VNGJpP;i=nabg=r)bvBi;XQAn@(; z2VWFHEQbPn{>`{h$Adsfy#xK_ef&E^9kdg!hY^!PPkQxHXq96-4VSq~t$N3EMt#%W` z7JPWMUL$ukxoJeiz8zbP&40_g=b+F|x$g{g2YEd>m6b^Ae_yuik9w?!BeDOfX2`S^ zll7-hwB4HHC$G(%B(nC5VKZ3~T2ZE4t{YM5v-onibMC|Cq+_&z6SZt#H%jcB;XMv^ zdGmQZEOpH zDa)bkNuXYxuSwIAIt8K(w&nTFZm%Oc8<=j)CU;F6ZdeUDnz@HHc6{n)%yb*vmVX)Y zd;X+?l8>pI9hQ7nN3T7_*RU@0x>gI~=sOqzzLCkeR825z{fTZwlz!J%?%ldaR#dmw zc1fmb_pYi1=G>-$b0+JMSp#piu$fx%2fuH&a*d*F@$P${c(Pj{TTK8vNqy`2hM%Xt z1p@C&RT4Kz3QOR@UjXxaJy*=%cmBNl5*&MMgUydz62-FXZ|R9*+0V5#Yz_CLQd_sPS0v{`-!YliOC#ZNux_9n3*lZ?&G`yu^bCv>37zJr_+m^oLKrP?Bmykp!!$LHvmS4hkma)-b_eH%i&=> z_<&61jPdWeJsRM5NA;0=0rlC#%6z{Cs3?JRj?ObeyDjIKi9_tF+)^Ptm0Sey*UyGu zj?QPNw?gl=D`|F4oLFZzhR(Zbn~l3xXSLa~4Ly`A*eR`!Q`qGTzg`BvG_#i(v(~wTAD)*!OSM*8zYwz;(7!{~a zhHfSE)bCoP zSln2|Nt!yhvc2#$RWNwF#7}-+dCeft7YB3Xg!qDZ;?BDg%~w4H`=+1HJ+WFCp}tG_ z?F@D65`|(u4Z(=XW+iY^S61r!{^;n6m%A%XB8+3oCEuEw4WK{vdybu7R#Dgq^xH-q zYwsD~6CFfmTSTAmNQxQTBp3x$1>8gu#N(#H zGY34817UqYKz@e#Cw4*Mssf0Kp}fzRj9t@ zV`X5Xk;I$dAH;lG^ON`cTjezS$J~b|_f=DV%iWlY>)!Jd!N12y{r<#G1a&a;Fx(;7 zU9Rq?%7g}7xzf_J$4q5GWAjwzl|;U$T#pTijCaG$S)G~Zj3gxgu$m!<^o6EME2-VW zIi{b$6tQJ9oB=9}u9db(CU9ITk+uVCp3Bs3#enWS!tjQ0QK(=UMvTJox(eDEHtrL` zW0#>zqqZ-C@to-K-JmjRd9?wy;i#@bi#xzEEHB`UY3G(azdI4Ce;rI2ZnWPOgDNlOUr_&6WZxa9E z4MeGD-DA>>NTL$JuNpx_u!XmlWs~*nX7I~F@l9xndpk-8E>X5gE$B9>CW+Ho; z92%zq77v2yzx>r2FJ|g}>-@tAIE+1gsn1(Z^;iNr2j$SJ(DcdV1F})lP3h6*FD-TI zN{wrou~92IUPqY)3EB8{Vs6JsQ#9|vocb-)f!dPN8r4*#=!2#)|6vgHzd?XTvP2Gt z9O<*@8|bd*6p6xYGol*UQ9?KD-fC~lts*uDt(GY=j!Plt^5L{LD(FZ>ctu^LW?sF{ zO8c#3CE_dmY?ll4hCcREfJ-sondZA!EkxB5SwD_|>6%=exojbsF&=OBXBI5!9mWMD z#a*6g{&Or94MIN&{jCY&vCzr^CTxY51vKu=S zv!T%3WArYyX@jwiN!RfykIwbe?8ycAgCKT z7a%3bl?}=*9I#YU+D`IA-F@;lrke_$XRQRs5ACmyC z<9(8gt<*C&aj)x}bS+$xQ3{Cq#GUF-9Q)VH)e%{L5{WC9M{YfjlR|?g**1HhjfO1f znZp${`90n5h+qP@Kx!WC$1u1z8yqR8zPm5NSzb`}V=6SI(2Nc?I@1bTe z*H~HyQ(X&>kuqP5DFam|s`6u5G!k#~1w~u4CZ2-9JyIPw&E3eWUeeR}=N1%}n6IVA zci^e8F_+nBZ(3kFP|3vuxDxP!J8!&=Ppgb|{ zq$_{e4wgA9ODqM1XB?BwRS&EbAQ=88eK@OZl~xN6Z_2SND5ynuKq4$7TNq<6p<#P# z4(ZW;)xXS`3WThLX{HDv%h5~S^2|0#QmL>u{d!SkZBqPyMaQOOtBV|dV_<93duWVl zUwiK2N5F3#6n+D?Bek-PM4b!oOV58iWn>Fn;OM(beJFig7aa^r%~VQ_{*33s$p`#u z(K4)s_%EN)lEEG{w5xOUZQP!RCBa)269&itw}^zY6MM?>cF|;v5$aw)JtL>u$~DEQ zVYR!Uz2mQxKrdi*x|_6n-e!htRoY9|VsGu}?5g6O`1qeJqO7)Exk`v56(wdkGjG+6 z@GUhG5a{xR;;|=Qex)muiP=j`=y*LERlQqddd72|{d<&V1y8*7bZqyd z2M;bs!Ff7lqGMczphxrW{pFbph=f4ik}8e8Rh3RIXko*}Wh=t%HA*buQcmogZxa8` zHw+FZ_wD1Ow|FmIhv%<%AqtNJ(k824_2DpD&ynZ?KklrvgO-)h!6^ShnV}9yzl1XC zMNCROncJluf?-kTlBX`j7V&eVoa^5|x8`EEO=gcqc6Ru2tB#}nYLqMcH-CgnvDj|K9MwpuqSr*Lad(I18)fh`)c1}#GYpM zT_5TW&B4`leR_2JEEmKb&0)SLz?G0H$yQ+*{3~lr7~qVXg)%j%iE462M_>D|JO;*lxh}e1dmFKf@T|7g zwmCIjXrQZridy+dWn*K_frY)G#fKu&)L^bEk6W$M6=Frgqso2}8S(}V_h;i9P?#Qv ztI5M!=48Pa^<+D=d_@YZ15@TY-u4kqxHL)|v#$I_Mmv))n^oGJ6;WmASG2$b16J-o zgw>Uw%=L-l*guIGjx#5N8MI{x6?ZinCKoI4Cc-BgHI0Ha?Ihd+vCgqsgL+}K ztjkPZY9~nI>iwUsGh=_*mz0Vrq?ytVuWq@9AImG!7GaClL2i_DLk`iRgn_rfCBVzlG6qtv3r&aQLUrXtcP=yFC282|N1v6^GF^8w z#%4RF2E~nALPOWuf4%ahuPVA?ueX}BU-5arxV_qQ*rycY7q!>vkp`P`ksMTPDO@+J z+Fp;=acMeI9lH12`7ROsug*c01(Ch&v8q4QtC2yQGx($92R|gUFQ8{x%$(d0kz^g> zy_+gN=G>WT=$aE4-yq20ywfNurXN6`N$fSyOma}Yq&@F=`k$6=vPZt~J5?Y`g<&qr zwW_o|J)n0Kg)Wq0j)=T&dy`?US)5L-i8MRK!^Msqm(;;Zv%YJHo>eA|ZsC#{oU-Tu zQJgXdKx?MQ<;-+eGQ1uEX@xzeL4r>qYR;k@cXU0fI>qJGQZYg2pdo#7y`v6Iby&CF z*`3Df4;NloE2PB|bJ6eaZAZ#&~&RRgZQoNaGY&6koKlP1A9hd!KjmxHHti{+A+ zaiVP0x=!Yh&E!Cos6$|FX~HSrVClIUinJbkWr)d7jsN^!wxgd%j$S*+6TwgnJo|OBHIq9>Z0?+@FL?ALJ``?i$q@Wj>0s`yUP<>-9f=HKI~WQt$Ld{ z84`C4fxHc1fii<+=$BK^Tu*m+oNUCIt~5b%TE!>c~taqKJXydDcfg_oD0%hClo6R0xT@aj7&@-koI z&>F~{N65Bqc)VhE89&@rp^zwV;Lx$7j6f(-chY;DJb|-Mg?G)-X-N1yL{l!QRUlVNdN8_`t-TWH&aij; z(qdydo}yLXB1oTCEetcl`g>k~aZb)FJH}gGJH(*;asvgHwC75`@k2&-WpH!v?3^XN zXh$4da*H~zOpA(M9fcRFbXs}z%F>y;O#Q?-^>tXP2wXS-MfO0QEZ3{6eWOxX?O#c# zZUEuQZ}|`Q&pfJUahg+zR2CUkoh9A?;u0Y)X|w(GfT>9fRK4RJw#SwR?(c~;-5m!8 zfOp6YK^1PI=hqL5|J6*A7KXQN@0VVHMvpYQg{oMv)OH%WwIi8Z85&?uvVH67toKJv zQSV+c@5G6NyJKZIOMl@OyRcx`^afhlfy5TM-HW0L?tyDGEMsn0=&*#oV-q$C4{9zyelOJtibBN9FMT`c(Y)Ne7(Cd*6CU zb)z0!>)*S|Q6GddJO5*tvEsL1$+yauZ{KbDqRN6TZj0)?h`?jgJ-Xf2>LoDAo}$(t z=l2ld)OjpXS0UPNFm-L(P?y#i{7I=vF#P>}7v|f-msgIC_PSj2@K3ypB9~wwUD>9G z%Y^kC&u3Q;gfcISpWkm&^{}q4RTtvjLv-L`+pmAOz}>Oq=M;}7;Uu+6IR{(nmx9hb z?7eico7cVs>c-xouuj>!>fl28GlIKI(&;j6V1&nr=2hy_+N)V?>}tqV!o#goI{NhStuU1RY2CBCS4oG&eZp{3uYpEm;DX)%BhpY2f;!)IT#d5DmN#NQ86M2TIJMeUpPv%xFv11&V0FE#A~a?%?+KN1>sksj!KNh zW%m5{4Bs1e|ICWAip?F{Svd$qIkoQ@RsO}GgL^7idw0|{z)NX@*^^G2OclQ*LLaSU zk|nd|tHO9*hc(L<^c#7kJSn+Lf`%`6)0pa(TFv}Sf2^no5EY71)*W@& z3GH**1DgU}c9NN=Q}o5L7#UY6i2gc2?fYhd)l@u!Tl=hlX}8jGrrqenfZK7!2V#p>e4fJH35i!oxk z+Srl0@P_Y!H(mF_(7q;-m~_nC1|I(zdWyHeAzSQWE92Yrf!_co?)HCMnXwTt5ZD`8 zLGkeX&ywu_mz9|-sLImM7aIkUjG$17Ve%qFXE8~!c6?$(j4cGVO_5-yh(ISdX>ka6 zJQ9hBpb(cxCw2nDFLUnRlfU1c_v}}0PLnVHoA1s`N8J^-oEopNpD4v9SZSo#!Mh-k z&|?4B=H?}VVSapkL_mBzLqO6J#J{HSA6sw-z7WHD2^OhOf5Ka10|T7hQkc<$z)cGj zg`o{R2qeIu;SxclMIj*pLqfuezCep;76r`fpb(%I&;Tq86d36J?l?D>F@ggKoZi{J zH~~5cb_5bq(t$T>obq#kAp$}J6b0;P;eMQZR6+yqd_t_Ckb~{Nlptxez#&d4XsFK4 zPN)FfdLRoJo!Bh+^T=Vs05Ap`m?NNIApcmHWkBx!-)J&`eGn|d`1L(F;bz)d)aXFK z2QY6Ekg&l+;cP_(46ukgI2M&Ppi8bng}wo;K0u#-{xo0^$bjFZTlwcX5sBqG0|t;F zHwTcS?F0&rc{EFS;LA!Y$o*{x9{~oaPh^PJvBHN319XN(Jey$fZ!26F71d?%payFVQW27oKn8MxY1klyZ_WPk9mLlu z$WP1Bx&51q2se<;!?6HQVq3#^`~Y&aYarl5hFJ#txxbtDH%I^=zyb*fI1AulV#NUe z#-kaAtv&PaUq%V`{0@X%KZ5-ExjFw_ng^KRLdDnHzkdH34Fy?w#j)|^x4H2@M=HvK zoq*hLA_9WG`g8;Y5)vA??_u@+%`@gBV7wmig_W?Kw z?>Bx39@iX44@`@q2P1(W_GOS)?XFD*ip7nCzMe}C20ge)3Xa^xZvsU?!i7CI5;fEd zu;5EVM}*=3c4n>Ee<<0!NT5r?#tHoTjPDeL1%HnRs$iZ${xJp*+ut`p#t(@@KU&9g z%rNwo{%-|ALHPyzE95j}a3IDE|M{AJAMZ&R^T;7-lqjdKQ9A;HfGAku@PLQruV9;n zi~)I3Xh|SYT!(GJVZY75zbV*<(F6NYe?*|Y_j_mhOyL9D1_=G{5LiUW7V4<$?>#~Z z11bIu@~@L_i|)#Xzr8%vNIKz@`$u(*VHcLjnIn})cLJ4aZnRuda(m2XVsE_Ym7028 zQGQ3}in@VK>)jX~?_%$qt4|RLw#Q<)f~}H4NKGz;rNILK1x5=~RPdng7>>IST-z#r zX;xomXNXiGWAepvPFEufS!%YTmEhS=VH{rAcEqBLz?RF%7$8ANCda$d!h)5t! z+qP}nww;b`JLy;*+qT}A9ox>|-{71&gMVTAmFFn=x z>X3?TC7)~x#kAXEjVcY7!)x94NQ3^O-+Fm5G>jM?j?Fw0V)Zoxt=nd~n>gL8T z@Jla>X0~#c;W+!okV&dUs#cVoEU(4u)HKiK3DNOdLFV-&Fj!qZm^`wCFj!| zdhJr0y~yom4ee0lK<|G$SHi4B7=m1ACpbRktokrC>J0Qu>LFMN<$uRHkT9qIy)hxA zCMI3dhh`{qGpB&v;A@C)2oG9k$rc=r5vkETlP*=WY3L_S!yUc&B0Cg7 z{+p2v$B6>VrVggtx23mTuA-P~9f~s(OFn+AlTYXq)u*Gz4dEVtQbl`eP$%M2jmbtG zt@w*S&G7L~u%I*zPtIbw_!v7!|FOyxtdCSZQvxP)d)*>3>(oC##w-ZyLGbYM1v~u_ z<<6qTuL_CLl`(-J-nC{$9S`4EC_x2aO6WR8Ydngh&eM^GX7#}fT$kKk7p0d*XRQSr z3o);P4s@xKY)4+@?iI|8ZuSv(L~=#$oFspq{OikaKSfsC0$?#ohJ#*WewD(BkJAaJ zJYmaVOv~#tg*pj$2aJENCifQg#Tz!dbeOzbr`&j}(dNS!zjuj@BKAnf(we8Rj_ubz zfuVqm_yDqkbsCN9%HPdnm&o>Pq~zsDubEZ(X)?%=!JBLKdTjkd+XW)<4ktJfKGM1} ztLns%5#s5PCc0>DWW1}?eA+JqJYhgcoFGqz{0A{!wPeQ6x3dqx3>r}(n}i38hzJ#t z1eyJbZh2U^J?5#+64$IpG|&H5els297e2<+ECLK^o>O!7mDy4m#7|TbAVMH9R;mr3 z%Ook$R@y5vy-+ZQzOy=#P9UeQHsG%iXuyV?t!FH(=C?9_`8QztbCOT=*!n@+?=TOV z?T^N+dAnHA5y5t5yxRxGNBnd~b54=wSb5>0@`TRr$p*_rStL9Dr;oJ$%JCUTtUwAI zS{c*TZ@Wrl*2npbJB3Q~%Osc?hpQXVa(zZ)3L-j`k-r9vv?)GDx^y?Zm35KnJBCJL z-e*nW`mV2!PGyuWGH>r;2Z&vi{j(~NO2HGE?n8D3t zxW3Fs^#X2vDhSP|sIXy`B`U{cKOqbRlG)V0q?^;Xt7vW%Fxjc;ZbaK_&b40LOS#Y~ zt`&i`gj-|26eSaGYy;n&WwmD4x|1`55u!p3O;_D3<{9}COu`uX=j|;(k6*-Zp3Cg9 zBcoX&AqV|)pH!;SS+05#cfz9WiO_4FOgT;|+s%1q&BR#@1C64xmn`FlWG(1!k=1VV z^lXsi8YhR`LB&Qctvr`9@(|v3AGt?)djLQ zB);ov7>4+~{eYxSch|GiN^*76tGm$Le)R3UaAx&|7L?id9*~0@!^pZqG`9m-nRq&z z7`T5Bz!{|5ql3`ombM2Jrys(uyo6BBbQ}HOLWmeuanB~ml}>7_;xiHohM=e?ZhNTs zWV=T5s4$7IJC+y5=pkue(j9;9SD{}HIbA^4;+QfVBe&Yk^9GC;gmVbl7niiXl}Z|g z36A`!3n2rBtgovEhdepXT<4Y-w)_lfmrq#v6r~8Mp{5#B->JKPk(C%U`~BvN6A0r= z_VZ)Z`C^!RgyXX~+;l6}?h*GlI+WZx_mx;tSdGtr12ZAP>6~zOhMyoQ2tEhpS=;x5 zaLbN#cu|zv>{*U+W|d7qG5SPvtzmo76t5PAJ@c;-hAeu)Y+gwug_1Y+z#<=t zbv9kRK8qZ@0;xL67_NFY1V_X}soPy9LCqnnwBEP7p^fYz_hssGs7QAzDyvj?zjR@G z8|OVRZE?&xuY}RR8849>D*d=2xc4Uhn8p0{*%eD6q}}^yWEv?;J@z-j0eDkEmKh{x zl@9$J`D#?ULRJ_JeprvW9QfEm;mzRTA4f}{`N{mu-IE^{ByR9y1V%4x1@1M{NU?*>H&Etq$vdzSCmfiEO|c*@irYSncKs5rIh zszOJ;%_H3muet1x_TZ1S`S!0c*qlbEqZan4b=Mpqm|)SfijS?&jd_mgiF??7U9bJU zoigNV-olL$K64vSoZ2Pgoy|EV-#0!nlPnBFDd%7);mnSle-ch<)i{3LYwBoiq8`gIg3q`D z(ENPi0mjcH%dCObjQqlVOJrP(QWnKhYwFY(>S%y`Wd{1H5}TE}d#l)YRu3dYBc%jnRi6lkK z=sX>wVyk7xbaq0p*t-54@7|~v>-TS6&L|Wzs-?9q2@aoWIvj$|C46s=;Nlr__2;x$ z-7TK2#LHxzJB-54_4{Aya|5!oZ5ZPekJ1Pqbd@BcH=8dY0EzA?7jm|UHI<;s0lkUi zA%Q4jJl4^PfleH^2s6@YGyYjz!7V3Q0yQnIL;AkfOG)-BxlT@xNvBF07p1fH%B;*& zh5YJP2<^Kj9Jqtjs*(CC8xKVV3F`cpMZ*)PH)0wJKlP=L8H^iay}e>xWes@8xv&E$ z@pnA};5)#8mvAnA(k!B+OQ5<(=<|C*wg~^f1vL0`L?R89%tWj6i{4d zjJ;wLg&xpE=I++^sH(7@8h327Fl8%#WRF^vpdI=;a5ne@?#>o|pZr=EBO8c@bS8@_ zc-*EwSPm&^x*5zf*f7(${yFz?Fxa&(lF1( zn1{5LrDcv}G~@mphWi*Xf0y(1-n6?NO*W)OtuJM(WT4CWUtvw5!5&|&?J0ReWT1PB z{cb7ykk3Udim1ma?25cX0ra_X(EI6rLSKI#k%PBTQuN8-IRLKlN+5&3*|+^R_?OE; z{!q>UbWts|b-Pkqo`hlDQj#pj^TbLUF63B{(SI{(5latZ_@Rt1{KjK3{CyeWx4 z5y)p3%bxu=IL11?d~;LONXq{+3jCHd;hSFfzZ2WDZR`K|{pl$G2HR!I-jg%}N9 zG#)nJn0^$CP1H5-VX0iFcXR}0{&9_w%FazaoICqr?Jx*L7$3w^# z8Aok{DLseE^iw9yckkFol1c%&HAaQ&N>s39H6I?`T%gd4CIous?I>kx@ zL-x?Lh@gkWDk6JSw_PJ_@3R0@l&0*!5#^?dhHlMU*wRZJp`o>Dj4{>_H*Dty zos3mkKwjeq+34Zg#RjXvP})V&_!jQ2)oMku|NQe@%CrN(Hz!Rn-ft^XGxS zobgIAfQjeGvneG>MPJC0C_}6>YNVExQ&=a$%8Ta0Zdc;5o@Bs?>a{zF?iANm@q3azfc%MLdm$%n3l@x z1Q`M?VpB_+a8EDkQ6f1-F-N~P?G{+LoSi&P}Xv^FbvyhHnr7X==CV*HeR*3-F*XBVvaI_ zV|%pSW{hvCTWjU~Qlf+~i8od~Scd}oz}d>R^?8@*oA}q%m7eUlc;$EvG2p+{`;s`_qM9wufg=4m=<&sUOBmW<2BUhANa; zmz3@*us)rurGsbGYQ_?fo$9k^YTH1am|~Q*4p~3g0Q`)tbTUp0!V#+nx#2MFuJTaR z>K`%tc95kg2puS-upi+4AK(t;y;Az0q!_a^@%R zg`{NA@K^giTgbo(kGIQET{4O&x>y!k!8BI}v)|?KO|nnK*4gZY?e9me4{ltyNDD0C zT!mklKh4nfKK=#W;p^sL`b%wCRBx<)nZr;Z%Xm8C!N03CffJjf^~6lahFmd7fP#t;8-1A7F|gu6hRZvuqyk;>CaN6>V=Z4bjEc))RXjQnEfSnBG2B6IWShh zeykdGb1OZ^aN6>|(|dsII$C?!u8aN~KryC0mtda^j^7Fre7psY)q zYE6N|5nMZ9*IB0&aaZT=fR?0fZ!H>{mqcI5VT8J6Yt?RiR4L_UHCZ}_~Adyb5bT)bxav&AzaluY)YKh1NxJ&;Iq=m zr+OLf>v~*N#T%hmrU&jNqa@l}O?M<1upsJggJ7s(sZFS1_GRwxmNj=;TD}U_4x+g< zddlM*mi?jvamJR(*eW%#r>G=Wds7e3HH2wc+Duoi-f8J2ls37E<2t`@!1Dul{Rhp`1)pWPZ;SQ`?NSE9 z4SSAH2A*}eaKTKx7ln5#&xHGG;3A_oj?u}VM^?iV*M@!ub1q0PE^pY*xX2euC%5B8 z7S+TCPTR(j(AKQ{j?HxI?S@;VC=;Q@T8o7McKm#2EIyGe*rm1;^Q|62B;V-b zGim6&*v{*-7~FR4g0@G?CXTQ+g^~_q+)DE?M(v5_$PiRCo1~Yud_MLYacs(z?el*X zA?0+Zd+%(va z`Oc+>Dzfb0JvM6bV@_bh3|Pnf|3wvVrkZZh2g~PR3hjxZX=ygF{j5p7*{1(&1>~qG zA+C8-E<{a{-CnLU6NLt)(ks67Cjf=Tv@N4E@UZW0c9Pr4gYG9&4ws?Ck8z7rLL+3% zy^F|blAGJ~9`R<)K#MYlP#GGABzdh|UKfnJiO)OMmRDP&{&})bw(0YsLXVD`RB7vJ zaES`W_GekUPdPh(>!-lBH_HhTCpcw9>MsLOL^U@u>HFce1Y{ZSt+x*DC6(B+_S;9DM-GYDPA zKcr?BAhbF>3jscHv5t06=@%zS4E3o^)KxFMm%eOY~|L+=Z(;YyBc3v3w(D z-EdHLJEI6^ov90IP|TQ;+LpC6)b4T&EOYZc$Fw=^lO^h8TNk56k}k1uV|yd@-?L}( z|Gj!K$1ezEO^&P3dvxn7Xu~ei2u99=C_BNpvb_pZUuE~r@gR7EZS(rSS!P`Si)F^b z&cX423^W!Z7FH&%|4XR;e`97WZ0xLT|G%*6HgL7nxD5t5Ss73G?f-rG-npy*ju5Gk4D<9Jl?E^ekKrWSu8 zrKl>K8$q)8v(e+FVpwFAv;^|MH`ayI0lj3X1> zI3OAw0yQ{4G~eAeH-P}OwcozSkd6is6WJabTEM87L63yvg*3%zpc7NtVrpCBaJgoF z{J`dQ=79mPuU=R`e-V&efjR*?ncN_$(_3~y2z#*@7SBNNiQ)9~Gar2-^DrCj9o%=# z4PHJzEIHimETMWe;b&OD`K=BdK<s^Z zoQkZNL_l;6Z7o1Nogw^N`1HXHKu#_}zj8^0Mxak$6B-W$A!369Um*HNr=JU)exASa z$5-zRXDu)=h#)ChB^`AoZG+Nk`H>1qYR4~+|Bga2x&HaIx3ai_0r|-B&RpNf$qI%4 z9@&B;qA!PF0>ym2x!0rDv&-Ak%hI>M3d|V4=Y?yZQi)GTA%cV~EXkoga12OpWe|dO z+U(K(&bs84Ospum=?hM)Eh$^MA)(vO)B1yFpSKTUK8v9#Gs*}K_Gwt zG>;AR*wkSBhHtR63H{1QzUj!^4iaccnTXmCqX#y>y9xvK9eR3Ua|{gD-q8;F<^QAc z$thxH3aYiC(+)fxyxJNc8CV=TB2*p7@EE(kmfrXgSB+i`#@@f;^||VA#*Cjn_#gbg zKdnbUIf;L|dcOLW|NJce1TI@3v_9|rZ~!sZcHzDPr3&q_I(_bz|2rvO1KP^^;`+9) z#l^v5PZY`ZPwS5&uDyPleNRw&RjUIA$IrjE9+%o(O$)~hC^hhojqiXOpv?Y~H$$FV zYwd1OK_0yU+BZgYBtPz-JeA1>5VNfY)B~heupUyNVrmX-KgqN1BjN!>L*$Pz9}q^AU?gTg$s6PyuvY1JsMmiM zX&@4AkoYm831q|gw=fGvn(T}a38 z?|%cE{|4{>4etI8tp1a9{*#{nlOFy_r~gSlKf-=Svdw}}cGlmJ!SwXsq3!)Vu!;O$ z@ZXYy6K}c)d$(ghF98i&-{1o+z&~O@uAi3NKddFYK9-)h@?Xxtoc-sBV7OXe;M{?t zn}V-xcZB03cep;E6XVaix0GCKj;@JaQ-W zwC!YFeMId!H{T(9>0kOd?F9&dX%N>d1><@~nv%D|UuBSM2=Ag0mvHZl?Cn?;f;LV} zl()W%3j|hA6@9sOKk1#Hnw#AH9l1dadoTNjmlDbyEo6=KiZH^B9@+sxbur! z-+fI^PT$I(^m34tUceud(-{(A-fGzaTrZ+@Qra(f;Xv*n)Ak?mfs*@I*pMjS?-mOq$ND}ZuI?8@q%Euh z!K3~pzaWO6()W7GqVO(QFEocAAI)IGl%LR_rx{SFM-UyN*|{J(Fp(=8(ar0s5h(tw zR>^RR%2s!QCFZx;EI+};Cs;M}wdm+q?#d5T(mQ#?k<{M+#ubfE7D4W`Z z07Z(sbJWe+NY_Iyf77=J6Zf8BC^5P0V%~tc*?^6Kn?hY8-lIyF+->jOs(_L1hs&h9 zstbC3JcNREjm^pf4Iv+zuMxEBrvavRt7w`vK3kjwyxF)YtbBsQX;}C3cMFumDFAJy zA0KG(k20NPaQ!#V$JmE;!Cx17k2M8989#qMlT+K+eP|oQyB;*}E$!Wdkg{IxdW->( zMMkRFN?AFpY2Qn1_11Idc=>I1f}w{iJ6-OHASIkZf$7@e>|_c$R7@B2%PNf&EV(wE zcu%2&9uL~Pzpc1egc=@|Vz7RF=LW#4R6ZOL!ZU(?gco@kkPsi44nwMa+wg4g4&S$H z)F@}@#7)m;B^gc3kp};qYa)ekdUxF5^JU;k<057TFR}-Lf$VVT_g+EFKq8~faZB@+ zlklrwcoaPQlXtv7r-lno@xTSFe(Obp4#0G+1+^L?poF*1$(@X!v=P&JW%hK2WF?ad=`K{j`Plb$m zbu`v2Cd^9VZ8=NZP{(Lv*#`t>2=dOqd9phXl-J~iFI#riudRp^Sr^g;Rm`vHL{u~V2(110OYitJ^Scr!d z_@yS*rIVy;LBsCyD6fwg`?}3sR`5Qipq5JR+U%--TO>D4SWqINuM<1j!Zj@|)N{as zoQ(@;g`f3Cv;jmDf+GNEx#a`z+PE1mb@7#x#A&h^lf#Cg3ZcEvEDX;Y1TE3n9=#PB zA^~V3JGE#botqhu*QlQGB;pOvUN2rJ`;W1gY{m!XaIzD7x@X$9iZ0f5rCf8aaZ)mU zRcl6x*?XtgRx~J!Vb($=Mi|hzwo!zB8`VY^y+hXiOJ91&lR-1ocl|C^y;e$`UsLd33`dG|@nwI0n?r_B;wbHM-(g!=*oQoCFiovO(a`Y5P?V)`|OVj=Z@vxddhq*c5FpyS*9(tLps5 zFIQT_NDXx;8TwQcyR`lbru2mI54V2}Mr5;@yDuPwI{cgoq$p4NF+0N*CKo@;D*C%i zgFKmpUP6&IEtCe<=u|`u^(a1gNuV2FNUk=mz_V{1JkVFAua;#TxYcE3KE}Qx?k&p2 zw%9`zx`(Lu#)YQ!1%df`2XE=vdDGmJz0(wjYd@I+a7uWoger4;Am=Pc_=)K$O`>xI zdeVB4%GzMd><-fEP5*eQmr^PcLyv_ZI9gqLY~N15$LNB$NKG7%HRe}KN^;GJ&fP@u z+NW}-PyRxg!G0@&rQu{XEe7YgG${4$o;8b3@1x;_7LEYcwcDU042XvPM<(FMOKGI| zoSy=J+fpUiP1t>gRDM!(lY=wzt*ftT#toL~(gaSUm?LrF5dD4a+i`$Ex#-mX32*1P zf1*OSFB{>kZ!Gy1%p=mz#x`qCLzX$zQDh(*c4{%8F zZBh>SU2wOpG62;5H4RaFYRr5U1aG^k1d#qp(K|csFOvKtZOPLO!q_)xJdqpi{>@7F z6>9yypOe2eyds8CeQ{0qaidnHa@p}owqfFia}Z6(8&bwash3%XvTovC-KPBvlGZDl zC-nzy_t?!Czic06eBYEvKs4R{0!>oiw5E2amG<~2AqQI5%yLe+g< z(=hU&uf)rd`l`nTGVSj&R$w2y>l8&ern)ijwE09xq5!45&CxAIk<{iNA$65({EV}e zKm(2-530bgW7cP39wY?dq29;d*lt;ab`&Vq3VMPHQiY?wYWWvv3+cm?VtN77YwKH? zg-RX>1y+TD7mYJO!0F;mmG-pnF1j&ANcXi7%$*#ZgnJ9=g7XJs{jy7y5}UeVJ->*{ zHF9uhEVKe6EEq9EFh>;POw={kNr8x9CJW#LrGFP>#lcb_D^h3Q#T9A1t}5GG?sd;L z&L~GM5PRT!iP4m_h;jQoVdQtTs>vy*Ckzbctv&<31XP{UVgLHlDn{m%J#JL4UrdN{ z)6vbs3pTOcvd|b&&K2^`>N?7<^fpzWk&egBW<5tpF$M<5AP#gBR zkH#cpBKt+ALbW^sZmr;EhHC}jR2=~dWbTJMy8%8UJ_H^Frg`W&W~fguXu;L{6!ioA zQ%>T@SrGV3ig^=q_muQqyAoE#ZD4H?3DJDw8H*g7KtP6Dd=v9rtdZMx&|T8k!EqeQ zJB-UZ?H8;tc-WQbN|Ik%f{BS&D8YVIFm2yupUMr#)|vg>>e6(A$SGZ{V}z1tfH}Md zQ1_l`MKgc|F#F>o$uviCnk;m5b#sTDLZA6P2pn}f<7b?BxYE>kIZAPCpqw3kNyag1 z*Pm6vJmzqnHEaazL^~m<41uz@jwFq+#z6X%T#=LnW|s!dbjyW(?CZ1t@6Yr&5e}oP zw0b<<6}gEil0UPyjdYTAyT0HiVlg?gXshF3E|)Q@{(-w?ubU;;dM;&PI~oR;DcmFW z?}9=RuojKlV=v(!v#-l{0{>%5fnNwYf7SpK%LeB({qG~h0<8nGn;)IV!2TpLTakm5 zK#VQp6Nd+oG8oQYej77-j?B$5T!v`mt)|WSV&Pz$q6xZ{WmF^f%#6dYyniDrvBGV} zbESj3XG1H+K8(&Fb+}495GOMh!V^JkFTm3o|LP}I8&jhlpAk+7}~G)B0ee^SChxfUl}YC(TT2DBL!?>c-E)HHx6^n*JpIWc1&YDRnHBnJ z&E_UK3d!8$?txl~pdD7WmZGn$m&{-!oTWe);i*tI7o1<_fD%2gj*2gyoT=|n{%hY; zZsvi5wsiNX)F${B5X)mhyta39u^>mE?aprFQLuE{38qk6-pG~BMIkyxdwf7Nuv8vN zvU+_C7gs^5!A6DpK_kUk!;p{NH^pRl=E4Wn&&{D;Gszla$Tqb$8E$v>P$NMpT=zG5{eDvt>TTtwNjXlU;K4KMkoVe{9iR+_jfym-Q<0-e%Z=G^gxfXTm#A1rc~;?J54owktlVGjlr)V;i z6_Vh;*#UhJQj{SLU9sv*@NATXI_s3KZCCtjG@Nlu>w%n5$>GKIJ9Mh`Vm;D9U#gjp z#o+VI4{|tl1d7jg&bx^-^461Ya}mm?cn3!U_{7+-aFOQvO89{F<8KsHDYZ6%SD z{KBI2O;Uy?p@K}Q#ta?FK!2(eZf69Ak?glkX{Vpi%lsX1@ zlc^3jHu0tvs}v?IhvUTY-}d(Or7bsu2(OqM9M{}SRPjmxB@7O7H4F|GyUwTTmdUKu z86$>MWol~R&7H1Ik?uHO5D%ud;5MMfMt7t!`T+o)8$X7upJ?mFi6XKV1m*d;#ae9k zZ44Q%^_61%Wn<2c&uEUY{(`0H2OqJMV%KT?%&HbNJn%Y~zcWZ@957^{ z=KAYhYq8)_A*K8;9j-i)?rjQd(cxCQZ$nN`F_><#17eVE7!mpccR=gdo2GEXxW;rl zVon%@D5Y{fjjksUv=fj_s6SX#iJXAAwJ{Uhdj7LtQ!q;Y5w4Svea^^$be3!|q{<04 z)|KR14_BKB27Qi7WBD$N_Q)AQ_21ov&E`#ib-0K!@Ju3HnFUz^o}hNhoRHMeg2hdS z{Lhejp%zPJBJ~wNvHMJ7G66w4OEIic;4u%_!uH(HUk(o*03mw4g>tn7>kt2+UsEw{ z*qB1n>WbxNK6*i6h!pALP~~PInus8j6mqGwRL0)!A?ZMO46FuN)YZJD)Zhu+RJ;%hc*RCjU`sC%ZxYMZs*Tx-hB@DR|S9h0Y0OA9qG7qzH66uPrWR#p~#o&!6rt!!2= ztRvYaV6wBznsCo3Q|txfl#~3!39;U!Y+QD+NEIO)6OY5Cf)C&~D zCGw`9W0OKo>=4v$LOUm=539Ln(gm24ja>h?zFaHo1H4?0iI_B~T)t z&^GNn#fs^R*AE4RI-91&@@7QIjplUy@@^fJRO3uXRFz`1Z5+b2jI_;FX17C+PohXj z9{g5tg5%XFTlM2e9Y!4KNt7tAka;P09qrRGLvsLYpWM6W|3K6=Zavb=RUC=tt{L8` zKQG$s%z$*KcXT)OE8yaP4=*|iX;q~2_8%g|>@t$Rm*@fV!A_(){uS>xuJ#^<9OH19 zqiy}&&zTd)ED%~r@}lV#r_U!44)&?^NFX1M!m2+>uXqtWERlv33Qtv!C35ne$mfW~ zy^*@c!OO-lQmoRU5Cah?h?}f1=|wmJFIU@GrLP{()`?TKJqr?U~GIHC7TeE|YP5Py~+ot|Z@=h+0!8{R)#XLCE)jd|KAQz3gEcifBq=+sT4qW~;qNZO?ZK#;e z3!x_~-s=t5@{EluAih9pG{;vBUx!JXqZ`gl*VU|)^>TFC|JJ~Pfu1nJr_eF<-P-?QlDc@xVfiVlS&PH}$aeHnyz?%>*;1V7 zH^)Qs>YX{zy}hu=AXmaIvcBQBd3McVh23w*5p)y2qmSO?{qqpIONTj`o-fUpy3KIm zgqznRw|bPCdl?qWLQaFRd_rud6Il1M_-K{+02acU6!&<~l%**~o7?Uyy?N5g5Xy~E z{uW&^;_`2H##YLNX{A=w^@T;4gvKCZx4h!qF8PToIdI<7KLowVMRv}=D*?`m3Uc|IOA^>Uf0J%@hS_> zw^vTO!O#wxddjR}h7H;Q{Z|8t6?!N8K{wnA!vHoc@O8^=QP<#&1vn4au`=*^thCA) zYbJZyVtCusm4I>mafLX&xD=0Qt9!zjS?PjYt4=vggLkB}&`>4l}AEM#gG!wzj2UptAulyeT#WO`d+Tp$kbns6QI5hH!BXBBFs}zhkMYR^f2k@REtGbxyAr z<8D!Zf?6j?mxFHIhzWb}ss(4wLWw(W@HjrHBUVEcci)0O(%s6@A8-8v04?V>cSL#1 z6;cMvFN!+gS%~>=X_l**3!;Eo)lb`W4>WLkby+|Xhhy$X5)8|xo-maheKB+-%sdO9 zbIuWZfXyMY5^oveCeRlwp=Mvh%eOaw^wJYf<^uSqutwPug1xxD30{RWt0j)qCBMk) z9V>);y1Z+Y;(gXHS$8fnbTLdW3`tloVa1o<0ZyV0R~~k#{@5m642%naw14{zjITrY z1p2Wsr2&ahm`}#06C1Pz0_G$E0h3CwwVYZy$jk3VQ;J{@0mjP1A^X2ykF!LE%Ki7j{`RE(;K~`6d3uoNbKqP$@fAj_1?A#@I4+QhG&>e z>C9O&q8<1PKn6mbZ1ghJfSF~vp+!{F$BhETD0qR$+7k8?zrfFLUERt-D1pDE8bDCL zFPjvCM_X;CrOLD_;pC+d73LN}9kyTVjVo23JDj!E^9kG4$;Nzic|he_7D2I8WbT?J z&ICtFIC_;#gs}3ORiUd|F73cBg*LJ3Q|zu03DqHwpH%4{{~>mHycNPwL;(T-g2a%$ zH$4=|KYsZBzdk$IV;RELPvK&mqJY+Gq+tE%DK>RV=1@pI|_g zo3_`N`I${aWVZCdODD;rD1d3&%J#DwG%x`8@V_kb2&o`uGCP1$MUOm7nhwy8Q)(hh zfmvRpR6q!2r31KaEai~RQ*d|`-2DBE(r$Ruii09PFo7njjNPH2g5IIbLrP%ll1#mujYZcenR_3cEVX+5 zc(E=$^mscAe|{vwsRv^mdtClo-&G)`vS$NQ-5?LagsU+i0a3o7=<(t-qA$>q%1p6V zV4&u5Gi@I9en1Wn$>OZ7S5JBNf=$V{c&XPB2IC89w-xG6qxWp1OJ8ljniSJiQUl>B zc@9m;_;nLAbu;G!kepO&?(AH_x~8>1gkdTGb3~PDHq%%Wzn=lC$bQ+y%Cg&J z?o@ch&PVF%R{Qe7t5zVSZ$1CohqADiWDWMi@`Vk!FYt9owNaM8`N->e9_VxS?8E-$ zRe&x*$kBua@(bwr)}xNji-ArFUvp($t zBKd4W6z+iHzfNkOD!<>sy-;i7!2yK~bZv;Q!_J95va#&kD|oi*Qbek%NNJA_pw)a$ zpte#?u(hHnG2`L!rRb1jft)>eiI)QdK;{i>ixXJqMtOW-ky#3i>>7H8re?n@mMmTo z1P9nvx^wQd6yVD|)P5r69qhTK<9;#0muBhDVcYy#u!v^rCGai%`j)^Ep8vk*nAd4l z23i*mrH#uy7hW~f8Z=-m&G&0Ei`~-YFCy0KHshFTBs$0vfUXAA;d*lfNWOyVzZGRI zB^DF5a!xwkK)2mycM)@&qu0iJZQhTBYhkzSc55RiFET>xNF3MG^=0et=AaS{MDl&B#b`4G-wb3rP0kJ@nC^k?$++>{@)kgG!y{`t8Vi-nSmUYTBh6qi15GO*4(Vp+E#wGG(0>LN;=FS&&_?EgA zxHhcqjC;5povTC2Axc@<4N>~U$@?*xtm*D|Y;(L9ZS}nsHFGD2?!2>Rxc@4~b6c3& zL-b2Vg|{d9Le4YJ=Wk_%wDyHTHF3Qez8{Y}7)an2X3G4vsF zCo}649>YV*S6vx$bcNx#ZiQ;6K|znsw53WE_MjLT{3MA{GAjF1$^ADhvmHG;WX4Zb zRF@z%h;BPu7s_+<-^C`hn+RKJDMsDItE5WKh51vP(Ke#QD4XwprN0A(m!5-O!tQpj z#%MVgw@YSqFKhw1yEw@SWSB;ygD9JO(1m67RD&$$*<}k5#PL++&Sh;T588C4rj0ShG@G3C$ln(e(uhjqU4lwSs z9Hgtt{*+3QF9k4O*+)u;U7<)!as4jFlhL#~-*3p~@%NFxhX#fX#YV$g6+b77&c`T& z**4Lsm(%WyejTv`{+njN@6yvEmj4ss1>4;#X0|$IEWxv61F+549a{ zE*G3pVL~af4s!5Oi71|C8CEE4PQ^Fw>R<*{PP81WD(w-mYLcti@m|E-PsdBjA`5~;IrvGCgG};Ugx zWZp!Zb;3YLnH9BvNE(iARm0i7Ss7{?4R#aKC*LcHt;T~Jlx-1$^YN)r`_jc4n1#I2 zU!+MczU=Fv6&*?T?=b@1ebr~In${|?df;5R4JRqI;Hr2fi#VV+4P6Q zUfTdwEqT3-i9xq=60;~%{$AsW<`^aAA8-w3O;L@w8)T>20ql5~r$|F=3M9|ldpEs| zDKPgW2P*wHY*+P71S@4n$N4dw`0Da9lz4*Rxm%MlcNIt#ql8uC$NhS={H!0o}Suxmc9$Wk@3L8#$&TB!+;0l zJ+r52G-=kW$Nq!_Kd!G?Jd78IXXmhLZV$RrTGHz!ar)@|oVu#ySyVlD_;2nU@~K;t zKEM7N%4g;dQX9c`=eM$cjPqC^e(h5oRkwf6EVi!DGTdl1VPwl$x8N90yjyjN7LxxX z@}HN~u4Tg~W@eTjNacAf5xCP>UmR?YwaF0}c}!A_ez{1J0Y-wP`^*&`K9_s}vyPC~ z=4P$%0i_dAyU_5vxz3HQ&Ls{NQ^#6WlfvBn7f~WD0%LdiwHFyZZ%MEdOslWlFcHbu z!z41UdcyY4Q;%K=JxpswGIAE)%gp787^=wH+wJ>pXQlaNpbh^zPtAVNFO;!&3sPvO4%Lil?dy*z2R&;!7_Ir^<2tgE$;%+ZLytY|NVfc-8M zx$ebkGmy3C@vK+H5qt?w9&X!w7DB)fuR`$~W>Uvss&JgQGq@`no~o^x#CakvESLQT zw1LzHl|Z`Ydj&1=ILb_#vMnx%%qxvNGoIavls`}065T6L;!V-B5VrHc(GLGvlYb4F z;axOD`vk~%I=UQF;RgDv00zP|^GiS+M7nR`?u>NnNU8tUO}FeF)eh90tmXOEXdg#a_-QFdA}}LvEBm_8ilT#+8Cc%TSp9muVdUJ=KBr zx^3{|ttv;!s?#+9boX{G2AJ?C6`K8O%M9L0FLlRoSAAA{1-bKZOD zeXM*3&<`PH?Ah;sPq}wl3|mjG0Ik1Hx8Z5z|H`S^8@evo88T`x=!a9}@yIy=I`b)0 z+{kTg&EazLP7nuj{AAlLeqL%JTlC*2y;+tUuc#|&LOOz-mfnr{BWJ$q?KFh zhpY*@?zmFfp(>5lQ$2$mm}8@0;~h4@)sy zm9!1&T-oE7R5kLOF#yv&LFIh#&JGsYkN%OfCiY>RQLvA|hLE<*p&ZU}kF6l~T# z)6HuVpuin+JAEU3!i#vZpwv`s9kcY^>m0|sj*}7~uxYC$-M^tP=?EryLc~yC37w`gC^`H*!2I zFin`FQ2L(bbv;?iZUej#g6A(0bY}*&=rKOJjbj>w0}CA5tT^yCWqP~? z?Ts`y{+vvWIv3J%!G)=MET4EqU{=@Gy%JFCuC93va2hkPr;!_}IPCwMke*Nr3stFk z->B*;;s|ZI#qpJt!!6Z|k9!eAP@R7T;U>uKs1Ni7ok!pRHU~mqG z)0G}Vqo8H@bnyryg(5Db4L$zLOLahTYP9q{jt`PIX{&vD-wFWYrs#}%shFJR&k25sbP4 zG(?hknKZjFF)o(h8*3^{nlBMwJd>;H2j!P&5jQ+0HXs)^njQr^g_y&pqYvjtoq*D( zSlW_{C9Lb=RTPvRqtf@kO}?NKrLMF=maLw%W~plv`I?8o|Lz)7>{_7-UT@LLutmrP zZUHUNVBra~=Ok%u-1u!E8&04Ia{Oc!rav2tEB9+z|3LA7*t&-xL82}Tz}02jHo9!v zwr$(CZM(W`+qP}n=G08Y#LVJf<~BF^^1gG=$IDu>bAoc45$~*#f$yl~*6&}sGfB^W zCVv0J_TiO&%KgUQ+I%7`j)m#ENlb9ZKM|-?Sv#p>)^+pUtpRr=^-s#>Dp8qu2enek zNc^HJLs(9%Vyf%UCC^+iu1+3(^G%IU$GVddFDaRt?^WY@a{cYXE&eD+lA~z-v&tnN zpOD8+*nljaPrkp(-qVt|7{?#vyJP%o6bYQnmv?Aq!>QP=pn4{Ss>ebF8$28$ta!iP$#Y%h1vL-LP4KX<2MKS(|Fm0{g*uX8tV{-HBh?kYQGJX`ofaBwMu>VhSa$ zv{fM9p{pB$o-^KcD}GErw5fey>$q?02IEexNB+j0Q(hA7K}U7Sf%7dQt7F$08o3)S zz4gJ&@SxZSN1$S5RA6RlwgP0oNZyTzS6Z#lM-su%tDGAtC<@DZbjgu*A7^qJm3DPr zDZ^Y)zMR6C$Liz!4%!=ynaSw^=5M#RyE;E>L*>Teq4rDIW;K2=|C*@o7G?rmk;Jtt z)R-(oT0Iqf9u9xy2W&1E#ekNDn*`eY`VER5kGw$5OiE<%y}V?ocnEcwz7t}x^qEk9M^ zLh3gv^WI+}It38o8r=~Hj{xyOtLawmyRQRoq}|bwPwww_zl5-$6>Y;o)+Ye z(fEe~@YpdKB*#cdTjFIjZx{-4oHgnnXLkOr=qb+P zmF)piYpA$3&N&S5redjXX%EPig*Zwb-)m+`LFI2Gy|w@b&-c?@O_6u@ec^F# z0wav*Ldrh;gt10guypy|)|IZ7*n@LyGzpk%>JTJfCSd0=le)_}O+gsbnMra>*S^6FDkH82 zh`!*f9_!Vi$bC(dZYkmZ!cC(+VipcX#Gsuv)K0-XQrmt}Rn52`|4gAk zHL3^40w1_o6{VwWG!B*kCCfm8Ve+j#QzfHv(pW)+>QSPk0w>(WWy;Z_p{W<2MW7Pz z^o(z36*3rW9`5jBjus<_b-{O8r8pbzGhOFuoOW}*ns!^F4a#DQ+EdcZZTjR8^bVnp zJ)&UHrIU#_ANl1lxETE1i&AOXi9T3=vz-~iEq2%nTS*t|VlLc-azA_MX|l=hx%u%a zjiRnchjdH+$XQcB`Oh3)~;T?oZ~qOL=(rXESD6kS>4##G6d71XjMEmRQogPl?K_YVPB z4R}TrcU~GECR1Y0x->#yb z&qXoa<0h@ly3d-$x*A}|U8uBen}?ZhK~MtJ zV}w4XPThx)5iaS(4&Ot_qBk2V$uqwEAOfmZLk~4hwrTC=$t;y>V5w>G+-03OrgdHD zGMb)Fi;cTqgmsnapbEBMAFnxIlvLJ&1;)orSUm-gf|bt4EO6^`M^yC$gXH3%WQ!wd zE(kNb<12)~yK=VH6I#Yjv*wCifFt)HUZ#M65A2f3=IuUiOm^e+&SQv<)vF`u%raAY zj}A%oJ0Q|V{3Oan&q!(?p+66cFw0hYDPhIY#>*BM?q_sF1_Rl@KK)ZTTu<)7gcmZi zlaaQ%0Y{>*)90tqpviMbvjaWcq;KYVtYt>s+TUiQ$td_qJXderF`f!pem;o@@dp;k z>YxzOPfpGgkXzR3_`Sb~Yh?kgVborR%99A3`2cGKNmreU-QD9Nr+se{YF9NStCvapI@aEk3yyR_S4^i(WW;l%Qq61v_hHhgyZ zQjx`bTpBzO*Kor$h{q3Yi~#?o!qO(S81tn%e3m^L=@Wryul1#aZISE+$?4yI!*oE* zER8|U+vBNq{UW0KhszlbPc*mW?gMq6^F} zWUNkc;{$WJPCMG8zhP4z2BLQV!FVmQ%1*O_rUhH|et5qBb*xyz>3;%C?Ui zv)hv;BHcD;3BPgnfI@uLac$q{7eEBKu7Y^q(g3t!rkU19lQ^tbL=I+;wf1m^n(AfO z+H%!(eu3cl_I(7MzaJmUnyACx7@`<_ifuX8ck^I{)BDJM#rk*4SzaU4s~1yR6>!gH zM`>a0x}9#_g(G`y6%nWFJ+qVs8TadBahP81Y()!DC4J3m*G;fe7)r`sGjrk+JN*R|%PN3o9YYZ-UYnFkN`wnx6%))y4j8N(PV%GH`~F`>}lqjgzaDEF&znx-GKa9%crD7=HFH$0SdK$ zS+55C3+XR|>Jrk0?rL0!&u~l8aQnWPoQqZ<1)jQ1WB-Atu+dxFdnmg3E1oC)ni3>k zwz@OeNg-A!qbTrDXj9Ik+0?KhJkKvJ!!h<FiNY{;8efq3r_=q4c{w#>ejWuUi6~HqOgu-|H#_@_8Nt$&KWlbBRMj}>} z9Fk|+QZvPTb&JNrv<_5#{vy;($OVlR5?luk6muU)-?~z3`9fS_(F&hDxbL#wMR4|t-p9-wviRd zL}%Q16ng54BD9}Dhy$8q{7Te;F8qZSMQ(BSAaEW(6{3TY?ua!OTf+fSHxU0=OCu=W z5ssfG&NWB8=7Ff~8Ltm8nI-^Kv`~|6gvbIgQ-Z)ak#-|2Q%gc&)a$^>wh9ZhYL^n2 z#u7t(bmq3}nzd`47lVT^N&%-LY!mZGtd0nqJ&+i>%#4Lhy-7W2tu#TCYL+=<&yRi6 z$ISNyI4LZrEmZ8E-f*8U+>^NM@c#Hn7VOY!C5BBDa1-Zh@$KJ>E3+~q6@vkZ)(Q?E zp$7K#^+&;4A6Ov>je6&x^T->#kQd(zL^?8rr@0PkBNugP5PV($grQ>!uQR^%uVZU~Z7WAoNGBZ-!&cXzeqH9^}?*TofO$ysSMcp8iU#xBvIr(XF=J8J5fk%yu}Sx8oizfyX4F zz&4i;GEVAstd|mB!Kl`j-MT)zD>fNe(k>>B!~t07xJfnCM)f_*@!>)#kPbHb5xlVA zo$RRG^;7N&x>n6~Zue11P$7=@DymzFB(Wh{ok@Ru3dphZmTHjQwTFj(hjRELh4xW}4@`-iJ`a)WcH(;Rr@0?%fin6x^Kb z7z3Nl^UWRy_a_YhifK~Vm=g7v6K!Xgo142va7e?Vzw>}k-TjZ#BS}Xlf z8WGYd-lD7G7t=v)@hSsJO+Uas8gTUrbdq8rEBNo$$`NPqaXia9t_XCA5Wq*MsbV+e zsR>V$W+(g_X*YcS6sS2KHV~iu&Uy3c{q_Lm!4r$}`S~8gZfequrO@FNl^<*{9;P930s8%RL;042p0~!9d_8Dp%&IuowDP;V#QWd!n%-zsLeAc#Gdacrj z2EoGtd}&f(s^}09QIU6WXoPj?q>7IuFhUHWG6W2F4GJY};rewjn5=J-JC!KA$T~wx z1Wp7V$#o@=#^_0{W;VPcyCIZOa#afd6yEe^*tp7MR1CB>(mEdg2krQuYb%1AGH~ln zJEa($>tBSj%V?`a^V0H(ccxac=1Ha;g$+Go6_CMSrg>GCnwyyLxNeG8q6$RZ6s>|{ z3L*4UEv(^~H&tQxuJt}^*mr*ku`c!)DFR+9IV;$$B}{-u#BK%o=M}pKs;F@Zd0Kk#_hYx}Mk8#}woSz#0IC$bALqv-BIP2E7bI zt05P!_6*9f)F(p*T|H=N`W$6|hJudlyYH}k*W=hPWWnZS{5R2%!WG-0W}nTJ zyx?N2G6MV9twDISq@)3Ja|0)ewuMnG8*fcjC1Wm@NKeHNt_~oqBQ3OLX1u>q8H&cK z>!Hg{atPSm?Q2#lb%m$+2%(uP#o{y|R@&?Wc;`gMT>!pMoBcjl(y!Ho%YnmqTp~WV z$zy=#f<=vtE8NLZ#Ehm;OUxD59zQ5f#@P)56;P9>-cAO!5EiHwqtC%5s6e;I*VBBeKk2x zN-aIu`;(^I+bDWv3-)Q@NV+|CjWu*mRJ$LS*;P=>2?Yvr{-q64zZF{?9^jC_FqFm4 z=kQuOlfgWn`OWe0MRhNF9tZ4MKhNv!g<2HUW!+`&66di(!37xl(ij`BqQ30B@|*t)s_ccc z2#|1QH~TQ;a_I?#D8|)CE}?mm3Jx1Yc2nr;z-sqLlpAXyJai#LNENs%(AfzbNQ} zt@bx3&;il%r0$b|<$w!xTOJwnY8R^bunIN#VWePzzEyXij-H$D@Y#ri!jZ2HcQCJ* z*2yD}q^LEgLb0^E7@L*t{fGzzT-rKkY?Fzt^EK25Qt<*D_Vi>8v<@$U?%m{Owf}Bz zpy5i$ac6HQ!$2fgV9djZq4&+oVqS%w<Z*whNH%;lZ?k^ zZ7ebV63QbNq29p`*mM2sdw@@XFyb-Kolj^Lhof+tFIJgBy*rQBD%}huH5czrbTTCD z2q#E@%Hf94Tm4%3btLH8o7Dl*VyebqEcyJ|$RdO}KG;}W!?_#>D*z&nRWz{Dgzd>R zHF!oAZR1rqqo-d>%|>6Y9d;CEx2FjH+Jxw!9!d?Tw)Q1*{vrrSu%GfUHb`b#&^`et z;lSf*LEQs6E~Zu>pw-zLPmoL6VDF}=HZ}whKK~^Ju?>rGODl1MDB2jMy`qqKXL1U7 zw@=SbX86!lCi8yp;&&MebqZtPMk`nz>ZZ)G@XfV&k$*e3%~>qcm%XIR{>f687hY|* zkAhL-gZZeoq!D5$LZ$he#ViJ*_AgNg)#F+}5?wE(n66tQ{D(^=XqUl@&8+E5*}V}F z;mqNIh9qdnrjEP+PLQ^V1Av87i%T{@qXd#A+}p_deH=Gt`m%9>?G$jb+wdA2$QeyS z9G4wsuJU!E_=oCI@ohhEP3PP&n>PK*G$ke5B&#_v4~Xx+4VJW}3;%R@TdaO}i@~jF zi2ZrwAyI^=@h5r?^1n^mN3RS_T)4K8Sg?Or4?Zw{^7w{Mi^9Un*=6^X6re38iCfD2 zRZT5HIMohtp(&K@&OcWVgjmkcB8T;^0o!smM@WBc%@h9!o^S#+%KGoow9r{+I=XNZ zcr{H!LmvwD^TnyawRu){|4C1XDt{7@A4E(}sx#bi;!9F}rAONi8a9MAx4T8v*qy@&StF5}o#W0egq zWmP$uj~FC7-3MZnTfcj%g-%u^NWLQP-mXIFS^6(#&4Cu4!a)d3q6D}9B!%c>Y;4nO z#PBc13RW|Gz6h@Gv8OGgZ!`sxa}&+W%96l!YGh!*uH5+Fu704th?q;nyj)C{{q4s|(fkOi6 zAU*H$IdQDxo`oYKoNz+f{1N@iOE(ipM!y!E206IytWlP}vkRhsgRDro34Wa#*p@3l zA#T_y-syN#xFTN<9{2*~0pWeAEOUpz#U? zS9+w$H#MCCvO{3jMuMD{^GDl%U0Ryf)}}VjpmO_ZkDM~~uKitj@WKqL30k7j^MgD_sOpHQoz1J&*GxKnDEQ*+aFzws1Cl6?0qs$VNVAHN+r;8Z@2wo|=_h4D?O^ zT5W{XJG>gjA1{}j87+gr{b6YS2Kb~6x&~1_ZlSk85n1Q+7qVW_+@UX0c&}J((a+=g zT?vY=|7`VTm>1f*(v?ae?zeS|$L_2vUG4F3HsY?*A~wHy-!v`P+2Dv|zk zA>MDD&dOjl`usyy#5IGRw^`k@_-*_xnGy#sjkns&ed{wK4pX4&z70cY(Ft>f zXA=3jh`ibrl;N7~t{|LJ;M6i-pS8CZ`THoX@}*Pfs^Nmj7lMV-*WtzTD=rfztxl)v z#gx(mO6cTex!QAaerx~QrtA_!HLNEumu;T=l$2yJnLthLT$nSlvjzqQA|t7;oTHd8 z4qT$NxD6ZuXokcYexPp;4fwnzGWv>TlLA$0i?HXav*uLDA`Dgr(eTKxFi5)zg#mt@ zUCrc)z@&P?FVy;aMsvo&yKKVEp@@AZ-4#hHrb&yB@zc=L+Iff9XR<6a#c|{Y^~Ji~ z(WGXHG*1r3m}jgs38b`uREnVM?D07bzdd3xPYiW+K_f+@=*nI-TmWom*JgxPKd4-@ z*Xi#LVWNC<*kze8)A?Qp(q)XbUe`L10v>Z4lTi~sH$a&07=>F)%1ZeTs>w0pi!sdf zeN|vdW~P;adRvcE@9&n5xWE}g;)bXJMvsFtXGk!oA0MjFw=R{$Y;#yjU6^*@q*m$mtg%98&#)J7gP12VnZQzed~1Lv$J@9Xf^#K~^*U)Nnd7|$$4EZ*Ml?d?2W znV9M@W~_RyPHPMCrH35L*73i^pUzL{KqpCXKHFzO)Sp=Or2S50HyewR6R=nMG_~Mud|0U0z zK@of`Ahly%CgZBPsiQ1~sf%@%5Ks&*!DXwp$$T0kRpwe973+AplBdL(CcCDf^)d1( zcesck!f`N$JPMW)e*FQ$Q#^{A!Q2SUvjH(IV_X9X?yaEJn062I&{~OfZ&cr~RqqA| zqTGWd=j_nR023EKwO^Ia0yy0rg1KTAJ$n?O7q0@b(Z7RLe@;T>n=~A~$9E&rX8z>X zLowhbCbVc%b=f#Sx?(3U+>!B6hILIEX=rDxGp##JK;~LTE@IBag41l)7}FQ~B)?sr z?<+rlZhVtQQq+fb7_e)L;#qH(PEHU*`?fS!)^O~H$@w>u*N_Z9(z`!>DjSUF<4zr` z*gVTz`LQL(`dsBl0oOZD^;>5ym(;|badsZ*YO-vYmdGnX)yCvQC_iqzVpe)@_-}K4 zbKS@1pOQe6u5lT}haEM>VhISsh5+KITl~8qh`jj6E~)kWXJ3f|4{O6RAjmv%s;QQD zjSG~9qDfbzPnGMU1L1PesNR%o)sco$!+tnzDQm923ha*^-Q?y?UcC-`YJ?qZWB8wD zKy)?S5zSt0-{m;E=PbM@VG0u~C6M}uwgT$&OaR^glbP-V2g>202W zD{cZ@f*yl{5GkgREmL|Ij%%_!(*NA>_X#@InjM=A_Y01p0Rn~9LXcbWWYN~a>s`IV zuttI#Cj;;E6?IX=&otU@tCXnzHfSFj`Mx2eN*EH69pxZgW##rJedfKaMK^eYZs!`) z$(ilxsWjMfH9w}bd$7&}c1MWJXv-=}d}0e@?3fv2k+CGJlqLr2G-%x z14jaQx{mgz#J@t|Yi!cVkj>=qj?jppfkmSuok(uG;|#+6evs)eXFd*PPS$b2t`^O~ zK+`Oi9L{@nq$@{Jg+^K-TSdZx`Sp)!i5YYV1JI$ZcVk>-s$eHNH=3*1ROCIVq08mZ zjH2$FGl;ZvX@NO;RH%r-fn@cD)!@b^(Cttgmt)fta;{L%yh2iMB_CMJSy-EKQ>r5M zp0Z|^$rvym++y`TmN^z9gB_XmYb^>VyC+w>3lKHHX44n4CwHu02h)?jni2Sf5Nolo zuLF2*3D5A14}4y1CUCc#ed(VRe_5i2sUySePa?w~llN6ChO;?MYKGYbl8F zbHjh>$4$R5YwdN-jC(H!8i+<&Ee^S(mrB&b76Dg0HA8zS;JMAHQl!?&(}`3hU7LMX zDb(}jwmBsY&iR(`{A3hh^zWN*PQ)XEFwsn!97m?{Kn0lJ>1*)ctUR&dpByg8#s-Zu zqLa7_W1;7qicpBq4m`}k^TNS_7PLH8Bgz`u4+z3&fDM-0afwg1FGGox(&d%SW*uVT zJaP77!-^=ZDzf>%{+0&vH`B&R+j70cXqCD+V9dAF^-V2wDSl8`!gsyqU{in<|K77f zvX(6)O8pDONKT;P<~jyJACl2j+pK2vPfBPQkv#054=b9#5zMzonYI zjjjZ5A)YsTShf*k+8`(TtW7xIYH_HjPz?7(9&eFEf(3Tl5(^{1>X8u%*H&ykc$}YTJ0q zF8<6;1AQ(CSE9um{*&~~*d=4gq{-&s3nQ?aR8{lbiqN~bN>JusUUPOHtON1{|3C0H$~nkOG9U_z2&*Y}z#|=1r+cqXVn86tfkOqh}6#hYX|zo}A;_6O$|( z{;yULqKgd3n6I?lu4_0bp!zhCa%trO7qSW-MYq$+L&d5coq-R*L$$Na$-X^R16m)PGK(P=A)tpdU3B7&)Xx@eY+t~iB{O)q@GV;eZ?cNH&RlD z04U_-2%5%SRbx;v1nGXorXVR`7Q{d~!J4q7+n13Xb#KBabMdM1fUQt|ur_Y{?>+2V zqra(zN*%XU&8bGZo8-b0t(*;NSR1jKpb`^x>1cH91q`n=-<)hPtI+bgQ87jeW!hX2 zXnl$q+T|I}hH=B5xYxn5!p^xvr!yDD#1siMP|i-bc_FH!XHPAB<{+-3{xHZba3G+$ z%8ypadK7$k5`*)~ur-qb!SL4g!WwcfM2J|yfP5&29HHG(7En{ToHbH*Q&gzA%FUrk_8Ag+SMtC&r2@5Dn>WI>v>ufe#x z`I#%bs7mBHrjXec9Ys>sg>t%KdcAvOH8Q??*+u(ShhN9$1cdAEV1`4wZghoMx)qsY zoV-*@=N!0H@09}rSIVY+IyH>_#eki}eI+vUWCk7~SY#hOOhagsUN`smmHc;gA|GYm z6%PxG^S~PYAwC<}X72OcMDg%79t9<*Ypg%tC{nw2<;}!AGy|=IxxdS2%dsLhdTU95 z2pPzHiu8Et%j+X?m_?9&B5I2xi!E^w8y$(YVFH-&Y#(^DBM6o0SOc!*+hvGsiW+dD zc0v8Fs8dNGO4mVe>??oP54Q8{2YW|X1sk|XM^A%V@@rk&3Sv{mBEwWgWJyZXc^S~i ziIX`O89NF|kUEC*xxi&!7PM!_u`acMFz2XJIR%ABNrpwa8M8&Q_X*gyz+W3N;+q(6 z|3K5@NxhIV)(J}Vzrl35KH3;o*1kx?G^9%oDgYDxUfZDa#HebjvD-dzkgyAhhZT^! zT9yj$pTqa+RlDQ?WeBf@b_O=JC#WMraSr4YUiXyNlFXIJ1dZ4z%<73kJnAr;1SBcy z?6?Wh<|OYB-yWalsQ3a-*Ef~y{r$>eV4j6>%k4;uXsV97=o7(EUBNtr3TkucqBRl5 z1^*)B^!4LAv<RP$5J`6s={T>MwTC#vKzg}~?bwN~Mx zy4d7xxD9;ewAc@0KY;=;1@@+RH!b!9B#uA7owLCb?FtZnLyz`pW@2`q^ffK7S_~ia zm`NtOZ9TAHm70FL(=(u#bI~F@X$K$=0v|h!nKAP>p9%e{$z8t;62R_0)iE_@sk_af zCKPBOzpw<|UFKYA_(esr5ESNJ9YGBrVHyH?cd=ich!-@-oCC|piL;5td$4pb=^c(Z zu;FJI0{ULIDV*}AA>I{yv}jQ{+heJ2y2l~E^KmfHFZS`8e9(q|KSoE44ZJ`Y$H6P? z#OhQ5J4N~$+u3B>cF=DV*%wBn?~RNDmKq$ARU-INa&H2HZZ}n>=ZzSi4?A6sRy3l~ z#+{{DBrAiEK#>V#G_1<{2T<8@A@2#5*gVf(%IG=)t6us3kkvK_?oDAAIVy_>l0lkA z@}ykR=qdd%DB{ql^j{>76P*>zs@)~UHO_0lY2=O<5=pk<*E5C|TOz|-2Mrr9fZNty z0xmvw%NEL>BaQ{zLNsE#2!ePv|9%()wQQV+FWxu!x)HqjSYpdy zFEnUh{atLkpo2WrcDWL4XFkw@Ev1$frMiyv_U)=#OO#?!@?aKj5<%rrN6V_2fIwr+ zt&gXM)un-p7l*2%QGD51FBp^4wIC~uj+o_e)YM@sA>+I0xBz0RPOSIlkP$-Ge55AVQZRITT+D`CZsQaBGO+YfeblHd`+F!n(G_Qr* z-?4oGlj(otbjc{6;&cE@aqax$mLzRJb-{MLCo$H&jq-G@hO34Lqpxv4tZt8# zO;UnYxQRq3zUUrOJ0IQSz2&SfNvk|9QJg93hauA{5n@C7+c<@ECR;+ zV^(VVb|J>32y034F4Yt7rtU0!z{iQf7Y(=Hv4Mj{a4Dim9&FD=jN7lx^4IM0+aB=c zP|Oz@Z&+NE6G-)zXkoWVY-@f)Fduf=*snq5kI=~mIlkZsQ`;E8?P!VHRnOG{?g{HL z=EL{w(Z$ZmXmBV>*tMht?DbhgvYA8pU1cddH}**p9~q7q^^NEC@8u_xZ_$7Cd5P45P#0@{iJk+{>{uGEBR zGKhI0?fH^4oS5|T8)~`{$owXj+0aFn&qQx@vehDKt-Cce7SL29dxKDznsw^NR_XgN zR#YoCPWl`DW;`4u<#Dc7J^Itl6#{IzCAMF|K$O0ycGPK7ZeG9DQR;`X0;M$=RXnIn z)*blTKs84h>h2Bco{#x@+W(EvRSI{bLSQ}$au$>E6VcVB9E6Bt{3umm#DBT0(Tkr~ zjiANH3a48VrDhbrQY&58Pm4Vjy};zubK#>b!B8W4jy)ny)(Vu0B-|Lrzk29V9RV^# zonocJhFgnbc5_8B0My;8IU`4TdT&B$}>6E`q*W^dZo!`>yHG4cB*Oj{U;q zbQ55NmXK`y$;8cc{XorjMR+u|m~{7mls5P)YHHbgUdd#l(ObC+`{tE0oej76BVQb= z2$fZrrO05^5uMkfuzyDh0FpMBmy~M4SH%&JzDZo4a@&Q#bul0`GymyyT#t>Ld@QyQ z2q5p!EYg6YHv~VyqE|wpj#0eWi=78n^K)*uC<&~>?ox>nUdk%!U(KeoY-87Vx5dmW z!1byXJm+8Cpr75|o9*0uYH|uXnxi@7<9G8h3%5x#lf1}V=)bq6fDl9@bNkss#u9;K zjJs6EgP=T>{|;qO(^Xjjr*XL7{oTz>WS@*9k#Y6 z)TIRml~ZsZKmLfFBNu>B*5`o~mAGg!R~DWY5QHmv@qJ(g7%Ka=(Z-f2qbYbfKYQe?hQ?i_DP_1H>Qz!3_MDq zCYlZ`Nv5^$llWme!Y}T%)Y{-jC@mh3EDBewvRqniL^^FQoA2v@F%rfgsKI9fZZ!|E z@XJWh{y9~3t1Yf4!`O7RB6xplY5kMwT+tKaou)hY?%T80sQ{3XAzALTU!Ua-gXF4^8tRmYLye5_==}dEgk> z3?YPLg|YMW)Af3bF0iQi-%(3q*NhF3W*;LpFtjO7f>B?U*K;S!Ky;iO4kQM8DtBXid)=v(5f{7ShtIW3k zt$@*``cf%7&SA+$EI?<5=*_uLg3Yv<^+&*R(pbpv&A9owzjoH#vtp_EB}T zBs<;B`x!{*vwG8nw%zB0m~P#0x$8P5Xo)t(y{}KEgfs-!p!V#O+y=BYO)9J)eZtY2UeoOD&MYU;K`Q?`$N;ay|SVl?#h zHW%lM^iL!=^`g*4!jm+v#A>Y#YsC@+L;Fs4>GVwXpVjUay{|}C_!6Lvrwwl~0mU)n zc_`FA`eUlkALbZHiC1@7ygl^VZeQp(bCjWm9%0sB2KeNnY+y~DiPV)w9pume6eZtZ z^n9DBP!vk?U!~=jUZpFAwsO>Ab9<@OU39#4t?6Adi#-hyZQ1dr16HnsX*z2X+hQjY zor33!pHbo1?Su^Am8)fD!Ce)aTMXGW5P$VMOa-(sO^atvGnDoe^X{?wb$oq4UCd4QJvPd^#CmJ^wv3Z>CJU(}A94uj=VoLk=xTW58HL)V zXi8bOs}fQbRQ(c!J$YWqFd+TRs=Z{WEhDk}HH<8YbS%mc z`7zasYfRl5qychV3#t(~f zDLH*eYE(<6ruAsgw;KS1jQoS!>NDd_mqh?<4P5&7Up#8iqQ^oLV)`D&*OglsP4eAl zls5Ee_CIg}40Qj26QE~gr~f}rfQ5mL@qeHGzb3%Sz)1f;m;gQ`t%$jmld%Int%#Mr zld+Jop{qaU?B+s0dWd(lA^a_o|})(nU9~`2XE68tCy#a_impR?_t-eRVkq% zkR#{?Ap&|rJ^45;xv5?yP;fx;umHY&03IGkwqdAeFpyjI{@HFjWQA|uM+-A_;J}eZ z0`$)GKadcMPY-|rBz}74?zK@|;K0aW{)gYjVFD9CO9bC`XnFqRa%jOpZ-B3ha@+i7 zt(lylxktL9_`FI0;3}vH1%7mN05SGp8U4TFk8c{(t!f9KAUNQ22faK1-s~pM^#>S> zV4DFTz8N|^oLgT$T@meeAKV$BAkbZ#zX``XACWEkeQez~9+3X7t|}04WWW#3HSLYA z|L*9{G(0(S@NEcw;O;L~O}PmL$~3=-HUw-C$7u+D$Wj%H!bE}7u5~?mh~8P0N@`Veq0nbIQYY#e!%=| zgPwp)F!uo;%Dx^wudjSH+a%UmlpR1S`Muzp5V&|fWJ*9D&f9{C64n|I-}W#T7xtEb?T7Wn7JgXycY)5r47 zx9kUx8u-r(aKJ&LfO0)YzC|JL`E##BAJQ;h+CK@tw(QWT;DLaoBl5GE zuG~6X-kxez{kZt`OnG$uEk?;C_yO5MtRFZFasQw?N5iv(@k)zcTxPv>7I$}4bM`p~ zs(aj}Q5VuI=A957&eIGyIv0V{(A)2AZqM2!U}6#j1P8U;*$*el1{wMjUt#nsXmq<{ zbE%^32@dr6QdRU|stw)+A72xG{Y-Q2@r8(3LO3eKOF{|JH^{8qs5-ku10l9C5DXVU zbI}(#5%had+EypUAb@-yL>hwww8EcA7~e&cf{T4g+hr>IuNYDsB$;fQf> zoKtyQNMVAqB=4&;hto-O)qWZ>q+NBhszla!5muMCy%Qe?t$M;STAE+~M+Ea%Aoxz= zP2ERMUB|Y9i={040%{=618<=U}cE4OH7mRw!4;Ihn;)f_}2UE?yXU> zs*`{L#B3a**Q4M;eTHKOzP8dxLYakCPGU@XWEFMgy+nE9(pt$m`BM9DJqXputEEL= zfv*AoC~U50@2l^?&hYO<)xUa5q%rGlyO|_Vve>J->>3&CwWce~WK=-%`zqTe70x8w z@{sD6jgk$_f+)`^BvLUfNge@g_m-8@9L1OSvJN_7Sux^_I6R~B`t^)9&^K{~s^b(8 zm&s(N=^0oo+%1k7NdVbeUoG<5oENE7ecZV*pTf}*pLR?R2QWH&Lyxh~xnMr`Rbw5T zZhxrUw$Nb?E@nbd=(50y6#pC`CLI4(n4|QT!UguI=7#q9>%EN`v|{8<<>GQvFrK*a zg{FJr!mN=mEYmc;TGS54YVP#_>HZi%Y%=mD*Qa@&#n)g9I@A%BQ;9q}Pqh=kn4f3i zi#r%AvRB2-`UyV|wK(Q>678<>QIJ4eF#+pD4e1cFLiMDw5 zTe@$it}F-}(UsNFl}4%PY*I)={8TcG_D{#}Vchinfi6EY)>lc39Utf`P2vm=MEay z?XvdutS(`KKf~T_aJG~6*vmZ)>0R^H}_9Z;-TUjS;vm1rQiSYQkClfq%XF6AO`4OceD z(@#-(V`#-ZRdCQl;;!+#jL-5;geRHdtvIgQx;q4t&I#0+~1kqxiO^4tPvI5k$~Gf1-e2#y^&wagZ_1&_lDBZMwd&*Cvn^T3DzOlQ(_mjHl) zJ*N!cax6_dvtbTD*sz@U2dzS=#&itt$}`vc*^ni$TdsDhfW;i;7a?1ncMLN;j`U~< zY<`C9wSE#!F2K-C)5m$ILXD0;rtaq%XZr{Pt8P6&nXpwhEK6p@Wk`V+6|>#A=4k;> zF?BRbbZ<-2Cfw46ELP9x!~(R#FX|6h!q z!+I_Zv?gQQcD~rQZQHi(?AY0HvSZt}ZQHh;oWGx*^xzEo2G$L{tE#G=smSLnuB()) zbqN9(&hBlC5_huAbt(2C&~J+|j;Xvt$}F4G6#xdIt(b~zx-r=sGj4X{3Ygw(jTzz$ z4pyi2J{zFFf<9nMnP|%=QA8ZxmyCryZ2KkIS1ri~Yby(OUi8Ft&5rNg8kxddVXlGs z$SpjVOf6baE3)V@4eN$uBmIU1#@dqk9Rm%~N?A+PyPlTv2NGk@NYpZ^sl1$5H8odi_GaP z(70-ntT&tLgij=I9i<8mH`{iPGddpkfl+KL$lN9mqW=GVXOOzt)!VB3Utw`7W@Hgc zv~E~XkTY1=F~L1WP%uyDxEx!tt=jHAwv%I`D_GaV2_w zCjLm2`Q&$w-pq5dHw#?LD}G3eb$lzbRL>hhZ@LCTT;+4LACKQiLEVXsmB)2gPd29D zDcaFhn5_>hr)jiPn|}T*pIDxNN%uRL+0v~G0rP0goSl_FJy=54epBKV0;^Tm$l#%T zz9pGPS*vq7Ygd}0S%wj8r8OwSI};Va%GD|3;UgomOTTIXsOY*6Rq)l4`)0CXyFB7n z&fzb=r-pSZ&N^k;8`}*;y`fd@3U%F=)>Hs)x;@ew@yk~7|A>@LzmQz5$RE(HC9j{; zVkzm-okH1{NsFrsTCcZC>YtVa-8n|}_v<>6a`_8zhy}?m1`SKvpXA#9x^+E5j+Zg` zZMC=<^+TUKt{de6I!FAP!6R|6n>{QD1xXEJI0 zE|Q2hTcp|k>y6$3w1YgLa#f&}D|eao!Ct-A2#2SYATC=N2}(`_h`(PH6CZh!xOH;= z)*lYDn?tG1^;Tl$=2Q^|fNCT68q7-735eWhn6LwW`GZ5pV^kB%^^T+lz!W5F*&0eQd z*Y(+KmM!7&=ZVK>-&yNTMLv!6-@$2oghQenY*KY7aVnOo=%C!D^f0#EJm~I1xoAgJ zgU?REzkdIm+)ZnH@I8o>PS1$7fZj2&zcz5E(5<>YyUFE1e+eLV$yFcBAVO)~vZNU< z>T9W8%kWEaq!AjoPx59gj}kva-HhQ zJ>{=2GND{`^`KYaLKmt}GP1d18ms$D`?qFX$?kl;=%N}tRJzrTj})hFjj8B;FQR*esW3?Q{wS4def=r1O{T63`v2n zqy4!oK|GL{8{$(JCAnL-7r98o>B(6aqIlPbgY@uti2y&6$rn zUZo04<~bR;$TXniw`m}>@QpA3M!9Hc^AN&OYgvlENyyZs_G+rjX zP*E`I{{Cn8jt@8WchzxPwJukYX7ot4eG2tr?aBU>c#h3w8>0?gq(bd{Cha`(n+m_C4 zdUZJzHJ=XDSRmp0gqR>>Ld;@h7_72wt3P(iI{`|50!wjLm=kaoJW#yVUXN}z1|py? zpk>_a<^yBB!ZN>^eVcTy-nLs&^9U+M?4)9#sfr}7sk?x(1ih0Sf2_Db*Y!#l(x zXlKc?`A&8)>Jw3TzYs@Zfsea1Fo z$iHi}J&>eL;%ZcxKqL}#JG@?hPDX+F4XJDP9Wj;0_S~U}=v&;z+{N!ax6=N572@rt zI^M{<^cgwRjKv(PzlI$@Gi#^3eimiDWAZO z#Ct!Bbz-y7VPbCo`^b6Zrmvt&p6)c_@zyVG{p6e1H>Bq6P{KX7#@0E_UPJtfF~H&T zondYXIABOqT0%qfZ&`$(Bm1$g#eBrWQhl9S1f7(D%hSr?q5Tg4?1EzQV;2t1QCNqK zdqr!s6~D4yC_s_Va`{cWkz@a;wOfil^l`FWt~8?wvUAyk5F8gNQORcfx?OtRqq}}$ zCa&A+#t}o*DW$G5`lu}?qpemR2fIo);t1^0HsabH^5&{QIaBXz!kA>PT%1v-*IDE@ z`Gs(eNTio$9=jMnHu6O6u$Rn1I=u|({ETHJ$>rL?8ew~2G_uw>KouV-)_1O^^pP~~ zUv4&mnEoy-`nwdSu^W{uhK)9ewo644cBzu`P<)htG=t??4xX(^U?$OhJ)~3GW=vYPU&kT)4Cn|yUD}~Yy33(Icyfi{% zjJonzyt16cZ+m17@#f~}sWTQ2fy5w1!xBtk+u5H@5juYh9wsM7%MjDpGxRs!1)2BF z)Kyzng_+IEjYfMv_K9U_vcY0XATB3vUe&21?uDlWuvyjmr>c4KovbnxuB17V2{?iv1KdpE@&O``rjh3u%o|2 z40jhn*ooW3LC##U^;ss)3a8`#hQuS|%`<7~&*{Uu=g5Oav;%o$#VQ(Hx6C274H2%4 z*~5Z}(YW&*9klc4bZG->nVMgS560?mlT{d#v^$r}?K#A1_H9ZHhLzajRJRlf0o_+!bYkTTYuB#h z1qY0-t-m@m3zuNzt-~;2*o~YRUhpStG%_>Du=HJ~Y~^NMaCu-TYY%N{a9|JbP1LEG zxqdW)BrEpUiP>&91=0#OFZkoOrHC&K>@32{--VckB}4tyAX3Tg7OxMwnZ;6~W~{h; z%c;XBP<^N!%Jl1#v~_sZGigqvwo3eoYS<0~?I+M*q|@sbo8~U?osb$L$=8|h5xa?E zgG+cEXgt_n)vspx6#_W+ZN}wMj|pA?4TE)@9ubxF6*A&SX<@mnq<$9DivFcZoA`A6 zaAy>LKK*k|FRe#h&htP6sRl}^tsg~$e)VuuReNa2A*ov8jy^0rx?A&y=wR#{@9=1lUV z`%9;A{{EOwi8MIc#_)Px2$m%%*RJ?L-$k1ic$>SHst3Px))?u8xq5 zExr5E@M1W8?eASa#rZF7Msx0z4iIHy(|zr^XQ`gVN7y^YanAEoiMKkTyYZ8*aBj35z-pN8RLVo{WYbLrg#z`z6<60ioJU9He7}b1 z_4_NW?@mVzvq2X8wd_v;U;uKW^p;HrRR{LL;C;I&nORi=?M~%eXKCSLr*>OtU*7^$09-4pn|~*pR7699Kik&TQL&XO4?j4sfyhpyQP~JB+o;K zXLR*s7Kz&mDj3?H@LUlnwV4d_Vw3j657@6b*rynh3S+y1NT zT7udWf&^E6=fC4L%Lu-C)R9(;Oi+1coi1=Hu0k|%el!qU8Eb4vtk95^$d|qJUf#3&Zb~=9Kjf=2!E@j5x6G?WMF{zjJ8kU ztK$2AH4q?+>(T|ZVSx|mJ!B38N~T|BB%_BIz18BVnIx`c#n%Oh3UEk=x_7z>2w`{p z7HdhZ&F{u$D8XNxv#^CCr7Mj-JK8564-cEH{5P@>ogL;k4O(gSA3Q_u=cpss?T% zy%qqNUtde-W>-gHU3e-gdl0&fs@~hB9Z%|fp{!^;u{xTmFsMCHIRb;uMs+xMa&_(E z-~>LjVB1IywZxX>$x6b$)JDFrhH4+q3M*@>l27Gp#LgI(;3FLAG+|nZx#%-SJV{BO zqv~^HJ;f>Q3h>a`B(eqkhc`-YD_Oy@`YZh*H5yJ7HcsLEUctiK=fX)7ft(i4TEq{D zuE(93g`X!E@WJm0{*Nn#d++RI*bFt^ZV;AbG$SM+p(J;~+){Ijqzae4XBarsr6ar= z9g768Y#as5lMPiJ=7_$6h@E4?l@uB{(ThjAf2XG(ow;5At7Q0-`O?g&oEpDp(?RYD-zc1QLZ|w{y|~Ne zWd3H(eORpbhatQhaTfJ&ZpOUdNvGA&Enafb1P~9^0mVi=!;UVD6J~l&1QkELw-D1( z8fmMmS_GU{HhaW|T81LwS}B{)RT2w2u_dF}TQcur;U+qz=d$8v;ZF7VF;;Suv3AHa z8d6oE=H(?uYfY8*7a_jH3B&(3TQdJ|vn2=n|1(=MF*CEW{%^Y_6AKI5{~a#>KX%I| zaK&t$7P=UlguR)O|5HKVUhf;(CU5fz+(X*h4(9n!%K;qh;}~${y31dB`>WBdp=#H| zWEb0hk{%r_sue3VwAGJBd2V<+(Kj$Q1&gGjcnr+Q(#XWj(nzAHSoTNPF6g&`M9~r? zTTc+-rR(=DnhR7;ch~L!P;+YpgYW{R#i0WPiyIi4lolGDmVw}V4 zk-#MwgiLg4i0CSmhvee;Eic>U)* z;anl(RVKBL1Jk9h5%fPBHPP2T1%fj~X7_Ff=AwZ~bG^r1-Rt{mEBM&X)`0@-iG7?b z&I=I*M_$ZZFX@gPRKO-}Pz?}*xw$z#fjZC}G|&@kqw$A|?)D_|TUyd_{Cjq9ZhYY% z(!PUk@I1mXkhdSi{?Xwfd?-gZchHabuf_XasGv}ALj-0Q@N^J5p%T$>_g<*4fX77F#^&!yneWl>-}}t9AlvSr z>wwkDtjo?9bi5sozMp__YvAAJ8W=&Bgskn~mx;E_uG_$f?&9kJdgLP#=m)S&nm@YJ zRX^k@0qbl(wCQwX1Z7uyARmu;Kv32%z|cP|1G!$#4?yW; zKj}ZhTed)e=3Zo;K&fwsp=bKqU!oij(+7?N2*!+`*d3e9Z^-ZSsPQkt1n@qvFUbG; z@mgQ-zeIBZM39?=XFs!d9`fqHfp|cGIe|SM#La*{4-)qPkyHl0szTVuC32@2X<-G9HpyX|dXpgk6CKcGDZ>6`x@P- z<@*i(WwT}BusD4!y{R?x)fo8Q>)lZ!nnSe=tLxe`9Kkf!BV2GYpb5V1uj8R&l&P<4WG7EBeQ?$G)R9Y-8L!}Tuj;X z3@os&%&G3zOAZnd^8)|rxXZbXPO3G}gEz(XY^4>;Ny6o5c+hzAi3g^d4eNhczOM__ zOXh;)VWr>M6T zU+&k8th51=fsjh5|+bwRddHNXvmwYtNd` zq<3sDn{lHpIyTk@yV_-GI90R8`h2IzYMYwxvlcsHEYUme36Vi;hO;w!YzBQ8N=m-U zkw9R~+=NFg7+M%ZKMDt9N|Q+CzR{gL6YwKVqF5PxKk{FK*wngleT(IMi{M(hhNQXY z3RYHo(CPcUG`vMPETiPKEv?Na#5e@X$NL>!?@bZ%#TEN7)wJn)-0b6!tUl{^g9J?l ztQ90dGbUw*!l@q>GW1`|{ZQ+f72Q-AptD&0>)zD!2{dahzHC+rr#$-%jPZcL1Q9cQ zTo(G9ibY8(1zb15K6hDjw`O~Dl>$_O|4rh`t9>VKJR`|}x0z^uItS*zBA7J+0X;Wv zuTrbc2la<>Cxu^j3I`xRAG3f4Th+k4%K2K%q>JfKx4VNC!ca=G6pizWA=cmLfWi2e zu6kZG#H2<3O5v#2b3KGI+cudQNg~P zG~iRYL|C?Xic-qYf401eN^gS>LeY)Smx2UwP`Xvj{M4lfMzR1av@|E5QSFA!E)wCO zjf|E%2kp5lpzq4kDQk>s6jUo~L}S=s8d$=1yScG9T<`@VBKm;+@kCmKZyRm@CpMI9(5w}4pE-I z{fZ-n$A*3kViDRUkavPTakqNf6&b;$gwp7gN4q*lspf9&X7-f%)~p;8nmPX2%l%fk znfRql0G7+kkB$k|lNlo>?-HPg3)ud2Yvh~j3|>~}(8n2zEBD+hsobPZjwPwRD0BYk zEbP1J;YRxHWZS)|UvCCZ@UFHZLGx(E`GE#mcE#sdD#DMG_wCZ%H(O7LcOKrER(`ZN z_wMH_3Y4L@lOrzm_v>3Fz1z#g14*ZeE}ec_itEzvoX=gW_#kMwxl^f#Yi&;JT>3FO z1;W)I`ijtmPbO6nl(G9}za1G;SN6{=KU9b`>rjC^iC5brF+bU;-CIY`csRolcV2a# zF13(haB7IzYpJjIxA4<1qH$m5BNI2JAd)Bv7>(*W1Pa=HGWX@)X0(D&w z>zU*e&i~X*rg!)V*ssVT@A(rDxQQ}Va86gK4?_4G_$Qwkig4XzOll24&b=&48fKEn zW{SIRvQEvY=Lm)IxWI^{sPzPIw3Y~`N5b&LS@W*rTLB6V^_00#J|hRTdMd9VbUxTF zN-a`x1t>H6+?S~LE7|p$F}iuVllSUJzAD&6-U?!K{mIloh-%6=Qj|9jo}*aMv`_5# zVZ3WguYqsZV5KP>(XMW1EA5W#VY9AoAXS9$q#^L3Z<6Vn7uRqHw<2GhFQfXNnZi-$ znwkmn5TCif(N8m1%ry(LTjaZ;ZdJl8ZlIEF;(qZau!*De`LN^DgfnL)4G@KrdE7wjgEG@e)*Q^=dasp3VA>TiA^dZ zHPj#76qdC;90aFg6Q<<||C1c>Qs(sH^{3ZR*6z+1 zv!qpT;?vD6053aHZo}8$Q!BLKh-QxQq=j_O-d0o?llBtT-Xx z%<)oN)9kS(_n@d13LHJYt4TYIt_vB5z+&ES-dsQ^bNH2KoM{dOd__thm|t5TePk!$ z*bw5OSf6IEqF&x@woTv-iA&{9Y~TVaF`Zsj#>0@I4_WI@NfR@rV(s5{Xc2voWzz>V z==*eICmi{ZtR80Oe&>C$2tKsGUo0nCy1(A;72SlFe9F~)7*K{{oL3A)IZ@JfG~rP* za9vdH$Lrp=TzaYJX4j3`ifJDmd1~h3&-1bSbo59i&Zp0}ZxO0ley6L!v~z3vC$<|jFC>Jf!wvQ6#2a9i zLti5$kdZ+`<1`})bgOk;CG1;v=h<+9-a$v=`V!|2LX#sb+yO*=@FFjt;@@>SS& zooAx$)^307UyY2XBksx!?ipf>btKcrKT%Kd)Ug^H6}^tQ%V8%xh zJP*#qmSy`*8|ZA9VE*K2x&BGk0Xsgq$i;d@t!@ZEu!ZTq=dbdCYnneMmMtM7dhGMw zb1LF#ae)1RpsHwAvQF*pzH3E}49aE1Nb@J3;H4j!}*B*Bz)Je~C25CIxS>nlNcc;O6!`Ei4}K6>SAmb^E=%|Cj!7^Lw; z2#SGHyg-l&q?Xr#1M!CN`rFBRvPL{2X!*mH#|zPRnV2eXCqYxj;m9!TGNau zUL1@W6Cm|h`)*$M{^+u#eh`vaGbj9F4234wZ(I|XU_Kt|fp*zrR81dYiJDV6@@VQj zx*5V&%~S&ENxETptLI0@qKN5K#lr4!@LT#BA$1A#ItOyoI4iX@chhL?J2^5if-)JQ z1)p;bH~Zv zE{xSwu`WM4Qx}qD+sg5&RZs3|&rtNH=8#E9?KUJDQ$LTY>Wo5olJs1djk)w7D7W@> zfJtZpanG9+buT4?_Y{Gmyut?+&)qr+!QG`?A1=@M@Di6_PErHorm#+#ig-{RU|s^3S83uH zFV2=zZvF?(nz$iV{>-Eyaw6J?u_khv(e>Vo#@oArmiKOHrFvq17}YLld6#p5$$Xq? zXgNPAV*E;2KDf6)O5VMlxqL{qlz-_lj0@#l#ehr3YGqu|&!NFM3yQv6$ViF_Mt@|y zR{|>cHV3|)Kq=Cd$<0B+aX3Ex{1%G{^NAak(|qk^JH7(#7NDPmQSJH7F2BS)GPLw+ zldyM)jFmh8H#j}L6fJ@(Ul0&pp_Fn-rRn{^C;-Txl^06-9L-e2b_PVJbZxN&+;VCw*@;RqXMNo=OBQ z*HNmk-ao<(c`QFmlh2>Q*dP^Y26Dv0g)>Ulj&6I0whL0fO#wg4jI;aHueWUcUkp_n zf4m;e%Jqo=)08*N5X^WZ@4H3__+$3yYHnw=bBvw1gdG#?Mi{x_0%d0^YePKMx(N5; zavMd@WgHdbQgk-fz;yu$dZ}(E#;ZYbQ5^?HkI1kv5pVZq`VF!-jUGC37HmcjcZqk) z{A%FV-NdXb5*V4JT;=``lpui zw|-{+US{avO{ROWCZxV{o~Zc|(}pdr5CfqckE8XGhq!skq=yo)NE3QfDVHDf5y9@` zT{lyCrd08EEn66Ix*+;=X-#>n_he5IYS8t3MDuSamN4~%%j9nCpcH?6GPci<>yJqd zmlxSb4&)DRpgyH+x$ucg%WhFs&8XH%1Cp=g!+fGucAY?*?NJa^$h1>{${9=TmP!_) zcuOThEtw6IR_m+e3t{fLijW&L<2>H7;4SgM*wYYo274I zNB^W4BG*!J$RVvSEfWL3;_{fqaymq}qmX;Xll8(xCz`ZP8xA7%TD~D2E7Yfmf}1?8 z!h{)~Y;R|J>dNpRerk3CME5*{Z{zYP@m;z=n1z;#{cYh`!^_*Mcf!zSKwWzsHffEVSa5{Z(0G)As>HME~%?9WI{@<#>m;|H4tp6y= ztq%A6+N_<;*rD+oxm!IxHVvoux>X}oAx{+RB5}+sbod-q9XxNUv&N7BAzJ+q;!y~$ zF~Pl9d2)P3-vhL+-oR|%D4wOE87d&JarVMkGMvz7i^E|Xl77QTd4M*Aw_+!3m4SA(C~az& zXY5ik4qa>=i3b^E?Ajc)A0TdY+HWx)&OK;`OI{h=VYLnKj~cQT4(R(4E!JrumNxe1 zQl>7`pdUI)hI|u>EiL+VQPoEDQ`t7w_J;*)BjrlUI~e>@-GEn*6z6<;lf9|bqRjYv zX0qtbC6Fzp&wuZ6tk?r&l*nFzMpJSmb_R;(5uk@g6+eX=>nn6SH_WPCaWR{bm~kyK zDM;KT^PDmWMhdUXuDlNUXs*p((>4)xq)cMih((z{C- zSg&XP6-n3vlMCz+^Qr1ITne-gBn^y99+DY(f2FOn-1{2*u~q*T9YS6qQIGN%!&NSx z1uA8MS@nz)BL$%^H(vs#kK#x9p(RBBgW>MYSAU&rSYkF0)hJJ#sDAHoGIdOp{@1WGaqn ze~H%W{J()TmVLzg4or@WsHeM&o5#GFQ!Lub%Nn=>rsWg&<2gUHP?CRqU*GjQ$wjsP z4smP$TyO)Ly(1F&p@2i32n6heyVcZMswI%sxrYrOO&07t7^UPrBeTf5UBr{W#h<-gI(*4`dzQC^&ba{({bn4ofZoo zExfshs_}Cj_GqB7V{!#XibVb8yZ%X%QBfP+(RC^6hUdMdt z`e!9Cog`E~=6YCjgp*(3N=~gVw9od0;;#uix01Pgu|(;#aP5Z)+`ZnYK|FiH*w0L+ zVm%J*Sc_jTIjRA8$w%wM*D>SF+3EpusYnlpASacFE@wq{t8RB0Me&P!+(ucw+xX0AJozq3dw^o^pkA=0zr)KdXrP{4s5?bNQ2{@#gN-=t+|;Y z54M(jwr(lz6Rsp6H6)Nh+Hox8l;k;warr<8SFBptPeqM$J<;{t)gtMt>9}m=7pn7& zq>zDpMG3CwU`e?rejn6NXFo}#b8uJrke!39Agx@Fr+_?eYk5Wt3slYcws85top7B! zBgK2x?fxZDV!R(G-tbIO|6Z<8mPHDTp6k86uSuko_E;^uow)LxYJvDu54VVth|H@qc_Zq zcz#!LnrCddTdTiRCj`8m9$flxY^UDuJcOCON_ffQ9)w%s2Wc=^j$0B=8+!*a#PA>WuUi(^6>Bt7gF$z-CIg1VW{5K zw#p!IP^HbnR$Hj^p+9gkDtKEB_Mo|5ERdzyaP>QD7$2@CY>DA&kZlPo4QKAiuQ5f`)`M}9tcGO2b;gnzJGr21iG)+8|4`Y zF=DpWT^qw}J`s^0@z9+_$C>)03AK^n(gDB&=?3M3SYw7R0|;>Ek$# zp{s5IIhe{1(iLN_qkEd(PfJ0VLCN7OG2;*N+D5+zZJx%E=s-=dC=gE`kohDiz7Z$8 zGFJujvr~x*y3lE;QnX_2x-;-{;qwKl%%n`HsSt^iXNEM;sqLiqONbx?6@Y0=vZblO zWEmW)p(Q_iUciRi8w7{(eVe()-TTpBGdFMXG}sZRoT=AXtfFUh9oxcaVj?liVRx>a zmIPoq`94K-XWnm4`Ex0G(~IjVQ!yBdLM0n5)StheQEA$-N>bvz4y7>!MNs=bg}?;y zn|Ex{OdH6_Xg}E%1>MY-M;|R83$s}-&#U>-8ktr^CEjS}4kn=&jdidCe%BNeT7uH( zv!TvVx@fSc-0iJyvH%Y+Y}0?*c*bQyed!RsA8$Pk{J=p#u|C9G+j~x`Hy2^$p@K!n zFmzMUW+~(4>Us1sBKbY$NMUog+AxMolO0xO{C2!|i*f`#sQs{DV_z~CrgE@(aUN=w zwrlU9Uz6t~{M&M8T4o>3nzSJI$5Y)r_bfUKsIoyKBdkH1i?r+N;)Z#n(1KvkcQ&rTZ<<9@K+e{vb(bMI{R?^jDfA-RDD`7Yg28m6& z9UtiLG7cu8;L@PabPz=42wZ%yR0@A>ORY|Yz?{p-~%F!Heb%bj`?hbdPdH{5PaKd3VByBxQ ztOc=RH)Oo5yTe@X=si$iLmpb13a;qR>g||~ZyZEMkb7ypqG5WQ*K{=t;c;~7@Mi;4 z#_>YWpoZ!JF!0V7Zq4y`zqGPcdjY-DBd=QZM6Ek34dgn7NNGC<)a?%~wk11SiPcefs=k2u*Z3O_2t{aZt;8+4bZSR*E7hJ8TR8;x}dWU!8xl zrgVgFx9zDco7)o3mBmZ>yz<_w$#Yz`a|U(n`fU++cWfe|yGRGqkw$dc>x%YV6GxVT zJ9l4|4z7xRn^{x#QX5o7vbV_0{@WaudZzB#gUHlP@r`2Rs8-%==7yW8zrM|N&MmvM zq*CPIakAo_+Mhl%|8Tz!P&9mjv4;l*o`T(h8o~!6Uqf9Ps*er)7wQu%)yRyn`=qBp z!QAz0nF9(<9OBOWuQ?91OezWH`qY}0Q6hL*G*(KqRak$Jiv6ePGg-AyB;7$r9S;D_ z*vyCmx-%0XHo{ntwAuu`zj4lRaDeGH@;P zN!Zyr?2PsLSwDFMAm6w}l$BO8MKi}hLy_H+C5umb)mK-v=T(_D#wrLXbA#1sIcJL9 z;ji<5al)^B)sqDt4cu%|%Zy72XLt4!)CeKnpKM;15V$RPw8<;l*BzI^hKXSSJT7FW zMxeR2N=84e(3IQ?160NOdUI9ux8ZnQslh{NJYgEu6FK~PO$I`Gkpt;W+y`wu#%3%l zqyu-=H?BX46pL|eA@Z~W3ROtn(UW<>TE}2^t?DOxjMXr|bh$R0kV0hs6>*SCH<1lU zamtyXZgO5qh2_%473St`!hK=`>;Cz7`YAawo1iZY3OtHCb34!Yy|T>sO5jnyy4(gx zerpS){0l>XG)6yv%=|_Z6qL1Cz4S$biMNanvwXQNUYv8Pk(+R_3RlCi z@>t_4g%DwQ#1EGF9JP}oJukCg*inZ_w8nd+xXA4HS+a9BVF$GV)!zC={w^uo@i06* zdQ8nT`EmM4qForyKZG|!D&n;^*QLqvr$z-mj^jupH(71}Ne;(1g>z>NsH^EkxnuF^ zQubZ~^eNcg+~5o~?*QWv%|d5lP{oc+R2n2$mKJMIf{YCd1wY*LUxwmCAB7W}gKW%E zH|Fr3d8*AMjsOW3bC7ej`IS2k+ydWc2ScQcufk-=;gYQHK=@o#Ojz)&99`4~b7Kx};tbqUP_1g0Z`RzkaX^6ngekb?D@JSFif zvtCDtT|u*;4gA8(AwWc+rNU2tY^?fmzvBH&`H#pM-n;x?<*2G{sL1$WBcU04JdkS0 zx;AmbwQ`Tgi-E)uv$_cV^J1N^Eqh{4|9p`(SY@q=;$SSzQ0a8gc4PZ=_nEWx*JC0s zaA<2GcZxwP--RnS+dOV?_=wz+Dy)*#OYEf`_y<%Fl}4BzY#P3FYZ<^I^!mE^GdV=# z4m58s4YSGAD}@jwtLWH@WE+GAL81;{rDlfzk=Fg5S?-swpWXeN-aq2UTnfZ7OmZN;pfE z)W#bjnMK!WY}w;zIVdYwfdX(Bq!eZv2G7pk0ysrBOI!c7%#45q!nG&1$zgV0gaPV^ z#1Vw*TiD2Ks)3{KWb~e%=G2a5Bkh(+5P(ewZV&hJovO;FHm zG;xU7ig%6ALXo=MK?>i|p-@O_GAqbDfhd@lh=zmEF4>UHW*-WOZ!<9Kw9PA2-Jdfh z5%?3Q0{-E_P86AU;DO{KRL-GUNO{+J1_3iet-=-3jaeO4`l^la#%cHftDQ{bJt{V< z?lwE$cG!r$_h*Qw-J!=PvbLFhJ7w_(x&vDi3P^+|L_=CEjpZ*8=- z58Oe_%8?nPuXG39lPrPyc7lrF$Z)bwnvtb?Ymd3Ts*E-_$@+u$orR-J#!l0@td{}* zhgpJSi#v)`(Bdcu6p-1cd4&Gt$6c`A4lyqqHm$wl+or==$0r~hQ!v8X)|$8%6FE@J zBlQgID29D|Efks++|BKeDB_!5DR$v?2a#LF>9JxdeatS%=|jGvgi(d3eRdDkH>I-+utS^xS3hk1u?%o5w3g^+ZMV%bSWLmx zG&#@RVbVx7sf-BC25&3dNI=@R?$K~~*c~&=4$@m^!WHV49q-IAvw4*Qx$WjntTMBU zxWFUtPY(lJeS6+NoLq+gUdOLJDNZr$+rqpt#=~7R3d4!e)9(c31T>Px3ZoA*htOnP ztxHSBY^EIX=|`oFSD`D_%)2xOUh)8{g|nAp^{@0GcDP4#BSw4ck>@r#<0pyN9~}ic zQ^XGp!2GZS;p&s;{Q2Z(PVBkT2wb{;B{Z!nfRltgbm{N0R8>7gslT_RZl%*LLtC+p z2tXg9c=ZafG%?HVqp4BZ#WSV`?Ab_tact;H5{p-sKFo?lL(4q!FGW4z>)x~yX|*z= zNh|x$@IG6NdnV}bO};V(u6OZ3sIh4tTqAP_{!g{ZL2b`%-pP$zK+UzaxW_8~_QDRO zrMl;*JgJQjAWhQqM-^%Iy$r9-HMXYno-Y6F-kZiuhfulYT}*Smf@xrGV_w2j zpGzKQj7+2tU3LmA&gs|{7@PS=mdLvNmK3w<=>2}=vB>C=`@698MzE;M-SfMhP70}x znQ7B-B012;>_?xPBYO|em8t*p@iQiy()gLQ-$q)=|Iah@l;EGpK)ANAmd<1l${^m! zh#76UO&epUF`wV-M@0;YYs7ktfQ&3-!Jhs$EGcAYLyVmvh0{>ln~!3H=^wDjtw}kR zNa1DXVF~qL7T7eb3QN2>n-8#$jjvNc_*|yd3XF;o&zyg==qtNOMR~YpK0FpWj#@qm z5w<)#U~p_M92>BQqQIr;+nC5%-eI==P@fA*_B_7T?Xgzb$g!>z)^#Hz_aPX(_%b0V zl<&GZKdG{;-zW@I!FVv)~%Dncf$nBK06uZ_3l_msXfL2h#LA6x24-x`>Sucz)P1NqG^Ow zmv!j@J(0mMy$=3hIvpd&%efi{hFK~95PGo+1D2tp{Bg?4g#*K0MMmkAVP*9g`l-K` z+s(&~=pyNYOSTPF@mJeNOJkHyb+Y@6eocz;5sDs4nNM|jsV$WEdYMF^Qz6Um3u@fM z;4U~l@Y)o{3^a74G5cT(ygY@T^($1(fwZr~Con&0M^#xG!n^xd*x35|ug>MVQQwXv zS<-r2<^6%aK*`MGLL&kIXF#E*BT}GuhZAjT_Z*W<_E~9R;#JP%_Q%drud{~wLjPmt zF{=bhI|ki-NXpLga=G^3K~m~kgm+vbRvZ`Dumg{l2BU>#!BCU!muh)8v1T%eOJNvU*rQ14MYr39zyi~a z!ULTDTjC#V^HENszOYxJUK8K&?WQ`j)W`o}?3-dl0lFr~wr$(CZQHhOZBCSS7KZ(TY4)GytqPF30XwnO+h(2E8J&EP2Fs4glxTgJvo(}GLg4=t7= zg!_1)c20!Z-b31KGnSM>ESk{~@cT>F@ZKKS^|hgLihfR+Wc#y&NzrCK$j$30-}mrThRd2B6-R4N#z+O9dcDLhj<&XB`kQ~>M5BwO|&2pTOqAE#Jj6diBpqQTH zjZj3x^k-2W3t=MtWpYosSy67D5gowGG5h28eNtQJHp6qQE)_tG7BDHp!M_sC%0$d2 zQ0;y}kv;_e=?sT!@q7Y?f#1U2TpB%GTDZEnRvLW4LMhHtf0SQPY@*OFoUGk_S$Z(~ zSMq{1iBiWVLSP8Hym(N`NhtU9YYSnRL#6vXqE6DGZ@sR2kTWnlzCXOYbn_X7q|pU8 z4uO_ZF~f@O&#lC6RJ+fg$SYr{RY1l1Xp?3e?eprN{#xdg5p`RL=^iEICTk0+HrB1K z=xt3qvW0BviDInL?aFEEqrV}6=ox#J;-hsrfferxX6?D6`$u5(@QIY9>6`O$P1#t;%FXWTQjTLm@ z+b2NIz0|$do}!dj)Gb_XsBTs8qMrfaHtsyybYaZQu|-H~Lg@WS^ot3+PAQ#hEA5{B zZ+ywQ$wNlO#@GoV=jUw{iT24vwGLqNNHo86NHe(az+T~|z^rxcb%iB;8Y?PZuGF1` z_ZFGAIM+`k#{nQt5=0!jD9c%=2K-_pBTLZ??dgOmt4tZf$m^$ZLdWmGWLH!=4`lm2 zdDajWz<+}!x77{m$a)Czr!%Mv!4%>Y%`E=5rhletPtQQm5Vmi%9Db@)%vmb99$q?r zhn2ZSg1-qHSeqof-8u8a)#(GbHFV6d)kP^0gxcCR-;Qm2KMn*l>{@YRPrdp)DO>3 z`Ea4p)qZ?HsLiZxAtLDYo2C$wA_{Iqh?Z-n+F2+bAR!eD}z;K9< zdX_esOo=lujya6+RX+M5*ORgRUnxzC&)&ojn5vMmZGr0;X-8**;53z{W?-TP;|(JI z1e2PFoPuLC$A%qOsch*yCrnR}^D4-&vwwSM?te;i|AGTdEwTJJeGRERv zLN|zFVKkmd9GYMuz{f_gD_m6+gt#;E&?)TQKYwKxyEpHPWcXSV8ZxHbS zU}021(VHNUfMh`8p9D|{2mqi^&;S8KAU8K-3MjDmO}RchsCywHM2GQT0SZsSD@BW} zMqVh`CBZ(x%pC>*2@C+F6p%6W zP**p>g3B*o=sh53U;!i~BcI+uK&Tr8dWtnXxVZ-Lc7d&V)czNS07M{|(EP98gdph+ z(9nl?6qKjuXViLkaVUbWY}594fF6Zp=stv?5RZ2O9Kc>Nu(OR$;hz{Xfj&3}w?Lv_ zCk(=Dg`O8Z1b_{I;2=T=60RZa8;E-Zp8)>LB=cyF&0kWlU}AFN?Tt>O8QI2Y%z^9nz~f>{thw$5Ss07L?iii(H`00)o( zZ-KfX{-_KuuK{0fKWs(j5O7Zd9st>M#sWbFatKf8f&>dY;6MVNp29)Ezl-;?sDKb4 z4k1B`0N@eKC~|kVR~F1e=XIkO~C=AV82nBO)UKf_^i^ckw>T;(jBR1GotRko^Bf z@09gwzq}6u*75`GgMBfl(E&~CKm=UwinIbn0ra0ipZ&_b?h^j;r~Xbn^df!taw|QD z_4|Fc{{VgQ`+2)lO#QZ_aQkZ-PNZ7kham1t0d@6&ZvE4k^|gQv0~LNo96zTokKuyy?`rv)$NKEf${>(r zr+4Wfw1j`FtAN0Xar`4?B}7mRZjViGHwEQTk zK1~TB@XnS^O7d6r1l9kgc_u;$o0v;IVD!H~YhC0she#q0n(>sP;kJvua;^jK|at(fm$aE=KOA+{-_Mc>;bhmMRR_(u2Xt|S&ToLHD&}9LoH4Pw>-uKvmpjEXB zJb@+w3ojgNS5h^DqPETOW*Nmw%~{)cZBN{vSwb|tMKjkesps~B*KhS=Clo<5f%;sP z!?0<6jO~R)+P0OBcHXxhGgCIHb06ZspM2M$hoQ#mD>Vb!V|lLrTFMYsQPI<|Fz&IH z?eoPTv}t1YeO;hqq(>z&$)N;B#`pYHQB=VnIbysqd3n*|LKYAll`E(VESWs$*yr_& zli#~sB(#X-bmsc9sk>HP)$pHU47x@pUbfMQ@^s(n-}AeGhD~^6H!0K%pFWH@RBZ7mwbFC%0_NrkV4%1P=c|Iy*S^3Xn}Q$YCwNJCfT&So!J5u zm!mb?gBV0ZUwmU9?zwjL_ss9*P4Bv*9EN~=UneRNVW)Bt@;Dx1h%AN`R*~$3N>0v% ze;bLe834V{!O@CzEo|JfyM&Ij-o$$eO@76t9K3VIEca<*pX-{V0qu2_TCQkwOo}G)R6i~KvI@s~7s7TO z>hErab)8VTIT%ua#g~~SrT8nScW0MnFc+do+Nru($5c$1Clx07v3UFSxO2MsE+^q_zj!7vhFL9|%QCJkguxBmORLv2+XeQyD2W=Y?)h~Rv{-J)f1dUJyWOA5@mJxr zRx>hGt*_5%*@*U@wcg7VxvQus&h9d~C?H_AzTZ{|HuPVDf04pc)}5(t!gZzNw7H_C zl-ZTbuj)3Ft&BXaJJ`O1B`S<#m47zK zRj$2t!V_&T8Y%Y*z(#));uyH~hEo2rSSy%MkL(dkQqEs7Sq4d@i@IA35%pESPuMGv z*MCShb^LrKEoHNH>o$51)_IONb8$Ln^_?M^E<2KLQ53~&OhLkb zld8Q()6=zcI#fZoUYZg`4gE_n1L7~?U~n~cSMD>fgLX?C#zS#mlSNhkT@3EyVp`>S z^X+56nqa5OF=CGHcGP+iHyR2M^D+#(t#omB4ga^)zLi{@$m_c5p?db^=;R%OF-{Ig zVYvPY2VH4?DbK5c@4E$+BMe`kUGkrCxlR33oCXXJ-QB0s8U04L2z|##@kAz`$@Mdw z{U;5hWEjzA-5senDG1?sKZw2`Qc4c9 z_B1}jb6nVhPY;#vVC#;4BwM5ViZt`d$i4f;R7#LzCNo=~o))k5EVvqX^Rk-IElzz$ zUT9Br^**$pf1kk|Q_=TU2nrilJ@T!!`$_hFpmAA8yED#Ns8X!5*(wFGl%f)nKTcJ# zCn{?wI*4e9ioxi19cHv>^l>U_#jhyAS&e)htTixuwb*!$-8p%Uh+0PEphi?WyEq-< zZbl?Bi9R8q?cxL{dbn!aWvp*=f~x46SHI~*6uj>>@XYV#JK>ZiqB6mlRJ41=?6YYN z3oc>sXrPxfm=*8}(ux|Z7x7(ZroJU7aeN(lZko#?!H|>ik$n4Ts9LQ7QK%M5dSoVd zVApI8wyjw+{+e;>Rn?)9q1K%9S&CrQo~Y}1<38%fut(KB{CKvtz!aw!-Q4l(7~dIe z0(ZK~mri}vFMYvd`7a#D+A@Q$?~*;X0IGj@v<}blFm(UsP{r5`EgcNAb#LVBS}Cv1 zSlnKU^?PBFFWX1aGR6#k#V2u*#wdO`@=VJU#8)0Ul|A6W=(n~qx@XWW3vL;Cq>L-9 z44ntg?%N2Al;9gqvjUeo&FMKkv;{2c-tQOW?=WeO=GFd;ct#om)0W;4bFX7J=c3l- zq>NZ7%PaHKcVCTlk|H{EJ_b8hFK9*V5nLFGUns~uT|c!ZmmX;o;YUW2Dn`2{dfy3ouji-3=8*{;5^e|78* z{vn$nyFeg67#G&+0h_6c!~^9az=k?-2n>B&8%_EKj}6%oe&pJ5Wi2iRiNk|~$*)lJ9%<{p!h9uq@9UYE+9UQBINH*kKE0McDRCkF z9-x5r-!qt12E1zbb`(xMf0e={PQI<^f|P%}D_1|RsQB7wOFevCm$sjAM4|)hRhD9l zJ|;ozSC;p;pnLyouI^S$EuUy^B%3u4=}eShB|sEA$TzJTmBtufiHs3E%loZHIPIA) z7;Vl!rBj9PJlveZZ1CQHZVfupy7hJ^f2!=Bc@o>nGzR9Rtkz7v8p#UJm*>;07^b$P zk%})(RD$1YjeKGLF4S&@CL-~;R9%OqIKDnw)=RkUyPu73*o@142aYC_K# z9|qxrqEb^_hHr}xo@!D61I@;DzzC{==|dPo=hECg^id#BunB#GN1n%Gj4=HG8=IwR z$Zs3>ifSetLd^zS&i6val#$D8!kwx>d7dxlm_q1bLJMBL?u~Qi-MN!0BJx%!^PKdk zW54)48rAN-`5q3H!g_?gojY6hXH+tMRljz6%f3I>Jc?2_;|Ij6^w#AS*6*5fH)viV z;cQ)P)i#V=uLL!yhhFlythY z0&h8T3&ug%SkJ0$YP*Av94%9Oisx{98HgjOvxg(tG3)?W=V5X(?g1#G&vyF(xC004 zW<9h@-gH`1uiadzCuUrJpgeNguW=@ms^V6c56%Bjj5*Isd*ioJU^Q!u57@o8y3t!A z-{*~)Oscirh5?Q2DZ6=ER&bCjEKBS(k)(LJ+~l-ObcLxal#T}xoSfY=w*P_bhUf5smRk+xtc6^ip z5*}?6Zwe~7wpG8CbJF#3Ig{UhYbJqo1gA3F8Zj9X~!;LsiCLngg#dtLoPSpW#Z{*};#LV|MKNso~<7!FGM^%2K zBE&Y8)St=kL-+08vjv=aD*s2aqhHPrr)5x#G$nuZye4 A@M^m$#DnV6BD!1a)k| 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 -#include -#include -#include -#include -#include -#include - -#include "cutils.h" - -typedef struct JSToken { - int tok; - char buf[20]; - char *str; - int len; - int size; - int line_num; /* line number for start of token */ - int lines; /* number of embedded linefeeds in token */ -} JSToken; - -enum { - TOK_EOF = 256, - TOK_IDENT, - TOK_STR1, - TOK_STR2, - TOK_STR3, - TOK_NUM, - TOK_COM, - TOK_LCOM, -}; - -void tok_reset(JSToken *tt) -{ - if (tt->str != tt->buf) { - free(tt->str); - tt->str = tt->buf; - tt->size = sizeof(tt->buf); - } - tt->len = 0; -} - -void tok_add_ch(JSToken *tt, int c) -{ - if (tt->len + 1 > tt->size) { - tt->size *= 2; - if (tt->str == tt->buf) { - tt->str = malloc(tt->size); - memcpy(tt->str, tt->buf, tt->len); - } else { - tt->str = realloc(tt->str, tt->size); - } - } - tt->str[tt->len++] = c; -} - -FILE *infile; -const char *filename; -int output_line_num; -int line_num; -int ch; -JSToken tokc; - -int skip_mask; -#define DEFINE_MAX 20 -char *define_tab[DEFINE_MAX]; -int define_len; - -void error(const char *fmt, ...) -{ - va_list ap; - va_start(ap, fmt); - if (filename) { - fprintf(stderr, "%s:%d: ", filename, line_num); - } else { - fprintf(stderr, "jscompress: "); - } - vfprintf(stderr, fmt, ap); - fprintf(stderr, "\n"); - va_end(ap); - exit(1); -} - -void define_symbol(const char *def) -{ - int i; - for (i = 0; i < define_len; i++) { - if (!strcmp(tokc.str, define_tab[i])) - return; - } - if (define_len >= DEFINE_MAX) - error("too many defines"); - define_tab[define_len++] = strdup(def); -} - -void undefine_symbol(const char *def) -{ - int i, j; - for (i = j = 0; i < define_len; i++) { - if (!strcmp(tokc.str, define_tab[i])) { - free(define_tab[i]); - } else { - define_tab[j++] = define_tab[i]; - } - } - define_len = j; -} - -const char *find_symbol(const char *def) -{ - int i; - for (i = 0; i < define_len; i++) { - if (!strcmp(tokc.str, define_tab[i])) - return "1"; - } - return NULL; -} - -void next(void); - -void nextch(void) -{ - ch = fgetc(infile); - if (ch == '\n') - line_num++; -} - -int skip_blanks(void) -{ - for (;;) { - next(); - if (tokc.tok != ' ' && tokc.tok != '\t' && - tokc.tok != TOK_COM && tokc.tok != TOK_LCOM) - return tokc.tok; - } -} - -void parse_directive(void) -{ - int ifdef, mask = skip_mask; - /* simplistic preprocessor: - #define / #undef / #ifdef / #ifndef / #else / #endif - no symbol substitution. - */ - skip_mask = 0; /* disable skipping to parse preprocessor line */ - nextch(); - if (skip_blanks() != TOK_IDENT) - error("expected preprocessing directive after #"); - - if (!strcmp(tokc.str, "define")) { - if (skip_blanks() != TOK_IDENT) - error("expected identifier after #define"); - define_symbol(tokc.str); - } else if (!strcmp(tokc.str, "undef")) { - if (skip_blanks() != TOK_IDENT) - error("expected identifier after #undef"); - undefine_symbol(tokc.str); - } else if ((ifdef = 1, !strcmp(tokc.str, "ifdef")) || - (ifdef = 0, !strcmp(tokc.str, "ifndef"))) { - if (skip_blanks() != TOK_IDENT) - error("expected identifier after #ifdef/#ifndef"); - mask = (mask << 2) | 2 | ifdef; - if (find_symbol(tokc.str)) - mask ^= 1; - } else if (!strcmp(tokc.str, "else")) { - if (!(mask & 2)) - error("#else without a #if"); - mask ^= 1; - } else if (!strcmp(tokc.str, "endif")) { - if (!(mask & 2)) - error("#endif without a #if"); - mask >>= 2; - } else { - error("unsupported preprocessing directive"); - } - if (skip_blanks() != '\n') - error("extra characters on preprocessing line"); - skip_mask = mask; -} - -/* return -1 if invalid char */ -static int hex_to_num(int ch) -{ - if (ch >= 'a' && ch <= 'f') - return ch - 'a' + 10; - else if (ch >= 'A' && ch <= 'F') - return ch - 'A' + 10; - else if (ch >= '0' && ch <= '9') - return ch - '0'; - else - return -1; -} - -void next(void) -{ -again: - tok_reset(&tokc); - tokc.line_num = line_num; - tokc.lines = 0; - switch(ch) { - case EOF: - tokc.tok = TOK_EOF; - if (skip_mask) - error("missing #endif"); - break; - case 'a' ... 'z': - case 'A' ... 'Z': - case '_': - case '$': - tok_add_ch(&tokc, ch); - nextch(); - while ((ch >= 'a' && ch <= 'z') || - (ch >= 'A' && ch <= 'Z') || - (ch >= '0' && ch <= '9') || - (ch == '_' || ch == '$')) { - tok_add_ch(&tokc, ch); - nextch(); - } - tok_add_ch(&tokc, '\0'); - tokc.tok = TOK_IDENT; - break; - case '.': - nextch(); - if (ch >= '0' && ch <= '9') { - tok_add_ch(&tokc, '.'); - goto has_dot; - } - tokc.tok = '.'; - break; - case '0': - tok_add_ch(&tokc, ch); - nextch(); - if (ch == 'x' || ch == 'X') { - /* hexa */ - tok_add_ch(&tokc, ch); - nextch(); - while ((ch >= 'a' && ch <= 'f') || - (ch >= 'A' && ch <= 'F') || - (ch >= '0' && ch <= '9')) { - tok_add_ch(&tokc, ch); - nextch(); - } - tok_add_ch(&tokc, '\0'); - tokc.tok = TOK_NUM; - break; - } - goto has_digit; - - case '1' ... '9': - tok_add_ch(&tokc, ch); - nextch(); - has_digit: - /* decimal */ - while (ch >= '0' && ch <= '9') { - tok_add_ch(&tokc, ch); - nextch(); - } - if (ch == '.') { - tok_add_ch(&tokc, ch); - nextch(); - has_dot: - while (ch >= '0' && ch <= '9') { - tok_add_ch(&tokc, ch); - nextch(); - } - } - if (ch == 'e' || ch == 'E') { - tok_add_ch(&tokc, ch); - nextch(); - if (ch == '+' || ch == '-') { - tok_add_ch(&tokc, ch); - nextch(); - } - while (ch >= '0' && ch <= '9') { - tok_add_ch(&tokc, ch); - nextch(); - } - } - tok_add_ch(&tokc, '\0'); - tokc.tok = TOK_NUM; - break; - case '`': - { - nextch(); - while (ch != '`' && ch != EOF) { - if (ch == '\\') { - tok_add_ch(&tokc, ch); - nextch(); - if (ch == EOF) { - error("unexpected char after '\\'"); - } - tok_add_ch(&tokc, ch); - } else { - tok_add_ch(&tokc, ch); - nextch(); - } - } - nextch(); - tok_add_ch(&tokc, 0); - tokc.tok = TOK_STR3; - } - break; - case '\"': - case '\'': - { - int n, i, c, hex_digit_count; - int quote_ch; - quote_ch = ch; - nextch(); - while (ch != quote_ch && ch != EOF) { - if (ch == '\\') { - nextch(); - switch(ch) { - case 'n': - tok_add_ch(&tokc, '\n'); - nextch(); - break; - case 'r': - tok_add_ch(&tokc, '\r'); - nextch(); - break; - case 't': - tok_add_ch(&tokc, '\t'); - nextch(); - break; - case 'v': - tok_add_ch(&tokc, '\v'); - nextch(); - break; - case '\"': - case '\'': - case '\\': - tok_add_ch(&tokc, ch); - nextch(); - break; - case '0' ... '7': - n = 0; - while (ch >= '0' && ch <= '7') { - n = n * 8 + (ch - '0'); - nextch(); - } - tok_add_ch(&tokc, n); - break; - case 'x': - case 'u': - if (ch == 'x') - hex_digit_count = 2; - else - hex_digit_count = 4; - nextch(); - n = 0; - for(i = 0; i < hex_digit_count; i++) { - c = hex_to_num(ch); - if (c < 0) - error("unexpected char after '\\x'"); - n = n * 16 + c; - nextch(); - } - if (n >= 256) - error("unicode is currently unsupported"); - tok_add_ch(&tokc, n); - break; - - default: - error("unexpected char after '\\'"); - } - } else { - /* XXX: should refuse embedded newlines */ - tok_add_ch(&tokc, ch); - nextch(); - } - } - nextch(); - tok_add_ch(&tokc, 0); - if (quote_ch == '\'') - tokc.tok = TOK_STR1; - else - tokc.tok = TOK_STR2; - } - break; - case '/': - nextch(); - if (ch == '/') { - tok_add_ch(&tokc, '/'); - tok_add_ch(&tokc, ch); - nextch(); - while (ch != '\n' && ch != EOF) { - tok_add_ch(&tokc, ch); - nextch(); - } - tok_add_ch(&tokc, '\0'); - tokc.tok = TOK_LCOM; - } else if (ch == '*') { - int last; - tok_add_ch(&tokc, '/'); - tok_add_ch(&tokc, ch); - last = 0; - for(;;) { - nextch(); - if (ch == EOF) - error("unterminated comment"); - if (ch == '\n') - tokc.lines++; - tok_add_ch(&tokc, ch); - if (last == '*' && ch == '/') - break; - last = ch; - } - nextch(); - tok_add_ch(&tokc, '\0'); - tokc.tok = TOK_COM; - } else { - tokc.tok = '/'; - } - break; - case '#': - parse_directive(); - goto again; - case '\n': - /* adjust line number */ - tokc.line_num--; - tokc.lines++; - /* fall thru */ - default: - tokc.tok = ch; - nextch(); - break; - } - if (skip_mask & 1) - goto again; -} - -void print_tok(FILE *f, JSToken *tt) -{ - /* keep output lines in sync with input lines */ - while (output_line_num < tt->line_num) { - putc('\n', f); - output_line_num++; - } - - switch(tt->tok) { - case TOK_IDENT: - case TOK_COM: - case TOK_LCOM: - fprintf(f, "%s", tt->str); - break; - case TOK_NUM: - { - unsigned long a; - char *p; - a = strtoul(tt->str, &p, 0); - if (*p == '\0' && a <= 0x7fffffff) { - /* must be an integer */ - fprintf(f, "%d", (int)a); - } else { - fprintf(f, "%s", tt->str); - } - } - break; - case TOK_STR3: - fprintf(f, "`%s`", tt->str); - break; - case TOK_STR1: - case TOK_STR2: - { - int i, c, quote_ch; - if (tt->tok == TOK_STR1) - quote_ch = '\''; - else - quote_ch = '\"'; - fprintf(f, "%c", quote_ch); - for(i = 0; i < tt->len - 1; i++) { - c = (uint8_t)tt->str[i]; - switch(c) { - case '\r': - fprintf(f, "\\r"); - break; - case '\n': - fprintf(f, "\\n"); - break; - case '\t': - fprintf(f, "\\t"); - break; - case '\v': - fprintf(f, "\\v"); - break; - case '\"': - case '\'': - if (c == quote_ch) - fprintf(f, "\\%c", c); - else - fprintf(f, "%c", c); - break; - case '\\': - fprintf(f, "\\\\"); - break; - default: - /* XXX: no utf-8 support! */ - if (c >= 32 && c <= 255) { - fprintf(f, "%c", c); - } else if (c <= 255) - fprintf(f, "\\x%02x", c); - else - fprintf(f, "\\u%04x", c); - break; - } - } - fprintf(f, "%c", quote_ch); - } - break; - default: - if (tokc.tok >= 256) - error("unsupported token in print_tok: %d", tt->tok); - fprintf(f, "%c", tt->tok); - break; - } - output_line_num += tt->lines; -} - -/* check if token pasting could occur */ -static BOOL compat_token(int c1, int c2) -{ - if ((c1 == TOK_IDENT || c1 == TOK_NUM) && - (c2 == TOK_IDENT || c2 == TOK_NUM)) - return FALSE; - - if ((c1 == c2 && strchr("+-<>&|=*/.", c1)) - || (c2 == '=' && strchr("+-<>&|!*/^%", c1)) - || (c1 == '=' && c2 == '>') - || (c1 == '/' && c2 == '*') - || (c1 == '.' && c2 == TOK_NUM) - || (c1 == TOK_NUM && c2 == '.')) - return FALSE; - - return TRUE; -} - -void js_compress(const char *filename, const char *outfilename, - BOOL do_strip, BOOL keep_header) -{ - FILE *outfile; - int ltok, seen_space; - - line_num = 1; - infile = fopen(filename, "rb"); - if (!infile) { - perror(filename); - exit(1); - } - - output_line_num = 1; - outfile = fopen(outfilename, "wb"); - if (!outfile) { - perror(outfilename); - exit(1); - } - - nextch(); - next(); - ltok = 0; - seen_space = 0; - if (do_strip) { - if (keep_header) { - while (tokc.tok == ' ' || - tokc.tok == '\n' || - tokc.tok == '\t' || - tokc.tok == '\v' || - tokc.tok == '\b' || - tokc.tok == '\f') { - seen_space = 1; - next(); - } - if (tokc.tok == TOK_COM) { - print_tok(outfile, &tokc); - //fprintf(outfile, "\n"); - ltok = tokc.tok; - seen_space = 0; - next(); - } - } - - for(;;) { - if (tokc.tok == TOK_EOF) - break; - if (tokc.tok == ' ' || - tokc.tok == '\r' || - tokc.tok == '\t' || - tokc.tok == '\v' || - tokc.tok == '\b' || - tokc.tok == '\f' || - tokc.tok == TOK_LCOM || - tokc.tok == TOK_COM) { - /* don't print spaces or comments */ - seen_space = 1; - } else if (tokc.tok == TOK_STR3) { - print_tok(outfile, &tokc); - ltok = tokc.tok; - seen_space = 0; - } else if (tokc.tok == TOK_STR1 || tokc.tok == TOK_STR2) { - int count, i; - /* find the optimal quote char */ - count = 0; - for(i = 0; i < tokc.len; i++) { - if (tokc.str[i] == '\'') - count++; - else if (tokc.str[i] == '\"') - count--; - } - if (count > 0) - tokc.tok = TOK_STR2; - else if (count < 0) - tokc.tok = TOK_STR1; - print_tok(outfile, &tokc); - ltok = tokc.tok; - seen_space = 0; - } else { - if (seen_space && !compat_token(ltok, tokc.tok)) { - fprintf(outfile, " "); - } - print_tok(outfile, &tokc); - ltok = tokc.tok; - seen_space = 0; - } - next(); - } - } else { - /* just handle preprocessing */ - while (tokc.tok != TOK_EOF) { - print_tok(outfile, &tokc); - next(); - } - } - - fclose(outfile); - fclose(infile); -} - -#define HASH_SIZE 30011 -#define MATCH_LEN_MIN 3 -#define MATCH_LEN_MAX (4 + 63) -#define DIST_MAX 65535 - -static int find_longest_match(int *pdist, const uint8_t *src, int src_len, - const int *hash_next, int cur_pos) -{ - int pos, i, match_len, match_pos, pos_min, len_max; - - len_max = min_int(src_len - cur_pos, MATCH_LEN_MAX); - match_len = 0; - match_pos = 0; - pos_min = max_int(cur_pos - DIST_MAX - 1, 0); - pos = hash_next[cur_pos]; - while (pos >= pos_min) { - for(i = 0; i < len_max; i++) { - if (src[cur_pos + i] != src[pos + i]) - break; - } - if (i > match_len) { - match_len = i; - match_pos = pos; - } - pos = hash_next[pos]; - } - *pdist = cur_pos - match_pos - 1; - return match_len; -} - -int lz_compress(uint8_t **pdst, const uint8_t *src, int src_len) -{ - int *hash_table, *hash_next; - uint32_t h, v; - int i, dist, len, len1, dist1; - uint8_t *dst, *q; - - /* build the hash table */ - - hash_table = malloc(sizeof(hash_table[0]) * HASH_SIZE); - for(i = 0; i < HASH_SIZE; i++) - hash_table[i] = -1; - hash_next = malloc(sizeof(hash_next[0]) * src_len); - for(i = 0; i < src_len; i++) - hash_next[i] = -1; - - for(i = 0; i < src_len - MATCH_LEN_MIN + 1; i++) { - h = ((src[i] << 16) | (src[i + 1] << 8) | src[i + 2]) % HASH_SIZE; - hash_next[i] = hash_table[h]; - hash_table[h] = i; - } - for(;i < src_len; i++) { - hash_next[i] = -1; - } - free(hash_table); - - dst = malloc(src_len + 4); /* never larger than the source */ - q = dst; - *q++ = src_len >> 24; - *q++ = src_len >> 16; - *q++ = src_len >> 8; - *q++ = src_len >> 0; - /* compress */ - i = 0; - while (i < src_len) { - if (src[i] >= 128) - return -1; - len = find_longest_match(&dist, src, src_len, hash_next, i); - if (len >= MATCH_LEN_MIN) { - /* heuristic: see if better length just after */ - len1 = find_longest_match(&dist1, src, src_len, hash_next, i + 1); - if (len1 > len) - goto no_match; - } - if (len < MATCH_LEN_MIN) { - no_match: - *q++ = src[i]; - i++; - } else if (len <= (3 + 15) && dist < (1 << 10)) { - v = 0x8000 | ((len - 3) << 10) | dist; - *q++ = v >> 8; - *q++ = v; - i += len; - } else if (len >= 4 && len <= (4 + 63) && dist < (1 << 16)) { - v = 0xc00000 | ((len - 4) << 16) | dist; - *q++ = v >> 16; - *q++ = v >> 8; - *q++ = v; - i += len; - } else { - goto no_match; - } - } - free(hash_next); - *pdst = dst; - return q - dst; -} - -static int load_file(uint8_t **pbuf, const char *filename) -{ - FILE *f; - uint8_t *buf; - int buf_len; - - f = fopen(filename, "rb"); - if (!f) { - perror(filename); - exit(1); - } - fseek(f, 0, SEEK_END); - buf_len = ftell(f); - fseek(f, 0, SEEK_SET); - buf = malloc(buf_len + 1); - fread(buf, 1, buf_len, f); - buf[buf_len] = '\0'; - fclose(f); - *pbuf = buf; - return buf_len; -} - -static void save_file(const char *filename, const uint8_t *buf, int buf_len) -{ - FILE *f; - - f = fopen(filename, "wb"); - if (!f) { - perror(filename); - exit(1); - } - fwrite(buf, 1, buf_len, f); - fclose(f); -} - -static void save_c_source(const char *filename, const uint8_t *buf, int buf_len, - const char *var_name) -{ - FILE *f; - int i; - - f = fopen(filename, "wb"); - if (!f) { - perror(filename); - exit(1); - } - fprintf(f, "/* This file is automatically generated - do not edit */\n\n"); - fprintf(f, "const uint8_t %s[] = {\n", var_name); - for(i = 0; i < buf_len; i++) { - fprintf(f, " 0x%02x,", buf[i]); - if ((i % 8) == 7 || (i == buf_len - 1)) - fprintf(f, "\n"); - } - fprintf(f, "};\n"); - fclose(f); -} - -#define DEFAULT_OUTPUT_FILENAME "out.js" - -void help(void) -{ - printf("jscompress version 1.0 Copyright (c) 2008-2018 Fabrice Bellard\n" - "usage: jscompress [options] filename\n" - "Javascript compressor\n" - "\n" - "-h print this help\n" - "-n do not compress spaces\n" - "-H keep the first comment\n" - "-c compress to file\n" - "-C name compress to C source ('name' is the variable name)\n" - "-D symbol define preprocessor symbol\n" - "-U symbol undefine preprocessor symbol\n" - "-o outfile set the output filename (default=%s)\n", - DEFAULT_OUTPUT_FILENAME); - exit(1); -} - -int main(int argc, char **argv) -{ - int c, do_strip, keep_header, compress; - const char *out_filename, *c_var, *fname; - char tmpfilename[1024]; - - do_strip = 1; - keep_header = 0; - out_filename = DEFAULT_OUTPUT_FILENAME; - compress = 0; - c_var = NULL; - for(;;) { - c = getopt(argc, argv, "hno:HcC:D:U:"); - if (c == -1) - break; - switch(c) { - case 'h': - help(); - break; - case 'n': - do_strip = 0; - break; - case 'o': - out_filename = optarg; - break; - case 'H': - keep_header = 1; - break; - case 'c': - compress = 1; - break; - case 'C': - c_var = optarg; - compress = 1; - break; - case 'D': - define_symbol(optarg); - break; - case 'U': - undefine_symbol(optarg); - break; - } - } - if (optind >= argc) - help(); - - filename = argv[optind++]; - - if (compress) { -#if defined(__ANDROID__) - /* XXX: use another directory ? */ - snprintf(tmpfilename, sizeof(tmpfilename), "out.%d", getpid()); -#else - snprintf(tmpfilename, sizeof(tmpfilename), "/tmp/out.%d", getpid()); -#endif - fname = tmpfilename; - } else { - fname = out_filename; - } - js_compress(filename, fname, do_strip, keep_header); - - if (compress) { - uint8_t *buf1, *buf2; - int buf1_len, buf2_len; - - buf1_len = load_file(&buf1, fname); - unlink(fname); - buf2_len = lz_compress(&buf2, buf1, buf1_len); - if (buf2_len < 0) { - fprintf(stderr, "Could not compress file (UTF8 chars are forbidden)\n"); - exit(1); - } - - if (c_var) { - save_c_source(out_filename, buf2, buf2_len, c_var); - } else { - save_file(out_filename, buf2, buf2_len); - } - free(buf1); - free(buf2); - } - return 0; -} diff --git a/libbf.h b/libbf.h index 6749b35..4576bf8 100644 --- a/libbf.h +++ b/libbf.h @@ -27,7 +27,7 @@ #include #include -#if defined(__x86_64__) +#if INTPTR_MAX >= INT64_MAX #define LIMB_LOG2_BITS 6 #else #define LIMB_LOG2_BITS 5 diff --git a/libregexp.c b/libregexp.c index bbb5e9d..379bfc7 100644 --- a/libregexp.c +++ b/libregexp.c @@ -75,7 +75,7 @@ typedef struct { int capture_count; int total_capture_count; /* -1 = not computed yet */ int has_named_captures; /* -1 = don't know, 0 = no, 1 = yes */ - void *mem_opaque; + void *opaque; DynBuf group_names; union { char error_msg[TMP_BUF_SIZE]; @@ -230,7 +230,7 @@ static int cr_init_char_range(REParseState *s, CharRange *cr, uint32_t c) invert = c & 1; c_pt = char_range_table[c >> 1]; len = *c_pt++; - cr_init(cr, s->mem_opaque, lre_realloc); + cr_init(cr, s->opaque, lre_realloc); for(i = 0; i < len * 2; i++) { if (cr_add_point(cr, c_pt[i])) goto fail; @@ -625,7 +625,7 @@ static int parse_unicode_property(REParseState *s, CharRange *cr, p++; q = name; while (is_unicode_char(*p)) { - if ((q - name) > sizeof(name) - 1) + if ((q - name) >= sizeof(name) - 1) goto unknown_property_name; *q++ = *p++; } @@ -634,7 +634,7 @@ static int parse_unicode_property(REParseState *s, CharRange *cr, if (*p == '=') { p++; while (is_unicode_char(*p)) { - if ((q - value) > sizeof(value) - 1) + if ((q - value) >= sizeof(value) - 1) return re_parse_error(s, "unknown unicode property value"); *q++ = *p++; } @@ -651,7 +651,7 @@ static int parse_unicode_property(REParseState *s, CharRange *cr, } else if (!strcmp(name, "Script_Extensions") || !strcmp(name, "scx")) { script_ext = TRUE; do_script: - cr_init(cr, s->mem_opaque, lre_realloc); + cr_init(cr, s->opaque, lre_realloc); ret = unicode_script(cr, value, script_ext); if (ret) { cr_free(cr); @@ -661,7 +661,7 @@ static int parse_unicode_property(REParseState *s, CharRange *cr, goto out_of_memory; } } else if (!strcmp(name, "General_Category") || !strcmp(name, "gc")) { - cr_init(cr, s->mem_opaque, lre_realloc); + cr_init(cr, s->opaque, lre_realloc); ret = unicode_general_category(cr, value); if (ret) { cr_free(cr); @@ -671,7 +671,7 @@ static int parse_unicode_property(REParseState *s, CharRange *cr, goto out_of_memory; } } else if (value[0] == '\0') { - cr_init(cr, s->mem_opaque, lre_realloc); + cr_init(cr, s->opaque, lre_realloc); ret = unicode_general_category(cr, name); if (ret == -1) { cr_free(cr); @@ -864,7 +864,7 @@ static int re_parse_char_class(REParseState *s, const uint8_t **pp) CharRange cr1_s, *cr1 = &cr1_s; BOOL invert; - cr_init(cr, s->mem_opaque, lre_realloc); + cr_init(cr, s->opaque, lre_realloc); p = *pp; p++; /* skip '[' */ invert = FALSE; @@ -1147,9 +1147,13 @@ static int re_parse_captures(REParseState *s, int *phas_named_captures, } } capture_index++; + if (capture_index >= CAPTURE_COUNT_MAX) + goto done; } } else { capture_index++; + if (capture_index >= CAPTURE_COUNT_MAX) + goto done; } break; case '\\': @@ -1163,6 +1167,7 @@ static int re_parse_captures(REParseState *s, int *phas_named_captures, break; } } + done: if (capture_name) return -1; else @@ -1734,6 +1739,9 @@ static int re_parse_disjunction(REParseState *s, BOOL is_backward_dir) { int start, len, pos; + if (lre_check_stack_overflow(s->opaque, 0)) + return re_parse_error(s, "stack overflow"); + start = s->byte_code.size; if (re_parse_alternative(s, is_backward_dir)) return -1; @@ -1819,7 +1827,7 @@ uint8_t *lre_compile(int *plen, char *error_msg, int error_msg_size, BOOL is_sticky; memset(s, 0, sizeof(*s)); - s->mem_opaque = opaque; + s->opaque = opaque; s->buf_ptr = (const uint8_t *)buf; s->buf_end = s->buf_ptr + buf_len; s->buf_start = s->buf_ptr; diff --git a/qjscalc.js b/qjscalc.js index 493869e..b7c5001 100644 --- a/qjscalc.js +++ b/qjscalc.js @@ -2625,6 +2625,17 @@ function atanh(a) return 0.5 * log((1 + x) / (1 - x)); } +function sigmoid(x) +{ + x = Float(x); + return 1 / (1 + exp(-x)); +} + +function lerp(a, b, t) +{ + return a + (b - a) * t; +} + var idn = Matrix.idn; var diag = Matrix.diag; var trans = Matrix.trans; diff --git a/quickjs-atom.h b/quickjs-atom.h index a353ad4..4c22794 100644 --- a/quickjs-atom.h +++ b/quickjs-atom.h @@ -113,6 +113,7 @@ DEF(caller, "caller") DEF(_eval_, "") DEF(_ret_, "") DEF(_var_, "") +DEF(_arg_var_, "") DEF(_with_, "") DEF(lastIndex, "lastIndex") DEF(target, "target") diff --git a/quickjs-libc.c b/quickjs-libc.c index 00a7536..e8b81e9 100644 --- a/quickjs-libc.c +++ b/quickjs-libc.c @@ -623,6 +623,97 @@ static JSValue js_std_getenv(JSContext *ctx, JSValueConst this_val, return JS_NewString(ctx, str); } +#if defined(_WIN32) +static void setenv(const char *name, const char *value, int overwrite) +{ + char *str; + size_t name_len, value_len; + name_len = strlen(name); + value_len = strlen(value); + str = malloc(name_len + 1 + value_len + 1); + memcpy(str, name, name_len); + str[name_len] = '='; + memcpy(str + name_len + 1, value, value_len); + str[name_len + 1 + value_len] = '\0'; + _putenv(str); + free(str); +} + +static void unsetenv(const char *name) +{ + setenv(name, "", TRUE); +} +#endif /* _WIN32 */ + +static JSValue js_std_setenv(JSContext *ctx, JSValueConst this_val, + int argc, JSValueConst *argv) +{ + const char *name, *value; + name = JS_ToCString(ctx, argv[0]); + if (!name) + return JS_EXCEPTION; + value = JS_ToCString(ctx, argv[1]); + if (!value) { + JS_FreeCString(ctx, name); + return JS_EXCEPTION; + } + setenv(name, value, TRUE); + JS_FreeCString(ctx, name); + JS_FreeCString(ctx, value); + return JS_UNDEFINED; +} + +static JSValue js_std_unsetenv(JSContext *ctx, JSValueConst this_val, + int argc, JSValueConst *argv) +{ + const char *name; + name = JS_ToCString(ctx, argv[0]); + if (!name) + return JS_EXCEPTION; + unsetenv(name); + JS_FreeCString(ctx, name); + return JS_UNDEFINED; +} + +/* return an object containing the list of the available environment + variables. */ +static JSValue js_std_getenviron(JSContext *ctx, JSValueConst this_val, + int argc, JSValueConst *argv) +{ + char **envp; + const char *name, *p, *value; + JSValue obj; + uint32_t idx; + size_t name_len; + JSAtom atom; + int ret; + + obj = JS_NewObject(ctx); + if (JS_IsException(obj)) + return JS_EXCEPTION; + envp = environ; + for(idx = 0; envp[idx] != NULL; idx++) { + name = envp[idx]; + p = strchr(name, '='); + name_len = p - name; + if (!p) + continue; + value = p + 1; + atom = JS_NewAtomLen(ctx, name, name_len); + if (atom == JS_ATOM_NULL) + goto fail; + ret = JS_DefinePropertyValue(ctx, obj, atom, JS_NewString(ctx, value), + JS_PROP_C_W_E); + JS_FreeAtom(ctx, atom); + if (ret < 0) + goto fail; + } + return obj; + fail: + JS_FreeValue(ctx, obj); + return JS_EXCEPTION; +} + static JSValue js_std_gc(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv) { @@ -1395,6 +1486,9 @@ static const JSCFunctionListEntry js_std_funcs[] = { JS_CFUNC_DEF("evalScript", 1, js_evalScript ), JS_CFUNC_DEF("loadScript", 1, js_loadScript ), JS_CFUNC_DEF("getenv", 1, js_std_getenv ), + JS_CFUNC_DEF("setenv", 1, js_std_setenv ), + JS_CFUNC_DEF("unsetenv", 1, js_std_unsetenv ), + JS_CFUNC_DEF("getenviron", 1, js_std_getenviron ), JS_CFUNC_DEF("urlGet", 1, js_std_urlGet ), JS_CFUNC_DEF("loadFile", 1, js_std_loadFile ), JS_CFUNC_DEF("strerror", 1, js_std_strerror ), @@ -1412,7 +1506,6 @@ static const JSCFunctionListEntry js_std_funcs[] = { JS_PROP_INT32_DEF("SEEK_CUR", SEEK_CUR, JS_PROP_CONFIGURABLE ), JS_PROP_INT32_DEF("SEEK_END", SEEK_END, JS_PROP_CONFIGURABLE ), JS_OBJECT_DEF("Error", js_std_error_props, countof(js_std_error_props), JS_PROP_CONFIGURABLE), - /* setenv, ... */ }; static const JSCFunctionListEntry js_std_file_proto_funcs[] = { diff --git a/quickjs-opcode.h b/quickjs-opcode.h index 387363c..c731a14 100644 --- a/quickjs-opcode.h +++ b/quickjs-opcode.h @@ -114,7 +114,7 @@ DEF( check_brand, 1, 2, 2, none) /* this_obj func -> this_obj func */ DEF( add_brand, 1, 2, 0, none) /* this_obj home_obj -> */ DEF( return_async, 1, 1, 0, none) DEF( throw, 1, 1, 0, none) -DEF( throw_var, 6, 0, 0, atom_u8) +DEF( throw_error, 6, 0, 0, atom_u8) DEF( eval, 5, 1, 1, npop_u16) /* func args... -> ret_val */ DEF( apply_eval, 3, 2, 1, u16) /* func array -> ret_eval */ DEF( regexp, 1, 2, 1, none) /* create a RegExp object from the pattern and a @@ -205,16 +205,15 @@ DEF( for_of_start, 1, 1, 3, none) DEF(for_await_of_start, 1, 1, 3, none) DEF( for_in_next, 1, 1, 3, none) DEF( for_of_next, 2, 3, 5, u8) -DEF(for_await_of_next, 1, 3, 4, none) +DEF(iterator_check_object, 1, 1, 1, none) DEF(iterator_get_value_done, 1, 1, 2, none) DEF( iterator_close, 1, 3, 0, none) DEF(iterator_close_return, 1, 4, 4, none) -DEF(async_iterator_close, 1, 3, 2, none) -DEF(async_iterator_next, 1, 4, 4, none) -DEF(async_iterator_get, 2, 4, 5, u8) +DEF( iterator_next, 1, 4, 4, none) +DEF( iterator_call, 2, 4, 5, u8) DEF( initial_yield, 1, 0, 0, none) DEF( yield, 1, 1, 2, none) -DEF( yield_star, 1, 2, 2, none) +DEF( yield_star, 1, 1, 2, none) DEF(async_yield_star, 1, 1, 2, none) DEF( await, 1, 1, 1, none) @@ -266,8 +265,6 @@ DEF( nop, 1, 0, 0, none) /* temporary opcodes: never emitted in the final bytecode */ -def(set_arg_valid_upto, 3, 0, 0, arg) /* emitted in phase 1, removed in phase 2 */ - def( enter_scope, 3, 0, 0, u16) /* emitted in phase 1, removed in phase 2 */ def( leave_scope, 3, 0, 0, u16) /* emitted in phase 1, removed in phase 2 */ diff --git a/quickjs.c b/quickjs.c index efc1d54..a39ff8f 100644 --- a/quickjs.c +++ b/quickjs.c @@ -199,7 +199,7 @@ typedef enum JSErrorEnum { } JSErrorEnum; #define JS_MAX_LOCAL_VARS 65536 -#define JS_STACK_SIZE_MAX 65536 +#define JS_STACK_SIZE_MAX 65534 #define JS_STRING_LEN_MAX ((1 << 30) - 1) #define __exception __attribute__((warn_unused_result)) @@ -506,14 +506,17 @@ typedef struct JSClosureVar { uint8_t is_arg : 1; uint8_t is_const : 1; uint8_t is_lexical : 1; - uint8_t var_kind : 3; /* see JSVarKindEnum */ - /* 9 bits available */ + uint8_t var_kind : 4; /* see JSVarKindEnum */ + /* 8 bits available */ uint16_t var_idx; /* is_local = TRUE: index to a normal variable of the parent function. otherwise: index to a closure variable of the parent function */ JSAtom var_name; } JSClosureVar; +#define ARG_SCOPE_INDEX 1 +#define ARG_SCOPE_END (-2) + typedef struct JSVarScope { int parent; /* index into fd->scopes of the enclosing scope */ int first; /* index into fd->vars of the last variable in this scope */ @@ -526,6 +529,7 @@ typedef enum { JS_VAR_NEW_FUNCTION_DECL, /* lexical var with async/generator function declaration */ JS_VAR_CATCH, + JS_VAR_FUNCTION_NAME, /* function expression name */ JS_VAR_PRIVATE_FIELD, JS_VAR_PRIVATE_METHOD, JS_VAR_PRIVATE_GETTER, @@ -533,12 +537,21 @@ typedef enum { JS_VAR_PRIVATE_GETTER_SETTER, /* must come after JS_VAR_PRIVATE_SETTER */ } JSVarKindEnum; +/* XXX: could use a different structure in bytecode functions to save + memory */ typedef struct JSVarDef { JSAtom var_name; - int scope_level; /* index into fd->scopes of this variable lexical scope */ - int scope_next; /* index into fd->vars of the next variable in the - * same or enclosing lexical scope */ - uint8_t is_func_var : 1; /* used for the function self reference */ + /* index into fd->scopes of this variable lexical scope */ + int scope_level; + /* during compilation: + - if scope_level = 0: scope in which the variable is defined + - if scope_level != 0: index into fd->vars of the next + variable in the same or enclosing lexical scope + in a bytecode function: + index into fd->vars of the next + variable in the same or enclosing lexical scope + */ + int scope_next; uint8_t is_const : 1; uint8_t is_lexical : 1; uint8_t is_captured : 1; @@ -548,7 +561,9 @@ typedef struct JSVarDef { JS_VAR_FUNCTION_DECL/JS_VAR_NEW_FUNCTION_DECL or scope level of the definition of the 'var' variables (they have scope_level = 0) */ - int func_pool_or_scope_idx : 24; /* only used during compilation */ + int func_pool_idx : 24; /* only used during compilation : index in + the constant pool for hoisted function + definition */ } JSVarDef; /* for the encoding of the pc2line table */ @@ -855,7 +870,7 @@ struct JSObject { uint8_t extensible : 1; uint8_t free_mark : 1; /* only used when freeing objects with cycles */ uint8_t is_exotic : 1; /* TRUE if object has exotic property handlers */ - uint8_t fast_array : 1; /* TRUE if u.array is used for get/put */ + uint8_t fast_array : 1; /* TRUE if u.array is used for get/put (for JS_CLASS_ARRAY, JS_CLASS_ARGUMENTS and typed arrays) */ uint8_t is_constructor : 1; /* TRUE if object is a constructor function */ uint8_t is_uncatchable_error : 1; /* if TRUE, error is not catchable */ uint8_t tmp_mark : 1; /* used in JS_WriteObjectRec() */ @@ -1000,7 +1015,7 @@ static JSValue JS_CallFree(JSContext *ctx, JSValue func_obj, JSValueConst this_o static JSValue JS_InvokeFree(JSContext *ctx, JSValue this_val, JSAtom atom, int argc, JSValueConst *argv); static __exception int JS_ToArrayLengthFree(JSContext *ctx, uint32_t *plen, - JSValue val); + JSValue val, BOOL is_array_ctor); static JSValue JS_EvalObject(JSContext *ctx, JSValueConst this_obj, JSValueConst val, int flags, int scope_idx); JSValue __attribute__((format(printf, 2, 3))) JS_ThrowInternalError(JSContext *ctx, const char *fmt, ...); @@ -1226,11 +1241,11 @@ static void add_gc_object(JSRuntime *rt, JSGCObjectHeader *h, JSGCObjectTypeEnum type); static void remove_gc_object(JSGCObjectHeader *h); static void js_async_function_free0(JSRuntime *rt, JSAsyncFunctionData *s); -static int js_instantiate_prototype(JSContext *ctx, JSObject *p, JSAtom atom, void *opaque); -static int js_module_ns_autoinit(JSContext *ctx, JSObject *p, JSAtom atom, +static JSValue js_instantiate_prototype(JSContext *ctx, JSObject *p, JSAtom atom, void *opaque); +static JSValue js_module_ns_autoinit(JSContext *ctx, JSObject *p, JSAtom atom, void *opaque); -static int JS_InstantiateFunctionListItem(JSContext *ctx, JSObject *p, - JSAtom atom, void *opaque); +static JSValue JS_InstantiateFunctionListItem2(JSContext *ctx, JSObject *p, + JSAtom atom, void *opaque); void JS_SetUncatchableError(JSContext *ctx, JSValueConst val, BOOL flag); static const JSClassExoticMethods js_arguments_exotic_methods; @@ -6710,6 +6725,21 @@ static JSValue JS_ThrowReferenceErrorUninitialized(JSContext *ctx, JSAtom name) JS_AtomGetStr(ctx, buf, sizeof(buf), name)); } +static JSValue JS_ThrowReferenceErrorUninitialized2(JSContext *ctx, + JSFunctionBytecode *b, + int idx, BOOL is_ref) +{ + JSAtom atom = JS_ATOM_NULL; + if (is_ref) { + atom = b->closure_var[idx].var_name; + } else { + /* not present if the function is stripped and contains no eval() */ + if (b->vardefs) + atom = b->vardefs[b->arg_count + idx].var_name; + } + return JS_ThrowReferenceErrorUninitialized(ctx, atom); +} + static JSValue JS_ThrowTypeErrorInvalidClass(JSContext *ctx, int class_id) { JSRuntime *rt = ctx->rt; @@ -6986,25 +7016,37 @@ int JS_IsInstanceOf(JSContext *ctx, JSValueConst val, JSValueConst obj) return JS_OrdinaryIsInstanceOf(ctx, val, obj); } -typedef int JSAutoInitFunc(JSContext *ctx, JSObject *p, JSAtom atom, void *opaque); +/* return the value associated to the autoinit property or an exception */ +typedef JSValue JSAutoInitFunc(JSContext *ctx, JSObject *p, JSAtom atom, void *opaque); static JSAutoInitFunc *js_autoinit_func_table[] = { js_instantiate_prototype, /* JS_AUTOINIT_ID_PROTOTYPE */ js_module_ns_autoinit, /* JS_AUTOINIT_ID_MODULE_NS */ - JS_InstantiateFunctionListItem, /* JS_AUTOINIT_ID_PROP */ + JS_InstantiateFunctionListItem2, /* JS_AUTOINIT_ID_PROP */ }; +/* warning: 'prs' is reallocated after it */ static int JS_AutoInitProperty(JSContext *ctx, JSObject *p, JSAtom prop, - JSProperty *pr) + JSProperty *pr, JSShapeProperty *prs) { - int ret; + JSValue val; JSContext *realm; JSAutoInitFunc *func; - + + if (js_shape_prepare_update(ctx, p, &prs)) + return -1; + realm = js_autoinit_get_realm(pr); func = js_autoinit_func_table[js_autoinit_get_id(pr)]; - ret = func(realm, p, prop, pr->u.init.opaque); - return ret; + /* 'func' shall not modify the object properties 'pr' */ + val = func(realm, p, prop, pr->u.init.opaque); + js_autoinit_free(ctx->rt, pr); + prs->flags &= ~JS_PROP_TMASK; + pr->u.value = JS_UNDEFINED; + if (JS_IsException(val)) + return -1; + pr->u.value = val; + return 0; } JSValue JS_GetPropertyInternal(JSContext *ctx, JSValueConst obj, @@ -7075,7 +7117,7 @@ JSValue JS_GetPropertyInternal(JSContext *ctx, JSValueConst obj, return JS_DupValue(ctx, val); } else if ((prs->flags & JS_PROP_TMASK) == JS_PROP_AUTOINIT) { /* Instantiate property and retry */ - if (JS_AutoInitProperty(ctx, p, prop, pr)) + if (JS_AutoInitProperty(ctx, p, prop, pr, prs)) return JS_EXCEPTION; continue; } @@ -7093,7 +7135,7 @@ JSValue JS_GetPropertyInternal(JSContext *ctx, JSValueConst obj, return JS_GetPropertyUint32(ctx, JS_MKPTR(JS_TAG_OBJECT, p), idx); } else if (p->class_id >= JS_CLASS_UINT8C_ARRAY && p->class_id <= JS_CLASS_FLOAT64_ARRAY) { - goto typed_array_oob; + return JS_UNDEFINED; } } else if (p->class_id >= JS_CLASS_UINT8C_ARRAY && p->class_id <= JS_CLASS_FLOAT64_ARRAY) { @@ -7102,9 +7144,6 @@ JSValue JS_GetPropertyInternal(JSContext *ctx, JSValueConst obj, if (ret != 0) { if (ret < 0) return JS_EXCEPTION; - typed_array_oob: - if (typed_array_is_detached(ctx, p)) - return JS_ThrowTypeErrorDetachedArrayBuffer(ctx); return JS_UNDEFINED; } } @@ -7337,6 +7376,22 @@ static int JS_CheckBrand(JSContext *ctx, JSValueConst obj, JSValueConst func) return 0; } +static uint32_t js_string_obj_get_length(JSContext *ctx, + JSValueConst obj) +{ + JSObject *p; + JSString *p1; + uint32_t len = 0; + + /* This is a class exotic method: obj class_id is JS_CLASS_STRING */ + p = JS_VALUE_GET_OBJ(obj); + if (JS_VALUE_GET_TAG(p->u.object_data) == JS_TAG_STRING) { + p1 = JS_VALUE_GET_STRING(p->u.object_data); + len = p1->len; + } + return len; +} + static int num_keys_cmp(const void *p1, const void *p2, void *opaque) { JSContext *ctx = opaque; @@ -7379,7 +7434,7 @@ static int __exception JS_GetOwnPropertyNamesInternal(JSContext *ctx, JSPropertyEnum *tab_atom, *tab_exotic; JSAtom atom; uint32_t num_keys_count, str_keys_count, sym_keys_count, atom_count; - uint32_t num_index, str_index, sym_index, exotic_count; + uint32_t num_index, str_index, sym_index, exotic_count, exotic_keys_count; BOOL is_enumerable, num_sorted; uint32_t num_key; JSAtomKindEnum kind; @@ -7392,6 +7447,7 @@ static int __exception JS_GetOwnPropertyNamesInternal(JSContext *ctx, num_keys_count = 0; str_keys_count = 0; sym_keys_count = 0; + exotic_keys_count = 0; exotic_count = 0; tab_exotic = NULL; sh = p->shape; @@ -7425,19 +7481,13 @@ static int __exception JS_GetOwnPropertyNamesInternal(JSContext *ctx, if (p->is_exotic) { if (p->fast_array) { - /* the implicit GetOwnProperty raises an exception if the - typed array is detached */ - if ((flags & (JS_GPN_SET_ENUM | JS_GPN_ENUM_ONLY)) && - (p->class_id >= JS_CLASS_UINT8C_ARRAY && - p->class_id <= JS_CLASS_FLOAT64_ARRAY) && - typed_array_is_detached(ctx, p) && - typed_array_get_length(ctx, p) != 0) { - JS_ThrowTypeErrorDetachedArrayBuffer(ctx); - return -1; - } if (flags & JS_GPN_STRING_MASK) { num_keys_count += p->u.array.count; } + } else if (p->class_id == JS_CLASS_STRING) { + if (flags & JS_GPN_STRING_MASK) { + num_keys_count += js_string_obj_get_length(ctx, JS_MKPTR(JS_TAG_OBJECT, p)); + } } else { const JSClassExoticMethods *em = ctx->rt->class_array[p->class_id].exotic; if (em && em->get_own_property_names) { @@ -7466,13 +7516,7 @@ static int __exception JS_GetOwnPropertyNamesInternal(JSContext *ctx, tab_exotic[i].is_enumerable = is_enumerable; } if (!(flags & JS_GPN_ENUM_ONLY) || is_enumerable) { - if (JS_AtomIsArrayIndex(ctx, &num_key, atom)) { - num_keys_count++; - } else if (kind == JS_ATOM_KIND_STRING) { - str_keys_count++; - } else { - sym_keys_count++; - } + exotic_keys_count++; } } } @@ -7482,7 +7526,7 @@ static int __exception JS_GetOwnPropertyNamesInternal(JSContext *ctx, /* fill them */ - atom_count = num_keys_count + str_keys_count + sym_keys_count; + atom_count = num_keys_count + str_keys_count + sym_keys_count + exotic_keys_count; /* avoid allocating 0 bytes */ tab_atom = js_malloc(ctx, sizeof(tab_atom[0]) * max_int(atom_count, 1)); if (!tab_atom) { @@ -7518,12 +7562,19 @@ static int __exception JS_GetOwnPropertyNamesInternal(JSContext *ctx, } if (p->is_exotic) { + int len; if (p->fast_array) { if (flags & JS_GPN_STRING_MASK) { - for(i = 0; i < p->u.array.count; i++) { + len = p->u.array.count; + goto add_array_keys; + } + } else if (p->class_id == JS_CLASS_STRING) { + if (flags & JS_GPN_STRING_MASK) { + len = js_string_obj_get_length(ctx, JS_MKPTR(JS_TAG_OBJECT, p)); + add_array_keys: + for(i = 0; i < len; i++) { tab_atom[num_index].atom = __JS_AtomFromUInt32(i); if (tab_atom[num_index].atom == JS_ATOM_NULL) { - js_free_prop_enum(ctx, tab_exotic, exotic_count); js_free_prop_enum(ctx, tab_atom, num_index); return -1; } @@ -7531,30 +7582,23 @@ static int __exception JS_GetOwnPropertyNamesInternal(JSContext *ctx, num_index++; } } - } - if (exotic_count > 0) { + } else { + /* Note: exotic keys are not reordered and comes after the object own properties. */ for(i = 0; i < exotic_count; i++) { atom = tab_exotic[i].atom; is_enumerable = tab_exotic[i].is_enumerable; kind = JS_AtomGetKind(ctx, atom); if ((!(flags & JS_GPN_ENUM_ONLY) || is_enumerable) && ((flags >> kind) & 1) != 0) { - if (JS_AtomIsArrayIndex(ctx, &num_key, atom)) { - j = num_index++; - num_sorted = FALSE; - } else if (kind == JS_ATOM_KIND_STRING) { - j = str_index++; - } else { - j = sym_index++; - } - tab_atom[j].atom = atom; - tab_atom[j].is_enumerable = is_enumerable; + tab_atom[sym_index].atom = atom; + tab_atom[sym_index].is_enumerable = is_enumerable; + sym_index++; } else { JS_FreeAtom(ctx, atom); } } + js_free(ctx, tab_exotic); } - js_free(ctx, tab_exotic); } assert(num_index == num_keys_count); @@ -7614,7 +7658,7 @@ retry: desc->value = JS_DupValue(ctx, val); } else if ((prs->flags & JS_PROP_TMASK) == JS_PROP_AUTOINIT) { /* Instantiate property and retry */ - if (JS_AutoInitProperty(ctx, p, prop, pr)) + if (JS_AutoInitProperty(ctx, p, prop, pr, prs)) return -1; goto retry; } @@ -7642,10 +7686,8 @@ retry: idx = __JS_AtomToUInt32(prop); if (idx < p->u.array.count) { if (desc) { - desc->flags = JS_PROP_WRITABLE | JS_PROP_ENUMERABLE; - if (p->class_id == JS_CLASS_ARRAY || - p->class_id == JS_CLASS_ARGUMENTS) - desc->flags |= JS_PROP_CONFIGURABLE; + desc->flags = JS_PROP_WRITABLE | JS_PROP_ENUMERABLE | + JS_PROP_CONFIGURABLE; desc->getter = JS_UNDEFINED; desc->setter = JS_UNDEFINED; desc->value = JS_GetPropertyUint32(ctx, JS_MKPTR(JS_TAG_OBJECT, p), idx); @@ -7653,19 +7695,6 @@ retry: return TRUE; } } - if (p->class_id >= JS_CLASS_UINT8C_ARRAY && - p->class_id <= JS_CLASS_FLOAT64_ARRAY) { - int ret; - ret = JS_AtomIsNumericIndex(ctx, prop); - if (ret != 0) { - if (ret < 0) - return -1; - if (typed_array_is_detached(ctx, p)) { - JS_ThrowTypeErrorDetachedArrayBuffer(ctx); - return -1; - } - } - } } else { const JSClassExoticMethods *em = ctx->rt->class_array[p->class_id].exotic; if (em && em->get_own_property) { @@ -7748,8 +7777,6 @@ int JS_HasProperty(JSContext *ctx, JSValueConst obj, JSAtom prop) if (ret != 0) { if (ret < 0) return -1; - /* the detached array test was done in - JS_GetOwnPropertyInternal() */ return FALSE; } } @@ -8074,7 +8101,7 @@ static int delete_property(JSContext *ctx, JSObject *p, JSAtom atom) return -1; goto redo; } else { - return FALSE; /* not configurable */ + return FALSE; } } } else { @@ -8114,15 +8141,19 @@ static int call_setter(JSContext *ctx, JSObject *setter, } /* set the array length and remove the array elements if necessary. */ -static int set_array_length(JSContext *ctx, JSObject *p, JSValue val, int flags) +static int set_array_length(JSContext *ctx, JSObject *p, JSValue val, + int flags) { uint32_t len, idx, cur_len; int i, ret; /* Note: this call can reallocate the properties of 'p' */ - ret = JS_ToArrayLengthFree(ctx, &len, val); + ret = JS_ToArrayLengthFree(ctx, &len, val, FALSE); if (ret) return -1; + /* JS_ToArrayLengthFree() must be done before the read-only test */ + if (unlikely(!(p->shape->prop[0].flags & JS_PROP_WRITABLE))) + return JS_ThrowTypeErrorReadOnly(ctx, flags, JS_ATOM_length); if (likely(p->fast_array)) { uint32_t old_len = p->u.array.count; @@ -8382,8 +8413,7 @@ retry: /* fast case */ set_value(ctx, &pr->u.value, val); return TRUE; - } else if ((prs->flags & (JS_PROP_LENGTH | JS_PROP_WRITABLE)) == - (JS_PROP_LENGTH | JS_PROP_WRITABLE)) { + } else if (prs->flags & JS_PROP_LENGTH) { assert(p->class_id == JS_CLASS_ARRAY); assert(prop == JS_ATOM_length); return set_array_length(ctx, p, val, flags); @@ -8399,7 +8429,7 @@ retry: return TRUE; } else if ((prs->flags & JS_PROP_TMASK) == JS_PROP_AUTOINIT) { /* Instantiate property and retry (potentially useless) */ - if (JS_AutoInitProperty(ctx, p, prop, pr)) { + if (JS_AutoInitProperty(ctx, p, prop, pr, prs)) { JS_FreeValue(ctx, val); return -1; } @@ -8437,10 +8467,6 @@ retry: JS_FreeValue(ctx, val); if (JS_IsException(val)) return -1; - if (typed_array_is_detached(ctx, p1)) { - JS_ThrowTypeErrorDetachedArrayBuffer(ctx); - return -1; - } return JS_ThrowTypeErrorOrFalse(ctx, flags, "out-of-bound numeric index"); } } @@ -8509,7 +8535,7 @@ retry: return call_setter(ctx, pr->u.getset.setter, this_obj, val, flags); } else if ((prs->flags & JS_PROP_TMASK) == JS_PROP_AUTOINIT) { /* Instantiate property and retry (potentially useless) */ - if (JS_AutoInitProperty(ctx, p1, prop, pr)) + if (JS_AutoInitProperty(ctx, p1, prop, pr, prs)) return -1; goto retry2; } else if (!(prs->flags & JS_PROP_WRITABLE)) { @@ -8677,12 +8703,7 @@ static int JS_SetPropertyValue(JSContext *ctx, JSValueConst this_obj, return -1; if (unlikely(idx >= (uint32_t)p->u.array.count)) { ta_out_of_bound: - if (typed_array_is_detached(ctx, p)) { - JS_ThrowTypeErrorDetachedArrayBuffer(ctx); - return -1; - } else { - return JS_ThrowTypeErrorOrFalse(ctx, flags, "out-of-bound numeric index"); - } + return JS_ThrowTypeErrorOrFalse(ctx, flags, "out-of-bound numeric index"); } p->u.array.u.double_ptr[idx] = d; break; @@ -8967,13 +8988,32 @@ int JS_DefineProperty(JSContext *ctx, JSValueConst this_obj, redo_prop_update: prs = find_own_property(&pr, p, prop); if (prs) { + /* the range of the Array length property is always tested before */ + if ((prs->flags & JS_PROP_LENGTH) && (flags & JS_PROP_HAS_VALUE)) { + uint32_t array_length; + if (JS_ToArrayLengthFree(ctx, &array_length, + JS_DupValue(ctx, val), FALSE)) { + return -1; + } + /* this code relies on the fact that Uint32 are never allocated */ + val = (JSValueConst)JS_NewUint32(ctx, array_length); + /* prs may have been modified */ + prs = find_own_property(&pr, p, prop); + assert(prs != NULL); + } /* property already exists */ if (!check_define_prop_flags(prs->flags, flags)) { not_configurable: return JS_ThrowTypeErrorOrFalse(ctx, flags, "property is not configurable"); } - retry: + if ((prs->flags & JS_PROP_TMASK) == JS_PROP_AUTOINIT) { + /* Instantiate property and retry */ + if (JS_AutoInitProperty(ctx, p, prop, pr, prs)) + return -1; + goto redo_prop_update; + } + if (flags & (JS_PROP_HAS_VALUE | JS_PROP_HAS_WRITABLE | JS_PROP_HAS_GET | JS_PROP_HAS_SET)) { if (flags & (JS_PROP_HAS_GET | JS_PROP_HAS_SET)) { @@ -8996,14 +9036,6 @@ int JS_DefineProperty(JSContext *ctx, JSValueConst this_obj, /* convert to getset */ if ((prs->flags & JS_PROP_TMASK) == JS_PROP_VARREF) { free_var_ref(ctx->rt, pr->u.var_ref); - } else if ((prs->flags & JS_PROP_TMASK) == JS_PROP_AUTOINIT) { - /* clear property and update */ - if (js_shape_prepare_update(ctx, p, &prs)) - return -1; - js_autoinit_free(ctx->rt, pr); - prs->flags &= ~JS_PROP_TMASK; - pr->u.value = JS_UNDEFINED; - goto retry; } else { JS_FreeValue(ctx, pr->u.value); } @@ -9051,39 +9083,17 @@ int JS_DefineProperty(JSContext *ctx, JSValueConst this_obj, pr->u.value = JS_UNDEFINED; } else if ((prs->flags & JS_PROP_TMASK) == JS_PROP_VARREF) { /* Note: JS_PROP_VARREF is always writable */ - } else if ((prs->flags & JS_PROP_TMASK) == JS_PROP_AUTOINIT) { - /* clear property and update */ - if (js_shape_prepare_update(ctx, p, &prs)) - return -1; - js_autoinit_free(ctx->rt, pr); - prs->flags &= ~JS_PROP_TMASK; - pr->u.value = JS_UNDEFINED; } else { if ((prs->flags & (JS_PROP_CONFIGURABLE | JS_PROP_WRITABLE)) == 0 && - (flags & JS_PROP_HAS_VALUE) && - !js_same_value(ctx, val, pr->u.value)) { - goto not_configurable; + (flags & JS_PROP_HAS_VALUE)) { + if (!js_same_value(ctx, val, pr->u.value)) { + goto not_configurable; + } else { + return TRUE; + } } } - if (prs->flags & JS_PROP_LENGTH) { - if (flags & JS_PROP_HAS_VALUE) { - res = set_array_length(ctx, p, JS_DupValue(ctx, val), - flags); - } else { - res = TRUE; - } - /* still need to reset the writable flag if needed. - The JS_PROP_LENGTH is reset to have the correct - read-only behavior in JS_SetProperty(). */ - if ((flags & (JS_PROP_HAS_WRITABLE | JS_PROP_WRITABLE)) == - JS_PROP_HAS_WRITABLE) { - prs = get_shape_prop(p->shape); - if (js_update_property_flags(ctx, p, &prs, - prs->flags & ~(JS_PROP_WRITABLE | JS_PROP_LENGTH))) - return -1; - } - return res; - } else if ((prs->flags & JS_PROP_TMASK) == JS_PROP_VARREF) { + if ((prs->flags & JS_PROP_TMASK) == JS_PROP_VARREF) { if (flags & JS_PROP_HAS_VALUE) { if (p->class_id == JS_CLASS_MODULE_NS) { /* JS_PROP_WRITABLE is always true for variable @@ -9107,9 +9117,27 @@ int JS_DefineProperty(JSContext *ctx, JSValueConst this_obj, pr->u.value = val1; prs->flags &= ~(JS_PROP_TMASK | JS_PROP_WRITABLE); } - } else if ((prs->flags & JS_PROP_TMASK) == JS_PROP_AUTOINIT) { - /* XXX: should never happen, type was reset above */ - abort(); + } else if (prs->flags & JS_PROP_LENGTH) { + if (flags & JS_PROP_HAS_VALUE) { + /* Note: no JS code is executable because + 'val' is guaranted to be a Uint32 */ + res = set_array_length(ctx, p, JS_DupValue(ctx, val), + flags); + } else { + res = TRUE; + } + /* still need to reset the writable flag if + needed. The JS_PROP_LENGTH is kept because the + Uint32 test is still done if the length + property is read-only. */ + if ((flags & (JS_PROP_HAS_WRITABLE | JS_PROP_WRITABLE)) == + JS_PROP_HAS_WRITABLE) { + prs = get_shape_prop(p->shape); + if (js_update_property_flags(ctx, p, &prs, + prs->flags & ~JS_PROP_WRITABLE)) + return -1; + } + return res; } else { if (flags & JS_PROP_HAS_VALUE) { JS_FreeValue(ctx, pr->u.value); @@ -9194,9 +9222,9 @@ int JS_DefineProperty(JSContext *ctx, JSValueConst this_obj, typed_array_oob: return JS_ThrowTypeErrorOrFalse(ctx, flags, "out-of-bound index in typed array"); } - prop_flags = get_prop_flags(flags, JS_PROP_ENUMERABLE | JS_PROP_WRITABLE); + prop_flags = get_prop_flags(flags, JS_PROP_ENUMERABLE | JS_PROP_WRITABLE | JS_PROP_CONFIGURABLE); if (flags & (JS_PROP_HAS_GET | JS_PROP_HAS_SET) || - prop_flags != (JS_PROP_ENUMERABLE | JS_PROP_WRITABLE)) { + prop_flags != (JS_PROP_ENUMERABLE | JS_PROP_WRITABLE | JS_PROP_CONFIGURABLE)) { return JS_ThrowTypeErrorOrFalse(ctx, flags, "invalid descriptor flags"); } if (flags & JS_PROP_HAS_VALUE) { @@ -9581,9 +9609,8 @@ static int JS_SetGlobalVar(JSContext *ctx, JSAtom prop, JSValue val, set_value(ctx, &pr->u.value, val); return 0; } - flags = JS_PROP_THROW_STRICT; - if (flag != 2 && is_strict_mode(ctx)) + if (is_strict_mode(ctx)) flags |= JS_PROP_NO_ADD; return JS_SetPropertyInternal(ctx, ctx->global_obj, prop, val, flags); } @@ -10918,11 +10945,10 @@ static int JS_ToUint8ClampFree(JSContext *ctx, int32_t *pres, JSValue val) } static __exception int JS_ToArrayLengthFree(JSContext *ctx, uint32_t *plen, - JSValue val) + JSValue val, BOOL is_array_ctor) { uint32_t tag, len; - redo: tag = JS_VALUE_GET_TAG(val); switch(tag) { case JS_TAG_INT: @@ -10959,16 +10985,36 @@ static __exception int JS_ToArrayLengthFree(JSContext *ctx, uint32_t *plen, double d; d = JS_VALUE_GET_FLOAT64(val); len = (uint32_t)d; - if (len != d) { - fail: - JS_ThrowRangeError(ctx, "invalid array length"); - return -1; - } + if (len != d) + goto fail; } else { - val = JS_ToNumberFree(ctx, val); - if (JS_IsException(val)) - return -1; - goto redo; + uint32_t len1; + + if (is_array_ctor) { + val = JS_ToNumberFree(ctx, val); + if (JS_IsException(val)) + return -1; + /* cannot recurse because val is a number */ + if (JS_ToArrayLengthFree(ctx, &len, val, TRUE)) + return -1; + } else { + /* legacy behavior: must do the conversion twice and compare */ + if (JS_ToUint32(ctx, &len, val)) { + JS_FreeValue(ctx, val); + return -1; + } + val = JS_ToNumberFree(ctx, val); + if (JS_IsException(val)) + return -1; + /* cannot recurse because val is a number */ + if (JS_ToArrayLengthFree(ctx, &len1, val, FALSE)) + return -1; + if (len1 != len) { + fail: + JS_ThrowRangeError(ctx, "invalid array length"); + return -1; + } + } } break; } @@ -15031,15 +15077,6 @@ static JSValue build_for_in_iterator(JSContext *ctx, JSValue obj) if (prs->flags & JS_PROP_ENUMERABLE) goto normal_case; } - /* the implicit GetOwnProperty raises an exception if the - typed array is detached */ - if ((p->class_id >= JS_CLASS_UINT8C_ARRAY && - p->class_id <= JS_CLASS_FLOAT64_ARRAY) && - typed_array_is_detached(ctx, p) && - typed_array_get_length(ctx, p) != 0) { - JS_ThrowTypeErrorDetachedArrayBuffer(ctx); - goto fail; - } /* for fast arrays, we only store the number of elements */ it->is_array = TRUE; it->array_length = p->u.array.count; @@ -15349,16 +15386,6 @@ static __exception int js_for_of_next(JSContext *ctx, JSValue *sp, int offset) return 0; } -static __exception int js_for_await_of_next(JSContext *ctx, JSValue *sp) -{ - JSValue result; - result = JS_Call(ctx, sp[-2], sp[-3], 0, NULL); - if (JS_IsException(result)) - return -1; - sp[0] = result; - return 0; -} - static JSValue JS_IteratorGetCompleteValue(JSContext *ctx, JSValueConst obj, BOOL *pdone) { @@ -15663,7 +15690,7 @@ static JSValue js_closure2(JSContext *ctx, JSValue func_obj, return JS_EXCEPTION; } -static int js_instantiate_prototype(JSContext *ctx, JSObject *p, JSAtom atom, void *opaque) +static JSValue js_instantiate_prototype(JSContext *ctx, JSObject *p, JSAtom atom, void *opaque) { JSValue obj, this_val; int ret; @@ -15671,15 +15698,17 @@ static int js_instantiate_prototype(JSContext *ctx, JSObject *p, JSAtom atom, vo this_val = JS_MKPTR(JS_TAG_OBJECT, p); obj = JS_NewObject(ctx); if (JS_IsException(obj)) - return -1; + return JS_EXCEPTION; set_cycle_flag(ctx, obj); set_cycle_flag(ctx, this_val); ret = JS_DefinePropertyValue(ctx, obj, JS_ATOM_constructor, JS_DupValue(ctx, this_val), JS_PROP_WRITABLE | JS_PROP_CONFIGURABLE); - if (JS_DefinePropertyValue(ctx, this_val, atom, obj, JS_PROP_WRITABLE) < 0 || ret < 0) - return -1; - return 0; + if (ret < 0) { + JS_FreeValue(ctx, obj); + return JS_EXCEPTION; + } + return obj; } static const uint16_t func_kind_to_class_id[] = { @@ -16645,11 +16674,12 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, JS_Throw(ctx, *--sp); goto exception; - CASE(OP_throw_var): + CASE(OP_throw_error): #define JS_THROW_VAR_RO 0 #define JS_THROW_VAR_REDECL 1 #define JS_THROW_VAR_UNINITIALIZED 2 -#define JS_THROW_VAR_DELETE_SUPER 3 +#define JS_THROW_ERROR_DELETE_SUPER 3 +#define JS_THROW_ERROR_ITERATOR_THROW 4 { JSAtom atom; int type; @@ -16665,8 +16695,11 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, if (type == JS_THROW_VAR_UNINITIALIZED) JS_ThrowReferenceErrorUninitialized(ctx, atom); else - if (type == JS_THROW_VAR_DELETE_SUPER) + if (type == JS_THROW_ERROR_DELETE_SUPER) JS_ThrowReferenceError(ctx, "unsupported reference to 'super'"); + else + if (type == JS_THROW_ERROR_ITERATOR_THROW) + JS_ThrowTypeError(ctx, "iterator does not have a throw method"); else JS_ThrowInternalError(ctx, "invalid throw var type %d", type); } @@ -16995,7 +17028,7 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, pc += 2; val = *var_refs[idx]->pvalue; if (unlikely(JS_IsUninitialized(val))) { - JS_ThrowReferenceErrorUninitialized(ctx, JS_ATOM_NULL); + JS_ThrowReferenceErrorUninitialized2(ctx, b, idx, TRUE); goto exception; } sp[0] = JS_DupValue(ctx, val); @@ -17008,7 +17041,7 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, idx = get_u16(pc); pc += 2; if (unlikely(JS_IsUninitialized(*var_refs[idx]->pvalue))) { - JS_ThrowReferenceErrorUninitialized(ctx, JS_ATOM_NULL); + JS_ThrowReferenceErrorUninitialized2(ctx, b, idx, TRUE); goto exception; } set_value(ctx, var_refs[idx]->pvalue, sp[-1]); @@ -17021,7 +17054,7 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, idx = get_u16(pc); pc += 2; if (unlikely(!JS_IsUninitialized(*var_refs[idx]->pvalue))) { - JS_ThrowReferenceErrorUninitialized(ctx, JS_ATOM_NULL); + JS_ThrowReferenceErrorUninitialized2(ctx, b, idx, TRUE); goto exception; } set_value(ctx, var_refs[idx]->pvalue, sp[-1]); @@ -17042,7 +17075,7 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, idx = get_u16(pc); pc += 2; if (unlikely(JS_IsUninitialized(var_buf[idx]))) { - JS_ThrowReferenceErrorUninitialized(ctx, JS_ATOM_NULL); + JS_ThrowReferenceErrorUninitialized2(ctx, b, idx, FALSE); goto exception; } sp[0] = JS_DupValue(ctx, var_buf[idx]); @@ -17055,7 +17088,7 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, idx = get_u16(pc); pc += 2; if (unlikely(JS_IsUninitialized(var_buf[idx]))) { - JS_ThrowReferenceErrorUninitialized(ctx, JS_ATOM_NULL); + JS_ThrowReferenceErrorUninitialized2(ctx, b, idx, FALSE); goto exception; } set_value(ctx, &var_buf[idx], sp[-1]); @@ -17294,16 +17327,17 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, sp += 1; *sp++ = JS_NewCatchOffset(ctx, 0); BREAK; - CASE(OP_for_await_of_next): - if (js_for_await_of_next(ctx, sp)) - goto exception; - sp += 1; - BREAK; CASE(OP_iterator_get_value_done): if (js_iterator_get_value_done(ctx, sp)) goto exception; sp += 1; BREAK; + CASE(OP_iterator_check_object): + if (unlikely(!JS_IsObject(sp[-1]))) { + JS_ThrowTypeError(ctx, "iterator must return an object"); + goto exception; + } + BREAK; CASE(OP_iterator_close): /* iter_obj next catch_offset -> */ @@ -17340,37 +17374,7 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, } BREAK; - CASE(OP_async_iterator_close): - /* iter_obj next catch_offset -> value flag */ - { - JSValue ret, method; - int ret_flag; - sp--; /* remove the catch offset */ - method = JS_GetProperty(ctx, sp[-2], JS_ATOM_return); - if (JS_IsException(method)) - goto exception; - if (JS_IsUndefined(method) || JS_IsNull(method)) { - ret = JS_UNDEFINED; - ret_flag = TRUE; - } else { - ret = JS_CallFree(ctx, method, sp[-2], 0, NULL); - if (JS_IsException(ret)) - goto exception; - if (!JS_IsObject(ret)) { - JS_FreeValue(ctx, ret); - JS_ThrowTypeErrorNotAnObject(ctx); - goto exception; - } - ret_flag = FALSE; - } - JS_FreeValue(ctx, sp[-2]); - JS_FreeValue(ctx, sp[-1]); - sp[-2] = ret; - sp[-1] = JS_NewBool(ctx, ret_flag); - } - BREAK; - - CASE(OP_async_iterator_next): + CASE(OP_iterator_next): /* stack: iter_obj next catch_offset val */ { JSValue ret; @@ -17383,26 +17387,28 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, } BREAK; - CASE(OP_async_iterator_get): + CASE(OP_iterator_call): /* stack: iter_obj next catch_offset val */ { JSValue method, ret; BOOL ret_flag; int flags; flags = *pc++; - /* XXX: use another opcode such as OP_throw_var */ - if (flags == 2) { - JS_ThrowTypeError(ctx, "iterator does not have a throw method"); - goto exception; - } - method = JS_GetProperty(ctx, sp[-4], flags ? JS_ATOM_throw : JS_ATOM_return); + method = JS_GetProperty(ctx, sp[-4], (flags & 1) ? + JS_ATOM_throw : JS_ATOM_return); if (JS_IsException(method)) goto exception; if (JS_IsUndefined(method) || JS_IsNull(method)) { ret_flag = TRUE; } else { - ret = JS_CallFree(ctx, method, sp[-4], - 1, (JSValueConst *)(sp - 1)); + if (flags & 2) { + /* no argument */ + ret = JS_CallFree(ctx, method, sp[-4], + 0, NULL); + } else { + ret = JS_CallFree(ctx, method, sp[-4], + 1, (JSValueConst *)(sp - 1)); + } if (JS_IsException(ret)) goto exception; JS_FreeValue(ctx, sp[-1]); @@ -17728,7 +17734,8 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, CASE(OP_put_ref_value): { - int ret; + int ret, flags; + flags = JS_PROP_THROW_STRICT; if (unlikely(JS_IsUndefined(sp[-3]))) { if (is_strict_mode(ctx)) { JSAtom atom = JS_ValueToAtom(ctx, sp[-2]); @@ -17740,8 +17747,11 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, } else { sp[-3] = JS_DupValue(ctx, ctx->global_obj); } + } else { + if (is_strict_mode(ctx)) + flags |= JS_PROP_NO_ADD; } - ret = JS_SetPropertyValue(ctx, sp[-3], sp[-2], sp[-1], JS_PROP_THROW_STRICT); + ret = JS_SetPropertyValue(ctx, sp[-3], sp[-2], sp[-1], flags); JS_FreeValue(ctx, sp[-3]); sp -= 3; if (unlikely(ret < 0)) @@ -18084,8 +18094,12 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, var_buf[idx] = JS_NewInt32(ctx, val + 1); } else { inc_loc_slow: - if (js_unary_arith_slow(ctx, var_buf + idx + 1, OP_inc)) + /* must duplicate otherwise the variable value may + be destroyed before JS code accesses it */ + op1 = JS_DupValue(ctx, op1); + if (js_unary_arith_slow(ctx, &op1 + 1, OP_inc)) goto exception; + set_value(ctx, &var_buf[idx], op1); } } BREAK; @@ -18105,8 +18119,12 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, var_buf[idx] = JS_NewInt32(ctx, val - 1); } else { dec_loc_slow: - if (js_unary_arith_slow(ctx, var_buf + idx + 1, OP_dec)) + /* must duplicate otherwise the variable value may + be destroyed before JS code accesses it */ + op1 = JS_DupValue(ctx, op1); + if (js_unary_arith_slow(ctx, &op1 + 1, OP_dec)) goto exception; + set_value(ctx, &var_buf[idx], op1); } } BREAK; @@ -18432,6 +18450,7 @@ static JSValue JS_CallInternal(JSContext *caller_ctx, JSValueConst func_obj, set_value(ctx, &sp[-1], val); break; case OP_with_put_var: + /* XXX: check if strict mode */ ret = JS_SetPropertyInternal(ctx, obj, atom, sp[-2], JS_PROP_THROW_STRICT); JS_FreeValue(ctx, sp[-1]); @@ -18922,13 +18941,11 @@ static JSValue js_generator_next(JSContext *ctx, JSValueConst this_val, JSGeneratorData *s = JS_GetOpaque(this_val, JS_CLASS_GENERATOR); JSStackFrame *sf; JSValue ret, func_ret; - JSValueConst iter_args[1]; *pdone = TRUE; if (!s) return JS_ThrowTypeError(ctx, "not a generator"); sf = &s->func_state.frame; - redo: switch(s->state) { default: case JS_GENERATOR_STATE_SUSPENDED_START: @@ -18940,85 +18957,16 @@ static JSValue js_generator_next(JSContext *ctx, JSValueConst this_val, } break; case JS_GENERATOR_STATE_SUSPENDED_YIELD_STAR: - { - int done; - JSValue method, iter_obj; - - iter_obj = sf->cur_sp[-2]; - if (magic == GEN_MAGIC_NEXT) { - method = JS_DupValue(ctx, sf->cur_sp[-1]); - } else { - method = JS_GetProperty(ctx, iter_obj, - magic == GEN_MAGIC_RETURN ? - JS_ATOM_return : JS_ATOM_throw); - if (JS_IsException(method)) - goto iter_exception; - } - if (magic != GEN_MAGIC_NEXT && - (JS_IsUndefined(method) || JS_IsNull(method))) { - /* default action */ - if (magic == GEN_MAGIC_RETURN) { - ret = JS_DupValue(ctx, argv[0]); - goto iter_done; - } else { - if (JS_IteratorClose(ctx, iter_obj, FALSE)) - goto iter_exception; - JS_ThrowTypeError(ctx, "iterator does not have a throw method"); - goto iter_exception; - } - } - ret = JS_IteratorNext2(ctx, iter_obj, method, argc, argv, &done); - JS_FreeValue(ctx, method); - if (JS_IsException(ret)) { - iter_exception: - goto exec_throw; - } - /* if not done, the iterator returns the exact object - returned by 'method' */ - if (done == 2) { - JSValue done_val, value; - done_val = JS_GetProperty(ctx, ret, JS_ATOM_done); - if (JS_IsException(done_val)) { - JS_FreeValue(ctx, ret); - goto iter_exception; - } - done = JS_ToBoolFree(ctx, done_val); - if (done) { - value = JS_GetProperty(ctx, ret, JS_ATOM_value); - JS_FreeValue(ctx, ret); - if (JS_IsException(value)) - goto iter_exception; - ret = value; - goto iter_done; - } else { - *pdone = 2; - } - } else { - if (done) { - /* 'yield *' returns the value associated to done = true */ - iter_done: - JS_FreeValue(ctx, sf->cur_sp[-2]); - JS_FreeValue(ctx, sf->cur_sp[-1]); - sf->cur_sp--; - goto exec_arg; - } else { - *pdone = FALSE; - } - } - break; - } - break; case JS_GENERATOR_STATE_SUSPENDED_YIELD: /* cur_sp[-1] was set to JS_UNDEFINED in the previous call */ ret = JS_DupValue(ctx, argv[0]); - if (magic == GEN_MAGIC_THROW) { + if (magic == GEN_MAGIC_THROW && + s->state == JS_GENERATOR_STATE_SUSPENDED_YIELD) { JS_Throw(ctx, ret); - exec_throw: s->func_state.throw_flag = TRUE; } else { - exec_arg: sf->cur_sp[-1] = ret; - sf->cur_sp[0] = JS_NewBool(ctx, (magic == GEN_MAGIC_RETURN)); + sf->cur_sp[0] = JS_NewInt32(ctx, magic); sf->cur_sp++; exec_no_arg: s->func_state.throw_flag = FALSE; @@ -19032,17 +18980,14 @@ static JSValue js_generator_next(JSContext *ctx, JSValueConst this_val, return func_ret; } if (JS_VALUE_GET_TAG(func_ret) == JS_TAG_INT) { + /* get the returned yield value at the top of the stack */ + ret = sf->cur_sp[-1]; + sf->cur_sp[-1] = JS_UNDEFINED; if (JS_VALUE_GET_INT(func_ret) == FUNC_RET_YIELD_STAR) { - /* 'yield *' */ s->state = JS_GENERATOR_STATE_SUSPENDED_YIELD_STAR; - iter_args[0] = JS_UNDEFINED; - argc = 1; - argv = iter_args; - goto redo; + /* return (value, done) object */ + *pdone = 2; } else { - /* get the return the yield value at the top of the stack */ - ret = sf->cur_sp[-1]; - sf->cur_sp[-1] = JS_UNDEFINED; *pdone = FALSE; } } else { @@ -19853,15 +19798,15 @@ typedef struct BlockEnv { int has_iterator; } BlockEnv; -typedef struct JSHoistedDef { - int cpool_idx; /* -1 means variable global definition */ - uint8_t force_init : 1; /* initialize to undefined */ +typedef struct JSGlobalVar { + int cpool_idx; /* if >= 0, index in the constant pool for hoisted + function defintion*/ + uint8_t force_init : 1; /* force initialization to undefined */ uint8_t is_lexical : 1; /* global let/const definition */ uint8_t is_const : 1; /* const definition */ - int var_idx; /* function object index if cpool_idx >= 0 */ int scope_level; /* scope of definition */ - JSAtom var_name; /* variable name if cpool_idx < 0 */ -} JSHoistedDef; + JSAtom var_name; /* variable name */ +} JSGlobalVar; typedef struct RelocEntry { struct RelocEntry *next; @@ -19924,6 +19869,7 @@ typedef struct JSFunctionDef { BOOL has_home_object; /* TRUE if the home object is available */ BOOL has_prototype; /* true if a prototype field is necessary */ BOOL has_simple_parameter_list; + BOOL has_parameter_expressions; /* if true, an argument scope is created */ BOOL has_use_strict; /* to reject directive in special cases */ BOOL has_eval_call; /* true if the function contains a call to eval() */ BOOL has_arguments_binding; /* true if the 'arguments' binding is @@ -19951,7 +19897,10 @@ typedef struct JSFunctionDef { int arg_count; /* number of arguments */ int defined_arg_count; int var_object_idx; /* -1 if none */ + int arg_var_object_idx; /* -1 if none (var object for the argument scope) */ int arguments_var_idx; /* -1 if none */ + int arguments_arg_idx; /* argument variable definition in argument scope, + -1 if none */ int func_var_idx; /* variable containing the current function (-1 if none, only used if is_func_expr is true) */ int eval_ret_idx; /* variable containing the return value of the eval, -1 if none */ @@ -19967,10 +19916,11 @@ typedef struct JSFunctionDef { int scope_count; /* number of entries used in the fd->scopes array */ JSVarScope *scopes; JSVarScope def_scope_array[4]; + int body_scope; /* scope of the body of the function or eval */ - int hoisted_def_count; - int hoisted_def_size; - JSHoistedDef *hoisted_def; + int global_var_count; + int global_var_size; + JSGlobalVar *global_vars; DynBuf byte_code; int last_opcode_pos; /* -1 if no last opcode */ @@ -21475,7 +21425,7 @@ static BOOL js_is_live_code(JSParseState *s) { case OP_return_undef: case OP_return_async: case OP_throw: - case OP_throw_var: + case OP_throw_error: case OP_goto: #if SHORT_OPCODES case OP_goto8: @@ -21647,6 +21597,21 @@ static int find_var(JSContext *ctx, JSFunctionDef *fd, JSAtom name) return find_arg(ctx, fd, name); } +/* find a variable declaration in a given scope */ +static int find_var_in_scope(JSContext *ctx, JSFunctionDef *fd, + JSAtom name, int scope_level) +{ + int scope_idx; + for(scope_idx = fd->scopes[scope_level].first; scope_idx >= 0; + scope_idx = fd->vars[scope_idx].scope_next) { + if (fd->vars[scope_idx].scope_level != scope_level) + break; + if (fd->vars[scope_idx].var_name == name) + return scope_idx; + } + return -1; +} + /* return true if scope == parent_scope or if scope is a child of parent_scope */ static BOOL is_child_scope(JSContext *ctx, JSFunctionDef *fd, @@ -21668,7 +21633,7 @@ static int find_var_in_child_scope(JSContext *ctx, JSFunctionDef *fd, for(i = 0; i < fd->var_count; i++) { JSVarDef *vd = &fd->vars[i]; if (vd->var_name == name && vd->scope_level == 0) { - if (is_child_scope(ctx, fd, vd->func_pool_or_scope_idx, + if (is_child_scope(ctx, fd, vd->scope_next, scope_level)) return i; } @@ -21677,11 +21642,11 @@ static int find_var_in_child_scope(JSContext *ctx, JSFunctionDef *fd, } -static JSHoistedDef *find_hoisted_def(JSFunctionDef *fd, JSAtom name) +static JSGlobalVar *find_global_var(JSFunctionDef *fd, JSAtom name) { int i; - for(i = 0; i < fd->hoisted_def_count; i++) { - JSHoistedDef *hf = &fd->hoisted_def[i]; + for(i = 0; i < fd->global_var_count; i++) { + JSGlobalVar *hf = &fd->global_vars[i]; if (hf->var_name == name) return hf; } @@ -21689,9 +21654,9 @@ static JSHoistedDef *find_hoisted_def(JSFunctionDef *fd, JSAtom name) } -static JSHoistedDef *find_lexical_hoisted_def(JSFunctionDef *fd, JSAtom name) +static JSGlobalVar *find_lexical_global_var(JSFunctionDef *fd, JSAtom name) { - JSHoistedDef *hf = find_hoisted_def(fd, name); + JSGlobalVar *hf = find_global_var(fd, name); if (hf && hf->is_lexical) return hf; else @@ -21711,7 +21676,7 @@ static int find_lexical_decl(JSContext *ctx, JSFunctionDef *fd, JSAtom name, } if (fd->is_eval && fd->eval_type == JS_EVAL_TYPE_GLOBAL) { - if (find_lexical_hoisted_def(fd, name)) + if (find_lexical_global_var(fd, name)) return GLOBAL_VAR_OFFSET; } return -1; @@ -21800,6 +21765,7 @@ static int add_var(JSContext *ctx, JSFunctionDef *fd, JSAtom name) vd = &fd->vars[fd->var_count++]; memset(vd, 0, sizeof(*vd)); vd->var_name = JS_DupAtom(ctx, name); + vd->func_pool_idx = -1; return fd->var_count - 1; } @@ -21823,22 +21789,47 @@ static int add_func_var(JSContext *ctx, JSFunctionDef *fd, JSAtom name) int idx = fd->func_var_idx; if (idx < 0 && (idx = add_var(ctx, fd, name)) >= 0) { fd->func_var_idx = idx; - fd->vars[idx].is_func_var = TRUE; + fd->vars[idx].var_kind = JS_VAR_FUNCTION_NAME; if (fd->js_mode & JS_MODE_STRICT) fd->vars[idx].is_const = TRUE; } return idx; } -static int add_arguments_var(JSContext *ctx, JSFunctionDef *fd, JSAtom name) +static int add_arguments_var(JSContext *ctx, JSFunctionDef *fd) { int idx = fd->arguments_var_idx; - if (idx < 0 && (idx = add_var(ctx, fd, name)) >= 0) { + if (idx < 0 && (idx = add_var(ctx, fd, JS_ATOM_arguments)) >= 0) { fd->arguments_var_idx = idx; } return idx; } +/* add an argument definition in the argument scope. Only needed when + "eval()" may be called in the argument scope. Return 0 if OK. */ +static int add_arguments_arg(JSContext *ctx, JSFunctionDef *fd) +{ + int idx; + if (fd->arguments_arg_idx < 0) { + idx = find_var_in_scope(ctx, fd, JS_ATOM_arguments, ARG_SCOPE_INDEX); + if (idx < 0) { + /* XXX: the scope links are not fully updated. May be an + issue if there are child scopes of the argument + scope */ + idx = add_var(ctx, fd, JS_ATOM_arguments); + if (idx < 0) + return -1; + fd->vars[idx].scope_next = fd->scopes[ARG_SCOPE_INDEX].first; + fd->scopes[ARG_SCOPE_INDEX].first = idx; + fd->vars[idx].scope_level = ARG_SCOPE_INDEX; + fd->vars[idx].is_lexical = TRUE; + + fd->arguments_arg_idx = idx; + } + } + return 0; +} + static int add_arg(JSContext *ctx, JSFunctionDef *fd, JSAtom name) { JSVarDef *vd; @@ -21854,32 +21845,27 @@ static int add_arg(JSContext *ctx, JSFunctionDef *fd, JSAtom name) vd = &fd->args[fd->arg_count++]; memset(vd, 0, sizeof(*vd)); vd->var_name = JS_DupAtom(ctx, name); + vd->func_pool_idx = -1; return fd->arg_count - 1; } -/* add a Hoisted definition for a function (cpool_idx >= 0) or a - global variable (cpool_idx = -1) */ -static JSHoistedDef *add_hoisted_def(JSContext *ctx, - JSFunctionDef *s, int cpool_idx, - JSAtom name, int var_idx, BOOL is_lexical) +/* add a global variable definition */ +static JSGlobalVar *add_global_var(JSContext *ctx, JSFunctionDef *s, + JSAtom name) { - JSHoistedDef *hf; + JSGlobalVar *hf; - if (js_resize_array(ctx, (void **)&s->hoisted_def, - sizeof(s->hoisted_def[0]), - &s->hoisted_def_size, s->hoisted_def_count + 1)) + if (js_resize_array(ctx, (void **)&s->global_vars, + sizeof(s->global_vars[0]), + &s->global_var_size, s->global_var_count + 1)) return NULL; - hf = &s->hoisted_def[s->hoisted_def_count++]; - hf->cpool_idx = cpool_idx; - hf->force_init = 0; - hf->is_lexical = is_lexical; + hf = &s->global_vars[s->global_var_count++]; + hf->cpool_idx = -1; + hf->force_init = FALSE; + hf->is_lexical = FALSE; hf->is_const = FALSE; - hf->var_idx = var_idx; hf->scope_level = s->scope_level; - hf->var_name = JS_ATOM_NULL; - if (name != JS_ATOM_NULL) { - hf->var_name = JS_DupAtom(ctx, name); - } + hf->var_name = JS_DupAtom(ctx, name); return hf; } @@ -21924,7 +21910,7 @@ static int define_var(JSParseState *s, JSFunctionDef *fd, JSAtom name, goto redef_lex_error; } } else { - if (fd->scope_level == 1) { + if (fd->scope_level == fd->body_scope) { redef_lex_error: /* redefining a scoped var in the same scope: error */ return js_parse_error(s, "invalid redefinition of lexical identifier"); @@ -21933,7 +21919,7 @@ static int define_var(JSParseState *s, JSFunctionDef *fd, JSAtom name, } if (var_def_type != JS_VAR_DEF_FUNCTION_DECL && var_def_type != JS_VAR_DEF_NEW_FUNCTION_DECL && - fd->scope_level == 1 && + fd->scope_level == fd->body_scope && find_arg(ctx, fd, name) >= 0) { /* lexical variable redefines a parameter name */ return js_parse_error(s, "invalid redefinition of parameter name"); @@ -21944,8 +21930,8 @@ static int define_var(JSParseState *s, JSFunctionDef *fd, JSAtom name, } if (fd->is_global_var) { - JSHoistedDef *hf; - hf = find_hoisted_def(fd, name); + JSGlobalVar *hf; + hf = find_global_var(fd, name); if (hf && is_child_scope(ctx, fd, hf->scope_level, fd->scope_level)) { return js_parse_error(s, "invalid redefinition of global identifier"); @@ -21955,11 +21941,12 @@ static int define_var(JSParseState *s, JSFunctionDef *fd, JSAtom name, if (fd->is_eval && (fd->eval_type == JS_EVAL_TYPE_GLOBAL || fd->eval_type == JS_EVAL_TYPE_MODULE) && - fd->scope_level == 1) { - JSHoistedDef *hf; - hf = add_hoisted_def(s->ctx, fd, -1, name, -1, TRUE); + fd->scope_level == fd->body_scope) { + JSGlobalVar *hf; + hf = add_global_var(s->ctx, fd, name); if (!hf) return -1; + hf->is_lexical = TRUE; hf->is_const = (var_def_type == JS_VAR_DEF_CONST); idx = GLOBAL_VAR_OFFSET; } else { @@ -21991,13 +21978,13 @@ static int define_var(JSParseState *s, JSFunctionDef *fd, JSAtom name, return js_parse_error(s, "invalid redefinition of lexical identifier"); } if (fd->is_global_var) { - JSHoistedDef *hf; - hf = find_hoisted_def(fd, name); + JSGlobalVar *hf; + hf = find_global_var(fd, name); if (hf && hf->is_lexical && hf->scope_level == fd->scope_level && fd->eval_type == JS_EVAL_TYPE_MODULE) { goto invalid_lexical_redefinition; } - hf = add_hoisted_def(s->ctx, fd, -1, name, -1, FALSE); + hf = add_global_var(s->ctx, fd, name); if (!hf) return -1; idx = GLOBAL_VAR_OFFSET; @@ -22010,7 +21997,7 @@ static int define_var(JSParseState *s, JSFunctionDef *fd, JSAtom name, if (idx >= 0) { if (name == JS_ATOM_arguments && fd->has_arguments_binding) fd->arguments_var_idx = idx; - fd->vars[idx].func_pool_or_scope_idx = fd->scope_level; + fd->vars[idx].scope_next = fd->scope_level; } } break; @@ -22052,8 +22039,9 @@ static __exception int js_parse_function_decl2(JSParseState *s, int function_line_num, JSParseExportEnum export_flag, JSFunctionDef **pfd); -static __exception int js_parse_assign_expr(JSParseState *s, int in_accepted); -static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag); +static __exception int js_parse_assign_expr2(JSParseState *s, int parse_flags); +static __exception int js_parse_assign_expr(JSParseState *s); +static __exception int js_parse_unary(JSParseState *s, int parse_flags); static void push_break_entry(JSFunctionDef *fd, BlockEnv *be, JSAtom label_name, int label_break, int label_cont, @@ -22385,8 +22373,9 @@ static BOOL is_regexp_allowed(int tok) } } -#define SKIP_HAS_SEMI (1 << 0) -#define SKIP_HAS_ELLIPSIS (1 << 1) +#define SKIP_HAS_SEMI (1 << 0) +#define SKIP_HAS_ELLIPSIS (1 << 1) +#define SKIP_HAS_ASSIGNMENT (1 << 2) /* XXX: improve speed with early bailout */ /* XXX: no longer works if regexps are present. Could use previous @@ -22459,7 +22448,10 @@ static int js_parse_skip_parens_token(JSParseState *s, int *pbits, BOOL no_line_ bits |= SKIP_HAS_ELLIPSIS; } break; - + case '=': + bits |= SKIP_HAS_ASSIGNMENT; + break; + case TOK_DIV_ASSIGN: tok_len = 2; goto parse_regexp; @@ -22574,7 +22566,7 @@ static __exception int js_parse_object_literal(JSParseState *s) if (s->token.val == TOK_ELLIPSIS) { if (next_token(s)) return -1; - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; emit_op(s, OP_null); /* dummy excludeList */ emit_op(s, OP_copy_data_properties); @@ -22633,7 +22625,7 @@ static __exception int js_parse_object_literal(JSParseState *s) } else { if (js_parse_expect(s, ':')) goto fail; - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) goto fail; if (name == JS_ATOM_NULL) { set_object_name_computed(s); @@ -22668,8 +22660,23 @@ static __exception int js_parse_object_literal(JSParseState *s) return -1; } -static __exception int js_parse_postfix_expr(JSParseState *s, - BOOL accept_lparen); +/* allow the 'in' binary operator */ +#define PF_IN_ACCEPTED (1 << 0) +/* allow function calls parsing in js_parse_postfix_expr() */ +#define PF_POSTFIX_CALL (1 << 1) +/* allow arrow functions parsing in js_parse_postfix_expr() */ +#define PF_ARROW_FUNC (1 << 2) +/* allow the exponentiation operator in js_parse_unary() */ +#define PF_POW_ALLOWED (1 << 3) +/* forbid the exponentiation operator in js_parse_unary() */ +#define PF_POW_FORBIDDEN (1 << 4) + +static __exception int js_parse_postfix_expr(JSParseState *s, int parse_flags); + +static __exception int js_parse_left_hand_side_expr(JSParseState *s) +{ + return js_parse_postfix_expr(s, PF_POSTFIX_CALL); +} /* XXX: is there is nicer solution ? */ static __exception int js_parse_class_default_ctor(JSParseState *s, @@ -22873,8 +22880,7 @@ static __exception int js_parse_class(JSParseState *s, BOOL is_class_expr, class_flags = JS_DEFINE_CLASS_HAS_HERITAGE; if (next_token(s)) goto fail; - /* XXX: the grammar only allows LeftHandSideExpression */ - if (js_parse_postfix_expr(s, TRUE)) + if (js_parse_left_hand_side_expr(s)) goto fail; } else { emit_op(s, OP_undefined); @@ -23081,7 +23087,7 @@ static __exception int js_parse_class(JSParseState *s, BOOL is_class_expr, if (s->token.val == '=') { if (next_token(s)) goto fail; - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) goto fail; } else { emit_op(s, OP_undefined); @@ -23285,7 +23291,7 @@ static __exception int js_parse_array_literal(JSParseState *s) while (s->token.val != ']' && idx < 32) { if (s->token.val == ',' || s->token.val == TOK_ELLIPSIS) break; - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; idx++; /* accept trailing comma */ @@ -23306,7 +23312,7 @@ static __exception int js_parse_array_literal(JSParseState *s) break; need_length = TRUE; if (s->token.val != ',') { - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; emit_op(s, OP_define_field); emit_u32(s, __JS_AtomFromUInt32(idx)); @@ -23341,7 +23347,7 @@ static __exception int js_parse_array_literal(JSParseState *s) if (s->token.val == TOK_ELLIPSIS) { if (next_token(s)) return -1; - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; #if 1 emit_op(s, OP_append); @@ -23373,7 +23379,7 @@ static __exception int js_parse_array_literal(JSParseState *s) } else { need_length = TRUE; if (s->token.val != ',') { - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; /* a idx val */ emit_op(s, OP_define_array_el); @@ -23781,6 +23787,8 @@ fail: return JS_ATOM_NULL; } +/* Return -1 if error, 0 if no initializer, 1 if an initializer is + present at the top level. */ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, int hasval, int has_ellipsis, BOOL allow_initializer) @@ -23789,7 +23797,8 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, int start_addr, assign_addr; JSAtom prop_name, var_name; int opcode, scope, tok1, skip_bits; - + BOOL has_initializer; + if (has_ellipsis < 0) { /* pre-parse destructuration target for spread detection */ js_parse_skip_parens_token(s, &skip_bits, FALSE); @@ -23842,7 +23851,7 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, label_lvalue = -1; depth_lvalue = 0; } else { - if (js_parse_postfix_expr(s, TRUE)) + if (js_parse_left_hand_side_expr(s)) return -1; if (get_lvalue(s, &opcode, &scope, &var_name, @@ -23898,7 +23907,7 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, emit_op(s, OP_get_field2); emit_u32(s, prop_name); } - if (js_parse_destructuring_element(s, tok, is_arg, TRUE, -1, TRUE)) + if (js_parse_destructuring_element(s, tok, is_arg, TRUE, -1, TRUE) < 0) return -1; if (s->token.val == '}') break; @@ -23935,7 +23944,7 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, if (var_name == JS_ATOM_NULL) goto prop_error; } else { - if (js_parse_postfix_expr(s, TRUE)) + if (js_parse_left_hand_side_expr(s)) goto prop_error; lvalue: if (get_lvalue(s, &opcode, &scope, &var_name, @@ -24033,7 +24042,7 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, if (next_token(s)) goto var_error; emit_op(s, OP_drop); - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) goto var_error; if (opcode == OP_scope_get_var || opcode == OP_get_ref_value) set_object_name(s, var_name); @@ -24097,7 +24106,7 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, emit_u8(s, 0); emit_op(s, OP_drop); } - if (js_parse_destructuring_element(s, tok, is_arg, TRUE, skip_bits & SKIP_HAS_ELLIPSIS, TRUE)) + if (js_parse_destructuring_element(s, tok, is_arg, TRUE, skip_bits & SKIP_HAS_ELLIPSIS, TRUE) < 0) return -1; } else { var_name = JS_ATOM_NULL; @@ -24111,7 +24120,7 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, opcode = OP_scope_get_var; scope = s->cur_func->scope_level; } else { - if (js_parse_postfix_expr(s, TRUE)) + if (js_parse_left_hand_side_expr(s)) return -1; if (get_lvalue(s, &opcode, &scope, &var_name, &label_lvalue, &enum_depth, FALSE, '[')) { @@ -24135,7 +24144,7 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, if (next_token(s)) goto var_error; emit_op(s, OP_drop); - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) goto var_error; if (opcode == OP_scope_get_var || opcode == OP_get_ref_value) set_object_name(s, var_name); @@ -24170,10 +24179,11 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, emit_label(s, label_parse); if (hasval) emit_op(s, OP_drop); - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; emit_goto(s, OP_goto, label_assign); emit_label(s, label_done); + has_initializer = TRUE; } else { /* normally hasval is true except if js_parse_skip_parens_token() was wrong in the parsing */ @@ -24186,8 +24196,9 @@ static int js_parse_destructuring_element(JSParseState *s, int tok, int is_arg, memset(s->cur_func->byte_code.buf + start_addr, OP_nop, assign_addr - start_addr); s->cur_func->label_slots[label_parse].ref_count--; + has_initializer = FALSE; } - return 0; + return has_initializer; prop_error: JS_FreeAtom(s->ctx, prop_name); @@ -24220,10 +24231,12 @@ static void optional_chain_test(JSParseState *s, int *poptional_chaining_label, emit_label(s, label_next); } -static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen) +/* allowed parse_flags: PF_POSTFIX_CALL, PF_ARROW_FUNC */ +static __exception int js_parse_postfix_expr(JSParseState *s, int parse_flags) { FuncCallType call_type; int optional_chaining_label; + BOOL accept_lparen = (parse_flags & PF_POSTFIX_CALL) != 0; call_type = FUNC_CALL_NORMAL; switch(s->token.val) { @@ -24321,7 +24334,8 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen } break; case '(': - if (js_parse_skip_parens_token(s, NULL, TRUE) == TOK_ARROW) { + if ((parse_flags & PF_ARROW_FUNC) && + js_parse_skip_parens_token(s, NULL, TRUE) == TOK_ARROW) { if (js_parse_function_decl(s, JS_PARSE_FUNC_ARROW, JS_FUNC_NORMAL, JS_ATOM_NULL, s->token.ptr, s->token.line_num)) @@ -24369,7 +24383,8 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen if (s->token.u.ident.is_reserved) { return js_parse_error_reserved_identifier(s); } - if (peek_token(s, TRUE) == TOK_ARROW) { + if ((parse_flags & PF_ARROW_FUNC) && + peek_token(s, TRUE) == TOK_ARROW) { if (js_parse_function_decl(s, JS_PARSE_FUNC_ARROW, JS_FUNC_NORMAL, JS_ATOM_NULL, s->token.ptr, s->token.line_num)) @@ -24388,10 +24403,11 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen JS_FUNC_ASYNC, JS_ATOM_NULL, source_ptr, source_line_num)) return -1; - } else if ((s->token.val == '(' && - js_parse_skip_parens_token(s, NULL, TRUE) == TOK_ARROW) || - (s->token.val == TOK_IDENT && !s->token.u.ident.is_reserved && - peek_token(s, TRUE) == TOK_ARROW)) { + } else if ((parse_flags & PF_ARROW_FUNC) && + ((s->token.val == '(' && + js_parse_skip_parens_token(s, NULL, TRUE) == TOK_ARROW) || + (s->token.val == TOK_IDENT && !s->token.u.ident.is_reserved && + peek_token(s, TRUE) == TOK_ARROW))) { if (js_parse_function_decl(s, JS_PARSE_FUNC_ARROW, JS_FUNC_ASYNC, JS_ATOM_NULL, source_ptr, source_line_num)) @@ -24421,7 +24437,7 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen { int skip_bits; if (js_parse_skip_parens_token(s, &skip_bits, FALSE) == '=') { - if (js_parse_destructuring_element(s, 0, 0, FALSE, skip_bits & SKIP_HAS_ELLIPSIS, TRUE)) + if (js_parse_destructuring_element(s, 0, 0, FALSE, skip_bits & SKIP_HAS_ELLIPSIS, TRUE) < 0) return -1; } else { if (s->token.val == '{') { @@ -24450,7 +24466,7 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen emit_atom(s, JS_ATOM_new_target); emit_u16(s, 0); } else { - if (js_parse_postfix_expr(s, FALSE)) + if (js_parse_postfix_expr(s, 0)) return -1; accept_lparen = TRUE; if (s->token.val != '(') { @@ -24503,7 +24519,7 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen return -1; if (!accept_lparen) return js_parse_error(s, "invalid use of 'import()'"); - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; if (js_parse_expect(s, ')')) return -1; @@ -24636,7 +24652,7 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen } if (s->token.val == TOK_ELLIPSIS) break; - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; arg_count++; if (s->token.val == ')') @@ -24656,7 +24672,7 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen if (s->token.val == TOK_ELLIPSIS) { if (next_token(s)) return -1; - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; #if 1 /* XXX: could pass is_last indicator? */ @@ -24687,7 +24703,7 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen emit_op(s, OP_nip1); #endif } else { - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; /* array idx val */ emit_op(s, OP_define_array_el); @@ -24789,16 +24805,19 @@ static __exception int js_parse_postfix_expr(JSParseState *s, BOOL accept_lparen } else if (s->token.val == '.') { if (next_token(s)) return -1; + parse_property: if (s->token.val == TOK_PRIVATE_NAME) { /* private class field */ if (get_prev_opcode(fd) == OP_get_super) { return js_parse_error(s, "private class field forbidden after super"); } + if (has_optional_chain) { + optional_chain_test(s, &optional_chaining_label, 1); + } emit_op(s, OP_scope_get_private_field); emit_atom(s, s->token.u.ident.atom); emit_u16(s, s->cur_func->scope_level); } else { - parse_property: if (!token_is_ident(s->token.val)) { return js_parse_error(s, "expecting field name"); } @@ -24857,7 +24876,7 @@ static __exception int js_parse_delete(JSParseState *s) if (next_token(s)) return -1; - if (js_parse_unary(s, -1)) + if (js_parse_unary(s, PF_POW_FORBIDDEN)) return -1; switch(opcode = get_prev_opcode(fd)) { case OP_get_field: @@ -24896,9 +24915,9 @@ static __exception int js_parse_delete(JSParseState *s) case OP_scope_get_private_field: return js_parse_error(s, "cannot delete a private class field"); case OP_get_super_value: - emit_op(s, OP_throw_var); + emit_op(s, OP_throw_error); emit_atom(s, JS_ATOM_NULL); - emit_u8(s, JS_THROW_VAR_DELETE_SUPER); + emit_u8(s, JS_THROW_ERROR_DELETE_SUPER); break; default: ret_true: @@ -24909,7 +24928,8 @@ static __exception int js_parse_delete(JSParseState *s) return 0; } -static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) +/* allowed parse_flags: PF_ARROW_FUNC, PF_POW_ALLOWED, PF_POW_FORBIDDEN */ +static __exception int js_parse_unary(JSParseState *s, int parse_flags) { int op; @@ -24922,7 +24942,7 @@ static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) op = s->token.val; if (next_token(s)) return -1; - if (js_parse_unary(s, -1)) + if (js_parse_unary(s, PF_POW_FORBIDDEN)) return -1; switch(op) { case '-': @@ -24944,7 +24964,7 @@ static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) default: abort(); } - exponentiation_flag = 0; + parse_flags = 0; break; case TOK_DEC: case TOK_INC: @@ -24954,7 +24974,6 @@ static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) op = s->token.val; if (next_token(s)) return -1; - /* XXX: should parse LeftHandSideExpression */ if (js_parse_unary(s, 0)) return -1; if (get_lvalue(s, &opcode, &scope, &name, &label, NULL, TRUE, op)) @@ -24969,7 +24988,7 @@ static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) JSFunctionDef *fd; if (next_token(s)) return -1; - if (js_parse_unary(s, -1)) + if (js_parse_unary(s, PF_POW_FORBIDDEN)) return -1; /* reference access should not return an exception, so we patch the get_var */ @@ -24978,13 +24997,13 @@ static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) fd->byte_code.buf[fd->last_opcode_pos] = OP_scope_get_var_undef; } emit_op(s, OP_typeof); - exponentiation_flag = 0; + parse_flags = 0; } break; case TOK_DELETE: if (js_parse_delete(s)) return -1; - exponentiation_flag = 0; + parse_flags = 0; break; case TOK_AWAIT: if (!(s->cur_func->func_kind & JS_FUNC_ASYNC)) @@ -24993,13 +25012,14 @@ static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) return js_parse_error(s, "await in default expression"); if (next_token(s)) return -1; - if (js_parse_unary(s, -1)) + if (js_parse_unary(s, PF_POW_FORBIDDEN)) return -1; emit_op(s, OP_await); - exponentiation_flag = 0; + parse_flags = 0; break; default: - if (js_parse_postfix_expr(s, TRUE)) + if (js_parse_postfix_expr(s, (parse_flags & PF_ARROW_FUNC) | + PF_POSTFIX_CALL)) return -1; if (!s->got_lf && (s->token.val == TOK_DEC || s->token.val == TOK_INC)) { @@ -25016,21 +25036,21 @@ static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) } break; } - if (exponentiation_flag) { + if (parse_flags & (PF_POW_ALLOWED | PF_POW_FORBIDDEN)) { #ifdef CONFIG_BIGNUM if (s->token.val == TOK_POW || s->token.val == TOK_MATH_POW) { /* Extended exponentiation syntax rules: we extend the ES7 grammar in order to have more intuitive semantics: -2**2 evaluates to -4. */ if (!(s->cur_func->js_mode & JS_MODE_MATH)) { - if (exponentiation_flag < 0) { + if (parse_flags & PF_POW_FORBIDDEN) { JS_ThrowSyntaxError(s->ctx, "unparenthesized unary expression can't appear on the left-hand side of '**'"); return -1; } } if (next_token(s)) return -1; - if (js_parse_unary(s, 1)) + if (js_parse_unary(s, PF_POW_ALLOWED)) return -1; emit_op(s, OP_pow); } @@ -25041,13 +25061,13 @@ static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) regarding the precedence of prefix operators and the postifx exponential, ES7 specifies that -2**2 is a syntax error. */ - if (exponentiation_flag < 0) { + if (parse_flags & PF_POW_FORBIDDEN) { JS_ThrowSyntaxError(s->ctx, "unparenthesized unary expression can't appear on the left-hand side of '**'"); return -1; } if (next_token(s)) return -1; - if (js_parse_unary(s, 1)) + if (js_parse_unary(s, PF_POW_ALLOWED)) return -1; emit_op(s, OP_pow); } @@ -25056,15 +25076,17 @@ static __exception int js_parse_unary(JSParseState *s, int exponentiation_flag) return 0; } +/* allowed parse_flags: PF_ARROW_FUNC, PF_IN_ACCEPTED */ static __exception int js_parse_expr_binary(JSParseState *s, int level, - BOOL in_accepted) + int parse_flags) { int op, opcode; if (level == 0) { - return js_parse_unary(s, 1); + return js_parse_unary(s, (parse_flags & PF_ARROW_FUNC) | + PF_POW_ALLOWED); } - if (js_parse_expr_binary(s, level - 1, in_accepted)) + if (js_parse_expr_binary(s, level - 1, parse_flags)) return -1; for(;;) { op = s->token.val; @@ -25134,7 +25156,7 @@ static __exception int js_parse_expr_binary(JSParseState *s, int level, opcode = OP_instanceof; break; case TOK_IN: - if (in_accepted) { + if (parse_flags & PF_IN_ACCEPTED) { opcode = OP_in; } else { return 0; @@ -25194,23 +25216,24 @@ static __exception int js_parse_expr_binary(JSParseState *s, int level, } if (next_token(s)) return -1; - if (js_parse_expr_binary(s, level - 1, in_accepted)) + if (js_parse_expr_binary(s, level - 1, parse_flags & ~PF_ARROW_FUNC)) return -1; emit_op(s, opcode); } return 0; } +/* allowed parse_flags: PF_ARROW_FUNC, PF_IN_ACCEPTED */ static __exception int js_parse_logical_and_or(JSParseState *s, int op, - BOOL in_accepted) + int parse_flags) { int label1; if (op == TOK_LAND) { - if (js_parse_expr_binary(s, 8, in_accepted)) + if (js_parse_expr_binary(s, 8, parse_flags)) return -1; } else { - if (js_parse_logical_and_or(s, TOK_LAND, in_accepted)) + if (js_parse_logical_and_or(s, TOK_LAND, parse_flags)) return -1; } if (s->token.val == op) { @@ -25224,10 +25247,11 @@ static __exception int js_parse_logical_and_or(JSParseState *s, int op, emit_op(s, OP_drop); if (op == TOK_LAND) { - if (js_parse_expr_binary(s, 8, in_accepted)) + if (js_parse_expr_binary(s, 8, parse_flags & ~PF_ARROW_FUNC)) return -1; } else { - if (js_parse_logical_and_or(s, TOK_LAND, in_accepted)) + if (js_parse_logical_and_or(s, TOK_LAND, + parse_flags & ~PF_ARROW_FUNC)) return -1; } if (s->token.val != op) { @@ -25242,11 +25266,11 @@ static __exception int js_parse_logical_and_or(JSParseState *s, int op, return 0; } -static __exception int js_parse_coalesce_expr(JSParseState *s, BOOL in_accepted) +static __exception int js_parse_coalesce_expr(JSParseState *s, int parse_flags) { int label1; - if (js_parse_logical_and_or(s, TOK_LOR, in_accepted)) + if (js_parse_logical_and_or(s, TOK_LOR, parse_flags)) return -1; if (s->token.val == TOK_DOUBLE_QUESTION_MARK) { label1 = new_label(s); @@ -25259,7 +25283,7 @@ static __exception int js_parse_coalesce_expr(JSParseState *s, BOOL in_accepted) emit_goto(s, OP_if_false, label1); emit_op(s, OP_drop); - if (js_parse_expr_binary(s, 8, in_accepted)) + if (js_parse_expr_binary(s, 8, parse_flags & ~PF_ARROW_FUNC)) return -1; if (s->token.val != TOK_DOUBLE_QUESTION_MARK) break; @@ -25269,18 +25293,19 @@ static __exception int js_parse_coalesce_expr(JSParseState *s, BOOL in_accepted) return 0; } -static __exception int js_parse_cond_expr(JSParseState *s, BOOL in_accepted) +/* allowed parse_flags: PF_ARROW_FUNC, PF_IN_ACCEPTED */ +static __exception int js_parse_cond_expr(JSParseState *s, int parse_flags) { int label1, label2; - if (js_parse_coalesce_expr(s, in_accepted)) + if (js_parse_coalesce_expr(s, parse_flags)) return -1; if (s->token.val == '?') { if (next_token(s)) return -1; label1 = emit_goto(s, OP_if_false, -1); - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; if (js_parse_expect(s, ':')) return -1; @@ -25289,7 +25314,7 @@ static __exception int js_parse_cond_expr(JSParseState *s, BOOL in_accepted) emit_label(s, label1); - if (js_parse_assign_expr(s, in_accepted)) + if (js_parse_assign_expr2(s, parse_flags & PF_IN_ACCEPTED)) return -1; emit_label(s, label2); @@ -25299,14 +25324,16 @@ static __exception int js_parse_cond_expr(JSParseState *s, BOOL in_accepted) static void emit_return(JSParseState *s, BOOL hasval); -static __exception int js_parse_assign_expr(JSParseState *s, BOOL in_accepted) +/* allowed parse_flags: PF_IN_ACCEPTED */ +static __exception int js_parse_assign_expr2(JSParseState *s, int parse_flags) { int opcode, op, scope; JSAtom name0 = JS_ATOM_NULL; JSAtom name; if (s->token.val == TOK_YIELD) { - BOOL is_star = FALSE; + BOOL is_star = FALSE, is_async; + if (!(s->cur_func->func_kind & JS_FUNC_GENERATOR)) return js_parse_error(s, "unexpected 'yield' keyword"); if (!s->cur_func->in_function_body) @@ -25323,109 +25350,120 @@ static __exception int js_parse_assign_expr(JSParseState *s, BOOL in_accepted) if (next_token(s)) return -1; } - if (js_parse_assign_expr(s, in_accepted)) + if (js_parse_assign_expr2(s, parse_flags)) return -1; } else { emit_op(s, OP_undefined); } - if (s->cur_func->func_kind == JS_FUNC_ASYNC_GENERATOR) { + is_async = (s->cur_func->func_kind == JS_FUNC_ASYNC_GENERATOR); + + if (is_star) { int label_loop, label_return, label_next; int label_return1, label_yield, label_throw, label_throw1; int label_throw2; - if (is_star) { - label_loop = new_label(s); - label_yield = new_label(s); + label_loop = new_label(s); + label_yield = new_label(s); - emit_op(s, OP_for_await_of_start); + emit_op(s, is_async ? OP_for_await_of_start : OP_for_of_start); - /* remove the catch offset (XXX: could avoid pushing back - undefined) */ - emit_op(s, OP_drop); - emit_op(s, OP_undefined); - - emit_op(s, OP_undefined); /* initial value */ - - emit_label(s, label_loop); - emit_op(s, OP_async_iterator_next); + /* remove the catch offset (XXX: could avoid pushing back + undefined) */ + emit_op(s, OP_drop); + emit_op(s, OP_undefined); + + emit_op(s, OP_undefined); /* initial value */ + + emit_label(s, label_loop); + emit_op(s, OP_iterator_next); + if (is_async) emit_op(s, OP_await); - emit_op(s, OP_iterator_get_value_done); - label_next = emit_goto(s, OP_if_true, -1); /* end of loop */ + emit_op(s, OP_iterator_check_object); + emit_op(s, OP_get_field2); + emit_atom(s, JS_ATOM_done); + label_next = emit_goto(s, OP_if_true, -1); /* end of loop */ + emit_label(s, label_yield); + if (is_async) { + /* OP_async_yield_star takes the value as parameter */ + emit_op(s, OP_get_field); + emit_atom(s, JS_ATOM_value); emit_op(s, OP_await); - emit_label(s, label_yield); emit_op(s, OP_async_yield_star); - emit_op(s, OP_dup); - label_return = emit_goto(s, OP_if_true, -1); - emit_op(s, OP_drop); - emit_goto(s, OP_goto, label_loop); - - emit_label(s, label_return); - emit_op(s, OP_push_i32); - emit_u32(s, 2); - emit_op(s, OP_strict_eq); - label_throw = emit_goto(s, OP_if_true, -1); - - /* return handling */ - emit_op(s, OP_await); - emit_op(s, OP_async_iterator_get); - emit_u8(s, 0); - label_return1 = emit_goto(s, OP_if_true, -1); - emit_op(s, OP_await); - emit_op(s, OP_iterator_get_value_done); - /* XXX: the spec does not indicate that an await should be - performed in case done = true, but the tests assume it */ - emit_goto(s, OP_if_false, label_yield); - - emit_label(s, label_return1); - emit_op(s, OP_nip); - emit_op(s, OP_nip); - emit_op(s, OP_nip); - emit_return(s, TRUE); - - /* throw handling */ - emit_label(s, label_throw); - emit_op(s, OP_async_iterator_get); - emit_u8(s, 1); - label_throw1 = emit_goto(s, OP_if_true, -1); - emit_op(s, OP_await); - emit_op(s, OP_iterator_get_value_done); - emit_goto(s, OP_if_false, label_yield); - /* XXX: the spec does not indicate that an await should be - performed in case done = true, but the tests assume it */ - emit_op(s, OP_await); - emit_goto(s, OP_goto, label_next); - /* close the iterator and throw a type error exception */ - emit_label(s, label_throw1); - emit_op(s, OP_async_iterator_get); - emit_u8(s, 0); - label_throw2 = emit_goto(s, OP_if_true, -1); - emit_op(s, OP_await); - emit_label(s, label_throw2); - emit_op(s, OP_async_iterator_get); - emit_u8(s, 2); /* throw the type error exception */ - emit_op(s, OP_drop); /* never reached */ - - emit_label(s, label_next); - emit_op(s, OP_nip); /* keep the value associated with - done = true */ - emit_op(s, OP_nip); - emit_op(s, OP_nip); } else { - emit_op(s, OP_await); - emit_op(s, OP_yield); - label_next = emit_goto(s, OP_if_false, -1); - emit_return(s, TRUE); - emit_label(s, label_next); + /* OP_yield_star takes (value, done) as parameter */ + emit_op(s, OP_yield_star); } + emit_op(s, OP_dup); + label_return = emit_goto(s, OP_if_true, -1); + emit_op(s, OP_drop); + emit_goto(s, OP_goto, label_loop); + + emit_label(s, label_return); + emit_op(s, OP_push_i32); + emit_u32(s, 2); + emit_op(s, OP_strict_eq); + label_throw = emit_goto(s, OP_if_true, -1); + + /* return handling */ + if (is_async) + emit_op(s, OP_await); + emit_op(s, OP_iterator_call); + emit_u8(s, 0); + label_return1 = emit_goto(s, OP_if_true, -1); + if (is_async) + emit_op(s, OP_await); + emit_op(s, OP_iterator_check_object); + emit_op(s, OP_get_field2); + emit_atom(s, JS_ATOM_done); + emit_goto(s, OP_if_false, label_yield); + + emit_op(s, OP_get_field); + emit_atom(s, JS_ATOM_value); + + emit_label(s, label_return1); + emit_op(s, OP_nip); + emit_op(s, OP_nip); + emit_op(s, OP_nip); + emit_return(s, TRUE); + + /* throw handling */ + emit_label(s, label_throw); + emit_op(s, OP_iterator_call); + emit_u8(s, 1); + label_throw1 = emit_goto(s, OP_if_true, -1); + if (is_async) + emit_op(s, OP_await); + emit_op(s, OP_iterator_check_object); + emit_op(s, OP_get_field2); + emit_atom(s, JS_ATOM_done); + emit_goto(s, OP_if_false, label_yield); + emit_goto(s, OP_goto, label_next); + /* close the iterator and throw a type error exception */ + emit_label(s, label_throw1); + emit_op(s, OP_iterator_call); + emit_u8(s, 2); + label_throw2 = emit_goto(s, OP_if_true, -1); + if (is_async) + emit_op(s, OP_await); + emit_label(s, label_throw2); + + emit_op(s, OP_throw_error); + emit_atom(s, JS_ATOM_NULL); + emit_u8(s, JS_THROW_ERROR_ITERATOR_THROW); + + emit_label(s, label_next); + emit_op(s, OP_get_field); + emit_atom(s, JS_ATOM_value); + emit_op(s, OP_nip); /* keep the value associated with + done = true */ + emit_op(s, OP_nip); + emit_op(s, OP_nip); } else { int label_next; - if (is_star) { - emit_op(s, OP_for_of_start); - emit_op(s, OP_drop); /* drop the catch offset */ - emit_op(s, OP_yield_star); - } else { - emit_op(s, OP_yield); - } + + if (is_async) + emit_op(s, OP_await); + emit_op(s, OP_yield); label_next = emit_goto(s, OP_if_false, -1); emit_return(s, TRUE); emit_label(s, label_next); @@ -25436,7 +25474,7 @@ static __exception int js_parse_assign_expr(JSParseState *s, BOOL in_accepted) /* name0 is used to check for OP_set_name pattern, not duplicated */ name0 = s->token.u.ident.atom; } - if (js_parse_cond_expr(s, in_accepted)) + if (js_parse_cond_expr(s, parse_flags | PF_ARROW_FUNC)) return -1; op = s->token.val; @@ -25447,7 +25485,7 @@ static __exception int js_parse_assign_expr(JSParseState *s, BOOL in_accepted) if (get_lvalue(s, &opcode, &scope, &name, &label, NULL, (op != '='), op) < 0) return -1; - if (js_parse_assign_expr(s, in_accepted)) { + if (js_parse_assign_expr2(s, parse_flags)) { JS_FreeAtom(s->ctx, name); return -1; } @@ -25491,7 +25529,7 @@ static __exception int js_parse_assign_expr(JSParseState *s, BOOL in_accepted) -1); emit_op(s, OP_drop); - if (js_parse_assign_expr(s, in_accepted)) { + if (js_parse_assign_expr2(s, parse_flags)) { JS_FreeAtom(s->ctx, name); return -1; } @@ -25533,11 +25571,17 @@ static __exception int js_parse_assign_expr(JSParseState *s, BOOL in_accepted) return 0; } -static __exception int js_parse_expr2(JSParseState *s, BOOL in_accepted) +static __exception int js_parse_assign_expr(JSParseState *s) +{ + return js_parse_assign_expr2(s, PF_IN_ACCEPTED); +} + +/* allowed parse_flags: PF_IN_ACCEPTED */ +static __exception int js_parse_expr2(JSParseState *s, int parse_flags) { BOOL comma = FALSE; for(;;) { - if (js_parse_assign_expr(s, in_accepted)) + if (js_parse_assign_expr2(s, parse_flags)) return -1; if (comma) { /* prevent get_lvalue from using the last expression @@ -25559,7 +25603,7 @@ static __exception int js_parse_expr2(JSParseState *s, BOOL in_accepted) static __exception int js_parse_expr(JSParseState *s) { - return js_parse_expr2(s, TRUE); + return js_parse_expr2(s, PF_IN_ACCEPTED); } static void push_break_entry(JSFunctionDef *fd, BlockEnv *be, @@ -25655,12 +25699,25 @@ static void emit_return(JSParseState *s, BOOL hasval) } emit_op(s, OP_iterator_close_return); if (s->cur_func->func_kind == JS_FUNC_ASYNC_GENERATOR) { - int label_next; - emit_op(s, OP_async_iterator_close); + int label_next, label_next2; + + emit_op(s, OP_drop); /* catch offset */ + emit_op(s, OP_drop); /* next */ + emit_op(s, OP_get_field2); + emit_atom(s, JS_ATOM_return); + /* stack: iter_obj return_func */ + emit_op(s, OP_dup); + emit_op(s, OP_is_undefined_or_null); label_next = emit_goto(s, OP_if_true, -1); + emit_op(s, OP_call_method); + emit_u16(s, 0); + emit_op(s, OP_iterator_check_object); emit_op(s, OP_await); + label_next2 = emit_goto(s, OP_goto, -1); emit_label(s, label_next); emit_op(s, OP_drop); + emit_label(s, label_next2); + emit_op(s, OP_drop); } else { emit_op(s, OP_iterator_close); } @@ -25748,7 +25805,8 @@ static __exception int js_parse_block(JSParseState *s) return 0; } -static __exception int js_parse_var(JSParseState *s, BOOL in_accepted, int tok, +/* allowed parse_flags: PF_IN_ACCEPTED */ +static __exception int js_parse_var(JSParseState *s, int parse_flags, int tok, BOOL export_flag) { JSContext *ctx = s->ctx; @@ -25788,7 +25846,7 @@ static __exception int js_parse_var(JSParseState *s, BOOL in_accepted, int tok, emit_u16(s, fd->scope_level); if (get_lvalue(s, &opcode, &scope, &name1, &label, NULL, FALSE, '=') < 0) goto var_error; - if (js_parse_assign_expr(s, in_accepted)) { + if (js_parse_assign_expr2(s, parse_flags)) { JS_FreeAtom(ctx, name1); goto var_error; } @@ -25796,7 +25854,7 @@ static __exception int js_parse_var(JSParseState *s, BOOL in_accepted, int tok, put_lvalue(s, opcode, scope, name1, label, PUT_LVALUE_NOKEEP, FALSE); } else { - if (js_parse_assign_expr(s, in_accepted)) + if (js_parse_assign_expr2(s, parse_flags)) goto var_error; set_object_name(s, name); emit_op(s, (tok == TOK_CONST || tok == TOK_LET) ? @@ -25823,7 +25881,7 @@ static __exception int js_parse_var(JSParseState *s, BOOL in_accepted, int tok, if ((s->token.val == '[' || s->token.val == '{') && js_parse_skip_parens_token(s, &skip_bits, FALSE) == '=') { emit_op(s, OP_undefined); - if (js_parse_destructuring_element(s, tok, 0, TRUE, skip_bits & SKIP_HAS_ELLIPSIS, TRUE)) + if (js_parse_destructuring_element(s, tok, 0, TRUE, skip_bits & SKIP_HAS_ELLIPSIS, TRUE) < 0) return -1; } else { return js_parse_error(s, "variable name expected"); @@ -25952,7 +26010,7 @@ static __exception int js_parse_for_in_of(JSParseState *s, int label_name, if (!(s->token.val == TOK_IDENT && !s->token.u.ident.is_reserved)) { if (s->token.val == '[' || s->token.val == '{') { - if (js_parse_destructuring_element(s, tok, 0, TRUE, -1, FALSE)) + if (js_parse_destructuring_element(s, tok, 0, TRUE, -1, FALSE) < 0) return -1; has_destructuring = TRUE; } else { @@ -25978,11 +26036,11 @@ static __exception int js_parse_for_in_of(JSParseState *s, int label_name, int skip_bits; if ((s->token.val == '[' || s->token.val == '{') && ((tok1 = js_parse_skip_parens_token(s, &skip_bits, FALSE)) == TOK_IN || tok1 == TOK_OF)) { - if (js_parse_destructuring_element(s, 0, 0, TRUE, skip_bits & SKIP_HAS_ELLIPSIS, TRUE)) + if (js_parse_destructuring_element(s, 0, 0, TRUE, skip_bits & SKIP_HAS_ELLIPSIS, TRUE) < 0) return -1; } else { int lvalue_label; - if (js_parse_postfix_expr(s, TRUE)) + if (js_parse_left_hand_side_expr(s)) return -1; if (get_lvalue(s, &opcode, &scope, &var_name, &lvalue_label, NULL, FALSE, TOK_FOR)) @@ -26002,7 +26060,7 @@ static __exception int js_parse_for_in_of(JSParseState *s, int label_name, /* parse and evaluate initializer prior to evaluating the object (only used with "for in" with a non lexical variable in non strict mode */ - if (next_token(s) || js_parse_assign_expr(s, FALSE)) { + if (next_token(s) || js_parse_assign_expr2(s, 0)) { JS_FreeAtom(ctx, var_name); return -1; } @@ -26035,7 +26093,7 @@ static __exception int js_parse_for_in_of(JSParseState *s, int label_name, if (next_token(s)) return -1; if (is_for_of) { - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; } else { if (js_parse_expr(s)) @@ -26088,7 +26146,11 @@ static __exception int js_parse_for_in_of(JSParseState *s, int label_name, if (is_for_of) { if (is_async) { /* call the next method */ - emit_op(s, OP_for_await_of_next); + /* stack: iter_obj next catch_offset */ + emit_op(s, OP_dup3); + emit_op(s, OP_drop); + emit_op(s, OP_call_method); + emit_u16(s, 0); /* get the result of the promise */ emit_op(s, OP_await); /* unwrap the value and done values */ @@ -26646,7 +26708,7 @@ static __exception int js_parse_statement_or_decl(JSParseState *s, if (!(s->token.val == TOK_IDENT && !s->token.u.ident.is_reserved)) { if (s->token.val == '[' || s->token.val == '{') { /* XXX: TOK_LET is not completely correct */ - if (js_parse_destructuring_element(s, TOK_LET, 0, TRUE, -1, TRUE)) + if (js_parse_destructuring_element(s, TOK_LET, 0, TRUE, -1, TRUE) < 0) goto fail; } else { js_parse_error(s, "identifier expected"); @@ -26712,18 +26774,37 @@ static __exception int js_parse_statement_or_decl(JSParseState *s, } emit_label(s, label_finally); if (s->token.val == TOK_FINALLY) { - int saved_eval_ret_idx; + int saved_eval_ret_idx = 0; /* avoid warning */ + if (next_token(s)) goto fail; /* on the stack: ret_value gosub_ret_value */ push_break_entry(s->cur_func, &block_env, JS_ATOM_NULL, -1, -1, 2); - saved_eval_ret_idx = s->cur_func->eval_ret_idx; - s->cur_func->eval_ret_idx = -1; - /* 'finally' does not update eval_ret */ + + if (s->cur_func->eval_ret_idx >= 0) { + /* 'finally' updates eval_ret only if not a normal + termination */ + saved_eval_ret_idx = + add_var(s->ctx, s->cur_func, JS_ATOM__ret_); + if (saved_eval_ret_idx < 0) + goto fail; + emit_op(s, OP_get_loc); + emit_u16(s, s->cur_func->eval_ret_idx); + emit_op(s, OP_put_loc); + emit_u16(s, saved_eval_ret_idx); + set_eval_ret_undefined(s); + } + if (js_parse_block(s)) goto fail; - s->cur_func->eval_ret_idx = saved_eval_ret_idx; + + if (s->cur_func->eval_ret_idx >= 0) { + emit_op(s, OP_get_loc); + emit_u16(s, saved_eval_ret_idx); + emit_op(s, OP_put_loc); + emit_u16(s, s->cur_func->eval_ret_idx); + } pop_break_entry(s->cur_func); } emit_op(s, OP_ret); @@ -27511,19 +27592,11 @@ static int exported_names_cmp(const void *p1, const void *p2, void *opaque) static JSValue js_get_module_ns(JSContext *ctx, JSModuleDef *m); -static int js_module_ns_autoinit(JSContext *ctx, JSObject *p, JSAtom atom, - void *opaque) +static JSValue js_module_ns_autoinit(JSContext *ctx, JSObject *p, JSAtom atom, + void *opaque) { JSModuleDef *m = opaque; - JSValue val, this_val = JS_MKPTR(JS_TAG_OBJECT, p); - - val = js_get_module_ns(ctx, m); - if (JS_IsException(val)) - return -1; - if (JS_DefinePropertyValue(ctx, this_val, atom, val, - JS_PROP_ENUMERABLE | JS_PROP_WRITABLE) < 0) - return -1; - return 0; + return js_get_module_ns(ctx, m); } static JSValue js_build_module_ns(JSContext *ctx, JSModuleDef *m) @@ -27741,7 +27814,7 @@ static int js_create_module_bytecode_function(JSContext *ctx, JSModuleDef *m) return -1; } -/* must be done before js_instantiate_module() because of cyclic references */ +/* must be done before js_link_module() because of cyclic references */ static int js_create_module_function(JSContext *ctx, JSModuleDef *m) { BOOL is_c_module; @@ -27784,7 +27857,7 @@ static int js_create_module_function(JSContext *ctx, JSModuleDef *m) /* Prepare a module to be executed by resolving all the imported variables. */ -static int js_instantiate_module(JSContext *ctx, JSModuleDef *m) +static int js_link_module(JSContext *ctx, JSModuleDef *m) { int i; JSImportEntry *mi; @@ -27792,7 +27865,8 @@ static int js_instantiate_module(JSContext *ctx, JSModuleDef *m) JSVarRef **var_refs, *var_ref; JSObject *p; BOOL is_c_module; - + JSValue ret_val; + if (m->instantiated) return 0; m->instantiated = TRUE; @@ -27806,7 +27880,7 @@ static int js_instantiate_module(JSContext *ctx, JSModuleDef *m) for(i = 0; i < m->req_module_entries_count; i++) { JSReqModuleEntry *rme = &m->req_module_entries[i]; - if (js_instantiate_module(ctx, rme->module) < 0) + if (js_link_module(ctx, rme->module) < 0) goto fail; } @@ -27925,6 +27999,12 @@ static int js_instantiate_module(JSContext *ctx, JSModuleDef *m) me->u.local.var_ref = var_ref; } } + + /* initialize the global variables */ + ret_val = JS_Call(ctx, m->func_obj, JS_TRUE, 0, NULL); + if (JS_IsException(ret_val)) + goto fail; + JS_FreeValue(ctx, ret_val); } #ifdef DUMP_MODULE_RESOLVE @@ -28324,7 +28404,7 @@ static __exception int js_parse_export(JSParseState *s) s->token.ptr, s->token.line_num, JS_PARSE_EXPORT_DEFAULT, NULL); } else { - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) return -1; } /* set the name of anonymous functions */ @@ -28567,7 +28647,9 @@ static JSFunctionDef *js_new_function_def(JSContext *ctx, fd->last_opcode_pos = -1; fd->func_name = JS_ATOM_NULL; fd->var_object_idx = -1; + fd->arg_var_object_idx = -1; fd->arguments_var_idx = -1; + fd->arguments_arg_idx = -1; fd->func_var_idx = -1; fd->eval_ret_idx = -1; fd->this_var_idx = -1; @@ -28576,13 +28658,14 @@ static JSFunctionDef *js_new_function_def(JSContext *ctx, fd->home_object_var_idx = -1; /* XXX: should distinguish arg, var and var object and body scopes */ - fd->scope_level = 0; /* 0: var/arg scope, 1:body scope */ - fd->scope_first = -1; fd->scopes = fd->def_scope_array; fd->scope_size = countof(fd->def_scope_array); fd->scope_count = 1; fd->scopes[0].first = -1; fd->scopes[0].parent = -1; + fd->scope_level = 0; /* 0: var/arg scope */ + fd->scope_first = -1; + fd->body_scope = -1; fd->filename = JS_NewAtom(ctx, filename); fd->line_num = line_num; @@ -28663,10 +28746,10 @@ static void js_free_function_def(JSContext *ctx, JSFunctionDef *fd) } js_free(ctx, fd->args); - for(i = 0; i < fd->hoisted_def_count; i++) { - JS_FreeAtom(ctx, fd->hoisted_def[i].var_name); + for(i = 0; i < fd->global_var_count; i++) { + JS_FreeAtom(ctx, fd->global_vars[i].var_name); } - js_free(ctx, fd->hoisted_def); + js_free(ctx, fd->global_vars); for(i = 0; i < fd->closure_var_count; i++) { JSClosureVar *cv = &fd->closure_var[i]; @@ -29350,19 +29433,27 @@ static int resolve_pseudo_var(JSContext *ctx, JSFunctionDef *s, switch(var_name) { case JS_ATOM_home_object: /* 'home_object' pseudo variable */ - var_idx = s->home_object_var_idx = add_var(ctx, s, var_name); + if (s->home_object_var_idx < 0) + s->home_object_var_idx = add_var(ctx, s, var_name); + var_idx = s->home_object_var_idx; break; case JS_ATOM_this_active_func: /* 'this.active_func' pseudo variable */ - var_idx = s->this_active_func_var_idx = add_var(ctx, s, var_name); + if (s->this_active_func_var_idx < 0) + s->this_active_func_var_idx = add_var(ctx, s, var_name); + var_idx = s->this_active_func_var_idx; break; case JS_ATOM_new_target: /* 'new.target' pseudo variable */ - var_idx = s->new_target_var_idx = add_var(ctx, s, var_name); + if (s->new_target_var_idx < 0) + s->new_target_var_idx = add_var(ctx, s, var_name); + var_idx = s->new_target_var_idx; break; case JS_ATOM_this: /* 'this' pseudo variable */ - var_idx = s->this_var_idx = add_var_this(ctx, s); + if (s->this_var_idx < 0) + s->this_var_idx = add_var_this(ctx, s); + var_idx = s->this_var_idx; break; default: var_idx = -1; @@ -29371,18 +29462,32 @@ static int resolve_pseudo_var(JSContext *ctx, JSFunctionDef *s, return var_idx; } +/* test if 'var_name' is in the variable object on the stack. If is it + the case, handle it and jump to 'label_done' */ +static void var_object_test(JSContext *ctx, JSFunctionDef *s, + JSAtom var_name, int op, DynBuf *bc, + int *plabel_done, BOOL is_with) +{ + dbuf_putc(bc, get_with_scope_opcode(op)); + dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); + *plabel_done = new_label_fd(s, *plabel_done); + dbuf_put_u32(bc, *plabel_done); + dbuf_putc(bc, is_with); + update_label(s, *plabel_done, 1); + s->jump_size++; +} + /* return the position of the next opcode */ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, JSAtom var_name, int scope_level, int op, DynBuf *bc, uint8_t *bc_buf, - LabelSlot *ls, int pos_next, int arg_valid) + LabelSlot *ls, int pos_next) { int idx, var_idx, is_put; int label_done; - BOOL is_func_var = FALSE; JSFunctionDef *fd; JSVarDef *vd; - BOOL is_pseudo_var; + BOOL is_pseudo_var, is_arg_scope; label_done = -1; @@ -29400,12 +29505,11 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, if (vd->var_name == var_name) { if (op == OP_scope_put_var || op == OP_scope_make_ref) { if (vd->is_const) { - dbuf_putc(bc, OP_throw_var); + dbuf_putc(bc, OP_throw_error); dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); dbuf_putc(bc, JS_THROW_VAR_RO); goto done; } - is_func_var = vd->is_func_var; } var_idx = idx; break; @@ -29413,33 +29517,16 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, if (vd->var_name == JS_ATOM__with_ && !is_pseudo_var) { dbuf_putc(bc, OP_get_loc); dbuf_put_u16(bc, idx); - dbuf_putc(bc, get_with_scope_opcode(op)); - dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); - label_done = new_label_fd(s, label_done); - dbuf_put_u32(bc, label_done); - dbuf_putc(bc, 1); - update_label(s, label_done, 1); - s->jump_size++; + var_object_test(ctx, s, var_name, op, bc, &label_done, 1); } idx = vd->scope_next; } + is_arg_scope = (idx == ARG_SCOPE_END); if (var_idx < 0) { - /* XXX: scoping issues: - should not resolve vars from the function body during argument parse, - `arguments` and function-name should not be hidden by later vars. - */ - var_idx = find_var(ctx, s, var_name); - if (var_idx >= 0) { - if (scope_level == 0 - && (var_idx & ARGUMENT_VAR_OFFSET) - && (var_idx - ARGUMENT_VAR_OFFSET) >= arg_valid) { - /* referring to an uninitialized argument */ - dbuf_putc(bc, OP_throw_var); - dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); - dbuf_putc(bc, JS_THROW_VAR_UNINITIALIZED); - } - if (!(var_idx & ARGUMENT_VAR_OFFSET)) - is_func_var = s->vars[var_idx].is_func_var; + /* argument scope: variables are not visible but pseudo + variables are visible */ + if (!is_arg_scope) { + var_idx = find_var(ctx, s, var_name); } if (var_idx < 0 && is_pseudo_var) @@ -29448,21 +29535,31 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, if (var_idx < 0 && var_name == JS_ATOM_arguments && s->has_arguments_binding) { /* 'arguments' pseudo variable */ - var_idx = add_arguments_var(ctx, s, var_name); + var_idx = add_arguments_var(ctx, s); } if (var_idx < 0 && s->is_func_expr && var_name == s->func_name) { /* add a new variable with the function name */ var_idx = add_func_var(ctx, s, var_name); - is_func_var = TRUE; } } if (var_idx >= 0) { + if ((op == OP_scope_put_var || op == OP_scope_make_ref) && + !(var_idx & ARGUMENT_VAR_OFFSET) && + s->vars[var_idx].is_const) { + /* only happens when assigning a function expression name + in strict mode */ + dbuf_putc(bc, OP_throw_error); + dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); + dbuf_putc(bc, JS_THROW_VAR_RO); + goto done; + } /* OP_scope_put_var_init is only used to initialize a lexical variable, so it is never used in a with or var object. It can be used with a closure (module global variable case). */ switch (op) { case OP_scope_make_ref: - if (is_func_var) { + if (!(var_idx & ARGUMENT_VAR_OFFSET) && + s->vars[var_idx].var_kind == JS_VAR_FUNCTION_NAME) { /* Create a dummy object reference for the func_var */ dbuf_putc(bc, OP_object); dbuf_putc(bc, OP_get_loc); @@ -29510,7 +29607,6 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, if (var_idx & ARGUMENT_VAR_OFFSET) { dbuf_putc(bc, OP_get_arg + is_put); dbuf_put_u16(bc, var_idx - ARGUMENT_VAR_OFFSET); - /* XXX: should test if argument reference needs TDZ check */ } else { if (is_put) { if (s->vars[var_idx].is_lexical) { @@ -29543,41 +29639,32 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, goto done; } /* check eval object */ - if (s->var_object_idx >= 0 && !is_pseudo_var) { + if (!is_arg_scope && s->var_object_idx >= 0 && !is_pseudo_var) { dbuf_putc(bc, OP_get_loc); dbuf_put_u16(bc, s->var_object_idx); - dbuf_putc(bc, get_with_scope_opcode(op)); - dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); - label_done = new_label_fd(s, label_done); - dbuf_put_u32(bc, label_done); - dbuf_putc(bc, 0); - update_label(s, label_done, 1); - s->jump_size++; + var_object_test(ctx, s, var_name, op, bc, &label_done, 0); } + /* check eval object in argument scope */ + if (s->arg_var_object_idx >= 0 && !is_pseudo_var) { + dbuf_putc(bc, OP_get_loc); + dbuf_put_u16(bc, s->arg_var_object_idx); + var_object_test(ctx, s, var_name, op, bc, &label_done, 0); + } + /* check parent scopes */ for (fd = s; fd->parent;) { scope_level = fd->parent_scope_level; fd = fd->parent; - if (scope_level == 0) { - /* function is defined as part of the argument parsing: hide vars - from the function body. - XXX: variables created from argument destructuring might need - to be visible, should refine this method. - */ - var_idx = find_arg(ctx, fd, var_name); - goto check_idx; - } for (idx = fd->scopes[scope_level].first; idx >= 0;) { vd = &fd->vars[idx]; if (vd->var_name == var_name) { if (op == OP_scope_put_var || op == OP_scope_make_ref) { if (vd->is_const) { - dbuf_putc(bc, OP_throw_var); + dbuf_putc(bc, OP_throw_error); dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); dbuf_putc(bc, JS_THROW_VAR_RO); goto done; } - is_func_var = vd->is_func_var; } var_idx = idx; break; @@ -29587,26 +29674,19 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, if (idx >= 0) { dbuf_putc(bc, OP_get_var_ref); dbuf_put_u16(bc, idx); - dbuf_putc(bc, get_with_scope_opcode(op)); - dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); - label_done = new_label_fd(s, label_done); - dbuf_put_u32(bc, label_done); - dbuf_putc(bc, 1); - update_label(s, label_done, 1); - s->jump_size++; + var_object_test(ctx, s, var_name, op, bc, &label_done, 1); } } idx = vd->scope_next; } + is_arg_scope = (idx == ARG_SCOPE_END); if (var_idx >= 0) break; - - var_idx = find_var(ctx, fd, var_name); - check_idx: - if (var_idx >= 0) { - if (!(var_idx & ARGUMENT_VAR_OFFSET)) - is_func_var = fd->vars[var_idx].is_func_var; - break; + + if (!is_arg_scope) { + var_idx = find_var(ctx, fd, var_name); + if (var_idx >= 0) + break; } if (is_pseudo_var) { var_idx = resolve_pseudo_var(ctx, fd, var_name); @@ -29614,33 +29694,39 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, break; } if (var_name == JS_ATOM_arguments && fd->has_arguments_binding) { - var_idx = add_arguments_var(ctx, fd, var_name); + var_idx = add_arguments_var(ctx, fd); break; } if (fd->is_func_expr && fd->func_name == var_name) { /* add a new variable with the function name */ var_idx = add_func_var(ctx, fd, var_name); - is_func_var = TRUE; break; } /* check eval object */ - if (fd->var_object_idx >= 0 && !is_pseudo_var) { - fd->vars[fd->var_object_idx].is_captured = 1; + if (!is_arg_scope && fd->var_object_idx >= 0 && !is_pseudo_var) { + vd = &fd->vars[fd->var_object_idx]; + vd->is_captured = 1; idx = get_closure_var(ctx, s, fd, FALSE, - fd->var_object_idx, JS_ATOM__var_, + fd->var_object_idx, vd->var_name, FALSE, FALSE, JS_VAR_NORMAL); dbuf_putc(bc, OP_get_var_ref); dbuf_put_u16(bc, idx); - dbuf_putc(bc, get_with_scope_opcode(op)); - dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); - label_done = new_label_fd(s, label_done); - dbuf_put_u32(bc, label_done); - dbuf_putc(bc, 0); - update_label(s, label_done, 1); - s->jump_size++; + var_object_test(ctx, s, var_name, op, bc, &label_done, 0); } + /* check eval object in argument scope */ + if (fd->arg_var_object_idx >= 0 && !is_pseudo_var) { + vd = &fd->vars[fd->arg_var_object_idx]; + vd->is_captured = 1; + idx = get_closure_var(ctx, s, fd, FALSE, + fd->arg_var_object_idx, vd->var_name, + FALSE, FALSE, JS_VAR_NORMAL); + dbuf_putc(bc, OP_get_var_ref); + dbuf_put_u16(bc, idx); + var_object_test(ctx, s, var_name, op, bc, &label_done, 0); + } + if (fd->is_eval) break; /* it it necessarily the top level function */ } @@ -29665,6 +29751,7 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, } goto has_idx; } else if ((cv->var_name == JS_ATOM__var_ || + cv->var_name == JS_ATOM__arg_var_ || cv->var_name == JS_ATOM__with_) && !is_pseudo_var) { int is_with = (cv->var_name == JS_ATOM__with_); if (fd != s) { @@ -29678,13 +29765,7 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, } dbuf_putc(bc, OP_get_var_ref); dbuf_put_u16(bc, idx); - dbuf_putc(bc, get_with_scope_opcode(op)); - dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); - label_done = new_label_fd(s, label_done); - dbuf_put_u32(bc, label_done); - dbuf_putc(bc, is_with); - update_label(s, label_done, 1); - s->jump_size++; + var_object_test(ctx, s, var_name, op, bc, &label_done, is_with); } } } @@ -29709,14 +29790,14 @@ static int resolve_scope_var(JSContext *ctx, JSFunctionDef *s, has_idx: if ((op == OP_scope_put_var || op == OP_scope_make_ref) && s->closure_var[idx].is_const) { - dbuf_putc(bc, OP_throw_var); + dbuf_putc(bc, OP_throw_error); dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); dbuf_putc(bc, JS_THROW_VAR_RO); goto done; } switch (op) { case OP_scope_make_ref: - if (is_func_var) { + if (s->closure_var[idx].var_kind == JS_VAR_FUNCTION_NAME) { /* Create a dummy object reference for the func_var */ dbuf_putc(bc, OP_object); dbuf_putc(bc, OP_get_var_ref); @@ -29956,7 +30037,7 @@ static int resolve_scope_private_field(JSContext *ctx, JSFunctionDef *s, break; case JS_VAR_PRIVATE_SETTER: /* XXX: add clearer error message */ - dbuf_putc(bc, OP_throw_var); + dbuf_putc(bc, OP_throw_error); dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); dbuf_putc(bc, JS_THROW_VAR_RO); break; @@ -29973,7 +30054,7 @@ static int resolve_scope_private_field(JSContext *ctx, JSFunctionDef *s, case JS_VAR_PRIVATE_METHOD: case JS_VAR_PRIVATE_GETTER: /* XXX: add clearer error message */ - dbuf_putc(bc, OP_throw_var); + dbuf_putc(bc, OP_throw_error); dbuf_put_u32(bc, JS_DupAtom(ctx, var_name)); dbuf_putc(bc, JS_THROW_VAR_RO); break; @@ -30025,17 +30106,33 @@ static void mark_eval_captured_variables(JSContext *ctx, JSFunctionDef *s, } } +/* XXX: should handle the argument scope generically */ +static BOOL is_var_in_arg_scope(const JSVarDef *vd) +{ + return (vd->var_name == JS_ATOM_home_object || + vd->var_name == JS_ATOM_this_active_func || + vd->var_name == JS_ATOM_new_target || + vd->var_name == JS_ATOM_this || + vd->var_name == JS_ATOM__arg_var_ || + vd->var_kind == JS_VAR_FUNCTION_NAME); +} + static void add_eval_variables(JSContext *ctx, JSFunctionDef *s) { JSFunctionDef *fd; JSVarDef *vd; int i, scope_level, scope_idx; - BOOL has_arguments_binding, has_this_binding; + BOOL has_arguments_binding, has_this_binding, is_arg_scope; /* in non strict mode, variables are created in the caller's environment object */ if (!s->is_eval && !(s->js_mode & JS_MODE_STRICT)) { s->var_object_idx = add_var(ctx, s, JS_ATOM__var_); + if (s->has_parameter_expressions) { + /* an additional variable object is needed for the + argument scope */ + s->arg_var_object_idx = add_var(ctx, s, JS_ATOM__arg_var_); + } } /* eval can potentially use 'arguments' so we must define it */ @@ -30051,8 +30148,14 @@ static void add_eval_variables(JSContext *ctx, JSFunctionDef *s) s->home_object_var_idx = add_var(ctx, s, JS_ATOM_home_object); } has_arguments_binding = s->has_arguments_binding; - if (has_arguments_binding) - add_arguments_var(ctx, s, JS_ATOM_arguments); + if (has_arguments_binding) { + add_arguments_var(ctx, s); + /* also add an arguments binding in the argument scope to + raise an error if a direct eval in the argument scope tries + to redefine it */ + if (s->has_parameter_expressions && !(s->js_mode & JS_MODE_STRICT)) + add_arguments_arg(ctx, s); + } if (s->is_func_expr && s->func_name != JS_ATOM_NULL) add_func_var(ctx, s, s->func_name); @@ -30069,7 +30172,6 @@ static void add_eval_variables(JSContext *ctx, JSFunctionDef *s) fd = fd->parent; if (!fd) break; - scope_idx = fd->scopes[scope_level].first; /* add 'this' if it was not previously added */ if (!has_this_binding && fd->has_this_binding) { if (fd->this_var_idx < 0) @@ -30084,7 +30186,7 @@ static void add_eval_variables(JSContext *ctx, JSFunctionDef *s) } /* add 'arguments' if it was not previously added */ if (!has_arguments_binding && fd->has_arguments_binding) { - add_arguments_var(ctx, fd, JS_ATOM_arguments); + add_arguments_var(ctx, fd); has_arguments_binding = TRUE; } /* add function name */ @@ -30092,6 +30194,7 @@ static void add_eval_variables(JSContext *ctx, JSFunctionDef *s) add_func_var(ctx, fd, fd->func_name); /* add lexical variables */ + scope_idx = fd->scopes[scope_level].first; while (scope_idx >= 0) { vd = &fd->vars[scope_idx]; vd->is_captured = 1; @@ -30099,24 +30202,37 @@ static void add_eval_variables(JSContext *ctx, JSFunctionDef *s) vd->var_name, vd->is_const, vd->is_lexical, vd->var_kind); scope_idx = vd->scope_next; } - /* add unscoped variables */ - for(i = 0; i < fd->arg_count; i++) { - vd = &fd->args[i]; - if (vd->var_name != JS_ATOM_NULL) { - get_closure_var(ctx, s, fd, - TRUE, i, vd->var_name, FALSE, FALSE, - JS_VAR_NORMAL); + is_arg_scope = (scope_idx == ARG_SCOPE_END); + if (!is_arg_scope) { + /* add unscoped variables */ + for(i = 0; i < fd->arg_count; i++) { + vd = &fd->args[i]; + if (vd->var_name != JS_ATOM_NULL) { + get_closure_var(ctx, s, fd, + TRUE, i, vd->var_name, FALSE, FALSE, + JS_VAR_NORMAL); + } } - } - for(i = 0; i < fd->var_count; i++) { - vd = &fd->vars[i]; - /* do not close top level last result */ - if (vd->scope_level == 0 && - vd->var_name != JS_ATOM__ret_ && - vd->var_name != JS_ATOM_NULL) { - get_closure_var(ctx, s, fd, - FALSE, i, vd->var_name, FALSE, FALSE, - JS_VAR_NORMAL); + for(i = 0; i < fd->var_count; i++) { + vd = &fd->vars[i]; + /* do not close top level last result */ + if (vd->scope_level == 0 && + vd->var_name != JS_ATOM__ret_ && + vd->var_name != JS_ATOM_NULL) { + get_closure_var(ctx, s, fd, + FALSE, i, vd->var_name, FALSE, FALSE, + JS_VAR_NORMAL); + } + } + } else { + for(i = 0; i < fd->var_count; i++) { + vd = &fd->vars[i]; + /* do not close top level last result */ + if (vd->scope_level == 0 && is_var_in_arg_scope(vd)) { + get_closure_var(ctx, s, fd, + FALSE, i, vd->var_name, FALSE, FALSE, + JS_VAR_NORMAL); + } } } if (fd->is_eval) { @@ -30134,6 +30250,18 @@ static void add_eval_variables(JSContext *ctx, JSFunctionDef *s) } } +static void set_closure_from_var(JSContext *ctx, JSClosureVar *cv, + JSVarDef *vd, int var_idx) +{ + cv->is_local = TRUE; + cv->is_arg = FALSE; + cv->is_const = vd->is_const; + cv->is_lexical = vd->is_lexical; + cv->var_kind = vd->var_kind; + cv->var_idx = var_idx; + cv->var_name = JS_DupAtom(ctx, vd->var_name); +} + /* for direct eval compilation: add references to the variables of the calling function */ static __exception int add_closure_variables(JSContext *ctx, JSFunctionDef *s, @@ -30141,7 +30269,8 @@ static __exception int add_closure_variables(JSContext *ctx, JSFunctionDef *s, { int i, count; JSVarDef *vd; - + BOOL is_arg_scope; + count = b->arg_count + b->var_count + b->closure_var_count; s->closure_var = NULL; s->closure_var_count = 0; @@ -30156,41 +30285,41 @@ static __exception int add_closure_variables(JSContext *ctx, JSFunctionDef *s, vd = &b->vardefs[b->arg_count + i]; if (vd->scope_level > 0) { JSClosureVar *cv = &s->closure_var[s->closure_var_count++]; - cv->is_local = TRUE; - cv->is_arg = FALSE; - cv->is_const = vd->is_const; - cv->is_lexical = vd->is_lexical; - cv->var_kind = vd->var_kind; - cv->var_idx = i; - cv->var_name = JS_DupAtom(ctx, vd->var_name); + set_closure_from_var(ctx, cv, vd, i); } i = vd->scope_next; } - /* Add argument variables */ - for(i = 0; i < b->arg_count; i++) { - JSClosureVar *cv = &s->closure_var[s->closure_var_count++]; - vd = &b->vardefs[i]; - cv->is_local = TRUE; - cv->is_arg = TRUE; - cv->is_const = FALSE; - cv->is_lexical = FALSE; - cv->var_kind = JS_VAR_NORMAL; - cv->var_idx = i; - cv->var_name = JS_DupAtom(ctx, vd->var_name); - } - /* Add local non lexical variables */ - for(i = 0; i < b->var_count; i++) { - vd = &b->vardefs[b->arg_count + i]; - if (vd->scope_level == 0 && vd->var_name != JS_ATOM__ret_) { + is_arg_scope = (i == ARG_SCOPE_END); + if (!is_arg_scope) { + /* Add argument variables */ + for(i = 0; i < b->arg_count; i++) { JSClosureVar *cv = &s->closure_var[s->closure_var_count++]; + vd = &b->vardefs[i]; cv->is_local = TRUE; - cv->is_arg = FALSE; + cv->is_arg = TRUE; cv->is_const = FALSE; cv->is_lexical = FALSE; cv->var_kind = JS_VAR_NORMAL; cv->var_idx = i; cv->var_name = JS_DupAtom(ctx, vd->var_name); } + /* Add local non lexical variables */ + for(i = 0; i < b->var_count; i++) { + vd = &b->vardefs[b->arg_count + i]; + if (vd->scope_level == 0 && vd->var_name != JS_ATOM__ret_) { + JSClosureVar *cv = &s->closure_var[s->closure_var_count++]; + set_closure_from_var(ctx, cv, vd, i); + } + } + } else { + /* only add pseudo variables */ + for(i = 0; i < b->var_count; i++) { + vd = &b->vardefs[b->arg_count + i]; + if (vd->scope_level == 0 && is_var_in_arg_scope(vd)) { + JSClosureVar *cv = &s->closure_var[s->closure_var_count++]; + set_closure_from_var(ctx, cv, vd, i); + } + } } for(i = 0; i < b->closure_var_count; i++) { JSClosureVar *cv0 = &b->closure_var[i]; @@ -30348,59 +30477,93 @@ static BOOL code_match(CodeContext *s, int pos, ...) static void instantiate_hoisted_definitions(JSContext *ctx, JSFunctionDef *s, DynBuf *bc) { - int i, idx, var_idx; + int i, idx, label_next = -1; - /* add the hoisted functions and variables */ - for(i = 0; i < s->hoisted_def_count; i++) { - JSHoistedDef *hf = &s->hoisted_def[i]; + /* add the hoisted functions in arguments and local variables */ + for(i = 0; i < s->arg_count; i++) { + JSVarDef *vd = &s->args[i]; + if (vd->func_pool_idx >= 0) { + dbuf_putc(bc, OP_fclosure); + dbuf_put_u32(bc, vd->func_pool_idx); + dbuf_putc(bc, OP_put_arg); + dbuf_put_u16(bc, i); + } + } + for(i = 0; i < s->var_count; i++) { + JSVarDef *vd = &s->vars[i]; + if (vd->scope_level == 0 && vd->func_pool_idx >= 0) { + dbuf_putc(bc, OP_fclosure); + dbuf_put_u32(bc, vd->func_pool_idx); + dbuf_putc(bc, OP_put_loc); + dbuf_put_u16(bc, i); + } + } + + /* the module global variables must be initialized before + evaluating the module so that the exported functions are + visible if there are cyclic module references */ + if (s->module) { + label_next = new_label_fd(s, -1); + + /* if 'this' is true, initialize the global variables and return */ + dbuf_putc(bc, OP_push_this); + dbuf_putc(bc, OP_if_false); + dbuf_put_u32(bc, label_next); + update_label(s, label_next, 1); + s->jump_size++; + } + + /* add the global variables (only happens if s->is_global_var is + true) */ + for(i = 0; i < s->global_var_count; i++) { + JSGlobalVar *hf = &s->global_vars[i]; int has_closure = 0; BOOL force_init = hf->force_init; - if (s->is_global_var && hf->var_name != JS_ATOM_NULL) { - /* we are in an eval, so the closure contains all the - enclosing variables */ - /* If the outer function has a variable environment, - create a property for the variable there */ - for(idx = 0; idx < s->closure_var_count; idx++) { - JSClosureVar *cv = &s->closure_var[idx]; - if (cv->var_name == hf->var_name) { - has_closure = 2; - force_init = FALSE; - break; - } - if (cv->var_name == JS_ATOM__var_) { - dbuf_putc(bc, OP_get_var_ref); - dbuf_put_u16(bc, idx); - has_closure = 1; - force_init = TRUE; - break; - } + /* we are in an eval, so the closure contains all the + enclosing variables */ + /* If the outer function has a variable environment, + create a property for the variable there */ + for(idx = 0; idx < s->closure_var_count; idx++) { + JSClosureVar *cv = &s->closure_var[idx]; + if (cv->var_name == hf->var_name) { + has_closure = 2; + force_init = FALSE; + break; } - if (!has_closure) { - int flags; - - flags = 0; - if (s->eval_type != JS_EVAL_TYPE_GLOBAL) - flags |= JS_PROP_CONFIGURABLE; - if (hf->cpool_idx >= 0 && !hf->is_lexical) { - /* global function definitions need a specific handling */ - dbuf_putc(bc, OP_fclosure); - dbuf_put_u32(bc, hf->cpool_idx); - - dbuf_putc(bc, OP_define_func); - dbuf_put_u32(bc, JS_DupAtom(ctx, hf->var_name)); - dbuf_putc(bc, flags); - - goto done_hoisted_def; - } else { - if (hf->is_lexical) { - flags |= DEFINE_GLOBAL_LEX_VAR; - if (!hf->is_const) - flags |= JS_PROP_WRITABLE; - } - dbuf_putc(bc, OP_define_var); - dbuf_put_u32(bc, JS_DupAtom(ctx, hf->var_name)); - dbuf_putc(bc, flags); + if (cv->var_name == JS_ATOM__var_ || + cv->var_name == JS_ATOM__arg_var_) { + dbuf_putc(bc, OP_get_var_ref); + dbuf_put_u16(bc, idx); + has_closure = 1; + force_init = TRUE; + break; + } + } + if (!has_closure) { + int flags; + + flags = 0; + if (s->eval_type != JS_EVAL_TYPE_GLOBAL) + flags |= JS_PROP_CONFIGURABLE; + if (hf->cpool_idx >= 0 && !hf->is_lexical) { + /* global function definitions need a specific handling */ + dbuf_putc(bc, OP_fclosure); + dbuf_put_u32(bc, hf->cpool_idx); + + dbuf_putc(bc, OP_define_func); + dbuf_put_u32(bc, JS_DupAtom(ctx, hf->var_name)); + dbuf_putc(bc, flags); + + goto done_global_var; + } else { + if (hf->is_lexical) { + flags |= DEFINE_GLOBAL_LEX_VAR; + if (!hf->is_const) + flags |= JS_PROP_WRITABLE; } + dbuf_putc(bc, OP_define_var); + dbuf_put_u32(bc, JS_DupAtom(ctx, hf->var_name)); + dbuf_putc(bc, flags); } } if (hf->cpool_idx >= 0 || force_init) { @@ -30415,37 +30578,35 @@ static void instantiate_hoisted_definitions(JSContext *ctx, JSFunctionDef *s, Dy } else { dbuf_putc(bc, OP_undefined); } - if (s->is_global_var) { - if (has_closure == 2) { - dbuf_putc(bc, OP_put_var_ref); - dbuf_put_u16(bc, idx); - } else if (has_closure == 1) { - dbuf_putc(bc, OP_define_field); - dbuf_put_u32(bc, JS_DupAtom(ctx, hf->var_name)); - dbuf_putc(bc, OP_drop); - } else { - /* XXX: Check if variable is writable and enumerable */ - dbuf_putc(bc, OP_put_var); - dbuf_put_u32(bc, JS_DupAtom(ctx, hf->var_name)); - } + if (has_closure == 2) { + dbuf_putc(bc, OP_put_var_ref); + dbuf_put_u16(bc, idx); + } else if (has_closure == 1) { + dbuf_putc(bc, OP_define_field); + dbuf_put_u32(bc, JS_DupAtom(ctx, hf->var_name)); + dbuf_putc(bc, OP_drop); } else { - var_idx = hf->var_idx; - if (var_idx & ARGUMENT_VAR_OFFSET) { - dbuf_putc(bc, OP_put_arg); - dbuf_put_u16(bc, var_idx - ARGUMENT_VAR_OFFSET); - } else { - dbuf_putc(bc, OP_put_loc); - dbuf_put_u16(bc, var_idx); - } + /* XXX: Check if variable is writable and enumerable */ + dbuf_putc(bc, OP_put_var); + dbuf_put_u32(bc, JS_DupAtom(ctx, hf->var_name)); } } - done_hoisted_def: + done_global_var: JS_FreeAtom(ctx, hf->var_name); } - js_free(ctx, s->hoisted_def); - s->hoisted_def = NULL; - s->hoisted_def_count = 0; - s->hoisted_def_size = 0; + + if (s->module) { + dbuf_putc(bc, OP_return_undef); + + dbuf_putc(bc, OP_label); + dbuf_put_u32(bc, label_next); + s->label_slots[label_next].pos2 = bc->size; + } + + js_free(ctx, s->global_vars); + s->global_vars = NULL; + s->global_var_count = 0; + s->global_var_size = 0; } static int skip_dead_code(JSFunctionDef *s, const uint8_t *bc_buf, int bc_len, @@ -30525,7 +30686,7 @@ static int get_label_pos(JSFunctionDef *s, int label) variables when necessary */ static __exception int resolve_variables(JSContext *ctx, JSFunctionDef *s) { - int pos, pos_next, bc_len, op, len, i, idx, arg_valid, line_num; + int pos, pos_next, bc_len, op, len, i, idx, line_num; uint8_t *bc_buf; JSAtom var_name; DynBuf bc_out; @@ -30538,47 +30699,43 @@ static __exception int resolve_variables(JSContext *ctx, JSFunctionDef *s) /* first pass for runtime checks (must be done before the variables are created) */ - if (s->is_global_var) { - for(i = 0; i < s->hoisted_def_count; i++) { - JSHoistedDef *hf = &s->hoisted_def[i]; - int flags; - - if (hf->var_name != JS_ATOM_NULL) { - /* check if global variable (XXX: simplify) */ - for(idx = 0; idx < s->closure_var_count; idx++) { - JSClosureVar *cv = &s->closure_var[idx]; - if (cv->var_name == hf->var_name) { - if (s->eval_type == JS_EVAL_TYPE_DIRECT && - cv->is_lexical) { - /* Check if a lexical variable is - redefined as 'var'. XXX: Could abort - compilation here, but for consistency - with the other checks, we delay the - error generation. */ - dbuf_putc(&bc_out, OP_throw_var); - dbuf_put_u32(&bc_out, JS_DupAtom(ctx, hf->var_name)); - dbuf_putc(&bc_out, JS_THROW_VAR_REDECL); - } - goto next; - } - if (cv->var_name == JS_ATOM__var_) - goto next; + for(i = 0; i < s->global_var_count; i++) { + JSGlobalVar *hf = &s->global_vars[i]; + int flags; + + /* check if global variable (XXX: simplify) */ + for(idx = 0; idx < s->closure_var_count; idx++) { + JSClosureVar *cv = &s->closure_var[idx]; + if (cv->var_name == hf->var_name) { + if (s->eval_type == JS_EVAL_TYPE_DIRECT && + cv->is_lexical) { + /* Check if a lexical variable is + redefined as 'var'. XXX: Could abort + compilation here, but for consistency + with the other checks, we delay the + error generation. */ + dbuf_putc(&bc_out, OP_throw_error); + dbuf_put_u32(&bc_out, JS_DupAtom(ctx, hf->var_name)); + dbuf_putc(&bc_out, JS_THROW_VAR_REDECL); } - - dbuf_putc(&bc_out, OP_check_define_var); - dbuf_put_u32(&bc_out, JS_DupAtom(ctx, hf->var_name)); - flags = 0; - if (hf->is_lexical) - flags |= DEFINE_GLOBAL_LEX_VAR; - if (hf->cpool_idx >= 0) - flags |= DEFINE_GLOBAL_FUNC_VAR; - dbuf_putc(&bc_out, flags); + goto next; } - next: ; + if (cv->var_name == JS_ATOM__var_ || + cv->var_name == JS_ATOM__arg_var_) + goto next; } + + dbuf_putc(&bc_out, OP_check_define_var); + dbuf_put_u32(&bc_out, JS_DupAtom(ctx, hf->var_name)); + flags = 0; + if (hf->is_lexical) + flags |= DEFINE_GLOBAL_LEX_VAR; + if (hf->cpool_idx >= 0) + flags |= DEFINE_GLOBAL_FUNC_VAR; + dbuf_putc(&bc_out, flags); + next: ; } - arg_valid = 0; line_num = 0; /* avoid warning */ for (pos = 0; pos < bc_len; pos = pos_next) { op = bc_buf[pos]; @@ -30590,9 +30747,6 @@ static __exception int resolve_variables(JSContext *ctx, JSFunctionDef *s) s->line_number_size++; goto no_change; - case OP_set_arg_valid_upto: - arg_valid = get_u16(bc_buf + pos + 1); - break; case OP_eval: /* convert scope index to adjusted variable index */ { int call_argc = get_u16(bc_buf + pos + 1); @@ -30618,7 +30772,7 @@ static __exception int resolve_variables(JSContext *ctx, JSFunctionDef *s) var_name = get_u32(bc_buf + pos + 1); scope = get_u16(bc_buf + pos + 5); pos_next = resolve_scope_var(ctx, s, var_name, scope, op, &bc_out, - NULL, NULL, pos_next, arg_valid); + NULL, NULL, pos_next); JS_FreeAtom(ctx, var_name); break; case OP_scope_make_ref: @@ -30631,7 +30785,7 @@ static __exception int resolve_variables(JSContext *ctx, JSFunctionDef *s) ls = &s->label_slots[label]; ls->ref_count--; /* always remove label reference */ pos_next = resolve_scope_var(ctx, s, var_name, scope, op, &bc_out, - bc_buf, ls, pos_next, arg_valid); + bc_buf, ls, pos_next); JS_FreeAtom(ctx, var_name); } break; @@ -30712,7 +30866,7 @@ static __exception int resolve_variables(JSContext *ctx, JSFunctionDef *s) case OP_return: case OP_return_undef: case OP_throw: - case OP_throw_var: + case OP_throw_error: case OP_ret: if (OPTIMIZE) { /* remove dead code */ @@ -30746,25 +30900,27 @@ static __exception int resolve_variables(JSContext *ctx, JSFunctionDef *s) { int scope_idx, scope = get_u16(bc_buf + pos + 1); - if (scope == 1) { + if (scope == s->body_scope) { instantiate_hoisted_definitions(ctx, s, &bc_out); } for(scope_idx = s->scopes[scope].first; scope_idx >= 0;) { JSVarDef *vd = &s->vars[scope_idx]; if (vd->scope_level == scope) { - if (vd->var_kind == JS_VAR_FUNCTION_DECL || - vd->var_kind == JS_VAR_NEW_FUNCTION_DECL) { - /* Initialize lexical variable upon entering scope */ - dbuf_putc(&bc_out, OP_fclosure); - dbuf_put_u32(&bc_out, vd->func_pool_or_scope_idx); - dbuf_putc(&bc_out, OP_put_loc); - dbuf_put_u16(&bc_out, scope_idx); - } else { - /* XXX: should check if variable can be used - before initialization */ - dbuf_putc(&bc_out, OP_set_loc_uninitialized); - dbuf_put_u16(&bc_out, scope_idx); + if (scope_idx != s->arguments_arg_idx) { + if (vd->var_kind == JS_VAR_FUNCTION_DECL || + vd->var_kind == JS_VAR_NEW_FUNCTION_DECL) { + /* Initialize lexical variable upon entering scope */ + dbuf_putc(&bc_out, OP_fclosure); + dbuf_put_u32(&bc_out, vd->func_pool_idx); + dbuf_putc(&bc_out, OP_put_loc); + dbuf_put_u16(&bc_out, scope_idx); + } else { + /* XXX: should check if variable can be used + before initialization */ + dbuf_putc(&bc_out, OP_set_loc_uninitialized); + dbuf_put_u16(&bc_out, scope_idx); + } } scope_idx = vd->scope_next; } else { @@ -31167,6 +31323,8 @@ static __exception int resolve_labels(JSContext *ctx, JSFunctionDef *s) dbuf_putc(&bc_out, OP_special_object); dbuf_putc(&bc_out, OP_SPECIAL_OBJECT_MAPPED_ARGUMENTS); } + if (s->arguments_arg_idx >= 0) + put_short_code(&bc_out, OP_set_loc, s->arguments_arg_idx); put_short_code(&bc_out, OP_put_loc, s->arguments_var_idx); } /* initialize a reference to the current function if needed */ @@ -31181,6 +31339,11 @@ static __exception int resolve_labels(JSContext *ctx, JSFunctionDef *s) dbuf_putc(&bc_out, OP_SPECIAL_OBJECT_VAR_OBJECT); put_short_code(&bc_out, OP_put_loc, s->var_object_idx); } + if (s->arg_var_object_idx >= 0) { + dbuf_putc(&bc_out, OP_special_object); + dbuf_putc(&bc_out, OP_SPECIAL_OBJECT_VAR_OBJECT); + put_short_code(&bc_out, OP_put_loc, s->arg_var_object_idx); + } for (pos = 0; pos < bc_len; pos = pos_next) { int val; @@ -31248,7 +31411,7 @@ static __exception int resolve_labels(JSContext *ctx, JSFunctionDef *s) case OP_return_undef: case OP_return_async: case OP_throw: - case OP_throw_var: + case OP_throw_error: pos_next = skip_dead_code(s, bc_buf, bc_len, pos_next, &line_num); goto no_change; @@ -31969,56 +32132,91 @@ static __exception int resolve_labels(JSContext *ctx, JSFunctionDef *s) /* compute the maximum stack size needed by the function */ typedef struct StackSizeState { + int bc_len; int stack_len_max; uint16_t *stack_level_tab; + int *pc_stack; + int pc_stack_len; + int pc_stack_size; } StackSizeState; -static __exception int compute_stack_size_rec(JSContext *ctx, - JSFunctionDef *fd, - StackSizeState *s, - int pos, int op, int stack_len) +/* 'op' is only used for error indication */ +static __exception int ss_check(JSContext *ctx, StackSizeState *s, + int pos, int op, int stack_len) { - int bc_len, diff, n_pop, pos_next; + if ((unsigned)pos >= s->bc_len) { + JS_ThrowInternalError(ctx, "bytecode buffer overflow (op=%d, pc=%d)", op, pos); + return -1; + } + if (stack_len > s->stack_len_max) { + s->stack_len_max = stack_len; + if (s->stack_len_max > JS_STACK_SIZE_MAX) { + JS_ThrowInternalError(ctx, "stack overflow (op=%d, pc=%d)", op, pos); + return -1; + } + } + if (s->stack_level_tab[pos] != 0xffff) { + /* already explored: check that the stack size is consistent */ + if (s->stack_level_tab[pos] != stack_len) { + JS_ThrowInternalError(ctx, "unconsistent stack size: %d %d (pc=%d)", + s->stack_level_tab[pos], stack_len, pos); + return -1; + } else { + return 0; + } + } + + /* mark as explored and store the stack size */ + s->stack_level_tab[pos] = stack_len; + + /* queue the new PC to explore */ + if (js_resize_array(ctx, (void **)&s->pc_stack, sizeof(s->pc_stack[0]), + &s->pc_stack_size, s->pc_stack_len + 1)) + return -1; + s->pc_stack[s->pc_stack_len++] = pos; + return 0; +} + +static __exception int compute_stack_size(JSContext *ctx, + JSFunctionDef *fd, + int *pstack_size) +{ + StackSizeState s_s, *s = &s_s; + int i, diff, n_pop, pos_next, stack_len, pos, op; const JSOpCode *oi; const uint8_t *bc_buf; - if (stack_len > s->stack_len_max) { - s->stack_len_max = stack_len; - if (s->stack_len_max > JS_STACK_SIZE_MAX) - goto stack_overflow; - } bc_buf = fd->byte_code.buf; - bc_len = fd->byte_code.size; - for(;;) { - if ((unsigned)pos >= bc_len) - goto buf_overflow; -#if 0 - printf("%5d: %d\n", pos, stack_len); -#endif - if (s->stack_level_tab[pos] != 0xffff) { - /* already explored: check that the stack size is consistent */ - if (s->stack_level_tab[pos] != stack_len) { - JS_ThrowInternalError(ctx, "unconsistent stack size: %d %d (pc=%d)", - s->stack_level_tab[pos], stack_len, pos); - return -1; - } else { - return 0; - } - } else { - s->stack_level_tab[pos] = stack_len; - } + s->bc_len = fd->byte_code.size; + /* bc_len > 0 */ + s->stack_level_tab = js_malloc(ctx, sizeof(s->stack_level_tab[0]) * + s->bc_len); + if (!s->stack_level_tab) + return -1; + for(i = 0; i < s->bc_len; i++) + s->stack_level_tab[i] = 0xffff; + s->stack_len_max = 0; + s->pc_stack = NULL; + s->pc_stack_len = 0; + s->pc_stack_size = 0; + /* breadth-first graph exploration */ + if (ss_check(ctx, s, 0, OP_invalid, 0)) + goto fail; + + while (s->pc_stack_len > 0) { + pos = s->pc_stack[--s->pc_stack_len]; + stack_len = s->stack_level_tab[pos]; op = bc_buf[pos]; if (op == 0 || op >= OP_COUNT) { JS_ThrowInternalError(ctx, "invalid opcode (op=%d, pc=%d)", op, pos); - return -1; + goto fail; } oi = &short_opcode_info(op); pos_next = pos + oi->size; - if (pos_next > bc_len) { - buf_overflow: + if (pos_next > s->bc_len) { JS_ThrowInternalError(ctx, "bytecode buffer overflow (op=%d, pc=%d)", op, pos); - return -1; + goto fail; } n_pop = oi->n_pop; /* call pops a variable number of arguments */ @@ -32034,13 +32232,15 @@ static __exception int compute_stack_size_rec(JSContext *ctx, if (stack_len < n_pop) { JS_ThrowInternalError(ctx, "stack underflow (op=%d, pc=%d)", op, pos); - return -1; + goto fail; } stack_len += oi->n_push - n_pop; if (stack_len > s->stack_len_max) { s->stack_len_max = stack_len; - if (s->stack_len_max > JS_STACK_SIZE_MAX) - goto stack_overflow; + if (s->stack_len_max > JS_STACK_SIZE_MAX) { + JS_ThrowInternalError(ctx, "stack overflow (op=%d, pc=%d)", op, pos); + goto fail; + } } switch(op) { case OP_tail_call: @@ -32049,9 +32249,9 @@ static __exception int compute_stack_size_rec(JSContext *ctx, case OP_return_undef: case OP_return_async: case OP_throw: - case OP_throw_var: + case OP_throw_error: case OP_ret: - goto done; + goto done_insn; case OP_goto: diff = get_u32(bc_buf + pos + 1); pos_next = pos + 1 + diff; @@ -32068,73 +32268,57 @@ static __exception int compute_stack_size_rec(JSContext *ctx, case OP_if_true8: case OP_if_false8: diff = (int8_t)bc_buf[pos + 1]; - if (compute_stack_size_rec(ctx, fd, s, pos + 1 + diff, op, stack_len)) - return -1; + if (ss_check(ctx, s, pos + 1 + diff, op, stack_len)) + goto fail; break; #endif case OP_if_true: case OP_if_false: case OP_catch: diff = get_u32(bc_buf + pos + 1); - if (compute_stack_size_rec(ctx, fd, s, pos + 1 + diff, op, stack_len)) - return -1; + if (ss_check(ctx, s, pos + 1 + diff, op, stack_len)) + goto fail; break; case OP_gosub: diff = get_u32(bc_buf + pos + 1); - if (compute_stack_size_rec(ctx, fd, s, pos + 1 + diff, op, stack_len + 1)) - return -1; + if (ss_check(ctx, s, pos + 1 + diff, op, stack_len + 1)) + goto fail; break; case OP_with_get_var: case OP_with_delete_var: diff = get_u32(bc_buf + pos + 5); - if (compute_stack_size_rec(ctx, fd, s, pos + 5 + diff, op, stack_len + 1)) - return -1; + if (ss_check(ctx, s, pos + 5 + diff, op, stack_len + 1)) + goto fail; break; case OP_with_make_ref: case OP_with_get_ref: case OP_with_get_ref_undef: diff = get_u32(bc_buf + pos + 5); - if (compute_stack_size_rec(ctx, fd, s, pos + 5 + diff, op, stack_len + 2)) - return -1; + if (ss_check(ctx, s, pos + 5 + diff, op, stack_len + 2)) + goto fail; break; case OP_with_put_var: diff = get_u32(bc_buf + pos + 5); - if (compute_stack_size_rec(ctx, fd, s, pos + 5 + diff, op, stack_len - 1)) - return -1; + if (ss_check(ctx, s, pos + 5 + diff, op, stack_len - 1)) + goto fail; break; default: break; } - pos = pos_next; + if (ss_check(ctx, s, pos_next, op, stack_len)) + goto fail; + done_insn: ; } - done: - return 0; - - stack_overflow: - JS_ThrowInternalError(ctx, "stack overflow (op=%d, pc=%d)", op, pos); - return -1; -} - -static __exception int compute_stack_size(JSContext *ctx, - JSFunctionDef *fd, - int *pstack_size) -{ - StackSizeState s_s, *s = &s_s; - int bc_len, i, ret; - - bc_len = fd->byte_code.size; - /* bc_len > 0 */ - s->stack_level_tab = js_malloc(ctx, sizeof(s->stack_level_tab[0]) * bc_len); - if (!s->stack_level_tab) - return -1; - for(i = 0; i < bc_len; i++) - s->stack_level_tab[i] = 0xffff; - s->stack_len_max = 0; - ret = compute_stack_size_rec(ctx, fd, s, 0, OP_invalid, 0); js_free(ctx, s->stack_level_tab); + js_free(ctx, s->pc_stack); *pstack_size = s->stack_len_max; - return ret; + return 0; + fail: + js_free(ctx, s->stack_level_tab); + js_free(ctx, s->pc_stack); + *pstack_size = 0; + return -1; } static int add_module_variables(JSContext *ctx, JSFunctionDef *fd) @@ -32142,14 +32326,14 @@ static int add_module_variables(JSContext *ctx, JSFunctionDef *fd) int i, idx; JSModuleDef *m = fd->module; JSExportEntry *me; - JSHoistedDef *hf; + JSGlobalVar *hf; /* The imported global variables were added as closure variables in js_parse_import(). We add here the module global variables. */ - for(i = 0; i < fd->hoisted_def_count; i++) { - hf = &fd->hoisted_def[i]; + for(i = 0; i < fd->global_var_count; i++) { + hf = &fd->global_vars[i]; if (add_closure_var(ctx, fd, TRUE, FALSE, i, hf->var_name, hf->is_const, hf->is_lexical, FALSE) < 0) return -1; @@ -32187,6 +32371,10 @@ static JSValue js_create_function(JSContext *ctx, JSFunctionDef *fd) for (scope = 0; scope < fd->scope_count; scope++) { fd->scopes[scope].first = -1; } + if (fd->has_parameter_expressions) { + /* special end of variable list marker for the argument scope */ + fd->scopes[ARG_SCOPE_INDEX].first = ARG_SCOPE_END; + } for (idx = 0; idx < fd->var_count; idx++) { JSVarDef *vd = &fd->vars[idx]; vd->scope_next = fd->scopes[vd->scope_level].first; @@ -32194,12 +32382,12 @@ static JSValue js_create_function(JSContext *ctx, JSFunctionDef *fd) } for (scope = 2; scope < fd->scope_count; scope++) { JSVarScope *sd = &fd->scopes[scope]; - if (sd->first == -1) + if (sd->first < 0) sd->first = fd->scopes[sd->parent].first; } for (idx = 0; idx < fd->var_count; idx++) { JSVarDef *vd = &fd->vars[idx]; - if (vd->scope_next == -1 && vd->scope_level > 1) { + if (vd->scope_next < 0 && vd->scope_level > 1) { scope = fd->scopes[vd->scope_level].parent; vd->scope_next = fd->scopes[scope].first; } @@ -32571,7 +32759,8 @@ static int js_parse_function_check_names(JSParseState *s, JSFunctionDef *fd, /* Check if argument name duplicates a destructuring parameter */ /* XXX: should have a flag for such variables */ for (i = 0; i < fd->var_count; i++) { - if (fd->vars[i].var_name == name) + if (fd->vars[i].var_name == name && + fd->vars[i].scope_level == 0) goto duplicate; } } @@ -32680,8 +32869,8 @@ static __exception int js_parse_function_decl2(JSParseState *s, if (fd->is_eval && fd->eval_type == JS_EVAL_TYPE_MODULE && (func_type == JS_PARSE_FUNC_STATEMENT || func_type == JS_PARSE_FUNC_VAR)) { - JSHoistedDef *hf; - hf = find_hoisted_def(fd, func_name); + JSGlobalVar *hf; + hf = find_global_var(fd, func_name); /* XXX: should check scope chain */ if (hf && hf->scope_level == fd->scope_level) { js_parse_error(s, "invalid redefinition of global identifier in module code"); @@ -32691,21 +32880,23 @@ static __exception int js_parse_function_decl2(JSParseState *s, } if (func_type == JS_PARSE_FUNC_VAR) { - /* Create lexical name here so function closure contains it */ if (!(fd->js_mode & JS_MODE_STRICT) + && func_kind == JS_FUNC_NORMAL && find_lexical_decl(ctx, fd, func_name, fd->scope_first, FALSE) < 0 && !((func_idx = find_var(ctx, fd, func_name)) >= 0 && (func_idx & ARGUMENT_VAR_OFFSET)) && !(func_name == JS_ATOM_arguments && fd->has_arguments_binding)) { create_func_var = TRUE; } + /* Create the lexical name here so that the function closure + contains it */ if (fd->is_eval && (fd->eval_type == JS_EVAL_TYPE_GLOBAL || fd->eval_type == JS_EVAL_TYPE_MODULE) && - fd->scope_level == 1) { + fd->scope_level == fd->body_scope) { /* avoid creating a lexical variable in the global scope. XXX: check annex B */ - JSHoistedDef *hf; - hf = find_hoisted_def(fd, func_name); + JSGlobalVar *hf; + hf = find_global_var(fd, func_name); /* XXX: should check scope chain */ if (hf && hf->scope_level == fd->scope_level) { js_parse_error(s, "invalid redefinition of global identifier"); @@ -32780,6 +32971,7 @@ static __exception int js_parse_function_decl2(JSParseState *s, /* parse arguments */ fd->has_simple_parameter_list = TRUE; + fd->has_parameter_expressions = FALSE; has_opt_arg = FALSE; if (func_type == JS_PARSE_FUNC_ARROW && s->token.val == TOK_IDENT) { JSAtom name; @@ -32792,13 +32984,30 @@ static __exception int js_parse_function_decl2(JSParseState *s, goto fail; fd->defined_arg_count = 1; } else { - if (js_parse_expect(s, '(')) - goto fail; + if (s->token.val == '(') { + int skip_bits; + /* if there is an '=' inside the parameter list, we + consider there is a parameter expression inside */ + js_parse_skip_parens_token(s, &skip_bits, FALSE); + if (skip_bits & SKIP_HAS_ASSIGNMENT) + fd->has_parameter_expressions = TRUE; + if (next_token(s)) + goto fail; + } else { + if (js_parse_expect(s, '(')) + goto fail; + } + if (fd->has_parameter_expressions) { + fd->scope_level = -1; /* force no parent scope */ + if (push_scope(s) < 0) + return -1; + } + while (s->token.val != ')') { JSAtom name; BOOL rest = FALSE; - int idx; + int idx, has_initializer; if (s->token.val == TOK_ELLIPSIS) { fd->has_simple_parameter_list = FALSE; @@ -32817,8 +33026,13 @@ static __exception int js_parse_function_decl2(JSParseState *s, emit_op(s, OP_get_arg); emit_u16(s, idx); } - if (js_parse_destructuring_element(s, TOK_VAR, 1, TRUE, -1, TRUE)) + has_initializer = js_parse_destructuring_element(s, fd->has_parameter_expressions ? TOK_LET : TOK_VAR, 1, TRUE, -1, TRUE); + if (has_initializer < 0) goto fail; + if (has_initializer) + has_opt_arg = TRUE; + if (!has_opt_arg) + fd->defined_arg_count++; } else if (s->token.val == TOK_IDENT) { if (s->token.u.ident.is_reserved) { js_parse_error_reserved_identifier(s); @@ -32829,6 +33043,11 @@ static __exception int js_parse_function_decl2(JSParseState *s, js_parse_error_reserved_identifier(s); goto fail; } + if (fd->has_parameter_expressions) { + if (define_var(s, fd, name, JS_VAR_DEF_LET) < 0) + goto fail; + } + /* XXX: could avoid allocating an argument if rest is true */ idx = add_arg(ctx, fd, name); if (idx < 0) goto fail; @@ -32837,70 +33056,55 @@ static __exception int js_parse_function_decl2(JSParseState *s, if (rest) { emit_op(s, OP_rest); emit_u16(s, idx); + if (fd->has_parameter_expressions) { + emit_op(s, OP_dup); + emit_op(s, OP_scope_put_var_init); + emit_atom(s, name); + emit_u16(s, fd->scope_level); + } emit_op(s, OP_put_arg); emit_u16(s, idx); fd->has_simple_parameter_list = FALSE; has_opt_arg = TRUE; } else if (s->token.val == '=') { + int label; + fd->has_simple_parameter_list = FALSE; has_opt_arg = TRUE; if (next_token(s)) goto fail; - /* optimize `x = void 0` default value: no code needed */ - if (s->token.val == TOK_VOID) { - JSParsePos pos; - js_parse_get_pos(s, &pos); - if (next_token(s)) - goto fail; - if (s->token.val == TOK_NUMBER) { - if (next_token(s)) - goto fail; - if (s->token.val == ',') { - if (next_token(s)) - goto fail; - continue; - } - if (s->token.val == ')') { - continue; - } - } - if (js_parse_seek_token(s, &pos)) - goto fail; + label = new_label(s); + emit_op(s, OP_get_arg); + emit_u16(s, idx); + emit_op(s, OP_dup); + emit_op(s, OP_undefined); + emit_op(s, OP_strict_eq); + emit_goto(s, OP_if_false, label); + emit_op(s, OP_drop); + if (js_parse_assign_expr(s)) + goto fail; + set_object_name(s, name); + emit_op(s, OP_dup); + emit_op(s, OP_put_arg); + emit_u16(s, idx); + emit_label(s, label); + emit_op(s, OP_scope_put_var_init); + emit_atom(s, name); + emit_u16(s, fd->scope_level); + } else { + if (!has_opt_arg) { + fd->defined_arg_count++; } -#if 0 - /* XXX: not correct for eval code */ - /* Check for a default value of `undefined` - to omit default argument processing */ - if (s->token.val == TOK_IDENT && - s->token.u.ident.atom == JS_ATOM_undefined && - fd->parent == NULL && - ((tok = peek_token(s, FALSE)) == ',' || tok == ')')) { - if (next_token(s)) /* ignore undefined token */ - goto fail; - } else -#endif - { - int label = new_label(s); - if (idx > 0) { - emit_op(s, OP_set_arg_valid_upto); - emit_u16(s, idx); - } + if (fd->has_parameter_expressions) { + /* copy the argument to the argument scope */ emit_op(s, OP_get_arg); emit_u16(s, idx); - emit_op(s, OP_undefined); - emit_op(s, OP_strict_eq); - emit_goto(s, OP_if_false, label); - if (js_parse_assign_expr(s, TRUE)) - goto fail; - set_object_name(s, name); - emit_op(s, OP_put_arg); - emit_u16(s, idx); - emit_label(s, label); + emit_op(s, OP_scope_put_var_init); + emit_atom(s, name); + emit_u16(s, fd->scope_level); } - } else if (!has_opt_arg) { - fd->defined_arg_count++; } } else { js_parse_error(s, "missing formal parameter"); @@ -32922,6 +33126,41 @@ static __exception int js_parse_function_decl2(JSParseState *s, } } + if (fd->has_parameter_expressions) { + int idx; + + /* Copy the variables in the argument scope to the variable + scope (see FunctionDeclarationInstantiation() in spec). The + normal arguments are already present, so no need to copy + them. */ + idx = fd->scopes[fd->scope_level].first; + while (idx >= 0) { + JSVarDef *vd = &fd->vars[idx]; + if (vd->scope_level != fd->scope_level) + break; + if (find_var(ctx, fd, vd->var_name) < 0) { + if (add_var(ctx, fd, vd->var_name) < 0) + goto fail; + vd = &fd->vars[idx]; /* fd->vars may have been reallocated */ + emit_op(s, OP_scope_get_var); + emit_atom(s, vd->var_name); + emit_u16(s, fd->scope_level); + emit_op(s, OP_scope_put_var); + emit_atom(s, vd->var_name); + emit_u16(s, 0); + } + idx = vd->scope_next; + } + + /* the argument scope has no parent, hence we don't use pop_scope(s) */ + emit_op(s, OP_leave_scope); + emit_u16(s, fd->scope_level); + + /* set the variable scope as the current scope */ + fd->scope_level = 0; + fd->scope_first = fd->scopes[fd->scope_level].first; + } + if (next_token(s)) goto fail; @@ -32933,7 +33172,8 @@ static __exception int js_parse_function_decl2(JSParseState *s, /* in generators, yield expression is forbidden during the parsing of the arguments */ fd->in_function_body = TRUE; - push_scope(s); /* enter body scope: fd->scope_level = 1 */ + push_scope(s); /* enter body scope */ + fd->body_scope = fd->scope_level; if (s->token.val == TOK_ARROW) { if (next_token(s)) @@ -32943,7 +33183,7 @@ static __exception int js_parse_function_decl2(JSParseState *s, if (js_parse_function_check_names(s, fd, func_name)) goto fail; - if (js_parse_assign_expr(s, TRUE)) + if (js_parse_assign_expr(s)) goto fail; if (func_kind != JS_FUNC_NORMAL) @@ -33025,10 +33265,10 @@ done: emit_u32(s, idx); if (create_func_var) { if (s->cur_func->is_global_var) { - JSHoistedDef *hf; + JSGlobalVar *hf; /* the global variable must be defined at the start of the function */ - hf = add_hoisted_def(ctx, s->cur_func, -1, func_name, -1, FALSE); + hf = add_global_var(ctx, s->cur_func, func_name); if (!hf) goto fail; /* it is considered as defined at the top level @@ -33058,7 +33298,7 @@ done: } if (lexical_func_idx >= 0) { /* lexical variable will be initialized upon entering scope */ - s->cur_func->vars[lexical_func_idx].func_pool_or_scope_idx = idx; + s->cur_func->vars[lexical_func_idx].func_pool_idx = idx; emit_op(s, OP_drop); } else { /* store function object into its lexical name */ @@ -33074,17 +33314,23 @@ done: if (var_idx < 0) goto fail; /* the variable will be assigned at the top of the function */ - if (!add_hoisted_def(ctx, s->cur_func, idx, JS_ATOM_NULL, var_idx, FALSE)) - goto fail; + if (var_idx & ARGUMENT_VAR_OFFSET) { + s->cur_func->args[var_idx - ARGUMENT_VAR_OFFSET].func_pool_idx = idx; + } else { + s->cur_func->vars[var_idx].func_pool_idx = idx; + } } else { JSAtom func_var_name; + JSGlobalVar *hf; if (func_name == JS_ATOM_NULL) func_var_name = JS_ATOM__default_; /* export default */ else func_var_name = func_name; /* the variable will be assigned at the top of the function */ - if (!add_hoisted_def(ctx, s->cur_func, idx, func_var_name, -1, FALSE)) + hf = add_global_var(ctx, s->cur_func, func_var_name); + if (!hf) goto fail; + hf->cpool_idx = idx; if (export_flag != JS_PARSE_EXPORT_NONE) { if (!add_export_entry(s, s->cur_func->module, func_var_name, export_flag == JS_PARSE_EXPORT_NAMED ? func_var_name : JS_ATOM_default, JS_EXPORT_TYPE_LOCAL)) @@ -33186,7 +33432,7 @@ static JSValue JS_EvalFunctionInternal(JSContext *ctx, JSValue fun_obj, JS_FreeValue(ctx, fun_obj); if (js_create_module_function(ctx, m) < 0) goto fail; - if (js_instantiate_module(ctx, m) < 0) + if (js_link_module(ctx, m) < 0) goto fail; ret_val = js_evaluate_module(ctx, m); if (JS_IsException(ret_val)) { @@ -33308,7 +33554,8 @@ static JSValue __JS_EvalInternal(JSContext *ctx, JSValueConst this_obj, s->allow_html_comments = !s->is_module; push_scope(s); /* body scope */ - + fd->body_scope = fd->scope_level; + err = js_parse_program(s); if (err) { fail: @@ -33371,19 +33618,27 @@ static JSValue JS_EvalObject(JSContext *ctx, JSValueConst this_obj, } -JSValue JS_Eval(JSContext *ctx, const char *input, size_t input_len, - const char *filename, int eval_flags) +JSValue JS_EvalThis(JSContext *ctx, JSValueConst this_obj, + const char *input, size_t input_len, + const char *filename, int eval_flags) { int eval_type = eval_flags & JS_EVAL_TYPE_MASK; JSValue ret; assert(eval_type == JS_EVAL_TYPE_GLOBAL || eval_type == JS_EVAL_TYPE_MODULE); - ret = JS_EvalInternal(ctx, ctx->global_obj, input, input_len, filename, + ret = JS_EvalInternal(ctx, this_obj, input, input_len, filename, eval_flags, -1); return ret; } +JSValue JS_Eval(JSContext *ctx, const char *input, size_t input_len, + const char *filename, int eval_flags) +{ + return JS_EvalThis(ctx, ctx->global_obj, input, input_len, filename, + eval_flags); +} + int JS_ResolveModule(JSContext *ctx, JSValueConst obj) { if (JS_VALUE_GET_TAG(obj) == JS_TAG_MODULE) { @@ -33980,7 +34235,6 @@ static int JS_WriteFunctionTag(BCWriterState *s, JSValueConst obj) bc_put_leb128(s, vd->scope_next + 1); flags = idx = 0; bc_set_flags(&flags, &idx, vd->var_kind, 4); - bc_set_flags(&flags, &idx, vd->is_func_var, 1); bc_set_flags(&flags, &idx, vd->is_const, 1); bc_set_flags(&flags, &idx, vd->is_lexical, 1); bc_set_flags(&flags, &idx, vd->is_captured, 1); @@ -34971,7 +35225,6 @@ static JSValue JS_ReadFunctionTag(BCReaderState *s) goto fail; idx = 0; vd->var_kind = bc_get_flags(v8, &idx, 4); - vd->is_func_var = bc_get_flags(v8, &idx, 1); vd->is_const = bc_get_flags(v8, &idx, 1); vd->is_lexical = bc_get_flags(v8, &idx, 1); vd->is_captured = bc_get_flags(v8, &idx, 1); @@ -35628,16 +35881,39 @@ static JSAtom find_atom(JSContext *ctx, const char *name) return atom; } -static int JS_InstantiateFunctionListItem(JSContext *ctx, JSObject *p, - JSAtom atom, void *opaque) +static JSValue JS_InstantiateFunctionListItem2(JSContext *ctx, JSObject *p, + JSAtom atom, void *opaque) { const JSCFunctionListEntry *e = opaque; - JSValueConst obj = JS_MKPTR(JS_TAG_OBJECT, p); + JSValue val; + + switch(e->def_type) { + case JS_DEF_CFUNC: + val = JS_NewCFunction2(ctx, e->u.func.cfunc.generic, + e->name, e->u.func.length, e->u.func.cproto, e->magic); + break; + case JS_DEF_PROP_STRING: + val = JS_NewAtomString(ctx, e->u.str); + break; + case JS_DEF_OBJECT: + val = JS_NewObject(ctx); + JS_SetPropertyFunctionList(ctx, val, e->u.prop_list.tab, e->u.prop_list.len); + break; + default: + abort(); + } + return val; +} + +static int JS_InstantiateFunctionListItem(JSContext *ctx, JSValueConst obj, + JSAtom atom, + const JSCFunctionListEntry *e) +{ JSValue val; int prop_flags = e->prop_flags; switch(e->def_type) { - case JS_DEF_ALIAS: + case JS_DEF_ALIAS: /* using autoinit for aliases is not safe */ { JSAtom atom1 = find_atom(ctx, e->u.alias.name); switch (e->u.alias.base) { @@ -35654,12 +35930,16 @@ static int JS_InstantiateFunctionListItem(JSContext *ctx, JSObject *p, abort(); } JS_FreeAtom(ctx, atom1); - goto setval; + if (atom == JS_ATOM_Symbol_toPrimitive) { + /* Symbol.toPrimitive functions are not writable */ + prop_flags = JS_PROP_CONFIGURABLE; + } else if (atom == JS_ATOM_Symbol_hasInstance) { + /* Function.prototype[Symbol.hasInstance] is not writable nor configurable */ + prop_flags = 0; + } } + break; case JS_DEF_CFUNC: - val = JS_NewCFunction2(ctx, e->u.func.cfunc.generic, - e->name, e->u.func.length, e->u.func.cproto, e->magic); - setval: if (atom == JS_ATOM_Symbol_toPrimitive) { /* Symbol.toPrimitive functions are not writable */ prop_flags = JS_PROP_CONFIGURABLE; @@ -35667,8 +35947,10 @@ static int JS_InstantiateFunctionListItem(JSContext *ctx, JSObject *p, /* Function.prototype[Symbol.hasInstance] is not writable nor configurable */ prop_flags = 0; } - break; - case JS_DEF_CGETSET: + JS_DefineAutoInitProperty(ctx, obj, atom, JS_AUTOINIT_ID_PROP, + (void *)e, prop_flags); + return 0; + case JS_DEF_CGETSET: /* XXX: use autoinit again ? */ case JS_DEF_CGETSET_MAGIC: { JSValue getter, setter; @@ -35692,9 +35974,6 @@ static int JS_InstantiateFunctionListItem(JSContext *ctx, JSObject *p, return 0; } break; - case JS_DEF_PROP_STRING: - val = JS_NewAtomString(ctx, e->u.str); - break; case JS_DEF_PROP_INT32: val = JS_NewInt32(ctx, e->u.i32); break; @@ -35707,10 +35986,11 @@ static int JS_InstantiateFunctionListItem(JSContext *ctx, JSObject *p, case JS_DEF_PROP_UNDEFINED: val = JS_UNDEFINED; break; + case JS_DEF_PROP_STRING: case JS_DEF_OBJECT: - val = JS_NewObject(ctx); - JS_SetPropertyFunctionList(ctx, val, e->u.prop_list.tab, e->u.prop_list.len); - break; + JS_DefineAutoInitProperty(ctx, obj, atom, JS_AUTOINIT_ID_PROP, + (void *)e, prop_flags); + return 0; default: abort(); } @@ -35721,36 +36001,12 @@ static int JS_InstantiateFunctionListItem(JSContext *ctx, JSObject *p, void JS_SetPropertyFunctionList(JSContext *ctx, JSValueConst obj, const JSCFunctionListEntry *tab, int len) { - int i, prop_flags; + int i; for (i = 0; i < len; i++) { const JSCFunctionListEntry *e = &tab[i]; JSAtom atom = find_atom(ctx, e->name); - - switch (e->def_type) { - case JS_DEF_CFUNC: - case JS_DEF_CGETSET: - case JS_DEF_CGETSET_MAGIC: - case JS_DEF_PROP_STRING: - case JS_DEF_ALIAS: - case JS_DEF_OBJECT: - prop_flags = JS_PROP_WRITABLE | JS_PROP_CONFIGURABLE | (e->prop_flags & JS_PROP_ENUMERABLE); - JS_DefineAutoInitProperty(ctx, obj, atom, - JS_AUTOINIT_ID_PROP, - (void *)e, prop_flags); - break; - case JS_DEF_PROP_INT32: - case JS_DEF_PROP_INT64: - case JS_DEF_PROP_DOUBLE: - case JS_DEF_PROP_UNDEFINED: - { - JSObject *p = JS_VALUE_GET_OBJ(obj); - JS_InstantiateFunctionListItem(ctx, p, atom, (void *)e); - } - break; - default: - abort(); - } + JS_InstantiateFunctionListItem(ctx, obj, atom, e); JS_FreeAtom(ctx, atom); } } @@ -37262,6 +37518,8 @@ static JSValue *build_arg_list(JSContext *ctx, uint32_t *plen, return tab; } +/* magic value: 0 = normal apply, 1 = apply for constructor, 2 = + Reflect.apply */ static JSValue js_function_apply(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv, int magic) { @@ -37273,14 +37531,14 @@ static JSValue js_function_apply(JSContext *ctx, JSValueConst this_val, return JS_EXCEPTION; this_arg = argv[0]; array_arg = argv[1]; - if (JS_VALUE_GET_TAG(array_arg) == JS_TAG_UNDEFINED || - JS_VALUE_GET_TAG(array_arg) == JS_TAG_NULL) { + if ((JS_VALUE_GET_TAG(array_arg) == JS_TAG_UNDEFINED || + JS_VALUE_GET_TAG(array_arg) == JS_TAG_NULL) && magic != 2) { return JS_Call(ctx, this_val, this_arg, 0, NULL); } tab = build_arg_list(ctx, &len, array_arg); if (!tab) return JS_EXCEPTION; - if (magic) { + if (magic & 1) { ret = JS_CallConstructor2(ctx, this_val, this_arg, len, (JSValueConst *)tab); } else { ret = JS_Call(ctx, this_val, this_arg, len, (JSValueConst *)tab); @@ -37650,7 +37908,7 @@ static JSValue js_array_constructor(JSContext *ctx, JSValueConst new_target, return obj; if (argc == 1 && JS_IsNumber(argv[0])) { uint32_t len; - if (JS_ToArrayLengthFree(ctx, &len, JS_DupValue(ctx, argv[0]))) + if (JS_ToArrayLengthFree(ctx, &len, JS_DupValue(ctx, argv[0]), TRUE)) goto fail; if (JS_SetProperty(ctx, obj, JS_ATOM_length, JS_NewUint32(ctx, len)) < 0) goto fail; @@ -39659,46 +39917,6 @@ static int js_string_get_own_property(JSContext *ctx, return FALSE; } -static uint32_t js_string_obj_get_length(JSContext *ctx, - JSValueConst obj) -{ - JSObject *p; - JSString *p1; - uint32_t len = 0; - - /* This is a class exotic method: obj class_id is JS_CLASS_STRING */ - p = JS_VALUE_GET_OBJ(obj); - if (JS_VALUE_GET_TAG(p->u.object_data) == JS_TAG_STRING) { - p1 = JS_VALUE_GET_STRING(p->u.object_data); - len = p1->len; - } - return len; -} - -static int js_string_get_own_property_names(JSContext *ctx, - JSPropertyEnum **ptab, - uint32_t *plen, - JSValueConst obj) -{ - JSPropertyEnum *tab; - uint32_t len, i; - - len = js_string_obj_get_length(ctx, obj); - tab = NULL; - if (len > 0) { - /* do not allocate 0 bytes */ - tab = js_malloc(ctx, sizeof(JSPropertyEnum) * len); - if (!tab) - return -1; - for(i = 0; i < len; i++) { - tab[i].atom = __JS_AtomFromUInt32(i); - } - } - *ptab = tab; - *plen = len; - return 0; -} - static int js_string_define_own_property(JSContext *ctx, JSValueConst this_obj, JSAtom prop, JSValueConst val, @@ -39755,7 +39973,6 @@ static int js_string_delete_property(JSContext *ctx, static const JSClassExoticMethods js_string_exotic_methods = { .get_own_property = js_string_get_own_property, - .get_own_property_names = js_string_get_own_property_names, .define_own_property = js_string_define_own_property, .delete_property = js_string_delete_property, }; @@ -40359,15 +40576,17 @@ static JSValue js_string___GetSubstitution(JSContext *ctx, JSValueConst this_val string_buffer_concat(b, sp, position + matched_len, sp->len); } else if (c >= '0' && c <= '9') { k = c - '0'; - c1 = string_get(rp, j); - if (c1 >= '0' && c1 <= '9') { - /* This behavior is specified in ES6 and refined in ECMA 2019 */ - /* ECMA 2019 does not have the extra test, but - Test262 S15.5.4.11_A3_T1..3 require this behavior */ - k1 = k * 10 + c1 - '0'; - if (k1 >= 1 && k1 < captures_len) { - k = k1; - j++; + if (j < len) { + c1 = string_get(rp, j); + if (c1 >= '0' && c1 <= '9') { + /* This behavior is specified in ES6 and refined in ECMA 2019 */ + /* ECMA 2019 does not have the extra test, but + Test262 S15.5.4.11_A3_T1..3 require this behavior */ + k1 = k * 10 + c1 - '0'; + if (k1 >= 1 && k1 < captures_len) { + k = k1; + j++; + } } } if (k >= 1 && k < captures_len) { @@ -42805,7 +43024,8 @@ static JSValue js_regexp_Symbol_replace(JSContext *ctx, JSValueConst this_val, tab = JS_NewArray(ctx); if (JS_IsException(tab)) goto exception; - if (JS_SetPropertyInt64(ctx, tab, 0, JS_DupValue(ctx, matched)) < 0) + if (JS_DefinePropertyValueInt64(ctx, tab, 0, JS_DupValue(ctx, matched), + JS_PROP_C_W_E | JS_PROP_THROW) < 0) goto exception; for(n = 1; n < nCaptures; n++) { JSValue capN; @@ -42817,7 +43037,8 @@ static JSValue js_regexp_Symbol_replace(JSContext *ctx, JSValueConst this_val, if (JS_IsException(capN)) goto exception; } - if (JS_SetPropertyInt64(ctx, tab, n, capN) < 0) + if (JS_DefinePropertyValueInt64(ctx, tab, n, capN, + JS_PROP_C_W_E | JS_PROP_THROW) < 0) goto exception; } JS_FreeValue(ctx, namedCaptures); @@ -42825,12 +43046,12 @@ static JSValue js_regexp_Symbol_replace(JSContext *ctx, JSValueConst this_val, if (JS_IsException(namedCaptures)) goto exception; if (functionalReplace) { - if (JS_SetPropertyInt64(ctx, tab, n++, JS_NewInt32(ctx, position)) < 0) + if (JS_DefinePropertyValueInt64(ctx, tab, n++, JS_NewInt32(ctx, position), JS_PROP_C_W_E | JS_PROP_THROW) < 0) goto exception; - if (JS_SetPropertyInt64(ctx, tab, n++, JS_DupValue(ctx, str)) < 0) + if (JS_DefinePropertyValueInt64(ctx, tab, n++, JS_DupValue(ctx, str), JS_PROP_C_W_E | JS_PROP_THROW) < 0) goto exception; if (!JS_IsUndefined(namedCaptures)) { - if (JS_SetPropertyInt64(ctx, tab, n++, JS_DupValue(ctx, namedCaptures)) < 0) + if (JS_DefinePropertyValueInt64(ctx, tab, n++, JS_DupValue(ctx, namedCaptures), JS_PROP_C_W_E | JS_PROP_THROW) < 0) goto exception; } args[0] = JS_UNDEFINED; @@ -42917,8 +43138,10 @@ static JSValue js_regexp_Symbol_search(JSContext *ctx, JSValueConst this_val, if (js_same_value(ctx, currentLastIndex, previousLastIndex)) { JS_FreeValue(ctx, previousLastIndex); } else { - if (JS_SetProperty(ctx, rx, JS_ATOM_lastIndex, previousLastIndex) < 0) + if (JS_SetProperty(ctx, rx, JS_ATOM_lastIndex, previousLastIndex) < 0) { + previousLastIndex = JS_UNDEFINED; goto exception; + } } JS_FreeValue(ctx, str); JS_FreeValue(ctx, currentLastIndex); @@ -43023,7 +43246,8 @@ static JSValue js_regexp_Symbol_split(JSContext *ctx, JSValueConst this_val, sub = js_sub_string(ctx, strp, p, q); if (JS_IsException(sub)) goto exception; - if (JS_SetPropertyInt64(ctx, A, lengthA++, sub) < 0) + if (JS_DefinePropertyValueInt64(ctx, A, lengthA++, sub, + JS_PROP_C_W_E | JS_PROP_THROW) < 0) goto exception; if (lengthA == lim) goto done; @@ -43034,7 +43258,7 @@ static JSValue js_regexp_Symbol_split(JSContext *ctx, JSValueConst this_val, sub = JS_ToStringFree(ctx, JS_GetPropertyInt64(ctx, z, i)); if (JS_IsException(sub)) goto exception; - if (JS_SetPropertyInt64(ctx, A, lengthA++, sub) < 0) + if (JS_DefinePropertyValueInt64(ctx, A, lengthA++, sub, JS_PROP_C_W_E | JS_PROP_THROW) < 0) goto exception; if (lengthA == lim) goto done; @@ -43049,7 +43273,7 @@ add_tail: sub = js_sub_string(ctx, strp, p, size); if (JS_IsException(sub)) goto exception; - if (JS_SetPropertyInt64(ctx, A, lengthA++, sub) < 0) + if (JS_DefinePropertyValueInt64(ctx, A, lengthA++, sub, JS_PROP_C_W_E | JS_PROP_THROW) < 0) goto exception; goto done; exception: @@ -43829,7 +44053,7 @@ void JS_AddIntrinsicJSON(JSContext *ctx) static JSValue js_reflect_apply(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv) { - return js_function_apply(ctx, argv[0], max_int(0, argc - 1), argv + 1, 0); + return js_function_apply(ctx, argv[0], max_int(0, argc - 1), argv + 1, 2); } static JSValue js_reflect_construct(JSContext *ctx, JSValueConst this_val, @@ -46772,26 +46996,15 @@ static JSValue js_promise_then_finally_func(JSContext *ctx, JSValueConst this_va { JSValueConst ctor = func_data[0]; JSValueConst onFinally = func_data[1]; - JSValue res, promise, resolving_funcs[2], ret, then_func; + JSValue res, promise, ret, then_func; res = JS_Call(ctx, onFinally, JS_UNDEFINED, 0, NULL); if (JS_IsException(res)) return res; - promise = js_new_promise_capability(ctx, resolving_funcs, ctor); - if (JS_IsException(promise)) { - JS_FreeValue(ctx, res); - return JS_EXCEPTION; - } - ret = JS_Call(ctx, resolving_funcs[0], JS_UNDEFINED, - 1, (JSValueConst*)&res); + promise = js_promise_resolve(ctx, ctor, 1, (JSValueConst *)&res, 0); JS_FreeValue(ctx, res); - JS_FreeValue(ctx, resolving_funcs[0]); - JS_FreeValue(ctx, resolving_funcs[1]); - if (JS_IsException(ret)) { - JS_FreeValue(ctx, promise); - return ret; - } - JS_FreeValue(ctx, ret); + if (JS_IsException(promise)) + return promise; if (magic == 0) { then_func = JS_NewCFunctionData(ctx, js_promise_finally_value_thunk, 0, 0, 1, argv); @@ -47503,7 +47716,7 @@ static JSValue JS_SetThisTimeValue(JSContext *ctx, JSValueConst this_val, double JSObject *p = JS_VALUE_GET_OBJ(this_val); if (p->class_id == JS_CLASS_DATE) { JS_FreeValue(ctx, p->u.object_data); - p->u.object_data = __JS_NewFloat64(ctx, v); + p->u.object_data = JS_NewFloat64(ctx, v); return JS_DupValue(ctx, p->u.object_data); } } @@ -47547,7 +47760,7 @@ static char const month_names[] = "JanFebMarAprMayJunJulAugSepOctNovDec"; static char const day_names[] = "SunMonTueWedThuFriSat"; static __exception int get_date_fields(JSContext *ctx, JSValueConst obj, - int64_t fields[9], int is_local, int force) + double fields[9], int is_local, int force) { double dval; int64_t d, days, wd, y, i, md, h, m, s, ms, tz = 0; @@ -47606,12 +47819,18 @@ static double time_clip(double t) { return NAN; } -static double set_date_fields(int64_t fields[], int is_local) { - int64_t days, y, m, md, h, d, i; - - i = fields[1]; - m = math_mod(i, 12); - y = fields[0] + (i - m) / 12; +/* The spec mandates the use of 'double' and it fixes the order + of the operations */ +static double set_date_fields(double fields[], int is_local) { + int64_t y; + double days, d, h, m1; + int i, m, md; + + m1 = fields[1]; + m = fmod(m1, 12); + if (m < 0) + m += 12; + y = (int64_t)(fields[0] + floor(m1 / 12)); days = days_from_year(y); for(i = 0; i < m; i++) { @@ -47621,7 +47840,8 @@ static double set_date_fields(int64_t fields[], int is_local) { days += md; } days += fields[2] - 1; - h = ((fields[3] * 60 + fields[4]) * 60 + fields[5]) * 1000 + fields[6]; + h = fields[3] * 3600000 + fields[4] * 60000 + + fields[5] * 1000 + fields[6]; d = days * 86400000 + h; if (is_local) d += getTimezoneOffset(d) * 60000; @@ -47632,7 +47852,7 @@ static JSValue get_date_field(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv, int magic) { // get_date_field(obj, n, is_local) - int64_t fields[9]; + double fields[9]; int res, n, is_local; is_local = magic & 0x0F; @@ -47646,14 +47866,14 @@ static JSValue get_date_field(JSContext *ctx, JSValueConst this_val, if (magic & 0x100) { // getYear fields[0] -= 1900; } - return JS_NewInt64(ctx, fields[n]); + return JS_NewFloat64(ctx, fields[n]); } static JSValue set_date_field(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv, int magic) { // _field(obj, first_field, end_field, args, is_local) - int64_t fields[9]; + double fields[9]; int res, first_field, end_field, is_local, i, n; double d, a; @@ -47695,7 +47915,7 @@ static JSValue get_date_string(JSContext *ctx, JSValueConst this_val, { // _string(obj, fmt, part) char buf[64]; - int64_t fields[9]; + double fields[9]; int res, fmt, part, pos; int y, mon, d, h, m, s, ms, wd, tz; @@ -47843,7 +48063,7 @@ static JSValue js_date_constructor(JSContext *ctx, JSValueConst new_target, } val = time_clip(val); } else { - int64_t fields[] = { 0, 0, 1, 0, 0, 0, 0 }; + double fields[] = { 0, 0, 1, 0, 0, 0, 0 }; if (n > 7) n = 7; for(i = 0; i < n; i++) { @@ -47862,12 +48082,12 @@ has_val: JSValueConst args[3]; args[0] = new_target; args[1] = ctx->class_proto[JS_CLASS_DATE]; - args[2] = __JS_NewFloat64(ctx, val); + args[2] = JS_NewFloat64(ctx, val); rv = js___date_create(ctx, JS_UNDEFINED, 3, args); #else rv = js_create_from_ctor(ctx, new_target, JS_CLASS_DATE); if (!JS_IsException(rv)) - JS_SetObjectData(ctx, rv, __JS_NewFloat64(ctx, val)); + JS_SetObjectData(ctx, rv, JS_NewFloat64(ctx, val)); #endif if (!JS_IsException(rv) && JS_IsUndefined(new_target)) { /* invoked as a function, return (new Date()).toString(); */ @@ -47883,7 +48103,7 @@ static JSValue js_Date_UTC(JSContext *ctx, JSValueConst this_val, int argc, JSValueConst *argv) { // UTC(y, mon, d, h, m, s, ms) - int64_t fields[] = { 0, 0, 1, 0, 0, 0, 0 }; + double fields[] = { 0, 0, 1, 0, 0, 0, 0 }; int i, n; double a; @@ -47901,7 +48121,7 @@ static JSValue js_Date_UTC(JSContext *ctx, JSValueConst this_val, if (i == 0 && fields[0] >= 0 && fields[0] < 100) fields[0] += 1900; } - return __JS_NewFloat64(ctx, set_date_fields(fields, 0)); + return JS_NewFloat64(ctx, set_date_fields(fields, 0)); } static void string_skip_spaces(JSString *sp, int *pp) { @@ -48011,6 +48231,7 @@ static JSValue js_Date_parse(JSContext *ctx, JSValueConst this_val, // parse(s) JSValue s, rv; int64_t fields[] = { 0, 1, 1, 0, 0, 0, 0 }; + double fields1[7]; int64_t tz, hh, mm; double d; int p, i, c, sgn; @@ -48123,8 +48344,10 @@ static JSValue js_Date_parse(JSContext *ctx, JSValueConst this_val, } } } - d = set_date_fields(fields, is_local) - tz * 60000; - rv = __JS_NewFloat64(ctx, d); + for(i = 0; i < 7; i++) + fields1[i] = fields[i]; + d = set_date_fields(fields1, is_local) - tz * 60000; + rv = JS_NewFloat64(ctx, d); done: JS_FreeValue(ctx, s); @@ -48194,7 +48417,7 @@ static JSValue js_date_getTime(JSContext *ctx, JSValueConst this_val, if (JS_ThisTimeValue(ctx, &v, this_val)) return JS_EXCEPTION; - return __JS_NewFloat64(ctx, v); + return JS_NewFloat64(ctx, v); } static JSValue js_date_setTime(JSContext *ctx, JSValueConst this_val, @@ -48223,7 +48446,7 @@ static JSValue js_date_setYear(JSContext *ctx, JSValueConst this_val, if (y >= 0 && y < 100) y += 1900; } - args[0] = __JS_NewFloat64(ctx, y); + args[0] = JS_NewFloat64(ctx, y); return set_date_field(ctx, this_val, 1, args, 0x011); } @@ -48714,9 +48937,11 @@ static JSValue JS_ToBigIntCtorFree(JSContext *ctx, JSValue val) } static JSValue js_bigint_constructor(JSContext *ctx, - JSValueConst this_val, + JSValueConst new_target, int argc, JSValueConst *argv) { + if (!JS_IsUndefined(new_target)) + return JS_ThrowTypeError(ctx, "not a constructor"); return JS_ToBigIntCtorFree(ctx, JS_DupValue(ctx, argv[0])); } @@ -48962,7 +49187,7 @@ static const JSCFunctionListEntry js_bigint_proto_funcs[] = { void JS_AddIntrinsicBigInt(JSContext *ctx) { JSRuntime *rt = ctx->rt; - JSValue obj1; + JSValueConst obj1; rt->bigint_ops.to_string = js_bigint_to_string; rt->bigint_ops.from_string = js_string_to_bigint; @@ -48974,9 +49199,8 @@ void JS_AddIntrinsicBigInt(JSContext *ctx) JS_SetPropertyFunctionList(ctx, ctx->class_proto[JS_CLASS_BIG_INT], js_bigint_proto_funcs, countof(js_bigint_proto_funcs)); - obj1 = JS_NewCFunction(ctx, js_bigint_constructor, "BigInt", 1); - JS_NewGlobalCConstructor2(ctx, obj1, "BigInt", - ctx->class_proto[JS_CLASS_BIG_INT]); + obj1 = JS_NewGlobalCConstructor(ctx, "BigInt", js_bigint_constructor, 1, + ctx->class_proto[JS_CLASS_BIG_INT]); JS_SetPropertyFunctionList(ctx, obj1, js_bigint_funcs, countof(js_bigint_funcs)); } @@ -49194,10 +49418,12 @@ static const JSCFunctionListEntry js_bigfloat_proto_funcs[] = { }; static JSValue js_bigfloat_constructor(JSContext *ctx, - JSValueConst this_val, + JSValueConst new_target, int argc, JSValueConst *argv) { JSValue val; + if (!JS_IsUndefined(new_target)) + return JS_ThrowTypeError(ctx, "not a constructor"); if (argc == 0) { bf_t *r; val = JS_NewBigFloat(ctx); @@ -49858,8 +50084,7 @@ static const JSCFunctionListEntry js_float_env_proto_funcs[] = { void JS_AddIntrinsicBigFloat(JSContext *ctx) { JSRuntime *rt = ctx->rt; - JSValue obj1; - JSValueConst obj2; + JSValueConst obj1; rt->bigfloat_ops.to_string = js_bigfloat_to_string; rt->bigfloat_ops.from_string = js_string_to_bigfloat; @@ -49873,9 +50098,8 @@ void JS_AddIntrinsicBigFloat(JSContext *ctx) JS_SetPropertyFunctionList(ctx, ctx->class_proto[JS_CLASS_BIG_FLOAT], js_bigfloat_proto_funcs, countof(js_bigfloat_proto_funcs)); - obj1 = JS_NewCFunction(ctx, js_bigfloat_constructor, "BigFloat", 1); - JS_NewGlobalCConstructor2(ctx, obj1, "BigFloat", - ctx->class_proto[JS_CLASS_BIG_FLOAT]); + obj1 = JS_NewGlobalCConstructor(ctx, "BigFloat", js_bigfloat_constructor, 1, + ctx->class_proto[JS_CLASS_BIG_FLOAT]); JS_SetPropertyFunctionList(ctx, obj1, js_bigfloat_funcs, countof(js_bigfloat_funcs)); @@ -49883,10 +50107,10 @@ void JS_AddIntrinsicBigFloat(JSContext *ctx) JS_SetPropertyFunctionList(ctx, ctx->class_proto[JS_CLASS_FLOAT_ENV], js_float_env_proto_funcs, countof(js_float_env_proto_funcs)); - obj2 = JS_NewGlobalCConstructorOnly(ctx, "BigFloatEnv", + obj1 = JS_NewGlobalCConstructorOnly(ctx, "BigFloatEnv", js_float_env_constructor, 1, ctx->class_proto[JS_CLASS_FLOAT_ENV]); - JS_SetPropertyFunctionList(ctx, obj2, js_float_env_funcs, + JS_SetPropertyFunctionList(ctx, obj1, js_float_env_funcs, countof(js_float_env_funcs)); } @@ -49989,10 +50213,12 @@ static JSValue JS_ToBigDecimalFree(JSContext *ctx, JSValue val, } static JSValue js_bigdecimal_constructor(JSContext *ctx, - JSValueConst this_val, + JSValueConst new_target, int argc, JSValueConst *argv) { JSValue val; + if (!JS_IsUndefined(new_target)) + return JS_ThrowTypeError(ctx, "not a constructor"); if (argc == 0) { bfdec_t *r; val = JS_NewBigDecimal(ctx); @@ -50348,7 +50574,7 @@ static const JSCFunctionListEntry js_bigdecimal_funcs[] = { void JS_AddIntrinsicBigDecimal(JSContext *ctx) { JSRuntime *rt = ctx->rt; - JSValue obj1; + JSValueConst obj1; rt->bigdecimal_ops.to_string = js_bigdecimal_to_string; rt->bigdecimal_ops.from_string = js_string_to_bigdecimal; @@ -50360,9 +50586,9 @@ void JS_AddIntrinsicBigDecimal(JSContext *ctx) JS_SetPropertyFunctionList(ctx, ctx->class_proto[JS_CLASS_BIG_DECIMAL], js_bigdecimal_proto_funcs, countof(js_bigdecimal_proto_funcs)); - obj1 = JS_NewCFunction(ctx, js_bigdecimal_constructor, "BigDecimal", 1); - JS_NewGlobalCConstructor2(ctx, obj1, "BigDecimal", - ctx->class_proto[JS_CLASS_BIG_DECIMAL]); + obj1 = JS_NewGlobalCConstructor(ctx, "BigDecimal", + js_bigdecimal_constructor, 1, + ctx->class_proto[JS_CLASS_BIG_DECIMAL]); JS_SetPropertyFunctionList(ctx, obj1, js_bigdecimal_funcs, countof(js_bigdecimal_funcs)); } @@ -50818,8 +51044,7 @@ static JSValue js_array_buffer_get_byteLength(JSContext *ctx, JSArrayBuffer *abuf = JS_GetOpaque2(ctx, this_val, class_id); if (!abuf) return JS_EXCEPTION; - if (abuf->detached) - return JS_ThrowTypeErrorDetachedArrayBuffer(ctx); + /* return 0 if detached */ return JS_NewUint32(ctx, abuf->byte_length); } diff --git a/quickjs.h b/quickjs.h index bb84829..92457a2 100644 --- a/quickjs.h +++ b/quickjs.h @@ -776,7 +776,10 @@ JS_BOOL JS_DetectModule(const char *input, size_t input_len); /* 'input' must be zero terminated i.e. input[input_len] = '\0'. */ JSValue JS_Eval(JSContext *ctx, const char *input, size_t input_len, const char *filename, int eval_flags); -JSValue JS_EvalFunction(JSContext *ctx, JSValue fun_obj); +/* same as JS_Eval() but with an explicit 'this_obj' parameter */ +JSValue JS_EvalThis(JSContext *ctx, JSValueConst this_obj, + const char *input, size_t input_len, + const char *filename, int eval_flags); JSValue JS_GetGlobalObject(JSContext *ctx); int JS_IsInstanceOf(JSContext *ctx, JSValueConst val, JSValueConst obj); int JS_DefineProperty(JSContext *ctx, JSValueConst this_obj, @@ -885,7 +888,9 @@ uint8_t *JS_WriteObject2(JSContext *ctx, size_t *psize, JSValueConst obj, #define JS_READ_OBJ_REFERENCE (1 << 3) /* allow object references */ JSValue JS_ReadObject(JSContext *ctx, const uint8_t *buf, size_t buf_len, int flags); - +/* instantiate and evaluate a bytecode function. Only used when + reading a script or module with JS_ReadObject() */ +JSValue JS_EvalFunction(JSContext *ctx, JSValue fun_obj); /* load the dependencies of the module 'obj'. Useful when JS_ReadObject() returns a module. */ int JS_ResolveModule(JSContext *ctx, JSValueConst obj); diff --git a/release.sh b/release.sh index a0bd6eb..6dc89fb 100755 --- a/release.sh +++ b/release.sh @@ -6,30 +6,23 @@ set -e version=`cat VERSION` if [ "$1" = "-h" ] ; then - echo "release.sh [all]" + echo "release.sh [release_list]" echo "" - echo "all: build all the archives. Otherwise only build the quickjs source archive." + echo "release_list: extras binary win_binary quickjs" + exit 1 fi -extras="no" -binary="no" -quickjs="no" +release_list="extras binary win_binary quickjs" -if [ "$1" = "all" ] ; then - extras="yes" - binary="yes" - quickjs="yes" -elif [ "$1" = "binary" ] ; then - binary="yes" -else - quickjs="yes" +if [ "$1" != "" ] ; then + release_list="$1" fi #################################################" # extras -if [ "$extras" = "yes" ] ; then +if echo $release_list | grep -w -q extras ; then d="quickjs-${version}" name="quickjs-extras-${version}" @@ -46,10 +39,58 @@ cp -a tests/bench-v8 $outdir/tests fi #################################################" -# binary release +# Windows binary release -if [ "$binary" = "yes" ] ; then +if echo $release_list | grep -w -q win_binary ; then +# win64 + +dlldir=/usr/x86_64-w64-mingw32/sys-root/mingw/bin +cross_prefix="x86_64-w64-mingw32-" +d="quickjs-win-x86_64-${version}" +outdir="/tmp/${d}" + +rm -rf $outdir +mkdir -p $outdir + +make CONFIG_WIN32=y qjs.exe +cp qjs.exe $outdir +${cross_prefix}strip $outdir/qjs.exe +cp $dlldir/libwinpthread-1.dll $outdir + +( cd /tmp/$d && rm -f ../${d}.zip && zip -r ../${d}.zip . ) + +make CONFIG_WIN32=y clean + +# win32 + +dlldir=/usr/i686-w64-mingw32/sys-root/mingw/bin +cross_prefix="i686-w64-mingw32-" +d="quickjs-win-i686-${version}" +outdir="/tmp/${d}" + +rm -rf $outdir +mkdir -p $outdir + +make clean +make CONFIG_WIN32=y clean + +make CONFIG_WIN32=y CONFIG_M32=y qjs.exe +cp qjs.exe $outdir +${cross_prefix}strip $outdir/qjs.exe +cp $dlldir/libwinpthread-1.dll $outdir + +( cd /tmp/$d && rm -f ../${d}.zip && zip -r ../${d}.zip . ) + +fi + +#################################################" +# Linux binary release + +if echo $release_list | grep -w -q binary ; then + +make clean +make CONFIG_WIN32=y clean make -j4 qjs run-test262 make -j4 CONFIG_M32=y qjs32 run-test262-32 strip qjs run-test262 qjs32 run-test262-32 @@ -80,7 +121,7 @@ fi #################################################" # quickjs -if [ "$quickjs" = "yes" ] ; then +if echo $release_list | grep -w -q quickjs ; then make build_doc @@ -98,7 +139,7 @@ cp Makefile VERSION TODO Changelog readme.txt release.sh unicode_download.sh \ libregexp.c libregexp.h libregexp-opcode.h \ libunicode.c libunicode.h libunicode-table.h \ libbf.c libbf.h \ - jscompress.c unicode_gen.c unicode_gen_def.h \ + unicode_gen.c unicode_gen_def.h \ run-test262.c test262o.conf test262.conf \ test262o_errors.txt test262_errors.txt \ $outdir diff --git a/test262.conf b/test262.conf index e1eeb03..f30a4ac 100644 --- a/test262.conf +++ b/test262.conf @@ -49,9 +49,12 @@ testdir=test262/test # skipped features are tagged as such to avoid warnings AggregateError +align-detached-buffer-semantics-with-web-reality +arbitrary-module-namespace-names=skip Array.prototype.flat Array.prototype.flatMap Array.prototype.flatten +Array.prototype.item=skip Array.prototype.values ArrayBuffer arrow-function @@ -82,7 +85,6 @@ DataView.prototype.getInt8 DataView.prototype.getUint16 DataView.prototype.getUint32 DataView.prototype.setUint8 -default-arg default-parameters destructuring-assignment destructuring-binding @@ -90,6 +92,7 @@ dynamic-import export-star-as-namespace-from-module FinalizationGroup=skip FinalizationRegistry=skip +FinalizationRegistry.prototype.cleanupSome=skip Float32Array Float64Array for-in-order @@ -99,10 +102,12 @@ globalThis hashbang host-gc-required=skip import.meta +Int16Array Int32Array Int8Array IsHTMLDDA json-superset +legacy-regexp=skip let logical-assignment-operators Map @@ -114,6 +119,7 @@ Object.fromEntries Object.is optional-catch-binding optional-chaining +Promise Promise.allSettled Promise.any Promise.prototype.finally @@ -135,6 +141,7 @@ string-trimming String.fromCodePoint String.prototype.endsWith String.prototype.includes +String.prototype.item=skip String.prototype.matchAll String.prototype.replaceAll String.prototype.trimEnd @@ -159,14 +166,19 @@ tail-call-optimization=skip template top-level-await=skip TypedArray +TypedArray.prototype.item=skip u180e Uint16Array +Uint32Array Uint8Array Uint8ClampedArray WeakMap WeakRef=skip WeakSet well-formed-json-stringify +__getter__ +__proto__ +__setter__ [exclude] # list excluded tests and directories here @@ -183,8 +195,5 @@ test262/test/built-ins/ThrowTypeError/unique-per-realm-function-proto.js #test262/test/built-ins/RegExp/CharacterClassEscapes/ #test262/test/built-ins/RegExp/property-escapes/ -# invalid tests -test262/test/language/module-code/verify-dfs.js - [tests] # list test files or use config.testdir diff --git a/test262_errors.txt b/test262_errors.txt index d00d4f1..502a650 100644 --- a/test262_errors.txt +++ b/test262_errors.txt @@ -1,30 +1,51 @@ test262/test/built-ins/Function/internals/Construct/derived-this-uninitialized-realm.js:20: Test262Error: Expected a ReferenceError but got a ReferenceError test262/test/built-ins/Function/internals/Construct/derived-this-uninitialized-realm.js:20: strict mode: Test262Error: Expected a ReferenceError but got a ReferenceError -test262/test/built-ins/Proxy/ownKeys/trap-is-undefined-target-is-proxy.js:29: Test262Error: Expected [0, length, foo, Symbol()] and [Symbol(), length, foo, 0] to have the same contents. -test262/test/built-ins/Proxy/ownKeys/trap-is-undefined-target-is-proxy.js:29: strict mode: Test262Error: Expected [0, length, foo, Symbol()] and [Symbol(), length, foo, 0] to have the same contents. test262/test/built-ins/RegExp/named-groups/non-unicode-property-names-valid.js:46: SyntaxError: invalid group name test262/test/built-ins/RegExp/named-groups/non-unicode-property-names-valid.js:46: strict mode: SyntaxError: invalid group name -test262/test/language/expressions/arrow-function/eval-var-scope-syntax-err.js:47: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all -test262/test/language/expressions/async-arrow-function/eval-var-scope-syntax-err.js:49: TypeError: $DONE() not called -test262/test/language/expressions/async-function/named-eval-var-scope-syntax-err.js:33: TypeError: $DONE() not called -test262/test/language/expressions/async-function/nameless-eval-var-scope-syntax-err.js:33: TypeError: $DONE() not called -test262/test/language/expressions/async-generator/eval-var-scope-syntax-err.js:28: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all -test262/test/language/expressions/async-generator/named-eval-var-scope-syntax-err.js:28: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all -test262/test/language/expressions/class/elements/grammar-private-field-optional-chaining.js:26: SyntaxError: expecting field name -test262/test/language/expressions/class/elements/grammar-private-field-optional-chaining.js:26: strict mode: SyntaxError: expecting field name +test262/test/built-ins/TypedArray/prototype/every/BigInt/callbackfn-detachbuffer.js:28: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/every/BigInt/callbackfn-detachbuffer.js:28: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/every/callbackfn-detachbuffer.js:28: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/every/callbackfn-detachbuffer.js:28: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/filter/BigInt/callbackfn-detachbuffer.js:20: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/filter/BigInt/callbackfn-detachbuffer.js:20: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/filter/callbackfn-detachbuffer.js:20: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/filter/callbackfn-detachbuffer.js:20: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/findIndex/BigInt/predicate-may-detach-buffer.js:36: Test262Error: throws a TypeError getting a value from the detached buffer Expected a TypeError to be thrown but no exception was thrown at all (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/findIndex/BigInt/predicate-may-detach-buffer.js:36: strict mode: Test262Error: throws a TypeError getting a value from the detached buffer Expected a TypeError to be thrown but no exception was thrown at all (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/forEach/BigInt/callbackfn-detachbuffer.js:28: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/forEach/BigInt/callbackfn-detachbuffer.js:28: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/forEach/callbackfn-detachbuffer.js:28: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/forEach/callbackfn-detachbuffer.js:28: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/map/BigInt/callbackfn-detachbuffer.js:20: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/map/BigInt/callbackfn-detachbuffer.js:20: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/map/callbackfn-detachbuffer.js:20: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/map/callbackfn-detachbuffer.js:20: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/reduce/BigInt/callbackfn-detachbuffer.js:29: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/reduce/BigInt/callbackfn-detachbuffer.js:29: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/reduce/callbackfn-detachbuffer.js:29: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/reduce/callbackfn-detachbuffer.js:29: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/reduceRight/BigInt/callbackfn-detachbuffer.js:29: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/reduceRight/BigInt/callbackfn-detachbuffer.js:29: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/reduceRight/callbackfn-detachbuffer.js:29: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/reduceRight/callbackfn-detachbuffer.js:29: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/some/BigInt/callbackfn-detachbuffer.js:28: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/some/BigInt/callbackfn-detachbuffer.js:28: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArray/prototype/some/callbackfn-detachbuffer.js:28: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArray/prototype/some/callbackfn-detachbuffer.js:28: strict mode: Test262Error: Expected SameValue(«1», «2») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/DefineOwnProperty/BigInt/detached-buffer.js:37: Test262Error: (Testing with BigInt64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/DefineOwnProperty/BigInt/detached-buffer.js:37: strict mode: Test262Error: (Testing with BigInt64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/DefineOwnProperty/detached-buffer.js:38: Test262Error: (Testing with Float64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/DefineOwnProperty/detached-buffer.js:38: strict mode: Test262Error: (Testing with Float64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/GetOwnProperty/BigInt/index-prop-desc.js:21: Test262Error: Expected SameValue(«43», «42») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/GetOwnProperty/BigInt/index-prop-desc.js:21: strict mode: Test262Error: Expected SameValue(«43», «42») to be true (Testing with BigInt64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/GetOwnProperty/index-prop-desc.js:22: Test262Error: Expected SameValue(«43», «42») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/GetOwnProperty/index-prop-desc.js:22: strict mode: Test262Error: Expected SameValue(«43», «42») to be true (Testing with Float64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/Set/BigInt/detached-buffer-realm.js:36: strict mode: TypeError: out-of-bound numeric index (Testing with BigInt64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/Set/BigInt/detached-buffer.js:34: TypeError: cannot convert bigint to number (Testing with BigInt64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/Set/BigInt/detached-buffer.js:32: strict mode: TypeError: out-of-bound numeric index (Testing with BigInt64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/Set/detached-buffer-realm.js:36: strict mode: TypeError: out-of-bound numeric index (Testing with Float64Array.) +test262/test/built-ins/TypedArrayConstructors/internals/Set/detached-buffer.js:32: strict mode: TypeError: out-of-bound numeric index (Testing with Float64Array.) test262/test/language/expressions/dynamic-import/usage-from-eval.js:26: TypeError: $DONE() not called test262/test/language/expressions/dynamic-import/usage-from-eval.js:26: strict mode: TypeError: $DONE() not called -test262/test/language/expressions/function/eval-var-scope-syntax-err.js:48: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all -test262/test/language/expressions/generators/eval-var-scope-syntax-err.js:49: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all -test262/test/language/expressions/object/method-definition/async-gen-meth-eval-var-scope-syntax-err.js:32: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all -test262/test/language/expressions/object/method-definition/async-meth-eval-var-scope-syntax-err.js:36: TypeError: $DONE() not called -test262/test/language/expressions/object/method-definition/gen-meth-eval-var-scope-syntax-err.js:54: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all -test262/test/language/expressions/object/method-definition/meth-eval-var-scope-syntax-err.js:50: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all test262/test/language/expressions/optional-chaining/optional-call-preserves-this.js:21: TypeError: cannot read property 'c' of undefined test262/test/language/expressions/optional-chaining/optional-call-preserves-this.js:15: strict mode: TypeError: cannot read property '_b' of undefined -test262/test/language/statements/async-function/eval-var-scope-syntax-err.js:33: TypeError: $DONE() not called -test262/test/language/statements/async-generator/eval-var-scope-syntax-err.js:28: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all -test262/test/language/statements/class/elements/grammar-private-field-optional-chaining.js:26: SyntaxError: expecting field name -test262/test/language/statements/class/elements/grammar-private-field-optional-chaining.js:26: strict mode: SyntaxError: expecting field name -test262/test/language/statements/function/eval-var-scope-syntax-err.js:49: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all -test262/test/language/statements/generators/eval-var-scope-syntax-err.js:49: Test262Error: Expected a SyntaxError to be thrown but no exception was thrown at all diff --git a/tests/test_builtin.js b/tests/test_builtin.js index 5650c52..c044b2c 100644 --- a/tests/test_builtin.js +++ b/tests/test_builtin.js @@ -17,6 +17,22 @@ function assert(actual, expected, message) { (message ? " (" + message + ")" : "")); } +function assert_throws(expected_error, func) +{ + var err = false; + try { + func(); + } catch(e) { + err = true; + if (!(e instanceof expected_error)) { + throw Error("unexpected exception type"); + } + } + if (!err) { + throw Error("expected exception"); + } +} + // load more elaborate version of assert if available try { __loadScript("test_assert.js"); } catch(e) {} @@ -39,7 +55,7 @@ function test_function() function constructor1(a) { this.x = a; } - + var r, g; r = my_func.call(null, 1, 2); @@ -48,6 +64,13 @@ function test_function() r = my_func.apply(null, [1, 2]); assert(r, 3, "apply"); + r = (function () { return 1; }).apply(null, undefined); + assert(r, 1); + + assert_throws(TypeError, (function() { + Reflect.apply((function () { return 1; }), null, undefined); + })); + r = new Function("a", "b", "return a + b;"); assert(r(2,3), 5, "function"); diff --git a/tests/test_language.js b/tests/test_language.js index 6b08467..8d13deb 100644 --- a/tests/test_language.js +++ b/tests/test_language.js @@ -15,6 +15,22 @@ function assert(actual, expected, message) { (message ? " (" + message + ")" : "")); } +function assert_throws(expected_error, func) +{ + var err = false; + try { + func(); + } catch(e) { + err = true; + if (!(e instanceof expected_error)) { + throw Error("unexpected exception type"); + } + } + if (!err) { + throw Error("expected exception"); + } +} + // load more elaborate version of assert if available try { __loadScript("test_assert.js"); } catch(e) {} @@ -233,8 +249,13 @@ function test_delete() function test_prototype() { - function f() { } + var f = function f() { }; assert(f.prototype.constructor, f, "prototype"); + + var g = function g() { }; + /* QuickJS bug */ + Object.defineProperty(g, "prototype", { writable: false }); + assert(g.prototype.constructor, g, "prototype"); } function test_arguments() @@ -376,6 +397,135 @@ function test_spread() assert(Object.getOwnPropertyNames(x).toString(), "0,length"); } +function test_function_length() +{ + assert( ((a, b = 1, c) => {}).length, 1); + assert( (([a,b]) => {}).length, 1); + assert( (({a,b}) => {}).length, 1); + assert( ((c, [a,b] = 1, d) => {}).length, 1); +} + +function test_argument_scope() +{ + var f; + var c = "global"; + + f = function(a = eval("var arguments")) {}; + assert_throws(SyntaxError, f); + + f = function(a = eval("1"), b = arguments[0]) { return b; }; + assert(f(12), 12); + + f = function(a, b = arguments[0]) { return b; }; + assert(f(12), 12); + + f = function(a, b = () => arguments) { return b; }; + assert(f(12)()[0], 12); + + f = function(a = eval("1"), b = () => arguments) { return b; }; + assert(f(12)()[0], 12); + + (function() { + "use strict"; + f = function(a = this) { return a; }; + assert(f.call(123), 123); + + f = function f(a = f) { return a; }; + assert(f(), f); + + f = function f(a = eval("f")) { return a; }; + assert(f(), f); + })(); + + f = (a = eval("var c = 1"), probe = () => c) => { + var c = 2; + assert(c, 2); + assert(probe(), 1); + } + f(); + + f = (a = eval("var arguments = 1"), probe = () => arguments) => { + var arguments = 2; + assert(arguments, 2); + assert(probe(), 1); + } + f(); + + f = function f(a = eval("var c = 1"), b = c, probe = () => c) { + assert(b, 1); + assert(c, 1); + assert(probe(), 1) + } + f(); + + assert(c, "global"); + f = function f(a, b = c, probe = () => c) { + eval("var c = 1"); + assert(c, 1); + assert(b, "global"); + assert(probe(), "global") + } + f(); + assert(c, "global"); + + f = function f(a = eval("var c = 1"), probe = (d = eval("c")) => d) { + assert(probe(), 1) + } + f(); +} + +function test_function_expr_name() +{ + var f; + + /* non strict mode test : assignment to the function name silently + fails */ + + f = function myfunc() { + myfunc = 1; + return myfunc; + }; + assert(f(), f); + + f = function myfunc() { + myfunc = 1; + (() => { + myfunc = 1; + })(); + return myfunc; + }; + assert(f(), f); + + f = function myfunc() { + eval("myfunc = 1"); + return myfunc; + }; + assert(f(), f); + + /* strict mode test : assignment to the function name raises a + TypeError exception */ + + f = function myfunc() { + "use strict"; + myfunc = 1; + }; + assert_throws(TypeError, f); + + f = function myfunc() { + "use strict"; + (() => { + myfunc = 1; + })(); + }; + assert_throws(TypeError, f); + + f = function myfunc() { + "use strict"; + eval("myfunc = 1"); + }; + assert_throws(TypeError, f); +} + test_op1(); test_cvt(); test_eq(); @@ -392,3 +542,6 @@ test_regexp_skip(); test_labels(); test_destructuring(); test_spread(); +test_function_length(); +test_argument_scope(); +test_function_expr_name();