OPENAFS-SA-2018-003 vlserver: prevent unbounded input to VL_RegisterAddrs
authorMark Vitale <mvitale@sinenomine.net>
Fri, 6 Jul 2018 01:11:30 +0000 (21:11 -0400)
committerBenjamin Kaduk <kaduk@mit.edu>
Sun, 9 Sep 2018 22:34:17 +0000 (17:34 -0500)
commit7629209219bbea3f127b33be06ac427ebc3a559e
treea6c25cc6ebbf8a27f72c07852274c881340a6f71
parentf5a80115f8f7f9418287547f0fc7fdb13d936f00
OPENAFS-SA-2018-003 vlserver: prevent unbounded input to VL_RegisterAddrs

VL_RegisterAddrs is defined with an input argument of type bulkaddrs,
which is defined to XDR as an unbounded array of afs_uint32 (IPv4 addresses):
  typedef afs_uint32 bulkaddrs<>

The <> with no value instructs rxgen to build client and server stubs
that allow for a maximum size of "~0u" or 0xFFFFFFFF.

Ostensibly the bulkaddrs array is unbounded to allow it to be shared
among VL_RegisterAddrs, VL_GetAddrs, and VL_GetAddrsU.  The VL_GetAddrs*
RPCs use bulkaddrs as an output array with a maximum size of MAXSERVERID
(254). VL_RegisterAddrss uses bulkaddrs as an input array, with a
nominal size of VL_MAXIPADDRS_PERMH (16).

However, RPCs with unbounded array inputs are susceptible to remote
denial-of-service attacks.  That is, a malicious client may send a
VL_RegisterAddrs request with an arbitrarily long array, forcing the
vlserver to expend large amounts of network bandwidth, cpu cycles, and
heap memory to unmarshal the argument.  Even though VL_RegisterAddrs
requires superuser authorization, this attack is exploitable by
non-authorized actors because XDR unmarshalling happens long before any
authorization checks can occur.

Because all uses of the type that our implementation support have fixed
bounds on valid data (whether input or output), apply an arbitrary
implementation limit (larger than any valid structure would be), to
prevent this class of attacks in the XDR decoder.

[kaduk@mit.edu: limit the bulkaddrs type instead of introducing a new type]

Change-Id: Ibcc962ccc46aec7552b86d1d9fda7cc14310bc03
src/vlserver/vldbint.xg