/**
 * @file output.cpp
 * Does all the output & comment formatting.
 *
 * $Id: output.cpp 510 2006-09-20 01:14:56Z bengardner $
 */

#include "uncrustify_types.h"
#include "prototypes.h"
#include "chunk_list.h"
#include <cstring>
#include <cstdlib>



void add_char(char ch)
  {
    /* convert a newline into the LF/CRLF/CR sequence */
  if (ch == '\n')
    {
    fputs(cpd.newline, cpd.fout);
    cpd.column      = 1;
    cpd.did_newline = 1;
    }
  else
    {
    fputc(ch, cpd.fout);

    if (ch == '\t')
      cpd.column = next_tab_column(cpd.column);
    else
      cpd.column++;
    }
  }

void add_text(const char *text)
  {
  char ch;

  while ((ch = *text) != 0)
    {
    text++;
    add_char(ch);
    }
  }

void add_text_len(const char *text, int len)
  {
  while (len-- > 0)
    {
    add_char(*text);
    text++;
    }
  }

/**
 * Advance to a specific column
 * cpd.column is the current column
 *
 * @param column  The column to advance to
 */
void output_to_column(int column, bool allow_tabs)
  {
  int nc;

  cpd.did_newline = 0;

  if (allow_tabs)
    {
      /* tab out as far as possible and then use spaces */
    while ((nc = next_tab_column(cpd.column)) <= column)
      add_text("\t");
    }

    /* space out the final bit */
  while (cpd.column < column)
    add_text(" ");
  }

void output_indent(int column, int brace_col)
  {
  if ((cpd.column == 1) && (cpd.settings[UO_indent_with_tabs].n != 0))
    {
    if (cpd.settings[UO_indent_with_tabs].n == 2)
      brace_col = column;

      /* tab out as far as possible and then use spaces */
    int nc;

    while ((nc = next_tab_column(cpd.column)) <= brace_col)
      add_text("\t");
    }

    /* space out the rest */
  while (cpd.column < column)
    add_text(" ");
  }

void output_parsed(FILE *pfile)
  {
  chunk_t *pc;
  int cnt;

  output_options(pfile);
  output_defines(pfile);
  output_types(pfile);

  fprintf(pfile, "-=====-\n");
  fprintf(pfile, "Line      Tag          Parent     Columns  Br/Lvl/pp Flg Nl  Text");

  for (pc = chunk_get_head(); pc != NULL; pc = chunk_get_next(pc))
    {
    fprintf(pfile, "\n%3d> %13.13s[%13.13s][%2d/%2d/%2d][%d/%d/%d][%6x][%d-%d]",
            pc->orig_line, get_token_name(pc->type),
            get_token_name(pc->parent_type),
            pc->column, pc->orig_col, pc->orig_col_end,
            pc->brace_level, pc->level, pc->pp_level,
            pc->flags, pc->nl_count, pc->after_tab);

    if ((pc->type != CT_NEWLINE) && (pc->len != 0))
      {
      for (cnt = 0; cnt < pc->column; cnt++)
        fprintf(pfile, " ");

      fprintf(pfile, "%.*s", pc->len, pc->str);
      }
    }

  fprintf(pfile, "\n-=====-\n");
  fflush(pfile);
  }

void output_options(FILE *pfile)
  {
  int idx;
  const option_map_value *ptr;

  fprintf(pfile, "-== Options ==-\n");

  for (idx = 0; idx < UO_option_count; idx++)
    {
    ptr = get_option_name(idx);

    if (ptr != NULL)
      {
      if (ptr->type == AT_BOOL)
        {
        fprintf(pfile, "%3d) %32s = %s\n",
                ptr->id, ptr->name,
                cpd.settings[ptr->id].b ? "True" : "False");
        }
      else if (ptr->type == AT_IARF)
        {
        fprintf(pfile, "%3d) %32s = %s\n",
                ptr->id, ptr->name,
                (cpd.settings[ptr->id].a == AV_ADD) ? "Add" :
                (cpd.settings[ptr->id].a == AV_REMOVE) ? "Remove" :
                (cpd.settings[ptr->id].a == AV_FORCE) ? "Force" : "Ignore");
        }
      else if (ptr->type == AT_LINE)
        {
        fprintf(pfile, "%3d) %32s = %s\n",
                ptr->id, ptr->name,
                (cpd.settings[ptr->id].le == LE_AUTO) ? "Auto" :
                (cpd.settings[ptr->id].le == LE_LF) ? "LF" :
                (cpd.settings[ptr->id].le == LE_CRLF) ? "CRLF" :
                (cpd.settings[ptr->id].le == LE_CR) ? "CR" : "???");
        }
      else     /* AT_NUM */
        fprintf(pfile, "%3d) %32s = %d\n",
                ptr->id, ptr->name, cpd.settings[ptr->id].n);
      }
    }
  }

