base.tq 45.3 KB
Newer Older
1 2 3 4
// Copyright 2018 the V8 project authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

5
type Arguments constexpr 'CodeStubArguments*';
6 7 8
type void generates 'void';
type never generates 'void';

9 10 11
type Tagged generates 'TNode<Object>';
type Smi extends Tagged generates 'TNode<Smi>';
type HeapObject extends Tagged generates 'TNode<HeapObject>';
12
type Object = Smi | HeapObject;
13 14
type int32 generates 'TNode<Int32T>' constexpr 'int32_t';
type uint32 generates 'TNode<Uint32T>' constexpr 'uint32_t';
15
type int64 generates 'TNode<Int64T>' constexpr 'int64_t';
16
type intptr generates 'TNode<IntPtrT>' constexpr 'intptr_t';
17
type uintptr generates 'TNode<UintPtrT>' constexpr 'uintptr_t';
18
type float32 generates 'TNode<Float32T>' constexpr 'float';
19 20
type float64 generates 'TNode<Float64T>' constexpr 'double';
type bool generates 'TNode<BoolT>' constexpr 'bool';
21
type string constexpr 'const char*';
22

23
type int31 extends int32 generates 'TNode<Int32T>' constexpr 'int31_t';
24
type RawPtr generates 'TNode<RawPtrT>' constexpr 'void*';
25 26
type AbstractCode extends HeapObject generates 'TNode<AbstractCode>';
type Code extends AbstractCode generates 'TNode<Code>';
27
type JSReceiver extends HeapObject generates 'TNode<JSReceiver>';
28
type Constructor extends JSReceiver generates 'TNode<JSReceiver>';
29
type Context extends HeapObject generates 'TNode<Context>';
30
type NativeContext extends Context generates 'TNode<Context>';
31
type String extends HeapObject generates 'TNode<String>';
32
type Oddball extends HeapObject generates 'TNode<Oddball>';
33
type HeapNumber extends HeapObject generates 'TNode<HeapNumber>';
34
type Number = Smi | HeapNumber;
35
type BigInt extends HeapObject generates 'TNode<BigInt>';
36
type Numeric = Number | BigInt;
37
type Boolean extends Oddball generates 'TNode<Oddball>';
38
type JSProxy extends JSReceiver generates 'TNode<JSProxy>';
39
type JSObject extends JSReceiver generates 'TNode<JSObject>';
40 41 42 43
type JSArgumentsObjectWithLength extends JSObject
    generates 'TNode<JSArgumentsObjectWithLength>';
type JSArray extends JSArgumentsObjectWithLength
    generates 'TNode<JSArray>';
44
transient type FastJSArray extends JSArray
45
    generates 'TNode<JSArray>';
46
transient type FastJSArrayForCopy extends FastJSArray
47
    generates 'TNode<JSArray>';
48 49
type JSFunction extends JSObject generates 'TNode<JSFunction>';
type JSBoundFunction extends JSObject generates 'TNode<JSBoundFunction>';
50
type Callable = JSFunction | JSBoundFunction | JSProxy;
51 52
type Map extends HeapObject generates 'TNode<Map>';
type FixedArrayBase extends HeapObject generates 'TNode<FixedArrayBase>';
53
type FixedArray extends FixedArrayBase generates 'TNode<FixedArray>';
54 55 56 57 58 59
type FixedDoubleArray extends FixedArrayBase
    generates 'TNode<FixedDoubleArray>';
type FixedTypedArrayBase extends FixedArrayBase
    generates 'TNode<FixedTypedArrayBase>';
type FixedTypedArray extends FixedTypedArrayBase
    generates 'TNode<FixedTypedArray>';
60 61
type SloppyArgumentsElements extends FixedArray
    generates 'TNode<FixedArray>';
62 63
type NumberDictionary extends HeapObject
    generates 'TNode<NumberDictionary>';
64

65
type NativeContextSlot generates 'TNode<IntPtrT>' constexpr 'int32_t';
66 67
const ARRAY_JOIN_STACK_INDEX: constexpr NativeContextSlot
    generates 'Context::ARRAY_JOIN_STACK_INDEX';
68 69
extern operator '[]' macro LoadContextElement(
    NativeContext, NativeContextSlot): Object;
70 71
extern operator '[]=' macro StoreContextElement(
    NativeContext, NativeContextSlot, Object): void;
72 73 74 75

extern operator '[]' macro LoadContextElement(Context, intptr): Object;
extern operator '[]' macro LoadContextElement(Context, Smi): Object;

76
type JSArrayBuffer extends JSObject generates 'TNode<JSArrayBuffer>';
77 78 79 80
type JSArrayBufferView extends JSObject
    generates 'TNode<JSArrayBufferView>';
type JSTypedArray extends JSArrayBufferView
    generates 'TNode<JSTypedArray>';
81
type JSDataView extends JSArrayBufferView generates 'TNode<JSDataView>';
82

83
type InstanceType generates 'TNode<Int32T>' constexpr 'InstanceType';
84 85
type ElementsKind generates 'TNode<Int32T>' constexpr 'ElementsKind';
type LanguageMode generates 'TNode<Smi>' constexpr 'LanguageMode';
86 87
type ExtractFixedArrayFlags
    generates 'TNode<Smi>' constexpr 'ExtractFixedArrayFlags';
88
type ParameterMode generates 'TNode<Int32T>' constexpr 'ParameterMode';
89
type RootIndex generates 'TNode<Int32T>' constexpr 'RootIndex';
90 91
type WriteBarrierMode
    generates 'TNode<Int32T>' constexpr 'WriteBarrierMode';
92

93
type MessageTemplate constexpr 'MessageTemplate';
94
type ToIntegerTruncationMode constexpr 'ToIntegerTruncationMode';
95
type AllocationFlags constexpr 'AllocationFlags';
96

97 98
const NO_ELEMENTS: constexpr ElementsKind generates 'NO_ELEMENTS';

99 100 101 102
const PACKED_SMI_ELEMENTS:
    constexpr ElementsKind generates 'PACKED_SMI_ELEMENTS';
const HOLEY_SMI_ELEMENTS:
    constexpr ElementsKind generates 'HOLEY_SMI_ELEMENTS';
103 104
const PACKED_ELEMENTS:
    constexpr ElementsKind generates 'PACKED_ELEMENTS';
105
const HOLEY_ELEMENTS: constexpr ElementsKind generates 'HOLEY_ELEMENTS';
106 107 108 109 110 111
const PACKED_DOUBLE_ELEMENTS:
    constexpr ElementsKind generates 'PACKED_DOUBLE_ELEMENTS';
const HOLEY_DOUBLE_ELEMENTS:
    constexpr ElementsKind generates 'HOLEY_DOUBLE_ELEMENTS';
const DICTIONARY_ELEMENTS:
    constexpr ElementsKind generates 'DICTIONARY_ELEMENTS';
112 113 114

const UINT8_ELEMENTS: constexpr ElementsKind generates 'UINT8_ELEMENTS';
const INT8_ELEMENTS: constexpr ElementsKind generates 'INT8_ELEMENTS';
115 116
const UINT16_ELEMENTS:
    constexpr ElementsKind generates 'UINT16_ELEMENTS';
117
const INT16_ELEMENTS: constexpr ElementsKind generates 'INT16_ELEMENTS';
118 119
const UINT32_ELEMENTS:
    constexpr ElementsKind generates 'UINT32_ELEMENTS';
120
const INT32_ELEMENTS: constexpr ElementsKind generates 'INT32_ELEMENTS';
121 122 123 124
const FLOAT32_ELEMENTS:
    constexpr ElementsKind generates 'FLOAT32_ELEMENTS';
const FLOAT64_ELEMENTS:
    constexpr ElementsKind generates 'FLOAT64_ELEMENTS';
