Constant fold CheckTypeInfoFlags on ImplementsDefaultHasInstance
[WebKit-https.git] / Source / JavaScriptCore / bytecode / SpeculatedType.cpp
1 /*
2  * Copyright (C) 2011-2017 Apple Inc. All rights reserved.
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  *
8  * 1.  Redistributions of source code must retain the above copyright
9  *     notice, this list of conditions and the following disclaimer.
10  * 2.  Redistributions in binary form must reproduce the above copyright
11  *     notice, this list of conditions and the following disclaimer in the
12  *     documentation and/or other materials provided with the distribution.
13  * 3.  Neither the name of Apple Inc. ("Apple") nor the names of
14  *     its contributors may be used to endorse or promote products derived
15  *     from this software without specific prior written permission.
16  *
17  * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
18  * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
19  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
20  * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
21  * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
22  * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
23  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
24  * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26  * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27  */
28
29 #include "config.h"
30 #include "SpeculatedType.h"
31
32 #include "DirectArguments.h"
33 #include "JSArray.h"
34 #include "JSBigInt.h"
35 #include "JSBoundFunction.h"
36 #include "JSCInlines.h"
37 #include "JSFunction.h"
38 #include "JSMap.h"
39 #include "JSSet.h"
40 #include "JSWeakMap.h"
41 #include "JSWeakSet.h"
42 #include "ProxyObject.h"
43 #include "RegExpObject.h"
44 #include "ScopedArguments.h"
45 #include "StringObject.h"
46 #include "ValueProfile.h"
47 #include <wtf/CommaPrinter.h>
48 #include <wtf/StringPrintStream.h>
49
50 namespace JSC {
51
52 struct PrettyPrinter {
53     PrettyPrinter(PrintStream& out)
54         : out(out)
55         , separator("|")
56     { }
57     
58     template<typename T>
59     void print(const T& value)
60     {
61         out.print(separator, value);
62     }
63     
64     PrintStream& out;
65     CommaPrinter separator;
66 };
67     
68 void dumpSpeculation(PrintStream& outStream, SpeculatedType value)
69 {
70     StringPrintStream strStream;
71     PrettyPrinter out(outStream);
72     PrettyPrinter strOut(strStream);
73     
74     if (value == SpecNone) {
75         out.print("None");
76         return;
77     }
78     
79     bool isTop = true;
80     
81     if ((value & SpecCell) == SpecCell)
82         strOut.print("Cell");
83     else {
84         if ((value & SpecObject) == SpecObject)
85             strOut.print("Object");
86         else {
87             if (value & SpecCellOther)
88                 strOut.print("OtherCell");
89             else
90                 isTop = false;
91     
92             if (value & SpecObjectOther)
93                 strOut.print("OtherObj");
94             else
95                 isTop = false;
96     
97             if (value & SpecFinalObject)
98                 strOut.print("Final");
99             else
100                 isTop = false;
101
102             if (value & SpecArray)
103                 strOut.print("Array");
104             else
105                 isTop = false;
106     
107             if (value & SpecInt8Array)
108                 strOut.print("Int8Array");
109             else
110                 isTop = false;
111     
112             if (value & SpecInt16Array)
113                 strOut.print("Int16Array");
114             else
115                 isTop = false;
116     
117             if (value & SpecInt32Array)
118                 strOut.print("Int32Array");
119             else
120                 isTop = false;
121     
122             if (value & SpecUint8Array)
123                 strOut.print("Uint8Array");
124             else
125                 isTop = false;
126
127             if (value & SpecUint8ClampedArray)
128                 strOut.print("Uint8ClampedArray");
129             else
130                 isTop = false;
131     
132             if (value & SpecUint16Array)
133                 strOut.print("Uint16Array");
134             else
135                 isTop = false;
136     
137             if (value & SpecUint32Array)
138                 strOut.print("Uint32Array");
139             else
140                 isTop = false;
141     
142             if (value & SpecFloat32Array)
143                 strOut.print("Float32array");
144             else
145                 isTop = false;
146     
147             if (value & SpecFloat64Array)
148                 strOut.print("Float64Array");
149             else
150                 isTop = false;
151     
152             if (value & SpecFunction)
153                 strOut.print("Function");
154             else
155                 isTop = false;
156     
157             if (value & SpecDirectArguments)
158                 strOut.print("DirectArguments");
159             else
160                 isTop = false;
161     
162             if (value & SpecScopedArguments)
163                 strOut.print("ScopedArguments");
164             else
165                 isTop = false;
166     
167             if (value & SpecStringObject)
168                 strOut.print("StringObject");
169             else
170                 isTop = false;
171     
172             if (value & SpecRegExpObject)
173                 strOut.print("RegExpObject");
174             else
175                 isTop = false;
176
177             if (value & SpecMapObject)
178                 strOut.print("MapObject");
179             else
180                 isTop = false;
181
182             if (value & SpecSetObject)
183                 strOut.print("SetObject");
184             else
185                 isTop = false;
186
187             if (value & SpecWeakMapObject)
188                 strOut.print("WeakMapObject");
189             else
190                 isTop = false;
191
192             if (value & SpecWeakSetObject)
193                 strOut.print("WeakSetObject");
194             else
195                 isTop = false;
196
197             if (value & SpecProxyObject)
198                 strOut.print("ProxyObject");
199             else
200                 isTop = false;
201
202             if (value & SpecDerivedArray)
203                 strOut.print("DerivedArray");
204             else
205                 isTop = false;
206         }
207
208         if ((value & SpecString) == SpecString)
209             strOut.print("String");
210         else {
211             if (value & SpecStringIdent)
212                 strOut.print("StringIdent");
213             else
214                 isTop = false;
215             
216             if (value & SpecStringVar)
217                 strOut.print("StringVar");
218             else
219                 isTop = false;
220         }
221
222         if (value & SpecSymbol)
223             strOut.print("Symbol");
224         else
225             isTop = false;
226
227         if (value & SpecBigInt)
228             strOut.print("BigInt");
229         else
230             isTop = false;
231     }
232     
233     if (value == SpecInt32Only)
234         strOut.print("Int32");
235     else {
236         if (value & SpecBoolInt32)
237             strOut.print("BoolInt32");
238         else
239             isTop = false;
240         
241         if (value & SpecNonBoolInt32)
242             strOut.print("NonBoolInt32");
243         else
244             isTop = false;
245     }
246     
247     if (value & SpecInt52Only)
248         strOut.print("Int52");
249         
250     if ((value & SpecBytecodeDouble) == SpecBytecodeDouble)
251         strOut.print("BytecodeDouble");
252     else {
253         if (value & SpecAnyIntAsDouble)
254             strOut.print("AnyIntAsDouble");
255         else
256             isTop = false;
257         
258         if (value & SpecNonIntAsDouble)
259             strOut.print("NonIntAsdouble");
260         else
261             isTop = false;
262         
263         if (value & SpecDoublePureNaN)
264             strOut.print("DoublePureNan");
265         else
266             isTop = false;
267     }
268     
269     if (value & SpecDoubleImpureNaN)
270         out.print("DoubleImpureNan");
271     
272     if (value & SpecBoolean)
273         strOut.print("Bool");
274     else
275         isTop = false;
276     
277     if (value & SpecOther)
278         strOut.print("Other");
279     else
280         isTop = false;
281     
282     if (isTop)
283         out.print("Top");
284     else
285         out.print(strStream.toCString());
286     
287     if (value & SpecEmpty)
288         out.print("Empty");
289 }
290
291 // We don't expose this because we don't want anyone relying on the fact that this method currently
292 // just returns string constants.
293 static const char* speculationToAbbreviatedString(SpeculatedType prediction)
294 {
295     if (isFinalObjectSpeculation(prediction))
296         return "<Final>";
297     if (isArraySpeculation(prediction))
298         return "<Array>";
299     if (isStringIdentSpeculation(prediction))
300         return "<StringIdent>";
301     if (isStringSpeculation(prediction))
302         return "<String>";
303     if (isFunctionSpeculation(prediction))
304         return "<Function>";
305     if (isInt8ArraySpeculation(prediction))
306         return "<Int8array>";
307     if (isInt16ArraySpeculation(prediction))
308         return "<Int16array>";
309     if (isInt32ArraySpeculation(prediction))
310         return "<Int32array>";
311     if (isUint8ArraySpeculation(prediction))
312         return "<Uint8array>";
313     if (isUint16ArraySpeculation(prediction))
314         return "<Uint16array>";
315     if (isUint32ArraySpeculation(prediction))
316         return "<Uint32array>";
317     if (isFloat32ArraySpeculation(prediction))
318         return "<Float32array>";
319     if (isFloat64ArraySpeculation(prediction))
320         return "<Float64array>";
321     if (isDirectArgumentsSpeculation(prediction))
322         return "<DirectArguments>";
323     if (isScopedArgumentsSpeculation(prediction))
324         return "<ScopedArguments>";
325     if (isStringObjectSpeculation(prediction))
326         return "<StringObject>";
327     if (isRegExpObjectSpeculation(prediction))
328         return "<RegExpObject>";
329     if (isStringOrStringObjectSpeculation(prediction))
330         return "<StringOrStringObject>";
331     if (isObjectSpeculation(prediction))
332         return "<Object>";
333     if (isCellSpeculation(prediction))
334         return "<Cell>";
335     if (isBoolInt32Speculation(prediction))
336         return "<BoolInt32>";
337     if (isInt32Speculation(prediction))
338         return "<Int32>";
339     if (isAnyIntAsDoubleSpeculation(prediction))
340         return "<AnyIntAsDouble>";
341     if (isInt52Speculation(prediction))
342         return "<Int52>";
343     if (isAnyIntSpeculation(prediction))
344         return "<AnyInt>";
345     if (isDoubleSpeculation(prediction))
346         return "<Double>";
347     if (isFullNumberSpeculation(prediction))
348         return "<Number>";
349     if (isBooleanSpeculation(prediction))
350         return "<Boolean>";
351     if (isOtherSpeculation(prediction))
352         return "<Other>";
353     if (isMiscSpeculation(prediction))
354         return "<Misc>";
355     return "";
356 }
357
358 void dumpSpeculationAbbreviated(PrintStream& out, SpeculatedType value)
359 {
360     out.print(speculationToAbbreviatedString(value));
361 }
362
363 SpeculatedType speculationFromTypedArrayType(TypedArrayType type)
364 {
365     switch (type) {
366     case TypeInt8:
367         return SpecInt8Array;
368     case TypeInt16:
369         return SpecInt16Array;
370     case TypeInt32:
371         return SpecInt32Array;
372     case TypeUint8:
373         return SpecUint8Array;
374     case TypeUint8Clamped:
375         return SpecUint8ClampedArray;
376     case TypeUint16:
377         return SpecUint16Array;
378     case TypeUint32:
379         return SpecUint32Array;
380     case TypeFloat32:
381         return SpecFloat32Array;
382     case TypeFloat64:
383         return SpecFloat64Array;
384     case NotTypedArray:
385     case TypeDataView:
386         break;
387     }
388     RELEASE_ASSERT_NOT_REACHED();
389     return SpecNone;
390 }
391
392 SpeculatedType speculationFromClassInfo(const ClassInfo* classInfo)
393 {
394     if (classInfo == JSString::info())
395         return SpecString;
396
397     if (classInfo == Symbol::info())
398         return SpecSymbol;
399     
400     if (classInfo == JSBigInt::info())
401         return SpecBigInt;
402
403     if (classInfo == JSFinalObject::info())
404         return SpecFinalObject;
405     
406     if (classInfo == JSArray::info())
407         return SpecArray;
408     
409     if (classInfo == DirectArguments::info())
410         return SpecDirectArguments;
411     
412     if (classInfo == ScopedArguments::info())
413         return SpecScopedArguments;
414     
415     if (classInfo == StringObject::info())
416         return SpecStringObject;
417
418     if (classInfo == RegExpObject::info())
419         return SpecRegExpObject;
420
421     if (classInfo == JSMap::info())
422         return SpecMapObject;
423
424     if (classInfo == JSSet::info())
425         return SpecSetObject;
426
427     if (classInfo == JSWeakMap::info())
428         return SpecWeakMapObject;
429
430     if (classInfo == JSWeakSet::info())
431         return SpecWeakSetObject;
432
433     if (classInfo == ProxyObject::info())
434         return SpecProxyObject;
435     
436     if (classInfo->isSubClassOf(JSFunction::info())) {
437         if (classInfo == JSBoundFunction::info())
438             return SpecFunctionWithNonDefaultHasInstance;
439         return SpecFunctionWithDefaultHasInstance;
440     }
441     
442     if (isTypedView(classInfo->typedArrayStorageType))
443         return speculationFromTypedArrayType(classInfo->typedArrayStorageType);
444
445     if (classInfo->isSubClassOf(JSArray::info()))
446         return SpecDerivedArray;
447     
448     if (classInfo->isSubClassOf(JSObject::info()))
449         return SpecObjectOther;
450     
451     return SpecCellOther;
452 }
453
454 SpeculatedType speculationFromStructure(Structure* structure)
455 {
456     if (structure->typeInfo().type() == StringType)
457         return SpecString;
458     if (structure->typeInfo().type() == SymbolType)
459         return SpecSymbol;
460     if (structure->typeInfo().type() == BigIntType)
461         return SpecBigInt;
462     if (structure->typeInfo().type() == DerivedArrayType)
463         return SpecDerivedArray;
464     return speculationFromClassInfo(structure->classInfo());
465 }
466
467 SpeculatedType speculationFromCell(JSCell* cell)
468 {
469     if (cell->isString()) {
470         JSString* string = jsCast<JSString*>(cell);
471         if (const StringImpl* impl = string->tryGetValueImpl()) {
472             if (impl->isAtomic())
473                 return SpecStringIdent;
474         }
475         return SpecStringVar;
476     }
477     return speculationFromStructure(cell->structure());
478 }
479
480 SpeculatedType speculationFromValue(JSValue value)
481 {
482     if (value.isEmpty())
483         return SpecEmpty;
484     if (value.isInt32()) {
485         if (value.asInt32() & ~1)
486             return SpecNonBoolInt32;
487         return SpecBoolInt32;
488     }
489     if (value.isDouble()) {
490         double number = value.asNumber();
491         if (number != number)
492             return SpecDoublePureNaN;
493         if (value.isAnyInt())
494             return SpecAnyIntAsDouble;
495         return SpecNonIntAsDouble;
496     }
497     if (value.isCell())
498         return speculationFromCell(value.asCell());
499     if (value.isBoolean())
500         return SpecBoolean;
501     ASSERT(value.isUndefinedOrNull());
502     return SpecOther;
503 }
504
505 TypedArrayType typedArrayTypeFromSpeculation(SpeculatedType type)
506 {
507     if (isInt8ArraySpeculation(type))
508         return TypeInt8;
509         
510     if (isInt16ArraySpeculation(type))
511         return TypeInt16;
512         
513     if (isInt32ArraySpeculation(type))
514         return TypeInt32;
515         
516     if (isUint8ArraySpeculation(type))
517         return TypeUint8;
518         
519     if (isUint8ClampedArraySpeculation(type))
520         return TypeUint8Clamped;
521         
522     if (isUint16ArraySpeculation(type))
523         return TypeUint16;
524         
525     if (isUint32ArraySpeculation(type))
526         return TypeUint32;
527         
528     if (isFloat32ArraySpeculation(type))
529         return TypeFloat32;
530         
531     if (isFloat64ArraySpeculation(type))
532         return TypeFloat64;
533     
534     return NotTypedArray;
535 }
536
537 SpeculatedType speculationFromJSType(JSType type)
538 {
539     switch (type) {
540     case StringType:
541         return SpecString;
542     case SymbolType:
543         return SpecSymbol;
544     case BigIntType:
545         return SpecBigInt;
546     case ArrayType:
547         return SpecArray;
548     case DerivedArrayType:
549         return SpecDerivedArray;
550     case RegExpObjectType:
551         return SpecRegExpObject;
552     case ProxyObjectType:
553         return SpecProxyObject;
554     case JSMapType:
555         return SpecMapObject;
556     case JSSetType:
557         return SpecSetObject;
558     case JSWeakMapType:
559         return SpecWeakMapObject;
560     case JSWeakSetType:
561         return SpecWeakSetObject;
562     default:
563         ASSERT_NOT_REACHED();
564     }
565     return SpecNone;
566 }
567
568 SpeculatedType leastUpperBoundOfStrictlyEquivalentSpeculations(SpeculatedType type)
569 {
570     if (type & (SpecAnyInt | SpecAnyIntAsDouble))
571         type |= (SpecAnyInt | SpecAnyIntAsDouble);
572     if (type & SpecString)
573         type |= SpecString;
574     return type;
575 }
576
577 bool valuesCouldBeEqual(SpeculatedType a, SpeculatedType b)
578 {
579     a = leastUpperBoundOfStrictlyEquivalentSpeculations(a);
580     b = leastUpperBoundOfStrictlyEquivalentSpeculations(b);
581     
582     // Anything could be equal to a string.
583     if (a & SpecString)
584         return true;
585     if (b & SpecString)
586         return true;
587     
588     // If both sides are definitely only objects, then equality is fairly sane.
589     if (isObjectSpeculation(a) && isObjectSpeculation(b))
590         return !!(a & b);
591     
592     // If either side could be an object or not, then we could call toString or
593     // valueOf, which could return anything.
594     if (a & SpecObject)
595         return true;
596     if (b & SpecObject)
597         return true;
598     
599     // Neither side is an object or string, so the world is relatively sane.
600     return !!(a & b);
601 }
602
603 SpeculatedType typeOfDoubleSum(SpeculatedType a, SpeculatedType b)
604 {
605     SpeculatedType result = a | b;
606     // Impure NaN could become pure NaN during addition because addition may clear bits.
607     if (result & SpecDoubleImpureNaN)
608         result |= SpecDoublePureNaN;
609     // Values could overflow, or fractions could become integers.
610     if (result & SpecDoubleReal)
611         result |= SpecDoubleReal;
612     return result;
613 }
614
615 SpeculatedType typeOfDoubleDifference(SpeculatedType a, SpeculatedType b)
616 {
617     return typeOfDoubleSum(a, b);
618 }
619
620 SpeculatedType typeOfDoubleProduct(SpeculatedType a, SpeculatedType b)
621 {
622     return typeOfDoubleSum(a, b);
623 }
624
625 static SpeculatedType polluteDouble(SpeculatedType value)
626 {
627     // Impure NaN could become pure NaN because the operation could clear some bits.
628     if (value & SpecDoubleImpureNaN)
629         value |= SpecDoubleNaN;
630     // Values could overflow, fractions could become integers, or an error could produce
631     // PureNaN.
632     if (value & SpecDoubleReal)
633         value |= SpecDoubleReal | SpecDoublePureNaN;
634     return value;
635 }
636
637 SpeculatedType typeOfDoubleQuotient(SpeculatedType a, SpeculatedType b)
638 {
639     return polluteDouble(a | b);
640 }
641
642 SpeculatedType typeOfDoubleMinMax(SpeculatedType a, SpeculatedType b)
643 {
644     SpeculatedType result = a | b;
645     // Impure NaN could become pure NaN during addition because addition may clear bits.
646     if (result & SpecDoubleImpureNaN)
647         result |= SpecDoublePureNaN;
648     return result;
649 }
650
651 SpeculatedType typeOfDoubleNegation(SpeculatedType value)
652 {
653     // Changing bits can make pure NaN impure and vice versa:
654     // 0xefff000000000000 (pure) - 0xffff000000000000 (impure)
655     if (value & SpecDoubleNaN)
656         value |= SpecDoubleNaN;
657     // We could get negative zero, which mixes SpecAnyIntAsDouble and SpecNotIntAsDouble.
658     // We could also overflow a large negative int into something that is no longer
659     // representable as an int.
660     if (value & SpecDoubleReal)
661         value |= SpecDoubleReal;
662     return value;
663 }
664
665 SpeculatedType typeOfDoubleAbs(SpeculatedType value)
666 {
667     return typeOfDoubleNegation(value);
668 }
669
670 SpeculatedType typeOfDoubleRounding(SpeculatedType value)
671 {
672     // Double Pure NaN can becomes impure when converted back from Float.
673     // and vice versa.
674     if (value & SpecDoubleNaN)
675         value |= SpecDoubleNaN;
676     // We might lose bits, which leads to a value becoming integer-representable.
677     if (value & SpecNonIntAsDouble)
678         value |= SpecAnyIntAsDouble;
679     return value;
680 }
681
682 SpeculatedType typeOfDoublePow(SpeculatedType xValue, SpeculatedType yValue)
683 {
684     // Math.pow() always return NaN if the exponent is NaN, unlike std::pow().
685     // We always set a pure NaN in that case.
686     if (yValue & SpecDoubleNaN)
687         xValue |= SpecDoublePureNaN;
688     return polluteDouble(xValue);
689 }
690
691 SpeculatedType typeOfDoubleBinaryOp(SpeculatedType a, SpeculatedType b)
692 {
693     return polluteDouble(a | b);
694 }
695
696 SpeculatedType typeOfDoubleUnaryOp(SpeculatedType value)
697 {
698     return polluteDouble(value);
699 }
700
701 SpeculatedType speculationFromString(const char* speculation)
702 {
703     if (!strncmp(speculation, "SpecNone", strlen("SpecNone")))
704         return SpecNone;
705     if (!strncmp(speculation, "SpecFinalObject", strlen("SpecFinalObject")))
706         return SpecFinalObject;
707     if (!strncmp(speculation, "SpecArray", strlen("SpecArray")))
708         return SpecArray;
709     if (!strncmp(speculation, "SpecFunction", strlen("SpecFunction")))
710         return SpecFunction;
711     if (!strncmp(speculation, "SpecInt8Array", strlen("SpecInt8Array")))
712         return SpecInt8Array;
713     if (!strncmp(speculation, "SpecInt16Array", strlen("SpecInt16Array")))
714         return SpecInt16Array;
715     if (!strncmp(speculation, "SpecInt32Array", strlen("SpecInt32Array")))
716         return SpecInt32Array;
717     if (!strncmp(speculation, "SpecUint8Array", strlen("SpecUint8Array")))
718         return SpecUint8Array;
719     if (!strncmp(speculation, "SpecUint8ClampedArray", strlen("SpecUint8ClampedArray")))
720         return SpecUint8ClampedArray;
721     if (!strncmp(speculation, "SpecUint16Array", strlen("SpecUint16Array")))
722         return SpecUint16Array;
723     if (!strncmp(speculation, "SpecUint32Array", strlen("SpecUint32Array")))
724         return SpecUint32Array;
725     if (!strncmp(speculation, "SpecFloat32Array", strlen("SpecFloat32Array")))
726         return SpecFloat32Array;
727     if (!strncmp(speculation, "SpecFloat64Array", strlen("SpecFloat64Array")))
728         return SpecFloat64Array;
729     if (!strncmp(speculation, "SpecTypedArrayView", strlen("SpecTypedArrayView")))
730         return SpecTypedArrayView;
731     if (!strncmp(speculation, "SpecDirectArguments", strlen("SpecDirectArguments")))
732         return SpecDirectArguments;
733     if (!strncmp(speculation, "SpecScopedArguments", strlen("SpecScopedArguments")))
734         return SpecScopedArguments;
735     if (!strncmp(speculation, "SpecStringObject", strlen("SpecStringObject")))
736         return SpecStringObject;
737     if (!strncmp(speculation, "SpecRegExpObject", strlen("SpecRegExpObject")))
738         return SpecRegExpObject;
739     if (!strncmp(speculation, "SpecMapObject", strlen("SpecMapObject")))
740         return SpecMapObject;
741     if (!strncmp(speculation, "SpecSetObject", strlen("SpecSetObject")))
742         return SpecSetObject;
743     if (!strncmp(speculation, "SpecWeakMapObject", strlen("SpecWeakMapObject")))
744         return SpecWeakMapObject;
745     if (!strncmp(speculation, "SpecWeakSetObject", strlen("SpecWeakSetObject")))
746         return SpecWeakSetObject;
747     if (!strncmp(speculation, "SpecProxyObject", strlen("SpecProxyObject")))
748         return SpecProxyObject;
749     if (!strncmp(speculation, "SpecDerivedArray", strlen("SpecDerivedArray")))
750         return SpecDerivedArray;
751     if (!strncmp(speculation, "SpecObjectOther", strlen("SpecObjectOther")))
752         return SpecObjectOther;
753     if (!strncmp(speculation, "SpecObject", strlen("SpecObject")))
754         return SpecObject;
755     if (!strncmp(speculation, "SpecStringIdent", strlen("SpecStringIdent")))
756         return SpecStringIdent;
757     if (!strncmp(speculation, "SpecStringVar", strlen("SpecStringVar")))
758         return SpecStringVar;
759     if (!strncmp(speculation, "SpecString", strlen("SpecString")))
760         return SpecString;
761     if (!strncmp(speculation, "SpecSymbol", strlen("SpecSymbol")))
762         return SpecSymbol;
763     if (!strncmp(speculation, "SpecBigInt", strlen("SpecBigInt")))
764         return SpecBigInt;
765     if (!strncmp(speculation, "SpecCellOther", strlen("SpecCellOther")))
766         return SpecCellOther;
767     if (!strncmp(speculation, "SpecCell", strlen("SpecCell")))
768         return SpecCell;
769     if (!strncmp(speculation, "SpecBoolInt32", strlen("SpecBoolInt32")))
770         return SpecBoolInt32;
771     if (!strncmp(speculation, "SpecNonBoolInt32", strlen("SpecNonBoolInt32")))
772         return SpecNonBoolInt32;
773     if (!strncmp(speculation, "SpecInt32Only", strlen("SpecInt32Only")))
774         return SpecInt32Only;
775     if (!strncmp(speculation, "SpecInt52Only", strlen("SpecInt52Only")))
776         return SpecInt52Only;
777     if (!strncmp(speculation, "SpecAnyInt", strlen("SpecAnyInt")))
778         return SpecAnyInt;
779     if (!strncmp(speculation, "SpecAnyIntAsDouble", strlen("SpecAnyIntAsDouble")))
780         return SpecAnyIntAsDouble;
781     if (!strncmp(speculation, "SpecNonIntAsDouble", strlen("SpecNonIntAsDouble")))
782         return SpecNonIntAsDouble;
783     if (!strncmp(speculation, "SpecDoubleReal", strlen("SpecDoubleReal")))
784         return SpecDoubleReal;
785     if (!strncmp(speculation, "SpecDoublePureNaN", strlen("SpecDoublePureNaN")))
786         return SpecDoublePureNaN;
787     if (!strncmp(speculation, "SpecDoubleImpureNaN", strlen("SpecDoubleImpureNaN")))
788         return SpecDoubleImpureNaN;
789     if (!strncmp(speculation, "SpecDoubleNaN", strlen("SpecDoubleNaN")))
790         return SpecDoubleNaN;
791     if (!strncmp(speculation, "SpecBytecodeDouble", strlen("SpecBytecodeDouble")))
792         return SpecBytecodeDouble;
793     if (!strncmp(speculation, "SpecFullDouble", strlen("SpecFullDouble")))
794         return SpecFullDouble;
795     if (!strncmp(speculation, "SpecBytecodeRealNumber", strlen("SpecBytecodeRealNumber")))
796         return SpecBytecodeRealNumber;
797     if (!strncmp(speculation, "SpecFullRealNumber", strlen("SpecFullRealNumber")))
798         return SpecFullRealNumber;
799     if (!strncmp(speculation, "SpecBytecodeNumber", strlen("SpecBytecodeNumber")))
800         return SpecBytecodeNumber;
801     if (!strncmp(speculation, "SpecFullNumber", strlen("SpecFullNumber")))
802         return SpecFullNumber;
803     if (!strncmp(speculation, "SpecBoolean", strlen("SpecBoolean")))
804         return SpecBoolean;
805     if (!strncmp(speculation, "SpecOther", strlen("SpecOther")))
806         return SpecOther;
807     if (!strncmp(speculation, "SpecMisc", strlen("SpecMisc")))
808         return SpecMisc;
809     if (!strncmp(speculation, "SpecHeapTop", strlen("SpecHeapTop")))
810         return SpecHeapTop;
811     if (!strncmp(speculation, "SpecPrimitive", strlen("SpecPrimitive")))
812         return SpecPrimitive;
813     if (!strncmp(speculation, "SpecEmpty", strlen("SpecEmpty")))
814         return SpecEmpty;
815     if (!strncmp(speculation, "SpecBytecodeTop", strlen("SpecBytecodeTop")))
816         return SpecBytecodeTop;
817     if (!strncmp(speculation, "SpecFullTop", strlen("SpecFullTop")))
818         return SpecFullTop;
819     if (!strncmp(speculation, "SpecCellCheck", strlen("SpecCellCheck")))
820         return SpecCellCheck;
821     RELEASE_ASSERT_NOT_REACHED();
822 }
823
824 } // namespace JSC
825