Nicer code

This commit is contained in:
Pierre Pronchery 2005-09-17 22:58:38 +00:00
parent 17c7d9fc15
commit 9501343314
3 changed files with 128 additions and 104 deletions

View File

@ -29,5 +29,8 @@ int event_register_io_write(Event * event, int fd, EventIOFunc func,
void * userdata);
int event_register_timeout(Event * event, struct timeval timeout,
EventTimeoutFunc func, void * userdata);
int event_unregister_io_read(Event * event, int fd);
int event_unregister_io_write(Event * event, int fd);
int event_unregister_timeout(Event * event, EventTimeoutFunc func);
#endif /* !_EVENT_H */

View File

@ -28,8 +28,10 @@ typedef struct _AppServerClient
int fd;
uint32_t addr; /* FIXME uint8_t[4] instead? */
uint16_t port;
char buffer_read[ASC_BUFSIZE];
char buffer_write[ASC_BUFSIZE];
char buf_read[ASC_BUFSIZE];
unsigned int buf_read_cnt;
char buf_write[ASC_BUFSIZE];
unsigned int buf_write_cnt;
} AppServerClient;
@ -44,6 +46,8 @@ AppServerClient * appserverclient_new(int fd, uint32_t addr, uint16_t port)
asc->fd = fd;
asc->addr = addr;
asc->port = port;
asc->buf_read_cnt = 0;
asc->buf_write_cnt = 0;
return asc;
}
@ -86,25 +90,60 @@ static int _appserver_accept(int fd, AppServer * appserver)
return 1;
if((asc = appserverclient_new(newfd, sa.sin_addr.s_addr, sa.sin_port))
== NULL)
return 1;
{
/* FIXME report error */
close(newfd);
return 0;
}
array_append(appserver->clients, asc);
event_register_io_read(appserver->event, newfd, _appserver_read,
appserver);
/* event_register_io_write(appserver->event, newfd, _appserver_write,
appserver); */
event_register_io_read(appserver->event, newfd,
(EventIOFunc)_appserver_read, appserver);
return 0;
}
static int _appserver_read(int fd, AppServer * appserver)
{
AppServerClient * asc = NULL;
unsigned int i;
ssize_t len;
for(i = 0; i < array_count(appserver->clients); i++)
{
if(array_get(appserver->clients, i, &asc))
break;
if(fd == asc->fd)
break;
asc = NULL;
}
if(asc == NULL)
return 1;
if((len = sizeof(asc->buf_read) - asc->buf_read_cnt) < 0
|| (len = read(fd, &asc->buf_read[asc->buf_read_cnt],
len)) <= 0)
{
if(asc->buf_write_cnt > 0)
event_unregister_io_write(appserver->event, fd);
event_unregister_io_read(appserver->event, fd);
appserverclient_delete(asc);
array_remove_pos(appserver->clients, i);
return 1;
}
asc->buf_read_cnt+=len;
#ifdef DEBUG
fprintf(stderr, "%s%d%s%d%s", "_appserver_read(", fd,
", appserver): ", len, " characters read\n");
#endif
return 0;
}
static int _appserver_write(int fd, AppServer * appserver)
{
AppServerClient * asc = NULL;
unsigned int i;
int len;
#ifdef DEBUG
fprintf(stderr, "%s%d%s", "_appserver_read(", fd, ", appserver)\n");
#endif
for(i = 0; i < array_count(appserver->clients); i++)
{
if(!array_get(appserver->clients, i, &asc))
@ -113,27 +152,23 @@ static int _appserver_read(int fd, AppServer * appserver)
break;
asc = NULL;
}
if(asc == NULL || (len = read(fd, asc->buffer_read,
sizeof(asc->buffer_read)-1)) < 0)
if(asc == NULL)
return 1;
if(len == 0)
len = asc->buf_read_cnt;
if((len = write(fd, asc->buf_write, len)) <= 0)
{
#ifdef DEBUG
perror("read");
#endif
close(fd);
if(asc->buf_read_cnt == ASC_BUFSIZE)
event_unregister_io_read(appserver->event, fd);
event_unregister_io_write(appserver->event, fd);
array_remove_pos(appserver->clients, i);
appserverclient_delete(asc);
return 1;
}
asc->buffer_read[len] = '\0';
fprintf(stderr, "\"%s\"\n", asc->buffer_read);
return 0;
}
static int _appserver_write(int fd, AppServer * appserver)
{
memmove(asc->buf_write, &asc->buf_write[len], len);
asc->buf_write_cnt-=len;
#ifdef DEBUG
fprintf(stderr, "%s%d%s", "_appserver_write(", fd, ", appserver)\n");
fprintf(stderr, "%s%d%s%d%s", "_appserver_write(", fd,
", appserver): ", len, " characters written\n");
#endif
return 0;
}
@ -216,8 +251,8 @@ static int _new_server(AppServer * appserver, int options)
perror("close"); /* FIXME report error appropriately */
return 1;
}
event_register_io_read(appserver->event, fd, _appserver_accept,
appserver);
event_register_io_read(appserver->event, fd,
(EventIOFunc)_appserver_accept, appserver);
return 0;
}

View File

