/* utils.c */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>

#include "snoop.h"


int hex2dec(char value) {
	if ((value >= '0') && (value <= '9'))
		return(value-'0');
	if ((toupper(value) >= 'A') && (toupper(value) <= 'F'))
		return(10 + toupper(value) - 'A');
	return(-1);
}


void clear_table() {
	int i;

	src_tbl = (char **)calloc(ADDR_TABLE_LEN,sizeof(char *));
	dst_tbl = (char **)calloc(ADDR_TABLE_LEN,sizeof(char *));
	for (i=0; i < ADDR_TABLE_LEN; i++) {
		src_tbl[i] = (char *)calloc(ETHER_ADDR_LEN,sizeof(char));
		dst_tbl[i] = (char *)calloc(ETHER_ADDR_LEN,sizeof(char));
	}

	return;
}


void build_buffers(PKTBUF far **head_buffer) {
	PKTBUF far *temp_buf;
	int i;

	*head_buffer = (PKTBUF far *)malloc(sizeof(PKTBUF));
	temp_buf = *head_buffer;
	temp_buf->pktsize_flag = 0;
	temp_buf->buffer = (char far *)malloc(ETHER_BUFSIZ*sizeof(char));
	temp_buf->next = (PKTBUF far *)malloc(sizeof(PKTBUF));

	for(i=0;i<N_BUFS-1;i++) {        			/* set up linked list of N_BUFS */
		temp_buf = temp_buf->next;
		temp_buf->pktsize_flag = 0;					/* buffers */
		temp_buf->buffer = (char far *)malloc(ETHER_BUFSIZ*sizeof(char));
		temp_buf->next = (PKTBUF far *)malloc(sizeof(PKTBUF));
	}

	// PROBLEM WITH THIS LINE: free(temp_buf->next);
	temp_buf->next = *head_buffer;					/* make linked list circular */

	return;
}

int get_drvrinfo(FILE *output, int pktdrvint, DRVR_INFO far *info) {
	int 			return_code=0;
	char far *ptr;

	return_code = drvrinfo(pktdrvint, info);

	if(return_code) {
			fprintf(output,"Packet driver functionality: basic %s%s\n",
				(info->drvr_functionality&EXTENDED)?("extended "):(""),
				(info->drvr_functionality&HIGH_PERF)?("high-performance "):(""));
			fprintf(output,"Packet driver version:       %u\n",info->drvr_version);
			fprintf(output,"Packet driver class:         %u\n",info->drvr_class);
			fprintf(output,"Packet driver number:        %u\n",info->drvr_number);
			fprintf(output,"Packet driver type:          %u\n",info->drvr_type);

			ptr = _fstrchr(info->drvr_name, '$');
			if(ptr)
				*ptr = '\0';

			fprintf(output,"Packet driver name:          %Fs\n",info->drvr_name);
	}

	return(return_code);
}


int access_type_all(int pktdrvint, DRVR_INFO far *info,
										ACCESS_TYPE far *access) {
	access->if_class  = info->drvr_class;
	access->if_type   = info->drvr_type;
	access->if_number = info->drvr_number;
	access->typelen   = 0;			/* if typelen=0, match all pkts */
	access->receiver_ptr  = receiver;
	return(acctype(pktdrvint, access));
}


void type_swap(ETHER_HEADER far *buf) {
	buf->type = (buf->type >> 8) + (buf->type << 8);
	return;
}


void display_stats(FILE *output) {
	fprintf(output,"\nStatistics:\tPackets reported                - %10lu\n",
					received_pkts);
	fprintf(output,  "           \tPackets lost                    - %10lu\n",
					discarded_pkts);
	fprintf(output,  "           \tPackets discarded due to filter - %10lu\n",
					filtered_out_pkts);
	fprintf(output,  "           \tPackets received                - %10lu\n",
					received_pkts+filtered_out_pkts);
	return;
}