예제 #1
0
        public void FsmPage()
        {
            int pageSize         = 32768;
            var dummyPageManager = new FileSystemPageManager(pageSize);
            var p = new Page(dummyPageManager, 0, new byte[pageSize]);

            var fsmh = new FreeSpaceMapPageHeader();
            var r    = new Random();

            PageFormatter.InitPage(p, fsmh);
            int fsmEntryCount = PageFormatter.GetFsmEntryCount(p);

            // set all values to "full"
            PageFormatter.SetAllFsmValues(p, FsmValue.Full);

            // check if all values are actually "full"
            for (int i = 0; i < fsmEntryCount; i++)
            {
                Assert.AreEqual(FsmValue.Full, PageFormatter.GetFsmValue(p, i));
            }

            var values = new FsmValue[fsmEntryCount];

            // set and keep random values
            for (int i = 0; i < fsmEntryCount; i++)
            {
                var value = (byte)r.Next((byte)FsmValue.Full + 1);
                PageFormatter.SetFsmValue(p, i, (FsmValue)value);
                values[i] = (FsmValue)value;
            }

            // compare it
            for (int i = 0; i < fsmEntryCount; i++)
            {
                Assert.AreEqual(values[i], PageFormatter.GetFsmValue(p, i));
            }
        }
예제 #2
0
        public void Set(long pageIndex, FsmValue value)
        {
            if (!_isInitialized)
            {
                Init();
            }

            IPage page = GetFsmPageByTargetPageIndex(pageIndex);

            if (page == null)
            {
                // fsm-page is missing for requested page index
                long previousPageIndex = _lastFsmPage.Index;
                var  missingPageCount  = (int)((pageIndex - (_fsmPageCount - _fsmPageIndexes.Count) * _entryPerPage) / _entryPerPage + 1);

                var pages = new List <IPage>(missingPageCount);

                // allocate new pages
                for (int i = 0; i < missingPageCount; i++)
                {
                    pages.Add(_pageManager.CreatePage());
                }

                var baseIndex = PageFormatter.GetBasePageIndex(_lastFsmPage);

                // initialize them
                for (int i = 0; i < missingPageCount; i++)
                {
                    baseIndex += _entryPerPage;
                    InitFsmPage(pages[i],
                                previousPageIndex,
                                i == missingPageCount - 1 ? -1 : pages[i + 1].Index,
                                baseIndex);
                    previousPageIndex = pages[i].Index;
                }

                // and update
                pages.ForEach(_pageManager.UpdatePage);

                // save reference to added pages
                var lastPageHeader = (FreeSpaceMapPageHeader)PageFormatter.GetPageHeader(_lastFsmPage);
                lastPageHeader.NextPageIndex = pages[0].Index;
                lastPageHeader.WriteToPage(_lastFsmPage);
                _pageManager.UpdatePage(_lastFsmPage);

                _lastFsmPage  = null;
                _fsmPageCount = -1;

                Set(pageIndex, value);
            }
            else
            {
                PageFormatter.SetFsmValue(page, (int)pageIndex % _entryPerPage, value);
                _pageManager.UpdatePage(page);

                var fsmValuesToUpdate = _luckyFsmPages.Where(item => item.Value.Page.Index == page.Index).Select(item => item.Key).ToList();

                foreach (var fsmValue in fsmValuesToUpdate)
                {
                    _luckyFsmPages[fsmValue].Page = page;
                }

                if (!_luckyFsmPages.ContainsKey(value))
                {
                    _luckyFsmPages[value] = new LuckyPage {
                        Page = page, LastGoodIndex = pageIndex
                    }
                }
                ;
                else
                {
                    if (_scanned.Contains(value))
                    {
                        _scanned.Remove(value);
                    }
                }
            }
        }