PyObject* JPypeModule::synchronized(PyObject* obj, PyObject* args) { JPCleaner cleaner; TRACE_IN("synchronized"); try { PyObject* o; JPyArg::parseTuple(args, "O!", &PyCObject_Type, &o); string desc = (char*)JPyCObject::getDesc(o); jobject obj; if (desc == "JPObject") { JPObject* jpo = (JPObject*)JPyCObject::asVoidPtr(o); obj = jpo->getObject(); cleaner.addLocal(obj); } else if (desc == "JPClass") { JPClass* jpo = (JPClass*)JPyCObject::asVoidPtr(o); obj = jpo->getClass(); cleaner.addLocal(obj); } else if (desc == "JPArray") { JPArray* jpo = (JPArray*)JPyCObject::asVoidPtr(o); obj = jpo->getObject(); cleaner.addLocal(obj); } else if (desc == "JPArrayClass") { JPArrayClass* jpo = (JPArrayClass*)JPyCObject::asVoidPtr(o); obj = jpo->getClass(); cleaner.addLocal(obj); } else if (hostEnv->isWrapper(o) && hostEnv->getWrapperTypeName(o).isObjectType()) { obj = hostEnv->getWrapperValue(o).l; cleaner.addLocal(obj); } // TODO proxy else { RAISE(JPypeException, "method only accepts object values."); } PyJPMonitor* c = PyJPMonitor::alloc(new JPMonitor(obj)); return (PyObject*)c; } PY_STANDARD_CATCH; PyErr_Clear(); Py_INCREF(Py_None); return Py_None; TRACE_OUT; }
EMatchType JPArrayClass::canConvertToJava(HostRef* o) { JPCleaner cleaner; if (JPEnv::getHost()->isNone(o)) { return _implicit; } if (JPEnv::getHost()->isArray(o)) { JPArray* a = JPEnv::getHost()->asArray(o); JPArrayClass* ca = a->getClass(); if (ca == this) { return _exact; } if (JPEnv::getJava()->IsAssignableFrom(ca->m_Class, m_Class)) { return _implicit; } } else if (JPEnv::getHost()->isUnicodeString(o) && m_ComponentType->getName().getType() ==JPTypeName::_char) { // Strings are also char[] return _implicit; } else if (JPEnv::getHost()->isByteString(o) && m_ComponentType->getName().getType() ==JPTypeName::_byte) { // Strings are also char[] return _implicit; } else if (JPEnv::getHost()->isSequence(o)) { EMatchType match = _implicit; int length = JPEnv::getHost()->getSequenceLength(o); for (int i = 0; i < length && match > _none; i++) { HostRef* obj = JPEnv::getHost()->getSequenceItem(o, i); cleaner.add(obj); EMatchType newMatch = m_ComponentType->canConvertToJava(obj); if (newMatch < match) { match = newMatch; } } return match; } return _none; }
PyObject* JPypeJavaArray::setArraySlice(PyObject* self, PyObject* arg) { TRACE_IN("JPypeJavaArray::setArraySlice") PyObject* arrayObject; int lo = -1; int hi = -1; PyObject* sequence; try { JPyArg::parseTuple(arg, "O!iiO", &PyCapsule_Type, &arrayObject, &lo, &hi, &sequence); JPArray* a = (JPArray*)JPyCObject::asVoidPtr(arrayObject); int length = a->getLength(); if(length == 0) Py_RETURN_NONE; if (lo < 0) lo = length + lo; if (lo < 0) lo = 0; else if (lo > length) lo = length; if (hi < 0) hi = length + hi; if (hi < 0) hi = 0; else if (hi > length) hi = length; if (lo > hi) lo = hi; const JPTypeName& componentName = a->getType()->getObjectType().getComponentName(); const string& name = componentName.getNativeName(); if(is_primitive(name[0])) { // for primitive types, we have fast setters available a->setRange(lo, hi, sequence); } else { // slow wrapped access for non primitive types vector<HostRef*> values; values.reserve(hi - lo); JPCleaner cleaner; for (Py_ssize_t i = 0; i < hi - lo; i++) { HostRef* v = new HostRef(JPySequence::getItem(sequence, i), false); values.push_back(v); cleaner.add(v); } a->setRange(lo, hi, values); } Py_RETURN_NONE; } PY_STANDARD_CATCH return NULL; TRACE_OUT }
PyObject* JPypeJavaArray::getArrayLength(PyObject* self, PyObject* arg) { try { PyObject* arrayObject; JPyArg::parseTuple(arg, "O!", &PyCObject_Type, &arrayObject); JPArray* a = (JPArray*)JPyCObject::asVoidPtr(arrayObject); int res = a->getLength(); return JPyInt::fromLong(res); } PY_STANDARD_CATCH return NULL; }
PyObject* JPypeJavaArray::getArrayItem(PyObject* self, PyObject* arg) { try { PyObject* arrayObject; int ndx; JPyArg::parseTuple(arg, "O!i", &PyCObject_Type, &arrayObject, &ndx); JPArray* a = (JPArray*)JPyCObject::asVoidPtr(arrayObject); HostRef* res = a->getItem(ndx); return detachRef(res); } PY_STANDARD_CATCH return NULL; }
PyObject* JPypeJavaArray::getArraySlice(PyObject* self, PyObject* arg) { PyObject* arrayObject; int lo = -1; int hi = -1; try { JPyArg::parseTuple(arg, "O!ii", &PyCapsule_Type, &arrayObject, &lo, &hi); JPArray* a = (JPArray*)JPyCObject::asVoidPtr(arrayObject); int length = a->getLength(); // stolen from jcc, to get nice slice support if (lo < 0) lo = length + lo; if (lo < 0) lo = 0; else if (lo > length) lo = length; if (hi < 0) hi = length + hi; if (hi < 0) hi = 0; else if (hi > length) hi = length; if (lo > hi) lo = hi; const JPTypeName& componentName = a->getType()->getObjectType().getComponentName(); const string& name = componentName.getNativeName(); if(is_primitive(name[0])) { // for primitive types, we have fast sequence generation available return a->getSequenceFromRange(lo, hi); } else { // slow wrapped access for non primitives vector<HostRef*> values = a->getRange(lo, hi); JPCleaner cleaner; PyObject* res = JPySequence::newList((int)values.size()); for (unsigned int i = 0; i < values.size(); i++) { JPySequence::setItem(res, i, (PyObject*)values[i]->data()); cleaner.add(values[i]); } return res; } } PY_STANDARD_CATCH return NULL; }
PyObject* JPypeJavaArray::setArrayItem(PyObject* self, PyObject* arg) { try { PyObject* arrayObject; int ndx; PyObject* value; JPyArg::parseTuple(arg, "O!iO", &PyCObject_Type, &arrayObject, &ndx, &value); JPArray* a = (JPArray*)JPyCObject::asVoidPtr(arrayObject); JPCleaner cleaner; HostRef* v = new HostRef(value); cleaner.add(v); a->setItem(ndx, v); Py_RETURN_NONE; } PY_STANDARD_CATCH return NULL; }
jvalue JPClass::convertToJava(HostRef* obj) { jvalue res; JPCleaner cleaner; res.l = NULL; // assume it is convertible; if (JPEnv::getHost()->isNone(obj)) { res.l = NULL; } string simpleName = m_Name.getSimpleName(); if (JPEnv::getHost()->isInt(obj) && (simpleName == "java.lang.Byte" || simpleName == "java.lang.Short" || simpleName == "java.lang.Integer")) { return buildObjectWrapper(obj); } if ((JPEnv::getHost()->isInt(obj) || JPEnv::getHost()->isLong(obj)) && simpleName == "java.lang.Long" && JPEnv::getHost()->isLong(obj)) { return buildObjectWrapper(obj); } if (JPEnv::getHost()->isFloat(obj) && (simpleName == "java.lang.Float" || simpleName == "java.lang.Double")) { if (JPEnv::getHost()->isFloat(obj)) { return buildObjectWrapper(obj); } } if (JPEnv::getHost()->isString(obj)) { JPTypeName name = JPTypeName::fromSimple("java.lang.String"); JPType* type = JPTypeManager::getType(name); return type->convertToJava(obj); } if (JPEnv::getHost()->isObject(obj)) { JPObject* ref = JPEnv::getHost()->asObject(obj); res.l = ref->getObject(); } if (JPEnv::getHost()->isProxy(obj)) { JPProxy* proxy = JPEnv::getHost()->asProxy(obj); res.l = proxy->getProxy(); } if (JPEnv::getHost()->isWrapper(obj)) { res = JPEnv::getHost()->getWrapperValue(obj); } if (JPEnv::getHost()->isInt(obj)) { JPTypeName tname = JPTypeName::fromType(JPTypeName::_int); JPType* t = JPTypeManager::getType(tname); res.l = t->convertToJavaObject(obj); } if (JPEnv::getHost()->isLong(obj)) { JPTypeName tname = JPTypeName::fromType(JPTypeName::_long); JPType* t = JPTypeManager::getType(tname); res.l = t->convertToJavaObject(obj); } if (JPEnv::getHost()->isFloat(obj)) { JPTypeName tname = JPTypeName::fromType(JPTypeName::_double); JPType* t = JPTypeManager::getType(tname); res.l = t->convertToJavaObject(obj); } if (JPEnv::getHost()->isBoolean(obj)) { JPTypeName tname = JPTypeName::fromType(JPTypeName::_boolean); JPType* t = JPTypeManager::getType(tname); res.l = t->convertToJavaObject(obj); } if (JPEnv::getHost()->isArray(obj) && simpleName == "java.lang.Object") { JPArray* a = JPEnv::getHost()->asArray(obj); res = a->getValue(); } return res; }
jvalue JPArrayClass::convertToJava(HostRef* obj) { JPCleaner cleaner; jvalue res; res.l = NULL; if (JPEnv::getHost()->isArray(obj)) { JPArray* a = JPEnv::getHost()->asArray(obj); res = a->getValue(); } else if (JPEnv::getHost()->isByteString(obj) && m_ComponentType->getName().getType() == JPTypeName::_byte && sizeof(char) == sizeof(jbyte)) { char* rawData; long size; JPEnv::getHost()->getRawByteString(obj, &rawData, size); jbyteArray array = JPEnv::getJava()->NewByteArray(size); cleaner.addLocal(array); res.l = array; jboolean isCopy; jbyte* contents = JPEnv::getJava()->GetByteArrayElements(array, &isCopy); memcpy(contents, rawData, size*sizeof(jbyte)); JPEnv::getJava()->ReleaseByteArrayElements(array, contents, 0); cleaner.removeLocal(array); } else if (JPEnv::getHost()->isUnicodeString(obj) && m_ComponentType->getName().getType() == JPTypeName::_char && JPEnv::getHost()->getUnicodeSize() == sizeof(jchar)) { jchar* rawData; long size; JPEnv::getHost()->getRawUnicodeString(obj, &rawData, size); jcharArray array = JPEnv::getJava()->NewCharArray(size); cleaner.addLocal(array); res.l = array; jboolean isCopy; jchar* contents = JPEnv::getJava()->GetCharArrayElements(array, &isCopy); memcpy(contents, rawData, size*sizeof(jchar)); JPEnv::getJava()->ReleaseCharArrayElements(array, contents, 0); cleaner.removeLocal(array); } else if (JPEnv::getHost()->isSequence(obj)) { int length = JPEnv::getHost()->getSequenceLength(obj); jarray array = m_ComponentType->newArrayInstance(length); cleaner.addLocal(array); res.l = array; for (int i = 0; i < length ; i++) { HostRef* obj2 = JPEnv::getHost()->getSequenceItem(obj, i); cleaner.add(obj2); m_ComponentType->setArrayItem(array, i, obj2); } cleaner.removeLocal(array); } return res; }