Unnamed Fossil Project

Changes
Login

Added function freePage2():

    /*
    ** This function is used to add page iPage to the database file free-list.
    ** It is assumed that the page is not already a part of the free-list.
    **
    ** The value passed as the second argument to this function is optional.
    ** If the caller happens to have a pointer to the MemPage object
    ** corresponding to page iPage handy, it may pass it as the second value. 
    ** Otherwise, it may pass NULL.
    **
    ** If a pointer to a MemPage object is passed as the second argument,
    ** its reference count is not altered by this function.
    */
    static int freePage2(BtShared *pBt, MemPage *pMemPage, Pgno iPage);

The normal version, "freePage(MemPage *)" is implemented using freePage2() and still used by most of the code.

Sometimes, when moving a list of overflow pages to the free-list, the pages had to be requested from the pager layer with the "noContent" flag set. In particular, when the pointer-map pages could be used to find a page in an overflow list and it was moved to become a free-list leaf, there is no need to load the page data into memory. In this case, instead of loading the page with the noContent flag set, avoid loading the page reference altogether and use freePage2()

The only other place PagerAcquire() is called with the noContent flag set is when loading a free-list leaf page. In this case sqlite3PagerDontRollback() is called immediately afterwards, and then sqlite3PagerWrite(). So, unless the bit corresponding to the page is set in the Pager.pAlwaysRollback bitvec, DontRollback() clears the NEED_READ flag. Or, if the bit in pAlwaysRollback is set, PagerWrite() loads the content from the page.

Patch changes things so that the pAlwaysRollback vector is maintained as part of the btree layer (where it is called pHasContent), and noContent is only passed to PagerAcquire() if the bit in pAlwaysRollback is clear. Therefore the PGHDR_NEED_READ flag will never be set and can be left out.

Passing noContent=1 to PagerAcquire() implies DontRollback(), so the functionality of DontRollback() is rolled into PagerAcquire().

PagerDontWrite() is simplified. It no longer has to manipulate the pAlwaysRollback bitvec. And we no longer worry about making sure the last page of the file is not marked DONT_WRITE in cases where the file has grown. Instead pager_truncate() is called from the CommitPhaseOne() to grow the file if required in the same way as it is to shrink it.