/*
 * Copyright (C) 1999-2002 Free Software Foundation, Inc.
 * This file is part of the GNU LIBICONV Library.
 *
 * The GNU LIBICONV Library is free software; you can redistribute it
 * and/or modify it under the terms of the GNU Library General Public
 * License as published by the Free Software Foundation; either version 2
 * of the License, or (at your option) any later version.
 *
 * The GNU LIBICONV 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
 * Library General Public License for more details.
 *
 * You should have received a copy of the GNU Library General Public
 * License along with the GNU LIBICONV Library; see the file COPYING.LIB.
 * If not, write to the Free Software Foundation, Inc., 59 Temple Place -
 * Suite 330, Boston, MA 02111-1307, USA.
 */

/*
 * ISO-2022-JP-3
 */

#include "jisx0213.h"

#define ESC 0x1b

/*
 * The state is composed of one of the following values
 */
#define STATE_ASCII             0  /* Esc ( B */
#define STATE_JISX0201ROMAN     1  /* Esc ( J */
#define STATE_JISX0201KATAKANA  2  /* Esc ( I */
#define STATE_JISX0208          3  /* Esc $ @ or Esc $ B */
#define STATE_JISX02131         4  /* Esc $ ( O */
#define STATE_JISX02132         5  /* Esc $ ( P */

/*
 * In the ISO-2022-JP-3 to UCS-4 direction, the state also holds the last
 * character to be output, shifted by 3 bits.
 */

static int
iso2022_jp3_mbtowc (conv_t conv, ucs4_t *pwc, const unsigned char *s, int n)
{
  ucs4_t last_wc = conv->istate >> 3;
  if (last_wc) {
    /* Output the buffered character. */
    conv->istate &= 7;
    *pwc = last_wc;
    return 0; /* Don't advance the input pointer. */
  } else {
    state_t state = conv->istate;
    int count = 0;
    unsigned char c;
    for (;;) {
      c = *s;
      if (c == ESC) {
        if (n < count+3)
          goto none;
        if (s[1] == '(') {
          if (s[2] == 'B') {
            state = STATE_ASCII;
            s += 3; count += 3;
            if (n < count+1)
              goto none;
            continue;
          }
          if (s[2] == 'J') {
            state = STATE_JISX0201ROMAN;
            s += 3; count += 3;
            if (n < count+1)
              goto none;
            continue;
          }
          if (s[2] == 'I') {
            state = STATE_JISX0201KATAKANA;
            s += 3; count += 3;
            if (n < count+1)
              goto none;
            continue;
          }
          return RET_ILSEQ;
        }
        if (s[1] == '$') {
          if (s[2] == '@' || s[2] == 'B') {
            /* We don't distinguish JIS X 0208-1978 and JIS X 0208-1983. */
            state = STATE_JISX0208;
            s += 3; count += 3;
            if (n < count+1)
              goto none;
            continue;
          }
          if (s[2] == '(') {
            if (n < count+4)
              goto none;
            if (s[3] == 'O') {
              state = STATE_JISX02131;
              s += 4; count += 4;
              if (n < count+1)
                goto none;
              continue;
            }
            if (s[3] == 'P') {
              state = STATE_JISX02132;
              s += 4; count += 4;
              if (n < count+1)
                goto none;
              continue;
            }
          }
          return RET_ILSEQ;
        }
        return RET_ILSEQ;
      }
      break;
    }
    switch (state) {
      case STATE_ASCII:
        if (c < 0x80) {
          int ret = ascii_mbtowc(conv,pwc,s,1);
          if (ret == RET_ILSEQ)
            return RET_ILSEQ;
          if (ret != 1) abort();
          conv->istate = state;
          return count+1;
        } else
          return RET_ILSEQ;
      case STATE_JISX0201ROMAN:
        if (c < 0x80) {
          int ret = jisx0201_mbtowc(conv,pwc,s,1);
          if (ret == RET_ILSEQ)
            return RET_ILSEQ;
          if (ret != 1) abort();
          conv->istate = state;
          return count+1;
        } else
          return RET_ILSEQ;
      case STATE_JISX0201KATAKANA:
        if (c < 0x80) {
          unsigned char buf = c+0x80;
          int ret = jisx0201_mbtowc(conv,pwc,&buf,1);
          if (ret == RET_ILSEQ)
            return RET_ILSEQ;
          if (ret != 1) abort();
          conv->istate = state;
          return count+1;
        } else
          return RET_ILSEQ;
      case STATE_JISX0208:
        if (n < count+2)
          goto none;
        if (s[0] < 0x80 && s[1] < 0x80) {
          int ret = jisx0208_mbtowc(conv,pwc,s,2);
          if (ret == RET_ILSEQ)
            return RET_ILSEQ;
          if (ret != 2) abort();
          conv->istate = state;
          return count+2;
        } else
          return RET_ILSEQ;
      case STATE_JISX02131:
      case STATE_JISX02132:
        if (n < count+2)
          goto none;
        if (s[0] < 0x80 && s[1] < 0x80) {
          ucs4_t wc = jisx0213_to_ucs4(((state-STATE_JISX02131+1)<<8)+s[0],s[1]);
          if (wc) {
            if (wc < 0x80) {
              /* It's a combining character. */
              ucs4_t wc1 = jisx0213_to_ucs_combining[wc - 1][0];
              ucs4_t wc2 = jisx0213_to_ucs_combining[wc - 1][1];
              /* We cannot output two Unicode characters at once. So,
                 output the first character and buffer the second one. */
              *pwc = wc1;
              conv->istate = (wc2 << 3) | state;
            } else {
              *pwc = wc;
              conv->istate = state;
            }
            return count+2;
          }
        }
        return RET_ILSEQ;
      default: abort();
    }
  none:
    conv->istate = state;
    return RET_TOOFEW(count);
  }
}

