SIONlib  1.7.1
Scalable I/O library for parallel access to task-local files
sion_internal_seek.c
Go to the documentation of this file.
1 /****************************************************************************
2 ** SIONLIB http://www.fz-juelich.de/jsc/sionlib **
3 *****************************************************************************
4 ** Copyright (c) 2008-2016 **
5 ** Forschungszentrum Juelich, Juelich Supercomputing Centre **
6 ** **
7 ** See the file COPYRIGHT in the package base directory for details **
8 ****************************************************************************/
9 
14 #include <stdlib.h>
15 #include <stdio.h>
16 #include <stdarg.h>
17 #include <string.h>
18 #include <time.h>
19 
20 #include <sys/time.h>
21 
22 #include "sion.h"
23 #include "sion_debug.h"
24 #include "sion_error_handler.h"
25 #include "sion_internal.h"
26 #include "sion_metadata.h"
27 #include "sion_filedesc.h"
28 #include "sion_fd.h"
29 #include "sion_file.h"
30 #include "sion_printts.h"
31 #include "sion_buffer.h"
32 
33 #include "sion_internal_seek.h"
34 
35 
36 #define DFUNCTION "_sion_seek_on_all_ranks_read"
37 
51  int rank,
52  int blocknr,
53  sion_int64 posinblk ) {
54  int rc = SION_SUCCESS;
55  int blknum;
56 
57  DPRINTFP((2, DFUNCTION, -1, "enter seek r=%d b=%d p=%ld fn=%s\n",
58  rank,blocknr, (long) posinblk,sion_filedesc->fname));
59 
60  if ((sion_filedesc->all_blockcount == NULL)
61  || (sion_filedesc->all_blocksizes == NULL)) {
62  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
63  "sion_seek: internal error, data structure not initialized, aborting ...\n"));
64  }
65 
66  /* check if RANK changed */
67  if ( (rank != SION_CURRENT_RANK) && (rank != sion_filedesc->rank) ) {
68 
69  DPRINTFP((32, DFUNCTION, -1, "rank has changed %d -> %d\n", sion_filedesc->rank, rank));
70 
71  if ((rank<0) || (rank >= sion_filedesc->ntasks)) {
72  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: parameter rank %d (max. %d) out of range, aborting ...\n",
73  rank, sion_filedesc->ntasks));
74  }
75 
76  /* check and update current position */
77  _sion_update_fileposition(sion_filedesc);
78 
79  /* store current position in all_* vectors */
80  sion_filedesc->all_currentpos[sion_filedesc->rank] = sion_filedesc->currentpos;
81  sion_filedesc->all_currentblocknr[sion_filedesc->rank] = sion_filedesc->currentblocknr;
82 
83  /* pointer to keyval structure */
84  if(sion_filedesc->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc->all_keyvalptr[sion_filedesc->rank] = sion_filedesc->keyvalptr;
85 
86  /* switch to new rank and restore current position of this rank */
87  sion_filedesc->rank = rank;
88  sion_filedesc->currentblocknr = sion_filedesc->all_currentblocknr[sion_filedesc->rank];
89  sion_filedesc->currentpos = sion_filedesc->all_currentpos[sion_filedesc->rank];
90  sion_filedesc->lastchunknr = sion_filedesc->all_blockcount[sion_filedesc->rank]-1;
91  sion_filedesc->startpos = sion_filedesc->all_startpointers[sion_filedesc->rank];
92  sion_filedesc->chunksize = sion_filedesc->all_chunksizes[sion_filedesc->rank];
93 
94  /* pointer to keyval structure */
95  if(sion_filedesc->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc->keyvalptr=sion_filedesc->all_keyvalptr[sion_filedesc->rank];
96 
97  for (blknum = 0; blknum <= sion_filedesc->lastchunknr; blknum++) {
98  sion_filedesc->blocksizes[blknum] = sion_filedesc->all_blocksizes[sion_filedesc->ntasks * blknum + sion_filedesc->rank];
99  }
100 
101  /* /\* do nothing on empty blocks *\/ */
102  /* if (!sion_filedesc->lastchunknr) { */
103  /* rc = SION_NOT_SUCCESS; */
104  /* DPRINTFP((2, DFUNCTION, -1, "leave seek rc=%d\n",rc)); */
105  /* return rc; */
106  /* } */
107 
108  /* rank has changed, therefore this information could not get from fileposition */
109  if (blocknr == SION_CURRENT_BLK) {
110  blocknr=sion_filedesc->currentblocknr;
111  }
112  if (posinblk == SION_CURRENT_POS) {
113  posinblk=sion_filedesc->currentpos - (sion_filedesc->startpos + sion_filedesc->currentblocknr * sion_filedesc->globalskip);
114 
115  if(sion_filedesc->keyvalmode==SION_KEYVAL_NONE) {
116 
117  /* check if just behind current block, go to next block */
118  if(posinblk>=sion_filedesc->blocksizes[blocknr]) {
119  posinblk=0;
120  /* do no more checks on empty blocks */
121  if (sion_filedesc->lastchunknr) {
122  blocknr++;
123  if(blocknr > sion_filedesc->lastchunknr) {
124  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: seek after end of file, returning ...\n"));
125  }
126  }
127  }
128 
129  }
130  }
131 
132  }
133 
134  /* seek new position in current rank, sets in all cases the filepointer */
135  rc=_sion_seek_on_current_rank_read(sion_filedesc,SION_CURRENT_RANK,blocknr,posinblk);
136 
137  DPRINTFP((2, DFUNCTION, -1, "leave seek rc=%d\n",rc));
138 
139  return(rc);
140 
141 }
142 #undef DFUNCTION
143 
144 #define DFUNCTION "_sion_seek_on_all_ranks_read_master"
145 
159  int rank,
160  int blocknr,
161  sion_int64 posinblk ) {
162  int rc = SION_SUCCESS;
163  int blknum, lfile, lrank;
164 
165  DPRINTFP((2, DFUNCTION, -1, "enter seek r=%d b=%d p=%ld fn=%s\n",
166  rank,blocknr, (long) posinblk,sion_filedesc->fname));
167 
168 #if 0
169  if ((sion_filedesc->all_blockcount == NULL)
170  || (sion_filedesc->all_blocksizes == NULL)) {
171  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
172  "sion_seek: internal error, data structure not initialized, aborting ...\n"));
173  }
174 #endif
175 
176  /* lookup file which contains current rank */
177  lfile=sion_filedesc->mapping[sion_filedesc->rank*2+0];
178  lrank=sion_filedesc->mapping[sion_filedesc->rank*2+1];
179 
180  /* check if RANK changed */
181  if ( (rank != SION_CURRENT_RANK) && (rank != sion_filedesc->rank) ) {
182 
183  if ((rank<0) || (rank >= sion_filedesc->ntasks)) {
184  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: parameter rank %d (max. %d) out of range, aborting ...\n",
185  rank, sion_filedesc->ntasks));
186  }
187 
188  /* check and update current position */
189  _sion_update_fileposition(sion_filedesc);
190 
191  /* store current position in all_* vectors */
192  sion_filedesc->multifiles[lfile]->all_currentpos[lrank] = sion_filedesc->currentpos;
193  sion_filedesc->multifiles[lfile]->all_currentblocknr[lrank] = sion_filedesc->currentblocknr;
194 
195  /* pointer to keyval structure */
196  if(sion_filedesc->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc->multifiles[lfile]->all_keyvalptr[lrank] = sion_filedesc->keyvalptr;
197 
198 
199  /* switch to new rank and restore current position of this rank */
200  sion_filedesc->rank = rank;
201 
202  /* lookup again file which contains current rank */
203  lfile=sion_filedesc->mapping[sion_filedesc->rank*2+0];
204  lrank=sion_filedesc->mapping[sion_filedesc->rank*2+1];
205 
206 
207  sion_filedesc->currentblocknr = sion_filedesc->multifiles[lfile]->all_currentblocknr[lrank];
208  sion_filedesc->currentpos = sion_filedesc->multifiles[lfile]->all_currentpos[lrank];
209  sion_filedesc->lastchunknr = sion_filedesc->multifiles[lfile]->all_blockcount[lrank]-1;
210  sion_filedesc->startpos = sion_filedesc->multifiles[lfile]->all_startpointers[lrank];
211  sion_filedesc->chunksize = sion_filedesc->multifiles[lfile]->all_chunksizes[lrank];
212  sion_filedesc->globalskip = sion_filedesc->multifiles[lfile]->globalskip;
213  for (blknum = 0; blknum < sion_filedesc->multifiles[lfile]->all_blockcount[lrank]; blknum++) {
214  sion_filedesc->blocksizes[blknum] = sion_filedesc->multifiles[lfile]->all_blocksizes[sion_filedesc->multifiles[lfile]->ntasks * blknum + lrank];
215  }
216  sion_filedesc->fileptr = sion_filedesc->multifiles[lfile]->fileptr;
217 
218  DPRINTFP((32, DFUNCTION, -1, "switch to file %d and lrank %d currentpos=%ld, currentblocknr=%d\n",lfile, lrank,(long) sion_filedesc->currentpos, sion_filedesc->currentblocknr ));
219 
220  /* pointer to keyval structure */
221  if(sion_filedesc->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc->keyvalptr=sion_filedesc->multifiles[lfile]->all_keyvalptr[lrank];
222 
223  /* set rank info in sub-file */
224  sion_filedesc->multifiles[lfile]->rank=lrank;
225 
226  /* rank has changed, therefore this information could not get from fileposition */
227  if (blocknr == SION_CURRENT_BLK) {
228  blocknr=sion_filedesc->currentblocknr;
229  }
230  if (posinblk == SION_CURRENT_POS) {
231  posinblk=sion_filedesc->currentpos - (sion_filedesc->startpos + sion_filedesc->currentblocknr * sion_filedesc->globalskip);
232 
233  if(sion_filedesc->keyvalmode==SION_KEYVAL_NONE) {
234 
235  /* check if just behind current block, go to next block */
236  if(posinblk>=sion_filedesc->blocksizes[blocknr]) {
237  posinblk=0;blocknr++;
238  if(blocknr > sion_filedesc->lastchunknr) {
239  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: seek after end of file, returning ...\n"));
240  }
241  }
242 
243  }
244  }
245 
246  }
247 
248  /* seek new position in current rank in sub-file, sets in all cases the filepointer */
249  rc=_sion_seek_on_current_rank_read(sion_filedesc,SION_CURRENT_RANK,blocknr,posinblk);
250 
251  DPRINTFP((2, DFUNCTION, -1, "leave seek rc=%d\n",rc));
252 
253  return(rc);
254 
255 }
256 #undef DFUNCTION
257 
258 
259 #define DFUNCTION "_sion_seek_on_current_rank_read"
260 
272  int rank,
273  int blocknr,
274  sion_int64 posinblk ) {
275  int rc = SION_SUCCESS;
276  int newblocknr = -1;
277  sion_int64 newposinblk=-1;
278 
279  DPRINTFP((2, DFUNCTION, -1, "enter seek r=%d b=%d p=%ld fn=%s\n",rank,blocknr, (long) posinblk,sion_filedesc->fname));
280 
281 
282  /* check RANK */
283  if ( (rank != SION_CURRENT_RANK) && (rank != sion_filedesc->rank) ) {
284  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
285  "sion_seek: parameter rank is different from current rank in parallel openened file, returning ...\n"));
286  }
287 
288  /* check requested BLOCK NUMBER */
289  if (blocknr == SION_ABSOLUTE_POS) {
290  /* search absolute position */
291  if(!_sion_seek_search_abs_pos(sion_filedesc,posinblk,&newblocknr,&newposinblk)) {
292  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN, "sion_seek: error in searching abs pos, returning ...\n"));
293  } else posinblk=newposinblk; /* for checking posinblk later */
294  DPRINTFP((32, DFUNCTION, -1, "sion_absolute_pos newblocknr=%d newpos=%ld fn=%s\n",newblocknr, (long) newposinblk, sion_filedesc->fname));
295  }
296  else if (blocknr == SION_END_POS) {
297  /* search position relative to end */
298  if (!_sion_seek_search_end_pos(sion_filedesc, posinblk, &newblocknr, &newposinblk)) {
299  return _sion_errorprint(SION_NOT_SUCCESS, _SION_ERROR_RETURN, "sion_seek: error in searching end pos, returning ...\n");
300  }
301  else { posinblk = newposinblk; /* for checking posinblk later */
302  }
303  DPRINTFP((32, DFUNCTION, -1, "sion_end_pos newblocknr=%d newpos=%ld fn=%s\n", newblocknr, (long)newposinblk, sion_filedesc->fname));
304  }
305  else {
306  if (blocknr == SION_CURRENT_BLK) {
307  newblocknr=sion_filedesc->currentblocknr;
308  DPRINTFP((32, DFUNCTION, -1, "sion_current_blk newblocknr=%d newpos=%ld fn=%s\n",newblocknr, (long) newposinblk, sion_filedesc->fname));
309  } else {
310  /* a blocknr is specified */
311  if ( (blocknr >= 0) && (blocknr <= sion_filedesc->lastchunknr) ) {
312  newblocknr=blocknr;
313  } else {
314  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
315  "sion_seek: parameter chunk number (%d) is out of range (0 .. %d), returning ...\n",
316  blocknr,sion_filedesc->lastchunknr));
317  }
318  DPRINTFP((32, DFUNCTION, -1, "new blocknr newblocknr=%d newpos=%ld fn=%s\n",newblocknr, (long) newposinblk, sion_filedesc->fname));
319  }
320  }
321 
322 
323  /* check requested POSITION IN BLOCK */
324  if (posinblk == SION_CURRENT_POS) {
325  _sion_update_fileposition(sion_filedesc);
326  newposinblk=sion_filedesc->currentpos - (sion_filedesc->startpos + sion_filedesc->currentblocknr * sion_filedesc->globalskip);
327  DPRINTFP((32, DFUNCTION, -1, "sion_current_pos newblocknr=%d newpos=%ld fn=%s %ld %ld %ld %ld\n",newblocknr, (long) newposinblk, sion_filedesc->fname,
328  (long) sion_filedesc->currentpos, (long) sion_filedesc->startpos,(long) sion_filedesc->currentblocknr,(long) sion_filedesc->globalskip));
329  } else {
330  /* a posinblk is specified */
331  if ( (sion_filedesc->keyvalmode!=SION_KEYVAL_NONE) || /* allow position outside block for keyval, file could already be scanned completly */
332  ( (posinblk >= 0) && (posinblk <= sion_filedesc->blocksizes[newblocknr]) )
333  )
334  {
335  newposinblk=posinblk;
336  } else {
337  DPRINTFP((2, DFUNCTION, -1, "sion_seek: parameter posinblk (%lld) is out of range (0 .. %lld), aborting ...\n",
338  posinblk, sion_filedesc->blocksizes[newblocknr]));
339  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
340  "sion_seek: parameter posinblk (%lld) is out of range (0 .. %lld), aborting ...\n",
341  posinblk, sion_filedesc->blocksizes[newblocknr]));
342  }
343  DPRINTFP((2, DFUNCTION, -1, "new posinblk newblocknr=%d newpos=%ld fn=%s\n",newblocknr, (long) newposinblk, sion_filedesc->fname));
344  }
345 
346  DPRINTFP((32, DFUNCTION, -1,
347  " before set pos: rank=%4d startpos=%ld currentblocknr=%d globalskip=%ld newposinblk=%ld\n", sion_filedesc->rank
348  ,(long) sion_filedesc->startpos, sion_filedesc->currentblocknr, (long) sion_filedesc->globalskip, (long) newposinblk));
349 
350  /* SET NEW POSITION */
351  DPRINTFP((32, DFUNCTION, 0, "file pos=%ld (%ld)\n", (long) _sion_file_get_position(sion_filedesc->fileptr), (long) sion_filedesc->currentpos));
352  sion_filedesc->currentblocknr = newblocknr;
353  sion_filedesc->currentpos = sion_filedesc->startpos
354  + sion_filedesc->currentblocknr * sion_filedesc->globalskip
355  + newposinblk;
356  _sion_file_purge(sion_filedesc->fileptr);
357  _sion_file_set_position(sion_filedesc->fileptr, sion_filedesc->currentpos);
358 
359  DPRINTFP((32, DFUNCTION, -1,
360  " set pos: rank=%4d newblocknr=%4d newposinblk=%4ld, set fileptr to position %14ld (%14ld) file=%s\n",
361  sion_filedesc->rank, sion_filedesc->currentblocknr, (long) newposinblk,
362  (long) _sion_file_get_position(sion_filedesc->fileptr),(long) sion_filedesc->currentpos,
363  sion_filedesc->fname));
364 
365 
366  DPRINTFP((2, DFUNCTION, -1, "leave seek rc=%d\n",rc));
367 
368  return(rc);
369 
370 }
371 #undef DFUNCTION
372 
373 #define DFUNCTION "_sion_seek_on_all_ranks_read_mapped"
374 
388  int rank,
389  int blocknr,
390  sion_int64 posinblk ) {
391  int rc = SION_SUCCESS;
392  int lfile, lrank, blknum, filenr, t;
393  _sion_filedesc *sion_filedesc_sub;
394 
395  DPRINTFP((2, DFUNCTION, -1, "enter seek r=%d b=%d p=%ld fn=%s\n",
396  rank,blocknr, (long) posinblk,sion_filedesc_master->fname));
397 
398  /* check if RANK changed */
399  if ( (rank != SION_CURRENT_RANK) && (rank != sion_filedesc_master->globalrank) ) {
400 
401  DPRINTFP((32, DFUNCTION, -1, "rank has changed %d -> %d\n", sion_filedesc_master->globalrank, rank));
402 
403  if ((rank<0) || (rank >= sion_filedesc_master->ntotaltasksinfile)) {
404  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: parameter rank %d (max. %d) out of range, aborting ...\n",
405  rank, sion_filedesc_master->ntotaltasksinfile));
406  }
407 
408  /* check and update current position */
409  _sion_update_fileposition(sion_filedesc_master);
410 
411  /* transfer meta data to corresponding sub datastructure */
412  lfile=sion_filedesc_master->filenumber;
413  lrank=sion_filedesc_master->rank; /* index to local list */
414  sion_filedesc_sub=sion_filedesc_master->multifiles[lfile];
415 
416  sion_filedesc_sub->currentpos = sion_filedesc_master->currentpos;
417  sion_filedesc_sub->currentblocknr = sion_filedesc_master->currentblocknr;
418 
419  /* pointer to keyval structure */
420  DPRINTFP((32, DFUNCTION, -1, "set keyvalptr on sub to master lfile=%d,lrank=%d to %x\n",lfile,lrank,sion_filedesc_master->keyvalptr));
421  if(sion_filedesc_sub->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc_sub->keyvalptr = sion_filedesc_master->keyvalptr;
422 
423  DPRINTFP((32, DFUNCTION, -1, "on file %d: sub,maxchunk=%d master,maxchunk=%d \n", lfile,sion_filedesc_sub->maxchunks, sion_filedesc_master->maxchunks));
424 
425  /* store data of current rank on sub datastructure */
426  DPRINTFP((32, DFUNCTION, -1, "store current information lrank=%d lastchunknr=%d\n", lrank,sion_filedesc_sub->lastchunknr));
427  sion_filedesc_sub->all_currentpos[lrank] = sion_filedesc_sub->currentpos;
428  sion_filedesc_sub->all_currentblocknr[lrank] = sion_filedesc_sub->currentblocknr;
429 
430  /* pointer to keyval structure -> all_keyvalptr */
431  DPRINTFP((32, DFUNCTION, -1, "keyvalptr sub file=%d all_keyvalptr[%d] = %x\n",lfile,lrank,sion_filedesc_sub->keyvalptr));
432  if(sion_filedesc_sub->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc_sub->all_keyvalptr[lrank] = sion_filedesc_sub->keyvalptr;
433 
434  /* lookup file which contains new global rank and set master */
435  sion_filedesc_sub=NULL;
436  lfile=lrank=-1;
437  DPRINTFP((32, DFUNCTION, -1, " nfiles=%d\n", sion_filedesc_master->nfiles));
438 
439  for(filenr=0;( (filenr<sion_filedesc_master->nfiles) && (lrank==-1) );filenr++) {
440  DPRINTFP((4, DFUNCTION, -1, " filenr=%d nlocaltasksinfile\n",
441  filenr,sion_filedesc_master->multifiles[filenr]->nlocaltasksinfile));
442 
443  for(t=0;( (t<sion_filedesc_master->multifiles[filenr]->nlocaltasksinfile) && (lrank==-1) );t++) {
444  DPRINTFP((4, DFUNCTION, -1, " check filenr=%d t=%d grank=%d with rank=%d\n",
445  filenr,t,sion_filedesc_master->multifiles[filenr]->all_globalranks[t],rank));
446  if(sion_filedesc_master->multifiles[filenr]->all_globalranks[t]==rank) {
447  sion_filedesc_sub=sion_filedesc_master->multifiles[filenr];
448  lfile=filenr;
449  lrank=t;
450  break;
451  }
452  }
453  }
454  DPRINTFP((32, DFUNCTION, -1, "grank %d is found in file %d with lrank %d\n", rank,lfile,lrank));
455  if((lrank==-1) || (sion_filedesc_sub == NULL)) {
456  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: parameter rank %d is not opened on this tasks (mapped mode), aborting ...\n",
457  rank));
458  }
459 
460  /* switch to new rank and restore current position of this rank */
461  sion_filedesc_master->globalrank = sion_filedesc_sub->all_globalranks[lrank];
462  sion_filedesc_master->rank = lrank;
463  sion_filedesc_master->filenumber = lfile;
464  sion_filedesc_master->currentblocknr = sion_filedesc_sub->all_currentblocknr[lrank];
465  sion_filedesc_master->currentpos = sion_filedesc_sub->all_currentpos[lrank];
466  sion_filedesc_master->lastchunknr = sion_filedesc_sub->all_blockcount[lrank]-1;
467  sion_filedesc_master->startpos = sion_filedesc_sub->all_startpointers[lrank];
468  sion_filedesc_master->chunksize = sion_filedesc_sub->all_chunksizes[lrank];
469 
470  /* pointer to keyval structure */
471  if(sion_filedesc_master->keyvalmode!=SION_KEYVAL_NONE) {
472  DPRINTFP((32, DFUNCTION, -1, "set keyvalptr on lfile=%d,lrank=%d to %x\n",lfile,lrank,sion_filedesc_sub->all_keyvalptr[lrank]));
473  sion_filedesc_master->keyvalptr = sion_filedesc_sub->all_keyvalptr[lrank];
474  }
475 
476  if(sion_filedesc_sub->maxchunks > sion_filedesc_master->maxchunks) {
477  _sion_realloc_filedesc_blocklist(sion_filedesc_master, sion_filedesc_sub->maxchunks);
478  }
479  for (blknum = 0; blknum <= sion_filedesc_master->lastchunknr; blknum++) {
480  sion_filedesc_master->blocksizes[blknum] = sion_filedesc_sub->all_blocksizes[sion_filedesc_sub->ntasks * blknum + lrank];
481  }
482  sion_filedesc_master->globalskip = sion_filedesc_sub->globalskip;
483  sion_filedesc_master->fileptr = sion_filedesc_sub->fileptr;
484 
485  /* rank has changed, therefore this information could not get from fileposition */
486  if (blocknr == SION_CURRENT_BLK) {
487  blocknr=sion_filedesc_master->currentblocknr;
488  }
489  if (posinblk == SION_CURRENT_POS) {
490  posinblk=sion_filedesc_master->currentpos - (sion_filedesc_master->startpos + sion_filedesc_master->currentblocknr * sion_filedesc_master->globalskip);
491 
492  if(sion_filedesc_master->keyvalmode==SION_KEYVAL_NONE) {
493 
494  /* check if just behind current block, go to next block */
495  if(posinblk>=sion_filedesc_master->blocksizes[blocknr]) {
496  posinblk=0;blocknr++;
497  if(blocknr > sion_filedesc_master->lastchunknr) {
498  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: seek after end of file, returning ...\n"));
499 
500  }
501  }
502 
503  }
504  }
505 
506  }
507 
508  _sion_print_filedesc(sion_filedesc_master, 512, "_sion_seek_on_all_ranks_read_mapped", 1);
509 
510  /* seek new position in current rank, set in all cases the filepointer */
511  _sion_seek_on_current_rank_read(sion_filedesc_master,SION_CURRENT_RANK,blocknr,posinblk);
512 
513  DPRINTFP((2, DFUNCTION, -1, "leave seek\n"));
514 
515  return(rc);
516 
517 }
518 #undef DFUNCTION
519 
520 
521 #define DFUNCTION "_sion_seek_on_all_ranks_write"
522 
536  int rank,
537  int blocknr,
538  sion_int64 posinblk ) {
539  int rc = SION_SUCCESS;
540  int blknum;
541 
542  DPRINTFP((2, DFUNCTION, -1, "enter seek r=%d b=%d p=%ld fn=%s\n",
543  rank,blocknr, (long) posinblk,sion_filedesc->fname));
544 
545  if ((sion_filedesc->all_blockcount == NULL)
546  || (sion_filedesc->all_blocksizes == NULL)) {
547  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
548  "sion_seek: internal error, data structure not initialized, aborting ...\n"));
549  }
550 
551  /* check if RANK changed */
552  if ( (rank != SION_CURRENT_RANK) && (rank != sion_filedesc->rank) ) {
553 
554  DPRINTFP((32, DFUNCTION, -1, "rank has changed %d -> %d\n", sion_filedesc->rank, rank));
555 
556  if ((rank<0) || (rank >= sion_filedesc->ntasks)) {
557  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: parameter rank %d (max. %d) out of range, aborting ...\n",
558  rank, sion_filedesc->ntasks));
559  }
560 
561  /* flush write buffer */
562  if (sion_filedesc->usebuffer) {
563  _sion_buffer_flush(sion_filedesc);
564  }
565 
566  /* update meta data of current rank */
567  _sion_flush_block(sion_filedesc);
568 
569  /* store current position in all_* vectors */
570  DPRINTFP((32, DFUNCTION, -1, "store data for rank %d currentpos=%d currentblocknr=%d lastchunknr=%d\n", sion_filedesc->rank,
571  (int) sion_filedesc->currentpos,
572  (int) sion_filedesc->currentblocknr,
573  (int) sion_filedesc->lastchunknr ));
574  sion_filedesc->all_currentpos[sion_filedesc->rank] = sion_filedesc->currentpos;
575  sion_filedesc->all_currentblocknr[sion_filedesc->rank] = sion_filedesc->currentblocknr;
576 
577  /* pointer to keyval structure */
578  if(sion_filedesc->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc->all_keyvalptr[sion_filedesc->rank] = sion_filedesc->keyvalptr;
579 
580  sion_filedesc->all_blockcount[sion_filedesc->rank] = sion_filedesc->lastchunknr + 1;
581  for (blknum = 0; blknum <= sion_filedesc->lastchunknr; blknum++) {
582  sion_filedesc->all_blocksizes[sion_filedesc->ntasks * blknum + sion_filedesc->rank] = sion_filedesc->blocksizes[blknum];
583  sion_filedesc->blocksizes[blknum]=0; /* reset entry */
584  }
585 
586  /* switch to new rank and restore current position of this rank */
587  sion_filedesc->rank = rank;
588  sion_filedesc->currentblocknr = sion_filedesc->all_currentblocknr[sion_filedesc->rank];
589  sion_filedesc->currentpos = sion_filedesc->all_currentpos[sion_filedesc->rank];
590  sion_filedesc->lastchunknr = sion_filedesc->all_blockcount[sion_filedesc->rank]-1;
591  sion_filedesc->startpos = sion_filedesc->all_startpointers[sion_filedesc->rank];
592  sion_filedesc->chunksize = sion_filedesc->all_chunksizes[sion_filedesc->rank];
593 
594  /* pointer to keyval structure */
595  if(sion_filedesc->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc->keyvalptr = sion_filedesc->all_keyvalptr[sion_filedesc->rank];
596 
597  for (blknum = 0; blknum <= sion_filedesc->lastchunknr; blknum++) {
598  sion_filedesc->blocksizes[blknum] = sion_filedesc->all_blocksizes[sion_filedesc->ntasks * blknum + sion_filedesc->rank];
599  }
600 
601  }
602 
603  /* seek new position in current rank, set in all cases the filepointer */
604  _sion_seek_on_current_rank_write(sion_filedesc,SION_CURRENT_RANK,blocknr,posinblk);
605 
606  DPRINTFP((2, DFUNCTION, -1, "leave seek\n"));
607 
608  return(rc);
609 
610 }
611 #undef DFUNCTION
612 
613 #define DFUNCTION "_sion_seek_on_all_ranks_write_mapped"
614 
628  int rank,
629  int blocknr,
630  sion_int64 posinblk ) {
631  int rc = SION_SUCCESS;
632  int lfile, lrank, blknum, filenr, t;
633  _sion_filedesc *sion_filedesc_sub;
634 
635  DPRINTFP((2, DFUNCTION, -1, "enter seek r=%d b=%d p=%ld fn=%s\n",
636  rank,blocknr, (long) posinblk,sion_filedesc_master->fname));
637 
638  /* check if RANK changed */
639  if ( (rank != SION_CURRENT_RANK) && (rank != sion_filedesc_master->globalrank) ) {
640 
641  DPRINTFP((32, DFUNCTION, -1, "rank has changed %d -> %d\n", sion_filedesc_master->globalrank, rank));
642 
643  if ((rank<0) || (rank >= sion_filedesc_master->ntotaltasksinfile)) {
644  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: parameter rank %d (max. %d) out of range, aborting ...\n",
645  rank, sion_filedesc_master->ntotaltasksinfile));
646  }
647 
648  /* flush write buffer */
649  if (sion_filedesc_master->usebuffer) {
650  _sion_buffer_flush(sion_filedesc_master);
651  }
652 
653  /* update meta data of current rank */
654  _sion_flush_block(sion_filedesc_master);
655 
656  /* transfer meta data to corresponding sub datastructure */
657  lfile=sion_filedesc_master->filenumber;
658  lrank=sion_filedesc_master->rank; /* index to local list */
659  sion_filedesc_sub=sion_filedesc_master->multifiles[lfile];
660 
661  sion_filedesc_sub->currentpos = sion_filedesc_master->currentpos;
662  sion_filedesc_sub->currentblocknr = sion_filedesc_master->currentblocknr;
663  sion_filedesc_sub->lastchunknr = sion_filedesc_master->lastchunknr;
664 
665  /* pointer to keyval structure */
666  if(sion_filedesc_sub->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc_sub->keyvalptr = sion_filedesc_master->keyvalptr;
667 
668  DPRINTFP((32, DFUNCTION, -1, "on file %d: sub,maxchunk=%d master,maxchunk=%d \n", lfile,sion_filedesc_sub->maxchunks, sion_filedesc_master->maxchunks));
669  if(sion_filedesc_sub->maxchunks < sion_filedesc_master->maxchunks) {
670  _sion_realloc_filedesc_blocklist(sion_filedesc_sub, sion_filedesc_master->maxchunks);
671  }
672 
673  /* store data of current rank on sub datastructure */
674  DPRINTFP((32, DFUNCTION, -1, "store current information lrank=%d lastchunknr=%d\n", lrank,sion_filedesc_sub->lastchunknr));
675  sion_filedesc_sub->all_currentpos[lrank] = sion_filedesc_sub->currentpos;
676  sion_filedesc_sub->all_currentblocknr[lrank] = sion_filedesc_sub->lastchunknr;
677  sion_filedesc_sub->all_blockcount[lrank] = sion_filedesc_sub->lastchunknr + 1;
678 
679  /* pointer to keyval structure */
680  if(sion_filedesc_sub->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc_sub->all_keyvalptr[lrank] = sion_filedesc_sub->keyvalptr;
681 
682  for (blknum = 0; blknum <= sion_filedesc_sub->lastchunknr; blknum++) {
683  sion_filedesc_sub->blocksizes[blknum] = sion_filedesc_master->blocksizes[blknum];
684  sion_filedesc_sub->all_blocksizes[sion_filedesc_sub->ntasks * blknum + lrank] = sion_filedesc_master->blocksizes[blknum];
685  }
686 
687  /* lookup file which contains new global rank and set master */
688  sion_filedesc_sub=NULL;
689  lfile=lrank=-1;
690  DPRINTFP((32, DFUNCTION, -1, " nfiles=%d\n", sion_filedesc_master->nfiles));
691 
692  for(filenr=0;( (filenr<sion_filedesc_master->nfiles) && (lrank==-1) );filenr++) {
693  DPRINTFP((32, DFUNCTION, -1, " filenr=%d nlocaltasksinfile\n",
694  filenr,sion_filedesc_master->multifiles[filenr]->nlocaltasksinfile));
695 
696  for(t=0;( (t<sion_filedesc_master->multifiles[filenr]->nlocaltasksinfile) && (lrank==-1) );t++) {
697  DPRINTFP((32, DFUNCTION, -1, " check filenr=%d t=%d grank=%d with rank=%d\n",
698  filenr,t,sion_filedesc_master->multifiles[filenr]->all_globalranks[t],rank));
699  if(sion_filedesc_master->multifiles[filenr]->all_globalranks[t]==rank) {
700  sion_filedesc_sub=sion_filedesc_master->multifiles[filenr];
701  lfile=filenr;
702  lrank=t;
703  break;
704  }
705  }
706  }
707  DPRINTFP((32, DFUNCTION, -1, "grank %d is found in file %d with lrank %d\n", rank,lfile,lrank));
708  if((lrank==-1) || (sion_filedesc_sub == NULL)) {
709  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,"sion_seek: parameter rank %d is not opened on this tasks (mapped mode), aborting ...\n",
710  rank));
711  }
712 
713  /* switch to new rank and restore current position of this rank */
714  sion_filedesc_master->globalrank = sion_filedesc_sub->all_globalranks[lrank];
715  sion_filedesc_master->rank = lrank;
716  sion_filedesc_master->filenumber = lfile;
717  sion_filedesc_master->currentblocknr = sion_filedesc_sub->all_currentblocknr[lrank];
718  sion_filedesc_master->currentpos = sion_filedesc_sub->all_currentpos[lrank];
719  sion_filedesc_master->lastchunknr = sion_filedesc_sub->all_blockcount[lrank]-1;
720  sion_filedesc_master->startpos = sion_filedesc_sub->all_startpointers[lrank];
721  sion_filedesc_master->chunksize = sion_filedesc_sub->all_chunksizes[lrank];
722 
723  /* pointer to keyval structure */
724  if(sion_filedesc_master->keyvalmode!=SION_KEYVAL_NONE) sion_filedesc_master->keyvalptr = sion_filedesc_sub->all_keyvalptr[lrank];
725 
726  if(sion_filedesc_sub->maxchunks > sion_filedesc_master->maxchunks) {
727  _sion_realloc_filedesc_blocklist(sion_filedesc_master, sion_filedesc_sub->maxchunks);
728  }
729  for (blknum = 0; blknum <= sion_filedesc_sub->lastchunknr; blknum++) {
730  sion_filedesc_master->blocksizes[blknum] = sion_filedesc_sub->all_blocksizes[sion_filedesc_sub->ntasks * blknum + lrank];
731  }
732 
733  sion_filedesc_master->globalskip = sion_filedesc_sub->globalskip;
734  sion_filedesc_master->fileptr = sion_filedesc_sub->fileptr;
735 
736  }
737 
738 
739  _sion_print_filedesc(sion_filedesc_master, 512, "_sion_seek_on_all_ranks_write_mapped", 1);
740 
741  /* seek new position in current rank, set in all cases the filepointer */
742  _sion_seek_on_current_rank_write(sion_filedesc_master,SION_CURRENT_RANK,blocknr,posinblk);
743 
744  DPRINTFP((2, DFUNCTION, -1, "leave seek\n"));
745 
746  return(rc);
747 
748 }
749 #undef DFUNCTION
750 
751 
752 #define DFUNCTION "_sion_seek_on_current_rank_write"
753 
765  int rank,
766  int blocknr,
767  sion_int64 posinblk ) {
768  int rc = SION_SUCCESS;
769 
770  DPRINTFP((2, DFUNCTION, -1, "enter seek r=%d b=%d p=%ld fn=%s\n",rank,blocknr, (long) posinblk,sion_filedesc->fname));
771 
772  /* check RANK */
773  if ( (rank != SION_CURRENT_RANK) && (rank != sion_filedesc->rank) ) {
774  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
775  "sion_seek: parameter rank is different from current rank in parallel openened file, returning ...\n"));
776  }
777 
778  /* check requested BLOCK NUMBER */
779  if (blocknr != SION_CURRENT_BLK) {
780  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
781  "sion_seek: serial write to file currently only for SION_CURRENT_BLK implemented, aborting ...\n"));
782  }
783 
784  /* check requested POSITION IN BLOCK */
785  if (posinblk != SION_CURRENT_POS) {
786  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
787  "sion_seek: serial write to file currently only for SION_CURRENT_POS implemented, aborting ...\n"));
788  }
789 
790  /* flush write buffer */
791  if (sion_filedesc->usebuffer) {
792  _sion_buffer_flush(sion_filedesc);
793  }
794 
795  /* SET NEW POSITION */
796  /* currently not necessary, due to that movements
797  inside rank currently not allowed for write-mode*/
798 
799  /* SET NEW POSITION */
800  _sion_file_purge(sion_filedesc->fileptr);
801  _sion_file_set_position(sion_filedesc->fileptr, sion_filedesc->currentpos);
802 
803  DPRINTFP((2, DFUNCTION, -1, "leave seek\n"));
804 
805  return(rc);
806 
807 }
808 #undef DFUNCTION
809 
810 #define DFUNCTION "_sion_seek_search_abs_pos"
811 
823  sion_int64 abspos,
824  int *newblocknr,
825  sion_int64 *newposinblk ) {
826  int rc = SION_SUCCESS;
827  sion_int64 bytes=-1;
828  sion_int64 bytesinblock = 0;
829 
830  if (abspos>=0) {
831  *newposinblk=abspos;
832  bytes=0;*newblocknr=0;
833  bytesinblock = sion_filedesc->blocksizes[*newblocknr];
834  while ( (*newblocknr<sion_filedesc->lastchunknr) && (bytes + bytesinblock < *newposinblk) ) {
835  bytes += bytesinblock;
836  (*newblocknr)++;
837  bytesinblock = sion_filedesc->blocksizes[*newblocknr];
838  }
839  *newposinblk-=bytes;
840  } else {
841  return(_sion_errorprint(SION_NOT_SUCCESS,_SION_ERROR_RETURN,
842  "sion_seek: parameter pos in chunk (%d) is negative, aborting ...\n", (int) abspos));
843  }
844 
845 
846  return(rc);
847 }
848 #undef DFUNCTION
849 
850 #define DFUNCTION "_sion_seek_search_end_pos"
851 
863  sion_int64 posend,
864  int* newblocknr,
865  sion_int64* newposinblk)
866 {
867  int rc = SION_SUCCESS;
868 
869  if (posend <= 0) {
870  *newposinblk = posend;
871  *newblocknr = sion_filedesc->lastchunknr;
872  do {
873  *newposinblk += sion_filedesc->blocksizes[*newblocknr];
874  (*newblocknr)--;
875  }
876  while ((*newblocknr >= 0) && (*newposinblk < 0));
877  /* Add one after loop */
878  (*newblocknr)++;
879  if (*newposinblk < 0) {
880  return _sion_errorprint(SION_NOT_SUCCESS, _SION_ERROR_RETURN,
881  "sion_seek: seek before beginning of file (posend = %ld, abspos = %ld), aborting ...\n", posend, *newposinblk);
882  }
883  }
884  else {
885  return _sion_errorprint(SION_NOT_SUCCESS, _SION_ERROR_RETURN,
886  "sion_seek: seek past end of file (%ld > 0), aborting ...\n", posend);
887  }
888 
889 
890  return rc;
891 }
892 #undef DFUNCTION
sion_int64 _sion_file_get_position(_sion_fileptr *sion_fileptr)
Get new position in file.
Definition: sion_file.c:272
int _sion_buffer_flush(_sion_filedesc *sion_filedesc)
Flush buffer.
Definition: sion_buffer.c:164
int _sion_flush_block(_sion_filedesc *sion_filedesc)
Update the internal data structure.
int _sion_seek_on_all_ranks_read(_sion_filedesc *sion_filedesc, int rank, int blocknr, sion_int64 posinblk)
Function to set the file pointer to a new position, updates internal data structure.
sion_int64 _sion_file_set_position(_sion_fileptr *sion_fileptr, sion_int64 startpointer)
Set new position in file.
Definition: sion_file.c:239
Sion File Descriptor Structure.
Definition: sion_filedesc.h:77
sion_int64 * all_blockcount
int _sion_file_purge(_sion_fileptr *sion_fileptr)
Purge data to file.
Definition: sion_file.c:328
int _sion_seek_on_all_ranks_read_mapped(_sion_filedesc *sion_filedesc_master, int rank, int blocknr, sion_int64 posinblk)
Function to set the file pointer to a new position, updates internal data structure.
sion_int64 * all_currentpos
int _sion_seek_on_all_ranks_write_mapped(_sion_filedesc *sion_filedesc_master, int rank, int blocknr, sion_int64 posinblk)
Function to set the file pointer to a new position, updates internal data structure.
sion_int64 * all_globalranks
sion_int64 * all_currentblocknr
#define SION_CURRENT_BLK
Definition: sion_const.h:67
int _sion_realloc_filedesc_blocklist(_sion_filedesc *sion_filedesc, sion_int32 maxchunks)
Increase the memory used by the internal sion structure for the blocklist.
#define SION_END_POS
Definition: sion_const.h:72
#define SION_KEYVAL_NONE
Definition: sion_const.h:80
int _sion_seek_search_abs_pos(_sion_filedesc *sion_filedesc, sion_int64 abspos, int *newblocknr, sion_int64 *newposinblk)
Find block and position inside block for absolute position abspos.
sion_int64 * all_startpointers
#define SION_CURRENT_RANK
Definition: sion_const.h:66
#define SION_CURRENT_POS
Definition: sion_const.h:70
int _sion_update_fileposition(_sion_filedesc *sion_filedesc)
Update the internal data structure (check fileposition)
int _sion_seek_search_end_pos(_sion_filedesc *sion_filedesc, sion_int64 posend, int *newblocknr, sion_int64 *newposinblk)
Find block and position inside block position relative to end.
int _sion_seek_on_all_ranks_read_master(_sion_filedesc *sion_filedesc, int rank, int blocknr, sion_int64 posinblk)
Function to set the file pointer to a new position, updates internal data structure.
#define SION_ABSOLUTE_POS
Definition: sion_const.h:71
sion_int64 * blocksizes
Definition: sion_filedesc.h:98
sion_int32 currentblocknr
Definition: sion_filedesc.h:95
sion_int64 * all_chunksizes
int _sion_print_filedesc(_sion_filedesc *sion_filedesc, int level, char *desc, int flag)
Print the initialized sion file description.
int _sion_seek_on_current_rank_read(_sion_filedesc *sion_filedesc, int rank, int blocknr, sion_int64 posinblk)
Function to set the file pointer to a new position in the same rank, updates internal data structure.
Sion Time Stamp Header.
int _sion_seek_on_all_ranks_write(_sion_filedesc *sion_filedesc, int rank, int blocknr, sion_int64 posinblk)
Function to set the file pointer to a new position, updates internal data structure.
sion_int64 * all_blocksizes
sion_int32 ntotaltasksinfile
sion_int32 nlocaltasksinfile
_sion_filedesc ** multifiles
_sion_fileptr * fileptr
Definition: sion_filedesc.h:80
int _sion_seek_on_current_rank_write(_sion_filedesc *sion_filedesc, int rank, int blocknr, sion_int64 posinblk)
Function to set the file pointer to a new position in the same rank, updates internal data structure.