changeset 1372:229e02867307

Fix format-string bugs by adding __attribute__((__format__)) in all applicable places and fixing all warnings my gcc produced. Among other things, this should fix several segfaults (including one I just ran into).
author Frits van Bommel <fvbommel wxs.nl>
date Sun, 17 May 2009 00:15:25 +0200
parents 967d28b7febe
children 551b01341728
files dmd/attrib.c dmd/dsymbol.h dmd/expression.c dmd/expression.h dmd/html.h dmd/lexer.h dmd/mars.h dmd/mtype.h dmd/root/root.h dmd/statement.h gen/arrays.cpp gen/logger.h gen/main.cpp gen/toir.cpp ir/irdsymbol.cpp
diffstat 15 files changed, 56 insertions(+), 31 deletions(-) [+]
line wrap: on
line diff
--- a/dmd/attrib.c	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/attrib.c	Sun May 17 00:15:25 2009 +0200
@@ -983,7 +983,7 @@
         }
         else
         {
-            error("command '%s' invalid");
+            error("command '%s' invalid", expr->toChars());
             fatal();
         }
     }
--- a/dmd/dsymbol.h	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/dsymbol.h	Sun May 17 00:15:25 2009 +0200
@@ -122,8 +122,8 @@
     char *locToChars();
     int equals(Object *o);
     int isAnonymous();
-    void error(Loc loc, const char *format, ...);
-    void error(const char *format, ...);
+    void error(Loc loc, const char *format, ...) IS_PRINTF(3);
+    void error(const char *format, ...) IS_PRINTF(2);
     void checkDeprecated(Loc loc, Scope *sc);
     Module *getModule();        // module where declared
     Module *getCompilationModule(); // possibly different for templates
--- a/dmd/expression.c	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/expression.c	Sun May 17 00:15:25 2009 +0200
@@ -1466,7 +1466,7 @@
 	    case Tdchar:	// BUG: need to cast(dchar)
 		if ((uinteger_t)v > 0xFF)
 		{
-		     buf->printf("'\\U%08x'", v);
+		     buf->printf("'\\U%08x'", (unsigned)v);
 		     break;
 		}
 	    case Tchar:
