Ejemplo n.º 1
0
// NewTuple returns a new *Tuple of the specified size.  However the entries are
// all set to NULL, so the tuple should not be shared, especially with Python
// code, until the entries have all been set.
//
// Return value: New Reference.
func NewTuple(size int64) (*Tuple, error) {
	ret := C.PyTuple_New(C.Py_ssize_t(size))
	if ret == nil {
		return nil, exception()
	}
	return newTuple(ret), nil
}
Ejemplo n.º 2
0
// PackTuple returns a new *Tuple which contains the arguments.  This tuple is
// ready to use.
//
// Return value: New Reference.
func PackTuple(items ...Object) (*Tuple, error) {
	ret := C.PyTuple_New(C.Py_ssize_t(len(items)))
	if ret == nil {
		return nil, exception()
	}

	// Since the ob_item array has a size of 1, Go won't let us index more than
	// a single entry, and if we try and use our own local type definition with
	// a flexible array member then cgo converts it to [0]byte which is even
	// less useful.  So, we resort to pointer manipulation - which is
	// unfortunate, as it's messy in Go.

	// base is a pointer to the first item in the array of PyObject pointers.
	// step is the size of a PyObject * (i.e. the number of bytes we need to add
	// to get to the next item).
	base := unsafe.Pointer(&(*C.PyTupleObject)(unsafe.Pointer(ret)).ob_item[0])
	step := uintptr(C.tupleItemSize())

	for _, item := range items {
		item.Incref()
		*(**C.PyObject)(base) = c(item)

		// Move base to point to the next item, by incrementing by step bytes
		base = unsafe.Pointer(uintptr(base) + step)
	}

	return newTuple(ret), nil
}
Ejemplo n.º 3
0
// encodeTuple translates a Go array to a Python object.
func encodeTuple(array []interface{}) (pyTuple *C.PyObject, err error) {
	if len(array) == 0 {
		pyTuple = pyEmptyTuple
		C.INCREF(pyTuple)
	} else {
		pyTuple = C.PyTuple_New(C.Py_ssize_t(len(array)))

		var ok bool

		defer func() {
			if !ok {
				C.DECREF(pyTuple)
				pyTuple = nil
			}
		}()

		for i, item := range array {
			var pyItem *C.PyObject

			if pyItem, err = encode(item); err != nil {
				return
			}

			C.Tuple_SET_ITEM(pyTuple, C.Py_ssize_t(i), pyItem)
		}

		ok = true
	}

	return
}
Ejemplo n.º 4
0
func threadInit() (defaultThreadState *C.PyThreadState) {
	initLock.Lock()
	defer initLock.Unlock()

	if !initialized {
		C.Py_InitializeEx(0)
		C.PyEval_InitThreads()
		C.PySys_SetArgvEx(0, nil, 0)

		pyEmptyTuple = C.PyTuple_New(0)
		falseObject = &object{C.False_INCREF()}
		trueObject = &object{C.True_INCREF()}

		defaultThreadState = C.PyEval_SaveThread()

		initialized = true
	}

	return
}
Ejemplo n.º 5
0
func GenerateEnviron(r *http.Request) *C.PyObject {
	_environ := C.PyDict_New()

	for k, _items := range r.Header {
		_values_tuple := C.PyTuple_New(C.Py_ssize_t(len(_items)))
		for i, _item := range _items {
			C.PyTuple_SetItem(
				_values_tuple,
				C.Py_ssize_t(i),
				PyString_FromString(_item),
			)
		}
		C.PyDict_SetItem(
			_environ,
			PyString_FromString(k),
			_values_tuple,
		)
	}
	//_environ = upgrade_to_wsgi(r, _environ)

	return _environ
}
Ejemplo n.º 6
0
func interfaceToPyObj(o interface{}) *C.PyObject {
	switch o.(type) {
	case int:
		return C.PyInt_FromLong(C.long(o.(int)))
	case int64:
		return C.PyInt_FromLong(C.long(o.(int64)))
	case string:
		strvalue := C.CString(o.(string))
		defer C.free(unsafe.Pointer(strvalue))
		return C.PyString_FromStringAndSize(strvalue, C.Py_ssize_t(len(o.(string))))
	case map[interface{}]interface{}:
		dict := C.PyDict_New()
		for key, value := range o.(map[interface{}]interface{}) {
			dictAddItem(dict, key, value)
		}
		return dict
	case map[string]string:
		dict := C.PyDict_New()
		for key, value := range o.(map[string]string) {
			dictAddItem(dict, key, value)
		}
		return dict
	case map[string]interface{}:
		dict := C.PyDict_New()
		for key, value := range o.(map[string]interface{}) {
			dictAddItem(dict, key, value)
		}
		return dict
	case []interface{}:
		list := C.PyTuple_New(C.Py_ssize_t(len(o.([]interface{}))))
		for i := range o.([]interface{}) {
			C.PyTuple_SetItem(list, C.Py_ssize_t(i), interfaceToPyObj(o.([]interface{})[i]))
		}
		return list
	default:
		return C.PyNone()
	}
}
Ejemplo n.º 7
0
// PyObject* PyTuple_New(Py_ssize_t len)
// Return value: New reference.
// Return a new tuple object of size len, or NULL on failure.
//
// Changed in version 2.5: This function used an int type for len. This might require changes in your code for properly supporting 64-bit systems.
func PyTuple_New(sz int) *PyObject {
	return togo(C.PyTuple_New(C.Py_ssize_t(sz)))
}
Ejemplo n.º 8
0
func upgrade_header_to_wsgi(r *http.Request) *C.PyObject {
	_environ := C.PyDict_New()

	for k, _items := range r.Header {
		_values_tuple := C.PyTuple_New(C.Py_ssize_t(len(_items)))
		for i, _item := range _items {
			C.PyTuple_SetItem(
				_values_tuple,
				C.Py_ssize_t(i),
				PyString_FromString(_item),
			)
		}

		// convert header name
		_k := strings.ToUpper(strings.Replace(k, "-", "_", -1))
		C.PyDict_SetItem(
			_environ,
			PyString_FromString("HTTP_"+_k),
			_values_tuple,
		)
	}

	C.PyDict_SetItem(
		_environ,
		PyString_FromString("X_FROM"),
		PyString_FromString("gowsgi"),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("REQUEST_METHOD"),
		PyString_FromString(r.Method),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("SCRIPT_NAME"),
		PyString_FromString(r.URL.Path),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("PATH_INFO"),
		PyString_FromString(r.URL.Path),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("QUERY_STRING"),
		PyString_FromString(r.URL.RawQuery),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("CONTENT_TYPE"),
		PyString_FromString(""),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("CONTENT_LENGTH"),
		PyString_FromString("0"),
	)

	_host, _port, _ := net.SplitHostPort(r.Host)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("SERVER_NAME"),
		PyString_FromString(_host),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("SERVER_PORT"),
		PyString_FromString(_port),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("SERVER_PROTOCOL"),
		PyString_FromString(r.Proto),
	)

	C.PyDict_SetItem(
		_environ,
		PyString_FromString("wsgi.url_scheme"),
		PyString_FromString(strings.ToLower(strings.Split(r.Proto, "/")[0])),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("wsgi.multithread"),
		C.PyBool_FromLong(1),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("wsgi.multiprocess"),
		C.PyBool_FromLong(1),
	)
	C.PyDict_SetItem(
		_environ,
		PyString_FromString("wsgi.run_once"),
		C.PyBool_FromLong(0),
	)

	return _environ
}
Ejemplo n.º 9
0
// NewTuple returns a new *PyObject of the specified size. However the entries
// are all set to NULL, so the tuple should not be shared, especially with
// Python code, until the entries have all been set.
//
// Return value: New Reference.
func NewTuple(size int) *Tuple {
	return (*Tuple)(PyObjectToGO(C.PyTuple_New(C.Py_ssize_t(size))))
}
Ejemplo n.º 10
0
// NewTuple returns a new *Tuple of the specified size.  However the entries are
// all set to NULL, so the tuple should not be shared, especially with Python
// code, until the entries have all been set.
//
// Return value: New Reference.
func NewTuple(size int) *Tuple {
	ret := C.PyTuple_New(C.Py_ssize_t(size))
	return newTuple(ret)
}