diff options
Diffstat (limited to 'sys/arch/mvme68k/stand/sboot/etherfun.c')
-rw-r--r-- | sys/arch/mvme68k/stand/sboot/etherfun.c | 320 |
1 files changed, 162 insertions, 158 deletions
diff --git a/sys/arch/mvme68k/stand/sboot/etherfun.c b/sys/arch/mvme68k/stand/sboot/etherfun.c index 7c107b00e8a..37b920a79b8 100644 --- a/sys/arch/mvme68k/stand/sboot/etherfun.c +++ b/sys/arch/mvme68k/stand/sboot/etherfun.c @@ -1,3 +1,5 @@ +/* $OpenBSD: etherfun.c,v 1.2 1996/04/28 10:49:36 deraadt Exp $ */ + /* * * Copyright (c) 1995 Charles D. Cranor and Seth Widoff @@ -31,183 +33,185 @@ */ /* etherfun.c */ +#include <sys/cdefs.h> #include "sboot.h" #include "etherfun.h" /* Construct and send a rev arp packet */ void -do_rev_arp () +do_rev_arp() { - int i; - - for ( i = 0; i < 6; i++ ) { - eh->ether_dhost[i] = 0xff; - } - bcopy(myea, eh->ether_shost, 6); - eh->ether_type = ETYPE_RARP; - - rarp->ar_hrd = 1; /* hardware type is 1 */ - rarp->ar_pro = PTYPE_IP; - rarp->ar_hln = 6; /* length of hardware address is 6 bytes */ - rarp->ar_pln = 4; /* length of ip address is 4 byte */ - rarp->ar_op = OPCODE_RARP; - bcopy(myea, rarp->arp_sha, sizeof(myea)); - bcopy(myea, rarp->arp_tha, sizeof(myea)); - for ( i = 0; i < 4; i++ ) { - rarp->arp_spa[i] = rarp->arp_tpa[i] = 0x00; - } - - le_put(buf, 76); + int i; + + for (i = 0; i < 6; i++) + eh->ether_dhost[i] = 0xff; + + bcopy(myea, eh->ether_shost, 6); + eh->ether_type = ETYPE_RARP; + + rarp->ar_hrd = 1; /* hardware type is 1 */ + rarp->ar_pro = PTYPE_IP; + rarp->ar_hln = 6; /* length of hardware address is 6 bytes */ + rarp->ar_pln = 4; /* length of ip address is 4 byte */ + rarp->ar_op = OPCODE_RARP; + bcopy(myea, rarp->arp_sha, sizeof(myea)); + bcopy(myea, rarp->arp_tha, sizeof(myea)); + for (i = 0; i < 4; i++) + rarp->arp_spa[i] = rarp->arp_tpa[i] = 0x00; + + le_put(buf, 76); } - -/* Recieve and disassemble the rev_arp reply */ +/* Receive and disassemble the rev_arp reply */ int -get_rev_arp () +get_rev_arp() { - le_get(buf, sizeof(buf), 6); - if ( eh->ether_type == ETYPE_RARP && rarp->ar_op == OPCODE_REPLY ) { - bcopy(rarp->arp_tpa, myip, sizeof(rarp->arp_tpa)); - bcopy(rarp->arp_spa, servip, sizeof(rarp->arp_spa)); - bcopy(rarp->arp_sha, servea, sizeof(rarp->arp_sha)); - return 1; - } - return 0; + le_get(buf, sizeof(buf), 6); + if (eh->ether_type == ETYPE_RARP && rarp->ar_op == OPCODE_REPLY) { + bcopy(rarp->arp_tpa, myip, sizeof(rarp->arp_tpa)); + bcopy(rarp->arp_spa, servip, sizeof(rarp->arp_spa)); + bcopy(rarp->arp_sha, servea, sizeof(rarp->arp_sha)); + return (1); + } + return (0); } /* Try to get a reply to a rev arp request */ - -int -rev_arp () -{ - int tries = 0; - while ( tries < 5 ) { - do_rev_arp(); - if ( get_rev_arp() ) { - return 1; - } - tries++; - } - return 0; -} - -/* Send a tftp read request or acknowledgement - mesgtype 0 is a read request, 1 is an aknowledgement */ - -void -do_send_tftp ( int mesgtype ) +int +rev_arp() { - u_long res, iptmp, lcv; - char *tot; - - if ( mesgtype == 0 ) { - tot = tftp_r + (sizeof(MSG)-1); - myport = (u_short)time(); - if (myport < 1000) myport += 1000; - servport = FTP_PORT; /* to start */ - } else { - tot = (char *)tftp_a + 4; - } - - bcopy (servea, eh->ether_dhost, sizeof(servea)); - bcopy (myea, eh->ether_shost, sizeof(myea)); - eh->ether_type = ETYPE_IP; - - iph->ip_v = IP_VERSION; - iph->ip_hl = IP_HLEN; - iph->ip_tos = 0; /* type of service is 0 */ - iph->ip_id = 0; /* id field is 0 */ - iph->ip_off = IP_DF; - iph->ip_ttl = 3; /* time to live is 3 seconds/hops */ - iph->ip_p = IPP_UDP; - bcopy(myip, iph->ip_src, sizeof(myip)); - bcopy(servip, iph->ip_dst, sizeof(servip)); - iph->ip_sum = 0; - iph->ip_len = tot - (char *)iph; - res = oc_cksum(iph, sizeof(struct ip), 0); - iph->ip_sum = 0xffff & ~res; - udph->uh_sport = myport; - udph->uh_dport = servport; - udph->uh_sum = 0; - - if ( mesgtype ) { - tftp_a->op_code = FTPOP_ACKN; - tftp_a->block = (u_short)(mesgtype); - } else { - bcopy (myip, &iptmp, sizeof(iptmp)); - bcopy(MSG, tftp_r, (sizeof(MSG)-1)); - for (lcv = 9; lcv >= 2; lcv--) { - tftp_r[lcv] = "0123456789ABCDEF"[iptmp & 0xF]; - - iptmp = iptmp >> 4; - } - } - - udph->uh_ulen = tot - (char *)udph; - - le_put( buf, tot - buf); + int tries = 0; + while (tries < 5) { + do_rev_arp(); + if (get_rev_arp()) + return (1); + tries++; + } + return (0); } -/* Attempt to tftp a file and read it into memory */ - -int -do_get_file () +/* + * Send a tftp read request or acknowledgement + * mesgtype 0 is a read request, 1 is an + * acknowledgement + */ +void +do_send_tftp(mesgtype) + int mesgtype; { - int fail = 0, oldlen; - char *loadat = (char *)LOAD_ADDR; - last_ack = 0; - - do_send_tftp( READ ); - while (1) { - if ( le_get(buf, sizeof(buf), 5) == 0) { /* timeout occured */ - if ( last_ack ) { - do_send_tftp( last_ack ); - } else { - do_send_tftp( READ ); - } - fail++; - if ( fail > 5 ) { - printf("\n"); - return 1; - } - } else { - printf("%x \r", tftp->info.block*512); - if ((eh->ether_type != ETYPE_IP) || (iph->ip_p != IPP_UDP)) { - fail++; - continue; - } - if (servport == FTP_PORT) servport = udph->uh_sport; - if (tftp->info.op_code == FTPOP_ERR) { - printf("TFTP: Download error %d: %s\n", - tftp->info.block, tftp->data); - return 1; - } - if (tftp->info.block != last_ack + 1) { /* we recieved the wrong block */ - if (tftp->info.block < last_ack +1) { - do_send_tftp(tftp->info.block); /* ackn whatever we recieved */ + u_long res, iptmp, lcv; + char *tot; + + if (mesgtype == 0) { + tot = tftp_r + (sizeof(MSG) - 1); + myport = (u_short) time(); + if (myport < 1000) + myport += 1000; + servport = FTP_PORT; /* to start */ + } else { + tot = (char *) tftp_a + 4; + } + + bcopy(servea, eh->ether_dhost, sizeof(servea)); + bcopy(myea, eh->ether_shost, sizeof(myea)); + eh->ether_type = ETYPE_IP; + + iph->ip_v = IP_VERSION; + iph->ip_hl = IP_HLEN; + iph->ip_tos = 0; /* type of service is 0 */ + iph->ip_id = 0; /* id field is 0 */ + iph->ip_off = IP_DF; + iph->ip_ttl = 3; /* time to live is 3 seconds/hops */ + iph->ip_p = IPP_UDP; + bcopy(myip, iph->ip_src, sizeof(myip)); + bcopy(servip, iph->ip_dst, sizeof(servip)); + iph->ip_sum = 0; + iph->ip_len = tot - (char *) iph; + res = oc_cksum(iph, sizeof(struct ip), 0); + iph->ip_sum = 0xffff & ~res; + udph->uh_sport = myport; + udph->uh_dport = servport; + udph->uh_sum = 0; + + if (mesgtype) { + tftp_a->op_code = FTPOP_ACKN; + tftp_a->block = (u_short) (mesgtype); } else { - do_send_tftp( last_ack ); /* ackn the last confirmed block */ - } - fail++; - } else { /* we got the right block */ - fail = 0; - last_ack++; - oldlen = udph->uh_ulen; - do_send_tftp( last_ack ); - /*printf("bcopy %x %x %d\n", &tftp->data, loadat, oldlen - 12);*/ - bcopy(&tftp->data, loadat, oldlen - 12); - loadat += oldlen - 12; - if (oldlen < (8 + 4 + 512)) { - printf("\n"); - return 0; - } - } - } - } - printf("\n"); - return 0; -} + bcopy(myip, &iptmp, sizeof(iptmp)); + bcopy(MSG, tftp_r, (sizeof(MSG) - 1)); + for (lcv = 9; lcv >= 2; lcv--) { + tftp_r[lcv] = "0123456789ABCDEF"[iptmp & 0xF]; + iptmp = iptmp >> 4; + } + } + udph->uh_ulen = tot - (char *) udph; + le_put(buf, tot - buf); +} +/* Attempt to tftp a file and read it into memory */ +int +do_get_file() +{ + int fail = 0, oldlen; + char *loadat = (char *) LOAD_ADDR; + last_ack = 0; + + do_send_tftp(READ); + while (1) { + if (le_get(buf, sizeof(buf), 5) == 0) { + /* timeout occured */ + if (last_ack) + do_send_tftp(last_ack); + else + do_send_tftp(READ); + + fail++; + if (fail > 5) { + printf("\n"); + return (1); + } + } else { + printf("%x \r", tftp->info.block * 512); + if ((eh->ether_type != ETYPE_IP) || (iph->ip_p != IPP_UDP)) { + fail++; + continue; + } + if (servport == FTP_PORT) + servport = udph->uh_sport; + if (tftp->info.op_code == FTPOP_ERR) { + printf("TFTP: Download error %d: %s\n", + tftp->info.block, tftp->data); + return (1); + } + if (tftp->info.block != last_ack + 1) { + /* we received the wrong block */ + if (tftp->info.block < last_ack + 1) { + /* nack whatever we received */ + do_send_tftp(tftp->info.block); + } else { + /* nack the last confirmed block */ + do_send_tftp(last_ack); + } + fail++; + } else {/* we got the right block */ + fail = 0; + last_ack++; + oldlen = udph->uh_ulen; + do_send_tftp(last_ack); + /* printf("bcopy %x %x %d\n", &tftp->data, + * loadat, oldlen - 12); */ + bcopy(&tftp->data, loadat, oldlen - 12); + loadat += oldlen - 12; + if (oldlen < (8 + 4 + 512)) { + printf("\n"); + return (0); + } + } + } + } + printf("\n"); + return (0); +} |