Bug 1037335 - Implement security policy violation event. draft
authorChung-Sheng Fu <cfu@mozilla.com>
Tue, 17 Oct 2017 15:02:21 +0800
changeset 684630 d11b2c23763f88efcd4d0ce64fe63d14a50973fd
parent 684629 255a49b0c36175ef5226155c967d5c341f7e8e21
child 684631 9016400cbfc7621f72d1d1950297a7aa222472a4
push id85682
push userbmo:cfu@mozilla.com
push dateMon, 23 Oct 2017 09:31:26 +0000
bugs1037335
milestone58.0a1
Bug 1037335 - Implement security policy violation event. MozReview-Commit-ID: 4BYThUXduI4
dom/interfaces/security/nsIContentSecurityPolicy.idl
dom/security/nsCSPContext.cpp
dom/security/nsCSPContext.h
dom/webidl/SecurityPolicyViolationEvent.webidl
dom/webidl/moz.build
--- a/dom/interfaces/security/nsIContentSecurityPolicy.idl
+++ b/dom/interfaces/security/nsIContentSecurityPolicy.idl
@@ -1,24 +1,21 @@
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #include "nsISerializable.idl"
 #include "nsIContentPolicy.idl"
 
 interface nsIURI;
-interface nsIChannel;
 interface nsIDocShell;
 interface nsIDOMDocument;
 interface nsIDOMEventTarget;
 interface nsIEventTarget;
 interface nsIPrincipal;
-interface nsIScriptElement;
-interface nsIURI;
 
 /**
  * nsIContentSecurityPolicy
  * Describes an XPCOM component used to model and enforce CSPs.  Instances of
  * this class may have multiple policies within them, but there should only be
  * one of these per document/principal.
  */
 
--- a/dom/security/nsCSPContext.cpp
+++ b/dom/security/nsCSPContext.cpp
@@ -13,16 +13,17 @@
 #include "nsError.h"
 #include "nsIAsyncVerifyRedirectCallback.h"
 #include "nsIClassInfoImpl.h"
 #include "nsIDocShell.h"
 #include "nsIDocShellTreeItem.h"
 #include "nsIDOMHTMLDocument.h"
 #include "nsIDOMHTMLElement.h"
 #include "nsIDOMNode.h"
+#include "nsIEventTarget.h"
 #include "nsIHttpChannel.h"
 #include "nsIInterfaceRequestor.h"
 #include "nsIInterfaceRequestorUtils.h"
 #include "nsIObjectInputStream.h"
 #include "nsIObjectOutputStream.h"
 #include "nsIObserver.h"
 #include "nsIObserverService.h"
 #include "nsIStringStream.h"
@@ -36,21 +37,21 @@
 #include "nsSupportsPrimitives.h"
 #include "nsThreadUtils.h"
 #include "nsString.h"
 #include "nsScriptSecurityManager.h"
 #include "nsStringStream.h"
 #include "mozilla/Logging.h"
 #include "mozilla/dom/CSPReportBinding.h"
 #include "mozilla/dom/CSPDictionariesBinding.h"
+#include "mozilla/dom/NodeBinding.h"
 #include "mozilla/net/ReferrerPolicy.h"
 #include "nsINetworkInterceptController.h"
 #include "nsSandboxFlags.h"
 #include "nsIScriptElement.h"
-#include "nsIEventTarget.h"
 #include "mozilla/dom/DocGroup.h"
 #include "nsXULAppAPI.h"
 
 using namespace mozilla;
 
 static LogModule*
 GetCspContextLog()
 {
@@ -833,47 +834,39 @@ StripURIForReporting(nsIURI* aURI,
     aURI->GetPrePath(outStrippedURI);
     return;
   }
 
   // 3) Return uri, with any fragment component removed.
   aURI->GetSpecIgnoringRef(outStrippedURI);
 }
 
-/**
- * Sends CSP violation reports to all sources listed under report-uri.
- *
- * @param aBlockedContentSource
- *        Either a CSP Source (like 'self', as string) or nsIURI: the source
- *        of the violation.
- * @param aOriginalUri
- *        The original URI if the blocked content is a redirect, else null
- * @param aViolatedDirective
- *        the directive that was violated (string).
- * @param aSourceFile
- *        name of the file containing the inline script violation
- * @param aScriptSample
- *        a sample of the violating inline script
- * @param aLineNum
- *        source line number of the violation (if available)
- */
 nsresult
-nsCSPContext::SendReports(nsISupports* aBlockedContentSource,
-                          nsIURI* aOriginalURI,
-                          nsAString& aViolatedDirective,
-                          uint32_t aViolatedPolicyIndex,
-                          nsAString& aSourceFile,
-                          nsAString& aScriptSample,
-                          uint32_t aLineNum)
+nsCSPContext::GatherSecurityPolicyViolationEventData(
+    nsISupports* aBlockedContentSource,
+    nsIURI* aOriginalURI,
+    nsAString& aViolatedDirective,
+    uint32_t aViolatedPolicyIndex,
+    nsAString& aSourceFile,
+    nsAString& aScriptSample,
+    uint32_t aLineNum,
+    mozilla::dom::SecurityPolicyViolationEventInit& aInit)
 {
   NS_ENSURE_ARG_MAX(aViolatedPolicyIndex, mPolicies.Length() - 1);
 
-  dom::CSPReport report;
   nsresult rv;
 
+  // document-uri
+  nsAutoCString reportDocumentURI;
+  StripURIForReporting(mSelfURI, mSelfURI, reportDocumentURI);
+  aInit.mDocumentURI = NS_ConvertUTF8toUTF16(reportDocumentURI);
+
+  // referrer
+  aInit.mReferrer = mReferrer;
+
   // blocked-uri
   if (aBlockedContentSource) {
     nsAutoCString reportBlockedURI;
     nsCOMPtr<nsIURI> uri = do_QueryInterface(aBlockedContentSource);
     // could be a string or URI
     if (uri) {
       StripURIForReporting(uri, mSelfURI, reportBlockedURI);
     } else {
@@ -882,89 +875,156 @@ nsCSPContext::SendReports(nsISupports* a
         cstr->GetData(reportBlockedURI);
       }
     }
     if (reportBlockedURI.IsEmpty()) {
       // this can happen for frame-ancestors violation where the violating
       // ancestor is cross-origin.
       NS_WARNING("No blocked URI (null aBlockedContentSource) for CSP violation report.");
     }
-    report.mCsp_report.mBlocked_uri = NS_ConvertUTF8toUTF16(reportBlockedURI);
+    aInit.mBlockedURI = NS_ConvertUTF8toUTF16(reportBlockedURI);
   }
 
-  // document-uri
-  nsAutoCString reportDocumentURI;
-  StripURIForReporting(mSelfURI, mSelfURI, reportDocumentURI);
-  report.mCsp_report.mDocument_uri = NS_ConvertUTF8toUTF16(reportDocumentURI);
+  // violated-directive
+  aInit.mViolatedDirective = aViolatedDirective;
+
+  // effective-directive
+  aInit.mEffectiveDirective = aViolatedDirective;
 
   // original-policy
   nsAutoString originalPolicy;
   rv = this->GetPolicyString(aViolatedPolicyIndex, originalPolicy);
   NS_ENSURE_SUCCESS(rv, rv);
-  report.mCsp_report.mOriginal_policy = originalPolicy;
-
-  // referrer
-  if (!mReferrer.IsEmpty()) {
-    report.mCsp_report.mReferrer = mReferrer;
-  }
-
-  // violated-directive
-  report.mCsp_report.mViolated_directive = aViolatedDirective;
+  aInit.mOriginalPolicy = originalPolicy;
 
   // source-file
-  if (!aSourceFile.IsEmpty()) {
+  [&aSourceFile] () {
+    if (aSourceFile.IsEmpty()) {
+      return;
+    }
+
     // if aSourceFile is a URI, we have to make sure to strip fragments
     nsCOMPtr<nsIURI> sourceURI;
     NS_NewURI(getter_AddRefs(sourceURI), aSourceFile);
-    if (sourceURI) {
-      nsAutoCString spec;
-      sourceURI->GetSpecIgnoringRef(spec);
-      aSourceFile = NS_ConvertUTF8toUTF16(spec);
+    if (!sourceURI) {
+      return;
+    }
+
+    nsAutoCString spec;
+    sourceURI->GetSpecIgnoringRef(spec);
+    aSourceFile = NS_ConvertUTF8toUTF16(spec);
+  } ();
+  aInit.mSourceFile = aSourceFile;
+
+  // sample
+  aInit.mSample = aScriptSample;
+
+  // disposition
+  aInit.mDisposition = mPolicies[aViolatedPolicyIndex]->getReportOnlyFlag()
+      ? mozilla::dom::SecurityPolicyViolationEventDisposition::Report
+      : mozilla::dom::SecurityPolicyViolationEventDisposition::Enforce;
+
+  // status-code
+  aInit.mStatusCode = [] (nsCOMPtr<nsIDocument> doc) -> uint16_t {
+    if (!doc) {
+      return 0;
+    }
+
+    nsCOMPtr<nsIHttpChannel> channel = do_QueryInterface(doc->GetChannel());
+    if (!channel) {
+      return 0;
+    }
+
+    uint32_t statusCode = 0;
+    nsresult rv = channel->GetResponseStatus(&statusCode);
+    if (NS_FAILED(rv)) {
+      return 0;
     }
+
+    return static_cast<uint16_t>(statusCode);
+  } (do_QueryReferent(mLoadingContext));
+
+  // line-number
+  aInit.mLineNumber = aLineNum;
+
+  // column-number
+  aInit.mColumnNumber = 0; // TODO
+
+  aInit.mBubbles = true;
+
+  return NS_OK;
+}
+
+nsresult
+nsCSPContext::SendReports(
+    const mozilla::dom::SecurityPolicyViolationEventInit& aInit,
+    uint32_t aViolatedPolicyIndex)
+{
+  NS_ENSURE_ARG_MAX(aViolatedPolicyIndex, mPolicies.Length() - 1);
+
+  dom::CSPReport report;
+
+  // blocked-uri
+  report.mCsp_report.mBlocked_uri = aInit.mBlockedURI;
+
+  // document-uri
+  report.mCsp_report.mDocument_uri = aInit.mDocumentURI;
+
+  // original-policy
+  report.mCsp_report.mOriginal_policy = aInit.mOriginalPolicy;
+
+  // referrer
+  report.mCsp_report.mReferrer = aInit.mReferrer;
+
+  // violated-directive
+  report.mCsp_report.mViolated_directive = aInit.mViolatedDirective;
+
+  // source-file
+  if (!aInit.mSourceFile.IsEmpty()) {
     report.mCsp_report.mSource_file.Construct();
-    report.mCsp_report.mSource_file.Value() = aSourceFile;
+    report.mCsp_report.mSource_file.Value() = aInit.mSourceFile;
   }
 
   // script-sample
-  if (!aScriptSample.IsEmpty()) {
+  if (!aInit.mSample.IsEmpty()) {
     report.mCsp_report.mScript_sample.Construct();
-    report.mCsp_report.mScript_sample.Value() = aScriptSample;
+    report.mCsp_report.mScript_sample.Value() = aInit.mSample;
   }
 
   // line-number
-  if (aLineNum != 0) {
+  if (aInit.mLineNumber != 0) {
     report.mCsp_report.mLine_number.Construct();
-    report.mCsp_report.mLine_number.Value() = aLineNum;
+    report.mCsp_report.mLine_number.Value() = aInit.mLineNumber;
   }
 
   nsString csp_report;
   if (!report.ToJSON(csp_report)) {
     return NS_ERROR_FAILURE;
   }
 
   // ---------- Assembled, now send it to all the report URIs ----------- //
 
   nsTArray<nsString> reportURIs;
   mPolicies[aViolatedPolicyIndex]->getReportURIs(reportURIs);
 
-
   nsCOMPtr<nsIDocument> doc = do_QueryReferent(mLoadingContext);
   nsCOMPtr<nsIURI> reportURI;
   nsCOMPtr<nsIChannel> reportChannel;
 
+  nsresult rv;
   for (uint32_t r = 0; r < reportURIs.Length(); r++) {
     nsAutoCString reportURICstring = NS_ConvertUTF16toUTF8(reportURIs[r]);
     // try to create a new uri from every report-uri string
     rv = NS_NewURI(getter_AddRefs(reportURI), reportURIs[r]);
     if (NS_FAILED(rv)) {
       const char16_t* params[] = { reportURIs[r].get() };
       CSPCONTEXTLOG(("Could not create nsIURI for report URI %s",
                      reportURICstring.get()));
       logToConsole("triedToSendReport", params, ArrayLength(params),
-                   aSourceFile, aScriptSample, aLineNum, 0, nsIScriptError::errorFlag);
+                   aInit.mSourceFile, aInit.mSample, aInit.mLineNumber, 0, nsIScriptError::errorFlag);
       continue; // don't return yet, there may be more URIs
     }
 
     // try to create a new channel for every report-uri
     nsLoadFlags loadFlags = nsIRequest::LOAD_NORMAL | nsIChannel::LOAD_CLASSIFY_URI;
     if (doc) {
       rv = NS_NewChannel(getter_AddRefs(reportChannel),
                          reportURI,
@@ -995,17 +1055,17 @@ nsCSPContext::SendReports(nsISupports* a
     // log a warning to console if scheme is not http or https
     bool isHttpScheme =
       (NS_SUCCEEDED(reportURI->SchemeIs("http", &isHttpScheme)) && isHttpScheme) ||
       (NS_SUCCEEDED(reportURI->SchemeIs("https", &isHttpScheme)) && isHttpScheme);
 
     if (!isHttpScheme) {
       const char16_t* params[] = { reportURIs[r].get() };
       logToConsole("reportURInotHttpsOrHttp2", params, ArrayLength(params),
-                   aSourceFile, aScriptSample, aLineNum, 0, nsIScriptError::errorFlag);
+                   aInit.mSourceFile, aInit.mSample, aInit.mLineNumber, 0, nsIScriptError::errorFlag);
       continue;
     }
 
     // make sure this is an anonymous request (no cookies) so in case the
     // policy URI is injected, it can't be abused for CSRF.
     nsLoadFlags flags;
     rv = reportChannel->GetLoadFlags(&flags);
     NS_ENSURE_SUCCESS(rv, rv);
@@ -1060,24 +1120,62 @@ nsCSPContext::SendReports(nsISupports* a
     // SetRequestContext is not given a channel).  This should fail quietly and
     // not return an error since it's really ok if reports don't go out, but
     // it's good to log the error locally.
 
     if (NS_FAILED(rv)) {
       const char16_t* params[] = { reportURIs[r].get() };
       CSPCONTEXTLOG(("AsyncOpen failed for report URI %s", NS_ConvertUTF16toUTF8(params[0]).get()));
       logToConsole("triedToSendReport", params, ArrayLength(params),
-                   aSourceFile, aScriptSample, aLineNum, 0, nsIScriptError::errorFlag);
+                   aInit.mSourceFile, aInit.mSample, aInit.mLineNumber, 0, nsIScriptError::errorFlag);
     } else {
       CSPCONTEXTLOG(("Sent violation report to URI %s", reportURICstring.get()));
     }
   }
   return NS_OK;
 }
 
+nsresult
+nsCSPContext::FireViolationEvent(
+    nsIDOMEventTarget* aTarget,
+    const mozilla::dom::SecurityPolicyViolationEventInit& aInit)
+{
+  nsCOMPtr<nsIDocument> doc = do_QueryReferent(mLoadingContext);
+  if (!doc) {
+    return NS_OK;
+  }
+
+  nsCOMPtr<nsINode> target = do_QueryInterface(aTarget);
+
+  // If target is not null, and global is a Window, and target’s
+  // shadow-including root is not global’s associated Document, set target to
+  // null.
+  mozilla::dom::GetRootNodeOptions opt;
+  opt.mComposed = true;
+  if (target && (doc != target->GetRootNode(opt))) {
+    target = nullptr;
+  }
+
+  // If target is null:
+  //   1. Set target be violation’s global object.
+  //   2. If target is a Window, set target to target’s associated Document.
+  if (!target) {
+    target = doc;
+  }
+
+  RefPtr<mozilla::dom::Event> event =
+      mozilla::dom::SecurityPolicyViolationEvent::Constructor(
+          target,
+          NS_LITERAL_STRING("securitypolicyviolation"),
+          aInit);
+
+  bool rv;
+  return target->DispatchEvent(event, &rv);
+}
+
 /**
  * Dispatched from the main thread to send reports for one CSP violation.
  */
 class CSPReportSenderRunnable final : public Runnable
 {
   public:
     CSPReportSenderRunnable(nsIDOMEventTarget* aTarget,
                             nsISupports* aBlockedContentSource,
@@ -1116,28 +1214,34 @@ class CSPReportSenderRunnable final : pu
         mObserverSubject = do_QueryInterface(supportscstr);
       }
     }
 
     NS_IMETHOD Run() override
     {
       MOZ_ASSERT(NS_IsMainThread());
 
+      // 0) prepare violation data
+      mozilla::dom::SecurityPolicyViolationEventInit init;
+      mCSPContext->GatherSecurityPolicyViolationEventData(
+          mBlockedContentSource, mOriginalURI,
+          mViolatedDirective, mViolatedPolicyIndex,
+          mSourceFile, mScriptSample, mLineNum,
+          init);
+
       // 1) notify observers
       nsCOMPtr<nsIObserverService> observerService = mozilla::services::GetObserverService();
       NS_ASSERTION(observerService, "needs observer service");
       nsresult rv = observerService->NotifyObservers(mObserverSubject,
                                                      CSP_VIOLATION_TOPIC,
                                                      mViolatedDirective.get());
       NS_ENSURE_SUCCESS(rv, rv);
 
       // 2) send reports for the policy that was violated
-      mCSPContext->SendReports(mBlockedContentSource, mOriginalURI,
-                               mViolatedDirective, mViolatedPolicyIndex,
-                               mSourceFile, mScriptSample, mLineNum);
+      mCSPContext->SendReports(init, mViolatedPolicyIndex);
 
       // 3) log to console (one per policy violation)
       // mBlockedContentSource could be a URI or a string.
       nsCOMPtr<nsIURI> blockedURI = do_QueryInterface(mBlockedContentSource);
       // if mBlockedContentSource is not a URI, it could be a string
       nsCOMPtr<nsISupportsCString> blockedString = do_QueryInterface(mBlockedContentSource);
 
       nsCString blockedDataStr;
@@ -1160,16 +1264,20 @@ class CSPReportSenderRunnable final : pu
         nsString blockedDataChar16 = NS_ConvertUTF8toUTF16(blockedDataStr);
         const char16_t* params[] = { mViolatedDirective.get(),
                                      blockedDataChar16.get() };
         mCSPContext->logToConsole(mReportOnlyFlag ? "CSPROViolationWithURI" :
                                                     "CSPViolationWithURI",
                                   params, ArrayLength(params), mSourceFile, mScriptSample,
                                   mLineNum, 0, nsIScriptError::errorFlag);
       }
+
+      // 4) fire violation event
+      mCSPContext->FireViolationEvent(mTarget, init);
+
       return NS_OK;
     }
 
   private:
     nsCOMPtr<nsIDOMEventTarget> mTarget;
     nsCOMPtr<nsISupports>   mBlockedContentSource;
     nsCOMPtr<nsIURI>        mOriginalURI;
     uint32_t                mViolatedPolicyIndex;
--- a/dom/security/nsCSPContext.h
+++ b/dom/security/nsCSPContext.h
@@ -3,16 +3,17 @@
 /* This Source Code Form is subject to the terms of the Mozilla Public
  * License, v. 2.0. If a copy of the MPL was not distributed with this
  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
 
 #ifndef nsCSPContext_h___
 #define nsCSPContext_h___
 
 #include "mozilla/dom/nsCSPUtils.h"
+#include "mozilla/dom/SecurityPolicyViolationEvent.h"
 #include "nsDataHashtable.h"
 #include "nsIChannel.h"
 #include "nsIChannelEventSink.h"
 #include "nsIClassInfo.h"
 #include "nsIContentSecurityPolicy.h"
 #include "nsIInterfaceRequestor.h"
 #include "nsISerializable.h"
 #include "nsIStreamListener.h"
@@ -53,23 +54,54 @@ class nsCSPContext : public nsIContentSe
                       const char16_t** aParams,
                       uint32_t aParamsLength,
                       const nsAString& aSourceName,
                       const nsAString& aSourceLine,
                       uint32_t aLineNumber,
                       uint32_t aColumnNumber,
                       uint32_t aSeverityFlag);
 
-    nsresult SendReports(nsISupports* aBlockedContentSource,
-                         nsIURI* aOriginalURI,
-                         nsAString& aViolatedDirective,
-                         uint32_t aViolatedPolicyIndex,
-                         nsAString& aSourceFile,
-                         nsAString& aScriptSample,
-                         uint32_t aLineNum);
+
+
+    /**
+     * Construct SecurityPolicyViolationEventInit structure.
+     *
+     * @param aBlockedContentSource
+     *        Either a CSP Source (like 'self', as string) or nsIURI: the source
+     *        of the violation.
+     * @param aOriginalUri
+     *        The original URI if the blocked content is a redirect, else null
+     * @param aViolatedDirective
+     *        the directive that was violated (string).
+     * @param aSourceFile
+     *        name of the file containing the inline script violation
+     * @param aScriptSample
+     *        a sample of the violating inline script
+     * @param aLineNum
+     *        source line number of the violation (if available)
+     * @param aInit
+     *        The output
+     */
+    nsresult GatherSecurityPolicyViolationEventData(
+        nsISupports* aBlockedContentSource,
+        nsIURI* aOriginalURI,
+        nsAString& aViolatedDirective,
+        uint32_t aViolatedPolicyIndex,
+        nsAString& aSourceFile,
+        nsAString& aScriptSample,
+        uint32_t aLineNum,
+        mozilla::dom::SecurityPolicyViolationEventInit& aInit);
+
+    nsresult SendReports(
+        const mozilla::dom::SecurityPolicyViolationEventInit& aInit,
+        uint32_t aViolatedPolicyIndex);
+
+    nsresult FireViolationEvent(
+        nsIDOMEventTarget* aTarget,
+        const mozilla::dom::SecurityPolicyViolationEventInit& aInit);
 
     nsresult AsyncReportViolation(nsIDOMEventTarget* aTarget,
                                   nsISupports* aBlockedContentSource,
                                   nsIURI* aOriginalURI,
                                   const nsAString& aViolatedDirective,
                                   uint32_t aViolatedPolicyIndex,
                                   const nsAString& aObserverSubject,
                                   const nsAString& aSourceFile,
new file mode 100644
--- /dev/null
+++ b/dom/webidl/SecurityPolicyViolationEvent.webidl
@@ -0,0 +1,41 @@
+/* This Source Code Form is subject to the terms of the Mozilla Public
+ * License, v. 2.0. If a copy of the MPL was not distributed with this file,
+ * You can obtain one at http://mozilla.org/MPL/2.0/. */
+
+enum SecurityPolicyViolationEventDisposition
+{
+  "enforce", "report"
+};
+
+[Constructor(DOMString type, optional SecurityPolicyViolationEventInit eventInitDict)]
+interface SecurityPolicyViolationEvent : Event
+{
+    readonly attribute DOMString      documentURI;
+    readonly attribute DOMString      referrer;
+    readonly attribute DOMString      blockedURI;
+    readonly attribute DOMString      violatedDirective;
+    readonly attribute DOMString      effectiveDirective;
+    readonly attribute DOMString      originalPolicy;
+    readonly attribute DOMString      sourceFile;
+    readonly attribute DOMString      sample;
+    readonly attribute SecurityPolicyViolationEventDisposition disposition;
+    readonly attribute unsigned short statusCode;
+    readonly attribute long           lineNumber;
+    readonly attribute long           columnNumber;
+};
+
+dictionary SecurityPolicyViolationEventInit : EventInit
+{
+    DOMString      documentURI = "";
+    DOMString      referrer = "";
+    DOMString      blockedURI = "";
+    DOMString      violatedDirective = "";
+    DOMString      effectiveDirective = "";
+    DOMString      originalPolicy = "";
+    DOMString      sourceFile = "";
+    DOMString      sample = "";
+    SecurityPolicyViolationEventDisposition disposition = "report";
+    unsigned short statusCode = 0;
+    long           lineNumber = 0;
+    long           columnNumber = 0;
+};
--- a/dom/webidl/moz.build
+++ b/dom/webidl/moz.build
@@ -1099,16 +1099,17 @@ GENERATED_EVENTS_WEBIDL_FILES = [
     'PluginCrashedEvent.webidl',
     'PopStateEvent.webidl',
     'PopupBlockedEvent.webidl',
     'PresentationConnectionAvailableEvent.webidl',
     'PresentationConnectionCloseEvent.webidl',
     'ProgressEvent.webidl',
     'PromiseRejectionEvent.webidl',
     'ScrollViewChangeEvent.webidl',
+    'SecurityPolicyViolationEvent.webidl',
     'StyleRuleChangeEvent.webidl',
     'StyleSheetApplicableStateChangeEvent.webidl',
     'StyleSheetChangeEvent.webidl',
     'TCPServerSocketEvent.webidl',
     'TCPSocketErrorEvent.webidl',
     'TCPSocketEvent.webidl',
     'TrackEvent.webidl',
     'UDPMessageEvent.webidl',