View Single Post
Posts: 838 | Thanked: 3,384 times | Joined on Mar 2009
#1
This post is about updating glibc (libc6) on Maemo5.

Stock Maemo5 has quite old eglibc-2.5.1 (2008-04-16).

glibc HISTORY:
Code:
2.3  - 2002-10-03
2.4  - 2006-03-06
2.5  - 2006-09-29
2.6  - 2007-05-15
2.7  - 2007-10-18
2.8  - 2008-04-12
2.9  - 2008-11-13
2.10 - 2009-05-09
2.11 - 2009-10-30
2.12 - 2010-05-03
2.13 - 2011-01-17
2.14 - 2011-05-31
2.15 - 2011-12-23 ... 2012-03-21
2.16 - 2012-06-30
2.17 - 2012-12-25
GOALS:
1) get it compiled
2) get it booted and running
3) optimize for N900


INVESTIGATING
I have tried to track origin of Maemo's eglibc and closest match is svn-2784 on eglibc-branch-2.5.
Code:
#sources of Maemo5 libc6
apt-get source libc6

#sources from upstream
svn checkout svn://svn.eglibc.org/branches/eglibc-2_5/ -r 2784 svn_eglibc-2.5_r2784

cd svn_eglibc-2.5_r2784
find ./ -name ".svn" | xargs rm -Rf
cd ..

tar xf glibc-2.5.1/glibc-2.5.tar.bz2
diff -Naur glibc-2.5/ svn_eglibc-2.5_r2784/libc/ | cat -n
#242 rows (where half of them are changelog)

diff -Naur linuxthreads svn_eglibc-2.5_r2784/linuxthreads/linuxthreads | cat -n
#115 rows

tar xf glibc-2.5.1/glibc-linuxthreads-2.5.tar.bz2
diff -Naur linuxthreads_db/ svn_eglibc-2.5_r2784/linuxthreads/linuxthreads_db/ | cat -n
#exactly same

tar xf glibc-2.5.1/glibc-ports-2007q3.tar.bz2
diff -Naur ports/ svn_eglibc-2.5_r2784/ports/ | cat -n
#977 rows (some 200 are about arm)

#Maemo source also contains tarred libidn, but it is already unpacked
tar xf glibc-2.5.1/glibc-libidn-2.5.tar.bz2
diff -Naur libidn/ glibc-2.5/libidn/
Then I figured out that patches added during packeting are almost useless, only arm-asm-page-header.diff is needed to get it compiled and running.


STEP1:
Starting with stock maemo SDK, i.e gcc-4.2.

Compile latest eglibc-2.5 from svn without Maemo-patches, but using very same packeting:

Code:
svn co svn://svn.eglibc.org/branches/eglibc-2_5 svn_eglibc-2.5
cd svn_eglibc-2.5
find ./ -name ".svn" | xargs rm -Rf

mv libc/ glibc-2.5
tar cjf ../glibc-2.5.tar.bz2 glibc-2.5

cd linuxthreads
tar cjf ../../glibc-linuxthreads-2.5.tar.bz2 linuxthreads  linuxthreads_db
cd ..

tar cjf ../glibc-ports-2007q3.tar.bz2 ports/

cd ..
rm -rf svn_eglibc-2.5

cp -r glibc-2.5.1/debian/ glibc-2.5.1/prep.sh svn_eglibc-2.5
#use only this patch
echo "arm-asm-page-header.diff" > svn_eglibc-2.5/debian/patches/00-list.armel

cd glibc-2.5.1
fakeroot dpkg-buildpackage
-> working package. Tested with fresh flashed device.


STEP2
Compile newer eglibc from upstream.

Fastest way to test them are just skip version numbering and use same commands as above but starting with:
svn co svn://svn.eglibc.org/branches/eglibc-2_6 svn_eglibc-2.5
-> works.

svn co svn://svn.eglibc.org/branches/eglibc-2_7 svn_eglibc-2.5
-> works

svn co svn://svn.eglibc.org/branches/eglibc-2_8 svn_eglibc-2.5
no need for "arm-asm-page-header.diff" anymore
-> works

svn co svn://svn.eglibc.org/branches/eglibc-2_10 svn_eglibc-2.5
-> works


svn co svn://svn.eglibc.org/branches/eglibc-2_11 -r 8593 svn_eglibc-2.11_8593
#version 2.10.90.
-> works

NOTE: 'ldd' with this version and later needs bash!

