gpt4 book ai didi

c# - 为什么我必须重建一个未更改的项目?

转载 作者:太空狗 更新时间:2023-10-29 20:37:00 24 4
gpt4 key购买 nike

我有以下 MASM 代码:

.386
.model flat, stdcall
option casemap :none

include \masm32\include\masm32rt.inc

.data
NewLine db 13, 10, 0
.code

LibMain proc instance:dword,reason:dword,unused:dword
mov eax, 1
ret
LibMain endp

PrintMess proc
print "Printed from assembly"
invoke StdOut, addr NewLine
ret
PrintMess endp

TestReturn proc number:dword
mov eax, number
ret
TestReturn endp

End LibMain

使用一个简单的 .def 文件:

LIBRARY MyLib
EXPORTS PrintMess
EXPORTS TestReturn

我从 C# 中调用 PrintMessTestReturn:

[DllImport("MyLib")]
static extern void PrintMess();

[DllImport("MyLib")]
static extern int TestReturn(int num);

static void Main(string[] args) {
Console.WriteLine("Printed from C#");

PrintMess();

int value = TestReturn(30);
Console.WriteLine("Returned: " + value);

Console.ReadKey(true);
}

我第一次运行它时,它在 Console.ReadKey(true) 处暂停,我得到了预期的输出:

Printed from C#
Printed from assembly
Returned: 30

如果我随后在我的 C# 项目中进行更改,比如将 TestReturn(30) 更改为 TestReturn(50) 那么它的行为就会很奇怪。该程序无误地终止,并且不会在 Console.ReadKey(true) 上暂停(似乎它甚至没有到达该行),这是我的输出:

Printed from C#
Printed from assembly

我必须重建装配项目。具体来说,我必须重新构建,如果我再进行一次常规构建,该程序将继续运行异常。当我重建时,输出和行为恢复正常并反射(reflect)输出中的数字变化。我的猜测是 Build 和 Rebuild 之间存在一些不同之处,这会部分破坏 DLL。

为什么我必须重建以及我如何设置它才能不必重建?

最佳答案

@HansPassant 很可能是正确的,但没有解释为什么必须重建。 @jacobaloysious 很接近。

VS 使用所谓的“托管进程”来简化和隔离调试。当您从 VS 调试 test.exe 时,实际上您正在调试 test.vshost.exe,它会加载您的 exe。停止调试时不会卸载主机可执行文件,因此您的真实可执行文件。当您在不更改任何内容的情况下构建代码时,VS 实际上只会检查文件是否是最新的。 VS 认为,如果文件没有改变,那么就没有必要重新加载宿主进程。如果您重建,即使您没有更改任何代码,您的真实可执行文件也会更新,这会强制终止主机进程并重新加载,以及您的真实可执行文件。

我想,这个过程实际上是为了通过预加载汇编代码来加速调试的启动。您可以尝试在项目属性中关闭“启用 Visual Studio 托管进程”。之后,您应该会看到您的项目按预期工作。

在您继续前进之前,请意识到@HansPassant 是正确的并且您的堆栈已损坏,并且随着时间的推移,您的项目将在意想不到的时间以最不愉快的方式以意想不到的方式失败。在大多数情况下,您的应用程序会抛出没有意义的异常,而在某些情况下,您的应用程序会消失。

关于c# - 为什么我必须重建一个未更改的项目?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/13940057/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com