Announcement

Collapse

Forum Guidelines

This forum is for finished source code that is working properly. If you have questions about this or any other source code, please post it in one of the Discussion Forums, not here.
See more
See less

Using Memory Mapped Files in place of RANDOM access

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • Using Memory Mapped Files in place of RANDOM access

    Code:
    ' file : mmfdemo.bas
    ' may 8 2004
    ' placed in public domain by author, michael mattias racine wi
    ' compiler     :  pb/windows 7.02
    ' win32api.inc :  5/9/02
    ' shows: use of memory mapped file and absolute array to replace fixed-record-length
    '        files using random access, using some 'wrapper' functions to make access simpler
    '        from within pb code.
    ' note this 'array' method only works with fixed-record-length files
    ' ---------------------------------------------------------------------------
    ' want more on mmfs?
    ' http://www.powerbasic.com/support/pb...ad.php?t=22585  (fred oxenby)
    ' http://www.powerbasic.com/support/pb...ad.php?t=23001  (this author)
    ' ---------------------------------------------------------------------------
    
    #include "win32api.inc"
    #if not %def (%invalid_handle_value_long)
      %invalid_handle_value_long = -1&
    #endif
    
    ' memory map a file for input only
    ' returns: true = pifdata, false=error
    function mapthisfile (szfilein as asciiz, hsys as long, hfilemapping as long, cbmapping as long) as dword
     ' note we need the values of hsys, hfilemapping and pifdata to unmap the file
     
      local w32 as win32_find_data, hsearch as long
      local pifdata as dword
      
      ' check that we can find the file, and get its size if we can
      hsearch      = findfirstfile (szfilein, w32)
      if hsearch <> %invalid_handle_value_long then
          cbmapping    =  w32.nfilesizelow
          closehandle     hsearch
      else
          function = 0
          exit function
      end if
     
      ' open the file for reading and get system handle. we could open with pb open and then open handle but
      ' that would just complicate this
      hsys          = createfile (szfilein, %generic_read, %file_share_read, byval %null, %open_existing, %file_attribute_normal, byval %null)
      if istrue hsys  then
         hfilemapping     = createfilemapping (hsys, byval %null, %page_readonly, byval %null, byval %null, byval %null)
         if istrue hfilemapping then
             ' map the file to our memory space and get pointer to data...
             pifdata    = mapviewoffile (hfilemapping, %file_map_read, byval %null, byval %null, byval %null)
             function   = pifdata
         else
             function    = 0
             closehandle hsys
             exit function
         end if
      else
          function = 0
          exit function
      end if
    
    end function
    
    function unmapmappedfile (pifdata as dword, hsys as long, hfilemapping as long) as long
        unmapviewoffile pifdata
        closehandle     hfilemapping
        closehandle     hsys
    end function
    
    %record_length  = 80
    
    function pbmain() as long
    
     local pifdata as dword, hsys as long, hfilemapping as long, cbmapping as long, szfile as asciiz * %max_path
     local nrec    as long, reclen as long
     local a()     as string * %record_length   ' will be our "random access file"
     
     
     ' for demo, build a test file.
     szfile    =     "mmftestfile.dat"
     nrec      =     10000
     reclen    =     %record_length
     call            createtestfile (szfile, nrec, reclen)
     
     ' map the file and get pointer to start of data
     pifdata   =      mapthisfile (szfile, hsys, hfilemapping, cbmapping)
     
     ' overlay an array
     redim            a (nrec -1) at pifdata
     ' prove success
     call             checkafewentries (a())
    
    ' clean up
     unmapmappedfile  pifdata, hsys, hfilemapping
    
     msgbox "end of demo",%mb_iconinformation or %mb_applmodal, "memory-mapped file demo"
    
    end function
    
    function createtestfile (szfile as asciiz, nrec as long, reclen as long) as long
    
        local hfile as long, w as string, i as long
    
        hfile = freefile
        open    szfile for random as hfile len=reclen
        for i  = 1 to nrec
            w  =   lset$ (using$("this is record number ###,###", i), reclen)
            put #hfile, i, abs w
        next
        close hfile
    end function
    
    function checkafewentries (a() as string * %record_length) as long
    
        local recno as long, w as string, msg as string
    
        do
             w = inputbox$("record number or <cancel> to quit ", "memory-mapped file demo")
             if w = " then
                 exit do
             else
                w = trim$(w)
                recno = val(w) - 1    ' minus one to account for zero-based array versus 1-based file
                if recno < lbound(a,1) or recno > ubound(a,1) then
                    msg = "requested record out of array range"
                else
                    msg = trim$(a(recno))
                end if
                msgbox using$("trimmed record _# ###,### ==>'", recno+1) & msg & "'" ' +1 : array subscript==>record number
             end if
       loop
    end function
    
    ' /// end of file mmfdemo.bas

    ------------------
    michael mattias
    tal systems inc.
    racine wi usa
    mailto:[email protected][email protected]</a>
    www.talsystems.com
    Michael Mattias
    Tal Systems (retired)
    Port Washington WI USA
    [email protected]
    http://www.talsystems.com
Working...
X