@ -37,7 +37,10 @@
# include "src/core/ext/xds/xds_bootstrap.h"
# include "src/core/ext/xds/xds_bootstrap.h"
# include "src/core/ext/xds/xds_channel_args.h"
# include "src/core/ext/xds/xds_channel_args.h"
# include "src/core/ext/xds/xds_client_stats.h"
# include "src/core/ext/xds/xds_client_stats.h"
# include "src/core/ext/xds/xds_cluster.h"
# include "src/core/ext/xds/xds_endpoint.h"
# include "src/core/ext/xds/xds_http_filters.h"
# include "src/core/ext/xds/xds_http_filters.h"
# include "src/core/ext/xds/xds_listener.h"
# include "src/core/lib/address_utils/sockaddr_utils.h"
# include "src/core/lib/address_utils/sockaddr_utils.h"
# include "src/core/lib/backoff/backoff.h"
# include "src/core/lib/backoff/backoff.h"
# include "src/core/lib/channel/channel_args.h"
# include "src/core/lib/channel/channel_args.h"
@ -76,11 +79,6 @@ const grpc_channel_args* g_channel_args ABSL_GUARDED_BY(*g_mu) = nullptr;
XdsClient * g_xds_client ABSL_GUARDED_BY ( * g_mu ) = nullptr ;
XdsClient * g_xds_client ABSL_GUARDED_BY ( * g_mu ) = nullptr ;
char * g_fallback_bootstrap_config ABSL_GUARDED_BY ( * g_mu ) = nullptr ;
char * g_fallback_bootstrap_config ABSL_GUARDED_BY ( * g_mu ) = nullptr ;
const char * kLdsTypeUrl = " envoy.config.listener.v3.Listener " ;
const char * kRdsTypeUrl = " envoy.config.route.v3.RouteConfiguration " ;
const char * kCdsTypeUrl = " envoy.config.cluster.v3.Cluster " ;
const char * kEdsTypeUrl = " envoy.config.endpoint.v3.ClusterLoadAssignment " ;
} // namespace
} // namespace
class XdsClient : : Notifier {
class XdsClient : : Notifier {
@ -202,7 +200,8 @@ class XdsClient::ChannelState::AdsCallState
explicit AdsResponseParser ( AdsCallState * ads_call_state )
explicit AdsResponseParser ( AdsCallState * ads_call_state )
: ads_call_state_ ( ads_call_state ) { }
: ads_call_state_ ( ads_call_state ) { }
absl : : Status ProcessAdsResponseFields ( AdsResponseFields fields ) override ;
absl : : Status ProcessAdsResponseFields ( AdsResponseFields fields ) override
ABSL_EXCLUSIVE_LOCKS_REQUIRED ( & XdsClient : : mu_ ) ;
void ParseResource ( const XdsEncodingContext & context , size_t idx ,
void ParseResource ( const XdsEncodingContext & context , size_t idx ,
absl : : string_view type_url ,
absl : : string_view type_url ,
@ -745,7 +744,7 @@ absl::Status XdsClient::ChannelState::AdsCallState::AdsResponseParser::
fields . version . c_str ( ) , fields . nonce . c_str ( ) , fields . num_resources ) ;
fields . version . c_str ( ) , fields . nonce . c_str ( ) , fields . num_resources ) ;
}
}
result_ . type =
result_ . type =
XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( fields . type_url ) ;
ads_call_state_ - > xds_client ( ) - > GetResource TypeLocked ( fields . type_url ) ;
if ( result_ . type = = nullptr ) {
if ( result_ . type = = nullptr ) {
return absl : : InvalidArgumentError (
return absl : : InvalidArgumentError (
absl : : StrCat ( " unknown resource type " , fields . type_url ) ) ;
absl : : StrCat ( " unknown resource type " , fields . type_url ) ) ;
@ -1778,7 +1777,7 @@ XdsClient::XdsClient(std::unique_ptr<XdsBootstrap> bootstrap,
certificate_provider_store_ ( MakeOrphanable < CertificateProviderStore > (
certificate_provider_store_ ( MakeOrphanable < CertificateProviderStore > (
bootstrap_ - > certificate_providers ( ) ) ) ,
bootstrap_ - > certificate_providers ( ) ) ) ,
api_ ( this , & grpc_xds_client_trace , bootstrap_ - > node ( ) ,
api_ ( this , & grpc_xds_client_trace , bootstrap_ - > node ( ) ,
& bootstrap_ - > certificate_providers ( ) ) {
& bootstrap_ - > certificate_providers ( ) , & symtab_ ) {
if ( GRPC_TRACE_FLAG_ENABLED ( grpc_xds_client_trace ) ) {
if ( GRPC_TRACE_FLAG_ENABLED ( grpc_xds_client_trace ) ) {
gpr_log ( GPR_INFO , " [xds_client %p] creating xds client " , this ) ;
gpr_log ( GPR_INFO , " [xds_client %p] creating xds client " , this ) ;
}
}
@ -1836,6 +1835,7 @@ void XdsClient::WatchResource(const XdsResourceType* type,
if ( ! resource_name . ok ( ) ) {
if ( ! resource_name . ok ( ) ) {
{
{
MutexLock lock ( & mu_ ) ;
MutexLock lock ( & mu_ ) ;
MaybeRegisterResourceTypeLocked ( type ) ;
invalid_watchers_ [ w ] = watcher ;
invalid_watchers_ [ w ] = watcher ;
}
}
grpc_error_handle error = GRPC_ERROR_CREATE_FROM_CPP_STRING (
grpc_error_handle error = GRPC_ERROR_CREATE_FROM_CPP_STRING (
@ -1851,6 +1851,7 @@ void XdsClient::WatchResource(const XdsResourceType* type,
}
}
{
{
MutexLock lock ( & mu_ ) ;
MutexLock lock ( & mu_ ) ;
MaybeRegisterResourceTypeLocked ( type ) ;
// TODO(donnadionne): If we get a request for an authority that is not
// TODO(donnadionne): If we get a request for an authority that is not
// configured in the bootstrap file, reject it.
// configured in the bootstrap file, reject it.
AuthorityState & authority_state =
AuthorityState & authority_state =
@ -1924,64 +1925,25 @@ void XdsClient::CancelResourceWatch(const XdsResourceType* type,
}
}
}
}
void XdsClient : : WatchListenerData (
void XdsClient : : MaybeRegisterResourceTypeLocked (
absl : : string_view listener_name ,
const XdsResourceType * resource_type ) {
RefCountedPtr < ListenerWatcherInterface > watcher ) {
auto it = resource_types_ . find ( resource_type - > type_url ( ) ) ;
WatchResource ( XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kLdsTypeUrl ) ,
if ( it ! = resource_types_ . end ( ) ) {
listener_name , std : : move ( watcher ) ) ;
GPR_ASSERT ( it - > second = = resource_type ) ;
}
return ;
}
void XdsClient : : CancelListenerDataWatch ( absl : : string_view listener_name ,
resource_types_ . emplace ( resource_type - > type_url ( ) , resource_type ) ;
ListenerWatcherInterface * watcher ,
v2_resource_types_ . emplace ( resource_type - > v2_type_url ( ) , resource_type ) ;
bool delay_unsubscription ) {
resource_type - > InitUpbSymtab ( symtab_ . ptr ( ) ) ;
CancelResourceWatch (
XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kLdsTypeUrl ) ,
listener_name , watcher , delay_unsubscription ) ;
}
void XdsClient : : WatchRouteConfigData (
absl : : string_view route_config_name ,
RefCountedPtr < RouteConfigWatcherInterface > watcher ) {
WatchResource ( XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kRdsTypeUrl ) ,
route_config_name , std : : move ( watcher ) ) ;
}
void XdsClient : : CancelRouteConfigDataWatch ( absl : : string_view route_config_name ,
RouteConfigWatcherInterface * watcher ,
bool delay_unsubscription ) {
CancelResourceWatch (
XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kRdsTypeUrl ) ,
route_config_name , watcher , delay_unsubscription ) ;
}
void XdsClient : : WatchClusterData (
absl : : string_view cluster_name ,
RefCountedPtr < ClusterWatcherInterface > watcher ) {
WatchResource ( XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kCdsTypeUrl ) ,
cluster_name , std : : move ( watcher ) ) ;
}
void XdsClient : : CancelClusterDataWatch ( absl : : string_view cluster_name ,
ClusterWatcherInterface * watcher ,
bool delay_unsubscription ) {
CancelResourceWatch (
XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kCdsTypeUrl ) ,
cluster_name , watcher , delay_unsubscription ) ;
}
void XdsClient : : WatchEndpointData (
absl : : string_view eds_service_name ,
RefCountedPtr < EndpointWatcherInterface > watcher ) {
WatchResource ( XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kEdsTypeUrl ) ,
eds_service_name , std : : move ( watcher ) ) ;
}
}
void XdsClient : : CancelEndpointDataWatch ( absl : : string_view eds_service_name ,
const XdsResourceType * XdsClient : : GetResourceTypeLocked (
EndpointWatcherInterface * watcher ,
absl : : string_view resource_type ) {
bool delay_unsubscription ) {
auto it = resource_types_ . find ( resource_type ) ;
CancelResourceWatch (
if ( it ! = resource_types_ . end ( ) ) return it - > second ;
XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kEdsTypeUrl ) ,
auto it2 = v2_resource_types_ . find ( resource_type ) ;
eds_service_name , watcher , delay_unsubscription ) ;
if ( it2 ! = v2_resource_types_ . end ( ) ) return it2 - > second ;
return nullptr ;
}
}
absl : : StatusOr < XdsClient : : XdsResourceName > XdsClient : : ParseXdsResourceName (
absl : : StatusOr < XdsClient : : XdsResourceName > XdsClient : : ParseXdsResourceName (
@ -2050,9 +2012,8 @@ RefCountedPtr<XdsClusterDropStats> XdsClient::AddClusterDropStats(
it - > first . second /*eds_service_name*/ ) ;
it - > first . second /*eds_service_name*/ ) ;
load_report_state . drop_stats = cluster_drop_stats . get ( ) ;
load_report_state . drop_stats = cluster_drop_stats . get ( ) ;
}
}
auto resource_name = ParseXdsResourceName (
auto resource_name =
cluster_name ,
ParseXdsResourceName ( cluster_name , XdsClusterResourceType : : Get ( ) ) ;
XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kCdsTypeUrl ) ) ;
GPR_ASSERT ( resource_name . ok ( ) ) ;
GPR_ASSERT ( resource_name . ok ( ) ) ;
auto a = authority_state_map_ . find ( resource_name - > authority ) ;
auto a = authority_state_map_ . find ( resource_name - > authority ) ;
if ( a ! = authority_state_map_ . end ( ) ) {
if ( a ! = authority_state_map_ . end ( ) ) {
@ -2114,9 +2075,8 @@ RefCountedPtr<XdsClusterLocalityStats> XdsClient::AddClusterLocalityStats(
std : : move ( locality ) ) ;
std : : move ( locality ) ) ;
locality_state . locality_stats = cluster_locality_stats . get ( ) ;
locality_state . locality_stats = cluster_locality_stats . get ( ) ;
}
}
auto resource_name = ParseXdsResourceName (
auto resource_name =
cluster_name ,
ParseXdsResourceName ( cluster_name , XdsClusterResourceType : : Get ( ) ) ;
XdsResourceTypeRegistry : : GetOrCreate ( ) - > GetType ( kCdsTypeUrl ) ) ;
GPR_ASSERT ( resource_name . ok ( ) ) ;
GPR_ASSERT ( resource_name . ok ( ) ) ;
auto a = authority_state_map_ . find ( resource_name - > authority ) ;
auto a = authority_state_map_ . find ( resource_name - > authority ) ;
if ( a ! = authority_state_map_ . end ( ) ) {
if ( a ! = authority_state_map_ . end ( ) ) {
@ -2285,23 +2245,9 @@ std::string XdsClient::DumpClientConfigBinary() {
// accessors for global state
// accessors for global state
//
//
namespace {
void InitResourceTypeRegistry ( ) {
auto * registry = XdsResourceTypeRegistry : : GetOrCreate ( ) ;
registry - > RegisterType ( absl : : make_unique < XdsListenerResourceType > ( ) ) ;
registry - > RegisterType ( absl : : make_unique < XdsRouteConfigResourceType > ( ) ) ;
registry - > RegisterType ( absl : : make_unique < XdsClusterResourceType > ( ) ) ;
registry - > RegisterType ( absl : : make_unique < XdsEndpointResourceType > ( ) ) ;
}
} // namespace
void XdsClientGlobalInit ( ) {
void XdsClientGlobalInit ( ) {
g_mu = new Mutex ;
g_mu = new Mutex ;
XdsHttpFilterRegistry : : Init ( ) ;
XdsHttpFilterRegistry : : Init ( ) ;
static gpr_once once = GPR_ONCE_INIT ;
gpr_once_init ( & once , InitResourceTypeRegistry ) ;
}
}
// TODO(roth): Find a better way to clear the fallback config that does
// TODO(roth): Find a better way to clear the fallback config that does