Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
58 changes: 53 additions & 5 deletions NativeScript/inspector/JsV8InspectorClient.h
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@

#include <functional>
#include <map>
#include <mutex>
#include <string>
#include <vector>

Expand All @@ -15,6 +16,8 @@

namespace v8_inspector {

class WorkerInspectorClient;

class JsV8InspectorClient : V8InspectorClient, V8Inspector::Channel {
public:
JsV8InspectorClient(tns::Runtime* runtime);
Expand All @@ -23,6 +26,20 @@ class JsV8InspectorClient : V8InspectorClient, V8Inspector::Channel {
void disconnect();
void dispatchMessage(const std::string& message);

// The single instance debugging the main isolate (created when IsDebug);
// also acts as the router for worker sessions. Null in release builds.
static JsV8InspectorClient* GetInstance();

// Thread-safe write to the connected frontend (no-op when disconnected).
void SendToFrontend(const std::string& message);

// Worker targets (Chrome DevTools Target domain, flat-session mode).
// Register/Unregister are called on the worker's own thread.
void RegisterWorkerTarget(int workerId, WorkerInspectorClient* client);
void UnregisterWorkerTarget(int workerId);
// Called on a worker thread by the Debugger.pause interrupt.
void SchedulePauseInWorker(int workerId);

// Overrides of V8Inspector::Channel
void sendResponse(int callId, std::unique_ptr<StringBuffer> message) override;
void sendNotification(std::unique_ptr<StringBuffer> message) override;
Expand Down Expand Up @@ -63,13 +80,39 @@ class JsV8InspectorClient : V8InspectorClient, V8Inspector::Channel {

// Streams backing Network.loadNetworkResource responses, read by the
// frontend through IO.read/IO.close (how Chrome DevTools fetches source
// maps from the target). Only touched from dispatchMessage (main thread).
// maps from the target). Served on the socket thread for any session;
// guarded by resourceStreamsMutex_.
struct ResourceStream {
std::string data;
size_t offset = 0;
};
std::map<std::string, ResourceStream> resourceStreams_;
int lastStreamId_ = 0;
std::mutex resourceStreamsMutex_;

// Worker targets announced to the frontend via Target.attachedToTarget,
// keyed by their flat-protocol sessionId. Guarded by workerTargetsMutex_;
// a registered client pointer stays valid until UnregisterWorkerTarget
// (which runs on the worker's own thread, before the client is deleted).
struct WorkerTarget {
int workerId;
WorkerInspectorClient* client;
bool announced = false;
};
std::map<std::string, WorkerTarget> workerTargets_;
std::mutex workerTargetsMutex_;
bool autoAttach_ = false; // guarded by workerTargetsMutex_

static JsV8InspectorClient* instance_;

std::mutex senderMutex_;

// Routes a frontend message carrying a sessionId to its worker session
// (socket thread). msgId is -1 when the message has no id.
void RouteToWorker(const std::string& sessionId, const std::string& method,
long long msgId, const std::string& message);
// Announces all not-yet-announced workers (after Target.setAutoAttach).
void AnnounceWorkerTargets();

// Override of V8InspectorClient
v8::Local<v8::Context> ensureDefaultContextInGroup(
Expand All @@ -90,10 +133,15 @@ class JsV8InspectorClient : V8InspectorClient, V8Inspector::Channel {
const v8::FunctionCallbackInfo<v8::Value>& args);

// Source map delivery to Chrome DevTools (Network.loadNetworkResource + IO
// domain). V8's inspector doesn't implement these embedder domains.
void HandleLoadNetworkResource(int msgId, const std::string& url);
void HandleIORead(int msgId, const std::string& handle, int size);
void HandleIOClose(int msgId, const std::string& handle);
// domain). V8's inspector doesn't implement these embedder domains. The
// handlers are filesystem-only and thread-safe; they serve any session
// (sessionId is echoed in the reply when non-empty).
void HandleLoadNetworkResource(int msgId, const std::string& url,
const std::string& sessionId);
void HandleIORead(int msgId, const std::string& handle, int size,
const std::string& sessionId);
void HandleIOClose(int msgId, const std::string& handle,
const std::string& sessionId);

// {N} specific helpers
bool CallDomainHandlerFunction(v8::Local<v8::Context> context,
Expand Down
Loading
Loading