Commit a22be47f authored by Ken Thomases's avatar Ken Thomases Committed by Alexandre Julliard

winemac: Add infrastructure to convert from Cocoa event time to Wine tick count.

parent 6e59740e
......@@ -33,6 +33,8 @@
{
NSMutableArray* eventQueues;
NSLock* eventQueuesLock;
NSTimeInterval eventTimeAdjustment;
}
- (void) transformProcessToForeground;
......@@ -40,6 +42,9 @@
- (BOOL) registerEventQueue:(WineEventQueue*)queue;
- (void) unregisterEventQueue:(WineEventQueue*)queue;
- (void) computeEventTimeAdjustmentFromTicks:(unsigned long long)tickcount uptime:(uint64_t)uptime_ns;
- (double) ticksForEventTime:(NSTimeInterval)eventTime;
@end
void OnMainThread(dispatch_block_t block);
......
......@@ -108,6 +108,16 @@ int macdrv_err_on;
[eventQueuesLock unlock];
}
- (void) computeEventTimeAdjustmentFromTicks:(unsigned long long)tickcount uptime:(uint64_t)uptime_ns
{
eventTimeAdjustment = (tickcount / 1000.0) - (uptime_ns / (double)NSEC_PER_SEC);
}
- (double) ticksForEventTime:(NSTimeInterval)eventTime
{
return (eventTime + eventTimeAdjustment) * 1000;
}
@end
/***********************************************************************
......
......@@ -19,6 +19,8 @@
*/
#import <AppKit/AppKit.h>
#include <mach/mach.h>
#include <mach/mach_time.h>
#include "macdrv_cocoa.h"
#import "cocoa_app.h"
......@@ -33,6 +35,13 @@ enum {
};
struct cocoa_app_startup_info {
NSConditionLock* lock;
unsigned long long tickcount;
uint64_t uptime_ns;
};
/***********************************************************************
* run_cocoa_app
*
......@@ -50,12 +59,14 @@ enum {
*/
static void run_cocoa_app(void* info)
{
NSConditionLock* lock = info;
struct cocoa_app_startup_info* startup_info = info;
NSConditionLock* lock = startup_info->lock;
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
[WineApplication sharedApplication];
[NSApp setDelegate:(WineApplication*)NSApp];
[NSApp computeEventTimeAdjustmentFromTicks:startup_info->tickcount uptime:startup_info->uptime_ns];
/* Retain the lock while we're using it, so macdrv_start_cocoa_app()
doesn't deallocate it in the middle of us unlocking it. */
......@@ -78,11 +89,13 @@ static void run_cocoa_app(void* info)
*
* Returns 0 on success, non-zero on failure.
*/
int macdrv_start_cocoa_app(void)
int macdrv_start_cocoa_app(unsigned long long tickcount)
{
int ret = -1;
CFRunLoopSourceRef source;
NSConditionLock* lock;
struct cocoa_app_startup_info startup_info;
uint64_t uptime_mach = mach_absolute_time();
mach_timebase_info_data_t mach_timebase;
NSDate* timeLimit;
CFRunLoopSourceContext source_context = { 0 };
......@@ -94,29 +107,34 @@ int macdrv_start_cocoa_app(void)
toTarget:[NSThread class]
withObject:nil];
lock = [[NSConditionLock alloc] initWithCondition:COCOA_APP_NOT_RUNNING];
startup_info.lock = [[NSConditionLock alloc] initWithCondition:COCOA_APP_NOT_RUNNING];
startup_info.tickcount = tickcount;
mach_timebase_info(&mach_timebase);
startup_info.uptime_ns = uptime_mach * mach_timebase.numer / mach_timebase.denom;
timeLimit = [NSDate dateWithTimeIntervalSinceNow:5];
source_context.info = lock;
source_context.info = &startup_info;
source_context.perform = run_cocoa_app;
source = CFRunLoopSourceCreate(NULL, 0, &source_context);
if (source && lock && timeLimit)
if (source && startup_info.lock && timeLimit)
{
CFRunLoopAddSource(CFRunLoopGetMain(), source, kCFRunLoopCommonModes);
CFRunLoopSourceSignal(source);
CFRunLoopWakeUp(CFRunLoopGetMain());
if ([lock lockWhenCondition:COCOA_APP_RUNNING beforeDate:timeLimit])
if ([startup_info.lock lockWhenCondition:COCOA_APP_RUNNING beforeDate:timeLimit])
{
[lock unlock];
[startup_info.lock unlock];
ret = 0;
}
}
if (source)
CFRelease(source);
[lock release];
[startup_info.lock release];
[pool release];
return ret;
}
......@@ -112,7 +112,7 @@ struct macdrv_display {
/* main */
extern int macdrv_err_on;
extern int macdrv_start_cocoa_app(void) DECLSPEC_HIDDEN;
extern int macdrv_start_cocoa_app(unsigned long long tickcount) DECLSPEC_HIDDEN;
/* display */
......
......@@ -40,7 +40,7 @@ static BOOL process_attach(void)
if ((thread_data_tls_index = TlsAlloc()) == TLS_OUT_OF_INDEXES) return FALSE;
macdrv_err_on = ERR_ON(macdrv);
if (macdrv_start_cocoa_app())
if (macdrv_start_cocoa_app(GetTickCount64()))
{
ERR("Failed to start Cocoa app main loop\n");
return FALSE;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment