Re: mmap problem

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



I have solved this problem. But I need to some clarification on the use of address in the kernel
space. Some explanation will be appreciated.

The hardware device is attached at physical address 0x9a1d20 (and continues for 0x3000 locations).
To access this device I need to convert the address to va, i.e. I use
contents at __va(0x9a1d20) from kernel space.

For memory mapping I have to use actual physical aaddress, why is this ?

Usman
--- "Usman S. Ansari" <uansari@yahoo.com> wrote:
> I am trying to mmap a device on PPC plateform. The device is at address space of 10100000
> (0x9a1d20). From within the driver I can read / write to the memory. But when I try to read /
> write from a user space program after memory mapping, I get SIGSEGV. PLEASE HELP.
> 
> The code for mmap:
> static int ocr_mmap(struct file *file, struct vm_area_struct *vma)
> {
>  unsigned long offset = vma->vm_pgoff << PAGE_SHIFT;
>  int minor = MINOR(file->f_dentry->d_inode->i_rdev);
> 
>  dT[minor].addr = (int) __va(dT[minor].addr);
> 
>  if (remap_page_range(vma->vm_start,                  /* start addr in process addr space */
>                       dT[minor].addr + offset,        /* addr to map */
> 		      vma->vm_end - vma->vm_start,    /* size to map */
> 		      vma->vm_page_prot) < 0)         /* flags */
>     return -EAGAIN;
> 
>  return(0);
> }
> The code for mmap in user space:
> 
> int main(void)
> {
>  int  fd, i;
>  char *ptr, *qtr;
>  
>  if ((fd = open("/dev/ocr_reg", O_RDWR)) < 0)
>     exit(1);
> 
>  if ((ptr = (char *) mmap(0, OCR_REG_SIZE, PROT_READ|PROT_WRITE, MAP_SHARED, fd, 0)) == NULL)
>     {
>      perror("error mmapping /dev/ocr_reg");
>      exit(1);
>     }
> 
>  printf("/dev/ocr_reg mmaped @ %x\n", ptr);
> 
>  qtr = ptr;
>  printf("Testing Register Area - Reading # 1\n");
>  printf("Address of ptr = %x\n", ptr);
>  printf("Address of qtr = %x\n", qtr);
>  printf("%x", *qtr); qtr++;
>  printf("%x", *qtr); qtr++;
>  printf("%x", *qtr);
> 
>  qtr = ptr;
>  printf("Testing Register Area - Writing\n");
>  *qtr = 0xf0; qtr++;
>  *qtr = 0x0f; qtr++;
>  *qtr = 0xcc;
> 
>  qtr = ptr;
>  printf("Testing Register Area - Reading # 2\n");
>  printf("%x", *qtr); qtr++;
>  printf("%x", *qtr); qtr++;
>  printf("%x", *qtr);
> 
>  if (munmap(0, OCR_REG_SIZE) != 0)
>     printf("munmap of /dev/ocr_reg failed\n");
> }
> The include files are:
> #include <linux/kernel.h>
> #include <linux/module.h>
> #include <linux/errno.h>
> #include <linux/fs.h>
> #include <linux/malloc.h>
> 
> #include <asm/mpc8xx.h>
> #include <asm/8xx_immap.h>
> #include <commproc.h>
> 
> Make flags:
> CC = ppc_8xx-gcc
> 
> CFLAGS_K =		-D__KERNEL__ $(NO_HARDWARE_FLAG) \
> 			-DMODULE -DMODVERSIONS \
> 			-D__powerpc__ -mcpu=860 \
> 			-Wall -Wstrict-prototypes \
> 			-Wno-uninitialized \
> 			-fomit-frame-pointer \
> 			-fsigned-char -msoft-float \
> 			-fno-builtin -ffixed-r2 \
> 			-pipe -mmultiple -mstring \
> 			-Os \
> 			-I/linux-2.4.4/include \
> 			-I/linux-2.4.4/arch/ppc/8xx_io
> 
> =====
> Usman S. Ansari
> Linux OS & Device Drivers
> 
> __________________________________________________
> Do You Yahoo!?
> Yahoo! - Official partner of 2002 FIFA World Cup
> http://fifaworldcup.yahoo.com
> 


=====
Usman S. Ansari
Linux OS & Device Drivers

__________________________________________________
Do You Yahoo!?
Yahoo! - Official partner of 2002 FIFA World Cup
http://fifaworldcup.yahoo.com
--
Kernelnewbies: Help each other learn about the Linux kernel.
Archive:       http://mail.nl.linux.org/kernelnewbies/
FAQ:           http://kernelnewbies.org/faq/


[Index of Archives]     [Newbies FAQ]     [Linux Kernel Mentors]     [Linux Kernel Development]     [IETF Annouce]     [Git]     [Networking]     [Security]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux RAID]     [Linux SCSI]     [Linux ACPI]
  Powered by Linux