Velocity Reviews - Computer Hardware Reviews

Velocity Reviews > Newsgroups > Programming > C Programming > copying files

Reply
Thread Tools

copying files

 
 
Hans Vlems
Guest
Posts: n/a
 
      02-16-2012
I'm maintaing large numbers of Adobe Reader files (.pdf). One of my
programs, written in C (gcc 4.4.4), must make a copies between
different filesystems of these pdf files.
There is AFAIK no library function that does this, which leaves me two
options:
1- use the console interface, i.e. build a command string and pass
this to system().
2- open the file, copy the contents and close the target
I'd rather avoid option 1 because system runs out of control of my
program.
My question is what read and write functions are best suited to copy
the (binary) pdf files?
'Performance is not the main objective, but I want to be sure that the
copy finished succesfully and accurately.
Hans
 
Reply With Quote
 
 
 
 
Malcolm McLean
Guest
Posts: n/a
 
      02-16-2012
On Feb 16, 9:03*am, Hans Vlems <(E-Mail Removed)> wrote:
> I'm maintaing large numbers of Adobe Reader files (.pdf). One of my
> programs, written in C (gcc 4.4.4), must make a copies between
> different filesystems of these pdf files.
> There is AFAIK no library function that does this, which leaves me two
> options:
> 1- use the console interface, i.e. build a command string and pass
> this to system().
> 2- open the file, copy the contents and close the target
> I'd rather avoid option 1 because system runs out of control of my
> program.
> My question is what read and write functions are best suited to copy
> the (binary) pdf files?
> 'Performance is not the main objective, but I want to be sure that the
> copy finished succesfully and accurately.
> Hans


/*
Untested code

return -2 can't open input, -3 can't open output, -1 read/write
error (probably hardware problems).
*/
int copy(const char *dest, const char *source)
{
FILE *fpin;
FILE *fpout;
int err;
int ch;

fpin = fopen(source, "rb2");
if(!fpin)
return -2;
fpout = fopen(dest, "wb");
if(!fpout)
{
fclose(fpin);
return -3;
}
while( (ch = fgetc(fpin)) != EOF)
{
err = fputc(ch, fpout);
if(err == EOF)
goto error_exit;
}
/* if EOF was generated by read error instead of end of file, feof
is false */
if(!feof(fpin))
goto error_exit;
fclose(fpin);
/* we need to check that fclose flushes data to destination
correctly */
err = fclose(fpout);
if(err == EOF)
goto error_exit;
return 0;

/* read/write error */
error_exit:
fclose(fpin);
fclose(fpout);
return -1;
}
 
Reply With Quote
 
 
 
 
Keith Thompson
Guest
Posts: n/a
 
      02-16-2012
Malcolm McLean <(E-Mail Removed)> writes:
[...]
> fpin = fopen(source, "rb2");

[...]

Is "rb2" a typo?

--
Keith Thompson (The_Other_Keith) http://www.velocityreviews.com/forums/(E-Mail Removed) <http://www.ghoti.net/~kst>
Will write code for food.
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"
 
Reply With Quote
 
Keith Thompson
Guest
Posts: n/a
 
      02-16-2012
Hans Vlems <(E-Mail Removed)> writes:
> I'm maintaing large numbers of Adobe Reader files (.pdf). One of my
> programs, written in C (gcc 4.4.4), must make a copies between
> different filesystems of these pdf files.
> There is AFAIK no library function that does this, which leaves me two
> options:
> 1- use the console interface, i.e. build a command string and pass
> this to system().
> 2- open the file, copy the contents and close the target
> I'd rather avoid option 1 because system runs out of control of my
> program.
> My question is what read and write functions are best suited to copy
> the (binary) pdf files?
> 'Performance is not the main objective, but I want to be sure that the
> copy finished succesfully and accurately.


I'd just invoke the OS's command to copy the files ("cp" on
Unix-like systems, "copy" on Windows, probably something else on
other systems). It's likely to be at least as fast as anything
you write yourself, and it may preserve metadata (permissions,
etc.) that you're not going to be able to handle in your own code
without considerable difficulty.

I'm not sure why system running "out of control" of your program
should be an issue; can you elaborate?

--
Keith Thompson (The_Other_Keith) (E-Mail Removed) <http://www.ghoti.net/~kst>
Will write code for food.
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"
 
