libubox
C utility functions for OpenWrt.
blob.c File Reference
#include "blob.h"

Go to the source code of this file.

Functions

static bool blob_buffer_grow (struct blob_buf *buf, int minlen)
 
static void blob_init (struct blob_attr *attr, int id, unsigned int len)
 
static struct blob_attroffset_to_attr (struct blob_buf *buf, int offset)
 
static int attr_to_offset (struct blob_buf *buf, struct blob_attr *attr)
 
bool blob_buf_grow (struct blob_buf *buf, int required)
 
static struct blob_attrblob_add (struct blob_buf *buf, struct blob_attr *pos, int id, int payload)
 
int blob_buf_init (struct blob_buf *buf, int id)
 
void blob_buf_free (struct blob_buf *buf)
 
void blob_fill_pad (struct blob_attr *attr)
 
void blob_set_raw_len (struct blob_attr *attr, unsigned int len)
 
struct blob_attrblob_new (struct blob_buf *buf, int id, int payload)
 
struct blob_attrblob_put_raw (struct blob_buf *buf, const void *ptr, unsigned int len)
 
struct blob_attrblob_put (struct blob_buf *buf, int id, const void *ptr, unsigned int len)
 
void * blob_nest_start (struct blob_buf *buf, int id)
 
void blob_nest_end (struct blob_buf *buf, void *cookie)
 
bool blob_check_type (const void *ptr, unsigned int len, int type)
 
static int blob_parse_attr (struct blob_attr *attr, size_t attr_len, struct blob_attr **data, const struct blob_attr_info *info, int max)
 
int blob_parse_untrusted (struct blob_attr *attr, size_t attr_len, struct blob_attr **data, const struct blob_attr_info *info, int max)
 
int blob_parse (struct blob_attr *attr, struct blob_attr **data, const struct blob_attr_info *info, int max)
 
bool blob_attr_equal (const struct blob_attr *a1, const struct blob_attr *a2)
 
struct blob_attrblob_memdup (struct blob_attr *attr)
 

Variables

static const size_t blob_type_minlen [BLOB_ATTR_LAST]
 

Function Documentation

◆ attr_to_offset()

static int attr_to_offset ( struct blob_buf buf,
struct blob_attr attr 
)
inlinestatic

Definition at line 51 of file blob.c.

52 {
53  return (char *)attr - (char *) buf->buf + BLOB_COOKIE;
54 }
#define BLOB_COOKIE
Definition: blob.h:31
void * buf
Definition: blob.h:68
Here is the caller graph for this function:

◆ blob_add()

static struct blob_attr* blob_add ( struct blob_buf buf,
struct blob_attr pos,
int  id,
int  payload 
)
static

Definition at line 71 of file blob.c.

72 {
73  int offset = attr_to_offset(buf, pos);
74  int required = (offset - BLOB_COOKIE + sizeof(struct blob_attr) + payload) - buf->buflen;
75  struct blob_attr *attr;
76 
77  if (required > 0) {
78  if (!blob_buf_grow(buf, required))
79  return NULL;
80  attr = offset_to_attr(buf, offset);
81  } else {
82  attr = pos;
83  }
84 
85  blob_init(attr, id, payload + sizeof(struct blob_attr));
86  blob_fill_pad(attr);
87  return attr;
88 }
static void blob_init(struct blob_attr *attr, int id, unsigned int len)
Definition: blob.c:36
static int attr_to_offset(struct blob_buf *buf, struct blob_attr *attr)
Definition: blob.c:51
bool blob_buf_grow(struct blob_buf *buf, int required)
Definition: blob.c:57
void blob_fill_pad(struct blob_attr *attr)
Definition: blob.c:113
static struct blob_attr * offset_to_attr(struct blob_buf *buf, int offset)
Definition: blob.c:44
Definition: blob.h:52
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_attr_equal()

bool blob_attr_equal ( const struct blob_attr a1,
const struct blob_attr a2 
)

Definition at line 311 of file blob.c.

312 {
313  if (!a1 && !a2)
314  return true;
315 
316  if (!a1 || !a2)
317  return false;
318 
319  if (blob_pad_len(a1) != blob_pad_len(a2))
320  return false;
321 
322  return !memcmp(a1, a2, blob_pad_len(a1));
323 }
static size_t blob_pad_len(const struct blob_attr *attr)
Definition: blob.h:118
Here is the call graph for this function:

