2009-07-26 6 views
73

커널에서 파일을 읽거나 쓰지 말아야하는 이유에 대한 모든 토론을 알고 있습니다. 대신에/proc 또는 netlink를 사용하여이를 수행하는 방법에 대해 설명합니다. 나는 어쨌든 읽고 쓰고 싶다. 나는 또한 Driving Me Nuts - Things You Never Should Do in the Kernel을 읽었다.Linux 커널 모듈에서 파일을 읽거나 쓰는 방법은 무엇입니까?

그러나 문제는 2.6.30은 sys_read()을 내보낼 수 없습니다. 오히려 그것의 포장은 SYSCALL_DEFINE3입니다. 내 모듈의 것을 사용한다면, 나는 다음과 같은 경고를 얻을 : 연결이 제대로 발생하지 않기 때문에

WARNING: "sys_read" [xxx.ko] undefined! 
WARNING: "sys_open" [xxx.ko] undefined! 

은 분명히 insmod 모듈을로드 할 수 없습니다.

질문 :

  • 하는 방법 (sys_read()/sys_open()가 수출되지 않음) 2.6.22 이후 커널 내에서 읽기/쓰기?
  • 일반적으로 커널 내에서 매크로 SYSCALL_DEFINEn()으로 싸여진 시스템 호출을 사용하는 방법은 무엇입니까?

답변

94

가능하면 파일 입출력을 피하십시오.

포함 : :

#include <linux/fs.h> 
#include <asm/segment.h> 
#include <asm/uaccess.h> 
#include <linux/buffer_head.h> 

(열 유사) 파일 열기 :

struct file *file_open(const char *path, int flags, int rights) 
{ 
    struct file *filp = NULL; 
    mm_segment_t oldfs; 
    int err = 0; 

    oldfs = get_fs(); 
    set_fs(get_ds()); 
    filp = filp_open(path, flags, rights); 
    set_fs(oldfs); 
    if (IS_ERR(filp)) { 
     err = PTR_ERR(filp); 
     return NULL; 
    } 
    return filp; 
} 

을 주요 아이디어는 "한 단계 더 깊은"가서 직접 콜 핸들러 대신 VFS level functions를 호출하는 것입니다 파일 닫기 (닫기와 유사) :

void file_close(struct file *file) 
{ 
    filp_close(file, NULL); 
} 

파일에서 데이터 읽기 (예 : prea d) : PWRITE 유사한 파일

int file_read(struct file *file, unsigned long long offset, unsigned char *data, unsigned int size) 
{ 
    mm_segment_t oldfs; 
    int ret; 

    oldfs = get_fs(); 
    set_fs(get_ds()); 

    ret = vfs_read(file, data, size, &offset); 

    set_fs(oldfs); 
    return ret; 
} 

쓰기 데이터()

int file_write(struct file *file, unsigned long long offset, unsigned char *data, unsigned int size) 
{ 
    mm_segment_t oldfs; 
    int ret; 

    oldfs = get_fs(); 
    set_fs(get_ds()); 

    ret = vfs_write(file, data, size, &offset); 

    set_fs(oldfs); 
    return ret; 
} 

동기화가) fsync를 행 (유사한 파일 변경 :

int file_sync(struct file *file) 
{ 
    vfs_fsync(file, 0); 
    return 0; 
} 

[편집] 처음을 나는 새로운 커널 버전에서 사라진 file_fsync를 사용할 것을 제안했다. 가난한 사람이 변화를 제안했지만 그 변화는 거부되었습니다. 편집을 거부하기 전에 편집을 거부했습니다.

+2

감사합니다. sys_read/sys_open 기능을 복제하여 비슷한 작업을 수행하려고 생각했습니다. 그러나 이것은 큰 도움입니다. 호기심, SYSCALL_DEFINE을 사용하여 선언 된 시스템 호출을 사용하는 방법이 있습니까? – Methos

+5

커널 2.6.30 (Ubuntu 9.04)에서이 코드를 시험해보고 파일을 읽으면 시스템이 충돌합니다. 누구나 같은 문제가 발생 했습니까? –

+0

@Enrico Detoma? 오 와우. 거기에 당신이 사용하는 모듈을 나에게 줄 수있는 방법이 있습니까? 전에 본 적 없니? – dmeister

관련 문제