Sorry, a new mistake has been removed If someone wants to test: a) msgfmt po/ca.po -o /usr/share/locale/ca/LC_MESSAGES/grub.mo b) edit /boot/grub/grub.cfg and change lang=C by lang=ca
Thanks, On Jan/24/2009, Carles Pina i Estany wrote: > > New version (same ChangeLog), fixing some warning messages, mistake in > 00_header, etc. > > On Jan/21/2009, Carles Pina i Estany wrote: > > > > Hello, > > > > I have been working with the gettext patch (and Robert gave me a hand, > > thanks) > > > > Take this version as a RFC and call for help (see at the bottom, it > > includes beer invitation in Fosdem). > > > > ChangeLog: > > ------------------- > > YYYY-MM-DD Carles Pina i Estany <car...@pina.cat> > > > > * Makefile.in: Add uptrans target to help to update .pot file > > * conf/common.rmk: Add grub-gettext_lib target, dependency and > > SOURCES, CFLAGS, LDFLAGS > > * kern/misc.c: Define grub_gettext symbol and add implement > > grub_gettext_dummy function > > * po/TODO: Temporary file with instructions of what Makefile.in > > will do > > * po/ca.po: Catalan translation stub > > * include/grub/misc.h: Define macro _(char *s). Declare > > grub_gettext_dummy and grub_gettext > > * gettext/gettext.c: New file with gettext implementation > > * normal/menu.c (print_message): add _( ) to some strings > > * util/grub.d/10_linux.in: include grub-gettext_lib file. > > For the Linux menuentry, call eval_gettext > > * util/grub.d/00_header.in: add locale_prefix and gettext > > locale detection and setting up the access to the mo directory > > * util/grub-mkconfig_lib.in: add get_locale_lang > > * util/grub-gettext_lib.in: new file > > ------------------- > > > > How to test and see something: > > -Apply the patch > > > > -In po/ execute msgfmt ca.po -o ca.mo > > > > -Copy ca.mo to /usr/share/locale/ca/LC_MESSAGES/grub.mo > > > > -Compile and install the patched Grub > > > > -Maybe the new 00_header will detect your language and add the > > configuration (this has not been tested) > > > > -In Grub2 console you should: > > set lang=ca > > set locale_prefix=/usr/share/locale > > insmod gettext > > (ESC) > > > > Then the lines under the menu box will appear in Catalan. > > > > The gettext module has a hook to the lang variable, if you change lang to > > a new value, it will reload the file. Ops! And I didn't do any hook for > > locale_prefix, I will do it but by the moment you can rmmod gettext > > and insmod again > > > > CALL FOR HELP: > > I need to write the Makefile.in (see po/TODO :-( ). I'm not used or > > familiar to write Makefiles :-( if someone wants to help it would > > speed up the process quite much. It needs only to merge the files with > > the new .pot, compile (msgfmt), and install to the correct directory. > > > > I exactly know what has to do, so if someone knows about > > installation/Makefiles and doesn't know about gettext it's not a > > problem, contact me. Else I will try to implement soon. > > > > I would even invite to a couple of beers in Fosdem if someone does > > this part :-) > > > > TODO: > > -the Makefile.in > > -and more testing about 00_header with gettext detection. > > -Add _("") for mainly all strings (I would do in a separate patch) > > -I have seen that Grub2 is not printing correctly the accents, > > could be a problem in gettext or in some other layer > > > > -- > > Carles Pina i Estany GPG id: 0x17756391 > > http://pinux.info > > > Index: Makefile.in > > =================================================================== > > --- Makefile.in (revision 1952) > > +++ Makefile.in (working copy) > > @@ -170,6 +170,16 @@ > > endif > > endif > > > > +#TODO: define on the header? > > +SHELLSDIR = $(srcdir)/util/grub.d > > +uptrans: > > + #TODO: only one xgettext for everything > > + xgettext -k_ -LC -o - `find "$(srcdir)/" -name '*.c'` -o po/grub.pot > > + > > + #TODO: in which variable we have all shell scripts? > > + xgettext -k_ -Lshell -o - $(SHELLSDIR)/00_header.in > > $(SHELLSDIR)/10_freebsd.in $(SHELLSDIR)/10_hurd.in $(SHELLSDIR)/10_linux.in > > $(SHELLSDIR)/10_windows.in $(SHELLSDIR)/30_os-prober.in > > $(SHELLSDIR)/40_custom.in -o po/grub.pot > > + > > + > > # Used for building modules externally > > pkglib_BUILDDIR += build_env.mk > > build_env.mk: Makefile > > Index: conf/common.rmk > > =================================================================== > > --- conf/common.rmk (revision 1952) > > +++ conf/common.rmk (working copy) > > @@ -142,6 +142,12 @@ > > lib_DATA += update-grub_lib > > CLEANFILES += update-grub_lib > > > > +grub-gettext_lib: util/grub-gettext_lib.in config.status > > + ./config.status --file=$@:$< > > + chmod +x $@ > > +lib_DATA += grub-gettext_lib > > +CLEANFILES += grub-gettext_lib > > + > > %: util/grub.d/%.in config.status > > ./config.status --file=$@:$< > > chmod +x $@ > > @@ -329,7 +335,7 @@ > > cmp.mod cat.mod help.mod search.mod > > \ > > loopback.mod fs_uuid.mod configfile.mod echo.mod \ > > terminfo.mod test.mod blocklist.mod hexdump.mod \ > > - read.mod sleep.mod loadenv.mod crc.mod > > + read.mod sleep.mod loadenv.mod crc.mod gettext.mod > > > > # For hello.mod. > > hello_mod_SOURCES = hello/hello.c > > @@ -492,3 +498,10 @@ > > bufio_mod_SOURCES = io/bufio.c > > bufio_mod_CFLAGS = $(COMMON_CFLAGS) > > bufio_mod_LDFLAGS = $(COMMON_LDFLAGS) > > + > > +# For gettext.mod. > > +gettext_mod_SOURCES = gettext/gettext.c > > +gettext_mod_CFLAGS = $(COMMON_CFLAGS) > > +gettext_mod_LDFLAGS = $(COMMON_LDFLAGS) > > + > > + > > Index: conf/common.mk > > =================================================================== > > --- conf/common.mk (revision 1952) > > +++ conf/common.mk (working copy) > > @@ -567,6 +567,12 @@ > > lib_DATA += update-grub_lib > > CLEANFILES += update-grub_lib > > > > +grub-gettext_lib: util/grub-gettext_lib.in config.status > > + ./config.status --file=$@:$< > > + chmod +x $@ > > +lib_DATA += grub-gettext_lib > > +CLEANFILES += grub-gettext_lib > > + > > %: util/grub.d/%.in config.status > > ./config.status --file=$@:$< > > chmod +x $@ > > @@ -2366,7 +2372,7 @@ > > cmp.mod cat.mod help.mod search.mod > > \ > > loopback.mod fs_uuid.mod configfile.mod echo.mod \ > > terminfo.mod test.mod blocklist.mod hexdump.mod \ > > - read.mod sleep.mod loadenv.mod crc.mod > > + read.mod sleep.mod loadenv.mod crc.mod gettext.mod > > > > # For hello.mod. > > hello_mod_SOURCES = hello/hello.c > > @@ -4236,3 +4242,62 @@ > > > > bufio_mod_CFLAGS = $(COMMON_CFLAGS) > > bufio_mod_LDFLAGS = $(COMMON_LDFLAGS) > > + > > +# For gettext.mod. > > +gettext_mod_SOURCES = gettext/gettext.c > > +CLEANFILES += gettext.mod mod-gettext.o mod-gettext.c pre-gettext.o > > gettext_mod-gettext_gettext.o und-gettext.lst > > +ifneq ($(gettext_mod_EXPORTS),no) > > +CLEANFILES += def-gettext.lst > > +DEFSYMFILES += def-gettext.lst > > +endif > > +MOSTLYCLEANFILES += gettext_mod-gettext_gettext.d > > +UNDSYMFILES += und-gettext.lst > > + > > +gettext.mod: pre-gettext.o mod-gettext.o $(TARGET_OBJ2ELF) > > + -rm -f $@ > > + $(TARGET_CC) $(gettext_mod_LDFLAGS) $(TARGET_LDFLAGS) $(MODULE_LDFLAGS) > > -Wl,-r,-d -o $@ pre-gettext.o mod-gettext.o > > + if test ! -z $(TARGET_OBJ2ELF); then ./$(TARGET_OBJ2ELF) $@ || (rm -f > > $@; exit 1); fi > > + $(STRIP) --strip-unneeded -K grub_mod_init -K grub_mod_fini -K > > _grub_mod_init -K _grub_mod_fini -R .note -R .comment $@ > > + > > +pre-gettext.o: $(gettext_mod_DEPENDENCIES) gettext_mod-gettext_gettext.o > > + -rm -f $@ > > + $(TARGET_CC) $(gettext_mod_LDFLAGS) $(TARGET_LDFLAGS) -Wl,-r,-d -o $@ > > gettext_mod-gettext_gettext.o > > + > > +mod-gettext.o: mod-gettext.c > > + $(TARGET_CC) $(TARGET_CPPFLAGS) $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) > > -c -o $@ $< > > + > > +mod-gettext.c: $(builddir)/moddep.lst $(srcdir)/genmodsrc.sh > > + sh $(srcdir)/genmodsrc.sh 'gettext' $< > $@ || (rm -f $@; exit 1) > > + > > +ifneq ($(gettext_mod_EXPORTS),no) > > +def-gettext.lst: pre-gettext.o > > + $(NM) -g --defined-only -P -p $< | sed 's/^\([^ ]*\).*/\1 gettext/' > $@ > > +endif > > + > > +und-gettext.lst: pre-gettext.o > > + echo 'gettext' > $@ > > + $(NM) -u -P -p $< | cut -f1 -d' ' >> $@ > > + > > +gettext_mod-gettext_gettext.o: gettext/gettext.c > > $(gettext/gettext.c_DEPENDENCIES) > > + $(TARGET_CC) -Igettext -I$(srcdir)/gettext $(TARGET_CPPFLAGS) > > $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) -MD -c -o $@ $< > > +-include gettext_mod-gettext_gettext.d > > + > > +CLEANFILES += cmd-gettext_mod-gettext_gettext.lst > > fs-gettext_mod-gettext_gettext.lst partmap-gettext_mod-gettext_gettext.lst > > +COMMANDFILES += cmd-gettext_mod-gettext_gettext.lst > > +FSFILES += fs-gettext_mod-gettext_gettext.lst > > +PARTMAPFILES += partmap-gettext_mod-gettext_gettext.lst > > + > > +cmd-gettext_mod-gettext_gettext.lst: gettext/gettext.c > > $(gettext/gettext.c_DEPENDENCIES) gencmdlist.sh > > + set -e; $(TARGET_CC) -Igettext -I$(srcdir)/gettext > > $(TARGET_CPPFLAGS) $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) -E $< | sh > > $(srcdir)/gencmdlist.sh gettext > $@ || (rm -f $@; exit 1) > > + > > +fs-gettext_mod-gettext_gettext.lst: gettext/gettext.c > > $(gettext/gettext.c_DEPENDENCIES) genfslist.sh > > + set -e; $(TARGET_CC) -Igettext -I$(srcdir)/gettext > > $(TARGET_CPPFLAGS) $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) -E $< | sh > > $(srcdir)/genfslist.sh gettext > $@ || (rm -f $@; exit 1) > > + > > +partmap-gettext_mod-gettext_gettext.lst: gettext/gettext.c > > $(gettext/gettext.c_DEPENDENCIES) genpartmaplist.sh > > + set -e; $(TARGET_CC) -Igettext -I$(srcdir)/gettext > > $(TARGET_CPPFLAGS) $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) -E $< | sh > > $(srcdir)/genpartmaplist.sh gettext > $@ || (rm -f $@; exit 1) > > + > > + > > +gettext_mod_CFLAGS = $(COMMON_CFLAGS) > > +gettext_mod_LDFLAGS = $(COMMON_LDFLAGS) > > + > > + > > Index: kern/misc.c > > =================================================================== > > --- kern/misc.c (revision 1952) > > +++ kern/misc.c (working copy) > > @@ -24,6 +24,8 @@ > > #include <grub/term.h> > > #include <grub/env.h> > > > > +char* (*grub_gettext) (const char *s) = grub_gettext_dummy; > > + > > void * > > grub_memmove (void *dest, const void *src, grub_size_t n) > > { > > @@ -1036,6 +1038,13 @@ > > return p - dest; > > } > > > > +/* grub_gettext_dummy is not translating anything. */ > > +char * > > +grub_gettext_dummy (const char *s) > > +{ > > + return s; > > +} > > + > > /* Abort GRUB. This function does not return. */ > > void > > grub_abort (void) > > Index: po/ca.po > > =================================================================== > > --- po/ca.po (revision 0) > > +++ po/ca.po (revision 0) > > @@ -0,0 +1,39 @@ > > +# SOME DESCRIPTIVE TITLE. > > +# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER > > +# This file is distributed under the same license as the PACKAGE package. > > +# FIRST AUTHOR <em...@address>, YEAR. > > +# > > +#, fuzzy > > +msgid "" > > +msgstr "" > > +"Project-Id-Version: PACKAGE VERSION\n" > > +"Report-Msgid-Bugs-To: \n" > > +"POT-Creation-Date: 2009-01-21 21:14+0100\n" > > +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" > > +"Last-Translator: FULL NAME <em...@address>\n" > > +"Language-Team: LANGUAGE <l...@li.org>\n" > > +"MIME-Version: 1.0\n" > > +"Content-Type: text/plain; charset=CHARSET\n" > > +"Content-Transfer-Encoding: 8bit\n" > > + > > +#: normal/menu.c:90 > > +#, c-format > > +msgid "" > > +"\n" > > +" Use the %C and %C keys to select which entry is highlighted.\n" > > +msgstr "" > > +"\n" > > +" Utilitzeu les tecles %C i %C per seleccionar l'entrada.\n" > > + > > +#: normal/menu.c:93 > > +msgid "" > > +" Press enter to boot the selected OS, 'e' to edit the\n" > > +" commands before booting or 'c' for a command-line." > > +msgstr "" > > +" Presioneu retorn per arrancar el SO seleccionat, 'e' editar\n" > > +" les comandes abans d'arrancar, 'c' per línia d'ordres." > > + > > +#: util/grub.d/10_linux.in:148 > > +#, sh-format > > +msgid "${OS}, linux ${version} (single-user mode)" > > +msgstr "${OS}, linux ${version} (mode mono-usuari)" > > Index: po/TODO > > =================================================================== > > --- po/TODO (revision 0) > > +++ po/TODO (revision 0) > > @@ -0,0 +1,5 @@ > > +Prepare a Makefile.in to: > > + > > +-Compile all .po to .mo (msgfmt $LANG.po -o $LANG.mo) > > +-Copy to /usr/share/locale/$LANG/LC_MESSAGES/grub.mo (or > > /usr/local/share/locale/$LANG/LC_MESSAGES/..., so $prefix...) > > +-Check that grub-gettext_lib.in is correct > > Index: include/grub/misc.h > > =================================================================== > > --- include/grub/misc.h (revision 1952) > > +++ include/grub/misc.h (working copy) > > @@ -31,6 +31,8 @@ > > /* XXX: If grub_memmove is too slow, we must implement grub_memcpy. */ > > #define grub_memcpy(d,s,n) grub_memmove ((d), (s), (n)) > > > > +#define _(s) grub_gettext(s) > > + > > void *EXPORT_FUNC(grub_memmove) (void *dest, const void *src, grub_size_t > > n); > > char *EXPORT_FUNC(grub_strcpy) (char *dest, const char *src); > > char *EXPORT_FUNC(grub_strncpy) (char *dest, const char *src, int c); > > @@ -84,6 +86,9 @@ > > grub_uint64_t EXPORT_FUNC(grub_divmod64) (grub_uint64_t n, > > grub_uint32_t d, grub_uint32_t *r); > > > > +char *EXPORT_FUNC(grub_gettext_dummy) (const char *s); > > +extern char *(*EXPORT_VAR(grub_gettext)) (const char *s);// = > > grub_gettext_dummy; > > + > > #ifdef NEED_ENABLE_EXECUTE_STACK > > void EXPORT_FUNC(__enable_execute_stack) (void *addr); > > #endif > > Index: gettext/gettext.c > > =================================================================== > > --- gettext/gettext.c (revision 0) > > +++ gettext/gettext.c (revision 0) > > @@ -0,0 +1,299 @@ > > +/* gettext.c - gettext module */ > > +/* > > + * GRUB -- GRand Unified Bootloader > > + * Copyright (C) 2009 Free Software Foundation, Inc. > > + * > > + * GRUB is free software: you can redistribute it and/or modify > > + * it under the terms of the GNU General Public License as published by > > + * the Free Software Foundation, either version 3 of the License, or > > + * (at your option) any later version. > > + * > > + * GRUB 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 General Public License for more details. > > + * > > + * You should have received a copy of the GNU General Public License > > + * along with GRUB. If not, see <http://www.gnu.org/licenses/>. > > + */ > > + > > +#include <grub/types.h> > > +#include <grub/misc.h> > > +#include <grub/mm.h> > > +#include <grub/err.h> > > +#include <grub/dl.h> > > +#include <grub/normal.h> > > +#include <grub/file.h> > > +#include <grub/kernel.h> > > + > > +/* > > + .mo file information from: > > + http://www.gnu.org/software/autoconf/manual/gettext/MO-Files.html . > > +*/ > > + > > + > > +static grub_file_t grub_mofile_open (const char *name); > > +static grub_file_t fd_mo; > > + > > +static int grub_gettext_offsetoriginal; > > +static int grub_gettext_max; > > + > > +static char* (*grub_gettext_original) (const char *s); > > + > > +#define GETTEXT_MAGIC_NUMBER 0 > > +#define GETTEXT_FILE_FORMAT 4 > > +#define GETTEXT_NUMBER_OF_STRINGS 8 > > +#define GETTEXT_OFFSET_ORIGINAL 12 > > +#define GETTEXT_OFFSET_TRANSLATION 16 > > + > > +static int > > +grub_gettext_get_info (int offset) > > +{ > > + int buf; > > + > > + grub_file_seek (fd_mo, offset); > > + grub_file_read (fd_mo, (char*) &buf, 4); > > + return buf; > > +} > > + > > +static void > > +grub_gettext_getstring_from_offset (int offset, int length, char > > *translation) > > +{ > > + grub_file_seek (fd_mo,offset); > > + grub_file_read (fd_mo,translation,length); > > + translation[length] = '\0'; > > +} > > + > > +static char* > > +grub_gettext_gettranslation_number (int i) > > +{ > > + int offsettranslation; > > + int position; > > + int length, offset; > > + char *translation; > > + > > + offsettranslation = grub_gettext_get_info (GETTEXT_OFFSET_TRANSLATION); > > + > > + position=offsettranslation+i*8; > > + > > + grub_file_seek (fd_mo, position); > > + grub_file_read (fd_mo, (char*) &length, 4); > > + > > + grub_file_seek (fd_mo, position + 4), > > + grub_file_read (fd_mo, (char*) &offset, 4); > > + > > + translation = grub_malloc(length + 1); > > + grub_gettext_getstring_from_offset (offset, length, translation); > > + > > + return translation; > > +} > > + > > +static char* > > +grub_gettext_getstring_num (int num) > > +{ > > + int position; > > + int length, offset; > > + char *original; > > + > > + /* Get position for string i. */ > > + position = grub_gettext_offsetoriginal + (num * 8); > > + > > + /* Get the length of the string i. */ > > + grub_file_seek (fd_mo, position); > > + grub_file_read (fd_mo, (char *) &length, 4); > > + > > + /* Get the offset of the string i. */ > > + grub_file_seek (fd_mo, position + 4); > > + grub_file_read (fd_mo, (char *) &offset, 4); > > + > > + /* Get the string i. */ > > + original = grub_malloc (length + 1); > > + grub_gettext_getstring_from_offset (offset, length, original); > > + > > + return original; > > +} > > + > > +static char* > > +grub_gettext_translate (char *orig) > > +{ > > + char *current_string; > > + char *ret; > > + > > + int min,max,current; > > + > > + if (fd_mo == 0) > > + return orig; > > + > > + min = 0; > > + max = grub_gettext_max; > > + > > + current = (max + min) / 2; > > + > > + while (current != min && current != max) > > + { > > + current_string = grub_gettext_getstring_num (current); > > + /* grub_printf("Current: %s\n",current_string); */ > > + > > + /* Search by bissection. */ > > + if (grub_strcmp (current_string, orig) < 0) > > + { > > + grub_free(current_string); > > + min=current; > > + } > > + else if (grub_strcmp (current_string, orig) > 0) > > + { > > + grub_free(current_string); > > + max=current; > > + } > > + else if (grub_strcmp (current_string, orig) == 0) > > + { > > + grub_free(current_string); > > + return grub_gettext_gettranslation_number (current); > > + } > > + current = (max+min)/2; > > + } > > + > > + ret = grub_malloc(grub_strlen(orig) + 1); > > + grub_strcpy(ret,orig); > > + return ret; > > +} > > + > > +// XXX: Return a real grub_err_t or static void > > +static grub_err_t > > +grub_cmd_translate (struct grub_arg_list *state __attribute__ ((unused)), > > + int argc __attribute__ ((unused)), > > + char **args __attribute__ ((unused))) > > +{ > > + if (argc != 1) > > + return grub_error (GRUB_ERR_BAD_ARGUMENT, "text to translate > > required"); > > + > > + char *translation; > > + > > + translation = grub_gettext_translate(args[0]); > > + grub_printf("%s\n",translation); > > + //grub_printf("grub__: %d\n",grub__); > > + > > + return 0; > > +} > > + > > +/* This is similar to grub_gzfile_open. */ > > +static grub_file_t > > +grub_mofile_open (const char *filename) > > +{ > > + int unsigned magic; > > + int version; > > + > > + /* Using fd_mo and not another variable because > > + it's needed for grub_gettext_get_info. */ > > + > > + fd_mo = grub_file_open (filename); > > + if (! fd_mo) > > + { > > + grub_error (GRUB_ERR_FILE_READ_ERROR, "Cannot read %s",filename); > > + return 0; > > + } > > + > > + magic = grub_gettext_get_info (GETTEXT_MAGIC_NUMBER); > > + > > + if (magic != 0x950412de) > > + { > > + grub_error (GRUB_ERR_BAD_FILE_TYPE, "mo: invalid mo file: %s", > > filename); > > + grub_file_close (fd_mo); > > + fd_mo = 0; > > + return 0; > > + } > > + > > + version = grub_gettext_get_info (GETTEXT_FILE_FORMAT); > > + > > + if (version != 0) > > + { > > + grub_error (GRUB_ERR_BAD_FILE_TYPE, "mo: invalid mo version in file: > > %s", filename); > > + fd_mo = 0; > > + return 0; > > + } > > + > > + /* > > + Do we want .mo.gz files? Then, the code: > > + file = grub_gzio_open (io, 0); // 0: transparent > > + if (! file) > > + { > > + grub_printf("Problems opening the file\n"); > > + grub_file_close (io); > > + return 0; > > + } > > + */ > > + > > + return fd_mo; > > +} > > + > > +static void > > +grub_gettext_init_ext (const char *lang) > > +{ > > + char *mo_file; > > + char *locale_prefix; > > + > > + locale_prefix = grub_env_get ("locale_prefix"); > > + > > + fd_mo = 0; > > + > > + // mo_file e.g.: /usr/share/locale/ca/LC_MESSAGES/grub.mo > > + > > + mo_file = grub_malloc (grub_strlen (locale_prefix) + sizeof ("/") + > > grub_strlen (lang) + sizeof ("/LC_MESSAGES/grub.mo")); > > + > > + if (! mo_file) > > + return; > > + > > + grub_sprintf (mo_file, "%s/%s/LC_MESSAGES/grub.mo", locale_prefix, lang); > > + /* XXX: lang is written by the user, need to sanitaze the input? */ > > + > > + fd_mo = grub_mofile_open(mo_file); > > + grub_free (mo_file); > > + > > + if (fd_mo) > > + { > > + grub_gettext_offsetoriginal = > > grub_gettext_get_info(GETTEXT_OFFSET_ORIGINAL); > > + grub_gettext_max = grub_gettext_get_info(GETTEXT_NUMBER_OF_STRINGS); > > + > > + grub_gettext_original = grub_gettext; > > + grub_gettext = grub_gettext_translate; > > + } > > +} > > + > > +static char* > > +grub_gettext_env_write_lang (struct grub_env_var *var __attribute__ > > ((unused)), > > + const char *val) > > +{ > > + grub_gettext_init_ext (val); > > + > > + return grub_strdup (val); > > +} > > + > > +GRUB_MOD_INIT(gettext) > > +{ > > + (void)mod; /* To stop warning. */ > > + > > + const char *lang; > > + > > + lang = grub_env_get ("lang"); > > + > > + grub_gettext_init_ext (lang); > > + > > + /* Testing: > > + grub_register_command ("_", grub_cmd_translate, GRUB_COMMAND_FLAG_BOTH, > > + "_", "internalization support trans", 0); > > + */ > > + > > + /* Reload .mo file information if lang changes. */ > > + grub_register_variable_hook ("lang", NULL, grub_gettext_env_write_lang); > > + > > + /* Preserve hooks after context changes. */ > > + grub_env_export ("lang"); > > +} > > + > > +GRUB_MOD_FINI(gettext) > > +{ > > + if (fd_mo != 0) > > + grub_file_close(fd_mo); > > + > > + grub_gettext = grub_gettext_original; > > +} > > Index: normal/menu.c > > =================================================================== > > --- normal/menu.c (revision 1952) > > +++ normal/menu.c (working copy) > > @@ -87,17 +87,16 @@ > > } > > else > > { > > - grub_printf ("\n\ > > - Use the %C and %C keys to select which entry is highlighted.\n", > > + grub_printf (_("\n\ > > + Use the %C and %C keys to select which entry is highlighted.\n"), > > (grub_uint32_t) GRUB_TERM_DISP_UP, (grub_uint32_t) > > GRUB_TERM_DISP_DOWN); > > - grub_printf ("\ > > + grub_printf (_("\ > > Press enter to boot the selected OS, \'e\' to edit the\n\ > > - commands before booting or \'c\' for a command-line."); > > + commands before booting or \'c\' for a command-line.")); > > if (nested) > > grub_printf ("\n\ > > ESC to return previous menu."); > > } > > - > > } > > > > static grub_menu_entry_t > > @@ -317,7 +316,7 @@ > > They are required to clear the line. */ > > char *msg = " The highlighted entry will be booted automatically in > > %ds. "; > > char *msg_end = grub_strchr (msg, '%'); > > - > > + > > grub_gotoxy (second_stage ? (msg_end - msg) : 0, GRUB_TERM_HEIGHT - 3); > > grub_printf (second_stage ? msg_end : msg, timeout); > > grub_gotoxy (GRUB_TERM_CURSOR_X, GRUB_TERM_FIRST_ENTRY_Y + offset); > > Index: util/grub.d/10_linux.in > > =================================================================== > > --- util/grub.d/10_linux.in (revision 1952) > > +++ util/grub.d/10_linux.in (working copy) > > @@ -20,6 +20,7 @@ > > exec_pref...@exec_prefix@ > > libd...@libdir@ > > . ${libdir}/grub/grub-mkconfig_lib > > +. ${libdir}/grub/grub-gettext_lib > > > > if [ "x${GRUB_DISTRIBUTOR}" = "x" ] ; then > > OS=GNU/Linux > > @@ -139,7 +140,7 @@ > > EOF > > > > cat << EOF > > -menuentry "${OS}, linux ${version} (single-user mode)" { > > +menuentry "$(eval_gettext '${OS}, linux ${version} (single-user mode)')" { > > EOF > > prepare_grub_to_access_device ${GRUB_DEVICE_BOOT} | sed -e "s/^/\t/" > > cat << EOF > > Index: util/grub.d/00_header.in > > =================================================================== > > --- util/grub.d/00_header.in (revision 1952) > > +++ util/grub.d/00_header.in (working copy) > > @@ -22,6 +22,7 @@ > > exec_pref...@exec_prefix@ > > libd...@libdir@ > > grub_prefix=`echo /boot/grub | sed ${transform}` > > +locale_prefix="/usr/share/locale" # TODO: dynamic with exec_prefix ? > > > > . ${libdir}/grub/grub-mkconfig_lib > > > > @@ -112,3 +113,17 @@ > > EOF > > ;; > > esac > > + > > +if test -e ${grub_prefix}/gettext.mod ; then > > + # Make the locales accesible > > + prepare_grub_to_access_device `${grub_probe} --target=device > > ${locale_prefix}` > > + lang=`get_locale_lang` > > + cat << EOF > > +if `make_system_path_relative_to_its_root ${locale_prefix}` ; then > > + set locale_prefix=${locale_prefix} > > + set lang=${lang} > > + insmod gettext > > +EOF > > +else > > + echo "gettext module is not available" > > +fi > > Index: util/grub-mkconfig_lib.in > > =================================================================== > > --- util/grub-mkconfig_lib.in (revision 1952) > > +++ util/grub-mkconfig_lib.in (working copy) > > @@ -176,3 +176,14 @@ > > fi > > return 0 > > } > > + > > +get_locale_lang () > > +{ > > + lang="`echo ${LANG} | cut -d _ -f 1`" > > + if [ "x${lang}" = "x" ] ; then > > + return 1 > > + else > > + echo "${lang}" > > + return 0 > > + fi > > +} > > Index: util/grub-gettext_lib.in > > =================================================================== > > --- util/grub-gettext_lib.in (revision 0) > > +++ util/grub-gettext_lib.in (revision 0) > > @@ -0,0 +1,23 @@ > > +# Configuration of grub-gettext > > +# Copyright (C) 2009 Free Software Foundation, Inc. > > +# > > +# GRUB is free software: you can redistribute it and/or modify > > +# it under the terms of the GNU General Public License as published by > > +# the Free Software Foundation, either version 3 of the License, or > > +# (at your option) any later version. > > +# > > +# GRUB 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 General Public License for more details. > > +# > > +# You should have received a copy of the GNU General Public License > > +# along with GRUB. If not, see <http://www.gnu.org/licenses/>. > > + > > +pref...@prefix@ > > +exec_pref...@exec_prefix@ > > +libd...@libdir@ > > + > > +textdomaind...@prefix@/share/locale > > +TEXTDOMAIN=grub > > +. gettext.sh > > > > Property changes on: util/grub-gettext_lib.in > > ___________________________________________________________________ > > Added: svn:mergeinfo > > > > > _______________________________________________ > > Grub-devel mailing list > > Grub-devel@gnu.org > > http://lists.gnu.org/mailman/listinfo/grub-devel > > -- > Carles Pina i Estany GPG id: 0x17756391 > http://pinux.info > Index: Makefile.in > =================================================================== > --- Makefile.in (revision 1954) > +++ Makefile.in (working copy) > @@ -112,6 +112,7 @@ > PKGDATA = $(pkgdata_DATA) $(pkgdata_SRCDIR) > PROGRAMS = $(bin_UTILITIES) $(sbin_UTILITIES) > SCRIPTS = $(bin_SCRIPTS) $(sbin_SCRIPTS) $(grub-mkconfig_SCRIPTS) > +GRUBD = $(srcdir)/util/grub.d > > CLEANFILES = > MOSTLYCLEANFILES = > @@ -170,6 +171,11 @@ > endif > endif > > +uptrans: > + xgettext -k_ -LC -o - `find "$(srcdir)/" -name '*.c'` -o po/grub.pot > + xgettext -k_ -Lshell -o - $(GRUBD)/* -j -o po/grub.pot > + > + > # Used for building modules externally > pkglib_BUILDDIR += build_env.mk > build_env.mk: Makefile > Index: conf/common.rmk > =================================================================== > --- conf/common.rmk (revision 1954) > +++ conf/common.rmk (working copy) > @@ -142,6 +142,12 @@ > lib_DATA += update-grub_lib > CLEANFILES += update-grub_lib > > +grub-gettext_lib: util/grub-gettext_lib.in config.status > + ./config.status --file=$@:$< > + chmod +x $@ > +lib_DATA += grub-gettext_lib > +CLEANFILES += grub-gettext_lib > + > %: util/grub.d/%.in config.status > ./config.status --file=$@:$< > chmod +x $@ > @@ -329,7 +335,7 @@ > cmp.mod cat.mod help.mod search.mod > \ > loopback.mod fs_uuid.mod configfile.mod echo.mod \ > terminfo.mod test.mod blocklist.mod hexdump.mod \ > - read.mod sleep.mod loadenv.mod crc.mod > + read.mod sleep.mod loadenv.mod crc.mod gettext.mod > > # For hello.mod. > hello_mod_SOURCES = hello/hello.c > @@ -492,3 +498,10 @@ > bufio_mod_SOURCES = io/bufio.c > bufio_mod_CFLAGS = $(COMMON_CFLAGS) > bufio_mod_LDFLAGS = $(COMMON_LDFLAGS) > + > +# For gettext.mod. > +gettext_mod_SOURCES = gettext/gettext.c > +gettext_mod_CFLAGS = $(COMMON_CFLAGS) > +gettext_mod_LDFLAGS = $(COMMON_LDFLAGS) > + > + > Index: conf/common.mk > =================================================================== > --- conf/common.mk (revision 1954) > +++ conf/common.mk (working copy) > @@ -567,6 +567,12 @@ > lib_DATA += update-grub_lib > CLEANFILES += update-grub_lib > > +grub-gettext_lib: util/grub-gettext_lib.in config.status > + ./config.status --file=$@:$< > + chmod +x $@ > +lib_DATA += grub-gettext_lib > +CLEANFILES += grub-gettext_lib > + > %: util/grub.d/%.in config.status > ./config.status --file=$@:$< > chmod +x $@ > @@ -2366,7 +2372,7 @@ > cmp.mod cat.mod help.mod search.mod > \ > loopback.mod fs_uuid.mod configfile.mod echo.mod \ > terminfo.mod test.mod blocklist.mod hexdump.mod \ > - read.mod sleep.mod loadenv.mod crc.mod > + read.mod sleep.mod loadenv.mod crc.mod gettext.mod > > # For hello.mod. > hello_mod_SOURCES = hello/hello.c > @@ -4236,3 +4242,62 @@ > > bufio_mod_CFLAGS = $(COMMON_CFLAGS) > bufio_mod_LDFLAGS = $(COMMON_LDFLAGS) > + > +# For gettext.mod. > +gettext_mod_SOURCES = gettext/gettext.c > +CLEANFILES += gettext.mod mod-gettext.o mod-gettext.c pre-gettext.o > gettext_mod-gettext_gettext.o und-gettext.lst > +ifneq ($(gettext_mod_EXPORTS),no) > +CLEANFILES += def-gettext.lst > +DEFSYMFILES += def-gettext.lst > +endif > +MOSTLYCLEANFILES += gettext_mod-gettext_gettext.d > +UNDSYMFILES += und-gettext.lst > + > +gettext.mod: pre-gettext.o mod-gettext.o $(TARGET_OBJ2ELF) > + -rm -f $@ > + $(TARGET_CC) $(gettext_mod_LDFLAGS) $(TARGET_LDFLAGS) $(MODULE_LDFLAGS) > -Wl,-r,-d -o $@ pre-gettext.o mod-gettext.o > + if test ! -z $(TARGET_OBJ2ELF); then ./$(TARGET_OBJ2ELF) $@ || (rm -f > $@; exit 1); fi > + $(STRIP) --strip-unneeded -K grub_mod_init -K grub_mod_fini -K > _grub_mod_init -K _grub_mod_fini -R .note -R .comment $@ > + > +pre-gettext.o: $(gettext_mod_DEPENDENCIES) gettext_mod-gettext_gettext.o > + -rm -f $@ > + $(TARGET_CC) $(gettext_mod_LDFLAGS) $(TARGET_LDFLAGS) -Wl,-r,-d -o $@ > gettext_mod-gettext_gettext.o > + > +mod-gettext.o: mod-gettext.c > + $(TARGET_CC) $(TARGET_CPPFLAGS) $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) > -c -o $@ $< > + > +mod-gettext.c: $(builddir)/moddep.lst $(srcdir)/genmodsrc.sh > + sh $(srcdir)/genmodsrc.sh 'gettext' $< > $@ || (rm -f $@; exit 1) > + > +ifneq ($(gettext_mod_EXPORTS),no) > +def-gettext.lst: pre-gettext.o > + $(NM) -g --defined-only -P -p $< | sed 's/^\([^ ]*\).*/\1 gettext/' > $@ > +endif > + > +und-gettext.lst: pre-gettext.o > + echo 'gettext' > $@ > + $(NM) -u -P -p $< | cut -f1 -d' ' >> $@ > + > +gettext_mod-gettext_gettext.o: gettext/gettext.c > $(gettext/gettext.c_DEPENDENCIES) > + $(TARGET_CC) -Igettext -I$(srcdir)/gettext $(TARGET_CPPFLAGS) > $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) -MD -c -o $@ $< > +-include gettext_mod-gettext_gettext.d > + > +CLEANFILES += cmd-gettext_mod-gettext_gettext.lst > fs-gettext_mod-gettext_gettext.lst partmap-gettext_mod-gettext_gettext.lst > +COMMANDFILES += cmd-gettext_mod-gettext_gettext.lst > +FSFILES += fs-gettext_mod-gettext_gettext.lst > +PARTMAPFILES += partmap-gettext_mod-gettext_gettext.lst > + > +cmd-gettext_mod-gettext_gettext.lst: gettext/gettext.c > $(gettext/gettext.c_DEPENDENCIES) gencmdlist.sh > + set -e; $(TARGET_CC) -Igettext -I$(srcdir)/gettext > $(TARGET_CPPFLAGS) $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) -E $< | sh > $(srcdir)/gencmdlist.sh gettext > $@ || (rm -f $@; exit 1) > + > +fs-gettext_mod-gettext_gettext.lst: gettext/gettext.c > $(gettext/gettext.c_DEPENDENCIES) genfslist.sh > + set -e; $(TARGET_CC) -Igettext -I$(srcdir)/gettext > $(TARGET_CPPFLAGS) $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) -E $< | sh > $(srcdir)/genfslist.sh gettext > $@ || (rm -f $@; exit 1) > + > +partmap-gettext_mod-gettext_gettext.lst: gettext/gettext.c > $(gettext/gettext.c_DEPENDENCIES) genpartmaplist.sh > + set -e; $(TARGET_CC) -Igettext -I$(srcdir)/gettext > $(TARGET_CPPFLAGS) $(TARGET_CFLAGS) $(gettext_mod_CFLAGS) -E $< | sh > $(srcdir)/genpartmaplist.sh gettext > $@ || (rm -f $@; exit 1) > + > + > +gettext_mod_CFLAGS = $(COMMON_CFLAGS) > +gettext_mod_LDFLAGS = $(COMMON_LDFLAGS) > + > + > Index: kern/misc.c > =================================================================== > --- kern/misc.c (revision 1954) > +++ kern/misc.c (working copy) > @@ -24,6 +24,8 @@ > #include <grub/term.h> > #include <grub/env.h> > > +const char* (*grub_gettext) (const char *s) = grub_gettext_dummy; > + > void * > grub_memmove (void *dest, const void *src, grub_size_t n) > { > @@ -1044,6 +1046,13 @@ > return p - dest; > } > > +/* grub_gettext_dummy is not translating anything. */ > +const char * > +grub_gettext_dummy (const char *s) > +{ > + return s; > +} > + > /* Abort GRUB. This function does not return. */ > void > grub_abort (void) > Index: po/ca.po > =================================================================== > --- po/ca.po (revision 0) > +++ po/ca.po (revision 0) > @@ -0,0 +1,39 @@ > +# SOME DESCRIPTIVE TITLE. > +# Copyright (C) YEAR THE PACKAGE'S COPYRIGHT HOLDER > +# This file is distributed under the same license as the PACKAGE package. > +# FIRST AUTHOR <em...@address>, YEAR. > +# > +#, fuzzy > +msgid "" > +msgstr "" > +"Project-Id-Version: PACKAGE VERSION\n" > +"Report-Msgid-Bugs-To: \n" > +"POT-Creation-Date: 2009-01-21 21:14+0100\n" > +"PO-Revision-Date: YEAR-MO-DA HO:MI+ZONE\n" > +"Last-Translator: FULL NAME <em...@address>\n" > +"Language-Team: LANGUAGE <l...@li.org>\n" > +"MIME-Version: 1.0\n" > +"Content-Type: text/plain; charset=CHARSET\n" > +"Content-Transfer-Encoding: 8bit\n" > + > +#: normal/menu.c:90 > +#, c-format > +msgid "" > +"\n" > +" Use the %C and %C keys to select which entry is highlighted.\n" > +msgstr "" > +"\n" > +" Utilitzeu les tecles %C i %C per seleccionar l'entrada.\n" > + > +#: normal/menu.c:93 > +msgid "" > +" Press enter to boot the selected OS, 'e' to edit the\n" > +" commands before booting or 'c' for a command-line." > +msgstr "" > +" Presioneu retorn per arrancar el SO seleccionat, 'e' editar\n" > +" les comandes abans d'arrancar, 'c' per línia d'ordres." > + > +#: util/grub.d/10_linux.in:148 > +#, sh-format > +msgid "${OS}, linux ${version} (single-user mode)" > +msgstr "${OS}, linux ${version} (mode mono-usuari)" > Index: po/TODO > =================================================================== > --- po/TODO (revision 0) > +++ po/TODO (revision 0) > @@ -0,0 +1,5 @@ > +Prepare a Makefile.in to: > + > +-Compile all .po to .mo (msgfmt $LANG.po -o $LANG.mo) > +-Copy to /usr/share/locale/$LANG/LC_MESSAGES/grub.mo (or > /usr/local/share/locale/$LANG/LC_MESSAGES/..., so $prefix...) > +-Check that grub-gettext_lib.in is correct > Index: include/grub/misc.h > =================================================================== > --- include/grub/misc.h (revision 1954) > +++ include/grub/misc.h (working copy) > @@ -31,6 +31,8 @@ > /* XXX: If grub_memmove is too slow, we must implement grub_memcpy. */ > #define grub_memcpy(d,s,n) grub_memmove ((d), (s), (n)) > > +#define _(s) grub_gettext(s) > + > void *EXPORT_FUNC(grub_memmove) (void *dest, const void *src, grub_size_t n); > char *EXPORT_FUNC(grub_strcpy) (char *dest, const char *src); > char *EXPORT_FUNC(grub_strncpy) (char *dest, const char *src, int c); > @@ -84,6 +86,9 @@ > grub_uint64_t EXPORT_FUNC(grub_divmod64) (grub_uint64_t n, > grub_uint32_t d, grub_uint32_t *r); > > +const char *EXPORT_FUNC(grub_gettext_dummy) (const char *s); > +extern const char *(*EXPORT_VAR(grub_gettext)) (const char *s);// = > grub_gettext_dummy; > + > #ifdef NEED_ENABLE_EXECUTE_STACK > void EXPORT_FUNC(__enable_execute_stack) (void *addr); > #endif > Index: gettext/gettext.c > =================================================================== > --- gettext/gettext.c (revision 0) > +++ gettext/gettext.c (revision 0) > @@ -0,0 +1,300 @@ > +/* gettext.c - gettext module */ > +/* > + * GRUB -- GRand Unified Bootloader > + * Copyright (C) 2009 Free Software Foundation, Inc. > + * > + * GRUB is free software: you can redistribute it and/or modify > + * it under the terms of the GNU General Public License as published by > + * the Free Software Foundation, either version 3 of the License, or > + * (at your option) any later version. > + * > + * GRUB 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 General Public License for more details. > + * > + * You should have received a copy of the GNU General Public License > + * along with GRUB. If not, see <http://www.gnu.org/licenses/>. > + */ > + > +#include <grub/types.h> > +#include <grub/misc.h> > +#include <grub/mm.h> > +#include <grub/err.h> > +#include <grub/dl.h> > +#include <grub/normal.h> > +#include <grub/file.h> > +#include <grub/kernel.h> > + > +/* > + .mo file information from: > + http://www.gnu.org/software/autoconf/manual/gettext/MO-Files.html . > +*/ > + > + > +static grub_file_t grub_mofile_open (const char *name); > +static grub_file_t fd_mo; > + > +static int grub_gettext_offsetoriginal; > +static int grub_gettext_max; > + > +static const char* (*grub_gettext_original) (const char *s); > + > +#define GETTEXT_MAGIC_NUMBER 0 > +#define GETTEXT_FILE_FORMAT 4 > +#define GETTEXT_NUMBER_OF_STRINGS 8 > +#define GETTEXT_OFFSET_ORIGINAL 12 > +#define GETTEXT_OFFSET_TRANSLATION 16 > + > +static int > +grub_gettext_get_info (int offset) > +{ > + int buf; > + > + grub_file_seek (fd_mo, offset); > + grub_file_read (fd_mo, (char*) &buf, 4); > + return buf; > +} > + > +static void > +grub_gettext_getstring_from_offset (int offset, int length, char > *translation) > +{ > + grub_file_seek (fd_mo,offset); > + grub_file_read (fd_mo,translation,length); > + translation[length] = '\0'; > +} > + > +static char* > +grub_gettext_gettranslation_number (int i) > +{ > + int offsettranslation; > + int position; > + int length, offset; > + char *translation; > + > + offsettranslation = grub_gettext_get_info (GETTEXT_OFFSET_TRANSLATION); > + > + position=offsettranslation+i*8; > + > + grub_file_seek (fd_mo, position); > + grub_file_read (fd_mo, (char*) &length, 4); > + > + grub_file_seek (fd_mo, position + 4), > + grub_file_read (fd_mo, (char*) &offset, 4); > + > + translation = grub_malloc(length + 1); > + grub_gettext_getstring_from_offset (offset, length, translation); > + > + return translation; > +} > + > +static char* > +grub_gettext_getstring_num (int num) > +{ > + int position; > + int length, offset; > + char *original; > + > + /* Get position for string i. */ > + position = grub_gettext_offsetoriginal + (num * 8); > + > + /* Get the length of the string i. */ > + grub_file_seek (fd_mo, position); > + grub_file_read (fd_mo, (char *) &length, 4); > + > + /* Get the offset of the string i. */ > + grub_file_seek (fd_mo, position + 4); > + grub_file_read (fd_mo, (char *) &offset, 4); > + > + /* Get the string i. */ > + original = grub_malloc (length + 1); > + grub_gettext_getstring_from_offset (offset, length, original); > + > + return original; > +} > + > +static const char* > +grub_gettext_translate (const char *orig) > +{ > + char *current_string; > + char *ret; > + > + int min,max,current; > + > + if (fd_mo == 0) > + return orig; > + > + min = 0; > + max = grub_gettext_max; > + > + current = (max + min) / 2; > + > + while (current != min && current != max) > + { > + current_string = grub_gettext_getstring_num (current); > + /* grub_printf("Current: %s\n",current_string); */ > + > + /* Search by bissection. */ > + if (grub_strcmp (current_string, orig) < 0) > + { > + grub_free(current_string); > + min=current; > + } > + else if (grub_strcmp (current_string, orig) > 0) > + { > + grub_free(current_string); > + max=current; > + } > + else if (grub_strcmp (current_string, orig) == 0) > + { > + grub_free(current_string); > + return grub_gettext_gettranslation_number (current); > + } > + current = (max+min)/2; > + } > + > + ret = grub_malloc(grub_strlen(orig) + 1); > + grub_strcpy(ret,orig); > + return ret; > +} > + > +// XXX: Return a real grub_err_t or static void > +/*static grub_err_t > +grub_cmd_translate (struct grub_arg_list *state __attribute__ ((unused)), > + int argc __attribute__ ((unused)), > + char **args __attribute__ ((unused))) > +{ > + if (argc != 1) > + return grub_error (GRUB_ERR_BAD_ARGUMENT, "text to translate required"); > + > + char *translation; > + > + translation = grub_gettext_translate(args[0]); > + grub_printf("%s\n",translation); > + //grub_printf("grub__: %d\n",grub__); > + > + return 0; > +} > +*/ > + > +/* This is similar to grub_gzfile_open. */ > +static grub_file_t > +grub_mofile_open (const char *filename) > +{ > + int unsigned magic; > + int version; > + > + /* Using fd_mo and not another variable because > + it's needed for grub_gettext_get_info. */ > + > + fd_mo = grub_file_open (filename); > + if (! fd_mo) > + { > + grub_error (GRUB_ERR_FILE_READ_ERROR, "Cannot read %s",filename); > + return 0; > + } > + > + magic = grub_gettext_get_info (GETTEXT_MAGIC_NUMBER); > + > + if (magic != 0x950412de) > + { > + grub_error (GRUB_ERR_BAD_FILE_TYPE, "mo: invalid mo file: %s", > filename); > + grub_file_close (fd_mo); > + fd_mo = 0; > + return 0; > + } > + > + version = grub_gettext_get_info (GETTEXT_FILE_FORMAT); > + > + if (version != 0) > + { > + grub_error (GRUB_ERR_BAD_FILE_TYPE, "mo: invalid mo version in file: > %s", filename); > + fd_mo = 0; > + return 0; > + } > + > + /* > + Do we want .mo.gz files? Then, the code: > + file = grub_gzio_open (io, 0); // 0: transparent > + if (! file) > + { > + grub_printf("Problems opening the file\n"); > + grub_file_close (io); > + return 0; > + } > + */ > + > + return fd_mo; > +} > + > +static void > +grub_gettext_init_ext (const char *lang) > +{ > + char *mo_file; > + char *locale_prefix; > + > + locale_prefix = grub_env_get ("locale_prefix"); > + > + fd_mo = 0; > + > + // mo_file e.g.: /usr/share/locale/ca/LC_MESSAGES/grub.mo > + > + mo_file = grub_malloc (grub_strlen (locale_prefix) + sizeof ("/") + > grub_strlen (lang) + sizeof ("/LC_MESSAGES/grub.mo")); > + > + if (! mo_file) > + return; > + > + grub_sprintf (mo_file, "%s/%s/LC_MESSAGES/grub.mo", locale_prefix, lang); > + /* XXX: lang is written by the user, need to sanitaze the input? */ > + > + fd_mo = grub_mofile_open(mo_file); > + grub_free (mo_file); > + > + if (fd_mo) > + { > + grub_gettext_offsetoriginal = > grub_gettext_get_info(GETTEXT_OFFSET_ORIGINAL); > + grub_gettext_max = grub_gettext_get_info(GETTEXT_NUMBER_OF_STRINGS); > + > + grub_gettext_original = grub_gettext; > + grub_gettext = grub_gettext_translate; > + } > +} > + > +static char* > +grub_gettext_env_write_lang (struct grub_env_var *var __attribute__ > ((unused)), > + const char *val) > +{ > + grub_gettext_init_ext (val); > + > + return grub_strdup (val); > +} > + > +GRUB_MOD_INIT(gettext) > +{ > + (void)mod; /* To stop warning. */ > + > + const char *lang; > + > + lang = grub_env_get ("lang"); > + > + grub_gettext_init_ext (lang); > + > + /* Testing: > + grub_register_command ("_", grub_cmd_translate, GRUB_COMMAND_FLAG_BOTH, > + "_", "internalization support trans", 0); > + */ > + > + /* Reload .mo file information if lang changes. */ > + grub_register_variable_hook ("lang", NULL, grub_gettext_env_write_lang); > + > + /* Preserve hooks after context changes. */ > + grub_env_export ("lang"); > +} > + > +GRUB_MOD_FINI(gettext) > +{ > + if (fd_mo != 0) > + grub_file_close(fd_mo); > + > + grub_gettext = grub_gettext_original; > +} > Index: normal/menu.c > =================================================================== > --- normal/menu.c (revision 1954) > +++ normal/menu.c (working copy) > @@ -87,12 +87,12 @@ > } > else > { > - grub_printf ("\n\ > - Use the %C and %C keys to select which entry is highlighted.\n", > + grub_printf (_("\n\ > + Use the %C and %C keys to select which entry is highlighted.\n"), > (grub_uint32_t) GRUB_TERM_DISP_UP, (grub_uint32_t) > GRUB_TERM_DISP_DOWN); > - grub_printf ("\ > + grub_printf (_("\ > Press enter to boot the selected OS, \'e\' to edit the\n\ > - commands before booting or \'c\' for a command-line."); > + commands before booting or \'c\' for a command-line.")); > if (nested) > grub_printf ("\n\ > ESC to return previous menu."); > Index: util/grub.d/10_linux.in > =================================================================== > --- util/grub.d/10_linux.in (revision 1954) > +++ util/grub.d/10_linux.in (working copy) > @@ -20,6 +20,7 @@ > exec_pref...@exec_prefix@ > libd...@libdir@ > . ${libdir}/grub/grub-mkconfig_lib > +. ${libdir}/grub/grub-gettext_lib > > if [ "x${GRUB_DISTRIBUTOR}" = "x" ] ; then > OS=GNU/Linux > @@ -139,7 +140,7 @@ > EOF > > cat << EOF > -menuentry "${OS}, linux ${version} (single-user mode)" { > +menuentry "$(eval_gettext '${OS}, linux ${version} (single-user mode)')" { > EOF > prepare_grub_to_access_device ${GRUB_DEVICE_BOOT} | sed -e "s/^/\t/" > cat << EOF > Index: util/grub.d/00_header.in > =================================================================== > --- util/grub.d/00_header.in (revision 1954) > +++ util/grub.d/00_header.in (working copy) > @@ -22,6 +22,7 @@ > exec_pref...@exec_prefix@ > libd...@libdir@ > grub_prefix=`echo /boot/grub | sed ${transform}` > +locale_prefix="/usr/share/locale" # TODO: dynamic with exec_prefix ? > > . ${libdir}/grub/grub-mkconfig_lib > > @@ -112,3 +113,18 @@ > EOF > ;; > esac > + > +if test -e ${grub_prefix}/gettext.mod ; then > + # Make the locales accesible > + prepare_grub_to_access_device `${grub_probe} --target=device > ${locale_prefix}` > + lang=`get_locale_lang` > + cat << EOF > +if `make_system_path_relative_to_its_root ${locale_prefix}` ; then > + set locale_prefix=${locale_prefix} > + set lang=${lang} > + insmod gettext > +fi > +EOF > +else > + echo "gettext module is not available" > +fi > Index: util/grub-mkconfig_lib.in > =================================================================== > --- util/grub-mkconfig_lib.in (revision 1954) > +++ util/grub-mkconfig_lib.in (working copy) > @@ -176,3 +176,14 @@ > fi > return 0 > } > + > +get_locale_lang () > +{ > + lang="`echo ${LANG} | cut -d _ -f 1`" > + if [ "x${lang}" = "x" ] ; then > + return 1 > + else > + echo "${lang}" > + return 0 > + fi > +} > Index: util/grub-gettext_lib.in > =================================================================== > --- util/grub-gettext_lib.in (revision 0) > +++ util/grub-gettext_lib.in (revision 0) > @@ -0,0 +1,23 @@ > +# Configuration of grub-gettext > +# Copyright (C) 2009 Free Software Foundation, Inc. > +# > +# GRUB is free software: you can redistribute it and/or modify > +# it under the terms of the GNU General Public License as published by > +# the Free Software Foundation, either version 3 of the License, or > +# (at your option) any later version. > +# > +# GRUB 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 General Public License for more details. > +# > +# You should have received a copy of the GNU General Public License > +# along with GRUB. If not, see <http://www.gnu.org/licenses/>. > + > +pref...@prefix@ > +exec_pref...@exec_prefix@ > +libd...@libdir@ > + > +textdomaind...@prefix@/share/locale > +TEXTDOMAIN=grub > +. gettext.sh > > Property changes on: util/grub-gettext_lib.in > ___________________________________________________________________ > Added: svn:mergeinfo > > _______________________________________________ > Grub-devel mailing list > Grub-devel@gnu.org > http://lists.gnu.org/mailman/listinfo/grub-devel -- Carles Pina i Estany GPG id: 0x17756391 http://pinux.info _______________________________________________ Grub-devel mailing list Grub-devel@gnu.org http://lists.gnu.org/mailman/listinfo/grub-devel