Reply With Quote
 
JohnF
Guest
Posts: n/a
 
      02-16-2012
Hans Vlems <(E-Mail Removed)> wrote:
> I'm maintaing large numbers of Adobe Reader files (.pdf). One of my
> programs, written in C (gcc 4.4.4), must make a copies between
> different filesystems of these pdf files.
> There is AFAIK no library function that does this, which leaves me two
> options:
> 1- use the console interface, i.e. build a command string and pass
> this to system().
> 2- open the file, copy the contents and close the target
> I'd rather avoid option 1 because system runs out of control of my
> program.
> My question is what read and write functions are best suited to copy
> the (binary) pdf files?
> 'Performance is not the main objective, but I want to be sure that the
> copy finished succesfully and accurately.
> Hans


I'm guessing you're already aware of what Malcolm suggested
in preceding followup, and it's not adequate. And since I've
read your posts in comp.os.vms, I'm also guessing we're
talking about an ods-2/5 filesystem at one end, and maybe a
linux ext3, or whatever, at the other. Could you elaborate on
that a little? And does linux have some ods-2/5 support so you
can mount a vms disk? I wasn't aware of that. If you can indeed
just mount it, then by all means try Malcolm's suggestion and
see what happens. Should just work if the ods filesystem support
is any good. Otherwise, how are you intending to even access
the disk? Decnet for linux (note that it's no longer being
very actively supported)? I think that would be the driving
question that dictates an appropriate answer to your question.
So you need to supply all that additional info first.
By the way, I usually just ftp zipped files back and forth
between vms and linux boxes on my soho lan. Despite your
"out of control" issue, I'd just write a script (using C's
system() if you want the script in C) to do the job, unless
security's some really, really significant issue for your
situation.
--
John Forkosh ( mailto: (E-Mail Removed) where j=john and f=forkosh )
 
Reply With Quote
 
Nobody
Guest
Posts: n/a
 
      02-16-2012
On Thu, 16 Feb 2012 01:03:12 -0800, Hans Vlems wrote:

> I'm maintaing large numbers of Adobe Reader files (.pdf). One of my
> programs, written in C (gcc 4.4.4), must make a copies between
> different filesystems of these pdf files.
> There is AFAIK no library function that does this, which leaves me two
> options:
> 1- use the console interface, i.e. build a command string and pass
> this to system().


Avoid system() unless executing a "canned" command supplied by the user.
If you need to spawn a child process with specific arguments, use fork()
and exec*() rather than attempting to construct a shell command.

> 2- open the file, copy the contents and close the target


First, you need to decide what you mean by "copy". Part of the reason that
there isn't a library function is that there isn't a single obvious
definition of what it means to copy a file. Two plausible choices are:

1. open() the destination, write the contents of the source to it, close()
it.

2. open() a temporary file in the same directory as the destination,
write the contents of the source to it, close() it, rename() it over the
original.

The two alternatives have many differences, including (but not limited to):

1. If there are multiple hard links to the destination, #1 will leave all
links intact, and all will refer to the modified file. #2 will break one
specific hard link, causing the filename to point to a new file; the
others will still refer to the original file.

2. If the destination file is open in some other process, #1 will cause
the process to immediately see the new contents, while #2 will only affect
processes which open() the file after the rename() has occurred.

3. #1 requires that you have write permission on the destination file if
it exists, or write permission on the directory if it doesn't. #2 requires
that you have write permission on the directory (the file's permissions
don't matter); if the destination exists and the directory has the sticky
bit set, you must own the file (or be root).

4. #1 won't affect the owner, group or permissions of an existing file. #2
will create a new file with your uid, primary gid and umask.

5. If the destination exists and is a device (block or character) or FIFO,
#1 will open() it and write to it. #2 will replace it with a file.

6. If the destination exists and is a symlink, #1 will open() it (i.e.
open its target) and write to it. #2 will replace it with a file.

Note that the Unix "cp" command is similar to option #1, except that if
the file exists but open()ing it fails and the "-f" flag is used, it
attempts to unlink() it then, if that succeeds, proceeds as if the file
didn't exist.

> I'd rather avoid option 1 because system runs out of control of my
> program.
> My question is what read and write functions are best suited to copy
> the (binary) pdf files?
> 'Performance is not the main objective, but I want to be sure that the
> copy finished succesfully and accurately.


