unit _MXDRVm_const;

interface

uses
  SysUtils,Types;

const MXDRVmVersion=010; // Ver0.10

const HT:char=char($09);
const CR:char=char($0d);
const LF:char=char($0a);
const SP:char=char($20);
const CRLF:string=char($0d)+char($0a);

const MXDRVDriverVersion210=210;
const MXDRVDriverVersion211=211;

type
  PByteLargeArray = ^TByteLargeArray;
  TByteLargeArray = array[0..1073741824] of Byte; // 1GB

type
  PSmallIntLargeArray = ^TSmallIntLargeArray;
  TSmallIntLargeArray = array[0..536870912] of SmallInt; // 1GB

// MDXArctect

const ADPCMCount=$60*$80+1; // ノートキー数＊音色数
const TimerBModify:double=(((4*1000*1000) shr 6)/1000);

type
  TMDX=record
    PDXFilename:string;
    FileSize,PDXFileSize:integer;
    PDXFileLoadFlag:boolean;
    Segment,VoiceOffset:word;
    MaxChannel:byte;
    MMLOffset: array[0..15] of word;
    Tempo:byte;
    ExtendPCM8:boolean; // False=ADPCM True=PCM8
    LoopCount:LongInt; // 0=NotLoop Over=Looped
    MasterVolume:LongInt; // 0=Minimum 256=Max
    SLFO3Param:smallint; // LFOType3用パラメータ
    FadeoutFlag:boolean; // False=NotFadeout True=FadeoutNow...
    RunPCM8ppFlag:boolean; // どれかのチャネルでMarcuryが動けばTrue
    EndFlag:boolean;
  end;

type
  TMMLChannel=record
    Enabled:boolean; // False=End True=Playing
    Mute:boolean; // False=NotMute True=Muted
    Buffer: array of byte;
    MMLSize:dword;
    Cmd: array[0..5] of byte;
    Looped:boolean; // False=NotLoop True=Looped
    NowPos:dword;
    NowVoice,NowVoiceSetting:integer;
    NowKeycode:byte;
    NowPanpot:byte;
    NowPortament:Longint;
    NowSync:boolean; // False=NotSync True=LFO Syncing
    NowPAMS:byte;
    NowPAMSEnabled:boolean;
    ADPCMRate:byte;
    LastPitch:longint;

    ppEnabled:boolean;
    ppFreqCnt,ppFreq:integer;
    ppOffset:dword;
    ppVolume:byte;
    ppVolume16:longint;
    ppKeycode:integer;
    ppPanpot:byte;
    ppConvFunc:byte;
    ppConvPosTable:PIntegerArray;
    ppConvModTable:PIntegerArray;
    ppData:PByteLargeArray;
    ppDataSize:integer;

    Slot32Enabled:boolean; // False=NotUseNoize True=UseNoize
    NowCarrierSlot:integer;

    RestClock,StopClock:smallint;
    LoopCount: array[0..256] of byte;
    LoopMax:byte;

    Noteon:boolean;
    Volume:byte;
    VolMode:boolean; // False=v0-15 True=@v0-127
    Quartz:byte;
    QuartzMode:boolean; // False=Clk*n/8 True=Clk-n
    KeyoffMode:boolean; // Next Keyon is False=Disabled True=Enabled
    Detune,Portament:Longint;
    KeyonDelay:byte;
    SignalWaitFlag,SetSignalWaitFlag:boolean; // False=Go True=Waiting

    // SoftLFO
    SLFODelay:byte; // Delay
    SLFONowDelay:byte; // Start Delay Count

    MPEnabled:boolean; // False=NotPhaseLFO True=UsePhaseLFO
    MPWaveType:byte; // 0=櫛形 1=矩形波 2=三角波
    MPFreq:word; // Frequency
    MPDisplace:LongInt; // Displacement
    MPMstDisplace:LongInt;
    MPNowFreq:word; // Now Freq
    MPNowCount:byte; // Now LoopCount useV210only
    MPNowDetune:LongInt; // Now Detune

    MAEnabled:boolean; // False=NotAmpritureLFO True=UseAmpritureLFO
    MAWaveType:byte; // 0=櫛形 1=矩形波 2=三角波
    MAFreq:word; // Frequency
    MADisplace:LongInt; // Displacement
    MAMstDisplace:LongInt;
    MANowFreq:word; // Now Freq
    MANowCount:byte; // LoopCount useV210only
    MANowDetune:LongInt; // Now Detune
  end;

type
  TVoicePartParams=array[0..5] of byte;

type
  TOPMVoice=record
    Enabled:boolean;
    Sync:boolean;
    AF,Slot:byte;
    Part: array[0..3] of TVoicePartParams;
  end;

type
  TADPCM=record // 4byte Start Adrs -and- 4byte Data Length
    Enabled:boolean;
    StartAdrs,Size:dword;
    ADPCMData:PByteLargeArray;
    PCMData:PSmallIntLargeArray;
  end;

const ADPCMSRCMode_X68Sound=0;
const ADPCMSRCMode_Nearest=1;
const ADPCMSRCMode_Linear=2;

// PCM8pp Marcury

const ppFreqMax=12;
const ppFreq_Var=0;
const ppFreq_3906=1;
const ppFreq_5208=2;
const ppFreq_7812=3;
const ppFreq_10416=4;
const ppFreq_15625=5;
const ppFreq_16000=6;
const ppFreq_22050=7;
const ppFreq_24000=8;
const ppFreq_32000=9;
const ppFreq_44100=10;
const ppFreq_48000=11;

