Function has no address, possibly due to compiler optimizations.

huangapple go评论93阅读模式
英文:

Function has no address, possibly due to compiler optimizations

问题

在Visual Studio 2022中,如果我尝试在Watch窗口中调用一个简单结构体的函数,然后我会得到"Function has no address, possibly due to compiler optimizations"错误。如果我在Watch窗口中调用一个模板函数,那么我会得到这个错误:"class "MyStruct" has no member "Multi"。如果我在源代码中使用这些函数一次,然后它们也会开始在Watch窗口中工作,但如何使它们在Watch窗口中工作而不必在源代码中使用它们呢?

我的代码:

struct MyStruct
{
    int i;
    MyStruct(int _i) : i{ _i } {}
    int Add(int x) { return i + x; };

    template<typename _Tp> inline _Tp Multi(int x)
    {
        return (_Tp)i * x;
    }
};

int main()
{
    MyStruct s1(2);
    //auto x1 = s1.Add(5);
    //auto x2 = s1.Multi<double>(9);

    return 0;
}

和Watch窗口:

Function has no address, possibly due to compiler optimizations.

我正在运行Debug版本。
链接器->调试->生成调试信息设置为"/DEBUG:FULL",并且禁用了优化:Disabled (/Od)。

英文:

In Visual Studio 2022 if I try to call a function of a simple struct in the Watch window then I get "Function has no address, possibly due to compiler optimizations" error. And if I call a template function in the Watch window, then I get this error: class "MyStruct" has no member "Multi<double>". If I use these functions one time in the source code, then they will also begin to work in the Watch window, but how to make them work in the Watch window without having to use them in the source code?

My code:

struct MyStruct
{
	int i;
	MyStruct(int _i) : i{ _i } {}
	int Add(int x) { return i + x; };

	template&lt;typename _Tp&gt; inline _Tp Multi(int x)
	{
		return (_Tp)i * x;
	}
};

int main()
{
	MyStruct s1(2);
	//auto x1 = s1.Add(5);
	//auto x2 = s1.Multi&lt;double&gt;(9);

	return 0;
}

And the Watch window:
Function has no address, possibly due to compiler optimizations.

I am running the Debug version.
Linker-> Debugging-> Generate Debug Info is set to "/DEBUG:FULL" and optimizations are disabled: Disabled (/Od).

答案1

得分: 7

不能。C++ 在根本上不以这种方式工作。模板不是一个函数。里面没有代码。它只是一个函数的模板,从字面上讲,根据定义和名称来说都是如此。换句话说,它只是一个实际函数的蓝图。

当代码引用一个模板并提供模板的参数(明确地或通过模板参数推导)时,才会得到一个实际的函数,有实际的代码。这个过程被称为模板实例化。

在模板函数被实例化之前,它在程序中实际上不存在,调试器无法调用它。调试器可以四处搜索,但它不会找到任何可以实际调用的内容。它不存在。但当模板被实例化为实际的代码的一部分时,调试器可以在程序的符号表中找到它的符号,并引用一个实际的函数并调用它。

理论上,一个调试器可以在调试器本身中包含一个C++编译器,或者使用外部C++编译器,以某种方式将模板实例化为实际函数并调用它。但实际上,很少有调试器能够以这种方式工作。

英文:

> how to make them work in the Watch window without having to use them in the source code

You can't. C++ simply doesn't work this way, on a fundamental level. A template is not a function. There's no code in there. It is a template for a function, in the most literal sense, by definition and name. In other words it's just a blueprint, of sorts, for an actual function.

When code references a template, and provides the template's parameters (explicitly, or via template argument deduction), only then you end up with an actual, honest-to-goodness function. With actual code. This process is called template instantiation.

And until a template function gets instantiated, it literally does not exist as part of the program, and there's nothing for the debugger to call. The debugger can search high and low, but it won't find anything it can actually invoke. It does not exist. But when a template gets instantiated, as part of actual code, the debugger can find its munged symbol in the program's symbol table, referencing an actual function, and call it.

Now, theoretically, it would be possible for a debugger to either include a C++ compiler as part of the debugger itself, or use the external C++ compiler, to, somehow, instantiate the template into an actual function and call it. But, practically, it is unlikely that there's some debugger, out there, that actually works like that.

huangapple
  • 本文由 发表于 2023年7月11日 06:53:28
  • 转载请务必保留本文链接:https://go.coder-hub.com/76657777.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定