Fix following possible bugs for SIOCSIFADDR, if in_ifinit() fails
commit44a87e427eb5c9e1373c7675af4404f8b7788074
authorSepherosa Ziehau <sephe@dragonflybsd.org>
Mon, 26 May 2008 13:29:33 +0000 (26 13:29 +0000)
committerSepherosa Ziehau <sephe@dragonflybsd.org>
Mon, 26 May 2008 13:29:33 +0000 (26 13:29 +0000)
tree4f6fec9bac1aa9f0eb2f8b8e5f3c934690659b36
parent4b83f092e2c891be34400d3ddace231756b5e393
Fix following possible bugs for SIOCSIFADDR, if in_ifinit() fails
Conditions:
   o  ifaceX has an AF_INET ia
   o  SIOCSIFADDR is used to change address, and new address' hash value is
      different from ia's
   o  ia is currently in hash bucket B1
   o  ia is removed from B1 and installed into hash table using new address
      hash value, assume its new hash bucket is B2, and B1 != B2
1) Dangling ia reference in inaddr hash table
   o  ifnet.if_ioctl fails
   o  ia is reinstalled into hash bucket B1, but without being first removed
      from hash bucket B2
   Hash bucket B2 will have a dangling reference to ia
2) ia is left in wrong hash bucket
   o  rtinit fails
   o  ia's address is restored to oldaddr
   ia itself is left in hash bucket indexed by new address's hash value

- In in_ifinit(), if it fails, unlink ia from inaddr hash table instead of
  delaying the unlinking to in_control_internal().  If necessary reinstall
  ia into inaddr hash table with original address
- After the above fix, in_control_internal() needs to unlink ia from inaddr
  only if cmd is SIOCDIFADDR and ia resides in inaddr hash table.  Whether
  ia is in inaddr hash table or not, is currently indicated by ia address's
  family; add XXX comment that this assumption is not good
- Constfy 'sin' parameter to in_ifinit()

Reviewed-by: dillon@
sys/netinet/in.c