125 126 127 128 129 130
const UINT8_CLAMPED_ELEMENTS:
    constexpr ElementsKind generates 'UINT8_CLAMPED_ELEMENTS';
const BIGUINT64_ELEMENTS:
    constexpr ElementsKind generates 'BIGUINT64_ELEMENTS';
const BIGINT64_ELEMENTS:
    constexpr ElementsKind generates 'BIGINT64_ELEMENTS';
131

132 133 134 135 136 137 138
const kNone: constexpr AllocationFlags generates 'kNone';
const kDoubleAlignment:
    constexpr AllocationFlags generates 'kDoubleAlignment';
const kPretenured: constexpr AllocationFlags generates 'kPretenured';
const kAllowLargeObjectAllocation:
    constexpr AllocationFlags generates 'kAllowLargeObjectAllocation';

139 140 141 142 143 144 145 146 147 148 149 150
type FixedUint8Array extends FixedTypedArray;
type FixedInt8Array extends FixedTypedArray;
type FixedUint16Array extends FixedTypedArray;
type FixedInt16Array extends FixedTypedArray;
type FixedUint32Array extends FixedTypedArray;
type FixedInt32Array extends FixedTypedArray;
type FixedFloat32Array extends FixedTypedArray;
type FixedFloat64Array extends FixedTypedArray;
type FixedUint8ClampedArray extends FixedTypedArray;
type FixedBigUint64Array extends FixedTypedArray;
type FixedBigInt64Array extends FixedTypedArray;

151 152 153 154 155 156 157 158 159 160 161
const kFixedDoubleArrays: constexpr ExtractFixedArrayFlags
    generates 'ExtractFixedArrayFlag::kFixedDoubleArrays';
const kAllFixedArrays: constexpr ExtractFixedArrayFlags
    generates 'ExtractFixedArrayFlag::kAllFixedArrays';
const kFixedArrays: constexpr ExtractFixedArrayFlags
    generates 'ExtractFixedArrayFlag::kFixedArrays';

const kFixedCOWArrayMapRootIndex:
    constexpr RootIndex generates 'RootIndex::kFixedCOWArrayMap';
const kEmptyFixedArrayRootIndex:
    constexpr RootIndex generates 'RootIndex::kEmptyFixedArray';
162 163
const kTheHoleValueRootIndex:
    constexpr RootIndex generates 'RootIndex::kTheHoleValue';
164 165 166 167 168 169 170

const kInvalidArrayLength: constexpr MessageTemplate
    generates 'MessageTemplate::kInvalidArrayLength';
const kCalledNonCallable: constexpr MessageTemplate
    generates 'MessageTemplate::kCalledNonCallable';
const kCalledOnNullOrUndefined: constexpr MessageTemplate
    generates 'MessageTemplate::kCalledOnNullOrUndefined';
171 172
const kInvalidStringLength: constexpr MessageTemplate
    generates 'MessageTemplate::kInvalidStringLength';
173 174

const kMaxSafeInteger: constexpr float64 generates 'kMaxSafeInteger';
175 176 177
const kStringMaxLength: constexpr int31 generates 'String::kMaxLength';
const kFixedArrayMaxLength:
    constexpr int31 generates 'FixedArray::kMaxLength';
178

179 180 181 182 183 184 185 186 187 188 189 190
const kMaxRegularHeapObjectSize: constexpr int31
    generates 'kMaxRegularHeapObjectSize';

const kMaxNewSpaceFixedArrayElements: constexpr int31
    generates 'FixedArray::kMaxRegularLength';
const kSloppyArgumentsArgumentsIndex: constexpr int31
    generates 'SloppyArgumentsElements::kArgumentsIndex';
const kSloppyArgumentsContextIndex: constexpr int31
    generates 'SloppyArgumentsElements::kContextIndex';
const kSloppyArgumentsParameterMapStart: constexpr int31
    generates 'SloppyArgumentsElements::kParameterMapStart';

191 192 193
const kTruncateMinusZero: constexpr ToIntegerTruncationMode
    generates 'ToIntegerTruncationMode::kTruncateMinusZero';

194 195
const kNotTypedArray: constexpr MessageTemplate
    generates 'MessageTemplate::kNotTypedArray';
196 197 198 199 200 201 202 203 204 205
const kDetachedOperation: constexpr MessageTemplate
    generates 'MessageTemplate::kDetachedOperation';
const kBadSortComparisonFunction: constexpr MessageTemplate
    generates 'MessageTemplate::kBadSortComparisonFunction';
const kIncompatibleMethodReceiver: constexpr MessageTemplate
    generates 'MessageTemplate::kIncompatibleMethodReceiver';
const kInvalidDataViewAccessorOffset: constexpr MessageTemplate
    generates 'MessageTemplate::kInvalidDataViewAccessorOffset';
const kStrictReadOnlyProperty: constexpr MessageTemplate
    generates 'MessageTemplate::kStrictReadOnlyProperty';
206

207 208 209 210 211
extern macro TheHoleConstant(): Oddball;
extern macro NullConstant(): Oddball;
extern macro UndefinedConstant(): Oddball;
extern macro TrueConstant(): Boolean;
extern macro FalseConstant(): Boolean;
212 213
extern macro Int32TrueConstant(): bool;
extern macro Int32FalseConstant(): bool;
214
extern macro EmptyStringConstant(): String;
215
extern macro LengthStringConstant(): String;
216 217 218 219 220 221

const Hole: Oddball = TheHoleConstant();
const Null: Oddball = NullConstant();
const Undefined: Oddball = UndefinedConstant();
const True: Boolean = TrueConstant();
const False: Boolean = FalseConstant();
222
const kEmptyString: String = EmptyStringConstant();
223
const kLengthString: String = LengthStringConstant();
224

225 226 227 228 229 230 231
const true: constexpr bool generates 'true';
const false: constexpr bool generates 'false';

const kStrict: constexpr LanguageMode generates 'LanguageMode::kStrict';
const kSloppy: constexpr LanguageMode generates 'LanguageMode::kSloppy';

const SMI_PARAMETERS: constexpr ParameterMode generates 'SMI_PARAMETERS';
232 233
const INTPTR_PARAMETERS:
    constexpr ParameterMode generates 'INTPTR_PARAMETERS';
234

235 236
const SKIP_WRITE_BARRIER:
    constexpr WriteBarrierMode generates 'SKIP_WRITE_BARRIER';
237

238 239
extern macro Is64(): constexpr bool;

240 241
extern macro SelectBooleanConstant(bool): Boolean;

242 243
extern macro Print(constexpr string);
extern macro Print(constexpr string, Object);
244
extern macro Comment(constexpr string);
245 246 247
extern macro Print(Object);
extern macro DebugBreak();
extern macro ToInteger_Inline(Context, Object): Number;
248 249
extern macro ToInteger_Inline(
    Context, Object, constexpr ToIntegerTruncationMode): Number;
250
extern macro ToLength_Inline(Context, Object): Number;
251
extern macro ToNumber_Inline(Context, Object): Number;
252
extern macro ToString_Inline(Context, Object): String;
253 254 255 256 257
extern transitioning macro GetProperty(implicit context: Context)(
    Object, Object): Object;
extern transitioning builtin SetProperty(implicit context: Context)(
    Object, Object, Object);
extern transitioning builtin DeleteProperty(implicit context: Context)(
258
    Object, Object, LanguageMode);
259
extern transitioning builtin HasProperty(implicit context: Context)(
260
    JSReceiver, Object): Boolean;
261
extern transitioning macro HasProperty_Inline(implicit context: Context)(
262
    JSReceiver, Object): Boolean;
263

