/*
 * Implementation of CLSID_SystemClock.
 *
 * hidenori@a2.ctktv.ne.jp
 */

#include "config.h"

#include "windef.h"
#include "winbase.h"
#include "wingdi.h"
#include "winuser.h"
#include "winerror.h"
#include "strmif.h"
#include "uuids.h"

#include "debugtools.h"
DEFAULT_DEBUG_CHANNEL(quartz);

#include "quartz_private.h"
#include "sysclock.h"


/***************************************************************************
 *
 *	new/delete for CLSID_SystemClock
 *
 */

/* can I use offsetof safely? - FIXME? */
static QUARTZ_IFEntry IFEntries[] =
{
  { &IID_IReferenceClock, offsetof(CSystemClock,refclk)-offsetof(CSystemClock,unk) },
};


static void QUARTZ_DestroySystemClock(IUnknown* punk)
{
	CSystemClock_THIS(punk,unk);

	CSystemClock_UninitIReferenceClock( This );
}

HRESULT QUARTZ_CreateSystemClock(IUnknown* punkOuter,void** ppobj)
{
	CSystemClock*	psc;
	HRESULT	hr;

	TRACE("(%p,%p)\n",punkOuter,ppobj);

	psc = (CSystemClock*)QUARTZ_AllocObj( sizeof(CSystemClock) );
	if ( psc == NULL )
		return E_OUTOFMEMORY;

	QUARTZ_IUnkInit( &psc->unk, punkOuter );
	hr = CSystemClock_InitIReferenceClock( psc );
	if ( FAILED(hr) )
	{
		QUARTZ_FreeObj( psc );
		return hr;
	}

	psc->unk.pEntries = IFEntries;
	psc->unk.dwEntries = sizeof(IFEntries)/sizeof(IFEntries[0]);
	psc->unk.pOnFinalRelease = QUARTZ_DestroySystemClock;

	*ppobj = (void*)(&psc->unk);

	return S_OK;
}


/***************************************************************************
 *
 *	CLSID_SystemClock::IReferenceClock
 *
 */

#define	QUARTZ_MSG_ADDTIMER			(WM_APP+0)
#define	QUARTZ_MSG_REMOVETIMER		(WM_APP+1)
#define	QUARTZ_MSG_EXITTHREAD		(WM_APP+2)


/****************************************************************************/

static QUARTZ_TimerEntry* IReferenceClock_AllocTimerEntry(CSystemClock* This)
{
	QUARTZ_TimerEntry*	pEntry;
	DWORD	dw;

	pEntry = &This->m_timerEntries[0];
	for ( dw = 0; dw < WINE_QUARTZ_SYSCLOCK_TIMER_MAX; dw++ )
	{
		if ( pEntry->hEvent == (HANDLE)NULL )
			return pEntry;
		pEntry ++;
	}

	return NULL;
}

static QUARTZ_TimerEntry* IReferenceClock_SearchTimer(CSystemClock* This, DWORD dwAdvCookie)
{
	QUARTZ_TimerEntry*	pEntry;
	DWORD	dw;

	pEntry = &This->m_timerEntries[0];
	for ( dw = 0; dw < WINE_QUARTZ_SYSCLOCK_TIMER_MAX; dw++ )
	{
		if ( pEntry->hEvent != (HANDLE)NULL &&
			 pEntry->dwAdvCookie == dwAdvCookie )
			return pEntry;
		pEntry ++;
	}

	return NULL;
}

