Azure SDK for Embedded C
az_json.h
Go to the documentation of this file.
1 // Copyright (c) Microsoft Corporation. All rights reserved.
2 // SPDX-License-Identifier: MIT
3 
16 #ifndef _az_JSON_H
17 #define _az_JSON_H
18 
19 #include <azure/core/az_result.h>
20 #include <azure/core/az_span.h>
21 
22 #include <stdbool.h>
23 #include <stdint.h>
24 
25 #include <azure/core/_az_cfg_prefix.h>
26 
30 typedef enum
31 {
44 
49 typedef struct
50 {
51  struct
52  {
53  // This uint64_t container represents a tiny stack to track the state during nested transitions.
54  // The first bit represents the state of the current depth (1 == object, 0 == array).
55  // Each subsequent bit is the parent / containing type (object or array).
56  uint64_t az_json_stack;
57  int32_t current_depth;
58  } _internal;
59 } _az_json_bit_stack;
60 
68 typedef struct
69 {
78 
79  // Avoid using enum as the first field within structs, to allow for { 0 } initialization.
80  // This is a workaround for IAR compiler warning [Pe188]: enumerated type mixed with another type.
81 
85 
90  int32_t size;
91 
92  struct
93  {
98 
102 
106 
109 
112 
115 
118  } _internal;
119 } az_json_token;
120 
121 // TODO: Should the parameters be reversed?
140 
151 AZ_NODISCARD az_result az_json_token_get_boolean(az_json_token const* json_token, bool* out_value);
152 
165 AZ_NODISCARD az_result
166 az_json_token_get_uint64(az_json_token const* json_token, uint64_t* out_value);
167 
180 AZ_NODISCARD az_result
181 az_json_token_get_uint32(az_json_token const* json_token, uint32_t* out_value);
182 
195 AZ_NODISCARD az_result az_json_token_get_int64(az_json_token const* json_token, int64_t* out_value);
196 
209 AZ_NODISCARD az_result az_json_token_get_int32(az_json_token const* json_token, int32_t* out_value);
210 
222 AZ_NODISCARD az_result az_json_token_get_double(az_json_token const* json_token, double* out_value);
223 
241  az_json_token const* json_token,
242  char* destination,
243  int32_t destination_max_size,
244  int32_t* out_string_length);
245 
259 AZ_NODISCARD bool az_json_token_is_text_equal(
260  az_json_token const* json_token,
261  az_span expected_text);
262 
263 /************************************ JSON WRITER ******************/
264 
268 typedef struct
269 {
270  struct
271  {
273  bool unused;
274  } _internal;
276 
287 {
289  ._internal = {
290  .unused = false,
291  },
292  };
293 
294  return options;
295 }
296 
304 typedef struct
305 {
306  struct
307  {
308  az_span destination_buffer;
309  int32_t bytes_written;
310  // For single contiguous buffer, bytes_written == total_bytes_written
311  int32_t total_bytes_written; // Currently, this is primarily used for testing.
312  az_span_allocator_fn allocator_callback;
313  void* user_context;
314  bool need_comma;
315  az_json_token_kind token_kind; // needed for validation, potentially #if/def with preconditions.
316  _az_json_bit_stack bit_stack; // needed for validation, potentially #if/def with preconditions.
317  az_json_writer_options options;
318  } _internal;
320 
335  az_json_writer* out_json_writer,
336  az_span destination_buffer,
337  az_json_writer_options const* options);
338 
360  az_json_writer* out_json_writer,
361  az_span first_destination_buffer,
362  az_span_allocator_fn allocator_callback,
363  void* user_context,
364  az_json_writer_options const* options);
365 
383 AZ_NODISCARD AZ_INLINE az_span
385 {
386  return az_span_slice(
387  json_writer->_internal.destination_buffer, 0, json_writer->_internal.bytes_written);
388 }
389 
404 AZ_NODISCARD az_result az_json_writer_append_string(az_json_writer* ref_json_writer, az_span value);
405 
433 AZ_NODISCARD az_result
435 
449 AZ_NODISCARD az_result
451 
463 AZ_NODISCARD az_result az_json_writer_append_bool(az_json_writer* ref_json_writer, bool value);
464 
476 AZ_NODISCARD az_result az_json_writer_append_int32(az_json_writer* ref_json_writer, int32_t value);
477 
503  az_json_writer* ref_json_writer,
504  double value,
505  int32_t fractional_digits);
506 
517 AZ_NODISCARD az_result az_json_writer_append_null(az_json_writer* ref_json_writer);
518 
532 
546 
558 
570 
571 /************************************ JSON READER ******************/
572 
576 typedef struct
577 {
578  struct
579  {
581  bool unused;
582  } _internal;
584 
595 {
597  ._internal = {
598  .unused = false,
599  },
600  };
601 
602  return options;
603 }
604 
611 typedef struct
612 {
616 
617  struct
618  {
621 
625 
629 
632  int32_t buffer_index;
633 
635  int32_t bytes_consumed;
636 
640 
644 
646  _az_json_bit_stack bit_stack;
647 
650  } _internal;
652 
673  az_json_reader* out_json_reader,
674  az_span json_buffer,
675  az_json_reader_options const* options);
676 
702  az_json_reader* out_json_reader,
703  az_span json_buffers[],
704  int32_t number_of_buffers,
705  az_json_reader_options const* options);
706 
719 AZ_NODISCARD az_result az_json_reader_next_token(az_json_reader* ref_json_reader);
720 
737 
738 #include <azure/core/_az_cfg_suffix.h>
739 
740 #endif // _az_JSON_H
az_json_token_get_double
AZ_NODISCARD az_result az_json_token_get_double(az_json_token const *json_token, double *out_value)
Gets the JSON token's number as a double.
az_json_writer_append_end_array
AZ_NODISCARD az_result az_json_writer_append_end_array(az_json_writer *ref_json_writer)
Appends the end of the current JSON array (i.e. ]).
az_result.h
Definition of az_result and helper functions.
az_json_token::pointer_to_first_buffer
az_span * pointer_to_first_buffer
Definition: az_json.h:105
AZ_JSON_TOKEN_FALSE
@ AZ_JSON_TOKEN_FALSE
The token kind is the JSON literal false.
Definition: az_json.h:41
az_json_reader
Returns the JSON tokens contained within a JSON buffer, one at a time.
Definition: az_json.h:612
az_json_writer_append_double
AZ_NODISCARD az_result az_json_writer_append_double(az_json_writer *ref_json_writer, double value, int32_t fractional_digits)
Appends a double number value.
az_json_reader_next_token
AZ_NODISCARD az_result az_json_reader_next_token(az_json_reader *ref_json_reader)
Reads the next token in the JSON text and updates the reader state.
az_json_writer_options
Allows the user to define custom behavior when writing JSON using the az_json_writer.
Definition: az_json.h:269
az_json_writer
Provides forward-only, non-cached writing of UTF-8 encoded JSON text into the provided buffer.
Definition: az_json.h:305
az_json_token::end_buffer_offset
int32_t end_buffer_offset
The offset within the particular segment within which this token ends.
Definition: az_json.h:117
az_json_writer_options_default
AZ_NODISCARD AZ_INLINE az_json_writer_options az_json_writer_options_default()
Gets the default json writer options which builds minimized JSON (with no extra white space) accordin...
Definition: az_json.h:286
az_json_writer_append_string
AZ_NODISCARD az_result az_json_writer_append_string(az_json_writer *ref_json_writer, az_span value)
Appends the UTF-8 text value (as a JSON string) into the buffer.
az_json_writer_append_end_object
AZ_NODISCARD az_result az_json_writer_append_end_object(az_json_writer *ref_json_writer)
Appends the end of the current JSON object (i.e. }).
az_json_writer_append_property_name
AZ_NODISCARD az_result az_json_writer_append_property_name(az_json_writer *ref_json_writer, az_span name)
Appends the UTF-8 property name (as a JSON string) which is the first part of a name/value pair of a ...
az_json_token_get_uint32
AZ_NODISCARD az_result az_json_token_get_uint32(az_json_token const *json_token, uint32_t *out_value)
Gets the JSON token's number as a 32-bit unsigned integer.
AZ_JSON_TOKEN_BEGIN_OBJECT
@ AZ_JSON_TOKEN_BEGIN_OBJECT
The token kind is the start of a JSON object.
Definition: az_json.h:33
az_json_reader::json_buffers
az_span * json_buffers
Definition: az_json.h:624
AZ_JSON_TOKEN_END_ARRAY
@ AZ_JSON_TOKEN_END_ARRAY
The token kind is the end of a JSON array.
Definition: az_json.h:36
az_json_reader::total_bytes_consumed
int32_t total_bytes_consumed
Definition: az_json.h:639
az_json_writer_append_begin_object
AZ_NODISCARD az_result az_json_writer_append_begin_object(az_json_writer *ref_json_writer)
Appends the beginning of a JSON object (i.e. {).
az_result
int32_t az_result
The type represents the various success and error conditions.
Definition: az_result.h:45
az_json_reader_options
Allows the user to define custom behavior when reading JSON using the az_json_reader.
Definition: az_json.h:577
az_json_reader::token
az_json_token token
Definition: az_json.h:615
az_json_writer_get_bytes_used_in_destination
AZ_NODISCARD AZ_INLINE az_span az_json_writer_get_bytes_used_in_destination(az_json_writer const *json_writer)
Returns the az_span containing the JSON text written to the underlying buffer so far,...
Definition: az_json.h:384
az_json_token::end_buffer_index
int32_t end_buffer_index
The segment index within the non-contiguous JSON payload where this token ends.
Definition: az_json.h:114
AZ_JSON_TOKEN_END_OBJECT
@ AZ_JSON_TOKEN_END_OBJECT
The token kind is the end of a JSON object.
Definition: az_json.h:34
az_json_reader_options::unused
bool unused
Currently, this is unused, but needed as a placeholder since we can't have an empty struct.
Definition: az_json.h:581
az_json_writer_options::unused
bool unused
Currently, this is unused, but needed as a placeholder since we can't have an empty struct.
Definition: az_json.h:273
az_json_writer_chunked_init
AZ_NODISCARD az_result az_json_writer_chunked_init(az_json_writer *out_json_writer, az_span first_destination_buffer, az_span_allocator_fn allocator_callback, void *user_context, az_json_writer_options const *options)
Initializes an az_json_writer which writes JSON text into a destination that can contain non-contiguo...
az_json_token_get_boolean
AZ_NODISCARD az_result az_json_token_get_boolean(az_json_token const *json_token, bool *out_value)
Gets the JSON token's boolean.
az_span_allocator_fn
az_result(* az_span_allocator_fn)(az_span_allocator_context *allocator_context, az_span *out_next_destination)
Defines the signature of the callback function that the caller must implement to provide the potentia...
Definition: az_span.h:524
AZ_JSON_TOKEN_STRING
@ AZ_JSON_TOKEN_STRING
The token kind is a JSON string.
Definition: az_json.h:38
az_json_reader::options
az_json_reader_options options
A copy of the options provided by the user.
Definition: az_json.h:649
az_json_reader::number_of_buffers
int32_t number_of_buffers
Definition: az_json.h:628
az_span_slice
AZ_NODISCARD az_span az_span_slice(az_span span, int32_t start_index, int32_t end_index)
Returns a new az_span which is a sub-span of the specified span.
az_json_token_get_uint64
AZ_NODISCARD az_result az_json_token_get_uint64(az_json_token const *json_token, uint64_t *out_value)
Gets the JSON token's number as a 64-bit unsigned integer.
AZ_JSON_TOKEN_PROPERTY_NAME
@ AZ_JSON_TOKEN_PROPERTY_NAME
The token kind is a JSON property name.
Definition: az_json.h:37
az_json_reader_options_default
AZ_NODISCARD AZ_INLINE az_json_reader_options az_json_reader_options_default()
Gets the default json reader options which reads the JSON strictly according to the JSON RFC.
Definition: az_json.h:594
az_json_reader::bit_stack
_az_json_bit_stack bit_stack
A limited stack to track the depth and nested JSON objects or arrays read so far.
Definition: az_json.h:646
az_span.h
An az_span represents a contiguous byte buffer and is used for string manipulations,...
az_json_token::kind
az_json_token_kind kind
Definition: az_json.h:84
AZ_JSON_TOKEN_NULL
@ AZ_JSON_TOKEN_NULL
The token kind is the JSON literal null.
Definition: az_json.h:42
az_json_reader::buffer_index
int32_t buffer_index
Definition: az_json.h:632
az_json_token::start_buffer_offset
int32_t start_buffer_offset
The offset within the particular segment within which this token starts.
Definition: az_json.h:111
az_json_writer_append_json_text
AZ_NODISCARD az_result az_json_writer_append_json_text(az_json_writer *ref_json_writer, az_span json_text)
Appends an existing UTF-8 encoded JSON text into the buffer, useful for appending nested JSON.
az_json_reader::json_buffer
az_span json_buffer
The first buffer containing the JSON payload.
Definition: az_json.h:620
az_json_writer_append_begin_array
AZ_NODISCARD az_result az_json_writer_append_begin_array(az_json_writer *ref_json_writer)
Appends the beginning of a JSON array (i.e. [).
az_json_token_get_string
AZ_NODISCARD az_result az_json_token_get_string(az_json_token const *json_token, char *destination, int32_t destination_max_size, int32_t *out_string_length)
Gets the JSON token's string after unescaping it, if required.
AZ_JSON_TOKEN_NUMBER
@ AZ_JSON_TOKEN_NUMBER
The token kind is a JSON number.
Definition: az_json.h:39
az_json_token_kind
az_json_token_kind
Defines symbols for the various kinds of JSON tokens that make up any JSON text.
Definition: az_json.h:31
AZ_JSON_TOKEN_NONE
@ AZ_JSON_TOKEN_NONE
There is no value (as distinct from AZ_JSON_TOKEN_NULL).
Definition: az_json.h:32
az_json_token::string_has_escaped_chars
bool string_has_escaped_chars
Definition: az_json.h:101
az_json_writer_append_bool
AZ_NODISCARD az_result az_json_writer_append_bool(az_json_writer *ref_json_writer, bool value)
Appends a boolean value (as a JSON literal true or false).
az_json_token
Represents a JSON token. The kind field indicates the type of the JSON token and the slice represents...
Definition: az_json.h:69
az_json_writer_append_null
AZ_NODISCARD az_result az_json_writer_append_null(az_json_writer *ref_json_writer)
Appends the JSON literal null.
az_json_token::size
int32_t size
Definition: az_json.h:90
AZ_JSON_TOKEN_TRUE
@ AZ_JSON_TOKEN_TRUE
The token kind is the JSON literal true.
Definition: az_json.h:40
AZ_JSON_TOKEN_BEGIN_ARRAY
@ AZ_JSON_TOKEN_BEGIN_ARRAY
The token kind is the start of a JSON array.
Definition: az_json.h:35
az_json_token::start_buffer_index
int32_t start_buffer_index
The segment index within the non-contiguous JSON payload where this token starts.
Definition: az_json.h:108
az_json_reader::is_complex_json
bool is_complex_json
Definition: az_json.h:643
az_json_token::is_multisegment
bool is_multisegment
Definition: az_json.h:97
az_json_token_is_text_equal
AZ_NODISCARD bool az_json_token_is_text_equal(az_json_token const *json_token, az_span expected_text)
Determines whether the unescaped JSON token value that the az_json_token points to is equal to the ex...
az_json_token_copy_into_span
az_span az_json_token_copy_into_span(az_json_token const *json_token, az_span destination)
Copies the content of the token az_json_token to the destination az_span.
az_json_reader_skip_children
AZ_NODISCARD az_result az_json_reader_skip_children(az_json_reader *ref_json_reader)
Reads and skips over any nested JSON elements.
az_json_token::slice
az_span slice
Definition: az_json.h:77
az_json_reader_init
AZ_NODISCARD az_result az_json_reader_init(az_json_reader *out_json_reader, az_span json_buffer, az_json_reader_options const *options)
Initializes an az_json_reader to read the JSON payload contained within the provided buffer.
az_json_token_get_int64
AZ_NODISCARD az_result az_json_token_get_int64(az_json_token const *json_token, int64_t *out_value)
Gets the JSON token's number as a 64-bit signed integer.
az_json_writer_append_int32
AZ_NODISCARD az_result az_json_writer_append_int32(az_json_writer *ref_json_writer, int32_t value)
Appends an int32_t number value.
az_json_reader_chunked_init
AZ_NODISCARD az_result az_json_reader_chunked_init(az_json_reader *out_json_reader, az_span json_buffers[], int32_t number_of_buffers, az_json_reader_options const *options)
Initializes an az_json_reader to read the JSON payload contained within the provided set of discontig...
az_json_token_get_int32
AZ_NODISCARD az_result az_json_token_get_int32(az_json_token const *json_token, int32_t *out_value)
Gets the JSON token's number as a 32-bit signed integer.
az_json_reader::bytes_consumed
int32_t bytes_consumed
The number of bytes consumed so far in the current buffer segment.
Definition: az_json.h:635
az_json_writer_init
AZ_NODISCARD az_result az_json_writer_init(az_json_writer *out_json_writer, az_span destination_buffer, az_json_writer_options const *options)
Initializes an az_json_writer which writes JSON text into a buffer.
az_span
Represents a "view" over a byte buffer that represents a contiguous region of memory....
Definition: az_span.h:33