1 //
2 //
3 // Copyright 2020 gRPC authors.
4 //
5 // Licensed under the Apache License, Version 2.0 (the "License");
6 // you may not use this file except in compliance with the License.
7 // You may obtain a copy of the License at
8 //
9 //     http://www.apache.org/licenses/LICENSE-2.0
10 //
11 // Unless required by applicable law or agreed to in writing, software
12 // distributed under the License is distributed on an "AS IS" BASIS,
13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 // See the License for the specific language governing permissions and
15 // limitations under the License.
16 //
17 //
18 
19 #include <grpc/support/port_platform.h>
20 
21 #include "src/core/lib/security/authorization/evaluate_args.h"
22 
23 #include "src/core/lib/iomgr/parse_address.h"
24 #include "src/core/lib/iomgr/resolve_address.h"
25 #include "src/core/lib/iomgr/sockaddr_utils.h"
26 #include "src/core/lib/slice/slice_utils.h"
27 
28 namespace grpc_core {
29 
GetPath() const30 absl::string_view EvaluateArgs::GetPath() const {
31   absl::string_view path;
32   if (metadata_ != nullptr && metadata_->idx.named.path != nullptr) {
33     grpc_linked_mdelem* elem = metadata_->idx.named.path;
34     const grpc_slice& val = GRPC_MDVALUE(elem->md);
35     path = StringViewFromSlice(val);
36   }
37   return path;
38 }
39 
GetHost() const40 absl::string_view EvaluateArgs::GetHost() const {
41   absl::string_view host;
42   if (metadata_ != nullptr && metadata_->idx.named.host != nullptr) {
43     grpc_linked_mdelem* elem = metadata_->idx.named.host;
44     const grpc_slice& val = GRPC_MDVALUE(elem->md);
45     host = StringViewFromSlice(val);
46   }
47   return host;
48 }
49 
GetMethod() const50 absl::string_view EvaluateArgs::GetMethod() const {
51   absl::string_view method;
52   if (metadata_ != nullptr && metadata_->idx.named.method != nullptr) {
53     grpc_linked_mdelem* elem = metadata_->idx.named.method;
54     const grpc_slice& val = GRPC_MDVALUE(elem->md);
55     method = StringViewFromSlice(val);
56   }
57   return method;
58 }
59 
GetHeaders() const60 std::multimap<absl::string_view, absl::string_view> EvaluateArgs::GetHeaders()
61     const {
62   std::multimap<absl::string_view, absl::string_view> headers;
63   if (metadata_ == nullptr) {
64     return headers;
65   }
66   for (grpc_linked_mdelem* elem = metadata_->list.head; elem != nullptr;
67        elem = elem->next) {
68     const grpc_slice& key = GRPC_MDKEY(elem->md);
69     const grpc_slice& val = GRPC_MDVALUE(elem->md);
70     headers.emplace(StringViewFromSlice(key), StringViewFromSlice(val));
71   }
72   return headers;
73 }
74 
GetLocalAddress() const75 absl::string_view EvaluateArgs::GetLocalAddress() const {
76   absl::string_view addr = grpc_endpoint_get_local_address(endpoint_);
77   size_t first_colon = addr.find(":");
78   size_t last_colon = addr.rfind(":");
79   if (first_colon == std::string::npos || last_colon == std::string::npos) {
80     return "";
81   } else {
82     return addr.substr(first_colon + 1, last_colon - first_colon - 1);
83   }
84 }
85 
GetLocalPort() const86 int EvaluateArgs::GetLocalPort() const {
87   if (endpoint_ == nullptr) {
88     return 0;
89   }
90   absl::StatusOr<URI> uri =
91       URI::Parse(grpc_endpoint_get_local_address(endpoint_));
92   grpc_resolved_address resolved_addr;
93   if (!uri.ok() || !grpc_parse_uri(*uri, &resolved_addr)) {
94     return 0;
95   }
96   return grpc_sockaddr_get_port(&resolved_addr);
97 }
98 
GetPeerAddress() const99 absl::string_view EvaluateArgs::GetPeerAddress() const {
100   absl::string_view addr = grpc_endpoint_get_peer(endpoint_);
101   size_t first_colon = addr.find(":");
102   size_t last_colon = addr.rfind(":");
103   if (first_colon == std::string::npos || last_colon == std::string::npos) {
104     return "";
105   } else {
106     return addr.substr(first_colon + 1, last_colon - first_colon - 1);
107   }
108 }
109 
GetPeerPort() const110 int EvaluateArgs::GetPeerPort() const {
111   if (endpoint_ == nullptr) {
112     return 0;
113   }
114   absl::StatusOr<URI> uri = URI::Parse(grpc_endpoint_get_peer(endpoint_));
115   grpc_resolved_address resolved_addr;
116   if (!uri.ok() || !grpc_parse_uri(*uri, &resolved_addr)) {
117     return 0;
118   }
119   return grpc_sockaddr_get_port(&resolved_addr);
120 }
121 
GetSpiffeId() const122 absl::string_view EvaluateArgs::GetSpiffeId() const {
123   if (auth_context_ == nullptr) {
124     return "";
125   }
126   grpc_auth_property_iterator it = grpc_auth_context_find_properties_by_name(
127       auth_context_, GRPC_PEER_SPIFFE_ID_PROPERTY_NAME);
128   const grpc_auth_property* prop = grpc_auth_property_iterator_next(&it);
129   if (prop == nullptr || grpc_auth_property_iterator_next(&it) != nullptr) {
130     return "";
131   }
132   return absl::string_view(prop->value, prop->value_length);
133 }
134 
GetCertServerName() const135 absl::string_view EvaluateArgs::GetCertServerName() const {
136   if (auth_context_ == nullptr) {
137     return "";
138   }
139   grpc_auth_property_iterator it = grpc_auth_context_find_properties_by_name(
140       auth_context_, GRPC_X509_CN_PROPERTY_NAME);
141   const grpc_auth_property* prop = grpc_auth_property_iterator_next(&it);
142   if (prop == nullptr || grpc_auth_property_iterator_next(&it) != nullptr) {
143     return "";
144   }
145   return absl::string_view(prop->value, prop->value_length);
146 }
147 
148 }  // namespace grpc_core
149