static DWORD IReferenceClock_OnTimerUpdated(CSystemClock* This)
{
	QUARTZ_TimerEntry*	pEntry;
	REFERENCE_TIME	rtCur;
	REFERENCE_TIME	rtSignal;
	REFERENCE_TIME	rtCount;
	HRESULT	hr;
	LONG	lCount;
	DWORD	dw;
	DWORD	dwTimeout = INFINITE;
	DWORD	dwTimeoutCur;

	hr = IReferenceClock_GetTime((IReferenceClock*)(&This->refclk),&rtCur);
	if ( hr != NOERROR )
		return INFINITE;

	pEntry = &This->m_timerEntries[0];
	for ( dw = 0; dw < WINE_QUARTZ_SYSCLOCK_TIMER_MAX; dw++ )
	{
		if ( pEntry->hEvent != (HANDLE)NULL )
		{
			rtSignal = pEntry->rtStart + pEntry->rtInterval;
			if ( rtCur >= rtSignal )
			{
				if ( pEntry->fPeriodic )
				{
					rtCount = ((rtCur - pEntry->rtStart) / pEntry->rtInterval);
					lCount = ( rtCount > (REFERENCE_TIME)0x7fffffff ) ?
						(LONG)0x7fffffff : (LONG)rtCount;
					if ( !ReleaseSemaphore( pEntry->hEvent, lCount, NULL ) )
					{
						while ( lCount > 0 )
						{
							if ( !ReleaseSemaphore( pEntry->hEvent, 1, NULL ) )
								break;
						}
					}
					dwTimeout = 0;
				}
				else
				{
					TRACE( "signal an event\n" );
					SetEvent( pEntry->hEvent );
					pEntry->hEvent = (HANDLE)NULL;
				}
			}
			else
			{
				rtCount = rtSignal - rtCur;
				/* [100ns] -> [ms] */
				rtCount = (rtCount+(REFERENCE_TIME)9999)/(REFERENCE_TIME)10000;
				dwTimeoutCur = (rtCount >= 0xfffffffe) ? (DWORD)0xfffffffe : (DWORD)rtCount;
				if ( dwTimeout > dwTimeoutCur )
					dwTimeout = dwTimeoutCur;
			}
		}
		pEntry ++;
	}

	return dwTimeout;
}

static
DWORD WINAPI IReferenceClock_TimerEntry( LPVOID lpvParam )
{
	CSystemClock*	This = (CSystemClock*)lpvParam;
	MSG	msg;
	DWORD	dwRes;
	DWORD	dwTimeout;

	/* initialize the message queue. */
	PeekMessageA( &msg, (HWND)NULL, 0, 0, PM_NOREMOVE );
	/* resume the owner thread. */
	SetEvent( This->m_hEventInit );

	TRACE( "Enter message loop.\n" );

	/* message loop. */
	dwTimeout = INFINITE;
	while ( 1 )
	{
		if ( dwTimeout > 0 )
		{
			dwRes = MsgWaitForMultipleObjects(
				0, NULL, FALSE,
				dwTimeout,
				QS_ALLEVENTS );
		}

		EnterCriticalSection( &This->m_csClock );
		dwTimeout = IReferenceClock_OnTimerUpdated(This);
		LeaveCriticalSection( &This->m_csClock );
		TRACE( "catch an event / timeout %lu\n", dwTimeout );

		while ( PeekMessageA( &msg, (HWND)NULL, 0, 0, PM_REMOVE ) )
		{
			if ( msg.message == WM_QUIT )
				goto quitthread;

			if ( msg.hwnd != (HWND)NULL )
			{
				TranslateMessage( &msg );
				DispatchMessageA( &msg );
			}
			else
			{
				switch ( msg.message )
				{
				case QUARTZ_MSG_ADDTIMER:
				case QUARTZ_MSG_REMOVETIMER:
					dwTimeout = 0;
					break;
				case QUARTZ_MSG_EXITTHREAD:
					PostQuitMessage(0);
					break;
				default:
					FIXME( "invalid message %04u\n", (unsigned)msg.message );
					break;
				}
			}
		}
	}

quitthread:
	TRACE( "quit thread\n" );
	return 0;
}

/****************************************************************************/

static HRESULT WINAPI
IReferenceClock_fnQueryInterface(IReferenceClock* iface,REFIID riid,void** ppobj)
{
	CSystemClock_THIS(iface,refclk);

	TRACE("(%p)->()\n",This);

	return IUnknown_QueryInterface(This->unk.punkControl,riid,ppobj);
}

static ULONG WINAPI
IReferenceClock_fnAddRef(IReferenceClock* iface)
{
	CSystemClock_THIS(iface,refclk);

	TRACE("(%p)->()\n",This);

	return IUnknown_AddRef(This->unk.punkControl);
}