const ppConvFunc_NotSupport=0;
const ppConvFunc_ADPCM=1;
const ppConvFunc_Mono8bit=2;
const ppConvFunc_Mono16bit=3;
const ppConvFunc_Stereo8bit=4;
const ppConvFunc_Stereo16bit=5;

// x68sound.dll

const X68SNDERR_PCMOUT=(-1);
const X68SNDERR_TIMER =(-2);
const X68SNDERR_MEMORY=(-3);
const X68SNDERR_NOTACTIVE=(-4);
const X68SNDERR_ALREADYACTIVE=(-5);
const X68SNDERR_BADARG=(-6);

const X68SNDERR_DLL   =(-1);
const X68SNDERR_FUNC  =(-2);

type
  TX68proc=procedure cdecl export;
  TX68func=function:longword cdecl export;

//int bet=5, pcmbuf=5, late=200; double rev=1.0;
function  X68Sound_Start(samprate,opmflag,adpcmflag,betw,pcmbuf,late:LongInt; rev:double):LongInt; cdecl; external 'X68Sound.dll';
function  X68Sound_Samprate(samprate:LongInt):LongInt; cdecl; external 'X68Sound.dll';
procedure X68Sound_Reset; cdecl; external 'X68Sound.dll';
procedure X68Sound_Free; cdecl; external 'X68Sound.dll';
function  X68Sound_TotalVolume(Volume:LongInt):LongInt; cdecl; external 'X68Sound.dll';

//extern "C" void (*X68Sound_BetwInt)(void (CALLBACK *proc)()=NULL);
procedure X68Sound_BetwInt(proc:TX68proc); cdecl; external 'X68Sound.dll';
//extern "C" void (*X68Sound_WaveFunc)(int (CALLBACK *func)()=NULL);
procedure X68Sound_WaveFunc(proc:TX68func); cdecl; external 'X68Sound.dll';

//int samprate=44100, opmflag=1, adpcmflag=1, pcmbuf=5);
function  X68Sound_StartPcm(samprate,opmflag,adpcmflag,pcmbuf:LongInt):LongInt; cdecl; external 'X68Sound.dll';
function  X68Sound_GetPcm(buf:PByteArray;len:LongInt):LongInt; cdecl; external 'X68Sound.dll';

function  X68Sound_OpmPeek:byte; cdecl; external 'X68Sound.dll';
procedure X68Sound_OpmReg(RegNo:byte); cdecl; external 'X68Sound.dll';
procedure X68Sound_OpmPoke(Data:byte); cdecl; external 'X68Sound.dll';
procedure X68Sound_OpmInt(proc:TX68proc); cdecl; external 'X68Sound.dll';

function  X68Sound_AdpcmPeek:byte; cdecl; external 'X68Sound.dll';
procedure X68Sound_AdpcmPoke(data:byte); cdecl; external 'X68Sound.dll';
function  X68Sound_PpiPeek:byte; cdecl; external 'X68Sound.dll';
procedure X68Sound_PpiPoke(data:byte); cdecl; external 'X68Sound.dll';
procedure X68Sound_PpiCtrl(data:byte); cdecl; external 'X68Sound.dll';
function  X68Sound_DmaPeek(adrs:byte):byte; cdecl; external 'X68Sound.dll';
procedure X68Sound_DmaPoke(adrs,data:byte); cdecl; external 'X68Sound.dll';
procedure X68Sound_DmaInt(proc:TX68proc); cdecl; external 'X68Sound.dll';
procedure X68Sound_DmaErrInt(proc:TX68proc); cdecl; external 'X68Sound.dll';
//procedure X68Sound_MemReadFunc(int (CALLBACK *func)(unsigned char *)=NULL); cdecl; external 'X68Sound.dll';

function X68Sound_Pcm8_Out(ch:LongInt; adrs:PByteArray; mode,len:LongInt):LongInt; cdecl; external 'X68Sound.dll';
function X68Sound_Pcm8_Aot(ch:LongInt; tbl:PByteArray; mode,cnt:LongInt):LongInt; cdecl; external 'X68Sound.dll';
function X68Sound_Pcm8_Lot(ch:LongInt; tbl:PByteArray; mode:LongInt):LongInt; cdecl; external 'X68Sound.dll';
function X68Sound_Pcm8_SetMode(ch:LongInt; mode:LongInt):LongInt; cdecl; external 'X68Sound.dll';
function X68Sound_Pcm8_GetRest(ch:LongInt):LongInt; cdecl; external 'X68Sound.dll';
function X68Sound_Pcm8_GetMode(ch:LongInt):LongInt; cdecl; external 'X68Sound.dll';
function X68Sound_Pcm8_Abort:LongInt; cdecl; external 'X68Sound.dll';

function  X68Sound_ErrorCode:LongInt; cdecl; external 'X68Sound.dll';
function  X68Sound_DebugValue:LongInt; cdecl; external 'X68Sound.dll';

procedure MoveMemory(Destination: Pointer; Source: Pointer; Length: DWORD);
procedure strcpyToPChar(src:string;dst:PChar);

implementation

procedure MoveMemory(Destination: Pointer; Source: Pointer; Length: DWORD);
begin
  Move(Source^, Destination^, Length);
end;

procedure strcpyToPChar(src:string;dst:PChar);
begin
  if src='' then begin
    dst[0]:=chr(0);
    end else begin
    MoveMemory(dst,@src[1],length(src));
    dst[length(src)]:=chr(0);
  end;
end;

end.



