예제 #1
0
static int Storage_header_set(PyObject *self, PyObject *value, void *closure) {

  PyObject *header = ((StorageObject*)self)->header;
  cdb_t *cdb       = ((StorageObject*)self)->cdb;
  char* key        = (char*)closure;

  if (strcmp(key, "name") == 0) {

    PyDict_SetItemString(header, key, value);
    strncpy(cdb->header->name, PyString_AsString(value), sizeof(cdb->header->name));
    cdb->synced = false;

  } else if (strcmp(key, "min_value") == 0) {

    PyDict_SetItemString(header, key, value);
    cdb->header->min_value = PyInt_AsUnsignedLongLongMask(value);
    cdb->synced = false;

  } else if (strcmp(key, "max_value") == 0) {

    PyDict_SetItemString(header, key, value);
    cdb->header->max_value = PyInt_AsUnsignedLongLongMask(value);
    cdb->synced = false;

  } else if (strcmp(key, "units") == 0) {

    PyDict_SetItemString(header, key, value);
    strncpy(cdb->header->units, PyString_AsString(value), sizeof(cdb->header->units));
    cdb->synced = false;
  }

  return 0;
}
예제 #2
0
파일: cfield.c 프로젝트: nanwu/pyston
static PyObject *
P_set(void *ptr, PyObject *value, Py_ssize_t size)
{
    void *v;
    if (value == Py_None) {
        *(void **)ptr = NULL;
        _RET(value);
    }

    if (!PyInt_Check(value) && !PyLong_Check(value)) {
        PyErr_SetString(PyExc_TypeError,
                        "cannot be converted to pointer");
        return NULL;
    }

#if SIZEOF_VOID_P <= SIZEOF_LONG
    v = (void *)PyInt_AsUnsignedLongMask(value);
#else
#ifndef HAVE_LONG_LONG
#   error "PyLong_AsVoidPtr: sizeof(void*) > sizeof(long), but no long long"
#elif SIZEOF_LONG_LONG < SIZEOF_VOID_P
#   error "PyLong_AsVoidPtr: sizeof(PY_LONG_LONG) < sizeof(void*)"
#endif
    v = (void *)PyInt_AsUnsignedLongLongMask(value);
#endif

    if (PyErr_Occurred())
        return NULL;

    *(void **)ptr = v;
    _RET(value);
}
예제 #3
0
파일: cfield.c 프로젝트: nanwu/pyston
static PyObject *
z_set(void *ptr, PyObject *value, Py_ssize_t size)
{
    if (value == Py_None) {
        *(char **)ptr = NULL;
        Py_INCREF(value);
        return value;
    }
    if (PyString_Check(value)) {
        *(char **)ptr = PyString_AS_STRING(value);
        Py_INCREF(value);
        return value;
    } else if (PyUnicode_Check(value)) {
        PyObject *str = PyUnicode_AsEncodedString(value,
                                                  _ctypes_conversion_encoding,
                                                  _ctypes_conversion_errors);
        if (str == NULL)
            return NULL;
        *(char **)ptr = PyString_AS_STRING(str);
        return str;
    } else if (PyInt_Check(value) || PyLong_Check(value)) {
#if SIZEOF_VOID_P == SIZEOF_LONG_LONG
        *(char **)ptr = (char *)PyInt_AsUnsignedLongLongMask(value);
#else
        *(char **)ptr = (char *)PyInt_AsUnsignedLongMask(value);
#endif
        _RET(value);
    }
    PyErr_Format(PyExc_TypeError,
                 "string or integer address expected instead of %s instance",
                 value->ob_type->tp_name);
    return NULL;
}
 void _extract(PyObject *obj, unsigned long long &val)
 {
     if (PyInt_Check(obj))
         val = (unsigned long long)PyInt_AsUnsignedLongLongMask(obj);
     else if (PyFloat_Check(obj))
         val = (unsigned long long)PyFloat_AsDouble(obj);
     else
         val = (unsigned long long)PyLong_AsLongLong(obj);
 }
