Ejemplo n.º 1
0
bool Socket::SetNonblocking()
{
    int ret;
    
    if (fd < 0)
    {
        Log_Trace("SetNonblocking on invalid file descriptor");
        return false;
    }
    
    ret = fcntl(fd, F_GETFL, 0);
    if (ret < 0)
    {
        Log_Errno();
        return false;
    }

    ret = fcntl(fd, F_SETFL, ret | O_NONBLOCK);
    if (ret < 0)
    {
        Log_Errno();
        return false;
    }
    
    return true;
}
Ejemplo n.º 2
0
bool Socket::Bind(int port)
{
    int                 ret;
    struct sockaddr_in  sa;
    int                 sockopt;

    sockopt = 1;
    ret = setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &sockopt, sizeof(sockopt));
    if (ret < 0)
    {
        Log_Errno();
        Close();
        return false;
    }
    
    memset(&sa, 0, sizeof(sa));
    sa.sin_port = htons((uint16_t)port);
    sa.sin_addr.s_addr = htonl(INADDR_ANY);
    
    ret = bind(fd, (struct sockaddr *)&sa, sizeof(struct sockaddr_in));
    if (ret < 0)
    {
        Log_Errno();
        Close();
        return false;
    }
    
    return true;
}
Ejemplo n.º 3
0
int64_t FS_FileSeek(FD fd, uint64_t offset, int whence_)
{
    off_t   ret;
    int     whence;

    whence = -1;
    switch (whence_)
    {
    case FS_SEEK_SET:
        whence = SEEK_SET;
        break;
    case FS_SEEK_CUR:
        whence = SEEK_CUR;
        break;
    case FS_SEEK_END:
        whence = SEEK_END;
        break;
    default:
        return -1;
    }

    ret = lseek(fd, offset, whence);
    if (ret < 0)
        Log_Errno("%d", fd);
    return ret;
}
Ejemplo n.º 4
0
bool Socket::Create(Proto proto_)
{
    int stype;
    
    if (fd >= 0)
    {
        Log_Trace("Called Create() on existing socket");
        return false;
    }
    
    if (proto_ == UDP)
        stype = SOCK_DGRAM;
    else
        stype = SOCK_STREAM;
    
    fd = socket(AF_INET, stype, 0);
    if (fd < 0)
    {
        Log_Errno();
        return false;
    }
        
    proto = proto_;
    listening = false;
    
//    SetReceiveBufferSize(64*KiB);
    
    return true;
}
Ejemplo n.º 5
0
bool AddKq(int ident, short filter, IOOperation* ioop)
{
	int				nev;
	struct kevent	ev;
	struct timespec timeout = { 0, 0 };
	
	if (kq < 0)
	{
		Log_Trace("kq < 0");
		return false;
	}
	
	EV_SET(&ev, ident, filter, EV_ADD | EV_ONESHOT, 0, 0, ioop);
	
	// add our interest in the event
	nev = kevent(kq, &ev, 1, NULL, 0, &timeout);
	if (nev < 0)
	{
		Log_Errno();
		return false;
	}
	
	if (ioop)
		ioop->active = true;
	
	return true;
}
Ejemplo n.º 6
0
void ProcessUDPRead(struct kevent* ev)
{
	int			salen, nread;
	UDPRead*	udpread;

	udpread = (UDPRead*) ev->udata;
	
	salen = ENDPOINT_SOCKADDR_SIZE;
	nread = recvfrom(udpread->fd,
					 udpread->data.buffer,
					 udpread->data.size,
					 0,
					 (sockaddr*) udpread->endpoint.GetSockAddr(),
					 (socklen_t*)&salen);
	
	if (nread < 0)
	{
		if (errno == EWOULDBLOCK || errno == EAGAIN)
			IOProcessor::Add(udpread); // try again
		else
			Log_Errno();
	}
	else
	{
		udpread->data.length = nread;
		Call(udpread->onComplete);
	}
					
	if (ev->flags & EV_EOF)
		Call(udpread->onClose);
}
Ejemplo n.º 7
0
void Signal::Wait()
{
    DWORD   ret;
    bool    stuck;

    SetWaiting(true);
    stuck = false;

    while (true)
    {
        DWORD timeout = 10000;
        //ret = WaitForSingleObject((HANDLE) impl.event, INFINITE);
        ret = WaitForSingleObject((HANDLE) impl.event, timeout);
        if (ret == WAIT_FAILED)
            Log_Errno();
        if (ret != WAIT_OBJECT_0 && ret != WAIT_TIMEOUT)
            Log_Debug("WaitForSingleObject: ret %d", ret);

        if (ret == WAIT_TIMEOUT)
        {
            if (stuck == false)
            {
                //Log_Debug("Waiting for long: %p in %U", this, ThreadPool::GetThreadID());
                stuck = true;
            }
            continue;
        }
        break;
    }
    SetWaiting(false);
}
Ejemplo n.º 8
0
ssize_t FS_FileReadOffs(FD fd, void* buf, size_t count, uint64_t offset)
{
    ssize_t ret;

    ret = pread(fd, buf, count, offset);
    if (ret < 0)
        Log_Errno("%d", fd);
    return ret;
}
Ejemplo n.º 9
0
void FS_CloseDir(FS_Dir dir)
{
    int ret;

    if ((DIR*) dir == NULL)
        return;

    ret = closedir((DIR*) dir);
    if (ret < 0)
        Log_Errno();
}
Ejemplo n.º 10
0
ssize_t FS_FileWriteOffs(FD fd, const void* buf, size_t count, uint64_t offset)
{
    ssize_t ret;

    dirtyFiles[fd] = true;

    ret = pwrite(fd, buf, count, offset);
    if (ret < 0)
        Log_Errno("%d", fd);
    return ret;
}
Ejemplo n.º 11
0
bool IOProcessor::Init(int maxfd_)
{
	rlimit rl;

	if (kq != 0)
		return true;

	terminated = false;
	
	kq = kqueue();
	if (kq < 0)
	{
		Log_Errno();
		return false;
	}

	SetupSignals();	
	
	rl.rlim_cur = maxfd_;
	rl.rlim_max = maxfd_;
	if (setrlimit(RLIMIT_NOFILE, &rl) < 0)
	{
		Log_Errno();
	}
		
	// setup async pipe
	if (pipe(asyncOpPipe) < 0)
	{
		Log_Errno();
		return false;
	}
	
	fcntl(asyncOpPipe[0], F_SETFD, FD_CLOEXEC);
	fcntl(asyncOpPipe[0], F_SETFD, O_NONBLOCK);
	fcntl(asyncOpPipe[1], F_SETFD, FD_CLOEXEC);

	if (!AddKq(asyncOpPipe[0], EVFILT_READ, NULL))
		return false;
		
	return true;
}
Ejemplo n.º 12
0
bool Socket::Accept(Socket *newSocket)
{
    newSocket->fd = accept(fd, NULL, NULL);
    if (newSocket->fd < 0)
    {
        Log_Errno();
        Close();
        return false;
    }
    
    return true;
}
Ejemplo n.º 13
0
int FS_FileTruncate(FD fd, uint64_t length)
{
    int ret;

    dirtyFiles[fd] = true;

    ret = ftruncate(fd, length);
    if (ret < 0)
        Log_Errno("%d", fd);

    return ret;
}
Ejemplo n.º 14
0
bool FS_CreateDir(const char* filename)
{
    int ret;

    ret = mkdir(filename, S_IRUSR | S_IWUSR | S_IXUSR);
    if (ret < 0)
    {
        Log_Errno("%s", filename);
        return false;
    }
    return true;
}
Ejemplo n.º 15
0
void Signal::Wait()
{
    DWORD   ret;

    SetWaiting(true);
    ret = WaitForSingleObject((HANDLE) impl.event, INFINITE);
    if (ret == WAIT_FAILED)
        Log_Errno();
    if (ret != WAIT_OBJECT_0)
        Log_Debug("WaitForSingleObject: ret %d", ret);
    SetWaiting(false);
}
Ejemplo n.º 16
0
bool FS_DeleteDir(const char* filename)
{
    int ret;

    ret = rmdir(filename);
    if (ret < 0)
    {
        Log_Errno("%s", filename);
        return false;
    }
    return true;
}
Ejemplo n.º 17
0
ssize_t FS_FileWrite(FD fd, const void* buf, size_t count)
{
    ssize_t ret;

    dirtyFiles[fd] = true;

    ret = write(fd, buf, count);
    if (ret < 0)
        Log_Errno("%d", fd);

    return ret;
}
Ejemplo n.º 18
0
FS_Dir FS_OpenDir(const char* filename)
{
    DIR*    dir;

    dir = opendir(filename);
    if (dir == NULL)
    {
        Log_Errno("%s", filename);
        return FS_INVALID_DIR;
    }

    return (FS_Dir) dir;
}
Ejemplo n.º 19
0
void FS_FileClose(FD fd)
{
    int ret;

    globalMutex.Lock();
    fileHandles.Remove(fd);
    dirtyFiles[fd] = false;
    globalMutex.Unlock();

    ret = close(fd);
    if (ret < 0)
        Log_Errno("%d", fd);
}
Ejemplo n.º 20
0
bool FS_Rename(const char* src, const char* dst)
{
    int     ret;

    ret = rename(src, dst);
    if (ret < 0)
    {
        Log_Errno("src: %s, dst: %s", src, dst);
        return false;
    }

    return true;
}
Ejemplo n.º 21
0
int64_t FS_FileSize(const char* path)
{
    int64_t     ret;
    struct stat buf;

    ret = stat(path, &buf);
    if (ret < 0)
    {
        Log_Errno("%s", path);
        return ret;
    }

    return buf.st_size;
}
Ejemplo n.º 22
0
int64_t FS_FileSize(FD fd)
{
    int64_t     ret;
    struct stat buf;

    ret = fstat(fd, &buf);
    if (ret < 0)
    {
        Log_Errno("%d", fd);
        return ret;
    }

    return buf.st_size;
}
Ejemplo n.º 23
0
void Socket::Close()
{
    int ret;
    
    if (fd != -1)
    {
        ret = close(fd);

        if (ret < 0)
            Log_Errno();

        fd = -1;
    }
}
Ejemplo n.º 24
0
void ProcessTCPWrite(struct kevent* ev)
{
	int			writelen, nwrite;
	TCPWrite*	tcpwrite;
	
	tcpwrite = (TCPWrite*) ev->udata;
	
	if (ev->flags & EV_EOF)
	{
		Call(tcpwrite->onClose);
		return;
	}
	
	if (tcpwrite->data.length == 0)
	{
		if (ev->flags & EV_EOF)
			Call(tcpwrite->onClose);
		else
			Call(tcpwrite->onComplete);

		return;
	}

	writelen = tcpwrite->data.length - tcpwrite->transferred;
	writelen = MIN(ev->data, writelen);
	
	if (writelen > 0)
	{
		nwrite = write(tcpwrite->fd,
					   tcpwrite->data.buffer + tcpwrite->transferred,
					   writelen);
		
		if (nwrite < 0)
		{
			if (errno == EWOULDBLOCK || errno == EAGAIN)
				IOProcessor::Add(tcpwrite);
			else if (!(ev->flags & EV_EOF))
				Log_Errno();
		}
		else
		{
			tcpwrite->transferred += nwrite;
			if (tcpwrite->transferred == tcpwrite->data.length)
				Call(tcpwrite->onComplete);
			else
				IOProcessor::Add(tcpwrite);
		}
	}
}
Ejemplo n.º 25
0
bool IOProcessor::Complete(Callable* callable)
{
	Log_Trace();

	int nwrite;
	
	nwrite = write(asyncOpPipe[1], &callable, sizeof(Callable*));
	if (nwrite < 0)
		Log_Errno();
	
	if (nwrite >= 0)
		return true;
	
	return false;
}
Ejemplo n.º 26
0
bool Socket::SendTo(void *data, int count, const Endpoint &endpoint)
{
    int ret;
    const struct sockaddr* sa =
    (const struct sockaddr*) ((Endpoint&) endpoint).GetSockAddr();
    
    ret = sendto(fd, data, count, 0, sa, ENDPOINT_SOCKADDR_SIZE);
    
    if (ret < 0)
    {
        Log_Errno();
        return false;
    }
    
    return true;
}
Ejemplo n.º 27
0
void ProcessTCPRead(struct kevent* ev)
{
	int			readlen, nread;
	TCPRead*	tcpread;
	
	tcpread = (TCPRead*) ev->udata;

	if (tcpread->listening)
	{
		Call(tcpread->onComplete);
	}
	else
	{
		if (tcpread->requested == IO_READ_ANY)
			readlen = tcpread->data.size - tcpread->data.length;
		else
			readlen = tcpread->requested - tcpread->data.length;
		readlen = MIN(ev->data, readlen);
		if (readlen > 0)
		{
			nread = read(tcpread->fd,
						 tcpread->data.buffer + tcpread->data.length,
						 readlen);
			
			if (nread < 0)
			{
				if (errno == EWOULDBLOCK || errno == EAGAIN)
					IOProcessor::Add(tcpread);
				else if (!(ev->flags & EV_EOF))
					Log_Errno();
			}
			else
			{
				tcpread->data.length += nread;
				if (tcpread->requested == IO_READ_ANY ||
				(int) tcpread->data.length == tcpread->requested)
					Call(tcpread->onComplete);
				else
					IOProcessor::Add(tcpread);
			}
		}
		
		if (ev->flags & EV_EOF)
			Call(tcpread->onClose);
	}
}
Ejemplo n.º 28
0
bool Socket::GetEndpoint(Endpoint &endpoint)
{
    int ret;
    struct sockaddr* sa = (struct sockaddr*) endpoint.GetSockAddr();
    socklen_t len = ENDPOINT_SOCKADDR_SIZE;
    
    ret = getpeername(fd, sa, &len);
    
    if (ret < 0)
    {
        Log_Errno();
        Close();
        return false;
    }
    
    return true;
}
Ejemplo n.º 29
0
bool Socket::Connect(Endpoint &endpoint)
{
    int ret;
    struct sockaddr* sa = (struct sockaddr*) endpoint.GetSockAddr();
    
    ret = connect(fd, sa, ENDPOINT_SOCKADDR_SIZE);
    
    if (ret < 0)
    {
        if (errno != EINPROGRESS)
        {
            Log_Errno();
            return false;
        }
    }

    return true;
}
Ejemplo n.º 30
0
bool IOProcessor::Remove(IOOperation* ioop)
{
	short			filter;
	int				nev;
	struct kevent	ev;
	struct timespec timeout = { 0, 0 };
	
	if (!ioop->active)
		return true;
		
	if (ioop->pending)
	{
		ioop->active = false;
		return true;
	}
	
	if (kq < 0)
	{
		Log_Trace("kq < 0");
		return false;
	}

	if (ioop->type == TCP_READ || ioop->type == UDP_READ)
		filter = EVFILT_READ;
	else
		filter = EVFILT_WRITE;
	
	EV_SET(&ev, ioop->fd, filter, EV_DELETE, 0, 0, 0);
	
	// delete event
	nev = kevent(kq, &ev, 1, NULL, 0, &timeout);
	if (nev < 0)
	{
		Log_Errno();
		// HACK:
		ioop->active = false;
		return false;
	}
	
	ioop->active = false;
	
	return true;
}