static PHP_METHOD(swoole_msgqueue, pop) { long type = 1; swQueue_data out; if (zend_parse_parameters(ZEND_NUM_ARGS(), "|l", &type) == FAILURE) { RETURN_FALSE; } swMsgQueue *queue = swoole_get_object(getThis()); out.mtype = type; int length = swMsgQueue_pop(queue, &out, sizeof(out.mdata)); if (length < 0) { RETURN_FALSE; } RETURN_STRINGL(out.mdata, length); }
static int swProcessPool_worker_loop(swProcessPool *pool, swWorker *worker) { struct { long mtype; swEventData buf; } out; int n = 0, ret; int task_n, worker_task_always = 0; if (pool->max_request < 1) { task_n = 1; worker_task_always = 1; } else { task_n = pool->max_request; n = swoole_system_random(1, pool->max_request / 2); if (n > 0) { task_n += n; } } /** * Use from_fd save the task_worker->id */ out.buf.info.from_fd = worker->id; if (pool->dispatch_mode == SW_DISPATCH_QUEUE) { out.mtype = 0; } else { out.mtype = worker->id + 1; } while (SwooleG.running > 0 && task_n > 0) { /** * fetch task */ if (pool->use_msgqueue) { n = swMsgQueue_pop(pool->queue, (swQueue_data *) &out, sizeof(out.buf)); if (n < 0 && errno != EINTR) { swSysError("[Worker#%d] msgrcv() failed.", worker->id); } } else if (pool->use_socket) { int fd = accept(pool->stream->socket, NULL, NULL); if (fd < 0) { if (errno == EAGAIN || errno == EINTR) { continue; } else { swSysError("accept(%d) failed.", pool->stream->socket); break; } } n = swStream_recv_blocking(fd, (void*) &out.buf, sizeof(out.buf)); if (n == SW_CLOSE) { close(fd); continue; } pool->stream->last_connection = fd; } else { n = read(worker->pipe_worker, &out.buf, sizeof(out.buf)); if (n < 0 && errno != EINTR) { swSysError("[Worker#%d] read(%d) failed.", worker->id, worker->pipe_worker); } } /** * timer */ if (n < 0) { if (errno == EINTR && SwooleG.signal_alarm) { alarm_handler: SwooleG.signal_alarm = 0; swTimer_select(&SwooleG.timer); } continue; } /** * do task */ worker->status = SW_WORKER_BUSY; worker->request_time = time(NULL); ret = pool->onTask(pool, &out.buf); worker->status = SW_WORKER_IDLE; worker->request_time = 0; worker->traced = 0; if (pool->use_socket && pool->stream->last_connection > 0) { int _end = 0; swSocket_write_blocking(pool->stream->last_connection, (void *) &_end, sizeof(_end)); close(pool->stream->last_connection); pool->stream->last_connection = 0; } /** * timer */ if (SwooleG.signal_alarm) { goto alarm_handler; } if (ret >= 0 && !worker_task_always) { task_n--; } } return SW_OK; }
static int swProcessPool_worker_loop(swProcessPool *pool, swWorker *worker) { struct { long mtype; swEventData buf; } out; int n, ret; int task_n, worker_task_always = 0; if (pool->max_request < 1) { task_n = 1; worker_task_always = 1; } else { task_n = pool->max_request; } /** * Use from_fd save the task_worker->id */ out.buf.info.from_fd = worker->id; if (pool->dispatch_mode == SW_DISPATCH_QUEUE) { out.mtype = 0; } else { out.mtype = worker->id + 1; } while (SwooleG.running > 0 && task_n > 0) { if (pool->use_msgqueue) { n = swMsgQueue_pop(pool->queue, (swQueue_data *) &out, sizeof(out.buf)); if (n < 0 && errno != EINTR) { swSysError("[Worker#%d] msgrcv() failed.", worker->id); } } else { n = read(worker->pipe_worker, &out.buf, sizeof(out.buf)); if (n < 0 && errno != EINTR) { swSysError("[Worker#%d] read(%d) failed.", worker->id, worker->pipe_worker); } } if (n < 0) { if (errno == EINTR && SwooleG.signal_alarm) { swTimer_select(&SwooleG.timer); } continue; } SwooleWG.worker->status = SW_WORKER_BUSY; ret = pool->onTask(pool, &out.buf); SwooleWG.worker->status = SW_WORKER_IDLE; if (ret >= 0 && !worker_task_always) { task_n--; } } return SW_OK; }