# PatchFile.cxx

This is a C++ example on how to use gdcm::Attribute

    /*=========================================================================

      Program: GDCM (Grassroots DICOM). A DICOM library
      Module:  $URL$

      Copyright (c) 2006-2009 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.

    =========================================================================*/
    /*
     * The image was a broken file where the Pixel Data element was 8 times too big
     * Apparently multiplying the BitsAllocated to 4 and multiplying the number of
     * frames by 2 would solve the problem
     *
     * This C++ code can be used to patch the header.
     */

    #include "gdcmReader.h"
    #include "gdcmImageReader.h"
    #include "gdcmWriter.h"
    #include "gdcmDataSet.h"
    #include "gdcmAttribute.h"

    int main(int argc, char *argv[])
    {
      if( argc < 3 )
        {
        return 1;
        }
      const char *f = argv[1];
      const char *out = argv[2];
      gdcm::Reader r;
      r.SetFileName( f );
      if( !r.Read() )
        {
        return 1;
        }

      gdcm::File &file = r.GetFile();
      gdcm::DataSet& ds = file.GetDataSet();
      // (0028,0100) US 16                                       #   2, 1 BitsAllocated
      // (0028,0101) US 16                                       #   2, 1 BitsStored
      // (0028,0102) US 15                                       #   2, 1 HighBit
      //
        {
        gdcm::Attribute<0x28,0x100> at;
        at.SetFromDataElement( ds.GetDataElement( at.GetTag() ) );
        if( at.GetValue() != 8 )
          {
          return 1;
          }
        at.SetValue( 32 );
        ds.Replace( at.GetAsDataElement() );
        }
        {
        gdcm::Attribute<0x28,0x101> at;
        at.SetFromDataElement( ds.GetDataElement( at.GetTag() ) );
        if( at.GetValue() != 8 )
          {
          return 1;
          }
        at.SetValue( 32 );
        ds.Replace( at.GetAsDataElement() );
        }
        {
        gdcm::Attribute<0x28,0x102> at;
        at.SetFromDataElement( ds.GetDataElement( at.GetTag() ) );
        if( at.GetValue() != 7 )
          {
          return 1;
          }
        at.SetValue( 31 );
        ds.Replace( at.GetAsDataElement() );
        }
      // (0028,0008) IS [56]                                     #   2, 1 NumberOfFrames

        {
        gdcm::Attribute<0x28,0x8> at;
        at.SetFromDataElement( ds.GetDataElement( at.GetTag() ) );
        at.SetValue( at.GetValue() * 2 );
        ds.Replace( at.GetAsDataElement() );
        }

      gdcm::Writer w;
      w.SetFile( file );
      w.SetCheckFileMetaInformation( false );
      w.SetFileName( out );
      if( !w.Write() )
        {
        return 1;
        }

      // Now let's see if we can read it as an image:
      gdcm::ImageReader ir;
      ir.SetFileName( out );
      if(!ir.Read())
        {
        return 1;
        }
      gdcm::Image &image = ir.GetImage();
      unsigned long len = image.GetBufferLength();
      const gdcm::ByteValue *bv = ir.GetFile().GetDataSet().GetDataElement( gdcm::Tag(0x7fe0,0x0010) ).GetByteValue();
      if( !bv || len != bv->GetLength() )
        {
        return 1;
        }
      std::cout << bv->GetLength() << " " << len << std::endl;

      std::cout << "Sucess to rewrite image !" << std::endl;
      image.Print( std::cout );
      return 0;
    }