[v8windbg] Fix curisolate() again

The last CL miscalculated the address of Isolate object. We should find the thread_local base address using `_tls_index_`. And, instead of calculating the address manually, all the location information is already available in `Location`. So, we can simply use the Location object to create a typed object.

Also, adding a testcase for `curisolate()` function.

Bug: v8:13394
Change-Id: I1da55bdf43a3b6100d141917eb97a1793939dca8
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/4220104
Reviewed-by: Seth Brenith <seth.brenith@microsoft.com>
Commit-Queue: Choongwoo Han <choongwoo.han@microsoft.com>
Cr-Commit-Position: refs/heads/main@{#85654}
This commit is contained in:
Choongwoo Han 2023-02-03 08:06:44 -08:00 committed by V8 LUCI CQ
parent f18065a3ca
commit d5784303a1
3 changed files with 21 additions and 34 deletions

View File

@ -4,8 +4,8 @@
#include "tools/v8windbg/src/cur-isolate.h"
HRESULT GetIsolateOffset(WRL::ComPtr<IDebugHostContext>& sp_ctx,
ptrdiff_t* isolate_offset) {
HRESULT GetIsolateLocation(WRL::ComPtr<IDebugHostContext>& sp_ctx,
Location* location) {
auto sp_v8_module = Extension::Current()->GetV8Module(sp_ctx);
if (sp_v8_module == nullptr) return E_FAIL;
@ -17,9 +17,7 @@ HRESULT GetIsolateOffset(WRL::ComPtr<IDebugHostContext>& sp_ctx,
if (kind != SymbolData) return E_FAIL;
WRL::ComPtr<IDebugHostData> sp_isolate_key_data;
RETURN_IF_FAIL(sp_isolate_sym.As(&sp_isolate_key_data));
Location location;
RETURN_IF_FAIL(sp_isolate_key_data->GetLocation(&location));
*isolate_offset = location.Offset;
RETURN_IF_FAIL(sp_isolate_key_data->GetLocation(location));
return S_OK;
}
@ -30,34 +28,8 @@ HRESULT GetCurrentIsolate(WRL::ComPtr<IModelObject>& sp_result) {
WRL::ComPtr<IDebugHostContext> sp_host_context;
RETURN_IF_FAIL(sp_debug_host->GetCurrentContext(&sp_host_context));
WRL::ComPtr<IModelObject> sp_curr_thread;
RETURN_IF_FAIL(GetCurrentThread(sp_host_context, &sp_curr_thread));
WRL::ComPtr<IModelObject> sp_environment, sp_environment_block;
WRL::ComPtr<IModelObject> sp_tls_pointer, sp_isolate_offset;
RETURN_IF_FAIL(
sp_curr_thread->GetKeyValue(L"Environment", &sp_environment, nullptr));
RETURN_IF_FAIL(sp_environment->GetKeyValue(L"EnvironmentBlock",
&sp_environment_block, nullptr));
// EnvironmentBlock and TlsSlots are native types (TypeUDT) and thus
// GetRawValue rather than GetKeyValue should be used to get field (member)
// values.
ModelObjectKind kind;
RETURN_IF_FAIL(sp_environment_block->GetKind(&kind));
if (kind != ModelObjectKind::ObjectTargetObject) return E_FAIL;
RETURN_IF_FAIL(sp_environment_block->GetRawValue(
SymbolField, L"ThreadLocalStoragePointer", 0, &sp_tls_pointer));
ptrdiff_t isolate_offset = -1;
RETURN_IF_FAIL(GetIsolateOffset(sp_host_context, &isolate_offset));
uint64_t isolate_ptr;
RETURN_IF_FAIL(UnboxULong64(sp_tls_pointer.Get(), &isolate_ptr));
isolate_ptr += isolate_offset;
Location isolate_addr{isolate_ptr};
Location isolate_addr;
RETURN_IF_FAIL(GetIsolateLocation(sp_host_context, &isolate_addr));
// If we got the isolate_key OK, then must have the V8 module loaded
// Get the internal Isolate type from it

View File

@ -18,7 +18,7 @@
HRESULT GetCurrentIsolate(WRL::ComPtr<IModelObject>& sp_result);
constexpr wchar_t kIsolateOffset[] = L"v8::internal::g_current_isolate_";
constexpr wchar_t kIsolate[] = L"v8::internal::Isolate";
constexpr wchar_t kIsolate[] = L"v8::internal::Isolate *";
class CurrIsolateAlias
: public WRL::RuntimeClass<

View File

@ -253,6 +253,21 @@ void RunTests() {
// {"empty_string \"\"", "SeqOneByteString"}, &output,
// p_debug_control.Get());
// Test for @$curisolate(). This should have the same output with
// `dx v8::internal::g_current_isolate_`.
output.ClearLog();
CHECK(SUCCEEDED(p_debug_control->Execute(
DEBUG_OUTCTL_ALL_CLIENTS, "dx v8::internal::g_current_isolate_",
DEBUG_EXECUTE_ECHO)));
size_t addr_pos = output.GetLog().find("0x");
CHECK(addr_pos != std::string::npos);
std::string expected_output = output.GetLog().substr(addr_pos);
output.ClearLog();
CHECK(SUCCEEDED(p_debug_control->Execute(
DEBUG_OUTCTL_ALL_CLIENTS, "dx @$curisolate()", DEBUG_EXECUTE_ECHO)));
CHECK_EQ(output.GetLog().substr(output.GetLog().find("0x")), expected_output);
// Detach before exiting
hr = p_client->DetachProcesses();
CHECK(SUCCEEDED(hr));