13b9b51feSCy Schubert /*
23b9b51feSCy Schubert  * Simple netbios-dgm transparent proxy for in-kernel use.
33b9b51feSCy Schubert  * For use with the NAT code.
43b9b51feSCy Schubert  * $Id$
53b9b51feSCy Schubert  */
63b9b51feSCy Schubert 
73b9b51feSCy Schubert /*-
83b9b51feSCy Schubert  * Copyright (c) 2002-2003 Paul J. Ledbetter III
93b9b51feSCy Schubert  * All rights reserved.
103b9b51feSCy Schubert  *
113b9b51feSCy Schubert  * Redistribution and use in source and binary forms, with or without
123b9b51feSCy Schubert  * modification, are permitted provided that the following conditions
133b9b51feSCy Schubert  * are met:
143b9b51feSCy Schubert  * 1. Redistributions of source code must retain the above copyright
153b9b51feSCy Schubert  *    notice, this list of conditions and the following disclaimer.
163b9b51feSCy Schubert  * 2. Redistributions in binary form must reproduce the above copyright
173b9b51feSCy Schubert  *    notice, this list of conditions and the following disclaimer in the
183b9b51feSCy Schubert  *    documentation and/or other materials provided with the distribution.
193b9b51feSCy Schubert  *
203b9b51feSCy Schubert  * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
213b9b51feSCy Schubert  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
223b9b51feSCy Schubert  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
233b9b51feSCy Schubert  * ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
243b9b51feSCy Schubert  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
253b9b51feSCy Schubert  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
263b9b51feSCy Schubert  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
273b9b51feSCy Schubert  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
283b9b51feSCy Schubert  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
293b9b51feSCy Schubert  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
303b9b51feSCy Schubert  * SUCH DAMAGE.
313b9b51feSCy Schubert  *
323b9b51feSCy Schubert  * $Id$
333b9b51feSCy Schubert  */
343b9b51feSCy Schubert 
353b9b51feSCy Schubert #define	IPF_NETBIOS_PROXY
363b9b51feSCy Schubert 
373b9b51feSCy Schubert void ipf_p_netbios_main_load(void);
383b9b51feSCy Schubert void ipf_p_netbios_main_unload(void);
393b9b51feSCy Schubert int ipf_p_netbios_out(void *, fr_info_t *, ap_session_t *, nat_t *);
403b9b51feSCy Schubert 
413b9b51feSCy Schubert static	frentry_t	netbiosfr;
423b9b51feSCy Schubert 
433b9b51feSCy Schubert int	netbios_proxy_init = 0;
443b9b51feSCy Schubert 
453b9b51feSCy Schubert /*
463b9b51feSCy Schubert  * Initialize local structures.
473b9b51feSCy Schubert  */
483b9b51feSCy Schubert void
ipf_p_netbios_main_load(void)49064a5a95SCy Schubert ipf_p_netbios_main_load(void)
503b9b51feSCy Schubert {
513b9b51feSCy Schubert 	bzero((char *)&netbiosfr, sizeof(netbiosfr));
523b9b51feSCy Schubert 	netbiosfr.fr_ref = 1;
533b9b51feSCy Schubert 	netbiosfr.fr_flags = FR_INQUE|FR_PASS|FR_QUICK|FR_KEEPSTATE;
543b9b51feSCy Schubert 	MUTEX_INIT(&netbiosfr.fr_lock, "NETBIOS proxy rule lock");
553b9b51feSCy Schubert 	netbios_proxy_init = 1;
563b9b51feSCy Schubert }
573b9b51feSCy Schubert 
583b9b51feSCy Schubert 
593b9b51feSCy Schubert void
ipf_p_netbios_main_unload(void)60064a5a95SCy Schubert ipf_p_netbios_main_unload(void)
613b9b51feSCy Schubert {
623b9b51feSCy Schubert 	if (netbios_proxy_init == 1) {
633b9b51feSCy Schubert 		MUTEX_DESTROY(&netbiosfr.fr_lock);
643b9b51feSCy Schubert 		netbios_proxy_init = 0;
653b9b51feSCy Schubert 	}
663b9b51feSCy Schubert }
673b9b51feSCy Schubert 
683b9b51feSCy Schubert 
693b9b51feSCy Schubert int
ipf_p_netbios_out(void * arg,fr_info_t * fin,ap_session_t * aps,nat_t * nat)70064a5a95SCy Schubert ipf_p_netbios_out(void *arg, fr_info_t *fin, ap_session_t *aps, nat_t *nat)
713b9b51feSCy Schubert {
723b9b51feSCy Schubert 	char dgmbuf[6];
733b9b51feSCy Schubert 	int off, dlen;
743b9b51feSCy Schubert 	udphdr_t *udp;
753b9b51feSCy Schubert 	ip_t *ip;
763b9b51feSCy Schubert 	mb_t *m;
773b9b51feSCy Schubert 
783b9b51feSCy Schubert 	aps = aps;	/* LINT */
793b9b51feSCy Schubert 	nat = nat;	/* LINT */
803b9b51feSCy Schubert 
813b9b51feSCy Schubert 	m = fin->fin_m;
823b9b51feSCy Schubert 	dlen = fin->fin_dlen - sizeof(*udp);
833b9b51feSCy Schubert 	/*
843b9b51feSCy Schubert 	 * no net bios datagram could possibly be shorter than this
853b9b51feSCy Schubert 	 */
863b9b51feSCy Schubert 	if (dlen < 11)
878c82b374SCy Schubert 		return (0);
883b9b51feSCy Schubert 
893b9b51feSCy Schubert 	ip = fin->fin_ip;
903b9b51feSCy Schubert 	udp = (udphdr_t *)fin->fin_dp;
913b9b51feSCy Schubert 	off = (char *)udp - (char *)ip + sizeof(*udp) + fin->fin_ipoff;
923b9b51feSCy Schubert 
933b9b51feSCy Schubert 	/*
943b9b51feSCy Schubert 	 * move past the
953b9b51feSCy Schubert 	 *	ip header;
963b9b51feSCy Schubert 	 *	udp header;
973b9b51feSCy Schubert 	 *	4 bytes into the net bios dgm header.
983b9b51feSCy Schubert 	 *  According to rfc1002, this should be the exact location of
993b9b51feSCy Schubert 	 *  the source address/port
1003b9b51feSCy Schubert 	 */
1013b9b51feSCy Schubert 	off += 4;
1023b9b51feSCy Schubert 
1033b9b51feSCy Schubert 	/* Copy NATed source Address/port*/
1043b9b51feSCy Schubert 	dgmbuf[0] = (char)((ip->ip_src.s_addr     ) &0xFF);
1053b9b51feSCy Schubert 	dgmbuf[1] = (char)((ip->ip_src.s_addr >> 8) &0xFF);
1063b9b51feSCy Schubert 	dgmbuf[2] = (char)((ip->ip_src.s_addr >> 16)&0xFF);
1073b9b51feSCy Schubert 	dgmbuf[3] = (char)((ip->ip_src.s_addr >> 24)&0xFF);
1083b9b51feSCy Schubert 
1093b9b51feSCy Schubert 	dgmbuf[4] = (char)((udp->uh_sport     )&0xFF);
1103b9b51feSCy Schubert 	dgmbuf[5] = (char)((udp->uh_sport >> 8)&0xFF);
1113b9b51feSCy Schubert 
1123b9b51feSCy Schubert 	/* replace data in packet */
1133b9b51feSCy Schubert 	COPYBACK(m, off, sizeof(dgmbuf), dgmbuf);
1143b9b51feSCy Schubert 
1158c82b374SCy Schubert 	return (0);
1163b9b51feSCy Schubert }
117