locklist.cpp
来自「WinCE5.0部分核心源码」· C++ 代码 · 共 311 行
CPP
311 行
//
// Copyright (c) Microsoft Corporation. All rights reserved.
//
//
// This source code is licensed under Microsoft Shared Source License
// Version 1.0 for Windows CE.
// For a copy of the license visit http://go.microsoft.com/fwlink/?LinkId=3223.
//
/*++
Module Name:
lockset.h
Abstract:
Lock List Abstraction. A lock list is a set of locks a global list range.
A lock list is sorted by the lowest byte locked by a lock. The list range
is defined as the lowest byte locked by a lock in the list and the highest
byte locked by a lock in the list.
Revision History:
--*/
#include "locklist.hpp"
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
CFileLockList::CFileLockList()
{
m_dwOwner = NULL;
m_pRange = new CRange();
m_pListHead = NULL;
m_pNextList = NULL;
}
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
CFileLockList::~CFileLockList()
{
CFileLock *pLockToDelete;
CFileLock *pNextLock;
if (NULL != m_pRange) {
delete m_pRange;
}
DEBUGCHK(NULL == m_pNextList);
// delete list
pLockToDelete = m_pListHead;
while (NULL != pLockToDelete) {
pNextLock = pLockToDelete->GetNext();
pLockToDelete->SetNext(NULL);
delete pLockToDelete;
pLockToDelete = pNextLock;
}
}
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
CFileLock *CFileLockList::GetLast()
{
CFileLock *pCurLock;
CFileLock *pMax;
ULONGLONG ullFurthestByte = 0;
pCurLock = m_pListHead;
pMax = pCurLock;
// find last lock in list
while (NULL != pCurLock) {
DEBUGCHK(NULL != pCurLock->GetRange());
if (ullFurthestByte < pCurLock->GetRange()->GetFinish()) {
ullFurthestByte = pCurLock->GetRange()->GetFinish();
pMax = pCurLock;
}
pCurLock = pCurLock->GetNext();
}
return pMax;
}
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
BOOL CFileLockList::IsEmpty()
{
return (NULL == m_pListHead) ? TRUE : FALSE;
}
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
BOOL CFileLockList::IsConflict(CRange *pRange)
{
CFileLock *pCurLock;
DEBUGCHK(NULL != pRange);
if (this->IsEmpty()) {
return FALSE;
}
DEBUGCHK(NULL != m_pRange);
switch (m_pRange->IsConflict(pRange)) {
case RCT_NOCONFLICT_BEFORE:
case RCT_NOCONFLICT_AFTER:
return FALSE;
case RCT_BOUNDARY:
return TRUE;
}
// target lies within range of list
pCurLock = m_pListHead;
while (NULL != pCurLock) {
DEBUGCHK(NULL != pCurLock->GetRange());
switch (pRange->IsConflict(pCurLock->GetRange())) {
case RCT_NOCONFLICT_BEFORE:
// (lock lists are sorted by start of range)
return FALSE;
case RCT_NOCONFLICT_AFTER:
pCurLock = pCurLock->GetNext();
break;
case RCT_BETWEEN:
case RCT_BOUNDARY:
return TRUE;
}
}
// target is after all locks in list
return FALSE;
}
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
VOID CFileLockList::Insert(CFileLock *pFileLock)
{
CFileLock *pBefore;
CFileLock *pAfter;
PREFAST_DEBUGCHK(NULL != pFileLock);
PREFAST_DEBUGCHK(NULL != pFileLock->GetRange());
PREFAST_DEBUGCHK(NULL == pFileLock->GetNext());
// update range of list
PREFAST_DEBUGCHK(NULL != m_pRange);
if (pFileLock->GetRange()->GetStart() < m_pRange->GetStart()) {
m_pRange->SetStart(pFileLock->GetRange()->GetStart());
}
if (pFileLock->GetRange()->GetFinish() > m_pRange->GetFinish()) {
m_pRange->SetFinish(pFileLock->GetRange()->GetFinish());
}
// find position of insertion
if (this->IsEmpty()) {
m_pListHead = pFileLock;
return;
}
pBefore = m_pListHead;
pAfter = pBefore;
while (NULL != pAfter) {
PREFAST_DEBUGCHK(NULL != pAfter->GetRange());
if (pFileLock->GetRange()->GetStart() < pAfter->GetRange()->GetStart()) {
break;
}
pBefore = pAfter;
pAfter = pAfter->GetNext();
}
// insert lock
// is lock to be inserted before first lock in list?
if (pAfter == m_pListHead) {
pFileLock->SetNext(m_pListHead);
m_pListHead = pFileLock;
}
else {
pBefore->SetNext(pFileLock);
pFileLock->SetNext(pAfter);
}
}
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
CFileLock *CFileLockList::Remove(CRange *pRange)
{
CFileLock *pBefore;
CFileLock *pAfter;
BOOL fFound = FALSE;
PREFAST_DEBUGCHK(NULL != pRange);
if (this->IsEmpty()) {
return NULL;
}
// find lock to remove
pBefore = m_pListHead;
pAfter = pBefore;
while (NULL != pAfter) {
PREFAST_DEBUGCHK(NULL != pAfter->GetRange());
if (pAfter->GetRange()->IsEqualTo(pRange)) {
fFound = TRUE;
break;
}
pBefore = pAfter;
pAfter = pAfter->GetNext();
}
// was lock found?
if (!fFound) {
return NULL;
}
// remove lock
if (pAfter == m_pListHead) {
m_pListHead = pAfter->GetNext();
}
else {
pBefore->SetNext(pAfter->GetNext());
}
// update range of list
PREFAST_DEBUGCHK(NULL != m_pRange);
if (!this->IsEmpty()) {
PREFAST_DEBUGCHK(NULL != pAfter->GetRange());
if (m_pRange->GetStart() == pAfter->GetRange()->GetStart()) {
m_pRange->SetStart(m_pListHead->GetRange()->GetStart());
}
if (m_pRange->GetFinish() == pAfter->GetRange()->GetFinish()) {
pBefore = this->GetLast();
PREFAST_DEBUGCHK(NULL != pBefore);
PREFAST_DEBUGCHK(NULL != pBefore->GetRange());
m_pRange->SetFinish(pBefore->GetRange()->GetFinish());
}
}
else {
m_pRange->SetStart(CRANGE_MAX_START);
m_pRange->SetFinish(CRANGE_MIN_FINISH);
}
// isolate removed lock
pAfter->SetNext(NULL);
// return removed lock
return pAfter;
}
// ----------------------------------------------------------------------------
// ----------------------------------------------------------------------------
BOOL CFileLockList::IsValid()
{
BOOL fResult;
CFileLock *pFileLock;
if (0 == m_dwOwner) {
fResult = FALSE;
goto exit;
}
if (NULL == m_pRange) {
fResult = FALSE;
goto exit;
}
// is list range valid?
if (!m_pRange->IsValid()) {
fResult = FALSE;
goto exit;
}
// is each lock in list valid?
pFileLock = m_pListHead;
while (NULL != pFileLock) {
if (!pFileLock->IsValid()) {
fResult = FALSE;
goto exit;
}
pFileLock = pFileLock->GetNext();
}
fResult = TRUE;
exit:;
return fResult;
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?