在linux模块中使用带参数的导出符号时丢失数据

时间:2015-01-31 10:14:41

标签: linux linux-kernel linux-device-driver

我正在尝试导出一个函数,以便可以从其他linux模块使用它,导出的函数被第二个模块成功检测到并且可以调用,但看起来我正在使用传递的数据参数。

我在互联网上找到的所有示例都使用void参数。

以下是两个模块:

#include <linux/module.h>
#include <linux/init.h>



static void exported_function(char* buffer, int n) {

  char msg[n];
  copy_from_user(msg, buffer, n);

  printk("MAIN received : %s\n", buffer);
  printk("MAIN copied : %s\n", msg);
  printk("MAIN size(n) : %s\n", n);

}

static int __init load_module(void) {
  printk("module loaded");

  return 0;
}

static void __exit unload_module(void) {
  printk("module unloaded");
}


module_init(load_module);
module_exit(unload_module);

EXPORT_SYMBOL(exported_function);

第二个是:

#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/uaccess.h>
#include <linux/fs.h>

extern void exported_function(char*, int);


int init_module(void) {
  printk("module COMM loaded");

  char* str = "AA";
  exported_function(str, 2);


  return 0;
}

void cleanup_module(void) {
  printk("module COMM unloaded!");
}

插入第二个模块后,我通过dmesg获得此输出:

[ 2951.103121] module loaded
[ 2951.104417] module COMM loadedMAIN received : AA
[ 2951.104422] MAIN copied : 
[ 2951.104424] MAIN size(n) : (null)

如您所见,n中的exported_function(char *buffer, int n)为空!但buffer

中没有数据丢失

我不明白为什么:/

感谢。

[编辑]

如果我将exported_function(char *, int)的签名更改为exported_function(int, int),则两个值都为空!!

1 个答案:

答案 0 :(得分:0)

予。在第二个模块中:

char* str = "AA";
exported_function(str, 2);

str基本上是3个字符,而不是2,您传递给exported_function。将第二个参数更改为3

II:在第一单元中:

printk("MAIN size(n) : %s\n", n);

这里打印的大小为n,格式说明符为字符串类型%s,更改为%d,您将从模块2中获得正确的值。

printk("MAIN size(n) : %d\n", n);

III:copy_from_user实际上是将数据从用户复制到内核空间,返回值是失败时无法复制的字节数,成功时为零。这意味着您必须收集返回的值,在您的情况下,由于您尝试从内核空间复制,因此它是非零的失败副本。

梗概:

unsigned long copy_from_user (  void *      to,
                   const void __user *      from,
                         unsigned long      n);