static int
iso2022_jp3_flushwc (conv_t conv, ucs4_t *pwc)
{
  ucs4_t last_wc = conv->istate >> 3;
  if (last_wc) {
    /* Output the buffered character. */
    conv->istate &= 7;
    *pwc = last_wc;
    return 1;
  } else
    return 0;
}

/*
 * In the UCS-4 to ISO-2022-JP-3 direction, the state also holds the last two
 * bytes to be output, shifted by 3 bits, and the STATE_xxxxx value that was
 * effective before this buffered character, shifted by 19 bits.
 */

/* Composition tables for each of the relevant combining characters.  */
static const struct { unsigned short base; unsigned short composed; } iso2022_jp3_comp_table_data[] = {
#define iso2022_jp3_comp_table02e5_idx 0
#define iso2022_jp3_comp_table02e5_len 1
  { 0x2b64, 0x2b65 }, /* 0x12B65 = 0x12B64 U+02E5 */
#define iso2022_jp3_comp_table02e9_idx (iso2022_jp3_comp_table02e5_idx+iso2022_jp3_comp_table02e5_len)
#define iso2022_jp3_comp_table02e9_len 1
  { 0x2b60, 0x2b66 }, /* 0x12B66 = 0x12B60 U+02E9 */
#define iso2022_jp3_comp_table0300_idx (iso2022_jp3_comp_table02e9_idx+iso2022_jp3_comp_table02e9_len)
#define iso2022_jp3_comp_table0300_len 5
  { 0x295c, 0x2b44 }, /* 0x12B44 = 0x1295C U+0300 */
  { 0x2b38, 0x2b48 }, /* 0x12B48 = 0x12B38 U+0300 */
  { 0x2b37, 0x2b4a }, /* 0x12B4A = 0x12B37 U+0300 */
  { 0x2b30, 0x2b4c }, /* 0x12B4C = 0x12B30 U+0300 */
  { 0x2b43, 0x2b4e }, /* 0x12B4E = 0x12B43 U+0300 */
#define iso2022_jp3_comp_table0301_idx (iso2022_jp3_comp_table0300_idx+iso2022_jp3_comp_table0300_len)
#define iso2022_jp3_comp_table0301_len 4
  { 0x2b38, 0x2b49 }, /* 0x12B49 = 0x12B38 U+0301 */
  { 0x2b37, 0x2b4b }, /* 0x12B4B = 0x12B37 U+0301 */
  { 0x2b30, 0x2b4d }, /* 0x12B4D = 0x12B30 U+0301 */
  { 0x2b43, 0x2b4f }, /* 0x12B4F = 0x12B43 U+0301 */
#define iso2022_jp3_comp_table309a_idx (iso2022_jp3_comp_table0301_idx+iso2022_jp3_comp_table0301_len)
#define iso2022_jp3_comp_table309a_len 14
  { 0x242b, 0x2477 }, /* 0x12477 = 0x1242B U+309A */
  { 0x242d, 0x2478 }, /* 0x12478 = 0x1242D U+309A */
  { 0x242f, 0x2479 }, /* 0x12479 = 0x1242F U+309A */
  { 0x2431, 0x247a }, /* 0x1247A = 0x12431 U+309A */
  { 0x2433, 0x247b }, /* 0x1247B = 0x12433 U+309A */
  { 0x252b, 0x2577 }, /* 0x12577 = 0x1252B U+309A */
  { 0x252d, 0x2578 }, /* 0x12578 = 0x1252D U+309A */
  { 0x252f, 0x2579 }, /* 0x12579 = 0x1252F U+309A */
  { 0x2531, 0x257a }, /* 0x1257A = 0x12531 U+309A */
  { 0x2533, 0x257b }, /* 0x1257B = 0x12533 U+309A */
  { 0x253b, 0x257c }, /* 0x1257C = 0x1253B U+309A */
  { 0x2544, 0x257d }, /* 0x1257D = 0x12544 U+309A */
  { 0x2548, 0x257e }, /* 0x1257E = 0x12548 U+309A */
  { 0x2675, 0x2678 }, /* 0x12678 = 0x12675 U+309A */
};