◆ blob_buf_free()

void blob_buf_free ( struct blob_buf buf)

Definition at line 104 of file blob.c.

105 {
106  free(buf->buf);
107  buf->buf = NULL;
108  buf->head = NULL;
109  buf->buflen = 0;
110 }
int buflen
Definition: blob.h:67
struct blob_attr * head
Definition: blob.h:65
Here is the caller graph for this function:

◆ blob_buf_grow()

bool blob_buf_grow ( struct blob_buf buf,
int  required 
)

Definition at line 57 of file blob.c.

58 {
59  int offset_head = attr_to_offset(buf, buf->head);
60 
61  if ((buf->buflen + required) > BLOB_ATTR_LEN_MASK)
62  return false;
63  if (!buf->grow || !buf->grow(buf, required))
64  return false;
65 
66  buf->head = offset_to_attr(buf, offset_head);
67  return true;
68 }
#define BLOB_ATTR_LEN_MASK
Definition: blob.h:48
bool(* grow)(struct blob_buf *buf, int minlen)
Definition: blob.h:66
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_buf_init()

int blob_buf_init ( struct blob_buf buf,
int  id 
)

Definition at line 91 of file blob.c.

92 {
93  if (!buf->grow)
94  buf->grow = blob_buffer_grow;
95 
96  buf->head = buf->buf;
97  if (blob_add(buf, buf->buf, id, 0) == NULL)
98  return -ENOMEM;
99 
100  return 0;
101 }
static bool blob_buffer_grow(struct blob_buf *buf, int minlen)
Definition: blob.c:22
static struct blob_attr * blob_add(struct blob_buf *buf, struct blob_attr *pos, int id, int payload)
Definition: blob.c:71
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_buffer_grow()

static bool blob_buffer_grow ( struct blob_buf buf,
int  minlen 
)
static

Definition at line 22 of file blob.c.

23 {
24  struct blob_buf *new;
25  int delta = ((minlen / 256) + 1) * 256;
26  new = realloc(buf->buf, buf->buflen + delta);
27  if (new) {
28  buf->buf = new;
29  memset(buf->buf + buf->buflen, 0, delta);
30  buf->buflen += delta;
31  }
32  return !!new;
33 }
Definition: blob.h:64
Here is the caller graph for this function:

◆ blob_check_type()

bool blob_check_type ( const void *  ptr,
unsigned int  len,
int  type 
)

Definition at line 202 of file blob.c.

203 {
204  const char *data = ptr;
205 
206  if (type >= BLOB_ATTR_LAST)
207  return false;
208 
209  if (type >= BLOB_ATTR_INT8 && type <= BLOB_ATTR_INT64) {
210  if (len != blob_type_minlen[type])
211  return false;
212  } else {
213  if (len < blob_type_minlen[type])
214  return false;
215  }
216 
217  if (type == BLOB_ATTR_STRING && data[len - 1] != 0)
218  return false;
219 
220  return true;
221 }
static const size_t blob_type_minlen[BLOB_ATTR_LAST]
Definition: blob.c:192
@ BLOB_ATTR_STRING
Definition: blob.h:37
@ BLOB_ATTR_LAST
Definition: blob.h:43
@ BLOB_ATTR_INT64
Definition: blob.h:41
@ BLOB_ATTR_INT8
Definition: blob.h:38
char data[]
Definition: blob.h:1
uint8_t type
Definition: udebug-proto.h:0
Here is the caller graph for this function:

◆ blob_fill_pad()

void blob_fill_pad ( struct blob_attr attr)

Definition at line 113 of file blob.c.

114 {
115  char *buf = (char *) attr;
116  int len = blob_pad_len(attr);
117  int delta = len - blob_raw_len(attr);
118 
119  if (delta > 0)
120  memset(buf + len - delta, 0, delta);
121 }
static size_t blob_raw_len(const struct blob_attr *attr)
Definition: blob.h:109
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_init()

static void blob_init ( struct blob_attr attr,
int  id,
unsigned int  len 
)
static

Definition at line 36 of file blob.c.