264 265 266
extern macro ThrowRangeError(Context, constexpr MessageTemplate): never;
extern macro ThrowTypeError(Context, constexpr MessageTemplate): never;
extern macro ThrowTypeError(Context, constexpr MessageTemplate, Object): never;
267 268
extern macro ThrowTypeError(
    Context, constexpr MessageTemplate, Object, Object, Object): never;
269
extern macro ArraySpeciesCreate(Context, Object, Number): JSReceiver;
270
extern macro ArrayCreate(implicit context: Context)(Number): JSArray;
271
extern macro InternalArrayCreate(Context, Number): JSArray;
272 273
extern macro EnsureArrayPushable(Map): ElementsKind
    labels Bailout;
274
extern macro EnsureArrayLengthWritable(Map) labels Bailout;
275 276 277 278 279 280 281
// TODO: Reduce duplication once varargs are supported in macros.
extern macro Construct(implicit context: Context)(
    Constructor, Object): JSReceiver;
extern macro Construct(implicit context: Context)(
    Constructor, Object, Object): JSReceiver;
extern macro Construct(implicit context: Context)(
    Constructor, Object, Object, Object): JSReceiver;
282

283
extern builtin ToObject(Context, Object): JSReceiver;
284
extern macro ToObject_Inline(Context, Object): JSReceiver;
285
extern macro IsNullOrUndefined(Object): bool;
286 287 288
extern macro IsTheHole(Object): bool;
extern macro IsString(HeapObject): bool;
extern builtin ToString(Context, Object): String;
289

290 291 292 293
extern transitioning runtime NormalizeElements(Context, JSObject);
extern transitioning runtime TransitionElementsKindWithKind(
    Context, JSObject, Smi);
extern transitioning runtime CreateDataProperty(implicit context: Context)(
294
    JSReceiver, Object, Object);
295

296 297 298
extern macro LoadRoot(constexpr RootIndex): Object;
extern macro StoreRoot(constexpr RootIndex, Object): Object;
extern macro LoadAndUntagToWord32Root(constexpr RootIndex): int32;
299

300
extern runtime StringEqual(Context, String, String): Oddball;
301 302 303
extern builtin StringLessThan(Context, String, String): Boolean;

extern macro StrictEqual(Object, Object): Boolean;
304
extern macro SmiLexicographicCompare(Smi, Smi): Smi;
305
extern runtime ReThrow(Context, Object): never;
306

307 308 309 310
extern operator '<' macro Int32LessThan(int32, int32): bool;
extern operator '>' macro Int32GreaterThan(int32, int32): bool;
extern operator '<=' macro Int32LessThanOrEqual(int32, int32): bool;
extern operator '>=' macro Int32GreaterThanOrEqual(int32, int32): bool;
311

312 313 314 315 316 317
extern operator '==' macro SmiEqual(Smi, Smi): bool;
extern operator '!=' macro SmiNotEqual(Smi, Smi): bool;
extern operator '<' macro SmiLessThan(Smi, Smi): bool;
extern operator '<=' macro SmiLessThanOrEqual(Smi, Smi): bool;
extern operator '>' macro SmiGreaterThan(Smi, Smi): bool;
extern operator '>=' macro SmiGreaterThanOrEqual(Smi, Smi): bool;
318

319 320
extern operator '==' macro ElementsKindEqual(
    constexpr ElementsKind, constexpr ElementsKind): constexpr bool;
321
extern operator '==' macro ElementsKindEqual(ElementsKind, ElementsKind): bool;
322 323 324 325
operator '!=' macro ElementsKindNotEqual(
    k1: ElementsKind, k2: ElementsKind): bool {
  return !ElementsKindEqual(k1, k2);
}
326 327 328 329
extern macro IsElementsKindLessThanOrEqual(
    ElementsKind, constexpr ElementsKind): bool;
extern macro IsElementsKindGreaterThan(
    ElementsKind, constexpr ElementsKind): bool;
330
extern macro IsFastElementsKind(constexpr ElementsKind): constexpr bool;
331
extern macro IsDoubleElementsKind(constexpr ElementsKind): constexpr bool;
332

333 334 335 336 337
extern macro IsFastAliasedArgumentsMap(implicit context: Context)(Map): bool;
extern macro IsSlowAliasedArgumentsMap(implicit context: Context)(Map): bool;
extern macro IsSloppyArgumentsMap(implicit context: Context)(Map): bool;
extern macro IsStrictArgumentsMap(implicit context: Context)(Map): bool;

338
extern macro SmiAbove(Smi, Smi): bool;
339

340
extern operator '==' macro WordEqual(intptr, intptr): bool;
341
extern operator '==' macro WordEqual(uintptr, uintptr): bool;
342
extern operator '!=' macro WordNotEqual(intptr, intptr): bool;
343
extern operator '!=' macro WordNotEqual(uintptr, uintptr): bool;
344
extern operator '<' macro IntPtrLessThan(intptr, intptr): bool;
345
extern operator '<' macro UintPtrLessThan(uintptr, uintptr): bool;
346
extern operator '>' macro IntPtrGreaterThan(intptr, intptr): bool;
347
extern operator '>' macro UintPtrGreaterThan(uintptr, uintptr): bool;
348
extern operator '<=' macro IntPtrLessThanOrEqual(intptr, intptr): bool;
349
extern operator '<=' macro UintPtrLessThanOrEqual(uintptr, uintptr): bool;
350
extern operator '>=' macro IntPtrGreaterThanOrEqual(intptr, intptr): bool;
351
extern operator '>=' macro UintPtrGreaterThanOrEqual(uintptr, uintptr): bool;
352

353
extern operator '==' macro Float64Equal(float64, float64): bool;
354
extern operator '!=' macro Float64NotEqual(float64, float64): bool;
355
extern operator '>' macro Float64GreaterThan(float64, float64): bool;
356

357 358
extern operator '==' macro BranchIfNumberEqual(Number, Number): never
    labels Taken, NotTaken;
359 360
extern operator '!=' macro BranchIfNumberNotEqual(Number, Number): never
    labels Taken, NotTaken;
361 362 363 364 365 366 367
extern operator '<' macro BranchIfNumberLessThan(Number, Number): never
    labels Taken, NotTaken;
extern operator '<=' macro BranchIfNumberLessThanOrEqual(Number, Number): never
    labels Taken, NotTaken;

extern operator '>' macro BranchIfNumberGreaterThan(Number, Number): never
    labels Taken, NotTaken;
368
extern operator '>=' macro BranchIfNumberGreaterThanOrEqual(Number, Number):
369 370
    never
    labels Taken, NotTaken;
371

372 373
extern operator '==' macro WordEqual(Object, Object): bool;
extern operator '!=' macro WordNotEqual(Object, Object): bool;
374 375 376

extern operator '+' macro SmiAdd(Smi, Smi): Smi;
extern operator '-' macro SmiSub(Smi, Smi): Smi;
377
extern operator '&' macro SmiAnd(Smi, Smi): Smi;
378
extern operator '|' macro SmiOr(Smi, Smi): Smi;
379
extern operator '>>>' macro SmiShr(Smi, constexpr int31): Smi;
380
extern operator '<<' macro SmiShl(Smi, constexpr int31): Smi;
381 382 383

extern operator '+' macro IntPtrAdd(intptr, intptr): intptr;
extern operator '-' macro IntPtrSub(intptr, intptr): intptr;
384
extern operator '*' macro IntPtrMul(intptr, intptr): intptr;
385
extern operator '/' macro IntPtrDiv(intptr, intptr): intptr;
386 387
extern operator '<<' macro WordShl(intptr, intptr): intptr;
extern operator '&' macro WordAnd(intptr, intptr): intptr;
388 389 390 391 392 393
extern operator '|' macro WordOr(intptr, intptr): intptr;