/**
 * This renders the chunk list to a file.
 */
void output_text(FILE *pfile)
  {
  chunk_t *pc;
  chunk_t *prev;
  int cnt;
  int lvlcol;
  bool allow_tabs;

  cpd.fout = pfile;

  for (pc = chunk_get_head(); pc != NULL; pc = chunk_get_next(pc))
    {
    if (pc->type == CT_NEWLINE)
      {
      for (cnt = 0; cnt < pc->nl_count; cnt++)
        add_char('\n');

      cpd.did_newline = 1;
      cpd.column      = 1;
      LOG_FMT(LOUTIND, " xx\n");
      }
    else if (pc->type == CT_COMMENT_MULTI)
      output_comment_multi(pc);
    else if (pc->type == CT_COMMENT_CPP)
      pc = output_comment_cpp(pc);
    else if (pc->len == 0)
        /* don't do anything for non-visible stuff */
      LOG_FMT(LOUTIND, " <%d> -", pc->column);
    else
      {
        /* indent to the 'level' first */
      if (cpd.did_newline)
        {
        if (cpd.settings[UO_indent_with_tabs].n == 1)
          {
          lvlcol = 1 + (pc->brace_level * cpd.settings[UO_indent_columns].n);

          if ((pc->column >= lvlcol) && (lvlcol > 1))
            output_to_column(lvlcol, true);
          }

        allow_tabs = (cpd.settings[UO_indent_with_tabs].n == 2) ||
                     (chunk_is_comment(pc) &&
                      (cpd.settings[UO_indent_with_tabs].n != 0));

        LOG_FMT(LOUTIND, "  %d> col %d/%d - ", pc->orig_line, pc->column, cpd.column);
        }
      else
        {
          /* not the first item on a line */
        if (cpd.settings[UO_align_keep_tabs].b)
          allow_tabs = pc->after_tab;
        else
          {
          prev       = chunk_get_prev(pc);
          allow_tabs = (cpd.settings[UO_align_with_tabs].b &&
                        ((pc->flags & PCF_WAS_ALIGNED) != 0) &&
                        (((pc->column - 1) % cpd.settings[UO_output_tab_size].n) == 0) &&
                        ((prev->column + prev->len + 1) != pc->column));
          }

        LOG_FMT(LOUTIND, " %d -", pc->column);
        }

      output_to_column(pc->column, allow_tabs);
      add_text_len(pc->str, pc->len);
      cpd.did_newline = chunk_is_newline(pc);
      }
    }
  }

/**
 * Given a multi-line comemnt block that starts in column X, figure out how
 * much subsequent lines should be indented.
 *
 * The answer is either 0 or 1.
 *
 * The decision is based on:
 *  - the first line length
 *  - the second line leader length
 *  - the last line length
 *
 * If the first and last line are the same length and don't contain any alnum
 * chars and (the first line len > 2 or the second leader is the same as the
 * first line length), then the indent is 0.
 *
 * If the leader on the second line is 1 wide or missing, then the indent is 1.
 *
 * Otherwise, the indent is 0.
 *
 * @param str       The comment string
 * @param len       Length of the comment
 * @param start_col Starting column
 * @return 0 or 1
 */
