mirror of
https://github.com/faucetsdn/ryu.git
synced 2026-05-05 12:26:11 +02:00
bgp: use sendall with lock
With the current design, multiple greenlets calls sendall() on a single tcp socket. This leads to a corrupted bgp message. This patch introduces mutex to work around the problem. However, I hope that we _fix_ the design where only one greenlet call sendall() on a signel tcp socket in the future. Signed-off-by: FUJITA Tomonori <fujita.tomonori@lab.ntt.co.jp>
This commit is contained in:
parent
783663afb2
commit
f513b8751d
@ -21,6 +21,7 @@ import socket
|
||||
import struct
|
||||
import traceback
|
||||
from socket import IPPROTO_TCP, TCP_NODELAY
|
||||
from eventlet import semaphore
|
||||
|
||||
from ryu.lib.packet import bgp
|
||||
from ryu.lib.packet.bgp import RouteFamily
|
||||
@ -104,6 +105,7 @@ class BgpProtocol(Protocol, Activity):
|
||||
self._recv_buff = ''
|
||||
self._socket = socket
|
||||
self._socket.setsockopt(IPPROTO_TCP, TCP_NODELAY, 1)
|
||||
self._sendlock = semaphore.Semaphore()
|
||||
self._signal_bus = signal_bus
|
||||
self._holdtime = None
|
||||
self._keepalive = None
|
||||
@ -362,7 +364,7 @@ class BgpProtocol(Protocol, Activity):
|
||||
"""
|
||||
notification = BGPNotification(code, subcode)
|
||||
reason = notification.reason
|
||||
self._socket.sendall(notification.serialize())
|
||||
self._send_with_lock(notification)
|
||||
self._signal_bus.bgp_error(self._peer, code, subcode, reason)
|
||||
LOG.error(
|
||||
'Sent notification to %r >> %s' %
|
||||
@ -370,6 +372,13 @@ class BgpProtocol(Protocol, Activity):
|
||||
)
|
||||
self._socket.close()
|
||||
|
||||
def _send_with_lock(self, msg):
|
||||
self._sendlock.acquire()
|
||||
try:
|
||||
self._socket.sendall(msg.serialize())
|
||||
finally:
|
||||
self._sendlock.release()
|
||||
|
||||
def send(self, msg):
|
||||
if not self.started:
|
||||
raise BgpProtocolException('Tried to send message to peer when '
|
||||
@ -378,7 +387,7 @@ class BgpProtocol(Protocol, Activity):
|
||||
# get peername before senging msg because sending msg can occur
|
||||
# conncetion lost
|
||||
peername = self.get_peername()
|
||||
self._socket.sendall(msg.serialize())
|
||||
self._send_with_lock(msg)
|
||||
|
||||
if msg.type == BGP_MSG_NOTIFICATION:
|
||||
LOG.error('Sent notification to %s >> %s' %
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user