-static size_t yaz_flush_ISO8859_1(yaz_iconv_t cd,
- char **outbuf, size_t *outbytesleft)
-{
- if (cd->compose_char)
- {
- unsigned char *outp = (unsigned char *) *outbuf;
- if (*outbytesleft < 1)
- {
- cd->my_errno = YAZ_ICONV_E2BIG;
- return (size_t)(-1);
- }
- *outp++ = (unsigned char) cd->compose_char;
- (*outbytesleft)--;
- *outbuf = (char *) outp;
- cd->compose_char = 0;
- }
- return 0;
-}
-
-static unsigned long lookup_marc8(yaz_iconv_t cd,
- unsigned long x, int *comb,
- const char **page_chr)
-{
- char utf8_buf[7];
- char *utf8_outbuf = utf8_buf;
- size_t utf8_outbytesleft = sizeof(utf8_buf)-1, r;
-
- r = yaz_write_UTF8(cd, x, &utf8_outbuf, &utf8_outbytesleft);
- if (r == (size_t)(-1))
- {
- cd->my_errno = YAZ_ICONV_EILSEQ;
- return 0;
- }
- else
- {
- unsigned char *inp;
- size_t inbytesleft, no_read_sub = 0;
- unsigned long x;
-
- *utf8_outbuf = '\0';
- inp = (unsigned char *) utf8_buf;
- inbytesleft = strlen(utf8_buf);
-
- x = yaz_marc8r_42_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "(B";
- return x;
- }
- x = yaz_marc8r_45_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "(B";
- return x;
- }
- x = yaz_marc8r_62_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "b";
- return x;
- }
- x = yaz_marc8r_70_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "p";
- return x;
- }
- x = yaz_marc8r_32_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "(2";
- return x;
- }
- x = yaz_marc8r_4E_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "(N";
- return x;
- }
- x = yaz_marc8r_51_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "(Q";
- return x;
- }
- x = yaz_marc8r_33_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "(3";
- return x;
- }
- x = yaz_marc8r_34_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "(4";
- return x;
- }
- x = yaz_marc8r_53_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "(S";
- return x;
- }
- x = yaz_marc8r_31_conv(inp, inbytesleft, &no_read_sub, comb, 255, 0);
- if (x)
- {
- *page_chr = ESC "$1";
- return x;
- }
- cd->my_errno = YAZ_ICONV_EILSEQ;
- return x;
- }
-}
-
-static size_t flush_combos(yaz_iconv_t cd,
- char **outbuf, size_t *outbytesleft)
-{
- unsigned long y = cd->write_marc8_last;
-
- if (!y)
- return 0;
-
- assert(cd->write_marc8_lpage);
- if (cd->write_marc8_lpage)
- {
- size_t r = yaz_write_marc8_page_chr(cd, outbuf, outbytesleft,
- cd->write_marc8_lpage);
- if (r)
- return r;
- }
-
- if (9 >= *outbytesleft)
- {
- cd->my_errno = YAZ_ICONV_E2BIG;
- return (size_t) (-1);
- }
- if (cd->write_marc8_ncr)
- {
- yaz_snprintf(*outbuf, 9, "&#x%04x;", y);
- (*outbytesleft) -= 8;
- (*outbuf) += 8;
- }
- else
- {
- size_t out_no = 0;
- unsigned char byte;
-
- byte = (unsigned char )((y>>16) & 0xff);
- if (byte)
- (*outbuf)[out_no++] = byte;
- byte = (unsigned char)((y>>8) & 0xff);
- if (byte)
- (*outbuf)[out_no++] = byte;
- byte = (unsigned char )(y & 0xff);
- if (byte)
- (*outbuf)[out_no++] = byte;
- *outbuf += out_no;
- (*outbytesleft) -= out_no;
- }
-
- if (cd->write_marc8_second_half_char)
- {
- *(*outbuf)++ = cd->write_marc8_second_half_char;
- (*outbytesleft)--;
- }
-
- cd->write_marc8_last = 0;
- cd->write_marc8_ncr = 0;
- cd->write_marc8_lpage = 0;
- cd->write_marc8_second_half_char = 0;
- return 0;
-}
-
-static size_t yaz_write_marc8_page_chr(yaz_iconv_t cd,
- char **outbuf, size_t *outbytesleft,
- const char *page_chr)
-{
- const char **old_page_chr = &cd->write_marc8_g0;
-
- /* are we going to a G1-set (such as such as ESC ")!E") */
- if (page_chr && page_chr[1] == ')')
- old_page_chr = &cd->write_marc8_g1;
-
- if (!*old_page_chr || strcmp(page_chr, *old_page_chr))
- {
- size_t plen = 0;
- const char *page_out = page_chr;
-
- if (*outbytesleft < 8)
- {
- cd->my_errno = YAZ_ICONV_E2BIG;
-
- return (size_t) (-1);
- }
-
- if (*old_page_chr)
- {
- if (!strcmp(*old_page_chr, ESC "p")
- || !strcmp(*old_page_chr, ESC "g")
- || !strcmp(*old_page_chr, ESC "b"))
- {
- page_out = ESC "s";
- /* Technique 1 leave */
- if (strcmp(page_chr, ESC "(B")) /* Not going ASCII page? */
- {
- /* Must leave script + enter new page */
- plen = strlen(page_out);
- memcpy(*outbuf, page_out, plen);
- (*outbuf) += plen;
- (*outbytesleft) -= plen;
- page_out = ESC "(B";
- }
- }
- }
- *old_page_chr = page_chr;
- plen = strlen(page_out);
- memcpy(*outbuf, page_out, plen);
- (*outbuf) += plen;
- (*outbytesleft) -= plen;
- }
- return 0;
-}
-
-
-static size_t yaz_write_marc8_2(yaz_iconv_t cd, unsigned long x,
- char **outbuf, size_t *outbytesleft,
- int loss_mode)
-{
- int comb = 0;
- int enable_ncr = 0;
- const char *page_chr = 0;
- unsigned long y = lookup_marc8(cd, x, &comb, &page_chr);
-
- if (!y)
- {
- if (loss_mode == 0 || cd->my_errno != YAZ_ICONV_EILSEQ)
- return (size_t) (-1);
- page_chr = ESC "(B";
- if (loss_mode == 1)
- y = '|';
- else
- {
- y = x;
- enable_ncr = 1;
- }
- }
-
- if (comb)
- {
- if (page_chr)
- {
- size_t r = yaz_write_marc8_page_chr(cd, outbuf, outbytesleft,
- page_chr);
- if (r)
- return r;
- }
- if (x == 0x0361)
- cd->write_marc8_second_half_char = 0xEC;
- else if (x == 0x0360)
- cd->write_marc8_second_half_char = 0xFB;
-
- if (*outbytesleft <= 1)
- {
- cd->my_errno = YAZ_ICONV_E2BIG;
- return (size_t) (-1);
- }
- *(*outbuf)++ = y;
- (*outbytesleft)--;
- }
- else
- {
- size_t r = flush_combos(cd, outbuf, outbytesleft);
- if (r)
- return r;
-
- cd->write_marc8_last = y;
- cd->write_marc8_lpage = page_chr;
- cd->write_marc8_ncr = enable_ncr;
- }
- return 0;
-}
-
-static size_t yaz_flush_marc8(yaz_iconv_t cd,
- char **outbuf, size_t *outbytesleft)
-{
- size_t r = flush_combos(cd, outbuf, outbytesleft);
- if (r)
- return r;
- cd->write_marc8_g1 = 0;
- return yaz_write_marc8_page_chr(cd, outbuf, outbytesleft, ESC "(B");
-}
-
-static size_t yaz_write_marc8_generic(yaz_iconv_t cd, unsigned long x,
- char **outbuf, size_t *outbytesleft,
- int loss_mode);
-
-static size_t yaz_write_marc8_normal(yaz_iconv_t cd, unsigned long x,
- char **outbuf, size_t *outbytesleft)
-{
- return yaz_write_marc8_generic(cd, x, outbuf, outbytesleft, 0);
-}
-
-static size_t yaz_write_marc8_lossy(yaz_iconv_t cd, unsigned long x,
- char **outbuf, size_t *outbytesleft)
-{
- return yaz_write_marc8_generic(cd, x, outbuf, outbytesleft, 1);
-}
-
-static size_t yaz_write_marc8_lossless(yaz_iconv_t cd, unsigned long x,
- char **outbuf, size_t *outbytesleft)
-{
- return yaz_write_marc8_generic(cd, x, outbuf, outbytesleft, 2);
-}
-
-static size_t yaz_write_marc8_generic(yaz_iconv_t cd, unsigned long x,
- char **outbuf, size_t *outbytesleft,
- int loss_mode)
-{
- if (x >= 0xc0 && x <= 0xff) /* optimization. min and max .y values */
- {
- int i;
- for (i = 0; latin1_comb[i].x1; i++)
- {
- if (x == latin1_comb[i].y)
- {
- size_t r ;
- /* save the output pointers .. */
- char *outbuf0 = *outbuf;
- size_t outbytesleft0 = *outbytesleft;
- int last_ch = cd->write_marc8_last;
- int ncr = cd->write_marc8_ncr;
- const char *lpage = cd->write_marc8_lpage;
-
- r = yaz_write_marc8_2(cd, latin1_comb[i].x1,
- outbuf, outbytesleft, loss_mode);
- if (r)
- return r;
- r = yaz_write_marc8_2(cd, latin1_comb[i].x2,
- outbuf, outbytesleft, loss_mode);
- if (r && cd->my_errno == YAZ_ICONV_E2BIG)
- {
- /* not enough room. reset output to original values */
- *outbuf = outbuf0;
- *outbytesleft = outbytesleft0;
- cd->write_marc8_last = last_ch;
- cd->write_marc8_ncr = ncr;
- cd->write_marc8_lpage = lpage;
- }
- return r;
- }
- }
- }
- return yaz_write_marc8_2(cd, x, outbuf, outbytesleft, loss_mode);
-}
-
-
-#if HAVE_WCHAR_H
-static size_t yaz_write_wchar_t(yaz_iconv_t cd, unsigned long x,
- char **outbuf, size_t *outbytesleft)