Skip to content

Commit ee8617d

Browse files
cborpretty.c: Use the new fragment API in the string dumpers
This means we don't need to allocate memory anymore, we just print directly from the CBOR byte stream. And since the pretty dumper now uses the fragment API, we don't need a separate test for validating it. But, for that reason, we need to test the dup/copy API separately. The use of the fragment API allows us to test that the dumper does detect one UTF-8 multibyte sequence split across different string chunks. Signed-off-by: Thiago Macieira <[email protected]>
1 parent 9b017b2 commit ee8617d

File tree

2 files changed

+133
-132
lines changed

2 files changed

+133
-132
lines changed

src/cborpretty.c

Lines changed: 32 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,6 @@
3636
#include <inttypes.h>
3737
#include <math.h>
3838
#include <stdio.h>
39-
#include <stdlib.h>
4039
#include <string.h>
4140

4241
/**
@@ -122,20 +121,22 @@
122121
* \value CborPrettyDefaultFlags Default conversion flags.
123122
*/
124123

125-
static int hexDump(FILE *out, const uint8_t *buffer, size_t n)
124+
static CborError hexDump(FILE *out, const void *ptr, size_t n)
126125
{
126+
const uint8_t *buffer = (const uint8_t *)ptr;
127127
while (n--) {
128128
int r = fprintf(out, "%02" PRIx8, *buffer++);
129129
if (r < 0)
130-
return r;
130+
return CborErrorIO;
131131
}
132-
return 0; /* should be n * 2, but we don't have the original n anymore */
132+
return CborNoError;
133133
}
134134

135135
/* This function decodes buffer as UTF-8 and prints as escaped UTF-16.
136136
* On UTF-8 decoding error, it returns CborErrorInvalidUtf8TextString */
137-
static int utf8EscapedDump(FILE *out, const char *buffer, size_t n)
137+
static CborError utf8EscapedDump(FILE *out, const void *ptr, size_t n)
138138
{
139+
const char *buffer = (const char *)ptr;
139140
uint32_t uc;
140141
while (n--) {
141142
uc = (uint8_t)*buffer++;
@@ -336,32 +337,36 @@ static CborError value_to_pretty(FILE *out, CborValue *it, int flags)
336337
break;
337338
}
338339

339-
case CborByteStringType:{
340+
case CborByteStringType:
341+
case CborTextStringType: {
340342
size_t n = 0;
341-
uint8_t *buffer;
342-
err = cbor_value_dup_byte_string(it, &buffer, &n, it);
343-
if (err)
344-
return err;
343+
const void *ptr;
344+
char close = '\'';
345+
char open[3] = "h'";
345346

346-
bool failed = fprintf(out, "h'") < 0 || hexDump(out, buffer, n) < 0 || fprintf(out, "'") < 0;
347-
free(buffer);
348-
return failed ? CborErrorIO : CborNoError;
349-
}
347+
if (type == CborTextStringType) {
348+
close = open[0] = '"';
349+
open[1] = '\0';
350+
}
350351

351-
case CborTextStringType: {
352-
size_t n = 0;
353-
char *buffer;
354-
err = cbor_value_dup_text_string(it, &buffer, &n, it);
355-
if (err)
356-
return err;
352+
if (fputs(open, out) < 0)
353+
return CborErrorIO;
354+
355+
while (1) {
356+
err = _cbor_value_get_string_chunk(it, &ptr, &n, it);
357+
if (err)
358+
return err;
359+
if (!ptr)
360+
break;
357361

358-
err = CborNoError;
359-
bool failed = fprintf(out, "\"") < 0
360-
|| (err = utf8EscapedDump(out, buffer, n)) != CborNoError
361-
|| fprintf(out, "\"") < 0;
362-
free(buffer);
363-
return err != CborNoError ? err :
364-
failed ? CborErrorIO : CborNoError;
362+
err = (type == CborByteStringType ? hexDump(out, ptr, n) : utf8EscapedDump(out, ptr, n));
363+
if (err)
364+
return err;
365+
}
366+
367+
if (fputc(close, out) < 0)
368+
return CborErrorIO;
369+
return CborNoError;
365370
}
366371

367372
case CborTagType: {

0 commit comments

Comments
 (0)