示例#1
0
int ioevent_set(struct fast_task_info *pTask, struct nio_thread_data *pThread,
	int sock, short event, IOEventCallback callback, const int timeout)
{
	int result;

	pTask->thread_data = pThread;
	pTask->event.fd = sock;
	pTask->event.callback = callback;
	if (ioevent_attach(&pThread->ev_puller,
		sock, event, pTask) < 0)
	{
		result = errno != 0 ? errno : ENOENT;
		logError("file: "__FILE__", line: %d, " \
			"ioevent_attach fail, " \
			"errno: %d, error info: %s", \
			__LINE__, result, STRERROR(result));
		return result;
	}

	pTask->event.timer.data = pTask;
	pTask->event.timer.expires = g_current_time + timeout;
	result = fast_timer_add(&pThread->timer, &pTask->event.timer);
	if (result != 0)
	{
		logError("file: "__FILE__", line: %d, " \
			"fast_timer_add fail, " \
			"errno: %d, error info: %s", \
			__LINE__, result, STRERROR(result));
		return result;
	}

	return 0;
}
示例#2
0
static void sched_deal_task_queue(ScheduleContext *pContext)
{
    FastDelayTask *task;

    pthread_mutex_lock(&pContext->delay_queue.lock);
    if (pContext->delay_queue.head == NULL)
    {
        pthread_mutex_unlock(&pContext->delay_queue.lock);
        return;
    }
    task  = pContext->delay_queue.head;
    pContext->delay_queue.head = NULL;
    pContext->delay_queue.tail = NULL;
    pthread_mutex_unlock(&pContext->delay_queue.lock);

    while (task != NULL)
    {
        fast_timer_add(&pContext->timer, (FastTimerEntry *)task);
        task = task->next;
    }
}
示例#3
0
static void client_sock_read(int sock, short event, void *arg)
{
	int bytes;
	int recv_bytes;
	struct fast_task_info *pTask;
        StorageClientInfo *pClientInfo;

	pTask = (struct fast_task_info *)arg;
        pClientInfo = (StorageClientInfo *)pTask->arg;
	if (pClientInfo->canceled)
	{
		return;
	}

	if (pClientInfo->stage != FDFS_STORAGE_STAGE_NIO_RECV)
	{
		if (event & IOEVENT_TIMEOUT) {
			pTask->event.timer.expires = g_current_time +
				g_fdfs_network_timeout;
			fast_timer_add(&pTask->thread_data->timer,
				&pTask->event.timer);
		}

		return;
	}

	if (event & IOEVENT_TIMEOUT)
	{
		if (pClientInfo->total_offset == 0 && pTask->req_count > 0)
		{
			pTask->event.timer.expires = g_current_time +
				g_fdfs_network_timeout;
			fast_timer_add(&pTask->thread_data->timer,
				&pTask->event.timer);
		}
		else
		{
			logError("file: "__FILE__", line: %d, " \
				"client ip: %s, recv timeout, " \
				"recv offset: %d, expect length: %d", \
				__LINE__, pTask->client_ip, \
				pTask->offset, pTask->length);

			task_finish_clean_up(pTask);
		}

		return;
	}

	if (event & IOEVENT_ERROR)
	{
		logDebug("file: "__FILE__", line: %d, " \
			"client ip: %s, recv error event: %d, "
			"close connection", __LINE__, pTask->client_ip, event);

		task_finish_clean_up(pTask);
		return;
	}

	fast_timer_modify(&pTask->thread_data->timer,
		&pTask->event.timer, g_current_time +
		g_fdfs_network_timeout);
	while (1)
	{
		if (pClientInfo->total_length == 0) //recv header
		{
			recv_bytes = sizeof(TrackerHeader) - pTask->offset;
		}
		else
		{
			recv_bytes = pTask->length - pTask->offset;
		}

		/*
		logInfo("total_length=%"PRId64", recv_bytes=%d, "
			"pTask->length=%d, pTask->offset=%d",
			pClientInfo->total_length, recv_bytes, 
			pTask->length, pTask->offset);
		*/

		bytes = recv(sock, pTask->data + pTask->offset, recv_bytes, 0);
		if (bytes < 0)
		{
			if (errno == EAGAIN || errno == EWOULDBLOCK)
			{
			}
			else if (errno == EINTR)
			{
				continue;
			}
			else
			{
				logError("file: "__FILE__", line: %d, " \
					"client ip: %s, recv failed, " \
					"errno: %d, error info: %s", \
					__LINE__, pTask->client_ip, \
					errno, STRERROR(errno));

				task_finish_clean_up(pTask);
			}

			return;
		}
		else if (bytes == 0)
		{
			logDebug("file: "__FILE__", line: %d, " \
				"client ip: %s, recv failed, " \
				"connection disconnected.", \
				__LINE__, pTask->client_ip);

			task_finish_clean_up(pTask);
			return;
		}

		if (pClientInfo->total_length == 0) //header
		{
			if (pTask->offset + bytes < sizeof(TrackerHeader))
			{
				pTask->offset += bytes;
				return;
			}

			pClientInfo->total_length=buff2long(((TrackerHeader *) \
						pTask->data)->pkg_len);
			if (pClientInfo->total_length < 0)
			{
				logError("file: "__FILE__", line: %d, " \
					"client ip: %s, pkg length: " \
					"%"PRId64" < 0", \
					__LINE__, pTask->client_ip, \
					pClientInfo->total_length);

				task_finish_clean_up(pTask);
				return;
			}

			pClientInfo->total_length += sizeof(TrackerHeader);
			if (pClientInfo->total_length > pTask->size)
			{
				pTask->length = pTask->size;
			}
			else
			{
				pTask->length = pClientInfo->total_length;
			}
		}

		pTask->offset += bytes;
		if (pTask->offset >= pTask->length) //recv current pkg done
		{
			if (pClientInfo->total_offset + pTask->length >= \
					pClientInfo->total_length)
			{
				/* current req recv done */
				pClientInfo->stage = FDFS_STORAGE_STAGE_NIO_SEND;
				pTask->req_count++;
			}

			if (pClientInfo->total_offset == 0)
			{
				pClientInfo->total_offset = pTask->length;
				storage_deal_task(pTask);
			}
			else
			{
				pClientInfo->total_offset += pTask->length;

				/* continue write to file */
				storage_dio_queue_push(pTask);
			}

			return;
		}
	}

	return;
}
示例#4
0
static void client_sock_read(int sock, short event, void *arg)
{
    int bytes;
    int recv_bytes;
    struct fast_task_info *pTask;

    pTask = (struct fast_task_info *)arg;

    if (event & IOEVENT_TIMEOUT)
    {
        if (pTask->offset == 0 && pTask->req_count > 0)
        {
            pTask->event.timer.expires = g_current_time +
                                         g_fdfs_network_timeout;
            fast_timer_add(&pTask->thread_data->timer,
                           &pTask->event.timer);
        }
        else
        {
            logError("file: "__FILE__", line: %d, " \
                     "client ip: %s, recv timeout, " \
                     "recv offset: %d, expect length: %d", \
                     __LINE__, pTask->client_ip, \
                     pTask->offset, pTask->length);

            task_finish_clean_up(pTask);
        }

        return;
    }

    if (event & IOEVENT_ERROR)
    {
        logDebug("file: "__FILE__", line: %d, " \
                 "client ip: %s, recv error event: %d, "
                 "close connection", __LINE__, pTask->client_ip, event);

        task_finish_clean_up(pTask);
        return;
    }

    while (1)
    {
        fast_timer_modify(&pTask->thread_data->timer,
                          &pTask->event.timer, g_current_time +
                          g_fdfs_network_timeout);
        if (pTask->length == 0) //recv header
        {
            recv_bytes = sizeof(TrackerHeader) - pTask->offset;
        }
        else
        {
            recv_bytes = pTask->length - pTask->offset;
        }

        bytes = recv(sock, pTask->data + pTask->offset, recv_bytes, 0);
        if (bytes < 0)
        {
            if (errno == EAGAIN || errno == EWOULDBLOCK)
            {
            }
            else if (errno == EINTR)
            {
                continue;
            }
            else
            {
                logError("file: "__FILE__", line: %d, " \
                         "client ip: %s, recv failed, " \
                         "errno: %d, error info: %s", \
                         __LINE__, pTask->client_ip, \
                         errno, STRERROR(errno));

                task_finish_clean_up(pTask);
            }

            return;
        }
        else if (bytes == 0)
        {
            logDebug("file: "__FILE__", line: %d, " \
                     "client ip: %s, recv failed, " \
                     "connection disconnected.", \
                     __LINE__, pTask->client_ip);

            task_finish_clean_up(pTask);
            return;
        }

        if (pTask->length == 0) //header
        {
            if (pTask->offset + bytes < sizeof(TrackerHeader))
            {
                pTask->offset += bytes;
                return;
            }

            pTask->length = buff2long(((TrackerHeader *) \
                                       pTask->data)->pkg_len);
            if (pTask->length < 0)
            {
                logError("file: "__FILE__", line: %d, " \
                         "client ip: %s, pkg length: %d < 0", \
                         __LINE__, pTask->client_ip, \
                         pTask->length);

                task_finish_clean_up(pTask);
                return;
            }

            pTask->length += sizeof(TrackerHeader);
            if (pTask->length > TRACKER_MAX_PACKAGE_SIZE)
            {
                logError("file: "__FILE__", line: %d, " \
                         "client ip: %s, pkg length: %d > " \
                         "max pkg size: %d", __LINE__, \
                         pTask->client_ip, pTask->length, \
                         TRACKER_MAX_PACKAGE_SIZE);

                task_finish_clean_up(pTask);
                return;
            }
        }

        pTask->offset += bytes;
        if (pTask->offset >= pTask->length) //recv done
        {
            pTask->req_count++;
            tracker_deal_task(pTask);
            return;
        }
    }

    return;
}