For robustness, choose option #2 above. If writing the file fails,
remove() the temporary file rather than rename()ing it. The original file
will be left intact.

Performance-wise, mmap()ing the source and write()ing directly from the
mmap()d region eliminates a copy. mmap()ing both source and destination
and memcpy()ing may or may nor provide any additional benefit.

 
Reply With Quote
 
Hans Vlems
Guest
Posts: n/a
 
      02-16-2012
On 16 feb, 10:49, JohnF <(E-Mail Removed)> wrote:
> Hans Vlems <(E-Mail Removed)> wrote:
> > I'm maintaing large numbers of Adobe Reader files (.pdf). One of my
> > programs, written in C (gcc 4.4.4), must make a copies between
> > different filesystems of these pdf files.
> > There is AFAIK no library function that does this, which leaves me two
> > options:
> > 1- use the console interface, i.e. build a command string and pass
> > this to system().
> > 2- open the file, copy the contents and close the target
> > I'd rather avoid option 1 because system runs out of control of my
> > program.
> > My question is what read and write functions are best suited to copy
> > the (binary) pdf files?
> > 'Performance is not the main objective, but I want to be sure that the
> > copy finished succesfully and accurately.
> > Hans

>
> I'm guessing you're already aware of what Malcolm suggested
> in preceding followup, and it's not adequate. And since I've
> read your posts in comp.os.vms, I'm also guessing we're
> talking about an ods-2/5 filesystem at one end, and maybe a
> linux ext3, or whatever, at the other. Could you elaborate on
> that a little? And does linux have some ods-2/5 support so you
> can mount a vms disk? I wasn't aware of that. If you can indeed
> just mount it, then by all means try Malcolm's suggestion and
> see what happens. Should just work if the ods filesystem support
> is any good. Otherwise, how are you intending to even access
> the disk? Decnet for linux (note that it's no longer being
> very actively supported)? I think that would be the driving
> question that dictates an appropriate answer to your question.
> So you need to supply all that additional info first.
> * *By the way, I usually just ftp zipped files back and forth
> between vms and linux boxes on my soho lan. Despite your
> "out of control" issue, I'd just write a script (using C's
> system() if you want the script in C) to do the job, unless
> security's some really, really significant issue for your
> situation.
> --
> John Forkosh *( mailto: *(E-Mail Removed) *where j=john and f=forkosh)- Tekst uit oorspronkelijk bericht niet weergeven -
>
> - Tekst uit oorspronkelijk bericht weergeven -


John,
your investigating powers are impressive! Unfortunately they've led
you into a dead end street...
On a VMS system I wouldn't have had the need to ask a question. VMS
has an IO subsystem (RMS) and a neatly documented API.
And I doubt I'd have used C to solve this problem since I have a
choice of at least 4 other languages that I'm more
comfortable with...
The project I'm involved in runs on a Windows platform, on Citrix
servers more precisely and I have _no_ provileges on these
systems. The reason I use the (old) DJGPP compiler is that doesn't
need a Windows install process that uses the registry.
The command line interface on WIndows doesn't even come close to what
DCL has to offer. But I digress.

I want to copy pdf files from one windows disk to another, so the
rename() function is useless. Next, I must retain the original file
which is another reason why rename() won't do.
C has a choice of functions to read from and write to diskfiles. I
want to be sure that all content gets copied, unaltered and without
inflating the file too much. One option is to read the input file one
byte at a time and write it until EOF is signalled.
Or read blocks, say 1 kB, and write them. Probably faster but may have
other drawbacks I'm not aware of.
The original post was written with this in mind and that was perhaps
not too smart.

Hans
 
Reply With Quote
 
Hans Vlems
Guest
Posts: n/a
 
      02-16-2012
On 16 feb, 10:23, Malcolm McLean <(E-Mail Removed)>
wrote:
> On Feb 16, 9:03*am, Hans Vlems <(E-Mail Removed)> wrote:
>
> > I'm maintaing large numbers of Adobe Reader files (.pdf). One of my
> > programs, written in C (gcc 4.4.4), must make a copies between
> > different filesystems of these pdf files.
> > There is AFAIK no library function that does this, which leaves me two
> > options:
> > 1- use the console interface, i.e. build a command string and pass
> > this to system().
> > 2- open the file, copy the contents and close the target
> > I'd rather avoid option 1 because system runs out of control of my
> > program.
> > My question is what read and write functions are best suited to copy
> > the (binary) pdf files?
> > 'Performance is not the main objective, but I want to be sure that the
> > copy finished succesfully and accurately.
> > Hans

