Cocoa Port: Remove and replace the high-overhead NSThread with the lower-overhead pthread_t. Improves video display performance when the frame rate is very high (greater than 600 FPS).
This commit is contained in:
parent
f9c32c9e79
commit
01c508f93a
|
@ -1199,7 +1199,7 @@ public:
|
|||
{
|
||||
if ([cdsOutput isKindOfClass:[CocoaDSDisplayVideo class]])
|
||||
{
|
||||
[CocoaDSUtil messageSendOneWay:[cdsOutput receivePort] msgID:MESSAGE_RECEIVE_GPU_FRAME];
|
||||
[(CocoaDSDisplayVideo *)cdsOutput signalMessage:MESSAGE_RECEIVE_GPU_FRAME];
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (C) 2011 Roger Manuel
|
||||
Copyright (C) 2012-2017 DeSmuME Team
|
||||
Copyright (C) 2012-2018 DeSmuME Team
|
||||
|
||||
This file is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
|
@ -362,13 +362,6 @@ enum
|
|||
MESSAGE_SET_RENDER3D_LINE_HACK,
|
||||
MESSAGE_SET_RENDER3D_MULTISAMPLE,
|
||||
|
||||
MESSAGE_SET_AUDIO_PROCESS_METHOD,
|
||||
MESSAGE_SET_SPU_ADVANCED_LOGIC,
|
||||
MESSAGE_SET_SPU_SYNC_MODE,
|
||||
MESSAGE_SET_SPU_SYNC_METHOD,
|
||||
MESSAGE_SET_SPU_INTERPOLATION_MODE,
|
||||
MESSAGE_SET_VOLUME,
|
||||
|
||||
MESSAGE_COPY_TO_PASTEBOARD
|
||||
};
|
||||
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (C) 2011 Roger Manuel
|
||||
Copyright (C) 2011-2017 DeSmuME team
|
||||
Copyright (C) 2011-2018 DeSmuME team
|
||||
|
||||
This file is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
|
@ -28,18 +28,31 @@
|
|||
@class NSImage;
|
||||
@class NSBitmapImageRep;
|
||||
|
||||
@interface CocoaDSOutput : CocoaDSThread
|
||||
@interface CocoaDSOutput : NSObject
|
||||
{
|
||||
uint32_t _threadMessageID;
|
||||
pthread_mutex_t _mutexMessageLoop;
|
||||
pthread_cond_t _condSignalMessage;
|
||||
pthread_t _pthread;
|
||||
|
||||
NSMutableDictionary *property;
|
||||
|
||||
pthread_mutex_t *mutexConsume;
|
||||
pthread_rwlock_t *rwlockProducer;
|
||||
|
||||
BOOL _idleState;
|
||||
OSSpinLock spinlockIdle;
|
||||
}
|
||||
|
||||
@property (readonly) NSMutableDictionary *property;
|
||||
@property (assign) pthread_rwlock_t *rwlockProducer;
|
||||
@property (readonly) pthread_mutex_t *mutexConsume;
|
||||
@property (assign) BOOL idle;
|
||||
|
||||
- (void) createThread;
|
||||
- (void) exitThread;
|
||||
|
||||
- (void) runMessageLoop;
|
||||
- (void) signalMessage:(int32_t)messageID;
|
||||
- (void) handleSignalMessageID:(int32_t)messageID;
|
||||
- (void) doCoreEmuFrame;
|
||||
- (void) handleEmuFrameProcessed;
|
||||
|
||||
|
@ -83,12 +96,6 @@
|
|||
- (NSString *) audioOutputEngineString;
|
||||
- (NSString *) spuInterpolationModeString;
|
||||
- (NSString *) spuSyncMethodString;
|
||||
- (void) handleSetVolume:(NSData *)volumeData;
|
||||
- (void) handleSetAudioOutputEngine:(NSData *)methodIdData;
|
||||
- (void) handleSetSpuAdvancedLogic:(NSData *)stateData;
|
||||
- (void) handleSetSpuSyncMode:(NSData *)modeIdData;
|
||||
- (void) handleSetSpuSyncMethod:(NSData *)methodIdData;
|
||||
- (void) handleSetSpuInterpolationMode:(NSData *)modeIdData;
|
||||
|
||||
@end
|
||||
|
||||
|
@ -174,3 +181,14 @@
|
|||
- (NSImage *) image;
|
||||
|
||||
@end
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C"
|
||||
{
|
||||
#endif
|
||||
|
||||
static void* RunOutputThread(void *arg);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (C) 2011 Roger Manuel
|
||||
Copyright (C) 2011-2017 DeSmuME team
|
||||
Copyright (C) 2011-2018 DeSmuME team
|
||||
|
||||
This file is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
|
@ -40,12 +40,11 @@
|
|||
@implementation CocoaDSOutput
|
||||
|
||||
@synthesize property;
|
||||
@synthesize mutexConsume;
|
||||
@synthesize rwlockProducer;
|
||||
|
||||
- (id)init
|
||||
{
|
||||
self = [super initWithAutoreleaseInterval:0.1];
|
||||
self = [super init];
|
||||
if (self == nil)
|
||||
{
|
||||
return self;
|
||||
|
@ -54,45 +53,107 @@
|
|||
property = [[NSMutableDictionary alloc] init];
|
||||
[property setValue:[NSDate date] forKey:@"outputTime"];
|
||||
|
||||
mutexConsume = (pthread_mutex_t *)malloc(sizeof(pthread_mutex_t));
|
||||
pthread_mutex_init(mutexConsume, NULL);
|
||||
|
||||
rwlockProducer = NULL;
|
||||
|
||||
_threadMessageID = MESSAGE_NONE;
|
||||
_pthread = NULL;
|
||||
|
||||
_idleState = NO;
|
||||
spinlockIdle = OS_SPINLOCK_INIT;
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)dealloc
|
||||
{
|
||||
// Force the thread to exit now so that we can safely release other resources.
|
||||
[self forceThreadExit];
|
||||
[self exitThread];
|
||||
|
||||
[property release];
|
||||
|
||||
pthread_mutex_destroy(mutexConsume);
|
||||
free(mutexConsume);
|
||||
mutexConsume = NULL;
|
||||
|
||||
[super dealloc];
|
||||
}
|
||||
|
||||
- (void) doCoreEmuFrame
|
||||
- (void) setIdle:(BOOL)theState
|
||||
{
|
||||
[CocoaDSUtil messageSendOneWay:self.receivePort msgID:MESSAGE_EMU_FRAME_PROCESSED];
|
||||
OSSpinLockLock(&spinlockIdle);
|
||||
_idleState = theState;
|
||||
OSSpinLockUnlock(&spinlockIdle);
|
||||
}
|
||||
|
||||
- (void)handlePortMessage:(NSPortMessage *)portMessage
|
||||
- (BOOL) idle
|
||||
{
|
||||
NSInteger message = (NSInteger)[portMessage msgid];
|
||||
OSSpinLockLock(&spinlockIdle);
|
||||
const BOOL theState = _idleState;
|
||||
OSSpinLockUnlock(&spinlockIdle);
|
||||
|
||||
switch (message)
|
||||
return theState;
|
||||
}
|
||||
|
||||
- (void) createThread
|
||||
{
|
||||
pthread_mutex_init(&_mutexMessageLoop, NULL);
|
||||
pthread_cond_init(&_condSignalMessage, NULL);
|
||||
pthread_create(&_pthread, NULL, &RunOutputThread, self);
|
||||
}
|
||||
|
||||
- (void) exitThread
|
||||
{
|
||||
pthread_mutex_lock(&_mutexMessageLoop);
|
||||
|
||||
if (_pthread != NULL)
|
||||
{
|
||||
_threadMessageID = MESSAGE_NONE;
|
||||
pthread_mutex_unlock(&_mutexMessageLoop);
|
||||
|
||||
pthread_cancel(_pthread);
|
||||
pthread_join(_pthread, NULL);
|
||||
_pthread = NULL;
|
||||
|
||||
pthread_cond_destroy(&_condSignalMessage);
|
||||
pthread_mutex_destroy(&_mutexMessageLoop);
|
||||
}
|
||||
else
|
||||
{
|
||||
pthread_mutex_unlock(&_mutexMessageLoop);
|
||||
}
|
||||
}
|
||||
|
||||
- (void) runMessageLoop
|
||||
{
|
||||
pthread_mutex_lock(&_mutexMessageLoop);
|
||||
|
||||
do
|
||||
{
|
||||
while (_threadMessageID == MESSAGE_NONE)
|
||||
{
|
||||
pthread_cond_wait(&_condSignalMessage, &_mutexMessageLoop);
|
||||
}
|
||||
|
||||
[self handleSignalMessageID:_threadMessageID];
|
||||
_threadMessageID = MESSAGE_NONE;
|
||||
|
||||
} while(true);
|
||||
}
|
||||
|
||||
- (void) signalMessage:(int32_t)messageID
|
||||
{
|
||||
pthread_mutex_lock(&_mutexMessageLoop);
|
||||
|
||||
_threadMessageID = messageID;
|
||||
pthread_cond_signal(&_condSignalMessage);
|
||||
|
||||
pthread_mutex_unlock(&_mutexMessageLoop);
|
||||
}
|
||||
|
||||
- (void) handleSignalMessageID:(int32_t)messageID
|
||||
{
|
||||
switch (messageID)
|
||||
{
|
||||
case MESSAGE_EMU_FRAME_PROCESSED:
|
||||
[self handleEmuFrameProcessed];
|
||||
break;
|
||||
|
||||
default:
|
||||
[super handlePortMessage:portMessage];
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -102,6 +163,11 @@
|
|||
// The base method does nothing.
|
||||
}
|
||||
|
||||
- (void) doCoreEmuFrame
|
||||
{
|
||||
[self signalMessage:MESSAGE_EMU_FRAME_PROCESSED];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation CocoaDSSpeaker
|
||||
|
@ -417,79 +483,6 @@
|
|||
return theString;
|
||||
}
|
||||
|
||||
- (void)handlePortMessage:(NSPortMessage*)portMessage
|
||||
{
|
||||
NSInteger message = (NSInteger)[portMessage msgid];
|
||||
NSArray *messageComponents = [portMessage components];
|
||||
|
||||
switch (message)
|
||||
{
|
||||
case MESSAGE_SET_AUDIO_PROCESS_METHOD:
|
||||
[self handleSetAudioOutputEngine:[messageComponents objectAtIndex:0]];
|
||||
break;
|
||||
|
||||
case MESSAGE_SET_SPU_ADVANCED_LOGIC:
|
||||
[self handleSetSpuAdvancedLogic:[messageComponents objectAtIndex:0]];
|
||||
break;
|
||||
|
||||
case MESSAGE_SET_SPU_SYNC_MODE:
|
||||
[self handleSetSpuSyncMode:[messageComponents objectAtIndex:0]];
|
||||
break;
|
||||
|
||||
case MESSAGE_SET_SPU_SYNC_METHOD:
|
||||
[self handleSetSpuSyncMethod:[messageComponents objectAtIndex:0]];
|
||||
break;
|
||||
|
||||
case MESSAGE_SET_SPU_INTERPOLATION_MODE:
|
||||
[self handleSetSpuInterpolationMode:[messageComponents objectAtIndex:0]];
|
||||
break;
|
||||
|
||||
case MESSAGE_SET_VOLUME:
|
||||
[self handleSetVolume:[messageComponents objectAtIndex:0]];
|
||||
break;
|
||||
|
||||
default:
|
||||
[super handlePortMessage:portMessage];
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
- (void) handleSetVolume:(NSData *)volumeData
|
||||
{
|
||||
const float vol = *(float *)[volumeData bytes];
|
||||
[self setVolume:vol];
|
||||
}
|
||||
|
||||
- (void) handleSetAudioOutputEngine:(NSData *)methodIdData
|
||||
{
|
||||
const NSInteger methodID = *(NSInteger *)[methodIdData bytes];
|
||||
[self setAudioOutputEngine:methodID];
|
||||
}
|
||||
|
||||
- (void) handleSetSpuAdvancedLogic:(NSData *)stateData
|
||||
{
|
||||
const BOOL theState = *(BOOL *)[stateData bytes];
|
||||
[self setSpuAdvancedLogic:theState];
|
||||
}
|
||||
|
||||
- (void) handleSetSpuSyncMode:(NSData *)modeIdData
|
||||
{
|
||||
const NSInteger modeID = *(NSInteger *)[modeIdData bytes];
|
||||
[self setSpuSyncMode:modeID];
|
||||
}
|
||||
|
||||
- (void) handleSetSpuSyncMethod:(NSData *)methodIdData
|
||||
{
|
||||
const NSInteger methodID = *(NSInteger *)[methodIdData bytes];
|
||||
[self setSpuSyncMethod:methodID];
|
||||
}
|
||||
|
||||
- (void) handleSetSpuInterpolationMode:(NSData *)modeIdData
|
||||
{
|
||||
const NSInteger modeID = *(NSInteger *)[modeIdData bytes];
|
||||
[self setSpuInterpolationMode:modeID];
|
||||
}
|
||||
|
||||
@end
|
||||
|
||||
@implementation CocoaDSDisplay
|
||||
|
@ -511,6 +504,8 @@
|
|||
_currentReceivedFrameIndex = 0;
|
||||
_receivedFrameCount = 0;
|
||||
|
||||
[self createThread];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
|
@ -519,18 +514,16 @@
|
|||
[super dealloc];
|
||||
}
|
||||
|
||||
- (void)handlePortMessage:(NSPortMessage *)portMessage
|
||||
- (void) handleSignalMessageID:(int32_t)messageID
|
||||
{
|
||||
NSInteger message = (NSInteger)[portMessage msgid];
|
||||
|
||||
switch (message)
|
||||
switch (messageID)
|
||||
{
|
||||
case MESSAGE_RECEIVE_GPU_FRAME:
|
||||
[self handleReceiveGPUFrame];
|
||||
break;
|
||||
|
||||
|
||||
default:
|
||||
[super handlePortMessage:portMessage];
|
||||
[super handleSignalMessageID:messageID];
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -1109,11 +1102,9 @@
|
|||
return filterID;
|
||||
}
|
||||
|
||||
- (void)handlePortMessage:(NSPortMessage *)portMessage
|
||||
- (void) handleSignalMessageID:(int32_t)messageID
|
||||
{
|
||||
NSInteger message = (NSInteger)[portMessage msgid];
|
||||
|
||||
switch (message)
|
||||
switch (messageID)
|
||||
{
|
||||
case MESSAGE_CHANGE_VIEW_PROPERTIES:
|
||||
[self handleChangeViewProperties];
|
||||
|
@ -1136,7 +1127,7 @@
|
|||
break;
|
||||
|
||||
default:
|
||||
[super handlePortMessage:portMessage];
|
||||
[super handleSignalMessageID:messageID];
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -1256,3 +1247,11 @@
|
|||
}
|
||||
|
||||
@end
|
||||
|
||||
static void* RunOutputThread(void *arg)
|
||||
{
|
||||
CocoaDSOutput *cdsDisplayOutput = (CocoaDSOutput *)arg;
|
||||
[cdsDisplayOutput runMessageLoop];
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (C) 2011 Roger Manuel
|
||||
Copyright (C) 2012-2017 DeSmuME team
|
||||
Copyright (C) 2012-2018 DeSmuME team
|
||||
|
||||
This file is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
|
@ -31,13 +31,6 @@
|
|||
|
||||
}
|
||||
|
||||
+ (void) messageSendOneWay:(NSPort *)sendPort msgID:(NSInteger)msgID;
|
||||
+ (void) messageSendOneWayWithMessageComponents:(NSPort *)sendPort msgID:(NSInteger)msgID array:(NSArray *)msgDataArray;
|
||||
+ (void) messageSendOneWayWithData:(NSPort *)sendPort msgID:(NSInteger)msgID data:(NSData *)msgData;
|
||||
+ (void) messageSendOneWayWithInteger:(NSPort *)sendPort msgID:(NSInteger)msgID integerValue:(NSInteger)integerValue;
|
||||
+ (void) messageSendOneWayWithFloat:(NSPort *)sendPort msgID:(NSInteger)msgID floatValue:(float)floatValue;
|
||||
+ (void) messageSendOneWayWithBool:(NSPort *)sendPort msgID:(NSInteger)msgID boolValue:(BOOL)boolValue;
|
||||
+ (void) messageSendOneWayWithRect:(NSPort *)sendPort msgID:(NSInteger)msgID rect:(NSRect)rect;
|
||||
+ (NSInteger) getIBActionSenderTag:(id)sender;
|
||||
+ (BOOL) getIBActionSenderButtonStateBool:(id)sender;
|
||||
|
||||
|
@ -54,39 +47,6 @@
|
|||
|
||||
@end
|
||||
|
||||
#if MAC_OS_X_VERSION_MAX_ALLOWED > MAC_OS_X_VERSION_10_4
|
||||
|
||||
#if MAC_OS_X_VERSION_MAX_ALLOWED > MAC_OS_X_VERSION_10_5
|
||||
@interface CocoaDSThread : NSObject <NSPortDelegate>
|
||||
#else
|
||||
@interface CocoaDSThread : NSObject
|
||||
#endif
|
||||
{
|
||||
NSThread *thread;
|
||||
BOOL threadExit;
|
||||
BOOL _idleState;
|
||||
NSTimeInterval autoreleaseInterval;
|
||||
NSPort *sendPort;
|
||||
NSPort *receivePort;
|
||||
|
||||
OSSpinLock spinlockIdle;
|
||||
}
|
||||
|
||||
@property (assign) NSThread *thread;
|
||||
@property (assign) BOOL threadExit;
|
||||
@property (assign) BOOL idle;
|
||||
@property (assign) NSTimeInterval autoreleaseInterval;
|
||||
@property (assign) NSPort *sendPort;
|
||||
@property (assign) NSPort *receivePort;
|
||||
|
||||
- (id) initWithAutoreleaseInterval:(NSTimeInterval)interval;
|
||||
- (void) runThread:(id)object;
|
||||
- (void) forceThreadExit;
|
||||
|
||||
@end
|
||||
|
||||
#endif
|
||||
|
||||
@protocol DirectoryURLDragDestTextFieldProtocol <NSObject>
|
||||
|
||||
@required
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*
|
||||
Copyright (C) 2011 Roger Manuel
|
||||
Copyright (C) 2012-2017 DeSmuME team
|
||||
Copyright (C) 2012-2018 DeSmuME team
|
||||
|
||||
This file is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
|
@ -30,94 +30,6 @@
|
|||
|
||||
@implementation CocoaDSUtil
|
||||
|
||||
static NSDate *distantFutureDate = [[NSDate distantFuture] retain];
|
||||
|
||||
+ (void) messageSendOneWay:(NSPort *)sendPort msgID:(NSInteger)msgID
|
||||
{
|
||||
if (sendPort == nil || ![sendPort isValid])
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
NSPortMessage *message = [[NSPortMessage alloc] initWithSendPort:sendPort receivePort:nil components:nil];
|
||||
[message setMsgid:msgID];
|
||||
[message sendBeforeDate:distantFutureDate];
|
||||
[message release];
|
||||
}
|
||||
|
||||
+ (void) messageSendOneWayWithMessageComponents:(NSPort *)sendPort msgID:(NSInteger)msgID array:(NSArray *)msgDataArray
|
||||
{
|
||||
if (sendPort == nil || ![sendPort isValid])
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
NSPortMessage *message = [[NSPortMessage alloc] initWithSendPort:sendPort receivePort:nil components:msgDataArray];
|
||||
[message setMsgid:msgID];
|
||||
[message sendBeforeDate:distantFutureDate];
|
||||
[message release];
|
||||
}
|
||||
|
||||
+ (void) messageSendOneWayWithData:(NSPort *)sendPort msgID:(NSInteger)msgID data:(NSData *)msgData
|
||||
{
|
||||
if (sendPort == nil || ![sendPort isValid])
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
NSArray *messageComponents = [[NSArray alloc] initWithObjects:msgData, nil];
|
||||
[CocoaDSUtil messageSendOneWayWithMessageComponents:sendPort msgID:msgID array:messageComponents];
|
||||
[messageComponents release];
|
||||
}
|
||||
|
||||
+ (void) messageSendOneWayWithInteger:(NSPort *)sendPort msgID:(NSInteger)msgID integerValue:(NSInteger)integerValue
|
||||
{
|
||||
if (sendPort == nil || ![sendPort isValid])
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
NSData *messageData = [[NSData alloc] initWithBytes:&integerValue length:sizeof(NSInteger)];
|
||||
[CocoaDSUtil messageSendOneWayWithData:sendPort msgID:msgID data:messageData];
|
||||
[messageData release];
|
||||
}
|
||||
|
||||
+ (void) messageSendOneWayWithFloat:(NSPort *)sendPort msgID:(NSInteger)msgID floatValue:(float)floatValue
|
||||
{
|
||||
if (sendPort == nil || ![sendPort isValid])
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
NSData *messageData = [[NSData alloc] initWithBytes:&floatValue length:sizeof(float)];
|
||||
[CocoaDSUtil messageSendOneWayWithData:sendPort msgID:msgID data:messageData];
|
||||
[messageData release];
|
||||
}
|
||||
|
||||
+ (void) messageSendOneWayWithBool:(NSPort *)sendPort msgID:(NSInteger)msgID boolValue:(BOOL)boolValue
|
||||
{
|
||||
if (sendPort == nil || ![sendPort isValid])
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
NSData *messageData = [[NSData alloc] initWithBytes:&boolValue length:sizeof(BOOL)];
|
||||
[CocoaDSUtil messageSendOneWayWithData:sendPort msgID:msgID data:messageData];
|
||||
[messageData release];
|
||||
}
|
||||
|
||||
+ (void) messageSendOneWayWithRect:(NSPort *)sendPort msgID:(NSInteger)msgID rect:(NSRect)rect
|
||||
{
|
||||
if (sendPort == nil || ![sendPort isValid])
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
NSData *messageData = [[NSData alloc] initWithBytes:&rect length:sizeof(NSRect)];
|
||||
[CocoaDSUtil messageSendOneWayWithData:sendPort msgID:msgID data:messageData];
|
||||
[messageData release];
|
||||
}
|
||||
|
||||
+ (NSInteger) getIBActionSenderTag:(id)sender
|
||||
{
|
||||
NSInteger senderTag = 0;
|
||||
|
@ -253,129 +165,6 @@ static NSDate *distantFutureDate = [[NSDate distantFuture] retain];
|
|||
|
||||
@end
|
||||
|
||||
#if MAC_OS_X_VERSION_MAX_ALLOWED > MAC_OS_X_VERSION_10_4
|
||||
@implementation CocoaDSThread
|
||||
|
||||
@synthesize thread;
|
||||
@synthesize threadExit;
|
||||
@dynamic idle;
|
||||
@synthesize autoreleaseInterval;
|
||||
@synthesize sendPort;
|
||||
@synthesize receivePort;
|
||||
|
||||
- (id)init
|
||||
{
|
||||
return [self initWithAutoreleaseInterval:15.0];
|
||||
}
|
||||
|
||||
- (id) initWithAutoreleaseInterval:(NSTimeInterval)interval
|
||||
{
|
||||
// Set up thread info.
|
||||
thread = nil;
|
||||
threadExit = NO;
|
||||
_idleState = NO;
|
||||
autoreleaseInterval = interval;
|
||||
|
||||
spinlockIdle = OS_SPINLOCK_INIT;
|
||||
|
||||
// Set up thread ports.
|
||||
sendPort = [[NSPort port] retain];
|
||||
[sendPort setDelegate:self];
|
||||
receivePort = [[NSPort port] retain];
|
||||
[receivePort setDelegate:self];
|
||||
|
||||
return self;
|
||||
}
|
||||
|
||||
- (void)dealloc
|
||||
{
|
||||
[self forceThreadExit];
|
||||
|
||||
[super dealloc];
|
||||
}
|
||||
|
||||
- (void) setIdle:(BOOL)theState
|
||||
{
|
||||
OSSpinLockLock(&spinlockIdle);
|
||||
_idleState = theState;
|
||||
OSSpinLockUnlock(&spinlockIdle);
|
||||
}
|
||||
|
||||
- (BOOL) idle
|
||||
{
|
||||
OSSpinLockLock(&spinlockIdle);
|
||||
const BOOL theState = _idleState;
|
||||
OSSpinLockUnlock(&spinlockIdle);
|
||||
|
||||
return theState;
|
||||
}
|
||||
|
||||
- (void) runThread:(id)object
|
||||
{
|
||||
NSAutoreleasePool *threadPool = [[NSAutoreleasePool alloc] init];
|
||||
NSRunLoop *runLoop = [NSRunLoop currentRunLoop];
|
||||
|
||||
[runLoop addPort:[self receivePort] forMode:NSDefaultRunLoopMode];
|
||||
[self setThread:[NSThread currentThread]];
|
||||
|
||||
do
|
||||
{
|
||||
NSAutoreleasePool *runLoopPool = [[NSAutoreleasePool alloc] init];
|
||||
NSDate *runDate = [[NSDate alloc] initWithTimeIntervalSinceNow:[self autoreleaseInterval]];
|
||||
[runLoop runUntilDate:runDate];
|
||||
[runDate release];
|
||||
[runLoopPool release];
|
||||
} while (![self threadExit]);
|
||||
|
||||
NSPort *tempSendPort = [self sendPort];
|
||||
[self setSendPort:nil];
|
||||
[tempSendPort invalidate];
|
||||
[tempSendPort release];
|
||||
|
||||
NSPort *tempReceivePort = [self receivePort];
|
||||
[self setReceivePort:nil];
|
||||
[tempReceivePort invalidate];
|
||||
[tempReceivePort release];
|
||||
|
||||
[threadPool release];
|
||||
[self setThread:nil];
|
||||
}
|
||||
|
||||
- (void) forceThreadExit
|
||||
{
|
||||
if ([self thread] == nil)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
[self setThreadExit:YES];
|
||||
[self setIdle:NO];
|
||||
|
||||
// Wait until the thread has shut down.
|
||||
while ([self thread] != nil)
|
||||
{
|
||||
[NSThread sleepUntilDate:[NSDate dateWithTimeIntervalSinceNow:0.01]];
|
||||
}
|
||||
}
|
||||
|
||||
- (void)handlePortMessage:(NSPortMessage *)portMessage
|
||||
{
|
||||
NSInteger message = (NSInteger)[portMessage msgid];
|
||||
|
||||
switch (message)
|
||||
{
|
||||
case MESSAGE_EXIT_THREAD:
|
||||
[self setThreadExit:YES];
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@end
|
||||
#endif
|
||||
|
||||
@implementation DirectoryURLDragDestTextField
|
||||
|
||||
- (id)initWithCoder:(NSCoder *)coder
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
Copyright (C) 2013-2017 DeSmuME team
|
||||
Copyright (C) 2013-2018 DeSmuME team
|
||||
|
||||
This file is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
|
@ -698,7 +698,7 @@ static std::unordered_map<NSScreen *, DisplayWindowController *> _screenMap; //
|
|||
|
||||
- (IBAction) copy:(id)sender
|
||||
{
|
||||
[CocoaDSUtil messageSendOneWay:[[[self view] cdsVideoOutput] receivePort] msgID:MESSAGE_COPY_TO_PASTEBOARD];
|
||||
[[[self view] cdsVideoOutput] signalMessage:MESSAGE_COPY_TO_PASTEBOARD];
|
||||
}
|
||||
|
||||
- (IBAction) changeHardwareMicGain:(id)sender
|
||||
|
@ -1311,12 +1311,6 @@ static std::unordered_map<NSScreen *, DisplayWindowController *> _screenMap; //
|
|||
// Add the video thread to the output list.
|
||||
[emuControl addOutputToCore:newDisplayOutput];
|
||||
|
||||
[NSThread detachNewThreadSelector:@selector(runThread:) toTarget:newDisplayOutput withObject:nil];
|
||||
while ([newDisplayOutput thread] == nil)
|
||||
{
|
||||
[NSThread sleepUntilDate:[NSDate dateWithTimeIntervalSinceNow:0.01]];
|
||||
}
|
||||
|
||||
// Setup default values per user preferences.
|
||||
[self setupUserDefaults];
|
||||
}
|
||||
|
@ -1449,7 +1443,6 @@ static std::unordered_map<NSScreen *, DisplayWindowController *> _screenMap; //
|
|||
- (void)windowWillClose:(NSNotification *)notification
|
||||
{
|
||||
[emuControl removeOutputFromCore:[[self view] cdsVideoOutput]];
|
||||
[[[self view] cdsVideoOutput] forceThreadExit];
|
||||
|
||||
[[emuControl windowList] removeObject:self];
|
||||
|
||||
|
@ -1946,7 +1939,7 @@ static std::unordered_map<NSScreen *, DisplayWindowController *> _screenMap; //
|
|||
- (void) setDisplayMainVideoSource:(NSInteger)displaySourceID
|
||||
{
|
||||
[[self cdsVideoOutput] setDisplayMainVideoSource:displaySourceID];
|
||||
[CocoaDSUtil messageSendOneWay:[[self cdsVideoOutput] receivePort] msgID:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
[[self cdsVideoOutput] signalMessage:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
}
|
||||
|
||||
- (NSInteger) displayMainVideoSource
|
||||
|
@ -1957,7 +1950,7 @@ static std::unordered_map<NSScreen *, DisplayWindowController *> _screenMap; //
|
|||
- (void) setDisplayTouchVideoSource:(NSInteger)displaySourceID
|
||||
{
|
||||
[[self cdsVideoOutput] setDisplayTouchVideoSource:displaySourceID];
|
||||
[CocoaDSUtil messageSendOneWay:[[self cdsVideoOutput] receivePort] msgID:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
[[self cdsVideoOutput] signalMessage:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
}
|
||||
|
||||
- (NSInteger) displayTouchVideoSource
|
||||
|
@ -1997,7 +1990,7 @@ static std::unordered_map<NSScreen *, DisplayWindowController *> _screenMap; //
|
|||
[macSharedData decrementViewsUsingDirectToCPUFiltering];
|
||||
}
|
||||
|
||||
[CocoaDSUtil messageSendOneWay:[[self cdsVideoOutput] receivePort] msgID:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
[[self cdsVideoOutput] signalMessage:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2029,7 +2022,7 @@ static std::unordered_map<NSScreen *, DisplayWindowController *> _screenMap; //
|
|||
}
|
||||
}
|
||||
|
||||
[CocoaDSUtil messageSendOneWay:[[self cdsVideoOutput] receivePort] msgID:MESSAGE_REPROCESS_AND_REDRAW];
|
||||
[[self cdsVideoOutput] signalMessage:MESSAGE_REPROCESS_AND_REDRAW];
|
||||
}
|
||||
|
||||
- (BOOL) sourceDeposterize
|
||||
|
@ -2040,7 +2033,7 @@ static std::unordered_map<NSScreen *, DisplayWindowController *> _screenMap; //
|
|||
- (void) setOutputFilter:(NSInteger)filterID
|
||||
{
|
||||
[[self cdsVideoOutput] setOutputFilter:filterID];
|
||||
[CocoaDSUtil messageSendOneWay:[[self cdsVideoOutput] receivePort] msgID:MESSAGE_REDRAW_VIEW];
|
||||
[[self cdsVideoOutput] signalMessage:MESSAGE_REDRAW_VIEW];
|
||||
}
|
||||
|
||||
- (NSInteger) outputFilter
|
||||
|
@ -2071,7 +2064,7 @@ static std::unordered_map<NSScreen *, DisplayWindowController *> _screenMap; //
|
|||
}
|
||||
}
|
||||
|
||||
[CocoaDSUtil messageSendOneWay:[[self cdsVideoOutput] receivePort] msgID:MESSAGE_REPROCESS_AND_REDRAW];
|
||||
[[self cdsVideoOutput] signalMessage:MESSAGE_REPROCESS_AND_REDRAW];
|
||||
}
|
||||
|
||||
- (NSInteger) pixelScaler
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
Copyright (C) 2013-2017 DeSmuME Team
|
||||
Copyright (C) 2013-2018 DeSmuME Team
|
||||
|
||||
This file is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
|
@ -1464,7 +1464,7 @@
|
|||
|
||||
for (DisplayWindowController *windowController in windowList)
|
||||
{
|
||||
[CocoaDSUtil messageSendOneWay:[[[windowController view] cdsVideoOutput] receivePort] msgID:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
[[[windowController view] cdsVideoOutput] signalMessage:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
}
|
||||
|
||||
[self setStatusText:NSSTRING_STATUS_EMULATOR_RESET];
|
||||
|
@ -1762,7 +1762,7 @@
|
|||
|
||||
for (DisplayWindowController *windowController in windowList)
|
||||
{
|
||||
[CocoaDSUtil messageSendOneWay:[[[windowController view] cdsVideoOutput] receivePort] msgID:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
[[[windowController view] cdsVideoOutput] signalMessage:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
}
|
||||
|
||||
[self setStatusText:NSSTRING_STATUS_ROM_LOADED];
|
||||
|
@ -1845,7 +1845,7 @@
|
|||
[[cdsCore cdsGPU] clearWithColor:0x8000];
|
||||
for (DisplayWindowController *windowController in windowList)
|
||||
{
|
||||
[CocoaDSUtil messageSendOneWay:[[[windowController view] cdsVideoOutput] receivePort] msgID:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
[[[windowController view] cdsVideoOutput] signalMessage:MESSAGE_RELOAD_REPROCESS_REDRAW];
|
||||
}
|
||||
|
||||
[self setStatusText:NSSTRING_STATUS_ROM_UNLOADED];
|
||||
|
|
|
@ -505,6 +505,7 @@ void MacOGLDisplayView::SetViewNeedsFlush()
|
|||
if (this->GetRenderToCALayer())
|
||||
{
|
||||
[this->_caLayer setNeedsDisplay];
|
||||
[CATransaction flush];
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue