mirror of
https://github.com/overte-org/overte.git
synced 2025-08-09 04:37:48 +02:00
Fixed exceptions/endian issues with DataViews
This commit is contained in:
parent
49302b2340
commit
28438d66b1
3 changed files with 68 additions and 21 deletions
|
@ -54,15 +54,32 @@ QScriptValue DataViewClass::construct(QScriptContext *context, QScriptEngine *en
|
||||||
}
|
}
|
||||||
|
|
||||||
QScriptValue bufferArg = context->argument(0);
|
QScriptValue bufferArg = context->argument(0);
|
||||||
QScriptValue byteOffsetArg = (context->argumentCount() >= 2) ? context->argument(1) : QScriptValue(-1);
|
QScriptValue byteOffsetArg = (context->argumentCount() >= 2) ? context->argument(1) : QScriptValue();
|
||||||
QScriptValue byteLengthArg = (context->argumentCount() >= 3) ? context->argument(2) : QScriptValue(-1);
|
QScriptValue byteLengthArg = (context->argumentCount() >= 3) ? context->argument(2) : QScriptValue();
|
||||||
|
|
||||||
QByteArray* arrayBuffer = (bufferArg.isValid()) ? qscriptvalue_cast<QByteArray*>(bufferArg.data()) :NULL;
|
QByteArray* arrayBuffer = (bufferArg.isValid()) ? qscriptvalue_cast<QByteArray*>(bufferArg.data()) :NULL;
|
||||||
if (!arrayBuffer) {
|
if (!arrayBuffer) {
|
||||||
|
engine->evaluate("throw \"TypeError: 1st argument not a ArrayBuffer\"");
|
||||||
return QScriptValue();
|
return QScriptValue();
|
||||||
}
|
}
|
||||||
|
if (byteOffsetArg.isNumber() &&
|
||||||
|
(byteOffsetArg.toInt32() < 0 ||
|
||||||
|
byteOffsetArg.toInt32() >= arrayBuffer->size())) {
|
||||||
|
engine->evaluate("throw \"RangeError: byteOffset out of range\"");
|
||||||
|
return QScriptValue();
|
||||||
|
}
|
||||||
|
if (byteLengthArg.isNumber() &&
|
||||||
|
(byteLengthArg.toInt32() < 0 ||
|
||||||
|
byteOffsetArg.toInt32() + byteLengthArg.toInt32() > arrayBuffer->size())) {
|
||||||
|
engine->evaluate("throw \"RangeError: byteLength out of range\"");
|
||||||
|
return QScriptValue();
|
||||||
|
}
|
||||||
|
|
||||||
QScriptValue newObject = cls->newInstance(bufferArg, byteOffsetArg.toInt32(), byteLengthArg.toInt32());
|
QScriptValue newObject = cls->newInstance(bufferArg,
|
||||||
|
(byteOffsetArg.isNumber()) ? byteOffsetArg.toInt32()
|
||||||
|
: 0,
|
||||||
|
(byteLengthArg.isNumber()) ? byteLengthArg.toInt32()
|
||||||
|
: arrayBuffer->size());
|
||||||
|
|
||||||
if (context->isCalledAsConstructor()) {
|
if (context->isCalledAsConstructor()) {
|
||||||
context->setThisObject(newObject);
|
context->setThisObject(newObject);
|
||||||
|
|
|
@ -18,7 +18,7 @@ class DataViewClass : public ArrayBufferViewClass {
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
public:
|
public:
|
||||||
DataViewClass(QScriptEngine* engine);
|
DataViewClass(QScriptEngine* engine);
|
||||||
QScriptValue newInstance(QScriptValue buffer, quint32 byteOffset = -1, quint32 byteLength = -1);
|
QScriptValue newInstance(QScriptValue buffer, quint32 byteOffset, quint32 byteLength);
|
||||||
|
|
||||||
QString name() const;
|
QString name() const;
|
||||||
QScriptValue prototype() const;
|
QScriptValue prototype() const;
|
||||||
|
|
|
@ -29,10 +29,10 @@ QByteArray* DataViewPrototype::thisArrayBuffer() const {
|
||||||
bool DataViewPrototype::realOffset(quint32& offset, size_t size) const {
|
bool DataViewPrototype::realOffset(quint32& offset, size_t size) const {
|
||||||
quint32 viewOffset = thisObject().data().property(BYTE_OFFSET_PROPERTY_NAME).toInt32();
|
quint32 viewOffset = thisObject().data().property(BYTE_OFFSET_PROPERTY_NAME).toInt32();
|
||||||
quint32 viewLength = thisObject().data().property(BYTE_LENGTH_PROPERTY_NAME).toInt32();
|
quint32 viewLength = thisObject().data().property(BYTE_LENGTH_PROPERTY_NAME).toInt32();
|
||||||
qDebug() << "View Offset: " << viewOffset << ", View Lenght: " << viewLength;
|
//qDebug() << "View Offset: " << viewOffset << ", View Lenght: " << viewLength;
|
||||||
qDebug() << "Offset: " << offset << ", Size: " << size;
|
//qDebug() << "Offset: " << offset << ", Size: " << size;
|
||||||
offset += viewOffset;
|
offset += viewOffset;
|
||||||
qDebug() << "New offset: " << offset << ", bool: " << ((offset + size) <= viewOffset + viewLength);
|
//qDebug() << "New offset: " << offset << ", bool: " << ((offset + size) <= viewOffset + viewLength);
|
||||||
return (offset + size) <= viewOffset + viewLength;
|
return (offset + size) <= viewOffset + viewLength;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -47,7 +47,8 @@ qint32 DataViewPrototype::getInt8(quint32 byteOffset) {
|
||||||
stream >> result;
|
stream >> result;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
return 42;
|
thisObject().engine()->evaluate("throw \"RangeError: byteOffset out of range\"");
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
quint32 DataViewPrototype::getUint8(quint32 byteOffset) {
|
quint32 DataViewPrototype::getUint8(quint32 byteOffset) {
|
||||||
|
@ -59,85 +60,92 @@ quint32 DataViewPrototype::getUint8(quint32 byteOffset) {
|
||||||
stream >> result;
|
stream >> result;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
return 42;
|
thisObject().engine()->evaluate("throw \"RangeError: byteOffset out of range\"");
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
qint32 DataViewPrototype::getInt16(quint32 byteOffset, bool littleEndian) {
|
qint32 DataViewPrototype::getInt16(quint32 byteOffset, bool littleEndian) {
|
||||||
if (realOffset(byteOffset, sizeof(qint16))) {
|
if (realOffset(byteOffset, sizeof(qint16))) {
|
||||||
QDataStream stream(*thisArrayBuffer());
|
QDataStream stream(*thisArrayBuffer());
|
||||||
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
qint16 result;
|
qint16 result;
|
||||||
stream >> result;
|
stream >> result;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
return 42;
|
thisObject().engine()->evaluate("throw \"RangeError: byteOffset out of range\"");
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
quint32 DataViewPrototype::getUint16(quint32 byteOffset, bool littleEndian) {
|
quint32 DataViewPrototype::getUint16(quint32 byteOffset, bool littleEndian) {
|
||||||
if (realOffset(byteOffset, sizeof(quint16))) {
|
if (realOffset(byteOffset, sizeof(quint16))) {
|
||||||
QDataStream stream(*thisArrayBuffer());
|
QDataStream stream(*thisArrayBuffer());
|
||||||
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
quint16 result;
|
quint16 result;
|
||||||
stream >> result;
|
stream >> result;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
return 42;
|
thisObject().engine()->evaluate("throw \"RangeError: byteOffset out of range\"");
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
qint32 DataViewPrototype::getInt32(quint32 byteOffset, bool littleEndian) {
|
qint32 DataViewPrototype::getInt32(quint32 byteOffset, bool littleEndian) {
|
||||||
if (realOffset(byteOffset, sizeof(qint32))) {
|
if (realOffset(byteOffset, sizeof(qint32))) {
|
||||||
QDataStream stream(*thisArrayBuffer());
|
QDataStream stream(*thisArrayBuffer());
|
||||||
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
qint32 result;
|
qint32 result;
|
||||||
stream >> result;
|
stream >> result;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
return 42;
|
thisObject().engine()->evaluate("throw \"RangeError: byteOffset out of range\"");
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
quint32 DataViewPrototype::getUint32(quint32 byteOffset, bool littleEndian) {
|
quint32 DataViewPrototype::getUint32(quint32 byteOffset, bool littleEndian) {
|
||||||
if (realOffset(byteOffset, sizeof(quint32))) {
|
if (realOffset(byteOffset, sizeof(quint32))) {
|
||||||
QDataStream stream(*thisArrayBuffer());
|
QDataStream stream(*thisArrayBuffer());
|
||||||
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
quint32 result;
|
quint32 result;
|
||||||
stream >> result;
|
stream >> result;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
return 42;
|
thisObject().engine()->evaluate("throw \"RangeError: byteOffset out of range\"");
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
float DataViewPrototype::getFloat32(quint32 byteOffset, bool littleEndian) {
|
float DataViewPrototype::getFloat32(quint32 byteOffset, bool littleEndian) {
|
||||||
if (realOffset(byteOffset, sizeof(float))) {
|
if (realOffset(byteOffset, sizeof(float))) {
|
||||||
QDataStream stream(*thisArrayBuffer());
|
QDataStream stream(*thisArrayBuffer());
|
||||||
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
float result;
|
float result;
|
||||||
stream >> result;
|
stream >> result;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
return 42;
|
thisObject().engine()->evaluate("throw \"RangeError: byteOffset out of range\"");
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
double DataViewPrototype::getFloat64(quint32 byteOffset, bool littleEndian) {
|
double DataViewPrototype::getFloat64(quint32 byteOffset, bool littleEndian) {
|
||||||
if (realOffset(byteOffset, sizeof(double))) {
|
if (realOffset(byteOffset, sizeof(double))) {
|
||||||
QDataStream stream(*thisArrayBuffer());
|
QDataStream stream(*thisArrayBuffer());
|
||||||
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
double result;
|
double result;
|
||||||
stream >> result;
|
stream >> result;
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
return 42;
|
thisObject().engine()->evaluate("throw \"RangeError: byteOffset out of range\"");
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
///////////////// SETTERS ////////////////////////////
|
///////////////// SETTERS ////////////////////////////
|
||||||
|
@ -148,6 +156,8 @@ void DataViewPrototype::setInt8(quint32 byteOffset, qint32 value) {
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
|
||||||
stream << (qint8)value;
|
stream << (qint8)value;
|
||||||
|
} else {
|
||||||
|
thisObject().engine()->evaluate("throw \"1RangeError: byteOffset out of range\"");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -157,6 +167,8 @@ void DataViewPrototype::setUint8(quint32 byteOffset, quint32 value) {
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
|
||||||
stream << (quint8)value;
|
stream << (quint8)value;
|
||||||
|
} else {
|
||||||
|
thisObject().engine()->evaluate("throw \"1RangeError: byteOffset out of range\"");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -164,8 +176,11 @@ void DataViewPrototype::setInt16(quint32 byteOffset, qint32 value, bool littleEn
|
||||||
if (realOffset(byteOffset, sizeof(qint16))) {
|
if (realOffset(byteOffset, sizeof(qint16))) {
|
||||||
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
stream << (qint16)value;
|
stream << (qint16)value;
|
||||||
|
} else {
|
||||||
|
thisObject().engine()->evaluate("throw \"1RangeError: byteOffset out of range\"");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -173,8 +188,11 @@ void DataViewPrototype::setUint16(quint32 byteOffset, quint32 value, bool little
|
||||||
if (realOffset(byteOffset, sizeof(quint16))) {
|
if (realOffset(byteOffset, sizeof(quint16))) {
|
||||||
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
stream << (quint16)value;
|
stream << (quint16)value;
|
||||||
|
} else {
|
||||||
|
thisObject().engine()->evaluate("throw \"1RangeError: byteOffset out of range\"");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -182,8 +200,11 @@ void DataViewPrototype::setInt32(quint32 byteOffset, qint32 value, bool littleEn
|
||||||
if (realOffset(byteOffset, sizeof(qint32))) {
|
if (realOffset(byteOffset, sizeof(qint32))) {
|
||||||
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
stream << (qint32)value;
|
stream << (qint32)value;
|
||||||
|
} else {
|
||||||
|
thisObject().engine()->evaluate("throw \"1RangeError: byteOffset out of range\"");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -191,8 +212,11 @@ void DataViewPrototype::setUint32(quint32 byteOffset, quint32 value, bool little
|
||||||
if (realOffset(byteOffset, sizeof(quint32))) {
|
if (realOffset(byteOffset, sizeof(quint32))) {
|
||||||
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
stream << (quint32)value;
|
stream << (quint32)value;
|
||||||
|
} else {
|
||||||
|
thisObject().engine()->evaluate("throw \"1RangeError: byteOffset out of range\"");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -200,8 +224,11 @@ void DataViewPrototype::setFloat32(quint32 byteOffset, float value, bool littleE
|
||||||
if (realOffset(byteOffset, sizeof(float))) {
|
if (realOffset(byteOffset, sizeof(float))) {
|
||||||
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
stream << value;
|
stream << value;
|
||||||
|
} else {
|
||||||
|
thisObject().engine()->evaluate("throw \"1RangeError: byteOffset out of range\"");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -209,8 +236,11 @@ void DataViewPrototype::setFloat64(quint32 byteOffset, double value, bool little
|
||||||
if (realOffset(byteOffset, sizeof(double))) {
|
if (realOffset(byteOffset, sizeof(double))) {
|
||||||
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
QDataStream stream(thisArrayBuffer(), QIODevice::ReadWrite);
|
||||||
stream.skipRawData(byteOffset);
|
stream.skipRawData(byteOffset);
|
||||||
|
stream.setByteOrder((littleEndian) ? QDataStream::LittleEndian : QDataStream::BigEndian);
|
||||||
|
|
||||||
stream << value;
|
stream << value;
|
||||||
|
} else {
|
||||||
|
thisObject().engine()->evaluate("throw \"1RangeError: byteOffset out of range\"");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue