// Copyright 2014 The Chromium Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #include "core/frame/SubresourceIntegrity.h" #include "core/HTMLNames.h" #include "core/dom/Document.h" #include "core/fetch/IntegrityMetadata.h" #include "core/fetch/Resource.h" #include "core/html/HTMLScriptElement.h" #include "platform/Crypto.h" #include "platform/weborigin/KURL.h" #include "platform/weborigin/SecurityOrigin.h" #include "testing/gtest/include/gtest/gtest.h" #include "wtf/RefPtr.h" #include "wtf/Vector.h" #include "wtf/dtoa/utils.h" #include "wtf/text/WTFString.h" namespace blink { static const char kBasicScript[] = "alert('test');"; static const char kSha256Integrity[] = "sha256-GAF48QOoxRvu0gZAmQivUdJPyBacqznBAXwnkfpmQX4="; static const char kSha256IntegrityLenientSyntax[] = "sha256-GAF48QOoxRvu0gZAmQivUdJPyBacqznBAXwnkfpmQX4="; static const char kSha256IntegrityWithEmptyOption[] = "sha256-GAF48QOoxRvu0gZAmQivUdJPyBacqznBAXwnkfpmQX4=?"; static const char kSha256IntegrityWithOption[] = "sha256-GAF48QOoxRvu0gZAmQivUdJPyBacqznBAXwnkfpmQX4=?foo=bar"; static const char kSha256IntegrityWithOptions[] = "sha256-GAF48QOoxRvu0gZAmQivUdJPyBacqznBAXwnkfpmQX4=?foo=bar?baz=foz"; static const char kSha256IntegrityWithMimeOption[] = "sha256-GAF48QOoxRvu0gZAmQivUdJPyBacqznBAXwnkfpmQX4=?ct=application/javascript"; static const char kSha384Integrity[] = "sha384-nep3XpvhUxpCMOVXIFPecThAqdY_uVeiD4kXSqXpx0YJUWU4fTTaFgciTuZk7fmE"; static const char kSha512Integrity[] = "sha512-TXkJw18PqlVlEUXXjeXbGetop1TKB3wYQIp1_ihxCOFGUfG9TYOaA1MlkpTAqSV6yaevLO8Tj5pgH1JmZ--ItA=="; static const char kSha384IntegrityLabeledAs256[] = "sha256-nep3XpvhUxpCMOVXIFPecThAqdY_uVeiD4kXSqXpx0YJUWU4fTTaFgciTuZk7fmE"; static const char kSha256AndSha384Integrities[] = "sha256-GAF48QOoxRvu0gZAmQivUdJPyBacqznBAXwnkfpmQX4= sha384-nep3XpvhUxpCMOVXIFPecThAqdY_uVeiD4kXSqXpx0YJUWU4fTTaFgciTuZk7fmE"; static const char kBadSha256AndGoodSha384Integrities[] = "sha256-deadbeef sha384-nep3XpvhUxpCMOVXIFPecThAqdY_uVeiD4kXSqXpx0YJUWU4fTTaFgciTuZk7fmE"; static const char kGoodSha256AndBadSha384Integrities[] = "sha256-GAF48QOoxRvu0gZAmQivUdJPyBacqznBAXwnkfpmQX4= sha384-deadbeef"; static const char kBadSha256AndBadSha384Integrities[] = "sha256-deadbeef sha384-deadbeef"; static const char kUnsupportedHashFunctionIntegrity[] = "sha1-JfLW308qMPKfb4DaHpUBEESwuPc="; class SubresourceIntegrityTest : public ::testing::Test { public: SubresourceIntegrityTest() : secureURL(ParsedURLString, "https://example.test:443") , insecureURL(ParsedURLString, "http://example.test:80") , secureOrigin(SecurityOrigin::create(secureURL)) , insecureOrigin(SecurityOrigin::create(insecureURL)) { } protected: virtual void SetUp() { document = Document::create(); scriptElement = HTMLScriptElement::create(*document, true); } void expectAlgorithm(const String& text, HashAlgorithm expectedAlgorithm) { Vector characters; text.appendTo(characters); const UChar* position = characters.data(); const UChar* end = characters.end(); HashAlgorithm algorithm; EXPECT_EQ(SubresourceIntegrity::AlgorithmValid, SubresourceIntegrity::parseAlgorithm(position, end, algorithm)); EXPECT_EQ(expectedAlgorithm, algorithm); EXPECT_EQ(end, position); } void expectAlgorithmFailure(const String& text, SubresourceIntegrity::AlgorithmParseResult expectedResult) { Vector characters; text.appendTo(characters); const UChar* position = characters.data(); const UChar* begin = characters.data(); const UChar* end = characters.end(); HashAlgorithm algorithm; EXPECT_EQ(expectedResult, SubresourceIntegrity::parseAlgorithm(position, end, algorithm)); EXPECT_EQ(begin, position); } void expectDigest(const String& text, const char* expectedDigest) { Vector characters; text.appendTo(characters); const UChar* position = characters.data(); const UChar* end = characters.end(); String digest; EXPECT_TRUE(SubresourceIntegrity::parseDigest(position, end, digest)); EXPECT_EQ(expectedDigest, digest); } void expectDigestFailure(const String& text) { Vector characters; text.appendTo(characters); const UChar* position = characters.data(); const UChar* end = characters.end(); String digest; EXPECT_FALSE(SubresourceIntegrity::parseDigest(position, end, digest)); EXPECT_TRUE(digest.isEmpty()); } void expectParse(const char* integrityAttribute, const char* expectedDigest, HashAlgorithm expectedAlgorithm) { IntegrityMetadataSet metadataSet; EXPECT_EQ(SubresourceIntegrity::IntegrityParseValidResult, SubresourceIntegrity::parseIntegrityAttribute(integrityAttribute, metadataSet)); EXPECT_EQ(1u, metadataSet.size()); if (metadataSet.size() > 0) { IntegrityMetadata metadata = *metadataSet.begin(); EXPECT_EQ(expectedDigest, metadata.digest()); EXPECT_EQ(expectedAlgorithm, metadata.algorithm()); } } void expectParseMultipleHashes(const char* integrityAttribute, const IntegrityMetadata expectedMetadataArray[], size_t expectedMetadataArraySize) { IntegrityMetadataSet expectedMetadataSet; for (size_t i = 0; i < expectedMetadataArraySize; i++) { expectedMetadataSet.add(expectedMetadataArray[i].toPair()); } IntegrityMetadataSet metadataSet; EXPECT_EQ(SubresourceIntegrity::IntegrityParseValidResult, SubresourceIntegrity::parseIntegrityAttribute(integrityAttribute, metadataSet)); EXPECT_TRUE(IntegrityMetadata::setsEqual(expectedMetadataSet, metadataSet)); } void expectParseFailure(const char* integrityAttribute) { IntegrityMetadataSet metadataSet; EXPECT_EQ(SubresourceIntegrity::IntegrityParseNoValidResult, SubresourceIntegrity::parseIntegrityAttribute(integrityAttribute, metadataSet)); } void expectEmptyParseResult(const char* integrityAttribute) { IntegrityMetadataSet metadataSet; EXPECT_EQ(SubresourceIntegrity::IntegrityParseValidResult, SubresourceIntegrity::parseIntegrityAttribute(integrityAttribute, metadataSet)); EXPECT_EQ(0u, metadataSet.size()); } enum CorsStatus { WithCors, NoCors }; void expectIntegrity(const char* integrity, const char* script, size_t size, const KURL& url, const KURL& requestorUrl, CorsStatus corsStatus = WithCors) { scriptElement->setAttribute(HTMLNames::integrityAttr, integrity); EXPECT_TRUE(SubresourceIntegrity::CheckSubresourceIntegrity(*scriptElement, script, size, url, *createTestResource(url, requestorUrl, corsStatus).get())); } void expectIntegrityFailure(const char* integrity, const char* script, size_t size, const KURL& url, const KURL& requestorUrl, CorsStatus corsStatus = WithCors) { scriptElement->setAttribute(HTMLNames::integrityAttr, integrity); EXPECT_FALSE(SubresourceIntegrity::CheckSubresourceIntegrity(*scriptElement, script, size, url, *createTestResource(url, requestorUrl, corsStatus).get())); } PassRefPtrWillBeRawPtr createTestResource(const KURL& url, const KURL& allowOriginUrl, CorsStatus corsStatus) { ResourceResponse response; response.setURL(url); response.setHTTPStatusCode(200); if (corsStatus == WithCors) { response.setHTTPHeaderField("access-control-allow-origin", SecurityOrigin::create(allowOriginUrl)->toAtomicString()); response.setHTTPHeaderField("access-control-allow-credentials", "true"); } RefPtrWillBeRawPtr resource = Resource::create(ResourceRequest(response.url()), Resource::Raw); resource->setResponse(response); return resource; } KURL secureURL; KURL insecureURL; RefPtr secureOrigin; RefPtr insecureOrigin; RefPtrWillBePersistent document; RefPtrWillBePersistent scriptElement; }; TEST_F(SubresourceIntegrityTest, Prioritization) { EXPECT_EQ(HashAlgorithmSha256, SubresourceIntegrity::getPrioritizedHashFunction(HashAlgorithmSha256, HashAlgorithmSha256)); EXPECT_EQ(HashAlgorithmSha384, SubresourceIntegrity::getPrioritizedHashFunction(HashAlgorithmSha384, HashAlgorithmSha384)); EXPECT_EQ(HashAlgorithmSha512, SubresourceIntegrity::getPrioritizedHashFunction(HashAlgorithmSha512, HashAlgorithmSha512)); EXPECT_EQ(HashAlgorithmSha384, SubresourceIntegrity::getPrioritizedHashFunction(HashAlgorithmSha384, HashAlgorithmSha256)); EXPECT_EQ(HashAlgorithmSha512, SubresourceIntegrity::getPrioritizedHashFunction(HashAlgorithmSha512, HashAlgorithmSha256)); EXPECT_EQ(HashAlgorithmSha512, SubresourceIntegrity::getPrioritizedHashFunction(HashAlgorithmSha512, HashAlgorithmSha384)); EXPECT_EQ(HashAlgorithmSha384, SubresourceIntegrity::getPrioritizedHashFunction(HashAlgorithmSha256, HashAlgorithmSha384)); EXPECT_EQ(HashAlgorithmSha512, SubresourceIntegrity::getPrioritizedHashFunction(HashAlgorithmSha256, HashAlgorithmSha512)); EXPECT_EQ(HashAlgorithmSha512, SubresourceIntegrity::getPrioritizedHashFunction(HashAlgorithmSha384, HashAlgorithmSha512)); } TEST_F(SubresourceIntegrityTest, ParseAlgorithm) { expectAlgorithm("sha256-", HashAlgorithmSha256); expectAlgorithm("sha384-", HashAlgorithmSha384); expectAlgorithm("sha512-", HashAlgorithmSha512); expectAlgorithm("sha-256-", HashAlgorithmSha256); expectAlgorithm("sha-384-", HashAlgorithmSha384); expectAlgorithm("sha-512-", HashAlgorithmSha512); expectAlgorithmFailure("sha1-", SubresourceIntegrity::AlgorithmUnknown); expectAlgorithmFailure("sha-1-", SubresourceIntegrity::AlgorithmUnknown); expectAlgorithmFailure("foobarsha256-", SubresourceIntegrity::AlgorithmUnknown); expectAlgorithmFailure("foobar-", SubresourceIntegrity::AlgorithmUnknown); expectAlgorithmFailure("-", SubresourceIntegrity::AlgorithmUnknown); expectAlgorithmFailure("sha256", SubresourceIntegrity::AlgorithmUnparsable); expectAlgorithmFailure("", SubresourceIntegrity::AlgorithmUnparsable); } TEST_F(SubresourceIntegrityTest, ParseDigest) { expectDigest("abcdefg", "abcdefg"); expectDigest("abcdefg?", "abcdefg"); expectDigest("ab+de/g", "ab+de/g"); expectDigest("ab-de_g", "ab+de/g"); expectDigestFailure("?"); expectDigestFailure("&&&foobar&&&"); expectDigestFailure("\x01\x02\x03\x04"); } // // End-to-end parsing tests. // TEST_F(SubresourceIntegrityTest, Parsing) { expectParseFailure("not_really_a_valid_anything"); expectParseFailure("sha256-&&&foobar&&&"); expectParseFailure("sha256-\x01\x02\x03\x04"); expectParseFailure("sha256-!!! sha256-!!!"); expectEmptyParseResult("foobar:///sha256-abcdefg"); expectEmptyParseResult("ni://sha256-abcdefg"); expectEmptyParseResult("ni:///sha256-abcdefg"); expectEmptyParseResult("notsha256atall-abcdefg"); expectParse( "sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse( "sha-256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse( " sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE= ", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse( "sha384-XVVXBGoYw6AJOh9J-Z8pBDMVVPfkBpngexkA7JqZu8d5GENND6TEIup_tA1v5GPr", "XVVXBGoYw6AJOh9J+Z8pBDMVVPfkBpngexkA7JqZu8d5GENND6TEIup/tA1v5GPr", HashAlgorithmSha384); expectParse( "sha-384-XVVXBGoYw6AJOh9J_Z8pBDMVVPfkBpngexkA7JqZu8d5GENND6TEIup_tA1v5GPr", "XVVXBGoYw6AJOh9J/Z8pBDMVVPfkBpngexkA7JqZu8d5GENND6TEIup/tA1v5GPr", HashAlgorithmSha384); expectParse( "sha512-tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ-07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", "tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ+07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", HashAlgorithmSha512); expectParse( "sha-512-tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ-07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", "tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ+07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", HashAlgorithmSha512); expectParse( "sha-512-tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ-07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==?ct=application/javascript", "tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ+07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", HashAlgorithmSha512); expectParse( "sha-512-tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ-07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==?ct=application/xhtml+xml", "tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ+07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", HashAlgorithmSha512); expectParse( "sha-512-tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ-07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==?foo=bar?ct=application/xhtml+xml", "tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ+07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", HashAlgorithmSha512); expectParse( "sha-512-tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ-07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==?ct=application/xhtml+xml?foo=bar", "tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ+07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", HashAlgorithmSha512); expectParse( "sha-512-tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ-07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==?baz=foz?ct=application/xhtml+xml?foo=bar", "tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ+07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", HashAlgorithmSha512); expectParseMultipleHashes("", 0, 0); expectParseMultipleHashes(" ", 0, 0); const IntegrityMetadata validSha384AndSha512[] = { IntegrityMetadata("XVVXBGoYw6AJOh9J+Z8pBDMVVPfkBpngexkA7JqZu8d5GENND6TEIup/tA1v5GPr", HashAlgorithmSha384), IntegrityMetadata("tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ+07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", HashAlgorithmSha512), }; expectParseMultipleHashes( "sha384-XVVXBGoYw6AJOh9J+Z8pBDMVVPfkBpngexkA7JqZu8d5GENND6TEIup/tA1v5GPr sha512-tbUPioKbVBplr0b1ucnWB57SJWt4x9dOE0Vy2mzCXvH3FepqDZ+07yMK81ytlg0MPaIrPAjcHqba5csorDWtKg==", validSha384AndSha512, WTF_ARRAY_LENGTH(validSha384AndSha512)); const IntegrityMetadata validSha256AndSha256[] = { IntegrityMetadata("BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256), IntegrityMetadata("deadbeef", HashAlgorithmSha256), }; expectParseMultipleHashes( "sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE= sha256-deadbeef", validSha256AndSha256, WTF_ARRAY_LENGTH(validSha256AndSha256)); const IntegrityMetadata validSha256AndInvalidSha256[] = { IntegrityMetadata("BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256), }; expectParseMultipleHashes( "sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE= sha256-!!!!", validSha256AndInvalidSha256, WTF_ARRAY_LENGTH(validSha256AndInvalidSha256)); const IntegrityMetadata invalidSha256AndValidSha256[] = { IntegrityMetadata("BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256), }; expectParseMultipleHashes( "sha256-!!! sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", invalidSha256AndValidSha256, WTF_ARRAY_LENGTH(invalidSha256AndValidSha256)); expectParse( "sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=?foo=bar", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse( "sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=?foo=bar?baz=foz", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse("sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=?", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse("sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=?foo=bar", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse("sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=?foo=bar?baz=foz", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse("sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=?foo", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse("sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=?foo=bar?", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); expectParse("sha256-BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=?foo:bar", "BpfBw7ivV8q2jLiT13fxDYAe2tJllusRSZ273h2nFSE=", HashAlgorithmSha256); } TEST_F(SubresourceIntegrityTest, ParsingBase64) { expectParse( "sha384-XVVXBGoYw6AJOh9J+Z8pBDMVVPfkBpngexkA7JqZu8d5GENND6TEIup/tA1v5GPr", "XVVXBGoYw6AJOh9J+Z8pBDMVVPfkBpngexkA7JqZu8d5GENND6TEIup/tA1v5GPr", HashAlgorithmSha384); } // // End-to-end tests of ::CheckSubresourceIntegrity. // TEST_F(SubresourceIntegrityTest, CheckSubresourceIntegrityInSecureOrigin) { document->updateSecurityOrigin(secureOrigin->isolatedCopy()); // Verify basic sha256, sha384, and sha512 integrity checks. expectIntegrity(kSha256Integrity, kBasicScript, strlen(kBasicScript), secureURL, secureURL); expectIntegrity(kSha256IntegrityLenientSyntax, kBasicScript, strlen(kBasicScript), secureURL, secureURL); expectIntegrity(kSha384Integrity, kBasicScript, strlen(kBasicScript), secureURL, secureURL); expectIntegrity(kSha512Integrity, kBasicScript, strlen(kBasicScript), secureURL, secureURL); // Verify multiple hashes in an attribute. expectIntegrity(kSha256AndSha384Integrities, kBasicScript, strlen(kBasicScript), secureURL, secureURL); expectIntegrity(kBadSha256AndGoodSha384Integrities, kBasicScript, strlen(kBasicScript), secureURL, secureURL); // The hash label must match the hash value. expectIntegrityFailure(kSha384IntegrityLabeledAs256, kBasicScript, strlen(kBasicScript), secureURL, secureURL); // With multiple values, at least one must match, and it must be the // strongest hash algorithm. expectIntegrityFailure(kGoodSha256AndBadSha384Integrities, kBasicScript, strlen(kBasicScript), secureURL, secureURL); expectIntegrityFailure(kBadSha256AndBadSha384Integrities, kBasicScript, strlen(kBasicScript), secureURL, secureURL); // Unsupported hash functions should succeed. expectIntegrity(kUnsupportedHashFunctionIntegrity, kBasicScript, strlen(kBasicScript), secureURL, secureURL); // All parameters are fine, and because this is not cross origin, CORS is // not needed. expectIntegrity(kSha256Integrity, kBasicScript, strlen(kBasicScript), secureURL, secureURL, NoCors); // Options should be ignored expectIntegrity(kSha256IntegrityWithEmptyOption, kBasicScript, strlen(kBasicScript), secureURL, secureURL, NoCors); expectIntegrity(kSha256IntegrityWithOption, kBasicScript, strlen(kBasicScript), secureURL, secureURL, NoCors); expectIntegrity(kSha256IntegrityWithOptions, kBasicScript, strlen(kBasicScript), secureURL, secureURL, NoCors); expectIntegrity(kSha256IntegrityWithMimeOption, kBasicScript, strlen(kBasicScript), secureURL, secureURL, NoCors); } TEST_F(SubresourceIntegrityTest, CheckSubresourceIntegrityInInsecureOrigin) { // The same checks as CheckSubresourceIntegrityInSecureOrigin should pass // here, with the expection of the NoCors check at the end. document->updateSecurityOrigin(insecureOrigin->isolatedCopy()); expectIntegrity(kSha256Integrity, kBasicScript, strlen(kBasicScript), secureURL, insecureURL); expectIntegrity(kSha256IntegrityLenientSyntax, kBasicScript, strlen(kBasicScript), secureURL, insecureURL); expectIntegrity(kSha384Integrity, kBasicScript, strlen(kBasicScript), secureURL, insecureURL); expectIntegrity(kSha512Integrity, kBasicScript, strlen(kBasicScript), secureURL, insecureURL); expectIntegrityFailure(kSha384IntegrityLabeledAs256, kBasicScript, strlen(kBasicScript), secureURL, insecureURL); expectIntegrity(kUnsupportedHashFunctionIntegrity, kBasicScript, strlen(kBasicScript), secureURL, insecureURL); expectIntegrity(kSha256AndSha384Integrities, kBasicScript, strlen(kBasicScript), secureURL, insecureURL); expectIntegrity(kBadSha256AndGoodSha384Integrities, kBasicScript, strlen(kBasicScript), secureURL, insecureURL); expectIntegrityFailure(kSha256Integrity, kBasicScript, strlen(kBasicScript), secureURL, insecureURL, NoCors); expectIntegrityFailure(kGoodSha256AndBadSha384Integrities, kBasicScript, strlen(kBasicScript), secureURL, insecureURL); } } // namespace blink