问题
I have a C++ library that uses the predefined macro __FUNCTION__
, by way of crtdefs.h. The macro is documented here. Here is my usage:
my.cpp
#include <crtdefs.h>
...
void f()
{
L(__FUNCTIONW__ L" : A diagnostic message");
}
static void L(const wchar_t* format, ...)
{
const size_t BUFFERLENGTH = 1024;
wchar_t buf[BUFFERLENGTH] = { 0 };
va_list args;
va_start(args, format);
int count = _vsnwprintf_s(buf, BUFFERLENGTH, _TRUNCATE, format, args);
va_end(args);
if (count != 0)
{
OutputDebugString(buf);
}
}
crtdefs.h
#define __FUNCTIONW__ _STR2WSTR(__FUNCTION__)
The library (which is compiled as a static library, if that matters) is consumed by another project in the same solution, a WPF app written in C#.
When I compile the lib, I get this error:
identifier "L__FUNCTION__" is undefined.
According to the docs, the macro isn't expanded if /P or /EP are passed to the compiler. I have verified that they are not. Are there other conditions where this macro is unavailable?
回答1:
Just use
L(__FUNCTION__ L" : A diagnostic message");
When adjacent string literals get combined, the result will be a wide string if any of the components were.
There's nothing immediately wrong with using L
as the name of a function... it's rather meaningless however. Good variable and function identifiers should be descriptive in order to help the reader understand the code. But the compiler doesn't care.
Since your L
function wraps vsprintf, you may also use:
L(L"%hs : A diagnostic message", __func__);
since __func__
is standardized as a narrow string, the %hs
format specifier is appropriate.
The rule is found in 2.14.5p13:
In translation phase 6 (2.2), adjacent string literals are concatenated. If both string literals have the same encoding-prefix, the resulting concatenated string literal has that encoding-prefix. If one string literal has no encoding-prefix, it is treated as a string literal of the same encoding-prefix as the other operand. If a UTF-8 string literal token is adjacent to a wide string literal token, the program is ill-formed. Any other concatenations are conditionally-supported with implementation-defined behavior.
回答2:
You list the error as this:
identifier "L__FUNCTION__" is undefined.
Note it's saying "L__FUNCTION__
" is not defined, not "__FUNCTION__
".
Don't use __FUNCTIONW__
in your code. MS didn't document that in the page you linked, they documented __FUNCTION__
. And you don't need to widen __FUNCTION__
.
ETA: I also note that you're not assigning that string to anything or printing it in anyway in f()
.
回答3:
I think the definition of __FUNCTIONW__
is incorrect. (I know you did not write it.)
From: http://gcc.gnu.org/onlinedocs/gcc/Function-Names.html
These identifiers are not preprocessor macros. In GCC 3.3 and earlier, in C only,
__FUNCTION__
and__PRETTY_FUNCTION__
were treated as string literals; they could be used to initialize char arrays, and they could be concatenated with other string literals. GCC 3.4 and later treat them as variables, like__func__
. In C++,__FUNCTION__
and__PRETTY_FUNCTION__
have always been variables.
At least in current GCC then you cannot prepend L
to __FUNCTION__
, because it is like trying to prepend L
to a variable. There probably was a version of VC++ (like there was of GCC) where this would have worked, but you are not using that version.
来源:https://stackoverflow.com/questions/23482297/why-would-function-be-undefined