Page MenuHomeFreeBSD

namei: Reset the lookup to start from the real root for abs symlink target
ClosedPublic

Authored by dchagin on Jun 9 2023, 6:52 PM.
Tags
None
Referenced Files
Unknown Object (File)
Mar 14 2024, 6:00 AM
Unknown Object (File)
Mar 14 2024, 6:00 AM
Unknown Object (File)
Mar 14 2024, 5:59 AM
Unknown Object (File)
Mar 14 2024, 5:59 AM
Unknown Object (File)
Mar 14 2024, 5:45 AM
Unknown Object (File)
Dec 31 2023, 10:13 PM
Unknown Object (File)
Dec 31 2023, 10:10 PM
Unknown Object (File)
Dec 31 2023, 10:09 PM

Details

Summary

Since fd745e1d Linux ABI specify's alternative root directory to reroot lookups.
First, an attempt is made to lookup the file in /ABI/original-path. If that
fails, the lookup is done in /original-path. In case of lookup symbolic link
with leading / in target namei() fails due to reroot reloads original file name.

Reported by: Goran Mekić, Vincent Milum Jr
Tested by: Goran Mekić

Diff Detail

Repository
rG FreeBSD src repository
Lint
Lint Not Applicable
Unit
Tests Not Applicable

Event Timeline

Does this work?

This is somehow reverse of what I proposed. I mean, if we met an abs-targeting symlink and ISRESTARTED is already set, then clear IRESTARTED and use the real root. Otherwise you do not get to the non-ABI namespace.

I tested this out, but it did not solve the font rendering issue that I was facing.

In D40479#921702, @kib wrote:

Does this work?

well, I wrote this before and waited until Goran test patch on a real application (Slack). It works for him and for me (fc-list).

This is somehow reverse of what I proposed. I mean, if we met an abs-targeting symlink and ISRESTARTED is already set, then clear IRESTARTED and use the real root. Otherwise you do not get to the non-ABI namespace.

Let’s synchronize ISRESTARTED meaning. Correct me please if Im wrong:

At first, lookup starts from the compat root (ni_rootdir set to pwd_adir), ISRESTARTED is not set, if lookup fails, we restart - reload origin-path, set ni_rootdir to pwd_rdir and set ISRESTARTED to prevent further restarts.

In our case /etc/fonts resolved by namei_follow_link() to /usr/local/etc/fonts, then namei_handle_root() due to leading / in target set dp to compat root again and vfs_lookup() tries to lookup /compat/linux/usr/local/etc/fonts, fails and only then restart from begin, i.e., set ISRESTARTED and reloads origin-path (/etc/fonts) and fails.

In my POV, if we successfully resolved / targeted symlink in the first attempt (compat root is set, ISRESTARTED not) we should prevent origin-path reloading.

PS. do we need to reload origin-path on restart? Or reset cn_nameptr to cn_pnbuf is enough?

I tested this out, but it did not solve the font rendering issue that I was facing.

dchagin@mordor:~/freebsd % sudo sysctl compat.linux.emul_path
compat.linux.emul_path: /compat/linux
dchagin@mordor:~/freebsd %
dchagin@mordor:~/freebsd % sudo ls -l /compat/linux/etc | grep fonts
lrwxr-xr-x 1 root wheel 20 1 апр. 2021 fonts -> /usr/local/etc/fonts
dchagin@mordor:~/freebsd %
dchagin@mordor:~/freebsd % sudo /compat/linux/usr/bin/fc-list | grep Zemen
/usr/local/share/fonts/TTF/GohaTibebZemen.ttf: Goha\-Tibeb Zemen:style=Regular
/usr/local/share/fonts/OTF/GohaTibebZemen.otf: Goha\-Tibeb Zemen:style=Regular
dchagin@mordor:~/freebsd %
dchagin@mordor:~/freebsd % sudo ls -l /compat/linux/etc/fonts/
total 56
drwxr-xr-x 2 root wheel 3584 26 февр. 17:32 conf.avail
drwxr-xr-x 2 root wheel 2048 26 февр. 17:32 conf.d
-rw-r--r-- 1 root wheel 2668 23 февр. 04:31 fonts.conf
-rw-r--r-- 1 root wheel 2668 23 февр. 04:31 fonts.conf.sample
-rw-r--r-- 1 root wheel 8254 3 дек. 2020 fonts.dtd
dchagin@mordor:~/freebsd %

I repeat, without a trace, I can't guess what's going on. So, please send a ktrace/kdump log

In D40479#921702, @kib wrote:

Does this work?

well, I wrote this before and waited until Goran test patch on a real application (Slack). It works for him and for me (fc-list).

This is somehow reverse of what I proposed. I mean, if we met an abs-targeting symlink and ISRESTARTED is already set, then clear IRESTARTED and use the real root. Otherwise you do not get to the non-ABI namespace.

Let’s synchronize ISRESTARTED meaning. Correct me please if Im wrong:

