static int __videobuf_mmap_mapper(struct videobuf_queue *q, struct videobuf_buffer *buf, struct vm_area_struct *vma) { struct videobuf_vmalloc_memory *mem; struct videobuf_mapping *map; int retval, pages; dprintk(1, "%s\n", __func__); /* create mapping + update buffer list */ map = kzalloc(sizeof(struct videobuf_mapping), GFP_KERNEL); if (NULL == map) return -ENOMEM; buf->map = map; map->start = vma->vm_start; map->end = vma->vm_end; map->q = q; buf->baddr = vma->vm_start; mem = buf->priv; BUG_ON(!mem); MAGIC_CHECK(mem->magic, MAGIC_VMAL_MEM); pages = PAGE_ALIGN(vma->vm_end - vma->vm_start); mem->vmalloc = vmalloc_user(pages); if (!mem->vmalloc) { printk(KERN_ERR "vmalloc (%d pages) failed\n", pages); goto error; } dprintk(1, "vmalloc is at addr %p (%d pages)\n", mem->vmalloc, pages); /* Try to remap memory */ retval = remap_vmalloc_range(vma, mem->vmalloc, 0); if (retval < 0) { printk(KERN_ERR "mmap: remap failed with error %d. ", retval); vfree(mem->vmalloc); goto error; } vma->vm_ops = &videobuf_vm_ops; vma->vm_flags |= VM_DONTEXPAND | VM_RESERVED; vma->vm_private_data = map; dprintk(1, "mmap %p: q=%p %08lx-%08lx (%lx) pgoff %08lx buf %d\n", map, q, vma->vm_start, vma->vm_end, (long int)buf->bsize, vma->vm_pgoff, buf->i); videobuf_vm_open(vma); return 0; error: mem = NULL; kfree(map); return -ENOMEM; }
static int __videobuf_mmap_mapper(struct videobuf_queue *q, struct videobuf_buffer *buf, struct vm_area_struct *vma) { struct videobuf_marucam_memory *mem; struct videobuf_mapping *map; int retval, pages; map = kzalloc(sizeof(struct videobuf_mapping), GFP_KERNEL); if (NULL == map) { marucam_err("Failed to allocate the video buffer map\n"); return -ENOMEM; } buf->map = map; map->q = q; buf->baddr = vma->vm_start; mem = buf->priv; BUG_ON(!mem); mem->mapped = 1; MAGIC_CHECK(mem->magic, MAGIC_MARUCAM_MEM); pages = PAGE_ALIGN(vma->vm_end - vma->vm_start); vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot); retval = remap_pfn_range(vma, vma->vm_start, (((struct marucam_device *)q->priv_data)->mem_base + vma->vm_pgoff) >> PAGE_SHIFT, pages, vma->vm_page_prot); if (retval < 0) { marucam_err("Failed to remap the memory: %d\n", retval); mem->mapped = 0; mem = NULL; kfree(map); return -ENOMEM; } vma->vm_ops = &videobuf_vm_ops; vma->vm_flags |= VM_DONTEXPAND | VM_RESERVED; vma->vm_private_data = map; videobuf_vm_open(vma); return 0; }
static int __videobuf_mmap_mapper(struct videobuf_queue *q, struct vm_area_struct *vma) { struct videobuf_dma_contig_memory *mem; struct videobuf_mapping *map; unsigned int first; int retval; unsigned long size, offset = vma->vm_pgoff << PAGE_SHIFT; dev_dbg(q->dev, "%s\n", __func__); if (!(vma->vm_flags & VM_WRITE) || !(vma->vm_flags & VM_SHARED)) return -EINVAL; /* look for first buffer to map */ for (first = 0; first < VIDEO_MAX_FRAME; first++) { if (!q->bufs[first]) continue; if (V4L2_MEMORY_MMAP != q->bufs[first]->memory) continue; if (q->bufs[first]->boff == offset) break; } if (VIDEO_MAX_FRAME == first) { dev_dbg(q->dev, "invalid user space offset [offset=0x%lx]\n", offset); return -EINVAL; } /* create mapping + update buffer list */ map = kzalloc(sizeof(struct videobuf_mapping), GFP_KERNEL); if (!map) return -ENOMEM; q->bufs[first]->map = map; map->start = vma->vm_start; map->end = vma->vm_end; map->q = q; q->bufs[first]->baddr = vma->vm_start; mem = q->bufs[first]->priv; BUG_ON(!mem); MAGIC_CHECK(mem->magic, MAGIC_DC_MEM); mem->size = PAGE_ALIGN(q->bufs[first]->bsize); mem->vaddr = dma_alloc_coherent(q->dev, mem->size, &mem->dma_handle, GFP_KERNEL); if (!mem->vaddr) { dev_err(q->dev, "dma_alloc_coherent size %ld failed\n", mem->size); goto error; } dev_dbg(q->dev, "dma_alloc_coherent data is at addr %p (size %ld)\n", mem->vaddr, mem->size); /* Try to remap memory */ size = vma->vm_end - vma->vm_start; size = (size < mem->size) ? size : mem->size; vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot); retval = remap_pfn_range(vma, vma->vm_start, mem->dma_handle >> PAGE_SHIFT, size, vma->vm_page_prot); if (retval) { dev_err(q->dev, "mmap: remap failed with error %d. ", retval); dma_free_coherent(q->dev, mem->size, mem->vaddr, mem->dma_handle); goto error; } vma->vm_ops = &videobuf_vm_ops; vma->vm_flags |= VM_DONTEXPAND; vma->vm_private_data = map; dev_dbg(q->dev, "mmap %p: q=%p %08lx-%08lx (%lx) pgoff %08lx buf %d\n", map, q, vma->vm_start, vma->vm_end, (long int) q->bufs[first]->bsize, vma->vm_pgoff, first); videobuf_vm_open(vma); return 0; error: kfree(map); return -ENOMEM; }
static int __videobuf_mmap_mapper(struct videobuf_queue *q, struct vm_area_struct *vma) { struct videobuf_vmalloc_memory *mem; struct videobuf_mapping *map; unsigned int first; int retval, pages; unsigned long offset = vma->vm_pgoff << PAGE_SHIFT; dprintk(1, "%s\n", __func__); if (!(vma->vm_flags & VM_WRITE) || !(vma->vm_flags & VM_SHARED)) return -EINVAL; /* look for first buffer to map */ for (first = 0; first < VIDEO_MAX_FRAME; first++) { if (NULL == q->bufs[first]) continue; if (V4L2_MEMORY_MMAP != q->bufs[first]->memory) continue; if (q->bufs[first]->boff == offset) break; } if (VIDEO_MAX_FRAME == first) { dprintk(1,"mmap app bug: offset invalid [offset=0x%lx]\n", (vma->vm_pgoff << PAGE_SHIFT)); return -EINVAL; } /* create mapping + update buffer list */ map = kzalloc(sizeof(struct videobuf_mapping), GFP_KERNEL); if (NULL == map) return -ENOMEM; q->bufs[first]->map = map; map->start = vma->vm_start; map->end = vma->vm_end; map->q = q; q->bufs[first]->baddr = vma->vm_start; mem = q->bufs[first]->priv; BUG_ON(!mem); MAGIC_CHECK(mem->magic, MAGIC_VMAL_MEM); pages = PAGE_ALIGN(vma->vm_end - vma->vm_start); mem->vmalloc = vmalloc_user(pages); if (!mem->vmalloc) { printk(KERN_ERR "vmalloc (%d pages) failed\n", pages); goto error; } dprintk(1, "vmalloc is at addr %p (%d pages)\n", mem->vmalloc, pages); /* Try to remap memory */ retval = remap_vmalloc_range(vma, mem->vmalloc, 0); if (retval < 0) { printk(KERN_ERR "mmap: remap failed with error %d. ", retval); vfree(mem->vmalloc); goto error; } vma->vm_ops = &videobuf_vm_ops; vma->vm_flags |= VM_DONTEXPAND | VM_RESERVED; vma->vm_private_data = map; dprintk(1,"mmap %p: q=%p %08lx-%08lx (%lx) pgoff %08lx buf %d\n", map, q, vma->vm_start, vma->vm_end, (long int) q->bufs[first]->bsize, vma->vm_pgoff, first); videobuf_vm_open(vma); return 0; error: mem = NULL; kfree(map); return -ENOMEM; }
static int __videobuf_mmap_mapper(struct videobuf_queue *q, struct videobuf_buffer *buf, struct vm_area_struct *vma) { struct videobuf_contig_pmem *mem; struct videobuf_mapping *map; int retval; unsigned long size; D("%s\n", __func__); /* create mapping + update buffer list */ map = kzalloc(sizeof(struct videobuf_mapping), GFP_KERNEL); if (!map) { pr_err("%s: kzalloc failed.\n", __func__); return -ENOMEM; } buf->map = map; map->q = q; buf->baddr = vma->vm_start; mem = buf->priv; D("mem = 0x%x\n", (u32)mem); D("buf = 0x%x\n", (u32)buf); BUG_ON(!mem); MAGIC_CHECK(mem->magic, MAGIC_PMEM); mem->size = PAGE_ALIGN(buf->bsize); mem->y_off = 0; mem->cbcr_off = (buf->bsize)*2/3; if (buf->i >= 0 && buf->i <= 3) mem->buffer_type = OUTPUT_TYPE_P; else mem->buffer_type = OUTPUT_TYPE_V; buf->bsize = mem->size; mem->phyaddr = msm_mem_allocate(mem->size); if (IS_ERR((void *)mem->phyaddr)) { pr_err("%s : pmem memory allocation failed\n", __func__); goto error; } /* Try to remap memory */ size = vma->vm_end - vma->vm_start; size = (size < mem->size) ? size : mem->size; vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot); retval = remap_pfn_range(vma, vma->vm_start, mem->phyaddr >> PAGE_SHIFT, size, vma->vm_page_prot); if (retval) { pr_err("mmap: remap failed with error %d. ", retval); retval = msm_mem_free(mem->phyaddr); if (retval < 0) printk(KERN_ERR "%s: Invalid memory location\n", __func__); else { mem->phyaddr = 0; } goto error; } vma->vm_ops = &videobuf_vm_ops; vma->vm_flags |= VM_DONTEXPAND; vma->vm_private_data = map; D("mmap %p: q=%p %08lx-%08lx (%lx) pgoff %08lx buf %d\n", map, q, vma->vm_start, vma->vm_end, (long int)buf->bsize, vma->vm_pgoff, buf->i); videobuf_vm_open(vma); return 0; error: kfree(map); return -ENOMEM; }