1/*---------------------------------------------------------------------------- 2 * 3 * File: 4 * eas_synth.h 5 * 6 * Contents and purpose: 7 * Declarations, interfaces, and prototypes for synth. 8 * 9 * Copyright Sonic Network Inc. 2004, 2005 10 11 * Licensed under the Apache License, Version 2.0 (the "License"); 12 * you may not use this file except in compliance with the License. 13 * You may obtain a copy of the License at 14 * 15 * http://www.apache.org/licenses/LICENSE-2.0 16 * 17 * Unless required by applicable law or agreed to in writing, software 18 * distributed under the License is distributed on an "AS IS" BASIS, 19 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 20 * See the License for the specific language governing permissions and 21 * limitations under the License. 22 * 23 *---------------------------------------------------------------------------- 24 * Revision Control: 25 * $Revision: 718 $ 26 * $Date: 2007-06-08 16:43:16 -0700 (Fri, 08 Jun 2007) $ 27 *---------------------------------------------------------------------------- 28*/ 29 30#ifndef _EAS_SYNTH_H 31#define _EAS_SYNTH_H 32 33#include "eas_types.h" 34#include "eas_sndlib.h" 35 36#ifdef _WT_SYNTH 37#include "eas_wtsynth.h" 38#endif 39 40#ifdef _FM_SYNTH 41#include "eas_fmsynth.h" 42#endif 43 44#ifndef NUM_OUTPUT_CHANNELS 45#define NUM_OUTPUT_CHANNELS 2 46#endif 47 48#ifndef MAX_SYNTH_VOICES 49#define MAX_SYNTH_VOICES 64 50#endif 51 52#ifndef MAX_VIRTUAL_SYNTHESIZERS 53#define MAX_VIRTUAL_SYNTHESIZERS 4 54#endif 55 56/* defines */ 57#ifndef NUM_PRIMARY_VOICES 58#define NUM_PRIMARY_VOICES MAX_SYNTH_VOICES 59#elif !defined(NUM_SECONDARY_VOICES) 60#define NUM_SECONDARY_VOICES (MAX_SYNTH_VOICES - NUM_PRIMARY_VOICES) 61#endif 62 63#if defined(EAS_WT_SYNTH) 64#define NUM_WT_VOICES MAX_SYNTH_VOICES 65 66/* FM on MCU */ 67#elif defined(EAS_FM_SYNTH) 68#define NUM_FM_VOICES MAX_SYNTH_VOICES 69 70/* wavetable drums on MCU, wavetable melodic on DSP */ 71#elif defined(EAS_SPLIT_WT_SYNTH) 72#define NUM_WT_VOICES MAX_SYNTH_VOICES 73 74/* wavetable drums and FM melodic on MCU */ 75#elif defined(EAS_HYBRID_SYNTH) 76#define NUM_WT_VOICES NUM_PRIMARY_VOICES 77#define NUM_FM_VOICES NUM_SECONDARY_VOICES 78 79/* wavetable drums on MCU, FM melodic on DSP */ 80#elif defined(EAS_SPLIT_HYBRID_SYNTH) 81#define NUM_WT_VOICES NUM_PRIMARY_VOICES 82#define NUM_FM_VOICES NUM_SECONDARY_VOICES 83 84/* FM synth on DSP */ 85#elif defined(EAS_SPLIT_FM_SYNTH) 86#define NUM_FM_VOICES MAX_SYNTH_VOICES 87 88#else 89#error "Unrecognized architecture option" 90#endif 91 92#define NUM_SYNTH_CHANNELS 16 93 94#define DEFAULT_SYNTH_VOICES MAX_SYNTH_VOICES 95 96/* use the following values to specify unassigned channels or voices */ 97#define UNASSIGNED_SYNTH_CHANNEL NUM_SYNTH_CHANNELS 98#define UNASSIGNED_SYNTH_VOICE MAX_SYNTH_VOICES 99 100 101/* synth parameters are updated every SYNTH_UPDATE_PERIOD_IN_SAMPLES */ 102#define SYNTH_UPDATE_PERIOD_IN_SAMPLES (EAS_I32)(0x1L << SYNTH_UPDATE_PERIOD_IN_BITS) 103 104/* stealing weighting factors */ 105#define NOTE_AGE_STEAL_WEIGHT 1 106#define NOTE_GAIN_STEAL_WEIGHT 4 107#define CHANNEL_POLY_STEAL_WEIGHT 12 108#define CHANNEL_PRIORITY_STEAL_WEIGHT 2 109#define NOTE_MATCH_PENALTY 128 110#define SYNTH_PRIORITY_WEIGHT 8 111 112/* default synth master volume */ 113#define DEFAULT_SYNTH_MASTER_VOLUME 0x7fff 114 115#define DEFAULT_SYNTH_PRIORITY 5 116 117/* default tuning values */ 118#define DEFAULT_PITCH_BEND_SENSITIVITY 200 /* 2 semitones */ 119#define DEFAULT_FINE_PITCH 0 /* 0 cents */ 120#define DEFAULT_COARSE_PITCH 0 /* 0 semitones */ 121 122/* default drum channel is 10, but is internally 9 due to unit offset */ 123#define DEFAULT_DRUM_CHANNEL 9 124 125/* drum channel can simultaneously play this many voices at most */ 126#define DEFAULT_CHANNEL_POLYPHONY_LIMIT 2 127 128/* default instrument is acoustic piano */ 129#define DEFAULT_MELODY_BANK_MSB 0x79 130#define DEFAULT_RHYTHM_BANK_MSB 0x78 131#define DEFAULT_MELODY_BANK_NUMBER (DEFAULT_MELODY_BANK_MSB << 8) 132#define DEFAULT_RHYTHM_BANK_NUMBER (DEFAULT_RHYTHM_BANK_MSB << 8) 133#define DEFAULT_SYNTH_PROGRAM_NUMBER 0 134 135#define DEFAULT_PITCH_BEND 0x2000 /* 0x2000 == (0x40 << 7) | 0x00 */ 136#define DEFAULT_MOD_WHEEL 0 137#define DEFAULT_CHANNEL_VOLUME 0x64 138#define DEFAULT_PAN 0x40 /* decimal 64, center */ 139 140#ifdef _REVERB 141#define DEFAULT_REVERB_SEND 40 /* some reverb */ 142#endif 143 144#ifdef _CHORUS 145#define DEFAULT_CHORUS_SEND 0 /* no chorus */ 146#endif 147 148#define DEFAULT_EAS_FILTER_CUTOFF_FREQUENCY 0 /* EAS synth uses a different default */ 149#define DEFAULT_FILTER_RESONANCE 0 150#define DEFAULT_EXPRESSION 0x7F 151 152#define DEFAULT_CHANNEL_PRESSURE 0 153 154#define DEFAULT_REGISTERED_PARAM 0x3FFF 155 156#define DEFAULT_CHANNEL_STATIC_GAIN 0 157#define DEFAULT_CHANNEL_STATIC_PITCH 0 158 159#define DEFAULT_LFO_MOD_WHEEL_TO_PITCH_CENTS 50 160#define DEFAULT_LFO_CHANNEL_PRESSURE_TO_PITCH_CENTS 50 161 162#define DEFAULT_KEY_NUMBER 0x69 163#define DEFAULT_VELOCITY 0x64 164#define DEFAULT_REGION_INDEX 0 165#define DEFAULT_ARTICULATION_INDEX 0 166#define DEFAULT_VOICE_GAIN 0 167#define DEFAULT_AGE 0 168#define DEFAULT_SP_MIDI_PRIORITY 16 169 170 171/* filter defines */ 172#define DEFAULT_FILTER_ZERO 0 173#define FILTER_CUTOFF_MAX_PITCH_CENTS 1919 174#define FILTER_CUTOFF_MIN_PITCH_CENTS -4467 175#define A5_PITCH_OFFSET_IN_CENTS 6900 176 177/*------------------------------------ 178 * S_SYNTH_CHANNEL data structure 179 *------------------------------------ 180*/ 181 182/* S_SYNTH_CHANNEL.m_nFlags */ 183#define CHANNEL_FLAG_SUSTAIN_PEDAL 0x01 184#define CHANNEL_FLAG_MUTE 0x02 185#define CHANNEL_FLAG_UPDATE_CHANNEL_PARAMETERS 0x04 186#define CHANNEL_FLAG_RHYTHM_CHANNEL 0x08 187#define CHANNEL_FLAG_EXTERNAL_AUDIO 0x10 188#define DEFAULT_CHANNEL_FLAGS 0 189 190/* macros for extracting virtual synth and channel numbers */ 191#define GET_VSYNTH(a) ((a) >> 4) 192#define GET_CHANNEL(a) ((a) & 15) 193 194typedef struct s_synth_channel_tag 195{ 196 /* use static channel parameters to reduce MIPs */ 197 /* parameters shared by multiple voices assigned to same channel */ 198 EAS_I32 staticPitch; /* (pitch bend * pitch sens) + fine pitch */ 199 EAS_I16 staticGain; /* (CC7 * CC11 * master vol)^2 */ 200 201 EAS_U16 regionIndex; /* index of first region in program */ 202 203 EAS_U16 bankNum; /* play programs from this bank */ 204 EAS_I16 pitchBend; /* pitch wheel value */ 205 EAS_I16 pitchBendSensitivity; 206 EAS_I16 registeredParam; /* currently selected registered param */ 207 208 209#if defined(_FM_SYNTH) 210 EAS_I16 lfoAmt; /* amount of LFO to apply to voice */ 211#endif 212 213 EAS_U8 programNum; /* play this instrument number */ 214 EAS_U8 modWheel; /* CC1 */ 215 EAS_U8 volume; /* CC7 */ 216 EAS_U8 pan; /* CC10 */ 217 218 EAS_U8 expression; /* CC11 */ 219 220 /* the following parameters are controlled by RPNs */ 221 EAS_I8 finePitch; 222 EAS_I8 coarsePitch; 223 224 EAS_U8 channelPressure; /* applied to all voices on a given channel */ 225 226 EAS_U8 channelFlags; /* bit field channelFlags for */ 227 /* CC64, SP-MIDI channel masking */ 228 229 EAS_U8 pool; /* SPMIDI channel voice pool */ 230 EAS_U8 mip; /* SPMIDI MIP setting */ 231 232#ifdef _REVERB 233 EAS_U8 reverbSend; /* CC91 */ 234#endif 235 236#ifdef _CHORUS 237 EAS_U8 chorusSend; /* CC93 */ 238#endif 239} S_SYNTH_CHANNEL; 240 241/*------------------------------------ 242 * S_SYNTH_VOICE data structure 243 *------------------------------------ 244*/ 245 246/* S_SYNTH_VOICE.m_nFlags */ 247#define VOICE_FLAG_UPDATE_VOICE_PARAMETERS 0x01 248#define VOICE_FLAG_SUSTAIN_PEDAL_DEFER_NOTE_OFF 0x02 249#define VOICE_FLAG_DEFER_MIDI_NOTE_OFF 0x04 250#define VOICE_FLAG_NO_SAMPLES_SYNTHESIZED_YET 0x08 251#define VOICE_FLAG_DEFER_MUTE 0x40 252#define DEFAULT_VOICE_FLAGS 0 253 254/* S_SYNTH_VOICE.m_eState */ 255typedef enum { 256 257 eVoiceStateFree = 0, 258 eVoiceStateStart, 259 eVoiceStatePlay, 260 eVoiceStateRelease, 261 eVoiceStateMuting, 262 eVoiceStateStolen, 263 eVoiceStateInvalid /* should never be in this state! */ 264 265} E_VOICE_STATE; 266#define DEFAULT_VOICE_STATE eVoiceStateFree 267 268typedef struct s_synth_voice_tag 269{ 270 271/* These parameters are common to both wavetable and FM 272 * synthesizers. The voice manager should only access this data. 273 * Any other data should be manipulated by the code that is 274 * specific to that synthesizer and reflected back through the 275 * common state data available here. 276 */ 277 EAS_U16 regionIndex; /* index to wave and playback params */ 278 EAS_I16 gain; /* current gain */ 279 EAS_U16 age; /* large value means old note */ 280 EAS_U16 nextRegionIndex; /* index to wave and playback params */ 281 EAS_U8 voiceState; /* current voice state */ 282 EAS_U8 voiceFlags; /* misc flags/bit fields */ 283 EAS_U8 channel; /* this voice plays on this synth channel */ 284 EAS_U8 note; /* 12 <= key number <= 108 */ 285 EAS_U8 velocity; /* 0 <= velocity <= 127 */ 286 EAS_U8 nextChannel; /* play stolen voice on this channel */ 287 EAS_U8 nextNote; /* 12 <= key number <= 108 */ 288 EAS_U8 nextVelocity; /* 0 <= velocity <= 127 */ 289} S_SYNTH_VOICE; 290 291/*------------------------------------ 292 * S_SYNTH data structure 293 * 294 * One instance for each MIDI stream 295 *------------------------------------ 296*/ 297 298/* S_SYNTH.m_nFlags */ 299#define SYNTH_FLAG_RESET_IS_REQUESTED 0x01 300#define SYNTH_FLAG_SP_MIDI_ON 0x02 301#define SYNTH_FLAG_UPDATE_ALL_CHANNEL_PARAMETERS 0x04 302#define SYNTH_FLAG_DEFERRED_MIDI_NOTE_OFF_PENDING 0x08 303#define DEFAULT_SYNTH_FLAGS SYNTH_FLAG_UPDATE_ALL_CHANNEL_PARAMETERS 304 305typedef struct s_synth_tag 306{ 307 struct s_eas_data_tag *pEASData; 308 const S_EAS *pEAS; 309 310#ifdef DLS_SYNTHESIZER 311 S_DLS *pDLS; 312#endif 313 314#ifdef EXTERNAL_AUDIO 315 EAS_EXT_PRG_CHG_FUNC cbProgChgFunc; 316 EAS_EXT_EVENT_FUNC cbEventFunc; 317 EAS_VOID_PTR *pExtAudioInstData; 318#endif 319 320 S_SYNTH_CHANNEL channels[NUM_SYNTH_CHANNELS]; 321 EAS_I32 totalNoteCount; 322 EAS_U16 maxPolyphony; 323 EAS_U16 numActiveVoices; 324 EAS_U16 masterVolume; 325 EAS_U8 channelsByPriority[NUM_SYNTH_CHANNELS]; 326 EAS_U8 poolCount[NUM_SYNTH_CHANNELS]; 327 EAS_U8 poolAlloc[NUM_SYNTH_CHANNELS]; 328 EAS_U8 synthFlags; 329 EAS_I8 globalTranspose; 330 EAS_U8 vSynthNum; 331 EAS_U8 refCount; 332 EAS_U8 priority; 333} S_SYNTH; 334 335/*------------------------------------ 336 * S_VOICE_MGR data structure 337 * 338 * One instance for each EAS library instance 339 *------------------------------------ 340*/ 341typedef struct s_voice_mgr_tag 342{ 343 S_SYNTH *pSynth[MAX_VIRTUAL_SYNTHESIZERS]; 344 EAS_PCM voiceBuffer[SYNTH_UPDATE_PERIOD_IN_SAMPLES]; 345 346#ifdef _FM_SYNTH 347 EAS_PCM operMixBuffer[SYNTH_UPDATE_PERIOD_IN_SAMPLES]; 348 S_FM_VOICE fmVoices[NUM_FM_VOICES]; 349#endif 350 351#ifdef _WT_SYNTH 352 S_WT_VOICE wtVoices[NUM_WT_VOICES]; 353#endif 354 355#ifdef _REVERB 356 EAS_PCM reverbSendBuffer[NUM_OUTPUT_CHANNELS * SYNTH_UPDATE_PERIOD_IN_SAMPLES]; 357#endif 358 359#ifdef _CHORUS 360 EAS_PCM chorusSendBuffer[NUM_OUTPUT_CHANNELS * SYNTH_UPDATE_PERIOD_IN_SAMPLES]; 361#endif 362 S_SYNTH_VOICE voices[MAX_SYNTH_VOICES]; 363 364 EAS_SNDLIB_HANDLE pGlobalEAS; 365 366#ifdef DLS_SYNTHESIZER 367 S_DLS *pGlobalDLS; 368#endif 369 370#ifdef _SPLIT_ARCHITECTURE 371 EAS_FRAME_BUFFER_HANDLE pFrameBuffer; 372#endif 373 374#if defined(_SECONDARY_SYNTH) || defined(EAS_SPLIT_WT_SYNTH) 375 EAS_U16 maxPolyphonyPrimary; 376 EAS_U16 maxPolyphonySecondary; 377#endif 378 379 EAS_I32 workload; 380 EAS_I32 maxWorkLoad; 381 382 EAS_U16 activeVoices; 383 EAS_U16 maxPolyphony; 384 385 EAS_U16 age; 386 387/* limits the number of voice starts in a frame for split architecture */ 388#ifdef MAX_VOICE_STARTS 389 EAS_U16 numVoiceStarts; 390#endif 391} S_VOICE_MGR; 392 393#endif /* #ifdef _EAS_SYNTH_H */ 394 395 396