Hello everyone, I'd like to present a draft of install script of new generic i18n module.
~ Abstract ~
Different distros have variables holding keyboard settings, fonts and so
in different files and even under different names. Sometimes it's
“SYSFONT” in /etc/sysconfig/i18n, sometimes it's “consolefont” in
/etc/conf.d/consolefont. I came up with idea to hold mappings in
configuration file (dracut.conf or dracut.conf.d/«distro».conf). The
script gathers variables and prepares two “unified” files inside
Dracut overlay.
The rest of the script is quite the same as redhat-i18n but some tweaks.
Dracut uses console_init written in C included in initscripts RPM, but
I'm gonna rewrite it in bash and then i18n module will be fully generic.
Please post here any doubts, questions, suggestions, insults… ;-)
Cheers,
Amadeusz Żołnowski
PS. What do you think about moving inst_decompress, mksubdirs into
dracut-functions?
--
#!/bin/bash
# WE EXPECT FOLLOWING VARS
#
# ~ Keyboard ~
# KEYMAP
# UNIKEYMAP
# GRP_TOGGLE
# EXT_KEYMAPS
#
# ~ i18n ~
# UNICODE
# SYSFONT
# CONTRANS
# UNIMAP
#
# ~ Locales ~
# LANG
# LC_*
#
#
# SAMPLE MAPPINGS
#
# ~ Fedora ~
# Keyboard: /etc/sysconfig/keyboard:KEYTABLE-KEYMAP
# i18n: /etc/sysconfig/i18n:SYSFONT,SYSFONTACM-CONTRANS,UNIMAP
#
# ~ Gentoo Base 1.0 ~
# Keyboard: /etc/conf.d/keymaps:KEYMAP,EXTENDED_KEYMAPS-EXT_KEYMAPS
# i18n: /etc/conf.d/consolefont:CONSOLEFONT-SYSFONT,CONSOLETRANSLATION-CONTRANS
/etc/rc.conf:UNICODE
#
# ~ Gentoo Base 2.0 ~
# Keyboard: /etc/conf.d/keymaps:keymap-KEYMAP,extended_keymaps-EXT_KEYMAPS
# i18n: /etc/conf.d/consolefont:consolefont-SYSFONT,consoletranslation-CONTRANS
/etc/rc.conf:unicode-UNICODE
KBDSUBDIRS=consolefonts,consoletrans,keymaps,unimaps
DEFAULT_SYSFONT=LatArCyrHeb-16
# Create all subdirectories for given path without creating the last element.
# $1 = path
mksubdirs() { mkdir -p ${1%/*}; }
# install function decompressing the target and handling symlinks
# $@ = list of compressed (gz or bz2) files or symlinks pointing to such files
#
# Function install targets in the same paths inside overlay but decompressed
# and without extensions (.gz, .bz2).
inst_decompress() {
local src dst realsrc realdst cmd
for src in $@
do
case ${src} in
*.gz) cmd='gzip -d' ;;
*.bz2) cmd='bzip2 -d' ;;
*) return 1 ;;
esac
if [[ -L ${src} ]]
then
realsrc="$(readlink -f ${src})" # symlink target with extension
dst="${src%.*}" # symlink without extension
realdst="${realsrc%.*}" # symlink target without extension
mksubdirs "${initdir}/${src}"
# Create symlink without extension to target without extension.
ln -s "${realdst}" "${initdir}/${dst}"
fi
# If the source is symlink we operate on its target.
[[ ${realsrc} ]] && src=${realsrc}
inst ${src}
# Decompress with chosen tool. We assume that tool changes name e.g.
# from 'name.gz' to 'name'.
${cmd} "${initdir}${src}"
done
}
# This is from 10redhat-i18n, not touched.
findkeymap () {
local MAP=$1
[[ ! -f $MAP ]] && \
MAP=$(find ${kbddir}/keymaps -type f -name $MAP -o -name $MAP.\* | head -n1)
[[ " $KEYMAPS " = *" $MAP "* ]] && return
KEYMAPS="$KEYMAPS $MAP"
case $MAP in
*.gz) cmd=zgrep;;
*.bz2) cmd=bzgrep;;
*) cmd=grep ;;
esac
for INCL in $($cmd "^include " $MAP | cut -d' ' -f2 | tr -d '"'); do
for FN in $(find ${kbddir}/keymaps -type f -name $INCL\*); do
findkeymap $FN
done
done
}
# Function gathers variables from distributed files among the tree, maps to
# specified names and prints the result in format "new-name=value".
#
# $@ = list in format specified below (BNF notation)
#
# <list> ::= <element> | <element> " " <list>
# <element> ::= <conf-file-name> ":" <map-list>
# <map-list> ::= <mapping> | <mapping> "," <map-list>
# <mapping> ::= <src-var> "-" <dst-var> | <src-var>
#
# We assume no whitespace are allowed between symbols.
# <conf-file-name> is a file holding <src-var> in your system.
# <src-var> is a variable holding value of meaning the same as <dst-var>.
# <dst-var> is a variable which will be set up inside initramfs.
# If <dst-var> has the same name as <src-var> we can omit <dst-var>.
#
# Hope it's clear. ;-)
#
# Example:
# /etc/conf.d/keymaps:KEYMAP,extended_keymaps-EXT_KEYMAPS
# <list> = /etc/conf.d/keymaps:KEYMAP,extended_keymaps-EXT_KEYMAPS
# <element> = /etc/conf.d/keymaps:KEYMAP,extended_keymaps-EXT_KEYMAPS
# <conf-file-name> = /etc/conf.d/keymaps
# <map-list> = KEYMAP,extended_keymaps-EXT_KEYMAPS
# <mapping> = KEYMAP
# <src-var> = KEYMAP
# <mapping> = extended_keymaps-EXT_KEYMAPS
# <src-var> = extended_keymaps
# <dst-var> = EXT_KEYMAPS
gather_vars() {
local item map value
for item in $@
do
item=(${item/:/ })
for map in ${item[1]/,/ }
do
map=(${map/-/ })
value=$(grep "^${map[0]}=" "${item[0]}")
value=${value#*=}
echo "${map[1]:-${map[0]}}=${value}"
done
done
}
# Function prints global variables in format name=value line by line.
# $@ = list of global variables' name
print_vars() {
local var value
for var in $@
do
value=$(eval echo \$$var)
[[ ${value} ]] && echo "${var}=\"${value}\""
done
}
install_items() {
dracut_install setfont loadkeys
inst ${moddir}/console_init /lib/udev/console_init
inst_rules ${moddir}/10-console.rules
}
install_all_kbd() {
local rel f
for f in $(eval find ${kbddir}/{${KBDSUBDIRS}} -type f -print)
do
rel=${f#${kbddir}}
rel=${rel#/}
inst "$f" "/lib/kbd/${rel}"
done
# remove unnecessary files
rm -f "${initdir}${kbddir}/consoletrans/utflist"
find "${initdir}${kbddir}/" -name README\* -delete
dracut_install gzip bzip2
}
install_local_keyboard() {
local keyboard_conf="${initdir}/etc/sysconfig/keyboard"
local map
eval $(gather_vars ${keyboard_vars})
# Gentoo user may have KEYMAP set to something like "-u pl2",
KEYMAP=${KEYMAP#-* }
EXT_KEYMAPS=${EXT_KEYMAPS:-backspace}
# I'm not sure of the purpose of UNIKEYMAP and GRP_TOGGLE. They were in
# original redhat-i18n module. Anyway it won't hurt.
EXT_KEYMAPS+=\ ${UNIKEYMAP}\ ${GRP_TOGGLE}
[[ ${KEYMAP} ]] || derror 'No KEYMAP.' || return 1
findkeymap ${KEYMAP}
for map in ${EXT_KEYMAPS}
do
dinfo "Adding bonus map: ${map}"
findkeymap ${map}
done
inst_decompress ${KEYMAPS}
mksubdirs ${keyboard_conf}
print_vars KEYMAP EXT_KEYMAPS > ${keyboard_conf}
}
install_local_i18n() {
local i18n_conf="${initdir}/etc/sysconfig/i18n"
eval $(gather_vars ${i18n_vars})
[[ ${SYSFONT} ]] || SYSFONT=${DEFAULT_SYSFONT}
inst_decompress ${kbddir}/consolefonts/${SYSFONT}*
if [[ ${CONTRANS} ]]
then
CONTRANS=${CONTRANS%.trans}
inst ${kbddir}/consoletrans/${CONTRANS}.trans
fi
if [[ ${UNIMAP} ]]
then
UNIMAP=${UNIMAP%.uni}
inst ${kbddir}/unimaps/${UNIMAP}.uni
fi
if [[ ${UNICODE} ]]
then
if [[ ${UNICODE^^} = YES || ${UNICODE} = 1 ]]
then
UNICODE=1
elif [[ ${UNICODE^^} = NO || ${UNICODE} = 0 ]]
then
UNICODE=0
else
UNICODE=''
fi
fi
if [[ ! ${UNICODE} && ${LANG^^} =~ .*\.UTF-?8 ]]
then
UNICODE=1
fi
mksubdirs ${i18n_conf}
print_vars UNICODE SYSFONT CONTRANS UNIMAP > ${i18n_conf}
}
for kbddir in /usr/lib/kbd /lib/kbd /usr/share
do
[[ -d "${kbddir}" ]] && \
for dir in ${KBDSUBDIRS//,/ }
do
[[ -d "${kbddir}/${dir}" ]] && continue
false
done || kbddir=''
done
[[ ${kbddir} ]] || {
derror "Directories ${KBDSUBDIRS//,/, } not found. Please inform us about
the issue including your OS name and version."
exit 1
}
# Testing
keyboard_vars=/etc/conf.d/keymaps:KEYMAP,EXTENDED_KEYMAPS-EXT_KEYMAPS
i18n_vars=/etc/conf.d/consolefont:CONSOLEFONT-SYSFONT,CONSOLETRANSLATION-CONTRANS\
/etc/rc.conf:UNICODE
install_items
if [[ ${hostonly} ]]
then
install_local_keyboard
install_local_i18n
else
install_all_kbd
fi
signature.asc
Description: PGP signature
