rip_routemap.c 27 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139
  1. /* RIPv2 routemap.
  2. * Copyright (C) 1999 Kunihiro Ishiguro <kunihiro@zebra.org>
  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. #include "memory.h"
  23. #include "prefix.h"
  24. #include "routemap.h"
  25. #include "command.h"
  26. #include "filter.h"
  27. #include "log.h"
  28. #include "sockunion.h" /* for inet_aton () */
  29. #include "plist.h"
  30. #include "ripd/ripd.h"
  31. struct rip_metric_modifier
  32. {
  33. enum
  34. {
  35. metric_increment,
  36. metric_decrement,
  37. metric_absolute
  38. } type;
  39. u_char metric;
  40. };
  41. /* Add rip route map rule. */
  42. int
  43. rip_route_match_add (struct vty *vty, struct route_map_index *index,
  44. char *command, char *arg)
  45. {
  46. int ret;
  47. ret = route_map_add_match (index, command, arg);
  48. if (ret)
  49. {
  50. switch (ret)
  51. {
  52. case RMAP_RULE_MISSING:
  53. vty_out (vty, "%% Can't find rule.%s", VTY_NEWLINE);
  54. return CMD_WARNING;
  55. break;
  56. case RMAP_COMPILE_ERROR:
  57. vty_out (vty, "%% Argument is malformed.%s", VTY_NEWLINE);
  58. return CMD_WARNING;
  59. break;
  60. }
  61. }
  62. return CMD_SUCCESS;
  63. }
  64. /* Delete rip route map rule. */
  65. int
  66. rip_route_match_delete (struct vty *vty, struct route_map_index *index,
  67. char *command, char *arg)
  68. {
  69. int ret;
  70. ret = route_map_delete_match (index, command, arg);
  71. if (ret)
  72. {
  73. switch (ret)
  74. {
  75. case RMAP_RULE_MISSING:
  76. vty_out (vty, "%% Can't find rule.%s", VTY_NEWLINE);
  77. return CMD_WARNING;
  78. break;
  79. case RMAP_COMPILE_ERROR:
  80. vty_out (vty, "%% Argument is malformed.%s", VTY_NEWLINE);
  81. return CMD_WARNING;
  82. break;
  83. }
  84. }
  85. return CMD_SUCCESS;
  86. }
  87. /* Add rip route map rule. */
  88. int
  89. rip_route_set_add (struct vty *vty, struct route_map_index *index,
  90. char *command, char *arg)
  91. {
  92. int ret;
  93. ret = route_map_add_set (index, command, arg);
  94. if (ret)
  95. {
  96. switch (ret)
  97. {
  98. case RMAP_RULE_MISSING:
  99. vty_out (vty, "%% Can't find rule.%s", VTY_NEWLINE);
  100. return CMD_WARNING;
  101. break;
  102. case RMAP_COMPILE_ERROR:
  103. vty_out (vty, "%% Argument is malformed.%s", VTY_NEWLINE);
  104. return CMD_WARNING;
  105. break;
  106. }
  107. }
  108. return CMD_SUCCESS;
  109. }
  110. /* Delete rip route map rule. */
  111. int
  112. rip_route_set_delete (struct vty *vty, struct route_map_index *index,
  113. char *command, char *arg)
  114. {
  115. int ret;
  116. ret = route_map_delete_set (index, command, arg);
  117. if (ret)
  118. {
  119. switch (ret)
  120. {
  121. case RMAP_RULE_MISSING:
  122. vty_out (vty, "%% Can't find rule.%s", VTY_NEWLINE);
  123. return CMD_WARNING;
  124. break;
  125. case RMAP_COMPILE_ERROR:
  126. vty_out (vty, "%% Argument is malformed.%s", VTY_NEWLINE);
  127. return CMD_WARNING;
  128. break;
  129. }
  130. }
  131. return CMD_SUCCESS;
  132. }
  133. /* Hook function for updating route_map assignment. */
  134. void
  135. rip_route_map_update ()
  136. {
  137. int i;
  138. if (rip)
  139. {
  140. for (i = 0; i < ZEBRA_ROUTE_MAX; i++)
  141. {
  142. if (rip->route_map[i].name)
  143. rip->route_map[i].map =
  144. route_map_lookup_by_name (rip->route_map[i].name);
  145. }
  146. }
  147. }
  148. /* `match metric METRIC' */
  149. /* Match function return 1 if match is success else return zero. */
  150. route_map_result_t
  151. route_match_metric (void *rule, struct prefix *prefix,
  152. route_map_object_t type, void *object)
  153. {
  154. u_int32_t *metric;
  155. struct rip_info *rinfo;
  156. if (type == RMAP_RIP)
  157. {
  158. metric = rule;
  159. rinfo = object;
  160. if (rinfo->metric == *metric)
  161. return RMAP_MATCH;
  162. else
  163. return RMAP_NOMATCH;
  164. }
  165. return RMAP_NOMATCH;
  166. }
  167. /* Route map `match metric' match statement. `arg' is METRIC value */
  168. void *
  169. route_match_metric_compile (char *arg)
  170. {
  171. u_int32_t *metric;
  172. metric = XMALLOC (MTYPE_ROUTE_MAP_COMPILED, sizeof (u_int32_t));
  173. *metric = atoi (arg);
  174. if(*metric > 0)
  175. return metric;
  176. XFREE (MTYPE_ROUTE_MAP_COMPILED, metric);
  177. return NULL;
  178. }
  179. /* Free route map's compiled `match metric' value. */
  180. void
  181. route_match_metric_free (void *rule)
  182. {
  183. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  184. }
  185. /* Route map commands for metric matching. */
  186. struct route_map_rule_cmd route_match_metric_cmd =
  187. {
  188. "metric",
  189. route_match_metric,
  190. route_match_metric_compile,
  191. route_match_metric_free
  192. };
  193. /* `match interface IFNAME' */
  194. /* Match function return 1 if match is success else return zero. */
  195. route_map_result_t
  196. route_match_interface (void *rule, struct prefix *prefix,
  197. route_map_object_t type, void *object)
  198. {
  199. struct rip_info *rinfo;
  200. struct interface *ifp;
  201. char *ifname;
  202. if (type == RMAP_RIP)
  203. {
  204. ifname = rule;
  205. ifp = if_lookup_by_name(ifname);
  206. if (!ifp)
  207. return RMAP_NOMATCH;
  208. rinfo = object;
  209. if (rinfo->ifindex_out == ifp->ifindex)
  210. return RMAP_MATCH;
  211. else
  212. return RMAP_NOMATCH;
  213. }
  214. return RMAP_NOMATCH;
  215. }
  216. /* Route map `match interface' match statement. `arg' is IFNAME value */
  217. /* XXX I don`t know if I need to check does interface exist? */
  218. void *
  219. route_match_interface_compile (char *arg)
  220. {
  221. return XSTRDUP (MTYPE_ROUTE_MAP_COMPILED, arg);
  222. }
  223. /* Free route map's compiled `match interface' value. */
  224. void
  225. route_match_interface_free (void *rule)
  226. {
  227. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  228. }
  229. /* Route map commands for interface matching. */
  230. struct route_map_rule_cmd route_match_interface_cmd =
  231. {
  232. "interface",
  233. route_match_interface,
  234. route_match_interface_compile,
  235. route_match_interface_free
  236. };
  237. /* `match ip next-hop IP_ACCESS_LIST' */
  238. /* Match function return 1 if match is success else return zero. */
  239. route_map_result_t
  240. route_match_ip_next_hop (void *rule, struct prefix *prefix,
  241. route_map_object_t type, void *object)
  242. {
  243. struct access_list *alist;
  244. struct rip_info *rinfo;
  245. struct prefix_ipv4 p;
  246. if (type == RMAP_RIP)
  247. {
  248. rinfo = object;
  249. p.family = AF_INET;
  250. p.prefix = rinfo->nexthop;
  251. p.prefixlen = IPV4_MAX_BITLEN;
  252. alist = access_list_lookup (AFI_IP, (char *) rule);
  253. if (alist == NULL)
  254. return RMAP_NOMATCH;
  255. return (access_list_apply (alist, &p) == FILTER_DENY ?
  256. RMAP_NOMATCH : RMAP_MATCH);
  257. }
  258. return RMAP_NOMATCH;
  259. }
  260. /* Route map `ip next-hop' match statement. `arg' should be
  261. access-list name. */
  262. void *
  263. route_match_ip_next_hop_compile (char *arg)
  264. {
  265. return XSTRDUP (MTYPE_ROUTE_MAP_COMPILED, arg);
  266. }
  267. /* Free route map's compiled `. */
  268. void
  269. route_match_ip_next_hop_free (void *rule)
  270. {
  271. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  272. }
  273. /* Route map commands for ip next-hop matching. */
  274. struct route_map_rule_cmd route_match_ip_next_hop_cmd =
  275. {
  276. "ip next-hop",
  277. route_match_ip_next_hop,
  278. route_match_ip_next_hop_compile,
  279. route_match_ip_next_hop_free
  280. };
  281. /* `match ip next-hop prefix-list PREFIX_LIST' */
  282. route_map_result_t
  283. route_match_ip_next_hop_prefix_list (void *rule, struct prefix *prefix,
  284. route_map_object_t type, void *object)
  285. {
  286. struct prefix_list *plist;
  287. struct rip_info *rinfo;
  288. struct prefix_ipv4 p;
  289. if (type == RMAP_RIP)
  290. {
  291. rinfo = object;
  292. p.family = AF_INET;
  293. p.prefix = rinfo->nexthop;
  294. p.prefixlen = IPV4_MAX_BITLEN;
  295. plist = prefix_list_lookup (AFI_IP, (char *) rule);
  296. if (plist == NULL)
  297. return RMAP_NOMATCH;
  298. return (prefix_list_apply (plist, &p) == PREFIX_DENY ?
  299. RMAP_NOMATCH : RMAP_MATCH);
  300. }
  301. return RMAP_NOMATCH;
  302. }
  303. void *
  304. route_match_ip_next_hop_prefix_list_compile (char *arg)
  305. {
  306. return XSTRDUP (MTYPE_ROUTE_MAP_COMPILED, arg);
  307. }
  308. void
  309. route_match_ip_next_hop_prefix_list_free (void *rule)
  310. {
  311. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  312. }
  313. struct route_map_rule_cmd route_match_ip_next_hop_prefix_list_cmd =
  314. {
  315. "ip next-hop prefix-list",
  316. route_match_ip_next_hop_prefix_list,
  317. route_match_ip_next_hop_prefix_list_compile,
  318. route_match_ip_next_hop_prefix_list_free
  319. };
  320. /* `match ip address IP_ACCESS_LIST' */
  321. /* Match function should return 1 if match is success else return
  322. zero. */
  323. route_map_result_t
  324. route_match_ip_address (void *rule, struct prefix *prefix,
  325. route_map_object_t type, void *object)
  326. {
  327. struct access_list *alist;
  328. if (type == RMAP_RIP)
  329. {
  330. alist = access_list_lookup (AFI_IP, (char *) rule);
  331. if (alist == NULL)
  332. return RMAP_NOMATCH;
  333. return (access_list_apply (alist, prefix) == FILTER_DENY ?
  334. RMAP_NOMATCH : RMAP_MATCH);
  335. }
  336. return RMAP_NOMATCH;
  337. }
  338. /* Route map `ip address' match statement. `arg' should be
  339. access-list name. */
  340. void *
  341. route_match_ip_address_compile (char *arg)
  342. {
  343. return XSTRDUP (MTYPE_ROUTE_MAP_COMPILED, arg);
  344. }
  345. /* Free route map's compiled `ip address' value. */
  346. void
  347. route_match_ip_address_free (void *rule)
  348. {
  349. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  350. }
  351. /* Route map commands for ip address matching. */
  352. struct route_map_rule_cmd route_match_ip_address_cmd =
  353. {
  354. "ip address",
  355. route_match_ip_address,
  356. route_match_ip_address_compile,
  357. route_match_ip_address_free
  358. };
  359. /* `match ip address prefix-list PREFIX_LIST' */
  360. route_map_result_t
  361. route_match_ip_address_prefix_list (void *rule, struct prefix *prefix,
  362. route_map_object_t type, void *object)
  363. {
  364. struct prefix_list *plist;
  365. if (type == RMAP_RIP)
  366. {
  367. plist = prefix_list_lookup (AFI_IP, (char *) rule);
  368. if (plist == NULL)
  369. return RMAP_NOMATCH;
  370. return (prefix_list_apply (plist, prefix) == PREFIX_DENY ?
  371. RMAP_NOMATCH : RMAP_MATCH);
  372. }
  373. return RMAP_NOMATCH;
  374. }
  375. void *
  376. route_match_ip_address_prefix_list_compile (char *arg)
  377. {
  378. return XSTRDUP (MTYPE_ROUTE_MAP_COMPILED, arg);
  379. }
  380. void
  381. route_match_ip_address_prefix_list_free (void *rule)
  382. {
  383. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  384. }
  385. struct route_map_rule_cmd route_match_ip_address_prefix_list_cmd =
  386. {
  387. "ip address prefix-list",
  388. route_match_ip_address_prefix_list,
  389. route_match_ip_address_prefix_list_compile,
  390. route_match_ip_address_prefix_list_free
  391. };
  392. /* `match tag TAG' */
  393. /* Match function return 1 if match is success else return zero. */
  394. route_map_result_t
  395. route_match_tag (void *rule, struct prefix *prefix,
  396. route_map_object_t type, void *object)
  397. {
  398. u_short *tag;
  399. struct rip_info *rinfo;
  400. if (type == RMAP_RIP)
  401. {
  402. tag = rule;
  403. rinfo = object;
  404. /* The information stored by rinfo is host ordered. */
  405. if (rinfo->tag == *tag)
  406. return RMAP_MATCH;
  407. else
  408. return RMAP_NOMATCH;
  409. }
  410. return RMAP_NOMATCH;
  411. }
  412. /* Route map `match tag' match statement. `arg' is TAG value */
  413. void *
  414. route_match_tag_compile (char *arg)
  415. {
  416. u_short *tag;
  417. tag = XMALLOC (MTYPE_ROUTE_MAP_COMPILED, sizeof (u_short));
  418. *tag = atoi (arg);
  419. return tag;
  420. }
  421. /* Free route map's compiled `match tag' value. */
  422. void
  423. route_match_tag_free (void *rule)
  424. {
  425. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  426. }
  427. /* Route map commands for tag matching. */
  428. struct route_map_rule_cmd route_match_tag_cmd =
  429. {
  430. "tag",
  431. route_match_tag,
  432. route_match_tag_compile,
  433. route_match_tag_free
  434. };
  435. /* `set metric METRIC' */
  436. /* Set metric to attribute. */
  437. route_map_result_t
  438. route_set_metric (void *rule, struct prefix *prefix,
  439. route_map_object_t type, void *object)
  440. {
  441. if (type == RMAP_RIP)
  442. {
  443. struct rip_metric_modifier *mod;
  444. struct rip_info *rinfo;
  445. mod = rule;
  446. rinfo = object;
  447. if (mod->type == metric_increment)
  448. rinfo->metric_out += mod->metric;
  449. else if (mod->type == metric_decrement)
  450. rinfo->metric_out -= mod->metric;
  451. else if (mod->type == metric_absolute)
  452. rinfo->metric_out = mod->metric;
  453. if (rinfo->metric_out < 1)
  454. rinfo->metric_out = 1;
  455. if (rinfo->metric_out > RIP_METRIC_INFINITY)
  456. rinfo->metric_out = RIP_METRIC_INFINITY;
  457. rinfo->metric_set = 1;
  458. }
  459. return RMAP_OKAY;
  460. }
  461. /* set metric compilation. */
  462. void *
  463. route_set_metric_compile (char *arg)
  464. {
  465. int len;
  466. char *pnt;
  467. int type;
  468. long metric;
  469. char *endptr = NULL;
  470. struct rip_metric_modifier *mod;
  471. len = strlen (arg);
  472. pnt = arg;
  473. if (len == 0)
  474. return NULL;
  475. /* Examine first character. */
  476. if (arg[0] == '+')
  477. {
  478. type = metric_increment;
  479. pnt++;
  480. }
  481. else if (arg[0] == '-')
  482. {
  483. type = metric_decrement;
  484. pnt++;
  485. }
  486. else
  487. type = metric_absolute;
  488. /* Check beginning with digit string. */
  489. if (*pnt < '0' || *pnt > '9')
  490. return NULL;
  491. /* Convert string to integer. */
  492. metric = strtol (pnt, &endptr, 10);
  493. if (metric == LONG_MAX || *endptr != '\0')
  494. return NULL;
  495. if (metric < 0 || metric > RIP_METRIC_INFINITY)
  496. return NULL;
  497. mod = XMALLOC (MTYPE_ROUTE_MAP_COMPILED,
  498. sizeof (struct rip_metric_modifier));
  499. mod->type = type;
  500. mod->metric = metric;
  501. return mod;
  502. }
  503. /* Free route map's compiled `set metric' value. */
  504. void
  505. route_set_metric_free (void *rule)
  506. {
  507. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  508. }
  509. /* Set metric rule structure. */
  510. struct route_map_rule_cmd route_set_metric_cmd =
  511. {
  512. "metric",
  513. route_set_metric,
  514. route_set_metric_compile,
  515. route_set_metric_free,
  516. };
  517. /* `set ip next-hop IP_ADDRESS' */
  518. /* Set nexthop to object. ojbect must be pointer to struct attr. */
  519. route_map_result_t
  520. route_set_ip_nexthop (void *rule, struct prefix *prefix,
  521. route_map_object_t type, void *object)
  522. {
  523. struct in_addr *address;
  524. struct rip_info *rinfo;
  525. if(type == RMAP_RIP)
  526. {
  527. /* Fetch routemap's rule information. */
  528. address = rule;
  529. rinfo = object;
  530. /* Set next hop value. */
  531. rinfo->nexthop_out = *address;
  532. }
  533. return RMAP_OKAY;
  534. }
  535. /* Route map `ip nexthop' compile function. Given string is converted
  536. to struct in_addr structure. */
  537. void *
  538. route_set_ip_nexthop_compile (char *arg)
  539. {
  540. int ret;
  541. struct in_addr *address;
  542. address = XMALLOC (MTYPE_ROUTE_MAP_COMPILED, sizeof (struct in_addr));
  543. ret = inet_aton (arg, address);
  544. if (ret == 0)
  545. {
  546. XFREE (MTYPE_ROUTE_MAP_COMPILED, address);
  547. return NULL;
  548. }
  549. return address;
  550. }
  551. /* Free route map's compiled `ip nexthop' value. */
  552. void
  553. route_set_ip_nexthop_free (void *rule)
  554. {
  555. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  556. }
  557. /* Route map commands for ip nexthop set. */
  558. struct route_map_rule_cmd route_set_ip_nexthop_cmd =
  559. {
  560. "ip next-hop",
  561. route_set_ip_nexthop,
  562. route_set_ip_nexthop_compile,
  563. route_set_ip_nexthop_free
  564. };
  565. /* `set tag TAG' */
  566. /* Set tag to object. ojbect must be pointer to struct attr. */
  567. route_map_result_t
  568. route_set_tag (void *rule, struct prefix *prefix,
  569. route_map_object_t type, void *object)
  570. {
  571. u_short *tag;
  572. struct rip_info *rinfo;
  573. if(type == RMAP_RIP)
  574. {
  575. /* Fetch routemap's rule information. */
  576. tag = rule;
  577. rinfo = object;
  578. /* Set next hop value. */
  579. rinfo->tag_out = *tag;
  580. }
  581. return RMAP_OKAY;
  582. }
  583. /* Route map `tag' compile function. Given string is converted
  584. to u_short. */
  585. void *
  586. route_set_tag_compile (char *arg)
  587. {
  588. u_short *tag;
  589. tag = XMALLOC (MTYPE_ROUTE_MAP_COMPILED, sizeof (u_short));
  590. *tag = atoi (arg);
  591. return tag;
  592. }
  593. /* Free route map's compiled `ip nexthop' value. */
  594. void
  595. route_set_tag_free (void *rule)
  596. {
  597. XFREE (MTYPE_ROUTE_MAP_COMPILED, rule);
  598. }
  599. /* Route map commands for tag set. */
  600. struct route_map_rule_cmd route_set_tag_cmd =
  601. {
  602. "tag",
  603. route_set_tag,
  604. route_set_tag_compile,
  605. route_set_tag_free
  606. };
  607. #define MATCH_STR "Match values from routing table\n"
  608. #define SET_STR "Set values in destination routing protocol\n"
  609. DEFUN (match_metric,
  610. match_metric_cmd,
  611. "match metric <0-4294967295>",
  612. MATCH_STR
  613. "Match metric of route\n"
  614. "Metric value\n")
  615. {
  616. return rip_route_match_add (vty, vty->index, "metric", argv[0]);
  617. }
  618. DEFUN (no_match_metric,
  619. no_match_metric_cmd,
  620. "no match metric",
  621. NO_STR
  622. MATCH_STR
  623. "Match metric of route\n")
  624. {
  625. if (argc == 0)
  626. return rip_route_match_delete (vty, vty->index, "metric", NULL);
  627. return rip_route_match_delete (vty, vty->index, "metric", argv[0]);
  628. }
  629. ALIAS (no_match_metric,
  630. no_match_metric_val_cmd,
  631. "no match metric <0-4294967295>",
  632. NO_STR
  633. MATCH_STR
  634. "Match metric of route\n"
  635. "Metric value\n")
  636. DEFUN (match_interface,
  637. match_interface_cmd,
  638. "match interface WORD",
  639. MATCH_STR
  640. "Match first hop interface of route\n"
  641. "Interface name\n")
  642. {
  643. return rip_route_match_add (vty, vty->index, "interface", argv[0]);
  644. }
  645. DEFUN (no_match_interface,
  646. no_match_interface_cmd,
  647. "no match interface",
  648. NO_STR
  649. MATCH_STR
  650. "Match first hop interface of route\n")
  651. {
  652. if (argc == 0)
  653. return rip_route_match_delete (vty, vty->index, "interface", NULL);
  654. return rip_route_match_delete (vty, vty->index, "interface", argv[0]);
  655. }
  656. ALIAS (no_match_interface,
  657. no_match_interface_val_cmd,
  658. "no match interface WORD",
  659. NO_STR
  660. MATCH_STR
  661. "Match first hop interface of route\n"
  662. "Interface name\n")
  663. DEFUN (match_ip_next_hop,
  664. match_ip_next_hop_cmd,
  665. "match ip next-hop (<1-199>|<1300-2699>|WORD)",
  666. MATCH_STR
  667. IP_STR
  668. "Match next-hop address of route\n"
  669. "IP access-list number\n"
  670. "IP access-list number (expanded range)\n"
  671. "IP Access-list name\n")
  672. {
  673. return rip_route_match_add (vty, vty->index, "ip next-hop", argv[0]);
  674. }
  675. DEFUN (no_match_ip_next_hop,
  676. no_match_ip_next_hop_cmd,
  677. "no match ip next-hop",
  678. NO_STR
  679. MATCH_STR
  680. IP_STR
  681. "Match next-hop address of route\n")
  682. {
  683. if (argc == 0)
  684. return rip_route_match_delete (vty, vty->index, "ip next-hop", NULL);
  685. return rip_route_match_delete (vty, vty->index, "ip next-hop", argv[0]);
  686. }
  687. ALIAS (no_match_ip_next_hop,
  688. no_match_ip_next_hop_val_cmd,
  689. "no match ip next-hop (<1-199>|<1300-2699>|WORD)",
  690. NO_STR
  691. MATCH_STR
  692. IP_STR
  693. "Match next-hop address of route\n"
  694. "IP access-list number\n"
  695. "IP access-list number (expanded range)\n"
  696. "IP Access-list name\n")
  697. DEFUN (match_ip_next_hop_prefix_list,
  698. match_ip_next_hop_prefix_list_cmd,
  699. "match ip next-hop prefix-list WORD",
  700. MATCH_STR
  701. IP_STR
  702. "Match next-hop address of route\n"
  703. "Match entries of prefix-lists\n"
  704. "IP prefix-list name\n")
  705. {
  706. return rip_route_match_add (vty, vty->index, "ip next-hop prefix-list", argv[0]);
  707. }
  708. DEFUN (no_match_ip_next_hop_prefix_list,
  709. no_match_ip_next_hop_prefix_list_cmd,
  710. "no match ip next-hop prefix-list",
  711. NO_STR
  712. MATCH_STR
  713. IP_STR
  714. "Match next-hop address of route\n"
  715. "Match entries of prefix-lists\n")
  716. {
  717. if (argc == 0)
  718. return rip_route_match_delete (vty, vty->index, "ip next-hop prefix-list", NULL);
  719. return rip_route_match_delete (vty, vty->index, "ip next-hop prefix-list", argv[0]);
  720. }
  721. ALIAS (no_match_ip_next_hop_prefix_list,
  722. no_match_ip_next_hop_prefix_list_val_cmd,
  723. "no match ip next-hop prefix-list WORD",
  724. NO_STR
  725. MATCH_STR
  726. IP_STR
  727. "Match next-hop address of route\n"
  728. "Match entries of prefix-lists\n"
  729. "IP prefix-list name\n")
  730. DEFUN (match_ip_address,
  731. match_ip_address_cmd,
  732. "match ip address (<1-199>|<1300-2699>|WORD)",
  733. MATCH_STR
  734. IP_STR
  735. "Match address of route\n"
  736. "IP access-list number\n"
  737. "IP access-list number (expanded range)\n"
  738. "IP Access-list name\n")
  739. {
  740. return rip_route_match_add (vty, vty->index, "ip address", argv[0]);
  741. }
  742. DEFUN (no_match_ip_address,
  743. no_match_ip_address_cmd,
  744. "no match ip address",
  745. NO_STR
  746. MATCH_STR
  747. IP_STR
  748. "Match address of route\n")
  749. {
  750. if (argc == 0)
  751. return rip_route_match_delete (vty, vty->index, "ip address", NULL);
  752. return rip_route_match_delete (vty, vty->index, "ip address", argv[0]);
  753. }
  754. ALIAS (no_match_ip_address,
  755. no_match_ip_address_val_cmd,
  756. "no match ip address (<1-199>|<1300-2699>|WORD)",
  757. NO_STR
  758. MATCH_STR
  759. IP_STR
  760. "Match address of route\n"
  761. "IP access-list number\n"
  762. "IP access-list number (expanded range)\n"
  763. "IP Access-list name\n")
  764. DEFUN (match_ip_address_prefix_list,
  765. match_ip_address_prefix_list_cmd,
  766. "match ip address prefix-list WORD",
  767. MATCH_STR
  768. IP_STR
  769. "Match address of route\n"
  770. "Match entries of prefix-lists\n"
  771. "IP prefix-list name\n")
  772. {
  773. return rip_route_match_add (vty, vty->index, "ip address prefix-list", argv[0]);
  774. }
  775. DEFUN (no_match_ip_address_prefix_list,
  776. no_match_ip_address_prefix_list_cmd,
  777. "no match ip address prefix-list",
  778. NO_STR
  779. MATCH_STR
  780. IP_STR
  781. "Match address of route\n"
  782. "Match entries of prefix-lists\n")
  783. {
  784. if (argc == 0)
  785. return rip_route_match_delete (vty, vty->index, "ip address prefix-list", NULL);
  786. return rip_route_match_delete (vty, vty->index, "ip address prefix-list", argv[0]);
  787. }
  788. ALIAS (no_match_ip_address_prefix_list,
  789. no_match_ip_address_prefix_list_val_cmd,
  790. "no match ip address prefix-list WORD",
  791. NO_STR
  792. MATCH_STR
  793. IP_STR
  794. "Match address of route\n"
  795. "Match entries of prefix-lists\n"
  796. "IP prefix-list name\n")
  797. DEFUN (match_tag,
  798. match_tag_cmd,
  799. "match tag <0-65535>",
  800. MATCH_STR
  801. "Match tag of route\n"
  802. "Metric value\n")
  803. {
  804. return rip_route_match_add (vty, vty->index, "tag", argv[0]);
  805. }
  806. DEFUN (no_match_tag,
  807. no_match_tag_cmd,
  808. "no match tag",
  809. NO_STR
  810. MATCH_STR
  811. "Match tag of route\n")
  812. {
  813. if (argc == 0)
  814. return rip_route_match_delete (vty, vty->index, "tag", NULL);
  815. return rip_route_match_delete (vty, vty->index, "tag", argv[0]);
  816. }
  817. ALIAS (no_match_tag,
  818. no_match_tag_val_cmd,
  819. "no match tag <0-65535>",
  820. NO_STR
  821. MATCH_STR
  822. "Match tag of route\n"
  823. "Metric value\n")
  824. /* set functions */
  825. DEFUN (set_metric,
  826. set_metric_cmd,
  827. "set metric <0-4294967295>",
  828. SET_STR
  829. "Metric value for destination routing protocol\n"
  830. "Metric value\n")
  831. {
  832. return rip_route_set_add (vty, vty->index, "metric", argv[0]);
  833. }
  834. ALIAS (set_metric,
  835. set_metric_addsub_cmd,
  836. "set metric <+/-metric>",
  837. SET_STR
  838. "Metric value for destination routing protocol\n"
  839. "Add or subtract BGP metric\n")
  840. DEFUN (no_set_metric,
  841. no_set_metric_cmd,
  842. "no set metric",
  843. NO_STR
  844. SET_STR
  845. "Metric value for destination routing protocol\n")
  846. {
  847. if (argc == 0)
  848. return rip_route_set_delete (vty, vty->index, "metric", NULL);
  849. return rip_route_set_delete (vty, vty->index, "metric", argv[0]);
  850. }
  851. ALIAS (no_set_metric,
  852. no_set_metric_val_cmd,
  853. "no set metric (<0-4294967295>|<+/-metric>)",
  854. NO_STR
  855. SET_STR
  856. "Metric value for destination routing protocol\n"
  857. "Metric value\n"
  858. "Add or subtract metric\n")
  859. DEFUN (set_ip_nexthop,
  860. set_ip_nexthop_cmd,
  861. "set ip next-hop A.B.C.D",
  862. SET_STR
  863. IP_STR
  864. "Next hop address\n"
  865. "IP address of next hop\n")
  866. {
  867. union sockunion su;
  868. int ret;
  869. ret = str2sockunion (argv[0], &su);
  870. if (ret < 0)
  871. {
  872. vty_out (vty, "%% Malformed next-hop address%s", VTY_NEWLINE);
  873. return CMD_WARNING;
  874. }
  875. return rip_route_set_add (vty, vty->index, "ip next-hop", argv[0]);
  876. }
  877. DEFUN (no_set_ip_nexthop,
  878. no_set_ip_nexthop_cmd,
  879. "no set ip next-hop",
  880. NO_STR
  881. SET_STR
  882. IP_STR
  883. "Next hop address\n")
  884. {
  885. if (argc == 0)
  886. return rip_route_set_delete (vty, vty->index, "ip next-hop", NULL);
  887. return rip_route_set_delete (vty, vty->index, "ip next-hop", argv[0]);
  888. }
  889. ALIAS (no_set_ip_nexthop,
  890. no_set_ip_nexthop_val_cmd,
  891. "no set ip next-hop A.B.C.D",
  892. NO_STR
  893. SET_STR
  894. IP_STR
  895. "Next hop address\n"
  896. "IP address of next hop\n")
  897. DEFUN (set_tag,
  898. set_tag_cmd,
  899. "set tag <0-65535>",
  900. SET_STR
  901. "Tag value for routing protocol\n"
  902. "Tag value\n")
  903. {
  904. return rip_route_set_add (vty, vty->index, "tag", argv[0]);
  905. }
  906. DEFUN (no_set_tag,
  907. no_set_tag_cmd,
  908. "no set tag",
  909. NO_STR
  910. SET_STR
  911. "Tag value for routing protocol\n")
  912. {
  913. if (argc == 0)
  914. return rip_route_set_delete (vty, vty->index, "tag", NULL);
  915. return rip_route_set_delete (vty, vty->index, "tag", argv[0]);
  916. }
  917. ALIAS (no_set_tag,
  918. no_set_tag_val_cmd,
  919. "no set tag <0-65535>",
  920. NO_STR
  921. SET_STR
  922. "Tag value for routing protocol\n"
  923. "Tag value\n")
  924. void
  925. rip_route_map_reset ()
  926. {
  927. ;
  928. }
  929. /* Route-map init */
  930. void
  931. rip_route_map_init ()
  932. {
  933. route_map_init ();
  934. route_map_init_vty ();
  935. route_map_add_hook (rip_route_map_update);
  936. route_map_delete_hook (rip_route_map_update);
  937. route_map_install_match (&route_match_metric_cmd);
  938. route_map_install_match (&route_match_interface_cmd);
  939. route_map_install_match (&route_match_ip_next_hop_cmd);
  940. route_map_install_match (&route_match_ip_next_hop_prefix_list_cmd);
  941. route_map_install_match (&route_match_ip_address_cmd);
  942. route_map_install_match (&route_match_ip_address_prefix_list_cmd);
  943. route_map_install_match (&route_match_tag_cmd);
  944. route_map_install_set (&route_set_metric_cmd);
  945. route_map_install_set (&route_set_ip_nexthop_cmd);
  946. route_map_install_set (&route_set_tag_cmd);
  947. install_element (RMAP_NODE, &match_metric_cmd);
  948. install_element (RMAP_NODE, &no_match_metric_cmd);
  949. install_element (RMAP_NODE, &no_match_metric_val_cmd);
  950. install_element (RMAP_NODE, &match_interface_cmd);
  951. install_element (RMAP_NODE, &no_match_interface_cmd);
  952. install_element (RMAP_NODE, &no_match_interface_val_cmd);
  953. install_element (RMAP_NODE, &match_ip_next_hop_cmd);
  954. install_element (RMAP_NODE, &no_match_ip_next_hop_cmd);
  955. install_element (RMAP_NODE, &no_match_ip_next_hop_val_cmd);
  956. install_element (RMAP_NODE, &match_ip_next_hop_prefix_list_cmd);
  957. install_element (RMAP_NODE, &no_match_ip_next_hop_prefix_list_cmd);
  958. install_element (RMAP_NODE, &no_match_ip_next_hop_prefix_list_val_cmd);
  959. install_element (RMAP_NODE, &match_ip_address_cmd);
  960. install_element (RMAP_NODE, &no_match_ip_address_cmd);
  961. install_element (RMAP_NODE, &no_match_ip_address_val_cmd);
  962. install_element (RMAP_NODE, &match_ip_address_prefix_list_cmd);
  963. install_element (RMAP_NODE, &no_match_ip_address_prefix_list_cmd);
  964. install_element (RMAP_NODE, &no_match_ip_address_prefix_list_val_cmd);
  965. install_element (RMAP_NODE, &match_tag_cmd);
  966. install_element (RMAP_NODE, &no_match_tag_cmd);
  967. install_element (RMAP_NODE, &no_match_tag_val_cmd);
  968. install_element (RMAP_NODE, &set_metric_cmd);
  969. install_element (RMAP_NODE, &set_metric_addsub_cmd);
  970. install_element (RMAP_NODE, &no_set_metric_cmd);
  971. install_element (RMAP_NODE, &no_set_metric_val_cmd);
  972. install_element (RMAP_NODE, &set_ip_nexthop_cmd);
  973. install_element (RMAP_NODE, &no_set_ip_nexthop_cmd);
  974. install_element (RMAP_NODE, &no_set_ip_nexthop_val_cmd);
  975. install_element (RMAP_NODE, &set_tag_cmd);
  976. install_element (RMAP_NODE, &no_set_tag_cmd);
  977. install_element (RMAP_NODE, &no_set_tag_val_cmd);
  978. }