/******************************************************************************
 *
 * Name:    skproc.c
 * Project:	GEnesis, PCI Gigabit Ethernet Adapter
 * Version:	$Revision: 1.4 $
 * Date:    $Date: 2003/02/25 14:16:37 $
 * Purpose:	Funktions to display statictic data
 *
 ******************************************************************************/

/******************************************************************************
 *
 *	(C)Copyright 1998-2003 SysKonnect GmbH.
 *
 *	This program is free software; you can redistribute it and/or modify
 *	it under the terms of the GNU General Public License as published by
 *	the Free Software Foundation; either version 2 of the License, or
 *	(at your option) any later version.
 *
 *	Created 22-Nov-2000
 *	Author: Mirko Lindner (mlindner@syskonnect.de)
 *
 *	The information in this file is provided "AS IS" without warranty.
 *
 ******************************************************************************/
/******************************************************************************
 *
 * History:
 *
 *	$Log: skproc.c,v $
 *	Revision 1.4  2003/02/25 14:16:37  mlindner
 *	Fix: Copyright statement
 *
 *	Revision 1.3  2002/10/02 12:59:51  mlindner
 *	Add: Support for Yukon
 *	Add: Speed check and setup
 *	Add: Merge source for kernel 2.2.x and 2.4.x
 *	Add: Read sensor names directly from VPD
 *	Fix: Volt values
 *
 *	Revision 1.2.2.7  2002/01/14 12:45:15  mlindner
 *	Fix: Editorial changes
 *
 *	Revision 1.2.2.6  2001/12/06 15:26:07  mlindner
 *	Fix: Return value of proc_read
 *
 *	Revision 1.2.2.5  2001/12/06 09:57:39  mlindner
 *	New ProcFs entries
 *
 *	Revision 1.2.2.4  2001/09/05 12:16:02  mlindner
 *	Add: New ProcFs entries
 *	Fix: Counter Errors (Jumbo == to long errors)
 *	Fix: Kernel error compilation
 *	Fix: too short counters
 *
 *	Revision 1.2.2.3  2001/06/25 07:26:26  mlindner
 *	Add: More error messages
 *
 *	Revision 1.2.2.2  2001/03/15 12:50:13  mlindner
 *	fix: ProcFS owner protection
 *
 *	Revision 1.2.2.1  2001/03/12 16:43:48  mlindner
 *	chg: 2.4 requirements for procfs
 *
 *	Revision 1.1  2001/01/22 14:15:31  mlindner
 *	added ProcFs functionality
 *	Dual Net functionality integrated
 *	Rlmt networks added
 *
 *
 ******************************************************************************/

#include <config.h>

#include <linux/proc_fs.h>

#include "h/skdrv1st.h"
#include "h/skdrv2nd.h"
#define ZEROPAD		1		/* pad with zero */
#define SIGN		2		/* unsigned/signed long */
#define PLUS		4		/* show plus */
#define SPACE		8		/* space if plus */
#define LEFT		16		/* left justified */
#define SPECIALX	32		/* 0x */
#define LARGE		64

extern SK_AC *pACList;
extern struct net_device *SkGeRootDev;

extern char *SkNumber (char *str,
		       long long num,
		       int base,
		       int size,
		       int precision,
		       int type);


/*****************************************************************************
 *
 *	proc_read - print "summaries" entry
 *
 * Description:
 *  This function fills the proc entry with statistic data about
 *  the ethernet device.
 *
 *
 * Returns: buffer with statistic data
 *
 */