>
> /*
> * *Untested code
>
> * *return -2 can't open input, -3 can't open output, -1 read/write
> error (probably hardware problems).
> */
> int copy(const char *dest, const char *source)
> {
> * FILE *fpin;
> * FILE *fpout;
> * int err;
> * int ch;
>
> * fpin = fopen(source, "rb2");
> * if(!fpin)
> * * return -2;
> * fpout = fopen(dest, "wb");
> * if(!fpout)
> * {
> * * fclose(fpin);
> * * return -3;
> * }
> * while( (ch = fgetc(fpin)) != EOF)
> * {
> * * err = fputc(ch, fpout);
> * * if(err == EOF)
> * * * goto error_exit;
> * }
> * /* if EOF was generated by read error instead of end of file, feof
> is false */
> * if(!feof(fpin))
> * * goto error_exit;
> * fclose(fpin);
> * /* we need to check that fclose flushes data to destination
> correctly */
> * err = fclose(fpout);
> * if(err == EOF)
> * * goto error_exit;
> * return 0;
>
> * /* read/write error */
> error_exit:
> * fclose(fpin);
> * fclose(fpout);
> * return -1;
>
>
>
> }- Tekst uit oorspronkelijk bericht niet weergeven -
>
> - Tekst uit oorspronkelijk bericht weergeven -


Malcolm,
thanks for the example. Copying the input file one byte per read
(getch) operation may not be the fastest way,
it does not inflate the detsination filesize (we pay for dsk storage
here).
Hans
 
Reply With Quote
 
Hans Vlems
Guest
Posts: n/a
 
      02-16-2012

On 16 feb, 10:31, Keith Thompson <(E-Mail Removed)> wrote:
> Malcolm McLean <(E-Mail Removed)> writes:
>
> [...]> * fpin = fopen(source, "rb2");
>
> [...]
>
> Is "rb2" a typo?
>
> --
> Keith Thompson (The_Other_Keith) (E-Mail Removed) *<http://www.ghoti.net/~kst>
> * * Will write code for food.
> "We must do something. *This is something. *Therefore, we must do this."
> * * -- Antony Jay and Jonathan Lynn, "Yes Minister"


Possibly, but the setting the proper filemode is not my main concern.
Hans
 
Reply With Quote
 
Kleuske
Guest
Posts: n/a
 
      02-16-2012
On Thu, 16 Feb 2012 01:03:12 -0800, Hans Vlems saw fit to publish the
following:

> I'm maintaing large numbers of Adobe Reader files (.pdf). One of my
> programs, written in C (gcc 4.4.4), must make a copies between different
> filesystems of these pdf files. There is AFAIK no library function that
> does this, which leaves me two options:
> 1- use the console interface, i.e. build a command string and pass this
> to system().


Don't. It's ineffective and may open up your system to abuse.


> 2- open the file, copy the contents and close the target I'd rather
> avoid option 1 because system runs out of control of my program.
> My question is what read and write functions are best suited to copy the
> (binary) pdf files?


Try fopen, fread, fwrite and fclose. Use a big buffer, since PDF's (especially
with grahics) tend to be big.

> 'Performance is not the main objective, but I want to be sure that the
> copy finished succesfully and accurately. Hans


Check for error codes.

--
Each kiss is as the first.
-- Miramanee, Kirk's wife, "The Paradise Syndrome",
stardate 4842.6
 
Reply With Quote
 
 
 
Reply

Thread Tools

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Copying files to Vista Program Files in ruby script Shawn Mcclain Ruby 0 09-28-2007 09:21 PM
XCOPY is not copying ascx files while it copies .dll files c.verma@gmail.com ASP .Net 0 01-14-2005 07:29 PM
copying multiple files yaduraj Perl 1 08-09-2004 06:06 PM
Copying files ......... ALPO ASP .Net 1 12-20-2003 09:33 PM
moving and copying encrypted files Paul L MCSE 8 11-04-2003 03:21 AM



Advertisments