11
** PSIO_RW(): Central function for all reads and writes on a PSIO unit.
13
** \params unit = The PSI unit number.
14
** \params buffer = The buffer containing the bytes for the read/write event.
15
** \params address = the PSIO global address for the start of the read/write.
16
** \params size = The number of bytes to read/write.
17
** \params = Indicates if the call is to read (0) or write (0) the input data.
21
int psio_rw(unsigned int unit, char *buffer, psio_address address, ULI size, int wrt)
28
ULI this_page, this_page_max, this_page_total;
29
unsigned int first_vol, this_vol, numvols;
30
ULI bytes_left, num_full_pages;
33
this_unit = &(psio_unit[unit]);
34
numvols = this_unit->numvols;
36
offset = address.offset;
38
/* Seek all volumes to correct starting positions */
39
first_vol = page % numvols;
40
errcod = psio_volseek(&(this_unit->vol[first_vol]), page, offset, numvols);
41
if(errcod == -1) psio_error(unit,PSIO_ERROR_LSEEK);
42
for(i=1,this_page=page+1; i < numvols; i++,this_page++) {
43
this_vol = this_page % numvols;
44
errcod = psio_volseek(&(this_unit->vol[this_vol]), this_page,
46
if(errcod == -1) psio_error(unit,PSIO_ERROR_LSEEK);
49
/* Number of bytes left on the first page */
50
this_page_max = PSIO_PAGELEN - offset;
52
/* If we have enough room on this page, use it */
53
if(size <= this_page_max) this_page_total = size;
54
else this_page_total = this_page_max;
58
errcod_uli = write(this_unit->vol[first_vol].stream, &(buffer[buf_offset]),
60
if(errcod_uli != this_page_total) psio_error(unit,PSIO_ERROR_WRITE);
63
errcod_uli = read(this_unit->vol[first_vol].stream, &(buffer[buf_offset]),
65
if(errcod_uli != this_page_total) psio_error(unit,PSIO_ERROR_READ);
68
/* Total number of bytes remaining to be read/written */
69
bytes_left = size - this_page_total;
71
/* Read/Write all the full pages */
72
num_full_pages = bytes_left/PSIO_PAGELEN;
73
buf_offset += this_page_total;
74
for(i=0,this_page=page+1; i < num_full_pages; i++,this_page++) {
75
this_vol = this_page % numvols;
76
this_page_total = PSIO_PAGELEN;
78
errcod_uli = write(this_unit->vol[this_vol].stream, &(buffer[buf_offset]),
80
if(errcod_uli != this_page_total) psio_error(unit,PSIO_ERROR_WRITE);
83
errcod_uli = read(this_unit->vol[this_vol].stream, &(buffer[buf_offset]),
85
if(errcod_uli != this_page_total) psio_error(unit,PSIO_ERROR_READ);
87
buf_offset += this_page_total;
90
/* Read/Write the final partial page */
91
bytes_left -= num_full_pages * PSIO_PAGELEN;
92
this_vol = this_page % numvols;
95
errcod_uli = write(this_unit->vol[this_vol].stream, &(buffer[buf_offset]),
97
if(errcod_uli != bytes_left) psio_error(unit,PSIO_ERROR_WRITE);
100
errcod_uli = read(this_unit->vol[this_vol].stream, &(buffer[buf_offset]),
102
if(errcod_uli != bytes_left) psio_error(unit,PSIO_ERROR_READ);