46
46
kmem_handle->align = kmem_entry->align;
48
48
if (kmem_handle->type != kmem_entry->type) {
49
mod_info("Invalid type of reusable kmem_entry\n");
49
mod_info("Invalid type of reusable kmem_entry, currently: %lu, but requested: %lu\n", kmem_entry->type, kmem_handle->type);
53
if (kmem_handle->type == PCILIB_KMEM_TYPE_PAGE) {
53
if ((kmem_handle->type&PCILIB_KMEM_TYPE_MASK) == PCILIB_KMEM_TYPE_PAGE) {
54
54
kmem_handle->size = kmem_entry->size;
55
55
} else if (kmem_handle->size != kmem_entry->size) {
56
mod_info("Invalid size of reusable kmem_entry\n");
56
mod_info("Invalid size of reusable kmem_entry, currently: %lu, but requested: %lu\n", kmem_entry->size, kmem_handle->size);
60
60
if (kmem_handle->align != kmem_entry->align) {
61
mod_info("Invalid alignment of reusable kmem_entry\n");
61
mod_info("Invalid alignment of reusable kmem_entry, currently: %lu, but requested: %lu\n", kmem_entry->align, kmem_handle->align);
132
133
retptr = (void*)__get_free_pages(GFP_KERNEL, get_order(PAGE_SIZE));
133
134
kmem_entry->dma_handle = 0;
134
135
kmem_handle->size = PAGE_SIZE;
136
// kmem_entry->dma_handle = pci_map_single(privdata->pdev, retptr, PAGE_SIZE, PCI_DMA_FROMDEVICE);
137
// printk("%llx %lx\n", kmem_entry->dma_handle, retptr);
138
if (kmem_entry->type == PCILIB_KMEM_TYPE_DMA_S2C_PAGE) {
139
kmem_entry->direction = PCI_DMA_TODEVICE;
140
kmem_entry->dma_handle = pci_map_single(privdata->pdev, retptr, PAGE_SIZE, PCI_DMA_TODEVICE);
141
if (pci_dma_mapping_error(privdata->pdev, kmem_entry->dma_handle)) {
142
free_page((unsigned long)retptr);
143
goto kmem_alloc_mem_fail;
145
} else if (kmem_entry->type == PCILIB_KMEM_TYPE_DMA_C2S_PAGE) {
146
kmem_entry->direction = PCI_DMA_FROMDEVICE;
147
kmem_entry->dma_handle = pci_map_single(privdata->pdev, retptr, PAGE_SIZE, PCI_DMA_FROMDEVICE);
148
if (pci_dma_mapping_error(privdata->pdev, kmem_entry->dma_handle)) {
149
free_page((unsigned long)retptr);
150
goto kmem_alloc_mem_fail;
140
158
goto kmem_alloc_mem_fail;
142
162
if (retptr == NULL)
143
163
goto kmem_alloc_mem_fail;
316
336
if ((kmem_entry = pcidriver_kmem_find_entry(privdata, &(kmem_sync->handle))) == NULL)
317
337
return -EINVAL; /* kmem_handle is not valid */
320
if (!kmem_entry->dma_handle) {
321
mod_info_dbg("Instead of synchronization, we are mapping kmem_entry with id: %d\n", kmem_entry->id);
322
if (kmem_sync->dir == PCIDRIVER_DMA_TODEVICE)
323
kmem_entry->dma_handle = pci_map_single(privdata->pdev, (void*)kmem_entry->cpua, kmem_entry->size, PCI_DMA_TODEVICE);
325
kmem_entry->dma_handle = pci_map_single(privdata->pdev, (void*)kmem_entry->cpua, kmem_entry->size, PCI_DMA_FROMDEVICE);
327
kmem_sync->handle.pa = kmem_entry->dma_handle;
339
if (kmem_entry->direction == PCI_DMA_NONE)
330
342
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,11)
331
343
switch (kmem_sync->dir) {
332
case PCIDRIVER_DMA_TODEVICE:
333
pci_dma_sync_single_for_device( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_TODEVICE );
335
case PCIDRIVER_DMA_FROMDEVICE:
336
pci_dma_sync_single_for_cpu( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_FROMDEVICE );
338
case PCIDRIVER_DMA_BIDIRECTIONAL:
339
pci_dma_sync_single_for_device( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_BIDIRECTIONAL );
340
pci_dma_sync_single_for_cpu( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_BIDIRECTIONAL );
344
case PCILIB_KMEM_SYNC_TODEVICE:
345
pci_dma_sync_single_for_device( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, kmem_entry->direction );
347
case PCILIB_KMEM_SYNC_FROMDEVICE:
348
pci_dma_sync_single_for_cpu( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, kmem_entry->direction );
350
case PCILIB_KMEM_SYNC_BIDIRECTIONAL:
351
pci_dma_sync_single_for_device( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, kmem_entry->direction );
352
pci_dma_sync_single_for_cpu( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, kmem_entry->direction );
343
355
return -EINVAL; /* wrong direction parameter */
346
358
switch (kmem_sync->dir) {
347
case PCIDRIVER_DMA_TODEVICE:
348
pci_dma_sync_single( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_TODEVICE );
350
case PCIDRIVER_DMA_FROMDEVICE:
351
pci_dma_sync_single( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_FROMDEVICE );
353
case PCIDRIVER_DMA_BIDIRECTIONAL:
354
pci_dma_sync_single( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_BIDIRECTIONAL );
359
case PCILIB_KMEM_SYNC_TODEVICE:
360
pci_dma_sync_single( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, kmem_entry->direction );
362
case PCILIB_KMEM_SYNC_FROMDEVICE:
363
pci_dma_sync_single( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, kmem_entry->direction );
365
case PCILIB_KMEM_SYNC_BIDIRECTIONAL:
366
pci_dma_sync_single( privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, kmem_entry->direction );
357
369
return -EINVAL; /* wrong direction parameter */
402
414
/* Release DMA memory */
403
switch (kmem_entry->type) {
415
switch (kmem_entry->type&PCILIB_KMEM_TYPE_MASK) {
404
416
case PCILIB_KMEM_TYPE_CONSISTENT:
405
417
pci_free_consistent( privdata->pdev, kmem_entry->size, (void *)(kmem_entry->cpua), kmem_entry->dma_handle );
407
419
case PCILIB_KMEM_TYPE_PAGE:
408
if (kmem_entry->dma_handle) pci_unmap_single(privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_TODEVICE);
420
if (kmem_entry->dma_handle) {
421
if (kmem_entry->type == PCILIB_KMEM_TYPE_DMA_S2C_PAGE) {
422
pci_unmap_single(privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_TODEVICE);
423
} else if (kmem_entry->type == PCILIB_KMEM_TYPE_DMA_C2S_PAGE) {
424
pci_unmap_single(privdata->pdev, kmem_entry->dma_handle, kmem_entry->size, PCI_DMA_FROMDEVICE);
409
427
free_page((unsigned long)kmem_entry->cpua);