2016-10-09 25 views
0

我正在阅读设备驱动程序的源代码。kmalloc许多结构,我应该一次kmalloc全部或分别

它试图用kmalloc 16 struct foo

spin_lock_bh(&sq->lock); 
for (i=0; i<16; i++) { 
     msg = kmalloc(sizeof(*msg), GFP_ATOMIC); 
     if (!msg) 
       break; 
     msg->next = sq->msg_first; 
     sq->msg_first = msg; 
     sq->nr_msgs++; 
}  
spin_unlock_bh(&sq->lock); 

所以,这将是更好kmalloc(sizeof(*msg) * 16, GFP_ATOMIC)?为什么?

+0

这是来自工作设备驱动程序的真实源代码吗?在锁上执行锁定,然后在不同的'spinlock_t'变量'sq-> avmi_lock'上解锁。这看起来不正确。 – Aleksey

+0

'会更好吗......' - 这是非常依赖你的需求。实际上,你正在为消息选择一个*类型的容器*:** list **(为每个元素分配,每个元素需要包含到下一个元素的链接)或** array **/** vector **(single分配给所有元素,任何元素都可以通过整数索引来访问)。 – Tsyvarev

回答

1

在没有看到源代码的情况下很难说任何明确的。以这种方式进行内存分配的基本原理可能与我们在此讨论的任何内容有很大不同。

一个合理的基本原理可能是这样的。正如你所看到的,分配的项目在一个单独的链接列表中链接在一起。这可能只是一个初始物品池,可以在驱动程序运行时扩展或缩短。初始池中的某些项目可能会在稍后时间被移除和释放。如果你要在一次分配中分配这个内存,你将无法做到这一点。由于这些项目链接到链接列表中,我不认为这将作为Tsyvarev暗示的阵列使用。

我必须说,多数情况下理由可以用一个单词来表征:因为。因为代码的作者认为这样做更方便,或更清晰等等。不幸的是,这种情况一直发生。只要这些地方不重要(即不在热门路线),没关系。你无法解决所有问题。

EDIT
如下面的响应所指出的,分配是用于高达 16项。这可能是一个故意的设计决定。如果分配在某个时候失败了,它就会分配循环分配尽可能多的项目,因为它可能超过16个。这实际上适合于这些项目可能构成初始池直至 16个项目的想法。

+0

*“因为”*也被称为“设计选择”。 – sawdust

+0

当然。只是这些设计选择很少在代码中评论。 – Aleksey

0

此代码尝试分配向上至16 struct foo s。但是如果没有足够的内存,那么它仍然会分配一些内存。您建议的更改是尝试分配16 struct foo,如果不能这样做,则尝试失败。如果只有一些分配的空间会怎么样?

此外,一个分配的分配器必须找到一个连续的内存区域,而多个它可以处理碎片内存。

相关问题