malloc和Memory_alloc的区别
一、DSP的堆分为系统堆(system heap)和用户创建的堆
Malloc是标准C的函数,它是从system heap上分配buffer。
a)在使用BIOS的情况下,通过BIOS.heapSize = 0x2000设定system heap的大小,
b)在不使用BIOS的情况下要在cmd文件中用-heap设定sytem heap的大小。
函数API是 void *malloc(unsigned int num_bytes)进行系统堆分配,void free(void *)进行释放;
Memory_alloc是从用户创建的heap(不是system heap)上分配bufer,它是BIOS的API,有下面4个入参。用户通过编辑BIOS的cfg文件可以创建自己的heap,参见下文。
Memory_alloc(heap_handle,size,align,error_block);
参数1 heap handler,即指向heap object的handler
参数2 size 需要分配的heap的size
参数3 align 对齐特性要求
参数4 Error_block 可以设成NULL
Memory_alloc得到的buffer用Memory_free释放,API有3个参数
Memory_free(heap_handle,block,size);
参数1 Heap_Handle,即指向heap object的handler
参数2 block, 即要释放的buffer的指针
参数3 size, 即要释放的buffer的size
二、DSP中用户堆的创建
/*
* The BIOS module will create the default heap for the system.
* Specify the size of this default heap.
*/
BIOS.heapSize = 0x2000; // 制定系统堆的大小。
var heapBufParams = new HeapBuf.Params;
heapBufParams.blockSize = 32; // heapBuf是以block为单位分配的
heapBufParams.numBlocks = 2;
heapBufParams.align = 8;
Program.global.task0Heap = HeapBuf.create(heapBufParams);
var heapMemParams2 = new HeapMem.Params;
heapMemParams2.size = 512; // heapMem是要多少分多少
heapMemParams2.align = 8;
Program.global.task1Heap = HeapMem.create(heapMemParams2);
下面是这3个heap在memory中的示意图,上图的物理地址是根据后面运行的结果推出来的,heap的具体位置是在link的时候确定的。
三、用户堆的存储段(map文件中的线索)
Map文件显示了link以后这些heap被分配在哪个section:
.far 0 0080d4a0 00003a68 UNINITIALIZED
0080d4a0 00002a50 memory_pe66.oe66 (.far)
// 从上面可以看出BIOS中定义的heap段被分配在.far section
0080fef0 00001000 memory_pe66.oe66 (.far:taskStackSection)
00810ef0 00000010 memory.obj (.far)
00810f00 00000008 rts6600_elf.lib : trgdrv.obj (.far)
四、用户堆的的使用
1.把BIOS中的heapBuf或heapMem转行成heap handle.
调用BIOS API获取heap的handler
IHeap_Handle heap = HeapBuf_Handle_upCast(task0Heap);
调用Memory_alloc()分配block buffer
for (i = 0; i < 2; i++) {
bufs[i] = Memory_alloc(heap, 32, 0, NULL);
}
调用Memory_free()释放block buffer
for (i = 0; i < 2; i++) {
Memory_free(heap, bufs[i], 32);
}
在watch窗口中可以观察task0Heap
初始化的状态
*(task0Heap) struct ti_sysbios_heaps_HeapBuf_Object {...} 0x008149F8
__fxns struct ti_sysbios_heaps_HeapBuf_Fxns__ * 0x00812C70
blockSize unsigned int 32
align unsigned int 8
numBlocks unsigned int 2
bufSize unsigned int 64
buf char * 0x0080D4A0
numFreeBlocks unsigned int 2
minFreeBlocks unsigned int 4294967295
__dummy char 0x60
分配了两个block以后的状态
*(task0Heap) struct ti_sysbios_heaps_HeapBuf_Object {...}
__fxns struct ti_sysbios_heaps_HeapBuf_Fxns__ * 0x00812C70
blockSize unsigned int 32
align unsigned int 8
numBlocks unsigned int 2
bufSize unsigned int 64
buf char * 0x0080D4A0
numFreeBlocks unsigned int 0
minFreeBlocks unsigned int 4294967295
__dummy char 0x18
获取buffer handler
IHeap_Handle heap = HeapMem_Handle_upCast(task1Heap);
连续分配3个buffer
bufs[0] = Memory_alloc(heap, 128, 0, NULL);
bufs[1] = Memory_alloc(heap, 64, 0, NULL);
bufs[2] = Memory_alloc(heap, 32, 0, NULL);
在watch窗口观察到的结果是:
bufs[0] void * 0x0080D4E0
bufs[1] void * 0x0080D560
bufs[2] void * 0x0080D5A0
初始化以后的状态
*(task1Heap) struct ti_sysbios_heaps_HeapMem_Object {...}
|- __fxns struct ti_sysbios_heaps_HeapMem_Fxns__ * 0x00812C98
|- align unsigned int 8
|- buf char * 0x0080D4E0
|- head struct ti_sysbios_heaps_HeapMem_Header {...}
|- next struct ti_sysbios_heaps_HeapMem_Header * 0x0080D4E0
|- size unsigned int 512
分配了3个buffer以后的状态
*(task1Heap) struct ti_sysbios_heaps_HeapMem_Object {...} 0x00814A20
|- __fxns struct ti_sysbios_heaps_HeapMem_Fxns__ * 0x00812C98
|- align unsigned int 8
|- buf char * 0x0080D4E0
|- head struct ti_sysbios_heaps_HeapMem_Header {...}
|- next struct ti_sysbios_heaps_HeapMem_Header * 0x0080D5C0
|- size unsigned int 512
继续执行
Memory_free(heap, bufs[1], 64);
Memory_free(heap, bufs[2], 32);
bufs[3] = Memory_alloc(heap, 16, 0, NULL);
在watch窗口观察到的结果是:
bufs[3] void * 0x0080D560
heapMem对象的变化是:
*(task1Heap) struct ti_sysbios_heaps_HeapMem_Object {...} 0x00814A20
|- __fxns struct ti_sysbios_heaps_HeapMem_Fxns__ * 0x00812C98
|- align unsigned int 8
|- buf char * 0x0080D4E0
|- head struct ti_sysbios_heaps_HeapMem_Header {...}
|- next struct ti_sysbios_heaps_HeapMem_Header * 0x0080D570
|- size unsigned int 512
可以看出bufs[3]是在bufs[2]释放后的位置上分配的。