libSplash
DomainCollector.cpp
1 
24 #include <algorithm>
25 #include <cassert>
26 #include <math.h>
27 
28 #include "splash/basetypes/basetypes.hpp"
29 #include "splash/DomainCollector.hpp"
30 #include "splash/core/DCDataSet.hpp"
31 #include "splash/core/DCGroup.hpp"
32 #include "splash/core/DCAttribute.hpp"
33 #include "splash/core/logging.hpp"
34 
35 namespace splash
36 {
37 
38  DomainCollector::DomainCollector(uint32_t maxFileHandles) :
39  SerialDataCollector(maxFileHandles)
40  {
41  }
42 
44  {
45  }
46 
48  const char* name)
49  throw (DCException)
50  {
51  if ((fileStatus != FST_MERGING) && (fileStatus != FST_READING))
52  throw DCException("DomainCollector::getGlobalDomain: this access is not permitted");
53 
54  Dimensions mpi_size;
55  if (fileStatus == FST_MERGING)
56  mpi_size.set(mpiTopology);
57  else
58  mpi_size.set(1, 1, 1);
59 
60  // Since all MPI processes must write domain information as a regular grid,
61  // we can just open the last MPI position to get the total size.
62  Dimensions mpi_position(mpi_size[0] - 1, mpi_size[1] - 1, mpi_size[2] - 1);
63 
64  Dimensions global_domain_size;
65  Dimensions global_domain_offset;
66 
67  readGlobalSizeFallback(id, name, global_domain_size.getPointer(), &mpi_position);
68  readGlobalOffsetFallback(id, name, global_domain_offset.getPointer(), &mpi_position);
69 
70  return Domain(global_domain_offset, global_domain_size);
71  }
72 
74  const char* name) throw (DCException)
75  {
76  if ((fileStatus != FST_MERGING) && (fileStatus != FST_READING))
77  throw DCException("DomainCollector::getLocalDomain: this access is not permitted");
78 
79  // this accesses the local information, for both normal and merged read
80  Dimensions mpi_position(0, 0, 0);
81 
82  Dimensions domain_size;
83  Dimensions domain_offset;
84 
85  readAttributeInfo(id, name, DOMCOL_ATTR_SIZE, &mpi_position).read(domain_size.getPointer(), domain_size.getSize());
86  readAttributeInfo(id, name, DOMCOL_ATTR_OFFSET, &mpi_position).read(domain_offset.getPointer(), domain_offset.getSize());
87 
88  return Domain(domain_offset, domain_size);
89  }
90 
91  void DomainCollector::writeDomainAttributes(
92  int32_t id,
93  const char *name,
94  DomDataClass dataClass,
95  const Domain localDomain,
96  const Domain globalDomain)
97  throw (DCException)
98  {
99  ColTypeInt32 int_t;
100  ColTypeDim dim_t;
101 
102  hid_t dset_handle = openDatasetHandle(id, name, NULL);
103 
104  DCAttribute::writeAttribute(DOMCOL_ATTR_CLASS, int_t.getDataType(),
105  dset_handle, &dataClass);
106  DCAttribute::writeAttribute(DOMCOL_ATTR_SIZE, dim_t.getDataType(),
107  dset_handle, localDomain.getSize().getPointer());
108  DCAttribute::writeAttribute(DOMCOL_ATTR_OFFSET, dim_t.getDataType(),
109  dset_handle, localDomain.getOffset().getPointer());
110  DCAttribute::writeAttribute(DOMCOL_ATTR_GLOBAL_SIZE, dim_t.getDataType(),
111  dset_handle, globalDomain.getSize().getPointer());
112  DCAttribute::writeAttribute(DOMCOL_ATTR_GLOBAL_OFFSET, dim_t.getDataType(),
113  dset_handle, globalDomain.getOffset().getPointer());
114 
115  closeDatasetHandle(dset_handle);
116  }
117 
118  bool DomainCollector::readDomainInfoForRank(
119  Dimensions mpiPosition,
120  int32_t id,
121  const char* name,
122  const Domain requestDomain,
123  Domain &fileDomain)
124  throw (DCException)
125  {
126  {
127  hid_t dset_handle = openDatasetHandle(id, name, &mpiPosition);
128  Dimensions global_domain_offset;
129 
130  DCAttribute::readAttribute(DOMCOL_ATTR_OFFSET, dset_handle,
131  fileDomain.getOffset().getPointer());
132 
133  DCAttribute::readAttribute(DOMCOL_ATTR_SIZE, dset_handle,
134  fileDomain.getSize().getPointer());
135 
136  DCAttribute::readAttribute(DOMCOL_ATTR_GLOBAL_OFFSET, dset_handle,
137  global_domain_offset.getPointer());
138 
139  fileDomain.getOffset() += global_domain_offset;
140 
141  closeDatasetHandle(dset_handle);
142  }
143 
144  // zero request sizes will not intersect with anything
145  if (requestDomain.getSize() == Dimensions(0, 0, 0))
146  return false;
147 
148  return Domain::testIntersection(requestDomain, fileDomain);
149  }
150 
151  void DomainCollector::readGridInternal(
152  DataContainer *dataContainer,
153  Dimensions mpiPosition,
154  int32_t id,
155  const char* name,
156  const Domain &clientDomain,
157  const Domain &requestDomain
158  )
159  throw (DCException)
160  {
161  log_msg(3, "dataclass = Grid");
162 
163  // When the first intersection is found, the whole destination
164  // buffer is allocated and added to the container.
165  if (dataContainer->getNumSubdomains() == 0)
166  {
167  std::stringstream group_id_name;
168  group_id_name << SDC_GROUP_DATA << "/" << id;
169  std::string group_id_string = group_id_name.str();
170 
171  DCGroup group;
172  group.open(handles.get(mpiPosition), group_id_string);
173 
174  size_t datatype_size = 0;
175  DCDataType dc_datatype = DCDT_UNKNOWN;
176 
177  try
178  {
179  DCDataSet tmp_dataset(name);
180  tmp_dataset.open(group.getHandle());
181 
182  datatype_size = tmp_dataset.getDataTypeSize();
183  dc_datatype = tmp_dataset.getDCDataType();
184 
185  tmp_dataset.close();
186  } catch (const DCException& e)
187  {
188  throw e;
189  }
190 
191  group.close();
192 
193  DomainData *target_data = new DomainData(
194  requestDomain, requestDomain.getSize(),
195  datatype_size, dc_datatype);
196 
197  dataContainer->add(target_data);
198  }
199 
200  // Compute the offsets and sizes for reading and
201  // writing this intersection.
202  Dimensions dst_offset(0, 0, 0);
203  Dimensions src_size(1, 1, 1);
204  Dimensions src_offset(0, 0, 0);
205 
206  Dimensions client_start = clientDomain.getOffset();
207  Dimensions client_size = clientDomain.getSize();
208 
209  size_t ndims = getNDims(handles.get(mpiPosition), id, name);
210  const Dimensions &request_offset = requestDomain.getOffset();
211  const Dimensions &request_size = requestDomain.getSize();
212 
213  for (uint32_t i = 0; i < ndims; ++i)
214  {
215  dst_offset[i] = std::max((int64_t) clientDomain.getOffset()[i] - (int64_t) request_offset[i], (int64_t) 0);
216 
217  dst_offset[i] = std::max((int64_t) clientDomain.getOffset()[i] -
218  (int64_t) request_offset[i], (int64_t) 0);
219 
220  if (request_offset[i] <= client_start[i])
221  {
222  // request starts before/equal client offset
223  src_offset[i] = 0;
224 
225  if (request_offset[i] + request_size[i] >= client_start[i] + client_size[i])
226  // end of request stretches beyond client limits
227  src_size[i] = client_size[i];
228  else
229  // end of request within client limits
230  src_size[i] = request_offset[i] + request_size[i] - client_start[i];
231  } else
232  {
233  // request starts after client offset
234  src_offset[i] = request_offset[i] - client_start[i];
235 
236  if (request_offset[i] + request_size[i] >= client_start[i] + client_size[i])
237  // end of request stretches beyond client limits
238  src_size[i] = client_size[i] - src_offset[i];
239  else
240  // end of request within client limits
241  src_size[i] = request_offset[i] + request_size[i] -
242  (client_start[i] + src_offset[i]);
243  }
244  }
245 
246  log_msg(3,
247  "clientDomain.getSize() = %s\n"
248  "dst_offset = %s "
249  "src_size = %s "
250  "src_offset = %s",
251  clientDomain.getSize().toString().c_str(),
252  dst_offset.toString().c_str(),
253  src_size.toString().c_str(),
254  src_offset.toString().c_str());
255 
256  assert(src_size[0] <= request_size[0]);
257  assert(src_size[1] <= request_size[1]);
258  assert(src_size[2] <= request_size[2]);
259 
260  // read intersecting partition into destination buffer
261  Dimensions elements_read(0, 0, 0);
262  uint32_t src_dims = 0;
263  readDataSet(handles.get(mpiPosition), id, name,
264  dataContainer->getIndex(0)->getSize(),
265  dst_offset,
266  src_size,
267  src_offset,
268  elements_read,
269  src_dims,
270  dataContainer->getIndex(0)->getData());
271 
272  if (!(elements_read == src_size))
273  throw DCException("DomainCollector::readGridInternal: Sizes are not equal but should be (2).");
274  }
275 
276  void DomainCollector::readPolyInternal(
277  DataContainer *dataContainer,
278  Dimensions mpiPosition,
279  int32_t id,
280  const char* name,
281  const Dimensions &dataSize,
282  const Domain &clientDomain,
283  bool lazyLoad
284  )
285  throw (DCException)
286  {
287  log_msg(3, "dataclass = Poly");
288 
289  if (dataSize.getScalarSize() > 0)
290  {
291  std::stringstream group_id_name;
292  group_id_name << SDC_GROUP_DATA << "/" << id;
293  std::string group_id_string = group_id_name.str();
294 
295  DCGroup group;
296  group.open(handles.get(mpiPosition), group_id_string);
297 
298  size_t datatype_size = 0;
299  DCDataType dc_datatype = DCDT_UNKNOWN;
300 
301  try
302  {
303  DCDataSet tmp_dataset(name);
304  tmp_dataset.open(group.getHandle());
305 
306  datatype_size = tmp_dataset.getDataTypeSize();
307  dc_datatype = tmp_dataset.getDCDataType();
308 
309  tmp_dataset.close();
310  } catch (const DCException& e)
311  {
312  throw e;
313  }
314 
315  group.close();
316 
317  DomainData *client_data = new DomainData(clientDomain,
318  dataSize, datatype_size, dc_datatype);
319 
320  if (lazyLoad)
321  {
322  client_data->setLoadingReference(PolyType,
323  handles.get(mpiPosition), id, name,
324  dataSize,
325  Dimensions(0, 0, 0),
326  Dimensions(0, 0, 0),
327  Dimensions(0, 0, 0));
328  } else
329  {
330  Dimensions size_read;
331  uint32_t src_ndims = 0;
332  readCompleteDataSet(handles.get(mpiPosition), id, name,
333  dataSize,
334  Dimensions(0, 0, 0),
335  Dimensions(0, 0, 0),
336  size_read,
337  src_ndims,
338  client_data->getData());
339 
340  if (!(size_read == dataSize))
341  throw DCException("DomainCollector::readPolyInternal: Sizes are not equal but should be (1).");
342  }
343 
344  dataContainer->add(client_data);
345  } else
346  {
347  log_msg(3, "skipping entry with 0 elements");
348  }
349  }
350 
351  bool DomainCollector::readDomainDataForRank(
352  DataContainer *dataContainer,
353  DomDataClass *dataClass,
354  Dimensions mpiPosition,
355  int32_t id,
356  const char* name,
357  const Domain requestDomain,
358  bool lazyLoad)
359  throw (DCException)
360  {
361  log_msg(3, "loading from mpi_position %s", mpiPosition.toString().c_str());
362 
363  bool readResult = false;
364  Domain local_client_domain, global_client_domain;
365  Dimensions data_size;
366  DomDataClass tmp_data_class = UndefinedType;
367 
368  {
369  hid_t dset_handle = openDatasetHandle(id, name, &mpiPosition);
370 
371  DCAttribute::readAttribute(DOMCOL_ATTR_OFFSET, dset_handle,
372  local_client_domain.getOffset().getPointer());
373 
374  DCAttribute::readAttribute(DOMCOL_ATTR_SIZE, dset_handle,
375  local_client_domain.getSize().getPointer());
376 
377  DCAttribute::readAttribute(DOMCOL_ATTR_GLOBAL_OFFSET, dset_handle,
378  global_client_domain.getOffset().getPointer());
379 
380  DCAttribute::readAttribute(DOMCOL_ATTR_GLOBAL_SIZE, dset_handle,
381  global_client_domain.getSize().getPointer());
382 
383  DCAttribute::readAttribute(DOMCOL_ATTR_CLASS, dset_handle,
384  &tmp_data_class);
385 
386  closeDatasetHandle(dset_handle);
387  }
388 
389  Domain client_domain(
390  local_client_domain.getOffset() + global_client_domain.getOffset(),
391  local_client_domain.getSize());
392 
393  readSizeInternal(handles.get(mpiPosition), id, name, data_size);
394 
395  log_msg(3,
396  "clientdom. = %s "
397  "requestdom.= %s "
398  "data size = %s",
399  client_domain.toString().c_str(),
400  requestDomain.toString().c_str(),
401  data_size.toString().c_str());
402 
403  const bool emptyRequest = (data_size.getScalarSize() == 1 &&
404  client_domain.getSize().getScalarSize() == 0);
405 
406  if (tmp_data_class == GridType && data_size != client_domain.getSize() &&
407  !emptyRequest)
408  {
409  std::cout << data_size.toString() << ", " << client_domain.getSize().toString() << std::endl;
410  throw DCException("DomainCollector::readDomain: Size of data must match domain size for Grid data.");
411  }
412 
413  if (*dataClass == UndefinedType)
414  {
415  *dataClass = tmp_data_class;
416  } else
417  if (tmp_data_class != *dataClass)
418  {
419  throw DCException("DomainCollector::readDomain: Data classes in files are inconsistent!");
420  }
421 
422  // test on intersection and add new DomainData to the container if necessary
423  if (Domain::testIntersection(requestDomain, client_domain))
424  {
425  readResult = true;
426 
427  switch (*dataClass)
428  {
429  case PolyType:
430  // Poly data has no internal grid structure,
431  // so the whole chunk has to be read and is added to the DataContainer.
432  readPolyInternal(dataContainer, mpiPosition, id, name,
433  data_size, client_domain, lazyLoad);
434  break;
435  case GridType:
436  // For Grid data, only the subchunk is read into its target position
437  // in the destination buffer.
438  readGridInternal(dataContainer, mpiPosition, id, name,
439  client_domain, requestDomain);
440  break;
441  default:
442  return false;
443  }
444  } else
445  {
446  log_msg(3, "no loading from this MPI position required");
447  }
448 
449  return readResult;
450  }
451 
453  const char* name,
454  Domain requestDomain,
455  DomDataClass* dataClass,
456  bool lazyLoad)
457  throw (DCException)
458  {
459  if ((fileStatus != FST_MERGING) && (fileStatus != FST_READING))
460  throw DCException("DomainCollector::readDomain: this access is not permitted");
461 
462  DataContainer *data_container = new DataContainer();
463  Dimensions request_offset = requestDomain.getOffset();
464 
465  log_msg(3,
466  "requestDomain = %s ",
467  requestDomain.toString().c_str());
468 
469  DomDataClass data_class = UndefinedType;
470  Dimensions mpi_size;
471 
472  if (fileStatus == FST_MERGING)
473  {
474  mpi_size.set(mpiTopology);
475  } else
476  mpi_size.set(1, 1, 1);
477 
478  Dimensions min_dims(0, 0, 0);
479  Dimensions max_dims(mpi_size);
480  max_dims = max_dims - Dimensions(1, 1, 1);
481 
482  // try to find the lowest corner (probably the file with the
483  // domain offset == globalOffset) of the full domain
484  // for periodically moving (e.g. moving window) simulations
485  // this happens to be _not_ at mpi_pos(0,0,0)
486  {
487  Dimensions delta(0, 0, 0);
488  Dimensions belowZero(min_dims);
489  Dimensions aboveZero(max_dims);
490  Domain minDom;
491  Domain globalDomain = getGlobalDomain(id, name);
492  do
493  {
494  log_msg(4, "find zero: belowZero = %s, aboveZero = %s",
495  belowZero.toString().c_str(),
496  aboveZero.toString().c_str());
497 
498  Domain maxDom;
499  readDomainInfoForRank(belowZero, id, name,
500  Domain(Dimensions(0, 0, 0), Dimensions(0, 0, 0)), minDom);
501  readDomainInfoForRank(aboveZero, id, name,
502  Domain(Dimensions(0, 0, 0), Dimensions(0, 0, 0)), maxDom);
503 
504  log_msg(4, "find zero: minDom.getOffset() = %s, maxDom.getOffset() = %s",
505  minDom.getOffset().toString().c_str(),
506  maxDom.getOffset().toString().c_str());
507 
508  for (size_t i = 0; i < DSP_DIM_MAX; ++i)
509  {
510  // zero still between min and max?
511  if (minDom.getOffset()[i] > maxDom.getOffset()[i])
512  {
513  delta[i] = ceil(((double) aboveZero[i] - (double) belowZero[i]) / 2.0);
514  belowZero[i] += delta[i];
515  } // found zero point for this i
516  else if (minDom.getOffset()[i] == globalDomain.getOffset()[i])
517  delta[i] = 0;
518  // jumped over the zero position during last +-=delta[i]
519  else
520  {
521  belowZero[i] -= delta[i];
522  aboveZero[i] -= delta[i];
523  }
524  }
525 
526  } while (delta != Dimensions(0, 0, 0));
527 
528  // search above or below zero point?
529  //
530  // the file with the largest mpi position, but not necessarily
531  // the one with the largest local domain offset
532  Domain lastDom;
533  readDomainInfoForRank(mpi_size - Dimensions(1, 1, 1), id, name,
534  Domain(Dimensions(0, 0, 0), Dimensions(0, 0, 0)), lastDom);
535  for (size_t i = 0; i < DSP_DIM_MAX; ++i)
536  {
537  if (request_offset[i] <= lastDom.getBack()[i])
538  {
539  min_dims[i] = belowZero[i];
540  max_dims[i] = mpi_size[i] - 1;
541  } else
542  {
543  min_dims[i] = 0;
544  belowZero[i] > 1 ? max_dims[i] = belowZero[i] - 1
545  : max_dims[i] = 0;
546  }
547  }
548  }
549 
550  Dimensions current_mpi_pos(min_dims);
551  Dimensions point_dim(1, 1, 1);
552 
553  // try to find top-left corner of requested domain
554  // stop if no new file can be tested for the requested domain
555  // (current_mpi_pos does not change anymore)
556  Dimensions last_mpi_pos(current_mpi_pos);
557  bool found_start = false;
558  do
559  {
560  log_msg(4, "find top-left: min_dims = %s, max_dims = %s",
561  min_dims.toString().c_str(),
562  max_dims.toString().c_str());
563 
564  Domain file_domain;
565  last_mpi_pos = current_mpi_pos;
566 
567  // set current_mpi_pos to be the 'center' between min_dims and max_dims
568  for (size_t i = 0; i < DSP_DIM_MAX; ++i)
569  {
570  current_mpi_pos[i] = min_dims[i] +
571  ceil(((double) max_dims[i] - (double) min_dims[i]) / 2.0);
572  }
573 
574  if (readDomainInfoForRank(current_mpi_pos, id, name,
575  Domain(request_offset, point_dim), file_domain))
576  {
577  found_start = true;
578  break;
579  }
580 
581  for (size_t i = 0; i < DSP_DIM_MAX; ++i)
582  {
583  if (request_offset[i] >= file_domain.getOffset()[i])
584  min_dims[i] = current_mpi_pos[i];
585 
586  if (request_offset[i] < file_domain.getOffset()[i])
587  max_dims[i] = current_mpi_pos[i] - 1;
588  }
589  } while (last_mpi_pos != current_mpi_pos);
590 
591  if (!found_start)
592  {
593  log_msg(2, "readDomain: no data found");
594  return data_container;
595  }
596 
597  // found top-left corner of requested domain
598  // In every file, domain attributes are read and evaluated.
599  // If the file domain and the requested domain intersect,
600  // the file domain is added to the DataContainer.
601 
602  // set new min_dims to top-left corner
603  for (size_t i = 0; i < DSP_DIM_MAX; ++i)
604  max_dims[i] = (current_mpi_pos[i] + mpi_size[i] - 1) % mpi_size[i];
605  min_dims = current_mpi_pos;
606 
607  log_msg(3, "readDomain: Looking for matching domain data in range "
608  "min_dims = %s "
609  "max_dims = %s",
610  min_dims.toString().c_str(),
611  max_dims.toString().c_str());
612 
613  bool found_last_entry = false;
614  // ..._lin indexes can range >= mpi_size since they are helper to
615  // calculate the next index (x,y,z) in the periodic modulo system
616  size_t z, z_lin = min_dims[2];
617  do
618  {
619  z = z_lin % mpi_size[2];
620  size_t y, y_lin = min_dims[1];
621  do
622  {
623  y = y_lin % mpi_size[1];
624  size_t x, x_lin = min_dims[0];
625  do
626  {
627  x = x_lin % mpi_size[0];
628  Dimensions mpi_position(x, y, z);
629 
630  if (!readDomainDataForRank(data_container,
631  &data_class,
632  mpi_position,
633  id,
634  name,
635  requestDomain,
636  lazyLoad))
637  {
638  // readDomainDataForRank returns false if no intersection
639  // has been found.
640  // Cut max_dims in the currently extending dimension if
641  // nothing can be found there, anymore.
642  if (z == min_dims[2])
643  {
644  if (y == min_dims[1])
645  {
646  max_dims[0] = (x + mpi_size[0] - 1) % mpi_size[0];
647  x = max_dims[0];
648  } else
649  {
650  max_dims[1] = (y + mpi_size[1] - 1) % mpi_size[1];
651  y = max_dims[1];
652  }
653  } else
654  {
655  found_last_entry = true;
656  break;
657  }
658  }
659 
660  x_lin++;
661  } while (x != max_dims[0]);
662 
663  if (found_last_entry)
664  break;
665 
666  y_lin++;
667  } while (y != max_dims[1]);
668 
669  if (found_last_entry)
670  break;
671 
672  z_lin++;
673  } while (z != max_dims[2]);
674 
675  if (dataClass != NULL)
676  *dataClass = data_class;
677 
678  return data_container;
679  }
680 
682  throw (DCException)
683  {
684  if (domainData == NULL)
685  {
686  throw DCException("DomainCollector::readDomainLazy: Invalid parameter, DomainData must not be NULL");
687  }
688 
689  DomainH5Ref *loadingRef = domainData->getLoadingReference();
690  if (loadingRef == NULL)
691  {
692  throw DCException("DomainCollector::readDomainLazy: This DomainData does not allow lazy loading");
693  }
694 
695  if (loadingRef->dataClass == UndefinedType)
696  {
697  throw DCException("DomainCollector::readDomainLazy: DomainData has invalid data class");
698  }
699 
700  if (loadingRef->dataClass == PolyType)
701  {
702  Dimensions elements_read;
703  uint32_t src_dims = 0;
704  readDataSet(loadingRef->handle,
705  loadingRef->id,
706  loadingRef->name.c_str(),
707  loadingRef->dstBuffer,
708  loadingRef->dstOffset,
709  loadingRef->srcSize,
710  loadingRef->srcOffset,
711  elements_read,
712  src_dims,
713  domainData->getData());
714 
715  if (!(elements_read == loadingRef->dstBuffer))
716  throw DCException("DomainCollector::readDomainLazy: Sizes are not equal but should be (1).");
717 
718  } else
719  {
720 
721  throw DCException("DomainCollector::readDomainLazy: data class not supported");
722  }
723  }
724 
726  const CollectionType& type,
727  uint32_t ndims,
728  const Selection select,
729  const char* name,
730  const Domain localDomain,
731  const Domain globalDomain,
732  DomDataClass dataClass,
733  const void* buf)
734  throw (DCException)
735  {
736  write(id, type, ndims, select, name, buf);
737  writeDomainAttributes(id, name, dataClass, localDomain, globalDomain);
738  }
739 
741  const CollectionType& type,
742  size_t count,
743  const char* name,
744  const Domain localDomain,
745  const Domain globalDomain,
746  const void* buf)
747  throw (DCException)
748  {
749  appendDomain(id, type, count, 0, 1, name, localDomain, globalDomain, buf);
750  }
751 
753  const CollectionType& type,
754  size_t count,
755  size_t offset,
756  size_t striding,
757  const char* name,
758  const Domain localDomain,
759  const Domain globalDomain,
760  const void* buf)
761  throw (DCException)
762  {
763  Dimensions elements(1, 1, 1);
764 
765  // temporarly change file access status to allow read access
766  FileStatusType old_file_status = fileStatus;
767  fileStatus = FST_READING;
768 
769  // try to get the number of elements already written, if any.
770  try
771  {
772  readSizeInternal(handles.get(0), id, name, elements);
773  } catch (const DCException&)
774  {
775  // nothing to do here but to make sure elements is set correctly
776  elements.set(0, 1, 1);
777  }
778 
779  fileStatus = old_file_status;
780 
781  elements[0] = elements[0] + count;
782 
783  append(id, type, count, offset, striding, name, buf);
784  writeDomainAttributes(id, name, PolyType, localDomain, globalDomain);
785  }
786 
787  void DomainCollector::readGlobalSizeFallback(int32_t id,
788  const char *dataName,
789  hsize_t* data,
790  Dimensions *mpiPosition)
791  throw (DCException)
792  {
793  try
794  {
795  readAttributeInfo(id, dataName, DOMCOL_ATTR_GLOBAL_SIZE, mpiPosition).read(data, sizeof(*data) * DSP_DIM_MAX);
796  } catch (const DCException&)
797  {
798  hsize_t local_size[DSP_DIM_MAX];
799  readAttributeInfo(id, dataName, DOMCOL_ATTR_SIZE, mpiPosition).read(local_size, sizeof(local_size));
800 
801  for (int i = 0; i < DSP_DIM_MAX; ++i)
802  data[i] = mpiTopology[i] * local_size[i];
803  }
804  }
805 
806  void DomainCollector::readGlobalOffsetFallback(int32_t id,
807  const char *dataName,
808  hsize_t* data,
809  Dimensions *mpiPosition)
810  throw (DCException)
811  {
812  try
813  {
814  readAttributeInfo(id, dataName, DOMCOL_ATTR_GLOBAL_OFFSET, mpiPosition).read(data, sizeof(*data) * DSP_DIM_MAX);
815  } catch (const DCException&)
816  {
817  for (int i = 0; i < DSP_DIM_MAX; ++i)
818  data[i] = 0;
819  }
820  }
821 }
hsize_t * getPointer()
Definition: Dimensions.hpp:192
Domain getGlobalDomain(int32_t id, const char *name)
std::string toString() const
Definition: Domain.hpp:142
void writeDomain(int32_t id, const CollectionType &type, uint32_t ndims, const Selection select, const char *name, const Domain localDomain, const Domain globalDomain, DomDataClass dataClass, const void *buf)
std::string toString() const
Definition: Dimensions.hpp:181
DataContainer * readDomain(int32_t id, const char *name, Domain domain, DomDataClass *dataClass, bool lazyLoad=false)
void append(int32_t id, const CollectionType &type, size_t count, const char *name, const void *data)
void readDomainLazy(DomainData *domainData)
Domain getLocalDomain(int32_t id, const char *name)
void set(hsize_t x, hsize_t y, hsize_t z)
Definition: Dimensions.hpp:230
Dimensions & getOffset()
Definition: Domain.hpp:101
Dimensions getBack() const
Definition: Domain.hpp:122
void setLoadingReference(int dataClass, hid_t handle, int32_t id, const char *name, const Dimensions dstBuffer, const Dimensions dstOffset, const Dimensions srcSize, const Dimensions srcOffset)
Definition: DomainData.hpp:153
size_t getScalarSize() const
Definition: Dimensions.hpp:219
Dimensions & getSize()
Definition: Domain.hpp:81
DomainData * getIndex(size_t index)
void write(int32_t id, const CollectionType &type, uint32_t ndims, const Selection select, const char *name, const void *data)
void add(DomainData *entry)
DomainCollector(uint32_t maxFileHandles)
static bool testIntersection(const Domain &d1, const Domain &d2)
Definition: Domain.hpp:156
const H5DataType & getDataType() const
EXTERN void log_msg(int level, const char *fmt,...)
Definition: logging.cpp:56
static size_t getSize()
Definition: Dimensions.hpp:210
void appendDomain(int32_t id, const CollectionType &type, size_t count, const char *name, const Domain localDomain, const Domain globalDomain, const void *buf)
void read(const CollectionType &colType, void *buf)
AttributeInfo readAttributeInfo(int32_t id, const char *dataName, const char *attrName, Dimensions *mpiPosition=NULL)