DataViewObject.h (8138B)
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_DataViewObject_h 8 #define vm_DataViewObject_h 9 10 #include "mozilla/CheckedInt.h" 11 #include "mozilla/Maybe.h" 12 13 #include "js/Class.h" 14 #include "vm/ArrayBufferViewObject.h" 15 #include "vm/JSObject.h" 16 17 namespace js { 18 19 class ArrayBufferObjectMaybeShared; 20 21 // In the DataViewObject, the private slot contains a raw pointer into 22 // the buffer. The buffer may be shared memory and the raw pointer 23 // should not be exposed without sharedness information accompanying 24 // it. 25 // 26 // DataViewObject is an abstract base class and has exactly two concrete 27 // subclasses, FixedLengthDataViewObject and ResizableDataViewObject. 28 29 class DataViewObject : public ArrayBufferViewObject { 30 protected: 31 static const ClassSpec classSpec_; 32 33 private: 34 template <typename NativeType> 35 SharedMem<uint8_t*> getDataPointer(uint64_t offset, size_t length, 36 bool* isSharedMemory); 37 38 static bool bufferGetterImpl(JSContext* cx, const CallArgs& args); 39 static bool bufferGetter(JSContext* cx, unsigned argc, Value* vp); 40 41 static bool byteLengthGetterImpl(JSContext* cx, const CallArgs& args); 42 static bool byteLengthGetter(JSContext* cx, unsigned argc, Value* vp); 43 44 static bool byteOffsetGetterImpl(JSContext* cx, const CallArgs& args); 45 static bool byteOffsetGetter(JSContext* cx, unsigned argc, Value* vp); 46 47 static bool getAndCheckConstructorArgs(JSContext* cx, HandleObject bufobj, 48 const CallArgs& args, 49 size_t* byteOffsetPtr, 50 size_t* byteLengthPtr, 51 AutoLength* autoLengthPtr); 52 static bool constructSameCompartment(JSContext* cx, HandleObject bufobj, 53 const CallArgs& args); 54 static bool constructWrapped(JSContext* cx, HandleObject bufobj, 55 const CallArgs& args); 56 57 static DataViewObject* create( 58 JSContext* cx, size_t byteOffset, size_t byteLength, 59 Handle<ArrayBufferObjectMaybeShared*> arrayBuffer, HandleObject proto); 60 61 public: 62 static const JSClass protoClass_; 63 64 /** 65 * Return the current byteLength, or |Nothing| if the DataView is detached or 66 * out-of-bounds. 67 */ 68 mozilla::Maybe<size_t> byteLength() { 69 return ArrayBufferViewObject::length(); 70 } 71 72 template <typename NativeType> 73 static bool offsetIsInBounds(uint64_t offset, size_t byteLength) { 74 return offsetIsInBounds(sizeof(NativeType), offset, byteLength); 75 } 76 static bool offsetIsInBounds(uint32_t byteSize, uint64_t offset, 77 size_t byteLength) { 78 MOZ_ASSERT(byteSize <= 8); 79 mozilla::CheckedInt<uint64_t> endOffset(offset); 80 endOffset += byteSize; 81 return endOffset.isValid() && endOffset.value() <= byteLength; 82 } 83 84 static bool construct(JSContext* cx, unsigned argc, Value* vp); 85 86 static bool getInt8Impl(JSContext* cx, const CallArgs& args); 87 static bool fun_getInt8(JSContext* cx, unsigned argc, Value* vp); 88 89 static bool getUint8Impl(JSContext* cx, const CallArgs& args); 90 static bool fun_getUint8(JSContext* cx, unsigned argc, Value* vp); 91 92 static bool getInt16Impl(JSContext* cx, const CallArgs& args); 93 static bool fun_getInt16(JSContext* cx, unsigned argc, Value* vp); 94 95 static bool getUint16Impl(JSContext* cx, const CallArgs& args); 96 static bool fun_getUint16(JSContext* cx, unsigned argc, Value* vp); 97 98 static bool getInt32Impl(JSContext* cx, const CallArgs& args); 99 static bool fun_getInt32(JSContext* cx, unsigned argc, Value* vp); 100 101 static bool getUint32Impl(JSContext* cx, const CallArgs& args); 102 static bool fun_getUint32(JSContext* cx, unsigned argc, Value* vp); 103 104 static bool getBigInt64Impl(JSContext* cx, const CallArgs& args); 105 static bool fun_getBigInt64(JSContext* cx, unsigned argc, Value* vp); 106 107 static bool getBigUint64Impl(JSContext* cx, const CallArgs& args); 108 static bool fun_getBigUint64(JSContext* cx, unsigned argc, Value* vp); 109 110 static bool getFloat16Impl(JSContext* cx, const CallArgs& args); 111 static bool fun_getFloat16(JSContext* cx, unsigned argc, Value* vp); 112 113 static bool getFloat32Impl(JSContext* cx, const CallArgs& args); 114 static bool fun_getFloat32(JSContext* cx, unsigned argc, Value* vp); 115 116 static bool getFloat64Impl(JSContext* cx, const CallArgs& args); 117 static bool fun_getFloat64(JSContext* cx, unsigned argc, Value* vp); 118 119 static bool setInt8Impl(JSContext* cx, const CallArgs& args); 120 static bool fun_setInt8(JSContext* cx, unsigned argc, Value* vp); 121 122 static bool setUint8Impl(JSContext* cx, const CallArgs& args); 123 static bool fun_setUint8(JSContext* cx, unsigned argc, Value* vp); 124 125 static bool setInt16Impl(JSContext* cx, const CallArgs& args); 126 static bool fun_setInt16(JSContext* cx, unsigned argc, Value* vp); 127 128 static bool setUint16Impl(JSContext* cx, const CallArgs& args); 129 static bool fun_setUint16(JSContext* cx, unsigned argc, Value* vp); 130 131 static bool setInt32Impl(JSContext* cx, const CallArgs& args); 132 static bool fun_setInt32(JSContext* cx, unsigned argc, Value* vp); 133 134 static bool setUint32Impl(JSContext* cx, const CallArgs& args); 135 static bool fun_setUint32(JSContext* cx, unsigned argc, Value* vp); 136 137 static bool setBigInt64Impl(JSContext* cx, const CallArgs& args); 138 static bool fun_setBigInt64(JSContext* cx, unsigned argc, Value* vp); 139 140 static bool setBigUint64Impl(JSContext* cx, const CallArgs& args); 141 static bool fun_setBigUint64(JSContext* cx, unsigned argc, Value* vp); 142 143 static bool setFloat16Impl(JSContext* cx, const CallArgs& args); 144 static bool fun_setFloat16(JSContext* cx, unsigned argc, Value* vp); 145 146 static bool setFloat32Impl(JSContext* cx, const CallArgs& args); 147 static bool fun_setFloat32(JSContext* cx, unsigned argc, Value* vp); 148 149 static bool setFloat64Impl(JSContext* cx, const CallArgs& args); 150 static bool fun_setFloat64(JSContext* cx, unsigned argc, Value* vp); 151 152 template <typename NativeType> 153 NativeType read(uint64_t offset, size_t length, bool isLittleEndian); 154 155 template <typename NativeType> 156 static bool read(JSContext* cx, Handle<DataViewObject*> obj, 157 const CallArgs& args, NativeType* val); 158 template <typename NativeType> 159 static bool write(JSContext* cx, Handle<DataViewObject*> obj, 160 const CallArgs& args); 161 162 private: 163 static const JSFunctionSpec methods[]; 164 static const JSPropertySpec properties[]; 165 }; 166 167 /** 168 * DataView whose buffer is a fixed-length (Shared)ArrayBuffer object. 169 */ 170 class FixedLengthDataViewObject : public DataViewObject { 171 public: 172 static const JSClass class_; 173 }; 174 175 /** 176 * DataView whose buffer is a resizable (Shared)ArrayBuffer object. 177 */ 178 class ResizableDataViewObject : public DataViewObject { 179 friend class DataViewObject; 180 181 static ResizableDataViewObject* create( 182 JSContext* cx, size_t byteOffset, size_t byteLength, 183 AutoLength autoLength, Handle<ArrayBufferObjectMaybeShared*> arrayBuffer, 184 HandleObject proto); 185 186 public: 187 static const uint8_t RESERVED_SLOTS = RESIZABLE_RESERVED_SLOTS; 188 189 static const JSClass class_; 190 }; 191 192 /** 193 * DataView whose buffer is an immutable ArrayBuffer object. 194 */ 195 class ImmutableDataViewObject : public DataViewObject { 196 friend class DataViewObject; 197 198 static ImmutableDataViewObject* create( 199 JSContext* cx, size_t byteOffset, size_t byteLength, 200 Handle<ArrayBufferObjectMaybeShared*> arrayBuffer, HandleObject proto); 201 202 public: 203 static const JSClass class_; 204 }; 205 206 // For structured cloning. 207 JSObject* NewDataView(JSContext* cx, HandleObject buffer, size_t byteOffset); 208 209 } // namespace js 210 211 template <> 212 inline bool JSObject::is<js::DataViewObject>() const { 213 return is<js::FixedLengthDataViewObject>() || 214 is<js::ResizableDataViewObject>() || is<js::ImmutableDataViewObject>(); 215 } 216 217 #endif /* vm_DataViewObject_h */