fix fd leak on connection failure
[rofl0r-microsocks.git] / sblist.c
blob96bbebcac38ab59cd1e81414694020fad50b4793
1 #undef _POSIX_C_SOURCE
2 #define _POSIX_C_SOURCE 200809L
3 #include "sblist.h"
4 #include <limits.h>
5 #include <stdlib.h>
6 #include <string.h>
7 #define MY_PAGE_SIZE 4096
9 sblist* sblist_new(size_t itemsize, size_t blockitems) {
10 sblist* ret = (sblist*) malloc(sizeof(sblist));
11 sblist_init(ret, itemsize, blockitems);
12 return ret;
15 static void sblist_clear(sblist* l) {
16 l->items = NULL;
17 l->capa = 0;
18 l->count = 0;
21 void sblist_init(sblist* l, size_t itemsize, size_t blockitems) {
22 if(l) {
23 l->blockitems = blockitems ? blockitems : MY_PAGE_SIZE / itemsize;
24 l->itemsize = itemsize;
25 sblist_clear(l);
29 void sblist_free_items(sblist* l) {
30 if(l) {
31 if(l->items) free(l->items);
32 sblist_clear(l);
36 void sblist_free(sblist* l) {
37 if(l) {
38 sblist_free_items(l);
39 free(l);
43 char* sblist_item_from_index(sblist* l, size_t idx) {
44 return l->items + (idx * l->itemsize);
47 void* sblist_get(sblist* l, size_t item) {
48 if(item < l->count) return (void*) sblist_item_from_index(l, item);
49 return NULL;
52 int sblist_set(sblist* l, void* item, size_t pos) {
53 if(pos >= l->count) return 0;
54 memcpy(sblist_item_from_index(l, pos), item, l->itemsize);
55 return 1;
58 int sblist_grow_if_needed(sblist* l) {
59 char* temp;
60 if(l->count == l->capa) {
61 temp = realloc(l->items, (l->capa + l->blockitems) * l->itemsize);
62 if(!temp) return 0;
63 l->capa += l->blockitems;
64 l->items = temp;
66 return 1;
69 int sblist_add(sblist* l, void* item) {
70 if(!sblist_grow_if_needed(l)) return 0;
71 l->count++;
72 return sblist_set(l, item, l->count - 1);