PVALLOC.C
上传用户:bangxh
上传日期:2007-01-31
资源大小:42235k
文件大小:8k
源码类别:

Windows编程

开发平台:

Visual C++

  1. /*
  2.  -  P V A L L O C . C
  3.  -
  4.  *  Copyright (C) 1995 Microsoft Corporation
  5.  *  Purpose:
  6.  *      Implementation of a chained memory manager.
  7.  *
  8.  */
  9. #include <string.h>
  10. #include <windows.h>
  11. #include <stdio.h>
  12. #include <stdlib.h>
  13. #include <pvalloc.h>
  14. #undef _PVALLOC_LOG
  15. #ifdef _PVALLOC_LOG
  16. static CB       cbTotalAlloc    = 0;
  17. static CB       ulTotalBlockNum = 0;
  18. #endif
  19. /*
  20.  -  PvAlloc
  21.  -
  22.  *  Purpose:
  23.  *      Allocates a chunk of memory on the global heap.
  24.  *
  25.  *  Parameters:
  26.  *      cbSize          - Count of bytes requested.
  27.  *
  28.  *  Returns:
  29.  *      lpv             - Pointer to the allocated memory
  30.  *
  31.  */
  32. PV PvAlloc(CB cbSize)
  33. {
  34.     PV      lpv         = pvNull;
  35.     HANDLE  hMem;
  36.     PPVINFO ppvinfo;
  37. #ifdef _PVALLOC_LOG
  38.     char    szFileName[80];
  39.     LPSTR   lpszTemp    = NULL;
  40.     FILE    *pFile      = NULL;
  41.     char    szBuff[128];
  42. #endif
  43.     /* Make sure allocations are in multiples of 4 */
  44.     if(cbSize < 4)
  45.         cbSize = 4;
  46.     else if(cbSize & 3)
  47.         cbSize += 4 - (cbSize & 3);
  48.     /* Allocate the block */
  49.     hMem = GlobalAlloc(GMEM_MOVEABLE, cbSize + sizeof(PVINFO));
  50.     if(hMem)
  51.     {
  52.         ppvinfo = (PPVINFO)GlobalLock(hMem);
  53.         ppvinfo->hMem    = hMem;
  54.         ppvinfo->lpvNext = pvNull;
  55.         ppvinfo->lpvBuf  = ((PB)ppvinfo) + sizeof(PVINFO);
  56. #ifdef _PVALLOC_LOG
  57.         ppvinfo->cbSize  = cbSize;
  58.         ulTotalBlockNum++;
  59.         ppvinfo->ulBlockNum = ulTotalBlockNum;
  60.         cbTotalAlloc += cbSize;
  61.         
  62.         // log to file
  63.         lpszTemp = getenv("TEMP");
  64.         if(lpszTemp)
  65.             strcpy(szFileName, lpszTemp);
  66.         else
  67.             strcpy(szFileName, "c:\temp");
  68.         strcat(szFileName, "\pvalloc.log");
  69.         
  70.         pFile = fopen(szFileName,"a");
  71.         if (pFile == NULL)     
  72.             goto NoFile;      
  73. //           return NULL;
  74.         fprintf(pFile, "Block: t%lutPvAlloc: %ld BytesttTotal: %ld Bytesn",
  75.                  ulTotalBlockNum, cbSize, cbTotalAlloc);
  76.         if (pFile)
  77.             fclose(pFile);
  78.         
  79.         // log to comm port
  80.         wsprintf(szBuff,"Block: t%lutPvAlloc: %ld BytesttTotal: %ld Bytesn",
  81.                  ulTotalBlockNum, cbSize, cbTotalAlloc);
  82.         OutputDebugString(szBuff);
  83.                         
  84. NoFile:                           
  85. #ifdef _WIN32
  86.         memset(ppvinfo->lpvBuf, 0xaa, (size_t)cbSize);
  87. #else
  88.         _fmemset(ppvinfo->lpvBuf, 0xaa, (size_t)cbSize);
  89. #endif  /* _WIN32 */
  90. #endif  /* _PVALLOC_LOG */
  91.         lpv = ppvinfo->lpvBuf;
  92.     }
  93.     return lpv;
  94. }
  95. /*
  96.  -  PvAllocMore
  97.  -
  98.  *  Purpose:
  99.  *      Allocates a chunk of memory and chains it to a parent block.
  100.  *
  101.  *  Parameters:
  102.  *      cbSize          - Count of additional bytes to allocate
  103.  *      lpvParent       - Pointer to parent in memory chain
  104.  *
  105.  *  Returns:
  106.  *      lpv             - Pointer to the allocated memory
  107.  *
  108.  */
  109. PV PvAllocMore(CB cbSize, PV lpvParent)
  110. {
  111.     PV          lpvStep = lpvParent;
  112.     PV          lpv     = pvNull;
  113.     PPVINFO     ppvinfoMore;
  114.     HANDLE      hMem;
  115.     PPVINFO     ppvinfo;
  116.     /* Step to the last link */
  117.     do
  118.     {
  119.         ppvinfoMore = (PPVINFO)(((PB)lpvStep) - sizeof(PVINFO));
  120.         lpvStep = ppvinfoMore->lpvNext;
  121.     }
  122.     while(ppvinfoMore->lpvNext != pvNull);
  123.     // beginning of section that was taken from PvAlloc
  124.     if(cbSize < 4)
  125.         cbSize = 4;
  126.     else if(cbSize & 3)
  127.         cbSize += 4 - (cbSize & 3);
  128.     hMem = GlobalAlloc(GMEM_MOVEABLE, cbSize + sizeof(PVINFO));
  129.     if(hMem)
  130.     {
  131.         ppvinfo = (PPVINFO)GlobalLock(hMem);
  132.         ppvinfo->hMem       = hMem;
  133.         ppvinfo->lpvNext    = pvNull;
  134.         ppvinfo->lpvBuf     = ((PB)ppvinfo) + sizeof(PVINFO);
  135. #ifdef _PVALLOC_LOG
  136.         ppvinfo->cbSize     = cbSize;
  137.         ppvinfo->ulBlockNum = ppvinfoMore->ulBlockNum;
  138.         cbTotalAlloc += cbSize;
  139. #ifdef _WIN32
  140.         memset(ppvinfo->lpvBuf, 0xaa, (size_t)cbSize);
  141. #else
  142.         _fmemset(ppvinfo->lpvBuf, 0xaa, (size_t)cbSize);
  143. #endif
  144. #endif
  145.         lpv = ppvinfo->lpvBuf;
  146.     }
  147.     else
  148.         return lpv;
  149.         
  150.     // end of section taken from pvalloc
  151. #ifdef _WIN32
  152.         memset(lpv, 0xbb, (size_t)cbSize);
  153. #else
  154.         _fmemset(lpv, 0xbb, (size_t)cbSize);
  155. #endif  /* _WIN32 */
  156.     ppvinfoMore->lpvNext = lpv;
  157.     return lpv;
  158. }
  159. /*
  160.  -  PvFree
  161.  -
  162.  *  Purpose:
  163.  *      This function frees memory allocated by PvAlloc or PvAllocMore.
  164.  *      After the call, the pointer memory will be invalid and should
  165.  *      not be referenced again.
  166.  *      When memory is allocated by PvAlloc and PvAllocMore, which can
  167.  *      contain several levels of pointers, all the application needs to
  168.  *      do to free the entire structure is call this routine with the
  169.  *      base pointer returned by the PvAlloc call.
  170.  *
  171.  *  Parameters:
  172.  *      lpv             - Pointer to memory to be freed.
  173.  *
  174.  *  Returns:
  175.  *      Void
  176.  *
  177.  */
  178. BOOL PvFree(PV lpv)
  179. {
  180.     PPVINFO ppvinfo;
  181. #ifdef _PVALLOC_LOG
  182.     CB      cbSize;
  183.     CB      ulBlockNum;
  184.     FILE    *pFile  = NULL;
  185.     CB      cbFree  = 0;
  186.     CB      cbTotalBeforeFree = cbTotalAlloc;
  187.     char    szFileName[80];
  188.     LPSTR   lpszTemp    = NULL;
  189.     char    szBuff[128];
  190. #endif
  191.     if(!lpv)
  192.         return 0;
  193.     ppvinfo = (PPVINFO)(((PB)lpv) - sizeof(PVINFO));
  194.     while(ppvinfo)
  195.     {
  196.         lpv = ppvinfo->lpvNext;
  197. #ifdef _PVALLOC_LOG
  198.         cbSize      = ppvinfo->cbSize;
  199.         cbFree      += ppvinfo->cbSize;
  200.         ulBlockNum  = ppvinfo->ulBlockNum;
  201. #ifdef _WIN32
  202.         memset(ppvinfo->lpvBuf, 0xcc, (size_t)ppvinfo->cbSize);
  203. #else
  204.         _fmemset(ppvinfo->lpvBuf, 0xcc, (size_t)ppvinfo->cbSize);
  205. #endif  /* _WIN32 */
  206. #endif  /* _PVALLOC_LOG */
  207.         if(GlobalUnlock(ppvinfo->hMem))
  208.             goto err;  // Our lock count is non-zero
  209.         if(GlobalFree(ppvinfo->hMem))
  210.             goto err;  // Failure
  211. #ifdef _PVALLOC_LOG
  212.         cbTotalAlloc -= cbSize;
  213. #endif
  214.         if(lpv)
  215.             ppvinfo = (PPVINFO)(((PB)lpv) - sizeof(PVINFO));
  216.         else
  217.             break;
  218.     }
  219. #ifdef _PVALLOC_LOG
  220.     
  221.     if((cbTotalBeforeFree - cbTotalAlloc) != cbFree)
  222.        goto err;
  223.        
  224.     // log to file
  225.     lpszTemp = getenv("TEMP");
  226.     if(lpszTemp)
  227.         strcpy(szFileName, lpszTemp);
  228.     else
  229.         strcpy(szFileName, "c:\temp");
  230.     strcat(szFileName, "\pvalloc.log");
  231.         
  232.     pFile = fopen(szFileName,"a");
  233.        
  234.     if (pFile == NULL)
  235.        goto err;
  236.     fprintf(pFile, "Block: t%lutt***PvFree***,  Freeing  %lu Bytes(Alloc and AllocMore)tUnFreed: %ld Bytesn",
  237.                     ulBlockNum, cbFree, cbTotalAlloc);
  238.     if (pFile)
  239.         fclose(pFile);
  240.      // log to comm port
  241.     wsprintf(szBuff,"Block: t%lutt***PvFree***,  Freeing  %lu Bytes(Alloc and AllocMore)tUnFreed: %ld Bytesn",
  242.                     ulBlockNum, cbFree, cbTotalAlloc);
  243.     OutputDebugString(szBuff);
  244. #endif  /* _PVALLOC_LOG */
  245.     return 0; // Success!
  246. err:
  247. #ifdef _PVALLOC_LOG
  248.     // find file to open
  249.     lpszTemp = getenv("TEMP");
  250.     if(lpszTemp)
  251.         strcpy(szFileName, lpszTemp);
  252.     else
  253.         strcpy(szFileName, "c:\temp");
  254.     strcat(szFileName, "\pvalloc.log");
  255.         
  256.     pFile = fopen(szFileName,"a");
  257.     if (pFile == NULL)
  258.        return 1;
  259.     fprintf(pFile, "Block: %lu Failure freeing: %ld BytestUnFreed: %ld Bytesn",
  260.              ulBlockNum, cbSize, cbTotalAlloc);
  261.     if (pFile)
  262.         fclose(pFile);
  263. #endif  /* _PVALLOC_LOG */
  264.     return 1; // Failure!
  265. }