예제 #5
0
파일: acpimodule.c 프로젝트: mfleming/bits
static bool acpi_object_from_python(PyObject *pyobj, ACPI_OBJECT *obj)
{
    PyObject *value;

    if (pyobj == Py_None) {
        obj->Type = ACPI_TYPE_ANY;
        return true;
    }
    if (!PyArg_ParseTuple(pyobj, "IO:acpi_object_from_python", &obj->Type, &value))
        return false;
    switch (obj->Type) {
    case ACPI_TYPE_INTEGER:
        obj->Integer.Value = PyInt_AsUnsignedLongLongMask(value);
        return true;
    case ACPI_TYPE_STRING:
        {
            Py_ssize_t length;
            if (PyString_AsStringAndSize(value, &obj->String.Pointer, &length) < 0)
                return false;
            if (length > GRUB_UINT_MAX) {
                PyErr_Format(PyExc_RuntimeError, "Python object provided as ACPI string had > 4G of data");
                return false;
            }
            obj->String.Length = length;
            return true;
        }
    case ACPI_TYPE_BUFFER:
        {
            Py_ssize_t length;
            if (PyString_AsStringAndSize(value, (char **)&obj->Buffer.Pointer, &length) < 0)
                return false;
            if (length > GRUB_UINT_MAX) {
                PyErr_Format(PyExc_RuntimeError, "Python object provided as ACPI buffer had > 4G of data");
                return false;
            }
            obj->Buffer.Length = length;
            return true;
        }
    case ACPI_TYPE_PACKAGE:
        return acpi_objects_from_python(value, &obj->Package.Elements, &obj->Package.Count);
    case ACPI_TYPE_POWER:
        return PyArg_ParseTuple(value, "II", &obj->PowerResource.SystemLevel, &obj->PowerResource.ResourceOrder);
    case ACPI_TYPE_PROCESSOR:
        return PyArg_ParseTuple(value, "IkI", &obj->Processor.ProcId, &obj->Processor.PblkAddress, &obj->Processor.PblkLength);
    default:
        PyErr_Format(PyExc_RuntimeError,
                     "Python object provided as ACPI method parameter used unhandled ACPI_OBJECT_TYPE %u.",
                     obj->Type);
        return false;
    }
}
예제 #6
0
static nvlist_t *
dict2nvl(PyObject *d)
{
	nvlist_t *nvl;
	int err;
	PyObject *key, *value;
	int pos = 0;

	if (!PyDict_Check(d)) {
		PyErr_SetObject(PyExc_ValueError, d);
		return (NULL);
	}

	err = nvlist_alloc(&nvl, NV_UNIQUE_NAME, 0);
	assert(err == 0);

	while (PyDict_Next(d, &pos, &key, &value)) {
		char *keystr = PyString_AsString(key);
		if (keystr == NULL) {
			PyErr_SetObject(PyExc_KeyError, key);
			nvlist_free(nvl);
			return (NULL);
		}

		if (PyDict_Check(value)) {
			nvlist_t *valnvl = dict2nvl(value);
			err = nvlist_add_nvlist(nvl, keystr, valnvl);
			nvlist_free(valnvl);
		} else if (value == Py_None) {
			err = nvlist_add_boolean(nvl, keystr);
		} else if (PyString_Check(value)) {
			char *valstr = PyString_AsString(value);
			err = nvlist_add_string(nvl, keystr, valstr);
		} else if (PyInt_Check(value)) {
			uint64_t valint = PyInt_AsUnsignedLongLongMask(value);
			err = nvlist_add_uint64(nvl, keystr, valint);
		} else if (PyBool_Check(value)) {
			boolean_t valbool = value == Py_True ? B_TRUE : B_FALSE;
			err = nvlist_add_boolean_value(nvl, keystr, valbool);
		} else {
			PyErr_SetObject(PyExc_ValueError, value);
			nvlist_free(nvl);
			return (NULL);
		}
		assert(err == 0);
	}

	return (nvl);
}
예제 #7
0
파일: cfield.c 프로젝트: nanwu/pyston
static int
get_ulonglong(PyObject *v, unsigned PY_LONG_LONG *p)
{
    unsigned PY_LONG_LONG x;
    if (PyFloat_Check(v)) {
        PyErr_SetString(PyExc_TypeError,
                        "int expected instead of float");
        return -1;
    }
    x = PyInt_AsUnsignedLongLongMask(v);
    if (x == (unsigned PY_LONG_LONG)-1 && PyErr_Occurred())
        return -1;
    *p = x;
    return 0;
}
static int
object_to_u64(PyObject *o, u_int64_t *u64)
{
    if (o == NULL)
        return (-1);
    if (PyLong_Check(o)) {
        *u64 = PyLong_AsUnsignedLongLong(o);
        return (0);
    }
    *u64 = PyInt_AsUnsignedLongLongMask(o);
    if (PyErr_Occurred())
        return (-1);

    return (0);
}
예제 #9
0
파일: ass2longlong.c 프로젝트: jwilk/Pyrex
static void __pyx_f_12ass2longlong_spam(void) {
  PY_LONG_LONG __pyx_v_L;
  unsigned PY_LONG_LONG __pyx_v_U;
  PyObject *__pyx_v_x;
  PY_LONG_LONG __pyx_1;
  PyObject *__pyx_2 = 0;
  unsigned PY_LONG_LONG __pyx_3;
  __pyx_v_x = Py_None; Py_INCREF(Py_None);

  /* "/Local/Projects/D/Pyrex/Source/Tests/8/ass2longlong.pyx":5 */
  __pyx_1 = PyInt_AsUnsignedLongLongMask(__pyx_v_x); if (PyErr_Occurred()) {__pyx_filename = __pyx_f[0]; __pyx_lineno = 5; goto __pyx_L1;}
  __pyx_v_L = __pyx_1;

  /* "/Local/Projects/D/Pyrex/Source/Tests/8/ass2longlong.pyx":6 */
  __pyx_2 = PyLong_FromLongLong(__pyx_v_L); if (!__pyx_2) {__pyx_filename = __pyx_f[0]; __pyx_lineno = 6; goto __pyx_L1;}
  Py_DECREF(__pyx_v_x);
  __pyx_v_x = __pyx_2;
  __pyx_2 = 0;

  /* "/Local/Projects/D/Pyrex/Source/Tests/8/ass2longlong.pyx":7 */
  __pyx_3 = PyInt_AsUnsignedLongLongMask(__pyx_v_x); if (PyErr_Occurred()) {__pyx_filename = __pyx_f[0]; __pyx_lineno = 7; goto __pyx_L1;}
  __pyx_v_U = __pyx_3;

  /* "/Local/Projects/D/Pyrex/Source/Tests/8/ass2longlong.pyx":8 */
  __pyx_2 = PyLong_FromUnsignedLongLong(__pyx_v_U); if (!__pyx_2) {__pyx_filename = __pyx_f[0]; __pyx_lineno = 8; goto __pyx_L1;}
  Py_DECREF(__pyx_v_x);
  __pyx_v_x = __pyx_2;
  __pyx_2 = 0;

  goto __pyx_L0;
  __pyx_L1:;
  Py_XDECREF(__pyx_2);
  __Pyx_WriteUnraisable("ass2longlong.spam");
  __pyx_L0:;
  Py_DECREF(__pyx_v_x);
}
예제 #10
0
파일: header-py.c 프로젝트: kaltsi/rpm
static int hdrAppendItem(Header h, rpmTagVal tag, rpmTagType type, PyObject *item)
{
    int rc = 0;

    switch (type) {
    case RPM_I18NSTRING_TYPE: /* XXX this needs to be handled separately */
    case RPM_STRING_TYPE:
    case RPM_STRING_ARRAY_TYPE: {
	PyObject *str = NULL;
	if (utf8FromPyObject(item, &str)) 
	    rc = headerPutString(h, tag, PyBytes_AsString(str));
	Py_XDECREF(str);
	} break;
    case RPM_BIN_TYPE: {
	uint8_t *val = (uint8_t *) PyBytes_AsString(item);
	rpm_count_t len = PyBytes_Size(item);
	rc = headerPutBin(h, tag, val, len);
	} break;
    case RPM_INT64_TYPE: {
	uint64_t val = PyInt_AsUnsignedLongLongMask(item);
	rc = headerPutUint64(h, tag, &val, 1);
	} break;
    case RPM_INT32_TYPE: {
	uint32_t val = PyInt_AsUnsignedLongMask(item);
	rc = headerPutUint32(h, tag, &val, 1);
	} break;
    case RPM_INT16_TYPE: {
	uint16_t val = PyInt_AsUnsignedLongMask(item);
	rc = headerPutUint16(h, tag, &val, 1);
	} break;
    case RPM_INT8_TYPE:
    case RPM_CHAR_TYPE: {
	uint8_t val = PyInt_AsUnsignedLongMask(item);
	rc = headerPutUint8(h, tag, &val, 1);
	} break;
    default:
	PyErr_SetString(PyExc_TypeError, "unhandled datatype");
    }
    return rc;
}
예제 #11
0
/* Copies a Python int or long object to an unsigned 64-bit value
 * Returns 1 if successful or -1 on error
 */