37 {
38  len &= BLOB_ATTR_LEN_MASK;
39  len |= (id << BLOB_ATTR_ID_SHIFT) & BLOB_ATTR_ID_MASK;
40  attr->id_len = cpu_to_be32(len);
41 }
#define BLOB_ATTR_ID_MASK
Definition: blob.h:46
#define BLOB_ATTR_ID_SHIFT
Definition: blob.h:47
uint32_t id_len
Definition: blob.h:53
#define cpu_to_be32(x)
Definition: utils.h:163
Here is the caller graph for this function:

◆ blob_memdup()

struct blob_attr* blob_memdup ( struct blob_attr attr)

Definition at line 326 of file blob.c.

327 {
328  struct blob_attr *ret;
329  int size = blob_pad_len(attr);
330 
331  ret = malloc(size);
332  if (!ret)
333  return NULL;
334 
335  memcpy(ret, attr, size);
336  return ret;
337 }
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_nest_end()

void blob_nest_end ( struct blob_buf buf,
void *  cookie 
)

Definition at line 185 of file blob.c.

186 {
187  struct blob_attr *attr = offset_to_attr(buf, (unsigned long) cookie);
188  blob_set_raw_len(attr, blob_pad_len(attr) + blob_len(buf->head));
189  buf->head = attr;
190 }
void blob_set_raw_len(struct blob_attr *attr, unsigned int len)
Definition: blob.c:124
static size_t blob_len(const struct blob_attr *attr)
Definition: blob.h:100
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_nest_start()

void* blob_nest_start ( struct blob_buf buf,
int  id 
)

Definition at line 175 of file blob.c.

176 {
177  unsigned long offset = attr_to_offset(buf, buf->head);
178  buf->head = blob_new(buf, id, 0);
179  if (!buf->head)
180  return NULL;
181  return (void *) offset;
182 }
struct blob_attr * blob_new(struct blob_buf *buf, int id, int payload)
Definition: blob.c:132
Here is the call graph for this function:

◆ blob_new()

struct blob_attr* blob_new ( struct blob_buf buf,
int  id,
int  payload 
)

Definition at line 132 of file blob.c.

133 {
134  struct blob_attr *attr;
135 
136  attr = blob_add(buf, blob_next(buf->head), id, payload);
137  if (!attr)
138  return NULL;
139 
140  blob_set_raw_len(buf->head, blob_pad_len(buf->head) + blob_pad_len(attr));
141  return attr;
142 }
static struct blob_attr * blob_next(const struct blob_attr *attr)
Definition: blob.h:185
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_parse()

int blob_parse ( struct blob_attr attr,
struct blob_attr **  data,
const struct blob_attr_info info,
int  max 
)

Definition at line 296 of file blob.c.

297 {
298  struct blob_attr *pos;
299  int found = 0;
300  size_t rem;
301 
302  memset(data, 0, sizeof(struct blob_attr *) * max);
303  blob_for_each_attr(pos, attr, rem) {
304  found += blob_parse_attr(pos, rem, data, info, max);
305  }
306 
307  return found;
308 }
static int blob_parse_attr(struct blob_attr *attr, size_t attr_len, struct blob_attr **data, const struct blob_attr_info *info, int max)
Definition: blob.c:224
#define blob_for_each_attr(pos, attr, rem)
Definition: blob.h:251
Here is the call graph for this function:

◆ blob_parse_attr()

static int blob_parse_attr ( struct blob_attr attr,
size_t  attr_len,
struct blob_attr **  data,
const struct blob_attr_info info,
int  max 
)
static

Definition at line 224 of file blob.c.

