Annotation of qemu/roms/openbios/libopenbios/ipchecksum.c, revision 1.1.1.1

1.1       root        1: /* Taken from Etherboot */
                      2: 
                      3: #include "libopenbios/ipchecksum.h"
                      4: 
                      5: unsigned short ipchksum(const void *data, unsigned long length)
                      6: {
                      7:        unsigned long sum;
                      8:        unsigned long i;
                      9:        const unsigned char *ptr;
                     10:        union {
                     11:            unsigned char byte[2];
                     12:            unsigned short word;
                     13:        } u;
                     14: 
                     15:        /* In the most straight forward way possible,
                     16:         * compute an ip style checksum.
                     17:         */
                     18:        sum = 0;
                     19:        ptr = data;
                     20:        for(i = 0; i < length; i++) {
                     21:                unsigned long value;
                     22:                value = ptr[i];
                     23:                if (i & 1) {
                     24:                        value <<= 8;
                     25:                }
                     26:                /* Add the new value */
                     27:                sum += value;
                     28:                /* Wrap around the carry */
                     29:                if (sum > 0xFFFF) {
                     30:                        sum = (sum + (sum >> 16)) & 0xFFFF;
                     31:                }
                     32:        }
                     33:        u.byte[0] = (unsigned char) sum;
                     34:        u.byte[1] = (unsigned char) (sum >> 8);
                     35:        return (unsigned short) ~u.word;
                     36: }
                     37: 
                     38: unsigned short add_ipchksums(unsigned long offset, unsigned short sum, unsigned short new)
                     39: {
                     40:        unsigned long checksum;
                     41:        sum = ~sum & 0xFFFF;
                     42:        new = ~new & 0xFFFF;
                     43:        if (offset & 1) {
                     44:                /* byte swap the sum if it came from an odd offset
                     45:                 * since the computation is endian independant this
                     46:                 * works.
                     47:                 */
                     48:                new = (new << 8) | (new >> 8);
                     49:        }
                     50:        checksum = sum + new;
                     51:        if (checksum > 0xFFFF) {
                     52:                checksum -= 0xFFFF;
                     53:        }
                     54:        return (~checksum) & 0xFFFF;
                     55: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.