Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #ifndef FeaturePolicy_h | 5 #ifndef CONTENT_COMMON_FEATURE_POLICY_FEATURE_POLICY_H_ |
| 6 #define FeaturePolicy_h | 6 #define CONTENT_COMMON_FEATURE_POLICY_FEATURE_POLICY_H_ |
| 7 | 7 |
| 8 #include "platform/PlatformExport.h" | 8 #include <map> |
| 9 #include "platform/weborigin/SecurityOrigin.h" | 9 #include <memory> |
| 10 #include "public/platform/WebFeaturePolicy.h" | 10 #include <string> |
| 11 #include "wtf/RefPtr.h" | 11 #include <vector> |
| 12 #include "wtf/Vector.h" | |
| 13 #include "wtf/text/WTFString.h" | |
| 14 | 12 |
| 15 #include <memory> | 13 #include "content/common/content_export.h" |
| 14 #include "third_party/WebKit/public/platform/WebFeaturePolicy.h" | |
| 15 #include "url/origin.h" | |
| 16 | 16 |
| 17 namespace blink { | 17 namespace content { |
| 18 | 18 |
| 19 // Feature Policy is a mechanism for controlling the availability of web | 19 // Feature Policy is a mechanism for controlling the availability of web |
| 20 // platform features in a frame, including all embedded frames. It can be used | 20 // platform features in a frame, including all embedded frames. It can be used |
| 21 // to remove features, automatically refuse API permission requests, or modify | 21 // to remove features, automatically refuse API permission requests, or modify |
| 22 // the behaviour of features. (The specific changes which are made depend on the | 22 // the behaviour of features. (The specific changes which are made depend on the |
| 23 // feature; see the specification for details). | 23 // feature; see the specification for details). |
| 24 // | 24 // |
| 25 // Policies can be defined in the HTTP header stream, with the |Feature-Policy| | 25 // Policies can be defined in the HTTP header stream, with the |Feature-Policy| |
| 26 // HTTP header, or can be set by |enable| and |disable| attributes on the iframe | 26 // HTTP header, or can be set by the |allow| attributes on the iframe element |
| 27 // element which embeds the document. | 27 // which embeds the document. |
| 28 // | 28 // |
| 29 // See https://wicg.github.io/FeaturePolicy/ | 29 // See https://wicg.github.io/FeaturePolicy/ |
| 30 // | 30 // |
| 31 // Key concepts: | 31 // Key concepts: |
| 32 // | 32 // |
| 33 // Features | 33 // Features |
| 34 // -------- | 34 // -------- |
| 35 // Features which can be controlled by policy are defined as instances of the | 35 // Features which can be controlled by policy are defined by instances of the |
| 36 // FeaturePoliicy::Feature struct. The features are referenced by pointer, so | 36 // FeaturePolicy::Feature struct. The features are referenced by the |
| 37 // only a single instance of each feature should be defined. The features which | 37 // |WebFeaturePolicyFeature| enum, declared in |WebFeaturePolicy.h|. |
| 38 // are declared in the feature policy specification are all defined in | |
| 39 // |FeaturePolicy.cpp|. | |
| 40 // | 38 // |
| 41 // Whitelists | 39 // Whitelists |
| 42 // ---------- | 40 // ---------- |
| 43 // Policies are defined as a mapping of feaure names to whitelists. Whitelists | 41 // Whitelists are collections of origins, although two special terms can be used |
| 44 // are collections of origins, although two special terms can be used when | 42 // when declaring them: |
| 45 // declaring them: | |
| 46 // "self" refers to the orgin of the frame which is declaring the policy. | 43 // "self" refers to the orgin of the frame which is declaring the policy. |
| 47 // "*" refers to all origins; any origin will match a whitelist which contains | 44 // "*" refers to all origins; any origin will match a whitelist which contains |
| 48 // it. | 45 // it. |
| 49 // | 46 // |
| 47 // Declarations | |
| 48 // ------------ | |
| 49 // A feature policy declaration is a mapping of a feature name to a whitelist. | |
| 50 // A set of declarations is a declared policy. | |
| 51 // | |
| 52 // Inherited Policy | |
| 53 // ---------------- | |
| 54 // In addition to the declared policy (which may be empty), every frame has | |
| 55 // an inherited policy, which is determined by the context in which it is | |
| 56 // embedded, or by the defaults for each feature in the case of the top-level | |
| 57 // document. | |
| 58 // | |
| 50 // Defaults | 59 // Defaults |
| 51 // -------- | 60 // -------- |
| 52 // Each defined feature has a default policy, which determines whether the | 61 // Each defined feature has a default policy, which determines whether the |
| 53 // feature is available when no policy has been declared, ans determines how the | 62 // feature is available when no policy has been declared, ans determines how the |
| 54 // feature is inherited across origin boundaries. | 63 // feature is inherited across origin boundaries. |
| 55 // | 64 // |
| 56 // If the default policy is in effect for a frame, then it controls how the | 65 // If the default policy is in effect for a frame, then it controls how the |
| 57 // feature is inherited by any cross-origin iframes embedded by the frame. (See | 66 // feature is inherited by any cross-origin iframes embedded by the frame. (See |
| 58 // the comments below in FeaturePolicy::DefaultPolicy for specifics) | 67 // the comments below in FeaturePolicy::DefaultPolicy for specifics) |
| 59 // | 68 // |
| 60 // Policy Inheritance | 69 // Policy Inheritance |
| 61 // ------------------ | 70 // ------------------ |
| 62 // Policies in effect for a frame are inherited by any child frames it embeds. | 71 // Policies in effect for a frame are inherited by any child frames it embeds. |
| 63 // Unless another policy is declared in the child, all same-origin children will | 72 // Unless another policy is declared in the child, all same-origin children will |
| 64 // receive the same set of enables features as the parent frame. Whether or not | 73 // receive the same set of enables features as the parent frame. Whether or not |
| 65 // features are inherited by cross-origin iframes without an explicit policy is | 74 // features are inherited by cross-origin iframes without an explicit policy is |
| 66 // determined by the feature's default policy. (Again, see the comments in | 75 // determined by the feature's default policy. (Again, see the comments in |
| 67 // FeaturePolicy::DefaultPolicy for details) | 76 // FeaturePolicy::DefaultPolicy for details) |
| 68 | 77 |
| 69 class PLATFORM_EXPORT FeaturePolicy final { | 78 // This struct holds feature policy whitelist data that needs to be replicated |
| 79 // between a RenderFrame and any of its associated RenderFrameProxies. A list of | |
| 80 // these form a FeaturePolicyHeader. | |
| 81 // NOTE: These types are used for replication frame state between processes. | |
| 82 // They exist only because we can't transfer WebVectors directly over IPC. | |
| 83 struct CONTENT_EXPORT FeaturePolicyParsedDeclaration { | |
| 84 FeaturePolicyParsedDeclaration(); | |
| 85 FeaturePolicyParsedDeclaration(std::string feature_name, | |
| 86 bool matches_all_origins, | |
| 87 std::vector<url::Origin> origins); | |
| 88 FeaturePolicyParsedDeclaration(const FeaturePolicyParsedDeclaration& rhs); | |
| 89 ~FeaturePolicyParsedDeclaration(); | |
| 90 | |
| 91 std::string feature_name; | |
| 92 bool matches_all_origins; | |
| 93 std::vector<url::Origin> origins; | |
| 94 }; | |
| 95 using FeaturePolicyHeader = std::vector<FeaturePolicyParsedDeclaration>; | |
| 96 | |
| 97 class CONTENT_EXPORT FeaturePolicy : public blink::WebFeaturePolicy { | |
| 70 public: | 98 public: |
| 71 // Represents a collection of origins which make up a whitelist in a feature | 99 // Represents a collection of origins which make up a whitelist in a feature |
| 72 // policy. This collection may be set to match every origin (corresponding to | 100 // policy. This collection may be set to match every origin (corresponding to |
| 73 // the "*" syntax in the policy string, in which case the contains() method | 101 // the "*" syntax in the policy string, in which case the Contains() method |
| 74 // will always return true. | 102 // will always return true. |
| 75 class Whitelist final { | 103 class Whitelist final { |
| 76 public: | 104 public: |
| 77 static std::unique_ptr<Whitelist> from( | |
| 78 const WebFeaturePolicy::ParsedWhitelist&); | |
| 79 | |
| 80 Whitelist(); | 105 Whitelist(); |
| 106 ~Whitelist(); | |
| 81 | 107 |
| 82 // Adds a single origin to the whitelist. | 108 // Adds a single origin to the whitelist. |
| 83 void add(RefPtr<SecurityOrigin>); | 109 void Add(const url::Origin& origin); |
| 84 | 110 |
| 85 // Adds all origins to the whitelist. | 111 // Adds all origins to the whitelist. |
| 86 void addAll(); | 112 void AddAll(); |
| 87 | 113 |
| 88 // Returns true if the given origin has been added to the whitelist. | 114 // Returns true if the given origin has been added to the whitelist. |
| 89 bool contains(const SecurityOrigin&) const; | 115 bool Contains(const url::Origin& origin) const; |
| 90 String toString(); | 116 |
| 117 // Extracts a Whitelist from a FeaturePolicyParsedDeclaration | |
| 118 static std::unique_ptr<Whitelist> FromDeclaration( | |
| 119 const FeaturePolicyParsedDeclaration& parsed_declaration); | |
|
raymes
2017/01/19 02:40:57
Can this just be an implementation detail (standal
iclelland
2017/01/19 05:40:40
Yes it can, thanks. Done.
| |
| 91 | 120 |
| 92 private: | 121 private: |
| 93 bool m_matchesAllOrigins; | 122 bool matches_all_origins_; |
| 94 Vector<RefPtr<SecurityOrigin>> m_origins; | 123 std::vector<url::Origin> origins_; |
| 95 }; | 124 }; |
| 96 | 125 |
| 97 // The FeaturePolicy::FeatureDefault enum defines the default enable state for | 126 // The FeaturePolicy::FeatureDefault enum defines the default enable state for |
| 98 // a feature when neither it nor any parent frame have declared an explicit | 127 // a feature when neither it nor any parent frame have declared an explicit |
| 99 // policy. The three possibilities map directly to Feature Policy Whitelist | 128 // policy. The three possibilities map directly to Feature Policy Whitelist |
| 100 // semantics. | 129 // semantics. |
| 101 enum class FeatureDefault { | 130 enum class FeatureDefault { |
| 102 // Equivalent to []. If this default policy is in effect for a frame, then | 131 // Equivalent to []. If this default policy is in effect for a frame, then |
| 103 // the feature will not be enabled for that frame or any of its children. | 132 // the feature will not be enabled for that frame or any of its children. |
| 104 DisableForAll, | 133 DisableForAll, |
| 105 | 134 |
| 106 // Equivalent to ["self"]. If this default policy is in effect for a frame, | 135 // Equivalent to ["self"]. If this default policy is in effect for a frame, |
| 107 // then the feature will be enabled for that frame, and any same-origin | 136 // then the feature will be enabled for that frame, and any same-origin |
| 108 // child frames, but not for any cross-origin child frames. | 137 // child frames, but not for any cross-origin child frames. |
| 109 EnableForSelf, | 138 EnableForSelf, |
| 110 | 139 |
| 111 // Equivalent to ["*"]. If in effect for a frame, then the feature is | 140 // Equivalent to ["*"]. If in effect for a frame, then the feature is |
| 112 // enabled for that frame and all of its children. | 141 // enabled for that frame and all of its children. |
| 113 EnableForAll | 142 EnableForAll |
| 114 }; | 143 }; |
| 115 | 144 |
| 116 // The FeaturePolicy::Feature struct is used to define all features under | 145 // The FeaturePolicy::Feature struct is used to define all features under |
| 117 // control of Feature Policy. There should only be one instance of this struct | 146 // control of Feature Policy. There should only be one instance of this struct |
| 118 // for any given feature (declared below). | 147 // for any given feature (declared below). |
| 119 struct Feature { | 148 struct Feature { |
| 120 // The name of the feature, as it should appear in a policy string | 149 // The name of the feature, as it should appear in a policy string |
| 121 const char* const featureName; | 150 const char* const feature_name; |
| 122 | 151 |
| 123 // Controls whether the feature should be available in the platform by | 152 // Controls whether the feature should be available in the platform by |
| 124 // default, in the absence of any declared policy. | 153 // default, in the absence of any declared policy. |
| 125 FeatureDefault defaultPolicy; | 154 FeatureDefault default_policy; |
| 126 }; | 155 }; |
| 127 | 156 |
| 128 using FeatureList = const Vector<const FeaturePolicy::Feature*>; | 157 using FeatureList = |
| 158 std::map<blink::WebFeaturePolicyFeature, const FeaturePolicy::Feature*>; | |
| 129 | 159 |
| 130 // Converts a JSON feature policy string into a vector of whitelists, one for | 160 ~FeaturePolicy() override; |
| 131 // each feature specified. Unrecognized features are parsed and included | |
| 132 // but will be filtered out when the policy is constructed. If |messages| is | |
| 133 // not null, then any errors in the input will cause an error message to be | |
| 134 // appended to it. | |
| 135 static WebParsedFeaturePolicy parseFeaturePolicy(const String& policy, | |
| 136 RefPtr<SecurityOrigin>, | |
| 137 Vector<String>* messages); | |
| 138 | 161 |
| 139 static std::unique_ptr<FeaturePolicy> createFromParentPolicy( | 162 static std::unique_ptr<FeaturePolicy> CreateFromParentPolicy( |
| 140 const FeaturePolicy* parent, | 163 const FeaturePolicy* parent_policy, |
| 141 RefPtr<SecurityOrigin>); | 164 url::Origin origin); |
| 165 | |
| 166 // Returns whether or not the given feature is enabled by this policy. | |
| 167 bool IsFeatureEnabledForOrigin(blink::WebFeaturePolicyFeature feature, | |
| 168 url::Origin origin) const; | |
| 169 | |
| 170 // Returns whether or not the given feature is enabled for the origin of the | |
| 171 // document that owns the policy. | |
| 172 bool IsFeatureEnabled(blink::WebFeaturePolicyFeature feature) const; | |
| 142 | 173 |
| 143 // Sets the declared policy from the parsed Feature-Policy HTTP header. | 174 // Sets the declared policy from the parsed Feature-Policy HTTP header. |
| 144 // Unrecognized features will be ignored. | 175 // Unrecognized features will be ignored. |
| 145 void setHeaderPolicy(const WebParsedFeaturePolicy&); | 176 void SetHeaderPolicy(const FeaturePolicyHeader& parsed_header); |
| 146 | |
| 147 // Returns whether or not the given feature is enabled by this policy. | |
| 148 bool isFeatureEnabledForOrigin(const Feature&, const SecurityOrigin&) const; | |
| 149 | |
| 150 // Returns whether or not the given feature is enabled for the frame that owns | |
| 151 // the policy. | |
| 152 bool isFeatureEnabled(const Feature&) const; | |
| 153 | |
| 154 // Returns the list of features which can be controlled by Feature Policy. | |
| 155 static FeatureList& getDefaultFeatureList(); | |
| 156 | |
| 157 String toString(); | |
| 158 | 177 |
| 159 private: | 178 private: |
| 160 friend class FeaturePolicyTest; | 179 friend class FeaturePolicyTest; |
| 161 friend class FeaturePolicyInFrameTest; | |
| 162 | 180 |
| 163 FeaturePolicy(RefPtr<SecurityOrigin>, FeatureList& features); | 181 explicit FeaturePolicy(url::Origin origin); |
| 182 FeaturePolicy(url::Origin origin, const FeatureList& feature_list); | |
| 183 static std::unique_ptr<FeaturePolicy> CreateFromParentPolicy( | |
| 184 const FeaturePolicy* parent_policy, | |
| 185 url::Origin origin, | |
| 186 const FeatureList& features); | |
| 164 | 187 |
| 165 static std::unique_ptr<FeaturePolicy> createFromParentPolicy( | 188 // Returns the list of features which can be controlled by Feature Policy. |
| 166 const FeaturePolicy* parent, | 189 static const FeatureList& getDefaultFeatureList(); |
| 167 RefPtr<SecurityOrigin>, | |
| 168 FeatureList& features); | |
| 169 | 190 |
| 170 RefPtr<SecurityOrigin> m_origin; | 191 url::Origin origin_; |
| 192 | |
| 193 // Map of feature names to declared whitelists. Any feature which is missing | |
| 194 // from this map should use the inherited policy. | |
| 195 std::map<blink::WebFeaturePolicyFeature, std::unique_ptr<Whitelist>> | |
| 196 whitelists_; | |
| 171 | 197 |
| 172 // Records whether or not each feature was enabled for this frame by its | 198 // Records whether or not each feature was enabled for this frame by its |
| 173 // parent frame. | 199 // parent frame. |
| 174 // TODO(iclelland): Generate, instead of this map, a set of bool flags, one | 200 // TODO(iclelland): Generate, instead of this map, a set of bool flags, one |
| 175 // for each feature, as all features are supposed to be represented here. | 201 // for each feature, as all features are supposed to be represented here. |
| 176 HashMap<const Feature*, bool> m_inheritedFeatures; | 202 std::map<blink::WebFeaturePolicyFeature, bool> inherited_policies_; |
| 177 | 203 |
| 178 // Map of feature names to declared whitelists. Any feature which is missing | 204 const FeatureList& feature_list_; |
| 179 // from this map should use the inherited policy. | |
| 180 HashMap<const Feature*, std::unique_ptr<Whitelist>> m_headerWhitelists; | |
| 181 | |
| 182 // Contains the set of all features which can be controlled by this policy. | |
| 183 FeatureList& m_features; | |
| 184 | |
| 185 DISALLOW_COPY_AND_ASSIGN(FeaturePolicy); | |
| 186 }; | 205 }; |
| 187 | 206 |
| 188 // Declarations for all features currently under control of the Feature Policy | 207 } // namespace content |
| 189 // mechanism should be placed here. | |
| 190 extern const PLATFORM_EXPORT FeaturePolicy::Feature kDocumentCookie; | |
| 191 extern const PLATFORM_EXPORT FeaturePolicy::Feature kDocumentDomain; | |
| 192 extern const PLATFORM_EXPORT FeaturePolicy::Feature kDocumentWrite; | |
| 193 extern const PLATFORM_EXPORT FeaturePolicy::Feature kGeolocationFeature; | |
| 194 extern const PLATFORM_EXPORT FeaturePolicy::Feature kFullscreenFeature; | |
| 195 extern const PLATFORM_EXPORT FeaturePolicy::Feature kMidiFeature; | |
| 196 extern const PLATFORM_EXPORT FeaturePolicy::Feature kNotificationsFeature; | |
| 197 extern const PLATFORM_EXPORT FeaturePolicy::Feature kPaymentFeature; | |
| 198 extern const PLATFORM_EXPORT FeaturePolicy::Feature kPushFeature; | |
| 199 extern const PLATFORM_EXPORT FeaturePolicy::Feature kSyncScript; | |
| 200 extern const PLATFORM_EXPORT FeaturePolicy::Feature kSyncXHR; | |
| 201 extern const PLATFORM_EXPORT FeaturePolicy::Feature kUsermedia; | |
| 202 extern const PLATFORM_EXPORT FeaturePolicy::Feature kVibrateFeature; | |
| 203 extern const PLATFORM_EXPORT FeaturePolicy::Feature kWebRTC; | |
| 204 | 208 |
| 205 } // namespace blink | 209 #endif // CONTENT_COMMON_FEATURE_POLICY_FEATURE_POLICY_H_ |
| 206 | |
| 207 #endif // FeaturePolicy_h | |
| OLD | NEW |