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