Data-ReqRep-Shared
view release on metacpan or search on metacpan
void
recv(self)
SV *self
PREINIT:
EXTRACT_HANDLE("Data::ReqRep::Shared", self);
const char *str;
uint32_t len;
uint64_t id;
bool utf8;
PPCODE:
int r = reqrep_try_recv(h, &str, &len, &utf8, &id);
if (r == -1) croak("Data::ReqRep::Shared: out of memory");
if (r == 1) {
SV *sv = newSVpvn(str, len);
if (utf8) SvUTF8_on(sv);
mXPUSHs(sv);
mXPUSHu((UV)id);
}
void
recv_wait(self, ...)
SV *self
PREINIT:
EXTRACT_HANDLE("Data::ReqRep::Shared", self);
double timeout = -1;
const char *str;
uint32_t len;
uint64_t id;
bool utf8;
PPCODE:
if (items > 1 && (SvGETMAGIC(ST(1)), SvOK(ST(1)))) timeout = SvNV(ST(1));
REEXTRACT_HANDLE("Data::ReqRep::Shared", self);
int r = reqrep_recv_wait(h, &str, &len, &utf8, &id, timeout);
if (r == -1) croak("Data::ReqRep::Shared: out of memory");
if (r == 1) {
SV *sv = newSVpvn(str, len);
if (utf8) SvUTF8_on(sv);
mXPUSHs(sv);
mXPUSHu((UV)id);
}
void
recv_multi(self, count)
SV *self
UV count
PREINIT:
EXTRACT_HANDLE("Data::ReqRep::Shared", self);
const char *str;
uint32_t len;
uint64_t id;
bool utf8;
PPCODE:
/* Hoist Perl SV construction out of process-shared futex mutex. */
struct { char *buf; uint32_t len; uint64_t id; bool utf8; } *items_buf = NULL;
UV n = 0;
int last_r = 0;
int oom = 0;
/* Cap count at the request-queue capacity: the queue can't hold more than
* req_cap items, so a single recv_multi can't return more than that. This
* also prevents an unvalidated huge count from overflowing the malloc size
* ((size_t)count * sizeof wraps -> tiny alloc -> heap overflow in the locked
* drain below). */
recv_wait_multi(self, count, ...)
SV *self
UV count
PREINIT:
EXTRACT_HANDLE("Data::ReqRep::Shared", self);
double timeout = -1;
const char *str;
uint32_t len;
uint64_t id;
bool utf8;
PPCODE:
if (items > 2 && (SvGETMAGIC(ST(2)), SvOK(ST(2)))) timeout = SvNV(ST(2));
REEXTRACT_HANDLE("Data::ReqRep::Shared", self);
/* Block until at least 1 */
int r = reqrep_recv_wait(h, &str, &len, &utf8, &id, timeout);
if (r == -1) croak("Data::ReqRep::Shared: out of memory");
if (r != 1) XSRETURN(0);
{
SV *sv = newSVpvn(str, len);
if (utf8) SvUTF8_on(sv);
mXPUSHs(sv);
void
drain(self, ...)
SV *self
PREINIT:
EXTRACT_HANDLE("Data::ReqRep::Shared", self);
const char *str;
uint32_t len;
uint64_t id;
bool utf8;
uint32_t max_count;
PPCODE:
max_count = (items > 1 && (SvGETMAGIC(ST(1)), SvOK(ST(1)))) ? (uint32_t)SvUV(ST(1)) : UINT32_MAX;
/* Hoist SV construction out of the mutex (see recv_multi). */
struct drain_item { char *buf; uint32_t len; uint64_t id; bool utf8; struct drain_item *next; } *drained_head = NULL, *drained_tail = NULL;
UV drained_n = 0;
int last_r = 0;
int oom = 0;
REEXTRACT_HANDLE("Data::ReqRep::Shared", self);
reqrep_mutex_lock(h->hdr);
while (max_count-- > 0) {
last_r = reqrep_recv_locked(h, &str, &len, &utf8, &id);
sv_setiv(SvRV(self), 0);
reqrep_destroy(h);
void
recv(self)
SV *self
PREINIT:
EXTRACT_HANDLE("Data::ReqRep::Shared::Int", self);
int64_t value;
uint64_t id;
PPCODE:
if (reqrep_int_try_recv(h, &value, &id)) {
mXPUSHi((IV)value);
mXPUSHu((UV)id);
}
void
recv_wait(self, ...)
SV *self
PREINIT:
EXTRACT_HANDLE("Data::ReqRep::Shared::Int", self);
double timeout = -1;
int64_t value;
uint64_t id;
PPCODE:
if (items > 1 && (SvGETMAGIC(ST(1)), SvOK(ST(1)))) timeout = SvNV(ST(1));
REEXTRACT_HANDLE("Data::ReqRep::Shared::Int", self);
if (reqrep_int_recv_wait(h, &value, &id, timeout)) {
mXPUSHi((IV)value);
mXPUSHu((UV)id);
}
bool
reply(self, id, value)
SV *self
( run in 1.165 second using v1.01-cache-2.11-cpan-92ad3014f07 )