summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNick Mathewson <nickm@torproject.org>2007-12-06 18:12:56 +0000
committerNick Mathewson <nickm@torproject.org>2007-12-06 18:12:56 +0000
commit3206bbca46f55e4eb4570566a9566dd10c182c6d (patch)
tree0ce70ceefbc043ba9bb86db687c51e20cd53315c
parent1e435af17e658c973f644c9c751ab58296413fcb (diff)
downloadlibevent-3206bbca46f55e4eb4570566a9566dd10c182c6d.tar.gz
r15171@tombo: nickm | 2007-12-06 12:47:47 -0500
Use GCC attributes (where available) to verify printf type-correctness. Fix some bugs this turned up. svn:r573
-rw-r--r--ChangeLog2
-rw-r--r--event.c2
-rw-r--r--event.h6
-rw-r--r--http.c39
-rw-r--r--log.h20
-rw-r--r--signal.c2
6 files changed, 44 insertions, 27 deletions
diff --git a/ChangeLog b/ChangeLog
index 49e584f2..6724efba 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -18,6 +18,8 @@ Changes in current version:
o small improvements to evhttp documentation
o always generate Date and Content-Length headers for HTTP/1.1 replies
o set the correct event base for HTTP close events
+ o When building with GCC, use the "format" attribute to verify type correctness of calls to printf-like functions.
+
Changes in 1.4.0:
o allow \r or \n individually to separate HTTP headers instead of the standard "\r\n"; from Charles Kerr.
diff --git a/event.c b/event.c
index d0187f34..be8ffd34 100644
--- a/event.c
+++ b/event.c
@@ -173,7 +173,7 @@ event_base_new(void)
struct event_base *base;
if ((base = event_calloc(1, sizeof(struct event_base))) == NULL)
- event_err(1, "%s: calloc");
+ event_err(1, "%s: calloc", __func__);
event_sigcb = NULL;
event_gotsig = 0;
diff --git a/event.h b/event.h
index 4a6f758b..d6fa3ee9 100644
--- a/event.h
+++ b/event.h
@@ -1015,7 +1015,11 @@ int evbuffer_add_buffer(struct evbuffer *, struct evbuffer *);
@param ... arguments that will be passed to printf(3)
@return 0 if successful, or -1 if an error occurred
*/
-int evbuffer_add_printf(struct evbuffer *, const char *fmt, ...);
+int evbuffer_add_printf(struct evbuffer *, const char *fmt, ...)
+#ifdef __GNUC__
+ __attribute__((format(printf, 2, 3)))
+#endif
+;
/**
diff --git a/http.c b/http.c
index 77bfb8f1..d9c53beb 100644
--- a/http.c
+++ b/http.c
@@ -1649,12 +1649,12 @@ evhttp_send_done(struct evhttp_connection *evcon, void *arg)
void
evhttp_send_error(struct evhttp_request *req, int error, const char *reason)
{
- const char *fmt = "<HTML><HEAD>\n"
- "<TITLE>%d %s</TITLE>\n"
- "</HEAD><BODY>\n"
- "<H1>Method Not Implemented</H1>\n"
- "Invalid method in request<P>\n"
- "</BODY></HTML>\n";
+#define ERR_FORMAT "<HTML><HEAD>\n" \
+ "<TITLE>%d %s</TITLE>\n" \
+ "</HEAD><BODY>\n" \
+ "<H1>Method Not Implemented</H1>\n" \
+ "Invalid method in request<P>\n" \
+ "</BODY></HTML>\n"
struct evbuffer *buf = evbuffer_new();
@@ -1663,11 +1663,12 @@ evhttp_send_error(struct evhttp_request *req, int error, const char *reason)
evhttp_response_code(req, error, reason);
- evbuffer_add_printf(buf, fmt, error, reason);
+ evbuffer_add_printf(buf, ERR_FORMAT, error, reason);
evhttp_send_page(req, buf);
evbuffer_free(buf);
+#undef ERR_FORMAT
}
/* Requires that headers and response code are already set up */
@@ -1722,7 +1723,7 @@ evhttp_send_reply_chunk(struct evhttp_request *req, struct evbuffer *databuf)
{
if (req->chunked) {
evbuffer_add_printf(req->evcon->output_buffer, "%x\r\n",
- EVBUFFER_LENGTH(databuf));
+ (unsigned)EVBUFFER_LENGTH(databuf));
}
evbuffer_add_buffer(req->evcon->output_buffer, databuf);
evhttp_write_buffer(req->evcon, NULL, NULL);
@@ -1829,8 +1830,9 @@ evhttp_decode_uri(const char *uri)
ret = event_malloc(strlen(uri) + 1);
if (ret == NULL)
- event_err(1, "%s: malloc(%d)", __func__, strlen(uri) + 1);
-
+ event_err(1, "%s: malloc(%lu)", __func__,
+ (unsigned long)(strlen(uri) + 1));
+
for (i = j = 0; uri[i] != '\0'; i++) {
c = uri[i];
if (c == '?') {
@@ -1947,25 +1949,26 @@ evhttp_handle_request(struct evhttp_request *req, void *arg)
return;
} else {
/* We need to send a 404 here */
- const char *fmt = "<html><head>"
- "<title>404 Not Found</title>"
- "</head><body>"
- "<h1>Not Found</h1>"
- "<p>The requested URL %s was not found on this server.</p>"
- "</body></html>\n";
+#define ERR_FORMAT "<html><head>" \
+ "<title>404 Not Found</title>" \
+ "</head><body>" \
+ "<h1>Not Found</h1>" \
+ "<p>The requested URL %s was not found on this server.</p>"\
+ "</body></html>\n"
char *escaped_html = evhttp_htmlescape(req->uri);
struct evbuffer *buf = evbuffer_new();
evhttp_response_code(req, HTTP_NOTFOUND, "Not Found");
- evbuffer_add_printf(buf, fmt, escaped_html);
+ evbuffer_add_printf(buf, ERR_FORMAT, escaped_html);
event_free(escaped_html);
-
+
evhttp_send_page(req, buf);
evbuffer_free(buf);
+#undef ERR_FORMAT
}
}
diff --git a/log.h b/log.h
index 1f843cf9..7bc6632b 100644
--- a/log.h
+++ b/log.h
@@ -27,12 +27,18 @@
#ifndef _LOG_H_
#define _LOG_H_
-void event_err(int eval, const char *fmt, ...);
-void event_warn(const char *fmt, ...);
-void event_errx(int eval, const char *fmt, ...);
-void event_warnx(const char *fmt, ...);
-void event_msgx(const char *fmt, ...);
-void _event_debugx(const char *fmt, ...);
+#ifdef __GNUC__
+#define EV_CHECK_FMT(a,b) __attribute__((format(printf, a, b)))
+#else
+#define EV_CHECK_FMT(a,b)
+#endif
+
+void event_err(int eval, const char *fmt, ...) EV_CHECK_FMT(2,3);
+void event_warn(const char *fmt, ...) EV_CHECK_FMT(1,2);
+void event_errx(int eval, const char *fmt, ...) EV_CHECK_FMT(2,3);
+void event_warnx(const char *fmt, ...) EV_CHECK_FMT(1,2);
+void event_msgx(const char *fmt, ...) EV_CHECK_FMT(1,2);
+void _event_debugx(const char *fmt, ...) EV_CHECK_FMT(1,2);
#ifdef USE_DEBUG
#define event_debug(x) _event_debugx x
@@ -40,4 +46,6 @@ void _event_debugx(const char *fmt, ...);
#define event_debug(x) do {;} while (0)
#endif
+#undef EV_CHECK_FMT
+
#endif
diff --git a/signal.c b/signal.c
index a160d1b3..fc1f7e3a 100644
--- a/signal.c
+++ b/signal.c
@@ -252,7 +252,7 @@ evsignal_handler(int sig)
if(evsignal_base == NULL) {
event_warn(
- "%s: received signal %s, but have no base configured",
+ "%s: received signal %d, but have no base configured",
__func__, sig);
return;
}