Example #1
0
FLOAT                               /*{ ret - floor(x)}*/
_floorf(
    FLOAT x                         /*{ (i) - value for which to compute floorf }*/
)
{
    FLOAT y;

    /*{ y = |x| }*/
    y = x;
    if (x < (FLOAT)0.0)
    {
        y = -y;
    }

    /*{ if x > 2^24 (max 23-bit int), result = x }*/
    if (y >= (FLOAT)16777216.0)
    {
        return x;
    }

    /*{ y = truncate(x) }*/
    y = TO_FLOAT(TO_LONG(x));

    /*{ if y > x, result = result - 1.0 }*/
    if (y > x)
    {
        y = SUB(y, 1.0);
    }

    return y;
}
Example #2
0
FLOAT                      /*{ ret - modf(x)}*/
_modff(
    FLOAT x,               /*{ (i) - value for which to compute modff }*/
    FLOAT *i               /*{ (o) - address to which integer part is written }*/
)
{
    FLOAT y;
    FLOAT fract;

    /*{ y = |x| }*/
    y = x;
    if (x < (FLOAT)0.0)
    {
        y = -y;
    }

    /*{ if |x| > 2^24 (max 23-bit int) }*/
    if (y >= (FLOAT)16777216.0)
    {
        /*{ int = x }*/
        /*{ return fract = 0.0 }*/
        *i = x;
        return (FLOAT)0.0;
    }

    /*{ if |x| < 1 }*/
    if (y < (FLOAT)1.0)
    {
        /*{ int = 0 }*/
        /*{ return fract = x }*/
        *i = (FLOAT)0.0;
        return x;
    }

    /*{ y = truncate(|x|) }*/
    y = TO_FLOAT(TO_LONG(y));

    /*{ if x < 0, y = -y }*/
    if (x < (FLOAT)0.0)
    {
        y = -y;
    }

    /*{ fract = x - y }*/
    fract = SUB(x, y);

    /*{ *i = y }*/
    *i = y;

    return fract;
}
Example #3
0
DOUBLE                            /*{ ret - cotd(x)       }*/
cotd
(
  DOUBLE x                        /*{ (i) - input value x }*/
)
{
    LONG n;
    DOUBLE xn;
    DOUBLE f, g;
    DOUBLE x_int, x_fract;
    DOUBLE result;
    DOUBLE xnum, xden;

    /*{ If x is outside the domain or zero, return 0.0 }*/
    if ((x > COT64_X_MAX) || (x < -COT64_X_MAX) || (x == 0.0L))
    {
        return 0.0L;
    }

    /*{ split x into x_int and x_fract for better argument reduction }*/
    x_int = TO_DOUBLE(TO_LONG(x));
    x_fract = SUBD(x, x_int);

    /*{ Reduce the input to range between -PI/4, PI/4 }*/
    /*{!INDENT}*/
    /*{ n = Rounded long x/(PI/2) }*/
    if (x > 0.0)
    {
        n = TO_LONG(ADDD(MPYD(x, INV_PI_2), 0.5));
    }
    else
    {
        n = TO_LONG(ADDD(MPYD(x, INV_PI_2), -0.5));
    }

    /*{ xn = (double)n }*/
    xn = TO_DOUBLE(n);

    /*{ f = x - xn*PI  }*/
    /* (using higher precision computation) */
    f = SUBD(x_int, MPYD(xn, PI_2_DC1));
    f = ADDD(f, x_fract);
    f = SUBD(f, MPYD(xn, PI_2_DC2));
    f = SUBD(f, MPYD(xn, PI_2_DC3));
    /*{!OUTDENT}*/

    if (f < 0.0L)
    {
        g = -f;
    }
    else
    {
        g = f;
    }
    /*{ If |f| < eps }*/
    if (g < EPS_DOUBLE)
    {
        /*{ if n is odd, return -f }*/
        if (n & 0x0001)
        {
            result = -f;
        }
        /*{ if n is even, return 1/f }*/
        else
        {
            result = DIVD(1.0L, f);
        }            
        return result;
    }

    /*{ g = f * f }*/
    g = MPYD(f, f);

    /*{ Compute sin approximation on reduced argument }*/
    /*{!INDENT}*/
    /*{ xnum = (((g * p3 + p2) * g + p1) * g * f + f }*/
    xnum = MPYD(g, TANDP_COEF3);
    xnum = ADDD(xnum, TANDP_COEF2);
    xnum = MPYD(xnum, g);
    xnum = ADDD(xnum, TANDP_COEF1);
    xnum = MPYD(xnum, g);
    xnum = MPYD(xnum, f);
    xnum = ADDD(xnum, f);

    /*{ xden = (((g * q4 + q3) * g + q2) * g +q1) * g + q0 }*/
    xden = MPYD(g, TANDQ_COEF4);
    xden = ADDD(xden, TANDQ_COEF3);
    xden = MPYD(xden, g);
    xden = ADDD(xden, TANDQ_COEF2);
    xden = MPYD(xden, g);
    xden = ADDD(xden, TANDQ_COEF1);
    xden = MPYD(xden, g);
    xden = ADDD(xden, TANDQ_COEF0);
    /*{!OUTDENT}*/

    /*{ if n is odd, result = -xnum/xden }*/
    if (n & 0x0001)
    {
        xnum = -xnum;
    }
    /*{ else n is even, result = xden/xnum }*/
    else
    {
        result = xden;
        xden = xnum;
        xnum = result;
    }            
    result = DIVD(xnum, xden);

    /*{ return result }*/
    return result;
}
Example #4
0
DOUBLE                            /*{ ret - cosd(x)       }*/
cosd
(
  DOUBLE x                        /*{ (i) - input value x }*/
)
{
    LONG n;
    DOUBLE y;
    DOUBLE xn;
    DOUBLE x_int, x_fract;
    DOUBLE f, g, result;
    int sign = 1;

    /*{ x = |x| (since cos(-x) == cos(x)) }*/
    if (x < 0.0L)
    {
        x = -x;
    }

    /*{ y = |x| + PI/2 }*/
    y = ADDD(x, PI_2);

    /*{ If x is outside domain, return 0.0 }*/
    if (y > COS64_X_MAX)
    {
        return 0.0L;
    }

    /*{ Reduce the input to range between -PI/2, PI/2 }*/
    /*{!INDENT}*/
    /*{ split x into x_int and x_fract for better argument reduction }*/
    x_int = TO_DOUBLE(TO_LONG(x));
    x_fract = SUBD(x, x_int);

    /*{ xn = Rounded long y/PI }*/
    n = TO_LONG(ADDD(MPYD(y, INV_PI), 0.5));
    xn = TO_DOUBLE(n);

    /*{ subtract 0.5 from xn  }*/
    /* (more accurate than adding PI/2 to input argument) */
    xn = SUBD(xn, 0.5L);


    /*{ f = x - xn*PI  }*/
    /* (using higher precision computation) */
    f = SUBD(x_int, MPYD(xn, PI_DC1));
    f = ADDD(f, x_fract);
    f = SUBD(f, MPYD(xn, PI_DC2));
    f = SUBD(f, MPYD(xn, PI_DC3));
    /*{!OUTDENT}*/

    /*{ sign = 1 }*/
    /*{ If n is odd, sign = -1 }*/
    if (n & 0x0001)
    {
        sign = -sign;
    }

    /*{ If |f| < eps, return f }*/
    if (f < 0.0L)
    {
        g = -f;
    }
    else
    {
        g = f;
    }

    if (g < EPS_DOUBLE)
    {
        result = f;
        if (sign < 0)
        {
            result = -result;
        }
        return result;
    }

    /*{ g = f * f }*/
    g = MPYD(f, f);

    /*{ Compute sin approximation }*/
    /*{!INDENT}*/
    /*{ result = ((((((((g * C8 + C7) * g + C6) * g + C5) * g + 
                      C4) * g + C3) * g + C2) * g + C1) * g) * f + f }*/
    result = MPYD(g, SIND_COEF8);
    result = ADDD(result, SIND_COEF7);
    result = MPYD(result, g);
    result = ADDD(result, SIND_COEF6);
    result = MPYD(result, g);
    result = ADDD(result, SIND_COEF5);
    result = MPYD(result, g);
    result = ADDD(result, SIND_COEF4);
    result = MPYD(result, g);
    result = ADDD(result, SIND_COEF3);
    result = MPYD(result, g);
    result = ADDD(result, SIND_COEF2);
    result = MPYD(result, g);
    result = ADDD(result, SIND_COEF1);
    result = MPYD(result, g);

    result = MPYD(result, f);
    result = ADDD(result, f);
    /*{!OUTDENT}*/

    /*{ if sign < 0, result = -result }*/
    if (sign < 0)
    {
        result = -result;
    }
    /* make sure -1.0 <= result <= 1.0 */
    if (result > 1.0L) {
      result = 1.0L;
    }
    else if (result < -1.0L) {
      result = -1.0L;
    }
    /*{ return result }*/
    return (result);
}
Example #5
0
/**
 * Evaluate the code and return the value
 * @return
 */
QVariant PythonScript::evaluateImpl() {
  ScopedPythonGIL lock;
  PyObject *compiledCode = this->compileToByteCode(true);
  if (!compiledCode) {
    return QVariant("");
  }
  PyObject *pyret;
  beginStdoutRedirect();
  if (PyCallable_Check(compiledCode)) {
    PyObject *empty_tuple = PyTuple_New(0);
    pyret = PyObject_Call(compiledCode, empty_tuple, localDict);
    Py_DECREF(empty_tuple);
  } else {
    pyret = PyEval_EvalCode(CODE_OBJECT(compiledCode), localDict, localDict);
  }
  endStdoutRedirect();
  if (!pyret) {
    if (PyErr_ExceptionMatches(PyExc_ValueError) ||
        PyErr_ExceptionMatches(PyExc_ZeroDivisionError)) {
      PyErr_Clear(); // silently ignore errors
      return QVariant("");
    } else {
      emit_error();
      return QVariant();
    }
  }

  QVariant qret = QVariant();
  /* None */
  if (pyret == Py_None) {
    qret = QVariant("");
  }
  /* numeric types */
  else if (PyFloat_Check(pyret)) {
    qret = QVariant(PyFloat_AS_DOUBLE(pyret));
  } else if (INT_CHECK(pyret)) {
    qret = QVariant((qlonglong)TO_LONG(pyret));
  }
#if !defined(IS_PY3K)
  else if (PyLong_Check(pyret)) {
    qret = QVariant((qlonglong)PyLong_AsLongLong(pyret));
  }
#endif
  else if (PyNumber_Check(pyret)) {
    PyObject *number = PyNumber_Float(pyret);
    if (number) {
      qret = QVariant(PyFloat_AS_DOUBLE(number));
      Py_DECREF(number);
    }
  }
  /* bool */
  else if (PyBool_Check(pyret)) {
    qret = QVariant(pyret == Py_True);
  }
  // could handle advanced types (such as PyList->QValueList) here if needed
  /* fallback: try to convert to (unicode) string */
  if (!qret.isValid()) {
#if defined(IS_PY3K)
    // In 3 everything is unicode
    PyObject *pystring = PyObject_Str(pyret);
    if (pystring) {
      qret = QVariant(QString::fromUtf8(_PyUnicode_AsString(pystring)));
    }
#else
    PyObject *pystring = PyObject_Unicode(pyret);
    if (pystring) {
      PyObject *asUTF8 =
          PyUnicode_EncodeUTF8(PyUnicode_AS_UNICODE(pystring),
                               (int)PyUnicode_GET_DATA_SIZE(pystring), nullptr);
      Py_DECREF(pystring);
      if (asUTF8) {
        qret = QVariant(QString::fromUtf8(PyString_AS_STRING(asUTF8)));
        Py_DECREF(asUTF8);
      } else if ((pystring = PyObject_Str(pyret))) {
        qret = QVariant(QString(PyString_AS_STRING(pystring)));
        Py_DECREF(pystring);
      }
    }
#endif
  }
  Py_DECREF(pyret);
  if (PyErr_Occurred()) {
    if (PyErr_ExceptionMatches(PyExc_ValueError) ||
        PyErr_ExceptionMatches(PyExc_ZeroDivisionError)) {
      PyErr_Clear(); // silently ignore errors
      return QVariant("");
    } else {
      emit_error();
    }
    return QVariant();
  }
  return qret;
}
Example #6
0
/**
 * This emits the error signal and resets the error state
 * of the python interpreter.
 */