extern operator '+' macro UintPtrAdd(uintptr, uintptr): uintptr;
extern operator '-' macro UintPtrSub(uintptr, uintptr): uintptr;
extern operator '>>>' macro WordShr(uintptr, uintptr): uintptr;
extern operator '<<' macro WordShl(uintptr, uintptr): uintptr;
394
extern operator '&' macro WordAnd(uintptr, uintptr): uintptr;
395
extern operator '|' macro WordOr(uintptr, uintptr): uintptr;
396

397
extern operator '+' macro Int32Add(int32, int32): int32;
398
extern operator '-' macro Int32Sub(int32, int32): int32;
399 400
extern operator '*' macro Int32Mul(int32, int32): int32;
extern operator '%' macro Int32Mod(int32, int32): int32;
401 402
extern operator '&' macro Word32And(int32, int32): int32;
extern operator '&' macro Word32And(uint32, uint32): uint32;
403
extern operator '==' macro
404
ConstexprInt31Equal(constexpr int31, constexpr int31): constexpr bool;
405

406 407 408 409 410 411 412 413 414
extern operator '==' macro Word32Equal(int32, int32): bool;
extern operator '==' macro Word32Equal(uint32, uint32): bool;
extern operator '!=' macro Word32NotEqual(int32, int32): bool;
extern operator '!=' macro Word32NotEqual(uint32, uint32): bool;
extern operator '>>>' macro Word32Shr(uint32, uint32): uint32;
extern operator '<<' macro Word32Shl(int32, int32): int32;
extern operator '<<' macro Word32Shl(uint32, uint32): uint32;
extern operator '|' macro Word32Or(int32, int32): int32;
extern operator '|' macro Word32Or(uint32, uint32): uint32;
415 416
extern operator '&' macro Word32And(bool, bool): bool;
extern operator '|' macro Word32Or(bool, bool): bool;
417

418 419
extern operator '+' macro Float64Add(float64, float64): float64;

420 421
extern operator '+' macro NumberAdd(Number, Number): Number;
extern operator '-' macro NumberSub(Number, Number): Number;
422 423
extern macro NumberMin(Number, Number): Number;
extern macro NumberMax(Number, Number): Number;
424
macro Min(x: Number, y: Number): Number {
425
  return NumberMin(x, y);
426
}
427
macro Max(x: Number, y: Number): Number {
428
  return NumberMax(x, y);
429
}
430

431 432 433
extern macro SmiMax(Smi, Smi): Smi;
extern macro SmiMin(Smi, Smi): Smi;

434
extern operator '!' macro ConstexprBoolNot(constexpr bool): constexpr bool;
435
extern operator '!' macro Word32BinaryNot(bool): bool;
436
extern operator '!' macro IsFalse(Boolean): bool;
437

438
extern operator '.map' macro LoadMap(HeapObject): Map;
439
extern transitioning operator '.map=' macro StoreMap(HeapObject, Map);
440 441
extern operator '.instanceType' macro LoadInstanceType(HeapObject):
    InstanceType;
442 443 444

extern operator '.length' macro LoadStringLengthAsWord(String): intptr;

445
extern operator '.length' macro GetArgumentsLength(constexpr Arguments): intptr;
446 447
extern operator '[]' macro GetArgumentValue(
    constexpr Arguments, intptr): Object;
448

449 450
extern macro TaggedIsSmi(Object): bool;
extern macro TaggedIsNotSmi(Object): bool;
451
extern macro TaggedIsPositiveSmi(Object): bool;
452
extern macro IsValidPositiveSmi(intptr): bool;
453

454 455 456 457 458 459 460 461 462 463 464 465 466 467
extern macro HeapObjectToJSDataView(HeapObject): JSDataView
    labels CastError;
extern macro TaggedToHeapObject(Object): HeapObject
    labels CastError;
extern macro TaggedToSmi(Object): Smi
    labels CastError;
extern macro HeapObjectToJSArray(HeapObject): JSArray
    labels CastError;
extern macro HeapObjectToCallable(HeapObject): Callable
    labels CastError;
extern macro HeapObjectToFixedArray(HeapObject): FixedArray
    labels CastError;
extern macro HeapObjectToFixedDoubleArray(HeapObject): FixedDoubleArray
    labels CastError;
468 469
extern macro HeapObjectToString(HeapObject): String
    labels CastError;
470 471
extern macro HeapObjectToConstructor(HeapObject): Constructor
    labels CastError;
472 473
extern macro HeapObjectToHeapNumber(HeapObject): HeapNumber
    labels CastError;
474 475 476
extern macro HeapObjectToSloppyArgumentsElements(HeapObject):
    SloppyArgumentsElements
    labels CastError;
477 478 479 480 481 482 483
extern macro TaggedToNumber(Object): Number
    labels CastError;

macro CastHeapObject<A: type>(o: HeapObject): A
    labels CastError;
CastHeapObject<HeapObject>(o: HeapObject): HeapObject
    labels CastError {
484 485
  return o;
}
486 487
CastHeapObject<FixedArray>(o: HeapObject): FixedArray
    labels CastError {
488
  return HeapObjectToFixedArray(o) otherwise CastError;
489
}
490 491
CastHeapObject<FixedDoubleArray>(o: HeapObject): FixedDoubleArray
    labels CastError {
492
  return HeapObjectToFixedDoubleArray(o) otherwise CastError;
493
}
494 495 496 497
CastHeapObject<SloppyArgumentsElements>(o: HeapObject): SloppyArgumentsElements
    labels CastError {
  return HeapObjectToSloppyArgumentsElements(o) otherwise CastError;
}
498 499
CastHeapObject<JSDataView>(o: HeapObject): JSDataView
    labels CastError {
500
  return HeapObjectToJSDataView(o) otherwise CastError;
501
}
502 503
CastHeapObject<Callable>(o: HeapObject): Callable
    labels CastError {
504
  return HeapObjectToCallable(o) otherwise CastError;
505
}
506 507
CastHeapObject<JSArray>(o: HeapObject): JSArray
    labels CastError {
508
  return HeapObjectToJSArray(o) otherwise CastError;
509
}
510 511 512 513
CastHeapObject<String>(o: HeapObject): String
    labels CastError {
  return HeapObjectToString(o) otherwise CastError;
}
514 515 516 517
CastHeapObject<Constructor>(o: HeapObject): Constructor
    labels CastError {
  return HeapObjectToConstructor(o) otherwise CastError;
}
518

519 520
macro Cast<A: type>(o: HeapObject): A
    labels CastError {
521
  return CastHeapObject<A>(o) otherwise CastError;
522 523
}

524
// CastHeapObject allows this default-implementation to be non-recursive.
525
// Otherwise the generated CSA code might run into infinite recursion.
526 527
macro Cast<A: type>(o: Object): A
    labels CastError {
528
  return CastHeapObject<A>(TaggedToHeapObject(o) otherwise CastError)
529
      otherwise CastError;
530
}
531 532
Cast<Smi>(o: Object): Smi
    labels CastError {
533
  return TaggedToSmi(o) otherwise CastError;
534
}
535 536
Cast<Number>(o: Object): Number
    labels CastError {
537
  return TaggedToNumber(o) otherwise CastError;
538
}
539

