fix api errors

This commit is contained in:
Taner Sener 2021-02-18 23:44:51 +00:00
parent 1294183928
commit 21821a8a51
14 changed files with 105 additions and 60 deletions

View File

@ -269,7 +269,7 @@ public class FFmpegKit {
* @param command string command * @param command string command
* @return array of arguments * @return array of arguments
*/ */
static String[] parseArguments(final String command) { public static String[] parseArguments(final String command) {
final List<String> argumentList = new ArrayList<>(); final List<String> argumentList = new ArrayList<>();
StringBuilder currentArgument = new StringBuilder(); StringBuilder currentArgument = new StringBuilder();
@ -326,7 +326,7 @@ public class FFmpegKit {
* @param arguments arguments * @param arguments arguments
* @return concatenated string containing all arguments * @return concatenated string containing all arguments
*/ */
static String argumentsToString(final String[] arguments) { public static String argumentsToString(final String[] arguments) {
if (arguments == null) { if (arguments == null) {
return "null"; return "null";
} }

View File

@ -664,6 +664,8 @@ public class FFmpegKitConfig {
* @param ffmpegSession FFmpeg session which includes command options/arguments * @param ffmpegSession FFmpeg session which includes command options/arguments
*/ */
public static void asyncFFmpegExecute(final FFmpegSession ffmpegSession) { public static void asyncFFmpegExecute(final FFmpegSession ffmpegSession) {
addSession(ffmpegSession);
AsyncFFmpegExecuteTask asyncFFmpegExecuteTask = new AsyncFFmpegExecuteTask(ffmpegSession); AsyncFFmpegExecuteTask asyncFFmpegExecuteTask = new AsyncFFmpegExecuteTask(ffmpegSession);
Future<?> future = asyncExecutorService.submit(asyncFFmpegExecuteTask); Future<?> future = asyncExecutorService.submit(asyncFFmpegExecuteTask);
ffmpegSession.setFuture(future); ffmpegSession.setFuture(future);
@ -676,6 +678,8 @@ public class FFmpegKitConfig {
* @param executorService executor service that will be used to run this asynchronous operation * @param executorService executor service that will be used to run this asynchronous operation
*/ */
public static void asyncFFmpegExecute(final FFmpegSession ffmpegSession, final ExecutorService executorService) { public static void asyncFFmpegExecute(final FFmpegSession ffmpegSession, final ExecutorService executorService) {
addSession(ffmpegSession);
AsyncFFmpegExecuteTask asyncFFmpegExecuteTask = new AsyncFFmpegExecuteTask(ffmpegSession); AsyncFFmpegExecuteTask asyncFFmpegExecuteTask = new AsyncFFmpegExecuteTask(ffmpegSession);
Future<?> future = executorService.submit(asyncFFmpegExecuteTask); Future<?> future = executorService.submit(asyncFFmpegExecuteTask);
ffmpegSession.setFuture(future); ffmpegSession.setFuture(future);
@ -687,6 +691,8 @@ public class FFmpegKitConfig {
* @param ffprobeSession FFprobe session which includes command options/arguments * @param ffprobeSession FFprobe session which includes command options/arguments
*/ */
public static void asyncFFprobeExecute(final FFprobeSession ffprobeSession) { public static void asyncFFprobeExecute(final FFprobeSession ffprobeSession) {
addSession(ffprobeSession);
AsyncFFprobeExecuteTask asyncFFmpegExecuteTask = new AsyncFFprobeExecuteTask(ffprobeSession); AsyncFFprobeExecuteTask asyncFFmpegExecuteTask = new AsyncFFprobeExecuteTask(ffprobeSession);
Future<?> future = asyncExecutorService.submit(asyncFFmpegExecuteTask); Future<?> future = asyncExecutorService.submit(asyncFFmpegExecuteTask);
ffprobeSession.setFuture(future); ffprobeSession.setFuture(future);
@ -699,6 +705,8 @@ public class FFmpegKitConfig {
* @param executorService executor service that will be used to run this asynchronous operation * @param executorService executor service that will be used to run this asynchronous operation
*/ */
public static void asyncFFprobeExecute(final FFprobeSession ffprobeSession, final ExecutorService executorService) { public static void asyncFFprobeExecute(final FFprobeSession ffprobeSession, final ExecutorService executorService) {
addSession(ffprobeSession);
AsyncFFprobeExecuteTask asyncFFmpegExecuteTask = new AsyncFFprobeExecuteTask(ffprobeSession); AsyncFFprobeExecuteTask asyncFFmpegExecuteTask = new AsyncFFprobeExecuteTask(ffprobeSession);
Future<?> future = executorService.submit(asyncFFmpegExecuteTask); Future<?> future = executorService.submit(asyncFFmpegExecuteTask);
ffprobeSession.setFuture(future); ffprobeSession.setFuture(future);
@ -711,6 +719,8 @@ public class FFmpegKitConfig {
* @param waitTimeout max time to wait until media information is transmitted * @param waitTimeout max time to wait until media information is transmitted
*/ */
public static void asyncGetMediaInformationExecute(final MediaInformationSession mediaInformationSession, final int waitTimeout) { public static void asyncGetMediaInformationExecute(final MediaInformationSession mediaInformationSession, final int waitTimeout) {
addSession(mediaInformationSession);
AsyncGetMediaInformationTask asyncGetMediaInformationTask = new AsyncGetMediaInformationTask(mediaInformationSession, waitTimeout); AsyncGetMediaInformationTask asyncGetMediaInformationTask = new AsyncGetMediaInformationTask(mediaInformationSession, waitTimeout);
Future<?> future = asyncExecutorService.submit(asyncGetMediaInformationTask); Future<?> future = asyncExecutorService.submit(asyncGetMediaInformationTask);
mediaInformationSession.setFuture(future); mediaInformationSession.setFuture(future);
@ -724,6 +734,8 @@ public class FFmpegKitConfig {
* @param waitTimeout max time to wait until media information is transmitted * @param waitTimeout max time to wait until media information is transmitted
*/ */
public static void asyncGetMediaInformationExecute(final MediaInformationSession mediaInformationSession, final ExecutorService executorService, final int waitTimeout) { public static void asyncGetMediaInformationExecute(final MediaInformationSession mediaInformationSession, final ExecutorService executorService, final int waitTimeout) {
addSession(mediaInformationSession);
AsyncGetMediaInformationTask asyncGetMediaInformationTask = new AsyncGetMediaInformationTask(mediaInformationSession, waitTimeout); AsyncGetMediaInformationTask asyncGetMediaInformationTask = new AsyncGetMediaInformationTask(mediaInformationSession, waitTimeout);
Future<?> future = executorService.submit(asyncGetMediaInformationTask); Future<?> future = executorService.submit(asyncGetMediaInformationTask);
mediaInformationSession.setFuture(future); mediaInformationSession.setFuture(future);
@ -936,12 +948,20 @@ public class FFmpegKitConfig {
*/ */
static void addSession(final Session session) { static void addSession(final Session session) {
synchronized (sessionHistoryLock) { synchronized (sessionHistoryLock) {
sessionHistoryMap.put(session.getSessionId(), session);
sessionHistoryList.add(session); /*
if (sessionHistoryList.size() > sessionHistorySize) { * ASYNC SESSIONS CALL THIS METHOD TWICE
try { * THIS CHECK PREVENTS ADDING THE SAME SESSION TWICE
sessionHistoryList.remove(0); */
} catch (final IndexOutOfBoundsException ignored) { final boolean sessionAlreadyAdded = sessionHistoryMap.containsKey(session.getSessionId());
if (!sessionAlreadyAdded) {
sessionHistoryMap.put(session.getSessionId(), session);
sessionHistoryList.add(session);
if (sessionHistoryList.size() > sessionHistorySize) {
try {
sessionHistoryList.remove(0);
} catch (final IndexOutOfBoundsException ignored) {
}
} }
} }
} }

View File

@ -50,9 +50,9 @@ public class FFprobeSession extends AbstractSession implements Session {
* @param executeCallback session specific execute callback function * @param executeCallback session specific execute callback function
* @param logCallback session specific log callback function * @param logCallback session specific log callback function
*/ */
FFprobeSession(final String[] arguments, public FFprobeSession(final String[] arguments,
final ExecuteCallback executeCallback, final ExecuteCallback executeCallback,
final LogCallback logCallback) { final LogCallback logCallback) {
this(arguments, executeCallback, logCallback, FFmpegKitConfig.getLogRedirectionStrategy()); this(arguments, executeCallback, logCallback, FFmpegKitConfig.getLogRedirectionStrategy());
} }
@ -64,10 +64,10 @@ public class FFprobeSession extends AbstractSession implements Session {
* @param logCallback session specific log callback function * @param logCallback session specific log callback function
* @param logRedirectionStrategy session specific log redirection strategy * @param logRedirectionStrategy session specific log redirection strategy
*/ */
FFprobeSession(final String[] arguments, public FFprobeSession(final String[] arguments,
final ExecuteCallback executeCallback, final ExecuteCallback executeCallback,
final LogCallback logCallback, final LogCallback logCallback,
final LogRedirectionStrategy logRedirectionStrategy) { final LogRedirectionStrategy logRedirectionStrategy) {
super(arguments, executeCallback, logCallback, logRedirectionStrategy); super(arguments, executeCallback, logCallback, logRedirectionStrategy);
} }

View File

@ -52,7 +52,7 @@ static AtomicLong *sessionIdGenerator = nil;
- (instancetype)init:(NSArray*)arguments withExecuteCallback:(ExecuteCallback)executeCallback withLogCallback:(LogCallback)logCallback withLogRedirectionStrategy:(LogRedirectionStrategy)logRedirectionStrategy { - (instancetype)init:(NSArray*)arguments withExecuteCallback:(ExecuteCallback)executeCallback withLogCallback:(LogCallback)logCallback withLogRedirectionStrategy:(LogRedirectionStrategy)logRedirectionStrategy {
self = [super init]; self = [super init];
if (self) { if (self) {
_sessionId = [sessionIdGenerator incrementAndGet]; _sessionId = [sessionIdGenerator getAndIncrement];
_executeCallback = executeCallback; _executeCallback = executeCallback;
_logCallback = logCallback; _logCallback = logCallback;
_createTime = [NSDate date]; _createTime = [NSDate date];
@ -150,7 +150,7 @@ static AtomicLong *sessionIdGenerator = nil;
NSLog(@"getAllLogsAsStringWithTimeout was called to return all logs but there are still logs being transmitted for session id %ld.", _sessionId); NSLog(@"getAllLogsAsStringWithTimeout was called to return all logs but there are still logs being transmitted for session id %ld.", _sessionId);
} }
return [self getAllLogsAsString]; return [self getLogsAsString];
} }
- (NSString*)getAllLogsAsString { - (NSString*)getAllLogsAsString {

View File

@ -17,48 +17,28 @@
* along with FFmpegKit. If not, see <http://www.gnu.org/licenses/>. * along with FFmpegKit. If not, see <http://www.gnu.org/licenses/>.
*/ */
#import <stdatomic.h>
#import "AtomicLong.h" #import "AtomicLong.h"
@interface AtomicLong()
@property (strong) NSRecursiveLock* lock;
@end
@implementation AtomicLong { @implementation AtomicLong {
long _value; atomic_int _value;
} }
- (instancetype)initWithValue:(long)value { - (instancetype)initWithValue:(long)value {
self = [super init]; self = [super init];
if (self) { if (self) {
_value = value; atomic_init(&_value, value);
_lock = [[NSRecursiveLock alloc] init];
} }
return self; return self;
} }
- (long)incrementAndGet { - (long)incrementAndGet {
long returnValue; return (long)atomic_fetch_add(&_value, 1) + 1;
[self.lock lock];
_value += 1;
returnValue = _value;
[self.lock unlock];
return returnValue;
} }
- (long)getAndIncrement { - (long)getAndIncrement {
long returnValue; return (long)atomic_fetch_add(&_value, 1);
[self.lock lock];
returnValue = _value;
_value += 1;
[self.lock unlock];
return returnValue;
} }
@end @end

View File

@ -27,6 +27,8 @@
@implementation FFmpegKit @implementation FFmpegKit
+ (void)initialize { + (void)initialize {
NSLog(@"Loading ffmpeg-kit.\n");
[FFmpegKitConfig class]; [FFmpegKitConfig class];
NSLog(@"Loaded ffmpeg-kit-%@-%@-%@-%@\n", [Packages getPackageName], [ArchDetect getArch], [FFmpegKitConfig getVersion], [FFmpegKitConfig getBuildDate]); NSLog(@"Loaded ffmpeg-kit-%@-%@-%@-%@\n", [Packages getPackageName], [ArchDetect getArch], [FFmpegKitConfig getVersion], [FFmpegKitConfig getBuildDate]);

View File

@ -373,6 +373,14 @@ typedef NS_ENUM(NSUInteger, Signal) {
*/ */
+ (int)messagesInTransmit:(long)sessionId; + (int)messagesInTransmit:(long)sessionId;
/**
* Converts session state to string.
*
* @param state session state
* @return string value
*/
+ (NSString*)sessionStateToString:(SessionState)state;
@end @end
#endif // FFMPEG_KIT_CONFIG_H #endif // FFMPEG_KIT_CONFIG_H

View File

@ -894,6 +894,8 @@ int executeFFprobe(long sessionId, NSArray* arguments) {
} }
+ (void)asyncFFmpegExecute:(FFmpegSession*)ffmpegSession onDispatchQueue:(dispatch_queue_t)queue { + (void)asyncFFmpegExecute:(FFmpegSession*)ffmpegSession onDispatchQueue:(dispatch_queue_t)queue {
[FFmpegKitConfig addSession:ffmpegSession];
dispatch_async(queue, ^{ dispatch_async(queue, ^{
[FFmpegKitConfig ffmpegExecute:ffmpegSession]; [FFmpegKitConfig ffmpegExecute:ffmpegSession];
ExecuteCallback globalExecuteCallback = [FFmpegKitConfig getExecuteCallback]; ExecuteCallback globalExecuteCallback = [FFmpegKitConfig getExecuteCallback];
@ -913,6 +915,8 @@ int executeFFprobe(long sessionId, NSArray* arguments) {
} }
+ (void)asyncFFprobeExecute:(FFprobeSession*)ffprobeSession onDispatchQueue:(dispatch_queue_t)queue { + (void)asyncFFprobeExecute:(FFprobeSession*)ffprobeSession onDispatchQueue:(dispatch_queue_t)queue {
[FFmpegKitConfig addSession:ffprobeSession];
dispatch_async(queue, ^{ dispatch_async(queue, ^{
[FFmpegKitConfig ffprobeExecute:ffprobeSession]; [FFmpegKitConfig ffprobeExecute:ffprobeSession];
ExecuteCallback globalExecuteCallback = [FFmpegKitConfig getExecuteCallback]; ExecuteCallback globalExecuteCallback = [FFmpegKitConfig getExecuteCallback];
@ -932,6 +936,8 @@ int executeFFprobe(long sessionId, NSArray* arguments) {
} }
+ (void)asyncGetMediaInformationExecute:(MediaInformationSession*)mediaInformationSession onDispatchQueue:(dispatch_queue_t)queue withTimeout:(int)waitTimeout { + (void)asyncGetMediaInformationExecute:(MediaInformationSession*)mediaInformationSession onDispatchQueue:(dispatch_queue_t)queue withTimeout:(int)waitTimeout {
[FFmpegKitConfig addSession:mediaInformationSession];
dispatch_async(queue, ^{ dispatch_async(queue, ^{
[FFmpegKitConfig getMediaInformationExecute:mediaInformationSession withTimeout:waitTimeout]; [FFmpegKitConfig getMediaInformationExecute:mediaInformationSession withTimeout:waitTimeout];
ExecuteCallback globalExecuteCallback = [FFmpegKitConfig getExecuteCallback]; ExecuteCallback globalExecuteCallback = [FFmpegKitConfig getExecuteCallback];
@ -1003,16 +1009,24 @@ int executeFFprobe(long sessionId, NSArray* arguments) {
} }
+ (void)addSession:(id<Session>)session { + (void)addSession:(id<Session>)session {
NSNumber* sessionIdNumber = [NSNumber numberWithLong:[session getSessionId]];
[sessionHistoryLock lock]; [sessionHistoryLock lock];
[sessionHistoryMap setObject:session forKey:[NSNumber numberWithLong:[session getSessionId]]]; /*
[sessionHistoryList addObject:session]; * ASYNC SESSIONS CALL THIS METHOD TWICE
if ([sessionHistoryList count] > sessionHistorySize) { * THIS CHECK PREVENTS ADDING THE SAME SESSION TWICE
id<Session> first = [sessionHistoryList firstObject]; */
if (first != nil) { if ([sessionHistoryMap objectForKey:sessionIdNumber] == nil) {
NSNumber* key = [NSNumber numberWithLong:[first getSessionId]]; [sessionHistoryMap setObject:session forKey:sessionIdNumber];
[sessionHistoryList removeObject:key]; [sessionHistoryList addObject:session];
[sessionHistoryMap removeObjectForKey:key]; if ([sessionHistoryList count] > sessionHistorySize) {
id<Session> first = [sessionHistoryList firstObject];
if (first != nil) {
NSNumber* key = [NSNumber numberWithLong:[first getSessionId]];
[sessionHistoryList removeObject:key];
[sessionHistoryMap removeObjectForKey:key];
}
} }
} }
@ -1130,4 +1144,14 @@ int executeFFprobe(long sessionId, NSArray* arguments) {
return atomic_load(&sessionInTransitMessageCountMap[sessionId % SESSION_MAP_SIZE]); return atomic_load(&sessionInTransitMessageCountMap[sessionId % SESSION_MAP_SIZE]);
} }
+ (NSString*)sessionStateToString:(SessionState)state {
switch (state) {
case SessionStateCreated: return @"CREATED";
case SessionStateRunning: return @"RUNNING";
case SessionStateFailed: return @"FAILED";
case SessionStateCompleted: return @"COMPLETED";
default: return @"";
}
}
@end @end

View File

@ -29,6 +29,10 @@
NSRecursiveLock* _statisticsLock; NSRecursiveLock* _statisticsLock;
} }
+ (void)initialize {
// EMPTY INITIALIZE
}
- (instancetype)init:(NSArray*)arguments { - (instancetype)init:(NSArray*)arguments {
self = [super init:arguments withExecuteCallback:nil withLogCallback:nil withLogRedirectionStrategy:[FFmpegKitConfig getLogRedirectionStrategy]]; self = [super init:arguments withExecuteCallback:nil withLogCallback:nil withLogRedirectionStrategy:[FFmpegKitConfig getLogRedirectionStrategy]];

View File

@ -31,6 +31,10 @@
return self; return self;
} }
+ (void)initialize {
// EMPTY INITIALIZE
}
- (instancetype)init:(NSArray*)arguments withExecuteCallback:(ExecuteCallback)executeCallback { - (instancetype)init:(NSArray*)arguments withExecuteCallback:(ExecuteCallback)executeCallback {
self = [super init:arguments withExecuteCallback:executeCallback withLogCallback:nil withLogRedirectionStrategy:[FFmpegKitConfig getLogRedirectionStrategy]]; self = [super init:arguments withExecuteCallback:executeCallback withLogCallback:nil withLogRedirectionStrategy:[FFmpegKitConfig getLogRedirectionStrategy]];

View File

@ -26,6 +26,10 @@
MediaInformation* _mediaInformation; MediaInformation* _mediaInformation;
} }
+ (void)initialize {
// EMPTY INITIALIZE
}
- (instancetype)init:(NSArray*)arguments { - (instancetype)init:(NSArray*)arguments {
self = [super init:arguments withExecuteCallback:nil withLogCallback:nil withLogRedirectionStrategy:LogRedirectionStrategyNeverPrintLogs]; self = [super init:arguments withExecuteCallback:nil withLogCallback:nil withLogRedirectionStrategy:LogRedirectionStrategyNeverPrintLogs];

View File

@ -56,4 +56,8 @@
return (_value == ReturnCodeCancel); return (_value == ReturnCodeCancel);
} }
- (NSString*)description {
return [NSString stringWithFormat:@"%d", _value];
}
@end @end

View File

@ -89,14 +89,7 @@ x86-64)
TARGET_CPU="x86_64" TARGET_CPU="x86_64"
TARGET_ARCH="x86_64" TARGET_ARCH="x86_64"
ASM_OPTIONS=" --disable-neon --disable-asm" ASM_OPTIONS=" --disable-neon --disable-asm"
case $FFMPEG_KIT_BUILD_TYPE in BITCODE_FLAGS=""
macos)
BITCODE_FLAGS="-fembed-bitcode -Wc,-fembed-bitcode"
;;
*)
BITCODE_FLAGS=""
;;
esac
;; ;;
x86-64-mac-catalyst) x86-64-mac-catalyst)
TARGET_CPU="x86_64" TARGET_CPU="x86_64"

View File

@ -4,7 +4,7 @@
ASM_OPTIONS="" ASM_OPTIONS=""
case ${ARCH} in case ${ARCH} in
*-mac-catalyst) *-mac-catalyst)
ASM_OPTIONS="--disable-video-cocoa --disable-render-metal --disable-haptic --disable-diskaudio --disable-joystick" ASM_OPTIONS="--disable-video-cocoa --disable-render-metal --disable-diskaudio"
;; ;;
esac esac
@ -33,6 +33,8 @@ overwrite_file "${FFMPEG_KIT_TMPDIR}"/source/config/config.sub "${BASEDIR}"/src/
--enable-static \ --enable-static \
--disable-shared \ --disable-shared \
--disable-video-opengl \ --disable-video-opengl \
--disable-joystick \
--disable-haptic \
${ASM_OPTIONS} \ ${ASM_OPTIONS} \
--host="${HOST}" || return 1 --host="${HOST}" || return 1