windows-nt/Source/XPSP1/NT/enduser/netmeeting/t120/mst123/crc.cpp
2020-09-26 16:20:57 +08:00

257 lines
4.7 KiB
C++

#include "precomp.h"
DEBUG_FILEZONE(ZONE_T120_T123PSTN);
/* crc.cpp
*
* Copyright (c) 1994-1995 by DataBeam Corporation, Lexington, KY
*
* Abstract:
* This is the implementation file for the CRC class.
*
* Private Instance Variables:
* CRC_Table[] - Look-up table for pre-calc CRC values.
* CRC_Poly - The algorithm's polynomial.
* CRC_Init - Initial register value.
* CRC_Check_Value - The value to compare the resulting received CRC.
* Invert - Determines wether to invert the CRC value before
* sending.
* CRC_Register - CRC register during execution.
*
* Caveats:
* None.
*
* Authors:
* Marvin Nicholson
*/
#include "crc.h"
/* CRC::CRC()
*
* Public
*
* Functional Description:
* The constructor fo CRC class initializes some member variables.
*/
CRC::CRC()
{
CRC_Width = 16; /* Width of the CRC register. */
CRC_Poly = 0x8408; /* Polynomial used in generating the CRC. */
CRC_Init = 0xFFFF; /* Initial value of the CRC register. */
Invert = TRUE; /* Enables 1's complement of CRC */
if (Invert)
{
/*
* If using 1's complement use this value to check incoming
* CRC.
*/
CRC_Check_Value = 0xF0B8;
}
else
{
/*
* If not inverting CRC on transmittion, use this value to
* check received CRC.
*/
CRC_Check_Value = 0x0000;
}
CRCTableGenerator (CRC_Poly);
}
/* CRC::~CRC()
*
* Public
*
* Functional Description:
* This is the destructor for the CRC class.
*/
CRC::~CRC()
{
}
/* ULONG CRC::OldCRCGenerator(HPUChar block_adr, ULONG block_len)
*
* Public
*
* Functional Description:
* This routine computes the CRC value using standard bit-shifting.
*/
ULONG CRC::OldCRCGenerator (
LPBYTE block_adr,
ULONG block_len)
{
Int i;
UChar input_byte;
USHORT byte_count;
CRC_Register = (USHORT) CRC_Init;
byte_count = 0;
while(byte_count < block_len)
{
input_byte = *(block_adr + byte_count);
CRC_Register ^= input_byte;
for(i=0; i<8; i++)
{
if(CRC_Register & 1)
{
CRC_Register >>= 1;
CRC_Register ^= (USHORT) CRC_Poly;
}
else
CRC_Register >>= 1;
}
byte_count++;
}
if (Invert)
return (CRC_Register ^ 0xFFFF);
else
return (CRC_Register);
}
/* ULONG CRC::CRCGenerator(HPUChar block_adr, ULONG block_len)
*
* Public
*
* Functional Descriprion:
* This routine computes the CRC value using a look-up table.
*/
ULONG CRC::CRCGenerator(
LPBYTE block_adr,
ULONG block_len)
{
CRC_Register = (USHORT) CRC_Init;
while(block_len--)
{
CRC_Register =
CRC_Table[(UChar) (((UChar) CRC_Register) ^ *block_adr++)] ^
(CRC_Register >> 8);
}
if (Invert)
return (CRC_Register ^ 0xFFFF);
else
return (CRC_Register);
}
/*
* USHORT CRC::CRCTableValue(
* Int index,
* ULONG poly)
*
* Functional Description
* This function generates a value that goes in the CRC_Table
*
* Formal Parameters
* index (i) - Index into the table
* poly (i) - Polynomial used to generate the value
*
* Return Value
* Value generated.
*
* Side Effects
* None
*
* Caveats
* None
*/
USHORT CRC::CRCTableValue(
Int index,
ULONG poly)
{
Int i;
ULONG r;
ULONG inbyte = (ULONG) index;
r = inbyte;
for(i=0; i<8; i++)
{
if (r & 1)
r = (r >> 1) ^ poly;
else
r >>= 1;
}
return ((USHORT) r);
}
/*
* void CRC::CRCTableGenerator (ULONG poly)
*
* Functional Description
* This function generates the CRC table
*
* Formal Parameters
* poly (i) - Polynomial used to generate the table
*
* Return Value
* None
*
* Side Effects
* None
*
* Caveats
* None
*/
void CRC::CRCTableGenerator (ULONG poly)
{
Int i;
for(i=0; i<CRC_TABLE_SIZE; i++)
CRC_Table[i] = CRCTableValue(i,poly);
}
/* BOOL CRC::CheckCRC(HPUChar block_adr, ULONG block_len)
*
* Public
*
* Functional Description:
* This routine computes the CRC of a datablock and its associated CRC and
* returns a TRUE value if the resulting CRC value is 0x0000
* or 0xF0B8.
*/
BOOL CRC::CheckCRC(
LPBYTE block_adr,
ULONG block_len)
{
CRC_Register = (USHORT) CRC_Init;
while(block_len--)
{
CRC_Register =
CRC_Table[(UChar) (((UChar) CRC_Register) ^ *block_adr++)] ^
(CRC_Register >> 8);
}
if (CRC_Register == CRC_Check_Value)
return TRUE;
else
return FALSE;
}
/*
* void CRC::GetOverhead (
* USHORT maximum_packet,
* USHORT * new_maximum_packet)
*
* Public
*
* Functional Description:
* This routine adds the number of overhead bytes generated by a CRC to
* the packet size passed in.
*/
void CRC::GetOverhead (
USHORT maximum_packet,
USHORT * new_maximum_packet)
{
*new_maximum_packet = maximum_packet + 2;
}