在 AQTime 下检测 运行?避免崩溃调试代码
Detect running under AQTime? Avoid crashing debugging code
我在 AQTime 中使用性能分析器。尝试 运行 在 IDE 下(使用 Embarcadero RAD Studio XE)。已检查的项目因此类代码而崩溃:
// Setting a Thread Name (Unmanaged):
// http://msdn.microsoft.com/en-us/library/xcb2z8hs(VS.71).aspx
procedure _NameThreadForDebugging(const ATID: Cardinal; const AThreadName: String);
type
TThreadNameInfo = record
FType: LongWord; // must be 0x1000
FName: PAnsiChar; // pointer to name (in user address space)
FThreadID: LongWord; // thread ID (-1 indicates caller thread)
FFlags: LongWord; // reserved for future use, must be zero
end;
var
ThreadNameInfo: TThreadNameInfo;
ThreadName: AnsiString;
begin
// Applicable only for debugged applications
if IsDebuggerPresent then
begin
FillChar(ThreadNameInfo, SizeOf(ThreadNameInfo), 0);
ThreadName := AnsiString(AThreadName);
ThreadNameInfo.FType := 00;
ThreadNameInfo.FName := PAnsiChar(ThreadName);
ThreadNameInfo.FThreadID := ATID;
try
RaiseException(cSetThreadNameExcep, 0, SizeOf(ThreadNameInfo) div SizeOf(LongWord), @ThreadNameInfo);
except
end;
Finalize(ThreadName);
end;
end;
当 运行 在 IDE 之外时工作正常(在这种情况下例程将退出而不做任何事情),或者当 运行 在通常的 IDE 调试器下(在这种情况下例程将引发异常,这将由 IDE 的调试器处理)。
然而,当 运行 在 AQTime 下 - 例程将在调用 kernel32.RaiseException 例程时崩溃(APPCRASH C00001A5 在 kernel32 中的某处)。我已经通过在这个调用周围放置 MessageBoxes 来确认这一点(try/except 块)。
显然,在AQTime 运行 下,IsDebuggerPresent 为True,但未正确处理异常。
问题:如何检测和避免这种情况?如何检查代码是否在AQTime下执行?
AQTime 是 8.22。
您可以检查以下默认传递给配置文件进程的环境变量:AQTIME_DEBUGGER_PRESENT
、AQTIME_SESSION_ID
和 AQTIME_VERSION
。
注意:确切的变量似乎取决于使用的探查器(或 AQTime 版本?)——在我的例子中,只有 AQTIME_SESSION_ID
和 AQTIME_VERSION
存在。
我在 AQTime 中使用性能分析器。尝试 运行 在 IDE 下(使用 Embarcadero RAD Studio XE)。已检查的项目因此类代码而崩溃:
// Setting a Thread Name (Unmanaged):
// http://msdn.microsoft.com/en-us/library/xcb2z8hs(VS.71).aspx
procedure _NameThreadForDebugging(const ATID: Cardinal; const AThreadName: String);
type
TThreadNameInfo = record
FType: LongWord; // must be 0x1000
FName: PAnsiChar; // pointer to name (in user address space)
FThreadID: LongWord; // thread ID (-1 indicates caller thread)
FFlags: LongWord; // reserved for future use, must be zero
end;
var
ThreadNameInfo: TThreadNameInfo;
ThreadName: AnsiString;
begin
// Applicable only for debugged applications
if IsDebuggerPresent then
begin
FillChar(ThreadNameInfo, SizeOf(ThreadNameInfo), 0);
ThreadName := AnsiString(AThreadName);
ThreadNameInfo.FType := 00;
ThreadNameInfo.FName := PAnsiChar(ThreadName);
ThreadNameInfo.FThreadID := ATID;
try
RaiseException(cSetThreadNameExcep, 0, SizeOf(ThreadNameInfo) div SizeOf(LongWord), @ThreadNameInfo);
except
end;
Finalize(ThreadName);
end;
end;
当 运行 在 IDE 之外时工作正常(在这种情况下例程将退出而不做任何事情),或者当 运行 在通常的 IDE 调试器下(在这种情况下例程将引发异常,这将由 IDE 的调试器处理)。
然而,当 运行 在 AQTime 下 - 例程将在调用 kernel32.RaiseException 例程时崩溃(APPCRASH C00001A5 在 kernel32 中的某处)。我已经通过在这个调用周围放置 MessageBoxes 来确认这一点(try/except 块)。
显然,在AQTime 运行 下,IsDebuggerPresent 为True,但未正确处理异常。
问题:如何检测和避免这种情况?如何检查代码是否在AQTime下执行?
AQTime 是 8.22。
您可以检查以下默认传递给配置文件进程的环境变量:AQTIME_DEBUGGER_PRESENT
、AQTIME_SESSION_ID
和 AQTIME_VERSION
。
注意:确切的变量似乎取决于使用的探查器(或 AQTime 版本?)——在我的例子中,只有 AQTIME_SESSION_ID
和 AQTIME_VERSION
存在。