C PROGRAM TO COPY A FILE USING SYSTEM CALLS

 These are the instructions to copy a file using C in a UNIX environment:

  • The source file needs to be opened in read-only mode.
  • The destination file needs to be opened in write mode.
  • If the destination file does not already exist, then it should be created by the program.
  • Then bytes are read from the source file and written to the destination file until the source file gets over.
  • The file descriptors must be closed before the program terminates.

The header files required are:

  • stdio.h for printf function
  • unistd.h for opencloseread, and write system calls
  • fcntl.h for constants prefixed with O_ and S_

The last two are only found in a Linux enviroment. If you want to execute the program on Windows, consider installing Cygwin or WSL.

The prototypes for the open system call are:

int open(const char *pathname, int flags); 
int open(const char *pathname, int flags, int mode); 

The parameter flags must include one of the following access modes: O_RDONLYO_WRONLY, or O_RDWR meaning opening the file read-only, write-only, or read/write, respectively. The file creation flags are O_CREATO_EXCLO_NOCTTY, and O_TRUNC. Zero or more file creation flags and file status flags can be bitwise-or'd in flags. The last parameter mode refers to permissions. open() return the new file descriptor, or -1 if an error occurred.

The prototype for the read system call is:

ssize_t read(int fd, void *buf, size_t count); 

This function attempts to read up to count bytes from file descriptor fd into the buffer starting at buf. The number of bytes read is returned. In case of an error, -1 is returned. If 0 is returned, that means EOF has been reached.

Program:

#include <stdio.h>
#include <unistd.h>
#include <fcntl.h> 

void main()
{
	char buf;
	int fd_one, fd_two;

	fd_one = open("first_file", O_RDONLY);

	if (fd_one == -1)
	{
		printf("Error opening first_file\n");
		close(fd_one);
		return;
	}

	fd_two = open("second_file", 
				  O_WRONLY | O_CREAT,
				  S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
	
	while(read(fd_one, &buf, 1))
	{
		write(fd_two, &buf, 1);
	}

	printf("Successful copy");

	close(fd_one);
	close(fd_two);
}

first_file (before):

hello world
bye

second_file (after):

hello world
bye

Let us discuss the line fd_two = open("second_file", O_WRONLY | O_CREAT, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);O_CREAT means that the file is created if it does not exist and O_WRONLY means that it is opened in write mode. The third parameter indicates permissions assigned to the file if it is created. If we omit this third parameter, then the second_file will be created with permissions ---sr-x--T. You can look at the permissions by running $ ls -l second_file. These permissions mean that the file cannot be read from or written to by the user. If you were to create a file using the terminal, it would be assigned the default permissions -rw-r--r--. These permissions indicate, and can be achieved with the flag:

  • Can be read by user; S_IRUSR
  • Can be written by user; S_IWUSR
  • Can be read by users in group; S_IRGRP
  • Can be read by others; S_IROTH irusr or iwusr or irgrp or iroth = rw-r--r--

Comments

Popular posts from this blog

OOP Assignment 3 helping materials

Square root Algorithm in C++

OOP lab 7 task solution