📄 pcsl_memory.c
字号:
} } /* while */ /* allocating */ if ((pcslMemoryHdr->free == 1) && (pcslMemoryHdr->size >= numBytesToAllocate)) {#if PCSL_BEST_FIT_ALLOCATION /* Keep looking for the best fit */ if (fitBlockHdr == NULL || fitBlockHdr->size > pcslMemoryHdr->size) { fitBlockHdr = pcslMemoryHdr; /* Found exact match */ if (pcslMemoryHdr->size == numBytesToAllocate) { break; } }#else fitBlockHdr = pcslMemoryHdr; break;#endif } /* end of allocating */ } /* end of else */ } /* end of for */ if (fitBlockHdr != NULL) { pcslMemoryHdr = fitBlockHdr; if (pcslMemoryHdr->size > (numBytesToAllocate + sizeof(_PcslMemHdr) + 4)) { /* split block */ _PcslMemHdrPtr nextHdr; nextHdr = (_PcslMemHdrPtr)((char *)pcslMemoryHdr + numBytesToAllocate + sizeof(_PcslMemHdr)); nextHdr->magic = MAGIC; nextHdr->free = 1; nextHdr->size = pcslMemoryHdr->size - numBytesToAllocate - sizeof(_PcslMemHdr);#ifdef PCSL_DEBUG nextHdr->guard = GUARD_WORD; nextHdr->guardSize = 0;#endif pcslMemoryHdr->size = numBytesToAllocate; } pcslMemoryHdr->free = 0; loc = (void*)((char*)pcslMemoryHdr + sizeof(_PcslMemHdr));#ifdef PCSL_DEBUG pcslMemoryHdr->guard = GUARD_WORD; /* Add head guard */ pcslMemoryHdr->filename = filename; pcslMemoryHdr->lineno = lineno; /* Add tail guard */ guardSize = pcslMemoryHdr->size - size; pcslMemoryHdr->guardSize = guardSize; guardPos = (void*)((char*)loc + pcslMemoryHdr->size - guardSize); for(i=0; i<guardSize; i++) { ((unsigned char*)guardPos)[i] = GUARD_BYTE; } PcslMemoryAllocated += numBytesToAllocate; if (PcslMemoryAllocated > PcslMemoryHighWaterMark) { PcslMemoryHighWaterMark = PcslMemoryAllocated; }#if PCSL_TRACE_MEMORY report("DEBUG: Requested %d provided %d at 0x%p\n", numBytesToAllocate, pcslMemoryHdr->size, loc); print_alloc("allocated", filename, lineno);#endif /* of PCSL_TRACE_MEMORY */#endif /* of PCSL_DEBUG */ return(loc); } REPORT1("DEBUG: Unable to allocate %d bytes\n", numBytesToAllocate); return((void *)0);}/** * FUNCTION: pcsl_mem_calloc_impl0() * TYPE: public operation * OVERVIEW: Allocate memory from the private PCSL memory pool, * memory contents are cleared * INTERFACE: * parameters: nelem Number of elements to allocate * elsize Size of one element * filename Filename where allocation occured * lineno Line number where allocation occured * returns: pointer to the newly allocated and cleared memory * */#ifdef PCSL_DEBUGvoid*pcsl_mem_calloc_impl0(unsigned int nelem, unsigned int elsize, char* filename, int lineno) { void *loc = NULL; if ((loc = pcsl_mem_malloc_impl0((nelem) * (elsize), filename, lineno)) != NULL) { memset(loc, 0, nelem * elsize); } return loc;}#elsevoid*pcsl_mem_calloc_impl0(unsigned int nelem, unsigned int elsize) { void *loc = NULL; if ((loc = pcsl_mem_malloc_impl0((nelem) * (elsize))) != NULL) { memset(loc, 0, nelem * elsize); } return loc;}#endif/** * FUNCTION: pcsl_mem_realloc_impl0() * TYPE: public operation * OVERVIEW: Re-allocate memory from the private PCSL memory pool * INTERFACE: * parameters: ptr Original memory pointer * size New size * filename Filename where allocation occured * lineno Line number where allocation occured * returns: pointer to the re-allocated memory * */#ifdef PCSL_DEBUGvoid*pcsl_mem_realloc_impl0(void* ptr, unsigned int size, char* filename, int lineno) {#elsevoid*pcsl_mem_realloc_impl0(void* ptr, unsigned int size) {#endif void* newPtr = NULL; _PcslMemHdrPtr memHdr; /* If ptr is NULL, realloc() behaves like malloc() for the given size. */ if (ptr == NULL) {#ifdef PCSL_DEBUG ptr = pcsl_mem_malloc_impl0(size, filename, lineno);#else ptr = pcsl_mem_malloc_impl0(size);#endif return ptr; } memHdr = (_PcslMemHdrPtr)((char*)ptr - sizeof(_PcslMemHdr)); if (memHdr->size != size) { if (size != 0) {#ifdef PCSL_DEBUG newPtr = pcsl_mem_malloc_impl0(size, filename, lineno);#else newPtr = pcsl_mem_malloc_impl0(size);#endif if (newPtr != NULL) { if (memHdr->size < size) { memcpy(newPtr, ptr, memHdr->size); } else { memcpy(newPtr, ptr, size); }#ifdef PCSL_DEBUG pcsl_mem_free_impl0(ptr, filename, lineno);#else pcsl_mem_free_impl0(ptr);#endif } } else { /* When size == 0, realloc() acts just like free() */#ifdef PCSL_DEBUG pcsl_mem_free_impl0(ptr, filename, lineno);#else pcsl_mem_free_impl0(ptr);#endif } } else { /* sizes are the same, just return the same pointer */ newPtr = ptr; } return newPtr;}/** * FUNCTION: pcsl_mem_strdup_impl0() * TYPE: public operation * OVERVIEW: Duplicate the given string * INTERFACE: * parameters: s1 String to duplicate * filename Filename where allocation occured * lineno Line number where allocation occured * returns: pointer to the duplicate string * */#ifdef PCSL_DEBUGchar*pcsl_mem_strdup_impl0(const char *s1, char* filename, int lineno) { char *p = (char *)pcsl_mem_malloc_impl0(strlen(s1) + 1, filename, lineno); if ( p != NULL ) { strcpy(p, s1); } return(p);}#elsechar*pcsl_mem_strdup_impl0(const char *s1) { char *p = (char *)pcsl_mem_malloc_impl0(strlen(s1) + 1); if ( p != NULL ) { strcpy(p, s1); } return(p);}#endif/** * FUNCTION: pcsl_mem_free_impl0() * TYPE: public operation * OVERVIEW: Free memory allocated from the private PCSL memory pool * INTERFACE: * parameters: ptr Pointer to allocated memory * filename Filename where allocation occured * lineno Line number where allocation occured * returns: <nothing> * */#ifdef PCSL_DEBUG voidpcsl_mem_free_impl0(void *ptr, char *filename, int lineno) { _PcslMemHdrPtr pcslMemoryHdr; if (ptr == NULL) { report("WARNING: Attempt to free NULL pointer\n"); print_alloc("freed", filename, lineno); } else if (((char*)ptr > PcslMemoryEnd) || ((char*)ptr < PcslMemoryStart)) { report("ERROR: Attempt to free memory out of scope: 0x%p\n", ptr); print_alloc("freed", filename, lineno); } else { pcslMemoryHdr = (_PcslMemHdrPtr)((char*)ptr -sizeof(_PcslMemHdr)); if (pcslMemoryHdr->magic != MAGIC) { report("ERROR: Attempt to free corrupted memory: 0x%p\n", ptr); print_alloc("freed", filename, lineno); } else if (pcslMemoryHdr->free != 0) { report("ERROR: Attempt to free memory twice: 0x%p\n", ptr); print_alloc("freed", filename, lineno); } else { PcslMemoryAllocated -= pcslMemoryHdr->size; /* The memory block header is valid, now check the guard data */ if (pcslMemoryHdr->guard != GUARD_WORD) { report("ERROR: Possible memory underrun: 0x%p\n", ptr); print_alloc("allocated", pcslMemoryHdr->filename, pcslMemoryHdr->lineno); print_alloc("freed", filename, lineno); } else if (verify_tail_guard_data(pcslMemoryHdr)) { report("ERROR: Possible memory overrun: 0x%p\n", ptr); print_alloc("allocated", pcslMemoryHdr->filename, pcslMemoryHdr->lineno); print_alloc("freed", filename, lineno); }#if PCSL_TRACE_MEMORY report("DEBUG: free %d bytes: 0x%p\n", pcslMemoryHdr->size, ptr); print_alloc("allocated", pcslMemoryHdr->filename, pcslMemoryHdr->lineno); print_alloc("freed", filename, lineno);#endif pcslMemoryHdr->free = 1; } } /* end of else */}#elsevoidpcsl_mem_free_impl0(void *ptr) { _PcslMemHdrPtr pcslMemoryHdr; if (ptr == NULL) { } else if (((char*)ptr > PcslMemoryEnd) || ((char*)ptr < PcslMemoryStart)) { } else { pcslMemoryHdr = (_PcslMemHdrPtr)((char*)ptr -sizeof(_PcslMemHdr)); if (pcslMemoryHdr->magic != MAGIC) { } else if (pcslMemoryHdr->free != 0) { } else { pcslMemoryHdr->free = 1; } } /* end of else */}#endif#ifdef PCSL_DEBUG/** * @internal * * FUNCTION: verify_tail_guard_data() * TYPE: private operation * OVERVIEW: Verify guard data at the end of the memory is valid * INTERFACE: * parameters: pcslMemoryHdr Pointer to memory block header * returns: 0 if guard data is valid; otherwise, the byte position * of the first incorrect guard data byte * */static intverify_tail_guard_data(_PcslMemHdrPtr pcslMemoryHdr) { void* guardPos; int guardSize; int i; guardSize = pcslMemoryHdr->guardSize; guardPos = (void*)((char*)pcslMemoryHdr + sizeof(_PcslMemHdr) + pcslMemoryHdr->size - guardSize - 1); for(i = 1; i <= guardSize; i++) { if (((unsigned char*)guardPos)[i] != GUARD_BYTE) { return i; } } return 0;}#endif/** * * FUNCTION: pcsl_mem_get_total_heap_impl0() * TYPE: public operation * OVERVIEW: Get the total amount of available heap * INTERFACE: * parameters: <none> * returns: The total amount of available heap * */intpcsl_mem_get_total_heap_impl0() { return (PcslMemoryEnd - PcslMemoryStart);}/** * FUNCTION: pcsl_mem_get_free_heap_impl0() * TYPE: public operation * OVERVIEW: Get the current amount of unused heap * INTERFACE: * parameters: <none> * returns: The current amount of unused heap * */intpcsl_mem_get_free_heap_impl0() { _PcslMemHdrPtr pcslMemoryHdr; char* pcslMemoryPtr; int size = 0; for (pcslMemoryPtr = PcslMemoryStart; pcslMemoryPtr < PcslMemoryEnd; pcslMemoryPtr += pcslMemoryHdr->size + sizeof(_PcslMemHdr)) { pcslMemoryHdr = (_PcslMemHdrPtr)pcslMemoryPtr;#ifdef PCSL_DEBUG if (pcslMemoryHdr->magic != MAGIC) { report("ERROR: Corrupted start of memory header: 0x%p\n", pcslMemoryPtr); return -1; } if (pcslMemoryHdr->guard != GUARD_WORD) { report("ERROR: Corrupted end of memory header: 0x%p\n", pcslMemoryPtr); return -1; } /* The memory block header is valid, now check the guard data */ if (verify_tail_guard_data(pcslMemoryHdr)) { report("ERROR: Memory overrun: 0x%p\n", pcslMemoryPtr); print_alloc("allocated", pcslMemoryHdr->filename, pcslMemoryHdr->lineno); }#endif if (pcslMemoryHdr->free != 1) { size += pcslMemoryHdr->size; } } return (pcsl_mem_get_total_heap_impl0() - size);}/* Set countMemoryLeaksOnly = 0 in order to get more verbose information */int pcsl_mem_malloc_dump_impl0(int countMemoryLeaksOnly){ char *localpcslMallocMemPtr = NULL; char *localpcslMallocMemStart = PcslMemoryStart; char *localpcslMallocMemEnd = PcslMemoryEnd; _PcslMemHdrPtr localpcslMallocMemHdr = NULL; int numberOfAllocatedBlocks = 0; REPORT3("PcslMemory=0x%p PcslMemoryStart=0x%p PcslMemoryEnd=0x%p\n", PcslMemory, PcslMemoryStart, PcslMemoryEnd); for (localpcslMallocMemPtr = localpcslMallocMemStart; localpcslMallocMemPtr < localpcslMallocMemEnd; localpcslMallocMemPtr += localpcslMallocMemHdr->size + sizeof(_PcslMemHdr)) { localpcslMallocMemHdr = (_PcslMemHdrPtr) localpcslMallocMemPtr; if (localpcslMallocMemHdr->magic != MAGIC) { REPORT1("ERROR: memory corruption at 0x%p\n", localpcslMallocMemPtr); return -1; } else { if (countMemoryLeaksOnly == 0) { REPORT4("hdr 0x%p free=%d size=%d address=0x%p\n", localpcslMallocMemHdr, localpcslMallocMemHdr->free, localpcslMallocMemHdr->size, (void *)(((char *)localpcslMallocMemHdr) + sizeof(_PcslMemHdr))); } if (localpcslMallocMemHdr->free != 1) { numberOfAllocatedBlocks += 1;#ifdef PCSL_DEBUG report("WARNING: memory leak: size=%d address=0x%p\n", localpcslMallocMemHdr->size, (void*)((char*)localpcslMallocMemHdr + sizeof(_PcslMemHdr))); print_alloc("allocated", localpcslMallocMemHdr->filename, localpcslMallocMemHdr->lineno);#endif } } } return numberOfAllocatedBlocks;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -