void machine_kexec(struct kimage *image)
{
	unsigned long page_list;
	unsigned long reboot_code_buffer_phys;
	void *reboot_code_buffer;


	page_list = image->head & PAGE_MASK;

	/* we need both effective and real address here */
	reboot_code_buffer_phys =
	    page_to_pfn(image->control_code_page) << PAGE_SHIFT;
	reboot_code_buffer = page_address(image->control_code_page);

	/* Prepare parameters for reboot_code_buffer*/
	kexec_start_address = image->start;
	kexec_indirection_page = page_list;
	kexec_mach_type = machine_arch_type;
	kexec_boot_atags = image->start - KEXEC_ARM_ZIMAGE_OFFSET + KEXEC_ARM_ATAGS_OFFSET;

	/* copy our kernel relocation code to the control code page */
	memcpy(reboot_code_buffer,
	       relocate_new_kernel, relocate_new_kernel_size);


	flush_icache_range((unsigned long) reboot_code_buffer,
			   (unsigned long) reboot_code_buffer + KEXEC_CONTROL_PAGE_SIZE);
	printk(KERN_INFO "Bye!\n");

	cpu_proc_fin();
	setup_mm_for_reboot(0); /* mode is not used, so just pass 0*/
	__virt_to_phys(cpu_reset)(reboot_code_buffer_phys);
}
static int __init parse_tag_initrd(const struct tag *tag)
{
	printk(KERN_WARNING "ATAG_INITRD is deprecated; "
		"please update your bootloader.\n");
	phys_initrd_start = __virt_to_phys(tag->u.initrd.start);
	phys_initrd_size = tag->u.initrd.size;
	return 0;
}
Example #3
0
static int __init qrd7627a_logbuf_init(void)
{
	nzi_buf_item_type input;
	extern char __log_buf[];
	extern unsigned long totalram_pages;
	extern atomic_long_t vm_stat[];

#ifdef CONFIG_PRINTK
	/* send the kernel log address */
	input.extension.len = 0;
	input.address = (uint32_t)__virt_to_phys((unsigned long)__log_buf);
	input.size = (1 << CONFIG_LOG_BUF_SHIFT);
	strncpy(input.file_name, "dmesg", NZI_ITEM_FILE_NAME_LENGTH);
	input.file_name[NZI_ITEM_FILE_NAME_LENGTH - 1] = 0;
	send_modem_logaddr(&input);
#endif

	/* ******struct task_struct part ******/
	TASK_OFFSET_SEND(tasks, "tasks_of");
	TASK_OFFSET_SEND(thread_group, "tg_of");
	TASK_OFFSET_SEND(mm, "mm_of");
	TASK_OFFSET_SEND(comm, "comm_of");
	TASK_OFFSET_SEND(pid, "pid_of");
	TASK_OFFSET_SEND(tgid, "tgid_of");
	/* ******struct task_struct end ******/

	/* totalram_pages */
	input.extension.len = 1;
	input.extension.data[0] = (uint32_t)MEM_INFO_TAG;
	input.address = (uint32_t)__virt_to_phys((unsigned long)&totalram_pages);
	input.size = sizeof(totalram_pages);
	strncpy(input.file_name, "totalram", NZI_ITEM_FILE_NAME_LENGTH);
	input.file_name[NZI_ITEM_FILE_NAME_LENGTH - 1] = 0;
	send_modem_logaddr(&input);

	/* vm_stat[vm_stat[NR_VM_ZONE_STAT_ITEMS]; */
	input.extension.len = 1;
	input.extension.data[0] = (uint32_t)MEM_INFO_TAG;
	input.address = (uint32_t)__virt_to_phys((unsigned long)vm_stat);
	input.size = sizeof(vm_stat);
	strncpy(input.file_name, "vm_stat", NZI_ITEM_FILE_NAME_LENGTH);
	input.file_name[NZI_ITEM_FILE_NAME_LENGTH - 1] = 0;
	send_modem_logaddr(&input);

	return 0;
}
Example #4
0
/*
 * initial ram disk
 */
void __init setup_initrd(unsigned int start, unsigned int size)
{
#ifdef CONFIG_BLK_DEV_INITRD
	if (start == 0)
		size = 0;
	phys_initrd_start = __virt_to_phys(start);
	phys_initrd_size = size;
#endif
}
void machine_kexec(struct kimage *image)
{
	unsigned long page_list;
	unsigned long reboot_code_buffer_phys;
	void *reboot_code_buffer;

	arch_kexec();

	page_list = image->head & PAGE_MASK;

	/* we need both effective and real address here */
	reboot_code_buffer_phys =
	    page_to_pfn(image->control_code_page) << PAGE_SHIFT;
	reboot_code_buffer = page_address(image->control_code_page);

	/* Prepare parameters for reboot_code_buffer*/
	mem_text_write_kernel_word(&kexec_start_address, image->start);
	mem_text_write_kernel_word(&kexec_indirection_page, page_list);
	mem_text_write_kernel_word(&kexec_mach_type, machine_arch_type);
	mem_text_write_kernel_word(&kexec_boot_atags, image->start - KEXEC_ARM_ZIMAGE_OFFSET + KEXEC_ARM_ATAGS_OFFSET);

#ifdef CONFIG_KEXEC_HARDBOOT
	mem_text_write_kernel_word(&kexec_hardboot, image->hardboot);
#endif

	/* copy our kernel relocation code to the control code page */
	memcpy(reboot_code_buffer,
	       relocate_new_kernel, relocate_new_kernel_size);


	flush_icache_range((unsigned long) reboot_code_buffer,
			   (unsigned long) reboot_code_buffer + KEXEC_CONTROL_PAGE_SIZE);
	printk(KERN_INFO "Bye!\n");

	if (kexec_reinit)
		kexec_reinit();
	local_irq_disable();
	local_fiq_disable();
	setup_mm_for_reboot(0); /* mode is not used, so just pass 0*/
#ifdef CONFIG_KEXEC_HARDBOOT
	if (image->hardboot && kexec_hardboot_hook)
		/* Run any final machine-specific shutdown code. */
		kexec_hardboot_hook();
#endif
	flush_cache_all();
	outer_flush_all();
	outer_disable();
	cpu_proc_fin();
	outer_inv_all();
	flush_cache_all();
	__virt_to_phys(cpu_reset)(reboot_code_buffer_phys);
}
/* NOTE: the size requested by user already accounts for ramfile header */
static int ramfile_mmap(struct file *file, struct vm_area_struct *vma)
{
	int ret_val = 0;
	unsigned long usize = vma->vm_end - vma->vm_start;
	void* pbuf;

	/* Check we don't exhaust all system memory to prevent crash before EEH
		is done with saving logs. Use the total free for now */

	unsigned int avail_mem = global_page_state(NR_FREE_PAGES)*PAGE_SIZE;
	printk(KERN_ERR "ramfile_mmap(0x%x), available 0x%x\n", usize, avail_mem);
	if (avail_mem < RAMFILE_LOW_WATERMARK) {
		printk(KERN_ERR "Rejected\n");
		return -ENOMEM;
	}

	/* Note: kmalloc allocates physically continous memory.
	vmalloc would allocate potentially physically discontinuous memory.
	The advantage of vmalloc is that it would be able to allocate more
	memory when physical memory available is fragmented */
	pbuf = kmalloc(usize, GFP_KERNEL);
#ifdef RAMFILE_DEBUG
	printk(KERN_ERR "ramfile_mmap(0x%x): ka=%.8x ua=%.8x\n", usize, pbuf, (unsigned int)vma->vm_start);
#endif
	if (!pbuf)
		return -ENOMEM;

	/* Allocated. Map this to user space and let it fill in the data.
		We do not want to waste a whole page for the ramfile_desc header,
		so we map all the buffer to user space, which should reserved the
		header area.
		We will fill the header and link it into the ramdump when user
		space is done and calls unmap. This way user mistake corrupting
		the header will not compromise the kernel operation.*/
	vma->vm_pgoff = __phys_to_pfn(__virt_to_phys((unsigned)pbuf)); /* needed during unmap/close */

	vma->vm_flags |= (VM_RESERVED|VM_IO);
	vma->vm_page_prot = pgprot_noncached(vma->vm_page_prot);

	ret_val = remap_pfn_range(vma, (unsigned int)vma->vm_start,
				vma->vm_pgoff, usize, vma->vm_page_prot);
	if (ret_val < 0) {
		kfree(pbuf);
		return ret_val;
	}
	vma->vm_ops = &ramfile_vm_ops;
	return(0);
}
Example #7
0
static void __init
request_standard_resources(struct meminfo *mi, struct machine_desc *mdesc)
{
	struct resource *res;
	int i;

	kernel_code.start  = __virt_to_phys(init_mm.start_code);
	kernel_code.end    = __virt_to_phys(init_mm.end_code - 1);
	kernel_data.start  = __virt_to_phys(init_mm.end_code);
	kernel_data.end    = __virt_to_phys(init_mm.brk - 1);

	for (i = 0; i < mi->nr_banks; i++) {
		unsigned long virt_start, virt_end;

		if (mi->bank[i].size == 0)
			continue;

		virt_start = __phys_to_virt(mi->bank[i].start);
		virt_end   = virt_start + mi->bank[i].size - 1;

		res = alloc_bootmem_low(sizeof(*res));
		res->name  = "System RAM";
		res->start = __virt_to_phys(virt_start);
		res->end   = __virt_to_phys(virt_end);
		res->flags = IORESOURCE_MEM | IORESOURCE_BUSY;

		request_resource(&iomem_resource, res);

		if (kernel_code.start >= res->start &&
		    kernel_code.end <= res->end)
			request_resource(res, &kernel_code);
		if (kernel_data.start >= res->start &&
		    kernel_data.end <= res->end)
			request_resource(res, &kernel_data);
	}

	if (mdesc->video_start) {
		video_ram.start = mdesc->video_start;
		video_ram.end   = mdesc->video_end;
		request_resource(&iomem_resource, &video_ram);
	}

	/*
	 * Some machines don't have the possibility of ever
	 * possessing lp0, lp1 or lp2
	 */
	if (mdesc->reserve_lp0)
		request_resource(&ioport_resource, &lp0);
	if (mdesc->reserve_lp1)
		request_resource(&ioport_resource, &lp1);
	if (mdesc->reserve_lp2)
		request_resource(&ioport_resource, &lp2);
}
fsl_shw_return_t
do_scc_decrypt_region(fsl_shw_uco_t * user_ctx,
		      void *partition_base, uint32_t offset_bytes,
		      uint32_t byte_count, const uint8_t * black_data,
		      uint32_t * IV, fsl_shw_cypher_mode_t cypher_mode)
{
	scc_return_t scc_ret;
	fsl_shw_return_t retval = FSL_RETURN_ERROR_S;

#ifdef FSL_HAVE_SCC2

#ifdef DIAG_ADAPTOR
	uint32_t *owner_32 = (uint32_t *) & (owner_id);

	LOG_KDIAG_ARGS
	    ("partition base: %p, offset: %i, count: %i, black data: %p\n",
	     partition_base, offset_bytes, byte_count, (void *)black_data);
#endif

	(void)user_ctx;

	/* The SCC2 DMA engine will be reading from the black ram, so we need to
	 * make sure that the data is pushed out of the cache.  Note that the red
	 * ram is not an issue because it is mapped with the cache disabled.
	 */
	os_cache_flush_range(black_data, byte_count);

	scc_ret =
	    scc_decrypt_region((uint32_t) partition_base, offset_bytes,
			       byte_count,
			       (uint8_t *) __virt_to_phys(black_data), IV,
			       cypher_mode);

	if (scc_ret == SCC_RET_OK) {
		retval = FSL_RETURN_OK_S;
	} else {
		retval = FSL_RETURN_ERROR_S;
	}

#else
	(void)scc_ret;
#endif				/* FSL_HAVE_SCC2 */

	return retval;
}
/*
 * partition_base - physical address of the partition
 * offset - offset, in blocks, of the data from the start of the partition
 * length - length, in bytes, of the data to be encrypted (multiple of 4)
 * black_data - virtual address that the encrypted data should be stored at
 * Note that this virtual address must be translatable using the __virt_to_phys
 * macro; ie, it can't be a specially mapped address.  To do encryption with those
 * addresses, use the scc_encrypt_region function directly.  This is to make
 * this function compatible with the user mode declaration, which does not know
 * the physical addresses of the data it is using.
 */
fsl_shw_return_t
do_scc_encrypt_region(fsl_shw_uco_t * user_ctx,
		      void *partition_base, uint32_t offset_bytes,
		      uint32_t byte_count, uint8_t * black_data,
		      uint32_t * IV, fsl_shw_cypher_mode_t cypher_mode)
{
	scc_return_t scc_ret;
	fsl_shw_return_t retval = FSL_RETURN_ERROR_S;

#ifdef FSL_HAVE_SCC2

#ifdef DIAG_ADAPTOR
	uint32_t *owner_32 = (uint32_t *) & (owner_id);

	LOG_KDIAG_ARGS
	    ("partition base: %p, offset: %i, count: %i, black data: %p\n",
	     partition_base, offset_bytes, byte_count, (void *)black_data);
#endif
	(void)user_ctx;

	os_cache_flush_range(black_data, byte_count);

	scc_ret =
	    scc_encrypt_region((uint32_t) partition_base, offset_bytes,
			       byte_count, __virt_to_phys(black_data), IV,
			       cypher_mode);

	if (scc_ret == SCC_RET_OK) {
		retval = FSL_RETURN_OK_S;
	} else {
		retval = FSL_RETURN_ERROR_S;
	}

	/* The SCC2 DMA engine should have written to the black ram, so we need to
	 * invalidate that region of memory.  Note that the red ram is not an
	 * because it is mapped with the cache disabled.
	 */
	os_cache_inv_range(black_data, byte_count);

#else
	(void)scc_ret;
#endif				/* FSL_HAVE_SCC2 */

	return retval;
}
Example #10
0
/*
 *  Main dma routine, requests dma according where you are in main alsa buffer
 */
static void audio_process_dma(struct audio_stream_a *s)
{
	struct snd_pcm_substream *substream = s->stream;
	struct snd_pcm_runtime *runtime;
	unsigned int dma_size;
	unsigned int offset;
	dma_addr_t dma_base;
	int ret = 0;
	//int stream_id = substream->pstr->stream;
	
	DPRINTK("s: %d, dmach: %d. active: %d", (int)s, s->dmach, s->active);
	
	if (s->active) {
		substream = s->stream;
		runtime = substream->runtime;
		dma_size = frames_to_bytes(runtime, runtime->period_size);
		/*DPRINTK("frame_bits=%d, period_size=%d, dma_size 1=%d",
			runtime->frame_bits, (int)runtime->period_size, dma_size);*/
		if (dma_size > MAX_DMA_SIZE)
			dma_size = CUT_DMA_SIZE;
		offset = dma_size * s->period;

		/*DPRINTK("offset: 0x%x, ->dma_area: 0x%x, ->dma_addr: 0x%x, final addr: 0x%x",
			offset, (unsigned int)runtime->dma_area, runtime->dma_addr, runtime->dma_addr+offset);*/

		dma_base = __virt_to_phys((dma_addr_t)runtime->dma_area);
		
		if (((runtime->channels == 2) && (runtime->format == SNDRV_PCM_FORMAT_S16_LE))  ||
			((runtime->channels == 1) && (runtime->format == SNDRV_PCM_FORMAT_S16_LE))) {
			ret = wmt_start_dma(s->dmach, runtime->dma_addr + offset, 0, dma_size);
		}

		if (ret) {
			printk(KERN_ERR "audio_process_dma: cannot queue DMA buffer (%i) \n", ret);
			return;
		}

		s->period++;
		s->period %= runtime->periods;
		s->periods++;
		s->offset = offset;
	}
}
static void load_file(char *filename, int count, unsigned long *segments)
{
        mm_segment_t old_fs = get_fs();
        int fd, i;

        void *ptr;
        unsigned long c = 0;

        int segc = 0;

        set_fs(KERNEL_DS);
        if ((fd = sys_open(filename, O_RDONLY, 0)) < 0) 
                panic("%s: open failed (%d)\n", filename, fd);
        while (c < count) {

        retry:
                while (!(ptr = kmalloc(segment_size, GFP_KERNEL))) {
                        if (segment_size == MIN_SEGMENT_SIZE)
                                panic("load_file: Out of memory\n");
                        segment_size >>= 1;
                }
                if (virt_to_phys(ptr) < MIN_ADDR) {
                        printk("not using %d bytes reserved memory at %p / %p\n", segment_size, ptr, __virt_to_phys(ptr));
                        goto retry;
                }

                i = sys_read(fd, ptr, segment_size);
                printk("loaded %d of %d bytes at %p / %p\n", i, count, ptr, __virt_to_phys(ptr));
                if (i > 0) {
                        *segments++ = virt_to_phys(ptr);
                        *segments++ = (unsigned long)i;
                        c += i;
                        segc++;
                }
                if (i < 0)
                        panic("load_file: read error\n");
        }
        *segments = 0;
        sys_close(fd);
        printk("%s: OK (%d segments)\n", filename, segc);
        set_fs(old_fs);
}
Example #12
0
/* Prototype: fasdmatype_t eesoxscsi_dma_setup(host, SCpnt, direction, min_type)
 * Purpose  : initialises DMA/PIO
 * Params   : host      - host
 *	      SCpnt     - command
 *	      direction - DMA on to/off of card
 *	      min_type  - minimum DMA support that we must have for this transfer
 * Returns  : type of transfer to be performed
 */
static fasdmatype_t
eesoxscsi_dma_setup(struct Scsi_Host *host, Scsi_Pointer *SCp,
		       fasdmadir_t direction, fasdmatype_t min_type)
{
	EESOXScsi_Info *info = (EESOXScsi_Info *)host->hostdata;
	int dmach = host->dma_channel;

	if (dmach != NO_DMA &&
	    (min_type == fasdma_real_all || SCp->this_residual >= 512)) {
		int buf;

		for(buf = 1; buf <= SCp->buffers_residual &&
			     buf < NR_SG; buf++) {
			info->dmasg[buf].address = __virt_to_bus(
				(unsigned long)SCp->buffer[buf].address);
			info->dmasg[buf].length = SCp->buffer[buf].length;

			eesoxscsi_invalidate(SCp->buffer[buf].address,
						SCp->buffer[buf].length,
						direction);
		}

		info->dmasg[0].address = __virt_to_phys((unsigned long)SCp->ptr);
		info->dmasg[0].length = SCp->this_residual;
		eesoxscsi_invalidate(SCp->ptr,
					SCp->this_residual, direction);

		disable_dma(dmach);
		set_dma_sg(dmach, info->dmasg, buf);
		set_dma_mode(dmach,
			     direction == DMA_OUT ? DMA_MODE_WRITE :
						    DMA_MODE_READ);
		enable_dma(dmach);
		return fasdma_real_all;
	}
	/*
	 * We don't do DMA, we only do slow PIO
	 *
	 * Some day, we will do Pseudo DMA
	 */
	return fasdma_pseudo;
}
Example #13
0
/* Prototype: fasdmatype_t powertecscsi_dma_setup(host, SCpnt, direction, min_type)
 * Purpose  : initialises DMA/PIO
 * Params   : host      - host
 *	      SCpnt     - command
 *	      direction - DMA on to/off of card
 *	      min_type  - minimum DMA support that we must have for this transfer
 * Returns  : type of transfer to be performed
 */
static fasdmatype_t
powertecscsi_dma_setup(struct Scsi_Host *host, Scsi_Pointer *SCp,
		       fasdmadir_t direction, fasdmatype_t min_type)
{
	PowerTecScsi_Info *info = (PowerTecScsi_Info *)host->hostdata;
	int dmach = host->dma_channel;

	if (dmach != NO_DMA &&
	    (min_type == fasdma_real_all || SCp->this_residual >= 512)) {
		int buf;

		for (buf = 1; buf <= SCp->buffers_residual &&
			      buf < NR_SG; buf++) {
			info->dmasg[buf].address = __virt_to_bus(
				(unsigned long)SCp->buffer[buf].address);
			info->dmasg[buf].length = SCp->buffer[buf].length;

			powertecscsi_invalidate(SCp->buffer[buf].address,
						SCp->buffer[buf].length,
						direction);
		}

		info->dmasg[0].address = __virt_to_phys((unsigned long)SCp->ptr);
		info->dmasg[0].length = SCp->this_residual;
		powertecscsi_invalidate(SCp->ptr,
					SCp->this_residual, direction);

		disable_dma(dmach);
		set_dma_sg(dmach, info->dmasg, buf);
		set_dma_mode(dmach,
			     direction == DMA_OUT ? DMA_MODE_WRITE :
						    DMA_MODE_READ);
		enable_dma(dmach);
		return fasdma_real_all;
	}

	/*
	 * If we're not doing DMA,
	 *  we'll do slow PIO
	 */
	return fasdma_pio;
}
void*
osl_dma_alloc_consistent(osl_t *osh, uint size, uint16 align_bits, uint *alloced, ulong *pap)
{
	void *va;
	uint16 align = (1 << align_bits);
	ASSERT((osh && (osh->magic == OS_HANDLE_MAGIC)));

	if (!ISALIGNED(DMA_CONSISTENT_ALIGN, align))
		size += align;
	*alloced = size;

#ifdef __ARM_ARCH_7A__
	va = kmalloc(size, GFP_ATOMIC | __GFP_ZERO);
	if (va)
		*pap = (ulong)__virt_to_phys((ulong)va);
#else
	va = pci_alloc_consistent(osh->pdev, size, (dma_addr_t*)pap);
#endif
	return va;
}
void machine_kexec(struct kimage *image)
{
	unsigned long page_list;
	unsigned long reboot_code_buffer_phys;
	void *reboot_code_buffer;
	arch_kexec();
	page_list = image->head & PAGE_MASK;
	reboot_code_buffer_phys =
	    page_to_pfn(image->control_code_page) << PAGE_SHIFT;
	reboot_code_buffer = page_address(image->control_code_page);
	kexec_start_address = image->start;
	kexec_indirection_page = page_list;
	kexec_mach_type = machine_arch_type;
	kexec_boot_atags = image->start - KEXEC_ARM_ZIMAGE_OFFSET + KEXEC_ARM_ATAGS_OFFSET;
	memcpy(reboot_code_buffer,
	       relocate_new_kernel, relocate_new_kernel_size);

	flush_icache_range((unsigned long) reboot_code_buffer,
			   (unsigned long) reboot_code_buffer + KEXEC_CONTROL_PAGE_SIZE);
	printk(KERN_INFO "Bye!\n");
	cpu_proc_fin();
	__virt_to_phys(cpu_reset)(reboot_code_buffer_phys);
}
Example #16
0
static void switch_pgd(unsigned long pgd, int pid) {
  /* The second parameter is context id, we don't support it. */
  cpu_v6_switch_mm(__virt_to_phys(pgd), 0);
}
Example #17
0
static int setup_rt_frame(struct ksignal *ksig, sigset_t *set,
			  struct pt_regs *regs)
{
	struct rt_sigframe __user *frame;
	int err = 0, sig = ksig->sig;
	unsigned long address = 0;
#ifdef CONFIG_MMU
	pmd_t *pmdp;
	pte_t *ptep;
#endif

	frame = get_sigframe(ksig, regs, sizeof(*frame));

	if (!access_ok(VERIFY_WRITE, frame, sizeof(*frame)))
		return -EFAULT;

	if (ksig->ka.sa.sa_flags & SA_SIGINFO)
		err |= copy_siginfo_to_user(&frame->info, &ksig->info);

	/* Create the ucontext. */
	err |= __put_user(0, &frame->uc.uc_flags);
	err |= __put_user(NULL, &frame->uc.uc_link);
	err |= __save_altstack(&frame->uc.uc_stack, regs->r1);
	err |= setup_sigcontext(&frame->uc.uc_mcontext,
			regs, set->sig[0]);
	err |= __copy_to_user(&frame->uc.uc_sigmask, set, sizeof(*set));

	/* Set up to return from userspace. If provided, use a stub
	 already in userspace. */
	/* minus 8 is offset to cater for "rtsd r15,8" */
	/* addi r12, r0, __NR_sigreturn */
	err |= __put_user(0x31800000 | __NR_rt_sigreturn ,
			frame->tramp + 0);
	/* brki r14, 0x8 */
	err |= __put_user(0xb9cc0008, frame->tramp + 1);

	/* Return from sighandler will jump to the tramp.
	 Negative 8 offset because return is rtsd r15, 8 */
	regs->r15 = ((unsigned long)frame->tramp)-8;

	address = ((unsigned long)frame->tramp);
#ifdef CONFIG_MMU
	pmdp = pmd_offset(pud_offset(
			pgd_offset(current->mm, address),
					address), address);

	preempt_disable();
	ptep = pte_offset_map(pmdp, address);
	if (pte_present(*ptep)) {
		address = (unsigned long) page_address(pte_page(*ptep));
		/* MS: I need add offset in page */
		address += ((unsigned long)frame->tramp) & ~PAGE_MASK;
		/* MS address is virtual */
		address = __virt_to_phys(address);
		invalidate_icache_range(address, address + 8);
		flush_dcache_range(address, address + 8);
	}
	pte_unmap(ptep);
	preempt_enable();
#else
	flush_icache_range(address, address + 8);
	flush_dcache_range(address, address + 8);
#endif
	if (err)
		return -EFAULT;

	/* Set up registers for signal handler */
	regs->r1 = (unsigned long) frame;

	/* Signal handler args: */
	regs->r5 = sig; /* arg 0: signum */
	regs->r6 = (unsigned long) &frame->info; /* arg 1: siginfo */
	regs->r7 = (unsigned long) &frame->uc; /* arg2: ucontext */
	/* Offset to handle microblaze rtid r14, 0 */
	regs->pc = (unsigned long)ksig->ka.sa.sa_handler;

#ifdef DEBUG_SIG
	pr_info("SIG deliver (%s:%d): sp=%p pc=%08lx\n",
		current->comm, current->pid, frame, regs->pc);
#endif

	return 0;
}
Example #18
0
static void __iomem *__ioremap(phys_addr_t addr, unsigned long size,
		unsigned long flags)
{
	unsigned long v, i;
	phys_addr_t p;
	int err;

	/*
	 * Choose an address to map it to.
	 * Once the vmalloc system is running, we use it.
	 * Before then, we use space going down from ioremap_base
	 * (ioremap_bot records where we're up to).
	 */
	p = addr & PAGE_MASK;
	size = PAGE_ALIGN(addr + size) - p;

	/*
	 * Don't allow anybody to remap normal RAM that we're using.
	 * mem_init() sets high_memory so only do the check after that.
	 *
	 * However, allow remap of rootfs: TBD
	 */

	if (mem_init_done &&
		p >= memory_start && p < virt_to_phys(high_memory) &&
		!(p >= __virt_to_phys((phys_addr_t)__bss_stop) &&
		p < __virt_to_phys((phys_addr_t)__bss_stop))) {
		pr_warn("__ioremap(): phys addr "PTE_FMT" is RAM lr %pf\n",
			(unsigned long)p, __builtin_return_address(0));
		return NULL;
	}

	if (size == 0)
		return NULL;

	/*
	 * Is it already mapped? If the whole area is mapped then we're
	 * done, otherwise remap it since we want to keep the virt addrs for
	 * each request contiguous.
	 *
	 * We make the assumption here that if the bottom and top
	 * of the range we want are mapped then it's mapped to the
	 * same virt address (and this is contiguous).
	 *  -- Cort
	 */

	if (mem_init_done) {
		struct vm_struct *area;
		area = get_vm_area(size, VM_IOREMAP);
		if (area == NULL)
			return NULL;
		v = (unsigned long) area->addr;
	} else {
		v = (ioremap_bot -= size);
	}

	if ((flags & _PAGE_PRESENT) == 0)
		flags |= _PAGE_KERNEL;
	if (flags & _PAGE_NO_CACHE)
		flags |= _PAGE_GUARDED;

	err = 0;
	for (i = 0; i < size && err == 0; i += PAGE_SIZE)
		err = map_page(v + i, p + i, flags);
	if (err) {
		if (mem_init_done)
			vfree((void *)v);
		return NULL;
	}

	return (void __iomem *) (v + ((unsigned long)addr & ~PAGE_MASK));
}
Example #19
0
static int s3c_mfc_ioctl(struct inode *inode, struct file *file, unsigned
		int cmd, unsigned long arg)
{
	int		ret	= 0;
	MFCInstCtx	*pMfcInst;
	MFC_HANDLE	*handle;
	unsigned char	*OutBuf	= NULL;
	MFC_CODECMODE	codec_mode	= 0;
	int		buf_size;
	unsigned int	tmp;
	MFC_ARGS	args;
	enc_info_t	enc_info;

// modified by RainAde for header type of mpeg4 (+ VOS/VO)
#if 1
	// Hdr0 : SPS or VOL
	// Hdr1 : PPS or VOS
	// Hdr2 : VO (VIS)
	int 	        nStrmLen, nHdrLen, nHdr0Len, nHdr1Len, nHdr2Len;
#else 
// modified by RainAde for composer interface
	int 	        nStrmLen, nHdrLen, nSps, nPps;
#endif

	void		*temp;
	unsigned int		vir_mv_addr;
	unsigned int		vir_mb_type_addr;

	
	//////////////////////
	//	Parameter Check	//
	//////////////////////
	handle = (MFC_HANDLE *)file->private_data;
	if (handle->mfc_inst == NULL) {
		return -EFAULT;
	}

	pMfcInst = handle->mfc_inst;


	switch(cmd)
	{
		case IOCTL_MFC_MPEG4_ENC_INIT:
		case IOCTL_MFC_H264_ENC_INIT:
		case IOCTL_MFC_H263_ENC_INIT:
			MFC_Mutex_Lock();
			LOG_MSG(LOG_TRACE, "mfc_ioctl", "cmd = %d\r\n", cmd);

			Copy_From_User(&args.enc_init, (MFC_ENC_INIT_ARG *)arg, sizeof(MFC_ENC_INIT_ARG));
			
			if ( cmd == IOCTL_MFC_MPEG4_ENC_INIT )
				codec_mode = MP4_ENC;
			else if ( cmd == IOCTL_MFC_H264_ENC_INIT )
				codec_mode = AVC_ENC;
			else if ( cmd == IOCTL_MFC_H263_ENC_INIT )
				codec_mode = H263_ENC;
			
			//////////////////////////////
			//	Initialize MFC Instance	//
			//////////////////////////////
			enc_info.width			= args.enc_init.in_width;
			enc_info.height			= args.enc_init.in_height;
			enc_info.bitrate		= args.enc_init.in_bitrate;
			enc_info.gopNum			= args.enc_init.in_gopNum;
			enc_info.frameRateRes	= args.enc_init.in_frameRateRes;
			enc_info.frameRateDiv	= args.enc_init.in_frameRateDiv;
			
			ret = MFCInst_Enc_Init(pMfcInst, codec_mode, &enc_info);
			
			args.enc_init.ret_code = ret;
			Copy_To_User((MFC_ENC_INIT_ARG *)arg, &args.enc_init, sizeof(MFC_ENC_INIT_ARG));
			
			MFC_Mutex_Release();
			break;
			
		case IOCTL_MFC_MPEG4_ENC_EXE:
		case IOCTL_MFC_H264_ENC_EXE:
		case IOCTL_MFC_H263_ENC_EXE:
			MFC_Mutex_Lock();

			Copy_From_User(&args.enc_exe, (MFC_ENC_EXE_ARG *)arg, sizeof(MFC_ENC_EXE_ARG));

			tmp = (pMfcInst->width * pMfcInst->height * 3) >> 1;
        
                        // from 2.8.5
			//dmac_clean_range(pMfcInst->pFramBuf, pMfcInst->pFramBuf + tmp);
			//outer_clean_range(__pa(pMfcInst->pFramBuf), __pa(pMfcInst->pFramBuf + tmp));
			// from 2.8.5 : cache flush
			cpu_cache.flush_kern_all();
			
			//////////////////////////
			//	Decode MFC Instance	//
			//////////////////////////

			// modified by RainAde for composer interface
			//ret = MFCInst_Encode(pMfcInst, &nStrmLen, &nHdrLen, &nHdr0Len, &nHdr1Len);
			// modified by RainAde for header type of mpeg4 (+ VOS/VO)
			ret = MFCInst_Encode(pMfcInst, &nStrmLen, &nHdrLen, &nHdr0Len, &nHdr1Len, &nHdr2Len);
			
                        // from 2.8.5
                        //dmac_clean_range(pMfcInst->pStrmBuf, pMfcInst->pStrmBuf + MFC_LINE_BUF_SIZE_PER_INSTANCE);
			//outer_clean_range(__pa(pMfcInst->pStrmBuf), __pa(pMfcInst->pStrmBuf + MFC_LINE_BUF_SIZE_PER_INSTANCE));
			
			args.enc_exe.ret_code	= ret;
			if (ret == MFCINST_RET_OK) {
				args.enc_exe.out_encoded_size = nStrmLen;
				args.enc_exe.out_header_size  = nHdrLen;
// modified by RainAde for composer interface
				args.enc_exe.out_header0_size  = nHdr0Len;
				args.enc_exe.out_header1_size  = nHdr1Len;	
				// modified by RainAde for header type of mpeg4 (+ VOS/VO)
				args.enc_exe.out_header2_size  = nHdr2Len;					
			}
			Copy_To_User((MFC_ENC_EXE_ARG *)arg, &args.enc_exe, sizeof(MFC_ENC_EXE_ARG));
			
			// added by RainAde for cache coherency
			cpu_cache.dma_inv_range(pMfcInst->pStrmBuf, pMfcInst->pStrmBuf + MFC_LINE_BUF_SIZE_PER_INSTANCE);
			
			MFC_Mutex_Release();
			break;
			
		case IOCTL_MFC_MPEG4_DEC_INIT:
		case IOCTL_MFC_H264_DEC_INIT:
		case IOCTL_MFC_H263_DEC_INIT:
		case IOCTL_MFC_VC1_DEC_INIT:
			MFC_Mutex_Lock();
#ifdef CONFIG_MACH_SATURN
			lcd_gamma_change(LCD_VIDEO); // when decoder init to start playing video, AMOLED gamma set to video mode
#endif

			Copy_From_User(&args.dec_init, (MFC_DEC_INIT_ARG *)arg, sizeof(MFC_DEC_INIT_ARG));
			
			// yj: fix the PiP problem
			cpu_cache.flush_kern_all();

			if ( cmd == IOCTL_MFC_MPEG4_DEC_INIT )
				codec_mode = MP4_DEC;
			else if ( cmd == IOCTL_MFC_H264_DEC_INIT )
				codec_mode = AVC_DEC;
			else if ( cmd == IOCTL_MFC_H263_DEC_INIT)
				codec_mode = H263_DEC;
			else {
				codec_mode = VC1_DEC;
			}
			
			//////////////////////////////
			//	Initialize MFC Instance	//
			//////////////////////////////
			ret = MFCInst_Init(pMfcInst, codec_mode, args.dec_init.in_strmSize);

			args.dec_init.ret_code	= ret;
			if (ret == MFCINST_RET_OK) {
				args.dec_init.out_width	     = pMfcInst->width;
				args.dec_init.out_height     = pMfcInst->height;
				args.dec_init.out_buf_width  = pMfcInst->buf_width;
				args.dec_init.out_buf_height = pMfcInst->buf_height;
			}
			Copy_To_User((MFC_DEC_INIT_ARG *)arg, &args.dec_init, sizeof(MFC_DEC_INIT_ARG));

			MFC_Mutex_Release();
			break;
			
		case IOCTL_MFC_MPEG4_DEC_EXE:
		case IOCTL_MFC_H264_DEC_EXE:
		case IOCTL_MFC_H263_DEC_EXE:
		case IOCTL_MFC_VC1_DEC_EXE:
			MFC_Mutex_Lock();

			Copy_From_User(&args.dec_exe, (MFC_DEC_EXE_ARG *)arg, sizeof(MFC_DEC_EXE_ARG));

			// from 2.8.5
			//dmac_clean_range(pMfcInst->pStrmBuf, pMfcInst->pStrmBuf + MFC_LINE_BUF_SIZE_PER_INSTANCE);
			//outer_clean_range(__pa(pMfcInst->pStrmBuf), __pa(pMfcInst->pStrmBuf + MFC_LINE_BUF_SIZE_PER_INSTANCE));
			// from 2.8.5 : cache flush
			cpu_cache.flush_kern_all();
			
			if (pMfcInst->inbuf_type == DEC_INBUF_LINE_BUF) {
				ret = MFCInst_Decode(pMfcInst, args.dec_exe.in_strmSize); 
			}
			else if (pMfcInst->inbuf_type == DEC_INBUF_RING_BUF) {
				ret = MFCInst_Decode_Stream(pMfcInst, args.dec_exe.in_strmSize);
			}
			else {
				LOG_MSG(LOG_ERROR, "s3c_mfc_ioctl", "Buffer type is not defined.\n");
				MFC_Mutex_Release();
				args.dec_exe.ret_code = -1;
				return -EINVAL;
			}

			args.dec_exe.ret_code = ret;
			Copy_To_User((MFC_DEC_EXE_ARG *)arg, &args.dec_exe, sizeof(MFC_DEC_EXE_ARG));

			// added by RainAde for cache coherency
			tmp = (pMfcInst->width * pMfcInst->height * 3) >> 1;
			cpu_cache.dma_inv_range(pMfcInst->pFramBuf, pMfcInst->pFramBuf + tmp);

			MFC_Mutex_Release();
			break;
			
		case IOCTL_MFC_GET_RING_BUF_ADDR:
			MFC_Mutex_Lock();

			Copy_From_User(&args.get_buf_addr, (MFC_GET_BUF_ADDR_ARG *)arg, sizeof(MFC_GET_BUF_ADDR_ARG));

			ret = MFCInst_GetRingBuf(pMfcInst, &OutBuf, &buf_size); 
			
			args.get_buf_addr.out_buf_size	= buf_size;
			args.get_buf_addr.out_buf_addr	= args.get_buf_addr.in_usr_data + ((int)(OutBuf - GetDataBufVirAddr()));
			args.get_buf_addr.ret_code		= ret;
			Copy_To_User((MFC_GET_BUF_ADDR_ARG *)arg, &args.get_buf_addr, sizeof(MFC_GET_BUF_ADDR_ARG));
			
			MFC_Mutex_Release();
			break;
			
		case IOCTL_MFC_GET_LINE_BUF_ADDR:
			MFC_Mutex_Lock();

			Copy_From_User(&args.get_buf_addr, (MFC_GET_BUF_ADDR_ARG *)arg, sizeof(MFC_GET_BUF_ADDR_ARG));

			ret = MFCInst_GetLineBuf(pMfcInst, &OutBuf, &buf_size);
			
			args.get_buf_addr.out_buf_size	= buf_size;
			args.get_buf_addr.out_buf_addr	= args.get_buf_addr.in_usr_data + (OutBuf - GetDataBufVirAddr());
			args.get_buf_addr.ret_code		= ret;

			Copy_To_User((MFC_GET_BUF_ADDR_ARG *)arg, &args.get_buf_addr, sizeof(MFC_GET_BUF_ADDR_ARG));

			MFC_Mutex_Release();
			break;
			
		case IOCTL_MFC_GET_DBK_BUF_ADDR:	// newly added by yj: returns to DBK_BUF' virtual address and its size.
			MFC_Mutex_Lock();

			Copy_From_User(&args.get_dbkbuf_addr, (MFC_GET_DBK_BUF_ARG *)arg, sizeof(MFC_GET_DBK_BUF_ARG));

			if (pMfcInst->isMp4DbkOn != 1) {
				LOG_MSG(LOG_ERROR, "s3c_mfc_ioctl", "MFC DBK_BUF is not internally allocated yet.\n");
				MFC_Mutex_Release();
				return -EFAULT;
			}

			args.get_dbkbuf_addr.out_buf_size	= (pMfcInst->buf_width * pMfcInst->buf_height * 3) >> 1;
			args.get_dbkbuf_addr.out_buf_addr = args.get_dbkbuf_addr.in_usr_mapped_addr + 
											((unsigned int)GetDbkBufVirAddr() - (unsigned int)GetDataBufVirAddr());
			
			args.get_dbkbuf_addr.ret_code	= MFCINST_RET_OK;
			
			Copy_To_User((MFC_GET_DBK_BUF_ARG *)arg, &args.get_dbkbuf_addr, sizeof(MFC_GET_DBK_BUF_ARG));
			
			MFC_Mutex_Release();
			break;
			
		case IOCTL_MFC_GET_FRAM_BUF_ADDR:
			MFC_Mutex_Lock();

			Copy_From_User(&args.get_buf_addr, (MFC_GET_BUF_ADDR_ARG *)arg, sizeof(MFC_GET_BUF_ADDR_ARG));

			if (pMfcInst->pFramBuf == NULL) {
				LOG_MSG(LOG_ERROR, "s3c_mfc_ioctl", "MFC Frame buffer is not internally allocated yet.\n");
				MFC_Mutex_Release();
				return -EFAULT;
			}

			// FRAM_BUF address is calculated differently for Encoder and Decoder.
			switch (pMfcInst->codec_mode) {
			case MP4_DEC:
			case AVC_DEC:
			case VC1_DEC:
			case H263_DEC:
				// Decoder case
				args.get_buf_addr.out_buf_size	= (pMfcInst->buf_width * pMfcInst->buf_height * 3) >> 1;

				tmp	= (unsigned int)args.get_buf_addr.in_usr_data + ( ((unsigned int) pMfcInst->pFramBuf)	\
					+ (pMfcInst->idx) * (args.get_buf_addr.out_buf_size + ZERO_COPY_HDR_SIZE) - (unsigned int)GetDataBufVirAddr() );
#if (MFC_ROTATE_ENABLE == 1)
				if ( (pMfcInst->codec_mode != VC1_DEC) && (pMfcInst->PostRotMode & 0x0010) ) {
					tmp	= (unsigned int)args.get_buf_addr.in_usr_data + ( ((unsigned int) pMfcInst->pFramBuf)	\
					+ (pMfcInst->frambufCnt) * (args.get_buf_addr.out_buf_size + ZERO_COPY_HDR_SIZE) - (unsigned int)GetDataBufVirAddr() );	
				}
#endif
				args.get_buf_addr.out_buf_addr = tmp;
				break;

			case MP4_ENC:
			case AVC_ENC:
			case H263_ENC:
				// Encoder case
				tmp = (pMfcInst->width * pMfcInst->height * 3) >> 1;
				args.get_buf_addr.out_buf_addr = args.get_buf_addr.in_usr_data + (pMfcInst->idx * tmp) + (int)(pMfcInst->pFramBuf - GetDataBufVirAddr());
				break;
			}

			args.get_buf_addr.ret_code	= MFCINST_RET_OK;
			Copy_To_User((MFC_GET_BUF_ADDR_ARG *)arg, &args.get_buf_addr, sizeof(MFC_GET_BUF_ADDR_ARG));

			MFC_Mutex_Release();
			break;
			
		case IOCTL_MFC_GET_PHY_FRAM_BUF_ADDR:
			MFC_Mutex_Lock();

			Copy_From_User(&args.get_buf_addr, (MFC_GET_BUF_ADDR_ARG *)arg, sizeof(MFC_GET_BUF_ADDR_ARG));

			args.get_buf_addr.out_buf_size	= (pMfcInst->buf_width * pMfcInst->buf_height * 3) >> 1;
//			args.get_buf_addr.out_buf_size	= ((pMfcInst->width+2*DIVX_PADDING) * (pMfcInst->height+2*DIVX_PADDING) * 3) >> 1;
		tmp	= (unsigned int)S3C6400_BASEADDR_MFC_DATA_BUF + ( ((unsigned int) pMfcInst->pFramBuf)	\
			+ (pMfcInst->idx) * (args.get_buf_addr.out_buf_size + ZERO_COPY_HDR_SIZE) - (unsigned int)GetDataBufVirAddr() );

//.[ i: sichoi 081103 (ROTATE)
#if (MFC_ROTATE_ENABLE == 1)
        if ( (pMfcInst->codec_mode != VC1_DEC) && (pMfcInst->PostRotMode & 0x0010) ) 
		{
            tmp = (unsigned int)S3C6400_BASEADDR_MFC_DATA_BUF + ( ((unsigned int) pMfcInst->pFramBuf)   \
            + (pMfcInst->frambufCnt) * (args.get_buf_addr.out_buf_size + ZERO_COPY_HDR_SIZE) - (unsigned int)GetDataBufVirAddr() );  
        }
#endif
//.] sichoi 081103

			args.get_buf_addr.out_buf_addr = tmp;
			args.get_buf_addr.ret_code = MFCINST_RET_OK;

			Copy_To_User((MFC_GET_BUF_ADDR_ARG *)arg, &args.get_buf_addr, sizeof(MFC_GET_BUF_ADDR_ARG));

			MFC_Mutex_Release();
			break;

		case IOCTL_MFC_GET_MPEG4_ASP_PARAM:
		#if (defined(DIVX_ENABLE) && (DIVX_ENABLE == 1))
			Copy_From_User(&args.mpeg4_asp_param, (MFC_GET_MPEG4ASP_ARG *)arg, sizeof(MFC_GET_MPEG4ASP_ARG));
		
			ret = MFCINST_RET_OK;
			args.mpeg4_asp_param.ret_code              = MFCINST_RET_OK;
			args.mpeg4_asp_param.mp4asp_vop_time_res   = pMfcInst->RET_DEC_SEQ_INIT_BAK_MP4ASP_VOP_TIME_RES;
			args.mpeg4_asp_param.byte_consumed         = pMfcInst->RET_DEC_PIC_RUN_BAK_BYTE_CONSUMED;
			args.mpeg4_asp_param.mp4asp_fcode          = pMfcInst->RET_DEC_PIC_RUN_BAK_MP4ASP_FCODE;
			args.mpeg4_asp_param.mp4asp_time_base_last = pMfcInst->RET_DEC_PIC_RUN_BAK_MP4ASP_TIME_BASE_LAST;
			args.mpeg4_asp_param.mp4asp_nonb_time_last = pMfcInst->RET_DEC_PIC_RUN_BAK_MP4ASP_NONB_TIME_LAST;
			args.mpeg4_asp_param.mp4asp_trd            = pMfcInst->RET_DEC_PIC_RUN_BAK_MP4ASP_MP4ASP_TRD;
			
   			args.mpeg4_asp_param.mv_addr      = (args.mpeg4_asp_param.in_usr_mapped_addr + MFC_STRM_BUF_SIZE) + (pMfcInst->mv_mbyte_addr - pMfcInst->phyadrFramBuf);
			args.mpeg4_asp_param.mb_type_addr = args.mpeg4_asp_param.mv_addr + 25920;	
			args.mpeg4_asp_param.mv_size      = 25920;
			args.mpeg4_asp_param.mb_type_size = 1620;
		
			vir_mv_addr = (unsigned int)((pMfcInst->pStrmBuf + MFC_STRM_BUF_SIZE) + (pMfcInst->mv_mbyte_addr - pMfcInst->phyadrFramBuf));
			vir_mb_type_addr = vir_mv_addr + 25920;

			Copy_To_User((MFC_GET_MPEG4ASP_ARG *)arg, &args.mpeg4_asp_param, sizeof(MFC_GET_MPEG4ASP_ARG));

                        // from 2.8.5
			//dmac_clean_range(vir_mv_addr, vir_mv_addr + args.mpeg4_asp_param.mv_size);
			//outer_clean_range(__pa(vir_mv_addr), __pa(vir_mv_addr + args.mpeg4_asp_param.mv_size));

			//dmac_clean_range(vir_mb_type_addr, vir_mb_type_addr + args.mpeg4_asp_param.mb_type_size);
			//outer_clean_range(__pa(vir_mb_type_addr), __pa(vir_mb_type_addr + args.mpeg4_asp_param.mb_type_size));
		#endif	
			break;
		case IOCTL_MFC_GET_CONFIG:
			MFC_Mutex_Lock();

			Copy_From_User(&args, (MFC_ARGS *)arg, sizeof(MFC_ARGS));

			ret = MFC_GetConfigParams(pMfcInst, &args);

			Copy_To_User((MFC_ARGS *)arg, &args, sizeof(MFC_ARGS));

			MFC_Mutex_Release();
			break;

		case IOCTL_MFC_SET_CONFIG:
			MFC_Mutex_Lock();

			Copy_From_User(&args, (MFC_ARGS *)arg, sizeof(MFC_ARGS));

			ret = MFC_SetConfigParams(pMfcInst, &args);

			Copy_To_User((MFC_ARGS *)arg, &args, sizeof(MFC_ARGS));
			
			MFC_Mutex_Release();
			break;

		case IOCTL_MFC_SET_H263_MULTIPLE_SLICE:
			MFC_Mutex_Lock();

			pMfcInst->multiple_slice = 1;

			MFC_Mutex_Release();
			break;

		case IOCTL_VIRT_TO_PHYS:
			//MFC_Mutex_Lock();

			temp = __virt_to_phys((void *)arg);
			return (int)temp;
			//MFC_Mutex_Release();
			break;
			
		default:
			MFC_Mutex_Lock();
			LOG_MSG(LOG_TRACE, "s3c_mfc_ioctl", "Requested ioctl command is not defined. (ioctl cmd=0x%X)\n", cmd);
			MFC_Mutex_Release();
			return -EINVAL;
	}

	switch(ret) {
	case MFCINST_RET_OK:
		return TRUE;
	default:
		return -1;
	}
	return -1;
}
Example #20
0
static int __init parse_tag_initrd(const struct tag *tag)
{
	phys_initrd_start = __virt_to_phys(tag->u.initrd.start);
	phys_initrd_size = tag->u.initrd.size;
	return 0;
}
Example #21
0
/*
 * The framework loads the hibernation image into this linked list,
 * for swsusp_arch_resume() to copy back to the proper destinations.
 *
 * To make this work if resume is triggered from initramfs, the
 * pagetables need to be switched to allow writes to kernel mem.
 */
void notrace __swsusp_arch_restore_prepare(void)
{
	cpu_switch_mm(__virt_to_phys(swapper_pg_dir), current->active_mm);
}
Example #22
0
/*
 * Consistent memory allocators. Used for DMA devices that want to
 * share uncached memory with the processor core.
 * My crufty no-MMU approach is simple. In the HW platform we can optionally
 * mirror the DDR up above the processor cacheable region.  So, memory accessed
 * in this mirror region will not be cached.  It's alloced from the same
 * pool as normal memory, but the handle we return is shifted up into the
 * uncached region.  This will no doubt cause big problems if memory allocated
 * here is not also freed properly. -- JW
 */
void *consistent_alloc(gfp_t gfp, size_t size, dma_addr_t *dma_handle)
{
	unsigned long order, vaddr;
	void *ret;
	unsigned int i, err = 0;
	struct page *page, *end;

#ifdef CONFIG_MMU
	phys_addr_t pa;
	struct vm_struct *area;
	unsigned long va;
#endif

	if (in_interrupt())
		BUG();

	/* Only allocate page size areas. */
	size = PAGE_ALIGN(size);
	order = get_order(size);

	vaddr = __get_free_pages(gfp, order);
	if (!vaddr)
		return NULL;

	/*
	 * we need to ensure that there are no cachelines in use,
	 * or worse dirty in this area.
	 */
	flush_dcache_range(virt_to_phys((void *)vaddr),
					virt_to_phys((void *)vaddr) + size);

#ifndef CONFIG_MMU
	ret = (void *)vaddr;
	/*
	 * Here's the magic!  Note if the uncached shadow is not implemented,
	 * it's up to the calling code to also test that condition and make
	 * other arranegments, such as manually flushing the cache and so on.
	 */
# ifdef CONFIG_XILINX_UNCACHED_SHADOW
	ret = (void *)((unsigned) ret | UNCACHED_SHADOW_MASK);
# endif
	if ((unsigned int)ret > cpuinfo.dcache_base &&
				(unsigned int)ret < cpuinfo.dcache_high)
		pr_warn("ERROR: Your cache coherent area is CACHED!!!\n");

	/* dma_handle is same as physical (shadowed) address */
	*dma_handle = (dma_addr_t)ret;
#else
	/* Allocate some common virtual space to map the new pages. */
	area = get_vm_area(size, VM_ALLOC);
	if (!area) {
		free_pages(vaddr, order);
		return NULL;
	}
	va = (unsigned long) area->addr;
	ret = (void *)va;

	/* This gives us the real physical address of the first page. */
	*dma_handle = pa = __virt_to_phys(vaddr);
#endif

	/*
	 * free wasted pages.  We skip the first page since we know
	 * that it will have count = 1 and won't require freeing.
	 * We also mark the pages in use as reserved so that
	 * remap_page_range works.
	 */
	page = virt_to_page(vaddr);
	end = page + (1 << order);

	split_page(page, order);

	for (i = 0; i < size && err == 0; i += PAGE_SIZE) {
#ifdef CONFIG_MMU
		/* MS: This is the whole magic - use cache inhibit pages */
		err = map_page(va + i, pa + i, _PAGE_KERNEL | _PAGE_NO_CACHE);
#endif

		SetPageReserved(page);
		page++;
	}

	/* Free the otherwise unused pages. */
	while (page < end) {
		__free_page(page);
		page++;
	}

	if (err) {
		free_pages(vaddr, order);
		return NULL;
	}

	return ret;
}
Example #23
0
/*
 *  Main dma routine, requests dma according where you are in main alsa buffer
 */
static void audio_process_dma(struct audio_stream_a *s)
{
	struct snd_pcm_substream *substream = s->stream;
	struct snd_pcm_runtime *runtime;
	unsigned int dma_size;
	unsigned int offset;
	dma_addr_t dma_base;
	int ret = 0;
	int stream_id = substream->pstr->stream;
	
	//DBG_DETAIL();
	DPRINTK("s: %d, dmach: %d. active: %d", (int)s, s->dmach, s->active);
	
	if (s->active) {
		substream = s->stream;
		runtime = substream->runtime;
		dma_size = frames_to_bytes(runtime, runtime->period_size);
		/*DPRINTK("frame_bits=%d, period_size=%d, dma_size 1=%d",
			runtime->frame_bits, (int)runtime->period_size, dma_size);*/
		if (dma_size > MAX_DMA_SIZE)
			dma_size = CUT_DMA_SIZE;
		offset = dma_size * s->period;

		/*DPRINTK("offset: 0x%x, ->dma_area: 0x%x, ->dma_addr: 0x%x, final addr: 0x%x",
			offset, (unsigned int)runtime->dma_area, runtime->dma_addr, runtime->dma_addr+offset);*/

		dma_base = __virt_to_phys((dma_addr_t)runtime->dma_area);

		//DPRINTK("dma address: 0x%x", dma_base+offset);
		/*DPRINTK("hw_ptr_interrupt: 0x%x, state: %d, hwptr: %u, applptr: %u, avail_min: %u", 
			(unsigned int)runtime->hw_ptr_interrupt, runtime->status->state, (unsigned int)runtime->status->hw_ptr,
			(unsigned int)runtime->control->appl_ptr, (unsigned int)runtime->control->avail_min);*/
		//DPRINTK("dmach: %u, dma_addr: %x, dma_size: %u", s->dmach, dma_base+offset, dma_size);
		//printk(KERN_INFO "offset: %u, dma_addr: %x, dma_size: %u\n", offset, dma_base+offset, dma_size);

#ifdef CONFIG_SND_WMT_SOC_I2S		
		if (!strcmp(wmt_dai_name, "i2s")) {
			if (stream_id == SNDRV_PCM_STREAM_PLAYBACK) {
				//printk(KERN_ERR  "audio_process_dma: format=0x%x, channels=0x%x \n", runtime->format, runtime->channels);
				
				wmt_sw_u2s(runtime->format, (unsigned char *)runtime->dma_buffer_p->area+offset, dma_size);
				
				if (((runtime->channels == 1) && (runtime->format == SNDRV_PCM_FORMAT_S16_LE)) ||
					((runtime->channels == 2) && (runtime->format == SNDRV_PCM_FORMAT_U8))) {
					wmt_pcm_fmt_trans(runtime->format, runtime->channels,
						(unsigned char *)runtime->dma_buffer_p->area + offset,
						(unsigned char *)dump_buf[stream_id].area + (2 * offset),
						dma_size);
					ret = wmt_start_dma(s->dmach, dump_buf[stream_id].addr + (2 * offset), 0, (2 * dma_size));
				}
				else if ((runtime->channels == 1) && (runtime->format == SNDRV_PCM_FORMAT_U8)) {
					wmt_pcm_fmt_trans(runtime->format, runtime->channels,
						(unsigned char *)runtime->dma_buffer_p->area + offset,
						(unsigned char *)dump_buf[stream_id].area + (4 * offset),
						dma_size);
					ret = wmt_start_dma(s->dmach, dump_buf[stream_id].addr + 4 * offset, 0, (4 * dma_size));
				}
				else if ((runtime->channels == 2) && (runtime->format == SNDRV_PCM_FORMAT_FLOAT)) {
					wmt_pcm_fmt_trans(runtime->format, runtime->channels,
						(unsigned char *)runtime->dma_buffer_p->area + offset,
						(unsigned char *)dump_buf[stream_id].area + (offset / 2),
						dma_size);
					ret = wmt_start_dma(s->dmach, dump_buf[stream_id].addr + (offset / 2), 0, (dma_size / 2));
				}
				else if ((runtime->channels == 1) && (runtime->format == SNDRV_PCM_FORMAT_FLOAT)) {
					wmt_pcm_fmt_trans(runtime->format, runtime->channels,
						(unsigned char *)runtime->dma_buffer_p->area + offset,
						(unsigned char *)dump_buf[stream_id].area + offset,
						dma_size);
					ret = wmt_start_dma(s->dmach, dump_buf[stream_id].addr + offset, 0, dma_size);
				}
			}
		
			if (((runtime->channels == 2) || (runtime->channels == 6)) && (runtime->format == SNDRV_PCM_FORMAT_S16_LE)) {
				if ((stream_id == SNDRV_PCM_STREAM_PLAYBACK) && (wfd_audbuf.enable)) {
					wmt_pcm_wfd_update(runtime->dma_buffer_p->area + offset, dma_size);
				}
				ret = wmt_start_dma(s->dmach, runtime->dma_addr + offset, 0, dma_size);
			}
		}
#endif
#ifdef CONFIG_SND_WMT_SOC_AC97
		if (!strcmp(wmt_dai_name, "ac97")) {
			ret = wmt_start_dma(s->dmach, runtime->dma_addr + offset, 0, dma_size);
		}
#endif

		if (ret) {
			printk(KERN_ERR  "audio_process_dma: cannot queue DMA buffer (%i) \n", ret);
			return;
		}

		s->period++;
		s->period %= runtime->periods;
		s->periods++;
		s->offset = offset;
	}
}
Example #24
0
static int s3c_mfc_ioctl(struct inode *inode, struct file *file, unsigned int cmd, unsigned long arg)
{
	int ret = 0;
	int buf_size;
	int nStrmLen, nHdrLen;
	int out;
	int yuv_size;
	int size;
	
	void		*temp;
	unsigned int	vir_mv_addr;
	unsigned int	vir_mb_type_addr;
	unsigned int	tmp;
	unsigned int	in_usr_data, yuv_buffer, run_index, out_buf_size, databuf_vaddr, offset;
	unsigned int	yuv_buff_cnt, databuf_paddr;
	unsigned char	*OutBuf	= NULL;
	unsigned char	*start, *end;
	
	s3c_mfc_inst_context_t	*pMfcInst;
	s3c_mfc_handle_t		*handle;
	s3c_mfc_codec_mode_t	codec_mode = 0;
	s3c_mfc_args_t		args;
	s3c_mfc_enc_info_t		enc_info;

	/* 
	 * Parameter Check
	 */
	handle = (s3c_mfc_handle_t *)file->private_data;
	if (handle->mfc_inst == NULL) {
		return -EFAULT;
	}

	pMfcInst = handle->mfc_inst;

	switch (cmd) {
	case S3C_MFC_IOCTL_MFC_MPEG4_ENC_INIT:
	case S3C_MFC_IOCTL_MFC_H264_ENC_INIT:
	case S3C_MFC_IOCTL_MFC_H263_ENC_INIT:
		mutex_lock(s3c_mfc_mutex);

		mfc_debug("cmd = %d\n", cmd);

		out = copy_from_user(&args.enc_init, (s3c_mfc_enc_init_arg_t *)arg, 
						sizeof(s3c_mfc_enc_init_arg_t));

		if ( cmd == S3C_MFC_IOCTL_MFC_MPEG4_ENC_INIT )
			codec_mode = MP4_ENC;
		else if ( cmd == S3C_MFC_IOCTL_MFC_H264_ENC_INIT )
			codec_mode = AVC_ENC;
		else if ( cmd == S3C_MFC_IOCTL_MFC_H263_ENC_INIT )
			codec_mode = H263_ENC;

		/* 
		 * Initialize MFC Instance
		 */
		enc_info.width			= args.enc_init.in_width;
		enc_info.height			= args.enc_init.in_height;
		enc_info.bitrate		= args.enc_init.in_bitrate;
		enc_info.gop_number		= args.enc_init.in_gopNum;
		enc_info.frame_rate_residual	= args.enc_init.in_frameRateRes;
		enc_info.frame_rate_division	= args.enc_init.in_frameRateDiv;

		/*
		enc_info.intraqp	= args.enc_init.in_intraqp;
		enc_info.qpmax		= args.enc_init.in_qpmax;
		enc_info.gamma		= args.enc_init.in_gamma;
		*/

		ret = s3c_mfc_instance_init_enc(pMfcInst, codec_mode, &enc_info);

		args.enc_init.ret_code = ret;
		out = copy_to_user((s3c_mfc_enc_init_arg_t *)arg, &args.enc_init, 
						sizeof(s3c_mfc_enc_init_arg_t));

		mutex_unlock(s3c_mfc_mutex);
		break;

	case S3C_MFC_IOCTL_MFC_MPEG4_ENC_EXE:
	case S3C_MFC_IOCTL_MFC_H264_ENC_EXE:
	case S3C_MFC_IOCTL_MFC_H263_ENC_EXE:
		mutex_lock(s3c_mfc_mutex);

		out = copy_from_user(&args.enc_exe, (s3c_mfc_enc_exe_arg_t *)arg, 
							sizeof(s3c_mfc_enc_exe_arg_t));

		tmp = (pMfcInst->width * pMfcInst->height * 3) >> 1;

		start = pMfcInst->yuv_buffer;
		size = tmp * pMfcInst->yuv_buffer_count; 
		dma_cache_maint(start, size, DMA_TO_DEVICE);

		/* 
		 * Encode MFC Instance
		 */
		ret = s3c_mfc_inst_enc(pMfcInst, &nStrmLen, &nHdrLen);

		start = pMfcInst->stream_buffer;
		size = pMfcInst->stream_buffer_size;
		dma_cache_maint(start, size, DMA_FROM_DEVICE);

		args.enc_exe.ret_code	= ret;
		if (ret == S3C_MFC_INST_RET_OK) {
			args.enc_exe.out_encoded_size = nStrmLen;
			args.enc_exe.out_header_size  = nHdrLen;
		}
		out = copy_to_user((s3c_mfc_enc_exe_arg_t *)arg, &args.enc_exe, 
						sizeof(s3c_mfc_enc_exe_arg_t));

		mutex_unlock(s3c_mfc_mutex);
		break;

	case S3C_MFC_IOCTL_MFC_MPEG4_DEC_INIT:
	case S3C_MFC_IOCTL_MFC_H264_DEC_INIT:
	case S3C_MFC_IOCTL_MFC_H263_DEC_INIT:
	case S3C_MFC_IOCTL_MFC_VC1_DEC_INIT:
		mutex_lock(s3c_mfc_mutex);

		out = copy_from_user(&args.dec_init, (s3c_mfc_dec_init_arg_t *)arg, 
							sizeof(s3c_mfc_dec_init_arg_t));

		if ( cmd == S3C_MFC_IOCTL_MFC_MPEG4_DEC_INIT )
			codec_mode = MP4_DEC;
		else if ( cmd == S3C_MFC_IOCTL_MFC_H264_DEC_INIT )
			codec_mode = AVC_DEC;
		else if ( cmd == S3C_MFC_IOCTL_MFC_H263_DEC_INIT)
			codec_mode = H263_DEC;
		else {
			codec_mode = VC1_DEC;
		}

		start = pMfcInst->stream_buffer;
		size = pMfcInst->stream_buffer_size;
		dma_cache_maint(start, size, DMA_TO_DEVICE);

		/* 
		 * Initialize MFC Instance
		 */
		ret = s3c_mfc_inst_init_dec(pMfcInst, codec_mode, 
						args.dec_init.in_strmSize);

		args.dec_init.ret_code	= ret;
		if (ret == S3C_MFC_INST_RET_OK) {
			args.dec_init.out_width	     = pMfcInst->width;
			args.dec_init.out_height     = pMfcInst->height;
			args.dec_init.out_buf_width  = pMfcInst->buf_width;
			args.dec_init.out_buf_height = pMfcInst->buf_height;
		}
		out = copy_to_user((s3c_mfc_dec_init_arg_t *)arg, &args.dec_init, 
							sizeof(s3c_mfc_dec_init_arg_t));

		mutex_unlock(s3c_mfc_mutex);
		break;

	case S3C_MFC_IOCTL_MFC_MPEG4_DEC_EXE:
	case S3C_MFC_IOCTL_MFC_H264_DEC_EXE:
	case S3C_MFC_IOCTL_MFC_H263_DEC_EXE:
	case S3C_MFC_IOCTL_MFC_VC1_DEC_EXE:
		mutex_lock(s3c_mfc_mutex);

		out = copy_from_user(&args.dec_exe, (s3c_mfc_dec_exe_arg_t *)arg, 
							sizeof(s3c_mfc_dec_exe_arg_t));

		tmp = (pMfcInst->width * pMfcInst->height * 3) >> 1;

		start = pMfcInst->stream_buffer;
		size = pMfcInst->stream_buffer_size;
		dma_cache_maint(start, size, DMA_TO_DEVICE);

		ret = s3c_mfc_inst_dec(pMfcInst, args.dec_exe.in_strmSize);

		start = pMfcInst->yuv_buffer;
		size = tmp * pMfcInst->yuv_buffer_count;
		dma_cache_maint(start, size, DMA_FROM_DEVICE);	

		args.dec_exe.ret_code = ret;
		out = copy_to_user((s3c_mfc_dec_exe_arg_t *)arg, &args.dec_exe,
						 sizeof(s3c_mfc_dec_exe_arg_t));

		mutex_unlock(s3c_mfc_mutex);
		break;

	case S3C_MFC_IOCTL_MFC_GET_LINE_BUF_ADDR:
		mutex_lock(s3c_mfc_mutex);

		out = copy_from_user(&args.get_buf_addr, 
			(s3c_mfc_get_buf_addr_arg_t *)arg, sizeof(s3c_mfc_get_buf_addr_arg_t));

		ret = s3c_mfc_inst_get_line_buff(pMfcInst, &OutBuf, &buf_size);

		args.get_buf_addr.out_buf_size	= buf_size;
		args.get_buf_addr.out_buf_addr	= args.get_buf_addr.in_usr_data + (OutBuf - s3c_mfc_get_databuf_virt_addr());
		args.get_buf_addr.ret_code	= ret;

		out = copy_to_user((s3c_mfc_get_buf_addr_arg_t *)arg, 
			&args.get_buf_addr, sizeof(s3c_mfc_get_buf_addr_arg_t));

		mutex_unlock(s3c_mfc_mutex);
		break;

	case S3C_MFC_IOCTL_MFC_GET_YUV_BUF_ADDR:
		mutex_lock(s3c_mfc_mutex);

		out = copy_from_user(&args.get_buf_addr, 
			(s3c_mfc_get_buf_addr_arg_t *)arg, 
			sizeof(s3c_mfc_get_buf_addr_arg_t));

		if (pMfcInst->yuv_buffer == NULL) {
			mfc_err("mfc frame buffer is not internally allocated yet\n");
			mutex_unlock(s3c_mfc_mutex);
			return -EFAULT;
		}

		/* FRAM_BUF address is calculated differently for Encoder and Decoder. */
		switch (pMfcInst->codec_mode) {
		case MP4_DEC:
		case AVC_DEC:
		case VC1_DEC:
		case H263_DEC:
			/* Decoder case */
			yuv_size = (pMfcInst->buf_width * pMfcInst->buf_height * 3) >> 1;
			args.get_buf_addr.out_buf_size = yuv_size;

			in_usr_data = (unsigned int)args.get_buf_addr.in_usr_data;
			yuv_buffer = (unsigned int)pMfcInst->yuv_buffer;
			run_index = pMfcInst->run_index;
			out_buf_size = args.get_buf_addr.out_buf_size;
			databuf_vaddr = (unsigned int)s3c_mfc_get_databuf_virt_addr();
			offset = yuv_buffer + run_index * out_buf_size - databuf_vaddr;
			
#if (S3C_MFC_ROTATE_ENABLE == 1)
			if ((pMfcInst->codec_mode != VC1_DEC) && 
				(pMfcInst->post_rotation_mode & 0x0010)) {
				yuv_buff_cnt = pMfcInst->yuv_buffer_count;
				offset = yuv_buffer + yuv_buff_cnt * out_buf_size - databuf_vaddr;
			}
#endif
			args.get_buf_addr.out_buf_addr = in_usr_data + offset;
			break;

		case MP4_ENC:
		case AVC_ENC:
		case H263_ENC:
			/* Encoder case */
			yuv_size = (pMfcInst->width * pMfcInst->height * 3) >> 1;
			in_usr_data = args.get_buf_addr.in_usr_data;
			run_index = pMfcInst->run_index;
			yuv_buffer = (unsigned int)pMfcInst->yuv_buffer;
			databuf_vaddr = (unsigned int)s3c_mfc_get_databuf_virt_addr();
			offset = run_index * yuv_size + (yuv_buffer - databuf_vaddr);
			
			args.get_buf_addr.out_buf_addr = in_usr_data + offset;			
			break;
		} /* end of switch (codec_mode) */

		args.get_buf_addr.ret_code = S3C_MFC_INST_RET_OK;
		out = copy_to_user((s3c_mfc_get_buf_addr_arg_t *)arg, &args.get_buf_addr, sizeof(s3c_mfc_get_buf_addr_arg_t));

		mutex_unlock(s3c_mfc_mutex);
		break;

	case S3C_MFC_IOCTL_MFC_GET_PHY_FRAM_BUF_ADDR:
		mutex_lock(s3c_mfc_mutex);

		out = copy_from_user(&args.get_buf_addr, 
			(s3c_mfc_get_buf_addr_arg_t *)arg, 
			sizeof(s3c_mfc_get_buf_addr_arg_t));

		yuv_size = (pMfcInst->buf_width * pMfcInst->buf_height * 3) >> 1;
		args.get_buf_addr.out_buf_size = yuv_size;
		yuv_buffer = (unsigned int)pMfcInst->yuv_buffer;
		run_index = pMfcInst->run_index;
		out_buf_size = args.get_buf_addr.out_buf_size;
		databuf_vaddr = (unsigned int)s3c_mfc_get_databuf_virt_addr();
		databuf_paddr = (unsigned int)S3C_MFC_BASEADDR_DATA_BUF;
		offset = yuv_buffer + run_index * out_buf_size - databuf_vaddr;		
		
#if (S3C_MFC_ROTATE_ENABLE == 1)
		if ((pMfcInst->codec_mode != VC1_DEC) && (pMfcInst->post_rotation_mode & 0x0010)) {
			yuv_buff_cnt = pMfcInst->yuv_buffer_count;
			offset = yuv_buffer + yuv_buff_cnt * out_buf_size - databuf_vaddr;
		}
#endif
		args.get_buf_addr.out_buf_addr = databuf_paddr + offset;
		args.get_buf_addr.ret_code = S3C_MFC_INST_RET_OK;

		out = copy_to_user((s3c_mfc_get_buf_addr_arg_t *)arg, 
			&args.get_buf_addr, sizeof(s3c_mfc_get_buf_addr_arg_t));

		mutex_unlock(s3c_mfc_mutex);
		break;

	case S3C_MFC_IOCTL_MFC_GET_MPEG4_ASP_PARAM:
#if (defined(DIVX_ENABLE) && (DIVX_ENABLE == 1))

		out = copy_from_user(&args.mpeg4_asp_param, (s3c_mfc_get_mpeg4asp_arg_t *)arg, \
							sizeof(s3c_mfc_get_mpeg4asp_arg_t));

		ret = S3C_MFC_INST_RET_OK;
		args.mpeg4_asp_param.ret_code = S3C_MFC_INST_RET_OK;
		args.mpeg4_asp_param.mp4asp_vop_time_res = pMfcInst->RET_DEC_SEQ_INIT_BAK_MP4ASP_VOP_TIME_RES;
		args.mpeg4_asp_param.byte_consumed = pMfcInst->RET_DEC_PIC_RUN_BAK_BYTE_CONSUMED;
		args.mpeg4_asp_param.mp4asp_fcode = pMfcInst->RET_DEC_PIC_RUN_BAK_MP4ASP_FCODE;
		args.mpeg4_asp_param.mp4asp_time_base_last = pMfcInst->RET_DEC_PIC_RUN_BAK_MP4ASP_TIME_BASE_LAST;
		args.mpeg4_asp_param.mp4asp_nonb_time_last = pMfcInst->RET_DEC_PIC_RUN_BAK_MP4ASP_NONB_TIME_LAST;
		args.mpeg4_asp_param.mp4asp_trd = pMfcInst->RET_DEC_PIC_RUN_BAK_MP4ASP_MP4ASP_TRD;

		args.mpeg4_asp_param.mv_addr = (args.mpeg4_asp_param.in_usr_mapped_addr + S3C_MFC_STREAM_BUF_SIZE) 	\
							+ (pMfcInst->mv_mbyte_addr - pMfcInst->phys_addr_yuv_buffer);
		args.mpeg4_asp_param.mb_type_addr = args.mpeg4_asp_param.mv_addr + S3C_MFC_MAX_MV_SIZE;	
		args.mpeg4_asp_param.mv_size = S3C_MFC_MAX_MV_SIZE;
		args.mpeg4_asp_param.mb_type_size = S3C_MFC_MAX_MBYTE_SIZE;

		vir_mv_addr = (unsigned int)((pMfcInst->stream_buffer + S3C_MFC_STREAM_BUF_SIZE) + \
					(pMfcInst->mv_mbyte_addr - pMfcInst->phys_addr_yuv_buffer));
		vir_mb_type_addr = vir_mv_addr + S3C_MFC_MAX_MV_SIZE;

		out = copy_to_user((s3c_mfc_get_mpeg4asp_arg_t *)arg, &args.mpeg4_asp_param, \
							sizeof(s3c_mfc_get_mpeg4asp_arg_t));
#endif	
		break;

	case S3C_MFC_IOCTL_MFC_GET_CONFIG:
		mutex_lock(s3c_mfc_mutex);

		out = copy_from_user(&args, (s3c_mfc_args_t *)arg, sizeof(s3c_mfc_args_t));

		ret = s3c_mfc_get_config_params(pMfcInst, &args);

		out = copy_to_user((s3c_mfc_args_t *)arg, &args, sizeof(s3c_mfc_args_t));

		mutex_unlock(s3c_mfc_mutex);
		break;

	case S3C_MFC_IOCTL_MFC_SET_CONFIG:
		mutex_lock(s3c_mfc_mutex);

		out = copy_from_user(&args, (s3c_mfc_args_t *)arg, sizeof(s3c_mfc_args_t));

		ret = s3c_mfc_set_config_params(pMfcInst, &args);

		out = copy_to_user((s3c_mfc_args_t *)arg, &args, sizeof(s3c_mfc_args_t));

		mutex_unlock(s3c_mfc_mutex);
		break;

	case S3C_MFC_IOCTL_VIRT_TO_PHYS:
		temp = __virt_to_phys((void *)arg);
		return (int)temp;
		break;

	default:
		mutex_lock(s3c_mfc_mutex);
		mfc_debug("requested ioctl command is not defined (ioctl cmd = 0x%x)\n", cmd);
		mutex_unlock(s3c_mfc_mutex);
		return -ENOIOCTLCMD;
	}

	switch (ret) {
	case S3C_MFC_INST_RET_OK:
		return 0;
	default:
		return -EPERM;
	}
	return -EPERM;
}