/*
 * out-plutil.c
 * plutil-like *output-only* format - NOT for machine parsing
 *
 * Copyright (c) 2023 Nikias Bassen All Rights Reserved.
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 */

#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <time.h>

#include <inttypes.h>
#include <ctype.h>
#include <math.h>
#include <limits.h>

#include <node.h>

#include "plist.h"
#include "strbuf.h"
#include "time64.h"
#include "hashtable.h"
#include "common.h"

static plist_err_t node_to_string(node_t node, bytearray_t **outbuf, uint32_t depth)
{
    plist_data_t node_data = NULL;

    char *val = NULL;
    int slen = 0;
    size_t val_len = 0;

    if (!node || !outbuf || !*outbuf) {
        return PLIST_ERR_INVALID_ARG;
    }

    node_data = plist_get_data(node);
    if (!node_data) {
        return PLIST_ERR_INVALID_ARG;
    }

    switch (node_data->type)
    {
    case PLIST_BOOLEAN:
    {
        if (node_data->boolval) {
            str_buf_append(*outbuf, "1", 1);
        } else {
            str_buf_append(*outbuf, "0", 1);
        }
    }
    break;

    case PLIST_NULL:
        str_buf_append(*outbuf, "<null>", 6);
	break;

    case PLIST_INT:
        val = (char*)malloc(64);
        if (!val) return PLIST_ERR_NO_MEM;
        if (node_data->length == 16) {
            slen = snprintf(val, 64, "%" PRIu64, node_data->intval);
        } else {
            slen = snprintf(val, 64, "%" PRIi64, node_data->intval);
        }
        if (slen < 0) {
            free(val);
            return PLIST_ERR_UNKNOWN;
        }
        val_len = (size_t)slen;
        str_buf_append(*outbuf, val, val_len);
        free(val);
        break;

    case PLIST_REAL:
        val = (char*)malloc(64);
        if (!val) return PLIST_ERR_NO_MEM;
        val_len = dtostr(val, 64, node_data->realval);
        str_buf_append(*outbuf, val, val_len);
        free(val);
        break;

    case PLIST_STRING:
    case PLIST_KEY: {
        if (!node_data->strval && node_data->length > 0) {
            return PLIST_ERR_INVALID_ARG;
        }
        const char *charmap[32] = {
            "\\u0000", "\\u0001", "\\u0002", "\\u0003", "\\u0004", "\\u0005", "\\u0006", "\\u0007",
            "\\b",     "\\t",     "\\n",     "\\u000b", "\\f",     "\\r",     "\\u000e", "\\u000f",
            "\\u0010", "\\u0011", "\\u0012", "\\u0013", "\\u0014", "\\u0015", "\\u0016", "\\u0017",
            "\\u0018", "\\u0019", "\\u001a", "\\u001b", "\\u001c", "\\u001d", "\\u001e", "\\u001f",
        };
        size_t j = 0;
        size_t len = 0;
        size_t start = 0;
        size_t cur = 0;

        str_buf_append(*outbuf, "\"", 1);

        len = node_data->length;
        for (j = 0; j < len; j++) {
            unsigned char ch = (unsigned char)node_data->strval[j];
            if (ch < 0x20) {
                str_buf_append(*outbuf, node_data->strval + start, cur - start);
                str_buf_append(*outbuf, charmap[ch], (charmap[ch][1] == 'u') ? 6 : 2);
                start = cur+1;
            } else if (ch == '"') {
                str_buf_append(*outbuf, node_data->strval + start, cur - start);
                str_buf_append(*outbuf, "\\\"", 2);
                start = cur+1;
            }
            cur++;
        }
        str_buf_append(*outbuf, node_data->strval + start, cur - start);

        str_buf_append(*outbuf, "\"", 1);
        } break;

    case PLIST_ARRAY: {
        str_buf_append(*outbuf, "[", 1);
        node_t ch;
        uint32_t cnt = 0;
        uint32_t i;
        for (ch = node_first_child(node); ch; ch = node_next_sibling(ch)) {
            str_buf_append(*outbuf, "\n", 1);
            for (i = 0; i <= depth; i++) {
                str_buf_append(*outbuf, "  ", 2);
            }
            char indexbuf[16];
            slen = snprintf(indexbuf, sizeof(indexbuf), "%u => ", cnt);
            if (slen < 0) {
                return PLIST_ERR_UNKNOWN;
            }
            str_buf_append(*outbuf, indexbuf, (size_t)slen);
            plist_err_t res = node_to_string(ch, outbuf, depth+1);
            if (res < 0) {
                return res;
            }
            cnt++;
        }
        if (cnt > 0) {
            str_buf_append(*outbuf, "\n", 1);
            for (i = 0; i < depth; i++) {
                str_buf_append(*outbuf, "  ", 2);
            }
        }
        str_buf_append(*outbuf, "]", 1);
        } break;
    case PLIST_DICT: {
        str_buf_append(*outbuf, "{", 1);
        node_t ch;
        uint32_t cnt = 0;
        uint32_t i;
        for (ch = node_first_child(node); ch; ch = node_next_sibling(ch)) {
            if (cnt % 2 == 0) {
                str_buf_append(*outbuf, "\n", 1);
                for (i = 0; i <= depth; i++) {
                    str_buf_append(*outbuf, "  ", 2);
                }
            }
            plist_err_t res = node_to_string(ch, outbuf, depth+1);
            if (res < 0) {
                return res;
            }
            if (cnt % 2 == 0) {
                str_buf_append(*outbuf, " => ", 4);
            }
            cnt++;
        }
        if (cnt > 0) {
            str_buf_append(*outbuf, "\n", 1);
            for (i = 0; i < depth; i++) {
                str_buf_append(*outbuf, "  ", 2);
            }
        }
        str_buf_append(*outbuf, "}", 1);
        } break;
    case PLIST_DATA:
        {
            if (!node_data->buff && node_data->length > 0) {
                return PLIST_ERR_INVALID_ARG;
            }
            val = (char*)calloc(1, 48);
            if (!val) return PLIST_ERR_NO_MEM;
            size_t len = node_data->length;
            slen = snprintf(val, 48, "{length = %" PRIu64 ", bytes = 0x", (uint64_t)len);
            if (slen < 0) {
                free(val);
                return PLIST_ERR_UNKNOWN;
            }
            str_buf_append(*outbuf, val, (size_t)slen);
            size_t j;
            if (len <= 24) {
                for (j = 0; j < len; j++) {
                    snprintf(val, 4, "%02x", (unsigned char)node_data->buff[j]);
                    str_buf_append(*outbuf, val, 2);
                }
            } else {
                for (j = 0; j < 16; j++) {
                    if (j > 0 && (j % 4 == 0))
                        str_buf_append(*outbuf, " ", 1);
                    snprintf(val, 4, "%02x", (unsigned char)node_data->buff[j]);
                    str_buf_append(*outbuf, val, 2);
                }
                str_buf_append(*outbuf, " ... ", 5);
                for (j = len - 8; j < len; j++) {
                    snprintf(val, 4, "%02x", (unsigned char)node_data->buff[j]);
                    str_buf_append(*outbuf, val, 2);
                    if (j > 0 && (j % 4 == 0))
                        str_buf_append(*outbuf, " ", 1);
                }
            }
            free(val);
            val = NULL;
            str_buf_append(*outbuf, "}", 1);
        }
        break;
    case PLIST_DATE:
        {
            Time64_T timev;
            if (plist_real_to_time64(node_data->realval, &timev) < 0) {
#if DEBUG
                fprintf(stderr, "libplist: ERROR: Encountered invalid date value %f\n", node_data->realval);
#endif
                return PLIST_ERR_INVALID_ARG;
            }
            struct TM _btime;
            struct TM *btime = gmtime64_r(&timev, &_btime);
            if (btime) {
                val = (char*)calloc(1, 26);
                if (!val) return PLIST_ERR_NO_MEM;
                struct tm _tmcopy;
                copy_TM64_to_tm(btime, &_tmcopy);
                val_len = strftime(val, 26, "%Y-%m-%d %H:%M:%S +0000", &_tmcopy);
                if (val_len > 0) {
                    str_buf_append(*outbuf, val, val_len);
                }
                free(val);
                val = NULL;
            }
        }
        break;
    case PLIST_UID:
        {
#define UID_FMT "<CFKeyedArchiverUID %p [%p]>{value = %" PRIu64 "}"
            slen = snprintf(NULL, 0, UID_FMT, node, node_data, node_data->intval);
            if (slen < 0) {
                return PLIST_ERR_UNKNOWN;
            }
            val_len = (size_t)slen;
            val = (char*)malloc(val_len + 1);
            if (!val) return PLIST_ERR_NO_MEM;
            slen = snprintf(val, val_len+1, UID_FMT, node, node_data, node_data->intval);
            if (slen < 0 || (size_t)slen > val_len) {
                free(val);
                return PLIST_ERR_UNKNOWN;
            }
            val_len = (size_t)slen;
            str_buf_append(*outbuf, val, val_len);
            free(val);
            val = NULL;
#undef UID_FMT
        }
        break;
    default:
        return PLIST_ERR_UNKNOWN;
    }

    return PLIST_ERR_SUCCESS;
}

