General C ++ memory pool code

Source: Internet
Author: User

The principle of http://blog.csdn.net/kevin_qing/article/details/608891 here

The previous Code cannot be found. Rewrite it once.

Added some simple error detection code. Helps debug memory problems.

Preliminary code, not carefully checked. Please leave a message if any bug exists.

 

// Type and macro # include <default. h> // debug information constbooldebugqmem = 1; structqmemdebuginfo {uint32_tmask; uint32_tsize; byteguard [128-8] ;}; template <bool flag, typename t, typename u> struct typeselectt {private: Template <bool> struct in {typedef t result ;}; template <> struct in <false> {typedef U result ;}; public: typedef typename in <flag>: Result result;}; // calculate Ln (X)/ln (Y) and convert it to an integer template <uint64_t X, uint 64_t y> struct logt {protected: Template <uint64_t x1> struct imp {Enum {next = (X1 + Y-1)/y ,}; enum {result = 1 + imP <next >:: result };}; template <> struct imP <1 >{ Enum {result = 0 };}; public: enum {result = imP <X >:: result };}; // x ^ ytemplate <uint64_t X, uint64_t y> struct powert {protected: template <uint64_t Y1> struct imp {Enum {next = y1-1}; Enum {result = x * imP <next >:: result };}; template <> struct imP <0> {Enum {Result = 1 };}; public: Enum {result = imP <y >:: result };}; // cache table, template <uint64_t index> struct cachecount {// table <> is not 0, 1, 2, and 3. Therefore, the compilation of <16B objects is not allowed, so the debugging information cannot be accommodated because the space is too small. Template <uint64_t> structtable; Template <> struct table <4 >{ Enum {result = 4096 };}; // 16B-> 64 ktemplate <> struct table <5 >{ Enum {result = 4096 };}; // 32B-> 128 ktemplate <> struct table <6 >{ Enum {result = 4096 };}; // 64b-> 256 ktemplate <> struct table <7 >{ Enum {result = 4096 };}; // 128b-> 512 ktemplate <> struct table <8 >{ Enum {result = 2048 };}; // 256b-> 512 ktemplate <> struct table <9 >{ Enum {result = 2048 };}; // 512b-> 1mt Emplate <> struct table <10 >{ Enum {result = 2048 };}; // 1 K-> 2 mtemplate <> struct table <11 >{ Enum {result = 2048 };}; // 2 k-> 4 mtemplate <> struct table <12 >{ Enum {result = 1024 };}; // 4 K-> 4 mtemplate <> struct table <13 >{ Enum {result = 1024 };}; // 8 K-> 8 mtemplate <> struct table <14 >{ Enum {result = 1024 };}; // 16 K-> 16 m // Add template for more use <> struct table <20 >{ Enum {result = 4 };}; // 1 m-> 4 mstructmincache {Enum {result = 2 };}; Enum {result = typeselectt <index <20, table <logt <index, 2 >:: result>, mincache >:: result :: result };}; // linked list, for available space recycling structqmemlink {qmemlink * Next;}; classqmemtest; byte * qalloc (size_t s) {returnnew byte [s];} template <size_t size> class qfixallocator {friendclassqmemtest; bytes; uint64_tallocbytes; uint64_tpoolbytes; qmemlink * mempool; Enum {sizefix = powert <2, logt <size, 2 >:: result}; Enum {caches = cacheco Unt <sizefix >:: result}; protected: qfixallocator () {usagebytes = 0; allocbytes = 0; poolbytes = 0; mempool = NULL;} public: void * alloc (size_t s) {assert (S <= sizefix); // avoid new [] Call to the wrong Allocator, host class should use a separate version of new [] () instead of calling New () qmemlink * r by default; If (mempool) {r = mempool; mempool = mempool-> next; poolbytes-= sizefix; usagebytes + = s; returnr;} byte * P = qalloc (sizefix * caches); mempool = (qmemlink *) P; For (INT I = 1; I <caches; ++ I) {r = (qmemlink *) P; P + = sizefix; r-> next = (qmemlink *) P;} r-> next = NULL; poolbytes + = (caches-1) * sizefix; usagebytes + = s; allocbytes + = caches * sizefix; returnp;} void free (void * P, size_t s) {qmemlink * l = (qmemlink *) P; l-> next = mempool; mempool = L; usagebytes-= s; poolbytes + = size;} voidstatus (uint64_t & U, uint64_t & A, uint64_t & P) const {u = usagebytes; A = allocbytes; P = poolbytes;} typedef qfixallocator me; static me instance ;}; typedefqfixallocator <pow ERT <2, 4>: Result> qfixallocator_4; typedefqfixallocator <powert <>: Result> qfixallocator_5; typedefqfixallocator <powert <>: Result> qfixallocator_6; typedefqfixallocator <powert <>: Result> failed; typedefqfixallocator <powert <>:: result> qfixallocator_9; typedefqfixallocator <powert <2, 10>: Result> qfixallocator_10; typedefqfixallocator <Po Wert <>: Result> qfixallocator_11; typedefqfixallocator <powert <>: Result> qfixallocator_12; typedefqfixallocator <powert <>: Result> qfixallocator_13; typedefqfixallocator <powert <>: Result> priority; typedefqfixallocator <powert <>: Result> qfixallocator_16; typedefqfixallocator <powert <2, 17>: Result> qfixallocator_17; typedefqfi Xallocator <powert <>: Result> priority; typedefqfixallocator <powert <>: Result> qfixallocator_19; typedefqfixallocator <powert <>: Result> qfixallocator_20; typedefqfixallocator <powert <2, 21>: Result> qfixallocator_21; Priority: instance; qfixallocator_13qfixallocator_13: instance; QF Ixallocator_14qfixallocator_14: instance; region: instance; qfixallocator_21qfixallocator_21: instance; template <Class Host> classqmemimpl {public: void * operatornew (Size_t size) {returnqfixallocator <powert <2, logt <sizeof (host), 2 >:: result >:: instance. alloc (size);} voidoperatordelete (void * P) {returnqfixallocator <powert <2, logt <sizeof (host), 2 >:: result >:: instance. free (p, sizeof (host);} void * operatornew [] (size_t size) {size + = 8; // x64 8-byte alignment ulongr, F; _ bitscanreverse (& R, size); _ bitscanreverse (& F, size); If (R! = F) // alignment + + R; Switch (r) {case19: // only the allocation of 1 MB bytes is processed here {uint32_t * P = (uint32_t *) qfixallocator_20 :: instance. alloc (size); * P = 19; // set mask ++ P; * P = size; return ++ P;} default: debugbreak ();} throw "Bad alloc";} voidoperatordelete [] (void * P) {uint32_t * p32 = (uint32_t *) P; p32-= 2; Switch (* p32) {case19: // only qfixallocator_20: instance. free (p32, * (p32 + 1); return; default: debugbreak () ;}}; template <Class Host> classqmemdebugimpl {Pu BLIC: void * operatornew (size_t size) {qmemdebuginfo * P = (optional *) qfixallocator <powert <2, logt <sizeof (host) + sizeof (qmemdebuginfo), 2> :: result>: instance. alloc (size); memset (p-> guard, 0, sizeof (p-> guard); P-> mask = logt <sizeof (host) + sizeof (qmemdebuginfo ), 2 >:: result; P-> mask | = 0x12345600; P-> size = size; return ++ P;} voidoperatordelete (void * P) {qmemdebuginfo * pdebug = (qmemdebuginfo *) P; -- pdebug; If (pdebug-> m Ask &(~ 0xff ))! = 0x12345600) {// The flag is incorrect. It may be the use of Delete, new [] debugbreak ();} If (pdebug-> size! = Sizeof (host) {// size error debugbreak ();} // other checks returnqfixallocator <powert <2, logt <sizeof (host) + sizeof (qmemdebuginfo ), 2 >:: result >:: instance. free (pdebug, sizeof (host);} void * operatornew [] (size_t size) {size + = sizeof (qmemdebuginfo); ulongr, F; If (! _ Bitscanreverse (& R, size) debugbreak (); // size 0, which is impossible _ bitscanreverse (& F, size); If (R! = F) // align + + R; qmemdebuginfo * P; Switch (r) {case19: P = (qmemdebuginfo *) qfixallocator_20: instance. alloc (size); P-> mask = 19; break; case20: P = (qmemdebuginfo *) qfixallocator_21: instance. alloc (size); P-> mask = 20; break; default: debugbreak ();} memset (p-> guard, 0, sizeof (p-> guard )); p-> size = size; return + P;} voidoperatordelete [] (void * P) {qmemdebuginfo * pdebug = (qmemdebuginfo *) P; -- pdebug; if (pdebug-> mask &(~ 0xff) {// The flag is incorrect. It may be caused by the use of Delete [], newdebugbreak ();} If (pdebug-> size <sizeof (host )) {// size error debugbreak () ;}ulongr, F; _ bitscanreverse (& R, pdebug-> size); _ bitscanreverse (& F, pdebug-> size ); if (R! = F) ++ R; If (pdebug-> mask! = R) debugbreak (); Switch (pdebug-> mask) {case19: qfixallocator_20: instance. free (pdebug, pdebug-> size); return; case20: qfixallocator_21: instance. free (pdebug, pdebug-> size); return; default: debugbreak () ;}}; template <Class Host> classqmempool: Public typeselectt <debugqmem, qmemdebugimpl 

 

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.