00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #ifndef __BITFIELD_H__
00022 #define __BITFIELD_H__
00023
00024 #include <inttypes.h>
00025
00026 #include "bt_assert.h"
00027
00032 template<int bits>
00033
00038 class bitfield_c {
00039
00040 private:
00041
00042 uint64_t field[(bits+63)/64];
00043
00044 public:
00045
00047 bitfield_c() {
00048 clear();
00049 }
00050
00052 bitfield_c(const char * val) {
00053 clear();
00054 operator=(val);
00055 }
00056
00058 bitfield_c(const bitfield_c<bits>& orig) {
00059 memcpy(field, orig.field, 8*((bits+63)/64));
00060 }
00061
00063 bool get(uint16_t pos) const {
00064 bt_assert(pos < bits);
00065 return field[pos >> 6] & (1ll << (pos & 63));
00066 }
00067
00069 void set(uint16_t pos) {
00070 bt_assert(pos < bits);
00071 field[pos >> 6] |= (1ll << (pos & 63));
00072 }
00073
00075 void reset(uint16_t pos) {
00076 bt_assert(pos < bits);
00077 field[pos >> 6] &= ~(1ll << (pos & 63));
00078 }
00079
00081 void clear(void) {
00082 memset(field, 0, 8*((bits+63)/64));
00083 }
00084
00086 bool notNull(void) {
00087 for (int i = 0; i < ((bits+63)/64); i++)
00088 if (field[i] > 0)
00089 return true;
00090
00091 return false;
00092 }
00093
00105 const bitfield_c<bits> & operator=(const char * val) {
00106
00107 size_t l = strlen(val);
00108
00109 bt_assert(4*l <= bits);
00110
00111 int fpos = 0;
00112 int bitpos = 0;
00113 field[0] = 0;
00114
00115 for (int i = l-1; i >= 0; i--) {
00116 uint64_t cval = 0;
00117
00118 if ((val[i] >= '0') && (val[i] <= '9'))
00119 cval = val[i]-'0';
00120 else if ((val[i] >= 'a') && (val[i] <= 'f'))
00121 cval = val[i] - 'a' + 10;
00122 else if ((val[i] >= 'A') && (val[i] <= 'F'))
00123 cval = val[i] - 'A' + 10;
00124 else
00125 bt_assert(0);
00126
00127 field[fpos] |= cval << bitpos;
00128
00129 bitpos += 4;
00130 if (bitpos >= 64) {
00131 bitpos = 0;
00132 fpos++;
00133 field[fpos] = 0;
00134 }
00135 }
00136
00137 return *this;
00138 }
00139
00141 bool operator==(const bitfield_c<bits> & op) const {
00142
00143 for (int i = 0; i < ((bits+63)/64); i++)
00144 if (op.field[i] != field[i])
00145 return false;
00146
00147 return true;
00148 }
00149
00151 bool operator!=(const bitfield_c<bits> & op) const {
00152
00153 for (int i = 0; i < ((bits+63)/64); i++)
00154 if (op.field[i] != field[i])
00155 return true;
00156
00157 return false;
00158 }
00159
00168 unsigned int countbits(void) const {
00169
00170 unsigned int res = 0;
00171
00172 for (int i = 0; i < ((bits+63)/64); i++) {
00173 uint64_t s = field[i];
00174
00175 s -= ((s >> 1) & 0x5555555555555555ll);
00176 s = (((s >> 2) & 0x3333333333333333ll) + (s & 0x3333333333333333ll));
00177 s = (((s >> 4) + s) & 0x0f0f0f0f0f0f0f0fll);
00178 s += (s >> 8);
00179 s += (s >> 16);
00180 s += (s >> 32);
00181
00182 res += (s & 0x3f);
00183 }
00184
00185 return res;
00186 }
00187
00191 void print(char * str, unsigned int len) const {
00192
00193 int idx = 0;
00194
00195 for (int i = ((bits+63)/64)-1; i >= 0; i--)
00196 idx += snprintf(str+idx, len-idx, "%016llx", field[i]);
00197 }
00198
00202 void print(void) const {
00203
00204 for (int i = ((bits+63)/64)-1; i >= 0; i--)
00205 printf("%016llx", field[i]);
00206 }
00207
00211 const bitfield_c<bits> operator&(const bitfield_c<bits> & right) const {
00212 bitfield_c<bits> res;
00213
00214 for (int i = 0; i < ((bits+63)/64); i++)
00215 res.field[i] = field[i] & right.field[i];
00216
00217 return res;
00218 }
00219
00223 const bitfield_c<bits> operator|(const bitfield_c<bits> & right) const {
00224 bitfield_c<bits> res;
00225
00226 for (int i = 0; i < ((bits+63)/64); i++)
00227 res.field[i] = field[i] | right.field[i];
00228
00229 return res;
00230 }
00231
00232 };
00233
00234
00235 #endif