ithewei 6 年之前
父節點
當前提交
2d65038c93
共有 5 個文件被更改,包括 185 次插入17 次删除
  1. 7 7
      base/hlog.c
  2. 9 9
      base/hlog.h
  3. 91 0
      event/nlog.c
  4. 30 0
      event/nlog.h
  5. 48 1
      examples/loop.c

+ 7 - 7
base/hlog.c

@@ -70,7 +70,7 @@ int hlog_printf(int level, const char* fmt, ...) {
         len += snprintf(s_logbuf + len, LOG_BUFSIZE - len, "%s", CL_CLR);
         len += snprintf(s_logbuf + len, LOG_BUFSIZE - len, "%s", CL_CLR);
     }
     }
 
 
-    s_logger(s_logbuf, len);
+    s_logger(level, s_logbuf, len);
 
 
     hmutex_unlock(&s_mutex);
     hmutex_unlock(&s_mutex);
     return len;
     return len;
@@ -80,12 +80,12 @@ void hlog_enable_color(int on) {
     s_logcolor = on;
     s_logcolor = on;
 }
 }
 
 
-void stdout_logger(const char* buf, int len) {
-    fprintf(stdout, "%s\n", buf);
+void stdout_logger(int loglevel, const char* buf, int len) {
+    fprintf(stdout, "%s", buf);
 }
 }
 
 
