aboutsummaryrefslogtreecommitdiff
path: root/lib/libalias/alias_nbt.c
diff options
context:
space:
mode:
Diffstat (limited to 'lib/libalias/alias_nbt.c')
-rw-r--r--lib/libalias/alias_nbt.c722
1 files changed, 0 insertions, 722 deletions
diff --git a/lib/libalias/alias_nbt.c b/lib/libalias/alias_nbt.c
deleted file mode 100644
index b51abd1c5da5..000000000000
--- a/lib/libalias/alias_nbt.c
+++ /dev/null
@@ -1,722 +0,0 @@
-/*-
- * Written by Atsushi Murai <amurai@spec.co.jp>
- * Copyright (c) 1998, System Planning and Engineering Co.
- * All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
- * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
- * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
- * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
- * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
- * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
- * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
- * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
- * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
- * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
- * SUCH DAMAGE.
- * TODO:
- * oClean up.
- * oConsidering for word alignment for other platform.
- */
-
-#include <sys/cdefs.h>
-__FBSDID("$FreeBSD$");
-
-/*
- alias_nbt.c performs special processing for NetBios over TCP/IP
- sessions by UDP.
-
- Initial version: May, 1998 (Atsushi Murai <amurai@spec.co.jp>)
-
- See HISTORY file for record of revisions.
-*/
-
-/* Includes */
-#include <ctype.h>
-#include <stdio.h>
-#include <string.h>
-#include <sys/types.h>
-#include <netinet/in_systm.h>
-#include <netinet/in.h>
-#include <arpa/inet.h>
-#include <netinet/ip.h>
-#include <netinet/udp.h>
-#include <netinet/tcp.h>
-
-#include "alias_local.h"
-
-typedef struct {
- struct in_addr oldaddr;
- u_short oldport;
- struct in_addr newaddr;
- u_short newport;
- u_short *uh_sum;
-} NBTArguments;
-
-typedef struct {
- unsigned char type;
- unsigned char flags;
- u_short id;
- struct in_addr source_ip;
- u_short source_port;
- u_short len;
- u_short offset;
-} NbtDataHeader;
-
-#define OpQuery 0
-#define OpUnknown 4
-#define OpRegist 5
-#define OpRelease 6
-#define OpWACK 7
-#define OpRefresh 8
-typedef struct {
- u_short nametrid;
- u_short dir: 1, opcode:4, nmflags:7, rcode:4;
- u_short qdcount;
- u_short ancount;
- u_short nscount;
- u_short arcount;
-} NbtNSHeader;
-
-#define FMT_ERR 0x1
-#define SRV_ERR 0x2
-#define IMP_ERR 0x4
-#define RFS_ERR 0x5
-#define ACT_ERR 0x6
-#define CFT_ERR 0x7
-
-
-#ifdef DEBUG
-static void
-PrintRcode(u_char rcode)
-{
-
- switch (rcode) {
- case FMT_ERR:
- printf("\nFormat Error.");
- case SRV_ERR:
- printf("\nSever failure.");
- case IMP_ERR:
- printf("\nUnsupported request error.\n");
- case RFS_ERR:
- printf("\nRefused error.\n");
- case ACT_ERR:
- printf("\nActive error.\n");
- case CFT_ERR:
- printf("\nName in conflict error.\n");
- default:
- printf("\n?%c?=%0x\n", '?', rcode);
-
- }
-}
-
-#endif
-
-
-/* Handling Name field */
-static u_char *
-AliasHandleName(u_char * p, char *pmax)
-{
-
- u_char *s;
- u_char c;
- int compress;
-
- /* Following length field */
-
- if (p == NULL || (char *)p >= pmax)
- return (NULL);
-
- if (*p & 0xc0) {
- p = p + 2;
- if ((char *)p > pmax)
- return (NULL);
- return ((u_char *) p);
- }
- while ((*p & 0x3f) != 0x00) {
- s = p + 1;
- if (*p == 0x20)
- compress = 1;
- else
- compress = 0;
-
- /* Get next length field */
- p = (u_char *) (p + (*p & 0x3f) + 1);
- if ((char *)p > pmax) {
- p = NULL;
- break;
- }
-#ifdef DEBUG
- printf(":");
-#endif
- while (s < p) {
- if (compress == 1) {
- c = (u_char) (((((*s & 0x0f) << 4) | (*(s + 1) & 0x0f)) - 0x11));
-#ifdef DEBUG
- if (isprint(c))
- printf("%c", c);
- else
- printf("<0x%02x>", c);
-#endif
- s += 2;
- } else {
-#ifdef DEBUG
- printf("%c", *s);
-#endif
- s++;
- }
- }
-#ifdef DEBUG
- printf(":");
-#endif
- fflush(stdout);
- }
-
- /* Set up to out of Name field */
- if (p == NULL || (char *)p >= pmax)
- p = NULL;
- else
- p++;
- return ((u_char *) p);
-}
-
-/*
- * NetBios Datagram Handler (IP/UDP)
- */
-#define DGM_DIRECT_UNIQ 0x10
-#define DGM_DIRECT_GROUP 0x11
-#define DGM_BROADCAST 0x12
-#define DGM_ERROR 0x13
-#define DGM_QUERY 0x14
-#define DGM_POSITIVE_RES 0x15
-#define DGM_NEGATIVE_RES 0x16
-
-int
-AliasHandleUdpNbt(
- struct libalias *la,
- struct ip *pip, /* IP packet to examine/patch */
- struct alias_link *lnk,
- struct in_addr *alias_address,
- u_short alias_port
-)
-{
- struct udphdr *uh;
- NbtDataHeader *ndh;
- u_char *p = NULL;
- char *pmax;
-
- (void)la;
- (void)lnk;
-
- /* Calculate data length of UDP packet */
- uh = (struct udphdr *)ip_next(pip);
- pmax = (char *)uh + ntohs(uh->uh_ulen);
-
- ndh = (NbtDataHeader *)udp_next(uh);
- if ((char *)(ndh + 1) > pmax)
- return (-1);
-#ifdef DEBUG
- printf("\nType=%02x,", ndh->type);
-#endif
- switch (ndh->type) {
- case DGM_DIRECT_UNIQ:
- case DGM_DIRECT_GROUP:
- case DGM_BROADCAST:
- p = (u_char *) ndh + 14;
- p = AliasHandleName(p, pmax); /* Source Name */
- p = AliasHandleName(p, pmax); /* Destination Name */
- break;
- case DGM_ERROR:
- p = (u_char *) ndh + 11;
- break;
- case DGM_QUERY:
- case DGM_POSITIVE_RES:
- case DGM_NEGATIVE_RES:
- p = (u_char *) ndh + 10;
- p = AliasHandleName(p, pmax); /* Destination Name */
- break;
- }
- if (p == NULL || (char *)p > pmax)
- p = NULL;
-#ifdef DEBUG
- printf("%s:%d-->", inet_ntoa(ndh->source_ip), ntohs(ndh->source_port));
-#endif
- /* Doing an IP address and Port number Translation */
- if (uh->uh_sum != 0) {
- int acc;
- u_short *sptr;
-
- acc = ndh->source_port;
- acc -= alias_port;
- sptr = (u_short *) & (ndh->source_ip);
- acc += *sptr++;
- acc += *sptr;
- sptr = (u_short *) alias_address;
- acc -= *sptr++;
- acc -= *sptr;
- ADJUST_CHECKSUM(acc, uh->uh_sum);
- }
- ndh->source_ip = *alias_address;
- ndh->source_port = alias_port;
-#ifdef DEBUG
- printf("%s:%d\n", inet_ntoa(ndh->source_ip), ntohs(ndh->source_port));
- fflush(stdout);
-#endif
- return ((p == NULL) ? -1 : 0);
-}
-
-/* Question Section */
-#define QS_TYPE_NB 0x0020
-#define QS_TYPE_NBSTAT 0x0021
-#define QS_CLAS_IN 0x0001
-typedef struct {
- u_short type; /* The type of Request */
- u_short class; /* The class of Request */
-} NBTNsQuestion;
-
-static u_char *
-AliasHandleQuestion(
- u_short count,
- NBTNsQuestion * q,
- char *pmax,
- NBTArguments * nbtarg)
-{
-
- (void)nbtarg;
-
- while (count != 0) {
- /* Name Filed */
- q = (NBTNsQuestion *) AliasHandleName((u_char *) q, pmax);
-
- if (q == NULL || (char *)(q + 1) > pmax) {
- q = NULL;
- break;
- }
- /* Type and Class filed */
- switch (ntohs(q->type)) {
- case QS_TYPE_NB:
- case QS_TYPE_NBSTAT:
- q = q + 1;
- break;
- default:
-#ifdef DEBUG
- printf("\nUnknown Type on Question %0x\n", ntohs(q->type));
-#endif
- break;
- }
- count--;
- }
-
- /* Set up to out of Question Section */
- return ((u_char *) q);
-}
-
-/* Resource Record */
-#define RR_TYPE_A 0x0001
-#define RR_TYPE_NS 0x0002
-#define RR_TYPE_NULL 0x000a
-#define RR_TYPE_NB 0x0020
-#define RR_TYPE_NBSTAT 0x0021
-#define RR_CLAS_IN 0x0001
-#define SizeOfNsResource 8
-typedef struct {
- u_short type;
- u_short class;
- unsigned int ttl;
- u_short rdlen;
-} NBTNsResource;
-
-#define SizeOfNsRNB 6
-typedef struct {
- u_short g: 1 , ont:2, resv:13;
- struct in_addr addr;
-} NBTNsRNB;
-
-static u_char *
-AliasHandleResourceNB(
- NBTNsResource * q,
- char *pmax,
- NBTArguments * nbtarg)
-{
- NBTNsRNB *nb;
- u_short bcount;
-
- if (q == NULL || (char *)(q + 1) > pmax)
- return (NULL);
- /* Check out a length */
- bcount = ntohs(q->rdlen);
-
- /* Forward to Resource NB position */
- nb = (NBTNsRNB *) ((u_char *) q + SizeOfNsResource);
-
- /* Processing all in_addr array */
-#ifdef DEBUG
- printf("NB rec[%s", inet_ntoa(nbtarg->oldaddr));
- printf("->%s, %dbytes] ", inet_ntoa(nbtarg->newaddr), bcount);
-#endif
- while (nb != NULL && bcount != 0) {
- if ((char *)(nb + 1) > pmax) {
- nb = NULL;
- break;
- }
-#ifdef DEBUG
- printf("<%s>", inet_ntoa(nb->addr));
-#endif
- if (!bcmp(&nbtarg->oldaddr, &nb->addr, sizeof(struct in_addr))) {
- if (*nbtarg->uh_sum != 0) {
- int acc;
- u_short *sptr;
-
- sptr = (u_short *) & (nb->addr);
- acc = *sptr++;
- acc += *sptr;
- sptr = (u_short *) & (nbtarg->newaddr);
- acc -= *sptr++;
- acc -= *sptr;
- ADJUST_CHECKSUM(acc, *nbtarg->uh_sum);
- }
- nb->addr = nbtarg->newaddr;
-#ifdef DEBUG
- printf("O");
-#endif
- }
-#ifdef DEBUG
- else {
- printf(".");
- }
-#endif
- nb = (NBTNsRNB *) ((u_char *) nb + SizeOfNsRNB);
- bcount -= SizeOfNsRNB;
- }
- if (nb == NULL || (char *)(nb + 1) > pmax) {
- nb = NULL;
- }
- return ((u_char *) nb);
-}
-
-#define SizeOfResourceA 6
-typedef struct {
- struct in_addr addr;
-} NBTNsResourceA;
-
-static u_char *
-AliasHandleResourceA(
- NBTNsResource * q,
- char *pmax,
- NBTArguments * nbtarg)
-{
- NBTNsResourceA *a;
- u_short bcount;
-
- if (q == NULL || (char *)(q + 1) > pmax)
- return (NULL);
-
- /* Forward to Resource A position */
- a = (NBTNsResourceA *) ((u_char *) q + sizeof(NBTNsResource));
-
- /* Check out of length */
- bcount = ntohs(q->rdlen);
-
- /* Processing all in_addr array */
-#ifdef DEBUG
- printf("Arec [%s", inet_ntoa(nbtarg->oldaddr));
- printf("->%s]", inet_ntoa(nbtarg->newaddr));
-#endif
- while (bcount != 0) {
- if (a == NULL || (char *)(a + 1) > pmax)
- return (NULL);
-#ifdef DEBUG
- printf("..%s", inet_ntoa(a->addr));
-#endif
- if (!bcmp(&nbtarg->oldaddr, &a->addr, sizeof(struct in_addr))) {
- if (*nbtarg->uh_sum != 0) {
- int acc;
- u_short *sptr;
-
- sptr = (u_short *) & (a->addr); /* Old */
- acc = *sptr++;
- acc += *sptr;
- sptr = (u_short *) & nbtarg->newaddr; /* New */
- acc -= *sptr++;
- acc -= *sptr;
- ADJUST_CHECKSUM(acc, *nbtarg->uh_sum);
- }
- a->addr = nbtarg->newaddr;
- }
- a++; /* XXXX */
- bcount -= SizeOfResourceA;
- }
- if (a == NULL || (char *)(a + 1) > pmax)
- a = NULL;
- return ((u_char *) a);
-}
-
-typedef struct {
- u_short opcode:4, flags:8, resv:4;
-} NBTNsResourceNULL;
-
-static u_char *
-AliasHandleResourceNULL(
- NBTNsResource * q,
- char *pmax,
- NBTArguments * nbtarg)
-{
- NBTNsResourceNULL *n;
- u_short bcount;
-
- (void)nbtarg;
-
- if (q == NULL || (char *)(q + 1) > pmax)
- return (NULL);
-
- /* Forward to Resource NULL position */
- n = (NBTNsResourceNULL *) ((u_char *) q + sizeof(NBTNsResource));
-
- /* Check out of length */
- bcount = ntohs(q->rdlen);
-
- /* Processing all in_addr array */
- while (bcount != 0) {
- if ((char *)(n + 1) > pmax) {
- n = NULL;
- break;
- }
- n++;
- bcount -= sizeof(NBTNsResourceNULL);
- }
- if ((char *)(n + 1) > pmax)
- n = NULL;
-
- return ((u_char *) n);
-}
-
-static u_char *
-AliasHandleResourceNS(
- NBTNsResource * q,
- char *pmax,
- NBTArguments * nbtarg)
-{
- NBTNsResourceNULL *n;
- u_short bcount;
-
- (void)nbtarg;
-
- if (q == NULL || (char *)(q + 1) > pmax)
- return (NULL);
-
- /* Forward to Resource NULL position */
- n = (NBTNsResourceNULL *) ((u_char *) q + sizeof(NBTNsResource));
-
- /* Check out of length */
- bcount = ntohs(q->rdlen);
-
- /* Resource Record Name Filed */
- q = (NBTNsResource *) AliasHandleName((u_char *) n, pmax); /* XXX */
-
- if (q == NULL || (char *)((u_char *) n + bcount) > pmax)
- return (NULL);
- else
- return ((u_char *) n + bcount);
-}
-
-typedef struct {
- u_short numnames;
-} NBTNsResourceNBSTAT;
-
-static u_char *
-AliasHandleResourceNBSTAT(
- NBTNsResource * q,
- char *pmax,
- NBTArguments * nbtarg)
-{
- NBTNsResourceNBSTAT *n;
- u_short bcount;
-
- (void)nbtarg;
-
- if (q == NULL || (char *)(q + 1) > pmax)
- return (NULL);
-
- /* Forward to Resource NBSTAT position */
- n = (NBTNsResourceNBSTAT *) ((u_char *) q + sizeof(NBTNsResource));
-
- /* Check out of length */
- bcount = ntohs(q->rdlen);
-
- if (q == NULL || (char *)((u_char *) n + bcount) > pmax)
- return (NULL);
- else
- return ((u_char *) n + bcount);
-}
-
-static u_char *
-AliasHandleResource(
- u_short count,
- NBTNsResource * q,
- char *pmax,
- NBTArguments
- * nbtarg)
-{
- while (count != 0) {
- /* Resource Record Name Filed */
- q = (NBTNsResource *) AliasHandleName((u_char *) q, pmax);
-
- if (q == NULL || (char *)(q + 1) > pmax)
- break;
-#ifdef DEBUG
- printf("type=%02x, count=%d\n", ntohs(q->type), count);
-#endif
-
- /* Type and Class filed */
- switch (ntohs(q->type)) {
- case RR_TYPE_NB:
- q = (NBTNsResource *) AliasHandleResourceNB(
- q,
- pmax,
- nbtarg
- );
- break;
- case RR_TYPE_A:
- q = (NBTNsResource *) AliasHandleResourceA(
- q,
- pmax,
- nbtarg
- );
- break;
- case RR_TYPE_NS:
- q = (NBTNsResource *) AliasHandleResourceNS(
- q,
- pmax,
- nbtarg
- );
- break;
- case RR_TYPE_NULL:
- q = (NBTNsResource *) AliasHandleResourceNULL(
- q,
- pmax,
- nbtarg
- );
- break;
- case RR_TYPE_NBSTAT:
- q = (NBTNsResource *) AliasHandleResourceNBSTAT(
- q,
- pmax,
- nbtarg
- );
- break;
- default:
-#ifdef DEBUG
- printf(
- "\nUnknown Type of Resource %0x\n",
- ntohs(q->type)
- );
-#endif
- break;
- }
- count--;
- }
- fflush(stdout);
- return ((u_char *) q);
-}
-
-int
-AliasHandleUdpNbtNS(
- struct libalias *la,
- struct ip *pip, /* IP packet to examine/patch */
- struct alias_link *lnk,
- struct in_addr *alias_address,
- u_short * alias_port,
- struct in_addr *original_address,
- u_short * original_port)
-{
- struct udphdr *uh;
- NbtNSHeader *nsh;
- u_char *p;
- char *pmax;
- NBTArguments nbtarg;
-
- (void)la;
- (void)lnk;
-
- /* Set up Common Parameter */
- nbtarg.oldaddr = *alias_address;
- nbtarg.oldport = *alias_port;
- nbtarg.newaddr = *original_address;
- nbtarg.newport = *original_port;
-
- /* Calculate data length of UDP packet */
- uh = (struct udphdr *)ip_next(pip);
- nbtarg.uh_sum = &(uh->uh_sum);
- nsh = (NbtNSHeader *)udp_next(uh);
- p = (u_char *) (nsh + 1);
- pmax = (char *)uh + ntohs(uh->uh_ulen);
-
- if ((char *)(nsh + 1) > pmax)
- return (-1);
-
-#ifdef DEBUG
- printf(" [%s] ID=%02x, op=%01x, flag=%02x, rcode=%01x, qd=%04x"
- ", an=%04x, ns=%04x, ar=%04x, [%d]-->",
- nsh->dir ? "Response" : "Request",
- nsh->nametrid,
- nsh->opcode,
- nsh->nmflags,
- nsh->rcode,
- ntohs(nsh->qdcount),
- ntohs(nsh->ancount),
- ntohs(nsh->nscount),
- ntohs(nsh->arcount),
- (u_char *) p - (u_char *) nsh
- );
-#endif
-
- /* Question Entries */
- if (ntohs(nsh->qdcount) != 0) {
- p = AliasHandleQuestion(
- ntohs(nsh->qdcount),
- (NBTNsQuestion *) p,
- pmax,
- &nbtarg
- );
- }
- /* Answer Resource Records */
- if (ntohs(nsh->ancount) != 0) {
- p = AliasHandleResource(
- ntohs(nsh->ancount),
- (NBTNsResource *) p,
- pmax,
- &nbtarg
- );
- }
- /* Authority Resource Recodrs */
- if (ntohs(nsh->nscount) != 0) {
- p = AliasHandleResource(
- ntohs(nsh->nscount),
- (NBTNsResource *) p,
- pmax,
- &nbtarg
- );
- }
- /* Additional Resource Recodrs */
- if (ntohs(nsh->arcount) != 0) {
- p = AliasHandleResource(
- ntohs(nsh->arcount),
- (NBTNsResource *) p,
- pmax,
- &nbtarg
- );
- }
-#ifdef DEBUG
- PrintRcode(nsh->rcode);
-#endif
- return ((p == NULL) ? -1 : 0);
-}