CSP: unsafe-eval tests timing out or failing
https://bugs.webkit.org/show_bug.cgi?id=231113
<rdar://problem/83425041>
Reviewed by Brent Fulgham.
LayoutTests/imported/w3c:
- web-platform-tests/content-security-policy/script-src/script-src-1_4-expected.txt:
- web-platform-tests/content-security-policy/script-src/script-src-1_4_1-expected.txt:
- web-platform-tests/content-security-policy/script-src/script-src-1_4_2-expected.txt:
- web-platform-tests/content-security-policy/script-src/script-src-strict_dynamic_eval-expected.txt: Added.
- web-platform-tests/content-security-policy/script-src/script-src-strict_dynamic_new_function-expected.txt: Added.
- web-platform-tests/content-security-policy/securitypolicyviolation/blockeduri-eval-expected.txt:
This test gets the report but gets an incorrect column number. The bug
seems tangential to this patch and we should fix it in a followup.
- web-platform-tests/content-security-policy/unsafe-eval/eval-blocked-and-sends-report.sub-expected.txt:
- web-platform-tests/content-security-policy/unsafe-eval/eval-blocked-in-about-blank-iframe.sub-expected.txt:
This test gets the report but reveals a bug where we don't allow
inline script to execute after calling eval() when unsafe-inline is
specified but not unsafe-eval. Tracking in rdar://83846298.
- web-platform-tests/content-security-policy/unsafe-eval/eval-blocked.sub-expected.txt:
- web-platform-tests/content-security-policy/unsafe-eval/eval-scripts-setInterval-blocked.sub-expected.txt:
- web-platform-tests/content-security-policy/unsafe-eval/eval-scripts-setTimeout-blocked.sub-expected.txt:
- web-platform-tests/content-security-policy/unsafe-eval/function-constructor-blocked.sub-expected.txt:
Source/JavaScriptCore:
Many imported unsafe-eval tests are failing because we don't report
violations to the DOM or report URI when an eval is blocked. This
patch adds support for that by calling
ContentSecurityPolicy::allowEval() when eval is disabled.
Eventually I think we can remove the evalEnabled() code and check the
CSP policy instead, but I will save that for another patch.
- API/JSAPIGlobalObject.cpp:
- API/JSAPIGlobalObject.mm:
- interpreter/Interpreter.cpp:
(JSC::eval):
- jsc.cpp:
- runtime/DirectEvalExecutable.cpp:
(JSC::DirectEvalExecutable::create):
- runtime/FunctionConstructor.cpp:
(JSC::constructFunction):
- runtime/IndirectEvalExecutable.cpp:
(JSC::IndirectEvalExecutable::create):
- runtime/JSGlobalObject.cpp:
- runtime/JSGlobalObject.h:
(JSC::JSGlobalObject::reportViolationForUnsafeEval):
Per the spec we should send the report to the element's document and
bubble it up to the window.
- runtime/JSGlobalObjectFunctions.cpp:
(JSC::JSC_DEFINE_HOST_FUNCTION):
Source/WebCore:
No new tests. This will cause existing tests to pass.
- bindings/js/JSDOMWindowBase.cpp:
(WebCore::JSDOMWindowBase::reportViolationForUnsafeEval):
Add new parameter LogToConsole to ContentSecurityPolicy::allowEval()
because in many cases we already log to console for eval violations
when we throw an error.
- bindings/js/JSDOMWindowBase.h:
- bindings/js/JSRemoteDOMWindowBase.cpp:
Per the spec, we should set the DOM target to be the element's
document. If the element is null, we set it to the window's document.
- bindings/js/JSWorkerGlobalScopeBase.cpp:
(WebCore::JSWorkerGlobalScopeBase::reportViolationForUnsafeEval):
- bindings/js/JSWorkerGlobalScopeBase.h:
- bindings/js/JSWorkletGlobalScopeBase.cpp:
(WebCore::JSWorkletGlobalScopeBase::reportViolationForUnsafeEval):
- bindings/js/JSWorkletGlobalScopeBase.h:
- page/DOMWindow.cpp:
(WebCore::DOMWindow::setTimeout):
(WebCore::DOMWindow::setInterval):
Cases where we do not log to console already, so we should do it when
we check for a violation.
- page/csp/ContentSecurityPolicy.cpp:
(WebCore::ContentSecurityPolicy::allowEval const):
(WebCore::ContentSecurityPolicy::reportViolation const):
Per the spec, the blockedURI for eval violations should be "eval".
This patch updates the blockedURI to be a string when passed to
reportViolation to allow this to happen.
(WebCore::ContentSecurityPolicy::logToConsole const):
Don't log an empty string to console. This allows us to pass an empty
string when shouldLogToConsole == LogToConsole::No so we don't need to
add an extra boolean to a lot of places to know whether to log.
- page/csp/ContentSecurityPolicy.h:
- workers/WorkerGlobalScope.cpp:
(WebCore::WorkerGlobalScope::setTimeout):
(WebCore::WorkerGlobalScope::setInterval):