Thread View: comp.unix.programmer
10 messages
10 total messages
Started by Randy Tidd
Mon, 10 Sep 1990 16:46
File pointer to a memory location?
Author: Randy Tidd
Date: Mon, 10 Sep 1990 16:46
Date: Mon, 10 Sep 1990 16:46
34 lines
2140 bytes
2140 bytes
With all these new comp.unix.* groups coming out, I hope it's appropriate to cross-post to .programmer and .internals... Anyhow, in the application i'm working on I have a series of routines that were written by someone else that do image processing (the fbm library, if you're familiar with it), including source. These routines take a file pointer as an argument, and they read the image-to-be-processed through this fp. Normally what you do is open a file and pass in a file pointer to it, or pass in stdin and pipe your image through the program through the shell. The problem is in my application, I am using a database and thus don't have files and thus I don't have file pointers either. What I *can* do is query the database for an image, and it gives me a block of memory that holds the image *exactly* as it is stored in file form. So what I have is a block of memory, having exactly the same size and contents of a file. What I have to do is pass my image processing routines a file pointer that points to this block of memory. If the routines used file *descriptors*, it wouldn't be a problem because I could just use pipes and be done with it. What I do now is query the database, get a block of memory, dump this memory to a temporary file, open the file with a file pointer, and pass the file pointer to the image processing routines. Not only is this dumb, but images can be a big as 3 megs and this is incredibly inefficient. Can anyone help me out? Randy Tidd GOOD rtidd@mwunix.mitre.org FAST #define DISCLAIM TRUE CHEAP -pick any two
Re: File pointer to a memory location?
Author: Conor P. Cahill
Date: Tue, 11 Sep 1990 00:13
Date: Tue, 11 Sep 1990 00:13
22 lines
1406 bytes
1406 bytes
In article <119609@linus.mitre.org> rtidd@ccels3.mitre.org (Randy Tidd) writes:
>What I do now is query the database, get a block of memory, dump this
>memory to a temporary file, open the file with a file pointer, and
>pass the file pointer to the image processing routines. Not only is
>this dumb, but images can be a big as 3 megs and this is incredibly
>inefficient.
>
>Can anyone help me out?
1. best solution is to change your routines to accept a pointer to a memory
area that has the image data
or
2. use the pipe like you had intended and on the recieving side (the read
side of the pipe file descriptor pair) use fdopen() to assign a file
pointer to the file descriptor.
--
Conor P. Cahill (703)430-9247 Virtual Technologies, Inc.,
uunet!virtech!cpcahil 46030 Manekin Plaza, Suite 160
Sterling, VA 22170
Re: File pointer to a memory location?
Author: Larry Wall
Date: Tue, 11 Sep 1990 01:54
Date: Tue, 11 Sep 1990 01:54
40 lines
1783 bytes
1783 bytes
In article <119609@linus.mitre.org> rtidd@ccels3.mitre.org (Randy Tidd) writes:
: What I do now is query the database, get a block of memory, dump this
: memory to a temporary file, open the file with a file pointer, and
: pass the file pointer to the image processing routines. Not only is
: this dumb, but images can be a big as 3 megs and this is incredibly
: inefficient.
:
: Can anyone help me out?
It *definitely* counts as cheating, and it's not entirely portable, but
if you're desperate you can generally do something like this:
#include <stdio.h>
main()
{
char *string = "Now is the time\nfor all good men\nto come to.\n";
FILE *fake = fopen("/dev/null", "r");
char buf[512];
fake->_ptr = string; /* pointer to your memory */
fake->_cnt = strlen(string); /* length of your memory */
/* test it */
while (fgets(buf,512,fake)) {
fputs(buf,stdout);
}
}
As soon as the _cnt runs down, it resets _ptr back to _base and refills
from the fd that's connected to /dev/null, so you get EOF.
If this doesn't work, look in /usr/include/stdio.h to see what the fields
are actually called.
Like I said, it's cheating. But then again, many versions of sprintf()
do the same thing in reverse.
Larry
Re: File pointer to a memory location?
Author: Steve Watt
Date: Tue, 11 Sep 1990 05:22
Date: Tue, 11 Sep 1990 05:22
49 lines
1917 bytes
1917 bytes
In article <119609@linus.mitre.org> rtidd@ccels3.mitre.org (Randy Tidd) writes:
>With all these new comp.unix.* groups coming out, I hope it's
>appropriate to cross-post to .programmer and .internals...
I'm not actually sure which is right, either. .programmer is probably closer.
>Anyhow, in the application i'm working on I have a series of routines
>that were written by someone else that do image processing (the fbm
[ slurp! ]
[ he doesn't have a file, but just a large block of RAM ]
>Can anyone help me out?
I just hacked this little piece of code together, you might find it amenable
to your application: Just set f._cnt to the size of the image block.
NOTE: This is terribly dependent on stdio being implemented in the
"standard unix" way... Or at least how it looks on my SCO box and my
DECStation.
----- ugh.c -----
#include <stdio.h>
char *buf = "This is a test of the emergency broadcast system. In the event\
of a real emergency, you would never have heard this signal. Seriously.\n";
main() {
FILE f;
int c;
f._cnt = strlen(buf);
f._ptr = f._base = buf;
f._flag = _IOEOF;
f._file = 0;
while ((c = getc(&f)) != EOF) {
putchar(c);
fflush(stdout);
}
}
----- end -----
Note also that you could just as easily have passed &f to some other function.
--
Steve Watt
...!claris!wattres!steve wattres!steve@claris.com also works
Don't let your schooling get in the way of your education.
Re: File pointer to a memory location?
Author: Roland McGrath
Date: Tue, 11 Sep 1990 05:28
Date: Tue, 11 Sep 1990 05:28
10 lines
980 bytes
980 bytes
The GNU C library (which I have not yet released) has `fmemopen': /* Create a new stream that refers to a memory buffer. */ extern FILE *fmemopen(char *s, size_t len, const char *modes); I believe Chris Torek's stdio for 4.4 BSD has something similar. -- Roland McGrath Free Software Foundation, Inc. roland@ai.mit.edu, uunet!ai.mit.edu!roland
Re: File pointer to a memory location?
Author: Thomas Tornblom
Date: Wed, 12 Sep 1990 09:05
Date: Wed, 12 Sep 1990 09:05
57 lines
3054 bytes
3054 bytes
In article <119609@linus.mitre.org> rtidd@ccels3.mitre.org (Randy Tidd) writes:
With all these new comp.unix.* groups coming out, I hope it's
appropriate to cross-post to .programmer and .internals...
Anyhow, in the application i'm working on I have a series of routines
that were written by someone else that do image processing (the fbm
library, if you're familiar with it), including source. These
routines take a file pointer as an argument, and they read the
image-to-be-processed through this fp. Normally what you do is open a
file and pass in a file pointer to it, or pass in stdin and pipe your
image through the program through the shell.
The problem is in my application, I am using a database and thus don't
have files and thus I don't have file pointers either. What I *can*
do is query the database for an image, and it gives me a block of
memory that holds the image *exactly* as it is stored in file form.
So what I have is a block of memory, having exactly the same size and
contents of a file. What I have to do is pass my image processing
routines a file pointer that points to this block of memory. If the
routines used file *descriptors*, it wouldn't be a problem because I
could just use pipes and be done with it.
You can make a fp from a fd by fp = fdopen(fd, type) it would however
require all the data to pass through the kernel once more.
What I do now is query the database, get a block of memory, dump this
memory to a temporary file, open the file with a file pointer, and
pass the file pointer to the image processing routines. Not only is
this dumb, but images can be a big as 3 megs and this is incredibly
inefficient.
Depending on the system you are using and whether you are concerned
with portability it could be done by faking up an _iobuf struct (the things
fp:s point at) that would hold a pointer to the block of memory and
have all the rest of the members in the struct set up to some sane value.
Something along the line of:
(Warning this is untested and non portable)
---------------
#include <stdio.h>
struct _iobuf fake;
FILE *getimage()
{
char *image;
/* read the image from the db and have image point at it */
fake._ptr = fake._base = image;
fake._cnt = fake._bufsiz = image_size;
fake._flag = _IOREAD | _IOMYBUF;
fake._file = -1;
return &fake;
}
---------------
Re: File pointer to a memory location?
Author: Ulf Reimann
Date: Wed, 12 Sep 1990 11:30
Date: Wed, 12 Sep 1990 11:30
26 lines
1451 bytes
1451 bytes
rtidd@ccels3.mitre.org (Randy Tidd) writes: >So what I have is a block of memory, having exactly the same size and >contents of a file. What I have to do is pass my image processing >routines a file pointer that points to this block of memory. If the >routines used file *descriptors*, it wouldn't be a problem because I >could just use pipes and be done with it. Hi, one way to do it is to set up a FILE structure (see /usr/include/stdio.h for details, it's struct _iobuf) and pass it's address to the routine expecting the file pointer. I once saw that trick in some source to sscanf(). The routine creates an iobuf structure, puts the pointer to the passed string in it (for the buffer) and calls doscanf() which does the desired processing, but with a file pointer. If you have problems doing that, maybe I can write some example code for you, but I'm short on time now... Hope that helps... Ulf #include <disclaim.h> Ulf Reimann, Hummelweg 30, 2900 Oldenburg, W-Germany, phone +49 (441) 5704245 e-mail: "reimann@faramir.informatik.uni-oldenburg.de" or "reimann@uniol.uucp"
Re: File pointer to a memory location?
Author: Amos Shapira
Date: Wed, 12 Sep 1990 13:16
Date: Wed, 12 Sep 1990 13:16
59 lines
2326 bytes
2326 bytes
rtidd@ccels3.mitre.org (Randy Tidd) writes:
>So what I have is a block of memory, having exactly the same size and
>contents of a file. What I have to do is pass my image processing
>routines a file pointer that points to this block of memory. If the
>routines used file *descriptors*, it wouldn't be a problem because I
>could just use pipes and be done with it.
There are two ways:
1. Once you have a file descriptor, you can get a file pointer to it with
fdopen(3s).
The bad thing about a pipes-based solution is that you are limited by the
size of the pipe, which is usually 4K.
2. The secnd solution, which seems to me much better, is to make what you
have suggest in your subject line, i.e. create a file pointer which points
to a memory location, this is how sscanf(3s) and co. works.
Here is a quick hack to demonstrate what I mean:
FILE *
memopen (cp, len)
char *cp;
int len;
{
FILE *fp;
if ((fp = (FILE *)malloc(sizeof(*fp))) == NULL)
return (NULL);
fp->_bufsiz = fp->_cnt = len;
fp->_base = fp->_ptr = (unsigned char *)cp;
fp->_flag = (short)_IOREAD _IOSTRG;
return (fp);
}
The interpretation of fields, as far as I remember, is:
_cnt: how much left to read from the buffer.
_bufsiz: the buffer size set by setbuf(3s) (in the above function, might be
better set to zero).
_base: the pointer to the first char in the buf (used to read a new buffer).
_ptr: pointer to next char to read.
Refferences: Definition of the getc(3s) macro in /usr/include/stdio.h
If you have access to sscanf(3s) then this is the ultimate answer.
Test by reading a real file pointer (e.g. stdin) and examinning
its fields between reads.
>Randy Tidd GOOD
>rtidd@mwunix.mitre.org FAST
>#define DISCLAIM TRUE CHEAP
> -pick any two
Hope this helps,
Amos Shapira
amoss@batata.huji.ac.il
Re: File pointer to a memory location?
Author: Randy Tidd
Date: Wed, 12 Sep 1990 16:28
Date: Wed, 12 Sep 1990 16:28
31 lines
1511 bytes
1511 bytes
Thanks for all the info posted about my "file pointer to a memory location" problem. I really got some good ideas that I hadn't come up with myself. I haven't had the time to implement them yet (<sigh> so many projects, so little time), but when I do I will be sure to post a summary of what I learned. Something I didn't mention, this code DOES has to be portable, but since I have access to the few systems that it has to port to I could always just do #ifdef's here and there. The systems it currently has to run on are: Sun 3 running SunOS 4.1 Sun3 running SunOS 4.0.3 Compaq 386 running 386/ix 2.0.2 Compaq 486 running 386/ix 2.2 Mac IIx running A/UX 1.1 Mac IIci running A/UX 2.0 Thanks to: cpcahil@virtech.uucp (Conor P. Cahill) lwall@jpl-devvax.JPL.NASA.GOV (Larry Wall) roland@ai.mit.edu (Roland McGrath) steve@wattres.UUCP (Steve Watt) thomas@uplog.se (Thomas Tornblom) amoss@huji.ac.il (Amos Shapira) Randy Tidd GOOD rtidd@mwunix.mitre.org FAST #define DISCLAIM TRUE CHEAP -pick any two
Re: File pointer to a memory location?
Author: Chris Torek
Date: Thu, 13 Sep 1990 09:43
Date: Thu, 13 Sep 1990 09:43
58 lines
2639 bytes
2639 bytes
In article <amoss.653145372@shum> amoss@huji.ac.il (Amos Shapira) writes:
>FILE *
>memopen (cp, len)
>char *cp;
>int len;
>{
> FILE *fp;
>
> if ((fp = (FILE *)malloc(sizeof(*fp))) == NULL)
> return (NULL);
>
> fp->_bufsiz = fp->_cnt = len;
> fp->_base = fp->_ptr = (unsigned char *)cp;
> fp->_flag = (short)_IOREAD _IOSTRG;
>
> return (fp);
>}
Notes:
1. SysV stdio does not have a _bufsiz field. (The buffer
`size' is found by a bletcherous hack: if fp->_file is
not equal to NOFILE, it uses _bufendtab[fp->_file],
otherwise it assumes that the highest legal user-space
address is 0x7fffffff. This is HORRIBLE.)
2. 4.[0123]BSD stdio never tests _IOSTRG.
3. _base and _ptr point to `char', not unsigned char, in
many stdios.
4. 4.4BSD stdio does not have any of these fields. (The FILE
structure contains the following fields:
_p _r _w _flags _file _bf._base _bf._size _lbfsize
_cookie _read _write _seek _close _ub._base _ub._size
_up _ur _ubuf[] _nbuf[] _lb._base _lb._size _blksize
_offset
_p corresponds closely to _ptr, _r and _w to _cnt, and
_bf to _base and _bufsiz. _flags holds similar flags
to _flag, but there are differences. One of _r and _w
is always 0, so that getc and putc always work. Other
stdio getc's and putc's mysteriously fail if you switch
from reading to writing and forget to fseek.)
== GIANT CAVEAT ***WARNING*** DANGER WILL ROBINSON
== ALL OF THE APPROACHES BELOW except fmemopen/funopen WILL FAIL IF THE
== CODE CALLS setbuf OR setvbuf.
If you want to read a memory region using the V7/4BSD stdio, try:
fp->_ptr = addr; /* possibly with (unsigned char *) cast */
fp->_cnt = nbytes;
fp->_flag = _IOSTRG; /* make _filbuf return error */
Under SysV, you are in trouble. You can fopen /dev/null for reading
and replace _ptr and _cnt; this is likely to work.
Under 4.4BSD, use fmemopen (if we put it back in) or funopen and setvbuf
(which is how fmemopen is implemented).
--
In-Real-Life: Chris Torek, Univ of MD Comp Sci Dept (+1 301 405 2750)
Domain: chris@cs.umd.edu Path: uunet!mimsy!chris
Thread Navigation
This is a paginated view of messages in the thread with full content displayed inline.
Messages are displayed in chronological order, with the original post highlighted in green.
Use pagination controls to navigate through all messages in large threads.
Back to All Threads