540
extern macro AllocateHeapNumberWithValue(float64): HeapNumber;
541 542
extern macro ChangeInt32ToTagged(int32): Number;
extern macro ChangeUint32ToTagged(uint32): Number;
543 544
extern macro ChangeUintPtrToFloat64(uintptr): float64;
extern macro ChangeUintPtrToTagged(uintptr): Number;
545
extern macro Unsigned(int32): uint32;
546
extern macro Unsigned(intptr): uintptr;
547 548
extern macro Unsigned(RawPtr): uintptr;
extern macro Signed(uint32): int32;
549
extern macro Signed(uintptr): intptr;
550
extern macro Signed(RawPtr): intptr;
551 552 553 554 555
extern macro TruncateIntPtrToInt32(intptr): int32;
extern macro SmiTag(intptr): Smi;
extern macro SmiFromInt32(int32): Smi;
extern macro SmiUntag(Smi): intptr;
extern macro SmiToInt32(Smi): int32;
556
extern macro RoundIntPtrToFloat64(intptr): float64;
557 558 559
extern macro LoadHeapNumberValue(HeapNumber): float64;
extern macro ChangeFloat32ToFloat64(float32): float64;
extern macro ChangeNumberToFloat64(Number): float64;
560
extern macro ChangeFloat64ToUintPtr(float64): uintptr;
561
extern macro ChangeInt32ToIntPtr(int32): intptr;   // Sign-extends.
562
extern macro ChangeUint32ToWord(uint32): uintptr;  // Doesn't sign-extend.
563 564
extern macro LoadNativeContext(Context): NativeContext;
extern macro LoadJSArrayElementsMap(constexpr ElementsKind, Context): Map;
565
extern macro ChangeNonnegativeNumberToUintPtr(Number): uintptr;
566 567 568 569 570

extern macro NumberConstant(constexpr float64): Number;
extern macro NumberConstant(constexpr int32): Number;
extern macro IntPtrConstant(constexpr int31): intptr;
extern macro IntPtrConstant(constexpr int32): intptr;
571
extern macro Int32Constant(constexpr int31): int31;
572
extern macro Int32Constant(constexpr int32): int32;
573
extern macro Float64Constant(constexpr int31): float64;
574 575
extern macro SmiConstant(constexpr int31): Smi;
extern macro BoolConstant(constexpr bool): bool;
576
extern macro StringConstant(constexpr string): String;
577 578
extern macro LanguageModeConstant(constexpr LanguageMode): LanguageMode;
extern macro Int32Constant(constexpr ElementsKind): ElementsKind;
579
extern macro IntPtrConstant(constexpr NativeContextSlot): NativeContextSlot;
580

581
macro FromConstexpr<A: type>(o: constexpr int31): A;
582
FromConstexpr<intptr>(i: constexpr int31): intptr {
583 584
  return IntPtrConstant(i);
}
585
FromConstexpr<int31>(i: constexpr int31): int31 {
586 587
  return Int32Constant(i);
}
588
FromConstexpr<int32>(i: constexpr int31): int32 {
589 590
  return Int32Constant(i);
}
591
FromConstexpr<uint32>(i: constexpr int31): uint32 {
592
  return Unsigned(Int32Constant(i));
593
}
594
FromConstexpr<uintptr>(i: constexpr int31): uintptr {
595 596
  return ChangeUint32ToWord(i);
}
597
FromConstexpr<Smi>(i: constexpr int31): Smi {
598 599
  return SmiConstant(i);
}
600
FromConstexpr<Number>(i: constexpr int31): Number {
601 602
  return SmiConstant(i);
}
603
FromConstexpr<float64>(i: constexpr int31): float64 {
604 605
  return Float64Constant(i);
}
606
macro FromConstexpr<A: type>(o: constexpr int32): A;
607
FromConstexpr<intptr>(i: constexpr int32): intptr {
608 609
  return IntPtrConstant(i);
}
610
FromConstexpr<int32>(i: constexpr int32): int32 {
611
  return Int32Constant(i);
612
}
613
FromConstexpr<Number>(i: constexpr int32): Number {
614 615
  return NumberConstant(i);
}
616
macro FromConstexpr<A: type>(o: constexpr float64): A;
617
FromConstexpr<Number>(f: constexpr float64): Number {
618 619
  return NumberConstant(f);
}
620
macro FromConstexpr<A: type>(b: constexpr bool): A;
621
FromConstexpr<bool>(b: constexpr bool): bool {
622 623
  return BoolConstant(b);
}
624
macro FromConstexpr<A: type>(l: constexpr LanguageMode): A;
625
FromConstexpr<LanguageMode>(b: constexpr LanguageMode): LanguageMode {
626 627
  return LanguageModeConstant(b);
}
628
macro FromConstexpr<A: type>(e: constexpr ElementsKind): A;
629
FromConstexpr<ElementsKind>(e: constexpr ElementsKind): ElementsKind {
630 631
  return Int32Constant(e);
}
632
macro FromConstexpr<A: type>(s: constexpr string): A;
633
FromConstexpr<String>(s: constexpr string): String {
634 635
  return StringConstant(s);
}
636
FromConstexpr<Object>(s: constexpr string): Object {
637 638
  return StringConstant(s);
}
639 640 641 642 643
macro FromConstexpr<A: type>(e: constexpr NativeContextSlot): A;
FromConstexpr<NativeContextSlot>(c: constexpr NativeContextSlot):
    NativeContextSlot {
  return IntPtrConstant(c);
}
644

645
macro Convert<A: type>(i: constexpr int31): A {
646 647
  return i;
}
648 649
extern macro ConvertElementsKindToInt(ElementsKind): int32;

650
macro Convert<A: type>(elementsKind: ElementsKind): A;
651 652
Convert<int32>(elementsKind: ElementsKind): int32 {
  return ConvertElementsKindToInt(elementsKind);
653 654
}

655
macro Convert<A: type>(i: int32): A;
656
Convert<Number>(i: int32): Number {
657 658
  return ChangeInt32ToTagged(i);
}
659
Convert<intptr>(i: int32): intptr {
660 661
  return ChangeInt32ToIntPtr(i);
}
662
Convert<Smi>(i: int32): Smi {
663 664
  return SmiFromInt32(i);
}
665
macro Convert<A: type>(ui: uint32): A;
666
Convert<Number>(ui: uint32): Number {
667 668
  return ChangeUint32ToTagged(ui);
}
669
Convert<Smi>(ui: uint32): Smi {
670
  return SmiFromInt32(Signed(ui));
671
}
672
Convert<uintptr>(ui: uint32): uintptr {
673
  return ChangeUint32ToWord(ui);
674
}
675
macro Convert<A: type>(i: intptr): A;
676
Convert<int32>(i: intptr): int32 {
677 678
  return TruncateIntPtrToInt32(i);
}
679
Convert<Smi>(i: intptr): Smi {
680 681
  return SmiTag(i);
}
682
macro Convert<A: type>(ui: uintptr): A;
683
Convert<uint32>(ui: uintptr): uint32 {
684
  return Unsigned(TruncateIntPtrToInt32(Signed(ui)));
685
}
686
macro Convert<A: type>(s: Smi): A;
687
Convert<intptr>(s: Smi): intptr {
688 689
  return SmiUntag(s);
}
690
Convert<int32>(s: Smi): int32 {
691 692
  return SmiToInt32(s);
}
693
macro Convert<A: type>(h: HeapNumber): A;
694
Convert<float64>(h: HeapNumber): float64 {
695 696
  return LoadHeapNumberValue(h);
}
697
macro Convert<A: type>(n: Number): A;
698
Convert<float64>(n: Number): float64 {
699 700
  return ChangeNumberToFloat64(n);
}
701 702 703
Convert<uintptr>(n: Number): uintptr {
  return ChangeNonnegativeNumberToUintPtr(n);
}
704
macro Convert<A: type>(f: float32): A;
705
Convert<float64>(f: float32): float64 {
706 707
  return ChangeFloat32ToFloat64(f);
}
708
macro Convert<A: type>(d: float64): A;
709
Convert<Number>(d: float64): Number {
710 711
  return AllocateHeapNumberWithValue(d);
}
712 713 714 715 716 717
Convert<float64>(ui: uintptr): float64 {
  return ChangeUintPtrToFloat64(ui);
}
Convert<Number>(ui: uintptr): Number {
  return ChangeUintPtrToTagged(ui);
}
718
Convert<uintptr>(d: float64): uintptr {
719 720
  return ChangeFloat64ToUintPtr(d);
}
721
macro Convert<A: type>(r: RawPtr): A;
722
Convert<uintptr>(r: RawPtr): uintptr {
723 724
  return Unsigned(r);
}
725
Convert<intptr>(r: RawPtr): intptr {
726 727
  return Signed(r);
}
728 729

