From: Bruno Haible Date: Fri, 24 Nov 2006 12:57:01 +0000 (+0000) Subject: Use ostream_t instead of 'FILE *'. X-Git-Tag: v0.17~641 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=954997dccac17bd5c8a27ea28690ca0b91e9c397;p=thirdparty%2Fgettext.git Use ostream_t instead of 'FILE *'. --- diff --git a/ChangeLog b/ChangeLog index 8d4d89ae6..e0d0e5dae 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,8 @@ +2006-11-23 Bruno Haible + + * autogen.sh (GNULIB_MODULES_TOOLS_FOR_SRC, + GNULIB_MODULES_LIBGETTEXTPO): Add ostream, file-ostream. + 2006-11-12 Bruno Haible * configure.ac (am__tar): Override automake's definition. diff --git a/autogen.sh b/autogen.sh index eb371d1b0..c48ee2da7 100755 --- a/autogen.sh +++ b/autogen.sh @@ -99,6 +99,7 @@ if test -n "$GNULIB_TOOL"; then error-progname execute exit + file-ostream findprog fnmatch-posix fstrcmp @@ -119,6 +120,7 @@ if test -n "$GNULIB_TOOL"; then memset minmax obstack + ostream pathname pipe progname @@ -176,6 +178,7 @@ if test -n "$GNULIB_TOOL"; then error error-progname exit + file-ostream fstrcmp fwriteerror gcd @@ -185,6 +188,7 @@ if test -n "$GNULIB_TOOL"; then iconv linebreak minmax + ostream pathname progname stdbool diff --git a/gettext-tools/src/ChangeLog b/gettext-tools/src/ChangeLog index 1eb6e2281..14535c22d 100644 --- a/gettext-tools/src/ChangeLog +++ b/gettext-tools/src/ChangeLog @@ -1,3 +1,29 @@ +2006-11-23 Bruno Haible + + * write-catalog.h: Include ostream.h. Don't include . + (struct catalog_output_format): Use ostream_t instead of 'FILE *'. + * write-catalog.c: Include ostream.h, file-ostream.h. + (msgdomain_list_print): Open a temporary file_ostream_t. + * write-po.h: Include ostream.h. Don't include . + (message_print_comment, message_print_comment_dot, + message_print_comment_filepos, message_print_comment_flags): Replace + 'FILE *' argument with an 'ostream_t' argument. + * write-po.c: Include ostream.h. + (message_print_comment, message_print_comment_dot, + message_print_comment_filepos, message_print_comment_flags, wrap, + print_blank_line, message_print, message_print_obsolete, + msgdomain_list_print_po): Replace 'FILE *' argument with an 'ostream_t' + argument. + * write-properties.c: Include ostream.h. + (write_escaped_string, write_message, write_properties, + msgdomain_list_print_properties): Replace 'FILE *' argument with an + 'ostream_t' argument. + * write-stringtable.c: Include ostream.h, xvasprintf.h. Don't include + . + (write_escaped_string, write_message, write_stringtable, + msgdomain_list_print_stringtable): Replace 'FILE *' argument with an + 'ostream_t' argument. + 2006-11-12 Bruno Haible * write-po.c (wrap): Indent by use of spaces, not tabs. diff --git a/gettext-tools/src/write-catalog.c b/gettext-tools/src/write-catalog.c index ec9ce0329..4e12272d7 100644 --- a/gettext-tools/src/write-catalog.c +++ b/gettext-tools/src/write-catalog.c @@ -28,6 +28,8 @@ #include #include +#include "ostream.h" +#include "file-ostream.h" #include "fwriteerror.h" #include "error-progname.h" #include "xvasprintf.h" @@ -71,6 +73,7 @@ msgdomain_list_print (msgdomain_list_ty *mdlp, const char *filename, bool force, bool debug) { FILE *fp; + file_ostream_t stream; /* We will not write anything if, for every domain, we have no message or only the header entry. */ @@ -204,7 +207,9 @@ message catalog has plural form translations, but the output format does not sup filename = _("standard output"); } - output_syntax->print (mdlp, fp, page_width, debug); + stream = file_ostream_create (fp); + output_syntax->print (mdlp, stream, page_width, debug); + ostream_free (stream); /* Make sure nothing went wrong. */ if (fwriteerror (fp)) diff --git a/gettext-tools/src/write-catalog.h b/gettext-tools/src/write-catalog.h index bc157c75a..923302900 100644 --- a/gettext-tools/src/write-catalog.h +++ b/gettext-tools/src/write-catalog.h @@ -19,8 +19,8 @@ #define _WRITE_CATALOG_H #include -#include +#include "ostream.h" #include "message.h" @@ -32,8 +32,8 @@ extern "C" { /* This structure describes a textual catalog output format. */ struct catalog_output_format { - /* Outputs a list of domains of messages to a file. */ - void (*print) (msgdomain_list_ty *mdlp, FILE *fp, size_t page_width, bool debug); + /* Outputs a list of domains of messages to a stream. */ + void (*print) (msgdomain_list_ty *mdlp, ostream_t stream, size_t page_width, bool debug); /* Whether the print function requires the MDLP to be encoded in UTF-8 encoding. */ diff --git a/gettext-tools/src/write-po.c b/gettext-tools/src/write-po.c index 2afce96cb..d7ed59ac6 100644 --- a/gettext-tools/src/write-po.c +++ b/gettext-tools/src/write-po.c @@ -44,6 +44,7 @@ #include "xalloc.h" #include "xallocsa.h" #include "c-strstr.h" +#include "ostream.h" #include "xvasprintf.h" #include "po-xerror.h" #include "gettext.h" @@ -146,7 +147,7 @@ make_c_width_description_string (enum is_wrap do_wrap) /* Output mp->comment as a set of comment lines. */ void -message_print_comment (const message_ty *mp, FILE *fp) +message_print_comment (const message_ty *mp, ostream_t stream) { if (mp->comment != NULL) { @@ -158,21 +159,21 @@ message_print_comment (const message_ty *mp, FILE *fp) do { const char *e; - putc ('#', fp); + ostream_write_str (stream, "#"); if (*s != '\0' && *s != ' ') - putc (' ', fp); + ostream_write_str (stream, " "); e = strchr (s, '\n'); if (e == NULL) { - fputs (s, fp); + ostream_write_str (stream, s); s = NULL; } else { - fwrite (s, 1, e - s, fp); + ostream_write_mem (stream, s, e - s); s = e + 1; } - putc ('\n', fp); + ostream_write_str (stream, "\n"); } while (s != NULL); } @@ -183,7 +184,7 @@ message_print_comment (const message_ty *mp, FILE *fp) /* Output mp->comment_dot as a set of comment lines. */ void -message_print_comment_dot (const message_ty *mp, FILE *fp) +message_print_comment_dot (const message_ty *mp, ostream_t stream) { if (mp->comment_dot != NULL) { @@ -192,12 +193,11 @@ message_print_comment_dot (const message_ty *mp, FILE *fp) for (j = 0; j < mp->comment_dot->nitems; ++j) { const char *s = mp->comment_dot->item[j]; - putc ('#', fp); - putc ('.', fp); + ostream_write_str (stream, "#."); if (*s != '\0' && *s != ' ') - putc (' ', fp); - fputs (s, fp); - putc ('\n', fp); + ostream_write_str (stream, " "); + ostream_write_str (stream, s); + ostream_write_str (stream, "\n"); } } } @@ -206,7 +206,7 @@ message_print_comment_dot (const message_ty *mp, FILE *fp) /* Output mp->filepos as a set of comment lines. */ void -message_print_comment_filepos (const message_ty *mp, FILE *fp, +message_print_comment_filepos (const message_ty *mp, ostream_t stream, bool uniforum, size_t page_width) { if (mp->filepos_count != 0) @@ -219,12 +219,16 @@ message_print_comment_filepos (const message_ty *mp, FILE *fp, { lex_pos_ty *pp = &mp->filepos[j]; char *cp = pp->file_name; + char *str; + while (cp[0] == '.' && cp[1] == '/') cp += 2; /* There are two Sun formats to choose from: SunOS and Solaris. Use the Solaris form here. */ - fprintf (fp, "# File: %s, line: %ld\n", - cp, (long) pp->line_number); + str = xasprintf ("# File: %s, line: %ld\n", + cp, (long) pp->line_number); + ostream_write_str (stream, str); + free (str); } } else @@ -232,7 +236,7 @@ message_print_comment_filepos (const message_ty *mp, FILE *fp, size_t column; size_t j; - fputs ("#:", fp); + ostream_write_str (stream, "#:"); column = 2; for (j = 0; j < mp->filepos_count; ++j) { @@ -253,13 +257,15 @@ message_print_comment_filepos (const message_ty *mp, FILE *fp, len = strlen (cp) + strlen (buffer) + 1; if (column > 2 && column + len >= page_width) { - fputs ("\n#:", fp); + ostream_write_str (stream, "\n#:"); column = 2; } - fprintf (fp, " %s%s", cp, buffer); + ostream_write_str (stream, " "); + ostream_write_str (stream, cp); + ostream_write_str (stream, buffer); column += len; } - putc ('\n', fp); + ostream_write_str (stream, "\n"); } } } @@ -268,7 +274,7 @@ message_print_comment_filepos (const message_ty *mp, FILE *fp, /* Output mp->is_fuzzy, mp->is_format, mp->do_wrap as a comment line. */ void -message_print_comment_flags (const message_ty *mp, FILE *fp, bool debug) +message_print_comment_flags (const message_ty *mp, ostream_t stream, bool debug) { if ((mp->is_fuzzy && mp->msgstr[0] != '\0') || has_significant_format_p (mp->is_format) @@ -277,15 +283,14 @@ message_print_comment_flags (const message_ty *mp, FILE *fp, bool debug) bool first_flag = true; size_t i; - putc ('#', fp); - putc (',', fp); + ostream_write_str (stream, "#,"); /* We don't print the fuzzy flag if the msgstr is empty. This might be introduced by the user but we want to normalize the output. */ if (mp->is_fuzzy && mp->msgstr[0] != '\0') { - fputs (" fuzzy", fp); + ostream_write_str (stream, " fuzzy"); first_flag = false; } @@ -293,24 +298,26 @@ message_print_comment_flags (const message_ty *mp, FILE *fp, bool debug) if (significant_format_p (mp->is_format[i])) { if (!first_flag) - putc (',', fp); + ostream_write_str (stream, ","); - fputs (make_format_description_string (mp->is_format[i], - format_language[i], debug), - fp); + ostream_write_str (stream, + make_format_description_string (mp->is_format[i], + format_language[i], + debug)); first_flag = false; } if (mp->do_wrap == no) { if (!first_flag) - putc (',', fp); + ostream_write_str (stream, ","); - fputs (make_c_width_description_string (mp->do_wrap), fp); + ostream_write_str (stream, + make_c_width_description_string (mp->do_wrap)); first_flag = false; } - putc ('\n', fp); + ostream_write_str (stream, "\n"); } } @@ -375,7 +382,8 @@ memcpy_small (void *dst, const void *src, size_t n) static void -wrap (const message_ty *mp, FILE *fp, const char *line_prefix, int extra_indent, +wrap (const message_ty *mp, ostream_t stream, + const char *line_prefix, int extra_indent, const char *name, const char *value, enum is_wrap do_wrap, size_t page_width, const char *charset) @@ -714,9 +722,9 @@ internationalized messages should not contain the `\\%c' escape sequence"), || memchr (linebreaks, UC_BREAK_POSSIBLE, portion_len) != NULL)) { if (line_prefix != NULL) - fputs (line_prefix, fp); - fputs (name, fp); - fputs (" \"\"\n", fp); + ostream_write_str (stream, line_prefix); + ostream_write_str (stream, name); + ostream_write_str (stream, " \"\"\n"); first_line = false; /* Recompute startcol and linebreaks. */ goto recompute; @@ -730,24 +738,24 @@ internationalized messages should not contain the `\\%c' escape sequence"), if (line_prefix != NULL) { - fputs (line_prefix, fp); + ostream_write_str (stream, line_prefix); currcol = strlen (line_prefix); } if (first_line) { - fputs (name, fp); + ostream_write_str (stream, name); currcol += strlen (name); if (indent) { if (extra_indent > 0) - fwrite (" ", 1, extra_indent, fp); + ostream_write_mem (stream, " ", extra_indent); currcol += extra_indent; - fwrite (" ", 1, 8 - (currcol & 7), fp); + ostream_write_mem (stream, " ", 8 - (currcol & 7)); currcol = (currcol + 8) & ~7; } else { - putc (' ', fp); + ostream_write_str (stream, " "); currcol++; } first_line = false; @@ -757,40 +765,40 @@ internationalized messages should not contain the `\\%c' escape sequence"), if (indent) { if (extra_indent > 0) - fwrite (" ", 1, extra_indent, fp); + ostream_write_mem (stream, " ", extra_indent); currcol += extra_indent; - fwrite (" ", 1, 8 - (currcol & 7), fp); + ostream_write_mem (stream, " ", 8 - (currcol & 7)); currcol = (currcol + 8) & ~7; } } } /* Print the portion itself, with linebreaks where necessary. */ - putc ('"', fp); + ostream_write_str (stream, "\""); for (i = 0; i < portion_len; i++) { if (linebreaks[i] == UC_BREAK_POSSIBLE) { int currcol; - fputs ("\"\n", fp); + ostream_write_str (stream, "\"\n"); currcol = 0; /* INDENT-S. */ if (line_prefix != NULL) { - fputs (line_prefix, fp); + ostream_write_str (stream, line_prefix); currcol = strlen (line_prefix); } if (indent) { - fwrite (" ", 1, 8 - (currcol & 7), fp); + ostream_write_mem (stream, " ", 8 - (currcol & 7)); currcol = (currcol + 8) & ~7; } - putc ('"', fp); + ostream_write_str (stream, "\""); } - putc (portion[i], fp); + ostream_write_mem (stream, &portion[i], 1); } - fputs ("\"\n", fp); + ostream_write_str (stream, "\"\n"); free (linebreaks); free (overrides); @@ -809,18 +817,19 @@ internationalized messages should not contain the `\\%c' escape sequence"), static void -print_blank_line (FILE *fp) +print_blank_line (ostream_t stream) { if (uniforum) - fputs ("#\n", fp); + ostream_write_str (stream, "#\n"); else - putc ('\n', fp); + ostream_write_str (stream, "\n"); } static void -message_print (const message_ty *mp, FILE *fp, const char *charset, - size_t page_width, bool blank_line, bool debug) +message_print (const message_ty *mp, ostream_t stream, + const char *charset, size_t page_width, bool blank_line, + bool debug) { int extra_indent; @@ -830,33 +839,33 @@ message_print (const message_ty *mp, FILE *fp, const char *charset, || mp->comment == NULL || mp->comment->nitems == 0 || mp->comment->item[0][0] != '\0')) - print_blank_line (fp); + print_blank_line (stream); /* Print translator comment if available. */ - message_print_comment (mp, fp); + message_print_comment (mp, stream); /* Print xgettext extracted comments. */ - message_print_comment_dot (mp, fp); + message_print_comment_dot (mp, stream); /* Print the file position comments. This will help a human who is trying to navigate the sources. There is no problem of getting repeated positions, because duplicates are checked for. */ - message_print_comment_filepos (mp, fp, uniforum, page_width); + message_print_comment_filepos (mp, stream, uniforum, page_width); /* Print flag information in special comment. */ - message_print_comment_flags (mp, fp, debug); + message_print_comment_flags (mp, stream, debug); /* Print the previous msgid. This helps the translator when the msgid has only slightly changed. */ if (mp->prev_msgctxt != NULL) - wrap (mp, fp, "#| ", 0, "msgctxt", mp->prev_msgctxt, mp->do_wrap, + wrap (mp, stream, "#| ", 0, "msgctxt", mp->prev_msgctxt, mp->do_wrap, page_width, charset); if (mp->prev_msgid != NULL) - wrap (mp, fp, "#| ", 0, "msgid", mp->prev_msgid, mp->do_wrap, page_width, - charset); - if (mp->prev_msgid_plural != NULL) - wrap (mp, fp, "#| ", 0, "msgid_plural", mp->prev_msgid_plural, mp->do_wrap, + wrap (mp, stream, "#| ", 0, "msgid", mp->prev_msgid, mp->do_wrap, page_width, charset); + if (mp->prev_msgid_plural != NULL) + wrap (mp, stream, "#| ", 0, "msgid_plural", mp->prev_msgid_plural, + mp->do_wrap, page_width, charset); extra_indent = (mp->prev_msgctxt != NULL || mp->prev_msgid != NULL || mp->prev_msgid_plural != NULL ? 3 @@ -890,16 +899,16 @@ different from yours. Consider using a pure ASCII msgid instead.\n\ free (warning_message); } if (mp->msgctxt != NULL) - wrap (mp, fp, NULL, extra_indent, "msgctxt", mp->msgctxt, mp->do_wrap, - page_width, charset); - wrap (mp, fp, NULL, extra_indent, "msgid", mp->msgid, mp->do_wrap, + wrap (mp, stream, NULL, extra_indent, "msgctxt", mp->msgctxt, mp->do_wrap, page_width, charset); + wrap (mp, stream, NULL, extra_indent, "msgid", mp->msgid, mp->do_wrap, + page_width, charset); if (mp->msgid_plural != NULL) - wrap (mp, fp, NULL, extra_indent, "msgid_plural", mp->msgid_plural, + wrap (mp, stream, NULL, extra_indent, "msgid_plural", mp->msgid_plural, mp->do_wrap, page_width, charset); if (mp->msgid_plural == NULL) - wrap (mp, fp, NULL, extra_indent, "msgstr", mp->msgstr, mp->do_wrap, + wrap (mp, stream, NULL, extra_indent, "msgstr", mp->msgstr, mp->do_wrap, page_width, charset); else { @@ -912,7 +921,7 @@ different from yours. Consider using a pure ASCII msgid instead.\n\ p += strlen (p) + 1, i++) { sprintf (prefix_buf, "msgstr[%u]", i); - wrap (mp, fp, NULL, extra_indent, prefix_buf, p, mp->do_wrap, + wrap (mp, stream, NULL, extra_indent, prefix_buf, p, mp->do_wrap, page_width, charset); } } @@ -920,8 +929,8 @@ different from yours. Consider using a pure ASCII msgid instead.\n\ static void -message_print_obsolete (const message_ty *mp, FILE *fp, const char *charset, - size_t page_width, bool blank_line) +message_print_obsolete (const message_ty *mp, ostream_t stream, + const char *charset, size_t page_width, bool blank_line) { int extra_indent; @@ -932,45 +941,44 @@ message_print_obsolete (const message_ty *mp, FILE *fp, const char *charset, /* Separate messages with a blank line. Uniforum doesn't like blank lines, so use an empty comment (unless there already is one). */ if (blank_line) - print_blank_line (fp); + print_blank_line (stream); /* Print translator comment if available. */ - message_print_comment (mp, fp); + message_print_comment (mp, stream); /* Print xgettext extracted comments (normally empty). */ - message_print_comment_dot (mp, fp); + message_print_comment_dot (mp, stream); /* Print the file position comments (normally empty). */ - message_print_comment_filepos (mp, fp, uniforum, page_width); + message_print_comment_filepos (mp, stream, uniforum, page_width); /* Print flag information in special comment. */ if (mp->is_fuzzy) { bool first = true; - putc ('#', fp); - putc (',', fp); + ostream_write_str (stream, "#,"); if (mp->is_fuzzy) { - fputs (" fuzzy", fp); + ostream_write_str (stream, " fuzzy"); first = false; } - putc ('\n', fp); + ostream_write_str (stream, "\n"); } /* Print the previous msgid. This helps the translator when the msgid has only slightly changed. */ if (mp->prev_msgctxt != NULL) - wrap (mp, fp, "#~| ", 0, "msgctxt", mp->prev_msgctxt, mp->do_wrap, + wrap (mp, stream, "#~| ", 0, "msgctxt", mp->prev_msgctxt, mp->do_wrap, page_width, charset); if (mp->prev_msgid != NULL) - wrap (mp, fp, "#~| ", 0, "msgid", mp->prev_msgid, mp->do_wrap, page_width, - charset); - if (mp->prev_msgid_plural != NULL) - wrap (mp, fp, "#~| ", 0, "msgid_plural", mp->prev_msgid_plural, mp->do_wrap, + wrap (mp, stream, "#~| ", 0, "msgid", mp->prev_msgid, mp->do_wrap, page_width, charset); + if (mp->prev_msgid_plural != NULL) + wrap (mp, stream, "#~| ", 0, "msgid_plural", mp->prev_msgid_plural, + mp->do_wrap, page_width, charset); extra_indent = (mp->prev_msgctxt != NULL || mp->prev_msgid != NULL || mp->prev_msgid_plural != NULL ? 1 @@ -1003,16 +1011,16 @@ different from yours. Consider using a pure ASCII msgid instead.\n\ free (warning_message); } if (mp->msgctxt != NULL) - wrap (mp, fp, "#~ ", extra_indent, "msgctxt", mp->msgctxt, mp->do_wrap, + wrap (mp, stream, "#~ ", extra_indent, "msgctxt", mp->msgctxt, mp->do_wrap, page_width, charset); - wrap (mp, fp, "#~ ", extra_indent, "msgid", mp->msgid, mp->do_wrap, + wrap (mp, stream, "#~ ", extra_indent, "msgid", mp->msgid, mp->do_wrap, page_width, charset); if (mp->msgid_plural != NULL) - wrap (mp, fp, "#~ ", extra_indent, "msgid_plural", mp->msgid_plural, + wrap (mp, stream, "#~ ", extra_indent, "msgid_plural", mp->msgid_plural, mp->do_wrap, page_width, charset); if (mp->msgid_plural == NULL) - wrap (mp, fp, "#~ ", extra_indent, "msgstr", mp->msgstr, mp->do_wrap, + wrap (mp, stream, "#~ ", extra_indent, "msgstr", mp->msgstr, mp->do_wrap, page_width, charset); else { @@ -1025,7 +1033,7 @@ different from yours. Consider using a pure ASCII msgid instead.\n\ p += strlen (p) + 1, i++) { sprintf (prefix_buf, "msgstr[%u]", i); - wrap (mp, fp, "#~ ", extra_indent, prefix_buf, p, mp->do_wrap, + wrap (mp, stream, "#~ ", extra_indent, prefix_buf, p, mp->do_wrap, page_width, charset); } } @@ -1033,8 +1041,8 @@ different from yours. Consider using a pure ASCII msgid instead.\n\ static void -msgdomain_list_print_po (msgdomain_list_ty *mdlp, FILE *fp, size_t page_width, - bool debug) +msgdomain_list_print_po (msgdomain_list_ty *mdlp, ostream_t stream, + size_t page_width, bool debug) { size_t j, k; bool blank_line; @@ -1054,8 +1062,10 @@ msgdomain_list_print_po (msgdomain_list_ty *mdlp, FILE *fp, size_t page_width, && strcmp (mdlp->item[k]->domain, MESSAGE_DOMAIN_DEFAULT) == 0)) { if (blank_line) - print_blank_line (fp); - fprintf (fp, "domain \"%s\"\n", mdlp->item[k]->domain); + print_blank_line (stream); + ostream_write_str (stream, "domain \""); + ostream_write_str (stream, mdlp->item[k]->domain); + ostream_write_str (stream, "\"\n"); blank_line = true; } @@ -1098,8 +1108,8 @@ msgdomain_list_print_po (msgdomain_list_ty *mdlp, FILE *fp, size_t page_width, for (j = 0; j < mlp->nitems; ++j) if (!mlp->item[j]->obsolete) { - message_print (mlp->item[j], fp, charset, page_width, blank_line, - debug); + message_print (mlp->item[j], stream, charset, page_width, + blank_line, debug); blank_line = true; } @@ -1107,7 +1117,7 @@ msgdomain_list_print_po (msgdomain_list_ty *mdlp, FILE *fp, size_t page_width, for (j = 0; j < mlp->nitems; ++j) if (mlp->item[j]->obsolete) { - message_print_obsolete (mlp->item[j], fp, charset, page_width, + message_print_obsolete (mlp->item[j], stream, charset, page_width, blank_line); blank_line = true; } diff --git a/gettext-tools/src/write-po.h b/gettext-tools/src/write-po.h index e5c2a8639..76f705e9b 100644 --- a/gettext-tools/src/write-po.h +++ b/gettext-tools/src/write-po.h @@ -20,10 +20,10 @@ #ifndef _WRITE_PO_H #define _WRITE_PO_H +#include "ostream.h" #include "message.h" #include -#include #ifdef __cplusplus @@ -41,14 +41,14 @@ extern bool /* These functions output parts of a message, as comments. */ extern void - message_print_comment (const message_ty *mp, FILE *fp); + message_print_comment (const message_ty *mp, ostream_t stream); extern void - message_print_comment_dot (const message_ty *mp, FILE *fp); + message_print_comment_dot (const message_ty *mp, ostream_t stream); extern void - message_print_comment_filepos (const message_ty *mp, FILE *fp, + message_print_comment_filepos (const message_ty *mp, ostream_t stream, bool uniforum, size_t page_width); extern void - message_print_comment_flags (const message_ty *mp, FILE *fp, + message_print_comment_flags (const message_ty *mp, ostream_t stream, bool debug); /* These functions set some parameters for use by 'output_format_po.print'. */ diff --git a/gettext-tools/src/write-properties.c b/gettext-tools/src/write-properties.c index 79bd0fb70..50df33ab9 100644 --- a/gettext-tools/src/write-properties.c +++ b/gettext-tools/src/write-properties.c @@ -35,6 +35,7 @@ #include "msgl-iconv.h" #include "po-charset.h" #include "utf8-ucs4.h" +#include "ostream.h" #include "write-po.h" #include "xalloc.h" @@ -122,9 +123,9 @@ conv_to_java (const char *string) return result; } -/* Writes a key or value to the file, without newline. */ +/* Writes a key or value to the stream, without newline. */ static void -write_escaped_string (FILE *fp, const char *str, bool in_key) +write_escaped_string (ostream_t stream, const char *str, bool in_key) { static const char hexdigit[] = "0123456789abcdef"; const char *str_limit = str + strlen (str); @@ -136,30 +137,15 @@ write_escaped_string (FILE *fp, const char *str, bool in_key) str += u8_mbtouc (&uc, (const unsigned char *) str, str_limit - str); /* Whitespace must be escaped. */ if (uc == 0x0020 && (first || in_key)) - { - putc ('\\', fp); - putc (' ', fp); - } + ostream_write_str (stream, "\\ "); else if (uc == 0x0009) - { - putc ('\\', fp); - putc ('t', fp); - } + ostream_write_str (stream, "\\t"); else if (uc == 0x000a) - { - putc ('\\', fp); - putc ('n', fp); - } + ostream_write_str (stream, "\\n"); else if (uc == 0x000d) - { - putc ('\\', fp); - putc ('r', fp); - } + ostream_write_str (stream, "\\r"); else if (uc == 0x000c) - { - putc ('\\', fp); - putc ('f', fp); - } + ostream_write_str (stream, "\\f"); else if (/* Backslash must be escaped. */ uc == '\\' /* Possible comment introducers must be escaped. */ @@ -167,8 +153,10 @@ write_escaped_string (FILE *fp, const char *str, bool in_key) /* Key terminators must be escaped. */ || uc == '=' || uc == ':') { - putc ('\\', fp); - putc (uc, fp); + char seq[2]; + seq[0] = '\\'; + seq[1] = uc; + ostream_write_mem (stream, seq, 2); } else if (uc >= 0x0020 && uc <= 0x007e) { @@ -176,66 +164,83 @@ write_escaped_string (FILE *fp, const char *str, bool in_key) We could treat non-ASCII ISO-8859-1 characters (0x0080..0x00FF) the same way, but there is no point in doing this; Sun's nativetoascii doesn't do it either. */ - putc (uc, fp); + char seq[1]; + seq[0] = uc; + ostream_write_mem (stream, seq, 1); } else if (uc < 0x10000) { /* Single UCS-2 'char' */ - fprintf (fp, "\\u%c%c%c%c", - hexdigit[(uc >> 12) & 0x0f], hexdigit[(uc >> 8) & 0x0f], - hexdigit[(uc >> 4) & 0x0f], hexdigit[uc & 0x0f]); + char seq[6]; + seq[0] = '\\'; + seq[1] = 'u'; + seq[2] = hexdigit[(uc >> 12) & 0x0f]; + seq[3] = hexdigit[(uc >> 8) & 0x0f]; + seq[4] = hexdigit[(uc >> 4) & 0x0f]; + seq[5] = hexdigit[uc & 0x0f]; + ostream_write_mem (stream, seq, 6); } else { /* UTF-16 surrogate: two 'char's. */ unsigned int uc1 = 0xd800 + ((uc - 0x10000) >> 10); unsigned int uc2 = 0xdc00 + ((uc - 0x10000) & 0x3ff); - fprintf (fp, "\\u%c%c%c%c", - hexdigit[(uc1 >> 12) & 0x0f], hexdigit[(uc1 >> 8) & 0x0f], - hexdigit[(uc1 >> 4) & 0x0f], hexdigit[uc1 & 0x0f]); - fprintf (fp, "\\u%c%c%c%c", - hexdigit[(uc2 >> 12) & 0x0f], hexdigit[(uc2 >> 8) & 0x0f], - hexdigit[(uc2 >> 4) & 0x0f], hexdigit[uc2 & 0x0f]); + char seq[6]; + seq[0] = '\\'; + seq[1] = 'u'; + seq[2] = hexdigit[(uc1 >> 12) & 0x0f]; + seq[3] = hexdigit[(uc1 >> 8) & 0x0f]; + seq[4] = hexdigit[(uc1 >> 4) & 0x0f]; + seq[5] = hexdigit[uc1 & 0x0f]; + ostream_write_mem (stream, seq, 6); + seq[0] = '\\'; + seq[1] = 'u'; + seq[2] = hexdigit[(uc2 >> 12) & 0x0f]; + seq[3] = hexdigit[(uc2 >> 8) & 0x0f]; + seq[4] = hexdigit[(uc2 >> 4) & 0x0f]; + seq[5] = hexdigit[uc2 & 0x0f]; + ostream_write_mem (stream, seq, 6); } first = false; } } -/* Writes a message to the file. */ +/* Writes a message to the stream. */ static void -write_message (FILE *fp, const message_ty *mp, size_t page_width, bool debug) +write_message (ostream_t stream, const message_ty *mp, + size_t page_width, bool debug) { /* Print translator comment if available. */ - message_print_comment (mp, fp); + message_print_comment (mp, stream); /* Print xgettext extracted comments. */ - message_print_comment_dot (mp, fp); + message_print_comment_dot (mp, stream); /* Print the file position comments. */ - message_print_comment_filepos (mp, fp, false, page_width); + message_print_comment_filepos (mp, stream, false, page_width); /* Print flag information in special comment. */ - message_print_comment_flags (mp, fp, debug); + message_print_comment_flags (mp, stream, debug); /* Put a comment mark if the message is the header or untranslated or fuzzy. */ if (is_header (mp) || mp->msgstr[0] == '\0' || (mp->is_fuzzy && !is_header (mp))) - putc ('!', fp); + ostream_write_str (stream, "!"); /* Now write the untranslated string and the translated string. */ - write_escaped_string (fp, mp->msgid, true); - putc ('=', fp); - write_escaped_string (fp, mp->msgstr, false); + write_escaped_string (stream, mp->msgid, true); + ostream_write_str (stream, "="); + write_escaped_string (stream, mp->msgstr, false); - putc ('\n', fp); + ostream_write_str (stream, "\n"); } -/* Writes an entire message list to the file. */ +/* Writes an entire message list to the stream. */ static void -write_properties (FILE *fp, message_list_ty *mlp, const char *canon_encoding, - size_t page_width, bool debug) +write_properties (ostream_t stream, message_list_ty *mlp, + const char *canon_encoding, size_t page_width, bool debug) { bool blank_line; size_t j, i; @@ -263,9 +268,9 @@ write_properties (FILE *fp, message_list_ty *mlp, const char *canon_encoding, if (mp->msgid_plural == NULL && !mp->obsolete) { if (blank_line) - putc ('\n', fp); + ostream_write_str (stream, "\n"); - write_message (fp, mp, page_width, debug); + write_message (stream, mp, page_width, debug); blank_line = true; } @@ -274,7 +279,7 @@ write_properties (FILE *fp, message_list_ty *mlp, const char *canon_encoding, /* Output the contents of a PO file in Java .properties syntax. */ static void -msgdomain_list_print_properties (msgdomain_list_ty *mdlp, FILE *fp, +msgdomain_list_print_properties (msgdomain_list_ty *mdlp, ostream_t stream, size_t page_width, bool debug) { message_list_ty *mlp; @@ -283,7 +288,7 @@ msgdomain_list_print_properties (msgdomain_list_ty *mdlp, FILE *fp, mlp = mdlp->item[0]->messages; else mlp = message_list_alloc (false); - write_properties (fp, mlp, mdlp->encoding, page_width, debug); + write_properties (stream, mlp, mdlp->encoding, page_width, debug); } /* Describes a PO file in Java .properties syntax. */ diff --git a/gettext-tools/src/write-stringtable.c b/gettext-tools/src/write-stringtable.c index 619a282bc..cd4709b60 100644 --- a/gettext-tools/src/write-stringtable.c +++ b/gettext-tools/src/write-stringtable.c @@ -24,7 +24,6 @@ #include "write-stringtable.h" #include -#include #include #include @@ -33,6 +32,8 @@ #include "msgl-iconv.h" #include "po-charset.h" #include "c-strstr.h" +#include "ostream.h" +#include "xvasprintf.h" #include "write-po.h" /* The format of NeXTstep/GNUstep .strings files is documented in @@ -55,51 +56,46 @@ UTF-16 instead of UCS-2, we use UTF-8 with BOM. BOMs are bad because they get in the way when concatenating files, but here we have no choice. */ -/* Writes a key or value to the file, without newline. */ +/* Writes a key or value to the stream, without newline. */ static void -write_escaped_string (FILE *fp, const char *str) +write_escaped_string (ostream_t stream, const char *str) { const char *str_limit = str + strlen (str); - putc ('"', fp); + ostream_write_str (stream, "\""); while (str < str_limit) { unsigned char c = (unsigned char) *str++; if (c == '\t') - { - putc ('\\', fp); - putc ('t', fp); - } + ostream_write_str (stream, "\\t"); else if (c == '\n') - { - putc ('\\', fp); - putc ('n', fp); - } + ostream_write_str (stream, "\\n"); else if (c == '\r') - { - putc ('\\', fp); - putc ('r', fp); - } + ostream_write_str (stream, "\\r"); else if (c == '\f') - { - putc ('\\', fp); - putc ('f', fp); - } + ostream_write_str (stream, "\\f"); else if (c == '\\' || c == '"') { - putc ('\\', fp); - putc (c, fp); + char seq[2]; + seq[0] = '\\'; + seq[1] = c; + ostream_write_mem (stream, seq, 2); } else - putc (c, fp); + { + char seq[1]; + seq[0] = c; + ostream_write_mem (stream, seq, 1); + } } - putc ('"', fp); + ostream_write_str (stream, "\""); } -/* Writes a message to the file. */ +/* Writes a message to the stream. */ static void -write_message (FILE *fp, const message_ty *mp, size_t page_width, bool debug) +write_message (ostream_t stream, const message_ty *mp, + size_t page_width, bool debug) { /* Print translator comment if available. */ if (mp->comment != NULL) @@ -114,31 +110,31 @@ write_message (FILE *fp, const message_ty *mp, size_t page_width, bool debug) whether we need C++ style for it. */ if (c_strstr (s, "*/") == NULL) { - fputs ("/*", fp); + ostream_write_str (stream, "/*"); if (*s != '\0' && *s != '\n' && *s != ' ') - putc (' ', fp); - fputs (s, fp); - fputs (" */\n", fp); + ostream_write_str (stream, " "); + ostream_write_str (stream, s); + ostream_write_str (stream, " */\n"); } else do { const char *e; - fputs ("//", fp); + ostream_write_str (stream, "//"); if (*s != '\0' && *s != '\n' && *s != ' ') - putc (' ', fp); + ostream_write_str (stream, " "); e = strchr (s, '\n'); if (e == NULL) { - fputs (s, fp); + ostream_write_str (stream, s); s = NULL; } else { - fwrite (s, 1, e - s, fp); + ostream_write_mem (stream, s, e - s); s = e + 1; } - putc ('\n', fp); + ostream_write_str (stream, "\n"); } while (s != NULL); } @@ -157,9 +153,9 @@ write_message (FILE *fp, const message_ty *mp, size_t page_width, bool debug) whether we need C++ style for it. */ if (c_strstr (s, "*/") == NULL) { - fputs ("/* Comment: ", fp); - fputs (s, fp); - fputs (" */\n", fp); + ostream_write_str (stream, "/* Comment: "); + ostream_write_str (stream, s); + ostream_write_str (stream, " */\n"); } else { @@ -167,23 +163,23 @@ write_message (FILE *fp, const message_ty *mp, size_t page_width, bool debug) do { const char *e; - fputs ("//", fp); + ostream_write_str (stream, "//"); if (first || (*s != '\0' && *s != '\n' && *s != ' ')) - putc (' ', fp); + ostream_write_str (stream, " "); if (first) - fputs ("Comment: ", fp); + ostream_write_str (stream, "Comment: "); e = strchr (s, '\n'); if (e == NULL) { - fputs (s, fp); + ostream_write_str (stream, s); s = NULL; } else { - fwrite (s, 1, e - s, fp); + ostream_write_mem (stream, s, e - s); s = e + 1; } - putc ('\n', fp); + ostream_write_str (stream, "\n"); first = false; } while (s != NULL); @@ -200,73 +196,78 @@ write_message (FILE *fp, const message_ty *mp, size_t page_width, bool debug) { lex_pos_ty *pp = &mp->filepos[j]; char *cp = pp->file_name; + char *str; + while (cp[0] == '.' && cp[1] == '/') cp += 2; - fprintf (fp, "/* File: %s:%ld */\n", cp, (long) pp->line_number); + str = xasprintf ("/* File: %s:%ld */\n", cp, (long) pp->line_number); + ostream_write_str (stream, str); + free (str); } } /* Print flag information in special comment. */ if (mp->is_fuzzy || mp->msgstr[0] == '\0') - fputs ("/* Flag: untranslated */\n", fp); + ostream_write_str (stream, "/* Flag: untranslated */\n"); if (mp->obsolete) - fputs ("/* Flag: unmatched */\n", fp); + ostream_write_str (stream, "/* Flag: unmatched */\n"); { size_t i; for (i = 0; i < NFORMATS; i++) if (significant_format_p (mp->is_format[i])) { - fputs ("/* Flag:", fp); - fputs (make_format_description_string (mp->is_format[i], - format_language[i], debug), - fp); - fputs (" */\n", fp); + ostream_write_str (stream, "/* Flag:"); + ostream_write_str (stream, + make_format_description_string (mp->is_format[i], + format_language[i], + debug)); + ostream_write_str (stream, " */\n"); } } /* Now write the untranslated string and the translated string. */ - write_escaped_string (fp, mp->msgid); - fputs (" = ", fp); + write_escaped_string (stream, mp->msgid); + ostream_write_str (stream, " = "); if (mp->msgstr[0] != '\0') { if (mp->is_fuzzy) { /* Output the msgid as value, so that at runtime the untranslated string is returned. */ - write_escaped_string (fp, mp->msgid); + write_escaped_string (stream, mp->msgid); /* Output the msgstr as a comment, so that at runtime propertyListFromStringsFileFormat ignores it. */ if (c_strstr (mp->msgstr, "*/") == NULL) { - fputs (" /* = ", fp); - write_escaped_string (fp, mp->msgstr); - fputs (" */", fp); + ostream_write_str (stream, " /* = "); + write_escaped_string (stream, mp->msgstr); + ostream_write_str (stream, " */"); } else { - fputs ("; // = ", fp); - write_escaped_string (fp, mp->msgstr); + ostream_write_str (stream, "; // = "); + write_escaped_string (stream, mp->msgstr); } } else - write_escaped_string (fp, mp->msgstr); + write_escaped_string (stream, mp->msgstr); } else { /* Output the msgid as value, so that at runtime the untranslated string is returned. */ - write_escaped_string (fp, mp->msgid); + write_escaped_string (stream, mp->msgid); } - putc (';', fp); + ostream_write_str (stream, ";"); - putc ('\n', fp); + ostream_write_str (stream, "\n"); } -/* Writes an entire message list to the file. */ +/* Writes an entire message list to the stream. */ static void -write_stringtable (FILE *fp, message_list_ty *mlp, const char *canon_encoding, - size_t page_width, bool debug) +write_stringtable (ostream_t stream, message_list_ty *mlp, + const char *canon_encoding, size_t page_width, bool debug) { bool blank_line; size_t j; @@ -276,7 +277,7 @@ write_stringtable (FILE *fp, message_list_ty *mlp, const char *canon_encoding, /* Output the BOM. */ if (!is_ascii_message_list (mlp)) - fputs ("\xef\xbb\xbf", fp); + ostream_write_str (stream, "\xef\xbb\xbf"); /* Loop through the messages. */ blank_line = false; @@ -287,9 +288,9 @@ write_stringtable (FILE *fp, message_list_ty *mlp, const char *canon_encoding, if (mp->msgid_plural == NULL) { if (blank_line) - putc ('\n', fp); + ostream_write_str (stream, "\n"); - write_message (fp, mp, page_width, debug); + write_message (stream, mp, page_width, debug); blank_line = true; } @@ -298,7 +299,7 @@ write_stringtable (FILE *fp, message_list_ty *mlp, const char *canon_encoding, /* Output the contents of a PO file in .strings syntax. */ static void -msgdomain_list_print_stringtable (msgdomain_list_ty *mdlp, FILE *fp, +msgdomain_list_print_stringtable (msgdomain_list_ty *mdlp, ostream_t stream, size_t page_width, bool debug) { message_list_ty *mlp; @@ -307,7 +308,7 @@ msgdomain_list_print_stringtable (msgdomain_list_ty *mdlp, FILE *fp, mlp = mdlp->item[0]->messages; else mlp = message_list_alloc (false); - write_stringtable (fp, mlp, mdlp->encoding, page_width, debug); + write_stringtable (stream, mlp, mdlp->encoding, page_width, debug); } /* Describes a PO file in .strings syntax. */