Add Chromium-only Blender WebEngine parity work
This commit is contained in:
663
blender-5.2.0/extern/mantaflow/helper/pwrapper/pconvert.cpp
vendored
Normal file
663
blender-5.2.0/extern/mantaflow/helper/pwrapper/pconvert.cpp
vendored
Normal file
@@ -0,0 +1,663 @@
|
||||
/******************************************************************************
|
||||
*
|
||||
* MantaFlow fluid solver framework
|
||||
* Copyright 2011 Tobias Pfaff, Nils Thuerey
|
||||
*
|
||||
* This program is free software, distributed under the terms of the
|
||||
* Apache License, Version 2.0
|
||||
* http://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Python argument wrappers and conversion tools
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "pythonInclude.h"
|
||||
#include <sstream>
|
||||
#include <algorithm>
|
||||
#include "vectorbase.h"
|
||||
#include "manta.h"
|
||||
|
||||
using namespace std;
|
||||
|
||||
//******************************************************************************
|
||||
// Explicit definition and instantiation of python object converters
|
||||
|
||||
namespace Manta {
|
||||
|
||||
extern PyTypeObject PbVec3Type;
|
||||
extern PyTypeObject PbVec4Type;
|
||||
|
||||
struct PbVec3 {
|
||||
PyObject_HEAD
|
||||
float data[3];
|
||||
};
|
||||
|
||||
struct PbVec4 {
|
||||
PyObject_HEAD
|
||||
float data[4];
|
||||
};
|
||||
|
||||
PyObject *getPyNone()
|
||||
{
|
||||
Py_INCREF(Py_None);
|
||||
return Py_None;
|
||||
}
|
||||
PyObject *incref(PyObject *obj)
|
||||
{
|
||||
Py_INCREF(obj);
|
||||
return obj;
|
||||
}
|
||||
|
||||
/*template<> PyObject* toPy<PyObject*>(PyObject* obj) {
|
||||
return obj;
|
||||
}*/
|
||||
template<> PyObject *toPy<int>(const int &v)
|
||||
{
|
||||
return PyLong_FromLong(v);
|
||||
}
|
||||
/*template<> PyObject* toPy<char*>(const (char*) & val) {
|
||||
return PyUnicode_DecodeLatin1(val,strlen(val),"replace");
|
||||
}*/
|
||||
template<> PyObject *toPy<string>(const string &val)
|
||||
{
|
||||
return PyUnicode_DecodeLatin1(val.c_str(), val.length(), "replace");
|
||||
}
|
||||
template<> PyObject *toPy<float>(const float &v)
|
||||
{
|
||||
return PyFloat_FromDouble(v);
|
||||
}
|
||||
template<> PyObject *toPy<double>(const double &v)
|
||||
{
|
||||
return PyFloat_FromDouble(v);
|
||||
}
|
||||
template<> PyObject *toPy<bool>(const bool &v)
|
||||
{
|
||||
return PyBool_FromLong(v);
|
||||
}
|
||||
template<> PyObject *toPy<Vec3i>(const Vec3i &v)
|
||||
{
|
||||
float x = (float)v.x, y = (float)v.y, z = (float)v.z;
|
||||
return PyObject_CallFunction((PyObject *)&PbVec3Type, (char *)"fff", x, y, z);
|
||||
}
|
||||
template<> PyObject *toPy<Vec3>(const Vec3 &v)
|
||||
{
|
||||
float x = (float)v.x, y = (float)v.y, z = (float)v.z;
|
||||
return PyObject_CallFunction((PyObject *)&PbVec3Type, (char *)"fff", x, y, z);
|
||||
}
|
||||
template<> PyObject *toPy<Vec4i>(const Vec4i &v)
|
||||
{
|
||||
float x = (float)v.x, y = (float)v.y, z = (float)v.z;
|
||||
return PyObject_CallFunction((PyObject *)&PbVec4Type, (char *)"ffff", x, y, z);
|
||||
}
|
||||
template<> PyObject *toPy<Vec4>(const Vec4 &v)
|
||||
{
|
||||
float x = (float)v.x, y = (float)v.y, z = (float)v.z;
|
||||
return PyObject_CallFunction((PyObject *)&PbVec4Type, (char *)"ffff", x, y, z);
|
||||
}
|
||||
template<> PyObject *toPy<PbClass *>(const PbClass_Ptr &obj)
|
||||
{
|
||||
return obj->getPyObject();
|
||||
}
|
||||
template<> PyObject *toPy<std::vector<PbClass *>>(const std::vector<PbClass *> &vec)
|
||||
{
|
||||
PyObject *listObj = PyList_New(vec.size());
|
||||
if (!listObj)
|
||||
throw logic_error("Unable to allocate memory for Python list");
|
||||
for (unsigned int i = 0; i < vec.size(); i++) {
|
||||
PbClass *pb = vec[i];
|
||||
PyObject *item = pb->getPyObject();
|
||||
if (!item) {
|
||||
Py_DECREF(listObj);
|
||||
throw logic_error("Unable to allocate memory for Python list");
|
||||
}
|
||||
PyList_SET_ITEM(listObj, i, item);
|
||||
}
|
||||
return listObj;
|
||||
}
|
||||
template<> PyObject *toPy<std::vector<float>>(const std::vector<float> &vec)
|
||||
{
|
||||
PyObject *listObj = PyList_New(vec.size());
|
||||
if (!listObj)
|
||||
throw logic_error("Unable to allocate memory for Python list");
|
||||
for (unsigned int i = 0; i < vec.size(); i++) {
|
||||
PyObject *item = toPy<float>(vec[i]);
|
||||
if (!item) {
|
||||
Py_DECREF(listObj);
|
||||
throw logic_error("Unable to allocate memory for Python list");
|
||||
}
|
||||
PyList_SET_ITEM(listObj, i, item);
|
||||
}
|
||||
return listObj;
|
||||
}
|
||||
|
||||
template<> float fromPy<float>(PyObject *obj)
|
||||
{
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
if (PyInt_Check(obj))
|
||||
return PyInt_AsLong(obj);
|
||||
#endif
|
||||
if (PyFloat_Check(obj))
|
||||
return PyFloat_AsDouble(obj);
|
||||
if (PyLong_Check(obj))
|
||||
return PyLong_AsDouble(obj);
|
||||
errMsg("argument is not a float");
|
||||
}
|
||||
template<> double fromPy<double>(PyObject *obj)
|
||||
{
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
if (PyInt_Check(obj))
|
||||
return PyInt_AsLong(obj);
|
||||
#endif
|
||||
if (PyFloat_Check(obj))
|
||||
return PyFloat_AsDouble(obj);
|
||||
if (PyLong_Check(obj))
|
||||
return PyLong_AsDouble(obj);
|
||||
errMsg("argument is not a double");
|
||||
}
|
||||
template<> PyObject *fromPy<PyObject *>(PyObject *obj)
|
||||
{
|
||||
return obj;
|
||||
}
|
||||
template<> PbClass *fromPy<PbClass *>(PyObject *obj)
|
||||
{
|
||||
PbClass *pbo = Pb::objFromPy(obj);
|
||||
|
||||
if (!PyType_Check(obj))
|
||||
return pbo;
|
||||
|
||||
const char *tname = ((PyTypeObject *)obj)->tp_name;
|
||||
pbo->setName(tname);
|
||||
|
||||
return pbo;
|
||||
}
|
||||
template<> std::vector<PbClass *> fromPy<std::vector<PbClass *>>(PyObject *obj)
|
||||
{
|
||||
std::vector<PbClass *> vec;
|
||||
if (PyList_Check(obj)) {
|
||||
int sz = PyList_Size(obj);
|
||||
for (int i = 0; i < sz; ++i) {
|
||||
PyObject *lobj = PyList_GetItem(obj, i);
|
||||
vec.push_back(fromPy<PbClass *>(lobj));
|
||||
}
|
||||
}
|
||||
return vec;
|
||||
}
|
||||
template<> std::vector<float> fromPy<std::vector<float>>(PyObject *obj)
|
||||
{
|
||||
std::vector<float> vec;
|
||||
if (PyList_Check(obj)) {
|
||||
int sz = PyList_Size(obj);
|
||||
for (int i = 0; i < sz; ++i) {
|
||||
PyObject *lobj = PyList_GetItem(obj, i);
|
||||
vec.push_back(fromPy<float>(lobj));
|
||||
}
|
||||
}
|
||||
return vec;
|
||||
}
|
||||
template<> int fromPy<int>(PyObject *obj)
|
||||
{
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
if (PyInt_Check(obj))
|
||||
return PyInt_AsLong(obj);
|
||||
#endif
|
||||
if (PyLong_Check(obj))
|
||||
return PyLong_AsDouble(obj);
|
||||
if (PyFloat_Check(obj)) {
|
||||
double a = PyFloat_AsDouble(obj);
|
||||
if (fabs(a - floor(a + 0.5)) > 1e-5)
|
||||
errMsg("argument is not an int");
|
||||
return (int)(a + 0.5);
|
||||
}
|
||||
errMsg("argument is not an int");
|
||||
}
|
||||
template<> string fromPy<string>(PyObject *obj)
|
||||
{
|
||||
if (PyUnicode_Check(obj))
|
||||
#ifdef BLENDER
|
||||
// Blender is completely UTF-8 based
|
||||
return PyBytes_AsString(PyUnicode_AsUTF8String(obj));
|
||||
#else
|
||||
return PyBytes_AsString(PyUnicode_AsLatin1String(obj));
|
||||
#endif
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
else if (PyString_Check(obj))
|
||||
return PyString_AsString(obj);
|
||||
#endif
|
||||
else
|
||||
errMsg("argument is not a string");
|
||||
}
|
||||
template<> const char *fromPy<const char *>(PyObject *obj)
|
||||
{
|
||||
if (PyUnicode_Check(obj))
|
||||
#ifdef BLENDER
|
||||
// Blender is completely UTF-8 based
|
||||
return PyBytes_AsString(PyUnicode_AsUTF8String(obj));
|
||||
#else
|
||||
return PyBytes_AsString(PyUnicode_AsLatin1String(obj));
|
||||
#endif
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
else if (PyString_Check(obj))
|
||||
return PyString_AsString(obj);
|
||||
#endif
|
||||
else
|
||||
errMsg("argument is not a string");
|
||||
}
|
||||
template<> bool fromPy<bool>(PyObject *obj)
|
||||
{
|
||||
if (!PyBool_Check(obj))
|
||||
errMsg("argument is not a boolean");
|
||||
return PyLong_AsLong(obj) != 0;
|
||||
}
|
||||
template<> Vec3 fromPy<Vec3>(PyObject *obj)
|
||||
{
|
||||
if (PyObject_IsInstance(obj, (PyObject *)&PbVec3Type)) {
|
||||
return Vec3(((PbVec3 *)obj)->data);
|
||||
}
|
||||
else if (PyTuple_Check(obj) && PyTuple_Size(obj) == 3) {
|
||||
return Vec3(fromPy<Real>(PyTuple_GetItem(obj, 0)),
|
||||
fromPy<Real>(PyTuple_GetItem(obj, 1)),
|
||||
fromPy<Real>(PyTuple_GetItem(obj, 2)));
|
||||
}
|
||||
errMsg("argument is not a Vec3");
|
||||
}
|
||||
template<> Vec3i fromPy<Vec3i>(PyObject *obj)
|
||||
{
|
||||
if (PyObject_IsInstance(obj, (PyObject *)&PbVec3Type)) {
|
||||
return toVec3iChecked(((PbVec3 *)obj)->data);
|
||||
}
|
||||
else if (PyTuple_Check(obj) && PyTuple_Size(obj) == 3) {
|
||||
return Vec3i(fromPy<int>(PyTuple_GetItem(obj, 0)),
|
||||
fromPy<int>(PyTuple_GetItem(obj, 1)),
|
||||
fromPy<int>(PyTuple_GetItem(obj, 2)));
|
||||
}
|
||||
errMsg("argument is not a Vec3i");
|
||||
}
|
||||
template<> Vec4 fromPy<Vec4>(PyObject *obj)
|
||||
{
|
||||
if (PyObject_IsInstance(obj, (PyObject *)&PbVec4Type)) {
|
||||
return Vec4(((PbVec4 *)obj)->data);
|
||||
}
|
||||
else if (PyTuple_Check(obj) && PyTuple_Size(obj) == 4) {
|
||||
return Vec4(fromPy<Real>(PyTuple_GetItem(obj, 0)),
|
||||
fromPy<Real>(PyTuple_GetItem(obj, 1)),
|
||||
fromPy<Real>(PyTuple_GetItem(obj, 2)),
|
||||
fromPy<Real>(PyTuple_GetItem(obj, 3)));
|
||||
}
|
||||
errMsg("argument is not a Vec4");
|
||||
}
|
||||
template<> Vec4i fromPy<Vec4i>(PyObject *obj)
|
||||
{
|
||||
if (PyObject_IsInstance(obj, (PyObject *)&PbVec4Type)) {
|
||||
return toVec4i(((PbVec4 *)obj)->data);
|
||||
}
|
||||
else if (PyTuple_Check(obj) && PyTuple_Size(obj) == 4) {
|
||||
return Vec4i(fromPy<int>(PyTuple_GetItem(obj, 0)),
|
||||
fromPy<int>(PyTuple_GetItem(obj, 1)),
|
||||
fromPy<int>(PyTuple_GetItem(obj, 2)),
|
||||
fromPy<int>(PyTuple_GetItem(obj, 3)));
|
||||
}
|
||||
errMsg("argument is not a Vec4i");
|
||||
}
|
||||
template<> PbType fromPy<PbType>(PyObject *obj)
|
||||
{
|
||||
PbType pb = {""};
|
||||
if (!PyType_Check(obj))
|
||||
return pb;
|
||||
|
||||
const char *tname = ((PyTypeObject *)obj)->tp_name;
|
||||
pb.S = tname;
|
||||
return pb;
|
||||
}
|
||||
template<> PbTypeVec fromPy<PbTypeVec>(PyObject *obj)
|
||||
{
|
||||
PbTypeVec vec;
|
||||
if (PyType_Check(obj)) {
|
||||
vec.T.push_back(fromPy<PbType>(obj));
|
||||
}
|
||||
else if (PyTuple_Check(obj)) {
|
||||
int sz = PyTuple_Size(obj);
|
||||
for (int i = 0; i < sz; i++)
|
||||
vec.T.push_back(fromPy<PbType>(PyTuple_GetItem(obj, i)));
|
||||
}
|
||||
else
|
||||
errMsg("argument is not a type tuple");
|
||||
return vec;
|
||||
}
|
||||
|
||||
template<class T> T *tmpAlloc(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
if (!tmp)
|
||||
throw Error("dynamic de-ref not supported for this type");
|
||||
|
||||
T *ptr = new T(fromPy<T>(obj));
|
||||
tmp->push_back([ptr]() { delete ptr; });
|
||||
return ptr;
|
||||
}
|
||||
template<> float *fromPyPtr<float>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<float>(obj, tmp);
|
||||
}
|
||||
template<> double *fromPyPtr<double>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<double>(obj, tmp);
|
||||
}
|
||||
template<> int *fromPyPtr<int>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<int>(obj, tmp);
|
||||
}
|
||||
template<> std::string *fromPyPtr<std::string>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<std::string>(obj, tmp);
|
||||
}
|
||||
template<> bool *fromPyPtr<bool>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<bool>(obj, tmp);
|
||||
}
|
||||
template<> Vec3 *fromPyPtr<Vec3>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<Vec3>(obj, tmp);
|
||||
}
|
||||
template<> Vec3i *fromPyPtr<Vec3i>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<Vec3i>(obj, tmp);
|
||||
}
|
||||
template<> Vec4 *fromPyPtr<Vec4>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<Vec4>(obj, tmp);
|
||||
}
|
||||
template<> Vec4i *fromPyPtr<Vec4i>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<Vec4i>(obj, tmp);
|
||||
}
|
||||
template<>
|
||||
std::vector<PbClass *> *fromPyPtr<std::vector<PbClass *>>(PyObject *obj, std::vector<TmpCleanupFn> *tmp)
|
||||
{
|
||||
return tmpAlloc<std::vector<PbClass *>>(obj, tmp);
|
||||
}
|
||||
|
||||
template<> bool isPy<float>(PyObject *obj)
|
||||
{
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
if (PyInt_Check(obj))
|
||||
return true;
|
||||
#endif
|
||||
return PyFloat_Check(obj) || PyLong_Check(obj);
|
||||
}
|
||||
template<> bool isPy<double>(PyObject *obj)
|
||||
{
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
if (PyInt_Check(obj))
|
||||
return true;
|
||||
#endif
|
||||
return PyFloat_Check(obj) || PyLong_Check(obj);
|
||||
}
|
||||
template<> bool isPy<PyObject *>(PyObject *obj)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
template<> bool isPy<int>(PyObject *obj)
|
||||
{
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
if (PyInt_Check(obj))
|
||||
return true;
|
||||
#endif
|
||||
if (PyLong_Check(obj))
|
||||
return true;
|
||||
if (PyFloat_Check(obj)) {
|
||||
double a = PyFloat_AsDouble(obj);
|
||||
return fabs(a - floor(a + 0.5)) < 1e-5;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
template<> bool isPy<string>(PyObject *obj)
|
||||
{
|
||||
if (PyUnicode_Check(obj))
|
||||
return true;
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
if (PyString_Check(obj))
|
||||
return true;
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
template<> bool isPy<const char *>(PyObject *obj)
|
||||
{
|
||||
if (PyUnicode_Check(obj))
|
||||
return true;
|
||||
#if PY_MAJOR_VERSION <= 2
|
||||
if (PyString_Check(obj))
|
||||
return true;
|
||||
#endif
|
||||
return false;
|
||||
}
|
||||
template<> bool isPy<bool>(PyObject *obj)
|
||||
{
|
||||
return PyBool_Check(obj);
|
||||
}
|
||||
template<> bool isPy<Vec3>(PyObject *obj)
|
||||
{
|
||||
if (PyObject_IsInstance(obj, (PyObject *)&PbVec3Type))
|
||||
return true;
|
||||
if (PyTuple_Check(obj) && PyTuple_Size(obj) == 3) {
|
||||
return isPy<Real>(PyTuple_GetItem(obj, 0)) && isPy<Real>(PyTuple_GetItem(obj, 1)) &&
|
||||
isPy<Real>(PyTuple_GetItem(obj, 2));
|
||||
}
|
||||
return false;
|
||||
}
|
||||
template<> bool isPy<Vec3i>(PyObject *obj)
|
||||
{
|
||||
if (PyObject_IsInstance(obj, (PyObject *)&PbVec3Type))
|
||||
return true;
|
||||
if (PyTuple_Check(obj) && PyTuple_Size(obj) == 3) {
|
||||
return isPy<int>(PyTuple_GetItem(obj, 0)) && isPy<int>(PyTuple_GetItem(obj, 1)) &&
|
||||
isPy<int>(PyTuple_GetItem(obj, 2));
|
||||
}
|
||||
return false;
|
||||
}
|
||||
template<> bool isPy<Vec4>(PyObject *obj)
|
||||
{
|
||||
if (PyObject_IsInstance(obj, (PyObject *)&PbVec4Type))
|
||||
return true;
|
||||
if (PyTuple_Check(obj) && PyTuple_Size(obj) == 4) {
|
||||
return isPy<Real>(PyTuple_GetItem(obj, 0)) && isPy<Real>(PyTuple_GetItem(obj, 1)) &&
|
||||
isPy<Real>(PyTuple_GetItem(obj, 2)) && isPy<Real>(PyTuple_GetItem(obj, 3));
|
||||
}
|
||||
return false;
|
||||
}
|
||||
template<> bool isPy<Vec4i>(PyObject *obj)
|
||||
{
|
||||
if (PyObject_IsInstance(obj, (PyObject *)&PbVec4Type))
|
||||
return true;
|
||||
if (PyTuple_Check(obj) && PyTuple_Size(obj) == 4) {
|
||||
return isPy<int>(PyTuple_GetItem(obj, 0)) && isPy<int>(PyTuple_GetItem(obj, 1)) &&
|
||||
isPy<int>(PyTuple_GetItem(obj, 2)) && isPy<int>(PyTuple_GetItem(obj, 3));
|
||||
}
|
||||
return false;
|
||||
}
|
||||
template<> bool isPy<PbType>(PyObject *obj)
|
||||
{
|
||||
return PyType_Check(obj);
|
||||
}
|
||||
template<> bool isPy<std::vector<PbClass *>>(PyObject *obj)
|
||||
{
|
||||
if (PyList_Check(obj))
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
template<> bool isPy<std::vector<float>>(PyObject *obj)
|
||||
{
|
||||
if (PyList_Check(obj))
|
||||
return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
//******************************************************************************
|
||||
// PbArgs class defs
|
||||
|
||||
PbArgs PbArgs::EMPTY(nullptr, nullptr);
|
||||
|
||||
PbArgs::PbArgs(PyObject *linarg, PyObject *dict) : mLinArgs(0), mKwds(0)
|
||||
{
|
||||
setup(linarg, dict);
|
||||
}
|
||||
PbArgs::~PbArgs()
|
||||
{
|
||||
for (auto &fn : mTmpStorageCleanup)
|
||||
fn();
|
||||
mTmpStorageCleanup.clear();
|
||||
}
|
||||
|
||||
void PbArgs::copy(PbArgs &a)
|
||||
{
|
||||
mKwds = a.mKwds;
|
||||
mData = a.mData;
|
||||
mLinData = a.mLinData;
|
||||
mLinArgs = a.mLinArgs;
|
||||
}
|
||||
void PbArgs::clear()
|
||||
{
|
||||
mLinArgs = 0;
|
||||
mKwds = 0;
|
||||
mData.clear();
|
||||
mLinData.clear();
|
||||
}
|
||||
|
||||
PbArgs &PbArgs::operator=(const PbArgs &a)
|
||||
{
|
||||
// mLinArgs = 0;
|
||||
// mKwds = 0;
|
||||
return *this;
|
||||
}
|
||||
|
||||
void PbArgs::setup(PyObject *linarg, PyObject *dict)
|
||||
{
|
||||
if (dict) {
|
||||
PyObject *key, *value;
|
||||
Py_ssize_t pos = 0;
|
||||
while (PyDict_Next(dict, &pos, &key, &value)) {
|
||||
DataElement el;
|
||||
el.obj = value;
|
||||
el.visited = false;
|
||||
mData[fromPy<string>(key)] = el;
|
||||
}
|
||||
mKwds = dict;
|
||||
}
|
||||
if (linarg) {
|
||||
size_t len = PyTuple_Size(linarg);
|
||||
for (size_t i = 0; i < len; i++) {
|
||||
DataElement el;
|
||||
el.obj = PyTuple_GetItem(linarg, i);
|
||||
el.visited = false;
|
||||
mLinData.push_back(el);
|
||||
}
|
||||
mLinArgs = linarg;
|
||||
}
|
||||
}
|
||||
|
||||
void PbArgs::addLinArg(PyObject *obj)
|
||||
{
|
||||
DataElement el = {obj, false};
|
||||
mLinData.push_back(el);
|
||||
}
|
||||
|
||||
void PbArgs::check()
|
||||
{
|
||||
if (has("nocheck"))
|
||||
return;
|
||||
|
||||
for (map<string, DataElement>::iterator it = mData.begin(); it != mData.end(); it++) {
|
||||
if (!it->second.visited)
|
||||
errMsg("Argument '" + it->first + "' unknown");
|
||||
}
|
||||
for (size_t i = 0; i < mLinData.size(); i++) {
|
||||
if (!mLinData[i].visited) {
|
||||
stringstream s;
|
||||
s << "Function does not read argument number #" << i;
|
||||
errMsg(s.str());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
FluidSolver *PbArgs::obtainParent()
|
||||
{
|
||||
FluidSolver *solver = getPtrOpt<FluidSolver>("solver", -1, nullptr);
|
||||
if (solver != 0)
|
||||
return solver;
|
||||
|
||||
for (map<string, DataElement>::iterator it = mData.begin(); it != mData.end(); it++) {
|
||||
PbClass *obj = Pb::objFromPy(it->second.obj);
|
||||
|
||||
if (obj) {
|
||||
if (solver == nullptr)
|
||||
solver = obj->getParent();
|
||||
}
|
||||
}
|
||||
for (vector<DataElement>::iterator it = mLinData.begin(); it != mLinData.end(); it++) {
|
||||
PbClass *obj = Pb::objFromPy(it->obj);
|
||||
|
||||
if (obj) {
|
||||
if (solver == nullptr)
|
||||
solver = obj->getParent();
|
||||
}
|
||||
}
|
||||
|
||||
return solver;
|
||||
}
|
||||
|
||||
void PbArgs::visit(int number, const string &key)
|
||||
{
|
||||
if (number >= 0 && number < (int)mLinData.size())
|
||||
mLinData[number].visited = true;
|
||||
map<string, DataElement>::iterator lu = mData.find(key);
|
||||
if (lu != mData.end())
|
||||
lu->second.visited = true;
|
||||
}
|
||||
|
||||
PyObject *PbArgs::getItem(const std::string &key, bool strict, ArgLocker *lk)
|
||||
{
|
||||
map<string, DataElement>::iterator lu = mData.find(key);
|
||||
if (lu == mData.end()) {
|
||||
if (strict)
|
||||
errMsg("Argument '" + key + "' is not defined.");
|
||||
return nullptr;
|
||||
}
|
||||
PbClass *pbo = Pb::objFromPy(lu->second.obj);
|
||||
// try to lock
|
||||
if (pbo && lk)
|
||||
lk->add(pbo);
|
||||
return lu->second.obj;
|
||||
}
|
||||
|
||||
PyObject *PbArgs::getItem(size_t number, bool strict, ArgLocker *lk)
|
||||
{
|
||||
if (number >= mLinData.size()) {
|
||||
if (!strict)
|
||||
return nullptr;
|
||||
stringstream s;
|
||||
s << "Argument number #" << number << " not specified.";
|
||||
errMsg(s.str());
|
||||
}
|
||||
PbClass *pbo = Pb::objFromPy(mLinData[number].obj);
|
||||
// try to lock
|
||||
if (pbo && lk)
|
||||
lk->add(pbo);
|
||||
return mLinData[number].obj;
|
||||
}
|
||||
|
||||
//******************************************************************************
|
||||
// ArgLocker class defs
|
||||
|
||||
void ArgLocker::add(PbClass *p)
|
||||
{
|
||||
if (find(locks.begin(), locks.end(), p) == locks.end()) {
|
||||
locks.push_back(p);
|
||||
p->lock();
|
||||
}
|
||||
}
|
||||
ArgLocker::~ArgLocker()
|
||||
{
|
||||
for (size_t i = 0; i < locks.size(); i++)
|
||||
locks[i]->unlock();
|
||||
locks.clear();
|
||||
}
|
||||
|
||||
} // namespace Manta
|
||||
Reference in New Issue
Block a user