1c87c5fbaSopenharmony_ci/* coap_encode.c -- encoding and decoding of CoAP data types
2c87c5fbaSopenharmony_ci *
3c87c5fbaSopenharmony_ci * Copyright (C) 2010,2011 Olaf Bergmann <bergmann@tzi.org>
4c87c5fbaSopenharmony_ci *
5c87c5fbaSopenharmony_ci * SPDX-License-Identifier: BSD-2-Clause
6c87c5fbaSopenharmony_ci *
7c87c5fbaSopenharmony_ci * This file is part of the CoAP library libcoap. Please see
8c87c5fbaSopenharmony_ci * README for terms of use.
9c87c5fbaSopenharmony_ci */
10c87c5fbaSopenharmony_ci
11c87c5fbaSopenharmony_ci/**
12c87c5fbaSopenharmony_ci * @file coap_encode.c
13c87c5fbaSopenharmony_ci * @brief Encoding and decoding Coap data types functions
14c87c5fbaSopenharmony_ci */
15c87c5fbaSopenharmony_ci
16c87c5fbaSopenharmony_ci#include "coap3/coap_internal.h"
17c87c5fbaSopenharmony_ci
18c87c5fbaSopenharmony_ci/* Carsten suggested this when fls() is not available: */
19c87c5fbaSopenharmony_ci#ifndef HAVE_FLS
20c87c5fbaSopenharmony_ciint
21c87c5fbaSopenharmony_cicoap_fls(unsigned int i) {
22c87c5fbaSopenharmony_ci  return coap_flsll(i);
23c87c5fbaSopenharmony_ci}
24c87c5fbaSopenharmony_ci#endif
25c87c5fbaSopenharmony_ci
26c87c5fbaSopenharmony_ci#ifndef HAVE_FLSLL
27c87c5fbaSopenharmony_ciint
28c87c5fbaSopenharmony_cicoap_flsll(long long j) {
29c87c5fbaSopenharmony_ci  unsigned long long i = (unsigned long long)j;
30c87c5fbaSopenharmony_ci  int n;
31c87c5fbaSopenharmony_ci  for (n = 0; i; n++)
32c87c5fbaSopenharmony_ci    i >>= 1;
33c87c5fbaSopenharmony_ci  return n;
34c87c5fbaSopenharmony_ci}
35c87c5fbaSopenharmony_ci#endif
36c87c5fbaSopenharmony_ci
37c87c5fbaSopenharmony_ciunsigned int
38c87c5fbaSopenharmony_cicoap_decode_var_bytes(const uint8_t *buf, size_t len) {
39c87c5fbaSopenharmony_ci  unsigned int i, n = 0;
40c87c5fbaSopenharmony_ci  for (i = 0; i < len; ++i)
41c87c5fbaSopenharmony_ci    n = (n << 8) + buf[i];
42c87c5fbaSopenharmony_ci
43c87c5fbaSopenharmony_ci  return n;
44c87c5fbaSopenharmony_ci}
45c87c5fbaSopenharmony_ci
46c87c5fbaSopenharmony_ciunsigned int
47c87c5fbaSopenharmony_cicoap_encode_var_safe(uint8_t *buf, size_t length, unsigned int val) {
48c87c5fbaSopenharmony_ci  unsigned int n, i;
49c87c5fbaSopenharmony_ci
50c87c5fbaSopenharmony_ci  for (n = 0, i = val; i && n < sizeof(val); ++n)
51c87c5fbaSopenharmony_ci    i >>= 8;
52c87c5fbaSopenharmony_ci
53c87c5fbaSopenharmony_ci  if (n > length) {
54c87c5fbaSopenharmony_ci    assert(n <= length);
55c87c5fbaSopenharmony_ci    return 0;
56c87c5fbaSopenharmony_ci  }
57c87c5fbaSopenharmony_ci  i = n;
58c87c5fbaSopenharmony_ci  while (i--) {
59c87c5fbaSopenharmony_ci    buf[i] = val & 0xff;
60c87c5fbaSopenharmony_ci    val >>= 8;
61c87c5fbaSopenharmony_ci  }
62c87c5fbaSopenharmony_ci
63c87c5fbaSopenharmony_ci  return n;
64c87c5fbaSopenharmony_ci}
65c87c5fbaSopenharmony_ci
66c87c5fbaSopenharmony_ciuint64_t
67c87c5fbaSopenharmony_cicoap_decode_var_bytes8(const uint8_t *buf, size_t len) {
68c87c5fbaSopenharmony_ci  unsigned int i;
69c87c5fbaSopenharmony_ci  uint64_t n = 0;
70c87c5fbaSopenharmony_ci  for (i = 0; i < len && i < sizeof(uint64_t); ++i)
71c87c5fbaSopenharmony_ci    n = (n << 8) + buf[i];
72c87c5fbaSopenharmony_ci
73c87c5fbaSopenharmony_ci  return n;
74c87c5fbaSopenharmony_ci}
75c87c5fbaSopenharmony_ci
76c87c5fbaSopenharmony_ciunsigned int
77c87c5fbaSopenharmony_cicoap_encode_var_safe8(uint8_t *buf, size_t length, uint64_t val) {
78c87c5fbaSopenharmony_ci  unsigned int n, i;
79c87c5fbaSopenharmony_ci  uint64_t tval = val;
80c87c5fbaSopenharmony_ci
81c87c5fbaSopenharmony_ci  for (n = 0; tval && n < sizeof(val); ++n)
82c87c5fbaSopenharmony_ci    tval >>= 8;
83c87c5fbaSopenharmony_ci
84c87c5fbaSopenharmony_ci  if (n > length) {
85c87c5fbaSopenharmony_ci    assert(n <= length);
86c87c5fbaSopenharmony_ci    return 0;
87c87c5fbaSopenharmony_ci  }
88c87c5fbaSopenharmony_ci  i = n;
89c87c5fbaSopenharmony_ci  while (i--) {
90c87c5fbaSopenharmony_ci    buf[i] = val & 0xff;
91c87c5fbaSopenharmony_ci    val >>= 8;
92c87c5fbaSopenharmony_ci  }
93c87c5fbaSopenharmony_ci
94c87c5fbaSopenharmony_ci  return n;
95c87c5fbaSopenharmony_ci}
96