1126261Smlaier/* $FreeBSD: releng/11.0/sys/netpfil/pf/in4_cksum.c 240494 2012-09-14 11:51:49Z glebius $ */ 2126258Smlaier/* $OpenBSD: in4_cksum.c,v 1.7 2003/06/02 23:28:13 millert Exp $ */ 3126258Smlaier/* $KAME: in4_cksum.c,v 1.10 2001/11/30 10:06:15 itojun Exp $ */ 4126258Smlaier/* $NetBSD: in_cksum.c,v 1.13 1996/10/13 02:03:03 christos Exp $ */ 5126258Smlaier 6126258Smlaier/* 7126258Smlaier * Copyright (C) 1999 WIDE Project. 8126258Smlaier * All rights reserved. 9126258Smlaier * 10126258Smlaier * Redistribution and use in source and binary forms, with or without 11126258Smlaier * modification, are permitted provided that the following conditions 12126258Smlaier * are met: 13126258Smlaier * 1. Redistributions of source code must retain the above copyright 14126258Smlaier * notice, this list of conditions and the following disclaimer. 15126258Smlaier * 2. Redistributions in binary form must reproduce the above copyright 16126258Smlaier * notice, this list of conditions and the following disclaimer in the 17126258Smlaier * documentation and/or other materials provided with the distribution. 18126258Smlaier * 3. Neither the name of the project nor the names of its contributors 19126258Smlaier * may be used to endorse or promote products derived from this software 20126258Smlaier * without specific prior written permission. 21126258Smlaier * 22126258Smlaier * THIS SOFTWARE IS PROVIDED BY THE PROJECT AND CONTRIBUTORS ``AS IS'' AND 23126258Smlaier * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 24126258Smlaier * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 25126258Smlaier * ARE DISCLAIMED. IN NO EVENT SHALL THE PROJECT OR CONTRIBUTORS BE LIABLE 26126258Smlaier * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 27126258Smlaier * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 28126258Smlaier * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 29126258Smlaier * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 30126258Smlaier * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 31126258Smlaier * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 32126258Smlaier * SUCH DAMAGE. 33126258Smlaier */ 34126258Smlaier 35126258Smlaier/* 36126258Smlaier * Copyright (c) 1988, 1992, 1993 37126258Smlaier * The Regents of the University of California. All rights reserved. 38126258Smlaier * 39126258Smlaier * Redistribution and use in source and binary forms, with or without 40126258Smlaier * modification, are permitted provided that the following conditions 41126258Smlaier * are met: 42126258Smlaier * 1. Redistributions of source code must retain the above copyright 43126258Smlaier * notice, this list of conditions and the following disclaimer. 44126258Smlaier * 2. Redistributions in binary form must reproduce the above copyright 45126258Smlaier * notice, this list of conditions and the following disclaimer in the 46126258Smlaier * documentation and/or other materials provided with the distribution. 47126258Smlaier * 3. Neither the name of the University nor the names of its contributors 48126258Smlaier * may be used to endorse or promote products derived from this software 49126258Smlaier * without specific prior written permission. 50126258Smlaier * 51126258Smlaier * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 52126258Smlaier * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 53126258Smlaier * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 54126258Smlaier * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 55126258Smlaier * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 56126258Smlaier * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 57126258Smlaier * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 58126258Smlaier * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 59126258Smlaier * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 60126258Smlaier * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 61126258Smlaier * SUCH DAMAGE. 62126258Smlaier * 63126258Smlaier * @(#)in_cksum.c 8.1 (Berkeley) 6/10/93 64126258Smlaier */ 65126258Smlaier 66126258Smlaier#include <sys/param.h> 67133181Smlaier#include <sys/systm.h> 68126258Smlaier#include <sys/mbuf.h> 69133181Smlaier 70126258Smlaier#include <netinet/in.h> 71126258Smlaier#include <netinet/in_systm.h> 72126258Smlaier#include <netinet/ip.h> 73126258Smlaier#include <netinet/ip_var.h> 74126258Smlaier 75133181Smlaier#include <machine/in_cksum.h> 76126258Smlaier 77126258Smlaier#define ADDCARRY(x) (x > 65535 ? x -= 65535 : x) 78213792Srpaulo#define REDUCE {l_util.l = sum; sum = l_util.s[0] + l_util.s[1]; (void)ADDCARRY(sum);} 79126258Smlaier 80133181Smlaierint in4_cksum(struct mbuf *, u_int8_t, int, int); 81126261Smlaier 82126261Smlaierint 83133181Smlaierin4_cksum(struct mbuf *m, u_int8_t nxt, int off, int len) 84126258Smlaier{ 85126258Smlaier union { 86126258Smlaier struct ipovly ipov; 87126258Smlaier u_int16_t w[10]; 88126258Smlaier } u; 89126258Smlaier union { 90126258Smlaier u_int16_t s[2]; 91126258Smlaier u_int32_t l; 92126258Smlaier } l_util; 93126258Smlaier 94133181Smlaier u_int16_t *w; 95133181Smlaier int psum; 96133181Smlaier int sum = 0; 97133181Smlaier 98126258Smlaier if (nxt != 0) { 99126258Smlaier /* pseudo header */ 100126258Smlaier if (off < sizeof(struct ipovly)) 101126258Smlaier panic("in4_cksum: offset too short"); 102126258Smlaier if (m->m_len < sizeof(struct ip)) 103126258Smlaier panic("in4_cksum: bad mbuf chain"); 104126258Smlaier bzero(&u.ipov, sizeof(u.ipov)); 105126258Smlaier u.ipov.ih_len = htons(len); 106126258Smlaier u.ipov.ih_pr = nxt; 107126258Smlaier u.ipov.ih_src = mtod(m, struct ip *)->ip_src; 108126258Smlaier u.ipov.ih_dst = mtod(m, struct ip *)->ip_dst; 109126258Smlaier w = u.w; 110126258Smlaier /* assumes sizeof(ipov) == 20 */ 111126258Smlaier sum += w[0]; sum += w[1]; sum += w[2]; sum += w[3]; sum += w[4]; 112126258Smlaier sum += w[5]; sum += w[6]; sum += w[7]; sum += w[8]; sum += w[9]; 113126258Smlaier } 114126258Smlaier 115133181Smlaier psum = in_cksum_skip(m, len + off, off); 116133181Smlaier psum = ~psum & 0xffff; 117133181Smlaier sum += psum; 118126258Smlaier REDUCE; 119126258Smlaier return (~sum & 0xffff); 120126258Smlaier} 121