Introduce struct __sourceloc

Replaces (const char *file, unsigned int line, const char *function) arguments
to all logging functions, simplifies malloc/free tracking code in
overlay_buffer.c and Rhizome manifest alloc/free tracking in rhizome_bundle.c.

Use __HERE__ macro instead of (__FILE__, __LINE__, __FUNCTION__) everywhere.

Special __NOWHERE__ macro is equivalent to (NULL, 0, NULL).

Declare net.c functions in new "net.h" header, so log.c doesn't have to pull
in the entire "serval.h" just to use write_str().

Facilitates progress on issue #2.
This commit is contained in:
Andrew Bettison 2012-08-23 12:31:07 +09:30
parent fd3da58a7c
commit 27a0a6eeb5
11 changed files with 169 additions and 148 deletions

View File

@ -88,6 +88,7 @@ HDRS= fifo.h \
sha2.h \ sha2.h \
conf.h \ conf.h \
log.h \ log.h \
net.h \
xprintf.h \ xprintf.h \
constants.h \ constants.h \
monitor-client.h \ monitor-client.h \

68
log.c
View File

@ -32,6 +32,7 @@ Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
#include <fcntl.h> #include <fcntl.h>
#include "log.h" #include "log.h"
#include "net.h"
#include "conf.h" #include "conf.h"
#include "strbuf.h" #include "strbuf.h"
#include "strbuf_helpers.h" #include "strbuf_helpers.h"
@ -128,7 +129,7 @@ static const char *_trimbuildpath(const char *path)
return &path[lastsep]; return &path[lastsep];
} }
static int _log_prepare(int level, const char *file, unsigned int line, const char *function) static int _log_prepare(int level, struct __sourceloc where)
{ {
if (level == LOG_LEVEL_SILENT) if (level == LOG_LEVEL_SILENT)
return 0; return 0;
@ -161,21 +162,22 @@ static int _log_prepare(int level, const char *file, unsigned int line, const ch
strbuf_sprintf(&logbuf, "%s.%03u ", buf, tv.tv_usec / 1000); strbuf_sprintf(&logbuf, "%s.%03u ", buf, tv.tv_usec / 1000);
} }
} }
if (file) { if (where.file) {
strbuf_sprintf(&logbuf, "%s", _trimbuildpath(file)); strbuf_sprintf(&logbuf, "%s", _trimbuildpath(where.file));
if (line) if (where.line)
strbuf_sprintf(&logbuf, ":%u", line); strbuf_sprintf(&logbuf, ":%u", where.line);
if (function) if (where.function)
strbuf_sprintf(&logbuf, ":%s()", function); strbuf_sprintf(&logbuf, ":%s()", where.function);
strbuf_putc(&logbuf, ' '); strbuf_putc(&logbuf, ' ');
} else if (function) { } else if (where.function) {
strbuf_sprintf(&logbuf, "%s() ", function); strbuf_sprintf(&logbuf, "%s() ", where.function);
} }
strbuf_putc(&logbuf, ' '); strbuf_putc(&logbuf, ' ');
return 1; return 1;
} }
static void _log_internal(int level, struct strbuf *buf){ static void _log_internal(int level, struct strbuf *buf)
{
#ifdef ANDROID #ifdef ANDROID
int alevel = ANDROID_LOG_UNKNOWN; int alevel = ANDROID_LOG_UNKNOWN;
switch (level) { switch (level) {
@ -196,20 +198,22 @@ static void _log_internal(int level, struct strbuf *buf){
#endif #endif
} }
void (*_log_implementation)(int level, struct strbuf *buf)=_log_internal; void (*_log_implementation)(int level, struct strbuf *buf) = _log_internal;
static void _log_finish(int level){ static void _log_finish(int level)
if(_log_implementation) {
if (_log_implementation)
_log_implementation(level, &logbuf); _log_implementation(level, &logbuf);
} }
void set_log_implementation(void (*log_function)(int level, struct strbuf *buf)){ void set_log_implementation(void (*log_function)(int level, struct strbuf *buf))
{
_log_implementation=log_function; _log_implementation=log_function;
} }
void logArgv(int level, const char *file, unsigned int line, const char *function, const char *label, int argc, const char *const *argv) void logArgv(int level, struct __sourceloc where, const char *label, int argc, const char *const *argv)
{ {
if (_log_prepare(level, file, line, function)) { if (_log_prepare(level, where)) {
if (label) { if (label) {
strbuf_puts(&logbuf, label); strbuf_puts(&logbuf, label);
strbuf_putc(&logbuf, ' '); strbuf_putc(&logbuf, ' ');
@ -227,47 +231,47 @@ void logArgv(int level, const char *file, unsigned int line, const char *functio
} }
} }
void logString(int level, const char *file, unsigned int line, const char *function, const char *str) void logString(int level, struct __sourceloc where, const char *str)
{ {
const char *s = str; const char *s = str;
const char *p; const char *p;
for (p = str; *p; ++p) { for (p = str; *p; ++p) {
if (*p == '\n') { if (*p == '\n') {
if (_log_prepare(level, file, line, function)) { if (_log_prepare(level, where)) {
strbuf_ncat(&logbuf, s, p - s); strbuf_ncat(&logbuf, s, p - s);
_log_finish(level); _log_finish(level);
} }
s = p + 1; s = p + 1;
} }
} }
if (p > s && _log_prepare(level, file, line, function)) { if (p > s && _log_prepare(level, where)) {
strbuf_ncat(&logbuf, s, p - s); strbuf_ncat(&logbuf, s, p - s);
_log_finish(level); _log_finish(level);
} }
} }
void logMessage(int level, const char *file, unsigned int line, const char *function, const char *fmt, ...) void logMessage(int level, struct __sourceloc where, const char *fmt, ...)
{ {
va_list ap; va_list ap;
va_start(ap, fmt); va_start(ap, fmt);
vlogMessage(level, file, line, function, fmt, ap); vlogMessage(level, where, fmt, ap);
va_end(ap); va_end(ap);
} }
void vlogMessage(int level, const char *file, unsigned int line, const char *function, const char *fmt, va_list ap) void vlogMessage(int level, struct __sourceloc where, const char *fmt, va_list ap)
{ {
if (_log_prepare(level, file, line, function)) { if (_log_prepare(level, where)) {
strbuf_vsprintf(&logbuf, fmt, ap); strbuf_vsprintf(&logbuf, fmt, ap);
_log_finish(level); _log_finish(level);
} }
} }
int logDump(int level, const char *file, unsigned int line, const char *function, char *name, unsigned char *addr, size_t len) int logDump(int level, struct __sourceloc where, char *name, unsigned char *addr, size_t len)
{ {
char buf[100]; char buf[100];
size_t i; size_t i;
if (name) if (name)
logMessage(level, file, line, function, "Dump of %s", name); logMessage(level, where, "Dump of %s", name);
for(i = 0; i < len; i += 16) { for(i = 0; i < len; i += 16) {
strbuf b = strbuf_local(buf, sizeof buf); strbuf b = strbuf_local(buf, sizeof buf);
strbuf_sprintf(b, " %04x :", i); strbuf_sprintf(b, " %04x :", i);
@ -279,7 +283,7 @@ int logDump(int level, const char *file, unsigned int line, const char *function
strbuf_puts(b, " "); strbuf_puts(b, " ");
for (j = 0; j < 16 && i + j < len; j++) for (j = 0; j < 16 && i + j < len; j++)
strbuf_sprintf(b, "%c", addr[i+j] >= ' ' && addr[i+j] < 0x7f ? addr[i+j] : '.'); strbuf_sprintf(b, "%c", addr[i+j] >= ' ' && addr[i+j] < 0x7f ? addr[i+j] : '.');
logMessage(level, file, line, function, "%s", strbuf_str(b)); logMessage(level, where, "%s", strbuf_str(b));
} }
return 0; return 0;
} }
@ -393,7 +397,7 @@ ssize_t get_self_executable_path(char *buf, size_t len)
return WHYF("Not implemented"); return WHYF("Not implemented");
} }
int log_backtrace(const char *file, unsigned int line, const char *function) int log_backtrace(struct __sourceloc where)
{ {
open_logging(); open_logging();
char execpath[160]; char execpath[160];
@ -445,7 +449,7 @@ int log_backtrace(const char *file, unsigned int line, const char *function)
} }
// parent // parent
close(stdout_fds[1]); close(stdout_fds[1]);
logMessage(LOG_LEVEL_DEBUG, file, line, function, "GDB BACKTRACE"); logMessage(LOG_LEVEL_DEBUG, where, "GDB BACKTRACE");
char buf[1024]; char buf[1024];
char *const bufe = buf + sizeof buf; char *const bufe = buf + sizeof buf;
char *linep = buf; char *linep = buf;
@ -457,14 +461,14 @@ int log_backtrace(const char *file, unsigned int line, const char *function)
for (; p < readp; ++p) for (; p < readp; ++p)
if (*p == '\n' || *p == '\0') { if (*p == '\n' || *p == '\0') {
*p = '\0'; *p = '\0';
logMessage(LOG_LEVEL_DEBUG, NULL, 0, NULL, "%s", linep); logMessage(LOG_LEVEL_DEBUG, __NOWHERE__, "%s", linep);
linep = p + 1; linep = p + 1;
} }
if (readp >= bufe && linep == buf) { if (readp >= bufe && linep == buf) {
// Line does not fit into buffer. // Line does not fit into buffer.
char t = bufe[-1]; char t = bufe[-1];
bufe[-1] = '\0'; bufe[-1] = '\0';
logMessage(LOG_LEVEL_DEBUG, NULL, 0, NULL, "%s", buf); logMessage(LOG_LEVEL_DEBUG, __NOWHERE__, "%s", buf);
buf[0] = t; buf[0] = t;
readp = buf + 1; readp = buf + 1;
} else if (readp + 120 >= bufe && linep != buf) { } else if (readp + 120 >= bufe && linep != buf) {
@ -480,7 +484,7 @@ int log_backtrace(const char *file, unsigned int line, const char *function)
WHY_perror("read"); WHY_perror("read");
if (readp > linep) { if (readp > linep) {
*readp = '\0'; *readp = '\0';
logMessage(LOG_LEVEL_DEBUG, NULL, 0, NULL, "%s", linep); logMessage(LOG_LEVEL_DEBUG, __NOWHERE__, "%s", linep);
} }
close(stdout_fds[0]); close(stdout_fds[0]);
int status = 0; int status = 0;
@ -488,7 +492,7 @@ int log_backtrace(const char *file, unsigned int line, const char *function)
WHY_perror("waitpid"); WHY_perror("waitpid");
strbuf b = strbuf_local(buf, sizeof buf); strbuf b = strbuf_local(buf, sizeof buf);
strbuf_append_exit_status(b, status); strbuf_append_exit_status(b, status);
logMessage(LOG_LEVEL_DEBUG, NULL, 0, NULL, "gdb %s", buf); logMessage(LOG_LEVEL_DEBUG, __NOWHERE__, "gdb %s", buf);
unlink(tempfile); unlink(tempfile);
return 0; return 0;
} }

36
log.h
View File

@ -63,29 +63,37 @@ extern unsigned int debug;
struct strbuf; struct strbuf;
struct __sourceloc {
const char *file;
unsigned int line;
const char *function;
};
void set_logging(FILE *f); void set_logging(FILE *f);
FILE *open_logging(); FILE *open_logging();
void close_logging(); void close_logging();
void logArgv(int level, const char *file, unsigned int line, const char *function, const char *label, int argc, const char *const *argv); void logArgv(int level, struct __sourceloc where, const char *label, int argc, const char *const *argv);
void logString(int level, const char *file, unsigned int line, const char *function, const char *str); void logString(int level, struct __sourceloc where, const char *str);
void logMessage(int level, const char *file, unsigned int line, const char *function, const char *fmt, ...); void logMessage(int level, struct __sourceloc where, const char *fmt, ...);
void vlogMessage(int level, const char *file, unsigned int line, const char *function, const char *fmt, va_list); void vlogMessage(int level, struct __sourceloc where, const char *fmt, va_list);
unsigned int debugFlagMask(const char *flagname); unsigned int debugFlagMask(const char *flagname);
int logDump(int level, const char *file, unsigned int line, const char *function, char *name, unsigned char *addr, size_t len); int logDump(int level, struct __sourceloc where, char *name, unsigned char *addr, size_t len);
char *toprint(char *dstStr, ssize_t dstBufSiz, const char *srcBuf, size_t srcBytes); char *toprint(char *dstStr, ssize_t dstBufSiz, const char *srcBuf, size_t srcBytes);
size_t toprint_strlen(const char *srcBuf, size_t srcBytes); size_t toprint_strlen(const char *srcBuf, size_t srcBytes);
ssize_t get_self_executable_path(char *buf, size_t len); ssize_t get_self_executable_path(char *buf, size_t len);
int log_backtrace(const char *file, unsigned int line, const char *function); int log_backtrace(struct __sourceloc where);
void set_log_implementation(void (*log_function)(int level, struct strbuf *buf)); void set_log_implementation(void (*log_function)(int level, struct strbuf *buf));
#define alloca_toprint(dstlen,buf,len) toprint((char *)alloca((dstlen) == -1 ? toprint_strlen((buf),(len)) + 1 : (dstlen)), (dstlen), (buf), (len)) #define alloca_toprint(dstlen,buf,len) toprint((char *)alloca((dstlen) == -1 ? toprint_strlen((buf),(len)) + 1 : (dstlen)), (dstlen), (buf), (len))
#define LOGF(L,F,...) (logMessage(L, __FILE__, __LINE__, __FUNCTION__, F, ##__VA_ARGS__)) #define __HERE__ ((struct __sourceloc){ .file = __FILE__, .line = __LINE__, .function = __FUNCTION__ })
#define LOGF_perror(L,F,...) logMessage_perror(L, __FILE__, __LINE__, __FUNCTION__, F, ##__VA_ARGS__) #define __NOWHERE__ ((struct __sourceloc){ .file = NULL, .line = 0, .function = NULL })
#define LOGF(L,F,...) (logMessage(L, __HERE__, F, ##__VA_ARGS__))
#define LOGF_perror(L,F,...) logMessage_perror(L, __HERE__, F, ##__VA_ARGS__)
#define LOG_perror(L,X) LOGF_perror(L, "%s", (X)) #define LOG_perror(L,X) LOGF_perror(L, "%s", (X))
#define logMessage_perror(L,file,line,func,F,...) \ #define logMessage_perror(L,where,F,...) (logMessage(L, where, F ": %s [errno=%d]", ##__VA_ARGS__, strerror(errno), errno))
(logMessage(L, file, line, func, F ": %s [errno=%d]", ##__VA_ARGS__, strerror(errno), errno))
#define FATALF(F,...) do { LOGF(LOG_LEVEL_FATAL, F, ##__VA_ARGS__); exit(-1); } while (1) #define FATALF(F,...) do { LOGF(LOG_LEVEL_FATAL, F, ##__VA_ARGS__); exit(-1); } while (1)
#define FATAL(X) FATALF("%s", (X)) #define FATAL(X) FATALF("%s", (X))
@ -102,7 +110,7 @@ void set_log_implementation(void (*log_function)(int level, struct strbuf *buf))
#define WARNF(F,...) LOGF(LOG_LEVEL_WARN, F, ##__VA_ARGS__) #define WARNF(F,...) LOGF(LOG_LEVEL_WARN, F, ##__VA_ARGS__)
#define WARN(X) WARNF("%s", (X)) #define WARN(X) WARNF("%s", (X))
#define WARN_perror(X) WARNF("%s: %s [errno=%d]", (X), strerror(errno), errno) #define WARN_perror(X) WARNF("%s: %s [errno=%d]", (X), strerror(errno), errno)
#define WHY_argv(X,ARGC,ARGV) logArgv(LOG_LEVEL_ERROR, __FILE__, __LINE__, __FUNCTION__, (X), (ARGC), (ARGV)) #define WHY_argv(X,ARGC,ARGV) logArgv(LOG_LEVEL_ERROR, __HERE__, (X), (ARGC), (ARGV))
#define INFOF(F,...) LOGF(LOG_LEVEL_INFO, F, ##__VA_ARGS__) #define INFOF(F,...) LOGF(LOG_LEVEL_INFO, F, ##__VA_ARGS__)
#define INFO(X) INFOF("%s", (X)) #define INFO(X) INFOF("%s", (X))
@ -112,10 +120,10 @@ void set_log_implementation(void (*log_function)(int level, struct strbuf *buf))
#define DEBUGF_perror(F,...) DEBUGF(F ": %s [errno=%d]", ##__VA_ARGS__, strerror(errno), errno) #define DEBUGF_perror(F,...) DEBUGF(F ": %s [errno=%d]", ##__VA_ARGS__, strerror(errno), errno)
#define DEBUG_perror(X) DEBUGF("%s: %s [errno=%d]", (X), strerror(errno), errno) #define DEBUG_perror(X) DEBUGF("%s: %s [errno=%d]", (X), strerror(errno), errno)
#define D DEBUG("D") #define D DEBUG("D")
#define DEBUG_argv(X,ARGC,ARGV) logArgv(LOG_LEVEL_DEBUG, __FILE__, __LINE__, __FUNCTION__, (X), (ARGC), (ARGV)) #define DEBUG_argv(X,ARGC,ARGV) logArgv(LOG_LEVEL_DEBUG, __HERE__, (X), (ARGC), (ARGV))
#define dump(X,A,N) logDump(LOG_LEVEL_DEBUG, __FILE__, __LINE__, __FUNCTION__, (X), (A), (N)) #define dump(X,A,N) logDump(LOG_LEVEL_DEBUG, __HERE__, (X), (A), (N))
#define BACKTRACE log_backtrace(__FILE__, __LINE__, __FUNCTION__) #define BACKTRACE log_backtrace(__HERE__)
#endif // __SERVALD_LOG_H #endif // __SERVALD_LOG_H

45
net.c
View File

@ -17,37 +17,40 @@ along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/ */
#include "serval.h" #include <unistd.h>
#include <errno.h>
#include <fcntl.h>
#include "net.h"
int _set_nonblock(int fd, const char *file, unsigned int line, const char *function) int _set_nonblock(int fd, struct __sourceloc where)
{ {
int flags; int flags;
if ((flags = fcntl(fd, F_GETFL, NULL)) == -1) { if ((flags = fcntl(fd, F_GETFL, NULL)) == -1) {
logMessage_perror(LOG_LEVEL_ERROR, file, line, function, "set_nonblock: fcntl(%d,F_GETFL,NULL)", fd); logMessage_perror(LOG_LEVEL_ERROR, where, "set_nonblock: fcntl(%d,F_GETFL,NULL)", fd);
return -1; return -1;
} }
if (fcntl(fd, F_SETFL, flags | O_NONBLOCK) == -1) { if (fcntl(fd, F_SETFL, flags | O_NONBLOCK) == -1) {
logMessage_perror(LOG_LEVEL_ERROR, file, line, function, "set_nonblock: fcntl(%d,F_SETFL,0x%x|O_NONBLOCK)", fd, flags); logMessage_perror(LOG_LEVEL_ERROR, where, "set_nonblock: fcntl(%d,F_SETFL,0x%x|O_NONBLOCK)", fd, flags);
return -1; return -1;
} }
return 0; return 0;
} }
int _set_block(int fd, const char *file, unsigned int line, const char *function) int _set_block(int fd, struct __sourceloc where)
{ {
int flags; int flags;
if ((flags = fcntl(fd, F_GETFL, NULL)) == -1) { if ((flags = fcntl(fd, F_GETFL, NULL)) == -1) {
logMessage_perror(LOG_LEVEL_ERROR, file, line, function, "set_block: fcntl(%d,F_GETFL,NULL)", fd); logMessage_perror(LOG_LEVEL_ERROR, where, "set_block: fcntl(%d,F_GETFL,NULL)", fd);
return -1; return -1;
} }
if (fcntl(fd, F_SETFL, flags & ~O_NONBLOCK) == -1) { if (fcntl(fd, F_SETFL, flags & ~O_NONBLOCK) == -1) {
logMessage_perror(LOG_LEVEL_ERROR, file, line, function, "set_block: fcntl(%d,F_SETFL,0x%x&~O_NONBLOCK)", fd, flags); logMessage_perror(LOG_LEVEL_ERROR, where, "set_block: fcntl(%d,F_SETFL,0x%x&~O_NONBLOCK)", fd, flags);
return -1; return -1;
} }
return 0; return 0;
} }
ssize_t _read_nonblock(int fd, void *buf, size_t len, const char *file, unsigned int line, const char *function) ssize_t _read_nonblock(int fd, void *buf, size_t len, struct __sourceloc where)
{ {
ssize_t nread = read(fd, buf, len); ssize_t nread = read(fd, buf, len);
if (nread == -1) { if (nread == -1) {
@ -59,30 +62,30 @@ ssize_t _read_nonblock(int fd, void *buf, size_t len, const char *file, unsigned
#endif #endif
return 0; return 0;
} }
logMessage_perror(LOG_LEVEL_ERROR, file, line, function, "read_nonblock: read(%d,%p,%lu)", logMessage_perror(LOG_LEVEL_ERROR, where, "read_nonblock: read(%d,%p,%lu)",
fd, buf, (unsigned long)len); fd, buf, (unsigned long)len);
return -1; return -1;
} }
return nread; return nread;
} }
ssize_t _write_all(int fd, const void *buf, size_t len, const char *file, unsigned int line, const char *function) ssize_t _write_all(int fd, const void *buf, size_t len, struct __sourceloc where)
{ {
ssize_t written = write(fd, buf, len); ssize_t written = write(fd, buf, len);
if (written == -1) { if (written == -1) {
logMessage_perror(LOG_LEVEL_ERROR, file, line, function, "write_all: write(%d,%p %s,%lu)", logMessage_perror(LOG_LEVEL_ERROR, where, "write_all: write(%d,%p %s,%lu)",
fd, buf, alloca_toprint(30, buf, len), (unsigned long)len); fd, buf, alloca_toprint(30, buf, len), (unsigned long)len);
return -1; return -1;
} }
if (written != len) { if (written != len) {
logMessage(LOG_LEVEL_ERROR, file, line, function, "write_all: write(%d,%p %s,%lu) returned %ld", logMessage(LOG_LEVEL_ERROR, where, "write_all: write(%d,%p %s,%lu) returned %ld",
fd, buf, alloca_toprint(30, buf, len), (unsigned long)len, (long)written); fd, buf, alloca_toprint(30, buf, len), (unsigned long)len, (long)written);
return -1; return -1;
} }
return written; return written;
} }
ssize_t _write_nonblock(int fd, const void *buf, size_t len, const char *file, unsigned int line, const char *function) ssize_t _write_nonblock(int fd, const void *buf, size_t len, struct __sourceloc where)
{ {
ssize_t written = write(fd, buf, len); ssize_t written = write(fd, buf, len);
if (written == -1) { if (written == -1) {
@ -94,30 +97,30 @@ ssize_t _write_nonblock(int fd, const void *buf, size_t len, const char *file, u
#endif #endif
return 0; return 0;
} }
logMessage_perror(LOG_LEVEL_ERROR, file, line, function, "write_nonblock: write(%d,%p %s,%lu)", logMessage_perror(LOG_LEVEL_ERROR, where, "write_nonblock: write(%d,%p %s,%lu)",
fd, buf, alloca_toprint(30, buf, len), (unsigned long)len); fd, buf, alloca_toprint(30, buf, len), (unsigned long)len);
return -1; return -1;
} }
return written; return written;
} }
ssize_t _write_all_nonblock(int fd, const void *buf, size_t len, const char *file, unsigned int line, const char *function) ssize_t _write_all_nonblock(int fd, const void *buf, size_t len, struct __sourceloc where)
{ {
ssize_t written = _write_nonblock(fd, buf, len, file, line, function); ssize_t written = _write_nonblock(fd, buf, len, where);
if (written != -1 && written != len) { if (written != -1 && written != len) {
logMessage(LOG_LEVEL_ERROR, file, line, function, "write_all_nonblock: write(%d,%p %s,%lu) returned %ld", logMessage(LOG_LEVEL_ERROR, where, "write_all_nonblock: write(%d,%p %s,%lu) returned %ld",
fd, buf, alloca_toprint(30, buf, len), (unsigned long)len, (long)written); fd, buf, alloca_toprint(30, buf, len), (unsigned long)len, (long)written);
return -1; return -1;
} }
return written; return written;
} }
ssize_t _write_str(int fd, const char *str, const char *file, unsigned int line, const char *function) ssize_t _write_str(int fd, const char *str, struct __sourceloc where)
{ {
return _write_all(fd, str, strlen(str), file, line, function); return _write_all(fd, str, strlen(str), where);
} }
ssize_t _write_str_nonblock(int fd, const char *str, const char *file, unsigned int line, const char *function) ssize_t _write_str_nonblock(int fd, const char *str, struct __sourceloc where)
{ {
return _write_all_nonblock(fd, str, strlen(str), file, line, function); return _write_all_nonblock(fd, str, strlen(str), where);
} }

43
net.h Normal file
View File

@ -0,0 +1,43 @@
/*
Copyright (C) 2012 Serval Project Inc.
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 2
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, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#ifndef __SERVALD_NET_H
#define __SERVALD_NET_H
#include <sys/types.h> // for size_t, ssize_t
#include "log.h" // for __HERE__ and struct __sourceloc
#define set_nonblock(fd) (_set_nonblock(fd, __HERE__))
#define set_block(fd) (_set_block(fd, __HERE__))
#define read_nonblock(fd,buf,len) (_read_nonblock(fd, buf, len, __HERE__))
#define write_all(fd,buf,len) (_write_all(fd, buf, len, __HERE__))
#define write_nonblock(fd,buf,len) (_write_nonblock(fd, buf, len, __HERE__))
#define write_all_nonblock(fd,buf,len) (_write_all_nonblock(fd, buf, len, __HERE__))
#define write_str(fd,str) (_write_str(fd, str, __HERE__))
#define write_str_nonblock(fd,str) (_write_str_nonblock(fd, str, __HERE__))
int _set_nonblock(int fd, struct __sourceloc where);
int _set_block(int fd, struct __sourceloc where);
ssize_t _read_nonblock(int fd, void *buf, size_t len, struct __sourceloc where);
ssize_t _write_all(int fd, const void *buf, size_t len, struct __sourceloc where);
ssize_t _write_nonblock(int fd, const void *buf, size_t len, struct __sourceloc where);
ssize_t _write_all_nonblock(int fd, const void *buf, size_t len, struct __sourceloc where);
ssize_t _write_str(int fd, const char *str, struct __sourceloc where);
ssize_t _write_str_nonblock(int fd, const char *str, struct __sourceloc where);
#endif // __SERVALD_NET_H

View File

@ -377,22 +377,22 @@ int ob_dump(overlay_buffer *b,char *desc)
#undef realloc #undef realloc
#define SDM_GUARD_AFTER 16384 #define SDM_GUARD_AFTER 16384
void *_serval_debug_malloc(unsigned int bytes,char *file,const char *func,int line) void *_serval_debug_malloc(unsigned int bytes, struct __sourceloc where)
{ {
void *r=malloc(bytes+SDM_GUARD_AFTER); void *r=malloc(bytes+SDM_GUARD_AFTER);
logMessage(LOG_LEVEL_DEBUG, file, line, func, "malloc(%d) -> %p", bytes, r); logMessage(LOG_LEVEL_DEBUG, where, "malloc(%d) -> %p", bytes, r);
return r; return r;
} }
void *_serval_debug_calloc(unsigned int bytes,unsigned int count,char *file,const char *func,int line) void *_serval_debug_calloc(unsigned int bytes, unsigned int count, struct __sourceloc where)
{ {
void *r=calloc((bytes*count)+SDM_GUARD_AFTER,1); void *r=calloc((bytes*count)+SDM_GUARD_AFTER,1);
logMessage(LOG_LEVEL_DEBUG, file, line, func, "calloc(%d,%d) -> %p", bytes, count, r); logMessage(LOG_LEVEL_DEBUG, where, "calloc(%d,%d) -> %p", bytes, count, r);
return r; return r;
} }
void _serval_debug_free(void *p,char *file,const char *func,int line) void _serval_debug_free(void *p, struct __sourceloc where)
{ {
free(p); free(p);
logMessage(LOG_LEVEL_DEBUG, file, line, func, "free(%p)", p); logMessage(LOG_LEVEL_DEBUG, where, "free(%p)", p);
} }

View File

@ -1155,7 +1155,7 @@ long long parse_quantity(char *q)
} }
} }
void logServalPacket(int level, const char *file, unsigned int line, const char *function, const char *message, const unsigned char *packet, size_t len) void logServalPacket(int level, struct __sourceloc where, const char *message, const unsigned char *packet, size_t len)
{ {
struct mallocbuf mb = STRUCT_MALLOCBUF_NULL; struct mallocbuf mb = STRUCT_MALLOCBUF_NULL;
if (serval_packetvisualise(XPRINTF_MALLOCBUF(&mb), message, packet, len) == -1) if (serval_packetvisualise(XPRINTF_MALLOCBUF(&mb), message, packet, len) == -1)
@ -1163,7 +1163,7 @@ void logServalPacket(int level, const char *file, unsigned int line, const char
else if (mb.buffer == NULL) else if (mb.buffer == NULL)
WHYF("serval_packetvisualise() output buffer missing, message=%s packet=%p len=%lu", alloca_toprint(-1, message, strlen(message)), packet, len); WHYF("serval_packetvisualise() output buffer missing, message=%s packet=%p len=%lu", alloca_toprint(-1, message, strlen(message)), packet, len);
else else
logString(level, file, line, function, mb.buffer); logString(level, where, mb.buffer);
if (mb.buffer) if (mb.buffer)
free(mb.buffer); free(mb.buffer);
} }

View File

@ -179,11 +179,10 @@ int rhizome_manifest_set_ll(rhizome_manifest *m,char *var,long long value);
int rhizome_manifest_set(rhizome_manifest *m, const char *var, const char *value); int rhizome_manifest_set(rhizome_manifest *m, const char *var, const char *value);
int rhizome_manifest_del(rhizome_manifest *m, const char *var); int rhizome_manifest_del(rhizome_manifest *m, const char *var);
long long rhizome_file_size(char *filename); long long rhizome_file_size(char *filename);
void _rhizome_manifest_free(const char *sourcefile,const char *funcname,int line, void _rhizome_manifest_free(struct __sourceloc where, rhizome_manifest *m);
rhizome_manifest *m); #define rhizome_manifest_free(m) _rhizome_manifest_free(__HERE__,m)
#define rhizome_manifest_free(m) _rhizome_manifest_free(__FILE__,__FUNCTION__,__LINE__,m) rhizome_manifest *_rhizome_new_manifest(struct __sourceloc where);
rhizome_manifest *_rhizome_new_manifest(const char *file,const char *func,int line); #define rhizome_new_manifest() _rhizome_new_manifest(__HERE__)
#define rhizome_new_manifest() _rhizome_new_manifest(__FILE__,__FUNCTION__,__LINE__)
int rhizome_manifest_pack_variables(rhizome_manifest *m); int rhizome_manifest_pack_variables(rhizome_manifest *m);
int rhizome_store_bundle(rhizome_manifest *m); int rhizome_store_bundle(rhizome_manifest *m);
int rhizome_manifest_add_group(rhizome_manifest *m,char *groupid); int rhizome_manifest_add_group(rhizome_manifest *m,char *groupid);

View File

@ -429,35 +429,27 @@ int rhizome_manifest_set_ll(rhizome_manifest *m,char *var,long long value)
rhizome_manifest manifests[MAX_RHIZOME_MANIFESTS]; rhizome_manifest manifests[MAX_RHIZOME_MANIFESTS];
char manifest_free[MAX_RHIZOME_MANIFESTS]; char manifest_free[MAX_RHIZOME_MANIFESTS];
int manifest_first_free=-1; int manifest_first_free=-1;
const char *manifest_alloc_sourcefiles[MAX_RHIZOME_MANIFESTS]; struct __sourceloc manifest_alloc_where[MAX_RHIZOME_MANIFESTS];
const char *manifest_alloc_functions[MAX_RHIZOME_MANIFESTS]; struct __sourceloc manifest_free_where[MAX_RHIZOME_MANIFESTS];
int manifest_alloc_lines[MAX_RHIZOME_MANIFESTS];
const char *manifest_free_sourcefiles[MAX_RHIZOME_MANIFESTS];
const char *manifest_free_functions[MAX_RHIZOME_MANIFESTS];
int manifest_free_lines[MAX_RHIZOME_MANIFESTS];
static void _log_manifest_trace(const char *filename, const char *funcname, int line, const char *operation) static void _log_manifest_trace(struct __sourceloc where, const char *operation)
{ {
int count_free = 0; int count_free = 0;
int i; int i;
for (i = 0; i != MAX_RHIZOME_MANIFESTS; ++i) for (i = 0; i != MAX_RHIZOME_MANIFESTS; ++i)
if (manifest_free[i]) if (manifest_free[i])
++count_free; ++count_free;
logMessage(LOG_LEVEL_DEBUG, filename, line, funcname, "%s(): count_free = %d", operation, count_free); logMessage(LOG_LEVEL_DEBUG, where, "%s(): count_free = %d", operation, count_free);
} }
rhizome_manifest *_rhizome_new_manifest(const char *filename, const char *funcname, int line) rhizome_manifest *_rhizome_new_manifest(struct __sourceloc where)
{ {
if (manifest_first_free<0) { if (manifest_first_free<0) {
/* Setup structures */ /* Setup structures */
int i; int i;
for(i=0;i<MAX_RHIZOME_MANIFESTS;i++) { for(i=0;i<MAX_RHIZOME_MANIFESTS;i++) {
manifest_alloc_sourcefiles[i]="<never allocated>"; manifest_alloc_where[i]=__NOWHERE__;
manifest_alloc_functions[i]="<never allocated>"; manifest_free_where[i]=__NOWHERE__;
manifest_alloc_lines[i]=-1;
manifest_free_sourcefiles[i]="<never freed>";
manifest_free_functions[i]="<never freed>";
manifest_free_lines[i]=-1;
manifest_free[i]=1; manifest_free[i]=1;
} }
manifest_first_free=0; manifest_first_free=0;
@ -467,14 +459,14 @@ rhizome_manifest *_rhizome_new_manifest(const char *filename, const char *funcna
if (manifest_first_free>=MAX_RHIZOME_MANIFESTS) if (manifest_first_free>=MAX_RHIZOME_MANIFESTS)
{ {
int i; int i;
logMessage(LOG_LEVEL_ERROR, filename, line, funcname, "%s(): no free manifest records, this probably indicates a memory leak", __FUNCTION__); logMessage(LOG_LEVEL_ERROR, where, "%s(): no free manifest records, this probably indicates a memory leak", __FUNCTION__);
WHYF(" Slot# | Last allocated by"); WHYF(" Slot# | Last allocated by");
for(i=0;i<MAX_RHIZOME_MANIFESTS;i++) { for(i=0;i<MAX_RHIZOME_MANIFESTS;i++) {
WHYF(" %-5d | %s:%d in %s()", WHYF(" %-5d | %s:%d in %s()",
i, i,
manifest_alloc_sourcefiles[i], manifest_alloc_where[i].file,
manifest_alloc_lines[i], manifest_alloc_where[i].line,
manifest_alloc_functions[i] manifest_alloc_where[i].function
); );
} }
return NULL; return NULL;
@ -486,32 +478,27 @@ rhizome_manifest *_rhizome_new_manifest(const char *filename, const char *funcna
/* Indicate where manifest was allocated, and that it is no longer /* Indicate where manifest was allocated, and that it is no longer
free. */ free. */
manifest_alloc_sourcefiles[manifest_first_free]=filename; manifest_alloc_where[manifest_first_free]=where;
manifest_alloc_lines[manifest_first_free]=line;
manifest_alloc_functions[manifest_first_free]=funcname;
manifest_free[manifest_first_free]=0; manifest_free[manifest_first_free]=0;
manifest_free_sourcefiles[manifest_first_free]="<not freed>"; manifest_free_where[manifest_first_free]=__NOWHERE__;
manifest_free_functions[manifest_first_free]="<not freed>";
manifest_free_lines[manifest_first_free]=-1;
/* Work out where next free manifest record lives */ /* Work out where next free manifest record lives */
for (; manifest_first_free < MAX_RHIZOME_MANIFESTS && !manifest_free[manifest_first_free]; ++manifest_first_free) for (; manifest_first_free < MAX_RHIZOME_MANIFESTS && !manifest_free[manifest_first_free]; ++manifest_first_free)
; ;
if (debug & DEBUG_MANIFESTS) _log_manifest_trace(filename, funcname, line, __FUNCTION__); if (debug & DEBUG_MANIFESTS) _log_manifest_trace(where, __FUNCTION__);
return m; return m;
} }
void _rhizome_manifest_free(const char *sourcefile,const char *funcname,int line, void _rhizome_manifest_free(struct __sourceloc where, rhizome_manifest *m)
rhizome_manifest *m)
{ {
if (!m) return; if (!m) return;
int i; int i;
int mid=m->manifest_record_number; int mid=m->manifest_record_number;
if (m!=&manifests[mid]) { if (m!=&manifests[mid]) {
logMessage(LOG_LEVEL_ERROR, sourcefile, line, funcname, logMessage(LOG_LEVEL_ERROR, where,
"%s(): asked to free manifest %p, which claims to be manifest slot #%d (%p), but isn't", "%s(): asked to free manifest %p, which claims to be manifest slot #%d (%p), but isn't",
__FUNCTION__, m, mid, &manifests[mid] __FUNCTION__, m, mid, &manifests[mid]
); );
@ -519,12 +506,12 @@ void _rhizome_manifest_free(const char *sourcefile,const char *funcname,int line
} }
if (manifest_free[mid]) { if (manifest_free[mid]) {
logMessage(LOG_LEVEL_ERROR, sourcefile, line, funcname, logMessage(LOG_LEVEL_ERROR, where,
"%s(): asked to free manifest slot #%d (%p), which was already freed at %s:%d:%s()", "%s(): asked to free manifest slot #%d (%p), which was already freed at %s:%d:%s()",
__FUNCTION__, mid, m, __FUNCTION__, mid, m,
manifest_free_sourcefiles[mid], manifest_free_where[mid].file,
manifest_free_lines[mid], manifest_free_where[mid].line,
manifest_free_functions[mid] manifest_free_where[mid].function
); );
exit(-1); exit(-1);
} }
@ -543,12 +530,10 @@ void _rhizome_manifest_free(const char *sourcefile,const char *funcname,int line
m->dataFileName=NULL; m->dataFileName=NULL;
manifest_free[mid]=1; manifest_free[mid]=1;
manifest_free_sourcefiles[mid]=sourcefile; manifest_free_where[mid]=where;
manifest_free_functions[mid]=funcname;
manifest_free_lines[mid]=line;
if (mid<manifest_first_free) manifest_first_free=mid; if (mid<manifest_first_free) manifest_first_free=mid;
if (debug & DEBUG_MANIFESTS) _log_manifest_trace(sourcefile, funcname, line, __FUNCTION__); if (debug & DEBUG_MANIFESTS) _log_manifest_trace(where, __FUNCTION__);
return; return;
} }

View File

@ -111,6 +111,7 @@ struct in_addr {
#include "constants.h" #include "constants.h"
#include "xprintf.h" #include "xprintf.h"
#include "log.h" #include "log.h"
#include "net.h"
#include "conf.h" #include "conf.h"
/* All wall clock times in the Serval daemon are represented in milliseconds /* All wall clock times in the Serval daemon are represented in milliseconds
@ -681,9 +682,9 @@ int overlay_interface_init_socket(int i);
time_ms_t overlay_time_until_next_tick(); time_ms_t overlay_time_until_next_tick();
int overlay_rx_messages(); int overlay_rx_messages();
void logServalPacket(int level, const char *file, unsigned int line, const char *function, const char *message, const unsigned char *packet, size_t len); void logServalPacket(int level, struct __sourceloc where, const char *message, const unsigned char *packet, size_t len);
#define DEBUG_packet_visualise(M,P,N) logServalPacket(LOG_LEVEL_DEBUG, __FILE__, __LINE__, __FUNCTION__, (M), (P), (N)) #define DEBUG_packet_visualise(M,P,N) logServalPacket(LOG_LEVEL_DEBUG, __HERE__, (M), (P), (N))
int overlay_add_selfannouncement(); int overlay_add_selfannouncement();
int overlay_frame_package_fmt1(overlay_frame *p,overlay_buffer *b); int overlay_frame_package_fmt1(overlay_frame *p,overlay_buffer *b);
@ -1000,13 +1001,13 @@ int dump_payload(overlay_frame *p,char *message);
int urandombytes(unsigned char *x,unsigned long long xlen); int urandombytes(unsigned char *x,unsigned long long xlen);
#ifdef MALLOC_PARANOIA #ifdef MALLOC_PARANOIA
#define malloc(X) _serval_debug_malloc(X,__FILE__,__FUNCTION__,__LINE__) #define malloc(X) _serval_debug_malloc(X,__HERE__)
#define calloc(X,Y) _serval_debug_calloc(X,Y,__FILE__,__FUNCTION__,__LINE__) #define calloc(X,Y) _serval_debug_calloc(X,Y,__HERE__)
#define free(X) _serval_debug_free(X,__FILE__,__FUNCTION__,__LINE__) #define free(X) _serval_debug_free(X,__HERE__)
void *_serval_debug_malloc(unsigned int bytes,char *file,const char *func,int line); void *_serval_debug_malloc(unsigned int bytes, struct __sourceloc where);
void *_serval_debug_calloc(unsigned int bytes,unsigned int count,char *file,const char *func,int line); void *_serval_debug_calloc(unsigned int bytes, unsigned int count, struct __sourceloc where);
void _serval_debug_free(void *p,char *file,const char *func,int line); void _serval_debug_free(void *p, struct __sourceloc where);
#endif #endif
@ -1118,24 +1119,6 @@ extern int sigIoFlag;
void sigPipeHandler(int signal); void sigPipeHandler(int signal);
void sigIoHandler(int signal); void sigIoHandler(int signal);
#define set_nonblock(fd) (_set_nonblock(fd, __FILE__, __LINE__, __FUNCTION__))
#define set_block(fd) (_set_block(fd, __FILE__, __LINE__, __FUNCTION__))
#define read_nonblock(fd,buf,len) (_read_nonblock(fd, buf, len, __FILE__, __LINE__, __FUNCTION__))
#define write_all(fd,buf,len) (_write_all(fd, buf, len, __FILE__, __LINE__, __FUNCTION__))
#define write_nonblock(fd,buf,len) (_write_nonblock(fd, buf, len, __FILE__, __LINE__, __FUNCTION__))
#define write_all_nonblock(fd,buf,len) (_write_all_nonblock(fd, buf, len, __FILE__, __LINE__, __FUNCTION__))
#define write_str(fd,str) (_write_str(fd, str, __FILE__, __LINE__, __FUNCTION__))
#define write_str_nonblock(fd,str) (_write_str_nonblock(fd, str, __FILE__, __LINE__, __FUNCTION__))
int _set_nonblock(int fd, const char *file, unsigned int line, const char *function);
int _set_block(int fd, const char *file, unsigned int line, const char *function);
ssize_t _read_nonblock(int fd, void *buf, size_t len, const char *file, unsigned int line, const char *function);
ssize_t _write_all(int fd, const void *buf, size_t len, const char *file, unsigned int line, const char *function);
ssize_t _write_nonblock(int fd, const void *buf, size_t len, const char *file, unsigned int line, const char *function);
ssize_t _write_all_nonblock(int fd, const void *buf, size_t len, const char *file, unsigned int line, const char *function);
ssize_t _write_str(int fd, const char *str, const char *file, unsigned int line, const char *function);
ssize_t _write_str_nonblock(int fd, const char *str, const char *file, unsigned int line, const char *function);
int rhizome_http_server_start(); int rhizome_http_server_start();
int overlay_mdp_setup_sockets(); int overlay_mdp_setup_sockets();

View File

@ -443,9 +443,4 @@ __STRBUF_INLINE int strbuf_overrun(const_strbuf sb) {
return sb->end && sb->current > sb->end; return sb->end && sb->current > sb->end;
} }
#define write_str(fd,str) (_write_str(fd, str, __FILE__, __LINE__, __FUNCTION__))
ssize_t _write_str(int fd, const char *str, const char *file, unsigned int line, const char *function);
ssize_t _write_str_nonblock(int fd, const char *str, const char *file, unsigned int line, const char *function);
#endif // __STRBUF_H__ #endif // __STRBUF_H__