int proc_read(char *buffer,
char **buffer_location,
off_t offset,
int buffer_length,
int *eof,
void *data)
{
	int len = 0;
	int t;
	int i;
	DEV_NET			*pNet;
	SK_AC			*pAC;
	char			test_buf[100];
	char			sens_msg[50];
	unsigned long		Flags;
	unsigned int		Size;
	struct SK_NET_DEVICE	*next;
	struct SK_NET_DEVICE	*SkgeProcDev = SkGeRootDev;

	SK_PNMI_STRUCT_DATA	*pPnmiStruct;
	SK_PNMI_STAT		*pPnmiStat;
	struct proc_dir_entry *file = (struct proc_dir_entry*) data;

	while (SkgeProcDev) {
		pNet = (DEV_NET*) SkgeProcDev->priv;
		pAC = pNet->pAC;
		next = pAC->Next;
		pPnmiStruct = &pAC->PnmiStruct;
		/* NetIndex in GetStruct is now required, zero is only dummy */

		for (t=pAC->GIni.GIMacsFound; t > 0; t--) {
			if ((pAC->GIni.GIMacsFound == 2) && pAC->RlmtNets == 1)
				t--;

			spin_lock_irqsave(&pAC->SlowPathLock, Flags);
			Size = SK_PNMI_STRUCT_SIZE;
			SkPnmiGetStruct(pAC, pAC->IoBase,
				pPnmiStruct, &Size, t-1);
			spin_unlock_irqrestore(&pAC->SlowPathLock, Flags);

			if (strcmp(pAC->dev[t-1]->name, file->name) == 0) {
				pPnmiStat = &pPnmiStruct->Stat[0];
				len = sprintf(buffer,
					"\nDetailed statistic for device %s\n",
					pAC->dev[t-1]->name);
				len += sprintf(buffer + len,
					"=======================================\n");

				/* Board statistics */
				len += sprintf(buffer + len,
					"\nBoard statistics\n\n");
				len += sprintf(buffer + len,
					"Active Port                    %c\n",
					'A' + pAC->Rlmt.Net[t-1].Port[pAC->Rlmt.
					Net[t-1].PrefPort]->PortNumber);
				len += sprintf(buffer + len,
					"Preferred Port                 %c\n",
					'A' + pAC->Rlmt.Net[t-1].Port[pAC->Rlmt.
					Net[t-1].PrefPort]->PortNumber);

				len += sprintf(buffer + len,
					"Bus speed (MHz)                %d\n",
					pPnmiStruct->BusSpeed);

				len += sprintf(buffer + len,
					"Bus width (Bit)                %d\n",
					pPnmiStruct->BusWidth);
				len += sprintf(buffer + len,
					"Hardware revision              v%d.%d\n",
					(pAC->GIni.GIPciHwRev >> 4) & 0x0F,
					pAC->GIni.GIPciHwRev & 0x0F);

				/* Print sensor informations */
				for (i=0; i < pAC->I2c.MaxSens; i ++) {
					/* Check type */
					switch (pAC->I2c.SenTable[i].SenType) {
					case 1:
						strcpy(sens_msg, pAC->I2c.SenTable[i].SenDesc);
						strcat(sens_msg, " (C)");
						len += sprintf(buffer + len,
							"%-25s      %d.%02d\n",
							sens_msg,
							pAC->I2c.SenTable[i].SenValue / 10,
							pAC->I2c.SenTable[i].SenValue % 10);

						strcpy(sens_msg, pAC->I2c.SenTable[i].SenDesc);
						strcat(sens_msg, " (F)");
						len += sprintf(buffer + len,
							"%-25s      %d.%02d\n",
							sens_msg,
							((((pAC->I2c.SenTable[i].SenValue)
							*10)*9)/5 + 3200)/100,
							((((pAC->I2c.SenTable[i].SenValue)
							*10)*9)/5 + 3200) % 10);
						break;
					case 2:
						strcpy(sens_msg, pAC->I2c.SenTable[i].SenDesc);
						strcat(sens_msg, " (V)");
						len += sprintf(buffer + len,
							"%-25s      %d.%03d\n",
							sens_msg,
							pAC->I2c.SenTable[i].SenValue / 1000,
							pAC->I2c.SenTable[i].SenValue % 1000);
						break;
					case 3:
						strcpy(sens_msg, pAC->I2c.SenTable[i].SenDesc);
						strcat(sens_msg, " (rpm)");
						len += sprintf(buffer + len,
							"%-25s      %d\n",
							sens_msg,
							pAC->I2c.SenTable[i].SenValue);
						break;
					default:
						break;
					}
				}

				/*Receive statistics */
				len += sprintf(buffer + len,
				"\nReceive statistics\n\n");

				len += sprintf(buffer + len,
					"Received bytes                 %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxOctetsOkCts,
					10,0,-1,0));
				len += sprintf(buffer + len,
					"Received packets               %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxOkCts,
					10,0,-1,0));
#if 0
				if (pAC->GIni.GP[0].PhyType == SK_PHY_XMAC &&
					pAC->HWRevision < 12) {
					pPnmiStruct->InErrorsCts = pPnmiStruct->InErrorsCts -
						pPnmiStat->StatRxShortsCts;
					pPnmiStat->StatRxShortsCts = 0;
				}
#endif
				if (pNet->Mtu > 1500)
					pPnmiStruct->InErrorsCts = pPnmiStruct->InErrorsCts -
						pPnmiStat->StatRxTooLongCts;

				len += sprintf(buffer + len,
					"Receive errors                 %s\n",
					SkNumber(test_buf, pPnmiStruct->InErrorsCts,
					10,0,-1,0));
				len += sprintf(buffer + len,
					"Receive drops                  %s\n",
					SkNumber(test_buf, pPnmiStruct->RxNoBufCts,
					10,0,-1,0));
				len += sprintf(buffer + len,
					"Received multicast             %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxMulticastOkCts,
					10,0,-1,0));
				len += sprintf(buffer + len,
					"Receive error types\n");
				len += sprintf(buffer + len,
					"   length                      %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxRuntCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   buffer overflow             %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxFifoOverflowCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   bad crc                     %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxFcsCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   framing                     %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxFramingCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   missed frames               %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxMissedCts,
					10, 0, -1, 0));

				if (pNet->Mtu > 1500)
					pPnmiStat->StatRxTooLongCts = 0;

				len += sprintf(buffer + len,
					"   too long                    %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxTooLongCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   carrier extension           %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxCextCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   too short                   %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxShortsCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   symbol                      %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxSymbolCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   LLC MAC size                %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxIRLengthCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   carrier event               %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxCarrierCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   jabber                      %s\n",
					SkNumber(test_buf, pPnmiStat->StatRxJabberCts,
					10, 0, -1, 0));


				/*Transmit statistics */
				len += sprintf(buffer + len,
				"\nTransmit statistics\n\n");

				len += sprintf(buffer + len,
					"Transmited bytes               %s\n",
					SkNumber(test_buf, pPnmiStat->StatTxOctetsOkCts,
					10,0,-1,0));
				len += sprintf(buffer + len,
					"Transmited packets             %s\n",
					SkNumber(test_buf, pPnmiStat->StatTxOkCts,
					10,0,-1,0));
				len += sprintf(buffer + len,
					"Transmit errors                %s\n",
					SkNumber(test_buf, pPnmiStat->StatTxSingleCollisionCts,
					10,0,-1,0));
				len += sprintf(buffer + len,
					"Transmit dropped               %s\n",
					SkNumber(test_buf, pPnmiStruct->TxNoBufCts,
					10,0,-1,0));
				len += sprintf(buffer + len,
					"Transmit collisions            %s\n",
					SkNumber(test_buf, pPnmiStat->StatTxSingleCollisionCts,
					10,0,-1,0));
				len += sprintf(buffer + len,
					"Transmit errors types\n");
				len += sprintf(buffer + len,
					"   excessive collision         %ld\n",
					pAC->stats.tx_aborted_errors);
				len += sprintf(buffer + len,
					"   carrier                     %s\n",
					SkNumber(test_buf, pPnmiStat->StatTxCarrierCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   fifo underrun               %s\n",
					SkNumber(test_buf, pPnmiStat->StatTxFifoUnderrunCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   heartbeat                   %s\n",
					SkNumber(test_buf, pPnmiStat->StatTxCarrierCts,
					10, 0, -1, 0));
				len += sprintf(buffer + len,
					"   window                      %ld\n",
					pAC->stats.tx_window_errors);

			}
		}
		SkgeProcDev = next;
	}
	if (offset >= len) {
		*eof = 1;
		return 0;
	}

	*buffer_location = buffer + offset;
	if (buffer_length >= len - offset) {
		*eof = 1;
	}
	return (min_t(int, buffer_length, len - offset));
}


