Warning: file_get_contents(/data/phpspider/zhask/data//catemap/4/c/61.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/css/35.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C linux用户宏的含义是什么?_C_Macros_Linux Kernel_Kernel - Fatal编程技术网

C linux用户宏的含义是什么?

C linux用户宏的含义是什么?,c,macros,linux-kernel,kernel,C,Macros,Linux Kernel,Kernel,我希望有人能解释linux内核源代码中使用的用户宏的细微差别 首先,宏观方面: # define __user __attribute__((noderef, address_space(1))) 现在,在谷歌搜索之后,我读到这个宏允许一个指针被指定为属于用户地址空间,并且它不应该被取消引用 我可能遗漏了一些显而易见的事实,但有人能解释一下这样一个宏观经济的含义吗?例如,这个宏在哪里有用的一个好例子是什么?再说一次,如果我遗漏了一些明显的东西,请原谅我 为了更好地理解这一点,我

我希望有人能解释linux内核源代码中使用的用户宏的细微差别

首先,宏观方面:

# define __user         __attribute__((noderef, address_space(1)))
现在,在谷歌搜索之后,我读到这个宏允许一个指针被指定为属于用户地址空间,并且它不应该被取消引用

我可能遗漏了一些显而易见的事实,但有人能解释一下这样一个宏观经济的含义吗?例如,这个宏在哪里有用的一个好例子是什么?再说一次,如果我遗漏了一些明显的东西,请原谅我

为了更好地理解这一点,我在检查一些USB代码(linux/usbdevice_fs.h)时访问了宏。我只是想对内核中使用的宏(或其他类似宏)有一个大致的了解


谢谢你的关注

它允许工具告诉内核开发人员,他们可能不正确地使用了不受信任的指针(或在当前虚拟地址映射中可能无效的指针)。

我认为用户标记了用户空间指针,并告诉开发人员/系统不要信任它。若用户给你们“无效”指针,那个么内核会尝试引用它(注意,内核可以在任何地方引用),它会破坏自己的空间

例如,在“read”(在您的usbdevice_fs.h中)中,应该为您提供一个(_用户)缓冲区来写入结果。所以您必须使用copy\u to\u user,但不能使用memcopy、strcpy或类似的东西


注意:这不是正式的定义/描述,而是我所知道的唯一部分。

编译器.h头文件中的
\uuu用户
宏是用其他一些宏定义的,如
\uu force
/
\uu内核
等。它们实际上对传统编译器(包括GCC/ICC等)没有任何用处,但对于诸如sparse之类的内核静态分析工具非常有用(更多信息请参见:sparse-Linux内核新手)。当您提到诸如
\uuuu user
/
\uu kernel
/
\uu force
等宏时,它对稀疏保持了特殊的意义。在Linux内核邮件列表中,Linus Torvalds这样解释它的使用:

记住这一点很重要:对于gcc来说,稀疏注释是没有意义的。它们仍然很有用,只要以一种相当可读的方式告诉程序员“嘿,你得到的指针不是一个普通的指针”,但最终,除非你使用稀疏,否则它们实际上什么都不做

不过。当您使用parse时,这完全是另一回事。对于“稀疏”而言,“iomem”有很多含义:

# define __iomem __attribute__((noderef, address_space(2)))
ie“iomem”的意思是两件不同的事情:它意味着稀疏应该抱怨

如果指针曾经被直接取消引用(它是一个“noderef”指针),并且它位于“地址空间2”中,而不是普通的地址空间(0)

现在,这意味着如果这样一个指针被传递到一个需要一个常规指针的函数中(因为它不是一个普通指针,显然不应该对它执行“strcmp()”等操作),sparse会抱怨,如果你试图将它转换到另一个地址空间中的另一个指针,sparse也会抱怨


有关好的示例,请参见do_execve()源代码。查看如何在count()中使用argv。如果只是取消引用(*argv[0])或其他内容,稀疏(1)将对此发出警告。address_space表示并非所有指针都是相等的,需要不同的(取消引用)规则,不应混合使用。@adobriyan在哪个头文件或源文件中可以找到此函数?我不想为了找到它而在文件系统中grep。一个路径就足够了是的,它可以让复制到用户有意义
\uuuuu属性
可以使用任意文本作为“属性”?它不限于对GCC本身有意义的固定集?@AlexD来自:
属性说明符的形式为_属性_u((属性列表))。属性列表可能是一个空的逗号分隔的属性序列,其中每个属性都是以下属性之一:1。空的。空属性将被忽略**2.属性名称(可以是标识符,如unused,也可以是保留字,如const)。**(…)
。它似乎可以是您想要的任何标识符(使用标识符命名约定)。