225 {
226  int id;
227  size_t len;
228  int found = 0;
229  size_t data_len;
230 
231  if (!attr || attr_len < sizeof(struct blob_attr))
232  return 0;
233 
234  id = blob_id(attr);
235  if (id >= max)
236  return 0;
237 
238  len = blob_raw_len(attr);
239  if (len > attr_len || len < sizeof(struct blob_attr))
240  return 0;
241 
242  data_len = blob_len(attr);
243  if (data_len > len)
244  return 0;
245 
246  if (info) {
247  int type = info[id].type;
248 
249  if (type < BLOB_ATTR_LAST) {
250  if (!blob_check_type(blob_data(attr), data_len, type))
251  return 0;
252  }
253 
254  if (info[id].minlen && len < info[id].minlen)
255  return 0;
256 
257  if (info[id].maxlen && len > info[id].maxlen)
258  return 0;
259 
260  if (info[id].validate && !info[id].validate(&info[id], attr))
261  return 0;
262  }
263 
264  if (!data[id])
265  found++;
266 
267  data[id] = attr;
268  return found;
269 }
bool blob_check_type(const void *ptr, unsigned int len, int type)
Definition: blob.c:202
static void * blob_data(const struct blob_attr *attr)
Definition: blob.h:75
static unsigned int blob_id(const struct blob_attr *attr)
Definition: blob.h:84
unsigned int type
Definition: blob.h:58
uint32_t id
Definition: udebug-proto.h:2
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_parse_untrusted()

int blob_parse_untrusted ( struct blob_attr attr,
size_t  attr_len,
struct blob_attr **  data,
const struct blob_attr_info info,
int  max 
)

Definition at line 272 of file blob.c.

273 {
274  struct blob_attr *pos;
275  size_t len = 0;
276  int found = 0;
277  size_t rem;
278 
279  if (!attr || attr_len < sizeof(struct blob_attr))
280  return 0;
281 
282  len = blob_raw_len(attr);
283  if (attr_len < len)
284  return 0;
285 
286  memset(data, 0, sizeof(struct blob_attr *) * max);
287  blob_for_each_attr_len(pos, attr, len, rem) {
288  found += blob_parse_attr(pos, rem, data, info, max);
289  }
290 
291  return found;
292 }
#define blob_for_each_attr_len(pos, attr, attr_len, rem)
Definition: blob.h:258
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_put()

struct blob_attr* blob_put ( struct blob_buf buf,
int  id,
const void *  ptr,
unsigned int  len 
)

Definition at line 161 of file blob.c.

162 {
163  struct blob_attr *attr;
164 
165  attr = blob_new(buf, id, len);
166  if (!attr)
167  return NULL;
168 
169  if (ptr)
170  memcpy(blob_data(attr), ptr, len);
171  return attr;
172 }
Here is the call graph for this function:
Here is the caller graph for this function:

◆ blob_put_raw()

struct blob_attr* blob_put_raw ( struct blob_buf buf,
const void *  ptr,
unsigned int  len 
)

Definition at line 145 of file blob.c.

146 {
147  struct blob_attr *attr;
148 
149  if (len < sizeof(struct blob_attr) || !ptr)
150  return NULL;
151 
152  attr = blob_add(buf, blob_next(buf->head), 0, len - sizeof(struct blob_attr));
153  if (!attr)
154  return NULL;
155  blob_set_raw_len(buf->head, blob_pad_len(buf->head) + len);
156  memcpy(attr, ptr, len);
157  return attr;
158 }
Here is the call graph for this function:

◆ blob_set_raw_len()

void blob_set_raw_len ( struct blob_attr attr,
unsigned int  len 
)

Definition at line 124 of file blob.c.

125 {
126  len &= BLOB_ATTR_LEN_MASK;
128  attr->id_len |= cpu_to_be32(len);
129 }
Here is the caller graph for this function:

◆ offset_to_attr()

static struct blob_attr* offset_to_attr ( struct blob_buf buf,
int  offset 
)
inlinestatic

Definition at line 44 of file blob.c.

45 {
46  void *ptr = (char *)buf->buf + offset - BLOB_COOKIE;
47  return ptr;
48 }
Here is the caller graph for this function:

Variable Documentation

◆ blob_type_minlen

const size_t blob_type_minlen[BLOB_ATTR_LAST]
static
Initial value:
= {
[BLOB_ATTR_INT8] = sizeof(uint8_t),
[BLOB_ATTR_INT16] = sizeof(uint16_t),
[BLOB_ATTR_INT32] = sizeof(uint32_t),
[BLOB_ATTR_INT64] = sizeof(uint64_t),
[BLOB_ATTR_DOUBLE] = sizeof(double),
}
@ BLOB_ATTR_INT16
Definition: blob.h:39
@ BLOB_ATTR_DOUBLE
Definition: blob.h:42
@ BLOB_ATTR_INT32
Definition: blob.h:40

Definition at line 192 of file blob.c.