VTK  9.0.3
vtkMultiBlockPLOT3DReaderInternals.h
Go to the documentation of this file.
1 /*=========================================================================
2 
3  Program: Visualization Toolkit
4  Module: vtkMultiBlockPLOT3DReaderInternals.h
5 
6  Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
7  All rights reserved.
8  See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
9 
10  This software is distributed WITHOUT ANY WARRANTY; without even
11  the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
12  PURPOSE. See the above copyright notice for more information.
13 
14 =========================================================================*/
15 #ifndef vtkMultiBlockPLOT3DReaderInternals_h
16 #define vtkMultiBlockPLOT3DReaderInternals_h
17 
18 #include "vtkByteSwap.h"
19 #include "vtkIOParallelModule.h" // For export macro
21 #include "vtkSmartPointer.h"
22 #include "vtkStructuredGrid.h"
23 
24 #include <exception>
25 #include <vector>
26 
28 
29 #ifdef _WIN64
30 #define vtk_fseek _fseeki64
31 #define vtk_ftell _ftelli64
32 #define vtk_off_t __int64
33 #else
34 #define vtk_fseek fseek
35 #define vtk_ftell ftell
36 #define vtk_off_t long
37 #endif
38 
40 {
41  struct Dims
42  {
43 
44  Dims() { memset(this->Values, 0, 3 * sizeof(int)); }
45 
46  int Values[3];
47  };
48 
49  std::vector<Dims> Dimensions;
50  std::vector<vtkSmartPointer<vtkStructuredGrid> > Blocks;
51 
53  {
55  int ByteOrder;
57  int MultiGrid;
59  int Precision; // in bytes
60  int IBlanking;
62  : BinaryFile(1)
63  , ByteOrder(vtkMultiBlockPLOT3DReader::FILE_BIG_ENDIAN)
64  , HasByteCount(1)
65  , MultiGrid(0)
67  , Precision(4)
68  , IBlanking(0)
69  {
70  }
71  };
72 
75 
77  : NeedToCheckXYZFile(true)
78  {
79  }
80 
81  int ReadInts(FILE* fp, int n, int* val);
82  void CheckBinaryFile(FILE* fp, size_t fileSize);
83  int CheckByteOrder(FILE* fp);
84  int CheckByteCount(FILE* fp);
85  int CheckMultiGrid(FILE* fp);
86  int Check2DGeom(FILE* fp);
88  int CheckCFile(FILE* fp, size_t fileSize);
89  size_t CalculateFileSize(int mgrid,
90  int precision, // in bytes
91  int blanking, int ndims, int hasByteCount, int nGrids, int* gridDims);
92  size_t CalculateFileSizeForBlock(int precision, // in bytes
93  int blanking, int ndims, int hasByteCount, int* gridDims);
94 
95  static void CalculateSkips(
96  const int extent[6], const int wextent[6], vtkIdType& preskip, vtkIdType& postskip)
97  {
98  vtkIdType nPtsInPlane = static_cast<vtkIdType>(wextent[1] + 1) * (wextent[3] + 1);
99  preskip = nPtsInPlane * extent[4];
100  postskip = nPtsInPlane * (wextent[5] - extent[5]);
101  }
102 };
103 
104 namespace
105 {
106 class Plot3DException : public std::exception
107 {
108 };
109 }
110 
111 // Description:
112 // vtkMultiBlockPLOT3DReaderRecord represents a data record in the file. For
113 // binary Plot3D files with record separators (i.e. leading and trailing length
114 // field per record see: https://software.intel.com/en-us/node/525311), if the
115 // record length is greater than 2,147,483,639 bytes, the record get split into
116 // multiple records. This class allows use to manage that.
117 // It corresponds to a complete record i.e. including all the records when split
118 // among multiple records due to length limit.
119 class VTKIOPARALLEL_EXPORT vtkMultiBlockPLOT3DReaderRecord
120 {
121  struct vtkSubRecord
122  {
123  vtkTypeUInt64 HeaderOffset;
124  vtkTypeUInt64 FooterOffset;
125  };
126 
127  typedef std::vector<vtkSubRecord> VectorOfSubRecords;
128  VectorOfSubRecords SubRecords;
129 
130 public:
131  // Description:
132  // A type for collection of sub-record separators i.e. separators encountered
133  // within a record when the record length is greater than 2,147,483,639 bytes.
134  typedef std::vector<vtkTypeUInt64> SubRecordSeparators;
135 
136  // Description:
137  // Since a sub-record separator is made up of the trailing length field of a
138  // sub-record and the leading length field of the next sub-record, it's length
139  // is two ints.
140  static const int SubRecordSeparatorWidth = sizeof(int) * 2;
141 
142  // Description:
143  // Initialize metadata about the record located at the given offset.
144  // This reads the file on the root node to populate record information,
145  // seeking and marching forward through the file if the record comprises of
146  // multiple sub-records. The file is reset back to the original starting
147  // position when done.
148  //
149  // This method has no effect for non-binary files or files that don't have
150  // record separators i.e. HasByteCount == 0.
151  bool Initialize(FILE* fp, vtkTypeUInt64 offset,
153  vtkMultiProcessController* controller);
154 
155  // Description:
156  // Returns true if:
157  // 1. file doesn't comprise of records i.e. ASCII or doesn't have byte-count markers.
158  // 2. offset is same as the start offset for this record.
159  bool AtStart(vtkTypeUInt64 offset)
160  {
161  return (this->SubRecords.size() == 0 || this->SubRecords.front().HeaderOffset == offset);
162  }
163 
164  // Description:
165  // Returns true if:
166  // 1. file doesn't comprise of records i.e. ASCII or doesn't have byte-count markers.
167  // 2. offset is at the end of this record i.e. the start of the next record.
168  bool AtEnd(vtkTypeUInt64 offset)
169  {
170  return (this->SubRecords.size() == 0 ||
171  (this->SubRecords.back().FooterOffset + sizeof(int) == offset));
172  }
173 
174  // Description:
175  // Returns the location of SubRecordSeparators (bad two 4-byte ints) between startOffset and
176  // (startOffset + length).
177  SubRecordSeparators GetSubRecordSeparators(vtkTypeUInt64 startOffset, vtkTypeUInt64 length) const;
178 
179  // Description:
180  // When reading between file offsets \c start and \c (start + length) from the file, if it has
181  // any sub-record separators, this method splits the read into chunks so that it skips the
182  // sub-record separators. The returned value is a vector of pairs (offset, length-in-bytes).
183  static std::vector<std::pair<vtkTypeUInt64, vtkTypeUInt64> > GetChunksToRead(
184  vtkTypeUInt64 start, vtkTypeUInt64 length, const std::vector<vtkTypeUInt64>& markers);
185 
186  // Description:
187  // If the block in file (start, start+length) steps over sub-record separators
188  // within this record, then this method will return a new length that includes
189  // the bytes for the separators to be skipped. Otherwise, simply returns the
190  // length.
191  vtkTypeUInt64 GetLengthWithSeparators(vtkTypeUInt64 start, vtkTypeUInt64 length) const;
192 
193  std::vector<std::pair<vtkTypeUInt64, vtkTypeUInt64> > GetChunksToRead(
194  vtkTypeUInt64 start, vtkTypeUInt64 length) const
195  {
196  return this->GetChunksToRead(start, length, this->GetSubRecordSeparators(start, length));
197  }
198 };
199 
200 #endif
201 // VTK-HeaderTest-Exclude: vtkMultiBlockPLOT3DReaderInternals.h
std::vector< std::pair< vtkTypeUInt64, vtkTypeUInt64 > > GetChunksToRead(vtkTypeUInt64 start, vtkTypeUInt64 length) const
static std::vector< std::pair< vtkTypeUInt64, vtkTypeUInt64 > > GetChunksToRead(vtkTypeUInt64 start, vtkTypeUInt64 length, const std::vector< vtkTypeUInt64 > &markers)
vtkTypeUInt64 GetLengthWithSeparators(vtkTypeUInt64 start, vtkTypeUInt64 length) const
bool Initialize(FILE *fp, vtkTypeUInt64 offset, const vtkMultiBlockPLOT3DReaderInternals::InternalSettings &settings, vtkMultiProcessController *controller)
SubRecordSeparators GetSubRecordSeparators(vtkTypeUInt64 startOffset, vtkTypeUInt64 length) const
Multiprocessing communication superclass.
@ length
Definition: vtkX3D.h:399
@ extent
Definition: vtkX3D.h:351
@ offset
Definition: vtkX3D.h:444
static void CalculateSkips(const int extent[6], const int wextent[6], vtkIdType &preskip, vtkIdType &postskip)
int ReadInts(FILE *fp, int n, int *val)
std::vector< vtkSmartPointer< vtkStructuredGrid > > Blocks
size_t CalculateFileSizeForBlock(int precision, int blanking, int ndims, int hasByteCount, int *gridDims)
size_t CalculateFileSize(int mgrid, int precision, int blanking, int ndims, int hasByteCount, int nGrids, int *gridDims)
int CheckCFile(FILE *fp, size_t fileSize)
void CheckBinaryFile(FILE *fp, size_t fileSize)
int vtkIdType
Definition: vtkType.h:338