/// <summary> /// /// </summary> /// <param name="pageid"></param> /// <param name="result"></param> protected override sealed void DoRead(uint pageid, byte[] result) { IRRFrame irrframe; //if not in hash map if (!map.TryGetValue(pageid, out irrframe)) { //add to hash map irrframe = new IRRFrame(pageid, pool.AllocSlot()); map[pageid] = irrframe; //load the page dev.Read(pageid, pool[irrframe.DataSlotId]); pool[irrframe.DataSlotId].CopyTo(result, 0); //add to IRR queue Frame frame = new Frame(pageid); frame.Dirty = false; irrQueue.Enqueue(frame); //(to be added) if the queue exceed a certain threshold, one frame should be kicked off. } else//in hash map { irrframe = map[pageid]; if (!irrframe.Resident) //miss non resident { irrframe.DataSlotId = pool.AllocSlot(); dev.Read(pageid, pool[irrframe.DataSlotId]); pool[irrframe.DataSlotId].CopyTo(result, 0); } //update IRR uint irr = irrQueue.accessIRR(pageid, false); irrframe.ReadIRR = irr; //possiblely 0, no effect if (irr == 0) { Frame frame = new Frame(pageid); frame.Dirty = false; irrQueue.Enqueue(frame); } } }
protected override void DoAccess(uint pageid, byte[] resultOrData, AccessType type) { LinkedListNode<IFrame> node; IFrame frame; if (map.TryGetValue(pageid, out node)) { frame = node.Value; list.Remove(node); } else { frame = new Frame(pageid); } PerformAccess(frame, resultOrData, type); node = list.AddFirst(frame); map[pageid] = node; }
/// <summary> /// /// </summary> /// <param name="pageid"></param> /// <param name="data"></param> protected override sealed void DoWrite(uint pageid, byte[] data) { Frame frame; //if not in hash map if (!map.TryGetValue(pageid, out frame)) { //add to hash map frame = new Frame(pageid, pool.AllocSlot()); map[pageid] = frame; //add to wirte queue writeQueue.Insert(0, pageid); //(to be added) if the queue exceed a certain threshold, one frame should be kicked off. } else//in hash map { frame = map[pageid]; //update if (IsInWriteWindow(pageid)) { changeLimit(-3);//TODO } if (!frame.Resident) //miss non resident allocate a slot { //在readQueue里前移到resident里 int index = readQueue.IndexOf(pageid); if (index != -1) { readQueue.RemoveAt(index); } frame.DataSlotId = pool.AllocSlot(); //移到resident的末尾 if (index != -1) { int lastReadResident = LastIndexOfResident(readQueue); Debug.Assert(index > lastReadResident); readQueue.Insert(lastReadResident + 1, pageid); } } writeQueue.Remove(pageid); writeQueue.Insert(0, pageid); } frame.Dirty = true; data.CopyTo(pool[frame.DataSlotId], 0); //if (writeQueue.Count > 2 * pool.NPages) //{ // uint removeId = writeQueue[writeQueue.Count - 1]; // writeQueue.RemoveAt(writeQueue.Count - 1); // int index = readQueue.IndexOf(removeId); // if (index < 0) // map.Remove(removeId); //} }
/// <summary> /// /// </summary> /// <param name="pageid"></param> /// <param name="result"></param> protected override sealed void DoRead(uint pageid, byte[] result) { Frame frame; //if not in hash map if (!map.TryGetValue(pageid, out frame)) { //add to hash map frame = new Frame(pageid, pool.AllocSlot()); map[pageid] = frame; //load the page dev.Read(pageid, pool[frame.DataSlotId]); pool[frame.DataSlotId].CopyTo(result, 0); //add to queue; readQueue.Insert(0, pageid); //(to be added) if the queue exceed a certain threshold, one frame should be kicked off. } else//in hash map { frame = map[pageid]; //update if (IsInReadWindow(pageid)) { changeLimit(1); } if (!frame.Resident) //miss non resident { //在writeQueue里前移到resident里 int index = writeQueue.IndexOf(pageid); if (index != -1) { writeQueue.RemoveAt(index); } frame.DataSlotId = pool.AllocSlot(); dev.Read(pageid, pool[frame.DataSlotId]); pool[frame.DataSlotId].CopyTo(result, 0); //移到resident的末尾 if (index != -1) { int lastWriteResident = LastIndexOfResident(writeQueue); Debug.Assert(index > lastWriteResident); writeQueue.Insert(lastWriteResident + 1, pageid); } } readQueue.Remove(pageid); readQueue.Insert(0, pageid); //if (readQueue.Count > 2 * pool.NPages) //{ // uint removeId = readQueue[readQueue.Count - 1]; // readQueue.RemoveAt(readQueue.Count - 1); // int index = writeQueue.IndexOf(removeId); // if (index < 0) // map.Remove(removeId); //} } }
/// <summary> /// /// </summary> /// <param name="pageid"></param> /// <param name="data"></param> protected override sealed void DoWrite(uint pageid, byte[] data) { IRRFrame irrframe; //if not in hash map if (!map.TryGetValue(pageid, out irrframe)) { //add to hash map irrframe = new IRRFrame(pageid, pool.AllocSlot()); map[pageid] = irrframe; //add to IRR queue Frame frame = new Frame(pageid); frame.Dirty = true; irrQueue.Enqueue(frame); //(to be added) if the queue exceed a certain threshold, one frame should be kicked off. } else//in hash map { irrframe = map[pageid]; if (!irrframe.Resident) //miss non resident allocate a slot { irrframe.DataSlotId = pool.AllocSlot(); } //update IRR uint irr = irrQueue.accessIRR(pageid, true); irrframe.WriteIRR = irr; //0 doesn't matter. if (irr == 0) { Frame frame = new Frame(pageid); frame.Dirty = true; irrQueue.Enqueue(frame); } } irrframe.Dirty = true; data.CopyTo(pool[irrframe.DataSlotId], 0); }