mirror of
https://github.com/clearlinux/uwsgi.git
synced 2026-09-01 11:15:57 +00:00
implemented perl spooler and fixed a leak in the CPython one
This commit is contained in:
@@ -63,6 +63,8 @@ struct uwsgi_perl {
|
||||
|
||||
char *shell;
|
||||
int shell_oneshot;
|
||||
|
||||
CV *spooler;
|
||||
};
|
||||
|
||||
void init_perl_embedded_module(void);
|
||||
|
||||
@@ -889,6 +889,59 @@ static void uwsgi_perl_hijack(void) {
|
||||
|
||||
}
|
||||
|
||||
static void uwsgi_perl_add_item(char *key, uint16_t keylen, char *val, uint16_t vallen, void *data) {
|
||||
|
||||
HV *spool_dict = (HV*) data;
|
||||
|
||||
hv_store(spool_dict, key, keylen, newSVpv(val, vallen), 0);
|
||||
}
|
||||
|
||||
|
||||
static int uwsgi_perl_spooler(char *filename, char *buf, uint16_t len, char *body, size_t body_len) {
|
||||
|
||||
int ret = -1;
|
||||
|
||||
if (!uperl.spooler) return 0;
|
||||
|
||||
dSP;
|
||||
ENTER;
|
||||
SAVETMPS;
|
||||
PUSHMARK(SP);
|
||||
|
||||
HV *spool_dict = newHV();
|
||||
|
||||
if (uwsgi_hooked_parse(buf, len, uwsgi_perl_add_item, (void *) spool_dict)) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
hv_store(spool_dict, "spooler_task_name", 18, newSVpv(filename, 0), 0);
|
||||
|
||||
if (body && body_len > 0) {
|
||||
hv_store(spool_dict, "body", 4, newSVpv(body, body_len), 0);
|
||||
}
|
||||
|
||||
XPUSHs( sv_2mortal((SV*)newRV_noinc((SV*)spool_dict)) );
|
||||
PUTBACK;
|
||||
|
||||
call_sv( SvRV((SV*)uperl.spooler), G_SCALAR|G_EVAL);
|
||||
|
||||
SPAGAIN;
|
||||
if(SvTRUE(ERRSV)) {
|
||||
uwsgi_log("[uwsgi-spooler-perl error] %s", SvPV_nolen(ERRSV));
|
||||
ret = -1;
|
||||
}
|
||||
else {
|
||||
ret = POPi;
|
||||
}
|
||||
|
||||
PUTBACK;
|
||||
FREETMPS;
|
||||
LEAVE;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
|
||||
struct uwsgi_plugin psgi_plugin = {
|
||||
|
||||
@@ -916,4 +969,6 @@ struct uwsgi_plugin psgi_plugin = {
|
||||
.atexit = uwsgi_perl_atexit,
|
||||
|
||||
.magic = uwsgi_perl_magic,
|
||||
|
||||
.spooler = uwsgi_perl_spooler,
|
||||
};
|
||||
|
||||
@@ -245,6 +245,13 @@ XS(XS_register_signal) {
|
||||
|
||||
}
|
||||
|
||||
XS(XS_spooler) {
|
||||
dXSARGS;
|
||||
psgi_check_args(1);
|
||||
uperl.spooler = (CV *) newRV_inc(ST(0));
|
||||
XSRETURN_YES;
|
||||
}
|
||||
|
||||
XS(XS_register_rpc) {
|
||||
dXSARGS;
|
||||
|
||||
@@ -948,4 +955,6 @@ void init_perl_embedded_module() {
|
||||
psgi_xs(sharedarea_readfast);
|
||||
psgi_xs(sharedarea_write);
|
||||
psgi_xs(sharedarea_wait);
|
||||
|
||||
psgi_xs(spooler);
|
||||
}
|
||||
|
||||
@@ -1585,7 +1585,11 @@ void uwsgi_python_add_item(char *key, uint16_t keylen, char *val, uint16_t valle
|
||||
|
||||
PyObject *pydict = (PyObject *) data;
|
||||
|
||||
PyDict_SetItem(pydict, PyString_FromStringAndSize(key, keylen), PyString_FromStringAndSize(val, vallen));
|
||||
PyObject *o_key = PyString_FromStringAndSize(key, keylen);
|
||||
PyObject *zero = PyString_FromStringAndSize(val, vallen);
|
||||
PyDict_SetItem(pydict, o_key, zero);
|
||||
Py_DECREF(o_key);
|
||||
Py_DECREF(zero);
|
||||
}
|
||||
|
||||
int uwsgi_python_spooler(char *filename, char *buf, uint16_t len, char *body, size_t body_len) {
|
||||
@@ -1594,9 +1598,6 @@ int uwsgi_python_spooler(char *filename, char *buf, uint16_t len, char *body, si
|
||||
|
||||
UWSGI_GET_GIL;
|
||||
|
||||
PyObject *spool_dict = PyDict_New();
|
||||
PyObject *spool_func, *pyargs, *ret;
|
||||
|
||||
if (!random_seed_reset) {
|
||||
uwsgi_python_reset_random_seed();
|
||||
random_seed_reset = 1;
|
||||
@@ -1608,14 +1609,19 @@ int uwsgi_python_spooler(char *filename, char *buf, uint16_t len, char *body, si
|
||||
return 0;
|
||||
}
|
||||
|
||||
spool_func = PyDict_GetItemString(up.embedded_dict, "spooler");
|
||||
PyObject *spool_func = PyDict_GetItemString(up.embedded_dict, "spooler");
|
||||
if (!spool_func) {
|
||||
// ignore
|
||||
UWSGI_RELEASE_GIL;
|
||||
return 0;
|
||||
}
|
||||
|
||||
PyObject *spool_dict = PyDict_New();
|
||||
PyObject *pyargs, *ret;
|
||||
|
||||
|
||||
if (uwsgi_hooked_parse(buf, len, uwsgi_python_add_item, spool_dict)) {
|
||||
Py_DECREF(spool_dict);
|
||||
// malformed packet, destroy it
|
||||
UWSGI_RELEASE_GIL;
|
||||
return -2;
|
||||
@@ -1623,7 +1629,9 @@ int uwsgi_python_spooler(char *filename, char *buf, uint16_t len, char *body, si
|
||||
|
||||
pyargs = PyTuple_New(1);
|
||||
|
||||
PyDict_SetItemString(spool_dict, "spooler_task_name", PyString_FromString(filename));
|
||||
PyObject *zero = PyString_FromString(filename);
|
||||
PyDict_SetItemString(spool_dict, "spooler_task_name", zero);
|
||||
Py_DECREF(zero);
|
||||
|
||||
if (body && body_len > 0) {
|
||||
PyDict_SetItemString(spool_dict, "body", PyString_FromStringAndSize(body, body_len));
|
||||
@@ -1634,12 +1642,18 @@ int uwsgi_python_spooler(char *filename, char *buf, uint16_t len, char *body, si
|
||||
|
||||
if (ret) {
|
||||
if (!PyInt_Check(ret)) {
|
||||
Py_DECREF(ret);
|
||||
Py_DECREF(spool_dict);
|
||||
Py_DECREF(pyargs);
|
||||
// error, retry
|
||||
UWSGI_RELEASE_GIL;
|
||||
return -1;
|
||||
}
|
||||
|
||||
int retval = (int) PyInt_AsLong(ret);
|
||||
Py_DECREF(ret);
|
||||
Py_DECREF(spool_dict);
|
||||
Py_DECREF(pyargs);
|
||||
UWSGI_RELEASE_GIL;
|
||||
return retval;
|
||||
|
||||
@@ -1648,6 +1662,9 @@ int uwsgi_python_spooler(char *filename, char *buf, uint16_t len, char *body, si
|
||||
if (PyErr_Occurred())
|
||||
PyErr_Print();
|
||||
|
||||
Py_DECREF(spool_dict);
|
||||
Py_DECREF(pyargs);
|
||||
|
||||
// error, retry
|
||||
UWSGI_RELEASE_GIL;
|
||||
return -1;
|
||||
|
||||
Reference in New Issue
Block a user