@ -61,12 +61,13 @@ Event * event_new(void)
free(event);
return NULL;
}
event->timeout.tv_sec = LONG_MAX;
event->timeout.tv_usec = LONG_MAX;
event->reads = eventioarray_new(); /* FIXME */
event->writes = eventioarray_new(); /* FIXME */
event->fdmax = -1;
FD_ZERO(&event->rfds);
FD_ZERO(&event->wfds);
event->reads = eventioarray_new(); /* FIXME */
event->writes = eventioarray_new(); /* FIXME */
event->timeout.tv_sec = LONG_MAX;
event->timeout.tv_usec = LONG_MAX;
return event;
}
@ -83,8 +84,7 @@ void event_delete(Event * event)
/* useful */
static void _loop_timeout(Event * event);
static void _loop_io_read(Event * event, fd_set * rfds);
static void _loop_io_write(Event * event, fd_set * wfds);
static void _loop_io(Event * event, eventioArray * eios, fd_set * fds);
int event_loop(Event * event)
{
struct timeval * timeout = event->timeout.tv_sec == LONG_MAX
@ -96,8 +96,8 @@ int event_loop(Event * event)
while((ret = select(event->fdmax+1, &rfds, &wfds, NULL, timeout)) != -1)
{
_loop_timeout(event);
_loop_io_read(event, &rfds);
_loop_io_write(event, &wfds);
_loop_io(event, event->reads, &rfds);
_loop_io(event, event->writes, &wfds);
timeout = event->timeout.tv_sec == LONG_MAX
&& event->timeout.tv_usec == LONG_MAX
? NULL : &event->timeout;
@ -107,8 +107,8 @@ int event_loop(Event * event)
if(ret != -1)
return 0;
#ifdef DEBUG
sleep(1);
perror("select");
sleep(1);
#endif
return 1;
}
@ -131,84 +131,27 @@ static void _loop_timeout(Event * event)
}
}
static int _io_fd_remove(Event * event, int fd);
static void _loop_io_read(Event * event, fd_set * rfds)
static void _loop_io(Event * event, eventioArray * eios, fd_set * fds)
{
unsigned int i = 0;
EventIO * eio;
int fd;
while(i < array_count(event->reads))
while(i < array_count(eios))
{
array_get(event->reads, i, &eio);
array_get(eios, i, &eio);
#ifdef DEBUG
fprintf(stderr, "%s%d%s%p%s", "_loop_reads(): i=", i,
fprintf(stderr, "%s%d%s%p%s", "_loop_io(): i=", i,
", eio=", eio, "\n");
#endif
if(FD_ISSET(eio->fd, rfds)
&& eio->func(eio->fd, eio->data) != 0)
{
event->fdmax = _io_fd_remove(event, eio->fd);
continue;
}
if((fd = eio->fd) <= event->fdmax && FD_ISSET(fd, fds)
&& eio->func(fd, eio->data) != 0)
event_unregister_io_read(event, fd);
else
i++;
}
}
static void _loop_io_write(Event * event, fd_set * wfds)
{
unsigned int i = 0;
EventIO * eio;
while(i < array_count(event->writes))
{
array_get(event->writes, i, &eio); /* FIXME check error */
#ifdef DEBUG
fprintf(stderr, "%s%d%s%p%s", "_loop_writes(): i=", i,
", eio=", eio, "\n");
#endif
if(FD_ISSET(eio->fd, wfds)
&& eio->func(eio->fd, eio->data) != 0)
{
event->fdmax = _io_fd_remove(event, eio->fd);
continue;
}
i++;
}
}
static int _io_fd_remove(Event * event, int fd)
{
unsigned int i;
int fdmax = -1;
EventIO * eio;
for(i = 0; i < array_count(event->reads); i++)
{
array_get(event->reads, i, &eio); /* FIXME check error */
if(eio->fd != fd)
{
fdmax = max(fdmax, eio->fd);
continue;
}
FD_CLR(eio->fd, &event->rfds);
free(eio);
array_remove_pos(event->reads, i);
}
for(i = 0; i < array_count(event->writes); i++)
{
array_get(event->writes, i, &eio); /* FIXME check error */
if(eio->fd != fd)
{
fdmax = max(fdmax, eio->fd);
continue;
}
FD_CLR(eio->fd, &event->wfds);
free(eio);
array_remove_pos(event->writes, i);
}
return fdmax;
}
/* event_register_io_read */
int event_register_io_read(Event * event, int fd, EventIOFunc func,
@ -267,3 +210,46 @@ int event_register_timeout(Event * event, struct timeval timeout,
}
return 0;
}
/* event_unregister_io_read */
static int _unregister_io(eventioArray * eios, fd_set * fds, int fd);
int event_unregister_io_read(Event * event, int fd)
{
event->fdmax = _unregister_io(event->reads, &event->rfds, fd);
event->fdmax = max(event->fdmax, _unregister_io(event->writes, NULL,
-1));
return 0;
}
/* event_unregister_io_write */
int event_unregister_io_write(Event * event, int fd)
{
event->fdmax = _unregister_io(event->writes, &event->wfds, fd);
event->fdmax = max(event->fdmax, _unregister_io(event->reads, NULL,
-1));
return 0;
}
static int _unregister_io(eventioArray * eios, fd_set * fds, int fd)
{
unsigned int i = 0;
EventIO * eio;
int fdmax = -1;
while(i < array_count(eios))
{
array_get(eios, i, &eio);
if(eio->fd != fd)
{
fdmax = max(fdmax, eio->fd);
i++;
continue;
}
FD_CLR(fd, fds);
array_remove_pos(eios, i);
free(eio);
}
return fdmax;
}