---Britton Kerin <[EMAIL PROTECTED]> wrote:
>
> I have been trying to read() audio data into an mmap()ed region
(from a file 
> just created and empty before the mmap call.  I know that read()
normally
> puts the data in a buffer and not a file, but with mmap() you get
back a 
> caddr_t pointer which I am hoping read() can use.  Here is the
relevant chunk 
> of code (full listing at bottom):
> 
>   /* create and memory map the target region */
>   printf("0: I'm still here sir!");

I believe someone else already pointed out that standard output is
line buffered.  Nothing is actually written until a newline is
printed.  Your program crashed before you wrote a newline, so you
didn't see any output.

>   status = target = open("targetfile", O_CREAT | O_RDWR, 777);

You forgot that octal constants must begin with a zero.  You should
have written 0777 instead of 777.

>   if (status < 0) 
>     perror("error opening target file");
>   printf("1: I'm still here sir!");
>   region = mmap(NULL, (off_t) 512, PROT_WRITE, MAP_SHARED, target, 0);

The file you just created is empty (0 bytes).  You must extend the
file to 512 bytes before you call mmap(), or at least before you
actually access the mmapped region of memory.  You got a bus error
because the memory accessed by read() was technically valid (because
it had been mmapped) but didn't actually exist (because the file was 0
bytes long).  Put the following code (or something similar) before
your call to mmap() to fix this.

/* Seek past the first 511 bytes.  They will be filled with 0's when
we write bytes after them. */
if (lseek(target, 511, SEEK_SET) < 0) {
   perror("lseek() error");
   exit(1);
}
/* Write a single 0 byte.  This extends the file to 512 bytes long. */
if (write(target, "", 1) < 0) {
   perror("write() error");
   exit(1);
}

>   printf("2: I'm still here sir!");
>   if (region == (caddr_t) (-1))
>     perror("mmap error");
> 
>   /* record sound into mmaped region */
>   printf("3: I'm still here sir!");
>   status = read(audio, (void *) region, 512); 
>   if (status != sizeof(region))
>     perror("read screwed one way or another");
> 
>   msync(region, 512, MS_SYNC);

You don't need to call msync().  msync() is only needed if you called
mmap() with MAP_PRIVATE.  Using MAP_SHARED tells the OS to keep the
memory constantly up-to-date.

> 
> with the read(audio, (void *) region, 512);
> line not commented out, when I run this program I get:
> 
> Bus error
> 
> and a file in the current directory:
> 
> -r----x--t   1 gandalf  gandalf         0 Feb  4 17:04 targetfile
> 
> None of the little I'm still here sir! message print with the read
in there, 
> so I assume I'm doing something drastic.  My questions:
> 
> 1.  Why does the file have those strange permissions?  I thought I
specified 
>     mode 777.

See above.

> 
> 2.  Is it possible to use read() into an mmap() this way?  Is there
some other 
>     function I should be using instead of read()?

Yes.  You can treat a pointer to a mmapped region *exactly* the same
way as any other pointer.
 
> 3.  Even if it is possible, is it a completely hairbrained approach?

That depends on what your ultimate goal is.  B')

I would strongly suggest you get a copy of
_Advanced_Programming_in_the_UNIX_Environment by W. Richard Stevens
(Addison-Wesley, 1993  ISBN: 0-201-56317-7).  This book covers mmap()
thoroughly as well as practically every other topic you'll need to do
Unix programming except for networking and threads.  You might also
get a copy of _Linux_Application_Development_.  Unfortunately, I don't
have the authors' names etc. on hand at the moment.  B')

HTH,

Bradford
==
Bradford C. Smith ([EMAIL PROTECTED])


_________________________________________________________
DO YOU YAHOO!?
Get your free @yahoo.com address at http://mail.yahoo.com

Reply via email to