Coverage Report

Created: 2025-03-25 06:24

/src/libcbor/src/cbor/common.c
Line
Count
Source (jump to first uncovered line)
1
/*
2
 * Copyright (c) 2014-2020 Pavel Kalvoda <me@pavelkalvoda.com>
3
 *
4
 * libcbor is free software; you can redistribute it and/or modify
5
 * it under the terms of the MIT license. See LICENSE for details.
6
 */
7
8
#include "cbor/common.h"
9
#include "arrays.h"
10
#include "bytestrings.h"
11
#include "data.h"
12
#include "floats_ctrls.h"
13
#include "ints.h"
14
#include "maps.h"
15
#include "strings.h"
16
#include "tags.h"
17
18
#ifdef DEBUG
19
bool _cbor_enable_assert = true;
20
#endif
21
22
291M
bool cbor_isa_uint(const cbor_item_t* item) {
23
291M
  return item->type == CBOR_TYPE_UINT;
24
291M
}
25
26
16.3M
bool cbor_isa_negint(const cbor_item_t* item) {
27
16.3M
  return item->type == CBOR_TYPE_NEGINT;
28
16.3M
}
29
30
30.6M
bool cbor_isa_bytestring(const cbor_item_t* item) {
31
30.6M
  return item->type == CBOR_TYPE_BYTESTRING;
32
30.6M
}
33
34
36.1M
bool cbor_isa_string(const cbor_item_t* item) {
35
36.1M
  return item->type == CBOR_TYPE_STRING;
36
36.1M
}
37
38
353M
bool cbor_isa_array(const cbor_item_t* item) {
39
353M
  return item->type == CBOR_TYPE_ARRAY;
40
353M
}
41
42
36.3M
bool cbor_isa_map(const cbor_item_t* item) {
43
36.3M
  return item->type == CBOR_TYPE_MAP;
44
36.3M
}
45
46
2.16M
bool cbor_isa_tag(const cbor_item_t* item) {
47
2.16M
  return item->type == CBOR_TYPE_TAG;
48
2.16M
}
49
50
90.3M
bool cbor_isa_float_ctrl(const cbor_item_t* item) {
51
90.3M
  return item->type == CBOR_TYPE_FLOAT_CTRL;
52
90.3M
}
53
54
94.6M
cbor_type cbor_typeof(const cbor_item_t* item) { return item->type; }
55
56
279M
bool cbor_is_int(const cbor_item_t* item) {
57
279M
  return cbor_isa_uint(item) || cbor_isa_negint(item);
58
279M
}
59
60
6.04M
bool cbor_is_bool(const cbor_item_t* item) {
61
6.04M
  return cbor_isa_float_ctrl(item) &&
62
6.04M
         (cbor_ctrl_value(item) == CBOR_CTRL_FALSE ||
63
6.04M
          cbor_ctrl_value(item) == CBOR_CTRL_TRUE);
64
6.04M
}
65
66
109k
bool cbor_is_null(const cbor_item_t* item) {
67
109k
  return cbor_isa_float_ctrl(item) && cbor_ctrl_value(item) == CBOR_CTRL_NULL;
68
109k
}
69
70
139k
bool cbor_is_undef(const cbor_item_t* item) {
71
139k
  return cbor_isa_float_ctrl(item) && cbor_ctrl_value(item) == CBOR_CTRL_UNDEF;
72
139k
}
73
74
681k
bool cbor_is_float(const cbor_item_t* item) {
75
681k
  return cbor_isa_float_ctrl(item) && !cbor_float_ctrl_is_ctrl(item);
76
681k
}
77
78
85.8M
cbor_item_t* cbor_incref(cbor_item_t* item) {
79
85.8M
  item->refcount++;
80
85.8M
  return item;
81
85.8M
}
82
83
131M
void cbor_decref(cbor_item_t** item_ref) {
84
131M
  cbor_item_t* item = *item_ref;
85
131M
  CBOR_ASSERT(item->refcount > 0);
86
131M
  if (--item->refcount == 0) {
87
65.9M
    switch (item->type) {
88
31.3M
      case CBOR_TYPE_UINT:
89
        /* Fallthrough */
90
33.4M
      case CBOR_TYPE_NEGINT:
91
        /* Combined allocation, freeing the item suffices */
92
33.4M
        { break; }
93
1.41M
      case CBOR_TYPE_BYTESTRING: {
94
1.41M
        if (cbor_bytestring_is_definite(item)) {
95
1.40M
          _cbor_free(item->data);
96
1.40M
        } else {
97
          /* We need to decref all chunks */
98
7.56k
          cbor_item_t** handle = cbor_bytestring_chunks_handle(item);
99
1.35M
          for (size_t i = 0; i < cbor_bytestring_chunk_count(item); i++)
100
1.34M
            cbor_decref(&handle[i]);
101
7.56k
          _cbor_free(((struct cbor_indefinite_string_data*)item->data)->chunks);
102
7.56k
          _cbor_free(item->data);
103
7.56k
        }
104
1.41M
        break;
105
31.3M
      }
106
1.78M
      case CBOR_TYPE_STRING: {
107
1.78M
        if (cbor_string_is_definite(item)) {
108
1.75M
          _cbor_free(item->data);
109
1.75M
        } else {
110
          /* We need to decref all chunks */
111
29.0k
          cbor_item_t** handle = cbor_string_chunks_handle(item);
112
1.71M
          for (size_t i = 0; i < cbor_string_chunk_count(item); i++)
113
1.68M
            cbor_decref(&handle[i]);
114
29.0k
          _cbor_free(((struct cbor_indefinite_string_data*)item->data)->chunks);
115
29.0k
          _cbor_free(item->data);
116
29.0k
        }
117
1.78M
        break;
118
31.3M
      }
119
18.9M
      case CBOR_TYPE_ARRAY: {
120
        /* Get all items and decref them */
121
18.9M
        cbor_item_t** handle = cbor_array_handle(item);
122
18.9M
        size_t size = cbor_array_size(item);
123
72.9M
        for (size_t i = 0; i < size; i++)
124
54.0M
          if (handle[i] != NULL) cbor_decref(&handle[i]);
125
18.9M
        _cbor_free(item->data);
126
18.9M
        break;
127
31.3M
      }
128
128k
      case CBOR_TYPE_MAP: {
129
128k
        struct cbor_pair* handle = cbor_map_handle(item);
130
4.28M
        for (size_t i = 0; i < item->metadata.map_metadata.end_ptr;
131
4.15M
             i++, handle++) {
132
4.15M
          cbor_decref(&handle->key);
133
4.15M
          if (handle->value != NULL) cbor_decref(&handle->value);
134
4.15M
        }
135
128k
        _cbor_free(item->data);
136
128k
        break;
137
31.3M
      }
138
471k
      case CBOR_TYPE_TAG: {
139
471k
        if (item->metadata.tag_metadata.tagged_item != NULL)
140
447k
          cbor_decref(&item->metadata.tag_metadata.tagged_item);
141
471k
        _cbor_free(item->data);
142
471k
        break;
143
31.3M
      }
144
9.75M
      case CBOR_TYPE_FLOAT_CTRL: {
145
        /* Floats have combined allocation */
146
9.75M
        break;
147
31.3M
      }
148
65.9M
    }
149
65.9M
    _cbor_free(item);
150
65.9M
    *item_ref = NULL;
151
65.9M
  }
152
131M
}
153
154
0
void cbor_intermediate_decref(cbor_item_t* item) { cbor_decref(&item); }
155
156
0
size_t cbor_refcount(const cbor_item_t* item) { return item->refcount; }
157
158
20.0M
cbor_item_t* cbor_move(cbor_item_t* item) {
159
20.0M
  item->refcount--;
160
20.0M
  return item;
161
20.0M
}