annotate val_array.c @ 832:76e588fedba8

nvl: make nvpair_value return -ENOENT for NULL pairs This brings it in line with the rest of the nvpair_value_* functions. Signed-off-by: Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
author Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
date Mon, 01 Mar 2021 19:35:15 -0500
parents 2730e7a80abd
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
1 /*
675
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
2 * Copyright (c) 2018-2019 Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
3 *
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
4 * Permission is hereby granted, free of charge, to any person obtaining a copy
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
5 * of this software and associated documentation files (the "Software"), to deal
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
6 * in the Software without restriction, including without limitation the rights
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
8 * copies of the Software, and to permit persons to whom the Software is
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
9 * furnished to do so, subject to the following conditions:
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
10 *
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
11 * The above copyright notice and this permission notice shall be included in
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
12 * all copies or substantial portions of the Software.
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
13 *
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
20 * SOFTWARE.
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
21 */
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
22
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
23 #include <jeffpc/mem.h>
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
24
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
25 #include "val_impl.h"
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
26
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
27 static struct val *__val_alloc_array(struct val **vals, size_t nelem,
676
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
28 bool dup, bool heap)
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
29 {
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
30 struct val *val;
675
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
31 size_t i;
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
32
676
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
33 if (dup) {
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
34 struct val **tmp;
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
35
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
36 /* no reason to ever duplicate a heap allocated array */
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
37 ASSERT(!heap);
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
38
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
39 tmp = mem_reallocarray(NULL, nelem, sizeof(struct val *));
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
40 if (!tmp) {
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
41 val = ERR_PTR(-ENOMEM);
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
42 goto err;
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
43 }
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
44
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
45 /*
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
46 * The multiplication can't overflow since the memory allocation
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
47 * already checks for it.
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
48 */
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
49 memcpy(tmp, vals, sizeof(struct val *) * nelem);
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
50
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
51 /* switch to the new array & free it on error or 0 refcnt */
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
52 vals = tmp;
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
53 heap = true;
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
54 }
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
55
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
56 val = __val_alloc(VT_ARRAY);
675
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
57 if (IS_ERR(val))
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
58 goto err;
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
59
675
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
60 val->_set_array.vals = vals;
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
61 val->_set_array.nelem = nelem;
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
62 val->static_alloc = !heap;
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
63
675
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
64 return val;
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
65
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
66 err:
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
67 for (i = 0; i < nelem; i++)
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
68 val_putref(vals[i]);
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
69
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
70 if (heap)
cf7308f74b62 val: use a goto for error handling in __val_alloc_array
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 463
diff changeset
71 free(vals);
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
72
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
73 return val;
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
74 }
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
75
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
76 struct val *val_alloc_array(struct val **vals, size_t nelem)
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
77 {
676
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
78 return __val_alloc_array(vals, nelem, false, true);
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
79 }
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
80
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
81 struct val *val_alloc_array_dup(struct val **vals, size_t nelem)
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
82 {
676
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
83 return __val_alloc_array(vals, nelem, true, false);
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
84 }
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
85
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
86 struct val *val_alloc_array_static(struct val **vals, size_t nelem)
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
87 {
676
2730e7a80abd val: don't leak val references on val_alloc_array_dup error
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents: 675
diff changeset
88 return __val_alloc_array(vals, nelem, false, false);
463
8f455913bfd0 val: introduce VT_ARRAY
Josef 'Jeff' Sipek <jeffpc@josefsipek.net>
parents:
diff changeset
89 }