标签:
Spiceserver内存操作部分也是整个项目用的比较多的模块,它自己封装了一套内存操作的函数,要掌握Spiceserver必须要掌握这些函数的使用,本篇我主要介绍一下我在阅读和使用这些函数及宏的一些理解,可能不是很全面,甚至理解不是很到位,后面有新的理解和发现再对blog进行更新。
void *spice_malloc(size_t n_bytes) SPICE_GNUC_MALLOC SPICE_GNUC_ALLOC_SIZE(1); void *spice_malloc0(size_t n_bytes) SPICE_GNUC_MALLOC SPICE_GNUC_ALLOC_SIZE(1); void *spice_realloc(void *mem, size_t n_bytes) SPICE_GNUC_WARN_UNUSED_RESULT; void *spice_malloc_n(size_t n_blocks, size_t n_block_bytes) SPICE_GNUC_MALLOC SPICE_GNUC_ALLOC_SIZE2(1,2); void *spice_malloc_n_m(size_t n_blocks, size_t n_block_bytes, size_t extra_size) SPICE_GNUC_MALLOC; void *spice_malloc0_n(size_t n_blocks, size_t n_block_bytes) SPICE_GNUC_MALLOC SPICE_GNUC_ALLOC_SIZE2(1,2); void *spice_realloc_n(void *mem, size_t n_blocks, size_t n_block_bytes) SPICE_GNUC_WARN_UNUSED_RESULT;
#define SPICE_GNUC_MALLOC __attribute__((__malloc__)) #define SPICE_GNUC_ALLOC_SIZE(x) __attribute__((__alloc_size__(x))) #define SPICE_GNUC_ALLOC_SIZE2(x,y) __attribute__((__alloc_size__(x,y)))有关这些宏的定义在https://developer.gnome.org/glib/stable/glib-Miscellaneous-Macros.html中可以找到。
void *spice_malloc(size_t n_bytes) { void *mem; if (SPICE_LIKELY(n_bytes)) {/* 用于判断n_bytes是不是不等于0 */ mem = malloc(n_bytes); if (SPICE_LIKELY(mem != NULL)) {/* 分配内存不等于NULL */ return mem; } MALLOC_ERROR("unable to allocate %lu bytes", (unsigned long)n_bytes); } return NULL; }
Spiceserver中比较常用的内存块结构:RedDataChunk、SpiceChunks,我这里简单写了一个有关它们使用的Demo,我先将一个文件内容读取到RedDataChunk结构中,然后将RedDataChunk结构中的数据拷贝到SpiceChunks中,使用了Spiceserver中的一些自定义函数,代码如下:
#include <unistd.h> #include <stdio.h> #include "mem.h" #define PACKAGE_LEN 512 /* 读取文件,将文件内容保存在red_chunk中 */ void get_chunk_from_file(const char *filepath, RedDataChunk *red_chunk) { FILE *file = fopen("./test.txt", "rb"); if( file == NULL ){ return; } RedDataChunk *cur_chunk = red_chunk; while(TRUE){ uint8_t *pBuff = spice_malloc0(PACKAGE_LEN+1);/* 分配内存 */ if( pBuff == NULL ){ break; } uint32_t read_len = fread(pBuff, 1, PACKAGE_LEN, file); if( read_len > 0 ){ RedDataChunk *chunk = spice_new(RedDataChunk, 1); chunk->data_size = read_len; chunk->data = pBuff; chunk ->prev_chunk = cur_chunk; chunk->next_chunk = NULL; cur_chunk->next_chunk = chunk; cur_chunk = chunk; } else{/* 未能读到数据 */ free(pBuff); break; } } fclose(file); } /* 释放RedDataChunk结构内存 */ void free_red_chunk(RedDataChunk *red_chunk) { RedDataChunk *cur_chunk = red_chunk->next_chunk; RedDataChunk *next_chunk; while(cur_chunk){ next_chunk = cur_chunk->next_chunk; free(cur_chunk); cur_chunk = next_chunk; } } /* 将保存在red_chunk中的数据拷贝到spice_chunks中 */ SpiceChunks *get_spicechunk(RedDataChunk *red_chunk) { int i; SpiceChunks *data; RedDataChunk *chunk; /* 计算RedDataChunk块的个数注意要去除头结点 */ for (i = 0, chunk = red_chunk->next_chunk; chunk != NULL; chunk = chunk->next_chunk) { i++; } data = spice_chunks_new(i);/* 分配SpiceChunks内存 */ data->data_size = 0; data->flags |= SPICE_CHUNKS_FLAGS_FREE; for (i = 0, chunk = red_chunk->next_chunk; chunk != NULL && i < data->num_chunks; chunk = chunk->next_chunk, i++) { data->chunk[i].data = chunk->data; data->chunk[i].len = chunk->data_size; data->data_size += chunk->data_size; } return data; } void print_chunks(SpiceChunks *chunks) { int i; for(i=0; i<chunks->num_chunks; i++){ printf("%s", chunks->chunk[i].data); } } int main(int argc, char **argv) { RedDataChunk red_chunks; get_chunk_from_file( "./test.txt", &red_chunks ); SpiceChunks *spice_chunks = get_spicechunk(&red_chunks); free_red_chunk(&red_chunks); print_chunks(spice_chunks);/* 打印 */ spice_chunks_destroy(spice_chunks); return 0; }
标签:
原文地址:http://blog.csdn.net/dailongjian2008/article/details/51355077