mirror of
https://github.com/WinampDesktop/winamp.git
synced 2024-12-18 16:05:53 +01:00
96 lines
1.4 KiB
C++
96 lines
1.4 KiB
C++
|
#include "main.h"
|
||
|
#include "./flagTracker.h"
|
||
|
|
||
|
FlagTracker::FlagTracker()
|
||
|
: flags(0), cache(0), updateRef(0), eventHandler(NULL), eventParam(0)
|
||
|
{
|
||
|
InitializeCriticalSection(&lock);
|
||
|
}
|
||
|
|
||
|
FlagTracker::~FlagTracker()
|
||
|
{
|
||
|
DeleteCriticalSection(&lock);
|
||
|
}
|
||
|
|
||
|
void FlagTracker::Set(UINT nFlags, UINT nMask)
|
||
|
{
|
||
|
EnterCriticalSection(&lock);
|
||
|
|
||
|
nFlags &= nMask;
|
||
|
|
||
|
UINT clearMask = ~(nFlags ^ nMask);
|
||
|
flags &= clearMask;
|
||
|
cache &= clearMask;
|
||
|
|
||
|
if (0 != nFlags)
|
||
|
{
|
||
|
Mark(nFlags);
|
||
|
}
|
||
|
|
||
|
LeaveCriticalSection(&lock);
|
||
|
}
|
||
|
|
||
|
UINT FlagTracker::Get()
|
||
|
{
|
||
|
return flags;
|
||
|
}
|
||
|
|
||
|
void FlagTracker::Mark(UINT nFlags)
|
||
|
{
|
||
|
EnterCriticalSection(&lock);
|
||
|
|
||
|
flags |= nFlags;
|
||
|
|
||
|
if (0 == updateRef)
|
||
|
{
|
||
|
if (NULL != eventHandler && 0 != nFlags)
|
||
|
{
|
||
|
eventHandler(nFlags, this, eventParam);
|
||
|
}
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
cache |= nFlags;
|
||
|
}
|
||
|
LeaveCriticalSection(&lock);
|
||
|
}
|
||
|
|
||
|
ULONG FlagTracker::BeginUpdate()
|
||
|
{
|
||
|
EnterCriticalSection(&lock);
|
||
|
ULONG r = InterlockedIncrement((LONG*)&updateRef);
|
||
|
LeaveCriticalSection(&lock);
|
||
|
return r;
|
||
|
}
|
||
|
|
||
|
ULONG FlagTracker::EndUpdate()
|
||
|
{
|
||
|
EnterCriticalSection(&lock);
|
||
|
|
||
|
ULONG r;
|
||
|
if (0 == updateRef)
|
||
|
{
|
||
|
r = 0;
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
r = InterlockedDecrement((LONG*)&updateRef);
|
||
|
if (0 == r && 0 != cache)
|
||
|
{
|
||
|
Mark(cache);
|
||
|
cache = 0;
|
||
|
}
|
||
|
}
|
||
|
LeaveCriticalSection(&lock);
|
||
|
return r;
|
||
|
}
|
||
|
|
||
|
void FlagTracker::SetEventHandler(EventHandler handler, ULONG_PTR user)
|
||
|
{
|
||
|
EnterCriticalSection(&lock);
|
||
|
|
||
|
eventHandler = handler;
|
||
|
eventParam = user;
|
||
|
|
||
|
LeaveCriticalSection(&lock);
|
||
|
}
|