static plist_err_t _node_estimate_size(node_t node, uint64_t *size, uint32_t depth, hashtable_t *visited)
{
    plist_data_t data;
    if (!node) {
        return PLIST_ERR_INVALID_ARG;
    }

    if (depth > PLIST_MAX_NESTING_DEPTH) {
#if DEBUG
        fprintf(stderr, "libplist: ERROR: maximum nesting depth (%u) exceeded\n", (unsigned)PLIST_MAX_NESTING_DEPTH);
#endif
        return PLIST_ERR_MAX_NESTING;
    }

    if (hash_table_lookup(visited, node)) {
#if DEBUG
        fprintf(stderr, "libplist: ERROR: circular reference detected\n");
#endif
        return PLIST_ERR_CIRCULAR_REF;
    }

    // mark as visited
    hash_table_insert(visited, node, (void*)1);

    data = plist_get_data(node);
    if (node->children) {
        node_t ch;
        unsigned int n_children = node_n_children(node);
        for (ch = node_first_child(node); ch; ch = node_next_sibling(ch)) {
            plist_err_t res = _node_estimate_size(ch, size, depth + 1, visited);
            if (res != PLIST_ERR_SUCCESS) {
                return res;
            }
        }
        switch (data->type) {
        case PLIST_DICT:
            *size += 2; // '{' and '}'
            *size += n_children-1; // number of ':' and ','
            *size += n_children; // number of '\n' and extra space
            *size += (uint64_t)n_children * (depth+1); // indent for every 2nd child
            *size += 1; // additional '\n'
            break;
        case PLIST_ARRAY:
            *size += 2; // '[' and ']'
            *size += n_children-1; // number of ','
            *size += n_children; // number of '\n'
            *size += (uint64_t)n_children * ((depth+1)<<1); // indent for every child
            *size += 1; // additional '\n'
            break;
        default:
            break;
	}
        *size += (depth << 1); // indent for {} and []
    } else {
        switch (data->type) {
        case PLIST_STRING:
        case PLIST_KEY:
            *size += data->length;
            *size += 2;
            break;
        case PLIST_INT:
            if (data->length == 16) {
                *size += num_digits_u(data->intval);
            } else {
                *size += num_digits_i((int64_t)data->intval);
            }
            break;
        case PLIST_REAL:
            *size += dtostr(NULL, 0, data->realval);
            break;
        case PLIST_BOOLEAN:
            *size += 1;
            break;
        case PLIST_NULL:
            *size += 6;
            break;
        case PLIST_DICT:
        case PLIST_ARRAY:
            *size += 2;
            break;
        case PLIST_DATA:
            *size = (data->length <= 24) ? 73 : 100;
            break;
        case PLIST_DATE:
            *size += 25;
            break;
        case PLIST_UID:
            *size += 88;
            break;
        default:
#ifdef DEBUG
            fprintf(stderr, "invalid node type encountered\n");
#endif
            return PLIST_ERR_UNKNOWN;
        }
    }
    if (depth == 0) {
        *size += 1; // final newline
    }
    return PLIST_ERR_SUCCESS;
}

