#include <sys/types.h>		/* types in read/write/seek */
#include <unistd.h>
#include <stdio.h>		/* for perror */
#include <errno.h>		/* for error number */

#include "global_defs.h"
#include "page.h"		/* for page size */
#include "random_rw.h"

/* Reads a page from disk, given the page address and the file descriptor
 */

int random_read( int fd, int page_no, void * the_page )
{
	off_t lseekrv;		/* return value from lseek */
	int result;

#ifdef VERBOSE
	printf("Reading page %d\n", page_no);
#endif    
	if (page_no < 0) {
		fprintf(stderr, "error in random_read: negative page number\n");
		return NEGATIVE_PAGE_NUMBER;
	}
	/* SEEK_SET is a magic constant.  See the man page for lseek() */
#ifdef VERBOSE
	printf("Seeking to %d\n", page_no * PAGESIZE);
	perror("before lseek");
#endif    
	lseekrv = lseek(fd, page_no * PAGESIZE, SEEK_SET);
	if ( -1 == lseekrv ) {
		perror("Ack!  Error in random_read() lseek()");
		fprintf(stderr, "lseek rv = %ld\n", lseekrv);
		return LSEEK_ERROR;
	}

	result = read(fd, the_page, PAGESIZE);
	if (result != PAGESIZE) {
		perror("Error in random_read read");
		return READ_ERROR;
	}
#ifdef VERBOSE
	printf("read was successful\n");
#endif    
	return OK;
}

/* Writes a page to disk, given the page number, file descriptor and a
 * page object to read into.
 */
int random_write( int fd, int page_no, void * the_page )
{
	int size;

#ifdef VERBOSE
	printf("Reading page %d\n", page_no);
#endif    
	if (page_no < 0)
		return NEGATIVE_PAGE_NUMBER; 
	/* SEEK_SET is a magic constant.  See the man page for lseek() */
#ifdef VERBOSE
	printf("Seeking to %d\n", page_no * PAGESIZE);
#endif    
	if ( -1 == lseek(fd, page_no * PAGESIZE, SEEK_SET)) {
		perror("Error in random_write lseek");
		return LSEEK_ERROR;
	}
	size = write(fd, the_page,PAGESIZE);
	if ( size != PAGESIZE ) {
		perror("Error in random_write write");
		return WRITE_ERROR;
	}
#ifdef VERBOSE
	printf("write was successful\n");
#endif    
	return OK;
}