#define SPLIT_STATE \
  unsigned short lasttwo = state >> 3; state_t prevstate = state >> 19; state &= 7
#define COMBINE_STATE \
  state |= (prevstate << 19) | (lasttwo << 3)
#define COMBINE_STATE_NO_LASTTWO \
  /* assume lasttwo == 0, then prevstate is ignored */

static int
iso2022_jp3_wctomb (conv_t conv, unsigned char *r, ucs4_t wc, int n)
{
  int count = 0;
  unsigned char buf[2];
  unsigned short jch;
  int ret;
  state_t state = conv->ostate;
  SPLIT_STATE;

  if (lasttwo) {
    /* Attempt to combine the last character with this one. */
    unsigned int idx;
    unsigned int len;

    if (wc == 0x02e5)
      idx = iso2022_jp3_comp_table02e5_idx,
      len = iso2022_jp3_comp_table02e5_len;
    else if (wc == 0x02e9)
      idx = iso2022_jp3_comp_table02e9_idx,
      len = iso2022_jp3_comp_table02e9_len;
    else if (wc == 0x0300)
      idx = iso2022_jp3_comp_table0300_idx,
      len = iso2022_jp3_comp_table0300_len;
    else if (wc == 0x0301)
      idx = iso2022_jp3_comp_table0301_idx,
      len = iso2022_jp3_comp_table0301_len;
    else if (wc == 0x309a)
      idx = iso2022_jp3_comp_table309a_idx,
      len = iso2022_jp3_comp_table309a_len;
    else
      goto not_combining;

    do
      if (iso2022_jp3_comp_table_data[idx].base == lasttwo)
        break;
    while (++idx, --len > 0);

    if (len > 0) {
      /* Output the combined character. */
      /* We know the combined character is in JISX0213 plane 1, but
         the buffered character may have been in JISX0208 or in
         JISX0213 plane 1. */
      count = (state != STATE_JISX02131 ? 4 : 0) + 2;
      if (n < count)
        return RET_TOOSMALL;
      if (state != STATE_JISX02131) {
        r[0] = ESC;
        r[1] = '$';
        r[2] = '(';
        r[3] = 'O';
        r += 4;
        state = STATE_JISX02131;
      }
      lasttwo = iso2022_jp3_comp_table_data[idx].composed;
      r[0] = (lasttwo >> 8) & 0xff;
      r[1] = lasttwo & 0xff;
      COMBINE_STATE_NO_LASTTWO;
      conv->ostate = state;
      return count;
    }

  not_combining:
    /* Output the buffered character. */
    /* We know it is in JISX0208 or in JISX0213 plane 1. */
    count = (prevstate != state ? 3 : 0) + 2;
    if (n < count)
      return RET_TOOSMALL;
    if (prevstate != state) {
      if (state != STATE_JISX0208) abort();
      r[0] = ESC;
      r[1] = '$';
      r[2] = 'B';
      r += 3;
    }
    r[0] = (lasttwo >> 8) & 0xff;
    r[1] = lasttwo & 0xff;
    r += 2;
  }

  /* Try ASCII. */
  ret = ascii_wctomb(conv,buf,wc,1);
  if (ret != RET_ILUNI) {
    if (ret != 1) abort();
    if (buf[0] < 0x80) {
      count += (state == STATE_ASCII ? 1 : 4);
      if (n < count)
        return RET_TOOSMALL;
      if (state != STATE_ASCII) {
        r[0] = ESC;
        r[1] = '(';
        r[2] = 'B';
        r += 3;
        state = STATE_ASCII;
      }
      r[0] = buf[0];
      COMBINE_STATE_NO_LASTTWO;
      conv->ostate = state;
      return count;
    }
  }

  /* Try JIS X 0201-1976 Roman. */
  ret = jisx0201_wctomb(conv,buf,wc,1);
  if (ret != RET_ILUNI) {
    if (ret != 1) abort();
    if (buf[0] < 0x80) {
      count += (state == STATE_JISX0201ROMAN ? 1 : 4);
      if (n < count)
        return RET_TOOSMALL;
      if (state != STATE_JISX0201ROMAN) {
        r[0] = ESC;
        r[1] = '(';
        r[2] = 'J';
        r += 3;
        state = STATE_JISX0201ROMAN;
      }
      r[0] = buf[0];
      COMBINE_STATE_NO_LASTTWO;
      conv->ostate = state;
      return count;
    }
  }

  jch = ucs4_to_jisx0213(wc);

  /* Try JIS X 0208-1990 in place of JIS X 0208-1978 and JIS X 0208-1983. */
  ret = jisx0208_wctomb(conv,buf,wc,2);
  if (ret != RET_ILUNI) {
    if (ret != 2) abort();
    if (buf[0] < 0x80 && buf[1] < 0x80) {
      if (jch & 0x0080) {
        /* A possible match in comp_table_data. Buffer it. */
        prevstate = state;
        lasttwo = jch & 0x7f7f;
        state = STATE_JISX0208;
        COMBINE_STATE;
        conv->ostate = state;
        return count;
      } else {
        count += (state == STATE_JISX0208 ? 2 : 5);
        if (n < count)
          return RET_TOOSMALL;
        if (state != STATE_JISX0208) {
          r[0] = ESC;
          r[1] = '$';
          r[2] = 'B';
          r += 3;
          state = STATE_JISX0208;
        }
        r[0] = buf[0];
        r[1] = buf[1];
        COMBINE_STATE_NO_LASTTWO;
        conv->ostate = state;
        return count;
      }
    }
  }

  /* Try JISX 0213 plane 1 and JISX 0213 plane 2. */
  if (jch != 0) {
    if (jch & 0x8000) {
      /* JISX 0213 plane 2. */
      if (state != STATE_JISX02132) {
        count += 4;
        if (n < count)
          return RET_TOOSMALL;
        r[0] = ESC;
        r[1] = '$';
        r[2] = '(';
        r[3] = 'P';
        r += 4;
        state = STATE_JISX02132;
      }
    } else {
      /* JISX 0213 plane 1. */
      if (state != STATE_JISX02131) {
        count += 4;
        if (n < count)
          return RET_TOOSMALL;
        r[0] = ESC;
        r[1] = '$';
        r[2] = '(';
        r[3] = 'O';
        r += 4;
        state = STATE_JISX02131;
      }
    }
    if (jch & 0x0080) {
      /* A possible match in comp_table_data. We have to buffer it. */
      /* We know it's a JISX 0213 plane 1 character. */
      if (jch & 0x8000) abort();
      prevstate = state;
      lasttwo = jch & 0x7f7f;
      COMBINE_STATE;
      conv->ostate = state;
      return count;
    }
    count += 2;
    if (n < count)
      return RET_TOOSMALL;
    r[0] = (jch >> 8) & 0x7f;
    r[1] = jch & 0x7f;
    COMBINE_STATE_NO_LASTTWO;
    conv->ostate = state;
    return count;
  }

  /* Try JIS X 0201-1976 Katakana. This is not officially part of
     ISO-2022-JP-3. Therefore we try it after all other attempts. */
  ret = jisx0201_wctomb(conv,buf,wc,1);
  if (ret != RET_ILUNI) {
    if (ret != 1) abort();
    if (buf[0] >= 0x80) {
      count += (state == STATE_JISX0201KATAKANA ? 1 : 4);
      if (n < count)
        return RET_TOOSMALL;
      if (state != STATE_JISX0201KATAKANA) {
        r[0] = ESC;
        r[1] = '(';
        r[2] = 'I';
        r += 3;
        state = STATE_JISX0201KATAKANA;
      }
      r[0] = buf[0]-0x80;
      COMBINE_STATE_NO_LASTTWO;
      conv->ostate = state;
      return count;
    }
  }

  return RET_ILUNI;
}

static int
iso2022_jp3_reset (conv_t conv, unsigned char *r, int n)
{
  state_t state = conv->ostate;
  SPLIT_STATE;
  {
    int count =
      (lasttwo ? (prevstate != state ? 3 : 0) + 2 : 0)
      + (state != STATE_ASCII ? 3 : 0);
    if (n < count)
      return RET_TOOSMALL;
    if (lasttwo) {
      if (prevstate != state) {
        if (state != STATE_JISX0208) abort();
        r[0] = ESC;
        r[1] = '$';
        r[2] = 'B';
        r += 3;
      }
      r[0] = (lasttwo >> 8) & 0xff;
      r[1] = lasttwo & 0xff;
      r += 2;
    }
    if (state != STATE_ASCII) {
      r[0] = ESC;
      r[1] = '(';
      r[2] = 'B';
    }
    /* conv->ostate = 0; will be done by the caller */
    return count;
  }
}

#undef COMBINE_STATE_NO_LASTTWO
#undef COMBINE_STATE
#undef SPLIT_STATE
#undef STATE_JISX02132
#undef STATE_JISX02131
#undef STATE_JISX0208
#undef STATE_JISX0201KATAKANA
#undef STATE_JISX0201ROMAN
#undef STATE_ASCII