int pyvmdk_integer_unsigned_copy_to_64bit(
     PyObject *integer_object,
     uint64_t *value_64bit,
     libcerror_error_t **error )
{
	static char *function   = "pyvmdk_integer_unsigned_copy_to_64bit";
	int result              = 0;

#if defined( HAVE_LONG_LONG )
	PY_LONG_LONG long_value = 0;
#else
	long long_value         = 0;
#endif

	if( integer_object == NULL )
	{
		libcerror_error_set(
		 error,
		 LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
		 LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
		 "%s: invalid integer object.",
		 function );

		return( -1 );
	}
	PyErr_Clear();

	result = PyObject_IsInstance(
	          integer_object,
	          (PyObject *) &PyLong_Type );

	if( result == -1 )
	{
		pyvmdk_error_fetch(
		 error,
		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
		 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
		 "%s: unable to determine if integer object is of type long.",
		 function );

		return( -1 );
	}
	else if( result != 0 )
	{
		PyErr_Clear();

#if defined( HAVE_LONG_LONG )
		long_value = PyLong_AsUnsignedLongLong(
		              integer_object );
#else
		long_value = PyLong_AsUnsignedLong(
		              integer_object );
#endif
	}
#if PY_MAJOR_VERSION < 3
	if( result == 0 )
	{
		PyErr_Clear();

		result = PyObject_IsInstance(
		          integer_object,
		          (PyObject *) &PyInt_Type );

		if( result == -1 )
		{
			pyvmdk_error_fetch(
			 error,
			 LIBCERROR_ERROR_DOMAIN_RUNTIME,
			 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
			 "%s: unable to determine if integer object is of type int.",
			 function );

			return( -1 );
		}
		else if( result != 0 )
		{
			PyErr_Clear();

#if defined( HAVE_LONG_LONG )
			long_value = PyInt_AsUnsignedLongLongMask(
				      integer_object );
#else
			long_value = PyInt_AsUnsignedLongMask(
				      integer_object );
#endif
		}
	}
#endif /* PY_MAJOR_VERSION < 3 */
	if( result == 0 )
	{
		libcerror_error_set(
		 error,
		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
		 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
		 "%s: unsupported integer object type.",
		 function );

		return( -1 );
	}
	if( PyErr_Occurred() )
	{
		pyvmdk_error_fetch(
		 error,
		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
		 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
		 "%s: unable to convert integer object to long.",
		 function );

		return( -1 );
	}
#if defined( HAVE_LONG_LONG )
#if ( SIZEOF_LONG_LONG > 8 )
	if( ( long_value < (PY_LONG_LONG) 0 )
	 || ( long_value > (PY_LONG_LONG) UINT64_MAX ) )
#else
	if( long_value < (PY_LONG_LONG) 0 )
#endif
	{
		libcerror_error_set(
		 error,
		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
		 LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS,
		 "%s: invalid long value out of bounds.",
		 function );

		return( -1 );
	}
#else
#if ( SIZEOF_LONG > 8 )
	if( ( long_value < (long) 0 )
	 || ( long_value > (long) UINT64_MAX ) )
#else
	if( long_value < (PY_LONG_LONG) 0 )
#endif
	{
		libcerror_error_set(
		 error,
		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
		 LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS,
		 "%s: invalid long value out of bounds.",
		 function );

		return( -1 );
	}
#endif
	*value_64bit = (uint64_t) long_value;

	return( 1 );
}
예제 #12
0
/* Copies a Python int or long object to an unsigned 64-bit value
 * Returns 1 if successful or -1 on error
 */
