ACloudViewer  3.9.4
A Modern Library for 3D Data Processing
SourceDestBufferImpl.cpp
Go to the documentation of this file.
1 /*
2  * Original work Copyright 2009 - 2010 Kevin Ackley (kackley@gwi.net)
3  * Modified work Copyright 2018 - 2020 Andy Maloney <asmaloney@gmail.com>
4  *
5  * Permission is hereby granted, free of charge, to any person or organization
6  * obtaining a copy of the software and accompanying documentation covered by
7  * this license (the "Software") to use, reproduce, display, distribute,
8  * execute, and transmit the Software, and to prepare derivative works of the
9  * Software, and to permit third-parties to whom the Software is furnished to
10  * do so, all subject to the following:
11  *
12  * The copyright notices in the Software and this entire statement, including
13  * the above license grant, this restriction and the following disclaimer,
14  * must be included in all copies of the Software, in whole or in part, and
15  * all derivative works of the Software, unless such copies or derivative
16  * works are solely in the form of machine-executable object code generated by
17  * a source language processor.
18  *
19  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21  * FITNESS FOR A PARTICULAR PURPOSE, TITLE AND NON-INFRINGEMENT. IN NO EVENT
22  * SHALL THE COPYRIGHT HOLDERS OR ANYONE DISTRIBUTING THE SOFTWARE BE LIABLE
23  * FOR ANY DAMAGES OR OTHER LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE,
24  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
25  * DEALINGS IN THE SOFTWARE.
26  */
27 
28 #include <cmath>
29 
30 #include "ImageFileImpl.h"
31 #include "SourceDestBufferImpl.h"
32 
33 using namespace e57;
34 
36  const size_t capacity, bool doConversion, bool doScaling ) :
37  destImageFile_( destImageFile ), pathName_( pathName ), capacity_( capacity ), doConversion_( doConversion ),
38  doScaling_( doScaling )
39 {
40 }
41 
42 template <typename T> void SourceDestBufferImpl::setTypeInfo( T *base, size_t stride )
43 {
44  static_assert( std::is_integral<T>::value || std::is_floating_point<T>::value,
45  "Integral or floating point required." );
46 
47  base_ = reinterpret_cast<char *>( base );
48  stride_ = stride;
49 
50  // this is a little ugly, but it saves us having to pass around the memory
51  // representation
52  if ( std::is_same<T, int8_t>::value )
53  {
54  memoryRepresentation_ = E57_INT8;
55  }
56  else if ( std::is_same<T, uint8_t>::value )
57  {
58  memoryRepresentation_ = E57_UINT8;
59  }
60  else if ( std::is_same<T, int16_t>::value )
61  {
62  memoryRepresentation_ = E57_INT16;
63  }
64  else if ( std::is_same<T, uint16_t>::value )
65  {
66  memoryRepresentation_ = E57_UINT16;
67  }
68  else if ( std::is_same<T, int32_t>::value )
69  {
70  memoryRepresentation_ = E57_INT32;
71  }
72  else if ( std::is_same<T, uint32_t>::value )
73  {
74  memoryRepresentation_ = E57_UINT32;
75  }
76  else if ( std::is_same<T, int64_t>::value )
77  {
78  memoryRepresentation_ = E57_INT64;
79  }
80  else if ( std::is_same<T, bool>::value )
81  {
82  memoryRepresentation_ = E57_BOOL;
83  }
84  else if ( std::is_same<T, float>::value )
85  {
86  memoryRepresentation_ = E57_REAL32;
87  }
88  else if ( std::is_same<T, double>::value )
89  {
90  memoryRepresentation_ = E57_REAL64;
91  }
92 
93  checkState_();
94 }
95 
96 template void SourceDestBufferImpl::setTypeInfo<int8_t>( int8_t *base, size_t stride );
97 template void SourceDestBufferImpl::setTypeInfo<uint8_t>( uint8_t *base, size_t stride );
98 template void SourceDestBufferImpl::setTypeInfo<int16_t>( int16_t *base, size_t stride );
99 template void SourceDestBufferImpl::setTypeInfo<uint16_t>( uint16_t *base, size_t stride );
100 template void SourceDestBufferImpl::setTypeInfo<int32_t>( int32_t *base, size_t stride );
101 template void SourceDestBufferImpl::setTypeInfo<uint32_t>( uint32_t *base, size_t stride );
102 template void SourceDestBufferImpl::setTypeInfo<int64_t>( int64_t *base, size_t stride );
103 template void SourceDestBufferImpl::setTypeInfo<bool>( bool *base, size_t stride );
104 template void SourceDestBufferImpl::setTypeInfo<float>( float *base, size_t stride );
105 template void SourceDestBufferImpl::setTypeInfo<double>( double *base, size_t stride );
106 
108  std::vector<ustring> *b ) :
109  destImageFile_( destImageFile ), pathName_( pathName ), memoryRepresentation_( E57_USTRING ), ustrings_( b )
110 {
112 
114  if ( b == nullptr )
115  {
116  throw E57_EXCEPTION2( E57_ERROR_BAD_BUFFER, "sdbuf.pathName=" + pathName );
117  }
118 
119  capacity_ = b->size();
120 
121  checkState_();
122 
126 }
127 
128 template <typename T> void SourceDestBufferImpl::_setNextReal( T inValue )
129 {
130  static_assert( std::is_same<T, double>::value || std::is_same<T, float>::value,
131  "_setNextReal() requires float or double type" );
132 
134 
136  if ( nextIndex_ >= capacity_ )
137  {
138  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
139  }
140 
143  char *p = &base_[nextIndex_ * stride_];
144 
145  switch ( memoryRepresentation_ )
146  {
147  case E57_INT8:
148  if ( !doConversion_ )
149  {
150  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
151  }
152  //??? fault if get special value: NaN, NegInf... (all other ints below
153  // too)
154  if ( inValue < E57_INT8_MIN || E57_INT8_MAX < inValue )
155  {
157  "pathName=" + pathName_ + " value=" + toString( inValue ) );
158  }
159  *reinterpret_cast<int8_t *>( p ) = static_cast<int8_t>( inValue );
160  break;
161  case E57_UINT8:
162  if ( !doConversion_ )
163  {
164  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
165  }
166  if ( inValue < E57_UINT8_MIN || E57_UINT8_MAX < inValue )
167  {
169  "pathName=" + pathName_ + " value=" + toString( inValue ) );
170  }
171  *reinterpret_cast<uint8_t *>( p ) = static_cast<uint8_t>( inValue );
172  break;
173  case E57_INT16:
174  if ( !doConversion_ )
175  {
176  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
177  }
178  if ( inValue < E57_INT16_MIN || E57_INT16_MAX < inValue )
179  {
181  "pathName=" + pathName_ + " value=" + toString( inValue ) );
182  }
183  *reinterpret_cast<int16_t *>( p ) = static_cast<int16_t>( inValue );
184  break;
185  case E57_UINT16:
186  if ( !doConversion_ )
187  {
188  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
189  }
190  if ( inValue < E57_UINT16_MIN || E57_UINT16_MAX < inValue )
191  {
193  "pathName=" + pathName_ + " value=" + toString( inValue ) );
194  }
195  *reinterpret_cast<uint16_t *>( p ) = static_cast<uint16_t>( inValue );
196  break;
197  case E57_INT32:
198  if ( !doConversion_ )
199  {
200  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
201  }
202  if ( inValue < E57_INT32_MIN || E57_INT32_MAX < inValue )
203  {
205  "pathName=" + pathName_ + " value=" + toString( inValue ) );
206  }
207  *reinterpret_cast<int32_t *>( p ) = static_cast<int32_t>( inValue );
208  break;
209  case E57_UINT32:
210  if ( !doConversion_ )
211  {
212  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
213  }
214  if ( inValue < E57_UINT32_MIN || E57_UINT32_MAX < inValue )
215  {
217  "pathName=" + pathName_ + " value=" + toString( inValue ) );
218  }
219  *reinterpret_cast<uint32_t *>( p ) = static_cast<uint32_t>( inValue );
220  break;
221  case E57_INT64:
222  if ( !doConversion_ )
223  {
224  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
225  }
226  if ( inValue < E57_INT64_MIN || E57_INT64_MAX < inValue )
227  {
229  "pathName=" + pathName_ + " value=" + toString( inValue ) );
230  }
231  *reinterpret_cast<int64_t *>( p ) = static_cast<int64_t>( inValue );
232  break;
233  case E57_BOOL:
234  if ( !doConversion_ )
235  {
236  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
237  }
238  *reinterpret_cast<bool *>( p ) = ( inValue ? false : true );
239  break;
240  case E57_REAL32:
241  if ( std::is_same<T, double>::value )
242  {
246  if ( inValue < E57_DOUBLE_MIN || E57_DOUBLE_MAX < inValue )
247  {
249  "pathName=" + pathName_ + " value=" + toString( inValue ) );
250  }
251  *reinterpret_cast<float *>( p ) = static_cast<float>( inValue );
252  }
253  else
254  {
255 #ifdef _MSC_VER
256  // MSVC is not smart enough to realize 'inValue' cannot be a double here, so disable warning
257 #pragma warning( disable : 4244 )
258  *reinterpret_cast<float *>( p ) = inValue;
259 #pragma warning( default : 4244 )
260 #else
261  *reinterpret_cast<float *>( p ) = inValue;
262 #endif
263  }
264  break;
265  case E57_REAL64:
266  //??? does this count as a conversion?
267  *reinterpret_cast<double *>( p ) = static_cast<double>( inValue );
268  break;
269  case E57_USTRING:
270  throw E57_EXCEPTION2( E57_ERROR_EXPECTING_NUMERIC, "pathName=" + pathName_ );
271  }
272 
273  nextIndex_++;
274 }
275 
276 void SourceDestBufferImpl::checkState_() const
277 {
280  ImageFileImplSharedPtr destImageFile( destImageFile_ );
281  if ( !destImageFile->isOpen() )
282  {
283  throw E57_EXCEPTION2( E57_ERROR_IMAGEFILE_NOT_OPEN, "fileName=" + destImageFile->fileName() );
284  }
285 
288  ImageFileImplSharedPtr imf( destImageFile_ );
289  imf->pathNameCheckWellFormed( pathName_ );
290 
291  if ( memoryRepresentation_ != E57_USTRING )
292  {
293  if ( base_ == nullptr )
294  {
295  throw E57_EXCEPTION2( E57_ERROR_BAD_BUFFER, "pathName=" + pathName_ );
296  }
297  if ( stride_ == 0 )
298  {
299  throw E57_EXCEPTION2( E57_ERROR_BAD_BUFFER, "pathName=" + pathName_ );
300  }
301  //??? check base alignment, depending on CPU type
302  //??? check if stride too small, positive or negative
303  }
304  else
305  {
306  if ( ustrings_ == nullptr )
307  {
308  throw E57_EXCEPTION2( E57_ERROR_BAD_BUFFER, "pathName=" + pathName_ );
309  }
310  }
311 }
312 
314 {
316 
318  if ( nextIndex_ >= capacity_ )
319  {
320  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
321  }
322 
325  char *p = &base_[nextIndex_ * stride_];
326  int64_t value;
327  switch ( memoryRepresentation_ )
328  {
329  case E57_INT8:
330  value = static_cast<int64_t>( *reinterpret_cast<int8_t *>( p ) );
331  break;
332  case E57_UINT8:
333  value = static_cast<int64_t>( *reinterpret_cast<uint8_t *>( p ) );
334  break;
335  case E57_INT16:
336  value = static_cast<int64_t>( *reinterpret_cast<int16_t *>( p ) );
337  break;
338  case E57_UINT16:
339  value = static_cast<int64_t>( *reinterpret_cast<uint16_t *>( p ) );
340  break;
341  case E57_INT32:
342  value = static_cast<int64_t>( *reinterpret_cast<int32_t *>( p ) );
343  break;
344  case E57_UINT32:
345  value = static_cast<int64_t>( *reinterpret_cast<uint32_t *>( p ) );
346  break;
347  case E57_INT64:
348  value = *reinterpret_cast<int64_t *>( p );
349  break;
350  case E57_BOOL:
351  if ( !doConversion_ )
352  {
353  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
354  }
356  value = ( *reinterpret_cast<bool *>( p ) ) ? 1 : 0;
357  break;
358  case E57_REAL32:
359  if ( !doConversion_ )
360  {
361  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
362  }
363  //??? fault if get special value: NaN, NegInf...
364  value = static_cast<int64_t>( *reinterpret_cast<float *>( p ) );
365  break;
366  case E57_REAL64:
367  if ( !doConversion_ )
368  {
369  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
370  }
371  //??? fault if get special value: NaN, NegInf...
372  value = static_cast<int64_t>( *reinterpret_cast<double *>( p ) );
373  break;
374  case E57_USTRING:
375  throw E57_EXCEPTION2( E57_ERROR_EXPECTING_NUMERIC, "pathName=" + pathName_ );
376  default:
377  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
378  }
379  nextIndex_++;
380  return ( value );
381 }
382 
383 int64_t SourceDestBufferImpl::getNextInt64( double scale, double offset )
384 {
386 
389 
393  if ( !doScaling_ )
394  {
396  return ( getNextInt64() );
397  }
398 
400  if ( scale == 0 )
401  {
402  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
403  }
404 
406  if ( nextIndex_ >= capacity_ )
407  {
408  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
409  }
410 
413  char *p = &base_[nextIndex_ * stride_];
414  double doubleRawValue;
415  switch ( memoryRepresentation_ )
416  {
417  case E57_INT8:
420  doubleRawValue = floor( ( *reinterpret_cast<int8_t *>( p ) - offset ) / scale + 0.5 );
421  break;
422  case E57_UINT8:
425  doubleRawValue = floor( ( *reinterpret_cast<uint8_t *>( p ) - offset ) / scale + 0.5 );
426  break;
427  case E57_INT16:
430  doubleRawValue = floor( ( *reinterpret_cast<int16_t *>( p ) - offset ) / scale + 0.5 );
431  break;
432  case E57_UINT16:
435  doubleRawValue = floor( ( *reinterpret_cast<uint16_t *>( p ) - offset ) / scale + 0.5 );
436  break;
437  case E57_INT32:
440  doubleRawValue = floor( ( *reinterpret_cast<int32_t *>( p ) - offset ) / scale + 0.5 );
441  break;
442  case E57_UINT32:
445  doubleRawValue = floor( ( *reinterpret_cast<uint32_t *>( p ) - offset ) / scale + 0.5 );
446  break;
447  case E57_INT64:
450  doubleRawValue = floor( ( *reinterpret_cast<int64_t *>( p ) - offset ) / scale + 0.5 );
451  break;
452  case E57_BOOL:
453  if ( *reinterpret_cast<bool *>( p ) )
454  {
455  doubleRawValue = floor( ( 1 - offset ) / scale + 0.5 );
456  }
457  else
458  {
459  doubleRawValue = floor( ( 0 - offset ) / scale + 0.5 );
460  }
461  break;
462  case E57_REAL32:
463  if ( !doConversion_ )
464  {
465  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
466  }
467  //??? fault if get special value: NaN, NegInf...
468 
471  doubleRawValue = floor( ( *reinterpret_cast<float *>( p ) - offset ) / scale + 0.5 );
472  break;
473  case E57_REAL64:
474  if ( !doConversion_ )
475  {
476  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
477  }
478  //??? fault if get special value: NaN, NegInf...
479 
482  doubleRawValue = floor( ( *reinterpret_cast<double *>( p ) - offset ) / scale + 0.5 );
483  break;
484  case E57_USTRING:
485  throw E57_EXCEPTION2( E57_ERROR_EXPECTING_NUMERIC, "pathName=" + pathName_ );
486  default:
487  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
488  }
490  if ( doubleRawValue < E57_INT64_MIN || E57_INT64_MAX < doubleRawValue )
491  {
493  "pathName=" + pathName_ + " value=" + toString( doubleRawValue ) );
494  }
495 
496  auto rawValue = static_cast<int64_t>( doubleRawValue );
497 
498  nextIndex_++;
499  return ( rawValue );
500 }
501 
503 {
505 
507  if ( nextIndex_ >= capacity_ )
508  {
509  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
510  }
511 
514  char *p = &base_[nextIndex_ * stride_];
515  float value;
516  switch ( memoryRepresentation_ )
517  {
518  case E57_INT8:
519  if ( !doConversion_ )
520  {
521  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
522  }
523  value = static_cast<float>( *reinterpret_cast<int8_t *>( p ) );
524  break;
525  case E57_UINT8:
526  if ( !doConversion_ )
527  {
528  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
529  }
530  value = static_cast<float>( *reinterpret_cast<uint8_t *>( p ) );
531  break;
532  case E57_INT16:
533  if ( !doConversion_ )
534  {
535  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
536  }
537  value = static_cast<float>( *reinterpret_cast<int16_t *>( p ) );
538  break;
539  case E57_UINT16:
540  if ( !doConversion_ )
541  {
542  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
543  }
544  value = static_cast<float>( *reinterpret_cast<uint16_t *>( p ) );
545  break;
546  case E57_INT32:
547  if ( !doConversion_ )
548  {
549  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
550  }
551  value = static_cast<float>( *reinterpret_cast<int32_t *>( p ) );
552  break;
553  case E57_UINT32:
554  if ( !doConversion_ )
555  {
556  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
557  }
558  value = static_cast<float>( *reinterpret_cast<uint32_t *>( p ) );
559  break;
560  case E57_INT64:
561  if ( !doConversion_ )
562  {
563  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
564  }
565  value = static_cast<float>( *reinterpret_cast<int64_t *>( p ) );
566  break;
567  case E57_BOOL:
568  if ( !doConversion_ )
569  {
570  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
571  }
572 
574  value = ( *reinterpret_cast<bool *>( p ) ) ? 1.0F : 0.0F;
575  break;
576  case E57_REAL32:
577  value = *reinterpret_cast<float *>( p );
578  break;
579  case E57_REAL64:
580  {
583  double d = *reinterpret_cast<double *>( p );
584 
586  if ( d < E57_DOUBLE_MIN || E57_DOUBLE_MAX < d )
587  {
588  throw E57_EXCEPTION2( E57_ERROR_REAL64_TOO_LARGE, "pathName=" + pathName_ + " value=" + toString( d ) );
589  }
590  value = static_cast<float>( d );
591  break;
592  }
593  case E57_USTRING:
594  throw E57_EXCEPTION2( E57_ERROR_EXPECTING_NUMERIC, "pathName=" + pathName_ );
595  default:
596  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
597  }
598  nextIndex_++;
599  return ( value );
600 }
601 
603 {
605 
607  if ( nextIndex_ >= capacity_ )
608  {
609  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
610  }
611 
614  char *p = &base_[nextIndex_ * stride_];
615  double value;
616  switch ( memoryRepresentation_ )
617  {
618  case E57_INT8:
619  if ( !doConversion_ )
620  {
621  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
622  }
623  value = static_cast<double>( *reinterpret_cast<int8_t *>( p ) );
624  break;
625  case E57_UINT8:
626  if ( !doConversion_ )
627  {
628  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
629  }
630  value = static_cast<double>( *reinterpret_cast<uint8_t *>( p ) );
631  break;
632  case E57_INT16:
633  if ( !doConversion_ )
634  {
635  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
636  }
637  value = static_cast<double>( *reinterpret_cast<int16_t *>( p ) );
638  break;
639  case E57_UINT16:
640  if ( !doConversion_ )
641  {
642  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
643  }
644  value = static_cast<double>( *reinterpret_cast<uint16_t *>( p ) );
645  break;
646  case E57_INT32:
647  if ( !doConversion_ )
648  {
649  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
650  }
651  value = static_cast<double>( *reinterpret_cast<int32_t *>( p ) );
652  break;
653  case E57_UINT32:
654  if ( !doConversion_ )
655  {
656  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
657  }
658  value = static_cast<double>( *reinterpret_cast<uint32_t *>( p ) );
659  break;
660  case E57_INT64:
661  if ( !doConversion_ )
662  {
663  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
664  }
665  value = static_cast<double>( *reinterpret_cast<int64_t *>( p ) );
666  break;
667  case E57_BOOL:
668  if ( !doConversion_ )
669  {
670  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
671  }
673  value = ( *reinterpret_cast<bool *>( p ) ) ? 1.0 : 0.0;
674  break;
675  case E57_REAL32:
676  value = static_cast<double>( *reinterpret_cast<float *>( p ) );
677  break;
678  case E57_REAL64:
679  value = *reinterpret_cast<double *>( p );
680  break;
681  case E57_USTRING:
682  throw E57_EXCEPTION2( E57_ERROR_EXPECTING_NUMERIC, "pathName=" + pathName_ );
683  default:
684  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
685  }
686  nextIndex_++;
687  return ( value );
688 }
689 
691 {
693 
695  if ( memoryRepresentation_ != E57_USTRING )
696  {
697  throw E57_EXCEPTION2( E57_ERROR_EXPECTING_USTRING, "pathName=" + pathName_ );
698  }
699 
701  if ( nextIndex_ >= capacity_ )
702  {
703  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
704  }
705 
707  return ( ( *ustrings_ )[nextIndex_++] );
708 }
709 
711 {
713 
715  if ( nextIndex_ >= capacity_ )
716  {
717  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
718  }
719 
722  char *p = &base_[nextIndex_ * stride_];
723 
724  switch ( memoryRepresentation_ )
725  {
726  case E57_INT8:
727  if ( value < E57_INT8_MIN || E57_INT8_MAX < value )
728  {
730  "pathName=" + pathName_ + " value=" + toString( value ) );
731  }
732  *reinterpret_cast<int8_t *>( p ) = static_cast<int8_t>( value );
733  break;
734  case E57_UINT8:
735  if ( value < E57_UINT8_MIN || E57_UINT8_MAX < value )
736  {
738  "pathName=" + pathName_ + " value=" + toString( value ) );
739  }
740  *reinterpret_cast<uint8_t *>( p ) = static_cast<uint8_t>( value );
741  break;
742  case E57_INT16:
743  if ( value < E57_INT16_MIN || E57_INT16_MAX < value )
744  {
746  "pathName=" + pathName_ + " value=" + toString( value ) );
747  }
748  *reinterpret_cast<int16_t *>( p ) = static_cast<int16_t>( value );
749  break;
750  case E57_UINT16:
751  if ( value < E57_UINT16_MIN || E57_UINT16_MAX < value )
752  {
754  "pathName=" + pathName_ + " value=" + toString( value ) );
755  }
756  *reinterpret_cast<uint16_t *>( p ) = static_cast<uint16_t>( value );
757  break;
758  case E57_INT32:
759  if ( value < E57_INT32_MIN || E57_INT32_MAX < value )
760  {
762  "pathName=" + pathName_ + " value=" + toString( value ) );
763  }
764  *reinterpret_cast<int32_t *>( p ) = static_cast<int32_t>( value );
765  break;
766  case E57_UINT32:
767  if ( value < E57_UINT32_MIN || E57_UINT32_MAX < value )
768  {
770  "pathName=" + pathName_ + " value=" + toString( value ) );
771  }
772  *reinterpret_cast<uint32_t *>( p ) = static_cast<uint32_t>( value );
773  break;
774  case E57_INT64:
775  *reinterpret_cast<int64_t *>( p ) = static_cast<int64_t>( value );
776  break;
777  case E57_BOOL:
778  *reinterpret_cast<bool *>( p ) = ( value ? false : true );
779  break;
780  case E57_REAL32:
781  if ( !doConversion_ )
782  {
783  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
784  }
785  //??? very large integers may lose some lowest bits here. error?
786  *reinterpret_cast<float *>( p ) = static_cast<float>( value );
787  break;
788  case E57_REAL64:
789  if ( !doConversion_ )
790  {
791  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
792  }
793  *reinterpret_cast<double *>( p ) = static_cast<double>( value );
794  break;
795  case E57_USTRING:
796  throw E57_EXCEPTION2( E57_ERROR_EXPECTING_NUMERIC, "pathName=" + pathName_ );
797  }
798 
799  nextIndex_++;
800 }
801 
802 void SourceDestBufferImpl::setNextInt64( int64_t value, double scale, double offset )
803 {
805 
808 
812  if ( !doScaling_ )
813  {
815  setNextInt64( value );
816  return;
817  }
818 
820  if ( nextIndex_ >= capacity_ )
821  {
822  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
823  }
824 
827  char *p = &base_[nextIndex_ * stride_];
828 
830  double scaledValue;
831  if ( memoryRepresentation_ == E57_REAL32 || memoryRepresentation_ == E57_REAL64 )
832  {
835  scaledValue = value * scale + offset;
836  }
837  else
838  {
842  scaledValue = floor( value * scale + offset + 0.5 );
843  }
844 
845  switch ( memoryRepresentation_ )
846  {
847  case E57_INT8:
848  if ( scaledValue < E57_INT8_MIN || E57_INT8_MAX < scaledValue )
849  {
851  "pathName=" + pathName_ + " scaledValue=" + toString( scaledValue ) );
852  }
853  *reinterpret_cast<int8_t *>( p ) = static_cast<int8_t>( scaledValue );
854  break;
855  case E57_UINT8:
856  if ( scaledValue < E57_UINT8_MIN || E57_UINT8_MAX < scaledValue )
857  {
859  "pathName=" + pathName_ + " scaledValue=" + toString( scaledValue ) );
860  }
861  *reinterpret_cast<uint8_t *>( p ) = static_cast<uint8_t>( scaledValue );
862  break;
863  case E57_INT16:
864  if ( scaledValue < E57_INT16_MIN || E57_INT16_MAX < scaledValue )
865  {
867  "pathName=" + pathName_ + " scaledValue=" + toString( scaledValue ) );
868  }
869  *reinterpret_cast<int16_t *>( p ) = static_cast<int16_t>( scaledValue );
870  break;
871  case E57_UINT16:
872  if ( scaledValue < E57_UINT16_MIN || E57_UINT16_MAX < scaledValue )
873  {
875  "pathName=" + pathName_ + " scaledValue=" + toString( scaledValue ) );
876  }
877  *reinterpret_cast<uint16_t *>( p ) = static_cast<uint16_t>( scaledValue );
878  break;
879  case E57_INT32:
880  if ( scaledValue < E57_INT32_MIN || E57_INT32_MAX < scaledValue )
881  {
883  "pathName=" + pathName_ + " scaledValue=" + toString( scaledValue ) );
884  }
885  *reinterpret_cast<int32_t *>( p ) = static_cast<int32_t>( scaledValue );
886  break;
887  case E57_UINT32:
888  if ( scaledValue < E57_UINT32_MIN || E57_UINT32_MAX < scaledValue )
889  {
891  "pathName=" + pathName_ + " scaledValue=" + toString( scaledValue ) );
892  }
893  *reinterpret_cast<uint32_t *>( p ) = static_cast<uint32_t>( scaledValue );
894  break;
895  case E57_INT64:
896  *reinterpret_cast<int64_t *>( p ) = static_cast<int64_t>( scaledValue );
897  break;
898  case E57_BOOL:
899  *reinterpret_cast<bool *>( p ) = ( scaledValue ? false : true );
900  break;
901  case E57_REAL32:
902  if ( !doConversion_ )
903  {
904  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
905  }
908  if ( scaledValue < E57_DOUBLE_MIN || E57_DOUBLE_MAX < scaledValue )
909  {
911  "pathName=" + pathName_ + " scaledValue=" + toString( scaledValue ) );
912  }
913  *reinterpret_cast<float *>( p ) = static_cast<float>( scaledValue );
914  break;
915  case E57_REAL64:
916  if ( !doConversion_ )
917  {
918  throw E57_EXCEPTION2( E57_ERROR_CONVERSION_REQUIRED, "pathName=" + pathName_ );
919  }
920  *reinterpret_cast<double *>( p ) = scaledValue;
921  break;
922  case E57_USTRING:
923  throw E57_EXCEPTION2( E57_ERROR_EXPECTING_NUMERIC, "pathName=" + pathName_ );
924  }
925 
926  nextIndex_++;
927 }
928 
930 {
931  _setNextReal( value );
932 }
933 
935 {
936  _setNextReal( value );
937 }
938 
940 {
942 
943  if ( memoryRepresentation_ != E57_USTRING )
944  {
945  throw E57_EXCEPTION2( E57_ERROR_EXPECTING_USTRING, "pathName=" + pathName_ );
946  }
947 
949  if ( nextIndex_ >= capacity_ )
950  {
951  throw E57_EXCEPTION2( E57_ERROR_INTERNAL, "pathName=" + pathName_ );
952  }
953 
955  ( *ustrings_ )[nextIndex_] = value;
956  nextIndex_++;
957 }
958 
959 void SourceDestBufferImpl::checkCompatible( const std::shared_ptr<SourceDestBufferImpl> &newBuf ) const
960 {
961  if ( pathName_ != newBuf->pathName() )
962  {
964  "pathName=" + pathName_ + " newPathName=" + newBuf->pathName() );
965  }
966  if ( memoryRepresentation_ != newBuf->memoryRepresentation() )
967  {
969  "memoryRepresentation=" + toString( memoryRepresentation_ ) +
970  " newMemoryType=" + toString( newBuf->memoryRepresentation() ) );
971  }
972  if ( capacity_ != newBuf->capacity() )
973  {
975  "capacity=" + toString( capacity_ ) + " newCapacity=" + toString( newBuf->capacity() ) );
976  }
977  if ( doConversion_ != newBuf->doConversion() )
978  {
980  "doConversion=" + toString( doConversion_ ) +
981  "newDoConversion=" + toString( newBuf->doConversion() ) );
982  }
983  if ( doConversion_ != newBuf->doConversion() )
984  {
986  "doConversion=" + toString( doConversion_ ) +
987  " newDoConversion=" + toString( newBuf->doConversion() ) );
988  }
989  if ( stride_ != newBuf->stride() )
990  {
992  "stride=" + toString( stride_ ) + " newStride=" + toString( newBuf->stride() ) );
993  }
994 }
995 
996 #ifdef E57_DEBUG
997 void SourceDestBufferImpl::dump( int indent, std::ostream &os )
998 {
1000 
1001  os << space( indent ) << "pathName: " << pathName_ << std::endl;
1002  os << space( indent ) << "memoryRepresentation: ";
1003  switch ( memoryRepresentation_ )
1004  {
1005  case E57_INT8:
1006  os << "int8_t" << std::endl;
1007  break;
1008  case E57_UINT8:
1009  os << "uint8_t" << std::endl;
1010  break;
1011  case E57_INT16:
1012  os << "int16_t" << std::endl;
1013  break;
1014  case E57_UINT16:
1015  os << "uint16_t" << std::endl;
1016  break;
1017  case E57_INT32:
1018  os << "int32_t" << std::endl;
1019  break;
1020  case E57_UINT32:
1021  os << "uint32_t" << std::endl;
1022  break;
1023  case E57_INT64:
1024  os << "int64_t" << std::endl;
1025  break;
1026  case E57_BOOL:
1027  os << "bool" << std::endl;
1028  break;
1029  case E57_REAL32:
1030  os << "float" << std::endl;
1031  break;
1032  case E57_REAL64:
1033  os << "double" << std::endl;
1034  break;
1035  case E57_USTRING:
1036  os << "ustring" << std::endl;
1037  break;
1038  default:
1039  os << "<unknown>" << std::endl;
1040  break;
1041  }
1042  os << space( indent ) << "base: " << static_cast<const void *>( base_ ) << std::endl;
1043  os << space( indent ) << "ustrings: " << static_cast<const void *>( ustrings_ ) << std::endl;
1044  os << space( indent ) << "capacity: " << capacity_ << std::endl;
1045  os << space( indent ) << "doConversion: " << doConversion_ << std::endl;
1046  os << space( indent ) << "doScaling: " << doScaling_ << std::endl;
1047  os << space( indent ) << "stride: " << stride_ << std::endl;
1048  os << space( indent ) << "nextIndex: " << nextIndex_ << std::endl;
1049 }
1050 #endif
int offset
#define E57_EXCEPTION2(ecode, context)
Definition: Common.h:68
size_t stride
void setNextString(const ustring &value)
void setTypeInfo(T *base, size_t stride=sizeof(T))
void dump(int indent=0, std::ostream &os=std::cout)
SourceDestBufferImpl(ImageFileImplWeakPtr destImageFile, const ustring &pathName, const size_t capacity, bool doConversion=false, bool doScaling=false)
void checkCompatible(const std::shared_ptr< SourceDestBufferImpl > &newBuf) const
ImageFileImplWeakPtr destImageFile() const
QTextStream & endl(QTextStream &stream)
Definition: QtCompat.h:718
MiniVec< float, N > floor(const MiniVec< float, N > &a)
Definition: MiniVec.h:75
std::weak_ptr< class ImageFileImpl > ImageFileImplWeakPtr
Definition: Common.h:189
std::shared_ptr< class ImageFileImpl > ImageFileImplSharedPtr
Definition: Common.h:188
@ E57_ERROR_BUFFERS_NOT_COMPATIBLE
SourceDestBuffers not compatible with previously given ones.
Definition: E57Exception.h:92
@ E57_ERROR_CONVERSION_REQUIRED
conversion required to assign element value, but not requested
Definition: E57Exception.h:82
@ E57_ERROR_INTERNAL
An unrecoverable inconsistent internal state was detected.
Definition: E57Exception.h:56
@ E57_ERROR_REAL64_TOO_LARGE
a 64 bit IEEE float was too large to store in a 32 bit IEEE float
Definition: E57Exception.h:53
@ E57_ERROR_IMAGEFILE_NOT_OPEN
destImageFile is no longer open
Definition: E57Exception.h:91
@ E57_ERROR_EXPECTING_NUMERIC
Expecting numeric representation in user's buffer, found ustring.
Definition: E57Exception.h:54
@ E57_ERROR_VALUE_NOT_REPRESENTABLE
a value could not be represented in the requested type
Definition: E57Exception.h:50
@ E57_ERROR_SCALED_VALUE_NOT_REPRESENTABLE
Definition: E57Exception.h:51
@ E57_ERROR_BAD_BUFFER
bad SourceDestBuffer
Definition: E57Exception.h:68
@ E57_ERROR_EXPECTING_USTRING
Expecting string representation in user's buffer, found numeric.
Definition: E57Exception.h:55
std::string ustring
UTF-8 encodeded Unicode string.
Definition: E57Format.h:54
@ E57_USTRING
Unicode UTF-8 std::string.
Definition: E57Format.h:90
@ E57_UINT32
32 bit unsigned integer
Definition: E57Format.h:85
@ E57_INT32
32 bit signed integer
Definition: E57Format.h:84
@ E57_UINT8
8 bit unsigned integer
Definition: E57Format.h:81
@ E57_INT64
64 bit signed integer
Definition: E57Format.h:86
@ E57_INT8
8 bit signed integer
Definition: E57Format.h:80
@ E57_REAL32
C++ float type.
Definition: E57Format.h:88
@ E57_UINT16
16 bit unsigned integer
Definition: E57Format.h:83
@ E57_BOOL
C++ boolean type.
Definition: E57Format.h:87
@ E57_INT16
16 bit signed integer
Definition: E57Format.h:82
@ E57_REAL64
C++ double type.
Definition: E57Format.h:89
std::string toString(T x)
Definition: Common.h:80
std::string space(size_t n)
Definition: Common.h:73