+2001-09-02 Bruno Haible <haible@clisp.cons.org>
+
+ * plural-exp.h: New file, extracted from gettextP.h.
+ * plural-exp.c: New file, extracted from loadmsgcat.c.
+ * gettextP.h (struct expression, struct parse_args,
+ __gettext_free_exp, __gettextparse): Move to plural-exp.h.
+ * loadmsgcat.c: Include plural-exp.h.
+ (PLURAL_PARSE): Move macro to plural-exp.h.
+ (plvar, plone, germanic_plural, INIT_GERMANIC_PLURAL): Move to
+ plural-exp.c.
+ (_nl_load_domain): Move plural handling code to plural-exp.c. Call
+ EXTRACT_PLURAL_EXPRESSION.
+ * dcigettext.c: Include plural-exp.h.
+ * plural.y: Include plural-exp.h, not gettextP.h.
+ (FREE_EXPRESSION): Move macro to plural-exp.h.
+ * Makefile.in (DEFS): Define IN_LIBINTL.
+ (COMHDRS): Add plural-exp.h.
+ (COMSRCS): Add plural-exp.c.
+ (OBJECTS): Add plural-exp.$lo.
+ Update dependencies.
+
2001-09-01 Bruno Haible <haible@clisp.cons.org>
* *.h, *.c, *.y, Makefile.in: Change copyright notice from GPL to LGPL.
YFLAGS = --name-prefix=__gettext
DEFS = -DLOCALEDIR=\"$(localedir)\" -DLOCALE_ALIAS_PATH=\"$(aliaspath)\" \
--DLIBDIR=\"$(libdir)\" @DEFS@
+-DLIBDIR=\"$(libdir)\" -DIN_LIBINTL @DEFS@
CPPFLAGS = @CPPFLAGS@
CFLAGS = @CFLAGS@
LDFLAGS = @LDFLAGS@
COMPILE = $(CC) -c $(DEFS) $(INCLUDES) $(CPPFLAGS) $(CFLAGS) $(XCFLAGS)
HEADERS = $(COMHDRS) libgnuintl.h libgettext.h loadinfo.h
-COMHDRS = gettext.h gettextP.h hash-string.h
+COMHDRS = gettext.h gettextP.h hash-string.h plural-exp.h
SOURCES = $(COMSRCS) intl-compat.c
COMSRCS = bindtextdom.c dcgettext.c dgettext.c gettext.c \
finddomain.c loadmsgcat.c localealias.c textdomain.c l10nflist.c \
explodename.c dcigettext.c dcngettext.c dngettext.c ngettext.c plural.y \
-localcharset.c
+plural-exp.c localcharset.c
OBJECTS = @INTLOBJS@ bindtextdom.$lo dcgettext.$lo dgettext.$lo gettext.$lo \
finddomain.$lo loadmsgcat.$lo localealias.$lo textdomain.$lo l10nflist.$lo \
explodename.$lo dcigettext.$lo dcngettext.$lo dngettext.$lo ngettext.$lo \
-plural.$lo localcharset.$lo
+plural.$lo plural-exp.$lo localcharset.$lo
GETTOBJS = intl-compat.$lo
DISTFILES.common = COPYING.LIB-2 COPYING.LIB-2.1 Makefile.in \
config.charset locale.alias ref-add.sin ref-del.sin $(HEADERS) $(SOURCES)
info dvi:
$(OBJECTS): ../config.h libgnuintl.h
-bindtextdom.$lo finddomain.$lo loadmsgcat.$lo: gettextP.h gettext.h loadinfo.h
-dcgettext.$lo: gettextP.h gettext.h hash-string.h loadinfo.h
+bindtextdom.$lo dcgettext.$lo dcigettext.$lo dcngettext.$lo dgettext.$lo dngettext.$lo finddomain.$lo gettext.$lo intl-compat.$lo loadmsgcat.$lo localealias.$lo ngettext.$lo textdomain.$lo: gettextP.h gettext.h loadinfo.h
+dcigettext.$lo: hash-string.h
+explodename.$lo l10nflist.$lo: loadinfo.h
+dcigettext.$lo loadmsgcat.$lo plural.$lo plural-exp.$lo: plural-exp.h
tags: TAGS
#endif
#include "gettextP.h"
+#include "plural-exp.h"
#ifdef _LIBC
# include <libintl.h>
#else
#endif
-/* This is the representation of the expressions to determine the
- plural form. */
-struct expression
-{
- int nargs; /* Number of arguments. */
- enum operator
- {
- /* Without arguments: */
- var, /* The variable "n". */
- num, /* Decimal number. */
- /* Unary operators: */
- lnot, /* Logical NOT. */
- /* Binary operators: */
- mult, /* Multiplication. */
- divide, /* Division. */
- module, /* Module operation. */
- plus, /* Addition. */
- minus, /* Subtraction. */
- less_than, /* Comparison. */
- greater_than, /* Comparison. */
- less_or_equal, /* Comparison. */
- greater_or_equal, /* Comparison. */
- equal, /* Comparision for equality. */
- not_equal, /* Comparision for inequality. */
- land, /* Logical AND. */
- lor, /* Logical OR. */
- /* Ternary operators: */
- qmop /* Question mark operator. */
- } operation;
- union
- {
- unsigned long int num; /* Number value for `num'. */
- struct expression *args[3]; /* Up to three arguments. */
- } val;
-};
-
-/* This is the data structure to pass information to the parser and get
- the result in a thread-safe way. */
-struct parse_args
-{
- const char *cp;
- struct expression *res;
-};
-
-
/* The representation of an opened message catalog. */
struct loaded_domain
{
const char *__codeset));
#endif
-#ifdef _LIBC
-extern void __gettext_free_exp PARAMS ((struct expression *exp))
- internal_function;
-extern int __gettextparse PARAMS ((void *arg));
-#else
-extern void gettext_free_exp__ PARAMS ((struct expression *exp))
- internal_function;
-extern int gettextparse__ PARAMS ((void *arg));
-#endif
-
/* @@ begin of epilog @@ */
#endif /* gettextP.h */
#include "gettext.h"
#include "gettextP.h"
+#include "plural-exp.h"
#ifdef _LIBC
# include "../locale/localeinfo.h"
# define munmap __munmap
#endif
-/* Names for the libintl functions are a problem. They must not clash
- with existing names and they should follow ANSI C. But this source
- code is also used in GNU C Library where the names have a __
- prefix. So we have to make a difference here. */
-#ifdef _LIBC
-# define PLURAL_PARSE __gettextparse
-#else
-# define PLURAL_PARSE gettextparse__
-#endif
-
/* For those losing systems which don't have `alloca' we have to add
some additional code emulating it. */
#ifdef HAVE_ALLOCA
cached by one of GCC's features. */
int _nl_msg_cat_cntr;
-#if (defined __GNUC__ && !defined __APPLE_CC__) \
- || (defined __STDC_VERSION__ && __STDC_VERSION__ >= 199901L)
-
-/* These structs are the constant expression for the germanic plural
- form determination. It represents the expression "n != 1". */
-static const struct expression plvar =
-{
- .nargs = 0,
- .operation = var,
-};
-static const struct expression plone =
-{
- .nargs = 0,
- .operation = num,
- .val =
- {
- .num = 1
- }
-};
-static struct expression germanic_plural =
-{
- .nargs = 2,
- .operation = not_equal,
- .val =
- {
- .args =
- {
- [0] = (struct expression *) &plvar,
- [1] = (struct expression *) &plone
- }
- }
-};
-
-# define INIT_GERMANIC_PLURAL()
-
-#else
-
-/* For compilers without support for ISO C 99 struct/union initializers:
- Initialization at run-time. */
-
-static struct expression plvar;
-static struct expression plone;
-static struct expression germanic_plural;
-
-static void
-init_germanic_plural ()
-{
- if (plone.val.num == 0)
- {
- plvar.nargs = 0;
- plvar.operation = var;
-
- plone.nargs = 0;
- plone.operation = num;
- plone.val.num = 1;
-
- germanic_plural.nargs = 2;
- germanic_plural.operation = not_equal;
- germanic_plural.val.args[0] = &plvar;
- germanic_plural.val.args[1] = &plone;
- }
-}
-
-# define INIT_GERMANIC_PLURAL() init_germanic_plural ()
-
-#endif
-
/* Initialize the codeset dependent parts of an opened message catalog.
Return the header entry. */
nullentry = _nl_init_domain_conv (domain_file, domain, domainbinding);
/* Also look for a plural specification. */
- if (nullentry != NULL)
- {
- const char *plural;
- const char *nplurals;
-
- plural = strstr (nullentry, "plural=");
- nplurals = strstr (nullentry, "nplurals=");
- if (plural == NULL || nplurals == NULL)
- goto no_plural;
- else
- {
- /* First get the number. */
- char *endp;
- unsigned long int n;
- struct parse_args args;
-
- nplurals += 9;
- while (*nplurals != '\0' && isspace ((unsigned char) *nplurals))
- ++nplurals;
-#if defined HAVE_STRTOUL || defined _LIBC
- n = strtoul (nplurals, &endp, 10);
-#else
- for (endp = nplurals, n = 0; *endp >= '0' && *endp <= '9'; endp++)
- n = n * 10 + (*endp - '0');
-#endif
- domain->nplurals = n;
- if (nplurals == endp)
- goto no_plural;
-
- /* Due to the restrictions bison imposes onto the interface of the
- scanner function we have to put the input string and the result
- passed up from the parser into the same structure which address
- is passed down to the parser. */
- plural += 7;
- args.cp = plural;
- if (PLURAL_PARSE (&args) != 0)
- goto no_plural;
- domain->plural = args.res;
- }
- }
- else
- {
- /* By default we are using the Germanic form: singular form only
- for `one', the plural form otherwise. Yes, this is also what
- English is using since English is a Germanic language. */
- no_plural:
- INIT_GERMANIC_PLURAL ();
- domain->plural = &germanic_plural;
- domain->nplurals = 2;
- }
+ EXTRACT_PLURAL_EXPRESSION (nullentry, &domain->plural, &domain->nplurals);
}
--- /dev/null
+/* Expression parsing for plural form selection.
+ Copyright (C) 2000, 2001 Free Software Foundation, Inc.
+ Written by Ulrich Drepper <drepper@cygnus.com>, 2000.
+
+ This program 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, or (at your option)
+ any later version.
+
+ This program 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 this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+ USA. */
+
+#ifdef HAVE_CONFIG_H
+# include <config.h>
+#endif
+
+#include <ctype.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "plural-exp.h"
+
+#if (defined __GNUC__ && !defined __APPLE_CC__) \
+ || (defined __STDC_VERSION__ && __STDC_VERSION__ >= 199901L)
+
+/* These structs are the constant expression for the germanic plural
+ form determination. It represents the expression "n != 1". */
+static const struct expression plvar =
+{
+ .nargs = 0,
+ .operation = var,
+};
+static const struct expression plone =
+{
+ .nargs = 0,
+ .operation = num,
+ .val =
+ {
+ .num = 1
+ }
+};
+static struct expression germanic_plural =
+{
+ .nargs = 2,
+ .operation = not_equal,
+ .val =
+ {
+ .args =
+ {
+ [0] = (struct expression *) &plvar,
+ [1] = (struct expression *) &plone
+ }
+ }
+};
+
+# define INIT_GERMANIC_PLURAL()
+
+#else
+
+/* For compilers without support for ISO C 99 struct/union initializers:
+ Initialization at run-time. */
+
+static struct expression plvar;
+static struct expression plone;
+static struct expression germanic_plural;
+
+static void
+init_germanic_plural ()
+{
+ if (plone.val.num == 0)
+ {
+ plvar.nargs = 0;
+ plvar.operation = var;
+
+ plone.nargs = 0;
+ plone.operation = num;
+ plone.val.num = 1;
+
+ germanic_plural.nargs = 2;
+ germanic_plural.operation = not_equal;
+ germanic_plural.val.args[0] = &plvar;
+ germanic_plural.val.args[1] = &plone;
+ }
+}
+
+# define INIT_GERMANIC_PLURAL() init_germanic_plural ()
+
+#endif
+
+void
+internal_function
+EXTRACT_PLURAL_EXPRESSION (nullentry, pluralp, npluralsp)
+ const char *nullentry;
+ struct expression **pluralp;
+ unsigned long int *npluralsp;
+{
+ if (nullentry != NULL)
+ {
+ const char *plural;
+ const char *nplurals;
+
+ plural = strstr (nullentry, "plural=");
+ nplurals = strstr (nullentry, "nplurals=");
+ if (plural == NULL || nplurals == NULL)
+ goto no_plural;
+ else
+ {
+ /* First get the number. */
+ char *endp;
+ unsigned long int n;
+ struct parse_args args;
+
+ nplurals += 9;
+ while (*nplurals != '\0' && isspace ((unsigned char) *nplurals))
+ ++nplurals;
+#if defined HAVE_STRTOUL || defined _LIBC
+ n = strtoul (nplurals, &endp, 10);
+#else
+ for (endp = nplurals, n = 0; *endp >= '0' && *endp <= '9'; endp++)
+ n = n * 10 + (*endp - '0');
+#endif
+ if (nplurals == endp)
+ goto no_plural;
+ *npluralsp = n;
+
+ /* Due to the restrictions bison imposes onto the interface of the
+ scanner function we have to put the input string and the result
+ passed up from the parser into the same structure which address
+ is passed down to the parser. */
+ plural += 7;
+ args.cp = plural;
+ if (PLURAL_PARSE (&args) != 0)
+ goto no_plural;
+ *pluralp = args.res;
+ }
+ }
+ else
+ {
+ /* By default we are using the Germanic form: singular form only
+ for `one', the plural form otherwise. Yes, this is also what
+ English is using since English is a Germanic language. */
+ no_plural:
+ INIT_GERMANIC_PLURAL ();
+ *pluralp = &germanic_plural;
+ *npluralsp = 2;
+ }
+}
--- /dev/null
+/* Expression parsing for plural form selection.
+ Copyright (C) 2000, 2001 Free Software Foundation, Inc.
+ Written by Ulrich Drepper <drepper@cygnus.com>, 2000.
+
+ This program 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, or (at your option)
+ any later version.
+
+ This program 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 this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
+ USA. */
+
+#ifndef _PLURAL_EXP_H
+#define _PLURAL_EXP_H
+
+#ifndef PARAMS
+# if __STDC__
+# define PARAMS(args) args
+# else
+# define PARAMS(args) ()
+# endif
+#endif
+
+#ifndef internal_function
+# define internal_function
+#endif
+
+
+/* This is the representation of the expressions to determine the
+ plural form. */
+struct expression
+{
+ int nargs; /* Number of arguments. */
+ enum operator
+ {
+ /* Without arguments: */
+ var, /* The variable "n". */
+ num, /* Decimal number. */
+ /* Unary operators: */
+ lnot, /* Logical NOT. */
+ /* Binary operators: */
+ mult, /* Multiplication. */
+ divide, /* Division. */
+ module, /* Modulo operation. */
+ plus, /* Addition. */
+ minus, /* Subtraction. */
+ less_than, /* Comparison. */
+ greater_than, /* Comparison. */
+ less_or_equal, /* Comparison. */
+ greater_or_equal, /* Comparison. */
+ equal, /* Comparison for equality. */
+ not_equal, /* Comparison for inequality. */
+ land, /* Logical AND. */
+ lor, /* Logical OR. */
+ /* Ternary operators: */
+ qmop /* Question mark operator. */
+ } operation;
+ union
+ {
+ unsigned long int num; /* Number value for `num'. */
+ struct expression *args[3]; /* Up to three arguments. */
+ } val;
+};
+
+/* This is the data structure to pass information to the parser and get
+ the result in a thread-safe way. */
+struct parse_args
+{
+ const char *cp;
+ struct expression *res;
+};
+
+
+/* Names for the libintl functions are a problem. This source code is used
+ 1. in the GNU C Library library,
+ 2. in the GNU libintl library,
+ 3. in the GNU gettext tools.
+ The function names in each situation must be different, to allow for
+ binary incompatible changes in 'struct expression'. Furthermore,
+ 1. in the GNU C Library library, the names have a __ prefix,
+ 2.+3. in the GNU libintl library and in the GNU gettext tools, the names
+ must follow ANSI C and not start with __.
+ So we have to distinguish the three cases. */
+#ifdef _LIBC
+# define FREE_EXPRESSION __gettext_free_exp
+# define PLURAL_PARSE __gettextparse
+# define EXTRACT_PLURAL_EXPRESSION __gettext_extract_plural
+#elif defined (IN_LIBINTL)
+# define FREE_EXPRESSION gettext_free_exp__
+# define PLURAL_PARSE gettextparse__
+# define EXTRACT_PLURAL_EXPRESSION gettext_extract_plural__
+#else
+# define FREE_EXPRESSION free_plural_expression
+# define PLURAL_PARSE parse_plural_expression
+# define EXTRACT_PLURAL_EXPRESSION extract_plural_expression
+#endif
+extern void FREE_EXPRESSION PARAMS ((struct expression *exp))
+ internal_function;
+extern int PLURAL_PARSE PARAMS ((void *arg));
+extern void EXTRACT_PLURAL_EXPRESSION PARAMS ((const char *nullentry,
+ struct expression **pluralp,
+ unsigned long int *npluralsp))
+ internal_function;
+
+#endif /* _PLURAL_EXP_H */
#endif
#include <stdlib.h>
-#include "gettextP.h"
-
-/* Names for the libintl functions are a problem. They must not clash
- with existing names and they should follow ANSI C. But this source
- code is also used in GNU C Library where the names have a __
- prefix. So we have to make a difference here. */
-#ifdef _LIBC
-# define FREE_EXPRESSION __gettext_free_exp
-#else
-# define FREE_EXPRESSION gettext_free_exp__
-# define __gettextparse gettextparse__
+#include "plural-exp.h"
+
+/* The main function generated by the parser is called __gettextparse,
+ but we want it to be called PLURAL_PARSE. */
+#ifndef _LIBC
+# define __gettextparse PLURAL_PARSE
#endif
#define YYLEX_PARAM &((struct parse_args *) arg)->cp