Purpose: Fetches a single row of data into the supplied object.

Return TypeFunction nameArguments
hzEcodehdbBinRepos::Fetch(hzChain&,uint32_t,)

Declared in file: hzDatabase.h
Defined in file : hdbBinRepos.cpp

Function Logic:

0:START 1:items 2:unknown 3:Return E_NOINIT 4:unknown 5:Return E_NOTOPEN 6:unknown 7:Return hzerr(E_RANGE,NULL datum id) 8:unknown 9:items rc 10:items datumId nAddr items nPosn 11:unknown 12:rc items 13:items items 14:unknown 15:rc items items 16:items 17:unknown 18:Return rc 19:workBuf items items items nPosn 20:unknown 21:rc items 22:hdr 23:HZ_BLOCKSIZE 24:toGet 25:unknown 26:toGet 27:soFar items 28:unknown 29:items 30:items soFar 31:unknown 32:hdr 33:toGet 34:unknown 35:toGet 36:items 37:unknown 38:items 39:items soFar 40:unknown 41:rc items items 42:items 43:items []workBuf 44:Return rc

Function body:

hzEcode hdbBinRepos::Fetch (hzChain& datum)uint32_t datumId, 
{
   //  Purpose: Fetches a single row of data into the supplied object.
   //  
   //  Arguments: 1) obj  The object to be populated
   //     2) datumId The object id
   //  
   //  Returns: E_NOTOPEN If the reader stream is not open for reading
   //     E_READFAIL The reader stream is already in a fialed state
   //     E_CORRUPT Row metadata not as expected. Possible overwrites
   //     E_FORMAT Data format error
   //     E_OK  The operation was successful
   _hzfunc("hdbBinRepos::Fetch") ;
   _datum_hd   hdr ;           //  Datum header
   char*       workBuf ;       //  Working buffer
   uint64_t    nAddr ;         //  Addr of object in file
   uint64_t    nPosn ;         //  Posn of m_Reader
   uint32_t    toGet ;         //  Bytes to get in the next read operation
   uint32_t    soFar ;         //  Bytes read so far
   hzEcode     rc = E_OK ;     //  Return code
   //  if (datum.Copies() > 1)
   //  threadLog("Copies of chain %u\n", datum.Copies()) ;
   datum.Clear() ;
   //  Repos not initialized?
   if (m_nInitState < 1)
       return E_NOINIT ;
   //  Repos not open?
   if (m_nInitState < 2)
       return E_NOTOPEN ;
   //  Zero datum id?
   if (!datumId)
       return hzerr(E_RANGE, "NULL datum id") ;
   //  Datum id out of range
   if (datumId > m_nSeqId)
   {
       threadLog("Out of range\n") ;
       rc = E_RANGE ;
   }
   //  Read in requested object
   m_LockIrd.Lock() ;
       //  Get datum header
       nAddr = (datumId-1)* sizeof(_datum_hd) ;
       m_RdI.seekg((streamoff) nAddr) ;
       nPosn = m_RdI.tellg() ;
       if (nPosn != nAddr)
       {
           rc = E_READFAIL ;
           threadLog("Could not seek header address %u for datum %u\n", nAddr, datumId) ;
       }
       else
       {
           threadLog("Found header address %u for datum %u\n", nAddr, datumId) ;
           m_RdI.read((char*) &hdr, sizeof(_datum_hd)) ;
           if (m_RdI.fail())
           {
               rc = E_READFAIL ;
               threadLog("Could not read header for datum %u", datumId) ;
               m_RdI.clear() ;
           }
       }
   m_LockIrd.Unlock() ;
   if (rc != E_OK)
       return rc ;
   workBuf = new char[HZ_BLOCKSIZE] ;
   m_LockDrd.Lock() ;
       //  Get datum
       threadLog("Found datum for datum %u addr %u, size %u\n", datumId, hdr.m_Addr, hdr.m_Size) ;
       m_RdD.seekg((streamoff) hdr.m_Addr) ;
       nPosn = m_RdD.tellg() ;
       if (nPosn != hdr.m_Addr)
       {
           rc = E_READFAIL ;
           threadLog("Could not seek data address %ul for datum %d\n", hdr.m_Addr, datumId) ;
       }
       else
       {
           //  threadLog("case A hdr size %u\n", hdr.m_Size) ;
           toGet = HZ_BLOCKSIZE - (hdr.m_Addr % HZ_BLOCKSIZE) ;
           if (toGet > hdr.m_Size)
               toGet = hdr.m_Size ;
           soFar = 0;
           //  threadLog("case B toget %u\n", toGet) ;
           m_RdD.read(workBuf, toGet) ;
           if (m_RdD.gcount() != toGet)
               threadLog("Warning: toget %u, got %u\n", toGet, m_RdD.gcount()) ;
           datum.Append(workBuf, toGet) ;
           soFar += toGet ;
           for (; soFar < hdr.m_Size ;)
           {
               toGet = hdr.m_Size - soFar ;
               if (toGet > HZ_BLOCKSIZE)
                   toGet = HZ_BLOCKSIZE ;
               //  threadLog("case C sofar %u toget %u\n", soFar, toGet) ;
               m_RdD.read(workBuf, toGet) ;
               if (m_RdD.gcount() != toGet)
                   threadLog("Warning: toget %u, got %u\n", toGet, m_RdD.gcount()) ;
               datum.Append(workBuf, toGet) ;
               soFar += toGet ;
           }
           //  threadLog("case 5\n") ;
           if (m_RdD.fail())
           {
               rc = E_READFAIL ;
               threadLog("m_RdD failed\n") ;
               m_RdD.clear() ;
           }
           threadLog("Now have %u bytes in Datum\n", datum.Size()) ;
       }
   m_LockDrd.Unlock() ;
   delete [] workBuf ;
   return rc ;
}