Example #1
0
static void dc_callvm_argBool_ppc64(DCCallVM* in_self, DCbool x)
{
  /* promote to longlong */
  dcArgLongLong(in_self, (DClonglong) x );
}
Example #2
0
int invoke(char const* signature, void* t)
{
  DCCallVM   * p = (DCCallVM*) G_callvm;
  char const * sig = signature;
  char         rtype;
  char         atype;
  int          pos = 0;
  int          s = 0;

  clear_V();
  
  rtype = *sig++;
  dcReset(p);

  while ( (atype = *sig++) != '\0') {
    pos++;
    switch(atype) {
      case 'c': dcArgChar    (p,K_c[pos]); break;
      case 's': dcArgShort   (p,K_s[pos]); break;
      case 'i': dcArgInt     (p,K_i[pos]); break;
      case 'j': dcArgLong    (p,K_j[pos]); break;
      case 'l': dcArgLongLong(p,K_l[pos]); break;
      case 'p': dcArgPointer (p,K_p[pos]); break;
      case 'f': dcArgFloat   (p,K_f[pos]); break;
      case 'd': dcArgDouble  (p,K_d[pos]); break;
      default: printf("unknown atype '%c' (1) ;", atype); return 0;
    }
  }
  
  switch(rtype) 
  {
    case 'v': dcCallVoid(p,t); s=1; /*TODO:check that no return-arg was touched.*/ break;
    case 'c': s = (dcCallChar    (p,t) == K_c[pos]) ; break;
    case 's': s = (dcCallShort   (p,t) == K_s[pos]) ; break;
    case 'i': s = (dcCallInt     (p,t) == K_i[pos]) ; break;
    case 'j': s = (dcCallLong    (p,t) == K_j[pos]) ; break;
    case 'l': s = (dcCallLongLong(p,t) == K_l[pos]) ; break;
    case 'p': s = (dcCallPointer (p,t) == K_p[pos]) ; break;
    case 'f': s = (dcCallFloat   (p,t) == K_f[pos]) ; break;
    case 'd': s = (dcCallDouble  (p,t) == K_d[pos]) ; break;
    default: printf("unknown rtype '%c'", rtype); return 0;
  }

  if (!s) { printf("rval wrong;"); return 0; }
  /* test: */
  sig = signature+1;
  pos = 1;
  while ( (atype = *sig++) != '\0') {
    switch(atype) {
#if 0
#define X(CH,T,QCH) case QCH: s = (V_##CH[pos] == K_##CH[pos]); break;
DEF_TYPES
#undef X
#endif
      case 'c': s = ( V_c[pos] == K_c[pos] ); if (!s) printf("'c':%d: %d != %d ; ", pos, V_c[pos], K_c[pos]); break;
      case 's': s = ( V_s[pos] == K_s[pos] ); if (!s) printf("'s':%d: %d != %d ; ", pos, V_s[pos], K_s[pos]); break;
      case 'i': s = ( V_i[pos] == K_i[pos] ); if (!s) printf("'i':%d: %d != %d ; ", pos, V_i[pos], K_i[pos]); break;
      case 'j': s = ( V_j[pos] == K_j[pos] ); if (!s) printf("'j':%d: %ld != %ld ; ", pos, V_j[pos], K_j[pos]); break;
      case 'l': s = ( V_l[pos] == K_l[pos] ); if (!s) printf("'l':%d: %lld != %lld ; ", pos, V_l[pos], K_l[pos]); break;
      case 'p': s = ( V_p[pos] == K_p[pos] ); if (!s) printf("'p':%d: %lld != %lld ; ", pos, (long long) V_p[pos], (long long) K_p[pos]); break;
      case 'f': s = ( V_f[pos] == K_f[pos] ); if (!s) printf("'f':%d: %f != %f ; ", pos, V_f[pos], K_f[pos]); break;
      case 'd': s = ( V_d[pos] == K_d[pos] ); if (!s) printf("'d':%d: %f != %f ; ", pos, V_d[pos], K_d[pos]); break;
      default: printf("unknown atype '%c' ; ", atype); return 0;
    }
    if (!s) {
      printf("arg mismatch at %d ; ", pos);
      return 0;
    }
    pos++;
  }
  return 1;
}
Example #3
0
static PyObject*
pydc_call(PyObject* self, PyObject* in_args)
{
  PyObject*   pcobj_funcptr;
  const char* signature;
  PyObject*   args;
  int         l;
  const char* ptr;
  char        ch;
  int         pos;
  void*       pfunc;
  
  if ( !PyArg_ParseTuple(in_args,"OsO", &pcobj_funcptr, &signature, &args) ) return PyErr_Format(PyExc_RuntimeError, "argument mismatch");
  pfunc = PyCObject_AsVoidPtr(pcobj_funcptr);  
  if ( !pfunc ) return PyErr_Format( PyExc_RuntimeError, "function pointer is NULL" );
  l = PyTuple_Size(args);

  ptr = signature;
  pos = 0; 

  dcReset(gpCall);
  
  while ( (ch = *ptr) != '\0' && ch != ')' ) 
  {
    PyObject* po;

    int index = pos+1;

    if (pos > l) return PyErr_Format( PyExc_RuntimeError, "expecting more arguments" );

    po = PyTuple_GetItem(args,pos);

    switch(ch) 
    {
      case DC_SIGCHAR_BOOL:
      {
        DCbool b;
        if ( !PyBool_Check(po) ) return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expecting a bool", index ); 
        b = (Py_True == po) ? DC_TRUE : DC_FALSE;
        dcArgBool(gpCall, b);
      }
      break;
      case DC_SIGCHAR_CHAR:
      {
        DCchar c;
        if ( PyString_Check(po) )
        {
          // Py_ssize_t l;
          size_t l;
          char* s;
          l = PyString_GET_SIZE(po);
          if (l != 1) return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expecting a string with length of 1 (a char string)", index );          
          s = PyString_AsString(po);          
          c = (DCchar) s[0];
        }
        else if ( PyInt_Check(po) ) 
        {
          long l;
          l = PyInt_AsLong(po);
          if ( (l > CHAR_MAX) || (l < CHAR_MIN)) return PyErr_Format( PyExc_RuntimeError, "value out of range at argument %d - expecting a char code", index );
          c = (DCchar) l;
        }
        else return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expecting a char", index );        
        dcArgChar(gpCall, c);
      }
      break;
      case DC_SIGCHAR_SHORT:
      {
        DCshort s;
        long v;
        if ( !PyInt_Check(po) )
          return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expecting a short int", index ); 
        v = PyInt_AS_LONG(po);
        if ( (v < SHRT_MIN) || (v > SHRT_MAX) ) 
          return PyErr_Format( PyExc_RuntimeError, "value out of range at argument %d - expecting a short value", index );
        s = (DCshort) v;
        dcArgShort(gpCall, s);
      } 
      break;
      case DC_SIGCHAR_INT:
      {
        long v;
        if ( !PyInt_Check(po) ) return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expecting an int", index ); 
        v = PyInt_AS_LONG(po);
        dcArgInt(gpCall, (DCint) v );
      }
      break;
      case DC_SIGCHAR_LONG:
      {
        long v;
        if ( !PyInt_Check(po) ) return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expecting an int", index ); 
        v = PyInt_AsLong(po);
        
      }
      break;
      case DC_SIGCHAR_LONGLONG:
      {
        PY_LONG_LONG pl;
        DClonglong dl;
        if ( !PyLong_Check(po) ) return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expecting a long long", index );
        pl = PyLong_AsLongLong(po);
        dl = (DClonglong) pl;
        dcArgLongLong(gpCall, dl );
      }
      break;
      case DC_SIGCHAR_FLOAT:
      {
        DCfloat f;
        if (!PyFloat_Check(po)) return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expeecting a float", index );
        f = (float) PyFloat_AsDouble(po);
        dcArgFloat(gpCall, f);
      }
      break;
      case DC_SIGCHAR_DOUBLE:
      {
        double d;
        if (!PyFloat_Check(po)) return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expeecting a float", index );
        d = PyFloat_AsDouble(po);
        dcArgDouble(gpCall, d);      
      }
      break;
      case DC_SIGCHAR_POINTER:
      {
        DCpointer ptr;
        if ( PyString_Check(po) ) {
          ptr = (DCpointer) PyString_AsString(po);
        } else if ( PyLong_Check(po) ) {
          ptr = (DCpointer) ( (DCint) PyLong_AsLongLong(po) );
        } else {
          return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expecting a promoting pointer-type (int,string)", index );
        }
        dcArgPointer(gpCall, ptr );
      }
      break;
      case 'S':
      {
        char* p;
        if (!PyString_Check(po) ) return PyErr_Format( PyExc_RuntimeError, "argument mismatch at pos %d - expecting a string", index );
        p = PyString_AsString(po);
        dcArgPointer(gpCall, (DCpointer) p );
      }
      break;
      default: return PyErr_Format( PyExc_RuntimeError, "unknown signature character '%c'", ch);
    }

    ++pos; ++ptr;

  }

  if (pos != l) return PyErr_Format( PyExc_RuntimeError, "too many arguments");

  if (ch == '\0') return PyErr_Format( PyExc_RuntimeError, "return value missing in signature");

  ch = *++ptr;

  switch(ch) 
  {
    case DC_SIGCHAR_VOID: dcCallVoid(gpCall, pfunc); Py_RETURN_NONE;
    case DC_SIGCHAR_BOOL: return Py_BuildValue("i", dcCallBool(gpCall, pfunc) );
    case DC_SIGCHAR_INT: return Py_BuildValue("i", dcCallInt(gpCall, pfunc) ); 
    case DC_SIGCHAR_LONGLONG: return Py_BuildValue("L", (unsigned long long) dcCallLongLong(gpCall, pfunc) );
    case DC_SIGCHAR_FLOAT: return Py_BuildValue("f", dcCallFloat(gpCall, pfunc) ); 
    case DC_SIGCHAR_DOUBLE: return Py_BuildValue("d", dcCallDouble(gpCall, pfunc) ); 
    case 's': return Py_BuildValue("s", dcCallPointer(gpCall, pfunc) ); 
    case DC_SIGCHAR_POINTER: return Py_BuildValue("p", dcCallPointer(gpCall, pfunc) ); 
    default:  return PyErr_Format( PyExc_RuntimeError, "invalid return type signature" );
  }
}
Example #4
0
template<> void _push_fn_arg<long long>(long long value) { dcArgLongLong(vm, value); }
Example #5
0
jboolean followArgs(CallTempStruct* call, DCArgs* args, int nTypes, ValueType* pTypes, CallFlags flags) 
{	
	JNIEnv* env = call->env;
	int iParam;
	for (iParam = 0; iParam < nTypes; iParam++) {
		ValueType type = pTypes[iParam];
		switch (type) {
			case eIntFlagSet:
				{
					jobject callIO = call && call->pCallIOs ? *(call->pCallIOs++) : NULL;
					if (flags & CALLING_JAVA) {
						int flags = dcbArgInt(args);
						jobject obj = createPointerFromIO(env, JLONG_TO_PTR ((jlong)flags), callIO);
						dcArgPointer(call->vm, obj);
						addTempCallLocalRef(call, obj);
					} else {
						jobject obj = (jobject)dcbArgPointer(args);
						int arg = (jint)getFlagValue(env, obj);
						(*env)->DeleteLocalRef(env, obj);
						if (flags & IS_VAR_ARGS)
							dcArgPointer(call->vm, (void*)(ptrdiff_t)arg);
						else
							dcArgInt(call->vm, arg);
					}
				}
				break;
			case eIntValue:
				{
					int arg = dcbArgInt(args);
					if (flags & IS_VAR_ARGS)
						dcArgPointer(call->vm, (void*)(ptrdiff_t)arg);
					else
						dcArgInt(call->vm, arg);
				}
				break;
			#define ARG_BOXED_INTEGRAL(type, capitalized) \
				{ \
					if (flags & CALLING_JAVA) { \
						type arg = (sizeof(type) == 4) ? (type)dcbArgInt(args) : (type)dcbArgLongLong(args); \
						jobject boxed = Box ## capitalized(env, arg); \
						dcArgPointer(call->vm, boxed); \
						addTempCallLocalRef(call, boxed); \
					} else { \
						jobject parg = dcbArgPointer(args); \
						jlong arg = Unbox ## capitalized(env, parg); \
						(*env)->DeleteLocalRef(env, parg); \
						if (flags & IS_VAR_ARGS) \
							dcArgPointer(call->vm, (void*)(ptrdiff_t)arg); \
						else if (sizeof(type) == 4) \
							dcArgInt(call->vm, (jint)arg); \
						else \
							dcArgLongLong(call->vm, (jlong)arg); \
					} \
				}
			#define ARG_UNBOXED_INTEGRAL(type, capitalized) \
				{ \
					if (flags & CALLING_JAVA) { \
						type arg = (sizeof(type) == 4) ? (type)dcbArgInt(args) : (type)dcbArgLongLong(args); \
						dcArgLongLong(call->vm, (jlong)arg); \
					} else { \
						jlong arg = dcbArgLongLong(args); \
						if (flags & IS_VAR_ARGS) \
							dcArgPointer(call->vm, (void*)(ptrdiff_t)arg); \
						else if (sizeof(type) == 4) \
							dcArgInt(call->vm, (jint)arg); \
						else \
							dcArgLongLong(call->vm, (jlong)arg); \
					} \
				}
			case eCLongValue:
				ARG_UNBOXED_INTEGRAL(long, CLong);
				break;
			case eSizeTValue:
				ARG_UNBOXED_INTEGRAL(size_t, SizeT);
				break;
			case eCLongObjectValue:
				ARG_BOXED_INTEGRAL(long, CLong);
				break;
			case eSizeTObjectValue:
				ARG_BOXED_INTEGRAL(size_t, SizeT);
				break;
			case eTimeTObjectValue:
				ARG_BOXED_INTEGRAL(time_t, TimeT);
				break;
			case eLongValue:
				dcArgLongLong(call->vm, dcbArgLongLong(args));
				break;
			case eShortValue:
				{
					short arg = dcbArgShort(args);
					if (flags & IS_VAR_ARGS)
						dcArgPointer(call->vm, (void*)(ptrdiff_t)arg);
					else
						dcArgShort(call->vm, arg);
				}
				break;
			case eBooleanValue:
			case eByteValue: 
				{
					char arg = dcbArgChar(args);
					if (flags & IS_VAR_ARGS)
						dcArgPointer(call->vm, (void*)(ptrdiff_t)arg);
					else
						dcArgChar(call->vm, arg);
				}
				break;
			case eFloatValue: 
				{
					float arg = dcbArgFloat(args);
					if (flags & IS_VAR_ARGS)
						dcArgDouble(call->vm, arg);
					else
						dcArgFloat(call->vm, arg);
				}
				break;
			case eDoubleValue:
				dcArgDouble(call->vm, dcbArgDouble(args));
				break;
			case ePointerValue:
				{
					void* ptr = dcbArgPointer(args);
					jobject callIO = call && call->pCallIOs ? *(call->pCallIOs++) : NULL;
					if (flags & CALLING_JAVA)
					{
						ptr = createPointerFromIO(env, ptr, callIO);
						addTempCallLocalRef(call, ptr);
					} else {
						ptr = ptr ? getPointerPeer(env, ptr) : NULL;
					}
					dcArgPointer(call->vm, ptr);
				}
				break;
			case eWCharValue:
				switch (sizeof(wchar_t)) {
				case 1:
					dcArgChar(call->vm, dcbArgChar(args));
					break;
				case 2:
					dcArgShort(call->vm, dcbArgShort(args));
					break;
				case 4:
					dcArgInt(call->vm, dcbArgInt(args));
					break;
				default:
					throwException(env, "Invalid wchar_t size for argument !");
					return JNI_FALSE;
				}
				break;
			case eNativeObjectValue: {
				jobject callIO = call && call->pCallIOs ? *(call->pCallIOs++) : NULL;
				DCstruct* s = getStructFromIO(env, callIO);
				void* pStruct = getNativeObjectPointerWithIO(env, dcbArgPointer(args), callIO);
				if (!s) {
					throwException(env, "Failed to get low-level struct representation !");
					return JNI_FALSE;
				}
				if (!pStruct) {
					throwException(env, "Struct by value cannot be null !");
					return JNI_FALSE;
				}
				dcArgStruct(call->vm, s, pStruct);
				break;
			}	
			case eEllipsis: {
				if (flags & CALLING_JAVA) {
					throwException(env, "Calling Java ellipsis is not supported yet !");
					return JNI_FALSE;
				} else {
					jobjectArray arr = (jobjectArray)dcbArgPointer(args);
					jsize n = (*env)->GetArrayLength(env, arr), i;

					for (i = 0; i < n; i++) {
						jobject arg = (*env)->GetObjectArrayElement(env, arr, i);
						#define TEST_INSTANCEOF(cl, st) \
							if ((*env)->IsInstanceOf(env, arg, cl)) st;

						if (arg == NULL)
							dcArgPointer(call->vm, NULL);//getPointerPeer(env, (void*)NULL));
						else
						// As per the C standard for varargs, all ints are promoted to ptrdiff_t and float is promoted to double : 
						TEST_INSTANCEOF(gIntClass, dcArgPointer(call->vm, (void*)(ptrdiff_t)UnboxInt(env, arg)))
						else
						TEST_INSTANCEOF(gLongClass, dcArgPointer(call->vm, (void*)(ptrdiff_t)UnboxLong(env, arg)))
						else
						TEST_INSTANCEOF(gShortClass, dcArgPointer(call->vm, (void*)(ptrdiff_t)UnboxShort(env, arg)))
						else
						TEST_INSTANCEOF(gByteClass, dcArgPointer(call->vm, (void*)(ptrdiff_t)UnboxByte(env, arg)))
						else
						TEST_INSTANCEOF(gBooleanClass, dcArgPointer(call->vm, (void*)(ptrdiff_t)(char)UnboxBoolean(env, arg)))
						else
						TEST_INSTANCEOF(gCharClass, dcArgPointer(call->vm, (void*)(ptrdiff_t)(short)UnboxChar(env, arg)))
						else
						TEST_INSTANCEOF(gDoubleClass, dcArgDouble(call->vm, UnboxDouble(env, arg)))
						else
						TEST_INSTANCEOF(gFloatClass, dcArgDouble(call->vm, UnboxFloat(env, arg)))
						else
						TEST_INSTANCEOF(gCLongClass, dcArgPointer(call->vm, (void*)(ptrdiff_t)(long)UnboxCLong(env, arg)))
						else
						TEST_INSTANCEOF(gSizeTClass, dcArgPointer(call->vm, (void*)(ptrdiff_t)UnboxSizeT(env, arg)))
						else
						TEST_INSTANCEOF(gPointerClass, dcArgPointer(call->vm, getPointerPeer(env, (void*)arg)))
						else {
							throwException(env, "Invalid value type in ellipsis");
							(*env)->DeleteLocalRef(env, arg);
							(*env)->DeleteLocalRef(env, arr);
							return JNI_FALSE;
						}
						(*env)->DeleteLocalRef(env, arg);
					}
					(*env)->DeleteLocalRef(env, arr);
				}
				break;
			}
			default:
				throwException(env, "Invalid argument value type !");
				return JNI_FALSE;
		}
	}
	if ((*env)->ExceptionCheck(env))
		return JNI_FALSE;
	return JNI_TRUE;
}