diff --git a/include/cclass.h b/include/cclass.h
deleted file mode 100644
index 355c318..0000000
--- a/include/cclass.h
+++ /dev/null
@@ -1,98 +0,0 @@
-/**
- * \file
- * cclass.h: basic "class-like" handling of code and data structures
- * Copyright (C) 2011 Georg Hopp
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see .
- */
-
-#ifndef __CCLASS_H__
-#define __CCLASS_H__
-
-#include
-#include
-#include
-
-#define CCLASS_MAGIC 0xFEFE
-
-
-typedef void (* ctor)(void *, va_list *);
-typedef void (* clr)(void *);
-typedef void (* dtor)(void *);
-typedef void (* jCtor)(void *, struct json_object *);
-typedef void (* jTo)(void *, struct json_object **);
-
-typedef struct _CCLASS {
- const int magic;
- size_t size;
- ctor __construct;
- clr __clear;
- dtor __destruct;
- jCtor __jsonConst;
- jTo __toJson;
-} * CCLASS;
-
-#define CCLASS_SIZE sizeof(struct _CCLASS)
-#define CCLASS_PTR_SIZE sizeof(CCLASS)
-
-#define __construct(_class) \
- static void __construct(_class this, va_list * params)
-#define __clear(_class) \
- static void __clear(_class this)
-#define __destruct(_class) \
- static void __destruct(_class this)
-#define __jsonConst(_class) \
- static void __jsonConst(_class this, struct json_object * json)
-#define __toJson(_class) \
- static void __toJson(_class this, struct json_object ** json)
-
-#define CLASS(_class) \
- struct _##_class; \
- typedef struct _##_class * _class; \
- extern const CCLASS const __##_class; \
- struct _##_class
-
-#define INIT_CLASS(_class) \
- __construct(_class); \
- __clear(_class); \
- __destruct(_class); \
- __jsonConst(_class); \
- __toJson(_class); \
- static const struct _CCLASS _cclass = { \
- CCLASS_MAGIC, \
- sizeof(struct _##_class), \
- (ctor)__construct, \
- (clr)__clear, \
- (dtor)__destruct, \
- (jCtor)__jsonConst, \
- (jTo)__toJson \
- }; const CCLASS __##_class = (const CCLASS)&_cclass
-
-void * _new(const CCLASS _class, ...);
-#define new(_class, ...) _new((__##_class), __VA_ARGS__)
-
-void * _newFromJson(const CCLASS _class, struct json_object * json);
-#define newFromJson(_class, json) _newFromJson((__##_class), (json))
-
-int _instanceOf(const CCLASS _class, void * _object);
-#define instanceOf(_class, object) _instanceOf((__##_class), (object))
-
-void clear(void * _object);
-void delete(void * _object);
-void toJson(void * _object, struct json_object ** json);
-int isObject(void * _object);
-
-#endif//__CCLASS_H__
-
-// vim: set et ts=4 sw=4:
diff --git a/include/class.h b/include/class.h
new file mode 100644
index 0000000..9f903ef
--- /dev/null
+++ b/include/class.h
@@ -0,0 +1,81 @@
+#ifndef __CLASS_H__
+#define __CLASS_H__
+
+#include
+#include
+#include
+#include
+
+#include "interface.h"
+
+#define _ISOC99_SOURCE
+
+#define CLASS_MAGIC 0xFEFE
+
+#define CLASS(name) \
+ struct c_##name; \
+ typedef struct c_##name * name; \
+ extern struct class * const _##name; \
+ struct c_##name
+
+#define EXTENDS(parent) \
+ const char _[sizeof(struct c_##parent)]
+
+#define _NULL NULL
+#define CREATE_CLASS(name,_parent,...) \
+ static struct class c_##name; \
+ static void _classInit_(void) { \
+ c_##name.parent = _##_parent; \
+ c_##name.init = NULL; \
+ } \
+ static struct class c_##name = { \
+ CLASS_MAGIC, \
+ NULL, \
+ sizeof(struct c_##name), \
+ _classInit_, \
+ INIT_IMPL(__VA_ARGS__) \
+ }; struct class * const _##name = &c_##name
+
+/**
+ * @TODO: actually i use gcc feature ## for variadoc... think about
+ * a way to make this standard.
+ */
+#define CALL(object,_iface,method,...) \
+ do { \
+ class_ptr class = class_getClass((object)); \
+ struct i_##_iface * iface; \
+ if (class->init) class->init(); \
+ iface = (struct i_##_iface *)class_getInterface(&class, &i_##_iface); \
+ while ((NULL == iface || NULL == iface->method) && HAS_PARENT(class)) { \
+ class = class->parent; \
+ if (class->init) class->init(); \
+ iface = (struct i_##_iface *)class_getInterface(&class, &i_##_iface); \
+ }; \
+ assert(NULL != iface->method); \
+ iface->method(object, ##__VA_ARGS__); \
+ } while(0)
+
+
+#define IFACE_GET(class,iface) (interfaceGet(&((class)->impl),(iface)))
+#define IFACE_EXISTS(class,iface) (NULL != IFACE_GET((class),(iface)))
+
+#define HAS_PARENT(class) (NULL != ((class)->parent))
+
+typedef void (* fptr_classInit)(void);
+
+struct class;
+typedef struct class * class_ptr;
+struct class {
+ const int magic;
+ class_ptr parent;
+ size_t object_size;
+ fptr_classInit init;
+ struct iface_impl impl;
+};
+
+extern inline void * class_getInterface(class_ptr *, iface_ptr);
+extern inline class_ptr class_getClass(void *);
+
+#endif // __CLASS_H__
+
+// vim: set ts=4 sw=4:
diff --git a/include/interface.h b/include/interface.h
new file mode 100644
index 0000000..27873e7
--- /dev/null
+++ b/include/interface.h
@@ -0,0 +1,39 @@
+#ifndef __INTERFACE_H__
+#define __INTERFACE_H__
+
+#include
+
+#define MAX_IFACE 32 // ATTENTION: every iface_impl will use MAX_IFACE * sizeof(void*)
+
+#define IFACE(name) ((const struct i_##name const*)&i_##name##_impl)
+
+#define INIT_IFACE(name,...) \
+ static const struct i_##name i_##name##_impl = {&i_##name,__VA_ARGS__}
+
+#define NUMARGS(...) (sizeof((const void*[]){__VA_ARGS__})/sizeof(void*))
+
+#define INIT_IMPL(...) {NUMARGS(__VA_ARGS__), 0, {__VA_ARGS__}}
+#define CREATE_IMPL(...) \
+ static struct iface_impl iface_impl = INIT_IMPL(__VA_ARGS__)
+
+#define METHOD_GET(iface,method) (iface->method)
+
+
+struct interface {
+ const char * name;
+ const size_t nmethods;
+};
+typedef const struct interface * iface_ptr;
+
+struct iface_impl {
+ const size_t nimpl; // number of interface implementations
+ char simpl; // implementations sorted??
+ const void * impl[MAX_IFACE]; // implementations
+};
+typedef struct iface_impl * iface_impl_ptr;
+
+extern struct interface * interfaceGet(iface_impl_ptr, const iface_ptr);
+
+#endif // __INTERFACE_H__
+
+// vim: set ts=4 sw=4:
diff --git a/include/interface/class.h b/include/interface/class.h
new file mode 100644
index 0000000..aafa637
--- /dev/null
+++ b/include/interface/class.h
@@ -0,0 +1,30 @@
+#ifndef __INTERFACE_CLASS_H__
+#define __INTERFACE_CLASS_H__
+
+#include
+
+#include "class.h"
+#include "interface.h"
+
+typedef void (* fptr_ctor)(void *, va_list *);
+typedef void (* fptr_dtor)(void *);
+typedef void (* fptr_clone)(void *, const void * const);
+
+extern const struct interface i_Class;
+
+struct i_Class {
+ const struct interface * const _;
+ fptr_ctor ctor;
+ fptr_dtor dtor;
+ fptr_clone clone;
+};
+
+extern inline void * classNew(class_ptr, ...);
+extern inline void classDelete(void **);
+
+#define new(class,...) classNew(_##class, __VA_ARGS__)
+#define delete(object) classDelete((void **)(object))
+
+#endif // __INTERFACE_CLASS_H__
+
+// vim: set ts=4 sw=4:
diff --git a/include/interface/logger.h b/include/interface/logger.h
new file mode 100644
index 0000000..803ae9b
--- /dev/null
+++ b/include/interface/logger.h
@@ -0,0 +1,22 @@
+#ifndef __INTERFACE_LOGGER_H__
+#define __INTERFACE_LOGGER_H__
+
+#include
+
+#include "interface.h"
+#include "logger.h"
+
+typedef void (* fptr_log)(void *, logger_level, const char * const);
+
+extern const struct interface i_Logger;
+
+struct i_Logger {
+ const struct interface * const _;
+ fptr_log log;
+};
+
+extern inline void loggerLog(void *, logger_level, const char * const, ...);
+
+#endif // __INTERFACE_LOGGER_H__
+
+// vim: set ts=4 sw=4:
diff --git a/include/logger.h b/include/logger.h
index 67fb033..bc7b87d 100644
--- a/include/logger.h
+++ b/include/logger.h
@@ -1,34 +1,33 @@
#ifndef __LOGGER_H__
#define __LOGGER_H__
-#include "cclass.h"
-
-
-#define LOGGER_EMERG 0
-#define LOGGER_ALERT 1
-#define LOGGER_CRIT 2
-#define LOGGER_ERR 3
-#define LOGGER_WARNING 4
-#define LOGGER_NOTICE 5
-#define LOGGER_INFO 6
-#define LOGGER_DEBUG 7
-
-#define MAX_LOG_FNCTS 10
-
-
-typedef void (*logger_logfnct)(int level, const char * msg);
-
-
-CLASS(LOGGER) {
- logger_logfnct logfncts[MAX_LOG_FNCTS];
- unsigned int logfncts_count;
+#include "class.h"
+
+typedef enum logger_level {
+ LOGGER_DEBUG=0,
+ LOGGER_INFO,
+ LOGGER_NOTICE,
+ LOGGER_WARNING,
+ LOGGER_ERR,
+ LOGGER_CRIT,
+ LOGGER_ALERT,
+ LOGGER_EMERG
+} logger_level;
+
+extern const char * const logger_level_str[];
+
+CLASS(Logger) {
+ logger_level min_level;
};
-void logger_log(LOGGER this, int level, const char * msg, ...)
- __attribute__((format (printf, 3, 4)));
+CLASS(LoggerStderr) {
+ EXTENDS(Logger);
+};
-void logger_add(LOGGER this, logger_logfnct logfunc);
+CLASS(LoggerSyslog) {
+ EXTENDS(Logger);
+};
-#endif /* __LOGGER_H__ */
+#endif // __LOGGER_H__
// vim: set ts=4 sw=4:
diff --git a/include/server.h b/include/server.h
index 2352b8f..a684a33 100644
--- a/include/server.h
+++ b/include/server.h
@@ -4,9 +4,9 @@
#include /* for printf() and fprintf() */
#include /* for select system call and related */
+#include "class.h"
#include "socket.h"
#include "logger.h"
-#include "cclass.h"
#define POLL_FD_NSIZE 1024
#define POLL_FD_SIZE (sizeof(struct pollfd) * POLL_FD_NSIZE)
@@ -23,14 +23,14 @@
typedef void (*server_read_hook)(const char *, size_t);
-CLASS(SERVER) {
- LOGGER logger;
- SOCK sock;
+CLASS(Server) {
+ Logger logger;
+ Sock sock;
nfds_t nfds;
struct pollfd fds[POLL_FD_NSIZE];
struct {
- SOCK sock;
+ Sock sock;
char * wbuf;
char * rbuf;
unsigned int rpos;
@@ -40,8 +40,8 @@ CLASS(SERVER) {
server_read_hook read_hook;
};
-void server_run(SERVER this);
-void server_close_conn(SERVER this, unsigned int handle);
+void serverRun(Server this);
+void serverCloseConn(Server this, unsigned int handle);
#endif // __SERVER_H__
diff --git a/include/socket.h b/include/socket.h
index 5c353aa..e5b116d 100644
--- a/include/socket.h
+++ b/include/socket.h
@@ -1,23 +1,23 @@
#ifndef __SOCKET_H__
#define __SOCKET_H__
-#include /* for in_port_t */
+#include /* for in_port_t */
+#include "class.h"
#include "logger.h"
-#include "cclass.h"
-
-CLASS(SOCK) {
- LOGGER logger;
+CLASS(Sock) {
+ Logger log;
in_port_t port;
struct sockaddr_in addr;
- int handle; /* socket handle for server */
+ int handle;
};
-void sock_connect(SOCK this, const char * addr);
-void sock_listen(SOCK this, int backlog);
-SOCK sock_accept(SOCK this, char remoteAddr[16]);
+void socketConnect(Sock this, const char * addr);
+void socketListen(Sock this, int backlog);
+Sock socketAccept(Sock this, char remoteAddr[16]);
-#endif /* __SOCKET_H__ */
+#endif // __SOCKET_H__
// vim: set ts=4 sw=4:
+
diff --git a/src/cclass.c b/src/cclass.c
deleted file mode 100644
index 3f02a69..0000000
--- a/src/cclass.c
+++ /dev/null
@@ -1,119 +0,0 @@
-/**
- * \file
- * cclass.c: basic "class-like" handling of code and data structures
- * Copyright (C) 2011 Georg Hopp
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see .
- */
-
-#include
-#include
-#include
-#include
-
-#include "cclass.h"
-
-#undef __construct
-#undef __clear
-#undef __destruct
-#undef __jsonConst
-#undef __toJson
-
-void *
-_new(const CCLASS _class, ...)
-{
- const CCLASS class = _class;
- void * object = calloc(1, class->size + sizeof(void *));
-
- * (const struct _CCLASS **)object = class;
- object += sizeof(CCLASS);
-
- if (class->__construct) {
- va_list params;
-
- va_start(params, _class);
- class->__construct(object, ¶ms);
- va_end(params);
- }
-
- return object;
-}
-
-void *
-_newFromJson(const CCLASS _class, struct json_object * json)
-{
- const CCLASS class = _class;
- void * object = calloc(1, class->size + sizeof(CCLASS));
-
- * (const struct _CCLASS **) object = class;
- object += sizeof(CCLASS);
-
- if (class->__jsonConst && json) {
- class->__jsonConst(object, json);
- }
-
- return object;
-}
-
-int
-_instanceOf(const CCLASS _class, void * _object)
-{
- const CCLASS * class = _object - sizeof(CCLASS);
-
- return (class && _class == *class);
-}
-
-
-void
-clear(void * _object)
-{
- const CCLASS * class = _object - sizeof(CCLASS);
-
- if (_object && *class && (*class)->__clear) {
- (*class)->__clear(_object);
- }
-}
-
-void
-delete(void ** _object)
-{
- const CCLASS * class = (*_object) - sizeof(CCLASS);
-
- if (*_object && *class && (*class)->__destruct) {
- (*class)->__destruct(*_object);
- }
-
- free((void *)class);
- *_object = NULL;
-}
-
-void
-toJson(void * _object, struct json_object ** json)
-{
- const CCLASS * class = _object - sizeof(CCLASS);
-
- if (_object && *class && (*class)->__toJson) {
- (*class)->__toJson(_object, json);
- }
-}
-
-int
-isObject(void * _object)
-{
- const CCLASS * class = _object - sizeof(CCLASS);
-
- return (_object && (*class) && CCLASS_MAGIC == (*class)->magic);
-}
-
-// vim: set et ts=4 sw=4:
diff --git a/src/class.c b/src/class.c
new file mode 100644
index 0000000..98d5604
--- /dev/null
+++ b/src/class.c
@@ -0,0 +1,28 @@
+#include
+#include
+
+#include "class.h"
+#include "interface.h"
+
+inline
+void *
+class_getInterface(class_ptr * class, iface_ptr _iface)
+{
+ void * iface = (void *)IFACE_GET(*class, _iface);
+
+ while(NULL == iface && HAS_PARENT(*class)) {
+ *class = (*class)->parent;
+ iface = (void *)IFACE_GET(*class, _iface);
+ }
+
+ return iface;
+}
+
+inline
+class_ptr
+class_getClass(void * object)
+{
+ return *(class_ptr *)(object - sizeof(void*));
+}
+
+// vim: set ts=4 sw=4:
diff --git a/src/daemonize.c b/src/daemonize.c
index 6776da1..e07a1af 100644
--- a/src/daemonize.c
+++ b/src/daemonize.c
@@ -17,7 +17,7 @@ void daemonize(void) {
setsid();
/* connect all standard streams to /dev/null */
- freopen("/dev/null", "w", stderr);
- freopen("/dev/null", "r", stdin);
- freopen("/dev/null", "w", stdout);
+ stderr = freopen("/dev/null", "w", stderr);
+ stdin = freopen("/dev/null", "r", stdin);
+ stdout = freopen("/dev/null", "w", stdout);
}
diff --git a/src/interface.c b/src/interface.c
new file mode 100644
index 0000000..2d8fa02
--- /dev/null
+++ b/src/interface.c
@@ -0,0 +1,45 @@
+#include
+#include
+
+#include "interface.h"
+
+#ifndef TRUE
+#define TRUE 1
+#endif // TRUE
+
+static
+inline
+int
+comp(const void * _a, const void * _b)
+{
+ const struct interface * a = **(const struct interface ***)_a;
+ const struct interface * b = **(const struct interface ***)_b;
+ return ((a)<(b))? -1 : ((a)>(b))? 1 : 0;
+}
+
+/**
+ * this one is important in selector functions to get the correct interface
+ * implementation of a class.
+ */
+struct interface *
+interfaceGet(iface_impl_ptr iface_impl, const iface_ptr _iface)
+{
+ const iface_ptr * iface = &_iface;
+ void * dummy;
+
+ if (! iface_impl->simpl) {
+ qsort((void**)(iface_impl->impl), iface_impl->nimpl, sizeof(iface_ptr), comp);
+ iface_impl->simpl=TRUE;
+ }
+
+ dummy = bsearch(
+ &iface,
+ iface_impl->impl,
+ iface_impl->nimpl,
+ sizeof(iface_ptr),
+ comp);
+
+ return dummy? *(struct interface **)dummy : dummy;
+}
+
+// vim: set ts=4 sw=4:
diff --git a/src/interface/class.c b/src/interface/class.c
new file mode 100644
index 0000000..9772224
--- /dev/null
+++ b/src/interface/class.c
@@ -0,0 +1,43 @@
+#include
+#include
+#include
+
+#include "class.h"
+#include "interface/class.h"
+
+const
+struct interface i_Class = {
+ "class",
+ 3
+};
+
+inline
+void *
+classNew(class_ptr class, ...)
+{
+ void * object = calloc(1, class->object_size + sizeof(void*));
+ va_list params;
+
+ if (class->init) class->init();
+
+ * (class_ptr *)object = class;
+ object += sizeof(void*);
+
+ va_start(params, class);
+ CALL(object, Class, ctor, ¶ms);
+ va_end(params);
+
+ return object;
+}
+
+inline
+void
+classDelete(void ** object)
+{
+ CALL(*object, Class, dtor);
+
+ free(*object - sizeof(void*));
+ *object = NULL;
+}
+
+// vim: set ts=4 sw=4:
diff --git a/src/interface/logger.c b/src/interface/logger.c
new file mode 100644
index 0000000..6829128
--- /dev/null
+++ b/src/interface/logger.c
@@ -0,0 +1,37 @@
+#include
+
+#include "logger.h"
+#include "interface/logger.h"
+
+const struct interface i_Logger = {
+ "logger",
+ 1
+};
+
+inline
+void
+loggerLog(void * _object, logger_level level, const char * const fmt, ...) {
+ Logger object = _object;
+
+ if (level >= object->min_level) {
+ char * msg = NULL;
+ size_t msg_size = 0;
+ va_list params;
+
+ va_start(params, fmt);
+ msg_size = vsnprintf(msg, msg_size, fmt, params);
+ va_end(params);
+
+ msg = malloc(msg_size + 1);
+
+ va_start(params, fmt);
+ vsnprintf(msg, msg_size + 1, fmt, params);
+ va_end(params);
+
+ CALL(_object, Logger, log, level, msg);
+
+ free(msg);
+ }
+}
+
+// vim: set ts=4 sw=4:
diff --git a/src/logger.c b/src/logger.c
index 96ad785..6a44531 100644
--- a/src/logger.c
+++ b/src/logger.c
@@ -1,18 +1,33 @@
-#include "logger.h"
+#include
-extern void logger_syslog(int level, const char * msg);
+#include "logger.h"
+#include "interface/class.h"
+#include "interface/logger.h"
-INIT_CLASS(LOGGER);
+const
+char * const
+logger_level_str[] = {
+ "DEBUG",
+ "INFO",
+ "NOTICE",
+ "WARNING",
+ "ERR",
+ "CRIT",
+ "ALERT",
+ "EMERG"
+};
-__construct(LOGGER)
+static
+void
+ctor(void * _this, va_list * params)
{
- this->logfncts[0] = logger_syslog;
- this->logfncts_count = 1;
+ Logger this = _this;
+ this->min_level = va_arg(*params, int);
}
-__destruct(LOGGER) {}
-__jsonConst(LOGGER) {}
-__toJson(LOGGER) {}
-__clear(LOGGER) {}
+static void dtor(void * _this) {}
+
+INIT_IFACE(Class, ctor, dtor, NULL);
+CREATE_CLASS(Logger, NULL, IFACE(Class));
// vim: set ts=4 sw=4:
diff --git a/src/logger/add.c b/src/logger/add.c
deleted file mode 100644
index 474fecc..0000000
--- a/src/logger/add.c
+++ /dev/null
@@ -1,11 +0,0 @@
-#include "logger.h"
-
-void
-logger_add(LOGGER this, logger_logfnct logfunc) {
- if (this->logfncts_count < MAX_LOG_FNCTS) {
- this->logfncts[this->logfncts_count] = logfunc;
- this->logfncts_count++;
- }
-}
-
-// vim: set ts=4 sw=4:
diff --git a/src/logger/log.c b/src/logger/log.c
deleted file mode 100644
index f4c5dfa..0000000
--- a/src/logger/log.c
+++ /dev/null
@@ -1,30 +0,0 @@
-#define _ISOC99_SOURCE
-
-#include
-#include
-
-#include "logger.h"
-
-void
-logger_log(LOGGER this, int level, const char * message, ...) {
- va_list args;
- char buffer[1025];
- logger_logfnct * logfnct;
-
- int maxBuf = sizeof(buffer)/sizeof(buffer[0]);
-
- memset(buffer, 0, maxBuf);
-
- va_start(args, message);
- vsnprintf(buffer, 1024, message, args);
- va_end(args);
-
- logfnct = this->logfncts;
-
- while (NULL != *logfnct) {
- (*logfnct)(level, buffer);
- logfnct++;
- }
-}
-
-// vim: set ts=4 sw=4:
diff --git a/src/logger/stderr.c b/src/logger/stderr.c
new file mode 100644
index 0000000..b6f5c56
--- /dev/null
+++ b/src/logger/stderr.c
@@ -0,0 +1,16 @@
+#include
+
+#include "logger.h"
+#include "interface/logger.h"
+
+static
+void
+logStderr(void * this, logger_level level, const char * const msg)
+{
+ fprintf(stderr, "[%s] %s\n", logger_level_str[level], msg);
+}
+
+INIT_IFACE(Logger, logStderr);
+CREATE_CLASS(LoggerStderr, Logger, IFACE(Logger));
+
+// vim: set ts=4 sw=4:
diff --git a/src/logger/syslog.c b/src/logger/syslog.c
index 0299fa8..a42f901 100644
--- a/src/logger/syslog.c
+++ b/src/logger/syslog.c
@@ -1,20 +1,29 @@
#include
-const int priority[] = {
- LOG_USER | LOG_EMERG,
- LOG_USER | LOG_ALERT,
- LOG_USER | LOG_CRIT,
- LOG_USER | LOG_ERR,
- LOG_USER | LOG_WARNING,
- LOG_USER | LOG_NOTICE,
- LOG_USER | LOG_INFO,
- LOG_USER | LOG_DEBUG
+#include "logger.h"
+#include "interface/logger.h"
+
+static
+const
+int syslog_priority[] = {
+ LOG_USER | LOG_DEBUG,
+ LOG_USER | LOG_INFO,
+ LOG_USER | LOG_NOTICE,
+ LOG_USER | LOG_WARNING,
+ LOG_USER | LOG_ERR,
+ LOG_USER | LOG_CRIT,
+ LOG_USER | LOG_ALERT,
+ LOG_USER | LOG_EMERG
};
+static
void
-logger_syslog(int level, const char * msg)
+logSyslog(void * this, logger_level level, const char * const msg)
{
- syslog(priority[level], "%s", msg);
+ syslog(syslog_priority[level], "[%s] %s", logger_level_str[level], msg);
}
+INIT_IFACE(Logger, logSyslog);
+CREATE_CLASS(LoggerSyslog, Logger, IFACE(Logger));
+
// vim: set ts=4 sw=4:
diff --git a/src/server.c b/src/server.c
index 73304c9..c366b5f 100644
--- a/src/server.c
+++ b/src/server.c
@@ -2,34 +2,38 @@
#include /* for memset and stuff */
#include /* for getopt */
+#include "class.h"
#include "server.h"
#include "socket.h"
-#include "server.h"
#include "logger.h"
-#include "cclass.h"
-
-INIT_CLASS(SERVER);
+#include "interface/class.h"
-__construct(SERVER)
+static
+void
+ctor(void * _this, va_list * params)
{
+ Server this = _this;
in_port_t port;
unsigned int backlog;
- this->logger = va_arg(* params, LOGGER);
+ this->logger = va_arg(* params, Logger);
port = va_arg(* params, int);
backlog = va_arg(* params, unsigned int);
- this->sock = new(SOCK, this->logger, port);
- sock_listen(this->sock, backlog);
+ this->sock = new(Sock, this->logger, port);
+ socketListen(this->sock, backlog);
(this->fds)[0].fd = this->sock->handle;
(this->fds)[0].events = POLLIN;
this->nfds = 1;
}
-__destruct(SERVER)
+static
+void
+dtor(void * _this)
{
- int i;
+ Server this = _this;
+ int i;
for (i=1; infds; i++) {
/*
@@ -41,8 +45,7 @@ __destruct(SERVER)
delete(&this->sock);
}
-__jsonConst(SERVER) {}
-__toJson(SERVER) {}
-__clear(SERVER) {}
+INIT_IFACE(Class, ctor, dtor, NULL);
+CREATE_CLASS(Server, NULL, IFACE(Class));
// vim: set ts=4 sw=4:
diff --git a/src/server/close_conn.c b/src/server/close_conn.c
index b131434..29dbcfd 100644
--- a/src/server/close_conn.c
+++ b/src/server/close_conn.c
@@ -1,9 +1,10 @@
#include
#include "server.h"
+#include "interface/class.h"
void
-server_close_conn(SERVER this, unsigned int i)
+serverCloseConn(Server this, unsigned int i)
{
delete(&((this->conns)[i].sock));
CLEAR_CONN(this, i);
diff --git a/src/server/run.c b/src/server/run.c
index 90bfd52..ecac6d7 100644
--- a/src/server/run.c
+++ b/src/server/run.c
@@ -4,17 +4,18 @@
#include /* for errno */
#include
-#include "include/logger.h"
-#include "include/server.h"
-#include "include/socket.h"
-#include "include/signalHandling.h"
+#include "server.h"
+#include "socket.h"
+#include "logger.h"
+#include "signalHandling.h"
+#include "interface/class.h"
#undef MAX
#define MAX(x,y) ((x) > (y) ? (x) : (y))
static
int
-server_poll(SERVER this) {
+serverPoll(Server this) {
int events;
/*
@@ -30,7 +31,7 @@ server_poll(SERVER this) {
/* Fallthrough */
case EINTR:
- logger_log(this->logger, LOGGER_CRIT,
+ loggerLog(this->logger, LOGGER_CRIT,
"poll systemcall failed: [%s] - service terminated",
strerror(errno));
//exit(EXIT_FAILURE); /* @TODO do real shutdown here */
@@ -42,13 +43,13 @@ server_poll(SERVER this) {
static
void
-server_handle_accept(SERVER this)
+serverHandleAccept(Server this)
{
if (0 != ((this->fds)[0].revents & POLLIN)) {
char remoteAddr[16] = "";
- SOCK acc;
+ Sock acc;
- acc = sock_accept(this->sock, remoteAddr);
+ acc = socketAccept(this->sock, remoteAddr);
if (-1 != acc->handle) {
(this->conns)[this->nfds].sock = acc; // save the socket handle
@@ -65,7 +66,7 @@ server_handle_accept(SERVER this)
static
int
-server_read(SERVER this)
+serverRead(Server this)
{
unsigned int i;
size_t _read;
@@ -85,7 +86,8 @@ server_read(SERVER this)
* read failure / close connection
* FALLTHROUGH
*/
- server_close_conn(this, i);
+ loggerLog(this->logger, LOGGER_INFO, "connection closed...");
+ serverCloseConn(this, i);
break;
default:
@@ -102,12 +104,12 @@ server_read(SERVER this)
}
void
-server_run(SERVER this)
+serverRun(Server this)
{
/*
* @TODO again...add verbosity to logger....
*/
- logger_log(this->logger, LOGGER_INFO, "service started");
+ loggerLog(this->logger, LOGGER_INFO, "service started");
while (!doShutdown) /* until error or signal */
{
@@ -116,16 +118,16 @@ server_run(SERVER this)
* @TODO take return value of poll into account with
* further handling!
*/
- events = server_poll(this);
+ events = serverPoll(this);
if (doShutdown) break;
/*
* handle accept
*/
- server_handle_accept(this);
+ serverHandleAccept(this);
/* handle reads */
- server_read(this);
+ serverRead(this);
}
}
diff --git a/src/socket.c b/src/socket.c
index 15b25ff..a744e5e 100644
--- a/src/socket.c
+++ b/src/socket.c
@@ -1,49 +1,46 @@
-#include /* for printf() and fprintf() */
-#include /* SO_REUSEADDR */
-#include /* for socket(), bind(), and connect() */
-#include /* for sockaddr_in and inet_ntoa() */
-#include /* for atoi() and exit() */
-#include /* for memset() */
-#include /* for close() */
-#include /* for errno */
-#include
+#include
+#include
-#include "logger.h"
-#include "cclass.h"
#include "socket.h"
+#include "logger.h"
+#include "interface/class.h"
+#include "interface/logger.h"
-
-INIT_CLASS(SOCK);
-
-__construct(SOCK)
+static
+void
+ctor(void * _this, va_list * params)
{
- int reUse = 1; /* TODO: make this configurable */
-
- this->logger = va_arg(* params, LOGGER);
- this->port = va_arg(* params, int);
-
- /* Create socket for incoming connections */
- if (-1 == (this->handle = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP))) {
- logger_log(this->logger, LOGGER_CRIT,
- "error opening socket: %s - service terminated",
- strerror(errno));
- exit(EXIT_FAILURE);
- }
+ Sock this = _this;
+ int reUse = 1; /* TODO: make this configurable */
+
+ this->log = va_arg(* params, Logger);
+ this->port = va_arg(* params, int);
+
+ /* Create socket for incoming connections */
+ if (-1 == (this->handle = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP))) {
+ loggerLog(this->log, LOGGER_CRIT,
+ "error opening socket: %s - service terminated",
+ strerror(errno));
+ exit(EXIT_FAILURE);
+ }
- /* Make the socket REUSE a TIME_WAIT socket */
- setsockopt(this->handle, SOL_SOCKET, SO_REUSEADDR, &reUse, sizeof (reUse));
+ /* Make the socket REUSE a TIME_WAIT socket */
+ setsockopt(this->handle, SOL_SOCKET, SO_REUSEADDR, &reUse, sizeof (reUse));
}
-__destruct(SOCK)
+static
+void
+dtor(void * _this)
{
+ Sock this = _this;
+
if (0 != this->handle) {
shutdown(this->handle, SHUT_RDWR);
close(this->handle);
}
}
-__jsonConst(SOCK) {}
-__toJson(SOCK) {}
-__clear(SOCK) {}
+INIT_IFACE(Class, ctor, dtor, NULL);
+CREATE_CLASS(Sock, NULL, IFACE(Class));
// vim: set ts=4 sw=4:
diff --git a/src/socket/accept.c b/src/socket/accept.c
index e01bdfe..708a45f 100644
--- a/src/socket/accept.c
+++ b/src/socket/accept.c
@@ -1,27 +1,19 @@
-#include /* for printf() and fprintf() */
-#include /* SO_REUSEADDR */
-#include /* for socket(), bind(), and connect() */
-#include /* for sockaddr_in and inet_ntoa() */
-#include /* for atoi() and exit() */
-#include /* for memset() */
-#include /* for close() */
#include /* for errno */
-#include
-#include "logger.h"
-#include "cclass.h"
#include "socket.h"
+#include "interface/class.h"
+#include "interface/logger.h"
-SOCK
-sock_accept(SOCK this, char remoteAddr[16])
+Sock
+socketAccept(Sock this, char remoteAddr[16])
{
- SOCK sock; /* Socket for client */
+ Sock sock; /* Socket for client */
unsigned int len; /* Length of client address data structure */
/* Set the size of the in-out parameter */
len = sizeof(this->addr);
- sock = new(SOCK, this->logger, this->port);
+ sock = new(Sock, this->log, this->port);
/**
* @TODO: change port to remote port on success
*/
@@ -29,10 +21,10 @@ sock_accept(SOCK this, char remoteAddr[16])
/* Wait for a client to connect */
sock->handle = accept(this->handle, (struct sockaddr *) &(sock->addr), &len);
if (-1 == sock->handle) {
- logger_log(this->logger, LOGGER_WARNING,
+ loggerLog(this->log, LOGGER_WARNING,
"error acception connection: %s", strerror(errno));
} else {
- logger_log(this->logger, LOGGER_INFO,
+ loggerLog(this->log, LOGGER_INFO,
"handling client %s\n", inet_ntoa((sock->addr).sin_addr));
}
diff --git a/src/socket/connect.c b/src/socket/connect.c
index 41ed76b..abb2348 100644
--- a/src/socket/connect.c
+++ b/src/socket/connect.c
@@ -1,27 +1,20 @@
-#include /* for printf() and fprintf() */
-#include /* SO_REUSEADDR */
-#include /* for socket(), bind(), and connect() */
-#include /* for sockaddr_in and inet_ntoa() */
#include /* for atoi() and exit() */
-#include /* for memset() */
-#include /* for close() */
#include /* for errno */
-#include
-#include "logger.h"
-#include "cclass.h"
#include "socket.h"
+#include "interface/class.h"
+#include "interface/logger.h"
void
-sock_connect(SOCK this, const char * addr)
+socketConnect(Sock this, const char * addr)
{
inet_pton(AF_INET, addr, &((this->addr).sin_addr));
(this->addr).sin_family = AF_INET; /* Internet address family */
(this->addr).sin_port = htons(this->port); /* Local port */
if (-1 == connect(this->handle, (struct sockaddr*) &(this->addr), sizeof(this->addr))) {
- logger_log(this->logger, LOGGER_CRIT,
+ loggerLog(this->log, LOGGER_CRIT,
"error connection socket: %s - service terminated",
strerror(errno));
exit(EXIT_FAILURE);
diff --git a/src/socket/listen.c b/src/socket/listen.c
index 847816e..13d3b65 100644
--- a/src/socket/listen.c
+++ b/src/socket/listen.c
@@ -1,20 +1,13 @@
-#include /* for printf() and fprintf() */
-#include /* SO_REUSEADDR */
-#include /* for socket(), bind(), and connect() */
-#include /* for sockaddr_in and inet_ntoa() */
#include /* for atoi() and exit() */
-#include /* for memset() */
-#include /* for close() */
#include /* for errno */
-#include
-#include "logger.h"
-#include "cclass.h"
#include "socket.h"
+#include "interface/class.h"
+#include "interface/logger.h"
void
-sock_listen(SOCK this, int backlog)
+socketListen(Sock this, int backlog)
{
(this->addr).sin_family = AF_INET; /* Internet address family */
(this->addr).sin_addr.s_addr = htonl(INADDR_ANY); /* Any incoming interface */
@@ -22,7 +15,7 @@ sock_listen(SOCK this, int backlog)
/* Bind to the local address */
if (-1 == bind(this->handle, (struct sockaddr *) &(this->addr), sizeof(this->addr))) {
- logger_log(this->logger, LOGGER_CRIT,
+ loggerLog(this->log, LOGGER_CRIT,
"error binding socket: %s - service terminated",
strerror(errno));
exit(EXIT_FAILURE);
@@ -30,7 +23,7 @@ sock_listen(SOCK this, int backlog)
/* Mark the socket so it will listen for incoming connections */
if (-1 == listen(this->handle, backlog)) {
- logger_log(this->logger, LOGGER_CRIT,
+ loggerLog(this->log, LOGGER_CRIT,
"error binding socket: %s - service terminated",
strerror(errno));
exit(EXIT_FAILURE);
diff --git a/src/testserver.c b/src/testserver.c
index 96bcba3..c290907 100644
--- a/src/testserver.c
+++ b/src/testserver.c
@@ -3,7 +3,9 @@
#include
#include "server.h"
+#include "logger.h"
#include "signalHandling.h"
+#include "interface/class.h"
static void
read_hook(const char * _buffer, size_t size)
@@ -11,7 +13,7 @@ read_hook(const char * _buffer, size_t size)
char buffer[1025];
memset(buffer, 0, 1025);
- snprintf(buffer, size, _buffer);
+ snprintf(buffer, 1025>size? size : 1024, "%s", _buffer);
printf("%s\n", buffer);
}
@@ -19,13 +21,13 @@ read_hook(const char * _buffer, size_t size)
int
main()
{
- LOGGER logger = new(LOGGER, NULL);
- SERVER server = new(SERVER, logger, 11212, SOMAXCONN);
+ Logger logger = new(LoggerStderr, LOGGER_INFO);
+ Server server = new(Server, logger, 11212, SOMAXCONN);
server->read_hook = read_hook;
init_signals();
- server_run(server);
+ serverRun(server);
delete(&server);
delete(&logger);