/*****************************************************************************
 *
 * SkDoDiv - convert 64bit number
 *
 * Description:
 *	This function "converts" a long long number.
 *
 * Returns:
 *	remainder of division
 */
static long SkDoDiv (long long Dividend, int Divisor, long long *pErg)
{
	long Rest;
	long long Ergebnis;
	long Akku;


	Akku = Dividend >> 32;

	Ergebnis = ((long long) (Akku / Divisor)) << 32;
	Rest = Akku % Divisor;

	Akku = Rest << 16;
	Akku |= ((Dividend & 0xFFFF0000) >> 16);


	Ergebnis += ((long long) (Akku / Divisor)) << 16;
	Rest = Akku % Divisor;

	Akku = Rest << 16;
	Akku |= (Dividend & 0xFFFF);

	Ergebnis += (Akku / Divisor);
	Rest = Akku % Divisor;

	*pErg = Ergebnis;
	return (Rest);
}


#if 0
#define do_div(n,base) ({ \
long long __res; \
__res = ((unsigned long long) n) % (unsigned) base; \
n = ((unsigned long long) n) / (unsigned) base; \
__res; })

#endif


/*****************************************************************************
 *
 * SkNumber - Print results
 *
 * Description:
 *	This function converts a long long number into a string.
 *
 * Returns:
 *	number as string
 */
char * SkNumber(char * str, long long num, int base, int size, int precision
	,int type)
{
	char c,sign,tmp[66], *strorg = str;
	const char *digits="0123456789abcdefghijklmnopqrstuvwxyz";
	int i;

	if (type & LARGE)
		digits = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ";
	if (type & LEFT)
		type &= ~ZEROPAD;
	if (base < 2 || base > 36)
		return 0;
	c = (type & ZEROPAD) ? '0' : ' ';
	sign = 0;
	if (type & SIGN) {
		if (num < 0) {
			sign = '-';
			num = -num;
			size--;
		} else if (type & PLUS) {
			sign = '+';
			size--;
		} else if (type & SPACE) {
			sign = ' ';
			size--;
		}
	}
	if (type & SPECIALX) {
		if (base == 16)
			size -= 2;
		else if (base == 8)
			size--;
	}
	i = 0;
	if (num == 0)
		tmp[i++]='0';
	else while (num != 0)
		tmp[i++] = digits[SkDoDiv(num,base, &num)];

	if (i > precision)
		precision = i;
	size -= precision;
	if (!(type&(ZEROPAD+LEFT)))
		while(size-->0)
			*str++ = ' ';
	if (sign)
		*str++ = sign;
	if (type & SPECIALX) {
		if (base==8)
			*str++ = '0';
		else if (base==16) {
			*str++ = '0';
			*str++ = digits[33];
		}
	}
	if (!(type & LEFT))
		while (size-- > 0)
			*str++ = c;
	while (i < precision--)
		*str++ = '0';
	while (i-- > 0)
		*str++ = tmp[i];
	while (size-- > 0)
		*str++ = ' ';

	str[0] = '\0';

	return strorg;
}
