-
Notifications
You must be signed in to change notification settings - Fork 4.8k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
add matching types for network streams
Signed-off-by: Kuat Yessenov <kuat@google.com>
- Loading branch information
Showing
6 changed files
with
419 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,83 @@ | ||
syntax = "proto3"; | ||
|
||
package envoy.type.matcher.v3; | ||
|
||
import "udpa/annotations/status.proto"; | ||
import "validate/validate.proto"; | ||
|
||
option java_package = "io.envoyproxy.envoy.type.matcher.v3"; | ||
option java_outer_classname = "NetworkInputsProto"; | ||
option java_multiple_files = true; | ||
option go_package = "github.com/envoyproxy/go-control-plane/envoy/type/matcher/v3;matcherv3"; | ||
option (udpa.annotations.file_status).package_version_status = ACTIVE; | ||
|
||
// [#protodoc-title: Common Network Matching Inputs] | ||
|
||
// Specifies that matching should be performed by the destination IP address. | ||
message DestinationIPInput { | ||
} | ||
|
||
// Specifies that matching should be performed by the destination port. | ||
message DestinationPortInput { | ||
} | ||
|
||
// Specifies that matching should be performed by the source IP address. | ||
message SourceIPInput { | ||
} | ||
|
||
// Specifies that matching should be performed by the source port. | ||
message SourcePortInput { | ||
} | ||
|
||
// Input that matches by the directly connected source IP address (this | ||
// will only be different from the source IP address when using a listener | ||
// filter that overrides the source address, such as the :ref:`Proxy Protocol | ||
// listener filter <config_listener_filters_proxy_protocol>`). | ||
message DirectSourceIPInput { | ||
} | ||
|
||
// Input that matches by the source IP type. | ||
// Specifies the source IP match type. The values include: | ||
// | ||
// * ``local`` - matches a connection originating from the same host, | ||
message SourceTypeInput { | ||
} | ||
|
||
// Input that matches by the requested server name (e.g. SNI in TLS), when detected by one of the listener filters. | ||
// | ||
// :ref:`TLS Inspector <config_listener_filters_tls_inspector>` provides the requested server name based on SNI. | ||
message ServerNameInput { | ||
} | ||
|
||
// Input that matches by the transport protocol, when | ||
// detected by one of the listener filters. | ||
// | ||
// Suggested values include: | ||
// | ||
// * ``raw_buffer`` - default, used when no transport protocol is detected, | ||
// * ``tls`` - set by :ref:`envoy.filters.listener.tls_inspector <config_listener_filters_tls_inspector>` | ||
// when TLS protocol is detected. | ||
message TransportProtocolInput { | ||
} | ||
|
||
// List of comma-separated requested application protocols, when detected by one of the listener filters. | ||
// | ||
// Suggested values in the list include: | ||
// | ||
// * ``http/1.1`` - set by :ref:`envoy.filters.listener.tls_inspector | ||
// <config_listener_filters_tls_inspector>` and :ref:`envoy.filters.listener.http_inspector | ||
// <config_listener_filters_http_inspector>`, | ||
// * ``h2`` - set by :ref:`envoy.filters.listener.tls_inspector <config_listener_filters_tls_inspector>` | ||
// * ``h2c`` - set by :ref:`envoy.filters.listener.http_inspector <config_listener_filters_http_inspector>` | ||
// | ||
// .. attention:: | ||
// | ||
// Currently, :ref:`TLS Inspector <config_listener_filters_tls_inspector>` provides | ||
// application protocol detection based on the requested | ||
// `ALPN <https://en.wikipedia.org/wiki/Application-Layer_Protocol_Negotiation>`_ values. | ||
// | ||
// However, the use of ALPN is pretty much limited to the HTTP/2 traffic on the Internet, | ||
// and matching on values other than ``h2`` is going to lead to a lot of false negatives, | ||
// unless all connecting clients are known to use ALPN. | ||
message ApplicationProtocolInput { | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
load( | ||
"//bazel:envoy_build_system.bzl", | ||
"envoy_cc_library", | ||
"envoy_package", | ||
) | ||
|
||
licenses(["notice"]) # Apache 2 | ||
|
||
envoy_package() | ||
|
||
envoy_cc_library( | ||
name = "data_impl_lib", | ||
hdrs = ["data_impl.h"], | ||
deps = [ | ||
"//envoy/network:filter_interface", | ||
], | ||
) | ||
|
||
envoy_cc_library( | ||
name = "inputs_lib", | ||
srcs = ["inputs.cc"], | ||
hdrs = ["inputs.h"], | ||
deps = [ | ||
"//envoy/matcher:matcher_interface", | ||
"//envoy/network:filter_interface", | ||
"//envoy/registry", | ||
"//source/common/network:utility_lib", | ||
"@envoy_api//envoy/type/matcher/v3:pkg_cc_proto", | ||
], | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,27 @@ | ||
#pragma once | ||
|
||
#include "envoy/network/filter.h" | ||
|
||
namespace Envoy { | ||
namespace Network { | ||
namespace Matching { | ||
|
||
/** | ||
* Implementation of Network::MatchingData, providing connection-level data to | ||
* the match tree. | ||
*/ | ||
class MatchingDataImpl : public MatchingData { | ||
public: | ||
static absl::string_view name() { return "network"; } | ||
|
||
void onSocket(const ConnectionSocket& socket) { socket_ = &socket; } | ||
|
||
virtual const ConnectionSocket& socket() { return *socket_; } | ||
|
||
private: | ||
const ConnectionSocket* socket_{}; | ||
}; | ||
|
||
} // namespace Matching | ||
} // namespace Network | ||
} // namespace Envoy |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,99 @@ | ||
#include "source/common/network/matching/inputs.h" | ||
|
||
#include "envoy/registry/registry.h" | ||
|
||
#include "source/common/network/utility.h" | ||
|
||
#include "absl/strings/str_cat.h" | ||
|
||
namespace Envoy { | ||
namespace Network { | ||
namespace Matching { | ||
|
||
Matcher::DataInputGetResult DestinationIPInput::get(const MatchingData& data) const { | ||
const auto& address = data.socket().connectionInfoProvider().localAddress(); | ||
if (address->type() != Network::Address::Type::Ip) { | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, absl::nullopt}; | ||
} | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, | ||
address->ip()->addressAsString()}; | ||
} | ||
|
||
Matcher::DataInputGetResult DestinationPortInput::get(const MatchingData& data) const { | ||
const auto& address = data.socket().connectionInfoProvider().localAddress(); | ||
if (address->type() != Network::Address::Type::Ip) { | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, absl::nullopt}; | ||
} | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, | ||
absl::StrCat(address->ip()->port())}; | ||
} | ||
|
||
Matcher::DataInputGetResult SourceIPInput::get(const MatchingData& data) const { | ||
const auto& address = data.socket().connectionInfoProvider().remoteAddress(); | ||
if (address->type() != Network::Address::Type::Ip) { | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, absl::nullopt}; | ||
} | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, | ||
address->ip()->addressAsString()}; | ||
} | ||
|
||
Matcher::DataInputGetResult SourcePortInput::get(const MatchingData& data) const { | ||
const auto& address = data.socket().connectionInfoProvider().remoteAddress(); | ||
if (address->type() != Network::Address::Type::Ip) { | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, absl::nullopt}; | ||
} | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, | ||
absl::StrCat(address->ip()->port())}; | ||
} | ||
|
||
Matcher::DataInputGetResult DirectSourceIPInput::get(const MatchingData& data) const { | ||
const auto& address = data.socket().connectionInfoProvider().directRemoteAddress(); | ||
if (address->type() != Network::Address::Type::Ip) { | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, absl::nullopt}; | ||
} | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, | ||
address->ip()->addressAsString()}; | ||
} | ||
|
||
Matcher::DataInputGetResult SourceTypeInput::get(const MatchingData& data) const { | ||
const bool is_local_connection = Network::Utility::isSameIpOrLoopback(data.socket()); | ||
if (is_local_connection) { | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, "local"}; | ||
} | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, absl::nullopt}; | ||
} | ||
|
||
Matcher::DataInputGetResult ServerNameInput::get(const MatchingData& data) const { | ||
if (!data.socket().requestedServerName().empty()) { | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, | ||
std::string(data.socket().requestedServerName())}; | ||
} | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, absl::nullopt}; | ||
} | ||
|
||
Matcher::DataInputGetResult TransportProtocolInput::get(const MatchingData& data) const { | ||
if (!data.socket().detectedTransportProtocol().empty()) { | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, | ||
std::string(data.socket().detectedTransportProtocol())}; | ||
} | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, absl::nullopt}; | ||
} | ||
|
||
Matcher::DataInputGetResult ApplicationProtocolInput::get(const MatchingData& data) const { | ||
return {Matcher::DataInputGetResult::DataAvailability::AllDataAvailable, | ||
absl::StrJoin(data.socket().requestedApplicationProtocols(), ",")}; | ||
} | ||
|
||
REGISTER_FACTORY(DestinationIPInputFactory, Matcher::DataInputFactory<MatchingData>); | ||
REGISTER_FACTORY(DestinationPortInputFactory, Matcher::DataInputFactory<MatchingData>); | ||
REGISTER_FACTORY(SourceIPInputFactory, Matcher::DataInputFactory<MatchingData>); | ||
REGISTER_FACTORY(SourcePortInputFactory, Matcher::DataInputFactory<MatchingData>); | ||
REGISTER_FACTORY(DirectSourceIPInputFactory, Matcher::DataInputFactory<MatchingData>); | ||
REGISTER_FACTORY(SourceTypeInputFactory, Matcher::DataInputFactory<MatchingData>); | ||
REGISTER_FACTORY(ServerNameInputFactory, Matcher::DataInputFactory<MatchingData>); | ||
REGISTER_FACTORY(TransportProtocolInputFactory, Matcher::DataInputFactory<MatchingData>); | ||
REGISTER_FACTORY(ApplicationProtocolInputFactory, Matcher::DataInputFactory<MatchingData>); | ||
|
||
} // namespace Matching | ||
} // namespace Network | ||
} // namespace Envoy |
Oops, something went wrong.