Skip to content

Commit

Permalink
Use qtbase add/sub/mul with overflow implementations.
Browse files Browse the repository at this point in the history
Those use compiler intrinsics when available. If not, the same code that
was previously in qtdeclarative is used.

Depends on 5ff7a3d96e0ce0dcb3d388b53d038cdd40c7a975 in qtbase.

Change-Id: I8adf1a9d368ffc4e368260de518725ed7be6d2b8
Reviewed-by: Lars Knoll <lars.knoll@theqtcompany.com>
  • Loading branch information
Erik Verbruggen authored and Simon Hausmann committed Nov 27, 2015
1 parent 77de21f commit c3a818d
Show file tree
Hide file tree
Showing 2 changed files with 11 additions and 64 deletions.
73 changes: 10 additions & 63 deletions src/qml/jsruntime/qv4math_p.h
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@
#include <qglobal.h>

#include <QtCore/qnumeric.h>
#include <QtCore/private/qnumeric_p.h>
#include <cmath>

#if defined(Q_CC_GNU)
Expand All @@ -59,84 +60,30 @@ QT_BEGIN_NAMESPACE

namespace QV4 {

#if defined(Q_CC_GNU) && defined(Q_PROCESSOR_X86)

static inline QMLJS_READONLY ReturnedValue add_int32(int a, int b)
{
quint8 overflow = 0;
int aa = a;

asm ("addl %2, %1\n"
"seto %0"
: "=q" (overflow), "=r" (aa)
: "r" (b), "1" (aa)
: "cc"
);
if (Q_UNLIKELY(overflow))
int result;
if (Q_UNLIKELY(add_overflow(a, b, &result)))
return Primitive::fromDouble(static_cast<double>(a) + b).asReturnedValue();
return Primitive::fromInt32(aa).asReturnedValue();
return Primitive::fromInt32(result).asReturnedValue();
}

static inline QMLJS_READONLY ReturnedValue sub_int32(int a, int b)
{
quint8 overflow = 0;
int aa = a;

asm ("subl %2, %1\n"
"seto %0"
: "=q" (overflow), "=r" (aa)
: "r" (b), "1" (aa)
: "cc"
);
if (Q_UNLIKELY(overflow))
int result;
if (Q_UNLIKELY(sub_overflow(a, b, &result)))
return Primitive::fromDouble(static_cast<double>(a) - b).asReturnedValue();
return Primitive::fromInt32(aa).asReturnedValue();
return Primitive::fromInt32(result).asReturnedValue();
}

static inline QMLJS_READONLY ReturnedValue mul_int32(int a, int b)
{
quint8 overflow = 0;
int aa = a;

asm ("imul %2, %1\n"
"setc %0"
: "=q" (overflow), "=r" (aa)
: "r" (b), "1" (aa)
: "cc"
);
if (Q_UNLIKELY(overflow))
int result;
if (Q_UNLIKELY(mul_overflow(a, b, &result)))
return Primitive::fromDouble(static_cast<double>(a) * b).asReturnedValue();
return Primitive::fromInt32(aa).asReturnedValue();
}

#else

static inline QMLJS_READONLY ReturnedValue add_int32(int a, int b)
{
qint64 result = static_cast<qint64>(a) + b;
if (Q_UNLIKELY(result > INT_MAX || result < INT_MIN))
return Primitive::fromDouble(static_cast<double>(a) + b).asReturnedValue();
return Primitive::fromInt32(static_cast<int>(result)).asReturnedValue();
return Primitive::fromInt32(result).asReturnedValue();
}

static inline QMLJS_READONLY ReturnedValue sub_int32(int a, int b)
{
qint64 result = static_cast<qint64>(a) - b;
if (Q_UNLIKELY(result > INT_MAX || result < INT_MIN))
return Primitive::fromDouble(static_cast<double>(a) - b).asReturnedValue();
return Primitive::fromInt32(static_cast<int>(result)).asReturnedValue();
}

static inline QMLJS_READONLY ReturnedValue mul_int32(int a, int b)
{
qint64 result = static_cast<qint64>(a) * b;
if (Q_UNLIKELY(result > INT_MAX || result < INT_MIN))
return Primitive::fromDouble(static_cast<double>(a) * b).asReturnedValue();
return Primitive::fromInt32(static_cast<int>(result)).asReturnedValue();
}

#endif

}

QT_END_NAMESPACE
Expand Down
2 changes: 1 addition & 1 deletion src/qmldevtools/qmldevtools.pro
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
option(host_build)
TARGET = QtQmlDevTools
QT = core
QT = core-private
CONFIG += static internal_module qmldevtools_build

# Don't use pch because the auto-generated header refers to QtBootstrap,
Expand Down

0 comments on commit c3a818d

Please sign in to comment.