Назад | Перейти на главную страницу

Компиляция ядра версии> = 2.6.34 на CentOS 5: набор RAID «ddf1_foo» не был активирован?

я бы хотел смонтировать Ceph FS на некоторых серверах CentOS 5. Поскольку ceph-fuse не удалось с ошибками ниже:

# ceph-fuse --no-fuse-big-writes -m 192.168.2.15:6789 /mnt/ceph/
ceph-fuse[7528]: starting ceph client
ceph-fuse[7528]: starting fuse
fuse: unknown option `atomic_o_trunc'
2013-04-04 13:51:21.128506 2b82d6e9e8f0 -1 fuse_lowlevel_new failed
ceph-fuse[7528]: fuse finished with error 33
ceph-fuse[7526]: mount failed: (33) Numerical argument out of domain

Google указал на этот но CentOS 5.x поставляется с ядром 2.6.18, я собираюсь скомпилировать более новое ядро, поддерживающее Ceph.

В .config был скопирован из работающего ядра с двумя дополнительными настройками:

CONFIG_SYSFS_DEPRECATED_V2=y
CONFIG_CEPH_FS=m

Но оба они дают мне следующую ошибку:

От первого предупреждения можно избавиться, отредактировав скрипт инициализации после извлечения образа ядра и удалив 2 строки:

echo "Loading dm-region-hash.ko module"
insmod /lib/dm-region-hash.ko 

http://funky-dennis.livejournal.com/3290.html

Как насчет второй ошибки:

device-mapper: table: 253:0: mirror: Error creating mirror dirty log
RAID set "ddf1_bar" was not activated

В основном они такие же, за исключением того, что следующие модули не загружаются в новое ядро:

echo "Loading dm-mem-cache.ko module"
insmod /lib/dm-mem-cache.ko 
echo "Loading dm-message.ko module"
insmod /lib/dm-message.ko 
echo "Loading dm-raid45.ko module"
insmod /lib/dm-raid45.ko 

Это причина RAID set "ddf1_foo" was not activated?


ОБНОВЛЕНИЕ Четверг, 4 апреля 21:40:32 ICT 2013

http://alistairphipps.com/wiki/index.php?title=Notes#LVM

Странное сообщение об ошибке, подобное «зеркальный журнал: нераспознанный аргумент синхронизации для зеркального журнала: 2», «таблица: зеркало: ошибка создания зеркального грязного журнала» означает, что у вас несовпадающие версии сопоставителя устройств ядра и инструментов пользовательского пространства: вероятно, ваше ядро ​​слишком недавно ваша версия инструментов lvm. Установите последнюю версию устройства сопоставления устройств и lvm2 из исходников, и он должен работать.

Я пробовал скомпилировать последнюю версию LVM2:

# /usr/sbin/lvm version
  LVM version:     2.02.98(2) (2012-10-15)
  Library version: 1.02.67-RHEL5 (2011-10-14)
  Driver version:  4.11.6

но ничего не изменилось.


ОБНОВЛЕНИЕ Сб, 6 апреля 18:51:31 ICT 2013

/lib/modules/2.6.18-274.el5/kernel/drivers/md/

|-- dm-crypt.ko
|-- dm-emc.ko
|-- dm-hp-sw.ko
|-- dm-log.ko
|-- dm-mem-cache.ko
|-- dm-message.ko
|-- dm-mirror.ko
|-- dm-mod.ko
|-- dm-multipath.ko
|-- dm-raid45.ko
|-- dm-rdac.ko
|-- dm-region_hash.ko
|-- dm-round-robin.ko
|-- dm-snapshot.ko
|-- dm-zero.ko
|-- faulty.ko
|-- linear.ko
|-- multipath.ko
|-- raid0.ko
|-- raid1.ko
|-- raid10.ko
|-- raid456.ko
`-- xor.ko

/lib/modules/2.6.34.14/kernel/drivers/md/

