1 //========= Copyright 1996-2005, Valve Corporation, All rights reserved. ============//
2 //
3 // Purpose:
4 //
5 // $NoKeywords: $
6 //=============================================================================//
7 
8 #ifndef BASETYPES_H
9 #define BASETYPES_H
10 #pragma once
11 
12 //SDR_PUBLIC #include "commonmacros.h"
13 //SDR_PUBLIC #include "wchartypes.h"
14 
15 #include "platform.h"
16 #include <cmath>
17 #include <cstdlib>
18 
19 typedef unsigned char byte;
20 typedef unsigned short word;
21 
22 // This is the preferred Min operator. Using the MIN macro can lead to unexpected
23 // side-effects or more expensive code.
24 template< class T >
Min(T const & val1,T const & val2)25 static FORCEINLINE T const & Min( T const &val1, T const &val2 )
26 {
27 	return val1 < val2 ? val1 : val2;
28 }
29 
30 // This is the preferred Max operator. Using the MAX macro can lead to unexpected
31 // side-effects or more expensive code.
32 template< class T >
Max(T const & val1,T const & val2)33 static FORCEINLINE T const & Max( T const &val1, T const &val2 )
34 {
35 	return val1 > val2 ? val1 : val2;
36 }
37 
38 template< class T >
Clamp(T const & val,T const & minVal,T const & maxVal)39 static FORCEINLINE T const & Clamp( T const &val, T const &minVal, T const &maxVal )
40 {
41 	if ( val < minVal )
42 		return minVal;
43 	else if ( val > maxVal )
44 		return maxVal;
45 	else
46 		return val;
47 }
48 
49 #undef min
50 #undef max
51 #undef MIN
52 #undef MAX
53 #define MIN( a, b )				( ( ( a ) < ( b ) ) ? ( a ) : ( b ) )
54 #define MAX( a, b )				( ( ( a ) > ( b ) ) ? ( a ) : ( b ) )
55 
56 
57 namespace basetypes
58 {
59 	template <class T>
IsPowerOf2(T n)60 	inline bool IsPowerOf2( T n )
61 	{
62 		return n > 0 && (n & (n - 1)) == 0;
63 	}
64 
65 	template <class T1, class T2>
ModPowerOf2(T1 a,T2 b)66 	inline T2 ModPowerOf2( T1 a, T2 b )
67 	{
68 		return T2( a ) & (b - 1);
69 	}
70 
71 	template <class T>
RoundDownToMultipleOf(T n,T m)72 	inline T RoundDownToMultipleOf( T n, T m )
73 	{
74 		return n - (IsPowerOf2( m ) ? ModPowerOf2( n, m ) : (n%m));
75 	}
76 
77 	template <class T>
RoundUpToMultipleOf(T n,T m)78 	inline T RoundUpToMultipleOf( T n, T m )
79 	{
80 		if ( !n )
81 		{
82 			return m;
83 		}
84 		else
85 		{
86 			return RoundDownToMultipleOf( n + m - 1, m );
87 		}
88 	}
89 }
90 //SDR_PUBLIC using namespace basetypes;
91 
92 //-----------------------------------------------------------------------------
93 // integer bitscan operations
94 //-----------------------------------------------------------------------------
95 #if defined(_MSC_VER) && ( defined(_M_IX86) || defined(_M_X64) )
96 extern "C" unsigned char _BitScanReverse(unsigned long* Index, unsigned long Mask);
97 extern "C" unsigned char _BitScanForward(unsigned long* Index, unsigned long Mask);
98 #pragma intrinsic(_BitScanReverse)
99 #pragma intrinsic(_BitScanForward)
100 #if defined(_M_X64)
101 extern "C" unsigned char _BitScanReverse64(unsigned long* Index, unsigned __int64 Mask);
102 extern "C" unsigned char _BitScanForward64(unsigned long* Index, unsigned __int64 Mask);
103 #pragma intrinsic(_BitScanReverse64)
104 #pragma intrinsic(_BitScanForward64)
105 #endif
106 #endif
107 
FindMostSignificantBit(uint32 n)108 inline int FindMostSignificantBit( uint32 n )
109 {
110 #if defined(_MSC_VER) && ( defined(_M_IX86) || defined(_M_X64) )
111 	unsigned long b;
112 	if ( !_BitScanReverse( &b, n ) )
113 		return -1;
114 	return (int)b;
115 #elif defined(__GNUC__)
116 	if ( !n ) return -1;
117 	return 31 - (int) __builtin_clz( n );
118 #else
119 	int b = -1;
120 	for ( ; n; ++b, n >>= 1 ) {}
121 	return b;
122 #endif
123 }
124 
FindMostSignificantBit64(uint64 n)125 inline int FindMostSignificantBit64( uint64 n )
126 {
127 #if defined(_MSC_VER) && defined(_M_X64)
128 	unsigned long b;
129 	if ( !_BitScanReverse64( &b, n ) )
130 		return -1;
131 	return (int)b;
132 #elif defined(_MSC_VER) && defined(_M_IX86)
133 	if ( n >> 32 )
134 		return 32 + FindMostSignificantBit( n >> 32 );
135 	return FindMostSignificantBit( (uint32) n );
136 #elif defined(__GNUC__)
137 	if ( !n ) return -1;
138 	return 63 - (int) __builtin_clzll( n );
139 #else
140 	int b = -1;
141 	for ( ; n; ++b, n >>= 1 ) {}
142 	return b;
143 #endif
144 }
145 
FindLeastSignificantBit(uint32 n)146 inline int FindLeastSignificantBit( uint32 n )
147 {
148 #if defined(_MSC_VER) && ( defined(_M_IX86) || defined(_M_X64) )
149 	unsigned long b;
150 	if ( !_BitScanForward( &b, n ) )
151 		return -1;
152 	return (int)b;
153 #elif defined(__GNUC__)
154 	if ( !n ) return -1;
155 	return __builtin_ctz( n );
156 #else
157 	// isolate low bit and call FindMSB
158 	return FindMostSignificantBit( n & (uint32)(-(int32)n) );
159 #endif
160 }
161 
FindLeastSignificantBit64(uint64 n)162 inline int FindLeastSignificantBit64( uint64 n )
163 {
164 #if defined(_MSC_VER) && defined(_M_X64)
165 	unsigned long b;
166 	if ( !_BitScanForward64( &b, n ) )
167 		return -1;
168 	return (int)b;
169 #elif defined(_MSC_VER) && defined(_M_IX86)
170 	if ( (uint32)n )
171 		return FindLeastSignificantBit( (uint32)n );
172 	if ( n >> 32 )
173 		return 32 + FindLeastSignificantBit( (uint32)(n >> 32) );
174 	return -1;
175 #elif defined(__GNUC__)
176 	if ( !n ) return -1;
177 	return __builtin_ctzll( n );
178 #else
179 	// isolate low bit and call FindMSB
180 	return FindMostSignificantBit64( n & (uint64)(-(int64)n) );
181 #endif
182 }
183 #endif // BASETYPES_H
184