libyang  2.1.148
libyang is YANG data modelling language parser and toolkit written (and providing API) in C.
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Macros Groups Pages
integer.c
Go to the documentation of this file.
1 
15 #define _GNU_SOURCE /* asprintf, strdup */
16 
17 #include "plugins_types.h"
18 
19 #include <stdint.h>
20 #include <stdio.h>
21 #include <stdlib.h>
22 
23 #include "libyang.h"
24 
25 /* additional internal headers for some useful simple macros */
26 #include "common.h"
27 #include "compat.h"
28 #include "plugins_internal.h" /* LY_TYPE_*_STR */
29 
42 static size_t integer_lyb_size[] = {
43  [LY_TYPE_INT8] = 1, [LY_TYPE_INT16] = 2, [LY_TYPE_INT32] = 4, [LY_TYPE_INT64] = 8,
45 };
46 
47 LIBYANG_API_DEF LY_ERR
48 lyplg_type_store_int(const struct ly_ctx *ctx, const struct lysc_type *type, const void *value, size_t value_len,
49  uint32_t options, LY_VALUE_FORMAT format, void *UNUSED(prefix_data), uint32_t hints,
50  const struct lysc_node *UNUSED(ctx_node), struct lyd_value *storage, struct lys_glob_unres *UNUSED(unres),
51  struct ly_err_item **err)
52 {
53  LY_ERR ret = LY_SUCCESS;
54  int64_t num = 0;
55  int base = 1;
56  char *canon = NULL;
57  struct lysc_type_num *type_num = (struct lysc_type_num *)type;
58 
59  /* init storage */
60  memset(storage, 0, sizeof *storage);
61  storage->realtype = type;
62 
63  if (format == LY_VALUE_LYB) {
64  /* validation */
65  if (value_len != integer_lyb_size[type->basetype]) {
66  ret = ly_err_new(err, LY_EVALID, LYVE_DATA, NULL, NULL, "Invalid LYB signed integer value size %zu (expected %zu).",
67  value_len, integer_lyb_size[type->basetype]);
68  goto cleanup;
69  }
70 
71  /* copy the integer and correct the byte order */
72  memcpy(&num, value, value_len);
73  num = le64toh(num);
74  } else {
75  /* check hints */
76  ret = lyplg_type_check_hints(hints, value, value_len, type->basetype, &base, err);
77  LY_CHECK_GOTO(ret, cleanup);
78 
79  /* parse the integer */
80  switch (type->basetype) {
81  case LY_TYPE_INT8:
82  ret = lyplg_type_parse_int("int8", base, INT64_C(-128), INT64_C(127), value, value_len, &num, err);
83  break;
84  case LY_TYPE_INT16:
85  ret = lyplg_type_parse_int("int16", base, INT64_C(-32768), INT64_C(32767), value, value_len, &num, err);
86  break;
87  case LY_TYPE_INT32:
88  ret = lyplg_type_parse_int("int32", base, INT64_C(-2147483648), INT64_C(2147483647), value, value_len, &num, err);
89  break;
90  case LY_TYPE_INT64:
91  ret = lyplg_type_parse_int("int64", base, INT64_C(-9223372036854775807) - INT64_C(1),
92  INT64_C(9223372036854775807), value, value_len, &num, err);
93  break;
94  default:
95  LOGINT(ctx);
96  ret = LY_EINT;
97  }
98  LY_CHECK_GOTO(ret, cleanup);
99  }
100 
101  /* set the value (matters for big-endian) and get the correct int64 number */
102  switch (type->basetype) {
103  case LY_TYPE_INT8:
104  storage->int8 = num;
105  num = storage->int8;
106  break;
107  case LY_TYPE_INT16:
108  storage->int16 = num;
109  num = storage->int16;
110  break;
111  case LY_TYPE_INT32:
112  storage->int32 = num;
113  num = storage->int32;
114  break;
115  case LY_TYPE_INT64:
116  storage->int64 = num;
117  num = storage->int64;
118  break;
119  default:
120  break;
121  }
122 
123  if (format == LY_VALUE_CANON) {
124  /* store canonical value */
125  if (options & LYPLG_TYPE_STORE_DYNAMIC) {
126  ret = lydict_insert_zc(ctx, (char *)value, &storage->_canonical);
127  options &= ~LYPLG_TYPE_STORE_DYNAMIC;
128  LY_CHECK_GOTO(ret, cleanup);
129  } else {
130  ret = lydict_insert(ctx, value, value_len, &storage->_canonical);
131  LY_CHECK_GOTO(ret, cleanup);
132  }
133  } else {
134  /* generate canonical value */
135  switch (type->basetype) {
136  case LY_TYPE_INT8:
137  LY_CHECK_ERR_GOTO(asprintf(&canon, "%" PRId8, storage->int8) == -1, ret = LY_EMEM, cleanup);
138  break;
139  case LY_TYPE_INT16:
140  LY_CHECK_ERR_GOTO(asprintf(&canon, "%" PRId16, storage->int16) == -1, ret = LY_EMEM, cleanup);
141  break;
142  case LY_TYPE_INT32:
143  LY_CHECK_ERR_GOTO(asprintf(&canon, "%" PRId32, storage->int32) == -1, ret = LY_EMEM, cleanup);
144  break;
145  case LY_TYPE_INT64:
146  LY_CHECK_ERR_GOTO(asprintf(&canon, "%" PRId64, storage->int64) == -1, ret = LY_EMEM, cleanup);
147  break;
148  default:
149  break;
150  }
151 
152  /* store it */
153  ret = lydict_insert_zc(ctx, canon, (const char **)&storage->_canonical);
154  LY_CHECK_GOTO(ret, cleanup);
155  }
156 
157  /* validate range of the number */
158  if (type_num->range) {
159  ret = lyplg_type_validate_range(type->basetype, type_num->range, num, storage->_canonical,
160  strlen(storage->_canonical), err);
161  LY_CHECK_GOTO(ret, cleanup);
162  }
163 
164 cleanup:
165  if (options & LYPLG_TYPE_STORE_DYNAMIC) {
166  free((void *)value);
167  }
168 
169  if (ret) {
170  lyplg_type_free_simple(ctx, storage);
171  }
172  return ret;
173 }
174 
175 LIBYANG_API_DEF LY_ERR
176 lyplg_type_compare_int(const struct lyd_value *val1, const struct lyd_value *val2)
177 {
178  if (val1->realtype != val2->realtype) {
179  return LY_ENOT;
180  }
181 
182  switch (val1->realtype->basetype) {
183  case LY_TYPE_INT8:
184  if (val1->int8 != val2->int8) {
185  return LY_ENOT;
186  }
187  break;
188  case LY_TYPE_INT16:
189  if (val1->int16 != val2->int16) {
190  return LY_ENOT;
191  }
192  break;
193  case LY_TYPE_INT32:
194  if (val1->int32 != val2->int32) {
195  return LY_ENOT;
196  }
197  break;
198  case LY_TYPE_INT64:
199  if (val1->int64 != val2->int64) {
200  return LY_ENOT;
201  }
202  break;
203  default:
204  break;
205  }
206  return LY_SUCCESS;
207 }
208 
209 LIBYANG_API_DEF const void *
210 lyplg_type_print_int(const struct ly_ctx *UNUSED(ctx), const struct lyd_value *value, LY_VALUE_FORMAT format,
211  void *UNUSED(prefix_data), ly_bool *dynamic, size_t *value_len)
212 {
213  int64_t prev_num = 0, num = 0;
214  void *buf;
215 
216  if (format == LY_VALUE_LYB) {
217  switch (value->realtype->basetype) {
218  case LY_TYPE_INT8:
219  prev_num = num = value->int8;
220  break;
221  case LY_TYPE_INT16:
222  prev_num = num = value->int16;
223  break;
224  case LY_TYPE_INT32:
225  prev_num = num = value->int32;
226  break;
227  case LY_TYPE_INT64:
228  prev_num = num = value->int64;
229  break;
230  default:
231  break;
232  }
233  num = htole64(num);
234  if (num == prev_num) {
235  /* values are equal, little-endian or int8 */
236  *dynamic = 0;
237  if (value_len) {
238  *value_len = integer_lyb_size[value->realtype->basetype];
239  }
240  return &value->int64;
241  } else {
242  /* values differ, big-endian */
243  buf = calloc(1, integer_lyb_size[value->realtype->basetype]);
244  LY_CHECK_RET(!buf, NULL);
245 
246  *dynamic = 1;
247  if (value_len) {
248  *value_len = integer_lyb_size[value->realtype->basetype];
249  }
250  memcpy(buf, &num, integer_lyb_size[value->realtype->basetype]);
251  return buf;
252  }
253  }
254 
255  /* use the cached canonical value */
256  if (dynamic) {
257  *dynamic = 0;
258  }
259  if (value_len) {
260  *value_len = strlen(value->_canonical);
261  }
262  return value->_canonical;
263 }
264 
265 LIBYANG_API_DEF LY_ERR
266 lyplg_type_store_uint(const struct ly_ctx *ctx, const struct lysc_type *type, const void *value, size_t value_len,
267  uint32_t options, LY_VALUE_FORMAT format, void *UNUSED(prefix_data), uint32_t hints,
268  const struct lysc_node *UNUSED(ctx_node), struct lyd_value *storage, struct lys_glob_unres *UNUSED(unres),
269  struct ly_err_item **err)
270 {
271  LY_ERR ret = LY_SUCCESS;
272  uint64_t num = 0;
273  int base = 0;
274  char *canon;
275  struct lysc_type_num *type_num = (struct lysc_type_num *)type;
276 
277  /* init storage */
278  memset(storage, 0, sizeof *storage);
279  storage->realtype = type;
280 
281  if (format == LY_VALUE_LYB) {
282  /* validation */
283  if (value_len != integer_lyb_size[type->basetype]) {
284  ret = ly_err_new(err, LY_EVALID, LYVE_DATA, NULL, NULL, "Invalid LYB unsigned integer value size %zu (expected %zu).",
285  value_len, integer_lyb_size[type->basetype]);
286  goto cleanup;
287  }
288 
289  /* copy the integer and correct the byte order */
290  memcpy(&num, value, value_len);
291  num = le64toh(num);
292  } else {
293  /* check hints */
294  ret = lyplg_type_check_hints(hints, value, value_len, type->basetype, &base, err);
295  LY_CHECK_GOTO(ret, cleanup);
296 
297  /* parse the integer */
298  switch (type->basetype) {
299  case LY_TYPE_UINT8:
300  ret = lyplg_type_parse_uint("uint8", base, UINT64_C(255), value, value_len, &num, err);
301  break;
302  case LY_TYPE_UINT16:
303  ret = lyplg_type_parse_uint("uint16", base, UINT64_C(65535), value, value_len, &num, err);
304  break;
305  case LY_TYPE_UINT32:
306  ret = lyplg_type_parse_uint("uint32", base, UINT64_C(4294967295), value, value_len, &num, err);
307  break;
308  case LY_TYPE_UINT64:
309  ret = lyplg_type_parse_uint("uint64", base, UINT64_C(18446744073709551615), value, value_len, &num, err);
310  break;
311  default:
312  LOGINT(ctx);
313  ret = LY_EINT;
314  }
315  LY_CHECK_GOTO(ret, cleanup);
316  }
317 
318  /* store value, matters for big-endian */
319  switch (type->basetype) {
320  case LY_TYPE_UINT8:
321  storage->uint8 = num;
322  break;
323  case LY_TYPE_UINT16:
324  storage->uint16 = num;
325  break;
326  case LY_TYPE_UINT32:
327  storage->uint32 = num;
328  break;
329  case LY_TYPE_UINT64:
330  storage->uint64 = num;
331  break;
332  default:
333  break;
334  }
335 
336  if (format == LY_VALUE_CANON) {
337  /* store canonical value */
338  if (options & LYPLG_TYPE_STORE_DYNAMIC) {
339  ret = lydict_insert_zc(ctx, (char *)value, &storage->_canonical);
340  options &= ~LYPLG_TYPE_STORE_DYNAMIC;
341  LY_CHECK_GOTO(ret, cleanup);
342  } else {
343  ret = lydict_insert(ctx, value, value_len, &storage->_canonical);
344  LY_CHECK_GOTO(ret, cleanup);
345  }
346  } else {
347  /* generate canonical value */
348  LY_CHECK_ERR_GOTO(asprintf(&canon, "%" PRIu64, num) == -1, ret = LY_EMEM, cleanup);
349 
350  /* store it */
351  ret = lydict_insert_zc(ctx, canon, (const char **)&storage->_canonical);
352  LY_CHECK_GOTO(ret, cleanup);
353  }
354 
355  /* validate range of the number */
356  if (type_num->range) {
357  ret = lyplg_type_validate_range(type->basetype, type_num->range, num, storage->_canonical,
358  strlen(storage->_canonical), err);
359  LY_CHECK_GOTO(ret, cleanup);
360  }
361 
362 cleanup:
363  if (options & LYPLG_TYPE_STORE_DYNAMIC) {
364  free((void *)value);
365  }
366 
367  if (ret) {
368  lyplg_type_free_simple(ctx, storage);
369  }
370  return ret;
371 }
372 
373 LIBYANG_API_DEF LY_ERR
374 lyplg_type_compare_uint(const struct lyd_value *val1, const struct lyd_value *val2)
375 {
376  switch (val1->realtype->basetype) {
377  case LY_TYPE_UINT8:
378  if (val1->uint8 != val2->uint8) {
379  return LY_ENOT;
380  }
381  break;
382  case LY_TYPE_UINT16:
383  if (val1->uint16 != val2->uint16) {
384  return LY_ENOT;
385  }
386  break;
387  case LY_TYPE_UINT32:
388  if (val1->uint32 != val2->uint32) {
389  return LY_ENOT;
390  }
391  break;
392  case LY_TYPE_UINT64:
393  if (val1->uint64 != val2->uint64) {
394  return LY_ENOT;
395  }
396  break;
397  default:
398  break;
399  }
400  return LY_SUCCESS;
401 }
402 
403 LIBYANG_API_DEF const void *
404 lyplg_type_print_uint(const struct ly_ctx *UNUSED(ctx), const struct lyd_value *value, LY_VALUE_FORMAT format,
405  void *UNUSED(prefix_data), ly_bool *dynamic, size_t *value_len)
406 {
407  uint64_t num = 0;
408  void *buf;
409 
410  if (format == LY_VALUE_LYB) {
411  switch (value->realtype->basetype) {
412  case LY_TYPE_UINT8:
413  num = value->uint8;
414  break;
415  case LY_TYPE_UINT16:
416  num = value->uint16;
417  break;
418  case LY_TYPE_UINT32:
419  num = value->uint32;
420  break;
421  case LY_TYPE_UINT64:
422  num = value->uint64;
423  break;
424  default:
425  break;
426  }
427  num = htole64(num);
428  if (num == value->uint64) {
429  /* values are equal, little-endian or uint8 */
430  *dynamic = 0;
431  if (value_len) {
432  *value_len = integer_lyb_size[value->realtype->basetype];
433  }
434  return &value->uint64;
435  } else {
436  /* values differ, big-endian */
437  buf = calloc(1, integer_lyb_size[value->realtype->basetype]);
438  LY_CHECK_RET(!buf, NULL);
439 
440  *dynamic = 1;
441  if (value_len) {
442  *value_len = integer_lyb_size[value->realtype->basetype];
443  }
444  memcpy(buf, &num, integer_lyb_size[value->realtype->basetype]);
445  return buf;
446  }
447  }
448 
449  /* use the cached canonical value */
450  if (dynamic) {
451  *dynamic = 0;
452  }
453  if (value_len) {
454  *value_len = strlen(value->_canonical);
455  }
456  return value->_canonical;
457 }
458 
467  {
468  .module = "",
469  .revision = NULL,
470  .name = LY_TYPE_UINT8_STR,
471 
472  .plugin.id = "libyang 2 - integers, version 1",
473  .plugin.store = lyplg_type_store_uint,
474  .plugin.validate = NULL,
475  .plugin.compare = lyplg_type_compare_uint,
476  .plugin.sort = NULL,
477  .plugin.print = lyplg_type_print_uint,
478  .plugin.duplicate = lyplg_type_dup_simple,
479  .plugin.free = lyplg_type_free_simple,
480  .plugin.lyb_data_len = 1,
481  }, {
482  .module = "",
483  .revision = NULL,
484  .name = LY_TYPE_UINT16_STR,
485 
486  .plugin.id = "libyang 2 - integers, version 1",
487  .plugin.store = lyplg_type_store_uint,
488  .plugin.validate = NULL,
489  .plugin.compare = lyplg_type_compare_uint,
490  .plugin.sort = NULL,
491  .plugin.print = lyplg_type_print_uint,
492  .plugin.duplicate = lyplg_type_dup_simple,
493  .plugin.free = lyplg_type_free_simple,
494  .plugin.lyb_data_len = 2,
495  }, {
496  .module = "",
497  .revision = NULL,
498  .name = LY_TYPE_UINT32_STR,
499 
500  .plugin.id = "libyang 2 - integers, version 1",
501  .plugin.store = lyplg_type_store_uint,
502  .plugin.validate = NULL,
503  .plugin.compare = lyplg_type_compare_uint,
504  .plugin.sort = NULL,
505  .plugin.print = lyplg_type_print_uint,
506  .plugin.duplicate = lyplg_type_dup_simple,
507  .plugin.free = lyplg_type_free_simple,
508  .plugin.lyb_data_len = 4,
509  }, {
510  .module = "",
511  .revision = NULL,
512  .name = LY_TYPE_UINT64_STR,
513 
514  .plugin.id = "libyang 2 - integers, version 1",
515  .plugin.store = lyplg_type_store_uint,
516  .plugin.validate = NULL,
517  .plugin.compare = lyplg_type_compare_uint,
518  .plugin.sort = NULL,
519  .plugin.print = lyplg_type_print_uint,
520  .plugin.duplicate = lyplg_type_dup_simple,
521  .plugin.free = lyplg_type_free_simple,
522  .plugin.lyb_data_len = 8,
523  }, {
524  .module = "",
525  .revision = NULL,
526  .name = LY_TYPE_INT8_STR,
527 
528  .plugin.id = "libyang 2 - integers, version 1",
529  .plugin.store = lyplg_type_store_int,
530  .plugin.validate = NULL,
531  .plugin.compare = lyplg_type_compare_int,
532  .plugin.sort = NULL,
533  .plugin.print = lyplg_type_print_int,
534  .plugin.duplicate = lyplg_type_dup_simple,
535  .plugin.free = lyplg_type_free_simple,
536  .plugin.lyb_data_len = 1,
537  }, {
538  .module = "",
539  .revision = NULL,
540  .name = LY_TYPE_INT16_STR,
541 
542  .plugin.id = "libyang 2 - integers, version 1",
543  .plugin.store = lyplg_type_store_int,
544  .plugin.validate = NULL,
545  .plugin.compare = lyplg_type_compare_int,
546  .plugin.sort = NULL,
547  .plugin.print = lyplg_type_print_int,
548  .plugin.duplicate = lyplg_type_dup_simple,
549  .plugin.free = lyplg_type_free_simple,
550  .plugin.lyb_data_len = 2,
551  }, {
552  .module = "",
553  .revision = NULL,
554  .name = LY_TYPE_INT32_STR,
555 
556  .plugin.id = "libyang 2 - integers, version 1",
557  .plugin.store = lyplg_type_store_int,
558  .plugin.validate = NULL,
559  .plugin.compare = lyplg_type_compare_int,
560  .plugin.sort = NULL,
561  .plugin.print = lyplg_type_print_int,
562  .plugin.duplicate = lyplg_type_dup_simple,
563  .plugin.free = lyplg_type_free_simple,
564  .plugin.lyb_data_len = 4,
565  }, {
566  .module = "",
567  .revision = NULL,
568  .name = LY_TYPE_INT64_STR,
569 
570  .plugin.id = "libyang 2 - integers, version 1",
571  .plugin.store = lyplg_type_store_int,
572  .plugin.validate = NULL,
573  .plugin.compare = lyplg_type_compare_int,
574  .plugin.sort = NULL,
575  .plugin.print = lyplg_type_print_int,
576  .plugin.duplicate = lyplg_type_dup_simple,
577  .plugin.free = lyplg_type_free_simple,
578  .plugin.lyb_data_len = 8,
579  },
580  {0}
581 };
struct lysc_type * realtype
Definition: tree_data.h:564
Compiled YANG data node.
Definition: tree_schema.h:1414
LIBYANG_API_DECL LY_ERR lyplg_type_parse_uint(const char *datatype, int base, uint64_t max, const char *value, size_t value_len, uint64_t *ret, struct ly_err_item **err)
Unsigned integer value parser and validator.
struct lyplg_type_record plugins_integer[]
Plugin information for integer types implementation.
Definition: integer.c:466
LIBYANG_API_DECL LY_ERR ly_err_new(struct ly_err_item **err, LY_ERR ecode, LY_VECODE vecode, char *path, char *apptag, const char *err_format,...) _FORMAT_PRINTF(6
Create and fill error structure.
LIBYANG_API_DECL LY_ERR lyplg_type_parse_int(const char *datatype, int base, int64_t min, int64_t max, const char *value, size_t value_len, int64_t *ret, struct ly_err_item **err)
Unsigned integer value parser and validator.
Definition: log.h:253
uint8_t ly_bool
Type to indicate boolean value.
Definition: log.h:28
LIBYANG_API_DECL const void * lyplg_type_print_int(const struct ly_ctx *ctx, const struct lyd_value *value, LY_VALUE_FORMAT format, void *prefix_data, ly_bool *dynamic, size_t *value_len)
Implementation of lyplg_type_print_clb for the built-in signed integer types.
#define LYPLG_TYPE_STORE_DYNAMIC
Definition: log.h:258
The main libyang public header.
YANG data representation.
Definition: tree_data.h:560
const char * _canonical
Definition: tree_data.h:561
LIBYANG_API_DECL const void * lyplg_type_print_uint(const struct ly_ctx *ctx, const struct lyd_value *value, LY_VALUE_FORMAT format, void *prefix_data, ly_bool *dynamic, size_t *value_len)
Implementation of lyplg_type_print_clb for the built-in unsigned integer types.
Libyang full error structure.
Definition: log.h:296
Definition: log.h:288
Definition: log.h:259
LIBYANG_API_DECL LY_ERR lyplg_type_store_int(const struct ly_ctx *ctx, const struct lysc_type *type, const void *value, size_t value_len, uint32_t options, LY_VALUE_FORMAT format, void *prefix_data, uint32_t hints, const struct lysc_node *ctx_node, struct lyd_value *storage, struct lys_glob_unres *unres, struct ly_err_item **err)
Implementation of lyplg_type_store_clb for the built-in signed integer types.
LIBYANG_API_DECL LY_ERR lydict_insert(const struct ly_ctx *ctx, const char *value, size_t len, const char **str_p)
Insert string into dictionary. If the string is already present, only a reference counter is incremen...
LIBYANG_API_DECL LY_ERR lyplg_type_compare_int(const struct lyd_value *val1, const struct lyd_value *val2)
Implementation of lyplg_type_compare_clb for the built-in signed integer types.
Definition: integer.c:176
struct lysc_range * range
Definition: tree_schema.h:1309
LIBYANG_API_DECL LY_ERR lyplg_type_check_hints(uint32_t hints, const char *value, size_t value_len, LY_DATA_TYPE type, int *base, struct ly_err_item **err)
Check that the type is suitable for the parser&#39;s hints (if any) in the specified format.
const char * module
Definition: log.h:265
LIBYANG_API_DECL LY_ERR lydict_insert_zc(const struct ly_ctx *ctx, char *value, const char **str_p)
Insert string into dictionary - zerocopy version. If the string is already present, only a reference counter is incremented and no memory allocation is performed. This insert function variant avoids duplication of specified value - it is inserted into the dictionary directly.
LY_VALUE_FORMAT
All kinds of supported value formats and prefix mappings to modules.
Definition: tree.h:234
LY_DATA_TYPE basetype
Definition: tree_schema.h:1299
LIBYANG_API_DECL LY_ERR lyplg_type_dup_simple(const struct ly_ctx *ctx, const struct lyd_value *original, struct lyd_value *dup)
Implementation of lyplg_type_dup_clb for a generic simple type.
LY_ERR
libyang&#39;s error codes returned by the libyang functions.
Definition: log.h:251
LIBYANG_API_DECL void lyplg_type_free_simple(const struct ly_ctx *ctx, struct lyd_value *value)
Implementation of lyplg_type_free_clb for a generic simple type.
LIBYANG_API_DECL LY_ERR lyplg_type_store_uint(const struct ly_ctx *ctx, const struct lysc_type *type, const void *value, size_t value_len, uint32_t options, LY_VALUE_FORMAT format, void *prefix_data, uint32_t hints, const struct lysc_node *ctx_node, struct lyd_value *storage, struct lys_glob_unres *unres, struct ly_err_item **err)
Implementation of lyplg_type_store_clb for the built-in unsigned integer types.
LIBYANG_API_DECL LY_ERR lyplg_type_compare_uint(const struct lyd_value *val1, const struct lyd_value *val2)
Implementation of lyplg_type_compare_clb for the built-in unsigned integer types. ...
Definition: integer.c:374
API for (user) types plugins.
libyang context handler.
LIBYANG_API_DECL LY_ERR lyplg_type_validate_range(LY_DATA_TYPE basetype, struct lysc_range *range, int64_t value, const char *strval, size_t strval_len, struct ly_err_item **err)
Data type validator for a range/length-restricted values.