tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

ConstantCompareOperand.h (2846B)


      1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
      2 * vim: set ts=8 sts=2 et sw=2 tw=80:
      3 * This Source Code Form is subject to the terms of the Mozilla Public
      4 * License, v. 2.0. If a copy of the MPL was not distributed with this
      5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
      6 
      7 #ifndef vm_ConstantCompareOperand_h
      8 #define vm_ConstantCompareOperand_h
      9 
     10 #include <stdint.h>
     11 
     12 #include "js/Value.h"
     13 
     14 namespace js {
     15 
     16 /*
     17 * Simple struct for encoding comparison operations with parse-time constant
     18 * values, presently used with the |StrictConstantEq| and |StrictConstantNe|
     19 * opcodes.
     20 *
     21 * The operand encodes the type of the constant and its payload. The type is
     22 * encoded in the high-byte and the payload in the low-byte of a 16-bit word.
     23 *
     24 * TODO (Bug 1958722): Investigate if larger payloads can be supported in the
     25 * empty bits of the type.
     26 */
     27 struct ConstantCompareOperand {
     28 public:
     29  enum class EncodedType : uint8_t {
     30    Int32 = JSVAL_TYPE_INT32,
     31    Boolean = JSVAL_TYPE_BOOLEAN,
     32    Null = JSVAL_TYPE_NULL,
     33    Undefined = JSVAL_TYPE_UNDEFINED,
     34  };
     35  static constexpr uint16_t OFFSET_OF_TYPE =
     36      sizeof(jsbytecode) + sizeof(JSValueType);
     37  static constexpr uint16_t OFFSET_OF_VALUE = sizeof(jsbytecode);
     38 
     39 private:
     40  uint16_t value_;
     41 
     42  static constexpr uint8_t SHIFT_TYPE = 8;
     43  static constexpr uint16_t MASK_TYPE = 0xFF00;
     44  static constexpr uint16_t MASK_VALUE = 0x00FF;
     45 
     46  static uint16_t encodeType(EncodedType type) {
     47    return static_cast<uint16_t>(type) << SHIFT_TYPE;
     48  }
     49 
     50  explicit ConstantCompareOperand(uint16_t value) : value_(value) {}
     51 
     52 public:
     53  explicit ConstantCompareOperand(int8_t value)
     54      : value_(encodeType(EncodedType::Int32) | static_cast<uint8_t>(value)) {
     55    MOZ_ASSERT(this->toInt32() == value);
     56  }
     57  explicit ConstantCompareOperand(bool value)
     58      : value_(encodeType(EncodedType::Boolean) | value) {
     59    MOZ_ASSERT(this->toBoolean() == value);
     60  }
     61  explicit ConstantCompareOperand(EncodedType type) : value_(encodeType(type)) {
     62    MOZ_ASSERT(type == EncodedType::Undefined || type == EncodedType::Null);
     63    MOZ_ASSERT(type == this->type());
     64  }
     65 
     66  static ConstantCompareOperand fromRawValue(uint16_t value) {
     67    return ConstantCompareOperand(value);
     68  }
     69 
     70  static bool CanEncodeInt32ValueAsOperand(int32_t value) {
     71    return value >= INT8_MIN && value <= INT8_MAX;
     72  }
     73 
     74  EncodedType type() const {
     75    return static_cast<EncodedType>((value_ & MASK_TYPE) >> SHIFT_TYPE);
     76  }
     77 
     78  int32_t toInt32() const {
     79    MOZ_ASSERT(type() == EncodedType::Int32);
     80    return static_cast<int8_t>(value_ & MASK_VALUE);
     81  }
     82 
     83  bool toBoolean() const {
     84    MOZ_ASSERT(type() == EncodedType::Boolean);
     85    return bool(value_ & MASK_VALUE);
     86  }
     87 
     88  uint16_t rawValue() const { return value_; }
     89 };
     90 
     91 }  // namespace js
     92 
     93 #endif /* vm_ConstantCompareOperand_h */