2017-02-14 14 views
0

У меня есть следующие chardev определены:Начало ENOTTY на IOCTL для модуля ядра Linux

.h

#define MAJOR_NUM 245 
#define MINOR_NUM 0 
#define IOCTL_MY_DEV1 _IOW(MAJOR_NUM, 0, unsigned long) 
#define IOCTL_MY_DEV2 _IOW(MAJOR_NUM, 1, unsigned long) 
#define IOCTL_MY_DEV3 _IOW(MAJOR_NUM, 2, unsigned long) 

модуль .c

static long device_ioctl(
        struct file* file, 
        unsigned int ioctl_num, 
        unsigned long ioctl_param) 
{ 
    ... 
} 

static int device_open(struct inode* inode, struct file* file) 
{ 
    ... 
} 

static int device_release(struct inode* inode, struct file* file) 
{ 
    ... 
} 

struct file_operations Fops = { 
    .open=device_open, 
    .unlocked_ioctl= device_ioctl, 
    .release=device_release 
}; 

static int __init my_dev_init(void) 
{ 
    register_chrdev(MAJOR_NUM, "MY_DEV", &Fops); 
    ... 
} 
module_init(my_dev_init); 

Мой код пользователя

ioctl(fd, IOCTL_MY_DEV1, 1); 

Всегда с такой же ошибкой: ENOTTY

Inappropriate ioctl for device

Я видел подобные вопросы: т.е.

Linux kernel module - IOCTL usage returns ENOTTY

Linux Kernel Module/IOCTL: inappropriate ioctl for device

Но их решения не работают для меня

+0

Вы проверили, вызвано ли ваше 'device_ioctl()'? (помещает вызов printk там) – nos

+0

@nos my 'device_ioctl()' не вызывается, поместить пустые тела только с 'printk' – Mugen

+0

У вас недостаточно зарегистрированная версия вашего вызова ioctl ... попробуйте заблокированный. –

ответ

1

ENOTTY выдается ядром когда ваш драйвер устройства не зарегистрировал функцию ioctl, которая будет вызвана , Боюсь, что ваша функция плохо зарегистрирована, вероятно, потому, что вы зарегистрировали ее в поле .unlocked_ioctl структуры struct file_operations.

Возможно, вы получите другой результат, если зарегистрируете его в заблокированной версии функции. Наиболее вероятной причиной является то, что индексный дескриптор заблокирован для вызова IOCTL (как это должно быть, чтобы избежать условий гонки с одновременным read или write операций на одном устройстве)

К сожалению, у меня нет доступа к дереву исходных текстов Linux для правильного имени используемого поля, но наверняка вы сможете найти его самостоятельно.