This is the end of this approach: later commits have new file ports/sysdeps/arm/eabi/backtrace.c which causes linking error:
backtrace.c:105: undefined reference to `_Unwind_Backtrace'

I'm pretty sure this is because of too old GCC (because it happens even I use newer binutils)


(Btw: even this will be workarounded, eglibc-2.12 fails, because it needs CFI support:
checking whether the CFI directive .cfi_sections is supported... no
configure: error: need .cfi_sections in this configuration

CFI stands for Call Frame Information and is a GNU AS extension to manage call frames.
http://www.logix.cz/michal/devel/gas-cfi/ I don't know is this used, but at least it is checked and failed.)

Here is the deb, I have tested it just reflashed N900 and didn't encounter any issues.
http://cc.oulu.fi/~rantalai/maemo5/e...emo1_armel.deb

STEP3
Use newer compiler: gcc-4.7.2 (and binutils-2.22)

Upstream versions between 2.5 ... 2.15 need one patch and then they can be compiled:
http://cc.oulu.fi/~rantalai/maemo5/e...ctor-nscd.diff

There are problem that locales might break: Every text on the screen looks like: "wdgt_va_24h_time"
(nothing helps from here: http://talk.maemo.org/showthread.php?t=52443)

This is tested way to get eglibc-2.10.90 compiled with gcc-4.7 fully working (including working locales).
You do not need thumb-support, but you need libstdc++6_4.7.2 and libgcc1_4.7.2 installed.

Code:
#FLASH (flasher-3.5 -f -R -F RX-51_2009SE_20.2010.36-2_PR_COMBINED_MR0_ARM.bin)
# (no rd-mode, just press continue on startup-wizard)
#enable wlan
#with hildon-application-manager: install openssh-server 
#continue over ssh:
apt-get install wget binutils bash
apt-get remove mp-fremantle-generic-pr
wget http://maemo.merlin1991.at/cssu/develdebs/gcc-4.7.2_fremantle_armel/packages/libstdc%2b%2b6_4.7.2-0%2bcssu0_armel.deb
wget http://maemo.merlin1991.at/cssu/develdebs/gcc-4.7.2_fremantle_armel/packages/libgcc1_4.7.2-0%2bcssu0_armel.deb
dpkg -i libgcc1_4.7.2-0+cssu0_armel.deb     libstdc++6_4.7.2-0+cssu0_armel.deb

#I'm pretty sure this is needed step.
mkdir 42 ; cd 42
wget http://cc.oulu.fi/~rantalai/maemo5/eglibc/2.10/with_gcc42_deb/libc6_2.10.90-maemo1_armel.deb
cd ..
dpkg -i 42/libc6_2.10.90-maemo1_armel.deb


mkdir 47 ; cd 47
wget http://cc.oulu.fi/~rantalai/maemo5/eglibc/2.10/with_gcc47_deb/libc6_2.10.90-maemo1_armel.deb
cd ..
dpkg -i 47/libc6_2.10.90-maemo1_armel.deb


reboot
#locale works


STEP4
Latest eglibc I could compiled so far is 2.16_r17194, version number 2.15.90. Next commit, svn-r17195, starts to complain about:
intl/dcigettext.c:714: undefined reference to `__libc_enable_secure'
elf/dl-addr.c:36: undefined reference to `_rtld_global'
(these are defined, but it fails to link them)
Commit message is "Merge changes between r17050 and r17194 from /fsf/trunk."


But locales are broken. Investigating from commandline: command locale gives three errors before shows current locale:

Code:
locale
locale: Cannot set LC_CTYPE to default locale: No such file or directory
locale: Cannot set LC_MESSAGES to default locale: No such file or directory
locale: Cannot set LC_COLLATE to default locale: No such file or directory
With 2.10.90 (one) workaround was first install very same version compiled older gcc, but now this is not an option.


STEP4b:
Take smaller steps. eglibc-2.11.0 (svn_r9170) with gcc-4.7 upgrading from 2.10.90.
-> locales are broken, this time only:
locale: Cannot set LC_CTYPE to default locale: No such file or directory
locale: Cannot set LC_ALL to default locale: No such file or directory

Stracing shows:
Code:
Nokia-N900:~# strace locale
execve("/usr/bin/locale", ["locale"], [/* 63 vars */]) = 0
brk(0)                                  = 0x18000
uname({sys="Linux", node="Nokia-N900", ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x4001d000
access("/etc/ld.so.preload", R_OK)      = -1 ENOENT (No such file or directory)
open("/etc/ld.so.cache", O_RDONLY)      = 3
fstat64(3, {st_mode=S_IFREG|0644, st_size=37968, ...}) = 0
mmap2(NULL, 37968, PROT_READ, MAP_PRIVATE, 3, 0) = 0x40026000
close(3)                                = 0
open("/lib/libc.so.6", O_RDONLY)        = 3
read(3, "\177ELF\1\1\1\0\0\0\0\0\0\0\0\0\3\0(\0\1\0\0\0\310o\1\0004\0\0\0"..., 512) = 512
fstat64(3, {st_mode=S_IFREG|0755, st_size=1167548, ...}) = 0
mmap2(NULL, 1209588, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x40030000
mprotect(0x4014a000, 32768, PROT_NONE)  = 0
mmap2(0x40152000, 12288, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x11a) = 0x40152000
mmap2(0x40155000, 9460, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x40155000
close(3)                                = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x4001e000
set_tls(0x4001e110, 0x4001e7e8, 0x40025050, 0x4001e110, 0x40025050) = 0
mprotect(0x40152000, 8192, PROT_READ)   = 0
mprotect(0x15000, 4096, PROT_READ)      = 0
mprotect(0x40024000, 4096, PROT_READ)   = 0
munmap(0x40026000, 37968)               = 0
open("/usr/lib/locale/locale-archive", O_RDONLY|O_LARGEFILE) = 3
fstat64(3, {st_mode=S_IFREG|0644, st_size=23911920, ...}) = 0
mmap2(NULL, 2097152, PROT_READ, MAP_PRIVATE, 3, 0) = 0x40158000
close(3)                                = 0
brk(0)                                  = 0x18000
brk(0x39000)                            = 0x39000
open("/usr/share/locale/locale.alias", O_RDONLY) = -1 ENOENT (No such file or directory)
open("/usr/lib/locale/en_GB/LC_CTYPE", O_RDONLY) = -1 ENOENT (No such file or directory)
open("/usr/lib/locale/en/LC_CTYPE", O_RDONLY) = -1 ENOENT (No such file or directory)
write(2, "locale: ", 8locale: )                 = 8
write(2, "Cannot set LC_CTYPE to default l"..., 37Cannot set LC_CTYPE to default locale) = 37
write(2, ": No such file or directory", 27: No such file or directory) = 27
write(2, "\n", 1
)                       = 1
open("/usr/share/locale/en_GB/LC_MESSAGES/libc.mo", O_RDONLY) = -1 ENOENT (No such file or directory)
open("/usr/share/locale/en/LC_MESSAGES/libc.mo", O_RDONLY) = -1 ENOENT (No such file or directory)
write(2, "locale: ", 8locale: )                 = 8
write(2, "Cannot set LC_ALL to default loc"..., 35Cannot set LC_ALL to default locale) = 35
write(2, ": No such file or directory", 27: No such file or directory) = 27
write(2, "\n", 1
)                       = 1
fstat64(1, {st_mode=S_IFCHR|0600, st_rdev=makedev(136, 0), ...}) = 0
mmap2(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x4001f000
write(1, "LANG=en_GB\n", 11LANG=en_GB
)            = 11
write(1, "LC_CTYPE=\"en_GB\"\n", 17LC_CTYPE="en_GB"
)    = 17
write(1, "LC_NUMERIC=en_GB\n", 17LC_NUMERIC=en_GB
)      = 17
write(1, "LC_TIME=en_GB\n", 14LC_TIME=en_GB
)         = 14
write(1, "LC_COLLATE=\"en_GB\"\n", 19LC_COLLATE="en_GB"
)  = 19
write(1, "LC_MONETARY=en_GB\n", 18LC_MONETARY=en_GB
)     = 18
write(1, "LC_MESSAGES=en_GB\n", 18LC_MESSAGES=en_GB
)     = 18
write(1, "LC_PAPER=en_GB\n", 15LC_PAPER=en_GB
)        = 15
write(1, "LC_NAME=en_GB\n", 14LC_NAME=en_GB
)         = 14
write(1, "LC_ADDRESS=en_GB\n", 17LC_ADDRESS=en_GB
)      = 17
write(1, "LC_TELEPHONE=en_GB\n", 19LC_TELEPHONE=en_GB
)    = 19
write(1, "LC_MEASUREMENT=en_GB\n", 21LC_MEASUREMENT=en_GB
)  = 21
write(1, "LC_IDENTIFICATION=en_GB\n", 24LC_IDENTIFICATION=en_GB
) = 24
write(1, "LC_ALL=\n", 8LC_ALL=
)                = 8
exit_group(0)                           = ?
Attached Images
 
 

The Following 33 Users Say Thank You to AapoRantalainen For This Useful Post: