11cb0ef41Sopenharmony_ci// Copyright 2016 the V8 project authors. All rights reserved.
21cb0ef41Sopenharmony_ci// Use of this source code is governed by a BSD-style license that can be
31cb0ef41Sopenharmony_ci// found in the LICENSE file.
41cb0ef41Sopenharmony_ci
51cb0ef41Sopenharmony_ci#include "src/inspector/v8-console-message.h"
61cb0ef41Sopenharmony_ci
71cb0ef41Sopenharmony_ci#include "include/v8-container.h"
81cb0ef41Sopenharmony_ci#include "include/v8-context.h"
91cb0ef41Sopenharmony_ci#include "include/v8-inspector.h"
101cb0ef41Sopenharmony_ci#include "include/v8-microtask-queue.h"
111cb0ef41Sopenharmony_ci#include "include/v8-primitive-object.h"
121cb0ef41Sopenharmony_ci#include "src/debug/debug-interface.h"
131cb0ef41Sopenharmony_ci#include "src/inspector/inspected-context.h"
141cb0ef41Sopenharmony_ci#include "src/inspector/protocol/Protocol.h"
151cb0ef41Sopenharmony_ci#include "src/inspector/string-util.h"
161cb0ef41Sopenharmony_ci#include "src/inspector/v8-console-agent-impl.h"
171cb0ef41Sopenharmony_ci#include "src/inspector/v8-inspector-impl.h"
181cb0ef41Sopenharmony_ci#include "src/inspector/v8-inspector-session-impl.h"
191cb0ef41Sopenharmony_ci#include "src/inspector/v8-runtime-agent-impl.h"
201cb0ef41Sopenharmony_ci#include "src/inspector/v8-stack-trace-impl.h"
211cb0ef41Sopenharmony_ci#include "src/inspector/value-mirror.h"
221cb0ef41Sopenharmony_ci#include "src/tracing/trace-event.h"
231cb0ef41Sopenharmony_ci
241cb0ef41Sopenharmony_cinamespace v8_inspector {
251cb0ef41Sopenharmony_ci
261cb0ef41Sopenharmony_cinamespace {
271cb0ef41Sopenharmony_ci
281cb0ef41Sopenharmony_ciString16 consoleAPITypeValue(ConsoleAPIType type) {
291cb0ef41Sopenharmony_ci  switch (type) {
301cb0ef41Sopenharmony_ci    case ConsoleAPIType::kLog:
311cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Log;
321cb0ef41Sopenharmony_ci    case ConsoleAPIType::kDebug:
331cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Debug;
341cb0ef41Sopenharmony_ci    case ConsoleAPIType::kInfo:
351cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Info;
361cb0ef41Sopenharmony_ci    case ConsoleAPIType::kError:
371cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Error;
381cb0ef41Sopenharmony_ci    case ConsoleAPIType::kWarning:
391cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Warning;
401cb0ef41Sopenharmony_ci    case ConsoleAPIType::kClear:
411cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Clear;
421cb0ef41Sopenharmony_ci    case ConsoleAPIType::kDir:
431cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Dir;
441cb0ef41Sopenharmony_ci    case ConsoleAPIType::kDirXML:
451cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Dirxml;
461cb0ef41Sopenharmony_ci    case ConsoleAPIType::kTable:
471cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Table;
481cb0ef41Sopenharmony_ci    case ConsoleAPIType::kTrace:
491cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Trace;
501cb0ef41Sopenharmony_ci    case ConsoleAPIType::kStartGroup:
511cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::StartGroup;
521cb0ef41Sopenharmony_ci    case ConsoleAPIType::kStartGroupCollapsed:
531cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::StartGroupCollapsed;
541cb0ef41Sopenharmony_ci    case ConsoleAPIType::kEndGroup:
551cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::EndGroup;
561cb0ef41Sopenharmony_ci    case ConsoleAPIType::kAssert:
571cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Assert;
581cb0ef41Sopenharmony_ci    case ConsoleAPIType::kTimeEnd:
591cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::TimeEnd;
601cb0ef41Sopenharmony_ci    case ConsoleAPIType::kCount:
611cb0ef41Sopenharmony_ci      return protocol::Runtime::ConsoleAPICalled::TypeEnum::Count;
621cb0ef41Sopenharmony_ci  }
631cb0ef41Sopenharmony_ci  return protocol::Runtime::ConsoleAPICalled::TypeEnum::Log;
641cb0ef41Sopenharmony_ci}
651cb0ef41Sopenharmony_ci
661cb0ef41Sopenharmony_ciconst char kGlobalConsoleMessageHandleLabel[] = "DevTools console";
671cb0ef41Sopenharmony_ciconst unsigned maxConsoleMessageCount = 1000;
681cb0ef41Sopenharmony_ciconst int maxConsoleMessageV8Size = 10 * 1024 * 1024;
691cb0ef41Sopenharmony_ciconst unsigned maxArrayItemsLimit = 10000;
701cb0ef41Sopenharmony_ciconst unsigned maxStackDepthLimit = 32;
711cb0ef41Sopenharmony_ci
721cb0ef41Sopenharmony_ciclass V8ValueStringBuilder {
731cb0ef41Sopenharmony_ci public:
741cb0ef41Sopenharmony_ci  static String16 toString(v8::Local<v8::Value> value,
751cb0ef41Sopenharmony_ci                           v8::Local<v8::Context> context) {
761cb0ef41Sopenharmony_ci    V8ValueStringBuilder builder(context);
771cb0ef41Sopenharmony_ci    if (!builder.append(value)) return String16();
781cb0ef41Sopenharmony_ci    return builder.toString();
791cb0ef41Sopenharmony_ci  }
801cb0ef41Sopenharmony_ci
811cb0ef41Sopenharmony_ci private:
821cb0ef41Sopenharmony_ci  enum {
831cb0ef41Sopenharmony_ci    IgnoreNull = 1 << 0,
841cb0ef41Sopenharmony_ci    IgnoreUndefined = 1 << 1,
851cb0ef41Sopenharmony_ci  };
861cb0ef41Sopenharmony_ci
871cb0ef41Sopenharmony_ci  explicit V8ValueStringBuilder(v8::Local<v8::Context> context)
881cb0ef41Sopenharmony_ci      : m_arrayLimit(maxArrayItemsLimit),
891cb0ef41Sopenharmony_ci        m_isolate(context->GetIsolate()),
901cb0ef41Sopenharmony_ci        m_tryCatch(context->GetIsolate()),
911cb0ef41Sopenharmony_ci        m_context(context) {}
921cb0ef41Sopenharmony_ci
931cb0ef41Sopenharmony_ci  bool append(v8::Local<v8::Value> value, unsigned ignoreOptions = 0) {
941cb0ef41Sopenharmony_ci    if (value.IsEmpty()) return true;
951cb0ef41Sopenharmony_ci    if ((ignoreOptions & IgnoreNull) && value->IsNull()) return true;
961cb0ef41Sopenharmony_ci    if ((ignoreOptions & IgnoreUndefined) && value->IsUndefined()) return true;
971cb0ef41Sopenharmony_ci    if (value->IsString()) return append(value.As<v8::String>());
981cb0ef41Sopenharmony_ci    if (value->IsStringObject())
991cb0ef41Sopenharmony_ci      return append(value.As<v8::StringObject>()->ValueOf());
1001cb0ef41Sopenharmony_ci    if (value->IsBigInt()) return append(value.As<v8::BigInt>());
1011cb0ef41Sopenharmony_ci    if (value->IsBigIntObject())
1021cb0ef41Sopenharmony_ci      return append(value.As<v8::BigIntObject>()->ValueOf());
1031cb0ef41Sopenharmony_ci    if (value->IsSymbol()) return append(value.As<v8::Symbol>());
1041cb0ef41Sopenharmony_ci    if (value->IsSymbolObject())
1051cb0ef41Sopenharmony_ci      return append(value.As<v8::SymbolObject>()->ValueOf());
1061cb0ef41Sopenharmony_ci    if (value->IsNumberObject()) {
1071cb0ef41Sopenharmony_ci      m_builder.append(
1081cb0ef41Sopenharmony_ci          String16::fromDouble(value.As<v8::NumberObject>()->ValueOf(), 6));
1091cb0ef41Sopenharmony_ci      return true;
1101cb0ef41Sopenharmony_ci    }
1111cb0ef41Sopenharmony_ci    if (value->IsBooleanObject()) {
1121cb0ef41Sopenharmony_ci      m_builder.append(value.As<v8::BooleanObject>()->ValueOf() ? "true"
1131cb0ef41Sopenharmony_ci                                                                : "false");
1141cb0ef41Sopenharmony_ci      return true;
1151cb0ef41Sopenharmony_ci    }
1161cb0ef41Sopenharmony_ci    if (value->IsArray()) return append(value.As<v8::Array>());
1171cb0ef41Sopenharmony_ci    if (value->IsProxy()) {
1181cb0ef41Sopenharmony_ci      m_builder.append("[object Proxy]");
1191cb0ef41Sopenharmony_ci      return true;
1201cb0ef41Sopenharmony_ci    }
1211cb0ef41Sopenharmony_ci    if (value->IsObject() && !value->IsDate() && !value->IsFunction() &&
1221cb0ef41Sopenharmony_ci        !value->IsNativeError() && !value->IsRegExp()) {
1231cb0ef41Sopenharmony_ci      v8::Local<v8::Object> object = value.As<v8::Object>();
1241cb0ef41Sopenharmony_ci      v8::Local<v8::String> stringValue;
1251cb0ef41Sopenharmony_ci      if (object->ObjectProtoToString(m_context).ToLocal(&stringValue))
1261cb0ef41Sopenharmony_ci        return append(stringValue);
1271cb0ef41Sopenharmony_ci    }
1281cb0ef41Sopenharmony_ci    v8::Local<v8::String> stringValue;
1291cb0ef41Sopenharmony_ci    if (!value->ToString(m_context).ToLocal(&stringValue)) return false;
1301cb0ef41Sopenharmony_ci    return append(stringValue);
1311cb0ef41Sopenharmony_ci  }
1321cb0ef41Sopenharmony_ci
1331cb0ef41Sopenharmony_ci  bool append(v8::Local<v8::Array> array) {
1341cb0ef41Sopenharmony_ci    for (const auto& it : m_visitedArrays) {
1351cb0ef41Sopenharmony_ci      if (it == array) return true;
1361cb0ef41Sopenharmony_ci    }
1371cb0ef41Sopenharmony_ci    uint32_t length = array->Length();
1381cb0ef41Sopenharmony_ci    if (length > m_arrayLimit) return false;
1391cb0ef41Sopenharmony_ci    if (m_visitedArrays.size() > maxStackDepthLimit) return false;
1401cb0ef41Sopenharmony_ci
1411cb0ef41Sopenharmony_ci    bool result = true;
1421cb0ef41Sopenharmony_ci    m_arrayLimit -= length;
1431cb0ef41Sopenharmony_ci    m_visitedArrays.push_back(array);
1441cb0ef41Sopenharmony_ci    for (uint32_t i = 0; i < length; ++i) {
1451cb0ef41Sopenharmony_ci      if (i) m_builder.append(',');
1461cb0ef41Sopenharmony_ci      v8::Local<v8::Value> value;
1471cb0ef41Sopenharmony_ci      if (!array->Get(m_context, i).ToLocal(&value)) continue;
1481cb0ef41Sopenharmony_ci      if (!append(value, IgnoreNull | IgnoreUndefined)) {
1491cb0ef41Sopenharmony_ci        result = false;
1501cb0ef41Sopenharmony_ci        break;
1511cb0ef41Sopenharmony_ci      }
1521cb0ef41Sopenharmony_ci    }
1531cb0ef41Sopenharmony_ci    m_visitedArrays.pop_back();
1541cb0ef41Sopenharmony_ci    return result;
1551cb0ef41Sopenharmony_ci  }
1561cb0ef41Sopenharmony_ci
1571cb0ef41Sopenharmony_ci  bool append(v8::Local<v8::Symbol> symbol) {
1581cb0ef41Sopenharmony_ci    m_builder.append("Symbol(");
1591cb0ef41Sopenharmony_ci    bool result = append(symbol->Description(m_isolate), IgnoreUndefined);
1601cb0ef41Sopenharmony_ci    m_builder.append(')');
1611cb0ef41Sopenharmony_ci    return result;
1621cb0ef41Sopenharmony_ci  }
1631cb0ef41Sopenharmony_ci
1641cb0ef41Sopenharmony_ci  bool append(v8::Local<v8::BigInt> bigint) {
1651cb0ef41Sopenharmony_ci    v8::Local<v8::String> bigint_string;
1661cb0ef41Sopenharmony_ci    if (!bigint->ToString(m_context).ToLocal(&bigint_string)) return false;
1671cb0ef41Sopenharmony_ci    bool result = append(bigint_string);
1681cb0ef41Sopenharmony_ci    if (m_tryCatch.HasCaught()) return false;
1691cb0ef41Sopenharmony_ci    m_builder.append('n');
1701cb0ef41Sopenharmony_ci    return result;
1711cb0ef41Sopenharmony_ci  }
1721cb0ef41Sopenharmony_ci
1731cb0ef41Sopenharmony_ci  bool append(v8::Local<v8::String> string) {
1741cb0ef41Sopenharmony_ci    if (m_tryCatch.HasCaught()) return false;
1751cb0ef41Sopenharmony_ci    if (!string.IsEmpty()) {
1761cb0ef41Sopenharmony_ci      m_builder.append(toProtocolString(m_isolate, string));
1771cb0ef41Sopenharmony_ci    }
1781cb0ef41Sopenharmony_ci    return true;
1791cb0ef41Sopenharmony_ci  }
1801cb0ef41Sopenharmony_ci
1811cb0ef41Sopenharmony_ci  String16 toString() {
1821cb0ef41Sopenharmony_ci    if (m_tryCatch.HasCaught()) return String16();
1831cb0ef41Sopenharmony_ci    return m_builder.toString();
1841cb0ef41Sopenharmony_ci  }
1851cb0ef41Sopenharmony_ci
1861cb0ef41Sopenharmony_ci  uint32_t m_arrayLimit;
1871cb0ef41Sopenharmony_ci  v8::Isolate* m_isolate;
1881cb0ef41Sopenharmony_ci  String16Builder m_builder;
1891cb0ef41Sopenharmony_ci  std::vector<v8::Local<v8::Array>> m_visitedArrays;
1901cb0ef41Sopenharmony_ci  v8::TryCatch m_tryCatch;
1911cb0ef41Sopenharmony_ci  v8::Local<v8::Context> m_context;
1921cb0ef41Sopenharmony_ci};
1931cb0ef41Sopenharmony_ci
1941cb0ef41Sopenharmony_ci}  // namespace
1951cb0ef41Sopenharmony_ci
1961cb0ef41Sopenharmony_ciV8ConsoleMessage::V8ConsoleMessage(V8MessageOrigin origin, double timestamp,
1971cb0ef41Sopenharmony_ci                                   const String16& message)
1981cb0ef41Sopenharmony_ci    : m_origin(origin),
1991cb0ef41Sopenharmony_ci      m_timestamp(timestamp),
2001cb0ef41Sopenharmony_ci      m_message(message),
2011cb0ef41Sopenharmony_ci      m_lineNumber(0),
2021cb0ef41Sopenharmony_ci      m_columnNumber(0),
2031cb0ef41Sopenharmony_ci      m_scriptId(0),
2041cb0ef41Sopenharmony_ci      m_contextId(0),
2051cb0ef41Sopenharmony_ci      m_type(ConsoleAPIType::kLog),
2061cb0ef41Sopenharmony_ci      m_exceptionId(0),
2071cb0ef41Sopenharmony_ci      m_revokedExceptionId(0) {}
2081cb0ef41Sopenharmony_ci
2091cb0ef41Sopenharmony_ciV8ConsoleMessage::~V8ConsoleMessage() = default;
2101cb0ef41Sopenharmony_ci
2111cb0ef41Sopenharmony_civoid V8ConsoleMessage::setLocation(const String16& url, unsigned lineNumber,
2121cb0ef41Sopenharmony_ci                                   unsigned columnNumber,
2131cb0ef41Sopenharmony_ci                                   std::unique_ptr<V8StackTraceImpl> stackTrace,
2141cb0ef41Sopenharmony_ci                                   int scriptId) {
2151cb0ef41Sopenharmony_ci  const char* dataURIPrefix = "data:";
2161cb0ef41Sopenharmony_ci  if (url.substring(0, strlen(dataURIPrefix)) == dataURIPrefix) {
2171cb0ef41Sopenharmony_ci    m_url = String16();
2181cb0ef41Sopenharmony_ci  } else {
2191cb0ef41Sopenharmony_ci    m_url = url;
2201cb0ef41Sopenharmony_ci  }
2211cb0ef41Sopenharmony_ci  m_lineNumber = lineNumber;
2221cb0ef41Sopenharmony_ci  m_columnNumber = columnNumber;
2231cb0ef41Sopenharmony_ci  m_stackTrace = std::move(stackTrace);
2241cb0ef41Sopenharmony_ci  m_scriptId = scriptId;
2251cb0ef41Sopenharmony_ci}
2261cb0ef41Sopenharmony_ci
2271cb0ef41Sopenharmony_civoid V8ConsoleMessage::reportToFrontend(
2281cb0ef41Sopenharmony_ci    protocol::Console::Frontend* frontend) const {
2291cb0ef41Sopenharmony_ci  DCHECK_EQ(V8MessageOrigin::kConsole, m_origin);
2301cb0ef41Sopenharmony_ci  String16 level = protocol::Console::ConsoleMessage::LevelEnum::Log;
2311cb0ef41Sopenharmony_ci  if (m_type == ConsoleAPIType::kDebug || m_type == ConsoleAPIType::kCount ||
2321cb0ef41Sopenharmony_ci      m_type == ConsoleAPIType::kTimeEnd)
2331cb0ef41Sopenharmony_ci    level = protocol::Console::ConsoleMessage::LevelEnum::Debug;
2341cb0ef41Sopenharmony_ci  else if (m_type == ConsoleAPIType::kError ||
2351cb0ef41Sopenharmony_ci           m_type == ConsoleAPIType::kAssert)
2361cb0ef41Sopenharmony_ci    level = protocol::Console::ConsoleMessage::LevelEnum::Error;
2371cb0ef41Sopenharmony_ci  else if (m_type == ConsoleAPIType::kWarning)
2381cb0ef41Sopenharmony_ci    level = protocol::Console::ConsoleMessage::LevelEnum::Warning;
2391cb0ef41Sopenharmony_ci  else if (m_type == ConsoleAPIType::kInfo)
2401cb0ef41Sopenharmony_ci    level = protocol::Console::ConsoleMessage::LevelEnum::Info;
2411cb0ef41Sopenharmony_ci  std::unique_ptr<protocol::Console::ConsoleMessage> result =
2421cb0ef41Sopenharmony_ci      protocol::Console::ConsoleMessage::create()
2431cb0ef41Sopenharmony_ci          .setSource(protocol::Console::ConsoleMessage::SourceEnum::ConsoleApi)
2441cb0ef41Sopenharmony_ci          .setLevel(level)
2451cb0ef41Sopenharmony_ci          .setText(m_message)
2461cb0ef41Sopenharmony_ci          .build();
2471cb0ef41Sopenharmony_ci  if (m_lineNumber) result->setLine(m_lineNumber);
2481cb0ef41Sopenharmony_ci  if (m_columnNumber) result->setColumn(m_columnNumber);
2491cb0ef41Sopenharmony_ci  if (!m_url.isEmpty()) result->setUrl(m_url);
2501cb0ef41Sopenharmony_ci  frontend->messageAdded(std::move(result));
2511cb0ef41Sopenharmony_ci}
2521cb0ef41Sopenharmony_ci
2531cb0ef41Sopenharmony_cistd::unique_ptr<protocol::Array<protocol::Runtime::RemoteObject>>
2541cb0ef41Sopenharmony_ciV8ConsoleMessage::wrapArguments(V8InspectorSessionImpl* session,
2551cb0ef41Sopenharmony_ci                                bool generatePreview) const {
2561cb0ef41Sopenharmony_ci  V8InspectorImpl* inspector = session->inspector();
2571cb0ef41Sopenharmony_ci  int contextGroupId = session->contextGroupId();
2581cb0ef41Sopenharmony_ci  int contextId = m_contextId;
2591cb0ef41Sopenharmony_ci  if (!m_arguments.size() || !contextId) return nullptr;
2601cb0ef41Sopenharmony_ci  InspectedContext* inspectedContext =
2611cb0ef41Sopenharmony_ci      inspector->getContext(contextGroupId, contextId);
2621cb0ef41Sopenharmony_ci  if (!inspectedContext) return nullptr;
2631cb0ef41Sopenharmony_ci
2641cb0ef41Sopenharmony_ci  v8::Isolate* isolate = inspectedContext->isolate();
2651cb0ef41Sopenharmony_ci  v8::HandleScope handles(isolate);
2661cb0ef41Sopenharmony_ci  v8::Local<v8::Context> context = inspectedContext->context();
2671cb0ef41Sopenharmony_ci
2681cb0ef41Sopenharmony_ci  auto args =
2691cb0ef41Sopenharmony_ci      std::make_unique<protocol::Array<protocol::Runtime::RemoteObject>>();
2701cb0ef41Sopenharmony_ci
2711cb0ef41Sopenharmony_ci  v8::Local<v8::Value> value = m_arguments[0]->Get(isolate);
2721cb0ef41Sopenharmony_ci  if (value->IsObject() && m_type == ConsoleAPIType::kTable &&
2731cb0ef41Sopenharmony_ci      generatePreview) {
2741cb0ef41Sopenharmony_ci    v8::MaybeLocal<v8::Array> columns;
2751cb0ef41Sopenharmony_ci    if (m_arguments.size() > 1) {
2761cb0ef41Sopenharmony_ci      v8::Local<v8::Value> secondArgument = m_arguments[1]->Get(isolate);
2771cb0ef41Sopenharmony_ci      if (secondArgument->IsArray()) {
2781cb0ef41Sopenharmony_ci        columns = secondArgument.As<v8::Array>();
2791cb0ef41Sopenharmony_ci      } else if (secondArgument->IsString()) {
2801cb0ef41Sopenharmony_ci        v8::TryCatch tryCatch(isolate);
2811cb0ef41Sopenharmony_ci        v8::Local<v8::Array> array = v8::Array::New(isolate);
2821cb0ef41Sopenharmony_ci        if (array->Set(context, 0, secondArgument).IsJust()) {
2831cb0ef41Sopenharmony_ci          columns = array;
2841cb0ef41Sopenharmony_ci        }
2851cb0ef41Sopenharmony_ci      }
2861cb0ef41Sopenharmony_ci    }
2871cb0ef41Sopenharmony_ci    std::unique_ptr<protocol::Runtime::RemoteObject> wrapped =
2881cb0ef41Sopenharmony_ci        session->wrapTable(context, value.As<v8::Object>(), columns);
2891cb0ef41Sopenharmony_ci    inspectedContext = inspector->getContext(contextGroupId, contextId);
2901cb0ef41Sopenharmony_ci    if (!inspectedContext) return nullptr;
2911cb0ef41Sopenharmony_ci    if (wrapped) {
2921cb0ef41Sopenharmony_ci      args->emplace_back(std::move(wrapped));
2931cb0ef41Sopenharmony_ci    } else {
2941cb0ef41Sopenharmony_ci      args = nullptr;
2951cb0ef41Sopenharmony_ci    }
2961cb0ef41Sopenharmony_ci  } else {
2971cb0ef41Sopenharmony_ci    for (size_t i = 0; i < m_arguments.size(); ++i) {
2981cb0ef41Sopenharmony_ci      std::unique_ptr<protocol::Runtime::RemoteObject> wrapped =
2991cb0ef41Sopenharmony_ci          session->wrapObject(context, m_arguments[i]->Get(isolate), "console",
3001cb0ef41Sopenharmony_ci                              generatePreview);
3011cb0ef41Sopenharmony_ci      inspectedContext = inspector->getContext(contextGroupId, contextId);
3021cb0ef41Sopenharmony_ci      if (!inspectedContext) return nullptr;
3031cb0ef41Sopenharmony_ci      if (!wrapped) {
3041cb0ef41Sopenharmony_ci        args = nullptr;
3051cb0ef41Sopenharmony_ci        break;
3061cb0ef41Sopenharmony_ci      }
3071cb0ef41Sopenharmony_ci      args->emplace_back(std::move(wrapped));
3081cb0ef41Sopenharmony_ci    }
3091cb0ef41Sopenharmony_ci  }
3101cb0ef41Sopenharmony_ci  return args;
3111cb0ef41Sopenharmony_ci}
3121cb0ef41Sopenharmony_ci
3131cb0ef41Sopenharmony_civoid V8ConsoleMessage::reportToFrontend(protocol::Runtime::Frontend* frontend,
3141cb0ef41Sopenharmony_ci                                        V8InspectorSessionImpl* session,
3151cb0ef41Sopenharmony_ci                                        bool generatePreview) const {
3161cb0ef41Sopenharmony_ci  int contextGroupId = session->contextGroupId();
3171cb0ef41Sopenharmony_ci  V8InspectorImpl* inspector = session->inspector();
3181cb0ef41Sopenharmony_ci
3191cb0ef41Sopenharmony_ci  if (m_origin == V8MessageOrigin::kException) {
3201cb0ef41Sopenharmony_ci    std::unique_ptr<protocol::Runtime::RemoteObject> exception =
3211cb0ef41Sopenharmony_ci        wrapException(session, generatePreview);
3221cb0ef41Sopenharmony_ci    if (!inspector->hasConsoleMessageStorage(contextGroupId)) return;
3231cb0ef41Sopenharmony_ci    std::unique_ptr<protocol::Runtime::ExceptionDetails> exceptionDetails =
3241cb0ef41Sopenharmony_ci        protocol::Runtime::ExceptionDetails::create()
3251cb0ef41Sopenharmony_ci            .setExceptionId(m_exceptionId)
3261cb0ef41Sopenharmony_ci            .setText(exception ? m_message : m_detailedMessage)
3271cb0ef41Sopenharmony_ci            .setLineNumber(m_lineNumber ? m_lineNumber - 1 : 0)
3281cb0ef41Sopenharmony_ci            .setColumnNumber(m_columnNumber ? m_columnNumber - 1 : 0)
3291cb0ef41Sopenharmony_ci            .build();
3301cb0ef41Sopenharmony_ci    if (m_scriptId)
3311cb0ef41Sopenharmony_ci      exceptionDetails->setScriptId(String16::fromInteger(m_scriptId));
3321cb0ef41Sopenharmony_ci    if (!m_url.isEmpty()) exceptionDetails->setUrl(m_url);
3331cb0ef41Sopenharmony_ci    if (m_stackTrace) {
3341cb0ef41Sopenharmony_ci      exceptionDetails->setStackTrace(
3351cb0ef41Sopenharmony_ci          m_stackTrace->buildInspectorObjectImpl(inspector->debugger()));
3361cb0ef41Sopenharmony_ci    }
3371cb0ef41Sopenharmony_ci    if (m_contextId) exceptionDetails->setExecutionContextId(m_contextId);
3381cb0ef41Sopenharmony_ci    if (exception) exceptionDetails->setException(std::move(exception));
3391cb0ef41Sopenharmony_ci    std::unique_ptr<protocol::DictionaryValue> data =
3401cb0ef41Sopenharmony_ci        getAssociatedExceptionData(inspector, session);
3411cb0ef41Sopenharmony_ci    if (data) exceptionDetails->setExceptionMetaData(std::move(data));
3421cb0ef41Sopenharmony_ci    frontend->exceptionThrown(m_timestamp, std::move(exceptionDetails));
3431cb0ef41Sopenharmony_ci    return;
3441cb0ef41Sopenharmony_ci  }
3451cb0ef41Sopenharmony_ci  if (m_origin == V8MessageOrigin::kRevokedException) {
3461cb0ef41Sopenharmony_ci    frontend->exceptionRevoked(m_message, m_revokedExceptionId);
3471cb0ef41Sopenharmony_ci    return;
3481cb0ef41Sopenharmony_ci  }
3491cb0ef41Sopenharmony_ci  if (m_origin == V8MessageOrigin::kConsole) {
3501cb0ef41Sopenharmony_ci    std::unique_ptr<protocol::Array<protocol::Runtime::RemoteObject>>
3511cb0ef41Sopenharmony_ci        arguments = wrapArguments(session, generatePreview);
3521cb0ef41Sopenharmony_ci    if (!inspector->hasConsoleMessageStorage(contextGroupId)) return;
3531cb0ef41Sopenharmony_ci    if (!arguments) {
3541cb0ef41Sopenharmony_ci      arguments =
3551cb0ef41Sopenharmony_ci          std::make_unique<protocol::Array<protocol::Runtime::RemoteObject>>();
3561cb0ef41Sopenharmony_ci      if (!m_message.isEmpty()) {
3571cb0ef41Sopenharmony_ci        std::unique_ptr<protocol::Runtime::RemoteObject> messageArg =
3581cb0ef41Sopenharmony_ci            protocol::Runtime::RemoteObject::create()
3591cb0ef41Sopenharmony_ci                .setType(protocol::Runtime::RemoteObject::TypeEnum::String)
3601cb0ef41Sopenharmony_ci                .build();
3611cb0ef41Sopenharmony_ci        messageArg->setValue(protocol::StringValue::create(m_message));
3621cb0ef41Sopenharmony_ci        arguments->emplace_back(std::move(messageArg));
3631cb0ef41Sopenharmony_ci      }
3641cb0ef41Sopenharmony_ci    }
3651cb0ef41Sopenharmony_ci    Maybe<String16> consoleContext;
3661cb0ef41Sopenharmony_ci    if (!m_consoleContext.isEmpty()) consoleContext = m_consoleContext;
3671cb0ef41Sopenharmony_ci    std::unique_ptr<protocol::Runtime::StackTrace> stackTrace;
3681cb0ef41Sopenharmony_ci    if (m_stackTrace) {
3691cb0ef41Sopenharmony_ci      switch (m_type) {
3701cb0ef41Sopenharmony_ci        case ConsoleAPIType::kAssert:
3711cb0ef41Sopenharmony_ci        case ConsoleAPIType::kError:
3721cb0ef41Sopenharmony_ci        case ConsoleAPIType::kTrace:
3731cb0ef41Sopenharmony_ci        case ConsoleAPIType::kWarning:
3741cb0ef41Sopenharmony_ci          stackTrace =
3751cb0ef41Sopenharmony_ci              m_stackTrace->buildInspectorObjectImpl(inspector->debugger());
3761cb0ef41Sopenharmony_ci          break;
3771cb0ef41Sopenharmony_ci        default:
3781cb0ef41Sopenharmony_ci          stackTrace =
3791cb0ef41Sopenharmony_ci              m_stackTrace->buildInspectorObjectImpl(inspector->debugger(), 0);
3801cb0ef41Sopenharmony_ci          break;
3811cb0ef41Sopenharmony_ci      }
3821cb0ef41Sopenharmony_ci    }
3831cb0ef41Sopenharmony_ci    frontend->consoleAPICalled(
3841cb0ef41Sopenharmony_ci        consoleAPITypeValue(m_type), std::move(arguments), m_contextId,
3851cb0ef41Sopenharmony_ci        m_timestamp, std::move(stackTrace), std::move(consoleContext));
3861cb0ef41Sopenharmony_ci    return;
3871cb0ef41Sopenharmony_ci  }
3881cb0ef41Sopenharmony_ci  UNREACHABLE();
3891cb0ef41Sopenharmony_ci}
3901cb0ef41Sopenharmony_ci
3911cb0ef41Sopenharmony_cistd::unique_ptr<protocol::DictionaryValue>
3921cb0ef41Sopenharmony_ciV8ConsoleMessage::getAssociatedExceptionData(
3931cb0ef41Sopenharmony_ci    V8InspectorImpl* inspector, V8InspectorSessionImpl* session) const {
3941cb0ef41Sopenharmony_ci  if (!m_arguments.size() || !m_contextId) return nullptr;
3951cb0ef41Sopenharmony_ci  DCHECK_EQ(1u, m_arguments.size());
3961cb0ef41Sopenharmony_ci
3971cb0ef41Sopenharmony_ci  v8::Isolate* isolate = inspector->isolate();
3981cb0ef41Sopenharmony_ci  v8::HandleScope handles(isolate);
3991cb0ef41Sopenharmony_ci  v8::MaybeLocal<v8::Value> maybe_exception = m_arguments[0]->Get(isolate);
4001cb0ef41Sopenharmony_ci  v8::Local<v8::Value> exception;
4011cb0ef41Sopenharmony_ci  if (!maybe_exception.ToLocal(&exception)) return nullptr;
4021cb0ef41Sopenharmony_ci
4031cb0ef41Sopenharmony_ci  return inspector->getAssociatedExceptionDataForProtocol(exception);
4041cb0ef41Sopenharmony_ci}
4051cb0ef41Sopenharmony_ci
4061cb0ef41Sopenharmony_cistd::unique_ptr<protocol::Runtime::RemoteObject>
4071cb0ef41Sopenharmony_ciV8ConsoleMessage::wrapException(V8InspectorSessionImpl* session,
4081cb0ef41Sopenharmony_ci                                bool generatePreview) const {
4091cb0ef41Sopenharmony_ci  if (!m_arguments.size() || !m_contextId) return nullptr;
4101cb0ef41Sopenharmony_ci  DCHECK_EQ(1u, m_arguments.size());
4111cb0ef41Sopenharmony_ci  InspectedContext* inspectedContext =
4121cb0ef41Sopenharmony_ci      session->inspector()->getContext(session->contextGroupId(), m_contextId);
4131cb0ef41Sopenharmony_ci  if (!inspectedContext) return nullptr;
4141cb0ef41Sopenharmony_ci
4151cb0ef41Sopenharmony_ci  v8::Isolate* isolate = inspectedContext->isolate();
4161cb0ef41Sopenharmony_ci  v8::HandleScope handles(isolate);
4171cb0ef41Sopenharmony_ci  // TODO(dgozman): should we use different object group?
4181cb0ef41Sopenharmony_ci  return session->wrapObject(inspectedContext->context(),
4191cb0ef41Sopenharmony_ci                             m_arguments[0]->Get(isolate), "console",
4201cb0ef41Sopenharmony_ci                             generatePreview);
4211cb0ef41Sopenharmony_ci}
4221cb0ef41Sopenharmony_ci
4231cb0ef41Sopenharmony_ciV8MessageOrigin V8ConsoleMessage::origin() const { return m_origin; }
4241cb0ef41Sopenharmony_ci
4251cb0ef41Sopenharmony_ciConsoleAPIType V8ConsoleMessage::type() const { return m_type; }
4261cb0ef41Sopenharmony_ci
4271cb0ef41Sopenharmony_ci// static
4281cb0ef41Sopenharmony_cistd::unique_ptr<V8ConsoleMessage> V8ConsoleMessage::createForConsoleAPI(
4291cb0ef41Sopenharmony_ci    v8::Local<v8::Context> v8Context, int contextId, int groupId,
4301cb0ef41Sopenharmony_ci    V8InspectorImpl* inspector, double timestamp, ConsoleAPIType type,
4311cb0ef41Sopenharmony_ci    const std::vector<v8::Local<v8::Value>>& arguments,
4321cb0ef41Sopenharmony_ci    const String16& consoleContext,
4331cb0ef41Sopenharmony_ci    std::unique_ptr<V8StackTraceImpl> stackTrace) {
4341cb0ef41Sopenharmony_ci  v8::Isolate* isolate = v8Context->GetIsolate();
4351cb0ef41Sopenharmony_ci
4361cb0ef41Sopenharmony_ci  std::unique_ptr<V8ConsoleMessage> message(
4371cb0ef41Sopenharmony_ci      new V8ConsoleMessage(V8MessageOrigin::kConsole, timestamp, String16()));
4381cb0ef41Sopenharmony_ci  if (stackTrace && !stackTrace->isEmpty()) {
4391cb0ef41Sopenharmony_ci    message->m_url = toString16(stackTrace->topSourceURL());
4401cb0ef41Sopenharmony_ci    message->m_lineNumber = stackTrace->topLineNumber();
4411cb0ef41Sopenharmony_ci    message->m_columnNumber = stackTrace->topColumnNumber();
4421cb0ef41Sopenharmony_ci  }
4431cb0ef41Sopenharmony_ci  message->m_stackTrace = std::move(stackTrace);
4441cb0ef41Sopenharmony_ci  message->m_consoleContext = consoleContext;
4451cb0ef41Sopenharmony_ci  message->m_type = type;
4461cb0ef41Sopenharmony_ci  message->m_contextId = contextId;
4471cb0ef41Sopenharmony_ci  for (size_t i = 0; i < arguments.size(); ++i) {
4481cb0ef41Sopenharmony_ci    std::unique_ptr<v8::Global<v8::Value>> argument(
4491cb0ef41Sopenharmony_ci        new v8::Global<v8::Value>(isolate, arguments.at(i)));
4501cb0ef41Sopenharmony_ci    argument->AnnotateStrongRetainer(kGlobalConsoleMessageHandleLabel);
4511cb0ef41Sopenharmony_ci    message->m_arguments.push_back(std::move(argument));
4521cb0ef41Sopenharmony_ci    message->m_v8Size +=
4531cb0ef41Sopenharmony_ci        v8::debug::EstimatedValueSize(isolate, arguments.at(i));
4541cb0ef41Sopenharmony_ci  }
4551cb0ef41Sopenharmony_ci  for (size_t i = 0, num_args = arguments.size(); i < num_args; ++i) {
4561cb0ef41Sopenharmony_ci    if (i) message->m_message += String16(" ");
4571cb0ef41Sopenharmony_ci    message->m_message +=
4581cb0ef41Sopenharmony_ci        V8ValueStringBuilder::toString(arguments[i], v8Context);
4591cb0ef41Sopenharmony_ci  }
4601cb0ef41Sopenharmony_ci
4611cb0ef41Sopenharmony_ci  v8::Isolate::MessageErrorLevel clientLevel = v8::Isolate::kMessageInfo;
4621cb0ef41Sopenharmony_ci  if (type == ConsoleAPIType::kDebug || type == ConsoleAPIType::kCount ||
4631cb0ef41Sopenharmony_ci      type == ConsoleAPIType::kTimeEnd) {
4641cb0ef41Sopenharmony_ci    clientLevel = v8::Isolate::kMessageDebug;
4651cb0ef41Sopenharmony_ci  } else if (type == ConsoleAPIType::kError ||
4661cb0ef41Sopenharmony_ci             type == ConsoleAPIType::kAssert) {
4671cb0ef41Sopenharmony_ci    clientLevel = v8::Isolate::kMessageError;
4681cb0ef41Sopenharmony_ci  } else if (type == ConsoleAPIType::kWarning) {
4691cb0ef41Sopenharmony_ci    clientLevel = v8::Isolate::kMessageWarning;
4701cb0ef41Sopenharmony_ci  } else if (type == ConsoleAPIType::kInfo) {
4711cb0ef41Sopenharmony_ci    clientLevel = v8::Isolate::kMessageInfo;
4721cb0ef41Sopenharmony_ci  } else if (type == ConsoleAPIType::kLog) {
4731cb0ef41Sopenharmony_ci    clientLevel = v8::Isolate::kMessageLog;
4741cb0ef41Sopenharmony_ci  }
4751cb0ef41Sopenharmony_ci
4761cb0ef41Sopenharmony_ci  if (type != ConsoleAPIType::kClear) {
4771cb0ef41Sopenharmony_ci    inspector->client()->consoleAPIMessage(
4781cb0ef41Sopenharmony_ci        groupId, clientLevel, toStringView(message->m_message),
4791cb0ef41Sopenharmony_ci        toStringView(message->m_url), message->m_lineNumber,
4801cb0ef41Sopenharmony_ci        message->m_columnNumber, message->m_stackTrace.get());
4811cb0ef41Sopenharmony_ci  }
4821cb0ef41Sopenharmony_ci
4831cb0ef41Sopenharmony_ci  return message;
4841cb0ef41Sopenharmony_ci}
4851cb0ef41Sopenharmony_ci
4861cb0ef41Sopenharmony_ci// static
4871cb0ef41Sopenharmony_cistd::unique_ptr<V8ConsoleMessage> V8ConsoleMessage::createForException(
4881cb0ef41Sopenharmony_ci    double timestamp, const String16& detailedMessage, const String16& url,
4891cb0ef41Sopenharmony_ci    unsigned lineNumber, unsigned columnNumber,
4901cb0ef41Sopenharmony_ci    std::unique_ptr<V8StackTraceImpl> stackTrace, int scriptId,
4911cb0ef41Sopenharmony_ci    v8::Isolate* isolate, const String16& message, int contextId,
4921cb0ef41Sopenharmony_ci    v8::Local<v8::Value> exception, unsigned exceptionId) {
4931cb0ef41Sopenharmony_ci  std::unique_ptr<V8ConsoleMessage> consoleMessage(
4941cb0ef41Sopenharmony_ci      new V8ConsoleMessage(V8MessageOrigin::kException, timestamp, message));
4951cb0ef41Sopenharmony_ci  consoleMessage->setLocation(url, lineNumber, columnNumber,
4961cb0ef41Sopenharmony_ci                              std::move(stackTrace), scriptId);
4971cb0ef41Sopenharmony_ci  consoleMessage->m_exceptionId = exceptionId;
4981cb0ef41Sopenharmony_ci  consoleMessage->m_detailedMessage = detailedMessage;
4991cb0ef41Sopenharmony_ci  if (contextId && !exception.IsEmpty()) {
5001cb0ef41Sopenharmony_ci    consoleMessage->m_contextId = contextId;
5011cb0ef41Sopenharmony_ci    consoleMessage->m_arguments.push_back(
5021cb0ef41Sopenharmony_ci        std::unique_ptr<v8::Global<v8::Value>>(
5031cb0ef41Sopenharmony_ci            new v8::Global<v8::Value>(isolate, exception)));
5041cb0ef41Sopenharmony_ci    consoleMessage->m_v8Size +=
5051cb0ef41Sopenharmony_ci        v8::debug::EstimatedValueSize(isolate, exception);
5061cb0ef41Sopenharmony_ci  }
5071cb0ef41Sopenharmony_ci  return consoleMessage;
5081cb0ef41Sopenharmony_ci}
5091cb0ef41Sopenharmony_ci
5101cb0ef41Sopenharmony_ci// static
5111cb0ef41Sopenharmony_cistd::unique_ptr<V8ConsoleMessage> V8ConsoleMessage::createForRevokedException(
5121cb0ef41Sopenharmony_ci    double timestamp, const String16& messageText,
5131cb0ef41Sopenharmony_ci    unsigned revokedExceptionId) {
5141cb0ef41Sopenharmony_ci  std::unique_ptr<V8ConsoleMessage> message(new V8ConsoleMessage(
5151cb0ef41Sopenharmony_ci      V8MessageOrigin::kRevokedException, timestamp, messageText));
5161cb0ef41Sopenharmony_ci  message->m_revokedExceptionId = revokedExceptionId;
5171cb0ef41Sopenharmony_ci  return message;
5181cb0ef41Sopenharmony_ci}
5191cb0ef41Sopenharmony_ci
5201cb0ef41Sopenharmony_civoid V8ConsoleMessage::contextDestroyed(int contextId) {
5211cb0ef41Sopenharmony_ci  if (contextId != m_contextId) return;
5221cb0ef41Sopenharmony_ci  m_contextId = 0;
5231cb0ef41Sopenharmony_ci  if (m_message.isEmpty()) m_message = "<message collected>";
5241cb0ef41Sopenharmony_ci  Arguments empty;
5251cb0ef41Sopenharmony_ci  m_arguments.swap(empty);
5261cb0ef41Sopenharmony_ci  m_v8Size = 0;
5271cb0ef41Sopenharmony_ci}
5281cb0ef41Sopenharmony_ci
5291cb0ef41Sopenharmony_ci// ------------------------ V8ConsoleMessageStorage
5301cb0ef41Sopenharmony_ci// ----------------------------
5311cb0ef41Sopenharmony_ci
5321cb0ef41Sopenharmony_ciV8ConsoleMessageStorage::V8ConsoleMessageStorage(V8InspectorImpl* inspector,
5331cb0ef41Sopenharmony_ci                                                 int contextGroupId)
5341cb0ef41Sopenharmony_ci    : m_inspector(inspector), m_contextGroupId(contextGroupId) {}
5351cb0ef41Sopenharmony_ci
5361cb0ef41Sopenharmony_ciV8ConsoleMessageStorage::~V8ConsoleMessageStorage() { clear(); }
5371cb0ef41Sopenharmony_ci
5381cb0ef41Sopenharmony_cinamespace {
5391cb0ef41Sopenharmony_ci
5401cb0ef41Sopenharmony_civoid TraceV8ConsoleMessageEvent(V8MessageOrigin origin, ConsoleAPIType type) {
5411cb0ef41Sopenharmony_ci  // Change in this function requires adjustment of Catapult/Telemetry metric
5421cb0ef41Sopenharmony_ci  // tracing/tracing/metrics/console_error_metric.html.
5431cb0ef41Sopenharmony_ci  // See https://crbug.com/880432
5441cb0ef41Sopenharmony_ci  if (origin == V8MessageOrigin::kException) {
5451cb0ef41Sopenharmony_ci    TRACE_EVENT_INSTANT0("v8.console", "V8ConsoleMessage::Exception",
5461cb0ef41Sopenharmony_ci                         TRACE_EVENT_SCOPE_THREAD);
5471cb0ef41Sopenharmony_ci  } else if (type == ConsoleAPIType::kError) {
5481cb0ef41Sopenharmony_ci    TRACE_EVENT_INSTANT0("v8.console", "V8ConsoleMessage::Error",
5491cb0ef41Sopenharmony_ci                         TRACE_EVENT_SCOPE_THREAD);
5501cb0ef41Sopenharmony_ci  } else if (type == ConsoleAPIType::kAssert) {
5511cb0ef41Sopenharmony_ci    TRACE_EVENT_INSTANT0("v8.console", "V8ConsoleMessage::Assert",
5521cb0ef41Sopenharmony_ci                         TRACE_EVENT_SCOPE_THREAD);
5531cb0ef41Sopenharmony_ci  }
5541cb0ef41Sopenharmony_ci}
5551cb0ef41Sopenharmony_ci
5561cb0ef41Sopenharmony_ci}  // anonymous namespace
5571cb0ef41Sopenharmony_ci
5581cb0ef41Sopenharmony_civoid V8ConsoleMessageStorage::addMessage(
5591cb0ef41Sopenharmony_ci    std::unique_ptr<V8ConsoleMessage> message) {
5601cb0ef41Sopenharmony_ci  int contextGroupId = m_contextGroupId;
5611cb0ef41Sopenharmony_ci  V8InspectorImpl* inspector = m_inspector;
5621cb0ef41Sopenharmony_ci  if (message->type() == ConsoleAPIType::kClear) clear();
5631cb0ef41Sopenharmony_ci
5641cb0ef41Sopenharmony_ci  TraceV8ConsoleMessageEvent(message->origin(), message->type());
5651cb0ef41Sopenharmony_ci
5661cb0ef41Sopenharmony_ci  inspector->forEachSession(
5671cb0ef41Sopenharmony_ci      contextGroupId, [&message](V8InspectorSessionImpl* session) {
5681cb0ef41Sopenharmony_ci        if (message->origin() == V8MessageOrigin::kConsole)
5691cb0ef41Sopenharmony_ci          session->consoleAgent()->messageAdded(message.get());
5701cb0ef41Sopenharmony_ci        session->runtimeAgent()->messageAdded(message.get());
5711cb0ef41Sopenharmony_ci      });
5721cb0ef41Sopenharmony_ci  if (!inspector->hasConsoleMessageStorage(contextGroupId)) return;
5731cb0ef41Sopenharmony_ci
5741cb0ef41Sopenharmony_ci  DCHECK(m_messages.size() <= maxConsoleMessageCount);
5751cb0ef41Sopenharmony_ci  if (m_messages.size() == maxConsoleMessageCount) {
5761cb0ef41Sopenharmony_ci    m_estimatedSize -= m_messages.front()->estimatedSize();
5771cb0ef41Sopenharmony_ci    m_messages.pop_front();
5781cb0ef41Sopenharmony_ci  }
5791cb0ef41Sopenharmony_ci  while (m_estimatedSize + message->estimatedSize() > maxConsoleMessageV8Size &&
5801cb0ef41Sopenharmony_ci         !m_messages.empty()) {
5811cb0ef41Sopenharmony_ci    m_estimatedSize -= m_messages.front()->estimatedSize();
5821cb0ef41Sopenharmony_ci    m_messages.pop_front();
5831cb0ef41Sopenharmony_ci  }
5841cb0ef41Sopenharmony_ci
5851cb0ef41Sopenharmony_ci  m_messages.push_back(std::move(message));
5861cb0ef41Sopenharmony_ci  m_estimatedSize += m_messages.back()->estimatedSize();
5871cb0ef41Sopenharmony_ci}
5881cb0ef41Sopenharmony_ci
5891cb0ef41Sopenharmony_civoid V8ConsoleMessageStorage::clear() {
5901cb0ef41Sopenharmony_ci  m_messages.clear();
5911cb0ef41Sopenharmony_ci  m_estimatedSize = 0;
5921cb0ef41Sopenharmony_ci  m_inspector->forEachSession(m_contextGroupId,
5931cb0ef41Sopenharmony_ci                              [](V8InspectorSessionImpl* session) {
5941cb0ef41Sopenharmony_ci                                session->releaseObjectGroup("console");
5951cb0ef41Sopenharmony_ci                              });
5961cb0ef41Sopenharmony_ci  m_data.clear();
5971cb0ef41Sopenharmony_ci}
5981cb0ef41Sopenharmony_ci
5991cb0ef41Sopenharmony_cibool V8ConsoleMessageStorage::shouldReportDeprecationMessage(
6001cb0ef41Sopenharmony_ci    int contextId, const String16& method) {
6011cb0ef41Sopenharmony_ci  std::set<String16>& reportedDeprecationMessages =
6021cb0ef41Sopenharmony_ci      m_data[contextId].m_reportedDeprecationMessages;
6031cb0ef41Sopenharmony_ci  auto it = reportedDeprecationMessages.find(method);
6041cb0ef41Sopenharmony_ci  if (it != reportedDeprecationMessages.end()) return false;
6051cb0ef41Sopenharmony_ci  reportedDeprecationMessages.insert(it, method);
6061cb0ef41Sopenharmony_ci  return true;
6071cb0ef41Sopenharmony_ci}
6081cb0ef41Sopenharmony_ci
6091cb0ef41Sopenharmony_ciint V8ConsoleMessageStorage::count(int contextId, const String16& id) {
6101cb0ef41Sopenharmony_ci  return ++m_data[contextId].m_count[id];
6111cb0ef41Sopenharmony_ci}
6121cb0ef41Sopenharmony_ci
6131cb0ef41Sopenharmony_civoid V8ConsoleMessageStorage::time(int contextId, const String16& id) {
6141cb0ef41Sopenharmony_ci  m_data[contextId].m_time[id] = m_inspector->client()->currentTimeMS();
6151cb0ef41Sopenharmony_ci}
6161cb0ef41Sopenharmony_ci
6171cb0ef41Sopenharmony_cibool V8ConsoleMessageStorage::countReset(int contextId, const String16& id) {
6181cb0ef41Sopenharmony_ci  std::map<String16, int>& count_map = m_data[contextId].m_count;
6191cb0ef41Sopenharmony_ci  if (count_map.find(id) == count_map.end()) return false;
6201cb0ef41Sopenharmony_ci
6211cb0ef41Sopenharmony_ci  count_map[id] = 0;
6221cb0ef41Sopenharmony_ci  return true;
6231cb0ef41Sopenharmony_ci}
6241cb0ef41Sopenharmony_ci
6251cb0ef41Sopenharmony_cidouble V8ConsoleMessageStorage::timeLog(int contextId, const String16& id) {
6261cb0ef41Sopenharmony_ci  std::map<String16, double>& time = m_data[contextId].m_time;
6271cb0ef41Sopenharmony_ci  auto it = time.find(id);
6281cb0ef41Sopenharmony_ci  if (it == time.end()) return 0.0;
6291cb0ef41Sopenharmony_ci  return m_inspector->client()->currentTimeMS() - it->second;
6301cb0ef41Sopenharmony_ci}
6311cb0ef41Sopenharmony_ci
6321cb0ef41Sopenharmony_cidouble V8ConsoleMessageStorage::timeEnd(int contextId, const String16& id) {
6331cb0ef41Sopenharmony_ci  std::map<String16, double>& time = m_data[contextId].m_time;
6341cb0ef41Sopenharmony_ci  auto it = time.find(id);
6351cb0ef41Sopenharmony_ci  if (it == time.end()) return 0.0;
6361cb0ef41Sopenharmony_ci  double elapsed = m_inspector->client()->currentTimeMS() - it->second;
6371cb0ef41Sopenharmony_ci  time.erase(it);
6381cb0ef41Sopenharmony_ci  return elapsed;
6391cb0ef41Sopenharmony_ci}
6401cb0ef41Sopenharmony_ci
6411cb0ef41Sopenharmony_cibool V8ConsoleMessageStorage::hasTimer(int contextId, const String16& id) {
6421cb0ef41Sopenharmony_ci  const std::map<String16, double>& time = m_data[contextId].m_time;
6431cb0ef41Sopenharmony_ci  return time.find(id) != time.end();
6441cb0ef41Sopenharmony_ci}
6451cb0ef41Sopenharmony_ci
6461cb0ef41Sopenharmony_civoid V8ConsoleMessageStorage::contextDestroyed(int contextId) {
6471cb0ef41Sopenharmony_ci  m_estimatedSize = 0;
6481cb0ef41Sopenharmony_ci  for (size_t i = 0; i < m_messages.size(); ++i) {
6491cb0ef41Sopenharmony_ci    m_messages[i]->contextDestroyed(contextId);
6501cb0ef41Sopenharmony_ci    m_estimatedSize += m_messages[i]->estimatedSize();
6511cb0ef41Sopenharmony_ci  }
6521cb0ef41Sopenharmony_ci  auto it = m_data.find(contextId);
6531cb0ef41Sopenharmony_ci  if (it != m_data.end()) m_data.erase(contextId);
6541cb0ef41Sopenharmony_ci}
6551cb0ef41Sopenharmony_ci
6561cb0ef41Sopenharmony_ci}  // namespace v8_inspector
657