Loading...
Searching...
No Matches
coap_asn1.c
Go to the documentation of this file.
/* coap_asn1.c -- ASN.1 handling functions
*
* Copyright (C) 2020-2023 Jon Shallow <supjps-libcoap@jpshallow.com>
*
* SPDX-License-Identifier: BSD-2-Clause
*
* This file is part of the CoAP library libcoap. Please see
* README for terms of use.
*/
#include "coap3/coap_internal.h"
size_t
asn1_len(const uint8_t **ptr) {
size_t len = 0;
if ((**ptr) & 0x80) {
size_t octets = (**ptr) & 0x7f;
(*ptr)++;
while (octets) {
len = (len << 8) + (**ptr);
(*ptr)++;
octets--;
}
} else {
len = (**ptr) & 0x7f;
(*ptr)++;
}
return len;
}
coap_asn1_tag_t
asn1_tag_c(const uint8_t **ptr, int *constructed, int *cls) {
coap_asn1_tag_t tag = 0;
uint8_t byte;
byte = (**ptr);
*constructed = (byte & 0x20) ? 1 : 0;
*cls = byte >> 6;
tag = byte & 0x1F;
(*ptr)++;
if (tag < 0x1F)
return tag;
/* Tag can be one byte or more based on B8 */
byte = (**ptr);
while (byte & 0x80) {
tag = (tag << 7) + (byte & 0x7F);
(*ptr)++;
byte = (**ptr);
}
/* Do the final one */
tag = (tag << 7) + (byte & 0x7F);
(*ptr)++;
return tag;
}
/* caller must free off returned coap_binary_t* */
coap_binary_t *
get_asn1_tag(coap_asn1_tag_t ltag, const uint8_t *ptr, size_t tlen,
asn1_validate validate) {
int constructed;
int class;
const uint8_t *acp = ptr;
uint8_t tag = asn1_tag_c(&acp, &constructed, &class);
size_t len = asn1_len(&acp);
coap_binary_t *tag_data;
while (tlen > 0 && len <= tlen) {
if (class == 2 && constructed == 1) {
/* Skip over element description */
tag = asn1_tag_c(&acp, &constructed, &class);
len = asn1_len(&acp);
}
if (tag == ltag) {
if (!validate || validate(acp, len)) {
tag_data = coap_new_binary(len);
if (tag_data == NULL)
return NULL;
tag_data->length = len;
memcpy(tag_data->s, acp, len);
return tag_data;
}
}
if (tag == 0x10 && constructed == 1) {
/* SEQUENCE or SEQUENCE OF */
tag_data = get_asn1_tag(ltag, acp, len, validate);
if (tag_data)
return tag_data;
}
acp += len;
tlen -= len;
tag = asn1_tag_c(&acp, &constructed, &class);
len = asn1_len(&acp);
}
return NULL;
}
coap_internal.h
Pulls together all the internal only header files.
get_asn1_tag
coap_binary_t * get_asn1_tag(coap_asn1_tag_t ltag, const uint8_t *ptr, size_t tlen, asn1_validate validate)
Get the asn1 tag and data from the current ptr.
Definition coap_asn1.c:65
asn1_tag_c
coap_asn1_tag_t asn1_tag_c(const uint8_t **ptr, int *constructed, int *cls)
Get the asn1 tag from the current ptr.
Definition coap_asn1.c:38
asn1_len
size_t asn1_len(const uint8_t **ptr)
Get the asn1 length from the current ptr.
Definition coap_asn1.c:19
coap_asn1_tag_t
coap_asn1_tag_t
Definition coap_asn1_internal.h:29
asn1_validate
int(* asn1_validate)(const uint8_t *data, size_t size)
Callback to validate the asn1 tag and data.
Definition coap_asn1_internal.h:47
coap_new_binary
coap_binary_t * coap_new_binary(size_t size)
Returns a new binary object with at least size bytes storage allocated.
Definition coap_str.c:77
coap_binary_t
CoAP binary data definition.
Definition coap_str.h:56
coap_binary_t::length
size_t length
length of binary data
Definition coap_str.h:57
coap_binary_t::s
uint8_t * s
binary data
Definition coap_str.h:58