static ULONG WINAPI
IReferenceClock_fnRelease(IReferenceClock* iface)
{
	CSystemClock_THIS(iface,refclk);

	TRACE("(%p)->()\n",This);

	return IUnknown_Release(This->unk.punkControl);
}

static HRESULT WINAPI
IReferenceClock_fnGetTime(IReferenceClock* iface,REFERENCE_TIME* prtTime)
{
	CSystemClock_THIS(iface,refclk);
	DWORD	dwTimeCur;

	TRACE( "(%p)->(%p)\n", This, prtTime );

	if ( prtTime == NULL )
		return E_POINTER;

	EnterCriticalSection( &This->m_csClock );

	dwTimeCur = GetTickCount();
	This->m_rtLast += (REFERENCE_TIME)(DWORD)(dwTimeCur - This->m_dwTimeLast) * (REFERENCE_TIME)10000;

	This->m_dwTimeLast = dwTimeCur;

	*prtTime = This->m_rtLast;

	LeaveCriticalSection( &This->m_csClock );

	return NOERROR;
}

static HRESULT WINAPI
IReferenceClock_fnAdviseTime(IReferenceClock* iface,REFERENCE_TIME rtBase,REFERENCE_TIME rtStream,HEVENT hEvent,DWORD_PTR* pdwAdvCookie)
{
	CSystemClock_THIS(iface,refclk);
	QUARTZ_TimerEntry*	pEntry;
	HRESULT	hr;
	REFERENCE_TIME	rtCur;

	TRACE( "(%p)->()\n", This );

	if ( pdwAdvCookie == NULL )
		return E_POINTER;
	if ( hEvent == (HANDLE)NULL )
		return E_INVALIDARG;

	EnterCriticalSection( &This->m_csClock );

	*pdwAdvCookie = (DWORD_PTR)(This->m_dwAdvCookieNext ++);

	hr = IReferenceClock_GetTime(iface,&rtCur);
	if ( hr != NOERROR )
		goto err;
	if ( rtCur >= (rtBase+rtStream) )
	{
		SetEvent(hEvent);
		hr = NOERROR;
		goto err;
	}

	pEntry = IReferenceClock_AllocTimerEntry(This);
	if ( pEntry == NULL )
	{
		hr = E_FAIL;
		goto err;
	}

        pEntry->dwAdvCookie = *pdwAdvCookie;
        pEntry->fPeriodic = FALSE;
        pEntry->hEvent = hEvent;
        pEntry->rtStart = rtBase;
        pEntry->rtInterval = rtStream;

	if ( !PostThreadMessageA(
			This->m_idThreadTimer,
			QUARTZ_MSG_ADDTIMER,
			0, 0 ) )
	{
		pEntry->hEvent = (HANDLE)NULL;
		hr = E_FAIL;
		goto err;
	}

	hr = NOERROR;
err:
	LeaveCriticalSection( &This->m_csClock );

	return hr;
}

static HRESULT WINAPI
IReferenceClock_fnAdvisePeriodic(IReferenceClock* iface,REFERENCE_TIME rtStart,REFERENCE_TIME rtPeriod,HSEMAPHORE hSemaphore,DWORD_PTR* pdwAdvCookie)
{
	CSystemClock_THIS(iface,refclk);
	QUARTZ_TimerEntry*	pEntry;
	HRESULT	hr;

	TRACE( "(%p)->()\n", This );

	if ( pdwAdvCookie == NULL )
		return E_POINTER;
	if ( hSemaphore == (HSEMAPHORE)NULL )
		return E_INVALIDARG;

	EnterCriticalSection( &This->m_csClock );

	*pdwAdvCookie = (DWORD_PTR)(This->m_dwAdvCookieNext ++);

	pEntry = IReferenceClock_AllocTimerEntry(This);
	if ( pEntry == NULL )
	{
		hr = E_FAIL;
		goto err;
	}

        pEntry->dwAdvCookie = *pdwAdvCookie;
        pEntry->fPeriodic = TRUE;
        pEntry->hEvent = (HANDLE)hSemaphore;
        pEntry->rtStart = rtStart;
        pEntry->rtInterval = rtPeriod;

	if ( !PostThreadMessageA(
			This->m_idThreadTimer,
			QUARTZ_MSG_ADDTIMER,
			0, 0 ) )
	{
		pEntry->hEvent = (HANDLE)NULL;
		hr = E_FAIL;
		goto err;
	}

	hr = NOERROR;
err:
	LeaveCriticalSection( &This->m_csClock );

	return hr;
}