-void stderr_logger(const char* buf, int len) {
-    fprintf(stderr, "%s\n", buf);
+void stderr_logger(int loglevel, const char* buf, int len) {
+    fprintf(stderr, "%s", buf);
 }
 }
 
 
 static void ts_logfile(time_t ts, char* buf, int len) {
 static void ts_logfile(time_t ts, char* buf, int len) {
@@ -148,10 +148,10 @@ static FILE* shift_logfile() {
     return s_logfp;
     return s_logfp;
 }
 }
 
 
-void file_logger(const char* buf, int len) {
+void file_logger(int loglevel, const char* buf, int len) {
     FILE* fp = shift_logfile();
     FILE* fp = shift_logfile();
     if (fp == NULL) return;
     if (fp == NULL) return;
-    fprintf(fp, "%s\n", buf);
+    fprintf(fp, "%s", buf);
     if (s_fflush) {
     if (s_fflush) {
         fflush(fp);
         fflush(fp);
     }
     }

+ 9 - 9
base/hlog.h

@@ -52,10 +52,10 @@ enum LOG_LEVEL {
 #define MAX_LOG_FILESIZE            (1<<23)  // 8M
 #define MAX_LOG_FILESIZE            (1<<23)  // 8M
 
 
 // logger
 // logger
-typedef void (*hlog_handler)(const char* buf, int len);
-void    stderr_logger(const char* buf, int len);
-void    stdout_logger(const char* buf, int len);
-void    file_logger(const char* buf, int len);
+typedef void (*hlog_handler)(int loglevel, const char* buf, int len);
+void    stderr_logger(int loglevel, const char* buf, int len);
+void    stdout_logger(int loglevel, const char* buf, int len);
+void    file_logger(int loglevel, const char* buf, int len);
 
 
 // common log settings
 // common log settings
 void    hlog_set_logger(hlog_handler fn);
 void    hlog_set_logger(hlog_handler fn);
@@ -63,11 +63,11 @@ void    hlog_set_level(int level);
 void    hlog_set_remain_days(int days);
 void    hlog_set_remain_days(int days);
 
 
 int     hlog_printf(int level, const char* fmt, ...);
 int     hlog_printf(int level, const char* fmt, ...);
-#define hlogd(fmt, ...) hlog_printf(LOG_LEVEL_DEBUG, fmt " [%s:%d:%s]", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
-#define hlogi(fmt, ...) hlog_printf(LOG_LEVEL_INFO,  fmt " [%s:%d:%s]", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
-#define hlogw(fmt, ...) hlog_printf(LOG_LEVEL_WARN,  fmt " [%s:%d:%s]", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
-#define hloge(fmt, ...) hlog_printf(LOG_LEVEL_ERROR, fmt " [%s:%d:%s]", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
-#define hlogf(fmt, ...) hlog_printf(LOG_LEVEL_FATAL, fmt " [%s:%d:%s]", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
+#define hlogd(fmt, ...) hlog_printf(LOG_LEVEL_DEBUG, fmt " [%s:%d:%s]\n", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
+#define hlogi(fmt, ...) hlog_printf(LOG_LEVEL_INFO,  fmt " [%s:%d:%s]\n", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
+#define hlogw(fmt, ...) hlog_printf(LOG_LEVEL_WARN,  fmt " [%s:%d:%s]\n", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
+#define hloge(fmt, ...) hlog_printf(LOG_LEVEL_ERROR, fmt " [%s:%d:%s]\n", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
+#define hlogf(fmt, ...) hlog_printf(LOG_LEVEL_FATAL, fmt " [%s:%d:%s]\n", ## __VA_ARGS__, __FILE__, __LINE__, __FUNCTION__)
 
 
 // below for file logger
 // below for file logger
 int     hlog_set_file(const char* file);
 int     hlog_set_file(const char* file);

+ 91 - 0
event/nlog.c

@@ -0,0 +1,91 @@
+#include "nlog.h"
+
+#include "list.h"
+#include "hdef.h"
+#include "hsocket.h"
+
+typedef struct network_logger_s {
+    hloop_t*            loop;
+    hio_t*              listenio;
+    struct list_head    clients;
+} network_logger_t;
+
+typedef struct nlog_client {
+    hio_t*              io;
+    struct list_node    node;
+} nlog_client;
+
+static network_logger_t s_logger = {0};
+
+void on_close(hio_t* io) {
+    printf("on_close fd=%d error=%d\n", io->fd, io->error);
+    struct list_node* next = s_logger.clients.next;
+    nlog_client* client;
+    while (next != &s_logger.clients) {
+        client = list_entry(next, nlog_client, node);
+        next = next->next;
+        printf("client->io=%p client->io->fd=%d io=%p io->fd=%d\n", client->io, client->io->fd, io, io->fd);
+        if (client->io == io) {
+            list_del(next->prev);
+            SAFE_FREE(client);
+            break;
+        }
+    }
+}
+
+void on_read(hio_t* io, void* buf, int readbytes) {
+    printf("on_read fd=%d readbytes=%d\n", io->fd, readbytes);
+    printf("< %s\n", buf);
+    // nothing to do
+}
+
+static void on_accept(hio_t* io, int connfd) {
+    printf("on_accept listenfd=%d connfd=%d\n", io->fd, connfd);
+    char localaddrstr[INET6_ADDRSTRLEN+16] = {0};
+    char peeraddrstr[INET6_ADDRSTRLEN+16] = {0};
+    printf("accept listenfd=%d connfd=%d [%s] <= [%s]\n", io->fd, connfd,
+            sockaddr_snprintf(io->localaddr, localaddrstr, sizeof(localaddrstr)),
+            sockaddr_snprintf(io->peeraddr, peeraddrstr, sizeof(peeraddrstr)));
+
+    static char s_readbuf[256] = {0};
+    hio_t* connio = hread(io->loop, connfd, s_readbuf, sizeof(s_readbuf), on_read);
+    connio->close_cb = on_close;
+
+    // free on_close
+    nlog_client* client;
+    SAFE_ALLOC_SIZEOF(client);
+    client->io = connio;
+    list_add(&client->node, &s_logger.clients);
+}
+
+void network_logger(int loglevel, const char* buf, int len) {
+    struct list_node* node;
+    nlog_client* client;
+    list_for_each (node, &s_logger.clients) {
+        client = list_entry(node, nlog_client, node);
+        hwrite(s_logger.loop, client->io->fd, buf, len, NULL);
+    }
+}
+
+hio_t* nlog_listen(hloop_t* loop, int port) {
+    list_init(&s_logger.clients);
+    s_logger.loop = loop;
+    s_logger.listenio = hlisten(loop, port, on_accept);
+    return s_logger.listenio;
+}
+
+void nlog_close() {
+    if (s_logger.loop == NULL) return;
+    struct list_node* next = s_logger.clients.next;
+    nlog_client* client;
+    while (next != &s_logger.clients) {
+        client = list_entry(next, nlog_client, node);
+        next = next->next;
+        list_del(next->prev);
+        SAFE_FREE(client);
+    }
+    if (s_logger.listenio) {
+        hclose(s_logger.listenio);
+        s_logger.listenio = NULL;
+    }
+}

+ 30 - 0
event/nlog.h

@@ -0,0 +1,30 @@
+#ifndef HW_NLOG_H_
+#define HW_NLOG_H_
+
+// nlog: extend hlog use hloop
+
+/* you can recv log by:
+ * Windows: telnet ip port
+ * Linux: nc ip port
+ */
+
+/*
+ * @code
+    hloop_t loop;
+    hloop_init(&loop);
+    hlog_set_logger(network_logger);
+    nlog_listen(&loop, DEFAULT_LOG_PORT);
+    hloop_run(&loop);
+    nlog_close();
+ */
+
+#include "hlog.h"
+#include "hloop.h"
+
+#define DEFAULT_LOG_PORT    10514
+
+void network_logger(int loglevel, const char* buf, int len);
+hio_t* nlog_listen(hloop_t* loop, int port);
+void nlog_close();
+
+#endif // HW_NLOG_H_

+ 48 - 1
examples/loop.c

@@ -1,5 +1,18 @@
 #include "hloop.h"
 #include "hloop.h"
 #include "hbase.h"
 #include "hbase.h"
+#include "nlog.h"
+
+void mylogger(int loglevel, const char* buf, int len) {
+    if (loglevel >= LOG_LEVEL_ERROR) {
+        stderr_logger(loglevel, buf, len);
+    }
+
+    if (loglevel >= LOG_LEVEL_INFO) {
+        file_logger(loglevel, buf, len);
+    }
+
+    network_logger(loglevel, buf, len);
+}
 
 
 void on_idle(hidle_t* idle) {
 void on_idle(hidle_t* idle) {
     printf("on_idle: event_id=%lu\tpriority=%d\tuserdata=%ld\n", idle->event_id, idle->priority, (long)idle->userdata);
     printf("on_idle: event_id=%lu\tpriority=%d\tuserdata=%ld\n", idle->event_id, idle->priority, (long)idle->userdata);
@@ -16,21 +29,55 @@ void cron_hourly(htimer_t* timer) {
     printf("cron_hourly: %s\n", ctime(&tt));
     printf("cron_hourly: %s\n", ctime(&tt));
 }
 }
 
 
+void timer_write_log(htimer_t* timer) {
+    static int cnt = 0;
+    hlogd("[%d] Do you recv me?", ++cnt);
+    hlogi("[%d] Do you recv me?", ++cnt);
+    hloge("[%d] Do you recv me?", ++cnt);
+}
+
+void on_stdin(hio_t* io, void* buf, int readbytes) {
+    printf("on_stdin fd=%d readbytes=%d\n", io->fd, readbytes);
+    printf("> %s\n", buf);
+    if (strncmp((char*)buf, "quit", 4) == 0) {
+        hloop_stop(io->loop);
+    }
+}
+
 int main() {
 int main() {
+    // memcheck atexit
     MEMCHECK;
     MEMCHECK;
 
 
     hloop_t loop;
     hloop_t loop;
     hloop_init(&loop);
     hloop_init(&loop);
+
+    // test idle and priority
     for (int i = HEVENT_LOWEST_PRIORITY; i <= HEVENT_HIGHEST_PRIORITY; ++i) {
     for (int i = HEVENT_LOWEST_PRIORITY; i <= HEVENT_HIGHEST_PRIORITY; ++i) {
         hidle_t* idle = hidle_add(&loop, on_idle, 10);
         hidle_t* idle = hidle_add(&loop, on_idle, 10);
         idle->priority = i;
         idle->priority = i;
     }
     }
+
+    // test timer timeout
     for (int i = 1; i <= 10; ++i) {
     for (int i = 1; i <= 10; ++i) {
         htimer_t* timer = htimer_add(&loop, on_timer, i*1000, 3);
         htimer_t* timer = htimer_add(&loop, on_timer, i*1000, 3);
         timer->userdata = (void*)i;
         timer->userdata = (void*)i;
     }
     }
+    // test timer period
     int minute = time(NULL)%3600/60;
     int minute = time(NULL)%3600/60;
-    htimer_add_period(&loop, cron_hourly, minute+1, -1, -1, -1, -1, 1);
+    htimer_add_period(&loop, cron_hourly, minute+1, -1, -1, -1, -1, INFINITE);
+
+    // test network_logger
+    htimer_add(&loop, timer_write_log, 1000, INFINITE);
+    hlog_set_logger(mylogger);
+    hlog_set_file("loop.log");
+    nlog_listen(&loop, DEFAULT_LOG_PORT);
+
+    // test nonblock stdin
+    printf("input 'quit' to quit loop\n");
+    char buf[64];
+    hread(&loop, STDIN_FILENO, buf, sizeof(buf), on_stdin);
+
     hloop_run(&loop);
     hloop_run(&loop);
+    nlog_close();
     return 0;
     return 0;
 }
 }