@@ -2934,7 +2934,7 @@
 void ArrayLiteralExp::toMangleBuffer(OutBuffer *buf)
 {
     size_t dim = elements ? elements->dim : 0;
-    buf->printf("A%u", dim);
+    buf->printf("A%zu", dim);
     for (size_t i = 0; i < dim; i++)
     {	Expression *e = (Expression *)elements->data[i];
 	e->toMangleBuffer(buf);
@@ -3068,7 +3068,7 @@
 void AssocArrayLiteralExp::toMangleBuffer(OutBuffer *buf)
 {
     size_t dim = keys->dim;
-    buf->printf("A%u", dim);
+    buf->printf("A%zu", dim);
     for (size_t i = 0; i < dim; i++)
     {	Expression *key = (Expression *)keys->data[i];
 	Expression *value = (Expression *)values->data[i];
@@ -3284,7 +3284,7 @@
 void StructLiteralExp::toMangleBuffer(OutBuffer *buf)
 {
     size_t dim = elements ? elements->dim : 0;
-    buf->printf("S%u", dim);
+    buf->printf("S%zu", dim);
     for (size_t i = 0; i < dim; i++)
     {	Expression *e = (Expression *)elements->data[i];
 	if (e)
--- a/dmd/expression.h	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/expression.h	Sun May 17 00:15:25 2009 +0200
@@ -98,8 +98,8 @@
     void print();
     char *toChars();
     virtual void dump(int indent);
-    void error(const char *format, ...);
-    void warning(const char *format, ...);
+    void error(const char *format, ...) IS_PRINTF(2);
+    void warning(const char *format, ...) IS_PRINTF(2);
     virtual void rvalue();
 
     static Expression *combine(Expression *e1, Expression *e2);
--- a/dmd/html.h	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/html.h	Sun May 17 00:15:25 2009 +0200
@@ -27,7 +27,7 @@
 
     Html(const char *sourcename, unsigned char *base, unsigned length);
 
-    void error(const char *format, ...);
+    void error(const char *format, ...) IS_PRINTF(2);
     void extractCode(OutBuffer *buf);
     void skipTag();
     void skipString();
--- a/dmd/lexer.h	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/lexer.h	Sun May 17 00:15:25 2009 +0200
@@ -292,8 +292,8 @@
     unsigned wchar(unsigned u);
     TOK number(Token *t);
     TOK inreal(Token *t);
-    void error(const char *format, ...);
-    void error(Loc loc, const char *format, ...);
+    void error(const char *format, ...) IS_PRINTF(2);
+    void error(Loc loc, const char *format, ...) IS_PRINTF(3);
     void pragma();
     unsigned decodeUTF();
     void getDocComment(Token *t, unsigned lineComment);
--- a/dmd/mars.h	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/mars.h	Sun May 17 00:15:25 2009 +0200
@@ -76,6 +76,14 @@
 #endif
 #endif
 
+#ifndef IS_PRINTF
+# ifdef __GNUC__
+#  define IS_PRINTF(FMTARG) __attribute((__format__ (__printf__, (FMTARG), (FMTARG)+1) ))
+# else
+#  define IS_PRINTF(FMTARG)
+# endif
+#endif
+
 #ifdef IN_GCC
 /* Changes for the GDC compiler by David Friedman */
 #endif
@@ -395,9 +403,9 @@
     MATCHexact		// exact match
 };
 
-void warning(Loc loc, const char *format, ...);
+void warning(Loc loc, const char *format, ...) IS_PRINTF(2);
 void vwarning(Loc loc, const char *format, va_list);
-void error(Loc loc, const char *format, ...);
+void error(Loc loc, const char *format, ...) IS_PRINTF(2);
 void verror(Loc loc, const char *format, va_list);
 void fatal();
 void err_nomem();
--- a/dmd/mtype.h	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/mtype.h	Sun May 17 00:15:25 2009 +0200
@@ -267,8 +267,8 @@
     Type *next;
     Type *nextOf() { return next; }
 
-    static void error(Loc loc, const char *format, ...);
-    static void warning(Loc loc, const char *format, ...);
+    static void error(Loc loc, const char *format, ...) IS_PRINTF(2);
+    static void warning(Loc loc, const char *format, ...) IS_PRINTF(2);
 
 #if IN_DMD
     // For backend
--- a/dmd/root/root.h	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/root/root.h	Sun May 17 00:15:25 2009 +0200
@@ -18,6 +18,14 @@
 #pragma once
 #endif
 
+#ifndef IS_PRINTF
+# ifdef __GNUC__
+#  define IS_PRINTF(FMTARG) __attribute((__format__ (__printf__, (FMTARG), (FMTARG)+1) ))
+# else
+#  define IS_PRINTF(FMTARG)
+# endif
+#endif
+
 typedef size_t hash_t;
 
 #include "dchar.h"
@@ -29,9 +37,9 @@
 
 int bstrcmp(unsigned char *s1, unsigned char *s2);
 char *bstr2str(unsigned char *b);
-void error(const char *format, ...);
+void error(const char *format, ...) IS_PRINTF(1);
 void error(const wchar_t *format, ...);
-void warning(const char *format, ...);
+void warning(const char *format, ...) IS_PRINTF(1);
 
 #ifndef TYPEDEFS
 #define TYPEDEFS
@@ -291,7 +299,7 @@
     void fill0(unsigned nbytes);
     void align(unsigned size);
     void vprintf(const char *format, va_list args);
-    void printf(const char *format, ...);
+    void printf(const char *format, ...) IS_PRINTF(2);
 #if M_UNICODE
     void vprintf(const unsigned short *format, va_list args);
     void printf(const unsigned short *format, ...);
--- a/dmd/statement.h	Sat May 16 23:44:27 2009 +0200
+++ b/dmd/statement.h	Sun May 17 00:15:25 2009 +0200
@@ -104,8 +104,8 @@
     void print();
     char *toChars();
 
-    void error(const char *format, ...);
-    void warning(const char *format, ...);
+    void error(const char *format, ...) IS_PRINTF(2);
+    void warning(const char *format, ...) IS_PRINTF(2);
     virtual void toCBuffer(OutBuffer *buf, HdrGenState *hgs);
     virtual TryCatchStatement *isTryCatchStatement() { return NULL; }
     virtual GotoStatement *isGotoStatement() { return NULL; }
--- a/gen/arrays.cpp	Sat May 16 23:44:27 2009 +0200
+++ b/gen/arrays.cpp	Sun May 17 00:15:25 2009 +0200
@@ -240,7 +240,7 @@
     // make sure the number of initializers is sane
     if (arrinit->index.dim > arrlen || arrinit->dim > arrlen)
     {
-        error(arrinit->loc, "too many initializers, %d, for array[%d]", arrinit->index.dim, arrlen);
+        error(arrinit->loc, "too many initializers, %u, for array[%zu]", arrinit->index.dim, arrlen);
         fatal();
     }
 
@@ -273,7 +273,7 @@
         // error check from dmd
         if (initvals[j] != NULL)
         {
-            error(arrinit->loc, "duplicate initialization for index %d", j);
+            error(arrinit->loc, "duplicate initialization for index %zu", j);
         }
 
         LLConstant* c = DtoConstInitializer(val->loc, elemty, val);
--- a/gen/logger.h	Sat May 16 23:44:27 2009 +0200
+++ b/gen/logger.h	Sun May 17 00:15:25 2009 +0200
@@ -3,6 +3,14 @@
 
 #include "llvm/Support/Streams.h"
 
+#ifndef IS_PRINTF
+# ifdef __GNUC__
+#  define IS_PRINTF(FMTARG) __attribute((__format__ (__printf__, (FMTARG), (FMTARG)+1) ))
+# else
+#  define IS_PRINTF(FMTARG)
+# endif
+#endif
+
 struct Loc;
 
 namespace Logger
@@ -10,13 +18,13 @@
     void indent();
     void undent();
     llvm::OStream cout();
-    void println(const char* fmt, ...);
-    void print(const char* fmt, ...);
+    void println(const char* fmt, ...) IS_PRINTF(1);
+    void print(const char* fmt, ...) IS_PRINTF(1);
     void enable();
     void disable();
     bool enabled();
 
-    void attention(Loc loc, const char* fmt, ...);
+    void attention(Loc loc, const char* fmt, ...) IS_PRINTF(2);
 
     struct LoggerScope
     {
--- a/gen/main.cpp	Sat May 16 23:44:27 2009 +0200
+++ b/gen/main.cpp	Sun May 17 00:15:25 2009 +0200
@@ -876,7 +876,7 @@
             delete stripMD;
         
             if(linker.LinkInModule(llvmModules[i], &errormsg))
-                error(errormsg.c_str());
+                error("%s", errormsg.c_str());
             delete llvmModules[i];
         }
         
--- a/gen/toir.cpp	Sat May 16 23:44:27 2009 +0200
+++ b/gen/toir.cpp	Sun May 17 00:15:25 2009 +0200
@@ -313,7 +313,8 @@
 
 LLConstant* RealExp::toConstElem(IRState* p)
 {
-    Logger::print("RealExp::toConstElem: %s @ %s | %LX\n", toChars(), type->toChars(), value);
+    Logger::print("RealExp::toConstElem: %s @ %s | %LX\n", toChars(), type->toChars(),
+        0xFFFFFFFFFFUL & *(long long unsigned*)&value);
     LOG_SCOPE;
     Type* t = type->toBasetype();
     return DtoConstFP(t, value);
@@ -2473,7 +2474,7 @@
         IF_LOG Logger::println("expr: %p", expr);
         if (expr)
         {
-            IF_LOG Logger::println("expr = %s", it.index, expr->toChars());
+            IF_LOG Logger::println("expr %zu = %s", it.index, expr->toChars());
             LLValue* v = DtoExprValue(vd->type, expr);
             initvalues.push_back(v);
         }
@@ -2606,7 +2607,7 @@
         Expression* ekey = (Expression*)keys->data[i];
         Expression* eval = (Expression*)values->data[i];
 
-        Logger::println("(%u) aa[%s] = %s", i, ekey->toChars(), eval->toChars());
+        Logger::println("(%zu) aa[%s] = %s", i, ekey->toChars(), eval->toChars());
 
         // index
         DValue* key = ekey->toElem(p);
--- a/ir/irdsymbol.cpp	Sat May 16 23:44:27 2009 +0200
+++ b/ir/irdsymbol.cpp	Sun May 17 00:15:25 2009 +0200
@@ -9,7 +9,7 @@
 
 void IrDsymbol::resetAll()
 {
-    Logger::println("resetting %u Dsymbols", list.size());
+    Logger::println("resetting %zu Dsymbols", list.size());
     std::set<IrDsymbol*>::iterator it;
     for(it = list.begin(); it != list.end(); ++it)
         (*it)->reset();