]> Creatis software - gdcm.git/blobdiff - src/gdcmDocument.cxx
dealing with 'zero length' integers
[gdcm.git] / src / gdcmDocument.cxx
index 7ab750eca46dfc0d5d2b30e5a4bc5def20170afa..cdcdd9cb1b69e1b335a8fd568573075c8f76e8d2 100644 (file)
@@ -3,8 +3,8 @@
   Program:   gdcm
   Module:    $RCSfile: gdcmDocument.cxx,v $
   Language:  C++
-  Date:      $Date: 2004/09/03 15:11:35 $
-  Version:   $Revision: 1.70 $
+  Date:      $Date: 2004/09/13 07:49:36 $
+  Version:   $Revision: 1.75 $
                                                                                 
   Copyright (c) CREATIS (Centre de Recherche et d'Applications en Traitement de
   l'Image). All rights reserved. See Doc/License.txt or
@@ -588,8 +588,8 @@ gdcmValEntry * gdcmDocument::ReplaceOrCreateByNumber(
                                          uint16_t elem )
 {
    gdcmValEntry* valEntry = 0;
-
    gdcmDocEntry* currentEntry = GetDocEntryByNumber( group, elem);
+   
    if (!currentEntry)
    {
       // The entry wasn't present and we simply create the required ValEntry:
@@ -610,7 +610,9 @@ gdcmValEntry * gdcmDocument::ReplaceOrCreateByNumber(
    else
    {
       valEntry = dynamic_cast< gdcmValEntry* >(currentEntry);
-      if ( !valEntry )
+      if ( !valEntry ) // Euuuuh? It wasn't a ValEntry
+                       // then we change it to a ValEntry ?
+                       // Shouldn't it be considered as an error ?
       {
          // We need to promote the gdcmDocEntry to a gdcmValEntry:
          valEntry = new gdcmValEntry(currentEntry);
@@ -662,7 +664,8 @@ gdcmBinEntry * gdcmDocument::ReplaceOrCreateByNumber(
       b = new gdcmBinEntry(a);
       AddEntry(b);
       b->SetVoidArea(voidArea);
-   }   
+   } 
+
    SetEntryByNumber(voidArea, lgth, group, elem);
    //b->SetVoidArea(voidArea);  //what if b == 0 !!
 
@@ -868,6 +871,9 @@ bool gdcmDocument::SetEntryByNumber(std::string const & content,
                                     uint16_t group,
                                     uint16_t element) 
 {
+   int c;
+   int l;
+
    gdcmValEntry* valEntry = GetValEntryByNumber(group, element);
    if (!valEntry )
    {
@@ -876,28 +882,31 @@ bool gdcmDocument::SetEntryByNumber(std::string const & content,
       return false;
    }
    // Non even content must be padded with a space (020H)...
-   std::string evenContent = content;
-   if( evenContent.length() % 2 )
+   std::string finalContent = content;
+   if( finalContent.length() % 2 )
    {
-      evenContent += '\0';  // ... therefore we padd with (000H) .!?!
+      finalContent += '\0';  // ... therefore we padd with (000H) .!?!
    }      
-   valEntry->SetValue(evenContent);
+   valEntry->SetValue(finalContent);
    
    // Integers have a special treatement for their length:
-   gdcmVRKey vr = valEntry->GetVR();
-   if( vr == "US" || vr == "SS" )
-   {
-      valEntry->SetLength(2);
-   }
-   else if( vr == "UL" || vr == "SL" )
-   {
-      valEntry->SetLength(4);
-   }
-   else
-   {
-      valEntry->SetLength(evenContent.length());
-   }
 
+   l = finalContent.length();
+   if ( l != 0) // To avoid to be cheated by 'zero length' integers
+   {   
+      gdcmVRKey vr = valEntry->GetVR();
+      if( vr == "US" || vr == "SS" )
+      {
+         c = CountSubstring(content, "\\") + 1; // for multivaluated items
+         l = c*2;
+      }
+      else if( vr == "UL" || vr == "SL" )
+      {
+         c = CountSubstring(content, "\\") + 1; // for multivaluated items
+         l = c*4;;
+      }
+   }
+   valEntry->SetLength(l);
    return true;
 } 
 
@@ -931,7 +940,7 @@ bool gdcmDocument::SetEntryByNumber(void *content,
 */      
    gdcmBinEntry* a = (gdcmBinEntry *)TagHT[key];           
    a->SetVoidArea(content);  
-   //a->SetLength(lgth);  // ???  
+   a->SetLength(lgth);
 
    return true;
 } 
@@ -1030,7 +1039,7 @@ void *gdcmDocument::LoadEntryVoidArea(uint16_t group, uint16_t elem)
       delete[] a;
       return NULL;
    }
-   /// \todo Drop any already existing void area! JPR
+   /// \TODO Drop any already existing void area! JPR
    SetEntryVoidAreaByNumber(a, group, elem);
 
    return a;
@@ -1502,44 +1511,42 @@ void gdcmDocument::LoadDocEntry(gdcmDocEntry* entry)
    if (length > MaxSizeLoadEntry)
    {
       if (gdcmBinEntry* binEntryPtr = dynamic_cast< gdcmBinEntry* >(entry) )
-      {         
-         s << "gdcm::NotLoaded (BinEntry)";
+      {  
+         //s << "gdcm::NotLoaded (BinEntry)";
+         s << GDCM_NOTLOADED;
          s << " Address:" << (long)entry->GetOffset();
          s << " Length:"  << entry->GetLength();
          s << " x(" << std::hex << entry->GetLength() << ")";
          binEntryPtr->SetValue(s.str());
       }
-      // to be sure we are at the end of the value ...
-      fseek(Fp, (long)entry->GetOffset()+(long)entry->GetLength(), SEEK_SET);      
-      // Following return introduced by JPR on version 1.25. Since the 
-      // treatement of a ValEntry is never executed (doh!) this means
-      // we were lucky up to now because we NEVER encountered a ValEntry
-      // whose length was bigger thant MaxSizeLoadEntry !? I can't believe
-      // this could ever work...
-      return;  //FIXME FIXME FIXME FIXME JPR ????
-
        // Be carefull : a BinEntry IS_A ValEntry ... 
-      if (gdcmValEntry* valEntryPtr = dynamic_cast< gdcmValEntry* >(entry) )
+      else if (gdcmValEntry* valEntryPtr = dynamic_cast< gdcmValEntry* >(entry) )
       {
-         s << "gdcm::NotLoaded. (ValEntry)";
+        // s << "gdcm::NotLoaded. (ValEntry)";
+         s << GDCM_NOTLOADED;  
          s << " Address:" << (long)entry->GetOffset();
          s << " Length:"  << entry->GetLength();
          s << " x(" << std::hex << entry->GetLength() << ")";
          valEntryPtr->SetValue(s.str());
       }
+      else
+      {
+         // fusible
+         std::cout<< "MaxSizeLoadEntry exceeded, neither a BinEntry "
+                  << "nor a ValEntry ?! Should never print that !" << std::endl;
+      }
+
       // to be sure we are at the end of the value ...
       fseek(Fp,(long)entry->GetOffset()+(long)entry->GetLength(),SEEK_SET);      
-
       return;
    }
 
    // When we find a BinEntry not very much can be done :
    if (gdcmBinEntry* binEntryPtr = dynamic_cast< gdcmBinEntry* >(entry) )
    {
-
-      LoadEntryVoidArea(binEntryPtr);
       s << "gdcm::Loaded (BinEntry)";
       binEntryPtr->SetValue(s.str());
+      LoadEntryVoidArea(binEntryPtr); // last one, not to erase length !
       return;
    }
     
@@ -1608,7 +1615,7 @@ void gdcmDocument::LoadDocEntry(gdcmDocEntry* entry)
       {
          dbg.Verbose(1, "gdcmDocument::LoadDocEntry",
                         "unread element value");
-         valEntry->SetValue("gdcm::UnRead");
+         valEntry->SetValue(GDCM_UNREAD);
          return;
       }