static plist_err_t node_estimate_size(node_t node, uint64_t *size, uint32_t depth)
{
    hashtable_t *visited = hash_table_new(plist_node_ptr_hash, plist_node_ptr_compare, NULL);
    if (!visited) return PLIST_ERR_NO_MEM;
    plist_err_t err = _node_estimate_size(node, size, depth, visited);
    hash_table_destroy(visited);
    return err;
}

static plist_err_t _plist_write_to_strbuf(plist_t plist, strbuf_t *outbuf, plist_write_options_t options)
{
    plist_err_t res = node_to_string((node_t)plist, &outbuf, 0);
    if (res < 0) {
        return res;
    }
    if (!(options & PLIST_OPT_NO_NEWLINE)) {
        str_buf_append(outbuf, "\n", 1);
    }
    return res;
}

plist_err_t plist_write_to_string_plutil(plist_t plist, char **output, uint32_t* length, plist_write_options_t options)
{
    uint64_t size = 0;
    plist_err_t res;

    if (!plist || !output || !length) {
        return PLIST_ERR_INVALID_ARG;
    }

    res = node_estimate_size((node_t)plist, &size, 0);
    if (res < 0) {
        return res;
    }

    strbuf_t *outbuf = str_buf_new(size);
    if (!outbuf) {
#if DEBUG
        fprintf(stderr, "%s: Could not allocate output buffer\n", __func__);
#endif
        return PLIST_ERR_NO_MEM;
    }

    res = _plist_write_to_strbuf(plist, outbuf, options);
    if (res < 0) {
        str_buf_free(outbuf);
        *output = NULL;
        *length = 0;
        return res;
    }
    str_buf_append(outbuf, "\0", 1);

    if (!outbuf->data) {
        str_buf_free(outbuf);
        *output = NULL;
        *length = 0;
        return PLIST_ERR_NO_MEM;
    }

    *output = (char*)outbuf->data;
    *length = outbuf->len - 1;

    outbuf->data = NULL;
    str_buf_free(outbuf);

    return PLIST_ERR_SUCCESS;
}

plist_err_t plist_write_to_stream_plutil(plist_t plist, FILE *stream, plist_write_options_t options)
{
    if (!plist || !stream) {
        return PLIST_ERR_INVALID_ARG;
    }
    strbuf_t *outbuf = str_buf_new_for_stream(stream);
    if (!outbuf) {
#if DEBUG
        fprintf(stderr, "%s: Could not allocate output buffer\n", __func__);
#endif
        return PLIST_ERR_NO_MEM;
    }

    plist_err_t res = _plist_write_to_strbuf(plist, outbuf, options);
    if (res < 0) {
        str_buf_free(outbuf);
        return res;
    }

    str_buf_free(outbuf);

    return PLIST_ERR_SUCCESS;
}