extern macro UnsafeCastNumberToHeapNumber(Number): HeapNumber;
730
extern macro UnsafeCastObjectToFixedArrayBase(Object): FixedArrayBase;
731
extern macro UnsafeCastObjectToFixedArray(Object): FixedArray;
732
extern macro UnsafeCastObjectToContext(Object): Context;
733 734 735 736 737 738 739 740
extern macro UnsafeCastObjectToFixedDoubleArray(Object): FixedDoubleArray;
extern macro UnsafeCastObjectToHeapNumber(Object): HeapNumber;
extern macro UnsafeCastObjectToCallable(Object): Callable;
extern macro UnsafeCastObjectToSmi(Object): Smi;
extern macro UnsafeCastObjectToNumber(Object): Number;
extern macro UnsafeCastObjectToHeapObject(Object): HeapObject;
extern macro UnsafeCastObjectToJSArray(Object): JSArray;
extern macro UnsafeCastObjectToFixedTypedArrayBase(Object): FixedTypedArrayBase;
741 742 743
extern macro UnsafeCastObjectToNumberDictionary(Object): NumberDictionary;
extern macro UnsafeCastObjectToJSReceiver(Object): JSReceiver;
extern macro UnsafeCastObjectToJSObject(Object): JSObject;
744
extern macro UnsafeCastObjectToMap(Object): Map;
745
extern macro UnsafeCastObjectToString(Object): String;
746

747
macro UnsafeCast<A: type>(n: Number): A;
748
UnsafeCast<HeapNumber>(n: Number): HeapNumber {
749 750
  return UnsafeCastNumberToHeapNumber(n);
}
751
macro UnsafeCast<A: type>(o: Object): A;
752
UnsafeCast<Object>(o: Object): Object {
753 754
  return o;
}
755
UnsafeCast<FixedArray>(o: Object): FixedArray {
756 757
  return UnsafeCastObjectToFixedArray(o);
}
758
UnsafeCast<FixedDoubleArray>(o: Object): FixedDoubleArray {
759 760
  return UnsafeCastObjectToFixedDoubleArray(o);
}
761
UnsafeCast<HeapNumber>(o: Object): HeapNumber {
762 763
  return UnsafeCastObjectToHeapNumber(o);
}
764
UnsafeCast<Callable>(o: Object): Callable {
765 766
  return UnsafeCastObjectToCallable(o);
}
767
UnsafeCast<Smi>(o: Object): Smi {
768 769
  return UnsafeCastObjectToSmi(o);
}
770
UnsafeCast<Number>(o: Object): Number {
771 772
  return UnsafeCastObjectToNumber(o);
}
773
UnsafeCast<HeapObject>(o: Object): HeapObject {
774 775
  return UnsafeCastObjectToHeapObject(o);
}
776
UnsafeCast<JSArray>(o: Object): JSArray {
777 778
  return UnsafeCastObjectToJSArray(o);
}
779
UnsafeCast<FixedTypedArrayBase>(o: Object): FixedTypedArrayBase {
780 781
  return UnsafeCastObjectToFixedTypedArrayBase(o);
}
782
UnsafeCast<NumberDictionary>(o: Object): NumberDictionary {
783 784
  return UnsafeCastObjectToNumberDictionary(o);
}
785
UnsafeCast<JSReceiver>(o: Object): JSReceiver {
786 787
  return UnsafeCastObjectToJSReceiver(o);
}
788
UnsafeCast<JSObject>(o: Object): JSObject {
789 790
  return UnsafeCastObjectToJSObject(o);
}
791
UnsafeCast<Map>(o: Object): Map {
792 793
  return UnsafeCastObjectToMap(o);
}
794
UnsafeCast<FixedArrayBase>(o: Object): FixedArrayBase {
795 796
  return UnsafeCastObjectToFixedArrayBase(o);
}
797 798 799
UnsafeCast<Context>(o: Object): Context {
  return UnsafeCastObjectToContext(o);
}
800 801 802
UnsafeCast<String>(o: Object): String {
  return UnsafeCastObjectToString(o);
}
803 804 805 806 807 808

// RawCasts should *never* be used anywhere in Torque code except for
// in Torque-based UnsafeCast operators preceeded by an appropriate
// type check().
extern macro RawCastObjectToJSArgumentsObjectWithLength(Object):
    JSArgumentsObjectWithLength;
809 810
extern macro RawCastObjectToFastJSArray(Object): FastJSArray;
extern macro RawCastObjectToFastJSArrayForCopy(Object): FastJSArrayForCopy;
811

812 813
macro BranchIfJSArgumentsObjectWithLength(implicit context: Context)(o: Object):
    never
814 815 816
    labels True, False {
  const heapObject: HeapObject = Cast<HeapObject>(o) otherwise False;
  const map: Map = heapObject.map;
817 818 819 820
  if (IsFastAliasedArgumentsMap(map)) goto True;
  if (IsSloppyArgumentsMap(map)) goto True;
  if (IsStrictArgumentsMap(map)) goto True;
  if (!IsSlowAliasedArgumentsMap(map)) goto False;
821 822 823
  goto True;
}

824 825 826 827
macro UnsafeCast<A: type>(implicit context: Context)(o: Object): A;
UnsafeCast<JSArgumentsObjectWithLength>(implicit context: Context)(o: Object):
    JSArgumentsObjectWithLength {
  assert(BranchIfJSArgumentsObjectWithLength(o));
828 829 830
  return RawCastObjectToJSArgumentsObjectWithLength(o);
}

831
Cast<JSArgumentsObjectWithLength>(implicit context: Context)(o: Object):
832 833
    JSArgumentsObjectWithLength
    labels CastError {
834 835
  if (BranchIfJSArgumentsObjectWithLength(o)) {
    return UnsafeCast<JSArgumentsObjectWithLength>(o);
836 837 838 839
  } else {
    goto CastError;
  }
}
840

841 842 843 844 845 846 847 848 849 850 851 852 853 854 855 856 857 858 859 860 861 862 863 864 865 866 867 868 869 870 871 872 873 874 875 876 877 878 879
UnsafeCast<FastJSArray>(implicit context: Context)(o: Object): FastJSArray {
  assert(BranchIfFastJSArray(o, context));
  return RawCastObjectToFastJSArray(o);
}

Cast<FastJSArray>(implicit context: Context)(o: Object): FastJSArray
    labels CastError {
  if (BranchIfFastJSArray(o, context)) {
    return UnsafeCast<FastJSArray>(o);
  } else {
    goto CastError;
  }
}

Cast<FastJSArray>(implicit context: Context)(ho: HeapObject): FastJSArray
    labels CastError {
  if (BranchIfFastJSArray(ho, context)) {
    return UnsafeCast<FastJSArray>(ho);
  } else {
    goto CastError;
  }
}

UnsafeCast<FastJSArrayForCopy>(implicit context: Context)(o: Object):
    FastJSArrayForCopy {
  assert(BranchIfFastJSArrayForCopy(o, context));
  return RawCastObjectToFastJSArrayForCopy(o);
}

Cast<FastJSArrayForCopy>(implicit context: Context)(o: Object):
    FastJSArrayForCopy
    labels CastError {
  if (BranchIfFastJSArrayForCopy(o, context)) {
    return UnsafeCast<FastJSArrayForCopy>(o);
  } else {
    goto CastError;
  }
}

