This file is indexed.

/usr/include/gdcm-2.6/gdcmDataElement.h is in libgdcm2-dev 2.6.6-3.

This file is owned by root:root, with mode 0o644.

The actual contents of the file can be viewed below.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
/*=========================================================================

  Program: GDCM (Grassroots DICOM). A DICOM library

  Copyright (c) 2006-2011 Mathieu Malaterre
  All rights reserved.
  See Copyright.txt or http://gdcm.sourceforge.net/Copyright.html for details.

     This software is distributed WITHOUT ANY WARRANTY; without even
     the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
     PURPOSE.  See the above copyright notice for more information.

=========================================================================*/
#ifndef GDCMDATAELEMENT_H
#define GDCMDATAELEMENT_H

#include "gdcmTag.h"
#include "gdcmVL.h"
#include "gdcmVR.h"
#include "gdcmByteValue.h"
#include "gdcmSmartPointer.h"

#include <set>

namespace gdcm_ns
{
// Data Element
// Contains multiple fields:
// -> Tag
// -> Optional VR (Explicit Transfer Syntax)
// -> ValueLength
// -> Value
// TODO: This class SHOULD be pure virtual. I don't want a user
// to shoot himself in the foot.

class SequenceOfItems;
class SequenceOfFragments;
/**
 * \brief Class to represent a Data Element
 * either Implicit or Explicit
 *
 * \details
 * DATA ELEMENT:
 * A unit of information as defined by a single entry in the data dictionary.
 * An encoded Information Object Definition (IOD) Attribute that is composed
 * of, at a minimum, three fields: a Data Element Tag, a Value Length, and a
 * Value Field. For some specific Transfer Syntaxes, a Data Element also
 * contains a VR Field where the Value Representation of that Data Element is
 * specified explicitly.
 *
 * Design:
 * \li A DataElement in GDCM always store VL (Value Length) on a 32 bits integer even when VL is 16 bits
 * \li A DataElement always store the VR even for Implicit TS, in which case VR is defaulted to VR::INVALID
 * \li For Item start/end (See 0xfffe tags), Value is NULL
 *
 * \see ExplicitDataElement ImplicitDataElement
 */
class GDCM_EXPORT DataElement
{
public:
  DataElement(const Tag& t = Tag(0), const VL& vl = 0, const VR &vr = VR::INVALID):TagField(t),ValueLengthField(vl),VRField(vr),ValueField(0) {}
  //DataElement( Attribute const &att );

  friend std::ostream& operator<<(std::ostream &_os, const DataElement &_val);

  /// Get Tag
  const Tag& GetTag() const { return TagField; }
  Tag& GetTag() { return TagField; }
  /// Set Tag
  /// Use with cautious (need to match Part 6)
  void SetTag(const Tag &t) { TagField = t; }

  /// Get VL
  const VL& GetVL() const { return ValueLengthField; }
  VL& GetVL() { return ValueLengthField; }
  /// Set VL
  /// Use with cautious (need to match Part 6), advanced user only
  /// \see SetByteValue
  void SetVL(const VL &vl) { ValueLengthField = vl; }
  void SetVLToUndefined();

  /// Get VR
  /// do not set VR::SQ on bytevalue data element
  VR const &GetVR() const { return VRField; }
  /// Set VR
  /// Use with cautious (need to match Part 6), advanced user only
  /// \pre vr is a VR::VRALL (not a dual one such as OB_OW)
  void SetVR(VR const &vr) {
    if( vr.IsVRFile() )
      VRField = vr;
  }

  /// Set/Get Value (bytes array, SQ of items, SQ of fragments):
  Value const &GetValue() const { gdcmAssertAlwaysMacro(ValueField); return *ValueField; }
  Value &GetValue() { return *ValueField; }
  /// \warning you need to set the ValueLengthField explicitly
  void SetValue(Value const & vl) {
    //assert( ValueField == 0 );
    ValueField = vl;
    ValueLengthField = vl.GetLength();
  }
  /// Check if Data Element is empty
  bool IsEmpty() const { return ValueField == 0 || (GetByteValue() && GetByteValue()->IsEmpty()); }

  /// Make Data Element empty (no Value)
  void Empty() { ValueField = 0; ValueLengthField = 0; }

  /// Clear Data Element (make Value empty and invalidate Tag & VR)
  void Clear()
    {
    TagField = 0;
    VRField = VR::INVALID;
    ValueField = 0;
    ValueLengthField = 0;
    }

  // Helper:
  /// Set the byte value
  /// \warning user need to read DICOM standard for an understanding of:
  /// * even padding
  /// * \0 vs space padding
  /// By default even padding is achieved using \0 regardless of the of VR
  void SetByteValue(const char *array, VL length)
    {
    ByteValue *bv = new ByteValue(array,length);
    SetValue( *bv );
    }
  /// Return the Value of DataElement as a ByteValue (if possible)
  /// \warning: You need to check for NULL return value
  const ByteValue* GetByteValue() const {
    // Get the raw pointer from the gdcm::SmartPointer
    const ByteValue *bv = dynamic_cast<const ByteValue*>(ValueField.GetPointer());
    return bv; // Will return NULL if not ByteValue
  }

