2012-12-13 22 views
0

IOCTL - 無效參數

#define IOCTL_ALLOC_MSG _IO(MAJOR_NUM, 0) 
#define IOCTL_DEALLOC_MSG _IO(MAJOR_NUM, 1) 

在頭文件。

,並在我寫的驅動程序文件:

struct file_operations memory_fops = { 
    unlocked_ioctl: device_ioctl, 
    open: memory_open, 
    release: memory_release 
}; 


int memory_init(void) { 
    int result; 

    /* Registering device */ 
    result = register_chrdev(MAJOR_NUM, "memory", &memory_fops); 
    if (result < 0) { 
    printk("<1>memory: cannot obtain major number %d\n", MAJOR_NUM); 
    return result; 
    } 

    allocfunc(); 

    printk("<1>Inserting memory module\n"); 
    return 0; 

} 

int device_ioctl(struct inode *inode, /* see include/linux/fs.h */ 
     struct file *file, /* ditto */ 
     unsigned int ioctl_num, /* number and param for ioctl */ 
     unsigned long ioctl_param) 
{ 
    /* 
    * Switch according to the ioctl called 
    */ 
    printk ("<l> inside ioctl \n"); 
    switch (ioctl_num) { 
    case IOCTL_ALLOC_MSG: 
     allocfunc(); 
     break; 
    case IOCTL_DEALLOC_MSG: 
     deallocfunc(); 
     break; 
    } 

    return 0; 
} 

我創建的字符文件中像

mknod /dev/memory c 60 0 

應用程序調用失敗

int main(int argc, char *argv[]) { 
    FILE * memfile; 

    /* Opening the device parlelport */ 
    memfile=fopen("memory","r+"); 
    if (memfile <0) { 
     printf (" cant open file \n"); 
     return -1; 
    } 

    /* We remove the buffer from the file i/o */ 
    int ret_val; 
    if (argc > 1) { 
     if (strcmp (argv[1], "mem") ==0) { 


      ret_val = ioctl(memfile, IOCTL_ALLOC_MSG); 

      if (ret_val < 0) { 
       printf("ioctl failed. Return code: %d, meaning: %s\n", ret_val, strerror(errno)); 
       return -1; 
      } 
     } 

當我運行的應用程序,我得到「ioctl失敗。返回代碼:-1,含義:無效參數」in:strerror(errno)

的printk:

Inserting memory module 

僅供參考,我嘗試用 「的/ dev /記憶」, 「記憶」 不同的名稱和主要的數字組合 - 但不成功。

+1

'MAJOR_NUM'的值是什麼?你確定60還沒有被另一個驅動程序使用嗎?即你的init_module()函數是什麼樣的,如果它應該調用register_chrdev(),結果是什麼?另外,你甚至不會顯示調用'strerror()'.... –

+0

MAJOR_NUM是60並且不被另一個驅動程序使用int memory_init(void){int result; /*註冊設備*/ result = register_chrdev(MAJOR_NUM,「memory」,&memory_fops); if(result <0){ printk(「<1> memory:can not obtain major number%d \ n」,MAJOR_NUM); 返回結果; } allocfunc(); printk(「<1>插入內存模塊\ n」); return 0; } --- app ---------- ret_val = ioctl(memfile,IOCTL_ALLOC_MSG);如果(ret_val <0)printf(「ioctl失敗。返回碼:%d,含義:%s \ n」,ret_val,strerror(errno)); return -1; } – resultsway

+0

好的,也許你可以在上面的代碼中編輯它?並且還請在'fopen()'之前添加所有的代碼,幷包括對'strerror()'的調用(尤其是顯示是否從'fopen()'中檢查了結果),並顯示來自直到'ioctl()'調用的時間(即,我想在那裏看到'printk()'和任何其他相關的輸出。) –

回答

4

您正在向ioctl()函數傳遞FILE*函數,但它需要一個文件描述符,即int

它應該至少會產生一個很大的警告,說你正在將一個指針轉換爲整型,而不是一個轉換,不是嗎?

有兩個明顯的解決方案:

  1. 使用fileno()函數來獲取從FILE*文件描述符。它應該是ioctl(fileno(memfile), IOCTL_ALLOC_MSG)。使用open()而不是fopen()。如果您正在編寫低級代碼,則這是首選解決方案,因爲您避免了FILE*強加的額外抽象層(所有緩衝區等等)。
+0

該死!我完全錯過了那一個! –

+0

非常好。 Thx一堆。儘管沒有警告。 – resultsway

+1

@furion:不客氣!嘗試使用'-Wall'編譯。它應該給出警告。也許你忘了'#include '並且你得到了自動函數聲明;如果是這種情況,你也應該有警告。 – rodrigo

0

我打算假設將fopen("memory")更改爲fopen("/dev/memory1")將解決您的代碼的初始問題。

@SunEric也指出了你的問題,你有你的驅動程序的初始化函數(memory_init())到allocFunc()呼叫的評論,然而這似乎是你希望你的IOCTL_ALLOC_MSG做什麼。這可能是你需要理順的下一個問題。

+0

對此感到抱歉,我對「/ dev/memory」「memory」的不同名稱和主要數字組合進行了嘗試 - 但徒勞無益。我嘗試過使用allocFunc()而沒有使用等,請忽略小問題。 Iam能夠成功地在memory_init()中看到printk。 – resultsway