880
const kCOWMap: Map = UnsafeCast<Map>(LoadRoot(kFixedCOWArrayMapRootIndex));
881
const kEmptyFixedArray: FixedArrayBase =
882
    UnsafeCast<FixedArrayBase>(LoadRoot(kEmptyFixedArrayRootIndex));
883

884 885
extern macro BranchIfFastJSArray(Object, Context): never
    labels Taken, NotTaken;
886 887
extern macro BranchIfFastJSArrayForCopy(Object, Context): never
    labels Taken, NotTaken;
888 889
extern macro BranchIfNotFastJSArray(Object, Context): never
    labels Taken, NotTaken;
890 891 892 893
macro BranchIfNotFastJSArrayForCopy(implicit context: Context)(o: Object):
    never
    labels Taken, NotTaken {
  BranchIfFastJSArrayForCopy(o, context) otherwise NotTaken, Taken;
894 895
}

896 897 898 899 900
extern macro IsPrototypeInitialArrayPrototype(Context, Map): bool;
extern macro IsNoElementsProtectorCellInvalid(): bool;
extern macro IsArraySpeciesProtectorCellInvalid(): bool;
extern macro IsTypedArraySpeciesProtectorCellInvalid(): bool;
extern macro IsPromiseSpeciesProtectorCellInvalid(): bool;
901

902 903
extern operator '.buffer' macro LoadTypedArrayBuffer(JSTypedArray):
    JSArrayBuffer;
904 905 906

extern operator '.data_ptr' macro LoadDataPtr(JSTypedArray): RawPtr;

907
extern operator '.elements_kind' macro LoadMapElementsKind(Map): ElementsKind;
908 909
extern operator '.elements_kind' macro LoadElementsKind(JSTypedArray):
    ElementsKind;
910

911 912
extern operator '.elements' macro LoadElements(JSObject): FixedArrayBase;
extern operator '.elements=' macro StoreElements(JSObject, FixedArrayBase);
913

914
extern operator '.length' macro LoadJSTypedArrayLength(JSTypedArray): Smi;
915
extern operator '.length' macro LoadJSArrayLength(JSArray): Number;
916 917
extern operator '.length' macro LoadJSArgumentsObjectWithLength(
    JSArgumentsObjectWithLength): Object;
918
extern operator '.length' macro LoadFastJSArrayLength(FastJSArray): Smi;
919 920 921
extern operator '.length=' macro StoreJSArrayLength(JSArray, Smi);

extern operator '.length' macro LoadFixedArrayBaseLength(FixedArrayBase): Smi;
922 923
extern operator '.length_intptr' macro LoadAndUntagFixedArrayBaseLength(
    FixedArrayBase): intptr;
924 925
extern operator '[]' macro LoadFixedArrayElement(FixedArray, intptr): Object;
extern operator '[]' macro LoadFixedArrayElement(FixedArray, Smi): Object;
926 927 928
extern operator '[]' macro LoadFixedArrayElement(
    FixedArray, constexpr int31): Object;
extern operator '[]=' macro StoreFixedArrayElement(
929
    FixedArray, intptr, Smi): void;
930
extern operator '[]=' macro StoreFixedArrayElement(
931 932 933 934 935
    FixedArray, intptr, HeapObject): void;
extern operator '[]=' macro StoreFixedArrayElement(
    FixedArray, constexpr int31, Smi): void;
extern operator '[]=' macro StoreFixedArrayElement(
    FixedArray, constexpr int31, HeapObject): void;
936 937
extern operator '[]=' macro StoreFixedArrayElementSmi(
    FixedArray, Smi, Object): void;
938 939
operator '[]=' macro StoreFixedDoubleArrayNumber(
    a: FixedDoubleArray, index: Smi, value: Number): void {
940
  a[index] = Convert<float64>(value);
941
}
942

943 944
extern macro StoreFixedArrayElementSmi(
    FixedArray, Smi, Object, constexpr WriteBarrierMode): void;
945

946 947
extern operator '.instance_type' macro LoadMapInstanceType(Map): int32;

948 949 950 951 952
extern macro LoadFixedDoubleArrayElement(FixedDoubleArray, Smi): float64;
extern macro Float64SilenceNaN(float64): float64;

extern macro StoreFixedDoubleArrayElement(
    FixedDoubleArray, Object, float64, constexpr ParameterMode);
953 954 955
extern macro StoreFixedArrayElement(
    FixedArray, intptr, Object, constexpr WriteBarrierMode): void;

956 957 958 959
macro StoreFixedDoubleArrayElementWithSmiIndex(
    array: FixedDoubleArray, index: Smi, value: float64) {
  StoreFixedDoubleArrayElement(array, index, value, SMI_PARAMETERS);
}
960
extern macro GetNumberDictionaryNumberOfElements(NumberDictionary): Smi;
961

962 963
extern macro BasicLoadNumberDictionaryElement(NumberDictionary, intptr): Object
    labels NotData, IfHole;
964
extern macro BasicStoreNumberDictionaryElement(NumberDictionary, intptr, Object)
965
labels NotData, IfHole, ReadOnly;
966

967
extern macro IsFastElementsKind(ElementsKind): bool;
968
extern macro IsDoubleElementsKind(ElementsKind): bool;
969 970
extern macro IsFastSmiOrTaggedElementsKind(ElementsKind): bool;
extern macro IsFastSmiElementsKind(ElementsKind): bool;
971
extern macro IsHoleyFastElementsKind(ElementsKind): bool;
972

973 974 975 976 977 978 979 980 981 982 983 984 985 986 987 988 989 990 991 992 993 994
macro AllowDoubleElements(kind: ElementsKind): ElementsKind {
  if (kind == PACKED_SMI_ELEMENTS) {
    return PACKED_DOUBLE_ELEMENTS;
  } else if (kind == HOLEY_SMI_ELEMENTS) {
    return HOLEY_DOUBLE_ELEMENTS;
  }
  return kind;
}

macro AllowNonNumberElements(kind: ElementsKind): ElementsKind {
  if (kind == PACKED_SMI_ELEMENTS) {
    return PACKED_ELEMENTS;
  } else if (kind == HOLEY_SMI_ELEMENTS) {
    return HOLEY_ELEMENTS;
  } else if (kind == PACKED_DOUBLE_ELEMENTS) {
    return PACKED_ELEMENTS;
  } else if (kind == HOLEY_DOUBLE_ELEMENTS) {
    return HOLEY_ELEMENTS;
  }
  return kind;
}

995 996
extern macro AllocateZeroedFixedArray(intptr): FixedArray;
extern macro AllocateZeroedFixedDoubleArray(intptr): FixedDoubleArray;
997
extern macro CalculateNewElementsCapacity(Smi): Smi;
998
extern macro CalculateNewElementsCapacity(intptr): intptr;
999

1000 1001
extern macro AllocateFixedArrayWithHoles(
    intptr, constexpr AllocationFlags): FixedArray;
1002
extern macro CopyFixedArrayElements(
1003 1004
    constexpr ElementsKind, FixedArray, constexpr ElementsKind, FixedArray,
    intptr, intptr, intptr): void;
1005
extern macro CopyFixedArrayElements(
1006 1007
    constexpr ElementsKind, FixedArray, constexpr ElementsKind, FixedArray, Smi,
    Smi, Smi): void;
1008

1009 1010
extern macro AllocateJSArray(constexpr ElementsKind, Map, intptr, Smi): JSArray;
extern macro AllocateJSArray(constexpr ElementsKind, Map, Smi, Smi): JSArray;
1011

1012
extern operator '[]=' macro StoreFixedDoubleArrayElementSmi(
1013 1014
    FixedDoubleArray, Smi, float64): void;

