mirror of
https://github.com/clearlinux/uwsgi.git
synced 2026-09-07 06:06:08 +00:00
theading support improvements
This commit is contained in:
@@ -4,11 +4,20 @@ extern struct uwsgi_server uwsgi;
|
||||
|
||||
void *simple_loop(void *arg1) {
|
||||
|
||||
int *core_ptr = (int *) arg1;
|
||||
int core_id = *core_ptr;
|
||||
long core_id = (long) arg1;
|
||||
PyThreadState *pts;
|
||||
|
||||
struct wsgi_request *wsgi_req = uwsgi.wsgi_requests[core_id];
|
||||
|
||||
pthread_setspecific(uwsgi.ut_key, (void *) wsgi_req);
|
||||
|
||||
uwsgi_log("started core %d\n", core_id);
|
||||
|
||||
if (core_id > 0) {
|
||||
pts = PyThreadState_New(uwsgi.main_thread->interp);
|
||||
pthread_setspecific(uwsgi.ut_save_key, (void *) pts);
|
||||
}
|
||||
|
||||
while (uwsgi.workers[uwsgi.mywid].manage_next_request) {
|
||||
|
||||
|
||||
@@ -18,11 +27,15 @@ void *simple_loop(void *arg1) {
|
||||
continue;
|
||||
}
|
||||
|
||||
uwsgi_get_gil();
|
||||
|
||||
if (wsgi_req_recv(wsgi_req)) {
|
||||
uwsgi_release_gil();
|
||||
continue;
|
||||
}
|
||||
|
||||
uwsgi_close_request(wsgi_req);
|
||||
uwsgi_release_gil();
|
||||
}
|
||||
|
||||
pthread_exit(NULL);
|
||||
|
||||
@@ -46,7 +46,9 @@ void master_loop(char **argv, char **environ) {
|
||||
#endif
|
||||
|
||||
int i,j;
|
||||
#ifdef UWSGI_UDP
|
||||
int rlen;
|
||||
#endif
|
||||
|
||||
struct timeval check_interval = {.tv_sec = 1,.tv_usec = 0 };
|
||||
|
||||
|
||||
+4
-4
@@ -105,13 +105,13 @@ int init_uwsgi_app(int loader, void *arg1, struct wsgi_request *wsgi_req, int ne
|
||||
}
|
||||
|
||||
#ifdef UWSGI_ASYNC
|
||||
wi->wsgi_environ = malloc(sizeof(PyObject*)*uwsgi.async);
|
||||
wi->wsgi_environ = malloc(sizeof(PyObject*)*uwsgi.cores);
|
||||
if (!wi->wsgi_environ) {
|
||||
uwsgi_error("malloc()");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
for(i=0;i<uwsgi.async;i++) {
|
||||
for(i=0;i<uwsgi.cores;i++) {
|
||||
wi->wsgi_environ[i] = PyDict_New();
|
||||
if (!wi->wsgi_environ[i]) {
|
||||
uwsgi_log("unable to allocate new env dictionary for app\n");
|
||||
@@ -171,13 +171,13 @@ int init_uwsgi_app(int loader, void *arg1, struct wsgi_request *wsgi_req, int ne
|
||||
}
|
||||
|
||||
#ifdef UWSGI_ASYNC
|
||||
wi->wsgi_args = malloc(sizeof(PyObject*)*uwsgi.async);
|
||||
wi->wsgi_args = malloc(sizeof(PyObject*)*uwsgi.cores);
|
||||
if (!wi->wsgi_args) {
|
||||
uwsgi_error("malloc()");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
for(i=0;i<uwsgi.async;i++) {
|
||||
for(i=0;i<uwsgi.cores;i++) {
|
||||
wi->wsgi_args[i] = PyTuple_New(wi->argc);
|
||||
if (!wi->wsgi_args[i]) {
|
||||
uwsgi_log("unable to allocate new tuple for app args\n");
|
||||
|
||||
@@ -12,6 +12,7 @@ PyObject *python_call(PyObject *callable, PyObject *args, int catch) {
|
||||
PyObject *pyret;
|
||||
|
||||
pyret = PyEval_CallObject(callable, args);
|
||||
|
||||
if (PyErr_Occurred()) {
|
||||
if (!catch) {
|
||||
PyErr_Print();
|
||||
|
||||
@@ -380,7 +380,7 @@ void wsgi_req_setup(struct wsgi_request *wsgi_req, int async_id) {
|
||||
#ifdef UWSGI_ASYNC
|
||||
wsgi_req->async_waiting_fd = -1;
|
||||
#endif
|
||||
wsgi_req->hvec = &uwsgi.async_hvec[wsgi_req->async_id];
|
||||
wsgi_req->hvec = uwsgi.async_hvec[wsgi_req->async_id];
|
||||
wsgi_req->buffer = uwsgi.async_buf[wsgi_req->async_id];
|
||||
|
||||
#ifdef UWSGI_ROUTING
|
||||
|
||||
@@ -968,6 +968,11 @@ int main(int argc, char *argv[], char *envp[]) {
|
||||
if (uwsgi.has_threads) {
|
||||
PyEval_InitThreads();
|
||||
uwsgi_log("threads support enabled\n");
|
||||
if (pthread_key_create(&uwsgi.ut_save_key, NULL)) {
|
||||
uwsgi_error("pthread_key_create()");
|
||||
exit(1);
|
||||
}
|
||||
pthread_setspecific(uwsgi.ut_save_key, (void *) PyThreadState_Get());
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -1437,12 +1442,16 @@ int main(int argc, char *argv[], char *envp[]) {
|
||||
|
||||
|
||||
|
||||
uwsgi.async_hvec = malloc((sizeof(struct iovec) * uwsgi.vec_size)*uwsgi.async);
|
||||
uwsgi.async_hvec = malloc(sizeof(struct iovec*)*uwsgi.cores);
|
||||
if (uwsgi.async_hvec == NULL) {
|
||||
uwsgi_log( "unable to allocate memory for iovec.\n");
|
||||
exit(1);
|
||||
}
|
||||
|
||||
for(i=0;i<uwsgi.cores;i++) {
|
||||
uwsgi.async_hvec[i] = malloc(sizeof(struct iovec) * uwsgi.vec_size);
|
||||
}
|
||||
|
||||
if (uwsgi.shared->options[UWSGI_OPTION_HARAKIRI] > 0 && !uwsgi.master_process) {
|
||||
signal(SIGALRM, (void *) &harakiri);
|
||||
}
|
||||
@@ -1544,10 +1553,10 @@ int main(int argc, char *argv[], char *envp[]) {
|
||||
uwsgi_error("pthread_key_create()");
|
||||
exit(1);
|
||||
}
|
||||
for(i=0;i<uwsgi.threads-1;i++) {
|
||||
for(i=1;i<uwsgi.threads;i++) {
|
||||
int j = i;
|
||||
a_thread = malloc(sizeof(pthread_t));
|
||||
pthread_create(a_thread, &pa, simple_loop, (void *) &i);
|
||||
uwsgi_log("started thread %d\n", i);
|
||||
pthread_create(a_thread, &pa, simple_loop, (void *) j);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1626,15 +1635,8 @@ cycle:
|
||||
}
|
||||
else {
|
||||
#endif
|
||||
wsgi_req_setup(uwsgi.wsgi_req, 0);
|
||||
|
||||
if (wsgi_req_accept(uwsgi.wsgi_req)) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (wsgi_req_recv(uwsgi.wsgi_req)) {
|
||||
continue;
|
||||
}
|
||||
int y = 0;
|
||||
simple_loop((void *) y);
|
||||
|
||||
#ifdef UWSGI_ASYNC
|
||||
}
|
||||
|
||||
@@ -14,8 +14,8 @@
|
||||
#define MAX_PYTHONPATH 64
|
||||
|
||||
#ifdef UWSGI_THREADING
|
||||
#define uwsgi_get_gil() if (uwsgi.has_threads) PyEval_AcquireLock()
|
||||
#define uwsgi_release_gil() if (uwsgi.has_threads) PyEval_ReleaseLock()
|
||||
#define uwsgi_get_gil() if (uwsgi.has_threads) { PyEval_AcquireLock(); PyThreadState_Swap((PyThreadState *) pthread_getspecific(uwsgi.ut_save_key)); }
|
||||
#define uwsgi_release_gil() if (uwsgi.has_threads) { pthread_setspecific(uwsgi.ut_save_key, (void *) PyThreadState_Swap(NULL)); PyEval_ReleaseLock();}
|
||||
#else
|
||||
#define uwsgi_get_gil()
|
||||
#define uwsgi_release_gil()
|
||||
@@ -554,7 +554,7 @@ struct uwsgi_server {
|
||||
|
||||
int vhost;
|
||||
|
||||
struct iovec *async_hvec;
|
||||
struct iovec **async_hvec;
|
||||
char **async_buf;
|
||||
char **async_post_buf;
|
||||
|
||||
@@ -795,6 +795,7 @@ struct uwsgi_server {
|
||||
int cores;
|
||||
int threads;
|
||||
pthread_key_t ut_key;
|
||||
pthread_key_t ut_save_key;
|
||||
};
|
||||
|
||||
struct uwsgi_cluster_node {
|
||||
@@ -1115,7 +1116,7 @@ struct wsgi_request *current_wsgi_req(void);
|
||||
inline struct wsgi_request *current_wsgi_req(void);
|
||||
#endif
|
||||
#else
|
||||
#define current_wsgi_req() uwsgi.wsgi_req
|
||||
#define current_wsgi_req() pthread_getspecific(uwsgi.ut_key)
|
||||
#endif
|
||||
|
||||
void sanitize_args(void);
|
||||
|
||||
+13
-11
@@ -99,6 +99,7 @@ int uwsgi_request_wsgi(struct wsgi_request *wsgi_req) {
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/* Standard WSGI request */
|
||||
if (!wsgi_req->uh.pktsize) {
|
||||
uwsgi_log( "Invalid WSGI request. skip.\n");
|
||||
@@ -117,6 +118,7 @@ int uwsgi_request_wsgi(struct wsgi_request *wsgi_req) {
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (!uwsgi.ignore_script_name) {
|
||||
|
||||
if (!wsgi_req->script_name)
|
||||
@@ -147,9 +149,9 @@ int uwsgi_request_wsgi(struct wsgi_request *wsgi_req) {
|
||||
#endif
|
||||
) {
|
||||
// a bit of magic: 1-1 = 0 / 0-1 = -1
|
||||
uwsgi_get_gil();
|
||||
//uwsgi_get_gil();
|
||||
wsgi_req->app_id = init_uwsgi_app(LOADER_DYN, (void *) wsgi_req, wsgi_req, uwsgi.single_interpreter-1);
|
||||
uwsgi_release_gil();
|
||||
//uwsgi_release_gil();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -181,9 +183,9 @@ int uwsgi_request_wsgi(struct wsgi_request *wsgi_req) {
|
||||
}
|
||||
|
||||
// set the interpreter
|
||||
uwsgi_get_gil();
|
||||
//uwsgi_get_gil();
|
||||
PyThreadState_Swap(wi->interpreter);
|
||||
uwsgi_release_gil();
|
||||
//uwsgi_release_gil();
|
||||
if (wi->chdir) {
|
||||
#ifdef UWSGI_DEBUG
|
||||
uwsgi_debug("chdir to %s\n", wi->chdir);
|
||||
@@ -197,6 +199,7 @@ int uwsgi_request_wsgi(struct wsgi_request *wsgi_req) {
|
||||
wi->requests++;
|
||||
|
||||
|
||||
|
||||
if (wsgi_req->protocol_len < 5) {
|
||||
uwsgi_log( "INVALID PROTOCOL: %.*s\n", wsgi_req->protocol_len, wsgi_req->protocol);
|
||||
internal_server_error(wsgi_req->poll.fd, "invalid HTTP protocol !!!");
|
||||
@@ -219,17 +222,16 @@ int uwsgi_request_wsgi(struct wsgi_request *wsgi_req) {
|
||||
wsgi_req->async_args = wi->wsgi_args;
|
||||
#endif
|
||||
|
||||
uwsgi_get_gil();
|
||||
//uwsgi_get_gil();
|
||||
|
||||
Py_INCREF((PyObject *)wsgi_req->async_environ);
|
||||
|
||||
|
||||
|
||||
for (i = 0; i < wsgi_req->var_cnt; i += 2) {
|
||||
/*
|
||||
#ifdef UWSGI_DEBUG
|
||||
uwsgi_debug("%.*s: %.*s\n", wsgi_req->hvec[i].iov_len, wsgi_req->hvec[i].iov_base, wsgi_req->hvec[i+1].iov_len, wsgi_req->hvec[i+1].iov_base);
|
||||
#endif
|
||||
*/
|
||||
#ifdef PYTHREE
|
||||
pydictkey = PyUnicode_DecodeLatin1(wsgi_req->hvec[i].iov_base, wsgi_req->hvec[i].iov_len, "ignore");
|
||||
pydictvalue = PyUnicode_DecodeLatin1(wsgi_req->hvec[i + 1].iov_base, wsgi_req->hvec[i + 1].iov_len, "ignore");
|
||||
@@ -242,7 +244,6 @@ int uwsgi_request_wsgi(struct wsgi_request *wsgi_req) {
|
||||
Py_DECREF(pydictvalue);
|
||||
}
|
||||
|
||||
|
||||
if (wsgi_req->uh.modifier1 == UWSGI_MODIFIER_MANAGE_PATH_INFO) {
|
||||
pydictkey = PyDict_GetItemString(wsgi_req->async_environ, "SCRIPT_NAME");
|
||||
if (pydictkey) {
|
||||
@@ -263,9 +264,9 @@ int uwsgi_request_wsgi(struct wsgi_request *wsgi_req) {
|
||||
|
||||
// set wsgi vars
|
||||
|
||||
uwsgi_release_gil();
|
||||
|
||||
if (uwsgi.post_buffering > 0 && wsgi_req->post_cl > (size_t) uwsgi.post_buffering) {
|
||||
//uwsgi_release_gil();
|
||||
wsgi_req->async_post = tmpfile();
|
||||
if (!wsgi_req->async_post) {
|
||||
uwsgi_error("tmpfile()");
|
||||
@@ -294,15 +295,16 @@ int uwsgi_request_wsgi(struct wsgi_request *wsgi_req) {
|
||||
post_remains -= post_chunk;
|
||||
}
|
||||
rewind(wsgi_req->async_post);
|
||||
//uwsgi_get_gil();
|
||||
}
|
||||
else {
|
||||
wsgi_req->async_post = fdopen(wsgi_req->poll.fd, "r");
|
||||
}
|
||||
|
||||
uwsgi_get_gil();
|
||||
|
||||
wsgi_req->async_result = (*wi->request_subhandler)(wsgi_req, wi);
|
||||
|
||||
|
||||
if (wsgi_req->async_result) {
|
||||
|
||||
|
||||
@@ -356,7 +358,7 @@ clear:
|
||||
PyThreadState_Swap(uwsgi.main_thread);
|
||||
}
|
||||
|
||||
uwsgi_release_gil();
|
||||
//uwsgi_release_gil();
|
||||
|
||||
clear2:
|
||||
|
||||
|
||||
@@ -21,9 +21,11 @@ PyObject *py_uwsgi_spit(PyObject * self, PyObject * args) {
|
||||
// use writev()
|
||||
|
||||
// is a Web3 response ?
|
||||
/*
|
||||
if (PyTuple_Size(args) == 3) {
|
||||
shift = 0;
|
||||
}
|
||||
*/
|
||||
|
||||
head = PyTuple_GetItem(args, 0+shift);
|
||||
if (!head) {
|
||||
|
||||
+2
-1
@@ -62,7 +62,7 @@ void *uwsgi_request_subhandler_wsgi(struct wsgi_request *wsgi_req, struct uwsgi_
|
||||
|
||||
wsgi_req->async_app = wi->wsgi_callable ;
|
||||
|
||||
PyDict_SetItemString(uwsgi.embedded_dict, "env", wsgi_req->async_environ);
|
||||
//PyDict_SetItemString(uwsgi.embedded_dict, "env", wsgi_req->async_environ);
|
||||
|
||||
// TODO: fix here
|
||||
//PyDict_SetItemString(wsgi_req->async_environ, "x-wsgiorg.uwsgi.version", uwsgi_version);
|
||||
@@ -79,6 +79,7 @@ void *uwsgi_request_subhandler_wsgi(struct wsgi_request *wsgi_req, struct uwsgi_
|
||||
// call
|
||||
|
||||
|
||||
|
||||
PyTuple_SetItem(wsgi_req->async_args, 0, wsgi_req->async_environ);
|
||||
return python_call(wsgi_req->async_app, wsgi_req->async_args, uwsgi.catch_exceptions);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user