browser/extensions/shumway/content/shumway.js

Thu, 22 Jan 2015 13:21:57 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Thu, 22 Jan 2015 13:21:57 +0100
branch
TOR_BUG_9701
changeset 15
b8a032363ba2
permissions
-rw-r--r--

Incorporate requested changes from Mozilla in review:
https://bugzilla.mozilla.org/show_bug.cgi?id=1123480#c6

     1 /*
     2  * Copyright 2013 Mozilla Foundation
     3  *
     4  * Licensed under the Apache License, Version 2.0 (the "License");
     5  * you may not use this file except in compliance with the License.
     6  * You may obtain a copy of the License at
     7  *
     8  *     http://www.apache.org/licenses/LICENSE-2.0
     9  *
    10  * Unless required by applicable law or agreed to in writing, software
    11  * distributed under the License is distributed on an "AS IS" BASIS,
    12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    13  * See the License for the specific language governing permissions and
    14  * limitations under the License.
    15  */
    17 // This file is automatically generated
    19 (function (global) {
    20   if (global.DataView)
    21     return;
    22   if (!global.ArrayBuffer)
    23     fail('ArrayBuffer not supported');
    24   if (!Object.defineProperties)
    25     fail('This module requires ECMAScript 5');
    26   var nativele = new Int8Array(new Int32Array([
    27       1
    28     ]).buffer)[0] === 1;
    29   var temp = new Uint8Array(8);
    30   global.DataView = function DataView(buffer, offset, length) {
    31     if (!(buffer instanceof ArrayBuffer))
    32       fail('Bad ArrayBuffer');
    33     offset = offset || 0;
    34     length = length || buffer.byteLength - offset;
    35     if (offset < 0 || length < 0 || offset + length > buffer.byteLength)
    36       fail('Illegal offset and/or length');
    37     Object.defineProperties(this, {
    38       buffer: {
    39         value: buffer,
    40         enumerable: false,
    41         writable: false,
    42         configurable: false
    43       },
    44       byteOffset: {
    45         value: offset,
    46         enumerable: false,
    47         writable: false,
    48         configurable: false
    49       },
    50       byteLength: {
    51         value: length,
    52         enumerable: false,
    53         writable: false,
    54         configurable: false
    55       },
    56       _bytes: {
    57         value: new Uint8Array(buffer, offset, length),
    58         enumerable: false,
    59         writable: false,
    60         configurable: false
    61       }
    62     });
    63   };
    64   global.DataView.prototype = {
    65     constructor: DataView,
    66     getInt8: function getInt8(offset) {
    67       return get(this, Int8Array, 1, offset);
    68     },
    69     getUint8: function getUint8(offset) {
    70       return get(this, Uint8Array, 1, offset);
    71     },
    72     getInt16: function getInt16(offset, le) {
    73       return get(this, Int16Array, 2, offset, le);
    74     },
    75     getUint16: function getUint16(offset, le) {
    76       return get(this, Uint16Array, 2, offset, le);
    77     },
    78     getInt32: function getInt32(offset, le) {
    79       return get(this, Int32Array, 4, offset, le);
    80     },
    81     getUint32: function getUint32(offset, le) {
    82       return get(this, Uint32Array, 4, offset, le);
    83     },
    84     getFloat32: function getFloat32(offset, le) {
    85       return get(this, Float32Array, 4, offset, le);
    86     },
    87     getFloat64: function getFloat32(offset, le) {
    88       return get(this, Float64Array, 8, offset, le);
    89     },
    90     setInt8: function setInt8(offset, value) {
    91       set(this, Int8Array, 1, offset, value);
    92     },
    93     setUint8: function setUint8(offset, value) {
    94       set(this, Uint8Array, 1, offset, value);
    95     },
    96     setInt16: function setInt16(offset, value, le) {
    97       set(this, Int16Array, 2, offset, value, le);
    98     },
    99     setUint16: function setUint16(offset, value, le) {
   100       set(this, Uint16Array, 2, offset, value, le);
   101     },
   102     setInt32: function setInt32(offset, value, le) {
   103       set(this, Int32Array, 4, offset, value, le);
   104     },
   105     setUint32: function setUint32(offset, value, le) {
   106       set(this, Uint32Array, 4, offset, value, le);
   107     },
   108     setFloat32: function setFloat32(offset, value, le) {
   109       set(this, Float32Array, 4, offset, value, le);
   110     },
   111     setFloat64: function setFloat64(offset, value, le) {
   112       set(this, Float64Array, 8, offset, value, le);
   113     }
   114   };
   115   function get(view, type, size, offset, le) {
   116     if (offset === undefined)
   117       fail('Missing required offset argument');
   118     if (offset < 0 || offset + size > view.byteLength)
   119       fail('Invalid index: ' + offset);
   120     if (size === 1 || !(!le) === nativele) {
   121       if ((view.byteOffset + offset) % size === 0)
   122         return new type(view.buffer, view.byteOffset + offset, 1)[0];
   123       else {
   124         for (var i = 0; i < size; i++)
   125           temp[i] = view._bytes[offset + i];
   126         return new type(temp.buffer)[0];
   127       }
   128     } else {
   129       for (var i = 0; i < size; i++)
   130         temp[size - i - 1] = view._bytes[offset + i];
   131       return new type(temp.buffer)[0];
   132     }
   133   }
   134   function set(view, type, size, offset, value, le) {
   135     if (offset === undefined)
   136       fail('Missing required offset argument');
   137     if (value === undefined)
   138       fail('Missing required value argument');
   139     if (offset < 0 || offset + size > view.byteLength)
   140       fail('Invalid index: ' + offset);
   141     if (size === 1 || !(!le) === nativele) {
   142       if ((view.byteOffset + offset) % size === 0) {
   143         new type(view.buffer, view.byteOffset + offset, 1)[0] = value;
   144       } else {
   145         new type(temp.buffer)[0] = value;
   146         for (var i = 0; i < size; i++)
   147           view._bytes[i + offset] = temp[i];
   148       }
   149     } else {
   150       new type(temp.buffer)[0] = value;
   151       for (var i = 0; i < size; i++)
   152         view._bytes[offset + i] = temp[size - 1 - i];
   153     }
   154   }
   155   function fail(msg) {
   156     throw new Error(msg);
   157   }
   158 }(this));
   159 ;
   160 var ByteArray = ByteArray || function (undefined) {
   161     ByteArrayClass.INITIAL_SIZE = 128;
   162     ByteArrayClass.DEFAULT_OBJECT_ENCODING = 3;
   163     function ByteArrayClass(bytes) {
   164       if (bytes instanceof ByteArray) {
   165         return bytes;
   166       }
   167       var initData = bytes || this.symbol && this.symbol.data;
   168       if (initData) {
   169         this.a = new ArrayBuffer(initData.length);
   170         this.length = initData.length;
   171         new Uint8Array(this.a).set(initData);
   172       } else {
   173         this.a = new ArrayBuffer(ByteArrayClass.INITIAL_SIZE);
   174         this.length = 0;
   175       }
   176       this.position = 0;
   177       this.cacheViews();
   178       this.nativele = new Int8Array(new Int32Array([]).buffer)[0] === 1;
   179       this.le = this.nativele;
   180       this.objectEncoding = ByteArrayClass.DEFAULT_OBJECT_ENCODING;
   181       this.bitBuffer = 0;
   182       this.bitLength = 0;
   183     }
   184     ;
   185     function throwEOFError() {
   186       runtime.throwErrorFromVM('flash.errors.EOFError', 'End of file was encountered.');
   187     }
   188     function throwRangeError() {
   189       var error = Errors.ParamRangeError;
   190       runtime.throwErrorFromVM('RangeError', getErrorMessage(error.code), error.code);
   191     }
   192     function throwCompressedDataError() {
   193       var error = Errors.CompressedDataError;
   194       runtime.throwErrorFromVM('CompressedDataError', getErrorMessage(error.code), error.code);
   195     }
   196     function checkRange(x, min, max) {
   197       if (x !== clamp(x, min, max)) {
   198         throwRangeError();
   199       }
   200     }
   201     function get(b, m, size) {
   202       if (b.position + size > b.length) {
   203         throwEOFError();
   204       }
   205       var v = b.view[m](b.position, b.le);
   206       b.position += size;
   207       return v;
   208     }
   209     function set(b, m, size, v) {
   210       var len = b.position + size;
   211       b.ensureCapacity(len);
   212       b.view[m](b.position, v, b.le);
   213       b.position = len;
   214       if (len > b.length) {
   215         b.length = len;
   216       }
   217     }
   218     var BAp = ByteArrayClass.prototype;
   219     BAp.cacheViews = function cacheViews() {
   220       var a = this.a;
   221       this.int8v = new Int8Array(a);
   222       this.uint8v = new Uint8Array(a);
   223       this.view = new DataView(a);
   224     };
   225     BAp.getBytes = function getBytes() {
   226       return new Uint8Array(this.a, 0, this.length);
   227     };
   228     BAp.ensureCapacity = function ensureCapacity(size) {
   229       var origa = this.a;
   230       if (origa.byteLength < size) {
   231         var newSize = origa.byteLength;
   232         while (newSize < size) {
   233           newSize *= 2;
   234         }
   235         var copya = new ArrayBuffer(newSize);
   236         var origv = this.int8v;
   237         this.a = copya;
   238         this.cacheViews();
   239         this.int8v.set(origv);
   240       }
   241     };
   242     BAp.clear = function clear() {
   243       this.length = 0;
   244       this.position = 0;
   245     };
   246     BAp.readBoolean = function readBoolean() {
   247       if (this.position + 1 > this.length) {
   248         throwEOFError();
   249       }
   250       return this.int8v[this.position++] !== 0;
   251     };
   252     BAp.readByte = function readByte() {
   253       if (this.position + 1 > this.length) {
   254         throwEOFError();
   255       }
   256       return this.int8v[this.position++];
   257     };
   258     BAp.readUnsignedByte = function readUnsignedByte() {
   259       if (this.position + 1 > this.length) {
   260         throwEOFError();
   261       }
   262       return this.uint8v[this.position++];
   263     };
   264     BAp.readBytes = function readBytes(bytes, offset, length) {
   265       var pos = this.position;
   266       if (!offset) {
   267         offset = 0;
   268       }
   269       if (!length) {
   270         length = this.length - pos;
   271       }
   272       if (pos + length > this.length) {
   273         throwEOFError();
   274       }
   275       if (bytes.length < offset + length) {
   276         bytes.ensureCapacity(offset + length);
   277         bytes.length = offset + length;
   278       }
   279       bytes.int8v.set(new Int8Array(this.a, pos, length), offset);
   280       this.position += length;
   281     };
   282     BAp.writeBoolean = function writeBoolean(v) {
   283       var len = this.position + 1;
   284       this.ensureCapacity(len);
   285       this.int8v[this.position++] = v ? 1 : 0;
   286       if (len > this.length) {
   287         this.length = len;
   288       }
   289     };
   290     BAp.writeByte = function writeByte(v) {
   291       var len = this.position + 1;
   292       this.ensureCapacity(len);
   293       this.int8v[this.position++] = v;
   294       if (len > this.length) {
   295         this.length = len;
   296       }
   297     };
   298     BAp.writeUnsignedByte = function writeUnsignedByte(v) {
   299       var len = this.position + 1;
   300       this.ensureCapacity(len);
   301       this.uint8v[this.position++] = v;
   302       if (len > this.length) {
   303         this.length = len;
   304       }
   305     };
   306     BAp.writeRawBytes = function writeRawBytes(bytes) {
   307       var len = this.position + bytes.length;
   308       this.ensureCapacity(len);
   309       this.int8v.set(bytes, this.position);
   310       this.position = len;
   311       if (len > this.length) {
   312         this.length = len;
   313       }
   314     };
   315     BAp.readRawBytes = function readRawBytes() {
   316       return new Int8Array(this.a, 0, this.length);
   317     };
   318     BAp.writeBytes = function writeBytes(bytes, offset, length) {
   319       if (arguments.length < 2) {
   320         offset = 0;
   321       }
   322       if (arguments.length < 3) {
   323         length = 0;
   324       }
   325       checkRange(offset, 0, bytes.length);
   326       checkRange(offset + length, 0, bytes.length);
   327       if (length === 0) {
   328         length = bytes.length - offset;
   329       }
   330       this.writeRawBytes(new Int8Array(bytes.a, offset, length));
   331     };
   332     BAp.readDouble = function readDouble() {
   333       return get(this, 'getFloat64', 8);
   334     };
   335     BAp.readFloat = function readFloat() {
   336       return get(this, 'getFloat32', 4);
   337     };
   338     BAp.readInt = function readInt() {
   339       return get(this, 'getInt32', 4);
   340     };
   341     BAp.readShort = function readShort() {
   342       return get(this, 'getInt16', 2);
   343     };
   344     BAp.readUnsignedInt = function readUnsignedInt() {
   345       return get(this, 'getUint32', 4);
   346     };
   347     BAp.readUnsignedShort = function readUnsignedShort() {
   348       return get(this, 'getUint16', 2);
   349     };
   350     BAp.writeDouble = function writeDouble(v) {
   351       set(this, 'setFloat64', 8, v);
   352     };
   353     BAp.writeFloat = function writeFloat(v) {
   354       set(this, 'setFloat32', 4, v);
   355     };
   356     BAp.writeInt = function writeInt(v) {
   357       set(this, 'setInt32', 4, v);
   358     };
   359     BAp.writeShort = function writeShort(v) {
   360       set(this, 'setInt16', 2, v);
   361     };
   362     BAp.writeUnsignedInt = function writeUnsignedInt(v) {
   363       set(this, 'setUint32', 4, v);
   364     };
   365     BAp.writeUnsignedShort = function writeUnsignedShort(v) {
   366       set(this, 'setUint16', 2, v);
   367     };
   368     var codeLengthOrder = [
   369         16,
   370         17,
   371         18,
   372         0,
   373         8,
   374         7,
   375         9,
   376         6,
   377         10,
   378         5,
   379         11,
   380         4,
   381         12,
   382         3,
   383         13,
   384         2,
   385         14,
   386         1,
   387         15
   388       ];
   389     var distanceCodes = [];
   390     var distanceExtraBits = [];
   391     for (var i = 0, j = 0, code = 1; i < 30; ++i) {
   392       distanceCodes[i] = code;
   393       code += 1 << (distanceExtraBits[i] = ~(~((j += i > 2 ? 1 : 0) / 2)));
   394     }
   395     var bitLengths = [];
   396     for (var i = 0; i < 32; ++i) {
   397       bitLengths[i] = 5;
   398     }
   399     var fixedDistanceTable = makeHuffmanTable(bitLengths);
   400     var lengthCodes = [];
   401     var lengthExtraBits = [];
   402     for (var i = 0, j = 0, code = 3; i < 29; ++i) {
   403       lengthCodes[i] = code - (i == 28 ? 1 : 0);
   404       code += 1 << (lengthExtraBits[i] = ~(~((j += i > 4 ? 1 : 0) / 4 % 6)));
   405     }
   406     for (var i = 0; i < 288; ++i) {
   407       bitLengths[i] = i < 144 || i > 279 ? 8 : i < 256 ? 9 : 7;
   408     }
   409     var fixedLiteralTable = makeHuffmanTable(bitLengths);
   410     function makeHuffmanTable(bitLengths) {
   411       var maxBits = Math.max.apply(null, bitLengths);
   412       var numLengths = bitLengths.length;
   413       var size = 1 << maxBits;
   414       var codes = new Uint32Array(size);
   415       for (var code = 0, len = 1, skip = 2; len <= maxBits; code <<= 1, ++len, skip <<= 1) {
   416         for (var val = 0; val < numLengths; ++val) {
   417           if (bitLengths[val] === len) {
   418             var lsb = 0;
   419             for (var i = 0; i < len; ++i) {
   420               lsb = lsb * 2 + (code >> i & 1);
   421             }
   422             for (var i = lsb; i < size; i += skip) {
   423               codes[i] = len << 16 | val;
   424             }
   425             ++code;
   426           }
   427         }
   428       }
   429       return {
   430         codes: codes,
   431         maxBits: maxBits
   432       };
   433     }
   434     function inflateBlock(input, output) {
   435       var header = readBits(input, 3);
   436       switch (header >> 1) {
   437       case 0:
   438         input.bitBuffer = input.bitLength = 0;
   439         var len = input.readUnsignedShort();
   440         var nlen = input.readUnsignedShort();
   441         if ((~nlen & 65535) !== len) {
   442           throwCompressedDataError();
   443         }
   444         output.writeBytes(input, input.position, len);
   445         input.position += len;
   446         break;
   447       case 1:
   448         inflate(input, output, fixedLiteralTable, fixedDistanceTable);
   449         break;
   450       case 2:
   451         var bitLengths = [];
   452         var numLiteralCodes = readBits(input, 5) + 257;
   453         var numDistanceCodes = readBits(input, 5) + 1;
   454         var numCodes = numLiteralCodes + numDistanceCodes;
   455         var numLengthCodes = readBits(input, 4) + 4;
   456         for (var i = 0; i < 19; ++i) {
   457           bitLengths[codeLengthOrder[i]] = i < numLengthCodes ? readBits(input, 3) : 0;
   458         }
   459         var codeLengthTable = makeHuffmanTable(bitLengths);
   460         bitLengths = [];
   461         var i = 0;
   462         var prev = 0;
   463         while (i < numCodes) {
   464           var j = 1;
   465           var sym = readCode(input, codeLengthTable);
   466           switch (sym) {
   467           case 16:
   468             j = readBits(input, 2) + 3;
   469             sym = prev;
   470             break;
   471           case 17:
   472             j = readBits(input, 3) + 3;
   473             sym = 0;
   474             break;
   475           case 18:
   476             j = readBits(input, 7) + 11;
   477             sym = 0;
   478             break;
   479           default:
   480             prev = sym;
   481           }
   482           while (j--) {
   483             bitLengths[i++] = sym;
   484           }
   485         }
   486         var distanceTable = makeHuffmanTable(bitLengths.splice(numLiteralCodes, numDistanceCodes));
   487         var literalTable = makeHuffmanTable(bitLengths);
   488         inflate(input, output, literalTable, distanceTable);
   489         break;
   490       default:
   491         fail('unknown block type', 'inflate');
   492       }
   493     }
   494     function readBits(input, size) {
   495       var buffer = input.bitBuffer;
   496       var bufflen = input.bitLength;
   497       while (size > bufflen) {
   498         buffer |= input.readUnsignedByte() << bufflen;
   499         bufflen += 8;
   500       }
   501       input.bitBuffer = buffer >>> size;
   502       input.bitLength = bufflen - size;
   503       return buffer & (1 << size) - 1;
   504     }
   505     function inflate(input, output, literalTable, distanceTable) {
   506       var sym;
   507       while ((sym = readCode(input, literalTable)) !== 256) {
   508         if (sym < 256) {
   509           output.writeUnsignedByte(sym);
   510         } else {
   511           sym -= 257;
   512           var len = lengthCodes[sym] + readBits(input, lengthExtraBits[sym]);
   513           sym = readCode(input, distanceTable);
   514           var distance = distanceCodes[sym] + readBits(input, distanceExtraBits[sym]);
   515           output.writeBytes(output, output.position - distance, len);
   516         }
   517       }
   518     }
   519     function readCode(input, codeTable) {
   520       var buffer = input.bitBuffer;
   521       var bitlen = input.bitLength;
   522       var maxBits = codeTable.maxBits;
   523       while (maxBits > bitlen) {
   524         buffer |= input.readUnsignedByte() << bitlen;
   525         bitlen += 8;
   526       }
   527       var code = codeTable.codes[buffer & (1 << maxBits) - 1];
   528       var len = code >> 16;
   529       if (!len) {
   530         throwCompressedDataError();
   531       }
   532       input.bitBuffer = buffer >>> len;
   533       input.bitLength = bitlen - len;
   534       return code & 65535;
   535     }
   536     function adler32(data, start, end) {
   537       var a = 1;
   538       var b = 0;
   539       for (var i = start; i < end; ++i) {
   540         a = (a + (data[i] & 255)) % 65521;
   541         b = (b + a) % 65521;
   542       }
   543       return b << 16 | a;
   544     }
   545     BAp.compress = function (algorithm) {
   546       this.position = 0;
   547       var output = new ByteArray();
   548       switch (algorithm) {
   549       case 'zlib':
   550         output.writeUnsignedByte(120);
   551         output.writeUnsignedByte(156);
   552       case 'deflate':
   553         output.le = true;
   554         var len = this.length;
   555         output.ensureCapacity(len + Math.ceil(len / 65535) * 5 + 4);
   556         while (len > 65535) {
   557           output.writeUnsignedByte(0);
   558           output.writeUnsignedShort(65535);
   559           output.writeUnsignedShort(0);
   560           output.writeBytes(this, this.position, 65535);
   561           this.position += 65535;
   562           len -= 65535;
   563         }
   564         output.writeUnsignedByte(0);
   565         output.writeUnsignedShort(len);
   566         output.writeUnsignedShort(~len & 65535);
   567         output.writeBytes(this, this.position, len);
   568         if (algorithm === 'zlib') {
   569           output.writeUnsignedInt(adler32(this.uint8v, 0, this.length));
   570         }
   571         break;
   572       default:
   573         return;
   574       }
   575       this.ensureCapacity(output.uint8v.length);
   576       this.uint8v.set(output.uint8v);
   577       this.length = output.length;
   578       this.position = 0;
   579     };
   580     BAp.uncompress = function (algorithm) {
   581       var output = new ByteArray();
   582       switch (algorithm) {
   583       case 'zlib':
   584         var header = this.readUnsignedShort();
   585         if ((header & 3840) !== 2048 || header % 31 !== 0 || header & 32) {
   586           throwCompressedDataError();
   587         }
   588       case 'deflate':
   589         var le = this.le;
   590         this.le = true;
   591         while (this.position < this.length - 6) {
   592           inflateBlock(this, output);
   593         }
   594         this.le = le;
   595         break;
   596       default:
   597         return;
   598       }
   599       this.ensureCapacity(output.uint8v.length);
   600       this.uint8v.set(output.uint8v);
   601       this.length = output.length;
   602       this.position = 0;
   603     };
   604     return ByteArrayClass;
   605   }();
   606 var Shumway;
   607 (function (Shumway) {
   608   (function (Options) {
   609     var Argument = function () {
   610         function Argument(shortName, longName, type, options) {
   611           this.shortName = shortName;
   612           this.longName = longName;
   613           this.type = type;
   614           options = options || {};
   615           this.positional = options.positional;
   616           this.parseFn = options.parse;
   617           this.value = options.defaultValue;
   618         }
   619         Argument.prototype.parse = function (value) {
   620           if (this.type === 'boolean') {
   621             true;
   622             this.value = value;
   623           } else if (this.type === 'number') {
   624             true;
   625             this.value = parseInt(value, 10);
   626           } else {
   627             this.value = value;
   628           }
   629           if (this.parseFn) {
   630             this.parseFn(this.value);
   631           }
   632         };
   633         return Argument;
   634       }();
   635     Options.Argument = Argument;
   636     var ArgumentParser = function () {
   637         function ArgumentParser() {
   638           this.args = [];
   639         }
   640         ArgumentParser.prototype.addArgument = function (shortName, longName, type, options) {
   641           var argument = new Argument(shortName, longName, type, options);
   642           this.args.push(argument);
   643           return argument;
   644         };
   645         ArgumentParser.prototype.addBoundOption = function (option) {
   646           var options = {
   647               parse: function (x) {
   648                 option.value = x;
   649               }
   650             };
   651           this.args.push(new Argument(option.shortName, option.longName, option.type, options));
   652         };
   653         ArgumentParser.prototype.addBoundOptionSet = function (optionSet) {
   654           var self = this;
   655           optionSet.options.forEach(function (x) {
   656             if (x instanceof OptionSet) {
   657               self.addBoundOptionSet(x);
   658             } else {
   659               true;
   660               self.addBoundOption(x);
   661             }
   662           });
   663         };
   664         ArgumentParser.prototype.getUsage = function () {
   665           var str = '';
   666           this.args.forEach(function (x) {
   667             if (!x.positional) {
   668               str += '[-' + x.shortName + '|--' + x.longName + (x.type === 'boolean' ? '' : ' ' + x.type[0].toUpperCase()) + ']';
   669             } else {
   670               str += x.longName;
   671             }
   672             str += ' ';
   673           });
   674           return str;
   675         };
   676         ArgumentParser.prototype.parse = function (args) {
   677           var nonPositionalArgumentMap = {};
   678           var positionalArgumentList = [];
   679           this.args.forEach(function (x) {
   680             if (x.positional) {
   681               positionalArgumentList.push(x);
   682             } else {
   683               nonPositionalArgumentMap['-' + x.shortName] = x;
   684               nonPositionalArgumentMap['--' + x.longName] = x;
   685             }
   686           });
   687           var leftoverArguments = [];
   688           while (args.length) {
   689             var argString = args.shift();
   690             var argument = null, value = argString;
   691             if (argString == '--') {
   692               leftoverArguments = leftoverArguments.concat(args);
   693               break;
   694             } else if (argString.slice(0, 1) == '-' || argString.slice(0, 2) == '--') {
   695               argument = nonPositionalArgumentMap[argString];
   696               true;
   697               if (!argument) {
   698                 continue;
   699               }
   700               if (argument.type !== 'boolean') {
   701                 value = args.shift();
   702                 true;
   703               } else {
   704                 value = true;
   705               }
   706             } else if (positionalArgumentList.length) {
   707               argument = positionalArgumentList.shift();
   708             } else {
   709               leftoverArguments.push(value);
   710             }
   711             if (argument) {
   712               argument.parse(value);
   713             }
   714           }
   715           true;
   716           return leftoverArguments;
   717         };
   718         return ArgumentParser;
   719       }();
   720     Options.ArgumentParser = ArgumentParser;
   721     var OptionSet = function () {
   722         function OptionSet(name) {
   723           this.name = name;
   724           this.options = [];
   725         }
   726         OptionSet.prototype.register = function (option) {
   727           this.options.push(option);
   728           return option;
   729         };
   730         OptionSet.prototype.trace = function (writer) {
   731           writer.enter(this.name + ' {');
   732           this.options.forEach(function (option) {
   733             option.trace(writer);
   734           });
   735           writer.leave('}');
   736         };
   737         return OptionSet;
   738       }();
   739     Options.OptionSet = OptionSet;
   740     var Option = function () {
   741         function Option(shortName, longName, type, defaultValue, description) {
   742           this.longName = longName;
   743           this.shortName = shortName;
   744           this.type = type;
   745           this.defaultValue = defaultValue;
   746           this.value = defaultValue;
   747           this.description = description;
   748         }
   749         Option.prototype.parse = function (value) {
   750           this.value = value;
   751         };
   752         Option.prototype.trace = function (writer) {
   753           writer.writeLn(('-' + this.shortName + '|--' + this.longName).padRight(' ', 30) + ' = ' + this.type + ' ' + this.value + ' [' + this.defaultValue + ']' + ' (' + this.description + ')');
   754         };
   755         return Option;
   756       }();
   757     Options.Option = Option;
   758   }(Shumway.Options || (Shumway.Options = {})));
   759   var Options = Shumway.Options;
   760 }(Shumway || (Shumway = {})));
   761 if (typeof exports !== 'undefined') {
   762   exports['Shumway'] = Shumway;
   763 }
   764 var ArgumentParser = Shumway.Options.ArgumentParser;
   765 var Option = Shumway.Options.Option;
   766 var OptionSet = Shumway.Options.OptionSet;
   767 var Option = Shumway.Options.Option;
   768 var OptionSet = Shumway.Options.OptionSet;
   769 var coreOptions = new OptionSet('Core Options');
   770 var Timeline = function () {
   771     var barColor = 'rgba(255,255,255, 0.075)';
   772     var backgroundColor = 'rgb(61, 61, 61)';
   773     var backgroundColorInfo = 'rgba(0,0,0, 0.85)';
   774     var fpsLineColor = 'rgb(255,64,0)';
   775     var textColor = '#ccc';
   776     function timeline(canvas) {
   777       this.depth = 0;
   778       this.start = 0;
   779       this.index = 0;
   780       this.marks = new Shumway.CircularBuffer(Int32Array);
   781       this.times = new Shumway.CircularBuffer(Float64Array);
   782       this.frameRate = 12;
   783       this.maxFrameTime = 1000 * 2 / this.frameRate;
   784       this.refreshFrequency = 10;
   785       this.refreshCounter = 0;
   786       this.count = 0;
   787       this.kinds = createEmptyObject();
   788       this.kindCount = 0;
   789       this.canvas = canvas;
   790       this.context = canvas.getContext('2d', {
   791         original: true
   792       });
   793       this.fillStyles = [
   794         'rgb(85, 152, 213)',
   795         '#bfd8a7',
   796         '#d906d7'
   797       ];
   798       window.addEventListener('resize', this.resizeHandler.bind(this), false);
   799       this.resizeHandler();
   800     }
   801     timeline.prototype.setFrameRate = function setFrameRate(frameRate) {
   802       this.frameRate = frameRate;
   803       this.maxFrameTime = 1000 * 2 / frameRate;
   804     };
   805     timeline.prototype.refreshEvery = function refreshEvery(freq) {
   806       this.refreshFrequency = freq;
   807       this.refreshCounter = 0;
   808     };
   809     var ENTER = 3203334144 | 0;
   810     var LEAVE = 3735879680 | 0;
   811     timeline.prototype.registerKind = function getKind(name, fillStyle) {
   812       if (this.kinds[name] === undefined) {
   813         this.fillStyles[this.kindCount] = fillStyle;
   814         this.kinds[name] = this.kindCount++;
   815       } else {
   816         this.fillStyles[this.kinds[name]] = fillStyle;
   817       }
   818     };
   819     timeline.prototype.getKind = function getKind(name) {
   820       if (this.kinds[name] === undefined) {
   821         this.kinds[name] = this.kindCount++;
   822         if (this.kindCount > this.fillStyles.length) {
   823           this.fillStyles.push(randomStyle());
   824         }
   825       }
   826       return this.kinds[name];
   827     };
   828     timeline.prototype.enter = function enter(name) {
   829       this.depth++;
   830       this.marks.write(ENTER | this.getKind(name));
   831       this.times.write(performance.now());
   832     };
   833     timeline.prototype.leave = function leave(name) {
   834       this.marks.write(LEAVE | this.getKind(name));
   835       this.times.write(performance.now());
   836       this.depth--;
   837       if (this.depth === 0) {
   838         this.count++;
   839         if (++this.refreshCounter == this.refreshFrequency) {
   840           this.refreshCounter = 0;
   841           this.paint();
   842         }
   843       }
   844     };
   845     timeline.prototype.gatherFrames = function gatherFrames(maxFrames) {
   846       var stack = [];
   847       var frames = [];
   848       var times = this.times;
   849       maxFrames++;
   850       this.marks.forEachInReverse(function (mark, i) {
   851         var time = times.get(i);
   852         if ((mark & 4294901760) === ENTER) {
   853           var node = stack.pop();
   854           node.startTime = time;
   855           if (!stack.length) {
   856             if (frames.length && !frames[0].total) {
   857               frames[0].total = frames[0].startTime - time;
   858             }
   859             frames.unshift(node);
   860           } else {
   861             var top = stack.top();
   862             if (!top.children) {
   863               top.children = [
   864                 node
   865               ];
   866             } else {
   867               top.children.push(node);
   868             }
   869           }
   870         } else if ((mark & 4294901760) === LEAVE) {
   871           if (frames.length > maxFrames) {
   872             return true;
   873           }
   874           stack.push({
   875             kind: mark & 65535,
   876             endTime: time
   877           });
   878         }
   879       });
   880       return frames;
   881     };
   882     timeline.prototype.resizeHandler = function resizeHandler(event) {
   883       var parent = this.canvas.parentElement;
   884       this.cw = parent.offsetWidth;
   885       this.ch = parent.offsetHeight - 1;
   886       var devicePixelRatio = window.devicePixelRatio || 1;
   887       var backingStoreRatio = this.context.webkitBackingStorePixelRatio || this.context.mozBackingStorePixelRatio || this.context.msBackingStorePixelRatio || this.context.oBackingStorePixelRatio || this.context.backingStorePixelRatio || 1;
   888       if (devicePixelRatio !== backingStoreRatio) {
   889         var ratio = devicePixelRatio / backingStoreRatio;
   890         this.canvas.width = this.cw * ratio;
   891         this.canvas.height = this.ch * ratio;
   892         this.canvas.style.width = this.cw + 'px';
   893         this.canvas.style.height = this.ch + 'px';
   894         this.context.scale(ratio, ratio);
   895       } else {
   896         this.canvas.width = this.cw;
   897         this.canvas.height = this.ch;
   898       }
   899       this.context.font = '10px Consolas, "Liberation Mono", Courier, monospace';
   900     };
   901     timeline.prototype.paint = function paint() {
   902       var w = 10;
   903       var gap = 1;
   904       var maxFrames = this.cw / (w + gap) | 0;
   905       var frames = this.gatherFrames(maxFrames);
   906       var context = this.context;
   907       var maxFrameTime = this.maxFrameTime;
   908       var fillStyles = this.fillStyles;
   909       context.clearRect(0, 0, this.cw, this.ch);
   910       var maxFrameRate = 0;
   911       var maxFrameRateCount = 0;
   912       var avgFrameRate = 0;
   913       var avgFrameRateCount = 0;
   914       var offsetW;
   915       context.save();
   916       context.translate(0, this.ch);
   917       context.scale(1, -this.ch / maxFrameTime);
   918       for (var i = 0; i < frames.length - 1; i++) {
   919         var frame = frames[i];
   920         maxFrameRate += frame.endTime - frame.startTime;
   921         maxFrameRateCount++;
   922         if (frame.total) {
   923           avgFrameRate += frame.total;
   924           avgFrameRateCount++;
   925         }
   926         offsetW = i * (w + gap);
   927         context.fillStyle = barColor;
   928         context.fillRect(offsetW, 0, w, frames[i + 1].startTime - frame.startTime);
   929         drawNode(frame, frame.startTime);
   930       }
   931       function drawNode(node, frameStartTime) {
   932         var nodeTime = node.endTime - node.startTime;
   933         var offsetH = node.startTime - frameStartTime;
   934         context.fillStyle = fillStyles[node.kind];
   935         context.fillRect(offsetW, offsetH, w, nodeTime);
   936         if (node.children) {
   937           var children = node.children;
   938           for (var i = 0, n = children.length; i < n; i++) {
   939             drawNode(children[i], frameStartTime);
   940           }
   941         }
   942       }
   943       var lineH = 1000 / this.frameRate;
   944       context.beginPath();
   945       context.lineWidth = 0.5;
   946       context.moveTo(0, lineH);
   947       context.lineTo(this.cw, lineH);
   948       context.strokeStyle = fpsLineColor;
   949       context.stroke();
   950       context.restore();
   951       context.fillStyle = backgroundColorInfo;
   952       context.fillRect(0, 0, this.cw, 20);
   953       var textOffset;
   954       var sFrameCount = this.count;
   955       var sMaxFrameRate = Math.round(1000 * maxFrameRateCount / maxFrameRate);
   956       var sAvgFrameRate = Math.round(1000 * avgFrameRateCount / avgFrameRate);
   957       var space = 5;
   958       textOffset = 5;
   959       context.fillStyle = textColor;
   960       context.fillText(sFrameCount, textOffset, 13);
   961       textOffset += context.measureText(sFrameCount).width + space;
   962       context.fillText(sMaxFrameRate, textOffset, 13);
   963       textOffset += context.measureText(sMaxFrameRate).width + space;
   964       context.fillText(sAvgFrameRate, textOffset, 13);
   965       var basicOffset = textOffset + context.measureText(sAvgFrameRate).width + space;
   966       textOffset = this.cw;
   967       for (var k in this.kinds) {
   968         context.fillStyle = this.fillStyles[this.getKind(k)];
   969         textOffset -= context.measureText(k).width + space;
   970         if (textOffset > basicOffset) {
   971           this.context.fillText(k, textOffset, 13);
   972         }
   973       }
   974     };
   975     return timeline;
   976   }();
   977 var create = Object.create;
   978 var defineProperty = Object.defineProperty;
   979 var keys = Object.keys;
   980 var isArray = Array.isArray;
   981 var fromCharCode = String.fromCharCode;
   982 var logE = Math.log;
   983 var max = Math.max;
   984 var min = Math.min;
   985 var pow = Math.pow;
   986 var push = Array.prototype.push;
   987 var slice = Array.prototype.slice;
   988 var splice = Array.prototype.splice;
   989 function fail(msg, context) {
   990   throw new Error((context ? context + ': ' : '') + msg);
   991 }
   992 function assert(cond, msg, context) {
   993   if (!cond)
   994     fail(msg, context);
   995 }
   996 function scriptProperties(namespace, props) {
   997   return props.reduce(function (o, p) {
   998     o[p] = namespace + ' ' + p;
   999     return o;
  1000   }, {});
  1002 function cloneObject(obj) {
  1003   var clone = Object.create(null);
  1004   for (var prop in obj)
  1005     clone[prop] = obj[prop];
  1006   return clone;
  1008 function sortNumeric(a, b) {
  1009   return a - b;
  1011 function sortByZindex(a, b) {
  1012   return a._zindex - b._zindex;
  1014 function rgbaObjToStr(color) {
  1015   return 'rgba(' + color.red + ',' + color.green + ',' + color.blue + ',' + color.alpha / 255 + ')';
  1017 function rgbIntAlphaToStr(color, alpha) {
  1018   color |= 0;
  1019   if (alpha >= 1) {
  1020     var colorStr = color.toString(16);
  1021     while (colorStr.length < 6) {
  1022       colorStr = '0' + colorStr;
  1024     return '#' + colorStr;
  1026   var red = color >> 16 & 255;
  1027   var green = color >> 8 & 255;
  1028   var blue = color & 255;
  1029   return 'rgba(' + red + ',' + green + ',' + blue + ',' + alpha + ')';
  1031 function argbUintToStr(argb) {
  1032   return 'rgba(' + (argb >>> 16 & 255) + ',' + (argb >>> 8 & 255) + ',' + (argb & 255) + ',' + (argb >>> 24 & 255) / 255 + ')';
  1034 (function functionNameSupport() {
  1035   if (eval('function t() {} t.name === \'t\'')) {
  1036     return;
  1038   Object.defineProperty(Function.prototype, 'name', {
  1039     get: function () {
  1040       if (this.__name) {
  1041         return this.__name;
  1043       var m = /function\s([^\(]+)/.exec(this.toString());
  1044       var name = m && m[1] !== 'anonymous' ? m[1] : null;
  1045       this.__name = name;
  1046       return name;
  1047     },
  1048     configurable: true,
  1049     enumerable: false
  1050   });
  1051 }());
  1052 var randomStyleCache;
  1053 var nextStyle = 0;
  1054 function randomStyle() {
  1055   if (!randomStyleCache) {
  1056     randomStyleCache = [
  1057       '#ff5e3a',
  1058       '#ff9500',
  1059       '#ffdb4c',
  1060       '#87fc70',
  1061       '#52edc7',
  1062       '#1ad6fd',
  1063       '#c644fc',
  1064       '#ef4db6',
  1065       '#4a4a4a',
  1066       '#dbddde',
  1067       '#ff3b30',
  1068       '#ff9500',
  1069       '#ffcc00',
  1070       '#4cd964',
  1071       '#34aadc',
  1072       '#007aff',
  1073       '#5856d6',
  1074       '#ff2d55',
  1075       '#8e8e93',
  1076       '#c7c7cc',
  1077       '#5ad427',
  1078       '#c86edf',
  1079       '#d1eefc',
  1080       '#e0f8d8',
  1081       '#fb2b69',
  1082       '#f7f7f7',
  1083       '#1d77ef',
  1084       '#d6cec3',
  1085       '#55efcb',
  1086       '#ff4981',
  1087       '#ffd3e0',
  1088       '#f7f7f7',
  1089       '#ff1300',
  1090       '#1f1f21',
  1091       '#bdbec2',
  1092       '#ff3a2d'
  1093     ];
  1095   return randomStyleCache[nextStyle++ % randomStyleCache.length];
  1097 (function PromiseClosure() {
  1098   var global = Function('return this')();
  1099   if (global.Promise) {
  1100     if (typeof global.Promise.all !== 'function') {
  1101       global.Promise.all = function (iterable) {
  1102         var count = 0, results = [], resolve, reject;
  1103         var promise = new global.Promise(function (resolve_, reject_) {
  1104             resolve = resolve_;
  1105             reject = reject_;
  1106           });
  1107         iterable.forEach(function (p, i) {
  1108           count++;
  1109           p.then(function (result) {
  1110             results[i] = result;
  1111             count--;
  1112             if (count === 0) {
  1113               resolve(results);
  1115           }, reject);
  1116         });
  1117         if (count === 0) {
  1118           resolve(results);
  1120         return promise;
  1121       };
  1123     if (typeof global.Promise.resolve !== 'function') {
  1124       global.Promise.resolve = function (x) {
  1125         return new global.Promise(function (resolve) {
  1126           resolve(x);
  1127         });
  1128       };
  1130     return;
  1132   function getDeferred(C) {
  1133     if (typeof C !== 'function') {
  1134       throw new TypeError('Invalid deferred constructor');
  1136     var resolver = createDeferredConstructionFunctions();
  1137     var promise = new C(resolver);
  1138     var resolve = resolver.resolve;
  1139     if (typeof resolve !== 'function') {
  1140       throw new TypeError('Invalid resolve construction function');
  1142     var reject = resolver.reject;
  1143     if (typeof reject !== 'function') {
  1144       throw new TypeError('Invalid reject construction function');
  1146     return {
  1147       promise: promise,
  1148       resolve: resolve,
  1149       reject: reject
  1150     };
  1152   function updateDeferredFromPotentialThenable(x, deferred) {
  1153     if (typeof x !== 'object' || x === null) {
  1154       return false;
  1156     try {
  1157       var then = x.then;
  1158       if (typeof then !== 'function') {
  1159         return false;
  1161       var thenCallResult = then.call(x, deferred.resolve, deferred.reject);
  1162     } catch (e) {
  1163       var reject = deferred.reject;
  1164       reject(e);
  1166     return true;
  1168   function isPromise(x) {
  1169     return typeof x === 'object' && x !== null && typeof x.promiseStatus !== 'undefined';
  1171   function rejectPromise(promise, reason) {
  1172     if (promise.promiseStatus !== 'unresolved') {
  1173       return;
  1175     var reactions = promise.rejectReactions;
  1176     promise.result = reason;
  1177     promise.resolveReactions = undefined;
  1178     promise.rejectReactions = undefined;
  1179     promise.promiseStatus = 'has-rejection';
  1180     triggerPromiseReactions(reactions, reason);
  1182   function resolvePromise(promise, resolution) {
  1183     if (promise.promiseStatus !== 'unresolved') {
  1184       return;
  1186     var reactions = promise.resolveReactions;
  1187     promise.result = resolution;
  1188     promise.resolveReactions = undefined;
  1189     promise.rejectReactions = undefined;
  1190     promise.promiseStatus = 'has-resolution';
  1191     triggerPromiseReactions(reactions, resolution);
  1193   function triggerPromiseReactions(reactions, argument) {
  1194     for (var i = 0; i < reactions.length; i++) {
  1195       queueMicrotask({
  1196         reaction: reactions[i],
  1197         argument: argument
  1198       });
  1201   function queueMicrotask(task) {
  1202     if (microtasksQueue.length === 0) {
  1203       setTimeout(handleMicrotasksQueue, 0);
  1205     microtasksQueue.push(task);
  1207   function executePromiseReaction(reaction, argument) {
  1208     var deferred = reaction.deferred;
  1209     var handler = reaction.handler;
  1210     var handlerResult, updateResult;
  1211     try {
  1212       handlerResult = handler(argument);
  1213     } catch (e) {
  1214       var reject = deferred.reject;
  1215       return reject(e);
  1217     if (handlerResult === deferred.promise) {
  1218       var reject = deferred.reject;
  1219       return reject(new TypeError('Self resolution'));
  1221     try {
  1222       updateResult = updateDeferredFromPotentialThenable(handlerResult, deferred);
  1223       if (!updateResult) {
  1224         var resolve = deferred.resolve;
  1225         return resolve(handlerResult);
  1227     } catch (e) {
  1228       var reject = deferred.reject;
  1229       return reject(e);
  1232   var microtasksQueue = [];
  1233   function handleMicrotasksQueue() {
  1234     while (microtasksQueue.length > 0) {
  1235       var task = microtasksQueue[0];
  1236       try {
  1237         executePromiseReaction(task.reaction, task.argument);
  1238       } catch (e) {
  1239         if (typeof Promise.onerror === 'function') {
  1240           Promise.onerror(e);
  1243       microtasksQueue.shift();
  1246   function throwerFunction(e) {
  1247     throw e;
  1249   function identityFunction(x) {
  1250     return x;
  1252   function createRejectPromiseFunction(promise) {
  1253     return function (reason) {
  1254       rejectPromise(promise, reason);
  1255     };
  1257   function createResolvePromiseFunction(promise) {
  1258     return function (resolution) {
  1259       resolvePromise(promise, resolution);
  1260     };
  1262   function createDeferredConstructionFunctions() {
  1263     var fn = function (resolve, reject) {
  1264       fn.resolve = resolve;
  1265       fn.reject = reject;
  1266     };
  1267     return fn;
  1269   function createPromiseResolutionHandlerFunctions(promise, fulfillmentHandler, rejectionHandler) {
  1270     return function (x) {
  1271       if (x === promise) {
  1272         return rejectionHandler(new TypeError('Self resolution'));
  1274       var cstr = promise.promiseConstructor;
  1275       if (isPromise(x)) {
  1276         var xConstructor = x.promiseConstructor;
  1277         if (xConstructor === cstr) {
  1278           return x.then(fulfillmentHandler, rejectionHandler);
  1281       var deferred = getDeferred(cstr);
  1282       var updateResult = updateDeferredFromPotentialThenable(x, deferred);
  1283       if (updateResult) {
  1284         var deferredPromise = deferred.promise;
  1285         return deferredPromise.then(fulfillmentHandler, rejectionHandler);
  1287       return fulfillmentHandler(x);
  1288     };
  1290   function createPromiseAllCountdownFunction(index, values, deferred, countdownHolder) {
  1291     return function (x) {
  1292       values[index] = x;
  1293       countdownHolder.countdown--;
  1294       if (countdownHolder.countdown === 0) {
  1295         deferred.resolve(values);
  1297     };
  1299   function Promise(resolver) {
  1300     if (typeof resolver !== 'function') {
  1301       throw new TypeError('resolver is not a function');
  1303     var promise = this;
  1304     if (typeof promise !== 'object') {
  1305       throw new TypeError('Promise to initialize is not an object');
  1307     promise.promiseStatus = 'unresolved';
  1308     promise.resolveReactions = [];
  1309     promise.rejectReactions = [];
  1310     promise.result = undefined;
  1311     var resolve = createResolvePromiseFunction(promise);
  1312     var reject = createRejectPromiseFunction(promise);
  1313     try {
  1314       var result = resolver(resolve, reject);
  1315     } catch (e) {
  1316       rejectPromise(promise, e);
  1318     promise.promiseConstructor = Promise;
  1319     return promise;
  1321   Promise.all = function (iterable) {
  1322     var deferred = getDeferred(this);
  1323     var values = [];
  1324     var countdownHolder = {
  1325         countdown: 0
  1326       };
  1327     var index = 0;
  1328     iterable.forEach(function (nextValue) {
  1329       var nextPromise = this.cast(nextValue);
  1330       var fn = createPromiseAllCountdownFunction(index, values, deferred, countdownHolder);
  1331       nextPromise.then(fn, deferred.reject);
  1332       index++;
  1333       countdownHolder.countdown++;
  1334     }, this);
  1335     if (index === 0) {
  1336       deferred.resolve(values);
  1338     return deferred.promise;
  1339   };
  1340   Promise.cast = function (x) {
  1341     if (isPromise(x)) {
  1342       return x;
  1344     var deferred = getDeferred(this);
  1345     deferred.resolve(x);
  1346     return deferred.promise;
  1347   };
  1348   Promise.reject = function (r) {
  1349     var deferred = getDeferred(this);
  1350     var rejectResult = deferred.reject(r);
  1351     return deferred.promise;
  1352   };
  1353   Promise.resolve = function (x) {
  1354     var deferred = getDeferred(this);
  1355     var rejectResult = deferred.resolve(x);
  1356     return deferred.promise;
  1357   };
  1358   Promise.prototype = {
  1359     'catch': function (onRejected) {
  1360       this.then(undefined, onRejected);
  1361     },
  1362     then: function (onFulfilled, onRejected) {
  1363       var promise = this;
  1364       if (!isPromise(promise)) {
  1365         throw new TypeError('this is not a Promises');
  1367       var cstr = promise.promiseConstructor;
  1368       var deferred = getDeferred(cstr);
  1369       var rejectionHandler = typeof onRejected === 'function' ? onRejected : throwerFunction;
  1370       var fulfillmentHandler = typeof onFulfilled === 'function' ? onFulfilled : identityFunction;
  1371       var resolutionHandler = createPromiseResolutionHandlerFunctions(promise, fulfillmentHandler, rejectionHandler);
  1372       var resolveReaction = {
  1373           deferred: deferred,
  1374           handler: resolutionHandler
  1375         };
  1376       var rejectReaction = {
  1377           deferred: deferred,
  1378           handler: rejectionHandler
  1379         };
  1380       switch (promise.promiseStatus) {
  1381       case 'unresolved':
  1382         promise.resolveReactions.push(resolveReaction);
  1383         promise.rejectReactions.push(rejectReaction);
  1384         break;
  1385       case 'has-resolution':
  1386         var resolution = promise.result;
  1387         queueMicrotask({
  1388           reaction: resolveReaction,
  1389           argument: resolution
  1390         });
  1391         break;
  1392       case 'has-rejection':
  1393         var rejection = promise.result;
  1394         queueMicrotask({
  1395           reaction: rejectReaction,
  1396           argument: rejection
  1397         });
  1398         break;
  1400       return deferred.promise;
  1402   };
  1403   global.Promise = Promise;
  1404 }());
  1405 var QuadTree = function (x, y, width, height, parent) {
  1406   this.x = x | 0;
  1407   this.y = y | 0;
  1408   this.width = width | 0;
  1409   this.height = height | 0;
  1410   if (parent) {
  1411     this.root = parent.root;
  1412     this.parent = parent;
  1413     this.level = parent.level + 1;
  1414   } else {
  1415     this.root = this;
  1416     this.parent = null;
  1417     this.level = 0;
  1419   this.reset();
  1420 };
  1421 QuadTree.prototype.reset = function () {
  1422   this.stuckObjects = null;
  1423   this.objects = null;
  1424   this.nodes = [];
  1425 };
  1426 QuadTree.prototype._findIndex = function (xMin, xMax, yMin, yMax) {
  1427   var midX = this.x + (this.width / 2 | 0);
  1428   var midY = this.y + (this.height / 2 | 0);
  1429   var top = yMin < midY && yMax < midY;
  1430   var bottom = yMin > midY;
  1431   if (xMin < midX && xMax < midX) {
  1432     if (top) {
  1433       return 1;
  1434     } else if (bottom) {
  1435       return 2;
  1437   } else if (xMin > midX) {
  1438     if (top) {
  1439       return 0;
  1440     } else if (bottom) {
  1441       return 3;
  1444   return -1;
  1445 };
  1446 QuadTree.prototype.insert = function (obj) {
  1447   var nodes = this.nodes;
  1448   if (nodes.length) {
  1449     var index = this._findIndex(obj.xMin, obj.xMax, obj.yMin, obj.yMax);
  1450     if (index > -1) {
  1451       nodes[index].insert(obj);
  1452     } else {
  1453       obj.prev = null;
  1454       if (this.stuckObjects) {
  1455         obj.next = this.stuckObjects;
  1456         this.stuckObjects.prev = obj;
  1457       } else {
  1458         obj.next = null;
  1460       this.stuckObjects = obj;
  1461       obj.parent = this;
  1463     return;
  1465   var numChildren = 1;
  1466   var item = this.objects;
  1467   if (!item) {
  1468     obj.prev = null;
  1469     obj.next = null;
  1470     this.objects = obj;
  1471   } else {
  1472     while (item.next) {
  1473       numChildren++;
  1474       item = item.next;
  1476     obj.prev = item;
  1477     obj.next = null;
  1478     item.next = obj;
  1480   if (numChildren > 4 && this.level < 10) {
  1481     this._subdivide();
  1482     item = this.objects;
  1483     while (item) {
  1484       var next = item.next;
  1485       this.insert(item);
  1486       item = next;
  1488     this.objects = null;
  1489     return;
  1491   obj.parent = this;
  1492 };
  1493 QuadTree.prototype.update = function (obj) {
  1494   var node = obj.parent;
  1495   if (node) {
  1496     if (obj.xMin >= node.x && obj.xMax <= node.x + node.width && obj.yMin >= node.y && obj.yMax <= node.y + node.height) {
  1497       if (node.nodes.length) {
  1498         var index = this._findIndex(obj.xMin, obj.xMax, obj.yMin, obj.yMax);
  1499         if (index > -1) {
  1500           node.remove(obj);
  1501           node = this.nodes[index];
  1502           node.insert(obj);
  1504       } else {
  1505         node.remove(obj);
  1506         node.insert(obj);
  1508       return;
  1510     node.remove(obj);
  1512   this.root.insert(obj);
  1513 };
  1514 QuadTree.prototype.remove = function (obj) {
  1515   var prev = obj.prev;
  1516   var next = obj.next;
  1517   if (prev) {
  1518     prev.next = next;
  1519     obj.prev = null;
  1520   } else {
  1521     var node = obj.parent;
  1522     if (node.objects === obj) {
  1523       node.objects = next;
  1524     } else if (node.stuckObjects === obj) {
  1525       node.stuckObjects = next;
  1528   if (next) {
  1529     next.prev = prev;
  1530     obj.next = null;
  1532   obj.parent = null;
  1533 };
  1534 QuadTree.prototype.retrieve = function (xMin, xMax, yMin, yMax) {
  1535   var stack = [];
  1536   var out = [];
  1537   var node = this;
  1538   do {
  1539     if (node.nodes.length) {
  1540       var index = node._findIndex(xMin, xMax, yMin, yMax);
  1541       if (index > -1) {
  1542         stack.push(node.nodes[index]);
  1543       } else {
  1544         stack.push.apply(stack, node.nodes);
  1547     var item = node.objects;
  1548     for (var i = 0; i < 2; i++) {
  1549       while (item) {
  1550         if (!(item.xMin > xMax || item.xMax < xMin || item.yMin > yMax || item.yMax < yMin)) {
  1551           out.push(item);
  1553         item = item.next;
  1555       item = node.stuckObjects;
  1557     node = stack.pop();
  1558   } while (node);
  1559   return out;
  1560 };
  1561 QuadTree.prototype._subdivide = function () {
  1562   var halfWidth = this.width / 2 | 0;
  1563   var halfHeight = this.height / 2 | 0;
  1564   var midX = this.x + halfWidth;
  1565   var midY = this.y + halfHeight;
  1566   this.nodes[0] = new QuadTree(midX, this.y, halfWidth, halfHeight, this);
  1567   this.nodes[1] = new QuadTree(this.x, this.y, halfWidth, halfHeight, this);
  1568   this.nodes[2] = new QuadTree(this.x, midY, halfWidth, halfHeight, this);
  1569   this.nodes[3] = new QuadTree(midX, midY, halfWidth, halfHeight, this);
  1570 };
  1571 var RegionCluster = function () {
  1572   this.regions = [];
  1573 };
  1574 RegionCluster.prototype.reset = function () {
  1575   this.regions.length = 0;
  1576 };
  1577 RegionCluster.prototype.insert = function (region) {
  1578   var regions = this.regions;
  1579   if (regions.length < 3) {
  1580     regions.push({
  1581       xMin: region.xMin,
  1582       xMax: region.xMax,
  1583       yMin: region.yMin,
  1584       yMax: region.yMax
  1585     });
  1586     return;
  1588   var a = region;
  1589   var b = regions[0];
  1590   var c = regions[1];
  1591   var d = regions[2];
  1592   var ab = (max(a.xMax, b.xMax) - min(a.xMin, b.xMin)) * (max(a.yMax, b.yMax) - min(a.yMin, b.yMin));
  1593   var rb = regions[0];
  1594   var ac = (max(a.xMax, c.xMax) - min(a.xMin, c.xMin)) * (max(a.yMax, c.yMax) - min(a.yMin, c.yMin));
  1595   var ad = (max(a.xMax, d.xMax) - min(a.xMin, d.xMin)) * (max(a.yMax, d.yMax) - min(a.yMin, d.yMin));
  1596   if (ac < ab) {
  1597     ab = ac;
  1598     rb = c;
  1600   if (ad < ab) {
  1601     ab = ad;
  1602     rb = d;
  1604   var bc = (max(b.xMax, c.xMax) - min(b.xMin, c.xMin)) * (max(b.yMax, c.yMax) - min(b.yMin, c.yMin));
  1605   var bd = (max(b.xMax, d.xMax) - min(b.xMin, d.xMin)) * (max(b.yMax, d.yMax) - min(b.yMin, d.yMin));
  1606   var cd = (max(c.xMax, d.xMax) - min(c.xMin, d.xMin)) * (max(c.yMax, d.yMax) - min(c.yMin, d.yMin));
  1607   if (ab < bc && ab < bd && ab < cd) {
  1608     if (a.xMin < rb.xMin) {
  1609       rb.xMin = a.xMin;
  1611     if (a.xMax > rb.xMax) {
  1612       rb.xMax = a.xMax;
  1614     if (a.yMin < rb.yMin) {
  1615       rb.yMin = a.yMin;
  1617     if (a.yMax > rb.yMax) {
  1618       rb.yMax = a.yMax;
  1620     return;
  1622   rb = regions[0];
  1623   var rc = regions[1];
  1624   if (bd < bc) {
  1625     bc = bd;
  1626     rc = regions[2];
  1628   if (cd < bc) {
  1629     rb = regions[1];
  1630     rc = regions[2];
  1632   if (rc.xMin < rb.xMin) {
  1633     rb.xMin = rc.xMin;
  1635   if (rc.xMax > rb.xMax) {
  1636     rb.xMax = rc.xMax;
  1638   if (rc.yMin < rb.yMin) {
  1639     rb.yMin = rc.yMin;
  1641   if (rc.yMax > rb.yMax) {
  1642     rb.yMax = rc.yMax;
  1644   rc.xMin = a.xMin;
  1645   rc.xMax = a.xMax;
  1646   rc.yMin = a.yMin;
  1647   rc.yMax = a.yMax;
  1648 };
  1649 RegionCluster.prototype.retrieve = function () {
  1650   return this.regions;
  1651 };
  1652 var EXTERNAL_INTERFACE_FEATURE = 1;
  1653 var CLIPBOARD_FEATURE = 2;
  1654 var SHAREDOBJECT_FEATURE = 3;
  1655 var VIDEO_FEATURE = 4;
  1656 var SOUND_FEATURE = 5;
  1657 var NETCONNECTION_FEATURE = 6;
  1658 if (!this.performance) {
  1659   this.performance = {};
  1661 if (!this.performance.now) {
  1662   this.performance.now = Date.now;
  1664 var SWF_TAG_CODE_CSM_TEXT_SETTINGS = 74;
  1665 var SWF_TAG_CODE_DEFINE_BINARY_DATA = 87;
  1666 var SWF_TAG_CODE_DEFINE_BITS = 6;
  1667 var SWF_TAG_CODE_DEFINE_BITS_JPEG2 = 21;
  1668 var SWF_TAG_CODE_DEFINE_BITS_JPEG3 = 35;
  1669 var SWF_TAG_CODE_DEFINE_BITS_JPEG4 = 90;
  1670 var SWF_TAG_CODE_DEFINE_BITS_LOSSLESS = 20;
  1671 var SWF_TAG_CODE_DEFINE_BITS_LOSSLESS2 = 36;
  1672 var SWF_TAG_CODE_DEFINE_BUTTON = 7;
  1673 var SWF_TAG_CODE_DEFINE_BUTTON2 = 34;
  1674 var SWF_TAG_CODE_DEFINE_BUTTON_CXFORM = 23;
  1675 var SWF_TAG_CODE_DEFINE_BUTTON_SOUND = 17;
  1676 var SWF_TAG_CODE_DEFINE_EDIT_TEXT = 37;
  1677 var SWF_TAG_CODE_DEFINE_FONT = 10;
  1678 var SWF_TAG_CODE_DEFINE_FONT2 = 48;
  1679 var SWF_TAG_CODE_DEFINE_FONT3 = 75;
  1680 var SWF_TAG_CODE_DEFINE_FONT4 = 91;
  1681 var SWF_TAG_CODE_DEFINE_FONT_ALIGN_ZONES = 73;
  1682 var SWF_TAG_CODE_DEFINE_FONT_INFO = 13;
  1683 var SWF_TAG_CODE_DEFINE_FONT_INFO2 = 62;
  1684 var SWF_TAG_CODE_DEFINE_FONT_NAME = 88;
  1685 var SWF_TAG_CODE_DEFINE_MORPH_SHAPE = 46;
  1686 var SWF_TAG_CODE_DEFINE_MORPH_SHAPE2 = 84;
  1687 var SWF_TAG_CODE_DEFINE_SCALING_GRID = 78;
  1688 var SWF_TAG_CODE_DEFINE_SCENE_AND_FRAME_LABEL_DATA = 86;
  1689 var SWF_TAG_CODE_DEFINE_SHAPE = 2;
  1690 var SWF_TAG_CODE_DEFINE_SHAPE2 = 22;
  1691 var SWF_TAG_CODE_DEFINE_SHAPE3 = 32;
  1692 var SWF_TAG_CODE_DEFINE_SHAPE4 = 83;
  1693 var SWF_TAG_CODE_DEFINE_SOUND = 14;
  1694 var SWF_TAG_CODE_DEFINE_SPRITE = 39;
  1695 var SWF_TAG_CODE_DEFINE_TEXT = 11;
  1696 var SWF_TAG_CODE_DEFINE_TEXT2 = 33;
  1697 var SWF_TAG_CODE_DEFINE_VIDEO_STREAM = 60;
  1698 var SWF_TAG_CODE_DO_ABC = 82;
  1699 var SWF_TAG_CODE_DO_ABC_ = 72;
  1700 var SWF_TAG_CODE_DO_ACTION = 12;
  1701 var SWF_TAG_CODE_DO_INIT_ACTION = 59;
  1702 var SWF_TAG_CODE_ENABLE_DEBUGGER = 58;
  1703 var SWF_TAG_CODE_ENABLE_DEBUGGER2 = 64;
  1704 var SWF_TAG_CODE_END = 0;
  1705 var SWF_TAG_CODE_EXPORT_ASSETS = 56;
  1706 var SWF_TAG_CODE_FILE_ATTRIBUTES = 69;
  1707 var SWF_TAG_CODE_FRAME_LABEL = 43;
  1708 var SWF_TAG_CODE_IMPORT_ASSETS = 57;
  1709 var SWF_TAG_CODE_IMPORT_ASSETS2 = 71;
  1710 var SWF_TAG_CODE_JPEG_TABLES = 8;
  1711 var SWF_TAG_CODE_METADATA = 77;
  1712 var SWF_TAG_CODE_PLACE_OBJECT = 4;
  1713 var SWF_TAG_CODE_PLACE_OBJECT2 = 26;
  1714 var SWF_TAG_CODE_PLACE_OBJECT3 = 70;
  1715 var SWF_TAG_CODE_PROTECT = 24;
  1716 var SWF_TAG_CODE_REMOVE_OBJECT = 5;
  1717 var SWF_TAG_CODE_REMOVE_OBJECT2 = 28;
  1718 var SWF_TAG_CODE_SCRIPT_LIMITS = 65;
  1719 var SWF_TAG_CODE_SET_BACKGROUND_COLOR = 9;
  1720 var SWF_TAG_CODE_SET_TAB_INDEX = 66;
  1721 var SWF_TAG_CODE_SHOW_FRAME = 1;
  1722 var SWF_TAG_CODE_SOUND_STREAM_BLOCK = 19;
  1723 var SWF_TAG_CODE_SOUND_STREAM_HEAD = 18;
  1724 var SWF_TAG_CODE_SOUND_STREAM_HEAD2 = 45;
  1725 var SWF_TAG_CODE_START_SOUND = 15;
  1726 var SWF_TAG_CODE_START_SOUND2 = 89;
  1727 var SWF_TAG_CODE_SYMBOL_CLASS = 76;
  1728 var SWF_TAG_CODE_VIDEO_FRAME = 61;
  1729 self.SWF = {};
  1730 var codeLengthOrder = [
  1731     16,
  1732     17,
  1733     18,
  1734     0,
  1735     8,
  1736     7,
  1737     9,
  1738     6,
  1739     10,
  1740     5,
  1741     11,
  1742     4,
  1743     12,
  1744     3,
  1745     13,
  1746     2,
  1747     14,
  1748     1,
  1749     15
  1750   ];
  1751 var distanceCodes = [];
  1752 var distanceExtraBits = [];
  1753 for (var i = 0, j = 0, code = 1; i < 30; ++i) {
  1754   distanceCodes[i] = code;
  1755   code += 1 << (distanceExtraBits[i] = ~(~((j += i > 2 ? 1 : 0) / 2)));
  1757 var bitLengths = [];
  1758 for (var i = 0; i < 32; ++i)
  1759   bitLengths[i] = 5;
  1760 var fixedDistanceTable = makeHuffmanTable(bitLengths);
  1761 var lengthCodes = [];
  1762 var lengthExtraBits = [];
  1763 for (var i = 0, j = 0, code = 3; i < 29; ++i) {
  1764   lengthCodes[i] = code - (i == 28 ? 1 : 0);
  1765   code += 1 << (lengthExtraBits[i] = ~(~((j += i > 4 ? 1 : 0) / 4 % 6)));
  1767 for (var i = 0; i < 288; ++i)
  1768   bitLengths[i] = i < 144 || i > 279 ? 8 : i < 256 ? 9 : 7;
  1769 var fixedLiteralTable = makeHuffmanTable(bitLengths);
  1770 function makeHuffmanTable(bitLengths) {
  1771   var maxBits = Math.max.apply(null, bitLengths);
  1772   var numLengths = bitLengths.length;
  1773   var size = 1 << maxBits;
  1774   var codes = new Uint32Array(size);
  1775   for (var code = 0, len = 1, skip = 2; len <= maxBits; code <<= 1, ++len, skip <<= 1) {
  1776     for (var val = 0; val < numLengths; ++val) {
  1777       if (bitLengths[val] === len) {
  1778         var lsb = 0;
  1779         for (var i = 0; i < len; ++i)
  1780           lsb = lsb * 2 + (code >> i & 1);
  1781         for (var i = lsb; i < size; i += skip)
  1782           codes[i] = len << 16 | val;
  1783         ++code;
  1787   return {
  1788     codes: codes,
  1789     maxBits: maxBits
  1790   };
  1792 function verifyDeflateHeader(bytes) {
  1793   var header = bytes[0] << 8 | bytes[1];
  1795 function createInflatedStream(bytes, outputLength) {
  1796   verifyDeflateHeader(bytes);
  1797   var stream = new Stream(bytes, 2);
  1798   var output = {
  1799       data: new Uint8Array(outputLength),
  1800       available: 0,
  1801       completed: false
  1802     };
  1803   var state = {
  1804       header: null,
  1805       distanceTable: null,
  1806       literalTable: null,
  1807       sym: null,
  1808       len: null,
  1809       sym2: null
  1810     };
  1811   do {
  1812     inflateBlock(stream, output, state);
  1813   } while (!output.completed && stream.pos < stream.end);
  1814   return new Stream(output.data, 0, output.available);
  1816 var InflateNoDataError = {};
  1817 function inflateBlock(stream, output, state) {
  1818   var header = state.header !== null ? state.header : state.header = readBits(stream.bytes, stream, 3);
  1819   switch (header >> 1) {
  1820   case 0:
  1821     stream.align();
  1822     var pos = stream.pos;
  1823     if (stream.end - pos < 4) {
  1824       throw InflateNoDataError;
  1826     var len = stream.getUint16(pos, true);
  1827     var nlen = stream.getUint16(pos + 2, true);
  1828     if (stream.end - pos < 4 + len) {
  1829       throw InflateNoDataError;
  1831     var begin = pos + 4;
  1832     var end = stream.pos = begin + len;
  1833     var sbytes = stream.bytes, dbytes = output.data;
  1834     dbytes.set(sbytes.subarray(begin, end), output.available);
  1835     output.available += len;
  1836     break;
  1837   case 1:
  1838     inflate(stream, output, fixedLiteralTable, fixedDistanceTable, state);
  1839     break;
  1840   case 2:
  1841     var distanceTable, literalTable;
  1842     if (state.distanceTable !== null) {
  1843       distanceTable = state.distanceTable;
  1844       literalTable = state.literalTable;
  1845     } else {
  1846       var sbytes = stream.bytes;
  1847       var savedBufferPos = stream.pos;
  1848       var savedBitBuffer = stream.bitBuffer;
  1849       var savedBitLength = stream.bitLength;
  1850       var bitLengths = [];
  1851       var numLiteralCodes, numDistanceCodes;
  1852       try {
  1853         numLiteralCodes = readBits(sbytes, stream, 5) + 257;
  1854         numDistanceCodes = readBits(sbytes, stream, 5) + 1;
  1855         var numCodes = numLiteralCodes + numDistanceCodes;
  1856         var numLengthCodes = readBits(sbytes, stream, 4) + 4;
  1857         for (var i = 0; i < 19; ++i)
  1858           bitLengths[codeLengthOrder[i]] = i < numLengthCodes ? readBits(sbytes, stream, 3) : 0;
  1859         var codeLengthTable = makeHuffmanTable(bitLengths);
  1860         bitLengths = [];
  1861         var i = 0;
  1862         var prev = 0;
  1863         while (i < numCodes) {
  1864           var j = 1;
  1865           var sym = readCode(sbytes, stream, codeLengthTable);
  1866           switch (sym) {
  1867           case 16:
  1868             j = readBits(sbytes, stream, 2) + 3;
  1869             sym = prev;
  1870             break;
  1871           case 17:
  1872             j = readBits(sbytes, stream, 3) + 3;
  1873             sym = 0;
  1874             break;
  1875           case 18:
  1876             j = readBits(sbytes, stream, 7) + 11;
  1877             sym = 0;
  1878             break;
  1879           default:
  1880             prev = sym;
  1882           while (j--)
  1883             bitLengths[i++] = sym;
  1885       } catch (e) {
  1886         stream.pos = savedBufferPos;
  1887         stream.bitBuffer = savedBitBuffer;
  1888         stream.bitLength = savedBitLength;
  1889         throw e;
  1891       distanceTable = state.distanceTable = makeHuffmanTable(bitLengths.splice(numLiteralCodes, numDistanceCodes));
  1892       literalTable = state.literalTable = makeHuffmanTable(bitLengths);
  1894     inflate(stream, output, literalTable, distanceTable, state);
  1895     state.distanceTable = null;
  1896     state.literalTable = null;
  1897     break;
  1898   default:
  1899     fail('unknown block type', 'inflate');
  1901   state.header = null;
  1902   output.completed = !(!(header & 1));
  1904 function readBits(bytes, stream, size) {
  1905   var bitBuffer = stream.bitBuffer;
  1906   var bitLength = stream.bitLength;
  1907   if (size > bitLength) {
  1908     var pos = stream.pos;
  1909     var end = stream.end;
  1910     do {
  1911       if (pos >= end) {
  1912         stream.pos = pos;
  1913         stream.bitBuffer = bitBuffer;
  1914         stream.bitLength = bitLength;
  1915         throw InflateNoDataError;
  1917       bitBuffer |= bytes[pos++] << bitLength;
  1918       bitLength += 8;
  1919     } while (size > bitLength);
  1920     stream.pos = pos;
  1922   stream.bitBuffer = bitBuffer >>> size;
  1923   stream.bitLength = bitLength - size;
  1924   return bitBuffer & (1 << size) - 1;
  1926 function inflate(stream, output, literalTable, distanceTable, state) {
  1927   var pos = output.available;
  1928   var dbytes = output.data;
  1929   var sbytes = stream.bytes;
  1930   var sym = state.sym !== null ? state.sym : readCode(sbytes, stream, literalTable);
  1931   while (sym !== 256) {
  1932     if (sym < 256) {
  1933       dbytes[pos++] = sym;
  1934     } else {
  1935       state.sym = sym;
  1936       sym -= 257;
  1937       var len = state.len !== null ? state.len : state.len = lengthCodes[sym] + readBits(sbytes, stream, lengthExtraBits[sym]);
  1938       var sym2 = state.sym2 !== null ? state.sym2 : state.sym2 = readCode(sbytes, stream, distanceTable);
  1939       var distance = distanceCodes[sym2] + readBits(sbytes, stream, distanceExtraBits[sym2]);
  1940       var i = pos - distance;
  1941       while (len--)
  1942         dbytes[pos++] = dbytes[i++];
  1943       state.sym2 = null;
  1944       state.len = null;
  1945       state.sym = null;
  1947     output.available = pos;
  1948     sym = readCode(sbytes, stream, literalTable);
  1951 function readCode(bytes, stream, codeTable) {
  1952   var bitBuffer = stream.bitBuffer;
  1953   var bitLength = stream.bitLength;
  1954   var maxBits = codeTable.maxBits;
  1955   if (maxBits > bitLength) {
  1956     var pos = stream.pos;
  1957     var end = stream.end;
  1958     do {
  1959       if (pos >= end) {
  1960         stream.pos = pos;
  1961         stream.bitBuffer = bitBuffer;
  1962         stream.bitLength = bitLength;
  1963         throw InflateNoDataError;
  1965       bitBuffer |= bytes[pos++] << bitLength;
  1966       bitLength += 8;
  1967     } while (maxBits > bitLength);
  1968     stream.pos = pos;
  1970   var code = codeTable.codes[bitBuffer & (1 << maxBits) - 1];
  1971   var len = code >> 16;
  1972   stream.bitBuffer = bitBuffer >>> len;
  1973   stream.bitLength = bitLength - len;
  1974   return code & 65535;
  1976 var StreamNoDataError = {};
  1977 var Stream = function StreamClosure() {
  1978     function Stream_align() {
  1979       this.bitBuffer = this.bitLength = 0;
  1981     function Stream_ensure(size) {
  1982       if (this.pos + size > this.end) {
  1983         throw StreamNoDataError;
  1986     function Stream_remaining() {
  1987       return this.end - this.pos;
  1989     function Stream_substream(begin, end) {
  1990       var stream = new Stream(this.bytes);
  1991       stream.pos = begin;
  1992       stream.end = end;
  1993       return stream;
  1995     function Stream_push(data) {
  1996       var bytes = this.bytes;
  1997       var newBytesLength = this.end + data.length;
  1998       if (newBytesLength > bytes.length) {
  1999         throw 'stream buffer overfow';
  2001       bytes.set(data, this.end);
  2002       this.end = newBytesLength;
  2004     function Stream(buffer, offset, length, maxLength) {
  2005       if (offset === undefined)
  2006         offset = 0;
  2007       if (buffer.buffer instanceof ArrayBuffer) {
  2008         offset += buffer.byteOffset;
  2009         buffer = buffer.buffer;
  2011       if (length === undefined)
  2012         length = buffer.byteLength - offset;
  2013       if (maxLength === undefined)
  2014         maxLength = length;
  2015       var bytes = new Uint8Array(buffer, offset, maxLength);
  2016       var stream = new DataView(buffer, offset, maxLength);
  2017       stream.bytes = bytes;
  2018       stream.pos = 0;
  2019       stream.end = length;
  2020       stream.bitBuffer = 0;
  2021       stream.bitLength = 0;
  2022       stream.align = Stream_align;
  2023       stream.ensure = Stream_ensure;
  2024       stream.remaining = Stream_remaining;
  2025       stream.substream = Stream_substream;
  2026       stream.push = Stream_push;
  2027       return stream;
  2029     return Stream;
  2030   }();
  2031 var FORMAT_COLORMAPPED = 3;
  2032 var FORMAT_15BPP = 4;
  2033 var FORMAT_24BPP = 5;
  2034 var FACTOR_5BBP = 255 / 31;
  2035 var crcTable = [];
  2036 for (var i = 0; i < 256; i++) {
  2037   var c = i;
  2038   for (var h = 0; h < 8; h++) {
  2039     if (c & 1)
  2040       c = 3988292384 ^ c >> 1 & 2147483647;
  2041     else
  2042       c = c >> 1 & 2147483647;
  2044   crcTable[i] = c;
  2046 function crc32(data, start, end) {
  2047   var crc = -1;
  2048   for (var i = start; i < end; i++) {
  2049     var a = (crc ^ data[i]) & 255;
  2050     var b = crcTable[a];
  2051     crc = crc >>> 8 ^ b;
  2053   return crc ^ -1;
  2055 function createPngChunk(type, data) {
  2056   var chunk = new Uint8Array(12 + data.length);
  2057   var p = 0;
  2058   var len = data.length;
  2059   chunk[p] = len >> 24 & 255;
  2060   chunk[p + 1] = len >> 16 & 255;
  2061   chunk[p + 2] = len >> 8 & 255;
  2062   chunk[p + 3] = len & 255;
  2063   chunk[p + 4] = type.charCodeAt(0) & 255;
  2064   chunk[p + 5] = type.charCodeAt(1) & 255;
  2065   chunk[p + 6] = type.charCodeAt(2) & 255;
  2066   chunk[p + 7] = type.charCodeAt(3) & 255;
  2067   if (data instanceof Uint8Array)
  2068     chunk.set(data, 8);
  2069   p = 8 + len;
  2070   var crc = crc32(chunk, 4, p);
  2071   chunk[p] = crc >> 24 & 255;
  2072   chunk[p + 1] = crc >> 16 & 255;
  2073   chunk[p + 2] = crc >> 8 & 255;
  2074   chunk[p + 3] = crc & 255;
  2075   return chunk;
  2077 function adler32(data, start, end) {
  2078   var a = 1;
  2079   var b = 0;
  2080   for (var i = start; i < end; ++i) {
  2081     a = (a + (data[i] & 255)) % 65521;
  2082     b = (b + a) % 65521;
  2084   return b << 16 | a;
  2086 function defineBitmap(tag) {
  2087   var width = tag.width;
  2088   var height = tag.height;
  2089   var hasAlpha = tag.hasAlpha;
  2090   var plte = '';
  2091   var trns = '';
  2092   var literals;
  2093   var bmpData = tag.bmpData;
  2094   switch (tag.format) {
  2095   case FORMAT_COLORMAPPED:
  2096     var colorType = 3;
  2097     var bytesPerLine = width + 3 & ~3;
  2098     var colorTableSize = tag.colorTableSize + 1;
  2099     var paletteSize = colorTableSize * (tag.hasAlpha ? 4 : 3);
  2100     var datalen = paletteSize + bytesPerLine * height;
  2101     var stream = createInflatedStream(bmpData, datalen);
  2102     var bytes = stream.bytes;
  2103     var pos = 0;
  2104     stream.ensure(paletteSize);
  2105     if (hasAlpha) {
  2106       var palette = new Uint8Array(paletteSize / 4 * 3);
  2107       var pp = 0;
  2108       var alphaValues = new Uint8Array(paletteSize / 4);
  2109       var pa = 0;
  2110       while (pos < paletteSize) {
  2111         palette[pp++] = bytes[pos];
  2112         palette[pp++] = bytes[pos + 1];
  2113         palette[pp++] = bytes[pos + 2];
  2114         alphaValues[pa++] = bytes[pos + 3];
  2115         pos += 4;
  2117       plte = createPngChunk('PLTE', palette);
  2118       trns = createPngChunk('tRNS', alphaValues);
  2119     } else {
  2120       plte = createPngChunk('PLTE', bytes.subarray(pos, pos + paletteSize));
  2121       pos += paletteSize;
  2123     literals = new Uint8Array(width * height + height);
  2124     var pl = 0;
  2125     while (pos < datalen) {
  2126       stream.ensure(bytesPerLine);
  2127       var begin = pos;
  2128       var end = begin + width;
  2129       pl++;
  2130       literals.set(bytes.subarray(begin, end), pl);
  2131       pl += end - begin;
  2132       stream.pos = pos += bytesPerLine;
  2134     break;
  2135   case FORMAT_15BPP:
  2136     var colorType = 2;
  2137     var bytesPerLine = width * 2 + 3 & ~3;
  2138     var stream = createInflatedStream(bmpData, bytesPerLine * height);
  2139     var pos = 0;
  2140     literals = new Uint8Array(width * height * 3 + height);
  2141     var pl = 0;
  2142     for (var y = 0; y < height; ++y) {
  2143       pl++;
  2144       stream.ensure(bytesPerLine);
  2145       for (var x = 0; x < width; ++x) {
  2146         var word = stream.getUint16(pos);
  2147         pos += 2;
  2148         literals[pl++] = 0 | FACTOR_5BBP * (word >> 10 & 31);
  2149         literals[pl++] = 0 | FACTOR_5BBP * (word >> 5 & 31);
  2150         literals[pl++] = 0 | FACTOR_5BBP * (word & 31);
  2152       stream.pos = pos += bytesPerLine;
  2154     break;
  2155   case FORMAT_24BPP:
  2156     var padding;
  2157     if (hasAlpha) {
  2158       var colorType = 6;
  2159       padding = 0;
  2160       literals = new Uint8Array(width * height * 4 + height);
  2161     } else {
  2162       var colorType = 2;
  2163       padding = 1;
  2164       literals = new Uint8Array(width * height * 3 + height);
  2166     var bytesPerLine = width * 4;
  2167     var stream = createInflatedStream(bmpData, bytesPerLine * height);
  2168     var bytes = stream.bytes;
  2169     var pos = 0;
  2170     var pl = 0;
  2171     for (var y = 0; y < height; ++y) {
  2172       stream.ensure(bytesPerLine);
  2173       pl++;
  2174       for (var x = 0; x < width; ++x) {
  2175         pos += padding;
  2176         if (hasAlpha) {
  2177           var alpha = bytes[pos];
  2178           if (alpha) {
  2179             var opacity = alpha / 255;
  2180             literals[pl++] = 0 | bytes[pos + 1] / opacity;
  2181             literals[pl++] = 0 | bytes[pos + 2] / opacity;
  2182             literals[pl++] = 0 | bytes[pos + 3] / opacity;
  2183             literals[pl++] = alpha;
  2184           } else {
  2185             pl += 4;
  2187         } else {
  2188           literals[pl++] = bytes[pos];
  2189           literals[pl++] = bytes[pos + 1];
  2190           literals[pl++] = bytes[pos + 2];
  2192         pos += 4 - padding;
  2194       stream.pos = pos;
  2196     break;
  2197   default:
  2198     fail('invalid format', 'bitmap');
  2200   var ihdr = new Uint8Array([
  2201       width >> 24 & 255,
  2202       width >> 16 & 255,
  2203       width >> 8 & 255,
  2204       width & 255,
  2205       height >> 24 & 255,
  2206       height >> 16 & 255,
  2207       height >> 8 & 255,
  2208       height & 255,
  2209       8,
  2210       colorType,
  2211       0,
  2212       0,
  2214     ]);
  2215   var len = literals.length;
  2216   var maxBlockLength = 65535;
  2217   var idat = new Uint8Array(2 + len + Math.ceil(len / maxBlockLength) * 5 + 4);
  2218   var pi = 0;
  2219   idat[pi++] = 120;
  2220   idat[pi++] = 156;
  2221   var pos = 0;
  2222   while (len > maxBlockLength) {
  2223     idat[pi++] = 0;
  2224     idat[pi++] = 255;
  2225     idat[pi++] = 255;
  2226     idat[pi++] = 0;
  2227     idat[pi++] = 0;
  2228     idat.set(literals.subarray(pos, pos + maxBlockLength), pi);
  2229     pi += maxBlockLength;
  2230     pos += maxBlockLength;
  2231     len -= maxBlockLength;
  2233   idat[pi++] = 1;
  2234   idat[pi++] = len & 255;
  2235   idat[pi++] = len >> 8 & 255;
  2236   idat[pi++] = ~len & 65535 & 255;
  2237   idat[pi++] = (~len & 65535) >> 8 & 255;
  2238   idat.set(literals.subarray(pos), pi);
  2239   pi += literals.length - pos;
  2240   var adler = adler32(literals, 0, literals.length);
  2241   idat[pi++] = adler >> 24 & 255;
  2242   idat[pi++] = adler >> 16 & 255;
  2243   idat[pi++] = adler >> 8 & 255;
  2244   idat[pi++] = adler & 255;
  2245   var chunks = [
  2246       new Uint8Array([
  2247         137,
  2248         80,
  2249         78,
  2250         71,
  2251         13,
  2252         10,
  2253         26,
  2254         10
  2255       ]),
  2256       createPngChunk('IHDR', ihdr),
  2257       plte,
  2258       trns,
  2259       createPngChunk('IDAT', idat),
  2260       createPngChunk('IEND', '')
  2261     ];
  2262   return {
  2263     type: 'image',
  2264     id: tag.id,
  2265     width: width,
  2266     height: height,
  2267     mimeType: 'image/png',
  2268     data: new Blob(chunks, {
  2269       type: 'image/png'
  2270     })
  2271   };
  2273 function defineButton(tag, dictionary) {
  2274   var characters = tag.characters;
  2275   var states = {
  2276       up: {},
  2277       over: {},
  2278       down: {},
  2279       hitTest: {}
  2280     };
  2281   var i = 0, character;
  2282   while (character = characters[i++]) {
  2283     if (character.eob)
  2284       break;
  2285     var characterItem = dictionary[character.symbolId];
  2286     var entry = {
  2287         symbolId: characterItem.id,
  2288         hasMatrix: !(!character.matrix),
  2289         matrix: character.matrix
  2290       };
  2291     if (character.stateUp)
  2292       states.up[character.depth] = entry;
  2293     if (character.stateOver)
  2294       states.over[character.depth] = entry;
  2295     if (character.stateDown)
  2296       states.down[character.depth] = entry;
  2297     if (character.stateHitTest)
  2298       states.hitTest[character.depth] = entry;
  2300   var button = {
  2301       type: 'button',
  2302       id: tag.id,
  2303       buttonActions: tag.buttonActions,
  2304       states: states
  2305     };
  2306   return button;
  2308 var nextFontId = 1;
  2309 function maxPower2(num) {
  2310   var maxPower = 0;
  2311   var val = num;
  2312   while (val >= 2) {
  2313     val /= 2;
  2314     ++maxPower;
  2316   return pow(2, maxPower);
  2318 function toString16(val) {
  2319   return fromCharCode(val >> 8 & 255, val & 255);
  2321 function toString32(val) {
  2322   return toString16(val >> 16) + toString16(val);
  2324 function defineFont(tag, dictionary) {
  2325   var tables = {};
  2326   var codes = [];
  2327   var glyphIndex = {};
  2328   var ranges = [];
  2329   var glyphs = tag.glyphs;
  2330   var glyphCount = glyphs.length;
  2331   if (tag.codes) {
  2332     codes = codes.concat(tag.codes);
  2333     for (var i = 0, code; code = codes[i]; ++i)
  2334       glyphIndex[code] = i;
  2335     codes.sort(function (a, b) {
  2336       return a - b;
  2337     });
  2338     var i = 0;
  2339     var code;
  2340     while (code = codes[i++]) {
  2341       var start = code;
  2342       var end = start;
  2343       var indices = [
  2344           i - 1
  2345         ];
  2346       while ((code = codes[i]) && end + 1 === code) {
  2347         ++end;
  2348         indices.push(i);
  2349         ++i;
  2351       ranges.push([
  2352         start,
  2353         end,
  2354         indices
  2355       ]);
  2357   } else {
  2358     var indices = [];
  2359     var UAC_OFFSET = 57344;
  2360     for (var i = 0; i < glyphCount; i++) {
  2361       var code = UAC_OFFSET + i;
  2362       codes.push(code);
  2363       glyphIndex[code] = i;
  2364       indices.push(i);
  2366     ranges.push([
  2367       UAC_OFFSET,
  2368       UAC_OFFSET + glyphCount - 1,
  2369       indices
  2370     ]);
  2372   var resolution = tag.resolution || 1;
  2373   var ascent = Math.ceil(tag.ascent / resolution) || 1024;
  2374   var descent = -Math.ceil(tag.descent / resolution) | 0;
  2375   var leading = tag.leading / resolution | 0;
  2376   tables['OS/2'] = '\0\x01\0\0' + toString16(tag.bold ? 700 : 400) + '\0\x05' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0\0\0\0\0\0\0\0\0' + '\0\0\0\0' + '\0\0\0\0' + '\0\0\0\0' + '\0\0\0\0' + 'ALF ' + toString16((tag.italic ? 1 : 0) | (tag.bold ? 32 : 0)) + toString16(codes[0]) + toString16(codes[codes.length - 1]) + toString16(ascent) + toString16(descent) + toString16(leading) + toString16(ascent) + toString16(-descent) + '\0\0\0\0' + '\0\0\0\0';
  2378   var startCount = '';
  2379   var endCount = '';
  2380   var idDelta = '';
  2381   var idRangeOffset = '';
  2382   var i = 0;
  2383   var range;
  2384   while (range = ranges[i++]) {
  2385     var start = range[0];
  2386     var end = range[1];
  2387     var code = range[2][0];
  2388     startCount += toString16(start);
  2389     endCount += toString16(end);
  2390     idDelta += toString16(code - start + 1 & 65535);
  2391     idRangeOffset += toString16(0);
  2393   endCount += '\xff\xff';
  2394   startCount += '\xff\xff';
  2395   idDelta += '\0\x01';
  2396   idRangeOffset += '\0\0';
  2397   var segCount = ranges.length + 1;
  2398   var searchRange = maxPower2(segCount) * 2;
  2399   var rangeShift = 2 * segCount - searchRange;
  2400   var format314 = '\0\0' + toString16(segCount * 2) + toString16(searchRange) + toString16(logE(segCount) / logE(2)) + toString16(rangeShift) + endCount + '\0\0' + startCount + idDelta + idRangeOffset;
  2402   tables['cmap'] = '\0\0\0\x01\0\x03\0\x01\0\0\0\f\0\x04' + toString16(format314.length + 4) + format314;
  2404   var glyf = '\0\x01\0\0\0\0\0\0\0\0\0\0\0\x001\0';
  2405   var loca = '\0\0';
  2406   var offset = 16;
  2407   var maxPoints = 0;
  2408   var xMins = [];
  2409   var xMaxs = [];
  2410   var yMins = [];
  2411   var yMaxs = [];
  2412   var maxContours = 0;
  2413   var i = 0;
  2414   var code;
  2415   while (code = codes[i++]) {
  2416     var glyph = glyphs[glyphIndex[code]];
  2417     var records = glyph.records;
  2418     var numberOfContours = 1;
  2419     var endPoint = 0;
  2420     var endPtsOfContours = '';
  2421     var flags = '';
  2422     var xCoordinates = '';
  2423     var yCoordinates = '';
  2424     var x = 0;
  2425     var y = 0;
  2426     var xMin = 1024;
  2427     var xMax = -1024;
  2428     var yMin = 1024;
  2429     var yMax = -1024;
  2430     for (var j = 0, record; record = records[j]; ++j) {
  2431       if (record.type) {
  2432         if (record.isStraight) {
  2433           if (record.isGeneral) {
  2434             flags += '\x01';
  2435             var dx = record.deltaX / resolution;
  2436             var dy = -record.deltaY / resolution;
  2437             xCoordinates += toString16(dx);
  2438             yCoordinates += toString16(dy);
  2439             x += dx;
  2440             y += dy;
  2441           } else if (record.isVertical) {
  2442             flags += '\x11';
  2443             var dy = -record.deltaY / resolution;
  2444             yCoordinates += toString16(dy);
  2445             y += dy;
  2446           } else {
  2447             flags += '!';
  2448             var dx = record.deltaX / resolution;
  2449             xCoordinates += toString16(dx);
  2450             x += dx;
  2452         } else {
  2453           flags += '\0';
  2454           var cx = record.controlDeltaX / resolution;
  2455           var cy = -record.controlDeltaY / resolution;
  2456           xCoordinates += toString16(cx);
  2457           yCoordinates += toString16(cy);
  2458           flags += '\x01';
  2459           var dx = record.anchorDeltaX / resolution;
  2460           var dy = -record.anchorDeltaY / resolution;
  2461           xCoordinates += toString16(dx);
  2462           yCoordinates += toString16(dy);
  2463           ++endPoint;
  2464           x += cx + dx;
  2465           y += cy + dy;
  2467         if (x < xMin)
  2468           xMin = x;
  2469         if (x > xMax)
  2470           xMax = x;
  2471         if (y < yMin)
  2472           yMin = y;
  2473         if (y > yMax)
  2474           yMax = y;
  2475         ++endPoint;
  2476       } else {
  2477         if (record.eos)
  2478           break;
  2479         if (record.move) {
  2480           if (endPoint) {
  2481             ++numberOfContours;
  2482             endPtsOfContours += toString16(endPoint - 1);
  2484           flags += '\x01';
  2485           var moveX = record.moveX / resolution;
  2486           var moveY = -record.moveY / resolution;
  2487           var dx = moveX - x;
  2488           var dy = moveY - y;
  2489           xCoordinates += toString16(dx);
  2490           yCoordinates += toString16(dy);
  2491           x = moveX;
  2492           y = moveY;
  2493           if (endPoint > maxPoints)
  2494             maxPoints = endPoint;
  2495           if (x < xMin)
  2496             xMin = x;
  2497           if (x > xMax)
  2498             xMax = x;
  2499           if (y < yMin)
  2500             yMin = y;
  2501           if (y > yMax)
  2502             yMax = y;
  2503           ++endPoint;
  2507     endPtsOfContours += toString16((endPoint || 1) - 1);
  2508     if (!j) {
  2509       xMin = xMax = yMin = yMax = 0;
  2510       flags += '1';
  2512     var entry = toString16(numberOfContours) + toString16(xMin) + toString16(yMin) + toString16(xMax) + toString16(yMax) + endPtsOfContours + '\0\0' + flags + xCoordinates + yCoordinates;
  2514     if (entry.length & 1)
  2515       entry += '\0';
  2516     glyf += entry;
  2517     loca += toString16(offset / 2);
  2518     offset += entry.length;
  2519     xMins.push(xMin);
  2520     xMaxs.push(xMax);
  2521     yMins.push(yMin);
  2522     yMaxs.push(yMax);
  2523     if (numberOfContours > maxContours)
  2524       maxContours = numberOfContours;
  2525     if (endPoint > maxPoints)
  2526       maxPoints = endPoint;
  2528   loca += toString16(offset / 2);
  2529   tables['glyf'] = glyf;
  2530   tables['head'] = '\0\x01\0\0\0\x01\0\0\0\0\0\0_\x0f<\xf5\0\v\x04\0\0\0\0\0' + toString32(Date.now()) + '\0\0\0\0' + toString32(Date.now()) + toString16(min.apply(null, xMins)) + toString16(min.apply(null, yMins)) + toString16(max.apply(null, xMaxs)) + toString16(max.apply(null, yMaxs)) + toString16((tag.italic ? 2 : 0) | (tag.bold ? 1 : 0)) + '\0\b' + '\0\x02' + '\0\0' + '\0\0';
  2532   var advance = tag.advance;
  2533   tables['hhea'] = '\0\x01\0\0' + toString16(ascent) + toString16(descent) + toString16(leading) + toString16(advance ? max.apply(null, advance) : 1024) + '\0\0' + '\0\0' + '\x03\xb8' + '\0\x01' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + toString16(glyphCount + 1);
  2535   var hmtx = '\0\0\0\0';
  2536   for (var i = 0; i < glyphCount; ++i)
  2537     hmtx += toString16(advance ? advance[i] / resolution : 1024) + '\0\0';
  2538   tables['hmtx'] = hmtx;
  2539   if (tag.kerning) {
  2540     var kerning = tag.kerning;
  2541     var nPairs = kerning.length;
  2542     var searchRange = maxPower2(nPairs) * 2;
  2543     var kern = '\0\0\0\x01\0\0' + toString16(14 + nPairs * 6) + '\0\x01' + toString16(nPairs) + toString16(searchRange) + toString16(logE(nPairs) / logE(2)) + toString16(2 * nPairs - searchRange);
  2545     var i = 0;
  2546     var record;
  2547     while (record = kerning[i++]) {
  2548       kern += toString16(glyphIndex[record.code1]) + toString16(glyphIndex[record.code2]) + toString16(record.adjustment);
  2551     tables['kern'] = kern;
  2553   tables['loca'] = loca;
  2554   tables['maxp'] = '\0\x01\0\0' + toString16(glyphCount + 1) + toString16(maxPoints) + toString16(maxContours) + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0' + '\0\0';
  2556   var uniqueId = 'swf-font-' + nextFontId++;
  2557   var fontName = tag.name || uniqueId;
  2558   var psName = fontName.replace(/ /g, '');
  2559   var strings = [
  2560       tag.copyright || 'Original licence',
  2561       fontName,
  2562       'Unknown',
  2563       uniqueId,
  2564       fontName,
  2565       '1.0',
  2566       psName,
  2567       'Unknown',
  2568       'Unknown',
  2569       'Unknown'
  2570     ];
  2571   var count = strings.length;
  2572   var name = '\0\0' + toString16(count) + toString16(count * 12 + 6);
  2573   var offset = 0;
  2574   var i = 0;
  2575   var str;
  2576   while (str = strings[i++]) {
  2577     name += '\0\x01\0\0\0\0' + toString16(i - 1) + toString16(str.length) + toString16(offset);
  2578     offset += str.length;
  2580   tables['name'] = name + strings.join('');
  2581   tables['post'] = '\0\x03\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0\0';
  2583   var names = keys(tables);
  2584   var numTables = names.length;
  2585   var header = '\0\x01\0\0' + toString16(numTables) + '\0\x80' + '\0\x03' + '\0 ';
  2587   var data = '';
  2588   var offset = numTables * 16 + header.length;
  2589   var i = 0;
  2590   var name;
  2591   while (name = names[i++]) {
  2592     var table = tables[name];
  2593     var length = table.length;
  2594     header += name + '\0\0\0\0' + toString32(offset) + toString32(length);
  2596     while (length & 3) {
  2597       table += '\0';
  2598       ++length;
  2600     data += table;
  2601     while (offset & 3)
  2602       ++offset;
  2603     offset += length;
  2605   var otf = header + data;
  2606   var unitPerEm = 1024;
  2607   var metrics = {
  2608       ascent: ascent / unitPerEm,
  2609       descent: -descent / unitPerEm,
  2610       leading: leading / unitPerEm
  2611     };
  2612   return {
  2613     type: 'font',
  2614     id: tag.id,
  2615     name: fontName,
  2616     uniqueName: psName + uniqueId,
  2617     codes: codes,
  2618     metrics: metrics,
  2619     bold: tag.bold === 1,
  2620     italic: tag.italic === 1,
  2621     data: otf
  2622   };
  2624 function getUint16(buff, pos) {
  2625   return buff[pos] << 8 | buff[pos + 1];
  2627 function parseJpegChunks(imgDef, bytes) {
  2628   var i = 0;
  2629   var n = bytes.length;
  2630   var chunks = [];
  2631   var code;
  2632   do {
  2633     var begin = i;
  2634     while (i < n && bytes[i] !== 255)
  2635       ++i;
  2636     while (i < n && bytes[i] === 255)
  2637       ++i;
  2638     code = bytes[i++];
  2639     if (code === 218) {
  2640       i = n;
  2641     } else if (code === 217) {
  2642       i += 2;
  2643       continue;
  2644     } else if (code < 208 || code > 216) {
  2645       var length = getUint16(bytes, i);
  2646       if (code >= 192 && code <= 195) {
  2647         imgDef.height = getUint16(bytes, i + 3);
  2648         imgDef.width = getUint16(bytes, i + 5);
  2650       i += length;
  2652     chunks.push(bytes.subarray(begin, i));
  2653   } while (i < n);
  2654   return chunks;
  2656 function defineImage(tag, dictionary) {
  2657   var img = {
  2658       type: 'image',
  2659       id: tag.id,
  2660       mimeType: tag.mimeType
  2661     };
  2662   var imgData = tag.imgData;
  2663   var chunks;
  2664   if (tag.mimeType === 'image/jpeg') {
  2665     chunks = parseJpegChunks(img, imgData);
  2666     var alphaData = tag.alphaData;
  2667     if (alphaData) {
  2668       img.mask = createInflatedStream(alphaData, img.width * img.height).bytes;
  2670     if (tag.incomplete) {
  2671       var tables = dictionary[0];
  2672       var header = tables.data;
  2673       if (header && header.size) {
  2674         chunks[0] = chunks[0].subarray(2);
  2675         chunks.unshift(header.slice(0, header.size - 2));
  2678   } else {
  2679     chunks = [
  2680       imgData
  2681     ];
  2683   img.data = new Blob(chunks, {
  2684     type: tag.mimeType
  2685   });
  2686   return img;
  2688 function defineLabel(tag, dictionary) {
  2689   var records = tag.records;
  2690   var m = tag.matrix;
  2691   var cmds = [
  2692       'c.save()',
  2693       'c.transform(' + [
  2694         m.a,
  2695         m.b,
  2696         m.c,
  2697         m.d,
  2698         m.tx / 20,
  2699         m.ty / 20
  2700       ].join(',') + ')',
  2701       'c.scale(0.05, 0.05)'
  2702     ];
  2703   var dependencies = [];
  2704   var x = 0;
  2705   var y = 0;
  2706   var i = 0;
  2707   var record;
  2708   var codes;
  2709   while (record = records[i++]) {
  2710     if (record.eot)
  2711       break;
  2712     if (record.hasFont) {
  2713       var font = dictionary[record.fontId];
  2714       codes = font.codes;
  2715       cmds.push('c.font="' + record.fontHeight + 'px \'' + font.uniqueName + '\'"');
  2716       dependencies.push(font.id);
  2718     if (record.hasColor) {
  2719       cmds.push('ct.setFillStyle(c,"' + rgbaObjToStr(record.color) + '")');
  2720       cmds.push('ct.setAlpha(c)');
  2721     } else {
  2722       cmds.push('ct.setAlpha(c,true)');
  2724     if (record.hasMoveX)
  2725       x = record.moveX;
  2726     if (record.hasMoveY)
  2727       y = record.moveY;
  2728     var entries = record.entries;
  2729     var j = 0;
  2730     var entry;
  2731     while (entry = entries[j++]) {
  2732       var code = codes[entry.glyphIndex];
  2733       var text = code >= 32 && code != 34 && code != 92 ? fromCharCode(code) : '\\u' + (code + 65536).toString(16).substring(1);
  2734       cmds.push('c.fillText("' + text + '",' + x + ',' + y + ')');
  2735       x += entry.advance;
  2738   cmds.push('c.restore()');
  2739   var label = {
  2740       type: 'label',
  2741       id: tag.id,
  2742       bbox: tag.bbox,
  2743       data: cmds.join('\n')
  2744     };
  2745   if (dependencies.length)
  2746     label.require = dependencies;
  2747   return label;
  2749 var GRAPHICS_FILL_CLIPPED_BITMAP = 65;
  2750 var GRAPHICS_FILL_FOCAL_RADIAL_GRADIENT = 19;
  2751 var GRAPHICS_FILL_LINEAR_GRADIENT = 16;
  2752 var GRAPHICS_FILL_NONSMOOTHED_CLIPPED_BITMAP = 67;
  2753 var GRAPHICS_FILL_NONSMOOTHED_REPEATING_BITMAP = 66;
  2754 var GRAPHICS_FILL_RADIAL_GRADIENT = 18;
  2755 var GRAPHICS_FILL_REPEATING_BITMAP = 64;
  2756 var GRAPHICS_FILL_SOLID = 0;
  2757 function applySegmentToStyles(segment, styles, linePaths, fillPaths, isMorph) {
  2758   if (!segment) {
  2759     return;
  2761   var commands = segment.commands;
  2762   var data = segment.data;
  2763   var morphData = segment.morphData;
  2764   if (morphData) {
  2766   var path;
  2767   var targetSegment;
  2768   var command;
  2769   var i;
  2770   if (styles.fill0) {
  2771     path = fillPaths[styles.fill0 - 1];
  2772     if (!(styles.fill1 || styles.line)) {
  2773       targetSegment = path.head();
  2774       targetSegment.commands = [];
  2775       targetSegment.data = [];
  2776       targetSegment.morphData = isMorph ? [] : null;
  2777     } else {
  2778       targetSegment = path.addSegment([], [], isMorph ? [] : null);
  2780     var targetCommands = targetSegment.commands;
  2781     var targetData = targetSegment.data;
  2782     var targetMorphData = targetSegment.morphData;
  2783     targetCommands.push(SHAPE_MOVE_TO);
  2784     var j = data.length - 2;
  2785     targetData.push(data[j], data[j + 1]);
  2786     if (isMorph) {
  2787       targetMorphData.push(morphData[j], morphData[j + 1]);
  2789     for (i = commands.length; i-- > 1; j -= 2) {
  2790       command = commands[i];
  2791       targetCommands.push(command);
  2792       targetData.push(data[j - 2], data[j - 1]);
  2793       if (isMorph) {
  2794         targetMorphData.push(morphData[j - 2], morphData[j - 1]);
  2796       if (command === SHAPE_CURVE_TO) {
  2797         targetData.push(data[j - 4], data[j - 3]);
  2798         if (isMorph) {
  2799           targetMorphData.push(morphData[j - 4], morphData[j - 3]);
  2801         j -= 2;
  2804     if (isMorph) {
  2807   if (styles.line && styles.fill1) {
  2808     path = linePaths[styles.line - 1];
  2809     path.addSegment(commands, data, morphData);
  2812 function convertRecordsToStyledPaths(records, fillPaths, linePaths, dictionary, dependencies, recordsMorph, transferables) {
  2813   var isMorph = recordsMorph !== null;
  2814   var styles = {
  2815       fill0: 0,
  2816       fill1: 0,
  2817       line: 0
  2818     };
  2819   var segment = null;
  2820   var allPaths;
  2821   var defaultPath;
  2822   var numRecords = records.length - 1;
  2823   var x = 0;
  2824   var y = 0;
  2825   var morphX = 0;
  2826   var morphY = 0;
  2827   var path;
  2828   for (var i = 0, j = 0; i < numRecords; i++) {
  2829     var record = records[i];
  2830     var morphRecord;
  2831     if (isMorph) {
  2832       morphRecord = recordsMorph[j++];
  2834     if (record.type === 0) {
  2835       if (segment) {
  2836         applySegmentToStyles(segment, styles, linePaths, fillPaths, isMorph);
  2838       if (record.hasNewStyles) {
  2839         if (!allPaths) {
  2840           allPaths = [];
  2842         push.apply(allPaths, fillPaths);
  2843         fillPaths = createPathsList(record.fillStyles, false, dictionary, dependencies);
  2844         push.apply(allPaths, linePaths);
  2845         linePaths = createPathsList(record.lineStyles, true, dictionary, dependencies);
  2846         if (defaultPath) {
  2847           allPaths.push(defaultPath);
  2848           defaultPath = null;
  2850         styles = {
  2851           fill0: 0,
  2852           fill1: 0,
  2853           line: 0
  2854         };
  2856       if (record.hasFillStyle0) {
  2857         styles.fill0 = record.fillStyle0;
  2859       if (record.hasFillStyle1) {
  2860         styles.fill1 = record.fillStyle1;
  2862       if (record.hasLineStyle) {
  2863         styles.line = record.lineStyle;
  2865       if (styles.fill1) {
  2866         path = fillPaths[styles.fill1 - 1];
  2867       } else if (styles.line) {
  2868         path = linePaths[styles.line - 1];
  2869       } else if (styles.fill0) {
  2870         path = fillPaths[styles.fill0 - 1];
  2872       if (record.move) {
  2873         x = record.moveX | 0;
  2874         y = record.moveY | 0;
  2876       if (path) {
  2877         segment = path.addSegment([], [], isMorph ? [] : null);
  2878         segment.commands.push(SHAPE_MOVE_TO);
  2879         segment.data.push(x, y);
  2880         if (isMorph) {
  2881           if (morphRecord.type === 0) {
  2882             morphX = morphRecord.moveX | 0;
  2883             morphY = morphRecord.moveY | 0;
  2884           } else {
  2885             morphX = x;
  2886             morphY = y;
  2887             j--;
  2889           segment.morphData.push(morphX, morphY);
  2892     } else {
  2893       if (!segment) {
  2894         if (!defaultPath) {
  2895           var style = {
  2896               color: {
  2897                 red: 0,
  2898                 green: 0,
  2899                 blue: 0,
  2900                 alpha: 255
  2901               },
  2902               width: 20
  2903             };
  2904           defaultPath = new SegmentedPath(null, processStyle(style, true));
  2906         segment = defaultPath.addSegment([], [], isMorph ? [] : null);
  2907         segment.commands.push(SHAPE_MOVE_TO);
  2908         segment.data.push(x, y);
  2909         if (isMorph) {
  2910           segment.morphData.push(morphX, morphY);
  2913       if (isMorph) {
  2914         while (morphRecord && morphRecord.type === 0) {
  2915           morphRecord = recordsMorph[j++];
  2917         if (!morphRecord) {
  2918           morphRecord = record;
  2921       if (record.isStraight && (!isMorph || morphRecord.isStraight)) {
  2922         x += record.deltaX | 0;
  2923         y += record.deltaY | 0;
  2924         segment.commands.push(SHAPE_LINE_TO);
  2925         segment.data.push(x, y);
  2926         if (isMorph) {
  2927           morphX += morphRecord.deltaX | 0;
  2928           morphY += morphRecord.deltaY | 0;
  2929           segment.morphData.push(morphX, morphY);
  2931       } else {
  2932         var cx, cy;
  2933         var deltaX, deltaY;
  2934         if (!record.isStraight) {
  2935           cx = x + record.controlDeltaX | 0;
  2936           cy = y + record.controlDeltaY | 0;
  2937           x = cx + record.anchorDeltaX | 0;
  2938           y = cy + record.anchorDeltaY | 0;
  2939         } else {
  2940           deltaX = record.deltaX | 0;
  2941           deltaY = record.deltaY | 0;
  2942           cx = x + (deltaX >> 1);
  2943           cy = y + (deltaY >> 1);
  2944           x += deltaX;
  2945           y += deltaY;
  2947         segment.commands.push(SHAPE_CURVE_TO);
  2948         segment.data.push(cx, cy, x, y);
  2949         if (isMorph) {
  2950           if (!morphRecord.isStraight) {
  2951             cx = morphX + morphRecord.controlDeltaX | 0;
  2952             cy = morphY + morphRecord.controlDeltaY | 0;
  2953             morphX = cx + morphRecord.anchorDeltaX | 0;
  2954             morphY = cy + morphRecord.anchorDeltaY | 0;
  2955           } else {
  2956             deltaX = morphRecord.deltaX | 0;
  2957             deltaY = morphRecord.deltaY | 0;
  2958             cx = morphX + (deltaX >> 1);
  2959             cy = morphY + (deltaY >> 1);
  2960             morphX += deltaX;
  2961             morphY += deltaY;
  2963           segment.morphData.push(cx, cy, morphX, morphY);
  2968   applySegmentToStyles(segment, styles, linePaths, fillPaths, isMorph);
  2969   if (allPaths) {
  2970     push.apply(allPaths, fillPaths);
  2971   } else {
  2972     allPaths = fillPaths;
  2974   push.apply(allPaths, linePaths);
  2975   if (defaultPath) {
  2976     allPaths.push(defaultPath);
  2978   var removeCount = 0;
  2979   for (i = 0; i < allPaths.length; i++) {
  2980     path = allPaths[i];
  2981     if (!path.head()) {
  2982       removeCount++;
  2983       continue;
  2985     allPaths[i - removeCount] = segmentedPathToShapePath(path, isMorph, transferables);
  2987   allPaths.length -= removeCount;
  2988   return allPaths;
  2990 function segmentedPathToShapePath(path, isMorph, transferables) {
  2991   var start = path.head();
  2992   var end = start;
  2993   var finalRoot = null;
  2994   var finalHead = null;
  2995   var skippedMoves = 0;
  2996   var current = start.prev;
  2997   while (start) {
  2998     while (current) {
  2999       if (path.segmentsConnect(current, start)) {
  3000         if (current.next !== start) {
  3001           path.removeSegment(current);
  3002           path.insertSegment(current, start);
  3004         start = current;
  3005         current = start.prev;
  3006         skippedMoves++;
  3007         continue;
  3009       if (path.segmentsConnect(end, current)) {
  3010         path.removeSegment(current);
  3011         end.next = current;
  3012         current = current.prev;
  3013         end.next.prev = end;
  3014         end.next.next = null;
  3015         end = end.next;
  3016         skippedMoves++;
  3017         continue;
  3019       current = current.prev;
  3021     current = start.prev;
  3022     if (!finalRoot) {
  3023       finalRoot = start;
  3024       finalHead = end;
  3025     } else {
  3026       finalHead.next = start;
  3027       start.prev = finalHead;
  3028       finalHead = end;
  3029       finalHead.next = null;
  3031     if (!current) {
  3032       break;
  3034     start = end = current;
  3035     current = start.prev;
  3037   var totalCommandsLength = -skippedMoves;
  3038   var totalDataLength = -skippedMoves << 1;
  3039   current = finalRoot;
  3040   while (current) {
  3041     totalCommandsLength += current.commands.length;
  3042     totalDataLength += current.data.length;
  3043     current = current.next;
  3045   var shape = new ShapePath(path.fillStyle, path.lineStyle, totalCommandsLength, totalDataLength, isMorph, transferables);
  3046   var allCommands = shape.commands;
  3047   var allData = shape.data;
  3048   var allMorphData = shape.morphData;
  3049   var commandsIndex = 0;
  3050   var dataIndex = 0;
  3051   current = finalRoot;
  3052   while (current) {
  3053     var commands = current.commands;
  3054     var data = current.data;
  3055     var morphData = current.morphData;
  3056     var offset = +(data[0] === allData[dataIndex - 2] && data[1] === allData[dataIndex - 1]);
  3057     for (var i = offset; i < commands.length; i++, commandsIndex++) {
  3058       allCommands[commandsIndex] = commands[i];
  3060     for (i = offset << 1; i < data.length; i++, dataIndex++) {
  3061       allData[dataIndex] = data[i];
  3062       if (isMorph) {
  3063         allMorphData[dataIndex] = morphData[i];
  3066     current = current.next;
  3068   return shape;
  3070 var CAPS_STYLE_TYPES = [
  3071     'round',
  3072     'none',
  3073     'square'
  3074   ];
  3075 var JOIN_STYLE_TYPES = [
  3076     'round',
  3077     'bevel',
  3078     'miter'
  3079   ];
  3080 function processStyle(style, isLineStyle, dictionary, dependencies) {
  3081   if (isLineStyle) {
  3082     style.lineCap = CAPS_STYLE_TYPES[style.endCapStyle | 0];
  3083     style.lineJoin = JOIN_STYLE_TYPES[style.joinStyle | 0];
  3084     style.miterLimit = (style.miterLimitFactor || 1.5) * 2;
  3085     if (!style.color && style.hasFill) {
  3086       var fillStyle = processStyle(style.fillStyle, false, dictionary, dependencies);
  3087       style.style = fillStyle.style;
  3088       style.type = fillStyle.type;
  3089       style.transform = fillStyle.transform;
  3090       style.records = fillStyle.records;
  3091       style.focalPoint = fillStyle.focalPoint;
  3092       style.bitmapId = fillStyle.bitmapId;
  3093       style.repeat = fillStyle.repeat;
  3094       style.fillStyle = null;
  3095       return style;
  3098   var color;
  3099   if (style.type === undefined || style.type === GRAPHICS_FILL_SOLID) {
  3100     color = style.color;
  3101     style.style = 'rgba(' + color.red + ',' + color.green + ',' + color.blue + ',' + color.alpha / 255 + ')';
  3102     style.color = null;
  3103     return style;
  3105   var scale;
  3106   switch (style.type) {
  3107   case GRAPHICS_FILL_LINEAR_GRADIENT:
  3108   case GRAPHICS_FILL_RADIAL_GRADIENT:
  3109   case GRAPHICS_FILL_FOCAL_RADIAL_GRADIENT:
  3110     scale = 819.2;
  3111     break;
  3112   case GRAPHICS_FILL_REPEATING_BITMAP:
  3113   case GRAPHICS_FILL_CLIPPED_BITMAP:
  3114   case GRAPHICS_FILL_NONSMOOTHED_REPEATING_BITMAP:
  3115   case GRAPHICS_FILL_NONSMOOTHED_CLIPPED_BITMAP:
  3116     if (dictionary[style.bitmapId]) {
  3117       dependencies.push(dictionary[style.bitmapId].id);
  3118       scale = 0.05;
  3120     break;
  3121   default:
  3122     fail('invalid fill style', 'shape');
  3124   if (!style.matrix) {
  3125     return style;
  3127   var matrix = style.matrix;
  3128   style.transform = {
  3129     a: matrix.a * scale,
  3130     b: matrix.b * scale,
  3131     c: matrix.c * scale,
  3132     d: matrix.d * scale,
  3133     e: matrix.tx,
  3134     f: matrix.ty
  3135   };
  3136   style.matrix = null;
  3137   return style;
  3139 function createPathsList(styles, isLineStyle, dictionary, dependencies) {
  3140   var paths = [];
  3141   for (var i = 0; i < styles.length; i++) {
  3142     var style = processStyle(styles[i], isLineStyle, dictionary, dependencies);
  3143     if (!isLineStyle) {
  3144       paths[i] = new SegmentedPath(style, null);
  3145     } else {
  3146       paths[i] = new SegmentedPath(null, style);
  3149   return paths;
  3151 function defineShape(tag, dictionary) {
  3152   var dependencies = [];
  3153   var transferables = [];
  3154   var fillPaths = createPathsList(tag.fillStyles, false, dictionary, dependencies);
  3155   var linePaths = createPathsList(tag.lineStyles, true, dictionary, dependencies);
  3156   var paths = convertRecordsToStyledPaths(tag.records, fillPaths, linePaths, dictionary, dependencies, tag.recordsMorph || null, transferables);
  3157   if (tag.bboxMorph) {
  3158     var mbox = tag.bboxMorph;
  3159     extendBoundsByPoint(tag.bbox, mbox.xMin, mbox.yMin);
  3160     extendBoundsByPoint(tag.bbox, mbox.xMax, mbox.yMax);
  3161     mbox = tag.strokeBboxMorph;
  3162     if (mbox) {
  3163       extendBoundsByPoint(tag.strokeBbox, mbox.xMin, mbox.yMin);
  3164       extendBoundsByPoint(tag.strokeBbox, mbox.xMax, mbox.yMax);
  3167   return {
  3168     type: 'shape',
  3169     id: tag.id,
  3170     strokeBbox: tag.strokeBbox,
  3171     strokeBboxMorph: tag.strokeBboxMorph,
  3172     bbox: tag.bbox,
  3173     bboxMorph: tag.bboxMorph,
  3174     isMorph: tag.isMorph,
  3175     paths: paths,
  3176     require: dependencies.length ? dependencies : null,
  3177     transferables: transferables
  3178   };
  3180 function logShape(paths, bbox) {
  3181   var output = '{"bounds":' + JSON.stringify(bbox) + ',"paths":[' + paths.map(function (path) {
  3182       return path.serialize();
  3183     }).join() + ']}';
  3184   console.log(output);
  3186 function SegmentedPath(fillStyle, lineStyle) {
  3187   this.fillStyle = fillStyle;
  3188   this.lineStyle = lineStyle;
  3189   this._head = null;
  3191 SegmentedPath.prototype = {
  3192   addSegment: function (commands, data, morphData) {
  3193     var segment = {
  3194         commands: commands,
  3195         data: data,
  3196         morphData: morphData,
  3197         prev: this._head,
  3198         next: null
  3199       };
  3200     if (this._head) {
  3201       this._head.next = segment;
  3203     this._head = segment;
  3204     return segment;
  3205   },
  3206   removeSegment: function (segment) {
  3207     if (segment.prev) {
  3208       segment.prev.next = segment.next;
  3210     if (segment.next) {
  3211       segment.next.prev = segment.prev;
  3213   },
  3214   insertSegment: function (segment, next) {
  3215     var prev = next.prev;
  3216     segment.prev = prev;
  3217     segment.next = next;
  3218     if (prev) {
  3219       prev.next = segment;
  3221     next.prev = segment;
  3222   },
  3223   head: function () {
  3224     return this._head;
  3225   },
  3226   segmentsConnect: function (first, second) {
  3227     var firstLength = first.data.length;
  3228     return first.data[firstLength - 2] === second.data[0] && first.data[firstLength - 1] === second.data[1];
  3230 };
  3231 var SHAPE_MOVE_TO = 1;
  3232 var SHAPE_LINE_TO = 2;
  3233 var SHAPE_CURVE_TO = 3;
  3234 var SHAPE_WIDE_MOVE_TO = 4;
  3235 var SHAPE_WIDE_LINE_TO = 5;
  3236 var SHAPE_CUBIC_CURVE_TO = 6;
  3237 var SHAPE_CIRCLE = 7;
  3238 var SHAPE_ELLIPSE = 8;
  3239 function ShapePath(fillStyle, lineStyle, commandsCount, dataLength, isMorph, transferables) {
  3240   this.fillStyle = fillStyle;
  3241   this.lineStyle = lineStyle;
  3242   if (commandsCount) {
  3243     this.commands = new Uint8Array(commandsCount);
  3244     this.data = new Int32Array(dataLength);
  3245     this.morphData = isMorph ? new Int32Array(dataLength) : null;
  3246   } else {
  3247     this.commands = [];
  3248     this.data = [];
  3250   this.bounds = null;
  3251   this.strokeBounds = null;
  3252   this.isMorph = !(!isMorph);
  3253   this.fullyInitialized = false;
  3254   if (inWorker) {
  3255     this.buffers = [
  3256       this.commands.buffer,
  3257       this.data.buffer
  3258     ];
  3259     transferables.push(this.commands.buffer, this.data.buffer);
  3260     if (isMorph) {
  3261       this.buffers.push(this.morphData.buffer);
  3262       transferables.push(this.morphData.buffer);
  3264   } else {
  3265     this.buffers = null;
  3268 ShapePath.prototype = {
  3269   get isEmpty() {
  3270     return this.commands.length === 0;
  3271   },
  3272   moveTo: function (x, y) {
  3273     if (this.commands[this.commands.length - 1] === SHAPE_MOVE_TO) {
  3274       this.data[this.data.length - 2] = x;
  3275       this.data[this.data.length - 1] = y;
  3276       return;
  3278     this.commands.push(SHAPE_MOVE_TO);
  3279     this.data.push(x, y);
  3280   },
  3281   lineTo: function (x, y) {
  3282     this.commands.push(SHAPE_LINE_TO);
  3283     this.data.push(x, y);
  3284   },
  3285   curveTo: function (controlX, controlY, anchorX, anchorY) {
  3286     this.commands.push(SHAPE_CURVE_TO);
  3287     this.data.push(controlX, controlY, anchorX, anchorY);
  3288   },
  3289   cubicCurveTo: function (control1X, control1Y, control2X, control2Y, anchorX, anchorY) {
  3290     this.commands.push(SHAPE_CUBIC_CURVE_TO);
  3291     this.data.push(control1X, control1Y, control2X, control2Y, anchorX, anchorY);
  3292   },
  3293   rect: function (x, y, w, h) {
  3294     var x2 = x + w;
  3295     var y2 = y + h;
  3296     this.commands.push(SHAPE_MOVE_TO, SHAPE_LINE_TO, SHAPE_LINE_TO, SHAPE_LINE_TO, SHAPE_LINE_TO);
  3297     this.data.push(x, y, x2, y, x2, y2, x, y2, x, y);
  3298   },
  3299   circle: function (x, y, radius) {
  3300     this.commands.push(SHAPE_CIRCLE);
  3301     this.data.push(x, y, radius);
  3302   },
  3303   ellipse: function (x, y, radiusX, radiusY) {
  3304     this.commands.push(SHAPE_ELLIPSE);
  3305     this.data.push(x, y, radiusX, radiusY);
  3306   },
  3307   draw: function (ctx, clip, ratio, colorTransform) {
  3308     if (clip && !this.fillStyle) {
  3309       return;
  3311     ctx.beginPath();
  3312     var commands = this.commands;
  3313     var data = this.data;
  3314     var morphData = this.morphData;
  3315     var formOpen = false;
  3316     var formOpenX = 0;
  3317     var formOpenY = 0;
  3318     if (!this.isMorph) {
  3319       for (var j = 0, k = 0; j < commands.length; j++) {
  3320         switch (commands[j]) {
  3321         case SHAPE_MOVE_TO:
  3322           formOpen = true;
  3323           formOpenX = data[k++] / 20;
  3324           formOpenY = data[k++] / 20;
  3325           ctx.moveTo(formOpenX, formOpenY);
  3326           break;
  3327         case SHAPE_WIDE_MOVE_TO:
  3328           ctx.moveTo(data[k++] / 20, data[k++] / 20);
  3329           k += 2;
  3330           break;
  3331         case SHAPE_LINE_TO:
  3332           ctx.lineTo(data[k++] / 20, data[k++] / 20);
  3333           break;
  3334         case SHAPE_WIDE_LINE_TO:
  3335           ctx.lineTo(data[k++] / 20, data[k++] / 20);
  3336           k += 2;
  3337           break;
  3338         case SHAPE_CURVE_TO:
  3339           ctx.quadraticCurveTo(data[k++] / 20, data[k++] / 20, data[k++] / 20, data[k++] / 20);
  3340           break;
  3341         case SHAPE_CUBIC_CURVE_TO:
  3342           ctx.bezierCurveTo(data[k++] / 20, data[k++] / 20, data[k++] / 20, data[k++] / 20, data[k++] / 20, data[k++] / 20);
  3343           break;
  3344         case SHAPE_CIRCLE:
  3345           if (formOpen) {
  3346             ctx.lineTo(formOpenX, formOpenY);
  3347             formOpen = false;
  3349           ctx.moveTo((data[k] + data[k + 2]) / 20, data[k + 1] / 20);
  3350           ctx.arc(data[k++] / 20, data[k++] / 20, data[k++] / 20, 0, Math.PI * 2, false);
  3351           break;
  3352         case SHAPE_ELLIPSE:
  3353           if (formOpen) {
  3354             ctx.lineTo(formOpenX, formOpenY);
  3355             formOpen = false;
  3357           var x = data[k++];
  3358           var y = data[k++];
  3359           var rX = data[k++];
  3360           var rY = data[k++];
  3361           var radius;
  3362           if (rX !== rY) {
  3363             ctx.save();
  3364             var ellipseScale;
  3365             if (rX > rY) {
  3366               ellipseScale = rX / rY;
  3367               radius = rY;
  3368               x /= ellipseScale;
  3369               ctx.scale(ellipseScale, 1);
  3370             } else {
  3371               ellipseScale = rY / rX;
  3372               radius = rX;
  3373               y /= ellipseScale;
  3374               ctx.scale(1, ellipseScale);
  3377           ctx.moveTo((x + radius) / 20, y / 20);
  3378           ctx.arc(x / 20, y / 20, radius / 20, 0, Math.PI * 2, false);
  3379           if (rX !== rY) {
  3380             ctx.restore();
  3382           break;
  3383         default:
  3384           if (commands[j] === 0 && j === commands.length - 1) {
  3385             break;
  3387           console.warn('Unknown drawing command encountered: ' + commands[j]);
  3390     } else {
  3391       for (var j = 0, k = 0; j < commands.length; j++) {
  3392         switch (commands[j]) {
  3393         case SHAPE_MOVE_TO:
  3394           ctx.moveTo(morph(data[k] / 20, morphData[k++] / 20, ratio), morph(data[k] / 20, morphData[k++] / 20, ratio));
  3395           break;
  3396         case SHAPE_LINE_TO:
  3397           ctx.lineTo(morph(data[k] / 20, morphData[k++] / 20, ratio), morph(data[k] / 20, morphData[k++] / 20, ratio));
  3398           break;
  3399         case SHAPE_CURVE_TO:
  3400           ctx.quadraticCurveTo(morph(data[k] / 20, morphData[k++] / 20, ratio), morph(data[k] / 20, morphData[k++] / 20, ratio), morph(data[k] / 20, morphData[k++] / 20, ratio), morph(data[k] / 20, morphData[k++] / 20, ratio));
  3401           break;
  3402         default:
  3403           console.warn('Drawing command not supported for morph shapes: ' + commands[j]);
  3407     if (!clip) {
  3408       var fillStyle = this.fillStyle;
  3409       if (fillStyle) {
  3410         colorTransform.setFillStyle(ctx, fillStyle.style);
  3411         ctx.imageSmoothingEnabled = ctx.mozImageSmoothingEnabled = fillStyle.smooth;
  3412         var m = fillStyle.transform;
  3413         ctx.save();
  3414         colorTransform.setAlpha(ctx);
  3415         if (m) {
  3416           ctx.transform(m.a, m.b, m.c, m.d, m.e / 20, m.f / 20);
  3418         ctx.fill();
  3419         ctx.restore();
  3421       var lineStyle = this.lineStyle;
  3422       if (lineStyle) {
  3423         colorTransform.setStrokeStyle(ctx, lineStyle.style);
  3424         ctx.save();
  3425         colorTransform.setAlpha(ctx);
  3426         ctx.lineWidth = Math.max(lineStyle.width / 20, 1);
  3427         ctx.lineCap = lineStyle.lineCap;
  3428         ctx.lineJoin = lineStyle.lineJoin;
  3429         ctx.miterLimit = lineStyle.miterLimit;
  3430         ctx.stroke();
  3431         ctx.restore();
  3433     } else {
  3434       ctx.fill();
  3436     ctx.closePath();
  3437   },
  3438   isPointInPath: function (x, y) {
  3439     if (!(this.fillStyle || this.lineStyle)) {
  3440       return false;
  3442     var bounds = this.strokeBounds || this.bounds || this._calculateBounds();
  3443     if (x < bounds.xMin || x > bounds.xMax || y < bounds.yMin || y > bounds.yMax) {
  3444       return false;
  3446     if (this.fillStyle && this.isPointInFill(x, y)) {
  3447       return true;
  3449     return this.lineStyle && this.lineStyle.width !== undefined && this.isPointInStroke(x, y);
  3450   },
  3451   isPointInFill: function (x, y) {
  3452     var commands = this.commands;
  3453     var data = this.data;
  3454     var length = commands.length;
  3455     var inside = false;
  3456     var fromX = 0;
  3457     var fromY = 0;
  3458     var toX = 0;
  3459     var toY = 0;
  3460     var localX;
  3461     var localY;
  3462     var cpX;
  3463     var cpY;
  3464     var rX;
  3465     var rY;
  3466     var formOpen = false;
  3467     var formOpenX = 0;
  3468     var formOpenY = 0;
  3469     for (var commandIndex = 0, dataIndex = 0; commandIndex < length; commandIndex++) {
  3470       switch (commands[commandIndex]) {
  3471       case SHAPE_WIDE_MOVE_TO:
  3472         dataIndex += 2;
  3473       case SHAPE_MOVE_TO:
  3474         toX = data[dataIndex++];
  3475         toY = data[dataIndex++];
  3476         if (formOpen && intersectsLine(x, y, fromX, fromY, formOpenX, formOpenY)) {
  3477           inside = !inside;
  3479         formOpen = true;
  3480         formOpenX = toX;
  3481         formOpenY = toY;
  3482         break;
  3483       case SHAPE_WIDE_LINE_TO:
  3484         dataIndex += 2;
  3485       case SHAPE_LINE_TO:
  3486         toX = data[dataIndex++];
  3487         toY = data[dataIndex++];
  3488         if (intersectsLine(x, y, fromX, fromY, toX, toY)) {
  3489           inside = !inside;
  3491         break;
  3492       case SHAPE_CURVE_TO:
  3493         cpX = data[dataIndex++];
  3494         cpY = data[dataIndex++];
  3495         toX = data[dataIndex++];
  3496         toY = data[dataIndex++];
  3497         if (cpY > y === fromY > y && toY > y === fromY > y) {
  3498           break;
  3500         if (fromX >= x && cpX >= x && toX >= x) {
  3501           inside = !inside;
  3502           break;
  3504         var a = fromY - 2 * cpY + toY;
  3505         var c = fromY - y;
  3506         var b = 2 * (cpY - fromY);
  3507         var d = b * b - 4 * a * c;
  3508         if (d < 0) {
  3509           break;
  3511         d = Math.sqrt(d);
  3512         a = 1 / (a + a);
  3513         var t1 = (d - b) * a;
  3514         var t2 = (-b - d) * a;
  3515         if (t1 >= 0 && t1 <= 1 && quadraticBezier(fromX, cpX, toX, t1) > x) {
  3516           inside = !inside;
  3518         if (t2 >= 0 && t2 <= 1 && quadraticBezier(fromX, cpX, toX, t2) > x) {
  3519           inside = !inside;
  3521         break;
  3522       case SHAPE_CUBIC_CURVE_TO:
  3523         cpX = data[dataIndex++];
  3524         cpY = data[dataIndex++];
  3525         var cp2X = data[dataIndex++];
  3526         var cp2Y = data[dataIndex++];
  3527         toX = data[dataIndex++];
  3528         toY = data[dataIndex++];
  3529         if (cpY > y === fromY > y && cp2Y > y === fromY > y && toY > y === fromY > y) {
  3530           break;
  3532         if (fromX >= x && cpX >= x && cp2X >= x && toX >= x) {
  3533           inside = !inside;
  3534           break;
  3536         var roots = cubicXAtY(fromX, fromY, cpX, cpY, cp2X, cp2Y, toX, toY, y);
  3537         for (var i = roots.length; i--;) {
  3538           if (roots[i] >= x) {
  3539             inside = !inside;
  3542         break;
  3543       case SHAPE_CIRCLE:
  3544         toX = data[dataIndex++];
  3545         toY = data[dataIndex++];
  3546         var r = data[dataIndex++];
  3547         localX = x - toX;
  3548         localY = y - toY;
  3549         if (localX * localX + localY * localY < r * r) {
  3550           inside = !inside;
  3552         toX += r;
  3553         break;
  3554       case SHAPE_ELLIPSE:
  3555         cpX = data[dataIndex++];
  3556         cpY = data[dataIndex++];
  3557         rX = data[dataIndex++];
  3558         rY = data[dataIndex++];
  3559         localX = x - cpX;
  3560         localY = y - cpY;
  3561         if (localX * localX / (rX * rX) + localY * localY / (rY * rY) <= 1) {
  3562           inside = !inside;
  3564         toX = cpX + rX;
  3565         toY = cpY;
  3566         break;
  3567       default:
  3568         if (!inWorker) {
  3569           console.warn('Drawing command not handled in isPointInPath: ' + commands[commandIndex]);
  3572       fromX = toX;
  3573       fromY = toY;
  3575     if (formOpen && intersectsLine(x, y, fromX, fromY, formOpenX, formOpenY)) {
  3576       inside = !inside;
  3578     return inside;
  3579   },
  3580   isPointInStroke: function (x, y) {
  3581     var commands = this.commands;
  3582     var data = this.data;
  3583     var length = commands.length;
  3584     var width = this.lineStyle.width;
  3585     var halfWidth = width / 2;
  3586     var halfWidthSq = halfWidth * halfWidth;
  3587     var minX = x - halfWidth;
  3588     var maxX = x + halfWidth;
  3589     var minY = y - halfWidth;
  3590     var maxY = y + halfWidth;
  3591     var fromX = 0;
  3592     var fromY = 0;
  3593     var toX = 0;
  3594     var toY = 0;
  3595     var localX;
  3596     var localY;
  3597     var cpX;
  3598     var cpY;
  3599     var rX;
  3600     var rY;
  3601     var curveX;
  3602     var curveY;
  3603     var t;
  3604     for (var commandIndex = 0, dataIndex = 0; commandIndex < length; commandIndex++) {
  3605       switch (commands[commandIndex]) {
  3606       case SHAPE_WIDE_MOVE_TO:
  3607         dataIndex += 2;
  3608       case SHAPE_MOVE_TO:
  3609         toX = data[dataIndex++];
  3610         toY = data[dataIndex++];
  3611         break;
  3612       case SHAPE_WIDE_LINE_TO:
  3613         dataIndex += 2;
  3614       case SHAPE_LINE_TO:
  3615         toX = data[dataIndex++];
  3616         toY = data[dataIndex++];
  3617         if (fromX === toX && fromY === toY) {
  3618           break;
  3620         if (maxX < fromX && maxX < toX || minX > fromX && minX > toX || maxY < fromY && maxY < toY || minY > fromY && minY > toY) {
  3621           break;
  3623         if (toX === fromX || toY === fromY) {
  3624           return true;
  3626         t = ((x - fromX) * (toX - fromX) + (y - fromY) * (toY - fromY)) / distanceSq(fromX, fromY, toX, toY);
  3627         if (t < 0) {
  3628           if (distanceSq(x, y, fromX, fromY) <= halfWidthSq) {
  3629             return true;
  3631           break;
  3633         if (t > 1) {
  3634           if (distanceSq(x, y, toX, toY) <= halfWidthSq) {
  3635             return true;
  3637           break;
  3639         if (distanceSq(x, y, fromX + t * (toX - fromX), fromY + t * (toY - fromY)) <= halfWidthSq) {
  3640           return true;
  3642         break;
  3643       case SHAPE_CURVE_TO:
  3644         cpX = data[dataIndex++];
  3645         cpY = data[dataIndex++];
  3646         toX = data[dataIndex++];
  3647         toY = data[dataIndex++];
  3648         var extremeX = quadraticBezierExtreme(fromX, cpX, toX);
  3649         if (maxX < fromX && maxX < extremeX && maxX < toX || minX > fromX && minX > extremeX && minX > toX) {
  3650           break;
  3652         var extremeY = quadraticBezierExtreme(fromY, cpY, toY);
  3653         if (maxY < fromY && maxY < extremeY && maxY < toY || minY > fromY && minY > extremeY && minY > toY) {
  3654           break;
  3656         for (t = 0; t < 1; t += 0.02) {
  3657           curveX = quadraticBezier(fromX, cpX, toX, t);
  3658           if (curveX < minX || curveX > maxX) {
  3659             continue;
  3661           curveY = quadraticBezier(fromY, cpY, toY, t);
  3662           if (curveY < minY || curveY > maxY) {
  3663             continue;
  3665           if ((x - curveX) * (x - curveX) + (y - curveY) * (y - curveY) < halfWidthSq) {
  3666             return true;
  3669         break;
  3670       case SHAPE_CUBIC_CURVE_TO:
  3671         cpX = data[dataIndex++];
  3672         cpY = data[dataIndex++];
  3673         var cp2X = data[dataIndex++];
  3674         var cp2Y = data[dataIndex++];
  3675         toX = data[dataIndex++];
  3676         toY = data[dataIndex++];
  3677         var extremesX = cubicBezierExtremes(fromX, cpX, cp2X, toX);
  3678         while (extremesX.length < 2) {
  3679           extremesX.push(toX);
  3681         if (maxX < fromX && maxX < toX && maxX < extremesX[0] && maxX < extremesX[1] || minX > fromX && minX > toX && minX > extremesX[0] && minX > extremesX[1]) {
  3682           break;
  3684         var extremesY = cubicBezierExtremes(fromY, cpY, cp2Y, toY);
  3685         while (extremesY.length < 2) {
  3686           extremesY.push(toY);
  3688         if (maxY < fromY && maxY < toY && maxY < extremesY[0] && maxY < extremesY[1] || minY > fromY && minY > toY && minY > extremesY[0] && minY > extremesY[1]) {
  3689           break;
  3691         for (t = 0; t < 1; t += 0.02) {
  3692           curveX = cubicBezier(fromX, cpX, cp2X, toX, t);
  3693           if (curveX < minX || curveX > maxX) {
  3694             continue;
  3696           curveY = cubicBezier(fromY, cpY, cp2Y, toY, t);
  3697           if (curveY < minY || curveY > maxY) {
  3698             continue;
  3700           if ((x - curveX) * (x - curveX) + (y - curveY) * (y - curveY) < halfWidthSq) {
  3701             return true;
  3704         break;
  3705       case SHAPE_CIRCLE:
  3706         cpX = data[dataIndex++];
  3707         cpY = data[dataIndex++];
  3708         var r = data[dataIndex++];
  3709         toX = cpX + r;
  3710         toY = cpY;
  3711         if (maxX < cpX - r || minX > cpX + r || maxY < cpY - r || minY > cpY + r) {
  3712           break;
  3714         localX = x - cpX;
  3715         localY = y - cpY;
  3716         var rMin = r - halfWidth;
  3717         var rMax = r + halfWidth;
  3718         var distSq = localX * localX + localY * localY;
  3719         if (distSq >= rMin * rMin && distSq <= rMax * rMax) {
  3720           return true;
  3722         break;
  3723       case SHAPE_ELLIPSE:
  3724         cpX = data[dataIndex++];
  3725         cpY = data[dataIndex++];
  3726         rX = data[dataIndex++];
  3727         rY = data[dataIndex++];
  3728         toX = cpX + rX;
  3729         toY = cpY;
  3730         localX = Math.abs(x - cpX);
  3731         localY = Math.abs(y - cpY);
  3732         localX -= halfWidth;
  3733         localY -= halfWidth;
  3734         if (localX * localX / (rX * rX) + localY * localY / (rY * rY) > 1) {
  3735           break;
  3737         localX += width;
  3738         localY += width;
  3739         if (localX * localX / (rX * rX) + localY * localY / (rY * rY) > 1) {
  3740           return true;
  3742         break;
  3743       default:
  3744         if (!inWorker) {
  3745           console.warn('Drawing command not handled in isPointInPath: ' + commands[commandIndex]);
  3748       fromX = toX;
  3749       fromY = toY;
  3751     return false;
  3752   },
  3753   getBounds: function (includeStroke) {
  3754     var bounds = includeStroke ? this.strokeBounds : this.bounds;
  3755     if (!bounds) {
  3756       this._calculateBounds();
  3757       bounds = includeStroke ? this.strokeBounds : this.bounds;
  3759     return bounds;
  3760   },
  3761   _calculateBounds: function () {
  3762     var commands = this.commands;
  3763     var data = this.data;
  3764     var length = commands.length;
  3765     var bounds;
  3766     if (commands[0] === SHAPE_MOVE_TO || commands[0] > SHAPE_CUBIC_CURVE_TO) {
  3767       bounds = {
  3768         xMin: data[0],
  3769         yMin: data[1]
  3770       };
  3771     } else {
  3772       bounds = {
  3773         xMin: 0,
  3774         yMin: 0
  3775       };
  3777     bounds.xMax = bounds.xMin;
  3778     bounds.yMax = bounds.yMin;
  3779     var fromX = bounds.xMin;
  3780     var fromY = bounds.yMin;
  3781     for (var commandIndex = 0, dataIndex = 0; commandIndex < length; commandIndex++) {
  3782       var toX;
  3783       var toY;
  3784       var cpX;
  3785       var cpY;
  3786       switch (commands[commandIndex]) {
  3787       case SHAPE_WIDE_MOVE_TO:
  3788         dataIndex += 2;
  3789       case SHAPE_MOVE_TO:
  3790         toX = data[dataIndex++];
  3791         toY = data[dataIndex++];
  3792         extendBoundsByPoint(bounds, toX, toY);
  3793         break;
  3794       case SHAPE_WIDE_LINE_TO:
  3795         dataIndex += 2;
  3796       case SHAPE_LINE_TO:
  3797         toX = data[dataIndex++];
  3798         toY = data[dataIndex++];
  3799         extendBoundsByPoint(bounds, toX, toY);
  3800         break;
  3801       case SHAPE_CURVE_TO:
  3802         cpX = data[dataIndex++];
  3803         cpY = data[dataIndex++];
  3804         toX = data[dataIndex++];
  3805         toY = data[dataIndex++];
  3806         extendBoundsByPoint(bounds, toX, toY);
  3807         if (cpX < fromX || cpX > toX) {
  3808           extendBoundsByX(bounds, quadraticBezierExtreme(fromX, cpX, toX));
  3810         if (cpY < fromY || cpY > toY) {
  3811           extendBoundsByY(bounds, quadraticBezierExtreme(fromY, cpY, toY));
  3813         break;
  3814       case SHAPE_CUBIC_CURVE_TO:
  3815         cpX = data[dataIndex++];
  3816         cpY = data[dataIndex++];
  3817         var cp2X = data[dataIndex++];
  3818         var cp2Y = data[dataIndex++];
  3819         toX = data[dataIndex++];
  3820         toY = data[dataIndex++];
  3821         extendBoundsByPoint(bounds, toX, toY);
  3822         var extremes;
  3823         var i;
  3824         if (cpX < fromX || cp2X < fromX || cpX > toX || cp2X > toX) {
  3825           extremes = cubicBezierExtremes(fromX, cpX, cp2X, toX);
  3826           for (i = extremes.length; i--;) {
  3827             extendBoundsByX(bounds, extremes[i]);
  3830         if (cpY < fromY || cp2Y < fromY || cpY > toY || cp2Y > toY) {
  3831           extremes = cubicBezierExtremes(fromY, cpY, cp2Y, toY);
  3832           for (i = extremes.length; i--;) {
  3833             extendBoundsByY(bounds, extremes[i]);
  3836         break;
  3837       case SHAPE_CIRCLE:
  3838         toX = data[dataIndex++];
  3839         toY = data[dataIndex++];
  3840         var radius = data[dataIndex++];
  3841         extendBoundsByPoint(bounds, toX - radius, toY - radius);
  3842         extendBoundsByPoint(bounds, toX + radius, toY + radius);
  3843         toX += radius;
  3844         break;
  3845       case SHAPE_ELLIPSE:
  3846         toX = data[dataIndex++];
  3847         toY = data[dataIndex++];
  3848         var radiusX = data[dataIndex++];
  3849         var radiusY = data[dataIndex++];
  3850         extendBoundsByPoint(bounds, toX - radiusX, toY - radiusY);
  3851         extendBoundsByPoint(bounds, toX + radiusX, toY + radiusY);
  3852         toX += radiusX;
  3853         break;
  3854       default:
  3855         if (!inWorker) {
  3856           console.warn('Drawing command not handled in bounds calculation: ' + commands[commandIndex]);
  3859       fromX = toX;
  3860       fromY = toY;
  3862     this.bounds = bounds;
  3863     if (this.lineStyle) {
  3864       var halfLineWidth = this.lineStyle.width / 2;
  3865       this.strokeBounds = {
  3866         xMin: bounds.xMin - halfLineWidth,
  3867         yMin: bounds.yMin - halfLineWidth,
  3868         xMax: bounds.xMax + halfLineWidth,
  3869         yMax: bounds.yMax + halfLineWidth
  3870       };
  3871       return this.strokeBounds;
  3872     } else {
  3873       this.strokeBounds = bounds;
  3875     return bounds;
  3876   },
  3877   serialize: function () {
  3878     var output = '{';
  3879     if (this.fillStyle) {
  3880       output += '"fill":' + JSON.stringify(this.fillStyle) + ',';
  3882     if (this.lineStyle) {
  3883       output += '"stroke":' + JSON.stringify(this.lineStyle) + ',';
  3885     output += '"commands":[' + Array.apply([], this.commands).join() + '],';
  3886     output += '"data":[' + Array.apply([], this.data).join() + ']';
  3887     return output + '}';
  3889 };
  3890 ShapePath.fromPlainObject = function (obj) {
  3891   var path = new ShapePath(obj.fill || null, obj.stroke || null);
  3892   path.commands = new Uint8Array(obj.commands);
  3893   path.data = new Int32Array(obj.data);
  3894   if (!inWorker) {
  3895     finishShapePath(path);
  3897   return path;
  3898 };
  3899 function distanceSq(x1, y1, x2, y2) {
  3900   var dX = x2 - x1;
  3901   var dY = y2 - y1;
  3902   return dX * dX + dY * dY;
  3904 function intersectsLine(x, y, x1, y1, x2, y2) {
  3905   return y2 > y !== y1 > y && x < (x1 - x2) * (y - y2) / (y1 - y2) + x2;
  3907 function quadraticBezier(from, cp, to, t) {
  3908   var inverseT = 1 - t;
  3909   return from * inverseT * inverseT + 2 * cp * inverseT * t + to * t * t;
  3911 function quadraticBezierExtreme(from, cp, to) {
  3912   var t = (from - cp) / (from - 2 * cp + to);
  3913   if (t < 0) {
  3914     return from;
  3916   if (t > 1) {
  3917     return to;
  3919   return quadraticBezier(from, cp, to, t);
  3921 function cubicBezier(from, cp, cp2, to, t) {
  3922   var tSq = t * t;
  3923   var inverseT = 1 - t;
  3924   var inverseTSq = inverseT * inverseT;
  3925   return from * inverseT * inverseTSq + 3 * cp * t * inverseTSq + 3 * cp2 * inverseT * tSq + to * t * tSq;
  3927 function cubicBezierExtremes(from, cp, cp2, to) {
  3928   var d1 = cp - from;
  3929   var d2 = cp2 - cp;
  3930   d2 *= 2;
  3931   var d3 = to - cp2;
  3932   if (d1 + d3 === d2) {
  3933     d3 *= 1.0001;
  3935   var fHead = 2 * d1 - d2;
  3936   var part1 = d2 - 2 * d1;
  3937   var fCenter = Math.sqrt(part1 * part1 - 4 * d1 * (d1 - d2 + d3));
  3938   var fTail = 2 * (d1 - d2 + d3);
  3939   var t1 = (fHead + fCenter) / fTail;
  3940   var t2 = (fHead - fCenter) / fTail;
  3941   var result = [];
  3942   if (t1 >= 0 && t1 <= 1) {
  3943     result.push(cubicBezier(from, cp, cp2, to, t1));
  3945   if (t2 >= 0 && t2 <= 1) {
  3946     result.push(cubicBezier(from, cp, cp2, to, t2));
  3948   return result;
  3950 function cubicXAtY(x0, y0, cx, cy, cx1, cy1, x1, y1, y) {
  3951   var dX = 3 * (cx - x0);
  3952   var dY = 3 * (cy - y0);
  3953   var bX = 3 * (cx1 - cx) - dX;
  3954   var bY = 3 * (cy1 - cy) - dY;
  3955   var c3X = x1 - x0 - dX - bX;
  3956   var c3Y = y1 - y0 - dY - bY;
  3957   function f(t) {
  3958     return t * (dY + t * (bY + t * c3Y)) + y0 - y;
  3960   function pointAt(t) {
  3961     if (t < 0) {
  3962       t = 0;
  3963     } else if (t > 1) {
  3964       t = 1;
  3966     return x0 + t * (dX + t * (bX + t * c3X));
  3968   function bisectCubicBezierRange(f, l, r, limit) {
  3969     if (Math.abs(r - l) <= limit) {
  3970       return;
  3972     var middle = 0.5 * (l + r);
  3973     if (f(l) * f(r) <= 0) {
  3974       left = l;
  3975       right = r;
  3976       return;
  3978     bisectCubicBezierRange(f, l, middle, limit);
  3979     bisectCubicBezierRange(f, middle, r, limit);
  3981   var left = 0;
  3982   var right = 1;
  3983   bisectCubicBezierRange(f, 0, 1, 0.05);
  3984   var t0 = findRoot(left, right, f, 50, 0.000001);
  3985   var evalResult = Math.abs(f(t0));
  3986   if (evalResult > 0.00001) {
  3987     return [];
  3989   var result = [];
  3990   if (t0 <= 1) {
  3991     result.push(pointAt(t0));
  3993   var a = c3Y;
  3994   var b = t0 * a + bY;
  3995   var c = t0 * b + dY;
  3996   var d = b * b - 4 * a * c;
  3997   if (d < 0) {
  3998     return result;
  4000   d = Math.sqrt(d);
  4001   a = 1 / (a + a);
  4002   var t1 = (d - b) * a;
  4003   var t2 = (-b - d) * a;
  4004   if (t1 >= 0 && t1 <= 1) {
  4005     result.push(pointAt(t1));
  4007   if (t2 >= 0 && t2 <= 1) {
  4008     result.push(pointAt(t2));
  4010   return result;
  4012 function findRoot(x0, x2, f, maxIterations, epsilon) {
  4013   var x1;
  4014   var y0;
  4015   var y1;
  4016   var y2;
  4017   var b;
  4018   var c;
  4019   var y10;
  4020   var y20;
  4021   var y21;
  4022   var xm;
  4023   var ym;
  4024   var temp;
  4025   var xmlast = x0;
  4026   y0 = f(x0);
  4027   if (y0 === 0) {
  4028     return x0;
  4030   y2 = f(x2);
  4031   if (y2 === 0) {
  4032     return x2;
  4034   if (y2 * y0 > 0) {
  4035     return x0;
  4037   var __iter = 0;
  4038   for (var i = 0; i < maxIterations; ++i) {
  4039     __iter++;
  4040     x1 = 0.5 * (x2 + x0);
  4041     y1 = f(x1);
  4042     if (y1 === 0) {
  4043       return x1;
  4045     if (Math.abs(x1 - x0) < epsilon) {
  4046       return x1;
  4048     if (y1 * y0 > 0) {
  4049       temp = x0;
  4050       x0 = x2;
  4051       x2 = temp;
  4052       temp = y0;
  4053       y0 = y2;
  4054       y2 = temp;
  4056     y10 = y1 - y0;
  4057     y21 = y2 - y1;
  4058     y20 = y2 - y0;
  4059     if (y2 * y20 < 2 * y1 * y10) {
  4060       x2 = x1;
  4061       y2 = y1;
  4062     } else {
  4063       b = (x1 - x0) / y10;
  4064       c = (y10 - y21) / (y21 * y20);
  4065       xm = x0 - b * y0 * (1 - c * y1);
  4066       ym = f(xm);
  4067       if (ym === 0) {
  4068         return xm;
  4070       if (Math.abs(xm - xmlast) < epsilon) {
  4071         return xm;
  4073       xmlast = xm;
  4074       if (ym * y0 < 0) {
  4075         x2 = xm;
  4076         y2 = ym;
  4077       } else {
  4078         x0 = xm;
  4079         y0 = ym;
  4080         x2 = x1;
  4081         y2 = y1;
  4085   return x1;
  4087 function extendBoundsByPoint(bounds, x, y) {
  4088   if (x < bounds.xMin) {
  4089     bounds.xMin = x;
  4090   } else if (x > bounds.xMax) {
  4091     bounds.xMax = x;
  4093   if (y < bounds.yMin) {
  4094     bounds.yMin = y;
  4095   } else if (y > bounds.yMax) {
  4096     bounds.yMax = y;
  4099 function extendBoundsByX(bounds, x) {
  4100   if (x < bounds.xMin) {
  4101     bounds.xMin = x;
  4102   } else if (x > bounds.xMax) {
  4103     bounds.xMax = x;
  4106 function extendBoundsByY(bounds, y) {
  4107   if (y < bounds.yMin) {
  4108     bounds.yMin = y;
  4109   } else if (y > bounds.yMax) {
  4110     bounds.yMax = y;
  4113 function morph(start, end, ratio) {
  4114   return start + (end - start) * ratio;
  4116 function finishShapePath(path, dictionaryResolved) {
  4117   if (path.fullyInitialized) {
  4118     return path;
  4120   if (!(path instanceof ShapePath)) {
  4121     var untypedPath = path;
  4122     path = new ShapePath(path.fillStyle, path.lineStyle, 0, 0, path.isMorph);
  4123     path.commands = new Uint8Array(untypedPath.buffers[0]);
  4124     path.data = new Int32Array(untypedPath.buffers[1]);
  4125     if (untypedPath.isMorph) {
  4126       path.morphData = new Int32Array(untypedPath.buffers[2]);
  4128     path.buffers = null;
  4130   path.fillStyle && initStyle(path.fillStyle, dictionaryResolved);
  4131   path.lineStyle && initStyle(path.lineStyle, dictionaryResolved);
  4132   path.fullyInitialized = true;
  4133   return path;
  4135 var inWorker = typeof window === 'undefined';
  4136 var factoryCtx = !inWorker ? document.createElement('canvas').getContext('2d') : null;
  4137 function buildLinearGradientFactory(colorStops) {
  4138   var defaultGradient = factoryCtx.createLinearGradient(-1, 0, 1, 0);
  4139   for (var i = 0; i < colorStops.length; i++) {
  4140     defaultGradient.addColorStop(colorStops[i].ratio, colorStops[i].color);
  4142   var fn = function createLinearGradient(ctx, colorTransform) {
  4143     var gradient = ctx.createLinearGradient(-1, 0, 1, 0);
  4144     for (var i = 0; i < colorStops.length; i++) {
  4145       colorTransform.addGradientColorStop(gradient, colorStops[i].ratio, colorStops[i].color);
  4147     return gradient;
  4148   };
  4149   fn.defaultFillStyle = defaultGradient;
  4150   return fn;
  4152 function buildRadialGradientFactory(focalPoint, colorStops) {
  4153   var defaultGradient = factoryCtx.createRadialGradient(focalPoint, 0, 0, 0, 0, 1);
  4154   for (var i = 0; i < colorStops.length; i++) {
  4155     defaultGradient.addColorStop(colorStops[i].ratio, colorStops[i].color);
  4157   var fn = function createRadialGradient(ctx, colorTransform) {
  4158     var gradient = ctx.createRadialGradient(focalPoint, 0, 0, 0, 0, 1);
  4159     for (var i = 0; i < colorStops.length; i++) {
  4160       colorTransform.addGradientColorStop(gradient, colorStops[i].ratio, colorStops[i].color);
  4162     return gradient;
  4163   };
  4164   fn.defaultFillStyle = defaultGradient;
  4165   return fn;
  4167 function buildBitmapPatternFactory(img, repeat) {
  4168   var defaultPattern = factoryCtx.createPattern(img, repeat);
  4169   var cachedTransform, cachedTransformKey;
  4170   var fn = function createBitmapPattern(ctx, colorTransform) {
  4171     if (!colorTransform.mode) {
  4172       return defaultPattern;
  4174     var key = colorTransform.getTransformFingerprint();
  4175     if (key === cachedTransformKey) {
  4176       return cachedTransform;
  4178     var canvas = document.createElement('canvas');
  4179     canvas.width = img.width;
  4180     canvas.height = img.height;
  4181     var ctx = canvas.getContext('2d');
  4182     colorTransform.setAlpha(ctx, true);
  4183     ctx.drawImage(img, 0, 0);
  4184     cachedTransform = ctx.createPattern(canvas, repeat);
  4185     cachedTransformKey = key;
  4186     return cachedTransform;
  4187   };
  4188   fn.defaultFillStyle = defaultPattern;
  4189   return fn;
  4191 function initStyle(style, dictionaryResolved) {
  4192   if (style.type === undefined) {
  4193     return;
  4195   switch (style.type) {
  4196   case GRAPHICS_FILL_SOLID:
  4197     break;
  4198   case GRAPHICS_FILL_LINEAR_GRADIENT:
  4199   case GRAPHICS_FILL_RADIAL_GRADIENT:
  4200   case GRAPHICS_FILL_FOCAL_RADIAL_GRADIENT:
  4201     var records = style.records, colorStops = [];
  4202     for (var j = 0, n = records.length; j < n; j++) {
  4203       var record = records[j];
  4204       var colorStr = rgbaObjToStr(record.color);
  4205       colorStops.push({
  4206         ratio: record.ratio / 255,
  4207         color: colorStr
  4208       });
  4210     var gradientConstructor;
  4211     var isLinear = style.type === GRAPHICS_FILL_LINEAR_GRADIENT;
  4212     if (isLinear) {
  4213       gradientConstructor = buildLinearGradientFactory(colorStops);
  4214     } else {
  4215       gradientConstructor = buildRadialGradientFactory((style.focalPoint | 0) / 20, colorStops);
  4217     style.style = gradientConstructor;
  4218     break;
  4219   case GRAPHICS_FILL_REPEATING_BITMAP:
  4220   case GRAPHICS_FILL_CLIPPED_BITMAP:
  4221   case GRAPHICS_FILL_NONSMOOTHED_REPEATING_BITMAP:
  4222   case GRAPHICS_FILL_NONSMOOTHED_CLIPPED_BITMAP:
  4223     var bitmap = dictionaryResolved[style.bitmapId];
  4224     var repeat = style.type === GRAPHICS_FILL_REPEATING_BITMAP || style.type === GRAPHICS_FILL_NONSMOOTHED_REPEATING_BITMAP;
  4225     style.style = buildBitmapPatternFactory(bitmap.props.img, repeat ? 'repeat' : 'no-repeat');
  4226     break;
  4227   default:
  4228     fail('invalid fill style', 'shape');
  4231 var SOUND_SIZE_8_BIT = 0;
  4232 var SOUND_SIZE_16_BIT = 1;
  4233 var SOUND_TYPE_MONO = 0;
  4234 var SOUND_TYPE_STEREO = 1;
  4235 var SOUND_FORMAT_PCM_BE = 0;
  4236 var SOUND_FORMAT_ADPCM = 1;
  4237 var SOUND_FORMAT_MP3 = 2;
  4238 var SOUND_FORMAT_PCM_LE = 3;
  4239 var SOUND_FORMAT_NELLYMOSER_16 = 4;
  4240 var SOUND_FORMAT_NELLYMOSER_8 = 5;
  4241 var SOUND_FORMAT_NELLYMOSER = 6;
  4242 var SOUND_FORMAT_SPEEX = 11;
  4243 var SOUND_RATES = [
  4244     5512,
  4245     11250,
  4246     22500,
  4247     44100
  4248   ];
  4249 var WaveHeader = new Uint8Array([
  4250     82,
  4251     73,
  4252     70,
  4253     70,
  4254     0,
  4255     0,
  4256     0,
  4257     0,
  4258     87,
  4259     65,
  4260     86,
  4261     69,
  4262     102,
  4263     109,
  4264     116,
  4265     32,
  4266     16,
  4267     0,
  4268     0,
  4269     0,
  4270     1,
  4271     0,
  4272     2,
  4273     0,
  4274     68,
  4275     172,
  4276     0,
  4277     0,
  4278     16,
  4279     177,
  4280     2,
  4281     0,
  4282     4,
  4283     0,
  4284     16,
  4285     0,
  4286     100,
  4287     97,
  4288     116,
  4289     97,
  4290     0,
  4291     0,
  4292     0,
  4294   ]);
  4295 function packageWave(data, sampleRate, channels, size, swapBytes) {
  4296   var sizeInBytes = size >> 3;
  4297   var sizePerSecond = channels * sampleRate * sizeInBytes;
  4298   var sizePerSample = channels * sizeInBytes;
  4299   var dataLength = data.length + (data.length & 1);
  4300   var buffer = new ArrayBuffer(WaveHeader.length + dataLength);
  4301   var bytes = new Uint8Array(buffer);
  4302   bytes.set(WaveHeader);
  4303   if (swapBytes) {
  4304     for (var i = 0, j = WaveHeader.length; i < data.length; i += 2, j += 2) {
  4305       bytes[j] = data[i + 1];
  4306       bytes[j + 1] = data[i];
  4308   } else {
  4309     bytes.set(data, WaveHeader.length);
  4311   var view = new DataView(buffer);
  4312   view.setUint32(4, dataLength + 36, true);
  4313   view.setUint16(22, channels, true);
  4314   view.setUint32(24, sampleRate, true);
  4315   view.setUint32(28, sizePerSecond, true);
  4316   view.setUint16(32, sizePerSample, true);
  4317   view.setUint16(34, size, true);
  4318   view.setUint32(40, dataLength, true);
  4319   return {
  4320     data: bytes,
  4321     mimeType: 'audio/wav'
  4322   };
  4324 function defineSound(tag, dictionary) {
  4325   var channels = tag.soundType == SOUND_TYPE_STEREO ? 2 : 1;
  4326   var samplesCount = tag.samplesCount;
  4327   var sampleRate = SOUND_RATES[tag.soundRate];
  4328   var data = tag.soundData;
  4329   var pcm, packaged;
  4330   switch (tag.soundFormat) {
  4331   case SOUND_FORMAT_PCM_BE:
  4332     pcm = new Float32Array(samplesCount * channels);
  4333     if (tag.soundSize == SOUND_SIZE_16_BIT) {
  4334       for (var i = 0, j = 0; i < pcm.length; i++, j += 2)
  4335         pcm[i] = (data[j] << 24 | data[j + 1] << 16) / 2147483648;
  4336       packaged = packageWave(data, sampleRate, channels, 16, true);
  4337     } else {
  4338       for (var i = 0; i < pcm.length; i++)
  4339         pcm[i] = (data[i] - 128) / 128;
  4340       packaged = packageWave(data, sampleRate, channels, 8, false);
  4342     break;
  4343   case SOUND_FORMAT_PCM_LE:
  4344     pcm = new Float32Array(samplesCount * channels);
  4345     if (tag.soundSize == SOUND_SIZE_16_BIT) {
  4346       for (var i = 0, j = 0; i < pcm.length; i++, j += 2)
  4347         pcm[i] = (data[j + 1] << 24 | data[j] << 16) / 2147483648;
  4348       packaged = packageWave(data, sampleRate, channels, 16, false);
  4349     } else {
  4350       for (var i = 0; i < pcm.length; i++)
  4351         pcm[i] = (data[i] - 128) / 128;
  4352       packaged = packageWave(data, sampleRate, channels, 8, false);
  4354     break;
  4355   case SOUND_FORMAT_MP3:
  4356     packaged = {
  4357       data: new Uint8Array(data.subarray(2)),
  4358       mimeType: 'audio/mpeg'
  4359     };
  4360     break;
  4361   case SOUND_FORMAT_ADPCM:
  4362     var pcm16 = new Int16Array(samplesCount * channels);
  4363     decodeACPCMSoundData(data, pcm16, channels);
  4364     pcm = new Float32Array(samplesCount * channels);
  4365     for (var i = 0; i < pcm.length; i++)
  4366       pcm[i] = pcm16[i] / 32768;
  4367     packaged = packageWave(new Uint8Array(pcm16.buffer), sampleRate, channels, 16, !new Uint8Array(new Uint16Array([
  4369     ]).buffer)[0]);
  4370     break;
  4371   default:
  4372     throw new Error('Unsupported audio format: ' + tag.soundFormat);
  4374   var sound = {
  4375       type: 'sound',
  4376       id: tag.id,
  4377       sampleRate: sampleRate,
  4378       channels: channels,
  4379       pcm: pcm
  4380     };
  4381   if (packaged)
  4382     sound.packaged = packaged;
  4383   return sound;
  4385 var ACPCMIndexTables = [
  4387       -1,
  4389     ],
  4391       -1,
  4392       -1,
  4393       2,
  4395     ],
  4397       -1,
  4398       -1,
  4399       -1,
  4400       -1,
  4401       2,
  4402       4,
  4403       6,
  4405     ],
  4407       -1,
  4408       -1,
  4409       -1,
  4410       -1,
  4411       -1,
  4412       -1,
  4413       -1,
  4414       -1,
  4415       1,
  4416       2,
  4417       4,
  4418       6,
  4419       8,
  4420       10,
  4421       13,
  4422       16
  4424   ];
  4425 var ACPCMStepSizeTable = [
  4426     7,
  4427     8,
  4428     9,
  4429     10,
  4430     11,
  4431     12,
  4432     13,
  4433     14,
  4434     16,
  4435     17,
  4436     19,
  4437     21,
  4438     23,
  4439     25,
  4440     28,
  4441     31,
  4442     34,
  4443     37,
  4444     41,
  4445     45,
  4446     50,
  4447     55,
  4448     60,
  4449     66,
  4450     73,
  4451     80,
  4452     88,
  4453     97,
  4454     107,
  4455     118,
  4456     130,
  4457     143,
  4458     157,
  4459     173,
  4460     190,
  4461     209,
  4462     230,
  4463     253,
  4464     279,
  4465     307,
  4466     337,
  4467     371,
  4468     408,
  4469     449,
  4470     494,
  4471     544,
  4472     598,
  4473     658,
  4474     724,
  4475     796,
  4476     876,
  4477     963,
  4478     1060,
  4479     1166,
  4480     1282,
  4481     1411,
  4482     1552,
  4483     1707,
  4484     1878,
  4485     2066,
  4486     2272,
  4487     2499,
  4488     2749,
  4489     3024,
  4490     3327,
  4491     3660,
  4492     4026,
  4493     4428,
  4494     4871,
  4495     5358,
  4496     5894,
  4497     6484,
  4498     7132,
  4499     7845,
  4500     8630,
  4501     9493,
  4502     10442,
  4503     11487,
  4504     12635,
  4505     13899,
  4506     15289,
  4507     16818,
  4508     18500,
  4509     20350,
  4510     22385,
  4511     24623,
  4512     27086,
  4513     29794,
  4514     32767
  4515   ];
  4516 function decodeACPCMSoundData(data, pcm16, channels) {
  4517   function readBits(n, signed) {
  4518     while (dataBufferLength < n) {
  4519       dataBuffer = dataBuffer << 8 | data[dataPosition++];
  4520       dataBufferLength += 8;
  4522     dataBufferLength -= n;
  4523     return dataBuffer >>> dataBufferLength & (1 << n) - 1;
  4525   var dataPosition = 0;
  4526   var dataBuffer = 0;
  4527   var dataBufferLength = 0;
  4528   var pcmPosition = 0;
  4529   var codeSize = readBits(2);
  4530   var indexTable = ACPCMIndexTables[codeSize];
  4531   while (pcmPosition < pcm16.length) {
  4532     var x = pcm16[pcmPosition++] = readBits(16) << 16 >> 16, x2;
  4533     var stepIndex = readBits(6), stepIndex2;
  4534     if (channels > 1) {
  4535       x2 = pcm16[pcmPosition++] = readBits(16) << 16 >> 16;
  4536       stepIndex2 = readBits(6);
  4538     var signMask = 1 << codeSize + 1;
  4539     for (var i = 0; i < 4095; i++) {
  4540       var nibble = readBits(codeSize + 2);
  4541       var step = ACPCMStepSizeTable[stepIndex];
  4542       var sum = 0;
  4543       for (var currentBit = signMask >> 1; currentBit; currentBit >>= 1, step >>= 1) {
  4544         if (nibble & currentBit)
  4545           sum += step;
  4547       x += (nibble & signMask ? -1 : 1) * (sum + step);
  4548       pcm16[pcmPosition++] = x = x < -32768 ? -32768 : x > 32767 ? 32767 : x;
  4549       stepIndex += indexTable[nibble & ~signMask];
  4550       stepIndex = stepIndex < 0 ? 0 : stepIndex > 88 ? 88 : stepIndex;
  4551       if (channels > 1) {
  4552         nibble = readBits(codeSize + 2);
  4553         step = ACPCMStepSizeTable[stepIndex2];
  4554         sum = 0;
  4555         for (var currentBit = signMask >> 1; currentBit; currentBit >>= 1, step >>= 1) {
  4556           if (nibble & currentBit)
  4557             sum += step;
  4559         x2 += (nibble & signMask ? -1 : 1) * (sum + step);
  4560         pcm16[pcmPosition++] = x2 = x2 < -32768 ? -32768 : x2 > 32767 ? 32767 : x2;
  4561         stepIndex2 += indexTable[nibble & ~signMask];
  4562         stepIndex2 = stepIndex2 < 0 ? 0 : stepIndex2 > 88 ? 88 : stepIndex2;
  4567 var nextSoundStreamId = 0;
  4568 function SwfSoundStream(samplesCount, sampleRate, channels) {
  4569   this.streamId = nextSoundStreamId++;
  4570   this.samplesCount = samplesCount;
  4571   this.sampleRate = sampleRate;
  4572   this.channels = channels;
  4573   this.format = null;
  4574   this.currentSample = 0;
  4576 SwfSoundStream.prototype = {
  4577   get info() {
  4578     return {
  4579       samplesCount: this.samplesCount,
  4580       sampleRate: this.sampleRate,
  4581       channels: this.channels,
  4582       format: this.format,
  4583       streamId: this.streamId
  4584     };
  4585   },
  4586   decode: function (data) {
  4587     throw new Error('SwfSoundStream.decode: not implemented');
  4589 };
  4590 function SwfSoundStream_decode_PCM(data) {
  4591   var pcm = new Float32Array(data.length);
  4592   for (var i = 0; i < pcm.length; i++)
  4593     pcm[i] = (data[i] - 128) / 128;
  4594   this.currentSample += pcm.length / this.channels;
  4595   return {
  4596     streamId: this.streamId,
  4597     samplesCount: pcm.length / this.channels,
  4598     pcm: pcm
  4599   };
  4601 function SwfSoundStream_decode_PCM_be(data) {
  4602   var pcm = new Float32Array(data.length / 2);
  4603   for (var i = 0, j = 0; i < pcm.length; i++, j += 2)
  4604     pcm[i] = (data[j] << 24 | data[j + 1] << 16) / 2147483648;
  4605   this.currentSample += pcm.length / this.channels;
  4606   return {
  4607     streamId: this.streamId,
  4608     samplesCount: pcm.length / this.channels,
  4609     pcm: pcm
  4610   };
  4612 function SwfSoundStream_decode_PCM_le(data) {
  4613   var pcm = new Float32Array(data.length / 2);
  4614   for (var i = 0, j = 0; i < pcm.length; i++, j += 2)
  4615     pcm[i] = (data[j + 1] << 24 | data[j] << 16) / 2147483648;
  4616   this.currentSample += pcm.length / this.channels;
  4617   return {
  4618     streamId: this.streamId,
  4619     samplesCount: pcm.length / this.channels,
  4620     pcm: pcm
  4621   };
  4623 function SwfSoundStream_decode_MP3(data) {
  4624   var samplesCount = data[1] << 8 | data[0];
  4625   var seek = data[3] << 8 | data[2];
  4626   this.currentSample += samplesCount;
  4627   return {
  4628     streamId: this.streamId,
  4629     samplesCount: samplesCount,
  4630     data: new Uint8Array(data.subarray(4)),
  4631     seek: seek
  4632   };
  4634 function createSoundStream(tag) {
  4635   var channels = tag.streamType == SOUND_TYPE_STEREO ? 2 : 1;
  4636   var samplesCount = tag.samplesCount;
  4637   var sampleRate = SOUND_RATES[tag.streamRate];
  4638   var stream = new SwfSoundStream(samplesCount, sampleRate, channels);
  4639   switch (tag.streamCompression) {
  4640   case SOUND_FORMAT_PCM_BE:
  4641     stream.format = 'wave';
  4642     if (tag.soundSize == SOUND_SIZE_16_BIT) {
  4643       stream.decode = SwfSoundStream_decode_PCM_be;
  4644     } else {
  4645       stream.decode = SwfSoundStream_decode_PCM;
  4647     break;
  4648   case SOUND_FORMAT_PCM_LE:
  4649     stream.format = 'wave';
  4650     if (tag.soundSize == SOUND_SIZE_16_BIT) {
  4651       stream.decode = SwfSoundStream_decode_PCM_le;
  4652     } else {
  4653       stream.decode = SwfSoundStream_decode_PCM;
  4655     break;
  4656   case SOUND_FORMAT_MP3:
  4657     stream.format = 'mp3';
  4658     stream.decode = SwfSoundStream_decode_MP3;
  4659     break;
  4660   default:
  4661     throw new Error('Unsupported audio format: ' + tag.soundFormat);
  4663   return stream;
  4665 function defineText(tag, dictionary) {
  4666   var dependencies = [];
  4667   if (tag.hasFont) {
  4668     var font = dictionary[tag.fontId];
  4669     tag.font = font.uniqueName;
  4670     dependencies.push(font.id);
  4672   var props = {
  4673       type: 'text',
  4674       id: tag.id,
  4675       variableName: tag.variableName,
  4676       tag: tag
  4677     };
  4678   if (dependencies.length)
  4679     props.require = dependencies;
  4680   return props;
  4682 var isWorker = typeof window === 'undefined';
  4683 if (isWorker) {
  4684   importScripts('../../../lib/mp3/mp3.js');
  4685   self.addEventListener('message', function (e) {
  4686     var data = e.data;
  4687     var sessionId = data.sessionId;
  4688     try {
  4689       switch (data.action) {
  4690       case 'create':
  4691         var session = new Session(sessionId);
  4692         sessions[sessionId] = session;
  4693         break;
  4694       case 'close':
  4695         var session = sessions[sessionId];
  4696         if (session) {
  4697           session.close();
  4698           sessions[sessionId] = null;
  4700         break;
  4701       case 'decode':
  4702         var session = sessions[sessionId];
  4703         if (!session) {
  4704           throw new Error('mp3 decoding session is unavailable');
  4706         session.decode(data.data);
  4707         break;
  4709     } catch (ex) {
  4710       self.postMessage({
  4711         sessionId: sessionId,
  4712         action: 'error',
  4713         message: ex.message
  4714       });
  4716   }, false);
  4717   var sessions = {};
  4718   function Session(id) {
  4719     this.id = id;
  4720     if (typeof MP3Decoder === 'undefined') {
  4721       throw new Error('mp3 decoder is not available');
  4723     var decoder = new MP3Decoder();
  4724     decoder.onframedata = function (frameData, channels, sampleRate, bitRate) {
  4725       self.postMessage({
  4726         sessionId: this.id,
  4727         action: 'frame',
  4728         frameData: frameData,
  4729         channels: channels,
  4730         sampleRate: sampleRate,
  4731         bitRate: bitRate
  4732       });
  4733     }.bind(this);
  4734     decoder.onid3tag = function (data) {
  4735       self.postMessage({
  4736         sessionId: this.id,
  4737         action: 'id3',
  4738         id3Data: data
  4739       });
  4740     }.bind(this);
  4741     this.decoder = decoder;
  4743   Session.prototype = {
  4744     decode: function (data) {
  4745       this.decoder.push(data);
  4746     },
  4747     close: function () {
  4748       self.postMessage({
  4749         sessionId: this.id,
  4750         action: 'closed'
  4751       });
  4753   };
  4754   self.console = {
  4755     log: function (s) {
  4756       self.postMessage({
  4757         action: 'console',
  4758         method: 'log',
  4759         message: s
  4760       });
  4761     },
  4762     error: function (s) {
  4763       self.postMessage({
  4764         action: 'console',
  4765         method: 'error',
  4766         message: s
  4767       });
  4769   };
  4770 } else {
  4771   var mp3Worker;
  4772   function createMP3Worker() {
  4773     var worker = new Worker(SHUMWAY_ROOT + 'swf/mp3worker.js');
  4774     worker.addEventListener('message', function (e) {
  4775       if (e.data.action === 'console') {
  4776         console[e.data.method].call(console, e.data.message);
  4778     });
  4779     return worker;
  4781   var nextSessionId = 0;
  4782   function MP3DecoderSession() {
  4783     mp3Worker = mp3Worker || createMP3Worker();
  4784     var sessionId = nextSessionId++;
  4785     this.id = sessionId;
  4786     this.onworkermessage = function (e) {
  4787       if (e.data.sessionId !== sessionId)
  4788         return;
  4789       var action = e.data.action;
  4790       switch (action) {
  4791       case 'closed':
  4792         if (this.onclosed)
  4793           this.onclosed();
  4794         mp3Worker.removeEventListener('message', this.onworkermessage, false);
  4795         break;
  4796       case 'frame':
  4797         this.onframedata(e.data.frameData, e.data.channels, e.data.sampleRate, e.data.bitRate);
  4798         break;
  4799       case 'id3':
  4800         if (this.onid3tag)
  4801           this.onid3tag(e.data.id3Data);
  4802         break;
  4803       case 'error':
  4804         if (this.onerror)
  4805           this.onerror(e.data.message);
  4806         break;
  4808     }.bind(this);
  4809     mp3Worker.addEventListener('message', this.onworkermessage, false);
  4810     mp3Worker.postMessage({
  4811       sessionId: sessionId,
  4812       action: 'create'
  4813     });
  4815   MP3DecoderSession.prototype = {
  4816     pushAsync: function (data) {
  4817       mp3Worker.postMessage({
  4818         sessionId: this.id,
  4819         action: 'decode',
  4820         data: data
  4821       });
  4822     },
  4823     close: function () {
  4824       mp3Worker.postMessage({
  4825         sessionId: this.id,
  4826         action: 'close'
  4827       });
  4829   };
  4830   MP3DecoderSession.processAll = function (data, onloaded) {
  4831     var currentBufferSize = 8000;
  4832     var currentBuffer = new Float32Array(currentBufferSize);
  4833     var bufferPosition = 0;
  4834     var id3Tags = [];
  4835     var sessionAborted = false;
  4836     var session = new MP3DecoderSession();
  4837     session.onframedata = function (frameData, channels, sampleRate, bitRate) {
  4838       var needed = frameData.length + bufferPosition;
  4839       if (needed > currentBufferSize) {
  4840         do {
  4841           currentBufferSize *= 2;
  4842         } while (needed > currentBufferSize);
  4843         var newBuffer = new Float32Array(currentBufferSize);
  4844         newBuffer.set(currentBuffer);
  4845         currentBuffer = newBuffer;
  4847       currentBuffer.set(frameData, bufferPosition);
  4848       bufferPosition += frameData.length;
  4849     };
  4850     session.onid3tag = function (tagData) {
  4851       id3Tags.push(tagData);
  4852     };
  4853     session.onclosed = function () {
  4854       if (sessionAborted)
  4855         return;
  4856       onloaded(currentBuffer.subarray(0, bufferPosition), id3Tags);
  4857     };
  4858     session.onerror = function (error) {
  4859       if (sessionAborted)
  4860         return;
  4861       sessionAborted = true;
  4862       onloaded(null, null, error);
  4863     };
  4864     session.pushAsync(data);
  4865     session.close();
  4866   };
  4868 SWF.embed = function (file, doc, container, options) {
  4869   var canvas = doc.createElement('canvas');
  4870   var ctx = canvas.getContext('2d');
  4871   var loader = new flash.display.Loader();
  4872   var loaderInfo = loader._contentLoaderInfo;
  4873   var stage = new flash.display.Stage();
  4874   var pixelRatio = 1;
  4875   var forceHidpiSetting = forceHidpi.value;
  4876   stage._loader = loader;
  4877   loaderInfo._parameters = options.movieParams;
  4878   loaderInfo._url = options.url || (typeof file === 'string' ? file : null);
  4879   loaderInfo._loaderURL = options.loaderURL || loaderInfo._url;
  4880   loader._parent = stage;
  4881   loader._stage = stage;
  4882   function setCanvasSize(width, height) {
  4883     if (pixelRatio === 1) {
  4884       canvas.width = width | 0;
  4885       canvas.height = height | 0;
  4886       return;
  4888     var canvasWidth = Math.floor(width * pixelRatio);
  4889     var canvasHeight = Math.floor(height * pixelRatio);
  4890     canvas.style.width = canvasWidth / pixelRatio + 'px';
  4891     canvas.style.height = canvasHeight / pixelRatio + 'px';
  4892     canvas.width = canvasWidth;
  4893     canvas.height = canvasHeight;
  4895   function fitCanvas(container) {
  4896     setCanvasSize(container.clientWidth, container.clientHeight);
  4897     stage._invalid = true;
  4899   loaderInfo._addEventListener('init', function () {
  4900     if (forceHidpiSetting || loaderInfo._swfVersion >= 18) {
  4901       pixelRatio = 'devicePixelRatio' in window ? window.devicePixelRatio : 1;
  4903     canvas._pixelRatio = pixelRatio;
  4904     stage._contentsScaleFactor = pixelRatio;
  4905     if (container.clientHeight) {
  4906       fitCanvas(container);
  4907       window.addEventListener('resize', function () {
  4908         fitCanvas(container);
  4909       });
  4910     } else {
  4911       setCanvasSize(stage._stageWidth / 20, stage._stageHeight / 20);
  4913     container.setAttribute('style', 'position: relative');
  4914     canvas.addEventListener('click', function () {
  4915       ShumwayKeyboardListener.focus = stage;
  4916       stage._mouseTarget._dispatchEvent('click');
  4917     });
  4918     canvas.addEventListener('dblclick', function () {
  4919       if (stage._mouseTarget._doubleClickEnabled) {
  4920         stage._mouseTarget._dispatchEvent('doubleClick');
  4922     });
  4923     canvas.addEventListener('mousedown', function () {
  4924       stage._mouseEvents.push('mousedown');
  4925     });
  4926     canvas.addEventListener('mousemove', function (domEvt) {
  4927       var node = this;
  4928       var left = 0;
  4929       var top = 0;
  4930       if (node.offsetParent) {
  4931         do {
  4932           left += node.offsetLeft;
  4933           top += node.offsetTop;
  4934         } while (node = node.offsetParent);
  4936       var m = stage._concatenatedTransform;
  4937       var mouseX = ((domEvt.pageX - left) * pixelRatio - m.tx / 20) / m.a;
  4938       var mouseY = ((domEvt.pageY - top) * pixelRatio - m.ty / 20) / m.d;
  4939       if (mouseX !== stage._mouseX || mouseY !== stage._mouseY) {
  4940         stage._mouseMoved = true;
  4941         stage._mouseX = mouseX * 20;
  4942         stage._mouseY = mouseY * 20;
  4944     });
  4945     canvas.addEventListener('mouseup', function () {
  4946       stage._mouseEvents.push('mouseup');
  4947     });
  4948     canvas.addEventListener('mouseover', function () {
  4949       stage._mouseMoved = true;
  4950       stage._mouseOver = true;
  4951     });
  4952     canvas.addEventListener('mouseout', function () {
  4953       stage._mouseMoved = true;
  4954       stage._mouseOver = false;
  4955     });
  4956     window.addEventListener('message', function (evt) {
  4957       var data = evt.data;
  4958       if (typeof data !== 'object' || data === null) {
  4959         return;
  4961       var type = data.type;
  4962       switch (type) {
  4963       case 'mousemove':
  4964       case 'mouseup':
  4965       case 'mousedown':
  4966         var isMouseMove = type === 'mousemove';
  4967         stage._mouseMoved = true;
  4968         stage._mouseOver = true;
  4969         stage._mouseX = data.x * 20;
  4970         stage._mouseY = data.y * 20;
  4971         if (!isMouseMove) {
  4972           stage._mouseEvents.push(type);
  4974         break;
  4975       case 'mouseover':
  4976       case 'mouseout':
  4977         stage._mouseMoved = true;
  4978         stage._mouseOver = type === 'mouseover';
  4979         break;
  4980       case 'keyup':
  4981       case 'keydown':
  4982         stage._dispatchEvent(new flash.events.KeyboardEvent(type === 'keyup' ? 'keyUp' : 'keyDown', true, false, data.charCode, data.keyCode, data.keyLocation, data.ctrlKey || false, data.altKey || false, data.shiftKey || false));
  4983         break;
  4985     }, false);
  4986     var bgcolor = loaderInfo._backgroundColor;
  4987     if (options.objectParams) {
  4988       var m;
  4989       if (options.objectParams.bgcolor && (m = /#([0-9A-F]{6})/i.exec(options.objectParams.bgcolor))) {
  4990         var hexColor = parseInt(m[1], 16);
  4991         bgcolor = {
  4992           red: hexColor >> 16 & 255,
  4993           green: hexColor >> 8 & 255,
  4994           blue: hexColor & 255,
  4995           alpha: 255
  4996         };
  4998       if (options.objectParams.wmode === 'transparent') {
  4999         bgcolor = {
  5000           red: 0,
  5001           green: 0,
  5002           blue: 0,
  5003           alpha: 0
  5004         };
  5007     stage._color = bgcolor;
  5008     ctx.fillStyle = rgbaObjToStr(bgcolor);
  5009     ctx.fillRect(0, 0, canvas.width, canvas.height);
  5010     var root = loader._content;
  5011     root._dispatchEvent('added', undefined, true);
  5012     root._dispatchEvent('addedToStage');
  5013     container.appendChild(canvas);
  5014     stage._domContainer = container;
  5015     if (options.onStageInitialized) {
  5016       options.onStageInitialized(stage);
  5018     var startPromise = options.startPromise || Promise.resolve();
  5019     startPromise.then(function () {
  5020       renderStage(stage, ctx, options);
  5021     });
  5022   });
  5023   if (options.onParsed) {
  5024     loaderInfo._addEventListener('parsed', function () {
  5025       options.onParsed();
  5026     });
  5028   if (options.onComplete) {
  5029     loaderInfo._addEventListener('complete', function () {
  5030       options.onComplete();
  5031     });
  5033   loader._load(typeof file === 'string' ? new flash.net.URLRequest(file) : file);
  5034   return loader;
  5035 };
  5036 var rendererOptions = coreOptions.register(new OptionSet('Renderer Options'));
  5037 var traceRenderer = rendererOptions.register(new Option('tr', 'traceRenderer', 'number', 0, 'trace renderer execution'));
  5038 var disableRenderVisitor = rendererOptions.register(new Option('drv', 'disableRenderVisitor', 'boolean', false, 'disable render visitor'));
  5039 var disableMouseVisitor = rendererOptions.register(new Option('dmv', 'disableMouseVisitor', 'boolean', false, 'disable mouse visitor'));
  5040 var showRedrawRegions = rendererOptions.register(new Option('rr', 'showRedrawRegions', 'boolean', false, 'show redraw regions'));
  5041 var renderAsWireframe = rendererOptions.register(new Option('raw', 'renderAsWireframe', 'boolean', false, 'render as wireframe'));
  5042 var showQuadTree = rendererOptions.register(new Option('qt', 'showQuadTree', 'boolean', false, 'show quad tree'));
  5043 var turboMode = rendererOptions.register(new Option('', 'turbo', 'boolean', false, 'turbo mode'));
  5044 var forceHidpi = rendererOptions.register(new Option('', 'forceHidpi', 'boolean', false, 'force hidpi'));
  5045 var skipFrameDraw = rendererOptions.register(new Option('', 'skipFrameDraw', 'boolean', false, 'skip frame when not on time'));
  5046 var hud = rendererOptions.register(new Option('', 'hud', 'boolean', false, 'show hud mode'));
  5047 var dummyAnimation = rendererOptions.register(new Option('', 'dummy', 'boolean', false, 'show test balls animation'));
  5048 var enableConstructChildren = rendererOptions.register(new Option('', 'constructChildren', 'boolean', true, 'Construct Children'));
  5049 var enableEnterFrame = rendererOptions.register(new Option('', 'enterFrame', 'boolean', true, 'Enter Frame'));
  5050 var enableAdvanceFrame = rendererOptions.register(new Option('', 'advanceFrame', 'boolean', true, 'Advance Frame'));
  5051 var CanvasCache = {
  5052     cache: [],
  5053     getCanvas: function getCanvas(protoCanvas) {
  5054       var tempCanvas = this.cache.shift();
  5055       if (!tempCanvas) {
  5056         tempCanvas = {
  5057           canvas: document.createElement('canvas')
  5058         };
  5059         tempCanvas.ctx = tempCanvas.canvas.getContext('2d');
  5061       tempCanvas.canvas.width = protoCanvas.width;
  5062       tempCanvas.canvas.height = protoCanvas.height;
  5063       tempCanvas.ctx.save();
  5064       return tempCanvas;
  5065     },
  5066     releaseCanvas: function releaseCanvas(tempCanvas) {
  5067       tempCanvas.ctx.restore();
  5068       this.cache.push(tempCanvas);
  5070   };
  5071 function isCanvasVisible(canvas) {
  5072   if (canvas.ownerDocument.hidden) {
  5073     return false;
  5075   if (canvas.mozVisible === false) {
  5076     return false;
  5078   return true;
  5080 function visitContainer(container, visitor, context) {
  5081   var children = container._children;
  5082   visitor.childrenStart(container);
  5083   for (var i = 0, n = children.length; i < n; i++) {
  5084     var child = children[i];
  5085     if (!child) {
  5086       continue;
  5088     if (visitor.ignoreVisibleAttribute || child._visible && !child._maskedObject) {
  5089       visitor.visit(child, visitContainer, context);
  5092   visitor.childrenEnd(container);
  5094 var BlendModeNameMap = {
  5095     'normal': 'normal',
  5096     'multiply': 'multiply',
  5097     'screen': 'screen',
  5098     'lighten': 'lighten',
  5099     'darken': 'darken',
  5100     'difference': 'difference',
  5101     'overlay': 'overlay',
  5102     'hardlight': 'hard-light'
  5103   };
  5104 function getBlendModeName(blendMode) {
  5105   return BlendModeNameMap[blendMode] || 'normal';
  5107 function RenderVisitor(root, ctx, invalidPath, refreshStage) {
  5108   this.root = root;
  5109   this.ctx = ctx;
  5110   this.depth = 0;
  5111   this.invalidPath = invalidPath;
  5112   this.refreshStage = refreshStage;
  5113   this.clipDepth = null;
  5114   this.clipStack = null;
  5116 RenderVisitor.prototype = {
  5117   ignoreVisibleAttribute: false,
  5118   start: function () {
  5119     visitContainer(this.root, this, new RenderingContext(this.refreshStage, this.invalidPath));
  5120   },
  5121   startFragment: function (matrix) {
  5122     var root = this.root;
  5123     var currentTransform = root._currentTransform;
  5124     var t = currentTransform;
  5125     if (matrix) {
  5126       t = root._currentTransform = {
  5127         a: matrix.a,
  5128         b: matrix.b,
  5129         c: matrix.c,
  5130         d: matrix.d,
  5131         tx: matrix.tx * 20 | 0,
  5132         ty: matrix.ty * 20 | 0
  5133       };
  5134       root._invalidateTransform();
  5136     var inverse;
  5137     if (t) {
  5138       inverse = new flash.geom.Matrix(t.a, t.b, t.c, t.d, t.tx / 20, t.ty / 20);
  5139       inverse.invert();
  5140       this.ctx.save();
  5141       this.ctx.transform(inverse.a, inverse.b, inverse.c, inverse.d, inverse.tx, inverse.ty);
  5143     this.visit(root, visitContainer, new RenderingContext(this.refreshStage, this.invalidPath));
  5144     if (t) {
  5145       this.ctx.restore();
  5147     if (matrix) {
  5148       root._currentTransform = currentTransform;
  5149       root._invalidateTransform();
  5151   },
  5152   childrenStart: function (parent) {
  5153     if (this.depth === 0) {
  5154       var ctx = this.ctx;
  5155       ctx.save();
  5156       if (this.invalidPath && !this.refreshStage && !renderAsWireframe.value) {
  5157         this.invalidPath.draw(ctx, false, 0, null);
  5158         ctx.clip();
  5160       var bgcolor = this.root._color;
  5161       if (bgcolor) {
  5162         if (bgcolor.alpha < 255) {
  5163           ctx.clearRect(0, 0, ctx.canvas.width, ctx.canvas.height);
  5165         if (bgcolor.alpha > 0) {
  5166           ctx.fillStyle = rgbaObjToStr(bgcolor);
  5167           if (this.invalidPath && !this.refreshStage && !renderAsWireframe.value) {
  5168             ctx.fill();
  5169           } else {
  5170             ctx.fillRect(0, 0, ctx.canvas.width, ctx.canvas.height);
  5174       ctx.mozFillRule = 'evenodd';
  5176     this.depth++;
  5177     if (this.clipDepth && this.clipDepth.length > 0) {
  5178       this.clipStack = {
  5179         depth: this.depth,
  5180         clip: this.clipDepth,
  5181         next: this.clipStack
  5182       };
  5183       this.clipDepth = null;
  5185   },
  5186   childrenEnd: function (parent) {
  5187     if (this.clipDepth) {
  5188       while (this.clipDepth.length > 0) {
  5189         var clipDepthInfo = this.clipDepth.pop();
  5190         this.clipEnd(clipDepthInfo);
  5191         this.ctx = clipDepthInfo.ctx;
  5193       this.clipDepth = null;
  5195     if (this.clipStack && this.clipStack.depth === this.depth) {
  5196       this.clipDepth = this.clipStack.clip;
  5197       this.clipStack = this.clipStack.next;
  5199     this.depth--;
  5200     if (this.depth === 0) {
  5201       this.ctx.restore();
  5202       this.invalidPath = null;
  5204   },
  5205   visit: function (child, visitContainer, context) {
  5206     var ctx = this.ctx;
  5207     var parentHasClippingMask = context.isClippingMask;
  5208     var parentColorTransform = context.colorTransform;
  5209     var clippingMask = parentHasClippingMask === true;
  5210     if (child._cxform) {
  5211       context.colorTransform = parentColorTransform.applyCXForm(child._cxform);
  5213     if (!clippingMask) {
  5214       while (this.clipDepth && this.clipDepth.length > 0 && child._depth > this.clipDepth[0].clipDepth) {
  5215         var clipDepthInfo = this.clipDepth.shift();
  5216         this.clipEnd(clipDepthInfo);
  5217         context.parentCtxs.shift();
  5218         ctx = this.ctx = clipDepthInfo.ctx;
  5220       if (this.clipDepth && this.clipDepth.length > 0 && child._depth <= this.clipDepth[0].clipDepth) {
  5221         ctx = this.ctx = this.clipDepth[0].maskee.ctx;
  5223       if (child._clipDepth) {
  5224         context.isClippingMask = clippingMask = true;
  5225         var clipDepthInfo = this.clipStart(child);
  5226         if (!this.clipDepth) {
  5227           this.clipDepth = [
  5228             clipDepthInfo
  5229           ];
  5230         } else {
  5231           this.clipDepth.unshift(clipDepthInfo);
  5233         context.parentCtxs.unshift(ctx);
  5234         ctx = this.ctx = clipDepthInfo.mask.ctx;
  5237     if (clippingMask && child._isContainer) {
  5238       ctx.save();
  5239       renderDisplayObject(child, ctx, context);
  5240       for (var i = 0, n = child._children.length; i < n; i++) {
  5241         var child1 = child._children[i];
  5242         if (!child1) {
  5243           continue;
  5245         if (this.ignoreVisibleAttribute || child1._visible && !child1._maskedObject) {
  5246           this.visit(child1, visitContainer, context);
  5249       ctx.restore();
  5250       ctx.fill();
  5251       context.isClippingMask = parentHasClippingMask;
  5252       context.colorTransform = parentColorTransform;
  5253       return;
  5255     ctx.save();
  5256     ctx.globalCompositeOperation = getBlendModeName(child._blendMode);
  5257     if (child._mask) {
  5258       var clipInfo = this.clipStart(child);
  5259       var mask = clipInfo.mask;
  5260       var maskee = clipInfo.maskee;
  5261       context.parentCtxs.push(ctx);
  5262       var savedClipDepth = this.clipDepth;
  5263       this.clipDepth = null;
  5264       this.ctx = mask.ctx;
  5265       this.visit(child._mask, visitContainer, new RenderingContext(this.refreshStage));
  5266       this.ctx = ctx;
  5267       this.clipDepth = savedClipDepth;
  5268       renderDisplayObject(child, maskee.ctx, context);
  5269       if (child._isContainer) {
  5270         this.ctx = maskee.ctx;
  5271         visitContainer(child, this, context);
  5272         this.ctx = ctx;
  5274       context.parentCtxs.pop();
  5275       this.clipEnd(clipInfo);
  5276     } else {
  5277       renderDisplayObject(child, ctx, context);
  5278       if (child._isContainer) {
  5279         visitContainer(child, this, context);
  5282     ctx.restore();
  5283     if (clippingMask) {
  5284       ctx.fill();
  5286     context.isClippingMask = parentHasClippingMask;
  5287     context.colorTransform = parentColorTransform;
  5288   },
  5289   clipStart: function (child) {
  5290     var m = child._parent._getConcatenatedTransform(null, true);
  5291     var tx = m.tx / 20;
  5292     var ty = m.ty / 20;
  5293     var mask = CanvasCache.getCanvas(this.ctx.canvas);
  5294     mask.ctx.setTransform(m.a, m.b, m.c, m.d, tx, ty);
  5295     var maskee = CanvasCache.getCanvas(this.ctx.canvas);
  5296     maskee.ctx.setTransform(m.a, m.b, m.c, m.d, tx, ty);
  5297     var clipInfo = {
  5298         ctx: this.ctx,
  5299         mask: mask,
  5300         maskee: maskee,
  5301         clipDepth: child._clipDepth
  5302       };
  5303     return clipInfo;
  5304   },
  5305   clipEnd: function (clipInfo) {
  5306     var ctx = clipInfo.ctx;
  5307     var mask = clipInfo.mask;
  5308     var maskee = clipInfo.maskee;
  5309     maskee.ctx.globalCompositeOperation = 'destination-in';
  5310     maskee.ctx.setTransform(1, 0, 0, 1, 0, 0);
  5311     maskee.ctx.drawImage(mask.canvas, 0, 0);
  5312     ctx.save();
  5313     ctx.setTransform(1, 0, 0, 1, 0, 0);
  5314     ctx.drawImage(maskee.canvas, 0, 0);
  5315     ctx.restore();
  5316     CanvasCache.releaseCanvas(mask);
  5317     CanvasCache.releaseCanvas(maskee);
  5319 };
  5320 function RenderingColorTransform() {
  5321   this.mode = null;
  5322   this.transform = [
  5323     1,
  5324     1,
  5325     1,
  5326     1,
  5327     0,
  5328     0,
  5329     0,
  5331   ];
  5333 RenderingColorTransform.prototype = {
  5334   applyCXForm: function (cxform) {
  5335     var t = this.transform;
  5336     t = [
  5337       t[0] * cxform.redMultiplier / 256,
  5338       t[1] * cxform.greenMultiplier / 256,
  5339       t[2] * cxform.blueMultiplier / 256,
  5340       t[3] * cxform.alphaMultiplier / 256,
  5341       t[4] * cxform.redMultiplier / 256 + cxform.redOffset,
  5342       t[5] * cxform.greenMultiplier / 256 + cxform.greenOffset,
  5343       t[6] * cxform.blueMultiplier / 256 + cxform.blueOffset,
  5344       t[7] * cxform.alphaMultiplier / 256 + cxform.alphaOffset
  5345     ];
  5346     var mode;
  5347     var PRECISION = 0.0001;
  5348     if (Math.abs(t[0] - 1) < PRECISION && Math.abs(t[1] - 1) < PRECISION && Math.abs(t[2] - 1) < PRECISION && t[3] >= 0 && Math.abs(t[4]) < PRECISION && Math.abs(t[5]) < PRECISION && Math.abs(t[6]) < PRECISION && Math.abs(t[7]) < PRECISION) {
  5349       mode = Math.abs(t[3] - 1) < PRECISION ? null : 'simple';
  5350     } else {
  5351       mode = 'complex';
  5353     var clone = Object.create(RenderingColorTransform.prototype);
  5354     clone.mode = mode;
  5355     clone.transform = t;
  5356     return clone;
  5357   },
  5358   setFillStyle: function (ctx, style) {
  5359     if (this.mode === 'complex') {
  5360       style = typeof style === 'function' ? style(ctx, this) : this.convertColor(style);
  5361     } else if (typeof style === 'number') {
  5362       style = this.convertNumericColor(style);
  5363     } else if (typeof style === 'function') {
  5364       style = style.defaultFillStyle;
  5366     ctx.fillStyle = style;
  5367   },
  5368   setStrokeStyle: function (ctx, style) {
  5369     if (this.mode === 'complex') {
  5370       style = typeof style === 'function' ? style(ctx, this) : this.convertColor(style);
  5371     } else if (typeof style === 'number') {
  5372       style = this.convertNumericColor(style);
  5373     } else if (typeof style === 'function') {
  5374       style = style.defaultFillStyle;
  5376     ctx.strokeStyle = style;
  5377   },
  5378   addGradientColorStop: function (gradient, ratio, style) {
  5379     if (this.mode === 'complex') {
  5380       style = this.convertColor(style);
  5381     } else if (typeof style === 'number') {
  5382       style = this.convertNumericColor(style);
  5384     gradient.addColorStop(ratio, style);
  5385   },
  5386   setAlpha: function (ctx, force) {
  5387     if (this.mode === 'simple' || force) {
  5388       var t = this.transform;
  5389       ctx.globalAlpha = Math.min(1, Math.max(0, ctx.globalAlpha * t[3]));
  5391   },
  5392   convertNumericColor: function (num) {
  5393     return '#' + (num | 16777216).toString(16).substr(1);
  5394   },
  5395   convertColor: function (style) {
  5396     var t = this.transform;
  5397     var m;
  5398     switch (typeof style) {
  5399     case 'string':
  5400       if (style[0] === '#') {
  5401         m = [
  5402           undefined,
  5403           parseInt(style.substr(1, 2), 16),
  5404           parseInt(style.substr(3, 2), 16),
  5405           parseInt(style.substr(5, 2), 16),
  5407         ];
  5409       m = m || /rgba\(([^,]+),([^,]+),([^,]+),([^)]+)\)/.exec(style);
  5410       if (!m) {
  5411         return style;
  5413       break;
  5414     case 'number':
  5415       m = [
  5416         style,
  5417         style >> 16 & 255,
  5418         style >> 8 & 255,
  5419         style & 255,
  5421       ];
  5422       break;
  5423     default:
  5424       return style;
  5426     var r = Math.min(255, Math.max(0, m[1] * t[0] + t[4])) | 0;
  5427     var g = Math.min(255, Math.max(0, m[2] * t[1] + t[5])) | 0;
  5428     var b = Math.min(255, Math.max(0, m[3] * t[2] + t[6])) | 0;
  5429     var a = Math.min(1, Math.max(0, m[4] * t[3] + t[7] / 256));
  5430     return 'rgba(' + r + ',' + g + ',' + b + ',' + a + ')';
  5431   },
  5432   getTransformFingerprint: function () {
  5433     return this.transform.join('|');
  5435 };
  5436 function RenderingContext(refreshStage, invalidPath) {
  5437   this.refreshStage = refreshStage === true;
  5438   this.invalidPath = invalidPath;
  5439   this.isClippingMask = false;
  5440   this.colorTransform = new RenderingColorTransform();
  5441   this.parentCtxs = [];
  5443 function renderDisplayObject(child, ctx, context) {
  5444   var m = child._currentTransform;
  5445   if (m) {
  5446     ctx.transform(m.a, m.b, m.c, m.d, m.tx / 20, m.ty / 20);
  5448   if (!renderAsWireframe.value) {
  5449     if (child._alpha !== 1) {
  5450       ctx.globalAlpha *= child._alpha;
  5452     if (context.invalidPath && !child._invalid && !context.refreshStage) {
  5453       return;
  5455     if (child._graphics) {
  5456       var graphics = child._graphics;
  5457       if (graphics._bitmap) {
  5458         ctx.save();
  5459         ctx.translate(child._bbox.xMin / 20, child._bbox.yMin / 20);
  5460         context.colorTransform.setAlpha(ctx, true);
  5461         ctx.drawImage(graphics._bitmap, 0, 0);
  5462         ctx.restore();
  5463       } else {
  5464         var ratio = child.ratio;
  5465         if (ratio === undefined) {
  5466           ratio = 0;
  5468         graphics.draw(ctx, context.isClippingMask, ratio, context.colorTransform);
  5471     if (child.draw) {
  5472       child.draw(ctx, child.ratio, context.colorTransform, context.parentCtxs);
  5474   } else {
  5475     if (!child._invalid && !context.refreshStage) {
  5476       return;
  5478     if (child.getBounds) {
  5479       var b = child.getBounds(null);
  5480       if (b && b.xMax - b.xMin > 0 && b.yMax - b.yMin > 0) {
  5481         if (!child._wireframeStrokeStyle) {
  5482           child._wireframeStrokeStyle = randomStyle();
  5484         ctx.save();
  5485         ctx.strokeStyle = child._wireframeStrokeStyle;
  5486         var x = b.xMin / 20;
  5487         var y = b.yMin / 20;
  5488         ctx.strokeRect(x + 0.5, y + 0.5, b.xMax / 20 - x - 1, b.yMax / 20 - y - 1);
  5489         ctx.restore();
  5493   child._invalid = false;
  5495 function renderQuadTree(ctx, qtree) {
  5496   ctx.strokeRect(qtree.x / 20, qtree.y / 20, qtree.width / 20, qtree.height / 20);
  5497   var nodes = qtree.nodes;
  5498   for (var i = 0; i < nodes.length; i++) {
  5499     renderQuadTree(ctx, nodes[i]);
  5502 var renderingTerminated = false;
  5503 var samplesLeftPlusOne = 0;
  5504 function triggerSampling(count) {
  5505   samplesLeftPlusOne = -count - 1;
  5507 function sampleStart() {
  5508   if (!samplesLeftPlusOne) {
  5509     return;
  5511   if (samplesLeftPlusOne < 0) {
  5512     console.profile('Sample');
  5513     samplesLeftPlusOne *= -1;
  5515   if (samplesLeftPlusOne > 0) {
  5516     console.info('Sampling Frame: ' + (samplesLeftPlusOne - 1));
  5519 function sampleEnd() {
  5520   if (!samplesLeftPlusOne) {
  5521     return;
  5523   samplesLeftPlusOne--;
  5524   if (samplesLeftPlusOne === 1) {
  5525     console.profileEnd('Sample');
  5528 var timeline;
  5529 var hudTimeline;
  5530 function timelineEnter(name) {
  5531   timeline && timeline.enter(name);
  5532   hudTimeline && hudTimeline.enter(name);
  5534 function timelineLeave(name) {
  5535   timeline && timeline.leave(name);
  5536   hudTimeline && hudTimeline.leave(name);
  5538 function timelineWrapBroadcastMessage(domain, message) {
  5539   timelineEnter(message);
  5540   domain.broadcastMessage(message);
  5541   timelineLeave(message);
  5543 function initializeHUD(stage, parentCanvas) {
  5544   var canvas = document.createElement('canvas');
  5545   var canvasContainer = document.createElement('div');
  5546   canvasContainer.appendChild(canvas);
  5547   canvasContainer.style.position = 'absolute';
  5548   canvasContainer.style.top = '0px';
  5549   canvasContainer.style.left = '0px';
  5550   canvasContainer.style.width = '100%';
  5551   canvasContainer.style.height = '150px';
  5552   canvasContainer.style.backgroundColor = 'rgba(0, 0, 0, 0.4)';
  5553   canvasContainer.style.pointerEvents = 'none';
  5554   parentCanvas.parentElement.appendChild(canvasContainer);
  5555   hudTimeline = new Timeline(canvas);
  5556   hudTimeline.setFrameRate(stage._frameRate);
  5557   hudTimeline.refreshEvery(10);
  5559 function createRenderDummyBalls(ctx, stage) {
  5560   var dummyBalls;
  5561   var radius = 10;
  5562   var speed = 1;
  5563   var m = stage._concatenatedTransform;
  5564   var scaleX = m.a, scaleY = m.d;
  5565   dummyBalls = [];
  5566   for (var i = 0; i < 10; i++) {
  5567     dummyBalls.push({
  5568       position: {
  5569         x: radius + Math.random() * ((ctx.canvas.width - 2 * radius) / scaleX),
  5570         y: radius + Math.random() * ((ctx.canvas.height - 2 * radius) / scaleY)
  5571       },
  5572       velocity: {
  5573         x: speed * (Math.random() - 0.5),
  5574         y: speed * (Math.random() - 0.5)
  5576     });
  5578   ctx.fillStyle = 'black';
  5579   ctx.lineWidth = 2;
  5580   ctx.fillRect(0, 0, ctx.canvas.width, ctx.canvas.height);
  5581   return function renderDummyBalls() {
  5582     ctx.fillStyle = 'black';
  5583     ctx.fillRect(0, 0, ctx.canvas.width, ctx.canvas.height);
  5584     ctx.strokeStyle = 'green';
  5585     dummyBalls.forEach(function (ball) {
  5586       var position = ball.position;
  5587       var velocity = ball.velocity;
  5588       ctx.beginPath();
  5589       ctx.arc(position.x, position.y, radius, 0, Math.PI * 2, true);
  5590       ctx.stroke();
  5591       var x = position.x + velocity.x;
  5592       var y = position.y + velocity.y;
  5593       if (x < radius || x > ctx.canvas.width / scaleX - radius) {
  5594         velocity.x *= -1;
  5596       if (y < radius || y > ctx.canvas.height / scaleY - radius) {
  5597         velocity.y *= -1;
  5599       position.x += velocity.x;
  5600       position.y += velocity.y;
  5601     });
  5602   };
  5604 function renderStage(stage, ctx, events) {
  5605   var frameWidth, frameHeight;
  5606   if (!timeline && hud.value) {
  5607     initializeHUD(stage, ctx.canvas);
  5609   function updateRenderTransform() {
  5610     frameWidth = ctx.canvas.width;
  5611     frameHeight = ctx.canvas.height;
  5612     var scaleX = frameWidth / stage._stageWidth * 20;
  5613     var scaleY = frameHeight / stage._stageHeight * 20;
  5614     switch (stage._scaleMode) {
  5615     case 'exactFit':
  5616       break;
  5617     case 'noBorder':
  5618       if (scaleX > scaleY) {
  5619         scaleY = scaleX;
  5620       } else {
  5621         scaleX = scaleY;
  5623       break;
  5624     case 'noScale':
  5625       var pixelRatio = ctx.canvas._pixelRatio || 1;
  5626       scaleX = pixelRatio;
  5627       scaleY = pixelRatio;
  5628       break;
  5629     case 'showAll':
  5630       if (scaleX < scaleY) {
  5631         scaleY = scaleX;
  5632       } else {
  5633         scaleX = scaleY;
  5635       break;
  5637     var align = stage._align;
  5638     var offsetX, offsetY;
  5639     if (align.indexOf('L') >= 0) {
  5640       offsetX = 0;
  5641     } else if (align.indexOf('R') >= 0) {
  5642       offsetX = frameWidth - scaleX * stage._stageWidth / 20;
  5643     } else {
  5644       offsetX = (frameWidth - scaleX * stage._stageWidth / 20) / 2;
  5646     if (align.indexOf('T') >= 0) {
  5647       offsetY = 0;
  5648     } else if (align.indexOf('B') >= 0) {
  5649       offsetY = frameHeight - scaleY * stage._stageHeight / 20;
  5650     } else {
  5651       offsetY = (frameHeight - scaleY * stage._stageHeight / 20) / 2;
  5653     ctx.setTransform(scaleX, 0, 0, scaleY, offsetX, offsetY);
  5654     var m = stage._concatenatedTransform;
  5655     m.a = scaleX;
  5656     m.d = scaleY;
  5657     m.tx = offsetX * 20;
  5658     m.ty = offsetY * 20;
  5660   updateRenderTransform();
  5661   var frameScheduler = new FrameScheduler();
  5662   stage._frameScheduler = frameScheduler;
  5663   var requestAnimationFrame = window.requestAnimationFrame || window.mozRequestAnimationFrame || window.webkitRequestAnimationFrame || window.oRequestAnimationFrame || window.msRequestAnimationFrame || window.setTimeout;
  5664   var renderDummyBalls = dummyAnimation.value && createRenderDummyBalls(ctx, stage);
  5665   console.timeEnd('Initialize Renderer');
  5666   console.timeEnd('Total');
  5667   var firstRun = true;
  5668   var frameCount = 0;
  5669   var frameFPSAverage = new Shumway.Metrics.Average(120);
  5670   var frameRequested = true;
  5671   function drawFrame(renderFrame, repaint) {
  5672     sampleStart();
  5673     var refreshStage = false;
  5674     if (stage._invalid) {
  5675       updateRenderTransform();
  5676       stage._invalid = false;
  5677       refreshStage = true;
  5679     var mouseMoved = false;
  5680     if (stage._mouseMoved) {
  5681       stage._mouseMoved = false;
  5682       mouseMoved = stage._mouseOver;
  5683     } else {
  5684       stage._handleMouseButtons();
  5686     if (renderFrame || refreshStage || mouseMoved) {
  5687       FrameCounter.clear();
  5688       var frameStartTime = performance.now();
  5689       timelineEnter('frame');
  5690       traceRenderer.value && appendToFrameTerminal('Begin Frame #' + frameCount++, 'purple');
  5691       var domain = avm2.systemDomain;
  5692       if (renderFrame) {
  5693         timelineEnter('events');
  5694         if (firstRun) {
  5695           firstRun = false;
  5696         } else {
  5697           enableAdvanceFrame.value && timelineWrapBroadcastMessage(domain, 'advanceFrame');
  5698           enableEnterFrame.value && timelineWrapBroadcastMessage(domain, 'enterFrame');
  5699           enableConstructChildren.value && timelineWrapBroadcastMessage(domain, 'constructChildren');
  5701         timelineWrapBroadcastMessage(domain, 'frameConstructed');
  5702         timelineWrapBroadcastMessage(domain, 'executeFrame');
  5703         timelineWrapBroadcastMessage(domain, 'exitFrame');
  5704         timelineLeave('events');
  5706       if (stage._deferRenderEvent) {
  5707         stage._deferRenderEvent = false;
  5708         domain.broadcastMessage('render', 'render');
  5710       var drawEnabled = isCanvasVisible(ctx.canvas) && (refreshStage || renderFrame) && (frameRequested || repaint || !skipFrameDraw.value);
  5711       if (drawEnabled && !repaint && skipFrameDraw.value && frameScheduler.shallSkipDraw) {
  5712         drawEnabled = false;
  5713         frameScheduler.skipDraw();
  5714         traceRenderer.value && appendToFrameTerminal('Skip Frame Draw', 'red');
  5716       if (drawEnabled) {
  5717         frameScheduler.startDraw();
  5718         var invalidPath = null;
  5719         traceRenderer.value && frameWriter.enter('> Invalidation');
  5720         timelineEnter('invalidate');
  5721         invalidPath = stage._processInvalidations(refreshStage);
  5722         timelineLeave('invalidate');
  5723         traceRenderer.value && frameWriter.leave('< Invalidation');
  5724         if (!disableRenderVisitor.value && !invalidPath.isEmpty) {
  5725           timelineEnter('render');
  5726           traceRenderer.value && frameWriter.enter('> Rendering');
  5727           new RenderVisitor(stage, ctx, invalidPath, refreshStage).start();
  5728           traceRenderer.value && frameWriter.leave('< Rendering');
  5729           timelineLeave('render');
  5731         if (showQuadTree.value) {
  5732           ctx.strokeStyle = 'green';
  5733           renderQuadTree(ctx, stage._qtree);
  5735         if (invalidPath && !refreshStage && showRedrawRegions.value) {
  5736           ctx.strokeStyle = 'red';
  5737           invalidPath.draw(ctx);
  5738           ctx.stroke();
  5740         frameScheduler.endDraw();
  5742       if (mouseMoved && !disableMouseVisitor.value) {
  5743         renderFrame && timelineEnter('mouse');
  5744         traceRenderer.value && frameWriter.enter('> Mouse Handling');
  5745         stage._handleMouse();
  5746         traceRenderer.value && frameWriter.leave('< Mouse Handling');
  5747         renderFrame && timelineLeave('mouse');
  5748         ctx.canvas.style.cursor = stage._cursor;
  5750       if (traceRenderer.value) {
  5751         frameWriter.enter('> Frame Counters');
  5752         for (var name in FrameCounter.counts) {
  5753           frameWriter.writeLn(name + ': ' + FrameCounter.counts[name]);
  5755         frameWriter.leave('< Frame Counters');
  5756         var frameElapsedTime = performance.now() - frameStartTime;
  5757         var frameFPS = 1000 / frameElapsedTime;
  5758         frameFPSAverage.push(frameFPS);
  5759         traceRenderer.value && appendToFrameTerminal('End Frame Time: ' + frameElapsedTime.toFixed(2) + ' (' + frameFPS.toFixed(2) + ' fps, ' + frameFPSAverage.average().toFixed(2) + ' average fps)', 'purple');
  5761       timelineLeave('frame');
  5762     } else {
  5763       traceRenderer.value && appendToFrameTerminal('Skip Frame', 'black');
  5765     sampleEnd();
  5767   (function draw() {
  5768     var renderFrame = true;
  5769     if (events.onBeforeFrame) {
  5770       var e = {
  5771           cancel: false
  5772         };
  5773       events.onBeforeFrame(e);
  5774       renderFrame = !e.cancel;
  5776     if (renderDummyBalls) {
  5777       if (renderFrame) {
  5778         renderDummyBalls();
  5779         events.onAfterFrame && events.onAfterFrame();
  5781       setTimeout(draw);
  5782       return;
  5784     frameScheduler.startFrame(stage._frameRate);
  5785     drawFrame(renderFrame, false);
  5786     frameScheduler.endFrame();
  5787     frameRequested = false;
  5788     if (!frameScheduler.isOnTime) {
  5789       traceRenderer.value && appendToFrameTerminal('Frame Is Late', 'red');
  5791     if (renderFrame && events.onAfterFrame) {
  5792       events.onAfterFrame();
  5794     if (renderingTerminated) {
  5795       if (events.onTerminated) {
  5796         events.onTerminated();
  5798       return;
  5800     setTimeout(draw, turboMode.value ? 0 : frameScheduler.nextFrameIn);
  5801   }());
  5802   (function frame() {
  5803     if (renderingTerminated) {
  5804       return;
  5806     frameRequested = true;
  5807     if ((stage._invalid || stage._mouseMoved) && !renderDummyBalls) {
  5808       drawFrame(false, true);
  5810     requestAnimationFrame(frame);
  5811   }());
  5813 var FrameScheduler = function () {
  5814     var STATS_TO_REMEMBER = 50;
  5815     var MAX_DRAWS_TO_SKIP = 2;
  5816     var INTERVAL_PADDING_MS = 4;
  5817     var SPEED_ADJUST_RATE = 0.9;
  5818     function FrameScheduler() {
  5819       this._drawStats = [];
  5820       this._drawStatsSum = 0;
  5821       this._drawStarted = 0;
  5822       this._drawsSkipped = 0;
  5823       this._expectedNextFrameAt = performance.now();
  5824       this._onTime = true;
  5825       this._trackDelta = false;
  5826       this._delta = 0;
  5827       this._onTimeDelta = 0;
  5829     FrameScheduler.prototype = {
  5830       get shallSkipDraw() {
  5831         if (this._drawsSkipped >= MAX_DRAWS_TO_SKIP) {
  5832           return false;
  5834         var averageDraw = this._drawStats.length < STATS_TO_REMEMBER ? 0 : this._drawStatsSum / this._drawStats.length;
  5835         var estimatedDrawEnd = performance.now() + averageDraw;
  5836         return estimatedDrawEnd + INTERVAL_PADDING_MS > this._expectedNextFrameAt;
  5837       },
  5838       get nextFrameIn() {
  5839         return Math.max(0, this._expectedNextFrameAt - performance.now());
  5840       },
  5841       get isOnTime() {
  5842         return this._onTime;
  5843       },
  5844       startFrame: function (frameRate) {
  5845         var interval = 1000 / frameRate;
  5846         var adjustedInterval = interval;
  5847         var delta = this._onTimeDelta + this._delta;
  5848         if (delta !== 0) {
  5849           if (delta < 0) {
  5850             adjustedInterval *= SPEED_ADJUST_RATE;
  5851           } else if (delta > 0) {
  5852             adjustedInterval /= SPEED_ADJUST_RATE;
  5854           this._onTimeDelta += interval - adjustedInterval;
  5856         this._expectedNextFrameAt += adjustedInterval;
  5857         this._onTime = true;
  5858       },
  5859       endFrame: function () {
  5860         var estimatedNextFrameStart = performance.now() + INTERVAL_PADDING_MS;
  5861         if (estimatedNextFrameStart > this._expectedNextFrameAt) {
  5862           if (this._trackDelta) {
  5863             this._onTimeDelta += this._expectedNextFrameAt - estimatedNextFrameStart;
  5864             console.log(this._onTimeDelta);
  5866           this._expectedNextFrameAt = estimatedNextFrameStart;
  5867           this._onTime = false;
  5869       },
  5870       startDraw: function () {
  5871         this._drawsSkipped = 0;
  5872         this._drawStarted = performance.now();
  5873       },
  5874       endDraw: function () {
  5875         var drawTime = performance.now() - this._drawStarted;
  5876         this._drawStats.push(drawTime);
  5877         this._drawStatsSum += drawTime;
  5878         while (this._drawStats.length > STATS_TO_REMEMBER) {
  5879           this._drawStatsSum -= this._drawStats.shift();
  5881       },
  5882       skipDraw: function () {
  5883         this._drawsSkipped++;
  5884       },
  5885       setDelta: function (value) {
  5886         if (!this._trackDelta) {
  5887           return;
  5889         this._delta = value;
  5890       },
  5891       startTrackDelta: function () {
  5892         this._trackDelta = true;
  5893       },
  5894       endTrackDelta: function () {
  5895         if (!this._trackDelta) {
  5896           return;
  5898         this._trackDelta = false;
  5899         this._delta = 0;
  5900         this._onTimeDelta = 0;
  5902     };
  5903     return FrameScheduler;
  5904   }();
  5905 var tagHandler = function (global) {
  5906     function defineShape($bytes, $stream, $, swfVersion, tagCode) {
  5907       $ || ($ = {});
  5908       $.id = readUi16($bytes, $stream);
  5909       var $0 = $.bbox = {};
  5910       bbox($bytes, $stream, $0, swfVersion, tagCode);
  5911       var isMorph = $.isMorph = tagCode === 46 || tagCode === 84;
  5912       if (isMorph) {
  5913         var $1 = $.bboxMorph = {};
  5914         bbox($bytes, $stream, $1, swfVersion, tagCode);
  5916       var hasStrokes = $.hasStrokes = tagCode === 83 || tagCode === 84;
  5917       if (hasStrokes) {
  5918         var $2 = $.strokeBbox = {};
  5919         bbox($bytes, $stream, $2, swfVersion, tagCode);
  5920         if (isMorph) {
  5921           var $3 = $.strokeBboxMorph = {};
  5922           bbox($bytes, $stream, $3, swfVersion, tagCode);
  5924         var reserved = readUb($bytes, $stream, 5);
  5925         $.fillWinding = readUb($bytes, $stream, 1);
  5926         $.nonScalingStrokes = readUb($bytes, $stream, 1);
  5927         $.scalingStrokes = readUb($bytes, $stream, 1);
  5929       if (isMorph) {
  5930         $.offsetMorph = readUi32($bytes, $stream);
  5931         morphShapeWithStyle($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes);
  5932       } else {
  5933         shapeWithStyle($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes);
  5935       return $;
  5937     function placeObject($bytes, $stream, $, swfVersion, tagCode) {
  5938       var flags, hasEvents, clip, hasName, hasRatio, hasCxform, hasMatrix, place;
  5939       var move, hasBackgroundColor, hasVisibility, hasImage, hasClassName, cache;
  5940       var blend, hasFilters, eoe;
  5941       $ || ($ = {});
  5942       if (tagCode > 4) {
  5943         if (tagCode > 26) {
  5944           flags = readUi16($bytes, $stream);
  5945         } else {
  5946           flags = readUi8($bytes, $stream);
  5948         hasEvents = $.hasEvents = flags >> 7 & 1;
  5949         clip = $.clip = flags >> 6 & 1;
  5950         hasName = $.hasName = flags >> 5 & 1;
  5951         hasRatio = $.hasRatio = flags >> 4 & 1;
  5952         hasCxform = $.hasCxform = flags >> 3 & 1;
  5953         hasMatrix = $.hasMatrix = flags >> 2 & 1;
  5954         place = $.place = flags >> 1 & 1;
  5955         move = $.move = flags & 1;
  5956         if (tagCode === 70) {
  5957           hasBackgroundColor = $.hasBackgroundColor = flags >> 15 & 1;
  5958           hasVisibility = $.hasVisibility = flags >> 14 & 1;
  5959           hasImage = $.hasImage = flags >> 12 & 1;
  5960           hasClassName = $.hasClassName = flags >> 11 & 1;
  5961           cache = $.cache = flags >> 10 & 1;
  5962           blend = $.blend = flags >> 9 & 1;
  5963           hasFilters = $.hasFilters = flags >> 8 & 1;
  5964         } else {
  5965           cache = $.cache = 0;
  5966           blend = $.blend = 0;
  5967           hasFilters = $.hasFilters = 0;
  5969         $.depth = readUi16($bytes, $stream);
  5970         if (hasClassName) {
  5971           $.className = readString($bytes, $stream, 0);
  5973         if (place) {
  5974           $.symbolId = readUi16($bytes, $stream);
  5976         if (hasMatrix) {
  5977           var $0 = $.matrix = {};
  5978           matrix($bytes, $stream, $0, swfVersion, tagCode);
  5980         if (hasCxform) {
  5981           var $1 = $.cxform = {};
  5982           cxform($bytes, $stream, $1, swfVersion, tagCode);
  5984         if (hasRatio) {
  5985           $.ratio = readUi16($bytes, $stream);
  5987         if (hasName) {
  5988           $.name = readString($bytes, $stream, 0);
  5990         if (clip) {
  5991           $.clipDepth = readUi16($bytes, $stream);
  5993         if (hasFilters) {
  5994           var count = readUi8($bytes, $stream);
  5995           var $2 = $.filters = [];
  5996           var $3 = count;
  5997           while ($3--) {
  5998             var $4 = {};
  5999             anyFilter($bytes, $stream, $4, swfVersion, tagCode);
  6000             $2.push($4);
  6003         if (blend) {
  6004           $.blendMode = readUi8($bytes, $stream);
  6006         if (cache) {
  6007           $.bmpCache = readUi8($bytes, $stream);
  6009         if (hasEvents) {
  6010           var reserved = readUi16($bytes, $stream);
  6011           if (swfVersion >= 6) {
  6012             var allFlags = readUi32($bytes, $stream);
  6013           } else {
  6014             var allFlags = readUi16($bytes, $stream);
  6016           var $28 = $.events = [];
  6017           do {
  6018             var $29 = {};
  6019             var temp = events($bytes, $stream, $29, swfVersion, tagCode);
  6020             eoe = temp.eoe;
  6021             $28.push($29);
  6022           } while (!eoe);
  6024         if (hasBackgroundColor) {
  6025           var $126 = $.backgroundColor = {};
  6026           argb($bytes, $stream, $126, swfVersion, tagCode);
  6028         if (hasVisibility) {
  6029           $.visibility = readUi8($bytes, $stream);
  6031       } else {
  6032         $.place = 1;
  6033         $.symbolId = readUi16($bytes, $stream);
  6034         $.depth = readUi16($bytes, $stream);
  6035         $.hasMatrix = 1;
  6036         var $30 = $.matrix = {};
  6037         matrix($bytes, $stream, $30, swfVersion, tagCode);
  6038         if ($stream.remaining()) {
  6039           $.hasCxform = 1;
  6040           var $31 = $.cxform = {};
  6041           cxform($bytes, $stream, $31, swfVersion, tagCode);
  6044       return $;
  6046     function removeObject($bytes, $stream, $, swfVersion, tagCode) {
  6047       $ || ($ = {});
  6048       if (tagCode === 5) {
  6049         $.symbolId = readUi16($bytes, $stream);
  6051       $.depth = readUi16($bytes, $stream);
  6052       return $;
  6054     function defineImage($bytes, $stream, $, swfVersion, tagCode) {
  6055       var imgData;
  6056       $ || ($ = {});
  6057       $.id = readUi16($bytes, $stream);
  6058       if (tagCode > 21) {
  6059         var alphaDataOffset = readUi32($bytes, $stream);
  6060         if (tagCode === 90) {
  6061           $.deblock = readFixed8($bytes, $stream);
  6063         imgData = $.imgData = readBinary($bytes, $stream, alphaDataOffset);
  6064         $.alphaData = readBinary($bytes, $stream, 0);
  6065       } else {
  6066         imgData = $.imgData = readBinary($bytes, $stream, 0);
  6068       switch (imgData[0] << 8 | imgData[1]) {
  6069       case 65496:
  6070       case 65497:
  6071         $.mimeType = 'image/jpeg';
  6072         break;
  6073       case 35152:
  6074         $.mimeType = 'image/png';
  6075         break;
  6076       case 18249:
  6077         $.mimeType = 'image/gif';
  6078         break;
  6079       default:
  6080         $.mimeType = 'application/octet-stream';
  6082       if (tagCode === 6) {
  6083         $.incomplete = 1;
  6085       return $;
  6087     function defineButton($bytes, $stream, $, swfVersion, tagCode) {
  6088       var eob, hasFilters, count, blend;
  6089       $ || ($ = {});
  6090       $.id = readUi16($bytes, $stream);
  6091       if (tagCode == 7) {
  6092         var $0 = $.characters = [];
  6093         do {
  6094           var $1 = {};
  6095           var temp = button($bytes, $stream, $1, swfVersion, tagCode);
  6096           eob = temp.eob;
  6097           $0.push($1);
  6098         } while (!eob);
  6099         $.actionsData = readBinary($bytes, $stream, 0);
  6100       } else {
  6101         var trackFlags = readUi8($bytes, $stream);
  6102         $.trackAsMenu = trackFlags >> 7 & 1;
  6103         var actionOffset = readUi16($bytes, $stream);
  6104         var $28 = $.characters = [];
  6105         do {
  6106           var $29 = {};
  6107           var flags = readUi8($bytes, $stream);
  6108           var eob = $29.eob = !flags;
  6109           if (swfVersion >= 8) {
  6110             blend = $29.blend = flags >> 5 & 1;
  6111             hasFilters = $29.hasFilters = flags >> 4 & 1;
  6112           } else {
  6113             blend = $29.blend = 0;
  6114             hasFilters = $29.hasFilters = 0;
  6116           $29.stateHitTest = flags >> 3 & 1;
  6117           $29.stateDown = flags >> 2 & 1;
  6118           $29.stateOver = flags >> 1 & 1;
  6119           $29.stateUp = flags & 1;
  6120           if (!eob) {
  6121             $29.symbolId = readUi16($bytes, $stream);
  6122             $29.depth = readUi16($bytes, $stream);
  6123             var $30 = $29.matrix = {};
  6124             matrix($bytes, $stream, $30, swfVersion, tagCode);
  6125             if (tagCode === 34) {
  6126               var $31 = $29.cxform = {};
  6127               cxform($bytes, $stream, $31, swfVersion, tagCode);
  6129             if (hasFilters) {
  6130               var count = readUi8($bytes, $stream);
  6131               var $2 = $.filters = [];
  6132               var $3 = count;
  6133               while ($3--) {
  6134                 var $4 = {};
  6135                 anyFilter($bytes, $stream, $4, swfVersion, tagCode);
  6136                 $2.push($4);
  6139             if (blend) {
  6140               $29.blendMode = readUi8($bytes, $stream);
  6143           $28.push($29);
  6144         } while (!eob);
  6145         if (!(!actionOffset)) {
  6146           var $56 = $.buttonActions = [];
  6147           do {
  6148             var $57 = {};
  6149             buttonCondAction($bytes, $stream, $57, swfVersion, tagCode);
  6150             $56.push($57);
  6151           } while ($stream.remaining() > 0);
  6154       return $;
  6156     function defineJPEGTables($bytes, $stream, $, swfVersion, tagCode) {
  6157       $ || ($ = {});
  6158       $.id = 0;
  6159       $.imgData = readBinary($bytes, $stream, 0);
  6160       $.mimeType = 'application/octet-stream';
  6161       return $;
  6163     function setBackgroundColor($bytes, $stream, $, swfVersion, tagCode) {
  6164       $ || ($ = {});
  6165       var $0 = $.color = {};
  6166       rgb($bytes, $stream, $0, swfVersion, tagCode);
  6167       return $;
  6169     function defineBinaryData($bytes, $stream, $, swfVersion, tagCode) {
  6170       $ || ($ = {});
  6171       $.id = readUi16($bytes, $stream);
  6172       var reserved = readUi32($bytes, $stream);
  6173       $.data = readBinary($bytes, $stream, 0);
  6174       return $;
  6176     function defineFont($bytes, $stream, $, swfVersion, tagCode) {
  6177       $ || ($ = {});
  6178       $.id = readUi16($bytes, $stream);
  6179       var firstOffset = readUi16($bytes, $stream);
  6180       var glyphCount = $.glyphCount = firstOffset / 2;
  6181       var restOffsets = [];
  6182       var $0 = glyphCount - 1;
  6183       while ($0--) {
  6184         restOffsets.push(readUi16($bytes, $stream));
  6186       $.offsets = [
  6187         firstOffset
  6188       ].concat(restOffsets);
  6189       var $1 = $.glyphs = [];
  6190       var $2 = glyphCount;
  6191       while ($2--) {
  6192         var $3 = {};
  6193         shape($bytes, $stream, $3, swfVersion, tagCode);
  6194         $1.push($3);
  6196       return $;
  6198     function defineLabel($bytes, $stream, $, swfVersion, tagCode) {
  6199       var eot;
  6200       $ || ($ = {});
  6201       $.id = readUi16($bytes, $stream);
  6202       var $0 = $.bbox = {};
  6203       bbox($bytes, $stream, $0, swfVersion, tagCode);
  6204       var $1 = $.matrix = {};
  6205       matrix($bytes, $stream, $1, swfVersion, tagCode);
  6206       var glyphBits = $.glyphBits = readUi8($bytes, $stream);
  6207       var advanceBits = $.advanceBits = readUi8($bytes, $stream);
  6208       var $2 = $.records = [];
  6209       do {
  6210         var $3 = {};
  6211         var temp = textRecord($bytes, $stream, $3, swfVersion, tagCode, glyphBits, advanceBits);
  6212         eot = temp.eot;
  6213         $2.push($3);
  6214       } while (!eot);
  6215       return $;
  6217     function doAction($bytes, $stream, $, swfVersion, tagCode) {
  6218       $ || ($ = {});
  6219       if (tagCode === 59) {
  6220         $.spriteId = readUi16($bytes, $stream);
  6222       $.actionsData = readBinary($bytes, $stream, 0);
  6223       return $;
  6225     function defineSound($bytes, $stream, $, swfVersion, tagCode) {
  6226       $ || ($ = {});
  6227       $.id = readUi16($bytes, $stream);
  6228       var soundFlags = readUi8($bytes, $stream);
  6229       $.soundFormat = soundFlags >> 4 & 15;
  6230       $.soundRate = soundFlags >> 2 & 3;
  6231       $.soundSize = soundFlags >> 1 & 1;
  6232       $.soundType = soundFlags & 1;
  6233       $.samplesCount = readUi32($bytes, $stream);
  6234       $.soundData = readBinary($bytes, $stream, 0);
  6235       return $;
  6237     function startSound($bytes, $stream, $, swfVersion, tagCode) {
  6238       $ || ($ = {});
  6239       if (tagCode == 15) {
  6240         $.soundId = readUi16($bytes, $stream);
  6242       if (tagCode == 89) {
  6243         $.soundClassName = readString($bytes, $stream, 0);
  6245       var $0 = $.soundInfo = {};
  6246       soundInfo($bytes, $stream, $0, swfVersion, tagCode);
  6247       return $;
  6249     function soundStreamHead($bytes, $stream, $, swfVersion, tagCode) {
  6250       $ || ($ = {});
  6251       var playbackFlags = readUi8($bytes, $stream);
  6252       $.playbackRate = playbackFlags >> 2 & 3;
  6253       $.playbackSize = playbackFlags >> 1 & 1;
  6254       $.playbackType = playbackFlags & 1;
  6255       var streamFlags = readUi8($bytes, $stream);
  6256       var streamCompression = $.streamCompression = streamFlags >> 4 & 15;
  6257       $.streamRate = streamFlags >> 2 & 3;
  6258       $.streamSize = streamFlags >> 1 & 1;
  6259       $.streamType = streamFlags & 1;
  6260       $.samplesCount = readUi32($bytes, $stream);
  6261       if (streamCompression == 2) {
  6262         $.latencySeek = readSi16($bytes, $stream);
  6264       return $;
  6266     function soundStreamBlock($bytes, $stream, $, swfVersion, tagCode) {
  6267       $ || ($ = {});
  6268       $.data = readBinary($bytes, $stream, 0);
  6269       return $;
  6271     function defineBitmap($bytes, $stream, $, swfVersion, tagCode) {
  6272       $ || ($ = {});
  6273       $.id = readUi16($bytes, $stream);
  6274       var format = $.format = readUi8($bytes, $stream);
  6275       $.width = readUi16($bytes, $stream);
  6276       $.height = readUi16($bytes, $stream);
  6277       $.hasAlpha = tagCode === 36;
  6278       if (format === 3) {
  6279         $.colorTableSize = readUi8($bytes, $stream);
  6281       $.bmpData = readBinary($bytes, $stream, 0);
  6282       return $;
  6284     function defineText($bytes, $stream, $, swfVersion, tagCode) {
  6285       $ || ($ = {});
  6286       $.id = readUi16($bytes, $stream);
  6287       var $0 = $.bbox = {};
  6288       bbox($bytes, $stream, $0, swfVersion, tagCode);
  6289       var flags = readUi16($bytes, $stream);
  6290       var hasText = $.hasText = flags >> 7 & 1;
  6291       $.wordWrap = flags >> 6 & 1;
  6292       $.multiline = flags >> 5 & 1;
  6293       $.password = flags >> 4 & 1;
  6294       $.readonly = flags >> 3 & 1;
  6295       var hasColor = $.hasColor = flags >> 2 & 1;
  6296       var hasMaxLength = $.hasMaxLength = flags >> 1 & 1;
  6297       var hasFont = $.hasFont = flags & 1;
  6298       var hasFontClass = $.hasFontClass = flags >> 15 & 1;
  6299       $.autoSize = flags >> 14 & 1;
  6300       var hasLayout = $.hasLayout = flags >> 13 & 1;
  6301       $.noSelect = flags >> 12 & 1;
  6302       $.border = flags >> 11 & 1;
  6303       $.wasStatic = flags >> 10 & 1;
  6304       $.html = flags >> 9 & 1;
  6305       $.useOutlines = flags >> 8 & 1;
  6306       if (hasFont) {
  6307         $.fontId = readUi16($bytes, $stream);
  6309       if (hasFontClass) {
  6310         $.fontClass = readString($bytes, $stream, 0);
  6312       if (hasFont) {
  6313         $.fontHeight = readUi16($bytes, $stream);
  6315       if (hasColor) {
  6316         var $1 = $.color = {};
  6317         rgba($bytes, $stream, $1, swfVersion, tagCode);
  6319       if (hasMaxLength) {
  6320         $.maxLength = readUi16($bytes, $stream);
  6322       if (hasLayout) {
  6323         $.align = readUi8($bytes, $stream);
  6324         $.leftMargin = readUi16($bytes, $stream);
  6325         $.rightMargin = readUi16($bytes, $stream);
  6326         $.indent = readSi16($bytes, $stream);
  6327         $.leading = readSi16($bytes, $stream);
  6329       $.variableName = readString($bytes, $stream, 0);
  6330       if (hasText) {
  6331         $.initialText = readString($bytes, $stream, 0);
  6333       return $;
  6335     function frameLabel($bytes, $stream, $, swfVersion, tagCode) {
  6336       $ || ($ = {});
  6337       $.name = readString($bytes, $stream, 0);
  6338       return $;
  6340     function defineFont2($bytes, $stream, $, swfVersion, tagCode) {
  6341       $ || ($ = {});
  6342       $.id = readUi16($bytes, $stream);
  6343       var hasLayout = $.hasLayout = readUb($bytes, $stream, 1);
  6344       if (swfVersion > 5) {
  6345         $.shiftJis = readUb($bytes, $stream, 1);
  6346       } else {
  6347         var reserved = readUb($bytes, $stream, 1);
  6349       $.smallText = readUb($bytes, $stream, 1);
  6350       $.ansi = readUb($bytes, $stream, 1);
  6351       var wideOffset = $.wideOffset = readUb($bytes, $stream, 1);
  6352       var wide = $.wide = readUb($bytes, $stream, 1);
  6353       $.italic = readUb($bytes, $stream, 1);
  6354       $.bold = readUb($bytes, $stream, 1);
  6355       if (swfVersion > 5) {
  6356         $.language = readUi8($bytes, $stream);
  6357       } else {
  6358         var reserved = readUi8($bytes, $stream);
  6359         $.language = 0;
  6361       var nameLength = readUi8($bytes, $stream);
  6362       $.name = readString($bytes, $stream, nameLength);
  6363       if (tagCode === 75) {
  6364         $.resolution = 20;
  6366       var glyphCount = $.glyphCount = readUi16($bytes, $stream);
  6367       if (wideOffset) {
  6368         var $0 = $.offsets = [];
  6369         var $1 = glyphCount;
  6370         while ($1--) {
  6371           $0.push(readUi32($bytes, $stream));
  6373         $.mapOffset = readUi32($bytes, $stream);
  6374       } else {
  6375         var $2 = $.offsets = [];
  6376         var $3 = glyphCount;
  6377         while ($3--) {
  6378           $2.push(readUi16($bytes, $stream));
  6380         $.mapOffset = readUi16($bytes, $stream);
  6382       var $4 = $.glyphs = [];
  6383       var $5 = glyphCount;
  6384       while ($5--) {
  6385         var $6 = {};
  6386         shape($bytes, $stream, $6, swfVersion, tagCode);
  6387         $4.push($6);
  6389       if (wide) {
  6390         var $47 = $.codes = [];
  6391         var $48 = glyphCount;
  6392         while ($48--) {
  6393           $47.push(readUi16($bytes, $stream));
  6395       } else {
  6396         var $49 = $.codes = [];
  6397         var $50 = glyphCount;
  6398         while ($50--) {
  6399           $49.push(readUi8($bytes, $stream));
  6402       if (hasLayout) {
  6403         $.ascent = readUi16($bytes, $stream);
  6404         $.descent = readUi16($bytes, $stream);
  6405         $.leading = readSi16($bytes, $stream);
  6406         var $51 = $.advance = [];
  6407         var $52 = glyphCount;
  6408         while ($52--) {
  6409           $51.push(readSi16($bytes, $stream));
  6411         var $53 = $.bbox = [];
  6412         var $54 = glyphCount;
  6413         while ($54--) {
  6414           var $55 = {};
  6415           bbox($bytes, $stream, $55, swfVersion, tagCode);
  6416           $53.push($55);
  6418         var kerningCount = readUi16($bytes, $stream);
  6419         var $56 = $.kerning = [];
  6420         var $57 = kerningCount;
  6421         while ($57--) {
  6422           var $58 = {};
  6423           kerning($bytes, $stream, $58, swfVersion, tagCode, wide);
  6424           $56.push($58);
  6427       return $;
  6429     function fileAttributes($bytes, $stream, $, swfVersion, tagCode) {
  6430       $ || ($ = {});
  6431       var reserved = readUb($bytes, $stream, 1);
  6432       $.useDirectBlit = readUb($bytes, $stream, 1);
  6433       $.useGpu = readUb($bytes, $stream, 1);
  6434       $.hasMetadata = readUb($bytes, $stream, 1);
  6435       $.doAbc = readUb($bytes, $stream, 1);
  6436       $.noCrossDomainCaching = readUb($bytes, $stream, 1);
  6437       $.relativeUrls = readUb($bytes, $stream, 1);
  6438       $.network = readUb($bytes, $stream, 1);
  6439       var pad = readUb($bytes, $stream, 24);
  6440       return $;
  6442     function doABC($bytes, $stream, $, swfVersion, tagCode) {
  6443       $ || ($ = {});
  6444       if (tagCode === 82) {
  6445         $.flags = readUi32($bytes, $stream);
  6446       } else {
  6447         $.flags = 0;
  6449       if (tagCode === 82) {
  6450         $.name = readString($bytes, $stream, 0);
  6451       } else {
  6452         $.name = '';
  6454       $.data = readBinary($bytes, $stream, 0);
  6455       return $;
  6457     function exportAssets($bytes, $stream, $, swfVersion, tagCode) {
  6458       $ || ($ = {});
  6459       var exportsCount = readUi16($bytes, $stream);
  6460       var $0 = $.exports = [];
  6461       var $1 = exportsCount;
  6462       while ($1--) {
  6463         var $2 = {};
  6464         $2.symbolId = readUi16($bytes, $stream);
  6465         $2.className = readString($bytes, $stream, 0);
  6466         $0.push($2);
  6468       return $;
  6470     function symbolClass($bytes, $stream, $, swfVersion, tagCode) {
  6471       $ || ($ = {});
  6472       var symbolCount = readUi16($bytes, $stream);
  6473       var $0 = $.exports = [];
  6474       var $1 = symbolCount;
  6475       while ($1--) {
  6476         var $2 = {};
  6477         $2.symbolId = readUi16($bytes, $stream);
  6478         $2.className = readString($bytes, $stream, 0);
  6479         $0.push($2);
  6481       return $;
  6483     function defineScalingGrid($bytes, $stream, $, swfVersion, tagCode) {
  6484       $ || ($ = {});
  6485       $.symbolId = readUi16($bytes, $stream);
  6486       var $0 = $.splitter = {};
  6487       bbox($bytes, $stream, $0, swfVersion, tagCode);
  6488       return $;
  6490     function defineScene($bytes, $stream, $, swfVersion, tagCode) {
  6491       $ || ($ = {});
  6492       var sceneCount = readEncodedU32($bytes, $stream);
  6493       var $0 = $.scenes = [];
  6494       var $1 = sceneCount;
  6495       while ($1--) {
  6496         var $2 = {};
  6497         $2.offset = readEncodedU32($bytes, $stream);
  6498         $2.name = readString($bytes, $stream, 0);
  6499         $0.push($2);
  6501       var labelCount = readEncodedU32($bytes, $stream);
  6502       var $3 = $.labels = [];
  6503       var $4 = labelCount;
  6504       while ($4--) {
  6505         var $5 = {};
  6506         $5.frame = readEncodedU32($bytes, $stream);
  6507         $5.name = readString($bytes, $stream, 0);
  6508         $3.push($5);
  6510       return $;
  6512     function bbox($bytes, $stream, $, swfVersion, tagCode) {
  6513       align($bytes, $stream);
  6514       var bits = readUb($bytes, $stream, 5);
  6515       var xMin = readSb($bytes, $stream, bits);
  6516       var xMax = readSb($bytes, $stream, bits);
  6517       var yMin = readSb($bytes, $stream, bits);
  6518       var yMax = readSb($bytes, $stream, bits);
  6519       $.xMin = xMin;
  6520       $.xMax = xMax;
  6521       $.yMin = yMin;
  6522       $.yMax = yMax;
  6523       align($bytes, $stream);
  6525     function rgb($bytes, $stream, $, swfVersion, tagCode) {
  6526       $.red = readUi8($bytes, $stream);
  6527       $.green = readUi8($bytes, $stream);
  6528       $.blue = readUi8($bytes, $stream);
  6529       $.alpha = 255;
  6530       return;
  6532     function rgba($bytes, $stream, $, swfVersion, tagCode) {
  6533       $.red = readUi8($bytes, $stream);
  6534       $.green = readUi8($bytes, $stream);
  6535       $.blue = readUi8($bytes, $stream);
  6536       $.alpha = readUi8($bytes, $stream);
  6537       return;
  6539     function argb($bytes, $stream, $, swfVersion, tagCode) {
  6540       $.alpha = readUi8($bytes, $stream);
  6541       $.red = readUi8($bytes, $stream);
  6542       $.green = readUi8($bytes, $stream);
  6543       $.blue = readUi8($bytes, $stream);
  6545     function fillSolid($bytes, $stream, $, swfVersion, tagCode, isMorph) {
  6546       if (tagCode > 22 || isMorph) {
  6547         var $125 = $.color = {};
  6548         rgba($bytes, $stream, $125, swfVersion, tagCode);
  6549       } else {
  6550         var $126 = $.color = {};
  6551         rgb($bytes, $stream, $126, swfVersion, tagCode);
  6553       if (isMorph) {
  6554         var $127 = $.colorMorph = {};
  6555         rgba($bytes, $stream, $127, swfVersion, tagCode);
  6557       return;
  6559     function matrix($bytes, $stream, $, swfVersion, tagCode) {
  6560       align($bytes, $stream);
  6561       var hasScale = readUb($bytes, $stream, 1);
  6562       if (hasScale) {
  6563         var bits = readUb($bytes, $stream, 5);
  6564         $.a = readFb($bytes, $stream, bits);
  6565         $.d = readFb($bytes, $stream, bits);
  6566       } else {
  6567         $.a = 1;
  6568         $.d = 1;
  6570       var hasRotate = readUb($bytes, $stream, 1);
  6571       if (hasRotate) {
  6572         var bits = readUb($bytes, $stream, 5);
  6573         $.b = readFb($bytes, $stream, bits);
  6574         $.c = readFb($bytes, $stream, bits);
  6575       } else {
  6576         $.b = 0;
  6577         $.c = 0;
  6579       var bits = readUb($bytes, $stream, 5);
  6580       var e = readSb($bytes, $stream, bits);
  6581       var f = readSb($bytes, $stream, bits);
  6582       $.tx = e;
  6583       $.ty = f;
  6584       align($bytes, $stream);
  6586     function cxform($bytes, $stream, $, swfVersion, tagCode) {
  6587       align($bytes, $stream);
  6588       var hasOffsets = readUb($bytes, $stream, 1);
  6589       var hasMultipliers = readUb($bytes, $stream, 1);
  6590       var bits = readUb($bytes, $stream, 4);
  6591       if (hasMultipliers) {
  6592         $.redMultiplier = readSb($bytes, $stream, bits);
  6593         $.greenMultiplier = readSb($bytes, $stream, bits);
  6594         $.blueMultiplier = readSb($bytes, $stream, bits);
  6595         if (tagCode > 4) {
  6596           $.alphaMultiplier = readSb($bytes, $stream, bits);
  6597         } else {
  6598           $.alphaMultiplier = 256;
  6600       } else {
  6601         $.redMultiplier = 256;
  6602         $.greenMultiplier = 256;
  6603         $.blueMultiplier = 256;
  6604         $.alphaMultiplier = 256;
  6606       if (hasOffsets) {
  6607         $.redOffset = readSb($bytes, $stream, bits);
  6608         $.greenOffset = readSb($bytes, $stream, bits);
  6609         $.blueOffset = readSb($bytes, $stream, bits);
  6610         if (tagCode > 4) {
  6611           $.alphaOffset = readSb($bytes, $stream, bits);
  6612         } else {
  6613           $.alphaOffset = 0;
  6615       } else {
  6616         $.redOffset = 0;
  6617         $.greenOffset = 0;
  6618         $.blueOffset = 0;
  6619         $.alphaOffset = 0;
  6621       align($bytes, $stream);
  6623     function fillGradient($bytes, $stream, $, swfVersion, tagCode, isMorph, type) {
  6624       var $128 = $.matrix = {};
  6625       matrix($bytes, $stream, $128, swfVersion, tagCode);
  6626       if (isMorph) {
  6627         var $129 = $.matrixMorph = {};
  6628         matrix($bytes, $stream, $129, swfVersion, tagCode);
  6630       gradient($bytes, $stream, $, swfVersion, tagCode, isMorph, type);
  6632     function gradient($bytes, $stream, $, swfVersion, tagCode, isMorph, type) {
  6633       if (tagCode === 83) {
  6634         $.spreadMode = readUb($bytes, $stream, 2);
  6635         $.interpolationMode = readUb($bytes, $stream, 2);
  6636       } else {
  6637         var pad = readUb($bytes, $stream, 4);
  6639       var count = $.count = readUb($bytes, $stream, 4);
  6640       var $130 = $.records = [];
  6641       var $131 = count;
  6642       while ($131--) {
  6643         var $132 = {};
  6644         gradientRecord($bytes, $stream, $132, swfVersion, tagCode, isMorph);
  6645         $130.push($132);
  6647       if (type === 19) {
  6648         $.focalPoint = readFixed8($bytes, $stream);
  6649         if (isMorph) {
  6650           $.focalPointMorph = readFixed8($bytes, $stream);
  6654     function gradientRecord($bytes, $stream, $, swfVersion, tagCode, isMorph) {
  6655       $.ratio = readUi8($bytes, $stream);
  6656       if (tagCode > 22) {
  6657         var $133 = $.color = {};
  6658         rgba($bytes, $stream, $133, swfVersion, tagCode);
  6659       } else {
  6660         var $134 = $.color = {};
  6661         rgb($bytes, $stream, $134, swfVersion, tagCode);
  6663       if (isMorph) {
  6664         $.ratioMorph = readUi8($bytes, $stream);
  6665         var $135 = $.colorMorph = {};
  6666         rgba($bytes, $stream, $135, swfVersion, tagCode);
  6669     function morphShapeWithStyle($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes) {
  6670       var eos, bits;
  6671       var temp = styles($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes);
  6672       var lineBits = temp.lineBits;
  6673       var fillBits = temp.fillBits;
  6674       var $160 = $.records = [];
  6675       do {
  6676         var $161 = {};
  6677         var temp = shapeRecord($bytes, $stream, $161, swfVersion, tagCode, isMorph, fillBits, lineBits, hasStrokes, bits);
  6678         var eos = temp.eos;
  6679         var flags = temp.flags;
  6680         var type = temp.type;
  6681         var fillBits = temp.fillBits;
  6682         var lineBits = temp.lineBits;
  6683         var bits = temp.bits;
  6684         $160.push($161);
  6685       } while (!eos);
  6686       var temp = styleBits($bytes, $stream, $, swfVersion, tagCode);
  6687       var fillBits = temp.fillBits;
  6688       var lineBits = temp.lineBits;
  6689       var $162 = $.recordsMorph = [];
  6690       do {
  6691         var $163 = {};
  6692         var temp = shapeRecord($bytes, $stream, $163, swfVersion, tagCode, isMorph, fillBits, lineBits, hasStrokes, bits);
  6693         eos = temp.eos;
  6694         var flags = temp.flags;
  6695         var type = temp.type;
  6696         var fillBits = temp.fillBits;
  6697         var lineBits = temp.lineBits;
  6698         bits = temp.bits;
  6699         $162.push($163);
  6700       } while (!eos);
  6702     function shapeWithStyle($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes) {
  6703       var eos;
  6704       var temp = styles($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes);
  6705       var fillBits = temp.fillBits;
  6706       var lineBits = temp.lineBits;
  6707       var $160 = $.records = [];
  6708       do {
  6709         var $161 = {};
  6710         var temp = shapeRecord($bytes, $stream, $161, swfVersion, tagCode, isMorph, fillBits, lineBits, hasStrokes, bits);
  6711         eos = temp.eos;
  6712         var flags = temp.flags;
  6713         var type = temp.type;
  6714         var fillBits = temp.fillBits;
  6715         var lineBits = temp.lineBits;
  6716         var bits = temp.bits;
  6717         $160.push($161);
  6718       } while (!eos);
  6720     function shapeRecord($bytes, $stream, $, swfVersion, tagCode, isMorph, fillBits, lineBits, hasStrokes, bits) {
  6721       var type = $.type = readUb($bytes, $stream, 1);
  6722       var flags = readUb($bytes, $stream, 5);
  6723       var eos = $.eos = !(type || flags);
  6724       if (type) {
  6725         var temp = shapeRecordEdge($bytes, $stream, $, swfVersion, tagCode, flags, bits);
  6726         var bits = temp.bits;
  6727       } else {
  6728         var temp = shapeRecordSetup($bytes, $stream, $, swfVersion, tagCode, flags, isMorph, fillBits, lineBits, hasStrokes, bits);
  6729         var fillBits = temp.fillBits;
  6730         var lineBits = temp.lineBits;
  6731         var bits = temp.bits;
  6733       return {
  6734         type: type,
  6735         flags: flags,
  6736         eos: eos,
  6737         fillBits: fillBits,
  6738         lineBits: lineBits,
  6739         bits: bits
  6740       };
  6742     function shapeRecordEdge($bytes, $stream, $, swfVersion, tagCode, flags, bits) {
  6743       var isStraight = 0, tmp = 0, bits = 0, isGeneral = 0, isVertical = 0;
  6744       isStraight = $.isStraight = flags >> 4;
  6745       tmp = flags & 15;
  6746       bits = tmp + 2;
  6747       if (isStraight) {
  6748         isGeneral = $.isGeneral = readUb($bytes, $stream, 1);
  6749         if (isGeneral) {
  6750           $.deltaX = readSb($bytes, $stream, bits);
  6751           $.deltaY = readSb($bytes, $stream, bits);
  6752         } else {
  6753           isVertical = $.isVertical = readUb($bytes, $stream, 1);
  6754           if (isVertical) {
  6755             $.deltaY = readSb($bytes, $stream, bits);
  6756           } else {
  6757             $.deltaX = readSb($bytes, $stream, bits);
  6760       } else {
  6761         $.controlDeltaX = readSb($bytes, $stream, bits);
  6762         $.controlDeltaY = readSb($bytes, $stream, bits);
  6763         $.anchorDeltaX = readSb($bytes, $stream, bits);
  6764         $.anchorDeltaY = readSb($bytes, $stream, bits);
  6766       return {
  6767         bits: bits
  6768       };
  6770     function shapeRecordSetup($bytes, $stream, $, swfVersion, tagCode, flags, isMorph, fillBits, lineBits, hasStrokes, bits) {
  6771       var hasNewStyles = 0, hasLineStyle = 0, hasFillStyle1 = 0;
  6772       var hasFillStyle0 = 0, move = 0;
  6773       if (tagCode > 2) {
  6774         hasNewStyles = $.hasNewStyles = flags >> 4;
  6775       } else {
  6776         hasNewStyles = $.hasNewStyles = 0;
  6778       hasLineStyle = $.hasLineStyle = flags >> 3 & 1;
  6779       hasFillStyle1 = $.hasFillStyle1 = flags >> 2 & 1;
  6780       hasFillStyle0 = $.hasFillStyle0 = flags >> 1 & 1;
  6781       move = $.move = flags & 1;
  6782       if (move) {
  6783         bits = readUb($bytes, $stream, 5);
  6784         $.moveX = readSb($bytes, $stream, bits);
  6785         $.moveY = readSb($bytes, $stream, bits);
  6787       if (hasFillStyle0) {
  6788         $.fillStyle0 = readUb($bytes, $stream, fillBits);
  6790       if (hasFillStyle1) {
  6791         $.fillStyle1 = readUb($bytes, $stream, fillBits);
  6793       if (hasLineStyle) {
  6794         $.lineStyle = readUb($bytes, $stream, lineBits);
  6796       if (hasNewStyles) {
  6797         var temp = styles($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes);
  6798         var lineBits = temp.lineBits;
  6799         var fillBits = temp.fillBits;
  6801       return {
  6802         lineBits: lineBits,
  6803         fillBits: fillBits,
  6804         bits: bits
  6805       };
  6807     function styles($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes) {
  6808       fillStyleArray($bytes, $stream, $, swfVersion, tagCode, isMorph);
  6809       lineStyleArray($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes);
  6810       var temp = styleBits($bytes, $stream, $, swfVersion, tagCode);
  6811       var fillBits = temp.fillBits;
  6812       var lineBits = temp.lineBits;
  6813       return {
  6814         fillBits: fillBits,
  6815         lineBits: lineBits
  6816       };
  6818     function fillStyleArray($bytes, $stream, $, swfVersion, tagCode, isMorph) {
  6819       var count;
  6820       var tmp = readUi8($bytes, $stream);
  6821       if (tagCode > 2 && tmp === 255) {
  6822         count = readUi16($bytes, $stream);
  6823       } else {
  6824         count = tmp;
  6826       var $4 = $.fillStyles = [];
  6827       var $5 = count;
  6828       while ($5--) {
  6829         var $6 = {};
  6830         fillStyle($bytes, $stream, $6, swfVersion, tagCode, isMorph);
  6831         $4.push($6);
  6834     function lineStyleArray($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes) {
  6835       var count;
  6836       var tmp = readUi8($bytes, $stream);
  6837       if (tagCode > 2 && tmp === 255) {
  6838         count = readUi16($bytes, $stream);
  6839       } else {
  6840         count = tmp;
  6842       var $138 = $.lineStyles = [];
  6843       var $139 = count;
  6844       while ($139--) {
  6845         var $140 = {};
  6846         lineStyle($bytes, $stream, $140, swfVersion, tagCode, isMorph, hasStrokes);
  6847         $138.push($140);
  6850     function styleBits($bytes, $stream, $, swfVersion, tagCode) {
  6851       align($bytes, $stream);
  6852       var fillBits = readUb($bytes, $stream, 4);
  6853       var lineBits = readUb($bytes, $stream, 4);
  6854       return {
  6855         fillBits: fillBits,
  6856         lineBits: lineBits
  6857       };
  6859     function fillStyle($bytes, $stream, $, swfVersion, tagCode, isMorph) {
  6860       var type = $.type = readUi8($bytes, $stream);
  6861       switch (type) {
  6862       case 0:
  6863         fillSolid($bytes, $stream, $, swfVersion, tagCode, isMorph);
  6864         break;
  6865       case 16:
  6866       case 18:
  6867       case 19:
  6868         fillGradient($bytes, $stream, $, swfVersion, tagCode, isMorph, type);
  6869         break;
  6870       case 64:
  6871       case 65:
  6872       case 66:
  6873       case 67:
  6874         fillBitmap($bytes, $stream, $, swfVersion, tagCode, isMorph, type);
  6875         break;
  6876       default:
  6879     function lineStyle($bytes, $stream, $, swfVersion, tagCode, isMorph, hasStrokes) {
  6880       $.width = readUi16($bytes, $stream);
  6881       if (isMorph) {
  6882         $.widthMorph = readUi16($bytes, $stream);
  6884       if (hasStrokes) {
  6885         align($bytes, $stream);
  6886         $.startCapStyle = readUb($bytes, $stream, 2);
  6887         var joinStyle = $.joinStyle = readUb($bytes, $stream, 2);
  6888         var hasFill = $.hasFill = readUb($bytes, $stream, 1);
  6889         $.noHscale = readUb($bytes, $stream, 1);
  6890         $.noVscale = readUb($bytes, $stream, 1);
  6891         $.pixelHinting = readUb($bytes, $stream, 1);
  6892         var reserved = readUb($bytes, $stream, 5);
  6893         $.noClose = readUb($bytes, $stream, 1);
  6894         $.endCapStyle = readUb($bytes, $stream, 2);
  6895         if (joinStyle === 2) {
  6896           $.miterLimitFactor = readFixed8($bytes, $stream);
  6898         if (hasFill) {
  6899           var $141 = $.fillStyle = {};
  6900           fillStyle($bytes, $stream, $141, swfVersion, tagCode, isMorph);
  6901         } else {
  6902           var $155 = $.color = {};
  6903           rgba($bytes, $stream, $155, swfVersion, tagCode);
  6904           if (isMorph) {
  6905             var $156 = $.colorMorph = {};
  6906             rgba($bytes, $stream, $156, swfVersion, tagCode);
  6909       } else {
  6910         if (tagCode > 22) {
  6911           var $157 = $.color = {};
  6912           rgba($bytes, $stream, $157, swfVersion, tagCode);
  6913         } else {
  6914           var $158 = $.color = {};
  6915           rgb($bytes, $stream, $158, swfVersion, tagCode);
  6917         if (isMorph) {
  6918           var $159 = $.colorMorph = {};
  6919           rgba($bytes, $stream, $159, swfVersion, tagCode);
  6923     function fillBitmap($bytes, $stream, $, swfVersion, tagCode, isMorph, type) {
  6924       $.bitmapId = readUi16($bytes, $stream);
  6925       var $18 = $.matrix = {};
  6926       matrix($bytes, $stream, $18, swfVersion, tagCode);
  6927       if (isMorph) {
  6928         var $19 = $.matrixMorph = {};
  6929         matrix($bytes, $stream, $19, swfVersion, tagCode);
  6931       $.condition = type === 64 || type === 67;
  6933     function filterGlow($bytes, $stream, $, swfVersion, tagCode, type) {
  6934       var count;
  6935       if (type === 4 || type === 7) {
  6936         count = readUi8($bytes, $stream);
  6937       } else {
  6938         count = 1;
  6940       var $5 = $.colors = [];
  6941       var $6 = count;
  6942       while ($6--) {
  6943         var $7 = {};
  6944         rgba($bytes, $stream, $7, swfVersion, tagCode);
  6945         $5.push($7);
  6947       if (type === 3) {
  6948         var $8 = $.higlightColor = {};
  6949         rgba($bytes, $stream, $8, swfVersion, tagCode);
  6951       if (type === 4 || type === 7) {
  6952         var $9 = $.ratios = [];
  6953         var $10 = count;
  6954         while ($10--) {
  6955           $9.push(readUi8($bytes, $stream));
  6958       $.blurX = readFixed($bytes, $stream);
  6959       $.blurY = readFixed($bytes, $stream);
  6960       if (type !== 2) {
  6961         $.angle = readFixed($bytes, $stream);
  6962         $.distance = readFixed($bytes, $stream);
  6964       $.strength = readFixed8($bytes, $stream);
  6965       $.innerShadow = readUb($bytes, $stream, 1);
  6966       $.knockout = readUb($bytes, $stream, 1);
  6967       $.compositeSource = readUb($bytes, $stream, 1);
  6968       if (type === 3) {
  6969         $.onTop = readUb($bytes, $stream, 1);
  6970       } else {
  6971         var reserved = readUb($bytes, $stream, 1);
  6973       if (type === 4 || type === 7) {
  6974         $.passes = readUb($bytes, $stream, 4);
  6975       } else {
  6976         var reserved = readUb($bytes, $stream, 4);
  6979     function filterBlur($bytes, $stream, $, swfVersion, tagCode) {
  6980       $.blurX = readFixed($bytes, $stream);
  6981       $.blurY = readFixed($bytes, $stream);
  6982       $.passes = readUb($bytes, $stream, 5);
  6983       var reserved = readUb($bytes, $stream, 3);
  6985     function filterConvolution($bytes, $stream, $, swfVersion, tagCode) {
  6986       var columns = $.columns = readUi8($bytes, $stream);
  6987       var rows = $.rows = readUi8($bytes, $stream);
  6988       $.divisor = readFloat($bytes, $stream);
  6989       $.bias = readFloat($bytes, $stream);
  6990       var $17 = $.weights = [];
  6991       var $18 = columns * rows;
  6992       while ($18--) {
  6993         $17.push(readFloat($bytes, $stream));
  6995       var $19 = $.defaultColor = {};
  6996       rgba($bytes, $stream, $19, swfVersion, tagCode);
  6997       var reserved = readUb($bytes, $stream, 6);
  6998       $.clamp = readUb($bytes, $stream, 1);
  6999       $.preserveAlpha = readUb($bytes, $stream, 1);
  7001     function filterColorMatrix($bytes, $stream, $, swfVersion, tagCode) {
  7002       var $20 = $.matrix = [];
  7003       var $21 = 20;
  7004       while ($21--) {
  7005         $20.push(readFloat($bytes, $stream));
  7008     function anyFilter($bytes, $stream, $, swfVersion, tagCode) {
  7009       var type = $.type = readUi8($bytes, $stream);
  7010       switch (type) {
  7011       case 0:
  7012       case 2:
  7013       case 3:
  7014       case 4:
  7015       case 7:
  7016         filterGlow($bytes, $stream, $, swfVersion, tagCode, type);
  7017         break;
  7018       case 1:
  7019         filterBlur($bytes, $stream, $, swfVersion, tagCode);
  7020         break;
  7021       case 5:
  7022         filterConvolution($bytes, $stream, $, swfVersion, tagCode);
  7023         break;
  7024       case 6:
  7025         filterColorMatrix($bytes, $stream, $, swfVersion, tagCode);
  7026         break;
  7027       default:
  7030     function events($bytes, $stream, $, swfVersion, tagCode) {
  7031       var flags, keyPress;
  7032       if (swfVersion >= 6) {
  7033         flags = readUi32($bytes, $stream);
  7034       } else {
  7035         flags = readUi16($bytes, $stream);
  7037       var eoe = $.eoe = !flags;
  7038       $.onKeyUp = flags >> 7 & 1;
  7039       $.onKeyDown = flags >> 6 & 1;
  7040       $.onMouseUp = flags >> 5 & 1;
  7041       $.onMouseDown = flags >> 4 & 1;
  7042       $.onMouseMove = flags >> 3 & 1;
  7043       $.onUnload = flags >> 2 & 1;
  7044       $.onEnterFrame = flags >> 1 & 1;
  7045       $.onLoad = flags & 1;
  7046       if (swfVersion >= 6) {
  7047         $.onDragOver = flags >> 15 & 1;
  7048         $.onRollOut = flags >> 14 & 1;
  7049         $.onRollOver = flags >> 13 & 1;
  7050         $.onReleaseOutside = flags >> 12 & 1;
  7051         $.onRelease = flags >> 11 & 1;
  7052         $.onPress = flags >> 10 & 1;
  7053         $.onInitialize = flags >> 9 & 1;
  7054         $.onData = flags >> 8 & 1;
  7055         if (swfVersion >= 7) {
  7056           $.onConstruct = flags >> 18 & 1;
  7057         } else {
  7058           $.onConstruct = 0;
  7060         keyPress = $.keyPress = flags >> 17 & 1;
  7061         $.onDragOut = flags >> 16 & 1;
  7063       if (!eoe) {
  7064         var length = $.length = readUi32($bytes, $stream);
  7065         if (keyPress) {
  7066           $.keyCode = readUi8($bytes, $stream);
  7068         $.actionsData = readBinary($bytes, $stream, length - (keyPress ? 1 : 0));
  7070       return {
  7071         eoe: eoe
  7072       };
  7074     function kerning($bytes, $stream, $, swfVersion, tagCode, wide) {
  7075       if (wide) {
  7076         $.code1 = readUi16($bytes, $stream);
  7077         $.code2 = readUi16($bytes, $stream);
  7078       } else {
  7079         $.code1 = readUi8($bytes, $stream);
  7080         $.code2 = readUi8($bytes, $stream);
  7082       $.adjustment = readUi16($bytes, $stream);
  7084     function textEntry($bytes, $stream, $, swfVersion, tagCode, glyphBits, advanceBits) {
  7085       $.glyphIndex = readUb($bytes, $stream, glyphBits);
  7086       $.advance = readSb($bytes, $stream, advanceBits);
  7088     function textRecordSetup($bytes, $stream, $, swfVersion, tagCode, flags) {
  7089       var hasFont = $.hasFont = flags >> 3 & 1;
  7090       var hasColor = $.hasColor = flags >> 2 & 1;
  7091       var hasMoveY = $.hasMoveY = flags >> 1 & 1;
  7092       var hasMoveX = $.hasMoveX = flags & 1;
  7093       if (hasFont) {
  7094         $.fontId = readUi16($bytes, $stream);
  7096       if (hasColor) {
  7097         if (tagCode === 33) {
  7098           var $4 = $.color = {};
  7099           rgba($bytes, $stream, $4, swfVersion, tagCode);
  7100         } else {
  7101           var $5 = $.color = {};
  7102           rgb($bytes, $stream, $5, swfVersion, tagCode);
  7105       if (hasMoveX) {
  7106         $.moveX = readSi16($bytes, $stream);
  7108       if (hasMoveY) {
  7109         $.moveY = readSi16($bytes, $stream);
  7111       if (hasFont) {
  7112         $.fontHeight = readUi16($bytes, $stream);
  7115     function textRecord($bytes, $stream, $, swfVersion, tagCode, glyphBits, advanceBits) {
  7116       var glyphCount;
  7117       align($bytes, $stream);
  7118       var flags = readUb($bytes, $stream, 8);
  7119       var eot = $.eot = !flags;
  7120       textRecordSetup($bytes, $stream, $, swfVersion, tagCode, flags);
  7121       if (!eot) {
  7122         var tmp = readUi8($bytes, $stream);
  7123         if (swfVersion > 6) {
  7124           glyphCount = $.glyphCount = tmp;
  7125         } else {
  7126           glyphCount = $.glyphCount = tmp & 127;
  7128         var $6 = $.entries = [];
  7129         var $7 = glyphCount;
  7130         while ($7--) {
  7131           var $8 = {};
  7132           textEntry($bytes, $stream, $8, swfVersion, tagCode, glyphBits, advanceBits);
  7133           $6.push($8);
  7136       return {
  7137         eot: eot
  7138       };
  7140     function soundEnvelope($bytes, $stream, $, swfVersion, tagCode) {
  7141       $.pos44 = readUi32($bytes, $stream);
  7142       $.volumeLeft = readUi16($bytes, $stream);
  7143       $.volumeRight = readUi16($bytes, $stream);
  7145     function soundInfo($bytes, $stream, $, swfVersion, tagCode) {
  7146       var reserved = readUb($bytes, $stream, 2);
  7147       $.stop = readUb($bytes, $stream, 1);
  7148       $.noMultiple = readUb($bytes, $stream, 1);
  7149       var hasEnvelope = $.hasEnvelope = readUb($bytes, $stream, 1);
  7150       var hasLoops = $.hasLoops = readUb($bytes, $stream, 1);
  7151       var hasOutPoint = $.hasOutPoint = readUb($bytes, $stream, 1);
  7152       var hasInPoint = $.hasInPoint = readUb($bytes, $stream, 1);
  7153       if (hasInPoint) {
  7154         $.inPoint = readUi32($bytes, $stream);
  7156       if (hasOutPoint) {
  7157         $.outPoint = readUi32($bytes, $stream);
  7159       if (hasLoops) {
  7160         $.loopCount = readUi16($bytes, $stream);
  7162       if (hasEnvelope) {
  7163         var envelopeCount = $.envelopeCount = readUi8($bytes, $stream);
  7164         var $1 = $.envelopes = [];
  7165         var $2 = envelopeCount;
  7166         while ($2--) {
  7167           var $3 = {};
  7168           soundEnvelope($bytes, $stream, $3, swfVersion, tagCode);
  7169           $1.push($3);
  7173     function button($bytes, $stream, $, swfVersion, tagCode) {
  7174       var hasFilters, blend;
  7175       var flags = readUi8($bytes, $stream);
  7176       var eob = $.eob = !flags;
  7177       if (swfVersion >= 8) {
  7178         blend = $.blend = flags >> 5 & 1;
  7179         hasFilters = $.hasFilters = flags >> 4 & 1;
  7180       } else {
  7181         blend = $.blend = 0;
  7182         hasFilters = $.hasFilters = 0;
  7184       $.stateHitTest = flags >> 3 & 1;
  7185       $.stateDown = flags >> 2 & 1;
  7186       $.stateOver = flags >> 1 & 1;
  7187       $.stateUp = flags & 1;
  7188       if (!eob) {
  7189         $.symbolId = readUi16($bytes, $stream);
  7190         $.depth = readUi16($bytes, $stream);
  7191         var $2 = $.matrix = {};
  7192         matrix($bytes, $stream, $2, swfVersion, tagCode);
  7193         if (tagCode === 34) {
  7194           var $3 = $.cxform = {};
  7195           cxform($bytes, $stream, $3, swfVersion, tagCode);
  7197         if (hasFilters) {
  7198           $.filterCount = readUi8($bytes, $stream);
  7199           var $4 = $.filters = {};
  7200           anyFilter($bytes, $stream, $4, swfVersion, tagCode);
  7202         if (blend) {
  7203           $.blendMode = readUi8($bytes, $stream);
  7206       return {
  7207         eob: eob
  7208       };
  7210     function buttonCondAction($bytes, $stream, $, swfVersion, tagCode) {
  7211       var buttonCondSize = readUi16($bytes, $stream);
  7212       var buttonConditions = readUi16($bytes, $stream);
  7213       $.idleToOverDown = buttonConditions >> 7 & 1;
  7214       $.outDownToIdle = buttonConditions >> 6 & 1;
  7215       $.outDownToOverDown = buttonConditions >> 5 & 1;
  7216       $.overDownToOutDown = buttonConditions >> 4 & 1;
  7217       $.overDownToOverUp = buttonConditions >> 3 & 1;
  7218       $.overUpToOverDown = buttonConditions >> 2 & 1;
  7219       $.overUpToIdle = buttonConditions >> 1 & 1;
  7220       $.idleToOverUp = buttonConditions & 1;
  7221       $.mouseEventFlags = buttonConditions & 511;
  7222       $.keyPress = buttonConditions >> 9 & 127;
  7223       $.overDownToIdle = buttonConditions >> 8 & 1;
  7224       if (!buttonCondSize) {
  7225         $.actionsData = readBinary($bytes, $stream, 0);
  7226       } else {
  7227         $.actionsData = readBinary($bytes, $stream, buttonCondSize - 4);
  7230     function shape($bytes, $stream, $, swfVersion, tagCode) {
  7231       var eos;
  7232       var temp = styleBits($bytes, $stream, $, swfVersion, tagCode);
  7233       var fillBits = temp.fillBits;
  7234       var lineBits = temp.lineBits;
  7235       var $4 = $.records = [];
  7236       do {
  7237         var $5 = {};
  7238         var isMorph = false;
  7239         var hasStrokes = false;
  7240         var temp = shapeRecord($bytes, $stream, $5, swfVersion, tagCode, isMorph, fillBits, lineBits, hasStrokes, bits);
  7241         eos = temp.eos;
  7242         var fillBits = temp.fillBits;
  7243         var lineBits = temp.lineBits;
  7244         var bits = bits;
  7245         $4.push($5);
  7246       } while (!eos);
  7248     return {
  7249       0: undefined,
  7250       1: undefined,
  7251       2: defineShape,
  7252       4: placeObject,
  7253       5: removeObject,
  7254       6: defineImage,
  7255       7: defineButton,
  7256       8: defineJPEGTables,
  7257       9: setBackgroundColor,
  7258       10: defineFont,
  7259       11: defineLabel,
  7260       12: doAction,
  7261       13: undefined,
  7262       14: defineSound,
  7263       15: startSound,
  7264       17: undefined,
  7265       18: soundStreamHead,
  7266       19: soundStreamBlock,
  7267       20: defineBitmap,
  7268       21: defineImage,
  7269       22: defineShape,
  7270       23: undefined,
  7271       24: undefined,
  7272       26: placeObject,
  7273       28: removeObject,
  7274       32: defineShape,
  7275       33: defineLabel,
  7276       34: defineButton,
  7277       35: defineImage,
  7278       36: defineBitmap,
  7279       37: defineText,
  7280       39: undefined,
  7281       43: frameLabel,
  7282       45: soundStreamHead,
  7283       46: defineShape,
  7284       48: defineFont2,
  7285       56: exportAssets,
  7286       57: undefined,
  7287       58: undefined,
  7288       59: doAction,
  7289       60: undefined,
  7290       61: undefined,
  7291       62: undefined,
  7292       64: undefined,
  7293       65: undefined,
  7294       66: undefined,
  7295       69: fileAttributes,
  7296       70: placeObject,
  7297       71: undefined,
  7298       72: doABC,
  7299       73: undefined,
  7300       74: undefined,
  7301       75: defineFont2,
  7302       76: symbolClass,
  7303       77: undefined,
  7304       78: defineScalingGrid,
  7305       82: doABC,
  7306       83: defineShape,
  7307       84: defineShape,
  7308       86: defineScene,
  7309       87: defineBinaryData,
  7310       88: undefined,
  7311       89: startSound,
  7312       90: defineImage,
  7313       91: undefined
  7314     };
  7315   }(this);
  7316 var readHeader = function readHeader($bytes, $stream, $, swfVersion, tagCode) {
  7317   $ || ($ = {});
  7318   var $0 = $.bbox = {};
  7319   align($bytes, $stream);
  7320   var bits = readUb($bytes, $stream, 5);
  7321   var xMin = readSb($bytes, $stream, bits);
  7322   var xMax = readSb($bytes, $stream, bits);
  7323   var yMin = readSb($bytes, $stream, bits);
  7324   var yMax = readSb($bytes, $stream, bits);
  7325   $0.xMin = xMin;
  7326   $0.xMax = xMax;
  7327   $0.yMin = yMin;
  7328   $0.yMax = yMax;
  7329   align($bytes, $stream);
  7330   var frameRateFraction = readUi8($bytes, $stream);
  7331   $.frameRate = readUi8($bytes, $stream) + frameRateFraction / 256;
  7332   $.frameCount = readUi16($bytes, $stream);
  7333   return $;
  7334 };
  7335 function readTags(context, stream, swfVersion, final, onprogress, onexception) {
  7336   var tags = context.tags;
  7337   var bytes = stream.bytes;
  7338   var lastSuccessfulPosition;
  7339   var tag = null;
  7340   if (context._readTag) {
  7341     tag = context._readTag;
  7342     context._readTag = null;
  7344   try {
  7345     while (stream.pos < stream.end) {
  7346       lastSuccessfulPosition = stream.pos;
  7347       stream.ensure(2);
  7348       var tagCodeAndLength = readUi16(bytes, stream);
  7349       if (!tagCodeAndLength) {
  7350         final = true;
  7351         break;
  7353       var tagCode = tagCodeAndLength >> 6;
  7354       var length = tagCodeAndLength & 63;
  7355       if (length === 63) {
  7356         stream.ensure(4);
  7357         length = readUi32(bytes, stream);
  7359       if (tag) {
  7360         if (tagCode === 1 && tag.code === 1) {
  7361           tag.repeat++;
  7362           stream.pos += length;
  7363           continue;
  7365         tags.push(tag);
  7366         if (onprogress && tag.id !== undefined) {
  7367           onprogress(context);
  7369         tag = null;
  7371       stream.ensure(length);
  7372       var substream = stream.substream(stream.pos, stream.pos += length);
  7373       var subbytes = substream.bytes;
  7374       var nextTag = {
  7375           code: tagCode
  7376         };
  7377       if (tagCode === 39) {
  7378         nextTag.type = 'sprite';
  7379         nextTag.id = readUi16(subbytes, substream);
  7380         nextTag.frameCount = readUi16(subbytes, substream);
  7381         nextTag.tags = [];
  7382         readTags(nextTag, substream, swfVersion, true);
  7383       } else if (tagCode === 1) {
  7384         nextTag.repeat = 1;
  7385       } else {
  7386         var handler = tagHandler[tagCode];
  7387         if (handler) {
  7388           handler(subbytes, substream, nextTag, swfVersion, tagCode);
  7391       tag = nextTag;
  7393     if (tag && final) {
  7394       tag.finalTag = true;
  7395       tags.push(tag);
  7396       if (onprogress) {
  7397         onprogress(context);
  7399     } else {
  7400       context._readTag = tag;
  7402   } catch (e) {
  7403     if (e !== StreamNoDataError) {
  7404       onexception && onexception(e);
  7405       throw e;
  7407     stream.pos = lastSuccessfulPosition;
  7408     context._readTag = tag;
  7411 function HeadTailBuffer(defaultSize) {
  7412   this.bufferSize = defaultSize || 16;
  7413   this.buffer = new Uint8Array(this.bufferSize);
  7414   this.pos = 0;
  7416 HeadTailBuffer.prototype = {
  7417   push: function (data, need) {
  7418     var bufferLengthNeed = this.pos + data.length;
  7419     if (this.bufferSize < bufferLengthNeed) {
  7420       var newBufferSize = this.bufferSize;
  7421       while (newBufferSize < bufferLengthNeed) {
  7422         newBufferSize <<= 1;
  7424       var newBuffer = new Uint8Array(newBufferSize);
  7425       if (this.bufferSize > 0) {
  7426         newBuffer.set(this.buffer);
  7428       this.buffer = newBuffer;
  7429       this.bufferSize = newBufferSize;
  7431     this.buffer.set(data, this.pos);
  7432     this.pos += data.length;
  7433     if (need)
  7434       return this.pos >= need;
  7435   },
  7436   getHead: function (size) {
  7437     return this.buffer.subarray(0, size);
  7438   },
  7439   getTail: function (offset) {
  7440     return this.buffer.subarray(offset, this.pos);
  7441   },
  7442   removeHead: function (size) {
  7443     var tail = this.getTail(size);
  7444     this.buffer = new Uint8Array(this.bufferSize);
  7445     this.buffer.set(tail);
  7446     this.pos = tail.length;
  7447   },
  7448   get arrayBuffer() {
  7449     return this.buffer.buffer;
  7450   },
  7451   get length() {
  7452     return this.pos;
  7453   },
  7454   createStream: function () {
  7455     return new Stream(this.arrayBuffer, 0, this.length);
  7457 };
  7458 function CompressedPipe(target, length) {
  7459   this.target = target;
  7460   this.length = length;
  7461   this.initialize = true;
  7462   this.buffer = new HeadTailBuffer(8096);
  7463   this.state = {
  7464     bitBuffer: 0,
  7465     bitLength: 0,
  7466     compression: {
  7467       header: null,
  7468       distanceTable: null,
  7469       literalTable: null,
  7470       sym: null,
  7471       len: null,
  7472       sym2: null
  7474   };
  7475   this.output = {
  7476     data: new Uint8Array(length),
  7477     available: 0,
  7478     completed: false
  7479   };
  7481 CompressedPipe.prototype = {
  7482   push: function (data, progressInfo) {
  7483     var buffer = this.buffer;
  7484     if (this.initialize) {
  7485       if (!buffer.push(data, 2))
  7486         return;
  7487       var headerBytes = buffer.getHead(2);
  7488       verifyDeflateHeader(headerBytes);
  7489       buffer.removeHead(2);
  7490       this.initialize = false;
  7491     } else {
  7492       buffer.push(data);
  7494     var stream = buffer.createStream();
  7495     stream.bitBuffer = this.state.bitBuffer;
  7496     stream.bitLength = this.state.bitLength;
  7497     var output = this.output;
  7498     var lastAvailable = output.available;
  7499     try {
  7500       do {
  7501         inflateBlock(stream, output, this.state.compression);
  7502       } while (stream.pos < buffer.length && !output.completed);
  7503     } catch (e) {
  7504       if (e !== InflateNoDataError)
  7505         throw e;
  7506     } finally {
  7507       this.state.bitBuffer = stream.bitBuffer;
  7508       this.state.bitLength = stream.bitLength;
  7510     buffer.removeHead(stream.pos);
  7511     this.target.push(output.data.subarray(lastAvailable, output.available), progressInfo);
  7513 };
  7514 function BodyParser(swfVersion, length, options) {
  7515   this.swf = {
  7516     swfVersion: swfVersion,
  7517     parseTime: 0
  7518   };
  7519   this.buffer = new HeadTailBuffer(32768);
  7520   this.initialize = true;
  7521   this.totalRead = 0;
  7522   this.length = length;
  7523   this.options = options;
  7525 BodyParser.prototype = {
  7526   push: function (data, progressInfo) {
  7527     if (data.length === 0)
  7528       return;
  7529     var swf = this.swf;
  7530     var swfVersion = swf.swfVersion;
  7531     var buffer = this.buffer;
  7532     var options = this.options;
  7533     var stream;
  7534     if (this.initialize) {
  7535       var PREFETCH_SIZE = 27;
  7536       if (!buffer.push(data, PREFETCH_SIZE))
  7537         return;
  7538       stream = buffer.createStream();
  7539       var bytes = stream.bytes;
  7540       readHeader(bytes, stream, swf);
  7541       var nextTagHeader = readUi16(bytes, stream);
  7542       var FILE_ATTRIBUTES_LENGTH = 4;
  7543       if (nextTagHeader == (SWF_TAG_CODE_FILE_ATTRIBUTES << 6 | FILE_ATTRIBUTES_LENGTH)) {
  7544         stream.ensure(FILE_ATTRIBUTES_LENGTH);
  7545         var substream = stream.substream(stream.pos, stream.pos += FILE_ATTRIBUTES_LENGTH);
  7546         var handler = tagHandler[SWF_TAG_CODE_FILE_ATTRIBUTES];
  7547         var fileAttributesTag = {
  7548             code: SWF_TAG_CODE_FILE_ATTRIBUTES
  7549           };
  7550         handler(substream.bytes, substream, fileAttributesTag, swfVersion, SWF_TAG_CODE_FILE_ATTRIBUTES);
  7551         swf.fileAttributes = fileAttributesTag;
  7552       } else {
  7553         stream.pos -= 2;
  7554         swf.fileAttributes = {};
  7556       if (options.onstart)
  7557         options.onstart(swf);
  7558       swf.tags = [];
  7559       this.initialize = false;
  7560     } else {
  7561       buffer.push(data);
  7562       stream = buffer.createStream();
  7564     var finalBlock = false;
  7565     if (progressInfo) {
  7566       swf.bytesLoaded = progressInfo.bytesLoaded;
  7567       swf.bytesTotal = progressInfo.bytesTotal;
  7568       finalBlock = progressInfo.bytesLoaded >= progressInfo.bytesTotal;
  7570     var readStartTime = performance.now();
  7571     readTags(swf, stream, swfVersion, finalBlock, options.onprogress, options.onexception);
  7572     swf.parseTime += performance.now() - readStartTime;
  7573     var read = stream.pos;
  7574     buffer.removeHead(read);
  7575     this.totalRead += read;
  7576     if (options.oncomplete && swf.tags[swf.tags.length - 1].finalTag) {
  7577       options.oncomplete(swf);
  7580 };
  7581 SWF.parseAsync = function swf_parseAsync(options) {
  7582   var buffer = new HeadTailBuffer();
  7583   var pipe = {
  7584       push: function (data, progressInfo) {
  7585         if (this.target !== undefined) {
  7586           return this.target.push(data, progressInfo);
  7588         if (!buffer.push(data, 8)) {
  7589           return null;
  7591         var bytes = buffer.getHead(8);
  7592         var magic1 = bytes[0];
  7593         var magic2 = bytes[1];
  7594         var magic3 = bytes[2];
  7595         if ((magic1 === 70 || magic1 === 67) && magic2 === 87 && magic3 === 83) {
  7596           var swfVersion = bytes[3];
  7597           var compressed = magic1 === 67;
  7598           parseSWF(compressed, swfVersion, progressInfo);
  7599           buffer = null;
  7600           return;
  7602         var isImage = false;
  7603         var imageType;
  7604         if (magic1 === 255 && magic2 === 216 && magic3 === 255) {
  7605           isImage = true;
  7606           imageType = 'image/jpeg';
  7607         } else if (magic1 === 137 && magic2 === 80 && magic3 === 78) {
  7608           isImage = true;
  7609           imageType = 'image/png';
  7611         if (isImage) {
  7612           parseImage(data, progressInfo.bytesTotal, imageType);
  7614         buffer = null;
  7615       },
  7616       close: function () {
  7617         if (buffer) {
  7618           var symbol = {
  7619               command: 'empty',
  7620               data: buffer.buffer.subarray(0, buffer.pos)
  7621             };
  7622           options.oncomplete && options.oncomplete(symbol);
  7624         if (this.target !== undefined && this.target.close) {
  7625           this.target.close();
  7628     };
  7629   function parseSWF(compressed, swfVersion, progressInfo) {
  7630     var stream = buffer.createStream();
  7631     stream.pos += 4;
  7632     var fileLength = readUi32(null, stream);
  7633     var bodyLength = fileLength - 8;
  7634     var target = new BodyParser(swfVersion, bodyLength, options);
  7635     if (compressed) {
  7636       target = new CompressedPipe(target, bodyLength);
  7638     target.push(buffer.getTail(8), progressInfo);
  7639     pipe['target'] = target;
  7641   function parseImage(data, bytesTotal, type) {
  7642     var buffer = new Uint8Array(bytesTotal);
  7643     buffer.set(data);
  7644     var bufferPos = data.length;
  7645     pipe['target'] = {
  7646       push: function (data) {
  7647         buffer.set(data, bufferPos);
  7648         bufferPos += data.length;
  7649       },
  7650       close: function () {
  7651         var props = {};
  7652         var chunks;
  7653         if (type == 'image/jpeg') {
  7654           chunks = parseJpegChunks(props, buffer);
  7655         } else {
  7656           chunks = [
  7657             buffer
  7658           ];
  7660         var symbol = {
  7661             type: 'image',
  7662             props: props,
  7663             data: new Blob(chunks, {
  7664               type: type
  7665             })
  7666           };
  7667         options.oncomplete && options.oncomplete(symbol);
  7669     };
  7671   return pipe;
  7672 };
  7673 SWF.parse = function (buffer, options) {
  7674   if (!options)
  7675     options = {};
  7676   var pipe = SWF.parseAsync(options);
  7677   var bytes = new Uint8Array(buffer);
  7678   var progressInfo = {
  7679       bytesLoaded: bytes.length,
  7680       bytesTotal: bytes.length
  7681     };
  7682   pipe.push(bytes, progressInfo);
  7683   pipe.close();
  7684 };
  7685 var $RELEASE = false;
  7686 var isWorker = typeof window === 'undefined';
  7687 if (isWorker && !true) {
  7688   importScripts.apply(null, [
  7689     '../../lib/DataView.js/DataView.js',
  7690     '../flash/util.js',
  7691     'config.js',
  7692     'swf.js',
  7693     'types.js',
  7694     'structs.js',
  7695     'tags.js',
  7696     'inflate.js',
  7697     'stream.js',
  7698     'templates.js',
  7699     'generator.js',
  7700     'handlers.js',
  7701     'parser.js',
  7702     'bitmap.js',
  7703     'button.js',
  7704     'font.js',
  7705     'image.js',
  7706     'label.js',
  7707     'shape.js',
  7708     'sound.js',
  7709     'text.js'
  7710   ]);
  7712 function defineSymbol(swfTag, symbols) {
  7713   var symbol;
  7714   switch (swfTag.code) {
  7715   case SWF_TAG_CODE_DEFINE_BITS:
  7716   case SWF_TAG_CODE_DEFINE_BITS_JPEG2:
  7717   case SWF_TAG_CODE_DEFINE_BITS_JPEG3:
  7718   case SWF_TAG_CODE_DEFINE_BITS_JPEG4:
  7719   case SWF_TAG_CODE_JPEG_TABLES:
  7720     symbol = defineImage(swfTag, symbols);
  7721     break;
  7722   case SWF_TAG_CODE_DEFINE_BITS_LOSSLESS:
  7723   case SWF_TAG_CODE_DEFINE_BITS_LOSSLESS2:
  7724     symbol = defineBitmap(swfTag);
  7725     break;
  7726   case SWF_TAG_CODE_DEFINE_BUTTON:
  7727   case SWF_TAG_CODE_DEFINE_BUTTON2:
  7728     symbol = defineButton(swfTag, symbols);
  7729     break;
  7730   case SWF_TAG_CODE_DEFINE_EDIT_TEXT:
  7731     symbol = defineText(swfTag, symbols);
  7732     break;
  7733   case SWF_TAG_CODE_DEFINE_FONT:
  7734   case SWF_TAG_CODE_DEFINE_FONT2:
  7735   case SWF_TAG_CODE_DEFINE_FONT3:
  7736   case SWF_TAG_CODE_DEFINE_FONT4:
  7737     symbol = defineFont(swfTag, symbols);
  7738     break;
  7739   case SWF_TAG_CODE_DEFINE_MORPH_SHAPE:
  7740   case SWF_TAG_CODE_DEFINE_MORPH_SHAPE2:
  7741   case SWF_TAG_CODE_DEFINE_SHAPE:
  7742   case SWF_TAG_CODE_DEFINE_SHAPE2:
  7743   case SWF_TAG_CODE_DEFINE_SHAPE3:
  7744   case SWF_TAG_CODE_DEFINE_SHAPE4:
  7745     symbol = defineShape(swfTag, symbols);
  7746     break;
  7747   case SWF_TAG_CODE_DEFINE_SOUND:
  7748     symbol = defineSound(swfTag, symbols);
  7749     break;
  7750   case SWF_TAG_CODE_DEFINE_BINARY_DATA:
  7751     symbol = {
  7752       type: 'binary',
  7753       id: swfTag.id,
  7754       data: swfTag.data
  7755     };
  7756     break;
  7757   case SWF_TAG_CODE_DEFINE_SPRITE:
  7758     var depths = {};
  7759     var frame = {
  7760         type: 'frame'
  7761       };
  7762     var frames = [];
  7763     var tags = swfTag.tags;
  7764     var frameScripts = null;
  7765     var frameIndex = 0;
  7766     var soundStream = null;
  7767     for (var i = 0, n = tags.length; i < n; i++) {
  7768       var tag = tags[i];
  7769       switch (tag.code) {
  7770       case SWF_TAG_CODE_DO_ACTION:
  7771         if (!frameScripts)
  7772           frameScripts = [];
  7773         frameScripts.push(frameIndex);
  7774         frameScripts.push(tag.actionsData);
  7775         break;
  7776       case SWF_TAG_CODE_START_SOUND:
  7777         var startSounds = frame.startSounds || (frame.startSounds = []);
  7778         startSounds.push(tag);
  7779         break;
  7780       case SWF_TAG_CODE_SOUND_STREAM_HEAD:
  7781         try {
  7782           soundStream = createSoundStream(tag);
  7783           frame.soundStream = soundStream.info;
  7784         } catch (e) {
  7786         break;
  7787       case SWF_TAG_CODE_SOUND_STREAM_BLOCK:
  7788         if (soundStream) {
  7789           frame.soundStreamBlock = soundStream.decode(tag.data);
  7791         break;
  7792       case SWF_TAG_CODE_FRAME_LABEL:
  7793         frame.labelName = tag.name;
  7794         break;
  7795       case SWF_TAG_CODE_PLACE_OBJECT:
  7796       case SWF_TAG_CODE_PLACE_OBJECT2:
  7797       case SWF_TAG_CODE_PLACE_OBJECT3:
  7798         depths[tag.depth] = tag;
  7799         break;
  7800       case SWF_TAG_CODE_REMOVE_OBJECT:
  7801       case SWF_TAG_CODE_REMOVE_OBJECT2:
  7802         depths[tag.depth] = null;
  7803         break;
  7804       case SWF_TAG_CODE_SHOW_FRAME:
  7805         frameIndex += tag.repeat;
  7806         frame.repeat = tag.repeat;
  7807         frame.depths = depths;
  7808         frames.push(frame);
  7809         depths = {};
  7810         frame = {
  7811           type: 'frame'
  7812         };
  7813         break;
  7816     symbol = {
  7817       type: 'sprite',
  7818       id: swfTag.id,
  7819       frameCount: swfTag.frameCount,
  7820       frames: frames,
  7821       frameScripts: frameScripts
  7822     };
  7823     break;
  7824   case SWF_TAG_CODE_DEFINE_TEXT:
  7825   case SWF_TAG_CODE_DEFINE_TEXT2:
  7826     symbol = defineLabel(swfTag, symbols);
  7827     break;
  7829   if (!symbol) {
  7830     return {
  7831       command: 'error',
  7832       message: 'unknown symbol type: ' + swfTag.code
  7833     };
  7835   symbol.isSymbol = true;
  7836   symbols[swfTag.id] = symbol;
  7837   return symbol;
  7839 function createParsingContext(commitData) {
  7840   var depths = {};
  7841   var symbols = {};
  7842   var frame = {
  7843       type: 'frame'
  7844     };
  7845   var tagsProcessed = 0;
  7846   var soundStream = null;
  7847   var lastProgressSent = 0;
  7848   return {
  7849     onstart: function (result) {
  7850       commitData({
  7851         command: 'init',
  7852         result: result
  7853       });
  7854     },
  7855     onprogress: function (result) {
  7856       if (Date.now() - lastProgressSent > 1000 / 24 || result.bytesLoaded === result.bytesTotal) {
  7857         commitData({
  7858           command: 'progress',
  7859           result: {
  7860             bytesLoaded: result.bytesLoaded,
  7861             bytesTotal: result.bytesTotal
  7863         });
  7864         lastProgressSent = Date.now();
  7866       var tags = result.tags;
  7867       for (var n = tags.length; tagsProcessed < n; tagsProcessed++) {
  7868         var tag = tags[tagsProcessed];
  7869         if ('id' in tag) {
  7870           var symbol = defineSymbol(tag, symbols);
  7871           commitData(symbol, symbol.transferables);
  7872           continue;
  7874         switch (tag.code) {
  7875         case SWF_TAG_CODE_DEFINE_SCENE_AND_FRAME_LABEL_DATA:
  7876           frame.sceneData = tag;
  7877           break;
  7878         case SWF_TAG_CODE_DEFINE_SCALING_GRID:
  7879           var symbolUpdate = {
  7880               isSymbol: true,
  7881               id: tag.symbolId,
  7882               updates: {
  7883                 scale9Grid: tag.splitter
  7885             };
  7886           commitData(symbolUpdate);
  7887           break;
  7888         case SWF_TAG_CODE_DO_ABC:
  7889         case SWF_TAG_CODE_DO_ABC_:
  7890           var abcBlocks = frame.abcBlocks;
  7891           if (abcBlocks)
  7892             abcBlocks.push({
  7893               data: tag.data,
  7894               flags: tag.flags
  7895             });
  7896           else
  7897             frame.abcBlocks = [
  7899                 data: tag.data,
  7900                 flags: tag.flags
  7902             ];
  7903           break;
  7904         case SWF_TAG_CODE_DO_ACTION:
  7905           var actionBlocks = frame.actionBlocks;
  7906           if (actionBlocks)
  7907             actionBlocks.push(tag.actionsData);
  7908           else
  7909             frame.actionBlocks = [
  7910               tag.actionsData
  7911             ];
  7912           break;
  7913         case SWF_TAG_CODE_DO_INIT_ACTION:
  7914           var initActionBlocks = frame.initActionBlocks || (frame.initActionBlocks = []);
  7915           initActionBlocks.push({
  7916             spriteId: tag.spriteId,
  7917             actionsData: tag.actionsData
  7918           });
  7919           break;
  7920         case SWF_TAG_CODE_START_SOUND:
  7921           var startSounds = frame.startSounds;
  7922           if (!startSounds)
  7923             frame.startSounds = startSounds = [];
  7924           startSounds.push(tag);
  7925           break;
  7926         case SWF_TAG_CODE_SOUND_STREAM_HEAD:
  7927           try {
  7928             soundStream = createSoundStream(tag);
  7929             frame.soundStream = soundStream.info;
  7930           } catch (e) {
  7932           break;
  7933         case SWF_TAG_CODE_SOUND_STREAM_BLOCK:
  7934           if (soundStream) {
  7935             frame.soundStreamBlock = soundStream.decode(tag.data);
  7937           break;
  7938         case SWF_TAG_CODE_EXPORT_ASSETS:
  7939           var exports = frame.exports;
  7940           if (exports)
  7941             frame.exports = exports.concat(tag.exports);
  7942           else
  7943             frame.exports = tag.exports.slice(0);
  7944           break;
  7945         case SWF_TAG_CODE_SYMBOL_CLASS:
  7946           var symbolClasses = frame.symbolClasses;
  7947           if (symbolClasses)
  7948             frame.symbolClasses = symbolClasses.concat(tag.exports);
  7949           else
  7950             frame.symbolClasses = tag.exports.slice(0);
  7951           break;
  7952         case SWF_TAG_CODE_FRAME_LABEL:
  7953           frame.labelName = tag.name;
  7954           break;
  7955         case SWF_TAG_CODE_PLACE_OBJECT:
  7956         case SWF_TAG_CODE_PLACE_OBJECT2:
  7957         case SWF_TAG_CODE_PLACE_OBJECT3:
  7958           depths[tag.depth] = tag;
  7959           break;
  7960         case SWF_TAG_CODE_REMOVE_OBJECT:
  7961         case SWF_TAG_CODE_REMOVE_OBJECT2:
  7962           depths[tag.depth] = null;
  7963           break;
  7964         case SWF_TAG_CODE_SET_BACKGROUND_COLOR:
  7965           frame.bgcolor = tag.color;
  7966           break;
  7967         case SWF_TAG_CODE_SHOW_FRAME:
  7968           frame.repeat = tag.repeat;
  7969           frame.depths = depths;
  7970           frame.complete = !(!tag.finalTag);
  7971           commitData(frame);
  7972           depths = {};
  7973           frame = {
  7974             type: 'frame'
  7975           };
  7976           break;
  7979     },
  7980     oncomplete: function (result) {
  7981       commitData(result);
  7982       var stats;
  7983       if (typeof result.swfVersion === 'number') {
  7984         var bbox = result.bbox;
  7985         stats = {
  7986           topic: 'parseInfo',
  7987           parseTime: result.parseTime,
  7988           bytesTotal: result.bytesTotal,
  7989           swfVersion: result.swfVersion,
  7990           frameRate: result.frameRate,
  7991           width: (bbox.xMax - bbox.xMin) / 20,
  7992           height: (bbox.yMax - bbox.yMin) / 20,
  7993           isAvm2: !(!result.fileAttributes.doAbc)
  7994         };
  7996       commitData({
  7997         command: 'complete',
  7998         stats: stats
  7999       });
  8000     },
  8001     onexception: function (e) {
  8002       commitData({
  8003         type: 'exception',
  8004         message: e.message,
  8005         stack: e.stack
  8006       });
  8008   };
  8010 function parseBytes(bytes, commitData) {
  8011   SWF.parse(bytes, createParsingContext(commitData));
  8013 function ResourceLoader(scope) {
  8014   this.subscription = null;
  8015   var self = this;
  8016   if (!isWorker) {
  8017     this.messenger = {
  8018       postMessage: function (data) {
  8019         self.onmessage({
  8020           data: data
  8021         });
  8023     };
  8024   } else {
  8025     this.messenger = scope;
  8026     scope.onmessage = function (event) {
  8027       self.listener(event.data);
  8028     };
  8031 ResourceLoader.prototype = {
  8032   terminate: function () {
  8033     this.messenger = null;
  8034     this.listener = null;
  8035   },
  8036   onmessage: function (event) {
  8037     this.listener(event.data);
  8038   },
  8039   postMessage: function (data) {
  8040     this.listener && this.listener(data);
  8041   },
  8042   listener: function (data) {
  8043     if (this.subscription) {
  8044       this.subscription.callback(data.data, data.progress);
  8045     } else if (data === 'pipe:') {
  8046       this.subscription = {
  8047         subscribe: function (callback) {
  8048           this.callback = callback;
  8050       };
  8051       this.parseLoadedData(this.messenger, this.subscription);
  8052     } else {
  8053       this.parseLoadedData(this.messenger, data);
  8055   },
  8056   parseLoadedData: function (loader, request, context) {
  8057     function commitData(data, transferables) {
  8058       try {
  8059         loader.postMessage(data, transferables);
  8060       } catch (ex) {
  8061         if (ex != 'DataCloneError') {
  8062           throw ex;
  8064         loader.postMessage(data);
  8067     if (request instanceof ArrayBuffer) {
  8068       parseBytes(request, commitData);
  8069     } else if ('subscribe' in request) {
  8070       var pipe = SWF.parseAsync(createParsingContext(commitData));
  8071       request.subscribe(function (data, progress) {
  8072         if (data) {
  8073           pipe.push(data, progress);
  8074         } else {
  8075           pipe.close();
  8077       });
  8078     } else if (typeof FileReaderSync !== 'undefined') {
  8079       var reader = new FileReaderSync();
  8080       var buffer = reader.readAsArrayBuffer(request);
  8081       parseBytes(buffer, commitData);
  8082     } else {
  8083       var reader = new FileReader();
  8084       reader.onload = function () {
  8085         parseBytes(this.result, commitData);
  8086       };
  8087       reader.readAsArrayBuffer(request);
  8090 };
  8091 if (isWorker) {
  8092   var loader = new ResourceLoader(this);
  8094 function ActionsDataStream(array, swfVersion) {
  8095   this.array = array;
  8096   this.position = 0;
  8097   this.end = array.length;
  8098   if (swfVersion >= 6) {
  8099     this.readString = this.readUTF8String;
  8100   } else {
  8101     this.readString = this.readANSIString;
  8103   var buffer = new ArrayBuffer(4);
  8104   new Int32Array(buffer)[0] = 1;
  8105   if (!new Uint8Array(buffer)[0]) {
  8106     throw new Error('big-endian platform');
  8109 ActionsDataStream.prototype = {
  8110   readUI8: function ActionsDataStream_readUI8() {
  8111     return this.array[this.position++];
  8112   },
  8113   readUI16: function ActionsDataStream_readUI16() {
  8114     var position = this.position, array = this.array;
  8115     var value = array[position + 1] << 8 | array[position];
  8116     this.position = position + 2;
  8117     return value;
  8118   },
  8119   readSI16: function ActionsDataStream_readSI16() {
  8120     var position = this.position, array = this.array;
  8121     var value = array[position + 1] << 8 | array[position];
  8122     this.position = position + 2;
  8123     return value < 32768 ? value : value - 65536;
  8124   },
  8125   readInteger: function ActionsDataStream_readInteger() {
  8126     var position = this.position, array = this.array;
  8127     var value = array[position] | array[position + 1] << 8 | array[position + 2] << 16 | array[position + 3] << 24;
  8128     this.position = position + 4;
  8129     return value;
  8130   },
  8131   readFloat: function ActionsDataStream_readFloat() {
  8132     var position = this.position;
  8133     var array = this.array;
  8134     var buffer = new ArrayBuffer(4);
  8135     var bytes = new Uint8Array(buffer);
  8136     bytes[0] = array[position];
  8137     bytes[1] = array[position + 1];
  8138     bytes[2] = array[position + 2];
  8139     bytes[3] = array[position + 3];
  8140     this.position = position + 4;
  8141     return new Float32Array(buffer)[0];
  8142   },
  8143   readDouble: function ActionsDataStream_readDouble() {
  8144     var position = this.position;
  8145     var array = this.array;
  8146     var buffer = new ArrayBuffer(8);
  8147     var bytes = new Uint8Array(buffer);
  8148     bytes[4] = array[position];
  8149     bytes[5] = array[position + 1];
  8150     bytes[6] = array[position + 2];
  8151     bytes[7] = array[position + 3];
  8152     bytes[0] = array[position + 4];
  8153     bytes[1] = array[position + 5];
  8154     bytes[2] = array[position + 6];
  8155     bytes[3] = array[position + 7];
  8156     this.position = position + 8;
  8157     return new Float64Array(buffer)[0];
  8158   },
  8159   readBoolean: function ActionsDataStream_readBoolean() {
  8160     return !(!this.readUI8());
  8161   },
  8162   readANSIString: function ActionsDataStream_readANSIString() {
  8163     var value = '';
  8164     var ch;
  8165     while (ch = this.readUI8()) {
  8166       value += String.fromCharCode(ch);
  8168     return value;
  8169   },
  8170   readUTF8String: function ActionsDataStream_readUTF8String() {
  8171     var value = '';
  8172     var ch;
  8173     while (ch = this.readUI8()) {
  8174       if (ch < 128) {
  8175         value += String.fromCharCode(ch);
  8176         continue;
  8178       if ((ch & 192) === 128) {
  8179         throw new Error('Invalid UTF8 encoding');
  8181       var currentPrefix = 192;
  8182       var validBits = 5;
  8183       do {
  8184         var mask = currentPrefix >> 1 | 128;
  8185         if ((ch & mask) === currentPrefix) {
  8186           break;
  8188         currentPrefix = mask;
  8189         --validBits;
  8190       } while (validBits >= 0);
  8191       var code = ch & (1 << validBits) - 1;
  8192       for (var i = 5; i >= validBits; --i) {
  8193         ch = this.readUI8();
  8194         if ((ch & 192) !== 128) {
  8195           throw new Error('Invalid UTF8 encoding');
  8197         code = code << 6 | ch & 63;
  8199       if (code >= 65536) {
  8200         value += String.fromCharCode(code - 65536 >> 10 & 1023 | 55296, code & 1023 | 56320);
  8201       } else {
  8202         value += String.fromCharCode(code);
  8205     return value;
  8206   },
  8207   readBytes: function ActionsDataStream_readBytes(length) {
  8208     var position = this.position;
  8209     var remaining = Math.max(this.end - position, 0);
  8210     if (remaining < length) {
  8211       length = remaining;
  8213     var subarray = this.array.subarray(position, position + length);
  8214     this.position = position + length;
  8215     return subarray;
  8217 };
  8218 if (typeof GLOBAL !== 'undefined') {
  8219   GLOBAL.ActionsDataStream = ActionsDataStream;
  8221 var AVM1_TRACE_ENABLED = false;
  8222 var AVM1_ERRORS_IGNORED = true;
  8223 var MAX_AVM1_HANG_TIMEOUT = 1000;
  8224 var MAX_AVM1_ERRORS_LIMIT = 1000;
  8225 var MAX_AVM1_STACK_LIMIT = 256;
  8226 function AS2ScopeListItem(scope, next) {
  8227   this.scope = scope;
  8228   this.next = next;
  8230 AS2ScopeListItem.prototype = {
  8231   create: function (scope) {
  8232     return new AS2ScopeListItem(scope, this);
  8234 };
  8235 function AS2Context(swfVersion) {
  8236   this.swfVersion = swfVersion;
  8237   this.globals = new avm1lib.AS2Globals(this);
  8238   this.initialScope = new AS2ScopeListItem(this.globals, null);
  8239   this.assets = {};
  8240   this.isActive = false;
  8241   this.executionProhibited = false;
  8242   this.abortExecutionAt = 0;
  8243   this.stackDepth = 0;
  8244   this.isTryCatchListening = false;
  8245   this.errorsIgnored = 0;
  8246   this.deferScriptExecution = true;
  8247   this.pendingScripts = [];
  8249 AS2Context.instance = null;
  8250 AS2Context.prototype = {
  8251   addAsset: function (className, symbolProps) {
  8252     this.assets[className] = symbolProps;
  8253   },
  8254   resolveTarget: function (target) {
  8255     if (!target) {
  8256       target = this.defaultTarget;
  8257     } else if (typeof target === 'string') {
  8258       target = lookupAS2Children(target, this.defaultTarget, this.globals.asGetPublicProperty('_root'));
  8260     if (typeof target !== 'object' || target === null || !('$nativeObject' in target)) {
  8261       throw new Error('Invalid AS2 target object: ' + Object.prototype.toString.call(target));
  8263     return target;
  8264   },
  8265   resolveLevel: function (level) {
  8266     return this.resolveTarget(this.globals['_level' + level]);
  8267   },
  8268   addToPendingScripts: function (fn) {
  8269     if (!this.deferScriptExecution) {
  8270       return fn();
  8272     this.pendingScripts.push(fn);
  8273   },
  8274   flushPendingScripts: function () {
  8275     var scripts = this.pendingScripts;
  8276     while (scripts.length) {
  8277       scripts.shift()();
  8279     this.deferScriptExecution = false;
  8281 };
  8282 function AS2Error(error) {
  8283   this.error = error;
  8285 function AS2CriticalError(message, error) {
  8286   this.message = message;
  8287   this.error = error;
  8289 AS2CriticalError.prototype = Object.create(Error.prototype);
  8290 function isAS2MovieClip(obj) {
  8291   return typeof obj === 'object' && obj && obj instanceof avm1lib.AS2MovieClip;
  8293 function as2GetType(v) {
  8294   if (v === null) {
  8295     return 'null';
  8297   var type = typeof v;
  8298   if (type === 'function') {
  8299     return 'object';
  8301   if (type === 'object' && isAS2MovieClip(v)) {
  8302     return 'movieclip';
  8304   return type;
  8306 function as2ToPrimitive(value) {
  8307   return as2GetType(value) !== 'object' ? value : value.valueOf();
  8309 function as2ToAddPrimitive(value) {
  8310   if (as2GetType(value) !== 'object') {
  8311     return value;
  8313   if (value instanceof Date && AS2Context.instance.swfVersion >= 6) {
  8314     return value.toString();
  8315   } else {
  8316     return value.valueOf();
  8319 function as2ToBoolean(value) {
  8320   switch (as2GetType(value)) {
  8321   default:
  8322   case 'undefined':
  8323   case 'null':
  8324     return false;
  8325   case 'boolean':
  8326     return value;
  8327   case 'number':
  8328     return value !== 0 && !isNaN(value);
  8329   case 'string':
  8330     return value.length !== 0;
  8331   case 'movieclip':
  8332   case 'object':
  8333     return true;
  8336 function as2ToNumber(value) {
  8337   value = as2ToPrimitive(value);
  8338   switch (as2GetType(value)) {
  8339   case 'undefined':
  8340   case 'null':
  8341     return AS2Context.instance.swfVersion >= 7 ? NaN : 0;
  8342   case 'boolean':
  8343     return value ? 1 : +0;
  8344   case 'number':
  8345     return value;
  8346   case 'string':
  8347     if (value === '' && AS2Context.instance.swfVersion < 5) {
  8348       return 0;
  8350     return +value;
  8351   default:
  8352     return AS2Context.instance.swfVersion >= 5 ? NaN : 0;
  8355 function as2ToInteger(value) {
  8356   var result = as2ToNumber(value);
  8357   if (isNaN(result)) {
  8358     return 0;
  8360   if (!isFinite(result) || result === 0) {
  8361     return result;
  8363   return (result < 0 ? -1 : 1) * Math.abs(result) | 0;
  8365 function as2ToInt32(value) {
  8366   var result = as2ToNumber(value);
  8367   return isNaN(result) || !isFinite(result) || result === 0 ? 0 : result | 0;
  8369 function as2ToString(value) {
  8370   switch (as2GetType(value)) {
  8371   case 'undefined':
  8372     return AS2Context.instance.swfVersion >= 7 ? 'undefined' : '';
  8373   case 'null':
  8374     return 'null';
  8375   case 'boolean':
  8376     return value ? 'true' : 'false';
  8377   case 'number':
  8378     return value.toString();
  8379   case 'string':
  8380     return value;
  8381   case 'movieclip':
  8382     return value.$targetPath;
  8383   case 'object':
  8384     var result = value.toString !== Function.prototype.toString ? value.toString() : value;
  8385     if (typeof result === 'string') {
  8386       return result;
  8388     return typeof value === 'function' ? '[type Function]' : '[type Object]';
  8391 function as2Compare(x, y) {
  8392   var x2 = as2ToPrimitive(x);
  8393   var y2 = as2ToPrimitive(y);
  8394   if (typeof x2 === 'string' && typeof y2 === 'string') {
  8395     return x2 < y2;
  8396   } else {
  8397     return as2ToNumber(x2) < as2ToNumber(y2);
  8400 function as2InstanceOf(obj, constructor) {
  8401   if (obj instanceof constructor) {
  8402     return true;
  8404   return false;
  8406 function as2ResolveProperty(obj, name) {
  8407   var avm2PublicName = Multiname.getPublicQualifiedName(name);
  8408   if (avm2PublicName in obj) {
  8409     return name;
  8411   if (isNumeric(name)) {
  8412     return null;
  8414   var lowerCaseName = avm2PublicName.toLowerCase();
  8415   for (var i in obj) {
  8416     if (i.toLowerCase() === lowerCaseName) {
  8417       notImplemented('FIX THIS');
  8420   return null;
  8422 function as2GetPrototype(obj) {
  8423   return obj && obj.asGetPublicProperty('prototype');
  8425 function isAvm2Class(obj) {
  8426   return typeof obj === 'object' && obj !== null && 'instanceConstructor' in obj;
  8428 function as2CreatePrototypeProxy(obj) {
  8429   var prototype = obj.asGetPublicProperty('prototype');
  8430   if (typeof Proxy === 'undefined') {
  8431     console.error('ES6 proxies are not found');
  8432     return prototype;
  8434   return Proxy.create({
  8435     getOwnPropertyDescriptor: function (name) {
  8436       return Object.getOwnPropertyDescriptor(prototype, name);
  8437     },
  8438     getPropertyDescriptor: function (name) {
  8439       for (var p = prototype; p; p = Object.getPrototypeOf(p)) {
  8440         var desc = Object.getOwnPropertyDescriptor(p, name);
  8441         if (desc)
  8442           return desc;
  8444     },
  8445     getOwnPropertyNames: function () {
  8446       return Object.getOwnPropertyNames(prototype);
  8447     },
  8448     getPropertyNames: function () {
  8449       var names = Object.getOwnPropertyNames(prototype);
  8450       for (var p = Object.getPrototypeOf(prototype); p; p = Object.getPrototypeOf(p)) {
  8451         names = names.concat(Object.getOwnPropertyNames(p));
  8453       return names;
  8454     },
  8455     defineProperty: function (name, desc) {
  8456       if (desc) {
  8457         if (typeof desc.value === 'function' && desc.value._setClass) {
  8458           desc.value._setClass(obj);
  8460         if (typeof desc.get === 'function' && desc.get._setClass) {
  8461           desc.get._setClass(obj);
  8463         if (typeof desc.set === 'function' && desc.set._setClass) {
  8464           desc.set._setClass(obj);
  8467       return Object.defineProperty(prototype, name, desc);
  8468     },
  8469     delete: function (name) {
  8470       return delete prototype[name];
  8471     },
  8472     fix: function () {
  8473       return undefined;
  8475   });
  8477 function executeActions(actionsData, context, scope) {
  8478   if (context.executionProhibited) {
  8479     return;
  8481   var actionTracer = ActionTracerFactory.get();
  8482   var scopeContainer = context.initialScope.create(scope);
  8483   var savedContext = AS2Context.instance;
  8484   try {
  8485     AS2Context.instance = context;
  8486     context.isActive = true;
  8487     context.abortExecutionAt = Date.now() + MAX_AVM1_HANG_TIMEOUT;
  8488     context.errorsIgnored = 0;
  8489     context.defaultTarget = scope;
  8490     context.globals.asSetPublicProperty('this', scope);
  8491     actionTracer.message('ActionScript Execution Starts');
  8492     actionTracer.indent();
  8493     interpretActions(actionsData, scopeContainer, null, []);
  8494   } catch (e) {
  8495     if (e instanceof AS2CriticalError) {
  8496       console.error('Disabling AVM1 execution');
  8497       context.executionProhibited = true;
  8499     throw e;
  8500   } finally {
  8501     context.isActive = false;
  8502     actionTracer.unindent();
  8503     actionTracer.message('ActionScript Execution Stops');
  8504     AS2Context.instance = savedContext;
  8507 function lookupAS2Children(targetPath, defaultTarget, root) {
  8508   var path = targetPath.split(/[\/.]/g);
  8509   if (path[path.length - 1] === '') {
  8510     path.pop();
  8512   var obj = defaultTarget;
  8513   if (path[0] === '' || path[0] === '_level0' || path[0] === '_root') {
  8514     obj = root;
  8515     path.shift();
  8517   while (path.length > 0) {
  8518     var prevObj = obj;
  8519     obj = obj.$lookupChild(path[0]);
  8520     if (!obj) {
  8521       throw new Error(path[0] + ' (expr ' + targetPath + ') is not found in ' + prevObj._target);
  8523     path.shift();
  8525   return obj;
  8527 function createBuiltinType(obj, args) {
  8528   if (obj === Array) {
  8529     var result = args;
  8530     if (args.length == 1 && typeof args[0] === 'number') {
  8531       result = [];
  8532       result.length = args[0];
  8534     return result;
  8536   if (obj === Boolean || obj === Number || obj === String || obj === Function) {
  8537     return obj.apply(null, args);
  8539   if (obj === Date) {
  8540     switch (args.length) {
  8541     case 0:
  8542       return new Date();
  8543     case 1:
  8544       return new Date(args[0]);
  8545     default:
  8546       return new Date(args[0], args[1], args.length > 2 ? args[2] : 1, args.length > 3 ? args[3] : 0, args.length > 4 ? args[4] : 0, args.length > 5 ? args[5] : 0, args.length > 6 ? args[6] : 0);
  8549   if (obj === Object) {
  8550     return {};
  8553 var AS2_SUPER_STUB = {};
  8554 function interpretActions(actionsData, scopeContainer, constantPool, registers) {
  8555   var currentContext = AS2Context.instance;
  8556   function setTarget(targetPath) {
  8557     if (!targetPath) {
  8558       currentContext.defaultTarget = scope;
  8559       return;
  8561     try {
  8562       currentContext.defaultTarget = lookupAS2Children(targetPath, defaultTarget, _global.asGetPublicProperty('_root'));
  8563     } catch (e) {
  8564       currentContext.defaultTarget = null;
  8565       throw e;
  8568   function defineFunction(functionName, parametersNames, registersAllocation, actionsData) {
  8569     var ownerClass;
  8570     var fn = function () {
  8571       var newScope = {};
  8572       newScope.asSetPublicProperty('this', this);
  8573       newScope.asSetPublicProperty('arguments', arguments);
  8574       newScope.asSetPublicProperty('super', AS2_SUPER_STUB);
  8575       newScope.asSetPublicProperty('__class', ownerClass);
  8576       var newScopeContainer = scopeContainer.create(newScope);
  8577       var i;
  8578       for (i = 0; i < arguments.length || i < parametersNames.length; i++) {
  8579         newScope.asSetPublicProperty(parametersNames[i], arguments[i]);
  8581       var registers = [];
  8582       if (registersAllocation) {
  8583         for (i = 0; i < registersAllocation.length; i++) {
  8584           var registerAllocation = registersAllocation[i];
  8585           if (!registerAllocation) {
  8586             continue;
  8588           if (registerAllocation.type == 'param') {
  8589             registers[i] = arguments[registerAllocation.index];
  8590           } else {
  8591             switch (registerAllocation.name) {
  8592             case 'this':
  8593               registers[i] = this;
  8594               break;
  8595             case 'arguments':
  8596               registers[i] = arguments;
  8597               break;
  8598             case 'super':
  8599               registers[i] = AS2_SUPER_STUB;
  8600               break;
  8601             case '_global':
  8602               registers[i] = _global;
  8603               break;
  8604             case '_parent':
  8605               registers[i] = scope.asGetPublicProperty('_parent');
  8606               break;
  8607             case '_root':
  8608               registers[i] = _global.asGetPublicProperty('_root');
  8609               break;
  8614       var savedContext = AS2Context.instance;
  8615       var savedIsActive = currentContext.isActive;
  8616       try {
  8617         AS2Context.instance = currentContext;
  8618         if (!savedIsActive) {
  8619           currentContext.abortExecutionAt = Date.now() + MAX_AVM1_HANG_TIMEOUT;
  8620           currentContext.errorsIgnored = 0;
  8621           currentContext.isActive = true;
  8623         currentContext.defaultTarget = scope;
  8624         actionTracer.indent();
  8625         currentContext.stackDepth++;
  8626         if (currentContext.stackDepth >= MAX_AVM1_STACK_LIMIT) {
  8627           throw new AS2CriticalError('long running script -- AVM1 recursion limit is reached');
  8629         return interpretActions(actionsData, newScopeContainer, constantPool, registers);
  8630       } finally {
  8631         currentContext.isActive = savedIsActive;
  8632         currentContext.stackDepth--;
  8633         actionTracer.unindent();
  8634         currentContext.defaultTarget = defaultTarget;
  8635         AS2Context.instance = savedContext;
  8637     };
  8638     ownerClass = fn;
  8639     fn._setClass = function (class_) {
  8640       ownerClass = class_;
  8641     };
  8642     fn.instanceConstructor = fn;
  8643     fn.debugName = 'avm1 ' + (functionName || '<function>');
  8644     if (functionName) {
  8645       fn.name = functionName;
  8647     return fn;
  8649   function deleteProperty(propertyName) {
  8650     for (var p = scopeContainer; p; p = p.next) {
  8651       if (p.scope.asHasProperty(undefined, propertyName, 0)) {
  8652         p.scope.asSetPublicProperty(propertyName, undefined);
  8653         return p.scope.asDeleteProperty(undefined, propertyName, 0);
  8656     return false;
  8658   function resolveVariableName(variableName, nonStrict) {
  8659     var obj, name, i;
  8660     if (variableName.indexOf(':') >= 0) {
  8661       var parts = variableName.split(':');
  8662       obj = lookupAS2Children(parts[0], defaultTarget, _global.asGetPublicProperty('_root'));
  8663       if (!obj) {
  8664         throw new Error(parts[0] + ' is undefined');
  8666       name = parts[1];
  8667     } else if (variableName.indexOf('.') >= 0) {
  8668       var objPath = variableName.split('.');
  8669       name = objPath.pop();
  8670       obj = _global;
  8671       for (i = 0; i < objPath.length; i++) {
  8672         obj = obj.asGetPublicProperty(objPath[i]) || obj[objPath[i]];
  8673         if (!obj) {
  8674           throw new Error(objPath.slice(0, i + 1) + ' is undefined');
  8678     if (!obj) {
  8679       return null;
  8681     var resolvedName = as2ResolveProperty(obj, name);
  8682     var resolved = resolvedName !== null;
  8683     if (resolved || nonStrict) {
  8684       return {
  8685         obj: obj,
  8686         name: resolvedName || name,
  8687         resolved: resolved
  8688       };
  8690     return null;
  8692   function getThis() {
  8693     var _this = scope.asGetPublicProperty('this');
  8694     if (_this) {
  8695       return _this;
  8697     for (var p = scopeContainer; p; p = p.next) {
  8698       resolvedName = as2ResolveProperty(p.scope, 'this');
  8699       if (resolvedName !== null) {
  8700         return p.scope.asGetPublicProperty(resolvedName);
  8704   function getVariable(variableName) {
  8705     if (scope.asHasProperty(undefined, variableName, 0)) {
  8706       return scope.asGetPublicProperty(variableName);
  8708     var target = resolveVariableName(variableName);
  8709     if (target) {
  8710       return target.obj.asGetPublicProperty(target.name);
  8712     var resolvedName, _this = getThis();
  8713     for (var p = scopeContainer; p; p = p.next) {
  8714       resolvedName = as2ResolveProperty(p.scope, variableName);
  8715       if (resolvedName !== null) {
  8716         return p.scope.asGetPublicProperty(resolvedName);
  8719     if (_this && (resolvedName = as2ResolveProperty(_this, variableName))) {
  8720       return _this.asGetPublicProperty(resolvedName);
  8722     var mc = isAS2MovieClip(defaultTarget) && defaultTarget.$lookupChild(variableName);
  8723     if (mc) {
  8724       return mc;
  8727   function setVariable(variableName, value) {
  8728     if (scope.asHasProperty(undefined, variableName, 0)) {
  8729       scope.asSetPublicProperty(variableName, value);
  8730       return;
  8732     var target = resolveVariableName(variableName, true);
  8733     if (target) {
  8734       target.obj.asSetPublicProperty(target.name, value);
  8735       return;
  8737     var resolvedName, _this = getThis();
  8738     if (_this && (resolvedName = as2ResolveProperty(_this, variableName))) {
  8739       return _this.asSetPublicProperty(resolvedName, value);
  8741     for (var p = scopeContainer; p.next; p = p.next) {
  8742       resolvedName = as2ResolveProperty(p.scope, variableName);
  8743       if (resolvedName !== null) {
  8744         return p.scope.asSetPublicProperty(resolvedName, value);
  8747     (_this || scope).asSetPublicProperty(variableName, value);
  8749   function getFunction(functionName) {
  8750     var fn = getVariable(functionName);
  8751     if (!(fn instanceof Function)) {
  8752       throw new Error('Function "' + functionName + '" is not found');
  8754     return fn;
  8756   function getObjectByName(objectName) {
  8757     var obj = getVariable(objectName);
  8758     if (!(obj instanceof Object)) {
  8759       throw new Error('Object "' + objectName + '" is not found');
  8761     return obj;
  8763   function processWith(obj, withBlock) {
  8764     var newScopeContainer = scopeContainer.create(Object(obj));
  8765     interpretActions(withBlock, newScopeContainer, constantPool, registers);
  8767   function processTry(catchIsRegisterFlag, finallyBlockFlag, catchBlockFlag, catchTarget, tryBlock, catchBlock, finallyBlock) {
  8768     var savedTryCatchState = currentContext.isTryCatchListening;
  8769     try {
  8770       currentContext.isTryCatchListening = true;
  8771       interpretActions(tryBlock, scopeContainer, constantPool, registers);
  8772     } catch (e) {
  8773       currentContext.isTryCatchListening = savedTryCatchState;
  8774       if (!catchBlockFlag) {
  8775         throw e;
  8777       if (!(e instanceof AS2Error)) {
  8778         throw e;
  8780       if (typeof catchTarget === 'string') {
  8781         scope[catchTarget] = e.error;
  8782       } else {
  8783         registers[catchTarget] = e.error;
  8785       interpretActions(catchBlock, scopeContainer, constantPool, registers);
  8786     } finally {
  8787       currentContext.isTryCatchListening = savedTryCatchState;
  8788       if (finallyBlockFlag) {
  8789         interpretActions(finallyBlock, scopeContainer, constantPool, registers);
  8793   function validateArgsCount(numArgs, maxAmount) {
  8794     if (isNaN(numArgs) || numArgs < 0 || numArgs > maxAmount || numArgs != (0 | numArgs)) {
  8795       throw new Error('Invalid number of arguments: ' + numArgs);
  8798   function readArgs(stack) {
  8799     var numArgs = +stack.pop();
  8800     validateArgsCount(numArgs, stack.length);
  8801     var args = [];
  8802     for (var i = 0; i < numArgs; i++) {
  8803       args.push(stack.pop());
  8805     return args;
  8807   var stream = new ActionsDataStream(actionsData, currentContext.swfVersion);
  8808   var _global = currentContext.globals;
  8809   var defaultTarget = currentContext.defaultTarget;
  8810   var stack = [];
  8811   var scope = scopeContainer.scope;
  8812   var isSwfVersion5 = currentContext.swfVersion >= 5;
  8813   var actionTracer = ActionTracerFactory.get();
  8814   var nextPosition;
  8815   if (scope.$nativeObject && scope.$nativeObject._deferScriptExecution) {
  8816     currentContext.deferScriptExecution = true;
  8818   function skipActions(count) {
  8819     while (count > 0 && stream.position < stream.end) {
  8820       var actionCode = stream.readUI8();
  8821       var length = actionCode >= 128 ? stream.readUI16() : 0;
  8822       stream.position += length;
  8823       count--;
  8825     nextPosition = stream.position;
  8827   var recoveringFromError = false;
  8828   var stackItemsExpected;
  8829   while (stream.position < stream.end) {
  8830     try {
  8831       var instructionsExecuted = 0;
  8832       var abortExecutionAt = currentContext.abortExecutionAt;
  8833       while (stream.position < stream.end) {
  8834         if (instructionsExecuted++ % 100 === 0 && Date.now() >= abortExecutionAt) {
  8835           throw new AS2CriticalError('long running script -- AVM1 instruction hang timeout');
  8837         var actionCode = stream.readUI8();
  8838         var length = actionCode >= 128 ? stream.readUI16() : 0;
  8839         nextPosition = stream.position + length;
  8840         stackItemsExpected = 0;
  8841         actionTracer.print(stream.position, actionCode, stack);
  8842         var frame, type, count, index, target, method, constr, codeSize, offset;
  8843         var name, variableName, methodName, functionName, targetName;
  8844         var paramName, resolvedName, objectName;
  8845         var value, a, b, c, f, sa, sb, obj, args, fn, result, flags, i;
  8846         var dragParams, register;
  8847         switch (actionCode | 0) {
  8848         case 129:
  8849           frame = stream.readUI16();
  8850           var nextActionCode = stream.readUI8();
  8851           nextPosition++;
  8852           methodName = nextActionCode === 6 ? 'gotoAndPlay' : 'gotoAndStop';
  8853           _global[methodName](frame + 1);
  8854           break;
  8855         case 131:
  8856           var urlString = stream.readString();
  8857           var targetString = stream.readString();
  8858           _global.getURL(urlString, targetString);
  8859           break;
  8860         case 4:
  8861           _global.nextFrame();
  8862           break;
  8863         case 5:
  8864           _global.prevFrame();
  8865           break;
  8866         case 6:
  8867           _global.play();
  8868           break;
  8869         case 7:
  8870           _global.stop();
  8871           break;
  8872         case 8:
  8873           _global.toggleHighQuality();
  8874           break;
  8875         case 9:
  8876           _global.stopAllSounds();
  8877           break;
  8878         case 138:
  8879           frame = stream.readUI16();
  8880           count = stream.readUI8();
  8881           if (!_global.ifFrameLoaded(frame)) {
  8882             skipActions(count);
  8884           break;
  8885         case 139:
  8886           targetName = stream.readString();
  8887           setTarget(targetName);
  8888           break;
  8889         case 140:
  8890           var label = stream.readString();
  8891           _global.gotoLabel(label);
  8892           break;
  8893         case 150:
  8894           while (stream.position < nextPosition) {
  8895             type = stream.readUI8();
  8896             switch (type) {
  8897             case 0:
  8898               value = stream.readString();
  8899               break;
  8900             case 1:
  8901               value = stream.readFloat();
  8902               break;
  8903             case 2:
  8904               value = null;
  8905               break;
  8906             case 3:
  8907               value = void 0;
  8908               break;
  8909             case 4:
  8910               value = registers[stream.readUI8()];
  8911               break;
  8912             case 5:
  8913               value = stream.readBoolean();
  8914               break;
  8915             case 6:
  8916               value = stream.readDouble();
  8917               break;
  8918             case 7:
  8919               value = stream.readInteger();
  8920               break;
  8921             case 8:
  8922               value = constantPool[stream.readUI8()];
  8923               break;
  8924             case 9:
  8925               value = constantPool[stream.readUI16()];
  8926               break;
  8927             default:
  8928               throw new Error('Unknown value type: ' + type);
  8930             stack.push(value);
  8932           break;
  8933         case 23:
  8934           stack.pop();
  8935           break;
  8936         case 10:
  8937           a = as2ToNumber(stack.pop());
  8938           b = as2ToNumber(stack.pop());
  8939           stack.push(a + b);
  8940           break;
  8941         case 11:
  8942           a = as2ToNumber(stack.pop());
  8943           b = as2ToNumber(stack.pop());
  8944           stack.push(b - a);
  8945           break;
  8946         case 12:
  8947           a = as2ToNumber(stack.pop());
  8948           b = as2ToNumber(stack.pop());
  8949           stack.push(a * b);
  8950           break;
  8951         case 13:
  8952           a = as2ToNumber(stack.pop());
  8953           b = as2ToNumber(stack.pop());
  8954           c = b / a;
  8955           stack.push(isSwfVersion5 ? c : isFinite(c) ? c : '#ERROR#');
  8956           break;
  8957         case 14:
  8958           a = as2ToNumber(stack.pop());
  8959           b = as2ToNumber(stack.pop());
  8960           f = a == b;
  8961           stack.push(isSwfVersion5 ? f : f ? 1 : 0);
  8962           break;
  8963         case 15:
  8964           a = as2ToNumber(stack.pop());
  8965           b = as2ToNumber(stack.pop());
  8966           f = b < a;
  8967           stack.push(isSwfVersion5 ? f : f ? 1 : 0);
  8968           break;
  8969         case 16:
  8970           a = as2ToBoolean(stack.pop());
  8971           b = as2ToBoolean(stack.pop());
  8972           f = a && b;
  8973           stack.push(isSwfVersion5 ? f : f ? 1 : 0);
  8974           break;
  8975         case 17:
  8976           a = as2ToBoolean(stack.pop());
  8977           b = as2ToBoolean(stack.pop());
  8978           f = a || b;
  8979           stack.push(isSwfVersion5 ? f : f ? 1 : 0);
  8980           break;
  8981         case 18:
  8982           f = !as2ToBoolean(stack.pop());
  8983           stack.push(isSwfVersion5 ? f : f ? 1 : 0);
  8984           break;
  8985         case 19:
  8986           sa = as2ToString(stack.pop());
  8987           sb = as2ToString(stack.pop());
  8988           f = sa == sb;
  8989           stack.push(isSwfVersion5 ? f : f ? 1 : 0);
  8990           break;
  8991         case 20:
  8992         case 49:
  8993           sa = as2ToString(stack.pop());
  8994           stack.push(_global.length(sa));
  8995           break;
  8996         case 33:
  8997           sa = as2ToString(stack.pop());
  8998           sb = as2ToString(stack.pop());
  8999           stack.push(sb + sa);
  9000           break;
  9001         case 21:
  9002           count = stack.pop();
  9003           index = stack.pop();
  9004           value = as2ToString(stack.pop());
  9005           stack.push(_global.substring(value, index, count));
  9006           break;
  9007         case 53:
  9008           count = stack.pop();
  9009           index = stack.pop();
  9010           value = as2ToString(stack.pop());
  9011           stack.push(_global.mbsubstring(value, index, count));
  9012           break;
  9013         case 41:
  9014           sa = as2ToString(stack.pop());
  9015           sb = as2ToString(stack.pop());
  9016           f = sb < sa;
  9017           stack.push(isSwfVersion5 ? f : f ? 1 : 0);
  9018           break;
  9019         case 24:
  9020           stack.push(_global.int(stack.pop()));
  9021           break;
  9022         case 50:
  9023           stack.push(_global.chr(stack.pop()));
  9024           break;
  9025         case 54:
  9026           stack.push(_global.mbchr(stack.pop()));
  9027           break;
  9028         case 51:
  9029           stack.push(_global.ord(stack.pop()));
  9030           break;
  9031         case 55:
  9032           stack.push(_global.mbord(stack.pop()));
  9033           break;
  9034         case 153:
  9035           offset = stream.readSI16();
  9036           nextPosition += offset;
  9037           break;
  9038         case 157:
  9039           offset = stream.readSI16();
  9040           f = !(!stack.pop());
  9041           if (f) {
  9042             nextPosition += offset;
  9044           break;
  9045         case 158:
  9046           label = stack.pop();
  9047           _global.call(label);
  9048           break;
  9049         case 28:
  9050           variableName = '' + stack.pop();
  9051           stackItemsExpected++;
  9052           stack.push(getVariable(variableName));
  9053           break;
  9054         case 29:
  9055           value = stack.pop();
  9056           variableName = '' + stack.pop();
  9057           setVariable(variableName, value);
  9058           break;
  9059         case 154:
  9060           flags = stream.readUI8();
  9061           target = stack.pop();
  9062           var url = stack.pop();
  9063           var sendVarsMethod;
  9064           if (flags & 1) {
  9065             sendVarsMethod = 'GET';
  9066           } else if (flags & 2) {
  9067             sendVarsMethod = 'POST';
  9069           var loadTargetFlag = flags & 1 << 6;
  9070           if (!loadTargetFlag) {
  9071             _global.getURL(url, target, sendVarsMethod);
  9072             break;
  9074           var loadVariablesFlag = flags & 1 << 7;
  9075           if (loadVariablesFlag) {
  9076             _global.loadVariables(url, target, sendVarsMethod);
  9077           } else {
  9078             _global.loadMovie(url, target, sendVarsMethod);
  9080           break;
  9081         case 159:
  9082           flags = stream.readUI8();
  9083           var gotoParams = [
  9084               stack.pop()
  9085             ];
  9086           if (!(!(flags & 2))) {
  9087             gotoParams.push(stream.readUI16());
  9089           var gotoMethod = !(!(flags & 1)) ? _global.gotoAndPlay : _global.gotoAndStop;
  9090           gotoMethod.apply(_global, gotoParams);
  9091           break;
  9092         case 32:
  9093           target = stack.pop();
  9094           setTarget(target);
  9095           break;
  9096         case 34:
  9097           index = stack.pop();
  9098           target = stack.pop();
  9099           stackItemsExpected++;
  9100           stack.push(_global.getAS2Property(target, index));
  9101           break;
  9102         case 35:
  9103           value = stack.pop();
  9104           index = stack.pop();
  9105           target = stack.pop();
  9106           _global.setAS2Property(target, index, value);
  9107           break;
  9108         case 36:
  9109           var depth = stack.pop();
  9110           target = stack.pop();
  9111           var source = stack.pop();
  9112           _global.duplicateMovieClip(source, target, depth);
  9113           break;
  9114         case 37:
  9115           target = stack.pop();
  9116           _global.removeMovieClip(target);
  9117           break;
  9118         case 39:
  9119           target = stack.pop();
  9120           var lockcenter = stack.pop();
  9121           var constrain = !stack.pop() ? null : {
  9122               y2: stack.pop(),
  9123               x2: stack.pop(),
  9124               y1: stack.pop(),
  9125               x1: stack.pop()
  9126             };
  9127           dragParams = [
  9128             target,
  9129             lockcenter
  9130           ];
  9131           if (constrain) {
  9132             dragParams = dragParams.push(constrain.x1, constrain.y1, constrain.x2, constrain.y2);
  9134           _global.startDrag.apply(_global, dragParams);
  9135           break;
  9136         case 40:
  9137           _global.stopDrag();
  9138           break;
  9139         case 141:
  9140           count = stream.readUI8();
  9141           frame = stack.pop();
  9142           if (!_global.ifFrameLoaded(frame)) {
  9143             skipActions(count);
  9145           break;
  9146         case 38:
  9147           value = stack.pop();
  9148           _global.trace(value);
  9149           break;
  9150         case 52:
  9151           stack.push(_global.getTimer());
  9152           break;
  9153         case 48:
  9154           stack.push(_global.random(stack.pop()));
  9155           break;
  9156         case 61:
  9157           functionName = stack.pop();
  9158           args = readArgs(stack);
  9159           stackItemsExpected++;
  9160           fn = getFunction(functionName);
  9161           result = fn.apply(scope, args);
  9162           stack.push(result);
  9163           break;
  9164         case 82:
  9165           methodName = stack.pop();
  9166           obj = stack.pop();
  9167           args = readArgs(stack);
  9168           stackItemsExpected++;
  9169           if (methodName !== null && methodName !== undefined && methodName !== '') {
  9170             if (obj === null || obj === undefined) {
  9171               throw new Error('Cannot call method ' + methodName + ' of ' + typeof obj);
  9172             } else if (obj !== AS2_SUPER_STUB) {
  9173               target = Object(obj);
  9174             } else {
  9175               target = as2GetPrototype(getVariable('__class').__super);
  9176               obj = getVariable('this');
  9178             resolvedName = as2ResolveProperty(target, methodName);
  9179             if (resolvedName === null) {
  9180               throw new Error('Method ' + methodName + ' is not defined.');
  9182             result = target.asGetPublicProperty(resolvedName).apply(obj, args);
  9183           } else if (obj !== AS2_SUPER_STUB) {
  9184             result = obj.apply(obj, args);
  9185           } else {
  9186             result = getVariable('__class').__super.apply(getVariable('this'), args);
  9188           stack.push(result);
  9189           break;
  9190         case 136:
  9191           count = stream.readUI16();
  9192           constantPool = [];
  9193           for (i = 0; i < count; i++) {
  9194             constantPool.push(stream.readString());
  9196           break;
  9197         case 155:
  9198           functionName = stream.readString();
  9199           count = stream.readUI16();
  9200           args = [];
  9201           for (i = 0; i < count; i++) {
  9202             args.push(stream.readString());
  9204           codeSize = stream.readUI16();
  9205           nextPosition += codeSize;
  9206           fn = defineFunction(functionName, args, null, stream.readBytes(codeSize));
  9207           if (functionName) {
  9208             scope.asSetPublicProperty(functionName, fn);
  9209           } else {
  9210             stack.push(fn);
  9212           break;
  9213         case 60:
  9214           value = stack.pop();
  9215           name = stack.pop();
  9216           scope.asSetPublicProperty(name, value);
  9217           break;
  9218         case 65:
  9219           name = stack.pop();
  9220           scope.asSetPublicProperty(name, undefined);
  9221           break;
  9222         case 58:
  9223           name = stack.pop();
  9224           obj = stack.pop();
  9225           obj.asSetPublicProperty(name, undefined);
  9226           stack.push(obj.asDeleteProperty(undefined, name, 0));
  9227           break;
  9228         case 59:
  9229           name = stack.pop();
  9230           result = deleteProperty(name);
  9231           stack.push(result);
  9232           break;
  9233         case 70:
  9234           objectName = stack.pop();
  9235           stack.push(null);
  9236           obj = getObjectByName(objectName);
  9237           forEachPublicProperty(obj, function (name) {
  9238             stack.push(name);
  9239           });
  9240           break;
  9241         case 73:
  9242           a = stack.pop();
  9243           b = stack.pop();
  9244           stack.push(a == b);
  9245           break;
  9246         case 78:
  9247           name = stack.pop();
  9248           obj = stack.pop();
  9249           if (name === 'prototype') {
  9250             stack.push(as2CreatePrototypeProxy(obj));
  9251           } else {
  9252             resolvedName = as2ResolveProperty(Object(obj), name);
  9253             stack.push(resolvedName === null ? undefined : obj.asGetPublicProperty(resolvedName));
  9255           break;
  9256         case 66:
  9257           obj = readArgs(stack);
  9258           stack.push(obj);
  9259           break;
  9260         case 67:
  9261           count = +stack.pop();
  9262           validateArgsCount(count, stack.length >> 1);
  9263           obj = {};
  9264           for (i = 0; i < count; i++) {
  9265             value = stack.pop();
  9266             name = stack.pop();
  9267             obj.asSetPublicProperty(name, value);
  9269           stack.push(obj);
  9270           break;
  9271         case 83:
  9272           methodName = stack.pop();
  9273           obj = stack.pop();
  9274           args = readArgs(stack);
  9275           stackItemsExpected++;
  9276           if (methodName !== null && methodName !== undefined && methodName !== '') {
  9277             resolvedName = as2ResolveProperty(obj, methodName);
  9278             if (resolvedName === null) {
  9279               throw new Error('Method ' + methodName + ' is not defined.');
  9281             if (obj === null || obj === undefined) {
  9282               throw new Error('Cannot call new using method ' + resolvedName + ' of ' + typeof obj);
  9284             method = obj.asGetPublicProperty(resolvedName);
  9285           } else {
  9286             if (obj === null || obj === undefined) {
  9287               throw new Error('Cannot call new using ' + typeof obj);
  9289             method = obj;
  9291           if (isAvm2Class(obj)) {
  9292             result = construct(obj, args);
  9293           } else {
  9294             result = Object.create(as2GetPrototype(method) || as2GetPrototype(Object));
  9295             method.apply(result, args);
  9297           result.constructor = method;
  9298           stack.push(result);
  9299           break;
  9300         case 64:
  9301           objectName = stack.pop();
  9302           obj = getObjectByName(objectName);
  9303           args = readArgs(stack);
  9304           stackItemsExpected++;
  9305           result = createBuiltinType(obj, args);
  9306           if (typeof result === 'undefined') {
  9307             if (isAvm2Class(obj)) {
  9308               result = construct(obj, args);
  9309             } else {
  9310               result = Object.create(as2GetPrototype(obj) || as2GetPrototype(Object));
  9311               obj.apply(result, args);
  9313             result.constructor = obj;
  9315           stack.push(result);
  9316           break;
  9317         case 79:
  9318           value = stack.pop();
  9319           name = stack.pop();
  9320           obj = stack.pop();
  9321           obj.asSetPublicProperty(name, value);
  9322           break;
  9323         case 69:
  9324           obj = stack.pop();
  9325           stack.push(as2GetType(obj) === 'movieclip' ? obj._target : void 0);
  9326           break;
  9327         case 148:
  9328           codeSize = stream.readUI16();
  9329           obj = stack.pop();
  9330           nextPosition += codeSize;
  9331           processWith(obj, stream.readBytes(codeSize));
  9332           break;
  9333         case 74:
  9334           stack.push(as2ToNumber(stack.pop()));
  9335           break;
  9336         case 75:
  9337           stack.push(as2ToString(stack.pop()));
  9338           break;
  9339         case 68:
  9340           obj = stack.pop();
  9341           result = as2GetType(obj);
  9342           stack.push(result);
  9343           break;
  9344         case 71:
  9345           a = as2ToAddPrimitive(stack.pop());
  9346           b = as2ToAddPrimitive(stack.pop());
  9347           if (typeof a === 'string' || typeof b === 'string') {
  9348             stack.push(as2ToString(b) + as2ToString(a));
  9349           } else {
  9350             stack.push(as2ToNumber(b) + as2ToNumber(a));
  9352           break;
  9353         case 72:
  9354           a = stack.pop();
  9355           b = stack.pop();
  9356           stack.push(as2Compare(b, a));
  9357           break;
  9358         case 63:
  9359           a = as2ToNumber(stack.pop());
  9360           b = as2ToNumber(stack.pop());
  9361           stack.push(b % a);
  9362           break;
  9363         case 96:
  9364           a = as2ToInt32(stack.pop());
  9365           b = as2ToInt32(stack.pop());
  9366           stack.push(b & a);
  9367           break;
  9368         case 99:
  9369           a = as2ToInt32(stack.pop());
  9370           b = as2ToInt32(stack.pop());
  9371           stack.push(b << a);
  9372           break;
  9373         case 97:
  9374           a = as2ToInt32(stack.pop());
  9375           b = as2ToInt32(stack.pop());
  9376           stack.push(b | a);
  9377           break;
  9378         case 100:
  9379           a = as2ToInt32(stack.pop());
  9380           b = as2ToInt32(stack.pop());
  9381           stack.push(b >> a);
  9382           break;
  9383         case 101:
  9384           a = as2ToInt32(stack.pop());
  9385           b = as2ToInt32(stack.pop());
  9386           stack.push(b >>> a);
  9387           break;
  9388         case 98:
  9389           a = as2ToInt32(stack.pop());
  9390           b = as2ToInt32(stack.pop());
  9391           stack.push(b ^ a);
  9392           break;
  9393         case 81:
  9394           a = as2ToNumber(stack.pop());
  9395           a--;
  9396           stack.push(a);
  9397           break;
  9398         case 80:
  9399           a = as2ToNumber(stack.pop());
  9400           a++;
  9401           stack.push(a);
  9402           break;
  9403         case 76:
  9404           stack.push(stack[stack.length - 1]);
  9405           break;
  9406         case 62:
  9407           return stack.pop();
  9408         case 77:
  9409           stack.push(stack.pop(), stack.pop());
  9410           break;
  9411         case 135:
  9412           register = stream.readUI8();
  9413           registers[register] = stack[stack.length - 1];
  9414           break;
  9415         case 84:
  9416           constr = stack.pop();
  9417           obj = stack.pop();
  9418           stack.push(as2InstanceOf(Object(obj), constr));
  9419           break;
  9420         case 85:
  9421           obj = stack.pop();
  9422           stack.push(null);
  9423           forEachPublicProperty(obj, function (name) {
  9424             stack.push(name);
  9425           });
  9426           break;
  9427         case 102:
  9428           a = stack.pop();
  9429           b = stack.pop();
  9430           stack.push(b === a);
  9431           break;
  9432         case 103:
  9433           a = stack.pop();
  9434           b = stack.pop();
  9435           stack.push(as2Compare(a, b));
  9436           break;
  9437         case 104:
  9438           sa = as2ToString(stack.pop());
  9439           sb = as2ToString(stack.pop());
  9440           f = sb > sa;
  9441           stack.push(isSwfVersion5 ? f : f ? 1 : 0);
  9442           break;
  9443         case 142:
  9444           functionName = stream.readString();
  9445           count = stream.readUI16();
  9446           var registerCount = stream.readUI8();
  9447           flags = stream.readUI16();
  9448           var registerAllocation = [];
  9449           args = [];
  9450           for (i = 0; i < count; i++) {
  9451             register = stream.readUI8();
  9452             paramName = stream.readString();
  9453             args.push(paramName);
  9454             if (register) {
  9455               registerAllocation[register] = {
  9456                 type: 'param',
  9457                 name: paramName,
  9458                 index: i
  9459               };
  9462           codeSize = stream.readUI16();
  9463           nextPosition += codeSize;
  9464           var j = 1;
  9465           if (flags & 1) {
  9466             registerAllocation[j++] = {
  9467               type: 'var',
  9468               name: 'this'
  9469             };
  9471           if (flags & 4) {
  9472             registerAllocation[j++] = {
  9473               type: 'var',
  9474               name: 'arguments'
  9475             };
  9477           if (flags & 16) {
  9478             registerAllocation[j++] = {
  9479               type: 'var',
  9480               name: 'super'
  9481             };
  9483           if (flags & 64) {
  9484             registerAllocation[j++] = {
  9485               type: 'var',
  9486               name: '_root'
  9487             };
  9489           if (flags & 128) {
  9490             registerAllocation[j++] = {
  9491               type: 'var',
  9492               name: '_parent'
  9493             };
  9495           if (flags & 256) {
  9496             registerAllocation[j++] = {
  9497               type: 'var',
  9498               name: '_global'
  9499             };
  9501           fn = defineFunction(functionName, args, registerAllocation, stream.readBytes(codeSize));
  9502           if (functionName) {
  9503             scope.asSetPublicProperty(functionName, fn);
  9504           } else {
  9505             stack.push(fn);
  9507           break;
  9508         case 105:
  9509           var constrSuper = stack.pop();
  9510           constr = stack.pop();
  9511           obj = Object.create(constrSuper.traitsPrototype || as2GetPrototype(constrSuper), {
  9512             constructor: {
  9513               value: constr,
  9514               enumerable: false
  9516           });
  9517           constr.__super = constrSuper;
  9518           constr.prototype = obj;
  9519           break;
  9520         case 43:
  9521           obj = stack.pop();
  9522           constr = stack.pop();
  9523           stack.push(as2InstanceOf(obj, constr) ? obj : null);
  9524           break;
  9525         case 44:
  9526           constr = stack.pop();
  9527           count = +stack.pop();
  9528           validateArgsCount(count, stack.length);
  9529           var interfaces = [];
  9530           for (i = 0; i < count; i++) {
  9531             interfaces.push(stack.pop());
  9533           constr.$interfaces = interfaces;
  9534           break;
  9535         case 143:
  9536           flags = stream.readUI8();
  9537           var catchIsRegisterFlag = !(!(flags & 4));
  9538           var finallyBlockFlag = !(!(flags & 2));
  9539           var catchBlockFlag = !(!(flags & 1));
  9540           var trySize = stream.readUI16();
  9541           var catchSize = stream.readUI16();
  9542           var finallySize = stream.readUI16();
  9543           var catchTarget = catchIsRegisterFlag ? stream.readUI8() : stream.readString();
  9544           nextPosition += trySize + catchSize + finallySize;
  9545           processTry(catchIsRegisterFlag, finallyBlockFlag, catchBlockFlag, catchTarget, stream.readBytes(trySize), stream.readBytes(catchSize), stream.readBytes(finallySize));
  9546           break;
  9547         case 42:
  9548           obj = stack.pop();
  9549           throw new AS2Error(obj);
  9550         case 45:
  9551           args = readArgs(stack);
  9552           stackItemsExpected++;
  9553           result = _global.fscommand.apply(null, args);
  9554           stack.push(result);
  9555           break;
  9556         case 137:
  9557           var mode = stream.readUI8();
  9558           break;
  9559         case 0:
  9560           return;
  9561         default:
  9562           throw new Error('Unknown action code: ' + actionCode);
  9564         stream.position = nextPosition;
  9565         recoveringFromError = false;
  9567     } catch (e) {
  9568       if (!AVM1_ERRORS_IGNORED && !currentContext.isTryCatchListening || e instanceof AS2CriticalError) {
  9569         throw e;
  9571       if (e instanceof AS2Error) {
  9572         throw e;
  9574       var AVM1_ERROR_TYPE = 1;
  9575       TelemetryService.reportTelemetry({
  9576         topic: 'error',
  9577         error: AVM1_ERROR_TYPE
  9578       });
  9579       stream.position = nextPosition;
  9580       if (stackItemsExpected > 0) {
  9581         while (stackItemsExpected--) {
  9582           stack.push(undefined);
  9585       if (!recoveringFromError) {
  9586         if (currentContext.errorsIgnored++ >= MAX_AVM1_ERRORS_LIMIT) {
  9587           throw new AS2CriticalError('long running script -- AVM1 errors limit is reached');
  9589         console.error('AVM1 error: ' + e);
  9590         avm2.exceptions.push({
  9591           source: 'avm1',
  9592           message: e.message,
  9593           stack: e.stack
  9594         });
  9595         recoveringFromError = true;
  9600 var ActionTracerFactory = function () {
  9601     var indentation = 0;
  9602     var tracer = {
  9603         print: function (position, actionCode, stack) {
  9604           var stackDump = [];
  9605           for (var q = 0; q < stack.length; q++) {
  9606             var item = stack[q];
  9607             stackDump.push(item && typeof item === 'object' ? '[' + (item.constructor && item.constructor.name ? item.constructor.name : 'Object') + ']' : item);
  9609           var indent = new Array(indentation + 1).join('..');
  9610           console.log('AVM1 trace: ' + indent + position + ': ' + ActionNamesMap[actionCode] + '(' + actionCode.toString(16) + '), ' + 'stack=' + stackDump);
  9611         },
  9612         indent: function () {
  9613           indentation++;
  9614         },
  9615         unindent: function () {
  9616           indentation--;
  9617         },
  9618         message: function (str) {
  9619           console.log('AVM1 trace: ------- ' + str);
  9621       };
  9622     var nullTracer = {
  9623         print: function () {
  9624         },
  9625         indent: function () {
  9626         },
  9627         unindent: function () {
  9628         },
  9629         message: function () {
  9631       };
  9632     function ActionTracerFactory() {
  9634     ActionTracerFactory.get = function () {
  9635       return AVM1_TRACE_ENABLED ? tracer : nullTracer;
  9636     };
  9637     return ActionTracerFactory;
  9638   }();
  9639 var ActionNamesMap = {
  9640     0: 'EOA',
  9641     4: 'ActionNextFrame',
  9642     5: 'ActionPreviousFrame',
  9643     6: 'ActionPlay',
  9644     7: 'ActionStop',
  9645     8: 'ActionToggleQuality',
  9646     9: 'ActionStopSounds',
  9647     10: 'ActionAdd',
  9648     11: 'ActionSubtract',
  9649     12: 'ActionMultiply',
  9650     13: 'ActionDivide',
  9651     14: 'ActionEquals',
  9652     15: 'ActionLess',
  9653     16: 'ActionAnd',
  9654     17: 'ActionOr',
  9655     18: 'ActionNot',
  9656     19: 'ActionStringEquals',
  9657     20: 'ActionStringLength',
  9658     21: 'ActionStringExtract',
  9659     23: 'ActionPop',
  9660     24: 'ActionToInteger',
  9661     28: 'ActionGetVariable',
  9662     29: 'ActionSetVariable',
  9663     32: 'ActionSetTarget2',
  9664     33: 'ActionStringAdd',
  9665     34: 'ActionGetProperty',
  9666     35: 'ActionSetProperty',
  9667     36: 'ActionCloneSprite',
  9668     37: 'ActionRemoveSprite',
  9669     38: 'ActionTrace',
  9670     39: 'ActionStartDrag',
  9671     40: 'ActionEndDrag',
  9672     41: 'ActionStringLess',
  9673     42: 'ActionThrow',
  9674     43: 'ActionCastOp',
  9675     44: 'ActionImplementsOp',
  9676     45: 'ActionFSCommand2',
  9677     48: 'ActionRandomNumber',
  9678     49: 'ActionMBStringLength',
  9679     50: 'ActionCharToAscii',
  9680     51: 'ActionAsciiToChar',
  9681     52: 'ActionGetTime',
  9682     53: 'ActionMBStringExtrac',
  9683     54: 'ActionMBCharToAscii',
  9684     55: 'ActionMBAsciiToChar',
  9685     58: 'ActionDelete',
  9686     59: 'ActionDelete2',
  9687     60: 'ActionDefineLocal',
  9688     61: 'ActionCallFunction',
  9689     62: 'ActionReturn',
  9690     63: 'ActionModulo',
  9691     64: 'ActionNewObject',
  9692     65: 'ActionDefineLocal2',
  9693     66: 'ActionInitArray',
  9694     67: 'ActionInitObject',
  9695     68: 'ActionTypeOf',
  9696     69: 'ActionTargetPath',
  9697     70: 'ActionEnumerate',
  9698     71: 'ActionAdd2',
  9699     72: 'ActionLess2',
  9700     73: 'ActionEquals2',
  9701     74: 'ActionToNumber',
  9702     75: 'ActionToString',
  9703     76: 'ActionPushDuplicate',
  9704     77: 'ActionStackSwap',
  9705     78: 'ActionGetMember',
  9706     79: 'ActionSetMember',
  9707     80: 'ActionIncrement',
  9708     81: 'ActionDecrement',
  9709     82: 'ActionCallMethod',
  9710     83: 'ActionNewMethod',
  9711     84: 'ActionInstanceOf',
  9712     85: 'ActionEnumerate2',
  9713     96: 'ActionBitAnd',
  9714     97: 'ActionBitOr',
  9715     98: 'ActionBitXor',
  9716     99: 'ActionBitLShift',
  9717     100: 'ActionBitRShift',
  9718     101: 'ActionBitURShift',
  9719     102: 'ActionStrictEquals',
  9720     103: 'ActionGreater',
  9721     104: 'ActionStringGreater',
  9722     105: 'ActionExtends',
  9723     129: 'ActionGotoFrame',
  9724     131: 'ActionGetURL',
  9725     135: 'ActionStoreRegister',
  9726     136: 'ActionConstantPool',
  9727     137: 'ActionStrictMode',
  9728     138: 'ActionWaitForFrame',
  9729     139: 'ActionSetTarget',
  9730     140: 'ActionGoToLabel',
  9731     141: 'ActionWaitForFrame2',
  9732     142: 'ActionDefineFunction',
  9733     143: 'ActionTry',
  9734     148: 'ActionWith',
  9735     150: 'ActionPush',
  9736     153: 'ActionJump',
  9737     154: 'ActionGetURL2',
  9738     155: 'ActionDefineFunction',
  9739     157: 'ActionIf',
  9740     158: 'ActionCall',
  9741     159: 'ActionGotoFrame2'
  9742   };
  9743 if (typeof GLOBAL !== 'undefined') {
  9744   GLOBAL.createBuiltinType = createBuiltinType;
  9745   GLOBAL.executeActions = executeActions;
  9746   GLOBAL.AS2Context = AS2Context;
  9748 var jsGlobal = function () {
  9749     return this || (1, eval)('this');
  9750   }();
  9751 var inBrowser = typeof console != 'undefined';
  9752 var release = true;
  9753 var debug = !true;
  9754 if (!jsGlobal.performance) {
  9755   jsGlobal.performance = {};
  9757 if (!jsGlobal.performance.now) {
  9758   jsGlobal.performance.now = dateNow;
  9760 function log(message) {
  9761   var optionalParams = [];
  9762   for (var _i = 0; _i < arguments.length - 1; _i++) {
  9763     optionalParams[_i] = arguments[_i + 1];
  9765   jsGlobal.print(message);
  9767 function warn(message) {
  9768   var optionalParams = [];
  9769   for (var _i = 0; _i < arguments.length - 1; _i++) {
  9770     optionalParams[_i] = arguments[_i + 1];
  9772   if (inBrowser) {
  9773     console.warn(message);
  9774   } else {
  9775     jsGlobal.print(message);
  9778 var Shumway;
  9779 (function (Shumway) {
  9780   (function (CharacterCodes) {
  9781     CharacterCodes[CharacterCodes['_0'] = 48] = '_0';
  9782     CharacterCodes[CharacterCodes['_1'] = 49] = '_1';
  9783     CharacterCodes[CharacterCodes['_2'] = 50] = '_2';
  9784     CharacterCodes[CharacterCodes['_3'] = 51] = '_3';
  9785     CharacterCodes[CharacterCodes['_4'] = 52] = '_4';
  9786     CharacterCodes[CharacterCodes['_5'] = 53] = '_5';
  9787     CharacterCodes[CharacterCodes['_6'] = 54] = '_6';
  9788     CharacterCodes[CharacterCodes['_7'] = 55] = '_7';
  9789     CharacterCodes[CharacterCodes['_8'] = 56] = '_8';
  9790     CharacterCodes[CharacterCodes['_9'] = 57] = '_9';
  9791   }(Shumway.CharacterCodes || (Shumway.CharacterCodes = {})));
  9792   var CharacterCodes = Shumway.CharacterCodes;
  9793   Shumway.UINT32_CHAR_BUFFER_LENGTH = 10;
  9794   Shumway.UINT32_MAX = 4294967295;
  9795   Shumway.UINT32_MAX_DIV_10 = 429496729;
  9796   Shumway.UINT32_MAX_MOD_10 = 5;
  9797   function isString(value) {
  9798     return typeof value === 'string';
  9800   Shumway.isString = isString;
  9801   function isFunction(value) {
  9802     return typeof value === 'function';
  9804   Shumway.isFunction = isFunction;
  9805   function isNumber(value) {
  9806     return typeof value === 'number';
  9808   Shumway.isNumber = isNumber;
  9809   function isNumberOrString(value) {
  9810     return typeof value === 'number' || typeof value === 'string';
  9812   Shumway.isNumberOrString = isNumberOrString;
  9813   function isObject(value) {
  9814     return typeof value === 'object' || typeof value === 'function';
  9816   Shumway.isObject = isObject;
  9817   function toNumber(x) {
  9818     return +x;
  9820   Shumway.toNumber = toNumber;
  9821   function isNumericString(value) {
  9822     return String(Number(value)) === value;
  9824   Shumway.isNumericString = isNumericString;
  9825   function isNumeric(value) {
  9826     if (typeof value === 'number') {
  9827       return true;
  9828     } else if (typeof value === 'string') {
  9829       return isIndex(value) || isNumericString(value);
  9830     } else {
  9831       Debug.notImplemented(typeof value);
  9834   Shumway.isNumeric = isNumeric;
  9835   function isIndex(value) {
  9836     var index = 0;
  9837     if (typeof value === 'number') {
  9838       index = value | 0;
  9839       if (value === index && index >= 0) {
  9840         return true;
  9842       return value >>> 0 === value;
  9844     if (typeof value !== 'string') {
  9845       return false;
  9847     var length = value.length;
  9848     if (length === 0) {
  9849       return false;
  9851     if (value === '0') {
  9852       return true;
  9854     if (length > Shumway.UINT32_CHAR_BUFFER_LENGTH) {
  9855       return false;
  9857     var i = 0;
  9858     index = value.charCodeAt(i++) - 48;
  9859     if (index < 1 || index > 9) {
  9860       return false;
  9862     var oldIndex = 0;
  9863     var c = 0;
  9864     while (i < length) {
  9865       c = value.charCodeAt(i++) - 48;
  9866       if (c < 0 || c > 9) {
  9867         return false;
  9869       oldIndex = index;
  9870       index = 10 * index + c;
  9872     if (oldIndex < Shumway.UINT32_MAX_DIV_10 || oldIndex === Shumway.UINT32_MAX_DIV_10 && c <= Shumway.UINT32_MAX_MOD_10) {
  9873       return true;
  9875     return false;
  9877   Shumway.isIndex = isIndex;
  9878   function isNullOrUndefined(value) {
  9879     return value == undefined;
  9881   Shumway.isNullOrUndefined = isNullOrUndefined;
  9882   (function (Debug) {
  9883     function backtrace() {
  9884       try {
  9885         throw new Error();
  9886       } catch (e) {
  9887         return e.stack ? e.stack.split('\n').slice(2).join('\n') : '';
  9890     Debug.backtrace = backtrace;
  9891     function error(message) {
  9892       if (!inBrowser) {
  9893         warn(Debug.backtrace());
  9895       throw new Error(message);
  9897     Debug.error = error;
  9898     function assert(condition) {
  9899       var args = [];
  9900       for (var _i = 0; _i < arguments.length - 1; _i++) {
  9901         args[_i] = arguments[_i + 1];
  9903       if (condition === '') {
  9904         condition = true;
  9906       if (!condition) {
  9907         var message = Array.prototype.slice.call(arguments);
  9908         message.shift();
  9909         Debug.error(message.join(''));
  9912     Debug.assert = assert;
  9913     function assertNotImplemented(condition, message) {
  9914       if (!condition) {
  9915         Debug.error('NotImplemented: ' + message);
  9918     Debug.assertNotImplemented = assertNotImplemented;
  9919     function warning(message) {
  9920       true;
  9922     Debug.warning = warning;
  9923     function notUsed(message) {
  9924       true;
  9926     Debug.notUsed = notUsed;
  9927     function notImplemented(message) {
  9928       true;
  9930     Debug.notImplemented = notImplemented;
  9931     function somewhatImplemented(message) {
  9932       Debug.warning('somewhatImplemented: ' + message);
  9934     Debug.somewhatImplemented = somewhatImplemented;
  9935     function unexpected(message) {
  9936       Debug.assert(false, 'Unexpected: ' + message);
  9938     Debug.unexpected = unexpected;
  9939   }(Shumway.Debug || (Shumway.Debug = {})));
  9940   var Debug = Shumway.Debug;
  9941   function getTicks() {
  9942     return performance.now();
  9944   Shumway.getTicks = getTicks;
  9945   (function (ArrayUtilities) {
  9946     function popManyInto(src, count, dst) {
  9947       true;
  9948       for (var i = count - 1; i >= 0; i--) {
  9949         dst[i] = src.pop();
  9951       dst.length = count;
  9953     ArrayUtilities.popManyInto = popManyInto;
  9954   }(Shumway.ArrayUtilities || (Shumway.ArrayUtilities = {})));
  9955   var ArrayUtilities = Shumway.ArrayUtilities;
  9956   (function (ObjectUtilities) {
  9957     function boxValue(value) {
  9958       if (Shumway.isNullOrUndefined(value) || Shumway.isObject(value)) {
  9959         return value;
  9961       return Object(value);
  9963     ObjectUtilities.boxValue = boxValue;
  9964     function toKeyValueArray(object) {
  9965       var hasOwnProperty = Object.prototype.hasOwnProperty;
  9966       var array = [];
  9967       for (var k in object) {
  9968         if (hasOwnProperty.call(object, k)) {
  9969           array.push([
  9970             k,
  9971             object[k]
  9972           ]);
  9975       return array;
  9977     ObjectUtilities.toKeyValueArray = toKeyValueArray;
  9978     function hasOwnProperty(object, name) {
  9979       return Object.prototype.hasOwnProperty.call(object, name);
  9981     ObjectUtilities.hasOwnProperty = hasOwnProperty;
  9982     function createEmptyObject() {
  9983       return Object.create(null);
  9985     ObjectUtilities.createEmptyObject = createEmptyObject;
  9986     function createMap() {
  9987       return Object.create(null);
  9989     ObjectUtilities.createMap = createMap;
  9990     function createArrayMap() {
  9991       return [];
  9993     ObjectUtilities.createArrayMap = createArrayMap;
  9994     function defineReadOnlyProperty(object, name, value) {
  9995       Object.defineProperty(object, name, {
  9996         value: value,
  9997         writable: false,
  9998         configurable: true,
  9999         enumerable: false
 10000       });
 10002     ObjectUtilities.defineReadOnlyProperty = defineReadOnlyProperty;
 10003     function getOwnPropertyDescriptors(object) {
 10004       var o = ObjectUtilities.createMap();
 10005       var properties = Object.getOwnPropertyNames(object);
 10006       for (var i = 0; i < properties.length; i++) {
 10007         o[properties[i]] = Object.getOwnPropertyDescriptor(object, properties[i]);
 10009       return o;
 10011     ObjectUtilities.getOwnPropertyDescriptors = getOwnPropertyDescriptors;
 10012     function cloneObject(object) {
 10013       var clone = ObjectUtilities.createEmptyObject();
 10014       for (var property in object) {
 10015         clone[property] = object[property];
 10017       return clone;
 10019     ObjectUtilities.cloneObject = cloneObject;
 10020     function copyProperties(object, template) {
 10021       for (var property in template) {
 10022         object[property] = template[property];
 10025     ObjectUtilities.copyProperties = copyProperties;
 10026     function getLatestGetterOrSetterPropertyDescriptor(object, name) {
 10027       var descriptor = {};
 10028       while (object) {
 10029         var tmp = Object.getOwnPropertyDescriptor(object, name);
 10030         if (tmp) {
 10031           descriptor.get = descriptor.get || tmp.get;
 10032           descriptor.set = descriptor.set || tmp.set;
 10034         if (descriptor.get && descriptor.set) {
 10035           break;
 10037         object = Object.getPrototypeOf(object);
 10039       return descriptor;
 10041     ObjectUtilities.getLatestGetterOrSetterPropertyDescriptor = getLatestGetterOrSetterPropertyDescriptor;
 10042     function defineNonEnumerableGetterOrSetter(obj, name, value, isGetter) {
 10043       var descriptor = ObjectUtilities.getLatestGetterOrSetterPropertyDescriptor(obj, name);
 10044       descriptor.configurable = true;
 10045       descriptor.enumerable = false;
 10046       if (isGetter) {
 10047         descriptor.get = value;
 10048       } else {
 10049         descriptor.set = value;
 10051       Object.defineProperty(obj, name, descriptor);
 10053     ObjectUtilities.defineNonEnumerableGetterOrSetter = defineNonEnumerableGetterOrSetter;
 10054     function defineNonEnumerableGetter(obj, name, getter) {
 10055       Object.defineProperty(obj, name, {
 10056         get: getter,
 10057         configurable: true,
 10058         enumerable: false
 10059       });
 10061     ObjectUtilities.defineNonEnumerableGetter = defineNonEnumerableGetter;
 10062     function defineNonEnumerableSetter(obj, name, setter) {
 10063       Object.defineProperty(obj, name, {
 10064         set: setter,
 10065         configurable: true,
 10066         enumerable: false
 10067       });
 10069     ObjectUtilities.defineNonEnumerableSetter = defineNonEnumerableSetter;
 10070     function defineNonEnumerableProperty(obj, name, value) {
 10071       Object.defineProperty(obj, name, {
 10072         value: value,
 10073         writable: true,
 10074         configurable: true,
 10075         enumerable: false
 10076       });
 10078     ObjectUtilities.defineNonEnumerableProperty = defineNonEnumerableProperty;
 10079     function defineNonEnumerableForwardingProperty(obj, name, otherName) {
 10080       Object.defineProperty(obj, name, {
 10081         get: FunctionUtilities.makeForwardingGetter(otherName),
 10082         set: FunctionUtilities.makeForwardingSetter(otherName),
 10083         writable: true,
 10084         configurable: true,
 10085         enumerable: false
 10086       });
 10088     ObjectUtilities.defineNonEnumerableForwardingProperty = defineNonEnumerableForwardingProperty;
 10089     function defineNewNonEnumerableProperty(obj, name, value) {
 10090       true;
 10091       ObjectUtilities.defineNonEnumerableProperty(obj, name, value);
 10093     ObjectUtilities.defineNewNonEnumerableProperty = defineNewNonEnumerableProperty;
 10094   }(Shumway.ObjectUtilities || (Shumway.ObjectUtilities = {})));
 10095   var ObjectUtilities = Shumway.ObjectUtilities;
 10096   (function (FunctionUtilities) {
 10097     function makeForwardingGetter(target) {
 10098       return new Function('return this["' + target + '"]');
 10100     FunctionUtilities.makeForwardingGetter = makeForwardingGetter;
 10101     function makeForwardingSetter(target) {
 10102       return new Function('value', 'this["' + target + '"] = value;');
 10104     FunctionUtilities.makeForwardingSetter = makeForwardingSetter;
 10105     function bindSafely(fn, object) {
 10106       true;
 10107       var f = fn.bind(object);
 10108       f.boundTo = object;
 10109       return f;
 10111     FunctionUtilities.bindSafely = bindSafely;
 10112   }(Shumway.FunctionUtilities || (Shumway.FunctionUtilities = {})));
 10113   var FunctionUtilities = Shumway.FunctionUtilities;
 10114   (function (StringUtilities) {
 10115     function toSafeString(value) {
 10116       if (typeof value === 'string') {
 10117         return '"' + value + '"';
 10119       if (typeof value === 'number' || typeof value === 'boolean') {
 10120         return String(value);
 10122       return typeof value;
 10124     StringUtilities.toSafeString = toSafeString;
 10125     function toSafeArrayString(array) {
 10126       var str = [];
 10127       for (var i = 0; i < array.length; i++) {
 10128         str.push(toSafeString(array[i]));
 10130       return str.join(', ');
 10132     StringUtilities.toSafeArrayString = toSafeArrayString;
 10133     function utf8decode(str) {
 10134       var bytes = new Uint8Array(str.length * 4);
 10135       var b = 0;
 10136       for (var i = 0, j = str.length; i < j; i++) {
 10137         var code = str.charCodeAt(i);
 10138         if (code <= 127) {
 10139           bytes[b++] = code;
 10140           continue;
 10142         if (55296 <= code && code <= 56319) {
 10143           var codeLow = str.charCodeAt(i + 1);
 10144           if (56320 <= codeLow && codeLow <= 57343) {
 10145             code = ((code & 1023) << 10) + (codeLow & 1023) + 65536;
 10146             ++i;
 10149         if ((code & 4292870144) !== 0) {
 10150           bytes[b++] = 248 | code >>> 24 & 3;
 10151           bytes[b++] = 128 | code >>> 18 & 63;
 10152           bytes[b++] = 128 | code >>> 12 & 63;
 10153           bytes[b++] = 128 | code >>> 6 & 63;
 10154           bytes[b++] = 128 | code & 63;
 10155         } else if ((code & 4294901760) !== 0) {
 10156           bytes[b++] = 240 | code >>> 18 & 7;
 10157           bytes[b++] = 128 | code >>> 12 & 63;
 10158           bytes[b++] = 128 | code >>> 6 & 63;
 10159           bytes[b++] = 128 | code & 63;
 10160         } else if ((code & 4294965248) !== 0) {
 10161           bytes[b++] = 224 | code >>> 12 & 15;
 10162           bytes[b++] = 128 | code >>> 6 & 63;
 10163           bytes[b++] = 128 | code & 63;
 10164         } else {
 10165           bytes[b++] = 192 | code >>> 6 & 31;
 10166           bytes[b++] = 128 | code & 63;
 10169       return bytes.subarray(0, b);
 10171     StringUtilities.utf8decode = utf8decode;
 10172     function utf8encode(bytes) {
 10173       var j = 0, str = '';
 10174       while (j < bytes.length) {
 10175         var b1 = bytes[j++] & 255;
 10176         if (b1 <= 127) {
 10177           str += String.fromCharCode(b1);
 10178         } else {
 10179           var currentPrefix = 192;
 10180           var validBits = 5;
 10181           do {
 10182             var mask = currentPrefix >> 1 | 128;
 10183             if ((b1 & mask) === currentPrefix)
 10184               break;
 10185             currentPrefix = currentPrefix >> 1 | 128;
 10186             --validBits;
 10187           } while (validBits >= 0);
 10188           if (validBits <= 0) {
 10189             str += String.fromCharCode(b1);
 10190             continue;
 10192           var code = b1 & (1 << validBits) - 1;
 10193           var invalid = false;
 10194           for (var i = 5; i >= validBits; --i) {
 10195             var bi = bytes[j++];
 10196             if ((bi & 192) != 128) {
 10197               invalid = true;
 10198               break;
 10200             code = code << 6 | bi & 63;
 10202           if (invalid) {
 10203             for (var k = j - (7 - i); k < j; ++k) {
 10204               str += String.fromCharCode(bytes[k] & 255);
 10206             continue;
 10208           if (code >= 65536) {
 10209             str += String.fromCharCode(code - 65536 >> 10 & 1023 | 55296, code & 1023 | 56320);
 10210           } else {
 10211             str += String.fromCharCode(code);
 10215       return str;
 10217     StringUtilities.utf8encode = utf8encode;
 10218     function base64ArrayBuffer(arrayBuffer) {
 10219       var base64 = '';
 10220       var encodings = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/';
 10221       var bytes = new Uint8Array(arrayBuffer);
 10222       var byteLength = bytes.byteLength;
 10223       var byteRemainder = byteLength % 3;
 10224       var mainLength = byteLength - byteRemainder;
 10225       var a, b, c, d;
 10226       var chunk;
 10227       for (var i = 0; i < mainLength; i = i + 3) {
 10228         chunk = bytes[i] << 16 | bytes[i + 1] << 8 | bytes[i + 2];
 10229         a = (chunk & 16515072) >> 18;
 10230         b = (chunk & 258048) >> 12;
 10231         c = (chunk & 4032) >> 6;
 10232         d = chunk & 63;
 10233         base64 += encodings[a] + encodings[b] + encodings[c] + encodings[d];
 10235       if (byteRemainder == 1) {
 10236         chunk = bytes[mainLength];
 10237         a = (chunk & 252) >> 2;
 10238         b = (chunk & 3) << 4;
 10239         base64 += encodings[a] + encodings[b] + '==';
 10240       } else if (byteRemainder == 2) {
 10241         chunk = bytes[mainLength] << 8 | bytes[mainLength + 1];
 10242         a = (chunk & 64512) >> 10;
 10243         b = (chunk & 1008) >> 4;
 10244         c = (chunk & 15) << 2;
 10245         base64 += encodings[a] + encodings[b] + encodings[c] + '=';
 10247       return base64;
 10249     StringUtilities.base64ArrayBuffer = base64ArrayBuffer;
 10250     function escapeString(str) {
 10251       if (str !== undefined) {
 10252         str = str.replace(/[^\w$]/gi, '$');
 10253         if (/^\d/.test(str)) {
 10254           str = '$' + str;
 10257       return str;
 10259     StringUtilities.escapeString = escapeString;
 10260     function fromCharCodeArray(buffer) {
 10261       var str = '', SLICE = 1024 * 16;
 10262       for (var i = 0; i < buffer.length; i += SLICE) {
 10263         var chunk = Math.min(buffer.length - i, SLICE);
 10264         str += String.fromCharCode.apply(null, buffer.subarray(i, i + chunk));
 10266       return str;
 10268     StringUtilities.fromCharCodeArray = fromCharCodeArray;
 10269     var _encoding = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789$_';
 10270     function variableLengthEncodeInt32(n) {
 10271       var e = _encoding;
 10272       var bitCount = 32 - IntegerUtilities.leadingZeros(n);
 10273       var l = Math.ceil(bitCount / 6);
 10274       var s = e[l];
 10275       for (var i = l - 1; i >= 0; i--) {
 10276         var offset = i * 6;
 10277         s += e[n >> offset & 63];
 10279       true;
 10280       return s;
 10282     StringUtilities.variableLengthEncodeInt32 = variableLengthEncodeInt32;
 10283     function toEncoding(n) {
 10284       return _encoding[n];
 10286     StringUtilities.toEncoding = toEncoding;
 10287     function fromEncoding(s) {
 10288       var c = s.charCodeAt(0);
 10289       var e = 0;
 10290       if (c >= 65 && c <= 90) {
 10291         return c - 65;
 10292       } else if (c >= 97 && c <= 122) {
 10293         return c - 71;
 10294       } else if (c >= 48 && c <= 57) {
 10295         return c + 4;
 10296       } else if (c === 36) {
 10297         return 62;
 10298       } else if (c === 95) {
 10299         return 63;
 10302     StringUtilities.fromEncoding = fromEncoding;
 10303     function variableLengthDecodeInt32(s) {
 10304       var l = StringUtilities.fromEncoding(s[0]);
 10305       var n = 0;
 10306       for (var i = 0; i < l; i++) {
 10307         var offset = (l - i - 1) * 6;
 10308         n |= StringUtilities.fromEncoding(s[1 + i]) << offset;
 10310       return n;
 10312     StringUtilities.variableLengthDecodeInt32 = variableLengthDecodeInt32;
 10313   }(Shumway.StringUtilities || (Shumway.StringUtilities = {})));
 10314   var StringUtilities = Shumway.StringUtilities;
 10315   (function (HashUtilities) {
 10316     var _md5R = new Uint8Array([
 10317         7,
 10318         12,
 10319         17,
 10320         22,
 10321         7,
 10322         12,
 10323         17,
 10324         22,
 10325         7,
 10326         12,
 10327         17,
 10328         22,
 10329         7,
 10330         12,
 10331         17,
 10332         22,
 10333         5,
 10334         9,
 10335         14,
 10336         20,
 10337         5,
 10338         9,
 10339         14,
 10340         20,
 10341         5,
 10342         9,
 10343         14,
 10344         20,
 10345         5,
 10346         9,
 10347         14,
 10348         20,
 10349         4,
 10350         11,
 10351         16,
 10352         23,
 10353         4,
 10354         11,
 10355         16,
 10356         23,
 10357         4,
 10358         11,
 10359         16,
 10360         23,
 10361         4,
 10362         11,
 10363         16,
 10364         23,
 10365         6,
 10366         10,
 10367         15,
 10368         21,
 10369         6,
 10370         10,
 10371         15,
 10372         21,
 10373         6,
 10374         10,
 10375         15,
 10376         21,
 10377         6,
 10378         10,
 10379         15,
 10380         21
 10381       ]);
 10382     var _md5K = new Int32Array([
 10383         -680876936,
 10384         -389564586,
 10385         606105819,
 10386         -1044525330,
 10387         -176418897,
 10388         1200080426,
 10389         -1473231341,
 10390         -45705983,
 10391         1770035416,
 10392         -1958414417,
 10393         -42063,
 10394         -1990404162,
 10395         1804603682,
 10396         -40341101,
 10397         -1502002290,
 10398         1236535329,
 10399         -165796510,
 10400         -1069501632,
 10401         643717713,
 10402         -373897302,
 10403         -701558691,
 10404         38016083,
 10405         -660478335,
 10406         -405537848,
 10407         568446438,
 10408         -1019803690,
 10409         -187363961,
 10410         1163531501,
 10411         -1444681467,
 10412         -51403784,
 10413         1735328473,
 10414         -1926607734,
 10415         -378558,
 10416         -2022574463,
 10417         1839030562,
 10418         -35309556,
 10419         -1530992060,
 10420         1272893353,
 10421         -155497632,
 10422         -1094730640,
 10423         681279174,
 10424         -358537222,
 10425         -722521979,
 10426         76029189,
 10427         -640364487,
 10428         -421815835,
 10429         530742520,
 10430         -995338651,
 10431         -198630844,
 10432         1126891415,
 10433         -1416354905,
 10434         -57434055,
 10435         1700485571,
 10436         -1894986606,
 10437         -1051523,
 10438         -2054922799,
 10439         1873313359,
 10440         -30611744,
 10441         -1560198380,
 10442         1309151649,
 10443         -145523070,
 10444         -1120210379,
 10445         718787259,
 10446         -343485551
 10447       ]);
 10448     function hashBytesTo32BitsMD5(data, offset, length) {
 10449       var r = _md5R;
 10450       var k = _md5K;
 10451       var h0 = 1732584193, h1 = -271733879, h2 = -1732584194, h3 = 271733878;
 10452       var paddedLength = length + 72 & ~63;
 10453       var padded = new Uint8Array(paddedLength);
 10454       var i, j, n;
 10455       for (i = 0; i < length; ++i) {
 10456         padded[i] = data[offset++];
 10458       padded[i++] = 128;
 10459       n = paddedLength - 8;
 10460       while (i < n) {
 10461         padded[i++] = 0;
 10463       padded[i++] = length << 3 & 255;
 10464       padded[i++] = length >> 5 & 255;
 10465       padded[i++] = length >> 13 & 255;
 10466       padded[i++] = length >> 21 & 255;
 10467       padded[i++] = length >>> 29 & 255;
 10468       padded[i++] = 0;
 10469       padded[i++] = 0;
 10470       padded[i++] = 0;
 10471       var w = new Int32Array(16);
 10472       for (i = 0; i < paddedLength;) {
 10473         for (j = 0; j < 16; ++j, i += 4) {
 10474           w[j] = padded[i] | padded[i + 1] << 8 | padded[i + 2] << 16 | padded[i + 3] << 24;
 10476         var a = h0, b = h1, c = h2, d = h3, f, g;
 10477         for (j = 0; j < 64; ++j) {
 10478           if (j < 16) {
 10479             f = b & c | ~b & d;
 10480             g = j;
 10481           } else if (j < 32) {
 10482             f = d & b | ~d & c;
 10483             g = 5 * j + 1 & 15;
 10484           } else if (j < 48) {
 10485             f = b ^ c ^ d;
 10486             g = 3 * j + 5 & 15;
 10487           } else {
 10488             f = c ^ (b | ~d);
 10489             g = 7 * j & 15;
 10491           var tmp = d, rotateArg = a + f + k[j] + w[g] | 0, rotate = r[j];
 10492           d = c;
 10493           c = b;
 10494           b = b + (rotateArg << rotate | rotateArg >>> 32 - rotate) | 0;
 10495           a = tmp;
 10497         h0 = h0 + a | 0;
 10498         h1 = h1 + b | 0;
 10499         h2 = h2 + c | 0;
 10500         h3 = h3 + d | 0;
 10502       return h0;
 10504     HashUtilities.hashBytesTo32BitsMD5 = hashBytesTo32BitsMD5;
 10505     function hashBytesTo32BitsAdler(data, offset, length) {
 10506       var a = 1;
 10507       var b = 0;
 10508       var end = offset + length;
 10509       for (var i = offset; i < end; ++i) {
 10510         a = (a + (data[i] & 255)) % 65521;
 10511         b = (b + a) % 65521;
 10513       return b << 16 | a;
 10515     HashUtilities.hashBytesTo32BitsAdler = hashBytesTo32BitsAdler;
 10516   }(Shumway.HashUtilities || (Shumway.HashUtilities = {})));
 10517   var HashUtilities = Shumway.HashUtilities;
 10518   (function (IntegerUtilities) {
 10519     function bitCount(i) {
 10520       i = i - (i >> 1 & 1431655765);
 10521       i = (i & 858993459) + (i >> 2 & 858993459);
 10522       return (i + (i >> 4) & 252645135) * 16843009 >> 24;
 10524     IntegerUtilities.bitCount = bitCount;
 10525     function ones(i) {
 10526       i = i - (i >> 1 & 1431655765);
 10527       i = (i & 858993459) + (i >> 2 & 858993459);
 10528       return (i + (i >> 4) & 252645135) * 16843009 >> 24;
 10530     IntegerUtilities.ones = ones;
 10531     function leadingZeros(i) {
 10532       i |= i >> 1;
 10533       i |= i >> 2;
 10534       i |= i >> 4;
 10535       i |= i >> 8;
 10536       i |= i >> 16;
 10537       return 32 - IntegerUtilities.ones(i);
 10539     IntegerUtilities.leadingZeros = leadingZeros;
 10540     function trailingZeros(i) {
 10541       return IntegerUtilities.ones((i & -i) - 1);
 10543     IntegerUtilities.trailingZeros = trailingZeros;
 10544     function getFlags(i, flags) {
 10545       var str = '';
 10546       for (var i = 0; i < flags.length; i++) {
 10547         if (i & 1 << i) {
 10548           str += flags[i] + ' ';
 10551       if (str.length === 0) {
 10552         return '';
 10554       return str.trim();
 10556     IntegerUtilities.getFlags = getFlags;
 10557     function isPowerOfTwo(x) {
 10558       return x && (x & x - 1) === 0;
 10560     IntegerUtilities.isPowerOfTwo = isPowerOfTwo;
 10561   }(Shumway.IntegerUtilities || (Shumway.IntegerUtilities = {})));
 10562   var IntegerUtilities = Shumway.IntegerUtilities;
 10563   var IndentingWriter = function () {
 10564       function IndentingWriter(suppressOutput, outFn) {
 10565         if (typeof suppressOutput === 'undefined') {
 10566           suppressOutput = false;
 10568         this._tab = '  ';
 10569         this._padding = '';
 10570         this._suppressOutput = suppressOutput;
 10571         this._out = outFn || IndentingWriter._consoleOutFn;
 10573       IndentingWriter.prototype.writeLn = function (str) {
 10574         if (!this._suppressOutput) {
 10575           this._out(this._padding + str);
 10577       };
 10578       IndentingWriter.prototype.writeLns = function (str) {
 10579         var lines = str.split('\n');
 10580         for (var i = 0; i < lines.length; i++) {
 10581           this.writeLn(lines[i]);
 10583       };
 10584       IndentingWriter.prototype.debugLn = function (str) {
 10585         this.colorLn(IndentingWriter.PURPLE, str);
 10586       };
 10587       IndentingWriter.prototype.yellowLn = function (str) {
 10588         this.colorLn(IndentingWriter.YELLOW, str);
 10589       };
 10590       IndentingWriter.prototype.greenLn = function (str) {
 10591         this.colorLn(IndentingWriter.GREEN, str);
 10592       };
 10593       IndentingWriter.prototype.redLn = function (str) {
 10594         this.colorLn(IndentingWriter.RED, str);
 10595       };
 10596       IndentingWriter.prototype.colorLn = function (color, str) {
 10597         if (!this._suppressOutput) {
 10598           if (!inBrowser) {
 10599             this._out(this._padding + color + str + IndentingWriter.ENDC);
 10600           } else {
 10601             this._out(this._padding + str);
 10604       };
 10605       IndentingWriter.prototype.enter = function (str) {
 10606         if (!this._suppressOutput) {
 10607           this._out(this._padding + str);
 10609         this.indent();
 10610       };
 10611       IndentingWriter.prototype.leaveAndEnter = function (str) {
 10612         this.leave(str);
 10613         this.indent();
 10614       };
 10615       IndentingWriter.prototype.leave = function (str) {
 10616         this.outdent();
 10617         if (!this._suppressOutput) {
 10618           this._out(this._padding + str);
 10620       };
 10621       IndentingWriter.prototype.indent = function () {
 10622         this._padding += this._tab;
 10623       };
 10624       IndentingWriter.prototype.outdent = function () {
 10625         if (this._padding.length > 0) {
 10626           this._padding = this._padding.substring(0, this._padding.length - this._tab.length);
 10628       };
 10629       IndentingWriter.prototype.writeArray = function (arr, detailed, noNumbers) {
 10630         if (typeof detailed === 'undefined') {
 10631           detailed = false;
 10633         if (typeof noNumbers === 'undefined') {
 10634           noNumbers = false;
 10636         detailed = detailed || false;
 10637         for (var i = 0, j = arr.length; i < j; i++) {
 10638           var prefix = '';
 10639           if (detailed) {
 10640             if (arr[i] === null) {
 10641               prefix = 'null';
 10642             } else if (arr[i] === undefined) {
 10643               prefix = 'undefined';
 10644             } else {
 10645               prefix = arr[i].constructor.name;
 10647             prefix += ' ';
 10649           var number = noNumbers ? '' : ('' + i).padRight(' ', 4);
 10650           this.writeLn(number + prefix + arr[i]);
 10652       };
 10653       IndentingWriter.PURPLE = '\x1b[94m';
 10654       IndentingWriter.YELLOW = '\x1b[93m';
 10655       IndentingWriter.GREEN = '\x1b[92m';
 10656       IndentingWriter.RED = '\x1b[91m';
 10657       IndentingWriter.ENDC = '\x1b[0m';
 10658       IndentingWriter._consoleOutFn = inBrowser ? console.info.bind(console) : print;
 10659       return IndentingWriter;
 10660     }();
 10661   Shumway.IndentingWriter = IndentingWriter;
 10662   var SortedListNode = function () {
 10663       function SortedListNode(value, next) {
 10664         this.value = value;
 10665         this.next = next;
 10667       return SortedListNode;
 10668     }();
 10669   var SortedList = function () {
 10670       function SortedList(compare) {
 10671         true;
 10672         this._compare = compare;
 10673         this._head = null;
 10674         this._length = 0;
 10676       SortedList.prototype.push = function (value) {
 10677         true;
 10678         this._length++;
 10679         if (!this._head) {
 10680           this._head = new SortedListNode(value, null);
 10681           return;
 10683         var curr = this._head;
 10684         var prev = null;
 10685         var node = new SortedListNode(value, null);
 10686         var compare = this._compare;
 10687         while (curr) {
 10688           if (compare(curr.value, node.value) > 0) {
 10689             if (prev) {
 10690               node.next = curr;
 10691               prev.next = node;
 10692             } else {
 10693               node.next = this._head;
 10694               this._head = node;
 10696             return;
 10698           prev = curr;
 10699           curr = curr.next;
 10701         prev.next = node;
 10702       };
 10703       SortedList.prototype.forEach = function (visitor) {
 10704         var curr = this._head;
 10705         var last = null;
 10706         while (curr) {
 10707           var result = visitor(curr.value);
 10708           if (result === SortedList.RETURN) {
 10709             return;
 10710           } else if (result === SortedList.DELETE) {
 10711             if (!last) {
 10712               curr = this._head = this._head.next;
 10713             } else {
 10714               curr = last.next = curr.next;
 10716           } else {
 10717             last = curr;
 10718             curr = curr.next;
 10721       };
 10722       SortedList.prototype.isEmpty = function () {
 10723         return !this._head;
 10724       };
 10725       SortedList.prototype.pop = function () {
 10726         if (!this._head) {
 10727           return undefined;
 10729         this._length--;
 10730         var ret = this._head;
 10731         this._head = this._head.next;
 10732         return ret.value;
 10733       };
 10734       SortedList.prototype.contains = function (value) {
 10735         var curr = this._head;
 10736         while (curr) {
 10737           if (curr.value === value) {
 10738             return true;
 10740           curr = curr.next;
 10742         return false;
 10743       };
 10744       SortedList.prototype.toString = function () {
 10745         var str = '[';
 10746         var curr = this._head;
 10747         while (curr) {
 10748           str += curr.value.toString();
 10749           curr = curr.next;
 10750           if (curr) {
 10751             str += ',';
 10754         str += ']';
 10755         return str;
 10756       };
 10757       SortedList.RETURN = 1;
 10758       SortedList.DELETE = 2;
 10759       return SortedList;
 10760     }();
 10761   Shumway.SortedList = SortedList;
 10762   var CIRCULAR_BUFFER_MASK = 4095;
 10763   var CIRCULAR_BUFFER_SIZE = 4096;
 10764   var CircularBuffer = function () {
 10765       function CircularBuffer(Type) {
 10766         this.index = 0;
 10767         this.start = 0;
 10768         this.array = new Type(CIRCULAR_BUFFER_SIZE);
 10770       CircularBuffer.prototype.get = function (i) {
 10771         return this.array[i];
 10772       };
 10773       CircularBuffer.prototype.forEachInReverse = function (visitor) {
 10774         if (this.isEmpty()) {
 10775           return;
 10777         var i = this.index === 0 ? CIRCULAR_BUFFER_SIZE - 1 : this.index - 1;
 10778         while (i !== this.start) {
 10779           if (visitor(this.array[i], i)) {
 10780             break;
 10782           i = i === 0 ? CIRCULAR_BUFFER_SIZE - 1 : i - 1;
 10784       };
 10785       CircularBuffer.prototype.write = function (value) {
 10786         this.array[this.index] = value;
 10787         this.index = this.index + 1 & CIRCULAR_BUFFER_MASK;
 10788         if (this.index === this.start) {
 10789           this.start = this.start + 1 & CIRCULAR_BUFFER_MASK;
 10791       };
 10792       CircularBuffer.prototype.isFull = function () {
 10793         return (this.index + 1 & CIRCULAR_BUFFER_MASK) === this.start;
 10794       };
 10795       CircularBuffer.prototype.isEmpty = function () {
 10796         return this.index === this.start;
 10797       };
 10798       return CircularBuffer;
 10799     }();
 10800   Shumway.CircularBuffer = CircularBuffer;
 10801 }(Shumway || (Shumway = {})));
 10802 var assert = Shumway.Debug.assert;
 10803 var IndentingWriter = Shumway.IndentingWriter;
 10804 var assert = Shumway.Debug.assert;
 10805 var $DEBUG;
 10806 var release = true;
 10807 var c4CoerceNonPrimitiveParameters = false;
 10808 var c4CoerceNonPrimitive = false;
 10809 var c4AsTypeLate = true;
 10810 var error = Shumway.Debug.error;
 10811 var assertNotImplemented = Shumway.Debug.assertNotImplemented;
 10812 var warning = Shumway.Debug.warning;
 10813 var notImplemented = Shumway.Debug.notImplemented;
 10814 var somewhatImplemented = Shumway.Debug.somewhatImplemented;
 10815 var unexpected = Shumway.Debug.unexpected;
 10816 var defineReadOnlyProperty = Shumway.ObjectUtilities.defineReadOnlyProperty;
 10817 var createEmptyObject = Shumway.ObjectUtilities.createEmptyObject;
 10818 var makeForwardingGetter = Shumway.FunctionUtilities.makeForwardingGetter;
 10819 var makeForwardingSetter = Shumway.FunctionUtilities.makeForwardingSetter;
 10820 var bindSafely = Shumway.FunctionUtilities.bindSafely;
 10821 var cloneObject = Shumway.ObjectUtilities.cloneObject;
 10822 var copyProperties = Shumway.ObjectUtilities.copyProperties;
 10823 var toSafeString = Shumway.StringUtilities.toSafeString;
 10824 var toSafeArrayString = Shumway.StringUtilities.toSafeArrayString;
 10825 var getLatestGetterOrSetterPropertyDescriptor = Shumway.ObjectUtilities.getLatestGetterOrSetterPropertyDescriptor;
 10826 var defineNonEnumerableGetterOrSetter = Shumway.ObjectUtilities.defineNonEnumerableGetterOrSetter;
 10827 var defineNonEnumerableGetter = Shumway.ObjectUtilities.defineNonEnumerableGetter;
 10828 var defineNonEnumerableSetter = Shumway.ObjectUtilities.defineNonEnumerableSetter;
 10829 var defineNonEnumerableProperty = Shumway.ObjectUtilities.defineNonEnumerableProperty;
 10830 var defineNonEnumerableForwardingProperty = Shumway.ObjectUtilities.defineNonEnumerableForwardingProperty;
 10831 var defineNewNonEnumerableProperty = Shumway.ObjectUtilities.defineNewNonEnumerableProperty;
 10832 var isNumeric = Shumway.isNumeric;
 10833 var isNullOrUndefined = Shumway.isNullOrUndefined;
 10834 var isPowerOfTwo = Shumway.IntegerUtilities.isPowerOfTwo;
 10835 function time(fn, count) {
 10836   var start = performance.now();
 10837   for (var i = 0; i < count; i++) {
 10838     fn();
 10840   var time = (performance.now() - start) / count;
 10841   console.info('Took: ' + time.toFixed(2) + 'ms.');
 10842   return time;
 10844 function clamp(x, min, max) {
 10845   if (x < min) {
 10846     return min;
 10847   } else if (x > max) {
 10848     return max;
 10850   return x;
 10852 var fromCharCodeArray = Shumway.StringUtilities.fromCharCodeArray;
 10853 function hasOwnProperty(object, name) {
 10854   return Object.prototype.hasOwnProperty.call(object, name);
 10856 var toKeyValueArray = Shumway.ObjectUtilities.toKeyValueArray;
 10857 var boxValue = Shumway.ObjectUtilities.boxValue;
 10858 function isObject(value) {
 10859   return typeof value === 'object' || typeof value === 'function';
 10861 function isString(value) {
 10862   return typeof value === 'string';
 10864 function isFunction(value) {
 10865   return typeof value === 'function';
 10867 function isNumber(value) {
 10868   return typeof value === 'number';
 10870 function toNumber(x) {
 10871   return +x;
 10873 function setBitFlags(flags, flag, value) {
 10874   return value ? flags | flag : flags & ~flag;
 10876 function getBitFlags(flags, flag) {
 10877   return !(!(flags & flag));
 10879 (function () {
 10880   function extendBuiltin(proto, prop, f) {
 10881     if (!proto[prop]) {
 10882       Object.defineProperty(proto, prop, {
 10883         value: f,
 10884         writable: true,
 10885         configurable: true,
 10886         enumerable: false
 10887       });
 10890   var Sp = String.prototype;
 10891   function removeColors(s) {
 10892     return s.replace(/\033\[[0-9]*m/g, '');
 10894   extendBuiltin(Sp, 'padRight', function (c, n) {
 10895     var str = this;
 10896     var length = removeColors(str).length;
 10897     if (!c || length >= n) {
 10898       return str;
 10900     var max = (n - length) / c.length;
 10901     for (var i = 0; i < max; i++) {
 10902       str += c;
 10904     return str;
 10905   });
 10906   extendBuiltin(Sp, 'padLeft', function (c, n) {
 10907     var str = this;
 10908     var length = str.length;
 10909     if (!c || length >= n) {
 10910       return str;
 10912     var max = (n - length) / c.length;
 10913     for (var i = 0; i < max; i++) {
 10914       str = c + str;
 10916     return str;
 10917   });
 10918   extendBuiltin(Sp, 'trim', function () {
 10919     return this.replace(/^\s+|\s+$/g, '');
 10920   });
 10921   extendBuiltin(Sp, 'endsWith', function (str) {
 10922     return this.indexOf(str, this.length - str.length) !== -1;
 10923   });
 10924   var Ap = Array.prototype;
 10925   extendBuiltin(Ap, 'popMany', function (count) {
 10926     true;
 10927     var start = this.length - count;
 10928     var res = this.slice(start, this.length);
 10929     this.splice(start, count);
 10930     return res;
 10931   });
 10932   extendBuiltin(Ap, 'pushMany', function (array) {
 10933     for (var i = 0; i < array.length; i++) {
 10934       this.push(array[i]);
 10936   });
 10937   extendBuiltin(Ap, 'clone', function () {
 10938     return this.slice(0);
 10939   });
 10940   extendBuiltin(Ap, 'first', function () {
 10941     true;
 10942     return this[0];
 10943   });
 10944   extendBuiltin(Ap, 'last', function () {
 10945     true;
 10946     return this[this.length - 1];
 10947   });
 10948   extendBuiltin(Ap, 'peek', function () {
 10949     true;
 10950     return this[this.length - 1];
 10951   });
 10952   extendBuiltin(Ap, 'empty', function () {
 10953     return this.length === 0;
 10954   });
 10955   extendBuiltin(Ap, 'pushUnique', function (v) {
 10956     for (var i = 0, j = this.length; i < j; i++) {
 10957       if (this[i] === v) {
 10958         return;
 10961     this.push(v);
 10962   });
 10963   var uniquesMap;
 10964   if (typeof Map !== 'undefined' && (uniquesMap = new Map()).clear) {
 10965     extendBuiltin(Ap, 'unique', function () {
 10966       var unique = [];
 10967       for (var i = 0; i < this.length; i++) {
 10968         if (uniquesMap.has(this[i])) {
 10969           continue;
 10971         unique.push(this[i]);
 10972         uniquesMap.set(this[i], true);
 10974       uniquesMap.clear();
 10975       return unique;
 10976     });
 10977   } else {
 10978     extendBuiltin(Ap, 'unique', function () {
 10979       var unique = [];
 10980       for (var i = 0; i < this.length; i++) {
 10981         unique.pushUnique(this[i]);
 10983       return unique;
 10984     });
 10986   extendBuiltin(Ap, 'replace', function (x, y) {
 10987     if (x === y) {
 10988       return 0;
 10990     var count = 0;
 10991     for (var i = 0; i < this.length; i++) {
 10992       if (this[i] === x) {
 10993         this[i] = y;
 10994         count++;
 10997     return count;
 10998   });
 10999   extendBuiltin(Ap, 'count', function (x) {
 11000     var count = 0;
 11001     for (var i = 0; i < this.length; i++) {
 11002       if (this[i] === x) {
 11003         count++;
 11006     return count;
 11007   });
 11008   extendBuiltin(Ap, 'notEmpty', function () {
 11009     return this.length > 0;
 11010   });
 11011   extendBuiltin(Ap, 'contains', function (val) {
 11012     return this.indexOf(val) >= 0;
 11013   });
 11014   extendBuiltin(Ap, 'top', function () {
 11015     return this.length && this[this.length - 1];
 11016   });
 11017   extendBuiltin(Ap, 'mapWithIndex', function (fn) {
 11018     var arr = [];
 11019     for (var i = 0; i < this.length; i++) {
 11020       arr.push(fn(this[i], i));
 11022     return arr;
 11023   });
 11024 }());
 11025 var utf8decode = Shumway.StringUtilities.utf8decode;
 11026 var utf8encode = Shumway.StringUtilities.utf8encode;
 11027 var escapeString = Shumway.StringUtilities.escapeString;
 11028 var bitCount = Shumway.IntegerUtilities.bitCount;
 11029 var ones = Shumway.IntegerUtilities.ones;
 11030 var leadingZeros = Shumway.IntegerUtilities.leadingZeros;
 11031 var trailingZeros = Shumway.IntegerUtilities.trailingZeros;
 11032 var getFlags = Shumway.IntegerUtilities.getFlags;
 11033 function BitSetFunctor(length) {
 11034   var ADDRESS_BITS_PER_WORD = 5;
 11035   var BITS_PER_WORD = 1 << ADDRESS_BITS_PER_WORD;
 11036   var BIT_INDEX_MASK = BITS_PER_WORD - 1;
 11037   var SIZE = length + (BITS_PER_WORD - 1) >> ADDRESS_BITS_PER_WORD << ADDRESS_BITS_PER_WORD;
 11038   function BitSet() {
 11039     this.count = 0;
 11040     this.dirty = 0;
 11041     this.size = SIZE;
 11042     this.bits = new Uint32Array(SIZE >> ADDRESS_BITS_PER_WORD);
 11044   function BitSetS() {
 11045     this.count = 0;
 11046     this.dirty = 0;
 11047     this.size = SIZE;
 11048     this.bits = 0;
 11050   var singleword = SIZE >> ADDRESS_BITS_PER_WORD === 1;
 11051   var Ctor = singleword ? BitSetS : BitSet;
 11052   Ctor.ADDRESS_BITS_PER_WORD = ADDRESS_BITS_PER_WORD;
 11053   Ctor.BITS_PER_WORD = BITS_PER_WORD;
 11054   Ctor.BIT_INDEX_MASK = BIT_INDEX_MASK;
 11055   Ctor.singleword = singleword;
 11056   BitSet.prototype = {
 11057     recount: function recount() {
 11058       if (!this.dirty) {
 11059         return;
 11061       var bits = this.bits;
 11062       var c = 0;
 11063       for (var i = 0, j = bits.length; i < j; i++) {
 11064         var v = bits[i];
 11065         v = v - (v >> 1 & 1431655765);
 11066         v = (v & 858993459) + (v >> 2 & 858993459);
 11067         c += (v + (v >> 4) & 252645135) * 16843009 >> 24;
 11069       this.count = c;
 11070       this.dirty = 0;
 11071     },
 11072     set: function set(i) {
 11073       var n = i >> ADDRESS_BITS_PER_WORD;
 11074       var old = this.bits[n];
 11075       var b = old | 1 << (i & BIT_INDEX_MASK);
 11076       this.bits[n] = b;
 11077       this.dirty |= old ^ b;
 11078     },
 11079     setAll: function setAll() {
 11080       var bits = this.bits;
 11081       for (var i = 0, j = bits.length; i < j; i++) {
 11082         bits[i] = 4294967295;
 11084       this.count = this.size;
 11085       this.dirty = 0;
 11086     },
 11087     assign: function assign(set) {
 11088       this.count = set.count;
 11089       this.dirty = set.dirty;
 11090       this.size = set.size;
 11091       for (var i = 0, j = this.bits.length; i < j; i++) {
 11092         this.bits[i] = set.bits[i];
 11094     },
 11095     clear: function clear(i) {
 11096       var n = i >> ADDRESS_BITS_PER_WORD;
 11097       var old = this.bits[n];
 11098       var b = old & ~(1 << (i & BIT_INDEX_MASK));
 11099       this.bits[n] = b;
 11100       this.dirty |= old ^ b;
 11101     },
 11102     get: function get(i) {
 11103       var word = this.bits[i >> ADDRESS_BITS_PER_WORD];
 11104       return (word & 1 << (i & BIT_INDEX_MASK)) !== 0;
 11105     },
 11106     clearAll: function clearAll() {
 11107       var bits = this.bits;
 11108       for (var i = 0, j = bits.length; i < j; i++) {
 11109         bits[i] = 0;
 11111       this.count = 0;
 11112       this.dirty = 0;
 11113     },
 11114     _union: function _union(other) {
 11115       var dirty = this.dirty;
 11116       var bits = this.bits;
 11117       var otherBits = other.bits;
 11118       for (var i = 0, j = bits.length; i < j; i++) {
 11119         var old = bits[i];
 11120         var b = old | otherBits[i];
 11121         bits[i] = b;
 11122         dirty |= old ^ b;
 11124       this.dirty = dirty;
 11125     },
 11126     intersect: function intersect(other) {
 11127       var dirty = this.dirty;
 11128       var bits = this.bits;
 11129       var otherBits = other.bits;
 11130       for (var i = 0, j = bits.length; i < j; i++) {
 11131         var old = bits[i];
 11132         var b = old & otherBits[i];
 11133         bits[i] = b;
 11134         dirty |= old ^ b;
 11136       this.dirty = dirty;
 11137     },
 11138     subtract: function subtract(other) {
 11139       var dirty = this.dirty;
 11140       var bits = this.bits;
 11141       var otherBits = other.bits;
 11142       for (var i = 0, j = bits.length; i < j; i++) {
 11143         var old = bits[i];
 11144         var b = old & ~otherBits[i];
 11145         bits[i] = b;
 11146         dirty |= old ^ b;
 11148       this.dirty = dirty;
 11149     },
 11150     negate: function negate() {
 11151       var dirty = this.dirty;
 11152       var bits = this.bits;
 11153       for (var i = 0, j = bits.length; i < j; i++) {
 11154         var old = bits[i];
 11155         var b = ~old;
 11156         bits[i] = b;
 11157         dirty |= old ^ b;
 11159       this.dirty = dirty;
 11160     },
 11161     forEach: function forEach(fn) {
 11162       true;
 11163       var bits = this.bits;
 11164       for (var i = 0, j = bits.length; i < j; i++) {
 11165         var word = bits[i];
 11166         if (word) {
 11167           for (var k = 0; k < BITS_PER_WORD; k++) {
 11168             if (word & 1 << k) {
 11169               fn(i * BITS_PER_WORD + k);
 11174     },
 11175     toArray: function toArray() {
 11176       var set = [];
 11177       var bits = this.bits;
 11178       for (var i = 0, j = bits.length; i < j; i++) {
 11179         var word = bits[i];
 11180         if (word) {
 11181           for (var k = 0; k < BITS_PER_WORD; k++) {
 11182             if (word & 1 << k) {
 11183               set.push(i * BITS_PER_WORD + k);
 11188       return set;
 11189     },
 11190     equals: function equals(other) {
 11191       if (this.size !== other.size) {
 11192         return false;
 11194       var bits = this.bits;
 11195       var otherBits = other.bits;
 11196       for (var i = 0, j = bits.length; i < j; i++) {
 11197         if (bits[i] !== otherBits[i]) {
 11198           return false;
 11201       return true;
 11202     },
 11203     contains: function contains(other) {
 11204       if (this.size !== other.size) {
 11205         return false;
 11207       var bits = this.bits;
 11208       var otherBits = other.bits;
 11209       for (var i = 0, j = bits.length; i < j; i++) {
 11210         if ((bits[i] | otherBits[i]) !== bits[i]) {
 11211           return false;
 11214       return true;
 11215     },
 11216     toBitString: function toBitString(on, off) {
 11217       on = on || '1';
 11218       off = off || '0';
 11219       var str = '';
 11220       for (var i = 0; i < length; i++) {
 11221         str += this.get(i) ? on : off;
 11223       return str;
 11224     },
 11225     length: length,
 11226     toString: function toString(names) {
 11227       var set = [];
 11228       for (var i = 0; i < length; i++) {
 11229         if (this.get(i)) {
 11230           set.push(names ? names[i] : i);
 11233       return set.join(', ');
 11234     },
 11235     isEmpty: function isEmpty() {
 11236       this.recount();
 11237       return this.count === 0;
 11238     },
 11239     clone: function clone() {
 11240       var set = new BitSet();
 11241       set._union(this);
 11242       return set;
 11244   };
 11245   BitSetS.prototype = {
 11246     recount: function recount() {
 11247       if (!this.dirty) {
 11248         return;
 11250       var c = 0;
 11251       var v = this.bits;
 11252       v = v - (v >> 1 & 1431655765);
 11253       v = (v & 858993459) + (v >> 2 & 858993459);
 11254       c += (v + (v >> 4) & 252645135) * 16843009 >> 24;
 11255       this.count = c;
 11256       this.dirty = 0;
 11257     },
 11258     set: function set(i) {
 11259       var old = this.bits;
 11260       var b = old | 1 << (i & BIT_INDEX_MASK);
 11261       this.bits = b;
 11262       this.dirty |= old ^ b;
 11263     },
 11264     setAll: function setAll() {
 11265       this.bits = 4294967295;
 11266       this.count = this.size;
 11267       this.dirty = 0;
 11268     },
 11269     assign: function assign(set) {
 11270       this.count = set.count;
 11271       this.dirty = set.dirty;
 11272       this.size = set.size;
 11273       this.bits = set.bits;
 11274     },
 11275     clear: function clear(i) {
 11276       var old = this.bits;
 11277       var b = old & ~(1 << (i & BIT_INDEX_MASK));
 11278       this.bits = b;
 11279       this.dirty |= old ^ b;
 11280     },
 11281     get: function get(i) {
 11282       return (this.bits & 1 << (i & BIT_INDEX_MASK)) !== 0;
 11283     },
 11284     clearAll: function clearAll() {
 11285       this.bits = 0;
 11286       this.count = 0;
 11287       this.dirty = 0;
 11288     },
 11289     _union: function _union(other) {
 11290       var old = this.bits;
 11291       var b = old | other.bits;
 11292       this.bits = b;
 11293       this.dirty = old ^ b;
 11294     },
 11295     intersect: function intersect(other) {
 11296       var old = this.bits;
 11297       var b = old & other.bits;
 11298       this.bits = b;
 11299       this.dirty = old ^ b;
 11300     },
 11301     subtract: function subtract(other) {
 11302       var old = this.bits;
 11303       var b = old & ~other.bits;
 11304       this.bits = b;
 11305       this.dirty = old ^ b;
 11306     },
 11307     negate: function negate() {
 11308       var old = this.bits;
 11309       var b = ~old;
 11310       this.bits = b;
 11311       this.dirty = old ^ b;
 11312     },
 11313     forEach: function forEach(fn) {
 11314       true;
 11315       var word = this.bits;
 11316       if (word) {
 11317         for (var k = 0; k < BITS_PER_WORD; k++) {
 11318           if (word & 1 << k) {
 11319             fn(k);
 11323     },
 11324     toArray: function toArray() {
 11325       var set = [];
 11326       var word = this.bits;
 11327       if (word) {
 11328         for (var k = 0; k < BITS_PER_WORD; k++) {
 11329           if (word & 1 << k) {
 11330             set.push(k);
 11334       return set;
 11335     },
 11336     equals: function equals(other) {
 11337       return this.bits === other.bits;
 11338     },
 11339     contains: function contains(other) {
 11340       var bits = this.bits;
 11341       return (bits | other.bits) === bits;
 11342     },
 11343     isEmpty: function isEmpty() {
 11344       this.recount();
 11345       return this.count === 0;
 11346     },
 11347     clone: function clone() {
 11348       var set = new BitSetS();
 11349       set._union(this);
 11350       return set;
 11351     },
 11352     toBitString: BitSet.prototype.toBitString,
 11353     toString: BitSet.prototype.toString,
 11354     length: length
 11355   };
 11356   return Ctor;
 11358 var Map = function () {
 11359     function map() {
 11360       this.elements = {};
 11362     map.prototype.set = function set(k, v) {
 11363       this.elements[k] = v;
 11364     };
 11365     map.prototype.get = function get(k) {
 11366       if (this.has(k)) {
 11367         return this.elements[k];
 11369       return undefined;
 11370     };
 11371     map.prototype.has = function has(k) {
 11372       return Object.prototype.hasOwnProperty.call(this.elements, k);
 11373     };
 11374     map.prototype.remove = function remove(k) {
 11375       if (this.has(k)) {
 11376         delete this.elements[k];
 11378     };
 11379     return map;
 11380   }();
 11381 (function checkWeakMap() {
 11382   if (typeof this.WeakMap === 'function')
 11383     return;
 11384   var id = 0;
 11385   function WeakMap() {
 11386     this.id = '$weakmap' + id++;
 11389   WeakMap.prototype = {
 11390     has: function (obj) {
 11391       return obj.hasOwnProperty(this.id);
 11392     },
 11393     get: function (obj, defaultValue) {
 11394       return obj.hasOwnProperty(this.id) ? obj[this.id] : defaultValue;
 11395     },
 11396     set: function (obj, value) {
 11397       Object.defineProperty(obj, this.id, {
 11398         value: value,
 11399         enumerable: false,
 11400         configurable: true
 11401       });
 11403   };
 11404   this.WeakMap = WeakMap;
 11405 }());
 11406 var Callback = function () {
 11407     function callback() {
 11408       this.queues = {};
 11410     callback.prototype.register = function register(type, callback) {
 11411       var queue = this.queues[type];
 11412       if (queue) {
 11413         if (queue.indexOf(callback) > -1) {
 11414           return;
 11416       } else {
 11417         queue = this.queues[type] = [];
 11419       queue.push(callback);
 11420     };
 11421     callback.prototype.unregister = function unregister(type, callback) {
 11422       var queue = this.queues[type];
 11423       if (!queue) {
 11424         return;
 11426       var i = queue.indexOf(callback);
 11427       if (i !== -1) {
 11428         queue.splice(i, 1);
 11430       if (queue.length === 0) {
 11431         this.queues[type] = null;
 11433     };
 11434     callback.prototype.notify = function notify(type, args) {
 11435       var queue = this.queues[type];
 11436       if (!queue) {
 11437         return;
 11439       queue = queue.slice();
 11440       var args = sliceArguments(arguments, 0);
 11441       for (var i = 0; i < queue.length; i++) {
 11442         if (false) {
 11443           Counter.count('callback(' + type + ').notify');
 11445         var callback = queue[i];
 11446         callback.apply(null, args);
 11448     };
 11449     callback.prototype.notify1 = function notify1(type, value) {
 11450       var queue = this.queues[type];
 11451       if (!queue) {
 11452         return;
 11454       queue = queue.slice();
 11455       for (var i = 0; i < queue.length; i++) {
 11456         if (false) {
 11457           Counter.count('callback(' + type + ').notify1');
 11459         var callback = queue[i];
 11460         callback(type, value);
 11462     };
 11463     return callback;
 11464   }();
 11465 function lazyClass(holder, name, initialize) {
 11466   Object.defineProperty(holder, name, {
 11467     get: function () {
 11468       var start = performance.now();
 11469       var value = initialize();
 11470       print('Initialized Class: ' + name + ' ' + (performance.now() - start).toFixed(4));
 11471       Object.defineProperty(holder, name, {
 11472         value: value,
 11473         writable: true
 11474       });
 11475       return value;
 11476     },
 11477     configurable: true
 11478   });
 11480 var hashBytesTo32BitsAdler = Shumway.HashUtilities.hashBytesTo32BitsAdler;
 11481 var hashBytesTo32BitsMD5 = Shumway.HashUtilities.hashBytesTo32BitsMD5;
 11482 var variableLengthEncodeInt32 = Shumway.StringUtilities.variableLengthEncodeInt32;
 11483 var fromEncoding = Shumway.StringUtilities.fromEncoding;
 11484 var variableLengthDecodeIdentifier = Shumway.StringUtilities.variableLengthDecodeInt32;
 11485 var toEncoding = Shumway.StringUtilities.toEncoding;
 11486 var Shumway;
 11487 (function (Shumway) {
 11488   (function (Options) {
 11489     var Argument = function () {
 11490         function Argument(shortName, longName, type, options) {
 11491           this.shortName = shortName;
 11492           this.longName = longName;
 11493           this.type = type;
 11494           options = options || {};
 11495           this.positional = options.positional;
 11496           this.parseFn = options.parse;
 11497           this.value = options.defaultValue;
 11499         Argument.prototype.parse = function (value) {
 11500           if (this.type === 'boolean') {
 11501             true;
 11502             this.value = value;
 11503           } else if (this.type === 'number') {
 11504             true;
 11505             this.value = parseInt(value, 10);
 11506           } else {
 11507             this.value = value;
 11509           if (this.parseFn) {
 11510             this.parseFn(this.value);
 11512         };
 11513         return Argument;
 11514       }();
 11515     Options.Argument = Argument;
 11516     var ArgumentParser = function () {
 11517         function ArgumentParser() {
 11518           this.args = [];
 11520         ArgumentParser.prototype.addArgument = function (shortName, longName, type, options) {
 11521           var argument = new Argument(shortName, longName, type, options);
 11522           this.args.push(argument);
 11523           return argument;
 11524         };
 11525         ArgumentParser.prototype.addBoundOption = function (option) {
 11526           var options = {
 11527               parse: function (x) {
 11528                 option.value = x;
 11530             };
 11531           this.args.push(new Argument(option.shortName, option.longName, option.type, options));
 11532         };
 11533         ArgumentParser.prototype.addBoundOptionSet = function (optionSet) {
 11534           var self = this;
 11535           optionSet.options.forEach(function (x) {
 11536             if (x instanceof OptionSet) {
 11537               self.addBoundOptionSet(x);
 11538             } else {
 11539               true;
 11540               self.addBoundOption(x);
 11542           });
 11543         };
 11544         ArgumentParser.prototype.getUsage = function () {
 11545           var str = '';
 11546           this.args.forEach(function (x) {
 11547             if (!x.positional) {
 11548               str += '[-' + x.shortName + '|--' + x.longName + (x.type === 'boolean' ? '' : ' ' + x.type[0].toUpperCase()) + ']';
 11549             } else {
 11550               str += x.longName;
 11552             str += ' ';
 11553           });
 11554           return str;
 11555         };
 11556         ArgumentParser.prototype.parse = function (args) {
 11557           var nonPositionalArgumentMap = {};
 11558           var positionalArgumentList = [];
 11559           this.args.forEach(function (x) {
 11560             if (x.positional) {
 11561               positionalArgumentList.push(x);
 11562             } else {
 11563               nonPositionalArgumentMap['-' + x.shortName] = x;
 11564               nonPositionalArgumentMap['--' + x.longName] = x;
 11566           });
 11567           var leftoverArguments = [];
 11568           while (args.length) {
 11569             var argString = args.shift();
 11570             var argument = null, value = argString;
 11571             if (argString == '--') {
 11572               leftoverArguments = leftoverArguments.concat(args);
 11573               break;
 11574             } else if (argString.slice(0, 1) == '-' || argString.slice(0, 2) == '--') {
 11575               argument = nonPositionalArgumentMap[argString];
 11576               true;
 11577               if (!argument) {
 11578                 continue;
 11580               if (argument.type !== 'boolean') {
 11581                 value = args.shift();
 11582                 true;
 11583               } else {
 11584                 value = true;
 11586             } else if (positionalArgumentList.length) {
 11587               argument = positionalArgumentList.shift();
 11588             } else {
 11589               leftoverArguments.push(value);
 11591             if (argument) {
 11592               argument.parse(value);
 11595           true;
 11596           return leftoverArguments;
 11597         };
 11598         return ArgumentParser;
 11599       }();
 11600     Options.ArgumentParser = ArgumentParser;
 11601     var OptionSet = function () {
 11602         function OptionSet(name) {
 11603           this.name = name;
 11604           this.options = [];
 11606         OptionSet.prototype.register = function (option) {
 11607           this.options.push(option);
 11608           return option;
 11609         };
 11610         OptionSet.prototype.trace = function (writer) {
 11611           writer.enter(this.name + ' {');
 11612           this.options.forEach(function (option) {
 11613             option.trace(writer);
 11614           });
 11615           writer.leave('}');
 11616         };
 11617         return OptionSet;
 11618       }();
 11619     Options.OptionSet = OptionSet;
 11620     var Option = function () {
 11621         function Option(shortName, longName, type, defaultValue, description) {
 11622           this.longName = longName;
 11623           this.shortName = shortName;
 11624           this.type = type;
 11625           this.defaultValue = defaultValue;
 11626           this.value = defaultValue;
 11627           this.description = description;
 11629         Option.prototype.parse = function (value) {
 11630           this.value = value;
 11631         };
 11632         Option.prototype.trace = function (writer) {
 11633           writer.writeLn(('-' + this.shortName + '|--' + this.longName).padRight(' ', 30) + ' = ' + this.type + ' ' + this.value + ' [' + this.defaultValue + ']' + ' (' + this.description + ')');
 11634         };
 11635         return Option;
 11636       }();
 11637     Options.Option = Option;
 11638   }(Shumway.Options || (Shumway.Options = {})));
 11639   var Options = Shumway.Options;
 11640 }(Shumway || (Shumway = {})));
 11641 if (typeof exports !== 'undefined') {
 11642   exports['Shumway'] = Shumway;
 11644 var ArgumentParser = Shumway.Options.ArgumentParser;
 11645 var Option = Shumway.Options.Option;
 11646 var OptionSet = Shumway.Options.OptionSet;
 11647 var ArgumentParser = Shumway.Options.ArgumentParser;
 11648 var Option = Shumway.Options.Option;
 11649 var OptionSet = Shumway.Options.OptionSet;
 11650 var Shumway;
 11651 (function (Shumway) {
 11652   (function (Metrics) {
 11653     var Timer = function () {
 11654         function Timer(parent, name) {
 11655           this._parent = parent;
 11656           this._timers = Shumway.ObjectUtilities.createMap();
 11657           this._name = name;
 11658           this._begin = 0;
 11659           this._last = 0;
 11660           this._total = 0;
 11661           this._count = 0;
 11663         Timer.time = function (name, fn) {
 11664           Timer.start(name);
 11665           fn();
 11666           Timer.stop();
 11667         };
 11668         Timer.start = function (name) {
 11669           Timer._top = Timer._top._timers[name] || (Timer._top._timers[name] = new Timer(Timer._top, name));
 11670           Timer._top.start();
 11671           var tmp = Timer._flat._timers[name] || (Timer._flat._timers[name] = new Timer(Timer._flat, name));
 11672           tmp.start();
 11673           Timer._flatStack.push(tmp);
 11674         };
 11675         Timer.stop = function () {
 11676           Timer._top.stop();
 11677           Timer._top = Timer._top._parent;
 11678           Timer._flatStack.pop().stop();
 11679         };
 11680         Timer.stopStart = function (name) {
 11681           Timer.stop();
 11682           Timer.start(name);
 11683         };
 11684         Timer.prototype.start = function () {
 11685           this._begin = Shumway.getTicks();
 11686         };
 11687         Timer.prototype.stop = function () {
 11688           this._last = Shumway.getTicks() - this._begin;
 11689           this._total += this._last;
 11690           this._count += 1;
 11691         };
 11692         Timer.prototype.toJSON = function () {
 11693           return {
 11694             name: this._name,
 11695             total: this._total,
 11696             timers: this._timers
 11697           };
 11698         };
 11699         Timer.prototype.trace = function (writer) {
 11700           writer.enter(this._name + ': ' + this._total.toFixed(2) + ' ms' + ', count: ' + this._count + ', average: ' + (this._total / this._count).toFixed(2) + ' ms');
 11701           for (var name in this._timers) {
 11702             this._timers[name].trace(writer);
 11704           writer.outdent();
 11705         };
 11706         Timer.trace = function (writer) {
 11707           Timer._base.trace(writer);
 11708           Timer._flat.trace(writer);
 11709         };
 11710         Timer._base = new Timer(null, 'Total');
 11711         Timer._top = Timer._base;
 11712         Timer._flat = new Timer(null, 'Flat');
 11713         Timer._flatStack = [];
 11714         return Timer;
 11715       }();
 11716     Metrics.Timer = Timer;
 11717     var Counter = function () {
 11718         function Counter(enabled) {
 11719           this._enabled = enabled;
 11720           this.clear();
 11722         Counter.prototype.setEnabled = function (enabled) {
 11723           this._enabled = enabled;
 11724         };
 11725         Counter.prototype.clear = function () {
 11726           this._counts = Shumway.ObjectUtilities.createMap();
 11727         };
 11728         Counter.prototype.toJSON = function () {
 11729           return {
 11730             counts: this._counts
 11731           };
 11732         };
 11733         Counter.prototype.count = function (name, increment) {
 11734           if (typeof increment === 'undefined') {
 11735             increment = 1;
 11737           if (!this._enabled) {
 11738             return;
 11740           if (this._counts[name] === undefined) {
 11741             this._counts[name] = 0;
 11743           this._counts[name] += increment;
 11744           return this._counts[name];
 11745         };
 11746         Counter.prototype.trace = function (writer) {
 11747           for (var name in this._counts) {
 11748             writer.writeLn(name + ': ' + this._counts[name]);
 11750         };
 11751         Counter.prototype.traceSorted = function (writer) {
 11752           var pairs = [];
 11753           for (var name in this._counts) {
 11754             pairs.push([
 11755               name,
 11756               this._counts[name]
 11757             ]);
 11759           pairs.sort(function (a, b) {
 11760             return b[1] - a[1];
 11761           });
 11762           pairs.forEach(function (pair) {
 11763             writer.writeLn(pair[0] + ': ' + pair[1]);
 11764           });
 11765         };
 11766         return Counter;
 11767       }();
 11768     Metrics.Counter = Counter;
 11769     var Average = function () {
 11770         function Average(max) {
 11771           this._samples = new Float64Array(max);
 11772           this._count = 0;
 11773           this._index = 0;
 11775         Average.prototype.push = function (sample) {
 11776           if (this._count < this._samples.length) {
 11777             this._count++;
 11779           this._index++;
 11780           this._samples[this._index % this._samples.length] = sample;
 11781         };
 11782         Average.prototype.average = function () {
 11783           var sum = 0;
 11784           for (var i = 0; i < this._count; i++) {
 11785             sum += this._samples[i];
 11787           return sum / this._count;
 11788         };
 11789         return Average;
 11790       }();
 11791     Metrics.Average = Average;
 11792   }(Shumway.Metrics || (Shumway.Metrics = {})));
 11793   var Metrics = Shumway.Metrics;
 11794 }(Shumway || (Shumway = {})));
 11795 var Timer = Shumway.Metrics.Timer;
 11796 var Counter = new Shumway.Metrics.Counter(true);
 11797 var Timer = Shumway.Metrics.Timer;
 11798 var Counter = new Shumway.Metrics.Counter(true);
 11799 var FrameCounter = new Shumway.Metrics.Counter(true);
 11800 var systemOptions = new OptionSet('System Options');
 11801 var disassemble = systemOptions.register(new Option('d', 'disassemble', 'boolean', false, 'disassemble'));
 11802 var traceLevel = systemOptions.register(new Option('t', 'traceLevel', 'number', 0, 'trace level'));
 11803 window.print = function (s) {
 11804   console.log(s);
 11805 };
 11806 var CONSTANT_Undefined = 0;
 11807 var CONSTANT_Utf8 = 1;
 11808 var CONSTANT_Float = 2;
 11809 var CONSTANT_Int = 3;
 11810 var CONSTANT_UInt = 4;
 11811 var CONSTANT_PrivateNs = 5;
 11812 var CONSTANT_Double = 6;
 11813 var CONSTANT_QName = 7;
 11814 var CONSTANT_Namespace = 8;
 11815 var CONSTANT_Multiname = 9;
 11816 var CONSTANT_False = 10;
 11817 var CONSTANT_True = 11;
 11818 var CONSTANT_Null = 12;
 11819 var CONSTANT_QNameA = 13;
 11820 var CONSTANT_MultinameA = 14;
 11821 var CONSTANT_RTQName = 15;
 11822 var CONSTANT_RTQNameA = 16;
 11823 var CONSTANT_RTQNameL = 17;
 11824 var CONSTANT_RTQNameLA = 18;
 11825 var CONSTANT_NameL = 19;
 11826 var CONSTANT_NameLA = 20;
 11827 var CONSTANT_NamespaceSet = 21;
 11828 var CONSTANT_PackageNamespace = 22;
 11829 var CONSTANT_PackageInternalNs = 23;
 11830 var CONSTANT_ProtectedNamespace = 24;
 11831 var CONSTANT_ExplicitNamespace = 25;
 11832 var CONSTANT_StaticProtectedNs = 26;
 11833 var CONSTANT_MultinameL = 27;
 11834 var CONSTANT_MultinameLA = 28;
 11835 var CONSTANT_TypeName = 29;
 11836 var CONSTANT_ClassSealed = 1;
 11837 var CONSTANT_ClassFinal = 2;
 11838 var CONSTANT_ClassInterface = 4;
 11839 var CONSTANT_ClassProtectedNs = 8;
 11840 var TRAIT_Slot = 0;
 11841 var TRAIT_Method = 1;
 11842 var TRAIT_Getter = 2;
 11843 var TRAIT_Setter = 3;
 11844 var TRAIT_Class = 4;
 11845 var TRAIT_Function = 5;
 11846 var TRAIT_Const = 6;
 11847 var ATTR_Final = 1;
 11848 var ATTR_Override = 2;
 11849 var ATTR_Metadata = 4;
 11850 var SLOT_var = 0;
 11851 var SLOT_method = 1;
 11852 var SLOT_getter = 2;
 11853 var SLOT_setter = 3;
 11854 var SLOT_class = 4;
 11855 var SLOT_function = 6;
 11856 var METHOD_Arguments = 1;
 11857 var METHOD_Activation = 2;
 11858 var METHOD_Needrest = 4;
 11859 var METHOD_HasOptional = 8;
 11860 var METHOD_IgnoreRest = 16;
 11861 var METHOD_Native = 32;
 11862 var METHOD_Setsdxns = 64;
 11863 var METHOD_HasParamNames = 128;
 11864 var OP_bkpt = 1;
 11865 var OP_nop = 2;
 11866 var OP_throw = 3;
 11867 var OP_getsuper = 4;
 11868 var OP_setsuper = 5;
 11869 var OP_dxns = 6;
 11870 var OP_dxnslate = 7;
 11871 var OP_kill = 8;
 11872 var OP_label = 9;
 11873 var OP_lf32x4 = 10;
 11874 var OP_sf32x4 = 11;
 11875 var OP_ifnlt = 12;
 11876 var OP_ifnle = 13;
 11877 var OP_ifngt = 14;
 11878 var OP_ifnge = 15;
 11879 var OP_jump = 16;
 11880 var OP_iftrue = 17;
 11881 var OP_iffalse = 18;
 11882 var OP_ifeq = 19;
 11883 var OP_ifne = 20;
 11884 var OP_iflt = 21;
 11885 var OP_ifle = 22;
 11886 var OP_ifgt = 23;
 11887 var OP_ifge = 24;
 11888 var OP_ifstricteq = 25;
 11889 var OP_ifstrictne = 26;
 11890 var OP_lookupswitch = 27;
 11891 var OP_pushwith = 28;
 11892 var OP_popscope = 29;
 11893 var OP_nextname = 30;
 11894 var OP_hasnext = 31;
 11895 var OP_pushnull = 32;
 11896 var OP_pushundefined = 33;
 11897 var OP_pushfloat = 34;
 11898 var OP_nextvalue = 35;
 11899 var OP_pushbyte = 36;
 11900 var OP_pushshort = 37;
 11901 var OP_pushtrue = 38;
 11902 var OP_pushfalse = 39;
 11903 var OP_pushnan = 40;
 11904 var OP_pop = 41;
 11905 var OP_dup = 42;
 11906 var OP_swap = 43;
 11907 var OP_pushstring = 44;
 11908 var OP_pushint = 45;
 11909 var OP_pushuint = 46;
 11910 var OP_pushdouble = 47;
 11911 var OP_pushscope = 48;
 11912 var OP_pushnamespace = 49;
 11913 var OP_hasnext2 = 50;
 11914 var OP_li8 = 53;
 11915 var OP_li16 = 54;
 11916 var OP_li32 = 55;
 11917 var OP_lf32 = 56;
 11918 var OP_lf64 = 57;
 11919 var OP_si8 = 58;
 11920 var OP_si16 = 59;
 11921 var OP_si32 = 60;
 11922 var OP_sf32 = 61;
 11923 var OP_sf64 = 62;
 11924 var OP_newfunction = 64;
 11925 var OP_call = 65;
 11926 var OP_construct = 66;
 11927 var OP_callmethod = 67;
 11928 var OP_callstatic = 68;
 11929 var OP_callsuper = 69;
 11930 var OP_callproperty = 70;
 11931 var OP_returnvoid = 71;
 11932 var OP_returnvalue = 72;
 11933 var OP_constructsuper = 73;
 11934 var OP_constructprop = 74;
 11935 var OP_callsuperid = 75;
 11936 var OP_callproplex = 76;
 11937 var OP_callinterface = 77;
 11938 var OP_callsupervoid = 78;
 11939 var OP_callpropvoid = 79;
 11940 var OP_sxi1 = 80;
 11941 var OP_sxi8 = 81;
 11942 var OP_sxi16 = 82;
 11943 var OP_applytype = 83;
 11944 var OP_pushfloat4 = 84;
 11945 var OP_newobject = 85;
 11946 var OP_newarray = 86;
 11947 var OP_newactivation = 87;
 11948 var OP_newclass = 88;
 11949 var OP_getdescendants = 89;
 11950 var OP_newcatch = 90;
 11951 var OP_findpropstrict = 93;
 11952 var OP_findproperty = 94;
 11953 var OP_finddef = 95;
 11954 var OP_getlex = 96;
 11955 var OP_setproperty = 97;
 11956 var OP_getlocal = 98;
 11957 var OP_setlocal = 99;
 11958 var OP_getglobalscope = 100;
 11959 var OP_getscopeobject = 101;
 11960 var OP_getproperty = 102;
 11961 var OP_getouterscope = 103;
 11962 var OP_initproperty = 104;
 11963 var OP_setpropertylate = 105;
 11964 var OP_deleteproperty = 106;
 11965 var OP_deletepropertylate = 107;
 11966 var OP_getslot = 108;
 11967 var OP_setslot = 109;
 11968 var OP_getglobalslot = 110;
 11969 var OP_setglobalslot = 111;
 11970 var OP_convert_s = 112;
 11971 var OP_esc_xelem = 113;
 11972 var OP_esc_xattr = 114;
 11973 var OP_convert_i = 115;
 11974 var OP_convert_u = 116;
 11975 var OP_convert_d = 117;
 11976 var OP_convert_b = 118;
 11977 var OP_convert_o = 119;
 11978 var OP_checkfilter = 120;
 11979 var OP_convert_f = 121;
 11980 var OP_unplus = 122;
 11981 var OP_convert_f4 = 123;
 11982 var OP_coerce = 128;
 11983 var OP_coerce_b = 129;
 11984 var OP_coerce_a = 130;
 11985 var OP_coerce_i = 131;
 11986 var OP_coerce_d = 132;
 11987 var OP_coerce_s = 133;
 11988 var OP_astype = 134;
 11989 var OP_astypelate = 135;
 11990 var OP_coerce_u = 136;
 11991 var OP_coerce_o = 137;
 11992 var OP_negate = 144;
 11993 var OP_increment = 145;
 11994 var OP_inclocal = 146;
 11995 var OP_decrement = 147;
 11996 var OP_declocal = 148;
 11997 var OP_typeof = 149;
 11998 var OP_not = 150;
 11999 var OP_bitnot = 151;
 12000 var OP_add = 160;
 12001 var OP_subtract = 161;
 12002 var OP_multiply = 162;
 12003 var OP_divide = 163;
 12004 var OP_modulo = 164;
 12005 var OP_lshift = 165;
 12006 var OP_rshift = 166;
 12007 var OP_urshift = 167;
 12008 var OP_bitand = 168;
 12009 var OP_bitor = 169;
 12010 var OP_bitxor = 170;
 12011 var OP_equals = 171;
 12012 var OP_strictequals = 172;
 12013 var OP_lessthan = 173;
 12014 var OP_lessequals = 174;
 12015 var OP_greaterthan = 175;
 12016 var OP_greaterequals = 176;
 12017 var OP_instanceof = 177;
 12018 var OP_istype = 178;
 12019 var OP_istypelate = 179;
 12020 var OP_in = 180;
 12021 var OP_increment_i = 192;
 12022 var OP_decrement_i = 193;
 12023 var OP_inclocal_i = 194;
 12024 var OP_declocal_i = 195;
 12025 var OP_negate_i = 196;
 12026 var OP_add_i = 197;
 12027 var OP_subtract_i = 198;
 12028 var OP_multiply_i = 199;
 12029 var OP_getlocal0 = 208;
 12030 var OP_getlocal1 = 209;
 12031 var OP_getlocal2 = 210;
 12032 var OP_getlocal3 = 211;
 12033 var OP_setlocal0 = 212;
 12034 var OP_setlocal1 = 213;
 12035 var OP_setlocal2 = 214;
 12036 var OP_setlocal3 = 215;
 12037 var OP_invalid = 237;
 12038 var OP_debug = 239;
 12039 var OP_debugline = 240;
 12040 var OP_debugfile = 241;
 12041 var OP_bkptline = 242;
 12042 var OP_timestamp = 243;
 12043 var INT_MIN_VALUE = -2147483648;
 12044 var INT_MAX_VALUE = 2147483647;
 12045 var UINT_MIN_VALUE = 0;
 12046 var UINT_MAX_VALUE = 4294967295;
 12047 var SORT_CASEINSENSITIVE = 1;
 12048 var SORT_DESCENDING = 2;
 12049 var SORT_UNIQUESORT = 4;
 12050 var SORT_RETURNINDEXEDARRAY = 8;
 12051 var SORT_NUMERIC = 16;
 12052 var Shumway;
 12053 (function (Shumway) {
 12054   (function (AVM2) {
 12055     AVM2.Errors = {
 12056       CallOfNonFunctionError: {
 12057         code: 1006,
 12058         message: '%1 is not a function.'
 12059       },
 12060       ConvertNullToObjectError: {
 12061         code: 1009,
 12062         message: 'Cannot access a property or method of a null object reference.'
 12063       },
 12064       ConvertUndefinedToObjectError: {
 12065         code: 1010,
 12066         message: 'A term is undefined and has no properties.'
 12067       },
 12068       ClassNotFoundError: {
 12069         code: 1014,
 12070         message: 'Class %1 could not be found.'
 12071       },
 12072       CheckTypeFailedError: {
 12073         code: 1034,
 12074         message: 'Type Coercion failed: cannot convert %1 to %2.'
 12075       },
 12076       WrongArgumentCountError: {
 12077         code: 1063,
 12078         message: 'Argument count mismatch on %1. Expected %2, got %3.'
 12079       },
 12080       XMLMarkupMustBeWellFormed: {
 12081         code: 1088,
 12082         message: 'The markup in the document following the root element must be well-formed.'
 12083       },
 12084       OutOfRangeError: {
 12085         code: 1125,
 12086         message: 'The index %1 is out of range %2.'
 12087       },
 12088       VectorFixedError: {
 12089         code: 1126,
 12090         message: 'Cannot change the length of a fixed Vector.'
 12091       },
 12092       InvalidParamError: {
 12093         code: 2004,
 12094         message: 'One of the parameters is invalid.'
 12095       },
 12096       ParamRangeError: {
 12097         code: 2006,
 12098         message: 'The supplied index is out of bounds.'
 12099       },
 12100       NullPointerError: {
 12101         code: 2007,
 12102         message: 'Parameter %1 must be non-null.'
 12103       },
 12104       InvalidEnumError: {
 12105         code: 2008,
 12106         message: 'Parameter %1 must be one of the accepted values.'
 12107       },
 12108       ArgumentError: {
 12109         code: 2015,
 12110         message: 'Invalid BitmapData.'
 12111       },
 12112       CompressedDataError: {
 12113         code: 2058,
 12114         message: 'There was an error decompressing the data.'
 12115       },
 12116       SocketConnectError: {
 12117         code: 2011,
 12118         message: 'Socket connection failed to %1:%2.'
 12119       },
 12120       CantAddSelfError: {
 12121         code: 2024,
 12122         message: 'An object cannot be added as a child of itself.'
 12123       },
 12124       NotAChildError: {
 12125         code: 2025,
 12126         message: 'The supplied DisplayObject must be a child of the caller.'
 12127       },
 12128       ExternalInterfaceNotAvailableError: {
 12129         code: 2067,
 12130         message: 'The ExternalInterface is not available in this container. ExternalInterface requires Internet Explorer ActiveX, Firefox, Mozilla 1.7.5 and greater, or other browsers that support NPRuntime.'
 12132     };
 12133     function getErrorMessage(index) {
 12134       if (!Shumway.AVM2.Runtime.debuggerMode.value) {
 12135         return 'Error #' + index;
 12137       for (var k in AVM2.Errors) {
 12138         if (AVM2.Errors[k].code == index) {
 12139           return 'Error #' + index + ': ' + AVM2.Errors[k].message;
 12142       return 'Error #' + index + ': (unknown)';
 12144     AVM2.getErrorMessage = getErrorMessage;
 12145     function formatErrorMessage(error) {
 12146       var args = [];
 12147       for (var _i = 0; _i < arguments.length - 1; _i++) {
 12148         args[_i] = arguments[_i + 1];
 12150       var message = error.message;
 12151       Array.prototype.slice.call(arguments, 1).forEach(function (x, i) {
 12152         message = message.replace('%' + (i + 1), x);
 12153       });
 12154       return 'Error #' + error.code + ': ' + message;
 12156     AVM2.formatErrorMessage = formatErrorMessage;
 12157     function translateErrorMessage(error) {
 12158       if (error.type) {
 12159         switch (error.type) {
 12160         case 'undefined_method':
 12161           return formatErrorMessage(AVM2.Errors.CallOfNonFunctionError, 'value');
 12162         default:
 12163           throw Shumway.Debug.notImplemented(error.type);
 12165       } else {
 12166         if (error.message.indexOf('is not a function') >= 0) {
 12167           return formatErrorMessage(AVM2.Errors.CallOfNonFunctionError, 'value');
 12169         return error.message;
 12172     AVM2.translateErrorMessage = translateErrorMessage;
 12173   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 12174   var AVM2 = Shumway.AVM2;
 12175 }(Shumway || (Shumway = {})));
 12176 var Errors = Shumway.AVM2.Errors;
 12177 var getErrorMessage = Shumway.AVM2.getErrorMessage;
 12178 var formatErrorMessage = Shumway.AVM2.formatErrorMessage;
 12179 var translateErrorMessage = Shumway.AVM2.translateErrorMessage;
 12180 var Errors = Shumway.AVM2.Errors;
 12181 var getErrorMessage = Shumway.AVM2.getErrorMessage;
 12182 var formatErrorMessage = Shumway.AVM2.formatErrorMessage;
 12183 var translateErrorMessage = Shumway.AVM2.translateErrorMessage;
 12184 var Shumway;
 12185 (function (Shumway) {
 12186   (function (AVM2) {
 12187     AVM2.opcodeTable = [
 12188       null,
 12190         name: 'bkpt',
 12191         canThrow: false,
 12192         operands: []
 12193       },
 12195         name: 'nop',
 12196         canThrow: false,
 12197         operands: []
 12198       },
 12200         name: 'throw',
 12201         canThrow: true,
 12202         operands: []
 12203       },
 12205         name: 'getsuper',
 12206         canThrow: true,
 12207         operands: [
 12209             name: 'index',
 12210             size: 'u30',
 12211             type: ''
 12214       },
 12216         name: 'setsuper',
 12217         canThrow: true,
 12218         operands: [
 12220             name: 'index',
 12221             size: 'u30',
 12222             type: ''
 12225       },
 12227         name: 'dxns',
 12228         canThrow: true,
 12229         operands: [
 12231             name: 'index',
 12232             size: 'u30',
 12233             type: ''
 12236       },
 12238         name: 'dxnslate',
 12239         canThrow: true,
 12240         operands: []
 12241       },
 12243         name: 'kill',
 12244         canThrow: false,
 12245         operands: [
 12247             name: 'index',
 12248             size: 'u30',
 12249             type: ''
 12252       },
 12254         name: 'label',
 12255         canThrow: false,
 12256         operands: []
 12257       },
 12259         name: 'lf32x4',
 12260         canThrow: true,
 12261         operands: []
 12262       },
 12264         name: 'sf32x4',
 12265         canThrow: true,
 12266         operands: []
 12267       },
 12269         name: 'ifnlt',
 12270         canThrow: true,
 12271         operands: [
 12273             name: 'offset',
 12274             size: 's24',
 12275             type: ''
 12278       },
 12280         name: 'ifnle',
 12281         canThrow: true,
 12282         operands: [
 12284             name: 'offset',
 12285             size: 's24',
 12286             type: ''
 12289       },
 12291         name: 'ifngt',
 12292         canThrow: true,
 12293         operands: [
 12295             name: 'offset',
 12296             size: 's24',
 12297             type: ''
 12300       },
 12302         name: 'ifnge',
 12303         canThrow: true,
 12304         operands: [
 12306             name: 'offset',
 12307             size: 's24',
 12308             type: ''
 12311       },
 12313         name: 'jump',
 12314         canThrow: false,
 12315         operands: [
 12317             name: 'offset',
 12318             size: 's24',
 12319             type: ''
 12322       },
 12324         name: 'iftrue',
 12325         canThrow: false,
 12326         operands: [
 12328             name: 'offset',
 12329             size: 's24',
 12330             type: ''
 12333       },
 12335         name: 'iffalse',
 12336         canThrow: false,
 12337         operands: [
 12339             name: 'offset',
 12340             size: 's24',
 12341             type: ''
 12344       },
 12346         name: 'ifeq',
 12347         canThrow: true,
 12348         operands: [
 12350             name: 'offset',
 12351             size: 's24',
 12352             type: ''
 12355       },
 12357         name: 'ifne',
 12358         canThrow: true,
 12359         operands: [
 12361             name: 'offset',
 12362             size: 's24',
 12363             type: ''
 12366       },
 12368         name: 'iflt',
 12369         canThrow: true,
 12370         operands: [
 12372             name: 'offset',
 12373             size: 's24',
 12374             type: ''
 12377       },
 12379         name: 'ifle',
 12380         canThrow: true,
 12381         operands: [
 12383             name: 'offset',
 12384             size: 's24',
 12385             type: ''
 12388       },
 12390         name: 'ifgt',
 12391         canThrow: true,
 12392         operands: [
 12394             name: 'offset',
 12395             size: 's24',
 12396             type: ''
 12399       },
 12401         name: 'ifge',
 12402         canThrow: true,
 12403         operands: [
 12405             name: 'offset',
 12406             size: 's24',
 12407             type: ''
 12410       },
 12412         name: 'ifstricteq',
 12413         canThrow: false,
 12414         operands: [
 12416             name: 'offset',
 12417             size: 's24',
 12418             type: ''
 12421       },
 12423         name: 'ifstrictne',
 12424         canThrow: false,
 12425         operands: [
 12427             name: 'offset',
 12428             size: 's24',
 12429             type: ''
 12432       },
 12434         name: 'lookupswitch',
 12435         canThrow: false,
 12436         operands: null
 12437       },
 12439         name: 'pushwith',
 12440         canThrow: false,
 12441         operands: []
 12442       },
 12444         name: 'popscope',
 12445         canThrow: false,
 12446         operands: []
 12447       },
 12449         name: 'nextname',
 12450         canThrow: true,
 12451         operands: []
 12452       },
 12454         name: 'hasnext',
 12455         canThrow: true,
 12456         operands: []
 12457       },
 12459         name: 'pushnull',
 12460         canThrow: false,
 12461         operands: []
 12462       },
 12464         name: 'pushundefined',
 12465         canThrow: false,
 12466         operands: []
 12467       },
 12468       null,
 12470         name: 'nextvalue',
 12471         canThrow: true,
 12472         operands: []
 12473       },
 12475         name: 'pushbyte',
 12476         canThrow: false,
 12477         operands: [
 12479             name: 'value',
 12480             size: 's08',
 12481             type: ''
 12484       },
 12486         name: 'pushshort',
 12487         canThrow: false,
 12488         operands: [
 12490             name: 'value',
 12491             size: 's16',
 12492             type: ''
 12495       },
 12497         name: 'pushtrue',
 12498         canThrow: false,
 12499         operands: []
 12500       },
 12502         name: 'pushfalse',
 12503         canThrow: false,
 12504         operands: []
 12505       },
 12507         name: 'pushnan',
 12508         canThrow: false,
 12509         operands: []
 12510       },
 12512         name: 'pop',
 12513         canThrow: false,
 12514         operands: []
 12515       },
 12517         name: 'dup',
 12518         canThrow: false,
 12519         operands: []
 12520       },
 12522         name: 'swap',
 12523         canThrow: false,
 12524         operands: []
 12525       },
 12527         name: 'pushstring',
 12528         canThrow: false,
 12529         operands: [
 12531             name: 'index',
 12532             size: 'u30',
 12533             type: 'S'
 12536       },
 12538         name: 'pushint',
 12539         canThrow: false,
 12540         operands: [
 12542             name: 'index',
 12543             size: 'u30',
 12544             type: 'I'
 12547       },
 12549         name: 'pushuint',
 12550         canThrow: false,
 12551         operands: [
 12553             name: 'index',
 12554             size: 'u30',
 12555             type: 'U'
 12558       },
 12560         name: 'pushdouble',
 12561         canThrow: false,
 12562         operands: [
 12564             name: 'index',
 12565             size: 'u30',
 12566             type: 'D'
 12569       },
 12571         name: 'pushscope',
 12572         canThrow: false,
 12573         operands: []
 12574       },
 12576         name: 'pushnamespace',
 12577         canThrow: false,
 12578         operands: [
 12580             name: 'index',
 12581             size: 'u30',
 12582             type: 'N'
 12585       },
 12587         name: 'hasnext2',
 12588         canThrow: true,
 12589         operands: [
 12591             name: 'object',
 12592             size: 'u30',
 12593             type: ''
 12594           },
 12596             name: 'index',
 12597             size: 'u30',
 12598             type: ''
 12601       },
 12603         name: 'lix8',
 12604         canThrow: true,
 12605         operands: null
 12606       },
 12608         name: 'lix16',
 12609         canThrow: true,
 12610         operands: null
 12611       },
 12613         name: 'li8',
 12614         canThrow: true,
 12615         operands: []
 12616       },
 12618         name: 'li16',
 12619         canThrow: true,
 12620         operands: []
 12621       },
 12623         name: 'li32',
 12624         canThrow: true,
 12625         operands: []
 12626       },
 12628         name: 'lf32',
 12629         canThrow: true,
 12630         operands: []
 12631       },
 12633         name: 'lf64',
 12634         canThrow: true,
 12635         operands: []
 12636       },
 12638         name: 'si8',
 12639         canThrow: true,
 12640         operands: []
 12641       },
 12643         name: 'si16',
 12644         canThrow: true,
 12645         operands: []
 12646       },
 12648         name: 'si32',
 12649         canThrow: true,
 12650         operands: []
 12651       },
 12653         name: 'sf32',
 12654         canThrow: true,
 12655         operands: []
 12656       },
 12658         name: 'sf64',
 12659         canThrow: true,
 12660         operands: []
 12661       },
 12662       null,
 12664         name: 'newfunction',
 12665         canThrow: true,
 12666         operands: [
 12668             name: 'index',
 12669             size: 'u30',
 12670             type: 'MI'
 12673       },
 12675         name: 'call',
 12676         canThrow: true,
 12677         operands: [
 12679             name: 'argCount',
 12680             size: 'u30',
 12681             type: ''
 12684       },
 12686         name: 'construct',
 12687         canThrow: true,
 12688         operands: [
 12690             name: 'argCount',
 12691             size: 'u30',
 12692             type: ''
 12695       },
 12697         name: 'callmethod',
 12698         canThrow: true,
 12699         operands: [
 12701             name: 'index',
 12702             size: 'u30',
 12703             type: ''
 12704           },
 12706             name: 'argCount',
 12707             size: 'u30',
 12708             type: ''
 12711       },
 12713         name: 'callstatic',
 12714         canThrow: true,
 12715         operands: [
 12717             name: 'index',
 12718             size: 'u30',
 12719             type: 'MI'
 12720           },
 12722             name: 'argCount',
 12723             size: 'u30',
 12724             type: ''
 12727       },
 12729         name: 'callsuper',
 12730         canThrow: true,
 12731         operands: [
 12733             name: 'index',
 12734             size: 'u30',
 12735             type: 'M'
 12736           },
 12738             name: 'argCount',
 12739             size: 'u30',
 12740             type: ''
 12743       },
 12745         name: 'callproperty',
 12746         canThrow: true,
 12747         operands: [
 12749             name: 'index',
 12750             size: 'u30',
 12751             type: 'M'
 12752           },
 12754             name: 'argCount',
 12755             size: 'u30',
 12756             type: ''
 12759       },
 12761         name: 'returnvoid',
 12762         canThrow: false,
 12763         operands: []
 12764       },
 12766         name: 'returnvalue',
 12767         canThrow: true,
 12768         operands: []
 12769       },
 12771         name: 'constructsuper',
 12772         canThrow: true,
 12773         operands: [
 12775             name: 'argCount',
 12776             size: 'u30',
 12777             type: ''
 12780       },
 12782         name: 'constructprop',
 12783         canThrow: true,
 12784         operands: [
 12786             name: 'index',
 12787             size: 'u30',
 12788             type: 'M'
 12789           },
 12791             name: 'argCount',
 12792             size: 'u30',
 12793             type: ''
 12796       },
 12798         name: 'callsuperid',
 12799         canThrow: true,
 12800         operands: null
 12801       },
 12803         name: 'callproplex',
 12804         canThrow: true,
 12805         operands: [
 12807             name: 'index',
 12808             size: 'u30',
 12809             type: 'M'
 12810           },
 12812             name: 'argCount',
 12813             size: 'u30',
 12814             type: ''
 12817       },
 12819         name: 'callinterface',
 12820         canThrow: true,
 12821         operands: null
 12822       },
 12824         name: 'callsupervoid',
 12825         canThrow: true,
 12826         operands: [
 12828             name: 'index',
 12829             size: 'u30',
 12830             type: 'M'
 12831           },
 12833             name: 'argCount',
 12834             size: 'u30',
 12835             type: ''
 12838       },
 12840         name: 'callpropvoid',
 12841         canThrow: true,
 12842         operands: [
 12844             name: 'index',
 12845             size: 'u30',
 12846             type: 'M'
 12847           },
 12849             name: 'argCount',
 12850             size: 'u30',
 12851             type: ''
 12854       },
 12856         name: 'sxi1',
 12857         canThrow: false,
 12858         operands: []
 12859       },
 12861         name: 'sxi8',
 12862         canThrow: false,
 12863         operands: []
 12864       },
 12866         name: 'sxi16',
 12867         canThrow: false,
 12868         operands: []
 12869       },
 12871         name: 'applytype',
 12872         canThrow: true,
 12873         operands: [
 12875             name: 'argCount',
 12876             size: 'u30',
 12877             type: ''
 12880       },
 12882         name: 'pushfloat4',
 12883         canThrow: false,
 12884         operands: null
 12885       },
 12887         name: 'newobject',
 12888         canThrow: true,
 12889         operands: [
 12891             name: 'argCount',
 12892             size: 'u30',
 12893             type: ''
 12896       },
 12898         name: 'newarray',
 12899         canThrow: true,
 12900         operands: [
 12902             name: 'argCount',
 12903             size: 'u30',
 12904             type: ''
 12907       },
 12909         name: 'newactivation',
 12910         canThrow: true,
 12911         operands: []
 12912       },
 12914         name: 'newclass',
 12915         canThrow: true,
 12916         operands: [
 12918             name: 'index',
 12919             size: 'u30',
 12920             type: 'CI'
 12923       },
 12925         name: 'getdescendants',
 12926         canThrow: true,
 12927         operands: [
 12929             name: 'index',
 12930             size: 'u30',
 12931             type: 'M'
 12934       },
 12936         name: 'newcatch',
 12937         canThrow: true,
 12938         operands: [
 12940             name: 'index',
 12941             size: 'u30',
 12942             type: 'EI'
 12945       },
 12947         name: 'findpropglobalstrict',
 12948         canThrow: true,
 12949         operands: null
 12950       },
 12952         name: 'findpropglobal',
 12953         canThrow: true,
 12954         operands: null
 12955       },
 12957         name: 'findpropstrict',
 12958         canThrow: true,
 12959         operands: [
 12961             name: 'index',
 12962             size: 'u30',
 12963             type: 'M'
 12966       },
 12968         name: 'findproperty',
 12969         canThrow: true,
 12970         operands: [
 12972             name: 'index',
 12973             size: 'u30',
 12974             type: 'M'
 12977       },
 12979         name: 'finddef',
 12980         canThrow: true,
 12981         operands: null
 12982       },
 12984         name: 'getlex',
 12985         canThrow: true,
 12986         operands: [
 12988             name: 'index',
 12989             size: 'u30',
 12990             type: 'M'
 12993       },
 12995         name: 'setproperty',
 12996         canThrow: true,
 12997         operands: [
 12999             name: 'index',
 13000             size: 'u30',
 13001             type: 'M'
 13004       },
 13006         name: 'getlocal',
 13007         canThrow: false,
 13008         operands: [
 13010             name: 'index',
 13011             size: 'u30',
 13012             type: ''
 13015       },
 13017         name: 'setlocal',
 13018         canThrow: false,
 13019         operands: [
 13021             name: 'index',
 13022             size: 'u30',
 13023             type: ''
 13026       },
 13028         name: 'getglobalscope',
 13029         canThrow: false,
 13030         operands: []
 13031       },
 13033         name: 'getscopeobject',
 13034         canThrow: false,
 13035         operands: [
 13037             name: 'index',
 13038             size: 'u30',
 13039             type: ''
 13042       },
 13044         name: 'getproperty',
 13045         canThrow: true,
 13046         operands: [
 13048             name: 'index',
 13049             size: 'u30',
 13050             type: 'M'
 13053       },
 13055         name: 'getouterscope',
 13056         canThrow: false,
 13057         operands: null
 13058       },
 13060         name: 'initproperty',
 13061         canThrow: true,
 13062         operands: [
 13064             name: 'index',
 13065             size: 'u30',
 13066             type: 'M'
 13069       },
 13070       null,
 13072         name: 'deleteproperty',
 13073         canThrow: true,
 13074         operands: [
 13076             name: 'index',
 13077             size: 'u30',
 13078             type: 'M'
 13081       },
 13082       null,
 13084         name: 'getslot',
 13085         canThrow: true,
 13086         operands: [
 13088             name: 'index',
 13089             size: 'u30',
 13090             type: ''
 13093       },
 13095         name: 'setslot',
 13096         canThrow: true,
 13097         operands: [
 13099             name: 'index',
 13100             size: 'u30',
 13101             type: ''
 13104       },
 13106         name: 'getglobalslot',
 13107         canThrow: false,
 13108         operands: [
 13110             name: 'index',
 13111             size: 'u30',
 13112             type: ''
 13115       },
 13117         name: 'setglobalslot',
 13118         canThrow: false,
 13119         operands: [
 13121             name: 'index',
 13122             size: 'u30',
 13123             type: ''
 13126       },
 13128         name: 'convert_s',
 13129         canThrow: true,
 13130         operands: []
 13131       },
 13133         name: 'esc_xelem',
 13134         canThrow: true,
 13135         operands: []
 13136       },
 13138         name: 'esc_xattr',
 13139         canThrow: true,
 13140         operands: []
 13141       },
 13143         name: 'convert_i',
 13144         canThrow: true,
 13145         operands: []
 13146       },
 13148         name: 'convert_u',
 13149         canThrow: true,
 13150         operands: []
 13151       },
 13153         name: 'convert_d',
 13154         canThrow: true,
 13155         operands: []
 13156       },
 13158         name: 'convert_b',
 13159         canThrow: true,
 13160         operands: []
 13161       },
 13163         name: 'convert_o',
 13164         canThrow: true,
 13165         operands: []
 13166       },
 13168         name: 'checkfilter',
 13169         canThrow: true,
 13170         operands: []
 13171       },
 13173         name: 'convert_f',
 13174         canThrow: true,
 13175         operands: []
 13176       },
 13178         name: 'unplus',
 13179         canThrow: true,
 13180         operands: []
 13181       },
 13183         name: 'convert_f4',
 13184         canThrow: true,
 13185         operands: []
 13186       },
 13187       null,
 13188       null,
 13189       null,
 13190       null,
 13192         name: 'coerce',
 13193         canThrow: true,
 13194         operands: [
 13196             name: 'index',
 13197             size: 'u30',
 13198             type: 'M'
 13201       },
 13203         name: 'coerce_b',
 13204         canThrow: true,
 13205         operands: []
 13206       },
 13208         name: 'coerce_a',
 13209         canThrow: true,
 13210         operands: []
 13211       },
 13213         name: 'coerce_i',
 13214         canThrow: true,
 13215         operands: []
 13216       },
 13218         name: 'coerce_d',
 13219         canThrow: true,
 13220         operands: []
 13221       },
 13223         name: 'coerce_s',
 13224         canThrow: true,
 13225         operands: []
 13226       },
 13228         name: 'astype',
 13229         canThrow: true,
 13230         operands: [
 13232             name: 'index',
 13233             size: 'u30',
 13234             type: 'M'
 13237       },
 13239         name: 'astypelate',
 13240         canThrow: true,
 13241         operands: []
 13242       },
 13244         name: 'coerce_u',
 13245         canThrow: true,
 13246         operands: []
 13247       },
 13249         name: 'coerce_o',
 13250         canThrow: true,
 13251         operands: []
 13252       },
 13253       null,
 13254       null,
 13255       null,
 13256       null,
 13257       null,
 13258       null,
 13260         name: 'negate',
 13261         canThrow: true,
 13262         operands: []
 13263       },
 13265         name: 'increment',
 13266         canThrow: true,
 13267         operands: []
 13268       },
 13270         name: 'inclocal',
 13271         canThrow: true,
 13272         operands: [
 13274             name: 'index',
 13275             size: 'u30',
 13276             type: ''
 13279       },
 13281         name: 'decrement',
 13282         canThrow: true,
 13283         operands: []
 13284       },
 13286         name: 'declocal',
 13287         canThrow: true,
 13288         operands: [
 13290             name: 'index',
 13291             size: 'u30',
 13292             type: ''
 13295       },
 13297         name: 'typeof',
 13298         canThrow: false,
 13299         operands: []
 13300       },
 13302         name: 'not',
 13303         canThrow: false,
 13304         operands: []
 13305       },
 13307         name: 'bitnot',
 13308         canThrow: true,
 13309         operands: []
 13310       },
 13311       null,
 13312       null,
 13313       null,
 13314       null,
 13315       null,
 13316       null,
 13317       null,
 13318       null,
 13320         name: 'add',
 13321         canThrow: true,
 13322         operands: []
 13323       },
 13325         name: 'subtract',
 13326         canThrow: true,
 13327         operands: []
 13328       },
 13330         name: 'multiply',
 13331         canThrow: true,
 13332         operands: []
 13333       },
 13335         name: 'divide',
 13336         canThrow: true,
 13337         operands: []
 13338       },
 13340         name: 'modulo',
 13341         canThrow: true,
 13342         operands: []
 13343       },
 13345         name: 'lshift',
 13346         canThrow: true,
 13347         operands: []
 13348       },
 13350         name: 'rshift',
 13351         canThrow: true,
 13352         operands: []
 13353       },
 13355         name: 'urshift',
 13356         canThrow: true,
 13357         operands: []
 13358       },
 13360         name: 'bitand',
 13361         canThrow: true,
 13362         operands: []
 13363       },
 13365         name: 'bitor',
 13366         canThrow: true,
 13367         operands: []
 13368       },
 13370         name: 'bitxor',
 13371         canThrow: true,
 13372         operands: []
 13373       },
 13375         name: 'equals',
 13376         canThrow: true,
 13377         operands: []
 13378       },
 13380         name: 'strictequals',
 13381         canThrow: true,
 13382         operands: []
 13383       },
 13385         name: 'lessthan',
 13386         canThrow: true,
 13387         operands: []
 13388       },
 13390         name: 'lessequals',
 13391         canThrow: true,
 13392         operands: []
 13393       },
 13395         name: 'greaterthan',
 13396         canThrow: true,
 13397         operands: []
 13398       },
 13400         name: 'greaterequals',
 13401         canThrow: true,
 13402         operands: []
 13403       },
 13405         name: 'instanceof',
 13406         canThrow: true,
 13407         operands: []
 13408       },
 13410         name: 'istype',
 13411         canThrow: true,
 13412         operands: [
 13414             name: 'index',
 13415             size: 'u30',
 13416             type: 'M'
 13419       },
 13421         name: 'istypelate',
 13422         canThrow: true,
 13423         operands: []
 13424       },
 13426         name: 'in',
 13427         canThrow: true,
 13428         operands: []
 13429       },
 13430       null,
 13431       null,
 13432       null,
 13433       null,
 13434       null,
 13435       null,
 13436       null,
 13437       null,
 13438       null,
 13439       null,
 13440       null,
 13442         name: 'increment_i',
 13443         canThrow: true,
 13444         operands: []
 13445       },
 13447         name: 'decrement_i',
 13448         canThrow: true,
 13449         operands: []
 13450       },
 13452         name: 'inclocal_i',
 13453         canThrow: true,
 13454         operands: [
 13456             name: 'index',
 13457             size: 'u30',
 13458             type: ''
 13461       },
 13463         name: 'declocal_i',
 13464         canThrow: true,
 13465         operands: [
 13467             name: 'index',
 13468             size: 'u30',
 13469             type: ''
 13472       },
 13474         name: 'negate_i',
 13475         canThrow: true,
 13476         operands: []
 13477       },
 13479         name: 'add_i',
 13480         canThrow: true,
 13481         operands: []
 13482       },
 13484         name: 'subtract_i',
 13485         canThrow: true,
 13486         operands: []
 13487       },
 13489         name: 'multiply_i',
 13490         canThrow: true,
 13491         operands: []
 13492       },
 13493       null,
 13494       null,
 13495       null,
 13496       null,
 13497       null,
 13498       null,
 13499       null,
 13500       null,
 13502         name: 'getlocal0',
 13503         canThrow: false,
 13504         operands: []
 13505       },
 13507         name: 'getlocal1',
 13508         canThrow: false,
 13509         operands: []
 13510       },
 13512         name: 'getlocal2',
 13513         canThrow: false,
 13514         operands: []
 13515       },
 13517         name: 'getlocal3',
 13518         canThrow: false,
 13519         operands: []
 13520       },
 13522         name: 'setlocal0',
 13523         canThrow: false,
 13524         operands: []
 13525       },
 13527         name: 'setlocal1',
 13528         canThrow: false,
 13529         operands: []
 13530       },
 13532         name: 'setlocal2',
 13533         canThrow: false,
 13534         operands: []
 13535       },
 13537         name: 'setlocal3',
 13538         canThrow: false,
 13539         operands: []
 13540       },
 13541       null,
 13542       null,
 13543       null,
 13544       null,
 13545       null,
 13546       null,
 13547       null,
 13548       null,
 13549       null,
 13550       null,
 13551       null,
 13552       null,
 13553       null,
 13554       null,
 13555       null,
 13556       null,
 13557       null,
 13558       null,
 13559       null,
 13560       null,
 13561       null,
 13563         name: 'invalid',
 13564         canThrow: false,
 13565         operands: []
 13566       },
 13567       null,
 13569         name: 'debug',
 13570         canThrow: true,
 13571         operands: [
 13573             name: 'debugType',
 13574             size: 'u08',
 13575             type: ''
 13576           },
 13578             name: 'index',
 13579             size: 'u30',
 13580             type: 'S'
 13581           },
 13583             name: 'reg',
 13584             size: 'u08',
 13585             type: ''
 13586           },
 13588             name: 'extra',
 13589             size: 'u30',
 13590             type: ''
 13593       },
 13595         name: 'debugline',
 13596         canThrow: true,
 13597         operands: [
 13599             name: 'lineNumber',
 13600             size: 'u30',
 13601             type: ''
 13604       },
 13606         name: 'debugfile',
 13607         canThrow: true,
 13608         operands: [
 13610             name: 'index',
 13611             size: 'u30',
 13612             type: 'S'
 13615       },
 13616       null,
 13617       null,
 13618       null,
 13619       null,
 13620       null,
 13621       null,
 13622       null,
 13623       null,
 13624       null,
 13625       null,
 13626       null,
 13627       null,
 13628       null,
 13629       null
 13630     ];
 13631     function opcodeName(op) {
 13632       return AVM2.opcodeTable[op].name;
 13634     AVM2.opcodeName = opcodeName;
 13635   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 13636   var AVM2 = Shumway.AVM2;
 13637 }(Shumway || (Shumway = {})));
 13638 var opcodeTable = Shumway.AVM2.opcodeTable;
 13639 var opcodeName = Shumway.AVM2.opcodeName;
 13640 var opcodeTable = Shumway.AVM2.opcodeTable;
 13641 var opcodeName = Shumway.AVM2.opcodeName;
 13642 var __extends = this.__extends || function (d, b) {
 13643     for (var p in b)
 13644       if (b.hasOwnProperty(p))
 13645         d[p] = b[p];
 13646     function __() {
 13647       this.constructor = d;
 13649     __.prototype = b.prototype;
 13650     d.prototype = new __();
 13651   };
 13652 var Shumway;
 13653 (function (Shumway) {
 13654   (function (AVM2) {
 13655     (function (ABC) {
 13656       var Timer = Shumway.Metrics.Timer;
 13657       var isString = Shumway.isString;
 13658       var isNumber = Shumway.isNumber;
 13659       var isNumeric = Shumway.isNumeric;
 13660       var isObject = Shumway.isObject;
 13661       var textDecoder = null;
 13662       if (typeof TextDecoder !== 'undefined') {
 13663         textDecoder = new TextDecoder();
 13665       var AbcStream = function () {
 13666           function AbcStream(bytes) {
 13667             this._bytes = bytes;
 13668             this._view = new DataView(bytes.buffer, bytes.byteOffset);
 13669             this._position = 0;
 13671           AbcStream._getResultBuffer = function (length) {
 13672             if (!AbcStream._resultBuffer || AbcStream._resultBuffer.length < length) {
 13673               AbcStream._resultBuffer = new Int32Array(length * 2);
 13675             return AbcStream._resultBuffer;
 13676           };
 13677           Object.defineProperty(AbcStream.prototype, 'position', {
 13678             get: function () {
 13679               return this._position;
 13680             },
 13681             enumerable: true,
 13682             configurable: true
 13683           });
 13684           AbcStream.prototype.remaining = function () {
 13685             return this._bytes.length - this._position;
 13686           };
 13687           AbcStream.prototype.seek = function (position) {
 13688             this._position = position;
 13689           };
 13690           AbcStream.prototype.readU8 = function () {
 13691             return this._bytes[this._position++];
 13692           };
 13693           AbcStream.prototype.readU8s = function (count) {
 13694             var b = new Uint8Array(count);
 13695             b.set(this._bytes.subarray(this._position, this._position + count), 0);
 13696             this._position += count;
 13697             return b;
 13698           };
 13699           AbcStream.prototype.readS8 = function () {
 13700             return this._bytes[this._position++] << 24 >> 24;
 13701           };
 13702           AbcStream.prototype.readU32 = function () {
 13703             return this.readS32() >>> 0;
 13704           };
 13705           AbcStream.prototype.readU30 = function () {
 13706             var result = this.readU32();
 13707             if (result & 3221225472) {
 13708               return result;
 13710             return result;
 13711           };
 13712           AbcStream.prototype.readU30Unsafe = function () {
 13713             return this.readU32();
 13714           };
 13715           AbcStream.prototype.readS16 = function () {
 13716             return this.readU30Unsafe() << 16 >> 16;
 13717           };
 13718           AbcStream.prototype.readS32 = function () {
 13719             var result = this.readU8();
 13720             if (result & 128) {
 13721               result = result & 127 | this.readU8() << 7;
 13722               if (result & 16384) {
 13723                 result = result & 16383 | this.readU8() << 14;
 13724                 if (result & 2097152) {
 13725                   result = result & 2097151 | this.readU8() << 21;
 13726                   if (result & 268435456) {
 13727                     result = result & 268435455 | this.readU8() << 28;
 13728                     result = result & 4294967295;
 13733             return result;
 13734           };
 13735           AbcStream.prototype.readWord = function () {
 13736             var result = this._view.getUint32(this._position, true);
 13737             this._position += 4;
 13738             return result;
 13739           };
 13740           AbcStream.prototype.readS24 = function () {
 13741             var u = this.readU8() | this.readU8() << 8 | this.readU8() << 16;
 13742             return u << 8 >> 8;
 13743           };
 13744           AbcStream.prototype.readDouble = function () {
 13745             var result = this._view.getFloat64(this._position, true);
 13746             this._position += 8;
 13747             return result;
 13748           };
 13749           AbcStream.prototype.readUTFString = function (length) {
 13750             if (textDecoder) {
 13751               var position = this._position;
 13752               this._position += length;
 13753               return textDecoder.decode(this._bytes.subarray(position, position + length));
 13755             var pos = this._position;
 13756             var end = pos + length;
 13757             var bytes = this._bytes;
 13758             var i = 0;
 13759             var result = AbcStream._getResultBuffer(length * 2);
 13760             while (pos < end) {
 13761               var c = bytes[pos++];
 13762               if (c <= 127) {
 13763                 result[i++] = c;
 13764               } else if (c >= 192) {
 13765                 var code = 0;
 13766                 if (c < 224) {
 13767                   code = (c & 31) << 6 | bytes[pos++] & 63;
 13768                 } else if (c < 240) {
 13769                   code = (c & 15) << 12 | (bytes[pos++] & 63) << 6 | bytes[pos++] & 63;
 13770                 } else {
 13771                   code = ((c & 7) << 18 | (bytes[pos++] & 63) << 12 | (bytes[pos++] & 63) << 6 | bytes[pos++] & 63) - 65536;
 13772                   result[i++] = ((code & 1047552) >>> 10) + 55296;
 13773                   code = (code & 1023) + 56320;
 13775                 result[i++] = code;
 13778             this._position = pos;
 13779             return Shumway.StringUtilities.fromCharCodeArray(result.subarray(0, i));
 13780           };
 13781           AbcStream._resultBuffer = new Int32Array(256);
 13782           return AbcStream;
 13783         }();
 13784       ABC.AbcStream = AbcStream;
 13785       var Parameter = function () {
 13786           function Parameter(name, type, value) {
 13787             this.name = name;
 13788             this.type = type;
 13789             this.value = value;
 13791           return Parameter;
 13792         }();
 13793       ABC.Parameter = Parameter;
 13794       var Trait = function () {
 13795           function Trait(abc, stream, holder) {
 13796             var constantPool = abc.constantPool;
 13797             var methods = abc.methods;
 13798             var classes = abc.classes;
 13799             var metadata = abc.metadata;
 13800             this.holder = holder;
 13801             this.name = constantPool.multinames[stream.readU30()];
 13802             var tag = stream.readU8();
 13803             this.kind = tag & 15;
 13804             this.attributes = tag >> 4 & 15;
 13805             true;
 13806             switch (this.kind) {
 13807             case 0:
 13808             case 6:
 13809               this.slotId = stream.readU30();
 13810               this.typeName = constantPool.multinames[stream.readU30()];
 13811               var valueIndex = stream.readU30();
 13812               this.value = undefined;
 13813               if (valueIndex !== 0) {
 13814                 this.hasDefaultValue = true;
 13815                 this.value = constantPool.getValue(stream.readU8(), valueIndex);
 13817               break;
 13818             case 1:
 13819             case 3:
 13820             case 2:
 13821               this.dispId = stream.readU30();
 13822               this.methodInfo = methods[stream.readU30()];
 13823               this.methodInfo.name = this.name;
 13824               AbcFile.attachHolder(this.methodInfo, this.holder);
 13825               this.methodInfo.abc = abc;
 13826               break;
 13827             case 4:
 13828               this.slotId = stream.readU30();
 13829               true;
 13830               this.classInfo = classes[stream.readU30()];
 13831               break;
 13832             case 5:
 13833               true;
 13834               break;
 13836             if (this.attributes & 4) {
 13837               var traitMetadata;
 13838               for (var i = 0, j = stream.readU30(); i < j; i++) {
 13839                 var md = metadata[stream.readU30()];
 13840                 if (md.name === '__go_to_definition_help' || md.name === '__go_to_ctor_definition_help') {
 13841                   continue;
 13843                 if (!traitMetadata) {
 13844                   traitMetadata = {};
 13846                 traitMetadata[md.name] = md;
 13848               if (traitMetadata) {
 13849                 if (this.isClass()) {
 13850                   this.classInfo.metadata = traitMetadata;
 13852                 this.metadata = traitMetadata;
 13856           Trait.prototype.isSlot = function () {
 13857             return this.kind === 0;
 13858           };
 13859           Trait.prototype.isConst = function () {
 13860             return this.kind === 6;
 13861           };
 13862           Trait.prototype.isMethod = function () {
 13863             return this.kind === 1;
 13864           };
 13865           Trait.prototype.isClass = function () {
 13866             return this.kind === 4;
 13867           };
 13868           Trait.prototype.isGetter = function () {
 13869             return this.kind === 2;
 13870           };
 13871           Trait.prototype.isSetter = function () {
 13872             return this.kind === 3;
 13873           };
 13874           Trait.prototype.isProtected = function () {
 13875             true;
 13876             return this.name.namespaces[0].isProtected();
 13877           };
 13878           Trait.prototype.kindName = function () {
 13879             switch (this.kind) {
 13880             case 0:
 13881               return 'Slot';
 13882             case 6:
 13883               return 'Const';
 13884             case 1:
 13885               return 'Method';
 13886             case 3:
 13887               return 'Setter';
 13888             case 2:
 13889               return 'Getter';
 13890             case 4:
 13891               return 'Class';
 13892             case 5:
 13893               return 'Function';
 13895             Shumway.Debug.unexpected();
 13896           };
 13897           Trait.prototype.isOverride = function () {
 13898             return this.attributes & 2;
 13899           };
 13900           Trait.prototype.isFinal = function () {
 13901             return this.attributes & 1;
 13902           };
 13903           Trait.prototype.toString = function () {
 13904             var str = Shumway.IntegerUtilities.getFlags(this.attributes, 'final|override|metadata'.split('|'));
 13905             if (str) {
 13906               str += ' ';
 13908             str += Multiname.getQualifiedName(this.name);
 13909             switch (this.kind) {
 13910             case 0:
 13911             case 6:
 13912               return str + ', typeName: ' + this.typeName + ', slotId: ' + this.slotId + ', value: ' + this.value;
 13913             case 1:
 13914             case 3:
 13915             case 2:
 13916               return str + ', ' + this.kindName() + ': ' + this.methodInfo.name;
 13917             case 4:
 13918               return str + ', slotId: ' + this.slotId + ', class: ' + this.classInfo;
 13919             case 5:
 13920               break;
 13922           };
 13923           Trait.parseTraits = function (abc, stream, holder) {
 13924             var count = stream.readU30();
 13925             var traits = [];
 13926             for (var i = 0; i < count; i++) {
 13927               traits.push(new Trait(abc, stream, holder));
 13929             return traits;
 13930           };
 13931           return Trait;
 13932         }();
 13933       ABC.Trait = Trait;
 13934       var Info = function () {
 13935           function Info(abc, index) {
 13936             this.abc = abc;
 13937             this.index = index;
 13939           return Info;
 13940         }();
 13941       ABC.Info = Info;
 13942       var MethodInfo = function (_super) {
 13943           __extends(MethodInfo, _super);
 13944           function MethodInfo(abc, index, stream) {
 13945             _super.call(this, abc, index);
 13946             var constantPool = abc.constantPool;
 13947             var parameterCount = stream.readU30();
 13948             this.returnType = constantPool.multinames[stream.readU30()];
 13949             this.parameters = [];
 13950             for (var i = 0; i < parameterCount; i++) {
 13951               this.parameters.push(new Parameter(undefined, constantPool.multinames[stream.readU30()], undefined));
 13953             this.debugName = constantPool.strings[stream.readU30()];
 13954             this.flags = stream.readU8();
 13955             var optionalCount = 0;
 13956             if (this.flags & 8) {
 13957               optionalCount = stream.readU30();
 13958               true;
 13959               for (var i = parameterCount - optionalCount; i < parameterCount; i++) {
 13960                 var valueIndex = stream.readU30();
 13961                 this.parameters[i].value = constantPool.getValue(stream.readU8(), valueIndex);
 13964             if (this.flags & 128) {
 13965               for (var i = 0; i < parameterCount; i++) {
 13966                 if (false) {
 13967                   this.parameters[i].name = constantPool.strings[stream.readU30()];
 13968                 } else {
 13969                   stream.readU30();
 13970                   this.parameters[i].name = MethodInfo._getParameterName(i);
 13973             } else {
 13974               for (var i = 0; i < parameterCount; i++) {
 13975                 this.parameters[i].name = MethodInfo._getParameterName(i);
 13979           MethodInfo._getParameterName = function (i) {
 13980             true;
 13981             return String.fromCharCode('A'.charCodeAt(0) + i);
 13982           };
 13983           MethodInfo.prototype.toString = function () {
 13984             var flags = Shumway.IntegerUtilities.getFlags(this.flags, 'NEED_ARGUMENTS|NEED_ACTIVATION|NEED_REST|HAS_OPTIONAL|||SET_DXN|HAS_PARAM_NAMES'.split('|'));
 13985             return (flags ? flags + ' ' : '') + this.name;
 13986           };
 13987           MethodInfo.prototype.hasOptional = function () {
 13988             return !(!(this.flags & 8));
 13989           };
 13990           MethodInfo.prototype.needsActivation = function () {
 13991             return !(!(this.flags & 2));
 13992           };
 13993           MethodInfo.prototype.needsRest = function () {
 13994             return !(!(this.flags & 4));
 13995           };
 13996           MethodInfo.prototype.needsArguments = function () {
 13997             return !(!(this.flags & 1));
 13998           };
 13999           MethodInfo.prototype.isNative = function () {
 14000             return !(!(this.flags & 32));
 14001           };
 14002           MethodInfo.prototype.isClassMember = function () {
 14003             return this.holder instanceof ClassInfo;
 14004           };
 14005           MethodInfo.prototype.isInstanceMember = function () {
 14006             return this.holder instanceof InstanceInfo;
 14007           };
 14008           MethodInfo.prototype.isScriptMember = function () {
 14009             return this.holder instanceof ScriptInfo;
 14010           };
 14011           MethodInfo.parseException = function (abc, stream) {
 14012             var multinames = abc.constantPool.multinames;
 14013             var ex = {
 14014                 start: stream.readU30(),
 14015                 end: stream.readU30(),
 14016                 target: stream.readU30(),
 14017                 typeName: multinames[stream.readU30()],
 14018                 varName: multinames[stream.readU30()]
 14019               };
 14020             true;
 14021             true;
 14022             return ex;
 14023           };
 14024           MethodInfo.parseBody = function (abc, stream) {
 14025             var constantPool = abc.constantPool;
 14026             var methods = abc.methods;
 14027             var index = stream.readU30();
 14028             var mi = methods[index];
 14029             mi.index = index;
 14030             mi.hasBody = true;
 14031             mi.hash = abc.hash + 196608 + index;
 14032             true;
 14033             mi.maxStack = stream.readU30();
 14034             mi.localCount = stream.readU30();
 14035             mi.initScopeDepth = stream.readU30();
 14036             mi.maxScopeDepth = stream.readU30();
 14037             mi.code = stream.readU8s(stream.readU30());
 14038             var exceptions = [];
 14039             var exceptionCount = stream.readU30();
 14040             for (var i = 0; i < exceptionCount; ++i) {
 14041               exceptions.push(MethodInfo.parseException(abc, stream));
 14043             mi.exceptions = exceptions;
 14044             mi.traits = Trait.parseTraits(abc, stream, mi);
 14045           };
 14046           MethodInfo.prototype.hasExceptions = function () {
 14047             return this.exceptions.length > 0;
 14048           };
 14049           return MethodInfo;
 14050         }(Info);
 14051       ABC.MethodInfo = MethodInfo;
 14052       var InstanceInfo = function (_super) {
 14053           __extends(InstanceInfo, _super);
 14054           function InstanceInfo(abc, index, stream) {
 14055             _super.call(this, abc, index);
 14056             this.runtimeId = InstanceInfo.nextID++;
 14057             var constantPool = abc.constantPool;
 14058             var methods = abc.methods;
 14059             this.name = constantPool.multinames[stream.readU30()];
 14060             true;
 14061             this.superName = constantPool.multinames[stream.readU30()];
 14062             this.flags = stream.readU8();
 14063             this.protectedNs = undefined;
 14064             if (this.flags & 8) {
 14065               this.protectedNs = constantPool.namespaces[stream.readU30()];
 14067             var interfaceCount = stream.readU30();
 14068             this.interfaces = [];
 14069             for (var i = 0; i < interfaceCount; i++) {
 14070               this.interfaces[i] = constantPool.multinames[stream.readU30()];
 14072             this.init = methods[stream.readU30()];
 14073             this.init.isInstanceInitializer = true;
 14074             this.init.name = this.name;
 14075             AbcFile.attachHolder(this.init, this);
 14076             this.traits = Trait.parseTraits(abc, stream, this);
 14078           InstanceInfo.prototype.toString = function () {
 14079             var flags = Shumway.IntegerUtilities.getFlags(this.flags & 8, 'sealed|final|interface|protected'.split('|'));
 14080             var str = (flags ? flags + ' ' : '') + this.name;
 14081             if (this.superName) {
 14082               str += ' extends ' + this.superName;
 14084             return str;
 14085           };
 14086           InstanceInfo.prototype.isFinal = function () {
 14087             return !(!(this.flags & 2));
 14088           };
 14089           InstanceInfo.prototype.isSealed = function () {
 14090             return !(!(this.flags & 1));
 14091           };
 14092           InstanceInfo.prototype.isInterface = function () {
 14093             return !(!(this.flags & 4));
 14094           };
 14095           InstanceInfo.nextID = 1;
 14096           return InstanceInfo;
 14097         }(Info);
 14098       ABC.InstanceInfo = InstanceInfo;
 14099       var ClassInfo = function (_super) {
 14100           __extends(ClassInfo, _super);
 14101           function ClassInfo(abc, index, stream) {
 14102             _super.call(this, abc, index);
 14103             this.runtimeId = ClassInfo.nextID++;
 14104             this.abc = abc;
 14105             this.hash = abc.hash + 65536 + index;
 14106             this.index = index;
 14107             this.init = abc.methods[stream.readU30()];
 14108             this.init.isClassInitializer = true;
 14109             AbcFile.attachHolder(this.init, this);
 14110             this.traits = Trait.parseTraits(abc, stream, this);
 14111             this.instanceInfo = abc.instances[index];
 14112             this.instanceInfo.classInfo = this;
 14113             this.defaultValue = ClassInfo._getDefaultValue(this.instanceInfo.name);
 14115           ClassInfo._getDefaultValue = function (qn) {
 14116             if (Multiname.getQualifiedName(qn) === Multiname.Int || Multiname.getQualifiedName(qn) === Multiname.Uint) {
 14117               return 0;
 14118             } else if (Multiname.getQualifiedName(qn) === Multiname.Number) {
 14119               return NaN;
 14120             } else if (Multiname.getQualifiedName(qn) === Multiname.Boolean) {
 14121               return false;
 14122             } else {
 14123               return null;
 14125           };
 14126           ClassInfo.prototype.toString = function () {
 14127             return this.instanceInfo.name.toString();
 14128           };
 14129           ClassInfo.nextID = 1;
 14130           return ClassInfo;
 14131         }(Info);
 14132       ABC.ClassInfo = ClassInfo;
 14133       var ScriptInfo = function (_super) {
 14134           __extends(ScriptInfo, _super);
 14135           function ScriptInfo(abc, index, stream) {
 14136             _super.call(this, abc, index);
 14137             this.runtimeId = ClassInfo.nextID++;
 14138             this.hash = abc.hash + 131072 + index;
 14139             this.name = abc.name + '$script' + index;
 14140             this.init = abc.methods[stream.readU30()];
 14141             this.init.isScriptInitializer = true;
 14142             AbcFile.attachHolder(this.init, this);
 14143             this.traits = Trait.parseTraits(abc, stream, this);
 14145           Object.defineProperty(ScriptInfo.prototype, 'entryPoint', {
 14146             get: function () {
 14147               return this.init;
 14148             },
 14149             enumerable: true,
 14150             configurable: true
 14151           });
 14152           ScriptInfo.prototype.toString = function () {
 14153             return this.name;
 14154           };
 14155           ScriptInfo.nextID = 1;
 14156           return ScriptInfo;
 14157         }(Info);
 14158       ABC.ScriptInfo = ScriptInfo;
 14159       var AbcFile = function () {
 14160           function AbcFile(bytes, name, hash) {
 14161             if (typeof hash === 'undefined') {
 14162               hash = 0;
 14164             Timer.start('Parse ABC');
 14165             this.name = name;
 14166             this.env = {};
 14167             var computedHash;
 14168             if (!hash || !true) {
 14169               Timer.start('Adler');
 14170               computedHash = Shumway.HashUtilities.hashBytesTo32BitsAdler(bytes, 0, bytes.length);
 14171               Timer.stop();
 14173             if (hash) {
 14174               this.hash = hash;
 14175               true;
 14176             } else {
 14177               this.hash = computedHash;
 14179             var n, i;
 14180             var stream = new AbcStream(bytes);
 14181             AbcFile._checkMagic(stream);
 14182             Timer.start('Parse constantPool');
 14183             this.constantPool = new ConstantPool(stream, this);
 14184             Timer.stop();
 14185             Timer.start('Parse Method Infos');
 14186             this.methods = [];
 14187             n = stream.readU30();
 14188             for (i = 0; i < n; ++i) {
 14189               this.methods.push(new MethodInfo(this, i, stream));
 14191             Timer.stop();
 14192             Timer.start('Parse MetaData Infos');
 14193             this.metadata = [];
 14194             n = stream.readU30();
 14195             for (i = 0; i < n; ++i) {
 14196               this.metadata.push(new MetaDataInfo(this, stream));
 14198             Timer.stop();
 14199             Timer.start('Parse Instance Infos');
 14200             this.instances = [];
 14201             n = stream.readU30();
 14202             for (i = 0; i < n; ++i) {
 14203               this.instances.push(new InstanceInfo(this, i, stream));
 14205             Timer.stop();
 14206             Timer.start('Parse Class Infos');
 14207             this.classes = [];
 14208             for (i = 0; i < n; ++i) {
 14209               this.classes.push(new ClassInfo(this, i, stream));
 14211             Timer.stop();
 14212             Timer.start('Parse Script Infos');
 14213             this.scripts = [];
 14214             n = stream.readU30();
 14215             for (i = 0; i < n; ++i) {
 14216               this.scripts.push(new ScriptInfo(this, i, stream));
 14218             Timer.stop();
 14219             Timer.start('Parse Method Body Info');
 14220             n = stream.readU30();
 14221             for (i = 0; i < n; ++i) {
 14222               MethodInfo.parseBody(this, stream);
 14224             Timer.stop();
 14225             Timer.stop();
 14227           AbcFile._checkMagic = function (stream) {
 14228             var magic = stream.readWord();
 14229             var flashPlayerBrannan = 46 << 16 | 15;
 14230             if (magic < flashPlayerBrannan) {
 14231               throw new Error('Invalid ABC File (magic = ' + Number(magic).toString(16) + ')');
 14233           };
 14234           Object.defineProperty(AbcFile.prototype, 'lastScript', {
 14235             get: function () {
 14236               true;
 14237               return this.scripts[this.scripts.length - 1];
 14238             },
 14239             enumerable: true,
 14240             configurable: true
 14241           });
 14242           AbcFile.attachHolder = function (mi, holder) {
 14243             true;
 14244             mi.holder = holder;
 14245           };
 14246           AbcFile.prototype.toString = function () {
 14247             return this.name;
 14248           };
 14249           return AbcFile;
 14250         }();
 14251       ABC.AbcFile = AbcFile;
 14252       var Namespace = function () {
 14253           function Namespace(kind, uri, prefix, uniqueURIHash) {
 14254             if (typeof uri === 'undefined') {
 14255               uri = '';
 14257             if (uri === undefined) {
 14258               uri = '';
 14260             if (prefix !== undefined) {
 14261               this.prefix = prefix;
 14263             this.kind = kind;
 14264             this.uri = uri;
 14265             this._buildNamespace(uniqueURIHash);
 14267           Namespace.prototype._buildNamespace = function (uniqueURIHash) {
 14268             if (this.kind === 22) {
 14269               this.kind = 8;
 14271             if (this.isPublic() && this.uri) {
 14272               var n = this.uri.length - 1;
 14273               var mark = this.uri.charCodeAt(n);
 14274               if (mark > Namespace._MIN_API_MARK) {
 14275                 this.uri = this.uri.substring(0, n - 1);
 14277             } else if (this.isUnique()) {
 14278               this.uri = 'private ' + uniqueURIHash;
 14280             this.qualifiedName = Namespace._qualifyNamespace(this.kind, this.uri, this.prefix ? this.prefix : '');
 14281           };
 14282           Namespace._hashNamespace = function (kind, uri, prefix) {
 14283             var data = new Int32Array(1 + uri.length + prefix.length);
 14284             var j = 0;
 14285             data[j++] = kind;
 14286             var index = Namespace._knownURIs.indexOf(uri);
 14287             if (index >= 0) {
 14288               return kind << 2 | index;
 14289             } else {
 14290               for (var i = 0; i < uri.length; i++) {
 14291                 data[j++] = uri.charCodeAt(i);
 14294             for (var i = 0; i < prefix.length; i++) {
 14295               data[j++] = prefix.charCodeAt(i);
 14297             return Shumway.HashUtilities.hashBytesTo32BitsMD5(data, 0, j);
 14298           };
 14299           Namespace._qualifyNamespace = function (kind, uri, prefix) {
 14300             var key = kind + uri;
 14301             var mangledNamespace = Namespace._mangledNamespaceCache[key];
 14302             if (mangledNamespace) {
 14303               return mangledNamespace;
 14305             mangledNamespace = Shumway.StringUtilities.variableLengthEncodeInt32(Namespace._hashNamespace(kind, uri, prefix));
 14306             Namespace._mangledNamespaceMap[mangledNamespace] = {
 14307               kind: kind,
 14308               uri: uri,
 14309               prefix: prefix
 14310             };
 14311             Namespace._mangledNamespaceCache[key] = mangledNamespace;
 14312             return mangledNamespace;
 14313           };
 14314           Namespace.fromQualifiedName = function (qn) {
 14315             var length = Shumway.StringUtilities.fromEncoding(qn[0]);
 14316             var mangledNamespace = qn.substring(0, length + 1);
 14317             var ns = Namespace._mangledNamespaceMap[mangledNamespace];
 14318             return new Namespace(ns.kind, ns.uri, ns.prefix);
 14319           };
 14320           Namespace.kindFromString = function (str) {
 14321             for (var kind in Namespace._kinds) {
 14322               if (Namespace._kinds[kind] === str) {
 14323                 return kind;
 14326             return true;
 14327           };
 14328           Namespace.createNamespace = function (uri, prefix) {
 14329             return new Namespace(8, uri, prefix);
 14330           };
 14331           Namespace.parse = function (constantPool, stream, hash) {
 14332             var kind = stream.readU8();
 14333             var uri = constantPool.strings[stream.readU30()];
 14334             return new Namespace(kind, uri, undefined, hash);
 14335           };
 14336           Namespace.prototype.isPublic = function () {
 14337             return this.kind === 8 || this.kind === 22;
 14338           };
 14339           Namespace.prototype.isProtected = function () {
 14340             return this.kind === 24;
 14341           };
 14342           Namespace.prototype.isUnique = function () {
 14343             return this.kind === 5 && !this.uri;
 14344           };
 14345           Namespace.prototype.isDynamic = function () {
 14346             return this.isPublic() && !this.uri;
 14347           };
 14348           Namespace.prototype.getURI = function () {
 14349             return this.uri;
 14350           };
 14351           Namespace.prototype.toString = function () {
 14352             return Namespace._kinds[this.kind] + (this.uri ? ' ' + this.uri : '');
 14353           };
 14354           Namespace.prototype.clone = function () {
 14355             var ns = Object.create(Namespace.prototype);
 14356             ns.kind = this.kind;
 14357             ns.uri = this.uri;
 14358             ns.prefix = this.prefix;
 14359             ns.qualifiedName = this.qualifiedName;
 14360             return ns;
 14361           };
 14362           Namespace.prototype.isEqualTo = function (other) {
 14363             return this.qualifiedName === other.qualifiedName;
 14364           };
 14365           Namespace.prototype.inNamespaceSet = function (set) {
 14366             for (var i = 0; i < set.length; i++) {
 14367               if (set[i].qualifiedName === this.qualifiedName) {
 14368                 return true;
 14371             return false;
 14372           };
 14373           Namespace.prototype.getAccessModifier = function () {
 14374             return Namespace._kinds[this.kind];
 14375           };
 14376           Namespace.prototype.getQualifiedName = function () {
 14377             return this.qualifiedName;
 14378           };
 14379           Namespace.fromSimpleName = function (simpleName) {
 14380             if (simpleName in Namespace._simpleNameCache) {
 14381               return Namespace._simpleNameCache[simpleName];
 14383             var namespaceNames;
 14384             if (simpleName.indexOf('[') === 0) {
 14385               true;
 14386               namespaceNames = simpleName.substring(1, simpleName.length - 1).split(',');
 14387             } else {
 14388               namespaceNames = [
 14389                 simpleName
 14390               ];
 14392             return Namespace._simpleNameCache[simpleName] = namespaceNames.map(function (name) {
 14393               name = name.trim();
 14394               var kindName, uri;
 14395               if (name.indexOf(' ') > 0) {
 14396                 kindName = name.substring(0, name.indexOf(' ')).trim();
 14397                 uri = name.substring(name.indexOf(' ') + 1).trim();
 14398               } else {
 14399                 var kinds = Namespace._kinds;
 14400                 if (name === kinds[8] || name === kinds[23] || name === kinds[5] || name === kinds[24] || name === kinds[25] || name === kinds[26]) {
 14401                   kindName = name;
 14402                   uri = '';
 14403                 } else {
 14404                   kindName = Namespace._publicPrefix;
 14405                   uri = name;
 14408               return new Namespace(Namespace.kindFromString(kindName), uri);
 14409             });
 14410           };
 14411           Namespace._publicPrefix = 'public';
 14412           Namespace._kinds = function () {
 14413             var map = Shumway.ObjectUtilities.createMap();
 14414             map[8] = Namespace._publicPrefix;
 14415             map[23] = 'packageInternal';
 14416             map[5] = 'private';
 14417             map[24] = 'protected';
 14418             map[25] = 'explicit';
 14419             map[26] = 'staticProtected';
 14420             return map;
 14421           }();
 14422           Namespace._MIN_API_MARK = 58004;
 14423           Namespace._MAX_API_MARK = 63743;
 14424           Namespace._knownURIs = [
 14425             ''
 14426           ];
 14427           Namespace._mangledNamespaceCache = Shumway.ObjectUtilities.createMap();
 14428           Namespace._mangledNamespaceMap = Shumway.ObjectUtilities.createMap();
 14429           Namespace.PUBLIC = new Namespace(8);
 14430           Namespace.PROTECTED = new Namespace(24);
 14431           Namespace.PROXY = new Namespace(8, 'http://www.adobe.com/2006/actionscript/flash/proxy');
 14432           Namespace._simpleNameCache = Shumway.ObjectUtilities.createMap();
 14433           return Namespace;
 14434         }();
 14435       ABC.Namespace = Namespace;
 14436       var Multiname = function () {
 14437           function Multiname(namespaces, name, flags) {
 14438             if (typeof flags === 'undefined') {
 14439               flags = 0;
 14441             if (name !== undefined) {
 14442               true;
 14444             this.runtimeId = Multiname._nextID++;
 14445             this.namespaces = namespaces;
 14446             this.name = name;
 14447             this.flags = flags;
 14449           Multiname.parse = function (constantPool, stream, multinames, patchFactoryTypes) {
 14450             var index = 0;
 14451             var kind = stream.readU8();
 14452             var name, namespaces = [], flags = 0;
 14453             switch (kind) {
 14454             case 7:
 14455             case 13:
 14456               index = stream.readU30();
 14457               if (index) {
 14458                 namespaces = [
 14459                   constantPool.namespaces[index]
 14460                 ];
 14461               } else {
 14462                 flags &= ~Multiname.RUNTIME_NAME;
 14464               index = stream.readU30();
 14465               if (index) {
 14466                 name = constantPool.strings[index];
 14468               break;
 14469             case 15:
 14470             case 16:
 14471               index = stream.readU30();
 14472               if (index) {
 14473                 name = constantPool.strings[index];
 14474               } else {
 14475                 flags &= ~Multiname.RUNTIME_NAME;
 14477               flags |= Multiname.RUNTIME_NAMESPACE;
 14478               break;
 14479             case 17:
 14480             case 18:
 14481               flags |= Multiname.RUNTIME_NAMESPACE;
 14482               flags |= Multiname.RUNTIME_NAME;
 14483               break;
 14484             case 9:
 14485             case 14:
 14486               index = stream.readU30();
 14487               if (index) {
 14488                 name = constantPool.strings[index];
 14489               } else {
 14490                 flags &= ~Multiname.RUNTIME_NAME;
 14492               index = stream.readU30();
 14493               true;
 14494               namespaces = constantPool.namespaceSets[index];
 14495               break;
 14496             case 27:
 14497             case 28:
 14498               flags |= Multiname.RUNTIME_NAME;
 14499               index = stream.readU30();
 14500               true;
 14501               namespaces = constantPool.namespaceSets[index];
 14502               break;
 14503             case 29:
 14504               var factoryTypeIndex = stream.readU32();
 14505               if (multinames[factoryTypeIndex]) {
 14506                 namespaces = multinames[factoryTypeIndex].namespaces;
 14507                 name = multinames[factoryTypeIndex].name;
 14509               var typeParameterCount = stream.readU32();
 14510               true;
 14511               var typeParameterIndex = stream.readU32();
 14512               true;
 14513               var mn = new Multiname(namespaces, name, flags);
 14514               mn.typeParameter = multinames[typeParameterIndex];
 14515               if (!multinames[factoryTypeIndex]) {
 14516                 patchFactoryTypes.push({
 14517                   multiname: mn,
 14518                   index: factoryTypeIndex
 14519                 });
 14521               return mn;
 14522             default:
 14523               Shumway.Debug.unexpected();
 14524               break;
 14526             switch (kind) {
 14527             case 13:
 14528             case 16:
 14529             case 18:
 14530             case 14:
 14531             case 28:
 14532               flags |= Multiname.ATTRIBUTE;
 14533               break;
 14535             return new Multiname(namespaces, name, flags);
 14536           };
 14537           Multiname.isMultiname = function (mn) {
 14538             return typeof mn === 'number' || typeof mn === 'string' || mn instanceof Multiname || mn instanceof Number;
 14539           };
 14540           Multiname.needsResolution = function (mn) {
 14541             return mn instanceof Multiname && mn.namespaces.length > 1;
 14542           };
 14543           Multiname.isQName = function (mn) {
 14544             if (mn instanceof Multiname) {
 14545               return mn.namespaces && mn.namespaces.length === 1;
 14547             return true;
 14548           };
 14549           Multiname.isRuntimeName = function (mn) {
 14550             return mn instanceof Multiname && mn.isRuntimeName();
 14551           };
 14552           Multiname.isRuntimeNamespace = function (mn) {
 14553             return mn instanceof Multiname && mn.isRuntimeNamespace();
 14554           };
 14555           Multiname.isRuntime = function (mn) {
 14556             return mn instanceof Multiname && mn.isRuntimeName() || mn.isRuntimeNamespace();
 14557           };
 14558           Multiname.getQualifiedName = function (mn) {
 14559             true;
 14560             if (mn instanceof Multiname) {
 14561               if (mn.qualifiedName !== undefined) {
 14562                 return mn.qualifiedName;
 14564               var name = String(mn.name);
 14565               if (isNumeric(name) && mn.namespaces[0].isPublic()) {
 14566                 return mn.qualifiedName = name;
 14568               mn = mn.qualifiedName = Multiname.qualifyName(mn.namespaces[0], name);
 14570             return mn;
 14571           };
 14572           Multiname.qualifyName = function (namespace, name) {
 14573             return '$' + namespace.qualifiedName + name;
 14574           };
 14575           Multiname.stripPublicQualifier = function (qn) {
 14576             var publicQualifier = '$' + Namespace.PUBLIC.qualifiedName;
 14577             var index = qn.indexOf(publicQualifier);
 14578             if (index !== 0) {
 14579               return undefined;
 14581             return qn.substring(publicQualifier.length);
 14582           };
 14583           Multiname.fromQualifiedName = function (qn) {
 14584             if (qn instanceof Multiname) {
 14585               return qn;
 14587             if (isNumeric(qn)) {
 14588               return new Multiname([
 14589                 Namespace.PUBLIC
 14590               ], qn);
 14592             if (qn[0] !== '$') {
 14593               return;
 14595             var ns = Namespace.fromQualifiedName(qn.substring(1));
 14596             return new Multiname([
 14597               ns
 14598             ], qn.substring(1 + ns.qualifiedName.length));
 14599           };
 14600           Multiname.getNameFromPublicQualifiedName = function (qn) {
 14601             var mn = Multiname.fromQualifiedName(qn);
 14602             true;
 14603             return mn.name;
 14604           };
 14605           Multiname.getFullQualifiedName = function (mn) {
 14606             var qn = Multiname.getQualifiedName(mn);
 14607             if (mn instanceof Multiname && mn.typeParameter) {
 14608               qn += '$' + Multiname.getFullQualifiedName(mn.typeParameter);
 14610             return qn;
 14611           };
 14612           Multiname.getPublicQualifiedName = function (name) {
 14613             if (isNumeric(name)) {
 14614               return Shumway.toNumber(name);
 14615             } else if (name !== null && isObject(name)) {
 14616               return name;
 14618             return Multiname.qualifyName(Namespace.PUBLIC, name);
 14619           };
 14620           Multiname.isPublicQualifiedName = function (qn) {
 14621             return typeof qn === 'number' || isNumeric(qn) || qn.indexOf(Namespace.PUBLIC.qualifiedName) === 1;
 14622           };
 14623           Multiname.getAccessModifier = function (mn) {
 14624             true;
 14625             if (typeof mn === 'number' || typeof mn === 'string' || mn instanceof Number) {
 14626               return 'public';
 14628             true;
 14629             return mn.namespaces[0].getAccessModifier();
 14630           };
 14631           Multiname.isNumeric = function (mn) {
 14632             if (typeof mn === 'number') {
 14633               return true;
 14634             } else if (typeof mn === 'string') {
 14635               return isNumeric(mn);
 14637             return !isNaN(parseInt(Multiname.getName(mn), 10));
 14638           };
 14639           Multiname.getName = function (mn) {
 14640             true;
 14641             true;
 14642             return mn.getName();
 14643           };
 14644           Multiname.isAnyName = function (mn) {
 14645             return typeof mn === 'object' && !mn.isRuntimeName() && !mn.name;
 14646           };
 14647           Multiname.fromSimpleName = function (simpleName) {
 14648             true;
 14649             if (simpleName in Multiname._simpleNameCache) {
 14650               return Multiname._simpleNameCache[simpleName];
 14652             var nameIndex, namespaceIndex, name, namespace;
 14653             nameIndex = simpleName.lastIndexOf('.');
 14654             if (nameIndex <= 0) {
 14655               nameIndex = simpleName.lastIndexOf(' ');
 14657             if (nameIndex > 0 && nameIndex < simpleName.length - 1) {
 14658               name = simpleName.substring(nameIndex + 1).trim();
 14659               namespace = simpleName.substring(0, nameIndex).trim();
 14660             } else {
 14661               name = simpleName;
 14662               namespace = '';
 14664             return Multiname._simpleNameCache[simpleName] = new Multiname(Namespace.fromSimpleName(namespace), name);
 14665           };
 14666           Multiname.prototype.getQName = function (index) {
 14667             true;
 14668             if (!this._qualifiedNameCache) {
 14669               this._qualifiedNameCache = Shumway.ObjectUtilities.createArrayMap();
 14671             var name = this._qualifiedNameCache[index];
 14672             if (!name) {
 14673               name = this._qualifiedNameCache[index] = new Multiname([
 14674                 this.namespaces[index]
 14675               ], this.name, this.flags);
 14677             return name;
 14678           };
 14679           Multiname.prototype.hasQName = function (qn) {
 14680             true;
 14681             if (this.name !== qn.name) {
 14682               return false;
 14684             for (var i = 0; i < this.namespaces.length; i++) {
 14685               if (this.namespaces[i].isEqualTo(qn.namespaces[0])) {
 14686                 return true;
 14689             return false;
 14690           };
 14691           Multiname.prototype.isAttribute = function () {
 14692             return this.flags & Multiname.ATTRIBUTE;
 14693           };
 14694           Multiname.prototype.isAnyName = function () {
 14695             return Multiname.isAnyName(this);
 14696           };
 14697           Multiname.prototype.isAnyNamespace = function () {
 14698             return !this.isRuntimeNamespace() && (this.namespaces.length === 0 || this.isAnyName() && this.namespaces.length !== 1);
 14699           };
 14700           Multiname.prototype.isRuntimeName = function () {
 14701             return !(!(this.flags & Multiname.RUNTIME_NAME));
 14702           };
 14703           Multiname.prototype.isRuntimeNamespace = function () {
 14704             return !(!(this.flags & Multiname.RUNTIME_NAMESPACE));
 14705           };
 14706           Multiname.prototype.isRuntime = function () {
 14707             return !(!(this.flags & (Multiname.RUNTIME_NAME | Multiname.RUNTIME_NAMESPACE)));
 14708           };
 14709           Multiname.prototype.isQName = function () {
 14710             return this.namespaces.length === 1 && !this.isAnyName();
 14711           };
 14712           Multiname.prototype.hasTypeParameter = function () {
 14713             return !(!this.typeParameter);
 14714           };
 14715           Multiname.prototype.getName = function () {
 14716             return this.name;
 14717           };
 14718           Multiname.prototype.getOriginalName = function () {
 14719             true;
 14720             var name = this.namespaces[0].uri;
 14721             if (name) {
 14722               name += '.';
 14724             return name + this.name;
 14725           };
 14726           Multiname.prototype.getNamespace = function () {
 14727             true;
 14728             true;
 14729             return this.namespaces[0];
 14730           };
 14731           Multiname.prototype.nameToString = function () {
 14732             if (this.isAnyName()) {
 14733               return '*';
 14734             } else {
 14735               var name = this.getName();
 14736               return this.isRuntimeName() ? '[]' : name;
 14738           };
 14739           Multiname.prototype.hasObjectName = function () {
 14740             return typeof this.name === 'object';
 14741           };
 14742           Multiname.prototype.toString = function () {
 14743             var str = this.isAttribute() ? '@' : '';
 14744             if (this.isAnyNamespace()) {
 14745               str += '*::' + this.nameToString();
 14746             } else if (this.isRuntimeNamespace()) {
 14747               str += '[]::' + this.nameToString();
 14748             } else if (this.namespaces.length === 1 && this.isQName()) {
 14749               str += this.namespaces[0].toString() + '::';
 14750               str += this.nameToString();
 14751             } else {
 14752               str += '{';
 14753               for (var i = 0, count = this.namespaces.length; i < count; i++) {
 14754                 str += this.namespaces[i].toString();
 14755                 if (i + 1 < count) {
 14756                   str += ',';
 14759               str += '}::' + this.nameToString();
 14761             if (this.hasTypeParameter()) {
 14762               str += '<' + this.typeParameter.toString() + '>';
 14764             return str;
 14765           };
 14766           Multiname.ATTRIBUTE = 1;
 14767           Multiname.RUNTIME_NAMESPACE = 2;
 14768           Multiname.RUNTIME_NAME = 4;
 14769           Multiname._nextID = 0;
 14770           Multiname._simpleNameCache = Shumway.ObjectUtilities.createMap();
 14771           Multiname.Int = Multiname.getPublicQualifiedName('int');
 14772           Multiname.Uint = Multiname.getPublicQualifiedName('uint');
 14773           Multiname.Class = Multiname.getPublicQualifiedName('Class');
 14774           Multiname.Array = Multiname.getPublicQualifiedName('Array');
 14775           Multiname.Object = Multiname.getPublicQualifiedName('Object');
 14776           Multiname.String = Multiname.getPublicQualifiedName('String');
 14777           Multiname.Number = Multiname.getPublicQualifiedName('Number');
 14778           Multiname.Boolean = Multiname.getPublicQualifiedName('Boolean');
 14779           Multiname.Function = Multiname.getPublicQualifiedName('Function');
 14780           Multiname.XML = Multiname.getPublicQualifiedName('XML');
 14781           Multiname.XMLList = Multiname.getPublicQualifiedName('XMLList');
 14782           Multiname.TEMPORARY = new Multiname([], '');
 14783           return Multiname;
 14784         }();
 14785       ABC.Multiname = Multiname;
 14786       var MetaDataInfo = function () {
 14787           function MetaDataInfo(abc, stream) {
 14788             var strings = abc.constantPool.strings;
 14789             var name = this.name = strings[stream.readU30()];
 14790             var itemCount = stream.readU30();
 14791             var keys = [];
 14792             var items = [];
 14793             for (var i = 0; i < itemCount; i++) {
 14794               keys[i] = strings[stream.readU30()];
 14796             for (var i = 0; i < itemCount; i++) {
 14797               var key = keys[i];
 14798               items[i] = {
 14799                 key: key,
 14800                 value: strings[stream.readU30()]
 14801               };
 14802               if (key && name === 'native') {
 14803                 true;
 14804                 this[key] = items[i].value;
 14807             this.value = items;
 14809           MetaDataInfo.prototype.toString = function () {
 14810             return '[' + this.name + ']';
 14811           };
 14812           return MetaDataInfo;
 14813         }();
 14814       ABC.MetaDataInfo = MetaDataInfo;
 14815       (function (CONSTANT) {
 14816         CONSTANT[CONSTANT['Undefined'] = 0] = 'Undefined';
 14817         CONSTANT[CONSTANT['Utf8'] = 1] = 'Utf8';
 14818         CONSTANT[CONSTANT['Float'] = 2] = 'Float';
 14819         CONSTANT[CONSTANT['Int'] = 3] = 'Int';
 14820         CONSTANT[CONSTANT['UInt'] = 4] = 'UInt';
 14821         CONSTANT[CONSTANT['PrivateNs'] = 5] = 'PrivateNs';
 14822         CONSTANT[CONSTANT['Double'] = 6] = 'Double';
 14823         CONSTANT[CONSTANT['QName'] = 7] = 'QName';
 14824         CONSTANT[CONSTANT['Namespace'] = 8] = 'Namespace';
 14825         CONSTANT[CONSTANT['Multiname'] = 9] = 'Multiname';
 14826         CONSTANT[CONSTANT['False'] = 10] = 'False';
 14827         CONSTANT[CONSTANT['True'] = 11] = 'True';
 14828         CONSTANT[CONSTANT['Null'] = 12] = 'Null';
 14829         CONSTANT[CONSTANT['QNameA'] = 13] = 'QNameA';
 14830         CONSTANT[CONSTANT['MultinameA'] = 14] = 'MultinameA';
 14831         CONSTANT[CONSTANT['RTQName'] = 15] = 'RTQName';
 14832         CONSTANT[CONSTANT['RTQNameA'] = 16] = 'RTQNameA';
 14833         CONSTANT[CONSTANT['RTQNameL'] = 17] = 'RTQNameL';
 14834         CONSTANT[CONSTANT['RTQNameLA'] = 18] = 'RTQNameLA';
 14835         CONSTANT[CONSTANT['NameL'] = 19] = 'NameL';
 14836         CONSTANT[CONSTANT['NameLA'] = 20] = 'NameLA';
 14837         CONSTANT[CONSTANT['NamespaceSet'] = 21] = 'NamespaceSet';
 14838         CONSTANT[CONSTANT['PackageNamespace'] = 22] = 'PackageNamespace';
 14839         CONSTANT[CONSTANT['PackageInternalNs'] = 23] = 'PackageInternalNs';
 14840         CONSTANT[CONSTANT['ProtectedNamespace'] = 24] = 'ProtectedNamespace';
 14841         CONSTANT[CONSTANT['ExplicitNamespace'] = 25] = 'ExplicitNamespace';
 14842         CONSTANT[CONSTANT['StaticProtectedNs'] = 26] = 'StaticProtectedNs';
 14843         CONSTANT[CONSTANT['MultinameL'] = 27] = 'MultinameL';
 14844         CONSTANT[CONSTANT['MultinameLA'] = 28] = 'MultinameLA';
 14845         CONSTANT[CONSTANT['TypeName'] = 29] = 'TypeName';
 14846         CONSTANT[CONSTANT['ClassSealed'] = 1] = 'ClassSealed';
 14847         CONSTANT[CONSTANT['ClassFinal'] = 2] = 'ClassFinal';
 14848         CONSTANT[CONSTANT['ClassInterface'] = 4] = 'ClassInterface';
 14849         CONSTANT[CONSTANT['ClassProtectedNs'] = 8] = 'ClassProtectedNs';
 14850       }(ABC.CONSTANT || (ABC.CONSTANT = {})));
 14851       var CONSTANT = ABC.CONSTANT;
 14852       (function (METHOD) {
 14853         METHOD[METHOD['Arguments'] = 1] = 'Arguments';
 14854         METHOD[METHOD['Activation'] = 2] = 'Activation';
 14855         METHOD[METHOD['Needrest'] = 4] = 'Needrest';
 14856         METHOD[METHOD['HasOptional'] = 8] = 'HasOptional';
 14857         METHOD[METHOD['IgnoreRest'] = 16] = 'IgnoreRest';
 14858         METHOD[METHOD['Native'] = 32] = 'Native';
 14859         METHOD[METHOD['Setsdxns'] = 64] = 'Setsdxns';
 14860         METHOD[METHOD['HasParamNames'] = 128] = 'HasParamNames';
 14861       }(ABC.METHOD || (ABC.METHOD = {})));
 14862       var METHOD = ABC.METHOD;
 14863       (function (TRAIT) {
 14864         TRAIT[TRAIT['Slot'] = 0] = 'Slot';
 14865         TRAIT[TRAIT['Method'] = 1] = 'Method';
 14866         TRAIT[TRAIT['Getter'] = 2] = 'Getter';
 14867         TRAIT[TRAIT['Setter'] = 3] = 'Setter';
 14868         TRAIT[TRAIT['Class'] = 4] = 'Class';
 14869         TRAIT[TRAIT['Function'] = 5] = 'Function';
 14870         TRAIT[TRAIT['Const'] = 6] = 'Const';
 14871       }(ABC.TRAIT || (ABC.TRAIT = {})));
 14872       var TRAIT = ABC.TRAIT;
 14873       (function (ATTR) {
 14874         ATTR[ATTR['Final'] = 1] = 'Final';
 14875         ATTR[ATTR['Override'] = 2] = 'Override';
 14876         ATTR[ATTR['Metadata'] = 4] = 'Metadata';
 14877       }(ABC.ATTR || (ABC.ATTR = {})));
 14878       var ATTR = ABC.ATTR;
 14879       (function (SORT) {
 14880         SORT[SORT['CASEINSENSITIVE'] = 1] = 'CASEINSENSITIVE';
 14881         SORT[SORT['DESCENDING'] = 2] = 'DESCENDING';
 14882         SORT[SORT['UNIQUESORT'] = 4] = 'UNIQUESORT';
 14883         SORT[SORT['RETURNINDEXEDARRAY'] = 8] = 'RETURNINDEXEDARRAY';
 14884         SORT[SORT['NUMERIC'] = 16] = 'NUMERIC';
 14885       }(ABC.SORT || (ABC.SORT = {})));
 14886       var SORT = ABC.SORT;
 14887       (function (OP) {
 14888         OP[OP['bkpt'] = 1] = 'bkpt';
 14889         OP[OP['nop'] = 2] = 'nop';
 14890         OP[OP['throw'] = 3] = 'throw';
 14891         OP[OP['getsuper'] = 4] = 'getsuper';
 14892         OP[OP['setsuper'] = 5] = 'setsuper';
 14893         OP[OP['dxns'] = 6] = 'dxns';
 14894         OP[OP['dxnslate'] = 7] = 'dxnslate';
 14895         OP[OP['kill'] = 8] = 'kill';
 14896         OP[OP['label'] = 9] = 'label';
 14897         OP[OP['lf32x4'] = 10] = 'lf32x4';
 14898         OP[OP['sf32x4'] = 11] = 'sf32x4';
 14899         OP[OP['ifnlt'] = 12] = 'ifnlt';
 14900         OP[OP['ifnle'] = 13] = 'ifnle';
 14901         OP[OP['ifngt'] = 14] = 'ifngt';
 14902         OP[OP['ifnge'] = 15] = 'ifnge';
 14903         OP[OP['jump'] = 16] = 'jump';
 14904         OP[OP['iftrue'] = 17] = 'iftrue';
 14905         OP[OP['iffalse'] = 18] = 'iffalse';
 14906         OP[OP['ifeq'] = 19] = 'ifeq';
 14907         OP[OP['ifne'] = 20] = 'ifne';
 14908         OP[OP['iflt'] = 21] = 'iflt';
 14909         OP[OP['ifle'] = 22] = 'ifle';
 14910         OP[OP['ifgt'] = 23] = 'ifgt';
 14911         OP[OP['ifge'] = 24] = 'ifge';
 14912         OP[OP['ifstricteq'] = 25] = 'ifstricteq';
 14913         OP[OP['ifstrictne'] = 26] = 'ifstrictne';
 14914         OP[OP['lookupswitch'] = 27] = 'lookupswitch';
 14915         OP[OP['pushwith'] = 28] = 'pushwith';
 14916         OP[OP['popscope'] = 29] = 'popscope';
 14917         OP[OP['nextname'] = 30] = 'nextname';
 14918         OP[OP['hasnext'] = 31] = 'hasnext';
 14919         OP[OP['pushnull'] = 32] = 'pushnull';
 14920         OP[OP['c'] = 33] = 'c';
 14921         OP[OP['pushundefined'] = 33] = 'pushundefined';
 14922         OP[OP['pushfloat'] = 34] = 'pushfloat';
 14923         OP[OP['nextvalue'] = 35] = 'nextvalue';
 14924         OP[OP['pushbyte'] = 36] = 'pushbyte';
 14925         OP[OP['pushshort'] = 37] = 'pushshort';
 14926         OP[OP['pushtrue'] = 38] = 'pushtrue';
 14927         OP[OP['pushfalse'] = 39] = 'pushfalse';
 14928         OP[OP['pushnan'] = 40] = 'pushnan';
 14929         OP[OP['pop'] = 41] = 'pop';
 14930         OP[OP['dup'] = 42] = 'dup';
 14931         OP[OP['swap'] = 43] = 'swap';
 14932         OP[OP['pushstring'] = 44] = 'pushstring';
 14933         OP[OP['pushint'] = 45] = 'pushint';
 14934         OP[OP['pushuint'] = 46] = 'pushuint';
 14935         OP[OP['pushdouble'] = 47] = 'pushdouble';
 14936         OP[OP['pushscope'] = 48] = 'pushscope';
 14937         OP[OP['pushnamespace'] = 49] = 'pushnamespace';
 14938         OP[OP['hasnext2'] = 50] = 'hasnext2';
 14939         OP[OP['li8'] = 53] = 'li8';
 14940         OP[OP['li16'] = 54] = 'li16';
 14941         OP[OP['li32'] = 55] = 'li32';
 14942         OP[OP['lf32'] = 56] = 'lf32';
 14943         OP[OP['lf64'] = 57] = 'lf64';
 14944         OP[OP['si8'] = 58] = 'si8';
 14945         OP[OP['si16'] = 59] = 'si16';
 14946         OP[OP['si32'] = 60] = 'si32';
 14947         OP[OP['sf32'] = 61] = 'sf32';
 14948         OP[OP['sf64'] = 62] = 'sf64';
 14949         OP[OP['newfunction'] = 64] = 'newfunction';
 14950         OP[OP['call'] = 65] = 'call';
 14951         OP[OP['construct'] = 66] = 'construct';
 14952         OP[OP['callmethod'] = 67] = 'callmethod';
 14953         OP[OP['callstatic'] = 68] = 'callstatic';
 14954         OP[OP['callsuper'] = 69] = 'callsuper';
 14955         OP[OP['callproperty'] = 70] = 'callproperty';
 14956         OP[OP['returnvoid'] = 71] = 'returnvoid';
 14957         OP[OP['returnvalue'] = 72] = 'returnvalue';
 14958         OP[OP['constructsuper'] = 73] = 'constructsuper';
 14959         OP[OP['constructprop'] = 74] = 'constructprop';
 14960         OP[OP['callsuperid'] = 75] = 'callsuperid';
 14961         OP[OP['callproplex'] = 76] = 'callproplex';
 14962         OP[OP['callinterface'] = 77] = 'callinterface';
 14963         OP[OP['callsupervoid'] = 78] = 'callsupervoid';
 14964         OP[OP['callpropvoid'] = 79] = 'callpropvoid';
 14965         OP[OP['sxi1'] = 80] = 'sxi1';
 14966         OP[OP['sxi8'] = 81] = 'sxi8';
 14967         OP[OP['sxi16'] = 82] = 'sxi16';
 14968         OP[OP['applytype'] = 83] = 'applytype';
 14969         OP[OP['pushfloat4'] = 84] = 'pushfloat4';
 14970         OP[OP['newobject'] = 85] = 'newobject';
 14971         OP[OP['newarray'] = 86] = 'newarray';
 14972         OP[OP['newactivation'] = 87] = 'newactivation';
 14973         OP[OP['newclass'] = 88] = 'newclass';
 14974         OP[OP['getdescendants'] = 89] = 'getdescendants';
 14975         OP[OP['newcatch'] = 90] = 'newcatch';
 14976         OP[OP['findpropstrict'] = 93] = 'findpropstrict';
 14977         OP[OP['findproperty'] = 94] = 'findproperty';
 14978         OP[OP['finddef'] = 95] = 'finddef';
 14979         OP[OP['getlex'] = 96] = 'getlex';
 14980         OP[OP['setproperty'] = 97] = 'setproperty';
 14981         OP[OP['getlocal'] = 98] = 'getlocal';
 14982         OP[OP['setlocal'] = 99] = 'setlocal';
 14983         OP[OP['getglobalscope'] = 100] = 'getglobalscope';
 14984         OP[OP['getscopeobject'] = 101] = 'getscopeobject';
 14985         OP[OP['getproperty'] = 102] = 'getproperty';
 14986         OP[OP['getouterscope'] = 103] = 'getouterscope';
 14987         OP[OP['initproperty'] = 104] = 'initproperty';
 14988         OP[OP['setpropertylate'] = 105] = 'setpropertylate';
 14989         OP[OP['deleteproperty'] = 106] = 'deleteproperty';
 14990         OP[OP['deletepropertylate'] = 107] = 'deletepropertylate';
 14991         OP[OP['getslot'] = 108] = 'getslot';
 14992         OP[OP['setslot'] = 109] = 'setslot';
 14993         OP[OP['getglobalslot'] = 110] = 'getglobalslot';
 14994         OP[OP['setglobalslot'] = 111] = 'setglobalslot';
 14995         OP[OP['convert_s'] = 112] = 'convert_s';
 14996         OP[OP['esc_xelem'] = 113] = 'esc_xelem';
 14997         OP[OP['esc_xattr'] = 114] = 'esc_xattr';
 14998         OP[OP['convert_i'] = 115] = 'convert_i';
 14999         OP[OP['convert_u'] = 116] = 'convert_u';
 15000         OP[OP['convert_d'] = 117] = 'convert_d';
 15001         OP[OP['convert_b'] = 118] = 'convert_b';
 15002         OP[OP['convert_o'] = 119] = 'convert_o';
 15003         OP[OP['checkfilter'] = 120] = 'checkfilter';
 15004         OP[OP['convert_f'] = 121] = 'convert_f';
 15005         OP[OP['unplus'] = 122] = 'unplus';
 15006         OP[OP['convert_f4'] = 123] = 'convert_f4';
 15007         OP[OP['coerce'] = 128] = 'coerce';
 15008         OP[OP['coerce_b'] = 129] = 'coerce_b';
 15009         OP[OP['coerce_a'] = 130] = 'coerce_a';
 15010         OP[OP['coerce_i'] = 131] = 'coerce_i';
 15011         OP[OP['coerce_d'] = 132] = 'coerce_d';
 15012         OP[OP['coerce_s'] = 133] = 'coerce_s';
 15013         OP[OP['astype'] = 134] = 'astype';
 15014         OP[OP['astypelate'] = 135] = 'astypelate';
 15015         OP[OP['coerce_u'] = 136] = 'coerce_u';
 15016         OP[OP['coerce_o'] = 137] = 'coerce_o';
 15017         OP[OP['negate'] = 144] = 'negate';
 15018         OP[OP['increment'] = 145] = 'increment';
 15019         OP[OP['inclocal'] = 146] = 'inclocal';
 15020         OP[OP['decrement'] = 147] = 'decrement';
 15021         OP[OP['declocal'] = 148] = 'declocal';
 15022         OP[OP['typeof'] = 149] = 'typeof';
 15023         OP[OP['not'] = 150] = 'not';
 15024         OP[OP['bitnot'] = 151] = 'bitnot';
 15025         OP[OP['add'] = 160] = 'add';
 15026         OP[OP['subtract'] = 161] = 'subtract';
 15027         OP[OP['multiply'] = 162] = 'multiply';
 15028         OP[OP['divide'] = 163] = 'divide';
 15029         OP[OP['modulo'] = 164] = 'modulo';
 15030         OP[OP['lshift'] = 165] = 'lshift';
 15031         OP[OP['rshift'] = 166] = 'rshift';
 15032         OP[OP['urshift'] = 167] = 'urshift';
 15033         OP[OP['bitand'] = 168] = 'bitand';
 15034         OP[OP['bitor'] = 169] = 'bitor';
 15035         OP[OP['bitxor'] = 170] = 'bitxor';
 15036         OP[OP['equals'] = 171] = 'equals';
 15037         OP[OP['strictequals'] = 172] = 'strictequals';
 15038         OP[OP['lessthan'] = 173] = 'lessthan';
 15039         OP[OP['lessequals'] = 174] = 'lessequals';
 15040         OP[OP['greaterthan'] = 175] = 'greaterthan';
 15041         OP[OP['greaterequals'] = 176] = 'greaterequals';
 15042         OP[OP['instanceof'] = 177] = 'instanceof';
 15043         OP[OP['istype'] = 178] = 'istype';
 15044         OP[OP['istypelate'] = 179] = 'istypelate';
 15045         OP[OP['in'] = 180] = 'in';
 15046         OP[OP['increment_i'] = 192] = 'increment_i';
 15047         OP[OP['decrement_i'] = 193] = 'decrement_i';
 15048         OP[OP['inclocal_i'] = 194] = 'inclocal_i';
 15049         OP[OP['declocal_i'] = 195] = 'declocal_i';
 15050         OP[OP['negate_i'] = 196] = 'negate_i';
 15051         OP[OP['add_i'] = 197] = 'add_i';
 15052         OP[OP['subtract_i'] = 198] = 'subtract_i';
 15053         OP[OP['multiply_i'] = 199] = 'multiply_i';
 15054         OP[OP['getlocal0'] = 208] = 'getlocal0';
 15055         OP[OP['getlocal1'] = 209] = 'getlocal1';
 15056         OP[OP['getlocal2'] = 210] = 'getlocal2';
 15057         OP[OP['getlocal3'] = 211] = 'getlocal3';
 15058         OP[OP['setlocal0'] = 212] = 'setlocal0';
 15059         OP[OP['setlocal1'] = 213] = 'setlocal1';
 15060         OP[OP['setlocal2'] = 214] = 'setlocal2';
 15061         OP[OP['setlocal3'] = 215] = 'setlocal3';
 15062         OP[OP['invalid'] = 237] = 'invalid';
 15063         OP[OP['debug'] = 239] = 'debug';
 15064         OP[OP['debugline'] = 240] = 'debugline';
 15065         OP[OP['debugfile'] = 241] = 'debugfile';
 15066         OP[OP['bkptline'] = 242] = 'bkptline';
 15067         OP[OP['timestamp'] = 243] = 'timestamp';
 15068       }(ABC.OP || (ABC.OP = {})));
 15069       var OP = ABC.OP;
 15070       var ConstantPool = function () {
 15071           function ConstantPool(stream, abc) {
 15072             var n;
 15073             var ints = [
 15075               ];
 15076             n = stream.readU30();
 15077             for (var i = 1; i < n; ++i) {
 15078               ints.push(stream.readS32());
 15080             var uints = [
 15082               ];
 15083             n = stream.readU30();
 15084             for (var i = 1; i < n; ++i) {
 15085               uints.push(stream.readU32());
 15087             var doubles = [
 15088                 NaN
 15089               ];
 15090             n = stream.readU30();
 15091             for (var i = 1; i < n; ++i) {
 15092               doubles.push(stream.readDouble());
 15094             Timer.start('Parse Strings');
 15095             var strings = [
 15096                 ''
 15097               ];
 15098             n = stream.readU30();
 15099             for (var i = 1; i < n; ++i) {
 15100               strings.push(stream.readUTFString(stream.readU30()));
 15102             this.positionAfterUTFStrings = stream.position;
 15103             Timer.stop();
 15104             this.ints = ints;
 15105             this.uints = uints;
 15106             this.doubles = doubles;
 15107             this.strings = strings;
 15108             Timer.start('Parse Namespaces');
 15109             var namespaces = [
 15110                 undefined
 15111               ];
 15112             n = stream.readU30();
 15113             for (var i = 1; i < n; ++i) {
 15114               namespaces.push(Namespace.parse(this, stream, abc.hash + i));
 15116             Timer.stop();
 15117             Timer.start('Parse Namespace Sets');
 15118             var namespaceSets = [
 15119                 undefined
 15120               ];
 15121             n = stream.readU30();
 15122             for (var i = 1; i < n; ++i) {
 15123               var count = stream.readU30();
 15124               var set = [];
 15125               set.runtimeId = ConstantPool._nextNamespaceSetID++;
 15126               for (var j = 0; j < count; ++j) {
 15127                 set.push(namespaces[stream.readU30()]);
 15129               namespaceSets.push(set);
 15131             Timer.stop();
 15132             this.namespaces = namespaces;
 15133             this.namespaceSets = namespaceSets;
 15134             Timer.start('Parse Multinames');
 15135             var multinames = [
 15136                 undefined
 15137               ];
 15138             var patchFactoryTypes = [];
 15139             n = stream.readU30();
 15140             for (var i = 1; i < n; ++i) {
 15141               multinames.push(Multiname.parse(this, stream, multinames, patchFactoryTypes));
 15143             Timer.stop();
 15144             this.multinames = multinames;
 15146           ConstantPool.prototype.getValue = function (kind, index) {
 15147             switch (kind) {
 15148             case 3:
 15149               return this.ints[index];
 15150             case 4:
 15151               return this.uints[index];
 15152             case 6:
 15153               return this.doubles[index];
 15154             case 1:
 15155               return this.strings[index];
 15156             case 11:
 15157               return true;
 15158             case 10:
 15159               return false;
 15160             case 12:
 15161               return null;
 15162             case 0:
 15163               return undefined;
 15164             case 8:
 15165             case 23:
 15166               return this.namespaces[index];
 15167             case 7:
 15168             case 14:
 15169             case 15:
 15170             case 16:
 15171             case 17:
 15172             case 18:
 15173             case 19:
 15174             case 20:
 15175               return this.multinames[index];
 15176             case 2:
 15177               Shumway.Debug.warning('TODO: CONSTANT.Float may be deprecated?');
 15178               break;
 15179             default:
 15180               true;
 15182           };
 15183           ConstantPool._nextNamespaceSetID = 1;
 15184           return ConstantPool;
 15185         }();
 15186       ABC.ConstantPool = ConstantPool;
 15187     }(AVM2.ABC || (AVM2.ABC = {})));
 15188     var ABC = AVM2.ABC;
 15189   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 15190   var AVM2 = Shumway.AVM2;
 15191 }(Shumway || (Shumway = {})));
 15192 var AbcFile = Shumway.AVM2.ABC.AbcFile;
 15193 var AbcStream = Shumway.AVM2.ABC.AbcStream;
 15194 var ConstantPool = Shumway.AVM2.ABC.ConstantPool;
 15195 var ClassInfo = Shumway.AVM2.ABC.ClassInfo;
 15196 var MetaDataInfo = Shumway.AVM2.ABC.MetaDataInfo;
 15197 var InstanceInfo = Shumway.AVM2.ABC.InstanceInfo;
 15198 var ScriptInfo = Shumway.AVM2.ABC.ScriptInfo;
 15199 var Trait = Shumway.AVM2.ABC.Trait;
 15200 var MethodInfo = Shumway.AVM2.ABC.MethodInfo;
 15201 var Multiname = Shumway.AVM2.ABC.Multiname;
 15202 var ASNamespace = Shumway.AVM2.ABC.Namespace;
 15203 var AbcFile = Shumway.AVM2.ABC.AbcFile;
 15204 var AbcStream = Shumway.AVM2.ABC.AbcStream;
 15205 var ConstantPool = Shumway.AVM2.ABC.ConstantPool;
 15206 var ClassInfo = Shumway.AVM2.ABC.ClassInfo;
 15207 var MetaDataInfo = Shumway.AVM2.ABC.MetaDataInfo;
 15208 var InstanceInfo = Shumway.AVM2.ABC.InstanceInfo;
 15209 var ScriptInfo = Shumway.AVM2.ABC.ScriptInfo;
 15210 var Trait = Shumway.AVM2.ABC.Trait;
 15211 var MethodInfo = Shumway.AVM2.ABC.MethodInfo;
 15212 var Multiname = Shumway.AVM2.ABC.Multiname;
 15213 var ASNamespace = Shumway.AVM2.ABC.Namespace;
 15214 var Bytecode = function () {
 15215     function Bytecode(code) {
 15216       var op = code.readU8();
 15217       this.op = op;
 15218       this.originalPosition = code.position;
 15219       var opdesc = Shumway.AVM2.opcodeTable[op];
 15220       if (!opdesc) {
 15221         unexpected('Unknown Op ' + op);
 15223       this.canThrow = opdesc.canThrow;
 15224       var i, n;
 15225       switch (op) {
 15226       case OP_lookupswitch:
 15227         var defaultOffset = code.readS24();
 15228         this.offsets = [];
 15229         var n = code.readU30() + 1;
 15230         for (i = 0; i < n; i++) {
 15231           this.offsets.push(code.readS24());
 15233         this.offsets.push(defaultOffset);
 15234         break;
 15235       default:
 15236         for (i = 0, n = opdesc.operands.length; i < n; i++) {
 15237           var operand = opdesc.operands[i];
 15238           switch (operand.size) {
 15239           case 'u08':
 15240             this[operand.name] = code.readU8();
 15241             break;
 15242           case 's08':
 15243             this[operand.name] = code.readS8();
 15244             break;
 15245           case 's16':
 15246             this[operand.name] = code.readS16();
 15247             break;
 15248           case 's24':
 15249             this[operand.name] = code.readS24();
 15250             break;
 15251           case 'u30':
 15252             this[operand.name] = code.readU30();
 15253             break;
 15254           case 'u32':
 15255             this[operand.name] = code.readU32();
 15256             break;
 15257           default:
 15258             unexpected();
 15263     Bytecode.prototype = {
 15264       makeBlockHead: function makeBlockHead(id) {
 15265         if (this.succs) {
 15266           return id;
 15268         this.bid = id;
 15269         this.succs = [];
 15270         this.preds = [];
 15271         this.dominatees = [];
 15272         return id + 1;
 15273       },
 15274       trace: function trace(writer) {
 15275         if (!this.succs) {
 15276           return;
 15278         writer.writeLn('#' + this.bid);
 15279       },
 15280       toString: function toString(abc) {
 15281         var opDescription = Shumway.AVM2.opcodeTable[this.op];
 15282         var str = opDescription.name.padRight(' ', 20);
 15283         var i, j;
 15284         if (this.op === OP_lookupswitch) {
 15285           str += 'targets:';
 15286           for (i = 0, j = this.targets.length; i < j; i++) {
 15287             str += (i > 0 ? ',' : '') + this.targets[i].position;
 15289         } else {
 15290           for (i = 0, j = opDescription.operands.length; i < j; i++) {
 15291             var operand = opDescription.operands[i];
 15292             if (operand.name === 'offset') {
 15293               str += 'target:' + this.target.position;
 15294             } else {
 15295               str += operand.name + ': ';
 15296               var value = this[operand.name];
 15297               if (abc) {
 15298                 switch (operand.type) {
 15299                 case '':
 15300                   str += value;
 15301                   break;
 15302                 case 'I':
 15303                   str += abc.constantPool.ints[value];
 15304                   break;
 15305                 case 'U':
 15306                   str += abc.constantPool.uints[value];
 15307                   break;
 15308                 case 'D':
 15309                   str += abc.constantPool.doubles[value];
 15310                   break;
 15311                 case 'S':
 15312                   str += abc.constantPool.strings[value];
 15313                   break;
 15314                 case 'N':
 15315                   str += abc.constantPool.namespaces[value];
 15316                   break;
 15317                 case 'CI':
 15318                   str += abc.classes[value];
 15319                   break;
 15320                 case 'M':
 15321                   str += abc.constantPool.multinames[value];
 15322                   break;
 15323                 default:
 15324                   str += '?';
 15325                   break;
 15327               } else {
 15328                 str += value;
 15331             if (i < j - 1) {
 15332               str += ', ';
 15336         return str;
 15338     };
 15339     return Bytecode;
 15340   }();
 15341 var Analysis = function () {
 15342     function blockSetClass(length, blockById) {
 15343       var BlockSet = BitSetFunctor(length);
 15344       var ADDRESS_BITS_PER_WORD = BlockSet.ADDRESS_BITS_PER_WORD;
 15345       var BITS_PER_WORD = BlockSet.BITS_PER_WORD;
 15346       var BIT_INDEX_MASK = BlockSet.BIT_INDEX_MASK;
 15347       BlockSet.singleton = function singleton(b) {
 15348         var bs = new BlockSet();
 15349         bs.set(b.bid);
 15350         bs.count = 1;
 15351         bs.dirty = 0;
 15352         return bs;
 15353       };
 15354       BlockSet.fromBlocks = function fromArray(other) {
 15355         var bs = new BlockSet();
 15356         bs.setBlocks(other);
 15357         return bs;
 15358       };
 15359       var Bsp = BlockSet.prototype;
 15360       if (BlockSet.singleword) {
 15361         Bsp.forEachBlock = function forEach(fn) {
 15362           true;
 15363           var byId = blockById;
 15364           var word = this.bits;
 15365           if (word) {
 15366             for (var k = 0; k < BITS_PER_WORD; k++) {
 15367               if (word & 1 << k) {
 15368                 fn(byId[k]);
 15372         };
 15373         Bsp.choose = function choose() {
 15374           var byId = blockById;
 15375           var word = this.bits;
 15376           if (word) {
 15377             for (var k = 0; k < BITS_PER_WORD; k++) {
 15378               if (word & 1 << k) {
 15379                 return byId[k];
 15383         };
 15384         Bsp.members = function members() {
 15385           var byId = blockById;
 15386           var set = [];
 15387           var word = this.bits;
 15388           if (word) {
 15389             for (var k = 0; k < BITS_PER_WORD; k++) {
 15390               if (word & 1 << k) {
 15391                 set.push(byId[k]);
 15395           return set;
 15396         };
 15397         Bsp.setBlocks = function setBlocks(bs) {
 15398           var bits = this.bits;
 15399           for (var i = 0, j = bs.length; i < j; i++) {
 15400             var id = bs[i].bid;
 15401             bits |= 1 << (id & BIT_INDEX_MASK);
 15403           this.bits = bits;
 15404         };
 15405       } else {
 15406         Bsp.forEachBlock = function forEach(fn) {
 15407           true;
 15408           var byId = blockById;
 15409           var bits = this.bits;
 15410           for (var i = 0, j = bits.length; i < j; i++) {
 15411             var word = bits[i];
 15412             if (word) {
 15413               for (var k = 0; k < BITS_PER_WORD; k++) {
 15414                 if (word & 1 << k) {
 15415                   fn(byId[i * BITS_PER_WORD + k]);
 15420         };
 15421         Bsp.choose = function choose() {
 15422           var byId = blockById;
 15423           var bits = this.bits;
 15424           for (var i = 0, j = bits.length; i < j; i++) {
 15425             var word = bits[i];
 15426             if (word) {
 15427               for (var k = 0; k < BITS_PER_WORD; k++) {
 15428                 if (word & 1 << k) {
 15429                   return byId[i * BITS_PER_WORD + k];
 15434         };
 15435         Bsp.members = function members() {
 15436           var byId = blockById;
 15437           var set = [];
 15438           var bits = this.bits;
 15439           for (var i = 0, j = bits.length; i < j; i++) {
 15440             var word = bits[i];
 15441             if (word) {
 15442               for (var k = 0; k < BITS_PER_WORD; k++) {
 15443                 if (word & 1 << k) {
 15444                   set.push(byId[i * BITS_PER_WORD + k]);
 15449           return set;
 15450         };
 15451         Bsp.setBlocks = function setBlocks(bs) {
 15452           var bits = this.bits;
 15453           for (var i = 0, j = bs.length; i < j; i++) {
 15454             var id = bs[i].bid;
 15455             bits[id >> ADDRESS_BITS_PER_WORD] |= 1 << (id & BIT_INDEX_MASK);
 15457         };
 15459       return BlockSet;
 15461     function Analysis(method) {
 15462       Counter.count('Analysis');
 15463       this.method = method;
 15464       if (this.method.code) {
 15465         Timer.start('Normalize');
 15466         this.normalizeBytecode();
 15467         Timer.stop();
 15470     Analysis.prototype = {
 15471       normalizeBytecode: function normalizeBytecode() {
 15472         function getInvalidTarget(cache, offset) {
 15473           if (cache && cache[offset]) {
 15474             return cache[offset];
 15476           var code = Object.create(Bytecode.prototype);
 15477           code.op = OP_invalid;
 15478           code.position = offset;
 15479           cache && (cache[offset] = code);
 15480           return code;
 15482         var method = this.method;
 15483         function accessLocal(index) {
 15484           if (index-- === 0)
 15485             return;
 15486           if (index < method.parameters.length) {
 15487             method.parameters[index].isUsed = true;
 15490         var bytecodesOffset = [];
 15491         var bytecodes = [];
 15492         var codeStream = new AbcStream(this.method.code);
 15493         var code;
 15494         while (codeStream.remaining() > 0) {
 15495           var pos = codeStream.position;
 15496           code = new Bytecode(codeStream);
 15497           switch (code.op) {
 15498           case OP_nop:
 15499           case OP_label:
 15500             bytecodesOffset[pos] = bytecodes.length;
 15501             continue;
 15502           case OP_lookupswitch:
 15503             this.method.hasLookupSwitches = true;
 15504             code.targets = [];
 15505             var offsets = code.offsets;
 15506             for (var i = 0, j = offsets.length; i < j; i++) {
 15507               offsets[i] += pos;
 15509             break;
 15510           case OP_jump:
 15511           case OP_iflt:
 15512           case OP_ifnlt:
 15513           case OP_ifle:
 15514           case OP_ifnle:
 15515           case OP_ifgt:
 15516           case OP_ifngt:
 15517           case OP_ifge:
 15518           case OP_ifnge:
 15519           case OP_ifeq:
 15520           case OP_ifne:
 15521           case OP_ifstricteq:
 15522           case OP_ifstrictne:
 15523           case OP_iftrue:
 15524           case OP_iffalse:
 15525             code.offset += codeStream.position;
 15526             break;
 15527           case OP_getlocal0:
 15528           case OP_getlocal1:
 15529           case OP_getlocal2:
 15530           case OP_getlocal3:
 15531             accessLocal(code.op - OP_getlocal0);
 15532             break;
 15533           case OP_getlocal:
 15534             accessLocal(code.index);
 15535             break;
 15536           default:
 15537             break;
 15539           code.position = bytecodes.length;
 15540           bytecodesOffset[pos] = bytecodes.length;
 15541           bytecodes.push(code);
 15543         var invalidJumps = {};
 15544         var newOffset;
 15545         for (var pc = 0, end = bytecodes.length; pc < end; pc++) {
 15546           code = bytecodes[pc];
 15547           switch (code.op) {
 15548           case OP_lookupswitch:
 15549             var offsets = code.offsets;
 15550             for (var i = 0, j = offsets.length; i < j; i++) {
 15551               newOffset = bytecodesOffset[offsets[i]];
 15552               code.targets.push(bytecodes[newOffset] || getInvalidTarget(invalidJumps, offsets[i]));
 15553               offsets[i] = newOffset;
 15555             break;
 15556           case OP_jump:
 15557           case OP_iflt:
 15558           case OP_ifnlt:
 15559           case OP_ifle:
 15560           case OP_ifnle:
 15561           case OP_ifgt:
 15562           case OP_ifngt:
 15563           case OP_ifge:
 15564           case OP_ifnge:
 15565           case OP_ifeq:
 15566           case OP_ifne:
 15567           case OP_ifstricteq:
 15568           case OP_ifstrictne:
 15569           case OP_iftrue:
 15570           case OP_iffalse:
 15571             newOffset = bytecodesOffset[code.offset];
 15572             code.target = bytecodes[newOffset] || getInvalidTarget(invalidJumps, code.offset);
 15573             code.offset = newOffset;
 15574             break;
 15575           default:
 15578         this.bytecodes = bytecodes;
 15579         var exceptions = this.method.exceptions;
 15580         for (var i = 0, j = exceptions.length; i < j; i++) {
 15581           var ex = exceptions[i];
 15582           ex.start = bytecodesOffset[ex.start];
 15583           ex.end = bytecodesOffset[ex.end];
 15584           ex.offset = bytecodesOffset[ex.target];
 15585           ex.target = bytecodes[ex.offset];
 15586           ex.target.exception = ex;
 15588       },
 15589       detectBasicBlocks: function detectBasicBlocks() {
 15590         var bytecodes = this.bytecodes;
 15591         var exceptions = this.method.exceptions;
 15592         var hasExceptions = exceptions.length > 0;
 15593         var blockById = {};
 15594         var code;
 15595         var pc, end;
 15596         var id = 0;
 15597         function tryTargets(block) {
 15598           var targets = [];
 15599           for (var i = 0, j = exceptions.length; i < j; i++) {
 15600             var ex = exceptions[i];
 15601             if (block.position >= ex.start && block.end.position <= ex.end) {
 15602               targets.push(ex.target);
 15605           return targets;
 15607         id = bytecodes[0].makeBlockHead(id);
 15608         for (pc = 0, end = bytecodes.length - 1; pc < end; pc++) {
 15609           code = bytecodes[pc];
 15610           switch (code.op) {
 15611           case OP_returnvoid:
 15612           case OP_returnvalue:
 15613           case OP_throw:
 15614             id = bytecodes[pc + 1].makeBlockHead(id);
 15615             break;
 15616           case OP_lookupswitch:
 15617             var targets = code.targets;
 15618             for (var i = 0, j = targets.length; i < j; i++) {
 15619               id = targets[i].makeBlockHead(id);
 15621             id = bytecodes[pc + 1].makeBlockHead(id);
 15622             break;
 15623           case OP_jump:
 15624           case OP_iflt:
 15625           case OP_ifnlt:
 15626           case OP_ifle:
 15627           case OP_ifnle:
 15628           case OP_ifgt:
 15629           case OP_ifngt:
 15630           case OP_ifge:
 15631           case OP_ifnge:
 15632           case OP_ifeq:
 15633           case OP_ifne:
 15634           case OP_ifstricteq:
 15635           case OP_ifstrictne:
 15636           case OP_iftrue:
 15637           case OP_iffalse:
 15638             id = code.target.makeBlockHead(id);
 15639             id = bytecodes[pc + 1].makeBlockHead(id);
 15640             break;
 15641           default:
 15644         code = bytecodes[end];
 15645         switch (code.op) {
 15646         case OP_returnvoid:
 15647         case OP_returnvalue:
 15648         case OP_throw:
 15649           break;
 15650         case OP_lookupswitch:
 15651           var targets = code.targets;
 15652           for (var i = 0, j = targets.length; i < j; i++) {
 15653             id = targets[i].makeBlockHead(id);
 15655           break;
 15656         case OP_jump:
 15657           id = code.target.makeBlockHead(id);
 15658           break;
 15659         case OP_iflt:
 15660         case OP_ifnlt:
 15661         case OP_ifle:
 15662         case OP_ifnle:
 15663         case OP_ifgt:
 15664         case OP_ifngt:
 15665         case OP_ifge:
 15666         case OP_ifnge:
 15667         case OP_ifeq:
 15668         case OP_ifne:
 15669         case OP_ifstricteq:
 15670         case OP_ifstrictne:
 15671         case OP_iftrue:
 15672         case OP_iffalse:
 15673           id = code.target.makeBlockHead(id);
 15674           bytecodes[pc + 1] = getInvalidTarget(null, pc + 1);
 15675           id = bytecodes[pc + 1].makeBlockHead(id);
 15676           break;
 15677         default:
 15679         if (hasExceptions) {
 15680           for (var i = 0, j = exceptions.length; i < j; i++) {
 15681             var ex = exceptions[i];
 15682             var tryStart = bytecodes[ex.start];
 15683             var afterTry = bytecodes[ex.end + 1];
 15684             id = tryStart.makeBlockHead(id);
 15685             if (afterTry) {
 15686               id = afterTry.makeBlockHead(id);
 15688             id = ex.target.makeBlockHead(id);
 15691         var currentBlock = bytecodes[0];
 15692         for (pc = 1, end = bytecodes.length; pc < end; pc++) {
 15693           if (!bytecodes[pc].succs) {
 15694             continue;
 15696           true;
 15697           blockById[currentBlock.bid] = currentBlock;
 15698           code = bytecodes[pc - 1];
 15699           currentBlock.end = code;
 15700           var nextBlock = bytecodes[pc];
 15701           switch (code.op) {
 15702           case OP_returnvoid:
 15703           case OP_returnvalue:
 15704           case OP_throw:
 15705             break;
 15706           case OP_lookupswitch:
 15707             for (var i = 0, j = code.targets.length; i < j; i++) {
 15708               currentBlock.succs.push(code.targets[i]);
 15710             break;
 15711           case OP_jump:
 15712             currentBlock.succs.push(code.target);
 15713             break;
 15714           case OP_iflt:
 15715           case OP_ifnlt:
 15716           case OP_ifle:
 15717           case OP_ifnle:
 15718           case OP_ifgt:
 15719           case OP_ifngt:
 15720           case OP_ifge:
 15721           case OP_ifnge:
 15722           case OP_ifeq:
 15723           case OP_ifne:
 15724           case OP_ifstricteq:
 15725           case OP_ifstrictne:
 15726           case OP_iftrue:
 15727           case OP_iffalse:
 15728             currentBlock.succs.push(code.target);
 15729             if (code.target !== nextBlock) {
 15730               currentBlock.succs.push(nextBlock);
 15732             break;
 15733           default:
 15734             currentBlock.succs.push(nextBlock);
 15736           if (hasExceptions) {
 15737             var targets = tryTargets(currentBlock);
 15738             currentBlock.hasCatches = targets.length > 0;
 15739             currentBlock.succs.push.apply(currentBlock.succs, targets);
 15741           currentBlock = nextBlock;
 15743         blockById[currentBlock.bid] = currentBlock;
 15744         code = bytecodes[end - 1];
 15745         switch (code.op) {
 15746         case OP_lookupswitch:
 15747           for (var i = 0, j = code.targets.length; i < j; i++) {
 15748             currentBlock.succs.push(code.targets[i]);
 15750           break;
 15751         case OP_jump:
 15752           currentBlock.succs.push(code.target);
 15753           break;
 15754         default:
 15756         currentBlock.end = code;
 15757         this.BlockSet = blockSetClass(id, blockById);
 15758       },
 15759       normalizeReachableBlocks: function normalizeReachableBlocks() {
 15760         var root = this.bytecodes[0];
 15761         true;
 15762         var ONCE = 1;
 15763         var BUNCH_OF_TIMES = 2;
 15764         var BlockSet = this.BlockSet;
 15765         var blocks = [];
 15766         var visited = {};
 15767         var ancestors = {};
 15768         var worklist = [
 15769             root
 15770           ];
 15771         var node;
 15772         ancestors[root.bid] = true;
 15773         while (node = worklist.top()) {
 15774           if (visited[node.bid]) {
 15775             if (visited[node.bid] === ONCE) {
 15776               visited[node.bid] = BUNCH_OF_TIMES;
 15777               blocks.push(node);
 15778               var succs = node.succs;
 15779               for (var i = 0, j = succs.length; i < j; i++) {
 15780                 succs[i].preds.push(node);
 15783             ancestors[node.bid] = false;
 15784             worklist.pop();
 15785             continue;
 15787           visited[node.bid] = ONCE;
 15788           ancestors[node.bid] = true;
 15789           var succs = node.succs;
 15790           for (var i = 0, j = succs.length; i < j; i++) {
 15791             var s = succs[i];
 15792             if (ancestors[s.bid]) {
 15793               if (!node.spbacks) {
 15794                 node.spbacks = new BlockSet();
 15796               node.spbacks.set(s.bid);
 15798             !visited[s.bid] && worklist.push(s);
 15801         this.blocks = blocks.reverse();
 15802       },
 15803       computeDominance: function computeDominance() {
 15804         function intersectDominators(doms, b1, b2) {
 15805           var finger1 = b1;
 15806           var finger2 = b2;
 15807           while (finger1 !== finger2) {
 15808             while (finger1 > finger2) {
 15809               finger1 = doms[finger1];
 15811             while (finger2 > finger1) {
 15812               finger2 = doms[finger2];
 15815           return finger1;
 15817         var blocks = this.blocks;
 15818         var n = blocks.length;
 15819         var doms = new Array(n);
 15820         doms[0] = 0;
 15821         var rpo = {};
 15822         for (var b = 0; b < n; b++) {
 15823           rpo[blocks[b].bid] = b;
 15825         var changed = true;
 15826         while (changed) {
 15827           changed = false;
 15828           for (var b = 1; b < n; b++) {
 15829             var preds = blocks[b].preds;
 15830             var j = preds.length;
 15831             var newIdom = rpo[preds[0].bid];
 15832             if (!(newIdom in doms)) {
 15833               for (var i = 1; i < j; i++) {
 15834                 newIdom = rpo[preds[i].bid];
 15835                 if (newIdom in doms) {
 15836                   break;
 15840             true;
 15841             for (var i = 0; i < j; i++) {
 15842               var p = rpo[preds[i].bid];
 15843               if (p === newIdom) {
 15844                 continue;
 15846               if (p in doms) {
 15847                 newIdom = intersectDominators(doms, p, newIdom);
 15850             if (doms[b] !== newIdom) {
 15851               doms[b] = newIdom;
 15852               changed = true;
 15856         blocks[0].dominator = blocks[0];
 15857         var block;
 15858         for (var b = 1; b < n; b++) {
 15859           block = blocks[b];
 15860           var idom = blocks[doms[b]];
 15861           block.dominator = idom;
 15862           idom.dominatees.push(block);
 15863           block.npreds = block.preds.length;
 15865         var worklist = [
 15866             blocks[0]
 15867           ];
 15868         blocks[0].level || (blocks[0].level = 0);
 15869         while (block = worklist.shift()) {
 15870           var dominatees = block.dominatees;
 15871           for (var i = 0, j = dominatees.length; i < j; i++) {
 15872             dominatees[i].level = block.level + 1;
 15874           worklist.push.apply(worklist, dominatees);
 15876       },
 15877       analyzeControlFlow: function analyzeControlFlow() {
 15878         true;
 15879         this.detectBasicBlocks();
 15880         this.normalizeReachableBlocks();
 15881         this.computeDominance();
 15882         this.analyzedControlFlow = true;
 15883         return true;
 15884       },
 15885       markLoops: function markLoops() {
 15886         if (!this.analyzedControlFlow && !this.analyzeControlFlow()) {
 15887           return false;
 15889         var BlockSet = this.BlockSet;
 15890         function findSCCs(root) {
 15891           var preorderId = 1;
 15892           var preorder = {};
 15893           var assigned = {};
 15894           var unconnectedNodes = [];
 15895           var pendingNodes = [];
 15896           var sccs = [];
 15897           var level = root.level + 1;
 15898           var worklist = [
 15899               root
 15900             ];
 15901           var node;
 15902           var u, s;
 15903           while (node = worklist.top()) {
 15904             if (preorder[node.bid]) {
 15905               if (pendingNodes.peek() === node) {
 15906                 pendingNodes.pop();
 15907                 var scc = [];
 15908                 do {
 15909                   u = unconnectedNodes.pop();
 15910                   assigned[u.bid] = true;
 15911                   scc.push(u);
 15912                 } while (u !== node);
 15913                 if (scc.length > 1 || u.spbacks && u.spbacks.get(u.bid)) {
 15914                   sccs.push(scc);
 15917               worklist.pop();
 15918               continue;
 15920             preorder[node.bid] = preorderId++;
 15921             unconnectedNodes.push(node);
 15922             pendingNodes.push(node);
 15923             var succs = node.succs;
 15924             for (var i = 0, j = succs.length; i < j; i++) {
 15925               s = succs[i];
 15926               if (s.level < level) {
 15927                 continue;
 15929               var sid = s.bid;
 15930               if (!preorder[sid]) {
 15931                 worklist.push(s);
 15932               } else if (!assigned[sid]) {
 15933                 while (preorder[pendingNodes.peek().bid] > preorder[sid]) {
 15934                   pendingNodes.pop();
 15939           return sccs;
 15941         function findLoopHeads(blocks) {
 15942           var heads = new BlockSet();
 15943           for (var i = 0, j = blocks.length; i < j; i++) {
 15944             var block = blocks[i];
 15945             var spbacks = block.spbacks;
 15946             if (!spbacks) {
 15947               continue;
 15949             var succs = block.succs;
 15950             for (var k = 0, l = succs.length; k < l; k++) {
 15951               var s = succs[k];
 15952               if (spbacks.get(s.bid)) {
 15953                 heads.set(s.dominator.bid);
 15957           return heads.members();
 15959         function LoopInfo(scc, loopId) {
 15960           var body = new BlockSet();
 15961           body.setBlocks(scc);
 15962           body.recount();
 15963           this.id = loopId;
 15964           this.body = body;
 15965           this.exit = new BlockSet();
 15966           this.save = {};
 15967           this.head = new BlockSet();
 15968           this.npreds = 0;
 15970         var heads = findLoopHeads(this.blocks);
 15971         if (heads.length <= 0) {
 15972           this.markedLoops = true;
 15973           return true;
 15975         var worklist = heads.sort(function (a, b) {
 15976             return a.level - b.level;
 15977           });
 15978         var loopId = 0;
 15979         for (var n = worklist.length - 1; n >= 0; n--) {
 15980           var top = worklist[n];
 15981           var sccs = findSCCs(top);
 15982           if (sccs.length === 0) {
 15983             continue;
 15985           for (var i = 0, j = sccs.length; i < j; i++) {
 15986             var scc = sccs[i];
 15987             var loop = new LoopInfo(scc, loopId++);
 15988             for (var k = 0, l = scc.length; k < l; k++) {
 15989               var h = scc[k];
 15990               if (h.level === top.level + 1 && !h.loop) {
 15991                 h.loop = loop;
 15992                 loop.head.set(h.bid);
 15993                 var preds = h.preds;
 15994                 for (var pi = 0, pj = preds.length; pi < pj; pi++) {
 15995                   loop.body.get(preds[pi].bid) && h.npreds--;
 15997                 loop.npreds += h.npreds;
 16000             for (var k = 0, l = scc.length; k < l; k++) {
 16001               var h = scc[k];
 16002               if (h.level === top.level + 1) {
 16003                 h.npreds = loop.npreds;
 16006             loop.head.recount();
 16009         this.markedLoops = true;
 16010         return true;
 16012     };
 16013     return Analysis;
 16014   }();
 16015 (function (exports) {
 16016   var lang = exports.lang = {
 16017       Node: {},
 16018       Program: {
 16019         extends: 'Node',
 16020         fields: [
 16021           '@body'
 16023       },
 16024       Statement: {
 16025         extends: 'Node'
 16026       },
 16027       EmptyStatement: {
 16028         extends: 'Statement'
 16029       },
 16030       BlockStatement: {
 16031         extends: 'Statement',
 16032         fields: [
 16033           '@body'
 16035       },
 16036       ExpressionStatement: {
 16037         extends: 'Statement',
 16038         fields: [
 16039           '@expression'
 16041       },
 16042       IfStatement: {
 16043         extends: 'Statement',
 16044         fields: [
 16045           '@test',
 16046           '@consequent',
 16047           '@alternate'
 16049       },
 16050       LabeledStatement: {
 16051         extends: 'Statement',
 16052         fields: [
 16053           '@label',
 16054           '@body'
 16056       },
 16057       BreakStatement: {
 16058         extends: 'Statement',
 16059         fields: [
 16060           '@label'
 16062       },
 16063       ContinueStatement: {
 16064         extends: 'Statement',
 16065         fields: [
 16066           '@label'
 16068       },
 16069       WithStatement: {
 16070         extends: 'Statement',
 16071         fields: [
 16072           '@object',
 16073           '@body'
 16075       },
 16076       SwitchStatement: {
 16077         extends: 'Statement',
 16078         fields: [
 16079           '@discriminant',
 16080           '@cases',
 16081           'lexical'
 16083       },
 16084       ReturnStatement: {
 16085         extends: 'Statement',
 16086         fields: [
 16087           '@argument'
 16089       },
 16090       ThrowStatement: {
 16091         extends: 'Statement',
 16092         fields: [
 16093           '@argument'
 16095       },
 16096       TryStatement: {
 16097         extends: 'Statement',
 16098         fields: [
 16099           '@block',
 16100           '@handlers',
 16101           '@finalizer'
 16103       },
 16104       WhileStatement: {
 16105         extends: 'Statement',
 16106         fields: [
 16107           '@test',
 16108           '@body'
 16110       },
 16111       DoWhileStatement: {
 16112         extends: 'Statement',
 16113         fields: [
 16114           '@body',
 16115           '@test'
 16117       },
 16118       ForStatement: {
 16119         extends: 'Statement',
 16120         fields: [
 16121           '@init',
 16122           '@test',
 16123           '@update',
 16124           '@body'
 16126       },
 16127       ForInStatement: {
 16128         extends: 'Statement',
 16129         fields: [
 16130           '@left',
 16131           '@right',
 16132           '@body',
 16133           'each'
 16135       },
 16136       LetStatement: {
 16137         extends: 'Statement',
 16138         fields: [
 16139           '@head',
 16140           '@body'
 16142       },
 16143       DebuggerStatement: {
 16144         extends: 'Statement'
 16145       },
 16146       Declaration: {
 16147         extends: 'Statement'
 16148       },
 16149       FunctionDeclaration: {
 16150         extends: 'Declaration',
 16151         fields: [
 16152           '@id',
 16153           '@params',
 16154           '@body',
 16155           '@decltype',
 16156           'generator',
 16157           'expression',
 16158           '@modifiers'
 16160       },
 16161       VariableDeclaration: {
 16162         extends: 'Declaration',
 16163         fields: [
 16164           'kind',
 16165           '@declarations'
 16167       },
 16168       VariableDeclarator: {
 16169         extends: 'Node',
 16170         fields: [
 16171           '@id',
 16172           '@init',
 16173           '@decltype',
 16174           '@arguments'
 16176       },
 16177       Expression: {
 16178         extends: 'Pattern'
 16179       },
 16180       ThisExpression: {
 16181         extends: 'Expression'
 16182       },
 16183       ArrayExpression: {
 16184         extends: 'Expression',
 16185         fields: [
 16186           '@elements'
 16188       },
 16189       ObjectExpression: {
 16190         extends: 'Expression',
 16191         fields: [
 16192           '@properties'
 16194       },
 16195       Property: {
 16196         extends: 'Node',
 16197         fields: [
 16198           '@key',
 16199           '@value',
 16200           'kind'
 16202       },
 16203       FunctionExpression: {
 16204         extends: 'Expression',
 16205         fields: [
 16206           '@id',
 16207           '@params',
 16208           '@body',
 16209           '@decltype',
 16210           'generator',
 16211           'expression'
 16213       },
 16214       SequenceExpression: {
 16215         extends: 'Expression',
 16216         fields: [
 16217           '@expressions'
 16219       },
 16220       UnaryExpression: {
 16221         extends: 'Expression',
 16222         fields: [
 16223           'operator',
 16224           '@argument',
 16225           'prefix'
 16227       },
 16228       BinaryExpression: {
 16229         extends: 'Expression',
 16230         fields: [
 16231           'operator',
 16232           '@left',
 16233           '@right'
 16235       },
 16236       AssignmentExpression: {
 16237         extends: 'Expression',
 16238         fields: [
 16239           '@left',
 16240           'operator',
 16241           '@right'
 16243       },
 16244       UpdateExpression: {
 16245         extends: 'Expression',
 16246         fields: [
 16247           'operator',
 16248           '@argument',
 16249           'prefix'
 16251       },
 16252       LogicalExpression: {
 16253         extends: 'Expression',
 16254         fields: [
 16255           'operator',
 16256           '@left',
 16257           '@right'
 16259       },
 16260       ConditionalExpression: {
 16261         extends: 'Expression',
 16262         fields: [
 16263           '@test',
 16264           '@consequent',
 16265           '@alternate'
 16267       },
 16268       NewExpression: {
 16269         extends: 'Expression',
 16270         fields: [
 16271           '@callee',
 16272           '@arguments'
 16274       },
 16275       CallExpression: {
 16276         extends: 'Expression',
 16277         fields: [
 16278           '@callee',
 16279           '@arguments'
 16281       },
 16282       MemberExpression: {
 16283         extends: 'Expression',
 16284         fields: [
 16285           '@object',
 16286           '@property',
 16287           'computed',
 16288           'kind'
 16290       },
 16291       YieldExpression: {
 16292         extends: 'Expression',
 16293         fields: [
 16294           '@argument'
 16296       },
 16297       ComprehensionExpression: {
 16298         extends: 'Expression',
 16299         fields: [
 16300           '@blocks',
 16301           '@filter'
 16303       },
 16304       GeneratorExpression: {
 16305         extends: 'Expression',
 16306         fields: [
 16307           '@blocks',
 16308           '@filter'
 16310       },
 16311       LetExpression: {
 16312         extends: 'Expression',
 16313         fields: [
 16314           '@head',
 16315           '@body'
 16317       },
 16318       Pattern: {
 16319         extends: 'Node'
 16320       },
 16321       ObjectPattern: {
 16322         extends: 'Pattern',
 16323         fields: [
 16324           '@properties'
 16326       },
 16327       ArrayPattern: {
 16328         extends: 'Pattern',
 16329         fields: [
 16330           '@elements'
 16332       },
 16333       SwitchCase: {
 16334         extends: 'Node',
 16335         fields: [
 16336           '@test',
 16337           '@consequent'
 16339       },
 16340       CatchClause: {
 16341         extends: 'Node',
 16342         fields: [
 16343           '@param',
 16344           '@guard',
 16345           '@body'
 16347       },
 16348       Identifier: {
 16349         extends: 'Expression',
 16350         fields: [
 16351           'name',
 16352           'kind'
 16354       },
 16355       Literal: {
 16356         extends: 'Expression',
 16357         fields: [
 16358           'value'
 16360       },
 16361       Type: {
 16362         extends: 'Node'
 16363       },
 16364       PointerType: {
 16365         extends: 'Type',
 16366         fields: [
 16367           '@base'
 16369       },
 16370       ArrayType: {
 16371         extends: 'PointerType',
 16372         fields: [
 16373           'length'
 16375       },
 16376       StructType: {
 16377         extends: 'Type',
 16378         fields: [
 16379           '@id',
 16380           '@members',
 16381           'isUnion'
 16383       },
 16384       MemberDeclarator: {
 16385         extends: 'Node',
 16386         fields: [
 16387           'modifiers',
 16388           '@declarator'
 16390       },
 16391       ArrowType: {
 16392         extends: 'Type',
 16393         fields: [
 16394           '@params',
 16395           '@return'
 16397       },
 16398       TypeIdentifier: {
 16399         extends: 'Type',
 16400         fields: [
 16401           'name'
 16403       },
 16404       TypeAliasDirective: {
 16405         extends: 'Node',
 16406         fields: [
 16407           '@original',
 16408           '@alias'
 16410       },
 16411       CastExpression: {
 16412         extends: 'Expression',
 16413         fields: [
 16414           '@as',
 16415           '@argument'
 16418     };
 16419   function allFields(spec) {
 16420     var fields = [
 16421         'leadingComments',
 16422         'loc'
 16423       ];
 16424     while (spec) {
 16425       if (spec.fields) {
 16426         fields = spec.fields.concat(fields);
 16428       spec = spec.extends ? lang[spec.extends] : null;
 16430     return fields;
 16433   exports.allFields = allFields;
 16434   function prefixUnderscore(s) {
 16435     return '_' + s;
 16437   function ensureConstructor(name, spec) {
 16438     if (!exports[name]) {
 16439       var fields = allFields(spec);
 16440       var children = [];
 16441       var body = [
 16442           'this.type = "' + name + '";'
 16443         ];
 16444       for (var i = 0, j = fields.length; i < j; i++) {
 16445         var fname = fields[i];
 16446         if (fname.charAt(0) === '@') {
 16447           fields[i] = fname = fname.substr(1);
 16448           children.push(fname);
 16450         body.push('this.' + fname + ' = _' + fname + ';');
 16452       var node = new Function(fields.map(prefixUnderscore), body.join('\n'));
 16453       if (spec.extends) {
 16454         var pnode = ensureConstructor(spec.extends, lang[spec.extends]);
 16455         node.prototype = Object.create(pnode.prototype);
 16457       Object.defineProperty(node.prototype, '_children', {
 16458         value: children,
 16459         writable: true,
 16460         configurable: true,
 16461         enumerable: false
 16462       });
 16463       exports[name] = node;
 16465     return exports[name];
 16467   for (var name in lang) {
 16468     ensureConstructor(name, lang[name]);
 16470   exports.makePass = function makePass(name, prop) {
 16471     return function (o) {
 16472       var trans, arr;
 16473       var child, children = this._children;
 16474       for (var i = 0, j = children.length; i < j; i++) {
 16475         if (!(child = this[children[i]])) {
 16476           continue;
 16478         if (child instanceof Array) {
 16479           arr = this[children[i]] = [];
 16480           for (var k = 0, l = child.length; k < l; k++) {
 16481             if (!child[k]) {
 16482               arr.push(child[k]);
 16483             } else if (typeof child[k][name] === 'function') {
 16484               trans = child[k][name](o);
 16485               if (trans !== null) {
 16486                 arr.push(trans);
 16490         } else if (typeof child[name] === 'function') {
 16491           trans = child[name](o);
 16492           if (trans === null) {
 16493             this[children[i]] = undefined;
 16494           } else {
 16495             this[children[i]] = trans;
 16499       if (typeof this[prop] === 'function') {
 16500         if (o.logger && typeof this.loc !== 'undefined') {
 16501           o.logger.push(this);
 16502           trans = this[prop](o);
 16503           o.logger.pop();
 16504         } else {
 16505           trans = this[prop](o);
 16507         if (trans === null) {
 16508           return null;
 16510         return trans ? trans : this;
 16512       return this;
 16513     };
 16514   };
 16515   exports.makePass = function makePass(name, prop, backward) {
 16516     return function (o) {
 16517       var trans, arr;
 16518       var child, children = this._children;
 16519       var i, k;
 16520       for (var x = 0, j = children.length; x < j; x++) {
 16521         i = backward ? children.length - 1 - x : x;
 16522         if (!(child = this[children[i]])) {
 16523           continue;
 16525         if (child instanceof Array) {
 16526           arr = this[children[i]] = [];
 16527           var y;
 16528           for (var y = 0, l = child.length; y < l; y++) {
 16529             k = backward ? child.length - 1 - y : y;
 16530             if (!child[k]) {
 16531               if (backward) {
 16532                 arr.unshift(child[k]);
 16533               } else {
 16534                 arr.push(child[k]);
 16536             } else if (typeof child[k][name] === 'function') {
 16537               trans = child[k][name](o);
 16538               if (trans !== null) {
 16539                 if (backward) {
 16540                   arr.unshift(trans);
 16541                 } else {
 16542                   arr.push(trans);
 16547         } else if (typeof child[name] === 'function') {
 16548           trans = child[name](o);
 16549           if (trans === null) {
 16550             this[children[i]] = undefined;
 16551           } else {
 16552             this[children[i]] = trans;
 16556       if (typeof this[prop] === 'function') {
 16557         if (o.logger && typeof this.loc !== 'undefined') {
 16558           o.logger.push(this);
 16559           trans = this[prop](o);
 16560           o.logger.pop();
 16561         } else {
 16562           trans = this[prop](o);
 16564         if (trans === null) {
 16565           return null;
 16567         return trans ? trans : this;
 16569       return this;
 16570     };
 16571   };
 16572   exports.lift = function lift(raw) {
 16573     if (!raw) {
 16574       return raw;
 16576     if (raw instanceof Array) {
 16577       return raw.map(function (r) {
 16578         return r ? lift(r) : r;
 16579       });
 16581     var type = raw.type;
 16582     var Node = exports[type];
 16583     if (!Node) {
 16584       throw new Error('unknown node type `' + type + '\'');
 16586     var node = new Node();
 16587     node.loc = raw.loc;
 16588     var fields = allFields(lang[type]);
 16589     for (var i = 0, j = fields.length; i < j; i++) {
 16590       var field;
 16591       if (fields[i].charAt(0) === '@') {
 16592         field = fields[i].substr(1);
 16593         if (raw[field]) {
 16594           node[field] = lift(raw[field]);
 16596       } else {
 16597         field = fields[i];
 16598         node[field] = raw[field];
 16601     return node;
 16602   };
 16603   exports.flatten = function flatten(node) {
 16604     if (!node) {
 16605       return node;
 16607     if (node instanceof Array) {
 16608       return node.map(function (n) {
 16609         return flatten(n);
 16610       });
 16612     var type = node.type;
 16613     var raw = {
 16614         type: type
 16615       };
 16616     var fields = allFields(lang[type]);
 16617     for (var i = 0, j = fields.length; i < j; i++) {
 16618       var field;
 16619       if (fields[i].charAt(0) === '@') {
 16620         field = fields[i].substr(1);
 16621         if (node[field]) {
 16622           raw[field] = flatten(node[field]);
 16623         } else {
 16624           raw[field] = null;
 16626       } else {
 16627         field = fields[i];
 16628         raw[field] = node[field];
 16631     return raw;
 16632   };
 16633 }(typeof exports === 'undefined' ? estransform = {} : exports));
 16634 (function (exports) {
 16635   var Syntax, Precedence, BinaryPrecedence, Regex, VisitorKeys, VisitorOption, isArray, base, indent, json, renumber, hexadecimal, quotes, escapeless, newline, space, parentheses, semicolons, extra, parse;
 16636   Syntax = {
 16637     AssignmentExpression: 'AssignmentExpression',
 16638     ArrayExpression: 'ArrayExpression',
 16639     BlockStatement: 'BlockStatement',
 16640     BinaryExpression: 'BinaryExpression',
 16641     BreakStatement: 'BreakStatement',
 16642     CallExpression: 'CallExpression',
 16643     CatchClause: 'CatchClause',
 16644     ConditionalExpression: 'ConditionalExpression',
 16645     ContinueStatement: 'ContinueStatement',
 16646     DoWhileStatement: 'DoWhileStatement',
 16647     DebuggerStatement: 'DebuggerStatement',
 16648     EmptyStatement: 'EmptyStatement',
 16649     ExpressionStatement: 'ExpressionStatement',
 16650     ForStatement: 'ForStatement',
 16651     ForInStatement: 'ForInStatement',
 16652     FunctionDeclaration: 'FunctionDeclaration',
 16653     FunctionExpression: 'FunctionExpression',
 16654     Identifier: 'Identifier',
 16655     IfStatement: 'IfStatement',
 16656     Literal: 'Literal',
 16657     LabeledStatement: 'LabeledStatement',
 16658     LogicalExpression: 'LogicalExpression',
 16659     MemberExpression: 'MemberExpression',
 16660     NewExpression: 'NewExpression',
 16661     ObjectExpression: 'ObjectExpression',
 16662     Program: 'Program',
 16663     Property: 'Property',
 16664     ReturnStatement: 'ReturnStatement',
 16665     SequenceExpression: 'SequenceExpression',
 16666     SwitchStatement: 'SwitchStatement',
 16667     SwitchCase: 'SwitchCase',
 16668     ThisExpression: 'ThisExpression',
 16669     ThrowStatement: 'ThrowStatement',
 16670     TryStatement: 'TryStatement',
 16671     UnaryExpression: 'UnaryExpression',
 16672     UpdateExpression: 'UpdateExpression',
 16673     VariableDeclaration: 'VariableDeclaration',
 16674     VariableDeclarator: 'VariableDeclarator',
 16675     WhileStatement: 'WhileStatement',
 16676     WithStatement: 'WithStatement'
 16677   };
 16678   Precedence = {
 16679     Sequence: 0,
 16680     Assignment: 1,
 16681     Conditional: 2,
 16682     LogicalOR: 3,
 16683     LogicalAND: 4,
 16684     BitwiseOR: 5,
 16685     BitwiseXOR: 6,
 16686     BitwiseAND: 7,
 16687     Equality: 8,
 16688     Relational: 9,
 16689     BitwiseSHIFT: 10,
 16690     Additive: 11,
 16691     Multiplicative: 12,
 16692     Unary: 13,
 16693     Postfix: 14,
 16694     Call: 15,
 16695     New: 16,
 16696     Member: 17,
 16697     Primary: 18
 16698   };
 16699   BinaryPrecedence = {
 16700     '||': Precedence.LogicalOR,
 16701     '&&': Precedence.LogicalAND,
 16702     '|': Precedence.BitwiseOR,
 16703     '^': Precedence.BitwiseXOR,
 16704     '&': Precedence.BitwiseAND,
 16705     '==': Precedence.Equality,
 16706     '!=': Precedence.Equality,
 16707     '===': Precedence.Equality,
 16708     '!==': Precedence.Equality,
 16709     '<': Precedence.Relational,
 16710     '>': Precedence.Relational,
 16711     '<=': Precedence.Relational,
 16712     '>=': Precedence.Relational,
 16713     'in': Precedence.Relational,
 16714     'instanceof': Precedence.Relational,
 16715     '<<': Precedence.BitwiseSHIFT,
 16716     '>>': Precedence.BitwiseSHIFT,
 16717     '>>>': Precedence.BitwiseSHIFT,
 16718     '+': Precedence.Additive,
 16719     '-': Precedence.Additive,
 16720     '*': Precedence.Multiplicative,
 16721     '%': Precedence.Multiplicative,
 16722     '/': Precedence.Multiplicative
 16723   };
 16724   Regex = {
 16725     NonAsciiIdentifierPart: new RegExp('[\xaa\xb5\xba\xc0-\xd6\xd8-\xf6\xf8-\u02c1\u02c6-\u02d1\u02e0-\u02e4\u02ec\u02ee\u0300-\u0374\u0376\u0377\u037a-\u037d\u0386\u0388-\u038a\u038c\u038e-\u03a1\u03a3-\u03f5\u03f7-\u0481\u0483-\u0487\u048a-\u0527\u0531-\u0556\u0559\u0561-\u0587\u0591-\u05bd\u05bf\u05c1\u05c2\u05c4\u05c5\u05c7\u05d0-\u05ea\u05f0-\u05f2\u0610-\u061a\u0620-\u0669\u066e-\u06d3\u06d5-\u06dc\u06df-\u06e8\u06ea-\u06fc\u06ff\u0710-\u074a\u074d-\u07b1\u07c0-\u07f5\u07fa\u0800-\u082d\u0840-\u085b\u08a0\u08a2-\u08ac\u08e4-\u08fe\u0900-\u0963\u0966-\u096f\u0971-\u0977\u0979-\u097f\u0981-\u0983\u0985-\u098c\u098f\u0990\u0993-\u09a8\u09aa-\u09b0\u09b2\u09b6-\u09b9\u09bc-\u09c4\u09c7\u09c8\u09cb-\u09ce\u09d7\u09dc\u09dd\u09df-\u09e3\u09e6-\u09f1\u0a01-\u0a03\u0a05-\u0a0a\u0a0f\u0a10\u0a13-\u0a28\u0a2a-\u0a30\u0a32\u0a33\u0a35\u0a36\u0a38\u0a39\u0a3c\u0a3e-\u0a42\u0a47\u0a48\u0a4b-\u0a4d\u0a51\u0a59-\u0a5c\u0a5e\u0a66-\u0a75\u0a81-\u0a83\u0a85-\u0a8d\u0a8f-\u0a91\u0a93-\u0aa8\u0aaa-\u0ab0\u0ab2\u0ab3\u0ab5-\u0ab9\u0abc-\u0ac5\u0ac7-\u0ac9\u0acb-\u0acd\u0ad0\u0ae0-\u0ae3\u0ae6-\u0aef\u0b01-\u0b03\u0b05-\u0b0c\u0b0f\u0b10\u0b13-\u0b28\u0b2a-\u0b30\u0b32\u0b33\u0b35-\u0b39\u0b3c-\u0b44\u0b47\u0b48\u0b4b-\u0b4d\u0b56\u0b57\u0b5c\u0b5d\u0b5f-\u0b63\u0b66-\u0b6f\u0b71\u0b82\u0b83\u0b85-\u0b8a\u0b8e-\u0b90\u0b92-\u0b95\u0b99\u0b9a\u0b9c\u0b9e\u0b9f\u0ba3\u0ba4\u0ba8-\u0baa\u0bae-\u0bb9\u0bbe-\u0bc2\u0bc6-\u0bc8\u0bca-\u0bcd\u0bd0\u0bd7\u0be6-\u0bef\u0c01-\u0c03\u0c05-\u0c0c\u0c0e-\u0c10\u0c12-\u0c28\u0c2a-\u0c33\u0c35-\u0c39\u0c3d-\u0c44\u0c46-\u0c48\u0c4a-\u0c4d\u0c55\u0c56\u0c58\u0c59\u0c60-\u0c63\u0c66-\u0c6f\u0c82\u0c83\u0c85-\u0c8c\u0c8e-\u0c90\u0c92-\u0ca8\u0caa-\u0cb3\u0cb5-\u0cb9\u0cbc-\u0cc4\u0cc6-\u0cc8\u0cca-\u0ccd\u0cd5\u0cd6\u0cde\u0ce0-\u0ce3\u0ce6-\u0cef\u0cf1\u0cf2\u0d02\u0d03\u0d05-\u0d0c\u0d0e-\u0d10\u0d12-\u0d3a\u0d3d-\u0d44\u0d46-\u0d48\u0d4a-\u0d4e\u0d57\u0d60-\u0d63\u0d66-\u0d6f\u0d7a-\u0d7f\u0d82\u0d83\u0d85-\u0d96\u0d9a-\u0db1\u0db3-\u0dbb\u0dbd\u0dc0-\u0dc6\u0dca\u0dcf-\u0dd4\u0dd6\u0dd8-\u0ddf\u0df2\u0df3\u0e01-\u0e3a\u0e40-\u0e4e\u0e50-\u0e59\u0e81\u0e82\u0e84\u0e87\u0e88\u0e8a\u0e8d\u0e94-\u0e97\u0e99-\u0e9f\u0ea1-\u0ea3\u0ea5\u0ea7\u0eaa\u0eab\u0ead-\u0eb9\u0ebb-\u0ebd\u0ec0-\u0ec4\u0ec6\u0ec8-\u0ecd\u0ed0-\u0ed9\u0edc-\u0edf\u0f00\u0f18\u0f19\u0f20-\u0f29\u0f35\u0f37\u0f39\u0f3e-\u0f47\u0f49-\u0f6c\u0f71-\u0f84\u0f86-\u0f97\u0f99-\u0fbc\u0fc6\u1000-\u1049\u1050-\u109d\u10a0-\u10c5\u10c7\u10cd\u10d0-\u10fa\u10fc-\u1248\u124a-\u124d\u1250-\u1256\u1258\u125a-\u125d\u1260-\u1288\u128a-\u128d\u1290-\u12b0\u12b2-\u12b5\u12b8-\u12be\u12c0\u12c2-\u12c5\u12c8-\u12d6\u12d8-\u1310\u1312-\u1315\u1318-\u135a\u135d-\u135f\u1380-\u138f\u13a0-\u13f4\u1401-\u166c\u166f-\u167f\u1681-\u169a\u16a0-\u16ea\u16ee-\u16f0\u1700-\u170c\u170e-\u1714\u1720-\u1734\u1740-\u1753\u1760-\u176c\u176e-\u1770\u1772\u1773\u1780-\u17d3\u17d7\u17dc\u17dd\u17e0-\u17e9\u180b-\u180d\u1810-\u1819\u1820-\u1877\u1880-\u18aa\u18b0-\u18f5\u1900-\u191c\u1920-\u192b\u1930-\u193b\u1946-\u196d\u1970-\u1974\u1980-\u19ab\u19b0-\u19c9\u19d0-\u19d9\u1a00-\u1a1b\u1a20-\u1a5e\u1a60-\u1a7c\u1a7f-\u1a89\u1a90-\u1a99\u1aa7\u1b00-\u1b4b\u1b50-\u1b59\u1b6b-\u1b73\u1b80-\u1bf3\u1c00-\u1c37\u1c40-\u1c49\u1c4d-\u1c7d\u1cd0-\u1cd2\u1cd4-\u1cf6\u1d00-\u1de6\u1dfc-\u1f15\u1f18-\u1f1d\u1f20-\u1f45\u1f48-\u1f4d\u1f50-\u1f57\u1f59\u1f5b\u1f5d\u1f5f-\u1f7d\u1f80-\u1fb4\u1fb6-\u1fbc\u1fbe\u1fc2-\u1fc4\u1fc6-\u1fcc\u1fd0-\u1fd3\u1fd6-\u1fdb\u1fe0-\u1fec\u1ff2-\u1ff4\u1ff6-\u1ffc\u200c\u200d\u203f\u2040\u2054\u2071\u207f\u2090-\u209c\u20d0-\u20dc\u20e1\u20e5-\u20f0\u2102\u2107\u210a-\u2113\u2115\u2119-\u211d\u2124\u2126\u2128\u212a-\u212d\u212f-\u2139\u213c-\u213f\u2145-\u2149\u214e\u2160-\u2188\u2c00-\u2c2e\u2c30-\u2c5e\u2c60-\u2ce4\u2ceb-\u2cf3\u2d00-\u2d25\u2d27\u2d2d\u2d30-\u2d67\u2d6f\u2d7f-\u2d96\u2da0-\u2da6\u2da8-\u2dae\u2db0-\u2db6\u2db8-\u2dbe\u2dc0-\u2dc6\u2dc8-\u2dce\u2dd0-\u2dd6\u2dd8-\u2dde\u2de0-\u2dff\u2e2f\u3005-\u3007\u3021-\u302f\u3031-\u3035\u3038-\u303c\u3041-\u3096\u3099\u309a\u309d-\u309f\u30a1-\u30fa\u30fc-\u30ff\u3105-\u312d\u3131-\u318e\u31a0-\u31ba\u31f0-\u31ff\u3400-\u4db5\u4e00-\u9fcc\ua000-\ua48c\ua4d0-\ua4fd\ua500-\ua60c\ua610-\ua62b\ua640-\ua66f\ua674-\ua67d\ua67f-\ua697\ua69f-\ua6f1\ua717-\ua71f\ua722-\ua788\ua78b-\ua78e\ua790-\ua793\ua7a0-\ua7aa\ua7f8-\ua827\ua840-\ua873\ua880-\ua8c4\ua8d0-\ua8d9\ua8e0-\ua8f7\ua8fb\ua900-\ua92d\ua930-\ua953\ua960-\ua97c\ua980-\ua9c0\ua9cf-\ua9d9\uaa00-\uaa36\uaa40-\uaa4d\uaa50-\uaa59\uaa60-\uaa76\uaa7a\uaa7b\uaa80-\uaac2\uaadb-\uaadd\uaae0-\uaaef\uaaf2-\uaaf6\uab01-\uab06\uab09-\uab0e\uab11-\uab16\uab20-\uab26\uab28-\uab2e\uabc0-\uabea\uabec\uabed\uabf0-\uabf9\uac00-\ud7a3\ud7b0-\ud7c6\ud7cb-\ud7fb\uf900-\ufa6d\ufa70-\ufad9\ufb00-\ufb06\ufb13-\ufb17\ufb1d-\ufb28\ufb2a-\ufb36\ufb38-\ufb3c\ufb3e\ufb40\ufb41\ufb43\ufb44\ufb46-\ufbb1\ufbd3-\ufd3d\ufd50-\ufd8f\ufd92-\ufdc7\ufdf0-\ufdfb\ufe00-\ufe0f\ufe20-\ufe26\ufe33\ufe34\ufe4d-\ufe4f\ufe70-\ufe74\ufe76-\ufefc\uff10-\uff19\uff21-\uff3a\uff3f\uff41-\uff5a\uff66-\uffbe\uffc2-\uffc7\uffca-\uffcf\uffd2-\uffd7\uffda-\uffdc]')
 16726   };
 16727   function getDefaultOptions() {
 16728     return {
 16729       indent: null,
 16730       base: null,
 16731       parse: null,
 16732       comment: false,
 16733       format: {
 16734         indent: {
 16735           style: '    ',
 16736           base: 0,
 16737           adjustMultilineComment: false
 16738         },
 16739         json: false,
 16740         renumber: false,
 16741         hexadecimal: false,
 16742         quotes: 'single',
 16743         escapeless: false,
 16744         compact: false,
 16745         parentheses: true,
 16746         semicolons: true
 16748     };
 16750   function stringToArray(str) {
 16751     var length = str.length, result = [], i;
 16752     for (i = 0; i < length; i += 1) {
 16753       result[i] = str.charAt(i);
 16755     return result;
 16757   function stringRepeat(str, num) {
 16758     var result = '';
 16759     for (num |= 0; num > 0; num >>>= 1, str += str) {
 16760       if (num & 1) {
 16761         result += str;
 16764     return result;
 16766   isArray = Array.isArray;
 16767   if (!isArray) {
 16768     isArray = function isArray(array) {
 16769       return Object.prototype.toString.call(array) === '[object Array]';
 16770     };
 16772   function endsWithLineTerminator(str) {
 16773     var len, ch;
 16774     len = str.length;
 16775     ch = str.charAt(len - 1);
 16776     return ch === '\r' || ch === '\n';
 16778   function shallowCopy(obj) {
 16779     var ret = {}, key;
 16780     for (key in obj) {
 16781       if (obj.hasOwnProperty(key)) {
 16782         ret[key] = obj[key];
 16785     return ret;
 16787   function deepCopy(obj) {
 16788     var ret = {}, key, val;
 16789     for (key in obj) {
 16790       if (obj.hasOwnProperty(key)) {
 16791         val = obj[key];
 16792         if (typeof val === 'object' && val !== null) {
 16793           ret[key] = deepCopy(val);
 16794         } else {
 16795           ret[key] = val;
 16799     return ret;
 16801   function updateDeeply(target, override) {
 16802     var key, val;
 16803     function isHashObject(target) {
 16804       return typeof target === 'object' && target instanceof Object && !(target instanceof RegExp);
 16806     for (key in override) {
 16807       if (override.hasOwnProperty(key)) {
 16808         val = override[key];
 16809         if (isHashObject(val)) {
 16810           if (isHashObject(target[key])) {
 16811             updateDeeply(target[key], val);
 16812           } else {
 16813             target[key] = updateDeeply({}, val);
 16815         } else {
 16816           target[key] = val;
 16820     return target;
 16822   function generateNumber(value) {
 16823     var result, point, temp, exponent, pos;
 16824     if (value !== value) {
 16825       throw new Error('Numeric literal whose value is NaN');
 16827     if (1 / value < 0) {
 16828       throw new Error('Numeric literal whose value is negative');
 16830     if (value === 1 / 0) {
 16831       return json ? 'null' : renumber ? '1e400' : '1e+400';
 16833     result = '' + value;
 16834     if (!renumber || result.length < 3) {
 16835       return result;
 16837     point = result.indexOf('.');
 16838     if (!json && result.charAt(0) === '0' && point === 1) {
 16839       point = 0;
 16840       result = result.slice(1);
 16842     temp = result;
 16843     result = result.replace('e+', 'e');
 16844     exponent = 0;
 16845     if ((pos = temp.indexOf('e')) > 0) {
 16846       exponent = +temp.slice(pos + 1);
 16847       temp = temp.slice(0, pos);
 16849     if (point >= 0) {
 16850       exponent -= temp.length - point - 1;
 16851       temp = +(temp.slice(0, point) + temp.slice(point + 1)) + '';
 16853     pos = 0;
 16854     while (temp.charAt(temp.length + pos - 1) === '0') {
 16855       pos -= 1;
 16857     if (pos !== 0) {
 16858       exponent -= pos;
 16859       temp = temp.slice(0, pos);
 16861     if (exponent !== 0) {
 16862       temp += 'e' + exponent;
 16864     if ((temp.length < result.length || hexadecimal && value > 1000000000000 && Math.floor(value) === value && (temp = '0x' + value.toString(16)).length < result.length) && +temp === value) {
 16865       result = temp;
 16867     return result;
 16869   function escapeAllowedCharacter(ch, next) {
 16870     var code = ch.charCodeAt(0), hex = code.toString(16), result = '\\';
 16871     switch (ch) {
 16872     case '\b':
 16873       result += 'b';
 16874       break;
 16875     case '\f':
 16876       result += 'f';
 16877       break;
 16878     case '\t':
 16879       result += 't';
 16880       break;
 16881     default:
 16882       if (json || code > 255) {
 16883         result += 'u' + '0000'.slice(hex.length) + hex;
 16884       } else if (ch === '\0' && '0123456789'.indexOf(next) < 0) {
 16885         result += '0';
 16886       } else if (ch === '\v') {
 16887         result += 'v';
 16888       } else {
 16889         result += 'x' + '00'.slice(hex.length) + hex;
 16891       break;
 16893     return result;
 16895   function escapeDisallowedCharacter(ch) {
 16896     var result = '\\';
 16897     switch (ch) {
 16898     case '\\':
 16899       result += '\\';
 16900       break;
 16901     case '\n':
 16902       result += 'n';
 16903       break;
 16904     case '\r':
 16905       result += 'r';
 16906       break;
 16907     case '\u2028':
 16908       result += 'u2028';
 16909       break;
 16910     case '\u2029':
 16911       result += 'u2029';
 16912       break;
 16913     default:
 16914       throw new Error('Incorrectly classified character');
 16916     return result;
 16918   function escapeString(str) {
 16919     var result = '', i, len, ch, next, singleQuotes = 0, doubleQuotes = 0, single;
 16920     if (typeof str[0] === 'undefined') {
 16921       str = stringToArray(str);
 16923     for (i = 0, len = str.length; i < len; i += 1) {
 16924       ch = str[i];
 16925       if (ch === '\'') {
 16926         singleQuotes += 1;
 16927       } else if (ch === '"') {
 16928         doubleQuotes += 1;
 16929       } else if (ch === '/' && json) {
 16930         result += '\\';
 16931       } else if ('\\\n\r\u2028\u2029'.indexOf(ch) >= 0) {
 16932         result += escapeDisallowedCharacter(ch);
 16933         continue;
 16934       } else if (json && ch < ' ' || !(json || escapeless || ch >= ' ' && ch <= '~')) {
 16935         result += escapeAllowedCharacter(ch, str[i + 1]);
 16936         continue;
 16938       result += ch;
 16940     single = !(quotes === 'double' || quotes === 'auto' && doubleQuotes < singleQuotes);
 16941     str = result;
 16942     result = single ? '\'' : '"';
 16943     if (typeof str[0] === 'undefined') {
 16944       str = stringToArray(str);
 16946     for (i = 0, len = str.length; i < len; i += 1) {
 16947       ch = str[i];
 16948       if (ch === '\'' && single || ch === '"' && !single) {
 16949         result += '\\';
 16951       result += ch;
 16953     return result + (single ? '\'' : '"');
 16955   function isWhiteSpace(ch) {
 16956     return '\t\v\f \xa0'.indexOf(ch) >= 0 || ch.charCodeAt(0) >= 5760 && '\u1680\u180e\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200a\u202f\u205f\u3000\ufeff'.indexOf(ch) >= 0;
 16958   function isLineTerminator(ch) {
 16959     return '\n\r\u2028\u2029'.indexOf(ch) >= 0;
 16961   function isIdentifierPart(ch) {
 16962     return ch === '$' || ch === '_' || ch === '\\' || ch >= 'a' && ch <= 'z' || ch >= 'A' && ch <= 'Z' || ch >= '0' && ch <= '9' || ch.charCodeAt(0) >= 128 && Regex.NonAsciiIdentifierPart.test(ch);
 16964   function join(left, right) {
 16965     var leftChar = left.charAt(left.length - 1), rightChar = right.charAt(0);
 16966     if ((leftChar === '+' || leftChar === '-') && leftChar === rightChar || isIdentifierPart(leftChar) && isIdentifierPart(rightChar)) {
 16967       return left + ' ' + right;
 16968     } else if (isWhiteSpace(leftChar) || isLineTerminator(leftChar) || isWhiteSpace(rightChar) || isLineTerminator(rightChar)) {
 16969       return left + right;
 16971     return left + space + right;
 16973   function addIndent(stmt) {
 16974     return base + stmt;
 16976   function calculateSpaces(str) {
 16977     var i;
 16978     for (i = str.length - 1; i >= 0; i -= 1) {
 16979       if (isLineTerminator(str.charAt(i))) {
 16980         break;
 16983     return str.length - 1 - i;
 16985   function adjustMultilineComment(value, specialBase) {
 16986     var array, i, len, line, j, ch, spaces, previousBase;
 16987     array = value.split(/\r\n|[\r\n]/);
 16988     spaces = Number.MAX_VALUE;
 16989     for (i = 1, len = array.length; i < len; i += 1) {
 16990       line = array[i];
 16991       j = 0;
 16992       while (j < line.length && isWhiteSpace(line[j])) {
 16993         j += 1;
 16995       if (spaces > j) {
 16996         spaces = j;
 16999     if (typeof specialBase !== 'undefined') {
 17000       previousBase = base;
 17001       if (array[1][spaces] === '*') {
 17002         specialBase += ' ';
 17004       base = specialBase;
 17005     } else {
 17006       if (spaces % 2 === 1) {
 17007         spaces -= 1;
 17009       previousBase = base;
 17011     for (i = 1, len = array.length; i < len; i += 1) {
 17012       array[i] = addIndent(array[i].slice(spaces));
 17014     base = previousBase;
 17015     return array.join('\n');
 17017   function generateComment(comment, specialBase) {
 17018     if (comment.type === 'Line') {
 17019       if (endsWithLineTerminator(comment.value)) {
 17020         return '//' + comment.value;
 17021       } else {
 17022         return '//' + comment.value + '\n';
 17025     if (extra.format.indent.adjustMultilineComment && /[\n\r]/.test(comment.value)) {
 17026       return adjustMultilineComment('/*' + comment.value + '*/', specialBase);
 17028     return '/*' + comment.value + '*/';
 17030   function addCommentsToStatement(stmt, result) {
 17031     var i, len, comment, save, node, tailingToStatement, specialBase, fragment;
 17032     if (stmt.leadingComments) {
 17033       save = result;
 17034       comment = stmt.leadingComments[0];
 17035       result = generateComment(comment);
 17036       if (!endsWithLineTerminator(result)) {
 17037         result += '\n';
 17039       for (i = 1, len = stmt.leadingComments.length; i < len; i += 1) {
 17040         comment = stmt.leadingComments[i];
 17041         fragment = generateComment(comment);
 17042         if (!endsWithLineTerminator(fragment)) {
 17043           fragment += '\n';
 17045         result += addIndent(fragment);
 17047       result += addIndent(save);
 17049     if (stmt.trailingComments) {
 17050       tailingToStatement = !endsWithLineTerminator(result);
 17051       specialBase = stringRepeat(' ', calculateSpaces(base + result + indent));
 17052       for (i = 0, len = stmt.trailingComments.length; i < len; i += 1) {
 17053         comment = stmt.trailingComments[i];
 17054         if (tailingToStatement) {
 17055           if (i === 0) {
 17056             result += indent;
 17057           } else {
 17058             result += specialBase;
 17060           result += generateComment(comment, specialBase);
 17061         } else {
 17062           result += addIndent(generateComment(comment));
 17064         if (i !== len - 1 && !endsWithLineTerminator(result)) {
 17065           result += '\n';
 17069     return result;
 17071   function parenthesize(text, current, should) {
 17072     if (current < should) {
 17073       return '(' + text + ')';
 17075     return text;
 17077   function maybeBlock(stmt, semicolonOptional) {
 17078     var previousBase, result, noLeadingComment;
 17079     noLeadingComment = !extra.comment || !stmt.leadingComments;
 17080     if (stmt.type === Syntax.BlockStatement && noLeadingComment) {
 17081       return space + generateStatement(stmt);
 17083     if (stmt.type === Syntax.EmptyStatement && noLeadingComment) {
 17084       return ';';
 17086     previousBase = base;
 17087     base += indent;
 17088     result = newline + addIndent(generateStatement(stmt, {
 17089       semicolonOptional: semicolonOptional
 17090     }));
 17091     base = previousBase;
 17092     return result;
 17094   function maybeBlockSuffix(stmt, result) {
 17095     if (stmt.type === Syntax.BlockStatement && (!extra.comment || !stmt.leadingComments) && !endsWithLineTerminator(result)) {
 17096       return space;
 17098     if (endsWithLineTerminator(result)) {
 17099       return addIndent('');
 17101     return (newline === '' ? ' ' : newline) + addIndent('');
 17103   function generateFunctionBody(node) {
 17104     var result, i, len;
 17105     result = '(';
 17106     for (i = 0, len = node.params.length; i < len; i += 1) {
 17107       result += node.params[i].name;
 17108       if (i + 1 < len) {
 17109         result += ',' + space;
 17112     return result + ')' + maybeBlock(node.body);
 17114   function generateExpression(expr, option) {
 17115     var result, precedence, currentPrecedence, previousBase, i, len, raw, fragment, allowIn, allowCall, allowUnparenthesizedNew;
 17116     precedence = option.precedence;
 17117     allowIn = option.allowIn;
 17118     allowCall = option.allowCall;
 17119     switch (expr.type) {
 17120     case Syntax.SequenceExpression:
 17121       result = '';
 17122       allowIn |= Precedence.Sequence < precedence;
 17123       for (i = 0, len = expr.expressions.length; i < len; i += 1) {
 17124         result += generateExpression(expr.expressions[i], {
 17125           precedence: Precedence.Assignment,
 17126           allowIn: allowIn,
 17127           allowCall: true
 17128         });
 17129         if (i + 1 < len) {
 17130           result += ',' + space;
 17133       result = parenthesize(result, Precedence.Sequence, precedence);
 17134       break;
 17135     case Syntax.AssignmentExpression:
 17136       allowIn |= Precedence.Assignment < precedence;
 17137       result = parenthesize(generateExpression(expr.left, {
 17138         precedence: Precedence.Call,
 17139         allowIn: allowIn,
 17140         allowCall: true
 17141       }) + space + expr.operator + space + generateExpression(expr.right, {
 17142         precedence: Precedence.Assignment,
 17143         allowIn: allowIn,
 17144         allowCall: true
 17145       }), Precedence.Assignment, precedence);
 17146       break;
 17147     case Syntax.ConditionalExpression:
 17148       allowIn |= Precedence.Conditional < precedence;
 17149       result = parenthesize(generateExpression(expr.test, {
 17150         precedence: Precedence.LogicalOR,
 17151         allowIn: allowIn,
 17152         allowCall: true
 17153       }) + space + '?' + space + generateExpression(expr.consequent, {
 17154         precedence: Precedence.Assignment,
 17155         allowIn: allowIn,
 17156         allowCall: true
 17157       }) + space + ':' + space + generateExpression(expr.alternate, {
 17158         precedence: Precedence.Assignment,
 17159         allowIn: allowIn,
 17160         allowCall: true
 17161       }), Precedence.Conditional, precedence);
 17162       break;
 17163     case Syntax.LogicalExpression:
 17164     case Syntax.BinaryExpression:
 17165       currentPrecedence = BinaryPrecedence[expr.operator];
 17166       allowIn |= currentPrecedence < precedence;
 17167       result = join(generateExpression(expr.left, {
 17168         precedence: currentPrecedence,
 17169         allowIn: allowIn,
 17170         allowCall: true
 17171       }), expr.operator);
 17172       fragment = generateExpression(expr.right, {
 17173         precedence: currentPrecedence + 1,
 17174         allowIn: allowIn,
 17175         allowCall: true
 17176       });
 17177       if (expr.operator === '/' && result.charAt(result.length - 1) === '/') {
 17178         result += ' ' + fragment;
 17179       } else {
 17180         result = join(result, fragment);
 17182       if (expr.operator === 'in' && !allowIn) {
 17183         result = '(' + result + ')';
 17184       } else {
 17185         result = parenthesize(result, currentPrecedence, precedence);
 17187       break;
 17188     case Syntax.CallExpression:
 17189       result = generateExpression(expr.callee, {
 17190         precedence: Precedence.Call,
 17191         allowIn: true,
 17192         allowCall: true,
 17193         allowUnparenthesizedNew: false
 17194       });
 17195       result += '(';
 17196       for (i = 0, len = expr['arguments'].length; i < len; i += 1) {
 17197         result += generateExpression(expr['arguments'][i], {
 17198           precedence: Precedence.Assignment,
 17199           allowIn: true,
 17200           allowCall: true
 17201         });
 17202         if (i + 1 < len) {
 17203           result += ',' + space;
 17206       result += ')';
 17207       if (!allowCall) {
 17208         result = '(' + result + ')';
 17209       } else {
 17210         result = parenthesize(result, Precedence.Call, precedence);
 17212       break;
 17213     case Syntax.NewExpression:
 17214       len = expr['arguments'].length;
 17215       allowUnparenthesizedNew = option.allowUnparenthesizedNew === undefined || option.allowUnparenthesizedNew;
 17216       result = join('new', generateExpression(expr.callee, {
 17217         precedence: Precedence.New,
 17218         allowIn: true,
 17219         allowCall: false,
 17220         allowUnparenthesizedNew: allowUnparenthesizedNew && !parentheses && len === 0
 17221       }));
 17222       if (!allowUnparenthesizedNew || parentheses || len > 0) {
 17223         result += '(';
 17224         for (i = 0; i < len; i += 1) {
 17225           result += generateExpression(expr['arguments'][i], {
 17226             precedence: Precedence.Assignment,
 17227             allowIn: true,
 17228             allowCall: true
 17229           });
 17230           if (i + 1 < len) {
 17231             result += ',' + space;
 17234         result += ')';
 17236       result = parenthesize(result, Precedence.New, precedence);
 17237       break;
 17238     case Syntax.MemberExpression:
 17239       result = generateExpression(expr.object, {
 17240         precedence: Precedence.Call,
 17241         allowIn: true,
 17242         allowCall: allowCall,
 17243         allowUnparenthesizedNew: false
 17244       });
 17245       if (expr.computed) {
 17246         result += '[' + generateExpression(expr.property, {
 17247           precedence: Precedence.Sequence,
 17248           allowIn: true,
 17249           allowCall: allowCall
 17250         }) + ']';
 17251       } else {
 17252         if (expr.object.type === Syntax.Literal && typeof expr.object.value === 'number') {
 17253           if (result.indexOf('.') < 0) {
 17254             if (!/[eExX]/.test(result) && !(result.length >= 2 && result[0] === '0')) {
 17255               result += '.';
 17259         result += '.' + expr.property.name;
 17261       result = parenthesize(result, Precedence.Member, precedence);
 17262       break;
 17263     case Syntax.UnaryExpression:
 17264       fragment = generateExpression(expr.argument, {
 17265         precedence: Precedence.Unary + (expr.argument.type === Syntax.UnaryExpression && expr.operator.length < 3 && expr.argument.operator === expr.operator ? 1 : 0),
 17266         allowIn: true,
 17267         allowCall: true
 17268       });
 17269       if (space === '') {
 17270         result = join(expr.operator, fragment);
 17271       } else {
 17272         result = expr.operator;
 17273         if (result.length > 2) {
 17274           result += ' ';
 17276         result += fragment;
 17278       result = parenthesize(result, Precedence.Unary, precedence);
 17279       break;
 17280     case Syntax.UpdateExpression:
 17281       if (expr.prefix) {
 17282         result = parenthesize(expr.operator + generateExpression(expr.argument, {
 17283           precedence: Precedence.Unary,
 17284           allowIn: true,
 17285           allowCall: true
 17286         }), Precedence.Unary, precedence);
 17287       } else {
 17288         result = parenthesize(generateExpression(expr.argument, {
 17289           precedence: Precedence.Postfix,
 17290           allowIn: true,
 17291           allowCall: true
 17292         }) + expr.operator, Precedence.Postfix, precedence);
 17294       break;
 17295     case Syntax.FunctionExpression:
 17296       result = 'function';
 17297       if (expr.id) {
 17298         result += ' ' + expr.id.name;
 17299       } else {
 17300         result += space;
 17302       result += generateFunctionBody(expr);
 17303       break;
 17304     case Syntax.ArrayExpression:
 17305       if (!expr.elements.length) {
 17306         result = '[]';
 17307         break;
 17309       result = '[' + newline;
 17310       previousBase = base;
 17311       base += indent;
 17312       for (i = 0, len = expr.elements.length; i < len; i += 1) {
 17313         if (!expr.elements[i]) {
 17314           result += addIndent('');
 17315           if (i + 1 === len) {
 17316             result += ',';
 17318         } else {
 17319           result += addIndent(generateExpression(expr.elements[i], {
 17320             precedence: Precedence.Assignment,
 17321             allowIn: true,
 17322             allowCall: true
 17323           }));
 17325         if (i + 1 < len) {
 17326           result += ',' + newline;
 17329       base = previousBase;
 17330       if (!endsWithLineTerminator(result)) {
 17331         result += newline;
 17333       result += addIndent(']');
 17334       break;
 17335     case Syntax.Property:
 17336       if (expr.kind === 'get' || expr.kind === 'set') {
 17337         result = expr.kind + ' ' + generateExpression(expr.key, {
 17338           precedence: Precedence.Sequence,
 17339           allowIn: true,
 17340           allowCall: true
 17341         }) + generateFunctionBody(expr.value);
 17342       } else {
 17343         result = generateExpression(expr.key, {
 17344           precedence: Precedence.Sequence,
 17345           allowIn: true,
 17346           allowCall: true
 17347         }) + ':' + space + generateExpression(expr.value, {
 17348           precedence: Precedence.Assignment,
 17349           allowIn: true,
 17350           allowCall: true
 17351         });
 17353       break;
 17354     case Syntax.ObjectExpression:
 17355       if (!expr.properties.length) {
 17356         result = '{}';
 17357         break;
 17359       result = '{' + newline;
 17360       previousBase = base;
 17361       base += indent;
 17362       for (i = 0, len = expr.properties.length; i < len; i += 1) {
 17363         result += addIndent(generateExpression(expr.properties[i], {
 17364           precedence: Precedence.Sequence,
 17365           allowIn: true,
 17366           allowCall: true
 17367         }));
 17368         if (i + 1 < len) {
 17369           result += ',' + newline;
 17372       base = previousBase;
 17373       if (!endsWithLineTerminator(result)) {
 17374         result += newline;
 17376       result += addIndent('}');
 17377       break;
 17378     case Syntax.ThisExpression:
 17379       result = 'this';
 17380       break;
 17381     case Syntax.Identifier:
 17382       result = expr.name;
 17383       break;
 17384     case Syntax.Literal:
 17385       if (expr.hasOwnProperty('raw') && parse) {
 17386         try {
 17387           raw = parse(expr.raw).body[0].expression;
 17388           if (raw.type === Syntax.Literal) {
 17389             if (raw.value === expr.value) {
 17390               result = expr.raw;
 17391               break;
 17394         } catch (e) {
 17397       if (expr.value === null) {
 17398         result = 'null';
 17399         break;
 17401       if (typeof expr.value === 'string') {
 17402         result = escapeString(expr.value);
 17403         break;
 17405       if (typeof expr.value === 'number') {
 17406         result = generateNumber(expr.value);
 17407         break;
 17409       result = expr.value.toString();
 17410       break;
 17411     default:
 17412       break;
 17414     if (result === undefined) {
 17415       throw new Error('Unknown expression type: ' + expr.type);
 17417     return result;
 17419   function generateStatement(stmt, option) {
 17420     var i, len, result, previousBase, node, allowIn, fragment, semicolon;
 17421     allowIn = true;
 17422     semicolon = ';';
 17423     if (option) {
 17424       allowIn = option.allowIn === undefined || option.allowIn;
 17425       if (!semicolons && option.semicolonOptional === true) {
 17426         semicolon = '';
 17429     switch (stmt.type) {
 17430     case Syntax.BlockStatement:
 17431       result = '{' + newline;
 17432       previousBase = base;
 17433       base += indent;
 17434       for (i = 0, len = stmt.body.length; i < len; i += 1) {
 17435         fragment = addIndent(generateStatement(stmt.body[i], {
 17436           semicolonOptional: i === len - 1
 17437         }));
 17438         result += fragment;
 17439         if (!endsWithLineTerminator(fragment)) {
 17440           result += newline;
 17443       base = previousBase;
 17444       result += addIndent('}');
 17445       break;
 17446     case Syntax.BreakStatement:
 17447       if (stmt.label) {
 17448         result = 'break ' + stmt.label.name + semicolon;
 17449       } else {
 17450         result = 'break' + semicolon;
 17452       break;
 17453     case Syntax.ContinueStatement:
 17454       if (stmt.label) {
 17455         result = 'continue ' + stmt.label.name + semicolon;
 17456       } else {
 17457         result = 'continue' + semicolon;
 17459       break;
 17460     case Syntax.DoWhileStatement:
 17461       result = join('do', maybeBlock(stmt.body));
 17462       result += maybeBlockSuffix(stmt.body, result);
 17463       result += 'while' + space + '(' + generateExpression(stmt.test, {
 17464         precedence: Precedence.Sequence,
 17465         allowIn: true,
 17466         allowCall: true
 17467       }) + ')' + semicolon;
 17468       break;
 17469     case Syntax.CatchClause:
 17470       previousBase = base;
 17471       base += indent;
 17472       result = 'catch' + space + '(' + generateExpression(stmt.param, {
 17473         precedence: Precedence.Sequence,
 17474         allowIn: true,
 17475         allowCall: true
 17476       }) + ')';
 17477       base = previousBase;
 17478       result += maybeBlock(stmt.body);
 17479       break;
 17480     case Syntax.DebuggerStatement:
 17481       result = 'debugger' + semicolon;
 17482       break;
 17483     case Syntax.EmptyStatement:
 17484       result = ';';
 17485       break;
 17486     case Syntax.ExpressionStatement:
 17487       result = generateExpression(stmt.expression, {
 17488         precedence: Precedence.Sequence,
 17489         allowIn: true,
 17490         allowCall: true
 17491       });
 17492       if (result.charAt(0) === '{' || result.slice(0, 8) === 'function' && ' ('.indexOf(result.charAt(8)) >= 0) {
 17493         result = '(' + result + ')' + semicolon;
 17494       } else {
 17495         result += semicolon;
 17497       break;
 17498     case Syntax.VariableDeclarator:
 17499       if (stmt.init) {
 17500         result = stmt.id.name + space + '=' + space + generateExpression(stmt.init, {
 17501           precedence: Precedence.Assignment,
 17502           allowIn: allowIn,
 17503           allowCall: true
 17504         });
 17505       } else {
 17506         result = stmt.id.name;
 17508       break;
 17509     case Syntax.VariableDeclaration:
 17510       result = stmt.kind;
 17511       if (stmt.declarations.length === 1 && stmt.declarations[0].init && stmt.declarations[0].init.type === Syntax.FunctionExpression) {
 17512         result += ' ' + generateStatement(stmt.declarations[0], {
 17513           allowIn: allowIn
 17514         });
 17515       } else {
 17516         previousBase = base;
 17517         base += indent;
 17518         node = stmt.declarations[0];
 17519         if (extra.comment && node.leadingComments) {
 17520           result += '\n' + addIndent(generateStatement(node, {
 17521             allowIn: allowIn
 17522           }));
 17523         } else {
 17524           result += ' ' + generateStatement(node, {
 17525             allowIn: allowIn
 17526           });
 17528         for (i = 1, len = stmt.declarations.length; i < len; i += 1) {
 17529           node = stmt.declarations[i];
 17530           if (extra.comment && node.leadingComments) {
 17531             result += ',' + newline + addIndent(generateStatement(node, {
 17532               allowIn: allowIn
 17533             }));
 17534           } else {
 17535             result += ',' + space + generateStatement(node, {
 17536               allowIn: allowIn
 17537             });
 17540         base = previousBase;
 17542       result += semicolon;
 17543       break;
 17544     case Syntax.ThrowStatement:
 17545       result = join('throw', generateExpression(stmt.argument, {
 17546         precedence: Precedence.Sequence,
 17547         allowIn: true,
 17548         allowCall: true
 17549       })) + semicolon;
 17550       break;
 17551     case Syntax.TryStatement:
 17552       result = 'try' + maybeBlock(stmt.block);
 17553       result += maybeBlockSuffix(stmt.block, result);
 17554       for (i = 0, len = stmt.handlers.length; i < len; i += 1) {
 17555         result += generateStatement(stmt.handlers[i]);
 17556         if (stmt.finalizer || i + 1 !== len) {
 17557           result += maybeBlockSuffix(stmt.handlers[i].body, result);
 17560       if (stmt.finalizer) {
 17561         result += 'finally' + maybeBlock(stmt.finalizer);
 17563       break;
 17564     case Syntax.SwitchStatement:
 17565       previousBase = base;
 17566       base += indent;
 17567       result = 'switch' + space + '(' + generateExpression(stmt.discriminant, {
 17568         precedence: Precedence.Sequence,
 17569         allowIn: true,
 17570         allowCall: true
 17571       }) + ')' + space + '{' + newline;
 17572       base = previousBase;
 17573       if (stmt.cases) {
 17574         for (i = 0, len = stmt.cases.length; i < len; i += 1) {
 17575           fragment = addIndent(generateStatement(stmt.cases[i], {
 17576             semicolonOptional: i === len - 1
 17577           }));
 17578           result += fragment;
 17579           if (!endsWithLineTerminator(fragment)) {
 17580             result += newline;
 17584       result += addIndent('}');
 17585       break;
 17586     case Syntax.SwitchCase:
 17587       previousBase = base;
 17588       base += indent;
 17589       if (stmt.test) {
 17590         result = join('case', generateExpression(stmt.test, {
 17591           precedence: Precedence.Sequence,
 17592           allowIn: true,
 17593           allowCall: true
 17594         })) + ':';
 17595       } else {
 17596         result = 'default:';
 17598       i = 0;
 17599       len = stmt.consequent.length;
 17600       if (len && stmt.consequent[0].type === Syntax.BlockStatement) {
 17601         fragment = maybeBlock(stmt.consequent[0]);
 17602         result += fragment;
 17603         i = 1;
 17605       if (i !== len && !endsWithLineTerminator(result)) {
 17606         result += newline;
 17608       for (; i < len; i += 1) {
 17609         fragment = addIndent(generateStatement(stmt.consequent[i], {
 17610           semicolonOptional: i === len - 1 && semicolon === ''
 17611         }));
 17612         result += fragment;
 17613         if (i + 1 !== len && !endsWithLineTerminator(fragment)) {
 17614           result += newline;
 17617       base = previousBase;
 17618       break;
 17619     case Syntax.IfStatement:
 17620       previousBase = base;
 17621       base += indent;
 17622       if (stmt.alternate) {
 17623         if (stmt.alternate.type === Syntax.IfStatement) {
 17624           result = 'if' + space + '(' + generateExpression(stmt.test, {
 17625             precedence: Precedence.Sequence,
 17626             allowIn: true,
 17627             allowCall: true
 17628           }) + ')';
 17629           base = previousBase;
 17630           result += maybeBlock(stmt.consequent);
 17631           result += maybeBlockSuffix(stmt.consequent, result);
 17632           result += 'else ' + generateStatement(stmt.alternate);
 17633         } else {
 17634           result = 'if' + space + '(' + generateExpression(stmt.test, {
 17635             precedence: Precedence.Sequence,
 17636             allowIn: true,
 17637             allowCall: true
 17638           }) + ')';
 17639           base = previousBase;
 17640           result += maybeBlock(stmt.consequent);
 17641           result += maybeBlockSuffix(stmt.consequent, result);
 17642           result += 'else';
 17643           result = join(result, maybeBlock(stmt.alternate, semicolon === ''));
 17645       } else {
 17646         result = 'if' + space + '(' + generateExpression(stmt.test, {
 17647           precedence: Precedence.Sequence,
 17648           allowIn: true,
 17649           allowCall: true
 17650         }) + ')';
 17651         base = previousBase;
 17652         result += maybeBlock(stmt.consequent, semicolon === '');
 17654       break;
 17655     case Syntax.ForStatement:
 17656       previousBase = base;
 17657       base += indent;
 17658       result = 'for' + space + '(';
 17659       if (stmt.init) {
 17660         if (stmt.init.type === Syntax.VariableDeclaration) {
 17661           result += generateStatement(stmt.init, {
 17662             allowIn: false
 17663           });
 17664         } else {
 17665           result += generateExpression(stmt.init, {
 17666             precedence: Precedence.Sequence,
 17667             allowIn: false,
 17668             allowCall: true
 17669           }) + ';';
 17671       } else {
 17672         result += ';';
 17674       if (stmt.test) {
 17675         result += space + generateExpression(stmt.test, {
 17676           precedence: Precedence.Sequence,
 17677           allowIn: true,
 17678           allowCall: true
 17679         }) + ';';
 17680       } else {
 17681         result += ';';
 17683       if (stmt.update) {
 17684         result += space + generateExpression(stmt.update, {
 17685           precedence: Precedence.Sequence,
 17686           allowIn: true,
 17687           allowCall: true
 17688         }) + ')';
 17689       } else {
 17690         result += ')';
 17692       base = previousBase;
 17693       result += maybeBlock(stmt.body, semicolon === '');
 17694       break;
 17695     case Syntax.ForInStatement:
 17696       result = 'for' + space + '(';
 17697       if (stmt.left.type === Syntax.VariableDeclaration) {
 17698         previousBase = base;
 17699         base += indent + indent;
 17700         result += stmt.left.kind + ' ' + generateStatement(stmt.left.declarations[0], {
 17701           allowIn: false
 17702         });
 17703         base = previousBase;
 17704       } else {
 17705         previousBase = base;
 17706         base += indent;
 17707         result += generateExpression(stmt.left, {
 17708           precedence: Precedence.Call,
 17709           allowIn: true,
 17710           allowCall: true
 17711         });
 17712         base = previousBase;
 17714       previousBase = base;
 17715       base += indent;
 17716       result = join(result, 'in');
 17717       result = join(result, generateExpression(stmt.right, {
 17718         precedence: Precedence.Sequence,
 17719         allowIn: true,
 17720         allowCall: true
 17721       })) + ')';
 17722       base = previousBase;
 17723       result += maybeBlock(stmt.body, semicolon === '');
 17724       break;
 17725     case Syntax.LabeledStatement:
 17726       result = stmt.label.name + ':' + maybeBlock(stmt.body, semicolon === '');
 17727       break;
 17728     case Syntax.Program:
 17729       result = '';
 17730       for (i = 0, len = stmt.body.length; i < len; i += 1) {
 17731         fragment = addIndent(generateStatement(stmt.body[i], {
 17732           semicolonOptional: i === len - 1
 17733         }));
 17734         result += fragment;
 17735         if (i + 1 < len && !endsWithLineTerminator(fragment)) {
 17736           result += newline;
 17739       break;
 17740     case Syntax.FunctionDeclaration:
 17741       result = 'function' + space;
 17742       if (stmt.id) {
 17743         result += (space === '' ? ' ' : '') + stmt.id.name;
 17745       result += generateFunctionBody(stmt);
 17746       break;
 17747     case Syntax.ReturnStatement:
 17748       if (stmt.argument) {
 17749         result = join('return', generateExpression(stmt.argument, {
 17750           precedence: Precedence.Sequence,
 17751           allowIn: true,
 17752           allowCall: true
 17753         })) + semicolon;
 17754       } else {
 17755         result = 'return' + semicolon;
 17757       break;
 17758     case Syntax.WhileStatement:
 17759       previousBase = base;
 17760       base += indent;
 17761       result = 'while' + space + '(' + generateExpression(stmt.test, {
 17762         precedence: Precedence.Sequence,
 17763         allowIn: true,
 17764         allowCall: true
 17765       }) + ')';
 17766       base = previousBase;
 17767       result += maybeBlock(stmt.body, semicolon === '');
 17768       break;
 17769     case Syntax.WithStatement:
 17770       previousBase = base;
 17771       base += indent;
 17772       result = 'with' + space + '(' + generateExpression(stmt.object, {
 17773         precedence: Precedence.Sequence,
 17774         allowIn: true,
 17775         allowCall: true
 17776       }) + ')';
 17777       base = previousBase;
 17778       result += maybeBlock(stmt.body, semicolon === '');
 17779       break;
 17780     default:
 17781       break;
 17783     if (result === undefined) {
 17784       throw new Error('Unknown statement type: ' + stmt.type);
 17786     if (extra.comment) {
 17787       return addCommentsToStatement(stmt, result);
 17789     return result;
 17791   function generate(node, options) {
 17792     var defaultOptions = getDefaultOptions();
 17793     if (typeof options !== 'undefined') {
 17794       if (typeof options.indent === 'string') {
 17795         defaultOptions.format.indent.style = options.indent;
 17797       if (typeof options.base === 'number') {
 17798         defaultOptions.format.indent.base = options.base;
 17800       options = updateDeeply(defaultOptions, options);
 17801       indent = options.format.indent.style;
 17802       if (typeof options.base === 'string') {
 17803         base = options.base;
 17804       } else {
 17805         base = stringRepeat(indent, options.format.indent.base);
 17807     } else {
 17808       options = defaultOptions;
 17809       indent = options.format.indent.style;
 17810       base = stringRepeat(indent, options.format.indent.base);
 17812     json = options.format.json;
 17813     renumber = options.format.renumber;
 17814     hexadecimal = json ? false : options.format.hexadecimal;
 17815     quotes = json ? 'double' : options.format.quotes;
 17816     escapeless = options.format.escapeless;
 17817     if (options.format.compact) {
 17818       newline = space = indent = base = '';
 17819     } else {
 17820       newline = '\n';
 17821       space = ' ';
 17823     parentheses = options.format.parentheses;
 17824     semicolons = options.format.semicolons;
 17825     parse = json ? null : options.parse;
 17826     extra = options;
 17827     switch (node.type) {
 17828     case Syntax.BlockStatement:
 17829     case Syntax.BreakStatement:
 17830     case Syntax.CatchClause:
 17831     case Syntax.ContinueStatement:
 17832     case Syntax.DoWhileStatement:
 17833     case Syntax.DebuggerStatement:
 17834     case Syntax.EmptyStatement:
 17835     case Syntax.ExpressionStatement:
 17836     case Syntax.ForStatement:
 17837     case Syntax.ForInStatement:
 17838     case Syntax.FunctionDeclaration:
 17839     case Syntax.IfStatement:
 17840     case Syntax.LabeledStatement:
 17841     case Syntax.Program:
 17842     case Syntax.ReturnStatement:
 17843     case Syntax.SwitchStatement:
 17844     case Syntax.SwitchCase:
 17845     case Syntax.ThrowStatement:
 17846     case Syntax.TryStatement:
 17847     case Syntax.VariableDeclaration:
 17848     case Syntax.VariableDeclarator:
 17849     case Syntax.WhileStatement:
 17850     case Syntax.WithStatement:
 17851       return generateStatement(node);
 17852     case Syntax.AssignmentExpression:
 17853     case Syntax.ArrayExpression:
 17854     case Syntax.BinaryExpression:
 17855     case Syntax.CallExpression:
 17856     case Syntax.ConditionalExpression:
 17857     case Syntax.FunctionExpression:
 17858     case Syntax.Identifier:
 17859     case Syntax.Literal:
 17860     case Syntax.LogicalExpression:
 17861     case Syntax.MemberExpression:
 17862     case Syntax.NewExpression:
 17863     case Syntax.ObjectExpression:
 17864     case Syntax.Property:
 17865     case Syntax.SequenceExpression:
 17866     case Syntax.ThisExpression:
 17867     case Syntax.UnaryExpression:
 17868     case Syntax.UpdateExpression:
 17869       return generateExpression(node, {
 17870         precedence: Precedence.Sequence,
 17871         allowIn: true,
 17872         allowCall: true
 17873       });
 17874     default:
 17875       break;
 17877     throw new Error('Unknown node type: ' + node.type);
 17879   VisitorKeys = {
 17880     AssignmentExpression: [
 17881       'left',
 17882       'right'
 17883     ],
 17884     ArrayExpression: [
 17885       'elements'
 17886     ],
 17887     BlockStatement: [
 17888       'body'
 17889     ],
 17890     BinaryExpression: [
 17891       'left',
 17892       'right'
 17893     ],
 17894     BreakStatement: [
 17895       'label'
 17896     ],
 17897     CallExpression: [
 17898       'callee',
 17899       'arguments'
 17900     ],
 17901     CatchClause: [
 17902       'param',
 17903       'body'
 17904     ],
 17905     ConditionalExpression: [
 17906       'test',
 17907       'consequent',
 17908       'alternate'
 17909     ],
 17910     ContinueStatement: [
 17911       'label'
 17912     ],
 17913     DoWhileStatement: [
 17914       'body',
 17915       'test'
 17916     ],
 17917     DebuggerStatement: [],
 17918     EmptyStatement: [],
 17919     ExpressionStatement: [
 17920       'expression'
 17921     ],
 17922     ForStatement: [
 17923       'init',
 17924       'test',
 17925       'update',
 17926       'body'
 17927     ],
 17928     ForInStatement: [
 17929       'left',
 17930       'right',
 17931       'body'
 17932     ],
 17933     FunctionDeclaration: [
 17934       'id',
 17935       'params',
 17936       'body'
 17937     ],
 17938     FunctionExpression: [
 17939       'id',
 17940       'params',
 17941       'body'
 17942     ],
 17943     Identifier: [],
 17944     IfStatement: [
 17945       'test',
 17946       'consequent',
 17947       'alternate'
 17948     ],
 17949     Literal: [],
 17950     LabeledStatement: [
 17951       'label',
 17952       'body'
 17953     ],
 17954     LogicalExpression: [
 17955       'left',
 17956       'right'
 17957     ],
 17958     MemberExpression: [
 17959       'object',
 17960       'property'
 17961     ],
 17962     NewExpression: [
 17963       'callee',
 17964       'arguments'
 17965     ],
 17966     ObjectExpression: [
 17967       'properties'
 17968     ],
 17969     Program: [
 17970       'body'
 17971     ],
 17972     Property: [
 17973       'key',
 17974       'value'
 17975     ],
 17976     ReturnStatement: [
 17977       'argument'
 17978     ],
 17979     SequenceExpression: [
 17980       'expressions'
 17981     ],
 17982     SwitchStatement: [
 17983       'descriminant',
 17984       'cases'
 17985     ],
 17986     SwitchCase: [
 17987       'test',
 17988       'consequent'
 17989     ],
 17990     ThisExpression: [],
 17991     ThrowStatement: [
 17992       'argument'
 17993     ],
 17994     TryStatement: [
 17995       'block',
 17996       'handlers',
 17997       'finalizer'
 17998     ],
 17999     UnaryExpression: [
 18000       'argument'
 18001     ],
 18002     UpdateExpression: [
 18003       'argument'
 18004     ],
 18005     VariableDeclaration: [
 18006       'declarations'
 18007     ],
 18008     VariableDeclarator: [
 18009       'id',
 18010       'init'
 18011     ],
 18012     WhileStatement: [
 18013       'test',
 18014       'body'
 18015     ],
 18016     WithStatement: [
 18017       'object',
 18018       'body'
 18019     ],
 18020     PointerType: [
 18021       'base'
 18022     ],
 18023     StructType: [
 18024       'id',
 18025       'fields'
 18026     ],
 18027     FieldDeclarator: [
 18028       'id',
 18029       'decltype'
 18030     ],
 18031     ArrowType: [
 18032       'params',
 18033       'return'
 18034     ],
 18035     TypeIdentifier: [],
 18036     TypeAliasDirective: [
 18037       'original',
 18038       'alias'
 18039     ],
 18040     CastExpression: [
 18041       'as',
 18042       'argument'
 18044   };
 18045   VisitorOption = {
 18046     Break: 1,
 18047     Skip: 2
 18048   };
 18049   function traverse(top, visitor) {
 18050     var worklist, leavelist, node, ret, current, current2, candidates, candidate;
 18051     worklist = [
 18052       top
 18053     ];
 18054     leavelist = [];
 18055     while (worklist.length) {
 18056       node = worklist.pop();
 18057       if (node) {
 18058         if (visitor.enter) {
 18059           ret = visitor.enter(node);
 18060         } else {
 18061           ret = undefined;
 18063         if (ret === VisitorOption.Break) {
 18064           return;
 18066         worklist.push(null);
 18067         leavelist.push(node);
 18068         if (ret !== VisitorOption.Skip) {
 18069           candidates = VisitorKeys[node.type];
 18070           current = candidates.length;
 18071           while ((current -= 1) >= 0) {
 18072             candidate = node[candidates[current]];
 18073             if (candidate) {
 18074               if (isArray(candidate)) {
 18075                 current2 = candidate.length;
 18076                 while ((current2 -= 1) >= 0) {
 18077                   if (candidate[current2]) {
 18078                     worklist.push(candidate[current2]);
 18081               } else {
 18082                 worklist.push(candidate);
 18087       } else {
 18088         node = leavelist.pop();
 18089         if (visitor.leave) {
 18090           ret = visitor.leave(node);
 18091         } else {
 18092           ret = undefined;
 18094         if (ret === VisitorOption.Break) {
 18095           return;
 18100   function upperBound(array, func) {
 18101     var diff, len, i, current;
 18102     len = array.length;
 18103     i = 0;
 18104     while (len) {
 18105       diff = len >>> 1;
 18106       current = i + diff;
 18107       if (func(array[current])) {
 18108         len = diff;
 18109       } else {
 18110         i = current + 1;
 18111         len -= diff + 1;
 18114     return i;
 18116   function lowerBound(array, func) {
 18117     var diff, len, i, current;
 18118     len = array.length;
 18119     i = 0;
 18120     while (len) {
 18121       diff = len >>> 1;
 18122       current = i + diff;
 18123       if (func(array[current])) {
 18124         i = current + 1;
 18125         len -= diff + 1;
 18126       } else {
 18127         len = diff;
 18130     return i;
 18132   function extendCommentRange(comment, tokens) {
 18133     var target, token;
 18134     target = upperBound(tokens, function search(token) {
 18135       return token.range[0] > comment.range[0];
 18136     });
 18137     comment.extendedRange = [
 18138       comment.range[0],
 18139       comment.range[1]
 18140     ];
 18141     if (target !== tokens.length) {
 18142       comment.extendedRange[1] = tokens[target].range[0];
 18144     target -= 1;
 18145     if (target >= 0) {
 18146       if (target < tokens.length) {
 18147         comment.extendedRange[0] = tokens[target].range[1];
 18148       } else if (token.length) {
 18149         comment.extendedRange[1] = tokens[tokens.length - 1].range[0];
 18152     return comment;
 18154   function attachComments(tree, providedComments, tokens) {
 18155     var comments = [], comment, len, i;
 18156     if (!tree.range) {
 18157       throw new Error('attachComments needs range information');
 18159     if (!tokens.length) {
 18160       if (providedComments.length) {
 18161         for (i = 0, len = providedComments.length; i < len; i += 1) {
 18162           comment = deepCopy(providedComments[i]);
 18163           comment.extendedRange = [
 18164             0,
 18165             tree.range[0]
 18166           ];
 18167           comments.push(comment);
 18169         tree.leadingComments = comments;
 18171       return tree;
 18173     for (i = 0, len = providedComments.length; i < len; i += 1) {
 18174       comments.push(extendCommentRange(deepCopy(providedComments[i]), tokens));
 18176     traverse(tree, {
 18177       cursor: 0,
 18178       enter: function (node) {
 18179         var comment;
 18180         while (this.cursor < comments.length) {
 18181           comment = comments[this.cursor];
 18182           if (comment.extendedRange[1] > node.range[0]) {
 18183             break;
 18185           if (comment.extendedRange[1] === node.range[0]) {
 18186             if (!node.leadingComments) {
 18187               node.leadingComments = [];
 18189             node.leadingComments.push(comment);
 18190             comments.splice(this.cursor, 1);
 18191           } else {
 18192             this.cursor += 1;
 18195         if (this.cursor === comments.length) {
 18196           return VisitorOption.Break;
 18198         if (comments[this.cursor].extendedRange[0] > node.range[1]) {
 18199           return VisitorOption.Skip;
 18202     });
 18203     traverse(tree, {
 18204       cursor: 0,
 18205       leave: function (node) {
 18206         var comment;
 18207         while (this.cursor < comments.length) {
 18208           comment = comments[this.cursor];
 18209           if (node.range[1] < comment.extendedRange[0]) {
 18210             break;
 18212           if (node.range[1] === comment.extendedRange[0]) {
 18213             if (!node.trailingComments) {
 18214               node.trailingComments = [];
 18216             node.trailingComments.push(comment);
 18217             comments.splice(this.cursor, 1);
 18218           } else {
 18219             this.cursor += 1;
 18222         if (this.cursor === comments.length) {
 18223           return VisitorOption.Break;
 18225         if (comments[this.cursor].extendedRange[0] > node.range[1]) {
 18226           return VisitorOption.Skip;
 18229     });
 18230     return tree;
 18232   exports.version = '0.0.6-dev';
 18233   exports.generate = generate;
 18234   exports.traverse = traverse;
 18235   exports.attachComments = attachComments;
 18236 }(typeof exports === 'undefined' ? escodegen = {} : exports));
 18237 var verifierOptions = systemOptions.register(new OptionSet('Verifier Options'));
 18238 var verifierTraceLevel = verifierOptions.register(new Option('tv', 'tv', 'number', 0, 'Verifier Trace Level'));
 18239 var Type = function () {
 18240     function type() {
 18241       unexpected('Type is Abstract');
 18243     type.prototype.equals = function (other) {
 18244       return this === other;
 18245     };
 18246     type.prototype.merge = function (other) {
 18247       unexpected('Merging ' + this + ' with ' + other);
 18248     };
 18249     type.cache = {
 18250       name: {},
 18251       classInfo: [],
 18252       instanceInfo: [],
 18253       scriptInfo: [],
 18254       methodInfo: []
 18255     };
 18256     type.from = function from(x, domain) {
 18257       var traitsTypeCache = null;
 18258       if (x instanceof ClassInfo) {
 18259         traitsTypeCache = type.cache.classInfo;
 18260       } else if (x instanceof InstanceInfo) {
 18261         traitsTypeCache = type.cache.instanceInfo;
 18262       } else if (x instanceof ScriptInfo) {
 18263         traitsTypeCache = type.cache.scriptInfo;
 18265       if (traitsTypeCache) {
 18266         return traitsTypeCache[x.runtimeId] || (traitsTypeCache[x.runtimeId] = new TraitsType(x, domain));
 18268       if (x instanceof ActivationInfo) {
 18269         return new TraitsType(x.methodInfo);
 18270       } else if (x instanceof Global) {
 18271         return new TraitsType(x.scriptInfo);
 18272       } else if (x instanceof Interface) {
 18273         return new TraitsType(x.classInfo, domain);
 18274       } else if (x instanceof MethodInfo) {
 18275         return new MethodType(x);
 18276       } else if (domain && x instanceof Class) {
 18277         return type.from(x.classInfo, domain);
 18279       return Type.Any;
 18280     };
 18281     type.fromSimpleName = function (name, domain) {
 18282       return Type.fromName(Multiname.fromSimpleName(name), domain);
 18283     };
 18284     type.fromName = function fromName(mn, domain) {
 18285       if (mn === undefined) {
 18286         return Type.Undefined;
 18287       } else {
 18288         var qn = Multiname.isQName(mn) ? Multiname.getFullQualifiedName(mn) : undefined;
 18289         if (qn) {
 18290           var ty = type.cache.name[qn];
 18291           if (ty) {
 18292             return ty;
 18295         if (qn === Multiname.getPublicQualifiedName('void')) {
 18296           return Type.Void;
 18298         true;
 18299         ty = domain.findClassInfo(mn);
 18300         ty = ty ? type.from(ty, domain) : Type.Any;
 18301         if (mn.hasTypeParameter()) {
 18302           ty = new ParameterizedType(ty, type.fromName(mn.typeParameter, domain));
 18304         return type.cache.name[qn] = ty;
 18306     };
 18307     type.prototype.applyType = function (parameter) {
 18308       return new ParameterizedType(this, parameter);
 18309     };
 18310     type.prototype.toString = function () {
 18311       return '[type]';
 18312     };
 18313     type.prototype.isNumeric = function () {
 18314       return this === Type.Int || this === Type.Uint || this === Type.Number;
 18315     };
 18316     type.prototype.isString = function () {
 18317       return this === Type.String;
 18318     };
 18319     type.prototype.isDirectlyReadable = function () {
 18320       return this === Type.Array;
 18321     };
 18322     type.prototype.isIndexedReadable = function () {
 18323       return this.isParameterizedType();
 18324     };
 18325     type.prototype.isDirectlyWriteable = function () {
 18326       return this === Type.Array;
 18327     };
 18328     type.prototype.isIndexedWriteable = function () {
 18329       return this.isParameterizedType();
 18330     };
 18331     type.prototype.isVector = function () {
 18332       return this.isParameterizedType();
 18333     };
 18334     type.prototype.isNotDirectlyIndexable = function () {
 18335       return this === Type.Any || this === Type.XML || this === Type.XMLList || this === Type.Dictionary;
 18336     };
 18337     type.prototype.isParameterizedType = function () {
 18338       return this instanceof ParameterizedType;
 18339     };
 18340     type.prototype.instanceType = function () {
 18341       return this;
 18342     };
 18343     type.prototype.getTrait = function () {
 18344       return null;
 18345     };
 18346     type.prototype.super = function () {
 18347       unexpected('Can\'t call super on ' + this);
 18348     };
 18349     type.prototype.isSubtypeOf = function (other) {
 18350       if (this === other || this.equals(other)) {
 18351         return true;
 18353       return this.merge(other) === this;
 18354     };
 18355     var typesInitialized = false;
 18356     type.initializeTypes = function (domain) {
 18357       if (typesInitialized) {
 18358         return;
 18360       type.Any = new AtomType('Any');
 18361       type.Null = new AtomType('Null');
 18362       type.Undefined = new AtomType('Undefined');
 18363       type.Void = new AtomType('Void');
 18364       type.Int = Type.fromSimpleName('int', domain).instanceType();
 18365       type.Uint = Type.fromSimpleName('uint', domain).instanceType();
 18366       type.Class = Type.fromSimpleName('Class', domain).instanceType();
 18367       type.Array = Type.fromSimpleName('Array', domain).instanceType();
 18368       type.Object = Type.fromSimpleName('Object', domain).instanceType();
 18369       type.String = Type.fromSimpleName('String', domain).instanceType();
 18370       type.Number = Type.fromSimpleName('Number', domain).instanceType();
 18371       type.Boolean = Type.fromSimpleName('Boolean', domain).instanceType();
 18372       type.Function = Type.fromSimpleName('Function', domain).instanceType();
 18373       type.XML = Type.fromSimpleName('XML', domain).instanceType();
 18374       type.XMLList = Type.fromSimpleName('XMLList', domain).instanceType();
 18375       type.Dictionary = Type.fromSimpleName('flash.utils.Dictionary', domain).instanceType();
 18376       typesInitialized = true;
 18377     };
 18378     return type;
 18379   }();
 18380 var AtomType = function () {
 18381     function atomType(name) {
 18382       this.name = name;
 18384     atomType.prototype = Object.create(Type.prototype);
 18385     atomType.prototype.toString = function () {
 18386       if (this === Type.Any) {
 18387         return '?';
 18388       } else if (this === Type.Undefined) {
 18389         return '_';
 18390       } else if (this === Type.Null) {
 18391         return 'X';
 18392       } else if (this === Type.Void) {
 18393         return 'V';
 18395       unexpected();
 18396     };
 18397     atomType.prototype.merge = function merge(other) {
 18398       if (other instanceof TraitsType) {
 18399         return Type.Any;
 18401       if (this === other) {
 18402         return this;
 18404       if (this === Type.Any || other === Type.Any) {
 18405         return Type.Any;
 18407       return Type.Any;
 18408     };
 18409     return atomType;
 18410   }();
 18411 var MethodType = function () {
 18412     function methodType(methodInfo) {
 18413       this.methodInfo = methodInfo;
 18415     methodType.prototype = Object.create(Type.prototype);
 18416     methodType.prototype.toString = function () {
 18417       return 'MT ' + this.methodInfo;
 18418     };
 18419     return methodType;
 18420   }();
 18421 var TraitsType = function () {
 18422     function traitsType(object, domain) {
 18423       true;
 18424       this.object = object;
 18425       this.traits = object.traits;
 18426       this.domain = domain;
 18427       if (this.object instanceof InstanceInfo) {
 18428         true;
 18431     traitsType.prototype = Object.create(Type.prototype);
 18432     function nameOf(x) {
 18433       if (x instanceof ScriptInfo) {
 18434         return 'SI';
 18435       } else if (x instanceof ClassInfo) {
 18436         return 'CI:' + x.instanceInfo.name.name;
 18437       } else if (x instanceof InstanceInfo) {
 18438         return 'II:' + x.name.name;
 18439       } else if (x instanceof MethodInfo) {
 18440         return 'MI';
 18441       } else if (x instanceof ActivationInfo) {
 18442         return 'AC';
 18444       true;
 18446     function findTraitBySlotId(traits, slotId) {
 18447       for (var i = traits.length - 1; i >= 0; i--) {
 18448         if (traits[i].slotId === slotId) {
 18449           return traits[i];
 18452       unexpected('Cannot find trait with slotId: ' + slotId + ' in ' + traits);
 18454     function findTraitByName(traits, mn, isSetter) {
 18455       var isGetter = !isSetter;
 18456       var trait;
 18457       if (!Multiname.isQName(mn)) {
 18458         if (mn instanceof MultinameType) {
 18459           return;
 18461         true;
 18462         var dy;
 18463         for (var i = 0, j = mn.namespaces.length; i < j; i++) {
 18464           var qn = mn.getQName(i);
 18465           if (mn.namespaces[i].isDynamic()) {
 18466             dy = qn;
 18467           } else {
 18468             if (trait = findTraitByName(traits, qn, isSetter)) {
 18469               return trait;
 18473         if (dy) {
 18474           return findTraitByName(traits, dy, isSetter);
 18476       } else {
 18477         var qn = Multiname.getQualifiedName(mn);
 18478         for (var i = 0, j = traits.length; i < j; i++) {
 18479           trait = traits[i];
 18480           if (Multiname.getQualifiedName(trait.name) === qn) {
 18481             if (isSetter && trait.isGetter() || isGetter && trait.isSetter()) {
 18482               continue;
 18484             return trait;
 18489     traitsType.prototype.getTrait = function (mn, isSetter, followSuperType) {
 18490       if (mn instanceof MultinameType) {
 18491         return null;
 18493       if (mn.isAttribute()) {
 18494         return null;
 18496       if (followSuperType && (this.isInstanceInfo() || this.isClassInfo())) {
 18497         var that = this;
 18498         do {
 18499           var trait = that.getTrait(mn, isSetter, false);
 18500           if (!trait) {
 18501             that = that.super();
 18503         } while (!trait && that);
 18504         return trait;
 18505       } else {
 18506         return findTraitByName(this.traits, mn, isSetter);
 18508     };
 18509     traitsType.prototype.getTraitAt = function (i) {
 18510       if (this.object instanceof ScriptInfo || this.object instanceof MethodInfo) {
 18511         return findTraitBySlotId(this.traits, i);
 18513     };
 18514     traitsType.prototype.toString = function () {
 18515       switch (this) {
 18516       case Type.Int:
 18517         return 'I';
 18518       case Type.Uint:
 18519         return 'U';
 18520       case Type.Array:
 18521         return 'A';
 18522       case Type.Object:
 18523         return 'O';
 18524       case Type.String:
 18525         return 'S';
 18526       case Type.Number:
 18527         return 'N';
 18528       case Type.Boolean:
 18529         return 'B';
 18530       case Type.Function:
 18531         return 'F';
 18533       return nameOf(this.object);
 18534     };
 18535     traitsType.prototype.instanceType = function () {
 18536       true;
 18537       return this.instanceCache || (this.instanceCache = Type.from(this.object.instanceInfo, this.domain));
 18538     };
 18539     traitsType.prototype.classType = function () {
 18540       true;
 18541       return this.instanceCache || (this.instanceCache = Type.from(this.object.classInfo, this.domain));
 18542     };
 18543     traitsType.prototype.super = function () {
 18544       if (this.object instanceof ClassInfo) {
 18545         return Type.Class;
 18547       true;
 18548       if (this.object.superName) {
 18549         var result = Type.fromName(this.object.superName, this.domain).instanceType();
 18550         true;
 18551         return result;
 18553       return null;
 18554     };
 18555     traitsType.prototype.isScriptInfo = function () {
 18556       return this.object instanceof ScriptInfo;
 18557     };
 18558     traitsType.prototype.isClassInfo = function () {
 18559       return this.object instanceof ClassInfo;
 18560     };
 18561     traitsType.prototype.isInstanceInfo = function () {
 18562       return this.object instanceof InstanceInfo;
 18563     };
 18564     traitsType.prototype.isInstanceOrClassInfo = function () {
 18565       return this.isInstanceInfo() || this.isClassInfo();
 18566     };
 18567     traitsType.prototype.equals = function (other) {
 18568       return this.traits === other.traits;
 18569     };
 18570     traitsType.prototype.merge = function (other) {
 18571       if (other instanceof TraitsType) {
 18572         if (this.equals(other)) {
 18573           return this;
 18575         if (this.isNumeric() && other.isNumeric()) {
 18576           return Type.Number;
 18578         if (this.isInstanceInfo() && other.isInstanceInfo()) {
 18579           var path = [];
 18580           for (var curr = this; curr; curr = curr.super()) {
 18581             path.push(curr);
 18583           for (var curr = other; curr; curr = curr.super()) {
 18584             for (var i = 0; i < path.length; i++) {
 18585               if (path[i].equals(curr)) {
 18586                 return curr;
 18590           return Type.Object;
 18593       return Type.Any;
 18594     };
 18595     return traitsType;
 18596   }();
 18597 var MultinameType = function () {
 18598     function multinameType(namespaces, name, flags) {
 18599       this.namespaces = namespaces;
 18600       this.name = name;
 18601       this.flags = flags;
 18603     multinameType.prototype = Object.create(Type.prototype);
 18604     multinameType.prototype.toString = function () {
 18605       return 'MN';
 18606     };
 18607     return multinameType;
 18608   }();
 18609 var ParameterizedType = function () {
 18610     function parameterizedType(type, parameter) {
 18611       this.type = type;
 18612       this.parameter = parameter;
 18614     parameterizedType.prototype = Object.create(Type.prototype);
 18615     parameterizedType.prototype.toString = function () {
 18616       return this.type + '<' + this.parameter + '>';
 18617     };
 18618     parameterizedType.prototype.instanceType = function () {
 18619       true;
 18620       return new ParameterizedType(this.type.instanceType(), this.parameter.instanceType());
 18621     };
 18622     parameterizedType.prototype.equals = function (other) {
 18623       if (other instanceof ParameterizedType) {
 18624         return this.type.equals(other.type) && this.parameter.equals(other.parameter);
 18626       return false;
 18627     };
 18628     parameterizedType.prototype.merge = function (other) {
 18629       if (other instanceof TraitsType) {
 18630         if (this.equals(other)) {
 18631           return this;
 18634       return Type.Any;
 18635     };
 18636     return parameterizedType;
 18637   }();
 18638 var TypeInformation = function () {
 18639     function typeInformation() {
 18641     typeInformation.prototype.toString = function () {
 18642       return toKeyValueArray(this).map(function (x) {
 18643         return x[0] + ': ' + x[1];
 18644       }).join(' | ');
 18645     };
 18646     return typeInformation;
 18647   }();
 18648 var Verifier = function () {
 18649     function VerifierError(message) {
 18650       this.name = 'VerifierError';
 18651       this.message = message || '';
 18653     var State = function () {
 18654         var id = 0;
 18655         function state() {
 18656           this.id = id += 1;
 18657           this.stack = [];
 18658           this.scope = [];
 18659           this.local = [];
 18661         state.prototype.clone = function clone() {
 18662           var s = new State();
 18663           s.originalId = this.id;
 18664           s.stack = this.stack.slice(0);
 18665           s.scope = this.scope.slice(0);
 18666           s.local = this.local.slice(0);
 18667           return s;
 18668         };
 18669         state.prototype.trace = function trace(writer) {
 18670           writer.writeLn(this.toString());
 18671         };
 18672         state.prototype.toString = function () {
 18673           return '<' + this.id + (this.originalId ? ':' + this.originalId : '') + ', L[' + this.local.join(', ') + ']' + ', S[' + this.stack.join(', ') + ']' + ', $[' + this.scope.join(', ') + ']>';
 18674         };
 18675         state.prototype.equals = function (other) {
 18676           return arrayEquals(this.stack, other.stack) && arrayEquals(this.scope, other.scope) && arrayEquals(this.local, other.local);
 18677         };
 18678         function arrayEquals(a, b) {
 18679           if (a.length != b.length) {
 18680             return false;
 18682           for (var i = a.length - 1; i >= 0; i--) {
 18683             if (!a[i].equals(b[i])) {
 18684               return false;
 18687           return true;
 18689         state.prototype.isSubset = function (other) {
 18690           return arraySubset(this.stack, other.stack) && arraySubset(this.scope, other.scope) && arraySubset(this.local, other.local);
 18691         };
 18692         function arraySubset(a, b) {
 18693           if (a.length != b.length) {
 18694             return false;
 18696           for (var i = a.length - 1; i >= 0; i--) {
 18697             if (a[i] === b[i] || a[i].equals(b[i])) {
 18698               continue;
 18700             if (a[i].merge(b[i]) !== a[i]) {
 18701               return false;
 18704           return true;
 18706         state.prototype.merge = function (other) {
 18707           mergeArrays(this.local, other.local);
 18708           mergeArrays(this.stack, other.stack);
 18709           mergeArrays(this.scope, other.scope);
 18710         };
 18711         function mergeArrays(a, b) {
 18712           true;
 18713           for (var i = a.length - 1; i >= 0; i--) {
 18714             true;
 18715             if (a[i] === b[i]) {
 18716               continue;
 18718             a[i] = a[i].merge(b[i]);
 18721         return state;
 18722       }();
 18723     var Verification = function () {
 18724         function verification(methodInfo, domain, savedScope) {
 18725           this.savedScope = savedScope;
 18726           this.methodInfo = methodInfo;
 18727           this.domain = domain;
 18728           this.writer = new IndentingWriter();
 18729           this.returnType = Type.Undefined;
 18731         verification.prototype.verify = function verify() {
 18732           var mi = this.methodInfo;
 18733           var writer = verifierTraceLevel.value ? this.writer : null;
 18734           var blocks = mi.analysis.blocks;
 18735           blocks.forEach(function (x) {
 18736             x.entryState = x.exitState = null;
 18737           });
 18738           if (writer) {
 18739             this.methodInfo.trace(writer);
 18741           var entryState = new State();
 18742           true;
 18743           this.thisType = mi.holder ? Type.from(mi.holder, this.domain) : Type.Any;
 18744           entryState.local.push(this.thisType);
 18745           for (var i = 0; i < mi.parameters.length; i++) {
 18746             entryState.local.push(Type.fromName(mi.parameters[i].type, this.domain).instanceType());
 18748           var remainingLocals = mi.localCount - mi.parameters.length - 1;
 18749           if (mi.needsRest() || mi.needsArguments()) {
 18750             entryState.local.push(Type.Array);
 18751             remainingLocals -= 1;
 18753           for (var i = 0; i < remainingLocals; i++) {
 18754             entryState.local.push(Type.Undefined);
 18756           true;
 18757           if (writer) {
 18758             entryState.trace(writer);
 18760           for (var bi = 0, len = blocks.length; bi < len; bi++) {
 18761             blocks[bi].bdo = bi;
 18763           var worklist = new Shumway.SortedList(function compare(blockA, blockB) {
 18764               return blockA.bdo - blockB.bdo;
 18765             });
 18766           blocks[0].entryState = entryState;
 18767           worklist.push(blocks[0]);
 18768           while (!worklist.isEmpty()) {
 18769             var block = worklist.pop();
 18770             var exitState = block.exitState = block.entryState.clone();
 18771             this.verifyBlock(block, exitState);
 18772             block.succs.forEach(function (successor) {
 18773               if (worklist.contains(successor)) {
 18774                 if (writer) {
 18775                   writer.writeLn('Forward Merged Block: ' + successor.bid + ' ' + exitState.toString() + ' with ' + successor.entryState.toString());
 18777                 successor.entryState.merge(exitState);
 18778                 if (writer) {
 18779                   writer.writeLn('Merged State: ' + successor.entryState);
 18781                 return;
 18783               if (successor.entryState) {
 18784                 if (!successor.entryState.isSubset(exitState)) {
 18785                   if (writer) {
 18786                     writer.writeLn('Backward Merged Block: ' + block.bid + ' with ' + successor.bid + ' ' + exitState.toString() + ' with ' + successor.entryState.toString());
 18788                   successor.entryState.merge(exitState);
 18789                   worklist.push(successor);
 18790                   if (writer) {
 18791                     writer.writeLn('Merged State: ' + successor.entryState);
 18794                 return;
 18796               successor.entryState = exitState.clone();
 18797               worklist.push(successor);
 18798               if (writer) {
 18799                 writer.writeLn('Added Block: ' + successor.bid + ' to worklist: ' + successor.entryState.toString());
 18801             });
 18803           if (writer) {
 18804             writer.writeLn('Inferred return type: ' + this.returnType);
 18806           this.methodInfo.inferredReturnType = this.returnType;
 18807         };
 18808         verification.prototype.verifyBlock = function verifyBlock(block, state) {
 18809           var savedScope = this.savedScope;
 18810           var globalScope = savedScope[0];
 18811           var local = state.local;
 18812           var stack = state.stack;
 18813           var scope = state.scope;
 18814           var writer = verifierTraceLevel.value ? this.writer : null;
 18815           var bytecodes = this.methodInfo.analysis.bytecodes;
 18816           var domain = this.domain;
 18817           var multinames = this.methodInfo.abc.constantPool.multinames;
 18818           var mi = this.methodInfo;
 18819           var bc, obj, fn, mn, l, r, val, type, returnType;
 18820           if (writer) {
 18821             writer.enter('verifyBlock: ' + block.bid + ', range: [' + block.position + ', ' + block.end.position + '], entryState: ' + state.toString() + ' {');
 18823           function construct(obj) {
 18824             if (obj instanceof TraitsType || obj instanceof ParameterizedType) {
 18825               if (obj === Type.Function || obj === Type.Class || obj === Type.Object) {
 18826                 return Type.Object;
 18828               return obj.instanceType();
 18829             } else {
 18830               return Type.Any;
 18833           function ti() {
 18834             return bc.ti || (bc.ti = new TypeInformation());
 18836           function push(x) {
 18837             true;
 18838             ti().type = x;
 18839             stack.push(x);
 18841           function pop() {
 18842             return stack.pop();
 18844           function findProperty(mn, strict) {
 18845             if (mn instanceof MultinameType) {
 18846               if (mn.name === 'Array') {
 18847                 debugger;
 18849               return Type.Any;
 18851             for (var i = scope.length - 1; i >= -savedScope.length; i--) {
 18852               var s = i >= 0 ? scope[i] : savedScope[savedScope.length + i];
 18853               if (s instanceof TraitsType) {
 18854                 var trait = s.getTrait(mn, false, true);
 18855                 if (trait) {
 18856                   ti().scopeDepth = scope.length - i - 1;
 18857                   if (s.isClassInfo() || s.isScriptInfo()) {
 18858                     ti().object = LazyInitializer.create(s.object);
 18860                   return s;
 18862               } else {
 18863                 if (mn.name === 'Array') {
 18864                   debugger;
 18866                 return Type.Any;
 18869             var resolved = domain.findDefiningScript(mn, false);
 18870             if (resolved) {
 18871               ti().object = LazyInitializer.create(resolved.script);
 18872               return Type.from(resolved.script, domain);
 18874             if (mn.name === 'Array') {
 18875               debugger;
 18877             return Type.Any;
 18879           function popMultiname() {
 18880             var mn = multinames[bc.index];
 18881             if (mn.isRuntime()) {
 18882               var namespaces = mn.namespaces;
 18883               var name = mn.name;
 18884               if (mn.isRuntimeName()) {
 18885                 name = pop();
 18887               if (mn.isRuntimeNamespace()) {
 18888                 namespaces = [
 18889                   pop()
 18890                 ];
 18892               return new MultinameType(namespaces, name, mn.flags);
 18894             return mn;
 18896           function accessSlot(obj) {
 18897             if (obj instanceof TraitsType) {
 18898               var trait = obj.getTraitAt(bc.index);
 18899               writer && writer.debugLn('accessSlot() -> ' + trait);
 18900               if (trait) {
 18901                 ti().trait = trait;
 18902                 if (trait.isSlot()) {
 18903                   return Type.fromName(trait.typeName, domain).instanceType();
 18904                 } else if (trait.isClass()) {
 18905                   return Type.from(trait.classInfo, domain);
 18909             return Type.Any;
 18911           function isNumericMultiname(mn) {
 18912             return mn instanceof Multiname && Multiname.isNumeric(mn) || mn instanceof MultinameType && (mn.name instanceof TraitsType && mn.name.isNumeric());
 18914           function getProperty(obj, mn) {
 18915             if (obj instanceof TraitsType || obj instanceof ParameterizedType) {
 18916               var trait = obj.getTrait(mn, false, true);
 18917               writer && writer.debugLn('getProperty(' + mn + ') -> ' + trait);
 18918               if (trait) {
 18919                 ti().trait = trait;
 18920                 if (trait.isSlot() || trait.isConst()) {
 18921                   return Type.fromName(trait.typeName, domain).instanceType();
 18922                 } else if (trait.isGetter()) {
 18923                   return Type.fromName(trait.methodInfo.returnType, domain).instanceType();
 18924                 } else if (trait.isClass()) {
 18925                   return Type.from(trait.classInfo, domain);
 18926                 } else if (trait.isMethod()) {
 18927                   return Type.from(trait.methodInfo, domain);
 18929               } else if (obj.isDirectlyReadable() && mn instanceof Multiname) {
 18930                 ti().propertyQName = Multiname.getPublicQualifiedName(mn.name);
 18932               if (isNumericMultiname(mn)) {
 18933                 if (obj.isIndexedReadable()) {
 18934                   ti().isIndexedReadable = true;
 18935                   if (obj.isVector()) {
 18936                     return obj.parameter;
 18938                 } else if (obj.isDirectlyReadable()) {
 18939                   ti().isDirectlyReadable = true;
 18943             return Type.Any;
 18945           function setProperty(obj, mn, value) {
 18946             if (obj instanceof TraitsType || obj instanceof ParameterizedType) {
 18947               var trait = obj.getTrait(mn, true, true);
 18948               writer && writer.debugLn('setProperty(' + mn + ') -> ' + trait);
 18949               if (trait) {
 18950                 ti().trait = trait;
 18951               } else if (obj.isDirectlyWriteable() && mn instanceof Multiname) {
 18952                 ti().propertyQName = Multiname.getPublicQualifiedName(mn.name);
 18954               if (isNumericMultiname(mn)) {
 18955                 if (obj.isDirectlyWriteable()) {
 18956                   ti().isDirectlyWriteable = true;
 18957                 } else if (obj.isVector()) {
 18958                   ti().isIndexedWriteable = true;
 18963           for (var bci = block.position, end = block.end.position; bci <= end; bci++) {
 18964             bc = bytecodes[bci];
 18965             var op = bc.op;
 18966             if (writer && verifierTraceLevel.value > 1) {
 18967               writer.writeLn(('stateBefore: ' + state.toString() + ' $$[' + savedScope.join(', ') + ']').padRight(' ', 100) + ' : ' + bci + ', ' + bc.toString(mi.abc));
 18969             switch (op) {
 18970             case 1:
 18971               break;
 18972             case 3:
 18973               pop();
 18974               break;
 18975             case 4:
 18976               mn = popMultiname();
 18977               obj = pop();
 18978               true;
 18979               ti().baseClass = LazyInitializer.create(this.thisType.super().classType().object);
 18980               push(getProperty(obj.super(), mn));
 18981               break;
 18982             case 5:
 18983               val = pop();
 18984               mn = popMultiname();
 18985               obj = pop();
 18986               true;
 18987               ti().baseClass = LazyInitializer.create(this.thisType.super().classType().object);
 18988               setProperty(obj.super(), mn, val);
 18989               break;
 18990             case 6:
 18991               notImplemented(bc);
 18992               break;
 18993             case 7:
 18994               notImplemented(bc);
 18995               break;
 18996             case 8:
 18997               state.local[bc.index] = Type.Undefined;
 18998               break;
 18999             case 10:
 19000               notImplemented(bc);
 19001               break;
 19002             case 11:
 19003               notImplemented(bc);
 19004               break;
 19005             case 12:
 19006             case 24:
 19007             case 13:
 19008             case 23:
 19009             case 14:
 19010             case 22:
 19011             case 15:
 19012             case 21:
 19013             case 19:
 19014             case 20:
 19015             case 25:
 19016             case 26:
 19017               pop();
 19018               pop();
 19019               break;
 19020             case 16:
 19021               break;
 19022             case 17:
 19023             case 18:
 19024               pop();
 19025               break;
 19026             case 27:
 19027               pop(Type.Int);
 19028               break;
 19029             case 29:
 19030               scope.pop();
 19031               break;
 19032             case 30:
 19033             case 35:
 19034               pop(Type.Int);
 19035               pop();
 19036               push(Type.Any);
 19037               break;
 19038             case 31:
 19039               push(Type.Boolean);
 19040               break;
 19041             case 50:
 19042               push(Type.Boolean);
 19043               break;
 19044             case 32:
 19045               push(Type.Null);
 19046               break;
 19047             case 33:
 19048               push(Type.Undefined);
 19049               break;
 19050             case 34:
 19051               notImplemented(bc);
 19052               break;
 19053             case 36:
 19054               push(Type.Int);
 19055               break;
 19056             case 37:
 19057               push(Type.Int);
 19058               break;
 19059             case 44:
 19060               push(Type.String);
 19061               break;
 19062             case 45:
 19063               push(Type.Int);
 19064               break;
 19065             case 46:
 19066               push(Type.Uint);
 19067               break;
 19068             case 47:
 19069               push(Type.Number);
 19070               break;
 19071             case 38:
 19072               push(Type.Boolean);
 19073               break;
 19074             case 39:
 19075               push(Type.Boolean);
 19076               break;
 19077             case 40:
 19078               push(Type.Number);
 19079               break;
 19080             case 41:
 19081               pop();
 19082               break;
 19083             case 42:
 19084               val = pop();
 19085               push(val);
 19086               push(val);
 19087               break;
 19088             case 43:
 19089               l = pop();
 19090               r = pop();
 19091               push(l);
 19092               push(r);
 19093               break;
 19094             case 28:
 19095               pop();
 19096               scope.push(Type.Any);
 19097               break;
 19098             case 48:
 19099               scope.push(pop());
 19100               break;
 19101             case 49:
 19102               notImplemented(bc);
 19103               break;
 19104             case 53:
 19105             case 54:
 19106             case 55:
 19107               push(Type.Int);
 19108               break;
 19109             case 56:
 19110             case 57:
 19111               push(Type.Number);
 19112               break;
 19113             case 58:
 19114             case 59:
 19115             case 60:
 19116               pop(Type.Int);
 19117               break;
 19118             case 61:
 19119             case 62:
 19120               pop(Type.Number);
 19121               break;
 19122             case 64:
 19123               push(Type.Function);
 19124               break;
 19125             case 65:
 19126               stack.popMany(bc.argCount);
 19127               obj = pop();
 19128               fn = pop();
 19129               push(Type.Any);
 19130               break;
 19131             case 67:
 19132               throw new VerifierError('callmethod');
 19133             case 68:
 19134               notImplemented(bc);
 19135               break;
 19136             case 69:
 19137             case 78:
 19138             case 79:
 19139             case 70:
 19140             case 76:
 19141               stack.popMany(bc.argCount);
 19142               mn = popMultiname();
 19143               obj = pop();
 19144               if (op === OP_callsuper || op === OP_callsupervoid) {
 19145                 obj = this.thisType.super();
 19146                 ti().baseClass = LazyInitializer.create(this.thisType.super().classType().object);
 19148               type = getProperty(obj, mn);
 19149               if (op === OP_callpropvoid || op === OP_callsupervoid) {
 19150                 break;
 19152               if (type instanceof MethodType) {
 19153                 returnType = Type.fromName(type.methodInfo.returnType, domain).instanceType();
 19154               } else if (type instanceof TraitsType && type.isClassInfo()) {
 19155                 returnType = type.instanceType();
 19156               } else {
 19157                 returnType = Type.Any;
 19159               push(returnType);
 19160               break;
 19161             case 71:
 19162               this.returnType.merge(Type.Undefined);
 19163               break;
 19164             case 72:
 19165               type = pop();
 19166               if (mi.returnType) {
 19167                 var coerceType = Type.fromName(mi.returnType, this.domain).instanceType();
 19168                 if (coerceType.isSubtypeOf(type)) {
 19169                   ti().noCoercionNeeded = true;
 19172               break;
 19173             case 73:
 19174               stack.popMany(bc.argCount);
 19175               stack.pop();
 19176               if (this.thisType.isInstanceInfo() && this.thisType.super() === Type.Object) {
 19177                 ti().noCallSuperNeeded = true;
 19178               } else {
 19179                 ti().baseClass = LazyInitializer.create(this.thisType.super().classType().object);
 19181               break;
 19182             case 66:
 19183               stack.popMany(bc.argCount);
 19184               push(construct(pop()));
 19185               break;
 19186             case 74:
 19187               stack.popMany(bc.argCount);
 19188               mn = popMultiname();
 19189               push(construct(getProperty(stack.pop(), mn)));
 19190               break;
 19191             case 75:
 19192               notImplemented(bc);
 19193               break;
 19194             case 77:
 19195               notImplemented(bc);
 19196               break;
 19197             case 80:
 19198             case 81:
 19199             case 82:
 19200               break;
 19201             case 83:
 19202               true;
 19203               val = pop();
 19204               obj = pop();
 19205               if (obj === Type.Any) {
 19206                 push(Type.Any);
 19207               } else {
 19208                 push(obj.applyType(val));
 19210               break;
 19211             case 84:
 19212               notImplemented(bc);
 19213               break;
 19214             case 85:
 19215               stack.popMany(bc.argCount * 2);
 19216               push(Type.Object);
 19217               break;
 19218             case 86:
 19219               stack.popMany(bc.argCount);
 19220               push(Type.Array);
 19221               break;
 19222             case 87:
 19223               push(Type.from(new ActivationInfo(this.methodInfo)));
 19224               break;
 19225             case 88:
 19226               push(Type.Any);
 19227               break;
 19228             case 89:
 19229               popMultiname();
 19230               pop();
 19231               push(Type.XMLList);
 19232               break;
 19233             case 90:
 19234               push(Type.Any);
 19235               break;
 19236             case 93:
 19237               push(findProperty(popMultiname(), true));
 19238               break;
 19239             case 94:
 19240               push(findProperty(popMultiname(), false));
 19241               break;
 19242             case 95:
 19243               notImplemented(bc);
 19244               break;
 19245             case 96:
 19246               mn = popMultiname();
 19247               push(getProperty(findProperty(mn, true), mn));
 19248               break;
 19249             case 104:
 19250             case 97:
 19251               val = pop();
 19252               mn = popMultiname();
 19253               obj = pop();
 19254               setProperty(obj, mn, val, bc);
 19255               break;
 19256             case 98:
 19257               push(local[bc.index]);
 19258               break;
 19259             case 99:
 19260               local[bc.index] = pop();
 19261               break;
 19262             case 100:
 19263               push(globalScope);
 19264               ti().object = LazyInitializer.create(globalScope.object);
 19265               break;
 19266             case 101:
 19267               push(scope[bc.index]);
 19268               break;
 19269             case 102:
 19270               mn = popMultiname();
 19271               obj = pop();
 19272               push(getProperty(obj, mn));
 19273               break;
 19274             case 103:
 19275               notImplemented(bc);
 19276               break;
 19277             case 105:
 19278               notImplemented(bc);
 19279               break;
 19280             case 106:
 19281               popMultiname();
 19282               pop();
 19283               push(Type.Boolean);
 19284               break;
 19285             case 107:
 19286               notImplemented(bc);
 19287               break;
 19288             case 108:
 19289               push(accessSlot(pop()));
 19290               break;
 19291             case 109:
 19292               val = pop();
 19293               obj = pop();
 19294               accessSlot(obj);
 19295               break;
 19296             case 110:
 19297               notImplemented(bc);
 19298               break;
 19299             case 111:
 19300               notImplemented(bc);
 19301               break;
 19302             case 112:
 19303               pop();
 19304               push(Type.String);
 19305               break;
 19306             case 113:
 19307               pop();
 19308               push(Type.String);
 19309               break;
 19310             case 114:
 19311               pop();
 19312               push(Type.String);
 19313               break;
 19314             case 131:
 19315             case 115:
 19316               pop();
 19317               push(Type.Int);
 19318               break;
 19319             case 136:
 19320             case 116:
 19321               pop();
 19322               push(Type.Uint);
 19323               break;
 19324             case 132:
 19325             case 117:
 19326               pop();
 19327               push(Type.Number);
 19328               break;
 19329             case 129:
 19330             case 118:
 19331               pop();
 19332               push(Type.Boolean);
 19333               break;
 19334             case 119:
 19335               notImplemented(bc);
 19336               break;
 19337             case 120:
 19338               break;
 19339             case 121:
 19340               pop();
 19341               push(Type.Number);
 19342               break;
 19343             case 122:
 19344               notImplemented(bc);
 19345               break;
 19346             case 123:
 19347               notImplemented(bc);
 19348               break;
 19349             case 128:
 19350               type = pop();
 19351               var coerceType = Type.fromName(multinames[bc.index], this.domain).instanceType();
 19352               if (coerceType.isSubtypeOf(type)) {
 19353                 ti().noCoercionNeeded = true;
 19355               push(coerceType);
 19356               break;
 19357             case 130:
 19358               break;
 19359             case 133:
 19360               pop();
 19361               push(Type.String);
 19362               break;
 19363             case 134:
 19364               notImplemented(bc);
 19365               break;
 19366             case 135:
 19367               type = pop();
 19368               pop();
 19369               if (type instanceof TraitsType) {
 19370                 push(type.instanceType());
 19371               } else {
 19372                 push(Type.Any);
 19374               break;
 19375             case 137:
 19376               notImplemented(bc);
 19377               break;
 19378             case 144:
 19379             case 145:
 19380             case 147:
 19381               pop();
 19382               push(Type.Number);
 19383               break;
 19384             case 146:
 19385             case 148:
 19386               local[bc.index] = Type.Number;
 19387               break;
 19388             case 149:
 19389               pop();
 19390               push(Type.String);
 19391               break;
 19392             case 150:
 19393               pop();
 19394               push(Type.Boolean);
 19395               break;
 19396             case 160:
 19397               r = pop();
 19398               l = pop();
 19399               if (l.isNumeric() && r.isNumeric()) {
 19400                 push(Type.Number);
 19401               } else if (l === Type.String || r === Type.String) {
 19402                 push(Type.String);
 19403               } else {
 19404                 push(Type.Any);
 19406               break;
 19407             case 161:
 19408             case 162:
 19409             case 163:
 19410             case 164:
 19411               pop();
 19412               pop();
 19413               push(Type.Number);
 19414               break;
 19415             case 168:
 19416             case 169:
 19417             case 170:
 19418             case 165:
 19419             case 166:
 19420             case 167:
 19421               pop();
 19422               pop();
 19423               push(Type.Int);
 19424               break;
 19425             case 151:
 19426               pop();
 19427               push(Type.Int);
 19428               break;
 19429             case 171:
 19430             case 172:
 19431             case 173:
 19432             case 174:
 19433             case 175:
 19434             case 176:
 19435             case 177:
 19436             case 180:
 19437               pop();
 19438               pop();
 19439               push(Type.Boolean);
 19440               break;
 19441             case 178:
 19442               pop();
 19443               push(Type.Boolean);
 19444               break;
 19445             case 179:
 19446               pop();
 19447               pop();
 19448               push(Type.Boolean);
 19449               break;
 19450             case 194:
 19451             case 195:
 19452               local[bc.index] = Type.Int;
 19453               break;
 19454             case 193:
 19455             case 192:
 19456             case 196:
 19457               pop();
 19458               push(Type.Int);
 19459               break;
 19460             case 197:
 19461             case 198:
 19462             case 199:
 19463               pop();
 19464               pop();
 19465               push(Type.Int);
 19466               break;
 19467             case 208:
 19468             case 209:
 19469             case 210:
 19470             case 211:
 19471               push(local[op - OP_getlocal0]);
 19472               break;
 19473             case 212:
 19474             case 213:
 19475             case 214:
 19476             case 215:
 19477               local[op - OP_setlocal0] = pop();
 19478               break;
 19479             case 239:
 19480               break;
 19481             case 240:
 19482               break;
 19483             case 241:
 19484               break;
 19485             case 242:
 19486               break;
 19487             case 243:
 19488               break;
 19489             default:
 19490               console.info('Not Implemented: ' + bc);
 19492             if (writer) {
 19493               if (bc.ti) {
 19494                 writer.debugLn('> TI: ' + bc.ti);
 19498           if (writer) {
 19499             writer.leave('}');
 19500             writer.writeLn('verifiedBlock: ' + block.bid + ', range: [' + block.position + ', ' + block.end.position + '], exitState: ' + state.toString());
 19502         };
 19503         return verification;
 19504       }();
 19505     function verifier() {
 19506       this.writer = new IndentingWriter();
 19508     verifier.prototype.verifyMethod = function (methodInfo, scope) {
 19509       try {
 19510         var domain = methodInfo.abc.applicationDomain;
 19511         var scopeObjects = scope.getScopeObjects();
 19512         if (!scopeObjects[scopeObjects.length - 1]) {
 19513           if (methodInfo.holder instanceof InstanceInfo) {
 19514             scopeObjects[scopeObjects.length - 1] = methodInfo.holder.classInfo;
 19515           } else if (methodInfo.holder instanceof ClassInfo) {
 19516             scopeObjects[scopeObjects.length - 1] = methodInfo.holder;
 19519         var savedScope = scopeObjects.map(function (object) {
 19520             if (object instanceof MethodInfo) {
 19521               return Type.from(new ActivationInfo(object));
 19523             return Type.from(object, domain);
 19524           });
 19525         new Verification(methodInfo, methodInfo.abc.applicationDomain, savedScope).verify();
 19526         methodInfo.verified = true;
 19527         Counter.count('Verifier: Methods');
 19528       } catch (e) {
 19529         if (e instanceof VerifierError) {
 19530           return;
 19532         throw e;
 19534     };
 19535     return verifier;
 19536   }();
 19537 (function (exports) {
 19538   var debug = false;
 19539   var IRDefinition = {
 19540       Control: {
 19541         Region: {
 19542           predecessors: {
 19543             array: true,
 19544             expand: 'control'
 19545           },
 19546           Start: {
 19547             _constructorText: 'this.control = this;',
 19548             scope: {
 19549               dynamic: true
 19550             },
 19551             domain: {
 19552               dynamic: true
 19555         },
 19556         End: {
 19557           control: {
 19558             assert: 'isControlOrNull'
 19559           },
 19560           Stop: {
 19561             store: {
 19562               assert: 'isStore'
 19563             },
 19564             argument: {
 19565               assert: ''
 19567           },
 19568           If: {
 19569             predicate: {
 19570               assert: ''
 19572           },
 19573           Switch: {
 19574             determinant: {
 19575               assert: ''
 19577           },
 19578           Jump: {}
 19580       },
 19581       Value: {
 19582         StoreDependent: {
 19583           control: {
 19584             assert: 'isControlOrNull',
 19585             nullable: true
 19586           },
 19587           store: {
 19588             assert: 'isStoreOrNull',
 19589             nullable: true
 19590           },
 19591           loads: {
 19592             dynamic: true,
 19593             nullable: true,
 19594             array: true
 19595           },
 19596           Call: {
 19597             callee: {
 19598               assert: ''
 19599             },
 19600             object: {
 19601               assert: 'isValueOrNull',
 19602               nullable: true
 19603             },
 19604             args: {
 19605               assert: 'isArray',
 19606               array: true
 19607             },
 19608             flags: {
 19609               internal: true,
 19610               assert: 'isNumber'
 19612           },
 19613           CallProperty: {
 19614             object: {
 19615               assert: ''
 19616             },
 19617             name: {
 19618               assert: ''
 19619             },
 19620             args: {
 19621               assert: 'isArray',
 19622               array: true
 19623             },
 19624             flags: {
 19625               internal: true,
 19626               assert: 'isNumber'
 19627             },
 19628             ASCallProperty: {
 19629               isLex: {
 19630                 assert: '',
 19631                 internal: true
 19633             },
 19634             ASCallSuper: {
 19635               scope: {
 19636                 assert: ''
 19639           },
 19640           New: {
 19641             callee: {
 19642               assert: ''
 19643             },
 19644             args: {
 19645               assert: '',
 19646               array: true
 19647             },
 19648             ASNew: {}
 19649           },
 19650           GetProperty: {
 19651             object: {
 19652               assert: ''
 19653             },
 19654             name: {
 19655               assert: ''
 19656             },
 19657             ASGetProperty: {
 19658               flags: {
 19659                 internal: true,
 19660                 assert: 'isNumber'
 19662             },
 19663             ASGetDescendants: {},
 19664             ASHasProperty: {},
 19665             ASGetSlot: {},
 19666             ASGetSuper: {
 19667               scope: {
 19668                 assert: ''
 19671           },
 19672           SetProperty: {
 19673             object: {
 19674               assert: ''
 19675             },
 19676             name: {
 19677               assert: ''
 19678             },
 19679             value: {
 19680               assert: ''
 19681             },
 19682             ASSetProperty: {
 19683               flags: {
 19684                 internal: true
 19686             },
 19687             ASSetSlot: {},
 19688             ASSetSuper: {
 19689               scope: {
 19690                 assert: ''
 19693           },
 19694           DeleteProperty: {
 19695             object: {
 19696               assert: ''
 19697             },
 19698             name: {
 19699               assert: ''
 19700             },
 19701             ASDeleteProperty: {}
 19702           },
 19703           ASFindProperty: {
 19704             scope: {
 19705               assert: ''
 19706             },
 19707             name: {
 19708               assert: ''
 19709             },
 19710             domain: {
 19711               assert: ''
 19712             },
 19713             strict: {
 19714               internal: true
 19717         },
 19718         Store: {},
 19719         Phi: {
 19720           control: {
 19721             assert: 'isControl',
 19722             nullable: true
 19723           },
 19724           args: {
 19725             array: true,
 19726             expand: 'value'
 19728         },
 19729         Variable: {
 19730           name: {
 19731             internal: true
 19733         },
 19734         Copy: {
 19735           argument: {}
 19736         },
 19737         Move: {
 19738           to: {},
 19739           from: {}
 19740         },
 19741         Projection: {
 19742           argument: {},
 19743           type: {
 19744             internal: true
 19745           },
 19746           selector: {
 19747             internal: true,
 19748             optional: true
 19750         },
 19751         Latch: {
 19752           control: {
 19753             assert: 'isControlOrNull',
 19754             nullable: true
 19755           },
 19756           condition: {},
 19757           left: {},
 19758           right: {}
 19759         },
 19760         Binary: {
 19761           operator: {
 19762             internal: true
 19763           },
 19764           left: {},
 19765           right: {}
 19766         },
 19767         Unary: {
 19768           operator: {
 19769             internal: true
 19770           },
 19771           argument: {}
 19772         },
 19773         Constant: {
 19774           value: {
 19775             internal: true
 19777         },
 19778         GlobalProperty: {
 19779           name: {
 19780             internal: true
 19782         },
 19783         This: {
 19784           control: {
 19785             assert: 'isControl'
 19787         },
 19788         Throw: {
 19789           control: {
 19790             assert: 'isControl'
 19791           },
 19792           argument: {}
 19793         },
 19794         Arguments: {
 19795           control: {
 19796             assert: 'isControl'
 19798         },
 19799         Parameter: {
 19800           control: {
 19801             assert: 'isControl'
 19802           },
 19803           index: {
 19804             internal: true
 19805           },
 19806           name: {
 19807             internal: true
 19809         },
 19810         NewArray: {
 19811           control: {
 19812             assert: 'isControl'
 19813           },
 19814           elements: {
 19815             array: true
 19817         },
 19818         NewObject: {
 19819           control: {
 19820             assert: 'isControl'
 19821           },
 19822           properties: {
 19823             array: true
 19825         },
 19826         KeyValuePair: {
 19827           key: {},
 19828           value: {}
 19829         },
 19830         ASScope: {
 19831           parent: {},
 19832           object: {},
 19833           isWith: {
 19834             internal: true
 19836         },
 19837         ASGlobal: {
 19838           control: {
 19839             assert: 'isControlOrNull',
 19840             nullable: true
 19841           },
 19842           scope: {
 19843             assert: 'isScope'
 19845         },
 19846         ASNewActivation: {
 19847           methodInfo: {
 19848             internal: true
 19850         },
 19851         ASMultiname: {
 19852           namespaces: {},
 19853           name: {},
 19854           flags: {
 19855             internal: true
 19859     };
 19860   function IRGenerator(root) {
 19861     var str = '';
 19862     function out(s) {
 19863       str += s + '\n';
 19865     var writer = new IndentingWriter(false, out);
 19866     function makeProperties(node) {
 19867       var result = [];
 19868       for (var k in node) {
 19869         if (isProperty(k)) {
 19870           node[k].name = k;
 19871           result.push(node[k]);
 19874       return result;
 19876     function isProperty(v) {
 19877       if (v[0] === '_') {
 19878         return false;
 19880       return v[0].toLowerCase() === v[0];
 19882     function generate(node, path) {
 19883       path = path.concat([
 19884         node
 19885       ]);
 19886       writer.enter('var ' + node._name + ' = (function () {');
 19887       var constructorName = node._name[0].toLowerCase() + node._name.slice(1) + 'Node';
 19888       if (constructorName.substring(0, 2) === 'aS') {
 19889         constructorName = 'as' + constructorName.substring(2);
 19891       var prototypeName = constructorName + '.prototype';
 19892       var properties = path.reduce(function (a, v) {
 19893           return a.concat(makeProperties(v));
 19894         }, []);
 19895       var parameters = properties.filter(function (property) {
 19896           return !property.dynamic;
 19897         });
 19898       var optionalParameters = parameters.filter(function (property) {
 19899           return property.optional;
 19900         });
 19901       var parameterString = parameters.map(function (property) {
 19902           if (property.expand) {
 19903             return property.expand;
 19905           return property.name;
 19906         }).join(', ');
 19907       writer.enter('function ' + constructorName + '(' + parameterString + ') {');
 19908       if (true) {
 19909         properties.forEach(function (property) {
 19910           if (property.assert === '') {
 19911             writer.writeLn('release || assert (!(' + property.name + ' == undefined), "' + property.name + '");');
 19912           } else if (property.assert) {
 19913             writer.writeLn('release || assert (' + property.assert + '(' + property.name + '), "' + property.name + '");');
 19915         });
 19916         writer.writeLn('release || assert (arguments.length >= ' + (parameters.length - optionalParameters.length) + ', "' + node._name + ' not enough args.");');
 19918       if (node._constructorText) {
 19919         writer.writeLn(node._constructorText);
 19921       properties.forEach(function (property) {
 19922         if (property.expand) {
 19923           writer.writeLn('this.' + property.name + ' = ' + property.expand + ' ? [' + property.expand + '] : [];');
 19924         } else if (property.dynamic) {
 19925           writer.writeLn('this.' + property.name + ' = undefined;');
 19926         } else {
 19927           writer.writeLn('this.' + property.name + ' = ' + property.name + ';');
 19929       });
 19930       writer.writeLn('this.id = nextID[nextID.length - 1] += 1;');
 19931       writer.leave('}');
 19932       if (path.length > 1) {
 19933         writer.writeLn(prototypeName + ' = ' + 'extend(' + path[path.length - 2]._name + ', "' + node._name + '");');
 19935       writer.writeLn(prototypeName + '.nodeName = "' + node._name + '";');
 19936       writer.enter(prototypeName + '.visitInputs = function (visitor) {');
 19937       properties.forEach(function (property) {
 19938         if (property.internal) {
 19939           return;
 19941         var str = '';
 19942         if (property.nullable) {
 19943           str += 'this.' + property.name + ' && ';
 19945         if (property.array) {
 19946           str += 'visitArrayInputs(this.' + property.name + ', visitor);';
 19947         } else {
 19948           str += 'visitor(this.' + property.name + ');';
 19950         writer.writeLn(str);
 19951       });
 19952       writer.leave('};');
 19953       writer.writeLn('return ' + constructorName + ';');
 19954       writer.leave('})();');
 19955       writer.writeLn('');
 19956       for (var name in node) {
 19957         if (name[0] === '_' || isProperty(name)) {
 19958           continue;
 19960         var child = node[name];
 19961         child._name = name;
 19962         generate(child, path);
 19965     IRDefinition._name = 'Node';
 19966     generate(IRDefinition, []);
 19967     return str;
 19969   var nextID = [];
 19970   var Node = function () {
 19971       function nodeNode() {
 19972         true;
 19973         this.id = nextID[nextID.length - 1] += 1;
 19975       nodeNode.prototype.nodeName = 'Node';
 19976       nodeNode.prototype.visitInputs = function (visitor) {
 19977       };
 19978       return nodeNode;
 19979     }();
 19980   var Control = function () {
 19981       function controlNode() {
 19982         true;
 19983         this.id = nextID[nextID.length - 1] += 1;
 19985       controlNode.prototype = extend(Node, 'Control');
 19986       controlNode.prototype.nodeName = 'Control';
 19987       controlNode.prototype.visitInputs = function (visitor) {
 19988       };
 19989       return controlNode;
 19990     }();
 19991   var Region = function () {
 19992       function regionNode(control) {
 19993         true;
 19994         this.predecessors = control ? [
 19995           control
 19996         ] : [];
 19997         this.id = nextID[nextID.length - 1] += 1;
 19999       regionNode.prototype = extend(Control, 'Region');
 20000       regionNode.prototype.nodeName = 'Region';
 20001       regionNode.prototype.visitInputs = function (visitor) {
 20002         visitArrayInputs(this.predecessors, visitor);
 20003       };
 20004       return regionNode;
 20005     }();
 20006   var Start = function () {
 20007       function startNode(control) {
 20008         true;
 20009         this.control = this;
 20010         this.predecessors = control ? [
 20011           control
 20012         ] : [];
 20013         this.scope = undefined;
 20014         this.domain = undefined;
 20015         this.id = nextID[nextID.length - 1] += 1;
 20017       startNode.prototype = extend(Region, 'Start');
 20018       startNode.prototype.nodeName = 'Start';
 20019       startNode.prototype.visitInputs = function (visitor) {
 20020         visitArrayInputs(this.predecessors, visitor);
 20021         visitor(this.scope);
 20022         visitor(this.domain);
 20023       };
 20024       return startNode;
 20025     }();
 20026   var End = function () {
 20027       function endNode(control) {
 20028         true;
 20029         true;
 20030         this.control = control;
 20031         this.id = nextID[nextID.length - 1] += 1;
 20033       endNode.prototype = extend(Control, 'End');
 20034       endNode.prototype.nodeName = 'End';
 20035       endNode.prototype.visitInputs = function (visitor) {
 20036         visitor(this.control);
 20037       };
 20038       return endNode;
 20039     }();
 20040   var Stop = function () {
 20041       function stopNode(control, store, argument) {
 20042         true;
 20043         true;
 20044         true;
 20045         true;
 20046         this.control = control;
 20047         this.store = store;
 20048         this.argument = argument;
 20049         this.id = nextID[nextID.length - 1] += 1;
 20051       stopNode.prototype = extend(End, 'Stop');
 20052       stopNode.prototype.nodeName = 'Stop';
 20053       stopNode.prototype.visitInputs = function (visitor) {
 20054         visitor(this.control);
 20055         visitor(this.store);
 20056         visitor(this.argument);
 20057       };
 20058       return stopNode;
 20059     }();
 20060   var If = function () {
 20061       function ifNode(control, predicate) {
 20062         true;
 20063         true;
 20064         true;
 20065         this.control = control;
 20066         this.predicate = predicate;
 20067         this.id = nextID[nextID.length - 1] += 1;
 20069       ifNode.prototype = extend(End, 'If');
 20070       ifNode.prototype.nodeName = 'If';
 20071       ifNode.prototype.visitInputs = function (visitor) {
 20072         visitor(this.control);
 20073         visitor(this.predicate);
 20074       };
 20075       return ifNode;
 20076     }();
 20077   var Switch = function () {
 20078       function switchNode(control, determinant) {
 20079         true;
 20080         true;
 20081         true;
 20082         this.control = control;
 20083         this.determinant = determinant;
 20084         this.id = nextID[nextID.length - 1] += 1;
 20086       switchNode.prototype = extend(End, 'Switch');
 20087       switchNode.prototype.nodeName = 'Switch';
 20088       switchNode.prototype.visitInputs = function (visitor) {
 20089         visitor(this.control);
 20090         visitor(this.determinant);
 20091       };
 20092       return switchNode;
 20093     }();
 20094   var Jump = function () {
 20095       function jumpNode(control) {
 20096         true;
 20097         true;
 20098         this.control = control;
 20099         this.id = nextID[nextID.length - 1] += 1;
 20101       jumpNode.prototype = extend(End, 'Jump');
 20102       jumpNode.prototype.nodeName = 'Jump';
 20103       jumpNode.prototype.visitInputs = function (visitor) {
 20104         visitor(this.control);
 20105       };
 20106       return jumpNode;
 20107     }();
 20108   var Value = function () {
 20109       function valueNode() {
 20110         true;
 20111         this.id = nextID[nextID.length - 1] += 1;
 20113       valueNode.prototype = extend(Node, 'Value');
 20114       valueNode.prototype.nodeName = 'Value';
 20115       valueNode.prototype.visitInputs = function (visitor) {
 20116       };
 20117       return valueNode;
 20118     }();
 20119   var StoreDependent = function () {
 20120       function storeDependentNode(control, store) {
 20121         true;
 20122         true;
 20123         true;
 20124         this.control = control;
 20125         this.store = store;
 20126         this.loads = undefined;
 20127         this.id = nextID[nextID.length - 1] += 1;
 20129       storeDependentNode.prototype = extend(Value, 'StoreDependent');
 20130       storeDependentNode.prototype.nodeName = 'StoreDependent';
 20131       storeDependentNode.prototype.visitInputs = function (visitor) {
 20132         this.control && visitor(this.control);
 20133         this.store && visitor(this.store);
 20134         this.loads && visitArrayInputs(this.loads, visitor);
 20135       };
 20136       return storeDependentNode;
 20137     }();
 20138   var Call = function () {
 20139       function callNode(control, store, callee, object, args, flags) {
 20140         true;
 20141         true;
 20142         true;
 20143         true;
 20144         true;
 20145         true;
 20146         true;
 20147         this.control = control;
 20148         this.store = store;
 20149         this.loads = undefined;
 20150         this.callee = callee;
 20151         this.object = object;
 20152         this.args = args;
 20153         this.flags = flags;
 20154         this.id = nextID[nextID.length - 1] += 1;
 20156       callNode.prototype = extend(StoreDependent, 'Call');
 20157       callNode.prototype.nodeName = 'Call';
 20158       callNode.prototype.visitInputs = function (visitor) {
 20159         this.control && visitor(this.control);
 20160         this.store && visitor(this.store);
 20161         this.loads && visitArrayInputs(this.loads, visitor);
 20162         visitor(this.callee);
 20163         this.object && visitor(this.object);
 20164         visitArrayInputs(this.args, visitor);
 20165       };
 20166       return callNode;
 20167     }();
 20168   var CallProperty = function () {
 20169       function callPropertyNode(control, store, object, name, args, flags) {
 20170         true;
 20171         true;
 20172         true;
 20173         true;
 20174         true;
 20175         true;
 20176         true;
 20177         this.control = control;
 20178         this.store = store;
 20179         this.loads = undefined;
 20180         this.object = object;
 20181         this.name = name;
 20182         this.args = args;
 20183         this.flags = flags;
 20184         this.id = nextID[nextID.length - 1] += 1;
 20186       callPropertyNode.prototype = extend(StoreDependent, 'CallProperty');
 20187       callPropertyNode.prototype.nodeName = 'CallProperty';
 20188       callPropertyNode.prototype.visitInputs = function (visitor) {
 20189         this.control && visitor(this.control);
 20190         this.store && visitor(this.store);
 20191         this.loads && visitArrayInputs(this.loads, visitor);
 20192         visitor(this.object);
 20193         visitor(this.name);
 20194         visitArrayInputs(this.args, visitor);
 20195       };
 20196       return callPropertyNode;
 20197     }();
 20198   var ASCallProperty = function () {
 20199       function asCallPropertyNode(control, store, object, name, args, flags, isLex) {
 20200         true;
 20201         true;
 20202         true;
 20203         true;
 20204         true;
 20205         true;
 20206         true;
 20207         true;
 20208         this.control = control;
 20209         this.store = store;
 20210         this.loads = undefined;
 20211         this.object = object;
 20212         this.name = name;
 20213         this.args = args;
 20214         this.flags = flags;
 20215         this.isLex = isLex;
 20216         this.id = nextID[nextID.length - 1] += 1;
 20218       asCallPropertyNode.prototype = extend(CallProperty, 'ASCallProperty');
 20219       asCallPropertyNode.prototype.nodeName = 'ASCallProperty';
 20220       asCallPropertyNode.prototype.visitInputs = function (visitor) {
 20221         this.control && visitor(this.control);
 20222         this.store && visitor(this.store);
 20223         this.loads && visitArrayInputs(this.loads, visitor);
 20224         visitor(this.object);
 20225         visitor(this.name);
 20226         visitArrayInputs(this.args, visitor);
 20227       };
 20228       return asCallPropertyNode;
 20229     }();
 20230   var ASCallSuper = function () {
 20231       function asCallSuperNode(control, store, object, name, args, flags, scope) {
 20232         true;
 20233         true;
 20234         true;
 20235         true;
 20236         true;
 20237         true;
 20238         true;
 20239         true;
 20240         this.control = control;
 20241         this.store = store;
 20242         this.loads = undefined;
 20243         this.object = object;
 20244         this.name = name;
 20245         this.args = args;
 20246         this.flags = flags;
 20247         this.scope = scope;
 20248         this.id = nextID[nextID.length - 1] += 1;
 20250       asCallSuperNode.prototype = extend(CallProperty, 'ASCallSuper');
 20251       asCallSuperNode.prototype.nodeName = 'ASCallSuper';
 20252       asCallSuperNode.prototype.visitInputs = function (visitor) {
 20253         this.control && visitor(this.control);
 20254         this.store && visitor(this.store);
 20255         this.loads && visitArrayInputs(this.loads, visitor);
 20256         visitor(this.object);
 20257         visitor(this.name);
 20258         visitArrayInputs(this.args, visitor);
 20259         visitor(this.scope);
 20260       };
 20261       return asCallSuperNode;
 20262     }();
 20263   var New = function () {
 20264       function newNode(control, store, callee, args) {
 20265         true;
 20266         true;
 20267         true;
 20268         true;
 20269         true;
 20270         this.control = control;
 20271         this.store = store;
 20272         this.loads = undefined;
 20273         this.callee = callee;
 20274         this.args = args;
 20275         this.id = nextID[nextID.length - 1] += 1;
 20277       newNode.prototype = extend(StoreDependent, 'New');
 20278       newNode.prototype.nodeName = 'New';
 20279       newNode.prototype.visitInputs = function (visitor) {
 20280         this.control && visitor(this.control);
 20281         this.store && visitor(this.store);
 20282         this.loads && visitArrayInputs(this.loads, visitor);
 20283         visitor(this.callee);
 20284         visitArrayInputs(this.args, visitor);
 20285       };
 20286       return newNode;
 20287     }();
 20288   var ASNew = function () {
 20289       function asNewNode(control, store, callee, args) {
 20290         true;
 20291         true;
 20292         true;
 20293         true;
 20294         true;
 20295         this.control = control;
 20296         this.store = store;
 20297         this.loads = undefined;
 20298         this.callee = callee;
 20299         this.args = args;
 20300         this.id = nextID[nextID.length - 1] += 1;
 20302       asNewNode.prototype = extend(New, 'ASNew');
 20303       asNewNode.prototype.nodeName = 'ASNew';
 20304       asNewNode.prototype.visitInputs = function (visitor) {
 20305         this.control && visitor(this.control);
 20306         this.store && visitor(this.store);
 20307         this.loads && visitArrayInputs(this.loads, visitor);
 20308         visitor(this.callee);
 20309         visitArrayInputs(this.args, visitor);
 20310       };
 20311       return asNewNode;
 20312     }();
 20313   var GetProperty = function () {
 20314       function getPropertyNode(control, store, object, name) {
 20315         true;
 20316         true;
 20317         true;
 20318         true;
 20319         true;
 20320         this.control = control;
 20321         this.store = store;
 20322         this.loads = undefined;
 20323         this.object = object;
 20324         this.name = name;
 20325         this.id = nextID[nextID.length - 1] += 1;
 20327       getPropertyNode.prototype = extend(StoreDependent, 'GetProperty');
 20328       getPropertyNode.prototype.nodeName = 'GetProperty';
 20329       getPropertyNode.prototype.visitInputs = function (visitor) {
 20330         this.control && visitor(this.control);
 20331         this.store && visitor(this.store);
 20332         this.loads && visitArrayInputs(this.loads, visitor);
 20333         visitor(this.object);
 20334         visitor(this.name);
 20335       };
 20336       return getPropertyNode;
 20337     }();
 20338   var ASGetProperty = function () {
 20339       function asGetPropertyNode(control, store, object, name, flags) {
 20340         true;
 20341         true;
 20342         true;
 20343         true;
 20344         true;
 20345         true;
 20346         this.control = control;
 20347         this.store = store;
 20348         this.loads = undefined;
 20349         this.object = object;
 20350         this.name = name;
 20351         this.flags = flags;
 20352         this.id = nextID[nextID.length - 1] += 1;
 20354       asGetPropertyNode.prototype = extend(GetProperty, 'ASGetProperty');
 20355       asGetPropertyNode.prototype.nodeName = 'ASGetProperty';
 20356       asGetPropertyNode.prototype.visitInputs = function (visitor) {
 20357         this.control && visitor(this.control);
 20358         this.store && visitor(this.store);
 20359         this.loads && visitArrayInputs(this.loads, visitor);
 20360         visitor(this.object);
 20361         visitor(this.name);
 20362       };
 20363       return asGetPropertyNode;
 20364     }();
 20365   var ASGetDescendants = function () {
 20366       function asGetDescendantsNode(control, store, object, name) {
 20367         true;
 20368         true;
 20369         true;
 20370         true;
 20371         true;
 20372         this.control = control;
 20373         this.store = store;
 20374         this.loads = undefined;
 20375         this.object = object;
 20376         this.name = name;
 20377         this.id = nextID[nextID.length - 1] += 1;
 20379       asGetDescendantsNode.prototype = extend(GetProperty, 'ASGetDescendants');
 20380       asGetDescendantsNode.prototype.nodeName = 'ASGetDescendants';
 20381       asGetDescendantsNode.prototype.visitInputs = function (visitor) {
 20382         this.control && visitor(this.control);
 20383         this.store && visitor(this.store);
 20384         this.loads && visitArrayInputs(this.loads, visitor);
 20385         visitor(this.object);
 20386         visitor(this.name);
 20387       };
 20388       return asGetDescendantsNode;
 20389     }();
 20390   var ASHasProperty = function () {
 20391       function asHasPropertyNode(control, store, object, name) {
 20392         true;
 20393         true;
 20394         true;
 20395         true;
 20396         true;
 20397         this.control = control;
 20398         this.store = store;
 20399         this.loads = undefined;
 20400         this.object = object;
 20401         this.name = name;
 20402         this.id = nextID[nextID.length - 1] += 1;
 20404       asHasPropertyNode.prototype = extend(GetProperty, 'ASHasProperty');
 20405       asHasPropertyNode.prototype.nodeName = 'ASHasProperty';
 20406       asHasPropertyNode.prototype.visitInputs = function (visitor) {
 20407         this.control && visitor(this.control);
 20408         this.store && visitor(this.store);
 20409         this.loads && visitArrayInputs(this.loads, visitor);
 20410         visitor(this.object);
 20411         visitor(this.name);
 20412       };
 20413       return asHasPropertyNode;
 20414     }();
 20415   var ASGetSlot = function () {
 20416       function asGetSlotNode(control, store, object, name) {
 20417         true;
 20418         true;
 20419         true;
 20420         true;
 20421         true;
 20422         this.control = control;
 20423         this.store = store;
 20424         this.loads = undefined;
 20425         this.object = object;
 20426         this.name = name;
 20427         this.id = nextID[nextID.length - 1] += 1;
 20429       asGetSlotNode.prototype = extend(GetProperty, 'ASGetSlot');
 20430       asGetSlotNode.prototype.nodeName = 'ASGetSlot';
 20431       asGetSlotNode.prototype.visitInputs = function (visitor) {
 20432         this.control && visitor(this.control);
 20433         this.store && visitor(this.store);
 20434         this.loads && visitArrayInputs(this.loads, visitor);
 20435         visitor(this.object);
 20436         visitor(this.name);
 20437       };
 20438       return asGetSlotNode;
 20439     }();
 20440   var ASGetSuper = function () {
 20441       function asGetSuperNode(control, store, object, name, scope) {
 20442         true;
 20443         true;
 20444         true;
 20445         true;
 20446         true;
 20447         true;
 20448         this.control = control;
 20449         this.store = store;
 20450         this.loads = undefined;
 20451         this.object = object;
 20452         this.name = name;
 20453         this.scope = scope;
 20454         this.id = nextID[nextID.length - 1] += 1;
 20456       asGetSuperNode.prototype = extend(GetProperty, 'ASGetSuper');
 20457       asGetSuperNode.prototype.nodeName = 'ASGetSuper';
 20458       asGetSuperNode.prototype.visitInputs = function (visitor) {
 20459         this.control && visitor(this.control);
 20460         this.store && visitor(this.store);
 20461         this.loads && visitArrayInputs(this.loads, visitor);
 20462         visitor(this.object);
 20463         visitor(this.name);
 20464         visitor(this.scope);
 20465       };
 20466       return asGetSuperNode;
 20467     }();
 20468   var SetProperty = function () {
 20469       function setPropertyNode(control, store, object, name, value) {
 20470         true;
 20471         true;
 20472         true;
 20473         true;
 20474         true;
 20475         true;
 20476         this.control = control;
 20477         this.store = store;
 20478         this.loads = undefined;
 20479         this.object = object;
 20480         this.name = name;
 20481         this.value = value;
 20482         this.id = nextID[nextID.length - 1] += 1;
 20484       setPropertyNode.prototype = extend(StoreDependent, 'SetProperty');
 20485       setPropertyNode.prototype.nodeName = 'SetProperty';
 20486       setPropertyNode.prototype.visitInputs = function (visitor) {
 20487         this.control && visitor(this.control);
 20488         this.store && visitor(this.store);
 20489         this.loads && visitArrayInputs(this.loads, visitor);
 20490         visitor(this.object);
 20491         visitor(this.name);
 20492         visitor(this.value);
 20493       };
 20494       return setPropertyNode;
 20495     }();
 20496   var ASSetProperty = function () {
 20497       function asSetPropertyNode(control, store, object, name, value, flags) {
 20498         true;
 20499         true;
 20500         true;
 20501         true;
 20502         true;
 20503         true;
 20504         this.control = control;
 20505         this.store = store;
 20506         this.loads = undefined;
 20507         this.object = object;
 20508         this.name = name;
 20509         this.value = value;
 20510         this.flags = flags;
 20511         this.id = nextID[nextID.length - 1] += 1;
 20513       asSetPropertyNode.prototype = extend(SetProperty, 'ASSetProperty');
 20514       asSetPropertyNode.prototype.nodeName = 'ASSetProperty';
 20515       asSetPropertyNode.prototype.visitInputs = function (visitor) {
 20516         this.control && visitor(this.control);
 20517         this.store && visitor(this.store);
 20518         this.loads && visitArrayInputs(this.loads, visitor);
 20519         visitor(this.object);
 20520         visitor(this.name);
 20521         visitor(this.value);
 20522       };
 20523       return asSetPropertyNode;
 20524     }();
 20525   var ASSetSlot = function () {
 20526       function asSetSlotNode(control, store, object, name, value) {
 20527         true;
 20528         true;
 20529         true;
 20530         true;
 20531         true;
 20532         true;
 20533         this.control = control;
 20534         this.store = store;
 20535         this.loads = undefined;
 20536         this.object = object;
 20537         this.name = name;
 20538         this.value = value;
 20539         this.id = nextID[nextID.length - 1] += 1;
 20541       asSetSlotNode.prototype = extend(SetProperty, 'ASSetSlot');
 20542       asSetSlotNode.prototype.nodeName = 'ASSetSlot';
 20543       asSetSlotNode.prototype.visitInputs = function (visitor) {
 20544         this.control && visitor(this.control);
 20545         this.store && visitor(this.store);
 20546         this.loads && visitArrayInputs(this.loads, visitor);
 20547         visitor(this.object);
 20548         visitor(this.name);
 20549         visitor(this.value);
 20550       };
 20551       return asSetSlotNode;
 20552     }();
 20553   var ASSetSuper = function () {
 20554       function asSetSuperNode(control, store, object, name, value, scope) {
 20555         true;
 20556         true;
 20557         true;
 20558         true;
 20559         true;
 20560         true;
 20561         true;
 20562         this.control = control;
 20563         this.store = store;
 20564         this.loads = undefined;
 20565         this.object = object;
 20566         this.name = name;
 20567         this.value = value;
 20568         this.scope = scope;
 20569         this.id = nextID[nextID.length - 1] += 1;
 20571       asSetSuperNode.prototype = extend(SetProperty, 'ASSetSuper');
 20572       asSetSuperNode.prototype.nodeName = 'ASSetSuper';
 20573       asSetSuperNode.prototype.visitInputs = function (visitor) {
 20574         this.control && visitor(this.control);
 20575         this.store && visitor(this.store);
 20576         this.loads && visitArrayInputs(this.loads, visitor);
 20577         visitor(this.object);
 20578         visitor(this.name);
 20579         visitor(this.value);
 20580         visitor(this.scope);
 20581       };
 20582       return asSetSuperNode;
 20583     }();
 20584   var DeleteProperty = function () {
 20585       function deletePropertyNode(control, store, object, name) {
 20586         true;
 20587         true;
 20588         true;
 20589         true;
 20590         true;
 20591         this.control = control;
 20592         this.store = store;
 20593         this.loads = undefined;
 20594         this.object = object;
 20595         this.name = name;
 20596         this.id = nextID[nextID.length - 1] += 1;
 20598       deletePropertyNode.prototype = extend(StoreDependent, 'DeleteProperty');
 20599       deletePropertyNode.prototype.nodeName = 'DeleteProperty';
 20600       deletePropertyNode.prototype.visitInputs = function (visitor) {
 20601         this.control && visitor(this.control);
 20602         this.store && visitor(this.store);
 20603         this.loads && visitArrayInputs(this.loads, visitor);
 20604         visitor(this.object);
 20605         visitor(this.name);
 20606       };
 20607       return deletePropertyNode;
 20608     }();
 20609   var ASDeleteProperty = function () {
 20610       function asDeletePropertyNode(control, store, object, name) {
 20611         true;
 20612         true;
 20613         true;
 20614         true;
 20615         true;
 20616         this.control = control;
 20617         this.store = store;
 20618         this.loads = undefined;
 20619         this.object = object;
 20620         this.name = name;
 20621         this.id = nextID[nextID.length - 1] += 1;
 20623       asDeletePropertyNode.prototype = extend(DeleteProperty, 'ASDeleteProperty');
 20624       asDeletePropertyNode.prototype.nodeName = 'ASDeleteProperty';
 20625       asDeletePropertyNode.prototype.visitInputs = function (visitor) {
 20626         this.control && visitor(this.control);
 20627         this.store && visitor(this.store);
 20628         this.loads && visitArrayInputs(this.loads, visitor);
 20629         visitor(this.object);
 20630         visitor(this.name);
 20631       };
 20632       return asDeletePropertyNode;
 20633     }();
 20634   var ASFindProperty = function () {
 20635       function asFindPropertyNode(control, store, scope, name, domain, strict) {
 20636         true;
 20637         true;
 20638         true;
 20639         true;
 20640         true;
 20641         true;
 20642         this.control = control;
 20643         this.store = store;
 20644         this.loads = undefined;
 20645         this.scope = scope;
 20646         this.name = name;
 20647         this.domain = domain;
 20648         this.strict = strict;
 20649         this.id = nextID[nextID.length - 1] += 1;
 20651       asFindPropertyNode.prototype = extend(StoreDependent, 'ASFindProperty');
 20652       asFindPropertyNode.prototype.nodeName = 'ASFindProperty';
 20653       asFindPropertyNode.prototype.visitInputs = function (visitor) {
 20654         this.control && visitor(this.control);
 20655         this.store && visitor(this.store);
 20656         this.loads && visitArrayInputs(this.loads, visitor);
 20657         visitor(this.scope);
 20658         visitor(this.name);
 20659         visitor(this.domain);
 20660       };
 20661       return asFindPropertyNode;
 20662     }();
 20663   var Store = function () {
 20664       function storeNode() {
 20665         true;
 20666         this.id = nextID[nextID.length - 1] += 1;
 20668       storeNode.prototype = extend(Value, 'Store');
 20669       storeNode.prototype.nodeName = 'Store';
 20670       storeNode.prototype.visitInputs = function (visitor) {
 20671       };
 20672       return storeNode;
 20673     }();
 20674   var Phi = function () {
 20675       function phiNode(control, value) {
 20676         true;
 20677         true;
 20678         this.control = control;
 20679         this.args = value ? [
 20680           value
 20681         ] : [];
 20682         this.id = nextID[nextID.length - 1] += 1;
 20684       phiNode.prototype = extend(Value, 'Phi');
 20685       phiNode.prototype.nodeName = 'Phi';
 20686       phiNode.prototype.visitInputs = function (visitor) {
 20687         this.control && visitor(this.control);
 20688         visitArrayInputs(this.args, visitor);
 20689       };
 20690       return phiNode;
 20691     }();
 20692   var Variable = function () {
 20693       function variableNode(name) {
 20694         true;
 20695         this.name = name;
 20696         this.id = nextID[nextID.length - 1] += 1;
 20698       variableNode.prototype = extend(Value, 'Variable');
 20699       variableNode.prototype.nodeName = 'Variable';
 20700       variableNode.prototype.visitInputs = function (visitor) {
 20701       };
 20702       return variableNode;
 20703     }();
 20704   var Copy = function () {
 20705       function copyNode(argument) {
 20706         true;
 20707         this.argument = argument;
 20708         this.id = nextID[nextID.length - 1] += 1;
 20710       copyNode.prototype = extend(Value, 'Copy');
 20711       copyNode.prototype.nodeName = 'Copy';
 20712       copyNode.prototype.visitInputs = function (visitor) {
 20713         visitor(this.argument);
 20714       };
 20715       return copyNode;
 20716     }();
 20717   var Move = function () {
 20718       function moveNode(to, from) {
 20719         true;
 20720         this.to = to;
 20721         this.from = from;
 20722         this.id = nextID[nextID.length - 1] += 1;
 20724       moveNode.prototype = extend(Value, 'Move');
 20725       moveNode.prototype.nodeName = 'Move';
 20726       moveNode.prototype.visitInputs = function (visitor) {
 20727         visitor(this.to);
 20728         visitor(this.from);
 20729       };
 20730       return moveNode;
 20731     }();
 20732   var Projection = function () {
 20733       function projectionNode(argument, type, selector) {
 20734         true;
 20735         this.argument = argument;
 20736         this.type = type;
 20737         this.selector = selector;
 20738         this.id = nextID[nextID.length - 1] += 1;
 20740       projectionNode.prototype = extend(Value, 'Projection');
 20741       projectionNode.prototype.nodeName = 'Projection';
 20742       projectionNode.prototype.visitInputs = function (visitor) {
 20743         visitor(this.argument);
 20744       };
 20745       return projectionNode;
 20746     }();
 20747   var Latch = function () {
 20748       function latchNode(control, condition, left, right) {
 20749         true;
 20750         true;
 20751         this.control = control;
 20752         this.condition = condition;
 20753         this.left = left;
 20754         this.right = right;
 20755         this.id = nextID[nextID.length - 1] += 1;
 20757       latchNode.prototype = extend(Value, 'Latch');
 20758       latchNode.prototype.nodeName = 'Latch';
 20759       latchNode.prototype.visitInputs = function (visitor) {
 20760         this.control && visitor(this.control);
 20761         visitor(this.condition);
 20762         visitor(this.left);
 20763         visitor(this.right);
 20764       };
 20765       return latchNode;
 20766     }();
 20767   var Binary = function () {
 20768       function binaryNode(operator, left, right) {
 20769         true;
 20770         this.operator = operator;
 20771         this.left = left;
 20772         this.right = right;
 20773         this.id = nextID[nextID.length - 1] += 1;
 20775       binaryNode.prototype = extend(Value, 'Binary');
 20776       binaryNode.prototype.nodeName = 'Binary';
 20777       binaryNode.prototype.visitInputs = function (visitor) {
 20778         visitor(this.left);
 20779         visitor(this.right);
 20780       };
 20781       return binaryNode;
 20782     }();
 20783   var Unary = function () {
 20784       function unaryNode(operator, argument) {
 20785         true;
 20786         this.operator = operator;
 20787         this.argument = argument;
 20788         this.id = nextID[nextID.length - 1] += 1;
 20790       unaryNode.prototype = extend(Value, 'Unary');
 20791       unaryNode.prototype.nodeName = 'Unary';
 20792       unaryNode.prototype.visitInputs = function (visitor) {
 20793         visitor(this.argument);
 20794       };
 20795       return unaryNode;
 20796     }();
 20797   var Constant = function () {
 20798       function constantNode(value) {
 20799         true;
 20800         this.value = value;
 20801         this.id = nextID[nextID.length - 1] += 1;
 20803       constantNode.prototype = extend(Value, 'Constant');
 20804       constantNode.prototype.nodeName = 'Constant';
 20805       constantNode.prototype.visitInputs = function (visitor) {
 20806       };
 20807       return constantNode;
 20808     }();
 20809   var GlobalProperty = function () {
 20810       function globalPropertyNode(name) {
 20811         true;
 20812         this.name = name;
 20813         this.id = nextID[nextID.length - 1] += 1;
 20815       globalPropertyNode.prototype = extend(Value, 'GlobalProperty');
 20816       globalPropertyNode.prototype.nodeName = 'GlobalProperty';
 20817       globalPropertyNode.prototype.visitInputs = function (visitor) {
 20818       };
 20819       return globalPropertyNode;
 20820     }();
 20821   var This = function () {
 20822       function thisNode(control) {
 20823         true;
 20824         true;
 20825         this.control = control;
 20826         this.id = nextID[nextID.length - 1] += 1;
 20828       thisNode.prototype = extend(Value, 'This');
 20829       thisNode.prototype.nodeName = 'This';
 20830       thisNode.prototype.visitInputs = function (visitor) {
 20831         visitor(this.control);
 20832       };
 20833       return thisNode;
 20834     }();
 20835   var Throw = function () {
 20836       function throwNode(control, argument) {
 20837         true;
 20838         true;
 20839         this.control = control;
 20840         this.argument = argument;
 20841         this.id = nextID[nextID.length - 1] += 1;
 20843       throwNode.prototype = extend(Value, 'Throw');
 20844       throwNode.prototype.nodeName = 'Throw';
 20845       throwNode.prototype.visitInputs = function (visitor) {
 20846         visitor(this.control);
 20847         visitor(this.argument);
 20848       };
 20849       return throwNode;
 20850     }();
 20851   var Arguments = function () {
 20852       function argumentsNode(control) {
 20853         true;
 20854         true;
 20855         this.control = control;
 20856         this.id = nextID[nextID.length - 1] += 1;
 20858       argumentsNode.prototype = extend(Value, 'Arguments');
 20859       argumentsNode.prototype.nodeName = 'Arguments';
 20860       argumentsNode.prototype.visitInputs = function (visitor) {
 20861         visitor(this.control);
 20862       };
 20863       return argumentsNode;
 20864     }();
 20865   var Parameter = function () {
 20866       function parameterNode(control, index, name) {
 20867         true;
 20868         true;
 20869         this.control = control;
 20870         this.index = index;
 20871         this.name = name;
 20872         this.id = nextID[nextID.length - 1] += 1;
 20874       parameterNode.prototype = extend(Value, 'Parameter');
 20875       parameterNode.prototype.nodeName = 'Parameter';
 20876       parameterNode.prototype.visitInputs = function (visitor) {
 20877         visitor(this.control);
 20878       };
 20879       return parameterNode;
 20880     }();
 20881   var NewArray = function () {
 20882       function newArrayNode(control, elements) {
 20883         true;
 20884         true;
 20885         this.control = control;
 20886         this.elements = elements;
 20887         this.id = nextID[nextID.length - 1] += 1;
 20889       newArrayNode.prototype = extend(Value, 'NewArray');
 20890       newArrayNode.prototype.nodeName = 'NewArray';
 20891       newArrayNode.prototype.visitInputs = function (visitor) {
 20892         visitor(this.control);
 20893         visitArrayInputs(this.elements, visitor);
 20894       };
 20895       return newArrayNode;
 20896     }();
 20897   var NewObject = function () {
 20898       function newObjectNode(control, properties) {
 20899         true;
 20900         true;
 20901         this.control = control;
 20902         this.properties = properties;
 20903         this.id = nextID[nextID.length - 1] += 1;
 20905       newObjectNode.prototype = extend(Value, 'NewObject');
 20906       newObjectNode.prototype.nodeName = 'NewObject';
 20907       newObjectNode.prototype.visitInputs = function (visitor) {
 20908         visitor(this.control);
 20909         visitArrayInputs(this.properties, visitor);
 20910       };
 20911       return newObjectNode;
 20912     }();
 20913   var KeyValuePair = function () {
 20914       function keyValuePairNode(key, value) {
 20915         true;
 20916         this.key = key;
 20917         this.value = value;
 20918         this.id = nextID[nextID.length - 1] += 1;
 20920       keyValuePairNode.prototype = extend(Value, 'KeyValuePair');
 20921       keyValuePairNode.prototype.nodeName = 'KeyValuePair';
 20922       keyValuePairNode.prototype.visitInputs = function (visitor) {
 20923         visitor(this.key);
 20924         visitor(this.value);
 20925       };
 20926       return keyValuePairNode;
 20927     }();
 20928   var ASScope = function () {
 20929       function asScopeNode(parent, object, isWith) {
 20930         true;
 20931         this.parent = parent;
 20932         this.object = object;
 20933         this.isWith = isWith;
 20934         this.id = nextID[nextID.length - 1] += 1;
 20936       asScopeNode.prototype = extend(Value, 'ASScope');
 20937       asScopeNode.prototype.nodeName = 'ASScope';
 20938       asScopeNode.prototype.visitInputs = function (visitor) {
 20939         visitor(this.parent);
 20940         visitor(this.object);
 20941       };
 20942       return asScopeNode;
 20943     }();
 20944   var ASGlobal = function () {
 20945       function asGlobalNode(control, scope) {
 20946         true;
 20947         true;
 20948         true;
 20949         this.control = control;
 20950         this.scope = scope;
 20951         this.id = nextID[nextID.length - 1] += 1;
 20953       asGlobalNode.prototype = extend(Value, 'ASGlobal');
 20954       asGlobalNode.prototype.nodeName = 'ASGlobal';
 20955       asGlobalNode.prototype.visitInputs = function (visitor) {
 20956         this.control && visitor(this.control);
 20957         visitor(this.scope);
 20958       };
 20959       return asGlobalNode;
 20960     }();
 20961   var ASNewActivation = function () {
 20962       function asNewActivationNode(methodInfo) {
 20963         true;
 20964         this.methodInfo = methodInfo;
 20965         this.id = nextID[nextID.length - 1] += 1;
 20967       asNewActivationNode.prototype = extend(Value, 'ASNewActivation');
 20968       asNewActivationNode.prototype.nodeName = 'ASNewActivation';
 20969       asNewActivationNode.prototype.visitInputs = function (visitor) {
 20970       };
 20971       return asNewActivationNode;
 20972     }();
 20973   var ASMultiname = function () {
 20974       function asMultinameNode(namespaces, name, flags) {
 20975         true;
 20976         this.namespaces = namespaces;
 20977         this.name = name;
 20978         this.flags = flags;
 20979         this.id = nextID[nextID.length - 1] += 1;
 20981       asMultinameNode.prototype = extend(Value, 'ASMultiname');
 20982       asMultinameNode.prototype.nodeName = 'ASMultiname';
 20983       asMultinameNode.prototype.visitInputs = function (visitor) {
 20984         visitor(this.namespaces);
 20985         visitor(this.name);
 20986       };
 20987       return asMultinameNode;
 20988     }();
 20989   function node() {
 20990     this.id = nextID[nextID.length - 1] += 1;
 20992   Node.startNumbering = function () {
 20993     nextID.push(0);
 20994   };
 20995   Node.stopNumbering = function () {
 20996     nextID.pop();
 20997   };
 20998   Node.prototype.toString = function (brief) {
 20999     if (brief) {
 21000       return nameOf(this);
 21002     var inputs = [];
 21003     this.visitInputs(function (input) {
 21004       inputs.push(nameOf(input));
 21005     });
 21006     var str = nameOf(this) + ' = ' + this.nodeName.toUpperCase();
 21007     if (this.toStringDetails) {
 21008       str += ' ' + this.toStringDetails();
 21010     if (inputs.length) {
 21011       str += ' ' + inputs.join(', ');
 21013     return str;
 21014   };
 21015   Node.prototype.visitInputsNoConstants = function visitInputs(visitor) {
 21016     this.visitInputs(function (node) {
 21017       if (isConstant(node)) {
 21018         return;
 21020       visitor(node);
 21021     });
 21022   };
 21023   Node.prototype.replaceInput = function (oldInput, newInput) {
 21024     var count = 0;
 21025     for (var k in this) {
 21026       var v = this[k];
 21027       if (v instanceof Node) {
 21028         if (v === oldInput) {
 21029           this[k] = newInput;
 21030           count++;
 21033       if (v instanceof Array) {
 21034         count += v.replace(oldInput, newInput);
 21037     return count;
 21038   };
 21039   Projection.Type = {
 21040     CASE: 'case',
 21041     TRUE: 'true',
 21042     FALSE: 'false',
 21043     STORE: 'store',
 21044     SCOPE: 'scope'
 21045   };
 21046   Projection.prototype.project = function () {
 21047     return this.argument;
 21048   };
 21049   Phi.prototype.seal = function seal() {
 21050     this.sealed = true;
 21051   };
 21052   Phi.prototype.pushValue = function pushValue(x) {
 21053     true;
 21054     true;
 21055     this.args.push(x);
 21056   };
 21057   KeyValuePair.prototype.mustFloat = true;
 21058   ASMultiname.prototype.mustFloat = true;
 21059   ASMultiname.prototype.isAttribute = function () {
 21060     return this.flags & 1;
 21061   };
 21062   var Flags = {
 21063       INDEXED: 1,
 21064       RESOLVED: 2,
 21065       PRISTINE: 4,
 21066       IS_METHOD: 8
 21067     };
 21068   var Operator = function () {
 21069       var map = {};
 21070       function operator(name, evaluate, binary) {
 21071         this.name = name;
 21072         this.binary = binary;
 21073         this.evaluate = evaluate;
 21074         map[name] = this;
 21076       operator.ADD = new operator('+', function (l, r) {
 21077         return l + r;
 21078       }, true);
 21079       operator.SUB = new operator('-', function (l, r) {
 21080         return l - r;
 21081       }, true);
 21082       operator.MUL = new operator('*', function (l, r) {
 21083         return l * r;
 21084       }, true);
 21085       operator.DIV = new operator('/', function (l, r) {
 21086         return l / r;
 21087       }, true);
 21088       operator.MOD = new operator('%', function (l, r) {
 21089         return l % r;
 21090       }, true);
 21091       operator.AND = new operator('&', function (l, r) {
 21092         return l & r;
 21093       }, true);
 21094       operator.OR = new operator('|', function (l, r) {
 21095         return l | r;
 21096       }, true);
 21097       operator.XOR = new operator('^', function (l, r) {
 21098         return l ^ r;
 21099       }, true);
 21100       operator.LSH = new operator('<<', function (l, r) {
 21101         return l << r;
 21102       }, true);
 21103       operator.RSH = new operator('>>', function (l, r) {
 21104         return l >> r;
 21105       }, true);
 21106       operator.URSH = new operator('>>>', function (l, r) {
 21107         return l >>> r;
 21108       }, true);
 21109       operator.SEQ = new operator('===', function (l, r) {
 21110         return l === r;
 21111       }, true);
 21112       operator.SNE = new operator('!==', function (l, r) {
 21113         return l !== r;
 21114       }, true);
 21115       operator.EQ = new operator('==', function (l, r) {
 21116         return l == r;
 21117       }, true);
 21118       operator.NE = new operator('!=', function (l, r) {
 21119         return l != r;
 21120       }, true);
 21121       operator.LE = new operator('<=', function (l, r) {
 21122         return l <= r;
 21123       }, true);
 21124       operator.GT = new operator('>', function (l, r) {
 21125         return l > r;
 21126       }, true);
 21127       operator.LT = new operator('<', function (l, r) {
 21128         return l < r;
 21129       }, true);
 21130       operator.GE = new operator('>=', function (l, r) {
 21131         return l >= r;
 21132       }, true);
 21133       operator.BITWISE_NOT = new operator('~', function (a) {
 21134         return ~a;
 21135       }, false);
 21136       operator.PLUS = new operator('+', function (a) {
 21137         return +a;
 21138       }, false);
 21139       operator.NEG = new operator('-', function (a) {
 21140         return -a;
 21141       }, false);
 21142       operator.TYPE_OF = new operator('typeof', function (a) {
 21143         return typeof a;
 21144       }, false);
 21145       operator.TRUE = new operator('!!', function (a) {
 21146         return !(!a);
 21147       }, false);
 21148       operator.FALSE = new operator('!', function (a) {
 21149         return !a;
 21150       }, false);
 21151       operator.AS_ADD = new operator('+', function (l, r) {
 21152         if (typeof l === 'string' || typeof r === 'string') {
 21153           return String(l) + String(r);
 21155         return l + r;
 21156       }, true);
 21157       function linkOpposites(a, b) {
 21158         a.not = b;
 21159         b.not = a;
 21161       linkOpposites(operator.SEQ, operator.SNE);
 21162       linkOpposites(operator.EQ, operator.NE);
 21163       linkOpposites(operator.TRUE, operator.FALSE);
 21164       operator.fromName = function fromName(name) {
 21165         return map[name];
 21166       };
 21167       operator.prototype.isBinary = function isBinary() {
 21168         return this.binary;
 21169       };
 21170       operator.prototype.toString = function toString() {
 21171         return this.name;
 21172       };
 21173       return operator;
 21174     }();
 21175   function extend(c, name) {
 21176     true;
 21177     return Object.create(c.prototype, {
 21178       nodeName: {
 21179         value: name
 21181     });
 21183   function nameOf(o) {
 21184     var useColors = false;
 21185     var result;
 21186     if (o instanceof Constant) {
 21187       if (o.value instanceof Multiname) {
 21188         return o.value.name;
 21190       return o.value;
 21191     } else if (o instanceof Variable) {
 21192       return o.name;
 21193     } else if (o instanceof Phi) {
 21194       return result = '|' + o.id + '|', useColors ? PURPLE + result + ENDC : result;
 21195     } else if (o instanceof Control) {
 21196       return result = '{' + o.id + '}', useColors ? RED + result + ENDC : result;
 21197     } else if (o instanceof Projection) {
 21198       if (o.type === Projection.Type.STORE) {
 21199         return result = '[' + o.id + '->' + o.argument.id + ']', useColors ? YELLOW + result + ENDC : result;
 21201       return result = '(' + o.id + ')', useColors ? GREEN + result + ENDC : result;
 21202     } else if (o instanceof Value) {
 21203       return result = '(' + o.id + ')', useColors ? GREEN + result + ENDC : result;
 21204     } else if (o instanceof Node) {
 21205       return o.id;
 21207     unexpected(o + ' ' + typeof o);
 21209   function toID(node) {
 21210     return node.id;
 21212   function visitArrayInputs(array, visitor) {
 21213     for (var i = 0; i < array.length; i++) {
 21214       visitor(array[i]);
 21217   function visitNothing() {
 21219   function isNotPhi(phi) {
 21220     return !isPhi(phi);
 21222   function isPhi(phi) {
 21223     return phi instanceof Phi;
 21225   function isScope(scope) {
 21226     return isPhi(scope) || scope instanceof ASScope || isProjection(scope, Projection.Type.SCOPE);
 21228   function isMultinameConstant(node) {
 21229     return node instanceof Constant && node.value instanceof Multiname;
 21231   function isMultiname(name) {
 21232     return isMultinameConstant(name) || name instanceof ASMultiname;
 21234   function isStore(store) {
 21235     return isPhi(store) || store instanceof Store || isProjection(store, Projection.Type.STORE);
 21237   function isConstant(constant) {
 21238     return constant instanceof Constant;
 21240   function isBoolean(boolean) {
 21241     return boolean === true || boolean === false;
 21243   function isInteger(integer) {
 21244     return integer | 0 === integer;
 21246   function isArray(array) {
 21247     return array instanceof Array;
 21249   function isControlOrNull(control) {
 21250     return isControl(control) || control === null;
 21252   function isStoreOrNull(store) {
 21253     return isStore(store) || store === null;
 21255   function isControl(control) {
 21256     return control instanceof Control;
 21258   function isValueOrNull(value) {
 21259     return isValue(value) || value === null;
 21261   function isValue(value) {
 21262     return value instanceof Value;
 21264   function isProjection(node, type) {
 21265     return node instanceof Projection && (!type || node.type === type);
 21267   var Null = new Constant(null);
 21268   var Undefined = new Constant(undefined);
 21269   Undefined.toString = function () {
 21270     return '_';
 21271   };
 21272   var Block = function () {
 21273       function block(id, start, end) {
 21274         if (start) {
 21275           true;
 21277         this.region = start;
 21278         this.id = id;
 21279         this.successors = [];
 21280         this.predecessors = [];
 21281         this.nodes = [
 21282           start,
 21283           end
 21284         ];
 21286       block.prototype.pushSuccessorAt = function pushSuccessor(successor, index, pushPredecessor) {
 21287         true;
 21288         true;
 21289         this.successors[index] = successor;
 21290         if (pushPredecessor) {
 21291           successor.pushPredecessor(this);
 21293       };
 21294       block.prototype.pushSuccessor = function pushSuccessor(successor, pushPredecessor) {
 21295         true;
 21296         this.successors.push(successor);
 21297         if (pushPredecessor) {
 21298           successor.pushPredecessor(this);
 21300       };
 21301       block.prototype.pushPredecessor = function pushPredecessor(predecessor) {
 21302         true;
 21303         this.predecessors.push(predecessor);
 21304       };
 21305       block.prototype.visitNodes = function (fn) {
 21306         var nodes = this.nodes;
 21307         for (var i = 0, j = nodes.length; i < j; i++) {
 21308           fn(nodes[i]);
 21310       };
 21311       block.prototype.visitSuccessors = function (fn) {
 21312         var successors = this.successors;
 21313         for (var i = 0, j = successors.length; i < j; i++) {
 21314           fn(successors[i]);
 21316       };
 21317       block.prototype.visitPredecessors = function (fn) {
 21318         var predecessors = this.predecessors;
 21319         for (var i = 0, j = predecessors.length; i < j; i++) {
 21320           fn(predecessors[i]);
 21322       };
 21323       block.prototype.append = function (node) {
 21324         true;
 21325         true;
 21326         true;
 21327         true;
 21328         if (node.mustFloat) {
 21329           return;
 21331         this.nodes.splice(this.nodes.length - 1, 0, node);
 21332       };
 21333       block.prototype.toString = function () {
 21334         return 'B' + this.id + (this.name ? ' (' + this.name + ')' : '');
 21335       };
 21336       block.prototype.trace = function (writer) {
 21337         writer.writeLn(this);
 21338       };
 21339       return block;
 21340     }();
 21341   var DFG = function () {
 21342       function constructor(exit) {
 21343         this.exit = exit;
 21345       constructor.prototype.buildCFG = function () {
 21346         return CFG.fromDFG(this);
 21347       };
 21348       function preOrderDepthFirstSearch(root, visitChildren, pre) {
 21349         var visited = [];
 21350         var worklist = [
 21351             root
 21352           ];
 21353         var push = worklist.push.bind(worklist);
 21354         var node;
 21355         while (node = worklist.pop()) {
 21356           if (visited[node.id] === 1) {
 21357             continue;
 21359           visited[node.id] = 1;
 21360           pre(node);
 21361           worklist.push(node);
 21362           visitChildren(node, push);
 21365       function postOrderDepthFirstSearch(root, visitChildren, post) {
 21366         var ONE_TIME = 1, MANY_TIMES = 2;
 21367         var visited = [];
 21368         var worklist = [
 21369             root
 21370           ];
 21371         function visitChild(child) {
 21372           if (!visited[child.id]) {
 21373             worklist.push(child);
 21376         var node;
 21377         while (node = worklist.top()) {
 21378           if (visited[node.id]) {
 21379             if (visited[node.id] === ONE_TIME) {
 21380               visited[node.id] = MANY_TIMES;
 21381               post(node);
 21383             worklist.pop();
 21384             continue;
 21386           visited[node.id] = ONE_TIME;
 21387           visitChildren(node, visitChild);
 21390       constructor.prototype.forEachInPreOrderDepthFirstSearch = function forEachInPreOrderDepthFirstSearch(visitor) {
 21391         var visited = new Array(1024);
 21392         var worklist = [
 21393             this.exit
 21394           ];
 21395         function push(node) {
 21396           if (isConstant(node)) {
 21397             return;
 21399           true;
 21400           worklist.push(node);
 21402         var node;
 21403         while (node = worklist.pop()) {
 21404           if (visited[node.id]) {
 21405             continue;
 21407           visited[node.id] = 1;
 21408           visitor && visitor(node);
 21409           worklist.push(node);
 21410           node.visitInputs(push);
 21412       };
 21413       constructor.prototype.forEach = function forEach(visitor, postOrder) {
 21414         var search = postOrder ? postOrderDepthFirstSearch : preOrderDepthFirstSearch;
 21415         search(this.exit, function (node, v) {
 21416           node.visitInputsNoConstants(v);
 21417         }, visitor);
 21418       };
 21419       constructor.prototype.traceMetrics = function (writer) {
 21420         var counter = new metrics.Counter(true);
 21421         preOrderDepthFirstSearch(this.exit, function (node, visitor) {
 21422           node.visitInputsNoConstants(visitor);
 21423         }, function (node) {
 21424           counter.count(node.nodeName);
 21425         });
 21426         counter.trace(writer);
 21427       };
 21428       constructor.prototype.trace = function (writer) {
 21429         var nodes = [];
 21430         var visited = {};
 21431         function colorOf(node) {
 21432           if (node instanceof Control) {
 21433             return 'yellow';
 21434           } else if (node instanceof Phi) {
 21435             return 'purple';
 21436           } else if (node instanceof Value) {
 21437             return 'green';
 21439           return 'white';
 21441         var blocks = [];
 21442         function followProjection(node) {
 21443           return node instanceof Projection ? node.project() : node;
 21445         function next(node) {
 21446           node = followProjection(node);
 21447           if (!visited[node.id]) {
 21448             visited[node.id] = true;
 21449             if (node.block) {
 21450               blocks.push(node.block);
 21452             nodes.push(node);
 21453             node.visitInputsNoConstants(next);
 21456         next(this.exit);
 21457         writer.writeLn('');
 21458         writer.enter('digraph DFG {');
 21459         writer.writeLn('graph [bgcolor = gray10];');
 21460         writer.writeLn('edge [color = white];');
 21461         writer.writeLn('node [shape = box, fontname = Consolas, fontsize = 11, color = white, fontcolor = white];');
 21462         writer.writeLn('rankdir = BT;');
 21463         function writeNode(node) {
 21464           writer.writeLn('N' + node.id + ' [label = "' + node.toString() + '", color = "' + colorOf(node) + '"];');
 21466         function defineNode(node) {
 21467           writer.writeLn('N' + node.id + ';');
 21469         blocks.forEach(function (block) {
 21470           writer.enter('subgraph cluster' + block.nodes[0].id + ' { bgcolor = gray20;');
 21471           block.visitNodes(function (node) {
 21472             defineNode(followProjection(node));
 21473           });
 21474           writer.leave('}');
 21475         });
 21476         nodes.forEach(writeNode);
 21477         nodes.forEach(function (node) {
 21478           node.visitInputsNoConstants(function (input) {
 21479             input = followProjection(input);
 21480             writer.writeLn('N' + node.id + ' -> ' + 'N' + input.id + ' [color=' + colorOf(input) + '];');
 21481           });
 21482         });
 21483         writer.leave('}');
 21484         writer.writeLn('');
 21485       };
 21486       return constructor;
 21487     }();
 21488   var CFG = function () {
 21489       function constructor() {
 21490         this.nextBlockID = 0;
 21491         this.blocks = [];
 21492         this.exit;
 21493         this.root;
 21495       constructor.fromDFG = function fromDFG(dfg) {
 21496         var cfg = new CFG();
 21497         true;
 21498         cfg.dfg = dfg;
 21499         var visited = [];
 21500         function buildEnd(end) {
 21501           if (end instanceof Projection) {
 21502             end = end.project();
 21504           true;
 21505           if (visited[end.id]) {
 21506             return;
 21508           visited[end.id] = true;
 21509           var start = end.control;
 21510           if (!(start instanceof Region)) {
 21511             start = end.control = new Region(start);
 21513           var block = start.block = cfg.buildBlock(start, end);
 21514           if (start instanceof Start) {
 21515             cfg.root = block;
 21517           for (var i = 0; i < start.predecessors.length; i++) {
 21518             var c = start.predecessors[i];
 21519             var d;
 21520             var trueProjection = false;
 21521             if (c instanceof Projection) {
 21522               d = c.project();
 21523               trueProjection = c.type === Projection.Type.TRUE;
 21524             } else {
 21525               d = c;
 21527             if (d instanceof Region) {
 21528               d = new Jump(c);
 21529               d = new Projection(d, Projection.Type.TRUE);
 21530               start.predecessors[i] = d;
 21531               d = d.project();
 21532               trueProjection = true;
 21534             buildEnd(d);
 21535             var controlBlock = d.control.block;
 21536             if (d instanceof Switch) {
 21537               true;
 21538               controlBlock.pushSuccessorAt(block, c.selector.value, true);
 21539             } else if (trueProjection && controlBlock.successors.length > 0) {
 21540               controlBlock.pushSuccessor(block, true);
 21541               controlBlock.hasFlippedSuccessors = true;
 21542             } else {
 21543               controlBlock.pushSuccessor(block, true);
 21547         buildEnd(dfg.exit);
 21548         cfg.splitCriticalEdges();
 21549         cfg.exit = dfg.exit.control.block;
 21550         cfg.computeDominators(true);
 21551         return cfg;
 21552       };
 21553       constructor.prototype.buildRootAndExit = function buildRootAndExit() {
 21554         true;
 21555         if (this.blocks[0].predecessors.length > 0) {
 21556           this.root = new Block(this.nextBlockID++);
 21557           this.blocks.push(this.root);
 21558           this.root.pushSuccessor(this.blocks[0], true);
 21559         } else {
 21560           this.root = this.blocks[0];
 21562         var exitBlocks = [];
 21563         for (var i = 0; i < this.blocks.length; i++) {
 21564           var block = this.blocks[i];
 21565           if (block.successors.length === 0) {
 21566             exitBlocks.push(block);
 21569         if (exitBlocks.length === 0) {
 21570           unexpected('Must have an exit block.');
 21571         } else if (exitBlocks.length === 1 && exitBlocks[0] !== this.root) {
 21572           this.exit = exitBlocks[0];
 21573         } else {
 21574           this.exit = new Block(this.nextBlockID++);
 21575           this.blocks.push(this.exit);
 21576           for (var i = 0; i < exitBlocks.length; i++) {
 21577             exitBlocks[i].pushSuccessor(this.exit, true);
 21580         true;
 21581         true;
 21582       };
 21583       constructor.prototype.fromString = function (list, rootName) {
 21584         var cfg = this;
 21585         var names = cfg.blockNames || (cfg.blockNames = {});
 21586         var blocks = cfg.blocks;
 21587         var sets = list.replace(/\ /g, '').split(',');
 21588         sets.forEach(function (set) {
 21589           var edgeList = set.split('->');
 21590           var last = null;
 21591           for (var i = 0; i < edgeList.length; i++) {
 21592             var next = edgeList[i];
 21593             if (last) {
 21594               buildEdge(last, next);
 21595             } else {
 21596               buildBlock(next);
 21598             last = next;
 21600         });
 21601         function buildBlock(name) {
 21602           var block = names[name];
 21603           if (block) {
 21604             return block;
 21606           names[name] = block = new Block(cfg.nextBlockID++);
 21607           block.name = name;
 21608           blocks.push(block);
 21609           return block;
 21611         function buildEdge(from, to) {
 21612           buildBlock(from).pushSuccessor(buildBlock(to), true);
 21614         true;
 21615         this.root = names[rootName];
 21616       };
 21617       constructor.prototype.buildBlock = function (start, end) {
 21618         var block = new Block(this.nextBlockID++, start, end);
 21619         this.blocks.push(block);
 21620         return block;
 21621       };
 21622       constructor.prototype.createBlockSet = function () {
 21623         if (!this.setConstructor) {
 21624           this.setConstructor = BitSetFunctor(this.blocks.length);
 21626         return new this.setConstructor();
 21627       };
 21628       constructor.prototype.computeReversePostOrder = function computeReversePostOrder() {
 21629         if (this.order) {
 21630           return this.order;
 21632         var order = this.order = [];
 21633         this.depthFirstSearch(null, order.push.bind(order));
 21634         order.reverse();
 21635         for (var i = 0; i < order.length; i++) {
 21636           order[i].rpo = i;
 21638         return order;
 21639       };
 21640       constructor.prototype.depthFirstSearch = function depthFirstSearch(preFn, postFn) {
 21641         var visited = this.createBlockSet();
 21642         function visit(node) {
 21643           visited.set(node.id);
 21644           if (preFn)
 21645             preFn(node);
 21646           var successors = node.successors;
 21647           for (var i = 0, j = successors.length; i < j; i++) {
 21648             var s = successors[i];
 21649             if (!visited.get(s.id)) {
 21650               visit(s);
 21653           if (postFn)
 21654             postFn(node);
 21656         visit(this.root);
 21657       };
 21658       constructor.prototype.computeDominators = function (apply) {
 21659         true;
 21660         var dom = new Int32Array(this.blocks.length);
 21661         for (var i = 0; i < dom.length; i++) {
 21662           dom[i] = -1;
 21664         var map = this.createBlockSet();
 21665         function computeCommonDominator(a, b) {
 21666           map.clearAll();
 21667           while (a >= 0) {
 21668             map.set(a);
 21669             a = dom[a];
 21671           while (b >= 0 && !map.get(b)) {
 21672             b = dom[b];
 21674           return b;
 21676         function computeDominator(blockID, parentID) {
 21677           if (dom[blockID] < 0) {
 21678             dom[blockID] = parentID;
 21679           } else {
 21680             dom[blockID] = computeCommonDominator(dom[blockID], parentID);
 21683         this.depthFirstSearch(function visit(block) {
 21684           var s = block.successors;
 21685           for (var i = 0, j = s.length; i < j; i++) {
 21686             computeDominator(s[i].id, block.id);
 21688         });
 21689         if (apply) {
 21690           for (var i = 0, j = this.blocks.length; i < j; i++) {
 21691             this.blocks[i].dominator = this.blocks[dom[i]];
 21693           function computeDominatorDepth(block) {
 21694             var dominatorDepth;
 21695             if (block.dominatorDepth !== undefined) {
 21696               return block.dominatorDepth;
 21697             } else if (!block.dominator) {
 21698               dominatorDepth = 0;
 21699             } else {
 21700               dominatorDepth = computeDominatorDepth(block.dominator) + 1;
 21702             return block.dominatorDepth = dominatorDepth;
 21704           for (var i = 0, j = this.blocks.length; i < j; i++) {
 21705             computeDominatorDepth(this.blocks[i]);
 21708         return dom;
 21709       };
 21710       constructor.prototype.computeLoops = function computeLoops() {
 21711         var active = this.createBlockSet();
 21712         var visited = this.createBlockSet();
 21713         var nextLoop = 0;
 21714         function makeLoopHeader(block) {
 21715           if (!block.isLoopHeader) {
 21716             block.isLoopHeader = true;
 21717             block.loops = 1 << nextLoop;
 21718             nextLoop += 1;
 21721         function visit(block) {
 21722           if (visited.get(block.id)) {
 21723             if (active.get(block.id)) {
 21724               makeLoopHeader(block);
 21726             return block.loops;
 21728           visited.set(block.id);
 21729           active.set(block.id);
 21730           var loops = 0;
 21731           for (var i = 0, j = block.successors.length; i < j; i++) {
 21732             loops |= visit(block.successors[i]);
 21734           if (block.isLoopHeader) {
 21735             loops &= ~block.loops;
 21737           block.loops = loops;
 21738           active.clear(block.id);
 21739           return loops;
 21741         var loop = visit(this.root);
 21742       };
 21743       function followProjection(node) {
 21744         return node instanceof Projection ? node.project() : node;
 21746       var Uses = function () {
 21747           function constructor() {
 21748             this.entries = [];
 21750           constructor.prototype.addUse = function addUse(def, use) {
 21751             var entry = this.entries[def.id];
 21752             if (!entry) {
 21753               entry = this.entries[def.id] = {
 21754                 def: def,
 21755                 uses: []
 21756               };
 21758             entry.uses.pushUnique(use);
 21759           };
 21760           constructor.prototype.trace = function (writer) {
 21761             writer.enter('> Uses');
 21762             this.entries.forEach(function (entry) {
 21763               writer.writeLn(entry.def.id + ' -> [' + entry.uses.map(toID).join(', ') + '] ' + entry.def);
 21764             });
 21765             writer.leave('<');
 21766           };
 21767           constructor.prototype.replace = function (def, value) {
 21768             var entry = this.entries[def.id];
 21769             if (entry.uses.length === 0) {
 21770               return false;
 21772             var count = 0;
 21773             entry.uses.forEach(function (use) {
 21774               count += use.replaceInput(def, value);
 21775             });
 21776             true;
 21777             entry.uses = [];
 21778             return true;
 21779           };
 21780           function updateUses(def, value) {
 21781             debug && writer.writeLn('Update ' + def + ' with ' + value);
 21782             var entry = useEntries[def.id];
 21783             if (entry.uses.length === 0) {
 21784               return false;
 21786             debug && writer.writeLn('Replacing: ' + def.id + ' in [' + entry.uses.map(toID).join(', ') + '] with ' + value.id);
 21787             var count = 0;
 21788             entry.uses.forEach(function (use) {
 21789               count += use.replaceInput(def, value);
 21790             });
 21791             true;
 21792             entry.uses = [];
 21793             return true;
 21795           return constructor;
 21796         }();
 21797       constructor.prototype.computeUses = function computeUses() {
 21798         Timer.start('computeUses');
 21799         var writer = debug && new IndentingWriter();
 21800         debug && writer.enter('> Compute Uses');
 21801         var dfg = this.dfg;
 21802         var uses = new Uses();
 21803         dfg.forEachInPreOrderDepthFirstSearch(function (use) {
 21804           use.visitInputs(function (def) {
 21805             uses.addUse(def, use);
 21806           });
 21807         });
 21808         if (debug) {
 21809           writer.enter('> Uses');
 21810           uses.entries.forEach(function (entry) {
 21811             writer.writeLn(entry.def.id + ' -> [' + entry.uses.map(toID).join(', ') + '] ' + entry.def);
 21812           });
 21813           writer.leave('<');
 21814           writer.leave('<');
 21816         Timer.stop();
 21817         return uses;
 21818       };
 21819       constructor.prototype.verify = function verify() {
 21820         var writer = debug && new IndentingWriter();
 21821         debug && writer.enter('> Verify');
 21822         var order = this.computeReversePostOrder();
 21823         order.forEach(function (block) {
 21824           if (block.phis) {
 21825             block.phis.forEach(function (phi) {
 21826               true;
 21827               true;
 21828             });
 21830         });
 21831         debug && writer.leave('<');
 21832       };
 21833       constructor.prototype.optimizePhis = function optimizePhis() {
 21834         var writer = debug && new IndentingWriter();
 21835         debug && writer.enter('> Optimize Phis');
 21836         var phis = [];
 21837         var useEntries = this.computeUses().entries;
 21838         useEntries.forEach(function (entry) {
 21839           if (isPhi(entry.def)) {
 21840             phis.push(entry.def);
 21842         });
 21843         debug && writer.writeLn('Trying to optimize ' + phis.length + ' phis.');
 21844         function updateUses(def, value) {
 21845           debug && writer.writeLn('Update ' + def + ' with ' + value);
 21846           var entry = useEntries[def.id];
 21847           if (entry.uses.length === 0) {
 21848             return false;
 21850           debug && writer.writeLn('Replacing: ' + def.id + ' in [' + entry.uses.map(toID).join(', ') + '] with ' + value.id);
 21851           var count = 0;
 21852           var entryUses = entry.uses;
 21853           for (var i = 0, j = entryUses.length; i < j; i++) {
 21854             count += entryUses[i].replaceInput(def, value);
 21856           true;
 21857           entry.uses = [];
 21858           return true;
 21860         function simplify(phi, args) {
 21861           args = args.unique();
 21862           if (args.length === 1) {
 21863             return args[0];
 21864           } else {
 21865             if (args.length === 2) {
 21866               if (args[0] === phi) {
 21867                 return args[1];
 21868               } else if (args[1] === phi) {
 21869                 return args[0];
 21871               return phi;
 21874           return phi;
 21876         var count = 0;
 21877         var iterations = 0;
 21878         var changed = true;
 21879         while (changed) {
 21880           iterations++;
 21881           changed = false;
 21882           phis.forEach(function (phi) {
 21883             var value = simplify(phi, phi.args);
 21884             if (value !== phi) {
 21885               if (updateUses(phi, value)) {
 21886                 changed = true;
 21887                 count++;
 21890           });
 21892         if (debug) {
 21893           writer.writeLn('Simplified ' + count + ' phis, in ' + iterations + ' iterations.');
 21894           writer.leave('<');
 21896       };
 21897       constructor.prototype.splitCriticalEdges = function splitCriticalEdges() {
 21898         var writer = debug && new IndentingWriter();
 21899         var blocks = this.blocks;
 21900         var criticalEdges = [];
 21901         debug && writer.enter('> Splitting Critical Edges');
 21902         for (var i = 0; i < blocks.length; i++) {
 21903           var successors = blocks[i].successors;
 21904           if (successors.length > 1) {
 21905             for (var j = 0; j < successors.length; j++) {
 21906               if (successors[j].predecessors.length > 1) {
 21907                 criticalEdges.push({
 21908                   from: blocks[i],
 21909                   to: successors[j]
 21910                 });
 21915         var criticalEdgeCount = criticalEdges.length;
 21916         if (criticalEdgeCount && debug) {
 21917           writer.writeLn('Splitting: ' + criticalEdgeCount);
 21918           this.trace(writer);
 21920         var edge;
 21921         while (edge = criticalEdges.pop()) {
 21922           var fromIndex = edge.from.successors.indexOf(edge.to);
 21923           var toIndex = edge.to.predecessors.indexOf(edge.from);
 21924           true;
 21925           debug && writer.writeLn('Splitting critical edge: ' + edge.from + ' -> ' + edge.to);
 21926           var toBlock = edge.to;
 21927           var toRegion = toBlock.region;
 21928           var control = toRegion.predecessors[toIndex];
 21929           var region = new Region(control);
 21930           var jump = new Jump(region);
 21931           var block = this.buildBlock(region, jump);
 21932           toRegion.predecessors[toIndex] = new Projection(jump, Projection.Type.TRUE);
 21933           var fromBlock = edge.from;
 21934           fromBlock.successors[fromIndex] = block;
 21935           block.pushPredecessor(fromBlock);
 21936           block.pushSuccessor(toBlock);
 21937           toBlock.predecessors[toIndex] = block;
 21939         if (criticalEdgeCount && debug) {
 21940           this.trace(writer);
 21942         if (criticalEdgeCount && !true) {
 21943           true;
 21945         debug && writer.leave('<');
 21946         return criticalEdgeCount;
 21947       };
 21948       constructor.prototype.allocateVariables = function allocateVariables() {
 21949         var writer = debug && new IndentingWriter();
 21950         debug && writer.enter('> Allocating Virtual Registers');
 21951         var order = this.computeReversePostOrder();
 21952         function allocate(node) {
 21953           if (isProjection(node, Projection.Type.STORE)) {
 21954             return;
 21956           if (node instanceof SetProperty) {
 21957             return;
 21959           if (node instanceof Value) {
 21960             node.variable = new Variable('v' + node.id);
 21961             debug && writer.writeLn('Allocated: ' + node.variable + ' to ' + node);
 21964         order.forEach(function (block) {
 21965           block.nodes.forEach(allocate);
 21966           if (block.phis) {
 21967             block.phis.forEach(allocate);
 21969         });
 21970         var blockMoves = [];
 21971         for (var i = 0; i < order.length; i++) {
 21972           var block = order[i];
 21973           var phis = block.phis;
 21974           var predecessors = block.predecessors;
 21975           if (phis) {
 21976             for (var j = 0; j < phis.length; j++) {
 21977               var phi = phis[j];
 21978               debug && writer.writeLn('Emitting moves for: ' + phi);
 21979               var arguments = phi.args;
 21980               true;
 21981               for (var k = 0; k < predecessors.length; k++) {
 21982                 var predecessor = predecessors[k];
 21983                 var argument = arguments[k];
 21984                 if (argument.abstract || isProjection(argument, Projection.Type.STORE)) {
 21985                   continue;
 21987                 var moves = blockMoves[predecessor.id] || (blockMoves[predecessor.id] = []);
 21988                 argument = argument.variable || argument;
 21989                 if (phi.variable !== argument) {
 21990                   moves.push(new Move(phi.variable, argument));
 21996         var blocks = this.blocks;
 21997         blockMoves.forEach(function (moves, blockID) {
 21998           var block = blocks[blockID];
 21999           var temporary = 0;
 22000           debug && writer.writeLn(block + ' Moves: ' + moves);
 22001           while (moves.length) {
 22002             for (var i = 0; i < moves.length; i++) {
 22003               var move = moves[i];
 22004               for (var j = 0; j < moves.length; j++) {
 22005                 if (i === j) {
 22006                   continue;
 22008                 if (moves[j].from === move.to) {
 22009                   move = null;
 22010                   break;
 22013               if (move) {
 22014                 moves.splice(i--, 1);
 22015                 block.append(move);
 22018             if (moves.length) {
 22019               debug && writer.writeLn('Breaking Cycle');
 22020               var move = moves[0];
 22021               var temp = new Variable('t' + temporary++);
 22022               blocks[blockID].append(new Move(temp, move.to));
 22023               for (var i = 1; i < moves.length; i++) {
 22024                 if (moves[i].from === move.to) {
 22025                   moves[i].from = temp;
 22030         });
 22031         debug && writer.leave('<');
 22032       };
 22033       constructor.prototype.scheduleEarly = function scheduleEarly() {
 22034         var debugScheduler = false;
 22035         var writer = debugScheduler && new IndentingWriter();
 22036         debugScheduler && writer.enter('> Schedule Early');
 22037         var cfg = this;
 22038         var dfg = this.dfg;
 22039         var scheduled = [];
 22040         var roots = [];
 22041         dfg.forEachInPreOrderDepthFirstSearch(function (node) {
 22042           if (node instanceof Region || node instanceof Jump) {
 22043             return;
 22045           if (node.control) {
 22046             roots.push(node);
 22048           if (isPhi(node)) {
 22049             node.args.forEach(function (input) {
 22050               if (shouldFloat(input)) {
 22051                 input.mustNotFloat = true;
 22053             });
 22055         }, true);
 22056         if (debugScheduler) {
 22057           roots.forEach(function (node) {
 22058             print('Root: ' + node);
 22059           });
 22061         for (var i = 0; i < roots.length; i++) {
 22062           var root = roots[i];
 22063           if (root instanceof Phi) {
 22064             var block = root.control.block;
 22065             (block.phis || (block.phis = [])).push(root);
 22067           if (root.control) {
 22068             schedule(root);
 22071         function isScheduled(node) {
 22072           return scheduled[node.id];
 22074         function shouldFloat(node) {
 22075           if (node.mustNotFloat || node.shouldNotFloat) {
 22076             return false;
 22078           if (node.mustFloat || node.shouldFloat) {
 22079             return true;
 22081           if (node instanceof Parameter || node instanceof This || node instanceof Arguments) {
 22082             return true;
 22084           return node instanceof Binary || node instanceof Unary || node instanceof Parameter;
 22086         function append(node) {
 22087           true;
 22088           scheduled[node.id] = true;
 22089           true;
 22090           if (shouldFloat(node)) {
 22091           } else {
 22092             node.control.block.append(node);
 22095         function scheduleIn(node, region) {
 22096           true;
 22097           true;
 22098           true;
 22099           debugScheduler && writer.writeLn('Scheduled: ' + node + ' in ' + region);
 22100           node.control = region;
 22101           append(node);
 22103         function schedule(node) {
 22104           debugScheduler && writer.enter('> Schedule: ' + node);
 22105           var inputs = [];
 22106           node.visitInputs(function (input) {
 22107             if (isConstant(input)) {
 22109                 return;
 22112             if (isValue(input)) {
 22113               inputs.push(followProjection(input));
 22115           });
 22116           debugScheduler && writer.writeLn('Inputs: [' + inputs.map(toID) + '], length: ' + inputs.length);
 22117           for (var i = 0; i < inputs.length; i++) {
 22118             var input = inputs[i];
 22119             if (isNotPhi(input) && !isScheduled(input)) {
 22120               schedule(input);
 22123           if (node.control) {
 22124             if (node instanceof End || node instanceof Phi || node instanceof Start || isScheduled(node)) {
 22125             } else {
 22126               append(node);
 22128           } else {
 22129             if (inputs.length) {
 22130               var x = inputs[0].control;
 22131               for (var i = 1; i < inputs.length; i++) {
 22132                 var y = inputs[i].control;
 22133                 if (x.block.dominatorDepth < y.block.dominatorDepth) {
 22134                   x = y;
 22137               scheduleIn(node, x);
 22138             } else {
 22139               scheduleIn(node, cfg.root.region);
 22142           debugScheduler && writer.leave('<');
 22144         debugScheduler && writer.leave('<');
 22145         roots.forEach(function (node) {
 22146           node = followProjection(node);
 22147           if (node === dfg.start || node instanceof Region) {
 22148             return;
 22150           true;
 22151         });
 22152       };
 22153       constructor.prototype.trace = function (writer) {
 22154         var visited = [];
 22155         var blocks = [];
 22156         function next(block) {
 22157           if (!visited[block.id]) {
 22158             visited[block.id] = true;
 22159             blocks.push(block);
 22160             block.visitSuccessors(next);
 22163         var root = this.root;
 22164         var exit = this.exit;
 22165         next(root);
 22166         function colorOf(block) {
 22167           return 'black';
 22169         function styleOf(block) {
 22170           return 'filled';
 22172         function shapeOf(block) {
 22173           true;
 22174           if (block === root) {
 22175             return 'house';
 22176           } else if (block === exit) {
 22177             return 'invhouse';
 22179           return 'box';
 22181         writer.writeLn('');
 22182         writer.enter('digraph CFG {');
 22183         writer.writeLn('graph [bgcolor = gray10];');
 22184         writer.writeLn('edge [fontname = Consolas, fontsize = 11, color = white, fontcolor = white];');
 22185         writer.writeLn('node [shape = box, fontname = Consolas, fontsize = 11, color = white, fontcolor = white, style = filled];');
 22186         writer.writeLn('rankdir = TB;');
 22187         blocks.forEach(function (block) {
 22188           var loopInfo = '';
 22189           var blockInfo = '';
 22190           var intervalInfo = '';
 22191           if (block.loops !== undefined) {
 22193           if (block.name !== undefined) {
 22194             blockInfo += ' ' + block.name;
 22196           if (block.rpo !== undefined) {
 22197             blockInfo += ' O: ' + block.rpo;
 22199           writer.writeLn('B' + block.id + ' [label = "B' + block.id + blockInfo + loopInfo + '", fillcolor = "' + colorOf(block) + '", shape=' + shapeOf(block) + ', style=' + styleOf(block) + '];');
 22200         });
 22201         blocks.forEach(function (block) {
 22202           block.visitSuccessors(function (successor) {
 22203             writer.writeLn('B' + block.id + ' -> ' + 'B' + successor.id);
 22204           });
 22205           if (block.dominator) {
 22206             writer.writeLn('B' + block.id + ' -> ' + 'B' + block.dominator.id + ' [color = orange];');
 22208           if (block.follow) {
 22209             writer.writeLn('B' + block.id + ' -> ' + 'B' + block.follow.id + ' [color = purple];');
 22211         });
 22212         writer.leave('}');
 22213         writer.writeLn('');
 22214       };
 22215       return constructor;
 22216     }();
 22217   var PeepholeOptimizer = function () {
 22218       function constructor() {
 22220       function foldUnary(node, truthy) {
 22221         true;
 22222         if (isConstant(node.argument)) {
 22223           return new Constant(node.operator.evaluate(node.argument.value));
 22225         if (truthy) {
 22226           var argument = fold(node.argument, true);
 22227           if (node.operator === Operator.TRUE) {
 22228             return argument;
 22230           if (argument instanceof Unary) {
 22231             if (node.operator === Operator.FALSE && argument.operator === Operator.FALSE) {
 22232               return argument.argument;
 22234           } else {
 22235             return new Unary(node.operator, argument);
 22238         return node;
 22240       function foldBinary(node, truthy) {
 22241         true;
 22242         if (isConstant(node.left) && isConstant(node.right)) {
 22243           return new Constant(node.operator.evaluate(node.left.value, node.right.value));
 22245         return node;
 22247       function fold(node, truthy) {
 22248         if (node instanceof Unary) {
 22249           return foldUnary(node, truthy);
 22250         } else if (node instanceof Binary) {
 22251           return foldBinary(node, truthy);
 22253         return node;
 22255       constructor.prototype.tryFold = fold;
 22256       return constructor;
 22257     }();
 22258   exports.isConstant = isConstant;
 22259   exports.Block = Block;
 22260   exports.Node = Node;
 22261   exports.Start = Start;
 22262   exports.Null = Null;
 22263   exports.Undefined = Undefined;
 22264   exports.This = This;
 22265   exports.Throw = Throw;
 22266   exports.Arguments = Arguments;
 22267   exports.ASGlobal = ASGlobal;
 22268   exports.Projection = Projection;
 22269   exports.Region = Region;
 22270   exports.Latch = Latch;
 22271   exports.Binary = Binary;
 22272   exports.Unary = Unary;
 22273   exports.Constant = Constant;
 22274   exports.ASFindProperty = ASFindProperty;
 22275   exports.GlobalProperty = GlobalProperty;
 22276   exports.GetProperty = GetProperty;
 22277   exports.SetProperty = SetProperty;
 22278   exports.CallProperty = CallProperty;
 22279   exports.ASCallProperty = ASCallProperty;
 22280   exports.ASCallSuper = ASCallSuper;
 22281   exports.ASGetProperty = ASGetProperty;
 22282   exports.ASGetSuper = ASGetSuper;
 22283   exports.ASHasProperty = ASHasProperty;
 22284   exports.ASDeleteProperty = ASDeleteProperty;
 22285   exports.ASGetDescendants = ASGetDescendants;
 22286   exports.ASSetProperty = ASSetProperty;
 22287   exports.ASSetSuper = ASSetSuper;
 22288   exports.ASGetSlot = ASGetSlot;
 22289   exports.ASSetSlot = ASSetSlot;
 22290   exports.Call = Call;
 22291   exports.ASNew = ASNew;
 22292   exports.Phi = Phi;
 22293   exports.Stop = Stop;
 22294   exports.If = If;
 22295   exports.Switch = Switch;
 22296   exports.End = End;
 22297   exports.Jump = Jump;
 22298   exports.ASScope = ASScope;
 22299   exports.Operator = Operator;
 22300   exports.Variable = Variable;
 22301   exports.Move = Move;
 22302   exports.Copy = Copy;
 22303   exports.Parameter = Parameter;
 22304   exports.NewArray = NewArray;
 22305   exports.NewObject = NewObject;
 22306   exports.ASNewActivation = ASNewActivation;
 22307   exports.KeyValuePair = KeyValuePair;
 22308   exports.ASMultiname = ASMultiname;
 22309   exports.DFG = DFG;
 22310   exports.CFG = CFG;
 22311   exports.Flags = Flags;
 22312   exports.PeepholeOptimizer = PeepholeOptimizer;
 22313 }(typeof exports === 'undefined' ? IR = {} : exports));
 22314 var c4Options = systemOptions.register(new OptionSet('C4 Options'));
 22315 var enableC4 = c4Options.register(new Option('c4', 'c4', 'boolean', false, 'Enable the C4 compiler.'));
 22316 var c4TraceLevel = c4Options.register(new Option('tc4', 'tc4', 'number', 0, 'Compiler Trace Level'));
 22317 var enableRegisterAllocator = c4Options.register(new Option('ra', 'ra', 'boolean', false, 'Enable register allocator.'));
 22318 var getPublicQualifiedName = Multiname.getPublicQualifiedName;
 22319 var createName = function createName(namespaces, name) {
 22320   if (isNumeric(name) || isObject(name)) {
 22321     return name;
 22323   return new Multiname(namespaces, name);
 22324 };
 22325 (function (exports) {
 22326   var Node = IR.Node;
 22327   var Start = IR.Start;
 22328   var Null = IR.Null;
 22329   var Undefined = IR.Undefined;
 22330   var This = IR.This;
 22331   var Projection = IR.Projection;
 22332   var Region = IR.Region;
 22333   var Binary = IR.Binary;
 22334   var Unary = IR.Unary;
 22335   var Constant = IR.Constant;
 22336   var Call = IR.Call;
 22337   var Phi = IR.Phi;
 22338   var Stop = IR.Stop;
 22339   var Operator = IR.Operator;
 22340   var Parameter = IR.Parameter;
 22341   var NewArray = IR.NewArray;
 22342   var NewObject = IR.NewObject;
 22343   var KeyValuePair = IR.KeyValuePair;
 22344   var isConstant = IR.isConstant;
 22345   var DFG = IR.DFG;
 22346   var CFG = IR.CFG;
 22347   var writer = new IndentingWriter();
 22348   var peepholeOptimizer = new IR.PeepholeOptimizer();
 22349   var USE_TYPE_OF_DEFAULT_ARGUMENT_CHECKING = false;
 22350   var State = function () {
 22351       var nextID = 0;
 22352       function constructor(index) {
 22353         this.id = nextID += 1;
 22354         this.index = index;
 22355         this.local = [];
 22356         this.stack = [];
 22357         this.scope = [];
 22358         this.store = Undefined;
 22359         this.loads = [];
 22360         this.saved = Undefined;
 22362       constructor.prototype.clone = function clone(index) {
 22363         var s = new State();
 22364         s.index = index !== undefined ? index : this.index;
 22365         s.local = this.local.slice(0);
 22366         s.stack = this.stack.slice(0);
 22367         s.scope = this.scope.slice(0);
 22368         s.loads = this.loads.slice(0);
 22369         s.saved = this.saved;
 22370         s.store = this.store;
 22371         return s;
 22372       };
 22373       constructor.prototype.matches = function matches(other) {
 22374         return this.stack.length === other.stack.length && this.scope.length === other.scope.length && this.local.length === other.local.length;
 22375       };
 22376       constructor.prototype.makeLoopPhis = function makeLoopPhis(control) {
 22377         var s = new State();
 22378         true;
 22379         function makePhi(x) {
 22380           var phi = new Phi(control, x);
 22381           phi.isLoop = true;
 22382           return phi;
 22384         s.index = this.index;
 22385         s.local = this.local.map(makePhi);
 22386         s.stack = this.stack.map(makePhi);
 22387         s.scope = this.scope.map(makePhi);
 22388         s.loads = this.loads.slice(0);
 22389         s.saved = this.saved;
 22390         s.store = makePhi(this.store);
 22391         return s;
 22392       };
 22393       constructor.prototype.optimize = function optimize() {
 22394         function optimize(x) {
 22395           if (x instanceof Phi && !x.isLoop) {
 22396             var args = x.args.unique();
 22397             if (args.length === 1) {
 22398               x.seal();
 22399               Counter.count('Builder: OptimizedPhi');
 22400               return args[0];
 22403           return x;
 22405         this.local = this.local.map(optimize);
 22406         this.stack = this.stack.map(optimize);
 22407         this.scope = this.scope.map(optimize);
 22408         this.saved = optimize(this.saved);
 22409         this.store = optimize(this.store);
 22410       };
 22411       function mergeValue(control, a, b) {
 22412         var phi = a instanceof Phi && a.control === control ? a : new Phi(control, a);
 22413         phi.pushValue(b);
 22414         return phi;
 22416       function mergeValues(control, a, b) {
 22417         for (var i = 0; i < a.length; i++) {
 22418           a[i] = mergeValue(control, a[i], b[i]);
 22421       constructor.prototype.merge = function merge(control, other) {
 22422         true;
 22423         true;
 22424         mergeValues(control, this.local, other.local);
 22425         mergeValues(control, this.stack, other.stack);
 22426         mergeValues(control, this.scope, other.scope);
 22427         this.store = mergeValue(control, this.store, other.store);
 22428         this.store.abstract = true;
 22429       };
 22430       constructor.prototype.trace = function trace(writer) {
 22431         writer.writeLn(this.toString());
 22432       };
 22433       function toBriefString(x) {
 22434         if (x instanceof Node) {
 22435           return x.toString(true);
 22437         return x;
 22439       constructor.prototype.toString = function () {
 22440         return '<' + String(this.id + ' @ ' + this.index).padRight(' ', 10) + (' M: ' + toBriefString(this.store)).padRight(' ', 14) + (' X: ' + toBriefString(this.saved)).padRight(' ', 14) + (' $: ' + this.scope.map(toBriefString).join(', ')).padRight(' ', 20) + (' L: ' + this.local.map(toBriefString).join(', ')).padRight(' ', 40) + (' S: ' + this.stack.map(toBriefString).join(', ')).padRight(' ', 60);
 22441       };
 22442       return constructor;
 22443     }();
 22444   function isNumericConstant(node) {
 22445     return node instanceof Constant && isNumeric(node.value);
 22447   function isStringConstant(node) {
 22448     return node instanceof Constant && isString(node.value);
 22450   function isMultinameConstant(node) {
 22451     return node instanceof Constant && node.value instanceof Multiname;
 22453   function hasNumericType(node) {
 22454     if (isNumericConstant(node)) {
 22455       return true;
 22457     return node.ty && node.ty.isNumeric();
 22459   function typesAreEqual(a, b) {
 22460     if (hasNumericType(a) && hasNumericType(b) || hasStringType(a) && hasStringType(b)) {
 22461       return true;
 22463     return false;
 22465   function hasStringType(node) {
 22466     if (isStringConstant(node)) {
 22467       return true;
 22469     return node.ty && node.ty.isString();
 22471   function constant(value) {
 22472     return new Constant(value);
 22474   function qualifiedNameConstant(name) {
 22475     return constant(Multiname.getQualifiedName(name));
 22477   function getJSPropertyWithState(state, object, path) {
 22478     true;
 22479     var names = path.split('.');
 22480     var node = object;
 22481     for (var i = 0; i < names.length; i++) {
 22482       node = new IR.GetProperty(null, state.store, node, constant(names[i]));
 22483       node.shouldFloat = true;
 22484       state.loads.push(node);
 22486     return node;
 22488   function globalProperty(name) {
 22489     var node = new IR.GlobalProperty(name);
 22490     node.mustFloat = true;
 22491     return node;
 22493   function warn(message) {
 22495   function unary(operator, argument) {
 22496     var node = new Unary(operator, argument);
 22497     if (peepholeOptimizer) {
 22498       node = peepholeOptimizer.tryFold(node);
 22500     return node;
 22502   function binary(operator, left, right) {
 22503     var node = new Binary(operator, left, right);
 22504     if (left.ty && left.ty !== Type.Any && left.ty === right.ty) {
 22505       if (operator === Operator.EQ) {
 22506         node.operator = Operator.SEQ;
 22507       } else if (operator === Operator.NE) {
 22508         node.operator = Operator.SNE;
 22511     if (peepholeOptimizer) {
 22512       node = peepholeOptimizer.tryFold(node);
 22514     return node;
 22516   function coerceInt(value) {
 22517     return binary(Operator.OR, value, constant(0));
 22519   function coerceUint(value) {
 22520     return binary(Operator.URSH, value, constant(0));
 22522   function coerceNumber(value) {
 22523     if (hasNumericType(value)) {
 22524       return value;
 22526     return unary(Operator.PLUS, value);
 22528   function coerceBoolean(value) {
 22529     return unary(Operator.FALSE, unary(Operator.FALSE, value));
 22531   function shouldNotFloat(node) {
 22532     node.shouldNotFloat = true;
 22533     return node;
 22535   function shouldFloat(node) {
 22536     true;
 22537     node.shouldFloat = true;
 22538     return node;
 22540   function mustFloat(node) {
 22541     node.mustFloat = true;
 22542     return node;
 22544   function callPure(callee, object, args) {
 22545     return new Call(null, null, callee, object, args, IR.Flags.PRISTINE);
 22547   function callGlobalProperty(name, value) {
 22548     return callPure(globalProperty(name), null, [
 22549       value
 22550     ]);
 22552   function convertString(value) {
 22553     if (isStringConstant(value)) {
 22554       return value;
 22556     return callPure(globalProperty('String'), null, [
 22557       value
 22558     ]);
 22560   function coerceString(value) {
 22561     if (isStringConstant(value)) {
 22562       return value;
 22564     return callPure(globalProperty('asCoerceString'), null, [
 22565       value
 22566     ]);
 22568   var coerceObject = callGlobalProperty.bind(null, 'asCoerceObject');
 22569   var coercers = createEmptyObject();
 22570   coercers[Multiname.Int] = coerceInt;
 22571   coercers[Multiname.Uint] = coerceUint;
 22572   coercers[Multiname.Number] = coerceNumber;
 22573   coercers[Multiname.String] = coerceString;
 22574   coercers[Multiname.Object] = coerceObject;
 22575   coercers[Multiname.Boolean] = coerceBoolean;
 22576   function getCoercerForType(multiname) {
 22577     true;
 22578     return coercers[Multiname.getQualifiedName(multiname)];
 22580   var callableConstructors = createEmptyObject();
 22581   callableConstructors[Multiname.Int] = coerceInt;
 22582   callableConstructors[Multiname.Uint] = coerceUint;
 22583   callableConstructors[Multiname.Number] = callGlobalProperty.bind(null, 'Number');
 22584   callableConstructors[Multiname.String] = callGlobalProperty.bind(null, 'String');
 22585   callableConstructors[Multiname.Object] = callGlobalProperty.bind(null, 'Object');
 22586   callableConstructors[Multiname.Boolean] = callGlobalProperty.bind(null, 'Boolean');
 22587   function getCallableConstructorForType(multiname) {
 22588     true;
 22589     return callableConstructors[Multiname.getQualifiedName(multiname)];
 22591   var Builder = function () {
 22592       function builder(methodInfo, scope, hasDynamicScope) {
 22593         true;
 22594         this.abc = methodInfo.abc;
 22595         this.scope = scope;
 22596         this.methodInfo = methodInfo;
 22597         this.hasDynamicScope = hasDynamicScope;
 22599       builder.prototype.buildStart = function (start) {
 22600         var mi = this.methodInfo;
 22601         var state = start.entryState = new State(0);
 22602         state.local.push(new This(start));
 22603         var parameterIndexOffset = this.hasDynamicScope ? 1 : 0;
 22604         var parameterCount = mi.parameters.length;
 22605         for (var i = 0; i < parameterCount; i++) {
 22606           state.local.push(new Parameter(start, parameterIndexOffset + i, mi.parameters[i].name));
 22608         for (var i = parameterCount; i < mi.localCount; i++) {
 22609           state.local.push(Undefined);
 22611         state.store = new Projection(start, Projection.Type.STORE);
 22612         if (this.hasDynamicScope) {
 22613           start.scope = new Parameter(start, 0, SAVED_SCOPE_NAME);
 22614         } else {
 22615           start.scope = new Constant(this.scope);
 22617         state.saved = new Projection(start, Projection.Type.SCOPE);
 22618         start.domain = new Constant(this.domain);
 22619         var args = new IR.Arguments(start);
 22620         if (mi.needsRest() || mi.needsArguments()) {
 22621           var offset = constant(parameterIndexOffset + (mi.needsRest() ? parameterCount : 0));
 22622           state.local[parameterCount + 1] = new Call(start, state.store, globalProperty('sliceArguments'), null, [
 22623             args,
 22624             offset
 22625           ], IR.Flags.PRISTINE);
 22627         var argumentsLength = getJSPropertyWithState(state, args, 'length');
 22628         for (var i = 0; i < parameterCount; i++) {
 22629           var parameter = mi.parameters[i];
 22630           var index = i + 1;
 22631           var local = state.local[index];
 22632           if (parameter.value !== undefined) {
 22633             var condition;
 22634             if (USE_TYPE_OF_DEFAULT_ARGUMENT_CHECKING) {
 22635               condition = new IR.Binary(Operator.SEQ, new IR.Unary(Operator.TYPE_OF, local), constant('undefined'));
 22636             } else {
 22637               condition = new IR.Binary(Operator.LT, argumentsLength, constant(parameterIndexOffset + i + 1));
 22639             local = new IR.Latch(null, condition, constant(parameter.value), local);
 22641           if (parameter.type && !parameter.type.isAnyName()) {
 22642             var coercer = getCoercerForType(parameter.type);
 22643             if (coercer) {
 22644               local = coercer(local);
 22645             } else if (c4CoerceNonPrimitiveParameters) {
 22646               local = new Call(start, state.store, globalProperty('asCoerceByMultiname'), null, [
 22647                 constant(this.abc.applicationDomain),
 22648                 constant(parameter.type),
 22649                 local
 22650               ], true);
 22653           state.local[index] = local;
 22655         return start;
 22656       };
 22657       builder.prototype.buildGraph = function buildGraph(callerRegion, callerState, inlineArguments) {
 22658         var analysis = this.methodInfo.analysis;
 22659         var blocks = analysis.blocks;
 22660         var bytecodes = analysis.bytecodes;
 22661         var methodInfo = this.methodInfo;
 22662         var ints = this.abc.constantPool.ints;
 22663         var uints = this.abc.constantPool.uints;
 22664         var doubles = this.abc.constantPool.doubles;
 22665         var strings = this.abc.constantPool.strings;
 22666         var methods = this.abc.methods;
 22667         var classes = this.abc.classes;
 22668         var multinames = this.abc.constantPool.multinames;
 22669         var domain = new Constant(this.abc.applicationDomain);
 22670         var traceBuilder = c4TraceLevel.value > 2;
 22671         var stopPoints = [];
 22672         for (var i = 0; i < blocks.length; i++) {
 22673           blocks[i].blockDominatorOrder = i;
 22675         var worklist = new Shumway.SortedList(function compare(a, b) {
 22676             return a.block.blockDominatorOrder - b.block.blockDominatorOrder;
 22677           });
 22678         var start = new Start(null);
 22679         this.buildStart(start);
 22680         var createFunctionCallee = globalProperty('createFunction');
 22681         worklist.push({
 22682           region: start,
 22683           block: blocks[0]
 22684         });
 22685         var next;
 22686         while (next = worklist.pop()) {
 22687           buildBlock(next.region, next.block, next.region.entryState.clone()).forEach(function (stop) {
 22688             var target = stop.target;
 22689             var region = target.region;
 22690             if (region) {
 22691               traceBuilder && writer.enter('Merging into region: ' + region + ' @ ' + target.position + ', block ' + target.bid + ' {');
 22692               traceBuilder && writer.writeLn('  R ' + region.entryState);
 22693               traceBuilder && writer.writeLn('+ I ' + stop.state);
 22694               region.entryState.merge(region, stop.state);
 22695               region.predecessors.push(stop.control);
 22696               traceBuilder && writer.writeLn('  = ' + region.entryState);
 22697               traceBuilder && writer.leave('}');
 22698             } else {
 22699               region = target.region = new Region(stop.control);
 22700               if (target.loop) {
 22701                 traceBuilder && writer.writeLn('Adding PHIs to loop region.');
 22703               region.entryState = target.loop ? stop.state.makeLoopPhis(region) : stop.state.clone(target.position);
 22704               traceBuilder && writer.writeLn('Adding new region: ' + region + ' @ ' + target.position + ' to worklist.');
 22705               worklist.push({
 22706                 region: region,
 22707                 block: target
 22708               });
 22710           });
 22711           traceBuilder && writer.enter('Worklist: {');
 22712           worklist.forEach(function (item) {
 22713             traceBuilder && writer.writeLn(item.region + ' ' + item.block.bdo + ' ' + item.region.entryState);
 22714           });
 22715           traceBuilder && writer.leave('}');
 22717         traceBuilder && writer.writeLn('Done');
 22718         function buildBlock(region, block, state) {
 22719           true;
 22720           state.optimize();
 22721           var typeState = block.entryState;
 22722           if (typeState) {
 22723             traceBuilder && writer.writeLn('Type State: ' + typeState);
 22724             for (var i = 0; i < typeState.local.length; i++) {
 22725               var type = typeState.local[i];
 22726               var local = state.local[i];
 22727               if (local.ty) {
 22728               } else {
 22729                 local.ty = type;
 22733           var local = state.local;
 22734           var stack = state.stack;
 22735           var scope = state.scope;
 22736           function savedScope() {
 22737             return state.saved;
 22739           function topScope(depth) {
 22740             if (depth !== undefined) {
 22741               if (depth < scope.length) {
 22742                 return scope[scope.length - 1 - depth];
 22743               } else if (depth === scope.length) {
 22744                 return savedScope();
 22745               } else {
 22746                 var s = savedScope();
 22747                 var savedScopeDepth = depth - scope.length;
 22748                 for (var i = 0; i < savedScopeDepth; i++) {
 22749                   s = getJSProperty(s, 'parent');
 22751                 return s;
 22754             if (scope.length > 0) {
 22755               return scope.top();
 22757             return savedScope();
 22759           var object, receiver, index, callee, value, multiname, type, args, pristine, left, right, operator;
 22760           function push(x) {
 22761             true;
 22762             if (bc.ti) {
 22763               if (x.ty) {
 22764               } else {
 22765                 x.ty = bc.ti.type;
 22768             stack.push(x);
 22770           function pop() {
 22771             return stack.pop();
 22773           function popMany(count) {
 22774             return stack.popMany(count);
 22776           function pushLocal(index) {
 22777             push(local[index]);
 22779           function popLocal(index) {
 22780             local[index] = shouldNotFloat(pop());
 22782           function buildMultiname(index) {
 22783             var multiname = multinames[index];
 22784             var namespaces, name, flags = multiname.flags;
 22785             if (multiname.isRuntimeName()) {
 22786               name = stack.pop();
 22787             } else {
 22788               name = constant(multiname.name);
 22790             if (multiname.isRuntimeNamespace()) {
 22791               namespaces = shouldFloat(new NewArray(region, [
 22792                 pop()
 22793               ]));
 22794             } else {
 22795               namespaces = constant(multiname.namespaces);
 22797             return new IR.ASMultiname(namespaces, name, flags);
 22799           function simplifyName(name) {
 22800             if (isMultinameConstant(name) && Multiname.isQName(name.value)) {
 22801               return constant(Multiname.getQualifiedName(name.value));
 22803             return name;
 22805           function getGlobalScope(ti) {
 22806             if (ti && ti.object) {
 22807               return constant(ti.object);
 22809             return new IR.ASGlobal(null, savedScope());
 22811           function findProperty(multiname, strict, ti) {
 22812             var slowPath = new IR.ASFindProperty(region, state.store, topScope(), multiname, domain, strict);
 22813             if (ti) {
 22814               if (ti.object) {
 22815                 if (ti.object instanceof Global && !ti.object.isExecuting()) {
 22816                   warn('Can\'t optimize findProperty ' + multiname + ', global object is not yet executed or executing.');
 22817                   return slowPath;
 22819                 return constant(ti.object);
 22820               } else if (ti.scopeDepth !== undefined) {
 22821                 return getScopeObject(topScope(ti.scopeDepth));
 22824             warn('Can\'t optimize findProperty ' + multiname);
 22825             return slowPath;
 22827           function getJSProperty(object, path) {
 22828             return getJSPropertyWithState(state, object, path);
 22830           function coerce(multiname, value) {
 22831             if (false && isConstant(value)) {
 22832               return constant(asCoerceByMultiname(domain.value, multiname, value.value));
 22833             } else {
 22834               var coercer = getCoercerForType(multiname);
 22835               if (coercer) {
 22836                 return coercer(value);
 22839             if (c4CoerceNonPrimitive) {
 22840               return call(globalProperty('asCoerceByMultiname'), null, [
 22841                 domain,
 22842                 constant(multiname),
 22843                 value
 22844               ]);
 22846             return value;
 22848           function getScopeObject(scope) {
 22849             if (scope instanceof IR.ASScope) {
 22850               return scope.object;
 22852             return getJSProperty(scope, 'object');
 22854           function store(node) {
 22855             state.store = new Projection(node, Projection.Type.STORE);
 22856             node.loads = state.loads.slice(0);
 22857             state.loads.length = 0;
 22858             return node;
 22860           function load(node) {
 22861             state.loads.push(node);
 22862             return node;
 22864           function resolveMultinameGlobally(multiname) {
 22865             var namespaces = multiname.namespaces;
 22866             var name = multiname.name;
 22867             if (!Shumway.AVM2.Runtime.globalMultinameAnalysis.value) {
 22868               return;
 22870             if (!isConstant(namespaces) || !isConstant(name) || multiname.isAttribute()) {
 22871               Counter.count('GlobalMultinameResolver: Cannot resolve runtime multiname or attribute.');
 22872               return;
 22874             if (isNumeric(name.value) || !isString(name.value) || !name.value) {
 22875               Counter.count('GlobalMultinameResolver: Cannot resolve numeric or any names.');
 22876               return false;
 22878             return GlobalMultinameResolver.resolveMultiname(new Multiname(namespaces.value, name.value, multiname.flags));
 22880           function callSuper(scope, object, multiname, args, ti) {
 22881             if (ti && ti.trait && ti.trait.isMethod() && ti.baseClass) {
 22882               var qn = VM_OPEN_METHOD_PREFIX + Multiname.getQualifiedName(ti.trait.name);
 22883               var callee = getJSProperty(constant(ti.baseClass), 'traitsPrototype.' + qn);
 22884               return call(callee, object, args);
 22886             return store(new IR.ASCallSuper(region, state.store, object, multiname, args, IR.Flags.PRISTINE, scope));
 22888           function getSuper(scope, object, multiname, ti) {
 22889             if (ti && ti.trait && ti.trait.isGetter() && ti.baseClass) {
 22890               var qn = VM_OPEN_GET_METHOD_PREFIX + Multiname.getQualifiedName(ti.trait.name);
 22891               var callee = getJSProperty(constant(ti.baseClass), 'traitsPrototype.' + qn);
 22892               return call(callee, object, []);
 22894             return store(new IR.ASGetSuper(region, state.store, object, multiname, scope));
 22896           function setSuper(scope, object, multiname, value, ti) {
 22897             if (ti && ti.trait && ti.trait.isSetter() && ti.baseClass) {
 22898               var qn = VM_OPEN_SET_METHOD_PREFIX + Multiname.getQualifiedName(ti.trait.name);
 22899               var callee = getJSProperty(constant(ti.baseClass), 'traitsPrototype.' + qn);
 22900               return call(callee, object, [
 22901                 value
 22902               ]);
 22904             return store(new IR.ASSetSuper(region, state.store, object, multiname, value, scope));
 22906           function constructSuper(scope, object, args, ti) {
 22907             if (ti) {
 22908               if (ti.noCallSuperNeeded) {
 22909                 return;
 22910               } else if (ti.baseClass) {
 22911                 var callee = getJSProperty(constant(ti.baseClass), 'instanceConstructorNoInitialize');
 22912                 call(callee, object, args);
 22913                 return;
 22916             callee = getJSProperty(scope, 'object.baseClass.instanceConstructorNoInitialize');
 22917             call(callee, object, args);
 22918             return;
 22920           function callProperty(object, multiname, args, isLex, ti) {
 22921             if (ti && ti.trait) {
 22922               if (ti.trait.isMethod()) {
 22923                 var openQn;
 22924                 if (ti.trait.holder instanceof InstanceInfo && ti.trait.holder.isInterface()) {
 22925                   openQn = Multiname.getPublicQualifiedName(Multiname.getName(ti.trait.name));
 22926                 } else {
 22927                   openQn = Multiname.getQualifiedName(ti.trait.name);
 22929                 openQn = VM_OPEN_METHOD_PREFIX + openQn;
 22930                 return store(new IR.CallProperty(region, state.store, object, constant(openQn), args, IR.Flags.PRISTINE));
 22931               } else if (ti.trait.isClass()) {
 22932                 var constructor = getCallableConstructorForType(ti.trait.name);
 22933                 if (constructor) {
 22934                   return constructor(args[0]);
 22936                 var qn = Multiname.getQualifiedName(ti.trait.name);
 22937                 return store(new IR.CallProperty(region, state.store, object, constant(qn), args, 0));
 22939             } else if (ti && ti.propertyQName) {
 22940               return store(new IR.CallProperty(region, state.store, object, constant(ti.propertyQName), args, IR.Flags.PRISTINE));
 22942             var qn = resolveMultinameGlobally(multiname);
 22943             if (qn) {
 22944               return store(new IR.ASCallProperty(region, state.store, object, constant(Multiname.getQualifiedName(qn)), args, IR.Flags.PRISTINE | IR.Flags.RESOLVED, isLex));
 22946             return store(new IR.ASCallProperty(region, state.store, object, multiname, args, IR.Flags.PRISTINE, isLex));
 22948           function getProperty(object, multiname, ti, getOpenMethod) {
 22949             true;
 22950             getOpenMethod = !(!getOpenMethod);
 22951             if (ti) {
 22952               if (ti.trait) {
 22953                 if (ti.trait.isConst() && ti.trait.hasDefaultValue) {
 22954                   return constant(ti.trait.value);
 22956                 var get = new IR.GetProperty(region, state.store, object, qualifiedNameConstant(ti.trait.name));
 22957                 return ti.trait.isGetter() ? store(get) : load(get);
 22959               if (ti.propertyQName) {
 22960                 return store(new IR.GetProperty(region, state.store, object, constant(ti.propertyQName)));
 22961               } else if (ti.isDirectlyReadable) {
 22962                 return store(new IR.GetProperty(region, state.store, object, multiname.name));
 22963               } else if (ti.isIndexedReadable) {
 22964                 return store(new IR.ASGetProperty(region, state.store, object, multiname, IR.Flags.INDEXED | (getOpenMethod ? IR.Flagas.IS_METHOD : 0)));
 22967             warn('Can\'t optimize getProperty ' + multiname);
 22968             var qn = resolveMultinameGlobally(multiname);
 22969             if (qn) {
 22970               return store(new IR.ASGetProperty(region, state.store, object, constant(Multiname.getQualifiedName(qn)), IR.Flags.RESOLVED | (getOpenMethod ? IR.Flagas.IS_METHOD : 0)));
 22972             Counter.count('Compiler: Slow ASGetProperty');
 22973             return store(new IR.ASGetProperty(region, state.store, object, multiname, getOpenMethod ? IR.Flagas.IS_METHOD : 0));
 22975           function setProperty(object, multiname, value, ti) {
 22976             true;
 22977             if (ti) {
 22978               if (ti.trait) {
 22979                 var coercer = ti.trait.typeName ? getCoercerForType(ti.trait.typeName) : null;
 22980                 if (coercer) {
 22981                   value = coercer(value);
 22983                 store(new IR.SetProperty(region, state.store, object, qualifiedNameConstant(ti.trait.name), value));
 22984                 return;
 22986               if (ti.propertyQName) {
 22987                 return store(new IR.SetProperty(region, state.store, object, constant(ti.propertyQName), value));
 22988               } else if (ti.isDirectlyWriteable) {
 22989                 return store(new IR.SetProperty(region, state.store, object, multiname.name, value));
 22990               } else if (ti.isIndexedWriteable) {
 22991                 return store(new IR.ASSetProperty(region, state.store, object, multiname, value, IR.Flags.INDEXED));
 22994             warn('Can\'t optimize setProperty ' + multiname);
 22995             var qn = resolveMultinameGlobally(multiname);
 22996             if (qn) {
 22998             return store(new IR.ASSetProperty(region, state.store, object, multiname, value, 0));
 23000           function getDescendants(object, name, ti) {
 23001             name = simplifyName(name);
 23002             return new IR.ASGetDescendants(region, state.store, object, name);
 23004           function getSlot(object, index, ti) {
 23005             if (ti) {
 23006               var trait = ti.trait;
 23007               if (trait) {
 23008                 if (trait.isConst() && ti.trait.hasDefaultValue) {
 23009                   return constant(trait.value);
 23011                 var slotQn = Multiname.getQualifiedName(trait.name);
 23012                 return store(new IR.GetProperty(region, state.store, object, constant(slotQn)));
 23015             warn('Can\'t optimize getSlot ' + index);
 23016             return store(new IR.ASGetSlot(null, state.store, object, index));
 23018           function setSlot(object, index, value, ti) {
 23019             if (ti) {
 23020               var trait = ti.trait;
 23021               if (trait) {
 23022                 var slotQn = Multiname.getQualifiedName(trait.name);
 23023                 store(new IR.SetProperty(region, state.store, object, constant(slotQn), value));
 23024                 return;
 23027             warn('Can\'t optimize setSlot ' + index);
 23028             store(new IR.ASSetSlot(region, state.store, object, index, value));
 23030           function call(callee, object, args) {
 23031             return store(new Call(region, state.store, callee, object, args, IR.Flags.PRISTINE));
 23033           function callCall(callee, object, args, pristine) {
 23034             return store(new Call(region, state.store, callee, object, args, pristine ? IR.Flags.PRISTINE : 0));
 23036           function truthyCondition(operator) {
 23037             var right;
 23038             if (operator.isBinary()) {
 23039               right = pop();
 23041             var left = pop();
 23042             var node;
 23043             if (right) {
 23044               node = binary(operator, left, right);
 23045             } else {
 23046               node = unary(operator, left);
 23048             if (peepholeOptimizer) {
 23049               node = peepholeOptimizer.tryFold(node, true);
 23051             return node;
 23053           function negatedTruthyCondition(operator) {
 23054             var node = unary(Operator.FALSE, truthyCondition(operator));
 23055             if (peepholeOptimizer) {
 23056               node = peepholeOptimizer.tryFold(node, true);
 23058             return node;
 23060           function pushExpression(operator, toInt) {
 23061             var left, right;
 23062             if (operator.isBinary()) {
 23063               right = pop();
 23064               left = pop();
 23065               if (toInt) {
 23066                 right = coerceInt(right);
 23067                 left = coerceInt(left);
 23069               push(binary(operator, left, right));
 23070             } else {
 23071               left = pop();
 23072               if (toInt) {
 23073                 left = coerceInt(left);
 23075               push(unary(operator, left));
 23078           var stops = null;
 23079           function buildIfStops(predicate) {
 23080             true;
 23081             var _if = new IR.If(region, predicate);
 23082             stops = [
 23084                 control: new Projection(_if, Projection.Type.FALSE),
 23085                 target: bytecodes[bc.position + 1],
 23086                 state: state
 23087               },
 23089                 control: new Projection(_if, Projection.Type.TRUE),
 23090                 target: bc.target,
 23091                 state: state
 23093             ];
 23095           function buildJumpStop() {
 23096             true;
 23097             stops = [
 23099                 control: region,
 23100                 target: bc.target,
 23101                 state: state
 23103             ];
 23105           function buildThrowStop() {
 23106             true;
 23107             stops = [];
 23109           function buildReturnStop() {
 23110             true;
 23111             stops = [];
 23113           function buildSwitchStops(determinant) {
 23114             true;
 23115             if (bc.targets.length > 2) {
 23116               stops = [];
 23117               var _switch = new IR.Switch(region, determinant);
 23118               for (var i = 0; i < bc.targets.length; i++) {
 23119                 stops.push({
 23120                   control: new Projection(_switch, Projection.Type.CASE, constant(i)),
 23121                   target: bc.targets[i],
 23122                   state: state
 23123                 });
 23125             } else {
 23126               true;
 23127               var predicate = binary(Operator.SEQ, determinant, constant(0));
 23128               var _if = new IR.If(region, predicate);
 23129               stops = [
 23131                   control: new Projection(_if, Projection.Type.FALSE),
 23132                   target: bc.targets[1],
 23133                   state: state
 23134                 },
 23136                   control: new Projection(_if, Projection.Type.TRUE),
 23137                   target: bc.targets[0],
 23138                   state: state
 23140               ];
 23143           if (traceBuilder) {
 23144             writer.writeLn('Processing Region: ' + region + ', Block: ' + block.bid);
 23145             writer.enter(('> state: ' + region.entryState.toString()).padRight(' ', 100));
 23147           region.processed = true;
 23148           var bc;
 23149           for (var bci = block.position, end = block.end.position; bci <= end; bci++) {
 23150             bc = bytecodes[bci];
 23151             var op = bc.op;
 23152             state.index = bci;
 23153             switch (op) {
 23154             case 3:
 23155               store(new IR.Throw(region, pop()));
 23156               stopPoints.push({
 23157                 region: region,
 23158                 store: state.store,
 23159                 value: Undefined
 23160               });
 23161               buildThrowStop();
 23162               break;
 23163             case 98:
 23164               pushLocal(bc.index);
 23165               break;
 23166             case 208:
 23167             case 209:
 23168             case 210:
 23169             case 211:
 23170               pushLocal(op - OP_getlocal0);
 23171               break;
 23172             case 99:
 23173               popLocal(bc.index);
 23174               break;
 23175             case 212:
 23176             case 213:
 23177             case 214:
 23178             case 215:
 23179               popLocal(op - OP_setlocal0);
 23180               break;
 23181             case 28:
 23182               scope.push(new IR.ASScope(topScope(), pop(), true));
 23183               break;
 23184             case 48:
 23185               scope.push(new IR.ASScope(topScope(), pop(), false));
 23186               break;
 23187             case 29:
 23188               scope.pop();
 23189               break;
 23190             case 100:
 23191               push(getGlobalScope(bc.ti));
 23192               break;
 23193             case 101:
 23194               push(getScopeObject(state.scope[bc.index]));
 23195               break;
 23196             case 93:
 23197               push(findProperty(buildMultiname(bc.index), true, bc.ti));
 23198               break;
 23199             case 94:
 23200               push(findProperty(buildMultiname(bc.index), false, bc.ti));
 23201               break;
 23202             case 102:
 23203               multiname = buildMultiname(bc.index);
 23204               object = pop();
 23205               push(getProperty(object, multiname, bc.ti, false));
 23206               break;
 23207             case 89:
 23208               multiname = buildMultiname(bc.index);
 23209               object = pop();
 23210               push(getDescendants(object, multiname, bc.ti));
 23211               break;
 23212             case 96:
 23213               multiname = buildMultiname(bc.index);
 23214               push(getProperty(findProperty(multiname, true, bc.ti), multiname, bc.ti, false));
 23215               break;
 23216             case 104:
 23217             case 97:
 23218               value = pop();
 23219               multiname = buildMultiname(bc.index);
 23220               object = pop();
 23221               setProperty(object, multiname, value, bc.ti);
 23222               break;
 23223             case 106:
 23224               multiname = buildMultiname(bc.index);
 23225               object = pop();
 23226               push(store(new IR.ASDeleteProperty(region, state.store, object, multiname)));
 23227               break;
 23228             case 108:
 23229               object = pop();
 23230               push(getSlot(object, constant(bc.index), bc.ti));
 23231               break;
 23232             case 109:
 23233               value = pop();
 23234               object = pop();
 23235               setSlot(object, constant(bc.index), value, bc.ti);
 23236               break;
 23237             case 4:
 23238               multiname = buildMultiname(bc.index);
 23239               object = pop();
 23240               push(getSuper(savedScope(), object, multiname, bc.ti));
 23241               break;
 23242             case 5:
 23243               value = pop();
 23244               multiname = buildMultiname(bc.index);
 23245               object = pop();
 23246               setSuper(savedScope(), object, multiname, value, bc.ti);
 23247               break;
 23248             case 241:
 23249             case 240:
 23250               break;
 23251             case 64:
 23252               push(callPure(createFunctionCallee, null, [
 23253                 constant(methods[bc.index]),
 23254                 topScope(),
 23255                 constant(true)
 23256               ]));
 23257               break;
 23258             case 65:
 23259               args = popMany(bc.argCount);
 23260               object = pop();
 23261               callee = pop();
 23262               push(callCall(callee, object, args));
 23263               break;
 23264             case 70:
 23265             case 79:
 23266             case 76:
 23267               args = popMany(bc.argCount);
 23268               multiname = buildMultiname(bc.index);
 23269               object = pop();
 23270               value = callProperty(object, multiname, args, op === OP_callproplex, bc.ti);
 23271               if (op !== OP_callpropvoid) {
 23272                 push(value);
 23274               break;
 23275             case 69:
 23276             case 78:
 23277               multiname = buildMultiname(bc.index);
 23278               args = popMany(bc.argCount);
 23279               object = pop();
 23280               value = callSuper(savedScope(), object, multiname, args, bc.ti);
 23281               if (op !== OP_callsupervoid) {
 23282                 push(value);
 23284               break;
 23285             case 66:
 23286               args = popMany(bc.argCount);
 23287               object = pop();
 23288               push(store(new IR.ASNew(region, state.store, object, args)));
 23289               break;
 23290             case 73:
 23291               args = popMany(bc.argCount);
 23292               object = pop();
 23293               constructSuper(savedScope(), object, args, bc.ti);
 23294               break;
 23295             case 74:
 23296               args = popMany(bc.argCount);
 23297               multiname = buildMultiname(bc.index);
 23298               object = pop();
 23299               callee = getProperty(object, multiname, bc.ti, false);
 23300               push(store(new IR.ASNew(region, state.store, callee, args)));
 23301               break;
 23302             case 128:
 23303               if (bc.ti && bc.ti.noCoercionNeeded) {
 23304                 Counter.count('Compiler: NoCoercionNeeded');
 23305                 break;
 23306               } else {
 23307                 Counter.count('Compiler: CoercionNeeded');
 23309               value = pop();
 23310               push(coerce(multinames[bc.index], value));
 23311               break;
 23312             case 131:
 23313             case 115:
 23314               push(coerceInt(pop()));
 23315               break;
 23316             case 136:
 23317             case 116:
 23318               push(coerceUint(pop()));
 23319               break;
 23320             case 132:
 23321             case 117:
 23322               push(coerceNumber(pop()));
 23323               break;
 23324             case 129:
 23325             case 118:
 23326               push(coerceBoolean(pop()));
 23327               break;
 23328             case 120:
 23329               push(call(globalProperty('checkFilter'), null, [
 23330                 pop()
 23331               ]));
 23332               break;
 23333             case 130:
 23334               break;
 23335             case 133:
 23336               push(coerceString(pop()));
 23337               break;
 23338             case 112:
 23339               push(convertString(pop()));
 23340               break;
 23341             case 135:
 23342               type = pop();
 23343               if (c4AsTypeLate) {
 23344                 value = pop();
 23345                 push(call(globalProperty('asAsType'), null, [
 23346                   type,
 23347                   value
 23348                 ]));
 23350               break;
 23351             case 72:
 23352             case 71:
 23353               value = Undefined;
 23354               if (op === OP_returnvalue) {
 23355                 value = pop();
 23356                 if (methodInfo.returnType) {
 23357                   if (!(bc.ti && bc.ti.noCoercionNeeded)) {
 23358                     value = coerce(methodInfo.returnType, value);
 23362               stopPoints.push({
 23363                 region: region,
 23364                 store: state.store,
 23365                 value: value
 23366               });
 23367               buildReturnStop();
 23368               break;
 23369             case 30:
 23370             case 35:
 23371               index = pop();
 23372               object = pop();
 23373               push(new IR.CallProperty(region, state.store, object, constant(op === OP_nextname ? 'asNextName' : 'asNextValue'), [
 23374                 index
 23375               ], IR.Flags.PRISTINE));
 23376               break;
 23377             case 50:
 23378               var temp = call(globalProperty('asHasNext2'), null, [
 23379                   local[bc.object],
 23380                   local[bc.index]
 23381                 ]);
 23382               local[bc.object] = getJSProperty(temp, 'object');
 23383               push(local[bc.index] = getJSProperty(temp, 'index'));
 23384               break;
 23385             case 32:
 23386               push(Null);
 23387               break;
 23388             case 33:
 23389               push(Undefined);
 23390               break;
 23391             case 34:
 23392               notImplemented();
 23393               break;
 23394             case 36:
 23395               push(constant(bc.value));
 23396               break;
 23397             case 37:
 23398               push(constant(bc.value));
 23399               break;
 23400             case 44:
 23401               push(constant(strings[bc.index]));
 23402               break;
 23403             case 45:
 23404               push(constant(ints[bc.index]));
 23405               break;
 23406             case 46:
 23407               push(constant(uints[bc.index]));
 23408               break;
 23409             case 47:
 23410               push(constant(doubles[bc.index]));
 23411               break;
 23412             case 38:
 23413               push(constant(true));
 23414               break;
 23415             case 39:
 23416               push(constant(false));
 23417               break;
 23418             case 40:
 23419               push(constant(NaN));
 23420               break;
 23421             case 41:
 23422               pop();
 23423               break;
 23424             case 42:
 23425               value = shouldNotFloat(pop());
 23426               push(value);
 23427               push(value);
 23428               break;
 23429             case 43:
 23430               state.stack.push(pop(), pop());
 23431               break;
 23432             case 239:
 23433             case OP_debugline:
 23434             case OP_debugfile:
 23435               break;
 23436             case 12:
 23437               buildIfStops(negatedTruthyCondition(Operator.LT));
 23438               break;
 23439             case 24:
 23440               buildIfStops(truthyCondition(Operator.GE));
 23441               break;
 23442             case 13:
 23443               buildIfStops(negatedTruthyCondition(Operator.LE));
 23444               break;
 23445             case 23:
 23446               buildIfStops(truthyCondition(Operator.GT));
 23447               break;
 23448             case 14:
 23449               buildIfStops(negatedTruthyCondition(Operator.GT));
 23450               break;
 23451             case 22:
 23452               buildIfStops(truthyCondition(Operator.LE));
 23453               break;
 23454             case 15:
 23455               buildIfStops(negatedTruthyCondition(Operator.GE));
 23456               break;
 23457             case 21:
 23458               buildIfStops(truthyCondition(Operator.LT));
 23459               break;
 23460             case 16:
 23461               buildJumpStop();
 23462               break;
 23463             case 17:
 23464               buildIfStops(truthyCondition(Operator.TRUE));
 23465               break;
 23466             case 18:
 23467               buildIfStops(truthyCondition(Operator.FALSE));
 23468               break;
 23469             case 19:
 23470               buildIfStops(truthyCondition(Operator.EQ));
 23471               break;
 23472             case 20:
 23473               buildIfStops(truthyCondition(Operator.NE));
 23474               break;
 23475             case 25:
 23476               buildIfStops(truthyCondition(Operator.SEQ));
 23477               break;
 23478             case 26:
 23479               buildIfStops(truthyCondition(Operator.SNE));
 23480               break;
 23481             case 27:
 23482               buildSwitchStops(pop());
 23483               break;
 23484             case 150:
 23485               pushExpression(Operator.FALSE);
 23486               break;
 23487             case 151:
 23488               pushExpression(Operator.BITWISE_NOT);
 23489               break;
 23490             case 160:
 23491               right = pop();
 23492               left = pop();
 23493               if (typesAreEqual(left, right)) {
 23494                 operator = Operator.ADD;
 23495               } else if (Shumway.AVM2.Runtime.useAsAdd) {
 23496                 operator = Operator.AS_ADD;
 23497               } else {
 23498                 operator = Operator.ADD;
 23500               push(binary(operator, left, right));
 23501               break;
 23502             case 197:
 23503               pushExpression(Operator.ADD, true);
 23504               break;
 23505             case 161:
 23506               pushExpression(Operator.SUB);
 23507               break;
 23508             case 198:
 23509               pushExpression(Operator.SUB, true);
 23510               break;
 23511             case 162:
 23512               pushExpression(Operator.MUL);
 23513               break;
 23514             case 199:
 23515               pushExpression(Operator.MUL, true);
 23516               break;
 23517             case 163:
 23518               pushExpression(Operator.DIV);
 23519               break;
 23520             case 164:
 23521               pushExpression(Operator.MOD);
 23522               break;
 23523             case 165:
 23524               pushExpression(Operator.LSH);
 23525               break;
 23526             case 166:
 23527               pushExpression(Operator.RSH);
 23528               break;
 23529             case 167:
 23530               pushExpression(Operator.URSH);
 23531               break;
 23532             case 168:
 23533               pushExpression(Operator.AND);
 23534               break;
 23535             case 169:
 23536               pushExpression(Operator.OR);
 23537               break;
 23538             case 170:
 23539               pushExpression(Operator.XOR);
 23540               break;
 23541             case 171:
 23542               pushExpression(Operator.EQ);
 23543               break;
 23544             case 172:
 23545               pushExpression(Operator.SEQ);
 23546               break;
 23547             case 173:
 23548               pushExpression(Operator.LT);
 23549               break;
 23550             case 174:
 23551               pushExpression(Operator.LE);
 23552               break;
 23553             case 175:
 23554               pushExpression(Operator.GT);
 23555               break;
 23556             case 176:
 23557               pushExpression(Operator.GE);
 23558               break;
 23559             case 144:
 23560               pushExpression(Operator.NEG);
 23561               break;
 23562             case 196:
 23563               pushExpression(Operator.NEG, true);
 23564               break;
 23565             case 145:
 23566             case 192:
 23567             case 147:
 23568             case 193:
 23569               push(constant(1));
 23570               if (op === OP_increment || op === OP_decrement) {
 23571                 push(coerceNumber(pop()));
 23572               } else {
 23573                 push(coerceInt(pop()));
 23575               if (op === OP_increment || op === OP_increment_i) {
 23576                 pushExpression(Operator.ADD);
 23577               } else {
 23578                 pushExpression(Operator.SUB);
 23580               break;
 23581             case 146:
 23582             case 194:
 23583             case 148:
 23584             case 195:
 23585               push(constant(1));
 23586               if (op === OP_inclocal || op === OP_declocal) {
 23587                 push(coerceNumber(local[bc.index]));
 23588               } else {
 23589                 push(coerceInt(local[bc.index]));
 23591               if (op === OP_inclocal || op === OP_inclocal_i) {
 23592                 pushExpression(Operator.ADD);
 23593               } else {
 23594                 pushExpression(Operator.SUB);
 23596               popLocal(bc.index);
 23597               break;
 23598             case 177:
 23599               type = pop();
 23600               value = pop();
 23601               push(call(getJSProperty(type, 'isInstanceOf'), null, [
 23602                 value
 23603               ]));
 23604               break;
 23605             case 178:
 23606               value = pop();
 23607               multiname = buildMultiname(bc.index);
 23608               type = getProperty(findProperty(multiname, false), multiname);
 23609               push(call(globalProperty('asIsType'), null, [
 23610                 type,
 23611                 value
 23612               ]));
 23613               break;
 23614             case 179:
 23615               type = pop();
 23616               value = pop();
 23617               push(call(globalProperty('asIsType'), null, [
 23618                 type,
 23619                 value
 23620               ]));
 23621               break;
 23622             case 180:
 23623               object = pop();
 23624               value = pop();
 23625               multiname = new IR.ASMultiname(Undefined, value, 0);
 23626               push(store(new IR.ASHasProperty(region, state.store, object, multiname)));
 23627               break;
 23628             case 149:
 23629               push(call(globalProperty('asTypeOf'), null, [
 23630                 pop()
 23631               ]));
 23632               break;
 23633             case 8:
 23634               push(Undefined);
 23635               popLocal(bc.index);
 23636               break;
 23637             case 83:
 23638               args = popMany(bc.argCount);
 23639               type = pop();
 23640               callee = globalProperty('applyType');
 23641               push(call(callee, null, [
 23642                 domain,
 23643                 type,
 23644                 new NewArray(region, args)
 23645               ]));
 23646               break;
 23647             case 86:
 23648               args = popMany(bc.argCount);
 23649               push(new NewArray(region, args));
 23650               break;
 23651             case 85:
 23652               var properties = [];
 23653               for (var i = 0; i < bc.argCount; i++) {
 23654                 var value = pop();
 23655                 var key = pop();
 23656                 true;
 23657                 key = constant(Multiname.getPublicQualifiedName(key.value));
 23658                 properties.push(new KeyValuePair(key, value));
 23660               push(new NewObject(region, properties));
 23661               break;
 23662             case 87:
 23663               push(new IR.ASNewActivation(constant(methodInfo)));
 23664               break;
 23665             case 88:
 23666               callee = globalProperty('createClass');
 23667               push(call(callee, null, [
 23668                 constant(classes[bc.index]),
 23669                 pop(),
 23670                 topScope()
 23671               ]));
 23672               break;
 23673             default:
 23674               unexpected('Not Implemented: ' + bc);
 23676             if (op === OP_debug || op === OP_debugfile || op === OP_debugline) {
 23677               continue;
 23679             if (traceBuilder) {
 23680               writer.writeLn(('state: ' + state.toString()).padRight(' ', 100) + ' : ' + bci + ', ' + bc.toString(this.abc));
 23683           if (traceBuilder) {
 23684             writer.leave(('< state: ' + state.toString()).padRight(' ', 100));
 23686           if (!stops) {
 23687             stops = [];
 23688             if (bc.position + 1 <= bytecodes.length) {
 23689               stops.push({
 23690                 control: region,
 23691                 target: bytecodes[bc.position + 1],
 23692                 state: state
 23693               });
 23696           return stops;
 23698         var stop;
 23699         if (stopPoints.length > 1) {
 23700           var stopRegion = new Region(null);
 23701           var stopValuePhi = new Phi(stopRegion, null);
 23702           var stopStorePhi = new Phi(stopRegion, null);
 23703           stopPoints.forEach(function (stopPoint) {
 23704             stopRegion.predecessors.push(stopPoint.region);
 23705             stopValuePhi.pushValue(stopPoint.value);
 23706             stopStorePhi.pushValue(stopPoint.store);
 23707           });
 23708           stop = new Stop(stopRegion, stopStorePhi, stopValuePhi);
 23709         } else {
 23710           stop = new Stop(stopPoints[0].region, stopPoints[0].store, stopPoints[0].value);
 23712         return new DFG(stop);
 23713       };
 23714       return builder;
 23715     }();
 23716   function buildMethod(verifier, methodInfo, scope, hasDynamicScope) {
 23717     true;
 23718     true;
 23719     true;
 23720     Counter.count('Compiler: Compiled Methods');
 23721     Timer.start('Compiler');
 23722     Timer.start('Mark Loops');
 23723     methodInfo.analysis.markLoops();
 23724     Timer.stop();
 23725     if (Shumway.AVM2.Runtime.enableVerifier.value) {
 23726       Timer.start('Verify');
 23727       verifier.verifyMethod(methodInfo, scope);
 23728       Timer.stop();
 23730     var traceSource = c4TraceLevel.value > 0;
 23731     var traceIR = c4TraceLevel.value > 1;
 23732     Timer.start('Build IR');
 23733     Node.startNumbering();
 23734     var dfg = new Builder(methodInfo, scope, hasDynamicScope).buildGraph();
 23735     Timer.stop();
 23736     traceIR && dfg.trace(writer);
 23737     Timer.start('Build CFG');
 23738     var cfg = dfg.buildCFG();
 23739     Timer.stop();
 23740     Timer.start('Optimize Phis');
 23741     cfg.optimizePhis();
 23742     Timer.stop();
 23743     Timer.start('Schedule Nodes');
 23744     cfg.scheduleEarly();
 23745     Timer.stop();
 23746     traceIR && cfg.trace(writer);
 23747     Timer.start('Verify IR');
 23748     cfg.verify();
 23749     Timer.stop();
 23750     Timer.start('Allocate Variables');
 23751     cfg.allocateVariables();
 23752     Timer.stop();
 23753     Timer.start('Generate Source');
 23754     var result = Backend.generate(cfg, enableRegisterAllocator.value);
 23755     Timer.stop();
 23756     traceSource && writer.writeLn(result.body);
 23757     Node.stopNumbering();
 23758     Timer.stop();
 23759     return result;
 23761   exports.buildMethod = buildMethod;
 23762 }(typeof exports === 'undefined' ? Builder = {} : exports));
 23763 var Compiler = new (function () {
 23764     function constructor() {
 23765       this.verifier = new Verifier();
 23767     constructor.prototype.compileMethod = function (methodInfo, scope, hasDynamicScope) {
 23768       return Builder.buildMethod(this.verifier, methodInfo, scope, hasDynamicScope);
 23769     };
 23770     return constructor;
 23771   }())();
 23772 (function (exports) {
 23773   var Control = function () {
 23774       var SEQ = 1;
 23775       var LOOP = 2;
 23776       var IF = 3;
 23777       var CASE = 4;
 23778       var SWITCH = 5;
 23779       var LABEL_CASE = 6;
 23780       var LABEL_SWITCH = 7;
 23781       var EXIT = 8;
 23782       var BREAK = 9;
 23783       var CONTINUE = 10;
 23784       var TRY = 11;
 23785       var CATCH = 12;
 23786       function Seq(body) {
 23787         this.kind = SEQ;
 23788         this.body = body;
 23790       Seq.prototype = {
 23791         trace: function (writer) {
 23792           var body = this.body;
 23793           for (var i = 0, j = body.length; i < j; i++) {
 23794             body[i].trace(writer);
 23796         },
 23797         first: function () {
 23798           return this.body[0];
 23799         },
 23800         slice: function (begin, end) {
 23801           return new Seq(this.body.slice(begin, end));
 23803       };
 23804       function Loop(body) {
 23805         this.kind = LOOP;
 23806         this.body = body;
 23808       Loop.prototype = {
 23809         trace: function (writer) {
 23810           writer.enter('loop {');
 23811           this.body.trace(writer);
 23812           writer.leave('}');
 23814       };
 23815       function If(cond, then, els, nothingThrownLabel) {
 23816         this.kind = IF;
 23817         this.cond = cond;
 23818         this.then = then;
 23819         this.else = els;
 23820         this.negated = false;
 23821         this.nothingThrownLabel = nothingThrownLabel;
 23823       If.prototype = {
 23824         trace: function (writer) {
 23825           this.cond.trace(writer);
 23826           if (this.nothingThrownLabel) {
 23827             writer.enter('if (label is ' + this.nothingThrownLabel + ') {');
 23829           writer.enter('if' + (this.negated ? ' not' : '') + ' {');
 23830           this.then && this.then.trace(writer);
 23831           if (this.else) {
 23832             writer.outdent();
 23833             writer.enter('} else {');
 23834             this.else.trace(writer);
 23836           writer.leave('}');
 23837           if (this.nothingThrownLabel) {
 23838             writer.leave('}');
 23841       };
 23842       function Case(index, body) {
 23843         this.kind = CASE;
 23844         this.index = index;
 23845         this.body = body;
 23847       Case.prototype = {
 23848         trace: function (writer) {
 23849           if (this.index >= 0) {
 23850             writer.writeLn('case ' + this.index + ':');
 23851           } else {
 23852             writer.writeLn('default:');
 23854           writer.indent();
 23855           this.body && this.body.trace(writer);
 23856           writer.outdent();
 23858       };
 23859       function Switch(determinant, cases, nothingThrownLabel) {
 23860         this.kind = SWITCH;
 23861         this.determinant = determinant;
 23862         this.cases = cases;
 23863         this.nothingThrownLabel = nothingThrownLabel;
 23865       Switch.prototype = {
 23866         trace: function (writer) {
 23867           if (this.nothingThrownLabel) {
 23868             writer.enter('if (label is ' + this.nothingThrownLabel + ') {');
 23870           this.determinant.trace(writer);
 23871           writer.writeLn('switch {');
 23872           for (var i = 0, j = this.cases.length; i < j; i++) {
 23873             this.cases[i].trace(writer);
 23875           writer.writeLn('}');
 23876           if (this.nothingThrownLabel) {
 23877             writer.leave('}');
 23880       };
 23881       function LabelCase(labels, body) {
 23882         this.kind = LABEL_CASE;
 23883         this.labels = labels;
 23884         this.body = body;
 23886       LabelCase.prototype = {
 23887         trace: function (writer) {
 23888           writer.enter('if (label is ' + this.labels.join(' or ') + ') {');
 23889           this.body && this.body.trace(writer);
 23890           writer.leave('}');
 23892       };
 23893       function LabelSwitch(cases) {
 23894         var labelMap = {};
 23895         for (var i = 0, j = cases.length; i < j; i++) {
 23896           var c = cases[i];
 23897           if (!c.labels) {
 23898             print(c.toSource());
 23900           for (var k = 0, l = c.labels.length; k < l; k++) {
 23901             labelMap[c.labels[k]] = c;
 23904         this.kind = LABEL_SWITCH;
 23905         this.cases = cases;
 23906         this.labelMap = labelMap;
 23908       LabelSwitch.prototype = {
 23909         trace: function (writer) {
 23910           for (var i = 0, j = this.cases.length; i < j; i++) {
 23911             this.cases[i].trace(writer);
 23914       };
 23915       function Exit(label) {
 23916         this.kind = EXIT;
 23917         this.label = label;
 23919       Exit.prototype = {
 23920         trace: function (writer) {
 23921           writer.writeLn('label = ' + this.label);
 23923       };
 23924       function Break(label, head) {
 23925         this.kind = BREAK;
 23926         this.label = label;
 23927         this.head = head;
 23929       Break.prototype = {
 23930         trace: function (writer) {
 23931           this.label && writer.writeLn('label = ' + this.label);
 23932           writer.writeLn('break');
 23934       };
 23935       function Continue(label, head) {
 23936         this.kind = CONTINUE;
 23937         this.label = label;
 23938         this.head = head;
 23939         this.necessary = true;
 23941       Continue.prototype = {
 23942         trace: function (writer) {
 23943           this.label && writer.writeLn('label = ' + this.label);
 23944           this.necessary && writer.writeLn('continue');
 23946       };
 23947       function Try(body, catches) {
 23948         this.kind = TRY;
 23949         this.body = body;
 23950         this.catches = catches;
 23952       Try.prototype = {
 23953         trace: function (writer) {
 23954           writer.enter('try {');
 23955           this.body.trace(writer);
 23956           writer.writeLn('label = ' + this.nothingThrownLabel);
 23957           for (var i = 0, j = this.catches.length; i < j; i++) {
 23958             this.catches[i].trace(writer);
 23960           writer.leave('}');
 23962       };
 23963       function Catch(varName, typeName, body) {
 23964         this.kind = CATCH;
 23965         this.varName = varName;
 23966         this.typeName = typeName;
 23967         this.body = body;
 23969       Catch.prototype = {
 23970         trace: function (writer) {
 23971           writer.outdent();
 23972           writer.enter('} catch (' + (this.varName || 'e') + (this.typeName ? ' : ' + this.typeName : '') + ') {');
 23973           this.body.trace(writer);
 23975       };
 23976       return {
 23977         SEQ: SEQ,
 23978         LOOP: LOOP,
 23979         IF: IF,
 23980         CASE: CASE,
 23981         SWITCH: SWITCH,
 23982         LABEL_CASE: LABEL_CASE,
 23983         LABEL_SWITCH: LABEL_SWITCH,
 23984         EXIT: EXIT,
 23985         BREAK: BREAK,
 23986         CONTINUE: CONTINUE,
 23987         TRY: TRY,
 23988         CATCH: CATCH,
 23989         Seq: Seq,
 23990         Loop: Loop,
 23991         If: If,
 23992         Case: Case,
 23993         Switch: Switch,
 23994         LabelCase: LabelCase,
 23995         LabelSwitch: LabelSwitch,
 23996         Exit: Exit,
 23997         Break: Break,
 23998         Continue: Continue,
 23999         Try: Try,
 24000         Catch: Catch
 24001       };
 24002     }();
 24003   var Analysis = function () {
 24004       function blockSetClass(length, blockById) {
 24005         var BlockSet = BitSetFunctor(length);
 24006         var ADDRESS_BITS_PER_WORD = BlockSet.ADDRESS_BITS_PER_WORD;
 24007         var BITS_PER_WORD = BlockSet.BITS_PER_WORD;
 24008         var BIT_INDEX_MASK = BlockSet.BIT_INDEX_MASK;
 24009         BlockSet.singleton = function singleton(b) {
 24010           var bs = new BlockSet();
 24011           bs.set(b.id);
 24012           bs.count = 1;
 24013           bs.dirty = 0;
 24014           return bs;
 24015         };
 24016         BlockSet.fromBlocks = function fromArray(other) {
 24017           var bs = new BlockSet();
 24018           bs.setBlocks(other);
 24019           return bs;
 24020         };
 24021         var Bsp = BlockSet.prototype;
 24022         if (BlockSet.singleword) {
 24023           Bsp.forEachBlock = function forEach(fn) {
 24024             true;
 24025             var byId = blockById;
 24026             var word = this.bits;
 24027             if (word) {
 24028               for (var k = 0; k < BITS_PER_WORD; k++) {
 24029                 if (word & 1 << k) {
 24030                   fn(byId[k]);
 24034           };
 24035           Bsp.choose = function choose() {
 24036             var byId = blockById;
 24037             var word = this.bits;
 24038             if (word) {
 24039               for (var k = 0; k < BITS_PER_WORD; k++) {
 24040                 if (word & 1 << k) {
 24041                   return byId[k];
 24045           };
 24046           Bsp.members = function members() {
 24047             var byId = blockById;
 24048             var set = [];
 24049             var word = this.bits;
 24050             if (word) {
 24051               for (var k = 0; k < BITS_PER_WORD; k++) {
 24052                 if (word & 1 << k) {
 24053                   set.push(byId[k]);
 24057             return set;
 24058           };
 24059           Bsp.setBlocks = function setBlocks(bs) {
 24060             var bits = this.bits;
 24061             for (var i = 0, j = bs.length; i < j; i++) {
 24062               var id = bs[i].id;
 24063               bits |= 1 << (id & BIT_INDEX_MASK);
 24065             this.bits = bits;
 24066           };
 24067         } else {
 24068           Bsp.forEachBlock = function forEach(fn) {
 24069             true;
 24070             var byId = blockById;
 24071             var bits = this.bits;
 24072             for (var i = 0, j = bits.length; i < j; i++) {
 24073               var word = bits[i];
 24074               if (word) {
 24075                 for (var k = 0; k < BITS_PER_WORD; k++) {
 24076                   if (word & 1 << k) {
 24077                     fn(byId[i * BITS_PER_WORD + k]);
 24082           };
 24083           Bsp.choose = function choose() {
 24084             var byId = blockById;
 24085             var bits = this.bits;
 24086             for (var i = 0, j = bits.length; i < j; i++) {
 24087               var word = bits[i];
 24088               if (word) {
 24089                 for (var k = 0; k < BITS_PER_WORD; k++) {
 24090                   if (word & 1 << k) {
 24091                     return byId[i * BITS_PER_WORD + k];
 24096           };
 24097           Bsp.members = function members() {
 24098             var byId = blockById;
 24099             var set = [];
 24100             var bits = this.bits;
 24101             for (var i = 0, j = bits.length; i < j; i++) {
 24102               var word = bits[i];
 24103               if (word) {
 24104                 for (var k = 0; k < BITS_PER_WORD; k++) {
 24105                   if (word & 1 << k) {
 24106                     set.push(byId[i * BITS_PER_WORD + k]);
 24111             return set;
 24112           };
 24113           Bsp.setBlocks = function setBlocks(bs) {
 24114             var bits = this.bits;
 24115             for (var i = 0, j = bs.length; i < j; i++) {
 24116               var id = bs[i].id;
 24117               bits[id >> ADDRESS_BITS_PER_WORD] |= 1 << (id & BIT_INDEX_MASK);
 24119           };
 24121         return BlockSet;
 24123       function Analysis(cfg, options) {
 24124         this.options = options || {};
 24125         this.BlockSet = blockSetClass(cfg.blocks.length, cfg.blocks);
 24126         this.hasExceptions = false;
 24127         this.normalizeReachableBlocks(cfg.root);
 24129       Analysis.prototype = {
 24130         normalizeReachableBlocks: function normalizeReachableBlocks(root) {
 24131           true;
 24132           var ONCE = 1;
 24133           var BUNCH_OF_TIMES = 2;
 24134           var BlockSet = this.BlockSet;
 24135           var blocks = [];
 24136           var visited = {};
 24137           var ancestors = {};
 24138           var worklist = [
 24139               root
 24140             ];
 24141           var node;
 24142           ancestors[root.id] = true;
 24143           while (node = worklist.top()) {
 24144             if (visited[node.id]) {
 24145               if (visited[node.id] === ONCE) {
 24146                 visited[node.id] = BUNCH_OF_TIMES;
 24147                 blocks.push(node);
 24149               ancestors[node.id] = false;
 24150               worklist.pop();
 24151               continue;
 24153             visited[node.id] = ONCE;
 24154             ancestors[node.id] = true;
 24155             var successors = node.successors;
 24156             for (var i = 0, j = successors.length; i < j; i++) {
 24157               var s = successors[i];
 24158               if (ancestors[s.id]) {
 24159                 if (!node.spbacks) {
 24160                   node.spbacks = new BlockSet();
 24162                 node.spbacks.set(s.id);
 24164               !visited[s.id] && worklist.push(s);
 24167           this.blocks = blocks.reverse();
 24168         },
 24169         computeDominance: function computeDominance() {
 24170           function intersectDominators(doms, b1, b2) {
 24171             var finger1 = b1;
 24172             var finger2 = b2;
 24173             while (finger1 !== finger2) {
 24174               while (finger1 > finger2) {
 24175                 finger1 = doms[finger1];
 24177               while (finger2 > finger1) {
 24178                 finger2 = doms[finger2];
 24181             return finger1;
 24183           var blocks = this.blocks;
 24184           var n = blocks.length;
 24185           var doms = new Array(n);
 24186           doms[0] = 0;
 24187           var rpo = [];
 24188           for (var b = 0; b < n; b++) {
 24189             rpo[blocks[b].id] = b;
 24190             blocks[b].dominatees = [];
 24192           var changed = true;
 24193           while (changed) {
 24194             changed = false;
 24195             for (var b = 1; b < n; b++) {
 24196               var predecessors = blocks[b].predecessors;
 24197               var j = predecessors.length;
 24198               var newIdom = rpo[predecessors[0].id];
 24199               if (!(newIdom in doms)) {
 24200                 for (var i = 1; i < j; i++) {
 24201                   newIdom = rpo[predecessors[i].id];
 24202                   if (newIdom in doms) {
 24203                     break;
 24207               true;
 24208               for (var i = 0; i < j; i++) {
 24209                 var p = rpo[predecessors[i].id];
 24210                 if (p === newIdom) {
 24211                   continue;
 24213                 if (p in doms) {
 24214                   newIdom = intersectDominators(doms, p, newIdom);
 24217               if (doms[b] !== newIdom) {
 24218                 doms[b] = newIdom;
 24219                 changed = true;
 24223           blocks[0].dominator = blocks[0];
 24224           var block;
 24225           for (var b = 1; b < n; b++) {
 24226             block = blocks[b];
 24227             var idom = blocks[doms[b]];
 24228             block.dominator = idom;
 24229             idom.dominatees.push(block);
 24230             block.npredecessors = block.predecessors.length;
 24232           var worklist = [
 24233               blocks[0]
 24234             ];
 24235           blocks[0].level || (blocks[0].level = 0);
 24236           while (block = worklist.shift()) {
 24237             var dominatees = block.dominatees;
 24238             for (var i = 0, j = dominatees.length; i < j; i++) {
 24239               dominatees[i].level = block.level + 1;
 24241             worklist.push.apply(worklist, dominatees);
 24243         },
 24244         computeFrontiers: function computeFrontiers() {
 24245           var BlockSet = this.BlockSet;
 24246           var blocks = this.blocks;
 24247           for (var b = 0, n = blocks.length; b < n; b++) {
 24248             blocks[b].frontier = new BlockSet();
 24250           for (var b = 1, n = blocks.length; b < n; b++) {
 24251             var block = blocks[b];
 24252             var predecessors = block.predecessors;
 24253             if (predecessors.length >= 2) {
 24254               var idom = block.dominator;
 24255               for (var i = 0, j = predecessors.length; i < j; i++) {
 24256                 var runner = predecessors[i];
 24257                 while (runner !== idom) {
 24258                   runner.frontier.set(block.id);
 24259                   runner = runner.dominator;
 24264         },
 24265         analyzeControlFlow: function analyzeControlFlow() {
 24266           this.computeDominance();
 24267           this.analyzedControlFlow = true;
 24268           return true;
 24269         },
 24270         markLoops: function markLoops() {
 24271           if (!this.analyzedControlFlow && !this.analyzeControlFlow()) {
 24272             return false;
 24274           var BlockSet = this.BlockSet;
 24275           function findSCCs(root) {
 24276             var preorderId = 1;
 24277             var preorder = {};
 24278             var assigned = {};
 24279             var unconnectedNodes = [];
 24280             var pendingNodes = [];
 24281             var sccs = [];
 24282             var level = root.level + 1;
 24283             var worklist = [
 24284                 root
 24285               ];
 24286             var node;
 24287             var u, s;
 24288             while (node = worklist.top()) {
 24289               if (preorder[node.id]) {
 24290                 if (pendingNodes.peek() === node) {
 24291                   pendingNodes.pop();
 24292                   var scc = [];
 24293                   do {
 24294                     u = unconnectedNodes.pop();
 24295                     assigned[u.id] = true;
 24296                     scc.push(u);
 24297                   } while (u !== node);
 24298                   if (scc.length > 1 || u.spbacks && u.spbacks.get(u.id)) {
 24299                     sccs.push(scc);
 24302                 worklist.pop();
 24303                 continue;
 24305               preorder[node.id] = preorderId++;
 24306               unconnectedNodes.push(node);
 24307               pendingNodes.push(node);
 24308               var successors = node.successors;
 24309               for (var i = 0, j = successors.length; i < j; i++) {
 24310                 s = successors[i];
 24311                 if (s.level < level) {
 24312                   continue;
 24314                 var sid = s.id;
 24315                 if (!preorder[sid]) {
 24316                   worklist.push(s);
 24317                 } else if (!assigned[sid]) {
 24318                   while (preorder[pendingNodes.peek().id] > preorder[sid]) {
 24319                     pendingNodes.pop();
 24324             return sccs;
 24326           function findLoopHeads(blocks) {
 24327             var heads = new BlockSet();
 24328             for (var i = 0, j = blocks.length; i < j; i++) {
 24329               var block = blocks[i];
 24330               var spbacks = block.spbacks;
 24331               if (!spbacks) {
 24332                 continue;
 24334               var successors = block.successors;
 24335               for (var k = 0, l = successors.length; k < l; k++) {
 24336                 var s = successors[k];
 24337                 if (spbacks.get(s.id)) {
 24338                   heads.set(s.dominator.id);
 24342             return heads.members();
 24344           function LoopInfo(scc, loopId) {
 24345             var body = new BlockSet();
 24346             body.setBlocks(scc);
 24347             body.recount();
 24348             this.id = loopId;
 24349             this.body = body;
 24350             this.exit = new BlockSet();
 24351             this.save = {};
 24352             this.head = new BlockSet();
 24353             this.npredecessors = 0;
 24355           var heads = findLoopHeads(this.blocks);
 24356           if (heads.length <= 0) {
 24357             this.markedLoops = true;
 24358             return true;
 24360           var worklist = heads.sort(function (a, b) {
 24361               return a.level - b.level;
 24362             });
 24363           var loopId = 0;
 24364           for (var n = worklist.length - 1; n >= 0; n--) {
 24365             var top = worklist[n];
 24366             var sccs = findSCCs(top);
 24367             if (sccs.length === 0) {
 24368               continue;
 24370             for (var i = 0, j = sccs.length; i < j; i++) {
 24371               var scc = sccs[i];
 24372               var loop = new LoopInfo(scc, loopId++);
 24373               for (var k = 0, l = scc.length; k < l; k++) {
 24374                 var h = scc[k];
 24375                 if (h.level === top.level + 1 && !h.loop) {
 24376                   h.loop = loop;
 24377                   loop.head.set(h.id);
 24378                   var predecessors = h.predecessors;
 24379                   for (var pi = 0, pj = predecessors.length; pi < pj; pi++) {
 24380                     loop.body.get(predecessors[pi].id) && h.npredecessors--;
 24382                   loop.npredecessors += h.npredecessors;
 24385               for (var k = 0, l = scc.length; k < l; k++) {
 24386                 var h = scc[k];
 24387                 if (h.level === top.level + 1) {
 24388                   h.npredecessors = loop.npredecessors;
 24391               loop.head.recount();
 24394           this.markedLoops = true;
 24395           return true;
 24396         },
 24397         induceControlTree: function induceControlTree() {
 24398           var hasExceptions = this.hasExceptions;
 24399           var BlockSet = this.BlockSet;
 24400           function maybe(exit, save) {
 24401             exit.recount();
 24402             if (exit.count === 0) {
 24403               return null;
 24405             exit.save = save;
 24406             return exit;
 24408           var exceptionId = this.blocks.length;
 24409           function induce(head, exit, save, loop, inLoopHead, lookupSwitch, fallthrough) {
 24410             var v = [];
 24411             while (head) {
 24412               if (head.count > 1) {
 24413                 var exit2 = new BlockSet();
 24414                 var save2 = {};
 24415                 var cases = [];
 24416                 var heads = head.members();
 24417                 for (var i = 0, j = heads.length; i < j; i++) {
 24418                   var h = heads[i];
 24419                   var bid = h.id;
 24420                   var c;
 24421                   if (h.loop && head.contains(h.loop.head)) {
 24422                     var loop2 = h.loop;
 24423                     if (!loop2.induced) {
 24424                       var lheads = loop2.head.members();
 24425                       var lheadsave = 0;
 24426                       for (k = 0, l = lheads.length; k < l; k++) {
 24427                         lheadsave += head.save[lheads[k].id];
 24429                       if (h.npredecessors - lheadsave > 0) {
 24430                         h.npredecessors -= head.save[bid];
 24431                         h.save = head.save[bid];
 24432                         c = induce(h, exit2, save2, loop);
 24433                         cases.push(new Control.LabelCase([
 24434                           bid
 24435                         ], c));
 24436                       } else {
 24437                         for (k = 0, l = lheads.length; k < l; k++) {
 24438                           var lh = lheads[k];
 24439                           lh.npredecessors -= lheadsave;
 24440                           lh.save = lheadsave;
 24442                         c = induce(h, exit2, save2, loop);
 24443                         cases.push(new Control.LabelCase(loop2.head.toArray(), c));
 24444                         loop2.induced = true;
 24447                   } else {
 24448                     h.npredecessors -= head.save[bid];
 24449                     h.save = head.save[bid];
 24450                     c = induce(h, exit2, save2, loop);
 24451                     cases.push(new Control.LabelCase([
 24452                       bid
 24453                     ], c));
 24456                 var pruned = [];
 24457                 var k = 0;
 24458                 var c;
 24459                 for (var i = 0, j = cases.length; i < j; i++) {
 24460                   c = cases[i];
 24461                   var labels = c.labels;
 24462                   var lk = 0;
 24463                   for (var ln = 0, nlabels = labels.length; ln < nlabels; ln++) {
 24464                     var bid = labels[ln];
 24465                     if (exit2.get(bid) && heads[i].npredecessors - head.save[bid] > 0) {
 24466                       pruned.push(bid);
 24467                     } else {
 24468                       labels[lk++] = bid;
 24471                   labels.length = lk;
 24472                   if (labels.length > 0) {
 24473                     cases[k++] = c;
 24476                 cases.length = k;
 24477                 if (cases.length === 0) {
 24478                   for (var i = 0, j = pruned.length; i < j; i++) {
 24479                     var bid = pruned[i];
 24480                     save[bid] = (save[bid] || 0) + head.save[bid];
 24481                     exit.set(bid);
 24483                   break;
 24485                 v.push(new Control.LabelSwitch(cases));
 24486                 head = maybe(exit2, save2);
 24487                 continue;
 24489               var h, bid, c;
 24490               if (head.count === 1) {
 24491                 h = head.choose();
 24492                 bid = h.id;
 24493                 h.npredecessors -= head.save[bid];
 24494                 h.save = head.save[bid];
 24495               } else {
 24496                 h = head;
 24497                 bid = h.id;
 24499               if (inLoopHead) {
 24500                 inLoopHead = false;
 24501               } else {
 24502                 if (loop && !loop.body.get(bid)) {
 24503                   h.npredecessors += h.save;
 24504                   loop.exit.set(bid);
 24505                   loop.save[bid] = (loop.save[bid] || 0) + h.save;
 24506                   v.push(new Control.Break(bid, loop));
 24507                   break;
 24509                 if (loop && h.loop === loop) {
 24510                   h.npredecessors += h.save;
 24511                   v.push(new Control.Continue(bid, loop));
 24512                   break;
 24514                 if (h === fallthrough) {
 24515                   break;
 24517                 if (h.npredecessors > 0) {
 24518                   h.npredecessors += h.save;
 24519                   save[bid] = (save[bid] || 0) + h.save;
 24520                   exit.set(bid);
 24521                   v.push(lookupSwitch ? new Control.Break(bid, lookupSwitch) : new Control.Exit(bid));
 24522                   break;
 24524                 if (h.loop) {
 24525                   var l = h.loop;
 24526                   var body;
 24527                   if (l.head.count === 1) {
 24528                     body = induce(l.head.choose(), null, null, l, true);
 24529                   } else {
 24530                     var lcases = [];
 24531                     var lheads = l.head.members();
 24532                     for (var i = 0, j = lheads.length; i < j; i++) {
 24533                       var lh = lheads[i];
 24534                       var lbid = lh.id;
 24535                       var c = induce(lh, null, null, l, true);
 24536                       lcases.push(new Control.LabelCase([
 24537                         lbid
 24538                       ], c));
 24540                     body = new Control.LabelSwitch(lcases);
 24542                   v.push(new Control.Loop(body));
 24543                   head = maybe(l.exit, l.save);
 24544                   continue;
 24547               var sv;
 24548               var successors;
 24549               var exit2 = new BlockSet();
 24550               var save2 = {};
 24551               if (hasExceptions && h.hasCatches) {
 24552                 var allsuccessors = h.successors;
 24553                 var catchsuccessors = [];
 24554                 successors = [];
 24555                 for (var i = 0, j = allsuccessors.length; i < j; i++) {
 24556                   var s = allsuccessors[i];
 24557                   (s.exception ? catchsuccessors : successors).push(s);
 24559                 var catches = [];
 24560                 for (var i = 0, j = catchsuccessors.length; i < j; i++) {
 24561                   var t = catchsuccessors[i];
 24562                   t.npredecessors -= 1;
 24563                   t.save = 1;
 24564                   var c = induce(t, exit2, save2, loop);
 24565                   var ex = t.exception;
 24566                   catches.push(new Control.Catch(ex.varName, ex.typeName, c));
 24568                 sv = new Control.Try(h, catches);
 24569               } else {
 24570                 successors = h.successors;
 24571                 sv = h;
 24573               if (successors.length > 2) {
 24574                 var cases = [];
 24575                 var targets = successors;
 24576                 for (var i = targets.length - 1; i >= 0; i--) {
 24577                   var t = targets[i];
 24578                   t.npredecessors -= 1;
 24579                   t.save = 1;
 24580                   c = induce(t, exit2, save2, loop, null, h, targets[i + 1]);
 24581                   cases.unshift(new Control.Case(i, c));
 24583                 cases.top().index = undefined;
 24584                 if (hasExceptions && h.hasCatches) {
 24585                   sv.nothingThrownLabel = exceptionId;
 24586                   sv = new Control.Switch(sv, cases, exceptionId++);
 24587                 } else {
 24588                   sv = new Control.Switch(sv, cases);
 24590                 head = maybe(exit2, save2);
 24591               } else if (successors.length === 2) {
 24592                 var branch1 = h.hasFlippedSuccessors ? successors[1] : successors[0];
 24593                 var branch2 = h.hasFlippedSuccessors ? successors[0] : successors[1];
 24594                 branch1.npredecessors -= 1;
 24595                 branch1.save = 1;
 24596                 var c1 = induce(branch1, exit2, save2, loop);
 24597                 branch2.npredecessors -= 1;
 24598                 branch2.save = 1;
 24599                 var c2 = induce(branch2, exit2, save2, loop);
 24600                 if (hasExceptions && h.hasCatches) {
 24601                   sv.nothingThrownLabel = exceptionId;
 24602                   sv = new Control.If(sv, c1, c2, exceptionId++);
 24603                 } else {
 24604                   sv = new Control.If(sv, c1, c2);
 24606                 head = maybe(exit2, save2);
 24607               } else {
 24608                 c = successors[0];
 24609                 if (c) {
 24610                   if (hasExceptions && h.hasCatches) {
 24611                     sv.nothingThrownLabel = c.id;
 24612                     save2[c.id] = (save2[c.id] || 0) + 1;
 24613                     exit2.set(c.id);
 24614                     head = maybe(exit2, save2);
 24615                   } else {
 24616                     c.npredecessors -= 1;
 24617                     c.save = 1;
 24618                     head = c;
 24620                 } else {
 24621                   if (hasExceptions && h.hasCatches) {
 24622                     sv.nothingThrownLabel = -1;
 24623                     head = maybe(exit2, save2);
 24624                   } else {
 24625                     head = c;
 24629               v.push(sv);
 24631             if (v.length > 1) {
 24632               return new Control.Seq(v);
 24634             return v[0];
 24636           var root = this.blocks[0];
 24637           this.controlTree = induce(root, new BlockSet(), {});
 24638         },
 24639         restructureControlFlow: function restructureControlFlow() {
 24640           Timer.start('Restructure Control Flow');
 24641           if (!this.markedLoops && !this.markLoops()) {
 24642             Timer.stop();
 24643             return false;
 24645           this.induceControlTree();
 24646           this.restructuredControlFlow = true;
 24647           Timer.stop();
 24648           return true;
 24649         },
 24650         trace: function (writer) {
 24651           function bid(node) {
 24652             return node.id;
 24654           function traceBlock(block) {
 24655             if (!block.dominator) {
 24656               writer.enter('block unreachable {');
 24657             } else {
 24658               writer.enter('block ' + block.id + (block.successors.length > 0 ? ' -> ' + block.successors.map(bid).join(',') : '') + ' {');
 24659               writer.writeLn('npredecessors'.padRight(' ', 10) + block.npredecessors);
 24660               writer.writeLn('idom'.padRight(' ', 10) + block.dominator.id);
 24661               writer.writeLn('domcs'.padRight(' ', 10) + block.dominatees.map(bid).join(','));
 24662               if (block.frontier) {
 24663                 writer.writeLn('frontier'.padRight(' ', 10) + '{' + block.frontier.toArray().join(',') + '}');
 24665               writer.writeLn('level'.padRight(' ', 10) + block.level);
 24667             if (block.loop) {
 24668               writer.writeLn('loop'.padRight(' ', 10) + '{' + block.loop.body.toArray().join(',') + '}');
 24669               writer.writeLn('  id'.padRight(' ', 10) + block.loop.id);
 24670               writer.writeLn('  head'.padRight(' ', 10) + '{' + block.loop.head.toArray().join(',') + '}');
 24671               writer.writeLn('  exit'.padRight(' ', 10) + '{' + block.loop.exit.toArray().join(',') + '}');
 24672               writer.writeLn('  npredecessors'.padRight(' ', 10) + block.loop.npredecessors);
 24674             writer.writeLn('');
 24675             if (block.position >= 0) {
 24676               for (var bci = block.position; bci <= block.end.position; bci++) {
 24677                 writer.writeLn(('' + bci).padRight(' ', 5) + bytecodes[bci]);
 24679             } else {
 24680               writer.writeLn('abstract');
 24682             writer.leave('}');
 24684           var bytecodes = this.bytecodes;
 24685           writer.enter('analysis {');
 24686           writer.enter('cfg {');
 24687           this.blocks.forEach(traceBlock);
 24688           writer.leave('}');
 24689           if (this.controlTree) {
 24690             writer.enter('control-tree {');
 24691             this.controlTree.trace(writer);
 24692             writer.leave('}');
 24694           writer.leave('}');
 24695         },
 24696         traceCFG: makeVizTrace([
 24698             fn: function (n) {
 24699               return n.successors || [];
 24700             },
 24701             style: ''
 24703         ], [
 24705             fn: function (n) {
 24706               return n.predecessors || [];
 24707             },
 24708             style: ''
 24710         ]),
 24711         traceDJ: makeVizTrace([
 24713             fn: function (n) {
 24714               return n.dominatees || [];
 24715             },
 24716             style: 'style=dashed'
 24717           },
 24719             fn: function (n) {
 24720               var crosses = new this.BlockSet();
 24721               crosses.setBlocks(n.successors);
 24722               crosses.subtract(this.BlockSet.fromBlocks(n.dominatees));
 24723               n.spbacks && crosses.subtract(n.spbacks);
 24724               return crosses.members();
 24725             },
 24726             style: ''
 24727           },
 24729             fn: function (n) {
 24730               return n.spbacks ? n.spbacks.members() : [];
 24731             },
 24732             style: 'style=bold'
 24734         ], [
 24736             fn: function (n) {
 24737               return n.predecessors || [];
 24738             },
 24739             style: ''
 24741         ], function (idFn, writer) {
 24742           var root = this.bytecodes[0];
 24743           var worklist = [
 24744               root
 24745             ];
 24746           var n;
 24747           var level = root.level;
 24748           var currentLevel = [];
 24749           while (n = worklist.shift()) {
 24750             if (level != n.level) {
 24751               writer.writeLn('{rank=same; ' + currentLevel.map(function (n) {
 24752                 return 'block_' + idFn(n);
 24753               }).join(' ') + '}');
 24754               currentLevel.length = 0;
 24755               level = n.level;
 24757             currentLevel.push(n);
 24758             worklist.push.apply(worklist, n.dominatees);
 24760         })
 24761       };
 24762       function makeVizTrace(successorFns, predecessorFns, postHook) {
 24763         return function (writer, name, prefix) {
 24764           function idFn(n) {
 24765             return prefix + n.id;
 24767           var analysis = this;
 24768           function bindToThis(x) {
 24769             x.fn = x.fn.bind(analysis);
 24771           prefix = prefix || '';
 24772           var bytecodes = this.bytecodes;
 24773           if (!bytecodes) {
 24774             return;
 24776           successorFns.forEach(bindToThis);
 24777           predecessorFns.forEach(bindToThis);
 24778           writeGraphViz(writer, name.toString(), bytecodes[0], idFn, function (n) {
 24779             return n.successors || [];
 24780           }, successorFns, predecessorFns, function (n) {
 24781             var str = 'Block: ' + n.id + '\\l';
 24782             return str;
 24783           }, postHook && postHook.bind(this, idFn));
 24784         };
 24786       return Analysis;
 24787     }();
 24788   exports.Control = Control;
 24789   exports.analyze = function (cfg) {
 24790     var analysis = new Analysis(cfg);
 24791     analysis.restructureControlFlow();
 24792     return analysis.controlTree;
 24793   };
 24794 }(typeof exports === 'undefined' ? Looper = {} : exports));
 24795 (function (exports) {
 24796   var TRACE_REGISTER_ALLOCATOR = false;
 24797   var T = estransform;
 24798   var Node = T.Node;
 24799   var Identifier = T.Identifier;
 24800   var VariableDeclaration = T.VariableDeclaration;
 24801   var VariableDeclarator = T.VariableDeclarator;
 24802   var AssignmentExpression = T.AssignmentExpression;
 24803   var MemberExpression = T.MemberExpression;
 24804   var IfStatement = T.IfStatement;
 24805   var WhileStatement = T.WhileStatement;
 24806   var FunctionDeclaration = T.FunctionDeclaration;
 24807   var writer = new IndentingWriter();
 24808   var LinearScan = function () {
 24809       function Interval(id, start, end) {
 24810         this.id = id;
 24811         this.start = start;
 24812         this.end = end;
 24814       Interval.prototype.toString = function () {
 24815         return '[' + this.start + ',' + this.end + ']';
 24816       };
 24817       function linearScan(intervals, maxRegisters) {
 24818         this.intervals = intervals.slice(0);
 24819         this.maxRegisters = maxRegisters;
 24821       linearScan.prototype.allocate = function () {
 24822         var intervals = this.intervals;
 24823         this.intervals.sort(function (a, b) {
 24824           return a.start - b.start;
 24825         });
 24826         var active = new SortedList(function (a, b) {
 24827             return a.end - b.end;
 24828           });
 24829         var maxRegisters = this.maxRegisters;
 24830         var freeRegisters = [];
 24831         for (var i = maxRegisters - 1; i >= 0; i--) {
 24832           freeRegisters.push('R' + i);
 24834         intervals.forEach(function (i) {
 24835           expireOldIntervals(i);
 24836           if (active.length === maxRegisters) {
 24837             notImplemented('Cannot Spill');
 24838           } else {
 24839             i.register = freeRegisters.pop();
 24840             TRACE_REGISTER_ALLOCATOR && writer.writeLn('Allocate: ' + i + ' ' + i.id + ' -> ' + i.register);
 24841             active.push(i);
 24843         });
 24844         function expireOldIntervals(i) {
 24845           active.forEach(function (j) {
 24846             if (j.end >= i.start) {
 24847               return SortedList.RETURN;
 24849             freeRegisters.push(j.register);
 24850             TRACE_REGISTER_ALLOCATOR && writer.writeLn('Release: ' + j + ' -> ' + j.register);
 24851             return SortedList.DELETE;
 24852           });
 24854       };
 24855       linearScan.Interval = Interval;
 24856       return linearScan;
 24857     }();
 24858   function allocateRegisters(program) {
 24859     var scan = T.makePass('scan', 'scanNode');
 24860     var label = 0;
 24861     Node.prototype.scan = function (o) {
 24862       this.position = label++;
 24863       return scan.apply(this, o);
 24864     };
 24865     var variables = [];
 24866     var variableIndexMap = {};
 24867     var identifiers = [];
 24868     FunctionDeclaration.prototype.scan = function () {
 24869       this.params.forEach(function (identifier) {
 24870         if (!(identifier.name in variableIndexMap)) {
 24871           variableIndexMap[identifier.name] = variables.length;
 24872           variables.push(identifier.name);
 24874       });
 24875       this.body.scan();
 24876       return this;
 24877     };
 24878     VariableDeclarator.prototype.scan = function () {
 24879       this.position = label++;
 24880       if (!(this.id.name in variableIndexMap)) {
 24881         variableIndexMap[this.id.name] = variables.length;
 24882         variables.push(this.id.name);
 24884       return this;
 24885     };
 24886     AssignmentExpression.prototype.scan = function (o) {
 24887       this.left.scan(o);
 24888       this.right.scan(o);
 24889       this.position = label++;
 24890       return this;
 24891     };
 24892     WhileStatement.prototype.scan = function (o) {
 24893       this.position = label++;
 24894       this.test.scan(o);
 24895       this.body.scan(o);
 24896       this.afterPosition = label++;
 24897       return this;
 24898     };
 24899     program.scan();
 24900     TRACE_REGISTER_ALLOCATOR && writer.writeLn('Local Variables: ' + variables);
 24901     var Set = BitSetFunctor(variables.length);
 24902     var Range = BitSetFunctor(label);
 24903     var ranges = [];
 24904     for (var i = 0; i < variables.length; i++) {
 24905       ranges.push(new Range());
 24907     function fill(range) {
 24908       var start = -1;
 24909       for (var i = 0; i < range.length; i++) {
 24910         if (range.get(i)) {
 24911           start = i;
 24912           break;
 24915       for (var i = range.length - 1; i >= 0; i--) {
 24916         if (range.get(i)) {
 24917           end = i;
 24918           break;
 24921       for (var i = start; i < end; i++) {
 24922         range.set(i);
 24925     function getRange(range) {
 24926       var start = -1, end = -1;
 24927       for (var i = 0; i < range.length; i++) {
 24928         if (range.get(i)) {
 24929           start = i;
 24930           break;
 24933       for (var i = range.length - 1; i >= 0; i--) {
 24934         if (range.get(i)) {
 24935           end = i;
 24936           break;
 24939       return [
 24940         start,
 24941         end
 24942       ];
 24944     function use(set, name, position) {
 24945       var index = variableIndexMap[name];
 24946       ranges[index].set(position);
 24947       set.set(index);
 24949     function def(set, name, position) {
 24950       var index = variableIndexMap[name];
 24951       ranges[index].set(position);
 24952       set.clear(index);
 24954     Node.prototype.markLiveness = T.makePass('markLiveness', 'markLivenessNode', true);
 24955     Identifier.prototype.markLiveness = function (o) {
 24956       var name = this.name;
 24957       if (name === 'undefined') {
 24958         return this;
 24960       if (o && o.isProperty) {
 24961         return this;
 24963       if (!(name in variableIndexMap)) {
 24964         return this;
 24966       identifiers.push(this);
 24967       var live = o.live;
 24968       use(live, name, this.position);
 24969       return this;
 24970     };
 24971     VariableDeclarator.prototype.markLiveness = function (o) {
 24972       var live = o.live;
 24973       identifiers.push(this.id);
 24974       return this;
 24975     };
 24976     IfStatement.prototype.markLiveness = function (o) {
 24977       var a = o.live.clone();
 24978       var b = o.live.clone();
 24979       this.alternate && this.alternate.markLiveness({
 24980         live: a
 24981       });
 24982       this.consequent && this.consequent.markLiveness({
 24983         live: b
 24984       });
 24985       o.live.assign(a);
 24986       o.live._union(b);
 24987       this.test.markLiveness(o);
 24988       return this;
 24989     };
 24990     WhileStatement.prototype.markLiveness = function (o) {
 24991       var a = o.live.clone();
 24992       TRACE_REGISTER_ALLOCATOR && writer.writeLn('END OF LOOP: ' + a);
 24993       var afterPosition = this.afterPosition;
 24994       do {
 24995         var b = a.clone();
 24996         this.body.markLiveness({
 24997           live: a
 24998         });
 24999         this.test.markLiveness({
 25000           live: a
 25001         });
 25002         TRACE_REGISTER_ALLOCATOR && writer.writeLn('TOP OF LOOP: ' + a);
 25003         var iterate = !b.equals(a);
 25004         if (iterate) {
 25005           TRACE_REGISTER_ALLOCATOR && writer.writeLn('ITERATE');
 25006           a.forEach(function (i) {
 25007             ranges[i].set(afterPosition);
 25008           });
 25010       } while (iterate);
 25011       o.live.assign(a);
 25012       return this;
 25013     };
 25014     AssignmentExpression.prototype.markLiveness = function (o) {
 25015       this.right.markLiveness(o);
 25016       if (this.left instanceof Identifier) {
 25017         def(o.live, this.left.name, this.position);
 25018         identifiers.push(this.left);
 25019       } else {
 25020         this.left.markLiveness(o);
 25022       return this;
 25023     };
 25024     MemberExpression.prototype.markLiveness = function (o) {
 25025       if (this.computed || !(this.property instanceof Identifier)) {
 25026         this.property.markLiveness(o);
 25028       this.object.markLiveness(o);
 25029       return this;
 25030     };
 25031     program.markLiveness({
 25032       live: new Set()
 25033     });
 25034     var intervals = [];
 25035     for (var i = 0; i < ranges.length; i++) {
 25036       var r = getRange(ranges[i]);
 25037       intervals.push(new LinearScan.Interval(i, r[0], r[1]));
 25039     var allocator = new LinearScan(intervals, 1024);
 25040     allocator.allocate();
 25041     var map = createEmptyObject();
 25042     for (var i = 0; i < variables.length; i++) {
 25043       map[variables[i]] = intervals[i].register;
 25045     if (true) {
 25046       for (var i = 0; i < identifiers.length; i++) {
 25047         if (identifiers[i].patched) {
 25048           continue;
 25050         identifiers[i].name = map[identifiers[i].name];
 25051         identifiers[i].patched = true;
 25054     if (TRACE_REGISTER_ALLOCATOR) {
 25055       for (var i = 0; i < ranges.length; i++) {
 25056         fill(ranges[i]);
 25057         writer.writeLn(String(i).padLeft(' ', 3) + ' ' + variables[i].padRight(' ', 5) + ': ' + ranges[i].toBitString('=', ' ') + ' ' + intervals[i].register);
 25060     return program;
 25062   Transform.transform = function (program) {
 25063     allocateRegisters(program);
 25064   };
 25065 }(typeof exports === 'undefined' ? Transform = {} : exports));
 25066 (function (exports) {
 25067   var T = estransform;
 25068   var Literal = T.Literal;
 25069   var Identifier = T.Identifier;
 25070   var VariableDeclaration = T.VariableDeclaration;
 25071   var VariableDeclarator = T.VariableDeclarator;
 25072   var MemberExpression = T.MemberExpression;
 25073   var BinaryExpression = T.BinaryExpression;
 25074   var CallExpression = T.CallExpression;
 25075   var AssignmentExpression = T.AssignmentExpression;
 25076   var ExpressionStatement = T.ExpressionStatement;
 25077   var ReturnStatement = T.ReturnStatement;
 25078   var FunctionDeclaration = T.FunctionDeclaration;
 25079   var ConditionalExpression = T.ConditionalExpression;
 25080   var ObjectExpression = T.ObjectExpression;
 25081   var ArrayExpression = T.ArrayExpression;
 25082   var UnaryExpression = T.UnaryExpression;
 25083   var NewExpression = T.NewExpression;
 25084   var Property = T.Property;
 25085   var BlockStatement = T.BlockStatement;
 25086   var ThisExpression = T.ThisExpression;
 25087   var ThrowStatement = T.ThrowStatement;
 25088   var IfStatement = T.IfStatement;
 25089   var WhileStatement = T.WhileStatement;
 25090   var BreakStatement = T.BreakStatement;
 25091   var ContinueStatement = T.ContinueStatement;
 25092   var SwitchStatement = T.SwitchStatement;
 25093   var SwitchCase = T.SwitchCase;
 25094   var Block = IR.Block;
 25095   var Operator = IR.Operator;
 25096   var Projection = IR.Projection;
 25097   var Start = IR.Start;
 25098   var Control = Looper.Control;
 25099   var Variable = IR.Variable;
 25100   Control.Break.prototype.compile = function (cx, state) {
 25101     return cx.compileBreak(this, state);
 25102   };
 25103   Control.Continue.prototype.compile = function (cx, state) {
 25104     return cx.compileContinue(this, state);
 25105   };
 25106   Control.Exit.prototype.compile = function (cx, state) {
 25107     return cx.compileExit(this, state);
 25108   };
 25109   Control.LabelSwitch.prototype.compile = function (cx, state) {
 25110     return cx.compileLabelSwitch(this, state);
 25111   };
 25112   Control.Seq.prototype.compile = function (cx, state) {
 25113     return cx.compileSequence(this, state);
 25114   };
 25115   Block.prototype.compile = function (cx, state) {
 25116     return cx.compileBlock(this, state);
 25117   };
 25118   Control.Loop.prototype.compile = function (cx, state) {
 25119     return cx.compileLoop(this, state);
 25120   };
 25121   Control.Switch.prototype.compile = function (cx, state) {
 25122     return cx.compileSwitch(this, state);
 25123   };
 25124   Control.If.prototype.compile = function (cx, state) {
 25125     return cx.compileIf(this, state);
 25126   };
 25127   Control.Try.prototype.compile = function (cx, state) {
 25128     return cx.compileTry(this, state);
 25129   };
 25130   function constant(value) {
 25131     if (typeof value === 'string' || value === null || value === true || value === false) {
 25132       return new Literal(value);
 25133     } else if (value === undefined) {
 25134       return new Identifier('undefined');
 25135     } else if (typeof value === 'object' || typeof value === 'function') {
 25136       return new Identifier(objectConstantName(value));
 25137     } else if (typeof value === 'number' && isNaN(value)) {
 25138       return new Identifier('NaN');
 25139     } else if (value === Infinity) {
 25140       return new Identifier('Infinity');
 25141     } else if (value === -Infinity) {
 25142       return new UnaryExpression('-', new Identifier('Infinity'));
 25143     } else if (typeof value === 'number' && 1 / value < 0) {
 25144       return new UnaryExpression('-', new Literal(Math.abs(value)));
 25145     } else if (typeof value === 'number') {
 25146       return new Literal(value);
 25147     } else {
 25148       unexpected('Cannot emit constant for value: ', value);
 25151   function id(name) {
 25152     true;
 25153     return new Identifier(name);
 25155   function isIdentifierStart(c) {
 25156     return c === '$' || c === '_' || c === '\\' || c >= 'a' && c <= 'z' || c >= 'A' && c <= 'Z';
 25158   function isIdentifierPart(c) {
 25159     return c === '$' || c === '_' || c === '\\' || c >= 'a' && c <= 'z' || c >= 'A' && c <= 'Z' || c >= '0' && c <= '9';
 25161   function isIdentifierName(s) {
 25162     if (!isIdentifierStart(s[0])) {
 25163       return false;
 25165     for (var i = 1; i < s.length; i++) {
 25166       if (!isIdentifierPart(s[i])) {
 25167         return false;
 25170     return true;
 25172   function property(obj) {
 25173     for (var i = 1; i < arguments.length; i++) {
 25174       var x = arguments[i];
 25175       if (typeof x === 'string') {
 25176         if (isIdentifierName(x)) {
 25177           obj = new MemberExpression(obj, new Identifier(x), false);
 25178         } else {
 25179           obj = new MemberExpression(obj, new Literal(x), true);
 25181       } else if (x instanceof Literal && isIdentifierName(x.value)) {
 25182         obj = new MemberExpression(obj, new Identifier(x.value), false);
 25183       } else {
 25184         obj = new MemberExpression(obj, x, true);
 25187     return obj;
 25189   function call(callee, args) {
 25190     true;
 25191     true;
 25192     return new CallExpression(callee, args);
 25194   function callCall(callee, object, args) {
 25195     return call(property(callee, 'call'), [
 25196       object
 25197     ].concat(args));
 25199   function assignment(left, right) {
 25200     true;
 25201     return new AssignmentExpression(left, '=', right);
 25203   function variableDeclaration(declarations) {
 25204     return new VariableDeclaration('var', declarations);
 25206   function negate(node) {
 25207     if (node instanceof Constant) {
 25208       if (node.value === true || node.value === false) {
 25209         return constant(!node.value);
 25211     } else if (node instanceof Identifier) {
 25212       return new UnaryExpression(Operator.FALSE.name, node);
 25214     true;
 25215     var left = node instanceof BinaryExpression ? node.left : node.argument;
 25216     var right = node.right;
 25217     var operator = Operator.fromName(node.operator);
 25218     if (operator === Operator.EQ && right instanceof Literal && right.value === false) {
 25219       return left;
 25221     if (operator === Operator.FALSE) {
 25222       return left;
 25224     if (operator.not) {
 25225       if (node instanceof BinaryExpression) {
 25226         return new BinaryExpression(operator.not.name, left, right);
 25227       } else {
 25228         return new UnaryExpression(operator.not.name, left);
 25231     return new UnaryExpression(Operator.FALSE.name, node);
 25233   function Context() {
 25234     this.label = new Variable('$L');
 25235     this.variables = [];
 25236     this.parameters = [];
 25238   Context.prototype.useVariable = function (variable) {
 25239     true;
 25240     return this.variables.pushUnique(variable);
 25241   };
 25242   Context.prototype.useParameter = function (parameter) {
 25243     return this.parameters[parameter.index] = parameter;
 25244   };
 25245   Context.prototype.compileLabelBody = function compileLabelBody(node) {
 25246     var body = [];
 25247     if (node.label !== undefined) {
 25248       this.useVariable(this.label);
 25249       body.push(new ExpressionStatement(assignment(id(this.label.name), new Literal(node.label))));
 25251     return body;
 25252   };
 25253   Context.prototype.compileBreak = function compileBreak(node) {
 25254     var body = this.compileLabelBody(node);
 25255     body.push(new BreakStatement(null));
 25256     return new BlockStatement(body);
 25257   };
 25258   Context.prototype.compileContinue = function compileContinue(node) {
 25259     var body = this.compileLabelBody(node);
 25260     body.push(new ContinueStatement(null));
 25261     return new BlockStatement(body);
 25262   };
 25263   Context.prototype.compileExit = function compileExit(node) {
 25264     return new BlockStatement(this.compileLabelBody(node));
 25265   };
 25266   Context.prototype.compileIf = function compileIf(node) {
 25267     var cr = node.cond.compile(this);
 25268     var tr = null, er = null;
 25269     if (node.then) {
 25270       tr = node.then.compile(this);
 25272     if (node.else) {
 25273       er = node.else.compile(this);
 25275     var condition = compileValue(cr.end.predicate, this);
 25276     condition = node.negated ? negate(condition) : condition;
 25277     cr.body.push(new IfStatement(condition, tr || new BlockStatement([]), er || null));
 25278     return cr;
 25279   };
 25280   Context.prototype.compileSwitch = function compileSwitch(node) {
 25281     var dr = node.determinant.compile(this);
 25282     var cases = [];
 25283     node.cases.forEach(function (x) {
 25284       var br;
 25285       if (x.body) {
 25286         br = x.body.compile(this);
 25288       var test = typeof x.index === 'number' ? new Literal(x.index) : undefined;
 25289       cases.push(new SwitchCase(test, br ? [
 25290         br
 25291       ] : []));
 25292     }, this);
 25293     var determinant = compileValue(dr.end.determinant, this);
 25294     dr.body.push(new SwitchStatement(determinant, cases, false));
 25295     return dr;
 25296   };
 25297   Context.prototype.compileLabelSwitch = function compileLabelSwitch(node) {
 25298     var statement = null;
 25299     var labelName = id(this.label.name);
 25300     function compileLabelTest(labelID) {
 25301       true;
 25302       return new BinaryExpression('===', labelName, new Literal(labelID));
 25304     for (var i = node.cases.length - 1; i >= 0; i--) {
 25305       var c = node.cases[i];
 25306       var labels = c.labels;
 25307       var labelTest = compileLabelTest(labels[0]);
 25308       for (var j = 1; j < labels.length; j++) {
 25309         labelTest = new BinaryExpression('||', labelTest, compileLabelTest(labels[j]));
 25311       statement = new IfStatement(labelTest, c.body ? c.body.compile(this) : new BlockStatement(), statement);
 25313     return statement;
 25314   };
 25315   Context.prototype.compileLoop = function compileLoop(node) {
 25316     var br = node.body.compile(this);
 25317     return new WhileStatement(constant(true), br);
 25318   };
 25319   Context.prototype.compileSequence = function compileSequence(node) {
 25320     var cx = this;
 25321     var body = [];
 25322     node.body.forEach(function (x) {
 25323       var result = x.compile(cx);
 25324       if (result instanceof BlockStatement) {
 25325         body = body.concat(result.body);
 25326       } else {
 25327         body.push(result);
 25329     });
 25330     return new BlockStatement(body);
 25331   };
 25332   Context.prototype.compileBlock = function compileBlock(block) {
 25333     var body = [];
 25334     for (var i = 1; i < block.nodes.length - 1; i++) {
 25335       var node = block.nodes[i];
 25336       var statement;
 25337       var to;
 25338       var from;
 25339       if (node instanceof IR.Throw) {
 25340         statement = compileValue(node, this, true);
 25341       } else {
 25342         if (node instanceof IR.Move) {
 25343           to = id(node.to.name);
 25344           this.useVariable(node.to);
 25345           from = compileValue(node.from, this);
 25346         } else {
 25347           if (node.variable) {
 25348             to = id(node.variable.name);
 25349             this.useVariable(node.variable);
 25350           } else {
 25351             to = null;
 25353           from = compileValue(node, this, true);
 25355         if (to) {
 25356           statement = new ExpressionStatement(assignment(to, from));
 25357         } else {
 25358           statement = new ExpressionStatement(from);
 25361       body.push(statement);
 25363     var end = block.nodes.last();
 25364     if (end instanceof IR.Stop) {
 25365       body.push(new ReturnStatement(compileValue(end.argument, this)));
 25367     var result = new BlockStatement(body);
 25368     result.end = block.nodes.last();
 25369     true;
 25370     return result;
 25371   };
 25372   function compileValue(value, cx, noVariable) {
 25373     true;
 25374     true;
 25375     true;
 25376     true;
 25377     if (noVariable || !value.variable) {
 25378       var node = value.compile(cx);
 25379       return node;
 25381     true;
 25382     return id(value.variable.name);
 25384   function compileMultiname(name, cx) {
 25385     return [
 25386       compileValue(name.namespaces, cx),
 25387       compileValue(name.name, cx),
 25388       constant(name.flags)
 25389     ];
 25391   function isArray(array) {
 25392     return array instanceof Array;
 25394   function compileValues(values, cx) {
 25395     true;
 25396     return values.map(function (value) {
 25397       return compileValue(value, cx);
 25398     });
 25400   IR.Parameter.prototype.compile = function (cx) {
 25401     cx.useParameter(this);
 25402     return id(this.name);
 25403   };
 25404   IR.Constant.prototype.compile = function (cx) {
 25405     return constant(this.value);
 25406   };
 25407   IR.Variable.prototype.compile = function (cx) {
 25408     return id(this.name);
 25409   };
 25410   IR.Phi.prototype.compile = function (cx) {
 25411     true;
 25412     return compileValue(this.variable, cx);
 25413   };
 25414   IR.ASScope.prototype.compile = function (cx) {
 25415     var parent = compileValue(this.parent, cx);
 25416     var object = compileValue(this.object, cx);
 25417     var isWith = new Literal(this.isWith);
 25418     return new NewExpression(id('Scope'), [
 25419       parent,
 25420       object,
 25421       isWith
 25422     ]);
 25423   };
 25424   IR.ASFindProperty.prototype.compile = function (cx) {
 25425     var scope = compileValue(this.scope, cx);
 25426     var name = compileMultiname(this.name, cx);
 25427     var domain = compileValue(this.domain, cx);
 25428     var strict = new Literal(this.strict);
 25429     return call(property(scope, 'findScopeProperty'), name.concat([
 25430       domain,
 25431       strict
 25432     ]));
 25433   };
 25434   IR.ASGetProperty.prototype.compile = function (cx) {
 25435     var object = compileValue(this.object, cx);
 25436     if (this.flags & IR.Flags.INDEXED) {
 25437       true;
 25438       return call(property(object, 'asGetNumericProperty'), [
 25439         compileValue(this.name.name, cx)
 25440       ]);
 25441     } else if (this.flags & IR.Flags.RESOLVED) {
 25442       return call(property(object, 'asGetResolvedStringProperty'), [
 25443         compileValue(this.name, cx)
 25444       ]);
 25446     var name = compileMultiname(this.name, cx);
 25447     var isMethod = new Literal(this.flags & IR.Flags.IS_METHOD);
 25448     return call(property(object, 'asGetProperty'), name.concat(isMethod));
 25449   };
 25450   IR.ASGetSuper.prototype.compile = function (cx) {
 25451     var scope = compileValue(this.scope, cx);
 25452     var object = compileValue(this.object, cx);
 25453     var name = compileMultiname(this.name, cx);
 25454     return call(property(object, 'asGetSuper'), [
 25455       scope
 25456     ].concat(name));
 25457   };
 25458   IR.Latch.prototype.compile = function (cx) {
 25459     return new ConditionalExpression(compileValue(this.condition, cx), compileValue(this.left, cx), compileValue(this.right, cx));
 25460   };
 25461   IR.Unary.prototype.compile = function (cx) {
 25462     return new UnaryExpression(this.operator.name, compileValue(this.argument, cx));
 25463   };
 25464   IR.Copy.prototype.compile = function (cx) {
 25465     return compileValue(this.argument, cx);
 25466   };
 25467   IR.Binary.prototype.compile = function (cx) {
 25468     var left = compileValue(this.left, cx);
 25469     var right = compileValue(this.right, cx);
 25470     if (this.operator === Operator.AS_ADD) {
 25471       return call(id('asAdd'), [
 25472         left,
 25473         right
 25474       ]);
 25476     return new BinaryExpression(this.operator.name, left, right);
 25477   };
 25478   IR.CallProperty.prototype.compile = function (cx) {
 25479     var object = compileValue(this.object, cx);
 25480     var name = compileValue(this.name, cx);
 25481     var callee = property(object, name);
 25482     var args = this.args.map(function (arg) {
 25483         return compileValue(arg, cx);
 25484       });
 25485     if (this.flags & IR.Flags.PRISTINE) {
 25486       return call(callee, args);
 25487     } else {
 25488       return callCall(callee, object, args);
 25490   };
 25491   IR.ASCallProperty.prototype.compile = function (cx) {
 25492     var object = compileValue(this.object, cx);
 25493     var args = this.args.map(function (arg) {
 25494         return compileValue(arg, cx);
 25495       });
 25496     if (this.flags & IR.Flags.RESOLVED) {
 25497       return call(property(object, 'asCallResolvedStringProperty'), [
 25498         compileValue(this.name, cx),
 25499         new Literal(this.isLex),
 25500         new ArrayExpression(args)
 25501       ]);
 25503     var name = compileMultiname(this.name, cx);
 25504     return call(property(object, 'asCallProperty'), name.concat([
 25505       new Literal(this.isLex),
 25506       new ArrayExpression(args)
 25507     ]));
 25508   };
 25509   IR.ASCallSuper.prototype.compile = function (cx) {
 25510     var scope = compileValue(this.scope, cx);
 25511     var object = compileValue(this.object, cx);
 25512     var args = this.args.map(function (arg) {
 25513         return compileValue(arg, cx);
 25514       });
 25515     var name = compileMultiname(this.name, cx);
 25516     return call(property(object, 'asCallSuper'), [
 25517       scope
 25518     ].concat(name).concat(new ArrayExpression(args)));
 25519   };
 25520   IR.Call.prototype.compile = function (cx) {
 25521     var args = this.args.map(function (arg) {
 25522         return compileValue(arg, cx);
 25523       });
 25524     var callee = compileValue(this.callee, cx);
 25525     var object;
 25526     if (this.object) {
 25527       object = compileValue(this.object, cx);
 25528     } else {
 25529       object = new Literal(null);
 25531     if (false && this.pristine && (this.callee instanceof IR.GetProperty && this.callee.object === this.object) || this.object === null) {
 25532       return call(callee, args);
 25533     } else {
 25534       return callCall(callee, object, args);
 25536   };
 25537   IR.ASNew.prototype.compile = function (cx) {
 25538     var args = this.args.map(function (arg) {
 25539         return compileValue(arg, cx);
 25540       });
 25541     var callee = compileValue(this.callee, cx);
 25542     callee = property(callee, 'instanceConstructor');
 25543     return new NewExpression(callee, args);
 25544   };
 25545   IR.This.prototype.compile = function (cx) {
 25546     return new ThisExpression();
 25547   };
 25548   IR.Throw.prototype.compile = function (cx) {
 25549     var argument = compileValue(this.argument, cx);
 25550     return new ThrowStatement(argument);
 25551   };
 25552   IR.Arguments.prototype.compile = function (cx) {
 25553     return id('arguments');
 25554   };
 25555   IR.ASGlobal.prototype.compile = function (cx) {
 25556     var scope = compileValue(this.scope, cx);
 25557     return property(scope, 'global', 'object');
 25558   };
 25559   IR.ASSetProperty.prototype.compile = function (cx) {
 25560     var object = compileValue(this.object, cx);
 25561     var value = compileValue(this.value, cx);
 25562     if (this.flags & IR.Flags.INDEXED) {
 25563       return call(property(object, 'asSetNumericProperty'), [
 25564         compileValue(this.name.name, cx),
 25565         value
 25566       ]);
 25568     var name = compileMultiname(this.name, cx);
 25569     return call(property(object, 'asSetProperty'), name.concat(value));
 25570   };
 25571   IR.ASSetSuper.prototype.compile = function (cx) {
 25572     var scope = compileValue(this.scope, cx);
 25573     var object = compileValue(this.object, cx);
 25574     var name = compileMultiname(this.name, cx);
 25575     var value = compileValue(this.value, cx);
 25576     return call(property(object, 'asSetSuper'), [
 25577       scope
 25578     ].concat(name).concat([
 25579       value
 25580     ]));
 25581   };
 25582   IR.ASDeleteProperty.prototype.compile = function (cx) {
 25583     var object = compileValue(this.object, cx);
 25584     var name = compileMultiname(this.name, cx);
 25585     return call(property(object, 'asDeleteProperty'), name);
 25586   };
 25587   IR.ASHasProperty.prototype.compile = function (cx) {
 25588     var object = compileValue(this.object, cx);
 25589     var name = compileMultiname(this.name, cx);
 25590     return call(property(object, 'asHasProperty'), name);
 25591   };
 25592   IR.GlobalProperty.prototype.compile = function (cx) {
 25593     return id(this.name);
 25594   };
 25595   IR.GetProperty.prototype.compile = function (cx) {
 25596     var object = compileValue(this.object, cx);
 25597     var name = compileValue(this.name, cx);
 25598     return property(object, name);
 25599   };
 25600   IR.SetProperty.prototype.compile = function (cx) {
 25601     var object = compileValue(this.object, cx);
 25602     var name = compileValue(this.name, cx);
 25603     var value = compileValue(this.value, cx);
 25604     return assignment(property(object, name), value);
 25605   };
 25606   IR.ASGetDescendants.prototype.compile = function (cx) {
 25607     var object = compileValue(this.object, cx);
 25608     var name = compileValue(this.name, cx);
 25609     return call(id('getDescendants'), [
 25610       object,
 25611       name
 25612     ]);
 25613   };
 25614   IR.ASSetSlot.prototype.compile = function (cx) {
 25615     var object = compileValue(this.object, cx);
 25616     var name = compileValue(this.name, cx);
 25617     var value = compileValue(this.value, cx);
 25618     return call(id('asSetSlot'), [
 25619       object,
 25620       name,
 25621       value
 25622     ]);
 25623   };
 25624   IR.ASGetSlot.prototype.compile = function (cx) {
 25625     var object = compileValue(this.object, cx);
 25626     var name = compileValue(this.name, cx);
 25627     return call(id('asGetSlot'), [
 25628       object,
 25629       name
 25630     ]);
 25631   };
 25632   IR.Projection.prototype.compile = function (cx) {
 25633     true;
 25634     true;
 25635     return compileValue(this.argument.scope, cx);
 25636   };
 25637   IR.NewArray.prototype.compile = function (cx) {
 25638     return new ArrayExpression(compileValues(this.elements, cx));
 25639   };
 25640   IR.NewObject.prototype.compile = function (cx) {
 25641     var properties = this.properties.map(function (property) {
 25642         var key = compileValue(property.key, cx);
 25643         var value = compileValue(property.value, cx);
 25644         return new Property(key, value, 'init');
 25645       });
 25646     return new ObjectExpression(properties);
 25647   };
 25648   IR.ASNewActivation.prototype.compile = function (cx) {
 25649     var methodInfo = compileValue(this.methodInfo, cx);
 25650     return call(id('asCreateActivation'), [
 25651       methodInfo
 25652     ]);
 25653   };
 25654   IR.ASMultiname.prototype.compile = function (cx) {
 25655     var namespaces = compileValue(this.namespaces, cx);
 25656     var name = compileValue(this.name, cx);
 25657     return call(id('createName'), [
 25658       namespaces,
 25659       name
 25660     ]);
 25661   };
 25662   function generateSource(node) {
 25663     return escodegen.generate(node, {
 25664       base: '',
 25665       indent: '  ',
 25666       comment: true,
 25667       format: {
 25668         compact: false
 25670     });
 25672   function generate(cfg, useRegisterAllocator) {
 25673     Timer.start('Looper');
 25674     var root = Looper.analyze(cfg);
 25675     Timer.stop();
 25676     var writer = new IndentingWriter();
 25677     var cx = new Context();
 25678     Timer.start('Construct AST');
 25679     var code = root.compile(cx);
 25680     Timer.stop();
 25681     var parameters = [];
 25682     for (var i = 0; i < cx.parameters.length; i++) {
 25683       var name = cx.parameters[i] ? cx.parameters[i].name : '_' + i;
 25684       parameters.push(id(name));
 25686     if (cx.variables.length) {
 25687       Counter.count('Backend: Locals', cx.variables.length);
 25688       var variables = variableDeclaration(cx.variables.map(function (variable) {
 25689           return new VariableDeclarator(id(variable.name));
 25690         }));
 25691       code.body.unshift(variables);
 25693     var node = new FunctionDeclaration(id('fn'), parameters, code);
 25694     if (useRegisterAllocator) {
 25695       if (c4TraceLevel.value > 0) {
 25696         writer.writeLn('=== BEFORE ===============================');
 25697         writer.writeLn(generateSource(node));
 25698         writer.writeLn('=== TRANSFORMING =========================');
 25700       Transform.transform(node);
 25701       if (c4TraceLevel.value > 0) {
 25702         writer.writeLn('=== AFTER ================================');
 25703         writer.writeLn(generateSource(node));
 25704         writer.writeLn('==========================================');
 25706       var body = generateSource(code);
 25707       return {
 25708         parameters: parameters.map(function (p) {
 25709           return p.name;
 25710         }),
 25711         body: body
 25712       };
 25714     Timer.start('Serialize AST');
 25715     var source = generateSource(code);
 25716     Timer.stop();
 25717     return {
 25718       parameters: parameters.map(function (p) {
 25719         return p.name;
 25720       }),
 25721       body: source
 25722     };
 25724   Backend.generate = generate;
 25725 }(typeof exports === 'undefined' ? Backend = {} : exports));
 25726 var Shumway;
 25727 (function (Shumway) {
 25728   (function (AVM2) {
 25729     (function (Runtime) {
 25730       var Multiname = Shumway.AVM2.ABC.Multiname;
 25731       var Namespace = Shumway.AVM2.ABC.Namespace;
 25732       var ClassInfo = Shumway.AVM2.ABC.ClassInfo;
 25733       var InstanceInfo = Shumway.AVM2.ABC.InstanceInfo;
 25734       var Trait = Shumway.AVM2.ABC.Trait;
 25735       var IndentingWriter = Shumway.IndentingWriter;
 25736       var createMap = Shumway.ObjectUtilities.createMap;
 25737       var defineNonEnumerableGetterOrSetter = Shumway.ObjectUtilities.defineNonEnumerableGetterOrSetter;
 25738       var defineNonEnumerableProperty = Shumway.ObjectUtilities.defineNonEnumerableProperty;
 25739       var defineReadOnlyProperty = Shumway.ObjectUtilities.defineReadOnlyProperty;
 25740       var bindSafely = Shumway.FunctionUtilities.bindSafely;
 25741       var vmNextTrampolineId = 1;
 25742       var vmNextMemoizerId = 1;
 25743       function getMethodOverrideKey(methodInfo) {
 25744         var key;
 25745         if (methodInfo.holder instanceof ClassInfo) {
 25746           key = 'static ' + methodInfo.holder.instanceInfo.name.getOriginalName() + '::' + methodInfo.name.getOriginalName();
 25747         } else if (methodInfo.holder instanceof InstanceInfo) {
 25748           key = methodInfo.holder.name.getOriginalName() + '::' + methodInfo.name.getOriginalName();
 25749         } else {
 25750           key = methodInfo.name.getOriginalName();
 25752         return key;
 25754       Runtime.getMethodOverrideKey = getMethodOverrideKey;
 25755       function checkMethodOverrides(methodInfo) {
 25756         if (methodInfo.name) {
 25757           var key = getMethodOverrideKey(methodInfo);
 25758           if (key in Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES) {
 25759             Shumway.Debug.warning('Overriding Method: ' + key);
 25760             return Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES[key];
 25764       Runtime.checkMethodOverrides = checkMethodOverrides;
 25765       function makeTrampoline(forward, parameterLength, description) {
 25766         true;
 25767         return function trampolineContext() {
 25768           var target = null;
 25769           var trampoline = function execute() {
 25770             if (Shumway.AVM2.Runtime.traceExecution.value >= 3) {
 25771               log('Trampolining');
 25773             Counter.count('Executing Trampoline');
 25774             Shumway.AVM2.Runtime.traceCallExecution.value > 1 && callWriter.writeLn('Trampoline: ' + description);
 25775             if (!target) {
 25776               target = forward(trampoline);
 25777               true;
 25779             return target.apply(this, arguments);
 25780           };
 25781           trampoline.trigger = function trigger() {
 25782             Counter.count('Triggering Trampoline');
 25783             if (!target) {
 25784               target = forward(trampoline);
 25785               true;
 25787           };
 25788           trampoline.isTrampoline = true;
 25789           trampoline.debugName = 'Trampoline #' + vmNextTrampolineId++;
 25790           defineReadOnlyProperty(trampoline, Shumway.AVM2.Runtime.VM_LENGTH, parameterLength);
 25791           return trampoline;
 25792         }();
 25794       Runtime.makeTrampoline = makeTrampoline;
 25795       function makeMemoizer(qn, target) {
 25796         function memoizer() {
 25797           Counter.count('Runtime: Memoizing');
 25798           if (Shumway.AVM2.Runtime.traceExecution.value >= 3) {
 25799             log('Memoizing: ' + qn);
 25801           Shumway.AVM2.Runtime.traceCallExecution.value > 1 && callWriter.writeLn('Memoizing: ' + qn);
 25802           if (Shumway.AVM2.Runtime.isNativePrototype(this)) {
 25803             Counter.count('Runtime: Method Closures');
 25804             return bindSafely(target.value, this);
 25806           if (isTrampoline(target.value)) {
 25807             target.value.trigger();
 25809           true;
 25810           var mc = null;
 25811           if (Shumway.AVM2.Runtime.isClass(this)) {
 25812             Counter.count('Runtime: Static Method Closures');
 25813             mc = bindSafely(target.value, this);
 25814             defineReadOnlyProperty(this, qn, mc);
 25815             return mc;
 25817           if (Object.prototype.hasOwnProperty.call(this, qn)) {
 25818             var pd = Object.getOwnPropertyDescriptor(this, qn);
 25819             if (pd.get) {
 25820               Counter.count('Runtime: Method Closures');
 25821               return bindSafely(target.value, this);
 25823             Counter.count('Runtime: Unpatched Memoizer');
 25824             return this[qn];
 25826           mc = bindSafely(target.value, this);
 25827           mc.methodInfo = target.value.methodInfo;
 25828           defineReadOnlyProperty(mc, Multiname.getPublicQualifiedName('prototype'), null);
 25829           defineReadOnlyProperty(this, qn, mc);
 25830           return mc;
 25832         var m = memoizer;
 25833         Counter.count('Runtime: Memoizers');
 25834         m.isMemoizer = true;
 25835         m.debugName = 'Memoizer #' + vmNextMemoizerId++;
 25836         return m;
 25838       Runtime.makeMemoizer = makeMemoizer;
 25839       function isTrampoline(fn) {
 25840         true;
 25841         return fn.isTrampoline;
 25843       Runtime.isTrampoline = isTrampoline;
 25844       function isMemoizer(fn) {
 25845         true;
 25846         return fn.isMemoizer;
 25848       Runtime.isMemoizer = isMemoizer;
 25849     }(AVM2.Runtime || (AVM2.Runtime = {})));
 25850     var Runtime = AVM2.Runtime;
 25851   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 25852   var AVM2 = Shumway.AVM2;
 25853 }(Shumway || (Shumway = {})));
 25854 var __extends = this.__extends || function (d, b) {
 25855     for (var p in b)
 25856       if (b.hasOwnProperty(p))
 25857         d[p] = b[p];
 25858     function __() {
 25859       this.constructor = d;
 25861     __.prototype = b.prototype;
 25862     d.prototype = new __();
 25863   };
 25864 var Shumway;
 25865 (function (Shumway) {
 25866   (function (AVM2) {
 25867     (function (Runtime) {
 25868       var Multiname = Shumway.AVM2.ABC.Multiname;
 25869       var Namespace = Shumway.AVM2.ABC.Namespace;
 25870       var MethodInfo = Shumway.AVM2.ABC.MethodInfo;
 25871       var ClassInfo = Shumway.AVM2.ABC.ClassInfo;
 25872       var InstanceInfo = Shumway.AVM2.ABC.InstanceInfo;
 25873       var ScriptInfo = Shumway.AVM2.ABC.ScriptInfo;
 25874       var Trait = Shumway.AVM2.ABC.Trait;
 25875       var IndentingWriter = Shumway.IndentingWriter;
 25876       var hasOwnProperty = Shumway.ObjectUtilities.hasOwnProperty;
 25877       var createMap = Shumway.ObjectUtilities.createMap;
 25878       var cloneObject = Shumway.ObjectUtilities.cloneObject;
 25879       var copyProperties = Shumway.ObjectUtilities.copyProperties;
 25880       var createEmptyObject = Shumway.ObjectUtilities.createEmptyObject;
 25881       var bindSafely = Shumway.FunctionUtilities.bindSafely;
 25882       var defineNonEnumerableGetterOrSetter = Shumway.ObjectUtilities.defineNonEnumerableGetterOrSetter;
 25883       var defineNonEnumerableProperty = Shumway.ObjectUtilities.defineNonEnumerableProperty;
 25884       var defineReadOnlyProperty = Shumway.ObjectUtilities.defineReadOnlyProperty;
 25885       var defineNonEnumerableGetter = Shumway.ObjectUtilities.defineNonEnumerableGetter;
 25886       var makeForwardingGetter = Shumway.FunctionUtilities.makeForwardingGetter;
 25887       var makeForwardingSetter = Shumway.FunctionUtilities.makeForwardingSetter;
 25888       var Binding = function () {
 25889           function Binding(trait) {
 25890             this.trait = trait;
 25892           Binding.getKey = function (qn, trait) {
 25893             var key = qn;
 25894             if (trait.isGetter()) {
 25895               key = Binding.GET_PREFIX + qn;
 25896             } else if (trait.isSetter()) {
 25897               key = Binding.SET_PREFIX + qn;
 25899             return key;
 25900           };
 25901           Binding.prototype.toString = function () {
 25902             return String(this.trait);
 25903           };
 25904           Binding.SET_PREFIX = 'set ';
 25905           Binding.GET_PREFIX = 'get ';
 25906           Binding.KEY_PREFIX_LENGTH = 4;
 25907           return Binding;
 25908         }();
 25909       Runtime.Binding = Binding;
 25910       var SlotInfo = function () {
 25911           function SlotInfo(name, isConst, type, trait) {
 25912             this.name = name;
 25913             this.isConst = isConst;
 25914             this.type = type;
 25915             this.trait = trait;
 25917           return SlotInfo;
 25918         }();
 25919       Runtime.SlotInfo = SlotInfo;
 25920       var SlotInfoMap = function () {
 25921           function SlotInfoMap() {
 25922             this.byID = createMap();
 25923             this.byQN = createMap();
 25925           return SlotInfoMap;
 25926         }();
 25927       Runtime.SlotInfoMap = SlotInfoMap;
 25928       var Bindings = function () {
 25929           function Bindings() {
 25930             this.map = createMap();
 25931             this.slots = [];
 25932             this.nextSlotId = 1;
 25934           Bindings.prototype.assignNextSlot = function (trait) {
 25935             true;
 25936             true;
 25937             if (!trait.slotId) {
 25938               trait.slotId = this.nextSlotId++;
 25939             } else {
 25940               this.nextSlotId = trait.slotId + 1;
 25942             true;
 25943             this.slots[trait.slotId] = trait;
 25944           };
 25945           Bindings.prototype.trace = function (writer) {
 25946             writer.enter('Bindings');
 25947             for (var key in this.map) {
 25948               var binding = this.map[key];
 25949               writer.writeLn(binding.trait.kindName() + ': ' + key + ' -> ' + binding);
 25951             writer.leaveAndEnter('Slots');
 25952             writer.writeArray(this.slots);
 25953             writer.outdent();
 25954           };
 25955           Bindings.prototype.applyTo = function (domain, object) {
 25956             true;
 25957             true;
 25958             true;
 25959             defineNonEnumerableProperty(object, Shumway.AVM2.Runtime.VM_SLOTS, new SlotInfoMap());
 25960             defineNonEnumerableProperty(object, Shumway.AVM2.Runtime.VM_BINDINGS, []);
 25961             defineNonEnumerableProperty(object, Shumway.AVM2.Runtime.VM_OPEN_METHODS, createMap());
 25962             defineNonEnumerableProperty(object, 'bindings', this);
 25963             defineNonEnumerableProperty(object, 'resolutionMap', []);
 25964             traitsWriter && traitsWriter.greenLn('Applying Traits');
 25965             for (var key in this.map) {
 25966               var binding = this.map[key];
 25967               var trait = binding.trait;
 25968               var qn = Multiname.getQualifiedName(trait.name);
 25969               if (trait.isSlot() || trait.isConst() || trait.isClass()) {
 25970                 var defaultValue = undefined;
 25971                 if (trait.isSlot() || trait.isConst()) {
 25972                   if (trait.hasDefaultValue) {
 25973                     defaultValue = trait.value;
 25974                   } else if (trait.typeName) {
 25975                     defaultValue = domain.findClassInfo(trait.typeName).defaultValue;
 25978                 if (key !== qn) {
 25979                   traitsWriter && traitsWriter.yellowLn('Binding Trait: ' + key + ' -> ' + qn);
 25980                   defineNonEnumerableGetter(object, key, makeForwardingGetter(qn));
 25981                   object.asBindings.pushUnique(key);
 25982                 } else {
 25983                   traitsWriter && traitsWriter.greenLn('Applying Trait ' + trait.kindName() + ': ' + trait);
 25984                   defineNonEnumerableProperty(object, qn, defaultValue);
 25985                   object.asBindings.pushUnique(qn);
 25986                   var slotInfo = new SlotInfo(qn, trait.isConst(), trait.typeName ? domain.getProperty(trait.typeName, false, false) : null, trait);
 25987                   object.asSlots.byID[trait.slotId] = slotInfo;
 25988                   object.asSlots.byQN[qn] = slotInfo;
 25990               } else if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
 25991                 if (trait.isGetter() || trait.isSetter()) {
 25992                   key = key.substring(Binding.KEY_PREFIX_LENGTH);
 25994                 if (key !== qn) {
 25995                   traitsWriter && traitsWriter.yellowLn('Binding Trait: ' + key + ' -> ' + qn);
 25996                 } else {
 25997                   traitsWriter && traitsWriter.greenLn('Applying Trait ' + trait.kindName() + ': ' + trait);
 25999                 object.asBindings.pushUnique(key);
 26000                 if (this instanceof ScriptBindings) {
 26001                   Shumway.AVM2.Runtime.applyNonMemoizedMethodTrait(key, trait, object, binding.scope, binding.natives);
 26002                 } else {
 26003                   Shumway.AVM2.Runtime.applyMemoizedMethodTrait(key, trait, object, binding.scope, binding.natives);
 26007           };
 26008           return Bindings;
 26009         }();
 26010       Runtime.Bindings = Bindings;
 26011       var ActivationBindings = function (_super) {
 26012           __extends(ActivationBindings, _super);
 26013           function ActivationBindings(methodInfo) {
 26014             _super.call(this);
 26015             true;
 26016             this.methodInfo = methodInfo;
 26017             var traits = methodInfo.traits;
 26018             for (var i = 0; i < traits.length; i++) {
 26019               var trait = traits[i];
 26020               true;
 26021               var key = Multiname.getQualifiedName(trait.name);
 26022               this.map[key] = new Binding(trait);
 26023               this.assignNextSlot(trait);
 26026           return ActivationBindings;
 26027         }(Bindings);
 26028       Runtime.ActivationBindings = ActivationBindings;
 26029       var CatchBindings = function (_super) {
 26030           __extends(CatchBindings, _super);
 26031           function CatchBindings(scope, trait) {
 26032             _super.call(this);
 26033             var key = Multiname.getQualifiedName(trait.name);
 26034             this.map[key] = new Binding(trait);
 26035             true;
 26036             this.assignNextSlot(trait);
 26038           return CatchBindings;
 26039         }(Bindings);
 26040       Runtime.CatchBindings = CatchBindings;
 26041       var ScriptBindings = function (_super) {
 26042           __extends(ScriptBindings, _super);
 26043           function ScriptBindings(scriptInfo, scope) {
 26044             _super.call(this);
 26045             this.scope = scope;
 26046             this.scriptInfo = scriptInfo;
 26047             var traits = scriptInfo.traits;
 26048             for (var i = 0; i < traits.length; i++) {
 26049               var trait = traits[i];
 26050               var name = Multiname.getQualifiedName(trait.name);
 26051               var key = Binding.getKey(name, trait);
 26052               var binding = this.map[key] = new Binding(trait);
 26053               if (trait.isSlot() || trait.isConst() || trait.isClass()) {
 26054                 this.assignNextSlot(trait);
 26056               if (trait.isClass()) {
 26057                 if (trait.metadata && trait.metadata.native) {
 26058                   trait.classInfo.native = trait.metadata.native;
 26061               if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
 26062                 binding.scope = this.scope;
 26066           return ScriptBindings;
 26067         }(Bindings);
 26068       Runtime.ScriptBindings = ScriptBindings;
 26069       var ClassBindings = function (_super) {
 26070           __extends(ClassBindings, _super);
 26071           function ClassBindings(classInfo, scope, natives) {
 26072             _super.call(this);
 26073             this.scope = scope;
 26074             this.natives = natives;
 26075             this.classInfo = classInfo;
 26076             var traits = classInfo.traits;
 26077             for (var i = 0; i < traits.length; i++) {
 26078               var trait = traits[i];
 26079               var name = Multiname.getQualifiedName(trait.name);
 26080               var key = Binding.getKey(name, trait);
 26081               var binding = this.map[key] = new Binding(trait);
 26082               if (trait.isSlot() || trait.isConst()) {
 26083                 this.assignNextSlot(trait);
 26085               if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
 26086                 binding.scope = this.scope;
 26087                 binding.natives = this.natives;
 26091           return ClassBindings;
 26092         }(Bindings);
 26093       Runtime.ClassBindings = ClassBindings;
 26094       var InstanceBindings = function (_super) {
 26095           __extends(InstanceBindings, _super);
 26096           function InstanceBindings(parent, instanceInfo, scope, natives) {
 26097             _super.call(this);
 26098             this.scope = scope;
 26099             this.natives = natives;
 26100             this.parent = parent;
 26101             this.instanceInfo = instanceInfo;
 26102             this.implementedInterfaces = parent ? cloneObject(parent.implementedInterfaces) : createEmptyObject();
 26103             if (parent) {
 26104               this.slots = parent.slots.slice();
 26105               this.nextSlotId = parent.nextSlotId;
 26107             this.extend(parent);
 26109           InstanceBindings.prototype.extend = function (parent) {
 26110             var ii = this.instanceInfo, ib;
 26111             var map = this.map;
 26112             var name, key, trait, binding, protectedName, protectedKey;
 26113             if (parent) {
 26114               for (key in parent.map) {
 26115                 binding = parent.map[key];
 26116                 trait = binding.trait;
 26117                 map[key] = binding;
 26118                 if (trait.isProtected()) {
 26119                   protectedName = Multiname.getQualifiedName(new Multiname([
 26120                     ii.protectedNs
 26121                   ], trait.name.getName()));
 26122                   protectedKey = Binding.getKey(protectedName, trait);
 26123                   map[protectedKey] = binding;
 26127             function writeOrOverwriteBinding(object, key, binding) {
 26128               var trait = binding.trait;
 26129               var oldBinding = object[key];
 26130               if (oldBinding) {
 26131                 var oldTrait = oldBinding.trait;
 26132                 true;
 26133                 true;
 26134               } else {
 26135                 true;
 26137               object[key] = binding;
 26139             function overwriteProtectedBinding(object, key, binding) {
 26140               if (key in object) {
 26141                 object[key] = binding;
 26144             var traits = ii.traits;
 26145             for (var i = 0; i < traits.length; i++) {
 26146               trait = traits[i];
 26147               name = Multiname.getQualifiedName(trait.name);
 26148               key = Binding.getKey(name, trait);
 26149               binding = new Binding(trait);
 26150               writeOrOverwriteBinding(map, key, binding);
 26151               if (trait.isProtected()) {
 26152                 ib = this.parent;
 26153                 while (ib) {
 26154                   protectedName = Multiname.getQualifiedName(new Multiname([
 26155                     ib.instanceInfo.protectedNs
 26156                   ], trait.name.getName()));
 26157                   protectedKey = Binding.getKey(protectedName, trait);
 26158                   overwriteProtectedBinding(map, protectedKey, binding);
 26159                   ib = ib.parent;
 26162               if (trait.isSlot() || trait.isConst()) {
 26163                 this.assignNextSlot(trait);
 26165               if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
 26166                 binding.scope = this.scope;
 26167                 binding.natives = this.natives;
 26170             var domain = ii.abc.applicationDomain;
 26171             var interfaces = ii.interfaces;
 26172             for (var i = 0; i < interfaces.length; i++) {
 26173               var interface = domain.getProperty(interfaces[i], true, true);
 26174               true;
 26175               copyProperties(this.implementedInterfaces, interface.interfaceBindings.implementedInterfaces);
 26176               this.implementedInterfaces[Multiname.getQualifiedName(interface.name)] = interface;
 26178             for (var interfaceName in this.implementedInterfaces) {
 26179               var interface = this.implementedInterfaces[interfaceName];
 26180               ib = interface.interfaceBindings;
 26181               for (var interfaceKey in ib.map) {
 26182                 var interfaceBinding = ib.map[interfaceKey];
 26183                 if (ii.isInterface()) {
 26184                   map[interfaceKey] = interfaceBinding;
 26185                 } else {
 26186                   name = Multiname.getPublicQualifiedName(interfaceBinding.trait.name.getName());
 26187                   key = Binding.getKey(name, interfaceBinding.trait);
 26188                   map[interfaceKey] = map[key];
 26192           };
 26193           InstanceBindings.prototype.toString = function () {
 26194             return this.instanceInfo.toString();
 26195           };
 26196           return InstanceBindings;
 26197         }(Bindings);
 26198       Runtime.InstanceBindings = InstanceBindings;
 26199       var traitsWriter = null;
 26200     }(AVM2.Runtime || (AVM2.Runtime = {})));
 26201     var Runtime = AVM2.Runtime;
 26202   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 26203   var AVM2 = Shumway.AVM2;
 26204 }(Shumway || (Shumway = {})));
 26205 var Binding = Shumway.AVM2.Runtime.Binding;
 26206 var Bindings = Shumway.AVM2.Runtime.Bindings;
 26207 var ActivationBindings = Shumway.AVM2.Runtime.ActivationBindings;
 26208 var CatchBindings = Shumway.AVM2.Runtime.CatchBindings;
 26209 var ScriptBindings = Shumway.AVM2.Runtime.ScriptBindings;
 26210 var ClassBindings = Shumway.AVM2.Runtime.ClassBindings;
 26211 var InstanceBindings = Shumway.AVM2.Runtime.InstanceBindings;
 26212 var Shumway;
 26213 (function (Shumway) {
 26214   (function (AVM2) {
 26215     (function (Runtime) {
 26216       var Multiname = Shumway.AVM2.ABC.Multiname;
 26217       var Namespace = Shumway.AVM2.ABC.Namespace;
 26218       var MethodInfo = Shumway.AVM2.ABC.MethodInfo;
 26219       var ClassInfo = Shumway.AVM2.ABC.ClassInfo;
 26220       var InstanceInfo = Shumway.AVM2.ABC.InstanceInfo;
 26221       var InstanceBindings = Shumway.AVM2.Runtime.InstanceBindings;
 26222       var ClassBindings = Shumway.AVM2.Runtime.ClassBindings;
 26223       var defineNonEnumerableGetterOrSetter = Shumway.ObjectUtilities.defineNonEnumerableGetterOrSetter;
 26224       var defineNonEnumerableProperty = Shumway.ObjectUtilities.defineNonEnumerableProperty;
 26225       var defineReadOnlyProperty = Shumway.ObjectUtilities.defineReadOnlyProperty;
 26226       var defineNonEnumerableGetter = Shumway.ObjectUtilities.defineNonEnumerableGetter;
 26227       var createEmptyObject = Shumway.ObjectUtilities.createEmptyObject;
 26228       var toKeyValueArray = Shumway.ObjectUtilities.toKeyValueArray;
 26229       var boxValue = Shumway.ObjectUtilities.boxValue;
 26230       function makeCacheKey(namespaces, name, flags) {
 26231         if (!namespaces) {
 26232           return name;
 26233         } else if (namespaces.length > 1) {
 26234           return namespaces.runtimeId + '$' + name;
 26235         } else {
 26236           return namespaces[0].qualifiedName + '$' + name;
 26239       var Scope = function () {
 26240           function Scope(parent, object, isWith) {
 26241             if (typeof isWith === 'undefined') {
 26242               isWith = false;
 26244             this.parent = parent;
 26245             this.object = boxValue(object);
 26246             true;
 26247             this.global = parent ? parent.global : this;
 26248             this.isWith = isWith;
 26249             this.cache = createEmptyObject();
 26251           Scope.prototype.findDepth = function (object) {
 26252             var current = this;
 26253             var depth = 0;
 26254             while (current) {
 26255               if (current.object === object) {
 26256                 return depth;
 26258               depth++;
 26259               current = current.parent;
 26261             return -1;
 26262           };
 26263           Scope.prototype.getScopeObjects = function () {
 26264             var objects = [];
 26265             var current = this;
 26266             while (current) {
 26267               objects.unshift(current.object);
 26268               current = current.parent;
 26270             return objects;
 26271           };
 26272           Scope.prototype.findScopeProperty = function (namespaces, name, flags, domain, strict, scopeOnly) {
 26273             Counter.count('findScopeProperty');
 26274             var object;
 26275             var key = makeCacheKey(namespaces, name, flags);
 26276             if (!scopeOnly && (object = this.cache[key])) {
 26277               return object;
 26279             if (this.object.asHasProperty(namespaces, name, flags, true)) {
 26280               return this.isWith ? this.object : this.cache[key] = this.object;
 26282             if (this.parent) {
 26283               return this.cache[key] = this.parent.findScopeProperty(namespaces, name, flags, domain, strict, scopeOnly);
 26285             if (scopeOnly)
 26286               return null;
 26287             if (object = domain.findDomainProperty(new Multiname(namespaces, name, flags), strict, true)) {
 26288               return object;
 26290             if (strict) {
 26291               Shumway.Debug.unexpected('Cannot find property ' + name);
 26293             return this.global.object;
 26294           };
 26295           return Scope;
 26296         }();
 26297       Runtime.Scope = Scope;
 26298       function bindFreeMethodScope(methodInfo, scope) {
 26299         var fn = methodInfo.freeMethod;
 26300         if (methodInfo.lastBoundMethod && methodInfo.lastBoundMethod.scope === scope) {
 26301           return methodInfo.lastBoundMethod.boundMethod;
 26303         true;
 26304         var boundMethod;
 26305         var asGlobal = scope.global.object;
 26306         if (!methodInfo.hasOptional() && !methodInfo.needsArguments() && !methodInfo.needsRest()) {
 26307           switch (methodInfo.parameters.length) {
 26308           case 0:
 26309             boundMethod = function () {
 26310               return fn.call(this === jsGlobal ? asGlobal : this, scope);
 26311             };
 26312             break;
 26313           case 1:
 26314             boundMethod = function (x) {
 26315               return fn.call(this === jsGlobal ? asGlobal : this, scope, x);
 26316             };
 26317             break;
 26318           case 2:
 26319             boundMethod = function (x, y) {
 26320               return fn.call(this === jsGlobal ? asGlobal : this, scope, x, y);
 26321             };
 26322             break;
 26323           case 3:
 26324             boundMethod = function (x, y, z) {
 26325               return fn.call(this === jsGlobal ? asGlobal : this, scope, x, y, z);
 26326             };
 26327             break;
 26328           default:
 26329             break;
 26332         if (!boundMethod) {
 26333           Counter.count('Bind Scope - Slow Path');
 26334           boundMethod = function () {
 26335             Array.prototype.unshift.call(arguments, scope);
 26336             var global = this === jsGlobal ? scope.global.object : this;
 26337             return fn.apply(global, arguments);
 26338           };
 26340         boundMethod.methodInfo = methodInfo;
 26341         boundMethod.instanceConstructor = boundMethod;
 26342         methodInfo.lastBoundMethod = {
 26343           scope: scope,
 26344           boundMethod: boundMethod
 26345         };
 26346         return boundMethod;
 26348       Runtime.bindFreeMethodScope = bindFreeMethodScope;
 26349     }(AVM2.Runtime || (AVM2.Runtime = {})));
 26350     var Runtime = AVM2.Runtime;
 26351   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 26352   var AVM2 = Shumway.AVM2;
 26353 }(Shumway || (Shumway = {})));
 26354 var playerglobalLoadedPromise;
 26355 var playerglobal;
 26356 var Shumway;
 26357 (function (Shumway) {
 26358   (function (AVM2) {
 26359     (function (Runtime) {
 26360       var AbcFile = Shumway.AVM2.ABC.AbcFile;
 26361       var Multiname = Shumway.AVM2.ABC.Multiname;
 26362       var Namespace = Shumway.AVM2.ABC.Namespace;
 26363       var MethodInfo = Shumway.AVM2.ABC.MethodInfo;
 26364       var ClassInfo = Shumway.AVM2.ABC.ClassInfo;
 26365       var InstanceInfo = Shumway.AVM2.ABC.InstanceInfo;
 26366       var ScriptInfo = Shumway.AVM2.ABC.ScriptInfo;
 26367       var createEmptyObject = Shumway.ObjectUtilities.createEmptyObject;
 26368       var IndentingWriter = Shumway.IndentingWriter;
 26369       (function (EXECUTION_MODE) {
 26370         EXECUTION_MODE[EXECUTION_MODE['INTERPRET'] = 1] = 'INTERPRET';
 26371         EXECUTION_MODE[EXECUTION_MODE['COMPILE'] = 2] = 'COMPILE';
 26372       }(Runtime.EXECUTION_MODE || (Runtime.EXECUTION_MODE = {})));
 26373       var EXECUTION_MODE = Runtime.EXECUTION_MODE;
 26374       function createNewCompartment() {
 26375         return newGlobal('new-compartment');
 26377       function executeScript(script) {
 26378         var abc = script.abc;
 26379         true;
 26380         var global = new Shumway.AVM2.Runtime.Global(script);
 26381         if (abc.applicationDomain.allowNatives) {
 26382           global[Multiname.getPublicQualifiedName('unsafeJSNative')] = getNative;
 26384         script.executing = true;
 26385         var scope = new Shumway.AVM2.Runtime.Scope(null, script.global);
 26386         createFunction(script.init, scope).call(script.global, false);
 26387         script.executed = true;
 26389       Runtime.executeScript = executeScript;
 26390       function ensureScriptIsExecuted(script, reason) {
 26391         if (typeof reason === 'undefined') {
 26392           reason = '';
 26394         if (!script.executed && !script.executing) {
 26395           if (Shumway.AVM2.Runtime.traceExecution.value >= 2) {
 26396             log('Executing Script For: ' + reason);
 26398           executeScript(script);
 26401       Runtime.ensureScriptIsExecuted = ensureScriptIsExecuted;
 26402       (function (Glue) {
 26403         Glue[Glue['PUBLIC_PROPERTIES'] = 1] = 'PUBLIC_PROPERTIES';
 26404         Glue[Glue['PUBLIC_METHODS'] = 2] = 'PUBLIC_METHODS';
 26405         Glue[Glue['ALL'] = 1 | 2] = 'ALL';
 26406       }(Runtime.Glue || (Runtime.Glue = {})));
 26407       var Glue = Runtime.Glue;
 26408       function grabAbc(abcName) {
 26409         var entry = playerglobal.scripts[abcName];
 26410         if (!entry) {
 26411           return null;
 26413         var offset = entry.offset;
 26414         var length = entry.length;
 26415         return new AbcFile(new Uint8Array(playerglobal.abcs, offset, length), abcName);
 26417       function findDefiningAbc(mn) {
 26418         if (!playerglobal) {
 26419           return null;
 26421         for (var i = 0; i < mn.namespaces.length; i++) {
 26422           var name = mn.namespaces[i].uri + ':' + mn.name;
 26423           var abcName = playerglobal.map[name];
 26424           if (abcName) {
 26425             break;
 26428         if (abcName) {
 26429           return grabAbc(abcName);
 26431         return null;
 26433       function promiseFile(path, responseType) {
 26434         return new Promise(function (resolve, reject) {
 26435           var xhr = new XMLHttpRequest();
 26436           xhr.open('GET', path);
 26437           xhr.responseType = responseType;
 26438           xhr.onload = function () {
 26439             if (xhr.response) {
 26440               resolve(xhr.response);
 26441             } else {
 26442               reject('Unable to load ' + path + ': ' + xhr.statusText);
 26444           };
 26445           xhr.send();
 26446         });
 26448       var AVM2 = function () {
 26449           function AVM2(sysMode, appMode, loadAVM1) {
 26450             this.systemDomain = new ApplicationDomain(this, null, sysMode, true);
 26451             this.applicationDomain = new ApplicationDomain(this, this.systemDomain, appMode, false);
 26452             this.findDefiningAbc = findDefiningAbc;
 26453             this.loadAVM1 = loadAVM1;
 26454             this.isAVM1Loaded = false;
 26455             this.exception = {
 26456               value: undefined
 26457             };
 26458             this.exceptions = [];
 26460           AVM2.initialize = function (sysMode, appMode, loadAVM1) {
 26461             AVM2.instance = new AVM2(sysMode, appMode, loadAVM1);
 26462           };
 26463           AVM2.currentAbc = function () {
 26464             var caller = arguments.callee;
 26465             var maxDepth = 20;
 26466             var abc = null;
 26467             for (var i = 0; i < maxDepth && caller; i++) {
 26468               var mi = caller.methodInfo;
 26469               if (mi) {
 26470                 abc = mi.abc;
 26471                 break;
 26473               caller = caller.caller;
 26475             return abc;
 26476           };
 26477           AVM2.currentDomain = function () {
 26478             var abc = AVM2.currentAbc();
 26479             return abc.applicationDomain;
 26480           };
 26481           AVM2.isPlayerglobalLoaded = function () {
 26482             return !(!playerglobal);
 26483           };
 26484           AVM2.loadPlayerglobal = function (abcsPath, catalogPath) {
 26485             if (playerglobalLoadedPromise) {
 26486               return Promise.reject('Playerglobal is already loaded');
 26488             playerglobalLoadedPromise = Promise.all([
 26489               promiseFile(abcsPath, 'arraybuffer'),
 26490               promiseFile(catalogPath, 'json')
 26491             ]).then(function (result) {
 26492               playerglobal = {
 26493                 abcs: result[0],
 26494                 map: Object.create(null),
 26495                 scripts: Object.create(null)
 26496               };
 26497               var catalog = result[1];
 26498               for (var i = 0; i < catalog.length; i++) {
 26499                 var abc = catalog[i];
 26500                 playerglobal.scripts[abc.name] = abc;
 26501                 if (typeof abc.defs === 'string') {
 26502                   playerglobal.map[abc.defs] = abc.name;
 26503                 } else {
 26504                   for (var j = 0; j < abc.defs.length; j++) {
 26505                     var def = abc.defs[j];
 26506                     playerglobal.map[def] = abc.name;
 26510             }, function (e) {
 26511               console.error(e);
 26512             });
 26513             return playerglobalLoadedPromise;
 26514           };
 26515           AVM2.prototype.notifyConstruct = function (instanceConstructor, args) {
 26516           };
 26517           AVM2.getStackTrace = function () {
 26518             Shumway.Debug.notImplemented('getStackTrace');
 26519           };
 26520           return AVM2;
 26521         }();
 26522       Runtime.AVM2 = AVM2;
 26523       var ApplicationDomain = function () {
 26524           function ApplicationDomain(vm, base, mode, allowNatives) {
 26525             true;
 26526             true;
 26527             this.vm = vm;
 26528             this.abcs = [];
 26529             this.loadedAbcs = {};
 26530             this.loadedClasses = [];
 26531             this.classCache = createEmptyObject();
 26532             this.scriptCache = createEmptyObject();
 26533             this.classInfoCache = createEmptyObject();
 26534             this.base = base;
 26535             this.allowNatives = allowNatives;
 26536             this.mode = mode;
 26537             this.onMessage = new Callback();
 26538             if (base) {
 26539               this.system = base.system;
 26540             } else {
 26541               this.system = this;
 26544           ApplicationDomain.passthroughCallable = function (f) {
 26545             return {
 26546               call: function ($this) {
 26547                 Array.prototype.shift.call(arguments);
 26548                 return f.apply($this, arguments);
 26549               },
 26550               apply: function ($this, args) {
 26551                 return f.apply($this, args);
 26553             };
 26554           };
 26555           ApplicationDomain.coerceCallable = function (type) {
 26556             return {
 26557               call: function ($this, value) {
 26558                 return Shumway.AVM2.Runtime.asCoerce(type, value);
 26559               },
 26560               apply: function ($this, args) {
 26561                 return Shumway.AVM2.Runtime.asCoerce(type, args[0]);
 26563             };
 26564           };
 26565           ApplicationDomain.constructingCallable = function (instanceConstructor) {
 26566             return {
 26567               call: function (self) {
 26568                 return new (Function.bind.apply(instanceConstructor, arguments))();
 26569               },
 26570               apply: function (self, args) {
 26571                 return new (Function.bind.apply(instanceConstructor, [
 26572                   self
 26573                 ].concat(args)))();
 26575             };
 26576           };
 26577           ApplicationDomain.prototype.getType = function (multiname) {
 26578             return this.getProperty(multiname, true, true);
 26579           };
 26580           ApplicationDomain.prototype.getProperty = function (multiname, strict, execute) {
 26581             var resolved = this.findDefiningScript(multiname, execute);
 26582             if (resolved) {
 26583               if (!resolved.script.executing) {
 26584                 return undefined;
 26586               return resolved.script.global[Multiname.getQualifiedName(resolved.trait.name)];
 26588             if (strict) {
 26589               return Shumway.Debug.unexpected('Cannot find property ' + multiname);
 26591             return undefined;
 26592           };
 26593           ApplicationDomain.prototype.getClass = function (simpleName) {
 26594             var cache = this.classCache;
 26595             var c = cache[simpleName];
 26596             if (!c) {
 26597               c = cache[simpleName] = this.getProperty(Multiname.fromSimpleName(simpleName), true, true);
 26599             true;
 26600             return c;
 26601           };
 26602           ApplicationDomain.prototype.findClass = function (simpleName) {
 26603             if (simpleName in this.classCache) {
 26604               return true;
 26606             return this.findDomainProperty(Multiname.fromSimpleName(simpleName), false, true);
 26607           };
 26608           ApplicationDomain.prototype.findDomainProperty = function (multiname, strict, execute) {
 26609             if (Shumway.AVM2.Runtime.traceDomain.value) {
 26610               log('ApplicationDomain.findDomainProperty: ' + multiname);
 26612             var resolved = this.findDefiningScript(multiname, execute);
 26613             if (resolved) {
 26614               return resolved.script.global;
 26616             if (strict) {
 26617               return Shumway.Debug.unexpected('Cannot find property ' + multiname);
 26618             } else {
 26619               return undefined;
 26621             return undefined;
 26622           };
 26623           ApplicationDomain.prototype.findClassInfo = function (mn) {
 26624             var originalQn;
 26625             if (Multiname.isQName(mn)) {
 26626               originalQn = Multiname.getQualifiedName(mn);
 26627               var ci = this.classInfoCache[originalQn];
 26628               if (ci) {
 26629                 return ci;
 26631             } else {
 26632               var ci = this.classInfoCache[mn.runtimeId];
 26633               if (ci) {
 26634                 return ci;
 26637             if (this.base) {
 26638               ci = this.base.findClassInfo(mn);
 26639               if (ci) {
 26640                 return ci;
 26643             var abcs = this.abcs;
 26644             for (var i = 0; i < abcs.length; i++) {
 26645               var abc = abcs[i];
 26646               var scripts = abc.scripts;
 26647               for (var j = 0; j < scripts.length; j++) {
 26648                 var script = scripts[j];
 26649                 var traits = script.traits;
 26650                 for (var k = 0; k < traits.length; k++) {
 26651                   var trait = traits[k];
 26652                   if (trait.isClass()) {
 26653                     var traitName = Multiname.getQualifiedName(trait.name);
 26654                     if (originalQn) {
 26655                       if (traitName === originalQn) {
 26656                         return this.classInfoCache[originalQn] = trait.classInfo;
 26658                     } else {
 26659                       for (var m = 0, n = mn.namespaces.length; m < n; m++) {
 26660                         var qn = mn.getQName(m);
 26661                         if (traitName === Multiname.getQualifiedName(qn)) {
 26662                           return this.classInfoCache[qn] = trait.classInfo;
 26670             if (!this.base && this.vm.findDefiningAbc) {
 26671               var abc = this.vm.findDefiningAbc(mn);
 26672               if (abc !== null && !this.loadedAbcs[abc.name]) {
 26673                 this.loadedAbcs[abc.name] = true;
 26674                 this.loadAbc(abc);
 26675                 return this.findClassInfo(mn);
 26678             return undefined;
 26679           };
 26680           ApplicationDomain.prototype.installNative = function (name, func) {
 26681             natives[name] = function () {
 26682               return func;
 26683             };
 26684           };
 26685           ApplicationDomain.prototype.findDefiningScript = function (mn, execute) {
 26686             var resolved = this.scriptCache[mn.runtimeId];
 26687             if (resolved && (resolved.script.executed || !execute)) {
 26688               return resolved;
 26690             if (this.base) {
 26691               resolved = this.base.findDefiningScript(mn, execute);
 26692               if (resolved) {
 26693                 return resolved;
 26696             Counter.count('ApplicationDomain: findDefiningScript');
 26697             var abcs = this.abcs;
 26698             for (var i = 0; i < abcs.length; i++) {
 26699               var abc = abcs[i];
 26700               var scripts = abc.scripts;
 26701               for (var j = 0; j < scripts.length; j++) {
 26702                 var script = scripts[j];
 26703                 var traits = script.traits;
 26704                 if (mn instanceof Multiname) {
 26705                   for (var k = 0; k < traits.length; k++) {
 26706                     var trait = traits[k];
 26707                     if (mn.hasQName(trait.name)) {
 26708                       if (execute) {
 26709                         ensureScriptIsExecuted(script, String(trait.name));
 26711                       return this.scriptCache[mn.runtimeId] = {
 26712                         script: script,
 26713                         trait: trait
 26714                       };
 26717                 } else {
 26718                   Shumway.Debug.unexpected();
 26722             if (!this.base && this.vm.findDefiningAbc) {
 26723               var abc = this.vm.findDefiningAbc(mn);
 26724               if (abc !== null && !this.loadedAbcs[abc.name]) {
 26725                 this.loadedAbcs[abc.name] = true;
 26726                 this.loadAbc(abc);
 26727                 return this.findDefiningScript(mn, execute);
 26730             return undefined;
 26731           };
 26732           ApplicationDomain.prototype.compileAbc = function (abc, writer) {
 26733             compileAbc(abc, writer);
 26734           };
 26735           ApplicationDomain.prototype.executeAbc = function (abc) {
 26736             this.loadAbc(abc);
 26737             executeScript(abc.lastScript);
 26738           };
 26739           ApplicationDomain.prototype.loadAbc = function (abc) {
 26740             if (Shumway.AVM2.Runtime.traceExecution.value) {
 26741               log('Loading: ' + abc.name);
 26743             abc.applicationDomain = this;
 26744             GlobalMultinameResolver.loadAbc(abc);
 26745             this.abcs.push(abc);
 26746             if (!this.base) {
 26747               Type.initializeTypes(this);
 26749           };
 26750           ApplicationDomain.prototype.broadcastMessage = function (type, message, origin) {
 26751             if (debug) {
 26752               Timer.start('broadcast: ' + type);
 26754             try {
 26755               this.onMessage.notify1(type, {
 26756                 data: message,
 26757                 origin: origin,
 26758                 source: this
 26759               });
 26760             } catch (e) {
 26761               avm2.exceptions.push({
 26762                 source: type,
 26763                 message: e.message,
 26764                 stack: e.stack
 26765               });
 26766               throw e;
 26768             if (debug) {
 26769               Timer.stop();
 26771           };
 26772           ApplicationDomain.prototype.traceLoadedClasses = function (lastOnly) {
 26773             var writer = new IndentingWriter();
 26774             lastOnly || writer.enter('Loaded Classes And Interfaces');
 26775             var classes = lastOnly ? [
 26776                 this.loadedClasses.last()
 26777               ] : this.loadedClasses;
 26778             classes.forEach(function (cls) {
 26779               if (cls !== Shumway.AVM2.Runtime.Class) {
 26780                 cls.trace(writer);
 26782             });
 26783             lastOnly || writer.leave('');
 26784           };
 26785           return ApplicationDomain;
 26786         }();
 26787       Runtime.ApplicationDomain = ApplicationDomain;
 26788       var SecurityDomain = function () {
 26789           function SecurityDomain() {
 26790             this.compartment = createNewCompartment();
 26791             this.compartment.homePath = homePath;
 26792             this.compartment.release = true;
 26793             this.compartment.eval(snarf('compartment.js'));
 26795           SecurityDomain.prototype.initializeShell = function (sysMode, appMode) {
 26796             var compartment = this.compartment;
 26797             compartment.AVM2.initialize(sysMode, appMode);
 26798             compartment.AVM2.instance.systemDomain.executeAbc(compartment.grabAbc(homePath + 'src/avm2/generated/builtin/builtin.abc'));
 26799             compartment.AVM2.instance.systemDomain.executeAbc(compartment.grabAbc(homePath + 'src/avm2/generated/shell/shell.abc'));
 26800             this.systemDomain = compartment.AVM2.instance.systemDomain;
 26801             this.applicationDomain = compartment.AVM2.instance.applicationDomain;
 26802           };
 26803           return SecurityDomain;
 26804         }();
 26805       Runtime.SecurityDomain = SecurityDomain;
 26806     }(AVM2.Runtime || (AVM2.Runtime = {})));
 26807     var Runtime = AVM2.Runtime;
 26808   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 26809   var AVM2 = Shumway.AVM2;
 26810 }(Shumway || (Shumway = {})));
 26811 var Glue = Shumway.AVM2.Runtime.Glue;
 26812 var ApplicationDomain = Shumway.AVM2.Runtime.ApplicationDomain;
 26813 var AVM2 = Shumway.AVM2.Runtime.AVM2;
 26814 var EXECUTION_MODE = Shumway.AVM2.Runtime.EXECUTION_MODE;
 26815 var ApplicationDomain = Shumway.AVM2.Runtime.ApplicationDomain;
 26816 var AVM2 = Shumway.AVM2.Runtime.AVM2;
 26817 var EXECUTION_MODE = Shumway.AVM2.Runtime.EXECUTION_MODE;
 26818 var Shumway;
 26819 (function (Shumway) {
 26820   (function (AVM2) {
 26821     (function (Runtime) {
 26822       var Multiname = Shumway.AVM2.ABC.Multiname;
 26823       var Namespace = Shumway.AVM2.ABC.Namespace;
 26824       var ClassInfo = Shumway.AVM2.ABC.ClassInfo;
 26825       var InstanceInfo = Shumway.AVM2.ABC.InstanceInfo;
 26826       var InstanceBindings = Shumway.AVM2.Runtime.InstanceBindings;
 26827       var ClassBindings = Shumway.AVM2.Runtime.ClassBindings;
 26828       var defineNonEnumerableGetterOrSetter = Shumway.ObjectUtilities.defineNonEnumerableGetterOrSetter;
 26829       var defineNonEnumerableProperty = Shumway.ObjectUtilities.defineNonEnumerableProperty;
 26830       var defineReadOnlyProperty = Shumway.ObjectUtilities.defineReadOnlyProperty;
 26831       var defineNonEnumerableGetter = Shumway.ObjectUtilities.defineNonEnumerableGetter;
 26832       var createEmptyObject = Shumway.ObjectUtilities.createEmptyObject;
 26833       var toKeyValueArray = Shumway.ObjectUtilities.toKeyValueArray;
 26834       var Interface = function () {
 26835           function Interface(classInfo) {
 26836             var ii = classInfo.instanceInfo;
 26837             true;
 26838             this.name = ii.name;
 26839             this.classInfo = classInfo;
 26841           Interface.createInterface = function (classInfo) {
 26842             var ii = classInfo.instanceInfo;
 26843             true;
 26844             if (Shumway.AVM2.Runtime.traceExecution.value) {
 26845               var str = 'Creating Interface ' + ii.name;
 26846               if (ii.interfaces.length) {
 26847                 str += ' implements ' + ii.interfaces.map(function (name) {
 26848                   return name.getName();
 26849                 }).join(', ');
 26851               log(str);
 26853             var cls = new Interface(classInfo);
 26854             cls.interfaceBindings = new InstanceBindings(null, ii, null, null);
 26855             return cls;
 26856           };
 26857           Interface.prototype.toString = function () {
 26858             return '[interface ' + this.name + ']';
 26859           };
 26860           Interface.prototype.isInstance = function (value) {
 26861             if (value === null || typeof value !== 'object') {
 26862               return false;
 26864             true;
 26865             var qualifiedName = Multiname.getQualifiedName(this.name);
 26866             return value.class.implementedInterfaces[qualifiedName] !== undefined;
 26867           };
 26868           Interface.prototype.trace = function (writer) {
 26869             writer.enter('interface ' + this.name.getName());
 26870             writer.enter('interfaceBindings: ');
 26871             this.interfaceBindings.trace(writer);
 26872             writer.outdent();
 26873             writer.outdent();
 26874             writer.leave('}');
 26875           };
 26876           Interface.prototype.call = function (self, x) {
 26877             return x;
 26878           };
 26879           Interface.prototype.apply = function (self, args) {
 26880             return args[0];
 26881           };
 26882           return Interface;
 26883         }();
 26884       Runtime.Interface = Interface;
 26885       function setDefaultProperties(cls) {
 26886         defineNonEnumerableProperty(cls.dynamicPrototype, Multiname.getPublicQualifiedName('constructor'), cls);
 26887         defineReadOnlyProperty(cls.traitsPrototype, 'class', cls);
 26888         defineReadOnlyProperty(cls.instanceConstructor, 'class', cls);
 26890       Runtime.setDefaultProperties = setDefaultProperties;
 26891       var Class = function () {
 26892           function Class(name, instanceConstructor, callable) {
 26893             this.debugName = name;
 26894             if (instanceConstructor) {
 26895               true;
 26896               this.instanceConstructor = instanceConstructor;
 26897               this.instanceConstructorNoInitialize = instanceConstructor;
 26898               this.hasInitialize = 0;
 26899               this.instanceConstructor.class = this;
 26901             if (!callable) {
 26902               callable = Shumway.AVM2.Runtime.ApplicationDomain.coerceCallable(this);
 26903             } else if (callable === Shumway.AVM2.Runtime.ApplicationDomain.coerceCallable) {
 26904               callable = Shumway.AVM2.Runtime.ApplicationDomain.coerceCallable(this);
 26906             defineNonEnumerableProperty(this, 'call', callable.call);
 26907             defineNonEnumerableProperty(this, 'apply', callable.apply);
 26909           Class.createClass = function (classInfo, baseClass, scope) {
 26910             var ci = classInfo;
 26911             var ii = ci.instanceInfo;
 26912             var domain = ci.abc.applicationDomain;
 26913             var className = Multiname.getName(ii.name);
 26914             var isNativeClass = ci.native;
 26915             if (isNativeClass) {
 26916               var buildClass = getNative(ci.native.cls);
 26917               if (!buildClass) {
 26918                 Shumway.Debug.unexpected('No native for ' + ci.native.cls);
 26920               if (!baseClass) {
 26921                 scope = new Scope(scope, Class);
 26924             var classScope = new Scope(scope, null);
 26925             var instanceConstructor = createFunction(ii.init, classScope, false);
 26926             var cls;
 26927             if (isNativeClass) {
 26928               cls = buildClass(domain, classScope, instanceConstructor, baseClass);
 26929             } else {
 26930               cls = new Class(className, instanceConstructor);
 26932             cls.className = className;
 26933             cls.classInfo = classInfo;
 26934             cls.scope = classScope;
 26935             classScope.object = cls;
 26936             var classNatives;
 26937             var instanceNatives;
 26938             if (isNativeClass) {
 26939               if (cls.native) {
 26940                 classNatives = cls.native.static;
 26941                 instanceNatives = cls.native.instance;
 26943             } else {
 26944               cls.extend(baseClass);
 26946             cls.classBindings = new ClassBindings(classInfo, classScope, classNatives);
 26947             cls.classBindings.applyTo(domain, cls);
 26948             defineReadOnlyProperty(cls, Shumway.AVM2.Runtime.VM_IS_CLASS, true);
 26949             cls.instanceBindings = new InstanceBindings(baseClass ? baseClass.instanceBindings : null, ii, classScope, instanceNatives);
 26950             if (cls.instanceConstructor) {
 26951               cls.instanceBindings.applyTo(domain, cls.traitsPrototype);
 26953             cls.implementedInterfaces = cls.instanceBindings.implementedInterfaces;
 26954             return cls;
 26955           };
 26956           Class.prototype.setSymbol = function (props) {
 26957             this.instanceConstructor.prototype.symbol = props;
 26958           };
 26959           Class.prototype.getSymbol = function () {
 26960             return this.instanceConstructor.prototype.symbol;
 26961           };
 26962           Class.prototype.initializeInstance = function (obj) {
 26963             var c = this;
 26964             var initializes = [];
 26965             while (c) {
 26966               if (c.hasInitialize & Class.OWN_INITIALIZE) {
 26967                 initializes.push(c.instanceConstructor.prototype.initialize);
 26969               c = c.baseClass;
 26971             var s;
 26972             while (s = initializes.pop()) {
 26973               s.call(obj);
 26975             Counter.count('Initialize Instance ' + obj.class);
 26976           };
 26977           Class.prototype.createInstance = function (args) {
 26978             var o = Object.create(this.instanceConstructor.prototype);
 26979             this.instanceConstructor.apply(o, args);
 26980             return o;
 26981           };
 26982           Class.prototype.createAsSymbol = function (props) {
 26983             var o = Object.create(this.instanceConstructor.prototype);
 26984             if (o.symbol) {
 26985               var symbol = Object.create(o.symbol);
 26986               for (var prop in props) {
 26987                 symbol[prop] = props[prop];
 26989               o.symbol = symbol;
 26990             } else {
 26991               o.symbol = props;
 26993             return o;
 26994           };
 26995           Class.prototype.extendNative = function (baseClass, native) {
 26996             this.baseClass = baseClass;
 26997             this.dynamicPrototype = Object.getPrototypeOf(native.prototype);
 26998             this.instanceConstructor.prototype = this.traitsPrototype = native.prototype;
 26999             setDefaultProperties(this);
 27000           };
 27001           Class.prototype.extendWrapper = function (baseClass, wrapper) {
 27002             true;
 27003             this.baseClass = baseClass;
 27004             this.dynamicPrototype = Object.create(baseClass.dynamicPrototype);
 27005             var traitsPrototype = Object.create(this.dynamicPrototype, Shumway.ObjectUtilities.getOwnPropertyDescriptors(wrapper.prototype));
 27006             this.instanceConstructor.prototype = this.traitsPrototype = traitsPrototype;
 27007             setDefaultProperties(this);
 27008           };
 27009           Class.prototype.extendBuiltin = function (baseClass) {
 27010             true;
 27011             this.baseClass = baseClass;
 27012             this.dynamicPrototype = this.traitsPrototype = this.instanceConstructor.prototype;
 27013             setDefaultProperties(this);
 27014           };
 27015           Class.prototype.extend = function (baseClass) {
 27016             true;
 27017             this.baseClass = baseClass;
 27018             this.dynamicPrototype = Object.create(baseClass.dynamicPrototype);
 27019             if (baseClass.hasInitialize) {
 27020               var instanceConstructorNoInitialize = this.instanceConstructor;
 27021               var self = this;
 27022               this.instanceConstructor = function () {
 27023                 self.initializeInstance(this);
 27024                 instanceConstructorNoInitialize.apply(this, arguments);
 27025               };
 27026               defineReadOnlyProperty(this.instanceConstructor, 'class', instanceConstructorNoInitialize.class);
 27027               this.hasInitialize |= Class.SUPER_INITIALIZE;
 27029             this.instanceConstructor.prototype = this.traitsPrototype = Object.create(this.dynamicPrototype);
 27030             setDefaultProperties(this);
 27031           };
 27032           Class.prototype.setDefaultProperties = function () {
 27033             setDefaultProperties(this);
 27034           };
 27035           Class.prototype.link = function (definition) {
 27036             true;
 27037             true;
 27038             if (definition.initialize) {
 27039               if (!this.hasInitialize) {
 27040                 var instanceConstructorNoInitialize = this.instanceConstructor;
 27041                 var self = this;
 27042                 this.instanceConstructor = function () {
 27043                   self.initializeInstance(this);
 27044                   instanceConstructorNoInitialize.apply(this, arguments);
 27045                 };
 27046                 defineReadOnlyProperty(this.instanceConstructor, 'class', instanceConstructorNoInitialize.class);
 27047                 this.instanceConstructor.prototype = instanceConstructorNoInitialize.prototype;
 27049               this.hasInitialize |= Class.OWN_INITIALIZE;
 27051             var dynamicPrototype = this.dynamicPrototype;
 27052             var keys = Object.keys(definition);
 27053             for (var i = 0; i < keys.length; i++) {
 27054               var propertyName = keys[i];
 27055               Object.defineProperty(dynamicPrototype, propertyName, Object.getOwnPropertyDescriptor(definition, propertyName));
 27057             function glueProperties(obj, properties) {
 27058               var keys = Object.keys(properties);
 27059               for (var i = 0; i < keys.length; i++) {
 27060                 var propertyName = keys[i];
 27061                 var propertyGlue = properties[propertyName];
 27062                 var propertySimpleName;
 27063                 var glueOpenMethod = false;
 27064                 if (propertyGlue.indexOf('open ') >= 0) {
 27065                   propertySimpleName = propertyGlue.substring(5);
 27066                   glueOpenMethod = true;
 27067                 } else {
 27068                   propertySimpleName = propertyGlue;
 27070                 true;
 27071                 var qn = Multiname.getQualifiedName(Multiname.fromSimpleName(propertySimpleName));
 27072                 if (glueOpenMethod) {
 27073                   qn = Shumway.AVM2.Runtime.VM_OPEN_METHOD_PREFIX + qn;
 27075                 true;
 27076                 var descriptor = Object.getOwnPropertyDescriptor(obj, qn);
 27077                 if (descriptor && descriptor.get) {
 27078                   Object.defineProperty(obj, propertyName, descriptor);
 27079                 } else {
 27080                   Object.defineProperty(obj, propertyName, {
 27081                     get: new Function('', 'return this.' + qn),
 27082                     set: new Function('v', 'this.' + qn + ' = v')
 27083                   });
 27087             function generatePropertiesFromTraits(traits) {
 27088               var properties = createEmptyObject();
 27089               traits.forEach(function (trait) {
 27090                 var ns = trait.name.getNamespace();
 27091                 if (!ns.isPublic()) {
 27092                   return;
 27094                 properties[trait.name.getName()] = (trait.isMethod() ? 'open ' : '') + 'public ' + trait.name.getName();
 27095               });
 27096               return properties;
 27098             var glue = definition.__glue__;
 27099             if (!glue) {
 27100               return;
 27102             if (glue.script) {
 27103               if (glue.script.instance) {
 27104                 if (Shumway.isNumber(glue.script.instance)) {
 27105                   true;
 27106                   glueProperties(dynamicPrototype, generatePropertiesFromTraits(this.classInfo.instanceInfo.traits));
 27107                 } else {
 27108                   glueProperties(dynamicPrototype, glue.script.instance);
 27111               if (glue.script.static) {
 27112                 if (Shumway.isNumber(glue.script.static)) {
 27113                   true;
 27114                   glueProperties(this, generatePropertiesFromTraits(this.classInfo.traits));
 27115                 } else {
 27116                   glueProperties(this, glue.script.static);
 27120           };
 27121           Class.prototype.linkNatives = function (definition) {
 27122             var glue = definition.__glue__;
 27123             this.native = glue.native;
 27124           };
 27125           Class.prototype.verify = function () {
 27126             var instanceConstructor = this.instanceConstructor;
 27127             var tP = this.traitsPrototype;
 27128             var dP = this.dynamicPrototype;
 27129             true;
 27130             true;
 27131             true;
 27132             true;
 27133             if (tP !== Object.prototype) {
 27135             true;
 27136           };
 27137           Class.prototype.coerce = function (value) {
 27138             return value;
 27139           };
 27140           Class.prototype.isInstanceOf = function (value) {
 27141             return this.isInstance(value);
 27142           };
 27143           Class.prototype.isInstance = function (value) {
 27144             if (value === null || typeof value !== 'object') {
 27145               return false;
 27147             return this.dynamicPrototype.isPrototypeOf(value);
 27148           };
 27149           Class.prototype.trace = function (writer) {
 27150             var description = this.debugName + (this.baseClass ? ' extends ' + this.baseClass.debugName : '');
 27151             writer.enter('class ' + description + ' {');
 27152             writer.writeLn('scope: ' + this.scope);
 27153             writer.writeLn('baseClass: ' + this.baseClass);
 27154             writer.writeLn('classInfo: ' + this.classInfo);
 27155             writer.writeLn('dynamicPrototype: ' + this.dynamicPrototype);
 27156             writer.writeLn('traitsPrototype: ' + this.traitsPrototype);
 27157             writer.writeLn('dynamicPrototype === traitsPrototype: ' + (this.dynamicPrototype === this.traitsPrototype));
 27158             writer.writeLn('instanceConstructor: ' + this.instanceConstructor);
 27159             writer.writeLn('instanceConstructorNoInitialize: ' + this.instanceConstructorNoInitialize);
 27160             writer.writeLn('instanceConstructor === instanceConstructorNoInitialize: ' + (this.instanceConstructor === this.instanceConstructorNoInitialize));
 27161             var traitsPrototype = this.traitsPrototype;
 27162             writer.enter('traitsPrototype: ');
 27163             if (traitsPrototype) {
 27164               writer.enter('VM_SLOTS: ');
 27165               writer.writeArray(traitsPrototype.asSlots.byID.map(function (slot) {
 27166                 return slot.trait;
 27167               }));
 27168               writer.outdent();
 27169               writer.enter('VM_BINDINGS: ');
 27170               writer.writeArray(traitsPrototype.asBindings.map(function (binding) {
 27171                 var pd = Object.getOwnPropertyDescriptor(traitsPrototype, binding);
 27172                 var str = binding;
 27173                 if (pd.get || pd.set) {
 27174                   if (pd.get) {
 27175                     str += ' getter: ' + debugName(pd.get);
 27177                   if (pd.set) {
 27178                     str += ' setter: ' + debugName(pd.set);
 27180                 } else {
 27181                   str += ' value: ' + debugName(pd.value);
 27183                 return str;
 27184               }));
 27185               writer.outdent();
 27186               writer.enter('VM_OPEN_METHODS: ');
 27187               writer.writeArray(toKeyValueArray(traitsPrototype.asOpenMethods).map(function (pair) {
 27188                 return pair[0] + ': ' + debugName(pair[1]);
 27189               }));
 27190               writer.outdent();
 27192             writer.enter('classBindings: ');
 27193             this.classBindings.trace(writer);
 27194             writer.outdent();
 27195             writer.enter('instanceBindings: ');
 27196             this.instanceBindings.trace(writer);
 27197             writer.outdent();
 27198             writer.outdent();
 27199             writer.writeLn('call: ' + this.call);
 27200             writer.writeLn('apply: ' + this.apply);
 27201             writer.leave('}');
 27202           };
 27203           Class.prototype.toString = function () {
 27204             return '[class ' + this.classInfo.instanceInfo.name.name + ']';
 27205           };
 27206           Class.OWN_INITIALIZE = 1;
 27207           Class.SUPER_INITIALIZE = 2;
 27208           return Class;
 27209         }();
 27210       Runtime.Class = Class;
 27211       var callable = Shumway.AVM2.Runtime.ApplicationDomain.coerceCallable(Class);
 27212       defineNonEnumerableProperty(Class, 'call', callable.call);
 27213       defineNonEnumerableProperty(Class, 'apply', callable.apply);
 27214       Class.instanceConstructor = Class;
 27215       Class.toString = Class.prototype.toString;
 27216       Class.native = {
 27217         instance: {
 27218           prototype: {
 27219             get: function () {
 27220               return this.dynamicPrototype;
 27224       };
 27225     }(AVM2.Runtime || (AVM2.Runtime = {})));
 27226     var Runtime = AVM2.Runtime;
 27227   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 27228   var AVM2 = Shumway.AVM2;
 27229 }(Shumway || (Shumway = {})));
 27230 var Interface = Shumway.AVM2.Runtime.Interface;
 27231 var Class = Shumway.AVM2.Runtime.Class;
 27232 var Binding = Shumway.AVM2.Runtime.Binding;
 27233 var Bindings = Shumway.AVM2.Runtime.Bindings;
 27234 var ActivationBindings = Shumway.AVM2.Runtime.ActivationBindings;
 27235 var CatchBindings = Shumway.AVM2.Runtime.CatchBindings;
 27236 var ScriptBindings = Shumway.AVM2.Runtime.ScriptBindings;
 27237 var ClassBindings = Shumway.AVM2.Runtime.ClassBindings;
 27238 var InstanceBindings = Shumway.AVM2.Runtime.InstanceBindings;
 27239 var Interface = Shumway.AVM2.Runtime.Interface;
 27240 var Class = Shumway.AVM2.Runtime.Class;
 27241 var XRegExp = function (undefined) {
 27242     var REGEX_DATA = 'xregexp', self, features = {
 27243         astral: false,
 27244         natives: false
 27245       }, nativ = {
 27246         exec: RegExp.prototype.exec,
 27247         test: RegExp.prototype.test,
 27248         match: String.prototype.match,
 27249         replace: String.prototype.replace,
 27250         split: String.prototype.split
 27251       }, fixed = {}, cache = {}, patternCache = {}, tokens = [], defaultScope = 'default', classScope = 'class', nativeTokens = {
 27252         'default': /\\(?:0(?:[0-3][0-7]{0,2}|[4-7][0-7]?)?|[1-9]\d*|x[\dA-Fa-f]{2}|u[\dA-Fa-f]{4}|c[A-Za-z]|[\s\S])|\(\?[:=!]|[?*+]\?|{\d+(?:,\d*)?}\??|[\s\S]/,
 27253         'class': /\\(?:[0-3][0-7]{0,2}|[4-7][0-7]?|x[\dA-Fa-f]{2}|u[\dA-Fa-f]{4}|c[A-Za-z]|[\s\S])|[\s\S]/
 27254       }, replacementToken = /\$(?:{([\w$]+)}|([\d$&`']))/g, correctExecNpcg = nativ.exec.call(/()??/, '')[1] === undefined, hasNativeY = RegExp.prototype.sticky !== undefined, registeredFlags = {
 27255         g: true,
 27256         i: true,
 27257         m: true,
 27258         y: hasNativeY
 27259       }, toString = {}.toString, add;
 27260     function augment(regex, captureNames, addProto) {
 27261       var p;
 27262       if (addProto) {
 27263         if (regex.__proto__) {
 27264           regex.__proto__ = self.prototype;
 27265         } else {
 27266           for (p in self.prototype) {
 27267             regex[p] = self.prototype[p];
 27271       regex[REGEX_DATA] = {
 27272         captureNames: captureNames
 27273       };
 27274       return regex;
 27276     function clipDuplicates(str) {
 27277       return nativ.replace.call(str, /([\s\S])(?=[\s\S]*\1)/g, '');
 27279     function copy(regex, options) {
 27280       if (!self.isRegExp(regex)) {
 27281         throw new TypeError('Type RegExp expected');
 27283       var flags = nativ.exec.call(/\/([a-z]*)$/i, String(regex))[1];
 27284       options = options || {};
 27285       if (options.add) {
 27286         flags = clipDuplicates(flags + options.add);
 27288       if (options.remove) {
 27289         flags = nativ.replace.call(flags, new RegExp('[' + options.remove + ']+', 'g'), '');
 27291       regex = augment(new RegExp(regex.source, flags), hasNamedCapture(regex) ? regex[REGEX_DATA].captureNames.slice(0) : null, options.addProto);
 27292       return regex;
 27294     function getBaseProps() {
 27295       return {
 27296         captureNames: null
 27297       };
 27299     function hasNamedCapture(regex) {
 27300       return !(!(regex[REGEX_DATA] && regex[REGEX_DATA].captureNames));
 27302     function indexOf(array, value) {
 27303       if (Array.prototype.indexOf) {
 27304         return array.indexOf(value);
 27306       var len = array.length, i;
 27307       for (i = 0; i < len; ++i) {
 27308         if (array[i] === value) {
 27309           return i;
 27312       return -1;
 27314     function isType(value, type) {
 27315       return toString.call(value) === '[object ' + type + ']';
 27317     function isQuantifierNext(pattern, pos, flags) {
 27318       return nativ.test.call(flags.indexOf('x') > -1 ? /^(?:\s+|#.*|\(\?#[^)]*\))*(?:[?*+]|{\d+(?:,\d*)?})/ : /^(?:\(\?#[^)]*\))*(?:[?*+]|{\d+(?:,\d*)?})/, pattern.slice(pos));
 27320     function prepareFlags(pattern, flags) {
 27321       var i;
 27322       if (clipDuplicates(flags) !== flags) {
 27323         throw new SyntaxError('Invalid duplicate regex flag ' + flags);
 27325       pattern = nativ.replace.call(pattern, /^\(\?([\w$]+)\)/, function ($0, $1) {
 27326         if (nativ.test.call(/[gy]/, $1)) {
 27327           throw new SyntaxError('Cannot use flag g or y in mode modifier ' + $0);
 27329         flags = clipDuplicates(flags + $1);
 27330         return '';
 27331       });
 27332       for (i = 0; i < flags.length; ++i) {
 27333         if (!registeredFlags[flags.charAt(i)]) {
 27334           throw new SyntaxError('Unknown regex flag ' + flags.charAt(i));
 27337       return {
 27338         pattern: pattern,
 27339         flags: flags
 27340       };
 27342     function prepareOptions(value) {
 27343       value = value || {};
 27344       if (isType(value, 'String')) {
 27345         value = self.forEach(value, /[^\s,]+/, function (match) {
 27346           this[match] = true;
 27347         }, {});
 27349       return value;
 27351     function registerFlag(flag) {
 27352       if (!/^[\w$]$/.test(flag)) {
 27353         throw new Error('Flag must be a single character A-Za-z0-9_$');
 27355       registeredFlags[flag] = true;
 27357     function runTokens(pattern, flags, pos, scope, context) {
 27358       var i = tokens.length, result = null, match, t;
 27359       while (i--) {
 27360         t = tokens[i];
 27361         if ((t.scope === scope || t.scope === 'all') && (!t.flag || flags.indexOf(t.flag) > -1)) {
 27362           match = self.exec(pattern, t.regex, pos, 'sticky');
 27363           if (match) {
 27364             result = {
 27365               matchLength: match[0].length,
 27366               output: t.handler.call(context, match, scope, flags),
 27367               reparse: t.reparse
 27368             };
 27369             break;
 27373       return result;
 27375     function setAstral(on) {
 27376       self.cache.flush('patterns');
 27377       features.astral = on;
 27379     function setNatives(on) {
 27380       RegExp.prototype.exec = (on ? fixed : nativ).exec;
 27381       RegExp.prototype.test = (on ? fixed : nativ).test;
 27382       String.prototype.match = (on ? fixed : nativ).match;
 27383       String.prototype.replace = (on ? fixed : nativ).replace;
 27384       String.prototype.split = (on ? fixed : nativ).split;
 27385       features.natives = on;
 27387     function toObject(value) {
 27388       if (value == null) {
 27389         throw new TypeError('Cannot convert null or undefined to object');
 27391       return value;
 27393     self = function (pattern, flags) {
 27394       var context = {
 27395           hasNamedCapture: false,
 27396           captureNames: []
 27397         }, scope = defaultScope, output = '', pos = 0, result, token, key;
 27398       if (self.isRegExp(pattern)) {
 27399         if (flags !== undefined) {
 27400           throw new TypeError('Cannot supply flags when copying a RegExp');
 27402         return copy(pattern, {
 27403           addProto: true
 27404         });
 27406       pattern = pattern === undefined ? '' : String(pattern);
 27407       flags = flags === undefined ? '' : String(flags);
 27408       key = pattern + '***' + flags;
 27409       if (!patternCache[key]) {
 27410         result = prepareFlags(pattern, flags);
 27411         pattern = result.pattern;
 27412         flags = result.flags;
 27413         while (pos < pattern.length) {
 27414           do {
 27415             result = runTokens(pattern, flags, pos, scope, context);
 27416             if (result && result.reparse) {
 27417               pattern = pattern.slice(0, pos) + result.output + pattern.slice(pos + result.matchLength);
 27419           } while (result && result.reparse);
 27420           if (result) {
 27421             output += result.output;
 27422             pos += result.matchLength || 1;
 27423           } else {
 27424             token = self.exec(pattern, nativeTokens[scope], pos, 'sticky')[0];
 27425             output += token;
 27426             pos += token.length;
 27427             if (token === '[' && scope === defaultScope) {
 27428               scope = classScope;
 27429             } else if (token === ']' && scope === classScope) {
 27430               scope = defaultScope;
 27434         patternCache[key] = {
 27435           pattern: nativ.replace.call(output, /\(\?:\)(?=\(\?:\))|^\(\?:\)|\(\?:\)$/g, ''),
 27436           flags: nativ.replace.call(flags, /[^gimy]+/g, ''),
 27437           captures: context.hasNamedCapture ? context.captureNames : null
 27438         };
 27440       key = patternCache[key];
 27441       return augment(new RegExp(key.pattern, key.flags), key.captures, true);
 27442     };
 27443     self.prototype = new RegExp();
 27444     self.version = '3.0.0-pre';
 27445     self.addToken = function (regex, handler, options) {
 27446       options = options || {};
 27447       var optionalFlags = options.optionalFlags, i;
 27448       if (options.flag) {
 27449         registerFlag(options.flag);
 27451       if (optionalFlags) {
 27452         optionalFlags = nativ.split.call(optionalFlags, '');
 27453         for (i = 0; i < optionalFlags.length; ++i) {
 27454           registerFlag(optionalFlags[i]);
 27457       tokens.push({
 27458         regex: copy(regex, {
 27459           add: 'g' + (hasNativeY ? 'y' : '')
 27460         }),
 27461         handler: handler,
 27462         scope: options.scope || defaultScope,
 27463         flag: options.flag,
 27464         reparse: options.reparse
 27465       });
 27466       self.cache.flush('patterns');
 27467     };
 27468     self.cache = function (pattern, flags) {
 27469       var key = pattern + '***' + (flags || '');
 27470       return cache[key] || (cache[key] = self(pattern, flags));
 27471     };
 27472     self.cache.flush = function (cacheName) {
 27473       if (cacheName === 'patterns') {
 27474         patternCache = {};
 27475       } else {
 27476         cache = {};
 27478     };
 27479     self.escape = function (str) {
 27480       return nativ.replace.call(toObject(str), /[-[\]{}()*+?.,\\^$|#\s]/g, '\\$&');
 27481     };
 27482     self.exec = function (str, regex, pos, sticky) {
 27483       var cacheFlags = 'g', match, r2;
 27484       if (hasNativeY && (sticky || regex.sticky && sticky !== false)) {
 27485         cacheFlags += 'y';
 27487       regex[REGEX_DATA] = regex[REGEX_DATA] || getBaseProps();
 27488       r2 = regex[REGEX_DATA][cacheFlags] || (regex[REGEX_DATA][cacheFlags] = copy(regex, {
 27489         add: cacheFlags,
 27490         remove: sticky === false ? 'y' : ''
 27491       }));
 27492       r2.lastIndex = pos = pos || 0;
 27493       match = fixed.exec.call(r2, str);
 27494       if (sticky && match && match.index !== pos) {
 27495         match = null;
 27497       if (regex.global) {
 27498         regex.lastIndex = match ? r2.lastIndex : 0;
 27500       return match;
 27501     };
 27502     self.forEach = function (str, regex, callback, context) {
 27503       var pos = 0, i = -1, match;
 27504       while (match = self.exec(str, regex, pos)) {
 27505         callback.call(context, match, ++i, str, regex);
 27506         pos = match.index + (match[0].length || 1);
 27508       return context;
 27509     };
 27510     self.globalize = function (regex) {
 27511       return copy(regex, {
 27512         add: 'g',
 27513         addProto: true
 27514       });
 27515     };
 27516     self.install = function (options) {
 27517       options = prepareOptions(options);
 27518       if (!features.astral && options.astral) {
 27519         setAstral(true);
 27521       if (!features.natives && options.natives) {
 27522         setNatives(true);
 27524     };
 27525     self.isInstalled = function (feature) {
 27526       return !(!features[feature]);
 27527     };
 27528     self.isRegExp = function (value) {
 27529       return toString.call(value) === '[object RegExp]';
 27530     };
 27531     self.match = function (str, regex, scope) {
 27532       var global = regex.global && scope !== 'one' || scope === 'all', cacheFlags = (global ? 'g' : '') + (regex.sticky ? 'y' : ''), result, r2;
 27533       regex[REGEX_DATA] = regex[REGEX_DATA] || getBaseProps();
 27534       r2 = regex[REGEX_DATA][cacheFlags || 'noGY'] || (regex[REGEX_DATA][cacheFlags || 'noGY'] = copy(regex, {
 27535         add: cacheFlags,
 27536         remove: scope === 'one' ? 'g' : ''
 27537       }));
 27538       result = nativ.match.call(toObject(str), r2);
 27539       if (regex.global) {
 27540         regex.lastIndex = scope === 'one' && result ? result.index + result[0].length : 0;
 27542       return global ? result || [] : result && result[0];
 27543     };
 27544     self.matchChain = function (str, chain) {
 27545       return function recurseChain(values, level) {
 27546         var item = chain[level].regex ? chain[level] : {
 27547             regex: chain[level]
 27548           }, matches = [], addMatch = function (match) {
 27549             if (item.backref) {
 27550               if (!(match.hasOwnProperty(item.backref) || +item.backref < match.length)) {
 27551                 throw new ReferenceError('Backreference to undefined group: ' + item.backref);
 27553               matches.push(match[item.backref] || '');
 27554             } else {
 27555               matches.push(match[0]);
 27557           }, i;
 27558         for (i = 0; i < values.length; ++i) {
 27559           self.forEach(values[i], item.regex, addMatch);
 27561         return level === chain.length - 1 || !matches.length ? matches : recurseChain(matches, level + 1);
 27562       }([
 27563         str
 27564       ], 0);
 27565     };
 27566     self.replace = function (str, search, replacement, scope) {
 27567       var isRegex = self.isRegExp(search), global = search.global && scope !== 'one' || scope === 'all', cacheFlags = (global ? 'g' : '') + (search.sticky ? 'y' : ''), s2 = search, result;
 27568       if (isRegex) {
 27569         search[REGEX_DATA] = search[REGEX_DATA] || getBaseProps();
 27570         s2 = search[REGEX_DATA][cacheFlags || 'noGY'] || (search[REGEX_DATA][cacheFlags || 'noGY'] = copy(search, {
 27571           add: cacheFlags,
 27572           remove: scope === 'one' ? 'g' : ''
 27573         }));
 27574       } else if (global) {
 27575         s2 = new RegExp(self.escape(String(search)), 'g');
 27577       result = fixed.replace.call(toObject(str), s2, replacement);
 27578       if (isRegex && search.global) {
 27579         search.lastIndex = 0;
 27581       return result;
 27582     };
 27583     self.replaceEach = function (str, replacements) {
 27584       var i, r;
 27585       for (i = 0; i < replacements.length; ++i) {
 27586         r = replacements[i];
 27587         str = self.replace(str, r[0], r[1], r[2]);
 27589       return str;
 27590     };
 27591     self.split = function (str, separator, limit) {
 27592       return fixed.split.call(toObject(str), separator, limit);
 27593     };
 27594     self.test = function (str, regex, pos, sticky) {
 27595       return !(!self.exec(str, regex, pos, sticky));
 27596     };
 27597     self.uninstall = function (options) {
 27598       options = prepareOptions(options);
 27599       if (features.astral && options.astral) {
 27600         setAstral(false);
 27602       if (features.natives && options.natives) {
 27603         setNatives(false);
 27605     };
 27606     self.union = function (patterns, flags) {
 27607       var parts = /(\()(?!\?)|\\([1-9]\d*)|\\[\s\S]|\[(?:[^\\\]]|\\[\s\S])*]/g, output = [], numCaptures = 0, numPriorCaptures, captureNames, pattern, rewrite = function (match, paren, backref) {
 27608           var name = captureNames[numCaptures - numPriorCaptures];
 27609           if (paren) {
 27610             ++numCaptures;
 27611             if (name) {
 27612               return '(?<' + name + '>';
 27614           } else if (backref) {
 27615             return '\\' + (+backref + numPriorCaptures);
 27617           return match;
 27618         }, i;
 27619       if (!(isType(patterns, 'Array') && patterns.length)) {
 27620         throw new TypeError('Must provide a nonempty array of patterns to merge');
 27622       for (i = 0; i < patterns.length; ++i) {
 27623         pattern = patterns[i];
 27624         if (self.isRegExp(pattern)) {
 27625           numPriorCaptures = numCaptures;
 27626           captureNames = pattern[REGEX_DATA] && pattern[REGEX_DATA].captureNames || [];
 27627           output.push(nativ.replace.call(self(pattern.source).source, parts, rewrite));
 27628         } else {
 27629           output.push(self.escape(pattern));
 27632       return self(output.join('|'), flags);
 27633     };
 27634     fixed.exec = function (str) {
 27635       var origLastIndex = this.lastIndex, match = nativ.exec.apply(this, arguments), name, r2, i;
 27636       if (match) {
 27637         if (!correctExecNpcg && match.length > 1 && indexOf(match, '') > -1) {
 27638           r2 = copy(this, {
 27639             remove: 'g'
 27640           });
 27641           nativ.replace.call(String(str).slice(match.index), r2, function () {
 27642             var len = arguments.length, i;
 27643             for (i = 1; i < len - 2; ++i) {
 27644               if (arguments[i] === undefined) {
 27645                 match[i] = undefined;
 27648           });
 27650         if (this[REGEX_DATA] && this[REGEX_DATA].captureNames) {
 27651           for (i = 1; i < match.length; ++i) {
 27652             name = this[REGEX_DATA].captureNames[i - 1];
 27653             if (name) {
 27654               match[name] = match[i];
 27658         if (this.global && !match[0].length && this.lastIndex > match.index) {
 27659           this.lastIndex = match.index;
 27662       if (!this.global) {
 27663         this.lastIndex = origLastIndex;
 27665       return match;
 27666     };
 27667     fixed.test = function (str) {
 27668       return !(!fixed.exec.call(this, str));
 27669     };
 27670     fixed.match = function (regex) {
 27671       var result;
 27672       if (!self.isRegExp(regex)) {
 27673         regex = new RegExp(regex);
 27674       } else if (regex.global) {
 27675         result = nativ.match.apply(this, arguments);
 27676         regex.lastIndex = 0;
 27677         return result;
 27679       return fixed.exec.call(regex, toObject(this));
 27680     };
 27681     fixed.replace = function (search, replacement) {
 27682       var isRegex = self.isRegExp(search), origLastIndex, captureNames, result;
 27683       if (isRegex) {
 27684         if (search[REGEX_DATA]) {
 27685           captureNames = search[REGEX_DATA].captureNames;
 27687         origLastIndex = search.lastIndex;
 27688       } else {
 27689         search += '';
 27691       if (isType(replacement, 'Function')) {
 27692         result = nativ.replace.call(String(this), search, function () {
 27693           var args = arguments, i;
 27694           if (captureNames) {
 27695             args[0] = new String(args[0]);
 27696             for (i = 0; i < captureNames.length; ++i) {
 27697               if (captureNames[i]) {
 27698                 args[0][captureNames[i]] = args[i + 1];
 27702           if (isRegex && search.global) {
 27703             search.lastIndex = args[args.length - 2] + args[0].length;
 27705           return replacement.apply(undefined, args);
 27706         });
 27707       } else {
 27708         result = nativ.replace.call(this == null ? this : String(this), search, function () {
 27709           var args = arguments;
 27710           return nativ.replace.call(String(replacement), replacementToken, function ($0, $1, $2) {
 27711             var n;
 27712             if ($1) {
 27713               n = +$1;
 27714               if (n <= args.length - 3) {
 27715                 return args[n] || '';
 27717               n = captureNames ? indexOf(captureNames, $1) : -1;
 27718               if (n < 0) {
 27719                 throw new SyntaxError('Backreference to undefined group ' + $0);
 27721               return args[n + 1] || '';
 27723             if ($2 === '$') {
 27724               return '$';
 27726             if ($2 === '&' || +$2 === 0) {
 27727               return args[0];
 27729             if ($2 === '`') {
 27730               return args[args.length - 1].slice(0, args[args.length - 2]);
 27732             if ($2 === '\'') {
 27733               return args[args.length - 1].slice(args[args.length - 2] + args[0].length);
 27735             $2 = +$2;
 27736             if (!isNaN($2)) {
 27737               if ($2 > args.length - 3) {
 27738                 throw new SyntaxError('Backreference to undefined group ' + $0);
 27740               return args[$2] || '';
 27742             throw new SyntaxError('Invalid token ' + $0);
 27743           });
 27744         });
 27746       if (isRegex) {
 27747         if (search.global) {
 27748           search.lastIndex = 0;
 27749         } else {
 27750           search.lastIndex = origLastIndex;
 27753       return result;
 27754     };
 27755     fixed.split = function (separator, limit) {
 27756       if (!self.isRegExp(separator)) {
 27757         return nativ.split.apply(this, arguments);
 27759       var str = String(this), output = [], origLastIndex = separator.lastIndex, lastLastIndex = 0, lastLength;
 27760       limit = (limit === undefined ? -1 : limit) >>> 0;
 27761       self.forEach(str, separator, function (match) {
 27762         if (match.index + match[0].length > lastLastIndex) {
 27763           output.push(str.slice(lastLastIndex, match.index));
 27764           if (match.length > 1 && match.index < str.length) {
 27765             Array.prototype.push.apply(output, match.slice(1));
 27767           lastLength = match[0].length;
 27768           lastLastIndex = match.index + lastLength;
 27770       });
 27771       if (lastLastIndex === str.length) {
 27772         if (!nativ.test.call(separator, '') || lastLength) {
 27773           output.push('');
 27775       } else {
 27776         output.push(str.slice(lastLastIndex));
 27778       separator.lastIndex = origLastIndex;
 27779       return output.length > limit ? output.slice(0, limit) : output;
 27780     };
 27781     add = self.addToken;
 27782     add(/\\([ABCE-RTUVXYZaeg-mopqyz]|c(?![A-Za-z])|u(?![\dA-Fa-f]{4})|x(?![\dA-Fa-f]{2}))/, function (match, scope) {
 27783       if (match[1] === 'B' && scope === defaultScope) {
 27784         return match[0];
 27786       throw new SyntaxError('Invalid escape ' + match[0]);
 27787     }, {
 27788       scope: 'all'
 27789     });
 27790     add(/\[(\^?)]/, function (match) {
 27791       return match[1] ? '[\\s\\S]' : '\\b\\B';
 27792     });
 27793     add(/\(\?#[^)]*\)/, function (match, scope, flags) {
 27794       return isQuantifierNext(match.input, match.index + match[0].length, flags) ? '' : '(?:)';
 27795     });
 27796     add(/\s+|#.*/, function (match, scope, flags) {
 27797       return isQuantifierNext(match.input, match.index + match[0].length, flags) ? '' : '(?:)';
 27798     }, {
 27799       flag: 'x'
 27800     });
 27801     add(/\./, function () {
 27802       return '[\\s\\S]';
 27803     }, {
 27804       flag: 's'
 27805     });
 27806     add(/\\k<([\w$]+)>/, function (match) {
 27807       var index = isNaN(match[1]) ? indexOf(this.captureNames, match[1]) + 1 : +match[1], endIndex = match.index + match[0].length;
 27808       if (!index || index > this.captureNames.length) {
 27809         throw new SyntaxError('Backreference to undefined group ' + match[0]);
 27811       return '\\' + index + (endIndex === match.input.length || isNaN(match.input.charAt(endIndex)) ? '' : '(?:)');
 27812     });
 27813     add(/\\(\d+)/, function (match, scope) {
 27814       if (!(scope === defaultScope && /^[1-9]/.test(match[1]) && +match[1] <= this.captureNames.length) && match[1] !== '0') {
 27815         throw new SyntaxError('Cannot use octal escape or backreference to undefined group ' + match[0]);
 27817       return match[0];
 27818     }, {
 27819       scope: 'all'
 27820     });
 27821     add(/\(\?P?<([\w$]+)>/, function (match) {
 27822       if (!isNaN(match[1])) {
 27823         throw new SyntaxError('Cannot use integer as capture name ' + match[0]);
 27825       if (match[1] === 'length' || match[1] === '__proto__') {
 27826         throw new SyntaxError('Cannot use reserved word as capture name ' + match[0]);
 27828       if (indexOf(this.captureNames, match[1]) > -1) {
 27829         throw new SyntaxError('Cannot use same name for multiple groups ' + match[0]);
 27831       this.captureNames.push(match[1]);
 27832       this.hasNamedCapture = true;
 27833       return '(';
 27834     });
 27835     add(/\((?!\?)/, function (match, scope, flags) {
 27836       if (flags.indexOf('n') > -1) {
 27837         return '(?:';
 27839       this.captureNames.push(null);
 27840       return '(';
 27841     }, {
 27842       optionalFlags: 'n'
 27843     });
 27844     return self;
 27845   }();
 27846 var Namespace = Shumway.AVM2.ABC.Namespace;
 27847 var Shumway;
 27848 (function (Shumway) {
 27849   (function (AVM2) {
 27850     (function (Runtime) {
 27851       var Option = Shumway.Options.Option;
 27852       var OptionSet = Shumway.Options.OptionSet;
 27853       var runtimeOptions = systemOptions.register(new OptionSet('Runtime Options'));
 27854       var traceScope = runtimeOptions.register(new Option('ts', 'traceScope', 'boolean', false, 'trace scope execution'));
 27855       Runtime.traceExecution = runtimeOptions.register(new Option('tx', 'traceExecution', 'number', 0, 'trace script execution'));
 27856       Runtime.traceCallExecution = runtimeOptions.register(new Option('txc', 'traceCallExecution', 'number', 0, 'trace call execution'));
 27857       var functionBreak = runtimeOptions.register(new Option('fb', 'functionBreak', 'number', -1, 'Inserts a debugBreak at function index #.'));
 27858       var compileOnly = runtimeOptions.register(new Option('co', 'compileOnly', 'number', -1, 'Compiles only function number.'));
 27859       var compileUntil = runtimeOptions.register(new Option('cu', 'compileUntil', 'number', -1, 'Compiles only until a function number.'));
 27860       Runtime.debuggerMode = runtimeOptions.register(new Option('dm', 'debuggerMode', 'boolean', false, 'matches avm2 debugger build semantics'));
 27861       Runtime.enableVerifier = runtimeOptions.register(new Option('verify', 'verify', 'boolean', false, 'Enable verifier.'));
 27862       Runtime.globalMultinameAnalysis = runtimeOptions.register(new Option('ga', 'globalMultinameAnalysis', 'boolean', false, 'Global multiname analysis.'));
 27863       var traceInlineCaching = runtimeOptions.register(new Option('tic', 'traceInlineCaching', 'boolean', false, 'Trace inline caching execution.'));
 27864       Runtime.codeCaching = runtimeOptions.register(new Option('cc', 'codeCaching', 'boolean', false, 'Enable code caching.'));
 27865       var compilerEnableExceptions = runtimeOptions.register(new Option('cex', 'exceptions', 'boolean', false, 'Compile functions with catch blocks.'));
 27866       var compilerMaximumMethodSize = runtimeOptions.register(new Option('cmms', 'maximumMethodSize', 'number', 4 * 1024, 'Compiler maximum method size.'));
 27867       Runtime.traceClasses = runtimeOptions.register(new Option('tc', 'traceClasses', 'boolean', false, 'trace class creation'));
 27868       Runtime.traceDomain = runtimeOptions.register(new Option('td', 'traceDomain', 'boolean', false, 'trace domain property access'));
 27869       Runtime.sealConstTraits = false;
 27870       Runtime.useAsAdd = true;
 27871       var useSurrogates = true;
 27872       var callCounter = new Shumway.Metrics.Counter(true);
 27873       var Multiname = Shumway.AVM2.ABC.Multiname;
 27874       var Namespace = Shumway.AVM2.ABC.Namespace;
 27875       var MethodInfo = Shumway.AVM2.ABC.MethodInfo;
 27876       var ClassInfo = Shumway.AVM2.ABC.ClassInfo;
 27877       var InstanceInfo = Shumway.AVM2.ABC.InstanceInfo;
 27878       var ScriptInfo = Shumway.AVM2.ABC.ScriptInfo;
 27879       var SORT = Shumway.AVM2.ABC.SORT;
 27880       var Trait = Shumway.AVM2.ABC.Trait;
 27881       var IndentingWriter = Shumway.IndentingWriter;
 27882       var hasOwnProperty = Shumway.ObjectUtilities.hasOwnProperty;
 27883       var createMap = Shumway.ObjectUtilities.createMap;
 27884       var cloneObject = Shumway.ObjectUtilities.cloneObject;
 27885       var copyProperties = Shumway.ObjectUtilities.copyProperties;
 27886       var createEmptyObject = Shumway.ObjectUtilities.createEmptyObject;
 27887       var boxValue = Shumway.ObjectUtilities.boxValue;
 27888       var bindSafely = Shumway.FunctionUtilities.bindSafely;
 27889       var defineNonEnumerableGetterOrSetter = Shumway.ObjectUtilities.defineNonEnumerableGetterOrSetter;
 27890       var defineNonEnumerableProperty = Shumway.ObjectUtilities.defineNonEnumerableProperty;
 27891       var defineReadOnlyProperty = Shumway.ObjectUtilities.defineReadOnlyProperty;
 27892       var defineNonEnumerableGetter = Shumway.ObjectUtilities.defineNonEnumerableGetter;
 27893       var makeForwardingGetter = Shumway.FunctionUtilities.makeForwardingGetter;
 27894       var makeForwardingSetter = Shumway.FunctionUtilities.makeForwardingSetter;
 27895       var toSafeString = Shumway.StringUtilities.toSafeString;
 27896       var toSafeArrayString = Shumway.StringUtilities.toSafeArrayString;
 27897       var TRAIT = Shumway.AVM2.ABC.TRAIT;
 27898       Runtime.VM_SLOTS = 'asSlots';
 27899       Runtime.VM_LENGTH = 'asLength';
 27900       Runtime.VM_BINDINGS = 'asBindings';
 27901       Runtime.VM_NATIVE_PROTOTYPE_FLAG = 'asIsNative';
 27902       Runtime.VM_OPEN_METHODS = 'asOpenMethods';
 27903       Runtime.VM_IS_CLASS = 'asIsClass';
 27904       Runtime.VM_IS_PROXY = 'asIsProxy';
 27905       Runtime.VM_CALL_PROXY = 'asCallProxy';
 27906       Runtime.VM_OPEN_METHOD_PREFIX = 'm';
 27907       Runtime.VM_MEMOIZER_PREFIX = 'z';
 27908       Runtime.VM_OPEN_SET_METHOD_PREFIX = 's';
 27909       Runtime.VM_OPEN_GET_METHOD_PREFIX = 'g';
 27910       Runtime.VM_NATIVE_BUILTIN_ORIGINALS = 'asOriginals';
 27911       Runtime.VM_METHOD_OVERRIDES = createEmptyObject();
 27912       var vmNextInterpreterFunctionId = 1;
 27913       var vmNextCompiledFunctionId = 1;
 27914       var totalFunctionCount = 0;
 27915       var compiledFunctionCount = 0;
 27916       var compilationCount = 0;
 27917       function isClass(object) {
 27918         true;
 27919         return Object.hasOwnProperty.call(object, Runtime.VM_IS_CLASS);
 27921       Runtime.isClass = isClass;
 27922       function isNativePrototype(object) {
 27923         return Object.prototype.hasOwnProperty.call(object, Runtime.VM_NATIVE_PROTOTYPE_FLAG);
 27925       Runtime.isNativePrototype = isNativePrototype;
 27926       var traitsWriter = null;
 27927       var callWriter = null;
 27928       function patch(patchTargets, value) {
 27929         true;
 27930         for (var i = 0; i < patchTargets.length; i++) {
 27931           var patchTarget = patchTargets[i];
 27932           if (Runtime.traceExecution.value >= 3) {
 27933             var str = 'Patching: ';
 27934             if (patchTarget.name) {
 27935               str += patchTarget.name;
 27936             } else if (patchTarget.get) {
 27937               str += 'get ' + patchTarget.get;
 27938             } else if (patchTarget.set) {
 27939               str += 'set ' + patchTarget.set;
 27941             traitsWriter && traitsWriter.redLn(str);
 27943           if (patchTarget.get) {
 27944             defineNonEnumerableGetterOrSetter(patchTarget.object, patchTarget.get, value, true);
 27945           } else if (patchTarget.set) {
 27946             defineNonEnumerableGetterOrSetter(patchTarget.object, patchTarget.set, value, false);
 27947           } else {
 27948             defineNonEnumerableProperty(patchTarget.object, patchTarget.name, value);
 27952       Runtime.patch = patch;
 27953       function applyNonMemoizedMethodTrait(qn, trait, object, scope, natives) {
 27954         true;
 27955         if (trait.isMethod()) {
 27956           var trampoline = Shumway.AVM2.Runtime.makeTrampoline(function (self) {
 27957               var fn = getTraitFunction(trait, scope, natives);
 27958               patch(self.patchTargets, fn);
 27959               return fn;
 27960             }, trait.methodInfo.parameters.length);
 27961           trampoline.patchTargets = [
 27963               object: object,
 27964               name: qn
 27965             },
 27967               object: object,
 27968               name: Runtime.VM_OPEN_METHOD_PREFIX + qn
 27970           ];
 27971           var closure = bindSafely(trampoline, object);
 27972           defineReadOnlyProperty(closure, Runtime.VM_LENGTH, trampoline.asLength);
 27973           defineReadOnlyProperty(closure, Multiname.getPublicQualifiedName('prototype'), null);
 27974           defineNonEnumerableProperty(object, qn, closure);
 27975           defineNonEnumerableProperty(object, Runtime.VM_OPEN_METHOD_PREFIX + qn, closure);
 27976         } else if (trait.isGetter() || trait.isSetter()) {
 27977           var trampoline = Shumway.AVM2.Runtime.makeTrampoline(function (self) {
 27978               var fn = getTraitFunction(trait, scope, natives);
 27979               patch(self.patchTargets, fn);
 27980               return fn;
 27981             }, trait.isSetter() ? 1 : 0);
 27982           if (trait.isGetter()) {
 27983             trampoline.patchTargets = [
 27985                 object: object,
 27986                 get: qn
 27988             ];
 27989           } else {
 27990             trampoline.patchTargets = [
 27992                 object: object,
 27993                 set: qn
 27995             ];
 27997           defineNonEnumerableGetterOrSetter(object, qn, trampoline, trait.isGetter());
 27998         } else {
 27999           Shumway.Debug.unexpected(trait);
 28002       Runtime.applyNonMemoizedMethodTrait = applyNonMemoizedMethodTrait;
 28003       function applyMemoizedMethodTrait(qn, trait, object, scope, natives) {
 28004         true;
 28005         if (trait.isMethod()) {
 28006           var memoizerTarget = {
 28007               value: null
 28008             };
 28009           var trampoline = Shumway.AVM2.Runtime.makeTrampoline(function (self) {
 28010               var fn = getTraitFunction(trait, scope, natives);
 28011               patch(self.patchTargets, fn);
 28012               return fn;
 28013             }, trait.methodInfo.parameters.length, String(trait.name));
 28014           memoizerTarget.value = trampoline;
 28015           var openMethods = object.asOpenMethods;
 28016           openMethods[qn] = trampoline;
 28017           defineNonEnumerableProperty(object, Runtime.VM_OPEN_METHOD_PREFIX + qn, trampoline);
 28018           defineNonEnumerableGetter(object, qn, Shumway.AVM2.Runtime.makeMemoizer(qn, memoizerTarget));
 28019           trampoline.patchTargets = [
 28021               object: memoizerTarget,
 28022               name: 'value'
 28023             },
 28025               object: openMethods,
 28026               name: qn
 28027             },
 28029               object: object,
 28030               name: Runtime.VM_OPEN_METHOD_PREFIX + qn
 28032           ];
 28033         } else if (trait.isGetter() || trait.isSetter()) {
 28034           var trampoline = Shumway.AVM2.Runtime.makeTrampoline(function (self) {
 28035               var fn = getTraitFunction(trait, scope, natives);
 28036               patch(self.patchTargets, fn);
 28037               return fn;
 28038             }, 0, String(trait.name));
 28039           if (trait.isGetter()) {
 28040             defineNonEnumerableProperty(object, Runtime.VM_OPEN_GET_METHOD_PREFIX + qn, trampoline);
 28041             trampoline.patchTargets = [
 28043                 object: object,
 28044                 get: qn
 28045               },
 28047                 object: object,
 28048                 name: Runtime.VM_OPEN_GET_METHOD_PREFIX + qn
 28050             ];
 28051           } else {
 28052             defineNonEnumerableProperty(object, Runtime.VM_OPEN_SET_METHOD_PREFIX + qn, trampoline);
 28053             trampoline.patchTargets = [
 28055                 object: object,
 28056                 set: qn
 28057               },
 28059                 object: object,
 28060                 name: Runtime.VM_OPEN_SET_METHOD_PREFIX + qn
 28062             ];
 28064           defineNonEnumerableGetterOrSetter(object, qn, trampoline, trait.isGetter());
 28067       Runtime.applyMemoizedMethodTrait = applyMemoizedMethodTrait;
 28068       function getNamespaceResolutionMap(namespaces) {
 28069         var self = this;
 28070         var map = self.resolutionMap[namespaces.runtimeId];
 28071         if (map)
 28072           return map;
 28073         map = self.resolutionMap[namespaces.runtimeId] = Shumway.ObjectUtilities.createMap();
 28074         var bindings = self.bindings;
 28075         for (var key in bindings.map) {
 28076           var multiname = key;
 28077           var trait = bindings.map[key].trait;
 28078           if (trait.isGetter() || trait.isSetter()) {
 28079             multiname = multiname.substring(Shumway.AVM2.Runtime.Binding.KEY_PREFIX_LENGTH);
 28081           multiname = Multiname.fromQualifiedName(multiname);
 28082           if (multiname.getNamespace().inNamespaceSet(namespaces)) {
 28083             map[multiname.getName()] = Multiname.getQualifiedName(trait.name);
 28086         return map;
 28088       Runtime.getNamespaceResolutionMap = getNamespaceResolutionMap;
 28089       function resolveMultinameProperty(namespaces, name, flags) {
 28090         var self = this;
 28091         if (typeof name === 'object') {
 28092           name = String(name);
 28094         if (Shumway.isNumeric(name)) {
 28095           return Shumway.toNumber(name);
 28097         if (!namespaces) {
 28098           return Multiname.getPublicQualifiedName(name);
 28100         if (namespaces.length > 1) {
 28101           var resolved = self.getNamespaceResolutionMap(namespaces)[name];
 28102           if (resolved)
 28103             return resolved;
 28104           return Multiname.getPublicQualifiedName(name);
 28105         } else {
 28106           return Multiname.qualifyName(namespaces[0], name);
 28109       Runtime.resolveMultinameProperty = resolveMultinameProperty;
 28110       function asGetPublicProperty(name) {
 28111         var self = this;
 28112         return self.asGetProperty(undefined, name, 0);
 28114       Runtime.asGetPublicProperty = asGetPublicProperty;
 28115       function asGetProperty(namespaces, name, flags) {
 28116         var self = this;
 28117         var resolved = self.resolveMultinameProperty(namespaces, name, flags);
 28118         if (self.asGetNumericProperty && Multiname.isNumeric(resolved)) {
 28119           return self.asGetNumericProperty(resolved);
 28121         return self[resolved];
 28123       Runtime.asGetProperty = asGetProperty;
 28124       function asGetPropertyLikelyNumeric(namespaces, name, flags) {
 28125         var self = this;
 28126         if (typeof name === 'number') {
 28127           return self.asGetNumericProperty(name);
 28129         return asGetProperty.call(self, namespaces, name, flags);
 28131       Runtime.asGetPropertyLikelyNumeric = asGetPropertyLikelyNumeric;
 28132       function asGetResolvedStringProperty(resolved) {
 28133         true;
 28134         return this[resolved];
 28136       Runtime.asGetResolvedStringProperty = asGetResolvedStringProperty;
 28137       function asCallResolvedStringProperty(resolved, isLex, args) {
 28138         var self = this;
 28139         var receiver = isLex ? null : this;
 28140         var openMethods = self.asOpenMethods;
 28141         var method;
 28142         if (receiver && openMethods && openMethods[resolved]) {
 28143           method = openMethods[resolved];
 28144         } else {
 28145           method = self[resolved];
 28147         return method.apply(receiver, args);
 28149       Runtime.asCallResolvedStringProperty = asCallResolvedStringProperty;
 28150       function asGetResolvedStringPropertyFallback(resolved) {
 28151         var self = this;
 28152         var name = Multiname.getNameFromPublicQualifiedName(resolved);
 28153         return self.asGetProperty([
 28154           Namespace.PUBLIC
 28155         ], name, 0);
 28157       Runtime.asGetResolvedStringPropertyFallback = asGetResolvedStringPropertyFallback;
 28158       function asSetPublicProperty(name, value) {
 28159         var self = this;
 28160         return self.asSetProperty(undefined, name, 0, value);
 28162       Runtime.asSetPublicProperty = asSetPublicProperty;
 28163       function asSetProperty(namespaces, name, flags, value) {
 28164         var self = this;
 28165         if (typeof name === 'object') {
 28166           name = String(name);
 28168         var resolved = self.resolveMultinameProperty(namespaces, name, flags);
 28169         if (self.asSetNumericProperty && Multiname.isNumeric(resolved)) {
 28170           return self.asSetNumericProperty(resolved, value);
 28172         var slotInfo = self.asSlots.byQN[resolved];
 28173         if (slotInfo) {
 28174           if (slotInfo.isConst) {
 28176           var type = slotInfo.type;
 28177           if (type && type.coerce) {
 28178             value = type.coerce(value);
 28181         self[resolved] = value;
 28183       Runtime.asSetProperty = asSetProperty;
 28184       function asSetPropertyLikelyNumeric(namespaces, name, flags, value) {
 28185         var self = this;
 28186         if (typeof name === 'number') {
 28187           self.asSetNumericProperty(name, value);
 28188           return;
 28190         return asSetProperty.call(self, namespaces, name, flags, value);
 28192       Runtime.asSetPropertyLikelyNumeric = asSetPropertyLikelyNumeric;
 28193       function asDefinePublicProperty(name, descriptor) {
 28194         var self = this;
 28195         return self.asDefineProperty(undefined, name, 0, descriptor);
 28197       Runtime.asDefinePublicProperty = asDefinePublicProperty;
 28198       function asDefineProperty(namespaces, name, flags, descriptor) {
 28199         var self = this;
 28200         if (typeof name === 'object') {
 28201           name = String(name);
 28203         var resolved = self.resolveMultinameProperty(namespaces, name, flags);
 28204         Object.defineProperty(self, resolved, descriptor);
 28206       Runtime.asDefineProperty = asDefineProperty;
 28207       function asCallPublicProperty(name, args) {
 28208         var self = this;
 28209         return self.asCallProperty(undefined, name, 0, false, args);
 28211       Runtime.asCallPublicProperty = asCallPublicProperty;
 28212       function asCallProperty(namespaces, name, flags, isLex, args) {
 28213         var self = this;
 28214         if (Runtime.traceCallExecution.value) {
 28215           var receiverClassName = self.class ? self.class.className + ' ' : '';
 28216           callWriter.enter('call ' + receiverClassName + name + '(' + toSafeArrayString(args) + ') #' + callCounter.count(name));
 28218         var receiver = isLex ? null : self;
 28219         var result;
 28220         if (isProxyObject(self)) {
 28221           result = self[Runtime.VM_CALL_PROXY](new Multiname(namespaces, name, flags), receiver, args);
 28222         } else {
 28223           var method;
 28224           var resolved = self.resolveMultinameProperty(namespaces, name, flags);
 28225           if (self.asGetNumericProperty && Multiname.isNumeric(resolved)) {
 28226             method = self.asGetNumericProperty(resolved);
 28227           } else {
 28228             var openMethods = self.asOpenMethods;
 28229             if (receiver && openMethods && openMethods[resolved]) {
 28230               method = openMethods[resolved];
 28231             } else {
 28232               method = self[resolved];
 28235           result = method.apply(receiver, args);
 28237         Runtime.traceCallExecution.value > 0 && callWriter.leave('return ' + toSafeString(result));
 28238         return result;
 28240       Runtime.asCallProperty = asCallProperty;
 28241       function asCallSuper(scope, namespaces, name, flags, args) {
 28242         var self = this;
 28243         if (Runtime.traceCallExecution.value) {
 28244           var receiverClassName = self.class ? self.class.className + ' ' : '';
 28245           callWriter.enter('call super ' + receiverClassName + name + '(' + toSafeArrayString(args) + ') #' + callCounter.count(name));
 28247         var baseClass = scope.object.baseClass;
 28248         var resolved = baseClass.traitsPrototype.resolveMultinameProperty(namespaces, name, flags);
 28249         var openMethods = baseClass.traitsPrototype.asOpenMethods;
 28250         var method = openMethods[resolved];
 28251         var result = method.apply(this, args);
 28252         Runtime.traceCallExecution.value > 0 && callWriter.leave('return ' + toSafeString(result));
 28253         return result;
 28255       Runtime.asCallSuper = asCallSuper;
 28256       function asSetSuper(scope, namespaces, name, flags, value) {
 28257         var self = this;
 28258         if (Runtime.traceCallExecution.value) {
 28259           var receiverClassName = self.class ? self.class.className + ' ' : '';
 28260           callWriter.enter('set super ' + receiverClassName + name + '(' + toSafeString(value) + ') #' + callCounter.count(name));
 28262         var baseClass = scope.object.baseClass;
 28263         var resolved = baseClass.traitsPrototype.resolveMultinameProperty(namespaces, name, flags);
 28264         if (self.asSlots.byQN[resolved]) {
 28265           this.asSetProperty(namespaces, name, flags, value);
 28266         } else {
 28267           baseClass.traitsPrototype[Runtime.VM_OPEN_SET_METHOD_PREFIX + resolved].call(this, value);
 28269         Runtime.traceCallExecution.value > 0 && callWriter.leave('');
 28271       Runtime.asSetSuper = asSetSuper;
 28272       function asGetSuper(scope, namespaces, name, flags) {
 28273         var self = this;
 28274         if (Runtime.traceCallExecution.value) {
 28275           var receiver = self.class ? self.class.className + ' ' : '';
 28276           callWriter.enter('get super ' + receiver + name + ' #' + callCounter.count(name));
 28278         var baseClass = scope.object.baseClass;
 28279         var resolved = baseClass.traitsPrototype.resolveMultinameProperty(namespaces, name, flags);
 28280         var result;
 28281         if (self.asSlots.byQN[resolved]) {
 28282           result = this.asGetProperty(namespaces, name, flags);
 28283         } else {
 28284           result = baseClass.traitsPrototype[Runtime.VM_OPEN_GET_METHOD_PREFIX + resolved].call(this);
 28286         Runtime.traceCallExecution.value > 0 && callWriter.leave('return ' + toSafeString(result));
 28287         return result;
 28289       Runtime.asGetSuper = asGetSuper;
 28290       function construct(cls, args) {
 28291         if (cls.classInfo) {
 28292           var qn = Multiname.getQualifiedName(cls.classInfo.instanceInfo.name);
 28293           if (qn === Multiname.String) {
 28294             return String.apply(null, args);
 28296           if (qn === Multiname.Boolean) {
 28297             return Boolean.apply(null, args);
 28299           if (qn === Multiname.Number) {
 28300             return Number.apply(null, args);
 28303         var c = cls.instanceConstructor;
 28304         var a = args;
 28305         switch (args.length) {
 28306         case 0:
 28307           return new c();
 28308         case 1:
 28309           return new c(a[0]);
 28310         case 2:
 28311           return new c(a[0], a[1]);
 28312         case 3:
 28313           return new c(a[0], a[1], a[2]);
 28314         case 4:
 28315           return new c(a[0], a[1], a[2], a[3]);
 28316         case 5:
 28317           return new c(a[0], a[1], a[2], a[3], a[4]);
 28318         case 6:
 28319           return new c(a[0], a[1], a[2], a[3], a[4], a[5]);
 28320         case 7:
 28321           return new c(a[0], a[1], a[2], a[3], a[4], a[5], a[6]);
 28322         case 8:
 28323           return new c(a[0], a[1], a[2], a[3], a[4], a[5], a[6], a[7]);
 28324         case 9:
 28325           return new c(a[0], a[1], a[2], a[3], a[4], a[5], a[6], a[7], a[8]);
 28326         case 10:
 28327           return new c(a[0], a[1], a[2], a[3], a[4], a[5], a[6], a[7], a[8], a[9]);
 28329         var applyArguments = [];
 28330         for (var i = 0; i < args.length; i++) {
 28331           applyArguments[i + 1] = args[i];
 28333         return new (Function.bind.apply(c, applyArguments))();
 28335       Runtime.construct = construct;
 28336       function asConstructProperty(namespaces, name, flags, args) {
 28337         var self = this;
 28338         var constructor = self.asGetProperty(namespaces, name, flags);
 28339         if (Runtime.traceCallExecution.value) {
 28340           callWriter.enter('construct ' + name + '(' + toSafeArrayString(args) + ') #' + callCounter.count(name));
 28342         var result = construct(constructor, args);
 28343         Runtime.traceCallExecution.value > 0 && callWriter.leave('return ' + toSafeString(result));
 28344         return result;
 28346       Runtime.asConstructProperty = asConstructProperty;
 28347       function nonProxyingHasProperty(object, name) {
 28348         return name in object;
 28350       Runtime.nonProxyingHasProperty = nonProxyingHasProperty;
 28351       function asHasProperty(namespaces, name, flags, nonProxy) {
 28352         var self = this;
 28353         if (self.hasProperty) {
 28354           return self.hasProperty(namespaces, name, flags);
 28356         if (nonProxy) {
 28357           return nonProxyingHasProperty(self, self.resolveMultinameProperty(namespaces, name, flags));
 28358         } else {
 28359           return self.resolveMultinameProperty(namespaces, name, flags) in this;
 28362       Runtime.asHasProperty = asHasProperty;
 28363       function asDeleteProperty(namespaces, name, flags) {
 28364         var self = this;
 28365         if (self.asHasTraitProperty(namespaces, name, flags)) {
 28366           return false;
 28368         var resolved = self.resolveMultinameProperty(namespaces, name, flags);
 28369         return delete self[resolved];
 28371       Runtime.asDeleteProperty = asDeleteProperty;
 28372       function asHasTraitProperty(namespaces, name, flags) {
 28373         var self = this;
 28374         var resolved = self.resolveMultinameProperty(namespaces, name, flags);
 28375         return self.asBindings.indexOf(resolved) >= 0;
 28377       Runtime.asHasTraitProperty = asHasTraitProperty;
 28378       function asGetNumericProperty(i) {
 28379         return this[i];
 28381       Runtime.asGetNumericProperty = asGetNumericProperty;
 28382       function asSetNumericProperty(i, v) {
 28383         this[i] = v;
 28385       Runtime.asSetNumericProperty = asSetNumericProperty;
 28386       function asGetDescendants(namespaces, name, flags) {
 28387         Shumway.Debug.notImplemented('asGetDescendants');
 28389       Runtime.asGetDescendants = asGetDescendants;
 28390       function asNextNameIndex(index) {
 28391         var self = this;
 28392         if (index === 0) {
 28393           defineNonEnumerableProperty(self, 'asEnumerableKeys', self.asGetEnumerableKeys());
 28395         var asEnumerableKeys = self.asEnumerableKeys;
 28396         while (index < asEnumerableKeys.length) {
 28397           if (self.asHasProperty(undefined, asEnumerableKeys[index], 0)) {
 28398             return index + 1;
 28400           index++;
 28402         return 0;
 28404       Runtime.asNextNameIndex = asNextNameIndex;
 28405       function asNextName(index) {
 28406         var self = this;
 28407         var asEnumerableKeys = self.asEnumerableKeys;
 28408         true;
 28409         return asEnumerableKeys[index - 1];
 28411       Runtime.asNextName = asNextName;
 28412       function asNextValue(index) {
 28413         return this.asGetPublicProperty(this.asNextName(index));
 28415       Runtime.asNextValue = asNextValue;
 28416       function asGetEnumerableKeys() {
 28417         var self = this;
 28418         var boxedValue = self.valueOf();
 28419         if (typeof boxedValue === 'string' || typeof boxedValue === 'number') {
 28420           return [];
 28422         var keys = Object.keys(this);
 28423         var result = [];
 28424         for (var i = 0; i < keys.length; i++) {
 28425           var key = keys[i];
 28426           if (Shumway.isNumeric(key)) {
 28427             result.push(key);
 28428           } else {
 28429             var name = Multiname.stripPublicQualifier(key);
 28430             if (name !== undefined) {
 28431               result.push(name);
 28435         return result;
 28437       Runtime.asGetEnumerableKeys = asGetEnumerableKeys;
 28438       function asTypeOf(x) {
 28439         if (x) {
 28440           if (x.constructor === String) {
 28441             return 'string';
 28442           } else if (x.constructor === Number) {
 28443             return 'number';
 28444           } else if (x.constructor === Boolean) {
 28445             return 'boolean';
 28446           } else if (x instanceof XML || x instanceof XMLList) {
 28447             return 'xml';
 28450         return typeof x;
 28452       Runtime.asTypeOf = asTypeOf;
 28453       function publicizeProperties(object) {
 28454         var keys = Object.keys(object);
 28455         for (var i = 0; i < keys.length; i++) {
 28456           var k = keys[i];
 28457           if (!Multiname.isPublicQualifiedName(k)) {
 28458             var v = object[k];
 28459             object[Multiname.getPublicQualifiedName(k)] = v;
 28460             delete object[k];
 28464       Runtime.publicizeProperties = publicizeProperties;
 28465       function asGetSlot(object, index) {
 28466         return object[object.asSlots.byID[index].name];
 28468       Runtime.asGetSlot = asGetSlot;
 28469       function asSetSlot(object, index, value) {
 28470         var slotInfo = object.asSlots.byID[index];
 28471         if (slotInfo.const) {
 28472           return;
 28474         var name = slotInfo.name;
 28475         var type = slotInfo.type;
 28476         if (type && type.coerce) {
 28477           object[name] = type.coerce(value);
 28478         } else {
 28479           object[name] = value;
 28482       Runtime.asSetSlot = asSetSlot;
 28483       function throwError(name, error) {
 28484         if (true) {
 28485           var message = Shumway.AVM2.formatErrorMessage.apply(null, Array.prototype.slice.call(arguments, 1));
 28486           throwErrorFromVM(Shumway.AVM2.Runtime.AVM2.currentDomain(), name, message, error.code);
 28487         } else {
 28488           throwErrorFromVM(Shumway.AVM2.Runtime.AVM2.currentDomain(), name, Shumway.AVM2.getErrorMessage(error.code), error.code);
 28491       Runtime.throwError = throwError;
 28492       function throwErrorFromVM(domain, errorClass, message, id) {
 28493         var error = new (domain.getClass(errorClass)).instanceConstructor(message, id);
 28494         throw error;
 28496       Runtime.throwErrorFromVM = throwErrorFromVM;
 28497       function translateError(domain, error) {
 28498         if (error instanceof Error) {
 28499           var type = domain.getClass(error.name);
 28500           if (type) {
 28501             return new type.instanceConstructor(Shumway.AVM2.translateErrorMessage(error));
 28503           Shumway.Debug.unexpected('Can\'t translate error: ' + error);
 28505         return error;
 28507       Runtime.translateError = translateError;
 28508       function asIsInstanceOf(type, value) {
 28509         return type.isInstanceOf(value);
 28511       Runtime.asIsInstanceOf = asIsInstanceOf;
 28512       function asIsType(type, value) {
 28513         return type.isInstance(value);
 28515       Runtime.asIsType = asIsType;
 28516       function asAsType(type, value) {
 28517         return asIsType(type, value) ? value : null;
 28519       Runtime.asAsType = asAsType;
 28520       function asCoerceByMultiname(domain, multiname, value) {
 28521         true;
 28522         switch (Multiname.getQualifiedName(multiname)) {
 28523         case Multiname.Int:
 28524           return asCoerceInt(value);
 28525         case Multiname.Uint:
 28526           return asCoerceUint(value);
 28527         case Multiname.String:
 28528           return asCoerceString(value);
 28529         case Multiname.Number:
 28530           return asCoerceNumber(value);
 28531         case Multiname.Boolean:
 28532           return asCoerceBoolean(value);
 28533         case Multiname.Object:
 28534           return asCoerceObject(value);
 28536         return asCoerce(domain.getType(multiname), value);
 28538       Runtime.asCoerceByMultiname = asCoerceByMultiname;
 28539       function asCoerce(type, value) {
 28540         if (type.coerce) {
 28541           return type.coerce(value);
 28543         if (Shumway.isNullOrUndefined(value)) {
 28544           return null;
 28546         if (type.isInstance(value)) {
 28547           return value;
 28548         } else {
 28549           true;
 28552       Runtime.asCoerce = asCoerce;
 28553       function asCoerceString(x) {
 28554         if (typeof x === 'string') {
 28555           return x;
 28556         } else if (x == undefined) {
 28557           return null;
 28559         return x + '';
 28561       Runtime.asCoerceString = asCoerceString;
 28562       function asCoerceInt(x) {
 28563         return x | 0;
 28565       Runtime.asCoerceInt = asCoerceInt;
 28566       function asCoerceUint(x) {
 28567         return x >>> 0;
 28569       Runtime.asCoerceUint = asCoerceUint;
 28570       function asCoerceNumber(x) {
 28571         return +x;
 28573       Runtime.asCoerceNumber = asCoerceNumber;
 28574       function asCoerceBoolean(x) {
 28575         return !(!x);
 28577       Runtime.asCoerceBoolean = asCoerceBoolean;
 28578       function asCoerceObject(x) {
 28579         if (x == undefined) {
 28580           return null;
 28582         if (typeof x === 'string' || typeof x === 'number') {
 28583           return x;
 28585         return Object(x);
 28587       Runtime.asCoerceObject = asCoerceObject;
 28588       function asDefaultCompareFunction(a, b) {
 28589         return String(a).localeCompare(String(b));
 28591       Runtime.asDefaultCompareFunction = asDefaultCompareFunction;
 28592       function asCompare(a, b, options, compareFunction) {
 28593         true;
 28594         true;
 28595         var result = 0;
 28596         if (!compareFunction) {
 28597           compareFunction = asDefaultCompareFunction;
 28599         if (options & 1) {
 28600           a = String(a).toLowerCase();
 28601           b = String(b).toLowerCase();
 28603         if (options & 16) {
 28604           a = Shumway.toNumber(a);
 28605           b = Shumway.toNumber(b);
 28606           result = a < b ? -1 : a > b ? 1 : 0;
 28607         } else {
 28608           result = compareFunction(a, b);
 28610         if (options & 2) {
 28611           result *= -1;
 28613         return result;
 28615       Runtime.asCompare = asCompare;
 28616       function asAdd(l, r) {
 28617         if (typeof l === 'string' || typeof r === 'string') {
 28618           return String(l) + String(r);
 28620         return l + r;
 28622       Runtime.asAdd = asAdd;
 28623       function asHasNext2(object, index) {
 28624         if (Shumway.isNullOrUndefined(object)) {
 28625           return {
 28626             index: 0,
 28627             object: null
 28628           };
 28630         object = boxValue(object);
 28631         var nextIndex = object.asNextNameIndex(index);
 28632         if (nextIndex > 0) {
 28633           return {
 28634             index: nextIndex,
 28635             object: object
 28636           };
 28638         while (true) {
 28639           var object = Object.getPrototypeOf(object);
 28640           if (!object) {
 28641             return {
 28642               index: 0,
 28643               object: null
 28644             };
 28646           nextIndex = object.asNextNameIndex(0);
 28647           if (nextIndex > 0) {
 28648             return {
 28649               index: nextIndex,
 28650               object: object
 28651             };
 28654         return {
 28655           index: 0,
 28656           object: null
 28657         };
 28659       Runtime.asHasNext2 = asHasNext2;
 28660       function getDescendants(object, mn) {
 28661         if (!isXMLType(object)) {
 28662           throw 'Not XML object in getDescendants';
 28664         return object.descendants(mn);
 28666       Runtime.getDescendants = getDescendants;
 28667       function checkFilter(value) {
 28668         if (!value.class || !isXMLType(value)) {
 28669           throw 'TypeError operand of childFilter not of XML type';
 28671         return value;
 28673       Runtime.checkFilter = checkFilter;
 28674       function initializeGlobalObject(global) {
 28675         var VM_NATIVE_BUILTIN_SURROGATES = [
 28677               name: 'Object',
 28678               methods: [
 28679                 'toString',
 28680                 'valueOf'
 28682             },
 28684               name: 'Function',
 28685               methods: [
 28686                 'toString',
 28687                 'valueOf'
 28690           ];
 28691         var originals = global[Runtime.VM_NATIVE_BUILTIN_ORIGINALS] = createEmptyObject();
 28692         VM_NATIVE_BUILTIN_SURROGATES.forEach(function (surrogate) {
 28693           var object = global[surrogate.name];
 28694           originals[surrogate.name] = createEmptyObject();
 28695           surrogate.methods.forEach(function (originalFunctionName) {
 28696             var originalFunction;
 28697             if (object.prototype.hasOwnProperty(originalFunctionName)) {
 28698               originalFunction = object.prototype[originalFunctionName];
 28699             } else {
 28700               originalFunction = originals['Object'][originalFunctionName];
 28702             originals[surrogate.name][originalFunctionName] = originalFunction;
 28703             var overrideFunctionName = Multiname.getPublicQualifiedName(originalFunctionName);
 28704             if (useSurrogates) {
 28705               global[surrogate.name].prototype[originalFunctionName] = function surrogate() {
 28706                 if (this[overrideFunctionName]) {
 28707                   return this[overrideFunctionName]();
 28709                 return originalFunction.call(this);
 28710               };
 28712           });
 28713         });
 28715           'Object',
 28716           'Number',
 28717           'Boolean',
 28718           'String',
 28719           'Array',
 28720           'Date',
 28721           'RegExp'
 28722         ].forEach(function (name) {
 28723           defineReadOnlyProperty(global[name].prototype, Runtime.VM_NATIVE_PROTOTYPE_FLAG, true);
 28724         });
 28725         defineNonEnumerableProperty(global.Object.prototype, 'getNamespaceResolutionMap', getNamespaceResolutionMap);
 28726         defineNonEnumerableProperty(global.Object.prototype, 'resolveMultinameProperty', resolveMultinameProperty);
 28727         defineNonEnumerableProperty(global.Object.prototype, 'asGetProperty', asGetProperty);
 28728         defineNonEnumerableProperty(global.Object.prototype, 'asGetPublicProperty', asGetPublicProperty);
 28729         defineNonEnumerableProperty(global.Object.prototype, 'asGetResolvedStringProperty', asGetResolvedStringProperty);
 28730         defineNonEnumerableProperty(global.Object.prototype, 'asSetProperty', asSetProperty);
 28731         defineNonEnumerableProperty(global.Object.prototype, 'asSetPublicProperty', asSetPublicProperty);
 28732         defineNonEnumerableProperty(global.Object.prototype, 'asDefineProperty', asDefineProperty);
 28733         defineNonEnumerableProperty(global.Object.prototype, 'asDefinePublicProperty', asDefinePublicProperty);
 28734         defineNonEnumerableProperty(global.Object.prototype, 'asCallProperty', asCallProperty);
 28735         defineNonEnumerableProperty(global.Object.prototype, 'asCallSuper', asCallSuper);
 28736         defineNonEnumerableProperty(global.Object.prototype, 'asGetSuper', asGetSuper);
 28737         defineNonEnumerableProperty(global.Object.prototype, 'asSetSuper', asSetSuper);
 28738         defineNonEnumerableProperty(global.Object.prototype, 'asCallPublicProperty', asCallPublicProperty);
 28739         defineNonEnumerableProperty(global.Object.prototype, 'asCallResolvedStringProperty', asCallResolvedStringProperty);
 28740         defineNonEnumerableProperty(global.Object.prototype, 'asConstructProperty', asConstructProperty);
 28741         defineNonEnumerableProperty(global.Object.prototype, 'asHasProperty', asHasProperty);
 28742         defineNonEnumerableProperty(global.Object.prototype, 'asHasTraitProperty', asHasTraitProperty);
 28743         defineNonEnumerableProperty(global.Object.prototype, 'asDeleteProperty', asDeleteProperty);
 28744         defineNonEnumerableProperty(global.Object.prototype, 'asNextName', asNextName);
 28745         defineNonEnumerableProperty(global.Object.prototype, 'asNextValue', asNextValue);
 28746         defineNonEnumerableProperty(global.Object.prototype, 'asNextNameIndex', asNextNameIndex);
 28747         defineNonEnumerableProperty(global.Object.prototype, 'asGetEnumerableKeys', asGetEnumerableKeys);
 28749           'Array',
 28750           'Int8Array',
 28751           'Uint8Array',
 28752           'Uint8ClampedArray',
 28753           'Int16Array',
 28754           'Uint16Array',
 28755           'Int32Array',
 28756           'Uint32Array',
 28757           'Float32Array',
 28758           'Float64Array'
 28759         ].forEach(function (name) {
 28760           if (!(name in global)) {
 28761             log(name + ' was not found in globals');
 28762             return;
 28764           defineNonEnumerableProperty(global[name].prototype, 'asGetNumericProperty', asGetNumericProperty);
 28765           defineNonEnumerableProperty(global[name].prototype, 'asSetNumericProperty', asSetNumericProperty);
 28766           defineNonEnumerableProperty(global[name].prototype, 'asGetProperty', asGetPropertyLikelyNumeric);
 28767           defineNonEnumerableProperty(global[name].prototype, 'asSetProperty', asSetPropertyLikelyNumeric);
 28768         });
 28769         global.Array.prototype.asGetProperty = function (namespaces, name, flags) {
 28770           if (typeof name === 'number') {
 28771             return this[name];
 28773           return asGetProperty.call(this, namespaces, name, flags);
 28774         };
 28775         global.Array.prototype.asSetProperty = function (namespaces, name, flags, value) {
 28776           if (typeof name === 'number') {
 28777             this[name] = value;
 28778             return;
 28780           return asSetProperty.call(this, namespaces, name, flags, value);
 28781         };
 28783       Runtime.initializeGlobalObject = initializeGlobalObject;
 28784       function nameInTraits(object, qn) {
 28785         if (object.hasOwnProperty(Runtime.VM_BINDINGS) && object.hasOwnProperty(qn)) {
 28786           return true;
 28788         var proto = Object.getPrototypeOf(object);
 28789         return proto.hasOwnProperty(Runtime.VM_BINDINGS) && proto.hasOwnProperty(qn);
 28791       Runtime.nameInTraits = nameInTraits;
 28792       function CatchScopeObject(domain, trait) {
 28793         if (trait) {
 28794           new Shumway.AVM2.Runtime.CatchBindings(new Shumway.AVM2.Runtime.Scope(null, this), trait).applyTo(domain, this);
 28797       Runtime.CatchScopeObject = CatchScopeObject;
 28798       var Global = function () {
 28799           function Global(script) {
 28800             this.scriptInfo = script;
 28801             script.global = this;
 28802             this.scriptBindings = new Shumway.AVM2.Runtime.ScriptBindings(script, new Shumway.AVM2.Runtime.Scope(null, this, false));
 28803             this.scriptBindings.applyTo(script.abc.applicationDomain, this);
 28804             script.loaded = true;
 28806           Global.prototype.toString = function () {
 28807             return '[object global]';
 28808           };
 28809           Global.prototype.isExecuted = function () {
 28810             return this.scriptInfo.executed;
 28811           };
 28812           Global.prototype.isExecuting = function () {
 28813             return this.scriptInfo.executing;
 28814           };
 28815           Global.prototype.ensureExecuted = function () {
 28816             Shumway.AVM2.Runtime.ensureScriptIsExecuted(this.scriptInfo);
 28817           };
 28818           return Global;
 28819         }();
 28820       Runtime.Global = Global;
 28821       defineNonEnumerableProperty(Global.prototype, Multiname.getPublicQualifiedName('toString'), function () {
 28822         return this.toString();
 28823       });
 28824       var LazyInitializer = function () {
 28825           function LazyInitializer(target) {
 28826             this.target = target;
 28828           LazyInitializer.create = function (target) {
 28829             if (target.asLazyInitializer) {
 28830               return target.asLazyInitializer;
 28832             return target.asLazyInitializer = new LazyInitializer(target);
 28833           };
 28834           LazyInitializer.prototype.getName = function () {
 28835             if (this.name) {
 28836               return this.name;
 28838             var target = this.target, initialize;
 28839             if (this.target instanceof ScriptInfo) {
 28840               var scriptInfo = target;
 28841               this.name = '$' + Shumway.StringUtilities.variableLengthEncodeInt32(scriptInfo.hash);
 28842               initialize = function () {
 28843                 Shumway.AVM2.Runtime.ensureScriptIsExecuted(target, 'Lazy Initializer');
 28844                 return scriptInfo.global;
 28845               };
 28846             } else if (this.target instanceof ClassInfo) {
 28847               var classInfo = target;
 28848               this.name = '$' + Shumway.StringUtilities.variableLengthEncodeInt32(classInfo.hash);
 28849               initialize = function () {
 28850                 if (classInfo.classObject) {
 28851                   return classInfo.classObject;
 28853                 return classInfo.abc.applicationDomain.getProperty(classInfo.instanceInfo.name);
 28854               };
 28855             } else {
 28856               Shumway.Debug.notImplemented(String(target));
 28858             var name = this.name;
 28859             Object.defineProperty(LazyInitializer._holder, name, {
 28860               get: function () {
 28861                 var value = initialize();
 28862                 Object.defineProperty(LazyInitializer._holder, name, {
 28863                   value: value,
 28864                   writable: true
 28865                 });
 28866                 return value;
 28867               },
 28868               configurable: true
 28869             });
 28870             return name;
 28871           };
 28872           LazyInitializer._holder = jsGlobal;
 28873           return LazyInitializer;
 28874         }();
 28875       Runtime.LazyInitializer = LazyInitializer;
 28876       function forEachPublicProperty(object, fn, self) {
 28877         if (!object.asBindings) {
 28878           for (var key in object) {
 28879             fn.call(self, key, object[key]);
 28881           return;
 28883         for (var key in object) {
 28884           if (Shumway.isNumeric(key)) {
 28885             fn.call(self, key, object[key]);
 28886           } else if (Multiname.isPublicQualifiedName(key) && object.asBindings.indexOf(key) < 0) {
 28887             var name = Multiname.stripPublicQualifier(key);
 28888             fn.call(self, name, object[key]);
 28892       Runtime.forEachPublicProperty = forEachPublicProperty;
 28893       function wrapJSObject(object) {
 28894         var wrapper = Object.create(object);
 28895         for (var i in object) {
 28896           Object.defineProperty(wrapper, Multiname.getPublicQualifiedName(i), function (object, i) {
 28897             return {
 28898               get: function () {
 28899                 return object[i];
 28900               },
 28901               set: function (value) {
 28902                 object[i] = value;
 28903               },
 28904               enumerable: true
 28905             };
 28906           }(object, i));
 28908         return wrapper;
 28910       Runtime.wrapJSObject = wrapJSObject;
 28911       function asCreateActivation(methodInfo) {
 28912         return Object.create(methodInfo.activationPrototype);
 28914       Runtime.asCreateActivation = asCreateActivation;
 28915       var GlobalMultinameResolver = function () {
 28916           function GlobalMultinameResolver() {
 28918           GlobalMultinameResolver.updateTraits = function (traits) {
 28919             for (var i = 0; i < traits.length; i++) {
 28920               var trait = traits[i];
 28921               var name = trait.name.name;
 28922               var namespace = trait.name.getNamespace();
 28923               if (!namespace.isDynamic()) {
 28924                 GlobalMultinameResolver.hasNonDynamicNamespaces[name] = true;
 28925                 if (GlobalMultinameResolver.wasResolved[name]) {
 28926                   Shumway.Debug.notImplemented('We have to the undo the optimization, ' + name + ' can now bind to ' + namespace);
 28930           };
 28931           GlobalMultinameResolver.loadAbc = function (abc) {
 28932             if (!Runtime.globalMultinameAnalysis.value) {
 28933               return;
 28935             var scripts = abc.scripts;
 28936             var classes = abc.classes;
 28937             var methods = abc.methods;
 28938             for (var i = 0; i < scripts.length; i++) {
 28939               GlobalMultinameResolver.updateTraits(scripts[i].traits);
 28941             for (var i = 0; i < classes.length; i++) {
 28942               GlobalMultinameResolver.updateTraits(classes[i].traits);
 28943               GlobalMultinameResolver.updateTraits(classes[i].instanceInfo.traits);
 28945             for (var i = 0; i < methods.length; i++) {
 28946               if (methods[i].traits) {
 28947                 GlobalMultinameResolver.updateTraits(methods[i].traits);
 28950           };
 28951           GlobalMultinameResolver.resolveMultiname = function (multiname) {
 28952             var name = multiname.name;
 28953             if (GlobalMultinameResolver.hasNonDynamicNamespaces[name]) {
 28954               return;
 28956             GlobalMultinameResolver.wasResolved[name] = true;
 28957             return new Multiname([
 28958               Namespace.PUBLIC
 28959             ], multiname.name);
 28960           };
 28961           GlobalMultinameResolver.hasNonDynamicNamespaces = createEmptyObject();
 28962           GlobalMultinameResolver.wasResolved = createEmptyObject();
 28963           return GlobalMultinameResolver;
 28964         }();
 28965       Runtime.GlobalMultinameResolver = GlobalMultinameResolver;
 28966       var ActivationInfo = function () {
 28967           function ActivationInfo(methodInfo) {
 28968             this.methodInfo = methodInfo;
 28970           return ActivationInfo;
 28971         }();
 28972       Runtime.ActivationInfo = ActivationInfo;
 28973       function sliceArguments(args, offset) {
 28974         if (typeof offset === 'undefined') {
 28975           offset = 0;
 28977         return Array.prototype.slice.call(args, offset);
 28979       Runtime.sliceArguments = sliceArguments;
 28980       function canCompile(mi) {
 28981         if (!mi.hasBody) {
 28982           return false;
 28984         if (mi.hasExceptions() && !compilerEnableExceptions.value) {
 28985           return false;
 28986         } else if (mi.code.length > compilerMaximumMethodSize.value) {
 28987           return false;
 28989         return true;
 28991       Runtime.canCompile = canCompile;
 28992       function shouldCompile(mi) {
 28993         if (!canCompile(mi)) {
 28994           return false;
 28996         if (mi.isClassInitializer || mi.isScriptInitializer) {
 28997           return false;
 28999         return true;
 29001       Runtime.shouldCompile = shouldCompile;
 29002       function forceCompile(mi) {
 29003         if (mi.hasExceptions()) {
 29004           return false;
 29006         var holder = mi.holder;
 29007         if (holder instanceof ClassInfo) {
 29008           holder = holder.instanceInfo;
 29010         if (holder instanceof InstanceInfo) {
 29011           var packageName = holder.name.namespaces[0].uri;
 29012           switch (packageName) {
 29013           case 'flash.geom':
 29014           case 'flash.events':
 29015             return true;
 29016           default:
 29017             break;
 29019           var className = holder.name.getOriginalName();
 29020           switch (className) {
 29021           case 'com.google.youtube.model.VideoData':
 29022             return true;
 29025         return false;
 29027       Runtime.forceCompile = forceCompile;
 29028       Runtime.CODE_CACHE = createEmptyObject();
 29029       function searchCodeCache(methodInfo) {
 29030         if (!Runtime.codeCaching.value) {
 29031           return;
 29033         var cacheInfo = Runtime.CODE_CACHE[methodInfo.abc.hash];
 29034         if (!cacheInfo) {
 29035           warn('Cannot Find Code Cache For ABC, name: ' + methodInfo.abc.name + ', hash: ' + methodInfo.abc.hash);
 29036           Counter.count('Code Cache ABC Miss');
 29037           return;
 29039         if (!cacheInfo.isInitialized) {
 29040           methodInfo.abc.scripts.forEach(function (scriptInfo) {
 29041             LazyInitializer.create(scriptInfo).getName();
 29042           });
 29043           methodInfo.abc.classes.forEach(function (classInfo) {
 29044             LazyInitializer.create(classInfo).getName();
 29045           });
 29046           cacheInfo.isInitialized = true;
 29048         var method = cacheInfo.methods[methodInfo.index];
 29049         if (!method) {
 29050           if (methodInfo.isInstanceInitializer || methodInfo.isClassInitializer) {
 29051             Counter.count('Code Cache Query On Initializer');
 29052           } else {
 29053             Counter.count('Code Cache MISS ON OTHER');
 29054             warn('Shouldn\'t MISS: ' + methodInfo + ' ' + methodInfo.debugName);
 29056           Counter.count('Code Cache Miss');
 29057           return;
 29059         log('Linking CC: ' + methodInfo);
 29060         Counter.count('Code Cache Hit');
 29061         return method;
 29063       Runtime.searchCodeCache = searchCodeCache;
 29064       function createInterpretedFunction(methodInfo, scope, hasDynamicScope) {
 29065         var mi = methodInfo;
 29066         var hasDefaults = false;
 29067         var defaults = mi.parameters.map(function (p) {
 29068             if (p.value !== undefined) {
 29069               hasDefaults = true;
 29071             return p.value;
 29072           });
 29073         var fn;
 29074         if (hasDynamicScope) {
 29075           fn = function (scope) {
 29076             var global = this === jsGlobal ? scope.global.object : this;
 29077             var args = sliceArguments(arguments, 1);
 29078             if (hasDefaults && args.length < defaults.length) {
 29079               args = args.concat(defaults.slice(args.length - defaults.length));
 29081             return Shumway.AVM2.Interpreter.interpretMethod(global, methodInfo, scope, args);
 29082           };
 29083         } else {
 29084           fn = function () {
 29085             var global = this === jsGlobal ? scope.global.object : this;
 29086             var args = sliceArguments(arguments);
 29087             if (hasDefaults && args.length < defaults.length) {
 29088               args = args.concat(defaults.slice(arguments.length - defaults.length));
 29090             return Shumway.AVM2.Interpreter.interpretMethod(global, methodInfo, scope, args);
 29091           };
 29093         fn.instanceConstructor = fn;
 29094         fn.debugName = 'Interpreter Function #' + vmNextInterpreterFunctionId++;
 29095         return fn;
 29097       Runtime.createInterpretedFunction = createInterpretedFunction;
 29098       function debugName(value) {
 29099         if (Shumway.isFunction(value)) {
 29100           return value.debugName;
 29102         return value;
 29104       Runtime.debugName = debugName;
 29105       function createCompiledFunction(methodInfo, scope, hasDynamicScope, breakpoint, deferCompilation) {
 29106         var mi = methodInfo;
 29107         var cached = searchCodeCache(mi);
 29108         if (!cached) {
 29109           var result = Compiler.compileMethod(mi, scope, hasDynamicScope);
 29110           var parameters = result.parameters;
 29111           var body = result.body;
 29113         var fnName = mi.name ? Multiname.getQualifiedName(mi.name) : 'fn' + compiledFunctionCount;
 29114         if (mi.holder) {
 29115           var fnNamePrefix = '';
 29116           if (mi.holder instanceof ClassInfo) {
 29117             fnNamePrefix = 'static$' + mi.holder.instanceInfo.name.getName();
 29118           } else if (mi.holder instanceof InstanceInfo) {
 29119             fnNamePrefix = mi.holder.name.getName();
 29120           } else if (mi.holder instanceof ScriptInfo) {
 29121             fnNamePrefix = 'script';
 29123           fnName = fnNamePrefix + '$' + fnName;
 29125         fnName = Shumway.StringUtilities.escapeString(fnName);
 29126         if (mi.verified) {
 29127           fnName += '$V';
 29129         if (compiledFunctionCount == functionBreak.value || breakpoint) {
 29130           body = '{ debugger; \n' + body + '}';
 29132         if (!cached) {
 29133           var fnSource = 'function ' + fnName + ' (' + parameters.join(', ') + ') ' + body;
 29135         if (traceLevel.value > 1) {
 29136           mi.trace(new IndentingWriter(), mi.abc);
 29138         mi.debugTrace = function () {
 29139           mi.trace(new IndentingWriter(), mi.abc);
 29140         };
 29141         if (traceLevel.value > 0) {
 29142           log(fnSource);
 29144         var fn = cached || new Function('return ' + fnSource)();
 29145         fn.debugName = 'Compiled Function #' + vmNextCompiledFunctionId++;
 29146         return fn;
 29148       Runtime.createCompiledFunction = createCompiledFunction;
 29149       function createFunction(mi, scope, hasDynamicScope, breakpoint) {
 29150         if (typeof breakpoint === 'undefined') {
 29151           breakpoint = false;
 29153         true;
 29154         if (mi.freeMethod) {
 29155           if (hasDynamicScope) {
 29156             return Shumway.AVM2.Runtime.bindFreeMethodScope(mi, scope);
 29158           return mi.freeMethod;
 29160         var fn;
 29161         if (fn = Shumway.AVM2.Runtime.checkMethodOverrides(mi)) {
 29162           true;
 29163           return fn;
 29165         ensureFunctionIsInitialized(mi);
 29166         totalFunctionCount++;
 29167         var useInterpreter = false;
 29168         if ((mi.abc.applicationDomain.mode === 1 || !shouldCompile(mi)) && !forceCompile(mi)) {
 29169           useInterpreter = true;
 29171         if (compileOnly.value >= 0) {
 29172           if (Number(compileOnly.value) !== totalFunctionCount) {
 29173             log('Compile Only Skipping ' + totalFunctionCount);
 29174             useInterpreter = true;
 29177         if (compileUntil.value >= 0) {
 29178           if (totalFunctionCount > 1000) {
 29179             log(Shumway.Debug.backtrace());
 29180             log(Shumway.AVM2.Runtime.AVM2.getStackTrace());
 29182           if (totalFunctionCount > compileUntil.value) {
 29183             log('Compile Until Skipping ' + totalFunctionCount);
 29184             useInterpreter = true;
 29187         if (useInterpreter) {
 29188           mi.freeMethod = createInterpretedFunction(mi, scope, hasDynamicScope);
 29189         } else {
 29190           compiledFunctionCount++;
 29191           if (compileOnly.value >= 0 || compileUntil.value >= 0) {
 29192             log('Compiling ' + totalFunctionCount);
 29194           mi.freeMethod = createCompiledFunction(mi, scope, hasDynamicScope, breakpoint, mi.isInstanceInitializer);
 29196         mi.freeMethod.methodInfo = mi;
 29197         if (hasDynamicScope) {
 29198           return Shumway.AVM2.Runtime.bindFreeMethodScope(mi, scope);
 29200         return mi.freeMethod;
 29202       Runtime.createFunction = createFunction;
 29203       function ensureFunctionIsInitialized(methodInfo) {
 29204         var mi = methodInfo;
 29205         if (!mi.analysis) {
 29206           mi.analysis = new Analysis(mi);
 29207           if (mi.needsActivation()) {
 29208             mi.activationPrototype = new ActivationInfo(mi);
 29209             new Shumway.AVM2.Runtime.ActivationBindings(mi).applyTo(mi.abc.applicationDomain, mi.activationPrototype);
 29211           var exceptions = mi.exceptions;
 29212           for (var i = 0, j = exceptions.length; i < j; i++) {
 29213             var handler = exceptions[i];
 29214             if (handler.varName) {
 29215               var varTrait = Object.create(Trait.prototype);
 29216               varTrait.kind = 0;
 29217               varTrait.name = handler.varName;
 29218               varTrait.typeName = handler.typeName;
 29219               varTrait.holder = mi;
 29220               handler.scopeObject = new CatchScopeObject(mi.abc.applicationDomain, varTrait);
 29221             } else {
 29222               handler.scopeObject = new CatchScopeObject(undefined, undefined);
 29227       Runtime.ensureFunctionIsInitialized = ensureFunctionIsInitialized;
 29228       function getTraitFunction(trait, scope, natives) {
 29229         true;
 29230         true;
 29231         var mi = trait.methodInfo;
 29232         var fn;
 29233         if (mi.isNative()) {
 29234           var md = trait.metadata;
 29235           if (md && md.native) {
 29236             var nativeName = md.native.value[0].value;
 29237             var makeNativeFunction = getNative(nativeName);
 29238             fn = makeNativeFunction && makeNativeFunction(null, scope);
 29239           } else if (md && md.unsafeJSNative) {
 29240             fn = getNative(md.unsafeJSNative.value[0].value);
 29241           } else if (natives) {
 29242             var k = Multiname.getName(mi.name);
 29243             if (trait.isGetter()) {
 29244               fn = natives[k] ? natives[k].get : undefined;
 29245             } else if (trait.isSetter()) {
 29246               fn = natives[k] ? natives[k].set : undefined;
 29247             } else {
 29248               fn = natives[k];
 29251           if (!fn) {
 29252             Shumway.Debug.warning('No native method for: ' + trait.kindName() + ' ' + mi.holder.name + '::' + Multiname.getQualifiedName(mi.name));
 29253             return function (mi) {
 29254               return function () {
 29255                 Shumway.Debug.warning('Calling undefined native method: ' + trait.kindName() + ' ' + mi.holder.name + '::' + Multiname.getQualifiedName(mi.name));
 29256               };
 29257             }(mi);
 29259         } else {
 29260           if (Runtime.traceExecution.value >= 2) {
 29261             log('Creating Function For Trait: ' + trait.holder + ' ' + trait);
 29263           fn = createFunction(mi, scope, false, false);
 29264           true;
 29266         if (Runtime.traceExecution.value >= 3) {
 29267           log('Made Function: ' + Multiname.getQualifiedName(mi.name));
 29269         return fn;
 29271       Runtime.getTraitFunction = getTraitFunction;
 29272       function createClass(classInfo, baseClass, scope) {
 29273         true;
 29274         var ci = classInfo;
 29275         var ii = ci.instanceInfo;
 29276         var domain = ci.abc.applicationDomain;
 29277         var className = Multiname.getName(ii.name);
 29278         if (Runtime.traceExecution.value) {
 29279           log('Creating ' + (ii.isInterface() ? 'Interface' : 'Class') + ': ' + className + (ci.native ? ' replaced with native ' + ci.native.cls : ''));
 29281         var cls;
 29282         if (ii.isInterface()) {
 29283           cls = Shumway.AVM2.Runtime.Interface.createInterface(classInfo);
 29284         } else {
 29285           cls = Shumway.AVM2.Runtime.Class.createClass(classInfo, baseClass, scope);
 29287         if (Runtime.traceClasses.value) {
 29288           domain.loadedClasses.push(cls);
 29289           domain.traceLoadedClasses(true);
 29291         if (ii.isInterface()) {
 29292           return cls;
 29294         domain.onMessage.notify1('classCreated', cls);
 29295         if (cls.instanceConstructor && cls !== Shumway.AVM2.Runtime.Class) {
 29296           cls.verify();
 29298         if (baseClass && (Multiname.getQualifiedName(baseClass.classInfo.instanceInfo.name.name) === 'Proxy' || baseClass.isProxy)) {
 29299           installProxyClassWrapper(cls);
 29300           cls.isProxy = true;
 29302         classInfo.classObject = cls;
 29303         createFunction(classInfo.init, scope, false, false).call(cls);
 29304         if (Runtime.sealConstTraits) {
 29305           this.sealConstantTraits(cls, ci.traits);
 29307         return cls;
 29309       Runtime.createClass = createClass;
 29310       function sealConstantTraits(object, traits) {
 29311         for (var i = 0, j = traits.length; i < j; i++) {
 29312           var trait = traits[i];
 29313           if (trait.isConst()) {
 29314             var qn = Multiname.getQualifiedName(trait.name);
 29315             var value = object[qn];
 29316             (function (qn, value) {
 29317               Object.defineProperty(object, qn, {
 29318                 configurable: false,
 29319                 enumerable: false,
 29320                 get: function () {
 29321                   return value;
 29322                 },
 29323                 set: function () {
 29324                   throwErrorFromVM(Shumway.AVM2.Runtime.AVM2.currentDomain(), 'ReferenceError', 'Illegal write to read-only property ' + qn + '.', 0);
 29326               });
 29327             }(qn, value));
 29331       Runtime.sealConstantTraits = sealConstantTraits;
 29332       function applyType(domain, factory, types) {
 29333         var factoryClassName = factory.classInfo.instanceInfo.name.name;
 29334         if (factoryClassName === 'Vector') {
 29335           true;
 29336           var type = types[0];
 29337           var typeClassName;
 29338           if (!Shumway.isNullOrUndefined(type)) {
 29339             typeClassName = type.classInfo.instanceInfo.name.name.toLowerCase();
 29340             switch (typeClassName) {
 29341             case 'int':
 29342             case 'uint':
 29343             case 'double':
 29344             case 'object':
 29345               return domain.getClass('packageInternal __AS3__.vec.Vector$' + typeClassName);
 29348           return domain.getClass('packageInternal __AS3__.vec.Vector$object').applyType(type);
 29349         } else {
 29350           return Shumway.Debug.notImplemented(factoryClassName);
 29353       Runtime.applyType = applyType;
 29354     }(AVM2.Runtime || (AVM2.Runtime = {})));
 29355     var Runtime = AVM2.Runtime;
 29356   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 29357   var AVM2 = Shumway.AVM2;
 29358 }(Shumway || (Shumway = {})));
 29359 var CC = Shumway.AVM2.Runtime.CODE_CACHE;
 29360 var VM_LENGTH = Shumway.AVM2.Runtime.VM_LENGTH;
 29361 var VM_IS_PROXY = Shumway.AVM2.Runtime.VM_IS_PROXY;
 29362 var VM_CALL_PROXY = Shumway.AVM2.Runtime.VM_CALL_PROXY;
 29363 var VM_NATIVE_BUILTIN_ORIGINALS = Shumway.AVM2.Runtime.VM_NATIVE_BUILTIN_ORIGINALS;
 29364 var VM_OPEN_METHOD_PREFIX = 'm';
 29365 var VM_OPEN_SET_METHOD_PREFIX = 's';
 29366 var VM_OPEN_GET_METHOD_PREFIX = 'g';
 29367 var SAVED_SCOPE_NAME = '$SS';
 29368 var originalStringReplace = String.prototype.replace;
 29369 XRegExp.install({
 29370   natives: true
 29371 });
 29372 var callWriter = new IndentingWriter(false, function (str) {
 29373     print(str);
 29374   });
 29375 var objectIDs = 0;
 29376 var OBJECT_NAME = 'Object Name';
 29377 function objectConstantName(object) {
 29378   true;
 29379   if (object.hasOwnProperty(OBJECT_NAME)) {
 29380     return object[OBJECT_NAME];
 29382   if (object instanceof LazyInitializer) {
 29383     return object.getName();
 29385   var name, id = objectIDs++;
 29386   if (object instanceof Global) {
 29387     name = '$G' + id;
 29388   } else if (object instanceof Multiname) {
 29389     name = '$M' + id;
 29390   } else if (isClass(object)) {
 29391     name = '$C' + id;
 29392   } else {
 29393     name = '$O' + id;
 29395   Object.defineProperty(object, OBJECT_NAME, {
 29396     value: name,
 29397     writable: false,
 29398     enumerable: false
 29399   });
 29400   jsGlobal[name] = object;
 29401   return name;
 29403 var isClass = Shumway.AVM2.Runtime.isClass;
 29404 var isTrampoline = Shumway.AVM2.Runtime.isTrampoline;
 29405 var isMemoizer = Shumway.AVM2.Runtime.isMemoizer;
 29406 var LazyInitializer = Shumway.AVM2.Runtime.LazyInitializer;
 29407 var getNamespaceResolutionMap = Shumway.AVM2.Runtime.getNamespaceResolutionMap;
 29408 var resolveMultinameProperty = Shumway.AVM2.Runtime.resolveMultinameProperty;
 29409 var asGetPublicProperty = Shumway.AVM2.Runtime.asGetPublicProperty;
 29410 var asGetProperty = Shumway.AVM2.Runtime.asGetProperty;
 29411 var asGetPropertyLikelyNumeric = Shumway.AVM2.Runtime.asGetPropertyLikelyNumeric;
 29412 var asGetResolvedStringProperty = Shumway.AVM2.Runtime.asGetResolvedStringProperty;
 29413 var asCallResolvedStringProperty = Shumway.AVM2.Runtime.asCallResolvedStringProperty;
 29414 var asGetResolvedStringPropertyFallback = Shumway.AVM2.Runtime.asGetResolvedStringPropertyFallback;
 29415 var asSetPublicProperty = Shumway.AVM2.Runtime.asSetPublicProperty;
 29416 var asSetProperty = Shumway.AVM2.Runtime.asSetProperty;
 29417 var asSetPropertyLikelyNumeric = Shumway.AVM2.Runtime.asSetPropertyLikelyNumeric;
 29418 var asDefinePublicProperty = Shumway.AVM2.Runtime.asDefinePublicProperty;
 29419 var asDefineProperty = Shumway.AVM2.Runtime.asDefineProperty;
 29420 var asCallPublicProperty = Shumway.AVM2.Runtime.asCallPublicProperty;
 29421 var asCallProperty = Shumway.AVM2.Runtime.asCallProperty;
 29422 var asCallSuper = Shumway.AVM2.Runtime.asCallSuper;
 29423 var asSetSuper = Shumway.AVM2.Runtime.asSetSuper;
 29424 var asGetSuper = Shumway.AVM2.Runtime.asGetSuper;
 29425 var construct = Shumway.AVM2.Runtime.construct;
 29426 var asConstructProperty = Shumway.AVM2.Runtime.asConstructProperty;
 29427 var asHasProperty = Shumway.AVM2.Runtime.asHasProperty;
 29428 var asDeleteProperty = Shumway.AVM2.Runtime.asDeleteProperty;
 29429 var asGetNumericProperty = Shumway.AVM2.Runtime.asGetNumericProperty;
 29430 var asSetNumericProperty = Shumway.AVM2.Runtime.asSetNumericProperty;
 29431 var asGetDescendants = Shumway.AVM2.Runtime.asGetDescendants;
 29432 var asNextNameIndex = Shumway.AVM2.Runtime.asNextNameIndex;
 29433 var asNextName = Shumway.AVM2.Runtime.asNextName;
 29434 var asNextValue = Shumway.AVM2.Runtime.asNextValue;
 29435 var asGetEnumerableKeys = Shumway.AVM2.Runtime.asGetEnumerableKeys;
 29436 var initializeGlobalObject = Shumway.AVM2.Runtime.initializeGlobalObject;
 29437 initializeGlobalObject(jsGlobal);
 29438 var asTypeOf = Shumway.AVM2.Runtime.asTypeOf;
 29439 var publicizeProperties = Shumway.AVM2.Runtime.publicizeProperties;
 29440 var asGetSlot = Shumway.AVM2.Runtime.asGetSlot;
 29441 var asSetSlot = Shumway.AVM2.Runtime.asSetSlot;
 29442 var asHasNext2 = Shumway.AVM2.Runtime.asHasNext2;
 29443 var getDescendants = Shumway.AVM2.Runtime.getDescendants;
 29444 var checkFilter = Shumway.AVM2.Runtime.checkFilter;
 29445 var ActivationInfo = Shumway.AVM2.Runtime.ActivationInfo;
 29446 var ScopeStack = Shumway.AVM2.Runtime.ScopeStack;
 29447 var Scope = Shumway.AVM2.Runtime.Scope;
 29448 var bindFreeMethodScope = Shumway.AVM2.Runtime.bindFreeMethodScope;
 29449 var nameInTraits = Shumway.AVM2.Runtime.nameInTraits;
 29450 function resolveMultiname(object, mn, traitsOnly) {
 29451   return object.resolveMultinameProperty(mn.namespaces, mn.name, mn.flags);
 29453 var sliceArguments = Shumway.AVM2.Runtime.sliceArguments;
 29454 var nonProxyingHasProperty = Shumway.AVM2.Runtime.nonProxyingHasProperty;
 29455 var forEachPublicProperty = Shumway.AVM2.Runtime.forEachPublicProperty;
 29456 var wrapJSObject = Shumway.AVM2.Runtime.wrapJSObject;
 29457 var asCreateActivation = Shumway.AVM2.Runtime.asCreateActivation;
 29458 var CatchScopeObject = Shumway.AVM2.Runtime.CatchScopeObject;
 29459 var Global = Shumway.AVM2.Runtime.Global;
 29460 var canCompile = Shumway.AVM2.Runtime.canCompile;
 29461 var shouldCompile = Shumway.AVM2.Runtime.shouldCompile;
 29462 var forceCompile = Shumway.AVM2.Runtime.forceCompile;
 29463 var createInterpretedFunction = Shumway.AVM2.Runtime.createInterpretedFunction;
 29464 var debugName = Shumway.AVM2.Runtime.debugName;
 29465 var createCompiledFunction = Shumway.AVM2.Runtime.createCompiledFunction;
 29466 var getMethodOverrideKey = Shumway.AVM2.Runtime.getMethodOverrideKey;
 29467 var checkMethodOverrides = Shumway.AVM2.Runtime.checkMethodOverrides;
 29468 var makeTrampoline = Shumway.AVM2.Runtime.makeTrampoline;
 29469 var makeMemoizer = Shumway.AVM2.Runtime.makeMemoizer;
 29470 var createFunction = Shumway.AVM2.Runtime.createFunction;
 29471 var ensureFunctionIsInitialized = Shumway.AVM2.Runtime.ensureFunctionIsInitialized;
 29472 var getTraitFunction = Shumway.AVM2.Runtime.getTraitFunction;
 29473 var createClass = Shumway.AVM2.Runtime.createClass;
 29474 var sealConstantTraits = Shumway.AVM2.Runtime.sealConstantTraits;
 29475 var applyType = Shumway.AVM2.Runtime.applyType;
 29476 var throwError = Shumway.AVM2.Runtime.throwError;
 29477 var throwErrorFromVM = Shumway.AVM2.Runtime.throwErrorFromVM;
 29478 var translateError = Shumway.AVM2.Runtime.translateError;
 29479 var asIsInstanceOf = Shumway.AVM2.Runtime.asIsInstanceOf;
 29480 var asIsType = Shumway.AVM2.Runtime.asIsType;
 29481 var asAsType = Shumway.AVM2.Runtime.asAsType;
 29482 var asCoerceByMultiname = Shumway.AVM2.Runtime.asCoerceByMultiname;
 29483 var asCoerce = Shumway.AVM2.Runtime.asCoerce;
 29484 var asCoerceString = Shumway.AVM2.Runtime.asCoerceString;
 29485 var asCoerceInt = Shumway.AVM2.Runtime.asCoerceInt;
 29486 var asCoerceUint = Shumway.AVM2.Runtime.asCoerceUint;
 29487 var asCoerceNumber = Shumway.AVM2.Runtime.asCoerceNumber;
 29488 var asCoerceBoolean = Shumway.AVM2.Runtime.asCoerceBoolean;
 29489 var asCoerceObject = Shumway.AVM2.Runtime.asCoerceObject;
 29490 var asDefaultCompareFunction = Shumway.AVM2.Runtime.asDefaultCompareFunction;
 29491 var asCompare = Shumway.AVM2.Runtime.asCompare;
 29492 var asAdd = Shumway.AVM2.Runtime.asAdd;
 29493 var GlobalMultinameResolver = Shumway.AVM2.Runtime.GlobalMultinameResolver;
 29494 var Shumway;
 29495 (function (Shumway) {
 29496   (function (AVM2) {
 29497     (function (Runtime) {
 29498       Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES['static mochi.as3.MochiServices::connect'] = function () {
 29499         return;
 29500       };
 29501       Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES['static MochiBot::track'] = function () {
 29502         return;
 29503       };
 29504       Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES['com.midasplayer.debug.DebugLog::trace'] = function (msg) {
 29505         log(msg);
 29506       };
 29507       Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES['com.midasplayer.engine.comm.DebugGameComm::getGameData'] = function () {
 29508         return '<gamedata randomseed="554884453" version="1">\n<musicOn>true</musicOn>\n<soundOn>true</soundOn>\n<isShortGame>false</isShortGame>\n<booster_1>0</booster_1>\n<booster_2>0</booster_2>\n<booster_3>0</booster_3>\n<booster_4>0</booster_4>\n<booster_5>0</booster_5>\n<bestScore>0</bestScore>\n<bestChain>0</bestChain>\n<bestLevel>0</bestLevel>\n<bestCrushed>0</bestCrushed>\n<bestMixed>0</bestMixed>\n<text id="outro.crushed">Candy crushed</text>\n<text id="outro.bestever">best ever</text>\n<text id="outro.trophy.two">scored {0} in one game</text>\n<text id="outro.combo_color_color">All Clear Created</text>\n<text id="outro.trophy.one">crushed {0} candy in one game</text>\n<text id="outro.score">Score</text>\n<text id="outro.opengame">Please register to play the full game</text>\n<text id="outro.chain">Longest chain</text>\n<text id="outro.time">Game ends in {0} seconds</text>\n<text id="outro.combo_color_line">Super Stripes Created</text>\n<text id="game.nomoves">No more moves!</text>\n<text id="outro.combo_wrapper_line">Mega-Candy Created</text>\n<text id="intro.time">Game starts in {0} seconds</text>\n<text id="outro.now">now</text>\n<text id="outro.level">Level reached</text>\n<text id="outro.title">Game Over</text>\n<text id="intro.info1">Match 3 Candy of the same colour to crush them. Matching 4 or 5 in different formations generates special sweets that are extra tasty.</text>\n<text id="intro.info2">You can also combine the special sweets for additional effects by switching them with each other. Try these combinations for a taste you will not forget: </text>\n<text id="outro.combo_color_wrapper">Double Colour Bombs Created</text>\n<text id="outro.trophy.three">made {0} combined candy in one game</text>\n<text id="intro.title">Play like this:</text>\n</gamedata>';
 29509       };
 29510       Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES['com.antkarlov.Preloader::com.antkarlov:Preloader.isUrl'] = function () {
 29511         return true;
 29512       };
 29513       Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES['static com.demonsters.debugger.MonsterDebugger::initialize'] = function () {
 29514       };
 29515       Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES['com.spilgames.api.core.tracking.TrackConfig::getTrackers'] = function () {
 29516         return [];
 29517       };
 29518       Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES['com.spilgames.api.components.TextFields.AutoFitTextFieldEx::com.spilgames.api.components.TextFields:AutoFitTextFieldEx.updateProperties'] = Shumway.AVM2.Runtime.VM_METHOD_OVERRIDES['com.spilgames.api.components.TextFields.AutoFitTextFieldEx::com.spilgames.api.components.TextFields:AutoFitTextFieldEx.updateTextSize'] = function () {
 29519       };
 29520     }(AVM2.Runtime || (AVM2.Runtime = {})));
 29521     var Runtime = AVM2.Runtime;
 29522   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 29523   var AVM2 = Shumway.AVM2;
 29524 }(Shumway || (Shumway = {})));
 29525 var checkArguments = true;
 29526 function asCheckVectorSetNumericProperty(i, length, fixed) {
 29527   if (i < 0 || i > length || i === length && fixed || !isNumeric(i)) {
 29528     throwError('RangeError', Errors.OutOfRangeError, i, length);
 29531 function asCheckVectorGetNumericProperty(i, length) {
 29532   if (i < 0 || i >= length || !isNumeric(i)) {
 29533     throwError('RangeError', Errors.OutOfRangeError, i, length);
 29536 var TypedArrayVector = function () {
 29537     var EXTRA_CAPACITY = 4;
 29538     var INITIAL_CAPACITY = 10;
 29539     var DEFAULT_VALUE = 0;
 29540     function vector(length, fixed) {
 29541       length = length | 0;
 29542       this._fixed = !(!fixed);
 29543       this._buffer = new Int32Array(Math.max(INITIAL_CAPACITY, length + EXTRA_CAPACITY));
 29544       this._offset = 0;
 29545       this._length = length;
 29547     vector.callable = function (object) {
 29548       if (object instanceof vector) {
 29549         return object;
 29551       var length = object.asGetProperty(undefined, 'length');
 29552       if (length !== undefined) {
 29553         var v = new vector(length, false);
 29554         for (var i = 0; i < length; i++) {
 29555           v.asSetNumericProperty(i, object.asGetPublicProperty(i));
 29557         return v;
 29559       unexpected();
 29560     };
 29561     vector.prototype.internalToString = function () {
 29562       var str = '';
 29563       var start = this._offset;
 29564       var end = start + this._length;
 29565       for (var i = 0; i < this._buffer.length; i++) {
 29566         if (i === start) {
 29567           str += '[';
 29569         if (i === end) {
 29570           str += ']';
 29572         str += this._buffer[i];
 29573         if (i < this._buffer.length - 1) {
 29574           str += ',';
 29577       if (this._offset + this._length === this._buffer.length) {
 29578         str += ']';
 29580       return str + ': offset: ' + this._offset + ', length: ' + this._length + ', capacity: ' + this._buffer.length;
 29581     };
 29582     vector.prototype.toString = function () {
 29583       var str = '';
 29584       for (var i = 0; i < this._length; i++) {
 29585         str += this._buffer[this._offset + i];
 29586         if (i < this._length - 1) {
 29587           str += ',';
 29590       return str;
 29591     };
 29592     vector.prototype._view = function () {
 29593       return this._buffer.subarray(this._offset, this._offset + this._length);
 29594     };
 29595     vector.prototype._ensureCapacity = function (length) {
 29596       var minCapacity = this._offset + length;
 29597       if (minCapacity < this._buffer.length) {
 29598         return;
 29600       if (length <= this._buffer.length) {
 29601         var offset = this._buffer.length - length >> 2;
 29602         this._buffer.set(this._view(), offset);
 29603         this._offset = offset;
 29604         return;
 29606       var oldCapacity = this._buffer.length;
 29607       var newCapacity = oldCapacity * 3 >> 2;
 29608       if (newCapacity < minCapacity) {
 29609         newCapacity = minCapacity;
 29611       var buffer = new Int32Array(newCapacity);
 29612       buffer.set(this._buffer, 0);
 29613       this._buffer = buffer;
 29614     };
 29615     vector.prototype.concat = function () {
 29616       notImplemented('TypedArrayVector.concat');
 29617     };
 29618     vector.prototype.every = function (callback, thisObject) {
 29619       for (var i = 0; i < this._length; i++) {
 29620         if (!callback.call(thisObject, this.asGetNumericProperty(i), i, this)) {
 29621           return false;
 29624       return true;
 29625     };
 29626     vector.prototype.filter = function (callback, thisObject) {
 29627       var v = new vector();
 29628       for (var i = 0; i < this._length; i++) {
 29629         if (callback.call(thisObject, this.asGetNumericProperty(i), i, this)) {
 29630           v.push(this.asGetNumericProperty(i));
 29633       return v;
 29634     };
 29635     vector.prototype.some = function (callback, thisObject) {
 29636       if (arguments.length !== 2) {
 29637         throwError('ArgumentError', Errors.WrongArgumentCountError);
 29638       } else if (!isFunction(callback)) {
 29639         throwError('ArgumentError', Errors.CheckTypeFailedError);
 29641       for (var i = 0; i < this._length; i++) {
 29642         if (callback.call(thisObject, this.asGetNumericProperty(i), i, this)) {
 29643           return true;
 29646       return false;
 29647     };
 29648     vector.prototype.forEach = function (callback, thisObject) {
 29649       for (var i = 0; i < this._length; i++) {
 29650         callback.call(thisObject, this.asGetNumericProperty(i), i, this);
 29652     };
 29653     vector.prototype.join = function (sep) {
 29654       notImplemented('TypedArrayVector.join');
 29655     };
 29656     vector.prototype.indexOf = function (searchElement, fromIndex) {
 29657       notImplemented('TypedArrayVector.indexOf');
 29658     };
 29659     vector.prototype.lastIndexOf = function (searchElement, fromIndex) {
 29660       notImplemented('TypedArrayVector.lastIndexOf');
 29661     };
 29662     vector.prototype.map = function (callback, thisObject) {
 29663       if (!isFunction(callback)) {
 29664         throwError('ArgumentError', Errors.CheckTypeFailedError);
 29666       var v = new vector();
 29667       for (var i = 0; i < this._length; i++) {
 29668         v.push(callback.call(thisObject, this.asGetNumericProperty(i), i, this));
 29670       return v;
 29671     };
 29672     vector.prototype.push = function () {
 29673       this._checkFixed();
 29674       this._ensureCapacity(this._length + arguments.length);
 29675       for (var i = 0; i < arguments.length; i++) {
 29676         this._buffer[this._offset + this._length++] = arguments[i];
 29678     };
 29679     vector.prototype.pop = function () {
 29680       this._checkFixed();
 29681       if (this._length === 0) {
 29682         return DEFAULT_VALUE;
 29684       this._length--;
 29685       return this._buffer[this._offset + this._length];
 29686     };
 29687     vector.prototype.reverse = function () {
 29688       var l = this._offset;
 29689       var r = this._offset + this._length - 1;
 29690       var b = this._buffer;
 29691       while (l < r) {
 29692         var t = b[l];
 29693         b[l] = b[r];
 29694         b[r] = t;
 29695         l++;
 29696         r--;
 29698     };
 29699     vector.CASEINSENSITIVE = 1;
 29700     vector.DESCENDING = 2;
 29701     vector.UNIQUESORT = 4;
 29702     vector.RETURNINDEXEDARRAY = 8;
 29703     vector.NUMERIC = 16;
 29704     function defaultCompareFunction(a, b) {
 29705       return String(a).localeCompare(String(b));
 29707     function compare(a, b, options, compareFunction) {
 29708       assertNotImplemented(!(options & vector.CASEINSENSITIVE), 'CASEINSENSITIVE');
 29709       assertNotImplemented(!(options & vector.UNIQUESORT), 'UNIQUESORT');
 29710       assertNotImplemented(!(options & vector.RETURNINDEXEDARRAY), 'RETURNINDEXEDARRAY');
 29711       var result = 0;
 29712       if (!compareFunction) {
 29713         compareFunction = defaultCompareFunction;
 29715       if (options & vector.NUMERIC) {
 29716         a = toNumber(a);
 29717         b = toNumber(b);
 29718         result = a < b ? -1 : a > b ? 1 : 0;
 29719       } else {
 29720         result = compareFunction(a, b);
 29722       if (options & vector.DESCENDING) {
 29723         result *= -1;
 29725       return result;
 29727     function _sort(a) {
 29728       var stack = [];
 29729       var sp = -1;
 29730       var l = 0;
 29731       var r = a.length - 1;
 29732       var i, j, swap, temp;
 29733       while (true) {
 29734         if (r - l <= 100) {
 29735           for (j = l + 1; j <= r; j++) {
 29736             swap = a[j];
 29737             i = j - 1;
 29738             while (i >= l && a[i] > swap) {
 29739               a[i + 1] = a[i--];
 29741             a[i + 1] = swap;
 29743           if (sp == -1) {
 29744             break;
 29746           r = stack[sp--];
 29747           l = stack[sp--];
 29748         } else {
 29749           var median = l + r >> 1;
 29750           i = l + 1;
 29751           j = r;
 29752           swap = a[median];
 29753           a[median] = a[i];
 29754           a[i] = swap;
 29755           if (a[l] > a[r]) {
 29756             swap = a[l];
 29757             a[l] = a[r];
 29758             a[r] = swap;
 29760           if (a[i] > a[r]) {
 29761             swap = a[i];
 29762             a[i] = a[r];
 29763             a[r] = swap;
 29765           if (a[l] > a[i]) {
 29766             swap = a[l];
 29767             a[l] = a[i];
 29768             a[i] = swap;
 29770           temp = a[i];
 29771           while (true) {
 29772             do {
 29773               i++;
 29774             } while (a[i] < temp);
 29775             do {
 29776               j--;
 29777             } while (a[j] > temp);
 29778             if (j < i) {
 29779               break;
 29781             swap = a[i];
 29782             a[i] = a[j];
 29783             a[j] = swap;
 29785           a[l + 1] = a[j];
 29786           a[j] = temp;
 29787           if (r - i + 1 >= j - l) {
 29788             stack[++sp] = i;
 29789             stack[++sp] = r;
 29790             r = j - 1;
 29791           } else {
 29792             stack[++sp] = l;
 29793             stack[++sp] = j - 1;
 29794             l = i;
 29798       return a;
 29800     vector.prototype._sortNumeric = function (descending) {
 29801       _sort(this._view());
 29802       if (descending) {
 29803         this.reverse();
 29805     };
 29806     vector.prototype.sort = function () {
 29807       if (arguments.length === 0) {
 29808         return Array.prototype.sort.call(this._view());
 29810       var compareFunction, options = 0;
 29811       if (arguments[0] instanceof Function) {
 29812         compareFunction = arguments[0];
 29813       } else if (isNumber(arguments[0])) {
 29814         options = arguments[0];
 29816       if (isNumber(arguments[1])) {
 29817         options = arguments[1];
 29819       if (options & TypedArrayVector.NUMERIC) {
 29820         return this._sortNumeric(options & vector.DESCENDING);
 29822       Array.prototype.sort.call(this._view(), function (a, b) {
 29823         return compare(a, b, options, compareFunction);
 29824       });
 29825     };
 29826     vector.prototype.asGetNumericProperty = function (i) {
 29827       checkArguments && asCheckVectorGetNumericProperty(i, this._length);
 29828       return this._buffer[this._offset + i];
 29829     };
 29830     vector.prototype.asSetNumericProperty = function (i, v) {
 29831       checkArguments && asCheckVectorSetNumericProperty(i, this._length, this._fixed);
 29832       if (i === this._length) {
 29833         this._ensureCapacity(this._length + 1);
 29834         this._length++;
 29836       this._buffer[this._offset + i] = v;
 29837     };
 29838     vector.prototype.shift = function () {
 29839       this._checkFixed();
 29840       if (this._length === 0) {
 29841         return 0;
 29843       this._length--;
 29844       return this._buffer[this._offset++];
 29845     };
 29846     vector.prototype._checkFixed = function () {
 29847       if (this._fixed) {
 29848         throwError('RangeError', Errors.VectorFixedError);
 29850     };
 29851     vector.prototype._slide = function (distance) {
 29852       this._buffer.set(this._view(), this._offset + distance);
 29853       this._offset += distance;
 29854     };
 29855     vector.prototype.unshift = function () {
 29856       this._checkFixed();
 29857       if (!arguments.length) {
 29858         return;
 29860       this._ensureCapacity(this._length + arguments.length);
 29861       this._slide(arguments.length);
 29862       this._offset -= arguments.length;
 29863       this._length += arguments.length;
 29864       for (var i = 0; i < arguments.length; i++) {
 29865         this._buffer[this._offset + i] = arguments[i];
 29867     };
 29868     vector.prototype.asGetEnumerableKeys = function () {
 29869       if (vector.prototype === this) {
 29870         return Object.prototype.asGetEnumerableKeys.call(this);
 29872       var keys = [];
 29873       for (var i = 0; i < this._length; i++) {
 29874         keys.push(i);
 29876       return keys;
 29877     };
 29878     vector.prototype.asHasProperty = function (namespaces, name, flags) {
 29879       if (vector.prototype === this || !isNumeric(name)) {
 29880         return Object.prototype.asHasProperty.call(this, namespaces, name, flags);
 29882       var index = toNumber(name);
 29883       return index >= 0 && index < this._length;
 29884     };
 29885     Object.defineProperty(vector.prototype, 'length', {
 29886       get: function () {
 29887         return this._length;
 29888       },
 29889       set: function (length) {
 29890         length = length >>> 0;
 29891         if (length > this._length) {
 29892           this._ensureCapacity(length);
 29893           for (var i = this._offset + this._length, j = this._offset + length; i < j; i++) {
 29894             this._buffer[i] = DEFAULT_VALUE;
 29897         this._length = length;
 29899     });
 29900     vector.prototype._spliceHelper = function (index, insertCount, deleteCount, args, offset) {
 29901       insertCount = clamp(insertCount, 0, args.length - offset);
 29902       deleteCount = clamp(deleteCount, 0, this._length - index);
 29903       this._ensureCapacity(this._length - deleteCount + insertCount);
 29904       var right = this._offset + index + deleteCount;
 29905       var slice = this._buffer.subarray(right, right + this._length - index - deleteCount);
 29906       this._buffer.set(slice, this._offset + index + insertCount);
 29907       this._length += insertCount - deleteCount;
 29908       for (var i = 0; i < insertCount; i++) {
 29909         this._buffer[this._offset + index + i] = args.asGetNumericProperty(offset + i);
 29911     };
 29912     vector.prototype.asGetEnumerableKeys = function () {
 29913       if (vector.prototype === this) {
 29914         return Object.prototype.asGetEnumerableKeys.call(this);
 29916       var keys = [];
 29917       for (var i = 0; i < this._length; i++) {
 29918         keys.push(i);
 29920       return keys;
 29921     };
 29922     return vector;
 29923   }();
 29924 var typedArrayVectorTemplate = 'var EXTRA_CAPACITY=4,INITIAL_CAPACITY=10,DEFAULT_VALUE=0;function vector(a,b){a|=0;this._fixed=!!b;this._buffer=new Int32Array(Math.max(INITIAL_CAPACITY,a+EXTRA_CAPACITY));this._offset=0;this._length=a}vector.callable=function(a){if(a instanceof vector)return a;var b=a.asGetProperty(void 0,"length");if(void 0!==b){for(var c=new vector(b,!1),d=0;d<b;d++)c.asSetNumericProperty(d,a.asGetPublicProperty(d));return c}unexpected()}; vector.prototype.internalToString=function(){for(var a="",b=this._offset,c=b+this._length,d=0;d<this._buffer.length;d++)d===b&&(a+="["),d===c&&(a+="]"),a+=this._buffer[d],d<this._buffer.length-1&&(a+=",");this._offset+this._length===this._buffer.length&&(a+="]");return a+": offset: "+this._offset+", length: "+this._length+", capacity: "+this._buffer.length};vector.prototype.toString=function(){for(var a="",b=0;b<this._length;b++)a+=this._buffer[this._offset+b],b<this._length-1&&(a+=",");return a}; vector.prototype._view=function(){return this._buffer.subarray(this._offset,this._offset+this._length)};vector.prototype._ensureCapacity=function(a){var b=this._offset+a;b<this._buffer.length||(a<=this._buffer.length?(b=this._buffer.length-a>>2,this._buffer.set(this._view(),b),this._offset=b):(a=3*this._buffer.length>>2,a<b&&(a=b),b=new Int32Array(a),b.set(this._buffer,0),this._buffer=b))}; vector.prototype.every=function(a,b){for(var c=0;c<this._length;c++)if(!a.call(b,this.asGetNumericProperty(c),c,this))return!1;return!0};vector.prototype.filter=function(a,b){for(var c=new vector,d=0;d<this._length;d++)a.call(b,this.asGetNumericProperty(d),d,this)&&c.push(this.asGetNumericProperty(d));return c}; vector.prototype.some=function(a,b){2!==arguments.length?throwError("ArgumentError",Errors.WrongArgumentCountError):isFunction(a)||throwError("ArgumentError",Errors.CheckTypeFailedError);for(var c=0;c<this._length;c++)if(a.call(b,this.asGetNumericProperty(c),c,this))return!0;return!1};vector.prototype.forEach=function(a,b){for(var c=0;c<this._length;c++)a.call(b,this.asGetNumericProperty(c),c,this)};vector.prototype.join=function(a){notImplemented("TypedArrayVector.join")}; vector.prototype.indexOf=function(a,b){notImplemented("TypedArrayVector.indexOf")};vector.prototype.lastIndexOf=function(a,b){notImplemented("TypedArrayVector.lastIndexOf")};vector.prototype.map=function(a,b){isFunction(a)||throwError("ArgumentError",Errors.CheckTypeFailedError);for(var c=new vector,d=0;d<this._length;d++)c.push(a.call(b,this.asGetNumericProperty(d),d,this));return c}; vector.prototype.push=function(){this._checkFixed();this._ensureCapacity(this._length+arguments.length);for(var a=0;a<arguments.length;a++)this._buffer[this._offset+this._length++]=arguments[a]};vector.prototype.pop=function(){this._checkFixed();if(0===this._length)return DEFAULT_VALUE;this._length--;return this._buffer[this._offset+this._length]};vector.prototype.reverse=function(){for(var a=this._offset,b=this._offset+this._length-1,c=this._buffer;a<b;){var d=c[a];c[a]=c[b];c[b]=d;a++;b--}}; vector.CASEINSENSITIVE=1;vector.DESCENDING=2;vector.UNIQUESORT=4;vector.RETURNINDEXEDARRAY=8;vector.NUMERIC=16;function defaultCompareFunction(a,b){return String(a).localeCompare(String(b))} function compare(a,b,c,d){assertNotImplemented(!(c&vector.CASEINSENSITIVE),"CASEINSENSITIVE");assertNotImplemented(!(c&vector.UNIQUESORT),"UNIQUESORT");assertNotImplemented(!(c&vector.RETURNINDEXEDARRAY),"RETURNINDEXEDARRAY");var f=0;d||(d=defaultCompareFunction);c&vector.NUMERIC?(a=toNumber(a),b=toNumber(b),f=a<b?-1:a>b?1:0):f=d(a,b);c&vector.DESCENDING&&(f*=-1);return f} function _sort(a){for(var b=[],c=-1,d=0,f=a.length-1,e,g,h,k;;)if(100>=f-d){for(g=d+1;g<=f;g++){h=a[g];for(e=g-1;e>=d&&a[e]>h;)a[e+1]=a[e--];a[e+1]=h}if(-1==c)break;f=b[c--];d=b[c--]}else{k=d+f>>1;e=d+1;g=f;h=a[k];a[k]=a[e];a[e]=h;a[d]>a[f]&&(h=a[d],a[d]=a[f],a[f]=h);a[e]>a[f]&&(h=a[e],a[e]=a[f],a[f]=h);a[d]>a[e]&&(h=a[d],a[d]=a[e],a[e]=h);for(k=a[e];;){do e++;while(a[e]<k);do g--;while(a[g]>k);if(g<e)break;h=a[e];a[e]=a[g];a[g]=h}a[d+1]=a[g];a[g]=k;f-e+1>=g-d?(b[++c]=e,b[++c]=f,f=g-1):(b[++c]=d, b[++c]=g-1,d=e)}return a}vector.prototype._sortNumeric=function(a){_sort(this._view());a&&this.reverse()};vector.prototype.sort=function(){if(0===arguments.length)return Array.prototype.sort.call(this._view());var a,b=0;arguments[0]instanceof Function?a=arguments[0]:isNumber(arguments[0])&&(b=arguments[0]);isNumber(arguments[1])&&(b=arguments[1]);if(b&TypedArrayVector.NUMERIC)return this._sortNumeric(b&vector.DESCENDING);Array.prototype.sort.call(this._view(),function(c,d){return compare(c,d,b,a)})}; vector.prototype.asGetNumericProperty=function(a){checkArguments&&asCheckVectorGetNumericProperty(a,this._length);return this._buffer[this._offset+a]};vector.prototype.asSetNumericProperty=function(a,b){checkArguments&&asCheckVectorSetNumericProperty(a,this._length,this._fixed);a===this._length&&(this._ensureCapacity(this._length+1),this._length++);this._buffer[this._offset+a]=b};vector.prototype.shift=function(){this._checkFixed();if(0===this._length)return 0;this._length--;return this._buffer[this._offset++]}; vector.prototype._checkFixed=function(){this._fixed&&throwError("RangeError",Errors.VectorFixedError)};vector.prototype._slide=function(a){this._buffer.set(this._view(),this._offset+a);this._offset+=a};vector.prototype.unshift=function(){this._checkFixed();if(arguments.length){this._ensureCapacity(this._length+arguments.length);this._slide(arguments.length);this._offset-=arguments.length;this._length+=arguments.length;for(var a=0;a<arguments.length;a++)this._buffer[this._offset+a]=arguments[a]}}; vector.prototype.asGetEnumerableKeys=function(){if(vector.prototype===this)return Object.prototype.asGetEnumerableKeys.call(this);for(var a=[],b=0;b<this._length;b++)a.push(b);return a};vector.prototype.asHasProperty=function(a,b,c){if(vector.prototype===this||!isNumeric(b))return Object.prototype.asHasProperty.call(this,a,b,c);a=toNumber(b);return 0<=a&&a<this._length}; Object.defineProperty(vector.prototype,"length",{get:function(){return this._length},set:function(a){a>>>=0;if(a>this._length){this._ensureCapacity(a);for(var b=this._offset+this._length,c=this._offset+a;b<c;b++)this._buffer[b]=DEFAULT_VALUE}this._length=a}}); vector.prototype._spliceHelper=function(a,b,c,d,f){debugger;b=clamp(b,0,d.length-f);c=clamp(c,0,this._length-a);this._ensureCapacity(this._length-c+b);var e=this._offset+a+c,e=this._buffer.subarray(e,e+this._length-a-c);this._buffer.set(e,this._offset+a+b);this._length+=b-c;for(c=0;c<b;c++)this._buffer[this._offset+a+c]=d.asGetNumericProperty(f+c)}; vector.prototype.asGetEnumerableKeys=function(){if(vector.prototype===this)return Object.prototype.asGetEnumerableKeys.call(this);for(var a=[],b=0;b<this._length;b++)a.push(b);return a};';
 29925 var Int32Vector = TypedArrayVector;
 29926 var Uint32Vector = new Function(originalStringReplace.call(typedArrayVectorTemplate, /Int32Array/g, 'Uint32Array') + ' return vector;')();
 29927 var Float64Vector = new Function(originalStringReplace.call(typedArrayVectorTemplate, /Int32Array/g, 'Float64Array') + ' return vector;')();
 29928 Int32Vector.prototype.asGetProperty = function (namespaces, name, flags) {
 29929   if (typeof name === 'number') {
 29930     return this.asGetNumericProperty(name);
 29932   return asGetProperty.call(this, namespaces, name, flags);
 29933 };
 29934 Int32Vector.prototype.asSetProperty = function (namespaces, name, flags, value) {
 29935   if (typeof name === 'number') {
 29936     this.asSetNumericProperty(name, value);
 29937     return;
 29939   return asSetProperty.call(this, namespaces, name, flags, value);
 29940 };
 29941 Uint32Vector.prototype.asGetProperty = function (namespaces, name, flags) {
 29942   if (typeof name === 'number') {
 29943     return this.asGetNumericProperty(name);
 29945   return asGetProperty.call(this, namespaces, name, flags);
 29946 };
 29947 Uint32Vector.prototype.asSetProperty = function (namespaces, name, flags, value) {
 29948   if (typeof name === 'number') {
 29949     this.asSetNumericProperty(name, value);
 29950     return;
 29952   return asSetProperty.call(this, namespaces, name, flags, value);
 29953 };
 29954 Float64Vector.prototype.asGetProperty = function (namespaces, name, flags) {
 29955   if (typeof name === 'number') {
 29956     return this.asGetNumericProperty(name);
 29958   return asGetProperty.call(this, namespaces, name, flags);
 29959 };
 29960 Float64Vector.prototype.asSetProperty = function (namespaces, name, flags, value) {
 29961   if (typeof name === 'number') {
 29962     this.asSetNumericProperty(name, value);
 29963     return;
 29965   return asSetProperty.call(this, namespaces, name, flags, value);
 29966 };
 29967 var GenericVector = function () {
 29968     function vector(length, fixed, type) {
 29969       length = length | 0;
 29970       this._fixed = !(!fixed);
 29971       this._buffer = new Array(length);
 29972       this._type = type;
 29973       this._defaultValue = type ? type.defaultValue : null;
 29974       this._fill(0, length, this._defaultValue);
 29976     vector.applyType = function applyType(type) {
 29977       function parameterizedVector(length, fixed) {
 29978         vector.call(this, length, fixed, type);
 29980       parameterizedVector.prototype = Object.create(vector.prototype);
 29981       parameterizedVector.callable = vector.callable;
 29982       return parameterizedVector;
 29983     };
 29984     vector.callable = function (object) {
 29985       if (object instanceof vector) {
 29986         return object;
 29988       var length = object.asGetProperty(undefined, 'length');
 29989       if (length !== undefined) {
 29990         var v = new vector(length, false);
 29991         for (var i = 0; i < length; i++) {
 29992           v.asSetNumericProperty(i, object.asGetPublicProperty(i));
 29994         return v;
 29996       unexpected();
 29997     };
 29998     vector.prototype._fill = function (index, length, value) {
 29999       for (var i = 0; i < length; i++) {
 30000         this._buffer[index + i] = value;
 30002     };
 30003     vector.prototype.toString = function () {
 30004       var str = '';
 30005       for (var i = 0; i < this._buffer.length; i++) {
 30006         str += this._buffer[i];
 30007         if (i < this._buffer.length - 1) {
 30008           str += ',';
 30011       return str;
 30012     };
 30013     vector.prototype.every = function (callback, thisObject) {
 30014       for (var i = 0; i < this._buffer.length; i++) {
 30015         if (!callback.call(thisObject, this.asGetNumericProperty(i), i, this)) {
 30016           return false;
 30019       return true;
 30020     };
 30021     vector.prototype.filter = function (callback, thisObject) {
 30022       var v = new vector();
 30023       for (var i = 0; i < this._buffer.length; i++) {
 30024         if (callback.call(thisObject, this.asGetNumericProperty(i), i, this)) {
 30025           v.push(this.asGetNumericProperty(i));
 30028       return v;
 30029     };
 30030     vector.prototype.some = function (callback, thisObject) {
 30031       if (arguments.length !== 2) {
 30032         throwError('ArgumentError', Errors.WrongArgumentCountError);
 30033       } else if (!isFunction(callback)) {
 30034         throwError('ArgumentError', Errors.CheckTypeFailedError);
 30036       for (var i = 0; i < this._buffer.length; i++) {
 30037         if (callback.call(thisObject, this.asGetNumericProperty(i), i, this)) {
 30038           return true;
 30041       return false;
 30042     };
 30043     vector.prototype.forEach = function (callback, thisObject) {
 30044       if (!isFunction(callback)) {
 30045         throwError('ArgumentError', Errors.CheckTypeFailedError);
 30047       for (var i = 0; i < this._buffer.length; i++) {
 30048         callback.call(thisObject, this.asGetNumericProperty(i), i, this);
 30050     };
 30051     vector.prototype.map = function (callback, thisObject) {
 30052       if (!isFunction(callback)) {
 30053         throwError('ArgumentError', Errors.CheckTypeFailedError);
 30055       var v = new vector();
 30056       for (var i = 0; i < this._buffer.length; i++) {
 30057         v.push(callback.call(thisObject, this.asGetNumericProperty(i), i, this));
 30059       return v;
 30060     };
 30061     vector.prototype.push = function () {
 30062       this._checkFixed();
 30063       for (var i = 0; i < arguments.length; i++) {
 30064         this._buffer.push(this._coerce(arguments[i]));
 30066     };
 30067     vector.prototype.pop = function () {
 30068       this._checkFixed();
 30069       if (this._buffer.length === 0) {
 30070         return undefined;
 30072       return this._buffer.pop();
 30073     };
 30074     vector.prototype.reverse = function () {
 30075       this._buffer.reverse();
 30076     };
 30077     vector.CASEINSENSITIVE = 1;
 30078     vector.DESCENDING = 2;
 30079     vector.UNIQUESORT = 4;
 30080     vector.RETURNINDEXEDARRAY = 8;
 30081     vector.NUMERIC = 16;
 30082     function defaultCompareFunction(a, b) {
 30083       return String(a).localeCompare(String(b));
 30085     function compare(a, b, options, compareFunction) {
 30086       assertNotImplemented(!(options & CASEINSENSITIVE), 'CASEINSENSITIVE');
 30087       assertNotImplemented(!(options & UNIQUESORT), 'UNIQUESORT');
 30088       assertNotImplemented(!(options & RETURNINDEXEDARRAY), 'RETURNINDEXEDARRAY');
 30089       var result = 0;
 30090       if (!compareFunction) {
 30091         compareFunction = defaultCompareFunction;
 30093       if (options & NUMERIC) {
 30094         a = toNumber(a);
 30095         b = toNumber(b);
 30096         result = a < b ? -1 : a > b ? 1 : 0;
 30097       } else {
 30098         result = compareFunction(a, b);
 30100       if (options & DESCENDING) {
 30101         result *= -1;
 30103       return result;
 30105     vector.prototype.sort = function (comparator) {
 30106       return this._buffer.sort(comparator);
 30107     };
 30108     vector.prototype.asGetNumericProperty = function (i) {
 30109       checkArguments && asCheckVectorGetNumericProperty(i, this._buffer.length);
 30110       return this._buffer[i];
 30111     };
 30112     vector.prototype._coerce = function (v) {
 30113       if (this._type) {
 30114         return this._type.coerce(v);
 30115       } else if (v === undefined) {
 30116         return null;
 30118       return v;
 30119     };
 30120     vector.prototype.asSetNumericProperty = function (i, v) {
 30121       checkArguments && asCheckVectorSetNumericProperty(i, this._buffer.length, this._fixed);
 30122       this._buffer[i] = this._coerce(v);
 30123     };
 30124     vector.prototype.shift = function () {
 30125       this._checkFixed();
 30126       if (this._buffer.length === 0) {
 30127         return undefined;
 30129       return this._buffer.shift();
 30130     };
 30131     vector.prototype._checkFixed = function () {
 30132       if (this._fixed) {
 30133         throwError('RangeError', Errors.VectorFixedError);
 30135     };
 30136     vector.prototype.unshift = function () {
 30137       if (!arguments.length) {
 30138         return;
 30140       this._checkFixed();
 30141       var items = [];
 30142       for (var i = 0; i < arguments.length; i++) {
 30143         items.push(this._coerce(arguments[i]));
 30145       this._buffer.unshift.apply(this._buffer, items);
 30146     };
 30147     Object.defineProperty(vector.prototype, 'length', {
 30148       get: function () {
 30149         return this._buffer.length;
 30150       },
 30151       set: function (length) {
 30152         length = length >>> 0;
 30153         if (length > this._buffer.length) {
 30154           for (var i = this._buffer.length; i < length; i++) {
 30155             this._buffer[i] = this._defaultValue;
 30157         } else {
 30158           this._buffer.length = length;
 30160         true;
 30162     });
 30163     vector.prototype._spliceHelper = function (index, insertCount, deleteCount, args, offset) {
 30164       insertCount = clamp(insertCount, 0, args.length - offset);
 30165       deleteCount = clamp(deleteCount, 0, this._buffer.length - index);
 30166       var items = [];
 30167       for (var i = 0; i < insertCount; i++) {
 30168         items.push(this._coerce(args.asGetNumericProperty(offset + i)));
 30170       this._buffer.splice.apply(this._buffer, [
 30171         index,
 30172         deleteCount
 30173       ].concat(items));
 30174     };
 30175     vector.prototype.asGetEnumerableKeys = function () {
 30176       if (vector.prototype === this) {
 30177         return Object.prototype.asGetEnumerableKeys.call(this);
 30179       var keys = [];
 30180       for (var i = 0; i < this._buffer.length; i++) {
 30181         keys.push(i);
 30183       return keys;
 30184     };
 30185     vector.prototype.asHasProperty = function (namespaces, name, flags) {
 30186       if (vector.prototype === this || !isNumeric(name)) {
 30187         return Object.prototype.asHasProperty.call(this, namespaces, name, flags);
 30189       var index = toNumber(name);
 30190       return index >= 0 && index < this._buffer.length;
 30191     };
 30192     return vector;
 30193   }();
 30194 GenericVector.prototype.asGetProperty = function (namespaces, name, flags) {
 30195   if (typeof name === 'number') {
 30196     return this.asGetNumericProperty(name);
 30198   return asGetProperty.call(this, namespaces, name, flags);
 30199 };
 30200 GenericVector.prototype.asSetProperty = function (namespaces, name, flags, value) {
 30201   if (typeof name === 'number') {
 30202     this.asSetNumericProperty(name, value);
 30203     return;
 30205   return asSetProperty.call(this, namespaces, name, flags, value);
 30206 };
 30207 function arraySort(o, args) {
 30208   if (args.length === 0) {
 30209     return o.sort();
 30211   var compareFunction, options = 0;
 30212   if (args[0] instanceof Function) {
 30213     compareFunction = args[0];
 30214   } else if (isNumber(args[0])) {
 30215     options = args[0];
 30217   if (isNumber(args[1])) {
 30218     options = args[1];
 30220   o.sort(function (a, b) {
 30221     return asCompare(a, b, options, compareFunction);
 30222   });
 30223   return o;
 30225 function ArrayClass(domain, scope, instanceConstructor, baseClass) {
 30226   var c = new Class('Array', Array, ApplicationDomain.passthroughCallable(Array));
 30227   c.extendBuiltin(baseClass);
 30228   var CACHE_NUMERIC_COMPARATORS = true;
 30229   var numericComparatorCache = createEmptyObject();
 30230   c.native = {
 30231     static: {
 30232       _pop: function _pop(o) {
 30233         return o.pop();
 30234       },
 30235       _reverse: function _reverse(o) {
 30236         return o.reverse();
 30237       },
 30238       _concat: function _concat(o, args) {
 30239         return o.concat.apply(o, args);
 30240       },
 30241       _shift: function _shift(o) {
 30242         return o.shift();
 30243       },
 30244       _slice: function _slice(o, A, B) {
 30245         return o.slice(A, B);
 30246       },
 30247       _unshift: function _unshift(o, args) {
 30248         return o.unshift.apply(o, args);
 30249       },
 30250       _splice: function _splice(o, args) {
 30251         return o.splice.apply(o, args);
 30252       },
 30253       _sort: function _sort(o, args) {
 30254         if (args.length === 0) {
 30255           return o.sort();
 30257         var compareFunction, options = 0;
 30258         if (args[0] instanceof Function) {
 30259           compareFunction = args[0];
 30260         } else if (isNumber(args[0])) {
 30261           options = args[0];
 30263         if (isNumber(args[1])) {
 30264           options = args[1];
 30266         o.sort(function (a, b) {
 30267           return asCompare(a, b, options, compareFunction);
 30268         });
 30269         return o;
 30270       },
 30271       _sortOn: function _sortOn(o, names, options) {
 30272         if (isString(names)) {
 30273           names = [
 30274             names
 30275           ];
 30277         if (isNumber(options)) {
 30278           options = [
 30279             options
 30280           ];
 30282         for (var i = names.length - 1; i >= 0; i--) {
 30283           var key = Multiname.getPublicQualifiedName(names[i]);
 30284           if (CACHE_NUMERIC_COMPARATORS && options[i] & SORT_NUMERIC) {
 30285             var str = 'var x = toNumber(a.' + key + '), y = toNumber(b.' + key + ');';
 30286             if (options[i] & SORT_DESCENDING) {
 30287               str += 'return x < y ? 1 : (x > y ? -1 : 0);';
 30288             } else {
 30289               str += 'return x < y ? -1 : (x > y ? 1 : 0);';
 30291             var numericComparator = numericComparatorCache[str];
 30292             if (!numericComparator) {
 30293               numericComparator = numericComparatorCache[str] = new Function('a', 'b', str);
 30295             o.sort(numericComparator);
 30296           } else {
 30297             o.sort(function (a, b) {
 30298               return asCompare(a[key], b[key], options[i] | 0);
 30299             });
 30302         return o;
 30303       },
 30304       _indexOf: function _indexOf(o, searchElement, fromIndex) {
 30305         return o.indexOf(searchElement, fromIndex);
 30306       },
 30307       _lastIndexOf: function _lastIndexOf(o, searchElement, fromIndex) {
 30308         return o.lastIndexOf(searchElement, fromIndex);
 30309       },
 30310       _every: function _every(o, callback, thisObject) {
 30311         for (var i = 0; i < o.length; i++) {
 30312           if (callback.call(thisObject, o[i], i, o) !== true) {
 30313             return false;
 30316         return false;
 30317       },
 30318       _filter: function _filter(o, callback, thisObject) {
 30319         var result = [];
 30320         for (var i = 0; i < o.length; i++) {
 30321           if (callback.call(thisObject, o[i], i, o) === true) {
 30322             result.push(o[i]);
 30325         return result;
 30326       },
 30327       _forEach: function _forEach(o, callback, thisObject) {
 30328         return o.forEach(callback, thisObject);
 30329       },
 30330       _map: function _map(o, callback, thisObject) {
 30331         return o.map(callback, thisObject);
 30332       },
 30333       _some: function _some(o, callback, thisObject) {
 30334         return o.some(callback, thisObject);
 30336     },
 30337     instance: {
 30338       pop: Array.prototype.pop,
 30339       push: Array.prototype.push,
 30340       unshift: Array.prototype.unshift,
 30341       length: {
 30342         get: function length() {
 30343           return this.length;
 30344         },
 30345         set: function length(newLength) {
 30346           this.length = newLength;
 30350   };
 30351   c.coerce = function (value) {
 30352     return value;
 30353   };
 30354   c.isInstanceOf = function (value) {
 30355     return true;
 30356   };
 30357   return c;
 30359 var XMLClass, XMLListClass, QNameClass, ASXML, XML, ASXMLList, XMLList;
 30360 var isXMLType, isXMLName, XMLParser;
 30361 (function () {
 30362   function XMLEncoder(ancestorNamespaces, indentLevel, prettyPrinting) {
 30363     function visit(node, encode) {
 30364       if (node.isXML) {
 30365         switch (node.kind) {
 30366         case 'element':
 30367           return encode.element(node);
 30368         case 'attribute':
 30369           return encode.attribute(node);
 30370         case 'text':
 30371           return encode.text(node);
 30372         case 'cdata':
 30373           return encode.cdata(node);
 30374         case 'comment':
 30375           return encode.comment(node);
 30376         case 'processing-instruction':
 30377           return encode.pi(node);
 30379       } else if (node.isXMLList) {
 30380         return encode.list(node);
 30381       } else {
 30382         throw 'Not implemented';
 30385     function encode(node, encoder) {
 30386       return visit(node, {
 30387         element: function (n) {
 30388           var s, a;
 30389           var ns = n.name.mn.namespaces[0];
 30390           var prefix = ns.prefix ? ns.prefix + ':' : '';
 30391           s = '<' + prefix + n.name.localName;
 30392           var namespaceDeclarations = [];
 30393           if (ns.prefix || ns.uri) {
 30394             namespaceDeclarations.push(ns);
 30396           if (prefix) {
 30397             namespaceDeclarations[ns.prefix] = true;
 30399           var t = n;
 30400           while (t) {
 30401             for (var i = 0; i < t.inScopeNamespaces.length; i++) {
 30402               ns = t.inScopeNamespaces[i];
 30403               if (!namespaceDeclarations[ns.prefix]) {
 30404                 namespaceDeclarations.push(ns);
 30405                 namespaceDeclarations[ns.prefix] = true;
 30408             t = t.parent;
 30410           for (var i = 0; i < namespaceDeclarations.length; i++) {
 30411             a = namespaceDeclarations[i];
 30412             if (a.prefix) {
 30413               s += ' xmlns:' + a.prefix + '="' + a.uri + '"';
 30414             } else {
 30415               s += ' xmlns="' + a.uri + '"';
 30418           for (var i = 0; i < n.attributes.length; i++) {
 30419             a = n.attributes[i];
 30420             var ns = n.name.uri;
 30421             var prefix = n.prefix ? ns.prefix + ':' : '';
 30422             var name = prefix + a.name.localName;
 30423             s += ' ' + name + '="' + a.value + '"';
 30425           if (n.children.length) {
 30426             s += '>';
 30427             for (var i = 0; i < n.children.length; i++) {
 30428               s += visit(n.children[i], this);
 30430             s += '</' + prefix + n.name.mn.name + '>';
 30431           } else {
 30432             s += '/>';
 30434           return s;
 30435         },
 30436         text: function (text) {
 30437           return escapeAttributeValue(text.value);
 30438         },
 30439         attribute: function (n) {
 30440           return escapeAttributeValue(n.value);
 30441         },
 30442         cdata: function (n) {
 30443         },
 30444         comment: function (n) {
 30445         },
 30446         pi: function (n) {
 30447         },
 30448         doctype: function (n) {
 30449         },
 30450         list: function (n) {
 30451           var s = '';
 30452           for (var i = 0; i < n.children.length; i++) {
 30453             if (i > 0) {
 30454               s += '\n';
 30456             s += toXMLString(n.children[i], []);
 30458           return s;
 30460       });
 30462     this.encode = encode;
 30464   function escapeAttributeValue(v) {
 30465     return v.replace('&', '&amp;').replace('<', '&lt;').replace('>', '&gt;');
 30467   XMLParser = function XMLParser() {
 30468     function parseXml(s, sink) {
 30469       var i = 0, scopes = [
 30471             space: 'default',
 30472             xmlns: '',
 30473             namespaces: {
 30474               'xmlns': 'http://www.w3.org/2000/xmlns/',
 30475               'xml': 'http://www.w3.org/XML/1998/namespace'
 30478         ];
 30479       function trim(s) {
 30480         return s.replace(/^\s+/, '').replace(/\s+$/, '');
 30482       function resolveEntities(s) {
 30483         return s.replace(/&([^;]+);/g, function (all, entity) {
 30484           if (entity.substring(0, 2) === '#x') {
 30485             return String.fromCharCode(parseInt(entity.substring(2), 16));
 30486           } else if (entity.substring(0, 1) === '#') {
 30487             return String.fromCharCode(parseInt(entity.substring(1), 10));
 30489           switch (entity) {
 30490           case 'lt':
 30491             return '<';
 30492           case 'gt':
 30493             return '>';
 30494           case 'amp':
 30495             return '&';
 30497           throw 'Unknown entity: ' + entity;
 30498         });
 30500       function isWhitespacePreserved() {
 30501         for (var j = scopes.length - 1; j >= 0; --j) {
 30502           if (scopes[j].space === 'preserve') {
 30503             return true;
 30506         return false;
 30508       function lookupDefaultNs() {
 30509         for (var j = scopes.length - 1; j >= 0; --j) {
 30510           if (scopes[j].hasOwnProperty('xmlns')) {
 30511             return scopes[j].xmlns;
 30515       function lookupNs(prefix) {
 30516         for (var j = scopes.length - 1; j >= 0; --j) {
 30517           if (scopes[j].namespaces.hasOwnProperty(prefix)) {
 30518             return scopes[j].namespaces[prefix];
 30521         throw 'Unknown namespace: ' + prefix;
 30523       function getName(name, resolveDefaultNs) {
 30524         var j = name.indexOf(':');
 30525         if (j >= 0) {
 30526           var namespace = lookupNs(name.substring(0, j));
 30527           var prefix = name.substring(0, j);
 30528           var localName = name.substring(j + 1);
 30529           return {
 30530             name: namespace + '::' + localName,
 30531             localName: localName,
 30532             prefix: prefix,
 30533             namespace: namespace
 30534           };
 30535         } else if (resolveDefaultNs) {
 30536           return {
 30537             name: name,
 30538             localName: name,
 30539             prefix: '',
 30540             namespace: lookupDefaultNs()
 30541           };
 30542         } else {
 30543           return {
 30544             name: name,
 30545             localName: name,
 30546             prefix: '',
 30547             namespace: ''
 30548           };
 30551       var whitespaceMap = {
 30552           '10': true,
 30553           '13': true,
 30554           '9': true,
 30555           '32': true
 30556         };
 30557       function isWhitespace(s, index) {
 30558         return s.charCodeAt(index) in whitespaceMap;
 30560       function parseContent(s, start) {
 30561         var pos = start, name, attributes = [];
 30562         function skipWs() {
 30563           while (pos < s.length && isWhitespace(s, pos)) {
 30564             ++pos;
 30567         while (pos < s.length && !isWhitespace(s, pos) && s.charAt(pos) !== '>' && s.charAt(pos) !== '/') {
 30568           ++pos;
 30570         name = s.substring(start, pos);
 30571         skipWs();
 30572         while (pos < s.length && s.charAt(pos) !== '>' && s.charAt(pos) !== '/' && s.charAt(pos) !== '?') {
 30573           skipWs();
 30574           var attrName = '', attrValue = '';
 30575           while (pos < s.length && !isWhitespace(s, pos) && s.charAt(pos) !== '=') {
 30576             attrName += s.charAt(pos);
 30577             ++pos;
 30579           skipWs();
 30580           if (s.charAt(pos) !== '=')
 30581             throw '\'=\' expected';
 30582           ++pos;
 30583           skipWs();
 30584           var attrEndChar = s.charAt(pos);
 30585           if (attrEndChar !== '"' && attrEndChar !== '\'')
 30586             throw 'Quote expected';
 30587           var attrEndIndex = s.indexOf(attrEndChar, ++pos);
 30588           if (attrEndIndex < 0)
 30589             throw new 'Unexpected EOF[6]'();
 30590           attrValue = s.substring(pos, attrEndIndex);
 30591           attributes.push({
 30592             name: attrName,
 30593             value: resolveEntities(attrValue)
 30594           });
 30595           pos = attrEndIndex + 1;
 30596           skipWs();
 30598         return {
 30599           name: name,
 30600           attributes: attributes,
 30601           parsed: pos - start
 30602         };
 30604       while (i < s.length) {
 30605         var ch = s.charAt(i);
 30606         var j = i;
 30607         if (ch === '<') {
 30608           ++j;
 30609           var ch2 = s.charAt(j), q, name;
 30610           switch (ch2) {
 30611           case '/':
 30612             ++j;
 30613             q = s.indexOf('>', j);
 30614             if (q < 0) {
 30615               throw 'Unexpected EOF[1]';
 30617             name = getName(s.substring(j, q), true);
 30618             sink.endElement(name);
 30619             scopes.pop();
 30620             j = q + 1;
 30621             break;
 30622           case '?':
 30623             ++j;
 30624             var content = parseContent(s, j);
 30625             if (s.substring(j + content.parsed, j + content.parsed + 2) != '?>') {
 30626               throw 'Unexpected EOF[2]';
 30628             sink.pi(content.name, content.attributes);
 30629             j += content.parsed + 2;
 30630             break;
 30631           case '!':
 30632             if (s.substring(j + 1, j + 3) === '--') {
 30633               q = s.indexOf('-->', j + 3);
 30634               if (q < 0) {
 30635                 throw 'Unexpected EOF[3]';
 30637               sink.comment(s.substring(j + 3, q));
 30638               j = q + 3;
 30639             } else if (s.substring(j + 1, j + 8) === '[CDATA[') {
 30640               q = s.indexOf(']]>', j + 8);
 30641               if (q < 0) {
 30642                 throw 'Unexpected EOF[4]';
 30644               sink.cdata(s.substring(j + 8, q));
 30645               j = q + 3;
 30646             } else if (s.substring(j + 1, j + 8) === 'DOCTYPE') {
 30647               var q2 = s.indexOf('[', j + 8), complexDoctype = false;
 30648               q = s.indexOf('>', j + 8);
 30649               if (q < 0) {
 30650                 throw 'Unexpected EOF[5]';
 30652               if (q2 > 0 && q > q2) {
 30653                 q = s.indexOf(']>', j + 8);
 30654                 if (q < 0) {
 30655                   throw 'Unexpected EOF[7]';
 30657                 complexDoctype = true;
 30659               var doctypeContent = s.substring(j + 8, q + (complexDoctype ? 1 : 0));
 30660               sink.doctype(doctypeContent);
 30661               j = q + (complexDoctype ? 2 : 1);
 30662             } else {
 30663               throw 'Unknown !tag';
 30665             break;
 30666           default:
 30667             var content = parseContent(s, j);
 30668             var isClosed = false;
 30669             if (s.substring(j + content.parsed, j + content.parsed + 2) === '/>') {
 30670               isClosed = true;
 30671             } else if (s.substring(j + content.parsed, j + content.parsed + 1) !== '>') {
 30672               throw 'Unexpected EOF[2]';
 30674             var scope = {
 30675                 namespaces: []
 30676               };
 30677             var contentAttributes = content.attributes;
 30678             for (q = 0; q < contentAttributes.length; ++q) {
 30679               var attribute = contentAttributes[q];
 30680               var attributeName = attribute.name;
 30681               if (attributeName.substring(0, 6) === 'xmlns:') {
 30682                 var prefix = attributeName.substring(6);
 30683                 var uri = attribute.value;
 30684                 scope.namespaces[prefix] = trim(uri);
 30685                 scope.namespaces.push({
 30686                   uri: uri,
 30687                   prefix: prefix
 30688                 });
 30689                 delete contentAttributes[q];
 30690               } else if (attributeName === 'xmlns') {
 30691                 var uri = attribute.value;
 30692                 scope.namespaces['xmlns'] = trim(uri);
 30693                 scope.namespaces.push({
 30694                   uri: uri,
 30695                   prefix: ''
 30696                 });
 30697                 delete contentAttributes[q];
 30698               } else if (attributeName.substring(0, 4) === 'xml:') {
 30699                 scope[attributeName.substring(4)] = trim(attribute.value);
 30700               } else if (attributeName.substring(0, 3) === 'xml') {
 30701                 throw 'Invalid xml attribute';
 30702               } else {
 30705             scopes.push(scope);
 30706             var attributes = [];
 30707             for (q = 0; q < contentAttributes.length; ++q) {
 30708               attribute = contentAttributes[q];
 30709               if (attribute) {
 30710                 attributes.push({
 30711                   name: getName(attribute.name, false),
 30712                   value: attribute.value
 30713                 });
 30716             sink.beginElement(getName(content.name, true), attributes, scope, isClosed);
 30717             j += content.parsed + (isClosed ? 2 : 1);
 30718             if (isClosed)
 30719               scopes.pop();
 30720             break;
 30722         } else {
 30723           do {
 30724             if (++j >= s.length)
 30725               break;
 30726           } while (s.charAt(j) !== '<');
 30727           var text = s.substring(i, j);
 30728           var isWs = text.replace(/^\s+/, '').length === 0;
 30729           if (!isWs || isWhitespacePreserved()) {
 30730             sink.text(resolveEntities(text), isWs);
 30733         i = j;
 30736     this.parseFromString = function (s, mimeType) {
 30737       var currentElement = new XML('element', '', '', '');
 30738       var elementsStack = [];
 30739       parseXml(s, {
 30740         beginElement: function (name, attrs, scope, isEmpty) {
 30741           var parent = currentElement;
 30742           elementsStack.push(parent);
 30743           currentElement = createNode('element', name.namespace, name.localName, name.prefix);
 30744           for (var i = 0; i < attrs.length; ++i) {
 30745             var rawAttr = attrs[i];
 30746             var attr = createNode('attribute', rawAttr.name.namespace, rawAttr.name.localName, rawAttr.name.prefix);
 30747             attr.value = rawAttr.value;
 30748             currentElement.attributes.push(attr);
 30750           var namespaces = scope.namespaces;
 30751           for (var i = 0; i < namespaces.length; ++i) {
 30752             var rawNs = namespaces[i];
 30753             var ns = ASNamespace.createNamespace(rawNs.uri, rawNs.prefix);
 30754             currentElement.inScopeNamespaces.push(ns);
 30756           parent.insert(parent.length(), currentElement);
 30757           if (isEmpty) {
 30758             currentElement = elementsStack.pop();
 30760         },
 30761         endElement: function (name) {
 30762           currentElement = elementsStack.pop();
 30763         },
 30764         text: function (text, isWhitespace) {
 30765           var node = createNode('text', '', '');
 30766           node.value = text;
 30767           currentElement.insert(currentElement.length(), node);
 30768         },
 30769         cdata: function (text) {
 30770           var node = createNode('text', '', '');
 30771           node.value = text;
 30772           currentElement.insert(currentElement.length(), node);
 30773         },
 30774         comment: function (text) {
 30775         },
 30776         pi: function (name, attrs) {
 30777         },
 30778         doctype: function (text) {
 30780       });
 30781       return currentElement;
 30782     };
 30783     function createNode(kind, uri, name, prefix) {
 30784       return new XML(kind, uri, name, prefix);
 30786   };
 30787   var xmlParser = new XMLParser();
 30788   isXMLType = function isXMLType(val) {
 30789     return val.isXML || val.isXMLList;
 30790   };
 30791   function toString(node) {
 30792     if (typeof node === 'object' && node !== null) {
 30793       switch (node.kind) {
 30794       case 'text':
 30795       case 'attribute':
 30796         return node.value;
 30797       default:
 30798         if (node.hasSimpleContent()) {
 30799           var str = '';
 30800           node.children.forEach(function (v, i) {
 30801             str += toString(v);
 30802           });
 30803           return str;
 30805         return toXMLString(node);
 30807     } else {
 30808       return String(node);
 30811   function toXMLString(node, ancestorNamespaces, indentLevel) {
 30812     return new XMLEncoder(ancestorNamespaces, indentLevel, true).encode(node);
 30814   function toXML(v) {
 30815     if (v === null) {
 30816       throw new TypeError(formatErrorMessage(Errors.ConvertNullToObjectError));
 30817     } else if (v === undefined) {
 30818       throw new TypeError(formatErrorMessage(Errors.ConvertUndefinedToObjectError));
 30819     } else if (v.isXML) {
 30820       return v;
 30821     } else if (v.isXMLList) {
 30822       if (v.length() === 1) {
 30823         return v.children[0];
 30825       throw new TypeError(formatErrorMessage(Errors.XMLMarkupMustBeWellFormed));
 30826     } else {
 30827       var x = xmlParser.parseFromString(String(v));
 30828       if (x.length() === 0) {
 30829         var x = new XML('text');
 30830         return x;
 30831       } else if (x.length() === 1) {
 30832         x.children[0].parent = null;
 30833         return x.children[0];
 30835       throw 'SyntaxError in ToXML';
 30838   var defaultNamespace = '';
 30839   function toXMLList(value) {
 30840     if (value === null) {
 30841       throw new TypeError(formatErrorMessage(Errors.ConvertNullToObjectError));
 30842     } else if (value === undefined) {
 30843       throw new TypeError(formatErrorMessage(Errors.ConvertUndefinedToObjectError));
 30844     } else if (value instanceof XML) {
 30845       var xl = new XMLList(value.parent, value.name);
 30846       xl.append(value);
 30847       return xl;
 30848     } else if (value instanceof XMLList) {
 30849       return value;
 30850     } else {
 30851       var s = '<parent xmlns=\'' + defaultNamespace + '\'>' + String(value) + '</parent>';
 30852       var x = new ASXML(s);
 30853       var xl = new XMLList();
 30854       for (var i = 0; i < x.length(); i++) {
 30855         var v = x.children[i];
 30856         v.parent = null;
 30857         xl.append(v);
 30859       return xl;
 30862   function toAttributeName(v) {
 30863     if (v === undefined || v === null || typeof v === 'boolean' || typeof v === 'number') {
 30864       throw 'TypeError: invalid operand to ToAttributeName()';
 30865     } else if (isXMLType(v)) {
 30866       v = toString(v);
 30867     } else if (v instanceof Object && v !== null) {
 30868       if (v instanceof QName) {
 30869         return new QName(v.uri, v.localName, true);
 30871       v = toString(v);
 30873     if (typeof v === 'string') {
 30874       var ns = new ASNamespace();
 30875       var qn = new QName(ns, v, true);
 30876     } else {
 30878     return qn;
 30880   function toXMLName(mn) {
 30881     return new QName(mn);
 30883   function getDefaultNamespace(scope) {
 30884     while (scope) {
 30885       var obj = scope.object;
 30886       if (obj.defaultNamepsace !== undefined) {
 30887         return obj.defaultNamespace;
 30889       scope = scope.parent;
 30891     var ns = ASNamespace.createNamespace('', '');
 30892     return ns;
 30894   isXMLName = function isXMLName(v) {
 30895     try {
 30896       var qn = new QName(v);
 30897     } catch (e) {
 30898       return false;
 30900     return true;
 30901   };
 30902   function asGetProperty(namespaces, name, flags, isMethod) {
 30903     var mn = isNumeric(name) ? toNumber(name) : name instanceof QName ? name.mn : new Multiname(namespaces ? namespaces : [
 30904         ASNamespace.PUBLIC
 30905       ], name, flags);
 30906     return this.getProperty(mn, isMethod);
 30908   function asSetProperty(namespaces, name, flags, value) {
 30909     var mn = isNumeric(name) ? toNumber(name) : name instanceof QName ? name.mn : new Multiname(namespaces ? namespaces : [
 30910         ASNamespace.PUBLIC
 30911       ], name, flags);
 30912     this.setProperty(mn, value);
 30914   function asHasProperty(namespaces, name, flags) {
 30915     var mn = isNumeric(name) ? toNumber(name) : name instanceof QName ? name.mn : new Multiname(namespaces ? namespaces : [
 30916         ASNamespace.PUBLIC
 30917       ], name, flags);
 30918     return this.hasProperty(mn);
 30920   function asCallProperty(namespaces, name, flags, isLex, args) {
 30921     var receiver = isLex ? null : this;
 30922     var property = this.asGetProperty(namespaces, name, flags, true);
 30923     if (!property) {
 30924       return this.toString().asCallProperty(namespaces ? namespaces : [
 30925         ASNamespace.PUBLIC
 30926       ], name, flags, isLex, args);
 30928     return property.apply(receiver, args);
 30930   var ATTR_NAME = 1;
 30931   var ELEM_NAME = 2;
 30932   var ANY_NAME = 4;
 30933   var ANY_NAMESPACE = 8;
 30934   function nameKind(mn) {
 30935     var flags = 0;
 30936     if (mn.isAttribute()) {
 30937       flags |= ATTR_NAME;
 30938     } else {
 30939       flags |= ELEM_NAME;
 30941     if (mn.isAnyName()) {
 30942       flags |= ANY_NAME;
 30944     if (mn.isAnyNamespace()) {
 30945       flags |= ANY_NAMESPACE;
 30947     return flags;
 30949   XMLClass = function XMLClass(runtime, scope, instanceConstructor, baseClass) {
 30950     var FLAG_IGNORE_COMMENTS = 1;
 30951     var FLAG_IGNORE_PROCESSING_INSTRUCTIONS = 2;
 30952     var FLAG_IGNORE_WHITESPACE = 4;
 30953     var FLAG_PRETTY_PRINTING = 8;
 30954     ASXML = function (value) {
 30955       if (!(this instanceof ASXML)) {
 30956         if (value instanceof ASXML) {
 30957           return value;
 30959         return new ASXML(value);
 30961       if (value === null || value === undefined) {
 30962         value = '';
 30964       var x = toXML(value);
 30965       if (isXMLType(value)) {
 30966         x = x.deepCopy();
 30968       return x;
 30969     };
 30970     XML = function (kind, uri, name, prefix) {
 30971       if (kind === undefined) {
 30972         kind = 'text';
 30974       if (uri === undefined) {
 30975         uri = '';
 30977       if (name === undefined) {
 30978         name = '';
 30980       this.init(kind, uri, name, prefix);
 30981     };
 30982     var c = new Class('XML', ASXML, ApplicationDomain.passthroughCallable(ASXML));
 30983     c.flags = FLAG_IGNORE_COMMENTS | FLAG_IGNORE_PROCESSING_INSTRUCTIONS | FLAG_IGNORE_WHITESPACE | FLAG_PRETTY_PRINTING;
 30984     c.prettyIndent = 2;
 30985     c.extend(baseClass);
 30986     var Xp = XML.prototype = ASXML.prototype;
 30987     Xp.init = function init(kind, uri, name, prefix) {
 30988       this.name = new QName(new Multiname([
 30989         new ASNamespace(prefix, uri)
 30990       ], name));
 30991       this.kind = kind;
 30992       this.parent = null;
 30993       this.inScopeNamespaces = [];
 30994       switch (kind) {
 30995       case 'element':
 30996         this.attributes = [];
 30997         this.children = [];
 30998         break;
 30999       case 'attribute':
 31000       case 'text':
 31001         this.value = '';
 31002         break;
 31003       default:
 31004         break;
 31006       return this;
 31007     };
 31008     Xp.length = function () {
 31009       if (!this.children) {
 31010         return 0;
 31012       return this.children.length;
 31013     };
 31014     Xp.canHandleProperties = true;
 31015     Xp.deepCopy = function () {
 31016       return new ASXML(toXMLString(this));
 31017     };
 31018     Xp.resolveValue = function resolveValue() {
 31019       return this;
 31020     };
 31021     Xp.hasSimpleContent = function hasSimpleContent() {
 31022       if (this.kind === 'comment' || this.kind === 'processing-instruction') {
 31023         return false;
 31025       var result = true;
 31026       if (this.children) {
 31027         this.children.forEach(function (v) {
 31028           if (v.kind === 'element') {
 31029             result = false;
 31031         });
 31033       return result;
 31034     };
 31035     Xp.asGetEnumerableKeys = function asGetEnumerableKeys() {
 31036       if (Xp === this) {
 31037         return Object.prototype.asGetEnumerableKeys.call(this);
 31039       var keys = [];
 31040       this.children.forEach(function (v, i) {
 31041         keys.push(v.name);
 31042       });
 31043       return keys;
 31044     };
 31045     function setAttribute(node, name, value) {
 31046       if (node.nodeType === Node.DOCUMENT_NODE) {
 31047         node.childNodes[0].setAttribute(name, value);
 31048       } else if (node.nodeType === Node.ELEMENT_NODE) {
 31049         node.setAttribute(name, value);
 31050       } else {
 31051         throw 'error or unhandled case in setAttribute';
 31054     Xp.setProperty = function (p, v) {
 31055       var x, i, c, n;
 31056       x = this;
 31057       if (p === p >>> 0) {
 31058         throw 'TypeError in XML.prototype.setProperty(): invalid property name ' + p;
 31060       if (x.kind === 'text' || x.kind === 'comment' || x.kind === 'processing-instruction' || x.kind === 'attribute') {
 31061         return;
 31063       if (!v || !v.isXML && !v.isXMLList || v.kind === 'text' || v.kind === 'attribute') {
 31064         c = toString(v);
 31065       } else {
 31066         c = v.deepCopy();
 31068       n = toXMLName(p);
 31069       if (n.isAttr) {
 31070         if (!this.attributes) {
 31071           return;
 31073         this.attributes.forEach(function (v, i, o) {
 31074           if (v.name === n.localName) {
 31075             delete o[i];
 31077         });
 31078         var a = new XML('attribute', n.uri, n.localName);
 31079         a.value = v;
 31080         a.parent = this;
 31081         this.attributes.push(a);
 31082         return;
 31084       var isValidName = isXMLName(n);
 31085       if (!isValidName && n.localName !== '*') {
 31086         return;
 31088       var i = undefined;
 31089       var primitiveAssign = !isXMLType(c) && n.localName !== '*';
 31090       for (var k = x.length() - 1; k >= 0; k--) {
 31091         if ((n.isAny || x.children[k].kind === 'element' && x.children[k].name.localName === n.localName) && (n.uri === null || x.children[k].kind === 'element' && x.children[k].name.uri === n.uri)) {
 31092           if (i !== undefined) {
 31093             x.deleteByIndex(String(i));
 31095           i = k;
 31098       if (i === undefined) {
 31099         i = x.length();
 31100         if (primitiveAssign) {
 31101           if (n.uri === null) {
 31102             var name = new QName(getDefaultNamespace(scope), n);
 31103           } else {
 31104             var name = new QName(n);
 31106           var y = new XML('element', name.uri, name.localName, name.prefix);
 31107           y.parent = x;
 31108           var ns = name.getNamespace();
 31109           x.replace(String(i), y);
 31110           y.addInScopeNamespace(ns);
 31113       if (primitiveAssign) {
 31114         x.children[i].children = [];
 31115         var s = toString(c);
 31116         if (s !== '') {
 31117           x.children[i].replace('0', s);
 31119       } else {
 31120         x.replace(String(i), c);
 31122       return;
 31123     };
 31124     Xp.asGetProperty = asGetProperty;
 31125     Xp.asGetResolvedStringProperty = asGetResolvedStringPropertyFallback;
 31126     Xp.asSetProperty = asSetProperty;
 31127     Xp.asHasProperty = asHasProperty;
 31128     Xp.asCallProperty = asCallProperty;
 31129     Xp.getProperty = function (mn, isMethod) {
 31130       if (isMethod) {
 31131         var resolved = Multiname.isQName(mn) ? mn : this.resolveMultinameProperty(mn.namespaces, mn.name, mn.flags);
 31132         return this[Multiname.getQualifiedName(resolved)];
 31134       if (!Multiname.isQName(mn) && isNumeric(mn)) {
 31135         if (Number(0) === 0) {
 31136           return this;
 31138         return null;
 31140       var x = this;
 31141       var name = toXMLName(mn);
 31142       var xl = new XMLList(x, name);
 31143       var flags = nameKind(name.mn);
 31144       var anyName = flags & ANY_NAME;
 31145       var anyNamespace = flags & ANY_NAMESPACE;
 31146       if (flags & ATTR_NAME) {
 31147         if (x.attributes) {
 31148           x.attributes.forEach(function (v, i) {
 31149             if ((anyName || v.name.localName === name.localName) && (anyNamespace || v.name.uri === name.uri)) {
 31150               xl.append(v);
 31152           });
 31154       } else {
 31155         x.children.forEach(function (v, i) {
 31156           if ((anyName || v.kind === 'element' && v.name.localName === name.localName) && (anyNamespace || v.kind === 'element' && v.name.uri === name.uri)) {
 31157             xl.append(v);
 31159         });
 31161       return xl;
 31162     };
 31163     Xp.hasProperty = function (mn, isMethod) {
 31164       if (isMethod) {
 31165         var resolved = Multiname.isQName(mn) ? mn : this.resolveMultinameProperty(mn.namespaces, mn.name, mn.flags);
 31166         return !(!this[Multiname.getQualifiedName(resolved)]);
 31168       if (!Multiname.isQName(mn) && isNumeric(mn)) {
 31169         if (Number(0) === 0) {
 31170           return true;
 31172         return false;
 31174       var name = toXMLName(mn);
 31175       var flags = nameKind(name.mn);
 31176       var anyName = flags & ANY_NAME;
 31177       var anyNamespace = flags & ANY_NAMESPACE;
 31178       if (flags & ATTR_NAME) {
 31179         return this.attributes.some(function (v, i) {
 31180           if ((anyName || v.name.localName === name.localName) && (anyNamespace || v.name.uri === name.uri)) {
 31181             return true;
 31183         });
 31184         if (x.attributes) {
 31185           x.attributes.forEach(function (v, i) {
 31186             if ((anyName || v.name.localName === name.localName) && (anyNamespace || v.name.uri === name.uri)) {
 31187               xl.append(v);
 31189           });
 31191       } else {
 31192         if (this.children.some(function (v, i) {
 31193             if ((anyName || v.kind === 'element' && v.name.localName === name.localName) && (anyNamespace || v.kind === 'element' && v.name.uri === name.uri)) {
 31194               return true;
 31196           })) {
 31197           return true;
 31199         var resolved = Multiname.isQName(mn) ? mn : this.resolveMultinameProperty(mn.namespaces, mn.name, mn.flags);
 31200         return !(!this[Multiname.getQualifiedName(resolved)]);
 31202     };
 31203     Xp.delete = function (key, isMethod) {
 31204       notImplemented('XML.[[Delete]]');
 31205     };
 31206     Xp.deleteByIndex = function (p) {
 31207       var x = this;
 31208       var i = p >>> 0;
 31209       if (String(i) !== String(p)) {
 31210         throw 'TypeError in XML.prototype.deleteByIndex(): invalid index ' + p;
 31212       if (p < x.length()) {
 31213         if (x.children[p]) {
 31214           x.children[p].parent = null;
 31215           delete x.children[p];
 31216           for (q = i + 1; q < x.length(); q++) {
 31217             x.children[q - 1] = x.children[q];
 31219           x.children.length = x.children.length - 1;
 31222     };
 31223     Xp.isXML = true;
 31224     Xp.insert = function insert(p, v) {
 31225       var x, s, i, n;
 31226       x = this;
 31227       if (x.kind === 'text' || x.kind === 'comment' || x.kind === 'processing-instruction' || x.kind === 'attribute') {
 31228         return;
 31230       i = p >>> 0;
 31231       if (String(p) !== String(i)) {
 31232         throw 'TypeError in XML.prototype.insert(): invalid property name ' + p;
 31234       if (x.kind === 'element') {
 31235         var a = x;
 31236         while (a) {
 31237           if (a === v) {
 31238             throw 'Error in XML.prototype.insert()';
 31240           a = a.parent;
 31243       if (x.isXMLList) {
 31244         n = x.length();
 31245         if (n === 0) {
 31246           return;
 31248       } else {
 31249         n = 1;
 31251       for (var j = x.length() - 1; j >= i; j--) {
 31252         x[j + n] = x[j];
 31254       if (x.isXMLList) {
 31255         n = v.length();
 31256         for (var j = 0; j < n; j++) {
 31257           v.children[j].parent = x;
 31258           x[i + j] = v[j];
 31260       } else {
 31261         v.parent = x;
 31262         x.children[i] = v;
 31264     };
 31265     Xp.replace = function (p, v) {
 31266       var x, s;
 31267       x = this;
 31268       if (x.kind === 'text' || x.kind === 'comment' || x.kind === 'processing-instruction' || x.kind === 'attribute') {
 31269         return;
 31271       var i = p >>> 0;
 31272       if (String(p) !== String(i)) {
 31273         throw 'TypeError in XML.prototype.replace(): invalid name ' + p;
 31275       if (i >= x.length()) {
 31276         p = String(x.length());
 31278       if (v.kind === 'element') {
 31279         var a = x;
 31280         while (a) {
 31281           if (a === v) {
 31282             throw 'Error in XML.prototype.replace()';
 31284           a = a.parent;
 31287       if (v.kind === 'element' || v.kind === 'text' || v.kind === 'comment' || v.kind === 'processing-instruction') {
 31288         v.parent = x;
 31289         if (x[p]) {
 31290           x.children[p].parent = null;
 31292         x.children[p] = v;
 31293       } else if (x.isXMLList) {
 31294         x.deleteByIndex(p);
 31295         x.insert(p, v);
 31296       } else {
 31297         s = toString(v);
 31298         t = new XML();
 31299         t.parent = x;
 31300         t.value = s;
 31301         if (x[p]) {
 31302           x.children[p].parent = null;
 31304         x.children[p] = t;
 31306     };
 31307     Xp.addInScopeNamespace = function (ns) {
 31308       var x, s;
 31309       x = this;
 31310       if (x.kind === 'text' || x.kind === 'comment' || x.kind === 'processing-instruction' || x.kind === 'attribute') {
 31311         return;
 31313       if (ns.prefix !== undefined) {
 31314         if (ns.prefix === '' && x.name.uri === '') {
 31315           return;
 31317         var match = null;
 31318         x.inScopeNamespaces.forEach(function (v, i) {
 31319           if (v.prefix === ns.prefix) {
 31320             match = v;
 31322         });
 31323         if (match !== null && match.uri !== ns.uri) {
 31324           x.inScopeNamespaces.forEach(function (v, i) {
 31325             if (v.prefix === match.prefix) {
 31326               x.inScopeNamespaces[i] = ns;
 31328           });
 31330         if (x.name.prefix === ns.prefix) {
 31331           x.name.prefix = undefined;
 31333         x.attributes.forEach(function (v, i) {
 31334           if (v.name.prefix === ns.name.prefix) {
 31335             v.name.prefix = undefined;
 31337         });
 31339     };
 31340     Xp.descendants = function (name) {
 31341       name = toXMLName(name);
 31342       var x = this;
 31343       var xl = new XMLList();
 31344       if (x.kind !== 'element') {
 31345         return xl;
 31347       if (name.isAttr) {
 31348         this.attributes.forEach(function (v, i) {
 31349           if (name.isAny || name.localName === v.name.localName) {
 31350             xl.append(v);
 31352         });
 31353       } else {
 31354         this.children.forEach(function (v, i) {
 31355           if (name.isAny || name.localName === v.name.localName) {
 31356             xl.append(v);
 31358         });
 31360       this.children.forEach(function (v, i) {
 31361         xl.append(v.descendants(name));
 31362       });
 31363       return xl;
 31364     };
 31365     Xp.comments = function () {
 31366       var x = this;
 31367       var xl = new XMLList(x, null);
 31368       x.children.forEach(function (v, i) {
 31369         if (v.kind === 'comment') {
 31370           xl.append(v);
 31372       });
 31373       return xl;
 31374     };
 31375     Xp.text = function () {
 31376       var x = this;
 31377       var xl = new XMLList(x, null);
 31378       x.children.forEach(function (v, i) {
 31379         if (v.kind === 'text') {
 31380           xl.append(v);
 31382       });
 31383       return xl;
 31384     };
 31385     c.native = {
 31386       static: {
 31387         ignoreComments: {
 31388           get: function ignoreComments() {
 31389             return getBitFlags(c.flags, FLAG_IGNORE_COMMENTS);
 31390           },
 31391           set: function ignoreComments(newIgnore) {
 31392             c.flags = setBitFlags(c.flags, FLAG_IGNORE_COMMENTS, newIgnore);
 31394         },
 31395         ignoreProcessingInstructions: {
 31396           get: function ignoreProcessingInstructions() {
 31397             return getBitFlags(c.flags, FLAG_IGNORE_PROCESSING_INSTRUCTIONS);
 31398           },
 31399           set: function ignoreProcessingInstructions(newIgnore) {
 31400             c.flags = setBitFlags(c.flags, FLAG_IGNORE_PROCESSING_INSTRUCTIONS, newIgnore);
 31402         },
 31403         ignoreWhitespace: {
 31404           get: function ignoreWhitespace() {
 31405             return getBitFlags(c.flags, FLAG_IGNORE_WHITESPACE);
 31406           },
 31407           set: function ignoreWhitespace(newIgnore) {
 31408             c.flags = setBitFlags(c.flags, FLAG_IGNORE_WHITESPACE, newIgnore);
 31410         },
 31411         prettyPrinting: {
 31412           get: function prettyPrinting() {
 31413             return getBitFlags(c.flags, FLAG_PRETTY_PRINTING);
 31414           },
 31415           set: function prettyPrinting(newPretty) {
 31416             c.flags = setBitFlags(c.flags, FLAG_PRETTY_PRINTING, newPretty);
 31418         },
 31419         prettyIndent: {
 31420           get: function prettyIndent() {
 31421             return c.prettyIndent;
 31422           },
 31423           set: function prettyIndent(newIndent) {
 31424             c.prettyIndent = newIndent;
 31427       },
 31428       instance: {
 31429         toString: function () {
 31430           return toString(this);
 31431         },
 31432         hasOwnProperty: function hasOwnProperty(P) {
 31433           somewhatImplemented('XML.hasOwnProperty');
 31434           return this.hasProperty(P);
 31435         },
 31436         propertyIsEnumerable: function propertyIsEnumerable(P) {
 31437           notImplemented('XML.propertyIsEnumerable');
 31438         },
 31439         addNamespace: function addNamespace(ns) {
 31440           notImplemented('XML.addNamespace');
 31441         },
 31442         appendChild: function appendChild(child) {
 31443           var children = this.getProperty('*');
 31444           children.setProperty(children.length(), child);
 31445           return this;
 31446         },
 31447         attribute: function attribute(name) {
 31448           return this.getProperty(toAttributeName(name));
 31449         },
 31450         attributes: function attributes() {
 31451           return this.getProperty(toAttributeName('*'));
 31452         },
 31453         child: function child(name) {
 31454           return this.getProperty(name);
 31455         },
 31456         childIndex: function childIndex() {
 31457           notImplemented('XML.childIndex');
 31458         },
 31459         children: function children() {
 31460           var list = new XMLList();
 31461           Array.prototype.push.apply(list.children, this.children);
 31462           return list;
 31463         },
 31464         comments: function comments() {
 31465           return this.comments();
 31466         },
 31467         contains: function contains(value) {
 31468           notImplemented('XML.contains');
 31469         },
 31470         copy: function copy() {
 31471           return this.deepCopy();
 31472         },
 31473         descendants: function descendants(name) {
 31474           if (name === undefined) {
 31475             name = '*';
 31477           return this.descendants(name);
 31478         },
 31479         elements: function elements(name) {
 31480           var x = this;
 31481           var any = false;
 31482           if (name === undefined) {
 31483             name = '*';
 31484             any = true;
 31486           var name = toXMLName(name);
 31487           var xl = new XMLList(this.parent, name);
 31488           x.children.forEach(function (v, i) {
 31489             if (v.kind === 'element' && (any || v.name.localName === name.localName) && (name.uri === null || v.kind === 'element' && v.name.uri === name.uri)) {
 31490               xl.append(v);
 31492           });
 31493           return xl;
 31494         },
 31495         hasComplexContent: function hasComplexContent() {
 31496           notImplemented('XML.hasComplexContent');
 31497         },
 31498         hasSimpleContent: function hasSimpleContent() {
 31499           return this.hasSimpleContent();
 31500         },
 31501         inScopeNamespaces: function inScopeNamespaces() {
 31502           notImplemented('XML.inScopeNamespaces');
 31503         },
 31504         insertChildAfter: function insertChildAfter(child1, child2) {
 31505           notImplemented('XML.insertChildAfter');
 31506         },
 31507         insertChildBefore: function insertChildBefore(child1, child2) {
 31508           notImplemented('XML.insertChildBefore');
 31509         },
 31510         localName: function localName() {
 31511           return this.name.localName;
 31512         },
 31513         name: function name() {
 31514           return this.name;
 31515         },
 31516         _namespace: function _namespace(prefix, argc) {
 31517           somewhatImplemented('XML._namespace()');
 31518           return this.name.uri;
 31519         },
 31520         namespaceDeclarations: function namespaceDeclarations() {
 31521           return new XMLList();
 31522         },
 31523         nodeKind: function nodeKind() {
 31524           return this.kind;
 31525         },
 31526         normalize: function normalize() {
 31527           notImplemented('XML.normalize');
 31528         },
 31529         parent: function parent() {
 31530           notImplemented('XML.parent');
 31531         },
 31532         processingInstructions: function processingInstructions(name) {
 31533           notImplemented('XML.processingInstructions');
 31534         },
 31535         prependChild: function prependChild(value) {
 31536           notImplemented('XML.prependChild');
 31537         },
 31538         removeNamespace: function removeNamespace(ns) {
 31539           notImplemented('XML.removeNamespace');
 31540         },
 31541         replace: function replace(propertyName, value) {
 31542           var c, x, s, i;
 31543           x = this;
 31544           if (x.kind === 'text' || x.kind === 'comment' || x.kind === 'processing-instruction' || x.kind === 'attribute') {
 31545             return x;
 31547           if (!isXMLType(value)) {
 31548             c = value.toString();
 31549           } else {
 31550             c = value.deepCopy();
 31552           var i = propertyName >>> 0;
 31553           if (String(propertyName) === String(i)) {
 31554             x.replace(propertyName, c);
 31555             return x;
 31557           n = new QName(propertyName);
 31558           i = undefined;
 31559           for (k = x.length() - 1; k >= 0; k--) {
 31560             var v = x.children[k];
 31561             if (n.isAny || v.kind === 'element' && v.name.localName === n.localName && (n.uri === null || v.kind === 'element' && v.name.uri === n.uri)) {
 31562               if (i !== undefined) {
 31563                 x.deleteByIndex(String(i));
 31565               i = k;
 31568           if (i !== undefined) {
 31569             x.replace(i.toString(), c);
 31571           return x;
 31572         },
 31573         setChildren: function setChildren(value) {
 31574           notImplemented('XML.setChildren');
 31575         },
 31576         setLocalName: function setLocalName(name) {
 31577           notImplemented('XML.setLocalName');
 31578         },
 31579         setName: function setName(name) {
 31580           notImplemented('XML.setName');
 31581         },
 31582         setNamespace: function setNamespace(ns) {
 31583           notImplemented('XML.setNamespace');
 31584         },
 31585         text: function text() {
 31586           return this.text();
 31587         },
 31588         toXMLString: function () {
 31589           return toXMLString(this);
 31590         },
 31591         notification: function notification() {
 31592           notImplemented('XML.notification');
 31593         },
 31594         setNotification: function setNotification(f) {
 31595           notImplemented('XML.setNotification');
 31598     };
 31599     return c;
 31600   };
 31601   XMLListClass = function XMLListClass(runtime, scope, instanceConstructor, baseClass) {
 31602     ASXMLList = function (value) {
 31603       if (!(this instanceof ASXMLList)) {
 31604         return callXMLList(value);
 31606       return constructXMLList(value);
 31607     };
 31608     function callXMLList(v) {
 31609       if (v === null || v === undefined) {
 31610         v = '';
 31612       return toXMLList(v);
 31614     function constructXMLList(val) {
 31615       if (val === null || val === undefined) {
 31616         val = '';
 31618       if (val.isXMLList) {
 31619         var xl = new XMLList();
 31620         xl.append(val);
 31621         return xl;
 31623       return toXMLList(val);
 31625     XMLList = function (targetObject, targetProperty) {
 31626       this.targetObject = targetObject ? targetObject : null;
 31627       this.targetProperty = targetProperty ? targetProperty : null;
 31628       this.children = [];
 31629     };
 31630     var c = new Class('XMLList', ASXMLList, ApplicationDomain.passthroughCallable(ASXMLList));
 31631     c.extend(baseClass);
 31632     var XLp = XMLList.prototype = ASXMLList.prototype;
 31633     XLp.canHandleProperties = true;
 31634     XLp.hasSimpleContent = function hasSimpleContent() {
 31635       if (this.length() === 0) {
 31636         return true;
 31637       } else if (this.length() === 1) {
 31638         return toXML(this).hasSimpleContent();
 31640       var result = true;
 31641       this.children.forEach(function (v) {
 31642         if (v.kind === 'element') {
 31643           result = false;
 31645       });
 31646       return result;
 31647     };
 31648     XLp.asGetProperty = asGetProperty;
 31649     XLp.asGetResolvedStringProperty = asGetResolvedStringPropertyFallback;
 31650     XLp.asSetProperty = asSetProperty;
 31651     XLp.asHasProperty = asHasProperty;
 31652     XLp.asCallProperty = asCallProperty;
 31653     XLp.setProperty = function (mn, v, isMethod) {
 31654       var x, i, r;
 31655       x = this;
 31656       i = mn >>> 0;
 31657       if (String(mn) === String(i)) {
 31658         var targetObject = this.targetObject;
 31659         var targetProperty = this.targetProperty;
 31660         if (targetObject !== null) {
 31661           r = targetObject.resolveValue();
 31662           if (r === null) {
 31663             return;
 31665         } else {
 31666           r = null;
 31668         if (i >= x.length()) {
 31669           if (r && r.isXMLList) {
 31670             if (r.length !== 1) {
 31671               return;
 31672             } else {
 31673               r = r.children[0];
 31676           if (r && r.kind !== 'element') {
 31677             return;
 31679           var y = new XML();
 31680           y.parent = r;
 31681           y.name = x.targetProperty;
 31682           if (targetProperty === null || targetProperty.localName === '*') {
 31683             y.name = null;
 31684             y.kind = 'text';
 31685           } else if (targetProperty.isAttr) {
 31686             var attributeExists = r.getProperty(y.name);
 31687             if (attributeExists.length() > 0) {
 31688               return;
 31690             r.kind = 'attribute';
 31691           } else {
 31692             y.kind = 'element';
 31694           i = x.length();
 31695           if (y.kind !== 'attribute') {
 31696             if (r !== null) {
 31697               if (i > 0) {
 31698                 var j = 0;
 31699                 while (j < r.length() - 1 && r.children[j] !== x.children[i - 1]) {
 31700                   j++;
 31702               } else {
 31703                 var j = r.length() - 1;
 31705               r.insert(String(j + 1), y);
 31707             if (v.isXML) {
 31708               y.name = v.name;
 31709             } else if (v.isXMLList) {
 31710               y.name = v.targetProperty;
 31713           x.append(y);
 31715         if (!v.isXML && !v.isXMLList || v.kind === 'text' || v.kind === 'attribute') {
 31716           v = toString(v);
 31718         if (x.children[i].kind === 'attribute') {
 31719           var z = toAttributeName(x.children[i].name);
 31720           x.children[i].parent.setProperty(z, v);
 31721           var attr = x.children[i].parent.getProperty(z);
 31722           x.children[i] = attr.children[0];
 31723         } else if (v.isXMLList) {
 31724           var c = v.deepCopy();
 31725           var parent = x.children[i].parent;
 31726           if (parent !== null) {
 31727             var q;
 31728             parent.children.some(function (v, p) {
 31729               if (v == x.children[i]) {
 31730                 q = p;
 31731                 return true;
 31733             });
 31734             parent.replace(q, c);
 31735             c.children.forEach(function (v, j) {
 31736               c.children[j] = parent.children[q >>> 0 + j];
 31737             });
 31739           if (c.length() === 0) {
 31740             for (var j = x + 1; j < x.length() - 1; j++) {
 31741               x.children[String(j - 1)] = x.children[j];
 31743           } else {
 31744             for (var j = x.length() - 1; j >= i + 1; j--) {
 31745               x.children[String(j + c.length() - 1)] = x.children[j];
 31748           for (var j = 0; j < c.length(); j++) {
 31749             x.children[i + j] = c.children[j];
 31751         } else if (v.isXML || (k = x.children[i].kind) === 'text' || k === 'comment' || k === 'processing-instruction') {
 31752           var parent = x.children[i].parent;
 31753           if (parent !== null) {
 31754             var q;
 31755             parent.children.some(function (v, p) {
 31756               if (v == x.children[i]) {
 31757                 q = p;
 31758                 return true;
 31760             });
 31761             parent.replace(q, v);
 31762             var v = parent.children[q];
 31764           if (typeof v === 'string') {
 31765             var t = new XML('text');
 31766             t.parent = x;
 31767             t.value = v;
 31768             x.children[i] = t;
 31769           } else {
 31770             x.children[i] = v;
 31772         } else {
 31773           x.children[i].setProperty('*', v);
 31775       } else if (x.length() <= 1) {
 31776         if (x.length() === 0) {
 31777           r = x.resolveValue();
 31778           if (r === null || r.length() !== 1) {
 31779             return;
 31781           x.append(r);
 31783         x.children[0].setProperty(mn, v);
 31785     };
 31786     XLp.getProperty = function (mn, isMethod) {
 31787       if (isMethod) {
 31788         var resolved = Multiname.isQName(mn) ? mn : this.resolveMultinameProperty(mn.namespaces, mn.name, mn.flags);
 31789         return this[Multiname.getQualifiedName(resolved)];
 31791       var x = this;
 31792       var i = mn >>> 0;
 31793       if (String(mn) === String(i)) {
 31794         return x.children[mn];
 31796       var name = toXMLName(mn);
 31797       var xl = new XMLList(this, name);
 31798       x.children.forEach(function (v, i) {
 31799         var xl2;
 31800         if (v.kind === 'element') {
 31801           xl2 = v.getProperty(mn);
 31802           if (xl2.length() > 0) {
 31803             xl.append(xl2);
 31806       });
 31807       return xl;
 31808     };
 31809     XLp.hasProperty = function (mn, isMethod) {
 31810       if (isMethod) {
 31811         var resolved = Multiname.isQName(mn) ? mn : this.resolveMultinameProperty(mn.namespaces, mn.name, mn.flags);
 31812         return !(!this[Multiname.getQualifiedName(resolved)]);
 31814       var x = this;
 31815       var i = mn >>> 0;
 31816       if (String(mn) === String(i)) {
 31817         return !(!x.children[mn]);
 31819       var name = toXMLName(mn);
 31820       return this.children.some(function (v, i) {
 31821         var xl2 = v.getProperty(mn);
 31822         if (xl2.length() > 0) {
 31823           return true;
 31825       });
 31826     };
 31827     XLp.delete = function (key, isMethod) {
 31828     };
 31829     XLp.append = function (val) {
 31830       if (val.isXMLList) {
 31831         this.targetObject = val.targetObject;
 31832         this.targetProperty = val.targetProperty;
 31833         if (val.length() === 0) {
 31834           return;
 31836         for (var i = 0; i < val.length(); i++) {
 31837           this.children.push(val.children[i]);
 31839       } else if (val.isXML) {
 31840         this.children.push(val);
 31842     };
 31843     XLp.length = function () {
 31844       return this.children.length;
 31845     };
 31846     XLp.resolve = function () {
 31847       var base = this.targetObject.resolveValue();
 31848       if (base === null) {
 31849         return null;
 31851       var target = this.targetObject.getProperty(this.targetProperty);
 31852       if (base.length === 0) {
 31853         notImplemented('XMLList.resolve');
 31854         base.setProperty(this.targetProperty, '');
 31855         target = base.getProperty(this.targetProperty);
 31856         return target;
 31858     };
 31859     XLp.deepCopy = function () {
 31860       var xl = new XMLList();
 31861       this.children.forEach(function (v, i) {
 31862         xl.children[i] = v.deepCopy();
 31863       });
 31864       return xl;
 31865     };
 31866     XLp.descendants = function (name) {
 31867       var xl = new XMLList(null);
 31868       this.children.forEach(function (v, i) {
 31869         if (v.kind === 'element') {
 31870           xl.append(v.descendants(name));
 31872       });
 31873       return xl;
 31874     };
 31875     XLp.resolveValue = function resolveValue() {
 31876       if (this.length() > 0) {
 31877         return this;
 31879       var x = this;
 31880       var name = x.name;
 31881       var targetObject = x.targetObject;
 31882       var targetProperty = x.targetProperty;
 31883       if (targetObject === null || targetProperty === null || name.isAttr || name.isAny) {
 31884         return null;
 31886       var base = targetObject.resolveValue();
 31887       if (base === null) {
 31888         return null;
 31890       var target = base.getProperty(targetProperty);
 31891       if (target.length() === 0) {
 31892         if (base.isXMLList && base.length() > 1) {
 31893           return null;
 31895         base.setProperty(targetProperty, '');
 31896         target = base.getProperty(targetProperty);
 31898       return target;
 31899     };
 31900     XLp.asGetEnumerableKeys = function asGetEnumerableKeys() {
 31901       if (XLp === this) {
 31902         return Object.prototype.asGetEnumerableKeys.call(this);
 31904       var keys = [];
 31905       this.children.forEach(function (v, i) {
 31906         keys.push(i);
 31907       });
 31908       return keys;
 31909     };
 31910     c.native = {
 31911       instance: {
 31912         init: function () {
 31915     };
 31916     XLp.isXMLList = true;
 31917     c.native = {
 31918       static: {},
 31919       instance: {
 31920         toString: function () {
 31921           return toString(this);
 31922         },
 31923         hasOwnProperty: function hasOwnProperty(P) {
 31924           somewhatImplemented('XMLList.hasOwnProperty');
 31925           return this.hasProperty(P);
 31926         },
 31927         propertyIsEnumerable: function propertyIsEnumerable(P) {
 31928           notImplemented('XMLList.propertyIsEnumerable');
 31929         },
 31930         attribute: function attribute(name) {
 31931           return this.getProperty(toAttributeName(name));
 31932         },
 31933         attributes: function attributes() {
 31934           return this.getProperty(toAttributeName('*'));
 31935         },
 31936         child: function child(propertyName) {
 31937           notImplemented('XMLList.child');
 31938         },
 31939         children: function children() {
 31940           var list = new XMLList();
 31941           for (var i = 0; i < this.children.length; i++) {
 31942             var child = this.children[i];
 31943             Array.prototype.push.apply(list.children, child.children);
 31945           return list;
 31946         },
 31947         comments: function comments() {
 31948           var x = this;
 31949           var xl = new XMLList(x, null);
 31950           x.children.forEach(function (v, i) {
 31951             if (v.kind === 'element') {
 31952               xl.append(v.comments());
 31954           });
 31955           return xl;
 31956         },
 31957         contains: function contains(value) {
 31958           for (var i = 0; i < this.children.length; i++) {
 31959             if (this.children[i] === value) {
 31960               return true;
 31963           return false;
 31964         },
 31965         copy: function copy() {
 31966           return this.deepCopy();
 31967         },
 31968         descendants: function descendants(name) {
 31969           return this.descendants(name === undefined ? '*' : name);
 31970         },
 31971         elements: function elements(name) {
 31972           var x = this;
 31973           var any = false;
 31974           if (name === undefined) {
 31975             name = '*';
 31976             any = true;
 31978           var name = toXMLName(name);
 31979           var xl = new XMLList(x, name);
 31980           x.children.forEach(function (v, i) {
 31981             if (v.kind === 'element') {
 31982               xl.append(v.comments());
 31984           });
 31985           return xl;
 31986         },
 31987         hasComplexContent: function hasComplexContent() {
 31988           notImplemented('XMLList.hasComplexContent');
 31989         },
 31990         hasSimpleContent: function hasSimpleContent() {
 31991           return this.hasSimpleContent();
 31992         },
 31993         length: function length() {
 31994           return this.children.length;
 31995         },
 31996         name: function name() {
 31997           return toXML(this).name;
 31998         },
 31999         normalize: function normalize() {
 32000           notImplemented('XMLList.normalize');
 32001         },
 32002         parent: function parent() {
 32003           notImplemented('XMLList.parent');
 32004         },
 32005         processingInstructions: function processingInstructions(name) {
 32006           notImplemented('XMLList.processingInstructions');
 32007         },
 32008         text: function text() {
 32009           var x = this;
 32010           var xl = new XMLList(x, null);
 32011           x.children.forEach(function (v, i) {
 32012             if (v.kind === 'text' || v.kind === 'element') {
 32013               xl.append(v.text());
 32015           });
 32016           return xl;
 32017         },
 32018         toXMLString: function () {
 32019           return toXMLString(this);
 32020         },
 32021         addNamespace: function addNamespace(ns) {
 32022           notImplemented('XMLList.addNamespace');
 32023         },
 32024         appendChild: function appendChild(child) {
 32025           toXML(this).appendChild(child);
 32026           return this;
 32027         },
 32028         childIndex: function childIndex() {
 32029           notImplemented('XMLList.childIndex');
 32030         },
 32031         inScopeNamespaces: function inScopeNamespaces() {
 32032           notImplemented('XMLList.inScopeNamespaces');
 32033         },
 32034         insertChildAfter: function insertChildAfter(child1, child2) {
 32035           notImplemented('XMLList.insertChildAfter');
 32036         },
 32037         insertChildBefore: function insertChildBefore(child1, child2) {
 32038           notImplemented('XMLList.insertChildBefore');
 32039         },
 32040         nodeKind: function nodeKind() {
 32041           return toXML(this).kind;
 32042         },
 32043         _namespace: function _namespace(prefix, argc) {
 32044           notImplemented('XMLList._namespace');
 32045         },
 32046         localName: function localName() {
 32047           notImplemented('XMLList.localName');
 32048         },
 32049         namespaceDeclarations: function namespaceDeclarations() {
 32050           somewhatImplemented('XMLList.prototype.namespaceDeclarations()');
 32051           return new XMLList();
 32052         },
 32053         prependChild: function prependChild(value) {
 32054           notImplemented('XMLList.prependChild');
 32055         },
 32056         removeNamespace: function removeNamespace(ns) {
 32057           notImplemented('XMLList.removeNamespace');
 32058         },
 32059         replace: function replace(propertyName, value) {
 32060           toXML(this).replace(propertyName, value);
 32061           return this;
 32062         },
 32063         setChildren: function setChildren(value) {
 32064           notImplemented('XMLList.setChildren');
 32065         },
 32066         setLocalName: function setLocalName(name) {
 32067           notImplemented('XMLList.setLocalName');
 32068         },
 32069         setName: function setName(name) {
 32070           notImplemented('XMLList.setName');
 32071         },
 32072         setNamespace: function setNamespace(ns) {
 32073           notImplemented('XMLList.setNamespace');
 32076     };
 32077     return c;
 32078   };
 32079   QNameClass = function QNameClass(runtime, scope, instanceConstructor, baseClass) {
 32080     QName = function QName(ns, name, isAttr) {
 32081       if (!(this instanceof QName)) {
 32082         if (name === undefined && ns instanceof QName) {
 32083           return ns;
 32084         } else {
 32085           return new QName(ns, name);
 32088       if (name === undefined) {
 32089         name = ns;
 32090         ns = undefined;
 32092       if (typeof ns === 'string' || ns instanceof QName) {
 32093         ns = new ASNamespace(ns);
 32095       var mn;
 32096       if (name instanceof QName) {
 32097         if (ns === undefined) {
 32098           mn = name.mn;
 32099         } else {
 32100           mn = new Multiname([
 32101             ns
 32102           ], name.mn.getName());
 32104       } else if (name instanceof Multiname) {
 32105         if (ns === undefined) {
 32106           if (name.isQName() || name.isAnyName() || name.isAnyNamespace()) {
 32107             mn = name;
 32108           } else {
 32109             mn = new Multiname([
 32110               getDefaultNamespace(scope)
 32111             ], name.getName(), name.flags);
 32113         } else {
 32114           mn = new Multiname([
 32115             ns
 32116           ], name.getName(), name.flags);
 32118       } else if (name === '*') {
 32119         mn = new Multiname([], null, isAttr ? Multiname.ATTRIBUTE : 0);
 32120       } else if (name === '@*') {
 32121         mn = new Multiname([], null, Multiname.ATTRIBUTE);
 32122       } else {
 32123         ns = ns === undefined ? getDefaultNamespace(scope) : ns;
 32124         if (name === undefined) {
 32125           mn = new Multiname([
 32126             ns
 32127           ], '');
 32128         } else {
 32129           mn = new Multiname([
 32130             ns
 32131           ], toString(name), isAttr ? Multiname.ATTRIBUTE : 0);
 32134       this.mn = mn;
 32135       this.isAny = mn.isAnyName();
 32136       this.isAnyNamespace = mn.isAnyNamespace();
 32137       this.isAttr = mn.isAttribute();
 32138     };
 32139     var c = new Class('QName', QName, ApplicationDomain.passthroughCallable(QName));
 32140     c.extend(baseClass);
 32141     QNp = QName.prototype;
 32142     defineNonEnumerableGetter(QNp, 'localName', function () {
 32143       if (!this._localName) {
 32144         this._localName = this.isAny ? '*' : this.mn.getName();
 32146       return this._localName;
 32147     });
 32148     defineNonEnumerableGetter(QNp, 'uri', function () {
 32149       if (!this._uri) {
 32150         var ns = this.mn.namespaces[0];
 32151         this._uri = ns && ns.uri ? ns.uri : this.isAny || this.isAnyNamespace ? null : '';
 32153       return this._uri;
 32154     });
 32155     defineNonEnumerableGetter(QNp, 'prefix', function () {
 32156       return this.mn.namespaces[0].prefix;
 32157     });
 32158     defineNonEnumerableSetter(QNp, 'prefix', function (prefix) {
 32159       this.mn.namespaces[0].prefix = prefix;
 32160     });
 32161     QNp.getNamespace = function (isns) {
 32162       if (this.uri === null) {
 32163         throw 'TypeError in QName.prototype.getNamespace()';
 32165       if (!isns) {
 32166         isns = [];
 32168       var ns;
 32169       for (var i = 0; i < isns.length; i++) {
 32170         if (this.uri === isns[i].uri) {
 32171           ns = isns[i];
 32174       if (!ns) {
 32175         ns = ASNamespace.createNamespace(this.uri);
 32177       return ns;
 32178     };
 32179     c.native = {
 32180       static: {},
 32181       instance: {
 32182         localName: {
 32183           get: function localName() {
 32184             return this.localName;
 32186         },
 32187         uri: {
 32188           get: function uri() {
 32189             return this.uri;
 32193     };
 32194     return c;
 32195   };
 32196 }());
 32197 var AMFUtils = function AMFUtilsClosure() {
 32198     var AMF0_NUMBER_MARKER = 0;
 32199     var AMF0_BOOLEAN_MARKER = 1;
 32200     var AMF0_STRING_MARKER = 2;
 32201     var AMF0_OBJECT_MARKER = 3;
 32202     var AMF0_NULL_MARKER = 5;
 32203     var AMF0_UNDEFINED_MARKER = 6;
 32204     var AMF0_REFERENCE_MARKER = 7;
 32205     var AMF0_ECMA_ARRAY_MARKER = 8;
 32206     var AMF0_OBJECT_END_MARKER = 9;
 32207     var AMF0_STRICT_ARRAY_MARKER = 10;
 32208     var AMF0_DATE_MARKER = 11;
 32209     var AMF0_LONG_STRING_MARKER = 12;
 32210     var AMF0_XML_MARKER = 15;
 32211     var AMF0_TYPED_OBJECT_MARKER = 16;
 32212     var AMF0_AVMPLUS_MARKER = 17;
 32213     function writeString(ba, s) {
 32214       if (s.length > 65535) {
 32215         throw 'AMF short string exceeded';
 32217       if (!s.length) {
 32218         ba.writeByte(0);
 32219         ba.writeByte(0);
 32220         return;
 32222       var bytes = utf8decode(s);
 32223       ba.writeByte(bytes.length >> 8 & 255);
 32224       ba.writeByte(bytes.length & 255);
 32225       for (var i = 0; i < bytes.length; i++) {
 32226         ba.writeByte(bytes[i]);
 32229     function readString(ba) {
 32230       var byteLength = ba.readByte() << 8 | ba.readByte();
 32231       if (!byteLength) {
 32232         return '';
 32234       var buffer = new Uint8Array(byteLength);
 32235       for (var i = 0; i < byteLength; i++) {
 32236         buffer[i] = ba.readByte();
 32238       return utf8encode(buffer);
 32240     function writeDouble(ba, value) {
 32241       var buffer = new ArrayBuffer(8);
 32242       var view = new DataView(buffer);
 32243       view.setFloat64(0, value, false);
 32244       for (var i = 0; i < buffer.byteLength; i++) {
 32245         ba.writeByte(view.getUint8(i));
 32248     function readDouble(ba) {
 32249       var buffer = new ArrayBuffer(8);
 32250       var view = new DataView(buffer);
 32251       for (var i = 0; i < buffer.byteLength; i++) {
 32252         view.setUint8(i, ba.readByte());
 32254       return view.getFloat64(0, false);
 32256     function setAvmProperty(obj, propertyName, value) {
 32257       obj.asSetPublicProperty(propertyName, value);
 32259     var amf0 = {
 32260         write: function (ba, obj) {
 32261           switch (typeof obj) {
 32262           case 'boolean':
 32263             ba.writeByte(AMF0_BOOLEAN_MARKER);
 32264             ba.writeByte(obj ? 1 : 0);
 32265             break;
 32266           case 'number':
 32267             ba.writeByte(AMF0_NUMBER_MARKER);
 32268             writeDouble(ba, obj);
 32269             break;
 32270           case 'undefined':
 32271             ba.writeByte(AMF0_UNDEFINED_MARKER);
 32272             break;
 32273           case 'string':
 32274             ba.writeByte(AMF0_STRING_MARKER);
 32275             writeString(ba, obj);
 32276             break;
 32277           case 'object':
 32278             if (obj === null) {
 32279               ba.writeByte(AMF0_NULL_MARKER);
 32280             } else if (Array.isArray(obj)) {
 32281               ba.writeByte(AMF0_ECMA_ARRAY_MARKER);
 32282               ba.writeByte(obj.length >>> 24 & 255);
 32283               ba.writeByte(obj.length >> 16 & 255);
 32284               ba.writeByte(obj.length >> 8 & 255);
 32285               ba.writeByte(obj.length & 255);
 32286               forEachPublicProperty(obj, function (key, value) {
 32287                 writeString(ba, key);
 32288                 this.write(ba, value);
 32289               }, this);
 32290               ba.writeByte(0);
 32291               ba.writeByte(0);
 32292               ba.writeByte(AMF0_OBJECT_END_MARKER);
 32293             } else {
 32294               ba.writeByte(AMF0_OBJECT_MARKER);
 32295               forEachPublicProperty(obj, function (key, value) {
 32296                 writeString(ba, key);
 32297                 this.write(ba, value);
 32298               }, this);
 32299               ba.writeByte(0);
 32300               ba.writeByte(0);
 32301               ba.writeByte(AMF0_OBJECT_END_MARKER);
 32303             return;
 32305         },
 32306         read: function (ba) {
 32307           var marker = ba.readByte();
 32308           switch (marker) {
 32309           case AMF0_NUMBER_MARKER:
 32310             return readDouble(ba);
 32311           case AMF0_BOOLEAN_MARKER:
 32312             return !(!ba.readByte());
 32313           case AMF0_STRING_MARKER:
 32314             return readString(ba);
 32315           case AMF0_OBJECT_MARKER:
 32316             var obj = {};
 32317             while (true) {
 32318               var key = readString(ba);
 32319               if (!key.length)
 32320                 break;
 32321               setAvmProperty(obj, key, this.read(ba));
 32323             if (ba.readByte() !== AMF0_OBJECT_END_MARKER) {
 32324               throw 'AMF0 End marker is not found';
 32326             return obj;
 32327           case AMF0_NULL_MARKER:
 32328             return null;
 32329           case AMF0_UNDEFINED_MARKER:
 32330             return undefined;
 32331           case AMF0_ECMA_ARRAY_MARKER:
 32332             var obj = [];
 32333             obj.length = ba.readByte() << 24 | ba.readByte() << 16 | ba.readByte() << 8 | ba.readByte();
 32334             while (true) {
 32335               var key = readString(ba);
 32336               if (!key.length)
 32337                 break;
 32338               setAvmProperty(obj, key, this.read(ba));
 32340             if (ba.readByte() !== AMF0_OBJECT_END_MARKER) {
 32341               throw 'AMF0 End marker is not found';
 32343             return obj;
 32344           case AMF0_STRICT_ARRAY_MARKER:
 32345             var obj = [];
 32346             obj.length = ba.readByte() << 24 | ba.readByte() << 16 | ba.readByte() << 8 | ba.readByte();
 32347             for (var i = 0; i < obj.length; i++) {
 32348               obj[i] = this.read(ba);
 32350             return obj;
 32351           case AMF0_AVMPLUS_MARKER:
 32352             return readAmf3Data(ba, {});
 32353           default:
 32354             throw 'AMF0 Unknown marker ' + marker;
 32357       };
 32358     var AMF3_UNDEFINED_MARKER = 0;
 32359     var AMF3_NULL_MARKER = 1;
 32360     var AMF3_FALSE_MARKER = 2;
 32361     var AMF3_TRUE_MARKER = 3;
 32362     var AMF3_INTEGER_MARKER = 4;
 32363     var AMF3_DOUBLE_MARKER = 5;
 32364     var AMF3_STRING_MARKER = 6;
 32365     var AMF3_XML_DOC_MARKER = 7;
 32366     var AMF3_DATE_MARKER = 8;
 32367     var AMF3_ARRAY_MARKER = 9;
 32368     var AMF3_OBJECT_MARKER = 10;
 32369     var AMF3_XML_MARKER = 11;
 32370     var AMF3_BYTEARRAY_MARKER = 12;
 32371     var AMF3_VECTOR_INT_MARKER = 13;
 32372     var AMF3_VECTOR_UINT_MARKER = 14;
 32373     var AMF3_VECTOR_DOUBLE_MARKER = 15;
 32374     var AMF3_VECTOR_OBJECT_MARKER = 16;
 32375     var AMF3_DICTIONARY_MARKER = 17;
 32376     function readU29(ba) {
 32377       var b1 = ba.readByte();
 32378       if ((b1 & 128) === 0) {
 32379         return b1;
 32381       var b2 = ba.readByte();
 32382       if ((b2 & 128) === 0) {
 32383         return (b1 & 127) << 7 | b2;
 32385       var b3 = ba.readByte();
 32386       if ((b3 & 128) === 0) {
 32387         return (b1 & 127) << 14 | (b2 & 127) << 7 | b3;
 32389       var b4 = ba.readByte();
 32390       return (b1 & 127) << 22 | (b2 & 127) << 15 | (b3 & 127) << 8 | b4;
 32392     function writeU29(ba, value) {
 32393       if ((value & 4294967168) === 0) {
 32394         ba.writeByte(value & 127);
 32395       } else if ((value & 4294950912) === 0) {
 32396         ba.writeByte(128 | value >> 7 & 127);
 32397         ba.writeByte(value & 127);
 32398       } else if ((value & 4292870144) === 0) {
 32399         ba.writeByte(128 | value >> 14 & 127);
 32400         ba.writeByte(128 | value >> 7 & 127);
 32401         ba.writeByte(value & 127);
 32402       } else if ((value & 3221225472) === 0) {
 32403         ba.writeByte(128 | value >> 22 & 127);
 32404         ba.writeByte(128 | value >> 15 & 127);
 32405         ba.writeByte(128 | value >> 8 & 127);
 32406         ba.writeByte(value & 255);
 32407       } else {
 32408         throw 'AMF3 U29 range';
 32411     function readUTF8vr(ba, caches) {
 32412       var u29s = readU29(ba);
 32413       if (u29s === 1) {
 32414         return '';
 32416       var stringsCache = caches.stringsCache || (caches.stringsCache = []);
 32417       if ((u29s & 1) === 0) {
 32418         return stringsCache[u29s >> 1];
 32420       var byteLength = u29s >> 1;
 32421       var buffer = new Uint8Array(byteLength);
 32422       for (var i = 0; i < byteLength; i++) {
 32423         buffer[i] = ba.readByte();
 32425       var value = utf8encode(buffer);
 32426       stringsCache.push(value);
 32427       return value;
 32429     function writeUTF8vr(ba, value, caches) {
 32430       if (value === '') {
 32431         ba.writeByte(1);
 32432         return;
 32434       var stringsCache = caches.stringsCache || (caches.stringsCache = []);
 32435       var index = stringsCache.indexOf(value);
 32436       if (index >= 0) {
 32437         writeU29(ba, index << 1);
 32438         return;
 32440       stringsCache.push(value);
 32441       var bytes = utf8decode(value);
 32442       writeU29(ba, 1 | bytes.length << 1);
 32443       for (var i = 0; i < bytes.length; i++) {
 32444         ba.writeByte(bytes[i]);
 32447     function readAmf3Data(ba, caches) {
 32448       var marker = ba.readByte();
 32449       switch (marker) {
 32450       case AMF3_NULL_MARKER:
 32451         return null;
 32452       case AMF3_UNDEFINED_MARKER:
 32453         return undefined;
 32454       case AMF3_FALSE_MARKER:
 32455         return false;
 32456       case AMF3_TRUE_MARKER:
 32457         return true;
 32458       case AMF3_INTEGER_MARKER:
 32459         return readU29(ba);
 32460       case AMF3_DOUBLE_MARKER:
 32461         return readDouble(ba);
 32462       case AMF3_STRING_MARKER:
 32463         return readUTF8vr(ba, caches);
 32464       case AMF3_DATE_MARKER:
 32465         return new Date(readDouble(ba));
 32466       case AMF3_OBJECT_MARKER:
 32467         var u29o = readU29(ba);
 32468         if ((u29o & 1) === 0) {
 32469           return caches.objectsCache[u29o >> 1];
 32471         if ((u29o & 4) !== 0) {
 32472           throw 'AMF3 Traits-Ext is not supported';
 32474         var traits, objectClass;
 32475         if ((u29o & 2) === 0) {
 32476           traits = caches.traitsCache[u29o >> 2];
 32477           objectClass = traits.class;
 32478         } else {
 32479           traits = {};
 32480           var aliasName = readUTF8vr(ba, caches);
 32481           traits.className = aliasName;
 32482           objectClass = aliasName && aliasesCache.names[aliasName];
 32483           traits.class = objectClass;
 32484           traits.isDynamic = (u29o & 8) !== 0;
 32485           traits.members = [];
 32486           var slots = objectClass && objectClass.instanceBindings.slots;
 32487           for (var i = 0, j = u29o >> 4; i < j; i++) {
 32488             var traitName = readUTF8vr(ba, caches);
 32489             var slot = null;
 32490             for (var j = 1; slots && j < slots.length; j++) {
 32491               if (slots[j].name.name === traitName) {
 32492                 slot = slots[j];
 32493                 break;
 32496             traits.members.push(slot ? Multiname.getQualifiedName(slot.name) : Multiname.getPublicQualifiedName(traitName));
 32498           (caches.traitsCache || (caches.traitsCache = [])).push(traits);
 32500         var obj = objectClass ? objectClass.createInstance() : {};
 32501         (caches.objectsCache || (caches.objectsCache = [])).push(obj);
 32502         for (var i = 0; i < traits.members.length; i++) {
 32503           var value = readAmf3Data(ba, caches);
 32504           obj[traits.members[i]] = value;
 32506         if (traits.isDynamic) {
 32507           while (true) {
 32508             var key = readUTF8vr(ba, caches);
 32509             if (!key.length)
 32510               break;
 32511             var value = readAmf3Data(ba, caches);
 32512             setAvmProperty(obj, key, value);
 32515         return obj;
 32516       case AMF3_ARRAY_MARKER:
 32517         var u29o = readU29(ba);
 32518         if ((u29o & 1) === 0) {
 32519           return caches.objectsCache[u29o >> 1];
 32521         var obj = [];
 32522         (caches.objectsCache || (caches.objectsCache = [])).push(obj);
 32523         var densePortionLength = u29o >> 1;
 32524         while (true) {
 32525           var key = readUTF8vr(ba, caches);
 32526           if (!key.length)
 32527             break;
 32528           var value = readAmf3Data(ba, caches);
 32529           setAvmProperty(obj, key, value);
 32531         for (var i = 0; i < densePortionLength; i++) {
 32532           var value = readAmf3Data(ba, caches);
 32533           setAvmProperty(obj, i, value);
 32535         return obj;
 32536       default:
 32537         throw 'AMF3 Unknown marker ' + marker;
 32540     function writeCachedReference(ba, obj, caches) {
 32541       var objectsCache = caches.objectsCache || (caches.objectsCache = []);
 32542       var index = objectsCache.indexOf(obj);
 32543       if (index < 0) {
 32544         objectsCache.push(obj);
 32545         return false;
 32547       writeU29(ba, index << 1);
 32548       return true;
 32550     function writeAmf3Data(ba, obj, caches) {
 32551       switch (typeof obj) {
 32552       case 'boolean':
 32553         ba.writeByte(obj ? AMF3_TRUE_MARKER : AMF3_FALSE_MARKER);
 32554         break;
 32555       case 'number':
 32556         if (obj === (obj | 0)) {
 32557           ba.writeByte(AMF3_INTEGER_MARKER);
 32558           writeU29(ba, obj);
 32559         } else {
 32560           ba.writeByte(AMF3_DOUBLE_MARKER);
 32561           writeDouble(ba, obj);
 32563         break;
 32564       case 'undefined':
 32565         ba.writeByte(AMF3_UNDEFINED_MARKER);
 32566         break;
 32567       case 'string':
 32568         ba.writeByte(AMF3_STRING_MARKER);
 32569         writeUTF8vr(ba, obj, caches);
 32570         break;
 32571       case 'object':
 32572         if (obj === null) {
 32573           ba.writeByte(AMF3_NULL_MARKER);
 32574         } else if (Array.isArray(obj)) {
 32575           ba.writeByte(AMF3_ARRAY_MARKER);
 32576           if (writeCachedReference(ba, obj, caches))
 32577             break;
 32578           var densePortionLength = 0;
 32579           while (densePortionLength in obj) {
 32580             ++densePortionLength;
 32582           writeU29(ba, densePortionLength << 1 | 1);
 32583           forEachPublicProperty(obj, function (i, value) {
 32584             if (isNumeric(i) && i >= 0 && i < densePortionLength) {
 32585               return;
 32587             writeUTF8vr(ba, i, caches);
 32588             writeAmf3Data(ba, value, caches);
 32589           });
 32590           writeUTF8vr(ba, '', caches);
 32591           for (var j = 0; j < densePortionLength; j++) {
 32592             writeAmf3Data(ba, obj[j], caches);
 32594         } else if (obj instanceof Date) {
 32595           ba.writeByte(AMF3_DATE_MARKER);
 32596           if (writeCachedReference(ba, obj, caches))
 32597             break;
 32598           writeU29(ba, 1);
 32599           writeDouble(ba, obj.valueOf());
 32600         } else {
 32601           ba.writeByte(AMF3_OBJECT_MARKER);
 32602           if (writeCachedReference(ba, obj, caches))
 32603             break;
 32604           var isDynamic = true;
 32605           var objectClass = obj.class;
 32606           if (objectClass) {
 32607             isDynamic = !objectClass.classInfo.instanceInfo.isSealed();
 32608             var aliasName = aliasesCache.classes.get(objectClass) || '';
 32609             var traits, traitsCount;
 32610             var traitsCache = caches.traitsCache || (caches.traitsCache = []);
 32611             var traitsInfos = caches.traitsInfos || (caches.traitsInfos = []);
 32612             var traitsRef = traitsCache.indexOf(objectClass);
 32613             if (traitsRef < 0) {
 32614               var slots = objectClass.instanceBindings.slots;
 32615               traits = [];
 32616               var traitsNames = [];
 32617               for (var i = 1; i < slots.length; i++) {
 32618                 var slot = slots[i];
 32619                 if (!slot.name.getNamespace().isPublic()) {
 32620                   continue;
 32622                 traits.push(Multiname.getQualifiedName(slot.name));
 32623                 traitsNames.push(slot.name.name);
 32625               traitsCache.push(objectClass);
 32626               traitsInfos.push(traits);
 32627               traitsCount = traitsNames.length;
 32628               writeU29(ba, (isDynamic ? 11 : 3) + (traitsCount << 4));
 32629               writeUTF8vr(ba, aliasName, caches);
 32630               for (var i = 0; i < traitsCount; i++) {
 32631                 writeUTF8vr(ba, traitsNames[i], caches);
 32633             } else {
 32634               traits = traitsInfos[traitsRef];
 32635               traitsCount = traits.length;
 32636               writeU29(ba, 1 + (traitsRef << 2));
 32638             for (var i = 0; i < traitsCount; i++) {
 32639               writeAmf3Data(ba, obj[traits[i]], caches);
 32641           } else {
 32642             writeU29(ba, 11);
 32643             writeUTF8vr(ba, '', caches);
 32645           if (isDynamic) {
 32646             forEachPublicProperty(obj, function (i, value) {
 32647               writeUTF8vr(ba, i, caches);
 32648               writeAmf3Data(ba, value, caches);
 32649             });
 32650             writeUTF8vr(ba, '', caches);
 32653         return;
 32656     var aliasesCache = {
 32657         classes: new WeakMap(),
 32658         names: Object.create(null)
 32659       };
 32660     var amf3 = {
 32661         write: function (ba, obj) {
 32662           writeAmf3Data(ba, obj, {});
 32663         },
 32664         read: function (ba) {
 32665           return readAmf3Data(ba, {});
 32667       };
 32668     return {
 32669       encodings: [
 32670         amf0,
 32671         null,
 32672         null,
 32673         amf3
 32674       ],
 32675       aliasesCache: aliasesCache
 32676     };
 32677   }();
 32678 function ProxyClass(runtime, scope, instanceConstructor, baseClass) {
 32679   function ProxyConstructor() {
 32680     somewhatImplemented('Proxy');
 32682   var c = new Class('Proxy', ProxyConstructor, ApplicationDomain.coerceCallable(ProxyConstructor));
 32683   c.extendBuiltin(baseClass);
 32684   return c;
 32686 var proxyTrapQns = {
 32687     'getProperty': null,
 32688     'setProperty': null,
 32689     'hasProperty': null,
 32690     'callProperty': null
 32691   };
 32692 for (var name in proxyTrapQns) {
 32693   proxyTrapQns[name] = VM_OPEN_METHOD_PREFIX + Multiname.getQualifiedName(new Multiname([
 32694     ASNamespace.PROXY
 32695   ], name));
 32697 function isProxyObject(obj) {
 32698   return obj[VM_IS_PROXY];
 32700 function nameFromQualifiedName(qn) {
 32701   if (isNumeric(qn)) {
 32702     return qn;
 32704   var mn = Multiname.fromQualifiedName(qn);
 32705   if (mn === undefined) {
 32706     return undefined;
 32708   return mn.name;
 32710 function hasNonProxyingCaller() {
 32711   var caller = arguments.callee;
 32712   var maxDepth = 5;
 32713   var domain;
 32714   for (var i = 0; i < maxDepth && caller; i++) {
 32715     if (caller === nonProxyingHasProperty) {
 32716       return true;
 32718     caller = caller.caller;
 32720   return false;
 32722 function installProxyClassWrapper(cls) {
 32723   var TRACE_PROXY = false;
 32724   if (TRACE_PROXY) {
 32725     print('proxy wrapping, class: ' + cls);
 32727   var instanceConstructor = cls.instanceConstructor;
 32728   function construct() {
 32729     if (TRACE_PROXY) {
 32730       print('proxy create, class: ' + cls);
 32732     var target = Object.create(instanceConstructor.prototype);
 32733     var proxy = Proxy.create({
 32734         get: function (o, qn) {
 32735           if (qn === VM_IS_PROXY) {
 32736             TRACE_PROXY && print('proxy check');
 32737             return true;
 32739           if (qn === VM_CALL_PROXY) {
 32740             TRACE_PROXY && print('proxy get caller');
 32741             return function apply(mn, receiver, args) {
 32742               receiver = receiver ? target : null;
 32743               if (TRACE_PROXY) {
 32744                 print('proxy call, class: ' + target.class + ', mn: ' + mn + 'hasNonProxyingCallerr: ' + hasNonProxyingCaller());
 32746               var resolved = Multiname.isQName(mn) ? mn : target.resolveMultinameProperty(mn.namespaces, mn.name, mn.flags);
 32747               var qn = resolved ? Multiname.getQualifiedName(resolved) : Multiname.getPublicQualifiedName(mn.name);
 32748               if (!nameInTraits(target, qn)) {
 32749                 return target[proxyTrapQns.callProperty](mn.name, args);
 32751               if (TRACE_PROXY) {
 32752                 TRACE_PROXY && print('> proxy pass through ' + resolved);
 32754               if (target.asOpenMethods && target.asOpenMethods[qn]) {
 32755                 return target.asOpenMethods[qn].apply(o, args);
 32757               return undefined;
 32758             };
 32760           if (TRACE_PROXY) {
 32761             print('proxy get, class: ' + target.class + ', qn: ' + qn + 'hasNonProxyingCallerr: ' + hasNonProxyingCaller());
 32763           if (!hasNonProxyingCaller()) {
 32764             var name = nameFromQualifiedName(qn);
 32765             if (name !== undefined && !nameInTraits(target, qn)) {
 32766               return target[proxyTrapQns.getProperty](name);
 32769           if (target.asOpenMethods && target.asOpenMethods[qn]) {
 32770             return bindSafely(target.asOpenMethods[qn], o);
 32772           TRACE_PROXY && print('> proxy pass through ' + qn);
 32773           return target[qn];
 32774         },
 32775         set: function (o, qn, value) {
 32776           if (TRACE_PROXY) {
 32777             print('proxy set, class: ' + target.class + ', qn: ' + qn + 'hasNonProxyingCallerr: ' + hasNonProxyingCaller());
 32779           if (!hasNonProxyingCaller()) {
 32780             var name = nameFromQualifiedName(qn);
 32781             if (name !== undefined && !nameInTraits(target, qn)) {
 32782               target[proxyTrapQns.setProperty](name, value);
 32783               return;
 32786           TRACE_PROXY && print('> proxy pass through ' + qn);
 32787           target[qn] = value;
 32788         },
 32789         has: function (qn) {
 32790           if (TRACE_PROXY) {
 32791             print('proxy has, class: ' + target.class + ', qn: ' + qn + 'hasNonProxyingCallerr: ' + hasNonProxyingCaller());
 32793           if (!hasNonProxyingCaller()) {
 32794             var name = nameFromQualifiedName(qn);
 32795             if (name !== undefined && !nameInTraits(target, qn)) {
 32796               return target[proxyTrapQns.hasProperty](name);
 32799           return qn in target;
 32800         },
 32801         hasOwn: function (qn) {
 32802           if (TRACE_PROXY) {
 32803             print('proxy hasOwn, class: ' + target.class + ', qn: ' + qn + 'hasNonProxyingCallerr: ' + hasNonProxyingCaller());
 32805           if (!hasNonProxyingCaller()) {
 32806             var name = nameFromQualifiedName(qn);
 32807             if (name !== undefined && !nameInTraits(target, qn)) {
 32808               return target[proxyTrapQns.hasProperty](name);
 32811           TRACE_PROXY && print('> proxy pass through ' + qn);
 32812           return !(!Object.getOwnPropertyDescriptor(target, qn));
 32813         },
 32814         enumerate: function () {
 32815           notImplemented('enumerate');
 32816         },
 32817         keys: function () {
 32818           notImplemented('keys');
 32820       }, instanceConstructor.prototype);
 32821     instanceConstructor.apply(proxy, sliceArguments(arguments, 0));
 32822     return proxy;
 32824   cls.instanceConstructor = construct;
 32826 function DictionaryClass(domain, scope, instanceConstructor, baseClass) {
 32827   function ASDictionary(weakKeys) {
 32828     this.weakKeys = weakKeys;
 32829     this.map = new WeakMap();
 32830     if (!weakKeys) {
 32831       this.keys = [];
 32833     this.primitiveMap = createEmptyObject();
 32835   var c = new Class('Dictionary', ASDictionary, ApplicationDomain.passthroughCallable(ASDictionary));
 32836   c.extendNative(baseClass, ASDictionary);
 32837   function makePrimitiveKey(key) {
 32838     if (typeof key === 'string' || typeof key === 'number') {
 32839       return key;
 32841     return undefined;
 32843   var prototype = ASDictionary.prototype;
 32844   defineNonEnumerableProperty(prototype, 'asGetProperty', function asGetProperty(namespaces, name, flags, isMethod) {
 32845     var key = makePrimitiveKey(name);
 32846     if (key !== undefined) {
 32847       return this.primitiveMap[key];
 32849     return this.map.get(Object(name));
 32850   });
 32851   defineNonEnumerableProperty(prototype, 'asGetResolvedStringProperty', asGetResolvedStringPropertyFallback);
 32852   defineNonEnumerableProperty(prototype, 'asSetProperty', function asSetProperty(namespaces, name, flags, value) {
 32853     var key = makePrimitiveKey(name);
 32854     if (key !== undefined) {
 32855       this.primitiveMap[key] = value;
 32856       return;
 32858     this.map.set(Object(name), value);
 32859     if (!this.weakKeys && this.keys.indexOf(name) < 0) {
 32860       this.keys.push(name);
 32862   });
 32863   defineNonEnumerableProperty(prototype, 'asCallProperty', function asCallProperty(namespaces, name, flags, isLex, args) {
 32864     notImplemented('asCallProperty');
 32865   });
 32866   defineNonEnumerableProperty(prototype, 'asHasProperty', function asHasProperty(namespaces, name, flags, nonProxy) {
 32867     var key = makePrimitiveKey(name);
 32868     if (key !== undefined) {
 32869       return key in this.primitiveMap;
 32871     return this.map.has(Object(name));
 32872   });
 32873   defineNonEnumerableProperty(prototype, 'asDeleteProperty', function asDeleteProperty(namespaces, name, flags) {
 32874     var key = makePrimitiveKey(name);
 32875     if (key !== undefined) {
 32876       delete this.primitiveMap[key];
 32878     this.map.delete(Object(name));
 32879     var i;
 32880     if (!this.weakKeys && (i = this.keys.indexOf(name)) >= 0) {
 32881       this.keys.splice(i, 1);
 32883     return true;
 32884   });
 32885   defineNonEnumerableProperty(prototype, 'asGetEnumerableKeys', function () {
 32886     if (prototype === this) {
 32887       return Object.prototype.asGetEnumerableKeys.call(this);
 32889     var primitiveMapKeys = [];
 32890     for (var k in this.primitiveMap) {
 32891       primitiveMapKeys.push(k);
 32893     if (this.weakKeys) {
 32894       return primitiveMapKeys;
 32896     return primitiveMapKeys.concat(this.keys);
 32897   });
 32898   c.native = {
 32899     instance: {
 32900       init: function () {
 32903   };
 32904   return c;
 32906 function debugBreak(message) {
 32907   debugger;
 32908   print('\x1b[91mdebugBreak: ' + message + '\x1b[0m');
 32910 var NativeASNamespace;
 32911 var natives = function () {
 32912     var C = ApplicationDomain.passthroughCallable;
 32913     var CC = ApplicationDomain.constructingCallable;
 32914     function ObjectClass(applicationDomain, scope, instanceConstructor, baseClass) {
 32915       var c = new Class('Object', Object, C(Object));
 32916       c.native = {
 32917         instance: {
 32918           isPrototypeOf: Object.prototype.isPrototypeOf,
 32919           hasOwnProperty: function (name) {
 32920             if (name === undefined) {
 32921               return false;
 32923             name = Multiname.getPublicQualifiedName(name);
 32924             if (Object.prototype.hasOwnProperty.call(this, name)) {
 32925               return true;
 32927             return Object.getPrototypeOf(this).hasOwnProperty(name);
 32928           },
 32929           propertyIsEnumerable: function (name) {
 32930             if (name === undefined) {
 32931               return false;
 32933             name = Multiname.getPublicQualifiedName(name);
 32934             return Object.prototype.propertyIsEnumerable.call(this, name);
 32936         },
 32937         static: {
 32938           _setPropertyIsEnumerable: function _setPropertyIsEnumerable(obj, name, isEnum) {
 32939             name = Multiname.getPublicQualifiedName(name);
 32940             var descriptor = Object.getOwnPropertyDescriptor(obj, name);
 32941             descriptor.enumerable = false;
 32942             Object.defineProperty(obj, name, descriptor);
 32945       };
 32946       c.dynamicPrototype = c.traitsPrototype = Object.prototype;
 32947       c.setDefaultProperties();
 32948       c.defaultValue = null;
 32949       c.coerce = function (value) {
 32950         return asCoerceObject(value);
 32951       };
 32952       c.isInstanceOf = function (value) {
 32953         if (value === null) {
 32954           return false;
 32956         return true;
 32957       };
 32958       c.isInstance = function (value) {
 32959         if (value === null || value === undefined) {
 32960           return false;
 32962         return true;
 32963       };
 32964       return c;
 32966     function ClassClass(runtime, scope, instanceConstructor, baseClass) {
 32967       var c = Class;
 32968       c.debugName = 'Class';
 32969       c.prototype.extendBuiltin.call(c, baseClass);
 32970       c.coerce = function (value) {
 32971         return value;
 32972       };
 32973       c.isInstanceOf = function (value) {
 32974         return true;
 32975       };
 32976       c.isInstance = function (value) {
 32977         return value instanceof c.instanceConstructor;
 32978       };
 32979       return c;
 32981     function BooleanClass(runtime, scope, instanceConstructor, baseClass) {
 32982       var c = new Class('Boolean', Boolean, C(Boolean));
 32983       c.extendBuiltin(baseClass);
 32984       c.native = {
 32985         instance: {
 32986           toString: Boolean.prototype.toString,
 32987           valueOf: Boolean.prototype.valueOf
 32989       };
 32990       c.coerce = Boolean;
 32991       c.isInstanceOf = function (value) {
 32992         return typeof value === 'boolean' || value instanceof Boolean;
 32993       };
 32994       c.isInstance = function (value) {
 32995         if (typeof value === 'boolean' || value instanceof Boolean) {
 32996           return true;
 32998         return false;
 32999       };
 33000       return c;
 33002     function FunctionClass(runtime, scope, instanceConstructor, baseClass) {
 33003       var c = new Class('Function', Function, C(Function));
 33004       c.extendBuiltin(baseClass);
 33005       c.native = {
 33006         instance: {
 33007           prototype: {
 33008             get: function () {
 33009               return this.prototype;
 33010             },
 33011             set: function (p) {
 33012               this.prototype = p;
 33014           },
 33015           length: {
 33016             get: function () {
 33017               if (this.hasOwnProperty(VM_LENGTH)) {
 33018                 return this.asLength;
 33020               return this.length;
 33022           },
 33023           call: Function.prototype.call,
 33024           apply: Function.prototype.apply
 33026       };
 33027       c.coerce = function (value) {
 33028         return value;
 33029       };
 33030       c.isInstanceOf = function (value) {
 33031         return typeof value === 'function';
 33032       };
 33033       c.isInstance = function (value) {
 33034         return typeof value === 'function';
 33035       };
 33036       return c;
 33038     function MethodClosure($this, fn) {
 33039       var bound = bindSafely(fn, $this);
 33040       defineNonEnumerableProperty(this, 'call', bound.call.bind(bound));
 33041       defineNonEnumerableProperty(this, 'apply', bound.apply.bind(bound));
 33043     MethodClosure.prototype = {
 33044       toString: function () {
 33045         return 'function Function() {}';
 33047     };
 33048     function MethodClosureClass(runtime, scope, instanceConstructor, baseClass) {
 33049       var c = new Class('MethodClosure', MethodClosure);
 33050       c.extendBuiltin(baseClass);
 33051       return c;
 33053     function StringClass(runtime, scope, instanceConstructor, baseClass) {
 33054       var c = new Class('String', String, C(String));
 33055       c.extendBuiltin(baseClass);
 33056       var Sp = String.prototype;
 33057       c.native = {
 33058         instance: {
 33059           length: {
 33060             get: function () {
 33061               return this.length;
 33063           },
 33064           indexOf: Sp.indexOf,
 33065           lastIndexOf: Sp.lastIndexOf,
 33066           charAt: Sp.charAt,
 33067           charCodeAt: Sp.charCodeAt,
 33068           concat: Sp.concat,
 33069           localeCompare: Sp.localeCompare,
 33070           match: function (re) {
 33071             if (re === void 0 || re === null) {
 33072               return null;
 33073             } else {
 33074               if (re instanceof RegExp && re.global) {
 33075                 var matches = [], m;
 33076                 while (m = re.exec(this)) {
 33077                   matches.push(m[0]);
 33079                 return matches;
 33081               if (!(re instanceof RegExp) && !(typeof re === 'string')) {
 33082                 re = String(re);
 33084               return this.match(re);
 33086           },
 33087           replace: Sp.replace,
 33088           search: function (re) {
 33089             if (re === void 0) {
 33090               return -1;
 33091             } else {
 33092               return this.search(re);
 33094           },
 33095           slice: Sp.slice,
 33096           split: Sp.split,
 33097           substr: Sp.substr,
 33098           substring: Sp.substring,
 33099           toLowerCase: Sp.toLowerCase,
 33100           toLocaleLowerCase: Sp.toLocaleLowerCase,
 33101           toUpperCase: function () {
 33102             var str = Sp.toUpperCase.apply(this);
 33103             var str = str.replace(/\u039C/g, String.fromCharCode(181));
 33104             return str;
 33105           },
 33106           toLocaleUpperCase: function () {
 33107             var str = Sp.toLocaleUpperCase.apply(this);
 33108             var str = str.replace(/\u039C/g, String.fromCharCode(181));
 33109             return str;
 33110           },
 33111           toString: Sp.toString,
 33112           valueOf: Sp.valueOf
 33113         },
 33114         static: String
 33115       };
 33116       c.isInstance = function (value) {
 33117         return value !== null && value !== undefined && typeof value.valueOf() === 'string';
 33118       };
 33119       c.coerce = function (value) {
 33120         if (value === null || value === undefined) {
 33121           return null;
 33123         return String(value);
 33124       };
 33125       c.isInstanceOf = function (value) {
 33126         return Object(value) instanceof String;
 33127       };
 33128       c.isInstance = function (value) {
 33129         return Object(value) instanceof String;
 33130       };
 33131       return c;
 33133     function VectorClass(domain, scope, instanceConstructor, baseClass) {
 33134       return createVectorClass(undefined, baseClass);
 33136     function ObjectVectorClass(domain, scope, instanceConstructor, baseClass) {
 33137       return createVectorClass(domain.getClass('Object'), baseClass);
 33139     function IntVectorClass(domain, scope, instanceConstructor, baseClass) {
 33140       return createVectorClass(domain.getClass('int'), baseClass);
 33142     function UIntVectorClass(domain, scope, instanceConstructor, baseClass) {
 33143       return createVectorClass(domain.getClass('uint'), baseClass);
 33145     function DoubleVectorClass(domain, scope, instanceConstructor, baseClass) {
 33146       return createVectorClass(domain.getClass('Number'), baseClass);
 33148     function createVectorClass(type, baseClass) {
 33149       var V;
 33150       if (type) {
 33151         var className = 'Vector$' + type.classInfo.instanceInfo.name.name;
 33152         switch (className) {
 33153         case 'Vector$int':
 33154           V = Int32Vector;
 33155           break;
 33156         case 'Vector$uint':
 33157           V = Uint32Vector;
 33158           break;
 33159         case 'Vector$Number':
 33160           V = Float64Vector;
 33161           break;
 33162         case 'Vector$Object':
 33163           V = GenericVector;
 33164           break;
 33165         default:
 33166           unexpected();
 33167           break;
 33169       } else {
 33170         V = GenericVector.applyType(null);
 33172       var Vp = V.prototype;
 33173       var cls = new Class(className, V, C(V.callable));
 33174       if (V === GenericVector) {
 33175         cls.applyType = function (type) {
 33176           return cls;
 33177         };
 33179       cls.extendWrapper(baseClass, V);
 33180       cls.native = {
 33181         instance: {
 33182           fixed: {
 33183             get: function () {
 33184               return this._fixed;
 33185             },
 33186             set: function (v) {
 33187               this._fixed = v;
 33189           },
 33190           length: {
 33191             get: function () {
 33192               return this.length;
 33193             },
 33194             set: function setLength(length) {
 33195               this.length = length;
 33197           },
 33198           push: Vp.push,
 33199           pop: Vp.pop,
 33200           shift: Vp.shift,
 33201           unshift: Vp.unshift,
 33202           _reverse: Vp.reverse,
 33203           _filter: Vp.filter,
 33204           _map: Vp.map,
 33205           newThisType: function newThisType() {
 33206             return new cls.instanceConstructor();
 33207           },
 33208           _spliceHelper: function _spliceHelper(insertPoint, insertCount, deleteCount, args, offset) {
 33209             return this._spliceHelper(insertPoint, insertCount, deleteCount, args, offset);
 33211         },
 33212         static: {
 33213           _some: function (o, callback, thisObject) {
 33214             return o.some(callback, thisObject);
 33215           },
 33216           _every: function (o, callback, thisObject) {
 33217             return o.every(callback, thisObject);
 33218           },
 33219           _forEach: function (o, callback, thisObject) {
 33220             return o.forEach(callback, thisObject);
 33221           },
 33222           _sort: arraySort
 33224       };
 33225       cls.vectorType = type;
 33226       cls.coerce = function (value) {
 33227         return value;
 33228       };
 33229       cls.isInstanceOf = function (value) {
 33230         return true;
 33231       };
 33232       cls.isInstance = function (value) {
 33233         if (value === null || typeof value !== 'object') {
 33234           return false;
 33236         if (!this.instanceConstructor.vectorType && value.class.vectorType) {
 33237           return true;
 33239         return this.instanceConstructor.prototype.isPrototypeOf(value);
 33240       };
 33241       return cls;
 33243     function NumberClass(runtime, scope, instanceConstructor, baseClass) {
 33244       var c = new Class('Number', Number, C(Number));
 33245       c.extendBuiltin(baseClass);
 33246       c.native = {
 33247         instance: Number.prototype
 33248       };
 33249       c.defaultValue = Number(0);
 33250       c.isInstance = function (value) {
 33251         return value !== null && value !== undefined && typeof value.valueOf() === 'number';
 33252       };
 33253       c.coerce = Number;
 33254       c.isInstanceOf = function (value) {
 33255         return Object(value) instanceof Number;
 33256       };
 33257       c.isInstance = function (value) {
 33258         return Object(value) instanceof Number;
 33259       };
 33260       return c;
 33262     function Int(x) {
 33263       return x | 0;
 33265     function boxedInt(x) {
 33266       return Object(x | 0);
 33268     function intClass(runtime, scope, instanceConstructor, baseClass) {
 33269       var c = new Class('int', boxedInt, C(Int));
 33270       c.extendBuiltin(baseClass);
 33271       c.defaultValue = 0;
 33272       c.coerce = Int;
 33273       c.isInstanceOf = function (value) {
 33274         return false;
 33275       };
 33276       c.isInstance = function (value) {
 33277         if (value instanceof Number) {
 33278           value = value.valueOf();
 33280         return (value | 0) === value;
 33281       };
 33282       return c;
 33284     function Uint(x) {
 33285       return x >>> 0;
 33287     function boxedUint(x) {
 33288       return Object(x >>> 0);
 33290     function uintClass(runtime, scope, instanceConstructor, baseClass) {
 33291       var c = new Class('uint', boxedUint, C(Uint));
 33292       c.extend(baseClass);
 33293       c.defaultValue = 0;
 33294       c.isInstanceOf = function (value) {
 33295         return false;
 33296       };
 33297       c.isInstance = function (value) {
 33298         if (value instanceof Number) {
 33299           value = value.valueOf();
 33301         return value >>> 0 === value;
 33302       };
 33303       c.coerce = Uint;
 33304       return c;
 33306     function MathClass(runtime, scope, instanceConstructor, baseClass) {
 33307       var c = new Class('Math');
 33308       c.native = {
 33309         static: Math
 33310       };
 33311       return c;
 33313     function DateClass(runtime, scope, instanceConstructor, baseClass) {
 33314       var c = new Class('Date', Date, C(Date));
 33315       c.extendBuiltin(baseClass);
 33316       c.native = {
 33317         instance: Date.prototype,
 33318         static: Date
 33319       };
 33320       return c;
 33322     function makeErrorClass(name) {
 33323       var ErrorDefinition = {
 33324           __glue__: {
 33325             script: {
 33326               instance: {
 33327                 message: 'public message',
 33328                 name: 'public name'
 33330             },
 33331             native: {
 33332               instance: {
 33333                 getStackTrace: function () {
 33334                   somewhatImplemented('Error.getStackTrace()');
 33335                   return AVM2.getStackTrace();
 33337               },
 33338               static: {
 33339                 getErrorMessage: getErrorMessage
 33343         };
 33344       return function (runtime, scope, instanceConstructor, baseClass) {
 33345         var c = new Class(name, instanceConstructor);
 33346         c.extend(baseClass);
 33347         if (name === 'Error') {
 33348           c.link(ErrorDefinition);
 33349           c.linkNatives(ErrorDefinition);
 33351         return c;
 33352       };
 33354     function RegExpClass(runtime, scope, instanceConstructor, baseClass) {
 33355       var c = new Class('RegExp', XRegExp, C(XRegExp));
 33356       c.extendBuiltin(baseClass);
 33357       RegExpClass.exec = function exec() {
 33358         var result = this.exec.apply(this, arguments);
 33359         if (!result) {
 33360           return result;
 33362         var keys = Object.keys(result);
 33363         for (var i = 0; i < keys.length; i++) {
 33364           var k = keys[i];
 33365           if (!isNumeric(k)) {
 33366             if (result[k] === undefined) {
 33367               result[k] = '';
 33371         publicizeProperties(result);
 33372         return result;
 33373       };
 33374       RegExpClass.test = function test() {
 33375         return this.exec.apply(this, arguments) !== null;
 33376       };
 33377       c.native = {
 33378         instance: {
 33379           global: {
 33380             get: function () {
 33381               return this.global;
 33383           },
 33384           source: {
 33385             get: function () {
 33386               return this.source;
 33388           },
 33389           ignoreCase: {
 33390             get: function () {
 33391               return this.ignoreCase;
 33393           },
 33394           multiline: {
 33395             get: function () {
 33396               return this.multiline;
 33398           },
 33399           lastIndex: {
 33400             get: function () {
 33401               return this.lastIndex;
 33402             },
 33403             set: function (i) {
 33404               this.lastIndex = i;
 33406           },
 33407           dotall: {
 33408             get: function () {
 33409               return this.dotall;
 33411           },
 33412           extended: {
 33413             get: function () {
 33414               return this.extended;
 33416           },
 33417           exec: RegExpClass.exec,
 33418           test: RegExpClass.test
 33420       };
 33421       return c;
 33423     function NamespaceClass(runtime, scope, instanceConstructor, baseClass) {
 33424       NativeASNamespace = function NativeASNamespace(prefixValue, uriValue) {
 33425         if (uriValue === undefined) {
 33426           uriValue = prefixValue;
 33427           prefixValue = undefined;
 33429         var prefix, uri;
 33430         if (prefixValue === undefined) {
 33431           if (uriValue === undefined) {
 33432             prefix = '';
 33433             uri = '';
 33434           } else if (typeof uriValue === 'object') {
 33435             prefix = uriValue.prefix;
 33436             if (uriValue instanceof ASNamespace) {
 33437               uri = uriValue.uri;
 33438             } else if (uriValue instanceof QName) {
 33439               uri = uriValue.uri;
 33441           } else {
 33442             uri = uriValue + '';
 33443             if (uri === '') {
 33444               prefix = '';
 33445             } else {
 33446               prefix = undefined;
 33449         } else {
 33450           if (typeof uriValue === 'object' && uriValue instanceof QName && uriValue.uri !== null) {
 33451             uri = uriValue.uri;
 33452           } else {
 33453             uri = uriValue + '';
 33455           if (uri === '') {
 33456             if (prefixValue === undefined || prefixValue + '' === '') {
 33457               prefix = '';
 33458             } else {
 33459               throw 'type error';
 33461           } else if (prefixValue === undefined || prefixValue === '') {
 33462             prefix = undefined;
 33463           } else if (false && !isXMLName(prefixValue)) {
 33464             prefix = undefined;
 33465           } else {
 33466             prefix = prefixValue + '';
 33469         return ASNamespace.createNamespace(uri, prefix);
 33470       };
 33471       var c = new Class('Namespace', NativeASNamespace, C(NativeASNamespace));
 33472       c.extendNative(baseClass, ASNamespace);
 33473       var Np = ASNamespace.prototype;
 33474       c.native = {
 33475         instance: {
 33476           prefix: {
 33477             get: Np.getPrefix
 33478           },
 33479           uri: {
 33480             get: Np.getURI
 33483       };
 33484       return c;
 33486     function JSONClass(runtime, scope, instanceConstructor, baseClass) {
 33487       function transformJSValueToAS(value) {
 33488         if (typeof value !== 'object') {
 33489           return value;
 33491         var keys = Object.keys(value);
 33492         var result = value instanceof Array ? [] : {};
 33493         for (var i = 0; i < keys.length; i++) {
 33494           result.asSetPublicProperty(keys[i], transformJSValueToAS(value[keys[i]]));
 33496         return result;
 33498       function transformASValueToJS(value) {
 33499         if (typeof value !== 'object') {
 33500           return value;
 33502         var keys = Object.keys(value);
 33503         var result = value instanceof Array ? [] : {};
 33504         for (var i = 0; i < keys.length; i++) {
 33505           var key = keys[i];
 33506           var jsKey = key;
 33507           if (!isNumeric(key)) {
 33508             jsKey = Multiname.getNameFromPublicQualifiedName(key);
 33510           result[jsKey] = transformASValueToJS(value[key]);
 33512         return result;
 33514       function ASJSON() {
 33516       var c = new Class('JSON', ASJSON, C(ASJSON));
 33517       c.extend(baseClass);
 33518       c.native = {
 33519         static: {
 33520           parseCore: function parseCore(text) {
 33521             return transformJSValueToAS(JSON.parse(text));
 33522           },
 33523           stringifySpecializedToString: function stringifySpecializedToString(value, replacerArray, replacerFunction, gap) {
 33524             return JSON.stringify(transformASValueToJS(value), replacerFunction, gap);
 33527       };
 33528       return c;
 33530     function CapabilitiesClass(runtime, scope, instanceConstructor, baseClass) {
 33531       function Capabilities() {
 33533       var c = new Class('Capabilities', Capabilities, C(Capabilities));
 33534       c.extend(baseClass);
 33535       c.native = {
 33536         static: {
 33537           playerType: {
 33538             get: function () {
 33539               return 'AVMPlus';
 33543       };
 33544       return c;
 33546     function FileClass(runtime, scope, instanceConstructor, baseClass) {
 33547       function File() {
 33549       var c = new Class('File', File, C(File));
 33550       c.extend(baseClass);
 33551       c.native = {
 33552         static: {
 33553           exists: function (filename) {
 33554             notImplemented('File.exists');
 33555             return false;
 33556           },
 33557           read: function (filename) {
 33558             return snarf(filename);
 33559           },
 33560           write: function (filename, data) {
 33561             notImplemented('File.write');
 33562             return true;
 33563           },
 33564           readByteArray: function (filename) {
 33565             var ByteArrayClass = AVM2.currentDomain().getClass('flash.utils.ByteArray');
 33566             var data = ByteArrayClass.createInstance();
 33567             data.writeRawBytes(snarf(filename, 'binary'));
 33568             return data;
 33569           },
 33570           writeByteArray: function (filename, bytes) {
 33571             write('bin/' + filename, bytes.getBytes());
 33572             return true;
 33575       };
 33576       return c;
 33578     function ShumwayClass(runtime, scope, instanceConstructor, baseClass) {
 33579       function Shumway() {
 33581       var c = new Class('Shumway', Shumway, C(Shumway));
 33582       c.extend(baseClass);
 33583       c.native = {
 33584         static: {
 33585           info: function (x) {
 33586             console.info(x);
 33587           },
 33588           json: function (x) {
 33589             return JSON.stringify(x);
 33590           },
 33591           eval: function (x) {
 33592             return eval(x);
 33593           },
 33594           debugger: function (x) {
 33595             debugger;
 33598       };
 33599       return c;
 33601     function constant(x) {
 33602       return function () {
 33603         return x;
 33604       };
 33606     function ByteArrayClass(runtime, scope, instanceConstructor, baseClass) {
 33607       var BA = function () {
 33608         ByteArray.call(this);
 33609       };
 33610       var BAp = BA.prototype = Object.create(ByteArray.prototype);
 33611       var c = new Class('ByteArray', BA, C(BA));
 33612       c.extendBuiltin(baseClass);
 33613       BAp.asGetNumericProperty = function (i) {
 33614         if (i >= this.length) {
 33615           return undefined;
 33617         return this.uint8v[i];
 33618       };
 33619       BAp.asSetNumericProperty = function (i, v) {
 33620         var len = i + 1;
 33621         this.ensureCapacity(len);
 33622         this.uint8v[i] = v;
 33623         if (len > this.length) {
 33624           this.length = len;
 33626       };
 33627       BAp.readUTF = function readUTF() {
 33628         return this.readUTFBytes(this.readShort());
 33629       };
 33630       BAp.readUTFBytes = function readUTFBytes(length) {
 33631         var pos = this.position;
 33632         if (pos + length > this.length) {
 33633           throwEOFError();
 33635         this.position += length;
 33636         return utf8encode(new Int8Array(this.a, pos, length));
 33637       };
 33638       BAp.writeUTF = function writeUTF(str) {
 33639         var bytes = utf8decode(str);
 33640         this.writeShort(bytes.length);
 33641         this.writeRawBytes(bytes);
 33642       };
 33643       BAp.writeUTFBytes = function writeUTFBytes(str) {
 33644         var bytes = utf8decode(str);
 33645         this.writeRawBytes(bytes);
 33646       };
 33647       BAp.toString = function toString() {
 33648         return utf8encode(new Int8Array(this.a, 0, this.length));
 33649       };
 33650       c.native = {
 33651         instance: {
 33652           length: {
 33653             get: function () {
 33654               return this.length;
 33655             },
 33656             set: function setLength(length) {
 33657               var cap = this.a.byteLength;
 33658               if (length > cap) {
 33659                 this.ensureCapacity(length);
 33661               this.length = length;
 33662               this.position = clamp(this.position, 0, this.length);
 33664           },
 33665           bytesAvailable: {
 33666             get: function () {
 33667               return this.length - this.position;
 33669           },
 33670           position: {
 33671             get: function () {
 33672               return this.position;
 33673             },
 33674             set: function (p) {
 33675               this.position = p;
 33677           },
 33678           endian: {
 33679             get: function () {
 33680               return this.le ? 'littleEndian' : 'bigEndian';
 33681             },
 33682             set: function (e) {
 33683               this.le = e === 'littleEndian';
 33685           },
 33686           objectEncoding: {
 33687             get: function () {
 33688               return this.objectEncoding;
 33689             },
 33690             set: function (v) {
 33691               this.objectEncoding = v;
 33693           },
 33694           writeBytes: BAp.writeBytes,
 33695           writeBoolean: BAp.writeBoolean,
 33696           writeByte: BAp.writeByte,
 33697           writeShort: BAp.writeShort,
 33698           writeInt: BAp.writeInt,
 33699           writeUnsignedInt: BAp.writeUnsignedInt,
 33700           writeFloat: BAp.writeFloat,
 33701           writeDouble: BAp.writeDouble,
 33702           writeMultiByte: BAp.writeMultiByte,
 33703           writeObject: function writeObject(v) {
 33704             return AMFUtils.encodings[this.objectEncoding].write(this, v);
 33705           },
 33706           writeUTF: BAp.writeUTF,
 33707           writeUTFBytes: BAp.writeUTFBytes,
 33708           readBoolean: BAp.readBoolean,
 33709           readByte: BAp.readByte,
 33710           readBytes: BAp.readBytes,
 33711           readUnsignedByte: BAp.readUnsignedByte,
 33712           readShort: BAp.readShort,
 33713           readUnsignedShort: BAp.readUnsignedShort,
 33714           readInt: BAp.readInt,
 33715           readUnsignedInt: BAp.readUnsignedInt,
 33716           readFloat: BAp.readFloat,
 33717           readDouble: BAp.readDouble,
 33718           readMultiByte: BAp.readMultiByte,
 33719           readObject: function readObject() {
 33720             return AMFUtils.encodings[this.objectEncoding].read(this);
 33721           },
 33722           readUTF: BAp.readUTF,
 33723           readUTFBytes: BAp.readUTFBytes,
 33724           toString: BAp.toString,
 33725           clear: BAp.clear,
 33726           _compress: BAp.compress,
 33727           _uncompress: BAp.uncompress
 33728         },
 33729         static: {
 33730           defaultObjectEncoding: {
 33731             get: function () {
 33732               return ByteArray.DEFAULT_OBJECT_ENCODING;
 33733             },
 33734             set: function (e) {
 33735               ByteArray.DEFAULT_OBJECT_ENCODING = e;
 33739       };
 33740       return c;
 33742     function DomainClass(runtime, scope, instanceConstructor, baseClass) {
 33743       var c = new Class('File', instanceConstructor, C(instanceConstructor));
 33744       c.extend(baseClass);
 33745       c.native = {
 33746         instance: {
 33747           init: function (base) {
 33748             this.base = base;
 33749             this.nativeObject = new ApplicationDomain(AVM2.instance, base ? base.nativeObject : null);
 33750           },
 33751           loadBytes: function (byteArray, swfVersion) {
 33752             this.nativeObject.executeAbc(new AbcFile(byteArray.readRawBytes()));
 33753           },
 33754           getClass: function (className) {
 33755             return this.nativeObject.getClass(className);
 33757         },
 33758         static: {
 33759           currentDomain: {
 33760             get: function () {
 33761               var domain = Object.create(instanceConstructor.prototype);
 33762               domain.nativeObject = AVM2.currentDomain();
 33763               return domain;
 33767       };
 33768       return c;
 33770     function SystemClass(runtime, scope, instanceConstructor, baseClass) {
 33771       var c = new Class('System', instanceConstructor, C(instanceConstructor));
 33772       c.extend(baseClass);
 33773       c.native = {
 33774         static: {
 33775           swfVersion: {
 33776             get: function () {
 33777               return 19;
 33779           },
 33780           apiVersion: {
 33781             get: function () {
 33782               return 26;
 33784           },
 33785           getArgv: function () {
 33786             return [];
 33787           },
 33788           getRunmode: function () {
 33789             return 'mixed';
 33792       };
 33793       return c;
 33795     function bugzilla(n) {
 33796       switch (n) {
 33797       case 574600:
 33798         return true;
 33800       return false;
 33802     return {
 33803       print: constant(print),
 33804       notImplemented: constant(notImplemented),
 33805       debugBreak: constant(debugBreak),
 33806       bugzilla: constant(bugzilla),
 33807       decodeURI: constant(decodeURI),
 33808       decodeURIComponent: constant(decodeURIComponent),
 33809       encodeURI: constant(encodeURI),
 33810       encodeURIComponent: constant(encodeURIComponent),
 33811       isNaN: constant(isNaN),
 33812       isFinite: constant(isFinite),
 33813       parseInt: constant(parseInt),
 33814       parseFloat: constant(parseFloat),
 33815       escape: constant(escape),
 33816       unescape: constant(unescape),
 33817       isXMLName: constant(typeof isXMLName !== 'undefined' ? isXMLName : function () {
 33818         notImplemented('Chrome doesn\'t support isXMLName.');
 33819       }),
 33820       Function: Function,
 33821       String: String,
 33822       Array: Array,
 33823       Number: Number,
 33824       Boolean: Boolean,
 33825       Math: Math,
 33826       Date: Date,
 33827       RegExp: RegExp,
 33828       Object: Object,
 33829       ObjectClass: ObjectClass,
 33830       Class: ClassClass,
 33831       NamespaceClass: NamespaceClass,
 33832       FunctionClass: FunctionClass,
 33833       MethodClosureClass: MethodClosureClass,
 33834       BooleanClass: BooleanClass,
 33835       StringClass: StringClass,
 33836       NumberClass: NumberClass,
 33837       intClass: intClass,
 33838       uintClass: uintClass,
 33839       ArrayClass: ArrayClass,
 33840       VectorClass: VectorClass,
 33841       ObjectVectorClass: ObjectVectorClass,
 33842       IntVectorClass: IntVectorClass,
 33843       UIntVectorClass: UIntVectorClass,
 33844       DoubleVectorClass: DoubleVectorClass,
 33845       ByteArrayClass: ByteArrayClass,
 33846       ProxyClass: ProxyClass,
 33847       ErrorClass: makeErrorClass('Error'),
 33848       DefinitionErrorClass: makeErrorClass('DefinitionError'),
 33849       EvalErrorClass: makeErrorClass('EvalError'),
 33850       RangeErrorClass: makeErrorClass('RangeError'),
 33851       ReferenceErrorClass: makeErrorClass('ReferenceError'),
 33852       SecurityErrorClass: makeErrorClass('SecurityError'),
 33853       SyntaxErrorClass: makeErrorClass('SyntaxError'),
 33854       TypeErrorClass: makeErrorClass('TypeError'),
 33855       URIErrorClass: makeErrorClass('URIError'),
 33856       VerifyErrorClass: makeErrorClass('VerifyError'),
 33857       UninitializedErrorClass: makeErrorClass('UninitializedError'),
 33858       ArgumentErrorClass: makeErrorClass('ArgumentError'),
 33859       DateClass: DateClass,
 33860       MathClass: MathClass,
 33861       RegExpClass: RegExpClass,
 33862       DictionaryClass: DictionaryClass,
 33863       XMLClass: XMLClass,
 33864       XMLListClass: XMLListClass,
 33865       QNameClass: QNameClass,
 33866       JSONClass: JSONClass,
 33867       ShumwayClass: ShumwayClass,
 33868       CapabilitiesClass: CapabilitiesClass,
 33869       FileClass: FileClass,
 33870       DomainClass: DomainClass,
 33871       SystemClass: SystemClass,
 33872       getQualifiedClassName: constant(function (value) {
 33873         if (value === null) {
 33874           return 'null';
 33875         } else if (value === undefined) {
 33876           return 'void';
 33878         switch (typeof value) {
 33879         case 'number':
 33880           if ((value | 0) === value) {
 33881             return 'int';
 33883           return 'Number';
 33884         case 'string':
 33885           return 'String';
 33886         case 'boolean':
 33887           return 'Boolean';
 33888         case 'object':
 33889           if (value instanceof Date) {
 33890             return 'Date';
 33892           var cls;
 33893           if (value instanceof Class) {
 33894             cls = value;
 33895           } else if (value.class) {
 33896             cls = value.class;
 33897           } else if (value.classInfo) {
 33898             cls = value;
 33900           if (cls) {
 33901             var name = cls.classInfo.instanceInfo.name;
 33902             var uri = name.namespaces[0].uri;
 33903             if (uri) {
 33904               return uri + '::' + name.name;
 33906             return name.name;
 33908           break;
 33910         return notImplemented(value + ' (' + typeof value + ')');
 33911       }),
 33912       getQualifiedSuperclassName: constant(function (value) {
 33913         switch (typeof value) {
 33914         case 'number':
 33915         case 'string':
 33916         case 'boolean':
 33917           return 'Object';
 33918         case 'function':
 33919           return 'Function';
 33920         case 'object':
 33921           if (value instanceof Date) {
 33922             return 'Object';
 33924           var cls;
 33925           if (value.class) {
 33926             cls = value.class;
 33927           } else if (value.classInfo) {
 33928             cls = value;
 33930           if (cls && cls.baseClass) {
 33931             var name = cls.baseClass.classInfo.instanceInfo.name;
 33932             var uri = name.namespaces[0].uri;
 33933             if (uri) {
 33934               return uri + '::' + name.name;
 33936             return name.name;
 33938           return 'Object';
 33940         return notImplemented(value + ' (superOf ' + typeof value + ')');
 33941       }),
 33942       getDefinitionByName: constant(function (name) {
 33943         var simpleName = String(name).replace('::', '.');
 33944         return AVM2.currentDomain().getClass(simpleName);
 33945       }),
 33946       describeTypeJSON: constant(describeTypeJSON),
 33947       original: jsGlobal[VM_NATIVE_BUILTIN_ORIGINALS]
 33948     };
 33949     function describeTypeJSON(o, flags) {
 33950       var Flags = {
 33951           HIDE_NSURI_METHODS: 1,
 33952           INCLUDE_BASES: 2,
 33953           INCLUDE_INTERFACES: 4,
 33954           INCLUDE_VARIABLES: 8,
 33955           INCLUDE_ACCESSORS: 16,
 33956           INCLUDE_METHODS: 32,
 33957           INCLUDE_METADATA: 64,
 33958           INCLUDE_CONSTRUCTOR: 128,
 33959           INCLUDE_TRAITS: 256,
 33960           USE_ITRAITS: 512,
 33961           HIDE_OBJECT: 1024
 33962         };
 33963       var declaredByKey = publicName('declaredBy');
 33964       var metadataKey = publicName('metadata');
 33965       var accessKey = publicName('access');
 33966       var uriKey = publicName('uri');
 33967       var nameKey = publicName('name');
 33968       var typeKey = publicName('type');
 33969       var returnTypeKey = publicName('returnType');
 33970       var valueKey = publicName('value');
 33971       var keyKey = publicName('key');
 33972       var parametersKey = publicName('parameters');
 33973       var optionalKey = publicName('optional');
 33974       var cls = o.classInfo ? o : Object.getPrototypeOf(o).class;
 33975       true;
 33976       var info = cls.classInfo;
 33977       var description = {};
 33978       description[nameKey] = unmangledQualifiedName(info.instanceInfo.name);
 33979       description[publicName('isDynamic')] = cls === o ? true : !(info.instanceInfo.flags & CONSTANT_ClassSealed);
 33980       description[publicName('isStatic')] = cls === o;
 33981       description[publicName('isFinal')] = cls === o ? true : !(info.instanceInfo.flags & CONSTANT_ClassFinal);
 33982       if (flags & Flags.INCLUDE_TRAITS) {
 33983         description[publicName('traits')] = addTraits(cls, flags);
 33985       var metadata = null;
 33986       if (info.metadata) {
 33987         metadata = Object.keys(info.metadata).map(function (key) {
 33988           return describeMetadata(info.metadata[key]);
 33989         });
 33991       description[metadataKey] = metadata;
 33992       return description;
 33993       function publicName(str) {
 33994         return Multiname.getPublicQualifiedName(str);
 33996       function unmangledQualifiedName(mn) {
 33997         var name = mn.name;
 33998         var namespace = mn.namespaces[0];
 33999         if (namespace && namespace.uri) {
 34000           return namespace.uri + '::' + name;
 34002         return name;
 34004       function describeMetadata(metadata) {
 34005         var result = {};
 34006         result[nameKey] = metadata.name;
 34007         result[valueKey] = metadata.value.map(function (value) {
 34008           var val = {};
 34009           val[keyKey] = value.key;
 34010           val[valueKey] = value.value;
 34011           return value;
 34012         });
 34013         return result;
 34015       function addTraits(cls, flags) {
 34016         var includedMembers = [
 34017             flags & Flags.INCLUDE_VARIABLES,
 34018             flags & Flags.INCLUDE_METHODS,
 34019             flags & Flags.INCLUDE_ACCESSORS,
 34020             flags & Flags.INCLUDE_ACCESSORS
 34021           ];
 34022         var includeBases = flags & Flags.INCLUDE_BASES;
 34023         var includeMetadata = flags & Flags.INCLUDE_METADATA;
 34024         var obj = {};
 34025         var basesVal = obj[publicName('bases')] = includeBases ? [] : null;
 34026         if (flags & Flags.INCLUDE_INTERFACES) {
 34027           var interfacesVal = obj[publicName('interfaces')] = [];
 34028           if (flags & Flags.USE_ITRAITS) {
 34029             for (var key in cls.implementedInterfaces) {
 34030               var ifaceName = cls.implementedInterfaces[key].name;
 34031               interfacesVal.push(unmangledQualifiedName(ifaceName));
 34034         } else {
 34035           obj[publicName('interfaces')] = null;
 34037         var variablesVal = obj[publicName('variables')] = flags & Flags.INCLUDE_VARIABLES ? [] : null;
 34038         var accessorsVal = obj[publicName('accessors')] = flags & Flags.INCLUDE_ACCESSORS ? [] : null;
 34039         var methodsVal = obj[publicName('methods')] = flags & Flags.INCLUDE_METHODS ? [] : null;
 34040         var encounteredAccessors = {};
 34041         var addBase = false;
 34042         while (cls) {
 34043           var className = unmangledQualifiedName(cls.classInfo.instanceInfo.name);
 34044           if (includeBases && addBase) {
 34045             basesVal.push(className);
 34046           } else {
 34047             addBase = true;
 34049           if (flags & Flags.USE_ITRAITS) {
 34050             describeTraits(cls.classInfo.instanceInfo.traits);
 34051           } else {
 34052             describeTraits(cls.classInfo.traits);
 34054           cls = cls.baseClass;
 34056         function describeTraits(traits) {
 34057           true;
 34058           for (var i = 0; traits && i < traits.length; i++) {
 34059             var t = traits[i];
 34060             if (!includedMembers[t.kind] || !t.name.getNamespace().isPublic() && !t.name.uri) {
 34061               continue;
 34063             var name = unmangledQualifiedName(t.name);
 34064             if (encounteredAccessors[name]) {
 34065               var val = encounteredAccessors[name];
 34066               val[accessKey] = 'readwrite';
 34067               if (t.kind === TRAIT_Getter) {
 34068                 val[typeKey] = unmangledQualifiedName(t.methodInfo.returnType);
 34070               continue;
 34072             var val = {};
 34073             if (includeMetadata && t.metadata) {
 34074               var metadataVal = val[metadataKey] = [];
 34075               for (var key in t.metadata) {
 34076                 metadataVal.push(describeMetadata(t.metadata[key]));
 34078             } else {
 34079               val[metadataKey] = null;
 34081             val[declaredByKey] = className;
 34082             val[uriKey] = t.name.uri === undefined ? null : t.name.uri;
 34083             val[nameKey] = name;
 34084             if (!t.typeName && !(t.methodInfo && t.methodInfo.returnType)) {
 34085               continue;
 34087             val[t.kind === TRAIT_Method ? returnTypeKey : typeKey] = unmangledQualifiedName(t.kind === TRAIT_Slot ? t.typeName : t.methodInfo.returnType);
 34088             switch (t.kind) {
 34089             case TRAIT_Slot:
 34090               val[accessKey] = 'readwrite';
 34091               variablesVal.push(val);
 34092               break;
 34093             case TRAIT_Method:
 34094               var parametersVal = val[parametersKey] = [];
 34095               var parameters = t.methodInfo.parameters;
 34096               for (var j = 0; j < parameters.length; j++) {
 34097                 var param = parameters[j];
 34098                 var paramVal = {};
 34099                 paramVal[typeKey] = param.type ? unmangledQualifiedName(param.type) : '*';
 34100                 paramVal[optionalKey] = 'value' in param;
 34101                 parametersVal.push(paramVal);
 34103               methodsVal.push(val);
 34104               break;
 34105             case TRAIT_Getter:
 34106             case TRAIT_Setter:
 34107               val[accessKey] = t.kind === TRAIT_Getter ? 'read' : 'write';
 34108               accessorsVal.push(val);
 34109               encounteredAccessors[name] = val;
 34110               break;
 34111             default:
 34112               break;
 34116         return obj;
 34119   }();
 34120 function getNative(path) {
 34121   var chain = path.split('.');
 34122   var v = natives;
 34123   for (var i = 0, j = chain.length; i < j; i++) {
 34124     v = v && v[chain[i]];
 34126   true;
 34127   return v;
 34129 var disassemblerOptions = systemOptions.register(new OptionSet('Disassembler Options'));
 34130 var filter = disassemblerOptions.register(new Option('f', 'filter', 'string', 'SpciMsmNtu', '[S]ource, constant[p]ool, [c]lasses, [i]nstances, [M]etadata, [s]cripts, [m]ethods, multi[N]ames, S[t]atistics, [u]tf'));
 34131 function traceArray(writer, name, array, abc) {
 34132   if (array.length === 0) {
 34133     return;
 34135   writer.enter(name + ' {');
 34136   array.forEach(function (a, idx) {
 34137     a.trace(writer, abc);
 34138   });
 34139   writer.leave('}');
 34141 AbcFile.prototype.trace = function trace(writer) {
 34142   if (filter.value.indexOf('p') >= 0) {
 34143     this.constantPool.trace(writer);
 34145   if (filter.value.indexOf('N') >= 0) {
 34146     this.constantPool.traceMultinamesOnly(writer);
 34148   if (filter.value.indexOf('c') >= 0) {
 34149     traceArray(writer, 'classes', this.classes);
 34151   if (filter.value.indexOf('i') >= 0) {
 34152     traceArray(writer, 'instances', this.instances);
 34154   if (filter.value.indexOf('M') >= 0) {
 34155     traceArray(writer, 'metadata', this.metadata);
 34157   if (filter.value.indexOf('s') >= 0) {
 34158     traceArray(writer, 'scripts', this.scripts);
 34160   if (filter.value.indexOf('m') >= 0) {
 34161     traceArray(writer, 'methods', this.methods, this);
 34163   if (filter.value.indexOf('S') >= 0) {
 34164     traceSource(writer, this);
 34166   if (filter.value.indexOf('t') >= 0) {
 34167     traceStatistics(writer, this);
 34169   if (filter.value.indexOf('u') >= 0) {
 34170     print(JSON.stringify({
 34171       strings: this.constantPool.strings,
 34172       positionAfterUTFStrings: this.constantPool.positionAfterUTFStrings
 34173     }, null, 2));
 34175 };
 34176 ConstantPool.prototype.trace = function (writer) {
 34177   writer.enter('constantPool {');
 34178   for (var key in this) {
 34179     if (key === 'namespaces') {
 34180       writer.enter('namespaces {');
 34181       this.namespaces.forEach(function (ns, i) {
 34182         writer.writeLn(('' + i).padRight(' ', 3) + (ns ? ns.toString() : '*'));
 34183       });
 34184       writer.leave('}');
 34185     } else if (this[key] instanceof Array) {
 34186       writer.enter(key + ' ' + this[key].length + ' {');
 34187       writer.writeArray(this[key]);
 34188       writer.leave('}');
 34191   writer.leave('}');
 34192 };
 34193 ConstantPool.prototype.traceMultinamesOnly = function (writer) {
 34194   writer.writeArray(this.multinames, null, true);
 34195 };
 34196 ClassInfo.prototype.trace = function (writer) {
 34197   writer.enter('class ' + this + ' {');
 34198   traceArray(writer, 'traits', this.traits);
 34199   writer.leave('}');
 34200 };
 34201 MetaDataInfo.prototype.trace = function (writer) {
 34202   writer.enter(this + ' {');
 34203   this.value.forEach(function (item) {
 34204     writer.writeLn((item.key ? item.key + ': ' : '') + '"' + item.value + '"');
 34205   });
 34206   writer.leave('}');
 34207 };
 34208 InstanceInfo.prototype.trace = function (writer) {
 34209   writer.enter('instance ' + this + ' {');
 34210   traceArray(writer, 'traits', this.traits);
 34211   writer.leave('}');
 34212 };
 34213 ScriptInfo.prototype.trace = function (writer) {
 34214   writer.enter('script ' + this + ' {');
 34215   traceArray(writer, 'traits', this.traits);
 34216   writer.leave('}');
 34217 };
 34218 Trait.prototype.trace = function (writer) {
 34219   if (this.metadata) {
 34220     for (var key in this.metadata) {
 34221       if (this.metadata.hasOwnProperty(key)) {
 34222         this.metadata[key].trace(writer);
 34226   writer.writeLn(this);
 34227 };
 34228 function traceAbc(writer, abc) {
 34229   abc.trace(writer);
 34231 function traceOperand(operand, abc, code) {
 34232   var value = 0;
 34233   switch (operand.size) {
 34234   case 's08':
 34235     value = code.readS8();
 34236     break;
 34237   case 'u08':
 34238     value = code.readU8();
 34239     break;
 34240   case 's16':
 34241     value = code.readS16();
 34242     break;
 34243   case 's24':
 34244     value = code.readS24();
 34245     break;
 34246   case 'u30':
 34247     value = code.readU30();
 34248     break;
 34249   case 'u32':
 34250     value = code.readU32();
 34251     break;
 34252   default:
 34253     true;
 34254     break;
 34256   var description = '';
 34257   switch (operand.type) {
 34258   case '':
 34259     break;
 34260   case 'I':
 34261     description = abc.constantPool.ints[value];
 34262     break;
 34263   case 'U':
 34264     description = abc.constantPool.uints[value];
 34265     break;
 34266   case 'D':
 34267     description = abc.constantPool.doubles[value];
 34268     break;
 34269   case 'S':
 34270     description = abc.constantPool.strings[value];
 34271     break;
 34272   case 'N':
 34273     description = abc.constantPool.namespaces[value];
 34274     break;
 34275   case 'CI':
 34276     description = abc.classes[value];
 34277     break;
 34278   case 'M':
 34279     return abc.constantPool.multinames[value];
 34280   default:
 34281     description = '?';
 34282     break;
 34284   return operand.name + ':' + value + (description === '' ? '' : ' (' + description + ')');
 34286 function traceOperands(opcode, abc, code, rewind) {
 34287   rewind = rewind || false;
 34288   var old = code.position;
 34289   var str = '';
 34290   if (opcode.operands === null) {
 34291     str = 'null';
 34292   } else {
 34293     opcode.operands.forEach(function (op, i) {
 34294       str += traceOperand(op, abc, code);
 34295       if (i < opcode.operands.length - 1) {
 34296         str += ', ';
 34298     });
 34300   if (rewind) {
 34301     code.seek(old);
 34303   return str;
 34305 MethodInfo.prototype.trace = function trace(writer) {
 34306   var abc = this.abc;
 34307   writer.enter('method' + (this.name ? ' ' + this.name : '') + ' {');
 34308   writer.writeLn('flags: ' + getFlags(this.flags, 'NEED_ARGUMENTS|NEED_ACTIVATION|NEED_REST|HAS_OPTIONAL||NATIVE|SET_DXN|HAS_PARAM_NAMES'.split('|')));
 34309   writer.writeLn('parameters: ' + this.parameters.map(function (x) {
 34310     return (x.type ? Multiname.getQualifiedName(x.type) + '::' : '') + x.name;
 34311   }));
 34312   if (!this.code) {
 34313     writer.leave('}');
 34314     return;
 34316   var code = new AbcStream(this.code);
 34317   traceArray(writer, 'traits', this.traits);
 34318   writer.enter('code {');
 34319   while (code.remaining() > 0) {
 34320     var bc = code.readU8();
 34321     var opcode = opcodeTable[bc];
 34322     var str, defaultOffset, offset, count;
 34323     str = ('' + code.position).padRight(' ', 6);
 34324     switch (bc) {
 34325     case OP_lookupswitch:
 34326       str += opcode.name + ': defaultOffset: ' + code.readS24();
 34327       var caseCount = code.readU30();
 34328       str += ', caseCount: ' + caseCount;
 34329       for (var i = 0; i < caseCount + 1; i++) {
 34330         str += ' offset: ' + code.readS24();
 34332       writer.writeLn(str);
 34333       break;
 34334     default:
 34335       if (opcode) {
 34336         str += opcode.name.padRight(' ', 20);
 34337         if (!opcode.operands) {
 34338           true;
 34339         } else {
 34340           if (opcode.operands.length > 0) {
 34341             str += traceOperands(opcode, abc, code);
 34343           writer.writeLn(str);
 34345       } else {
 34346         true;
 34348       break;
 34351   writer.leave('}');
 34352   writer.leave('}');
 34353 };
 34354 var SourceTracer = function () {
 34355     function literal(value) {
 34356       if (value === undefined) {
 34357         return 'undefined';
 34358       } else if (value === null) {
 34359         return 'null';
 34360       } else if (typeof value === 'string') {
 34361         return '"' + value + '"';
 34362       } else {
 34363         return String(value);
 34366     function getSignature(mi, excludeTypesAndDefaultValues) {
 34367       return mi.parameters.map(function (x) {
 34368         var str = x.name;
 34369         if (!excludeTypesAndDefaultValues) {
 34370           if (x.type) {
 34371             str += ':' + x.type.getName();
 34373           if (x.value !== undefined) {
 34374             str += ' = ' + literal(x.value);
 34377         return str;
 34378       }).join(', ');
 34380     function SourceTracer(writer) {
 34381       this.writer = writer;
 34383     SourceTracer.prototype = {
 34384       traceTraits: function traceTraits(traits, isStatic, inInterfaceNamespace) {
 34385         var writer = this.writer;
 34386         var tracer = this;
 34387         traits.forEach(function (trait) {
 34388           var str;
 34389           var accessModifier = Multiname.getAccessModifier(trait.name);
 34390           var namespaceName = trait.name.namespaces[0].uri;
 34391           if (namespaceName) {
 34392             if (namespaceName === 'http://adobe.com/AS3/2006/builtin') {
 34393               namespaceName = 'AS3';
 34395             if (accessModifier === 'public') {
 34396               str = inInterfaceNamespace === namespaceName ? '' : namespaceName;
 34397             } else {
 34398               str = accessModifier;
 34400           } else {
 34401             str = accessModifier;
 34403           if (isStatic) {
 34404             str += ' static';
 34406           if (trait.isSlot() || trait.isConst()) {
 34407             tracer.traceMetadata(trait.metadata);
 34408             if (trait.isConst()) {
 34409               str += ' const';
 34410             } else {
 34411               str += ' var';
 34413             str += ' ' + trait.name.getName();
 34414             if (trait.typeName) {
 34415               str += ':' + trait.typeName.getName();
 34417             if (trait.value) {
 34418               str += ' = ' + literal(trait.value);
 34420             writer.writeLn(str + ';');
 34421           } else if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
 34422             tracer.traceMetadata(trait.metadata);
 34423             var mi = trait.methodInfo;
 34424             if (trait.attributes & ATTR_Override) {
 34425               str += ' override';
 34427             if (mi.isNative()) {
 34428               str += ' native';
 34430             str += ' function';
 34431             str += trait.isGetter() ? ' get' : trait.isSetter() ? ' set' : '';
 34432             str += ' ' + trait.name.getName();
 34433             str += '(' + getSignature(mi) + ')';
 34434             str += mi.returnType ? ':' + mi.returnType.getName() : '';
 34435             if (true) {
 34436               var className;
 34437               var prefix = '';
 34438               if (trait.holder instanceof ClassInfo) {
 34439                 className = trait.holder.instanceInfo.name;
 34440                 if (className.namespaces[0].uri) {
 34441                   prefix += className.namespaces[0].uri + '::';
 34443                 prefix += className.getName();
 34444                 prefix += '$/';
 34445               } else if (trait.holder instanceof InstanceInfo) {
 34446                 className = trait.holder.name;
 34447                 if (className.namespaces[0].uri) {
 34448                   prefix += className.namespaces[0].uri + '::';
 34450                 prefix += className.getName();
 34451                 prefix += '/';
 34452               } else {
 34453                 prefix = 'global/';
 34455               var getSet = trait.isGetter() ? 'get ' : trait.isSetter() ? 'set ' : '';
 34456               if (!mi.isNative()) {
 34459             if (mi.isNative()) {
 34460               writer.writeLn(str + ';');
 34461             } else {
 34462               if (inInterfaceNamespace) {
 34463                 writer.writeLn(str + ';');
 34464               } else {
 34465                 writer.writeLn(str + ' { notImplemented("' + trait.name.getName() + '"); }');
 34468           } else if (trait.isClass()) {
 34469             var className = trait.classInfo.instanceInfo.name;
 34470             writer.enter('package ' + className.namespaces[0].uri + ' {\n');
 34471             tracer.traceMetadata(trait.metadata);
 34472             tracer.traceClass(trait.classInfo);
 34473             writer.leave('\n}');
 34474             tracer.traceClassStub(trait);
 34475           } else {
 34476             notImplemented();
 34478         });
 34479       },
 34480       traceClassStub2: function traceClassStub(trait) {
 34481         var writer = this.writer;
 34482         var ci = trait.classInfo;
 34483         var ii = ci.instanceInfo;
 34484         var name = ii.name.getName();
 34485         var native = trait.metadata ? trait.metadata.native : null;
 34486         if (!native) {
 34487           return false;
 34489         writer.writeLn('Cut and paste the following into `native.js\' and edit accordingly');
 34490         writer.writeLn('8< --------------------------------------------------------------');
 34491         writer.enter('natives.' + native.cls + ' = function ' + native.cls + '(runtime, scope, instanceConstructor, baseClass) {');
 34492         writer.writeLn('var c = new Class("' + name + '", instanceConstructor, ApplicationDomain.passthroughCallable(instanceConstructor));');
 34493         writer.writeLn('c.extend(baseClass);\n');
 34494         function traceTraits(traits, isStatic) {
 34495           var nativeMethodTraits = [];
 34496           traits.forEach(function (trait, i) {
 34497             if (trait.isMethod() || trait.isGetter() || trait.isSetter()) {
 34498               if (trait.methodInfo.isNative()) {
 34499                 nativeMethodTraits.push(trait);
 34502           });
 34503           nativeMethodTraits.forEach(function (trait, i) {
 34504             var mi = trait.methodInfo;
 34505             var traitName = trait.name.getName();
 34506             writer.writeLn('// ' + traitName + ' :: ' + (mi.parameters.length ? getSignature(mi) : 'void') + ' -> ' + (mi.returnType ? mi.returnType.getName() : 'any'));
 34507             var prop;
 34508             if (trait.isGetter()) {
 34509               prop = '"get ' + traitName + '"';
 34510             } else if (trait.isSetter()) {
 34511               prop = '"set ' + traitName + '"';
 34512             } else {
 34513               prop = traitName;
 34515             writer.enter(prop + ': function ' + traitName + '(' + getSignature(mi, true) + ') {');
 34516             writer.writeLn('  notImplemented("' + name + '.' + traitName + '");');
 34517             writer.leave('}' + (i === nativeMethodTraits.length - 1 ? '' : ',\n'));
 34518           });
 34520         writer.enter('c.nativeStatics = {');
 34521         traceTraits(ci.traits, true);
 34522         writer.leave('};\n');
 34523         writer.enter('c.nativeMethods = {');
 34524         traceTraits(ii.traits);
 34525         writer.leave('};\n');
 34526         writer.writeLn('return c;');
 34527         writer.leave('};');
 34528         writer.writeLn('-------------------------------------------------------------- >8');
 34529         return true;
 34530       },
 34531       traceClassStub: function traceClassStub(trait) {
 34532         var writer = this.writer;
 34533         var ci = trait.classInfo;
 34534         var ii = ci.instanceInfo;
 34535         var className = ii.name.getName();
 34536         var native = trait.metadata ? trait.metadata.native : null;
 34537         writer.writeLn('Cut and paste the following glue and edit accordingly.');
 34538         writer.writeLn('Class ' + ii);
 34539         writer.writeLn('8< --------------------------------------------------------------');
 34540         var uri = ii.name.namespaces[0].uri;
 34541         writer.enter('var ' + className + 'Definition = (function () {');
 34542         function maxTraitNameLength(traits) {
 34543           var length = 0;
 34544           traits.forEach(function (t) {
 34545             length = Math.max(t.name.name.length, length);
 34546           });
 34547           return length;
 34549         function quote(s) {
 34550           return '\'' + s + '\'';
 34552         function filterTraits(traits, isNative) {
 34553           function isMethod(x) {
 34554             return x.isMethod() || x.isGetter() || x.isSetter();
 34556           return {
 34557             properties: traits.filter(function (trait) {
 34558               return !isNative && !isMethod(trait);
 34559             }),
 34560             methods: traits.filter(function (trait) {
 34561               return isMethod(trait) && isNative === trait.methodInfo.isNative();
 34562             })
 34563           };
 34565         function writeTraits(traits, isNative, isStatic) {
 34566           traits = filterTraits(traits, isNative);
 34567           var methods = [];
 34568           var gettersAndSetters = createEmptyObject();
 34569           traits.methods.forEach(function (trait, i) {
 34570             var traitName = trait.name.getName();
 34571             if (trait.isGetter() || trait.isSetter()) {
 34572               if (!gettersAndSetters[traitName]) {
 34573                 gettersAndSetters[traitName] = [];
 34575               gettersAndSetters[traitName].push(trait);
 34576             } else {
 34577               methods.push(trait);
 34579           });
 34580           function writeTrait(trait, writeComma) {
 34581             var mi = trait.methodInfo;
 34582             var traitName = trait.name.getName();
 34583             var signature = '// (' + (mi.parameters.length ? getSignature(mi) : 'void') + ') -> ' + (mi.returnType ? mi.returnType.getName() : 'any');
 34584             var propertyName = traitName;
 34585             if (trait.isGetter()) {
 34586               propertyName = 'get';
 34587             } else if (trait.isSetter()) {
 34588               propertyName = 'set';
 34590             writer.enter(propertyName + ': function ' + traitName + '(' + getSignature(mi, true) + ') { ' + signature);
 34591             writer.writeLn('notImplemented("' + className + '.' + traitName + '");');
 34592             if (!isStatic) {
 34593               if (trait.isGetter()) {
 34594                 writer.writeLn('return this._' + traitName + ';');
 34595               } else if (trait.isSetter()) {
 34596                 writer.writeLn('this._' + traitName + ' = ' + mi.parameters[0].name + ';');
 34599             writer.leave('}' + (writeComma ? ',' : ''));
 34601           for (var i = 0; i < methods.length; i++) {
 34602             writeTrait(methods[i], i < methods.length - 1);
 34604           var keyValues = toKeyValueArray(gettersAndSetters);
 34605           for (var j = 0; j < keyValues.length; j++) {
 34606             writer.enter(keyValues[j][0] + ': {');
 34607             var list = keyValues[j][1];
 34608             for (var i = 0; i < list.length; i++) {
 34609               writeTrait(list[i], i < list.length - 1);
 34611             writer.leave('}' + (j < keyValues.length - 1 ? ',' : ''));
 34613           traits.properties.forEach(function (trait, i) {
 34614             var traitName = trait.name.getName();
 34615             var last = i === traits.properties.length - 1;
 34616             if (trait.name.getNamespace().isPublic()) {
 34617               writer.writeLn(traitName + ': ' + quote('public ' + trait.name.name) + (last ? '' : ','));
 34619           });
 34621         writer.enter('return {');
 34622         writer.writeLn('// (' + getSignature(ii.init, false) + ')');
 34623         writer.writeLn('__class__: "' + uri + '.' + className + '",');
 34624         writer.enter('initialize: function () {');
 34625         writer.leave('},');
 34626         writer.enter('__glue__: {');
 34627         writer.enter('native: {');
 34628         writer.enter('static: {');
 34629         writeTraits(ci.traits, true, true);
 34630         writer.leave('},');
 34631         writer.enter('instance: {');
 34632         writeTraits(ii.traits, true);
 34633         writer.leave('}');
 34634         writer.leave('},');
 34635         writer.enter('script: {');
 34636         writer.writeLn('instance: Glue.ALL');
 34637         writer.leave('}');
 34638         writer.leave('}');
 34639         writer.leave('};');
 34640         writer.leave('}).call(this);');
 34641         writer.writeLn('-------------------------------------------------------------- >8');
 34642         return true;
 34643       },
 34644       traceClass: function traceClass(ci) {
 34645         var writer = this.writer;
 34646         var ii = ci.instanceInfo;
 34647         var name = ii.name;
 34648         var str = Multiname.getAccessModifier(name);
 34649         if (ii.isFinal()) {
 34650           str += ' final';
 34652         if (!ii.isSealed()) {
 34653           str += ' dynamic';
 34655         str += ii.isInterface() ? ' interface ' : ' class ';
 34656         str += name.getName();
 34657         if (ii.superName && ii.superName.getName() !== 'Object') {
 34658           str += ' extends ' + ii.superName.getName();
 34660         if (ii.interfaces.length) {
 34661           str += ' implements ' + ii.interfaces.map(function (x) {
 34662             return x.getName();
 34663           }).join(', ');
 34665         writer.enter(str + ' {');
 34666         if (!ii.isInterface()) {
 34667           writer.writeLn('public function ' + name.getName() + '(' + getSignature(ii.init) + ') {}');
 34669         var interfaceNamespace;
 34670         if (ii.isInterface()) {
 34671           interfaceNamespace = name.namespaces[0].uri + ':' + name.name;
 34673         this.traceTraits(ci.traits, true, interfaceNamespace);
 34674         this.traceTraits(ii.traits, false, interfaceNamespace);
 34675         writer.leave('}');
 34676       },
 34677       traceMetadata: function traceMetadata(metadata) {
 34678         var writer = this.writer;
 34679         for (var key in metadata) {
 34680           if (metadata.hasOwnProperty(key)) {
 34681             if (key.indexOf('__') === 0) {
 34682               continue;
 34684             writer.writeLn('[' + key + '(' + metadata[key].value.map(function (m) {
 34685               var str = m.key ? m.key + '=' : '';
 34686               return str + '"' + m.value + '"';
 34687             }).join(', ') + ')]');
 34691     };
 34692     return SourceTracer;
 34693   }();
 34694 function traceSource(writer, abc) {
 34695   var tracer = new SourceTracer(writer);
 34696   abc.scripts.forEach(function (script) {
 34697     tracer.traceTraits(script.traits);
 34698   });
 34700 function traceStatistics(writer, abc) {
 34701   var libraryClassCounter = new Shumway.Metrics.Counter(true);
 34702   var librarySuperClassCounter = new Shumway.Metrics.Counter(true);
 34703   var libraryMethodCounter = new Shumway.Metrics.Counter(true);
 34704   var libraryProperties = new Shumway.Metrics.Counter(true);
 34705   var definedClasses = {};
 34706   var definedMethods = {};
 34707   var definedProperties = {};
 34708   abc.classes.forEach(function (x) {
 34709     var className = x.instanceInfo.name.name;
 34710     definedClasses[className] = true;
 34711   });
 34712   abc.scripts.forEach(function (s) {
 34713     s.traits.forEach(function (t) {
 34714       if (t.isClass()) {
 34715         var superClassName = t.classInfo.instanceInfo.superName ? t.classInfo.instanceInfo.superName.name : '?';
 34716         if (!(superClassName in definedClasses)) {
 34717           librarySuperClassCounter.count(superClassName);
 34719         t.classInfo.traits.forEach(function (st) {
 34720           if (st.isMethod()) {
 34721             definedMethods[st.name.name] = true;
 34722           } else {
 34723             definedProperties[st.name.name] = true;
 34725         });
 34726         t.classInfo.instanceInfo.traits.forEach(function (it) {
 34727           if (it.isMethod() && !(it.attributes & ATTR_Override)) {
 34728             definedMethods[it.name.name] = true;
 34729           } else {
 34730             definedProperties[it.name.name] = true;
 34732         });
 34734     });
 34735   });
 34736   var opCounter = new Shumway.Metrics.Counter(true);
 34737   abc.methods.forEach(function (m) {
 34738     if (!m.code) {
 34739       return;
 34741     function readOperand(operand) {
 34742       var value = 0;
 34743       switch (operand.size) {
 34744       case 's08':
 34745         value = code.readS8();
 34746         break;
 34747       case 'u08':
 34748         value = code.readU8();
 34749         break;
 34750       case 's16':
 34751         value = code.readS16();
 34752         break;
 34753       case 's24':
 34754         value = code.readS24();
 34755         break;
 34756       case 'u30':
 34757         value = code.readU30();
 34758         break;
 34759       case 'u32':
 34760         value = code.readU32();
 34761         break;
 34762       default:
 34763         true;
 34764         break;
 34766       var description = '';
 34767       switch (operand.type) {
 34768       case '':
 34769         break;
 34770       case 'I':
 34771         description = abc.constantPool.ints[value];
 34772         break;
 34773       case 'U':
 34774         description = abc.constantPool.uints[value];
 34775         break;
 34776       case 'D':
 34777         description = abc.constantPool.doubles[value];
 34778         break;
 34779       case 'S':
 34780         description = abc.constantPool.strings[value];
 34781         break;
 34782       case 'N':
 34783         description = abc.constantPool.namespaces[value];
 34784         break;
 34785       case 'CI':
 34786         description = abc.classes[value];
 34787         break;
 34788       case 'M':
 34789         description = abc.constantPool.multinames[value];
 34790         break;
 34791       default:
 34792         description = '?';
 34793         break;
 34795       return description;
 34797     var code = new AbcStream(m.code);
 34798     while (code.remaining() > 0) {
 34799       var bc = code.readU8();
 34800       var op = opcodeTable[bc];
 34801       var operands = null;
 34802       if (op) {
 34803         opCounter.count(op.name);
 34804         if (op.operands) {
 34805           operands = op.operands.map(readOperand);
 34807         switch (bc) {
 34808         case OP_call:
 34809         case OP_callmethod:
 34810           continue;
 34811         case OP_callproperty:
 34812         case OP_callproplex:
 34813         case OP_callpropvoid:
 34814         case OP_callstatic:
 34815         case OP_callsuper:
 34816         case OP_callsupervoid:
 34817           if (operands[0] && !(operands[0].name in definedMethods)) {
 34818             libraryMethodCounter.count(operands[0].name);
 34820           break;
 34821         case OP_constructprop:
 34822           if (operands[0] && !(operands[0].name in definedClasses)) {
 34823             libraryClassCounter.count(operands[0].name);
 34825           break;
 34826         case OP_getproperty:
 34827         case OP_setproperty:
 34828           if (operands[0] && !(operands[0].name in definedProperties)) {
 34829             libraryProperties.count(operands[0].name);
 34831           break;
 34835   });
 34836   writer.writeLn(JSON.stringify({
 34837     definedClasses: definedClasses,
 34838     definedMethods: definedMethods,
 34839     definedProperties: definedProperties,
 34840     libraryClasses: libraryClassCounter.counts,
 34841     librarySuperClasses: librarySuperClassCounter.counts,
 34842     libraryMethods: libraryMethodCounter.counts,
 34843     libraryProperties: libraryProperties.counts,
 34844     operations: opCounter.counts
 34845   }, null, 2));
 34847 var Shumway;
 34848 (function (Shumway) {
 34849   (function (AVM2) {
 34850     var OP = Shumway.AVM2.ABC.OP;
 34851     var Scope = Shumway.AVM2.Runtime.Scope;
 34852     var asCoerceByMultiname = Shumway.AVM2.Runtime.asCoerceByMultiname;
 34853     var asGetSlot = Shumway.AVM2.Runtime.asGetSlot;
 34854     var asSetSlot = Shumway.AVM2.Runtime.asSetSlot;
 34855     var asHasNext2 = Shumway.AVM2.Runtime.asHasNext2;
 34856     var asCoerce = Shumway.AVM2.Runtime.asCoerce;
 34857     var asCoerceString = Shumway.AVM2.Runtime.asCoerceString;
 34858     var asAsType = Shumway.AVM2.Runtime.asAsType;
 34859     var asTypeOf = Shumway.AVM2.Runtime.asTypeOf;
 34860     var asIsInstanceOf = Shumway.AVM2.Runtime.asIsInstanceOf;
 34861     var asIsType = Shumway.AVM2.Runtime.asIsType;
 34862     var applyType = Shumway.AVM2.Runtime.applyType;
 34863     var createFunction = Shumway.AVM2.Runtime.createFunction;
 34864     var createClass = Shumway.AVM2.Runtime.createClass;
 34865     var getDescendants = Shumway.AVM2.Runtime.getDescendants;
 34866     var checkFilter = Shumway.AVM2.Runtime.checkFilter;
 34867     var asAdd = Shumway.AVM2.Runtime.asAdd;
 34868     var translateError = Shumway.AVM2.Runtime.translateError;
 34869     var asCreateActivation = Shumway.AVM2.Runtime.asCreateActivation;
 34870     var sliceArguments = Shumway.AVM2.Runtime.sliceArguments;
 34871     var boxValue = Shumway.ObjectUtilities.boxValue;
 34872     var popManyInto = Shumway.ArrayUtilities.popManyInto;
 34873     var construct = Shumway.AVM2.Runtime.construct;
 34874     var Multiname = Shumway.AVM2.ABC.Multiname;
 34875     var ScopeStack = function () {
 34876         function ScopeStack(parent) {
 34877           this.parent = parent;
 34878           this.stack = [];
 34879           this.isWith = [];
 34881         ScopeStack.prototype.push = function (object, isWith) {
 34882           this.stack.push(object);
 34883           this.isWith.push(!(!isWith));
 34884         };
 34885         ScopeStack.prototype.get = function (index) {
 34886           return this.stack[index];
 34887         };
 34888         ScopeStack.prototype.clear = function () {
 34889           this.stack.length = 0;
 34890           this.isWith.length = 0;
 34891         };
 34892         ScopeStack.prototype.pop = function () {
 34893           this.isWith.pop();
 34894           this.stack.pop();
 34895         };
 34896         ScopeStack.prototype.topScope = function () {
 34897           if (!this.scopes) {
 34898             this.scopes = [];
 34900           var parent = this.parent;
 34901           for (var i = 0; i < this.stack.length; i++) {
 34902             var object = this.stack[i], isWith = this.isWith[i], scope = this.scopes[i];
 34903             if (!scope || scope.parent !== parent || scope.object !== object || scope.isWith !== isWith) {
 34904               scope = this.scopes[i] = new Scope(parent, object, isWith);
 34906             parent = scope;
 34908           return parent;
 34909         };
 34910         return ScopeStack;
 34911       }();
 34912     function popNameInto(stack, mn, out) {
 34913       out.flags = mn.flags;
 34914       if (mn.isRuntimeName()) {
 34915         out.name = stack.pop();
 34916       } else {
 34917         out.name = mn.name;
 34919       if (mn.isRuntimeNamespace()) {
 34920         out.namespaces = [
 34921           stack.pop()
 34922         ];
 34923       } else {
 34924         out.namespaces = mn.namespaces;
 34927     var Interpreter = function () {
 34928         function Interpreter() {
 34930         Interpreter.interpretMethod = function ($this, method, savedScope, methodArgs) {
 34931           true;
 34932           Counter.count('Interpret Method');
 34933           var abc = method.abc;
 34934           var ints = abc.constantPool.ints;
 34935           var uints = abc.constantPool.uints;
 34936           var doubles = abc.constantPool.doubles;
 34937           var strings = abc.constantPool.strings;
 34938           var methods = abc.methods;
 34939           var multinames = abc.constantPool.multinames;
 34940           var domain = abc.applicationDomain;
 34941           var exceptions = method.exceptions;
 34942           var locals = [
 34943               $this
 34944             ];
 34945           var stack = [], scopeStack = new ScopeStack(savedScope);
 34946           var parameterCount = method.parameters.length;
 34947           var argCount = methodArgs.length;
 34948           var value;
 34949           for (var i = 0; i < parameterCount; i++) {
 34950             var parameter = method.parameters[i];
 34951             if (i < argCount) {
 34952               value = methodArgs[i];
 34953             } else {
 34954               value = parameter.value;
 34956             if (parameter.type && !parameter.type.isAnyName()) {
 34957               value = asCoerceByMultiname(domain, parameter.type, value);
 34959             locals.push(value);
 34961           if (method.needsRest()) {
 34962             locals.push(sliceArguments(methodArgs, parameterCount));
 34963           } else if (method.needsArguments()) {
 34964             locals.push(sliceArguments(methodArgs, 0));
 34966           var bytecodes = method.analysis.bytecodes;
 34967           var object, index, multiname, result, a, b, args = [], mn = Multiname.TEMPORARY;
 34968           interpretLabel:
 34969             for (var pc = 0, end = bytecodes.length; pc < end;) {
 34970               try {
 34971                 var bc = bytecodes[pc];
 34972                 var op = bc.op;
 34973                 switch (op | 0) {
 34974                 case 3:
 34975                   throw stack.pop();
 34976                 case 4:
 34977                   popNameInto(stack, multinames[bc.index], mn);
 34978                   stack.push(stack.pop().asGetSuper(savedScope, mn.namespaces, mn.name, mn.flags));
 34979                   break;
 34980                 case 5:
 34981                   value = stack.pop();
 34982                   popNameInto(stack, multinames[bc.index], mn);
 34983                   stack.pop().asSetSuper(savedScope, mn.namespaces, mn.name, mn.flags, value);
 34984                   break;
 34985                 case 8:
 34986                   locals[bc.index] = undefined;
 34987                   break;
 34988                 case 12:
 34989                   b = stack.pop();
 34990                   a = stack.pop();
 34991                   pc = !(a < b) ? bc.offset : pc + 1;
 34992                   continue;
 34993                 case 24:
 34994                   b = stack.pop();
 34995                   a = stack.pop();
 34996                   pc = a >= b ? bc.offset : pc + 1;
 34997                   continue;
 34998                 case 13:
 34999                   b = stack.pop();
 35000                   a = stack.pop();
 35001                   pc = !(a <= b) ? bc.offset : pc + 1;
 35002                   continue;
 35003                 case 23:
 35004                   b = stack.pop();
 35005                   a = stack.pop();
 35006                   pc = a > b ? bc.offset : pc + 1;
 35007                   continue;
 35008                 case 14:
 35009                   b = stack.pop();
 35010                   a = stack.pop();
 35011                   pc = !(a > b) ? bc.offset : pc + 1;
 35012                   continue;
 35013                 case 22:
 35014                   b = stack.pop();
 35015                   a = stack.pop();
 35016                   pc = a <= b ? bc.offset : pc + 1;
 35017                   continue;
 35018                 case 15:
 35019                   b = stack.pop();
 35020                   a = stack.pop();
 35021                   pc = !(a >= b) ? bc.offset : pc + 1;
 35022                   continue;
 35023                 case 21:
 35024                   b = stack.pop();
 35025                   a = stack.pop();
 35026                   pc = a < b ? bc.offset : pc + 1;
 35027                   continue;
 35028                 case 16:
 35029                   pc = bc.offset;
 35030                   continue;
 35031                 case 17:
 35032                   pc = !(!stack.pop()) ? bc.offset : pc + 1;
 35033                   continue;
 35034                 case 18:
 35035                   pc = !stack.pop() ? bc.offset : pc + 1;
 35036                   continue;
 35037                 case 19:
 35038                   b = stack.pop();
 35039                   a = stack.pop();
 35040                   pc = a == b ? bc.offset : pc + 1;
 35041                   continue;
 35042                 case 20:
 35043                   b = stack.pop();
 35044                   a = stack.pop();
 35045                   pc = a != b ? bc.offset : pc + 1;
 35046                   continue;
 35047                 case 25:
 35048                   b = stack.pop();
 35049                   a = stack.pop();
 35050                   pc = a === b ? bc.offset : pc + 1;
 35051                   continue;
 35052                 case 26:
 35053                   b = stack.pop();
 35054                   a = stack.pop();
 35055                   pc = a !== b ? bc.offset : pc + 1;
 35056                   continue;
 35057                 case 27:
 35058                   index = stack.pop();
 35059                   if (index < 0 || index >= bc.offsets.length) {
 35060                     index = bc.offsets.length - 1;
 35062                   pc = bc.offsets[index];
 35063                   continue;
 35064                 case 28:
 35065                   scopeStack.push(boxValue(stack.pop()), true);
 35066                   break;
 35067                 case 29:
 35068                   scopeStack.pop();
 35069                   break;
 35070                 case 30:
 35071                   index = stack.pop();
 35072                   stack[stack.length - 1] = boxValue(stack[stack.length - 1]).asNextName(index);
 35073                   break;
 35074                 case 35:
 35075                   index = stack.pop();
 35076                   stack[stack.length - 1] = boxValue(stack[stack.length - 1]).asNextValue(index);
 35077                   break;
 35078                 case 50:
 35079                   result = asHasNext2(locals[bc.object], locals[bc.index]);
 35080                   locals[bc.object] = result.object;
 35081                   locals[bc.index] = result.index;
 35082                   stack.push(!(!result.index));
 35083                   break;
 35084                 case 32:
 35085                   stack.push(null);
 35086                   break;
 35087                 case 33:
 35088                   stack.push(undefined);
 35089                   break;
 35090                 case 36:
 35091                 case 37:
 35092                   stack.push(bc.value);
 35093                   break;
 35094                 case 44:
 35095                   stack.push(strings[bc.index]);
 35096                   break;
 35097                 case 45:
 35098                   stack.push(ints[bc.index]);
 35099                   break;
 35100                 case 46:
 35101                   stack.push(uints[bc.index]);
 35102                   break;
 35103                 case 47:
 35104                   stack.push(doubles[bc.index]);
 35105                   break;
 35106                 case 38:
 35107                   stack.push(true);
 35108                   break;
 35109                 case 39:
 35110                   stack.push(false);
 35111                   break;
 35112                 case 40:
 35113                   stack.push(NaN);
 35114                   break;
 35115                 case 41:
 35116                   stack.pop();
 35117                   break;
 35118                 case 42:
 35119                   stack.push(stack[stack.length - 1]);
 35120                   break;
 35121                 case 43:
 35122                   object = stack[stack.length - 1];
 35123                   stack[stack.length - 1] = stack[stack.length - 2];
 35124                   stack[stack.length - 2] = object;
 35125                   break;
 35126                 case 48:
 35127                   scopeStack.push(boxValue(stack.pop()), false);
 35128                   break;
 35129                 case 64:
 35130                   stack.push(createFunction(methods[bc.index], scopeStack.topScope(), true));
 35131                   break;
 35132                 case 65:
 35133                   popManyInto(stack, bc.argCount, args);
 35134                   object = stack.pop();
 35135                   stack[stack.length - 1] = stack[stack.length - 1].apply(object, args);
 35136                   break;
 35137                 case 66:
 35138                   popManyInto(stack, bc.argCount, args);
 35139                   stack[stack.length - 1] = construct(stack[stack.length - 1], args);
 35140                   break;
 35141                 case 71:
 35142                   return;
 35143                 case 72:
 35144                   if (method.returnType) {
 35145                     return asCoerceByMultiname(domain, method.returnType, stack.pop());
 35147                   return stack.pop();
 35148                 case 73:
 35149                   popManyInto(stack, bc.argCount, args);
 35150                   object = stack.pop();
 35151                   savedScope.object.baseClass.instanceConstructorNoInitialize.apply(object, args);
 35152                   break;
 35153                 case 74:
 35154                   popManyInto(stack, bc.argCount, args);
 35155                   popNameInto(stack, multinames[bc.index], mn);
 35156                   object = boxValue(stack[stack.length - 1]);
 35157                   object = object.asConstructProperty(mn.namespaces, mn.name, mn.flags, args);
 35158                   stack[stack.length - 1] = object;
 35159                   break;
 35160                 case 75:
 35161                   Shumway.Debug.notImplemented('OP.callsuperid');
 35162                   break;
 35163                 case 76:
 35164                 case 70:
 35165                 case 79:
 35166                   popManyInto(stack, bc.argCount, args);
 35167                   popNameInto(stack, multinames[bc.index], mn);
 35168                   result = boxValue(stack.pop()).asCallProperty(mn.namespaces, mn.name, mn.flags, op === 76, args);
 35169                   if (op !== 79) {
 35170                     stack.push(result);
 35172                   break;
 35173                 case 69:
 35174                 case 78:
 35175                   popManyInto(stack, bc.argCount, args);
 35176                   popNameInto(stack, multinames[bc.index], mn);
 35177                   result = stack.pop().asCallSuper(savedScope, mn.namespaces, mn.name, mn.flags, args);
 35178                   if (op !== 78) {
 35179                     stack.push(result);
 35181                   break;
 35182                 case 83:
 35183                   popManyInto(stack, bc.argCount, args);
 35184                   stack[stack.length - 1] = applyType(domain, stack[stack.length - 1], args);
 35185                   break;
 35186                 case 85:
 35187                   object = {};
 35188                   for (var i = 0; i < bc.argCount; i++) {
 35189                     value = stack.pop();
 35190                     object[Multiname.getPublicQualifiedName(stack.pop())] = value;
 35192                   stack.push(object);
 35193                   break;
 35194                 case 86:
 35195                   object = [];
 35196                   popManyInto(stack, bc.argCount, args);
 35197                   object.push.apply(object, args);
 35198                   stack.push(object);
 35199                   break;
 35200                 case 87:
 35201                   true;
 35202                   stack.push(asCreateActivation(method));
 35203                   break;
 35204                 case 88:
 35205                   stack[stack.length - 1] = createClass(abc.classes[bc.index], stack[stack.length - 1], scopeStack.topScope());
 35206                   break;
 35207                 case 89:
 35208                   popNameInto(stack, multinames[bc.index], mn);
 35209                   stack.push(getDescendants(stack.pop(), mn));
 35210                   break;
 35211                 case 90:
 35212                   true;
 35213                   stack.push(exceptions[bc.index].scopeObject);
 35214                   break;
 35215                 case 94:
 35216                 case 93:
 35217                   popNameInto(stack, multinames[bc.index], mn);
 35218                   stack.push(scopeStack.topScope().findScopeProperty(mn.namespaces, mn.name, mn.flags, domain, op === 93, false));
 35219                   break;
 35220                 case 96:
 35221                   multiname = multinames[bc.index];
 35222                   object = scopeStack.topScope().findScopeProperty(multiname.namespaces, multiname.name, multiname.flags, domain, true, false);
 35223                   stack.push(object.asGetProperty(multiname.namespaces, multiname.name, multiname.flags));
 35224                   break;
 35225                 case 104:
 35226                 case 97:
 35227                   value = stack.pop();
 35228                   popNameInto(stack, multinames[bc.index], mn);
 35229                   boxValue(stack.pop()).asSetProperty(mn.namespaces, mn.name, mn.flags, value);
 35230                   break;
 35231                 case 98:
 35232                   stack.push(locals[bc.index]);
 35233                   break;
 35234                 case 99:
 35235                   locals[bc.index] = stack.pop();
 35236                   break;
 35237                 case 100:
 35238                   stack.push(savedScope.global.object);
 35239                   break;
 35240                 case 101:
 35241                   stack.push(scopeStack.get(bc.index));
 35242                   break;
 35243                 case 102:
 35244                   popNameInto(stack, multinames[bc.index], mn);
 35245                   stack[stack.length - 1] = boxValue(stack[stack.length - 1]).asGetProperty(mn.namespaces, mn.name, mn.flags);
 35246                   break;
 35247                 case 106:
 35248                   popNameInto(stack, multinames[bc.index], mn);
 35249                   stack[stack.length - 1] = boxValue(stack[stack.length - 1]).asDeleteProperty(mn.namespaces, mn.name, mn.flags);
 35250                   break;
 35251                 case 108:
 35252                   stack[stack.length - 1] = asGetSlot(stack[stack.length - 1], bc.index);
 35253                   break;
 35254                 case 109:
 35255                   value = stack.pop();
 35256                   object = stack.pop();
 35257                   asSetSlot(object, bc.index, value);
 35258                   break;
 35259                 case 112:
 35260                   stack[stack.length - 1] = stack[stack.length - 1] + '';
 35261                   break;
 35262                 case 131:
 35263                 case 115:
 35264                   stack[stack.length - 1] |= 0;
 35265                   break;
 35266                 case 136:
 35267                 case 116:
 35268                   stack[stack.length - 1] >>>= 0;
 35269                   break;
 35270                 case 132:
 35271                 case 117:
 35272                   stack[stack.length - 1] = +stack[stack.length - 1];
 35273                   break;
 35274                 case 129:
 35275                 case 118:
 35276                   stack[stack.length - 1] = !(!stack[stack.length - 1]);
 35277                   break;
 35278                 case 120:
 35279                   stack[stack.length - 1] = checkFilter(stack[stack.length - 1]);
 35280                   break;
 35281                 case 128:
 35282                   stack[stack.length - 1] = asCoerce(domain.getType(multinames[bc.index]), stack[stack.length - 1]);
 35283                   break;
 35284                 case 130:
 35285                   break;
 35286                 case 133:
 35287                   stack[stack.length - 1] = asCoerceString(stack[stack.length - 1]);
 35288                   break;
 35289                 case 135:
 35290                   stack[stack.length - 2] = asAsType(stack.pop(), stack[stack.length - 1]);
 35291                   break;
 35292                 case 137:
 35293                   object = stack[stack.length - 1];
 35294                   stack[stack.length - 1] = object == undefined ? null : object;
 35295                   break;
 35296                 case 144:
 35297                   stack[stack.length - 1] = -stack[stack.length - 1];
 35298                   break;
 35299                 case 145:
 35300                   ++stack[stack.length - 1];
 35301                   break;
 35302                 case 146:
 35303                   ++locals[bc.index];
 35304                   break;
 35305                 case 147:
 35306                   --stack[stack.length - 1];
 35307                   break;
 35308                 case 148:
 35309                   --locals[bc.index];
 35310                   break;
 35311                 case 149:
 35312                   stack[stack.length - 1] = asTypeOf(stack[stack.length - 1]);
 35313                   break;
 35314                 case 150:
 35315                   stack[stack.length - 1] = !stack[stack.length - 1];
 35316                   break;
 35317                 case 151:
 35318                   stack[stack.length - 1] = ~stack[stack.length - 1];
 35319                   break;
 35320                 case 160:
 35321                   stack[stack.length - 2] = asAdd(stack[stack.length - 2], stack.pop());
 35322                   break;
 35323                 case 161:
 35324                   stack[stack.length - 2] -= stack.pop();
 35325                   break;
 35326                 case 162:
 35327                   stack[stack.length - 2] *= stack.pop();
 35328                   break;
 35329                 case 163:
 35330                   stack[stack.length - 2] /= stack.pop();
 35331                   break;
 35332                 case 164:
 35333                   stack[stack.length - 2] %= stack.pop();
 35334                   break;
 35335                 case 165:
 35336                   stack[stack.length - 2] <<= stack.pop();
 35337                   break;
 35338                 case 166:
 35339                   stack[stack.length - 2] >>= stack.pop();
 35340                   break;
 35341                 case 167:
 35342                   stack[stack.length - 2] >>>= stack.pop();
 35343                   break;
 35344                 case 168:
 35345                   stack[stack.length - 2] &= stack.pop();
 35346                   break;
 35347                 case 169:
 35348                   stack[stack.length - 2] |= stack.pop();
 35349                   break;
 35350                 case 170:
 35351                   stack[stack.length - 2] ^= stack.pop();
 35352                   break;
 35353                 case 171:
 35354                   stack[stack.length - 2] = stack[stack.length - 2] == stack.pop();
 35355                   break;
 35356                 case 172:
 35357                   stack[stack.length - 2] = stack[stack.length - 2] === stack.pop();
 35358                   break;
 35359                 case 173:
 35360                   stack[stack.length - 2] = stack[stack.length - 2] < stack.pop();
 35361                   break;
 35362                 case 174:
 35363                   stack[stack.length - 2] = stack[stack.length - 2] <= stack.pop();
 35364                   break;
 35365                 case 175:
 35366                   stack[stack.length - 2] = stack[stack.length - 2] > stack.pop();
 35367                   break;
 35368                 case 176:
 35369                   stack[stack.length - 2] = stack[stack.length - 2] >= stack.pop();
 35370                   break;
 35371                 case 177:
 35372                   stack[stack.length - 2] = asIsInstanceOf(stack.pop(), stack[stack.length - 1]);
 35373                   break;
 35374                 case 178:
 35375                   stack[stack.length - 1] = asIsType(domain.getType(multinames[bc.index]), stack[stack.length - 1]);
 35376                   break;
 35377                 case 179:
 35378                   stack[stack.length - 2] = asIsType(stack.pop(), stack[stack.length - 1]);
 35379                   break;
 35380                 case 180:
 35381                   stack[stack.length - 2] = boxValue(stack.pop()).asHasProperty(null, stack[stack.length - 1]);
 35382                   break;
 35383                 case 192:
 35384                   stack[stack.length - 1] = (stack[stack.length - 1] | 0) + 1;
 35385                   break;
 35386                 case 193:
 35387                   stack[stack.length - 1] = (stack[stack.length - 1] | 0) - 1;
 35388                   break;
 35389                 case 194:
 35390                   locals[bc.index] = (locals[bc.index] | 0) + 1;
 35391                   break;
 35392                 case 195:
 35393                   locals[bc.index] = (locals[bc.index] | 0) - 1;
 35394                   break;
 35395                 case 196:
 35396                   stack[stack.length - 1] = ~stack[stack.length - 1];
 35397                   break;
 35398                 case 197:
 35399                   stack[stack.length - 2] = stack[stack.length - 2] + stack.pop() | 0;
 35400                   break;
 35401                 case 198:
 35402                   stack[stack.length - 2] = stack[stack.length - 2] - stack.pop() | 0;
 35403                   break;
 35404                 case 199:
 35405                   stack[stack.length - 2] = stack[stack.length - 2] * stack.pop() | 0;
 35406                   break;
 35407                 case 208:
 35408                 case 209:
 35409                 case 210:
 35410                 case 211:
 35411                   stack.push(locals[op - 208]);
 35412                   break;
 35413                 case 212:
 35414                 case 213:
 35415                 case 214:
 35416                 case 215:
 35417                   locals[op - 212] = stack.pop();
 35418                   break;
 35419                 case 239:
 35420                 case 240:
 35421                 case 241:
 35422                   break;
 35423                 default:
 35424                   Shumway.Debug.notImplemented(Shumway.AVM2.opcodeName(op));
 35426                 pc++;
 35427               } catch (e) {
 35428                 if (exceptions.length < 1) {
 35429                   throw e;
 35431                 e = translateError(domain, e);
 35432                 for (var i = 0, j = exceptions.length; i < j; i++) {
 35433                   var handler = exceptions[i];
 35434                   if (pc >= handler.start && pc <= handler.end && (!handler.typeName || domain.getType(handler.typeName).isInstance(e))) {
 35435                     stack.length = 0;
 35436                     stack.push(e);
 35437                     scopeStack.clear();
 35438                     pc = handler.offset;
 35439                     continue interpretLabel;
 35442                 throw e;
 35445         };
 35446         return Interpreter;
 35447       }();
 35448     AVM2.Interpreter = Interpreter;
 35449   }(Shumway.AVM2 || (Shumway.AVM2 = {})));
 35450   var AVM2 = Shumway.AVM2;
 35451 }(Shumway || (Shumway = {})));
 35452 Shumway.AVM2.Runtime.enableVerifier.value = true;
 35453 release = true;
 35454 var avm2Root = SHUMWAY_ROOT + 'avm2/';
 35455 var builtinPath = avm2Root + 'generated/builtin/builtin.abc';
 35456 var avm1Path = avm2Root + 'generated/avm1lib/avm1lib.abc';
 35457 var BinaryFileReader = function binaryFileReader() {
 35458     function constructor(url, responseType) {
 35459       this.url = url;
 35460       this.responseType = responseType || 'arraybuffer';
 35462     constructor.prototype = {
 35463       readAll: function (progress, complete) {
 35464         var url = this.url;
 35465         var xhr = new XMLHttpRequest();
 35466         var async = true;
 35467         xhr.open('GET', this.url, async);
 35468         xhr.responseType = this.responseType;
 35469         if (progress) {
 35470           xhr.onprogress = function (event) {
 35471             progress(xhr.response, event.loaded, event.total);
 35472           };
 35474         xhr.onreadystatechange = function (event) {
 35475           if (xhr.readyState === 4) {
 35476             if (xhr.status !== 200 && xhr.status !== 0) {
 35477               unexpected('Path: ' + url + ' not found.');
 35478               complete(null, xhr.statusText);
 35479               return;
 35481             complete(xhr.response);
 35483         };
 35484         xhr.send(null);
 35485       },
 35486       readAsync: function (ondata, onerror, onopen, oncomplete, onhttpstatus) {
 35487         var xhr = new XMLHttpRequest({
 35488             mozSystem: true
 35489           });
 35490         var url = this.url;
 35491         xhr.open(this.method || 'GET', url, true);
 35492         var isNotProgressive;
 35493         try {
 35494           xhr.responseType = 'moz-chunked-arraybuffer';
 35495           isNotProgressive = xhr.responseType !== 'moz-chunked-arraybuffer';
 35496         } catch (e) {
 35497           isNotProgressive = true;
 35499         if (isNotProgressive) {
 35500           xhr.responseType = 'arraybuffer';
 35502         xhr.onprogress = function (e) {
 35503           if (isNotProgressive)
 35504             return;
 35505           ondata(new Uint8Array(xhr.response), {
 35506             loaded: e.loaded,
 35507             total: e.total
 35508           });
 35509         };
 35510         xhr.onreadystatechange = function (event) {
 35511           if (xhr.readyState === 2 && onhttpstatus) {
 35512             onhttpstatus(url, xhr.status, xhr.getAllResponseHeaders());
 35514           if (xhr.readyState === 4) {
 35515             if (xhr.status !== 200 && xhr.status !== 0) {
 35516               onerror(xhr.statusText);
 35518             if (isNotProgressive) {
 35519               var buffer = xhr.response;
 35520               ondata(new Uint8Array(buffer), {
 35521                 loaded: buffer.byteLength,
 35522                 total: buffer.byteLength
 35523               });
 35525             if (oncomplete) {
 35526               oncomplete();
 35528           } else if (xhr.readyState === 2 && onopen) {
 35529             onopen();
 35531         };
 35532         xhr.send(null);
 35534     };
 35535     return constructor;
 35536   }();
 35537 var libraryAbcs;
 35538 function grabAbc(abcName) {
 35539   var entry = libraryScripts[abcName];
 35540   if (entry) {
 35541     var offset = entry.offset;
 35542     var length = entry.length;
 35543     return new AbcFile(new Uint8Array(libraryAbcs, offset, length), abcName);
 35545   return null;
 35547 var avm2;
 35548 function createAVM2(builtinPath, libraryPath, avm1Path, sysMode, appMode, next) {
 35549   avm2 = new AVM2(sysMode, appMode, loadAVM1);
 35550   var builtinAbc, avm1Abc;
 35551   AVM2.loadPlayerglobal(libraryPath.abcs, libraryPath.catalog).then(function () {
 35552     new BinaryFileReader(builtinPath).readAll(null, function (buffer) {
 35553       builtinAbc = new AbcFile(new Uint8Array(buffer), 'builtin.abc');
 35554       executeAbc();
 35555     });
 35556   });
 35557   function loadAVM1(next) {
 35558     new BinaryFileReader(avm1Path).readAll(null, function (buffer) {
 35559       avm1Abc = new AbcFile(new Uint8Array(buffer), 'avm1.abc');
 35561       avm2.systemDomain.executeAbc(avm1Abc);
 35562       next();
 35563     });
 35565   function executeAbc() {
 35566     avm2.builtinsLoaded = false;
 35567     avm2.systemDomain.onMessage.register('classCreated', Stubs.onClassCreated);
 35568     avm2.systemDomain.executeAbc(builtinAbc);
 35569     avm2.builtinsLoaded = true;
 35570     console.info(JSON.stringify(Counter.toJSON()));
 35571     console.timeEnd('Load AVM2');
 35572     next(avm2);
 35576   var MAX_SNAP_DRAW_SCALE_TO_CACHE = 8;
 35577   var CACHE_SNAP_DRAW_AFTER = 3;
 35578   var BitmapDefinition = function () {
 35579       function setBitmapData(value) {
 35580         if (this._bitmapData) {
 35581           this._bitmapData._changeNotificationTarget = null;
 35583         this._bitmapData = value;
 35584         if (this._bitmapData) {
 35585           this._bitmapData._changeNotificationTarget = this;
 35587         if (value) {
 35588           var canvas = value._drawable;
 35589           this._bbox = {
 35590             xMin: 0,
 35591             yMin: 0,
 35592             xMax: canvas.width * 20,
 35593             yMax: canvas.height * 20
 35594           };
 35595         } else {
 35596           this._bbox = {
 35597             xMin: 0,
 35598             yMin: 0,
 35599             xMax: 0,
 35600             yMax: 0
 35601           };
 35603         this._drawableChanged();
 35604         this._invalidateBounds();
 35605         this._invalidateTransform();
 35607       return {
 35608         __class__: 'flash.display.Bitmap',
 35609         draw: function (ctx, ratio, colorTransform) {
 35610           if (!this._bitmapData) {
 35611             return;
 35613           var scaledImage;
 35614           ctx.save();
 35615           if (this._pixelSnapping === 'auto' || this._pixelSnapping === 'always') {
 35616             var transform = this._getConcatenatedTransform(null, true);
 35617             var EPSILON = 0.001;
 35618             var aInt = Math.abs(Math.round(transform.a));
 35619             var dInt = Math.abs(Math.round(transform.d));
 35620             var snapPixels;
 35621             if (aInt >= 1 && aInt <= MAX_SNAP_DRAW_SCALE_TO_CACHE && dInt >= 1 && dInt <= MAX_SNAP_DRAW_SCALE_TO_CACHE && Math.abs(Math.abs(transform.a) / aInt - 1) <= EPSILON && Math.abs(Math.abs(transform.d) / dInt - 1) <= EPSILON && Math.abs(transform.b) <= EPSILON && Math.abs(transform.c) <= EPSILON) {
 35622               if (aInt === 1 && dInt === 1) {
 35623                 snapPixels = true;
 35624               } else {
 35625                 var sizeKey = aInt + 'x' + dInt;
 35626                 if (this._snapImageCache.size !== sizeKey) {
 35627                   this._snapImageCache.size = sizeKey;
 35628                   this._snapImageCache.hits = 0;
 35629                   this._snapImageCache.image = null;
 35631                 if (++this._snapImageCache.hits === CACHE_SNAP_DRAW_AFTER) {
 35632                   this._cacheSnapImage(sizeKey, aInt, dInt);
 35634                 scaledImage = this._snapImageCache.image;
 35635                 snapPixels = !(!scaledImage);
 35637             } else {
 35638               snapPixels = false;
 35640             if (snapPixels) {
 35641               ctx.setTransform(transform.a < 0 ? -1 : 1, 0, 0, transform.d < 0 ? -1 : 1, transform.tx / 20 | 0, transform.ty / 20 | 0);
 35644           colorTransform.setAlpha(ctx, true);
 35645           ctx.imageSmoothingEnabled = ctx.mozImageSmoothingEnabled = this._smoothing;
 35646           ctx.drawImage(scaledImage || this._bitmapData._getDrawable(), 0, 0);
 35647           ctx.imageSmoothingEnabled = ctx.mozImageSmoothingEnabled = false;
 35648           ctx.restore();
 35649           traceRenderer.value && frameWriter.writeLn('Bitmap.draw() snapping: ' + this._pixelSnapping + ', dimensions: ' + this._bitmapData._drawable.width + ' x ' + this._bitmapData._drawable.height);
 35650         },
 35651         _drawableChanged: function () {
 35652           this._invalidate();
 35653           this._snapImageCache.image = null;
 35654           this._snapImageCache.hints = 0;
 35655         },
 35656         _cacheSnapImage: function (sizeKey, xScale, yScale) {
 35657           Counter.count('Cache scaled image');
 35658           var original = this._bitmapData._getDrawable();
 35659           var canvas = document.createElement('canvas');
 35660           canvas.width = xScale * original.width;
 35661           canvas.height = yScale * original.height;
 35662           var ctx = canvas.getContext('2d');
 35663           ctx.imageSmoothingEnabled = ctx.mozImageSmoothingEnabled = this._smoothing;
 35664           ctx.drawImage(original, 0, 0, original.width, original.height, 0, 0, canvas.width, canvas.height);
 35665           var cache = this._snapImageCache;
 35666           var image = document.createElement('img');
 35667           cache._tmp = [
 35668             canvas,
 35669             image
 35670           ];
 35671           if ('toBlob' in canvas) {
 35672             canvas.toBlob(function (blob) {
 35673               if (cache.size !== sizeKey) {
 35674                 return;
 35676               image.onload = function () {
 35677                 URL.revokeObjectURL(blob);
 35678                 if (cache.size === sizeKey) {
 35679                   cache.image = image;
 35681               };
 35682               image.src = URL.createObjectURL(blob);
 35683             });
 35684           } else {
 35685             image.onload = function () {
 35686               if (cache.size === sizeKey) {
 35687                 cache.image = image;
 35689             };
 35690             image.src = canvas.toDataURL();
 35692         },
 35693         initialize: function () {
 35694         },
 35695         __glue__: {
 35696           native: {
 35697             static: {},
 35698             instance: {
 35699               ctor: function (bitmapData, pixelSnapping, smoothing) {
 35700                 if (pixelSnapping === 'never' || pixelSnapping === 'always') {
 35701                   this._pixelSnapping = pixelSnapping;
 35702                 } else {
 35703                   this._pixelSnapping = 'auto';
 35705                 this._smoothing = !(!smoothing);
 35706                 this._snapImageCache = {
 35707                   hits: 0,
 35708                   size: '',
 35709                   image: null
 35710                 };
 35711                 if (!bitmapData && this.symbol) {
 35712                   var symbol = this.symbol;
 35713                   bitmapData = new flash.display.BitmapData(symbol.width, symbol.height, true, 0);
 35714                   bitmapData._ctx.imageSmoothingEnabled = this._smoothing;
 35715                   bitmapData._ctx.mozImageSmoothingEnabled = this._smoothing;
 35716                   bitmapData._ctx.drawImage(symbol.img, 0, 0);
 35717                   bitmapData._ctx.imageSmoothingEnabled = false;
 35718                   bitmapData._ctx.mozImageSmoothingEnabled = false;
 35720                 setBitmapData.call(this, bitmapData || null);
 35721               },
 35722               pixelSnapping: {
 35723                 get: function pixelSnapping() {
 35724                   return this._pixelSnapping;
 35725                 },
 35726                 set: function pixelSnapping(value) {
 35727                   this._pixelSnapping = value;
 35729               },
 35730               smoothing: {
 35731                 get: function smoothing() {
 35732                   return this._smoothing;
 35733                 },
 35734                 set: function smoothing(value) {
 35735                   this._smoothing = value;
 35737               },
 35738               bitmapData: {
 35739                 get: function bitmapData() {
 35740                   return this._bitmapData;
 35741                 },
 35742                 set: setBitmapData
 35747       };
 35748     }.call(this);
 35750 var CACHE_DRAWABLE_AFTER = 10;
 35751 var BitmapDataDefinition = function () {
 35752     function replaceRect(ctx, x, y, w, h, alpha) {
 35753       if (alpha < 255) {
 35754         ctx.clearRect(x, y, w, h);
 35756       if (alpha > 0) {
 35757         ctx.fillRect(x, y, w, h);
 35760     var def = {
 35761         __class__: 'flash.display.BitmapData',
 35762         initialize: function () {
 35763           this._changeNotificationTarget = null;
 35764           this._locked = false;
 35765           this._requested = 0;
 35766           this._cache = null;
 35767           if (this.symbol) {
 35768             this._img = this.symbol.img;
 35769             this._skipCopyToCanvas = this.symbol.skipCopyToCanvas;
 35771         },
 35772         _checkCanvas: function () {
 35773           if (this._drawable === null)
 35774             throw ArgumentError();
 35775         },
 35776         ctor: function (width, height, transparent, backgroundColor) {
 35777           if (this._img) {
 35778             width = this._img.naturalWidth || this._img.width;
 35779             height = this._img.naturalHeight || this._img.height;
 35780           } else if (isNaN(width + height) || width <= 0 || height <= 0) {
 35781             throwError('ArgumentError', Errors.ArgumentError);
 35783           this._transparent = transparent === undefined ? true : !(!transparent);
 35784           this._backgroundColor = backgroundColor === undefined ? 4294967295 : backgroundColor;
 35785           if (!this._transparent) {
 35786             this._backgroundColor |= 4278190080;
 35788           if (this._skipCopyToCanvas) {
 35789             this._drawable = this._img;
 35790           } else {
 35791             var canvas = document.createElement('canvas');
 35792             this._ctx = canvas.getContext('2d');
 35793             canvas.width = width | 0;
 35794             canvas.height = height | 0;
 35795             this._drawable = canvas;
 35796             if (!this._transparent || !this._img && this._backgroundColor) {
 35797               this.fillRect(new flash.geom.Rectangle(0, 0, width | 0, height | 0), this._backgroundColor);
 35799             if (this._img) {
 35800               this._ctx.drawImage(this._img, 0, 0);
 35803         },
 35804         dispose: function () {
 35805           this._ctx = null;
 35806           this._drawable.width = 0;
 35807           this._drawable.height = 0;
 35808           this._drawable = null;
 35809         },
 35810         draw: function (source, matrix, colorTransform, blendMode, clipRect, smoothing) {
 35811           this._checkCanvas();
 35812           var ctx = this._ctx;
 35813           ctx.save();
 35814           ctx.beginPath();
 35815           if (clipRect && clipRect.width > 0 && clipRect.height > 0) {
 35816             ctx.rect(clipRect.x, clipRect.y, clipRect.width, clipRect.height);
 35817             ctx.clip();
 35819           if (matrix) {
 35820             ctx.transform(matrix.a, matrix.b, matrix.c, matrix.d, matrix.tx, matrix.ty);
 35822           ctx.globalCompositeOperation = getBlendModeName(blendMode);
 35823           ctx.imageSmoothingEnabled = ctx.mozImageSmoothingEnabled = !(!smoothing);
 35824           if (flash.display.BitmapData.class.isInstanceOf(source)) {
 35825             ctx.drawImage(source._drawable, 0, 0);
 35826           } else {
 35827             new RenderVisitor(source, ctx, null, true).startFragment(matrix);
 35829           ctx.imageSmoothingEnabled = ctx.mozImageSmoothingEnabled = false;
 35830           ctx.restore();
 35831           this._invalidate();
 35832         },
 35833         fillRect: function (rect, color) {
 35834           this._checkCanvas();
 35835           if (!this._transparent) {
 35836             color |= 4278190080;
 35838           var ctx = this._ctx;
 35839           ctx.fillStyle = argbUintToStr(color);
 35840           replaceRect(ctx, rect.x, rect.y, rect.width, rect.height, color >>> 24 & 255);
 35841           this._invalidate();
 35842         },
 35843         getPixel: function (x, y) {
 35844           this._checkCanvas();
 35845           var data = this._ctx.getImageData(x, y, 1, 1).data;
 35846           return dataToRGB(data);
 35847         },
 35848         getPixel32: function (x, y) {
 35849           this._checkCanvas();
 35850           var data = this._ctx.getImageData(x, y, 1, 1).data;
 35851           return dataToARGB(data);
 35852         },
 35853         _invalidate: function (changeRect) {
 35854           if (changeRect) {
 35855             somewhatImplemented('BitmapData._invalidate(changeRect)');
 35857           if (this._locked) {
 35858             return;
 35860           if (this._changeNotificationTarget) {
 35861             this._changeNotificationTarget._drawableChanged();
 35863           this._requested = 0;
 35864           this._cache = null;
 35865         },
 35866         _getDrawable: function () {
 35867           if (this._img === this._drawable) {
 35868             return this._drawable;
 35870           this._requested++;
 35871           if (this._requested >= CACHE_DRAWABLE_AFTER) {
 35872             if (!this._cache) {
 35873               Counter.count('Cache drawable');
 35874               var img = document.createElement('img');
 35875               if ('toBlob' in this._drawable) {
 35876                 this._drawable.toBlob(function (blob) {
 35877                   img.src = URL.createObjectURL(blob);
 35878                   img.onload = function () {
 35879                     URL.revokeObjectURL(blob);
 35880                   };
 35881                 });
 35882               } else {
 35883                 img.src = this._drawable.toDataURL();
 35885               this._cache = img;
 35887             if (this._cache.width > 0) {
 35888               return this._cache;
 35891           return this._drawable;
 35892         },
 35893         setPixel: function (x, y, color) {
 35894           this.fillRect({
 35895             x: x,
 35896             y: y,
 35897             width: 1,
 35898             height: 1
 35899           }, color | 4278190080);
 35900           this._invalidate();
 35901         },
 35902         setPixel32: function (x, y, color) {
 35903           this.fillRect({
 35904             x: x,
 35905             y: y,
 35906             width: 1,
 35907             height: 1
 35908           }, color);
 35909           this._invalidate();
 35910         },
 35911         copyPixels: function copyPixels(sourceBitmapData, sourceRect, destPoint, alphaBitmapData, alphaPoint, mergeAlpha) {
 35912           if (alphaBitmapData) {
 35913             notImplemented('BitmapData.copyPixels w/ alpha');
 35915           var w = sourceRect.width;
 35916           var h = sourceRect.height;
 35917           var sx = sourceRect.x;
 35918           var sy = sourceRect.y;
 35919           var dx = destPoint.x;
 35920           var dy = destPoint.y;
 35921           var offsetx = -Math.min(0, sx, dx);
 35922           var offsety = -Math.min(0, sy, dy);
 35923           var correctionw = Math.min(0, this._ctx.canvas.width - dx - w, sourceBitmapData._drawable.width - sx - w) - offsetx;
 35924           var correctionh = Math.min(0, this._ctx.canvas.height - dy - h, sourceBitmapData._drawable.height - sy - h) - offsety;
 35925           if (!mergeAlpha) {
 35926             this._ctx.clearRect(dx, dy, w, h);
 35928           if (w + correctionw > 0 && h + correctionh > 0) {
 35929             this._ctx.drawImage(sourceBitmapData._drawable, sx + offsetx, sy + offsety, w + correctionw, h + correctionh, dx + offsetx, dy + offsety, w + correctionw, h + correctionh);
 35931           this._invalidate();
 35932         },
 35933         lock: function lock() {
 35934           this._locked = true;
 35935         },
 35936         unlock: function unlock(changeRect) {
 35937           this._locked = false;
 35938           this._invalidate(changeRect);
 35939         },
 35940         clone: function () {
 35941           this._checkCanvas();
 35942           var bd = new flash.display.BitmapData(this._drawable.width, this._drawable.height, true, 0);
 35943           bd._ctx.drawImage(this._drawable, 0, 0);
 35944           return bd;
 35945         },
 35946         scroll: function (x, y) {
 35947           this._checkCanvas();
 35948           this._ctx.draw(this._drawable, x, y);
 35949           this._ctx.save();
 35950           var color = this._img ? 0 : this._backgroundColor;
 35951           if (!this._transparent) {
 35952             color |= 4278190080;
 35954           var alpha = color >>> 24 & 255;
 35955           this._ctx.fillStyle = argbUintToStr(color);
 35956           var w = this._drawable.width;
 35957           var h = this._drawable.height;
 35958           if (x > 0) {
 35959             replaceRect(this._ctx, 0, 0, x, h, alpha);
 35960           } else if (x < 0) {
 35961             replaceRect(this._ctx, w + x, 0, -x, h, alpha);
 35963           if (y > 0) {
 35964             replaceRect(this._ctx, 0, 0, w, y, alpha);
 35965           } else if (y < 0) {
 35966             replaceRect(this._ctx, h + y, w, -y, alpha);
 35968           this._ctx.restore();
 35969           this._invalidate();
 35970         },
 35971         get width() {
 35972           return this._drawable.width;
 35973         },
 35974         get height() {
 35975           return this._drawable.height;
 35977       };
 35978     var desc = Object.getOwnPropertyDescriptor;
 35979     def.__glue__ = {
 35980       native: {
 35981         instance: {
 35982           ctor: def.ctor,
 35983           fillRect: def.fillRect,
 35984           dispose: def.dispose,
 35985           getPixel: def.getPixel,
 35986           getPixel32: def.getPixel32,
 35987           setPixel: def.setPixel,
 35988           setPixel32: def.setPixel32,
 35989           copyPixels: def.copyPixels,
 35990           lock: def.lock,
 35991           unlock: def.unlock,
 35992           draw: def.draw,
 35993           clone: def.clone,
 35994           scroll: def.scroll,
 35995           width: desc(def, 'width'),
 35996           height: desc(def, 'height')
 35999     };
 36000     return def;
 36001   }.call(this);
 36002 function dataToRGB(data) {
 36003   return data[0] << 16 | data[1] << 8 | data[2];
 36005 function dataToARGB(data) {
 36006   return data[3] << 24 | dataToRGB(data);
 36008 var DisplayObjectDefinition = function () {
 36009     var blendModes;
 36010     var nextInstanceId = 1;
 36011     function generateName() {
 36012       return 'instance' + nextInstanceId++;
 36014     var broadcastedEvents = {
 36015         advanceFrame: false,
 36016         enterFrame: true,
 36017         constructChildren: false,
 36018         frameConstructed: true,
 36019         executeFrame: false,
 36020         exitFrame: true,
 36021         render: true
 36022       };
 36023     var point = {
 36024         x: 0,
 36025         y: 0
 36026       };
 36027     var def = {
 36028         __class__: 'flash.display.DisplayObject',
 36029         initialize: function () {
 36030           var blendModeClass = flash.display.BlendMode.class;
 36031           this._alpha = 1;
 36032           this._animated = false;
 36033           this._bbox = null;
 36034           this._bitmap = null;
 36035           this._blendMode = blendModeClass.NORMAL;
 36036           this._bounds = {
 36037             xMin: 0,
 36038             xMax: 0,
 36039             yMin: 0,
 36040             yMax: 0,
 36041             invalid: true
 36042           };
 36043           this._cacheAsBitmap = false;
 36044           this._children = [];
 36045           this._clipDepth = null;
 36046           this._currentTransform = {
 36047             a: 1,
 36048             b: 0,
 36049             c: 0,
 36050             d: 1,
 36051             tx: 0,
 36052             ty: 0
 36053           };
 36054           this._concatenatedTransform = {
 36055             a: 1,
 36056             b: 0,
 36057             c: 0,
 36058             d: 1,
 36059             tx: 0,
 36060             ty: 0,
 36061             invalid: true
 36062           };
 36063           this._current3DTransform = null;
 36064           this._cxform = null;
 36065           this._graphics = null;
 36066           this._filters = [];
 36067           this._loader = null;
 36068           this._mouseChildren = true;
 36069           this._mouseOver = false;
 36070           this._mouseX = 0;
 36071           this._mouseY = 0;
 36072           this._name = null;
 36073           this._opaqueBackground = null;
 36074           this._owned = false;
 36075           this._parent = null;
 36076           this._rotation = 0;
 36077           this._rotationCos = 1;
 36078           this._rotationSin = 0;
 36079           this._scale9Grid = null;
 36080           this._scaleX = 1;
 36081           this._scaleY = 1;
 36082           this._stage = null;
 36083           this._visible = true;
 36084           this._hidden = false;
 36085           this._wasCachedAsBitmap = false;
 36086           this._destroyed = false;
 36087           this._maskedObject = null;
 36088           this._scrollRect = null;
 36089           this._invalid = false;
 36090           this._region = null;
 36091           this._level = -1;
 36092           this._index = -1;
 36093           this._depth = -1;
 36094           this._isContainer = false;
 36095           this._invisible = false;
 36096           this._zindex = 0;
 36097           blendModes = [
 36098             blendModeClass.NORMAL,
 36099             blendModeClass.NORMAL,
 36100             blendModeClass.LAYER,
 36101             blendModeClass.MULTIPLY,
 36102             blendModeClass.SCREEN,
 36103             blendModeClass.LIGHTEN,
 36104             blendModeClass.DARKEN,
 36105             blendModeClass.DIFFERENCE,
 36106             blendModeClass.ADD,
 36107             blendModeClass.SUBTRACT,
 36108             blendModeClass.INVERT,
 36109             blendModeClass.ALPHA,
 36110             blendModeClass.ERASE,
 36111             blendModeClass.OVERLAY,
 36112             blendModeClass.HARDLIGHT,
 36113             blendModeClass.SHADER
 36114           ];
 36115           var s = this.symbol;
 36116           if (s) {
 36117             this._animated = s.animated || false;
 36118             this._bbox = s.bbox || null;
 36119             this._blendMode = this._resolveBlendMode(s.blendMode);
 36120             this._children = s.children || [];
 36121             this._clipDepth = s.clipDepth || null;
 36122             this._cxform = s.cxform || null;
 36123             this._loader = s.loader || null;
 36124             this._name = s.name || null;
 36125             this._owned = s.owned || false;
 36126             this._parent = s.parent || null;
 36127             this._level = isNaN(s.level) ? -1 : s.level;
 36128             this._index = isNaN(s.index) ? -1 : s.index;
 36129             this._depth = isNaN(s.depth) ? -1 : s.depth;
 36130             this._root = s.root || null;
 36131             this._stage = s.stage || null;
 36132             var scale9Grid = s.scale9Grid;
 36133             if (scale9Grid) {
 36134               this._scale9Grid = new flash.geom.Rectangle(scale9Grid.left, scale9Grid.top, scale9Grid.right - scale9Grid.left, scale9Grid.bottom - scale9Grid.top);
 36136             var matrix = s.currentTransform;
 36137             if (matrix) {
 36138               this._setTransformMatrix(matrix, false);
 36141           this._accessibilityProperties = null;
 36142           var self = this;
 36143           this._onBroadcastMessage = function (type) {
 36144             var listeners = self._listeners;
 36145             if (listeners[type]) {
 36146               self._dispatchEvent(type);
 36148           };
 36149         },
 36150         _addEventListener: function addEventListener(type, listener, useCapture, priority) {
 36151           if (broadcastedEvents[type] === false) {
 36152             avm2.systemDomain.onMessage.register(type, listener);
 36153             return;
 36155           if (type in broadcastedEvents && !this._listeners[type]) {
 36156             avm2.systemDomain.onMessage.register(type, this._onBroadcastMessage);
 36158           this._addEventListenerImpl(type, listener, useCapture, priority);
 36159         },
 36160         _removeEventListener: function addEventListener(type, listener, useCapture) {
 36161           if (broadcastedEvents[type] === false) {
 36162             avm2.systemDomain.onMessage.unregister(type, listener);
 36163             return;
 36165           this._removeEventListenerImpl(type, listener, useCapture);
 36166           if (type in broadcastedEvents && !this._listeners[type]) {
 36167             avm2.systemDomain.onMessage.unregister(type, this._onBroadcastMessage);
 36169         },
 36170         _resolveBlendMode: function (blendModeNumeric) {
 36171           return blendModes[blendModeNumeric] || flash.display.BlendMode.class.NORMAL;
 36172         },
 36173         _getConcatenatedTransform: function (targetCoordSpace, toDeviceSpace) {
 36174           var stage = this._stage;
 36175           if (this === this._stage) {
 36176             return toDeviceSpace ? this._concatenatedTransform : this._currentTransform;
 36178           if (targetCoordSpace === this._parent) {
 36179             return this._currentTransform;
 36181           var invalidNode = null;
 36182           var m, m2, targetCoordMatrix;
 36183           var currentNode = this;
 36184           while (currentNode !== stage) {
 36185             if (currentNode._concatenatedTransform.invalid) {
 36186               invalidNode = currentNode;
 36188             if (currentNode === targetCoordSpace) {
 36189               targetCoordMatrix = currentNode._concatenatedTransform;
 36191             currentNode = currentNode._parent;
 36193           if (invalidNode) {
 36194             if (this._parent === stage) {
 36195               m = this._concatenatedTransform;
 36196               m2 = this._currentTransform;
 36197               m.a = m2.a;
 36198               m.b = m2.b;
 36199               m.c = m2.c;
 36200               m.d = m2.d;
 36201               m.tx = m2.tx;
 36202               m.ty = m2.ty;
 36203             } else {
 36204               var stack = [];
 36205               var currentNode = this;
 36206               while (currentNode !== invalidNode) {
 36207                 stack.push(currentNode);
 36208                 currentNode = currentNode._parent;
 36210               var node = invalidNode;
 36211               do {
 36212                 var parent = node._parent;
 36213                 m = node._concatenatedTransform;
 36214                 m2 = node._currentTransform;
 36215                 if (parent) {
 36216                   if (parent !== stage) {
 36217                     var m3 = parent._concatenatedTransform;
 36218                     m.a = m2.a * m3.a + m2.b * m3.c;
 36219                     m.b = m2.a * m3.b + m2.b * m3.d;
 36220                     m.c = m2.c * m3.a + m2.d * m3.c;
 36221                     m.d = m2.d * m3.d + m2.c * m3.b;
 36222                     m.tx = m2.tx * m3.a + m3.tx + m2.ty * m3.c;
 36223                     m.ty = m2.ty * m3.d + m3.ty + m2.tx * m3.b;
 36225                 } else {
 36226                   m.a = m2.a;
 36227                   m.b = m2.b;
 36228                   m.c = m2.c;
 36229                   m.d = m2.d;
 36230                   m.tx = m2.tx;
 36231                   m.ty = m2.ty;
 36233                 m.invalid = false;
 36234                 var nextNode = stack.pop();
 36235                 var children = node._children;
 36236                 for (var i = 0; i < children.length; i++) {
 36237                   var child = children[i];
 36238                   if (child !== nextNode) {
 36239                     child._concatenatedTransform.invalid = true;
 36242                 node = nextNode;
 36243               } while (node);
 36245           } else {
 36246             m = this._concatenatedTransform;
 36248           if (targetCoordSpace && targetCoordSpace !== this._stage) {
 36249             m2 = targetCoordMatrix || targetCoordSpace._getConcatenatedTransform(null, false);
 36250             var a = 1, b = 0, c = 0, d = 1, tx = 0, ty = 0;
 36251             if (m2.b || m2.c) {
 36252               var det = 1 / (m2.a * m2.d - m2.b * m2.c);
 36253               a = m2.d * det;
 36254               b = -m2.b * det;
 36255               c = -m2.c * det;
 36256               d = m2.a * det;
 36257               tx = -(a * m2.tx + c * m2.ty);
 36258               ty = -(b * m2.tx + d * m2.ty);
 36259             } else {
 36260               a = 1 / m2.a;
 36261               d = 1 / m2.d;
 36262               tx = m2.tx * -a;
 36263               ty = m2.ty * -d;
 36265             return {
 36266               a: a * m.a + c * m.b,
 36267               b: b * m.a + d * m.b,
 36268               c: a * m.c + c * m.d,
 36269               d: b * m.c + d * m.d,
 36270               tx: a * m.tx + c * m.ty + tx,
 36271               ty: b * m.tx + d * m.ty + ty
 36272             };
 36274           if (toDeviceSpace && stage) {
 36275             m2 = stage._concatenatedTransform;
 36276             return {
 36277               a: m.a * m2.a,
 36278               b: m.b * m2.d,
 36279               c: m.c * m2.a,
 36280               d: m.d * m2.d,
 36281               tx: m.tx * m2.a + m2.tx,
 36282               ty: m.ty * m2.d + m2.ty
 36283             };
 36285           return m;
 36286         },
 36287         _applyCurrentTransform: function (pt) {
 36288           var m = this._getConcatenatedTransform(null, false);
 36289           var x = pt.x;
 36290           var y = pt.y;
 36291           pt.x = m.a * x + m.c * y + m.tx | 0;
 36292           pt.y = m.d * y + m.b * x + m.ty | 0;
 36293         },
 36294         _applyConcatenatedInverseTransform: function (pt) {
 36295           var m = this._getConcatenatedTransform(null, false);
 36296           var det = 1 / (m.a * m.d - m.b * m.c);
 36297           var x = pt.x - m.tx;
 36298           var y = pt.y - m.ty;
 36299           pt.x = (m.d * x - m.c * y) * det | 0;
 36300           pt.y = (m.a * y - m.b * x) * det | 0;
 36301         },
 36302         _hitTest: function (use_xy, x, y, useShape, hitTestObject) {
 36303           if (use_xy) {
 36304             point.x = x;
 36305             point.y = y;
 36306             this._applyConcatenatedInverseTransform(point);
 36307             var b = this._getContentBounds();
 36308             if (!(point.x >= b.xMin && point.x < b.xMax && point.y >= b.yMin && point.y < b.yMax)) {
 36309               return false;
 36311             if (!useShape || !this._graphics) {
 36312               return true;
 36314             if (this._graphics) {
 36315               var subpaths = this._graphics._paths;
 36316               for (var i = 0, n = subpaths.length; i < n; i++) {
 36317                 var path = subpaths[i];
 36318                 if (path.isPointInPath(point.x, point.y)) {
 36319                   return true;
 36321                 if (path.strokeStyle) {
 36322                   var strokePath = path._strokePath;
 36323                   if (!strokePath) {
 36324                     strokePath = path.strokePath(path.drawingStyles);
 36325                     path._strokePath = strokePath;
 36327                   if (strokePath.isPointInPath(point.x, point.y)) {
 36328                     return true;
 36333             var children = this._children;
 36334             for (var i = 0, n = children.length; i < n; i++) {
 36335               var child = children[i];
 36336               if (child._hitTest && child._hitTest(true, x, y, true, null)) {
 36337                 return true;
 36340             return false;
 36342           var b1 = this.getBounds(this._stage);
 36343           var b2 = hitTestObject.getBounds(hitTestObject._stage);
 36344           x = Math.max(b1.xMin, b2.xMin);
 36345           y = Math.max(b1.yMin, b2.yMin);
 36346           var width = Math.min(b1.xMax, b2.xMax) - x;
 36347           var height = Math.min(b1.yMax, b2.yMax) - y;
 36348           return width > 0 && height > 0;
 36349         },
 36350         _invalidate: function () {
 36351           this._invalid = true;
 36352         },
 36353         _invalidateBounds: function () {
 36354           var currentNode = this;
 36355           while (currentNode && !currentNode._bounds.invalid) {
 36356             currentNode._bounds.invalid = true;
 36357             currentNode = currentNode._parent;
 36359         },
 36360         _invalidateTransform: function () {
 36361           this._concatenatedTransform.invalid = true;
 36362           if (this._parent) {
 36363             this._parent._invalidateBounds();
 36365         },
 36366         _setTransformMatrix: function (matrix, convertToTwips) {
 36367           var a = matrix.a;
 36368           var b = matrix.b;
 36369           var c = matrix.c;
 36370           var d = matrix.d;
 36371           var tx, ty;
 36372           if (convertToTwips) {
 36373             tx = matrix.tx * 20 | 0;
 36374             ty = matrix.ty * 20 | 0;
 36375           } else {
 36376             tx = matrix.tx;
 36377             ty = matrix.ty;
 36379           var angle = a !== 0 ? Math.atan(b / a) : b > 0 ? Math.PI / 2 : -Math.PI / 2;
 36380           this._rotation = angle * 180 / Math.PI;
 36381           this._rotationCos = Math.cos(angle);
 36382           this._rotationSin = Math.sin(angle);
 36383           var sx = Math.sqrt(a * a + b * b);
 36384           this._scaleX = a > 0 ? sx : -sx;
 36385           var sy = Math.sqrt(d * d + c * c);
 36386           this._scaleY = d > 0 ? sy : -sy;
 36387           var transform = this._currentTransform;
 36388           transform.a = a;
 36389           transform.b = b;
 36390           transform.c = c;
 36391           transform.d = d;
 36392           transform.tx = tx;
 36393           transform.ty = ty;
 36394           this._invalidateTransform();
 36395         },
 36396         get accessibilityProperties() {
 36397           return this._accessibilityProperties;
 36398         },
 36399         set accessibilityProperties(val) {
 36400           this._accessibilityProperties = val;
 36401         },
 36402         get alpha() {
 36403           return this._alpha;
 36404         },
 36405         set alpha(val) {
 36406           if (val === this._alpha) {
 36407             return;
 36409           this._invalidate();
 36410           this._alpha = val;
 36411           this._animated = false;
 36412         },
 36413         get blendMode() {
 36414           return this._blendMode;
 36415         },
 36416         set blendMode(val) {
 36417           if (blendModes.indexOf(val) >= 0) {
 36418             this._blendMode = val;
 36419           } else {
 36420             throwError('ArgumentError', Errors.InvalidEnumError, 'blendMode');
 36422           this._animated = false;
 36423         },
 36424         get cacheAsBitmap() {
 36425           return this._cacheAsBitmap;
 36426         },
 36427         set cacheAsBitmap(val) {
 36428           this._cacheAsBitmap = this._filters.length ? true : val;
 36429           this._animated = false;
 36430         },
 36431         get filters() {
 36432           return this._filters;
 36433         },
 36434         set filters(val) {
 36435           if (val.length) {
 36436             if (!this._filters.length)
 36437               this._wasCachedAsBitmap = this._cacheAsBitmap;
 36438             this._cacheAsBitmap = true;
 36439           } else {
 36440             this._cacheAsBitmap = this._wasCachedAsBitmap;
 36442           this._filters = val;
 36443           this._animated = false;
 36444         },
 36445         get height() {
 36446           var bounds = this._getContentBounds();
 36447           var t = this._currentTransform;
 36448           return Math.abs(t.b) * (bounds.xMax - bounds.xMin) + Math.abs(t.d) * (bounds.yMax - bounds.yMin) | 0;
 36449         },
 36450         set height(val) {
 36451           if (val < 0) {
 36452             return;
 36454           var u = Math.abs(this._rotationCos);
 36455           var v = Math.abs(this._rotationSin);
 36456           var bounds = this._getContentBounds();
 36457           var baseHeight = v * (bounds.xMax - bounds.xMin) + u * (bounds.yMax - bounds.yMin);
 36458           if (!baseHeight) {
 36459             return;
 36461           var baseWidth = u * (bounds.xMax - bounds.xMin) + v * (bounds.yMax - bounds.yMin);
 36462           this.scaleX = this.width / baseWidth;
 36463           this.scaleY = val / baseHeight;
 36464         },
 36465         get loaderInfo() {
 36466           return this._loader && this._loader._contentLoaderInfo || this._parent.loaderInfo;
 36467         },
 36468         get mask() {
 36469           return this._mask;
 36470         },
 36471         set mask(val) {
 36472           if (this._mask === val) {
 36473             return;
 36475           this._invalidate();
 36476           if (val && val._maskedObject) {
 36477             val._maskedObject.mask = null;
 36479           this._mask = val;
 36480           if (val) {
 36481             val._maskedObject = this;
 36483           this._animated = false;
 36484         },
 36485         get name() {
 36486           return this._name || (this._name = generateName());
 36487         },
 36488         set name(val) {
 36489           this._name = val;
 36490         },
 36491         get mouseX() {
 36492           if (!this._stage) {
 36493             return 0;
 36495           point.x = this._stage._mouseX;
 36496           point.y = this._stage._mouseY;
 36497           this._applyConcatenatedInverseTransform(point);
 36498           return point.x;
 36499         },
 36500         get mouseY() {
 36501           if (!this._stage) {
 36502             return 0;
 36504           point.x = this._stage._mouseX;
 36505           point.y = this._stage._mouseY;
 36506           this._applyConcatenatedInverseTransform(point);
 36507           return point.y;
 36508         },
 36509         get opaqueBackground() {
 36510           return this._opaqueBackground;
 36511         },
 36512         set opaqueBackground(val) {
 36513           this._opaqueBackground = val;
 36514           this._animated = false;
 36515         },
 36516         get parent() {
 36517           return this._index > -1 ? this._parent : null;
 36518         },
 36519         get root() {
 36520           return this._stage && this._stage._root;
 36521         },
 36522         get rotation() {
 36523           return this._rotation;
 36524         },
 36525         set rotation(val) {
 36526           val %= 360;
 36527           if (val > 180) {
 36528             val -= 360;
 36530           if (val === this._rotation)
 36531             return;
 36532           this._invalidate();
 36533           this._invalidateTransform();
 36534           this._rotation = val;
 36535           var u, v;
 36536           switch (val) {
 36537           case 0:
 36538           case 360:
 36539             u = 1, v = 0;
 36540             break;
 36541           case 90:
 36542           case -270:
 36543             u = 0, v = 1;
 36544             break;
 36545           case 180:
 36546           case -180:
 36547             u = -1, v = 0;
 36548             break;
 36549           case 270:
 36550           case -90:
 36551             u = 0, v = -1;
 36552             break;
 36553           default:
 36554             var angle = this._rotation / 180 * Math.PI;
 36555             u = Math.cos(angle);
 36556             v = Math.sin(angle);
 36557             break;
 36559           this._rotationCos = u;
 36560           this._rotationSin = v;
 36561           var m = this._currentTransform;
 36562           m.a = u * this._scaleX;
 36563           m.b = v * this._scaleX;
 36564           m.c = -v * this._scaleY;
 36565           m.d = u * this._scaleY;
 36566           this._animated = false;
 36567         },
 36568         get rotationX() {
 36569           return 0;
 36570         },
 36571         set rotationX(val) {
 36572           somewhatImplemented('DisplayObject.rotationX');
 36573         },
 36574         get rotationY() {
 36575           return 0;
 36576         },
 36577         set rotationY(val) {
 36578           somewhatImplemented('DisplayObject.rotationY');
 36579         },
 36580         get rotationZ() {
 36581           return this.rotation;
 36582         },
 36583         set rotationZ(val) {
 36584           this.rotation = val;
 36585           somewhatImplemented('DisplayObject.rotationZ');
 36586         },
 36587         get stage() {
 36588           return this._stage;
 36589         },
 36590         get scaleX() {
 36591           return this._scaleX;
 36592         },
 36593         set scaleX(val) {
 36594           if (val === this._scaleX)
 36595             return;
 36596           this._invalidate();
 36597           this._invalidateTransform();
 36598           this._scaleX = val;
 36599           var m = this._currentTransform;
 36600           m.a = this._rotationCos * val;
 36601           m.b = this._rotationSin * val;
 36602           this._animated = false;
 36603         },
 36604         get scaleY() {
 36605           return this._scaleY;
 36606         },
 36607         set scaleY(val) {
 36608           if (val === this._scaleY)
 36609             return;
 36610           this._invalidate();
 36611           this._invalidateTransform();
 36612           this._scaleY = val;
 36613           var m = this._currentTransform;
 36614           m.c = -this._rotationSin * val;
 36615           m.d = this._rotationCos * val;
 36616           this._animated = false;
 36617         },
 36618         get scaleZ() {
 36619           return 1;
 36620         },
 36621         set scaleZ(val) {
 36622           somewhatImplemented('DisplayObject.scaleZ');
 36623         },
 36624         get scale9Grid() {
 36625           return this._scale9Grid;
 36626         },
 36627         set scale9Grid(val) {
 36628           somewhatImplemented('DisplayObject.scale9Grid');
 36629           this._scale9Grid = val;
 36630           this._animated = false;
 36631         },
 36632         get scrollRect() {
 36633           return this._scrollRect;
 36634         },
 36635         set scrollRect(val) {
 36636           somewhatImplemented('DisplayObject.scrollRect');
 36637           this._scrollRect = val;
 36638         },
 36639         get transform() {
 36640           return new flash.geom.Transform(this);
 36641         },
 36642         set transform(val) {
 36643           var transform = this.transform;
 36644           transform.colorTransform = val.colorTransform;
 36645           if (val.matrix3D) {
 36646             transform.matrix3D = val.matrix3D;
 36647           } else {
 36648             transform.matrix = val.matrix;
 36650         },
 36651         get visible() {
 36652           return this._visible;
 36653         },
 36654         set visible(val) {
 36655           if (val === this._visible)
 36656             return;
 36657           this._invalidate();
 36658           this._visible = val;
 36659           this._animated = false;
 36660         },
 36661         get width() {
 36662           var bounds = this._getContentBounds();
 36663           var t = this._currentTransform;
 36664           return Math.abs(t.a) * (bounds.xMax - bounds.xMin) + Math.abs(t.c) * (bounds.yMax - bounds.yMin) | 0;
 36665         },
 36666         set width(val) {
 36667           if (val < 0) {
 36668             return;
 36670           var u = Math.abs(this._rotationCos);
 36671           var v = Math.abs(this._rotationSin);
 36672           var bounds = this._getContentBounds();
 36673           var baseWidth = u * (bounds.xMax - bounds.xMin) + v * (bounds.yMax - bounds.yMin);
 36674           if (!baseWidth) {
 36675             return;
 36677           var baseHeight = v * (bounds.xMax - bounds.xMin) + u * (bounds.yMax - bounds.yMin);
 36678           this.scaleY = this.height / baseHeight;
 36679           this.scaleX = val / baseWidth;
 36680         },
 36681         get x() {
 36682           return this._currentTransform.tx;
 36683         },
 36684         set x(val) {
 36685           if (val === this._currentTransform.tx) {
 36686             return;
 36688           this._invalidate();
 36689           this._invalidateTransform();
 36690           this._currentTransform.tx = val;
 36691           this._animated = false;
 36692         },
 36693         get y() {
 36694           return this._currentTransform.ty;
 36695         },
 36696         set y(val) {
 36697           if (val === this._currentTransform.ty) {
 36698             return;
 36700           this._invalidate();
 36701           this._invalidateTransform();
 36702           this._currentTransform.ty = val;
 36703           this._animated = false;
 36704         },
 36705         get z() {
 36706           return 0;
 36707         },
 36708         set z(val) {
 36709           somewhatImplemented('DisplayObject.z');
 36710         },
 36711         _getContentBounds: function () {
 36712           var bounds = this._bounds;
 36713           if (bounds.invalid) {
 36714             var bbox = this._bbox;
 36715             var xMin = Number.MAX_VALUE;
 36716             var xMax = Number.MIN_VALUE;
 36717             var yMin = Number.MAX_VALUE;
 36718             var yMax = Number.MIN_VALUE;
 36719             if (bbox) {
 36720               xMin = bbox.xMin;
 36721               xMax = bbox.xMax;
 36722               yMin = bbox.yMin;
 36723               yMax = bbox.yMax;
 36724             } else {
 36725               var children = this._children;
 36726               var numChildren = children.length;
 36727               for (var i = 0; i < numChildren; i++) {
 36728                 var child = children[i];
 36729                 if (!flash.display.DisplayObject.class.isInstanceOf(child)) {
 36730                   continue;
 36732                 var b = child.getBounds(this);
 36733                 var x1 = b.xMin;
 36734                 var y1 = b.yMin;
 36735                 var x2 = b.xMax;
 36736                 var y2 = b.yMax;
 36737                 xMin = Math.min(xMin, x1, x2);
 36738                 xMax = Math.max(xMax, x1, x2);
 36739                 yMin = Math.min(yMin, y1, y2);
 36740                 yMax = Math.max(yMax, y1, y2);
 36742               if (this._graphics) {
 36743                 var b = this._graphics._getBounds(true);
 36744                 if (b.xMin !== b.xMax && b.yMin !== b.yMax) {
 36745                   var x1 = b.xMin;
 36746                   var y1 = b.yMin;
 36747                   var x2 = b.xMax;
 36748                   var y2 = b.yMax;
 36749                   xMin = Math.min(xMin, x1, x2);
 36750                   xMax = Math.max(xMax, x1, x2);
 36751                   yMin = Math.min(yMin, y1, y2);
 36752                   yMax = Math.max(yMax, y1, y2);
 36756             if (xMin === Number.MAX_VALUE) {
 36757               xMin = xMax = yMin = yMax = 0;
 36759             bounds.xMin = xMin;
 36760             bounds.xMax = xMax;
 36761             bounds.yMin = yMin;
 36762             bounds.yMax = yMax;
 36763             bounds.invalid = false;
 36765           return bounds;
 36766         },
 36767         _getRegion: function getRegion(targetCoordSpace) {
 36768           var b;
 36769           var filters = this._filters;
 36770           if (filters.length) {
 36771             var xMin = Number.MAX_VALUE;
 36772             var xMax = Number.MIN_VALUE;
 36773             var yMin = Number.MAX_VALUE;
 36774             var yMax = Number.MIN_VALUE;
 36775             if (this._graphics) {
 36776               b = this._graphics._getBounds(true);
 36777               if (b) {
 36778                 xMin = b.xMin;
 36779                 xMax = b.xMax;
 36780                 yMin = b.yMin;
 36781                 yMax = b.yMax;
 36784             var children = this._children;
 36785             for (var i = 0; i < children.length; i++) {
 36786               var child = children[i];
 36787               b = children[i]._getRegion(this);
 36788               if (b.xMin < xMin) {
 36789                 xMin = b.xMin;
 36791               if (b.xMax > xMax) {
 36792                 xMax = b.xMax;
 36794               if (b.yMin < yMin) {
 36795                 yMin = b.yMin;
 36797               if (b.yMax > yMax) {
 36798                 yMax = b.yMax;
 36801             if (xMin === Number.MAX_VALUE) {
 36802               return {
 36803                 xMin: 0,
 36804                 xMax: 0,
 36805                 yMin: 0,
 36806                 yMax: 0
 36807               };
 36809             b = {
 36810               xMin: xMin,
 36811               xMax: xMax,
 36812               yMin: yMin,
 36813               yMax: yMax
 36814             };
 36815             for (var i = 0; i < filters.length; i++) {
 36816               filters[i]._updateFilterBounds(b);
 36818           } else {
 36819             b = this._graphics ? this._graphics._getBounds(true) : this._getContentBounds();
 36821           return this._getTransformedRect(b, targetCoordSpace);
 36822         },
 36823         getBounds: function (targetCoordSpace) {
 36824           return this._getTransformedRect(this._getContentBounds(), targetCoordSpace);
 36825         },
 36826         _getTransformedRect: function (rect, targetCoordSpace) {
 36827           if (!targetCoordSpace || targetCoordSpace === this) {
 36828             return rect;
 36830           var xMin = rect.xMin;
 36831           var xMax = rect.xMax;
 36832           var yMin = rect.yMin;
 36833           var yMax = rect.yMax;
 36834           if (xMax - xMin === 0 || yMax - yMin === 0) {
 36835             return {
 36836               xMin: 0,
 36837               yMin: 0,
 36838               xMax: 0,
 36839               yMax: 0
 36840             };
 36842           var m = targetCoordSpace && !flash.display.DisplayObject.class.isInstanceOf(targetCoordSpace) ? targetCoordSpace : this._getConcatenatedTransform(targetCoordSpace, false);
 36843           var x0 = m.a * xMin + m.c * yMin + m.tx | 0;
 36844           var y0 = m.b * xMin + m.d * yMin + m.ty | 0;
 36845           var x1 = m.a * xMax + m.c * yMin + m.tx | 0;
 36846           var y1 = m.b * xMax + m.d * yMin + m.ty | 0;
 36847           var x2 = m.a * xMax + m.c * yMax + m.tx | 0;
 36848           var y2 = m.b * xMax + m.d * yMax + m.ty | 0;
 36849           var x3 = m.a * xMin + m.c * yMax + m.tx | 0;
 36850           var y3 = m.b * xMin + m.d * yMax + m.ty | 0;
 36851           var tmp = 0;
 36852           if (x0 > x1) {
 36853             tmp = x0;
 36854             x0 = x1;
 36855             x1 = tmp;
 36857           if (x2 > x3) {
 36858             tmp = x2;
 36859             x2 = x3;
 36860             x3 = tmp;
 36862           xMin = x0 < x2 ? x0 : x2;
 36863           xMax = x1 > x3 ? x1 : x3;
 36864           if (y0 > y1) {
 36865             tmp = y0;
 36866             y0 = y1;
 36867             y1 = tmp;
 36869           if (y2 > y3) {
 36870             tmp = y2;
 36871             y2 = y3;
 36872             y3 = tmp;
 36874           yMin = y0 < y2 ? y0 : y2;
 36875           yMax = y1 > y3 ? y1 : y3;
 36876           return {
 36877             xMin: xMin,
 36878             yMin: yMin,
 36879             xMax: xMax,
 36880             yMax: yMax
 36881           };
 36882         },
 36883         hitTestObject: function (obj) {
 36884           return this._hitTest(false, 0, 0, false, obj);
 36885         },
 36886         hitTestPoint: function (x, y, shapeFlag) {
 36887           return this._hitTest(true, x, y, shapeFlag, null);
 36888         },
 36889         destroy: function () {
 36890           if (this._destroyed) {
 36891             return;
 36893           this._destroyed = true;
 36894           this.cleanupBroadcastListeners();
 36895         },
 36896         cleanupBroadcastListeners: function () {
 36897           var listenerLists = this._listeners;
 36898           for (var type in listenerLists) {
 36899             avm2.systemDomain.onMessage.unregister(type, this._onBroadcastMessage);
 36902       };
 36903     var desc = Object.getOwnPropertyDescriptor;
 36904     def.__glue__ = {
 36905       native: {
 36906         instance: {
 36907           root: desc(def, 'root'),
 36908           stage: desc(def, 'stage'),
 36909           name: desc(def, 'name'),
 36910           parent: desc(def, 'parent'),
 36911           mask: desc(def, 'mask'),
 36912           visible: desc(def, 'visible'),
 36913           x: {
 36914             get: function x() {
 36915               return this.x / 20;
 36916             },
 36917             set: function x(value) {
 36918               this.x = value * 20 | 0;
 36920           },
 36921           y: {
 36922             get: function y() {
 36923               return this.y / 20;
 36924             },
 36925             set: function y(value) {
 36926               this.y = value * 20 | 0;
 36928           },
 36929           z: {
 36930             get: function z() {
 36931               return this.z / 20;
 36932             },
 36933             set: function z(value) {
 36934               this.z = value * 20 | 0;
 36936           },
 36937           scaleX: desc(def, 'scaleX'),
 36938           scaleY: desc(def, 'scaleY'),
 36939           scaleZ: desc(def, 'scaleZ'),
 36940           mouseX: {
 36941             get: function mouseX() {
 36942               return this.mouseX / 20;
 36943             },
 36944             set: function mouseX(value) {
 36945               this.mouseX = value * 20 | 0;
 36947           },
 36948           mouseY: {
 36949             get: function mouseY() {
 36950               return this.mouseY / 20;
 36951             },
 36952             set: function mouseY(value) {
 36953               this.mouseY = value * 20 | 0;
 36955           },
 36956           rotation: desc(def, 'rotation'),
 36957           rotationX: desc(def, 'rotationX'),
 36958           rotationY: desc(def, 'rotationY'),
 36959           rotationZ: desc(def, 'rotationZ'),
 36960           alpha: desc(def, 'alpha'),
 36961           width: {
 36962             get: function width() {
 36963               return this.width / 20;
 36964             },
 36965             set: function width(value) {
 36966               this.width = value * 20 | 0;
 36968           },
 36969           height: {
 36970             get: function height() {
 36971               return this.height / 20;
 36972             },
 36973             set: function height(value) {
 36974               this.height = value * 20 | 0;
 36976           },
 36977           _hitTest: function (use_xy, x, y, useShape, hitTestObject) {
 36978             x = x * 20 | 0;
 36979             y = y * 20 | 0;
 36980             return this._hitTest(use_xy, x, y, useShape, hitTestObject);
 36981           },
 36982           cacheAsBitmap: desc(def, 'cacheAsBitmap'),
 36983           opaqueBackground: desc(def, 'opaqueBackground'),
 36984           scrollRect: desc(def, 'scrollRect'),
 36985           filters: desc(def, 'filters'),
 36986           blendMode: desc(def, 'blendMode'),
 36987           transform: desc(def, 'transform'),
 36988           scale9Grid: desc(def, 'scale9Grid'),
 36989           loaderInfo: desc(def, 'loaderInfo'),
 36990           accessibilityProperties: desc(def, 'accessibilityProperties'),
 36991           globalToLocal: function (pt) {
 36992             point.x = pt.x * 20 | 0;
 36993             point.y = pt.y * 20 | 0;
 36994             this._applyConcatenatedInverseTransform(point);
 36995             return new flash.geom.Point(point.x / 20, point.y / 20);
 36996           },
 36997           localToGlobal: function (pt) {
 36998             point.x = pt.x * 20 | 0;
 36999             point.y = pt.y * 20 | 0;
 37000             this._applyCurrentTransform(point);
 37001             return new flash.geom.Point(point.x / 20, point.y / 20);
 37002           },
 37003           getBounds: function (targetCoordSpace) {
 37004             var bounds = this.getBounds(targetCoordSpace);
 37005             return new flash.geom.Rectangle(bounds.xMin / 20, bounds.yMin / 20, (bounds.xMax - bounds.xMin) / 20, (bounds.yMax - bounds.yMin) / 20);
 37006           },
 37007           getRect: function (targetCoordSpace) {
 37008             somewhatImplemented('DisplayObject.getRect');
 37009             var bounds = this.getBounds(targetCoordSpace);
 37010             return new flash.geom.Rectangle(bounds.xMin / 20, bounds.yMin / 20, (bounds.xMax - bounds.xMin) / 20, (bounds.yMax - bounds.yMin) / 20);
 37014     };
 37015     return def;
 37016   }.call(this);
 37017 var DisplayObjectContainerDefinition = function () {
 37018     var def = {
 37019         get mouseChildren() {
 37020           return this._mouseChildren;
 37021         },
 37022         set mouseChildren(val) {
 37023           this._mouseChildren = val;
 37024         },
 37025         get numChildren() {
 37026           return this._children.length;
 37027         },
 37028         get tabChildren() {
 37029           return this._tabChildren;
 37030         },
 37031         set tabChildren(val) {
 37032           this._tabChildren = val;
 37033         },
 37034         get textSnapshot() {
 37035           notImplemented();
 37036         },
 37037         addChild: function (child) {
 37038           return this.addChildAt(child, this._children.length);
 37039         },
 37040         addChildAt: function (child, index) {
 37041           if (child === this) {
 37042             throwError('ArgumentError', Errors.CantAddSelfError);
 37044           if (child._parent === this) {
 37045             return this.setChildIndex(child, index);
 37047           var children = this._children;
 37048           if (index < 0 || index > children.length) {
 37049             throwError('RangeError', Errors.ParamRangeError);
 37051           if (child._index > -1) {
 37052             var LoaderClass = avm2.systemDomain.getClass('flash.display.Loader');
 37053             if (LoaderClass.isInstanceOf(child._parent)) {
 37054               def.removeChild.call(child._parent, child);
 37055             } else {
 37056               child._parent.removeChild(child);
 37059           if (!this._sparse) {
 37060             for (var i = children.length; i && i > index; i--) {
 37061               children[i - 1]._index++;
 37064           children.splice(index, 0, child);
 37065           child._invalidateTransform();
 37066           child._owned = false;
 37067           child._parent = this;
 37068           child._stage = this._stage;
 37069           child._index = index;
 37070           child._dispatchEvent('added', undefined, true);
 37071           if (this._stage) {
 37072             this._stage._addToStage(child);
 37074           return child;
 37075         },
 37076         areInaccessibleObjectsUnderPoint: function (pt) {
 37077           notImplemented();
 37078         },
 37079         contains: function (child) {
 37080           return child._parent === this;
 37081         },
 37082         getChildAt: function (index) {
 37083           var children = this._children;
 37084           if (index < 0 || index > children.length) {
 37085             throwError('RangeError', Errors.ParamRangeError);
 37087           var child = children[index];
 37088           if (!flash.display.DisplayObject.class.isInstanceOf(child)) {
 37089             return null;
 37091           return child;
 37092         },
 37093         getChildByName: function (name) {
 37094           var children = this._children;
 37095           for (var i = 0, n = children.length; i < n; i++) {
 37096             var child = children[i];
 37097             if (child.name === name) {
 37098               return this.getChildAt(i);
 37101           return null;
 37102         },
 37103         getChildIndex: function (child) {
 37104           if (child._parent !== this) {
 37105             throwError('ArgumentError', Errors.NotAChildError);
 37107           return this._sparse ? this._children.indexOf(child) : child._index;
 37108         },
 37109         getObjectsUnderPoint: function (pt) {
 37110           notImplemented();
 37111         },
 37112         removeChild: function (child) {
 37113           if (child._parent !== this) {
 37114             throwError('ArgumentError', Errors.NotAChildError);
 37116           return this.removeChildAt(this.getChildIndex(child));
 37117         },
 37118         removeChildAt: function (index) {
 37119           var children = this._children;
 37120           if (index < 0 || index >= children.length) {
 37121             throwError('RangeError', Errors.ParamRangeError);
 37123           var child = children[index];
 37124           child._dispatchEvent('removed', undefined, true);
 37125           if (this._stage) {
 37126             this._stage._removeFromStage(child);
 37128           if (!this._sparse) {
 37129             for (var i = children.length; i && i > index; i--) {
 37130               children[i - 1]._index--;
 37133           children.splice(index, 1);
 37134           child._invalidateTransform();
 37135           child._owned = false;
 37136           child._parent = null;
 37137           child._index = -1;
 37138           return child;
 37139         },
 37140         setChildIndex: function (child, index) {
 37141           if (child._parent !== this) {
 37142             throwError('ArgumentError', Errors.NotAChildError);
 37144           var currentIndex = this.getChildIndex(child);
 37145           if (currentIndex === index) {
 37146             return;
 37148           var children = this._children;
 37149           if (index < 0 || index > children.length) {
 37150             throwError('RangeError', Errors.ParamRangeError);
 37152           children.splice(currentIndex, 1);
 37153           children.splice(index, 0, child);
 37154           if (!this._sparse) {
 37155             var i = currentIndex < index ? currentIndex : index;
 37156             while (i < children.length) {
 37157               children[i]._index = i++;
 37160           child._owned = false;
 37161           child._invalidate();
 37162           return child;
 37163         },
 37164         removeChildren: function (beginIndex, endIndex) {
 37165           beginIndex = arguments.length < 1 ? 0 : beginIndex | 0;
 37166           endIndex = arguments.length < 2 ? 2147483647 : endIndex | 0;
 37167           var numChildren = this._children.length;
 37168           if (beginIndex < 0 || endIndex < 0 || endIndex < beginIndex) {
 37169             throwError('RangeError', Errors.ParamRangeError);
 37171           if (numChildren === 0) {
 37172             return;
 37174           if (endIndex > numChildren - 1) {
 37175             endIndex = numChildren - 1;
 37177           var count = endIndex - beginIndex + 1;
 37178           while (count--) {
 37179             this.removeChildAt(beginIndex);
 37181         },
 37182         swapChildren: function (child1, child2) {
 37183           if (child1._parent !== this || child2._parent !== this) {
 37184             throwError('ArgumentError', Errors.NotAChildError);
 37186           this.swapChildrenAt(this.getChildIndex(child1), this.getChildIndex(child2));
 37187         },
 37188         swapChildrenAt: function (index1, index2) {
 37189           var children = this._children;
 37190           var numChildren = children.length;
 37191           if (index1 < 0 || index1 > numChildren || index2 < 0 || index2 > numChildren) {
 37192             throwError('RangeError', Errors.ParamRangeError);
 37194           var child1 = children[index1];
 37195           var child2 = children[index2];
 37196           children[index1] = child2;
 37197           children[index2] = child1;
 37198           child1._index = index2;
 37199           child2._index = index1;
 37200           child1._owned = false;
 37201           child2._owned = false;
 37202           child1._invalidate();
 37203           child2._invalidate();
 37204         },
 37205         destroy: function () {
 37206           if (this._destroyed) {
 37207             return;
 37209           this._destroyed = true;
 37210           this._children.forEach(function (child) {
 37211             if (child.destroy) {
 37212               child.destroy();
 37214           });
 37215           this.cleanupBroadcastListeners();
 37217       };
 37218     var desc = Object.getOwnPropertyDescriptor;
 37219     def.initialize = function () {
 37220       this._mouseChildren = true;
 37221       this._tabChildren = true;
 37222       this._sparse = false;
 37223       this._isContainer = true;
 37224     };
 37225     def.__glue__ = {
 37226       native: {
 37227         instance: {
 37228           numChildren: desc(def, 'numChildren'),
 37229           tabChildren: desc(def, 'tabChildren'),
 37230           mouseChildren: desc(def, 'mouseChildren'),
 37231           textSnapshot: desc(def, 'textSnapshot'),
 37232           addChild: def.addChild,
 37233           addChildAt: def.addChildAt,
 37234           removeChild: def.removeChild,
 37235           removeChildAt: def.removeChildAt,
 37236           getChildIndex: def.getChildIndex,
 37237           setChildIndex: def.setChildIndex,
 37238           getChildAt: def.getChildAt,
 37239           getChildByName: def.getChildByName,
 37240           contains: def.contains,
 37241           swapChildrenAt: def.swapChildrenAt,
 37242           swapChildren: def.swapChildren,
 37243           removeChildren: def.removeChildren
 37246     };
 37247     return def;
 37248   }.call(this);
 37249 var FrameLabelDefinition = function () {
 37250     return {
 37251       __class__: 'flash.display.FrameLabel',
 37252       initialize: function () {
 37253       },
 37254       __glue__: {
 37255         native: {
 37256           static: {},
 37257           instance: {
 37258             ctor: function ctor(name, frame) {
 37259               this._name = name;
 37260               this._frame = frame;
 37261             },
 37262             name: {
 37263               get: function name() {
 37264                 return this._name;
 37266             },
 37267             frame: {
 37268               get: function frame() {
 37269                 return this._frame;
 37275     };
 37276   }.call(this);
 37277 var GraphicsDefinition = function () {
 37278     var GRAPHICS_PATH_WINDING_EVEN_ODD = 'evenOdd';
 37279     var GRAPHICS_PATH_WINDING_NON_ZERO = 'nonZero';
 37280     var def = {
 37281         __class__: 'flash.display.Graphics',
 37282         initialize: function () {
 37283           this._paths = [];
 37284           this.beginPath();
 37285           this._bitmap = null;
 37286           this._parent = 0;
 37287           this.bbox = null;
 37288           this.strokeBbox = null;
 37289         },
 37290         _invalidate: function () {
 37291           this.bbox = null;
 37292           this.strokeBbox = null;
 37293           this._parent._invalidate();
 37294           this._parent._invalidateBounds();
 37295         },
 37296         beginPath: function () {
 37297           var oldPath = this._currentPath;
 37298           if (oldPath && (oldPath.commands.length === 0 || oldPath.commands.length === 1 && oldPath.commands[0] === SHAPE_MOVE_TO)) {
 37299             return;
 37301           var path = this._currentPath = new ShapePath(null, null);
 37302           this._paths.push(path);
 37303           if (oldPath) {
 37304             path.fillStyle = oldPath.fillStyle;
 37305             path.lineStyle = oldPath.lineStyle;
 37306             path.fillRule = oldPath.fillRule;
 37308         },
 37309         _drawPathObject: function (path) {
 37310           if (path.__class__ === 'flash.display.GraphicsPath')
 37311             this.drawPath(path.commands, path.data, path.winding);
 37312           else if (path.__class__ === 'flash.display.GraphicsTrianglePath')
 37313             this.drawTriangles(path.vertices, path.indices, path.uvtData, path.culling);
 37314         },
 37315         draw: function (ctx, clip, ratio, colorTransform) {
 37316           var paths = this._paths;
 37317           for (var i = 0; i < paths.length; i++) {
 37318             paths[i].draw(ctx, clip, ratio, colorTransform);
 37320         },
 37321         beginFill: function (color, alpha) {
 37322           if (alpha === undefined)
 37323             alpha = 1;
 37324           this.beginPath();
 37325           this._currentPath.fillStyle = alpha ? {
 37326             style: rgbIntAlphaToStr(color, alpha)
 37327           } : null;
 37328         },
 37329         beginGradientFill: function (type, colors, alphas, ratios, matrix, spreadMethod, interpolationMethod, focalPos) {
 37330           var style = createGradientStyle(type, colors, alphas, ratios, matrix, spreadMethod, interpolationMethod, focalPos);
 37331           this.beginPath();
 37332           this._currentPath.fillStyle = style;
 37333         },
 37334         beginBitmapFill: function (bitmap, matrix, repeat, smooth) {
 37335           this.beginPath();
 37336           repeat = repeat !== false;
 37337           this._currentPath.fillStyle = createPatternStyle(bitmap, matrix, repeat, !(!smooth));
 37338         },
 37339         clear: function () {
 37340           this._invalidate();
 37341           this._paths = [];
 37342           this._currentPath = null;
 37343           this.beginPath();
 37344         },
 37345         copyFrom: function (sourceGraphics) {
 37346           notImplemented('Graphics#copyFrom');
 37347         },
 37348         cubicCurveTo: function (cp1x, cp1y, cp2x, cp2y, x, y) {
 37349           this._invalidate();
 37350           this._currentPath.cubicCurveTo(cp1x * 20 | 0, cp1y * 20 | 0, cp2x * 20 | 0, cp2y * 20 | 0, x * 20 | 0, y * 20 | 0);
 37351         },
 37352         curveTo: function (cpx, cpy, x, y) {
 37353           this._invalidate();
 37354           this._currentPath.curveTo(cpx * 20 | 0, cpy * 20 | 0, x * 20 | 0, y * 20 | 0);
 37355         },
 37356         drawCircle: function (x, y, radius) {
 37357           var radius2 = radius * 2;
 37358           this.drawRoundRect(x - radius, y - radius, radius2, radius2, radius2, radius2);
 37359         },
 37360         drawEllipse: function (x, y, width, height) {
 37361           this.drawRoundRect(x, y, width, height, width, height);
 37362         },
 37363         drawPath: function (commands, data, winding) {
 37364           this._invalidate();
 37365           this.beginPath();
 37366           this._currentPath.fillRule = winding || GRAPHICS_PATH_WINDING_EVEN_ODD;
 37367           this._currentPath.commands = commands;
 37368           this._currentPath.data = data;
 37369         },
 37370         drawRect: function (x, y, w, h) {
 37371           if (isNaN(w + h))
 37372             throwError('ArgumentError', Errors.InvalidParamError);
 37373           this._invalidate();
 37374           this._currentPath.rect(x * 20 | 0, y * 20 | 0, w * 20 | 0, h * 20 | 0);
 37375         },
 37376         drawRoundRect: function (x, y, w, h, ellipseWidth, ellipseHeight) {
 37377           if (isNaN(w + h + ellipseWidth) || ellipseHeight !== undefined && isNaN(ellipseHeight)) {
 37378             throwError('ArgumentError', Errors.InvalidParamError);
 37380           this._invalidate();
 37381           if (ellipseHeight === undefined) {
 37382             ellipseHeight = ellipseWidth;
 37384           x = x * 20 | 0;
 37385           y = y * 20 | 0;
 37386           w = w * 20 | 0;
 37387           h = h * 20 | 0;
 37388           if (!ellipseHeight || !ellipseWidth) {
 37389             this._currentPath.rect(x, y, w, h);
 37390             return;
 37392           var radiusX = ellipseWidth / 2 * 20 | 0;
 37393           var radiusY = ellipseHeight / 2 * 20 | 0;
 37394           var hw = w / 2 | 0;
 37395           var hh = h / 2 | 0;
 37396           if (radiusX > hw) {
 37397             radiusX = hw;
 37399           if (radiusY > hh) {
 37400             radiusY = hh;
 37402           if (hw === radiusX && hh === radiusY) {
 37403             if (radiusX === radiusY)
 37404               this._currentPath.circle(x + radiusX, y + radiusY, radiusX);
 37405             else
 37406               this._currentPath.ellipse(x + radiusX, y + radiusY, radiusX, radiusY);
 37407             return;
 37409           var right = x + w;
 37410           var bottom = y + h;
 37411           var xlw = x + radiusX;
 37412           var xrw = right - radiusX;
 37413           var ytw = y + radiusY;
 37414           var ybw = bottom - radiusY;
 37415           this._currentPath.moveTo(right, ybw);
 37416           this._currentPath.curveTo(right, bottom, xrw, bottom);
 37417           this._currentPath.lineTo(xlw, bottom);
 37418           this._currentPath.curveTo(x, bottom, x, ybw);
 37419           this._currentPath.lineTo(x, ytw);
 37420           this._currentPath.curveTo(x, y, xlw, y);
 37421           this._currentPath.lineTo(xrw, y);
 37422           this._currentPath.curveTo(right, y, right, ytw);
 37423           this._currentPath.lineTo(right, ybw);
 37424         },
 37425         drawRoundRectComplex: function (x, y, w, h, topLeftRadius, topRightRadius, bottomLeftRadius, bottomRightRadius) {
 37426           if (isNaN(w + h + topLeftRadius + topRightRadius + bottomLeftRadius + bottomRightRadius)) {
 37427             throwError('ArgumentError', Errors.InvalidParamError);
 37429           this._invalidate();
 37430           x = x * 20 | 0;
 37431           y = y * 20 | 0;
 37432           w = w * 20 | 0;
 37433           h = h * 20 | 0;
 37434           if (!topLeftRadius && !topRightRadius && !bottomLeftRadius && !bottomRightRadius) {
 37435             this._currentPath.rect(x, y, w, h);
 37436             return;
 37438           topLeftRadius = topLeftRadius * 20 | 0;
 37439           topRightRadius = topRightRadius * 20 | 0;
 37440           bottomLeftRadius = bottomLeftRadius * 20 | 0;
 37441           bottomRightRadius = bottomRightRadius * 20 | 0;
 37442           var right = x + w;
 37443           var bottom = y + h;
 37444           var xtl = x + topLeftRadius;
 37445           this._currentPath.moveTo(right, bottom - bottomRightRadius);
 37446           this._currentPath.curveTo(right, bottom, right - bottomRightRadius, bottom);
 37447           this._currentPath.lineTo(x + bottomLeftRadius, bottom);
 37448           this._currentPath.curveTo(x, bottom, x, bottom - bottomLeftRadius);
 37449           this._currentPath.lineTo(x, y + topLeftRadius);
 37450           this._currentPath.curveTo(x, y, xtl, y);
 37451           this._currentPath.lineTo(right - topRightRadius, y);
 37452           this._currentPath.curveTo(right, y, right, y + topRightRadius);
 37453           this._currentPath.lineTo(right, bottom - bottomRightRadius);
 37454         },
 37455         drawTriangles: function (vertices, indices, uvtData, cullingStr) {
 37456           if (vertices === null || vertices.length === 0) {
 37457             return;
 37459           var numVertices = vertices.length / 2;
 37460           var numTriangles = 0;
 37461           if (indices) {
 37462             if (indices.length % 3) {
 37463               throwError('ArgumentError', Errors.InvalidParamError);
 37464             } else {
 37465               numTriangles = indices.length / 3;
 37467           } else {
 37468             if (vertices.length % 6) {
 37469               throwError('ArgumentError', Errors.InvalidParamError);
 37470             } else {
 37471               numTriangles = vertices.length / 6;
 37474           var numStrides = 0;
 37475           if (uvtData) {
 37476             if (uvtData.length == numVertices * 2) {
 37477               numStrides = 2;
 37478             } else if (uvtData.length == numVertices * 3) {
 37479               numStrides = 3;
 37480             } else {
 37481               throwError('ArgumentError', Errors.InvalidParamError);
 37484           var culling = 0;
 37485           if (cullingStr === 'none') {
 37486             culling = 0;
 37487           } else if (cullingStr === 'negative') {
 37488             culling = -1;
 37489           } else if (cullingStr === 'positive') {
 37490             culling = 1;
 37491           } else {
 37492             throwError('ArgumentError', Errors.InvalidEnumError, 'culling');
 37494           notImplemented('Graphics#drawTriangles');
 37495         },
 37496         endFill: function () {
 37497           this.beginPath();
 37498           this._currentPath.fillStyle = null;
 37499         },
 37500         lineBitmapStyle: function (bitmap, matrix, repeat, smooth) {
 37501           this.beginPath();
 37502           this._currentPath.lineStyle = createPatternStyle(bitmap, matrix, repeat, smooth);
 37503         },
 37504         lineGradientStyle: function (type, colors, alphas, ratios, matrix, spreadMethod, interpolationMethod, focalPos) {
 37505           var style = createGradientStyle(type, colors, alphas, ratios, matrix, spreadMethod, interpolationMethod, focalPos);
 37506           this.beginPath();
 37507           this._currentPath.lineStyle = style;
 37508         },
 37509         lineStyle: function (width, color, alpha, pxHinting, scale, cap, joint, mlimit) {
 37510           this.beginPath();
 37511           if (width) {
 37512             if (alpha === undefined)
 37513               alpha = 1;
 37514             if (mlimit === undefined)
 37515               mlimit = 3;
 37516             this._currentPath.lineStyle = {
 37517               style: rgbIntAlphaToStr(color, alpha),
 37518               lineCap: cap || 'round',
 37519               lineJoin: cap || 'round',
 37520               width: width * 20 | 0,
 37521               miterLimit: mlimit * 2
 37522             };
 37523           } else {
 37524             this._currentPath.lineStyle = null;
 37526         },
 37527         lineTo: function (x, y) {
 37528           this._invalidate();
 37529           this._currentPath.lineTo(x * 20 | 0, y * 20 | 0);
 37530         },
 37531         moveTo: function (x, y) {
 37532           this._currentPath.moveTo(x * 20 | 0, y * 20 | 0);
 37533         },
 37534         _getBounds: function (includeStroke) {
 37535           var bbox = includeStroke ? this.strokeBbox : this.bbox;
 37536           if (bbox) {
 37537             return bbox;
 37539           var subpaths = this._paths;
 37540           var xMins = [], yMins = [], xMaxs = [], yMaxs = [];
 37541           for (var i = 0, n = subpaths.length; i < n; i++) {
 37542             var path = subpaths[i];
 37543             if (path.commands.length) {
 37544               var b = path.getBounds(includeStroke);
 37545               if (b) {
 37546                 xMins.push(b.xMin);
 37547                 yMins.push(b.yMin);
 37548                 xMaxs.push(b.xMax);
 37549                 yMaxs.push(b.yMax);
 37553           if (xMins.length === 0) {
 37554             bbox = {
 37555               xMin: 0,
 37556               yMin: 0,
 37557               xMax: 0,
 37558               yMax: 0
 37559             };
 37560           } else {
 37561             bbox = {
 37562               xMin: Math.min.apply(Math, xMins),
 37563               yMin: Math.min.apply(Math, yMins),
 37564               xMax: Math.max.apply(Math, xMaxs),
 37565               yMax: Math.max.apply(Math, yMaxs)
 37566             };
 37568           if (includeStroke) {
 37569             this.strokeBbox = bbox;
 37570           } else {
 37571             this.bbox = bbox;
 37573           return bbox;
 37575       };
 37576     def.__glue__ = {
 37577       native: {
 37578         instance: {
 37579           beginFill: def.beginFill,
 37580           beginGradientFill: def.beginGradientFill,
 37581           beginBitmapFill: def.beginBitmapFill,
 37582           beginFillObject: def.beginFillObject,
 37583           beginStrokeObject: def.beginStrokeObject,
 37584           clear: def.clear,
 37585           copyFrom: def.copyFrom,
 37586           cubicCurveTo: def.cubicCurveTo,
 37587           curveTo: def.curveTo,
 37588           drawCircle: def.drawCircle,
 37589           drawEllipse: def.drawEllipse,
 37590           drawPath: def.drawPath,
 37591           drawRect: def.drawRect,
 37592           drawRoundRect: def.drawRoundRect,
 37593           drawRoundRectComplex: def.drawRoundRectComplex,
 37594           drawTriangles: def.drawTriangles,
 37595           endFill: def.endFill,
 37596           lineBitmapStyle: def.lineBitmapStyle,
 37597           lineGradientStyle: def.lineGradientStyle,
 37598           lineStyle: def.lineStyle,
 37599           moveTo: def.moveTo,
 37600           lineTo: def.lineTo
 37603     };
 37604     return def;
 37605   }.call(this);
 37606 function createPatternStyle(bitmap, matrix, repeat, smooth) {
 37607   var repeatStyle = repeat === false ? 'no-repeat' : 'repeat';
 37608   var pattern = factoryCtx.createPattern(bitmap._drawable, repeatStyle);
 37609   var transform = matrix ? {
 37610       a: matrix.a,
 37611       b: matrix.b,
 37612       c: matrix.c,
 37613       d: matrix.d,
 37614       e: matrix.tx,
 37615       f: matrix.ty
 37616     } : {
 37617       a: 1,
 37618       b: 0,
 37619       c: 0,
 37620       d: 1,
 37621       e: 0,
 37622       f: 0
 37623     };
 37624   return {
 37625     style: pattern,
 37626     transform: transform,
 37627     smooth: smooth
 37628   };
 37630 function createGradientStyle(type, colors, alphas, ratios, matrix, spreadMethod, interpolationMethod, focalPos) {
 37631   type === null || type === undefined && throwError('TypeError', Errors.NullPointerError, 'type');
 37632   colors === null || type === undefined && throwError('TypeError', Errors.NullPointerError, 'colors');
 37633   if (!(type === 'linear' || type === 'radial')) {
 37634     throwError('ArgumentError', Errors.InvalidEnumError, 'type');
 37636   var colorStops = [];
 37637   for (var i = 0, n = colors.length; i < n; i++) {
 37638     colorStops.push({
 37639       ratio: ratios[i] / 255,
 37640       color: rgbIntAlphaToStr(colors[i], alphas[i])
 37641     });
 37643   var gradientConstructor;
 37644   if (type === 'linear') {
 37645     gradientConstructor = buildLinearGradientFactory(colorStops);
 37646   } else {
 37647     gradientConstructor = buildRadialGradientFactory(focalPos || 0, colorStops);
 37649   var scale = 819.2;
 37650   var transform = matrix ? {
 37651       a: scale * matrix.a,
 37652       b: scale * matrix.b,
 37653       c: scale * matrix.c,
 37654       d: scale * matrix.d,
 37655       e: matrix.tx,
 37656       f: matrix.ty
 37657     } : {
 37658       a: scale,
 37659       b: 0,
 37660       c: 0,
 37661       d: scale,
 37662       e: 0,
 37663       f: 0
 37664     };
 37665   return {
 37666     style: gradientConstructor,
 37667     transform: transform
 37668   };
 37670 function drawGraphicsData(data) {
 37671   if (data === null) {
 37672     return;
 37674   for (var i = 0; i < data.length; i++) {
 37675     var item = data[i];
 37676     if (flash.display.IGraphicsPath.class.isInstanceOf(item)) {
 37677       this._drawPathObject(item);
 37678     } else if (flash.display.IGraphicsStroke.class.isInstanceOf(item)) {
 37679       this.beginStrokeObject(item);
 37680     } else if (flash.display.IGraphicsFill.class.isInstanceOf(item)) {
 37681       this.beginFillObject(item);
 37685 var InteractiveObjectDefinition = function () {
 37686     var def = {
 37687         initialize: function () {
 37688           this._contextMenu = null;
 37689           this._doubleClickEnabled = false;
 37690           this._focusRect = null;
 37691           this._mouseEnabled = true;
 37692           this._tabEnabled = false;
 37693         },
 37694         get accessibilityImplementation() {
 37695           return null;
 37696         },
 37697         set accessibilityImplementation(val) {
 37698           somewhatImplemented('accessibilityImplementation');
 37699         },
 37700         get contextMenu() {
 37701           somewhatImplemented('contextMenu');
 37702           return this._contextMenu;
 37703         },
 37704         set contextMenu(val) {
 37705           somewhatImplemented('contextMenu');
 37706           this._contextMenu = val;
 37707         },
 37708         get doubleClickEnabled() {
 37709           return this._doubleClickEnabled;
 37710         },
 37711         set doubleClickEnabled(val) {
 37712           this._doubleClickEnabled = val;
 37713         },
 37714         get focusRect() {
 37715           return this._focusRect;
 37716         },
 37717         set focusRect(val) {
 37718           this._focusRect = val;
 37719         },
 37720         get mouseEnabled() {
 37721           return this._mouseEnabled;
 37722         },
 37723         set mouseEnabled(val) {
 37724           this._mouseEnabled = val;
 37725         },
 37726         get needsSoftKeyboard() {
 37727           return false;
 37728         },
 37729         set needsSoftKeyboard(val) {
 37730           notImplemented();
 37731         },
 37732         get softKeyboardInputAreaOfInterest() {
 37733           return null;
 37734         },
 37735         set softKeyboardInputAreaOfInterest(val) {
 37736           notImplemented();
 37737         },
 37738         get tabEnabled() {
 37739           return this._tabEnabled;
 37740         },
 37741         set tabEnabled(val) {
 37742           var old = this._tabEnabled;
 37743           this._tabEnabled = val;
 37744           if (old !== val) {
 37745             var Event = flash.events.Event;
 37746             this._dispatchEvent(new Event('tabEnabledChange', false, false));
 37748         },
 37749         requestSoftKeyboard: function () {
 37750           notImplemented();
 37752       };
 37753     var desc = Object.getOwnPropertyDescriptor;
 37754     def.__glue__ = {
 37755       native: {
 37756         instance: {
 37757           tabEnabled: desc(def, 'tabEnabled'),
 37758           tabIndex: {
 37759             get: function tabIndex() {
 37760               return this._tabIndex;
 37761             },
 37762             set: function tabIndex(index) {
 37763               this._tabIndex = index;
 37765           },
 37766           focusRect: desc(def, 'focusRect'),
 37767           mouseEnabled: desc(def, 'mouseEnabled'),
 37768           doubleClickEnabled: desc(def, 'doubleClickEnabled'),
 37769           accessibilityImplementation: desc(def, 'accessibilityImplementation'),
 37770           softKeyboardInputAreaOfInterest: desc(def, 'softKeyboardInputAreaOfInterest'),
 37771           needsSoftKeyboard: desc(def, 'needsSoftKeyboard'),
 37772           contextMenu: desc(def, 'contextMenu'),
 37773           requestSoftKeyboard: def.requestSoftKeyboard
 37776     };
 37777     return def;
 37778   }.call(this);
 37779 var $RELEASE = false;
 37780 var LoaderDefinition = function () {
 37781     var WORKERS_ENABLED = true;
 37782     var LOADER_PATH = true ? 'shumway-worker.js' : 'swf/resourceloader.js';
 37783     var head = document.head;
 37784     head.insertBefore(document.createElement('style'), head.firstChild);
 37785     var style = document.styleSheets[0];
 37786     var def = {
 37787         __class__: 'flash.display.Loader',
 37788         initialize: function () {
 37789           this._contentLoaderInfo = new flash.display.LoaderInfo();
 37790           this._contentLoaderInfo._loader = this;
 37791           this._dictionary = {};
 37792           this._dictionaryResolved = {};
 37793           this._displayList = null;
 37794           this._timeline = [];
 37795           this._lastPromise = null;
 37796           this._uncaughtErrorEvents = null;
 37797           this._worker = null;
 37798           var abc = AVM2.currentAbc();
 37799           if (abc && abc.env.loader) {
 37800             this._contentLoaderInfo._loaderURL = abc.env.loader._contentLoaderInfo._url;
 37802         },
 37803         _commitData: function (data) {
 37804           switch (data.command) {
 37805           case 'init':
 37806             this._init(data.result);
 37807             break;
 37808           case 'progress':
 37809             this._updateProgress(data.result);
 37810             break;
 37811           case 'complete':
 37812             var frameConstructed = new Promise(function (resolve) {
 37813                 avm2.systemDomain.onMessage.register('frameConstructed', function waitForFrame(type) {
 37814                   if (type === 'frameConstructed') {
 37815                     resolve();
 37816                     avm2.systemDomain.onMessage.unregister('frameConstructed', waitForFrame);
 37818                 });
 37819               });
 37820             this._contentLoaderInfo._dispatchEvent('parsed');
 37821             Promise.all([
 37822               frameConstructed,
 37823               this._lastPromise
 37824             ]).then(function () {
 37825               this._content._complete = true;
 37826               this._contentLoaderInfo._dispatchEvent('complete');
 37827             }.bind(this));
 37828             var stats = data.stats;
 37829             if (stats) {
 37830               TelemetryService.reportTelemetry(stats);
 37832             this._worker && this._worker.terminate();
 37833             break;
 37834           case 'empty':
 37835             this._lastPromise = Promise.resolve();
 37836             break;
 37837           case 'error':
 37838             this._contentLoaderInfo._dispatchEvent('ioError', flash.events.IOErrorEvent);
 37839             break;
 37840           default:
 37841             if (data.id === 0)
 37842               break;
 37843             if (data.isSymbol)
 37844               this._commitSymbol(data);
 37845             else if (data.type === 'frame')
 37846               this._commitFrame(data);
 37847             else if (data.type === 'image')
 37848               this._commitImage(data);
 37849             break;
 37851         },
 37852         _updateProgress: function (state) {
 37853           var loaderInfo = this._contentLoaderInfo;
 37854           loaderInfo._bytesLoaded = state.bytesLoaded || 0;
 37855           loaderInfo._bytesTotal = state.bytesTotal || 0;
 37856           var event = new flash.events.ProgressEvent('progress', false, false, loaderInfo._bytesLoaded, loaderInfo._bytesTotal);
 37857           loaderInfo._dispatchEvent(event);
 37858         },
 37859         _buildFrame: function (currentDisplayList, timeline, promiseQueue, frame, frameNum) {
 37860           var loader = this;
 37861           var dictionary = loader._dictionary;
 37862           var dictionaryResolved = loader._dictionaryResolved;
 37863           var displayList = {};
 37864           var depths = [];
 37865           var cmds = frame.depths;
 37866           if (currentDisplayList) {
 37867             var currentDepths = currentDisplayList.depths;
 37868             for (var i = 0; i < currentDepths.length; i++) {
 37869               var depth = currentDepths[i];
 37870               if (cmds[depth] === null) {
 37871                 continue;
 37873               displayList[depth] = currentDisplayList[depth];
 37874               depths.push(depth);
 37877           for (var depth in cmds) {
 37878             var cmd = cmds[depth];
 37879             if (!cmd) {
 37880               continue;
 37882             if (cmd.move) {
 37883               var oldCmd = cmd;
 37884               cmd = cloneObject(currentDisplayList[depth]);
 37885               for (var prop in oldCmd) {
 37886                 var val = oldCmd[prop];
 37887                 if (val) {
 37888                   cmd[prop] = val;
 37892             if (cmd.symbolId) {
 37893               var itemPromise = dictionary[cmd.symbolId];
 37894               if (itemPromise && !dictionaryResolved[cmd.symbolId]) {
 37895                 promiseQueue.push(itemPromise);
 37897               cmd = cloneObject(cmd);
 37898               Object.defineProperty(cmd, 'symbolInfo', {
 37899                 get: function (dictionaryResolved, symbolId) {
 37900                   return function () {
 37901                     return dictionaryResolved[symbolId];
 37902                   };
 37903                 }(dictionaryResolved, cmd.symbolId)
 37904               });
 37906             if (!displayList[depth]) {
 37907               depths.push(depth);
 37909             displayList[depth] = cmd;
 37911           depths.sort(sortNumeric);
 37912           displayList.depths = depths;
 37913           var i = frame.repeat;
 37914           while (i--) {
 37915             timeline.push(displayList);
 37917           return displayList;
 37918         },
 37919         _commitFrame: function (frame) {
 37920           var abcBlocks = frame.abcBlocks;
 37921           var actionBlocks = frame.actionBlocks;
 37922           var initActionBlocks = frame.initActionBlocks;
 37923           var exports = frame.exports;
 37924           var symbolClasses = frame.symbolClasses;
 37925           var sceneData = frame.sceneData;
 37926           var loader = this;
 37927           var dictionary = loader._dictionary;
 37928           var loaderInfo = loader._contentLoaderInfo;
 37929           var timeline = loader._timeline;
 37930           var frameNum = timeline.length + 1;
 37931           var framePromiseResolve;
 37932           var framePromise = new Promise(function (resolve) {
 37933               framePromiseResolve = resolve;
 37934             });
 37935           var labelName = frame.labelName;
 37936           var prevPromise = this._lastPromise;
 37937           this._lastPromise = framePromise;
 37938           var promiseQueue = [
 37939               prevPromise
 37940             ];
 37941           this._displayList = this._buildFrame(this._displayList, timeline, promiseQueue, frame, frameNum);
 37942           var framesLoaded = timeline.length;
 37943           if (frame.bgcolor)
 37944             loaderInfo._backgroundColor = frame.bgcolor;
 37945           else if (isNullOrUndefined(loaderInfo._backgroundColor))
 37946             loaderInfo._backgroundColor = {
 37947               red: 255,
 37948               green: 255,
 37949               blue: 255,
 37950               alpha: 255
 37951             };
 37952           Promise.all(promiseQueue).then(function () {
 37953             if (abcBlocks && loader._isAvm2Enabled) {
 37954               var appDomain = avm2.applicationDomain;
 37955               for (var i = 0, n = abcBlocks.length; i < n; i++) {
 37956                 var abc = new AbcFile(abcBlocks[i].data, 'abc_block_' + i);
 37957                 abc.env.loader = loader;
 37958                 if (abcBlocks[i].flags) {
 37959                   appDomain.loadAbc(abc);
 37960                 } else {
 37961                   appDomain.executeAbc(abc);
 37965             if (symbolClasses && loader._isAvm2Enabled) {
 37966               var symbolClassesPromises = [];
 37967               for (var i = 0, n = symbolClasses.length; i < n; i++) {
 37968                 var asset = symbolClasses[i];
 37969                 var symbolPromise = dictionary[asset.symbolId];
 37970                 if (!symbolPromise)
 37971                   continue;
 37972                 symbolPromise.then(function (className) {
 37973                   return function symbolPromiseResolved(symbolInfo) {
 37974                     symbolInfo.className = className;
 37975                     avm2.applicationDomain.getClass(className).setSymbol(symbolInfo.props);
 37976                   };
 37977                 }(asset.className));
 37978                 symbolClassesPromises.push(symbolPromise);
 37980               return Promise.all(symbolClassesPromises);
 37982             if (exports && !loader._isAvm2Enabled) {
 37983               var exportPromises = [];
 37984               for (var i = 0, n = exports.length; i < n; i++) {
 37985                 var asset = exports[i];
 37986                 var symbolPromise = dictionary[asset.symbolId];
 37987                 if (!symbolPromise)
 37988                   continue;
 37989                 symbolPromise.then(function (className) {
 37990                   return function symbolPromiseResolved(symbolInfo) {
 37991                     loader._avm1Context.addAsset(className, symbolInfo.props);
 37992                   };
 37993                 }(asset.className));
 37994                 exportPromises.push(symbolPromise);
 37996               return Promise.all(exportPromises);
 37998           }).then(function () {
 37999             var root = loader._content;
 38000             var labelMap;
 38001             if (!root) {
 38002               var parent = loader._parent;
 38003               true;
 38004               var rootInfo = loader._dictionaryResolved[0];
 38005               var rootClass = avm2.applicationDomain.getClass(rootInfo.className);
 38006               root = rootClass.createAsSymbol({
 38007                 framesLoaded: framesLoaded,
 38008                 loader: loader,
 38009                 parent: parent || loader,
 38010                 index: parent ? 0 : -1,
 38011                 level: parent ? 0 : -1,
 38012                 timeline: timeline,
 38013                 totalFrames: rootInfo.props.totalFrames,
 38014                 stage: loader._stage,
 38015                 complete: frame.complete
 38016               });
 38017               if (!loader._isAvm2Enabled) {
 38018                 var avm1Context = loader._avm1Context;
 38019                 var _root = root;
 38020                 if (parent && parent !== loader._stage) {
 38021                   var parentLoader = parent.loaderInfo._loader;
 38022                   while (parentLoader._parent && parentLoader._parent !== loader._stage) {
 38023                     parentLoader = parentLoader._parent.loaderInfo._loader;
 38025                   if (parentLoader._isAvm2Enabled) {
 38026                     somewhatImplemented('AVM1Movie');
 38027                     this._worker && this._worker.terminate();
 38028                     return;
 38030                   _root = parentLoader._content;
 38032                 var as2Object = _root._getAS2Object();
 38033                 avm1Context.globals.asSetPublicProperty('_root', as2Object);
 38034                 avm1Context.globals.asSetPublicProperty('_level0', as2Object);
 38035                 avm1Context.globals.asSetPublicProperty('_level1', as2Object);
 38036                 var parameters = loader.loaderInfo._parameters;
 38037                 for (var paramName in parameters) {
 38038                   if (!(paramName in as2Object)) {
 38039                     as2Object[paramName] = parameters[paramName];
 38043               var isRootMovie = parent && parent == loader._stage && loader._stage._children.length === 0;
 38044               if (isRootMovie) {
 38045                 parent._frameRate = loaderInfo._frameRate;
 38046                 parent._stageHeight = loaderInfo._height;
 38047                 parent._stageWidth = loaderInfo._width;
 38048                 parent._root = root;
 38049                 parent._setup();
 38050               } else {
 38051                 loader._children.push(root);
 38053               var labels;
 38054               labelMap = root.symbol.labelMap = createEmptyObject();
 38055               if (sceneData) {
 38056                 var scenes = [];
 38057                 var startFrame;
 38058                 var endFrame = root.symbol.totalFrames - 1;
 38059                 var sd = sceneData.scenes;
 38060                 var ld = sceneData.labels;
 38061                 var i = sd.length;
 38062                 while (i--) {
 38063                   var s = sd[i];
 38064                   startFrame = s.offset;
 38065                   labels = [];
 38066                   var j = ld.length;
 38067                   while (j--) {
 38068                     var lbl = ld[j];
 38069                     if (lbl.frame >= startFrame && lbl.frame <= endFrame) {
 38070                       labelMap[lbl.name] = lbl.frame + 1;
 38071                       labels.unshift(new flash.display.FrameLabel(lbl.name, lbl.frame - startFrame + 1));
 38074                   var scene = new flash.display.Scene(s.name, labels, endFrame - startFrame + 1);
 38075                   scene._startFrame = startFrame + 1;
 38076                   scene._endFrame = endFrame + 1;
 38077                   scenes.unshift(scene);
 38078                   endFrame = startFrame - 1;
 38080                 root.symbol.scenes = scenes;
 38081               } else {
 38082                 labels = [];
 38083                 if (labelName) {
 38084                   labelMap[labelName] = frameNum;
 38085                   labels.push(new flash.display.FrameLabel(labelName, frameNum));
 38087                 var scene = new flash.display.Scene('Scene 1', labels, root.symbol.totalFrames);
 38088                 scene._startFrame = 1;
 38089                 scene._endFrame = root.symbol.totalFrames;
 38090                 root.symbol.scenes = [
 38091                   scene
 38092                 ];
 38094               if (loader._stage) {
 38095                 loader._stage._children[0] = root;
 38097               rootClass.instanceConstructor.call(root);
 38098               loader._content = root;
 38099             } else {
 38100               root._framesLoaded = framesLoaded;
 38101               if (labelName && root._labelMap) {
 38102                 if (root._labelMap[labelName] === undefined) {
 38103                   root._labelMap[labelName] = frameNum;
 38104                   for (var i = 0, n = root.symbol.scenes.length; i < n; i++) {
 38105                     var scene = root.symbol.scenes[i];
 38106                     if (frameNum >= scene._startFrame && frameNum <= scene._endFrame) {
 38107                       scene.labels.push(new flash.display.FrameLabel(labelName, frameNum - scene._startFrame));
 38108                       break;
 38114             if (frame.startSounds) {
 38115               root._registerStartSounds(frameNum, frame.startSounds);
 38117             if (frame.soundStream) {
 38118               root._initSoundStream(frame.soundStream);
 38120             if (frame.soundStreamBlock) {
 38121               root._addSoundStreamBlock(frameNum, frame.soundStreamBlock);
 38123             if (!loader._isAvm2Enabled) {
 38124               var avm1Context = loader._avm1Context;
 38125               if (initActionBlocks) {
 38126                 for (var i = 0; i < initActionBlocks.length; i++) {
 38127                   var spriteId = initActionBlocks[i].spriteId;
 38128                   var actionsData = initActionBlocks[i].actionsData;
 38129                   root.addFrameScript(frameNum - 1, function (actionsData, spriteId, state) {
 38130                     if (state.executed)
 38131                       return;
 38132                     state.executed = true;
 38133                     return executeActions(actionsData, avm1Context, this._getAS2Object());
 38134                   }.bind(root, actionsData, spriteId, {
 38135                     executed: false
 38136                   }));
 38139               if (actionBlocks) {
 38140                 for (var i = 0; i < actionBlocks.length; i++) {
 38141                   var block = actionBlocks[i];
 38142                   root.addFrameScript(frameNum - 1, function (block) {
 38143                     return function () {
 38144                       return executeActions(block, avm1Context, this._getAS2Object());
 38145                     };
 38146                   }(block));
 38150             if (frameNum === 1)
 38151               loaderInfo._dispatchEvent(new flash.events.Event('init', false, false));
 38152             framePromiseResolve(frame);
 38153           });
 38154         },
 38155         _commitImage: function (imageInfo) {
 38156           var loader = this;
 38157           var imgPromiseResolve;
 38158           var imgPromise = this._lastPromise = new Promise(function (resolve) {
 38159               imgPromiseResolve = resolve;
 38160             });
 38161           var img = new Image();
 38162           imageInfo.props.img = img;
 38163           img.onload = function () {
 38164             var Bitmap = avm2.systemDomain.getClass('flash.display.Bitmap');
 38165             var BitmapData = avm2.systemDomain.getClass('flash.display.BitmapData');
 38166             var props = imageInfo.props;
 38167             props.parent = loader._parent;
 38168             props.stage = loader._stage;
 38169             props.skipCopyToCanvas = true;
 38170             var bitmapData = BitmapData.createAsSymbol(props);
 38171             BitmapData.instanceConstructor.call(bitmapData, 0, 0, true, 4294967295);
 38172             var image = Bitmap.createAsSymbol(bitmapData);
 38173             Bitmap.instanceConstructor.call(image, bitmapData);
 38174             image._parent = loader;
 38175             loader._children.push(image);
 38176             loader._invalidateBounds();
 38177             loader._content = image;
 38178             imgPromiseResolve(imageInfo);
 38179             var loaderInfo = loader._contentLoaderInfo;
 38180             loaderInfo._width = image.width;
 38181             loaderInfo._height = image.height;
 38182             loaderInfo._dispatchEvent('init');
 38183           };
 38184           img.src = URL.createObjectURL(imageInfo.data);
 38185           imageInfo.data = null;
 38186         },
 38187         _commitSymbol: function (symbol) {
 38188           var dictionary = this._dictionary;
 38189           var dictionaryResolved = this._dictionaryResolved;
 38190           if ('updates' in symbol) {
 38191             dictionary[symbol.id].then(function (s) {
 38192               for (var i in symbol.updates) {
 38193                 s.props[i] = symbol.updates[i];
 38195             });
 38196             return;
 38198           var className = 'flash.display.DisplayObject';
 38199           var dependencies = symbol.require;
 38200           var promiseQueue = [];
 38201           var props = {
 38202               symbolId: symbol.id,
 38203               loader: this
 38204             };
 38205           var symbolPromiseResolve;
 38206           var symbolPromise = new Promise(function (resolve) {
 38207               symbolPromiseResolve = resolve;
 38208             });
 38209           if (dependencies && dependencies.length) {
 38210             for (var i = 0, n = dependencies.length; i < n; i++) {
 38211               var dependencyId = dependencies[i];
 38212               var dependencyPromise = dictionary[dependencyId];
 38213               if (dependencyPromise && !dictionaryResolved[dependencyId])
 38214                 promiseQueue.push(dependencyPromise);
 38217           switch (symbol.type) {
 38218           case 'button':
 38219             var states = {};
 38220             for (var stateName in symbol.states) {
 38221               var characters = [];
 38222               var displayList = {};
 38223               var state = symbol.states[stateName];
 38224               var depths = Object.keys(state);
 38225               for (var i = 0; i < depths.length; i++) {
 38226                 var depth = depths[i];
 38227                 var cmd = state[depth];
 38228                 var characterPromise = dictionary[cmd.symbolId];
 38229                 if (characterPromise && !dictionaryResolved[cmd.symbolId]) {
 38230                   promiseQueue.push(characterPromise);
 38232                 characters.push(characterPromise);
 38233                 displayList[depth] = Object.create(cmd, {
 38234                   symbolInfo: {
 38235                     get: function (dictionaryResolved, symbolId) {
 38236                       return function () {
 38237                         return dictionaryResolved[symbolId];
 38238                       };
 38239                     }(dictionaryResolved, cmd.symbolId)
 38241                 });
 38243               depths.sort(sortNumeric);
 38244               displayList.depths = depths;
 38245               states[stateName] = {
 38246                 className: 'flash.display.Sprite',
 38247                 props: {
 38248                   loader: this,
 38249                   timeline: [
 38250                     displayList
 38253               };
 38255             className = 'flash.display.SimpleButton';
 38256             props.states = states;
 38257             props.buttonActions = symbol.buttonActions;
 38258             break;
 38259           case 'font':
 38260             var charset = fromCharCode.apply(null, symbol.codes);
 38261             if (charset) {
 38262               style.insertRule('@font-face{font-family:"' + symbol.uniqueName + '";' + 'src:url(data:font/opentype;base64,' + btoa(symbol.data) + ')' + '}', style.cssRules.length);
 38263               if (!/Mozilla\/5.0.*?rv:(\d+).*? Gecko/.test(window.navigator.userAgent)) {
 38264                 var testDiv = document.createElement('div');
 38265                 testDiv.setAttribute('style', 'position: absolute; top: 0; right: 0;visibility: hidden; z-index: -500;font-family:"' + symbol.uniqueName + '";');
 38266                 testDiv.textContent = 'font test';
 38267                 document.body.appendChild(testDiv);
 38268                 var fontPromise = new Promise(function (resolve) {
 38269                     setTimeout(function () {
 38270                       resolve();
 38271                       document.body.removeChild(testDiv);
 38272                     }, 200);
 38273                   });
 38274                 promiseQueue.push(fontPromise);
 38277             className = 'flash.text.Font';
 38278             props.name = symbol.name;
 38279             props.uniqueName = symbol.uniqueName;
 38280             props.charset = symbol.charset;
 38281             props.bold = symbol.bold;
 38282             props.italic = symbol.italic;
 38283             props.metrics = symbol.metrics;
 38284             this._registerFont(className, props);
 38285             break;
 38286           case 'image':
 38287             var img = new Image();
 38288             var imgPromiseResolve;
 38289             var imgPromise = new Promise(function (resolve) {
 38290                 imgPromiseResolve = resolve;
 38291               });
 38292             img.onload = function () {
 38293               if (symbol.mask) {
 38294                 var maskCanvas = document.createElement('canvas');
 38295                 maskCanvas.width = symbol.width;
 38296                 maskCanvas.height = symbol.height;
 38297                 var maskContext = maskCanvas.getContext('2d');
 38298                 maskContext.drawImage(img, 0, 0);
 38299                 var maskImageData = maskContext.getImageData(0, 0, symbol.width, symbol.height);
 38300                 var maskImageDataBytes = maskImageData.data;
 38301                 var symbolMaskBytes = symbol.mask;
 38302                 var length = maskImageData.width * maskImageData.height;
 38303                 for (var i = 0, j = 3; i < length; i++, j += 4) {
 38304                   maskImageDataBytes[j] = symbolMaskBytes[i];
 38306                 maskContext.putImageData(maskImageData, 0, 0);
 38307                 props.img = maskCanvas;
 38309               imgPromiseResolve();
 38310             };
 38311             img.src = URL.createObjectURL(symbol.data);
 38312             promiseQueue.push(imgPromise);
 38313             className = 'flash.display.Bitmap';
 38314             props.img = img;
 38315             props.width = symbol.width;
 38316             props.height = symbol.height;
 38317             break;
 38318           case 'label':
 38319             var drawFn = new Function('c,r,ct', symbol.data);
 38320             className = 'flash.text.StaticText';
 38321             props.bbox = symbol.bbox;
 38322             props.draw = drawFn;
 38323             break;
 38324           case 'text':
 38325             props.bbox = symbol.bbox;
 38326             props.html = symbol.html;
 38327             if (symbol.type === 'label') {
 38328               className = 'flash.text.StaticText';
 38329             } else {
 38330               className = 'flash.text.TextField';
 38331               props.tag = symbol.tag;
 38332               props.variableName = symbol.variableName;
 38334             break;
 38335           case 'shape':
 38336             className = symbol.morph ? 'flash.display.MorphShape' : 'flash.display.Shape';
 38337             props.bbox = symbol.bbox;
 38338             props.strokeBbox = symbol.strokeBbox;
 38339             props.paths = symbol.paths;
 38340             props.dictionaryResolved = dictionaryResolved;
 38341             break;
 38342           case 'sound':
 38343             if (!symbol.pcm && !PLAY_USING_AUDIO_TAG) {
 38344               var decodePromiseResolve;
 38345               var decodePromise = new Promise(function (resolve) {
 38346                   decodePromiseResolve = resolve;
 38347                 });
 38348               MP3DecoderSession.processAll(symbol.packaged.data, function (props, pcm, id3tags, error) {
 38349                 props.pcm = pcm || new Uint8Array(0);
 38350                 decodePromiseResolve();
 38351                 if (error) {
 38352                   console.error('ERROR: ' + error);
 38354               }.bind(null, props));
 38355               promiseQueue.push(decodePromise);
 38357             className = 'flash.media.Sound';
 38358             props.sampleRate = symbol.sampleRate;
 38359             props.channels = symbol.channels;
 38360             props.pcm = symbol.pcm;
 38361             props.packaged = symbol.packaged;
 38362             break;
 38363           case 'binary':
 38364             props.data = symbol.data;
 38365             break;
 38366           case 'sprite':
 38367             var displayList = null;
 38368             var frameCount = symbol.frameCount;
 38369             var labelMap = {};
 38370             var frameNum = 1;
 38371             var frames = symbol.frames;
 38372             var timeline = [];
 38373             var startSoundRegistrations = [];
 38374             for (var i = 0, n = frames.length; i < n; i++) {
 38375               var frame = frames[i];
 38376               var frameNum = timeline.length + 1;
 38377               if (frame.labelName) {
 38378                 labelMap[frame.labelName] = frameNum;
 38380               if (frame.startSounds) {
 38381                 startSoundRegistrations[frameNum] = frame.startSounds;
 38382                 for (var j = 0; j < frame.startSounds.length; j++) {
 38383                   var soundId = frame.startSounds[j].soundId;
 38384                   var itemPromise = dictionary[soundId];
 38385                   if (itemPromise && !dictionaryResolved[soundId]) {
 38386                     promiseQueue.push(itemPromise);
 38390               displayList = this._buildFrame(displayList, timeline, promiseQueue, frame, frameNum);
 38392             var frameScripts = {};
 38393             if (!this._isAvm2Enabled) {
 38394               if (symbol.frameScripts) {
 38395                 var data = symbol.frameScripts;
 38396                 for (var i = 0; i < data.length; i += 2) {
 38397                   var frameNum = data[i] + 1;
 38398                   var block = data[i + 1];
 38399                   var script = function (block, loader) {
 38400                       return function () {
 38401                         var avm1Context = loader._avm1Context;
 38402                         return executeActions(block, avm1Context, this._getAS2Object());
 38403                       };
 38404                     }(block, this);
 38405                   if (!frameScripts[frameNum])
 38406                     frameScripts[frameNum] = [
 38407                       script
 38408                     ];
 38409                   else
 38410                     frameScripts[frameNum].push(script);
 38414             className = 'flash.display.MovieClip';
 38415             props.timeline = timeline;
 38416             props.framesLoaded = frameCount;
 38417             props.labelMap = labelMap;
 38418             props.frameScripts = frameScripts;
 38419             props.totalFrames = frameCount;
 38420             props.startSoundRegistrations = startSoundRegistrations;
 38421             break;
 38423           dictionary[symbol.id] = symbolPromise;
 38424           Promise.all(promiseQueue).then(function () {
 38425             var symbolInfo = {
 38426                 className: className,
 38427                 props: props
 38428               };
 38429             dictionaryResolved[symbol.id] = symbolInfo;
 38430             symbolPromiseResolve(symbolInfo);
 38431           });
 38432         },
 38433         _registerFont: function (className, props) {
 38434           this._vmPromise.then(function () {
 38435             var fontClass = avm2.applicationDomain.getClass(className);
 38436             var font = fontClass.createAsSymbol(props);
 38437             fontClass.instanceConstructor.call(font);
 38438           });
 38439         },
 38440         _init: function (info) {
 38441           var loader = this;
 38442           var loaderInfo = loader._contentLoaderInfo;
 38443           loaderInfo._swfVersion = info.swfVersion;
 38444           var bbox = info.bbox;
 38445           loaderInfo._width = bbox.xMax - bbox.xMin;
 38446           loaderInfo._height = bbox.yMax - bbox.yMin;
 38447           loaderInfo._frameRate = info.frameRate;
 38448           var vmPromiseResolve, vmPromiseReject;
 38449           var vmPromise = new Promise(function (resolve, reject) {
 38450               vmPromiseResolve = resolve;
 38451               vmPromiseReject = reject;
 38452             });
 38453           vmPromise.resolve = vmPromiseResolve;
 38454           vmPromise.reject = vmPromiseReject;
 38455           var documentPromise = new Promise(function (resolve) {
 38456               vmPromise.then(function () {
 38457                 var rootInfo = {
 38458                     className: 'flash.display.MovieClip',
 38459                     props: {
 38460                       totalFrames: info.frameCount
 38462                   };
 38463                 loader._dictionaryResolved[0] = rootInfo;
 38464                 resolve(rootInfo);
 38465               });
 38466             });
 38467           loader._dictionary[0] = documentPromise;
 38468           loader._lastPromise = documentPromise;
 38469           loader._vmPromise = vmPromise;
 38470           loader._isAvm2Enabled = info.fileAttributes.doAbc;
 38471           this._setup();
 38472         },
 38473         _load: function (request, checkPolicyFile, applicationDomain, securityDomain, requestedContentParent, parameters, deblockingFilter, allowCodeImport, imageDecodingPolicy) {
 38474           if (flash.net.URLRequest.class.isInstanceOf(request)) {
 38475             this._contentLoaderInfo._url = request._url;
 38477           var worker;
 38478           if (WORKERS_ENABLED) {
 38479             worker = new Worker(SHUMWAY_ROOT + LOADER_PATH);
 38480           } else {
 38481             worker = new ResourceLoader(window);
 38483           var loader = this;
 38484           loader._worker = worker;
 38485           worker.onmessage = function (evt) {
 38486             if (evt.data.type === 'exception') {
 38487               avm2.exceptions.push({
 38488                 source: 'parser',
 38489                 message: evt.data.message,
 38490                 stack: evt.data.stack
 38491               });
 38492             } else {
 38493               loader._commitData(evt.data);
 38495           };
 38496           if (flash.net.URLRequest.class.isInstanceOf(request)) {
 38497             var session = FileLoadingService.createSession();
 38498             session.onprogress = function (data, progress) {
 38499               worker.postMessage({
 38500                 data: data,
 38501                 progress: progress
 38502               });
 38503             };
 38504             session.onerror = function (error) {
 38505               loader._commitData({
 38506                 command: 'error',
 38507                 error: error
 38508               });
 38509             };
 38510             session.onopen = function () {
 38511               worker.postMessage('pipe:');
 38512             };
 38513             session.onclose = function () {
 38514               worker.postMessage({
 38515                 data: null
 38516               });
 38517             };
 38518             session.open(request._toFileRequest());
 38519           } else {
 38520             worker.postMessage(request);
 38522         },
 38523         _setup: function () {
 38524           var loader = this;
 38525           var stage = loader._stage;
 38526           if (loader._isAvm2Enabled) {
 38527             var mouseClass = avm2.systemDomain.getClass('flash.ui.Mouse');
 38528             mouseClass._stage = stage;
 38529             loader._vmPromise.resolve();
 38530             return;
 38532           if (!avm2.loadAVM1) {
 38533             loader._vmPromise.reject('AVM1 loader is not found');
 38534             return;
 38536           var loaded = function () {
 38537             var loaderInfo = loader._contentLoaderInfo;
 38538             var avm1Context = new AS2Context(loaderInfo._swfVersion);
 38539             avm1Context.stage = stage;
 38540             loader._avm1Context = avm1Context;
 38541             avm1lib.AS2Key.class.$bind(stage);
 38542             avm1lib.AS2Mouse.class.$bind(stage);
 38543             stage._addEventListener('frameConstructed', avm1Context.flushPendingScripts.bind(avm1Context), false, Number.MAX_VALUE);
 38544             loader._vmPromise.resolve();
 38545           };
 38546           if (avm2.isAVM1Loaded) {
 38547             if (AS2Context.instance) {
 38548               loader._avm1Context = AS2Context.instance;
 38549               loader._vmPromise.resolve();
 38550             } else {
 38551               loaded();
 38553           } else {
 38554             avm2.isAVM1Loaded = true;
 38555             avm2.loadAVM1(loaded);
 38557         },
 38558         get contentLoaderInfo() {
 38559           return this._contentLoaderInfo;
 38560         },
 38561         get content() {
 38562           somewhatImplemented('Loader.content');
 38563           return this._content;
 38565       };
 38566     def.__glue__ = {
 38567       native: {
 38568         instance: {
 38569           content: Object.getOwnPropertyDescriptor(def, 'content'),
 38570           contentLoaderInfo: Object.getOwnPropertyDescriptor(def, 'contentLoaderInfo'),
 38571           _getJPEGLoaderContextdeblockingfilter: function (context) {
 38572             return 0;
 38573           },
 38574           _load: def._load,
 38575           _loadBytes: function _loadBytes(bytes, checkPolicyFile, applicationDomain, securityDomain, requestedContentParent, parameters, deblockingFilter, allowLoadBytesCodeExecution, imageDecodingPolicy) {
 38576             this._load(bytes.a, checkPolicyFile, applicationDomain, securityDomain, requestedContentParent, parameters, deblockingFilter, allowLoadBytesCodeExecution, imageDecodingPolicy);
 38577           },
 38578           _unload: function _unload(halt, gc) {
 38579             somewhatImplemented('Loader._unload, do we even need to do anything here?');
 38580           },
 38581           _close: function _close() {
 38582             somewhatImplemented('Loader._close');
 38583           },
 38584           _getUncaughtErrorEvents: function _getUncaughtErrorEvents() {
 38585             somewhatImplemented('Loader._getUncaughtErrorEvents');
 38586             return this._uncaughtErrorEvents;
 38587           },
 38588           _setUncaughtErrorEvents: function _setUncaughtErrorEvents(value) {
 38589             somewhatImplemented('Loader._setUncaughtErrorEvents');
 38590             this._uncaughtErrorEvents = value;
 38594     };
 38595     return def;
 38596   }.call(this);
 38597 var LoaderInfoDefinition = function () {
 38598     function dispatchEvent(event) {
 38599       notImplemented('LoaderInfo.dispatchEvent');
 38601     return {
 38602       __class__: 'flash.display.LoaderInfo',
 38603       initialize: function () {
 38604         this._actionScriptVersion = null;
 38605         this._backgroundColor = null;
 38606         this._bytes = null;
 38607         this._bytesLoaded = 0;
 38608         this._bytesTotal = 0;
 38609         this._content = null;
 38610         this._contentType = null;
 38611         this._frameRate = null;
 38612         this._height = null;
 38613         this._loader = null;
 38614         this._loaderURL = null;
 38615         this._swfVersion = null;
 38616         this._url = null;
 38617         this._width = null;
 38618         this._uncaughtErrorEvents = null;
 38619       },
 38620       __glue__: {
 38621         native: {
 38622           static: {
 38623             getLoaderInfoByDefinition: function getLoaderInfoByDefinition(object) {
 38624               notImplemented('LoaderInfo.getLoaderInfoByDefinition');
 38626           },
 38627           instance: {
 38628             _getArgs: function _getArgs() {
 38629               var params = this._parameters;
 38630               var mangled = {};
 38631               for (var k in params) {
 38632                 mangled[Multiname.getPublicQualifiedName(k)] = params[k];
 38634               return mangled;
 38635             },
 38636             _getUncaughtErrorEvents: function _getUncaughtErrorEvents() {
 38637               somewhatImplemented('Loader._getUncaughtErrorEvents');
 38638               return this._uncaughtErrorEvents;
 38639             },
 38640             _setUncaughtErrorEvents: function _setUncaughtErrorEvents(value) {
 38641               somewhatImplemented('Loader._setUncaughtErrorEvents');
 38642               this._uncaughtErrorEvents = value;
 38643             },
 38644             loaderURL: {
 38645               get: function loaderURL() {
 38646                 return this._loaderURL;
 38648             },
 38649             url: {
 38650               get: function url() {
 38651                 return this._url;
 38653             },
 38654             isURLInaccessible: {
 38655               get: function isURLInaccessible() {
 38656                 return this._isURLInaccessible;
 38658             },
 38659             bytesLoaded: {
 38660               get: function bytesLoaded() {
 38661                 return this._bytesLoaded;
 38663             },
 38664             bytesTotal: {
 38665               get: function bytesTotal() {
 38666                 return this._bytesTotal;
 38668             },
 38669             applicationDomain: {
 38670               get: function applicationDomain() {
 38671                 return new flash.system.ApplicationDomain(avm2.applicationDomain);
 38673             },
 38674             swfVersion: {
 38675               get: function swfVersion() {
 38676                 return this._swfVersion;
 38678             },
 38679             actionScriptVersion: {
 38680               get: function actionScriptVersion() {
 38681                 return this._actionScriptVersion;
 38683             },
 38684             frameRate: {
 38685               get: function frameRate() {
 38686                 return this._frameRate;
 38688             },
 38689             width: {
 38690               get: function width() {
 38691                 return this._width;
 38693             },
 38694             height: {
 38695               get: function height() {
 38696                 return this._height;
 38698             },
 38699             contentType: {
 38700               get: function contentType() {
 38701                 return this._contentType;
 38703             },
 38704             sharedEvents: {
 38705               get: function sharedEvents() {
 38706                 return this._sharedEvents;
 38708             },
 38709             parentSandboxBridge: {
 38710               get: function parentSandboxBridge() {
 38711                 return this._parentSandboxBridge;
 38712               },
 38713               set: function parentSandboxBridge(door) {
 38714                 this._parentSandboxBridge = door;
 38716             },
 38717             childSandboxBridge: {
 38718               get: function childSandboxBridge() {
 38719                 return this._childSandboxBridge;
 38720               },
 38721               set: function childSandboxBridge(door) {
 38722                 this._childSandboxBridge = door;
 38724             },
 38725             sameDomain: {
 38726               get: function sameDomain() {
 38727                 return this._sameDomain;
 38729             },
 38730             childAllowsParent: {
 38731               get: function childAllowsParent() {
 38732                 return this._childAllowsParent;
 38734             },
 38735             parentAllowsChild: {
 38736               get: function parentAllowsChild() {
 38737                 return this._parentAllowsChild;
 38739             },
 38740             loader: {
 38741               get: function loader() {
 38742                 return this._loader;
 38744             },
 38745             content: {
 38746               get: function content() {
 38747                 return this._loader._content;
 38749             },
 38750             bytes: {
 38751               get: function bytes() {
 38752                 return this._bytes;
 38756         },
 38757         script: {
 38758           instance: scriptProperties('public', [
 38759             'swfVersion',
 38760             'bytesTotal',
 38761             'bytesLoaded',
 38762             'parameters',
 38763             'uncaughtErrorEvent'
 38764           ])
 38767     };
 38768   }.call(this);
 38769 var MorphShapeDefinition = function () {
 38770     var def = {
 38771         __class__: 'flash.display.MorphShape',
 38772         initialize: function () {
 38773           var graphics = this._graphics = new flash.display.Graphics();
 38774           var s = this.symbol;
 38775           if (s && s.paths) {
 38776             graphics._paths = s.paths;
 38777             graphics.bbox = s.bbox;
 38778             graphics.strokeBbox = s.strokeBbox;
 38779             if (this._stage && this._stage._quality === 'low' && !graphics._bitmap)
 38780               graphics._cacheAsBitmap(this._bbox);
 38783       };
 38784     def.__glue__ = {
 38785       native: {
 38786         instance: {
 38787           graphics: {
 38788             get: function () {
 38789               return this._graphics;
 38794     };
 38795     return def;
 38796   }.call(this);
 38797 var MovieClipDefinition = function () {
 38798     var def = {
 38799         __class__: 'flash.display.MovieClip',
 38800         initialize: function () {
 38801           this._playHead = 1;
 38802           this._currentFrame = 1;
 38803           this._currentFrameLabel = null;
 38804           this._currentLabel = null;
 38805           this._currentScene = 0;
 38806           this._enabled = true;
 38807           this._frameScripts = {};
 38808           this._framesLoaded = 1;
 38809           this._isPlaying = false;
 38810           this._labelMap = {};
 38811           this._sceneFrameMap = {};
 38812           this._sceneMap = {};
 38813           this._scenes = null;
 38814           this._timeline = null;
 38815           this._totalFrames = 1;
 38816           this._startSoundRegistrations = [];
 38817           this._allowFrameNavigation = true;
 38818           this._complete = true;
 38819           var s = this.symbol;
 38820           if (s) {
 38821             this._timeline = s.timeline || null;
 38822             this._framesLoaded = s.framesLoaded || 1;
 38823             this._labelMap = Object.create(s.labelMap || null);
 38824             this._frameScripts = Object.create(s.frameScripts || null);
 38825             this._totalFrames = s.totalFrames || 1;
 38826             this._startSoundRegistrations = s.startSoundRegistrations || [];
 38827             this._scenes = s.scenes || null;
 38828             this._complete = s.complete === false ? false : true;
 38829             var map = this._labelMap;
 38830             for (var name in map) {
 38831               var frame = map[name];
 38832               if (frame == 1) {
 38833                 this._currentFrameLabel = this._currentLabel = name;
 38837           this._enterFrame(1);
 38838           var self = this;
 38839           this._onExecuteFrame = function onExecuteFrame() {
 38840             self._removeEventListener('executeFrame', onExecuteFrame);
 38841             self._allowFrameNavigation = false;
 38842             self._callFrame(self._currentFrame);
 38843             self._allowFrameNavigation = true;
 38844             if (self._playHead !== self._currentFrame) {
 38845               self._gotoFrame(self._playHead, true);
 38847             self._postConstructChildren();
 38848           };
 38849           this._addEventListener('executeFrame', this._onExecuteFrame);
 38850           if (this._complete && this._totalFrames <= 1) {
 38851             return this;
 38853           this._onAdvanceFrame = function onAdvanceFrame() {
 38854             var frameNum = self._playHead + 1;
 38855             if (self._complete && frameNum > self._totalFrames) {
 38856               frameNum = 1;
 38857             } else if (frameNum > self._framesLoaded) {
 38858               return;
 38860             self._updateDisplayList(frameNum);
 38861             if (self._sparse) {
 38862               self._addEventListener('constructChildren', self._onConstructChildren);
 38864             self._startSounds(frameNum);
 38865             self._enterFrame(frameNum);
 38866             if (frameNum in self._frameScripts) {
 38867               self._addEventListener('executeFrame', self._onExecuteFrame);
 38869           };
 38870           this._onConstructChildren = function onConstructChildren() {
 38871             self._removeEventListener('constructChildren', onConstructChildren);
 38872             self._constructChildren();
 38873           };
 38874           this.play();
 38875         },
 38876         _updateDisplayList: function (nextFrameNum) {
 38877           this._destructChildren(nextFrameNum);
 38878           this._declareChildren(nextFrameNum);
 38879         },
 38880         _declareChildren: function declareChildren(nextFrameNum) {
 38881           var currentFrame = this._currentFrame;
 38882           if (nextFrameNum === currentFrame) {
 38883             return;
 38885           var timeline = this._timeline;
 38886           var nextDisplayList = timeline[nextFrameNum - 1];
 38887           if (nextDisplayList === timeline[currentFrame - 1]) {
 38888             return;
 38890           var prevDisplayListItem = null;
 38891           var currentDisplayListItem = this._currentDisplayList;
 38892           var children = this._children;
 38893           var depths = nextDisplayList.depths;
 38894           var index = children.length;
 38895           var i = depths.length;
 38896           while (i--) {
 38897             var depth = depths[i], depthInt = depth | 0;
 38898             while (currentDisplayListItem && currentDisplayListItem.depth > depthInt) {
 38899               prevDisplayListItem = currentDisplayListItem;
 38900               currentDisplayListItem = currentDisplayListItem.next;
 38902             var currentChild = null;
 38903             if (currentDisplayListItem && currentDisplayListItem.depth === depthInt) {
 38904               currentChild = currentDisplayListItem.obj;
 38905               if (currentChild && currentChild._owned) {
 38906                 index = this.getChildIndex(currentChild);
 38909             var currentCmd = currentDisplayListItem && currentDisplayListItem.depth === depthInt ? currentDisplayListItem.cmd : null;
 38910             var nextCmd = nextDisplayList[depth];
 38911             if (!nextCmd || nextCmd === currentCmd) {
 38912               continue;
 38914             if (currentCmd && currentChild && nextCmd.symbolId === currentCmd.symbolId && nextCmd.ratio === currentCmd.ratio) {
 38915               if (currentChild._animated) {
 38916                 currentChild._invalidate();
 38917                 if (nextCmd.hasMatrix) {
 38918                   currentChild._setTransformMatrix(nextCmd.matrix, false);
 38920                 if (nextCmd.hasCxform) {
 38921                   currentChild._cxform = nextCmd.cxform;
 38923                 if (nextCmd.clip) {
 38924                   currentChild._clipDepth = nextCmd.clipDepth;
 38926                 if (nextCmd.hasName) {
 38927                   currentChild.name = nextCmd.name;
 38929                 if (nextCmd.blend) {
 38930                   currentChild._blendMode = this._resolveBlendMode(nextCmd.blendMode);
 38933               currentDisplayListItem.cmd = nextCmd;
 38934               continue;
 38936             var newDisplayListItem = this._addTimelineChild(nextCmd, index);
 38937             newDisplayListItem.next = currentDisplayListItem;
 38938             if (prevDisplayListItem) {
 38939               prevDisplayListItem.next = newDisplayListItem;
 38940             } else {
 38941               this._currentDisplayList = newDisplayListItem;
 38943             prevDisplayListItem = newDisplayListItem;
 38945         },
 38946         _destructChildren: function destructChildren(nextFrameNum) {
 38947           var currentFrame = this._currentFrame;
 38948           if (nextFrameNum === currentFrame) {
 38949             return;
 38951           var timeline = this._timeline;
 38952           var nextDisplayList = timeline[nextFrameNum - 1];
 38953           if (nextDisplayList === timeline[currentFrame - 1]) {
 38954             return;
 38956           var prevEntry = null;
 38957           var currentEntry = this._currentDisplayList;
 38958           var toRemove = null;
 38959           while (currentEntry) {
 38960             var depth = currentEntry.depth;
 38961             var currentCmd = currentEntry.cmd;
 38962             var nextCmd = nextDisplayList[depth];
 38963             if (!nextCmd || nextCmd.symbolId !== currentCmd.symbolId || nextCmd.ratio !== currentCmd.ratio) {
 38964               var nextDisplayListItem = currentEntry.next;
 38965               if (prevEntry) {
 38966                 prevEntry.next = nextDisplayListItem;
 38967               } else {
 38968                 this._currentDisplayList = nextDisplayListItem;
 38970               currentEntry.next = toRemove;
 38971               toRemove = currentEntry;
 38972               currentEntry = nextDisplayListItem;
 38973             } else {
 38974               prevEntry = currentEntry;
 38975               currentEntry = currentEntry.next;
 38978           while (toRemove) {
 38979             var child = toRemove.obj;
 38980             if (child && child._owned) {
 38981               this._sparse = true;
 38982               this.removeChild(child);
 38983               child.destroy();
 38984               if (child._isPlaying) {
 38985                 child.stop();
 38988             toRemove = toRemove.next;
 38990         },
 38991         _gotoFrame: function gotoFrame(frameNum, execute) {
 38992           var enterFrame = frameNum !== this._currentFrame;
 38993           if (this._allowFrameNavigation || !this._loader._isAvm2Enabled) {
 38994             if (enterFrame) {
 38995               this._updateDisplayList(frameNum);
 38996               this._enterFrame(frameNum);
 38998             this._constructChildren();
 38999             if (this._loader._isAvm2Enabled && this.loaderInfo._swfVersion >= 10) {
 39000               if (enterFrame) {
 39001                 this._addEventListener('executeFrame', this._onExecuteFrame);
 39003               var domain = avm2.systemDomain;
 39004               domain.broadcastMessage('frameConstructed');
 39005               domain.broadcastMessage('executeFrame');
 39006               domain.broadcastMessage('exitFrame');
 39007               return;
 39009             if (enterFrame && (execute || !this._loader._isAvm2Enabled)) {
 39010               this._callFrame(frameNum);
 39012             this._postConstructChildren();
 39013             return;
 39015           if (enterFrame) {
 39016             this._playHead = frameNum;
 39018         },
 39019         _enterFrame: function navigate(frameNum) {
 39020           if (frameNum === this._currentFrame) {
 39021             return;
 39023           this._currentFrameLabel = null;
 39024           if (frameNum === 1) {
 39025             this._currentLabel = null;
 39027           var map = this._labelMap;
 39028           for (var name in map) {
 39029             if (map[name] === frameNum) {
 39030               this._currentFrameLabel = this._currentLabel = name;
 39031               break;
 39034           if (this._scenes) {
 39035             var scenes = this._scenes;
 39036             for (var j = 0, n = scenes.length; j < n; j++) {
 39037               var scene = scenes[j];
 39038               if (frameNum >= scene._startFrame && frameNum <= scene._endFrame) {
 39039                 this._currentScene = j;
 39040                 break;
 39044           this._playHead = this._currentFrame = frameNum;
 39045         },
 39046         _callFrame: function callFrame(frame) {
 39047           if (isNaN(frame)) {
 39048             frame = this._labelMap[frame];
 39049             if (frame === undefined) {
 39050               return;
 39053           if (frame in this._frameScripts) {
 39054             var scripts = this._frameScripts[frame];
 39055             try {
 39056               for (var i = 0, n = scripts.length; i < n; i++) {
 39057                 scripts[i].call(this);
 39059             } catch (e) {
 39060               var AVM2_ERROR_TYPE = 2;
 39061               TelemetryService.reportTelemetry({
 39062                 topic: 'error',
 39063                 error: AVM2_ERROR_TYPE
 39064               });
 39065               if (false) {
 39066                 console.error('error ' + e + ', stack: \n' + e.stack);
 39068               this.stop();
 39069               throw e;
 39072         },
 39073         _gotoButtonState: function gotoButtonState(stateName) {
 39074           if (this._enabled) {
 39075             this.gotoLabel('_' + stateName);
 39077         },
 39078         _getAbsFrameNum: function (frameNum, sceneName) {
 39079           if (frameNum < 1) {
 39080             frameNum = 1;
 39082           if (sceneName && this._scenes && this._scenes.length > 1) {
 39083             var scenes = this._scenes;
 39084             for (var i = 0; i < scenes.length; i++) {
 39085               var scene = scenes[i];
 39086               if (scene.name === sceneName) {
 39087                 frameNum += scene._startFrame - 1;
 39088                 if (frameNum > scene._endFrame) {
 39089                   frameNum = scene._endFrame;
 39091                 break;
 39095           if (frameNum > this._framesLoaded) {
 39096             return this._framesLoaded;
 39098           return frameNum;
 39099         },
 39100         _registerStartSounds: function (frameNum, starts) {
 39101           this._startSoundRegistrations[frameNum] = starts;
 39102         },
 39103         _initSoundStream: function (streamInfo) {
 39104           this._soundStream = new MovieClipSoundStream(streamInfo, this);
 39105         },
 39106         _addSoundStreamBlock: function (frameNum, streamBlock) {
 39107           this._soundStream.appendBlock(frameNum, streamBlock);
 39108         },
 39109         _startSounds: function (frameNum) {
 39110           var starts = this._startSoundRegistrations[frameNum];
 39111           if (starts) {
 39112             var sounds = this._sounds || (this._sounds = {});
 39113             var loader = this.loaderInfo._loader;
 39114             for (var i = 0; i < starts.length; i++) {
 39115               var start = starts[i];
 39116               var symbolId = start.soundId;
 39117               var info = start.soundInfo;
 39118               var sound = sounds[symbolId];
 39119               if (!sound) {
 39120                 var symbolInfo = loader._dictionaryResolved[symbolId];
 39121                 if (!symbolInfo)
 39122                   continue;
 39123                 var symbolClass = avm2.systemDomain.findClass(symbolInfo.className) ? avm2.systemDomain.getClass(symbolInfo.className) : avm2.applicationDomain.getClass(symbolInfo.className);
 39124                 var soundObj = symbolClass.createAsSymbol(symbolInfo.props);
 39125                 symbolClass.instanceConstructor.call(soundObj);
 39126                 sounds[symbolId] = sound = {
 39127                   object: soundObj
 39128                 };
 39130               if (sound.channel) {
 39131                 sound.channel.stop();
 39132                 sound.channel = null;
 39134               if (!info.stop) {
 39135                 var loops = info.hasLoops ? info.loopCount : 0;
 39136                 sound.channel = sound.object.play(0, loops);
 39140           if (this._soundStream) {
 39141             this._soundStream.playFrame(frameNum);
 39143         },
 39144         _getAS2Object: function () {
 39145           if (!this.$as2Object) {
 39146             if (this._avm1SymbolClass) {
 39147               var nativeObject = this, nativeObjectClass = this._avm1SymbolClass;
 39148               var constructWrapper = function () {
 39149                 this.init(nativeObject);
 39150                 nativeObjectClass.call(this);
 39151               };
 39152               constructWrapper.prototype = Object.create(nativeObjectClass.prototype);
 39153               constructWrapper.instanceConstructor = constructWrapper;
 39154               constructWrapper.debugName = 'avm1 <symbol constructor wrapper>';
 39155               construct(constructWrapper);
 39156             } else {
 39157               new avm1lib.AS2MovieClip(this);
 39160           return this.$as2Object;
 39161         },
 39162         get currentFrame() {
 39163           var frameNum = this._currentFrame;
 39164           return this._scenes ? frameNum - this.currentScene._startFrame + 1 : frameNum;
 39165         },
 39166         get currentFrameLabel() {
 39167           return this._currentFrameLabel;
 39168         },
 39169         get currentLabel() {
 39170           return this._currentLabel;
 39171         },
 39172         get currentLabels() {
 39173           if (this._scenes) {
 39174             return this._scenes[this._currentScene].labels;
 39175           } else {
 39176             var labels = [];
 39177             var map = this._labelMap;
 39178             for (var name in map) {
 39179               labels.push(new flash.display.FrameLabel(name, map[name]));
 39181             return labels;
 39183         },
 39184         get currentScene() {
 39185           return this._scenes ? this._scenes[this._currentScene] : new flash.display.Scene('', this.currentLabels, this._framesLoaded);
 39186         },
 39187         get enabled() {
 39188           return this._enabled;
 39189         },
 39190         set enabled(val) {
 39191           this._enabled = val;
 39192         },
 39193         get framesLoaded() {
 39194           return this._framesLoaded;
 39195         },
 39196         get totalFrames() {
 39197           return this._totalFrames;
 39198         },
 39199         get scenes() {
 39200           return this._scenes || [
 39201             new flash.display.Scene('', this.currentLabels, this._framesLoaded)
 39202           ];
 39203         },
 39204         get trackAsMenu() {
 39205           return false;
 39206         },
 39207         set trackAsMenu(val) {
 39208           notImplemented();
 39209         },
 39210         addFrameScript: function () {
 39211           var frameScripts = this._frameScripts;
 39212           for (var i = 0, n = arguments.length; i < n; i += 2) {
 39213             var frameNum = arguments[i] + 1;
 39214             var fn = arguments[i + 1];
 39215             if (!fn) {
 39216               continue;
 39218             var scripts = frameScripts[frameNum];
 39219             if (scripts) {
 39220               scripts.push(fn);
 39221             } else {
 39222               frameScripts[frameNum] = [
 39223                 fn
 39224               ];
 39226             if (frameNum === this._currentFrame) {
 39227               this._addEventListener('executeFrame', this._onExecuteFrame);
 39230         },
 39231         gotoAndPlay: function (frame, scene) {
 39232           this.play();
 39233           if (isNaN(frame)) {
 39234             this.gotoLabel(frame);
 39235           } else {
 39236             this._gotoFrame(this._getAbsFrameNum(frame, scene));
 39238         },
 39239         gotoAndStop: function (frame, scene) {
 39240           this.stop();
 39241           if (isNaN(frame)) {
 39242             this.gotoLabel(frame);
 39243           } else {
 39244             this._gotoFrame(this._getAbsFrameNum(frame, scene));
 39246         },
 39247         gotoLabel: function (labelName) {
 39248           var frameNum = this._labelMap[labelName];
 39249           if (frameNum !== undefined) {
 39250             this._gotoFrame(frameNum);
 39252         },
 39253         isPlaying: function () {
 39254           return this._isPlaying;
 39255         },
 39256         nextFrame: function () {
 39257           this.stop();
 39258           if (this._currentFrame < this._framesLoaded) {
 39259             this._gotoFrame(this._currentFrame + 1);
 39261         },
 39262         nextScene: function () {
 39263           if (this._scenes && this._currentScene < this._scenes.length - 1) {
 39264             this._gotoFrame(this._scenes[this._currentScene + 1]._startFrame);
 39266         },
 39267         play: function () {
 39268           if (this._isPlaying || this._complete && this._totalFrames <= 1) {
 39269             return;
 39271           this._isPlaying = true;
 39272           this._addEventListener('advanceFrame', this._onAdvanceFrame);
 39273         },
 39274         prevFrame: function () {
 39275           this.stop();
 39276           if (this._currentFrame > 1) {
 39277             this._gotoFrame(this._currentFrame - 1);
 39279         },
 39280         prevScene: function () {
 39281           if (this._scenes && this._currentScene > 0) {
 39282             this._gotoFrame(this._scenes[this._currentScene - 1]._startFrame);
 39284         },
 39285         stop: function () {
 39286           if (!this._isPlaying || this._complete && this._totalFrames <= 1) {
 39287             return;
 39289           this._isPlaying = false;
 39290           this._removeEventListener('advanceFrame', this._onAdvanceFrame);
 39292       };
 39293     var desc = Object.getOwnPropertyDescriptor;
 39294     def.__glue__ = {
 39295       native: {
 39296         instance: {
 39297           currentFrame: desc(def, 'currentFrame'),
 39298           framesLoaded: desc(def, 'framesLoaded'),
 39299           totalFrames: desc(def, 'totalFrames'),
 39300           trackAsMenu: desc(def, 'trackAsMenu'),
 39301           scenes: desc(def, 'scenes'),
 39302           currentScene: desc(def, 'currentScene'),
 39303           currentLabel: desc(def, 'currentLabel'),
 39304           currentFrameLabel: desc(def, 'currentFrameLabel'),
 39305           enabled: desc(def, 'enabled'),
 39306           isPlaying: desc(def, 'isPlaying'),
 39307           play: def.play,
 39308           stop: def.stop,
 39309           nextFrame: def.nextFrame,
 39310           prevFrame: def.prevFrame,
 39311           gotoAndPlay: def.gotoAndPlay,
 39312           gotoAndStop: def.gotoAndStop,
 39313           addFrameScript: def.addFrameScript,
 39314           prevScene: def.prevScene,
 39315           nextScene: def.nextScene
 39318     };
 39319     return def;
 39320   }.call(this);
 39321 var MovieClipSoundStream = function () {
 39322     var MP3_MIME_TYPE = 'audio/mpeg';
 39323     function openMediaSource(soundStream, mediaSource) {
 39324       var sourceBuffer;
 39325       try {
 39326         sourceBuffer = mediaSource.addSourceBuffer(MP3_MIME_TYPE);
 39327         soundStream.mediaSource = mediaSource;
 39328         soundStream.sourceBuffer = sourceBuffer;
 39329         soundStream.rawFrames.forEach(function (data) {
 39330           sourceBuffer.appendBuffer(data);
 39331         });
 39332         delete soundStream.rawFrames;
 39333       } catch (e) {
 39334         console.error('MediaSource mp3 playback is not supported: ' + e);
 39337     function syncTime(element, movieClip) {
 39338       var initialized = false;
 39339       var startMediaTime, startRealTime;
 39340       element.addEventListener('timeupdate', function (e) {
 39341         if (!initialized) {
 39342           startMediaTime = element.currentTime;
 39343           startRealTime = performance.now();
 39344           initialized = true;
 39345           movieClip._stage._frameScheduler.startTrackDelta();
 39346           return;
 39348         var mediaDelta = element.currentTime - startMediaTime;
 39349         var realDelta = performance.now() - startRealTime;
 39350         movieClip._stage._frameScheduler.setDelta(realDelta - mediaDelta * 1000);
 39351       });
 39352       element.addEventListener('pause', function (e) {
 39353         movieClip._stage._frameScheduler.endTrackDelta();
 39354         initialized = false;
 39355       });
 39356       element.addEventListener('seeking', function (e) {
 39357         movieClip._stage._frameScheduler.endTrackDelta();
 39358         initialized = false;
 39359       });
 39361     function MovieClipSoundStream(streamInfo, movieClip) {
 39362       this.movieClip = movieClip;
 39363       this.data = {
 39364         sampleRate: streamInfo.sampleRate,
 39365         channels: streamInfo.channels
 39366       };
 39367       this.seekIndex = [];
 39368       this.position = 0;
 39369       var isMP3 = streamInfo.format === 'mp3';
 39370       if (isMP3 && PLAY_USING_AUDIO_TAG) {
 39371         var element = document.createElement('audio');
 39372         element.preload = 'metadata';
 39373         element.loop = false;
 39374         syncTime(element, movieClip);
 39375         if (element.canPlayType(MP3_MIME_TYPE)) {
 39376           this.element = element;
 39377           if (typeof MediaSource !== 'undefined') {
 39378             var mediaSource = new MediaSource();
 39379             mediaSource.addEventListener('sourceopen', openMediaSource.bind(null, this, mediaSource));
 39380             element.src = URL.createObjectURL(mediaSource);
 39381           } else {
 39382             console.warn('MediaSource is not supported');
 39384           this.rawFrames = [];
 39385           return;
 39388       var totalSamples = streamInfo.samplesCount * streamInfo.channels;
 39389       this.data.pcm = new Float32Array(totalSamples);
 39390       if (isMP3) {
 39391         var soundStream = this;
 39392         soundStream.decoderPosition = 0;
 39393         soundStream.decoderSession = new MP3DecoderSession();
 39394         soundStream.decoderSession.onframedata = function (frameData) {
 39395           var position = soundStream.decoderPosition;
 39396           soundStream.data.pcm.set(frameData, position);
 39397           soundStream.decoderPosition = position + frameData.length;
 39398         }.bind(this);
 39399         soundStream.decoderSession.onerror = function (error) {
 39400           console.error('ERROR: MP3DecoderSession: ' + error);
 39401         };
 39404     MovieClipSoundStream.prototype = {
 39405       appendBlock: function (frameNum, streamBlock) {
 39406         var streamPosition = this.position;
 39407         this.seekIndex[frameNum] = streamPosition + streamBlock.seek * this.data.channels;
 39408         this.position = streamPosition + streamBlock.samplesCount * this.data.channels;
 39409         if (this.sourceBuffer) {
 39410           this.sourceBuffer.appendBuffer(streamBlock.data);
 39411           return;
 39413         if (this.rawFrames) {
 39414           this.rawFrames.push(streamBlock.data);
 39415           return;
 39417         var decoderSession = this.decoderSession;
 39418         if (decoderSession) {
 39419           decoderSession.pushAsync(streamBlock.data);
 39420         } else {
 39421           this.data.pcm.set(streamBlock.pcm, streamPosition);
 39423       },
 39424       playFrame: function (frameNum) {
 39425         if (isNaN(this.seekIndex[frameNum])) {
 39426           return;
 39428         var PAUSE_WHEN_OF_SYNC_GREATER = 1;
 39429         var PLAYBACK_ADJUSTMENT = 0.25;
 39430         var element = this.element;
 39431         if (element) {
 39432           var soundStreamData = this.data;
 39433           var time = this.seekIndex[frameNum] / soundStreamData.sampleRate / soundStreamData.channels;
 39434           if (!this.channel && (this.movieClip._complete || this.sourceBuffer)) {
 39435             if (!this.sourceBuffer) {
 39436               var blob = new Blob(this.rawFrames);
 39437               element.src = URL.createObjectURL(blob);
 39439             var symbolClass = flash.media.SoundChannel.class;
 39440             var channel = symbolClass.createAsSymbol({
 39441                 element: element
 39442               });
 39443             symbolClass.instanceConstructor.call(channel);
 39444             this.channel = channel;
 39445             this.expectedFrame = 0;
 39446             this.waitFor = 0;
 39447           } else if (this.sourceBuffer || !isNaN(element.duration)) {
 39448             if (this.mediaSource && this.movieClip._complete) {
 39449               this.mediaSource.endOfStream();
 39450               this.mediaSource = null;
 39452             var elementTime = element.currentTime;
 39453             if (this.expectedFrame !== frameNum) {
 39454               if (element.paused) {
 39455                 element.play();
 39456                 element.addEventListener('playing', function setTime(e) {
 39457                   element.removeEventListener('playing', setTime);
 39458                   element.currentTime = time;
 39459                 });
 39460               } else {
 39461                 element.currentTime = time;
 39463             } else if (this.waitFor > 0) {
 39464               if (this.waitFor <= time) {
 39465                 if (element.paused) {
 39466                   element.play();
 39468                 this.waitFor = 0;
 39470             } else if (elementTime - time > PAUSE_WHEN_OF_SYNC_GREATER) {
 39471               console.warn('Sound is faster than frames by ' + (elementTime - time));
 39472               this.waitFor = elementTime - PLAYBACK_ADJUSTMENT;
 39473               element.pause();
 39474             } else if (time - elementTime > PAUSE_WHEN_OF_SYNC_GREATER) {
 39475               console.warn('Sound is slower than frames by ' + (time - elementTime));
 39476               element.currentTime = time + PLAYBACK_ADJUSTMENT;
 39478             this.expectedFrame = frameNum + 1;
 39480         } else if (!this.sound) {
 39481           var symbolClass = flash.media.Sound.class;
 39482           var sound = symbolClass.createAsSymbol(this.data);
 39483           symbolClass.instanceConstructor.call(sound);
 39484           var channel = sound.play();
 39485           this.sound = sound;
 39486           this.channel = channel;
 39489     };
 39490     return MovieClipSoundStream;
 39491   }();
 39492 var NativeMenuDefinition = function () {
 39493     return {
 39494       __class__: 'flash.display.NativeMenu',
 39495       initialize: function () {
 39496       },
 39497       __glue__: {
 39498         native: {
 39499           static: {},
 39500           instance: {}
 39503     };
 39504   }.call(this);
 39505 var NativeMenuItemDefinition = function () {
 39506     return {
 39507       __class__: 'flash.display.NativeMenuItem',
 39508       initialize: function () {
 39509       },
 39510       __glue__: {
 39511         native: {
 39512           static: {},
 39513           instance: {
 39514             enabled: {
 39515               get: function enabled() {
 39516                 somewhatImplemented('NativeMenuItem.enabled');
 39517                 return this._enabled;
 39518               },
 39519               set: function enabled(isSeparator) {
 39520                 somewhatImplemented('NativeMenuItem.enabled');
 39521                 this._enabled = isSeparator;
 39527     };
 39528   }.call(this);
 39529 var SceneDefinition = function () {
 39530     return {
 39531       __class__: 'flash.display.Scene',
 39532       initialize: function () {
 39533         this._startFrame = 1;
 39534         this._endFrame = 1;
 39535       },
 39536       __glue__: {
 39537         native: {
 39538           static: {},
 39539           instance: {}
 39540         },
 39541         script: {
 39542           static: {},
 39543           instance: {
 39544             name: {
 39545               get: function name() {
 39546                 notImplemented('Scene.name');
 39547                 return this._name;
 39549             },
 39550             labels: {
 39551               get: function labels() {
 39552                 notImplemented('Scene.labels');
 39553                 return this._labels;
 39555             },
 39556             numFrames: {
 39557               get: function numFrames() {
 39558                 notImplemented('Scene.numFrames');
 39559                 return this._numFrames;
 39565     };
 39566   }.call(this);
 39567 var ShaderDefinition = function () {
 39568     return {
 39569       __class__: 'flash.display.Shader',
 39570       initialize: function () {
 39571         this._data = null;
 39572       },
 39573       __glue__: {
 39574         native: {
 39575           static: {},
 39576           instance: {
 39577             data: {
 39578               get: function data() {
 39579                 return this._data;
 39580               },
 39581               set: function data(p) {
 39582                 this._data = p;
 39584             },
 39585             precisionHint: {
 39586               get: function precisionHint() {
 39587                 return this._precisionHint;
 39588               },
 39589               set: function precisionHint(p) {
 39590                 this._precisionHint = p;
 39594         },
 39595         script: {
 39596           instance: Glue.ALL
 39599     };
 39600   }.call(this);
 39601 var ShaderDataDefinition = function () {
 39602     return {
 39603       __class__: 'flash.display.ShaderData',
 39604       initialize: function () {
 39605         this._byteCode = null;
 39606       },
 39607       __glue__: {
 39608         native: {
 39609           static: {},
 39610           instance: {
 39611             _setByteCode: function _setByteCode(code) {
 39612               this._byteCode = code;
 39615         },
 39616         script: {
 39617           instance: Glue.ALL
 39620     };
 39621   }.call(this);
 39622 var ShapeDefinition = function () {
 39623     var def = {
 39624         __class__: 'flash.display.Shape',
 39625         initialize: function () {
 39626           var graphics = this._graphics = new flash.display.Graphics();
 39627           graphics._parent = this;
 39628           var s = this.symbol;
 39629           if (s && s.paths) {
 39630             graphics._paths = s.paths;
 39631             for (var i = 0; i < s.paths.length; i++) {
 39632               s.paths[i] = finishShapePath(s.paths[i], s.dictionaryResolved);
 39634             graphics.bbox = s.bbox;
 39635             graphics.strokeBbox = s.strokeBbox;
 39636             if (this._stage && this._stage._quality === 'low' && !graphics._bitmap)
 39637               graphics._cacheAsBitmap(this._bbox);
 39638             this.ratio = s.ratio || 0;
 39641       };
 39642     def.__glue__ = {
 39643       native: {
 39644         instance: {
 39645           graphics: {
 39646             get: function () {
 39647               return this._graphics;
 39652     };
 39653     return def;
 39654   }.call(this);
 39655 var SimpleButtonDefinition = function () {
 39656     var AVM1KeyCodeMap = [
 39657         0,
 39658         37,
 39659         39,
 39660         36,
 39661         35,
 39662         45,
 39663         46,
 39664         0,
 39665         8,
 39666         0,
 39667         0,
 39668         0,
 39669         0,
 39670         13,
 39671         38,
 39672         40,
 39673         33,
 39674         34,
 39675         9,
 39676         27
 39677       ];
 39678     var AVM1MouseTransitionEvents = [
 39679         0,
 39680         0,
 39681         1,
 39682         128,
 39683         64,
 39684         0,
 39685         0,
 39686         32,
 39687         2,
 39688         0,
 39689         0,
 39690         4,
 39691         256,
 39692         16,
 39693         8,
 39695       ];
 39696     return {
 39697       __class__: 'flash.display.SimpleButton',
 39698       initialize: function () {
 39699         this._useHandCursor = true;
 39700         this._enabled = true;
 39701         this._trackAsMenu = false;
 39702         this._upState = null;
 39703         this._overState = null;
 39704         this._downState = null;
 39705         this._hitTestState = null;
 39706         this._currentButtonState = 'up';
 39707         this._mouseChildren = false;
 39708         this._buttonMode = true;
 39709         this._prevAvm1StateCode = 0;
 39710         this._avm1StateCode = 0;
 39711         this._avm1MouseEvents = null;
 39712         this._isContainer = true;
 39713         var s = this.symbol;
 39714         if (s) {
 39715           var states = s.states;
 39716           if (states.down) {
 39717             this._downState = this._constructState(states.down, this);
 39719           if (states.hitTest) {
 39720             this._hitTestState = this._constructState(states.hitTest, this);
 39722           if (states.over) {
 39723             this._overState = this._constructState(states.over, this);
 39725           if (states.up) {
 39726             this._upState = this._constructState(states.up, this);
 39729         if (this._loader && !this._loader._isAvm2Enabled && s && s.buttonActions) {
 39730           this._addEventListener('addedToStage', function (e) {
 39731             this._initAvm1Events(s.buttonActions);
 39732           }.bind(this), false);
 39734       },
 39735       _constructState: function constructState(symbolInfo) {
 39736         var symbolClass = avm2.systemDomain.findClass(symbolInfo.className) ? avm2.systemDomain.getClass(symbolInfo.className) : avm2.applicationDomain.getClass(symbolInfo.className);
 39737         var instance = symbolClass.createAsSymbol(symbolInfo.props);
 39738         symbolClass.instanceConstructor.call(instance);
 39739         if (instance._children.length === 1) {
 39740           instance = instance._children[0];
 39741           instance._parent = null;
 39742           instance._index = -1;
 39744         return instance;
 39745       },
 39746       _updateButton: function updateButton() {
 39747         var state = null;
 39748         switch (this._currentButtonState) {
 39749         case 'up':
 39750           state = this._upState;
 39751           break;
 39752         case 'over':
 39753           state = this._overState;
 39754           break;
 39755         case 'down':
 39756           state = this._downState;
 39757           break;
 39759         if (!state) {
 39760           return;
 39762         var currentChild = this._children[0];
 39763         if (currentChild) {
 39764           if (currentChild === state) {
 39765             return;
 39767           if (this._stage) {
 39768             this._stage._removeFromStage(currentChild);
 39770           currentChild._invalidateTransform();
 39772         if (!state) {
 39773           this._children.shift();
 39774           return;
 39776         this._children[0] = state;
 39777         state._parent = this;
 39778         state._invalidateTransform();
 39779         if (this._stage) {
 39780           this._stage._addToStage(state);
 39782       },
 39783       _gotoButtonState: function gotoButtonState(buttonState) {
 39784         this._invalidateBounds();
 39785         this._currentButtonState = buttonState;
 39786         this._updateButton();
 39787         if (this._avm1MouseEvents) {
 39788           this._processAvm1MouseEvents(this._avm1MouseEvents);
 39790       },
 39791       _getRegion: function getRegion(targetCoordSpace) {
 39792         if (!this._hitTestState) {
 39793           return {
 39794             xMin: 0,
 39795             yMin: 0,
 39796             xMax: 0,
 39797             yMax: 0
 39798           };
 39800         var b = this._hitTestState.getBounds(null);
 39801         return this._getTransformedRect(b, targetCoordSpace);
 39802       },
 39803       _getAS2Object: function () {
 39804         if (!this.$as2Object) {
 39805           new avm1lib.AS2Button(this);
 39807         return this.$as2Object;
 39808       },
 39809       _initAvm1Events: function (buttonActions) {
 39810         var loader = this._loader;
 39811         var avm1Context = loader._avm1Context;
 39812         var keyEvents = null;
 39813         for (var i = 0; i < buttonActions.length; i++) {
 39814           var buttonAction = buttonActions[i];
 39815           var fn = function (actionBlock) {
 39816               return executeActions(actionBlock, avm1Context, this._getAS2Object());
 39817             }.bind(this.parent, buttonAction.actionsData);
 39818           var mouseEventFlags = buttonAction.mouseEventFlags;
 39819           if (mouseEventFlags) {
 39820             var mouseEvents = this._avm1MouseEvents || (this._avm1MouseEvents = []);
 39821             mouseEvents.push({
 39822               flags: mouseEventFlags,
 39823               listener: fn
 39824             });
 39826           var keyPress = buttonAction.keyPress;
 39827           if (keyPress) {
 39828             keyEvents = keyEvents || (keyEvents = []);
 39829             keyEvents.push({
 39830               keyCode: AVM1KeyCodeMap[keyPress] || 0,
 39831               charCode: keyPress,
 39832               listener: fn
 39833             });
 39836         if (keyEvents) {
 39837           var keyListener = function (e) {
 39838             for (var i = 0; i < keyEvents.length; i++) {
 39839               var keyEvent = keyEvents[i];
 39840               if (keyEvent.keyCode ? keyEvent.keyCode === e.keyCode : keyEvent.charCode === e.charCode) {
 39841                 keyEvent.listener();
 39844           };
 39845           var KeyboardEventClass = flash.events.KeyboardEvent;
 39846           this.stage._addEventListener(KeyboardEventClass.class.KEY_DOWN, keyListener, false);
 39847           this._addEventListener('removedFromStage', function (stage) {
 39848             stage._removeEventListener(KeyboardEventClass.class.KEY_DOWN, keyListener, false);
 39849           }.bind(this, this.stage), false);
 39851       },
 39852       _processAvm1MouseEvents: function (mouseEvents) {
 39853         var prevAvm1StateCode = this._avm1StateCode;
 39854         var avm1StateCode = (this._currentButtonState === 'down' ? 1 : 0) | (this._currentButtonState !== 'up' ? 2 : 0);
 39855         if (prevAvm1StateCode !== avm1StateCode) {
 39856           this._prevAvm1StateCode = prevAvm1StateCode;
 39857           this._avm1StateCode = avm1StateCode;
 39858           var flag = AVM1MouseTransitionEvents[prevAvm1StateCode << 2 | avm1StateCode];
 39859           for (var i = 0; i < mouseEvents.length; i++) {
 39860             var mouseEvent = mouseEvents[i];
 39861             if ((mouseEvent.flags & flag) !== 0) {
 39862               mouseEvent.listener();
 39866       },
 39867       __glue__: {
 39868         native: {
 39869           instance: {
 39870             _updateButton: function _updateButton() {
 39871               this._updateButton();
 39872             },
 39873             useHandCursor: {
 39874               get: function useHandCursor() {
 39875                 return this._useHandCursor;
 39876               },
 39877               set: function useHandCursor(value) {
 39878                 this._useHandCursor = value;
 39880             },
 39881             enabled: {
 39882               get: function enabled() {
 39883                 return this._enabled;
 39884               },
 39885               set: function enabled(value) {
 39886                 this._enabled = value;
 39888             },
 39889             trackAsMenu: {
 39890               get: function trackAsMenu() {
 39891                 notImplemented('SimpleButton.trackAsMenu');
 39892                 return this._trackAsMenu;
 39893               },
 39894               set: function trackAsMenu(value) {
 39895                 notImplemented('SimpleButton.trackAsMenu');
 39896                 this._trackAsMenu = value;
 39898             },
 39899             upState: {
 39900               get: function upState() {
 39901                 return this._upState;
 39902               },
 39903               set: function upState(value) {
 39904                 this._upState = value;
 39905                 this._updateButton();
 39907             },
 39908             overState: {
 39909               get: function overState() {
 39910                 return this._overState;
 39911               },
 39912               set: function overState(value) {
 39913                 this._overState = value;
 39914                 this._updateButton();
 39916             },
 39917             downState: {
 39918               get: function downState() {
 39919                 return this._downState;
 39920               },
 39921               set: function downState(value) {
 39922                 this._downState = value;
 39923                 this._updateButton();
 39925             },
 39926             hitTestState: {
 39927               get: function hitTestState() {
 39928                 return this._hitTestState;
 39929               },
 39930               set: function hitTestState(value) {
 39931                 if (value === this._hitTestState) {
 39932                   return;
 39934                 this._invalidate();
 39935                 this._hitTestState = value;
 39937             },
 39938             soundTransform: {
 39939               get: function soundTransform() {
 39940                 notImplemented('SimpleButton.soundTransform');
 39941                 return this._soundTransform;
 39942               },
 39943               set: function soundTransform(value) {
 39944                 notImplemented('SimpleButton.soundTransform');
 39945                 this._soundTransform = value;
 39951     };
 39952   }.call(this);
 39953 var SpriteDefinition = function () {
 39954     var def = {
 39955         __class__: 'flash.display.Sprite',
 39956         initialize: function () {
 39957           this._buttonMode = false;
 39958           this._hitArea = null;
 39959           this._useHandCursor = true;
 39960           this._hitTarget = null;
 39961           this._currentDisplayList = null;
 39962           var s = this.symbol;
 39963           if (s) {
 39964             this._graphics = s.graphics || new flash.display.Graphics();
 39965             if (s.timeline) {
 39966               var displayList = s.timeline[0];
 39967               if (displayList) {
 39968                 var depths = displayList.depths;
 39969                 for (var i = 0; i < depths.length; i++) {
 39970                   var cmd = displayList[depths[i]];
 39971                   if (cmd) {
 39972                     var displayListItem = this._addTimelineChild(cmd);
 39973                     displayListItem.next = this._currentDisplayList;
 39974                     this._currentDisplayList = displayListItem;
 39979           } else {
 39980             this._graphics = new flash.display.Graphics();
 39982           this._graphics._parent = this;
 39983         },
 39984         _addTimelineChild: function addTimelineChild(cmd, index) {
 39985           var symbolInfo = cmd.symbolInfo;
 39986           var props = Object.create(symbolInfo.props);
 39987           props.symbolId = cmd.symbolId;
 39988           props.depth = cmd.depth;
 39989           if (cmd.clip) {
 39990             props.clipDepth = cmd.clipDepth;
 39992           if (cmd.hasCxform) {
 39993             props.cxform = cmd.cxform;
 39995           if (cmd.hasMatrix) {
 39996             props.currentTransform = cmd.matrix;
 39998           if (cmd.hasName) {
 39999             props.name = cmd.name;
 40001           if (cmd.hasRatio) {
 40002             props.ratio = cmd.ratio / 65535;
 40004           if (cmd.blend) {
 40005             props.blendMode = cmd.blendMode;
 40007           var displayListItem = {
 40008               cmd: cmd,
 40009               depth: cmd.depth,
 40010               className: symbolInfo.className,
 40011               props: props,
 40012               events: cmd.events,
 40013               obj: null
 40014             };
 40015           if (index !== undefined) {
 40016             this._children.splice(index, 0, displayListItem);
 40017           } else {
 40018             this._children.push(displayListItem);
 40020           this._sparse = true;
 40021           return displayListItem;
 40022         },
 40023         _constructChildren: function () {
 40024           if (!this._sparse) {
 40025             return;
 40027           var loader = this._loader;
 40028           var children = this._children;
 40029           for (var i = 0; i < children.length; i++) {
 40030             var displayListItem = children[i];
 40031             Counter.count('constructChild');
 40032             if (flash.display.DisplayObject.class.isInstanceOf(displayListItem)) {
 40033               displayListItem._index = i;
 40034             } else {
 40035               var symbolClass = avm2.systemDomain.findClass(displayListItem.className) ? avm2.systemDomain.getClass(displayListItem.className) : avm2.applicationDomain.getClass(displayListItem.className);
 40036               var props = Object.create(displayListItem.props);
 40037               var name = props.name;
 40038               props.animated = true;
 40039               props.owned = true;
 40040               props.parent = this;
 40041               props.stage = this._stage;
 40042               if (this._level > -1) {
 40043                 props.level = this._level + 1;
 40045               props.index = i;
 40046               var instance = symbolClass.createAsSymbol(props);
 40047               if (name) {
 40048                 this[Multiname.getPublicQualifiedName(name)] = instance;
 40050               symbolClass.instanceConstructor.call(instance);
 40051               if (flash.display.BitmapData.class.isInstanceOf(instance)) {
 40052                 var bitmapData = instance;
 40053                 instance = flash.display.Bitmap.class.createAsSymbol(props);
 40054                 flash.display.Bitmap.class.instanceConstructor.call(instance, bitmapData);
 40056               if (!loader._isAvm2Enabled) {
 40057                 this._initAvm1Bindings(instance, name, displayListItem.events);
 40058                 instance._dispatchEvent('init');
 40059                 instance._dispatchEvent('construct');
 40060                 instance._needLoadEvent = true;
 40061               } else {
 40062                 instance._dispatchEvent('load');
 40064               instance._dispatchEvent('added', undefined, true);
 40065               if (this._stage) {
 40066                 this._stage._addToStage(instance);
 40068               children[i] = instance;
 40069               displayListItem.obj = instance;
 40072           this._sparse = false;
 40073         },
 40074         _postConstructChildren: function () {
 40075           var loader = this._loader;
 40076           if (!loader || loader._isAvm2Enabled) {
 40077             return;
 40079           var children = this._children;
 40080           for (var i = 0; i < children.length; i++) {
 40081             var instance = children[i];
 40082             if (instance._needLoadEvent) {
 40083               instance._needLoadEvent = false;
 40084               instance._dispatchEvent('load');
 40087         },
 40088         _duplicate: function (name, depth, initObject) {
 40089           var loader = this._loader;
 40090           var parent = this._parent;
 40091           var children = parent._children;
 40092           var symbolClass = this.class;
 40093           var symbolInfo = this.symbol;
 40094           var props = Object.create(symbolInfo);
 40095           props.name = name;
 40096           props.parent = parent;
 40097           props.depth = depth;
 40098           var instance = symbolClass.createAsSymbol(props);
 40099           if (name && loader && !loader._isAvm2Enabled && !parent.asHasProperty(undefined, name, 0, false)) {
 40100             parent.asSetPublicProperty(name, instance);
 40102           symbolClass.instanceConstructor.call(instance);
 40103           instance._index = children.length;
 40104           children.push(instance);
 40105           if (!loader._isAvm2Enabled) {
 40106             parent._initAvm1Bindings(instance, name, symbolInfo && symbolInfo.events);
 40107             instance._dispatchEvent('init');
 40108             instance._dispatchEvent('construct');
 40110           instance._dispatchEvent('load');
 40111           instance._dispatchEvent('added');
 40112           if (this._stage) {
 40113             instance._invalidate();
 40115           return instance;
 40116         },
 40117         _insertChildAtDepth: function (child, depth) {
 40118           this.addChild(child);
 40119           var name = child._name;
 40120           var loader = this._loader;
 40121           if (name && loader && !loader._isAvm2Enabled && !this._getAS2Object().asHasProperty(undefined, name, 0, true)) {
 40122             this._getAS2Object().asSetPublicProperty(name, child._getAS2Object());
 40124         },
 40125         _initAvm1Bindings: function (instance, name, events) {
 40126           var loader = this._loader;
 40127           var avm1Context = loader._avm1Context;
 40128           var symbolProps = instance.symbol;
 40129           if (symbolProps && symbolProps.variableName) {
 40130             instance._getAS2Object().asSetPublicProperty('variable', symbolProps.variableName);
 40132           if (events) {
 40133             var eventsBound = [];
 40134             for (var i = 0; i < events.length; i++) {
 40135               var event = events[i];
 40136               if (event.eoe) {
 40137                 break;
 40139               var fn = function (actionBlock) {
 40140                   return executeActions(actionBlock, avm1Context, this._getAS2Object());
 40141                 }.bind(instance, event.actionsData);
 40142               for (var eventName in event) {
 40143                 if (eventName.indexOf('on') !== 0 || !event[eventName])
 40144                   continue;
 40145                 var avm2EventName = eventName[2].toLowerCase() + eventName.substring(3);
 40146                 if (avm2EventName === 'enterFrame') {
 40147                   avm2EventName = 'frameConstructed';
 40149                 var avm2EventTarget = instance;
 40150                 if (avm2EventName === 'mouseDown' || avm2EventName === 'mouseUp' || avm2EventName === 'mouseMove') {
 40151                   avm2EventTarget = this._stage;
 40153                 avm2EventTarget._addEventListener(avm2EventName, fn, false);
 40154                 eventsBound.push({
 40155                   name: avm2EventName,
 40156                   fn: fn,
 40157                   target: avm2EventTarget
 40158                 });
 40161             if (eventsBound.length > 0) {
 40162               instance._addEventListener('removed', function (eventsBound) {
 40163                 for (var i = 0; i < eventsBound.length; i++) {
 40164                   eventsBound[i].target._removeEventListener(eventsBound[i].name, eventsBound[i].fn, false);
 40166               }.bind(instance, eventsBound), false);
 40169           if (name && this._getAS2Object && instance._getAS2Object) {
 40170             this._getAS2Object().asSetPublicProperty(name, instance._getAS2Object());
 40172         },
 40173         _gotoButtonState: function gotoButtonState(stateName) {
 40174         },
 40175         get buttonMode() {
 40176           return this._buttonMode;
 40177         },
 40178         set buttonMode(val) {
 40179           this._buttonMode = val;
 40180         },
 40181         get graphics() {
 40182           return this._graphics;
 40183         },
 40184         get hitArea() {
 40185           return this._hitArea;
 40186         },
 40187         set hitArea(val) {
 40188           if (this._hitArea === val) {
 40189             return;
 40191           if (val && val._hitTarget) {
 40192             val._hitTarget.hitArea = null;
 40194           this._hitArea = val;
 40195           if (val) {
 40196             val._hitTarget = this;
 40198         },
 40199         get soundTransform() {
 40200           notImplemented();
 40201         },
 40202         set soundTransform(val) {
 40203           notImplemented();
 40204         },
 40205         get useHandCursor() {
 40206           return this._useHandCursor;
 40207         },
 40208         set useHandCursor(val) {
 40209           this._useHandCursor = val;
 40210           if (this._stage) {
 40211             this._stage._mouseMoved = true;
 40213         },
 40214         startDrag: function (lockCenter, bounds) {
 40215           notImplemented();
 40216         },
 40217         startTouchDrag: function (touchPointID, lockCenter, bounds) {
 40218           notImplemented();
 40219         },
 40220         stopDrag: function () {
 40221           notImplemented();
 40222         },
 40223         stopTouchDrag: function (touchPointID) {
 40224           notImplemented();
 40226       };
 40227     var desc = Object.getOwnPropertyDescriptor;
 40228     def.__glue__ = {
 40229       native: {
 40230         instance: {
 40231           graphics: desc(def, 'graphics'),
 40232           buttonMode: desc(def, 'buttonMode'),
 40233           dropTarget: desc(def, 'dropTarget'),
 40234           startDrag: def.startDrag,
 40235           stopDrag: def.stopDrag,
 40236           startTouchDrag: def.startTouchDrag,
 40237           stopTouchDrag: def.stopTouchDrag,
 40238           constructChildren: def._constructChildren,
 40239           hitArea: desc(def, 'hitArea'),
 40240           useHandCursor: desc(def, 'useHandCursor'),
 40241           soundTransform: desc(def, 'soundTransform')
 40244     };
 40245     return def;
 40246   }.call(this);
 40247 var StageDefinition = function () {
 40248     return {
 40249       __class__: 'flash.display.Stage',
 40250       initialize: function () {
 40251         this._frameRate = 24;
 40252         this._scaleMode = 'showAll';
 40253         this._align = '';
 40254         this._stageWidth = 0;
 40255         this._stageHeight = 0;
 40256         this._quality = 'high';
 40257         this._color = 4294967295;
 40258         this._stage = this;
 40259         this._deferRenderEvent = false;
 40260         this._focus = null;
 40261         this._showDefaultContextMenu = true;
 40262         this._displayState = 'normal';
 40263         this._colorCorrection = 'default';
 40264         this._stageFocusRect = true;
 40265         this._fullScreenSourceRect = null;
 40266         this._wmodeGPU = false;
 40267         this._root = null;
 40268         this._qtree = null;
 40269         this._invalidRegions = new RegionCluster();
 40270         this._mouseMoved = false;
 40271         this._mouseTarget = this;
 40272         this._mouseEvents = [];
 40273         this._cursor = 'auto';
 40274         this._stageVideos = [];
 40275         this._concatenatedTransform.invalid = false;
 40276       },
 40277       _setup: function setup(ctx, options) {
 40278         this._qtree = new QuadTree(0, 0, this._stageWidth, this._stageHeight, null);
 40279         this._invalid = true;
 40280       },
 40281       _addToStage: function addToStage(displayObject) {
 40282         displayObject._stage = this;
 40283         var parent = displayObject._parent;
 40284         displayObject._level = parent._level + 1;
 40285         displayObject._invalid = true;
 40286         var children = displayObject._children;
 40287         for (var i = 0; i < children.length; i++) {
 40288           var child = children[i];
 40289           if (child._stage === null) {
 40290             this._addToStage(child);
 40293         displayObject._dispatchEvent('addedToStage');
 40294       },
 40295       _removeFromStage: function removeFromStage(displayObject) {
 40296         var children = displayObject._children;
 40297         for (var i = 0; i < children.length; i++) {
 40298           var child = children[i];
 40299           if (child._stage) {
 40300             this._removeFromStage(children[i]);
 40303         displayObject._dispatchEvent('removedFromStage');
 40304         displayObject._stage = null;
 40305         displayObject._level = -1;
 40306         if (displayObject._region) {
 40307           this._qtree.remove(displayObject._region);
 40308           this._invalidRegions.insert(displayObject._region);
 40309           displayObject._region = null;
 40311       },
 40312       _processInvalidations: function processInvalidations(refreshStage) {
 40313         var qtree = this._qtree;
 40314         var invalidRegions = this._invalidRegions;
 40315         var stack = [];
 40316         var zindex = 0;
 40317         var children = this._children;
 40318         var i = children.length;
 40319         while (i--) {
 40320           var child = children[i];
 40321           if (refreshStage) {
 40322             child._invalid = true;
 40324           child._invisible = !child._visible;
 40325           stack.push(child);
 40327         while (stack.length) {
 40328           var node = stack.pop();
 40329           var m = node._concatenatedTransform;
 40330           var children = node._children;
 40331           var i = children.length;
 40332           while (i--) {
 40333             var child = children[i];
 40334             if (!flash.display.DisplayObject.class.isInstanceOf(child)) {
 40335               continue;
 40337             if (node._invalid) {
 40338               child._invalid = true;
 40340             if (m.invalid) {
 40341               child._concatenatedTransform.invalid = true;
 40343             child._invisible = node._invisible || !child._visible;
 40344             stack.push(child);
 40346           if (node._level && m.invalid) {
 40347             var m2 = node._currentTransform;
 40348             var m3 = node._parent._concatenatedTransform;
 40349             m.a = m2.a * m3.a + m2.b * m3.c;
 40350             m.b = m2.a * m3.b + m2.b * m3.d;
 40351             m.c = m2.c * m3.a + m2.d * m3.c;
 40352             m.d = m2.d * m3.d + m2.c * m3.b;
 40353             m.tx = m2.tx * m3.a + m3.tx + m2.ty * m3.c;
 40354             m.ty = m2.ty * m3.d + m3.ty + m2.tx * m3.b;
 40355             m.invalid = false;
 40357           var invalidRegion = node._region;
 40358           var currentRegion = node._getRegion(m);
 40359           var hidden = node._invisible || !currentRegion || currentRegion.xMax - currentRegion.xMin === 0 || currentRegion.yMax - currentRegion.yMin === 0 || currentRegion.xMax <= 0 || currentRegion.xMin >= this._stageWidth || currentRegion.yMax <= 0 || currentRegion.yMin >= this._stageHeight;
 40360           if (node._invalid) {
 40361             if (invalidRegion) {
 40362               invalidRegions.insert(invalidRegion);
 40364             if (!hidden && (!invalidRegion || currentRegion.xMin !== invalidRegion.xMin || currentRegion.yMin !== invalidRegion.yMin || currentRegion.xMax !== invalidRegion.xMax || currentRegion.yMax !== invalidRegion.yMax)) {
 40365               invalidRegions.insert(currentRegion);
 40368           if (hidden) {
 40369             if (invalidRegion) {
 40370               qtree.remove(invalidRegion);
 40371               node._region = null;
 40373           } else if (invalidRegion) {
 40374             invalidRegion.xMin = currentRegion.xMin;
 40375             invalidRegion.xMax = currentRegion.xMax;
 40376             invalidRegion.yMin = currentRegion.yMin;
 40377             invalidRegion.yMax = currentRegion.yMax;
 40378             qtree.update(invalidRegion);
 40379           } else {
 40380             currentRegion.obj = node;
 40381             qtree.insert(currentRegion);
 40382             node._region = currentRegion;
 40384           node._zindex = zindex++;
 40386         var invalidPath = new ShapePath();
 40387         if (refreshStage) {
 40388           invalidPath.rect(0, 0, this._stageWidth, this._stageHeight);
 40389           invalidRegions.reset();
 40390           return invalidPath;
 40392         var redrawRegions = invalidRegions.retrieve();
 40393         for (var i = 0; i < redrawRegions.length; i++) {
 40394           var region = redrawRegions[i];
 40395           var xMin = region.xMin - region.xMin % 20 - 40;
 40396           var yMin = region.yMin - region.yMin % 20 - 40;
 40397           var xMax = region.xMax - region.xMax % 20 + 80;
 40398           var yMax = region.yMax - region.yMax % 20 + 80;
 40399           var intersectees = qtree.retrieve(xMin, xMax, yMin, yMax);
 40400           for (var j = 0; j < intersectees.length; j++) {
 40401             var item = intersectees[j];
 40402             item.obj._invalid = true;
 40404           invalidPath.rect(xMin, yMin, xMax - xMin, yMax - yMin);
 40406         invalidRegions.reset();
 40407         return invalidPath;
 40408       },
 40409       _handleMouseButtons: function () {
 40410         if (this._mouseEvents.length === 0) {
 40411           return;
 40413         var eventType = this._mouseEvents.shift();
 40414         switch (eventType) {
 40415         case 'mousedown':
 40416           if (this._mouseTarget._buttonMode) {
 40417             this._mouseTarget._gotoButtonState('down');
 40419           this._mouseTarget._dispatchEvent('mouseDown');
 40420           break;
 40421         case 'mouseup':
 40422           if (this._mouseTarget._buttonMode) {
 40423             this._mouseTarget._gotoButtonState('over');
 40425           this._mouseTarget._dispatchEvent('mouseUp');
 40426           break;
 40428       },
 40429       _handleMouse: function handleMouse() {
 40430         var mouseX = this._mouseX;
 40431         var mouseY = this._mouseY;
 40432         var candidates = this._qtree.retrieve(mouseX, mouseX, mouseY, mouseY);
 40433         var objectsUnderMouse = [];
 40434         for (var i = 0; i < candidates.length; i++) {
 40435           var item = candidates[i];
 40436           var displayObject = item.obj;
 40437           var isUnderMouse = false;
 40438           if (flash.display.SimpleButton.class.isInstanceOf(displayObject)) {
 40439             if (!displayObject._enabled) {
 40440               continue;
 40442             var hitArea = displayObject._hitTestState;
 40443             hitArea._parent = displayObject;
 40444             isUnderMouse = hitArea._hitTest(true, mouseX, mouseY, true);
 40445             hitArea._parent = null;
 40446           } else {
 40447             isUnderMouse = displayObject._hitTest(true, mouseX, mouseY, true);
 40449           if (isUnderMouse) {
 40450             var currentNode = displayObject;
 40451             var lastEnabled = null;
 40452             if (!flash.display.InteractiveObject.class.isInstanceOf(currentNode)) {
 40453               lastEnabled = currentNode;
 40454               currentNode = currentNode._parent;
 40456             do {
 40457               if (!currentNode._mouseEnabled) {
 40458                 lastEnabled = null;
 40459               } else if (lastEnabled === null) {
 40460                 lastEnabled = currentNode;
 40462               currentNode = currentNode._parent;
 40463             } while (currentNode);
 40464             objectsUnderMouse.push(lastEnabled);
 40467         var target;
 40468         if (objectsUnderMouse.length) {
 40469           objectsUnderMouse.sort(sortByZindex);
 40470           var i = objectsUnderMouse.length;
 40471           while (i--) {
 40472             target = null;
 40473             var currentNode = objectsUnderMouse[i];
 40474             if (!flash.display.InteractiveObject.class.isInstanceOf(currentNode)) {
 40475               var j = i;
 40476               while (j--) {
 40477                 if (objectsUnderMouse[j]._parent === currentNode._parent && flash.display.InteractiveObject.class.isInstanceOf(objectsUnderMouse[j])) {
 40478                   currentNode = objectsUnderMouse[j];
 40479                   i = j;
 40483             do {
 40484               if (flash.display.InteractiveObject.class.isInstanceOf(currentNode)) {
 40485                 if ((!target || !currentNode._mouseChildren) && !currentNode._hitArea) {
 40486                   target = currentNode;
 40489               currentNode = currentNode._parent;
 40490             } while (currentNode);
 40491             if (target !== objectsUnderMouse[i] && flash.display.SimpleButton.class.isInstanceOf(target)) {
 40492               continue;
 40494             break;
 40497         if (!target) {
 40498           target = this;
 40499         } else if (target._hitTarget) {
 40500           target = target._hitTarget;
 40502         if (target === this._mouseTarget) {
 40503           target._dispatchEvent('mouseMove');
 40504         } else {
 40505           if (this._mouseTarget._buttonMode) {
 40506             this._mouseTarget._gotoButtonState('up');
 40508           this._mouseTarget._dispatchEvent('mouseOut');
 40509           var nodeLeft = this._mouseTarget;
 40510           var containerLeft = nodeLeft._parent;
 40511           var nodeEntered = target;
 40512           var containerEntered = nodeEntered._parent;
 40513           var cursor = 'auto';
 40514           while (nodeLeft._level >= 0 && nodeLeft !== containerEntered) {
 40515             if (nodeLeft._hasEventListener('rollOut')) {
 40516               nodeLeft._dispatchEvent('rollOut');
 40518             nodeLeft = nodeLeft._parent;
 40520           while (nodeEntered._level >= 0 && nodeEntered !== containerLeft) {
 40521             if (nodeEntered._hasEventListener('rollOver')) {
 40522               nodeEntered._dispatchEvent('rollOver');
 40524             if (nodeEntered._buttonMode && nodeEntered._useHandCursor) {
 40525               cursor = 'pointer';
 40527             nodeEntered = nodeEntered._parent;
 40529           if (target._buttonMode) {
 40530             target._gotoButtonState('over');
 40532           target._dispatchEvent('mouseOver');
 40533           this._mouseTarget = target;
 40534           this._cursor = cursor;
 40536       },
 40537       _as2SetLevel: function (level, loader) {
 40538         somewhatImplemented('Stage._as2SetLevel');
 40539         this.addChild(loader);
 40540       },
 40541       __glue__: {
 40542         native: {
 40543           instance: {
 40544             invalidate: function invalidate() {
 40545               this._invalid = true;
 40546               this._deferRenderEvent = true;
 40547             },
 40548             isFocusInaccessible: function isFocusInaccessible() {
 40549               notImplemented('Stage.isFocusInaccessible');
 40550             },
 40551             set_displayState: function set_displayState(value) {
 40552               somewhatImplemented('Stage.set_displayState');
 40553               this._displayState = value;
 40554             },
 40555             get_simulatedFullScreenWidth: function get_simulatedFullScreenWidth() {
 40556               notImplemented('Stage.get_simulatedFullScreenWidth');
 40557             },
 40558             get_simulatedFullScreenHeight: function get_simulatedFullScreenHeight() {
 40559               notImplemented('Stage.get_simulatedFullScreenHeight');
 40560             },
 40561             removeChildAt: function removeChildAt(index) {
 40562               notImplemented('Stage.removeChildAt');
 40563             },
 40564             swapChildrenAt: function swapChildrenAt(index1, index2) {
 40565               notImplemented('Stage.swapChildrenAt');
 40566             },
 40567             requireOwnerPermissions: function requireOwnerPermissions() {
 40568               somewhatImplemented('Stage.requireOwnerPermissions');
 40569             },
 40570             frameRate: {
 40571               get: function frameRate() {
 40572                 return this._frameRate;
 40573               },
 40574               set: function frameRate(value) {
 40575                 this._frameRate = value;
 40577             },
 40578             scaleMode: {
 40579               get: function scaleMode() {
 40580                 return this._scaleMode;
 40581               },
 40582               set: function scaleMode(value) {
 40583                 this._scaleMode = value;
 40584                 this._invalid = true;
 40586             },
 40587             align: {
 40588               get: function align() {
 40589                 return this._align;
 40590               },
 40591               set: function align(value) {
 40592                 this._align = value;
 40593                 this._invalid = true;
 40595             },
 40596             stageWidth: {
 40597               get: function stageWidth() {
 40598                 return this._stageWidth / 20;
 40599               },
 40600               set: function stageWidth(value) {
 40601                 notImplemented('Stage.stageWidth');
 40602                 this._stageWidth = value * 20 | 0;
 40604             },
 40605             stageHeight: {
 40606               get: function stageHeight() {
 40607                 return this._stageHeight / 20;
 40608               },
 40609               set: function stageHeight(value) {
 40610                 notImplemented('Stage.stageHeight');
 40611                 this._stageHeight = value * 20 | 0;
 40613             },
 40614             showDefaultContextMenu: {
 40615               get: function showDefaultContextMenu() {
 40616                 return this._showDefaultContextMenu;
 40617               },
 40618               set: function showDefaultContextMenu(value) {
 40619                 somewhatImplemented('Stage.showDefaultContextMenu');
 40620                 this._showDefaultContextMenu = value;
 40622             },
 40623             focus: {
 40624               get: function focus() {
 40625                 return this._focus;
 40626               },
 40627               set: function focus(newFocus) {
 40628                 somewhatImplemented('Stage.focus');
 40629                 this._focus = newFocus;
 40631             },
 40632             colorCorrection: {
 40633               get: function colorCorrection() {
 40634                 return this._colorCorrection;
 40635               },
 40636               set: function colorCorrection(value) {
 40637                 notImplemented('Stage.colorCorrection');
 40638                 this._colorCorrection = value;
 40640             },
 40641             colorCorrectionSupport: {
 40642               get: function colorCorrectionSupport() {
 40643                 return false;
 40645             },
 40646             stageFocusRect: {
 40647               get: function stageFocusRect() {
 40648                 return this._stageFocusRect;
 40649               },
 40650               set: function stageFocusRect(on) {
 40651                 somewhatImplemented('Stage.stageFocusRect');
 40652                 this._stageFocusRect = on;
 40654             },
 40655             quality: {
 40656               get: function quality() {
 40657                 return this._quality;
 40658               },
 40659               set: function quality(value) {
 40660                 somewhatImplemented('Stage.stageFocusRect');
 40661                 this._quality = value;
 40663             },
 40664             displayState: {
 40665               get: function displayState() {
 40666                 return this._displayState;
 40667               },
 40668               set: function displayState(value) {
 40669                 this._displayState = value;
 40671             },
 40672             simulatedDisplayState: {
 40673               get: function simulatedDisplayState() {
 40674                 notImplemented('Stage.simulatedDisplayState');
 40675                 return this._simulatedDisplayState;
 40676               },
 40677               set: function simulatedDisplayState(value) {
 40678                 notImplemented('Stage.simulatedDisplayState');
 40679                 this._simulatedDisplayState = value;
 40681             },
 40682             fullScreenSourceRect: {
 40683               get: function fullScreenSourceRect() {
 40684                 return this._fullScreenSourceRect;
 40685               },
 40686               set: function fullScreenSourceRect(value) {
 40687                 notImplemented('Stage.fullScreenSourceRect');
 40688                 this._fullScreenSourceRect = value;
 40690             },
 40691             simulatedFullScreenSourceRect: {
 40692               get: function simulatedFullScreenSourceRect() {
 40693                 notImplemented('Stage.simulatedFullScreenSourceRect');
 40694                 return this._simulatedFullScreenSourceRect;
 40695               },
 40696               set: function simulatedFullScreenSourceRect(value) {
 40697                 notImplemented('Stage.simulatedFullScreenSourceRect');
 40698                 this._simulatedFullScreenSourceRect = value;
 40700             },
 40701             stageVideos: {
 40702               get: function stageVideos() {
 40703                 somewhatImplemented('Stage.stageVideos');
 40704                 return this._stageVideos;
 40706             },
 40707             stage3Ds: {
 40708               get: function stage3Ds() {
 40709                 notImplemented('Stage.stage3Ds');
 40710                 return this._stage3Ds;
 40712             },
 40713             color: {
 40714               get: function color() {
 40715                 return this._color;
 40716               },
 40717               set: function color(color) {
 40718                 this._color = color;
 40719                 this._invalid = true;
 40721             },
 40722             fullScreenWidth: {
 40723               get: function fullScreenWidth() {
 40724                 notImplemented('Stage.fullScreenWidth');
 40725                 return this._fullScreenWidth;
 40727             },
 40728             fullScreenHeight: {
 40729               get: function fullScreenHeight() {
 40730                 notImplemented('Stage.fullScreenHeight');
 40731                 return this._fullScreenHeight;
 40733             },
 40734             wmodeGPU: {
 40735               get: function wmodeGPU() {
 40736                 somewhatImplemented('Stage.wmodeGPU');
 40737                 return this._wmodeGPU;
 40739             },
 40740             softKeyboardRect: {
 40741               get: function softKeyboardRect() {
 40742                 notImplemented('Stage.softKeyboardRect');
 40743                 return this._softKeyboardRect;
 40745             },
 40746             allowsFullScreen: {
 40747               get: function allowsFullScreen() {
 40748                 return false;
 40750             },
 40751             displayContextInfo: {
 40752               get: function displayContextInfo() {
 40753                 notImplemented('Stage.displayContextInfo');
 40754                 return this._displayContextInfo;
 40760     };
 40761   }.call(this);
 40763   var EventDefinition = function () {
 40764       return {
 40765         __class__: 'flash.events.Event',
 40766         initialize: function () {
 40767           this._stopPropagation = false;
 40768           this._stopImmediatePropagation = false;
 40769           this._isDefaultPrevented = false;
 40770           this._target = null;
 40771           this._currentTarget = null;
 40772           this._eventPhase = 2;
 40773         },
 40774         __glue__: {
 40775           native: {
 40776             instance: {
 40777               ctor: function ctor(type, bubbles, cancelable) {
 40778                 Counter.count('Event: ' + type);
 40779                 this._type = type;
 40780                 this._bubbles = bubbles;
 40781                 this._cancelable = cancelable;
 40782               },
 40783               stopPropagation: function stopPropagation() {
 40784                 this._stopPropagation = true;
 40785               },
 40786               stopImmediatePropagation: function stopImmediatePropagation() {
 40787                 this._stopImmediatePropagation = this._stopPropagation = true;
 40788               },
 40789               preventDefault: function preventDefault() {
 40790                 if (this._cancelable)
 40791                   this._isDefaultPrevented = true;
 40792               },
 40793               isDefaultPrevented: function isDefaultPrevented() {
 40794                 return this._isDefaultPrevented;
 40795               },
 40796               type: {
 40797                 get: function type() {
 40798                   return this._type;
 40800               },
 40801               bubbles: {
 40802                 get: function bubbles() {
 40803                   return this._bubbles;
 40805               },
 40806               cancelable: {
 40807                 get: function cancelable() {
 40808                   return this._cancelable;
 40810               },
 40811               target: {
 40812                 get: function target() {
 40813                   return this._target;
 40815               },
 40816               currentTarget: {
 40817                 get: function currentTarget() {
 40818                   return this._currentTarget;
 40820               },
 40821               eventPhase: {
 40822                 get: function eventPhase() {
 40823                   return this._eventPhase;
 40827           },
 40828           script: {
 40829             static: Glue.ALL,
 40830             instance: {
 40831               clone: 'open public clone'
 40835       };
 40836     }.call(this);
 40838 var EventDispatcherDefinition = function () {
 40839     var mouseEvents = {
 40840         click: true,
 40841         contextMenu: true,
 40842         doubleClick: true,
 40843         middleClick: true,
 40844         middleMouseDown: true,
 40845         middleMouseUp: true,
 40846         mouseDown: true,
 40847         mouseMove: true,
 40848         mouseOut: true,
 40849         mouseOver: true,
 40850         mouseUp: true,
 40851         mouseWheel: true,
 40852         releaseOutside: true,
 40853         rightClick: true,
 40854         rightMouseDown: true,
 40855         rightMouseUp: true,
 40856         rollOut: false,
 40857         rollOver: false
 40858       };
 40859     function doDispatchEvent(dispatcher, event, eventClass, bubbles) {
 40860       var target = dispatcher._target;
 40861       var type = event._type || event;
 40862       var listeners = dispatcher._listeners[type];
 40863       if (bubbles || typeof event === 'string' && mouseEvents[event] || event._bubbles) {
 40864         var ancestors = [];
 40865         var currentNode = target._parent;
 40866         while (currentNode) {
 40867           if (currentNode._hasEventListener(type)) {
 40868             ancestors.push(currentNode);
 40870           currentNode = currentNode._parent;
 40872         if (!listeners && !ancestors.length) {
 40873           return true;
 40875         var keepPropagating = true;
 40876         var i = ancestors.length;
 40877         while (i-- && keepPropagating) {
 40878           var currentTarget = ancestors[i];
 40879           var queue = currentTarget._captureListeners[type];
 40880           keepPropagating = processListeners(queue, event, eventClass, bubbles, target, currentTarget, 1);
 40882         if (listeners && keepPropagating) {
 40883           keepPropagating = processListeners(listeners, event, eventClass, bubbles, target);
 40885         for (var i = 0; i < ancestors.length && keepPropagating; i++) {
 40886           var currentTarget = ancestors[i];
 40887           var queue = currentTarget._listeners[type];
 40888           keepPropagating = processListeners(queue, event, eventClass, bubbles, target, currentTarget, 3);
 40890       } else if (listeners) {
 40891         processListeners(listeners, event, eventClass, bubbles, target);
 40893       return !event._isDefaultPrevented;
 40895     function processListeners(queue, event, eventClass, bubbles, target, currentTarget, eventPhase) {
 40896       if (queue) {
 40897         queue = queue.slice();
 40898         var needsInit = true;
 40899         try {
 40900           for (var i = 0; i < queue.length; i++) {
 40901             var item = queue[i];
 40902             var methodInfo = item.handleEvent.methodInfo;
 40903             if (methodInfo) {
 40904               if (methodInfo.parameters.length) {
 40905                 if (!methodInfo.parameters[0].isUsed) {
 40906                   item.handleEvent();
 40907                   continue;
 40911             if (needsInit) {
 40912               if (typeof event === 'string') {
 40913                 if (eventClass) {
 40914                   event = new eventClass(event);
 40915                 } else {
 40916                   if (mouseEvents[event]) {
 40917                     event = new flash.events.MouseEvent(event, mouseEvents[event]);
 40918                     if (target._stage) {
 40919                       event._localX = target.mouseX;
 40920                       event._localY = target.mouseY;
 40922                   } else {
 40923                     event = new flash.events.Event(event);
 40926               } else if (event._target) {
 40927                 event = event.clone();
 40929               event._target = target;
 40930               event._currentTarget = currentTarget || target;
 40931               event._eventPhase = eventPhase || 2;
 40932               needsInit = false;
 40934             item.handleEvent(event);
 40935             if (event._stopImmediatePropagation) {
 40936               break;
 40939         } catch (e) {
 40940           avm2.exceptions.push({
 40941             source: 'avm2',
 40942             message: e.message,
 40943             stack: e.stack
 40944           });
 40945           throw e;
 40948       return !event._stopPropagation;
 40950     return {
 40951       __class__: 'flash.events.EventDispatcher',
 40952       initialize: function () {
 40953         this._target = this;
 40954         this._listeners = {};
 40955         this._captureListeners = {};
 40956       },
 40957       _addEventListenerImpl: function addEventListenerImpl(type, listener, useCapture, priority) {
 40958         if (typeof listener !== 'function') {
 40959           throwError('TypeError', Errors.CheckTypeFailedError, listener, 'Function');
 40961         var listeners = useCapture ? this._captureListeners : this._listeners;
 40962         var queue = listeners[type];
 40963         var listenerObj = {
 40964             handleEvent: listener,
 40965             priority: priority || 0
 40966           };
 40967         if (queue) {
 40968           var level = queue.length;
 40969           var i = level;
 40970           while (i--) {
 40971             var item = queue[i];
 40972             if (item.handleEvent === listener) {
 40973               return;
 40975             if (priority > item.priority) {
 40976               level = i;
 40979           queue.splice(level, 0, listenerObj);
 40980         } else {
 40981           listeners[type] = [
 40982             listenerObj
 40983           ];
 40985       },
 40986       _addEventListener: function addEventListener(type, listener, useCapture, priority) {
 40987         this._addEventListenerImpl(type, listener, useCapture, priority);
 40988       },
 40989       _removeEventListenerImpl: function removeEventListenerImpl(type, listener, useCapture) {
 40990         if (typeof listener !== 'function') {
 40991           throwError('TypeError', Errors.CheckTypeFailedError, listener, 'Function');
 40993         var listeners = useCapture ? this._captureListeners : this._listeners;
 40994         var queue = listeners[type];
 40995         if (queue) {
 40996           for (var i = 0; i < queue.length; i++) {
 40997             var item = queue[i];
 40998             if (item.handleEvent === listener) {
 40999               queue.splice(i, 1);
 41000               if (!queue.length) {
 41001                 listeners[type] = null;
 41003               return;
 41007       },
 41008       _removeEventListener: function removeEventListener(type, listener, useCapture) {
 41009         this._removeEventListenerImpl(type, listener, useCapture);
 41010       },
 41011       _hasEventListener: function hasEventListener(type) {
 41012         return this._listeners[type] || this._captureListeners[type];
 41013       },
 41014       _dispatchEvent: function dispatchEvent(event, eventClass, bubbles) {
 41015         doDispatchEvent(this, event, eventClass, bubbles);
 41016       },
 41017       __glue__: {
 41018         native: {
 41019           instance: {
 41020             ctor: function ctor(target) {
 41021               this._target = target || this;
 41022             },
 41023             addEventListener: function addEventListener(type, listener, useCapture, priority, useWeakReference) {
 41024               this._addEventListener(type, listener, useCapture, priority);
 41025             },
 41026             removeEventListener: function removeEventListener(type, listener, useCapture) {
 41027               this._removeEventListener(type, listener, useCapture);
 41028             },
 41029             hasEventListener: function hasEventListener(type) {
 41030               return this._hasEventListener(type);
 41031             },
 41032             willTrigger: function willTrigger(type) {
 41033               var currentNode = this._target;
 41034               do {
 41035                 if (currentNode._hasEventListener(type)) {
 41036                   return true;
 41038               } while (currentNode = currentNode._parent);
 41039               return false;
 41040             },
 41041             dispatchEventFunction: function dispatchEventFunction(event) {
 41042               return doDispatchEvent(this, event);
 41047     };
 41048   }.call(this);
 41049 var KeyboardEventDefinition = function () {
 41050     return {
 41051       __class__: 'flash.events.KeyboardEvent',
 41052       __glue__: {
 41053         native: {
 41054           instance: {
 41055             updateAfterEvent: function updateAfterEvent() {
 41056               notImplemented('KeyboardEvent.updateAfterEvent');
 41057             },
 41058             charCode: {
 41059               get: function charCode() {
 41060                 return this._charCode;
 41061               },
 41062               set: function charCode(value) {
 41063                 this._charCode = value;
 41065             },
 41066             ctrlKey: {
 41067               get: function ctrlKey() {
 41068                 return this._ctrlKey;
 41069               },
 41070               set: function ctrlKey(value) {
 41071                 this._ctrlKey = value;
 41073             },
 41074             altKey: {
 41075               get: function altKey() {
 41076                 return this._altKey;
 41077               },
 41078               set: function altKey(value) {
 41079                 this._altKey = value;
 41081             },
 41082             shiftKey: {
 41083               get: function shiftKey() {
 41084                 return this._shiftKey;
 41085               },
 41086               set: function shiftKey(value) {
 41087                 this._shiftKey = value;
 41091         },
 41092         script: {
 41093           static: Glue.ALL,
 41094           instance: {
 41095             keyCode: 'public keyCode'
 41099     };
 41100   }.call(this);
 41101 var MouseEventDefinition = function () {
 41102     return {
 41103       __class__: 'flash.events.MouseEvent',
 41104       initialize: function () {
 41105         this._localX = NaN;
 41106         this._localY = NaN;
 41107       },
 41108       __glue__: {
 41109         native: {
 41110           instance: {
 41111             updateAfterEvent: function updateAfterEvent() {
 41112             },
 41113             getStageX: function getStageX() {
 41114               if (this._target) {
 41115                 var m = this._target._getConcatenatedTransform(null, false);
 41116                 var x = m.a * this._localX + m.c * this._localY + m.tx;
 41117                 return x / 20;
 41119               return this._localX / 20;
 41120             },
 41121             getStageY: function getStageY() {
 41122               if (this._target) {
 41123                 var m = this._target._getConcatenatedTransform(null, false);
 41124                 var y = m.d * this._localY + m.b * this._localX + m.ty;
 41125                 return y / 20;
 41127               return this._localY / 20;
 41128             },
 41129             localX: {
 41130               get: function localX() {
 41131                 return this._localX / 20;
 41132               },
 41133               set: function localX(value) {
 41134                 this._localX = value * 20 | 0;
 41136             },
 41137             localY: {
 41138               get: function localY() {
 41139                 return this._localY / 20;
 41140               },
 41141               set: function localY(value) {
 41142                 this._localY = value * 20 | 0;
 41146         },
 41147         script: {
 41148           static: Glue.ALL
 41151     };
 41152   }.call(this);
 41153 var TextEventDefinition = function () {
 41154     return {
 41155       __class__: 'flash.events.TextEvent',
 41156       __glue__: {
 41157         native: {
 41158           instance: {
 41159             copyNativeData: function copyNativeData(other) {
 41160               notImplemented('TextEvent.copyNativeData');
 41165     };
 41166   }.call(this);
 41167 var TimerEventDefinition = function () {
 41168     return {
 41169       __class__: 'flash.events.TimerEvent',
 41170       __glue__: {
 41171         native: {
 41172           instance: {
 41173             updateAfterEvent: function updateAfterEvent() {
 41174               notImplemented('TimerEvent.updateAfterEvent');
 41179     };
 41180   }.call(this);
 41182   var ExternalInterfaceDefinition = function () {
 41183       function getAvailable() {
 41184         return true;
 41186       var initialized = false;
 41187       var registeredCallbacks = {};
 41188       function callIn(functionName, args) {
 41189         if (!registeredCallbacks.hasOwnProperty(functionName))
 41190           return;
 41191         return registeredCallbacks[functionName](functionName, args);
 41193       return {
 41194         __class__: 'flash.external.ExternalInterface',
 41195         initialize: function () {
 41196         },
 41197         __glue__: {
 41198           native: {
 41199             static: {
 41200               _initJS: function _initJS() {
 41201                 if (initialized)
 41202                   return;
 41203                 TelemetryService.reportTelemetry({
 41204                   topic: 'feature',
 41205                   feature: EXTERNAL_INTERFACE_FEATURE
 41206                 });
 41207                 initialized = true;
 41208                 FirefoxCom.initJS(callIn);
 41209               },
 41210               _getPropNames: function _getPropNames(obj) {
 41211                 var keys = [];
 41212                 forEachPublicProperty(obj, function (key) {
 41213                   keys.push(key);
 41214                 });
 41215                 return keys;
 41216               },
 41217               _addCallback: function _addCallback(functionName, closure, hasNullCallback) {
 41218                 FirefoxCom.request('externalCom', {
 41219                   action: 'register',
 41220                   functionName: functionName,
 41221                   remove: hasNullCallback
 41222                 });
 41223                 if (hasNullCallback) {
 41224                   delete registeredCallbacks[functionName];
 41225                 } else {
 41226                   registeredCallbacks[functionName] = closure;
 41228               },
 41229               _evalJS: function _evalJS(expression) {
 41230                 return FirefoxCom.requestSync('externalCom', {
 41231                   action: 'eval',
 41232                   expression: expression
 41233                 });
 41234               },
 41235               _callOut: function _callOut(request) {
 41236                 return FirefoxCom.requestSync('externalCom', {
 41237                   action: 'call',
 41238                   request: request
 41239                 });
 41240               },
 41241               available: {
 41242                 get: getAvailable
 41243               },
 41244               objectID: {
 41245                 get: function objectID() {
 41246                   return FirefoxCom.requestSync('externalCom', {
 41247                     action: 'getId'
 41248                   });
 41250               },
 41251               activeX: {
 41252                 get: function activeX() {
 41253                   return false;
 41256             },
 41257             instance: {}
 41260       };
 41261     }.call(this);
 41264   var BevelFilterDefinition = function () {
 41265       var def = {
 41266           __class__: 'flash.filters.BevelFilter',
 41267           initialize: function () {
 41268           },
 41269           _updateFilterBounds: function (bounds) {
 41271         };
 41272       def.__glue__ = {};
 41273       return def;
 41274     }.call(this);
 41276 var BitmapFilterDefinition = function () {
 41277     var def = {
 41278         __class__: 'flash.filters.BitmapFilter',
 41279         initialize: function () {
 41280         },
 41281         _updateFilterBounds: function (bounds) {
 41283       };
 41284     def.__glue__ = {};
 41285     return def;
 41286   }.call(this);
 41287 var BlurFilterDefinition = function () {
 41288     return {
 41289       __class__: 'flash.filters.BlurFilter',
 41290       initialize: function () {
 41291       },
 41292       _updateFilterBounds: function (bounds) {
 41293         var bx = this._blurX * this._quality * 20;
 41294         var by = this._blurY * this._quality * 20;
 41295         bounds.xMin -= bx;
 41296         bounds.xMax += bx;
 41297         bounds.yMin -= by;
 41298         bounds.yMax += by;
 41299       },
 41300       __glue__: {
 41301         native: {
 41302           static: {},
 41303           instance: {
 41304             blurX: {
 41305               get: function blurX() {
 41306                 return this._blurX;
 41307               },
 41308               set: function blurX(value) {
 41309                 this._blurX = value;
 41311             },
 41312             blurY: {
 41313               get: function blurY() {
 41314                 return this._blurY;
 41315               },
 41316               set: function blurY(value) {
 41317                 this._blurY = value;
 41319             },
 41320             quality: {
 41321               get: function quality() {
 41322                 return this._quality;
 41323               },
 41324               set: function quality(value) {
 41325                 this._quality = value;
 41331     };
 41332   }.call(this);
 41333 var ColorMatrixFilterDefinition = function () {
 41334     return {
 41335       __class__: 'flash.filters.ColorMatrixFilter',
 41336       initialize: function () {
 41337       },
 41338       _updateFilterBounds: function (bounds) {
 41339       },
 41340       __glue__: {
 41341         native: {
 41342           instance: {
 41343             matrix: {
 41344               get: function matrix() {
 41345                 return this._matrix;
 41346               },
 41347               set: function matrix(value) {
 41348                 this._matrix = value;
 41354     };
 41355   }.call(this);
 41356 var ConvolutionFilterDefinition = function () {
 41357     var def = {
 41358         __class__: 'flash.filters.ConvolutionFilter',
 41359         initialize: function () {
 41360         },
 41361         _updateFilterBounds: function (bounds) {
 41363       };
 41364     def.__glue__ = {};
 41365     return def;
 41366   }.call(this);
 41367 var DisplacementMapFilterDefinition = function () {
 41368     var def = {
 41369         __class__: 'flash.filters.DisplacementMapFilter',
 41370         initialize: function () {
 41371         },
 41372         _updateFilterBounds: function (bounds) {
 41374       };
 41375     def.__glue__ = {};
 41376     return def;
 41377   }.call(this);
 41378 var DropShadowFilterDefinition = function () {
 41379     return {
 41380       __class__: 'flash.filters.DropShadowFilter',
 41381       initialize: function () {
 41382       },
 41383       _updateFilterBounds: function (bounds) {
 41384         var a = this._angle * Math.PI / 180;
 41385         var dy = Math.sin(a) * this._distance;
 41386         var dx = Math.cos(a) * this._distance;
 41387         var bx = this._blurX * this._quality * 20;
 41388         var by = this._blurY * this._quality * 20;
 41389         bounds.xMin -= bx - (dx > 0 ? 0 : dx);
 41390         bounds.xMax += bx + Math.abs(dx);
 41391         bounds.yMin -= by - (dy > 0 ? 0 : dy);
 41392         bounds.yMax += by + Math.abs(dy);
 41393       },
 41394       __glue__: {
 41395         native: {
 41396           instance: {
 41397             distance: {
 41398               get: function distance() {
 41399                 return this._distance;
 41400               },
 41401               set: function distance(value) {
 41402                 this._distance = value;
 41404             },
 41405             angle: {
 41406               get: function angle() {
 41407                 return this._angle;
 41408               },
 41409               set: function angle(value) {
 41410                 this._angle = value;
 41412             },
 41413             color: {
 41414               get: function color() {
 41415                 return this._color;
 41416               },
 41417               set: function color(value) {
 41418                 this._color = value;
 41420             },
 41421             alpha: {
 41422               get: function alpha() {
 41423                 return this._alpha;
 41424               },
 41425               set: function alpha(value) {
 41426                 this._alpha = value;
 41428             },
 41429             blurX: {
 41430               get: function blurX() {
 41431                 return this._blurX;
 41432               },
 41433               set: function blurX(value) {
 41434                 this._blurX = value;
 41436             },
 41437             blurY: {
 41438               get: function blurY() {
 41439                 return this._blurY;
 41440               },
 41441               set: function blurY(value) {
 41442                 this._blurY = value;
 41444             },
 41445             hideObject: {
 41446               get: function hideObject() {
 41447                 return this._hideObject;
 41448               },
 41449               set: function hideObject(value) {
 41450                 this._hideObject = value;
 41452             },
 41453             inner: {
 41454               get: function inner() {
 41455                 return this._inner;
 41456               },
 41457               set: function inner(value) {
 41458                 this._inner = value;
 41460             },
 41461             knockout: {
 41462               get: function knockout() {
 41463                 return this._knockout;
 41464               },
 41465               set: function knockout(value) {
 41466                 this._knockout = value;
 41468             },
 41469             quality: {
 41470               get: function quality() {
 41471                 return this._quality;
 41472               },
 41473               set: function quality(value) {
 41474                 this._quality = value;
 41476             },
 41477             strength: {
 41478               get: function strength() {
 41479                 return this._strength;
 41480               },
 41481               set: function strength(value) {
 41482                 this._strength = value;
 41488     };
 41489   }.call(this);
 41490 var GlowFilterDefinition = function () {
 41491     return {
 41492       __class__: 'flash.filters.GlowFilter',
 41493       initialize: function () {
 41494       },
 41495       _updateFilterBounds: function (bounds) {
 41496         var bx = this._blurX * this._quality * 20;
 41497         var by = this._blurY * this._quality * 20;
 41498         bounds.xMin -= bx;
 41499         bounds.xMax += bx;
 41500         bounds.yMin -= by;
 41501         bounds.yMax += by;
 41502       },
 41503       __glue__: {
 41504         native: {
 41505           static: {},
 41506           instance: {
 41507             color: {
 41508               get: function color() {
 41509                 return this._color;
 41510               },
 41511               set: function color(value) {
 41512                 this._color = value;
 41514             },
 41515             alpha: {
 41516               get: function alpha() {
 41517                 return this._alpha;
 41518               },
 41519               set: function alpha(value) {
 41520                 this._alpha = value;
 41522             },
 41523             blurX: {
 41524               get: function blurX() {
 41525                 return this._blurX;
 41526               },
 41527               set: function blurX(value) {
 41528                 this._blurX = value;
 41530             },
 41531             blurY: {
 41532               get: function blurY() {
 41533                 return this._blurY;
 41534               },
 41535               set: function blurY(value) {
 41536                 this._blurY = value;
 41538             },
 41539             inner: {
 41540               get: function inner() {
 41541                 return this._inner;
 41542               },
 41543               set: function inner(value) {
 41544                 this._inner = value;
 41546             },
 41547             knockout: {
 41548               get: function knockout() {
 41549                 return this._knockout;
 41550               },
 41551               set: function knockout(value) {
 41552                 this._knockout = value;
 41554             },
 41555             quality: {
 41556               get: function quality() {
 41557                 return this._quality;
 41558               },
 41559               set: function quality(value) {
 41560                 this._quality = value;
 41562             },
 41563             strength: {
 41564               get: function strength() {
 41565                 return this._strength;
 41566               },
 41567               set: function strength(value) {
 41568                 this._strength = value;
 41574     };
 41575   }.call(this);
 41576 var GradientBevelFilterDefinition = function () {
 41577     var def = {
 41578         __class__: 'flash.filters.GradientBevelFilter',
 41579         initialize: function () {
 41580         },
 41581         _updateFilterBounds: function (bounds) {
 41583       };
 41584     def.__glue__ = {};
 41585     return def;
 41586   }.call(this);
 41587 var GradientGlowFilterDefinition = function () {
 41588     var def = {
 41589         __class__: 'flash.filters.GradientGlowFilter',
 41590         initialize: function () {
 41591         },
 41592         _updateFilterBounds: function (bounds) {
 41594       };
 41595     def.__glue__ = {};
 41596     return def;
 41597   }.call(this);
 41598 var ShaderFilterDefinition = function () {
 41599     var def = {
 41600         __class__: 'flash.filters.ShaderFilter',
 41601         initialize: function () {
 41602         },
 41603         _updateFilterBounds: function (bounds) {
 41605       };
 41606     def.__glue__ = {};
 41607     return def;
 41608   }.call(this);
 41610   var ColorTransformDefinition = function () {
 41611       return {
 41612         __class__: 'flash.geom.ColorTransform',
 41613         __glue__: {
 41614           script: {
 41615             instance: Glue.ALL
 41618       };
 41619     }.call(this);
 41621 var MatrixDefinition = function () {
 41622     return {
 41623       __class__: 'flash.geom.Matrix',
 41624       __glue__: {
 41625         script: {
 41626           instance: Glue.ALL
 41629     };
 41630   }.call(this);
 41631 var Matrix3DDefinition = function () {
 41632     var precision = 1e-7;
 41633     var transposeTransform = new Uint32Array([
 41634         0,
 41635         4,
 41636         8,
 41637         12,
 41638         1,
 41639         5,
 41640         9,
 41641         13,
 41642         2,
 41643         6,
 41644         10,
 41645         14,
 41646         3,
 41647         7,
 41648         11,
 41649         15
 41650       ]);
 41651     function getRotationMatrix(theta, u, v, w, a, b, c) {
 41652       var u2 = u * u, v2 = v * v, w2 = w * w;
 41653       var L2 = u2 + v2 + w2, L = Math.sqrt(L2);
 41654       u /= L;
 41655       v /= L;
 41656       w /= L;
 41657       u2 /= L2;
 41658       v2 /= L2;
 41659       w2 /= L2;
 41660       var cos = Math.cos(theta), sin = Math.sin(theta);
 41661       return new flash.geom.Matrix3D([
 41662         u2 + (v2 + w2) * cos,
 41663         u * v * (1 - cos) + w * sin,
 41664         u * w * (1 - cos) - v * sin,
 41665         0,
 41666         u * v * (1 - cos) - w * sin,
 41667         v2 + (u2 + w2) * cos,
 41668         v * w * (1 - cos) + u * sin,
 41669         0,
 41670         u * w * (1 - cos) + v * sin,
 41671         v * w * (1 - cos) - u * sin,
 41672         w2 + (u2 + v2) * cos,
 41673         0,
 41674         (a * (v2 + w2) - u * (b * v + c * w)) * (1 - cos) + (b * w - c * v) * sin,
 41675         (b * (u2 + w2) - v * (a * u + c * w)) * (1 - cos) + (c * u - a * w) * sin,
 41676         (c * (u2 + v2) - w * (a * u + b * v)) * (1 - cos) + (a * v - b * u) * sin,
 41678       ]);
 41680     return {
 41681       __class__: 'flash.geom.Matrix3D',
 41682       initialize: function () {
 41683       },
 41684       __glue__: {
 41685         native: {
 41686           static: {
 41687             interpolate: function interpolate(thisMat, toMat, percent) {
 41688               notImplemented('Matrix3D.interpolate');
 41690           },
 41691           instance: {
 41692             ctor: function ctor(v) {
 41693               this._matrix = new Float32Array(16);
 41694               if (v && v.length >= 16) {
 41695                 this.copyRawDataFrom(v, 0, false);
 41696               } else {
 41697                 this.identity();
 41699             },
 41700             clone: function clone() {
 41701               return new flash.geom.Matrix3D(this._matrix);
 41702             },
 41703             copyToMatrix3D: function copyToMatrix3D(dest) {
 41704               dest._matrix.set(this._matrix);
 41705             },
 41706             append: function append(lhs) {
 41707               var ma = lhs._matrix, mb = this._matrix, m = this._matrix;
 41708               var ma11 = ma[0], ma12 = ma[4], ma13 = ma[8], ma14 = ma[12], ma21 = ma[1], ma22 = ma[5], ma23 = ma[9], ma24 = ma[13], ma31 = ma[2], ma32 = ma[6], ma33 = ma[10], ma34 = ma[14], ma41 = ma[3], ma42 = ma[7], ma43 = ma[11], ma44 = ma[15];
 41709               var mb11 = mb[0], mb12 = mb[4], mb13 = mb[8], mb14 = mb[12], mb21 = mb[1], mb22 = mb[5], mb23 = mb[9], mb24 = mb[13], mb31 = mb[2], mb32 = mb[6], mb33 = mb[10], mb34 = mb[14], mb41 = mb[3], mb42 = mb[7], mb43 = mb[11], mb44 = mb[15];
 41710               m[0] = ma11 * mb11 + ma12 * mb21 + ma13 * mb31 + ma14 * mb41;
 41711               m[1] = ma21 * mb11 + ma22 * mb21 + ma23 * mb31 + ma24 * mb41;
 41712               m[2] = ma31 * mb11 + ma32 * mb21 + ma33 * mb31 + ma34 * mb41;
 41713               m[3] = ma41 * mb11 + ma42 * mb21 + ma43 * mb31 + ma44 * mb41;
 41714               m[4] = ma11 * mb12 + ma12 * mb22 + ma13 * mb32 + ma14 * mb42;
 41715               m[5] = ma21 * mb12 + ma22 * mb22 + ma23 * mb32 + ma24 * mb42;
 41716               m[6] = ma31 * mb12 + ma32 * mb22 + ma33 * mb32 + ma34 * mb42;
 41717               m[7] = ma41 * mb12 + ma42 * mb22 + ma43 * mb32 + ma44 * mb42;
 41718               m[8] = ma11 * mb13 + ma12 * mb23 + ma13 * mb33 + ma14 * mb43;
 41719               m[9] = ma21 * mb13 + ma22 * mb23 + ma23 * mb33 + ma24 * mb43;
 41720               m[10] = ma31 * mb13 + ma32 * mb23 + ma33 * mb33 + ma34 * mb43;
 41721               m[11] = ma41 * mb13 + ma42 * mb23 + ma43 * mb33 + ma44 * mb43;
 41722               m[12] = ma11 * mb14 + ma12 * mb24 + ma13 * mb34 + ma14 * mb44;
 41723               m[13] = ma21 * mb14 + ma22 * mb24 + ma23 * mb34 + ma24 * mb44;
 41724               m[14] = ma31 * mb14 + ma32 * mb24 + ma33 * mb34 + ma34 * mb44;
 41725               m[15] = ma41 * mb14 + ma42 * mb24 + ma43 * mb34 + ma44 * mb44;
 41726             },
 41727             prepend: function prepend(rhs) {
 41728               var ma = this._matrix, mb = rhs._matrix, m = this._matrix;
 41729               var ma11 = ma[0], ma12 = ma[4], ma13 = ma[8], ma14 = ma[12], ma21 = ma[1], ma22 = ma[5], ma23 = ma[9], ma24 = ma[13], ma31 = ma[2], ma32 = ma[6], ma33 = ma[10], ma34 = ma[14], ma41 = ma[3], ma42 = ma[7], ma43 = ma[11], ma44 = ma[15];
 41730               var mb11 = mb[0], mb12 = mb[4], mb13 = mb[8], mb14 = mb[12], mb21 = mb[1], mb22 = mb[5], mb23 = mb[9], mb24 = mb[13], mb31 = mb[2], mb32 = mb[6], mb33 = mb[10], mb34 = mb[14], mb41 = mb[3], mb42 = mb[7], mb43 = mb[11], mb44 = mb[15];
 41731               m[0] = ma11 * mb11 + ma12 * mb21 + ma13 * mb31 + ma14 * mb41;
 41732               m[1] = ma21 * mb11 + ma22 * mb21 + ma23 * mb31 + ma24 * mb41;
 41733               m[2] = ma31 * mb11 + ma32 * mb21 + ma33 * mb31 + ma34 * mb41;
 41734               m[3] = ma41 * mb11 + ma42 * mb21 + ma43 * mb31 + ma44 * mb41;
 41735               m[4] = ma11 * mb12 + ma12 * mb22 + ma13 * mb32 + ma14 * mb42;
 41736               m[5] = ma21 * mb12 + ma22 * mb22 + ma23 * mb32 + ma24 * mb42;
 41737               m[6] = ma31 * mb12 + ma32 * mb22 + ma33 * mb32 + ma34 * mb42;
 41738               m[7] = ma41 * mb12 + ma42 * mb22 + ma43 * mb32 + ma44 * mb42;
 41739               m[8] = ma11 * mb13 + ma12 * mb23 + ma13 * mb33 + ma14 * mb43;
 41740               m[9] = ma21 * mb13 + ma22 * mb23 + ma23 * mb33 + ma24 * mb43;
 41741               m[10] = ma31 * mb13 + ma32 * mb23 + ma33 * mb33 + ma34 * mb43;
 41742               m[11] = ma41 * mb13 + ma42 * mb23 + ma43 * mb33 + ma44 * mb43;
 41743               m[12] = ma11 * mb14 + ma12 * mb24 + ma13 * mb34 + ma14 * mb44;
 41744               m[13] = ma21 * mb14 + ma22 * mb24 + ma23 * mb34 + ma24 * mb44;
 41745               m[14] = ma31 * mb14 + ma32 * mb24 + ma33 * mb34 + ma34 * mb44;
 41746               m[15] = ma41 * mb14 + ma42 * mb24 + ma43 * mb34 + ma44 * mb44;
 41747             },
 41748             invert: function invert() {
 41749               var d = this.determinant;
 41750               if (Math.abs(d) < precision) {
 41751                 return false;
 41753               d = 1 / d;
 41754               var m = this._matrix;
 41755               var m11 = m[0], m12 = m[1], m13 = m[2], m14 = m[3], m21 = m[4], m22 = m[5], m23 = m[6], m24 = m[7], m31 = m[8], m32 = m[9], m33 = m[10], m34 = m[11], m41 = m[12], m42 = m[13], m43 = m[14], m44 = m[15];
 41756               m[0] = d * (m22 * (m33 * m44 - m43 * m34) - m32 * (m23 * m44 - m43 * m24) + m42 * (m23 * m34 - m33 * m24));
 41757               m[1] = -d * (m12 * (m33 * m44 - m43 * m34) - m32 * (m13 * m44 - m43 * m14) + m42 * (m13 * m34 - m33 * m14));
 41758               m[2] = d * (m12 * (m23 * m44 - m43 * m24) - m22 * (m13 * m44 - m43 * m14) + m42 * (m13 * m24 - m23 * m14));
 41759               m[3] = -d * (m12 * (m23 * m34 - m33 * m24) - m22 * (m13 * m34 - m33 * m14) + m32 * (m13 * m24 - m23 * m14));
 41760               m[4] = -d * (m21 * (m33 * m44 - m43 * m34) - m31 * (m23 * m44 - m43 * m24) + m41 * (m23 * m34 - m33 * m24));
 41761               m[5] = d * (m11 * (m33 * m44 - m43 * m34) - m31 * (m13 * m44 - m43 * m14) + m41 * (m13 * m34 - m33 * m14));
 41762               m[6] = -d * (m11 * (m23 * m44 - m43 * m24) - m21 * (m13 * m44 - m43 * m14) + m41 * (m13 * m24 - m23 * m14));
 41763               m[7] = d * (m11 * (m23 * m34 - m33 * m24) - m21 * (m13 * m34 - m33 * m14) + m31 * (m13 * m24 - m23 * m14));
 41764               m[8] = d * (m21 * (m32 * m44 - m42 * m34) - m31 * (m22 * m44 - m42 * m24) + m41 * (m22 * m34 - m32 * m24));
 41765               m[9] = -d * (m11 * (m32 * m44 - m42 * m34) - m31 * (m12 * m44 - m42 * m14) + m41 * (m12 * m34 - m32 * m14));
 41766               m[10] = d * (m11 * (m22 * m44 - m42 * m24) - m21 * (m12 * m44 - m42 * m14) + m41 * (m12 * m24 - m22 * m14));
 41767               m[11] = -d * (m11 * (m22 * m34 - m32 * m24) - m21 * (m12 * m34 - m32 * m14) + m31 * (m12 * m24 - m22 * m14));
 41768               m[12] = -d * (m21 * (m32 * m43 - m42 * m33) - m31 * (m22 * m43 - m42 * m23) + m41 * (m22 * m33 - m32 * m23));
 41769               m[13] = d * (m11 * (m32 * m43 - m42 * m33) - m31 * (m12 * m43 - m42 * m13) + m41 * (m12 * m33 - m32 * m13));
 41770               m[14] = -d * (m11 * (m22 * m43 - m42 * m23) - m21 * (m12 * m43 - m42 * m13) + m41 * (m12 * m23 - m22 * m13));
 41771               m[15] = d * (m11 * (m22 * m33 - m32 * m23) - m21 * (m12 * m33 - m32 * m13) + m31 * (m12 * m23 - m22 * m13));
 41772               return true;
 41773             },
 41774             identity: function identity() {
 41775               var m = this._matrix;
 41776               m[0] = m[5] = m[10] = m[15] = 1;
 41777               m[1] = m[2] = m[3] = m[4] = m[6] = m[7] = m[8] = m[9] = m[11] = m[12] = m[13] = m[14] = 0;
 41778             },
 41779             decompose: function decompose(orientationStyle) {
 41780               notImplemented('Matrix3D.decompose');
 41781             },
 41782             recompose: function recompose(components, orientationStyle) {
 41783               notImplemented('Matrix3D.recompose');
 41784             },
 41785             appendTranslation: function appendTranslation(x, y, z) {
 41786               var m = this._matrix;
 41787               var m41 = m[3], m42 = m[7], m43 = m[11], m44 = m[15];
 41788               m[0] += x * m41;
 41789               m[1] += y * m41;
 41790               m[2] += z * m41;
 41791               m[4] += x * m42;
 41792               m[5] += y * m42;
 41793               m[6] += z * m42;
 41794               m[8] += x * m43;
 41795               m[9] += y * m43;
 41796               m[10] += z * m43;
 41797               m[12] += x * m44;
 41798               m[13] += y * m44;
 41799               m[14] += z * m44;
 41800             },
 41801             appendRotation: function appendRotation(degrees, axis, pivotPoint) {
 41802               this.append(getRotationMatrix(degrees / 180 * Math.PI, axis.x, axis.y, axis.z, pivotPoint ? pivotPoint.x : 0, pivotPoint ? pivotPoint.y : 0, pivotPoint ? pivotPoint.z : 0));
 41803             },
 41804             appendScale: function appendScale(xScale, yScale, zScale) {
 41805               var m = this._matrix;
 41806               m[0] *= xScale;
 41807               m[1] *= yScale;
 41808               m[2] *= zScale;
 41809               m[4] *= xScale;
 41810               m[5] *= yScale;
 41811               m[6] *= zScale;
 41812               m[8] *= xScale;
 41813               m[9] *= yScale;
 41814               m[10] *= zScale;
 41815               m[12] *= xScale;
 41816               m[13] *= yScale;
 41817               m[14] *= zScale;
 41818             },
 41819             prependTranslation: function prependTranslation(x, y, z) {
 41820               var m = this._matrix;
 41821               var m11 = m[0], m12 = m[4], m13 = m[8], m14 = m[12], m21 = m[1], m22 = m[5], m23 = m[9], m24 = m[13], m31 = m[2], m32 = m[6], m33 = m[10], m34 = m[14], m41 = m[3], m42 = m[7], m43 = m[11], m44 = m[15];
 41822               m[12] += m11 * x + m12 * y + m13 * z;
 41823               m[13] += m21 * x + m22 * y + m23 * z;
 41824               m[14] += m31 * x + m32 * y + m33 * z;
 41825               m[15] += m41 * x + m42 * y + m43 * z;
 41826             },
 41827             prependRotation: function prependRotation(degrees, axis, pivotPoint) {
 41828               this.prepend(getRotationMatrix(degrees / 180 * Math.PI, axis.x, axis.y, axis.z, pivotPoint ? pivotPoint.x : 0, pivotPoint ? pivotPoint.y : 0, pivotPoint ? pivotPoint.z : 0));
 41829             },
 41830             prependScale: function prependScale(xScale, yScale, zScale) {
 41831               var m = this._matrix;
 41832               m[0] *= xScale;
 41833               m[1] *= xScale;
 41834               m[2] *= xScale;
 41835               m[3] *= xScale;
 41836               m[4] *= yScale;
 41837               m[5] *= yScale;
 41838               m[6] *= yScale;
 41839               m[7] *= yScale;
 41840               m[8] *= zScale;
 41841               m[9] *= zScale;
 41842               m[10] *= zScale;
 41843               m[11] *= zScale;
 41844             },
 41845             transformVector: function transformVector(v) {
 41846               var m = this._matrix;
 41847               var x = v.x, y = v.y, z = v.z;
 41848               return new flash.geom.Vector3D(m[0] * x + m[4] * y + m[8] * z + m[12], m[1] * x + m[5] * y + m[9] * z + m[13], m[2] * x + m[6] * y + m[10] * z + m[14]);
 41849             },
 41850             deltaTransformVector: function deltaTransformVector(v) {
 41851               var m = this._matrix;
 41852               var x = v.x, y = v.y, z = v.z;
 41853               return new flash.geom.Vector3D(m[0] * x + m[4] * y + m[8] * z, m[1] * x + m[5] * y + m[9] * z, m[2] * x + m[6] * y + m[10] * z);
 41854             },
 41855             transformVectors: function transformVectors(vin, vout) {
 41856               var m = this._matrix;
 41857               var m11 = m[0], m12 = m[4], m13 = m[8], m14 = m[12], m21 = m[1], m22 = m[5], m23 = m[9], m24 = m[13], m31 = m[2], m32 = m[6], m33 = m[10], m34 = m[14], m41 = m[3], m42 = m[7], m43 = m[11], m44 = m[15];
 41858               for (var i = 0; i < vin.length - 2; i += 3) {
 41859                 var x = vin.asGetNumericProperty(i), y = vin.asGetNumericProperty(i + 1), z = vin.asGetNumericProperty(i + 2);
 41860                 vout.push(m11 * x + m12 * y + m13 * z + m14);
 41861                 vout.push(m21 * x + m22 * y + m23 * z + m24);
 41862                 vout.push(m31 * x + m32 * y + m33 * z + m34);
 41864             },
 41865             transpose: function transpose() {
 41866               var m = this._matrix;
 41867               var tmp;
 41868               tmp = m[1];
 41869               m[1] = m[4];
 41870               m[4] = tmp;
 41871               tmp = m[2];
 41872               m[2] = m[8];
 41873               m[5] = tmp;
 41874               tmp = m[3];
 41875               m[3] = m[12];
 41876               m[12] = tmp;
 41877               tmp = m[6];
 41878               m[6] = m[9];
 41879               m[9] = tmp;
 41880               tmp = m[7];
 41881               m[7] = m[13];
 41882               m[13] = tmp;
 41883               tmp = m[11];
 41884               m[11] = m[14];
 41885               m[14] = tmp;
 41886             },
 41887             pointAt: function pointAt(pos, at, up) {
 41888               notImplemented('Matrix3D.pointAt');
 41889             },
 41890             interpolateTo: function interpolateTo(toMat, percent) {
 41891               notImplemented('Matrix3D.interpolateTo');
 41892             },
 41893             copyFrom: function copyFrom(sourceMatrix3D) {
 41894               this._matrix.set(sourceMatrix3D._matrix);
 41895             },
 41896             copyRawDataTo: function copyRawDataTo(vector, index, transpose) {
 41897               var m = this._matrix;
 41898               if (transpose) {
 41899                 for (var i = 0, j = index | 0; i < 16; i++, j++) {
 41900                   vector.asSetNumericProperty(j, m[transposeTransform[i]]);
 41902               } else {
 41903                 for (var i = 0, j = index | 0; i < 16; i++, j++) {
 41904                   vector.asSetNumericProperty(j, m[i]);
 41907             },
 41908             copyRawDataFrom: function copyRawDataFrom(vector, index, transpose) {
 41909               var m = this._matrix;
 41910               if (transpose) {
 41911                 for (var i = 0, j = index | 0; i < 16; i++, j++) {
 41912                   m[transposeTransform[i]] = vector.asGetNumericProperty(j) || 0;
 41914               } else {
 41915                 for (var i = 0, j = index | 0; i < 16; i++, j++) {
 41916                   m[i] = vector.asGetNumericProperty(j) || 0;
 41919             },
 41920             copyRowTo: function copyRowTo(row, vector3D) {
 41921               var offset = row | 0;
 41922               var m = this._matrix;
 41923               vector3D.x = m[offset];
 41924               vector3D.y = m[offset + 4];
 41925               vector3D.z = m[offset + 8];
 41926               vector3D.w = m[offset + 12];
 41927             },
 41928             copyColumnTo: function copyColumnTo(column, vector3D) {
 41929               var offset = column << 2;
 41930               var m = this._matrix;
 41931               vector3D.x = m[offset];
 41932               vector3D.y = m[offset + 1];
 41933               vector3D.z = m[offset + 2];
 41934               vector3D.w = m[offset + 3];
 41935             },
 41936             copyRowFrom: function copyRowFrom(row, vector3D) {
 41937               var offset = row | 0;
 41938               var m = this._matrix;
 41939               m[offset] = vector3D.x;
 41940               m[offset + 4] = vector3D.y;
 41941               m[offset + 8] = vector3D.z;
 41942               m[offset + 12] = vector3D.w;
 41943             },
 41944             copyColumnFrom: function copyColumnFrom(column, vector3D) {
 41945               var offset = column << 2;
 41946               var m = this._matrix;
 41947               m[offset] = vector3D.x;
 41948               m[offset + 1] = vector3D.y;
 41949               m[offset + 2] = vector3D.z;
 41950               m[offset + 3] = vector3D.w;
 41951             },
 41952             rawData: {
 41953               get: function rawData() {
 41954                 var result = new Float64Vector();
 41955                 this.copyRawDataTo(result, 0, false);
 41956                 return result;
 41957               },
 41958               set: function rawData(v) {
 41959                 this.copyRawDataFrom(v, 0, false);
 41961             },
 41962             position: {
 41963               get: function position() {
 41964                 var m = this._matrix;
 41965                 return new flash.geom.Vector3D(m[12], m[13], m[14]);
 41966               },
 41967               set: function position(pos) {
 41968                 var m = this._matrix;
 41969                 m[12] = pos.x;
 41970                 m[13] = pos.y;
 41971                 m[14] = pos.z;
 41973             },
 41974             determinant: {
 41975               get: function determinant() {
 41976                 var m = this._matrix;
 41977                 var m11 = m[0], m12 = m[4], m13 = m[8], m14 = m[12], m21 = m[1], m22 = m[5], m23 = m[9], m24 = m[13], m31 = m[2], m32 = m[6], m33 = m[10], m34 = m[14], m41 = m[3], m42 = m[7], m43 = m[11], m44 = m[15];
 41978                 var d;
 41979                 d = m11 * (m22 * (m33 * m44 - m43 * m34) - m32 * (m23 * m44 - m43 * m24) + m42 * (m23 * m34 - m33 * m24)) - m21 * (m12 * (m33 * m44 - m43 * m34) - m32 * (m13 * m44 - m43 * m14) + m42 * (m13 * m34 - m33 * m14)) + m31 * (m12 * (m23 * m44 - m43 * m24) - m22 * (m13 * m44 - m43 * m14) + m42 * (m13 * m24 - m23 * m14)) - m41 * (m12 * (m23 * m34 - m33 * m24) - m22 * (m13 * m34 - m33 * m14) + m32 * (m13 * m24 - m23 * m14));
 41980                 return d;
 41984         },
 41985         script: {
 41986           instance: Glue.ALL
 41989     };
 41990   }.call(this);
 41991 var PointDefinition = function () {
 41992     return {
 41993       __class__: 'flash.geom.Point',
 41994       __glue__: {
 41995         script: {
 41996           static: Glue.ALL,
 41997           instance: Glue.ALL
 42000     };
 42001   }.call(this);
 42002 var RectangleDefinition = function () {
 42003     return {
 42004       __class__: 'flash.geom.Rectangle',
 42005       __glue__: {
 42006         script: {
 42007           instance: Glue.ALL
 42010     };
 42011   }.call(this);
 42012 var TransformDefinition = function () {
 42013     var def = {
 42014         __class__: 'flash.geom.Transform',
 42015         get colorTransform() {
 42016           var cxform = this._target._cxform;
 42017           if (cxform) {
 42018             return new flash.geom.ColorTransform(cxform.redMultiplier / 256, cxform.greenMultiplier / 256, cxform.blueMultiplier / 256, cxform.alphaMultiplier / 256, cxform.redOffset, cxform.greenOffset, cxform.blueOffset, cxform.alphaOffset);
 42019           } else {
 42020             return new flash.geom.ColorTransform();
 42022         },
 42023         set colorTransform(val) {
 42024           var CTClass = avm2.systemDomain.getClass('flash.geom.ColorTransform');
 42025           if (!CTClass.isInstanceOf(val)) {
 42026             throwError('TypeError', Errors.CheckTypeFailedError, val, 'flash.geom.ColorTransform');
 42028           this._target._cxform = {
 42029             redMultiplier: val.redMultiplier * 256,
 42030             greenMultiplier: val.greenMultiplier * 256,
 42031             blueMultiplier: val.blueMultiplier * 256,
 42032             alphaMultiplier: val.alphaMultiplier * 256,
 42033             redOffset: val.redOffset,
 42034             greenOffset: val.greenOffset,
 42035             blueOffset: val.blueOffset,
 42036             alphaOffset: val.alphaOffset
 42037           };
 42038           this._target._invalidate();
 42039         },
 42040         get concatenatedColorTransform() {
 42041           var cxform = this.colorTransform;
 42042           cxform.concat(this._target.parent.transform.concatenatedColorTransform);
 42043           return cxform;
 42044         },
 42045         get concatenatedMatrix() {
 42046           if (this._target._current3DTransform) {
 42047             return null;
 42049           var m = this._target._getConcatenatedTransform(null, false);
 42050           return new flash.geom.Matrix(m.a, m.b, m.c, m.d, m.tx / 20, m.ty / 20);
 42051         },
 42052         get matrix() {
 42053           if (this._target._current3DTransform) {
 42054             return null;
 42056           var m = this._target._currentTransform;
 42057           return new flash.geom.Matrix(m.a, m.b, m.c, m.d, m.tx / 20, m.ty / 20);
 42058         },
 42059         set matrix(val) {
 42060           if (!flash.geom.Matrix.class.isInstanceOf(val)) {
 42061             throwError('TypeError', Errors.CheckTypeFailedError, val, 'flash.geom.Matrix');
 42063           var target = this._target;
 42064           target._invalidate();
 42065           target._setTransformMatrix(val, true);
 42066           target._current3DTransform = null;
 42067           target._animated = false;
 42068         },
 42069         get matrix3D() {
 42070           var m = this._target._current3DTransform;
 42071           return m && m.clone();
 42072         },
 42073         set matrix3D(val) {
 42074           var Matrix3DClass = avm2.systemDomain.getClass('flash.geom.Matrix3D');
 42075           if (!Matrix3DClass.isInstanceOf(val)) {
 42076             throwError('TypeError', Errors.CheckTypeFailedError, val, 'flash.geom.Matrix3D');
 42078           var raw = val.rawData;
 42079           this.matrix = new flash.geom.Matrix(raw.asGetPublicProperty(0), raw.asGetPublicProperty(1), raw.asGetPublicProperty(4), raw.asGetPublicProperty(5), raw.asGetPublicProperty(12), raw.asGetPublicProperty(13));
 42080           this._target._current3DTransform = val;
 42081         },
 42082         ctor: function (target) {
 42083           this._target = target;
 42085       };
 42086     var desc = Object.getOwnPropertyDescriptor;
 42087     def.__glue__ = {
 42088       native: {
 42089         instance: {
 42090           colorTransform: desc(def, 'colorTransform'),
 42091           concatenatedColorTransform: desc(def, 'concatenatedColorTransform'),
 42092           concatenatedMatrix: desc(def, 'concatenatedMatrix'),
 42093           matrix: desc(def, 'matrix'),
 42094           matrix3D: desc(def, 'matrix3D'),
 42095           ctor: def.ctor
 42098     };
 42099     return def;
 42100   }.call(this);
 42101 var Vector3DDefinition = function () {
 42102     return {
 42103       __class__: 'flash.geom.Vector3D',
 42104       initialize: function () {
 42105       },
 42106       __glue__: {
 42107         script: {
 42108           instance: Glue.ALL
 42111     };
 42112   }.call(this);
 42114   var ID3InfoDefinition = function () {
 42115       return {
 42116         __glue__: {
 42117           script: {
 42118             instance: {
 42119               songName: 'public songName',
 42120               genre: 'public genre',
 42121               artist: 'public artist',
 42122               track: 'public track',
 42123               album: 'public album',
 42124               year: 'public year',
 42125               comment: 'public comment'
 42129       };
 42130     }.call(this);
 42132 var MicrophoneDefinition = function () {
 42133     return {
 42134       __class__: 'flash.media.Microphone',
 42135       initialize: function () {
 42136       },
 42137       __glue__: {
 42138         native: {
 42139           static: {
 42140             getMicrophone: function getMicrophone(index) {
 42141               notImplemented('Microphone.getMicrophone');
 42142             },
 42143             getEnhancedMicrophone: function getEnhancedMicrophone(index) {
 42144               notImplemented('Microphone.getEnhancedMicrophone');
 42145             },
 42146             names: {
 42147               get: function names() {
 42148                 notImplemented('Microphone.names');
 42150             },
 42151             isSupported: {
 42152               get: function isSupported() {
 42153                 notImplemented('Microphone.isSupported');
 42156           },
 42157           instance: {
 42158             setSilenceLevel: function setSilenceLevel(silenceLevel, timeout) {
 42159               notImplemented('Microphone.setSilenceLevel');
 42160             },
 42161             setUseEchoSuppression: function setUseEchoSuppression(useEchoSuppression) {
 42162               notImplemented('Microphone.setUseEchoSuppression');
 42163             },
 42164             setLoopBack: function setLoopBack(state) {
 42165               notImplemented('Microphone.setLoopBack');
 42166             },
 42167             gain: {
 42168               set: function gain(gain) {
 42169                 notImplemented('Microphone.gain');
 42170                 this._gain = gain;
 42171               },
 42172               get: function gain() {
 42173                 notImplemented('Microphone.gain');
 42174                 return this._gain;
 42176             },
 42177             rate: {
 42178               set: function rate(rate) {
 42179                 notImplemented('Microphone.rate');
 42180                 this._rate = rate;
 42181               },
 42182               get: function rate() {
 42183                 notImplemented('Microphone.rate');
 42184                 return this._rate;
 42186             },
 42187             codec: {
 42188               set: function codec(codec) {
 42189                 notImplemented('Microphone.codec');
 42190                 this._codec = codec;
 42191               },
 42192               get: function codec() {
 42193                 notImplemented('Microphone.codec');
 42194                 return this._codec;
 42196             },
 42197             framesPerPacket: {
 42198               get: function framesPerPacket() {
 42199                 notImplemented('Microphone.framesPerPacket');
 42200                 return this._framesPerPacket;
 42201               },
 42202               set: function framesPerPacket(frames) {
 42203                 notImplemented('Microphone.framesPerPacket');
 42204                 this._framesPerPacket = frames;
 42206             },
 42207             encodeQuality: {
 42208               get: function encodeQuality() {
 42209                 notImplemented('Microphone.encodeQuality');
 42210                 return this._encodeQuality;
 42211               },
 42212               set: function encodeQuality(quality) {
 42213                 notImplemented('Microphone.encodeQuality');
 42214                 this._encodeQuality = quality;
 42216             },
 42217             noiseSuppressionLevel: {
 42218               get: function noiseSuppressionLevel() {
 42219                 notImplemented('Microphone.noiseSuppressionLevel');
 42220                 return this._noiseSuppressionLevel;
 42221               },
 42222               set: function noiseSuppressionLevel(level) {
 42223                 notImplemented('Microphone.noiseSuppressionLevel');
 42224                 this._noiseSuppressionLevel = level;
 42226             },
 42227             enableVAD: {
 42228               get: function enableVAD() {
 42229                 notImplemented('Microphone.enableVAD');
 42230                 return this._enableVAD;
 42231               },
 42232               set: function enableVAD(enable) {
 42233                 notImplemented('Microphone.enableVAD');
 42234                 this._enableVAD = enable;
 42236             },
 42237             activityLevel: {
 42238               get: function activityLevel() {
 42239                 notImplemented('Microphone.activityLevel');
 42240                 return this._activityLevel;
 42242             },
 42243             index: {
 42244               get: function index() {
 42245                 notImplemented('Microphone.index');
 42246                 return this._index;
 42248             },
 42249             muted: {
 42250               get: function muted() {
 42251                 notImplemented('Microphone.muted');
 42252                 return this._muted;
 42254             },
 42255             name: {
 42256               get: function name() {
 42257                 notImplemented('Microphone.name');
 42258                 return this._name;
 42260             },
 42261             silenceLevel: {
 42262               get: function silenceLevel() {
 42263                 notImplemented('Microphone.silenceLevel');
 42264                 return this._silenceLevel;
 42266             },
 42267             silenceTimeout: {
 42268               get: function silenceTimeout() {
 42269                 notImplemented('Microphone.silenceTimeout');
 42270                 return this._silenceTimeout;
 42272             },
 42273             useEchoSuppression: {
 42274               get: function useEchoSuppression() {
 42275                 notImplemented('Microphone.useEchoSuppression');
 42276                 return this._useEchoSuppression;
 42278             },
 42279             soundTransform: {
 42280               get: function soundTransform() {
 42281                 notImplemented('Microphone.soundTransform');
 42282                 return this._soundTransform;
 42283               },
 42284               set: function soundTransform(sndTransform) {
 42285                 notImplemented('Microphone.soundTransform');
 42286                 this._soundTransform = sndTransform;
 42288             },
 42289             enhancedOptions: {
 42290               get: function enhancedOptions() {
 42291                 notImplemented('Microphone.enhancedOptions');
 42292                 return this._enhancedOptions;
 42293               },
 42294               set: function enhancedOptions(options) {
 42295                 notImplemented('Microphone.enhancedOptions');
 42296                 this._enhancedOptions = options;
 42300         },
 42301         script: {
 42302           instance: Glue.ALL
 42305     };
 42306   }.call(this);
 42307 var PLAY_USING_AUDIO_TAG = true;
 42308 var SoundDefinition = function () {
 42309     function getAudioDescription(soundData, onComplete) {
 42310       var audioElement = document.createElement('audio');
 42311       if (!audioElement.canPlayType(soundData.mimeType)) {
 42312         onComplete({
 42313           duration: 0
 42314         });
 42315         return;
 42317       audioElement.preload = 'metadata';
 42318       var blob = new Blob([
 42319           soundData.data
 42320         ], {
 42321           type: soundData.mimeType
 42322         });
 42323       audioElement.src = URL.createObjectURL(blob);
 42324       audioElement.load();
 42325       audioElement.addEventListener('loadedmetadata', function () {
 42326         onComplete({
 42327           duration: this.duration * 1000
 42328         });
 42329       });
 42331     var def = {
 42332         initialize: function initialize() {
 42333           this._playQueue = [];
 42334           this._url = null;
 42335           this._length = 0;
 42336           this._bytesTotal = 0;
 42337           this._bytesLoaded = 0;
 42338           this._id3 = new flash.media.ID3Info();
 42339           var s = this.symbol;
 42340           if (s) {
 42341             var soundData = {};
 42342             if (s.pcm) {
 42343               soundData.sampleRate = s.sampleRate;
 42344               soundData.channels = s.channels;
 42345               soundData.pcm = s.pcm;
 42346               soundData.end = s.pcm.length;
 42348             soundData.completed = true;
 42349             if (s.packaged) {
 42350               soundData.data = s.packaged.data.buffer;
 42351               soundData.mimeType = s.packaged.mimeType;
 42353             var _this = this;
 42354             getAudioDescription(soundData, function (description) {
 42355               _this._length = description.duration;
 42356             });
 42357             this._soundData = soundData;
 42359           TelemetryService.reportTelemetry({
 42360             topic: 'feature',
 42361             feature: SOUND_FEATURE
 42362           });
 42363         },
 42364         close: function close() {
 42365           somewhatImplemented('Sound.close');
 42366         },
 42367         extract: function extract(target, length, startPosition) {
 42368           notImplemented('Sound.extract');
 42369         },
 42370         _load: function _load(request, checkPolicyFile, bufferTime) {
 42371           if (!request) {
 42372             return;
 42374           var _this = this;
 42375           var stream = this._stream = new flash.net.URLStream();
 42376           var ByteArrayClass = avm2.systemDomain.getClass('flash.utils.ByteArray');
 42377           var data = ByteArrayClass.createInstance();
 42378           var dataPosition = 0;
 42379           var mp3DecodingSession = null;
 42380           var soundData = {
 42381               completed: false
 42382             };
 42383           stream._addEventListener('progress', function (event) {
 42384             _this._bytesLoaded = event[Multiname.getPublicQualifiedName('bytesLoaded')];
 42385             _this._bytesTotal = event[Multiname.getPublicQualifiedName('bytesTotal')];
 42386             if (!PLAY_USING_AUDIO_TAG && !mp3DecodingSession) {
 42387               mp3DecodingSession = decodeMP3(soundData, function (duration, final) {
 42388                 if (_this._length === 0) {
 42389                   _this._soundData = soundData;
 42390                   _this._playQueue.forEach(function (item) {
 42391                     item.channel._playSoundDataViaChannel(soundData, item.startTime);
 42392                   });
 42394                 _this._length = final ? duration * 1000 : Math.max(duration, mp3DecodingSession.estimateDuration(_this._bytesTotal)) * 1000;
 42395               });
 42397             var bytesAvailable = stream.bytesAvailable;
 42398             stream.readBytes(data, dataPosition, bytesAvailable);
 42399             if (mp3DecodingSession) {
 42400               mp3DecodingSession.pushData(new Uint8Array(data.a, dataPosition, bytesAvailable));
 42402             dataPosition += bytesAvailable;
 42403             _this._dispatchEvent(event);
 42404           });
 42405           stream._addEventListener('complete', function (event) {
 42406             _this._dispatchEvent(event);
 42407             soundData.data = data.a;
 42408             soundData.mimeType = 'audio/mpeg';
 42409             soundData.completed = true;
 42410             if (PLAY_USING_AUDIO_TAG) {
 42411               _this._soundData = soundData;
 42412               getAudioDescription(soundData, function (description) {
 42413                 _this._length = description.duration;
 42414               });
 42415               _this._playQueue.forEach(function (item) {
 42416                 item.channel._playSoundDataViaAudio(soundData, item.startTime);
 42417               });
 42419             if (mp3DecodingSession) {
 42420               mp3DecodingSession.close();
 42422           });
 42423           stream.load(request);
 42424         },
 42425         loadCompressedDataFromByteArray: function loadCompressedDataFromByteArray(bytes, bytesLength) {
 42426           notImplemented('Sound#loadCompressedDataFromByteArray');
 42427         },
 42428         loadPCMFromByteArray: function loadPCMFromByteArray(bytes, samples, format, stereo, sampleRate) {
 42429           notImplemented('Sound#loadPCMFromByteArray');
 42430         },
 42431         play: function play(startTime, loops, soundTransform) {
 42432           startTime = startTime || 0;
 42433           loops = loops || 0;
 42434           var channel = new flash.media.SoundChannel();
 42435           channel._sound = this;
 42436           channel._soundTransform = isNullOrUndefined(soundTransform) ? new flash.media.SoundTransform() : soundTransform;
 42437           this._playQueue.push({
 42438             channel: channel,
 42439             startTime: startTime
 42440           });
 42441           if (this._soundData) {
 42442             if (PLAY_USING_AUDIO_TAG)
 42443               channel._playSoundDataViaAudio(this._soundData, startTime, loops);
 42444             else
 42445               channel._playSoundDataViaChannel(this._soundData, startTime, loops);
 42447           return channel;
 42448         },
 42449         get bytesLoaded() {
 42450           return this._bytesLoaded;
 42451         },
 42452         get bytesTotal() {
 42453           return this._bytesTotal;
 42454         },
 42455         get id3() {
 42456           return this._id3;
 42457         },
 42458         get isBuffering() {
 42459           notImplemented('Sound#isBuffering');
 42460         },
 42461         get isURLInaccessible() {
 42462           notImplemented('Sound#isURLInaccessible');
 42463         },
 42464         get length() {
 42465           return this._length;
 42466         },
 42467         get url() {
 42468           return this._url;
 42470       };
 42471     function decodeMP3(soundData, ondurationchanged) {
 42472       var currentSize = 8000;
 42473       var pcm = new Float32Array(currentSize);
 42474       var position = 0;
 42475       var lastTimeRatio = 0;
 42476       var durationEstimationData = {
 42477           estimateBitRate: true,
 42478           bitRateSum: 0,
 42479           bitRateCount: 0,
 42480           metadataSize: 0,
 42481           averageBitRate: 0
 42482         };
 42483       var mp3DecoderSession = new MP3DecoderSession();
 42484       mp3DecoderSession.onframedata = function (frame, channels, sampleRate, bitRate) {
 42485         if (durationEstimationData.estimateBitRate) {
 42486           var FramesToEstimate = 200;
 42487           if (durationEstimationData.bitRateCount < FramesToEstimate) {
 42488             durationEstimationData.bitRateSum += bitRate;
 42489             durationEstimationData.bitRateCount++;
 42490           } else {
 42491             durationEstimationData.estimateBitRate = false;
 42493           this.averageBitRate = durationEstimationData.bitRateSum / durationEstimationData.bitRateCount;
 42495         if (frame.length === 0)
 42496           return;
 42497         if (!position) {
 42498           soundData.sampleRate = sampleRate, soundData.channels = channels;
 42499           soundData.pcm = pcm;
 42501         if (position + frame.length >= currentSize) {
 42502           do {
 42503             currentSize *= 2;
 42504           } while (position + frame.length >= currentSize);
 42505           var newPcm = new Float32Array(currentSize);
 42506           newPcm.set(pcm);
 42507           pcm = soundData.pcm = newPcm;
 42509         pcm.set(frame, position);
 42510         soundData.end = position += frame.length;
 42511         lastTimeRatio = 1 / soundData.sampleRate / soundData.channels;
 42512         ondurationchanged(position * lastTimeRatio, false);
 42513       };
 42514       mp3DecoderSession.onid3tag = function (data) {
 42515         durationEstimationData.metadataSize += data.length;
 42516       }, mp3DecoderSession.onclosed = function () {
 42517         ondurationchanged(position * lastTimeRatio, true);
 42518       };
 42519       var completed = false;
 42520       return {
 42521         pushData: function (data) {
 42522           mp3DecoderSession.pushAsync(data);
 42523         },
 42524         estimateDuration: function (fileSize) {
 42525           return Math.max(0, (fileSize - durationEstimationData.metadataSize) * 8 / durationEstimationData.averageBitRate);
 42526         },
 42527         close: function () {
 42528           mp3DecoderSession.close();
 42530       };
 42532     var desc = Object.getOwnPropertyDescriptor;
 42533     def.__glue__ = {
 42534       native: {
 42535         instance: {
 42536           close: def.close,
 42537           extract: def.extract,
 42538           _load: def._load,
 42539           loadCompressedDataFromByteArray: def.loadCompressedDataFromByteArray,
 42540           loadPCMFromByteArray: def.loadPCMFromByteArray,
 42541           play: def.play,
 42542           bytesLoaded: desc(def, 'bytesLoaded'),
 42543           bytesTotal: desc(def, 'bytesTotal'),
 42544           id3: desc(def, 'id3'),
 42545           isBuffering: desc(def, 'isBuffering'),
 42546           isURLInaccessible: desc(def, 'isURLInaccessible'),
 42547           length: desc(def, 'length'),
 42548           url: desc(def, 'url')
 42551     };
 42552     return def;
 42553   }.call(this);
 42554 var SoundChannelDefinition = function () {
 42555     return {
 42556       initialize: function () {
 42557         this._element = null;
 42558         this._position = 0;
 42559         this._leftPeak = 0;
 42560         this._rightPeak = 0;
 42561         this._pcmData = null;
 42562         this._soundTransform = new flash.media.SoundTransform();
 42563         this._soundMixerClass = avm2.systemDomain.getClass('flash.media.SoundMixer');
 42564         var s = this.symbol;
 42565         if (s) {
 42566           this._element = s.element || null;
 42568         if (this._element) {
 42569           this._registerWithSoundMixer();
 42571       },
 42572       _registerWithSoundMixer: function () {
 42573         this._soundMixerClass.native.static._registerChannel(this);
 42574       },
 42575       _unregisterWithSoundMixer: function () {
 42576         this._soundMixerClass.native.static._unregisterChannel(this);
 42577       },
 42578       _applySoundTransform: function () {
 42579         var volume = this._soundTransform._volume;
 42580         if (this._soundMixerClass._soundTransform) {
 42581           volume *= this._soundMixerClass._soundTransform._volume;
 42583         volume *= this._soundMixerClass.native.static._getMasterVolume();
 42584         if (this._element) {
 42585           this._element.volume = clamp(volume, 0, 1);
 42587         if (this._audioChannel) {
 42589       },
 42590       _playSoundDataViaChannel: function (soundData, startTime, loops) {
 42591         this._registerWithSoundMixer();
 42592         var self = this;
 42593         var startPosition = Math.round(startTime / 1000 * soundData.sampleRate) * soundData.channels;
 42594         var position = startPosition;
 42595         this._position = startTime;
 42596         this._audioChannel = createAudioChannel(soundData.sampleRate, soundData.channels);
 42597         this._audioChannel.ondatarequested = function (e) {
 42598           var end = soundData.end;
 42599           if (position >= end && soundData.completed) {
 42600             self._unregisterWithSoundMixer();
 42601             self._audioChannel.stop();
 42602             self._dispatchEvent(new flash.events.Event('soundComplete', false, false));
 42603             return;
 42605           var left = e.count;
 42606           var data = e.data;
 42607           var source = soundData.pcm;
 42608           do {
 42609             var count = Math.min(end - position, left);
 42610             for (var j = 0; j < count; j++) {
 42611               data[j] = source[position++];
 42613             left -= count;
 42614             if (position >= end) {
 42615               if (!loops)
 42616                 break;
 42617               loops--;
 42618               position = startPosition;
 42620           } while (left > 0);
 42621           self._position = position / soundData.sampleRate / soundData.channels * 1000;
 42622         };
 42623         this._audioChannel.start();
 42624         this._applySoundTransform();
 42625       },
 42626       _playSoundDataViaAudio: function (soundData, startTime, loops) {
 42627         if (!soundData.mimeType)
 42628           return;
 42629         this._registerWithSoundMixer();
 42630         this._position = startTime;
 42631         var self = this;
 42632         var lastCurrentTime = 0;
 42633         var element = document.createElement('audio');
 42634         if (!element.canPlayType(soundData.mimeType)) {
 42635           console.error('ERROR: "' + soundData.mimeType + '" ' + 'type playback is not supported by the browser');
 42636           return;
 42638         element.preload = 'metadata';
 42639         element.loop = loops > 0;
 42640         var blob = new Blob([
 42641             soundData.data
 42642           ], {
 42643             type: soundData.mimeType
 42644           });
 42645         element.src = URL.createObjectURL(blob);
 42646         element.addEventListener('loadeddata', function loaded() {
 42647           element.currentTime = startTime / 1000;
 42648           element.play();
 42649         });
 42650         element.addEventListener('timeupdate', function timeupdate() {
 42651           var currentTime = element.currentTime;
 42652           if (loops && lastCurrentTime > currentTime) {
 42653             --loops;
 42654             if (!loops)
 42655               element.loop = false;
 42656             if (currentTime < startTime / 1000)
 42657               element.currentTime = startTime / 1000;
 42659           self._position = (lastCurrentTime = currentTime) * 1000;
 42660         });
 42661         element.addEventListener('ended', function ended() {
 42662           self._unregisterWithSoundMixer();
 42663           self._dispatchEvent(new flash.events.Event('soundComplete', false, false));
 42664           self._element = null;
 42665         });
 42666         this._element = element;
 42667         this._applySoundTransform();
 42668       },
 42669       __glue__: {
 42670         native: {
 42671           static: {},
 42672           instance: {
 42673             stop: function stop() {
 42674               if (this._element) {
 42675                 this._unregisterWithSoundMixer();
 42676                 this._element.pause();
 42678               if (this._audioChannel) {
 42679                 this._unregisterWithSoundMixer();
 42680                 this._audioChannel.stop();
 42682             },
 42683             'position': {
 42684               get: function position() {
 42685                 return this._position;
 42687             },
 42688             'leftPeak': {
 42689               get: function leftPeak() {
 42690                 return this._leftPeak;
 42692             },
 42693             'rightPeak': {
 42694               get: function rightPeak() {
 42695                 return this.rightPeak;
 42697             },
 42698             'soundTransform': {
 42699               get: function soundTransform() {
 42700                 somewhatImplemented('SoundChannel.soundTransform');
 42701                 return new flash.media.SoundTransform(this._soundTransform._volume, this._soundTransform.pan);
 42702               },
 42703               set: function soundTransform(soundTransform) {
 42704                 somewhatImplemented('SoundChannel.soundTransform');
 42705                 this._soundTransform = isNullOrUndefined(soundTransform) ? new flash.media.SoundTransform() : soundTransform;
 42706                 this._applySoundTransform();
 42710         },
 42711         script: {
 42712           instance: scriptProperties('public', [
 42713             'stop'
 42714           ])
 42717     };
 42718   }.call(this);
 42719 function createAudioChannel(sampleRate, channels) {
 42720   if (WebAudioChannel.isSupported)
 42721     return new WebAudioChannel(sampleRate, channels);
 42722   else
 42723     error('PCM data playback is not supported by the browser');
 42725 function AudioResampler(sourceRate, targetRate) {
 42726   this.sourceRate = sourceRate;
 42727   this.targetRate = targetRate;
 42728   this.tail = [];
 42729   this.sourceOffset = 0;
 42731 AudioResampler.prototype = {
 42732   ondatarequested: function (e) {
 42733   },
 42734   getData: function (channelsData, count) {
 42735     var k = this.sourceRate / this.targetRate;
 42736     var offset = this.sourceOffset;
 42737     var needed = Math.ceil((count - 1) * k + offset) + 1;
 42738     var sourceData = [];
 42739     for (var channel = 0; channel < channelsData.length; channel++)
 42740       sourceData.push(new Float32Array(needed));
 42741     var e = {
 42742         data: sourceData,
 42743         count: needed
 42744       };
 42745     this.ondatarequested(e);
 42746     for (var channel = 0; channel < channelsData.length; channel++) {
 42747       var data = channelsData[channel];
 42748       var source = sourceData[channel];
 42749       for (var j = 0; j < count; j++) {
 42750         var i = j * k + offset;
 42751         var i1 = i | 0, i2 = Math.ceil(i) | 0;
 42752         var source_i1 = i1 < 0 ? this.tail[channel] : source[i1];
 42753         if (i1 === i2) {
 42754           data[j] = source_i1;
 42755         } else {
 42756           var alpha = i - i1;
 42757           data[j] = source_i1 * (1 - alpha) + source[i2] * alpha;
 42760       this.tail[channel] = source[needed - 1];
 42762     this.sourceOffset = (count - 1) * k + offset - (needed - 1);
 42764 };
 42765 function WebAudioChannel(sampleRate, channels) {
 42766   var context = WebAudioChannel.context;
 42767   if (!context) {
 42768     if (typeof AudioContext !== 'undefined')
 42769       context = new AudioContext();
 42770     else
 42771       context = new webkitAudioContext();
 42772     WebAudioChannel.context = context;
 42774   this.context = context;
 42775   this.contextSampleRate = context.sampleRate || 44100;
 42776   this.channels = channels;
 42777   this.sampleRate = sampleRate;
 42778   if (this.contextSampleRate != sampleRate) {
 42779     this.resampler = new AudioResampler(sampleRate, this.contextSampleRate);
 42780     this.resampler.ondatarequested = function (e) {
 42781       this.requestData(e.data, e.count);
 42782     }.bind(this);
 42785 WebAudioChannel.prototype = {
 42786   start: function () {
 42787     var source = this.context.createScriptProcessor ? this.context.createScriptProcessor(2048, 0, this.channels) : this.context.createJavaScriptNode(2048, 0, this.channels);
 42788     var self = this;
 42789     source.onaudioprocess = function (e) {
 42790       var channelsData = [];
 42791       for (var i = 0; i < self.channels; i++)
 42792         channelsData.push(e.outputBuffer.getChannelData(i));
 42793       var count = channelsData[0].length;
 42794       if (self.resampler) {
 42795         self.resampler.getData(channelsData, count);
 42796       } else {
 42797         var e = {
 42798             data: channelsData,
 42799             count: count
 42800           };
 42801         self.requestData(channelsData, count);
 42803     };
 42804     source.connect(this.context.destination);
 42805     this.source = source;
 42806   },
 42807   stop: function () {
 42808     this.source.disconnect(this.context.destination);
 42809   },
 42810   requestData: function (channelsData, count) {
 42811     var channels = this.channels;
 42812     var buffer = new Float32Array(count * channels);
 42813     var e = {
 42814         data: buffer,
 42815         count: buffer.length
 42816       };
 42817     this.ondatarequested(e);
 42818     for (var j = 0, p = 0; j < count; j++) {
 42819       for (var i = 0; i < channels; i++)
 42820         channelsData[i][j] = buffer[p++];
 42823 };
 42824 WebAudioChannel.isSupported = function () {
 42825   return typeof AudioContext !== 'undefined' || typeof webkitAudioContext != 'undefined';
 42826 }();
 42827 var SoundMixerDefinition = function () {
 42828     var masterVolume = 1;
 42829     var registeredChannels = [];
 42830     return {
 42831       __class__: 'flash.media.SoundMixer',
 42832       initialize: function () {
 42833       },
 42834       __glue__: {
 42835         native: {
 42836           static: {
 42837             _registerChannel: function _registerChannel(channel) {
 42838               registeredChannels.push(channel);
 42839             },
 42840             _unregisterChannel: function _unregisterChannel(channel) {
 42841               var index = registeredChannels.indexOf(channel);
 42842               if (index >= 0)
 42843                 registeredChannels.splice(index, 1);
 42844             },
 42845             _getMasterVolume: function _getMasterVolume() {
 42846               return masterVolume;
 42847             },
 42848             _setMasterVolume: function _setMasterVolume(volume) {
 42849               masterVolume = volume;
 42850               registeredChannels.forEach(function (channel) {
 42851                 channel._applySoundTransform();
 42852               });
 42853             },
 42854             stopAll: function stopAll() {
 42855               registeredChannels.forEach(function (channel) {
 42856                 channel.stop();
 42857               });
 42858               registeredChannels = [];
 42859             },
 42860             computeSpectrum: function computeSpectrum(outputArray, FFTMode, stretchFactor) {
 42861               somewhatImplemented('SoundMixer.computeSpectrum');
 42862               var data = new Float32Array(1024);
 42863               for (var i = 0; i < 1024; i++) {
 42864                 data[i] = Math.random();
 42866               outputArray.writeRawBytes(data);
 42867               outputArray.position = 0;
 42868             },
 42869             areSoundsInaccessible: function areSoundsInaccessible() {
 42870               notImplemented('SoundMixer.areSoundsInaccessible');
 42871             },
 42872             bufferTime: {
 42873               get: function bufferTime() {
 42874                 notImplemented('SoundMixer.bufferTime');
 42875               },
 42876               set: function bufferTime(pA) {
 42877                 notImplemented('SoundMixer.bufferTime');
 42879             },
 42880             soundTransform: {
 42881               get: function soundTransform() {
 42882                 somewhatImplemented('SoundMixer.soundTransform');
 42883                 return isNullOrUndefined(this._soundTransform) ? new flash.media.SoundTransform() : new flash.media.SoundTransform(this._soundTransform._volume, this._soundTransform.pan);
 42884               },
 42885               set: function soundTransform(soundTransform) {
 42886                 somewhatImplemented('SoundMixer.soundTransform');
 42887                 this._soundTransform = isNullOrUndefined(soundTransform) ? new flash.media.SoundTransform() : soundTransform;
 42888                 registeredChannels.forEach(function (channel) {
 42889                   channel._applySoundTransform();
 42890                 });
 42892             },
 42893             audioPlaybackMode: {
 42894               get: function audioPlaybackMode() {
 42895                 notImplemented('SoundMixer.audioPlaybackMode');
 42896               },
 42897               set: function audioPlaybackMode(pA) {
 42898                 notImplemented('SoundMixer.audioPlaybackMode');
 42900             },
 42901             useSpeakerphoneForVoice: {
 42902               get: function useSpeakerphoneForVoice() {
 42903                 notImplemented('SoundMixer.useSpeakerphoneForVoice');
 42904               },
 42905               set: function useSpeakerphoneForVoice(pA) {
 42906                 notImplemented('SoundMixer.useSpeakerphoneForVoice');
 42909           },
 42910           instance: {}
 42913     };
 42914   }.call(this);
 42915 var SoundTransformDefinition = function () {
 42916     return {
 42917       __class__: 'flash.media.SoundTransform',
 42918       initialize: function () {
 42919       },
 42920       _updateTransform: function () {
 42921         somewhatImplemented('SoundTransform._updateTransform');
 42922       },
 42923       __glue__: {
 42924         native: {
 42925           static: {},
 42926           instance: {
 42927             volume: {
 42928               get: function volume() {
 42929                 return this._volume;
 42930               },
 42931               set: function volume(volume) {
 42932                 this._volume = volume;
 42933                 this._updateTransform();
 42935             },
 42936             leftToLeft: {
 42937               get: function leftToLeft() {
 42938                 return this._leftToLeft;
 42939               },
 42940               set: function leftToLeft(leftToLeft) {
 42941                 this._leftToLeft = leftToLeft;
 42942                 this._updateTransform();
 42944             },
 42945             leftToRight: {
 42946               get: function leftToRight() {
 42947                 return this._leftToRight;
 42948               },
 42949               set: function leftToRight(leftToRight) {
 42950                 this._leftToRight = leftToRight;
 42951                 this._updateTransform();
 42953             },
 42954             rightToRight: {
 42955               get: function rightToRight() {
 42956                 return this._rightToRight;
 42957               },
 42958               set: function rightToRight(rightToRight) {
 42959                 this._rightToRight = rightToRight;
 42960                 this._updateTransform();
 42962             },
 42963             rightToLeft: {
 42964               get: function rightToLeft() {
 42965                 return this._rightToLeft;
 42966               },
 42967               set: function rightToLeft(rightToLeft) {
 42968                 this._rightToLeft = rightToLeft;
 42969                 this._updateTransform();
 42973         },
 42974         script: {
 42975           instance: {
 42976             pan: 'public pan'
 42980     };
 42981   }.call(this);
 42982 var StageVideoDefinition = function () {
 42983     return {
 42984       __class__: 'flash.media.StageVideo',
 42985       initialize: function () {
 42986       },
 42987       __glue__: {
 42988         native: {
 42989           static: {},
 42990           instance: {
 42991             attachNetStream: function attachNetStream(netStream) {
 42992               notImplemented('StageVideo.attachNetStream');
 42993             },
 42994             attachCamera: function attachCamera(theCamera) {
 42995               notImplemented('StageVideo.attachCamera');
 42996             },
 42997             viewPort: {
 42998               get: function viewPort() {
 42999                 notImplemented('StageVideo.viewPort');
 43000                 return this._viewPort;
 43001               },
 43002               set: function viewPort(rect) {
 43003                 notImplemented('StageVideo.viewPort');
 43004                 this._viewPort = rect;
 43006             },
 43007             pan: {
 43008               set: function pan(point) {
 43009                 notImplemented('StageVideo.pan');
 43010                 this._pan = point;
 43011               },
 43012               get: function pan() {
 43013                 notImplemented('StageVideo.pan');
 43014                 return this._pan;
 43016             },
 43017             zoom: {
 43018               set: function zoom(point) {
 43019                 notImplemented('StageVideo.zoom');
 43020                 this._zoom = point;
 43021               },
 43022               get: function zoom() {
 43023                 notImplemented('StageVideo.zoom');
 43024                 return this._zoom;
 43026             },
 43027             depth: {
 43028               set: function depth(depth) {
 43029                 notImplemented('StageVideo.depth');
 43030                 this._depth = depth;
 43031               },
 43032               get: function depth() {
 43033                 notImplemented('StageVideo.depth');
 43034                 return this._depth;
 43036             },
 43037             videoWidth: {
 43038               get: function videoWidth() {
 43039                 notImplemented('StageVideo.videoWidth');
 43040                 return this._videoWidth;
 43042             },
 43043             videoHeight: {
 43044               get: function videoHeight() {
 43045                 notImplemented('StageVideo.videoHeight');
 43046                 return this._videoHeight;
 43048             },
 43049             colorSpaces: {
 43050               get: function colorSpaces() {
 43051                 notImplemented('StageVideo.colorSpaces');
 43052                 return this._colorSpaces;
 43058     };
 43059   }.call(this);
 43060 var VideoDefinition = function () {
 43061     function burnHole(ctx, x, y, width, height) {
 43062       ctx.save();
 43063       ctx.beginPath();
 43064       ctx.rect(0, 0, width, height);
 43065       ctx.clip();
 43066       ctx.clearRect(0, 0, width, height);
 43067       ctx.restore();
 43069     var def = {
 43070         initialize: function initialize() {
 43071           TelemetryService.reportTelemetry({
 43072             topic: 'feature',
 43073             feature: VIDEO_FEATURE
 43074           });
 43075         },
 43076         attachNetStream: function (netStream) {
 43077           if (this._netStream === netStream) {
 43078             return;
 43080           if (this._netStream) {
 43081             this._netStream._videoReady.then(function (element) {
 43082               this._element = null;
 43083               if (this._added) {
 43084                 element.remove();
 43085                 this._added = false;
 43087             }.bind(this));
 43089           this._netStream = netStream;
 43090           if (!netStream) {
 43091             return;
 43093           netStream._videoReady.then(function (element) {
 43094             this._element = element;
 43095             netStream._videoMetadataReady.then(function (url) {
 43096               this._element.width = this._videoWidth = this._element.videoWidth;
 43097               this._element.height = this._videoHeight = this._element.videoHeight;
 43098               if (this.stage) {
 43099                 this.stage._invalid = true;
 43101             }.bind(this));
 43102           }.bind(this));
 43103         },
 43104         ctor: function (width, height) {
 43105           if (!width || width < 0)
 43106             width = 320;
 43107           if (!height || height < 0)
 43108             height = 240;
 43109           this._bbox = {
 43110             xMin: 0,
 43111             yMin: 0,
 43112             xMax: width * 20,
 43113             yMax: height * 20
 43114           };
 43115           this._initialWidth = this._videoWidth = width;
 43116           this._initialHeight = this._videoHeight = height;
 43117           this._netStream = null;
 43118           this._element = null;
 43119           this._added = false;
 43120         },
 43121         draw: function (ctx, ratio, ct, parentCtxs) {
 43122           if (!this._element) {
 43123             return;
 43125           if (!this._added && this._stage) {
 43126             this._stage._domContainer.appendChild(this._element);
 43127             this._added = true;
 43129           var width = this._initialWidth;
 43130           var height = this._initialHeight;
 43131           var matrix = this._getConcatenatedTransform(null, true);
 43132           var scaleFactor = this.stage && this.stage._contentsScaleFactor || 1;
 43133           var a = matrix.a / scaleFactor;
 43134           var b = matrix.b / scaleFactor;
 43135           var c = matrix.c / scaleFactor;
 43136           var d = matrix.d / scaleFactor;
 43137           var e = matrix.tx / 20 / scaleFactor;
 43138           var f = matrix.ty / 20 / scaleFactor;
 43139           if (width > 0 && height > 0) {
 43140             burnHole(ctx, 0, 0, width, height);
 43141             parentCtxs.forEach(function (ctx) {
 43142               ctx.save();
 43143               ctx.setTransform(a, b, c, d, e, f);
 43144               burnHole(ctx, 0, 0, width, height);
 43145               ctx.restore();
 43146             });
 43148           var sx = width / this._videoWidth;
 43149           var sy = height / this._videoHeight;
 43150           var cssTransform = 'transform: matrix(' + sx * a + ',' + sx * b + ',' + sy * c + ',' + sy * d + ',' + e + ',' + f + ');';
 43151           if (this._currentCssTransform !== cssTransform) {
 43152             this._currentCssTransform = cssTransform;
 43153             this._element.setAttribute('style', 'position: absolute; top:0; left:0; z-index: -100;transform-origin: 0px 0px 0;' + cssTransform + '-webkit-transform-origin: 0px 0px 0; -webkit-' + cssTransform);
 43156       };
 43157     def.__glue__ = {
 43158       native: {
 43159         instance: {
 43160           attachNetStream: def.attachNetStream,
 43161           ctor: def.ctor,
 43162           smoothing: {
 43163             get: function smoothing() {
 43164               return this._smoothing;
 43165             },
 43166             set: function smoothing(value) {
 43167               somewhatImplemented('Video.smoothing');
 43168               this._smoothing = value;
 43170           },
 43171           videoHeight: {
 43172             get: function videoHeight() {
 43173               return this._videoHeight;
 43175           },
 43176           videoWidth: {
 43177             get: function videoWidth() {
 43178               return this._videoWidth;
 43183     };
 43184     return def;
 43185   }.call(this);
 43187   var FileFilterDefinition = function () {
 43188       return {
 43189         __class__: 'flash.net.FileFilter',
 43190         initialize: function () {
 43191           this._description = null;
 43192           this._extension = null;
 43193           this._macType = null;
 43194         },
 43195         __glue__: {
 43196           native: {
 43197             static: {},
 43198             instance: {
 43199               description: {
 43200                 get: function description() {
 43201                   return this._description;
 43202                 },
 43203                 set: function description(value) {
 43204                   this._description = value;
 43206               },
 43207               extension: {
 43208                 get: function extension() {
 43209                   return this._extension;
 43210                 },
 43211                 set: function extension(value) {
 43212                   this._extension = value;
 43214               },
 43215               macType: {
 43216                 get: function macType() {
 43217                   return this._macType;
 43218                 },
 43219                 set: function macType(value) {
 43220                   this._macType = value;
 43226       };
 43227     }.call(this);
 43229 var LocalConnectionDefinition = function () {
 43230     return {
 43231       __class__: 'flash.net.LocalConnection',
 43232       initialize: function () {
 43233       },
 43234       __glue__: {
 43235         native: {
 43236           static: {},
 43237           instance: {
 43238             close: function close() {
 43239               notImplemented('LocalConnection.close');
 43240             },
 43241             connect: function connect(connectionName) {
 43242               notImplemented('LocalConnection.connect');
 43243             },
 43244             send: function send(connectionName, methodName) {
 43245               notImplemented('LocalConnection.send');
 43246             },
 43247             allowDomain: function allowDomain() {
 43248               notImplemented('LocalConnection.allowDomain');
 43249             },
 43250             allowInsecureDomain: function allowInsecureDomain() {
 43251               notImplemented('LocalConnection.allowInsecureDomain');
 43252             },
 43253             domain: {
 43254               get: function domain() {
 43255                 somewhatImplemented('LocalConnection.domain');
 43256                 var url = FileLoadingService.resolveUrl('/');
 43257                 var m = /:\/\/(.+?)[:?#\/]/.exec(url);
 43258                 return m && m[1];
 43260             },
 43261             client: {
 43262               get: function client() {
 43263                 notImplemented('LocalConnection.client');
 43264                 return this._client;
 43265               },
 43266               set: function client(client) {
 43267                 notImplemented('LocalConnection.client');
 43268                 this._client = client;
 43270             },
 43271             isPerUser: {
 43272               get: function isPerUser() {
 43273                 notImplemented('LocalConnection.isPerUser');
 43274                 return this._isPerUser;
 43275               },
 43276               set: function isPerUser(newValue) {
 43277                 notImplemented('LocalConnection.isPerUser');
 43278                 this._isPerUser = newValue;
 43284     };
 43285   }.call(this);
 43286 var NetConnectionDefinition = function () {
 43287     var defaultObjectEncoding = 3;
 43288     return {
 43289       __class__: 'flash.net.NetConnection',
 43290       initialize: function () {
 43291         TelemetryService.reportTelemetry({
 43292           topic: 'feature',
 43293           feature: NETCONNECTION_FEATURE
 43294         });
 43295       },
 43296       _invoke: function (index, args) {
 43297         var simulated = false, result;
 43298         switch (index) {
 43299         case 2:
 43300           simulated = true;
 43301           break;
 43303         (simulated ? somewhatImplemented : notImplemented)('NetConnection._invoke (' + index + ')');
 43304         return result;
 43305       },
 43306       __glue__: {
 43307         native: {
 43308           static: {
 43309             defaultObjectEncoding: {
 43310               get: function defaultObjectEncoding() {
 43311                 return defaultObjectEncoding;
 43312               },
 43313               set: function defaultObjectEncoding(version) {
 43314                 somewhatImplemented('NetConnection.defaultObjectEncoding');
 43315                 return defaultObjectEncoding;
 43318           },
 43319           instance: {
 43320             ctor: function ctor() {
 43321               this._uri = null;
 43322               this._connected = false;
 43323               this._client = null;
 43324               this._proxyType = 'none';
 43325               this._objectEncoding = defaultObjectEncoding;
 43326             },
 43327             connect: function connect(command) {
 43328               var NetStatusEvent = flash.events.NetStatusEvent;
 43329               somewhatImplemented('NetConnection.connect');
 43330               this._uri = command;
 43331               if (!command) {
 43332                 this._connected = true;
 43333                 this._dispatchEvent(new NetStatusEvent(NetStatusEvent.class.NET_STATUS, false, false, wrapJSObject({
 43334                   level: 'status',
 43335                   code: 'NetConnection.Connect.Success'
 43336                 })));
 43337               } else {
 43338                 this._dispatchEvent(new NetStatusEvent(NetStatusEvent.class.NET_STATUS, false, false, wrapJSObject({
 43339                   level: 'status',
 43340                   code: 'NetConnection.Connect.Failed'
 43341                 })));
 43343             },
 43344             call: function call(command, responder) {
 43345               notImplemented('NetConnection.call');
 43346             },
 43347             connected: {
 43348               get: function connected() {
 43349                 return this._connected;
 43351             },
 43352             uri: {
 43353               get: function uri() {
 43354                 return this._uri;
 43356             },
 43357             client: {
 43358               get: function client() {
 43359                 return this._client;
 43360               },
 43361               set: function client(object) {
 43362                 this._client = object;
 43364             },
 43365             objectEncoding: {
 43366               get: function objectEncoding() {
 43367                 return this._objectEncoding;
 43368               },
 43369               set: function objectEncoding(version) {
 43370                 somewhatImplemented('NetConnection.objectEncoding');
 43371                 this._objectEncoding = version;
 43373             },
 43374             proxyType: {
 43375               get: function proxyType() {
 43376                 return this._proxyType;
 43377               },
 43378               set: function proxyType(ptype) {
 43379                 notImplemented('NetConnection.proxyType');
 43380                 this._proxyType = ptype;
 43382             },
 43383             connectedProxyType: {
 43384               get: function connectedProxyType() {
 43385                 notImplemented('NetConnection.connectedProxyType');
 43386                 return this._connectedProxyType;
 43388             },
 43389             usingTLS: {
 43390               get: function usingTLS() {
 43391                 somewhatImplemented('NetConnection.usingTLS');
 43392                 return false;
 43394             },
 43395             protocol: {
 43396               get: function protocol() {
 43397                 notImplemented('NetConnection.protocol');
 43398                 return this._protocol;
 43400             },
 43401             maxPeerConnections: {
 43402               get: function maxPeerConnections() {
 43403                 notImplemented('NetConnection.maxPeerConnections');
 43404                 return this._maxPeerConnections;
 43405               },
 43406               set: function maxPeerConnections(maxPeers) {
 43407                 notImplemented('NetConnection.maxPeerConnections');
 43408                 this._maxPeerConnections = maxPeers;
 43410             },
 43411             nearID: {
 43412               get: function nearID() {
 43413                 notImplemented('NetConnection.nearID');
 43414                 return this._nearID;
 43416             },
 43417             farID: {
 43418               get: function farID() {
 43419                 notImplemented('NetConnection.farID');
 43420                 return this._farID;
 43422             },
 43423             nearNonce: {
 43424               get: function nearNonce() {
 43425                 notImplemented('NetConnection.nearNonce');
 43426                 return this._nearNonce;
 43428             },
 43429             farNonce: {
 43430               get: function farNonce() {
 43431                 notImplemented('NetConnection.farNonce');
 43432                 return this._farNonce;
 43434             },
 43435             unconnectedPeerStreams: {
 43436               get: function unconnectedPeerStreams() {
 43437                 notImplemented('NetConnection.unconnectedPeerStreams');
 43438                 return this._unconnectedPeerStreams;
 43440             },
 43441             invoke: function invokeWithArgsArray(index) {
 43442               return this._invoke(index, Array.prototype.slice.call(arguments, 1));
 43443             },
 43444             invokeWithArgsArray: function invokeWithArgsArray(index, p_arguments) {
 43445               return this._invoke.call(this, index, p_arguments);
 43450     };
 43451   }.call(this);
 43452 var USE_MEDIASOURCE_API = false;
 43453 var NetStreamDefinition = function () {
 43454     return {
 43455       __class__: 'flash.net.NetStream',
 43456       initialize: function () {
 43457       },
 43458       _invoke: function (index, args) {
 43459         var simulated = false, result;
 43460         var videoElement = this._videoElement;
 43461         switch (index) {
 43462         case 4:
 43463           this._videoState.bufferTime = args[0];
 43464           simulated = true;
 43465           break;
 43466         case 202:
 43467           switch (args[1]) {
 43468           case 'pause':
 43469             simulated = true;
 43470             if (videoElement) {
 43471               if (args[3] !== false && !videoElement.paused) {
 43472                 videoElement.pause();
 43473               } else if (args[3] !== true && videoElement.paused) {
 43474                 videoElement.play();
 43476               videoElement.currentTime = args[4] / 1000;
 43478             break;
 43479           case 'seek':
 43480             simulated = true;
 43481             if (videoElement && !videoElement.paused) {
 43482               videoElement.currentTime = args[3] / 1000;
 43484             break;
 43486           break;
 43487         case 300:
 43488           result = videoElement ? videoElement.currentTime : 0;
 43489           simulated = true;
 43490           break;
 43491         case 302:
 43492           result = this._videoState.bufferTime;
 43493           simulated = true;
 43494           break;
 43495         case 303:
 43496           result = videoElement ? videoElement.duration : 0;
 43497           simulated = true;
 43498           break;
 43499         case 305:
 43500           result = this._videoState.buffer === 'full' ? 100 : this._videoState.buffer === 'progress' ? 50 : 0;
 43501           simulated = true;
 43502           break;
 43503         case 306:
 43504           result = 100;
 43505           simulated = true;
 43506           break;
 43508         (simulated ? somewhatImplemented : notImplemented)('NetStream._invoke (' + index + ')');
 43509         return result;
 43510       },
 43511       _createVideoElement: function (url) {
 43512         function notifyPlayStart(e) {
 43513           if (netStream._videoState.started) {
 43514             return;
 43516           netStream._videoState.started = true;
 43517           netStream._dispatchEvent(new NetStatusEvent(NetStatusEvent.class.NET_STATUS, false, false, wrapJSObject({
 43518             code: 'NetStream.Play.Start',
 43519             level: 'status'
 43520           })));
 43522         function notifyPlayStop(e) {
 43523           netStream._videoState.started = false;
 43524           netStream._dispatchEvent(new NetStatusEvent(NetStatusEvent.class.NET_STATUS, false, false, wrapJSObject({
 43525             code: 'NetStream.Play.Stop',
 43526             level: 'status'
 43527           })));
 43529         function notifyBufferFull(e) {
 43530           netStream._videoState.buffer = 'full';
 43531           netStream._dispatchEvent(new NetStatusEvent(NetStatusEvent.class.NET_STATUS, false, false, wrapJSObject({
 43532             code: 'NetStream.Buffer.Full',
 43533             level: 'status'
 43534           })));
 43536         function notifyProgress(e) {
 43537           netStream._videoState.buffer = 'progress';
 43539         function notifyBufferEmpty(e) {
 43540           netStream._videoState.buffer = 'empty';
 43541           netStream._dispatchEvent(new NetStatusEvent(NetStatusEvent.class.NET_STATUS, false, false, wrapJSObject({
 43542             code: 'NetStream.Buffer.Empty',
 43543             level: 'status'
 43544           })));
 43546         function notifyError(e) {
 43547           var code = e.target.error.code === 4 ? 'NetStream.Play.NoSupportedTrackFound' : e.target.error.code === 3 ? 'NetStream.Play.FileStructureInvalid' : 'NetStream.Play.StreamNotFound';
 43548           netStream._dispatchEvent(new NetStatusEvent(NetStatusEvent.class.NET_STATUS, false, false, wrapJSObject({
 43549             code: code,
 43550             level: 'error'
 43551           })));
 43553         function notifyMetadata(e) {
 43554           netStream._videoMetadataReady.resolve({
 43555             videoWidth: element.videoWidth,
 43556             videoHeight: element.videoHeight
 43557           });
 43558           if (netStream._client) {
 43559             var data = {};
 43560             data.asSetPublicProperty('width', element.videoWidth);
 43561             data.asSetPublicProperty('height', element.videoHeight);
 43562             data.asSetPublicProperty('duration', element.duration);
 43563             netStream._client.asCallPublicProperty('onMetaData', [
 43564               data
 43565             ]);
 43568         var NetStatusEvent = flash.events.NetStatusEvent;
 43569         var netStream = this;
 43570         if (/\.mp4$/i.test(url) && /Intel Mac OS X.*?Firefox\/\d+/.test(window.navigator.userAgent)) {
 43571           url = 'http://videos-cdn.mozilla.net/brand/Mozilla_2011_Story.webm';
 43573         var element = document.createElement('video');
 43574         element.preload = 'metadata';
 43575         element.src = url;
 43576         element.addEventListener('play', notifyPlayStart);
 43577         element.addEventListener('ended', notifyPlayStop);
 43578         element.addEventListener('loadeddata', notifyBufferFull);
 43579         element.addEventListener('progress', notifyProgress);
 43580         element.addEventListener('waiting', notifyBufferEmpty);
 43581         element.addEventListener('loadedmetadata', notifyMetadata);
 43582         element.addEventListener('error', notifyError);
 43583         element.play();
 43584         this._videoElement = element;
 43585         this._videoReady.resolve(element);
 43586       },
 43587       __glue__: {
 43588         script: {
 43589           instance: scriptProperties('public', [
 43590             'appendBytes',
 43591             'appendBytesAction'
 43592           ])
 43593         },
 43594         native: {
 43595           static: {},
 43596           instance: {
 43597             ctor: function ctor(connection, peerID) {
 43598               somewhatImplemented('NetStream.ctor');
 43599               this._contentTypeHint = null;
 43600               this._mediaSource = null;
 43601               this._checkPolicyFile = true;
 43602               this._videoElement = null;
 43603               var videoReadyResolve, videoReadyReject;
 43604               this._videoReady = new Promise(function (resolve, reject) {
 43605                 videoReadyResolve = resolve;
 43606                 videoReadyReject = reject;
 43607               });
 43608               this._videoReady.resolve = videoReadyResolve;
 43609               this._videoReady.reject = videoReadyReject;
 43610               var videoMetadataReadyResolve, videoMetadataReadyReject;
 43611               this._videoMetadataReady = new Promise(function (resolve, reject) {
 43612                 videoMetadataReadyResolve = resolve;
 43613                 videoMetadataReadyReject = reject;
 43614               });
 43615               this._videoMetadataReady.resolve = videoMetadataReadyResolve;
 43616               this._videoMetadataReady.reject = videoMetadataReadyReject;
 43617               this._videoState = {
 43618                 started: false,
 43619                 buffer: 'empty',
 43620                 bufferTime: 0.1
 43621               };
 43622             },
 43623             onResult: function onResult(streamId) {
 43624               notImplemented('NetStream.onResult');
 43625             },
 43626             dispose: function dispose() {
 43627               notImplemented('NetStream.dispose');
 43628             },
 43629             play: function play(url) {
 43630               var isMediaSourceEnabled = USE_MEDIASOURCE_API;
 43631               if (isMediaSourceEnabled && typeof MediaSource === 'undefined') {
 43632                 console.warn('MediaSource API is not enabled, falling back to regular playback');
 43633                 isMediaSourceEnabled = false;
 43635               if (!isMediaSourceEnabled) {
 43636                 somewhatImplemented('NetStream.play');
 43637                 this._createVideoElement(FileLoadingService.resolveUrl(url));
 43638                 return;
 43640               var mediaSource = new MediaSource();
 43641               mediaSource.addEventListener('sourceopen', function (e) {
 43642                 this._mediaSource = mediaSource;
 43643               }.bind(this));
 43644               mediaSource.addEventListener('sourceend', function (e) {
 43645                 this._mediaSource = null;
 43646               }.bind(this));
 43647               this._createVideoElement(window.URL.createObjectURL(mediaSource));
 43648               if (!url) {
 43649                 return;
 43651               var request = new flash.net.URLRequest(url);
 43652               request._checkPolicyFile = this._checkPolicyFile;
 43653               var stream = new flash.net.URLStream();
 43654               stream._addEventListener('httpStatus', function (e) {
 43655                 var responseHeaders = e.asGetPublicProperty('responseHeaders');
 43656                 var contentTypeHeader = responseHeaders.filter(function (h) {
 43657                     return h.asGetPublicProperty('name') === 'Content-Type';
 43658                   })[0];
 43659                 if (contentTypeHeader && contentTypeHeader.asGetPublicProperty('value') !== 'application/octet-stream') {
 43660                   this._contentTypeHint = contentTypeHeader.asGetPublicProperty('value');
 43662               }.bind(this));
 43663               stream._addEventListener('progress', function (e) {
 43664                 var available = stream.bytesAvailable;
 43665                 var ByteArrayClass = avm2.systemDomain.getClass('flash.utils.ByteArray');
 43666                 var data = ByteArrayClass.createInstance();
 43667                 stream.readBytes(data, 0, available);
 43668                 this.appendBytes(data);
 43669               }.bind(this));
 43670               stream._addEventListener('complete', function (e) {
 43671                 this.appendBytesAction('endSequence');
 43672               }.bind(this));
 43673               stream.load(request);
 43674             },
 43675             play2: function play2(param) {
 43676               notImplemented('NetStream.play2');
 43677             },
 43678             invoke: function invoke(index) {
 43679               return this._invoke(index, Array.prototype.slice.call(arguments, 1));
 43680             },
 43681             invokeWithArgsArray: function invokeWithArgsArray(index, p_arguments) {
 43682               return this._invoke.call(this, index, p_arguments);
 43683             },
 43684             appendBytes: function appendBytes(bytes) {
 43685               if (this._mediaSource) {
 43686                 if (!this._mediaSourceBuffer) {
 43687                   this._mediaSourceBuffer = this._mediaSource.addSourceBuffer(this._contentTypeHint);
 43689                 this._mediaSourceBuffer.appendBuffer(new Uint8Array(bytes.a, 0, bytes.length));
 43691               somewhatImplemented('NetStream.appendBytes');
 43692             },
 43693             appendBytesAction: function appendBytesAction(netStreamAppendBytesAction) {
 43694               if (netStreamAppendBytesAction === 'endSequence' && this._mediaSource) {
 43695                 this._mediaSource.endOfStream();
 43697               somewhatImplemented('NetStream.appendBytesAction');
 43698             },
 43699             info: {
 43700               get: function info() {
 43701                 notImplemented('NetStream.info');
 43702                 return this._info;
 43704             },
 43705             multicastInfo: {
 43706               get: function multicastInfo() {
 43707                 notImplemented('NetStream.multicastInfo');
 43708                 return this._multicastInfo;
 43710             },
 43711             soundTransform: {
 43712               get: function soundTransform() {
 43713                 return this._soundTransform;
 43714               },
 43715               set: function soundTransform(sndTransform) {
 43716                 somewhatImplemented('NetStream.soundTransform');
 43717                 this._soundTransform = sndTransform;
 43719             },
 43720             checkPolicyFile: {
 43721               get: function checkPolicyFile() {
 43722                 return this._checkPolicyFile;
 43723               },
 43724               set: function checkPolicyFile(state) {
 43725                 this._checkPolicyFile = state;
 43727             },
 43728             client: {
 43729               get: function client() {
 43730                 somewhatImplemented('NetStream.client');
 43731                 return this._client;
 43732               },
 43733               set: function client(object) {
 43734                 somewhatImplemented('NetStream.client');
 43735                 this._client = object;
 43737             },
 43738             objectEncoding: {
 43739               get: function objectEncoding() {
 43740                 notImplemented('NetStream.objectEncoding');
 43741                 return this._objectEncoding;
 43743             },
 43744             multicastPushNeighborLimit: {
 43745               get: function multicastPushNeighborLimit() {
 43746                 notImplemented('NetStream.multicastPushNeighborLimit');
 43747                 return this._multicastPushNeighborLimit;
 43748               },
 43749               set: function multicastPushNeighborLimit(neighbors) {
 43750                 notImplemented('NetStream.multicastPushNeighborLimit');
 43751                 this._multicastPushNeighborLimit = neighbors;
 43753             },
 43754             multicastWindowDuration: {
 43755               get: function multicastWindowDuration() {
 43756                 notImplemented('NetStream.multicastWindowDuration');
 43757                 return this._multicastWindowDuration;
 43758               },
 43759               set: function multicastWindowDuration(seconds) {
 43760                 notImplemented('NetStream.multicastWindowDuration');
 43761                 this._multicastWindowDuration = seconds;
 43763             },
 43764             multicastRelayMarginDuration: {
 43765               get: function multicastRelayMarginDuration() {
 43766                 notImplemented('NetStream.multicastRelayMarginDuration');
 43767                 return this._multicastRelayMarginDuration;
 43768               },
 43769               set: function multicastRelayMarginDuration(seconds) {
 43770                 notImplemented('NetStream.multicastRelayMarginDuration');
 43771                 this._multicastRelayMarginDuration = seconds;
 43773             },
 43774             multicastAvailabilityUpdatePeriod: {
 43775               get: function multicastAvailabilityUpdatePeriod() {
 43776                 notImplemented('NetStream.multicastAvailabilityUpdatePeriod');
 43777                 return this._multicastAvailabilityUpdatePeriod;
 43778               },
 43779               set: function multicastAvailabilityUpdatePeriod(seconds) {
 43780                 notImplemented('NetStream.multicastAvailabilityUpdatePeriod');
 43781                 this._multicastAvailabilityUpdatePeriod = seconds;
 43783             },
 43784             multicastFetchPeriod: {
 43785               get: function multicastFetchPeriod() {
 43786                 notImplemented('NetStream.multicastFetchPeriod');
 43787                 return this._multicastFetchPeriod;
 43788               },
 43789               set: function multicastFetchPeriod(seconds) {
 43790                 notImplemented('NetStream.multicastFetchPeriod');
 43791                 this._multicastFetchPeriod = seconds;
 43793             },
 43794             multicastAvailabilitySendToAll: {
 43795               get: function multicastAvailabilitySendToAll() {
 43796                 notImplemented('NetStream.multicastAvailabilitySendToAll');
 43797                 return this._multicastAvailabilitySendToAll;
 43798               },
 43799               set: function multicastAvailabilitySendToAll(value) {
 43800                 notImplemented('NetStream.multicastAvailabilitySendToAll');
 43801                 this._multicastAvailabilitySendToAll = value;
 43803             },
 43804             farID: {
 43805               get: function farID() {
 43806                 notImplemented('NetStream.farID');
 43807                 return this._farID;
 43809             },
 43810             nearNonce: {
 43811               get: function nearNonce() {
 43812                 notImplemented('NetStream.nearNonce');
 43813                 return this._nearNonce;
 43815             },
 43816             farNonce: {
 43817               get: function farNonce() {
 43818                 notImplemented('NetStream.farNonce');
 43819                 return this._farNonce;
 43821             },
 43822             peerStreams: {
 43823               get: function peerStreams() {
 43824                 notImplemented('NetStream.peerStreams');
 43825                 return this._peerStreams;
 43827             },
 43828             audioReliable: {
 43829               get: function audioReliable() {
 43830                 notImplemented('NetStream.audioReliable');
 43831                 return this._audioReliable;
 43832               },
 43833               set: function audioReliable(reliable) {
 43834                 notImplemented('NetStream.audioReliable');
 43835                 this._audioReliable = reliable;
 43837             },
 43838             videoReliable: {
 43839               get: function videoReliable() {
 43840                 notImplemented('NetStream.videoReliable');
 43841                 return this._videoReliable;
 43842               },
 43843               set: function videoReliable(reliable) {
 43844                 notImplemented('NetStream.videoReliable');
 43845                 this._videoReliable = reliable;
 43847             },
 43848             dataReliable: {
 43849               get: function dataReliable() {
 43850                 notImplemented('NetStream.dataReliable');
 43851                 return this._dataReliable;
 43852               },
 43853               set: function dataReliable(reliable) {
 43854                 notImplemented('NetStream.dataReliable');
 43855                 this._dataReliable = reliable;
 43857             },
 43858             audioSampleAccess: {
 43859               get: function audioSampleAccess() {
 43860                 notImplemented('NetStream.audioSampleAccess');
 43861                 return this._audioSampleAccess;
 43862               },
 43863               set: function audioSampleAccess(reliable) {
 43864                 notImplemented('NetStream.audioSampleAccess');
 43865                 this._audioSampleAccess = reliable;
 43867             },
 43868             videoSampleAccess: {
 43869               get: function videoSampleAccess() {
 43870                 notImplemented('NetStream.videoSampleAccess');
 43871                 return this._videoSampleAccess;
 43872               },
 43873               set: function videoSampleAccess(reliable) {
 43874                 notImplemented('NetStream.videoSampleAccess');
 43875                 this._videoSampleAccess = reliable;
 43877             },
 43878             useHardwareDecoder: {
 43879               get: function useHardwareDecoder() {
 43880                 notImplemented('NetStream.useHardwareDecoder');
 43881                 return this._useHardwareDecoder;
 43882               },
 43883               set: function useHardwareDecoder(v) {
 43884                 notImplemented('NetStream.useHardwareDecoder');
 43885                 this._useHardwareDecoder = v;
 43887             },
 43888             useJitterBuffer: {
 43889               get: function useJitterBuffer() {
 43890                 notImplemented('NetStream.useJitterBuffer');
 43891                 return this._useJitterBuffer;
 43892               },
 43893               set: function useJitterBuffer(value) {
 43894                 notImplemented('NetStream.useJitterBuffer');
 43895                 this._useJitterBuffer = value;
 43897             },
 43898             videoStreamSettings: {
 43899               get: function videoStreamSettings() {
 43900                 notImplemented('NetStream.videoStreamSettings');
 43901                 return this._videoStreamSettings;
 43902               },
 43903               set: function videoStreamSettings(settings) {
 43904                 notImplemented('NetStream.videoStreamSettings');
 43905                 this._videoStreamSettings = settings;
 43911     };
 43912   }.call(this);
 43913 var ObjectEncodingDefinition = function () {
 43914     return {
 43915       __class__: 'flash.net.ObjectEncoding',
 43916       initialize: function () {
 43917       },
 43918       __glue__: {
 43919         native: {
 43920           static: {
 43921             dynamicPropertyWriter: {
 43922               get: function dynamicPropertyWriter() {
 43923                 notImplemented('ObjectEncoding.dynamicPropertyWriter');
 43924               },
 43925               set: function dynamicPropertyWriter(object) {
 43926                 notImplemented('ObjectEncoding.dynamicPropertyWriter');
 43929           },
 43930           instance: {}
 43933     };
 43934   }.call(this);
 43935 var ResponderDefinition = function () {
 43936     var def = {
 43937         ctor: function (result, status) {
 43939       };
 43940     def.__glue__ = {
 43941       native: {
 43942         instance: {
 43943           ctor: def.ctor
 43946     };
 43947     return def;
 43948   }.call(this);
 43949 var SharedObjectDefinition = function () {
 43950     var _defaultObjectEncoding = 3;
 43951     var sharedObjects = createEmptyObject();
 43952     function invokeWithArgsArray(index, args) {
 43953       var simulated = false, result;
 43954       switch (index) {
 43955       case 4:
 43956         result = JSON.stringify(this._data).length - 2;
 43957         simulated = true;
 43958         break;
 43959       case 6:
 43960         this._data = {};
 43961         sessionStorage.removeItem(this._path);
 43962         simulated = true;
 43963         break;
 43964       case 2:
 43965         sessionStorage.setItem(this._path, JSON.stringify(this._data));
 43966         simulated = true;
 43967         result = true;
 43968         break;
 43969       case 3:
 43970         simulated = true;
 43971         break;
 43973       (simulated ? somewhatImplemented : notImplemented)('SharedObject.invoke (' + index + ')');
 43974       return result;
 43976     return {
 43977       __class__: 'flash.net.SharedObject',
 43978       initialize: function () {
 43979         this._path = null;
 43980         this._data = null;
 43981         this._objectEncoding = _defaultObjectEncoding;
 43982         TelemetryService.reportTelemetry({
 43983           topic: 'feature',
 43984           feature: SHAREDOBJECT_FEATURE
 43985         });
 43986       },
 43987       __glue__: {
 43988         native: {
 43989           static: {
 43990             deleteAll: function deleteAll(url) {
 43991               notImplemented('SharedObject.deleteAll');
 43992             },
 43993             getDiskUsage: function getDiskUsage(url) {
 43994               notImplemented('SharedObject.getDiskUsage');
 43995             },
 43996             getLocal: function getLocal(name, localPath, secure) {
 43997               var path = (localPath || '') + '/' + name;
 43998               if (sharedObjects[path]) {
 43999                 return sharedObjects[path];
 44001               var so = new flash.net.SharedObject();
 44002               so._path = path;
 44003               var data = sessionStorage.getItem(path);
 44004               so._data = data ? JSON.parse(data) : {};
 44005               return so;
 44006             },
 44007             getRemote: function getRemote(name, remotePath, persistence, secure) {
 44008               notImplemented('SharedObject.getRemote');
 44009             },
 44010             defaultObjectEncoding: {
 44011               get: function defaultObjectEncoding() {
 44012                 return _defaultObjectEncoding;
 44013               },
 44014               set: function defaultObjectEncoding(version) {
 44015                 _defaultObjectEncoding = version;
 44018           },
 44019           instance: {
 44020             setDirty: function setDirty(propertyName) {
 44021               somewhatImplemented('SharedObject.setDirty');
 44022             },
 44023             invoke: function invoke(index) {
 44024               return invokeWithArgsArray.call(this, index, Array.prototype.slice.call(arguments, 1));
 44025             },
 44026             invokeWithArgsArray: function invokeWithArgsArray(index, args) {
 44027               return invokeWithArgsArray.call(this, index, args);
 44028             },
 44029             data: {
 44030               get: function data() {
 44031                 return this._data;
 44033             },
 44034             objectEncoding: {
 44035               get: function objectEncoding() {
 44036                 return this._objectEncoding;
 44037               },
 44038               set: function objectEncoding(version) {
 44039                 this._objectEncoding = version;
 44041             },
 44042             client: {
 44043               get: function client() {
 44044                 notImplemented('SharedObject.client');
 44045                 return this._client;
 44046               },
 44047               set: function client(object) {
 44048                 notImplemented('SharedObject.client');
 44049                 this._client = object;
 44055     };
 44056   }.call(this);
 44057 var SocketDefinition = function () {
 44058     return {
 44059       __class__: 'flash.net.Socket',
 44060       initialize: function () {
 44061         this._connected = false;
 44062       },
 44063       __glue__: {
 44064         native: {
 44065           static: {},
 44066           instance: {
 44067             internalGetSecurityErrorMessage: function internalGetSecurityErrorMessage(host, port) {
 44068               somewhatImplemented('Socket.internalGetSecurityErrorMessage');
 44069               return 'SecurityErrorEvent';
 44070             },
 44071             internalConnect: function internalConnect(host, port) {
 44072               somewhatImplemented('Socket.internalConnect');
 44073               throwError('SecurityError', Errors.SocketConnectError, host, port);
 44074             },
 44075             didFailureOccur: function didFailureOccur() {
 44076               somewhatImplemented('Socket.didFailureOccur');
 44077               return true;
 44078             },
 44079             readBytes: function readBytes(bytes, offset, length) {
 44080               notImplemented('Socket.readBytes');
 44081             },
 44082             writeBytes: function writeBytes(bytes, offset, length) {
 44083               notImplemented('Socket.writeBytes');
 44084             },
 44085             writeBoolean: function writeBoolean(value) {
 44086               notImplemented('Socket.writeBoolean');
 44087             },
 44088             writeByte: function writeByte(value) {
 44089               notImplemented('Socket.writeByte');
 44090             },
 44091             writeShort: function writeShort(value) {
 44092               notImplemented('Socket.writeShort');
 44093             },
 44094             writeInt: function writeInt(value) {
 44095               notImplemented('Socket.writeInt');
 44096             },
 44097             writeUnsignedInt: function writeUnsignedInt(value) {
 44098               notImplemented('Socket.writeUnsignedInt');
 44099             },
 44100             writeFloat: function writeFloat(value) {
 44101               notImplemented('Socket.writeFloat');
 44102             },
 44103             writeDouble: function writeDouble(value) {
 44104               notImplemented('Socket.writeDouble');
 44105             },
 44106             writeMultiByte: function writeMultiByte(value, charSet) {
 44107               notImplemented('Socket.writeMultiByte');
 44108             },
 44109             writeUTF: function writeUTF(value) {
 44110               notImplemented('Socket.writeUTF');
 44111             },
 44112             writeUTFBytes: function writeUTFBytes(value) {
 44113               notImplemented('Socket.writeUTFBytes');
 44114             },
 44115             readBoolean: function readBoolean() {
 44116               notImplemented('Socket.readBoolean');
 44117             },
 44118             readByte: function readByte() {
 44119               notImplemented('Socket.readByte');
 44120             },
 44121             readUnsignedByte: function readUnsignedByte() {
 44122               notImplemented('Socket.readUnsignedByte');
 44123             },
 44124             readShort: function readShort() {
 44125               notImplemented('Socket.readShort');
 44126             },
 44127             readUnsignedShort: function readUnsignedShort() {
 44128               notImplemented('Socket.readUnsignedShort');
 44129             },
 44130             readInt: function readInt() {
 44131               notImplemented('Socket.readInt');
 44132             },
 44133             readUnsignedInt: function readUnsignedInt() {
 44134               notImplemented('Socket.readUnsignedInt');
 44135             },
 44136             readFloat: function readFloat() {
 44137               notImplemented('Socket.readFloat');
 44138             },
 44139             readDouble: function readDouble() {
 44140               notImplemented('Socket.readDouble');
 44141             },
 44142             readMultiByte: function readMultiByte(length, charSet) {
 44143               notImplemented('Socket.readMultiByte');
 44144             },
 44145             readUTF: function readUTF() {
 44146               notImplemented('Socket.readUTF');
 44147             },
 44148             readUTFBytes: function readUTFBytes(length) {
 44149               notImplemented('Socket.readUTFBytes');
 44150             },
 44151             internalClose: function internalClose() {
 44152               notImplemented('Socket.internalClose');
 44153             },
 44154             flush: function flush() {
 44155               notImplemented('Socket.flush');
 44156             },
 44157             writeObject: function writeObject(object) {
 44158               notImplemented('Socket.writeObject');
 44159             },
 44160             readObject: function readObject() {
 44161               notImplemented('Socket.readObject');
 44162             },
 44163             bytesAvailable: {
 44164               get: function bytesAvailable() {
 44165                 notImplemented('Socket.bytesAvailable');
 44166                 return this._bytesAvailable;
 44168             },
 44169             connected: {
 44170               get: function connected() {
 44171                 somewhatImplemented('Socket.connected');
 44172                 return this._connected;
 44174             },
 44175             objectEncoding: {
 44176               get: function objectEncoding() {
 44177                 notImplemented('Socket.objectEncoding');
 44178                 return this._objectEncoding;
 44179               },
 44180               set: function objectEncoding(version) {
 44181                 notImplemented('Socket.objectEncoding');
 44182                 this._objectEncoding = version;
 44184             },
 44185             endian: {
 44186               get: function endian() {
 44187                 notImplemented('Socket.endian');
 44188                 return this._endian;
 44189               },
 44190               set: function endian(type) {
 44191                 notImplemented('Socket.endian');
 44192                 this._endian = type;
 44194             },
 44195             bytesPending: {
 44196               get: function bytesPending() {
 44197                 notImplemented('Socket.bytesPending');
 44198                 return this._bytesPending;
 44202         },
 44203         script: {
 44204           instance: Glue.ALL
 44207     };
 44208   }.call(this);
 44209 var URLLoaderDefinition = function () {
 44210     return {
 44211       initialize: function () {
 44212       },
 44213       __glue__: {
 44214         native: {
 44215           static: {},
 44216           instance: {}
 44217         },
 44218         script: {
 44219           static: {},
 44220           instance: {
 44221             data: 'public data',
 44222             dataFormat: 'public dataFormat',
 44223             bytesTotal: 'public bytesTotal',
 44224             bytesLoaded: 'public bytesLoaded',
 44225             load: 'public load'
 44229     };
 44230   }.call(this);
 44231 var URLRequestDefinition = function () {
 44232     function toFileLoadingServiceRequest() {
 44233       var obj = {};
 44234       obj.url = this._url;
 44235       obj.method = this._method;
 44236       obj.checkPolicyFile = this._checkPolicyFile;
 44237       if (this._data) {
 44238         obj.mimeType = this._contentType;
 44239         var ByteArrayClass = avm2.systemDomain.getClass('flash.utils.ByteArray');
 44240         if (ByteArrayClass.isInstanceOf(this._data)) {
 44241           obj.data = new Uint8Array(this._data.a, 0, this._data.length);
 44242         } else {
 44243           var data = this._data.asGetPublicProperty('toString').call(this._data);
 44244           if (this._method === 'GET') {
 44245             var i = obj.url.lastIndexOf('?');
 44246             obj.url = (i < 0 ? obj.url : obj.url.substring(0, i)) + '?' + data;
 44247           } else {
 44248             obj.data = data;
 44252       return obj;
 44254     var def = {
 44255         initialize: function () {
 44256           this._url = null;
 44257           this._method = 'GET';
 44258           this._data = null;
 44259           this._digest = null;
 44260           this._contentType = 'application/x-www-form-urlencoded';
 44261           this._requestHeaders = null;
 44262           this._checkPolicyFile = true;
 44263           this._toFileRequest = toFileLoadingServiceRequest;
 44264         },
 44265         setMethod: function (val) {
 44266           this._method = val;
 44267         },
 44268         setRequestHeaders: function (val) {
 44269           this._requestHeaders = val;
 44270         },
 44271         get contentType() {
 44272           return this._contentType;
 44273         },
 44274         set contentType(val) {
 44275           this._contentType = val;
 44276         },
 44277         get data() {
 44278           return this._data;
 44279         },
 44280         set data(val) {
 44281           this._data = val;
 44282         },
 44283         get digest() {
 44284           return this._digest;
 44285         },
 44286         set digest(val) {
 44287           this._digest = val;
 44288         },
 44289         get method() {
 44290           return this._method;
 44291         },
 44292         set method(method) {
 44293           this._method = method;
 44294         },
 44295         get requestHeaders() {
 44296           return this._requestHeaders;
 44297         },
 44298         set requestHeaders(requestHeaders) {
 44299           this._requestHeaders = requestHeaders;
 44300         },
 44301         get url() {
 44302           return this._url;
 44303         },
 44304         set url(val) {
 44305           this._url = val;
 44307       };
 44308     var desc = Object.getOwnPropertyDescriptor;
 44309     def.__glue__ = {
 44310       native: {
 44311         instance: {
 44312           setMethod: def.setMethod,
 44313           setRequestHeaders: def.setRequestHeaders,
 44314           contentType: desc(def, 'contentType'),
 44315           data: desc(def, 'data'),
 44316           digest: desc(def, 'digest'),
 44317           method: desc(def, 'method'),
 44318           requestHeaders: desc(def, 'requestHeaders'),
 44319           url: desc(def, 'url')
 44322     };
 44323     return def;
 44324   }.call(this);
 44325 var URLStreamDefinition = function () {
 44326     var def = {
 44327         initialize: function () {
 44328           this._stream = null;
 44329           this._connected = false;
 44330           this._littleEndian = false;
 44331         },
 44332         close: function close() {
 44333           this._session.close();
 44334         },
 44335         load: function load(request) {
 44336           var session = FileLoadingService.createSession();
 44337           var self = this;
 44338           var initStream = true;
 44339           session.onprogress = function (data, progressState) {
 44340             if (initStream) {
 44341               initStream = false;
 44342               var length = Math.max(progressState.bytesTotal, data.length);
 44343               var buffer = new ArrayBuffer(length);
 44344               self._stream = new Stream(buffer, 0, 0, length);
 44345             } else if (self._stream.end + data.length > self._stream.bytes.length) {
 44346               var length = self._stream.end + data.length;
 44347               var buffer = new ArrayBuffer(length);
 44348               var newStream = new Stream(buffer, 0, 0, length);
 44349               newStream.push(self._stream.bytes.subarray(0, self._stream.end));
 44350               self._stream = newStream;
 44352             self._stream.push(data);
 44353             var ProgressEventClass = avm2.systemDomain.getClass('flash.events.ProgressEvent');
 44354             self._dispatchEvent(ProgressEventClass.createInstance([
 44355               'progress',
 44356               false,
 44357               false,
 44358               progressState.bytesLoaded,
 44359               progressState.bytesTotal
 44360             ]));
 44361           };
 44362           session.onerror = function (error) {
 44363             self._connected = false;
 44364             if (!self._stream) {
 44365               self._stream = new Stream(new ArrayBuffer(0), 0, 0, 0);
 44367             self._dispatchEvent(new flash.events.IOErrorEvent(flash.events.IOErrorEvent.class.IO_ERROR, false, false, error));
 44368           };
 44369           session.onopen = function () {
 44370             self._connected = true;
 44371             self._dispatchEvent(new flash.events.Event('open', false, false));
 44372           };
 44373           session.onhttpstatus = function (location, httpStatus, httpHeaders) {
 44374             var HTTPStatusEventClass = avm2.systemDomain.getClass('flash.events.HTTPStatusEvent');
 44375             var URLRequestHeaderClass = avm2.systemDomain.getClass('flash.net.URLRequestHeader');
 44376             var httpStatusEvent = HTTPStatusEventClass.createInstance([
 44377                 'httpStatus',
 44378                 false,
 44379                 false,
 44380                 httpStatus
 44381               ]);
 44382             var headers = [];
 44383             httpHeaders.split(/(?:\n|\r?\n)/g).forEach(function (h) {
 44384               var m = /^([^:]+): (.*)$/.exec(h);
 44385               if (m) {
 44386                 headers.push(URLRequestHeaderClass.createInstance([
 44387                   m[1],
 44388                   m[2]
 44389                 ]));
 44390                 if (m[1] === 'Location') {
 44391                   location = m[2];
 44394             });
 44395             httpStatusEvent.asSetPublicProperty('responseHeaders', headers);
 44396             httpStatusEvent.asSetPublicProperty('responseURL', location);
 44397             self._dispatchEvent(httpStatusEvent);
 44398           };
 44399           session.onclose = function () {
 44400             self._connected = false;
 44401             if (!self._stream) {
 44402               self._stream = new Stream(new ArrayBuffer(0), 0, 0, 0);
 44404             self._dispatchEvent(new flash.events.Event('complete', false, false));
 44405           };
 44406           session.open(request._toFileRequest());
 44407           this._session = session;
 44408         },
 44409         readBoolean: function readBoolean() {
 44410           notImplemented('URLStream.readBoolean');
 44411         },
 44412         readByte: function readByte() {
 44413           var stream = this._stream;
 44414           stream.ensure(1);
 44415           return stream.bytes[stream.pos++];
 44416         },
 44417         readBytes: function readBytes(bytes, offset, length) {
 44418           if (length < 0)
 44419             throw 'Invalid length argument';
 44420           var stream = this._stream;
 44421           if (!length)
 44422             length = stream.remaining();
 44423           else
 44424             stream.ensure(length);
 44425           bytes.writeRawBytes(stream.bytes.subarray(stream.pos, stream.pos + length), offset, length);
 44426           stream.pos += length;
 44427         },
 44428         readDouble: function readDouble() {
 44429           notImplemented('URLStream.readDouble');
 44430         },
 44431         readFloat: function readFloat() {
 44432           notImplemented('URLStream.readFloat');
 44433         },
 44434         readInt: function readInt() {
 44435           notImplemented('URLStream.readInt');
 44436         },
 44437         readMultiByte: function readMultiByte(length, charSet) {
 44438           notImplemented('URLStream.readMultiByte');
 44439         },
 44440         readObject: function readObject() {
 44441           notImplemented('URLStream.readObject');
 44442         },
 44443         readShort: function readShort() {
 44444           notImplemented('URLStream.readShort');
 44445         },
 44446         readUTF: function readUTF() {
 44447           return this.readUTFBytes(this.readUnsignedShort());
 44448         },
 44449         readUTFBytes: function readUTFBytes(length) {
 44450           if (length < 0)
 44451             throw 'Invalid length argument';
 44452           var stream = this._stream;
 44453           stream.ensure(length);
 44454           var str = utf8encode(stream.bytes.subarray(stream.pos, stream.pos + length));
 44455           stream.pos += length;
 44456           return str;
 44457         },
 44458         readUnsignedByte: function readUnsignedByte() {
 44459           notImplemented('URLStream.readUnsignedByte');
 44460         },
 44461         readUnsignedInt: function readUnsignedInt() {
 44462           notImplemented('URLStream.readUnsignedInt');
 44463         },
 44464         readUnsignedShort: function readUnsignedShort() {
 44465           var stream = this._stream;
 44466           stream.ensure(2);
 44467           var result = stream.getUint16(stream.pos, this._littleEndian);
 44468           stream.pos += 2;
 44469           return result;
 44470         },
 44471         get bytesAvailable() {
 44472           return this._stream.remaining();
 44473         },
 44474         get connected() {
 44475           return this._connected;
 44476         },
 44477         get endian() {
 44478           return this._littleEndian ? 'littleEndian' : 'bigEndian';
 44479         },
 44480         set endian(val) {
 44481           this._littleEndian = val == 'littleEndian';
 44482         },
 44483         get objectEncoding() {
 44484           notImplemented('URLStream.objectEncoding');
 44485         },
 44486         set objectEncoding(val) {
 44487           notImplemented('URLStream.objectEncoding');
 44489       };
 44490     var desc = Object.getOwnPropertyDescriptor;
 44491     def.__glue__ = {
 44492       native: {
 44493         instance: {
 44494           close: def.close,
 44495           load: def.load,
 44496           readBoolean: def.readBoolean,
 44497           readByte: def.readByte,
 44498           readBytes: def.readBytes,
 44499           readDouble: def.readDouble,
 44500           readFloat: def.readFloat,
 44501           readInt: def.readInt,
 44502           readMultiByte: def.readMultiByte,
 44503           readObject: def.readObject,
 44504           readShort: def.readShort,
 44505           readUTF: def.readUTF,
 44506           readUTFBytes: def.readUTFBytes,
 44507           readUnsignedByte: def.readUnsignedByte,
 44508           readUnsignedInt: def.readUnsignedInt,
 44509           readUnsignedShort: def.readUnsignedShort,
 44510           bytesAvailable: desc(def, 'bytesAvailable'),
 44511           connected: desc(def, 'connected'),
 44512           endian: desc(def, 'endian'),
 44513           objectEncoding: desc(def, 'objectEncoding')
 44516     };
 44517     return def;
 44518   }.call(this);
 44520   var ApplicationDomainDefinition = function () {
 44521       return {
 44522         __class__: 'flash.system.ApplicationDomain',
 44523         initialize: function () {
 44524         },
 44525         __glue__: {
 44526           native: {
 44527             static: {
 44528               currentDomain: {
 44529                 get: function currentDomain() {
 44530                   return new flash.system.ApplicationDomain(AVM2.currentDomain());
 44532               },
 44533               MIN_DOMAIN_MEMORY_LENGTH: {
 44534                 get: function MIN_DOMAIN_MEMORY_LENGTH() {
 44535                   notImplemented('ApplicationDomain.MIN_DOMAIN_MEMORY_LENGTH');
 44538             },
 44539             instance: {
 44540               ctor: function ctor(parentDomainOrNativeObject) {
 44541                 if (parentDomainOrNativeObject instanceof ApplicationDomain) {
 44542                   this.nativeObject = parentDomainOrNativeObject;
 44543                   return;
 44545                 var parentNativeObject = parentDomainOrNativeObject ? parentDomainOrNativeObject.nativeObject : AVM2.currentDomain().system;
 44546                 this.nativeObject = new ApplicationDomain(parentNativeObject.vm, parentNativeObject);
 44547               },
 44548               getDefinition: function getDefinition(name) {
 44549                 var simpleName = name.replace('::', '.');
 44550                 return this.nativeObject.getProperty(Multiname.fromSimpleName(simpleName), true, true);
 44551               },
 44552               hasDefinition: function hasDefinition(name) {
 44553                 if (name === undefined) {
 44554                   return false;
 44556                 var simpleName = name.replace('::', '.');
 44557                 return !(!this.nativeObject.findDomainProperty(Multiname.fromSimpleName(simpleName), false, false));
 44558               },
 44559               getQualifiedDefinitionNames: function getQualifiedDefinitionNames() {
 44560                 notImplemented('ApplicationDomain.getQualifiedDefinitionNames');
 44561               },
 44562               parentDomain: {
 44563                 get: function parentDomain() {
 44564                   var base = this.nativeObject.base;
 44565                   if (!base) {
 44566                     return undefined;
 44568                   return new flash.system.ApplicationDomain(base);
 44570               },
 44571               domainMemory: {
 44572                 get: function domainMemory() {
 44573                   notImplemented('ApplicationDomain.domainMemory');
 44574                   return this._domainMemory;
 44575                 },
 44576                 set: function domainMemory(mem) {
 44577                   notImplemented('ApplicationDomain.domainMemory');
 44578                   this._domainMemory = mem;
 44582           },
 44583           script: {
 44584             static: Glue.ALL,
 44585             instance: Glue.ALL
 44588       };
 44589     }.call(this);
 44591 var CapabilitiesDefinition = function () {
 44592     var def = {};
 44593     var os;
 44594     var userAgent = window.navigator.userAgent;
 44595     if (userAgent.indexOf('Macintosh') > 0) {
 44596       os = 'Mac OS 10.5.2';
 44597     } else if (userAgent.indexOf('Windows') > 0) {
 44598       os = 'Windows XP';
 44599     } else if (userAgent.indexOf('Linux') > 0) {
 44600       os = 'Linux';
 44601     } else if (/(iPad|iPhone|iPod|Android)/.test(userAgent)) {
 44602       os = 'iPhone3,1';
 44603     } else {
 44604       notImplemented();
 44606     def.__glue__ = {
 44607       native: {
 44608         static: {
 44609           version: {
 44610             get: function version() {
 44611               return 'SHUMWAY 10,0,0,0';
 44612             },
 44613             enumerable: true
 44614           },
 44615           os: {
 44616             get: function () {
 44617               return os;
 44618             },
 44619             enumerable: true
 44620           },
 44621           serverString: {
 44622             get: function () {
 44623               var str = toKeyValueArray({
 44624                   OS: os
 44625                 }).map(function (pair) {
 44626                   return pair[0] + '=' + encodeURIComponent(pair[1]);
 44627                 }).join('&');
 44628               somewhatImplemented('Capabilities.serverString: ' + str);
 44629               return str;
 44631           },
 44632           hasAccessibility: {
 44633             get: function hasAccessibility() {
 44634               somewhatImplemented('Capabilities.hasAccessibility');
 44635               return false;
 44637           },
 44638           isDebugger: {
 44639             get: function isDebugger() {
 44640               return false;
 44642           },
 44643           screenResolutionX: {
 44644             get: function screenResolutionX() {
 44645               return window.screen.width;
 44647           },
 44648           screenResolutionY: {
 44649             get: function screenResolutionY() {
 44650               return window.screen.height;
 44652           },
 44653           manufacturer: {
 44654             get: function manufacturer() {
 44655               somewhatImplemented('Capabilities.manufacturer');
 44656               return 'Mozilla Research';
 44658           },
 44659           language: {
 44660             get: function language() {
 44661               somewhatImplemented('Capabilities.language');
 44662               return 'en';
 44664           },
 44665           playerType: {
 44666             get: function playerType() {
 44667               somewhatImplemented('Capabilities.playerType');
 44668               return 'PlugIn';
 44672       },
 44673       script: {
 44674         static: scriptProperties('public', [
 44675           'version',
 44676           'os'
 44677         ])
 44679     };
 44680     return def;
 44681   }.call(this);
 44682 var FSCommandDefinition = function () {
 44683     var def = {};
 44684     function fscommand(command, parameters) {
 44685       console.log('FSCommand: ' + command + '; ' + parameters);
 44686       switch (command.toLowerCase()) {
 44687       case 'quit':
 44688         renderingTerminated = true;
 44689         return;
 44690       case 'debugger':
 44691         debugger;
 44692         return;
 44693       default:
 44694         break;
 44697     def.__glue__ = {
 44698       native: {
 44699         static: {
 44700           _fscommand: fscommand
 44703     };
 44704     return def;
 44705   }.call(this);
 44706 var SecurityDefinition = function () {
 44707     var _exactSettings;
 44708     return {
 44709       __class__: 'flash.system.Security',
 44710       initialize: function () {
 44711       },
 44712       __glue__: {
 44713         native: {
 44714           static: {
 44715             allowDomain: function allowDomain() {
 44716               somewhatImplemented('Security.allowDomain ["' + Array.prototype.join.call(arguments, '", "') + '"]');
 44717             },
 44718             allowInsecureDomain: function allowInsecureDomain() {
 44719               somewhatImplemented('Security.allowInsecureDomain');
 44720             },
 44721             loadPolicyFile: function loadPolicyFile(url) {
 44722               somewhatImplemented('Security.loadPolicyFile');
 44723             },
 44724             duplicateSandboxBridgeInputArguments: function duplicateSandboxBridgeInputArguments(toplevel, args) {
 44725               notImplemented('Security.duplicateSandboxBridgeInputArguments');
 44726             },
 44727             duplicateSandboxBridgeOutputArgument: function duplicateSandboxBridgeOutputArgument(toplevel, arg) {
 44728               notImplemented('Security.duplicateSandboxBridgeOutputArgument');
 44729             },
 44730             showSettings: function showSettings(panel) {
 44731               notImplemented('Security.showSettings');
 44732             },
 44733             exactSettings: {
 44734               get: function () {
 44735                 return _exactSettings;
 44736               },
 44737               set: function (value) {
 44738                 _exactSettings = value;
 44740             },
 44741             disableAVM1Loading: {
 44742               get: function disableAVM1Loading() {
 44743                 notImplemented('Security.disableAVM1Loading');
 44744               },
 44745               set: function disableAVM1Loading(value) {
 44746                 notImplemented('Security.disableAVM1Loading');
 44748             },
 44749             sandboxType: {
 44750               get: function () {
 44751                 somewhatImplemented('Security.sandboxType');
 44752                 return 'remote';
 44754             },
 44755             pageDomain: {
 44756               get: function pageDomain() {
 44757                 somewhatImplemented('Security.pageDomain');
 44758                 var pageHost = FileLoadingService.resolveUrl('/');
 44759                 var parts = pageHost.split('/');
 44760                 parts.pop();
 44761                 return parts.pop();
 44767     };
 44768   }.call(this);
 44769 var SecurityDomainDefinition = function () {
 44770     return {
 44771       __class__: 'flash.system.SecurityDomain',
 44772       initialize: function () {
 44773       },
 44774       _currentDomain: null,
 44775       __glue__: {
 44776         native: {
 44777           static: {
 44778             currentDomain: {
 44779               get: function () {
 44780                 return this._currentDomain;
 44783           },
 44784           instance: {
 44785             ctor_impl: function ctor_impl() {
 44786               notImplemented('SecurityDomain.ctor_impl');
 44787             },
 44788             domainID: {
 44789               get: function domainID() {
 44790                 notImplemented('SecurityDomain.domainID');
 44791                 return this._domainID;
 44797     };
 44798   }.call(this);
 44799 var SystemDefinition = function () {
 44800     return {
 44801       __class__: 'flash.system.System',
 44802       initialize: function () {
 44803       },
 44804       __glue__: {
 44805         native: {
 44806           static: {
 44807             setClipboard: function setClipboard(string) {
 44808               FirefoxCom.request('setClipboard', string);
 44809               TelemetryService.reportTelemetry({
 44810                 topic: 'feature',
 44811                 feature: CLIPBOARD_FEATURE
 44812               });
 44813             },
 44814             pause: function pause() {
 44815               somewhatImplemented('System.pause');
 44816             },
 44817             resume: function resume() {
 44818               somewhatImplemented('System.resume');
 44819             },
 44820             exit: function exit(code) {
 44821               somewhatImplemented('System.exit');
 44822               renderingTerminated = true;
 44823             },
 44824             gc: function gc() {
 44825               somewhatImplemented('System.gc');
 44826             },
 44827             pauseForGCIfCollectionImminent: function pauseForGCIfCollectionImminent(imminence) {
 44828               notImplemented('System.pauseForGCIfCollectionImminent');
 44829             },
 44830             disposeXML: function disposeXML(node) {
 44831               notImplemented('System.disposeXML');
 44832             },
 44833             ime: {
 44834               get: function ime() {
 44835                 notImplemented('System.ime');
 44837             },
 44838             totalMemoryNumber: {
 44839               get: function totalMemoryNumber() {
 44840                 if (performance.memory) {
 44841                   return performance.memory.usedJSHeapSize;
 44843                 return 0;
 44845             },
 44846             freeMemory: {
 44847               get: function freeMemory() {
 44848                 notImplemented('System.freeMemory');
 44850             },
 44851             privateMemory: {
 44852               get: function privateMemory() {
 44853                 return 0;
 44855             },
 44856             processCPUUsage: {
 44857               get: function processCPUUsage() {
 44858                 notImplemented('System.processCPUUsage');
 44860             },
 44861             useCodePage: {
 44862               get: function useCodePage() {
 44863                 somewhatImplemented('System.useCodePage');
 44864                 return false;
 44865               },
 44866               set: function useCodePage(value) {
 44867                 notImplemented('System.useCodePage');
 44869             },
 44870             vmVersion: {
 44871               get: function vmVersion() {
 44872                 somewhatImplemented('System.vmVersion');
 44873                 return '1.0 shumway';
 44875             },
 44876             swfVersion: {
 44877               get: function () {
 44878                 return 19;
 44880             },
 44881             apiVersion: {
 44882               get: function () {
 44883                 return 26;
 44885             },
 44886             getArgv: function () {
 44887               return [];
 44888             },
 44889             getRunmode: function () {
 44890               return 'mixed';
 44892           },
 44893           instance: {}
 44896     };
 44897   }.call(this);
 44899   var FontDefinition = function () {
 44900       var fonts = [];
 44901       var fontsByUniqueName = Object.create(null);
 44902       var fontsByNameStyleType = Object.create(null);
 44903       var _deviceFontMetrics;
 44904       var def = {
 44905           __class__: 'flash.text.Font',
 44906           initialize: function () {
 44907             var s = this.symbol;
 44908             if (s) {
 44909               this._fontName = s.name || null;
 44910               this._uniqueName = s.uniqueName;
 44911               if (s.bold) {
 44912                 if (s.italic) {
 44913                   this._fontStyle = 'boldItalic';
 44914                 } else {
 44915                   this._fontStyle = 'bold';
 44917               } else if (s.italic) {
 44918                 this._fontStyle = 'italic';
 44919               } else {
 44920                 this._fontStyle = 'regular';
 44922               var metrics = s.metrics;
 44923               metrics.height = metrics.ascent + metrics.descent + metrics.leading;
 44924               this._metrics = metrics;
 44925               this._fontType = 'embedded';
 44926               fonts.push(this);
 44927               fontsByUniqueName[this._uniqueName] = this;
 44928               var ident = this._fontName.toLowerCase() + '_' + this._fontStyle + '_embedded';
 44929               fontsByNameStyleType[ident] = this;
 44931           },
 44932           get fontName() {
 44933             return this._fontName;
 44934           },
 44935           get fontStyle() {
 44936             return this._fontStyle;
 44937           },
 44938           get fontType() {
 44939             return this._fontType;
 44940           },
 44941           hasGlyphs: function hasGlyphs(str) {
 44942             return true;
 44943           },
 44944           getFont: function (name, style, embedded) {
 44945             var ident = name.toLowerCase() + '_' + style + (embedded ? '_embedded' : '_device');
 44946             var font = fontsByNameStyleType[ident];
 44947             if (font) {
 44948               return font;
 44950             font = new flash.text.Font();
 44951             font._fontName = font._uniqueName = name;
 44952             font._fontStyle = style;
 44953             font._fontType = 'device';
 44954             var metrics = deviceFontMetrics()[name];
 44955             if (!metrics) {
 44956               metrics = deviceFontMetrics().serif;
 44957               font._fontName = font._uniqueName = 'serif';
 44959             font._metrics = {
 44960               ascent: metrics[0],
 44961               descent: metrics[1],
 44962               leading: metrics[2]
 44963             };
 44964             font._metrics.height = metrics[0] + metrics[1] + metrics[2];
 44965             fontsByNameStyleType[ident] = font;
 44966             return font;
 44967           },
 44968           getFontByUniqueName: function (name) {
 44969             return fontsByUniqueName[name];
 44971         };
 44972       function enumerateFonts(device) {
 44973         return fonts.slice();
 44975       function registerFont(font) {
 44976         somewhatImplemented('Font.registerFont');
 44978       function deviceFontMetrics() {
 44979         if (_deviceFontMetrics) {
 44980           return _deviceFontMetrics;
 44982         var userAgent = window.navigator.userAgent;
 44983         if (userAgent.indexOf('Windows') > -1) {
 44984           _deviceFontMetrics = DEVICE_FONT_METRICS_WIN;
 44985         } else if (/(Macintosh|iPad|iPhone|iPod|Android)/.test(userAgent)) {
 44986           _deviceFontMetrics = DEVICE_FONT_METRICS_MAC;
 44987         } else {
 44988           _deviceFontMetrics = DEVICE_FONT_METRICS_LINUX;
 44990         return _deviceFontMetrics;
 44992       var desc = Object.getOwnPropertyDescriptor;
 44993       def.__glue__ = {
 44994         native: {
 44995           instance: {
 44996             fontName: desc(def, 'fontName'),
 44997             fontStyle: desc(def, 'fontStyle'),
 44998             fontType: desc(def, 'fontType'),
 44999             hasGlyphs: def.hasGlyphs
 45000           },
 45001           static: {
 45002             enumerateFonts: enumerateFonts,
 45003             registerFont: registerFont
 45006       };
 45007       return def;
 45008     }.call(this);
 45009   var DEVICE_FONT_METRICS_WIN = {
 45010       'serif': [
 45011         1,
 45012         0.25,
 45014       ],
 45015       'sans-serif': [
 45016         1,
 45017         0.25,
 45019       ],
 45020       'monospace': [
 45021         1,
 45022         0.25,
 45024       ],
 45025       'birch std': [
 45026         0.9167,
 45027         0.25,
 45029       ],
 45030       'blackoak std': [
 45031         1,
 45032         0.3333,
 45034       ],
 45035       'chaparral pro': [
 45036         0.8333,
 45037         0.3333,
 45039       ],
 45040       'chaparral pro light': [
 45041         0.8333,
 45042         0.3333,
 45044       ],
 45045       'charlemagne std': [
 45046         0.9167,
 45047         0.25,
 45049       ],
 45050       'cooper std black': [
 45051         0.9167,
 45052         0.25,
 45054       ],
 45055       'giddyup std': [
 45056         0.8333,
 45057         0.3333,
 45059       ],
 45060       'hobo std': [
 45061         1.0833,
 45062         0.3333,
 45064       ],
 45065       'kozuka gothic pro b': [
 45066         1,
 45067         0.4167,
 45069       ],
 45070       'kozuka gothic pro el': [
 45071         1.0833,
 45072         0.25,
 45074       ],
 45075       'kozuka gothic pro h': [
 45076         1,
 45077         0.4167,
 45079       ],
 45080       'kozuka gothic pro l': [
 45081         1,
 45082         0.3333,
 45084       ],
 45085       'kozuka gothic pro m': [
 45086         1.0833,
 45087         0.3333,
 45089       ],
 45090       'kozuka gothic pro r': [
 45091         1,
 45092         0.3333,
 45094       ],
 45095       'kozuka mincho pro b': [
 45096         1.0833,
 45097         0.25,
 45099       ],
 45100       'kozuka mincho pro el': [
 45101         1.0833,
 45102         0.25,
 45104       ],
 45105       'kozuka mincho pro h': [
 45106         1.1667,
 45107         0.25,
 45109       ],
 45110       'kozuka mincho pro l': [
 45111         1.0833,
 45112         0.25,
 45114       ],
 45115       'kozuka mincho pro m': [
 45116         1.0833,
 45117         0.25,
 45119       ],
 45120       'kozuka mincho pro r': [
 45121         1.0833,
 45122         0.25,
 45124       ],
 45125       'mesquite std': [
 45126         0.9167,
 45127         0.25,
 45129       ],
 45130       'minion pro cond': [
 45131         1,
 45132         0.3333,
 45134       ],
 45135       'minion pro med': [
 45136         1,
 45137         0.3333,
 45139       ],
 45140       'minion pro smbd': [
 45141         1,
 45142         0.3333,
 45144       ],
 45145       'myriad arabic': [
 45146         1,
 45147         0.4167,
 45149       ],
 45150       'nueva std': [
 45151         0.75,
 45152         0.25,
 45154       ],
 45155       'nueva std cond': [
 45156         0.75,
 45157         0.25,
 45159       ],
 45160       'ocr a std': [
 45161         0.8333,
 45162         0.25,
 45164       ],
 45165       'orator std': [
 45166         1.0833,
 45167         0.25,
 45169       ],
 45170       'poplar std': [
 45171         0.9167,
 45172         0.25,
 45174       ],
 45175       'prestige elite std': [
 45176         0.9167,
 45177         0.25,
 45179       ],
 45180       'rosewood std regular': [
 45181         0.8333,
 45182         0.3333,
 45184       ],
 45185       'stencil std': [
 45186         1,
 45187         0.3333,
 45189       ],
 45190       'trajan pro': [
 45191         1,
 45192         0.25,
 45194       ],
 45195       'kozuka gothic pr6n b': [
 45196         1.4167,
 45197         0.4167,
 45199       ],
 45200       'kozuka gothic pr6n el': [
 45201         1.4167,
 45202         0.3333,
 45204       ],
 45205       'kozuka gothic pr6n h': [
 45206         1.4167,
 45207         0.4167,
 45209       ],
 45210       'kozuka gothic pr6n l': [
 45211         1.4167,
 45212         0.3333,
 45214       ],
 45215       'kozuka gothic pr6n m': [
 45216         1.5,
 45217         0.3333,
 45219       ],
 45220       'kozuka gothic pr6n r': [
 45221         1.4167,
 45222         0.3333,
 45224       ],
 45225       'kozuka mincho pr6n b': [
 45226         1.3333,
 45227         0.3333,
 45229       ],
 45230       'kozuka mincho pr6n el': [
 45231         1.3333,
 45232         0.3333,
 45234       ],
 45235       'kozuka mincho pr6n h': [
 45236         1.4167,
 45237         0.3333,
 45239       ],
 45240       'kozuka mincho pr6n l': [
 45241         1.3333,
 45242         0.3333,
 45244       ],
 45245       'kozuka mincho pr6n m': [
 45246         1.3333,
 45247         0.3333,
 45249       ],
 45250       'kozuka mincho pr6n r': [
 45251         1.3333,
 45252         0.3333,
 45254       ],
 45255       'letter gothic std': [
 45256         1,
 45257         0.25,
 45259       ],
 45260       'minion pro': [
 45261         1,
 45262         0.3333,
 45264       ],
 45265       'myriad hebrew': [
 45266         0.8333,
 45267         0.3333,
 45269       ],
 45270       'myriad pro': [
 45271         0.9167,
 45272         0.25,
 45274       ],
 45275       'myriad pro cond': [
 45276         0.9167,
 45277         0.25,
 45279       ],
 45280       'myriad pro light': [
 45281         1,
 45282         0.25,
 45284       ],
 45285       'marlett': [
 45286         1,
 45287         0,
 45289       ],
 45290       'arial': [
 45291         1,
 45292         0.25,
 45294       ],
 45295       'arabic transparent': [
 45296         1,
 45297         0.25,
 45299       ],
 45300       'arial baltic': [
 45301         1,
 45302         0.25,
 45304       ],
 45305       'arial ce': [
 45306         1,
 45307         0.25,
 45309       ],
 45310       'arial cyr': [
 45311         1,
 45312         0.25,
 45314       ],
 45315       'arial greek': [
 45316         1,
 45317         0.25,
 45319       ],
 45320       'arial tur': [
 45321         1,
 45322         0.25,
 45324       ],
 45325       'batang': [
 45326         0.8333,
 45327         0.1667,
 45329       ],
 45330       'batangche': [
 45331         0.8333,
 45332         0.1667,
 45334       ],
 45335       'gungsuh': [
 45336         0.8333,
 45337         0.1667,
 45339       ],
 45340       'gungsuhche': [
 45341         0.8333,
 45342         0.1667,
 45344       ],
 45345       'courier new': [
 45346         1,
 45347         0.25,
 45349       ],
 45350       'courier new baltic': [
 45351         1,
 45352         0.25,
 45354       ],
 45355       'courier new ce': [
 45356         1,
 45357         0.25,
 45359       ],
 45360       'courier new cyr': [
 45361         1,
 45362         0.25,
 45364       ],
 45365       'courier new greek': [
 45366         1,
 45367         0.25,
 45369       ],
 45370       'courier new tur': [
 45371         1,
 45372         0.25,
 45374       ],
 45375       'daunpenh': [
 45376         0.6667,
 45377         0.6667,
 45379       ],
 45380       'dokchampa': [
 45381         1.4167,
 45382         0.5833,
 45384       ],
 45385       'estrangelo edessa': [
 45386         0.75,
 45387         0.3333,
 45389       ],
 45390       'euphemia': [
 45391         1.0833,
 45392         0.3333,
 45394       ],
 45395       'gautami': [
 45396         1.1667,
 45397         0.8333,
 45399       ],
 45400       'vani': [
 45401         1.0833,
 45402         0.75,
 45404       ],
 45405       'gulim': [
 45406         0.8333,
 45407         0.1667,
 45409       ],
 45410       'gulimche': [
 45411         0.8333,
 45412         0.1667,
 45414       ],
 45415       'dotum': [
 45416         0.8333,
 45417         0.1667,
 45419       ],
 45420       'dotumche': [
 45421         0.8333,
 45422         0.1667,
 45424       ],
 45425       'impact': [
 45426         1.0833,
 45427         0.25,
 45429       ],
 45430       'iskoola pota': [
 45431         1,
 45432         0.3333,
 45434       ],
 45435       'kalinga': [
 45436         1.0833,
 45437         0.5,
 45439       ],
 45440       'kartika': [
 45441         1,
 45442         0.4167,
 45444       ],
 45445       'khmer ui': [
 45446         1.0833,
 45447         0.3333,
 45449       ],
 45450       'lao ui': [
 45451         1,
 45452         0.25,
 45454       ],
 45455       'latha': [
 45456         1.0833,
 45457         0.4167,
 45459       ],
 45460       'lucida console': [
 45461         0.75,
 45462         0.25,
 45464       ],
 45465       'malgun gothic': [
 45466         1,
 45467         0.25,
 45469       ],
 45470       'mangal': [
 45471         1.0833,
 45472         0.3333,
 45474       ],
 45475       'meiryo': [
 45476         1.0833,
 45477         0.4167,
 45479       ],
 45480       'meiryo ui': [
 45481         1,
 45482         0.25,
 45484       ],
 45485       'microsoft himalaya': [
 45486         0.5833,
 45487         0.4167,
 45489       ],
 45490       'microsoft jhenghei': [
 45491         1,
 45492         0.3333,
 45494       ],
 45495       'microsoft yahei': [
 45496         1.0833,
 45497         0.3333,
 45499       ],
 45500       'mingliu': [
 45501         0.8333,
 45502         0.1667,
 45504       ],
 45505       'pmingliu': [
 45506         0.8333,
 45507         0.1667,
 45509       ],
 45510       'mingliu_hkscs': [
 45511         0.8333,
 45512         0.1667,
 45514       ],
 45515       'mingliu-extb': [
 45516         0.8333,
 45517         0.1667,
 45519       ],
 45520       'pmingliu-extb': [
 45521         0.8333,
 45522         0.1667,
 45524       ],
 45525       'mingliu_hkscs-extb': [
 45526         0.8333,
 45527         0.1667,
 45529       ],
 45530       'mongolian baiti': [
 45531         0.8333,
 45532         0.25,
 45534       ],
 45535       'ms gothic': [
 45536         0.8333,
 45537         0.1667,
 45539       ],
 45540       'ms pgothic': [
 45541         0.8333,
 45542         0.1667,
 45544       ],
 45545       'ms ui gothic': [
 45546         0.8333,
 45547         0.1667,
 45549       ],
 45550       'ms mincho': [
 45551         0.8333,
 45552         0.1667,
 45554       ],
 45555       'ms pmincho': [
 45556         0.8333,
 45557         0.1667,
 45559       ],
 45560       'mv boli': [
 45561         1.1667,
 45562         0.25,
 45564       ],
 45565       'microsoft new tai lue': [
 45566         1,
 45567         0.4167,
 45569       ],
 45570       'nyala': [
 45571         0.9167,
 45572         0.3333,
 45574       ],
 45575       'microsoft phagspa': [
 45576         1.0833,
 45577         0.25,
 45579       ],
 45580       'plantagenet cherokee': [
 45581         1,
 45582         0.4167,
 45584       ],
 45585       'raavi': [
 45586         1.0833,
 45587         0.6667,
 45589       ],
 45590       'segoe script': [
 45591         1.0833,
 45592         0.5,
 45594       ],
 45595       'segoe ui': [
 45596         1,
 45597         0.25,
 45599       ],
 45600       'segoe ui semibold': [
 45601         1,
 45602         0.25,
 45604       ],
 45605       'segoe ui light': [
 45606         1,
 45607         0.25,
 45609       ],
 45610       'segoe ui symbol': [
 45611         1,
 45612         0.25,
 45614       ],
 45615       'shruti': [
 45616         1.0833,
 45617         0.5,
 45619       ],
 45620       'simsun': [
 45621         0.8333,
 45622         0.1667,
 45624       ],
 45625       'nsimsun': [
 45626         0.8333,
 45627         0.1667,
 45629       ],
 45630       'simsun-extb': [
 45631         0.8333,
 45632         0.1667,
 45634       ],
 45635       'sylfaen': [
 45636         1,
 45637         0.3333,
 45639       ],
 45640       'microsoft tai le': [
 45641         1,
 45642         0.3333,
 45644       ],
 45645       'times new roman': [
 45646         1,
 45647         0.25,
 45649       ],
 45650       'times new roman baltic': [
 45651         1,
 45652         0.25,
 45654       ],
 45655       'times new roman ce': [
 45656         1,
 45657         0.25,
 45659       ],
 45660       'times new roman cyr': [
 45661         1,
 45662         0.25,
 45664       ],
 45665       'times new roman greek': [
 45666         1,
 45667         0.25,
 45669       ],
 45670       'times new roman tur': [
 45671         1,
 45672         0.25,
 45674       ],
 45675       'tunga': [
 45676         1.0833,
 45677         0.75,
 45679       ],
 45680       'vrinda': [
 45681         1,
 45682         0.4167,
 45684       ],
 45685       'shonar bangla': [
 45686         0.8333,
 45687         0.5,
 45689       ],
 45690       'microsoft yi baiti': [
 45691         0.8333,
 45692         0.1667,
 45694       ],
 45695       'tahoma': [
 45696         1,
 45697         0.1667,
 45699       ],
 45700       'microsoft sans serif': [
 45701         1.0833,
 45702         0.1667,
 45704       ],
 45705       'angsana new': [
 45706         0.9167,
 45707         0.4167,
 45709       ],
 45710       'aparajita': [
 45711         0.75,
 45712         0.4167,
 45714       ],
 45715       'cordia new': [
 45716         0.9167,
 45717         0.5,
 45719       ],
 45720       'ebrima': [
 45721         1.0833,
 45722         0.5,
 45724       ],
 45725       'gisha': [
 45726         0.9167,
 45727         0.25,
 45729       ],
 45730       'kokila': [
 45731         0.8333,
 45732         0.3333,
 45734       ],
 45735       'leelawadee': [
 45736         0.9167,
 45737         0.25,
 45739       ],
 45740       'microsoft uighur': [
 45741         1.0833,
 45742         0.5,
 45744       ],
 45745       'moolboran': [
 45746         0.6667,
 45747         0.6667,
 45749       ],
 45750       'symbol': [
 45751         1,
 45752         0.25,
 45754       ],
 45755       'utsaah': [
 45756         0.8333,
 45757         0.4167,
 45759       ],
 45760       'vijaya': [
 45761         1.0833,
 45762         0.25,
 45764       ],
 45765       'wingdings': [
 45766         0.9167,
 45767         0.25,
 45769       ],
 45770       'andalus': [
 45771         1.3333,
 45772         0.4167,
 45774       ],
 45775       'arabic typesetting': [
 45776         0.8333,
 45777         0.5,
 45779       ],
 45780       'simplified arabic': [
 45781         1.3333,
 45782         0.5,
 45784       ],
 45785       'simplified arabic fixed': [
 45786         1,
 45787         0.4167,
 45789       ],
 45790       'sakkal majalla': [
 45791         0.9167,
 45792         0.5,
 45794       ],
 45795       'traditional arabic': [
 45796         1.3333,
 45797         0.5,
 45799       ],
 45800       'aharoni': [
 45801         0.75,
 45802         0.25,
 45804       ],
 45805       'david': [
 45806         0.75,
 45807         0.25,
 45809       ],
 45810       'frankruehl': [
 45811         0.75,
 45812         0.25,
 45814       ],
 45815       'fangsong': [
 45816         0.8333,
 45817         0.1667,
 45819       ],
 45820       'simhei': [
 45821         0.8333,
 45822         0.1667,
 45824       ],
 45825       'kaiti': [
 45826         0.8333,
 45827         0.1667,
 45829       ],
 45830       'browallia new': [
 45831         0.8333,
 45832         0.4167,
 45834       ],
 45835       'lucida sans unicode': [
 45836         1.0833,
 45837         0.25,
 45839       ],
 45840       'arial black': [
 45841         1.0833,
 45842         0.3333,
 45844       ],
 45845       'calibri': [
 45846         0.9167,
 45847         0.25,
 45849       ],
 45850       'cambria': [
 45851         0.9167,
 45852         0.25,
 45854       ],
 45855       'cambria math': [
 45856         3.0833,
 45857         2.5,
 45859       ],
 45860       'candara': [
 45861         0.9167,
 45862         0.25,
 45864       ],
 45865       'comic sans ms': [
 45866         1.0833,
 45867         0.3333,
 45869       ],
 45870       'consolas': [
 45871         0.9167,
 45872         0.25,
 45874       ],
 45875       'constantia': [
 45876         0.9167,
 45877         0.25,
 45879       ],
 45880       'corbel': [
 45881         0.9167,
 45882         0.25,
 45884       ],
 45885       'franklin gothic medium': [
 45886         1,
 45887         0.3333,
 45889       ],
 45890       'gabriola': [
 45891         1.1667,
 45892         0.6667,
 45894       ],
 45895       'georgia': [
 45896         1,
 45897         0.25,
 45899       ],
 45900       'palatino linotype': [
 45901         1.0833,
 45902         0.3333,
 45904       ],
 45905       'segoe print': [
 45906         1.25,
 45907         0.5,
 45909       ],
 45910       'trebuchet ms': [
 45911         1.0833,
 45912         0.4167,
 45914       ],
 45915       'verdana': [
 45916         1,
 45917         0.1667,
 45919       ],
 45920       'webdings': [
 45921         1.0833,
 45922         0.5,
 45924       ],
 45925       'lucida bright': [
 45926         0.9167,
 45927         0.25,
 45929       ],
 45930       'lucida sans': [
 45931         0.9167,
 45932         0.25,
 45934       ],
 45935       'lucida sans typewriter': [
 45936         0.9167,
 45937         0.25,
 45939       ],
 45940       'gentium basic': [
 45941         0.8333,
 45942         0.25,
 45944       ],
 45945       'dejavu serif condensed': [
 45946         0.9167,
 45947         0.25,
 45949       ],
 45950       'arimo': [
 45951         1,
 45952         0.25,
 45954       ],
 45955       'dejavu sans condensed': [
 45956         0.9167,
 45957         0.25,
 45959       ],
 45960       'dejavu sans': [
 45961         0.9167,
 45962         0.25,
 45964       ],
 45965       'dejavu sans light': [
 45966         0.9167,
 45967         0.25,
 45969       ],
 45970       'opensymbol': [
 45971         0.8333,
 45972         0.1667,
 45974       ],
 45975       'gentium book basic': [
 45976         0.8333,
 45977         0.25,
 45979       ],
 45980       'dejavu sans mono': [
 45981         0.9167,
 45982         0.25,
 45984       ],
 45985       'dejavu serif': [
 45986         0.9167,
 45987         0.25,
 45989       ],
 45990       'calibri light': [
 45991         0.9167,
 45992         0.25,
 45995     };
 45996   var DEVICE_FONT_METRICS_MAC = {
 45997       'al bayan plain': [
 45998         1,
 45999         0.5,
 46001       ],
 46002       'al bayan bold': [
 46003         1,
 46004         0.5833,
 46006       ],
 46007       'american typewriter': [
 46008         0.9167,
 46009         0.25,
 46011       ],
 46012       'american typewriter bold': [
 46013         0.9167,
 46014         0.25,
 46016       ],
 46017       'american typewriter condensed': [
 46018         0.9167,
 46019         0.25,
 46021       ],
 46022       'american typewriter condensed bold': [
 46023         0.9167,
 46024         0.25,
 46026       ],
 46027       'american typewriter condensed light': [
 46028         0.8333,
 46029         0.25,
 46031       ],
 46032       'american typewriter light': [
 46033         0.9167,
 46034         0.25,
 46036       ],
 46037       'andale mono': [
 46038         0.9167,
 46039         0.25,
 46041       ],
 46042       'apple symbols': [
 46043         0.6667,
 46044         0.25,
 46046       ],
 46047       'arial bold italic': [
 46048         0.9167,
 46049         0.25,
 46051       ],
 46052       'arial bold': [
 46053         0.9167,
 46054         0.25,
 46056       ],
 46057       'arial italic': [
 46058         0.9167,
 46059         0.25,
 46061       ],
 46062       'arial hebrew': [
 46063         0.75,
 46064         0.3333,
 46066       ],
 46067       'arial hebrew bold': [
 46068         0.75,
 46069         0.3333,
 46071       ],
 46072       'arial': [
 46073         0.9167,
 46074         0.25,
 46076       ],
 46077       'arial narrow': [
 46078         0.9167,
 46079         0.25,
 46081       ],
 46082       'arial narrow bold': [
 46083         0.9167,
 46084         0.25,
 46086       ],
 46087       'arial narrow bold italic': [
 46088         0.9167,
 46089         0.25,
 46091       ],
 46092       'arial narrow italic': [
 46093         0.9167,
 46094         0.25,
 46096       ],
 46097       'arial rounded mt bold': [
 46098         0.9167,
 46099         0.25,
 46101       ],
 46102       'arial unicode ms': [
 46103         1.0833,
 46104         0.25,
 46106       ],
 46107       'avenir black': [
 46108         1,
 46109         0.3333,
 46111       ],
 46112       'avenir black oblique': [
 46113         1,
 46114         0.3333,
 46116       ],
 46117       'avenir book': [
 46118         1,
 46119         0.3333,
 46121       ],
 46122       'avenir book oblique': [
 46123         1,
 46124         0.3333,
 46126       ],
 46127       'avenir heavy': [
 46128         1,
 46129         0.3333,
 46131       ],
 46132       'avenir heavy oblique': [
 46133         1,
 46134         0.3333,
 46136       ],
 46137       'avenir light': [
 46138         1,
 46139         0.3333,
 46141       ],
 46142       'avenir light oblique': [
 46143         1,
 46144         0.3333,
 46146       ],
 46147       'avenir medium': [
 46148         1,
 46149         0.3333,
 46151       ],
 46152       'avenir medium oblique': [
 46153         1,
 46154         0.3333,
 46156       ],
 46157       'avenir oblique': [
 46158         1,
 46159         0.3333,
 46161       ],
 46162       'avenir roman': [
 46163         1,
 46164         0.3333,
 46166       ],
 46167       'avenir next bold': [
 46168         1,
 46169         0.3333,
 46171       ],
 46172       'avenir next bold italic': [
 46173         1,
 46174         0.3333,
 46176       ],
 46177       'avenir next demi bold': [
 46178         1,
 46179         0.3333,
 46181       ],
 46182       'avenir next demi bold italic': [
 46183         1,
 46184         0.3333,
 46186       ],
 46187       'avenir next heavy': [
 46188         1,
 46189         0.3333,
 46191       ],
 46192       'avenir next heavy italic': [
 46193         1,
 46194         0.3333,
 46196       ],
 46197       'avenir next italic': [
 46198         1,
 46199         0.3333,
 46201       ],
 46202       'avenir next medium': [
 46203         1,
 46204         0.3333,
 46206       ],
 46207       'avenir next medium italic': [
 46208         1,
 46209         0.3333,
 46211       ],
 46212       'avenir next regular': [
 46213         1,
 46214         0.3333,
 46216       ],
 46217       'avenir next ultra light': [
 46218         1,
 46219         0.3333,
 46221       ],
 46222       'avenir next ultra light italic': [
 46223         1,
 46224         0.3333,
 46226       ],
 46227       'avenir next condensed bold': [
 46228         1,
 46229         0.3333,
 46231       ],
 46232       'avenir next condensed bold italic': [
 46233         1,
 46234         0.3333,
 46236       ],
 46237       'avenir next condensed demi bold': [
 46238         1,
 46239         0.3333,
 46241       ],
 46242       'avenir next condensed demi bold italic': [
 46243         1,
 46244         0.3333,
 46246       ],
 46247       'avenir next condensed heavy': [
 46248         1,
 46249         0.3333,
 46251       ],
 46252       'avenir next condensed heavy italic': [
 46253         1,
 46254         0.3333,
 46256       ],
 46257       'avenir next condensed italic': [
 46258         1,
 46259         0.3333,
 46261       ],
 46262       'avenir next condensed medium': [
 46263         1,
 46264         0.3333,
 46266       ],
 46267       'avenir next condensed medium italic': [
 46268         1,
 46269         0.3333,
 46271       ],
 46272       'avenir next condensed regular': [
 46273         1,
 46274         0.3333,
 46276       ],
 46277       'avenir next condensed ultra light': [
 46278         1,
 46279         0.3333,
 46281       ],
 46282       'avenir next condensed ultra light italic': [
 46283         1,
 46284         0.3333,
 46286       ],
 46287       'ayuthaya': [
 46288         1.0833,
 46289         0.3333,
 46291       ],
 46292       'baghdad': [
 46293         0.9167,
 46294         0.4167,
 46296       ],
 46297       'bangla mn': [
 46298         0.9167,
 46299         0.6667,
 46301       ],
 46302       'bangla mn bold': [
 46303         0.9167,
 46304         0.6667,
 46306       ],
 46307       'bangla sangam mn': [
 46308         0.9167,
 46309         0.4167,
 46311       ],
 46312       'bangla sangam mn bold': [
 46313         0.9167,
 46314         0.4167,
 46316       ],
 46317       'baskerville': [
 46318         0.9167,
 46319         0.25,
 46321       ],
 46322       'baskerville bold': [
 46323         0.9167,
 46324         0.25,
 46326       ],
 46327       'baskerville bold italic': [
 46328         0.9167,
 46329         0.25,
 46331       ],
 46332       'baskerville italic': [
 46333         0.9167,
 46334         0.25,
 46336       ],
 46337       'baskerville semibold': [
 46338         0.9167,
 46339         0.25,
 46341       ],
 46342       'baskerville semibold italic': [
 46343         0.9167,
 46344         0.25,
 46346       ],
 46347       'big caslon medium': [
 46348         0.9167,
 46349         0.25,
 46351       ],
 46352       'brush script mt italic': [
 46353         0.9167,
 46354         0.3333,
 46356       ],
 46357       'chalkboard': [
 46358         1,
 46359         0.25,
 46361       ],
 46362       'chalkboard bold': [
 46363         1,
 46364         0.25,
 46366       ],
 46367       'chalkboard se bold': [
 46368         1.1667,
 46369         0.25,
 46371       ],
 46372       'chalkboard se light': [
 46373         1.1667,
 46374         0.25,
 46376       ],
 46377       'chalkboard se regular': [
 46378         1.1667,
 46379         0.25,
 46381       ],
 46382       'chalkduster': [
 46383         1,
 46384         0.25,
 46386       ],
 46387       'charcoal cy': [
 46388         1,
 46389         0.25,
 46391       ],
 46392       'cochin': [
 46393         0.9167,
 46394         0.25,
 46396       ],
 46397       'cochin bold': [
 46398         0.9167,
 46399         0.25,
 46401       ],
 46402       'cochin bold italic': [
 46403         0.9167,
 46404         0.25,
 46406       ],
 46407       'cochin italic': [
 46408         0.9167,
 46409         0.25,
 46411       ],
 46412       'comic sans ms': [
 46413         1.0833,
 46414         0.25,
 46416       ],
 46417       'comic sans ms bold': [
 46418         1.0833,
 46419         0.25,
 46421       ],
 46422       'copperplate': [
 46423         0.75,
 46424         0.25,
 46426       ],
 46427       'copperplate bold': [
 46428         0.75,
 46429         0.25,
 46431       ],
 46432       'copperplate light': [
 46433         0.75,
 46434         0.25,
 46436       ],
 46437       'corsiva hebrew': [
 46438         0.6667,
 46439         0.3333,
 46441       ],
 46442       'corsiva hebrew bold': [
 46443         0.6667,
 46444         0.3333,
 46446       ],
 46447       'courier': [
 46448         0.75,
 46449         0.25,
 46451       ],
 46452       'courier bold': [
 46453         0.75,
 46454         0.25,
 46456       ],
 46457       'courier bold oblique': [
 46458         0.75,
 46459         0.25,
 46461       ],
 46462       'courier oblique': [
 46463         0.75,
 46464         0.25,
 46466       ],
 46467       'courier new bold italic': [
 46468         0.8333,
 46469         0.3333,
 46471       ],
 46472       'courier new bold': [
 46473         0.8333,
 46474         0.3333,
 46476       ],
 46477       'courier new italic': [
 46478         0.8333,
 46479         0.3333,
 46481       ],
 46482       'courier new': [
 46483         0.8333,
 46484         0.3333,
 46486       ],
 46487       'biaukai': [
 46488         0.8333,
 46489         0.1667,
 46491       ],
 46492       'damascus': [
 46493         0.5833,
 46494         0.4167,
 46496       ],
 46497       'damascus bold': [
 46498         0.5833,
 46499         0.4167,
 46501       ],
 46502       'decotype naskh': [
 46503         1.1667,
 46504         0.6667,
 46506       ],
 46507       'devanagari mt': [
 46508         0.9167,
 46509         0.6667,
 46511       ],
 46512       'devanagari mt bold': [
 46513         0.9167,
 46514         0.6667,
 46516       ],
 46517       'devanagari sangam mn': [
 46518         0.9167,
 46519         0.4167,
 46521       ],
 46522       'devanagari sangam mn bold': [
 46523         0.9167,
 46524         0.4167,
 46526       ],
 46527       'didot': [
 46528         0.9167,
 46529         0.3333,
 46531       ],
 46532       'didot bold': [
 46533         1,
 46534         0.3333,
 46536       ],
 46537       'didot italic': [
 46538         0.9167,
 46539         0.25,
 46541       ],
 46542       'euphemia ucas': [
 46543         1.0833,
 46544         0.25,
 46546       ],
 46547       'euphemia ucas bold': [
 46548         1.0833,
 46549         0.25,
 46551       ],
 46552       'euphemia ucas italic': [
 46553         1.0833,
 46554         0.25,
 46556       ],
 46557       'futura condensed extrabold': [
 46558         1,
 46559         0.25,
 46561       ],
 46562       'futura condensed medium': [
 46563         1,
 46564         0.25,
 46566       ],
 46567       'futura medium': [
 46568         1,
 46569         0.25,
 46571       ],
 46572       'futura medium italic': [
 46573         1,
 46574         0.25,
 46576       ],
 46577       'gb18030 bitmap': [
 46578         1,
 46579         0.6667,
 46581       ],
 46582       'geeza pro': [
 46583         0.9167,
 46584         0.3333,
 46586       ],
 46587       'geeza pro bold': [
 46588         0.9167,
 46589         0.3333,
 46591       ],
 46592       'geneva': [
 46593         1,
 46594         0.25,
 46596       ],
 46597       'geneva cy': [
 46598         1,
 46599         0.25,
 46601       ],
 46602       'georgia': [
 46603         0.9167,
 46604         0.25,
 46606       ],
 46607       'georgia bold': [
 46608         0.9167,
 46609         0.25,
 46611       ],
 46612       'georgia bold italic': [
 46613         0.9167,
 46614         0.25,
 46616       ],
 46617       'georgia italic': [
 46618         0.9167,
 46619         0.25,
 46621       ],
 46622       'gill sans': [
 46623         0.9167,
 46624         0.25,
 46626       ],
 46627       'gill sans bold': [
 46628         0.9167,
 46629         0.25,
 46631       ],
 46632       'gill sans bold italic': [
 46633         0.9167,
 46634         0.25,
 46636       ],
 46637       'gill sans italic': [
 46638         0.9167,
 46639         0.25,
 46641       ],
 46642       'gill sans light': [
 46643         0.9167,
 46644         0.25,
 46646       ],
 46647       'gill sans light italic': [
 46648         0.9167,
 46649         0.25,
 46651       ],
 46652       'gujarati mt': [
 46653         0.9167,
 46654         0.6667,
 46656       ],
 46657       'gujarati mt bold': [
 46658         0.9167,
 46659         0.6667,
 46661       ],
 46662       'gujarati sangam mn': [
 46663         0.8333,
 46664         0.4167,
 46666       ],
 46667       'gujarati sangam mn bold': [
 46668         0.8333,
 46669         0.4167,
 46671       ],
 46672       'gurmukhi mn': [
 46673         0.9167,
 46674         0.25,
 46676       ],
 46677       'gurmukhi mn bold': [
 46678         0.9167,
 46679         0.25,
 46681       ],
 46682       'gurmukhi sangam mn': [
 46683         0.9167,
 46684         0.3333,
 46686       ],
 46687       'gurmukhi sangam mn bold': [
 46688         0.9167,
 46689         0.3333,
 46691       ],
 46692       'helvetica': [
 46693         0.75,
 46694         0.25,
 46696       ],
 46697       'helvetica bold': [
 46698         0.75,
 46699         0.25,
 46701       ],
 46702       'helvetica bold oblique': [
 46703         0.75,
 46704         0.25,
 46706       ],
 46707       'helvetica light': [
 46708         0.75,
 46709         0.25,
 46711       ],
 46712       'helvetica light oblique': [
 46713         0.75,
 46714         0.25,
 46716       ],
 46717       'helvetica oblique': [
 46718         0.75,
 46719         0.25,
 46721       ],
 46722       'helvetica neue': [
 46723         0.9167,
 46724         0.25,
 46726       ],
 46727       'helvetica neue bold': [
 46728         1,
 46729         0.25,
 46731       ],
 46732       'helvetica neue bold italic': [
 46733         1,
 46734         0.25,
 46736       ],
 46737       'helvetica neue condensed black': [
 46738         1,
 46739         0.25,
 46741       ],
 46742       'helvetica neue condensed bold': [
 46743         1,
 46744         0.25,
 46746       ],
 46747       'helvetica neue italic': [
 46748         0.9167,
 46749         0.25,
 46751       ],
 46752       'helvetica neue light': [
 46753         1,
 46754         0.25,
 46756       ],
 46757       'helvetica neue light italic': [
 46758         0.9167,
 46759         0.25,
 46761       ],
 46762       'helvetica neue medium': [
 46763         1,
 46764         0.25,
 46766       ],
 46767       'helvetica neue ultralight': [
 46768         0.9167,
 46769         0.25,
 46771       ],
 46772       'helvetica neue ultralight italic': [
 46773         0.9167,
 46774         0.25,
 46776       ],
 46777       'herculanum': [
 46778         0.8333,
 46779         0.1667,
 46781       ],
 46782       'hiragino kaku gothic pro w3': [
 46783         0.9167,
 46784         0.0833,
 46786       ],
 46787       'hiragino kaku gothic pro w6': [
 46788         0.9167,
 46789         0.0833,
 46791       ],
 46792       'hiragino kaku gothic pron w3': [
 46793         0.9167,
 46794         0.0833,
 46796       ],
 46797       'hiragino kaku gothic pron w6': [
 46798         0.9167,
 46799         0.0833,
 46801       ],
 46802       'hiragino kaku gothic std w8': [
 46803         0.9167,
 46804         0.0833,
 46806       ],
 46807       'hiragino kaku gothic stdn w8': [
 46808         0.9167,
 46809         0.0833,
 46811       ],
 46812       'hiragino maru gothic pro w4': [
 46813         0.9167,
 46814         0.0833,
 46816       ],
 46817       'hiragino maru gothic pron w4': [
 46818         0.9167,
 46819         0.0833,
 46821       ],
 46822       'hiragino mincho pro w3': [
 46823         0.9167,
 46824         0.0833,
 46826       ],
 46827       'hiragino mincho pro w6': [
 46828         0.9167,
 46829         0.0833,
 46831       ],
 46832       'hiragino mincho pron w3': [
 46833         0.9167,
 46834         0.0833,
 46836       ],
 46837       'hiragino mincho pron w6': [
 46838         0.9167,
 46839         0.0833,
 46841       ],
 46842       'hiragino sans gb w3': [
 46843         0.9167,
 46844         0.0833,
 46846       ],
 46847       'hiragino sans gb w6': [
 46848         0.9167,
 46849         0.0833,
 46851       ],
 46852       'hoefler text black': [
 46853         0.75,
 46854         0.25,
 46856       ],
 46857       'hoefler text black italic': [
 46858         0.75,
 46859         0.25,
 46861       ],
 46862       'hoefler text italic': [
 46863         0.75,
 46864         0.25,
 46866       ],
 46867       'hoefler text ornaments': [
 46868         0.8333,
 46869         0.1667,
 46871       ],
 46872       'hoefler text': [
 46873         0.75,
 46874         0.25,
 46876       ],
 46877       'impact': [
 46878         1,
 46879         0.25,
 46881       ],
 46882       'inaimathi': [
 46883         0.8333,
 46884         0.4167,
 46886       ],
 46887       'headlinea regular': [
 46888         0.8333,
 46889         0.1667,
 46891       ],
 46892       'pilgi regular': [
 46893         0.8333,
 46894         0.25,
 46896       ],
 46897       'gungseo regular': [
 46898         0.8333,
 46899         0.25,
 46901       ],
 46902       'pcmyungjo regular': [
 46903         0.8333,
 46904         0.25,
 46906       ],
 46907       'kailasa regular': [
 46908         1.0833,
 46909         0.5833,
 46911       ],
 46912       'kannada mn': [
 46913         0.9167,
 46914         0.25,
 46916       ],
 46917       'kannada mn bold': [
 46918         0.9167,
 46919         0.25,
 46921       ],
 46922       'kannada sangam mn': [
 46923         1,
 46924         0.5833,
 46926       ],
 46927       'kannada sangam mn bold': [
 46928         1,
 46929         0.5833,
 46931       ],
 46932       'kefa bold': [
 46933         0.9167,
 46934         0.25,
 46936       ],
 46937       'kefa regular': [
 46938         0.9167,
 46939         0.25,
 46941       ],
 46942       'khmer mn': [
 46943         1,
 46944         0.6667,
 46946       ],
 46947       'khmer mn bold': [
 46948         1,
 46949         0.6667,
 46951       ],
 46952       'khmer sangam mn': [
 46953         1.0833,
 46954         0.6667,
 46956       ],
 46957       'kokonor regular': [
 46958         1.0833,
 46959         0.5833,
 46961       ],
 46962       'krungthep': [
 46963         1,
 46964         0.25,
 46966       ],
 46967       'kufistandardgk': [
 46968         0.9167,
 46969         0.5,
 46971       ],
 46972       'lao mn': [
 46973         0.9167,
 46974         0.4167,
 46976       ],
 46977       'lao mn bold': [
 46978         0.9167,
 46979         0.4167,
 46981       ],
 46982       'lao sangam mn': [
 46983         1,
 46984         0.3333,
 46986       ],
 46987       'apple ligothic medium': [
 46988         0.8333,
 46989         0.1667,
 46991       ],
 46992       'lihei pro': [
 46993         0.8333,
 46994         0.1667,
 46996       ],
 46997       'lisong pro': [
 46998         0.8333,
 46999         0.1667,
 47001       ],
 47002       'lucida grande': [
 47003         1,
 47004         0.25,
 47006       ],
 47007       'lucida grande bold': [
 47008         1,
 47009         0.25,
 47011       ],
 47012       'malayalam mn': [
 47013         1,
 47014         0.4167,
 47016       ],
 47017       'malayalam mn bold': [
 47018         1,
 47019         0.4167,
 47021       ],
 47022       'malayalam sangam mn': [
 47023         0.8333,
 47024         0.4167,
 47026       ],
 47027       'malayalam sangam mn bold': [
 47028         0.8333,
 47029         0.4167,
 47031       ],
 47032       'marion bold': [
 47033         0.6667,
 47034         0.3333,
 47036       ],
 47037       'marion italic': [
 47038         0.6667,
 47039         0.3333,
 47041       ],
 47042       'marion regular': [
 47043         0.6667,
 47044         0.3333,
 47046       ],
 47047       'marker felt thin': [
 47048         0.8333,
 47049         0.25,
 47051       ],
 47052       'marker felt wide': [
 47053         0.9167,
 47054         0.25,
 47056       ],
 47057       'menlo bold': [
 47058         0.9167,
 47059         0.25,
 47061       ],
 47062       'menlo bold italic': [
 47063         0.9167,
 47064         0.25,
 47066       ],
 47067       'menlo italic': [
 47068         0.9167,
 47069         0.25,
 47071       ],
 47072       'menlo regular': [
 47073         0.9167,
 47074         0.25,
 47076       ],
 47077       'microsoft sans serif': [
 47078         0.9167,
 47079         0.25,
 47081       ],
 47082       'monaco': [
 47083         1,
 47084         0.25,
 47086       ],
 47087       'gurmukhi mt': [
 47088         0.8333,
 47089         0.4167,
 47091       ],
 47092       'mshtakan': [
 47093         0.9167,
 47094         0.25,
 47096       ],
 47097       'mshtakan bold': [
 47098         0.9167,
 47099         0.25,
 47101       ],
 47102       'mshtakan boldoblique': [
 47103         0.9167,
 47104         0.25,
 47106       ],
 47107       'mshtakan oblique': [
 47108         0.9167,
 47109         0.25,
 47111       ],
 47112       'myanmar mn': [
 47113         1,
 47114         0.4167,
 47116       ],
 47117       'myanmar mn bold': [
 47118         1,
 47119         0.4167,
 47121       ],
 47122       'myanmar sangam mn': [
 47123         0.9167,
 47124         0.4167,
 47126       ],
 47127       'nadeem': [
 47128         0.9167,
 47129         0.4167,
 47131       ],
 47132       'nanum brush script': [
 47133         0.9167,
 47134         0.25,
 47136       ],
 47137       'nanumgothic': [
 47138         0.9167,
 47139         0.25,
 47141       ],
 47142       'nanumgothic bold': [
 47143         0.9167,
 47144         0.25,
 47146       ],
 47147       'nanumgothic extrabold': [
 47148         0.9167,
 47149         0.25,
 47151       ],
 47152       'nanummyeongjo': [
 47153         0.9167,
 47154         0.25,
 47156       ],
 47157       'nanummyeongjo bold': [
 47158         0.9167,
 47159         0.25,
 47161       ],
 47162       'nanummyeongjo extrabold': [
 47163         0.9167,
 47164         0.25,
 47166       ],
 47167       'nanum pen script': [
 47168         0.9167,
 47169         0.25,
 47171       ],
 47172       'optima bold': [
 47173         0.9167,
 47174         0.25,
 47176       ],
 47177       'optima bold italic': [
 47178         0.9167,
 47179         0.25,
 47181       ],
 47182       'optima extrablack': [
 47183         1,
 47184         0.25,
 47186       ],
 47187       'optima italic': [
 47188         0.9167,
 47189         0.25,
 47191       ],
 47192       'optima regular': [
 47193         0.9167,
 47194         0.25,
 47196       ],
 47197       'oriya mn': [
 47198         0.9167,
 47199         0.25,
 47201       ],
 47202       'oriya mn bold': [
 47203         0.9167,
 47204         0.25,
 47206       ],
 47207       'oriya sangam mn': [
 47208         0.8333,
 47209         0.4167,
 47211       ],
 47212       'oriya sangam mn bold': [
 47213         0.8333,
 47214         0.4167,
 47216       ],
 47217       'osaka': [
 47218         1,
 47219         0.25,
 47221       ],
 47222       'osaka-mono': [
 47223         0.8333,
 47224         0.1667,
 47226       ],
 47227       'palatino bold': [
 47228         0.8333,
 47229         0.25,
 47231       ],
 47232       'palatino bold italic': [
 47233         0.8333,
 47234         0.25,
 47236       ],
 47237       'palatino italic': [
 47238         0.8333,
 47239         0.25,
 47241       ],
 47242       'palatino': [
 47243         0.8333,
 47244         0.25,
 47246       ],
 47247       'papyrus': [
 47248         0.9167,
 47249         0.5833,
 47251       ],
 47252       'papyrus condensed': [
 47253         0.9167,
 47254         0.5833,
 47256       ],
 47257       'plantagenet cherokee': [
 47258         0.6667,
 47259         0.25,
 47261       ],
 47262       'raanana': [
 47263         0.75,
 47264         0.25,
 47266       ],
 47267       'raanana bold': [
 47268         0.75,
 47269         0.25,
 47271       ],
 47272       'hei regular': [
 47273         0.8333,
 47274         0.1667,
 47276       ],
 47277       'kai regular': [
 47278         0.8333,
 47279         0.1667,
 47281       ],
 47282       'stfangsong': [
 47283         0.8333,
 47284         0.1667,
 47286       ],
 47287       'stheiti': [
 47288         0.8333,
 47289         0.1667,
 47291       ],
 47292       'heiti sc light': [
 47293         0.8333,
 47294         0.1667,
 47296       ],
 47297       'heiti sc medium': [
 47298         0.8333,
 47299         0.1667,
 47301       ],
 47302       'heiti tc light': [
 47303         0.8333,
 47304         0.1667,
 47306       ],
 47307       'heiti tc medium': [
 47308         0.8333,
 47309         0.1667,
 47311       ],
 47312       'stkaiti': [
 47313         0.8333,
 47314         0.1667,
 47316       ],
 47317       'kaiti sc black': [
 47318         1.0833,
 47319         0.3333,
 47321       ],
 47322       'kaiti sc bold': [
 47323         1.0833,
 47324         0.3333,
 47326       ],
 47327       'kaiti sc regular': [
 47328         1.0833,
 47329         0.3333,
 47331       ],
 47332       'stsong': [
 47333         0.8333,
 47334         0.1667,
 47336       ],
 47337       'songti sc black': [
 47338         1.0833,
 47339         0.3333,
 47341       ],
 47342       'songti sc bold': [
 47343         1.0833,
 47344         0.3333,
 47346       ],
 47347       'songti sc light': [
 47348         1.0833,
 47349         0.3333,
 47351       ],
 47352       'songti sc regular': [
 47353         1.0833,
 47354         0.3333,
 47356       ],
 47357       'stxihei': [
 47358         0.8333,
 47359         0.1667,
 47361       ],
 47362       'sathu': [
 47363         0.9167,
 47364         0.3333,
 47366       ],
 47367       'silom': [
 47368         1,
 47369         0.3333,
 47371       ],
 47372       'sinhala mn': [
 47373         0.9167,
 47374         0.25,
 47376       ],
 47377       'sinhala mn bold': [
 47378         0.9167,
 47379         0.25,
 47381       ],
 47382       'sinhala sangam mn': [
 47383         1.1667,
 47384         0.3333,
 47386       ],
 47387       'sinhala sangam mn bold': [
 47388         1.1667,
 47389         0.3333,
 47391       ],
 47392       'skia regular': [
 47393         0.75,
 47394         0.25,
 47396       ],
 47397       'symbol': [
 47398         0.6667,
 47399         0.3333,
 47401       ],
 47402       'tahoma negreta': [
 47403         1,
 47404         0.1667,
 47406       ],
 47407       'tamil mn': [
 47408         0.9167,
 47409         0.25,
 47411       ],
 47412       'tamil mn bold': [
 47413         0.9167,
 47414         0.25,
 47416       ],
 47417       'tamil sangam mn': [
 47418         0.75,
 47419         0.25,
 47421       ],
 47422       'tamil sangam mn bold': [
 47423         0.75,
 47424         0.25,
 47426       ],
 47427       'telugu mn': [
 47428         0.9167,
 47429         0.25,
 47431       ],
 47432       'telugu mn bold': [
 47433         0.9167,
 47434         0.25,
 47436       ],
 47437       'telugu sangam mn': [
 47438         1,
 47439         0.5833,
 47441       ],
 47442       'telugu sangam mn bold': [
 47443         1,
 47444         0.5833,
 47446       ],
 47447       'thonburi': [
 47448         1.0833,
 47449         0.25,
 47451       ],
 47452       'thonburi bold': [
 47453         1.0833,
 47454         0.25,
 47456       ],
 47457       'times bold': [
 47458         0.75,
 47459         0.25,
 47461       ],
 47462       'times bold italic': [
 47463         0.75,
 47464         0.25,
 47466       ],
 47467       'times italic': [
 47468         0.75,
 47469         0.25,
 47471       ],
 47472       'times roman': [
 47473         0.75,
 47474         0.25,
 47476       ],
 47477       'times new roman bold italic': [
 47478         0.9167,
 47479         0.25,
 47481       ],
 47482       'times new roman bold': [
 47483         0.9167,
 47484         0.25,
 47486       ],
 47487       'times new roman italic': [
 47488         0.9167,
 47489         0.25,
 47491       ],
 47492       'times new roman': [
 47493         0.9167,
 47494         0.25,
 47496       ],
 47497       'trebuchet ms bold italic': [
 47498         0.9167,
 47499         0.25,
 47501       ],
 47502       'trebuchet ms': [
 47503         0.9167,
 47504         0.25,
 47506       ],
 47507       'trebuchet ms bold': [
 47508         0.9167,
 47509         0.25,
 47511       ],
 47512       'trebuchet ms italic': [
 47513         0.9167,
 47514         0.25,
 47516       ],
 47517       'verdana': [
 47518         1,
 47519         0.25,
 47521       ],
 47522       'verdana bold': [
 47523         1,
 47524         0.25,
 47526       ],
 47527       'verdana bold italic': [
 47528         1,
 47529         0.25,
 47531       ],
 47532       'verdana italic': [
 47533         1,
 47534         0.25,
 47536       ],
 47537       'webdings': [
 47538         0.8333,
 47539         0.1667,
 47541       ],
 47542       'wingdings 2': [
 47543         0.8333,
 47544         0.25,
 47546       ],
 47547       'wingdings 3': [
 47548         0.9167,
 47549         0.25,
 47551       ],
 47552       'yuppy sc regular': [
 47553         1.0833,
 47554         0.3333,
 47556       ],
 47557       'yuppy tc regular': [
 47558         1.0833,
 47559         0.3333,
 47561       ],
 47562       'zapf dingbats': [
 47563         0.8333,
 47564         0.1667,
 47566       ],
 47567       'zapfino': [
 47568         1.9167,
 47569         1.5,
 47572     };
 47573   var DEVICE_FONT_METRICS_LINUX = {
 47574       'kacstfarsi': [
 47575         1.0831,
 47576         0.5215,
 47578       ],
 47579       'meera': [
 47580         0.682,
 47581         0.4413,
 47583       ],
 47584       'freemono': [
 47585         0.8023,
 47586         0.2006,
 47588       ],
 47589       'undotum': [
 47590         1.0029,
 47591         0.2808,
 47593       ],
 47594       'loma': [
 47595         1.1634,
 47596         0.4814,
 47598       ],
 47599       'century schoolbook l': [
 47600         1.0029,
 47601         0.3209,
 47603       ],
 47604       'kacsttitlel': [
 47605         1.0831,
 47606         0.5215,
 47608       ],
 47609       'undinaru': [
 47610         1.0029,
 47611         0.2407,
 47613       ],
 47614       'ungungseo': [
 47615         1.0029,
 47616         0.2808,
 47618       ],
 47619       'garuda': [
 47620         1.3238,
 47621         0.6017,
 47623       ],
 47624       'rekha': [
 47625         1.1232,
 47626         0.2808,
 47628       ],
 47629       'purisa': [
 47630         1.1232,
 47631         0.5215,
 47633       ],
 47634       'dejavu sans mono': [
 47635         0.9628,
 47636         0.2407,
 47638       ],
 47639       'vemana2000': [
 47640         0.8825,
 47641         0.8424,
 47643       ],
 47644       'kacstoffice': [
 47645         1.0831,
 47646         0.5215,
 47648       ],
 47649       'umpush': [
 47650         1.2837,
 47651         0.682,
 47653       ],
 47654       'opensymbol': [
 47655         0.8023,
 47656         0.2006,
 47658       ],
 47659       'sawasdee': [
 47660         1.1232,
 47661         0.4413,
 47663       ],
 47664       'urw palladio l': [
 47665         1.0029,
 47666         0.3209,
 47668       ],
 47669       'freeserif': [
 47670         0.9227,
 47671         0.3209,
 47673       ],
 47674       'kacstdigital': [
 47675         1.0831,
 47676         0.5215,
 47678       ],
 47679       'ubuntu condensed': [
 47680         0.9628,
 47681         0.2006,
 47683       ],
 47684       'unpilgi': [
 47685         1.0029,
 47686         0.4413,
 47688       ],
 47689       'mry_kacstqurn': [
 47690         1.4442,
 47691         0.7221,
 47693       ],
 47694       'urw gothic l': [
 47695         1.0029,
 47696         0.2407,
 47698       ],
 47699       'dingbats': [
 47700         0.8424,
 47701         0.1605,
 47703       ],
 47704       'urw chancery l': [
 47705         1.0029,
 47706         0.3209,
 47708       ],
 47709       'phetsarath ot': [
 47710         1.0831,
 47711         0.5215,
 47713       ],
 47714       'tlwg typist': [
 47715         0.8825,
 47716         0.4012,
 47718       ],
 47719       'kacstletter': [
 47720         1.0831,
 47721         0.5215,
 47723       ],
 47724       'utkal': [
 47725         1.2035,
 47726         0.6418,
 47728       ],
 47729       'dejavu sans light': [
 47730         0.9628,
 47731         0.2407,
 47733       ],
 47734       'norasi': [
 47735         1.2436,
 47736         0.5215,
 47738       ],
 47739       'dejavu serif condensed': [
 47740         0.9628,
 47741         0.2407,
 47743       ],
 47744       'kacstone': [
 47745         1.2436,
 47746         0.6418,
 47748       ],
 47749       'liberation sans narrow': [
 47750         0.9628,
 47751         0.2407,
 47753       ],
 47754       'symbol': [
 47755         1.043,
 47756         0.3209,
 47758       ],
 47759       'nanummyeongjo': [
 47760         0.9227,
 47761         0.2407,
 47763       ],
 47764       'untitled1': [
 47765         0.682,
 47766         0.5616,
 47768       ],
 47769       'lohit gujarati': [
 47770         0.9628,
 47771         0.4012,
 47773       ],
 47774       'liberation mono': [
 47775         0.8424,
 47776         0.3209,
 47778       ],
 47779       'kacstart': [
 47780         1.0831,
 47781         0.5215,
 47783       ],
 47784       'mallige': [
 47785         1.0029,
 47786         0.682,
 47788       ],
 47789       'bitstream charter': [
 47790         1.0029,
 47791         0.2407,
 47793       ],
 47794       'nanumgothic': [
 47795         0.9227,
 47796         0.2407,
 47798       ],
 47799       'liberation serif': [
 47800         0.9227,
 47801         0.2407,
 47803       ],
 47804       'dejavu sans condensed': [
 47805         0.9628,
 47806         0.2407,
 47808       ],
 47809       'ubuntu': [
 47810         0.9628,
 47811         0.2006,
 47813       ],
 47814       'courier 10 pitch': [
 47815         0.8825,
 47816         0.3209,
 47818       ],
 47819       'nimbus sans l': [
 47820         0.9628,
 47821         0.3209,
 47823       ],
 47824       'takaopgothic': [
 47825         0.8825,
 47826         0.2006,
 47828       ],
 47829       'wenquanyi micro hei mono': [
 47830         0.9628,
 47831         0.2407,
 47833       ],
 47834       'dejavu sans': [
 47835         0.9628,
 47836         0.2407,
 47838       ],
 47839       'kedage': [
 47840         1.0029,
 47841         0.682,
 47843       ],
 47844       'kinnari': [
 47845         1.3238,
 47846         0.5215,
 47848       ],
 47849       'tlwgmono': [
 47850         0.8825,
 47851         0.4012,
 47853       ],
 47854       'standard symbols l': [
 47855         1.043,
 47856         0.3209,
 47858       ],
 47859       'lohit punjabi': [
 47860         1.2035,
 47861         0.682,
 47863       ],
 47864       'nimbus mono l': [
 47865         0.8424,
 47866         0.2808,
 47868       ],
 47869       'rachana': [
 47870         0.682,
 47871         0.5616,
 47873       ],
 47874       'waree': [
 47875         1.2436,
 47876         0.4413,
 47878       ],
 47879       'kacstposter': [
 47880         1.0831,
 47881         0.5215,
 47883       ],
 47884       'khmer os': [
 47885         1.2837,
 47886         0.7622,
 47888       ],
 47889       'freesans': [
 47890         1.0029,
 47891         0.3209,
 47893       ],
 47894       'gargi': [
 47895         0.9628,
 47896         0.2808,
 47898       ],
 47899       'nimbus roman no9 l': [
 47900         0.9628,
 47901         0.3209,
 47903       ],
 47904       'dejavu serif': [
 47905         0.9628,
 47906         0.2407,
 47908       ],
 47909       'wenquanyi micro hei': [
 47910         0.9628,
 47911         0.2407,
 47913       ],
 47914       'ubuntu light': [
 47915         0.9628,
 47916         0.2006,
 47918       ],
 47919       'tlwgtypewriter': [
 47920         0.9227,
 47921         0.4012,
 47923       ],
 47924       'kacstpen': [
 47925         1.0831,
 47926         0.5215,
 47928       ],
 47929       'tlwg typo': [
 47930         0.8825,
 47931         0.4012,
 47933       ],
 47934       'mukti narrow': [
 47935         1.2837,
 47936         0.4413,
 47938       ],
 47939       'ubuntu mono': [
 47940         0.8424,
 47941         0.2006,
 47943       ],
 47944       'lohit bengali': [
 47945         1.0029,
 47946         0.4413,
 47948       ],
 47949       'liberation sans': [
 47950         0.9227,
 47951         0.2407,
 47953       ],
 47954       'unbatang': [
 47955         1.0029,
 47956         0.2808,
 47958       ],
 47959       'kacstdecorative': [
 47960         1.1232,
 47961         0.5215,
 47963       ],
 47964       'khmer os system': [
 47965         1.2436,
 47966         0.6017,
 47968       ],
 47969       'saab': [
 47970         1.0029,
 47971         0.682,
 47973       ],
 47974       'kacsttitle': [
 47975         1.0831,
 47976         0.5215,
 47978       ],
 47979       'mukti narrow bold': [
 47980         1.2837,
 47981         0.4413,
 47983       ],
 47984       'lohit hindi': [
 47985         1.0029,
 47986         0.5215,
 47988       ],
 47989       'kacstqurn': [
 47990         1.0831,
 47991         0.5215,
 47993       ],
 47994       'urw bookman l': [
 47995         0.9628,
 47996         0.2808,
 47998       ],
 47999       'kacstnaskh': [
 48000         1.0831,
 48001         0.5215,
 48003       ],
 48004       'kacstscreen': [
 48005         1.0831,
 48006         0.5215,
 48008       ],
 48009       'pothana2000': [
 48010         0.8825,
 48011         0.8424,
 48013       ],
 48014       'ungraphic': [
 48015         1.0029,
 48016         0.2808,
 48018       ],
 48019       'lohit tamil': [
 48020         0.8825,
 48021         0.361,
 48023       ],
 48024       'kacstbook': [
 48025         1.0831,
 48026         0.5215,
 48029     };
 48030   DEVICE_FONT_METRICS_MAC.__proto__ = DEVICE_FONT_METRICS_WIN;
 48031   DEVICE_FONT_METRICS_LINUX.__proto__ = DEVICE_FONT_METRICS_MAC;
 48033 var StaticTextDefinition = function () {
 48034     var def = {
 48035         __class__: 'flash.text.StaticText',
 48036         initialize: function () {
 48037           var s = this.symbol;
 48038           if (s) {
 48039             this.draw = s.draw;
 48041         },
 48042         get text() {
 48043           return this._text;
 48044         },
 48045         set text(val) {
 48046           this._text = val;
 48048       };
 48049     var desc = Object.getOwnPropertyDescriptor;
 48050     def.__glue__ = {
 48051       native: {
 48052         instance: {
 48053           text: desc(def, 'text')
 48056     };
 48057     return def;
 48058   }.call(this);
 48059 var StyleSheetDefinition = function () {
 48060     return {
 48061       __class__: 'flash.text.StyleSheet',
 48062       initialize: function () {
 48063       },
 48064       __glue__: {
 48065         native: {
 48066           static: {},
 48067           instance: {
 48068             _update: function _update() {
 48069               somewhatImplemented('StyleSheet._update');
 48070             },
 48071             _parseCSSInternal: function _parseCSSInternal(cssText) {
 48072               somewhatImplemented('StyleSheet._parseCSSInternal');
 48073               return null;
 48074             },
 48075             _parseCSSFontFamily: function _parseCSSFontFamily(fontFamily) {
 48076               notImplemented('StyleSheet._parseCSSFontFamily');
 48077             },
 48078             _parseColor: function _parseColor(color) {
 48079               notImplemented('StyleSheet._parseColor');
 48080             },
 48081             _styles: {
 48082               get: function _styles() {
 48083                 return this.__styles;
 48084               },
 48085               set: function _styles(styles) {
 48086                 somewhatImplemented('StyleSheet._styles');
 48087                 this.__styles = styles;
 48093     };
 48094   }.call(this);
 48095 var TextFieldDefinition = function () {
 48096     var def = {
 48097         __class__: 'flash.text.TextField',
 48098         initialize: function () {
 48099           this._bbox = {
 48100             xMin: 0,
 48101             yMin: 0,
 48102             xMax: 2000,
 48103             yMax: 2000
 48104           };
 48105           var initialFormat = {
 48106               align: 'LEFT',
 48107               face: 'serif',
 48108               size: 12,
 48109               letterspacing: 0,
 48110               kerning: 0,
 48111               color: 0,
 48112               leading: 0
 48113             };
 48114           this._content = new TextFieldContent(initialFormat);
 48115           this._type = 'dynamic';
 48116           this._embedFonts = false;
 48117           this._selectable = true;
 48118           this._autoSize = 'none';
 48119           this._scrollV = 1;
 48120           this._maxScrollV = 1;
 48121           this._bottomScrollV = 1;
 48122           this._drawingOffsetH = 0;
 48123           this._background = false;
 48124           this._border = false;
 48125           this._backgroundColor = 16777215;
 48126           this._backgroundColorStr = '#ffffff';
 48127           this._borderColor = 0;
 48128           this._borderColorStr = '#000000';
 48129           var s = this.symbol;
 48130           if (!s) {
 48131             this._currentTransform.tx -= 40;
 48132             this._currentTransform.ty -= 40;
 48133             this._content.resolveFont(initialFormat, false);
 48134             this.text = '';
 48135             return;
 48137           var tag = s.tag;
 48138           var bbox = tag.bbox;
 48139           this._currentTransform.tx += bbox.xMin;
 48140           this._currentTransform.ty += bbox.yMin;
 48141           this._bbox.xMax = bbox.xMax - bbox.xMin;
 48142           this._bbox.yMax = bbox.yMax - bbox.yMin;
 48143           if (tag.hasLayout) {
 48144             initialFormat.size = tag.fontHeight / 20;
 48145             initialFormat.leading = (tag.leading | 0) / 20;
 48147           if (tag.hasColor) {
 48148             initialFormat.color = rgbaObjToStr(tag.color);
 48150           if (tag.hasFont) {
 48151             var font = FontDefinition.getFontByUniqueName(tag.font);
 48152             initialFormat.font = font;
 48153             initialFormat.face = font._fontName;
 48154             initialFormat.bold = font.symbol.bold;
 48155             initialFormat.italic = font.symbol.italic;
 48156             initialFormat.str = this._content.makeFormatString(initialFormat);
 48158           this._content.multiline = !(!tag.multiline);
 48159           this._content.wordWrap = !(!tag.wordWrap);
 48160           this._embedFonts = !(!tag.useOutlines);
 48161           this._selectable = !tag.noSelect;
 48162           this._border = !(!tag.border);
 48163           switch (tag.align) {
 48164           case 1:
 48165             initialFormat.align = 'right';
 48166             break;
 48167           case 2:
 48168             initialFormat.align = 'center';
 48169             break;
 48170           case 3:
 48171             initialFormat.align = 'justified';
 48172             break;
 48173           default:
 48175           if (tag.initialText) {
 48176             if (tag.html) {
 48177               this.htmlText = tag.initialText;
 48178             } else {
 48179               this.text = tag.initialText;
 48181           } else {
 48182             this.text = '';
 48184         },
 48185         _getAS2Object: function () {
 48186           if (!this.$as2Object) {
 48187             new avm1lib.AS2TextField(this);
 48189           return this.$as2Object;
 48190         },
 48191         replaceText: function (begin, end, str) {
 48192           var text = this._content.text;
 48193           this.text = text.substring(0, begin) + str + text.substring(end);
 48194         },
 48195         draw: function (ctx, ratio, colorTransform) {
 48196           this.ensureDimensions();
 48197           var bounds = this._bbox;
 48198           var width = bounds.xMax / 20;
 48199           var height = bounds.yMax / 20;
 48200           if (width <= 0 || height <= 0) {
 48201             return;
 48203           ctx.save();
 48204           ctx.beginPath();
 48205           ctx.rect(0, 0, width + 1, height + 1);
 48206           ctx.clip();
 48207           if (this._background) {
 48208             colorTransform.setFillStyle(ctx, this._backgroundColorStr);
 48209             ctx.fill();
 48211           if (this._border) {
 48212             colorTransform.setStrokeStyle(ctx, this._borderColorStr);
 48213             ctx.lineCap = 'square';
 48214             ctx.lineWidth = 1;
 48215             ctx.strokeRect(0.5, 0.5, width | 0, height | 0);
 48217           ctx.closePath();
 48218           if (this._content.lines.length === 0) {
 48219             ctx.restore();
 48220             return;
 48222           ctx.translate(2, 2);
 48223           ctx.save();
 48224           colorTransform.setAlpha(ctx);
 48225           var runs = this._content._textRuns;
 48226           var offsetY = this._content.lines[this._scrollV - 1].y;
 48227           for (var i = 0; i < runs.length; i++) {
 48228             var run = runs[i];
 48229             if (run.type === 'f') {
 48230               ctx.restore();
 48231               ctx.font = run.format.str;
 48232               colorTransform.setFillStyle(ctx, run.format.color);
 48233               ctx.save();
 48234               colorTransform.setAlpha(ctx);
 48235             } else {
 48236               if (run.y < offsetY) {
 48237                 continue;
 48239               ctx.fillText(run.text, run.x - this._drawingOffsetH, run.y - offsetY);
 48242           ctx.restore();
 48243           ctx.restore();
 48244         },
 48245         invalidateDimensions: function () {
 48246           this._invalidate();
 48247           this._invalidateBounds();
 48248           this._dimensionsValid = false;
 48249         },
 48250         ensureDimensions: function () {
 48251           if (this._dimensionsValid) {
 48252             return;
 48254           var bounds = this._bbox;
 48255           var combinedAlign = this._content.calculateMetrics(bounds, this._embedFonts);
 48256           this._scrollV = 1;
 48257           this._maxScrollV = 1;
 48258           this._bottomScrollV = 1;
 48259           var autoSize = this._autoSize;
 48260           if (autoSize === 'none') {
 48261             var maxVisibleY = (bounds.yMax - 80) / 20;
 48262             if (this._content.textHeight > maxVisibleY) {
 48263               var lines = this._content.lines;
 48264               for (var i = 0; i < lines.length; i++) {
 48265                 var line = lines[i];
 48266                 if (line.y + line.height > maxVisibleY) {
 48267                   this._maxScrollV = i + 1;
 48268                   this._bottomScrollV = i === 0 ? 1 : i;
 48269                   break;
 48273           } else {
 48274             var width = Math.max(bounds.xMax / 20 - 4, 1);
 48275             var targetWidth = this._content.textWidth;
 48276             var align = combinedAlign;
 48277             var diffX = 0;
 48278             if (align !== 'mixed') {
 48279               switch (autoSize) {
 48280               case 'left':
 48281                 break;
 48282               case 'center':
 48283                 diffX = width - targetWidth >> 1;
 48284                 break;
 48285               case 'right':
 48286                 diffX = width - targetWidth;
 48288               if (align === 'left') {
 48289                 this._drawingOffsetH = 0;
 48290               } else {
 48291                 var offset;
 48292                 switch (autoSize) {
 48293                 case 'left':
 48294                   offset = width - targetWidth;
 48295                   break;
 48296                 case 'center':
 48297                   offset = diffX << 1;
 48298                   break;
 48299                 case 'right':
 48300                   offset = diffX;
 48301                   break;
 48303                 if (align === 'center') {
 48304                   offset >>= 1;
 48306                 this._drawingOffsetH = offset;
 48308               this._invalidateTransform();
 48309               this._currentTransform.tx += diffX * 20 | 0;
 48310               bounds.xMax = (targetWidth * 20 | 0) + 80;
 48312             bounds.yMax = (this._content.textHeight * 20 | 0) + 80;
 48313             console.log(bounds.yMax);
 48314             this._invalidateBounds();
 48316           this._dimensionsValid = true;
 48317         },
 48318         get text() {
 48319           return this._content.text;
 48320         },
 48321         set text(val) {
 48322           this._content.text = val;
 48323           this.invalidateDimensions();
 48324         },
 48325         get htmlText() {
 48326           return this._content.htmlText;
 48327         },
 48328         set htmlText(val) {
 48329           this._content.htmlText = val;
 48330           this.invalidateDimensions();
 48331         },
 48332         get defaultTextFormat() {
 48333           var format = this._content.defaultTextFormat;
 48334           return new flash.text.TextFormat().fromObject(format);
 48335         },
 48336         set defaultTextFormat(val) {
 48337           this._content.defaultTextFormat = val.toObject();
 48338           this.invalidateDimensions();
 48339         },
 48340         getTextFormat: function (beginIndex, endIndex) {
 48341           return this.defaultTextFormat;
 48342         },
 48343         setTextFormat: function (format, beginIndex, endIndex) {
 48344           this.defaultTextFormat = format;
 48345           if (this.text === this.htmlText) {
 48346             this.text = this.text;
 48348           this.invalidateDimensions();
 48349         },
 48350         get x() {
 48351           this.ensureDimensions();
 48352           return this._currentTransform.tx;
 48353         },
 48354         set x(val) {
 48355           if (val === this._currentTransform.tx) {
 48356             return;
 48358           this._invalidate();
 48359           this._invalidateBounds();
 48360           this._invalidateTransform();
 48361           this._currentTransform.tx = val;
 48362         },
 48363         get width() {
 48364           this.ensureDimensions();
 48365           return this._bbox.xMax;
 48366         },
 48367         set width(value) {
 48368           if (value < 0) {
 48369             return;
 48371           this._bbox.xMax = value;
 48372           this.invalidateDimensions();
 48373         },
 48374         get height() {
 48375           this.ensureDimensions();
 48376           return this._bbox.yMax;
 48377         },
 48378         set height(value) {
 48379           if (value < 0) {
 48380             return;
 48382           this._bbox.yMax = value;
 48383           this._invalidate();
 48384         },
 48385         _getContentBounds: function () {
 48386           this.ensureDimensions();
 48387           return this._bbox;
 48388         },
 48389         _getRegion: function getRegion(targetCoordSpace) {
 48390           return this._getTransformedRect(this._getContentBounds(), targetCoordSpace);
 48391         },
 48392         getLineMetrics: function (lineIndex) {
 48393           this.ensureDimensions();
 48394           if (lineIndex < 0 || lineIndex >= this._content.lines.length) {
 48395             throwError('RangeError', Errors.ParamRangeError);
 48397           var line = this._content.lines[lineIndex];
 48398           var format = line.largestFormat;
 48399           var metrics = format.font._metrics;
 48400           var size = format.size;
 48401           var ascent = metrics.ascent * size + 0.49999 | 0;
 48402           var descent = metrics.descent * size + 0.49999 | 0;
 48403           var leading = metrics.leading * size + 0.49999 + line.leading | 0;
 48404           return new flash.text.TextLineMetrics(line.x + 2, line.width, line.height, ascent, descent, leading);
 48405         },
 48406         getCharBoundaries: function getCharBoundaries(index) {
 48407           somewhatImplemented('TextField.getCharBoundaries');
 48408           return new flash.geom.Rectangle(0, 0, 0, 0);
 48410       };
 48411     var desc = Object.getOwnPropertyDescriptor;
 48412     def.__glue__ = {
 48413       native: {
 48414         instance: {
 48415           text: desc(def, 'text'),
 48416           defaultTextFormat: desc(def, 'defaultTextFormat'),
 48417           draw: def.draw,
 48418           htmlText: desc(def, 'htmlText'),
 48419           replaceText: def.replaceText,
 48420           getTextFormat: def.getTextFormat,
 48421           setTextFormat: def.setTextFormat,
 48422           getCharBoundaries: def.getCharBoundaries,
 48423           autoSize: {
 48424             get: function autoSize() {
 48425               return this._autoSize;
 48426             },
 48427             set: function autoSize(value) {
 48428               if (this._autoSize === value) {
 48429                 return;
 48431               this._autoSize = value;
 48432               this.invalidateDimensions();
 48434           },
 48435           multiline: {
 48436             get: function multiline() {
 48437               return this._content.multiline;
 48438             },
 48439             set: function multiline(value) {
 48440               if (this._content.multiline === value) {
 48441                 return;
 48443               this._content.multiline = value;
 48444               this.invalidateDimensions();
 48446           },
 48447           textColor: {
 48448             get: function textColor() {
 48449               return this._content.textColor;
 48450             },
 48451             set: function textColor(value) {
 48452               if (this._content.textColor === value) {
 48453                 return;
 48455               this._content.textColor = value;
 48456               this._invalidate();
 48458           },
 48459           selectable: {
 48460             get: function selectable() {
 48461               return this._selectable;
 48462             },
 48463             set: function selectable(value) {
 48464               somewhatImplemented('TextField.selectable');
 48465               this._selectable = value;
 48467           },
 48468           wordWrap: {
 48469             get: function wordWrap() {
 48470               return this._content.wordWrap;
 48471             },
 48472             set: function wordWrap(value) {
 48473               if (this._content.wordWrap === value) {
 48474                 return;
 48476               this._content.wordWrap = value;
 48477               this.invalidateDimensions();
 48479           },
 48480           textHeight: {
 48481             get: function textHeight() {
 48482               this.ensureDimensions();
 48483               return this._content.textHeight;
 48485           },
 48486           textWidth: {
 48487             get: function textWidth() {
 48488               this.ensureDimensions();
 48489               return this._content.textWidth;
 48491           },
 48492           length: {
 48493             get: function length() {
 48494               return this.text.length;
 48496           },
 48497           numLines: {
 48498             get: function numLines() {
 48499               this.ensureDimensions();
 48500               return this._content.lines.length;
 48502           },
 48503           getLineMetrics: function (lineIndex) {
 48504             return this.getLineMetrics(lineIndex);
 48505           },
 48506           setSelection: function (beginIndex, endIndex) {
 48507             somewhatImplemented('TextField.setSelection');
 48508           },
 48509           scrollV: {
 48510             get: function scrollV() {
 48511               return this._scrollV;
 48512             },
 48513             set: function scrollV(value) {
 48514               this.ensureDimensions();
 48515               value = Math.max(1, Math.min(this._maxScrollV, value));
 48516               this._scrollV = value;
 48518           },
 48519           bottomScrollV: {
 48520             get: function bottomScrollV() {
 48521               this.ensureDimensions();
 48522               if (this._scrollV === 1) {
 48523                 return this._bottomScrollV;
 48525               var maxVisibleY = (this._bbox.yMax - 80) / 20;
 48526               var lines = this._content.lines;
 48527               var offsetY = lines[this._scrollV - 1].y;
 48528               for (var i = this._bottomScrollV; i < lines.length; i++) {
 48529                 var line = lines[i];
 48530                 if (line.y + line.height + offsetY > maxVisibleY) {
 48531                   return i + 1;
 48535           },
 48536           maxScrollV: {
 48537             get: function maxScrollV() {
 48538               this.ensureDimensions();
 48539               return this._maxScrollV;
 48541           },
 48542           maxScrollH: {
 48543             get: function maxScrollH() {
 48544               this.ensureDimensions();
 48545               return Math.max(this._content.textWidth - this._bbox.xMax / 20 + 4, 0);
 48547           },
 48548           background: {
 48549             get: function background() {
 48550               return this._background;
 48551             },
 48552             set: function background(value) {
 48553               if (this._background === value) {
 48554                 return;
 48556               this._background = value;
 48557               this._invalidate();
 48559           },
 48560           backgroundColor: {
 48561             get: function backgroundColor() {
 48562               return this._backgroundColor;
 48563             },
 48564             set: function backgroundColor(value) {
 48565               if (this._backgroundColor === value) {
 48566                 return;
 48568               this._backgroundColor = value;
 48569               this._backgroundColorStr = rgbIntAlphaToStr(value, 1);
 48570               if (this._background) {
 48571                 this._invalidate();
 48574           },
 48575           border: {
 48576             get: function border() {
 48577               return this._border;
 48578             },
 48579             set: function border(value) {
 48580               if (this._border === value) {
 48581                 return;
 48583               this._border = value;
 48584               this._invalidate();
 48586           },
 48587           borderColor: {
 48588             get: function borderColor() {
 48589               return this._borderColor;
 48590             },
 48591             set: function borderColor(value) {
 48592               if (this._borderColor === value) {
 48593                 return;
 48595               this._borderColor = value;
 48596               this._borderColorStr = rgbIntAlphaToStr(value, 1);
 48597               if (this._border) {
 48598                 this._invalidate();
 48601           },
 48602           type: {
 48603             get: function borderColor() {
 48604               return this._type;
 48605             },
 48606             set: function borderColor(value) {
 48607               somewhatImplemented('TextField.type');
 48608               this._type = value;
 48610           },
 48611           embedFonts: {
 48612             get: function embedFonts() {
 48613               return this._embedFonts;
 48614             },
 48615             set: function embedFonts(value) {
 48616               this.invalidateDimensions();
 48617               this._embedFonts = value;
 48619           },
 48620           condenseWhite: {
 48621             get: function condenseWhite() {
 48622               return this._content.condenseWhite;
 48623             },
 48624             set: function condenseWhite(value) {
 48625               somewhatImplemented('TextField.condenseWhite');
 48626               this._content.condenseWhite = value;
 48628           },
 48629           sharpness: {
 48630             get: function sharpness() {
 48631               return this._sharpness;
 48632             },
 48633             set: function sharpness(value) {
 48634               somewhatImplemented('TextField.sharpness');
 48635               this._sharpness = value;
 48640     };
 48641     return def;
 48642   }.call(this);
 48643 function TextFieldContent(initialFormat) {
 48644   this.defaultTextFormat = initialFormat;
 48645   this.textWidth = 0;
 48646   this.textHeight = 0;
 48647   this.condenseWhite = false;
 48648   this.wordWrap = false;
 48649   this.multiline = false;
 48650   this.textColor = null;
 48651   this._text = '';
 48652   this._htmlText = '';
 48653   this._createTrunk();
 48654   this._textRuns = null;
 48655   this._htmlParser = document.createElement('p');
 48656   this._measureCtx = document.createElement('canvas').getContext('2d');
 48658 TextFieldContent.knownNodeTypes = {
 48659   'BR': true,
 48660   'LI': true,
 48661   'P': true,
 48662   'B': true,
 48663   'I': true,
 48664   'FONT': true,
 48665   'TEXTFORMAT': true,
 48666   'U': true,
 48667   'A': true,
 48668   'IMG': true,
 48669   'SPAN': true
 48670 };
 48671 TextFieldContent.WRAP_OPPORTUNITIES = {
 48672   ' ': true,
 48673   '.': true,
 48674   '-': true,
 48675   '\t': true
 48676 };
 48677 TextFieldContent.TextLine = function (y) {
 48678   this.x = 0;
 48679   this.width = 0;
 48680   this.y = y;
 48681   this.height = 0;
 48682   this.leading = 0;
 48683   this.runs = [];
 48684   this.largestFormat = null;
 48685 };
 48686 TextFieldContent.prototype = {
 48687   get text() {
 48688     return this._text;
 48689   },
 48690   set text(val) {
 48691     val = val + '';
 48692     if (this._text === val) {
 48693       return;
 48695     var lines = [];
 48696     var lineOffset = 0;
 48697     for (var index = 0; index < val.length;) {
 48698       var char = val[index];
 48699       if (char === '\r' || char === '\n') {
 48700         lines.push(val.substring(lineOffset, index));
 48701         lineOffset = index;
 48702         if (char === '\r' && val[index + 1] === '\n') {
 48703           index++;
 48706       index++;
 48708     lines.push(val.substring(lineOffset, index));
 48709     this._createTrunk();
 48710     this._text = val;
 48711     this._htmlText = val;
 48712     this._tree.children[0].children[0] = {
 48713       type: 'plain-text',
 48714       lines: lines
 48715     };
 48716   },
 48717   get htmlText() {
 48718     return this._htmlText;
 48719   },
 48720   set htmlText(val) {
 48721     if (this._htmlText === val) {
 48722       return;
 48724     this.defaultTextFormat.bold = false;
 48725     this.defaultTextFormat.italic = false;
 48726     this._parseHtml(val);
 48727   },
 48728   calculateMetrics: function (bounds, embedFonts) {
 48729     var initialFormat = this.defaultTextFormat;
 48730     this.resolveFont(initialFormat, embedFonts);
 48731     this.lines = [];
 48732     this._textRuns = [
 48734         type: 'f',
 48735         format: initialFormat
 48737     ];
 48738     var width = Math.max(bounds.xMax / 20 - 4, 1);
 48739     var height = Math.max(bounds.yMax / 20 - 4, 1);
 48740     var state = {
 48741         ctx: this._measureCtx,
 48742         w: width,
 48743         h: height,
 48744         maxLineWidth: 0,
 48745         formats: [
 48746           initialFormat
 48747         ],
 48748         currentFormat: initialFormat,
 48749         line: new TextFieldContent.TextLine(0),
 48750         wordWrap: this.wordWrap,
 48751         combinedAlign: null,
 48752         textColor: this.textColor,
 48753         embedFonts: embedFonts
 48754       };
 48755     this._collectRuns(state, this._tree);
 48756     this._finishLine(state, false);
 48757     this.textWidth = state.maxLineWidth | 0;
 48758     this.textHeight = state.line.y | 0;
 48759     return state.combinedAlign;
 48760   },
 48761   makeFormatString: function (format) {
 48762     var boldItalic = '';
 48763     if (format.italic) {
 48764       boldItalic += 'italic';
 48766     if (format.bold) {
 48767       boldItalic += ' bold';
 48769     return boldItalic + ' ' + format.size + 'px ' + (format.font._uniqueName || format.font._fontName);
 48770   },
 48771   resolveFont: function (format, embedded) {
 48772     var face = format.face.toLowerCase();
 48773     if (face === '_sans') {
 48774       face = 'sans-serif';
 48775     } else if (face === '_serif') {
 48776       face = 'serif';
 48777     } else if (face === '_typewriter') {
 48778       face = 'monospace';
 48780     var style;
 48781     if (format.bold) {
 48782       if (format.italic) {
 48783         style = 'boldItalic';
 48784       } else {
 48785         style = 'bold';
 48787     } else if (format.italic) {
 48788       style = 'italic';
 48789     } else {
 48790       style = 'regular';
 48792     var font = FontDefinition.getFont(face, style, embedded);
 48793     format.font = font;
 48794   },
 48795   _parseHtml: function (val) {
 48796     this._htmlParser.innerHTML = val;
 48797     var rootElement = this._htmlParser.childNodes.length !== 1 ? this._htmlParser : this._htmlParser.childNodes[0];
 48798     this._text = '';
 48799     this._htmlText = val;
 48800     this._createTrunk();
 48801     if (rootElement.nodeType === 3) {
 48802       this._convertNode(rootElement, this._tree.children[0].children);
 48804     var initialNodeList = [
 48805         rootElement
 48806       ];
 48807     var attributes;
 48808     var format;
 48809     var key;
 48810     if (initialNodeList.length == 1 && rootElement.localName.toUpperCase() == 'P') {
 48811       attributes = this._extractAttributes(rootElement);
 48812       format = this._tree.format;
 48813       for (key in attributes) {
 48814         format[key] = attributes[key];
 48816       initialNodeList = rootElement.childNodes;
 48817       rootElement = rootElement.childNodes[0];
 48819     if (initialNodeList.length == 1 && rootElement.localName.toUpperCase() == 'FONT') {
 48820       attributes = this._extractAttributes(rootElement);
 48821       format = this._tree.children[0].format;
 48822       for (key in attributes) {
 48823         format[key] = attributes[key];
 48825       initialNodeList = rootElement.childNodes;
 48827     this._convertNodeList(initialNodeList, this._tree.children[0].children);
 48828   },
 48829   _createTrunk: function () {
 48830     var initialFormat = this.defaultTextFormat;
 48831     this._tree = {
 48832       type: 'SPAN',
 48833       format: {
 48834         ALIGN: initialFormat.align
 48835       },
 48836       children: []
 48837     };
 48838     var fontAttributes = {
 48839         FACE: initialFormat.face,
 48840         LETTERSPACING: initialFormat.letterSpacing,
 48841         KERNING: initialFormat.kerning,
 48842         LEADING: initialFormat.leading,
 48843         COLOR: initialFormat.color
 48844       };
 48845     this._tree.children[0] = {
 48846       type: 'FONT',
 48847       format: fontAttributes,
 48848       children: []
 48849     };
 48850   },
 48851   _convertNode: function (input, destinationList) {
 48852     if (!(input.nodeType === 1 || input.nodeType === 3) || input.prefix) {
 48853       return;
 48855     var node;
 48856     if (input.nodeType === 3) {
 48857       var text = input.textContent;
 48858       node = {
 48859         type: 'text',
 48860         text: text,
 48861         format: null,
 48862         children: null
 48863       };
 48864       this._text += text;
 48865       destinationList.push(node);
 48866       return;
 48868     var nodeType = input.localName.toUpperCase();
 48869     if (!TextFieldContent.knownNodeTypes[nodeType] || this.multiline === false && (nodeType === 'P' || nodeType === 'BR')) {
 48870       if (nodeType === 'SBR') {
 48871         destinationList.push({
 48872           type: 'BR',
 48873           text: null,
 48874           format: null,
 48875           children: null
 48876         });
 48878       this._convertNodeList(input.childNodes, destinationList);
 48879       return;
 48881     node = {
 48882       type: nodeType,
 48883       text: null,
 48884       format: this._extractAttributes(input),
 48885       children: []
 48886     };
 48887     this._convertNodeList(input.childNodes, node.children);
 48888     destinationList.push(node);
 48889   },
 48890   _convertNodeList: function (from, to) {
 48891     var childCount = from.length;
 48892     for (var i = 0; i < childCount; i++) {
 48893       this._convertNode(from[i], to);
 48895   },
 48896   _extractAttributes: function (node) {
 48897     var attributesList = node.attributes;
 48898     var attributesMap = {};
 48899     for (var i = 0; i < attributesList.length; i++) {
 48900       var attr = attributesList[i];
 48901       if (attr.prefix) {
 48902         continue;
 48904       attributesMap[attr.localName.toUpperCase()] = attr.value;
 48906     return attributesMap;
 48907   },
 48908   _collectRuns: function (state, node) {
 48909     var formatNode = false;
 48910     var blockNode = false;
 48911     switch (node.type) {
 48912     case 'plain-text':
 48913       var lines = node.lines;
 48914       for (var i = 0; i < lines.length; i++) {
 48915         this._addRunsForText(state, lines[i]);
 48916         if (i < lines.length - 1) {
 48917           this._finishLine(state, true);
 48920       return;
 48921     case 'text':
 48922       this._addRunsForText(state, node.text);
 48923       return;
 48924     case 'BR':
 48925       this._finishLine(state, true);
 48926       return;
 48927     case 'LI':
 48928     case 'P':
 48929       this._finishLine(state, false);
 48930       this._pushFormat(state, node);
 48931       blockNode = true;
 48932       break;
 48933     case 'B':
 48934     case 'I':
 48935     case 'FONT':
 48936     case 'TEXTFORMAT':
 48937       this._pushFormat(state, node);
 48938       formatNode = true;
 48939       break;
 48940     case 'U':
 48941     case 'A':
 48942     case 'IMG':
 48943     case 'SPAN':
 48944     default:
 48946     for (var i = 0; i < node.children.length; i++) {
 48947       var child = node.children[i];
 48948       this._collectRuns(state, child);
 48950     if (formatNode) {
 48951       this._popFormat(state);
 48953     if (blockNode) {
 48954       this._finishLine(state, true);
 48956   },
 48957   _addRunsForText: function (state, text) {
 48958     if (!text) {
 48959       return;
 48961     if (!state.wordWrap) {
 48962       this._addTextRun(state, text, state.ctx.measureText(text).width);
 48963       return;
 48965     while (text.length) {
 48966       var width = state.ctx.measureText(text).width;
 48967       var availableWidth = state.w - state.line.width;
 48968       if (availableWidth <= 0) {
 48969         this._finishLine(state, false);
 48970         availableWidth = state.w - state.line.width;
 48972       if (width <= availableWidth) {
 48973         this._addTextRun(state, text, width);
 48974         break;
 48975       } else {
 48976         var offset = text.length / width * availableWidth | 0;
 48977         while (state.ctx.measureText(text.substr(0, offset)).width < availableWidth && offset < text.length) {
 48978           offset++;
 48980         var wrapOffset = offset;
 48981         while (wrapOffset > -1) {
 48982           if (TextFieldContent.WRAP_OPPORTUNITIES[text[wrapOffset]]) {
 48983             wrapOffset++;
 48984             break;
 48986           wrapOffset--;
 48988         if (wrapOffset === -1) {
 48989           if (state.line.width > 0) {
 48990             this._finishLine(state, false);
 48991             continue;
 48993           while (state.ctx.measureText(text.substr(0, offset)).width > availableWidth) {
 48994             offset--;
 48996           if (offset === 0) {
 48997             offset = 1;
 48999           wrapOffset = offset;
 49001         var runText = text.substr(0, wrapOffset);
 49002         width = state.ctx.measureText(runText).width;
 49003         this._addTextRun(state, runText, width);
 49004         if (state.wordWrap) {
 49005           this._finishLine(state, false);
 49007         text = text.substr(wrapOffset);
 49010   },
 49011   _addTextRun: function (state, text, width) {
 49012     if (text.length === 0) {
 49013       return;
 49015     var line = state.line;
 49016     var format = state.currentFormat;
 49017     var size = format.size;
 49018     var run = {
 49019         type: 't',
 49020         text: text,
 49021         x: line.width
 49022       };
 49023     this._textRuns.push(run);
 49024     state.line.runs.push(run);
 49025     line.width += width | 0;
 49026     if (line.leading === 0 && format.leading > line.leading) {
 49027       line.leading = format.leading;
 49029     if (!line.largestFormat || size > line.largestFormat.size) {
 49030       line.largestFormat = format;
 49032   },
 49033   _finishLine: function (state, forceNewline) {
 49034     var line = state.line;
 49035     if (line.runs.length === 0) {
 49036       if (forceNewline) {
 49037         var format = state.currentFormat;
 49038         state.line.y += format.font._metrics.height * format.size + format.leading | 0;
 49040       return;
 49042     var runs = line.runs;
 49043     var format = line.largestFormat;
 49044     var baselinePos = line.y + format.font._metrics.ascent * format.size;
 49045     for (var i = runs.length; i--;) {
 49046       runs[i].y = baselinePos;
 49048     var align = (state.currentFormat.align || '').toLowerCase();
 49049     if (state.combinedAlign === null) {
 49050       state.combinedAlign = align;
 49051     } else if (state.combinedAlign !== align) {
 49052       state.combinedAlign = 'mixed';
 49054     if (align === 'center' || align === 'right') {
 49055       var offset = Math.max(state.w - line.width, 0);
 49056       if (align === 'center') {
 49057         offset >>= 1;
 49059       for (i = runs.length; i--;) {
 49060         runs[i].x += offset;
 49063     line.height = format.font._metrics.height * format.size + line.leading | 0;
 49064     state.maxLineWidth = Math.max(state.maxLineWidth, line.width);
 49065     this.lines.push(line);
 49066     state.line = new TextFieldContent.TextLine(line.y + line.height);
 49067   },
 49068   _pushFormat: function (state, node) {
 49069     var attributes = node.format;
 49070     var format = Object.create(state.formats[state.formats.length - 1]);
 49071     var fontChanged = false;
 49072     switch (node.type) {
 49073     case 'P':
 49074       if (attributes.ALIGN === format.align) {
 49075         return;
 49077       format.align = attributes.ALIGN;
 49078       break;
 49079     case 'B':
 49080       format.bold = true;
 49081       fontChanged = true;
 49082       break;
 49083     case 'I':
 49084       format.italic = true;
 49085       fontChanged = true;
 49086       break;
 49087     case 'FONT':
 49088       if (attributes.COLOR !== undefined) {
 49089         format.color = attributes.COLOR;
 49091       if (attributes.FACE !== undefined) {
 49092         format.face = attributes.FACE;
 49093         fontChanged = true;
 49095       if (attributes.SIZE !== undefined) {
 49096         format.size = parseFloat(attributes.SIZE);
 49098       if (attributes.LETTERSPACING !== undefined) {
 49099         format.letterspacing = parseFloat(attributes.LETTERSPACING);
 49101       if (attributes.KERNING !== undefined) {
 49102         format.kerning = attributes.KERNING && true;
 49104     case 'TEXTFORMAT':
 49105       if (attributes.LEADING !== undefined) {
 49106         format.leading = parseFloat(attributes.LEADING);
 49108       if (attributes.INDENT !== undefined) {
 49109         state.line.x = attributes.INDENT;
 49110         state.line.width += attributes.INDENT | 0;
 49112       break;
 49113     default:
 49114       warning('Unknown format node encountered: ' + node.type);
 49115       return;
 49117     if (state.textColor !== null) {
 49118       format.color = rgbIntAlphaToStr(state.textColor, 1);
 49120     if (fontChanged) {
 49121       this.resolveFont(format, state.embedFonts);
 49123     format.str = this.makeFormatString(format);
 49124     state.formats.push(format);
 49125     this._textRuns.push({
 49126       type: 'f',
 49127       format: format
 49128     });
 49129     state.currentFormat = format;
 49130     state.ctx.font = format.str;
 49131   },
 49132   _popFormat: function (state) {
 49133     state.formats.pop();
 49134     var format = state.currentFormat = state.formats[state.formats.length - 1];
 49135     this._textRuns.push({
 49136       type: 'f',
 49137       format: format
 49138     });
 49139     state.ctx.font = state.str;
 49141 };
 49142 var TextFormatDefinition = function () {
 49143     var measureTextField;
 49144     return {
 49145       __class__: 'flash.text.TextFormat',
 49146       initialize: function () {
 49147       },
 49148       fromObject: function (obj) {
 49149         this._font = obj.face || null;
 49150         this._size = typeof obj.size === 'number' ? obj.size : null;
 49151         this._color = typeof obj.color === 'number' ? obj.color : null;
 49152         this._bold = typeof obj.bold === 'boolean' ? obj.bold : null;
 49153         this._italic = typeof obj.italic === 'boolean' ? obj.italic : null;
 49154         this._underline = typeof obj.underline === 'boolean' ? obj.underline : null;
 49155         this._url = obj.url || null;
 49156         this._target = obj.target || null;
 49157         this._align = obj.align || null;
 49158         this._leftMargin = typeof obj.leftMargin === 'number' ? obj.leftMargin : null;
 49159         this._rightMargin = typeof obj.rightMargin === 'number' ? obj.rightMargin : null;
 49160         this._indent = typeof obj.indent === 'number' ? obj.indent : null;
 49161         this._leading = typeof obj.leading === 'number' ? obj.leading : null;
 49162         return this;
 49163       },
 49164       toObject: function () {
 49165         return {
 49166           face: this._font || 'serif',
 49167           size: this._size || 12,
 49168           color: this._color || 0,
 49169           bold: this._bold || false,
 49170           italic: this._italic || false,
 49171           underline: this._underline || false,
 49172           url: this._url,
 49173           target: this._target,
 49174           align: this._align || 'left',
 49175           leftMargin: this._leftMargin || 0,
 49176           rightMargin: this._rightMargin || 0,
 49177           indent: this._indent || 0,
 49178           leading: this._leading || 0
 49179         };
 49180       },
 49181       as2GetTextExtent: function (text, width) {
 49182         if (!measureTextField) {
 49183           measureTextField = new flash.text.TextField();
 49184           measureTextField._multiline = true;
 49186         if (!isNaN(width) && width > 0) {
 49187           measureTextField.width = width + 4;
 49188           measureTextField._wordWrap = true;
 49189         } else {
 49190           measureTextField._wordWrap = false;
 49192         measureTextField.defaultTextFormat = this;
 49193         measureTextField.text = text;
 49194         measureTextField.ensureDimensions();
 49195         var result = {};
 49196         var textWidth = measureTextField._textWidth;
 49197         var textHeight = measureTextField._textHeight;
 49198         result.asSetPublicProperty('width', textWidth);
 49199         result.asSetPublicProperty('height', textHeight);
 49200         result.asSetPublicProperty('textFieldWidth', textWidth + 4);
 49201         result.asSetPublicProperty('textFieldHeight', textHeight + 4);
 49202         var metrics = measureTextField.getLineMetrics(0);
 49203         result.asSetPublicProperty('ascent', metrics.asGetPublicProperty('ascent'));
 49204         result.asSetPublicProperty('descent', metrics.asGetPublicProperty('descent'));
 49205         return result;
 49206       },
 49207       __glue__: {
 49208         native: {
 49209           static: {},
 49210           instance: {
 49211             align: {
 49212               get: function align() {
 49213                 return this._align;
 49214               },
 49215               set: function align(value) {
 49216                 this._align = value;
 49218             },
 49219             blockIndent: {
 49220               get: function blockIndent() {
 49221                 return this._blockIndent;
 49222               },
 49223               set: function blockIndent(value) {
 49224                 this._blockIndent = value;
 49226             },
 49227             bold: {
 49228               get: function bold() {
 49229                 return this._bold;
 49230               },
 49231               set: function bold(value) {
 49232                 this._bold = value;
 49234             },
 49235             bullet: {
 49236               get: function bullet() {
 49237                 return this._bullet;
 49238               },
 49239               set: function bullet(value) {
 49240                 this._bullet = value;
 49242             },
 49243             color: {
 49244               get: function color() {
 49245                 return this._color;
 49246               },
 49247               set: function color(value) {
 49248                 this._color = value;
 49250             },
 49251             display: {
 49252               get: function display() {
 49253                 return this._display;
 49254               },
 49255               set: function display(value) {
 49256                 this._display = value;
 49258             },
 49259             font: {
 49260               get: function font() {
 49261                 return this._font;
 49262               },
 49263               set: function font(value) {
 49264                 this._font = value;
 49266             },
 49267             indent: {
 49268               get: function indent() {
 49269                 return this._indent;
 49270               },
 49271               set: function indent(value) {
 49272                 this._indent = value;
 49274             },
 49275             italic: {
 49276               get: function italic() {
 49277                 return this._italic;
 49278               },
 49279               set: function italic(value) {
 49280                 this._italic = value;
 49282             },
 49283             kerning: {
 49284               get: function kerning() {
 49285                 return this._kerning;
 49286               },
 49287               set: function kerning(value) {
 49288                 this._kerning = value;
 49290             },
 49291             leading: {
 49292               get: function leading() {
 49293                 return this._leading;
 49294               },
 49295               set: function leading(value) {
 49296                 this._leading = value;
 49298             },
 49299             leftMargin: {
 49300               get: function leftMargin() {
 49301                 return this._leftMargin;
 49302               },
 49303               set: function leftMargin(value) {
 49304                 this._leftMargin = value;
 49306             },
 49307             letterSpacing: {
 49308               get: function letterSpacing() {
 49309                 return this._letterSpacing;
 49310               },
 49311               set: function letterSpacing(value) {
 49312                 this._letterSpacing = value;
 49314             },
 49315             rightMargin: {
 49316               get: function rightMargin() {
 49317                 return this._rightMargin;
 49318               },
 49319               set: function rightMargin(value) {
 49320                 this._rightMargin = value;
 49322             },
 49323             size: {
 49324               get: function size() {
 49325                 return this._size;
 49326               },
 49327               set: function size(value) {
 49328                 this._size = value;
 49330             },
 49331             tabStops: {
 49332               get: function tabStops() {
 49333                 return this._tabStops;
 49334               },
 49335               set: function tabStops(value) {
 49336                 this._tabStops = value;
 49338             },
 49339             target: {
 49340               get: function target() {
 49341                 return this._target;
 49342               },
 49343               set: function target(value) {
 49344                 this._target = value;
 49346             },
 49347             underline: {
 49348               get: function underline() {
 49349                 return this._underline;
 49350               },
 49351               set: function underline(value) {
 49352                 this._underline = value;
 49354             },
 49355             url: {
 49356               get: function url() {
 49357                 return this._url;
 49358               },
 49359               set: function url(value) {
 49360                 this._url = value;
 49366     };
 49367   }.call(this);
 49368 var ContentElementDefinition = function () {
 49369     return {
 49370       __class__: 'flash.text.engine.ContentElement',
 49371       initialize: function () {
 49372       },
 49373       __glue__: {
 49374         native: {
 49375           static: {},
 49376           instance: {
 49377             textBlock: {
 49378               get: function textBlock() {
 49379                 notImplemented('ContentElement.textBlock');
 49380                 return this._textBlock;
 49382             },
 49383             textBlockBeginIndex: {
 49384               get: function textBlockBeginIndex() {
 49385                 notImplemented('ContentElement.textBlockBeginIndex');
 49386                 return this._textBlockBeginIndex;
 49388             },
 49389             elementFormat: {
 49390               get: function elementFormat() {
 49391                 return this._elementFormat;
 49392               },
 49393               set: function elementFormat(value) {
 49394                 somewhatImplemented('ContentElement.elementFormat');
 49395                 this._elementFormat = value;
 49397             },
 49398             eventMirror: {
 49399               get: function eventMirror() {
 49400                 return this._eventMirror;
 49401               },
 49402               set: function eventMirror(value) {
 49403                 somewhatImplemented('ContentElement.eventMirror');
 49404                 this._eventMirror = value;
 49406             },
 49407             groupElement: {
 49408               get: function groupElement() {
 49409                 notImplemented('ContentElement.groupElement');
 49410                 return this._groupElement;
 49412             },
 49413             rawText: {
 49414               get: function rawText() {
 49415                 notImplemented('ContentElement.rawText');
 49416                 return this._rawText;
 49418             },
 49419             text: {
 49420               get: function text() {
 49421                 notImplemented('ContentElement.text');
 49422                 return this._text;
 49424             },
 49425             textRotation: {
 49426               get: function textRotation() {
 49427                 return this._textRotation;
 49428               },
 49429               set: function textRotation(value) {
 49430                 somewhatImplemented('ContentElement.textRotation');
 49431                 this._textRotation = value;
 49437     };
 49438   }.call(this);
 49439 var ElementFormatDefinition = function () {
 49440     return {
 49441       __class__: 'flash.text.engine.ElementFormat',
 49442       initialize: function () {
 49443       },
 49444       __glue__: {
 49445         native: {
 49446           static: {},
 49447           instance: {
 49448             getFontMetrics: function getFontMetrics() {
 49449               notImplemented('ElementFormat.getFontMetrics');
 49450             },
 49451             alignmentBaseline: {
 49452               get: function alignmentBaseline() {
 49453                 return this._alignmentBaseline;
 49454               },
 49455               set: function alignmentBaseline(alignmentBaseline) {
 49456                 somewhatImplemented('ElementFormat.alignmentBaseline');
 49457                 this._alignmentBaseline = alignmentBaseline;
 49459             },
 49460             alpha: {
 49461               get: function alpha() {
 49462                 return this._alpha;
 49463               },
 49464               set: function alpha(value) {
 49465                 somewhatImplemented('ElementFormat.alpha');
 49466                 this._alpha = value;
 49468             },
 49469             baselineShift: {
 49470               get: function baselineShift() {
 49471                 return this._baselineShift;
 49472               },
 49473               set: function baselineShift(value) {
 49474                 somewhatImplemented('ElementFormat.baselineShift');
 49475                 this._baselineShift = value;
 49477             },
 49478             breakOpportunity: {
 49479               get: function breakOpportunity() {
 49480                 return this._breakOpportunity;
 49481               },
 49482               set: function breakOpportunity(opportunityType) {
 49483                 somewhatImplemented('ElementFormat.breakOpportunity');
 49484                 this._breakOpportunity = opportunityType;
 49486             },
 49487             color: {
 49488               get: function color() {
 49489                 return this._color;
 49490               },
 49491               set: function color(value) {
 49492                 somewhatImplemented('ElementFormat.color');
 49493                 this._color = value;
 49495             },
 49496             dominantBaseline: {
 49497               get: function dominantBaseline() {
 49498                 return this._dominantBaseline;
 49499               },
 49500               set: function dominantBaseline(dominantBaseline) {
 49501                 somewhatImplemented('ElementFormat.dominantBaseline');
 49502                 this._dominantBaseline = dominantBaseline;
 49504             },
 49505             fontDescription: {
 49506               get: function fontDescription() {
 49507                 return this._fontDescription;
 49508               },
 49509               set: function fontDescription(value) {
 49510                 somewhatImplemented('ElementFormat.fontDescription');
 49511                 this._fontDescription = value;
 49513             },
 49514             digitCase: {
 49515               get: function digitCase() {
 49516                 return this._digitCase;
 49517               },
 49518               set: function digitCase(digitCaseType) {
 49519                 somewhatImplemented('ElementFormat.digitCase');
 49520                 this._digitCase = digitCaseType;
 49522             },
 49523             digitWidth: {
 49524               get: function digitWidth() {
 49525                 return this._digitWidth;
 49526               },
 49527               set: function digitWidth(digitWidthType) {
 49528                 somewhatImplemented('ElementFormat.digitWidth');
 49529                 this._digitWidth = digitWidthType;
 49531             },
 49532             ligatureLevel: {
 49533               get: function ligatureLevel() {
 49534                 return this._ligatureLevel;
 49535               },
 49536               set: function ligatureLevel(ligatureLevelType) {
 49537                 somewhatImplemented('ElementFormat.ligatureLevel');
 49538                 this._ligatureLevel = ligatureLevelType;
 49540             },
 49541             fontSize: {
 49542               get: function fontSize() {
 49543                 return this._fontSize;
 49544               },
 49545               set: function fontSize(value) {
 49546                 somewhatImplemented('ElementFormat.fontSize');
 49547                 this._fontSize = value;
 49549             },
 49550             kerning: {
 49551               get: function kerning() {
 49552                 return this._kerning;
 49553               },
 49554               set: function kerning(value) {
 49555                 somewhatImplemented('ElementFormat.kerning');
 49556                 this._kerning = value;
 49558             },
 49559             locale: {
 49560               get: function locale() {
 49561                 return this._locale;
 49562               },
 49563               set: function locale(value) {
 49564                 somewhatImplemented('ElementFormat.locale');
 49565                 this._locale = value;
 49567             },
 49568             textRotation: {
 49569               get: function textRotation() {
 49570                 return this._textRotation;
 49571               },
 49572               set: function textRotation(value) {
 49573                 somewhatImplemented('ElementFormat.textRotation');
 49574                 this._textRotation = value;
 49576             },
 49577             trackingRight: {
 49578               get: function trackingRight() {
 49579                 return this._trackingRight;
 49580               },
 49581               set: function trackingRight(value) {
 49582                 somewhatImplemented('ElementFormat.trackingRight');
 49583                 this._trackingRight = value;
 49585             },
 49586             trackingLeft: {
 49587               get: function trackingLeft() {
 49588                 return this._trackingLeft;
 49589               },
 49590               set: function trackingLeft(value) {
 49591                 somewhatImplemented('ElementFormat.trackingLeft');
 49592                 this._trackingLeft = value;
 49594             },
 49595             typographicCase: {
 49596               get: function typographicCase() {
 49597                 return this._typographicCase;
 49598               },
 49599               set: function typographicCase(typographicCaseType) {
 49600                 somewhatImplemented('ElementFormat.typographicCase');
 49601                 this._typographicCase = typographicCaseType;
 49603             },
 49604             locked: {
 49605               get: function locked() {
 49606                 notImplemented('ElementFormat.locked');
 49607                 return this._locked;
 49608               },
 49609               set: function locked(value) {
 49610                 notImplemented('ElementFormat.locked');
 49611                 this._locked = value;
 49617     };
 49618   }.call(this);
 49619 var FontDescriptionDefinition = function () {
 49620     return {
 49621       __class__: 'flash.text.engine.FontDescription',
 49622       initialize: function () {
 49623       },
 49624       __glue__: {
 49625         native: {
 49626           static: {
 49627             isFontCompatible: function isFontCompatible(fontName, fontWeight, fontPosture) {
 49628               notImplemented('FontDescription.isFontCompatible');
 49629             },
 49630             isDeviceFontCompatible: function isDeviceFontCompatible(fontName, fontWeight, fontPosture) {
 49631               notImplemented('FontDescription.isDeviceFontCompatible');
 49633           },
 49634           instance: {
 49635             renderingMode: {
 49636               get: function renderingMode() {
 49637                 return this._renderingMode;
 49638               },
 49639               set: function renderingMode(value) {
 49640                 somewhatImplemented('FontDescription.renderingMode');
 49641                 this._renderingMode = value;
 49643             },
 49644             fontLookup: {
 49645               get: function fontLookup() {
 49646                 return this._fontLookup;
 49647               },
 49648               set: function fontLookup(value) {
 49649                 somewhatImplemented('FontDescription.fontLookup');
 49650                 this._fontLookup = value;
 49652             },
 49653             fontName: {
 49654               get: function fontName() {
 49655                 return this._fontName;
 49656               },
 49657               set: function fontName(value) {
 49658                 somewhatImplemented('FontDescription.fontName');
 49659                 this._fontName = value;
 49661             },
 49662             fontPosture: {
 49663               get: function fontPosture() {
 49664                 return this._fontPosture;
 49665               },
 49666               set: function fontPosture(value) {
 49667                 somewhatImplemented('FontDescription.fontPosture');
 49668                 this._fontPosture = value;
 49670             },
 49671             fontWeight: {
 49672               get: function fontWeight() {
 49673                 return this._fontWeight;
 49674               },
 49675               set: function fontWeight(value) {
 49676                 somewhatImplemented('FontDescription.fontWeight');
 49677                 this._fontWeight = value;
 49679             },
 49680             cffHinting: {
 49681               get: function cffHinting() {
 49682                 return this._cffHinting;
 49683               },
 49684               set: function cffHinting(value) {
 49685                 somewhatImplemented('FontDescription.cffHinting');
 49686                 this._cffHinting = value;
 49688             },
 49689             locked: {
 49690               get: function locked() {
 49691                 notImplemented('FontDescription.locked');
 49692                 return this._locked;
 49693               },
 49694               set: function locked(value) {
 49695                 notImplemented('FontDescription.locked');
 49696                 this._locked = value;
 49700         },
 49701         script: {
 49702           static: {},
 49703           instance: {}
 49706     };
 49707   }.call(this);
 49708 var GroupElementDefinition = function () {
 49709     return {
 49710       __class__: 'flash.text.engine.GroupElement',
 49711       initialize: function () {
 49712       },
 49713       __glue__: {
 49714         native: {
 49715           static: {},
 49716           instance: {
 49717             getElementAt: function getElementAt(index) {
 49718               notImplemented('GroupElement.getElementAt');
 49719             },
 49720             setElements: function setElements(value) {
 49721               somewhatImplemented('GroupElement.setElements');
 49722               this._elements = value;
 49723             },
 49724             groupElements: function groupElements(beginIndex, endIndex) {
 49725               notImplemented('GroupElement.groupElements');
 49726             },
 49727             ungroupElements: function ungroupElements(groupIndex) {
 49728               notImplemented('GroupElement.ungroupElements');
 49729             },
 49730             mergeTextElements: function mergeTextElements(beginIndex, endIndex) {
 49731               notImplemented('GroupElement.mergeTextElements');
 49732             },
 49733             splitTextElement: function splitTextElement(elementIndex, splitIndex) {
 49734               notImplemented('GroupElement.splitTextElement');
 49735             },
 49736             replaceElements: function replaceElements(beginIndex, endIndex, newElements) {
 49737               notImplemented('GroupElement.replaceElements');
 49738             },
 49739             getElementAtCharIndex: function getElementAtCharIndex(charIndex) {
 49740               notImplemented('GroupElement.getElementAtCharIndex');
 49741             },
 49742             elementCount: {
 49743               get: function elementCount() {
 49744                 notImplemented('GroupElement.elementCount');
 49745                 return this._elementCount;
 49751     };
 49752   }.call(this);
 49753 var SpaceJustifierDefinition = function () {
 49754     return {
 49755       __class__: 'flash.text.engine.SpaceJustifier',
 49756       initialize: function () {
 49757         this._letterSpacing = false;
 49758         this._optimumSpacing = 1;
 49759         this._minimumSpacing = 0.5;
 49760         this._maximumSpacing = 1.5;
 49761       },
 49762       __glue__: {
 49763         native: {
 49764           static: {},
 49765           instance: {
 49766             cloneSpacing: function cloneSpacing(justifier) {
 49767               somewhatImplemented('SpaceJustifier.cloneSpacing');
 49768               justifier._optimumSpacing = this._optimumSpacing;
 49769               justifier._minimumSpacing = this._minimumSpacing;
 49770               justifier._maximumSpacing = this._maximumSpacing;
 49771             },
 49772             letterSpacing: {
 49773               get: function letterSpacing() {
 49774                 return this._letterSpacing;
 49775               },
 49776               set: function letterSpacing(value) {
 49777                 somewhatImplemented('SpaceJustifier.letterSpacing');
 49778                 this._letterSpacing = value;
 49780             },
 49781             minimumSpacing: {
 49782               get: function minimumSpacing() {
 49783                 return this._minimumSpacing;
 49784               },
 49785               set: function minimumSpacing(value) {
 49786                 somewhatImplemented('SpaceJustifier.minimumSpacing');
 49787                 this._minimumSpacing = value;
 49789             },
 49790             optimumSpacing: {
 49791               get: function optimumSpacing() {
 49792                 return this._optimumSpacing;
 49793               },
 49794               set: function optimumSpacing(value) {
 49795                 somewhatImplemented('SpaceJustifier.optimumSpacing');
 49796                 this._optimumSpacing = value;
 49798             },
 49799             maximumSpacing: {
 49800               get: function maximumSpacing() {
 49801                 return this._maximumSpacing;
 49802               },
 49803               set: function maximumSpacing(value) {
 49804                 somewhatImplemented('SpaceJustifier.maximumSpacing');
 49805                 this._maximumSpacing = value;
 49811     };
 49812   }.call(this);
 49813 var TextBlockDefinition = function () {
 49814     return {
 49815       __class__: 'flash.text.engine.TextBlock',
 49816       initialize: function () {
 49817         this._firstLine = null;
 49818         this._lastLine = null;
 49819       },
 49820       __glue__: {
 49821         native: {
 49822           static: {},
 49823           instance: {
 49824             getTextJustifier: function getTextJustifier() {
 49825               return this._textJustifier;
 49826             },
 49827             setTextJustifier: function setTextJustifier(value) {
 49828               somewhatImplemented('TextBlock.setTextJustifier');
 49829               this._textJustifier = value;
 49830             },
 49831             getTabStops: function getTabStops() {
 49832               return this._tabStops;
 49833             },
 49834             setTabStops: function setTabStops(value) {
 49835               somewhatImplemented('TextBlock.setTabStops');
 49836               this._tabStops = value;
 49837             },
 49838             findNextAtomBoundary: function findNextAtomBoundary(afterCharIndex) {
 49839               notImplemented('TextBlock.findNextAtomBoundary');
 49840             },
 49841             findPreviousAtomBoundary: function findPreviousAtomBoundary(beforeCharIndex) {
 49842               notImplemented('TextBlock.findPreviousAtomBoundary');
 49843             },
 49844             findNextWordBoundary: function findNextWordBoundary(afterCharIndex) {
 49845               notImplemented('TextBlock.findNextWordBoundary');
 49846             },
 49847             findPreviousWordBoundary: function findPreviousWordBoundary(beforeCharIndex) {
 49848               notImplemented('TextBlock.findPreviousWordBoundary');
 49849             },
 49850             getTextLineAtCharIndex: function getTextLineAtCharIndex(charIndex) {
 49851               notImplemented('TextBlock.getTextLineAtCharIndex');
 49852             },
 49853             DoCreateTextLine: function DoCreateTextLine(previousLine, width, lineOffset, fitSomething, reuseLine) {
 49854               somewhatImplemented('TextBlock.DoCreateTextLine');
 49855               if (previousLine) {
 49856                 return null;
 49858               var textLine = new flash.text.engine.TextLine();
 49859               textLine._textBlock = this;
 49860               textLine._specifiedWidth = width;
 49861               textLine._rawTextLength = 0;
 49862               textLine._textWidth = 0;
 49863               textLine._textHeight = 0;
 49864               textLine._ascent = 0;
 49865               textLine._descent = 0;
 49866               textLine._unjustifiedTextWidth = 0;
 49867               textLine._validity = 'valid';
 49868               textLine._previousLine = null;
 49869               textLine._nextLine = null;
 49870               this._firstLine = textLine;
 49871               this._lastLine = textLine;
 49872               return textLine;
 49873             },
 49874             releaseLineCreationData: function releaseLineCreationData() {
 49875               notImplemented('TextBlock.releaseLineCreationData');
 49876             },
 49877             releaseLines: function releaseLines(firstLine, lastLine) {
 49878               notImplemented('TextBlock.releaseLines');
 49879             },
 49880             dump: function dump() {
 49881               notImplemented('TextBlock.dump');
 49882             },
 49883             applyNonLinearFontScaling: {
 49884               get: function applyNonLinearFontScaling() {
 49885                 return this._applyNonLinearFontScaling;
 49886               },
 49887               set: function applyNonLinearFontScaling(value) {
 49888                 somewhatImplemented('TextBlock.applyNonLinearFontScaling');
 49889                 this._applyNonLinearFontScaling = value;
 49891             },
 49892             baselineFontDescription: {
 49893               get: function baselineFontDescription() {
 49894                 return this._baselineFontDescription;
 49895               },
 49896               set: function baselineFontDescription(value) {
 49897                 somewhatImplemented('TextBlock.baselineFontDescription');
 49898                 this._baselineFontDescription = value;
 49900             },
 49901             baselineFontSize: {
 49902               get: function baselineFontSize() {
 49903                 return this._baselineFontSize;
 49904               },
 49905               set: function baselineFontSize(value) {
 49906                 somewhatImplemented('TextBlock.baselineFontSize');
 49907                 this._baselineFontSize = value;
 49909             },
 49910             baselineZero: {
 49911               get: function baselineZero() {
 49912                 return this._baselineZero;
 49913               },
 49914               set: function baselineZero(value) {
 49915                 somewhatImplemented('TextBlock.baselineZero');
 49916                 this._baselineZero = value;
 49918             },
 49919             content: {
 49920               get: function content() {
 49921                 return this._content;
 49922               },
 49923               set: function content(value) {
 49924                 somewhatImplemented('TextBlock.content');
 49925                 this._content = value;
 49927             },
 49928             bidiLevel: {
 49929               get: function bidiLevel() {
 49930                 return this._bidiLevel;
 49931               },
 49932               set: function bidiLevel(value) {
 49933                 somewhatImplemented('TextBlock.bidiLevel');
 49934                 this._bidiLevel = value;
 49936             },
 49937             firstInvalidLine: {
 49938               get: function firstInvalidLine() {
 49939                 notImplemented('TextBlock.firstInvalidLine');
 49940                 return this._firstInvalidLine;
 49942             },
 49943             firstLine: {
 49944               get: function firstLine() {
 49945                 somewhatImplemented('TextBlock.firstLine');
 49946                 return this._firstLine;
 49948             },
 49949             lastLine: {
 49950               get: function lastLine() {
 49951                 somewhatImplemented('TextBlock.lastLine');
 49952                 return this._lastLine;
 49954             },
 49955             textLineCreationResult: {
 49956               get: function textLineCreationResult() {
 49957                 notImplemented('TextBlock.textLineCreationResult');
 49958                 return this._textLineCreationResult;
 49960             },
 49961             lineRotation: {
 49962               get: function lineRotation() {
 49963                 return this._lineRotation;
 49964               },
 49965               set: function lineRotation(value) {
 49966                 somewhatImplemented('TextBlock.lineRotation');
 49967                 this._lineRotation = value;
 49973     };
 49974   }.call(this);
 49975 var TextElementDefinition = function () {
 49976     return {
 49977       __class__: 'flash.text.engine.TextElement',
 49978       initialize: function () {
 49979       },
 49980       __glue__: {
 49981         native: {
 49982           static: {},
 49983           instance: {
 49984             replaceText: function replaceText(beginIndex, endIndex, newText) {
 49985               somewhatImplemented('TextElement.replaceText');
 49986               var text = this._text || '';
 49987               this._text = text.slice(0, beginIndex) + newText + text.slice(endIndex);
 49988             },
 49989             text: {
 49990               set: function text(value) {
 49991                 somewhatImplemented('TextElement.text');
 49992                 this._text = value;
 49998     };
 49999   }.call(this);
 50000 var TextJustifierDefinition = function () {
 50001     return {
 50002       __class__: 'flash.text.engine.TextJustifier',
 50003       initialize: function () {
 50004         this._locale = null;
 50005         this._lineJustification = null;
 50006       },
 50007       __glue__: {
 50008         native: {
 50009           static: {},
 50010           instance: {
 50011             setLocale: function setLocale(value) {
 50012               somewhatImplemented('TextJustifier.setLocale');
 50013               this._locale = value;
 50014             },
 50015             locale: {
 50016               get: function locale() {
 50017                 return this._locale;
 50019             },
 50020             lineJustification: {
 50021               get: function lineJustification() {
 50022                 return this._lineJustification;
 50023               },
 50024               set: function lineJustification(value) {
 50025                 somewhatImplemented('TextJustifier.lineJustification');
 50026                 this._lineJustification = value;
 50032     };
 50033   }.call(this);
 50034 var TextLineDefinition = function () {
 50035     return {
 50036       __class__: 'flash.text.engine.TextLine',
 50037       initialize: function () {
 50038       },
 50039       __glue__: {
 50040         native: {
 50041           static: {},
 50042           instance: {
 50043             getAtomIndexAtPoint: function getAtomIndexAtPoint(stageX, stageY) {
 50044               notImplemented('TextLine.getAtomIndexAtPoint');
 50045             },
 50046             getAtomIndexAtCharIndex: function getAtomIndexAtCharIndex(charIndex) {
 50047               notImplemented('TextLine.getAtomIndexAtCharIndex');
 50048             },
 50049             getAtomBounds: function getAtomBounds(atomIndex) {
 50050               notImplemented('TextLine.getAtomBounds');
 50051             },
 50052             getAtomBidiLevel: function getAtomBidiLevel(atomIndex) {
 50053               notImplemented('TextLine.getAtomBidiLevel');
 50054             },
 50055             getAtomTextRotation: function getAtomTextRotation(atomIndex) {
 50056               notImplemented('TextLine.getAtomTextRotation');
 50057             },
 50058             getAtomTextBlockBeginIndex: function getAtomTextBlockBeginIndex(atomIndex) {
 50059               notImplemented('TextLine.getAtomTextBlockBeginIndex');
 50060             },
 50061             getAtomTextBlockEndIndex: function getAtomTextBlockEndIndex(atomIndex) {
 50062               notImplemented('TextLine.getAtomTextBlockEndIndex');
 50063             },
 50064             getAtomCenter: function getAtomCenter(atomIndex) {
 50065               notImplemented('TextLine.getAtomCenter');
 50066             },
 50067             getAtomWordBoundaryOnLeft: function getAtomWordBoundaryOnLeft(atomIndex) {
 50068               notImplemented('TextLine.getAtomWordBoundaryOnLeft');
 50069             },
 50070             getAtomGraphic: function getAtomGraphic(atomIndex) {
 50071               notImplemented('TextLine.getAtomGraphic');
 50072             },
 50073             getBaselinePosition: function getBaselinePosition(baseline) {
 50074               notImplemented('TextLine.getBaselinePosition');
 50075             },
 50076             dump: function dump() {
 50077               notImplemented('TextLine.dump');
 50078             },
 50079             textBlock: {
 50080               get: function textBlock() {
 50081                 notImplemented('TextLine.textBlock');
 50082                 return this._textBlock;
 50084             },
 50085             hasGraphicElement: {
 50086               get: function hasGraphicElement() {
 50087                 notImplemented('TextLine.hasGraphicElement');
 50088                 return this._hasGraphicElement;
 50090             },
 50091             hasTabs: {
 50092               get: function hasTabs() {
 50093                 notImplemented('TextLine.hasTabs');
 50094                 return this._hasTabs;
 50096             },
 50097             nextLine: {
 50098               get: function nextLine() {
 50099                 somewhatImplemented('TextLine.nextLine');
 50100                 return this._nextLine;
 50102             },
 50103             previousLine: {
 50104               get: function previousLine() {
 50105                 somewhatImplemented('TextLine.previousLine');
 50106                 return this._previousLine;
 50108             },
 50109             ascent: {
 50110               get: function ascent() {
 50111                 somewhatImplemented('TextLine.ascent');
 50112                 return this._ascent;
 50114             },
 50115             descent: {
 50116               get: function descent() {
 50117                 somewhatImplemented('TextLine.descent');
 50118                 return this._descent;
 50120             },
 50121             textHeight: {
 50122               get: function textHeight() {
 50123                 somewhatImplemented('TextLine.textHeight');
 50124                 return this._textHeight;
 50126             },
 50127             textWidth: {
 50128               get: function textWidth() {
 50129                 somewhatImplemented('TextLine.textWidth');
 50130                 return this._textWidth;
 50132             },
 50133             totalAscent: {
 50134               get: function totalAscent() {
 50135                 notImplemented('TextLine.totalAscent');
 50136                 return this._totalAscent;
 50138             },
 50139             totalDescent: {
 50140               get: function totalDescent() {
 50141                 notImplemented('TextLine.totalDescent');
 50142                 return this._totalDescent;
 50144             },
 50145             totalHeight: {
 50146               get: function totalHeight() {
 50147                 notImplemented('TextLine.totalHeight');
 50148                 return this._totalHeight;
 50150             },
 50151             textBlockBeginIndex: {
 50152               get: function textBlockBeginIndex() {
 50153                 notImplemented('TextLine.textBlockBeginIndex');
 50154                 return this._textBlockBeginIndex;
 50156             },
 50157             rawTextLength: {
 50158               get: function rawTextLength() {
 50159                 somewhatImplemented('TextLine.rawTextLength');
 50160                 return this._rawTextLength;
 50162             },
 50163             specifiedWidth: {
 50164               get: function specifiedWidth() {
 50165                 somewhatImplemented('TextLine.specifiedWidth');
 50166                 return this._specifiedWidth;
 50168             },
 50169             unjustifiedTextWidth: {
 50170               get: function unjustifiedTextWidth() {
 50171                 somewhatImplemented('TextLine.unjustifiedTextWidth');
 50172                 return this._unjustifiedTextWidth;
 50174             },
 50175             validity: {
 50176               get: function validity() {
 50177                 return this._validity;
 50178               },
 50179               set: function validity(value) {
 50180                 somewhatImplemented('TextLine.validity');
 50181                 this._validity = value;
 50183             },
 50184             atomCount: {
 50185               get: function atomCount() {
 50186                 notImplemented('TextLine.atomCount');
 50187                 return this._atomCount;
 50189             },
 50190             mirrorRegions: {
 50191               get: function mirrorRegions() {
 50192                 notImplemented('TextLine.mirrorRegions');
 50193                 return this._mirrorRegions;
 50199     };
 50200   }.call(this);
 50202   var ContextMenuDefinition = function () {
 50203       return {
 50204         __class__: 'flash.ui.ContextMenu',
 50205         initialize: function () {
 50206         },
 50207         __glue__: {
 50208           native: {
 50209             static: {
 50210               _checkSupported: function _checkSupported() {
 50211                 notImplemented('ContextMenu._checkSupported');
 50213             },
 50214             instance: {
 50215               cloneLinkAndClipboardProperties: function cloneLinkAndClipboardProperties(c) {
 50216                 notImplemented('ContextMenu.cloneLinkAndClipboardProperties');
 50217               },
 50218               builtInItems: {
 50219                 get: function builtInItems() {
 50220                   somewhatImplemented('ContextMenu.builtInItems');
 50221                   return this._builtInItems;
 50222                 },
 50223                 set: function builtInItems(value) {
 50224                   somewhatImplemented('ContextMenu.builtInItems');
 50225                   this._builtInItems = value;
 50227               },
 50228               customItems: {
 50229                 get: function customItems() {
 50230                   somewhatImplemented('ContextMenu.customItems');
 50231                   return this._customItems;
 50232                 },
 50233                 set: function customItems(value) {
 50234                   somewhatImplemented('ContextMenu.customItems');
 50235                   this._customItems = value;
 50237               },
 50238               link: {
 50239                 get: function link() {
 50240                   notImplemented('ContextMenu.link');
 50241                   return this._link;
 50242                 },
 50243                 set: function link(value) {
 50244                   notImplemented('ContextMenu.link');
 50245                   this._link = value;
 50247               },
 50248               clipboardMenu: {
 50249                 get: function clipboardMenu() {
 50250                   notImplemented('ContextMenu.clipboardMenu');
 50251                   return this._clipboardMenu;
 50252                 },
 50253                 set: function clipboardMenu(value) {
 50254                   notImplemented('ContextMenu.clipboardMenu');
 50255                   this._clipboardMenu = value;
 50257               },
 50258               clipboardItems: {
 50259                 get: function clipboardItems() {
 50260                   notImplemented('ContextMenu.clipboardItems');
 50261                   return this._clipboardItems;
 50262                 },
 50263                 set: function clipboardItems(value) {
 50264                   notImplemented('ContextMenu.clipboardItems');
 50265                   this._clipboardItems = value;
 50271       };
 50272     }.call(this);
 50274 var ContextMenuItemDefinition = function () {
 50275     return {
 50276       __class__: 'flash.ui.ContextMenuItem',
 50277       initialize: function () {
 50278       },
 50279       __glue__: {
 50280         native: {
 50281           static: {},
 50282           instance: {
 50283             caption: {
 50284               get: function caption() {
 50285                 somewhatImplemented('ContextMenuItem.caption');
 50286                 return this._caption;
 50287               },
 50288               set: function caption(value) {
 50289                 somewhatImplemented('ContextMenuItem.caption');
 50290                 this._caption = value;
 50292             },
 50293             separatorBefore: {
 50294               get: function separatorBefore() {
 50295                 somewhatImplemented('ContextMenuItem.separatorBefore');
 50296                 return this._separatorBefore;
 50297               },
 50298               set: function separatorBefore(value) {
 50299                 somewhatImplemented('ContextMenuItem.separatorBefore');
 50300                 this._separatorBefore = value;
 50302             },
 50303             visible: {
 50304               get: function visible() {
 50305                 somewhatImplemented('ContextMenuItem.visible');
 50306                 return this._visible;
 50307               },
 50308               set: function visible(value) {
 50309                 somewhatImplemented('ContextMenuItem.visible');
 50310                 this._visible = value;
 50316     };
 50317   }.call(this);
 50318 var ShumwayKeyboardListener = {
 50319     _lastKeyCode: 0,
 50320     _captureKeyPress: false,
 50321     _charCodeMap: [],
 50322     focus: null,
 50323     handleEvent: function (domEvt) {
 50324       var keyCode = domEvt.keyCode;
 50325       if (domEvt.type === 'keydown') {
 50326         this._lastKeyCode = keyCode;
 50327         this._captureKeyPress = keyCode === 8 || keyCode === 9 || keyCode === 13 || keyCode === 32 || keyCode >= 48 && keyCode <= 90 || keyCode > 145;
 50328         if (this._captureKeyPress) {
 50329           return;
 50331         this._charCodeMap[keyCode] = 0;
 50332       } else if (domEvt.type === 'keypress') {
 50333         if (this._captureKeyPress) {
 50334           keyCode = this._lastKeyCode;
 50335           this._charCodeMap[keyCode] = domEvt.charCode;
 50336         } else {
 50337           return;
 50340       if (this.focus) {
 50341         this.focus._dispatchEvent(new flash.events.KeyboardEvent(domEvt.type === 'keyup' ? 'keyUp' : 'keyDown', true, false, domEvt.type === 'keyup' ? this._charCodeMap[keyCode] : domEvt.charCode, domEvt.type === 'keyup' ? domEvt.keyCode : this._lastKeyCode, domEvt.keyLocation, domEvt.ctrlKey, domEvt.altKey, domEvt.shiftKey));
 50344   };
 50345 window.addEventListener('keydown', ShumwayKeyboardListener);
 50346 window.addEventListener('keypress', ShumwayKeyboardListener);
 50347 window.addEventListener('keyup', ShumwayKeyboardListener);
 50348 var KeyboardDefinition = function () {
 50349     var def = {
 50350         get capsLock() {
 50351           return false;
 50352         },
 50353         get hasVirtualKeyboard() {
 50354           return false;
 50355         },
 50356         get numLock() {
 50357           return false;
 50358         },
 50359         get physicalKeyboardType() {
 50360           return 'alphanumeric';
 50361         },
 50362         get isAccessible() {
 50363           return true;
 50365       };
 50366     var desc = Object.getOwnPropertyDescriptor;
 50367     def.__glue__ = {
 50368       script: {
 50369         static: scriptProperties('public', [
 50370           'A',
 50371           'ALTERNATE',
 50372           'AUDIO',
 50373           'B',
 50374           'BACK',
 50375           'BACKQUOTE',
 50376           'BACKSLASH',
 50377           'BACKSPACE',
 50378           'BLUE',
 50379           'C',
 50380           'CAPS_LOCK',
 50381           'CHANNEL_DOWN',
 50382           'CHANNEL_UP',
 50383           'COMMA',
 50384           'COMMAND',
 50385           'CONTROL',
 50386           'D',
 50387           'DELETE',
 50388           'DOWN',
 50389           'DVR',
 50390           'E',
 50391           'END',
 50392           'ENTER',
 50393           'EQUAL',
 50394           'ESCAPE',
 50395           'EXIT',
 50396           'F',
 50397           'F1',
 50398           'F10',
 50399           'F11',
 50400           'F12',
 50401           'F13',
 50402           'F14',
 50403           'F15',
 50404           'F2',
 50405           'F3',
 50406           'F4',
 50407           'F5',
 50408           'F6',
 50409           'F7',
 50410           'F8',
 50411           'F9',
 50412           'FAST_FORWARD',
 50413           'G',
 50414           'GREEN',
 50415           'GUIDE',
 50416           'H',
 50417           'HELP',
 50418           'HOME',
 50419           'I',
 50420           'INFO',
 50421           'INPUT',
 50422           'INSERT',
 50423           'J',
 50424           'K',
 50425           'KEYNAME_BEGIN',
 50426           'KEYNAME_BREAK',
 50427           'KEYNAME_CLEARDISPLAY',
 50428           'KEYNAME_CLEARLINE',
 50429           'KEYNAME_DELETE',
 50430           'KEYNAME_DELETECHAR',
 50431           'KEYNAME_DELETELINE',
 50432           'KEYNAME_DOWNARROW',
 50433           'KEYNAME_END',
 50434           'KEYNAME_EXECUTE',
 50435           'KEYNAME_F1',
 50436           'KEYNAME_F10',
 50437           'KEYNAME_F11',
 50438           'KEYNAME_F12',
 50439           'KEYNAME_F13',
 50440           'KEYNAME_F14',
 50441           'KEYNAME_F15',
 50442           'KEYNAME_F16',
 50443           'KEYNAME_F17',
 50444           'KEYNAME_F18',
 50445           'KEYNAME_F19',
 50446           'KEYNAME_F2',
 50447           'KEYNAME_F20',
 50448           'KEYNAME_F21',
 50449           'KEYNAME_F22',
 50450           'KEYNAME_F23',
 50451           'KEYNAME_F24',
 50452           'KEYNAME_F25',
 50453           'KEYNAME_F26',
 50454           'KEYNAME_F27',
 50455           'KEYNAME_F28',
 50456           'KEYNAME_F29',
 50457           'KEYNAME_F3',
 50458           'KEYNAME_F30',
 50459           'KEYNAME_F31',
 50460           'KEYNAME_F32',
 50461           'KEYNAME_F33',
 50462           'KEYNAME_F34',
 50463           'KEYNAME_F35',
 50464           'KEYNAME_F4',
 50465           'KEYNAME_F5',
 50466           'KEYNAME_F6',
 50467           'KEYNAME_F7',
 50468           'KEYNAME_F8',
 50469           'KEYNAME_F9',
 50470           'KEYNAME_FIND',
 50471           'KEYNAME_HELP',
 50472           'KEYNAME_HOME',
 50473           'KEYNAME_INSERT',
 50474           'KEYNAME_INSERTCHAR',
 50475           'KEYNAME_INSERTLINE',
 50476           'KEYNAME_LEFTARROW',
 50477           'KEYNAME_MENU',
 50478           'KEYNAME_MODESWITCH',
 50479           'KEYNAME_NEXT',
 50480           'KEYNAME_PAGEDOWN',
 50481           'KEYNAME_PAGEUP',
 50482           'KEYNAME_PAUSE',
 50483           'KEYNAME_PREV',
 50484           'KEYNAME_PRINT',
 50485           'KEYNAME_PRINTSCREEN',
 50486           'KEYNAME_REDO',
 50487           'KEYNAME_RESET',
 50488           'KEYNAME_RIGHTARROW',
 50489           'KEYNAME_SCROLLLOCK',
 50490           'KEYNAME_SELECT',
 50491           'KEYNAME_STOP',
 50492           'KEYNAME_SYSREQ',
 50493           'KEYNAME_SYSTEM',
 50494           'KEYNAME_UNDO',
 50495           'KEYNAME_UPARROW',
 50496           'KEYNAME_USER',
 50497           'L',
 50498           'LAST',
 50499           'LEFT',
 50500           'LEFTBRACKET',
 50501           'LIVE',
 50502           'M',
 50503           'MASTER_SHELL',
 50504           'MENU',
 50505           'MINUS',
 50506           'N',
 50507           'NEXT',
 50508           'NUMBER_0',
 50509           'NUMBER_1',
 50510           'NUMBER_2',
 50511           'NUMBER_3',
 50512           'NUMBER_4',
 50513           'NUMBER_5',
 50514           'NUMBER_6',
 50515           'NUMBER_7',
 50516           'NUMBER_8',
 50517           'NUMBER_9',
 50518           'NUMPAD',
 50519           'NUMPAD_0',
 50520           'NUMPAD_1',
 50521           'NUMPAD_2',
 50522           'NUMPAD_3',
 50523           'NUMPAD_4',
 50524           'NUMPAD_5',
 50525           'NUMPAD_6',
 50526           'NUMPAD_7',
 50527           'NUMPAD_8',
 50528           'NUMPAD_9',
 50529           'NUMPAD_ADD',
 50530           'NUMPAD_DECIMAL',
 50531           'NUMPAD_DIVIDE',
 50532           'NUMPAD_ENTER',
 50533           'NUMPAD_MULTIPLY',
 50534           'NUMPAD_SUBTRACT',
 50535           'O',
 50536           'P',
 50537           'PAGE_DOWN',
 50538           'PAGE_UP',
 50539           'PAUSE',
 50540           'PERIOD',
 50541           'PLAY',
 50542           'PREVIOUS',
 50543           'Q',
 50544           'QUOTE',
 50545           'R',
 50546           'RECORD',
 50547           'RED',
 50548           'REWIND',
 50549           'RIGHT',
 50550           'RIGHTBRACKET',
 50551           'S',
 50552           'SEARCH',
 50553           'SEMICOLON',
 50554           'SETUP',
 50555           'SHIFT',
 50556           'SKIP_BACKWARD',
 50557           'SKIP_FORWARD',
 50558           'SLASH',
 50559           'SPACE',
 50560           'STOP',
 50561           'STRING_BEGIN',
 50562           'STRING_BREAK',
 50563           'STRING_CLEARDISPLAY',
 50564           'STRING_CLEARLINE',
 50565           'STRING_DELETE',
 50566           'STRING_DELETECHAR',
 50567           'STRING_DELETELINE',
 50568           'STRING_DOWNARROW',
 50569           'STRING_END',
 50570           'STRING_EXECUTE',
 50571           'STRING_F1',
 50572           'STRING_F10',
 50573           'STRING_F11',
 50574           'STRING_F12',
 50575           'STRING_F13',
 50576           'STRING_F14',
 50577           'STRING_F15',
 50578           'STRING_F16',
 50579           'STRING_F17',
 50580           'STRING_F18',
 50581           'STRING_F19',
 50582           'STRING_F2',
 50583           'STRING_F20',
 50584           'STRING_F21',
 50585           'STRING_F22',
 50586           'STRING_F23',
 50587           'STRING_F24',
 50588           'STRING_F25',
 50589           'STRING_F26',
 50590           'STRING_F27',
 50591           'STRING_F28',
 50592           'STRING_F29',
 50593           'STRING_F3',
 50594           'STRING_F30',
 50595           'STRING_F31',
 50596           'STRING_F32',
 50597           'STRING_F33',
 50598           'STRING_F34',
 50599           'STRING_F35',
 50600           'STRING_F4',
 50601           'STRING_F5',
 50602           'STRING_F6',
 50603           'STRING_F7',
 50604           'STRING_F8',
 50605           'STRING_F9',
 50606           'STRING_FIND',
 50607           'STRING_HELP',
 50608           'STRING_HOME',
 50609           'STRING_INSERT',
 50610           'STRING_INSERTCHAR',
 50611           'STRING_INSERTLINE',
 50612           'STRING_LEFTARROW',
 50613           'STRING_MENU',
 50614           'STRING_MODESWITCH',
 50615           'STRING_NEXT',
 50616           'STRING_PAGEDOWN',
 50617           'STRING_PAGEUP',
 50618           'STRING_PAUSE',
 50619           'STRING_PREV',
 50620           'STRING_PRINT',
 50621           'STRING_PRINTSCREEN',
 50622           'STRING_REDO',
 50623           'STRING_RESET',
 50624           'STRING_RIGHTARROW',
 50625           'STRING_SCROLLLOCK',
 50626           'STRING_SELECT',
 50627           'STRING_STOP',
 50628           'STRING_SYSREQ',
 50629           'STRING_SYSTEM',
 50630           'STRING_UNDO',
 50631           'STRING_UPARROW',
 50632           'STRING_USER',
 50633           'SUBTITLE',
 50634           'T',
 50635           'TAB',
 50636           'U',
 50637           'UP',
 50638           'V',
 50639           'VOD',
 50640           'W',
 50641           'X',
 50642           'Y',
 50643           'YELLOW',
 50644           'Z',
 50645           'CharCodeStrings'
 50646         ])
 50647       },
 50648       native: {
 50649         instance: {
 50650           capsLock: desc(def, 'capsLock'),
 50651           hasVirtualKeyboard: desc(def, 'hasVirtualKeyboard'),
 50652           numLock: desc(def, 'numLock'),
 50653           physicalKeyboardType: desc(def, 'physicalKeyboardType'),
 50654           isAccessible: desc(def, 'isAccessible')
 50657     };
 50658     return def;
 50659   }.call(this);
 50660 var MouseDefinition = function () {
 50661     var def = {
 50662         __class__: 'flash.ui.Mouse'
 50663       };
 50664     function hide() {
 50666     function show() {
 50668     function registerCursor() {
 50669       notImplemented();
 50671     function unregisterCursor() {
 50672       notImplemented();
 50674     def.__glue__ = {
 50675       native: {
 50676         static: {
 50677           cursor: {
 50678             get: function () {
 50679               return 'auto';
 50680             },
 50681             set: function () {
 50682               notImplemented();
 50684           },
 50685           supportsCursor: {
 50686             get: function () {
 50687               return true;
 50689           },
 50690           supportsNativeCursor: {
 50691             get: function () {
 50692               return true;
 50694           },
 50695           hide: hide,
 50696           show: show,
 50697           registerCursor: registerCursor,
 50698           unregisterCursor: unregisterCursor
 50701     };
 50702     return def;
 50703   }.call(this);
 50704 var MouseCursorDataDefinition = function () {
 50705     return {
 50706       __class__: 'flash.ui.MouseCursorData',
 50707       initialize: function () {
 50708       },
 50709       __glue__: {
 50710         native: {
 50711           static: {},
 50712           instance: {
 50713             data: {
 50714               get: function data() {
 50715                 notImplemented('MouseCursorData.data');
 50716                 return this._data;
 50717               },
 50718               set: function data(data) {
 50719                 notImplemented('MouseCursorData.data');
 50720                 this._data = data;
 50722             },
 50723             hotSpot: {
 50724               get: function hotSpot() {
 50725                 notImplemented('MouseCursorData.hotSpot');
 50726                 return this._hotSpot;
 50727               },
 50728               set: function hotSpot(data) {
 50729                 notImplemented('MouseCursorData.hotSpot');
 50730                 this._hotSpot = data;
 50732             },
 50733             frameRate: {
 50734               get: function frameRate() {
 50735                 notImplemented('MouseCursorData.frameRate');
 50736                 return this._frameRate;
 50737               },
 50738               set: function frameRate(data) {
 50739                 notImplemented('MouseCursorData.frameRate');
 50740                 this._frameRate = data;
 50746     };
 50747   }.call(this);
 50749   var DictionaryDefinition = function () {
 50750       return {
 50751         __class__: 'flash.utils.Dictionary',
 50752         initialize: function () {
 50753         },
 50754         __glue__: {
 50755           native: {
 50756             static: {},
 50757             instance: {
 50758               init: function init(weakKeys) {
 50759                 notImplemented('Dictionary.init');
 50764       };
 50765     }.call(this);
 50767 var TimerDefinition = function () {
 50768     var def = {
 50769         __class__: 'flash.utils.Timer',
 50770         initialize: function () {
 50771           this._running = false;
 50773       };
 50774     def.__glue__ = {
 50775       native: {
 50776         instance: {
 50777           running: {
 50778             get: function () {
 50779               return this._running;
 50781           },
 50782           _start: function (delay, closure) {
 50783             this._running = true;
 50784             this.interval = setInterval(closure, delay);
 50785           },
 50786           stop: function () {
 50787             this._running = false;
 50788             clearInterval(this.interval);
 50789           },
 50790           _tick: function () {
 50791             if (!this._running) {
 50792               return;
 50794             this._dispatchEvent(new flash.events.TimerEvent('timer', true, false));
 50798     };
 50799     return def;
 50800   }.call(this);
 50802   var AccessibilityDefinition = function () {
 50803       return {
 50804         __class__: 'flash.accessibility.Accessibility',
 50805         initialize: function () {
 50806         },
 50807         __glue__: {
 50808           native: {
 50809             static: {
 50810               sendEvent: function sendEvent(source, childID, eventType, nonHTML) {
 50811                 notImplemented('Accessibility.sendEvent');
 50812               },
 50813               updateProperties: function updateProperties() {
 50814                 notImplemented('Accessibility.updateProperties');
 50815               },
 50816               active: {
 50817                 get: function active() {
 50818                   somewhatImplemented('Accessibility.active');
 50819                   return false;
 50822             },
 50823             instance: {}
 50826       };
 50827     }.call(this);
 50830   var AS2ButtonDefinition = function () {
 50831       var def = {
 50832           __class__: 'avm1lib.AS2Button',
 50833           initialize: function () {
 50835         };
 50836       var desc = Object.getOwnPropertyDescriptor;
 50837       def.__glue__ = {
 50838         native: {
 50839           instance: {
 50840             _as3Object: {
 50841               get: function () {
 50842                 return this.$nativeObject;
 50844             },
 50845             _init: function init(nativeButton) {
 50846               Object.defineProperty(this, '$nativeObject', {
 50847                 value: nativeButton
 50848               });
 50849               nativeButton.$as2Object = this;
 50850               initDefaultListeners(this);
 50853         },
 50854         script: {
 50855           instance: Glue.ALL
 50857       };
 50858       return def;
 50859     }.call(this);
 50861 var AS2GlobalsDefinition = function () {
 50862     var def = {
 50863         __class__: 'avm1lib.AS2Globals',
 50864         initialize: function () {
 50865           flash.text.TextFormat.prototype.asDefinePublicProperty('getTextExtent', {
 50866             value: TextFormatDefinition.as2GetTextExtent,
 50867             writable: false,
 50868             enumerable: false,
 50869             configurable: false
 50870           });
 50872       };
 50873     def.__glue__ = {
 50874       native: {
 50875         instance: {
 50876           ASSetPropFlags: function ASSetPropFlags(obj, children, flags, allowFalse) {
 50877           },
 50878           _addToPendingScripts: function _addToPendingScripts(subject, fn, args) {
 50879             AS2Context.instance.addToPendingScripts(function () {
 50880               fn.apply(subject, args);
 50881             });
 50882           },
 50883           _setLevel: function _setLevel(level, loader) {
 50884             AS2Context.instance.stage._as2SetLevel(level, loader);
 50885           },
 50886           trace: function (expression) {
 50887             var trace = avm2.applicationDomain.getProperty(Multiname.fromSimpleName('trace'), true, true);
 50888             trace(expression);
 50890         },
 50891         static: {
 50892           _addInternalClasses: function _addInternalClasses(proto) {
 50893             proto.asSetPublicProperty('Object', Stubs.Object);
 50894             proto.asSetPublicProperty('Function', Stubs.Function);
 50895             proto.asSetPublicProperty('Array', Stubs.Array);
 50896             proto.asSetPublicProperty('Number', Stubs.Number);
 50897             proto.asSetPublicProperty('Math', avm2.systemDomain.getClass('Math'));
 50898             proto.asSetPublicProperty('Boolean', Stubs.Boolean);
 50899             proto.asSetPublicProperty('Date', Stubs.Date);
 50900             proto.asSetPublicProperty('RegExp', Stubs.RegExp);
 50901             proto.asSetPublicProperty('String', Stubs.String);
 50904       },
 50905       script: {
 50906         instance: Glue.ALL
 50908     };
 50909     return def;
 50910   }.call(this);
 50911 var AS2MovieClipDefinition = function () {
 50912     var def = {
 50913         __class__: 'avm1lib.AS2MovieClip',
 50914         initialize: function () {
 50915         },
 50916         _insertChildAtDepth: function _insertChildAtDepth(mc, depth) {
 50917           return this.$nativeObject._insertChildAtDepth(mc, depth);
 50918         },
 50919         _duplicate: function _duplicate(name, depth, initObject) {
 50920           return this.$nativeObject._duplicate(name, depth, initObject);
 50921         },
 50922         _constructSymbol: function constructSymbol(symbolId, name) {
 50923           var theClass = AS2Context.instance.classes && AS2Context.instance.classes[symbolId];
 50924           var symbolProps = AS2Context.instance.assets[symbolId];
 50925           var symbolClass = flash.display.MovieClip.class;
 50926           var mc = symbolClass.createAsSymbol(symbolProps);
 50927           mc._avm1SymbolClass = theClass;
 50928           symbolClass.instanceConstructor.call(mc);
 50929           this.$nativeObject.addChild(mc);
 50930           return mc;
 50931         },
 50932         _gotoLabel: function (label) {
 50933           this.$nativeObject.gotoLabel(label);
 50934         },
 50935         _callFrame: function callFrame(frame) {
 50936           this.$nativeObject._callFrame(frame);
 50937         },
 50938         init: function init(nativeMovieClip) {
 50939           if (!nativeMovieClip) {
 50940             return;
 50942           Object.defineProperty(this, '$nativeObject', {
 50943             value: nativeMovieClip
 50944           });
 50945           nativeMovieClip.$as2Object = this;
 50946           initDefaultListeners(this);
 50948       };
 50949     var desc = Object.getOwnPropertyDescriptor;
 50950     def.__glue__ = {
 50951       native: {
 50952         instance: {
 50953           _as3Object: {
 50954             get: function () {
 50955               return this.$nativeObject;
 50957           },
 50958           _init: def.init,
 50959           _insertChildAtDepth: def._insertChildAtDepth,
 50960           _duplicate: def._duplicate,
 50961           _constructSymbol: def._constructSymbol,
 50962           _callFrame: def._callFrame,
 50963           _gotoLabel: def._gotoLabel
 50965       },
 50966       script: {
 50967         instance: Glue.ALL
 50969     };
 50970     return def;
 50971   }.call(this);
 50972 var AS2MovieClipLoaderDefinition = function () {
 50973     var def = {
 50974         __class__: 'avm1lib.AS2MovieClipLoader',
 50975         initialize: function () {
 50976         },
 50977         get _bytesLoaded() {
 50978           return this.$nativeObject._contentLoaderInfo._bytesLoaded;
 50980       };
 50981     var desc = Object.getOwnPropertyDescriptor;
 50982     def.__glue__ = {
 50983       native: {
 50984         instance: {
 50985           $nativeObject: {
 50986             get: function () {
 50987               return this.$nativeObject;
 50989           },
 50990           _bytesLoaded: desc(def, '_bytesLoaded')
 50992       },
 50993       script: {
 50994         instance: Glue.ALL
 50996     };
 50997     return def;
 50998   }.call(this);
 50999 var AS2TextFieldDefinition = function () {
 51000     var def = {
 51001         __class__: 'avm1lib.AS2TextField',
 51002         initialize: function () {
 51003           this._variable = '';
 51005       };
 51006     def.__glue__ = {
 51007       native: {
 51008         instance: {
 51009           variable: {
 51010             get: function () {
 51011               return this._variable;
 51012             },
 51013             set: function (name) {
 51014               if (name === this._variable) {
 51015                 return;
 51017               this._variable = name;
 51018               var instance = this.$nativeObject;
 51019               var hasPath = name.indexOf('.') >= 0 || name.indexOf(':') >= 0;
 51020               var clip;
 51021               if (hasPath) {
 51022                 var targetPath = name.split(/[.:\/]/g);
 51023                 name = targetPath.pop();
 51024                 if (targetPath[0] == '_root' || targetPath[0] === '') {
 51025                   clip = instance.root._getAS2Object();
 51026                   targetPath.shift();
 51027                   if (targetPath[0] === '') {
 51028                     targetPath.shift();
 51030                 } else {
 51031                   clip = instance._parent._getAS2Object();
 51033                 while (targetPath.length > 0) {
 51034                   var childName = targetPath.shift();
 51035                   clip = clip.asGetPublicProperty(childName) || clip[childName];
 51036                   if (!clip) {
 51037                     throw new Error('Cannot find ' + childName + ' variable');
 51040               } else {
 51041                 clip = instance._parent._getAS2Object();
 51043               if (!clip.asHasProperty(undefined, name, 0)) {
 51044                 clip.asSetPublicProperty(name, instance.text);
 51046               instance._addEventListener('advanceFrame', function () {
 51047                 instance.text = '' + clip.asGetPublicProperty(name);
 51048               });
 51050           },
 51051           _as3Object: {
 51052             get: function () {
 51053               return this.$nativeObject;
 51055           },
 51056           _init: function init(nativeTextField) {
 51057             Object.defineProperty(this, '$nativeObject', {
 51058               value: nativeTextField
 51059             });
 51060             nativeTextField.$as2Object = this;
 51061             initDefaultListeners(this);
 51064       },
 51065       script: {
 51066         instance: Glue.ALL
 51068     };
 51069     return def;
 51070   }.call(this);
 51071 var AS2UtilsDefinition = function () {
 51072     var def = {
 51073         __class__: 'avm1lib.AS2Utils',
 51074         initialize: function () {
 51076       };
 51077     function installObjectMethods() {
 51078       var c = Stubs.Object, p = c.asGetPublicProperty('prototype');
 51079       c.asSetPublicProperty('registerClass', function registerClass(name, theClass) {
 51080         var classes = AS2Context.instance.classes || (AS2Context.instance.classes = {});
 51081         classes[name] = theClass;
 51082       });
 51083       p.asDefinePublicProperty('addProperty', {
 51084         value: function addProperty(name, getter, setter) {
 51085           if (typeof name !== 'string' || name === '') {
 51086             return false;
 51088           if (typeof getter !== 'function') {
 51089             return false;
 51091           if (typeof setter !== 'function' && setter !== null) {
 51092             return false;
 51094           this.asDefinePublicProperty(name, {
 51095             get: getter,
 51096             set: setter || undefined,
 51097             configurable: true,
 51098             enumerable: true
 51099           });
 51100           return true;
 51101         },
 51102         writable: false,
 51103         enumerable: false,
 51104         configurable: false
 51105       });
 51107     def.__glue__ = {
 51108       native: {
 51109         static: {
 51110           getAS2Object: function (nativeObject) {
 51111             return nativeObject && nativeObject._getAS2Object ? nativeObject._getAS2Object() : null;
 51112           },
 51113           addProperty: function (obj, propertyName, getter, setter, enumerable) {
 51114             obj.asDefinePublicProperty(propertyName, {
 51115               get: getter,
 51116               set: setter || undefined,
 51117               enumerable: enumerable,
 51118               configurable: true
 51119             });
 51120           },
 51121           resolveTarget: function (target_mc) {
 51122             return AS2Context.instance.resolveTarget(target_mc);
 51123           },
 51124           resolveLevel: function (level) {
 51125             return AS2Context.instance.resolveLevel(level);
 51126           },
 51127           currentStage: {
 51128             get: function () {
 51129               return AS2Context.instance.stage;
 51131           },
 51132           _installObjectMethods: installObjectMethods
 51135     };
 51136     return def;
 51137   }.call(this);
 51138 function initDefaultListeners(thisArg) {
 51139   var defaultListeners = thisArg.asGetPublicProperty('$defaultListeners');
 51140   if (!defaultListeners) {
 51141     return;
 51143   for (var i = 0; i < defaultListeners.length; i++) {
 51144     var p = defaultListeners[i];
 51145     p.asGetPublicProperty('setter').call(thisArg, p.value);
 51148 function bindNativeClassDefinition(nativeName, definition) {
 51149   natives[nativeName] = function (domain, scope, instanceConstructor, baseClass) {
 51150     var c = new Class(undefined, instanceConstructor, ApplicationDomain.coerceCallable);
 51151     c.extend(baseClass);
 51152     c.linkNatives(definition);
 51153     return c;
 51154   };
 51156 var Stubs = new function () {
 51157     var that = this;
 51158     var definitions = createEmptyObject();
 51159     var DEFAULT_DEFINITION = {
 51160         __glue__: {
 51161           script: {
 51162             instance: Glue.ALL,
 51163             static: Glue.ALL
 51166       };
 51167     this.getClassNames = function () {
 51168       return Object.keys(definitions);
 51169     };
 51170     this.onClassCreated = function (eventType, cls) {
 51171       var classOriginalName = cls.classInfo.instanceInfo.name.getOriginalName();
 51172       if (classOriginalName in definitions) {
 51173         cls.link(definitions[classOriginalName] || DEFAULT_DEFINITION);
 51175     };
 51176     function makeStub(container, classSimpleName, shortName) {
 51177       Object.defineProperty(container, shortName, {
 51178         get: function () {
 51179           var cls = avm2.systemDomain.getClass(classSimpleName);
 51180           true;
 51181           Object.defineProperty(container, shortName, {
 51182             value: cls.instanceConstructor,
 51183             writable: false
 51184           });
 51185           return container[shortName];
 51186         },
 51187         configurable: true
 51188       });
 51191       'Boolean',
 51192       'Date',
 51193       'String',
 51194       'Function',
 51195       'Object',
 51196       'Number',
 51197       'Math',
 51198       'Array',
 51199       'RegExp'
 51200     ].forEach(function (classSimpleName) {
 51201       makeStub(that, classSimpleName, classSimpleName);
 51202     });
 51204       'Error',
 51205       'DefinitionError',
 51206       'EvalError',
 51207       'RangeError',
 51208       'ReferenceError',
 51209       'SecurityError',
 51210       'SyntaxError',
 51211       'TypeError',
 51212       'URIError',
 51213       'VerifyError',
 51214       'UninitializedError',
 51215       'ArgumentError'
 51216     ].forEach(function (classSimpleName) {
 51217       makeStub(that, classSimpleName, classSimpleName);
 51218     });
 51219     function M(classSimpleName, nativeName, definition) {
 51220       return {
 51221         classSimpleName: classSimpleName,
 51222         nativeName: nativeName,
 51223         definition: definition
 51224       };
 51227       M('flash.display.DisplayObject', 'DisplayObjectClass', DisplayObjectDefinition),
 51228       M('flash.display.InteractiveObject', 'InteractiveObjectClass', InteractiveObjectDefinition),
 51229       M('flash.display.DisplayObjectContainer', 'ContainerClass', DisplayObjectContainerDefinition),
 51230       M('flash.display.Sprite', 'SpriteClass', SpriteDefinition),
 51231       M('flash.display.MovieClip', 'MovieClipClass', MovieClipDefinition),
 51232       M('flash.display.Shape', 'ShapeClass', ShapeDefinition),
 51233       M('flash.display.Bitmap', 'BitmapClass', BitmapDefinition),
 51234       M('flash.display.BitmapData', 'BitmapDataClass', BitmapDataDefinition),
 51235       M('flash.display.Stage', 'StageClass', StageDefinition),
 51236       M('flash.display.Loader', 'LoaderClass', LoaderDefinition),
 51237       M('flash.display.LoaderInfo', 'LoaderInfoClass', LoaderInfoDefinition),
 51238       M('flash.display.Graphics', 'GraphicsClass', GraphicsDefinition),
 51239       M('flash.display.SimpleButton', 'SimpleButtonClass', SimpleButtonDefinition),
 51240       M('flash.display.MorphShape', 'MorphShapeClass', MorphShapeDefinition),
 51241       M('flash.display.NativeMenu', 'MenuClass', NativeMenuDefinition),
 51242       M('flash.display.NativeMenuItem', 'MenuItemClass', NativeMenuItemDefinition),
 51243       M('flash.display.FrameLabel', 'FrameLabelClass', FrameLabelDefinition),
 51244       M('flash.display.Scene'),
 51245       M('flash.display.BlendMode'),
 51246       M('flash.display.Shader', 'ShaderClass', ShaderDefinition),
 51247       M('flash.display.ShaderData', 'ShaderDataClass', ShaderDataDefinition),
 51248       M('flash.filters.BevelFilter', 'BevelFilterClass', BevelFilterDefinition),
 51249       M('flash.filters.BitmapFilter', 'BitmapFilterClass', BitmapFilterDefinition),
 51250       M('flash.filters.BlurFilter', 'BlurFilterClass', BlurFilterDefinition),
 51251       M('flash.filters.ColorMatrixFilter', 'ColorMatrixFilterClass', ColorMatrixFilterDefinition),
 51252       M('flash.filters.ConvolutionFilter', 'ConvolutionFilterClass', ConvolutionFilterDefinition),
 51253       M('flash.filters.DisplacementMapFilter', 'DisplacementMapFilterClass', DisplacementMapFilterDefinition),
 51254       M('flash.filters.DropShadowFilter', 'DropShadowFilterClass', DropShadowFilterDefinition),
 51255       M('flash.filters.GlowFilter', 'GlowFilterClass', GlowFilterDefinition),
 51256       M('flash.filters.GradientBevelFilter', 'GradientBevelFilterClass', GradientBevelFilterDefinition),
 51257       M('flash.filters.GradientGlowFilter', 'GradientGlowFilterClass', GradientGlowFilterDefinition),
 51258       M('flash.filters.ShaderFilter', 'ShaderFilterClass', ShaderFilterDefinition),
 51259       M('flash.geom.Point', 'PointClass', PointDefinition),
 51260       M('flash.geom.Rectangle', 'RectangleClass', RectangleDefinition),
 51261       M('flash.geom.Matrix', 'MatrixClass', MatrixDefinition),
 51262       M('flash.geom.Matrix3D', 'Matrix3DClass', Matrix3DDefinition),
 51263       M('flash.geom.Vector3D', 'Vector3DClass', Vector3DDefinition),
 51264       M('flash.geom.Transform', 'TransformClass', TransformDefinition),
 51265       M('flash.geom.ColorTransform', 'ColorTransformClass', ColorTransformDefinition),
 51266       M('flash.events.EventDispatcher', 'EventDispatcherClass', EventDispatcherDefinition),
 51267       M('flash.events.Event', 'EventClass', EventDefinition),
 51268       M('flash.events.IOErrorEvent'),
 51269       M('flash.events.NetStatusEvent'),
 51270       M('flash.events.KeyboardEvent', 'KeyboardEventClass', KeyboardEventDefinition),
 51271       M('flash.events.MouseEvent', 'MouseEventClass', MouseEventDefinition),
 51272       M('flash.events.TextEvent', 'TextEventClass', TextEventDefinition),
 51273       M('flash.events.TimerEvent', 'TimerEventClass', TimerEventDefinition),
 51274       M('flash.events.ProgressEvent'),
 51275       M('flash.events.NetStatusEvent'),
 51276       M('flash.external.ExternalInterface', 'ExternalInterfaceClass', ExternalInterfaceDefinition),
 51277       M('flash.ui.ContextMenu', 'ContextMenuClass', ContextMenuDefinition),
 51278       M('flash.ui.ContextMenuItem', 'ContextMenuItemClass', ContextMenuItemDefinition),
 51279       M('flash.ui.Keyboard', 'KeyboardClass', KeyboardDefinition),
 51280       M('flash.ui.Mouse', 'MouseClass', MouseDefinition),
 51281       M('flash.ui.MouseCursorData', 'MouseCursorDataClass', MouseCursorDataDefinition),
 51282       M('flash.text.Font', 'FontClass', FontDefinition),
 51283       M('flash.text.TextField', 'TextFieldClass', TextFieldDefinition),
 51284       M('flash.text.StaticText', 'StaticTextClass', StaticTextDefinition),
 51285       M('flash.text.StyleSheet', 'StyleSheetClass', StyleSheetDefinition),
 51286       M('flash.text.TextFormat', 'TextFormatClass', TextFormatDefinition),
 51287       M('flash.text.TextLineMetrics'),
 51288       M('flash.text.engine.ContentElement', 'ContentElementClass', ContentElementDefinition),
 51289       M('flash.text.engine.ElementFormat', 'ElementFormatClass', ElementFormatDefinition),
 51290       M('flash.text.engine.FontDescription', 'FontDescriptionClass', FontDescriptionDefinition),
 51291       M('flash.text.engine.GroupElement', 'GroupElementClass', GroupElementDefinition),
 51292       M('flash.text.engine.SpaceJustifier', 'SpaceJustifierClass', SpaceJustifierDefinition),
 51293       M('flash.text.engine.TextBlock', 'TextBlockClass', TextBlockDefinition),
 51294       M('flash.text.engine.TextElement', 'TextElementClass', TextElementDefinition),
 51295       M('flash.text.engine.TextJustifier', 'TextJustifierClass', TextJustifierDefinition),
 51296       M('flash.text.engine.TextLine', 'TextLineClass', TextLineDefinition),
 51297       M('flash.media.Sound', 'SoundClass', SoundDefinition),
 51298       M('flash.media.SoundChannel', 'SoundChannelClass', SoundChannelDefinition),
 51299       M('flash.media.SoundMixer', 'SoundMixerClass', SoundMixerDefinition),
 51300       M('flash.media.SoundTransform', 'SoundTransformClass', SoundTransformDefinition),
 51301       M('flash.media.Video', 'VideoClass', VideoDefinition),
 51302       M('flash.media.ID3Info', 'ID3InfoClass', ID3InfoDefinition),
 51303       M('flash.media.Microphone', 'MicrophoneClass', MicrophoneDefinition),
 51304       M('flash.net.FileFilter', 'FileFilterClass', FileFilterDefinition),
 51305       M('flash.net.NetConnection', 'NetConnectionClass', NetConnectionDefinition),
 51306       M('flash.net.NetStream', 'NetStreamClass', NetStreamDefinition),
 51307       M('flash.net.Responder', 'ResponderClass', ResponderDefinition),
 51308       M('flash.net.URLRequest', 'URLRequestClass', URLRequestDefinition),
 51309       M('flash.net.URLStream', 'URLStreamClass', URLStreamDefinition),
 51310       M('flash.net.URLLoader', 'URLLoaderClass', URLLoaderDefinition),
 51311       M('flash.net.SharedObject', 'SharedObjectClass', SharedObjectDefinition),
 51312       M('flash.net.ObjectEncoding', 'ObjectEncodingClass', ObjectEncodingDefinition),
 51313       M('flash.net.LocalConnection', 'LocalConnectionClass', LocalConnectionDefinition),
 51314       M('flash.net.Socket', 'SocketClass', SocketDefinition),
 51315       M('flash.net.URLVariables'),
 51316       M('packageInternal flash.system.FSCommand', 'FSCommandClass', FSCommandDefinition),
 51317       M('flash.system.Capabilities', 'CapabilitiesClass', CapabilitiesDefinition),
 51318       M('flash.system.System', 'SystemClass', SystemDefinition),
 51319       M('flash.system.Security', 'SecurityClass', SecurityDefinition),
 51320       M('flash.system.SecurityDomain', 'SecurityDomainClass', SecurityDomainDefinition),
 51321       M('flash.system.ApplicationDomain', 'ApplicationDomainClass', ApplicationDomainDefinition),
 51322       M('flash.accessibility.Accessibility', 'AccessibilityClass', AccessibilityDefinition),
 51323       M('flash.utils.Timer', 'TimerClass', TimerDefinition),
 51324       M('avm1lib.AS2Utils', 'AS2Utils', AS2UtilsDefinition),
 51325       M('avm1lib.AS2Broadcaster'),
 51326       M('avm1lib.AS2Key'),
 51327       M('avm1lib.AS2Mouse'),
 51328       M('avm1lib.AS2MovieClip', 'AS2MovieClip', AS2MovieClipDefinition),
 51329       M('avm1lib.AS2Button', 'AS2Button', AS2ButtonDefinition),
 51330       M('avm1lib.AS2TextField', 'AS2TextField', AS2TextFieldDefinition),
 51331       M('avm1lib.AS2Stage'),
 51332       M('avm1lib.AS2System'),
 51333       M('avm1lib.AS2Color'),
 51334       M('avm1lib.AS2Globals', 'AS2Globals', AS2GlobalsDefinition),
 51335       M('avm1lib.AS2MovieClipLoader', 'AS2MovieClipLoader', AS2MovieClipLoaderDefinition)
 51336     ].forEach(function (m) {
 51337       var className = Multiname.fromSimpleName(m.classSimpleName);
 51338       var path = className.getOriginalName().split('.');
 51339       var container = this;
 51340       for (var i = 0, j = path.length - 1; i < j; i++) {
 51341         if (!container[path[i]]) {
 51342           container[path[i]] = {};
 51344         container = container[path[i]];
 51346       makeStub(container, m.classSimpleName, path[path.length - 1]);
 51347       if (m.nativeName) {
 51348         bindNativeClassDefinition(m.nativeName, m.definition);
 51350       definitions[className.getOriginalName()] = m.definition;
 51351     });
 51352   }();
 51353 natives['FlashUtilScript::getAliasName'] = function (domain, scope, instanceConstructor, baseClass) {
 51354   return function getAliasName(value) {
 51355     return value.debugName;
 51356   };
 51357 };
 51358 natives['FlashUtilScript::getDefinitionByName'] = natives.getDefinitionByName;
 51359 natives['FlashUtilScript::getTimer'] = function GetTimerMethod(domain, scope, instanceConstructor, baseClass) {
 51360   var start = Date.now();
 51361   return function getTimer() {
 51362     return Date.now() - start;
 51363   };
 51364 };
 51365 natives['FlashUtilScript::escapeMultiByte'] = function EscapeMultiByteMethod(domain, scope, instanceConstructor, baseClass) {
 51366   return escape;
 51367 };
 51368 natives['FlashUtilScript::unescapeMultiByte'] = function UnescapeMultiByteMethod(domain, scope, instanceConstructor, baseClass) {
 51369   return unescape;
 51370 };
 51371 natives['FlashNetScript::navigateToURL'] = function GetNavigateToURLMethod(domain, scope, instanceConstructor, baseClass) {
 51372   return function navigateToURL(request, window_) {
 51373     if (request === null || request === undefined) {
 51374       throwError('TypeError', Errors.NullPointerError, 'request');
 51376     var RequestClass = avm2.systemDomain.getClass('flash.net.URLRequest');
 51377     if (!RequestClass.isInstanceOf(request)) {
 51378       throwError('TypeError', Errors.CheckTypeFailedError, request, 'flash.net.URLRequest');
 51380     var url = request.url;
 51381     if (/^fscommand:/i.test(url)) {
 51382       var fscommand = avm2.applicationDomain.getProperty(Multiname.fromSimpleName('flash.system.fscommand'), true, true);
 51383       fscommand.call(null, url.substring('fscommand:'.length), window_);
 51384       return;
 51386     var targetWindow = window_ || '_parent';
 51387     window.open(FileLoadingService.resolveUrl(url), targetWindow);
 51388   };
 51389 };
 51390 natives['FlashNetScript::sendToURL'] = function GetSendToURLMethod(domain, scope, instanceConstructor, baseClass) {
 51391   return function sendToURL(request) {
 51392     if (request === null || request === undefined) {
 51393       throwError('TypeError', Errors.NullPointerError, 'request');
 51395     var RequestClass = avm2.systemDomain.getClass('flash.net.URLRequest');
 51396     if (!RequestClass.isInstanceOf(request)) {
 51397       throwError('TypeError', Errors.CheckTypeFailedError, request, 'flash.net.URLRequest');
 51399     var session = FileLoadingService.createSession();
 51400     session.onprogress = function () {
 51401     };
 51402     session.open(request);
 51403   };
 51404 };
 51405 natives['Toplevel::registerClassAlias'] = function GetRegisterClassAliasMethod(domain, scope, instance, baseClass) {
 51406   return function registerClassAlias(aliasName, classObject) {
 51407     if (!aliasName) {
 51408       throwError('TypeError', Errors.NullPointerError, 'aliasName');
 51410     if (!classObject) {
 51411       throwError('TypeError', Errors.NullPointerError, 'classObject');
 51413     AMFUtils.aliasesCache.classes.set(classObject, aliasName);
 51414     AMFUtils.aliasesCache.names[aliasName] = classObject;
 51415   };
 51416 };
 51417 natives['Toplevel::getClassByAlias'] = function GetGetClassByAliasMethod(domain, scope, instance, baseClass) {
 51418   return function getClassByAlias(aliasName) {
 51419     if (!aliasName) {
 51420       throwError('TypeError', Errors.NullPointerError, 'aliasName');
 51422     var classObject = AMFUtils.aliasesCache.names[aliasName];
 51423     if (!classObject) {
 51424       throwError('ReferenceError', Errors.ClassNotFoundError, aliasName);
 51426     return classObject;
 51427   };
 51428 };

mercurial