Created BitUnion type which lets you define nested bitfields for an integer in a...
authorGabe Black <gblack@eecs.umich.edu>
Sat, 17 Mar 2007 23:33:00 +0000 (23:33 +0000)
committerGabe Black <gblack@eecs.umich.edu>
Sat, 17 Mar 2007 23:33:00 +0000 (23:33 +0000)
--HG--
extra : convert_revision : 56a9d06b6b7274a493dae4b290c5f9b42e59f20d

src/base/bitfield.hh

index 79dbcc86c45889dcc5332c58ba21856cd7a734a5..179e14896e29f3c791dd9acb71a3dfd26484fe1f 100644 (file)
@@ -33,6 +33,7 @@
 #define __BASE_BITFIELD_HH__
 
 #include <inttypes.h>
+//#include "base/misc.hh"
 
 /**
  * Generate a 64-bit mask of 'nbits' 1s, right justified.
@@ -130,6 +131,192 @@ findMsbSet(uint64_t val) {
     return msb;
 }
 
+template<class Data, int first, int last=first>
+class BitfieldBase
+{
+  protected:
+    uint8_t __data[sizeof(Data)];
+
+    //These are defined here so it can be specialized for Data, but can be
+    //hidden by RO and WO variants.
+    inline uint64_t getBits(int _first, int _last)
+    {
+        //build up the right bits from the byte array "data"
+        //panic("Not yet implemented.\n");
+        return 0;
+    }
+
+    inline void setBits(int _first, int _last, uint64_t val)
+    {
+        //Set the right bits from the byte array "data"
+        //panic("Not yet implemented.\n");
+    }
+};
+
+template<class Data, int first, int last=first>
+class BitfieldNativeBase
+{
+  protected:
+    Data __data;
+
+    inline uint64_t getBits(int _first, int _last)
+    {
+        return bits(__data, first, last);
+    }
+
+    inline void setBits(int _first, int _last, uint64_t val)
+    {
+        replaceBits(__data, first, last, val);
+    }
+};
+
+template <int first>
+class BitfieldBase<uint64_t, first, first> :
+        public BitfieldNativeBase<uint64_t, first, first>
+{};
+
+template <int first, int last>
+class BitfieldBase<uint64_t, first, last> :
+        public BitfieldNativeBase<uint64_t, first, last>
+{};
+
+template <int first>
+class BitfieldBase<uint32_t, first, first> :
+        public BitfieldNativeBase<uint32_t, first, first>
+{};
+
+template <int first, int last>
+class BitfieldBase<uint32_t, first, last> :
+        public BitfieldNativeBase<uint32_t, first, last>
+{};
+
+template <int first>
+class BitfieldBase<uint16_t, first, first> :
+        public BitfieldNativeBase<uint16_t, first, first>
+{};
+
+template <int first, int last>
+class BitfieldBase<uint16_t, first, last> :
+        public BitfieldNativeBase<uint16_t, first, last>
+{};
+
+template <int first>
+class BitfieldBase<uint8_t, first, first> :
+        public BitfieldNativeBase<uint8_t, first, first>
+{};
+
+template <int first, int last>
+class BitfieldBase<uint8_t, first, last> :
+        public BitfieldNativeBase<uint8_t, first, last>
+{};
+
+template<class Data, int first, int last=first>
+class _BitfieldRO : public BitfieldBase<Data, first, last>
+{
+  public:
+    operator const Data & ()
+    {
+        return this->getBits(first, last);
+    }
+};
+
+template<class Data, int first, int last=first>
+class _BitfieldWO : public BitfieldBase<Data, first, last>
+{
+  public:
+    const Data & operator = (const Data & _data)
+    {
+        this->setBits(first, last, _data);
+        return *this;
+    }
+};
+
+template<class Data, int first, int last=first>
+class _BitfieldRW : public BitfieldBase<Data, first, last>
+{
+  public:
+    operator const Data ()
+    {
+        return this->getBits(first, last);
+    }
+
+    const Data operator = (const Data & _data)
+    {
+        this->setBits(first, last, _data);
+        return *this;
+    }
+};
+
+template <class Type, class Base>
+class BitUnionOperators : public Base
+{
+  public:
+    operator const Type ()
+    {
+        return Base::__data;
+    }
+
+    const Type operator = (const Type & _data)
+    {
+        Base::__data = _data;
+    }
+
+    bool operator < (const Base & base)
+    {
+        return Base::__data < base.__data;
+    }
+
+    bool operator == (const Base & base)
+    {
+        return Base::__data == base.__data;
+    }
+};
+
+#define __BitUnion(type, name) \
+    class __##name { \
+      public: \
+        typedef type __DataType; \
+        union { \
+            type __data;\
+
+#define EndBitUnion(name) \
+        }; \
+    }; \
+    typedef BitUnionOperators<__##name::__DataType, __##name> name;
+
+#define __SubBitUnion(type, name) \
+        union { \
+            type __data; \
+            inline operator const __DataType () \
+            { return __data; } \
+            \
+            inline const __DataType operator = (const __DataType & _data) \
+            { __data = _data; }
+
+#define EndSubBitUnion(name) } name;
+
+//Regular read/write bitfields
+#define BitfieldRW(first, last) _BitfieldRW<__DataType, first, last>
+#define SubBitUnionRW(name, first, last) \
+        __SubBitUnion(BitfieldRW(first, last), name)
+#define Bitfield(first, last) BitfieldRW(first, last)
+#define SubBitUnion(name, first, last) SubBitUnionRW(name, first, last)
+
+//Read only bitfields
+#define BitfieldRO(first, last) _BitfieldRO<__DataType, first, last>
+#define SubBitUnionRO(name, first, last) \
+        __SubBitUnion(BitfieldRO(first, last), name)
+
+//Write only bitfields
+#define BitfieldWO(first, last) _BitfieldWO<__DataType, first, last>
+#define SubBitUnionWO(name, first, last) \
+        __SubBitUnion(BitfieldWO(first, last), name)
+
+#define BitUnion(type, name) __BitUnion(type, name)
 
+#define BitUnion64(name) __BitUnion(uint64_t, name)
+#define BitUnion32(name) __BitUnion(uint32_t, name)
+#define BitUnion16(name) __BitUnion(uint16_t, name)
+#define BitUnion8(name) __BitUnion(uint8_t, name)
 
 #endif // __BASE_BITFIELD_HH__