At first, lookup starts from the compat root (ni_rootdir set to pwd_adir), ISRESTARTED is not set, if lookup fails, we restart - reload origin-path, set ni_rootdir to pwd_rdir and set ISRESTARTED to prevent further restarts.

In our case /etc/fonts resolved by namei_follow_link() to /usr/local/etc/fonts, then namei_handle_root() due to leading / in target set dp to compat root again and vfs_lookup() tries to lookup /compat/linux/usr/local/etc/fonts, fails and only then restart from begin, i.e., set ISRESTARTED and reloads origin-path (/etc/fonts) and fails.

In my POV, if we successfully resolved / targeted symlink in the first attempt (compat root is set, ISRESTARTED not) we should prevent origin-path reloading.

Hm, ok. Perhaps some more words along what you wrote there, should be added as a comment explaining IRESTARTED somewhere.

PS. do we need to reload origin-path on restart? Or reset cn_nameptr to cn_pnbuf is enough?

ATM I believe nameptr is enough (or even more, reloading origin-path would cause some failures).

Fix comment, vrele(dp) after ni_rootdir check

This revision is now accepted and ready to land.Jun 12 2023, 10:56 PM

This still doesn't fix the issue.

I downloaded the latest FreeBSD 14.0-CURRENT ISO image, performed a fresh install, and did the following:

sysrc linux_enable="YES"
service linux start
pkg install fontconfig linux-c7-fontconfig font-adobe-75dpi

And then I tested with

fc-list
/compat/linux/usr/bin/fc-list

The FreeBSD binary worked, the Linux binary still has the same "not found" error attempting to locate the config file.

I repeat, without a trace, I can't guess what's going on. So, please send a ktrace/kdump log

https://vincerants.com/public/ktrace.out

This still doesn't fix the issue.

I downloaded the latest FreeBSD 14.0-CURRENT ISO image, performed a fresh install, and did the following:

sysrc linux_enable="YES"
service linux start
pkg install fontconfig linux-c7-fontconfig font-adobe-75dpi

And then I tested with

fc-list
/compat/linux/usr/bin/fc-list

The FreeBSD binary worked, the Linux binary still has the same "not found" error attempting to locate the config file.

I repeat, without a trace, I can't guess what's going on. So, please send a ktrace/kdump log

https://vincerants.com/public/ktrace.out

This is how the trace looks like at me:

65810 100946 fc-list 0.000180267 CALL L64 linux_access(0x604b90,0x4<R_OK>)
65810 100946 fc-list 0.000020656 NAMI L64 "/etc/fonts/fonts.conf"
65810 100946 fc-list 0.000095482 RET L64 linux_access 0

65810 100946 fc-list 0.000045686 CALL L64 linux_access(0x604bb0,0x4<R_OK>)
65810 100946 fc-list 0.000018685 NAMI L64 "/etc/fonts/fonts.conf"
65810 100946 fc-list 0.000049243 RET L64 linux_access 0
65810 100946 fc-list 0.000020232 CALL L64 linux_readlink(0x603230,0x7fffffff9900,0xfff)
65810 100946 fc-list 0.000014556 NAMI L64 "/etc/fonts/fonts.conf"
65810 100946 fc-list 0.000044729 RET L64 linux_readlink -1 errno -22 Invalid argument
65810 100946 fc-list 0.000019414 CALL L64 linux_newstat(0x603230,0x7fffffffa880)
65810 100946 fc-list 0.000014753 NAMI L64 "/etc/fonts/fonts.conf"
65810 100946 fc-list 0.000046509 STRU L64 struct stat {dev=136, ino=11059133, mode=0100644, nlink=1, uid=0, gid=0, rdev=22115903, atime=1688325346.417249000, mtime=1677115899, ctime=1677421954.886158000, birthtime=1677115899, size=2668, blksize=32768, blocks=8, flags=0x0 }
65810 100946 fc-list 0.000015586 RET L64 linux_newstat 0
65810 100946 fc-list 0.000014891 CALL L64 linux_open(0x604b90,0x80000<O_RDONLY|O_CLOEXEC>)
65810 100946 fc-list 0.000015416 NAMI L64 "/etc/fonts/fonts.conf"
65810 100946 fc-list 0.000048499 RET L64 linux_open 3

what is sysctl compat.linux.emul_path?

As I already mentioned, my test was done from a fresh installation off of a FreeBSD 14-CURRENT ISO image. Everything other than what I had described was 100% defaults.

compat.linux.emul_path: /compat/linux

I even went as far as to record a video of the copy-pastable repro instructions that I gave to show the issue.

www.youtube.com/watch?v=N46TGrCK4t8

As I already mentioned, my test was done from a fresh installation off of a FreeBSD 14-CURRENT ISO image. Everything other than what I had described was 100% defaults.

compat.linux.emul_path: /compat/linux

I even went as far as to record a video of the copy-pastable repro instructions that I gave to show the issue.

www.youtube.com/watch?v=N46TGrCK4t8

We found the cause of the problem, on it