home *** CD-ROM | disk | FTP | other *** search
/ Inter.Net 55-1 / Inter.Net 55-1.iso / beos / PPBeDevKit.ZIP / PLAYERPR.TAR / PlayerPRO / Source / Import-Export / IT.c < prev    next >
Encoding:
C/C++ Source or Header  |  1998-12-26  |  27.9 KB  |  1,055 lines

  1. /********************                        ***********************/
  2. //
  3. //    Player PRO 5.0 - DRIVER SOURCE CODE -
  4. //
  5. //    Library Version 5.0
  6. //
  7. //    To use with MAD Library for Mac: Symantec, CodeWarrior and MPW
  8. //
  9. //    Antoine ROSSET
  10. //    16 Tranchees
  11. //    1206 GENEVA
  12. //    SWITZERLAND
  13. //
  14. //    COPYRIGHT ANTOINE ROSSET 1996, 1997, 1998
  15. //
  16. //    Thank you for your interest in PlayerPRO !
  17. //
  18. //    FAX:                (+41 22) 346 11 97
  19. //    PHONE:             (+41 79) 203 74 62
  20. //    Internet:     RossetAntoine@bluewin.ch
  21. //
  22. /********************                        ***********************/
  23.  
  24.  
  25. #include "RDriver.h"
  26. #include "FileUtils.h"
  27. #include "IT.h"
  28.  
  29. #ifdef _MAC_H
  30. #if defined(powerc) || defined(__powerc)
  31. enum {
  32.         PlayerPROPlug = kCStackBased
  33.         | RESULT_SIZE(SIZE_CODE(sizeof(OSErr)))
  34.         | STACK_ROUTINE_PARAMETER(1, SIZE_CODE(sizeof( OSType)))
  35.         | STACK_ROUTINE_PARAMETER(2, SIZE_CODE(sizeof( Ptr)))
  36.         | STACK_ROUTINE_PARAMETER(3, SIZE_CODE(sizeof( MADMusic*)))
  37.         | STACK_ROUTINE_PARAMETER(4, SIZE_CODE(sizeof( PPInfoRec*)))
  38.         | STACK_ROUTINE_PARAMETER(5, SIZE_CODE(sizeof( MADDriverSettings*)))
  39. };
  40.  
  41. ProcInfoType __procinfo = PlayerPROPlug;
  42. #else
  43. #include <A4Stuff.h>
  44. #endif
  45. #endif
  46.  
  47. #define LOW(para) ((para) & 15)
  48. #define HI(para) ((para) >> 4)
  49.  
  50. Cmd* GetMADCommand( register short PosX, register short    TrackIdX, register PatData*    tempMusicPat)
  51. {
  52.     if( PosX < 0) PosX = 0;
  53.     else if( PosX >= tempMusicPat->header.size) PosX = tempMusicPat->header.size -1;
  54.         
  55.     return( & (tempMusicPat->Cmds[ (tempMusicPat->header.size * TrackIdX) + PosX]));
  56. }
  57.  
  58. Ptr MADPlugNewPtr( long size, MADDriverSettings* init)
  59. {
  60.     if( init->sysMemory) return NewPtrSys( size);
  61.     else return NewPtr( size);
  62. }
  63.  
  64. Ptr MADPlugNewPtrClear( long size, MADDriverSettings* init)
  65. {
  66.     if( init->sysMemory) return NewPtrSysClear( size);
  67.     else return NewPtrClear( size);
  68. }
  69.  
  70. void mystrcpy( Ptr a, Ptr b)
  71. {
  72.     BlockMove( b + 1, a, b[ 0]);
  73. }
  74.  
  75. Boolean compMem( Ptr a, Ptr b, long s)
  76. {
  77. long     i;
  78.  
  79.     for( i = 0; i < s; i++)
  80.     {
  81.         if( a[ i] != b[ i]) return false;
  82.     }
  83.     
  84.     return true;
  85. }
  86.  
  87. void ConvertITEffect( Byte B0, Byte B1, Byte *Cmd, Byte *Arg)
  88. {
  89.     Byte        LoB1 = LOW( B1);
  90.     Byte        HiB1 = HI( B1);
  91.     
  92.     switch( B0 + 0x40)
  93.     {
  94.         default:    *Cmd = 0;            *Arg = 0;        break;
  95.         // Speed
  96.         case 'A':    *Cmd = speedE;        *Arg = B1;    break;
  97.         // Tempo
  98.         case 'T':    *Cmd = speedE;        *Arg = B1;    break;
  99.  
  100.         case 'B':    *Cmd = fastskipE;        *Arg = B1;    break;
  101.  
  102.         case 'C':    *Cmd = skipE;            *Arg = B1;    break;
  103.  
  104.         case 'D':
  105.             if( LoB1 == 0 || HiB1 == 0)        // Slide volume
  106.             {
  107.                 *Cmd = slidevolE;        *Arg = B1;
  108.             }
  109.             else if( HiB1 == 0x0F)        // Fine Slide volume DOWN
  110.             {
  111.                 *Cmd = extendedE;
  112.                 *Arg = 11 << 4;
  113.                 *Arg += LoB1;
  114.             }
  115.             else if( LoB1 == 0x0F)        // Fine Slide volume UP
  116.             {
  117.                 *Cmd = extendedE;
  118.                 *Arg = 10 << 4;
  119.                 *Arg += HiB1;
  120.             }
  121.         break;
  122.         
  123.         case 'E':
  124.             if( HiB1 == 0x0F)        // FineSlide DOWN
  125.             {
  126.                 *Cmd = extendedE;
  127.                 *Arg = 2 << 4;        //not supported
  128.                 *Arg += LoB1;
  129.             }
  130.             else if( HiB1 == 0x0E)    // ExtraFineSlide DOWN
  131.             {
  132.                 *Cmd = 0;            *Arg = 0;        //not supported
  133.             }
  134.             else                    // Slide DOWN
  135.             {
  136.                 *Cmd = upslideE;        *Arg = B1;
  137.             }
  138.         break;
  139.  
  140.         case 'F':
  141.             if( HiB1 == 0x0F)        // FineSlide UP
  142.             {
  143.                 *Cmd = extendedE;
  144.                 *Arg = 1 << 4;        //not supported
  145.                 *Arg += LoB1;
  146.             }
  147.             else if( HiB1 == 0x0E)    // ExtraFineSlide UP
  148.             {
  149.                 *Cmd = 0;            *Arg = 0;        //not supported
  150.             }
  151.             else                    // Slide UP
  152.             {
  153.                 *Cmd = downslideE;        *Arg = B1;
  154.             }
  155.         break;
  156.  
  157.         case 'G':    *Cmd = portamentoE;    *Arg = B1;    break;
  158.         case 'H':    *Cmd = vibratoE;        *Arg = B1;    break;
  159.         
  160.         case 'J':    *Cmd = arpeggioE;        *Arg = B1;    break;
  161.         case 'K':    *Cmd = vibratoslideE;    *Arg = B1;    break;
  162.         case 'L':    *Cmd = portaslideE;        *Arg = B1;    break;
  163.         case 'O':    *Cmd = offsetE;        *Arg = B1;    break;
  164.  
  165.         case 'S':        // Special Effects
  166.             switch( HiB1)
  167.             {
  168.                 default:    *Cmd = 0;        *Arg = 0;                            break;
  169.                 case 2:    *Cmd = extendedE;    *Arg = 5 << 4;        *Arg += LoB1;        break;    // FineTune
  170.                 case 3:    *Cmd = extendedE;    *Arg = 4 << 4;        *Arg += LoB1;        break;    // Set Vibrato WaveForm
  171.                 case 4:    *Cmd = extendedE;    *Arg = 7 << 4;        *Arg += LoB1;        break;    // Set Tremolo WaveForm
  172.                 case 0xB:    *Cmd = extendedE;    *Arg = 6 << 4;        *Arg += LoB1;        break;    // Loop pattern
  173.                 case 0xC:    *Cmd = extendedE;    *Arg = 12 << 4;    *Arg += LoB1;        break;    // Cut sample
  174.                 case 0xD:    *Cmd = extendedE;    *Arg = 13 << 4;    *Arg += LoB1;        break;    // Delay sample
  175.                 case 0xE:    *Cmd = extendedE;    *Arg = 14 << 4;    *Arg += LoB1;        break;    // Delay pattern
  176.             }
  177.         break;
  178.     }
  179. }
  180.  
  181. void ConvertMADEffect( Byte Cmd, Byte Arg, Byte *B0, Byte *B1)
  182. {
  183.     *B0 = 0;
  184.     *B1 = 0;
  185.  
  186.     switch( Cmd)
  187.     {
  188.         case speedE:        *B0 = 'A' - 0x40;    *B1 = Arg;    break;
  189.         case fastskipE:        *B0 = 'B' - 0x40;    *B1 = Arg;    break;
  190.         case skipE:        *B0 = 'C' - 0x40;    *B1 = Arg;    break;
  191.         case slidevolE:        *B0 = 'D' - 0x40;    *B1 = Arg;    break;
  192.         case upslideE:        *B0 = 'E' - 0x40;    *B1 = Arg;    break;
  193.         case downslideE:    *B0 = 'F' - 0x40;    *B1 = Arg;    break;
  194.         case portamentoE:    *B0 = 'G' - 0x40;    *B1 = Arg;    break;
  195.         case vibratoE:        *B0 = 'H' - 0x40;    *B1 = Arg;    break;
  196.         
  197.         case arpeggioE:        *B0 = 'J' - 0x40;    *B1 = Arg;    break;
  198.         case vibratoslideE:    *B0 = 'K' - 0x40;    *B1 = Arg;    break;
  199.         case portaslideE:    *B0 = 'L' - 0x40;    *B1 = Arg;    break;
  200.         case offsetE:        *B0 = 'O' - 0x40;    *B1 = Arg;    break;
  201.         
  202.         case extendedE:
  203.             switch( (Arg & 0xF0) >> 4)
  204.             {
  205.                 case 1:    *B0 = 'F' - 0x40;    *B1 = 0xf0 + (Arg & 0x0F);        break;
  206.                 case 2:    *B0 = 'E' - 0x40;    *B1 = 0xf0 + (Arg & 0x0F);        break;
  207.                 
  208.                 case 5:    *B0 = 'S' - 0x40;    *B1 = 0x20 + (Arg & 0x0F);        break;
  209.                 
  210.                 case 4:    *B0 = 'S' - 0x40;    *B1 = 0x30 + (Arg & 0x0F);        break;
  211.                 case 7:    *B0 = 'S' - 0x40;    *B1 = 0x40 + (Arg & 0x0F);        break;
  212.                 case 6:    *B0 = 'S' - 0x40;    *B1 = 0xb0 + (Arg & 0x0F);        break;
  213.                 case 12:    *B0 = 'S' - 0x40;    *B1 = 0xc0 + (Arg & 0x0F);        break;
  214.                 case 13:    *B0 = 'S' - 0x40;    *B1 = 0xd0 + (Arg & 0x0F);        break;
  215.                 case 14:    *B0 = 'S' - 0x40;    *B1 = 0xe0 + (Arg & 0x0F);        break;
  216.                 
  217.                 case 11:    *B0 = 'D' - 0x40;    *B1 = 0xf0 + (Arg & 0x0F);        break;
  218.                 case 10:    *B0 = 'D' - 0x40;    *B1 = 0x0f + ((Arg & 0x0F)<<4);    break;
  219.             }
  220.         break;
  221.     }
  222. }
  223.  
  224. OSErr ConvertIT2Mad( Ptr theIT, long MODSize, MADMusic *theMAD, MADDriverSettings *init)
  225. {
  226.     long                 i, x, z, channel, Row;
  227.     Ptr                    MaxPtr;
  228.     Ptr                    theInstrument[ 256];
  229.     Byte                tempChar, *theITCopy;
  230.     short                maxTrack;
  231.     short                ITperiod[ 12] = {1712,1616,1524,1440,1356,1280,1208,1140,1076,1016, 960, 907};
  232.     
  233.     /**** Variables pour le MAD ****/
  234.     Cmd                *aCmd;
  235.     
  236.     /**** Variables pour le IT ****/
  237.     
  238.     ITForm            ITinfo;
  239.     /********************************/
  240.     
  241.     for( i = 0 ; i < 256; i ++)
  242.     {
  243.         theInstrument[ i] = 0L;
  244.     }
  245.     
  246.     /**** Header principal *****/
  247.     theITCopy = (Byte*) theIT;
  248.     
  249.     BlockMove( theITCopy, &ITinfo, sizeof( ITinfo));
  250.     theITCopy += 192;
  251.     
  252.     INT16(  &ITinfo.orderNum);
  253.     INT16(  &ITinfo.insNum);
  254.     INT16(  &ITinfo.smpNum);
  255.     INT16(  &ITinfo.patNum);
  256.     INT16(  &ITinfo.flags);
  257.     INT16(  &ITinfo.cwtv);
  258.     INT16(  &ITinfo.cmwt);
  259.     
  260. //    if( ITinfo.cmwt < 0x200) DebugStr("\pOld Ins Format");
  261.     
  262.     /**** Order Num *****/
  263.     ITinfo.orders = (unsigned char *) MADPlugNewPtr( ITinfo.orderNum, init);
  264.     if( ITinfo.orders == 0L) return MADNeedMemory;
  265.     BlockMove( theITCopy, ITinfo.orders, ITinfo.orderNum);
  266.     theITCopy += ITinfo.orderNum;
  267.     
  268.     /**** Ins Num *****/
  269.     ITinfo.parapins = (long *) MADPlugNewPtr( ITinfo.insNum * 4L, init);
  270.     if( ITinfo.parapins == 0L) return MADNeedMemory;
  271.     BlockMove( theITCopy, ITinfo.parapins, ITinfo.insNum * 4L);
  272.     theITCopy += ITinfo.insNum * 4L;
  273.     for( i = 0; i < ITinfo.insNum; i++)
  274.     {
  275.         INT32(  &ITinfo.parapins[ i]);
  276.     }
  277. //    if( ITinfo.insNum > 0) DebugStr("\pInsNum");
  278.     
  279.     /**** Samp Num *****/
  280.     ITinfo.parapsamp = (long *) MADPlugNewPtr( ITinfo.smpNum * 4L, init);
  281.     if( ITinfo.parapsamp == 0L) return MADNeedMemory;
  282.     BlockMove( theITCopy, ITinfo.parapsamp, ITinfo.smpNum * 4L);
  283.     theITCopy += ITinfo.smpNum * 4L;
  284.     for( i = 0; i < ITinfo.smpNum; i++)
  285.     {
  286.         INT32(  &ITinfo.parapsamp[ i]);
  287.     }
  288.     
  289.     /**** Pat Num *****/
  290.     ITinfo.parappat = (long *) MADPlugNewPtr( ITinfo.patNum * 4L, init);
  291.     if( ITinfo.parappat == 0L) return MADNeedMemory;
  292.     BlockMove( theITCopy, ITinfo.parappat, ITinfo.patNum * 4L);
  293.     theITCopy += ITinfo.patNum * 4L;
  294.     for( i = 0; i < ITinfo.patNum; i++)
  295.     {
  296.         INT32(  &ITinfo.parappat[ i]);
  297.     }
  298.     
  299.     if( ITinfo.flags & 4)
  300.     {
  301.         /**** Ins Data ****/
  302.     //    if( ITinfo.insNum > 64) ITinfo.insNum = 64;
  303.         ITinfo.insdata = (ITInsForm *) MADPlugNewPtr( sizeof(ITInsForm) * ITinfo.insNum, init);
  304.         if( ITinfo.insdata == 0L) return MADNeedMemory;
  305.         for (i = 0; i < ITinfo.insNum; i++)
  306.         {
  307.             theITCopy = (Byte*) theIT;
  308.             theITCopy += ITinfo.parapins[i];
  309.             
  310.             BlockMove( theITCopy, &ITinfo.insdata[i], sizeof( ITInsForm));
  311.             
  312.             if( !compMem( (Ptr) &ITinfo.insdata[i].ID, "IMPI", 4))
  313.             {
  314.                 DisposePtr( (Ptr) ITinfo.orders);            DisposePtr( (Ptr) ITinfo.parapins);
  315.                 DisposePtr( (Ptr) ITinfo.parappat);        DisposePtr( (Ptr) ITinfo.insdata);
  316.                 DisposePtr( (Ptr) ITinfo.parapsamp);
  317.                 
  318.                 return MADIncompatibleFile;
  319.             }
  320.         }
  321.     }
  322.     
  323.     /**** Samp Data ****/
  324.     //if( ITinfo.insNum > 64) ITinfo.insNum = 64;
  325.     ITinfo.sampdata = (ITSampForm *) MADPlugNewPtr( sizeof(ITSampForm) * ITinfo.smpNum, init);
  326.     if( ITinfo.sampdata == 0L) return MADNeedMemory;
  327.     for (i = 0; i < ITinfo.smpNum; i++)
  328.     {
  329.         theITCopy = (Byte*) theIT;
  330.         theITCopy += ITinfo.parapsamp[i];
  331.         
  332.         BlockMove( theITCopy, &ITinfo.sampdata[i], sizeof( ITSampForm));
  333.         
  334.         if( !compMem( (Ptr) &ITinfo.sampdata[i].ID, "IMPS", 4))
  335.         {
  336.             DisposePtr( (Ptr) ITinfo.orders);            DisposePtr( (Ptr) ITinfo.parapins);
  337.             DisposePtr( (Ptr) ITinfo.parappat);        DisposePtr( (Ptr) ITinfo.insdata);
  338.             DisposePtr( (Ptr) ITinfo.parapsamp);        DisposePtr( (Ptr) ITinfo.sampdata);
  339.             
  340.             return MADIncompatibleFile;
  341.         }
  342.         
  343.             INT32( &ITinfo.sampdata[i].length);
  344.             INT32( &ITinfo.sampdata[i].loopBegin);
  345.             INT32( &ITinfo.sampdata[i].loopEnd);
  346.             INT32( &ITinfo.sampdata[i].C5Speed);
  347.             INT32( &ITinfo.sampdata[i].SusLoopBegin);
  348.             INT32( &ITinfo.sampdata[i].SusLoopEnd);
  349.             INT32( &ITinfo.sampdata[i].samplePtr);
  350.             INT16( &ITinfo.sampdata[i].Convert);
  351.         
  352.         if( ITinfo.sampdata[i].length > 0)
  353.         {
  354.             theInstrument[ i] = (Ptr) theIT;
  355.             theInstrument[ i] += ITinfo.sampdata[i].samplePtr;
  356.         }
  357.         else theInstrument[ i] = 0;
  358.     }
  359.     
  360.     
  361.     // ******** Le IT a ÄtÄ lu et analysÄ ***********
  362.     // ******** Copie des informations dans le MAD ***
  363.     
  364.     theMAD->header = (MADSpec*) MADPlugNewPtrClear( sizeof( MADSpec), init);
  365.     if( theMAD->header == 0L) return MADNeedMemory;
  366.         
  367.     theMAD->header->MAD = 'MADI';
  368.     for(i=0; i<32; i++) theMAD->header->name[i] = 0;
  369.     for(i=0; i<28; i++) theMAD->header->name[i] = ITinfo.name[i];
  370.     
  371.     mystrcpy( theMAD->header->infos, (Ptr) "\pConverted by PlayerPRO IT Plug (⌐Antoine ROSSET <rossetantoine@bluewin.ch>)");
  372.     
  373.     theMAD->header->numPat            = ITinfo.patNum;
  374.     theMAD->header->numPointers    = ITinfo.orderNum;
  375.     theMAD->header->speed                = ITinfo.iSpeed;
  376.     theMAD->header->tempo                = ITinfo.iTempo;
  377.     
  378.     for(i=0; i<128; i++) theMAD->header->oPointers[ i] = 0;
  379.     for(i=0; i<ITinfo.orderNum; i++)
  380.     {
  381.         theMAD->header->oPointers[ i] = ITinfo.orders[i];
  382.         
  383.         if( theMAD->header->oPointers[ i] < 0 || theMAD->header->oPointers[ i] >= ITinfo.patNum) theMAD->header->oPointers[ i] = 0;
  384.     }
  385.     
  386.     for( i = 0; i < MAXTRACK; i++)
  387.     {
  388.         if( i < 64)
  389.         {
  390.             theMAD->header->chanPan[ i] = ITinfo.chanPan[ i];
  391.             theMAD->header->chanVol[ i] = ITinfo.chanVol[ i];
  392.         }
  393.         else
  394.         {
  395.             if( i % 2 == 0) theMAD->header->chanPan[ i] = MAX_PANNING/4;
  396.             else theMAD->header->chanPan[ i] = MAX_PANNING - MAX_PANNING/4;
  397.             
  398.             theMAD->header->chanVol[ i] = MAX_VOLUME;
  399.         }
  400.     }
  401.     theMAD->header->generalVol        = 64;
  402.     theMAD->header->generalSpeed    = 80;
  403.     theMAD->header->generalPitch    = 80;
  404.  
  405.     
  406.     // ********************
  407.     // ***** INSTRUMENTS *****
  408.     // ********************
  409.     
  410.     theMAD->fid = ( InstrData*) MADPlugNewPtrClear( sizeof( InstrData) * (long) MAXINSTRU, init);
  411.     if( !theMAD->fid) return MADNeedMemory;
  412.     
  413.     theMAD->sample = ( sData**) MADPlugNewPtrClear( sizeof( sData*) * (long) MAXINSTRU * (long) MAXSAMPLE, init);
  414.     if( !theMAD->sample) return MADNeedMemory;
  415.     
  416.     for( i = 0; i < MAXINSTRU; i++) theMAD->fid[ i].firstSample = i * MAXSAMPLE;
  417.     
  418.     for(i  = 0 ; i < MAXINSTRU; i++)
  419.     {
  420.         for( x = 0; x < MAXSAMPLE; x++) theMAD->sample[ i*MAXSAMPLE + x] = 0L;
  421.         
  422.         theMAD->fid[i].numSamples    = 0;
  423.     }
  424.     
  425.     if( ITinfo.flags & 4)        // USE INSTRUMENTS
  426.     {
  427.         short minSamp;
  428.     
  429.         for(i=0; i<ITinfo.insNum; i++)
  430.         {
  431.             InstrData        *curIns = &theMAD->fid[ i];
  432.             
  433.             curIns->type    = 0;
  434.             
  435.             {
  436.                 sData    *curData;
  437.                 short    prevSamp, zz;
  438.                 
  439.                 // Instrument conversion
  440.                 
  441.                 curIns->numSamples    = 0;    //ITinfo.insdata[ i].NoS;
  442.                 INT16( &ITinfo.insdata[ i].FadeOut);
  443.                 
  444.                 for( x = 0; x < 26; x++) curIns->name[ x] = ITinfo.insdata[ i].INSName[ x];
  445.                 
  446.                 for( x = 0; x < 96; x++) curIns->what[ x] = 0;
  447.                 
  448.                 minSamp = 200;
  449.                 for( x = 0; x < 120; x++)
  450.                 {
  451.                     if( ITinfo.insdata[ i].keyMap[ x].samp)
  452.                     {
  453.                         if( ITinfo.insdata[ i].keyMap[ x].samp-1 < minSamp) minSamp = ITinfo.insdata[ i].keyMap[ x].samp-1;
  454.                     }
  455.                 }
  456.                 
  457.                 for( x = 0; x < 120; x++)
  458.                 {
  459.                     if( ITinfo.insdata[ i].keyMap[ x].samp)
  460.                     {
  461.                         if( ITinfo.insdata[ i].keyMap[ x].note < 96)
  462.                         {
  463.                             curIns->what[ ITinfo.insdata[ i].keyMap[ x].note] = ITinfo.insdata[ i].keyMap[ x].samp-1 - minSamp;
  464.                         }
  465.                     }
  466.                 }
  467.                 
  468.                 // Samples conversion
  469.                 
  470.                 zz = 0;
  471.                 prevSamp = -1;
  472.                 
  473.                 for( zz = 0; zz < 120; zz++)
  474.                 {
  475.                     if( prevSamp != ITinfo.insdata[ i].keyMap[ zz].samp-1 && ITinfo.insdata[ i].keyMap[ zz].samp != 0)
  476.                     {
  477.                         prevSamp = ITinfo.insdata[ i].keyMap[ zz].samp-1;
  478.                         
  479.                         curData = theMAD->sample[ i*MAXSAMPLE + curIns->numSamples] = (sData*) MADPlugNewPtrClear( sizeof( sData), init);
  480.                         if( curData == 0L) return MADNeedMemory;
  481.                         
  482.                         curData->size            = ITinfo.sampdata[ prevSamp].length;
  483.                         
  484.                         if( ITinfo.sampdata[prevSamp].Flag&16)
  485.                         {
  486.                             curData->loopBeg     = ITinfo.sampdata[ prevSamp].loopBegin;
  487.                             curData->loopSize    = ITinfo.sampdata[ prevSamp].loopEnd - ITinfo.sampdata[ prevSamp].loopBegin;
  488.                         }
  489.                         else
  490.                         {
  491.                             curData->loopBeg = 0;
  492.                             curData->loopSize = 0;
  493.                         }
  494.                         
  495.                         curData->vol            = ITinfo.sampdata[ prevSamp].GvL;
  496.                         curData->c2spd        = ITinfo.sampdata[ prevSamp].C5Speed;
  497.                         curData->loopType    = 0;
  498.                         curData->amp            = 8;
  499.                     
  500.                         if( ITinfo.sampdata[prevSamp].Flag&2)
  501.                         {
  502.                             curData->amp        = 16;
  503.                             
  504.                             curData->size        *= 2;
  505.                             curData->loopBeg    *= 2;
  506.                             curData->loopSize *= 2;
  507.                         }
  508.                         
  509.                         
  510.                         curData->relNote    = -12;
  511.                         for( z = 0; z < 26; z++) curData->name[ z] = ITinfo.sampdata[ prevSamp].SampName[ z];
  512.                         
  513.                         curData->data         = MADPlugNewPtr( curData->size, init);
  514.                         if( curData->data == 0L) return MADNeedMemory;
  515.                         
  516.                         if( curData->data != 0L)
  517.                         {
  518.                             BlockMove( theInstrument[ prevSamp], curData->data, curData->size);
  519.                             
  520.                             if( !(ITinfo.sampdata[ prevSamp].Convert & 1) && curData->amp == 8)
  521.                             {
  522.                                 long temp;
  523.                                 
  524.                                 for( temp = 0; temp < curData->size; temp++) *(curData->data + temp) -= 0x80;
  525.                             }
  526.                             
  527.                             if( curData->amp == 16)
  528.                             {
  529.                                 unsigned short     *tempShort = (unsigned short*) curData->data;
  530.                                 long                         temp;
  531.                                 
  532.                                 for( temp = 0; temp < curData->size/2; temp++)
  533.                                 {
  534.                                     INT16(  &( (tempShort[ temp])));
  535.                                     
  536.                                     if( !(ITinfo.sampdata[ prevSamp].Convert & 1)) *(tempShort + temp) -= 0x8000;
  537.                                 }
  538.                             }
  539.                         }
  540.                         curIns->numSamples++;
  541.                     }
  542.                 }
  543.             }
  544.         }
  545.     }
  546.     else                                        // USE SAMPLES AS INSTRUMENTS
  547.     {
  548.         for(i=0; i<ITinfo.smpNum; i++)
  549.         {
  550.             InstrData        *curIns = &theMAD->fid[ i];
  551.             
  552.             curIns->type    = 0;
  553.             
  554.             if( theInstrument[ i] != 0L)
  555.             {
  556.                 sData    *curData;
  557.                 
  558.                 curIns->numSamples    = 1;
  559.                 curIns->volFade            = DEFAULT_VOLFADE;
  560.                 
  561.                 curData = theMAD->sample[ i*MAXSAMPLE + 0] = (sData*) MADPlugNewPtrClear( sizeof( sData), init);
  562.                 if( curData == 0L) return MADNeedMemory;
  563.                 
  564.                 curData->size            = ITinfo.sampdata[i].length;
  565.                 curData->loopBeg     = ITinfo.sampdata[i].loopBegin;
  566.                 curData->loopSize    = ITinfo.sampdata[i].loopEnd - ITinfo.sampdata[i].loopBegin;
  567.                 curData->vol            = ITinfo.sampdata[i].GvL;
  568.                 curData->c2spd        = ITinfo.sampdata[i].C5Speed;
  569.                 curData->loopType    = 0;
  570.                 curData->amp            = 8;
  571.                 
  572.                 if( ITinfo.sampdata[i].Flag&2)
  573.                 {
  574.                     curData->amp        = 16;
  575.                     
  576.                     curData->size        *= 2;
  577.                     curData->loopBeg    *= 2;
  578.                     curData->loopSize     *= 2;
  579.                 }
  580.                 
  581.                 curData->relNote    = -12;
  582.                 for( x = 0; x < 26; x++) curIns->name[x] = ITinfo.sampdata[i].SampName[x];
  583.                 
  584.                 curData->data         = MADPlugNewPtr( curData->size, init);
  585.                 if( curData->data == 0L) return MADNeedMemory;
  586.                 
  587.                 if( curData->data != 0L)
  588.                 {
  589.                     BlockMove( theInstrument[i], curData->data, curData->size);
  590.                     
  591.                     if( !(ITinfo.sampdata[i].Convert & 1) && curData->amp == 8)
  592.                     {
  593.                         long temp;
  594.                         
  595.                         for( temp = 0; temp < curData->size; temp++) *(curData->data + temp) -= 0x80;
  596.                     }
  597.                     
  598.                     if( curData->amp == 16)
  599.                     {
  600.                         unsigned short     *tempShort = (unsigned short*) curData->data;
  601.                         long                         temp;
  602.                         
  603.                         for( temp = 0; temp < curData->size/2; temp++)
  604.                         {
  605.                             INT16(  &( (tempShort[ temp])));
  606.                             
  607.                             if( !(ITinfo.sampdata[ i].Convert & 1)) *(tempShort + temp) -= 0x8000;
  608.                         }
  609.                     }
  610.                 }
  611.             }
  612.             else curIns->numSamples = 0;
  613.         }
  614.     }
  615.     //    *********************
  616.     //    *           Check MaxTrack         *
  617.     //    *********************
  618.     
  619.     maxTrack = 0;
  620.     
  621.     for( i = 0; i < theMAD->header->numPat ; i++)
  622.     {
  623.         ITPatForm        *curITPat;
  624.         
  625.         if( ITinfo.parappat[i])
  626.         {
  627.             curITPat = (ITPatForm*) (theIT + ITinfo.parappat[i]);
  628.             
  629.                 INT16(  &curITPat->length);
  630.                 INT16(  &curITPat->row);
  631.             
  632.             if( ITinfo.parappat[i] > 0)
  633.             {
  634.                 Ptr             curDataPat = curITPat->data;
  635.                 char            maskvariable = 0, prevmaskvariable[ MAXTRACK];
  636.                 Boolean        NeedChannelToRead = true;
  637.                 short            xx;
  638.                 
  639.                 for( xx = 0; xx < MAXTRACK; xx++) prevmaskvariable[ xx] = 0;
  640.                 
  641.                 Row = 0;
  642.                 while( Row < curITPat->row)
  643.                 {
  644.                         tempChar = *curDataPat;
  645.                         curDataPat++;
  646.                         
  647.                         if( tempChar == 0) Row++;
  648.                         else
  649.                         {
  650.                             if( NeedChannelToRead)
  651.                             {
  652.                                 // Channel
  653.                                 channel = (tempChar-1) & 63;
  654.                                 
  655.                                 if( channel > maxTrack) maxTrack = channel;
  656.                             }
  657.                             
  658.                             if(tempChar & 128)
  659.                             {
  660.                                 prevmaskvariable[ channel] = maskvariable = *curDataPat;
  661.                                 curDataPat++;
  662.                             }
  663.                             else maskvariable = prevmaskvariable[ channel];
  664.                             
  665.                             // NOTE
  666.                             if( maskvariable & 1) curDataPat++;
  667.                             if( maskvariable & 2) curDataPat++;
  668.                             if( maskvariable & 4) curDataPat++;
  669.                             if( maskvariable & 8) curDataPat += 2;
  670.                         }
  671.                 }
  672.                 
  673.                 if( curDataPat - curITPat->data !=  curITPat->length) return MADUnknowErr;
  674.             }
  675.         }
  676.     }
  677.     
  678.     maxTrack += 2;
  679.     maxTrack /= 2;
  680.     maxTrack *= 2;
  681.     
  682.     // ********************
  683.     // ***** TEMPORAIRE ******
  684.     // ********************
  685.     
  686.     theMAD->header->numChn = maxTrack;
  687.     
  688.     for( i = 0; i < MAXPATTERN; i++) theMAD->partition[ i] = 0L;
  689.     for( i = 0; i < theMAD->header->numPat ; i++)
  690.     {
  691.         ITPatForm        *curITPat;
  692.         
  693.         if( ITinfo.parappat[i])
  694.         {
  695.             curITPat = (ITPatForm*) (theIT + ITinfo.parappat[i]);
  696.             /*
  697.             curITPat->length     = INT16(  &curITPat->length);
  698.             curITPat->row         = INT16(  &curITPat->row);
  699.             
  700.             Deja fait dans la recherche du maxtrack
  701.             */
  702.             
  703.             theMAD->partition[ i] = (PatData*) MADPlugNewPtrClear( sizeof( PatHeader) + theMAD->header->numChn * curITPat->row * sizeof( Cmd), init);
  704.             if( theMAD->partition[ i] == 0L) return MADNeedMemory;
  705.             
  706.             theMAD->partition[ i]->header.size             = curITPat->row;
  707.             theMAD->partition[ i]->header.compMode     = 'NONE';
  708.             
  709.             for( x = 0; x < 20; x++) theMAD->partition[ i]->header.name[ x] = 0;
  710.             
  711.             MaxPtr = (Ptr) theMAD->partition[ i];
  712.             MaxPtr += sizeof( PatHeader) + theMAD->header->numChn * curITPat->row * sizeof( Cmd);
  713.             
  714.             for( Row = 0; Row < curITPat->row; Row++)
  715.             {
  716.                 for(z = 0; z < theMAD->header->numChn; z++)
  717.                 {
  718.                     aCmd = GetMADCommand( Row, z, theMAD->partition[ i]);
  719.                     
  720.                     aCmd->note        = 0xFF;
  721.                     aCmd->ins            = 0;
  722.                     aCmd->cmd            = 0;
  723.                     aCmd->arg            = 0;
  724.                     aCmd->vol            = 0xFF;
  725.                 }
  726.             }
  727.         }
  728.         else    // No Data for this pattern - Clear Pattern
  729.         {
  730.             #define DEFSIZE 10L
  731.         
  732.             theMAD->partition[ i] = (PatData*) MADPlugNewPtrClear( sizeof( PatHeader) + theMAD->header->numChn * DEFSIZE * sizeof( Cmd), init);
  733.             if( theMAD->partition[ i] == 0L) return MADNeedMemory;
  734.             
  735.             theMAD->partition[ i]->header.size             = DEFSIZE;
  736.             theMAD->partition[ i]->header.compMode     = 'NONE';
  737.             
  738.             MADstrcpy( theMAD->partition[ i]->header.name, "Not used pattern");
  739.             
  740.             for( Row = 0; Row < DEFSIZE; Row++)
  741.             {
  742.                 for(z = 0; z < theMAD->header->numChn; z++)
  743.                 {
  744.                     aCmd = GetMADCommand( Row, z, theMAD->partition[ i]);
  745.                     
  746.                     aCmd->note        = 0xFF;
  747.                     aCmd->ins            = 0;
  748.                     aCmd->cmd            = 0;
  749.                     aCmd->arg            = 0;
  750.                     aCmd->vol            = 0xFF;
  751.                 }
  752.             }
  753.         }
  754.         
  755.         if( ITinfo.parappat[i])
  756.         {
  757.             Ptr             curDataPat = curITPat->data;
  758.             char            maskvariable = 0, prevmaskvariable[ MAXTRACK];
  759.             Boolean        NeedChannelToRead = true;
  760.             short            xx;
  761.             
  762.             char            lastnote[ MAXTRACK], lastins[ MAXTRACK], lastvol[ MAXTRACK], lastcmd[ MAXTRACK], lasteff[ MAXTRACK];
  763.             
  764.             for( xx = 0; xx < MAXTRACK; xx++) prevmaskvariable[ xx] = 0;
  765.             
  766.             Row = 0;
  767.             while( Row < curITPat->row)
  768.             {
  769.                     tempChar = *curDataPat;
  770.                     curDataPat++;
  771.                     
  772.                     if( tempChar == 0) Row++;
  773.                     else
  774.                     {
  775.                         if( NeedChannelToRead)
  776.                         {
  777.                             // Channel
  778.                             channel = (tempChar-1) & 63;
  779.                             if( channel >= 0 && channel < theMAD->header->numChn) aCmd = GetMADCommand( Row, channel, theMAD->partition[ i]);
  780.                             else
  781.                             {
  782.                                 return MADUnknowErr;
  783.                             }
  784.                         }
  785.                         
  786.                         if(tempChar & 128)
  787.                         {
  788.                             prevmaskvariable[ channel] = maskvariable = *curDataPat;
  789.                             curDataPat++;
  790.                         }
  791.                         else maskvariable = prevmaskvariable[ channel];
  792.                         
  793.                         // NOTE
  794.                         if( maskvariable & 1 || maskvariable & 16)
  795.                         {
  796.                             char note;
  797.                             
  798.                             if( maskvariable & 1) note = *curDataPat++;
  799.                             else note = lastnote[ channel];
  800.                             lastnote[ channel] = note;
  801.                             
  802.                             if( aCmd != 0L)
  803.                             {
  804.                                 aCmd->note = note;
  805.                                 if( aCmd->note == 255) aCmd->note = 0xFE;
  806.                                 else if( aCmd->note < 0 || aCmd->note >= NUMBER_NOTES) aCmd->note = 0xFF;
  807.                             }
  808.                         }
  809.                         
  810.                         // INSTRUMENT
  811.                         if( maskvariable & 2 || maskvariable & 32)
  812.                         {
  813.                             char ins;
  814.                             
  815.                             if( maskvariable & 2) ins = *curDataPat++;
  816.                             else ins = lastins[ channel];
  817.                             lastins[ channel] = ins;
  818.                             
  819.                             if( aCmd != 0L) aCmd->ins = ins;
  820.                         }
  821.                         
  822.                         // VOLUME
  823.                         if( maskvariable & 4 || maskvariable & 64)
  824.                         {
  825.                             char vol;
  826.                             
  827.                             if( maskvariable & 4) vol = *curDataPat++;
  828.                             else vol = lastvol[ channel];
  829.                             lastvol[ channel] = vol;
  830.                             
  831.                             if( aCmd != 0L)
  832.                             {
  833.                                 aCmd->vol = vol;
  834.                                 if( aCmd->vol > 64) aCmd->vol = 64;
  835.                                 aCmd->vol += 0x10;
  836.                             }
  837.                         }
  838.                         else aCmd->vol = 255;
  839.                         
  840.                         // PARAMETER
  841.                         if( maskvariable & 8 || maskvariable & 128)
  842.                         {
  843.                             char eff, cmd;
  844.                             
  845.                             if( maskvariable & 8)
  846.                             {
  847.                                 eff = *curDataPat++;
  848.                                 cmd = *curDataPat++;
  849.                             }
  850.                             else
  851.                             {
  852.                                 eff = lasteff[ channel];
  853.                                 cmd = lastcmd[ channel];
  854.                             }
  855.                             lasteff[ channel] = eff;
  856.                             lastcmd[ channel] = cmd;
  857.                             
  858.                             if( aCmd != 0L)
  859.                             {
  860.                                     ConvertITEffect( eff, cmd, &aCmd->cmd, &aCmd->arg);
  861.                             }
  862.                         }
  863.                     }
  864.             }
  865.             
  866.             if( curDataPat - curITPat->data !=  curITPat->length) return MADUnknowErr;
  867.         }
  868.     }
  869.     
  870.     DisposePtr( (Ptr) ITinfo.orders);            DisposePtr( (Ptr) ITinfo.parapins);
  871.     DisposePtr( (Ptr) ITinfo.parappat);        DisposePtr( (Ptr) ITinfo.insdata);
  872.     DisposePtr( (Ptr) ITinfo.parapsamp);        DisposePtr( (Ptr) ITinfo.sampdata);
  873.  
  874.     return noErr;
  875. }
  876.  
  877. OSErr ExtractITInfo( PPInfoRec *info, Ptr AlienFile)
  878. {
  879.     short            i;
  880.     ITForm        ITinfo;
  881.     /********************************/
  882.  
  883.     /**** Header principal *****/
  884.     BlockMove( AlienFile, &ITinfo, 96);
  885.     
  886.     /*** Signature ***/
  887.     
  888.     info->signature = 'IT  ';
  889.     
  890.     /*** Internal name ***/
  891.     
  892.     ITinfo.name[ 26] = '\0';
  893.     MADstrcpy( info->internalFileName, ITinfo.name);
  894.     
  895.     /*** Total Patterns ***/
  896.     
  897.     INT16(  &ITinfo.patNum);
  898.     info->totalPatterns = ITinfo.patNum;
  899.     
  900.     /*** Partition Length ***/
  901.     
  902.     INT16( &ITinfo.orderNum);
  903.     info->partitionLength = ITinfo.orderNum;
  904.     
  905.     /*** Total Instruments ***/
  906.     
  907.     INT16(  &ITinfo.insNum);
  908.     info->totalInstruments = ITinfo.insNum;
  909.     
  910.     /*** Tracks ***/
  911.     
  912.     //info->totalTracks     = INT16(  &ITinfo.insNum);
  913.     
  914.     MADstrcpy( info->formatDescription, "IT Plug");
  915.     
  916.     return noErr;
  917. }
  918.  
  919. OSErr TestITFile( Ptr AlienFile)
  920. {
  921. ITForm    *myIT = ( ITForm*) AlienFile;
  922.  
  923.     if( compMem( (Ptr) &myIT->ID, "IMPM", 4)) return   noErr;
  924.     else return  MADFileNotSupportedByThisPlug;
  925. }
  926.  
  927. #ifndef _MAC_H
  928.  
  929. extern "C" EXP OSErr FillPlug( PlugInfo *p);
  930. extern "C" EXP OSErr mainPLUG( OSType order, Ptr AlienFileName, MADMusic *MadFile, PPInfoRec *info, MADDriverSettings *init);
  931.  
  932. EXP OSErr FillPlug( PlugInfo *p)        // Function USED IN DLL - For PC & BeOS
  933. {
  934.     MADstrcpy( p->type,         ".IT");
  935.     MADstrcpy( p->MenuName,     "IT Files");
  936.     p->mode    =    'EXIM';
  937.     
  938.     return noErr;
  939. }
  940. #endif
  941.  
  942. #ifdef _MAC_H
  943. EXP OSErr main( OSType order, Ptr AlienFileName, MADMusic *MadFile, PPInfoRec *info, MADDriverSettings *init)
  944. #else
  945. OSErr mainPLUG( OSType order, Ptr AlienFileName, MADMusic *MadFile, PPInfoRec *info, MADDriverSettings *init)
  946. #endif
  947. {
  948.     OSErr        myErr;
  949.     Ptr            AlienFile;
  950.     long        sndSize;
  951.     UNFILE    iFileRefI;
  952.     
  953.     #ifdef _MAC_H
  954.     #ifndef powerc
  955.         long    oldA4 = SetCurrentA4();             //this call is necessary for strings in 68k code resources
  956.     #endif
  957.     #endif
  958.     
  959.     myErr = noErr;
  960.  
  961.     switch( order)
  962.     {
  963.         case 'IMPL':
  964.             iFileRefI = iFileOpen( AlienFileName);
  965.             if( iFileRefI)
  966.             {
  967.                 sndSize = iGetEOF( iFileRefI);
  968.                 
  969.                 // ** MEMORY Test Start
  970.                 AlienFile = MADPlugNewPtr( sndSize * 2L, init);
  971.                 if( AlienFile == 0L) myErr = MADNeedMemory;
  972.                 // ** MEMORY Test End
  973.                 
  974.                 else
  975.                 {
  976.                     DisposePtr( AlienFile);
  977.                     
  978.                     AlienFile = MADPlugNewPtr( sndSize, init);
  979.                     if( AlienFile == 0L) myErr = MADNeedMemory;
  980.                     else
  981.                     {
  982.                         myErr = iRead( sndSize, AlienFile, iFileRefI);
  983.                         
  984.                         if( myErr == noErr)
  985.                         {
  986.                             myErr = TestITFile( AlienFile);
  987.                             if( myErr == noErr)
  988.                             {
  989.                                 myErr = ConvertIT2Mad( AlienFile,  sndSize, MadFile, init);
  990.                             }
  991.                         }
  992.                     }
  993.                     DisposePtr( AlienFile);    AlienFile = 0L;
  994.                 }
  995.                 iClose( iFileRefI);
  996.             }
  997.         break;
  998.         
  999.         case 'TEST':
  1000.                 iFileRefI = iFileOpen( AlienFileName);
  1001.             if( iFileRefI)
  1002.             {
  1003.                 sndSize = 1024L;
  1004.                 
  1005.                 AlienFile = MADPlugNewPtr( sndSize, init);
  1006.                 if( AlienFile == 0L) myErr = MADNeedMemory;
  1007.                 else
  1008.                 {
  1009.                     myErr = iRead( sndSize, AlienFile, iFileRefI);
  1010.                     
  1011.                     myErr = TestITFile( AlienFile);
  1012.                     
  1013.                     DisposePtr( AlienFile);    AlienFile = 0L;
  1014.                 }
  1015.                 iClose( iFileRefI);
  1016.             }
  1017.         break;
  1018.  
  1019.         case 'INFO':
  1020.             iFileRefI = iFileOpen( AlienFileName);
  1021.             if( iFileRefI)
  1022.             {
  1023.                 info->fileSize = iGetEOF( iFileRefI);
  1024.             
  1025.                 sndSize = 5000L;    // Read only 5000 first bytes for optimisation
  1026.                 
  1027.                 AlienFile = MADPlugNewPtr( sndSize, init);
  1028.                 if( AlienFile == 0L) myErr = MADNeedMemory;
  1029.                 else
  1030.                 {
  1031.                     myErr = iRead( sndSize, AlienFile, iFileRefI);
  1032.                     if( myErr == noErr)
  1033.                     {
  1034.                         myErr = TestITFile( AlienFile);
  1035.                         if( !myErr) myErr = ExtractITInfo( info, AlienFile);
  1036.                     }
  1037.                     DisposePtr( AlienFile);    AlienFile = 0L;
  1038.                 }
  1039.                 iClose( iFileRefI);
  1040.             }
  1041.         break;
  1042.         
  1043.         default:
  1044.             myErr = MADOrderNotImplemented;
  1045.         break;
  1046.     }
  1047.     
  1048.     #ifdef _MAC_H
  1049.     #ifndef powerc
  1050.         SetA4( oldA4);
  1051.     #endif
  1052.     #endif
  1053.  
  1054.     return myErr;
  1055. }