static int calculate_comment_body_indent(const char *str, int len, int start_col)
  {
  int idx       = 0;
  int first_len = 0;
  int last_len  = 0;
  int width     = 0;

    /* find the last line length */
  for (idx = len - 1; idx > 0; idx--)
    {
    if ((str[idx] == '\n') || (str[idx] == '\r'))
      {
      idx++;

      while ((idx < len) && ((str[idx] == ' ') || (str[idx] == '\t')))
        idx++;

      last_len = len - idx;
      break;
      }
    }

    /* find the first line length */
  for (idx = 0; idx < len; idx++)
    {
    if ((str[idx] == '\n') || (str[idx] == '\r'))
      {
      first_len = idx;

      while ((str[first_len - 1] == ' ') || (str[first_len - 1] == '\t'))
        first_len--;

        /* handle DOS endings */
      if ((str[idx] == '\r') && (str[idx + 1] == '\n'))
        idx++;

      idx++;
      break;
      }
    }

    /* Scan the second line */
  width = 0;

  for (/* nada */; idx < len; idx++)
    {
    if ((str[idx] == ' ') || (str[idx] == '\t'))
      {
      if (width > 0)
        break;

      continue;
      }

    if ((str[idx] == '\n') || (str[idx] == '\r'))
        /* Done with second line */
      break;

      /* Count the leading chars */
    if ((str[idx] == '*') ||
        (str[idx] == '|') ||
        (str[idx] == '\\') ||
        (str[idx] == '#') ||
        (str[idx] == '+'))
      width++;
    else
      break;
    }

  //LOG_FMT(LSYS, "%s: first=%d last=%d width=%d\n", __func__, first_len, last_len, width);

    /*TODO: make the first_len minimum (4) configurable? */
  if ((first_len == last_len) && ((first_len > 4) || first_len == width))
    return 0;

  return (width == 2) ? 0 : 1;
  }

/**
 * Outputs the CPP comment at pc.
 * CPP comment combining is done here
 *
 * @return the last chunk output'd
 */
chunk_t *output_comment_cpp(chunk_t *first)
  {
  int col    = first->column;
  int col_br = 1 + (first->brace_level * cpd.settings[UO_indent_columns].n);

    /* Make sure we have at least one space past the last token */
  if (first->parent_type == CT_COMMENT_END)
    {
    chunk_t *prev = chunk_get_prev(first);

    if (prev != NULL)
      {
      int col_min = prev->column + prev->len + 1;

      if (col < col_min)
        col = col_min;
      }
    }

    /* Bump out to the column */
  output_indent(col, col_br);

  if (!cpd.settings[UO_cmt_cpp_to_c].b)
    {
    add_text_len(first->str, first->len);
    return first;
    }

    /* If we are grouping, see if there is something to group */
  bool combined = false;

  if (cpd.settings[UO_cmt_cpp_group].b)
    {
      /* next is a newline by definition */
    chunk_t *next = chunk_get_next(first);

    if ((next != NULL) && (next->nl_count == 1))
      {
      next = chunk_get_next(next);

      /**
       * Only combine the next comment if they are both at indent level or
       * the second one is NOT at indent or less
       *
       * A trailing comment cannot be combined with a comment at indent
       * level or less
       */
      if ((next != NULL) &&
          (next->type == CT_COMMENT_CPP) &&
          (((next->column == 1) && (first->column == 1)) ||
           ((next->column == col_br) && (first->column == col_br)) ||
           ((next->column > col_br) && (first->parent_type == CT_COMMENT_END))))
        combined = true;
      }
    }

  if (!combined)
    {
      /* nothing to group: just output a single line */
    add_text_len("/*", 2);

    if ((first->str[2] != ' ') && (first->str[2] != '\t'))
      add_char(' ');

    add_text_len(&first->str[2], first->len - 2);
    add_text_len(" */", 3);
    return first;
    }

  chunk_t *pc   = first;
  chunk_t *last = first;

    /* Output the first line */
  add_text_len("/*", 2);

  if (combined && cpd.settings[UO_cmt_cpp_nl_start].b)
    /* I suppose someone more clever could do this without a goto or
     * repeating too much code...
     */
    goto cpp_newline;

  goto cpp_addline;

    /* Output combined lines */
  while ((pc = chunk_get_next(pc)) != NULL)
    {
    if ((pc->type == CT_NEWLINE) && (pc->nl_count == 1))
      continue;

    if (pc->type != CT_COMMENT_CPP)
      break;

    if (((pc->column == 1) && (first->column == 1)) ||
        ((pc->column == col_br) && (first->column == col_br)) ||
        ((pc->column > col_br) && (first->parent_type == CT_COMMENT_END)))
      {
      last = pc;
cpp_newline:
      add_char('\n');
      output_indent(col, col_br);
      add_char(' ');
      add_char(cpd.settings[UO_cmt_star_cont].b ? '*' : ' ');
cpp_addline:

      if ((pc->str[2] != ' ') && (pc->str[2] != '\t'))
        add_char(' ');

      add_text_len(&pc->str[2], pc->len - 2);
      }
    }

  if (cpd.settings[UO_cmt_cpp_nl_end].b)
    {
    add_char('\n');
    output_indent(col, col_br);
    }

  add_text_len(" */", 3);
  return last;
  }