  /// Interpret the Value stored in the DataElement. This is more robust (but also more
  /// expensive) to call this function rather than the simpliest form: GetSequenceOfItems()
  /// It also return NULL when the Value is NOT of type SequenceOfItems
  /// \warning in case GetSequenceOfItems() succeed the function return this value, otherwise
  /// it creates a new SequenceOfItems, you should handle that in your case, for instance:
  /// SmartPointer<SequenceOfItems> sqi = de.GetValueAsSQ();
  SmartPointer<SequenceOfItems> GetValueAsSQ() const;

  /// Return the Value of DataElement as a Sequence Of Fragments (if possible)
  /// \warning: You need to check for NULL return value
  const SequenceOfFragments* GetSequenceOfFragments() const;
  SequenceOfFragments* GetSequenceOfFragments();

  /// return if Value Length if of undefined length
  bool IsUndefinedLength() const {
    return ValueLengthField.IsUndefined();
  }

  DataElement(const DataElement &_val)
    {
    if( this != &_val)
      {
      *this = _val;
      }
    }

  bool operator<(const DataElement &de) const
    {
    return GetTag() < de.GetTag();
    }
  DataElement &operator=(const DataElement &de)
    {
    TagField = de.TagField;
    ValueLengthField = de.ValueLengthField;
    VRField = de.VRField;
    ValueField = de.ValueField; // Pointer copy
    return *this;
    }

  bool operator==(const DataElement &de) const
    {
    bool b = TagField == de.TagField
      && ValueLengthField == de.ValueLengthField
      && VRField == de.VRField;
    if( !ValueField && !de.ValueField )
      {
      return b;
      }
    if( ValueField && de.ValueField )
      {
      return b && (*ValueField == *de.ValueField);
      }
    // ValueField != de.ValueField
    return false;
    }

  // The following fonctionalities are dependant on:
  // # The Transfer Syntax: Explicit or Implicit
  // # The Byte encoding: Little Endian / Big Endian

  /*
   * The following was inspired by a C++ idiom: Curiously Recurring Template Pattern
   * Ref: http://en.wikipedia.org/wiki/Curiously_Recurring_Template_Pattern
   * The typename TDE is typically a derived class *without* any data
   * while TSwap is a simple template parameter to achieve byteswapping (and allow factorization of
   * highly identical code)
   */
  template <typename TDE>
  VL GetLength() const {
    return static_cast<const TDE*>(this)->GetLength();
  }

  template <typename TDE, typename TSwap>
  std::istream &Read(std::istream &is) {
    return static_cast<TDE*>(this)->template Read<TSwap>(is);
  }

  template <typename TDE, typename TSwap>
  std::istream &ReadOrSkip(std::istream &is, std::set<Tag> const &skiptags) {
    (void)skiptags;
    return static_cast<TDE*>(this)->template Read<TSwap>(is);
  }

  template <typename TDE, typename TSwap>
  std::istream &ReadPreValue(std::istream &is, std::set<Tag> const &skiptags) {
    (void)skiptags;
    return static_cast<TDE*>(this)->template ReadPreValue<TSwap>(is);
  }
  template <typename TDE, typename TSwap>
  std::istream &ReadValue(std::istream &is, std::set<Tag> const &skiptags) {
    (void)skiptags;
    return static_cast<TDE*>(this)->template ReadValue<TSwap>(is);
  }
  template <typename TDE, typename TSwap>
  std::istream &ReadValueWithLength(std::istream &is, VL & length, std::set<Tag> const &skiptags) {
    (void)skiptags;
    return static_cast<TDE*>(this)->template ReadValueWithLength<TSwap>(is, length);
  }

  template <typename TDE, typename TSwap>
  std::istream &ReadWithLength(std::istream &is, VL &length) {
    return static_cast<TDE*>(this)->template ReadWithLength<TSwap>(is,length);
  }

  template <typename TDE, typename TSwap>
  const std::ostream &Write(std::ostream &os) const {
    return static_cast<const TDE*>(this)->template Write<TSwap>(os);
  }

protected:
  Tag TagField;
  // This is the value read from the file, might be different from the length of Value Field
  VL ValueLengthField; // Can be 0xFFFFFFFF

  // Value Representation
  VR VRField;
  typedef SmartPointer<Value> ValuePtr;
  ValuePtr ValueField;

  void SetValueFieldLength( VL vl, bool readvalues );
};
//-----------------------------------------------------------------------------
inline std::ostream& operator<<(std::ostream &os, const DataElement &val)
{
  os << val.TagField;
  os << "\t" << val.VRField;
  os << "\t" << val.ValueLengthField;
  if( val.ValueField )
    {
    val.ValueField->Print( os << "\t" );
    }
  return os;
}

inline bool operator!=(const DataElement& lhs, const DataElement& rhs)
{
  return ! ( lhs == rhs );
}

} // end namespace gdcm_ns

#endif //GDCMDATAELEMENT_H