1015
extern macro LoadDoubleWithHoleCheck(FixedDoubleArray, Smi): float64
1016
    labels IfHole;
1017 1018
extern macro LoadDoubleWithHoleCheck(FixedDoubleArray, intptr): float64
    labels IfHole;
1019
extern macro StoreFixedDoubleArrayHoleSmi(FixedDoubleArray, Smi): void;
1020

1021 1022 1023 1024 1025 1026 1027
extern transitioning macro Call(Context, Callable, Object): Object;
extern transitioning macro Call(Context, Callable, Object, Object): Object;
extern transitioning macro Call(
    Context, Callable, Object, Object, Object): Object;
extern transitioning macro Call(
    Context, Callable, Object, Object, Object, Object): Object;
extern transitioning macro Call(
1028
    Context, Callable, Object, Object, Object, Object, Object): Object;
1029
extern transitioning macro Call(
1030
    Context, Callable, Object, Object, Object, Object, Object, Object): Object;
1031

1032
extern builtin CloneFastJSArray(Context, FastJSArrayForCopy): JSArray;
1033
extern macro ExtractFixedArray(FixedArrayBase, Smi, Smi, Smi): FixedArrayBase;
1034 1035
extern macro ExtractFixedArray(
    FixedArrayBase, Smi, Smi, Smi,
1036
    constexpr ExtractFixedArrayFlags): FixedArrayBase;
1037

1038 1039 1040 1041
extern macro ExtractFixedArray(
    FixedArray, intptr, intptr, intptr,
    constexpr ExtractFixedArrayFlags): FixedArray;

1042 1043
extern builtin ExtractFastJSArray(Context, JSArray, Smi, Smi): JSArray;

1044 1045 1046 1047 1048 1049 1050 1051 1052 1053 1054 1055 1056 1057 1058 1059 1060 1061 1062 1063 1064 1065 1066 1067 1068 1069 1070 1071 1072 1073
extern macro MoveElements(
    constexpr ElementsKind, FixedArrayBase, intptr, intptr, intptr): void;
macro TorqueMoveElements(
    elements: FixedArray, dstIndex: intptr, srcIndex: intptr,
    count: intptr): void {
  MoveElements(HOLEY_ELEMENTS, elements, dstIndex, srcIndex, count);
}
macro TorqueMoveElements(
    elements: FixedDoubleArray, dstIndex: intptr, srcIndex: intptr,
    count: intptr): void {
  MoveElements(HOLEY_DOUBLE_ELEMENTS, elements, dstIndex, srcIndex, count);
}

extern macro CopyElements(
    constexpr ElementsKind, FixedArrayBase, intptr, FixedArrayBase, intptr,
    intptr): void;
macro TorqueCopyElements(
    dstElements: FixedArray, dstIndex: intptr, srcElements: FixedArray,
    srcIndex: intptr, count: intptr): void {
  CopyElements(
      HOLEY_ELEMENTS, dstElements, dstIndex, srcElements, srcIndex, count);
}
macro TorqueCopyElements(
    dstElements: FixedDoubleArray, dstIndex: intptr,
    srcElements: FixedDoubleArray, srcIndex: intptr, count: intptr): void {
  CopyElements(
      HOLEY_DOUBLE_ELEMENTS, dstElements, dstIndex, srcElements, srcIndex,
      count);
}

1074
transitioning macro LoadElementNoHole<T: type>(a: JSArray, index: Smi): Object
1075
    labels IfHole;
1076 1077

LoadElementNoHole<FixedArray>(a: JSArray, index: Smi): Object
1078
    labels IfHole {
1079 1080
  try {
    let elements: FixedArray =
1081
        Cast<FixedArray>(a.elements) otherwise Unexpected;
1082 1083 1084 1085 1086 1087 1088 1089 1090 1091 1092 1093
    let e: Object = elements[index];
    if (e == Hole) {
      goto IfHole;
    }
    return e;
  }
  label Unexpected {
    unreachable;
  }
}

LoadElementNoHole<FixedDoubleArray>(a: JSArray, index: Smi): Object
1094
    labels IfHole {
1095 1096
  try {
    let elements: FixedDoubleArray =
1097
        Cast<FixedDoubleArray>(a.elements) otherwise Unexpected;
1098 1099 1100 1101 1102 1103 1104 1105
    let e: float64 = LoadDoubleWithHoleCheck(elements, index) otherwise IfHole;
    return AllocateHeapNumberWithValue(e);
  }
  label Unexpected {
    unreachable;
  }
}

1106 1107 1108
extern macro TransitionElementsKind(JSObject, Map, ElementsKind, ElementsKind):
    void
    labels Bailout;
1109

1110
extern macro IsCallable(HeapObject): bool;
1111
extern macro IsJSArray(HeapObject): bool;
1112
extern macro IsJSReceiver(HeapObject): bool;
1113 1114
extern macro TaggedIsCallable(Object): bool;
extern macro IsDetachedBuffer(JSArrayBuffer): bool;
1115
extern macro IsHeapNumber(HeapObject): bool;
1116
extern macro IsFixedArray(HeapObject): bool;
1117
extern macro IsNumber(Object): bool;
1118 1119
extern macro IsExtensibleMap(Map): bool;
extern macro IsCustomElementsReceiverInstanceType(int32): bool;
1120
extern macro IsFastJSArray(Object, Context): bool;
1121
extern macro Typeof(Object): Object;
1122
extern macro LoadTargetFromFrame(): JSFunction;
1123

1124 1125
// Return true iff number is NaN.
macro NumberIsNaN(number: Number): bool {
1126 1127
  typeswitch (number) {
    case (Smi): {
1128
      return false;
1129 1130 1131 1132 1133
    }
    case (hn: HeapNumber): {
      let value: float64 = Convert<float64>(hn);
      return value != value;
    }
1134
  }
1135
}
1136

1137 1138
extern macro BranchIfToBooleanIsTrue(Object): never
    labels Taken, NotTaken;
1139 1140

macro ToBoolean(obj: Object): bool {
1141
  if (BranchIfToBooleanIsTrue(obj)) {
1142
    return true;
1143
  } else {
1144
    return false;
1145 1146
  }
}
1147

1148 1149
macro ToIndex(input: Object, context: Context): Number
    labels RangeError {
1150 1151 1152 1153 1154 1155 1156 1157 1158 1159 1160
  if (input == Undefined) {
    return 0;
  }

  let value: Number = ToInteger_Inline(context, input, kTruncateMinusZero);
  if (value < 0 || value > kMaxSafeInteger) {
    goto RangeError;
  }

  return value;
}
1161

1162 1163
transitioning macro GetLengthProperty(implicit context: Context)(o: Object):
    Number {
1164
  try {
1165 1166 1167 1168 1169
    typeswitch (o) {
      case (a: JSArray): {
        return a.length;
      }
      case (a: JSArgumentsObjectWithLength): {
1170
        goto ToLength(a.length);
1171 1172 1173 1174 1175
      }
      case (Object): deferred {
        goto ToLength(GetProperty(o, kLengthString));
      }
    }
1176
  }
1177
  label ToLength(length: Object) deferred {
1178 1179 1180
    return ToLength_Inline(context, length);
  }
}
1181 1182 1183 1184 1185 1186 1187 1188 1189 1190 1191

extern macro NumberToString(Number): String;
extern macro HasOnlyOneByteChars(InstanceType): bool;
extern macro AllocateSeqOneByteString(implicit context: Context)(uint32):
    String;
extern macro AllocateSeqTwoByteString(implicit context: Context)(uint32):
    String;
extern macro TryIntPtrAdd(intptr, intptr): intptr
    labels IfOverflow;

extern builtin ObjectToString(Context, Object): Object;
1192
extern builtin StringRepeat(Context, String, Number): String;