Find max UDP payload -- python socket send/sendto
<p>How can I find the maximum length of a UDP payload in Python (Python 2), preferably platform-independent?</p>

<p>Specifically, I want to avoid <code>[Errno 90] Message too long</code> AKA <code>errno.EMSGSIZE</code>.</p>

<h3>Background</h3>

<ul>
<li>The maximum allowed by the UDP packet format <a href="http://stackoverflow.com/a/9853152/461834">is 65536</a>).</li>
<li><p>The maximum allowed by the IPv4 packet format <a href="http://stackoverflow.com/a/1098940/461834">seems to be 65507</a>.</p></li>
<li><p>Yet it seems that <a href="http://stackoverflow.com/a/35335138/461834">some systems set the limit lower</a>.</p></li>
</ul>

<h3>What I am not asking</h3>

<ul>
<li><a href="http://stackoverflow.com/questions/1098897/what-is-the-largest-safe-udp-packet-size-on-the-internet">What is the largest Safe UDP Packet Size on the Internet</a>?</li>
<li>What is the maximum UDP payload that can fit in one IPv4 datagram?</li>
<li>What is the maximum UDP payload that can fit in one Ethernet frame?</li>
</ul>

<h3>Demo Code</h3>

<p>To see the error in action:</p>

<pre><code>import socket

msg_len = 65537  # Not even possible!

ip_address = "127.0.0.1"
port = 5005
msg = "A" * msg_len

sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
sock.sendto(msg, (ip_address, port))
</code></pre>

<p>Well, there's always the try-it-and-see approach... I wouldn't call this elegant, but it is platform-independent:</p>

<pre><code>import socket

def canSendUDPPacketOfSize(sock, packetSize):
   ip_address = "127.0.0.1"
   port = 5005
   try:
      msg = "A" * packetSize
      if (sock.sendto(msg, (ip_address, port)) == len(msg)):
         return True
   except:
      pass
   return False

def get_max_udp_packet_size_aux(sock, largestKnownGoodSize, smallestKnownBadSize):
   if ((largestKnownGoodSize+1) == smallestKnownBadSize):
      return largestKnownGoodSize
   else:
      newMidSize = int((largestKnownGoodSize+smallestKnownBadSize)/2)
      if (canSendUDPPacketOfSize(sock, newMidSize)):
         return get_max_udp_packet_size_aux(sock, newMidSize, smallestKnownBadSize)
      else:
         return get_max_udp_packet_size_aux(sock, largestKnownGoodSize, newMidSize)

def get_max_udp_packet_size():
   sock = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
   ret = get_max_udp_packet_size_aux(sock, 0, 65508)
   sock.close()
   return ret

print "Maximum UDP packet send size is", get_max_udp_packet_size()
</code></pre>

python sockets networking udp