int pyewf_integer_unsigned_copy_to_64bit(
     PyObject *integer_object,
     uint64_t *value_64bit,
     libcerror_error_t **error )
{
	PyObject *exception_string    = NULL;
	PyObject *exception_traceback = NULL;
	PyObject *exception_type      = NULL;
	PyObject *exception_value     = NULL;
	char *error_string            = NULL;
	static char *function         = "pyewf_integer_unsigned_copy_to_64bit";
	int result                    = 0;

#if defined( HAVE_LONG_LONG )
	PY_LONG_LONG long_value       = 0;
#else
	long long_value               = 0;
#endif

	if( integer_object == NULL )
	{
		libcerror_error_set(
		 error,
		 LIBCERROR_ERROR_DOMAIN_ARGUMENTS,
		 LIBCERROR_ARGUMENT_ERROR_INVALID_VALUE,
		 "%s: invalid integer object.",
		 function );

		return( -1 );
	}
	PyErr_Clear();

	result = PyObject_IsInstance(
	          integer_object,
	          (PyObject *) &PyLong_Type );

	if( result == -1 )
	{
		PyErr_Fetch(
		 &exception_type,
		 &exception_value,
		 &exception_traceback );

		exception_string = PyObject_Repr(
		                    exception_value );

		error_string = PyString_AsString(
		                exception_string );

		if( error_string != NULL )
		{
			libcerror_error_set(
			 error,
			 LIBCERROR_ERROR_DOMAIN_RUNTIME,
			 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
			 "%s: unable to determine if integer object is of type long with error: %s.",
			 function,
			 error_string );
		}
		else
		{
			libcerror_error_set(
			 error,
			 LIBCERROR_ERROR_DOMAIN_RUNTIME,
			 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
			 "%s: unable to determine if integer object is of type long.",
			 function );
		}
		Py_DecRef(
		 exception_string );

		return( -1 );
	}
	else if( result != 0 )
	{
		PyErr_Clear();

#if defined( HAVE_LONG_LONG )
		long_value = PyLong_AsUnsignedLongLong(
		              integer_object );
#else
		long_value = PyLong_AsUnsignedLong(
		              integer_object );
#endif
	}
	if( result == 0 )
	{
		PyErr_Clear();

		result = PyObject_IsInstance(
		          integer_object,
		          (PyObject *) &PyInt_Type );

		if( result == -1 )
		{
			PyErr_Fetch(
			 &exception_type,
			 &exception_value,
			 &exception_traceback );

			exception_string = PyObject_Repr(
					    exception_value );

			error_string = PyString_AsString(
					exception_string );

			if( error_string != NULL )
			{
				libcerror_error_set(
				 error,
				 LIBCERROR_ERROR_DOMAIN_RUNTIME,
				 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
				 "%s: unable to determine if integer object is of type int with error: %s.",
				 function,
				 error_string );
			}
			else
			{
				libcerror_error_set(
				 error,
				 LIBCERROR_ERROR_DOMAIN_RUNTIME,
				 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
				 "%s: unable to determine if integer object is of type int.",
				 function );
			}
			Py_DecRef(
			 exception_string );

			return( -1 );
		}
		else if( result != 0 )
		{
			PyErr_Clear();

#if defined( HAVE_LONG_LONG )
			long_value = PyInt_AsUnsignedLongLongMask(
				      integer_object );
#else
			long_value = PyInt_AsUnsignedLongMask(
				      integer_object );
#endif
		}
	}
	if( result == 0 )
	{
		libcerror_error_set(
		 error,
		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
		 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
		 "%s: unsupported integer object type.",
		 function );

		return( -1 );
	}
	if( PyErr_Occurred() )
	{
		PyErr_Fetch(
		 &exception_type,
		 &exception_value,
		 &exception_traceback );

		exception_string = PyObject_Repr(
				    exception_value );

		error_string = PyString_AsString(
				exception_string );

		if( error_string != NULL )
		{
			libcerror_error_set(
			 error,
			 LIBCERROR_ERROR_DOMAIN_RUNTIME,
			 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
			 "%s: unable to convert integer object to long with error: %s.",
			 function,
			 error_string );
		}
		else
		{
			libcerror_error_set(
			 error,
			 LIBCERROR_ERROR_DOMAIN_RUNTIME,
			 LIBCERROR_RUNTIME_ERROR_GET_FAILED,
			 "%s: unable to convert integer object to long.",
			 function );
		}
		Py_DecRef(
		 exception_string );

		return( -1 );
	}
#if defined( HAVE_LONG_LONG )
#if ( SIZEOF_LONG_LONG > 8 )
	if( ( long_value < (PY_LONG_LONG) 0 )
	 || ( long_value > (PY_LONG_LONG) UINT64_MAX ) )
#else
	if( long_value < (PY_LONG_LONG) 0 )
#endif
	{
		libcerror_error_set(
		 error,
		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
		 LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS,
		 "%s: invalid long value out of bounds.",
		 function );

		return( -1 );
	}
#else
#if ( SIZEOF_LONG > 8 )
	if( ( long_value < (long) 0 )
	 || ( long_value > (long) UINT64_MAX ) )
#else
	if( long_value < (PY_LONG_LONG) 0 )
#endif
	{
		libcerror_error_set(
		 error,
		 LIBCERROR_ERROR_DOMAIN_RUNTIME,
		 LIBCERROR_RUNTIME_ERROR_VALUE_OUT_OF_BOUNDS,
		 "%s: invalid long value out of bounds.",
		 function );

		return( -1 );
	}
#endif
	*value_64bit = (uint64_t) long_value;

	return( 1 );
}
예제 #13
0
파일: cfield.c 프로젝트: nanwu/pyston
static PyObject *
Z_set(void *ptr, PyObject *value, Py_ssize_t size)
{
    if (value == Py_None) {
        *(wchar_t **)ptr = NULL;
        Py_INCREF(value);
        return value;
    }
    if (PyString_Check(value)) {
        value = PyUnicode_FromEncodedObject(value,
                                            _ctypes_conversion_encoding,
                                            _ctypes_conversion_errors);
        if (!value)
            return NULL;
    } else if (PyInt_Check(value) || PyLong_Check(value)) {
#if SIZEOF_VOID_P == SIZEOF_LONG_LONG
        *(wchar_t **)ptr = (wchar_t *)PyInt_AsUnsignedLongLongMask(value);
#else
        *(wchar_t **)ptr = (wchar_t *)PyInt_AsUnsignedLongMask(value);
#endif
        Py_INCREF(Py_None);
        return Py_None;
    } else if (!PyUnicode_Check(value)) {
        PyErr_Format(PyExc_TypeError,
                     "unicode string or integer address expected instead of %s instance",
                     value->ob_type->tp_name);
        return NULL;
    } else
        Py_INCREF(value);
#ifdef HAVE_USABLE_WCHAR_T
    /* HAVE_USABLE_WCHAR_T means that Py_UNICODE and wchar_t is the same
       type.  So we can copy directly.  Hm, are unicode objects always NUL
       terminated in Python, internally?
     */
    *(wchar_t **)ptr = PyUnicode_AS_UNICODE(value);
    return value;
#else
    {
        /* We must create a wchar_t* buffer from the unicode object,
           and keep it alive */
        PyObject *keep;
        wchar_t *buffer;

        int size = PyUnicode_GET_SIZE(value);
        size += 1; /* terminating NUL */
        size *= sizeof(wchar_t);
        buffer = (wchar_t *)PyMem_Malloc(size);
        if (!buffer) {
            Py_DECREF(value);
            return PyErr_NoMemory();
        }
        memset(buffer, 0, size);
        keep = CAPSULE_NEW(buffer, CTYPES_CAPSULE_WCHAR_T);
        if (!keep) {
            Py_DECREF(value);
            PyMem_Free(buffer);
            return NULL;
        }
        *(wchar_t **)ptr = (wchar_t *)buffer;
        if (-1 == PyUnicode_AsWideChar((PyUnicodeObject *)value,
                                       buffer, PyUnicode_GET_SIZE(value))) {
            Py_DECREF(value);
            Py_DECREF(keep);
            return NULL;
        }
        Py_DECREF(value);
        return keep;
    }
#endif
}