@@ -385,14 +385,53 @@ int mca_io_ompio_file_sync (ompi_file_t *fh)
385
385
return ret ;
386
386
}
387
387
388
+ static void mca_io_ompio_file_get_eof_offset (ompio_file_t * fh ,
389
+ OMPI_MPI_OFFSET_TYPE in_offset ,
390
+ OMPI_MPI_OFFSET_TYPE * out_offset )
391
+ {
392
+ /* a file_seek with SEEK_END might require an actual offset that is
393
+ not lined up with the end of the file, depending on the file view.
394
+ This routine determines the closest (smaller or equal) offset to
395
+ the provided in_offset value, avoiding gaps in the file view and avoiding to
396
+ break up an etype.
397
+ */
398
+ OMPI_MPI_OFFSET_TYPE offset = 0 , prev_offset = 0 , start_offset = 0 ;
399
+ size_t k = 0 , blocklen = 0 ;
400
+ size_t index_in_file_view = 0 ;
401
+
402
+ in_offset -= fh -> f_disp ;
403
+ if ( fh -> f_view_size > 0 ) {
404
+ /* starting offset of the current copy of the filew view */
405
+ start_offset = in_offset / fh -> f_view_extent ;
406
+
407
+ index_in_file_view = 0 ;
408
+ /* determine block id that the offset is located in and
409
+ the starting offset of that block */
410
+ while ( offset <= in_offset && index_in_file_view < fh -> f_iov_count ) {
411
+ prev_offset = offset ;
412
+ offset = start_offset + (OMPI_MPI_OFFSET_TYPE )(intptr_t ) fh -> f_decoded_iov [index_in_file_view ++ ].iov_base ;
413
+ }
414
+
415
+ offset = prev_offset ;
416
+ blocklen = fh -> f_decoded_iov [index_in_file_view - 1 ].iov_len ;
417
+ while ( offset <= in_offset && k <= blocklen ) {
418
+ prev_offset = offset ;
419
+ offset += fh -> f_etype_size ;
420
+ k += fh -> f_etype_size ;
421
+ }
422
+
423
+ * out_offset = prev_offset ;
424
+ }
425
+ return ;
426
+ }
388
427
389
428
int mca_io_ompio_file_seek (ompi_file_t * fh ,
390
429
OMPI_MPI_OFFSET_TYPE off ,
391
430
int whence )
392
431
{
393
432
int ret = OMPI_SUCCESS ;
394
433
mca_common_ompio_data_t * data ;
395
- OMPI_MPI_OFFSET_TYPE offset , temp_offset ;
434
+ OMPI_MPI_OFFSET_TYPE offset , temp_offset , temp_offset2 ;
396
435
397
436
data = (mca_common_ompio_data_t * ) fh -> f_io_selected_data ;
398
437
@@ -409,15 +448,17 @@ int mca_io_ompio_file_seek (ompi_file_t *fh,
409
448
case MPI_SEEK_CUR :
410
449
ret = mca_common_ompio_file_get_position (& data -> ompio_fh ,
411
450
& temp_offset );
412
- offset += temp_offset ;
451
+ offset += temp_offset * data -> ompio_fh . f_etype_size ;
413
452
if (offset < 0 ) {
414
453
OPAL_THREAD_UNLOCK (& fh -> f_lock );
415
454
return OMPI_ERROR ;
416
455
}
417
456
break ;
418
457
case MPI_SEEK_END :
419
458
ret = data -> ompio_fh .f_fs -> fs_file_get_size (& data -> ompio_fh ,
420
- & temp_offset );
459
+ & temp_offset2 );
460
+ mca_io_ompio_file_get_eof_offset (& data -> ompio_fh ,
461
+ temp_offset2 , & temp_offset );
421
462
offset += temp_offset ;
422
463
if (offset < 0 || OMPI_SUCCESS != ret ) {
423
464
OPAL_THREAD_UNLOCK (& fh -> f_lock );
@@ -436,6 +477,7 @@ int mca_io_ompio_file_seek (ompi_file_t *fh,
436
477
return ret ;
437
478
}
438
479
480
+
439
481
int mca_io_ompio_file_get_position (ompi_file_t * fd ,
440
482
OMPI_MPI_OFFSET_TYPE * offset )
441
483
{
0 commit comments