summaryrefslogtreecommitdiff
path: root/chromium/services/network/public/cpp/cors/origin_access_list.h
blob: 8591e978de61afea621c0e2bdb2197c6d4d5402f (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
// Copyright 2018 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.

#ifndef SERVICES_NETWORK_PUBLIC_CPP_CORS_ORIGIN_ACCESS_LIST_H_
#define SERVICES_NETWORK_PUBLIC_CPP_CORS_ORIGIN_ACCESS_LIST_H_

#include <map>
#include <string>
#include <vector>

#include "base/component_export.h"
#include "base/containers/flat_map.h"
#include "base/macros.h"
#include "mojo/public/cpp/bindings/struct_ptr.h"
#include "services/network/public/cpp/cors/origin_access_entry.h"
#include "services/network/public/mojom/cors_origin_pattern.mojom-shared.h"
#include "url/origin.h"

namespace network {

struct ResourceRequest;

namespace mojom {
class CorsOriginPattern;
class CorsOriginAccessPatterns;
}  // namespace mojom

namespace cors {

// A class to manage origin access allow / block lists. If these lists conflict,
// blocklisting is respected. These lists are managed per source-origin basis.
class COMPONENT_EXPORT(NETWORK_CPP) OriginAccessList {
 public:
  using CorsOriginPatternPtr = mojo::StructPtr<mojom::CorsOriginPattern>;

  // Represents if a queried conditions are is allowed, blocked, or not listed
  // in the access list.
  enum class AccessState {
    kAllowed,
    kBlocked,
    kNotListed,
  };

  OriginAccessList();

  OriginAccessList(const OriginAccessList&) = delete;
  OriginAccessList& operator=(const OriginAccessList&) = delete;

  ~OriginAccessList();

  // Clears the old allow list for |source_origin|, and set |patterns| to the
  // allow list. When two or more patterns in a list match, the entry with the
  // higher |priority| takes precedence.
  void SetAllowListForOrigin(const url::Origin& source_origin,
                             const std::vector<CorsOriginPatternPtr>& patterns);

  // Adds an access pattern by |protocol|, |domain|, |port|,
  // |domain_match_mode|, |port_match_mode|, and |priority| to the allow list
  // for |source_origin|.
  void AddAllowListEntryForOrigin(
      const url::Origin& source_origin,
      const std::string& protocol,
      const std::string& domain,
      const uint16_t port,
      const mojom::CorsDomainMatchMode domain_match_mode,
      const mojom::CorsPortMatchMode port_match_mode,
      const mojom::CorsOriginAccessMatchPriority priority);

  // Clears the old block list for |source_origin| and set |patterns| to the
  // block list. When two or more patterns in a list match, the entry with the
  // higher |priority| takes precedence.
  void SetBlockListForOrigin(const url::Origin& source_origin,
                             const std::vector<CorsOriginPatternPtr>& patterns);

  // Adds an access pattern by |protocol|, |domain|, |port|,
  // |domain_match_mode|, |port_match_mode|, and |priority| to the block list
  // for |source_origin|.
  void AddBlockListEntryForOrigin(
      const url::Origin& source_origin,
      const std::string& protocol,
      const std::string& domain,
      const uint16_t port,
      const mojom::CorsDomainMatchMode domain_match_mode,
      const mojom::CorsPortMatchMode port_match_mode,
      const mojom::CorsOriginAccessMatchPriority priority);

  // Clears the old allow/block lists for |source_origin|.
  void ClearForOrigin(const url::Origin& source_origin);

  // Clears the old allow/block lists.
  void Clear();

  // Returns |destination|'s AccessState in the list for |source_origin|.
  AccessState CheckAccessState(const url::Origin& source_origin,
                               const GURL& destination) const;

  // Returns |request.url|'s AccessState in |this| list for the origin
  // calculated based on |request.request_initiator| and
  // |request.isolated_world_origin|.
  //
  // Note: This helper might not do the right thing when processing redirects
  // (because |request.url| might not be updated yet).
  AccessState CheckAccessState(const ResourceRequest& request) const;

  // Creates mojom::CorsPriginAccessPatterns instance vector that represents
  // |this| OriginAccessList instance.
  std::vector<mojo::StructPtr<mojom::CorsOriginAccessPatterns>>
  CreateCorsOriginAccessPatternsList() const;

 private:
  enum class MapType {
    kAllowPatterns,
    kBlockPatterns,
  };
  using Patterns = std::vector<OriginAccessEntry>;
  using PatternsMap = base::flat_map<MapType, Patterns>;
  using OriginPatternsMap =
      std::map<std::string /* source_origin */, PatternsMap>;

  static void SetForOrigin(const url::Origin& source_origin,
                           const std::vector<CorsOriginPatternPtr>& patterns,
                           OriginPatternsMap* map,
                           MapType type);
  static void AddForOrigin(const url::Origin& source_origin,
                           const CorsOriginPatternPtr& pattern,
                           OriginPatternsMap* map,
                           MapType type);
  static mojom::CorsOriginAccessMatchPriority GetHighestPriorityOfRuleForOrigin(
      const url::Origin& destination_origin,
      const PatternsMap& patterns_map,
      MapType type);

  OriginPatternsMap map_;
};

}  // namespace cors

}  // namespace network

#endif  // SERVICES_NETWORK_PUBLIC_CPP_CORS_ORIGIN_ACCESS_LIST_H_