Использование lstat/stat из ядра Linux?

Я надеюсь, что кто-нибудь сможет проверить мои предположения на вопрос «Можно ли назвать lstat и/или stat из ядра Linux 3.10.0 в Centos 7. Я искал и читал столько, сколько мог найти, и только Я могу запутаться Я не могу сказать, доступны ли примеры, которые я нахожу, только для пространства ядра или пространства пользователя.

Основной вопрос: могу ли я вызвать lstat или stat из ядра?

В частности, я добавляю это в exec.c в каталоге fs.

Цель состоит в том, чтобы различать файлы, которые являются либо символическими, либо жесткими ссылками и предназначены только для обучения.

Если это правда, буду ли я вызывать lstat/stat или версию "64" - я использую архитектуру X86, если это имеет значение.

Добавлено 18.11.2015 Согласно комментарию ниже

// These two lines are in the original exec.c file
struct file *file;
file = do_filp_open(AT_FDCWD, &tmp, &open_exec_flags, LOOKUP_FOLLOW);


// In the open_exec function I added the following
struct stat buf;
int lstat(struct file, struct stat buf);
mm_segment_t security_old_fs;

security_old_fs = get_fs();
set_fs(KERNEL_DS);
if (lstat(*file, buf) == -)
    printk(KERN_INFO "stat error\n");
    goto exit;
}
set_fs(security_old_fs);

Затем запустите «сделать» и посмотрите

LINK    vmlinux
LD      vmlinux.o
MODPOST vmlinux.o
GEN     .version
CHK     include/generated/compile.h
UPD     include/generated/compile.h
CC      init/version.o
D      init/built-in.o
fs/built-in.o: In function`open_exec':
/home/user/rpmbuild/SOURCES/linux-3.10.0-123.20.1.el7/fs/exec.c:946: undefined reference to `lstat'
make: *** [vmlinux] Error 1

Любые указатели будут полезны.


person rhg_lnx    schedule 23.10.2015    source источник
comment
stat системный вызов определяется как SYSCALL_DEFINE2(stat,...) в fs/stat.c. lstat определен под ним. Как видите, реализация этих системных вызовов использует vfs_stat/vfs_lstat. Для использования этих функций внутри пространства ядра вам нужно, чтобы аргумент пути интерпретировался как принадлежащий пространству пользователя. Например, используя set_fs/get_fs.   -  person Tsyvarev    schedule 24.10.2015
comment
@tsyvarev Я добавил комментарии в конец исходного запроса, показывающие, что я пробовал, и результаты. Кажется, я все еще что-то упускаю? Результаты такие же при использовании stat/lstat/fstat.   -  person rhg_lnx    schedule 19.11.2015


Ответы (1)


В ядре Linux нет функций stat/lstat.

Существуют функции sys_stat/sys_lstat, которые реализуют соответствующие системные вызовы, но вызов этих функций внутри ядра не рекомендуется: эти функции могут использовать специальные соглашения для передачи аргументов, которые отличаются от общепринятых соглашений в ядре.

На самом деле существует функция vfs_stat, которая вызывается sys_stat и выполняет наибольшую работу . Обратите внимание, что эта функция ожидает, что имя файла будет расположено в пространстве пользователя. Для использования этой функции для имени файла, выделенного ядром, можно использовать set_fs подход:

int my_stat(const char* name, struct kstat* stat)
{
    int res;
    mm_segment_t security_old_fs;

    security_old_fs = get_fs();
    set_fs(KERNEL_DS);

    res = vfs_stat((const char __user *)name, stat);

    set_fs(security_old_fs);

    return res;
}

Атрибуты файла хранятся в переменной типа ядра struct kstat, которая определена в include/linux/stat.h.

Точно так же vfs_lstat выполняет большую часть работы sys_lstat.

Обратите внимание, что и vfs_stat, и vfs_lstat используют соглашения 0/-E для возвращаемого значения: 0 возвращается в случае успеха, отрицательный код ошибки возвращается в случае неудачи.

person Tsyvarev    schedule 19.11.2015