From: <sag...@us...> - 2013-06-30 18:20:37
|
Revision: 2452 http://sourceforge.net/p/modplug/code/2452 Author: saga-games Date: 2013-06-30 18:20:28 +0000 (Sun, 30 Jun 2013) Log Message: ----------- [Ref] S3I loader uses existing code from S3M loader now. Modified Paths: -------------- trunk/OpenMPT/mptrack/mptrack_08.vcproj trunk/OpenMPT/mptrack/mptrack_10.vcxproj trunk/OpenMPT/mptrack/mptrack_10.vcxproj.filters trunk/OpenMPT/soundlib/Load_s3m.cpp trunk/OpenMPT/soundlib/SampleFormats.cpp trunk/OpenMPT/soundlib/Sndfile.h Added Paths: ----------- trunk/OpenMPT/soundlib/S3MTools.cpp trunk/OpenMPT/soundlib/S3MTools.h Modified: trunk/OpenMPT/mptrack/mptrack_08.vcproj =================================================================== --- trunk/OpenMPT/mptrack/mptrack_08.vcproj 2013-06-30 17:53:24 UTC (rev 2451) +++ trunk/OpenMPT/mptrack/mptrack_08.vcproj 2013-06-30 18:20:28 UTC (rev 2452) @@ -1449,6 +1449,14 @@ > </File> <File + RelativePath="..\soundlib\S3MTools.cpp" + > + </File> + <File + RelativePath="..\soundlib\S3MTools.h" + > + </File> + <File RelativePath="..\soundlib\WAVTools.cpp" > </File> Modified: trunk/OpenMPT/mptrack/mptrack_10.vcxproj =================================================================== --- trunk/OpenMPT/mptrack/mptrack_10.vcxproj 2013-06-30 17:53:24 UTC (rev 2451) +++ trunk/OpenMPT/mptrack/mptrack_10.vcxproj 2013-06-30 18:20:28 UTC (rev 2452) @@ -287,6 +287,7 @@ <ClCompile Include="..\soundlib\patternContainer.cpp" /> <ClCompile Include="..\soundlib\plugins\JBridge.cpp" /> <ClCompile Include="..\soundlib\RowVisitor.cpp" /> + <ClCompile Include="..\soundlib\S3MTools.cpp" /> <ClCompile Include="..\soundlib\SampleFormats.cpp" /> <ClCompile Include="..\soundlib\SampleIO.cpp" /> <ClCompile Include="..\soundlib\Sndfile.cpp" /> @@ -506,6 +507,7 @@ <ClInclude Include="..\soundlib\plugins\PlugInterface.h" /> <ClInclude Include="..\soundlib\Resampler.h" /> <ClInclude Include="..\soundlib\RowVisitor.h" /> + <ClInclude Include="..\soundlib\S3MTools.h" /> <ClInclude Include="..\soundlib\SampleFormatConverters.h" /> <ClInclude Include="..\soundlib\SampleIO.h" /> <ClInclude Include="..\soundlib\Sndfile.h" /> Modified: trunk/OpenMPT/mptrack/mptrack_10.vcxproj.filters =================================================================== --- trunk/OpenMPT/mptrack/mptrack_10.vcxproj.filters 2013-06-30 17:53:24 UTC (rev 2451) +++ trunk/OpenMPT/mptrack/mptrack_10.vcxproj.filters 2013-06-30 18:20:28 UTC (rev 2452) @@ -478,6 +478,9 @@ <ClCompile Include="MPTrackUtil.cpp"> <Filter>Source Files\mptrack</Filter> </ClCompile> + <ClCompile Include="..\soundlib\S3MTools.cpp"> + <Filter>Source Files\soundlib\Module Loaders</Filter> + </ClCompile> </ItemGroup> <ItemGroup> <ClInclude Include="..\soundlib\Loaders.h"> @@ -879,6 +882,9 @@ <ClInclude Include="MPTrackUtil.h"> <Filter>Header Files\mptrack</Filter> </ClInclude> + <ClInclude Include="..\soundlib\S3MTools.h"> + <Filter>Source Files\soundlib\Module Loaders</Filter> + </ClInclude> </ItemGroup> <ItemGroup> <None Include="res\bitmap1.bmp"> Modified: trunk/OpenMPT/soundlib/Load_s3m.cpp =================================================================== --- trunk/OpenMPT/soundlib/Load_s3m.cpp 2013-06-30 17:53:24 UTC (rev 2451) +++ trunk/OpenMPT/soundlib/Load_s3m.cpp 2013-06-30 18:20:28 UTC (rev 2452) @@ -10,6 +10,7 @@ #include "stdafx.h" #include "Loaders.h" +#include "S3MTools.h" #include "../common/version.h" #ifdef MODPLUG_TRACKER #include "../mptrack/moddoc.h" // Logging @@ -149,246 +150,6 @@ } -#ifdef NEEDS_PRAGMA_PACK -#pragma pack(push, 1) -#endif - -// S3M File Header -struct PACKED S3MFileHeader -{ - // Magic Bytes - enum S3MMagic - { - idSCRM = 0x4D524353, - idEOF = 0x1A, - idS3MType = 0x10, - idPanning = 0xFC, - }; - - // Tracker Versions in the cwtv field - enum S3MTrackerVersions - { - trackerMask = 0xF000, - versionMask = 0x0FFF, - - trkScreamTracker = 0x1000, - trkImagoOrpheus = 0x2000, - trkImpulseTracker = 0x3000, - trkSchismTracker = 0x4000, - trkOpenMPT = 0x5000, - trkBeRoTracker = 0x6000, - trkCreamTracker = 0x7000, - - trkST3_20 = 0x1320, - trkIT2_14 = 0x3214, - trkBeRoTrackerOld = 0x4100, // Used from 2004 to 2012 - }; - - // Flags - enum S3MHeaderFlags - { - zeroVolOptim = 0x08, // Volume 0 optimisations - amigaLimits = 0x10, // Enforce Amiga limits - fastVolumeSlides = 0x40, // Fast volume slides (like in ST3.00) - }; - - // S3M Format Versions - enum S3MFormatVersion - { - oldVersion = 0x01, // Old Version, signed samples - newVersion = 0x02, // New Version, unsigned samples - }; - - char name[28]; // Song Title - uint8 dosEof; // Supposed to be 0x1A, but even ST3 seems to ignore this sometimes (see STRSHINE.S3M by Purple Motion) - uint8 fileType; // File Type, 0x10 = ST3 module - char reserved1[2]; // Reserved - uint16 ordNum; // Number of order items - uint16 smpNum; // Number of sample parapointers - uint16 patNum; // Number of pattern parapointers - uint16 flags; // Flags, see S3MHeaderFlags - uint16 cwtv; // "Made With" Tracker ID, see S3MTrackerVersions - uint16 formatVersion; // Format Version, see S3MFormatVersion - uint32 magic; // "SCRM" magic bytes - uint8 globalVol; // Default Global Volume (0...64) - uint8 speed; // Default Speed (1...254) - uint8 tempo; // Default Tempo (33...255) - uint8 masterVolume; // Sample Volume (0...127, stereo if high bit is set) - uint8 ultraClicks; // Number of channels used for ultra click removal - uint8 usePanningTable; // 0xFC => read extended panning table - char reserved2[8]; // More reserved bytes - uint16 special; // Pointer to special custom data (unused) - uint8 channels[32]; // Channel setup - - // Convert all multi-byte numeric values to current platform's endianness or vice versa. - void ConvertEndianness() - { - SwapBytesLE(ordNum); - SwapBytesLE(smpNum); - SwapBytesLE(patNum); - SwapBytesLE(flags); - SwapBytesLE(cwtv); - SwapBytesLE(formatVersion); - SwapBytesLE(magic); - } -}; - -STATIC_ASSERT(sizeof(S3MFileHeader) == 96); - - -// S3M Sample Header -struct PACKED S3MSampleHeader -{ - enum SampleMagic - { - idSCRS = 0x53524353, - }; - - enum SampleType - { - typeNone = 0, - typePCM = 1, - typeAdMel = 2, - }; - - enum SampleFlags - { - smpLoop = 0x01, - smpStereo = 0x02, - smp16Bit = 0x04, - }; - - enum SamplePacking - { - pUnpacked = 0x00, // PCM - pDP30ADPCM = 0x01, // Unused packing type - pADPCM = 0x04, // MODPlugin ADPCM :( - }; - - uint8 sampleType; // Sample type, see SampleType - char filename[12]; // Sample filename - uint8 dataPointer[3]; // Pointer to sample data (divided by 16) - uint32 length; // Sample length, in samples - uint32 loopStart; // Loop start, in samples - uint32 loopEnd; // Loop end, in samples - uint8 defaultVolume; // Default volume (0...64) - char reserved1; // Reserved - uint8 pack; // Packing algorithm, SamplePacking - uint8 flags; // Sample flags - uint32 c5speed; // Middle-C frequency - char reserved2[12]; // Reserved + Internal ST3 stuff - char name[28]; // Sample name - uint32 magic; // "SCRS" magic bytes ("SCRI" for Adlib instruments) - - // Convert all multi-byte numeric values to current platform's endianness or vice versa. - void ConvertEndianness() - { - SwapBytesLE(length); - SwapBytesLE(loopStart); - SwapBytesLE(loopEnd); - SwapBytesLE(c5speed); - SwapBytesLE(magic); - } - - // Convert an S3M sample header to OpenMPT's internal sample header. - void ConvertToMPT(ModSample &mptSmp) const - { - mptSmp.Initialize(MOD_TYPE_S3M); - mpt::String::Read<mpt::String::maybeNullTerminated>(mptSmp.filename, filename); - - if((sampleType == typePCM || sampleType == typeNone) && magic == idSCRS) - { - // Sample Length and Loops - if(sampleType == typePCM) - { - mptSmp.nLength = length; - mptSmp.nLoopStart = MIN(loopStart, mptSmp.nLength - 1); - mptSmp.nLoopEnd = MIN(loopEnd, mptSmp.nLength); - mptSmp.uFlags.set(CHN_LOOP, (flags & smpLoop) != 0); - } - - if(mptSmp.nLoopEnd < 2 || mptSmp.nLoopStart >= mptSmp.nLoopEnd || mptSmp.nLoopEnd - mptSmp.nLoopStart < 1) - { - mptSmp.nLoopStart = mptSmp.nLoopEnd = 0; - mptSmp.uFlags.reset(); - } - - // Volume / Panning - mptSmp.nVolume = MIN(defaultVolume, 64) * 4; - - // C-5 frequency - mptSmp.nC5Speed = c5speed; - if(mptSmp.nC5Speed == 0) - { - mptSmp.nC5Speed = 8363; - } else if(mptSmp.nC5Speed < 1024) - { - mptSmp.nC5Speed = 1024; - } - } - } - - // Convert OpenMPT's internal sample header to an S3M sample header. - SmpLength ConvertToS3M(const ModSample &mptSmp) - { - SmpLength smpLength = 0; - mpt::String::Write<mpt::String::maybeNullTerminated>(filename, mptSmp.filename); - - if(mptSmp.pSample != nullptr) - { - sampleType = typePCM; - length = static_cast<uint32>(MIN(mptSmp.nLength, uint32_max)); - loopStart = static_cast<uint32>(MIN(mptSmp.nLoopStart, uint32_max)); - loopEnd = static_cast<uint32>(MIN(mptSmp.nLoopEnd, uint32_max)); - - smpLength = length; - - flags = (mptSmp.uFlags & CHN_LOOP) ? smpLoop : 0; - if(mptSmp.uFlags & CHN_16BIT) - { - flags |= smp16Bit; - } - if(mptSmp.uFlags & CHN_STEREO) - { - flags |= smpStereo; - } - } else - { - sampleType = typeNone; - } - - defaultVolume = static_cast<uint8>(MIN(mptSmp.nVolume / 4, 64)); - if(mptSmp.nC5Speed != 0) - { - c5speed = mptSmp.nC5Speed; - } else - { - c5speed = ModSample::TransposeToFrequency(mptSmp.RelativeTone, mptSmp.nFineTune); - } - magic = idSCRS; - - return smpLength; - } - - // Retrieve the internal sample format flags for this sample. - SampleIO GetSampleFormat(bool signedSamples) const - { - if(pack == S3MSampleHeader::pADPCM && !(flags & S3MSampleHeader::smp16Bit) && !(flags & S3MSampleHeader::smpStereo)) - { - // MODPlugin :( - return SampleIO(SampleIO::_8bit, SampleIO::mono, SampleIO::littleEndian, SampleIO::ADPCM); - } else - { - return SampleIO( - (flags & S3MSampleHeader::smp16Bit) ? SampleIO::_16bit : SampleIO::_8bit, - (flags & S3MSampleHeader::smpStereo) ? SampleIO::stereoSplit : SampleIO::mono, - SampleIO::littleEndian, - signedSamples ? SampleIO::signedPCM : SampleIO::unsignedPCM); - } - } -}; - - // Pattern decoding flags enum S3MPattern { @@ -403,14 +164,7 @@ s3mNoteNone = 0xFF, }; -STATIC_ASSERT(sizeof(S3MSampleHeader) == 80); - -#ifdef NEEDS_PRAGMA_PACK -#pragma pack(pop) -#endif - - // Functor for fixing PixPlay 4-Bit Zxx panning commands struct FixPixPlayPanning //====================== @@ -628,8 +382,8 @@ continue; } + sampleHeader.ConvertToMPT(Samples[smp + 1]); mpt::String::Read<mpt::String::nullTerminated>(m_szNames[smp + 1], sampleHeader.name); - sampleHeader.ConvertToMPT(Samples[smp + 1]); if(sampleHeader.sampleType >= S3MSampleHeader::typeAdMel) { Added: trunk/OpenMPT/soundlib/S3MTools.cpp =================================================================== --- trunk/OpenMPT/soundlib/S3MTools.cpp (rev 0) +++ trunk/OpenMPT/soundlib/S3MTools.cpp 2013-06-30 18:20:28 UTC (rev 2452) @@ -0,0 +1,143 @@ +/* + * S3MTools.cpp + * ------------ + * Purpose: Definition of S3M file structures and helper functions + * Notes : (currently none) + * Authors: OpenMPT Devs + * The OpenMPT source code is released under the BSD license. Read LICENSE for more details. + */ + + +#include "stdafx.h" +#include "Loaders.h" +#include "S3MTools.h" +#include "../common/StringFixer.h" + + +// Convert all multi-byte numeric values to current platform's endianness or vice versa. +void S3MFileHeader::ConvertEndianness() +//------------------------------------- +{ + SwapBytesLE(ordNum); + SwapBytesLE(smpNum); + SwapBytesLE(patNum); + SwapBytesLE(flags); + SwapBytesLE(cwtv); + SwapBytesLE(formatVersion); + SwapBytesLE(magic); +} + + +// Convert all multi-byte numeric values to current platform's endianness or vice versa. +void S3MSampleHeader::ConvertEndianness() +//--------------------------------------- +{ + SwapBytesLE(length); + SwapBytesLE(loopStart); + SwapBytesLE(loopEnd); + SwapBytesLE(c5speed); + SwapBytesLE(magic); +} + + +// Convert an S3M sample header to OpenMPT's internal sample header. +void S3MSampleHeader::ConvertToMPT(ModSample &mptSmp) const +//--------------------------------------------------------- +{ + mptSmp.Initialize(MOD_TYPE_S3M); + mpt::String::Read<mpt::String::maybeNullTerminated>(mptSmp.filename, filename); + + if((sampleType == typePCM || sampleType == typeNone) && magic == idSCRS) + { + // Sample Length and Loops + if(sampleType == typePCM) + { + mptSmp.nLength = length; + mptSmp.nLoopStart = MIN(loopStart, mptSmp.nLength - 1); + mptSmp.nLoopEnd = MIN(loopEnd, mptSmp.nLength); + mptSmp.uFlags.set(CHN_LOOP, (flags & smpLoop) != 0); + } + + if(mptSmp.nLoopEnd < 2 || mptSmp.nLoopStart >= mptSmp.nLoopEnd || mptSmp.nLoopEnd - mptSmp.nLoopStart < 1) + { + mptSmp.nLoopStart = mptSmp.nLoopEnd = 0; + mptSmp.uFlags.reset(); + } + + // Volume / Panning + mptSmp.nVolume = MIN(defaultVolume, 64) * 4; + + // C-5 frequency + mptSmp.nC5Speed = c5speed; + if(mptSmp.nC5Speed == 0) + { + mptSmp.nC5Speed = 8363; + } else if(mptSmp.nC5Speed < 1024) + { + mptSmp.nC5Speed = 1024; + } + } +} + + +// Convert OpenMPT's internal sample header to an S3M sample header. +SmpLength S3MSampleHeader::ConvertToS3M(const ModSample &mptSmp) +//-------------------------------------------------------------- +{ + SmpLength smpLength = 0; + mpt::String::Write<mpt::String::maybeNullTerminated>(filename, mptSmp.filename); + + if(mptSmp.pSample != nullptr) + { + sampleType = typePCM; + length = static_cast<uint32>(MIN(mptSmp.nLength, uint32_max)); + loopStart = static_cast<uint32>(MIN(mptSmp.nLoopStart, uint32_max)); + loopEnd = static_cast<uint32>(MIN(mptSmp.nLoopEnd, uint32_max)); + + smpLength = length; + + flags = (mptSmp.uFlags & CHN_LOOP) ? smpLoop : 0; + if(mptSmp.uFlags & CHN_16BIT) + { + flags |= smp16Bit; + } + if(mptSmp.uFlags & CHN_STEREO) + { + flags |= smpStereo; + } + } else + { + sampleType = typeNone; + } + + defaultVolume = static_cast<uint8>(MIN(mptSmp.nVolume / 4, 64)); + if(mptSmp.nC5Speed != 0) + { + c5speed = mptSmp.nC5Speed; + } else + { + c5speed = ModSample::TransposeToFrequency(mptSmp.RelativeTone, mptSmp.nFineTune); + } + magic = idSCRS; + + return smpLength; +} + + +// Retrieve the internal sample format flags for this sample. +SampleIO S3MSampleHeader::GetSampleFormat(bool signedSamples) const +//----------------------------------------------------------------- +{ + if(pack == S3MSampleHeader::pADPCM && !(flags & S3MSampleHeader::smp16Bit) && !(flags & S3MSampleHeader::smpStereo)) + { + // MODPlugin :( + return SampleIO(SampleIO::_8bit, SampleIO::mono, SampleIO::littleEndian, SampleIO::ADPCM); + } else + { + return SampleIO( + (flags & S3MSampleHeader::smp16Bit) ? SampleIO::_16bit : SampleIO::_8bit, + (flags & S3MSampleHeader::smpStereo) ? SampleIO::stereoSplit : SampleIO::mono, + SampleIO::littleEndian, + signedSamples ? SampleIO::signedPCM : SampleIO::unsignedPCM); + } +} \ No newline at end of file Added: trunk/OpenMPT/soundlib/S3MTools.h =================================================================== --- trunk/OpenMPT/soundlib/S3MTools.h (rev 0) +++ trunk/OpenMPT/soundlib/S3MTools.h 2013-06-30 18:20:28 UTC (rev 2452) @@ -0,0 +1,154 @@ +/* + * S3MTools.h + * ---------- + * Purpose: Definition of S3M file structures and helper functions + * Notes : (currently none) + * Authors: OpenMPT Devs + * The OpenMPT source code is released under the BSD license. Read LICENSE for more details. + */ + + +#pragma once + +#include "../soundlib/ModSample.h" +#include "../soundlib/SampleIO.h" + + +#ifdef NEEDS_PRAGMA_PACK +#pragma pack(push, 1) +#endif + +// S3M File Header +struct PACKED S3MFileHeader +{ + // Magic Bytes + enum S3MMagic + { + idSCRM = 0x4D524353, + idEOF = 0x1A, + idS3MType = 0x10, + idPanning = 0xFC, + }; + + // Tracker Versions in the cwtv field + enum S3MTrackerVersions + { + trackerMask = 0xF000, + versionMask = 0x0FFF, + + trkScreamTracker = 0x1000, + trkImagoOrpheus = 0x2000, + trkImpulseTracker = 0x3000, + trkSchismTracker = 0x4000, + trkOpenMPT = 0x5000, + trkBeRoTracker = 0x6000, + trkCreamTracker = 0x7000, + + trkST3_20 = 0x1320, + trkIT2_14 = 0x3214, + trkBeRoTrackerOld = 0x4100, // Used from 2004 to 2012 + }; + + // Flags + enum S3MHeaderFlags + { + zeroVolOptim = 0x08, // Volume 0 optimisations + amigaLimits = 0x10, // Enforce Amiga limits + fastVolumeSlides = 0x40, // Fast volume slides (like in ST3.00) + }; + + // S3M Format Versions + enum S3MFormatVersion + { + oldVersion = 0x01, // Old Version, signed samples + newVersion = 0x02, // New Version, unsigned samples + }; + + char name[28]; // Song Title + uint8 dosEof; // Supposed to be 0x1A, but even ST3 seems to ignore this sometimes (see STRSHINE.S3M by Purple Motion) + uint8 fileType; // File Type, 0x10 = ST3 module + char reserved1[2]; // Reserved + uint16 ordNum; // Number of order items + uint16 smpNum; // Number of sample parapointers + uint16 patNum; // Number of pattern parapointers + uint16 flags; // Flags, see S3MHeaderFlags + uint16 cwtv; // "Made With" Tracker ID, see S3MTrackerVersions + uint16 formatVersion; // Format Version, see S3MFormatVersion + uint32 magic; // "SCRM" magic bytes + uint8 globalVol; // Default Global Volume (0...64) + uint8 speed; // Default Speed (1...254) + uint8 tempo; // Default Tempo (33...255) + uint8 masterVolume; // Sample Volume (0...127, stereo if high bit is set) + uint8 ultraClicks; // Number of channels used for ultra click removal + uint8 usePanningTable; // 0xFC => read extended panning table + char reserved2[8]; // More reserved bytes + uint16 special; // Pointer to special custom data (unused) + uint8 channels[32]; // Channel setup + + // Convert all multi-byte numeric values to current platform's endianness or vice versa. + void ConvertEndianness(); +}; + +STATIC_ASSERT(sizeof(S3MFileHeader) == 96); + + +// S3M Sample Header +struct PACKED S3MSampleHeader +{ + enum SampleMagic + { + idSCRS = 0x53524353, + }; + + enum SampleType + { + typeNone = 0, + typePCM = 1, + typeAdMel = 2, + }; + + enum SampleFlags + { + smpLoop = 0x01, + smpStereo = 0x02, + smp16Bit = 0x04, + }; + + enum SamplePacking + { + pUnpacked = 0x00, // PCM + pDP30ADPCM = 0x01, // Unused packing type + pADPCM = 0x04, // MODPlugin ADPCM :( + }; + + uint8 sampleType; // Sample type, see SampleType + char filename[12]; // Sample filename + uint8 dataPointer[3]; // Pointer to sample data (divided by 16) + uint32 length; // Sample length, in samples + uint32 loopStart; // Loop start, in samples + uint32 loopEnd; // Loop end, in samples + uint8 defaultVolume; // Default volume (0...64) + char reserved1; // Reserved + uint8 pack; // Packing algorithm, SamplePacking + uint8 flags; // Sample flags + uint32 c5speed; // Middle-C frequency + char reserved2[12]; // Reserved + Internal ST3 stuff + char name[28]; // Sample name + uint32 magic; // "SCRS" magic bytes ("SCRI" for Adlib instruments) + + // Convert all multi-byte numeric values to current platform's endianness or vice versa. + void ConvertEndianness(); + // Convert an S3M sample header to OpenMPT's internal sample header. + void ConvertToMPT(ModSample &mptSmp) const; + // Convert OpenMPT's internal sample header to an S3M sample header. + SmpLength ConvertToS3M(const ModSample &mptSmp); + // Retrieve the internal sample format flags for this sample. + SampleIO GetSampleFormat(bool signedSamples) const; +}; + +STATIC_ASSERT(sizeof(S3MSampleHeader) == 80); + + +#ifdef NEEDS_PRAGMA_PACK +#pragma pack(pop) +#endif Modified: trunk/OpenMPT/soundlib/SampleFormats.cpp =================================================================== --- trunk/OpenMPT/soundlib/SampleFormats.cpp 2013-06-30 17:53:24 UTC (rev 2451) +++ trunk/OpenMPT/soundlib/SampleFormats.cpp 2013-06-30 18:20:28 UTC (rev 2452) @@ -20,6 +20,7 @@ #include "Wav.h" #include "ITTools.h" #include "XMTools.h" +#include "S3MTools.h" #include "WAVTools.h" #include "../common/version.h" #include "ChunkReader.h" @@ -72,7 +73,7 @@ && !ReadITSSample(nSample, file) && !ReadPATSample(nSample, const_cast<BYTE*>(lpMemFile), dwFileLength) && !Read8SVXSample(nSample, const_cast<BYTE*>(lpMemFile), dwFileLength) - && !ReadS3ISample(nSample, const_cast<BYTE*>(lpMemFile), dwFileLength) + && !ReadS3ISample(nSample, file) && !ReadFLACSample(nSample, file) && !ReadMP3Sample(nSample, file)) { @@ -113,21 +114,22 @@ uint32 psig[20]; file.ReadArrayLE(psig); file.SkipBack(80); - if((psig[0] == LittleEndian(0x46464952) && psig[2] == LittleEndian(0x45564157)) // RIFF....WAVE signature - || (psig[0] == LittleEndian(0x5453494C) && psig[2] == LittleEndian(0x65766177)) // LIST....wave - || psig[76/4] == LittleEndian(0x53524353) // S3I signature - || (psig[0] == BigEndian(0x464F524D) && psig[2] == LittleEndian(0x46464941)) // AIFF signature - || (psig[0] == BigEndian(0x464F524D) && psig[2] == LittleEndian(0x43464941)) // AIFF-C signature - || (psig[0] == BigEndian(0x464F524D) && psig[2] == LittleEndian(0x58565338)) // 8SVX signature - || psig[0] == LittleEndian(ITSample::magic) // ITS signature + if( (!memcmp(&psig[0], "RIFF", 4) && !memcmp(&psig[2], "WAVE", 4)) // RIFF....WAVE signature + || (!memcmp(&psig[0], "LIST", 4) && !memcmp(&psig[2], "wave", 4)) // LIST....wave + || !memcmp(&psig[76 / 4], "SCRS", 4) // S3I signature + || (!memcmp(&psig[0], "FORM", 4) && + (!memcmp(&psig[2], "AIFF", 4) // AIFF signature + || !memcmp(&psig[2], "AIFC", 4) // AIFF-C signature + || !memcmp(&psig[2], "8SVX", 4))) // 8SVX signature + || psig[0] == LittleEndian(ITSample::magic) // ITS signature #ifndef NO_FLAC - || psig[0] == LittleEndian('CaLf') // FLAC signature + || !memcmp(&psig[0], "fLaC", 4) // FLAC signature #endif // NO_FLAC #ifndef NO_MP3_SAMPLES - || IsMPEG(file) // MPEG signature - || IsID3(file) // MP3 signature + || IsMPEG(file) // MPEG signature + || IsID3(file) // MP3 signature #endif // NO_MP3_SAMPLES - ) + ) { // Scanning free sample SAMPLEINDEX nSample = GetNextFreeSample(nInstr); @@ -906,74 +908,28 @@ ///////////////////////////////////////////////////////////// // S3I Samples -#ifdef NEEDS_PRAGMA_PACK -#pragma pack(push, 1) -#endif -typedef struct PACKED S3ISAMPLESTRUCT +bool CSoundFile::ReadS3ISample(SAMPLEINDEX nSample, FileReader &file) +//------------------------------------------------------------------- { - BYTE id; - char filename[12]; - BYTE reserved1; - WORD offset; - DWORD length; - DWORD loopstart; - DWORD loopend; - BYTE volume; - BYTE reserved2; - BYTE pack; - BYTE flags; - DWORD nC5Speed; - DWORD reserved3; - DWORD reserved4; - DWORD date; - char name[28]; - DWORD scrs; -} S3ISAMPLESTRUCT; + file.Rewind(); -STATIC_ASSERT(sizeof(S3ISAMPLESTRUCT) == 80); + S3MSampleHeader sampleHeader; + if(!file.ReadConvertEndianness(sampleHeader) + || sampleHeader.sampleType != S3MSampleHeader::typePCM + || sampleHeader.magic != S3MSampleHeader::idSCRS + || !file.Seek((sampleHeader.dataPointer[1] << 4) | (sampleHeader.dataPointer[2] << 12) | (sampleHeader.dataPointer[0] << 20))) + { + return false; + } -#ifdef NEEDS_PRAGMA_PACK -#pragma pack(pop) -#endif + DestroySampleThreadsafe(nSample); -bool CSoundFile::ReadS3ISample(SAMPLEINDEX nSample, const LPBYTE lpMemFile, DWORD dwFileLength) -//--------------------------------------------------------------------------------------------- -{ - // TODO: Rewrite using already existing structs from Load_s3m.cpp - S3ISAMPLESTRUCT *pss = (S3ISAMPLESTRUCT *)lpMemFile; ModSample &sample = Samples[nSample]; - DWORD dwMemPos; - SampleIO flags; - - if ((!lpMemFile) || (dwFileLength < sizeof(S3ISAMPLESTRUCT)) - || (pss->id != 0x01) || (((DWORD)pss->offset << 4) >= dwFileLength) - || (pss->scrs != 0x53524353)) return false; - - DestroySampleThreadsafe(nSample); - dwMemPos = pss->offset << 4; - - sample.Initialize(); - mpt::String::Read<mpt::String::maybeNullTerminated>(sample.filename, pss->filename); - mpt::String::Read<mpt::String::nullTerminated>(m_szNames[nSample], pss->name); - - sample.nLength = pss->length; - sample.nLoopStart = pss->loopstart; - sample.nLoopEnd = pss->loopend; - sample.nVolume = pss->volume << 2; - sample.nC5Speed = pss->nC5Speed; - if(pss->flags & 0x01) sample.uFlags |= CHN_LOOP; - + sampleHeader.ConvertToMPT(sample); + mpt::String::Read<mpt::String::nullTerminated>(m_szNames[nSample], sampleHeader.name); + sampleHeader.GetSampleFormat(false).ReadSample(sample, file); sample.Convert(MOD_TYPE_S3M, GetType()); - - FileReader chunk(lpMemFile + dwMemPos, dwFileLength - dwMemPos); - SampleIO( - (pss->flags & 0x04) ? SampleIO::_16bit : SampleIO::_8bit, - (pss->flags & 0x02) ? SampleIO::stereoSplit : SampleIO::mono, - SampleIO::littleEndian, - SampleIO::unsignedPCM) - .ReadSample(sample, chunk); - return true; } Modified: trunk/OpenMPT/soundlib/Sndfile.h =================================================================== --- trunk/OpenMPT/soundlib/Sndfile.h 2013-06-30 17:53:24 UTC (rev 2451) +++ trunk/OpenMPT/soundlib/Sndfile.h 2013-06-30 18:20:28 UTC (rev 2452) @@ -786,7 +786,7 @@ bool ReadSampleFromFile(SAMPLEINDEX nSample, FileReader &file); bool ReadWAVSample(SAMPLEINDEX nSample, FileReader &file, FileReader *wsmpChunk = nullptr); bool ReadPATSample(SAMPLEINDEX nSample, const LPBYTE lpMemFile, DWORD dwFileLength); - bool ReadS3ISample(SAMPLEINDEX nSample, const LPBYTE lpMemFile, DWORD dwFileLength); + bool ReadS3ISample(SAMPLEINDEX nSample, FileReader &file); bool ReadAIFFSample(SAMPLEINDEX nSample, FileReader &file); bool ReadXISample(SAMPLEINDEX nSample, FileReader &file); bool ReadITSSample(SAMPLEINDEX nSample, FileReader &file, bool rewind = true); This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |