questzdoom/Projects/Android/jni/SupportLibs/fluidsynth/fluid_sys.h
2021-04-20 21:09:02 +01:00

314 lines
7.5 KiB
C

/* FluidSynth - A Software Synthesizer
*
* Copyright (C) 2003 Peter Hanappe and others.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Library General Public License
* as published by the Free Software Foundation; either version 2 of
* the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Library General Public License for more details.
*
* You should have received a copy of the GNU Library General Public
* License along with this library; if not, write to the Free
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
* 02111-1307, USA
*/
/**
This header contains a bunch of (mostly) system and machine
dependent functions:
- timers
- current time in milliseconds and microseconds
- debug logging
- profiling
- memory locking
- checking for floating point exceptions
*/
#ifndef _FLUID_SYS_H
#define _FLUID_SYS_H
#include "fluidsynth_priv.h"
void fluid_sys_config(void);
void fluid_log_config(void);
void fluid_time_config(void);
/*
* Utility functions
*/
char *fluid_strtok (char **str, char *delim);
/**
Additional debugging system, separate from the log system. This
allows to print selected debug messages of a specific subsystem.
*/
extern unsigned int fluid_debug_flags;
#if DEBUG
enum fluid_debug_level {
FLUID_DBG_DRIVER = 1
};
int fluid_debug(int level, char * fmt, ...);
#else
#define fluid_debug
#endif
/** fluid_curtime() returns the current time in milliseconds. This time
should only be used in relative time measurements. */
/** fluid_utime() returns the time in micro seconds. this time should
only be used to measure duration (relative times). */
#if defined(WIN32)
#define fluid_curtime() GetTickCount()
double fluid_utime(void);
#elif defined(MACOS9)
#include <OSUtils.h>
#include <Timer.h>
unsigned int fluid_curtime();
#define fluid_utime() 0.0
#elif defined(__OS2__)
#define INCL_DOS
#include <os2.h>
typedef int socklen_t;
unsigned int fluid_curtime(void);
double fluid_utime(void);
#else
unsigned int fluid_curtime(void);
double fluid_utime(void);
#endif
/**
Timers
*/
/* if the callback function returns 1 the timer will continue; if it
returns 0 it will stop */
typedef int (*fluid_timer_callback_t)(void* data, unsigned int msec);
typedef struct _fluid_timer_t fluid_timer_t;
fluid_timer_t* new_fluid_timer(int msec, fluid_timer_callback_t callback,
void* data, int new_thread, int auto_destroy);
int delete_fluid_timer(fluid_timer_t* timer);
int fluid_timer_join(fluid_timer_t* timer);
int fluid_timer_stop(fluid_timer_t* timer);
/**
Muteces
*/
#if defined(MACOS9)
typedef int fluid_mutex_t;
#define fluid_mutex_init(_m) { (_m) = 0; }
#define fluid_mutex_destroy(_m)
#define fluid_mutex_lock(_m)
#define fluid_mutex_unlock(_m)
#elif defined(WIN32)
typedef HANDLE fluid_mutex_t;
#define fluid_mutex_init(_m) { (_m) = CreateMutex(NULL, 0, NULL); }
#define fluid_mutex_destroy(_m) if (_m) { CloseHandle(_m); }
#define fluid_mutex_lock(_m) WaitForSingleObject(_m, INFINITE)
#define fluid_mutex_unlock(_m) ReleaseMutex(_m)
#elif defined(__OS2__)
typedef HMTX fluid_mutex_t;
#define fluid_mutex_init(_m) { (_m) = 0; DosCreateMutexSem( NULL, &(_m), 0, FALSE ); }
#define fluid_mutex_destroy(_m) if (_m) { DosCloseMutexSem(_m); }
#define fluid_mutex_lock(_m) DosRequestMutexSem(_m, -1L)
#define fluid_mutex_unlock(_m) DosReleaseMutexSem(_m)
#else
typedef pthread_mutex_t fluid_mutex_t;
#define fluid_mutex_init(_m) pthread_mutex_init(&(_m), NULL)
#define fluid_mutex_destroy(_m) pthread_mutex_destroy(&(_m))
#define fluid_mutex_lock(_m) pthread_mutex_lock(&(_m))
#define fluid_mutex_unlock(_m) pthread_mutex_unlock(&(_m))
#endif
/**
Threads
*/
typedef struct _fluid_thread_t fluid_thread_t;
typedef void (*fluid_thread_func_t)(void* data);
/** When detached, 'join' does not work and the thread destroys itself
when finished. */
fluid_thread_t* new_fluid_thread(fluid_thread_func_t func, void* data, int detach);
int delete_fluid_thread(fluid_thread_t* thread);
int fluid_thread_join(fluid_thread_t* thread);
/**
Sockets
*/
/** The function should return 0 if no error occured, non-zero
otherwise. If the function return non-zero, the socket will be
closed by the server. */
typedef int (*fluid_server_func_t)(void* data, fluid_socket_t client_socket, char* addr);
fluid_server_socket_t* new_fluid_server_socket(int port, fluid_server_func_t func, void* data);
int delete_fluid_server_socket(fluid_server_socket_t* sock);
int fluid_server_socket_join(fluid_server_socket_t* sock);
/** Create a new client socket. */
fluid_socket_t new_fluid_client_socket(char* host, int port);
/** Delete the client socket. This function should only be called on
sockets create with 'new_fluid_client_socket'. */
void delete_fluid_client_socket(fluid_socket_t sock);
void fluid_socket_close(fluid_socket_t sock);
fluid_istream_t fluid_socket_get_istream(fluid_socket_t sock);
fluid_ostream_t fluid_socket_get_ostream(fluid_socket_t sock);
/**
Profiling
*/
/**
Profile numbers. List all the pieces of code you want to profile
here. Be sure to add an entry in the fluid_profile_data table in
fluid_sys.c
*/
enum {
FLUID_PROF_WRITE_S16,
FLUID_PROF_ONE_BLOCK,
FLUID_PROF_ONE_BLOCK_CLEAR,
FLUID_PROF_ONE_BLOCK_VOICE,
FLUID_PROF_ONE_BLOCK_VOICES,
FLUID_PROF_ONE_BLOCK_REVERB,
FLUID_PROF_ONE_BLOCK_CHORUS,
FLUID_PROF_VOICE_NOTE,
FLUID_PROF_VOICE_RELEASE,
FLUID_PROF_LAST
};
#if WITH_PROFILING
void fluid_profiling_print(void);
/** Profiling data. Keep track of min/avg/max values to execute a
piece of code. */
typedef struct _fluid_profile_data_t {
int num;
char* description;
double min, max, total;
unsigned int count;
} fluid_profile_data_t;
extern fluid_profile_data_t fluid_profile_data[];
/** Macro to obtain a time refence used for the profiling */
#define fluid_profile_ref() fluid_utime()
/** Macro to calculate the min/avg/max. Needs a time refence and a
profile number. */
#define fluid_profile(_num,_ref) { \
double _now = fluid_utime(); \
double _delta = _now - _ref; \
fluid_profile_data[_num].min = _delta < fluid_profile_data[_num].min ? _delta : fluid_profile_data[_num].min; \
fluid_profile_data[_num].max = _delta > fluid_profile_data[_num].max ? _delta : fluid_profile_data[_num].max; \
fluid_profile_data[_num].total += _delta; \
fluid_profile_data[_num].count++; \
_ref = _now; \
}
#else
/* No profiling */
#define fluid_profiling_print()
#define fluid_profile_ref() 0
#define fluid_profile(_num,_ref)
#endif
/**
Memory locking
Memory locking is used to avoid swapping of the large block of
sample data.
*/
#if defined(HAVE_SYS_MMAN_H) && !defined(__OS2__)
#define fluid_mlock(_p,_n) mlock(_p, _n)
#define fluid_munlock(_p,_n) munlock(_p,_n)
#else
#define fluid_mlock(_p,_n) 0
#define fluid_munlock(_p,_n)
#endif
/**
Floating point exceptions
fluid_check_fpe() checks for "unnormalized numbers" and other
exceptions of the floating point processsor.
*/
#ifdef FPE_CHECK
#define fluid_check_fpe(expl) fluid_check_fpe_i386(expl)
#define fluid_clear_fpe() fluid_clear_fpe_i386()
#else
#define fluid_check_fpe(expl)
#define fluid_clear_fpe()
#endif
unsigned int fluid_check_fpe_i386(char * explanation_in_case_of_fpe);
void fluid_clear_fpe_i386(void);
#endif /* _FLUID_SYS_H */