2 * Copyright (C) 2014 Apple Inc. All rights reserved.
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the
11 * documentation and/or other materials provided with the distribution.
13 * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
18 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
19 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
20 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 #include "JSConsoleClient.h"
31 #include "InspectorConsoleAgent.h"
32 #include "InspectorProfilerAgent.h"
33 #include "ScriptArguments.h"
34 #include "ScriptCallStack.h"
35 #include "ScriptCallStackFactory.h"
38 #include <CoreFoundation/CoreFoundation.h>
45 static bool sLogToSystemConsole
= false;
47 bool JSConsoleClient::logToSystemConsole()
49 return sLogToSystemConsole
;
52 void JSConsoleClient::setLogToSystemConsole(bool shouldLog
)
54 sLogToSystemConsole
= shouldLog
;
57 void JSConsoleClient::initializeLogToSystemConsole()
60 sLogToSystemConsole
= true;
62 Boolean keyExistsAndHasValidFormat
= false;
63 Boolean preference
= CFPreferencesGetAppBooleanValue(CFSTR("JavaScriptCoreOutputConsoleMessagesToSystemConsole"), kCFPreferencesCurrentApplication
, &keyExistsAndHasValidFormat
);
64 if (keyExistsAndHasValidFormat
)
65 sLogToSystemConsole
= preference
;
69 JSConsoleClient::JSConsoleClient(InspectorConsoleAgent
* consoleAgent
, InspectorProfilerAgent
* profilerAgent
)
71 , m_consoleAgent(consoleAgent
)
72 , m_profilerAgent(profilerAgent
)
74 static std::once_flag initializeLogging
;
75 std::call_once(initializeLogging
, []{
76 JSConsoleClient::initializeLogToSystemConsole();
80 void JSConsoleClient::messageWithTypeAndLevel(MessageType type
, MessageLevel level
, JSC::ExecState
* exec
, PassRefPtr
<ScriptArguments
> prpArguments
)
82 RefPtr
<ScriptArguments
> arguments
= prpArguments
;
84 if (JSConsoleClient::logToSystemConsole())
85 ConsoleClient::printConsoleMessageWithArguments(MessageSource::ConsoleAPI
, type
, level
, exec
, arguments
);
88 arguments
->getFirstArgumentAsString(message
);
89 m_consoleAgent
->addMessageToConsole(MessageSource::ConsoleAPI
, type
, level
, message
, exec
, arguments
.release());
92 void JSConsoleClient::count(ExecState
* exec
, PassRefPtr
<ScriptArguments
> arguments
)
94 m_consoleAgent
->count(exec
, arguments
);
97 void JSConsoleClient::profile(JSC::ExecState
* exec
, const String
& title
)
99 if (!m_profilerAgent
->enabled())
102 String resolvedTitle
= m_profilerAgent
->startProfiling(title
);
104 RefPtr
<ScriptCallStack
> callStack(createScriptCallStackForConsole(exec
, 1));
105 m_consoleAgent
->addMessageToConsole(MessageSource::ConsoleAPI
, MessageType::Profile
, MessageLevel::Debug
, resolvedTitle
, callStack
);
108 void JSConsoleClient::profileEnd(JSC::ExecState
* exec
, const String
& title
)
110 if (!m_profilerAgent
->enabled())
113 RefPtr
<JSC::Profile
> profile
= m_profilerAgent
->stopProfiling(title
);
117 RefPtr
<ScriptCallStack
> callStack(createScriptCallStackForConsole(exec
, 1));
118 String message
= makeString(profile
->title(), '#', String::number(profile
->uid()));
119 m_consoleAgent
->addMessageToConsole(MessageSource::ConsoleAPI
, MessageType::Profile
, MessageLevel::Debug
, message
, callStack
);
122 void JSConsoleClient::time(ExecState
*, const String
& title
)
124 m_consoleAgent
->startTiming(title
);
127 void JSConsoleClient::timeEnd(ExecState
* exec
, const String
& title
)
129 RefPtr
<ScriptCallStack
> callStack(createScriptCallStackForConsole(exec
, 1));
130 m_consoleAgent
->stopTiming(title
, callStack
.release());
133 void JSConsoleClient::timeStamp(ExecState
*, PassRefPtr
<ScriptArguments
>)
135 // FIXME: JSContext inspection needs a timeline.
136 warnUnimplemented(ASCIILiteral("console.timeStamp"));
139 void JSConsoleClient::warnUnimplemented(const String
& method
)
141 String message
= method
+ " is currently ignored in JavaScript context inspection.";
142 m_consoleAgent
->addMessageToConsole(MessageSource::ConsoleAPI
, MessageType::Log
, MessageLevel::Warning
, message
, nullptr, nullptr);
145 } // namespace Inspector