using System; using System.Collections.Generic; using System.Linq; using System.Text; namespace C64NET35 { public sealed class CBit { /// /// The max number of bits in byte /// public const int BIT_SIZE_BYTE = 8; /// /// The max number of bits in short /// public const int BIT_SIZE_SHORT = 16; /// /// The max number of bits in int /// public const int BIT_SIZE_INT = 32; /// /// The max number of bits in long /// public const int BIT_SIZE_LONG = 64; /// /// Private constructor /// private CBit() { } #region Byte Methods /// /// Gets the size of the input value in bits /// /// The input value /// public static int SizeOf ( byte pInput ) { int iRetval = 0; if ( pInput == 0 ) { iRetval = 0; } else if ( pInput == 1 ) { iRetval = 1; } else if ( pInput < 0 ) { iRetval = BIT_SIZE_BYTE; } else { int lTemp = 0; for ( int i = BIT_SIZE_BYTE -1; i > 1; i-- ) { lTemp = 1 << i-1; if ( (pInput & lTemp) == lTemp ) { iRetval = i; break; } } } return iRetval; } /// /// Gets the bits from a number as a number. /// /// The input value. /// The start position. /// public static byte GetBits ( byte pInput, int pStartIndex ) { return GetBits ( pInput, pStartIndex, BIT_SIZE_BYTE, false ); } /// /// Gets the bits. /// /// The p input. /// Start index of the p. /// if set to true [p shift]. /// public static byte GetBits ( byte pInput, int pStartIndex, bool pShift ) { return GetBits ( pInput, pStartIndex, BIT_SIZE_BYTE, pShift); } /// /// Gets the bits. /// /// The p input. /// Start index of the p. /// Length of the p. /// public static byte GetBits ( byte pInput, int pStartIndex, int pLength ) { return GetBits ( pInput, pStartIndex, pLength, false); } /// /// Gets a number in the specified range of bits /// /// /// /// public static byte GetBits ( byte pInput, int pStartIndex, int pLength, bool pShift ) { int lRetval = 0,lSize = 0,lTemp = 0; int lPosition = 1; if ( pInput < 2 && pInput > 0 ) { return pInput; //Should be either a 0 or 1 } lSize = SizeOf(pInput); if ( pStartIndex < 1 || pStartIndex > BIT_SIZE_SHORT ) { throw new ArgumentException("Start bit is out of range.","pStartIndex"); } if ( pLength < 0 || pLength + pStartIndex > BIT_SIZE_BYTE + 1 ) { throw new ArgumentException("End bit is out of range.","pLength"); } for ( int i = pStartIndex; (i < pLength + pStartIndex) && (lPosition <= lSize); i++ ) { lTemp = 1 << i - 1; if ( (pInput & lTemp) == lTemp ) { lRetval |= (1 << (lPosition - 1)); } lPosition++; } if ( pShift && lPosition < lSize ) { lRetval <<= lSize - lPosition; } return (byte) lRetval; } /// /// Sets the bits. /// /// The p dest. /// The p source. /// Index of the p source. /// public static byte SetBits ( byte pDest, byte pSource, int pSourceIndex ) { return SetBits ( pDest, pSource, pSourceIndex, 0, BIT_SIZE_BYTE ); } /// /// Sets the bits. /// /// The p dest. /// The p source. /// Index of the p source. /// Length of the p. /// public static byte SetBits ( byte pDest, byte pSource, int pSourceIndex, int pLength ) { return SetBits ( pDest, pSource, pSourceIndex, 0, pLength ); } /// /// Sets the bits. /// /// The dest. /// The source. /// Index of the source. /// Index of the dest. /// Length to read. /// public static byte SetBits ( byte pDest, byte pSource, int pSourceIndex, int pDestIndex, int pLength ) { int lSourceSize = 0, lTemp1 = 0; if ( pSourceIndex < 1 || pSourceIndex > BIT_SIZE_BYTE ) { throw new ArgumentException("Start bit is out of range.","pSourceIndex"); } if ( pDestIndex < 0 || pDestIndex > BIT_SIZE_BYTE ) { throw new ArgumentException("End bit is out of range.","pDestIndex"); } if ( pLength < 0 || pLength + pDestIndex > BIT_SIZE_BYTE ) { throw new ArgumentException("End bit is out of range.","pLength"); } pSource = GetBits(pSource,pSourceIndex,pLength); lSourceSize = SizeOf(pSource); int lPosition = 1; for ( int i = pDestIndex; (i < lSourceSize + pDestIndex); i++ ) { lTemp1 = 1 << lPosition - 1; if ( (pSource & lTemp1) == lTemp1 ) { pDest |= ((byte)(1 << (i - 1))); } else { lTemp1 = 1 << i - 1; if ( (pDest & lTemp1) == lTemp1 ) { pDest ^= ((byte)(1 << (i - 1))); } } lPosition++; } return (byte) pDest; } /// /// Determines whether [is bit set] [the specified p input]. /// /// The p input. /// The p position. /// /// true if [is bit set] [the specified p input]; otherwise, false. /// public static bool IsBitSet ( byte pInput, int pPosition) { return GetBits(pInput,pPosition,1,false) == 1; } /// /// Changes the value of the bit at the specified positon /// /// /// /// public static byte ChangeBit ( byte pInput, int pPosition ) { if ( pPosition > BIT_SIZE_BYTE ) { throw new ArgumentException("Position out of range","pPosition"); } return pInput ^= (byte)(1 << (pPosition - 1)); } /// /// Sets the value of a bit /// /// The p input. /// The p position. /// if set to true [p on]. /// public static byte SetBit ( byte pInput, int pPosition, bool pOn ) { if ( pPosition > BIT_SIZE_BYTE ) { throw new ArgumentException("Position out of range","pPosition"); } bool lIsSet = IsBitSet(pInput,pPosition); if ( pOn && !lIsSet || pOn && lIsSet) { pInput ^= (byte)((1 << (pPosition - 1))); } return pInput; } #endregion Byte Methods #region Short Methods /// /// Checks to see if number is less than 0. /// /// /// public static bool IsNegative ( short pInputValue ) { return (pInputValue & 0x8000) == 0x8000; } /// /// Changes the value from positive to negative and vis versa /// /// The value /// public short ChangeSign ( short pInputValue ) { return (short)(pInputValue ^ 0x8000); } /// /// Gets the size of the input value in bits /// /// The input value /// public static int SizeOf ( short pInput ) { int iRetval = 0; if ( pInput == 0 ) { iRetval = 0; } else if ( pInput == 1 ) { iRetval = 1; } else if ( pInput < 0 ) { iRetval = BIT_SIZE_SHORT; } else { int lTemp = 0; for ( int i = BIT_SIZE_SHORT -1; i > 1; i-- ) { lTemp = 1 << i-1; if ( (pInput & lTemp) == lTemp ) { iRetval = i; break; } } } return iRetval; } /// /// Gets the bits from a number as a number. /// /// The input value. /// The start position. /// public static short GetBits ( short pInput, int pStartIndex ) { return GetBits ( pInput, pStartIndex, BIT_SIZE_SHORT, false ); } /// /// Gets the bits. /// /// The p input. /// Start index of the p. /// if set to true [p shift]. /// public static short GetBits ( short pInput, int pStartIndex, bool pShift ) { return GetBits ( pInput, pStartIndex, BIT_SIZE_SHORT, pShift); } /// /// Gets the bits. /// /// The p input. /// Start index of the p. /// Length of the p. /// public static short GetBits ( short pInput, int pStartIndex, int pLength ) { return GetBits ( pInput, pStartIndex, pLength, false); } /// /// Gets a number in the specified range of bits /// /// /// /// public static short GetBits ( short pInput, int pStartIndex, int pLength, bool pShift ) { int lRetval = 0,lSize = 0,lTemp = 0; int lPosition = 1; if ( pInput < 2 && pInput > 0 ) { return pInput; //Should be either a 0 or 1 } lSize = SizeOf(pInput); if ( pStartIndex < 1 || pStartIndex > BIT_SIZE_SHORT ) { throw new ArgumentException("Start bit is out of range.","pStartIndex"); } if ( pLength < 0 || pLength + pStartIndex > BIT_SIZE_SHORT + 1 ) { throw new ArgumentException("End bit is out of range.","pLength"); } for ( int i = pStartIndex; (i < pLength + pStartIndex) && (lPosition <= lSize); i++ ) { lTemp = 1 << i - 1; if ( (pInput & lTemp) == lTemp ) { lRetval |= (1 << (lPosition - 1)); } lPosition++; } if ( pShift && lPosition < lSize ) { lRetval <<= lSize - lPosition; } return (short) lRetval; } /// /// Sets the bits. /// /// The p dest. /// The p source. /// Index of the p source. /// public static short SetBits ( short pDest, short pSource, int pSourceIndex ) { return SetBits ( pDest, pSource, pSourceIndex, 0, BIT_SIZE_SHORT ); } /// /// Sets the bits. /// /// The p dest. /// The p source. /// Index of the p source. /// Length of the p. /// public static int SetBits ( short pDest, short pSource, int pSourceIndex, int pLength ) { return SetBits ( pDest, pSource, pSourceIndex, 0, pLength ); } /// /// Sets the bits. /// /// The dest. /// The source. /// Index of the source. /// Index of the dest. /// Length to read. /// public static short SetBits ( short pDest, short pSource, int pSourceIndex, int pDestIndex, int pLength ) { int lSourceSize = 0, lTemp1 = 0; if ( pSourceIndex < 1 || pSourceIndex > BIT_SIZE_SHORT ) { throw new ArgumentException("Start bit is out of range.","pSourceIndex"); } if ( pDestIndex < 0 || pDestIndex > BIT_SIZE_SHORT ) { throw new ArgumentException("End bit is out of range.","pDestIndex"); } if ( pLength < 0 || pLength + pDestIndex > BIT_SIZE_SHORT ) { throw new ArgumentException("End bit is out of range.","pLength"); } pSource = GetBits(pSource,pSourceIndex,pLength); lSourceSize = SizeOf(pSource); int lPosition = 1; for ( int i = pDestIndex; (i < lSourceSize + pDestIndex); i++ ) { lTemp1 = 1 << lPosition - 1; if ( (pSource & lTemp1) == lTemp1 ) { pDest |= ((short)(1 << (i - 1))); } else { lTemp1 = 1 << i - 1; if ( (pDest & lTemp1) == lTemp1 ) { pDest ^= ((short)(1 << (i - 1))); } } lPosition++; } return pDest; } /// /// Determines whether [is bit set] [the specified p input]. /// /// The p input. /// The p position. /// /// true if [is bit set] [the specified p input]; otherwise, false. /// public static bool IsBitSet ( short pInput, int pPosition) { return GetBits(pInput,pPosition,1,false) == 1; } /// /// Changes the value of the bit at the specified positon /// /// /// /// public static short ChangeBit ( short pInput, int pPosition ) { if ( pPosition > BIT_SIZE_SHORT ) { throw new ArgumentException("Position out of range","pPosition"); } return pInput ^= (short)(1 << (pPosition - 1)); } /// /// Sets the value of a bit /// /// The p input. /// The p position. /// if set to true [p on]. /// public static short SetBit ( short pInput, int pPosition, bool pOn ) { if ( pPosition > BIT_SIZE_SHORT ) { throw new ArgumentException("Position out of range","pPosition"); } bool lIsSet = IsBitSet(pInput,pPosition); if ( pOn && !lIsSet || pOn && lIsSet) { pInput ^= (short)(1 << (pPosition - 1)); } return pInput; } #endregion Short Methods #region Int Methods /// /// Checks to see if number is less than 0. /// /// /// public static bool IsNegative ( int pInputValue ) { return (pInputValue & 0x80000000) == 0x80000000; } /// /// Changes the value from positive to negative and vis versa /// /// The value /// public int ChangeSign ( int pInputValue ) { return (int) (pInputValue ^ 0x80000000); } /// /// Gets the size of the input value in bits /// /// The input value /// public static int SizeOf ( int pInput ) { int iRetval = 0; if ( pInput == 0 ) { iRetval = 0; } else if ( pInput == 1 ) { iRetval = 1; } else if ( pInput < 0 ) { iRetval = BIT_SIZE_INT; } else { int lTemp = 0; for ( int i = BIT_SIZE_INT -1; i > 1; i-- ) { lTemp = 1 << i-1; if ( (pInput & lTemp) == lTemp ) { iRetval = i; break; } } } return iRetval; } /// /// Gets the bits from a number as a number. /// /// The input value. /// The start position. /// public static int GetBits ( int pInput, int pStartIndex ) { return GetBits ( pInput, pStartIndex, BIT_SIZE_INT, false ); } /// /// Gets the bits. /// /// The p input. /// Start index of the p. /// if set to true [p shift]. /// public static int GetBits ( int pInput, int pStartIndex, bool pShift ) { return GetBits ( pInput, pStartIndex, BIT_SIZE_INT, pShift); } /// /// Gets the bits. /// /// The p input. /// Start index of the p. /// Length of the p. /// public static int GetBits ( int pInput, int pStartIndex, int pLength ) { return GetBits ( pInput, pStartIndex, pLength, false); } /// /// Gets a number in the specified range of bits /// /// /// /// public static int GetBits ( int pInput, int pStartIndex, int pLength, bool pShift ) { int lRetval = 0,lSize = 0,lTemp = 0; int lPosition = 1; if ( pInput < 2 && pInput > 0 ) { return pInput; //Should be either a 0 or 1 } lSize = SizeOf(pInput); if ( pStartIndex < 1 || pStartIndex > BIT_SIZE_INT ) { throw new ArgumentException("Start bit is out of range.","pStartIndex"); } if ( pLength < 0 || pLength + pStartIndex > BIT_SIZE_INT + 1 ) { throw new ArgumentException("End bit is out of range.","pLength"); } for ( int i = pStartIndex; (i < pLength + pStartIndex) && (lPosition <= lSize); i++ ) { lTemp = 1 << i - 1; if ( (pInput & lTemp) == lTemp ) { lRetval |= (1 << (lPosition - 1)); } lPosition++; } if ( pShift && lPosition < lSize ) { lRetval <<= lSize - lPosition; } return lRetval; } /// /// Sets the bits. /// /// The p dest. /// The p source. /// Index of the p source. /// public static int SetBits ( int pDest, int pSource, int pSourceIndex ) { return SetBits ( pDest, pSource, pSourceIndex, 0, BIT_SIZE_INT ); } /// /// Sets the bits. /// /// The p dest. /// The p source. /// Index of the p source. /// Length of the p. /// public static int SetBits ( int pDest, int pSource, int pSourceIndex, int pLength ) { return SetBits ( pDest, pSource, pSourceIndex, 0, pLength ); } /// /// Sets the bits. /// /// The dest. /// The source. /// Index of the source. /// Index of the dest. /// Length to read. /// public static int SetBits ( int pDest, int pSource, int pSourceIndex, int pDestIndex, int pLength ) { int lSourceSize = 0, lTemp1 = 0; if ( pSourceIndex < 1 || pSourceIndex > BIT_SIZE_INT ) { throw new ArgumentException("Start bit is out of range.","pSourceIndex"); } if ( pDestIndex < 0 || pDestIndex > BIT_SIZE_INT ) { throw new ArgumentException("End bit is out of range.","pDestIndex"); } if ( pLength < 0 || pLength + pDestIndex > BIT_SIZE_INT ) { throw new ArgumentException("End bit is out of range.","pLength"); } pSource = GetBits(pSource,pSourceIndex,pLength); lSourceSize = SizeOf(pSource); int lPosition = 1; for ( int i = pDestIndex; (i < lSourceSize + pDestIndex); i++ ) { lTemp1 = 1 << lPosition - 1; if ( (pSource & lTemp1) == lTemp1 ) { pDest |= (1 << (i - 1)); } else { lTemp1 = 1 << i - 1; if ( (pDest & lTemp1) == lTemp1 ) { pDest ^= (1 << (i - 1)); } } lPosition++; } return pDest; } /// /// Determines whether [is bit set] [the specified p input]. /// /// The p input. /// The p position. /// /// true if [is bit set] [the specified p input]; otherwise, false. /// public static bool IsBitSet ( int pInput, int pPosition) { return GetBits(pInput,pPosition,1,false) == 1; } /// /// Changes the value of the bit at the specified positon /// /// /// /// public static int ChangeBit ( int pInput, int pPosition ) { if ( pPosition > BIT_SIZE_INT ) { throw new ArgumentException("Position out of range","pPosition"); } return pInput ^= (1 << (pPosition - 1)); } /// /// Sets the value of a bit /// /// The p input. /// The p position. /// if set to true [p on]. /// public static int SetBit ( int pInput, int pPosition, bool pOn ) { if ( pPosition > BIT_SIZE_INT ) { throw new ArgumentException("Position out of range","pPosition"); } bool lIsSet = IsBitSet(pInput,pPosition); if ( pOn && !lIsSet || pOn && lIsSet) { pInput ^= (1 << (pPosition - 1)); } return pInput; } #endregion Int Methods #region Long Methods /// /// Checks to see if number is less than 0. /// /// /// public static bool IsNegative ( long pInputValue ) { return (((ulong)pInputValue) & 0x8000000000000000) == 0x8000000000000000; } /// /// Changes the value from positive to negative and vis versa /// /// The value /// public long ChangeSign ( long pInputValue ) { return (long)(((ulong)pInputValue) ^ 0x8000000000000000); } /// /// Gets the size of the input value in bits /// /// The input value /// public static int SizeOf ( long pInput ) { int iRetval = 0; if ( pInput == 0 ) { iRetval = 0; } else if ( pInput == 1 ) { iRetval = 1; } else if ( pInput < 0 ) { iRetval = BIT_SIZE_LONG; } else { long lTemp = 0; for ( int i = BIT_SIZE_LONG -1; i > 1; i-- ) { lTemp = 1 << i-1; if ( (pInput & lTemp) == lTemp ) { iRetval = i; break; } } } return iRetval; } /// /// Gets the bits from a number as a number. /// /// The input value. /// The start position. /// public static long GetBits ( long pInput, int pStartIndex ) { return GetBits ( pInput, pStartIndex, BIT_SIZE_LONG, false ); } /// /// Gets the bits. /// /// The p input. /// Start index of the p. /// if set to true [p shift]. /// public static long GetBits ( long pInput, int pStartIndex, bool pShift ) { return GetBits ( pInput, pStartIndex, BIT_SIZE_LONG, pShift); } /// /// Gets the bits. /// /// The p input. /// Start index of the p. /// Length of the p. /// public static long GetBits ( long pInput, int pStartIndex, int pLength ) { return GetBits ( pInput, pStartIndex, pLength, false); } /// /// Gets a number in the specified range of bits /// /// /// /// public static long GetBits ( long pInput, int pStartIndex, int pLength, bool pShift ) { long lRetval = 0,lSize = 0,lTemp = 0; long lPosition = 1; if ( pInput < 2 && pInput > 0 ) { return pInput; //Should be either a 0 or 1 } lSize = SizeOf(pInput); if ( pStartIndex < 1 || pStartIndex > BIT_SIZE_LONG ) { throw new ArgumentException("Start bit is out of range.","pStartIndex"); } if ( pLength < 0 || pLength + pStartIndex > BIT_SIZE_LONG + 1 ) { throw new ArgumentException("End bit is out of range.","pLength"); } for ( int i = pStartIndex; (i < pLength + pStartIndex) && (lPosition <= lSize); i++ ) { lTemp = 1 << i - 1; if ( (pInput & lTemp) == lTemp ) { lRetval |= (1 << ((int)(lPosition - 1))); } lPosition++; } if ( pShift && lPosition < lSize ) { lRetval <<= ((int)(lSize - lPosition)); } return lRetval; } /// /// Sets the bits. /// /// The p dest. /// The p source. /// Index of the p source. /// public static long SetBits ( long pDest, long pSource, int pSourceIndex ) { return SetBits ( pDest, pSource, pSourceIndex, 0, BIT_SIZE_LONG ); } /// /// Sets the bits. /// /// The p dest. /// The p source. /// Index of the p source. /// Length of the p. /// public static long SetBits ( long pDest, long pSource, int pSourceIndex, int pLength ) { return SetBits ( pDest, pSource, pSourceIndex, 0, pLength ); } /// /// Sets the bits. /// /// The dest. /// The source. /// Index of the source. /// Index of the dest. /// Length to read. /// public static long SetBits ( long pDest, long pSource, int pSourceIndex, int pDestIndex, int pLength ) { long lSourceSize = 0, lTemp1 = 0; if ( pSourceIndex < 1 || pSourceIndex > BIT_SIZE_LONG ) { throw new ArgumentException("Start bit is out of range.","pSourceIndex"); } if ( pDestIndex < 0 || pDestIndex > BIT_SIZE_LONG ) { throw new ArgumentException("End bit is out of range.","pDestIndex"); } if ( pLength < 0 || pLength + pDestIndex > BIT_SIZE_LONG ) { throw new ArgumentException("End bit is out of range.","pLength"); } pSource = GetBits(pSource,pSourceIndex,pLength); lSourceSize = SizeOf(pSource); int lPosition = 1; for ( int i = pDestIndex; (i < lSourceSize + pDestIndex); i++ ) { lTemp1 = 1 << lPosition - 1; if ( (pSource & lTemp1) == lTemp1 ) { pDest |= (1 << (i - 1)); } else { lTemp1 = 1 << i - 1; if ( (pDest & lTemp1) == lTemp1 ) { pDest ^= (1 << (i - 1)); } } lPosition++; } return pDest; } /// /// Determines whether [is bit set] [the specified p input]. /// /// The p input. /// The p position. /// /// true if [is bit set] [the specified p input]; otherwise, false. /// public static bool IsBitSet ( long pInput, int pPosition) { return GetBits(pInput,pPosition,1,false) == 1; } /// /// Changes the value of the bit at the specified positon /// /// /// /// public static long ChangeBit ( long pInput, int pPosition ) { if ( pPosition > BIT_SIZE_LONG ) { throw new ArgumentException("Position out of range","pPosition"); } return pInput ^= (1 << (pPosition - 1)); } /// /// Sets the value of a bit /// /// The p input. /// The p position. /// if set to true [p on]. /// public static long SetBit ( long pInput, int pPosition, bool pOn ) { if ( pPosition > BIT_SIZE_LONG ) { throw new ArgumentException("Position out of range","pPosition"); } bool lIsSet = IsBitSet(pInput,pPosition); if ( pOn && !lIsSet || pOn && lIsSet) { pInput ^= (1 << (pPosition - 1)); } return pInput; } #endregion Long Methods /// /// The return value is the high-order double word of the specified value. /// /// /// public static int HiDword ( long pDWord ) { return ((int) (((pDWord) >> 32) & 0xFFFFFFFF)) ; } /// /// The return value is the low-order word of the specified value. /// /// The value /// public static int LoDword(long pDWord) { return ((int)pDWord); } /// /// The return value is the high-order word of the specified value. /// /// /// public static short HiWord ( int pDWord ) { return ((short) (((pDWord) >> 16) & 0xFFFF)) ; } /// /// The return value is the low-order word of the specified value. /// /// The value /// public static short LoWord(int pDWord) { return ((short)pDWord); } /// /// The return value is the high-order byte of the specified value. /// /// The value /// public static byte HiByte(short pWord) { return ((byte) (((short) (pWord) >> 8) & 0xFF)); } /// /// The return value is the low-order byte of the specified value. /// /// The value /// public static byte LoByte(short pWord) { return ((byte)pWord); } /// /// Makes a 64 bit long from two 32 bit integers /// /// The low order value. /// The high order value. /// public static long MakeLong ( int pValueLow, int pValueHigh ) { if ( pValueHigh == 0 ) { return (long) pValueLow; } long lTemp = SizeOf(pValueHigh); lTemp = (pValueHigh << ((BIT_SIZE_LONG) - ((int)lTemp + 1))); return (long)(pValueLow | lTemp); } /// /// Makes a 32 bit integer from two 16 bit shorts /// /// The low order value. /// The high order value. /// public static int MakeDword ( short pValueLow, short pValueHigh ) { if ( pValueHigh == 0 ) { return (int) pValueLow; } int lTemp = SizeOf(pValueHigh); lTemp = pValueHigh << ((BIT_SIZE_INT) - (lTemp + 1)); return (int)(lTemp | pValueLow); } /// /// Makes a 16 bit short from two bytes /// /// The low order value. /// The high order value. /// public static short MakeWord ( byte pValueLow, byte pValueHigh ) { if ( pValueHigh == 0 ) { return (short) pValueLow; } int lTemp = SizeOf(pValueHigh); lTemp = pValueHigh << ((BIT_SIZE_SHORT) - (lTemp + 1)); return (short)(pValueLow | lTemp); } } }