sdm845: Select VBOOT_MIGRATE_WORKING_DATA, now required
[coreboot.git] / src / commonlib / iobuf.c
blobb73ee1929e9af44abf5297b485c07eb289dd6984
1 /*
2 * This file is part of the coreboot project.
4 * Copyright 2017 Google Inc.
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; version 2 of the License.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
16 #include <commonlib/endian.h>
17 #include <commonlib/iobuf.h>
18 #include <string.h>
20 static int ibuf_check_size(const struct ibuf *ib, size_t sz)
22 if (ibuf_remaining(ib) < sz)
23 return -1;
25 return 0;
28 void ibuf_init(struct ibuf *ib, const void *b, size_t sz)
30 ib->b = b;
31 ib->n_read = 0;
32 ib->capacity = sz;
35 void ibuf_from_obuf(struct ibuf *ib, const struct obuf *ob)
37 ibuf_init(ib, ob->b, ob->n_written);
40 int ibuf_splice(const struct ibuf *src, struct ibuf *dst, size_t off, size_t sz)
42 size_t end = off + sz;
43 size_t capacity = ibuf_capacity(src);
44 size_t nr_read = ibuf_nr_read(src);
46 if (end < off || end < sz || end > capacity)
47 return -1;
49 ibuf_init(dst, &src->b[off], sz);
51 /* Handle previously read data in src. */
52 if (off < nr_read)
53 dst->n_read = nr_read - off;
55 return 0;
58 int ibuf_splice_current(const struct ibuf *src, struct ibuf *dst, size_t sz)
60 return ibuf_splice(src, dst, ibuf_nr_read(src), sz);
63 int ibuf_split(const struct ibuf *src, struct ibuf *a, struct ibuf *b,
64 size_t boundary)
66 if (ibuf_splice(src, a, 0, boundary))
67 return -1;
69 return ibuf_splice(src, b, boundary, ibuf_capacity(src) - boundary);
72 const void *ibuf_oob_drain(struct ibuf *ib, size_t sz)
74 const void *b;
76 if (ibuf_check_size(ib, sz))
77 return NULL;
79 b = &ib->b[ib->n_read];
80 ib->n_read += sz;
82 return b;
85 int ibuf_read(struct ibuf *ib, void *data, size_t sz)
87 const void *b = ibuf_oob_drain(ib, sz);
89 if (b == NULL)
90 return -1;
92 memcpy(data, b, sz);
94 return 0;
97 int ibuf_read_be8(struct ibuf *ib, uint8_t *v)
99 size_t sz = sizeof(*v);
101 if (ibuf_check_size(ib, sz))
102 return -1;
104 *v = read_at_be8(ib->b, ib->n_read);
105 ib->n_read += sz;
107 return 0;
110 int ibuf_read_be16(struct ibuf *ib, uint16_t *v)
112 size_t sz = sizeof(*v);
114 if (ibuf_check_size(ib, sz))
115 return -1;
117 *v = read_at_be16(ib->b, ib->n_read);
118 ib->n_read += sz;
120 return 0;
123 int ibuf_read_be32(struct ibuf *ib, uint32_t *v)
125 size_t sz = sizeof(*v);
127 if (ibuf_check_size(ib, sz))
128 return -1;
130 *v = read_at_be32(ib->b, ib->n_read);
131 ib->n_read += sz;
133 return 0;
136 int ibuf_read_be64(struct ibuf *ib, uint64_t *v)
138 size_t sz = sizeof(*v);
140 if (ibuf_check_size(ib, sz))
141 return -1;
143 *v = read_at_be64(ib->b, ib->n_read);
144 ib->n_read += sz;
146 return 0;
149 int ibuf_read_le8(struct ibuf *ib, uint8_t *v)
151 size_t sz = sizeof(*v);
153 if (ibuf_check_size(ib, sz))
154 return -1;
156 *v = read_at_le8(ib->b, ib->n_read);
157 ib->n_read += sz;
159 return 0;
162 int ibuf_read_le16(struct ibuf *ib, uint16_t *v)
164 size_t sz = sizeof(*v);
166 if (ibuf_check_size(ib, sz))
167 return -1;
169 *v = read_at_le16(ib->b, ib->n_read);
170 ib->n_read += sz;
172 return 0;
175 int ibuf_read_le32(struct ibuf *ib, uint32_t *v)
177 size_t sz = sizeof(*v);
179 if (ibuf_check_size(ib, sz))
180 return -1;
182 *v = read_at_le32(ib->b, ib->n_read);
183 ib->n_read += sz;
185 return 0;
188 int ibuf_read_le64(struct ibuf *ib, uint64_t *v)
190 size_t sz = sizeof(*v);
192 if (ibuf_check_size(ib, sz))
193 return -1;
195 *v = read_at_le64(ib->b, ib->n_read);
196 ib->n_read += sz;
198 return 0;
201 int ibuf_read_n8(struct ibuf *ib, uint8_t *v)
203 return ibuf_read(ib, v, sizeof(*v));
206 int ibuf_read_n16(struct ibuf *ib, uint16_t *v)
208 return ibuf_read(ib, v, sizeof(*v));
211 int ibuf_read_n32(struct ibuf *ib, uint32_t *v)
213 return ibuf_read(ib, v, sizeof(*v));
216 int ibuf_read_n64(struct ibuf *ib, uint64_t *v)
218 return ibuf_read(ib, v, sizeof(*v));
221 static int obuf_check_size(const struct obuf *ob, size_t sz)
223 if (obuf_remaining(ob) < sz)
224 return -1;
226 return 0;
229 void obuf_init(struct obuf *ob, void *b, size_t sz)
231 ob->b = b;
232 ob->n_written = 0;
233 ob->capacity = sz;
236 int obuf_splice(const struct obuf *src, struct obuf *dst, size_t off, size_t sz)
238 size_t end = off + sz;
239 size_t capacity = obuf_capacity(src);
240 size_t nr_written = obuf_nr_written(src);
242 if (end < off || end < sz || end > capacity)
243 return -1;
245 obuf_init(dst, &src->b[off], sz);
247 /* Handle previously written data in src. */
248 if (off < nr_written)
249 dst->n_written = nr_written - off;
251 return 0;
254 int obuf_splice_current(const struct obuf *src, struct obuf *dst, size_t sz)
256 return obuf_splice(src, dst, obuf_nr_written(src), sz);
259 int obuf_split(const struct obuf *src, struct obuf *a, struct obuf *b,
260 size_t boundary)
262 if (obuf_splice(src, a, 0, boundary))
263 return -1;
265 return obuf_splice(src, b, boundary, obuf_capacity(src) - boundary);
268 void *obuf_oob_fill(struct obuf *ob, size_t sz)
270 void *b;
272 if (obuf_check_size(ob, sz))
273 return NULL;
275 b = &ob->b[ob->n_written];
276 ob->n_written += sz;
278 return b;
281 int obuf_write(struct obuf *ob, const void *data, size_t sz)
283 void *b;
285 b = obuf_oob_fill(ob, sz);
286 if (b == NULL)
287 return -1;
289 memcpy(b, data, sz);
291 return 0;
294 int obuf_write_be8(struct obuf *ob, uint8_t v)
296 size_t sz = sizeof(v);
298 if (obuf_check_size(ob, sz))
299 return -1;
301 write_at_be8(ob->b, v, ob->n_written);
302 ob->n_written += sz;
304 return 0;
307 int obuf_write_be16(struct obuf *ob, uint16_t v)
309 size_t sz = sizeof(v);
311 if (obuf_check_size(ob, sz))
312 return -1;
314 write_at_be16(ob->b, v, ob->n_written);
315 ob->n_written += sz;
317 return 0;
320 int obuf_write_be32(struct obuf *ob, uint32_t v)
322 size_t sz = sizeof(v);
324 if (obuf_check_size(ob, sz))
325 return -1;
327 write_at_be32(ob->b, v, ob->n_written);
328 ob->n_written += sz;
330 return 0;
333 int obuf_write_be64(struct obuf *ob, uint64_t v)
335 size_t sz = sizeof(v);
337 if (obuf_check_size(ob, sz))
338 return -1;
340 write_at_be64(ob->b, v, ob->n_written);
341 ob->n_written += sz;
343 return 0;
346 int obuf_write_le8(struct obuf *ob, uint8_t v)
348 size_t sz = sizeof(v);
350 if (obuf_check_size(ob, sz))
351 return -1;
353 write_at_le8(ob->b, v, ob->n_written);
354 ob->n_written += sz;
356 return 0;
359 int obuf_write_le16(struct obuf *ob, uint16_t v)
361 size_t sz = sizeof(v);
363 if (obuf_check_size(ob, sz))
364 return -1;
366 write_at_le16(ob->b, v, ob->n_written);
367 ob->n_written += sz;
369 return 0;
372 int obuf_write_le32(struct obuf *ob, uint32_t v)
374 size_t sz = sizeof(v);
376 if (obuf_check_size(ob, sz))
377 return -1;
379 write_at_le32(ob->b, v, ob->n_written);
380 ob->n_written += sz;
382 return 0;
385 int obuf_write_le64(struct obuf *ob, uint64_t v)
387 size_t sz = sizeof(v);
389 if (obuf_check_size(ob, sz))
390 return -1;
392 write_at_le64(ob->b, v, ob->n_written);
393 ob->n_written += sz;
395 return 0;
398 int obuf_write_n8(struct obuf *ob, uint8_t v)
400 return obuf_write(ob, &v, sizeof(v));
403 int obuf_write_n16(struct obuf *ob, uint16_t v)
405 return obuf_write(ob, &v, sizeof(v));
408 int obuf_write_n32(struct obuf *ob, uint32_t v)
410 return obuf_write(ob, &v, sizeof(v));
413 int obuf_write_n64(struct obuf *ob, uint64_t v)
415 return obuf_write(ob, &v, sizeof(v));
418 const void *obuf_contents(const struct obuf *ob, size_t *sz)
420 *sz = obuf_nr_written(ob);
421 return ob->b;