File: raw.c

package info (click to toggle)
uwsgi 2.0.31-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 6,564 kB
  • sloc: ansic: 87,066; python: 7,004; cpp: 1,133; java: 708; perl: 678; sh: 585; ruby: 555; makefile: 148; xml: 130; cs: 121; objc: 37; php: 28; erlang: 20; javascript: 11
file content (90 lines) | stat: -rw-r--r-- 2,442 bytes parent folder | download | duplicates (4)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
#include "uwsgi_python.h"

extern struct uwsgi_server uwsgi;
extern struct uwsgi_python up;

static int manage_raw_response(struct wsgi_request *wsgi_req) {
	int ret = 0;
	if (!wsgi_req->async_force_again) {
		ret = uwsgi_python_send_body(wsgi_req, (PyObject *) wsgi_req->async_result);
		if (ret == 0) {
			if (PyInt_Check((PyObject *) wsgi_req->async_result) || PyObject_HasAttrString((PyObject *) wsgi_req->async_result, "fileno")) {
				// is it a file ?
				int fd = PyObject_AsFileDescriptor((PyObject *) wsgi_req->async_result);
				if (fd >= 0) {
					wsgi_req->sendfile_fd = fd;
					uwsgi_response_sendfile_do(wsgi_req, fd, 0, 0);
					wsgi_req->sendfile_fd = -1;
					return UWSGI_OK;
				}
			}
		}
	}
	if (ret == 0) {
		if (!wsgi_req->async_placeholder) {
			wsgi_req->async_placeholder = PyObject_GetIter((PyObject *) wsgi_req->async_result);
			if (!wsgi_req->async_placeholder)
				return UWSGI_OK;
		}

		PyObject *pychunk = PyIter_Next((PyObject *) wsgi_req->async_placeholder);
		if (!pychunk)
			return UWSGI_OK;
		ret = uwsgi_python_send_body(wsgi_req, pychunk);
		if (ret == 0) {
			if (PyInt_Check(pychunk) || PyObject_HasAttrString(pychunk, "fileno")) {
				// is it a file ?
				int fd = PyObject_AsFileDescriptor(pychunk);
				if (fd >= 0) {
					wsgi_req->sendfile_fd = fd;
					uwsgi_response_sendfile_do(wsgi_req, fd, 0, 0);
					wsgi_req->sendfile_fd = -1;
				}
			}
		}
		Py_DECREF(pychunk);
		return UWSGI_AGAIN;
	}
	return UWSGI_OK;
}

int uwsgi_request_python_raw(struct wsgi_request *wsgi_req) {
	if (!up.raw_callable)
		return UWSGI_OK;

	// back from async
	if (wsgi_req->async_force_again) {
		UWSGI_GET_GIL int ret = manage_raw_response(wsgi_req);
		if (ret == UWSGI_AGAIN) {
			wsgi_req->async_force_again = 1;
			UWSGI_RELEASE_GIL return UWSGI_AGAIN;
		}
		goto end;
	}

	UWSGI_GET_GIL PyObject * args = PyTuple_New(1);
	PyTuple_SetItem(args, 0, PyInt_FromLong(wsgi_req->fd));
	wsgi_req->async_result = PyObject_CallObject(up.raw_callable, args);
	Py_DECREF(args);
	if (wsgi_req->async_result) {
		for (;;) {
			int ret = manage_raw_response(wsgi_req);
			if (ret == UWSGI_AGAIN) {
				wsgi_req->async_force_again = 1;
				if (uwsgi.async > 1) {
					UWSGI_RELEASE_GIL return UWSGI_AGAIN;
				}
				continue;
			}
			break;
		}
	}
end:
	if (PyErr_Occurred())
		PyErr_Print();
	if (wsgi_req->async_result) {
		Py_DECREF((PyObject *) wsgi_req->async_result);
	}
	UWSGI_RELEASE_GIL;
	return UWSGI_OK;
}