rarp.c 2.2 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394
  1. // SPDX-License-Identifier: GPL-2.0+
  2. /*
  3. * (C) Copyright 2000-2002
  4. * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
  5. */
  6. #include <common.h>
  7. #include <command.h>
  8. #include <log.h>
  9. #include <net.h>
  10. #include <net/tftp.h>
  11. #include "nfs.h"
  12. #include "bootp.h"
  13. #include "rarp.h"
  14. #define TIMEOUT 5000UL /* Milliseconds before trying BOOTP again */
  15. int rarp_try;
  16. /*
  17. * Handle a RARP received packet.
  18. */
  19. void rarp_receive(struct ip_udp_hdr *ip, unsigned len)
  20. {
  21. struct arp_hdr *arp;
  22. debug_cond(DEBUG_NET_PKT, "Got RARP\n");
  23. arp = (struct arp_hdr *)ip;
  24. if (len < ARP_HDR_SIZE) {
  25. printf("bad length %d < %d\n", len, ARP_HDR_SIZE);
  26. return;
  27. }
  28. if ((ntohs(arp->ar_op) != RARPOP_REPLY) ||
  29. (ntohs(arp->ar_hrd) != ARP_ETHER) ||
  30. (ntohs(arp->ar_pro) != PROT_IP) ||
  31. (arp->ar_hln != 6) || (arp->ar_pln != 4)) {
  32. puts("invalid RARP header\n");
  33. } else {
  34. net_copy_ip(&net_ip, &arp->ar_data[16]);
  35. if (net_server_ip.s_addr == 0)
  36. net_copy_ip(&net_server_ip, &arp->ar_data[6]);
  37. memcpy(net_server_ethaddr, &arp->ar_data[0], 6);
  38. debug_cond(DEBUG_DEV_PKT, "Got good RARP\n");
  39. net_auto_load();
  40. }
  41. }
  42. /*
  43. * Timeout on BOOTP request.
  44. */
  45. static void rarp_timeout_handler(void)
  46. {
  47. if (rarp_try >= CONFIG_NET_RETRY_COUNT) {
  48. puts("\nRetry count exceeded; starting again\n");
  49. net_start_again();
  50. } else {
  51. net_set_timeout_handler(TIMEOUT, rarp_timeout_handler);
  52. rarp_request();
  53. }
  54. }
  55. void rarp_request(void)
  56. {
  57. uchar *pkt;
  58. struct arp_hdr *rarp;
  59. int eth_hdr_size;
  60. printf("RARP broadcast %d\n", ++rarp_try);
  61. pkt = net_tx_packet;
  62. eth_hdr_size = net_set_ether(pkt, net_bcast_ethaddr, PROT_RARP);
  63. pkt += eth_hdr_size;
  64. rarp = (struct arp_hdr *)pkt;
  65. rarp->ar_hrd = htons(ARP_ETHER);
  66. rarp->ar_pro = htons(PROT_IP);
  67. rarp->ar_hln = 6;
  68. rarp->ar_pln = 4;
  69. rarp->ar_op = htons(RARPOP_REQUEST);
  70. memcpy(&rarp->ar_data[0], net_ethaddr, 6); /* source ET addr */
  71. memcpy(&rarp->ar_data[6], &net_ip, 4); /* source IP addr */
  72. /* dest ET addr = source ET addr ??*/
  73. memcpy(&rarp->ar_data[10], net_ethaddr, 6);
  74. /* dest IP addr set to broadcast */
  75. memset(&rarp->ar_data[16], 0xff, 4);
  76. net_send_packet(net_tx_packet, eth_hdr_size + ARP_HDR_SIZE);
  77. net_set_timeout_handler(TIMEOUT, rarp_timeout_handler);
  78. }