rt_netlink.c 51 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904
  1. /* Kernel routing table updates using netlink over GNU/Linux system.
  2. * Copyright (C) 1997, 98, 99 Kunihiro Ishiguro
  3. *
  4. * This file is part of GNU Zebra.
  5. *
  6. * GNU Zebra is free software; you can redistribute it and/or modify it
  7. * under the terms of the GNU General Public License as published by the
  8. * Free Software Foundation; either version 2, or (at your option) any
  9. * later version.
  10. *
  11. * GNU Zebra is distributed in the hope that it will be useful, but
  12. * WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  14. * General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU General Public License
  17. * along with GNU Zebra; see the file COPYING. If not, write to the Free
  18. * Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
  19. * 02111-1307, USA.
  20. */
  21. #include <zebra.h>
  22. /* Hack for GNU libc version 2. */
  23. #ifndef MSG_TRUNC
  24. #define MSG_TRUNC 0x20
  25. #endif /* MSG_TRUNC */
  26. #include "linklist.h"
  27. #include "if.h"
  28. #include "log.h"
  29. #include "prefix.h"
  30. #include "connected.h"
  31. #include "table.h"
  32. #include "rib.h"
  33. #include "thread.h"
  34. #include "privs.h"
  35. #include "zebra/zserv.h"
  36. #include "zebra/rt.h"
  37. #include "zebra/redistribute.h"
  38. #include "zebra/interface.h"
  39. #include "zebra/debug.h"
  40. /* Socket interface to kernel */
  41. struct nlsock
  42. {
  43. int sock;
  44. int seq;
  45. struct sockaddr_nl snl;
  46. const char *name;
  47. } netlink = { -1, 0, {0}, "netlink-listen"}, /* kernel messages */
  48. netlink_cmd = { -1, 0, {0}, "netlink-cmd"}; /* command channel */
  49. struct message nlmsg_str[] = {
  50. {RTM_NEWROUTE, "RTM_NEWROUTE"},
  51. {RTM_DELROUTE, "RTM_DELROUTE"},
  52. {RTM_GETROUTE, "RTM_GETROUTE"},
  53. {RTM_NEWLINK, "RTM_NEWLINK"},
  54. {RTM_DELLINK, "RTM_DELLINK"},
  55. {RTM_GETLINK, "RTM_GETLINK"},
  56. {RTM_NEWADDR, "RTM_NEWADDR"},
  57. {RTM_DELADDR, "RTM_DELADDR"},
  58. {RTM_GETADDR, "RTM_GETADDR"},
  59. {0, NULL}
  60. };
  61. const char *nexthop_types_desc[] =
  62. {
  63. "none",
  64. "Directly connected",
  65. "Interface route",
  66. "IPv4 nexthop",
  67. "IPv4 nexthop with ifindex",
  68. "IPv4 nexthop with ifname",
  69. "IPv6 nexthop",
  70. "IPv6 nexthop with ifindex",
  71. "IPv6 nexthop with ifname",
  72. "Null0 nexthop",
  73. };
  74. extern struct zebra_t zebrad;
  75. extern struct zebra_privs_t zserv_privs;
  76. extern u_int32_t nl_rcvbufsize;
  77. /* Note: on netlink systems, there should be a 1-to-1 mapping between interface
  78. names and ifindex values. */
  79. static void
  80. set_ifindex(struct interface *ifp, unsigned int ifi_index)
  81. {
  82. struct interface *oifp;
  83. if (((oifp = if_lookup_by_index(ifi_index)) != NULL) && (oifp != ifp))
  84. {
  85. if (ifi_index == IFINDEX_INTERNAL)
  86. zlog_err("Netlink is setting interface %s ifindex to reserved "
  87. "internal value %u", ifp->name, ifi_index);
  88. else
  89. {
  90. if (IS_ZEBRA_DEBUG_KERNEL)
  91. zlog_debug("interface index %d was renamed from %s to %s",
  92. ifi_index, oifp->name, ifp->name);
  93. if (if_is_up(oifp))
  94. zlog_err("interface rename detected on up interface: index %d "
  95. "was renamed from %s to %s, results are uncertain!",
  96. ifi_index, oifp->name, ifp->name);
  97. if_delete_update(oifp);
  98. }
  99. }
  100. ifp->ifindex = ifi_index;
  101. }
  102. /* Make socket for Linux netlink interface. */
  103. static int
  104. netlink_socket (struct nlsock *nl, unsigned long groups)
  105. {
  106. int ret;
  107. struct sockaddr_nl snl;
  108. int sock;
  109. int namelen;
  110. int save_errno;
  111. sock = socket (AF_NETLINK, SOCK_RAW, NETLINK_ROUTE);
  112. if (sock < 0)
  113. {
  114. zlog (NULL, LOG_ERR, "Can't open %s socket: %s", nl->name,
  115. safe_strerror (errno));
  116. return -1;
  117. }
  118. ret = fcntl (sock, F_SETFL, O_NONBLOCK);
  119. if (ret < 0)
  120. {
  121. zlog (NULL, LOG_ERR, "Can't set %s socket flags: %s", nl->name,
  122. safe_strerror (errno));
  123. close (sock);
  124. return -1;
  125. }
  126. /* Set receive buffer size if it's set from command line */
  127. if (nl_rcvbufsize)
  128. {
  129. u_int32_t oldsize, oldlen;
  130. u_int32_t newsize, newlen;
  131. oldlen = sizeof(oldsize);
  132. newlen = sizeof(newsize);
  133. ret = getsockopt(sock, SOL_SOCKET, SO_RCVBUF, &oldsize, &oldlen);
  134. if (ret < 0)
  135. {
  136. zlog (NULL, LOG_ERR, "Can't get %s receive buffer size: %s", nl->name,
  137. safe_strerror (errno));
  138. close (sock);
  139. return -1;
  140. }
  141. ret = setsockopt(sock, SOL_SOCKET, SO_RCVBUF, &nl_rcvbufsize,
  142. sizeof(nl_rcvbufsize));
  143. if (ret < 0)
  144. {
  145. zlog (NULL, LOG_ERR, "Can't set %s receive buffer size: %s", nl->name,
  146. safe_strerror (errno));
  147. close (sock);
  148. return -1;
  149. }
  150. ret = getsockopt(sock, SOL_SOCKET, SO_RCVBUF, &newsize, &newlen);
  151. if (ret < 0)
  152. {
  153. zlog (NULL, LOG_ERR, "Can't get %s receive buffer size: %s", nl->name,
  154. safe_strerror (errno));
  155. close (sock);
  156. return -1;
  157. }
  158. zlog (NULL, LOG_INFO,
  159. "Setting netlink socket receive buffer size: %u -> %u",
  160. oldsize, newsize);
  161. }
  162. memset (&snl, 0, sizeof snl);
  163. snl.nl_family = AF_NETLINK;
  164. snl.nl_groups = groups;
  165. /* Bind the socket to the netlink structure for anything. */
  166. if (zserv_privs.change (ZPRIVS_RAISE))
  167. {
  168. zlog (NULL, LOG_ERR, "Can't raise privileges");
  169. return -1;
  170. }
  171. ret = bind (sock, (struct sockaddr *) &snl, sizeof snl);
  172. save_errno = errno;
  173. if (zserv_privs.change (ZPRIVS_LOWER))
  174. zlog (NULL, LOG_ERR, "Can't lower privileges");
  175. if (ret < 0)
  176. {
  177. zlog (NULL, LOG_ERR, "Can't bind %s socket to group 0x%x: %s",
  178. nl->name, snl.nl_groups, safe_strerror (save_errno));
  179. close (sock);
  180. return -1;
  181. }
  182. /* multiple netlink sockets will have different nl_pid */
  183. namelen = sizeof snl;
  184. ret = getsockname (sock, (struct sockaddr *) &snl, (socklen_t *) &namelen);
  185. if (ret < 0 || namelen != sizeof snl)
  186. {
  187. zlog (NULL, LOG_ERR, "Can't get %s socket name: %s", nl->name,
  188. safe_strerror (errno));
  189. close (sock);
  190. return -1;
  191. }
  192. nl->snl = snl;
  193. nl->sock = sock;
  194. return ret;
  195. }
  196. int
  197. set_netlink_blocking (struct nlsock *nl, int *flags)
  198. {
  199. /* Change socket flags for blocking I/O. */
  200. if ((*flags = fcntl (nl->sock, F_GETFL, 0)) < 0)
  201. {
  202. zlog (NULL, LOG_ERR, "%s:%i F_GETFL error: %s",
  203. __FUNCTION__, __LINE__, safe_strerror (errno));
  204. return -1;
  205. }
  206. *flags &= ~O_NONBLOCK;
  207. if (fcntl (nl->sock, F_SETFL, *flags) < 0)
  208. {
  209. zlog (NULL, LOG_ERR, "%s:%i F_SETFL error: %s",
  210. __FUNCTION__, __LINE__, safe_strerror (errno));
  211. return -1;
  212. }
  213. return 0;
  214. }
  215. int
  216. set_netlink_nonblocking (struct nlsock *nl, int *flags)
  217. {
  218. /* Restore socket flags for nonblocking I/O */
  219. *flags |= O_NONBLOCK;
  220. if (fcntl (nl->sock, F_SETFL, *flags) < 0)
  221. {
  222. zlog (NULL, LOG_ERR, "%s:%i F_SETFL error: %s",
  223. __FUNCTION__, __LINE__, safe_strerror (errno));
  224. return -1;
  225. }
  226. return 0;
  227. }
  228. /* Get type specified information from netlink. */
  229. static int
  230. netlink_request (int family, int type, struct nlsock *nl)
  231. {
  232. int ret;
  233. struct sockaddr_nl snl;
  234. int save_errno;
  235. struct
  236. {
  237. struct nlmsghdr nlh;
  238. struct rtgenmsg g;
  239. } req;
  240. /* Check netlink socket. */
  241. if (nl->sock < 0)
  242. {
  243. zlog (NULL, LOG_ERR, "%s socket isn't active.", nl->name);
  244. return -1;
  245. }
  246. memset (&snl, 0, sizeof snl);
  247. snl.nl_family = AF_NETLINK;
  248. memset (&req, 0, sizeof req);
  249. req.nlh.nlmsg_len = sizeof req;
  250. req.nlh.nlmsg_type = type;
  251. req.nlh.nlmsg_flags = NLM_F_ROOT | NLM_F_MATCH | NLM_F_REQUEST;
  252. req.nlh.nlmsg_pid = 0;
  253. req.nlh.nlmsg_seq = ++nl->seq;
  254. req.g.rtgen_family = family;
  255. /* linux appears to check capabilities on every message
  256. * have to raise caps for every message sent
  257. */
  258. if (zserv_privs.change (ZPRIVS_RAISE))
  259. {
  260. zlog (NULL, LOG_ERR, "Can't raise privileges");
  261. return -1;
  262. }
  263. ret = sendto (nl->sock, (void *) &req, sizeof req, 0,
  264. (struct sockaddr *) &snl, sizeof snl);
  265. save_errno = errno;
  266. if (zserv_privs.change (ZPRIVS_LOWER))
  267. zlog (NULL, LOG_ERR, "Can't lower privileges");
  268. if (ret < 0)
  269. {
  270. zlog (NULL, LOG_ERR, "%s sendto failed: %s", nl->name,
  271. safe_strerror (save_errno));
  272. return -1;
  273. }
  274. return 0;
  275. }
  276. /* Receive message from netlink interface and pass those information
  277. to the given function. */
  278. static int
  279. netlink_parse_info (int (*filter) (struct sockaddr_nl *, struct nlmsghdr *),
  280. struct nlsock *nl)
  281. {
  282. int status;
  283. int ret = 0;
  284. int error;
  285. while (1)
  286. {
  287. char buf[4096];
  288. struct iovec iov = { buf, sizeof buf };
  289. struct sockaddr_nl snl;
  290. struct msghdr msg = { (void *) &snl, sizeof snl, &iov, 1, NULL, 0, 0 };
  291. struct nlmsghdr *h;
  292. int save_errno;
  293. if (zserv_privs.change (ZPRIVS_RAISE))
  294. zlog (NULL, LOG_ERR, "Can't raise privileges");
  295. status = recvmsg (nl->sock, &msg, 0);
  296. save_errno = errno;
  297. if (zserv_privs.change (ZPRIVS_LOWER))
  298. zlog (NULL, LOG_ERR, "Can't lower privileges");
  299. if (status < 0)
  300. {
  301. if (save_errno == EINTR)
  302. continue;
  303. if (save_errno == EWOULDBLOCK || save_errno == EAGAIN)
  304. break;
  305. zlog (NULL, LOG_ERR, "%s recvmsg overrun: %s",
  306. nl->name, safe_strerror(save_errno));
  307. continue;
  308. }
  309. if (status == 0)
  310. {
  311. zlog (NULL, LOG_ERR, "%s EOF", nl->name);
  312. return -1;
  313. }
  314. if (msg.msg_namelen != sizeof snl)
  315. {
  316. zlog (NULL, LOG_ERR, "%s sender address length error: length %d",
  317. nl->name, msg.msg_namelen);
  318. return -1;
  319. }
  320. /* JF: Ignore messages that aren't from the kernel */
  321. if ( snl.nl_pid != 0 )
  322. {
  323. zlog ( NULL, LOG_ERR, "Ignoring message from pid %u", snl.nl_pid );
  324. continue;
  325. }
  326. for (h = (struct nlmsghdr *) buf; NLMSG_OK (h, (unsigned int) status);
  327. h = NLMSG_NEXT (h, status))
  328. {
  329. /* Finish of reading. */
  330. if (h->nlmsg_type == NLMSG_DONE)
  331. return ret;
  332. /* Error handling. */
  333. if (h->nlmsg_type == NLMSG_ERROR)
  334. {
  335. struct nlmsgerr *err = (struct nlmsgerr *) NLMSG_DATA (h);
  336. /* If the error field is zero, then this is an ACK */
  337. if (err->error == 0)
  338. {
  339. if (IS_ZEBRA_DEBUG_KERNEL)
  340. {
  341. zlog_debug ("%s: %s ACK: type=%s(%u), seq=%u, pid=%u",
  342. __FUNCTION__, nl->name,
  343. lookup (nlmsg_str, err->msg.nlmsg_type),
  344. err->msg.nlmsg_type, err->msg.nlmsg_seq,
  345. err->msg.nlmsg_pid);
  346. }
  347. /* return if not a multipart message, otherwise continue */
  348. if (!(h->nlmsg_flags & NLM_F_MULTI))
  349. {
  350. return 0;
  351. }
  352. continue;
  353. }
  354. if (h->nlmsg_len < NLMSG_LENGTH (sizeof (struct nlmsgerr)))
  355. {
  356. zlog (NULL, LOG_ERR, "%s error: message truncated",
  357. nl->name);
  358. return -1;
  359. }
  360. /* Deal with Error Noise - MAG */
  361. {
  362. int loglvl = LOG_ERR;
  363. int errnum = err->error;
  364. int msg_type = err->msg.nlmsg_type;
  365. if (nl == &netlink_cmd
  366. && (-errnum == ENODEV || -errnum == ESRCH)
  367. && (msg_type == RTM_NEWROUTE || msg_type == RTM_DELROUTE))
  368. loglvl = LOG_DEBUG;
  369. zlog (NULL, loglvl, "%s error: %s, type=%s(%u), "
  370. "seq=%u, pid=%u",
  371. nl->name, safe_strerror (-errnum),
  372. lookup (nlmsg_str, msg_type),
  373. msg_type, err->msg.nlmsg_seq, err->msg.nlmsg_pid);
  374. }
  375. /*
  376. ret = -1;
  377. continue;
  378. */
  379. return -1;
  380. }
  381. /* OK we got netlink message. */
  382. if (IS_ZEBRA_DEBUG_KERNEL)
  383. zlog_debug ("netlink_parse_info: %s type %s(%u), seq=%u, pid=%u",
  384. nl->name,
  385. lookup (nlmsg_str, h->nlmsg_type), h->nlmsg_type,
  386. h->nlmsg_seq, h->nlmsg_pid);
  387. /* skip unsolicited messages originating from command socket */
  388. if (nl != &netlink_cmd && h->nlmsg_pid == netlink_cmd.snl.nl_pid)
  389. {
  390. if (IS_ZEBRA_DEBUG_KERNEL)
  391. zlog_debug ("netlink_parse_info: %s packet comes from %s",
  392. netlink_cmd.name, nl->name);
  393. continue;
  394. }
  395. error = (*filter) (&snl, h);
  396. if (error < 0)
  397. {
  398. zlog (NULL, LOG_ERR, "%s filter function error", nl->name);
  399. ret = error;
  400. }
  401. }
  402. /* After error care. */
  403. if (msg.msg_flags & MSG_TRUNC)
  404. {
  405. zlog (NULL, LOG_ERR, "%s error: message truncated", nl->name);
  406. continue;
  407. }
  408. if (status)
  409. {
  410. zlog (NULL, LOG_ERR, "%s error: data remnant size %d", nl->name,
  411. status);
  412. return -1;
  413. }
  414. }
  415. return ret;
  416. }
  417. /* Utility function for parse rtattr. */
  418. static void
  419. netlink_parse_rtattr (struct rtattr **tb, int max, struct rtattr *rta,
  420. int len)
  421. {
  422. while (RTA_OK (rta, len))
  423. {
  424. if (rta->rta_type <= max)
  425. tb[rta->rta_type] = rta;
  426. rta = RTA_NEXT (rta, len);
  427. }
  428. }
  429. /* Called from interface_lookup_netlink(). This function is only used
  430. during bootstrap. */
  431. int
  432. netlink_interface (struct sockaddr_nl *snl, struct nlmsghdr *h)
  433. {
  434. int len;
  435. struct ifinfomsg *ifi;
  436. struct rtattr *tb[IFLA_MAX + 1];
  437. struct interface *ifp;
  438. char *name;
  439. int i;
  440. ifi = NLMSG_DATA (h);
  441. if (h->nlmsg_type != RTM_NEWLINK)
  442. return 0;
  443. len = h->nlmsg_len - NLMSG_LENGTH (sizeof (struct ifinfomsg));
  444. if (len < 0)
  445. return -1;
  446. /* Looking up interface name. */
  447. memset (tb, 0, sizeof tb);
  448. netlink_parse_rtattr (tb, IFLA_MAX, IFLA_RTA (ifi), len);
  449. #ifdef IFLA_WIRELESS
  450. /* check for wireless messages to ignore */
  451. if ((tb[IFLA_WIRELESS] != NULL) && (ifi->ifi_change == 0))
  452. {
  453. if (IS_ZEBRA_DEBUG_KERNEL)
  454. zlog_debug ("%s: ignoring IFLA_WIRELESS message", __func__);
  455. return 0;
  456. }
  457. #endif /* IFLA_WIRELESS */
  458. if (tb[IFLA_IFNAME] == NULL)
  459. return -1;
  460. name = (char *) RTA_DATA (tb[IFLA_IFNAME]);
  461. /* Add interface. */
  462. ifp = if_get_by_name (name);
  463. set_ifindex(ifp, ifi->ifi_index);
  464. ifp->flags = ifi->ifi_flags & 0x0000fffff;
  465. ifp->mtu6 = ifp->mtu = *(int *) RTA_DATA (tb[IFLA_MTU]);
  466. ifp->metric = 1;
  467. /* Hardware type and address. */
  468. ifp->hw_type = ifi->ifi_type;
  469. if (tb[IFLA_ADDRESS])
  470. {
  471. int hw_addr_len;
  472. hw_addr_len = RTA_PAYLOAD (tb[IFLA_ADDRESS]);
  473. if (hw_addr_len > INTERFACE_HWADDR_MAX)
  474. zlog_warn ("Hardware address is too large: %d", hw_addr_len);
  475. else
  476. {
  477. ifp->hw_addr_len = hw_addr_len;
  478. memcpy (ifp->hw_addr, RTA_DATA (tb[IFLA_ADDRESS]), hw_addr_len);
  479. for (i = 0; i < hw_addr_len; i++)
  480. if (ifp->hw_addr[i] != 0)
  481. break;
  482. if (i == hw_addr_len)
  483. ifp->hw_addr_len = 0;
  484. else
  485. ifp->hw_addr_len = hw_addr_len;
  486. }
  487. }
  488. if_add_update (ifp);
  489. return 0;
  490. }
  491. /* Lookup interface IPv4/IPv6 address. */
  492. int
  493. netlink_interface_addr (struct sockaddr_nl *snl, struct nlmsghdr *h)
  494. {
  495. int len;
  496. struct ifaddrmsg *ifa;
  497. struct rtattr *tb[IFA_MAX + 1];
  498. struct interface *ifp;
  499. void *addr;
  500. void *broad;
  501. u_char flags = 0;
  502. char *label = NULL;
  503. ifa = NLMSG_DATA (h);
  504. if (ifa->ifa_family != AF_INET
  505. #ifdef HAVE_IPV6
  506. && ifa->ifa_family != AF_INET6
  507. #endif /* HAVE_IPV6 */
  508. )
  509. return 0;
  510. if (h->nlmsg_type != RTM_NEWADDR && h->nlmsg_type != RTM_DELADDR)
  511. return 0;
  512. len = h->nlmsg_len - NLMSG_LENGTH (sizeof (struct ifaddrmsg));
  513. if (len < 0)
  514. return -1;
  515. memset (tb, 0, sizeof tb);
  516. netlink_parse_rtattr (tb, IFA_MAX, IFA_RTA (ifa), len);
  517. ifp = if_lookup_by_index (ifa->ifa_index);
  518. if (ifp == NULL)
  519. {
  520. zlog_err ("netlink_interface_addr can't find interface by index %d",
  521. ifa->ifa_index);
  522. return -1;
  523. }
  524. if (IS_ZEBRA_DEBUG_KERNEL) /* remove this line to see initial ifcfg */
  525. {
  526. char buf[BUFSIZ];
  527. zlog_debug ("netlink_interface_addr %s %s:",
  528. lookup (nlmsg_str, h->nlmsg_type), ifp->name);
  529. if (tb[IFA_LOCAL])
  530. zlog_debug (" IFA_LOCAL %s/%d",
  531. inet_ntop (ifa->ifa_family, RTA_DATA (tb[IFA_LOCAL]),
  532. buf, BUFSIZ), ifa->ifa_prefixlen);
  533. if (tb[IFA_ADDRESS])
  534. zlog_debug (" IFA_ADDRESS %s/%d",
  535. inet_ntop (ifa->ifa_family, RTA_DATA (tb[IFA_ADDRESS]),
  536. buf, BUFSIZ), ifa->ifa_prefixlen);
  537. if (tb[IFA_BROADCAST])
  538. zlog_debug (" IFA_BROADCAST %s/%d",
  539. inet_ntop (ifa->ifa_family, RTA_DATA (tb[IFA_BROADCAST]),
  540. buf, BUFSIZ), ifa->ifa_prefixlen);
  541. if (tb[IFA_LABEL] && strcmp (ifp->name, RTA_DATA (tb[IFA_LABEL])))
  542. zlog_debug (" IFA_LABEL %s", (char *)RTA_DATA (tb[IFA_LABEL]));
  543. if (tb[IFA_CACHEINFO])
  544. {
  545. struct ifa_cacheinfo *ci = RTA_DATA (tb[IFA_CACHEINFO]);
  546. zlog_debug (" IFA_CACHEINFO pref %d, valid %d",
  547. ci->ifa_prefered, ci->ifa_valid);
  548. }
  549. }
  550. /* logic copied from iproute2/ip/ipaddress.c:print_addrinfo() */
  551. if (tb[IFA_LOCAL] == NULL)
  552. tb[IFA_LOCAL] = tb[IFA_ADDRESS];
  553. if (tb[IFA_ADDRESS] == NULL)
  554. tb[IFA_ADDRESS] = tb[IFA_LOCAL];
  555. /* local interface address */
  556. addr = (tb[IFA_LOCAL] ? RTA_DATA(tb[IFA_LOCAL]) : NULL);
  557. /* is there a peer address? */
  558. /* N.B. I do not understand why the memcmp compares 4 bytes regardless
  559. of address family, but this is exactly how it appears in
  560. print_addrinfo. I wonder if it should be RTA_PAYLOAD(tb[IFA_ADDRESS])
  561. instead of 4... */
  562. if (tb[IFA_ADDRESS] &&
  563. memcmp(RTA_DATA(tb[IFA_ADDRESS]), RTA_DATA(tb[IFA_LOCAL]), 4))
  564. {
  565. broad = RTA_DATA(tb[IFA_ADDRESS]);
  566. SET_FLAG (flags, ZEBRA_IFA_PEER);
  567. }
  568. else
  569. /* seeking a broadcast address */
  570. broad = (tb[IFA_BROADCAST] ? RTA_DATA(tb[IFA_BROADCAST]) : NULL);
  571. /* addr is primary key, SOL if we don't have one */
  572. if (addr == NULL)
  573. {
  574. zlog_debug ("%s: NULL address", __func__);
  575. return -1;
  576. }
  577. /* Flags. */
  578. if (ifa->ifa_flags & IFA_F_SECONDARY)
  579. SET_FLAG (flags, ZEBRA_IFA_SECONDARY);
  580. /* Label */
  581. if (tb[IFA_LABEL])
  582. label = (char *) RTA_DATA (tb[IFA_LABEL]);
  583. if (ifp && label && strcmp (ifp->name, label) == 0)
  584. label = NULL;
  585. /* Register interface address to the interface. */
  586. if (ifa->ifa_family == AF_INET)
  587. {
  588. if (h->nlmsg_type == RTM_NEWADDR)
  589. connected_add_ipv4 (ifp, flags,
  590. (struct in_addr *) addr, ifa->ifa_prefixlen,
  591. (struct in_addr *) broad, label);
  592. else
  593. connected_delete_ipv4 (ifp, flags,
  594. (struct in_addr *) addr, ifa->ifa_prefixlen,
  595. (struct in_addr *) broad);
  596. }
  597. #ifdef HAVE_IPV6
  598. if (ifa->ifa_family == AF_INET6)
  599. {
  600. if (h->nlmsg_type == RTM_NEWADDR)
  601. connected_add_ipv6 (ifp, flags,
  602. (struct in6_addr *) addr, ifa->ifa_prefixlen,
  603. (struct in6_addr *) broad, label);
  604. else
  605. connected_delete_ipv6 (ifp,
  606. (struct in6_addr *) addr, ifa->ifa_prefixlen,
  607. (struct in6_addr *) broad);
  608. }
  609. #endif /* HAVE_IPV6 */
  610. return 0;
  611. }
  612. /* Looking up routing table by netlink interface. */
  613. int
  614. netlink_routing_table (struct sockaddr_nl *snl, struct nlmsghdr *h)
  615. {
  616. int len;
  617. struct rtmsg *rtm;
  618. struct rtattr *tb[RTA_MAX + 1];
  619. u_char flags = 0;
  620. char anyaddr[16] = { 0 };
  621. int index;
  622. int table;
  623. int metric;
  624. void *dest;
  625. void *gate;
  626. rtm = NLMSG_DATA (h);
  627. if (h->nlmsg_type != RTM_NEWROUTE)
  628. return 0;
  629. if (rtm->rtm_type != RTN_UNICAST)
  630. return 0;
  631. table = rtm->rtm_table;
  632. #if 0 /* we weed them out later in rib_weed_tables () */
  633. if (table != RT_TABLE_MAIN && table != zebrad.rtm_table_default)
  634. return 0;
  635. #endif
  636. len = h->nlmsg_len - NLMSG_LENGTH (sizeof (struct rtmsg));
  637. if (len < 0)
  638. return -1;
  639. memset (tb, 0, sizeof tb);
  640. netlink_parse_rtattr (tb, RTA_MAX, RTM_RTA (rtm), len);
  641. if (rtm->rtm_flags & RTM_F_CLONED)
  642. return 0;
  643. if (rtm->rtm_protocol == RTPROT_REDIRECT)
  644. return 0;
  645. if (rtm->rtm_protocol == RTPROT_KERNEL)
  646. return 0;
  647. if (rtm->rtm_src_len != 0)
  648. return 0;
  649. /* Route which inserted by Zebra. */
  650. if (rtm->rtm_protocol == RTPROT_ZEBRA)
  651. flags |= ZEBRA_FLAG_SELFROUTE;
  652. index = 0;
  653. metric = 0;
  654. dest = NULL;
  655. gate = NULL;
  656. if (tb[RTA_OIF])
  657. index = *(int *) RTA_DATA (tb[RTA_OIF]);
  658. if (tb[RTA_DST])
  659. dest = RTA_DATA (tb[RTA_DST]);
  660. else
  661. dest = anyaddr;
  662. /* Multipath treatment is needed. */
  663. if (tb[RTA_GATEWAY])
  664. gate = RTA_DATA (tb[RTA_GATEWAY]);
  665. if (tb[RTA_PRIORITY])
  666. metric = *(int *) RTA_DATA(tb[RTA_PRIORITY]);
  667. if (rtm->rtm_family == AF_INET)
  668. {
  669. struct prefix_ipv4 p;
  670. p.family = AF_INET;
  671. memcpy (&p.prefix, dest, 4);
  672. p.prefixlen = rtm->rtm_dst_len;
  673. rib_add_ipv4 (ZEBRA_ROUTE_KERNEL, flags, &p, gate, index, table, metric, 0);
  674. }
  675. #ifdef HAVE_IPV6
  676. if (rtm->rtm_family == AF_INET6)
  677. {
  678. struct prefix_ipv6 p;
  679. p.family = AF_INET6;
  680. memcpy (&p.prefix, dest, 16);
  681. p.prefixlen = rtm->rtm_dst_len;
  682. rib_add_ipv6 (ZEBRA_ROUTE_KERNEL, flags, &p, gate, index, table,
  683. metric, 0);
  684. }
  685. #endif /* HAVE_IPV6 */
  686. return 0;
  687. }
  688. struct message rtproto_str[] = {
  689. {RTPROT_REDIRECT, "redirect"},
  690. {RTPROT_KERNEL, "kernel"},
  691. {RTPROT_BOOT, "boot"},
  692. {RTPROT_STATIC, "static"},
  693. {RTPROT_GATED, "GateD"},
  694. {RTPROT_RA, "router advertisement"},
  695. {RTPROT_MRT, "MRT"},
  696. {RTPROT_ZEBRA, "Zebra"},
  697. #ifdef RTPROT_BIRD
  698. {RTPROT_BIRD, "BIRD"},
  699. #endif /* RTPROT_BIRD */
  700. {0, NULL}
  701. };
  702. /* Routing information change from the kernel. */
  703. int
  704. netlink_route_change (struct sockaddr_nl *snl, struct nlmsghdr *h)
  705. {
  706. int len;
  707. struct rtmsg *rtm;
  708. struct rtattr *tb[RTA_MAX + 1];
  709. char anyaddr[16] = { 0 };
  710. int index;
  711. int table;
  712. void *dest;
  713. void *gate;
  714. rtm = NLMSG_DATA (h);
  715. if (!(h->nlmsg_type == RTM_NEWROUTE || h->nlmsg_type == RTM_DELROUTE))
  716. {
  717. /* If this is not route add/delete message print warning. */
  718. zlog_warn ("Kernel message: %d\n", h->nlmsg_type);
  719. return 0;
  720. }
  721. /* Connected route. */
  722. if (IS_ZEBRA_DEBUG_KERNEL)
  723. zlog_debug ("%s %s %s proto %s",
  724. h->nlmsg_type ==
  725. RTM_NEWROUTE ? "RTM_NEWROUTE" : "RTM_DELROUTE",
  726. rtm->rtm_family == AF_INET ? "ipv4" : "ipv6",
  727. rtm->rtm_type == RTN_UNICAST ? "unicast" : "multicast",
  728. lookup (rtproto_str, rtm->rtm_protocol));
  729. if (rtm->rtm_type != RTN_UNICAST)
  730. {
  731. return 0;
  732. }
  733. table = rtm->rtm_table;
  734. if (table != RT_TABLE_MAIN && table != zebrad.rtm_table_default)
  735. {
  736. return 0;
  737. }
  738. len = h->nlmsg_len - NLMSG_LENGTH (sizeof (struct rtmsg));
  739. if (len < 0)
  740. return -1;
  741. memset (tb, 0, sizeof tb);
  742. netlink_parse_rtattr (tb, RTA_MAX, RTM_RTA (rtm), len);
  743. if (rtm->rtm_flags & RTM_F_CLONED)
  744. return 0;
  745. if (rtm->rtm_protocol == RTPROT_REDIRECT)
  746. return 0;
  747. if (rtm->rtm_protocol == RTPROT_KERNEL)
  748. return 0;
  749. if (rtm->rtm_protocol == RTPROT_ZEBRA && h->nlmsg_type == RTM_NEWROUTE)
  750. return 0;
  751. if (rtm->rtm_src_len != 0)
  752. {
  753. zlog_warn ("netlink_route_change(): no src len");
  754. return 0;
  755. }
  756. index = 0;
  757. dest = NULL;
  758. gate = NULL;
  759. if (tb[RTA_OIF])
  760. index = *(int *) RTA_DATA (tb[RTA_OIF]);
  761. if (tb[RTA_DST])
  762. dest = RTA_DATA (tb[RTA_DST]);
  763. else
  764. dest = anyaddr;
  765. if (tb[RTA_GATEWAY])
  766. gate = RTA_DATA (tb[RTA_GATEWAY]);
  767. if (rtm->rtm_family == AF_INET)
  768. {
  769. struct prefix_ipv4 p;
  770. p.family = AF_INET;
  771. memcpy (&p.prefix, dest, 4);
  772. p.prefixlen = rtm->rtm_dst_len;
  773. if (IS_ZEBRA_DEBUG_KERNEL)
  774. {
  775. if (h->nlmsg_type == RTM_NEWROUTE)
  776. zlog_debug ("RTM_NEWROUTE %s/%d",
  777. inet_ntoa (p.prefix), p.prefixlen);
  778. else
  779. zlog_debug ("RTM_DELROUTE %s/%d",
  780. inet_ntoa (p.prefix), p.prefixlen);
  781. }
  782. if (h->nlmsg_type == RTM_NEWROUTE)
  783. rib_add_ipv4 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, table, 0, 0);
  784. else
  785. rib_delete_ipv4 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, table);
  786. }
  787. #ifdef HAVE_IPV6
  788. if (rtm->rtm_family == AF_INET6)
  789. {
  790. struct prefix_ipv6 p;
  791. char buf[BUFSIZ];
  792. p.family = AF_INET6;
  793. memcpy (&p.prefix, dest, 16);
  794. p.prefixlen = rtm->rtm_dst_len;
  795. if (IS_ZEBRA_DEBUG_KERNEL)
  796. {
  797. if (h->nlmsg_type == RTM_NEWROUTE)
  798. zlog_debug ("RTM_NEWROUTE %s/%d",
  799. inet_ntop (AF_INET6, &p.prefix, buf, BUFSIZ),
  800. p.prefixlen);
  801. else
  802. zlog_debug ("RTM_DELROUTE %s/%d",
  803. inet_ntop (AF_INET6, &p.prefix, buf, BUFSIZ),
  804. p.prefixlen);
  805. }
  806. if (h->nlmsg_type == RTM_NEWROUTE)
  807. rib_add_ipv6 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, 0, 0, 0);
  808. else
  809. rib_delete_ipv6 (ZEBRA_ROUTE_KERNEL, 0, &p, gate, index, 0);
  810. }
  811. #endif /* HAVE_IPV6 */
  812. return 0;
  813. }
  814. int
  815. netlink_link_change (struct sockaddr_nl *snl, struct nlmsghdr *h)
  816. {
  817. int len;
  818. struct ifinfomsg *ifi;
  819. struct rtattr *tb[IFLA_MAX + 1];
  820. struct interface *ifp;
  821. char *name;
  822. ifi = NLMSG_DATA (h);
  823. if (!(h->nlmsg_type == RTM_NEWLINK || h->nlmsg_type == RTM_DELLINK))
  824. {
  825. /* If this is not link add/delete message so print warning. */
  826. zlog_warn ("netlink_link_change: wrong kernel message %d\n",
  827. h->nlmsg_type);
  828. return 0;
  829. }
  830. len = h->nlmsg_len - NLMSG_LENGTH (sizeof (struct ifinfomsg));
  831. if (len < 0)
  832. return -1;
  833. /* Looking up interface name. */
  834. memset (tb, 0, sizeof tb);
  835. netlink_parse_rtattr (tb, IFLA_MAX, IFLA_RTA (ifi), len);
  836. #ifdef IFLA_WIRELESS
  837. /* check for wireless messages to ignore */
  838. if ((tb[IFLA_WIRELESS] != NULL) && (ifi->ifi_change == 0))
  839. {
  840. if (IS_ZEBRA_DEBUG_KERNEL)
  841. zlog_debug ("%s: ignoring IFLA_WIRELESS message", __func__);
  842. return 0;
  843. }
  844. #endif /* IFLA_WIRELESS */
  845. if (tb[IFLA_IFNAME] == NULL)
  846. return -1;
  847. name = (char *) RTA_DATA (tb[IFLA_IFNAME]);
  848. /* Add interface. */
  849. if (h->nlmsg_type == RTM_NEWLINK)
  850. {
  851. ifp = if_lookup_by_name (name);
  852. if (ifp == NULL || !CHECK_FLAG (ifp->status, ZEBRA_INTERFACE_ACTIVE))
  853. {
  854. if (ifp == NULL)
  855. ifp = if_get_by_name (name);
  856. set_ifindex(ifp, ifi->ifi_index);
  857. ifp->flags = ifi->ifi_flags & 0x0000fffff;
  858. ifp->mtu6 = ifp->mtu = *(int *) RTA_DATA (tb[IFLA_MTU]);
  859. ifp->metric = 1;
  860. /* If new link is added. */
  861. if_add_update (ifp);
  862. }
  863. else
  864. {
  865. /* Interface status change. */
  866. set_ifindex(ifp, ifi->ifi_index);
  867. ifp->mtu6 = ifp->mtu = *(int *) RTA_DATA (tb[IFLA_MTU]);
  868. ifp->metric = 1;
  869. if (if_is_operative (ifp))
  870. {
  871. ifp->flags = ifi->ifi_flags & 0x0000fffff;
  872. if (!if_is_operative (ifp))
  873. if_down (ifp);
  874. else
  875. /* Must notify client daemons of new interface status. */
  876. zebra_interface_up_update (ifp);
  877. }
  878. else
  879. {
  880. ifp->flags = ifi->ifi_flags & 0x0000fffff;
  881. if (if_is_operative (ifp))
  882. if_up (ifp);
  883. }
  884. }
  885. }
  886. else
  887. {
  888. /* RTM_DELLINK. */
  889. ifp = if_lookup_by_name (name);
  890. if (ifp == NULL)
  891. {
  892. zlog (NULL, LOG_WARNING, "interface %s is deleted but can't find",
  893. name);
  894. return 0;
  895. }
  896. if_delete_update (ifp);
  897. }
  898. return 0;
  899. }
  900. int
  901. netlink_information_fetch (struct sockaddr_nl *snl, struct nlmsghdr *h)
  902. {
  903. switch (h->nlmsg_type)
  904. {
  905. case RTM_NEWROUTE:
  906. return netlink_route_change (snl, h);
  907. break;
  908. case RTM_DELROUTE:
  909. return netlink_route_change (snl, h);
  910. break;
  911. case RTM_NEWLINK:
  912. return netlink_link_change (snl, h);
  913. break;
  914. case RTM_DELLINK:
  915. return netlink_link_change (snl, h);
  916. break;
  917. case RTM_NEWADDR:
  918. return netlink_interface_addr (snl, h);
  919. break;
  920. case RTM_DELADDR:
  921. return netlink_interface_addr (snl, h);
  922. break;
  923. default:
  924. zlog_warn ("Unknown netlink nlmsg_type %d\n", h->nlmsg_type);
  925. break;
  926. }
  927. return 0;
  928. }
  929. /* Interface lookup by netlink socket. */
  930. int
  931. interface_lookup_netlink (void)
  932. {
  933. int ret;
  934. int flags;
  935. int snb_ret;
  936. /*
  937. * Change netlink socket flags to blocking to ensure we get
  938. * a reply via nelink_parse_info
  939. */
  940. snb_ret = set_netlink_blocking (&netlink_cmd, &flags);
  941. if (snb_ret < 0)
  942. zlog (NULL, LOG_WARNING,
  943. "%s:%i Warning: Could not set netlink socket to blocking.",
  944. __FUNCTION__, __LINE__);
  945. /* Get interface information. */
  946. ret = netlink_request (AF_PACKET, RTM_GETLINK, &netlink_cmd);
  947. if (ret < 0)
  948. return ret;
  949. ret = netlink_parse_info (netlink_interface, &netlink_cmd);
  950. if (ret < 0)
  951. return ret;
  952. /* Get IPv4 address of the interfaces. */
  953. ret = netlink_request (AF_INET, RTM_GETADDR, &netlink_cmd);
  954. if (ret < 0)
  955. return ret;
  956. ret = netlink_parse_info (netlink_interface_addr, &netlink_cmd);
  957. if (ret < 0)
  958. return ret;
  959. #ifdef HAVE_IPV6
  960. /* Get IPv6 address of the interfaces. */
  961. ret = netlink_request (AF_INET6, RTM_GETADDR, &netlink_cmd);
  962. if (ret < 0)
  963. return ret;
  964. ret = netlink_parse_info (netlink_interface_addr, &netlink_cmd);
  965. if (ret < 0)
  966. return ret;
  967. #endif /* HAVE_IPV6 */
  968. /* restore socket flags */
  969. if (snb_ret == 0)
  970. set_netlink_nonblocking (&netlink_cmd, &flags);
  971. return 0;
  972. }
  973. /* Routing table read function using netlink interface. Only called
  974. bootstrap time. */
  975. int
  976. netlink_route_read (void)
  977. {
  978. int ret;
  979. int flags;
  980. int snb_ret;
  981. /*
  982. * Change netlink socket flags to blocking to ensure we get
  983. * a reply via nelink_parse_info
  984. */
  985. snb_ret = set_netlink_blocking (&netlink_cmd, &flags);
  986. if (snb_ret < 0)
  987. zlog (NULL, LOG_WARNING,
  988. "%s:%i Warning: Could not set netlink socket to blocking.",
  989. __FUNCTION__, __LINE__);
  990. /* Get IPv4 routing table. */
  991. ret = netlink_request (AF_INET, RTM_GETROUTE, &netlink_cmd);
  992. if (ret < 0)
  993. return ret;
  994. ret = netlink_parse_info (netlink_routing_table, &netlink_cmd);
  995. if (ret < 0)
  996. return ret;
  997. #ifdef HAVE_IPV6
  998. /* Get IPv6 routing table. */
  999. ret = netlink_request (AF_INET6, RTM_GETROUTE, &netlink_cmd);
  1000. if (ret < 0)
  1001. return ret;
  1002. ret = netlink_parse_info (netlink_routing_table, &netlink_cmd);
  1003. if (ret < 0)
  1004. return ret;
  1005. #endif /* HAVE_IPV6 */
  1006. /* restore flags */
  1007. if (snb_ret == 0)
  1008. set_netlink_nonblocking (&netlink_cmd, &flags);
  1009. return 0;
  1010. }
  1011. /* Utility function comes from iproute2.
  1012. Authors: Alexey Kuznetsov, <kuznet@ms2.inr.ac.ru> */
  1013. int
  1014. addattr_l (struct nlmsghdr *n, int maxlen, int type, void *data, int alen)
  1015. {
  1016. int len;
  1017. struct rtattr *rta;
  1018. len = RTA_LENGTH (alen);
  1019. if (NLMSG_ALIGN (n->nlmsg_len) + len > maxlen)
  1020. return -1;
  1021. rta = (struct rtattr *) (((char *) n) + NLMSG_ALIGN (n->nlmsg_len));
  1022. rta->rta_type = type;
  1023. rta->rta_len = len;
  1024. memcpy (RTA_DATA (rta), data, alen);
  1025. n->nlmsg_len = NLMSG_ALIGN (n->nlmsg_len) + len;
  1026. return 0;
  1027. }
  1028. int
  1029. rta_addattr_l (struct rtattr *rta, int maxlen, int type, void *data, int alen)
  1030. {
  1031. int len;
  1032. struct rtattr *subrta;
  1033. len = RTA_LENGTH (alen);
  1034. if (RTA_ALIGN (rta->rta_len) + len > maxlen)
  1035. return -1;
  1036. subrta = (struct rtattr *) (((char *) rta) + RTA_ALIGN (rta->rta_len));
  1037. subrta->rta_type = type;
  1038. subrta->rta_len = len;
  1039. memcpy (RTA_DATA (subrta), data, alen);
  1040. rta->rta_len = NLMSG_ALIGN (rta->rta_len) + len;
  1041. return 0;
  1042. }
  1043. /* Utility function comes from iproute2.
  1044. Authors: Alexey Kuznetsov, <kuznet@ms2.inr.ac.ru> */
  1045. int
  1046. addattr32 (struct nlmsghdr *n, int maxlen, int type, int data)
  1047. {
  1048. int len;
  1049. struct rtattr *rta;
  1050. len = RTA_LENGTH (4);
  1051. if (NLMSG_ALIGN (n->nlmsg_len) + len > maxlen)
  1052. return -1;
  1053. rta = (struct rtattr *) (((char *) n) + NLMSG_ALIGN (n->nlmsg_len));
  1054. rta->rta_type = type;
  1055. rta->rta_len = len;
  1056. memcpy (RTA_DATA (rta), &data, 4);
  1057. n->nlmsg_len = NLMSG_ALIGN (n->nlmsg_len) + len;
  1058. return 0;
  1059. }
  1060. static int
  1061. netlink_talk_filter (struct sockaddr_nl *snl, struct nlmsghdr *h)
  1062. {
  1063. zlog_warn ("netlink_talk: ignoring message type 0x%04x", h->nlmsg_type);
  1064. return 0;
  1065. }
  1066. /* sendmsg() to netlink socket then recvmsg(). */
  1067. int
  1068. netlink_talk (struct nlmsghdr *n, struct nlsock *nl)
  1069. {
  1070. int status;
  1071. struct sockaddr_nl snl;
  1072. struct iovec iov = { (void *) n, n->nlmsg_len };
  1073. struct msghdr msg = { (void *) &snl, sizeof snl, &iov, 1, NULL, 0, 0 };
  1074. int flags = 0;
  1075. int snb_ret;
  1076. int save_errno;
  1077. memset (&snl, 0, sizeof snl);
  1078. snl.nl_family = AF_NETLINK;
  1079. n->nlmsg_seq = ++nl->seq;
  1080. /* Request an acknowledgement by setting NLM_F_ACK */
  1081. n->nlmsg_flags |= NLM_F_ACK;
  1082. if (IS_ZEBRA_DEBUG_KERNEL)
  1083. zlog_debug ("netlink_talk: %s type %s(%u), seq=%u", nl->name,
  1084. lookup (nlmsg_str, n->nlmsg_type), n->nlmsg_type,
  1085. n->nlmsg_seq);
  1086. /* Send message to netlink interface. */
  1087. if (zserv_privs.change (ZPRIVS_RAISE))
  1088. zlog (NULL, LOG_ERR, "Can't raise privileges");
  1089. status = sendmsg (nl->sock, &msg, 0);
  1090. save_errno = errno;
  1091. if (zserv_privs.change (ZPRIVS_LOWER))
  1092. zlog (NULL, LOG_ERR, "Can't lower privileges");
  1093. if (status < 0)
  1094. {
  1095. zlog (NULL, LOG_ERR, "netlink_talk sendmsg() error: %s",
  1096. safe_strerror (save_errno));
  1097. return -1;
  1098. }
  1099. /*
  1100. * Change socket flags for blocking I/O.
  1101. * This ensures we wait for a reply in netlink_parse_info().
  1102. */
  1103. snb_ret = set_netlink_blocking (nl, &flags);
  1104. if (snb_ret < 0)
  1105. zlog (NULL, LOG_WARNING,
  1106. "%s:%i Warning: Could not set netlink socket to blocking.",
  1107. __FUNCTION__, __LINE__);
  1108. /*
  1109. * Get reply from netlink socket.
  1110. * The reply should either be an acknowlegement or an error.
  1111. */
  1112. status = netlink_parse_info (netlink_talk_filter, nl);
  1113. /* Restore socket flags for nonblocking I/O */
  1114. if (snb_ret == 0)
  1115. set_netlink_nonblocking (nl, &flags);
  1116. return status;
  1117. }
  1118. /* Routing table change via netlink interface. */
  1119. int
  1120. netlink_route (int cmd, int family, void *dest, int length, void *gate,
  1121. int index, int zebra_flags, int table)
  1122. {
  1123. int ret;
  1124. int bytelen;
  1125. struct sockaddr_nl snl;
  1126. int discard;
  1127. struct
  1128. {
  1129. struct nlmsghdr n;
  1130. struct rtmsg r;
  1131. char buf[1024];
  1132. } req;
  1133. memset (&req, 0, sizeof req);
  1134. bytelen = (family == AF_INET ? 4 : 16);
  1135. req.n.nlmsg_len = NLMSG_LENGTH (sizeof (struct rtmsg));
  1136. req.n.nlmsg_flags = NLM_F_CREATE | NLM_F_REQUEST;
  1137. req.n.nlmsg_type = cmd;
  1138. req.r.rtm_family = family;
  1139. req.r.rtm_table = table;
  1140. req.r.rtm_dst_len = length;
  1141. if ((zebra_flags & ZEBRA_FLAG_BLACKHOLE)
  1142. || (zebra_flags & ZEBRA_FLAG_REJECT))
  1143. discard = 1;
  1144. else
  1145. discard = 0;
  1146. if (cmd == RTM_NEWROUTE)
  1147. {
  1148. req.r.rtm_protocol = RTPROT_ZEBRA;
  1149. req.r.rtm_scope = RT_SCOPE_UNIVERSE;
  1150. if (discard)
  1151. {
  1152. if (zebra_flags & ZEBRA_FLAG_BLACKHOLE)
  1153. req.r.rtm_type = RTN_BLACKHOLE;
  1154. else if (zebra_flags & ZEBRA_FLAG_REJECT)
  1155. req.r.rtm_type = RTN_UNREACHABLE;
  1156. else
  1157. assert (RTN_BLACKHOLE != RTN_UNREACHABLE); /* false */
  1158. }
  1159. else
  1160. req.r.rtm_type = RTN_UNICAST;
  1161. }
  1162. if (dest)
  1163. addattr_l (&req.n, sizeof req, RTA_DST, dest, bytelen);
  1164. if (!discard)
  1165. {
  1166. if (gate)
  1167. addattr_l (&req.n, sizeof req, RTA_GATEWAY, gate, bytelen);
  1168. if (index > 0)
  1169. addattr32 (&req.n, sizeof req, RTA_OIF, index);
  1170. }
  1171. /* Destination netlink address. */
  1172. memset (&snl, 0, sizeof snl);
  1173. snl.nl_family = AF_NETLINK;
  1174. /* Talk to netlink socket. */
  1175. ret = netlink_talk (&req.n, &netlink_cmd);
  1176. if (ret < 0)
  1177. return -1;
  1178. return 0;
  1179. }
  1180. /* Routing table change via netlink interface. */
  1181. int
  1182. netlink_route_multipath (int cmd, struct prefix *p, struct rib *rib,
  1183. int family)
  1184. {
  1185. int bytelen;
  1186. struct sockaddr_nl snl;
  1187. struct nexthop *nexthop = NULL;
  1188. int nexthop_num = 0;
  1189. int discard;
  1190. struct
  1191. {
  1192. struct nlmsghdr n;
  1193. struct rtmsg r;
  1194. char buf[1024];
  1195. } req;
  1196. memset (&req, 0, sizeof req);
  1197. bytelen = (family == AF_INET ? 4 : 16);
  1198. req.n.nlmsg_len = NLMSG_LENGTH (sizeof (struct rtmsg));
  1199. req.n.nlmsg_flags = NLM_F_CREATE | NLM_F_REQUEST;
  1200. req.n.nlmsg_type = cmd;
  1201. req.r.rtm_family = family;
  1202. req.r.rtm_table = rib->table;
  1203. req.r.rtm_dst_len = p->prefixlen;
  1204. if ((rib->flags & ZEBRA_FLAG_BLACKHOLE) || (rib->flags & ZEBRA_FLAG_REJECT))
  1205. discard = 1;
  1206. else
  1207. discard = 0;
  1208. if (cmd == RTM_NEWROUTE)
  1209. {
  1210. req.r.rtm_protocol = RTPROT_ZEBRA;
  1211. req.r.rtm_scope = RT_SCOPE_UNIVERSE;
  1212. if (discard)
  1213. {
  1214. if (rib->flags & ZEBRA_FLAG_BLACKHOLE)
  1215. req.r.rtm_type = RTN_BLACKHOLE;
  1216. else if (rib->flags & ZEBRA_FLAG_REJECT)
  1217. req.r.rtm_type = RTN_UNREACHABLE;
  1218. else
  1219. assert (RTN_BLACKHOLE != RTN_UNREACHABLE); /* false */
  1220. }
  1221. else
  1222. req.r.rtm_type = RTN_UNICAST;
  1223. }
  1224. addattr_l (&req.n, sizeof req, RTA_DST, &p->u.prefix, bytelen);
  1225. /* Metric. */
  1226. addattr32 (&req.n, sizeof req, RTA_PRIORITY, rib->metric);
  1227. if (discard)
  1228. {
  1229. if (cmd == RTM_NEWROUTE)
  1230. for (nexthop = rib->nexthop; nexthop; nexthop = nexthop->next)
  1231. SET_FLAG (nexthop->flags, NEXTHOP_FLAG_FIB);
  1232. goto skip;
  1233. }
  1234. /* Multipath case. */
  1235. if (rib->nexthop_active_num == 1 || MULTIPATH_NUM == 1)
  1236. {
  1237. for (nexthop = rib->nexthop; nexthop; nexthop = nexthop->next)
  1238. {
  1239. if ((cmd == RTM_NEWROUTE
  1240. && CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE))
  1241. || (cmd == RTM_DELROUTE
  1242. && CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_FIB)))
  1243. {
  1244. if (CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_RECURSIVE))
  1245. {
  1246. if (IS_ZEBRA_DEBUG_KERNEL)
  1247. {
  1248. zlog_debug
  1249. ("netlink_route_multipath() (recursive, 1 hop): "
  1250. "%s %s/%d, type %s", lookup (nlmsg_str, cmd),
  1251. #ifdef HAVE_IPV6
  1252. (family == AF_INET) ? inet_ntoa (p->u.prefix4) :
  1253. inet6_ntoa (p->u.prefix6),
  1254. #else
  1255. inet_ntoa (p->u.prefix4),
  1256. #endif /* HAVE_IPV6 */
  1257. p->prefixlen, nexthop_types_desc[nexthop->rtype]);
  1258. }
  1259. if (nexthop->rtype == NEXTHOP_TYPE_IPV4
  1260. || nexthop->rtype == NEXTHOP_TYPE_IPV4_IFINDEX)
  1261. {
  1262. addattr_l (&req.n, sizeof req, RTA_GATEWAY,
  1263. &nexthop->rgate.ipv4, bytelen);
  1264. if (IS_ZEBRA_DEBUG_KERNEL)
  1265. zlog_debug("netlink_route_multipath() (recursive, "
  1266. "1 hop): nexthop via %s if %u",
  1267. inet_ntoa (nexthop->rgate.ipv4),
  1268. nexthop->rifindex);
  1269. }
  1270. #ifdef HAVE_IPV6
  1271. if (nexthop->rtype == NEXTHOP_TYPE_IPV6
  1272. || nexthop->rtype == NEXTHOP_TYPE_IPV6_IFINDEX
  1273. || nexthop->rtype == NEXTHOP_TYPE_IPV6_IFNAME)
  1274. {
  1275. addattr_l (&req.n, sizeof req, RTA_GATEWAY,
  1276. &nexthop->rgate.ipv6, bytelen);
  1277. if (IS_ZEBRA_DEBUG_KERNEL)
  1278. zlog_debug("netlink_route_multipath() (recursive, "
  1279. "1 hop): nexthop via %s if %u",
  1280. inet6_ntoa (nexthop->rgate.ipv6),
  1281. nexthop->rifindex);
  1282. }
  1283. #endif /* HAVE_IPV6 */
  1284. if (nexthop->rtype == NEXTHOP_TYPE_IFINDEX
  1285. || nexthop->rtype == NEXTHOP_TYPE_IFNAME
  1286. || nexthop->rtype == NEXTHOP_TYPE_IPV4_IFINDEX
  1287. || nexthop->rtype == NEXTHOP_TYPE_IPV6_IFINDEX
  1288. || nexthop->rtype == NEXTHOP_TYPE_IPV6_IFNAME)
  1289. {
  1290. addattr32 (&req.n, sizeof req, RTA_OIF,
  1291. nexthop->rifindex);
  1292. if (IS_ZEBRA_DEBUG_KERNEL)
  1293. zlog_debug("netlink_route_multipath() (recursive, "
  1294. "1 hop): nexthop via if %u",
  1295. nexthop->rifindex);
  1296. }
  1297. }
  1298. else
  1299. {
  1300. if (IS_ZEBRA_DEBUG_KERNEL)
  1301. {
  1302. zlog_debug
  1303. ("netlink_route_multipath() (single hop): "
  1304. "%s %s/%d, type %s", lookup (nlmsg_str, cmd),
  1305. #ifdef HAVE_IPV6
  1306. (family == AF_INET) ? inet_ntoa (p->u.prefix4) :
  1307. inet6_ntoa (p->u.prefix6),
  1308. #else
  1309. inet_ntoa (p->u.prefix4),
  1310. #endif /* HAVE_IPV6 */
  1311. p->prefixlen, nexthop_types_desc[nexthop->type]);
  1312. }
  1313. if (nexthop->type == NEXTHOP_TYPE_IPV4
  1314. || nexthop->type == NEXTHOP_TYPE_IPV4_IFINDEX)
  1315. {
  1316. addattr_l (&req.n, sizeof req, RTA_GATEWAY,
  1317. &nexthop->gate.ipv4, bytelen);
  1318. if (IS_ZEBRA_DEBUG_KERNEL)
  1319. zlog_debug("netlink_route_multipath() (single hop): "
  1320. "nexthop via %s if %u",
  1321. inet_ntoa (nexthop->gate.ipv4),
  1322. nexthop->ifindex);
  1323. }
  1324. #ifdef HAVE_IPV6
  1325. if (nexthop->type == NEXTHOP_TYPE_IPV6
  1326. || nexthop->type == NEXTHOP_TYPE_IPV6_IFNAME
  1327. || nexthop->type == NEXTHOP_TYPE_IPV6_IFINDEX)
  1328. {
  1329. addattr_l (&req.n, sizeof req, RTA_GATEWAY,
  1330. &nexthop->gate.ipv6, bytelen);
  1331. if (IS_ZEBRA_DEBUG_KERNEL)
  1332. zlog_debug("netlink_route_multipath() (single hop): "
  1333. "nexthop via %s if %u",
  1334. inet6_ntoa (nexthop->gate.ipv6),
  1335. nexthop->ifindex);
  1336. }
  1337. #endif /* HAVE_IPV6 */
  1338. if (nexthop->type == NEXTHOP_TYPE_IFINDEX
  1339. || nexthop->type == NEXTHOP_TYPE_IFNAME
  1340. || nexthop->type == NEXTHOP_TYPE_IPV4_IFINDEX
  1341. || nexthop->type == NEXTHOP_TYPE_IPV6_IFINDEX
  1342. || nexthop->type == NEXTHOP_TYPE_IPV6_IFNAME)
  1343. {
  1344. addattr32 (&req.n, sizeof req, RTA_OIF, nexthop->ifindex);
  1345. if (IS_ZEBRA_DEBUG_KERNEL)
  1346. zlog_debug("netlink_route_multipath() (single hop): "
  1347. "nexthop via if %u", nexthop->ifindex);
  1348. }
  1349. }
  1350. if (cmd == RTM_NEWROUTE)
  1351. SET_FLAG (nexthop->flags, NEXTHOP_FLAG_FIB);
  1352. nexthop_num++;
  1353. break;
  1354. }
  1355. }
  1356. }
  1357. else
  1358. {
  1359. char buf[1024];
  1360. struct rtattr *rta = (void *) buf;
  1361. struct rtnexthop *rtnh;
  1362. rta->rta_type = RTA_MULTIPATH;
  1363. rta->rta_len = RTA_LENGTH (0);
  1364. rtnh = RTA_DATA (rta);
  1365. nexthop_num = 0;
  1366. for (nexthop = rib->nexthop;
  1367. nexthop && (MULTIPATH_NUM == 0 || nexthop_num < MULTIPATH_NUM);
  1368. nexthop = nexthop->next)
  1369. {
  1370. if ((cmd == RTM_NEWROUTE
  1371. && CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_ACTIVE))
  1372. || (cmd == RTM_DELROUTE
  1373. && CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_FIB)))
  1374. {
  1375. nexthop_num++;
  1376. rtnh->rtnh_len = sizeof (*rtnh);
  1377. rtnh->rtnh_flags = 0;
  1378. rtnh->rtnh_hops = 0;
  1379. rta->rta_len += rtnh->rtnh_len;
  1380. if (CHECK_FLAG (nexthop->flags, NEXTHOP_FLAG_RECURSIVE))
  1381. {
  1382. if (IS_ZEBRA_DEBUG_KERNEL)
  1383. {
  1384. zlog_debug ("netlink_route_multipath() "
  1385. "(recursive, multihop): %s %s/%d type %s",
  1386. lookup (nlmsg_str, cmd),
  1387. #ifdef HAVE_IPV6
  1388. (family == AF_INET) ? inet_ntoa (p->u.prefix4) :
  1389. inet6_ntoa (p->u.prefix6),
  1390. #else
  1391. inet_ntoa (p->u.prefix4),
  1392. #endif /* HAVE_IPV6 */
  1393. p->prefixlen, nexthop_types_desc[nexthop->rtype]);
  1394. }
  1395. if (nexthop->rtype == NEXTHOP_TYPE_IPV4
  1396. || nexthop->rtype == NEXTHOP_TYPE_IPV4_IFINDEX)
  1397. {
  1398. rta_addattr_l (rta, 4096, RTA_GATEWAY,
  1399. &nexthop->rgate.ipv4, bytelen);
  1400. rtnh->rtnh_len += sizeof (struct rtattr) + 4;
  1401. if (IS_ZEBRA_DEBUG_KERNEL)
  1402. zlog_debug("netlink_route_multipath() (recursive, "
  1403. "multihop): nexthop via %s if %u",
  1404. inet_ntoa (nexthop->rgate.ipv4),
  1405. nexthop->rifindex);
  1406. }
  1407. #ifdef HAVE_IPV6
  1408. if (nexthop->rtype == NEXTHOP_TYPE_IPV6
  1409. || nexthop->rtype == NEXTHOP_TYPE_IPV6_IFNAME
  1410. || nexthop->rtype == NEXTHOP_TYPE_IPV6_IFINDEX)
  1411. {
  1412. rta_addattr_l (rta, 4096, RTA_GATEWAY,
  1413. &nexthop->rgate.ipv6, bytelen);
  1414. if (IS_ZEBRA_DEBUG_KERNEL)
  1415. zlog_debug("netlink_route_multipath() (recursive, "
  1416. "multihop): nexthop via %s if %u",
  1417. inet6_ntoa (nexthop->rgate.ipv6),
  1418. nexthop->rifindex);
  1419. }
  1420. #endif /* HAVE_IPV6 */
  1421. /* ifindex */
  1422. if (nexthop->rtype == NEXTHOP_TYPE_IFINDEX
  1423. || nexthop->rtype == NEXTHOP_TYPE_IFNAME
  1424. || nexthop->rtype == NEXTHOP_TYPE_IPV4_IFINDEX
  1425. || nexthop->rtype == NEXTHOP_TYPE_IPV6_IFINDEX
  1426. || nexthop->rtype == NEXTHOP_TYPE_IPV6_IFNAME)
  1427. {
  1428. rtnh->rtnh_ifindex = nexthop->rifindex;
  1429. if (IS_ZEBRA_DEBUG_KERNEL)
  1430. zlog_debug("netlink_route_multipath() (recursive, "
  1431. "multihop): nexthop via if %u",
  1432. nexthop->rifindex);
  1433. }
  1434. else
  1435. {
  1436. rtnh->rtnh_ifindex = 0;
  1437. }
  1438. }
  1439. else
  1440. {
  1441. if (IS_ZEBRA_DEBUG_KERNEL)
  1442. {
  1443. zlog_debug ("netlink_route_multipath() (multihop): "
  1444. "%s %s/%d, type %s", lookup (nlmsg_str, cmd),
  1445. #ifdef HAVE_IPV6
  1446. (family == AF_INET) ? inet_ntoa (p->u.prefix4) :
  1447. inet6_ntoa (p->u.prefix6),
  1448. #else
  1449. inet_ntoa (p->u.prefix4),
  1450. #endif /* HAVE_IPV6 */
  1451. p->prefixlen, nexthop_types_desc[nexthop->type]);
  1452. }
  1453. if (nexthop->type == NEXTHOP_TYPE_IPV4
  1454. || nexthop->type == NEXTHOP_TYPE_IPV4_IFINDEX)
  1455. {
  1456. rta_addattr_l (rta, 4096, RTA_GATEWAY,
  1457. &nexthop->gate.ipv4, bytelen);
  1458. rtnh->rtnh_len += sizeof (struct rtattr) + 4;
  1459. if (IS_ZEBRA_DEBUG_KERNEL)
  1460. zlog_debug("netlink_route_multipath() (multihop): "
  1461. "nexthop via %s if %u",
  1462. inet_ntoa (nexthop->gate.ipv4),
  1463. nexthop->ifindex);
  1464. }
  1465. #ifdef HAVE_IPV6
  1466. if (nexthop->type == NEXTHOP_TYPE_IPV6
  1467. || nexthop->type == NEXTHOP_TYPE_IPV6_IFNAME
  1468. || nexthop->type == NEXTHOP_TYPE_IPV6_IFINDEX)
  1469. {
  1470. rta_addattr_l (rta, 4096, RTA_GATEWAY,
  1471. &nexthop->gate.ipv6, bytelen);
  1472. if (IS_ZEBRA_DEBUG_KERNEL)
  1473. zlog_debug("netlink_route_multipath() (multihop): "
  1474. "nexthop via %s if %u",
  1475. inet6_ntoa (nexthop->gate.ipv6),
  1476. nexthop->ifindex);
  1477. }
  1478. #endif /* HAVE_IPV6 */
  1479. /* ifindex */
  1480. if (nexthop->type == NEXTHOP_TYPE_IFINDEX
  1481. || nexthop->type == NEXTHOP_TYPE_IFNAME
  1482. || nexthop->type == NEXTHOP_TYPE_IPV4_IFINDEX
  1483. || nexthop->type == NEXTHOP_TYPE_IPV6_IFNAME
  1484. || nexthop->type == NEXTHOP_TYPE_IPV6_IFINDEX)
  1485. {
  1486. rtnh->rtnh_ifindex = nexthop->ifindex;
  1487. if (IS_ZEBRA_DEBUG_KERNEL)
  1488. zlog_debug("netlink_route_multipath() (multihop): "
  1489. "nexthop via if %u", nexthop->ifindex);
  1490. }
  1491. else
  1492. {
  1493. rtnh->rtnh_ifindex = 0;
  1494. }
  1495. }
  1496. rtnh = RTNH_NEXT (rtnh);
  1497. if (cmd == RTM_NEWROUTE)
  1498. SET_FLAG (nexthop->flags, NEXTHOP_FLAG_FIB);
  1499. }
  1500. }
  1501. if (rta->rta_len > RTA_LENGTH (0))
  1502. addattr_l (&req.n, 1024, RTA_MULTIPATH, RTA_DATA (rta),
  1503. RTA_PAYLOAD (rta));
  1504. }
  1505. /* If there is no useful nexthop then return. */
  1506. if (nexthop_num == 0)
  1507. {
  1508. if (IS_ZEBRA_DEBUG_KERNEL)
  1509. zlog_debug ("netlink_route_multipath(): No useful nexthop.");
  1510. return 0;
  1511. }
  1512. skip:
  1513. /* Destination netlink address. */
  1514. memset (&snl, 0, sizeof snl);
  1515. snl.nl_family = AF_NETLINK;
  1516. /* Talk to netlink socket. */
  1517. return netlink_talk (&req.n, &netlink_cmd);
  1518. }
  1519. int
  1520. kernel_add_ipv4 (struct prefix *p, struct rib *rib)
  1521. {
  1522. return netlink_route_multipath (RTM_NEWROUTE, p, rib, AF_INET);
  1523. }
  1524. int
  1525. kernel_delete_ipv4 (struct prefix *p, struct rib *rib)
  1526. {
  1527. return netlink_route_multipath (RTM_DELROUTE, p, rib, AF_INET);
  1528. }
  1529. #ifdef HAVE_IPV6
  1530. int
  1531. kernel_add_ipv6 (struct prefix *p, struct rib *rib)
  1532. {
  1533. return netlink_route_multipath (RTM_NEWROUTE, p, rib, AF_INET6);
  1534. }
  1535. int
  1536. kernel_delete_ipv6 (struct prefix *p, struct rib *rib)
  1537. {
  1538. return netlink_route_multipath (RTM_DELROUTE, p, rib, AF_INET6);
  1539. }
  1540. /* Delete IPv6 route from the kernel. */
  1541. int
  1542. kernel_delete_ipv6_old (struct prefix_ipv6 *dest, struct in6_addr *gate,
  1543. unsigned int index, int flags, int table)
  1544. {
  1545. return netlink_route (RTM_DELROUTE, AF_INET6, &dest->prefix,
  1546. dest->prefixlen, gate, index, flags, table);
  1547. }
  1548. #endif /* HAVE_IPV6 */
  1549. /* Interface address modification. */
  1550. int
  1551. netlink_address (int cmd, int family, struct interface *ifp,
  1552. struct connected *ifc)
  1553. {
  1554. int bytelen;
  1555. struct prefix *p;
  1556. struct
  1557. {
  1558. struct nlmsghdr n;
  1559. struct ifaddrmsg ifa;
  1560. char buf[1024];
  1561. } req;
  1562. p = ifc->address;
  1563. memset (&req, 0, sizeof req);
  1564. bytelen = (family == AF_INET ? 4 : 16);
  1565. req.n.nlmsg_len = NLMSG_LENGTH (sizeof (struct ifaddrmsg));
  1566. req.n.nlmsg_flags = NLM_F_REQUEST;
  1567. req.n.nlmsg_type = cmd;
  1568. req.ifa.ifa_family = family;
  1569. req.ifa.ifa_index = ifp->ifindex;
  1570. req.ifa.ifa_prefixlen = p->prefixlen;
  1571. addattr_l (&req.n, sizeof req, IFA_LOCAL, &p->u.prefix, bytelen);
  1572. if (family == AF_INET && cmd == RTM_NEWADDR)
  1573. {
  1574. if (!CONNECTED_PEER(ifc) && ifc->destination)
  1575. {
  1576. p = ifc->destination;
  1577. addattr_l (&req.n, sizeof req, IFA_BROADCAST, &p->u.prefix,
  1578. bytelen);
  1579. }
  1580. }
  1581. if (CHECK_FLAG (ifc->flags, ZEBRA_IFA_SECONDARY))
  1582. SET_FLAG (req.ifa.ifa_flags, IFA_F_SECONDARY);
  1583. if (ifc->label)
  1584. addattr_l (&req.n, sizeof req, IFA_LABEL, ifc->label,
  1585. strlen (ifc->label) + 1);
  1586. return netlink_talk (&req.n, &netlink_cmd);
  1587. }
  1588. int
  1589. kernel_address_add_ipv4 (struct interface *ifp, struct connected *ifc)
  1590. {
  1591. return netlink_address (RTM_NEWADDR, AF_INET, ifp, ifc);
  1592. }
  1593. int
  1594. kernel_address_delete_ipv4 (struct interface *ifp, struct connected *ifc)
  1595. {
  1596. return netlink_address (RTM_DELADDR, AF_INET, ifp, ifc);
  1597. }
  1598. extern struct thread_master *master;
  1599. /* Kernel route reflection. */
  1600. int
  1601. kernel_read (struct thread *thread)
  1602. {
  1603. int ret;
  1604. int sock;
  1605. sock = THREAD_FD (thread);
  1606. ret = netlink_parse_info (netlink_information_fetch, &netlink);
  1607. thread_add_read (zebrad.master, kernel_read, NULL, netlink.sock);
  1608. return 0;
  1609. }
  1610. /* Exported interface function. This function simply calls
  1611. netlink_socket (). */
  1612. void
  1613. kernel_init (void)
  1614. {
  1615. unsigned long groups;
  1616. groups = RTMGRP_LINK | RTMGRP_IPV4_ROUTE | RTMGRP_IPV4_IFADDR;
  1617. #ifdef HAVE_IPV6
  1618. groups |= RTMGRP_IPV6_ROUTE | RTMGRP_IPV6_IFADDR;
  1619. #endif /* HAVE_IPV6 */
  1620. netlink_socket (&netlink, groups);
  1621. netlink_socket (&netlink_cmd, 0);
  1622. /* Register kernel socket. */
  1623. if (netlink.sock > 0)
  1624. thread_add_read (zebrad.master, kernel_read, NULL, netlink.sock);
  1625. }