Line data Source code
1 : /* 2 : * Copyright (c) 2013 Juniper Networks, Inc. All rights reserved. 3 : */ 4 : 5 : #include <boost/foreach.hpp> 6 : #include <boost/scoped_ptr.hpp> 7 : 8 : #include "base/task_annotations.h" 9 : #include "bgp/bgp_factory.h" 10 : #include "bgp/bgp_path.h" 11 : #include "bgp/bgp_xmpp_peer_close.h" 12 : #include "bgp/bgp_xmpp_rtarget_manager.h" 13 : #include "bgp/peer_close_manager.h" 14 : #include "bgp/bgp_xmpp_channel.h" 15 : #include "xmpp/xmpp_connection.h" 16 : #include "xmpp/xmpp_server.h" 17 : 18 : using std::string; 19 : using std::vector; 20 : 21 392 : BgpXmppPeerClose::BgpXmppPeerClose(BgpXmppChannel *channel) : 22 392 : channel_(channel) { 23 392 : } 24 : 25 784 : BgpXmppPeerClose::~BgpXmppPeerClose() { 26 784 : } 27 : 28 5719 : PeerCloseManager *BgpXmppPeerClose::GetManager() const { 29 5719 : return channel_->close_manager(); 30 : } 31 : 32 5406 : void BgpXmppPeerClose::UpdateRouteStats(Address::Family family, 33 : const BgpPath *old_path, 34 : uint32_t path_flags) const { 35 5406 : GetManager()->UpdateRouteStats(family, old_path, path_flags); 36 5407 : } 37 : 38 56 : bool BgpXmppPeerClose::IsReady() const { 39 56 : return channel_->Peer()->IsReady(); 40 : } 41 : 42 86781 : IPeer *BgpXmppPeerClose::peer() const { 43 86781 : return channel_->Peer(); 44 : } 45 : 46 36 : int BgpXmppPeerClose::GetGracefulRestartTime() const { 47 36 : return channel_->manager()->xmpp_server()->GetGracefulRestartTime(); 48 : } 49 : 50 16 : int BgpXmppPeerClose::GetLongLivedGracefulRestartTime() const { 51 16 : return channel_->manager()->xmpp_server()-> 52 16 : GetLongLivedGracefulRestartTime(); 53 : } 54 : 55 : // Mark all current subscription as 'stale' 56 : // Concurrency: Protected with a mutex from peer close manager 57 36 : void BgpXmppPeerClose::GracefulRestartStale() { 58 36 : channel_->StaleCurrentSubscriptions(); 59 36 : } 60 : 61 : // Mark all current subscriptions as 'llgr_stale' 62 : // Concurrency: Protected with a mutex from peer close manager 63 8 : void BgpXmppPeerClose::LongLivedGracefulRestartStale() { 64 8 : channel_->LlgrStaleCurrentSubscriptions(); 65 8 : } 66 : 67 : // Delete all current subscriptions which are still stale. 68 : // Concurrency: Protected with a mutex from peer close manager 69 8 : void BgpXmppPeerClose::GracefulRestartSweep() { 70 8 : channel_->SweepCurrentSubscriptions(); 71 8 : } 72 : 73 304 : bool BgpXmppPeerClose::IsCloseGraceful() const { 74 : // Do not close gracefully if connection is already marked for deletion. 75 304 : if (channel_->channel()->connection()->IsDeleted()) 76 144 : return false; 77 160 : return channel_->manager()->xmpp_server()->IsPeerCloseGraceful(); 78 : } 79 : 80 8 : bool BgpXmppPeerClose::IsCloseLongLivedGraceful() const { 81 8 : return IsCloseGraceful() && GetLongLivedGracefulRestartTime() != 0; 82 : } 83 : 84 : // EoR from xmpp is afi independent at the moment. 85 36 : void BgpXmppPeerClose::GetGracefulRestartFamilies(Families *families) const { 86 36 : families->insert(Address::UNSPEC); 87 36 : } 88 : 89 8 : void BgpXmppPeerClose::GetLongLivedGracefulRestartFamilies(Families *families) const { 90 8 : families->insert(Address::UNSPEC); 91 8 : } 92 : 93 8 : void BgpXmppPeerClose::ReceiveEndOfRIB(Address::Family family) { 94 8 : channel_->ReceiveEndOfRIB(family); 95 8 : } 96 : 97 : // Process any pending subscriptions as close manager is now no longer 98 : // using membership manager. 99 212 : void BgpXmppPeerClose::MembershipRequestCallbackComplete() { 100 212 : CHECK_CONCURRENCY(GetTaskName()); 101 212 : if (channel_) { 102 52 : assert(!GetManager()->IsMembershipInUse()); 103 52 : channel_->ProcessPendingSubscriptions(); 104 : } 105 212 : } 106 : 107 11424 : const char *BgpXmppPeerClose::GetTaskName() const { 108 11424 : return "bgp::Config"; 109 : } 110 : 111 392 : int BgpXmppPeerClose::GetTaskInstance() const { 112 392 : return 0; 113 : } 114 : 115 232 : void BgpXmppPeerClose::CustomClose() { 116 232 : channel_->rtarget_manager()->Close(); 117 232 : channel_->ClearSubscriptions(); 118 232 : } 119 : 120 44 : void BgpXmppPeerClose::CloseComplete() { 121 44 : assert(!channel_->channel()->connection()->IsDeleted()); 122 44 : channel_->set_peer_closed(false); 123 44 : channel_->channel()->UnRegisterReceive(xmps::BGP); 124 44 : } 125 : 126 232 : void BgpXmppPeerClose::Delete() { 127 232 : channel_->set_delete_in_progress(true); 128 232 : channel_->set_peer_closed(true); 129 232 : channel_->manager()->increment_deleting_count(); 130 232 : channel_->manager()->Enqueue(channel_); 131 232 : channel_ = NULL; 132 232 : } 133 : 134 260 : void BgpXmppPeerClose::Close(bool graceful) { 135 260 : if (channel_) { 136 260 : assert(channel_->peer_deleted()); 137 260 : if (!IsCloseGraceful()) 138 224 : graceful = false; 139 260 : GetManager()->Close(graceful); 140 : } 141 260 : }