void PythonScript::emit_error() {
  // gil is necessary so other things don't continue
  ScopedPythonGIL lock;

  // return early if nothing happened
  if (!PyErr_Occurred()) {
    emit finished(MSG_FINISHED);
    return;
  }
  // get the error information out
  PyObject *exception(nullptr), *value(nullptr), *traceback(nullptr);
  PyErr_Fetch(&exception, &value, &traceback);

  // special check for system exceptions
  if (bool(exception) &&
      PyErr_GivenExceptionMatches(exception, PyExc_SystemExit) &&
      PyObject_HasAttrString(exception, "code")) {
    // value is the return code handed to sys.exit
    long code = 0;
    if (bool(value) && INT_CHECK(value)) {
      code = TO_LONG(value);
    }

    // if we are returning 0 then cleanup and return
    if (code == 0) {
      // maybe shouldn't clear the error, but for now this
      // is the agreed upon behavior
      PyErr_Clear();
      Py_XDECREF(traceback);
      Py_XDECREF(exception);
      Py_XDECREF(value);
      emit finished(MSG_FINISHED);
      return;
    }
  }

  // prework on the exception handling
  PyErr_NormalizeException(&exception, &value, &traceback);
  PyErr_Clear();

  // convert the traceback into something useful
  int lineNumber = 0;
  QString filename;
  if (traceback) {
    PyTracebackObject *tb = (PyTracebackObject *)traceback;
    lineNumber = tb->tb_lineno;
    filename = TO_CSTRING(tb->tb_frame->f_code->co_filename);
  }

  // the error message is the full (formated) traceback
  PyObject *str_repr = PyObject_Str(value);
  QString message;
  QTextStream msgStream(&message);
  if (value && str_repr) {
    if (exception == PyExc_SyntaxError) {
      msgStream << constructSyntaxErrorStr(value);
    } else {
      QString excTypeName(
          value->ob_type
              ->tp_name); // This is fully qualified with the module name
      excTypeName = excTypeName.section(".", -1);
      msgStream << excTypeName << ": " << TO_CSTRING(str_repr);
    }

  } else {
    msgStream << "Unknown exception has occurred.";
  }
  tracebackToMsg(msgStream, (PyTracebackObject *)(traceback));
  msgStream << "\n";

  Py_XDECREF(traceback);
  Py_XDECREF(exception);
  Py_XDECREF(value);

  emit error(msgStream.readAll(), filename, lineNumber);
}