|-- dm-crypt.ko
|-- dm-log.ko
|-- dm-mirror.ko
|-- dm-mod.ko
|-- dm-multipath.ko
|-- dm-region-hash.ko
|-- dm-round-robin.ko
|-- dm-snapshot.ko
|-- dm-zero.ko
|-- faulty.ko
|-- linear.ko
|-- multipath.ko
|-- raid0.ko
|-- raid1.ko
|-- raid10.ko
|-- raid456.ko
`-- raid6_pq.ko

ОБНОВЛЕНИЕ 10 апреля, среда, 11:22:54, ICT 2013

Сделайте поиск в исходной папке, я нашел это:

# grep -lr 'Error creating mirror dirty log' /usr/src/linux-2.6.34.14
/usr/src/linux-2.6.34.14/drivers/md/dm-raid1.c

dm-raid1.c:

static struct dm_dirty_log *create_dirty_log(struct dm_target *ti,
                         unsigned argc, char **argv,
                         unsigned *args_used)
{
    unsigned param_count;
    struct dm_dirty_log *dl;

    if (argc < 2) {
        ti->error = "Insufficient mirror log arguments";
        return NULL;
    }

    if (sscanf(argv[1], "%u", &param_count) != 1) {
        ti->error = "Invalid mirror log argument count";
        return NULL;
    }

    *args_used = 2 + param_count;

    if (argc < *args_used) {
        ti->error = "Insufficient mirror log arguments";
        return NULL;
    }

    dl = dm_dirty_log_create(argv[0], ti, mirror_flush, param_count,
                 argv + 2);
    if (!dl) {
        ti->error = "Error creating mirror dirty log";
        return NULL;
    }

    return dl;
}

dm-log.c:

struct dm_dirty_log *dm_dirty_log_create(const char *type_name,
            struct dm_target *ti,
            int (*flush_callback_fn)(struct dm_target *ti),
            unsigned int argc, char **argv)
{
    struct dm_dirty_log_type *type;
    struct dm_dirty_log *log;

    log = kmalloc(sizeof(*log), GFP_KERNEL);
    if (!log)
        return NULL;

    type = get_type(type_name);
    if (!type) {
        kfree(log);
        return NULL;
    }

    log->flush_callback_fn = flush_callback_fn;
    log->type = type;
    if (type->ctr(log, ti, argc, argv)) {
        kfree(log);
        put_type(type);
        return NULL;
    }

    return log;
}

Благодаря всей помощи моего друга проблема решена.

С первой попытки закомментировал строку ti->error = "Error creating mirror dirty log"; в dm-raid1.c, и вставил несколько строк отладки в dm-log.c чтобы определить, что вызвало указанную выше ошибку:

    log = kmalloc(sizeof(*log), GFP_KERNEL);
    if (!log)
        ti->error = "kmalloc error";
        return NULL;

    type = get_type(type_name);
    if (!type) {
        kfree(log);
        ti->error = "get_type error";
        return NULL;
    }

    log->flush_callback_fn = flush_callback_fn;
    log->type = type;
    if (type->ctr(log, ti, argc, argv)) {
        kfree(log);
        put_type(type);
        ti->error = "ctr error";
        return NULL;
    }

затем перекомпилировали ядро ​​и получили:

Со второй попытки он хочет получить значение type_name:

if (type->ctr(log, ti, argc, argv)) {
    kfree(log);
    put_type(type);
    char* typeN = kmalloc(1000, GFP_KERNEL);
    char* pTypeN = typeN;
    char* ptype_name = type_name;
    while (*ptype_name != '\0') {
        *pTypeN = *ptype_name;
        ++pTypeN;
        ++ptype_name;
    }
    ti->error = typeN;
    return NULL;
}

Продолжить отслеживание до core_ctr и create_log_context используя вышеуказанный метод:

static int create_log_context(struct dm_dirty_log *log, struct dm_target *ti,
                  unsigned int argc, char **argv,
                  struct dm_dev *dev)
{
    enum sync sync = DEFAULTSYNC;

    struct log_c *lc;
    uint32_t region_size;
    unsigned int region_count;
    size_t bitset_size, buf_size;
    int r;

    if (argc < 1 || argc > 2) {
        DMWARN("wrong number of arguments to dirty region log");
        ti->error = "argc < 1 or > 2";
        return -EINVAL;
    }

    if (argc > 1) {
        if (!strcmp(argv[1], "sync"))
            sync = FORCESYNC;
        else if (!strcmp(argv[1], "nosync"))
            sync = NOSYNC;
        else {
            DMWARN("unrecognised sync argument to "
                   "dirty region log: %s", argv[1]);
            ti->error = "unrecognised sync argument to";
            return -EINVAL;
        }
    }

if (argc < 1 || argc > 2) {
    DMWARN("wrong number of arguments to dirty region log");
    char* argcStr = kmalloc(1000, GFP_KERNEL);
    char* pArgc = argcStr;
    unsigned int temp = argc;
    do {
        *pArgc = temp % 10;
        ++pArgc;
        temp = temp / 10;
    } while (temp > 0);
    *pArgc = ' ';
    ++pArgc;
    //copy argv;
    int i = 0;
    for (i; i < argc; ++i) {
        char* pArgv = argv[i];
        while (*pArgv != '\0') {
            *pArgc = *pArgv;
            ++pArgc;
            ++pArgv;
        }
        *pArgc = ' ';
        ++pArgc;
    }
    *pArgc = '\0';
    ti->error = argcStr;
    return -EINVAL;
}

Обратите внимание, что код ASCII символа черного сердца ... 3.

Не знаю, почему автор путает core_ctr с disk_ctr. В type_name является core но количество аргументов равно 3, поэтому он обрезает последний аргумент (block_on_error), вставив в dm_dirty_log_create структура:

struct dm_dirty_log *dm_dirty_log_create(const char *type_name,
            struct dm_target *ti,
            int (*flush_callback_fn)(struct dm_target *ti),
            unsigned int argc, char **argv)
{
    struct dm_dirty_log_type *type;
    struct dm_dirty_log *log;

    log = kmalloc(sizeof(*log), GFP_KERNEL);
    if (!log) {
        ti->error = "kmalloc error";
        return NULL;
    }

    char* core = "core";
    char* pCore = core;
    int is_core = 1;

    char* ptype_name = type_name;
    while (*ptype_name != '\0') {
        if (*pCore != *ptype_name) {
            is_core = 0;
        }
        ++pCore;
        ++ptype_name;
    }

    if (is_core && *pCore == *ptype_name && argc == 3) {
        --argc;
    }
    type = get_type(type_name);

Давай посмотрим что происходит:

# uname -r
2.6.34.14

# dmraid -s
*** Group superset .ddf1_disks
--> Active Subset
name   : ddf1_VCBOOT
size   : 489971712
stride : 128
type   : mirror
status : ok
subsets: 0
devs   : 2
spares : 0

# modprobe ceph

# lsmod | grep ceph
ceph                  176676  0 

# df -h
Filesystem            Size  Used Avail Use% Mounted on
/dev/mapper/ddf1_VCBOOTp3
                      219G   17G  191G   8% /
/dev/mapper/ddf1_VCBOOTp1
                       99M   64M   30M  69% /boot
tmpfs                  48G   16M   48G   1% /dev/shm
192.168.2.13:6789,192.168.2.14:6789,192.168.2.15:6789:/
                       72T   28T   45T  39% /mnt/ceph

Почему вы вообще используете рейдовый массив в формате ddf? Похоже, вы пытаетесь активировать его с помощью dmraid, который не получил развития уже несколько лет и более или менее изношен. mdadm поддерживается гораздо лучше, а последние версии действительно поддерживают формат ddf, хотя его собственный формат предпочтительнее.

Убедитесь, что вы загрузили модуль dm-log.

По ошибке Ceph 4286, FUSE требуется ядро ​​как минимум 2.6.24 для atomic_o_trunc. Я нашел RPM для 2.6.25. Похоже, это ядро ​​предназначено для кластера HPC.

Я думаю, что ваша проблема связана с серьезными модификациями, которые Red Hat вносит в свои версии ядра. Это значительно усложняет попытку использования новых ядер в зависимости от конфигурации вашего оборудования и требований к программному обеспечению.