void output_comment_multi(chunk_t *pc)
  {
  int cmt_col = pc->column;
  const char *cmt_str;
  int remaining;
  char ch;
  chunk_t    *prev;
  char line[1024];
  int line_len;
  int line_count = 0;
  int ccol;
  int col_diff = 0;
  int xtra     = 1;

  prev = chunk_get_prev(pc);

  if ((prev != NULL) && (prev->type != CT_NEWLINE))
    cmt_col = pc->orig_col;
  else
    col_diff = pc->orig_col - pc->column;

  //   fprintf(stderr, "Indenting1 line %d to col %d (orig=%d) col_diff=%d\n",
  //           pc->orig_line, cmt_col, pc->orig_col, col_diff);

  xtra = calculate_comment_body_indent(pc->str, pc->len, pc->column);

  ccol      = 1;
  remaining = pc->len;
  cmt_str   = pc->str;
  line_len  = 0;

  while (remaining > 0)
    {
    ch = *cmt_str;
    cmt_str++;
    remaining--;

      /* handle the CRLF and CR endings. convert both to LF */
    if (ch == '\r')
      {
      ch = '\n';

      if (*cmt_str == '\n')
        {
        cmt_str++;
        remaining--;
        }
      }

      /* Find the start column */
    if (line_len == 0)
      {
      if (ch == ' ')
        {
        ccol++;
        continue;
        }
      else if (ch == '\t')
        {
        ccol = calc_next_tab_column(ccol, cpd.settings[UO_input_tab_size].n);
        continue;
        }
      else
        {
        //fprintf(stderr, "%d] Text starts in col %d\n", line_count, ccol);
        }
      }

    line[line_len++] = ch;

      /* If we just hit an end of line OR we just hit end-of-comment... */
    if ((ch == '\n') || (remaining == 0))
      {
      line_count++;

        /* strip trailing tabs and spaces before the newline */
      if (ch == '\n')
        {
        line_len--;

        while ((line_len > 0) &&
               ((line[line_len - 1] == ' ') ||
                (line[line_len - 1] == '\t')))
          line_len--;

        line[line_len++] = ch;
        }

      line[line_len] = 0;

      if (line_count == 1)
        {
        /* this is the first line - add unchanged */

          /*TODO: need to support indent_with_tabs mode 1 */
        output_to_column(cmt_col, cpd.settings[UO_indent_with_tabs].b);
        add_text_len(line, line_len);
        }
      else
        {
        /* This is not the first line, so we need to indent to the
         * correct column.
         */
        ccol -= col_diff;

        if (ccol < cmt_col)
          ccol = cmt_col;

        if (line[0] == '\n')
          {
            /* Emtpy line - just a '\n' */
          if (cpd.settings[UO_cmt_star_cont].b)
            {
            output_to_column(cmt_col, cpd.settings[UO_indent_with_tabs].b);
            add_text((xtra == 1) ? " *" : "*");
            }

          add_char('\n');
          }
        else
          {
            /* If this doesn't start with a '*' or '|' */
          if ((line[0] != '*') && (line[0] != '|') && (line[0] != '#') &&
              (line[0] != '\\') && (line[0] != '+'))
            {
            output_to_column(cmt_col, cpd.settings[UO_indent_with_tabs].b);

            if (cpd.settings[UO_cmt_star_cont].b)
              add_text((xtra == 1) ? " * " : "*  ");
            else
              add_text("   ");

            output_to_column(ccol, cpd.settings[UO_indent_with_tabs].b);
            }
          else
            output_to_column(cmt_col + xtra, cpd.settings[UO_indent_with_tabs].b);

          add_text_len(line, line_len);
          }
        }

      line_len = 0;
      ccol     = 1;
      }
    }
  }

