#include "jprint.h" void JPrintElement(jprint_state *State) { if(State->NeedsComma == true) { fprintf(State->F, ","); } else { State->NeedsComma = true; } } void JPrint_null(jprint_state *State) { JPrintElement(State); fprintf(State->F, "null"); } void JPrint_bool(jprint_state *State, bool E) { JPrintElement(State); fprintf(State->F, "%s", E ? "true" : "false"); } void JPrint_ssize_t(jprint_state *State, ssize_t E) { JPrintElement(State); fprintf(State->F, "%zd", E); } void JPrint_double(jprint_state *State, double E) { JPrintElement(State); fprintf(State->F, "%f", E); } void JPrint_string(jprint_state *State, char const E[]) { JPrintElement(State); fprintf(State->F, "\""); for(size_t i = 0; E[i] != '\0'; ++i) { if(__builtin_expect(E[i] == '\\', false)) { fputc('\\', State->F); fputc('\\', State->F); } else if(__builtin_expect(E[i] == '"', false)) { fputc('\\', State->F); fputc('"', State->F); } else { fputc(E[i], State->F); } } fprintf(State->F, "\""); } void JPrint_string_n(jprint_state *State, char const E[], size_t Length) { JPrintElement(State); fprintf(State->F, "\""); for(size_t i = 0; i < Length && E[i] != '\0'; ++i) { if(__builtin_expect(E[i] == '\\', false)) { fputc('\\', State->F); fputc('\\', State->F); } else if(__builtin_expect(E[i] == '"', false)) { fputc('\\', State->F); fputc('"', State->F); } else { fputc(E[i], State->F); } } fprintf(State->F, "\""); } void JPrintArrayBegin(jprint_state *State) { JPrintElement(State); State->NeedsComma = false; fprintf(State->F, "["); } void JPrintArrayEnd(jprint_state *State) { fprintf(State->F, "]"); State->NeedsComma = true; } void JPrintObjectBegin(jprint_state *State) { JPrintElement(State); State->NeedsComma = false; fprintf(State->F, "{"); } void JPrintObjectEnd(jprint_state *State) { fprintf(State->F, "}"); State->NeedsComma = true; } void JPrintMember(jprint_state *State, char const T[]) { JPrintElement(State); State->NeedsComma = false; fprintf(State->F, "\"%s\":", T); } void JPrintMember_n(jprint_state *State, char const T[], size_t Length) { JPrintElement(State); State->NeedsComma = false; fprintf(State->F, "\"%.*s\":", (int)Length, T); } void JPrint_ucl_object_t(jprint_state *State, ucl_object_t const *E) { if(E == NULL) { JPrint_null(State); return; } switch(E->type) { case UCL_OBJECT: { JPrintObjectBegin(State); ucl_object_t const *v; ucl_object_iter_t it = NULL; while((v = ucl_iterate_object(E, &it, true))) { char const *k = ucl_object_key(v); if(k == NULL) continue; JPrintMember(State, k); JPrint_ucl_object_t(State, v); } JPrintObjectEnd(State); break; } case UCL_ARRAY: { JPrintArrayBegin(State); ucl_object_t const *v; ucl_object_iter_t it = NULL; while((v = ucl_iterate_object(E, &it, true))) JPrint_ucl_object_t(State, v); JPrintArrayEnd(State); break; } case UCL_STRING: JPrint_string(State, ucl_object_tostring(E)); break; case UCL_INT: JPrint_ssize_t(State, ucl_object_toint(E)); break; case UCL_FLOAT: JPrint_double(State, ucl_object_todouble(E)); break; case UCL_BOOLEAN: JPrint_bool(State, ucl_object_toboolean(E)); break; case UCL_NULL: JPrint_null(State); break; default: __builtin_unreachable(); } }