From 1f834b569c8a39f44882c2f2010a9f0ecffdaab1 Mon Sep 17 00:00:00 2001 From: Nathan Binkert Date: Wed, 7 Feb 2007 22:11:30 -0800 Subject: Get rid of the gross operator,()/variadic macro hack that made ccprintf and friends work, turn it into a normal function (though it still has a slightly strange implementation.) All instances of variadic macros are not yet removed, but I know how, and it will happen. One side effect of this new implementation is that a cprintf statement can now only have 16 parameters, though it's easy enough to raise this number if needed. --HG-- extra : convert_revision : 85cb3c17f8e2ecf9cd2f31ea80a760a28ea127a7 --- src/base/cprintf.hh | 205 +++++++++++++++++++++++++--------------------------- 1 file changed, 99 insertions(+), 106 deletions(-) (limited to 'src/base/cprintf.hh') diff --git a/src/base/cprintf.hh b/src/base/cprintf.hh index dd2256e69..7f8e33367 100644 --- a/src/base/cprintf.hh +++ b/src/base/cprintf.hh @@ -1,5 +1,5 @@ /* - * Copyright (c) 2002-2005 The Regents of The University of Michigan + * Copyright (c) 2002-2006 The Regents of The University of Michigan * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -29,142 +29,135 @@ * Steve Reinhardt */ -#ifndef __CPRINTF_HH__ -#define __CPRINTF_HH__ +#ifndef __BASE_CPRINTF_HH__ +#define __BASE_CPRINTF_HH__ +#include #include #include #include +#include "base/varargs.hh" #include "base/cprintf_formats.hh" namespace cp { -class ArgList +#define CPRINTF_DECLARATION VARARGS_DECLARATION(cp::Print) +#define CPRINTF_DEFINITION VARARGS_DEFINITION(cp::Print) + +struct Print { - private: - class Base - { - public: - virtual ~Base() {} - virtual void process(std::ostream &out, Format &fmt) = 0; - }; + protected: + std::ostream &stream; + const char *format; + const char *ptr; + + std::ios::fmtflags saved_flags; + char saved_fill; + int saved_precision; + + void process(Format &fmt); + + public: + Print(std::ostream &stream, const std::string &format); + Print(std::ostream &stream, const char *format); + ~Print(); template - class Node : public Base + void + add_arg(const T &data) { - public: - const T &data; - - public: - Node(const T &d) : data(d) {} - virtual void process(std::ostream &out, Format &fmt) { - switch (fmt.format) { - case Format::character: - format_char(out, data, fmt); - break; - - case Format::integer: - format_integer(out, data, fmt); - break; - - case Format::floating: - format_float(out, data, fmt); - break; - - case Format::string: - format_string(out, data, fmt); - break; - - default: - out << ""; - break; - } - } - }; + Format fmt; + process(fmt); - typedef std::list list_t; + switch (fmt.format) { + case Format::character: + format_char(stream, data, fmt); + break; - protected: - list_t objects; - std::ostream *stream; + case Format::integer: + format_integer(stream, data, fmt); + break; - public: - ArgList() : stream(&std::cout) {} - ~ArgList(); + case Format::floating: + format_float(stream, data, fmt); + break; - template - void append(const T &data) { - Base *obj = new ArgList::Node(data); - objects.push_back(obj); - } + case Format::string: + format_string(stream, data, fmt); + break; - template - void prepend(const T &data) { - Base *obj = new ArgList::Node(data); - objects.push_front(obj); + default: + stream << ""; + break; + } } - void dump(const std::string &format); - void dump(std::ostream &strm, const std::string &fmt) - { stream = &strm; dump(fmt); } + void end_args(); +}; - std::string dumpToString(const std::string &format); +/* end namespace cp */ } - friend ArgList &operator<<(std::ostream &str, ArgList &list); -}; +typedef VarArgs::List CPrintfArgsList; + +inline void +ccprintf(std::ostream &stream, const char *format, const CPrintfArgsList &args) +{ + cp::Print print(stream, format); + args.add_args(print); +} -template -inline ArgList & -operator,(ArgList &alist, const T &data) +inline void +ccprintf(std::ostream &stream, const char *format, CPRINTF_DECLARATION) { - alist.append(data); - return alist; + cp::Print print(stream, format); + VARARGS_ADDARGS(print); } -class ArgListNull { -}; +inline void +cprintf(const char *format, CPRINTF_DECLARATION) +{ + ccprintf(std::cout, format, VARARGS_ALLARGS); +} + +inline std::string +csprintf(const char *format, CPRINTF_DECLARATION) +{ + std::stringstream stream; + ccprintf(stream, format, VARARGS_ALLARGS); + return stream.str(); +} -inline ArgList & -operator,(ArgList &alist, ArgListNull) -{ return alist; } +/* + * functions again with std::string. We have both so we don't waste + * time converting const char * to std::string since we don't take + * advantage of it. + */ +inline void +ccprintf(std::ostream &stream, const std::string &format, + const CPrintfArgsList &args) +{ + ccprintf(stream, format.c_str(), args); +} -// -// cprintf(format, args, ...) prints to cout -// (analogous to printf()) -// inline void -__cprintf(const std::string &format, ArgList &args) -{ args.dump(format); delete &args; } -#define __cprintf__(format, ...) \ - cp::__cprintf(format, (*(new cp::ArgList), __VA_ARGS__)) -#define cprintf(...) \ - __cprintf__(__VA_ARGS__, cp::ArgListNull()) - -// -// ccprintf(stream, format, args, ...) prints to the specified stream -// (analogous to fprintf()) -// +ccprintf(std::ostream &stream, const std::string &format, CPRINTF_DECLARATION) +{ + ccprintf(stream, format, VARARGS_ALLARGS); +} + inline void -__ccprintf(std::ostream &stream, const std::string &format, ArgList &args) -{ args.dump(stream, format); delete &args; } -#define __ccprintf__(stream, format, ...) \ - cp::__ccprintf(stream, format, (*(new cp::ArgList), __VA_ARGS__)) -#define ccprintf(stream, ...) \ - __ccprintf__(stream, __VA_ARGS__, cp::ArgListNull()) - -// -// csprintf(format, args, ...) returns a string -// (roughly analogous to sprintf()) -// -inline std::string -__csprintf(const std::string &format, ArgList &args) -{ std::string s = args.dumpToString(format); delete &args; return s; } -#define __csprintf__(format, ...) \ - cp::__csprintf(format, (*(new cp::ArgList), __VA_ARGS__)) -#define csprintf(...) \ - __csprintf__(__VA_ARGS__, cp::ArgListNull()) +cprintf(const std::string &format, CPRINTF_DECLARATION) +{ + ccprintf(std::cout, format, VARARGS_ALLARGS); +} +inline std::string +csprintf(const std::string &format, CPRINTF_DECLARATION) +{ + std::stringstream stream; + ccprintf(stream, format, VARARGS_ALLARGS); + return stream.str(); } #endif // __CPRINTF_HH__ -- cgit v1.2.3