static HRESULT WINAPI
IReferenceClock_fnUnadvise(IReferenceClock* iface,DWORD_PTR dwAdvCookie)
{
	CSystemClock_THIS(iface,refclk);
	QUARTZ_TimerEntry*	pEntry;

	TRACE( "(%p)->(%lu)\n", This, (DWORD)dwAdvCookie );

	EnterCriticalSection( &This->m_csClock );

	pEntry = IReferenceClock_SearchTimer(This,(DWORD)dwAdvCookie);
	if ( pEntry != NULL )
	{
		pEntry->hEvent = (HANDLE)NULL;
	}

	LeaveCriticalSection( &This->m_csClock );

	return NOERROR;
}

static ICOM_VTABLE(IReferenceClock) irefclk =
{
	ICOM_MSVTABLE_COMPAT_DummyRTTIVALUE
	/* IUnknown fields */
	IReferenceClock_fnQueryInterface,
	IReferenceClock_fnAddRef,
	IReferenceClock_fnRelease,
	/* IReferenceClock fields */
	IReferenceClock_fnGetTime,
	IReferenceClock_fnAdviseTime,
	IReferenceClock_fnAdvisePeriodic,
	IReferenceClock_fnUnadvise,
};


HRESULT CSystemClock_InitIReferenceClock( CSystemClock* psc )
{
	HANDLE	hEvents[2];

	TRACE("(%p)\n",psc);
	ICOM_VTBL(&psc->refclk) = &irefclk;

	InitializeCriticalSection( &psc->m_csClock );
	psc->m_dwTimeLast = GetTickCount();
	psc->m_rtLast = (REFERENCE_TIME)0;
	psc->m_hThreadTimer = (HANDLE)NULL;
	psc->m_hEventInit = (HANDLE)NULL;
	psc->m_idThreadTimer = 0;
	psc->m_dwAdvCookieNext = 1;
	ZeroMemory( psc->m_timerEntries, sizeof(psc->m_timerEntries) );

	psc->m_hEventInit = CreateEventA( NULL, TRUE, FALSE, NULL );
	if ( psc->m_hEventInit == (HANDLE)NULL )
		goto err;

	psc->m_hThreadTimer = CreateThread(
		NULL, 0,
		IReferenceClock_TimerEntry,
		psc, 0, &psc->m_idThreadTimer );

	if ( psc->m_hThreadTimer == (HANDLE)NULL )
	{
		CloseHandle( psc->m_hEventInit );
		psc->m_hEventInit = (HANDLE)NULL;
		goto err;
	}

	hEvents[0] = psc->m_hEventInit;
	hEvents[1] = psc->m_hThreadTimer;
	if ( WaitForMultipleObjects( 2, hEvents, FALSE, INFINITE )
			!= WAIT_OBJECT_0 )
	{
		CloseHandle( psc->m_hEventInit );
		psc->m_hEventInit = (HANDLE)NULL;
		CloseHandle( psc->m_hThreadTimer );
		psc->m_hThreadTimer = (HANDLE)NULL;
		goto err;
	}

	return NOERROR;

err:
	DeleteCriticalSection( &psc->m_csClock );
	return E_FAIL;
}

void CSystemClock_UninitIReferenceClock( CSystemClock* psc )
{
	TRACE("(%p)\n",psc);

	if ( psc->m_hThreadTimer != (HANDLE)NULL )
	{
		if ( PostThreadMessageA(
			psc->m_idThreadTimer,
			QUARTZ_MSG_EXITTHREAD,
			0, 0 ) )
		{
			WaitForSingleObject( psc->m_hThreadTimer, INFINITE );
		}
		CloseHandle( psc->m_hThreadTimer );
		psc->m_hThreadTimer = (HANDLE)NULL;
	}

	DeleteCriticalSection( &psc->m_csClock );
}
