@@ -95,7 +95,10 @@ GlobalOrderWriter::GlobalOrderWriter(
9595 , fragment_size_(fragment_size)
9696 , current_fragment_size_(0 )
9797 , rows_written_(0 )
98- , start_(0 ) {
98+ , tiles_in_current_row_(0 )
99+ , start_(0 )
100+ , end_(0 )
101+ , nd_if_dense_split_{} {
99102 // Check the layout is global order.
100103 if (layout_ != Layout::GLOBAL_ORDER) {
101104 throw GlobalOrderWriterException (
@@ -785,11 +788,16 @@ Status GlobalOrderWriter::global_write() {
785788 // Compute the number of tiles that will fit in this fragment.
786789 auto num = num_tiles_to_write (idx, tile_num, tiles);
787790
788- if (tile_num != num && array_schema_.array_type () == ArrayType::DENSE) {
791+ if (array_schema_.array_type () ==
792+ ArrayType::DENSE) { // && this is consolidation
789793 // if it is a dense array and not all tiles can fit in the current
790- // fragment then we need to split the domain
791- NDRange new_nd = ndranges_after_split (num);
792- frag_meta->init_domain (new_nd);
794+ // fragment then we need to split the domain, otherwise if all tiles can
795+ // fit it means that we are in the middle of a write
796+ nd_if_dense_split_ = ndranges_after_split (num, tile_num != num);
797+ }
798+
799+ if (tile_num != num && !nd_if_dense_split_.empty ()) {
800+ frag_meta->init_domain (nd_if_dense_split_);
793801 }
794802
795803 // If we're resuming a fragment write and the first tile doesn't fit into
@@ -1453,7 +1461,8 @@ uint64_t GlobalOrderWriter::num_tiles_per_row(const Domain& domain) {
14531461 return ret;
14541462}
14551463
1456- NDRange GlobalOrderWriter::ndranges_after_split (uint64_t num) {
1464+ NDRange GlobalOrderWriter::ndranges_after_split (
1465+ uint64_t num, bool reached_end_of_fragment) {
14571466 // Expand domain to full tiles
14581467 auto & domain{array_schema_.domain ()};
14591468 if (disable_checks_consolidation_) {
@@ -1464,16 +1473,21 @@ NDRange GlobalOrderWriter::ndranges_after_split(uint64_t num) {
14641473 // Calculate how many tiles each row can hold
14651474 uint64_t tiles_per_row = num_tiles_per_row (domain);
14661475
1467- if (num % tiles_per_row != 0 ) {
1476+ // Calculate how many rows we will write in the current fragment
1477+ uint64_t rows_of_tiles_to_write =
1478+ (num - tiles_in_current_row_) / tiles_per_row;
1479+ uint64_t remainder_of_tiles = (num - tiles_in_current_row_) % tiles_per_row;
1480+ tiles_in_current_row_ = remainder_of_tiles;
1481+
1482+ // If we have not written a full row and we have reached the end of the
1483+ // fragment abort
1484+ if (tiles_in_current_row_ != 0 && reached_end_of_fragment) {
14681485 throw GlobalOrderWriterException (
14691486 " The target fragment size cannot be achieved. Please try using a "
14701487 " different size, or there might be a misconfiguration in the array "
14711488 " schema." );
14721489 }
14731490
1474- // Calculate how many rows we will write in the current fragment
1475- uint64_t rows_of_tiles_to_write = num / tiles_per_row;
1476-
14771491 // Create NDRange object and reserve for dims
14781492 auto dim_num = domain.dim_num ();
14791493 NDRange nd;
@@ -1498,9 +1512,14 @@ NDRange GlobalOrderWriter::ndranges_after_split(uint64_t num) {
14981512 };
14991513
15001514 start_ = apply_with_type (ll, dim->type ());
1515+ end_ = apply_with_type (ll, dim->type ());
15011516 }
15021517 uint64_t end = start_ + (rows_of_tiles_to_write * tile_extent) - 1 ;
15031518
1519+ if (tiles_in_current_row_ != 0 && !reached_end_of_fragment && end < end_) {
1520+ end++;
1521+ }
1522+
15041523 // Add range
15051524 Range range (&start_, &end, sizeof (int ));
15061525 nd.emplace_back (range);
0 commit comments