linux下platform_device中的dma_mask與coherent_dma_mask

來源:互聯網
上載者:User

一:dma_mask與coherent_dma_mask的定義

在linux核心中,引入了platform_device與platform_driver,這樣就很方便了平台的裝置與驅動。在include\linux\platform_device.h下:

struct platform_device {
 const char * name;
 int  id;
 struct
device dev;
 u32  num_resources;
 struct resource * resource;

 const struct platform_device_id *id_entry;

 /* arch specific additions */
 struct pdev_archdata archdata;
};

而struct device dev,在include\linux\device.h中:

struct device {
 struct device  *parent;

 struct device_private *p;

 struct kobject kobj;
 const char  *init_name; /* initial name of the device */
 struct device_type *type;

 struct mutex  mutex; /* mutex to synchronize calls to
      * its driver.
      */

 struct bus_type *bus;  /* type of bus device is on */
 struct device_driver *driver; /* which driver has allocated this
        device */
 void  *platform_data; /* Platform specific data, device
        core doesn't touch it */
 struct dev_pm_info power;

#ifdef CONFIG_NUMA
 int  numa_node; /* NUMA node this device is close to */
#endif
 u64  *dma_mask; /*
dma mask (if dma'able device) */
 u64  coherent_dma_mask;/* Like dma_mask, but for
          alloc_coherent mappings as
          not all hardware supports
          64 bit addresses for consistent
          allocations such descriptors. */

 struct device_dma_parameters *dma_parms;

 struct list_head dma_pools; /* dma pools (if dma'ble) */

 struct dma_coherent_mem *dma_mem; /* internal for coherent mem
          override */
 /* arch specific additions */
 struct dev_archdata archdata;
#ifdef CONFIG_OF
 struct device_node *of_node;
#endif

 dev_t   devt; /* dev_t, creates the sysfs "dev" */

 spinlock_t  devres_lock;
 struct list_head devres_head;

 struct klist_node knode_class;
 struct class  *class;
 const struct attribute_group **groups; /* optional groups */

 void (*release)(struct device *dev);
};
dma_mask與coherent_dma_mask這兩個參數表示它能定址的物理地址的範圍,核心通過這兩個參數分配合適的實體記憶體給 device。其中dma_coherent_mask則作用於申請一致性DMA緩衝區。因為不是所有的硬體都能夠支援64bit的地址寬度。如果 addr_phy 是一個物理地址,且 (u64)addr_phy <= *dev->dma_mask,那麼 該 device 就可以定址該物理地址。如果 device 只能定址32位地址,那麼 mask 應為 0xffffffff。依此類推。

例如,在linux2.6.38中:

/* USB EHCI Host Controller */

static
u64 nuc900_device_usb_ehci_dmamask = 0xffffffffUL;

static struct platform_device nuc900_device_ehci = {
        .name    = "nuc900-ehci",
        .id    = -1,
        .num_resources   = ARRAY_SIZE(nuc900_ehci_resource),
        .resource   = nuc900_ehci_resource,
        .dev              = {
                .dma_mask = &nuc900_device_usb_ehci_dmamask,
                .coherent_dma_mask
= 0xffffffffUL
        }
};

二:sample
code


這段代碼摘錄自 arch\arm\mm\dma-mapping.c

    u64 limit;
    /*
     * Sanity check the allocation size.
     */
    size = PAGE_ALIGN(size);
    //這個 limit 就是通過 mask 計算得到的裝置最大定址範圍。
    limit = (mask + 1) & ~mask;
    //當 size 超出 limit 時,說明分配的地址超出了裝置的最大定址能力,這時返回錯誤。
    if ((limit && size >= limit) ||
        size >= (CONSISTENT_END - CONSISTENT_BASE)) {
        printk(KERN_WARNING "coherent allocation too big "
               "(requested %#x mask %#llx)\n", size, mask);
        goto no_page;
    }

 

相關文章

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.