mirror of
https://github.com/claunia/cuetools.net.git
synced 2025-12-16 18:14:25 +00:00
Switch to using libwavpack 5.1.0
This commit is contained in:
3
.gitignore
vendored
3
.gitignore
vendored
@@ -4,6 +4,7 @@ bin/
|
||||
lib/
|
||||
Release/
|
||||
Debug/
|
||||
*.vcxproj.filters
|
||||
*.vcxproj.user
|
||||
*.csproj.user
|
||||
*.sdf
|
||||
@@ -14,3 +15,5 @@ launchSettings.json
|
||||
/CUETools/TestResults
|
||||
/ThirdParty/*/libFLAC_dynamic.*
|
||||
/ThirdParty/*/MACLib.*
|
||||
/ThirdParty/*/wavpackdll.*
|
||||
/ThirdParty/*/libwavpack.*
|
||||
|
||||
@@ -1,39 +0,0 @@
|
||||
|
||||
using namespace System;
|
||||
using namespace System::Reflection;
|
||||
using namespace System::Runtime::CompilerServices;
|
||||
using namespace System::Runtime::InteropServices;
|
||||
using namespace System::Security::Permissions;
|
||||
|
||||
//
|
||||
// General Information about an assembly is controlled through the following
|
||||
// set of attributes. Change these attribute values to modify the information
|
||||
// associated with an assembly.
|
||||
//
|
||||
[assembly:AssemblyTitleAttribute("WavPackDotNet")];
|
||||
[assembly:AssemblyDescriptionAttribute("")];
|
||||
[assembly:AssemblyConfigurationAttribute("")];
|
||||
[assembly:AssemblyCompanyAttribute("")];
|
||||
[assembly:AssemblyProductAttribute("")];
|
||||
[assembly:AssemblyCopyrightAttribute("Copyright 2006-2007 Moitah")];
|
||||
[assembly:AssemblyTrademarkAttribute("")];
|
||||
[assembly:AssemblyCultureAttribute("")];
|
||||
|
||||
//
|
||||
// Version information for an assembly consists of the following four values:
|
||||
//
|
||||
// Major Version
|
||||
// Minor Version
|
||||
// Build Number
|
||||
// Revision
|
||||
//
|
||||
// You can specify all the value or you can default the Revision and Build Numbers
|
||||
// by using the '*' as shown below:
|
||||
|
||||
[assembly:AssemblyVersionAttribute("2.1.7.0")];
|
||||
|
||||
[assembly:ComVisible(false)];
|
||||
|
||||
[assembly:CLSCompliantAttribute(true)];
|
||||
|
||||
[assembly:SecurityPermission(SecurityAction::RequestMinimum, UnmanagedCode = true)];
|
||||
@@ -1,518 +0,0 @@
|
||||
// ****************************************************************************
|
||||
//
|
||||
// Copyright (c) 2006-2007 Moitah (moitah@yahoo.com)
|
||||
// All rights reserved.
|
||||
//
|
||||
// Redistribution and use in source and binary forms, with or without
|
||||
// modification, are permitted provided that the following conditions are met:
|
||||
//
|
||||
// * Redistributions of source code must retain the above copyright notice,
|
||||
// this list of conditions and the following disclaimer.
|
||||
// * Redistributions in binary form must reproduce the above copyright
|
||||
// notice, this list of conditions and the following disclaimer in the
|
||||
// documentation and/or other materials provided with the distribution.
|
||||
// * Neither the name of the author nor the names of its contributors may be
|
||||
// used to endorse or promote products derived from this software without
|
||||
// specific prior written permission.
|
||||
//
|
||||
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
// ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
|
||||
// LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
|
||||
// CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
|
||||
// SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
|
||||
// INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
|
||||
// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
|
||||
// ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
|
||||
// POSSIBILITY OF SUCH DAMAGE.
|
||||
//
|
||||
// ****************************************************************************
|
||||
|
||||
using namespace System;
|
||||
using namespace System::ComponentModel;
|
||||
using namespace System::Runtime::InteropServices;
|
||||
using namespace System::Security::Cryptography;
|
||||
using namespace System::IO;
|
||||
using namespace CUETools::Codecs;
|
||||
|
||||
#include <stdio.h>
|
||||
#include <memory.h>
|
||||
#include "wavpack.h"
|
||||
#include <string.h>
|
||||
|
||||
namespace CUETools { namespace Codecs { namespace WavPack {
|
||||
int write_block(void *id, void *data, int32_t length);
|
||||
|
||||
[UnmanagedFunctionPointer(CallingConvention::Cdecl)]
|
||||
public delegate int32_t DecoderReadDelegate(void *id, void *data, int32_t bcount);
|
||||
[UnmanagedFunctionPointer(CallingConvention::Cdecl)]
|
||||
public delegate uint32_t DecoderTellDelegate(void *id);
|
||||
[UnmanagedFunctionPointer(CallingConvention::Cdecl)]
|
||||
public delegate int DecoderSeekDelegate(void *id, uint32_t pos);
|
||||
[UnmanagedFunctionPointer(CallingConvention::Cdecl)]
|
||||
public delegate int DecoderSeekRelativeDelegate(void *id, int32_t delta, int mode);
|
||||
[UnmanagedFunctionPointer(CallingConvention::Cdecl)]
|
||||
public delegate int DecoderPushBackDelegate(void *id, int c);
|
||||
[UnmanagedFunctionPointer(CallingConvention::Cdecl)]
|
||||
public delegate uint32_t DecoderLengthDelegate(void *id);
|
||||
[UnmanagedFunctionPointer(CallingConvention::Cdecl)]
|
||||
public delegate int DecoderCanSeekDelegate(void *id);
|
||||
|
||||
[AudioDecoderClass("libwavpack", "wv", 1)]
|
||||
public ref class WavPackReader : public IAudioSource
|
||||
{
|
||||
public:
|
||||
WavPackReader(String^ path, Stream^ IO, Stream^ IO_WVC)
|
||||
{
|
||||
Initialize (path, IO, IO_WVC);
|
||||
}
|
||||
|
||||
WavPackReader(String^ path, Stream^ IO)
|
||||
{
|
||||
Initialize (path, IO, nullptr);
|
||||
}
|
||||
|
||||
void Initialize(String^ path, Stream^ IO, Stream^ IO_WVC)
|
||||
{
|
||||
char errorMessage[256];
|
||||
|
||||
_readDel = gcnew DecoderReadDelegate (this, &WavPackReader::ReadCallback);
|
||||
_tellDel = gcnew DecoderTellDelegate (this, &WavPackReader::TellCallback);
|
||||
_seekDel = gcnew DecoderSeekDelegate (this, &WavPackReader::SeekCallback);
|
||||
_seekRelDel = gcnew DecoderSeekRelativeDelegate (this, &WavPackReader::SeekRelCallback);
|
||||
_pushBackDel = gcnew DecoderPushBackDelegate (this, &WavPackReader::PushBackCallback);
|
||||
_lengthDel = gcnew DecoderLengthDelegate (this, &WavPackReader::LengthCallback);
|
||||
_canSeekDel = gcnew DecoderCanSeekDelegate (this, &WavPackReader::CanSeekCallback);
|
||||
|
||||
ioReader = new WavpackStreamReader;
|
||||
ioReader->read_bytes = (int32_t (*)(void *, void *, int32_t)) Marshal::GetFunctionPointerForDelegate(_readDel).ToPointer();
|
||||
ioReader->get_pos = (uint32_t (*)(void *)) Marshal::GetFunctionPointerForDelegate(_tellDel).ToPointer();
|
||||
ioReader->set_pos_abs = (int (*)(void *, uint32_t)) Marshal::GetFunctionPointerForDelegate(_seekDel).ToPointer();
|
||||
ioReader->set_pos_rel = (int (*)(void *, int32_t, int)) Marshal::GetFunctionPointerForDelegate(_seekRelDel).ToPointer();
|
||||
ioReader->push_back_byte = (int (*)(void *, int)) Marshal::GetFunctionPointerForDelegate(_pushBackDel).ToPointer();
|
||||
ioReader->get_length = (uint32_t (*)(void *)) Marshal::GetFunctionPointerForDelegate(_lengthDel).ToPointer();
|
||||
ioReader->can_seek = (int (*)(void *)) Marshal::GetFunctionPointerForDelegate(_canSeekDel).ToPointer();
|
||||
ioReader->write_bytes = NULL;
|
||||
|
||||
_IO_ungetc = _IO_WVC_ungetc = -1;
|
||||
|
||||
_path = path;
|
||||
|
||||
_IO = (IO != nullptr) ? IO : gcnew FileStream (path, FileMode::Open, FileAccess::Read, FileShare::Read);
|
||||
_IO_WVC = (IO != nullptr) ? IO_WVC : System::IO::File::Exists (path+"c") ? gcnew FileStream (path+"c", FileMode::Open, FileAccess::Read, FileShare::Read) : nullptr;
|
||||
|
||||
_wpc = WavpackOpenFileInputEx (ioReader, "v", _IO_WVC != nullptr ? "c" : NULL, errorMessage, OPEN_WVC, 0);
|
||||
if (_wpc == NULL) {
|
||||
throw gcnew Exception("Unable to initialize the decoder.");
|
||||
}
|
||||
|
||||
pcm = gcnew AudioPCMConfig(
|
||||
WavpackGetBitsPerSample(_wpc),
|
||||
WavpackGetNumChannels(_wpc),
|
||||
(int)WavpackGetSampleRate(_wpc),
|
||||
(AudioPCMConfig::SpeakerConfig)WavpackGetChannelMask(_wpc));
|
||||
_sampleCount = WavpackGetNumSamples(_wpc);
|
||||
_sampleOffset = 0;
|
||||
}
|
||||
|
||||
~WavPackReader()
|
||||
{
|
||||
delete ioReader;
|
||||
}
|
||||
|
||||
virtual property AudioPCMConfig^ PCM {
|
||||
AudioPCMConfig^ get() {
|
||||
return pcm;
|
||||
}
|
||||
}
|
||||
|
||||
virtual property Int64 Length {
|
||||
Int64 get() {
|
||||
return _sampleCount;
|
||||
}
|
||||
}
|
||||
|
||||
virtual property Int64 Position {
|
||||
Int64 get() {
|
||||
return _sampleOffset;
|
||||
}
|
||||
void set(Int64 offset) {
|
||||
_sampleOffset = offset;
|
||||
if (!WavpackSeekSample(_wpc, offset)) {
|
||||
throw gcnew Exception("Unable to seek.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
virtual property Int64 Remaining {
|
||||
Int64 get() {
|
||||
return _sampleCount - _sampleOffset;
|
||||
}
|
||||
}
|
||||
|
||||
virtual property String^ Path {
|
||||
String^ get() {
|
||||
return _path;
|
||||
}
|
||||
}
|
||||
|
||||
virtual void Close()
|
||||
{
|
||||
if (_wpc != NULL)
|
||||
_wpc = WavpackCloseFile(_wpc);
|
||||
if (_IO != nullptr)
|
||||
{
|
||||
_IO->Close ();
|
||||
_IO = nullptr;
|
||||
}
|
||||
if (_IO_WVC != nullptr)
|
||||
{
|
||||
_IO_WVC->Close ();
|
||||
_IO_WVC = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
virtual int Read(AudioBuffer^ sampleBuffer, int maxLength)
|
||||
{
|
||||
sampleBuffer->Prepare(this, maxLength);
|
||||
|
||||
pin_ptr<Int32> pSampleBuffer = &sampleBuffer->Samples[0, 0];
|
||||
int samplesRead = WavpackUnpackSamples(_wpc, pSampleBuffer, sampleBuffer->Length);
|
||||
_sampleOffset += samplesRead;
|
||||
if (samplesRead != sampleBuffer->Length)
|
||||
throw gcnew Exception("Decoder returned a different number of samples than requested.");
|
||||
return sampleBuffer->Length;
|
||||
}
|
||||
|
||||
virtual property AudioDecoderSettings^ Settings {
|
||||
AudioDecoderSettings^ get(void) {
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
WavpackContext *_wpc;
|
||||
Int32 _sampleCount, _sampleOffset;
|
||||
AudioPCMConfig^ pcm;
|
||||
String^ _path;
|
||||
Stream^ _IO;
|
||||
Stream^ _IO_WVC;
|
||||
DecoderReadDelegate^ _readDel;
|
||||
DecoderTellDelegate^ _tellDel;
|
||||
DecoderSeekDelegate^ _seekDel;
|
||||
DecoderSeekRelativeDelegate^ _seekRelDel;
|
||||
DecoderPushBackDelegate^ _pushBackDel;
|
||||
DecoderLengthDelegate^ _lengthDel;
|
||||
DecoderCanSeekDelegate^ _canSeekDel;
|
||||
array<unsigned char>^ _readBuffer;
|
||||
int _IO_ungetc, _IO_WVC_ungetc;
|
||||
WavpackStreamReader* ioReader;
|
||||
|
||||
int32_t ReadCallback (void *id, void *data, int32_t bcount)
|
||||
{
|
||||
Stream^ IO = (*(char*)id=='c') ? _IO_WVC : _IO;
|
||||
int IO_ungetc = (*(char*)id=='c') ? _IO_WVC_ungetc : _IO_ungetc;
|
||||
int unget_len = 0;
|
||||
|
||||
if (IO_ungetc != -1)
|
||||
{
|
||||
*(unsigned char*)data = (unsigned char) IO_ungetc;
|
||||
if (IO == _IO)
|
||||
_IO_ungetc = -1;
|
||||
else
|
||||
_IO_WVC_ungetc = -1;
|
||||
bcount --;
|
||||
if (!bcount)
|
||||
return 1;
|
||||
data = 1 + (unsigned char*)data;
|
||||
unget_len = 1;
|
||||
}
|
||||
|
||||
if (_readBuffer == nullptr || _readBuffer->Length < bcount)
|
||||
_readBuffer = gcnew array<unsigned char>(bcount < 0x4000 ? 0x4000 : bcount);
|
||||
int len = IO->Read (_readBuffer, 0, bcount);
|
||||
if (len) Marshal::Copy (_readBuffer, 0, (IntPtr)data, len);
|
||||
return len + unget_len;
|
||||
}
|
||||
|
||||
uint32_t TellCallback(void *id)
|
||||
{
|
||||
Stream^ IO = (*(char*)id=='c') ? _IO_WVC : _IO;
|
||||
return IO->Position;
|
||||
}
|
||||
|
||||
int SeekCallback (void *id, uint32_t pos)
|
||||
{
|
||||
Stream^ IO = (*(char*)id=='c') ? _IO_WVC : _IO;
|
||||
IO->Position = pos;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int SeekRelCallback (void *id, int32_t delta, int mode)
|
||||
{
|
||||
Stream^ IO = (*(char*)id=='c') ? _IO_WVC : _IO;
|
||||
switch (mode)
|
||||
{
|
||||
case SEEK_SET:
|
||||
IO->Seek (delta, System::IO::SeekOrigin::Begin);
|
||||
break;
|
||||
case SEEK_END:
|
||||
IO->Seek (delta, System::IO::SeekOrigin::End);
|
||||
break;
|
||||
case SEEK_CUR:
|
||||
IO->Seek (delta, System::IO::SeekOrigin::Current);
|
||||
break;
|
||||
default:
|
||||
return -1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int PushBackCallback (void *id, int c)
|
||||
{
|
||||
Stream^ IO = (*(char*)id=='c') ? _IO_WVC : _IO;
|
||||
if (IO == _IO)
|
||||
{
|
||||
if (_IO_ungetc != -1)
|
||||
throw gcnew Exception("Double PushBackCallback unsupported.");
|
||||
_IO_ungetc = c;
|
||||
} else
|
||||
{
|
||||
if (_IO_WVC_ungetc != -1)
|
||||
throw gcnew Exception("Double PushBackCallback unsupported.");
|
||||
_IO_WVC_ungetc = c;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
uint32_t LengthCallback (void *id)
|
||||
{
|
||||
Stream^ IO = (*(char*)id=='c') ? _IO_WVC : _IO;
|
||||
return IO->Length;
|
||||
}
|
||||
|
||||
int CanSeekCallback(void *id)
|
||||
{
|
||||
Stream^ IO = (*(char*)id=='c') ? _IO_WVC : _IO;
|
||||
return IO->CanSeek;
|
||||
}
|
||||
};
|
||||
|
||||
public ref class WavPackWriterSettings : AudioEncoderSettings
|
||||
{
|
||||
public:
|
||||
WavPackWriterSettings()
|
||||
: AudioEncoderSettings("fast normal high high+", "normal")
|
||||
{
|
||||
_md5Sum = true;
|
||||
_extraMode = 0;
|
||||
}
|
||||
|
||||
[DefaultValue(0)]
|
||||
[DisplayName("ExtraMode")]
|
||||
property Int32 ExtraMode {
|
||||
Int32 get() {
|
||||
return _extraMode;
|
||||
}
|
||||
void set(Int32 value) {
|
||||
if ((value < 0) || (value > 6)) {
|
||||
throw gcnew Exception("Invalid extra mode.");
|
||||
}
|
||||
_extraMode = value;
|
||||
}
|
||||
}
|
||||
|
||||
[DefaultValue(true)]
|
||||
[DisplayName("MD5")]
|
||||
[Description("Calculate MD5 hash for audio stream")]
|
||||
property bool MD5Sum {
|
||||
bool get() {
|
||||
return _md5Sum;
|
||||
}
|
||||
void set(bool value) {
|
||||
_md5Sum = value;
|
||||
}
|
||||
}
|
||||
|
||||
private:
|
||||
bool _md5Sum;
|
||||
Int32 _extraMode;
|
||||
};
|
||||
|
||||
[AudioEncoderClass("libwavpack", "wv", true, 1, WavPackWriterSettings::typeid)]
|
||||
public ref class WavPackWriter : IAudioDest
|
||||
{
|
||||
public:
|
||||
WavPackWriter(String^ path, WavPackWriterSettings^ settings)
|
||||
{
|
||||
_settings = settings;
|
||||
|
||||
if (_settings->PCM->BitsPerSample < 16 || _settings->PCM->BitsPerSample > 24)
|
||||
throw gcnew Exception("Bits per sample must be 16..24.");
|
||||
|
||||
_path = path;
|
||||
|
||||
IntPtr pathChars = Marshal::StringToHGlobalUni(path);
|
||||
_hFile = _wfopen((const wchar_t*)pathChars.ToPointer(), L"w+b");
|
||||
Marshal::FreeHGlobal(pathChars);
|
||||
if (!_hFile) {
|
||||
throw gcnew Exception("Unable to open file.");
|
||||
}
|
||||
}
|
||||
|
||||
virtual void Close()
|
||||
{
|
||||
if (_settings->MD5Sum)
|
||||
{
|
||||
_md5hasher->TransformFinalBlock (gcnew array<unsigned char>(1), 0, 0);
|
||||
pin_ptr<unsigned char> md5_digest = &_md5hasher->Hash[0];
|
||||
WavpackStoreMD5Sum (_wpc, md5_digest);
|
||||
}
|
||||
|
||||
WavpackFlushSamples(_wpc);
|
||||
_wpc = WavpackCloseFile(_wpc);
|
||||
fclose(_hFile);
|
||||
|
||||
if ((_finalSampleCount != 0) && (_samplesWritten != _finalSampleCount))
|
||||
throw gcnew Exception("Samples written differs from the expected sample count.");
|
||||
}
|
||||
|
||||
virtual void Delete()
|
||||
{
|
||||
try { Close (); } catch (Exception^) {}
|
||||
File::Delete(_path);
|
||||
}
|
||||
|
||||
virtual property Int64 FinalSampleCount
|
||||
{
|
||||
Int64 get()
|
||||
{
|
||||
return _finalSampleCount;
|
||||
}
|
||||
void set(Int64 value)
|
||||
{
|
||||
if (value < 0)
|
||||
throw gcnew Exception("Invalid final sample count.");
|
||||
if (_initialized)
|
||||
throw gcnew Exception("Final sample count cannot be changed after encoding begins.");
|
||||
_finalSampleCount = value;
|
||||
}
|
||||
}
|
||||
|
||||
virtual void Write(AudioBuffer^ sampleBuffer)
|
||||
{
|
||||
if (!_initialized)
|
||||
Initialize();
|
||||
|
||||
sampleBuffer->Prepare(this);
|
||||
|
||||
if (_settings->MD5Sum)
|
||||
UpdateHash(sampleBuffer->Bytes, sampleBuffer->ByteLength);
|
||||
|
||||
if ((_settings->PCM->BitsPerSample & 7) != 0)
|
||||
{
|
||||
if (_shiftedSampleBuffer == nullptr || _shiftedSampleBuffer.GetLength(0) < sampleBuffer->Length)
|
||||
_shiftedSampleBuffer = gcnew array<int,2>(sampleBuffer->Length, _settings->PCM->ChannelCount);
|
||||
int shift = 8 - (_settings->PCM->BitsPerSample & 7);
|
||||
int ch = _settings->PCM->ChannelCount;
|
||||
for (int i = 0; i < sampleBuffer->Length; i++)
|
||||
for (int c = 0; c < ch; c++)
|
||||
_shiftedSampleBuffer[i,c] = sampleBuffer->Samples[i,c] << shift;
|
||||
pin_ptr<Int32> pSampleBuffer = &_shiftedSampleBuffer[0, 0];
|
||||
if (!WavpackPackSamples(_wpc, (int32_t*)pSampleBuffer, sampleBuffer->Length))
|
||||
throw gcnew Exception("An error occurred while encoding.");
|
||||
} else
|
||||
{
|
||||
pin_ptr<Int32> pSampleBuffer = &sampleBuffer->Samples[0, 0];
|
||||
if (!WavpackPackSamples(_wpc, (int32_t*)pSampleBuffer, sampleBuffer->Length))
|
||||
throw gcnew Exception("An error occurred while encoding.");
|
||||
}
|
||||
|
||||
_samplesWritten += sampleBuffer->Length;
|
||||
}
|
||||
|
||||
virtual property String^ Path
|
||||
{
|
||||
String^ get() {
|
||||
return _path;
|
||||
}
|
||||
}
|
||||
|
||||
virtual property AudioEncoderSettings^ Settings
|
||||
{
|
||||
AudioEncoderSettings^ get()
|
||||
{
|
||||
return _settings;
|
||||
}
|
||||
}
|
||||
|
||||
void UpdateHash(array<unsigned char>^ buff, Int32 len)
|
||||
{
|
||||
if (!_initialized) Initialize();
|
||||
|
||||
if (!_settings->MD5Sum || !_md5hasher)
|
||||
throw gcnew Exception("MD5 not enabled.");
|
||||
_md5hasher->TransformBlock (buff, 0, len, buff, 0);
|
||||
}
|
||||
|
||||
private:
|
||||
FILE *_hFile;
|
||||
bool _initialized;
|
||||
WavpackContext *_wpc;
|
||||
Int32 _finalSampleCount, _samplesWritten;
|
||||
String^ _path;
|
||||
MD5^ _md5hasher;
|
||||
array<int,2>^ _shiftedSampleBuffer;
|
||||
WavPackWriterSettings^ _settings;
|
||||
|
||||
void Initialize() {
|
||||
WavpackConfig config;
|
||||
|
||||
_wpc = WavpackOpenFileOutput(write_block, _hFile, NULL);
|
||||
if (!_wpc) {
|
||||
throw gcnew Exception("Unable to create the encoder.");
|
||||
}
|
||||
|
||||
memset(&config, 0, sizeof(WavpackConfig));
|
||||
config.bits_per_sample = _settings->PCM->BitsPerSample;
|
||||
config.bytes_per_sample = (_settings->PCM->BitsPerSample + 7) / 8;
|
||||
config.num_channels = _settings->PCM->ChannelCount;
|
||||
config.channel_mask = (int32_t)_settings->PCM->ChannelMask;
|
||||
config.sample_rate = _settings->PCM->SampleRate;
|
||||
Int32 _compressionMode = _settings->EncoderModeIndex;
|
||||
if (_compressionMode == 0) config.flags |= CONFIG_FAST_FLAG;
|
||||
if (_compressionMode == 2) config.flags |= CONFIG_HIGH_FLAG;
|
||||
if (_compressionMode == 3) config.flags |= CONFIG_HIGH_FLAG | CONFIG_VERY_HIGH_FLAG;
|
||||
if (_settings->ExtraMode != 0)
|
||||
{
|
||||
config.flags |= CONFIG_EXTRA_MODE;
|
||||
config.xmode = _settings->ExtraMode;
|
||||
}
|
||||
if (_settings->MD5Sum)
|
||||
{
|
||||
_md5hasher = gcnew MD5CryptoServiceProvider ();
|
||||
config.flags |= CONFIG_MD5_CHECKSUM;
|
||||
}
|
||||
config.block_samples = (int)_settings->BlockSize;
|
||||
if (_settings->BlockSize > 0 && _settings->BlockSize < 2048)
|
||||
config.flags |= CONFIG_MERGE_BLOCKS;
|
||||
|
||||
if (!WavpackSetConfiguration(_wpc, &config, (_finalSampleCount == 0) ? -1 : _finalSampleCount)) {
|
||||
throw gcnew Exception("Invalid configuration setting.");
|
||||
}
|
||||
|
||||
if (!WavpackPackInit(_wpc)) {
|
||||
throw gcnew Exception("Unable to initialize the encoder.");
|
||||
}
|
||||
|
||||
_initialized = true;
|
||||
}
|
||||
};
|
||||
|
||||
#pragma unmanaged
|
||||
int write_block(void *id, void *data, int32_t length) {
|
||||
return (fwrite(data, 1, length, (FILE*)id) == length);
|
||||
}
|
||||
}}}
|
||||
@@ -1,229 +0,0 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|x64">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|x64">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<ProjectGuid>{CC2E74B6-534A-43D8-9F16-AC03FE955000}</ProjectGuid>
|
||||
<RootNamespace>CUETools.Codecs.WavPack</RootNamespace>
|
||||
<Keyword>ManagedCProj</Keyword>
|
||||
<WindowsTargetPlatformVersion>10.0.16299.0</WindowsTargetPlatformVersion>
|
||||
<TargetFrameworkVersion>v4.0</TargetFrameworkVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<CLRSupport>true</CLRSupport>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<CLRSupport>true</CLRSupport>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<CLRSupport>true</CLRSupport>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<CLRSupport>true</CLRSupport>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup>
|
||||
<_ProjectFileVersion>10.0.40219.1</_ProjectFileVersion>
|
||||
<OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(SolutionDir)..\bin\$(Configuration)\plugins\$(Platform)\net40\</OutDir>
|
||||
<IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(SolutionDir)..\obj\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
|
||||
<LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</LinkIncremental>
|
||||
<OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">$(SolutionDir)..\bin\$(Configuration)\plugins\$(Platform)\net40\</OutDir>
|
||||
<IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">$(SolutionDir)..\obj\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
|
||||
<LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</LinkIncremental>
|
||||
<OutDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(SolutionDir)..\bin\$(Configuration)\plugins\$(Platform)\net40\</OutDir>
|
||||
<IntDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(SolutionDir)..\obj\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
|
||||
<LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</LinkIncremental>
|
||||
<OutDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">$(SolutionDir)..\bin\$(Configuration)\plugins\$(Platform)\net40\</OutDir>
|
||||
<IntDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">$(SolutionDir)..\obj\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
|
||||
<LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|x64'">false</LinkIncremental>
|
||||
<CodeAnalysisRuleSet Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">AllRules.ruleset</CodeAnalysisRuleSet>
|
||||
<CodeAnalysisRules Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" />
|
||||
<CodeAnalysisRuleAssemblies Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" />
|
||||
<CodeAnalysisRuleSet Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">AllRules.ruleset</CodeAnalysisRuleSet>
|
||||
<CodeAnalysisRules Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" />
|
||||
<CodeAnalysisRuleAssemblies Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" />
|
||||
<CodeAnalysisRuleSet Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">AllRules.ruleset</CodeAnalysisRuleSet>
|
||||
<CodeAnalysisRules Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" />
|
||||
<CodeAnalysisRuleAssemblies Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" />
|
||||
<CodeAnalysisRuleSet Condition="'$(Configuration)|$(Platform)'=='Release|x64'">AllRules.ruleset</CodeAnalysisRuleSet>
|
||||
<CodeAnalysisRules Condition="'$(Configuration)|$(Platform)'=='Release|x64'" />
|
||||
<CodeAnalysisRuleAssemblies Condition="'$(Configuration)|$(Platform)'=='Release|x64'" />
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<ClCompile>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<AdditionalIncludeDirectories>../wavpack-4.5.0/include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<AssemblyDebug>true</AssemblyDebug>
|
||||
<RandomizedBaseAddress>false</RandomizedBaseAddress>
|
||||
<DataExecutionPrevention>
|
||||
</DataExecutionPrevention>
|
||||
<TargetMachine>MachineX86</TargetMachine>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
||||
<Midl>
|
||||
<TargetEnvironment>X64</TargetEnvironment>
|
||||
</Midl>
|
||||
<ClCompile>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<AdditionalIncludeDirectories>../wavpack-4.5.0/include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<AssemblyDebug>true</AssemblyDebug>
|
||||
<RandomizedBaseAddress>false</RandomizedBaseAddress>
|
||||
<DataExecutionPrevention>
|
||||
</DataExecutionPrevention>
|
||||
<TargetMachine>MachineX64</TargetMachine>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile>
|
||||
<AdditionalIncludeDirectories>../wavpack-4.5.0/include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalUsingDirectories>%(AdditionalUsingDirectories)</AdditionalUsingDirectories>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<RandomizedBaseAddress>false</RandomizedBaseAddress>
|
||||
<DataExecutionPrevention>
|
||||
</DataExecutionPrevention>
|
||||
<TargetMachine>MachineX86</TargetMachine>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
||||
<Midl>
|
||||
<TargetEnvironment>X64</TargetEnvironment>
|
||||
</Midl>
|
||||
<ClCompile>
|
||||
<AdditionalIncludeDirectories>../wavpack-4.5.0/include;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
|
||||
<AdditionalUsingDirectories>%(AdditionalUsingDirectories)</AdditionalUsingDirectories>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<AdditionalLibraryDirectories>%(AdditionalLibraryDirectories)</AdditionalLibraryDirectories>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
<RandomizedBaseAddress>false</RandomizedBaseAddress>
|
||||
<DataExecutionPrevention>
|
||||
</DataExecutionPrevention>
|
||||
<TargetMachine>MachineX64</TargetMachine>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="System">
|
||||
<CopyLocalSatelliteAssemblies>true</CopyLocalSatelliteAssemblies>
|
||||
<ReferenceOutputAssembly>true</ReferenceOutputAssembly>
|
||||
</Reference>
|
||||
<Reference Include="System.Data">
|
||||
<CopyLocalSatelliteAssemblies>true</CopyLocalSatelliteAssemblies>
|
||||
<ReferenceOutputAssembly>true</ReferenceOutputAssembly>
|
||||
</Reference>
|
||||
<Reference Include="System.Xml">
|
||||
<CopyLocalSatelliteAssemblies>true</CopyLocalSatelliteAssemblies>
|
||||
<ReferenceOutputAssembly>true</ReferenceOutputAssembly>
|
||||
</Reference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="AssemblyInfo.cpp" />
|
||||
<ClCompile Include="CUETools.Codecs.WavPack.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="resource.h" />
|
||||
<ClInclude Include="WavPack\wavpack.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="app.ico" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="app.rc" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\CUETools.Codecs\CUETools.Codecs.csproj">
|
||||
<Project>{6458a13a-30ef-45a9-9d58-e5031b17bee2}</Project>
|
||||
<Private>false</Private>
|
||||
<ReferenceOutputAssembly>true</ReferenceOutputAssembly>
|
||||
<CopyLocalSatelliteAssemblies>false</CopyLocalSatelliteAssemblies>
|
||||
<LinkLibraryDependencies>true</LinkLibraryDependencies>
|
||||
<UseLibraryDependencyInputs>false</UseLibraryDependencyInputs>
|
||||
</ProjectReference>
|
||||
<ProjectReference Include="..\wavpack-4.5.0\src\libwavpack.vcxproj">
|
||||
<Project>{5cccb9cf-0384-458f-ba08-72b73866840f}</Project>
|
||||
<ReferenceOutputAssembly>false</ReferenceOutputAssembly>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
||||
Binary file not shown.
|
Before Width: | Height: | Size: 1.1 KiB |
@@ -1,63 +0,0 @@
|
||||
// Microsoft Visual C++ generated resource script.
|
||||
//
|
||||
#include "resource.h"
|
||||
|
||||
#define APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#undef APSTUDIO_READONLY_SYMBOLS
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// English (U.S.) resources
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Icon
|
||||
//
|
||||
|
||||
// Icon placed first or with lowest ID value becomes application icon
|
||||
|
||||
LANGUAGE 9, 1
|
||||
#pragma code_page(1252)
|
||||
1 ICON "app.ico"
|
||||
|
||||
#ifdef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// TEXTINCLUDE
|
||||
//
|
||||
|
||||
1 TEXTINCLUDE
|
||||
BEGIN
|
||||
"resource.h\0"
|
||||
"\0"
|
||||
END
|
||||
|
||||
2 TEXTINCLUDE
|
||||
BEGIN
|
||||
"#include ""afxres.h""\r\n"
|
||||
"\0"
|
||||
END
|
||||
|
||||
3 TEXTINCLUDE
|
||||
BEGIN
|
||||
"\0"
|
||||
END
|
||||
|
||||
#endif // APSTUDIO_INVOKED
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
|
||||
#ifndef APSTUDIO_INVOKED
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Generated from the TEXTINCLUDE 3 resource.
|
||||
//
|
||||
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
#endif // not APSTUDIO_INVOKED
|
||||
|
||||
@@ -1,3 +0,0 @@
|
||||
//{{NO_DEPENDENCIES}}
|
||||
// Microsoft Visual C++ generated include file.
|
||||
// Used by app.rc
|
||||
29
CUETools.Codecs.libwavpack/CUETools.Codecs.libwavpack.csproj
Normal file
29
CUETools.Codecs.libwavpack/CUETools.Codecs.libwavpack.csproj
Normal file
@@ -0,0 +1,29 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net40;net20;netstandard2.0</TargetFrameworks>
|
||||
<Version>2.1.7.0</Version>
|
||||
<AssemblyName>CUETools.Codecs.libwavpack</AssemblyName>
|
||||
<RootNamespace>CUETools.Codecs.libwavpack</RootNamespace>
|
||||
<Product>CUETools</Product>
|
||||
<Description>A library for encoding wavpack using official encoder.</Description>
|
||||
<Copyright>Copyright (c) 2008-2018 Grigory Chudov</Copyright>
|
||||
<Authors>Grigory Chudov</Authors>
|
||||
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
|
||||
<OutputPath>..\bin\$(Configuration)\plugins</OutputPath>
|
||||
<RepositoryUrl>https://github.com/gchudov/cuetools.net</RepositoryUrl>
|
||||
<RepositoryType>git</RepositoryType>
|
||||
<Company />
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemDefinitionGroup>
|
||||
<ProjectReference>
|
||||
<Private>False</Private>
|
||||
</ProjectReference>
|
||||
</ItemDefinitionGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\CUETools.Codecs\CUETools.Codecs.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
213
CUETools.Codecs.libwavpack/Reader.cs
Normal file
213
CUETools.Codecs.libwavpack/Reader.cs
Normal file
@@ -0,0 +1,213 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.ComponentModel;
|
||||
using System.IO;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Text;
|
||||
using CUETools.Codecs;
|
||||
|
||||
namespace CUETools.Codecs.libwavpack
|
||||
{
|
||||
[AudioDecoderClass("libwavpack", "wv", 1)]
|
||||
public unsafe class Reader : IAudioSource
|
||||
{
|
||||
private readonly void* IO_ID_WV = ((IntPtr)1).ToPointer();
|
||||
private readonly void* IO_ID_WVC = ((IntPtr)2).ToPointer();
|
||||
public Reader(string path, Stream IO, Stream IO_WVC)
|
||||
{
|
||||
m_read_bytes = ReadCallback;
|
||||
m_get_pos = TellCallback;
|
||||
m_set_pos_abs = SeekCallback;
|
||||
m_set_pos_rel = SeekRelativeCallback;
|
||||
m_push_back_byte = PushBackCallback;
|
||||
m_get_length = LengthCallback;
|
||||
m_can_seek = CanSeekCallback;
|
||||
|
||||
m_ioReader = (WavpackStreamReader64*)Marshal.AllocHGlobal(sizeof(WavpackStreamReader64)).ToPointer();
|
||||
m_ioReader->read_bytes = Marshal.GetFunctionPointerForDelegate(m_read_bytes);
|
||||
m_ioReader->write_bytes = IntPtr.Zero;
|
||||
m_ioReader->get_pos = Marshal.GetFunctionPointerForDelegate(m_get_pos);
|
||||
m_ioReader->set_pos_abs = Marshal.GetFunctionPointerForDelegate(m_set_pos_abs);
|
||||
m_ioReader->set_pos_rel = Marshal.GetFunctionPointerForDelegate(m_set_pos_rel);
|
||||
m_ioReader->push_back_byte = Marshal.GetFunctionPointerForDelegate(m_push_back_byte);
|
||||
m_ioReader->get_length = Marshal.GetFunctionPointerForDelegate(m_get_length);
|
||||
m_ioReader->can_seek = Marshal.GetFunctionPointerForDelegate(m_can_seek);
|
||||
m_ioReader->truncate_here = IntPtr.Zero;
|
||||
m_ioReader->close = IntPtr.Zero;
|
||||
|
||||
_IO_ungetc = _IO_WVC_ungetc = -1;
|
||||
|
||||
_path = path;
|
||||
|
||||
_IO = (IO != null) ? IO : new FileStream (path, FileMode.Open, FileAccess.Read, FileShare.Read);
|
||||
_IO_WVC = (IO != null) ? IO_WVC : File.Exists (path+"c") ? new FileStream (path+"c", FileMode.Open, FileAccess.Read, FileShare.Read) : null;
|
||||
|
||||
string errorMessage;
|
||||
|
||||
_wpc = wavpackdll.WavpackOpenFileInputEx64(m_ioReader, IO_ID_WV, IO_ID_WVC, out errorMessage, OpenFlags.OPEN_WVC, 0);
|
||||
if (_wpc == null) {
|
||||
throw new Exception("Unable to initialize the decoder: " + errorMessage);
|
||||
}
|
||||
|
||||
pcm = new AudioPCMConfig(
|
||||
wavpackdll.WavpackGetBitsPerSample(_wpc),
|
||||
wavpackdll.WavpackGetNumChannels(_wpc),
|
||||
(int)wavpackdll.WavpackGetSampleRate(_wpc),
|
||||
(AudioPCMConfig.SpeakerConfig)wavpackdll.WavpackGetChannelMask(_wpc));
|
||||
_sampleCount = wavpackdll.WavpackGetNumSamples64(_wpc);
|
||||
_sampleOffset = 0;
|
||||
}
|
||||
|
||||
public Reader(string path, Stream IO)
|
||||
: this(path, IO, null)
|
||||
{}
|
||||
|
||||
public AudioDecoderSettings Settings => null;
|
||||
|
||||
public AudioPCMConfig PCM => pcm;
|
||||
|
||||
public string Path => _path;
|
||||
|
||||
public long Length => _sampleCount;
|
||||
|
||||
public long Position
|
||||
{
|
||||
get => _sampleOffset;
|
||||
|
||||
set
|
||||
{
|
||||
_sampleOffset = value;
|
||||
if (0 == wavpackdll.WavpackSeekSample64(_wpc, value))
|
||||
throw new Exception("unable to seek: " + wavpackdll.WavpackGetErrorMessage(_wpc));
|
||||
}
|
||||
}
|
||||
|
||||
public long Remaining => _sampleCount - _sampleOffset;
|
||||
|
||||
public void Close()
|
||||
{
|
||||
if (_wpc != null)
|
||||
_wpc = wavpackdll.WavpackCloseFile(_wpc);
|
||||
if (_IO != null)
|
||||
{
|
||||
_IO.Close ();
|
||||
_IO = null;
|
||||
}
|
||||
if (_IO_WVC != null)
|
||||
{
|
||||
_IO_WVC.Close ();
|
||||
_IO_WVC = null;
|
||||
}
|
||||
Marshal.FreeHGlobal((IntPtr)m_ioReader);
|
||||
m_ioReader = null;
|
||||
}
|
||||
|
||||
public int Read(AudioBuffer buff, int maxLength)
|
||||
{
|
||||
buff.Prepare(this, maxLength);
|
||||
fixed (int*pSampleBuffer = &buff.Samples[0,0])
|
||||
{
|
||||
uint samplesRead = wavpackdll.WavpackUnpackSamples(_wpc, pSampleBuffer, (uint)buff.Length);
|
||||
_sampleOffset += samplesRead;
|
||||
if (samplesRead != buff.Length)
|
||||
throw new Exception("Decoder returned a different number of samples than requested.");
|
||||
}
|
||||
return buff.Length;
|
||||
}
|
||||
|
||||
private int ReadCallback(void* id, void* data, int bcount)
|
||||
{
|
||||
Stream IO = (id == IO_ID_WVC) ? _IO_WVC : _IO;
|
||||
int IO_ungetc = (id == IO_ID_WVC) ? _IO_WVC_ungetc : _IO_ungetc;
|
||||
int unget_len = 0;
|
||||
|
||||
if (IO_ungetc != -1)
|
||||
{
|
||||
*(byte*)data = (byte) IO_ungetc;
|
||||
if (IO == _IO)
|
||||
_IO_ungetc = -1;
|
||||
else
|
||||
_IO_WVC_ungetc = -1;
|
||||
bcount--;
|
||||
if (bcount <= 0)
|
||||
return 1;
|
||||
data = 1 + (byte*)data;
|
||||
unget_len = 1;
|
||||
}
|
||||
|
||||
if (_readBuffer == null || _readBuffer.Length < bcount)
|
||||
_readBuffer = new byte[Math.Max(bcount, 0x4000)];
|
||||
int len = IO.Read(_readBuffer, 0, bcount);
|
||||
if (len > 0) Marshal.Copy(_readBuffer, 0, (IntPtr)data, len);
|
||||
return len + unget_len;
|
||||
}
|
||||
|
||||
long TellCallback(void* id)
|
||||
{
|
||||
Stream IO = (id == IO_ID_WVC) ? _IO_WVC : _IO;
|
||||
return IO.Position;
|
||||
}
|
||||
|
||||
int SeekCallback(void* id, long pos)
|
||||
{
|
||||
Stream IO = (id == IO_ID_WVC) ? _IO_WVC : _IO;
|
||||
IO.Position = pos;
|
||||
return 0;
|
||||
}
|
||||
|
||||
int SeekRelativeCallback(void* id, long delta, int mode)
|
||||
{
|
||||
Stream IO = (id == IO_ID_WVC) ? _IO_WVC : _IO;
|
||||
IO.Seek(delta, (SeekOrigin)(mode));
|
||||
return 0;
|
||||
}
|
||||
|
||||
int PushBackCallback(void* id, int c)
|
||||
{
|
||||
Stream IO = (id == IO_ID_WVC) ? _IO_WVC : _IO;
|
||||
if (IO == _IO)
|
||||
{
|
||||
if (_IO_ungetc != -1)
|
||||
throw new Exception("Double PushBackCallback unsupported.");
|
||||
_IO_ungetc = c;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (_IO_WVC_ungetc != -1)
|
||||
throw new Exception("Double PushBackCallback unsupported.");
|
||||
_IO_WVC_ungetc = c;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
long LengthCallback(void* id)
|
||||
{
|
||||
Stream IO = (id == IO_ID_WVC) ? _IO_WVC : _IO;
|
||||
return IO.Length;
|
||||
}
|
||||
|
||||
int CanSeekCallback(void* id)
|
||||
{
|
||||
Stream IO = (id == IO_ID_WVC) ? _IO_WVC : _IO;
|
||||
return IO.CanSeek ? 1 : 0;
|
||||
}
|
||||
|
||||
WavpackContext* _wpc;
|
||||
long _sampleCount, _sampleOffset;
|
||||
Stream _IO;
|
||||
Stream _IO_WVC;
|
||||
string _path;
|
||||
int _IO_ungetc, _IO_WVC_ungetc;
|
||||
AudioPCMConfig pcm;
|
||||
WavpackStreamReader64* m_ioReader;
|
||||
DecoderReadDelegate m_read_bytes;
|
||||
DecoderTellDelegate64 m_get_pos;
|
||||
DecoderSeekDelegate64 m_set_pos_abs;
|
||||
DecoderSeekRelativeDelegate64 m_set_pos_rel;
|
||||
DecoderPushBackDelegate m_push_back_byte;
|
||||
DecoderLengthDelegate64 m_get_length;
|
||||
DecoderCanSeekDelegate m_can_seek;
|
||||
byte[] _readBuffer;
|
||||
}
|
||||
}
|
||||
221
CUETools.Codecs.libwavpack/Writer.cs
Normal file
221
CUETools.Codecs.libwavpack/Writer.cs
Normal file
@@ -0,0 +1,221 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.ComponentModel;
|
||||
using System.IO;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Security.Cryptography;
|
||||
using System.Text;
|
||||
using CUETools.Codecs;
|
||||
|
||||
namespace CUETools.Codecs.libwavpack
|
||||
{
|
||||
public class WriterSettings : AudioEncoderSettings
|
||||
{
|
||||
public WriterSettings()
|
||||
: base("fast normal high high+", "normal")
|
||||
{
|
||||
}
|
||||
|
||||
[DefaultValue(0)]
|
||||
[DisplayName("ExtraMode")]
|
||||
public int ExtraMode {
|
||||
get => m_extraMode;
|
||||
set {
|
||||
if ((value < 0) || (value > 6)) {
|
||||
throw new Exception("Invalid extra mode.");
|
||||
}
|
||||
m_extraMode = value;
|
||||
}
|
||||
}
|
||||
|
||||
[DefaultValue(true)]
|
||||
[DisplayName("MD5")]
|
||||
[Description("Calculate MD5 hash for audio stream")]
|
||||
public bool MD5Sum { get; set; }
|
||||
|
||||
[DisplayName("Version")]
|
||||
[Description("Library version")]
|
||||
public string Version => Marshal.PtrToStringAnsi(wavpackdll.WavpackGetLibraryVersionString());
|
||||
|
||||
private int m_extraMode;
|
||||
};
|
||||
|
||||
[AudioEncoderClass("libwavpack", "wv", true, 1, typeof(WriterSettings))]
|
||||
public unsafe class Writer : IAudioDest
|
||||
{
|
||||
public Writer(string path, Stream output, WriterSettings settings)
|
||||
{
|
||||
m_path = path;
|
||||
m_stream = output;
|
||||
m_settings = settings;
|
||||
m_streamGiven = output != null;
|
||||
m_initialized = false;
|
||||
m_finalSampleCount = 0;
|
||||
m_samplesWritten = 0;
|
||||
m_blockOutput = BlockOutputCallback;
|
||||
if (m_settings.PCM.BitsPerSample < 16 || m_settings.PCM.BitsPerSample > 24)
|
||||
throw new Exception("bits per sample must be 16..24");
|
||||
}
|
||||
|
||||
public Writer(string path, WriterSettings settings)
|
||||
: this(path, null, settings)
|
||||
{
|
||||
}
|
||||
|
||||
public AudioEncoderSettings Settings => m_settings;
|
||||
|
||||
public string Path { get => m_path; }
|
||||
|
||||
public long FinalSampleCount
|
||||
{
|
||||
get => m_finalSampleCount;
|
||||
set
|
||||
{
|
||||
if (value < 0)
|
||||
throw new Exception("invalid final sample count");
|
||||
if (m_initialized)
|
||||
throw new Exception("final sample count cannot be changed after encoding begins");
|
||||
m_finalSampleCount = value;
|
||||
}
|
||||
}
|
||||
|
||||
public void Close()
|
||||
{
|
||||
if (m_initialized)
|
||||
{
|
||||
if (m_settings.MD5Sum)
|
||||
{
|
||||
_md5hasher.TransformFinalBlock (new byte[1], 0, 0);
|
||||
fixed (byte* md5_digest = &_md5hasher.Hash[0])
|
||||
wavpackdll.WavpackStoreMD5Sum (_wpc, md5_digest);
|
||||
}
|
||||
wavpackdll.WavpackFlushSamples(_wpc);
|
||||
_wpc = wavpackdll.WavpackCloseFile(_wpc);
|
||||
m_initialized = false;
|
||||
}
|
||||
if (m_stream != null)
|
||||
{
|
||||
m_stream.Close();
|
||||
m_stream = null;
|
||||
}
|
||||
if ((m_finalSampleCount != 0) && (m_samplesWritten != m_finalSampleCount))
|
||||
throw new Exception("samples written differs from the expected sample count");
|
||||
}
|
||||
|
||||
public void Delete()
|
||||
{
|
||||
try
|
||||
{
|
||||
if (m_initialized)
|
||||
{
|
||||
_wpc = wavpackdll.WavpackCloseFile(_wpc);
|
||||
m_initialized = false;
|
||||
}
|
||||
if (m_stream != null)
|
||||
{
|
||||
m_stream.Close();
|
||||
m_stream = null;
|
||||
}
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
}
|
||||
if (m_path != "")
|
||||
File.Delete(m_path);
|
||||
}
|
||||
|
||||
private void UpdateHash(byte[] buff, int len)
|
||||
{
|
||||
if (!m_settings.MD5Sum) throw new Exception("MD5 not enabled.");
|
||||
if (!m_initialized) Initialize();
|
||||
_md5hasher.TransformBlock (buff, 0, len, buff, 0);
|
||||
}
|
||||
|
||||
public void Write(AudioBuffer sampleBuffer)
|
||||
{
|
||||
if (!m_initialized) Initialize();
|
||||
|
||||
sampleBuffer.Prepare(this);
|
||||
|
||||
if (m_settings.MD5Sum)
|
||||
UpdateHash(sampleBuffer.Bytes, sampleBuffer.ByteLength);
|
||||
|
||||
int[,] samples = sampleBuffer.Samples;
|
||||
if ((m_settings.PCM.BitsPerSample & 7) != 0)
|
||||
{
|
||||
if (_shiftedSampleBuffer == null || _shiftedSampleBuffer.GetLength(0) < sampleBuffer.Length)
|
||||
_shiftedSampleBuffer = new int[sampleBuffer.Length, m_settings.PCM.ChannelCount];
|
||||
int shift = 8 - (m_settings.PCM.BitsPerSample & 7);
|
||||
int ch = m_settings.PCM.ChannelCount;
|
||||
for (int i = 0; i < sampleBuffer.Length; i++)
|
||||
for (int c = 0; c < ch; c++)
|
||||
_shiftedSampleBuffer[i, c] = sampleBuffer.Samples[i, c] << shift;
|
||||
samples = _shiftedSampleBuffer;
|
||||
}
|
||||
|
||||
fixed (int* pSampleBuffer = &samples[0, 0])
|
||||
if (0 == wavpackdll.WavpackPackSamples(_wpc, pSampleBuffer, (uint)sampleBuffer.Length))
|
||||
throw new Exception("An error occurred while encoding: " + wavpackdll.WavpackGetErrorMessage(_wpc));
|
||||
|
||||
m_samplesWritten += sampleBuffer.Length;
|
||||
}
|
||||
|
||||
private int BlockOutputCallback(void* id, byte[] data, int bcount)
|
||||
{
|
||||
m_stream.Write(data, 0, bcount);
|
||||
return 1;
|
||||
}
|
||||
|
||||
void Initialize()
|
||||
{
|
||||
if (m_stream == null)
|
||||
m_stream = new FileStream(m_path, FileMode.Create, FileAccess.Write, FileShare.Read, 0x10000);
|
||||
|
||||
WavpackConfig config = new WavpackConfig();
|
||||
config.bits_per_sample = m_settings.PCM.BitsPerSample;
|
||||
config.bytes_per_sample = (m_settings.PCM.BitsPerSample + 7) / 8;
|
||||
config.num_channels = m_settings.PCM.ChannelCount;
|
||||
config.channel_mask = (int)m_settings.PCM.ChannelMask;
|
||||
config.sample_rate = m_settings.PCM.SampleRate;
|
||||
config.flags = ConfigFlags.CONFIG_COMPATIBLE_WRITE;
|
||||
Int32 _compressionMode = m_settings.EncoderModeIndex;
|
||||
if (_compressionMode == 0) config.flags |= ConfigFlags.CONFIG_FAST_FLAG;
|
||||
if (_compressionMode == 2) config.flags |= ConfigFlags.CONFIG_HIGH_FLAG;
|
||||
if (_compressionMode == 3) config.flags |= ConfigFlags.CONFIG_HIGH_FLAG | ConfigFlags.CONFIG_VERY_HIGH_FLAG;
|
||||
if (m_settings.ExtraMode != 0)
|
||||
{
|
||||
config.flags |= ConfigFlags.CONFIG_EXTRA_MODE;
|
||||
config.xmode = m_settings.ExtraMode;
|
||||
}
|
||||
if (m_settings.MD5Sum)
|
||||
{
|
||||
_md5hasher = new MD5CryptoServiceProvider ();
|
||||
config.flags |= ConfigFlags.CONFIG_MD5_CHECKSUM;
|
||||
}
|
||||
config.block_samples = (int)m_settings.BlockSize;
|
||||
if (m_settings.BlockSize > 0 && m_settings.BlockSize < 2048)
|
||||
config.flags |= ConfigFlags.CONFIG_MERGE_BLOCKS;
|
||||
|
||||
_wpc = wavpackdll.WavpackOpenFileOutput(m_blockOutput, null, null);
|
||||
if (_wpc == null)
|
||||
throw new Exception("Unable to create the encoder.");
|
||||
if (0 == wavpackdll.WavpackSetConfiguration64(_wpc, &config, (m_finalSampleCount == 0) ? -1 : m_finalSampleCount, null))
|
||||
throw new Exception("Invalid configuration setting:" + wavpackdll.WavpackGetErrorMessage(_wpc));
|
||||
if (0 == wavpackdll.WavpackPackInit(_wpc))
|
||||
throw new Exception("Unable to initialize the encoder: " + wavpackdll.WavpackGetErrorMessage(_wpc));
|
||||
|
||||
m_initialized = true;
|
||||
}
|
||||
|
||||
int[,] _shiftedSampleBuffer;
|
||||
WavpackContext* _wpc;
|
||||
WriterSettings m_settings;
|
||||
Stream m_stream;
|
||||
MD5 _md5hasher;
|
||||
bool m_streamGiven;
|
||||
bool m_initialized;
|
||||
string m_path;
|
||||
Int64 m_finalSampleCount, m_samplesWritten;
|
||||
EncoderBlockOutput m_blockOutput;
|
||||
}
|
||||
}
|
||||
124
CUETools.Codecs.libwavpack/libwavpack.cs
Normal file
124
CUETools.Codecs.libwavpack/libwavpack.cs
Normal file
@@ -0,0 +1,124 @@
|
||||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
namespace CUETools.Codecs.libwavpack
|
||||
{
|
||||
internal enum OpenFlags : int
|
||||
{
|
||||
OPEN_WVC = 0x1, // open/read "correction" file
|
||||
OPEN_TAGS = 0x2, // read ID3v1 / APEv2 tags (seekable file)
|
||||
OPEN_WRAPPER = 0x4, // make audio wrapper available (i.e. RIFF)
|
||||
OPEN_2CH_MAX = 0x8, // open multichannel as stereo (no downmix)
|
||||
OPEN_NORMALIZE = 0x10, // normalize floating point data to +/- 1.0
|
||||
OPEN_STREAMING = 0x20, // "streaming" mode blindly unpacks blocks
|
||||
// w/o regard to header file position info
|
||||
OPEN_EDIT_TAGS = 0x40, // allow editing of tags
|
||||
OPEN_FILE_UTF8 = 0x80, // assume filenames are UTF-8 encoded, not ANSI (Windows only)
|
||||
// new for version 5
|
||||
OPEN_DSD_NATIVE = 0x100, // open DSD files as bitstreams
|
||||
// (returned as 8-bit "samples" stored in 32-bit words)
|
||||
OPEN_DSD_AS_PCM = 0x200, // open DSD files as 24-bit PCM (decimated 8x)
|
||||
OPEN_ALT_TYPES = 0x400, // application is aware of alternate file types & qmode
|
||||
// (just affects retrieving wrappers & MD5 checksums)
|
||||
OPEN_NO_CHECKSUM = 0x800, // don't verify block checksums before decoding
|
||||
};
|
||||
|
||||
internal enum ConfigFlags : uint
|
||||
{
|
||||
CONFIG_BYTES_STORED = 3, // 1-4 bytes/sample
|
||||
CONFIG_MONO_FLAG = 4, // not stereo
|
||||
CONFIG_HYBRID_FLAG = 8, // hybrid mode
|
||||
CONFIG_JOINT_STEREO = 0x10, // joint stereo
|
||||
CONFIG_CROSS_DECORR = 0x20, // no-delay cross decorrelation
|
||||
CONFIG_HYBRID_SHAPE = 0x40, // noise shape (hybrid mode only)
|
||||
CONFIG_FLOAT_DATA = 0x80, // ieee 32-bit floating point data
|
||||
|
||||
CONFIG_FAST_FLAG = 0x200, // fast mode
|
||||
CONFIG_HIGH_FLAG = 0x800, // high quality mode
|
||||
CONFIG_VERY_HIGH_FLAG = 0x1000, // very high
|
||||
CONFIG_BITRATE_KBPS = 0x2000, // bitrate is kbps, not bits / sample
|
||||
CONFIG_AUTO_SHAPING = 0x4000, // automatic noise shaping
|
||||
CONFIG_SHAPE_OVERRIDE = 0x8000, // shaping mode specified
|
||||
CONFIG_JOINT_OVERRIDE = 0x10000, // joint-stereo mode specified
|
||||
CONFIG_DYNAMIC_SHAPING = 0x20000, // dynamic noise shaping
|
||||
CONFIG_CREATE_EXE = 0x40000, // create executable
|
||||
CONFIG_CREATE_WVC = 0x80000, // create correction file
|
||||
CONFIG_OPTIMIZE_WVC = 0x100000, // maximize bybrid compression
|
||||
CONFIG_COMPATIBLE_WRITE = 0x400000, // write files for decoders < 4.3
|
||||
CONFIG_CALC_NOISE = 0x800000, // calc noise in hybrid mode
|
||||
CONFIG_LOSSY_MODE = 0x1000000, // obsolete (for information)
|
||||
CONFIG_EXTRA_MODE = 0x2000000, // extra processing mode
|
||||
CONFIG_SKIP_WVX = 0x4000000, // no wvx stream w/ floats & big ints
|
||||
CONFIG_MD5_CHECKSUM = 0x8000000, // compute & store MD5 signature
|
||||
CONFIG_MERGE_BLOCKS = 0x10000000, // merge blocks of equal redundancy (for lossyWAV)
|
||||
CONFIG_PAIR_UNDEF_CHANS = 0x20000000, // encode undefined channels in stereo pairs
|
||||
CONFIG_OPTIMIZE_MONO = 0x80000000, // optimize for mono streams posing as stereo
|
||||
};
|
||||
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate int DecoderReadDelegate(void* id, void* data, int bcount);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate UInt32 DecoderTellDelegate(void* id);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate int DecoderSeekDelegate(void* id, uint pos);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate int DecoderSeekRelativeDelegate(void* id, int delta, int mode);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate int DecoderPushBackDelegate(void* id, int c);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate UInt32 DecoderLengthDelegate(void* id);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate int DecoderCanSeekDelegate(void* id);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate int WriteBytesDelegate(void* id, void* data, int bcount);
|
||||
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate long DecoderTellDelegate64(void* id);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate int DecoderSeekDelegate64(void* id, long pos);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate int DecoderSeekRelativeDelegate64(void* id, long delta, int mode);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate long DecoderLengthDelegate64(void* id);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate long DecoderTruncateDelegate(void* id);
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate long DecoderCloseDelegate(void* id);
|
||||
|
||||
[UnmanagedFunctionPointer(CallingConvention.Cdecl)]
|
||||
internal unsafe delegate int EncoderBlockOutput(void* id, [MarshalAs(UnmanagedType.LPArray, SizeParamIndex = 2), In] byte[] data, int bcount);
|
||||
|
||||
[StructLayout(LayoutKind.Sequential), Serializable]
|
||||
internal unsafe struct WavpackStreamReader64
|
||||
{
|
||||
internal IntPtr read_bytes;
|
||||
internal IntPtr write_bytes;
|
||||
internal IntPtr get_pos;
|
||||
internal IntPtr set_pos_abs;
|
||||
internal IntPtr set_pos_rel;
|
||||
internal IntPtr push_back_byte;
|
||||
internal IntPtr get_length;
|
||||
internal IntPtr can_seek;
|
||||
internal IntPtr truncate_here;
|
||||
internal IntPtr close;
|
||||
};
|
||||
|
||||
[StructLayout(LayoutKind.Sequential), Serializable]
|
||||
internal unsafe struct WavpackConfig
|
||||
{
|
||||
internal float bitrate, shaping_weight;
|
||||
internal int bits_per_sample, bytes_per_sample;
|
||||
internal int qmode;
|
||||
internal ConfigFlags flags;
|
||||
internal int xmode, num_channels, float_norm_exp;
|
||||
internal int block_samples, extra_flags, sample_rate, channel_mask;
|
||||
internal fixed byte md5_checksum[16];
|
||||
internal byte md5_read;
|
||||
internal int num_tag_strings;
|
||||
internal char** tag_strings;
|
||||
};
|
||||
|
||||
internal struct WavpackContext
|
||||
{
|
||||
}
|
||||
}
|
||||
85
CUETools.Codecs.libwavpack/wavpackdll.cs
Normal file
85
CUETools.Codecs.libwavpack/wavpackdll.cs
Normal file
@@ -0,0 +1,85 @@
|
||||
using System;
|
||||
using System.Runtime.InteropServices;
|
||||
|
||||
namespace CUETools.Codecs.libwavpack
|
||||
{
|
||||
internal unsafe static class wavpackdll
|
||||
{
|
||||
internal const string DllName = "wavpackdll";
|
||||
internal const CallingConvention DllCallingConvention = CallingConvention.Cdecl;
|
||||
|
||||
[DllImport("kernel32.dll")]
|
||||
private static extern IntPtr LoadLibrary(string dllToLoad);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern WavpackContext* WavpackOpenFileInputEx64 (WavpackStreamReader64 *reader, void *wv_id, void *wvc_id,
|
||||
[param: MarshalAs(UnmanagedType.LPTStr), Out()] out string error,
|
||||
OpenFlags flags, int norm_offset);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern long WavpackGetNumSamples64 (WavpackContext *wpc);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern int WavpackSeekSample64 (WavpackContext *wpc, long sample);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern WavpackContext* WavpackCloseFile (WavpackContext *wpc);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern uint WavpackUnpackSamples (WavpackContext *wpc, int *buffer, uint samples);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern int WavpackGetBitsPerSample(WavpackContext* wpc);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern int WavpackGetNumChannels(WavpackContext* wpc);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern uint WavpackGetSampleRate(WavpackContext* wpc);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern int WavpackGetChannelMask(WavpackContext* wpc);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern IntPtr WavpackGetLibraryVersionString();
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern int WavpackStoreMD5Sum(WavpackContext* wpc, byte* data);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern int WavpackFlushSamples(WavpackContext* wpc);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern int WavpackPackSamples(WavpackContext* wpc, int* sample_buffer, uint sample_count);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern string WavpackGetErrorMessage(WavpackContext* wpc);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern WavpackContext* WavpackOpenFileOutput(EncoderBlockOutput blockout, void* wv_id, void* wvc_id);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern int WavpackSetConfiguration64(WavpackContext* wpc, WavpackConfig* config, long total_samples, byte* chan_ids);
|
||||
|
||||
[DllImport(DllName, CallingConvention = DllCallingConvention)]
|
||||
internal static extern int WavpackPackInit(WavpackContext* wpc);
|
||||
|
||||
|
||||
static wavpackdll()
|
||||
{
|
||||
var myPath = new Uri(typeof(wavpackdll).Assembly.CodeBase).LocalPath;
|
||||
var myFolder = System.IO.Path.GetDirectoryName(myPath);
|
||||
var is64 = IntPtr.Size == 8;
|
||||
var subfolder = is64 ? "x64" : "win32";
|
||||
#if NET40
|
||||
IntPtr Dll = LoadLibrary(System.IO.Path.Combine(myFolder, subfolder, DllName + ".dll"));
|
||||
#else
|
||||
IntPtr Dll = LoadLibrary(System.IO.Path.Combine(System.IO.Path.Combine(myFolder, subfolder), DllName + ".dll"));
|
||||
#endif
|
||||
if (Dll == IntPtr.Zero)
|
||||
Dll = LoadLibrary(DllName + ".dll");
|
||||
if (Dll == IntPtr.Zero)
|
||||
throw new DllNotFoundException();
|
||||
}
|
||||
};
|
||||
}
|
||||
@@ -57,10 +57,6 @@ Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CUETools", "CUETools.csproj
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "CUETools.Codecs.APE", "..\CUETools.Codecs.APE\CUETools.Codecs.APE.vcxproj", "{9AE965C4-301E-4C01-B90F-297AF341ACC6}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "CUETools.Codecs.WavPack", "..\CUETools.Codecs.WavPack\CUETools.Codecs.WavPack.vcxproj", "{CC2E74B6-534A-43D8-9F16-AC03FE955000}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libwavpack", "..\wavpack-4.5.0\src\libwavpack.vcxproj", "{5CCCB9CF-0384-458F-BA08-72B73866840F}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "CUETools.ARCUE", "..\CUETools.ARCUE\CUETools.ARCUE.csproj", "{A5A8D8FA-9E32-4010-8AAF-AE580C5AF728}"
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
{6458A13A-30EF-45A9-9D58-E5031B17BEE2} = {6458A13A-30EF-45A9-9D58-E5031B17BEE2}
|
||||
@@ -191,6 +187,12 @@ Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "MACLib", "..\ThirdParty\MAC
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "OpenCLNet", "..\ThirdParty\openclnet\source\OpenCLNet.csproj", "{8373E3B2-16F0-4FD3-A13B-0B0248FFC228}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "CUETools.Codecs.libwavpack", "..\CUETools.Codecs.libwavpack\CUETools.Codecs.libwavpack.csproj", "{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libwavpack", "..\ThirdParty\WavPack\src\libwavpack.vcxproj", "{5CCCB9CF-0384-458F-BA08-72B73866840F}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "wavpackdll", "..\ThirdParty\WavPack\wavpackdll\wavpackdll.vcxproj", "{1A87F412-BA74-4DBB-9F77-FD55C042FB63}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Any CPU = Debug|Any CPU
|
||||
@@ -235,38 +237,6 @@ Global
|
||||
{9AE965C4-301E-4C01-B90F-297AF341ACC6}.Release|x64.ActiveCfg = Release|x64
|
||||
{9AE965C4-301E-4C01-B90F-297AF341ACC6}.Release|x64.Build.0 = Release|x64
|
||||
{9AE965C4-301E-4C01-B90F-297AF341ACC6}.Release|x86.ActiveCfg = Release|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Debug|Any CPU.ActiveCfg = Debug|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Debug|Mixed Platforms.ActiveCfg = Debug|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Debug|Mixed Platforms.Build.0 = Debug|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Debug|x64.Build.0 = Debug|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Release|Any CPU.ActiveCfg = Release|Win32
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Release|Mixed Platforms.ActiveCfg = Release|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Release|Mixed Platforms.Build.0 = Release|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Release|Win32.Build.0 = Release|Win32
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Release|x64.ActiveCfg = Release|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Release|x64.Build.0 = Release|x64
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000}.Release|x86.ActiveCfg = Release|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Any CPU.ActiveCfg = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Mixed Platforms.ActiveCfg = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Mixed Platforms.Build.0 = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|x64.Build.0 = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|x86.ActiveCfg = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Any CPU.ActiveCfg = Release|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Mixed Platforms.ActiveCfg = Release|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Mixed Platforms.Build.0 = Release|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Win32.Build.0 = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|x64.ActiveCfg = Release|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|x64.Build.0 = Release|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|x86.ActiveCfg = Release|x64
|
||||
{A5A8D8FA-9E32-4010-8AAF-AE580C5AF728}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{A5A8D8FA-9E32-4010-8AAF-AE580C5AF728}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{A5A8D8FA-9E32-4010-8AAF-AE580C5AF728}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||
@@ -1135,6 +1105,62 @@ Global
|
||||
{8373E3B2-16F0-4FD3-A13B-0B0248FFC228}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{8373E3B2-16F0-4FD3-A13B-0B0248FFC228}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{8373E3B2-16F0-4FD3-A13B-0B0248FFC228}.Release|x86.Build.0 = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|Win32.ActiveCfg = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|Win32.Build.0 = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|x64.ActiveCfg = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|x64.Build.0 = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|x86.ActiveCfg = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Debug|x86.Build.0 = Debug|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|Mixed Platforms.Build.0 = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|Win32.ActiveCfg = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|Win32.Build.0 = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|x64.ActiveCfg = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|x64.Build.0 = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|x86.ActiveCfg = Release|Any CPU
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443}.Release|x86.Build.0 = Release|Any CPU
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Any CPU.ActiveCfg = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Mixed Platforms.ActiveCfg = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Mixed Platforms.Build.0 = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|x64.Build.0 = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|x86.Build.0 = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Any CPU.ActiveCfg = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Mixed Platforms.ActiveCfg = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Mixed Platforms.Build.0 = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Win32.Build.0 = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|x64.ActiveCfg = Release|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|x64.Build.0 = Release|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|x86.ActiveCfg = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|x86.Build.0 = Release|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Debug|Any CPU.ActiveCfg = Debug|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Debug|Mixed Platforms.ActiveCfg = Debug|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Debug|Mixed Platforms.Build.0 = Debug|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Debug|x64.Build.0 = Debug|x64
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Debug|x86.Build.0 = Debug|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Release|Any CPU.ActiveCfg = Release|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Release|Mixed Platforms.ActiveCfg = Release|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Release|Mixed Platforms.Build.0 = Release|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Release|Win32.Build.0 = Release|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Release|x64.ActiveCfg = Release|x64
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Release|x64.Build.0 = Release|x64
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Release|x86.ActiveCfg = Release|Win32
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63}.Release|x86.Build.0 = Release|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
@@ -1148,8 +1174,6 @@ Global
|
||||
{9A0D1EB8-269E-4165-971C-541C96AA506F} = {5D823ABE-D280-4800-824C-2633CBAB2EA9}
|
||||
{0E404B8B-FF82-427F-ADE4-77B54A29219F} = {5D823ABE-D280-4800-824C-2633CBAB2EA9}
|
||||
{9AE965C4-301E-4C01-B90F-297AF341ACC6} = {39A17A65-E893-44B8-A312-DDCDD990D9D1}
|
||||
{CC2E74B6-534A-43D8-9F16-AC03FE955000} = {39A17A65-E893-44B8-A312-DDCDD990D9D1}
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F} = {8B179853-B7D6-479C-B8B2-6CBCE835D040}
|
||||
{A5A8D8FA-9E32-4010-8AAF-AE580C5AF728} = {4B59E09C-A51F-4B80-91BE-987904DCEF7D}
|
||||
{32338A04-5B6B-4C63-8EE7-C6400F73B5D7} = {FD0D49DB-8F02-4A64-A9A3-A5AF54481770}
|
||||
{F2EC7193-D5E5-4252-9803-5CEB407E910F} = {93B7AE1D-DEF6-4A04-A222-5CDE09DF262D}
|
||||
@@ -1193,6 +1217,9 @@ Global
|
||||
{4CEFBC83-C215-11DB-8314-0800200C9A66} = {8B179853-B7D6-479C-B8B2-6CBCE835D040}
|
||||
{21BF980F-C022-4DCC-9250-7C73528E422B} = {8B179853-B7D6-479C-B8B2-6CBCE835D040}
|
||||
{8373E3B2-16F0-4FD3-A13B-0B0248FFC228} = {7E402406-7E51-4F0D-8209-60824C1CD6E8}
|
||||
{4D1B3411-F4F7-4E62-B7CB-A3AC3D530443} = {93B7AE1D-DEF6-4A04-A222-5CDE09DF262D}
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F} = {8B179853-B7D6-479C-B8B2-6CBCE835D040}
|
||||
{1A87F412-BA74-4DBB-9F77-FD55C042FB63} = {8B179853-B7D6-479C-B8B2-6CBCE835D040}
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
SolutionGuid = {C634D169-5814-4203-94B6-6A11371DDA95}
|
||||
|
||||
2
ThirdParty/MAC_SDK
vendored
2
ThirdParty/MAC_SDK
vendored
Submodule ThirdParty/MAC_SDK updated: bb37bfafa4...ec5e7e8ee7
2
ThirdParty/WavPack
vendored
2
ThirdParty/WavPack
vendored
Submodule ThirdParty/WavPack updated: 8e3fe45a7b...c2d60b18d7
2
ThirdParty/flac
vendored
2
ThirdParty/flac
vendored
Submodule ThirdParty/flac updated: 36fce5b650...6735ddd460
@@ -1,379 +0,0 @@
|
||||
----------------------------
|
||||
Release 4.50 - June 13, 2008
|
||||
----------------------------
|
||||
|
||||
WavPack Library Source Code - 4.50
|
||||
----------------------------------
|
||||
added: dynamic noise shaping for improved hybrid quality
|
||||
added: option to merge blocks of similar redundancy
|
||||
added: ability to store and retrieve extra mode level
|
||||
fixed: alignment fault on some big-endian machines
|
||||
fixed: compiling with enable-mmx on gcc 4.3.x (thanks Joachim)
|
||||
improved: allow bitrate to be calculated for files down to 1/10 second
|
||||
improved: decoding of corrupt files (prevents heap overrun crashes)
|
||||
|
||||
wavpack.exe (command-line encoder) - 4.50
|
||||
-----------------------------------------
|
||||
added: dynamic noise shaping for improved hybrid quality
|
||||
added: --channel-order option to reorder nonconforming multichannel files
|
||||
added: --merge-blocks option to optimize storage of LossyWAV output files
|
||||
added: ignore -o on Windows for compatibility with Linux version
|
||||
fixed: alignment fault on some big-endian machines
|
||||
improved: reformatted and expanded --help display
|
||||
|
||||
wvunpack.exe (command-line decoder) - 4.50
|
||||
------------------------------------------
|
||||
fixed: don't ignore fractions of seconds in --skip option
|
||||
added: show extra level and dns status for newer files (-s command)
|
||||
added: ignore -o on Windows for compatibility with Linux version
|
||||
improved: decoding of corrupt files (prevents heap overrun crashes)
|
||||
improved: display bitrate for files down to 1/10 second
|
||||
|
||||
in_wv.dll (winamp plugin) - 2.5
|
||||
-------------------------------
|
||||
added: transcoding API (allows CD burning, format conversion, ReplayGain calc, etc.)
|
||||
added: metadata writing API (for Auto-Tag, etc.)
|
||||
added: full Unicode support for info box (older Winamps) and media library
|
||||
added: standard Winamp metadata display & edit for newer Winamps
|
||||
added: option to pass multichannel audio
|
||||
added: option to pass all audio as 16-bit (for better compatibility)
|
||||
added: option to output 24-bit audio when ReplayGain is active
|
||||
added: genre display to info box (older Winamps)
|
||||
fixed: seek bar sometimes vacillates when moved
|
||||
fixed: crash when winamp is opened with files in playlist moved or deleted
|
||||
improved: hi-res audio now output as 24-bit (not 32-bit) for better compatibility (EQ, etc.)
|
||||
improved: performance of adding tracks to library, especially from network drives
|
||||
improved: decoding of corrupt files (prevents heap overrun crashes)
|
||||
|
||||
cool_wv4.flt (CoolEdit / Audition filter) - 2.9
|
||||
-----------------------------------------------
|
||||
added: about box
|
||||
added: dynamic noise shaping for improved hybrid quality
|
||||
improved: display bitrate for files as short as 1/10 second
|
||||
improved: decoding of corrupt files (prevents heap overrun crashes)
|
||||
improved: replace "extra processing" switch with a slider (0-6)
|
||||
|
||||
|
||||
--------------------------
|
||||
Release 4.41 - May 6, 2007
|
||||
--------------------------
|
||||
|
||||
WavPack Library Source Code - 4.41
|
||||
----------------------------------
|
||||
added: create wavpackdll.dll for Windows (not used yet)
|
||||
fixed: corrupt floating-point audio on big-endian machines
|
||||
fixed: put MSVC projects in their own subdir (fixed build problems)
|
||||
fixed: limit RIFF data buffering to 16 MB to prevent out-of-memory crash
|
||||
improved: attempt to mute errors when decoding corrupt legacy WavPack files
|
||||
improved: overall performance enhancements of 10% to 30% (depending on mode)
|
||||
added: MMX intrinsics for 24-bit (and higher) stereo encoding (thanks to
|
||||
Joachim Henke)
|
||||
|
||||
wavpack.exe (command-line encoder) - 4.41
|
||||
-----------------------------------------
|
||||
fixed: corrupt floating-point audio on big-endian machines
|
||||
improved: refuse to encode WAV files over 4 GB or with over 16 MB RIFF data
|
||||
improved: overall performance enhancements of 10% to 30% (depending on mode)
|
||||
added: MMX intrinsics for 24-bit (and higher) stereo encoding (thanks to
|
||||
Joachim Henke)
|
||||
|
||||
wvunpack.exe (command-line decoder) - 4.41
|
||||
------------------------------------------
|
||||
fixed: corrupt floating-point audio on big-endian machines
|
||||
fixed: restore files mistakenly encoded with huge RIFF chunks
|
||||
improved: attempt to mute errors when decoding corrupt legacy WavPack files
|
||||
improved: overall performance enhancements of 10% to 30% (depending on mode)
|
||||
added: --skip and --until commands to unpack specified range of audio data
|
||||
added: MMX intrinsics for 24-bit (and higher) stereo encoding (thanks to
|
||||
Joachim Henke)
|
||||
|
||||
wvgain.exe (command-line ReplayGain scanner) - 4.41
|
||||
---------------------------------------------------
|
||||
improved: overall performance enhancements of 10% to 30% (depending on mode)
|
||||
added: MMX intrinsics for 24-bit (and higher) stereo encoding (thanks to
|
||||
Joachim Henke)
|
||||
|
||||
cool_wv4.flt (CoolEdit / Audition filter) - 2.8
|
||||
-----------------------------------------------
|
||||
fixed: read all RIFF metadata from files created in other applications
|
||||
improved: attempt to mute errors when decoding corrupt legacy WavPack files
|
||||
improved: overall performance enhancements of 10% to 30% (depending on mode)
|
||||
added: MMX intrinsics for 24-bit (and higher) stereo encoding (thanks to
|
||||
Joachim Henke)
|
||||
|
||||
|
||||
-------------------------------
|
||||
Release 4.40 - December 3, 2006
|
||||
-------------------------------
|
||||
|
||||
WavPack Library Source Code - 4.40
|
||||
----------------------------------
|
||||
added: new hardware-friendly "high" mode that compresses almost as well as
|
||||
old "high" mode but decodes significantly faster; old "high" mode
|
||||
now available as "very high"
|
||||
added: option added to improve compression of mono material in stereo files
|
||||
(requires at least version 4.3 decoder)
|
||||
added: function to obtain channel mapping information on decoding
|
||||
added: function to get trailing wrapper info (RIFF) without decoding file
|
||||
improved: "extra" mode levels 1-3 completely revamped, fast enough for use
|
||||
improved: reorganized to create a standard library that should more easily
|
||||
integrate into other applications; eliminated namespace issues
|
||||
improved: more robust handling of corrupt files
|
||||
|
||||
wavpack.exe (command-line encoder) - 4.40
|
||||
-----------------------------------------
|
||||
added: accepts long option names including --help for full usage info
|
||||
added: new hardware-friendly "high" mode that compresses almost as well as
|
||||
old "high" mode but decodes significantly faster; old "high" mode
|
||||
now available as "very high" (-hh)
|
||||
added: --optimize-mono option added to improve compression of mono material
|
||||
in stereo files (requires at least version 4.3 decoder)
|
||||
improved: "extra" mode levels 1-3 completely revamped, fast enough for use
|
||||
improved: switched to Microsoft Visual Studio 2005 (win32 only)
|
||||
removed: support for Windows 95
|
||||
|
||||
wvunpack.exe (command-line decoder) - 4.40
|
||||
------------------------------------------
|
||||
added: cuesheet extraction (to .cue file or stdout)
|
||||
added: wav header generation on decode for files with missing RIFF
|
||||
information, or forced with -w option
|
||||
added: more summary info (wrapper info + channel assignments)
|
||||
improved: more robust handling of corrupt files
|
||||
improved: separate options for raw (-r) and blind stream decoding (-b)
|
||||
improved: switched to Microsoft Visual Studio 2005 (win32 only)
|
||||
removed: support for Windows 95
|
||||
|
||||
wvgain.exe (command-line ReplayGain scanner) - 4.40
|
||||
---------------------------------------------------
|
||||
improved: switched to Microsoft Visual Studio 2005 (win32 only)
|
||||
removed: support for Windows 95
|
||||
|
||||
wvselfx.exe (self-extraction stub) - 4.40
|
||||
------------------------------------------
|
||||
added: automatic cuesheet extraction (if present in APEv2 tag)
|
||||
|
||||
in_wv.dll (winamp plugin) - 2.4
|
||||
-------------------------------
|
||||
fixed: quietly skips deleted files in playlist
|
||||
improved: more robust handling of corrupt files
|
||||
improved: APEv2 tags are read even if followed by ID3v1 tag
|
||||
|
||||
cool_wv4.flt (CoolEdit / Audition filter) - 2.7
|
||||
-----------------------------------------------
|
||||
added: new hardware-friendly "high" mode that compresses almost as well as
|
||||
old "high" mode but decodes significantly faster; old "high" mode
|
||||
now available as "v. high"
|
||||
improved: more robust handling of corrupt files
|
||||
|
||||
|
||||
----------------------
|
||||
Update - April 5, 2006
|
||||
----------------------
|
||||
|
||||
WavPack Library Source Code - 4.32
|
||||
wavpack.exe (command-line encoder) - 4.32
|
||||
-----------------------------------------
|
||||
fixed: generating RIFF headers on big-endian machines caused crash
|
||||
|
||||
|
||||
--------------------------
|
||||
Update - December 10, 2005
|
||||
--------------------------
|
||||
|
||||
wavpack.exe (command-line encoder) - 4.31
|
||||
wvunpack.exe (command-line decoder) - 4.31
|
||||
------------------------------------------
|
||||
fixed: detect debug mode in all cases (win32 only)
|
||||
improved: use latest service pack and SDK for building (win32 only)
|
||||
improved: better directory choice for logging file (win32 only)
|
||||
improved: allow shell to expand wildcards (*nix only)
|
||||
added: option (-o) to specify output directory or path (*nix only)
|
||||
added: option (-t) to copy timestamp (*nix only)
|
||||
|
||||
wvgain.exe (command-line ReplayGain scanner) - 4.31
|
||||
---------------------------------------------------
|
||||
new
|
||||
|
||||
WavPack Library Source Code - 4.31
|
||||
----------------------------------
|
||||
fixed: failing seek with some files that had been played to the end
|
||||
fixed: small memory leak when opening hybrid lossless files
|
||||
improved: signed characters no longer must be default
|
||||
improved: APEv2 tags are read even if followed by ID3v1 tag
|
||||
improved: limited APEv2 tag editing capability
|
||||
|
||||
|
||||
------------------------------
|
||||
Release 4.3 - November 1, 2005
|
||||
------------------------------
|
||||
|
||||
wavpack.exe (command-line encoder) - 4.3
|
||||
----------------------------------------
|
||||
fixed: bug causing termination error with very wide screen widths
|
||||
added: command-line option (-l) to use low priority for batch operation
|
||||
added: command-line option (-r) to generate a fresh RIFF header
|
||||
added: debug mode (rename to wavpack_debug.exe)
|
||||
added: automatically detect lower resolution data even without -x1
|
||||
added: src and dst dirs are searched also for tag source files (handy for EAC)
|
||||
added: wildcard accepted for tag source files (handy for EAC)
|
||||
added: handle non-standard sampling rates
|
||||
improved: returns error status for any error
|
||||
improved: use longer blocks in multichannel files (better "high" compression)
|
||||
|
||||
wvunpack.exe (command-line decoder) - 4.3
|
||||
-----------------------------------------
|
||||
fixed: very rare decoding bug causing overflow with hi-res files
|
||||
fixed: bug causing termination error with very wide screen widths
|
||||
fixed: formatting error in duration display
|
||||
added: command-line option (-ss) to include tags in summary dump
|
||||
added: command-line option (-l) to use low priority for batch operation
|
||||
added: debug mode (rename to wvunpack_debug.exe)
|
||||
improved: returns error status for any error
|
||||
improved: more robust decoding of damaged (or invalid) files
|
||||
|
||||
in_wv.dll (winamp plugin) - 2.3
|
||||
nxWavPack.dll (Nero plugin) - 1.2
|
||||
WavPack_Apollo.dll (Apollo plugin) - 1.3
|
||||
cool_wv4.flt (CoolEdit / Audition filter) - 2.6
|
||||
-----------------------------------------------
|
||||
fixed: very rare decoding bug causing overflow with hi-res files
|
||||
improved: handle ID3v1.1 tags (now includes track number)
|
||||
improved: more robust decoding of damaged (or invalid) files
|
||||
added: handle non-standard sampling rates
|
||||
|
||||
foo_wavpack.dll (foobar plugin) - 2.3
|
||||
-----------------------------------------------
|
||||
fixed: any error during WavPack file open caused crash if wvc file present
|
||||
fixed: very rare decoding bug causing overflow with hi-res files
|
||||
improved: more robust decoding of damaged (or invalid) files
|
||||
added: handle non-standard sampling rates
|
||||
|
||||
WavPack Library Source Code - 4.3
|
||||
---------------------------------
|
||||
fixed: very rare decoding bug causing overflow with hi-res files
|
||||
added: automatic generation of RIFF wav header during encoding
|
||||
added: new functions to access tags by index (instead of item name)
|
||||
added: automatically detect lower resolution data during encoding
|
||||
added: handle non-standard sampling rates
|
||||
improved: more robust decoding of damaged (or invalid) files
|
||||
improved: use longer blocks in multichannel files (better "high" compression)
|
||||
improved: two structures renamed to avoid namespace conflict
|
||||
removed: legacy code for Borland compiler
|
||||
|
||||
|
||||
--------------------------
|
||||
Update - September 1, 2005
|
||||
--------------------------
|
||||
|
||||
wavpack.exe (command-line encoder) - 4.22
|
||||
cool_wv4.flt (CoolEdit / Audition filter) - 2.5
|
||||
-----------------------------------------------
|
||||
fixed: possible corrupt files written (24 or 32-bit + "extra" mode)
|
||||
|
||||
|
||||
---------------------------
|
||||
Release 4.2 - April 2, 2005
|
||||
---------------------------
|
||||
|
||||
wavpack.exe (command-line encoder) - 4.2
|
||||
----------------------------------------
|
||||
fixed: handling of wav files larger than 2 gig
|
||||
improved: stereo lossless encoding speed (including "extra" mode)
|
||||
added: -i option to ignore length specified in wav header
|
||||
added: -w option to write APEv2 tags directly from command line
|
||||
|
||||
wvunpack.exe (command-line decoder) - 4.2
|
||||
-----------------------------------------
|
||||
improved: decoding speed
|
||||
|
||||
in_wv.dll (winamp plugin) - 2.2
|
||||
-------------------------------
|
||||
added: winamp media library support
|
||||
improved: decoding speed
|
||||
|
||||
foo_wavpack.dll (foobar plugin) - 2.2
|
||||
-------------------------------------
|
||||
improved: decoding speed
|
||||
|
||||
nxWavPack.dll (Nero plugin) - 1.1
|
||||
Cool_wv4.flt (CoolEdit / Audition filter) - 2.4
|
||||
-----------------------------------------------
|
||||
fixed: handling of wav files larger than 2 gig
|
||||
improved: encoding and decoding speed
|
||||
|
||||
WavPack Library Source Code - 4.2
|
||||
---------------------------------
|
||||
improved: encoding and decoding speed
|
||||
fixed: works correctly with 64-bit compilers
|
||||
added: mode bit to open files in "streaming" mode
|
||||
|
||||
|
||||
--------------------------
|
||||
Update - December 12, 2004
|
||||
--------------------------
|
||||
|
||||
WavPack_Apollo.dll (Apollo plugin) - 1.2
|
||||
----------------------------------------
|
||||
fixed: crash when Apollo opened and WavPack plugin can't find config file
|
||||
|
||||
|
||||
--------------------------------
|
||||
Release 4.1 - September 14, 2004
|
||||
--------------------------------
|
||||
|
||||
wavpack.exe (command-line encoder) - 4.1
|
||||
----------------------------------------
|
||||
fixed: hybrid mode + "extra" mode + very low bitrates making corrupt files
|
||||
fixed: mono or multichannel files causing crash (no corruption possible)
|
||||
added: third name specification for "correction" file (EAC specific)
|
||||
added: -t option to preserve timestamps
|
||||
added: error summary for batch mode
|
||||
|
||||
wvunpack.exe (command-line decoder) - 4.1
|
||||
-----------------------------------------
|
||||
fixed: hybrid mode decoding bugs (very obscure situations)
|
||||
added: -s option to dump file summary to stdout
|
||||
added: -t option to preserve timestamps
|
||||
added: error summary for batch mode
|
||||
|
||||
wvselfx.exe (self-extraction stub) - 4.1
|
||||
----------------------------------------
|
||||
fixed: hybrid mode decoding bugs (very obscure situations)
|
||||
|
||||
in_wv.dll (winamp plugin) - 2.1
|
||||
-------------------------------
|
||||
fixed: international characters in tags display properly (UTF-8 to Ansi)
|
||||
added: maximum tag data field width changed from 64 chars to 128 chars
|
||||
added: new infobox items including encoder version & modes, track #, md5
|
||||
|
||||
foo_wavpack.dll (foobar plugin) - 2.1
|
||||
-------------------------------------
|
||||
added: new database items including encoder version & modes and md5
|
||||
|
||||
WavPack_Apollo.dll (Apollo plugin) - 1.1
|
||||
----------------------------------------
|
||||
fixed: international characters in tags display properly (UTF-8 to Ansi)
|
||||
|
||||
Cool_wv4.flt (CoolEdit / Audition filter) - 2.2
|
||||
-----------------------------------------------
|
||||
fixed: hybrid mode + "extra" mode + very low bitrates making corrupt files
|
||||
fixed: saving mono file causing crash (no corruption possible)
|
||||
fixed: hybrid mode decoding bugs (very obscure situations)
|
||||
fixed: partial saves (with "Cancel") have incorrect RIFF header if unpacked
|
||||
|
||||
nxWavPack.dll (Nero plugin) - 1.0
|
||||
---------------------------------
|
||||
new
|
||||
|
||||
WavPack Library Source Code - 4.1
|
||||
---------------------------------
|
||||
fixed: hybrid mode + "extra" mode + very low bitrates making corrupt files
|
||||
fixed: mono or multichannel files causing crash (no corruption possible)
|
||||
fixed: hybrid mode decoding bugs (very obscure situations)
|
||||
added: mode bits for determining additional encode info (extra, sfx)
|
||||
added: function to return total compressed file length (including wvc)
|
||||
added: function to return encoder version (1, 2, 3, or 4)
|
||||
added: ability to obtain MD5 sum before decoding file (requires seek to end)
|
||||
added: mode bit for determining tag type (for proper character translation)
|
||||
added: ability to encode WavPack files without knowing length in advance
|
||||
added: option for small "information only" version of library
|
||||
@@ -1,103 +0,0 @@
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
// **** WAVPACK **** //
|
||||
// Hybrid Lossless Wavefile Compressor //
|
||||
// Copyright (c) 1998 - 2006 Conifer Software. //
|
||||
// All Rights Reserved. //
|
||||
// Distributed under the BSD Software License (see license.txt) //
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
This package contains all the source code required to build the WavPack
|
||||
command-line programs and the WavPack library and it has been tested on many
|
||||
platforms.
|
||||
|
||||
On Windows there are solution and project files for Visual Studio 2005 and
|
||||
additional sourcecode to build the CoolEdit/Audition plugin and the winamp
|
||||
plugin. The CoolEdit/Audition plugin provides a good example for using the
|
||||
library to both read and write WavPack files.
|
||||
|
||||
To build everything on Linux, type:
|
||||
|
||||
1. ./configure [--enable-mmx]
|
||||
2. make
|
||||
3. make install (optionally, to install into /usr/local/bin)
|
||||
|
||||
If you are using the code directly from SVN (rather than a distribution)
|
||||
then you will need to do a ./autogen.sh before the configure step. For
|
||||
processors that support MMX, use the --enable-mmx switch to utilize MMX
|
||||
intrinsics to speed up encoding of stereo 24-bit (and higher) audio.
|
||||
|
||||
Notes:
|
||||
|
||||
1. There are two documentation files contained in the distribution:
|
||||
|
||||
doc/library_use.txt contains a detailed description of the API provided
|
||||
by WavPack library appropriate for read and writing
|
||||
WavPack files
|
||||
|
||||
doc/file_format.txt contains a description of the WavPack file format,
|
||||
including details needed for parsing WavPack blocks
|
||||
and interpreting the block header and flags
|
||||
|
||||
There is also a description of the WavPack algorithms in the forth edition
|
||||
of David Salomon's book "Data Compression: The Complete Reference". The
|
||||
section on WavPack can be found here:
|
||||
|
||||
www.wavpack.com/WavPack.pdf
|
||||
|
||||
2. This code is designed to be easy to port to other platforms. File I/O is
|
||||
done with streams and all file functions (except "fopen") are handled in
|
||||
a wrapper in the "utils.c" module. The code is endian-independent.
|
||||
|
||||
To maintain compatibility on various platforms, the following conventions
|
||||
are used: A "short" must be 16-bits and an "int" must be 32-bits.
|
||||
The "long" type is not used. The "char" type must be 8-bits, signed or
|
||||
unsigned.
|
||||
|
||||
3. For WavPack file decoding, a library interface in "wputils.c" provides all
|
||||
the functionality required for both the winamp plugin and the "wvunpack"
|
||||
command-line program (including the transparent decoding of "correction"
|
||||
files). There is also an alternate entry point that uses reader callbacks
|
||||
for all input, although in this case it is the caller's responsibility to
|
||||
to open the "correction" file. The header file "include/wavpack.h"
|
||||
includes everything needed while hiding all the WavPack internals from the
|
||||
application.
|
||||
|
||||
4. For WavPack file creation, the library interface in "wputils.c" provides
|
||||
all the functionality for both the Audition filter and the "wavpack"
|
||||
command-line program. No file I/O is performed by the library when creating
|
||||
WavPack files. Instead, the user supplies a "write_block" function that
|
||||
accepts completed WavPack blocks. It is also possible to append APEv2 tags
|
||||
to WavPack files during creation and edit APEv2 tags on existing files
|
||||
(although there is no support currently for "binary" fields in the tags).
|
||||
|
||||
5. The following #define's can be optionally used to eliminate some functionality
|
||||
to create smaller binaries. It is important that they must be specified
|
||||
the same for the compilation of ALL files:
|
||||
|
||||
NO_UNPACK no unpacking of audio samples from WavPack files
|
||||
(also don't include unpack.c)
|
||||
NO_PACK no creating WavPack files from raw audio data
|
||||
(also don't include pack.c, extra1.c and extra2.c)
|
||||
INFO_ONLY to obtain information from WavPack files, but not audio
|
||||
(also don't include pack.c, extra1.c and extra2.c)
|
||||
NO_SEEKING to not allow seeking to a specific sample index (unpack only)
|
||||
NO_USE_FSTREAMS to not open WavPack files by name using fstreams
|
||||
NO_TAGS to not read specified fields from ID3v1 and APEv2 tags and
|
||||
create APEv2 tags
|
||||
VER4_ONLY to only handle WavPack files from versions 4.0 onward
|
||||
WIN32 required for Win32 platform
|
||||
|
||||
6. There are alternate versions of this library available specifically designed
|
||||
for "resource limited" CPUs or hardware encoding and decoding. There is the
|
||||
"tiny decoder" library which works with less than 32k of code and less than
|
||||
4k of data and has assembly language optimizations for the ARM and Freescale
|
||||
ColdFire CPUs. The "tiny encoder" is also designed for embedded use and
|
||||
handles the pure lossless, lossy, and hybrid lossless modes. Neither of the
|
||||
"tiny" versions use any memory allocation functions nor do they require
|
||||
floating-point arithmetic support.
|
||||
|
||||
For applications requiring very low latency, there is a special version of
|
||||
the library that supports a variation on the regular WavPack block format
|
||||
to facilitate this.
|
||||
|
||||
7. Questions or comments should be directed to david@wavpack.com
|
||||
@@ -1,304 +0,0 @@
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
// **** WAVPACK **** //
|
||||
// Hybrid Lossless Wavefile Compressor //
|
||||
// Copyright (c) 1998 - 2006 Conifer Software. //
|
||||
// All Rights Reserved. //
|
||||
// Distributed under the BSD Software License (see license.txt) //
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// wavpack.h
|
||||
|
||||
#ifndef WAVPACK_H
|
||||
#define WAVPACK_H
|
||||
|
||||
// This header file contains all the definitions required to use the
|
||||
// functions in "wputils.c" to read and write WavPack files and streams.
|
||||
|
||||
#include <sys/types.h>
|
||||
|
||||
#if defined(_WIN32) && !defined(__MINGW32__)
|
||||
#include <stdlib.h>
|
||||
typedef unsigned __int64 uint64_t;
|
||||
typedef unsigned __int32 uint32_t;
|
||||
typedef unsigned __int16 uint16_t;
|
||||
typedef unsigned __int8 uint8_t;
|
||||
typedef __int64 int64_t;
|
||||
typedef __int32 int32_t;
|
||||
typedef __int16 int16_t;
|
||||
typedef __int8 int8_t;
|
||||
typedef float float32_t;
|
||||
#else
|
||||
#include <inttypes.h>
|
||||
#endif
|
||||
|
||||
typedef unsigned char uchar;
|
||||
|
||||
#if !defined(__GNUC__) || defined(WIN32)
|
||||
typedef unsigned short ushort;
|
||||
typedef unsigned int uint;
|
||||
#endif
|
||||
|
||||
// RIFF / wav header formats (these occur at the beginning of both wav files
|
||||
// and pre-4.0 WavPack files that are not in the "raw" mode). Generally, an
|
||||
// application using the library to read or write WavPack files will not be
|
||||
// concerned with any of these.
|
||||
|
||||
typedef struct {
|
||||
char ckID [4];
|
||||
uint32_t ckSize;
|
||||
char formType [4];
|
||||
} RiffChunkHeader;
|
||||
|
||||
typedef struct {
|
||||
char ckID [4];
|
||||
uint32_t ckSize;
|
||||
} ChunkHeader;
|
||||
|
||||
#define ChunkHeaderFormat "4L"
|
||||
|
||||
typedef struct {
|
||||
ushort FormatTag, NumChannels;
|
||||
uint32_t SampleRate, BytesPerSecond;
|
||||
ushort BlockAlign, BitsPerSample;
|
||||
ushort cbSize, ValidBitsPerSample;
|
||||
int32_t ChannelMask;
|
||||
ushort SubFormat;
|
||||
char GUID [14];
|
||||
} WaveHeader;
|
||||
|
||||
#define WaveHeaderFormat "SSLLSSSSLS"
|
||||
|
||||
// This is the ONLY structure that occurs in WavPack files (as of version
|
||||
// 4.0), and is the preamble to every block in both the .wv and .wvc
|
||||
// files (in little-endian format). Normally, this structure has no use
|
||||
// to an application using the library to read or write WavPack files,
|
||||
// but if an application needs to manually parse WavPack files then this
|
||||
// would be used (with appropriate endian correction).
|
||||
|
||||
typedef struct {
|
||||
char ckID [4];
|
||||
uint32_t ckSize;
|
||||
short version;
|
||||
uchar track_no, index_no;
|
||||
uint32_t total_samples, block_index, block_samples, flags, crc;
|
||||
} WavpackHeader;
|
||||
|
||||
#define WavpackHeaderFormat "4LS2LLLLL"
|
||||
|
||||
// or-values for WavpackHeader.flags
|
||||
#define BYTES_STORED 3 // 1-4 bytes/sample
|
||||
#define MONO_FLAG 4 // not stereo
|
||||
#define HYBRID_FLAG 8 // hybrid mode
|
||||
#define JOINT_STEREO 0x10 // joint stereo
|
||||
#define CROSS_DECORR 0x20 // no-delay cross decorrelation
|
||||
#define HYBRID_SHAPE 0x40 // noise shape (hybrid mode only)
|
||||
#define FLOAT_DATA 0x80 // ieee 32-bit floating point data
|
||||
|
||||
#define INT32_DATA 0x100 // special extended int handling
|
||||
#define HYBRID_BITRATE 0x200 // bitrate noise (hybrid mode only)
|
||||
#define HYBRID_BALANCE 0x400 // balance noise (hybrid stereo mode only)
|
||||
|
||||
#define INITIAL_BLOCK 0x800 // initial block of multichannel segment
|
||||
#define FINAL_BLOCK 0x1000 // final block of multichannel segment
|
||||
|
||||
#define SHIFT_LSB 13
|
||||
#define SHIFT_MASK (0x1fL << SHIFT_LSB)
|
||||
|
||||
#define MAG_LSB 18
|
||||
#define MAG_MASK (0x1fL << MAG_LSB)
|
||||
|
||||
#define SRATE_LSB 23
|
||||
#define SRATE_MASK (0xfL << SRATE_LSB)
|
||||
|
||||
#define FALSE_STEREO 0x40000000 // block is stereo, but data is mono
|
||||
|
||||
#define IGNORED_FLAGS 0x18000000 // reserved, but ignore if encountered
|
||||
#define NEW_SHAPING 0x20000000 // use IIR filter for negative shaping
|
||||
#define UNKNOWN_FLAGS 0x80000000 // also reserved, but refuse decode if
|
||||
// encountered
|
||||
|
||||
#define MONO_DATA (MONO_FLAG | FALSE_STEREO)
|
||||
|
||||
#define MIN_STREAM_VERS 0x402 // lowest stream version we'll decode
|
||||
#define MAX_STREAM_VERS 0x410 // highest stream version we'll decode or encode
|
||||
#define CUR_STREAM_VERS 0x407 // stream version we are writing now
|
||||
|
||||
// These are the mask bit definitions for the metadata chunk id byte (see format.txt)
|
||||
|
||||
#define ID_UNIQUE 0x3f
|
||||
#define ID_OPTIONAL_DATA 0x20
|
||||
#define ID_ODD_SIZE 0x40
|
||||
#define ID_LARGE 0x80
|
||||
|
||||
#define ID_DUMMY 0x0
|
||||
#define ID_ENCODER_INFO 0x1
|
||||
#define ID_DECORR_TERMS 0x2
|
||||
#define ID_DECORR_WEIGHTS 0x3
|
||||
#define ID_DECORR_SAMPLES 0x4
|
||||
#define ID_ENTROPY_VARS 0x5
|
||||
#define ID_HYBRID_PROFILE 0x6
|
||||
#define ID_SHAPING_WEIGHTS 0x7
|
||||
#define ID_FLOAT_INFO 0x8
|
||||
#define ID_INT32_INFO 0x9
|
||||
#define ID_WV_BITSTREAM 0xa
|
||||
#define ID_WVC_BITSTREAM 0xb
|
||||
#define ID_WVX_BITSTREAM 0xc
|
||||
#define ID_CHANNEL_INFO 0xd
|
||||
|
||||
#define ID_RIFF_HEADER (ID_OPTIONAL_DATA | 0x1)
|
||||
#define ID_RIFF_TRAILER (ID_OPTIONAL_DATA | 0x2)
|
||||
#define ID_REPLAY_GAIN (ID_OPTIONAL_DATA | 0x3) // never used (APEv2)
|
||||
#define ID_CUESHEET (ID_OPTIONAL_DATA | 0x4) // never used (APEv2)
|
||||
#define ID_CONFIG_BLOCK (ID_OPTIONAL_DATA | 0x5)
|
||||
#define ID_MD5_CHECKSUM (ID_OPTIONAL_DATA | 0x6)
|
||||
#define ID_SAMPLE_RATE (ID_OPTIONAL_DATA | 0x7)
|
||||
|
||||
///////////////////////// WavPack Configuration ///////////////////////////////
|
||||
|
||||
// This external structure is used during encode to provide configuration to
|
||||
// the encoding engine and during decoding to provide fle information back to
|
||||
// the higher level functions. Not all fields are used in both modes.
|
||||
|
||||
typedef struct {
|
||||
float bitrate, shaping_weight;
|
||||
int bits_per_sample, bytes_per_sample;
|
||||
int qmode, flags, xmode, num_channels, float_norm_exp;
|
||||
int32_t block_samples, extra_flags, sample_rate, channel_mask;
|
||||
uchar md5_checksum [16], md5_read;
|
||||
int num_tag_strings;
|
||||
char **tag_strings;
|
||||
} WavpackConfig;
|
||||
|
||||
#define CONFIG_HYBRID_FLAG 8 // hybrid mode
|
||||
#define CONFIG_JOINT_STEREO 0x10 // joint stereo
|
||||
#define CONFIG_HYBRID_SHAPE 0x40 // noise shape (hybrid mode only)
|
||||
#define CONFIG_FAST_FLAG 0x200 // fast mode
|
||||
#define CONFIG_HIGH_FLAG 0x800 // high quality mode
|
||||
#define CONFIG_VERY_HIGH_FLAG 0x1000 // very high
|
||||
#define CONFIG_BITRATE_KBPS 0x2000 // bitrate is kbps, not bits / sample
|
||||
#define CONFIG_SHAPE_OVERRIDE 0x8000 // shaping mode specified
|
||||
#define CONFIG_JOINT_OVERRIDE 0x10000 // joint-stereo mode specified
|
||||
#define CONFIG_DYNAMIC_SHAPING 0x20000 // dynamic noise shaping
|
||||
#define CONFIG_CREATE_EXE 0x40000 // create executable
|
||||
#define CONFIG_CREATE_WVC 0x80000 // create correction file
|
||||
#define CONFIG_OPTIMIZE_WVC 0x100000 // maximize bybrid compression
|
||||
#define CONFIG_CALC_NOISE 0x800000 // calc noise in hybrid mode
|
||||
#define CONFIG_EXTRA_MODE 0x2000000 // extra processing mode
|
||||
#define CONFIG_SKIP_WVX 0x4000000 // no wvx stream w/ floats & big ints
|
||||
#define CONFIG_MD5_CHECKSUM 0x8000000 // store MD5 signature
|
||||
#define CONFIG_MERGE_BLOCKS 0x10000000 // merge blocks of equal redundancy (for lossyWAV)
|
||||
#define CONFIG_OPTIMIZE_MONO 0x80000000 // optimize for mono streams posing as stereo
|
||||
|
||||
////////////// Callbacks used for reading & writing WavPack streams //////////
|
||||
|
||||
typedef struct {
|
||||
int32_t (*read_bytes)(void *id, void *data, int32_t bcount);
|
||||
uint32_t (*get_pos)(void *id);
|
||||
int (*set_pos_abs)(void *id, uint32_t pos);
|
||||
int (*set_pos_rel)(void *id, int32_t delta, int mode);
|
||||
int (*push_back_byte)(void *id, int c);
|
||||
uint32_t (*get_length)(void *id);
|
||||
int (*can_seek)(void *id);
|
||||
|
||||
// this callback is for writing edited tags only
|
||||
int32_t (*write_bytes)(void *id, void *data, int32_t bcount);
|
||||
} WavpackStreamReader;
|
||||
|
||||
typedef int (*WavpackBlockOutput)(void *id, void *data, int32_t bcount);
|
||||
|
||||
//////////////////////////// function prototypes /////////////////////////////
|
||||
|
||||
// Note: See wputils.c sourcecode for descriptions for using these functions.
|
||||
|
||||
typedef void WavpackContext;
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
WavpackContext *WavpackOpenFileInputEx (WavpackStreamReader *reader, void *wv_id, void *wvc_id, char *error, int flags, int norm_offset);
|
||||
WavpackContext *WavpackOpenFileInput (const wchar_t *infilename, char *error, int flags, int norm_offset);
|
||||
|
||||
#define OPEN_WVC 0x1 // open/read "correction" file
|
||||
#define OPEN_TAGS 0x2 // read ID3v1 / APEv2 tags (seekable file)
|
||||
#define OPEN_WRAPPER 0x4 // make audio wrapper available (i.e. RIFF)
|
||||
#define OPEN_2CH_MAX 0x8 // open multichannel as stereo (no downmix)
|
||||
#define OPEN_NORMALIZE 0x10 // normalize floating point data to +/- 1.0
|
||||
#define OPEN_STREAMING 0x20 // "streaming" mode blindly unpacks blocks
|
||||
// w/o regard to header file position info
|
||||
#define OPEN_EDIT_TAGS 0x40 // allow editing of tags
|
||||
|
||||
int WavpackGetMode (WavpackContext *wpc);
|
||||
|
||||
#define MODE_WVC 0x1
|
||||
#define MODE_LOSSLESS 0x2
|
||||
#define MODE_HYBRID 0x4
|
||||
#define MODE_FLOAT 0x8
|
||||
#define MODE_VALID_TAG 0x10
|
||||
#define MODE_HIGH 0x20
|
||||
#define MODE_FAST 0x40
|
||||
#define MODE_EXTRA 0x80 // extra mode used, see MODE_XMODE for possible level
|
||||
#define MODE_APETAG 0x100
|
||||
#define MODE_SFX 0x200
|
||||
#define MODE_VERY_HIGH 0x400
|
||||
#define MODE_MD5 0x800
|
||||
#define MODE_XMODE 0x7000 // mask for extra level (1-6, 0=unknown)
|
||||
#define MODE_DNS 0x8000
|
||||
|
||||
char *WavpackGetErrorMessage (WavpackContext *wpc);
|
||||
int WavpackGetVersion (WavpackContext *wpc);
|
||||
uint32_t WavpackUnpackSamples (WavpackContext *wpc, int32_t *buffer, uint32_t samples);
|
||||
uint32_t WavpackGetNumSamples (WavpackContext *wpc);
|
||||
uint32_t WavpackGetSampleIndex (WavpackContext *wpc);
|
||||
int WavpackGetNumErrors (WavpackContext *wpc);
|
||||
int WavpackLossyBlocks (WavpackContext *wpc);
|
||||
int WavpackSeekSample (WavpackContext *wpc, uint32_t sample);
|
||||
WavpackContext *WavpackCloseFile (WavpackContext *wpc);
|
||||
uint32_t WavpackGetSampleRate (WavpackContext *wpc);
|
||||
int WavpackGetBitsPerSample (WavpackContext *wpc);
|
||||
int WavpackGetBytesPerSample (WavpackContext *wpc);
|
||||
int WavpackGetNumChannels (WavpackContext *wpc);
|
||||
int WavpackGetChannelMask (WavpackContext *wpc);
|
||||
int WavpackGetReducedChannels (WavpackContext *wpc);
|
||||
int WavpackGetFloatNormExp (WavpackContext *wpc);
|
||||
int WavpackGetMD5Sum (WavpackContext *wpc, uchar data [16]);
|
||||
uint32_t WavpackGetWrapperBytes (WavpackContext *wpc);
|
||||
uchar *WavpackGetWrapperData (WavpackContext *wpc);
|
||||
void WavpackFreeWrapper (WavpackContext *wpc);
|
||||
void WavpackSeekTrailingWrapper (WavpackContext *wpc);
|
||||
double WavpackGetProgress (WavpackContext *wpc);
|
||||
uint32_t WavpackGetFileSize (WavpackContext *wpc);
|
||||
double WavpackGetRatio (WavpackContext *wpc);
|
||||
double WavpackGetAverageBitrate (WavpackContext *wpc, int count_wvc);
|
||||
double WavpackGetInstantBitrate (WavpackContext *wpc);
|
||||
int WavpackGetNumTagItems (WavpackContext *wpc);
|
||||
int WavpackGetTagItem (WavpackContext *wpc, const char *item, char *value, int size);
|
||||
int WavpackGetTagItemIndexed (WavpackContext *wpc, int index, char *item, int size);
|
||||
int WavpackAppendTagItem (WavpackContext *wpc, const char *item, const char *value, int vsize);
|
||||
int WavpackDeleteTagItem (WavpackContext *wpc, const char *item);
|
||||
int WavpackWriteTag (WavpackContext *wpc);
|
||||
|
||||
WavpackContext *WavpackOpenFileOutput (WavpackBlockOutput blockout, void *wv_id, void *wvc_id);
|
||||
int WavpackSetConfiguration (WavpackContext *wpc, WavpackConfig *config, uint32_t total_samples);
|
||||
int WavpackAddWrapper (WavpackContext *wpc, void *data, uint32_t bcount);
|
||||
int WavpackStoreMD5Sum (WavpackContext *wpc, uchar data [16]);
|
||||
int WavpackPackInit (WavpackContext *wpc);
|
||||
int WavpackPackSamples (WavpackContext *wpc, int32_t *sample_buffer, uint32_t sample_count);
|
||||
int WavpackFlushSamples (WavpackContext *wpc);
|
||||
void WavpackUpdateNumSamples (WavpackContext *wpc, void *first_block);
|
||||
void *WavpackGetWrapperLocation (void *first_block, uint32_t *size);
|
||||
double WavpackGetEncodedNoise (WavpackContext *wpc, double *peak);
|
||||
|
||||
void WavpackFloatNormalize (int32_t *values, int32_t num_values, int delta_exp);
|
||||
|
||||
void WavpackLittleEndianToNative (void *data, char *format);
|
||||
void WavpackNativeToLittleEndian (void *data, char *format);
|
||||
|
||||
uint32_t WavpackGetLibraryVersion (void);
|
||||
const char *WavpackGetLibraryVersionString (void);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif
|
||||
@@ -1,25 +0,0 @@
|
||||
Copyright (c) 1998 - 2008 Conifer Software
|
||||
All rights reserved.
|
||||
|
||||
Redistribution and use in source and binary forms, with or without
|
||||
modification, are permitted provided that the following conditions are met:
|
||||
|
||||
* Redistributions of source code must retain the above copyright notice,
|
||||
this list of conditions and the following disclaimer.
|
||||
* Redistributions in binary form must reproduce the above copyright notice,
|
||||
this list of conditions and the following disclaimer in the
|
||||
documentation and/or other materials provided with the distribution.
|
||||
* Neither the name of Conifer Software nor the names of its contributors
|
||||
may be used to endorse or promote products derived from this software
|
||||
without specific prior written permission.
|
||||
|
||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
|
||||
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR
|
||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
|
||||
SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
|
||||
CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
|
||||
OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
|
||||
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||
@@ -1,271 +0,0 @@
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
// **** WAVPACK **** //
|
||||
// Hybrid Lossless Wavefile Compressor //
|
||||
// Copyright (c) 1998 - 2006 Conifer Software. //
|
||||
// All Rights Reserved. //
|
||||
// Distributed under the BSD Software License (see license.txt) //
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// bits.c
|
||||
|
||||
// This module provides utilities to support the BitStream structure which is
|
||||
// used to read and write all WavPack audio data streams. It also contains a
|
||||
// wrapper for the stream I/O functions and a set of functions dealing with
|
||||
// endian-ness, both for enhancing portability. Finally, a debug wrapper for
|
||||
// the malloc() system is provided.
|
||||
|
||||
#include "wavpack_local.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <ctype.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#if defined(WIN32)
|
||||
#include <io.h>
|
||||
#else
|
||||
#include <unistd.h>
|
||||
#endif
|
||||
|
||||
////////////////////////// Bitstream functions ////////////////////////////////
|
||||
|
||||
#if !defined(NO_UNPACK) || defined(INFO_ONLY)
|
||||
|
||||
// Open the specified BitStream and associate with the specified buffer.
|
||||
|
||||
static void bs_read (Bitstream *bs);
|
||||
|
||||
void bs_open_read (Bitstream *bs, void *buffer_start, void *buffer_end)
|
||||
{
|
||||
bs->error = bs->sr = bs->bc = 0;
|
||||
bs->ptr = (bs->buf = buffer_start) - 1;
|
||||
bs->end = buffer_end;
|
||||
bs->wrap = bs_read;
|
||||
}
|
||||
|
||||
// This function is only called from the getbit() and getbits() macros when
|
||||
// the BitStream has been exhausted and more data is required. Sinve these
|
||||
// bistreams no longer access files, this function simple sets an error and
|
||||
// resets the buffer.
|
||||
|
||||
static void bs_read (Bitstream *bs)
|
||||
{
|
||||
bs->ptr = bs->buf - 1;
|
||||
bs->error = 1;
|
||||
}
|
||||
|
||||
// This function is called to close the bitstream. It returns the number of
|
||||
// full bytes actually read as bits.
|
||||
|
||||
uint32_t bs_close_read (Bitstream *bs)
|
||||
{
|
||||
uint32_t bytes_read;
|
||||
|
||||
if (bs->bc < sizeof (*(bs->ptr)) * 8)
|
||||
bs->ptr++;
|
||||
|
||||
bytes_read = (uint32_t)(bs->ptr - bs->buf) * sizeof (*(bs->ptr));
|
||||
|
||||
if (!(bytes_read & 1))
|
||||
++bytes_read;
|
||||
|
||||
CLEAR (*bs);
|
||||
return bytes_read;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef NO_PACK
|
||||
|
||||
// Open the specified BitStream using the specified buffer pointers. It is
|
||||
// assumed that enough buffer space has been allocated for all data that will
|
||||
// be written, otherwise an error will be generated.
|
||||
|
||||
static void bs_write (Bitstream *bs);
|
||||
|
||||
void bs_open_write (Bitstream *bs, void *buffer_start, void *buffer_end)
|
||||
{
|
||||
bs->error = bs->sr = bs->bc = 0;
|
||||
bs->ptr = bs->buf = buffer_start;
|
||||
bs->end = buffer_end;
|
||||
bs->wrap = bs_write;
|
||||
}
|
||||
|
||||
// This function is only called from the putbit() and putbits() macros when
|
||||
// the buffer is full, which is now flagged as an error.
|
||||
|
||||
static void bs_write (Bitstream *bs)
|
||||
{
|
||||
bs->ptr = bs->buf;
|
||||
bs->error = 1;
|
||||
}
|
||||
|
||||
// This function forces a flushing write of the specified BitStream, and
|
||||
// returns the total number of bytes written into the buffer.
|
||||
|
||||
uint32_t bs_close_write (Bitstream *bs)
|
||||
{
|
||||
uint32_t bytes_written;
|
||||
|
||||
if (bs->error)
|
||||
return (uint32_t) -1;
|
||||
|
||||
while (1) {
|
||||
while (bs->bc)
|
||||
putbit_1 (bs);
|
||||
|
||||
bytes_written = (uint32_t)(bs->ptr - bs->buf) * sizeof (*(bs->ptr));
|
||||
|
||||
if (bytes_written & 1) {
|
||||
putbit_1 (bs);
|
||||
}
|
||||
else
|
||||
break;
|
||||
};
|
||||
|
||||
CLEAR (*bs);
|
||||
return bytes_written;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
/////////////////////// Endian Correction Routines ////////////////////////////
|
||||
|
||||
void little_endian_to_native (void *data, char *format)
|
||||
{
|
||||
uchar *cp = (uchar *) data;
|
||||
int32_t temp;
|
||||
|
||||
while (*format) {
|
||||
switch (*format) {
|
||||
case 'L':
|
||||
temp = cp [0] + ((int32_t) cp [1] << 8) + ((int32_t) cp [2] << 16) + ((int32_t) cp [3] << 24);
|
||||
* (int32_t *) cp = temp;
|
||||
cp += 4;
|
||||
break;
|
||||
|
||||
case 'S':
|
||||
temp = cp [0] + (cp [1] << 8);
|
||||
* (short *) cp = (short) temp;
|
||||
cp += 2;
|
||||
break;
|
||||
|
||||
default:
|
||||
if (isdigit (*format))
|
||||
cp += *format - '0';
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
format++;
|
||||
}
|
||||
}
|
||||
|
||||
void native_to_little_endian (void *data, char *format)
|
||||
{
|
||||
uchar *cp = (uchar *) data;
|
||||
int32_t temp;
|
||||
|
||||
while (*format) {
|
||||
switch (*format) {
|
||||
case 'L':
|
||||
temp = * (int32_t *) cp;
|
||||
*cp++ = (uchar) temp;
|
||||
*cp++ = (uchar) (temp >> 8);
|
||||
*cp++ = (uchar) (temp >> 16);
|
||||
*cp++ = (uchar) (temp >> 24);
|
||||
break;
|
||||
|
||||
case 'S':
|
||||
temp = * (short *) cp;
|
||||
*cp++ = (uchar) temp;
|
||||
*cp++ = (uchar) (temp >> 8);
|
||||
break;
|
||||
|
||||
default:
|
||||
if (isdigit (*format))
|
||||
cp += *format - '0';
|
||||
|
||||
break;
|
||||
}
|
||||
|
||||
format++;
|
||||
}
|
||||
}
|
||||
|
||||
////////////////////////// Debug Wrapper for Malloc ///////////////////////////
|
||||
|
||||
#ifdef DEBUG_ALLOC
|
||||
|
||||
void *vptrs [512];
|
||||
|
||||
static void *add_ptr (void *ptr)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < 512; ++i)
|
||||
if (!vptrs [i]) {
|
||||
vptrs [i] = ptr;
|
||||
break;
|
||||
}
|
||||
|
||||
if (i == 512)
|
||||
error_line ("too many mallocs!");
|
||||
|
||||
return ptr;
|
||||
}
|
||||
|
||||
static void *del_ptr (void *ptr)
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i = 0; i < 512; ++i)
|
||||
if (vptrs [i] == ptr) {
|
||||
vptrs [i] = NULL;
|
||||
break;
|
||||
}
|
||||
|
||||
if (i == 512)
|
||||
error_line ("free invalid ptr!");
|
||||
|
||||
return ptr;
|
||||
}
|
||||
|
||||
void *malloc_db (uint32_t size)
|
||||
{
|
||||
if (size)
|
||||
return add_ptr (malloc (size));
|
||||
else
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void free_db (void *ptr)
|
||||
{
|
||||
if (ptr)
|
||||
free (del_ptr (ptr));
|
||||
}
|
||||
|
||||
void *realloc_db (void *ptr, uint32_t size)
|
||||
{
|
||||
if (ptr && size)
|
||||
return add_ptr (realloc (del_ptr (ptr), size));
|
||||
else if (size)
|
||||
return malloc_db (size);
|
||||
else
|
||||
free_db (ptr);
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int32_t dump_alloc (void)
|
||||
{
|
||||
int i, j;
|
||||
|
||||
for (j = i = 0; i < 512; ++i)
|
||||
if (vptrs [i])
|
||||
j++;
|
||||
|
||||
return j;
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -1,671 +0,0 @@
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
// **** WAVPACK **** //
|
||||
// Hybrid Lossless Wavefile Compressor //
|
||||
// Copyright (c) 1998 - 2006 Conifer Software. //
|
||||
// All Rights Reserved. //
|
||||
// Distributed under the BSD Software License (see license.txt) //
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// extra1.c
|
||||
|
||||
// This module handles the "extra" mode for mono files.
|
||||
|
||||
#include "wavpack_local.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <math.h>
|
||||
|
||||
//#define USE_OVERHEAD
|
||||
#define LOG_LIMIT 6912
|
||||
//#define EXTRA_DUMP
|
||||
|
||||
#ifdef DEBUG_ALLOC
|
||||
#define malloc malloc_db
|
||||
#define realloc realloc_db
|
||||
#define free free_db
|
||||
void *malloc_db (uint32_t size);
|
||||
void *realloc_db (void *ptr, uint32_t size);
|
||||
void free_db (void *ptr);
|
||||
int32_t dump_alloc (void);
|
||||
#endif
|
||||
|
||||
//////////////////////////////// local tables ///////////////////////////////
|
||||
|
||||
typedef struct {
|
||||
int32_t *sampleptrs [MAX_NTERMS+2];
|
||||
struct decorr_pass dps [MAX_NTERMS];
|
||||
int nterms, log_limit;
|
||||
uint32_t best_bits;
|
||||
} WavpackExtraInfo;
|
||||
|
||||
static void decorr_mono_pass (int32_t *in_samples, int32_t *out_samples, uint32_t num_samples, struct decorr_pass *dpp, int dir)
|
||||
{
|
||||
int m = 0, i;
|
||||
|
||||
dpp->sum_A = 0;
|
||||
|
||||
if (dir < 0) {
|
||||
out_samples += (num_samples - 1);
|
||||
in_samples += (num_samples - 1);
|
||||
dir = -1;
|
||||
}
|
||||
else
|
||||
dir = 1;
|
||||
|
||||
dpp->weight_A = restore_weight (store_weight (dpp->weight_A));
|
||||
|
||||
for (i = 0; i < 8; ++i)
|
||||
dpp->samples_A [i] = exp2s (log2s (dpp->samples_A [i]));
|
||||
|
||||
if (dpp->term > MAX_TERM) {
|
||||
while (num_samples--) {
|
||||
int32_t left, sam_A;
|
||||
|
||||
if (dpp->term & 1)
|
||||
sam_A = 2 * dpp->samples_A [0] - dpp->samples_A [1];
|
||||
else
|
||||
sam_A = (3 * dpp->samples_A [0] - dpp->samples_A [1]) >> 1;
|
||||
|
||||
dpp->samples_A [1] = dpp->samples_A [0];
|
||||
dpp->samples_A [0] = left = in_samples [0];
|
||||
|
||||
left -= apply_weight (dpp->weight_A, sam_A);
|
||||
update_weight (dpp->weight_A, dpp->delta, sam_A, left);
|
||||
dpp->sum_A += dpp->weight_A;
|
||||
out_samples [0] = left;
|
||||
in_samples += dir;
|
||||
out_samples += dir;
|
||||
}
|
||||
}
|
||||
else if (dpp->term > 0) {
|
||||
while (num_samples--) {
|
||||
int k = (m + dpp->term) & (MAX_TERM - 1);
|
||||
int32_t left, sam_A;
|
||||
|
||||
sam_A = dpp->samples_A [m];
|
||||
dpp->samples_A [k] = left = in_samples [0];
|
||||
m = (m + 1) & (MAX_TERM - 1);
|
||||
|
||||
left -= apply_weight (dpp->weight_A, sam_A);
|
||||
update_weight (dpp->weight_A, dpp->delta, sam_A, left);
|
||||
dpp->sum_A += dpp->weight_A;
|
||||
out_samples [0] = left;
|
||||
in_samples += dir;
|
||||
out_samples += dir;
|
||||
}
|
||||
}
|
||||
|
||||
if (m && dpp->term > 0 && dpp->term <= MAX_TERM) {
|
||||
int32_t temp_A [MAX_TERM];
|
||||
int k;
|
||||
|
||||
memcpy (temp_A, dpp->samples_A, sizeof (dpp->samples_A));
|
||||
|
||||
for (k = 0; k < MAX_TERM; k++) {
|
||||
dpp->samples_A [k] = temp_A [m];
|
||||
m = (m + 1) & (MAX_TERM - 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void reverse_mono_decorr (struct decorr_pass *dpp)
|
||||
{
|
||||
if (dpp->term > MAX_TERM) {
|
||||
int32_t sam_A;
|
||||
|
||||
if (dpp->term & 1)
|
||||
sam_A = 2 * dpp->samples_A [0] - dpp->samples_A [1];
|
||||
else
|
||||
sam_A = (3 * dpp->samples_A [0] - dpp->samples_A [1]) >> 1;
|
||||
|
||||
dpp->samples_A [1] = dpp->samples_A [0];
|
||||
dpp->samples_A [0] = sam_A;
|
||||
|
||||
if (dpp->term & 1)
|
||||
sam_A = 2 * dpp->samples_A [0] - dpp->samples_A [1];
|
||||
else
|
||||
sam_A = (3 * dpp->samples_A [0] - dpp->samples_A [1]) >> 1;
|
||||
|
||||
dpp->samples_A [1] = sam_A;
|
||||
}
|
||||
else if (dpp->term > 1) {
|
||||
int i = 0, j = dpp->term - 1, cnt = dpp->term / 2;
|
||||
|
||||
while (cnt--) {
|
||||
i &= (MAX_TERM - 1);
|
||||
j &= (MAX_TERM - 1);
|
||||
dpp->samples_A [i] ^= dpp->samples_A [j];
|
||||
dpp->samples_A [j] ^= dpp->samples_A [i];
|
||||
dpp->samples_A [i++] ^= dpp->samples_A [j--];
|
||||
}
|
||||
|
||||
// CLEAR (dpp->samples_A);
|
||||
}
|
||||
}
|
||||
|
||||
static void decorr_mono_buffer (int32_t *samples, int32_t *outsamples, uint32_t num_samples, struct decorr_pass *dpp, int tindex)
|
||||
{
|
||||
struct decorr_pass dp, *dppi = dpp + tindex;
|
||||
int delta = dppi->delta, pre_delta, term = dppi->term;
|
||||
|
||||
if (delta == 7)
|
||||
pre_delta = 7;
|
||||
else if (delta < 2)
|
||||
pre_delta = 3;
|
||||
else
|
||||
pre_delta = delta + 1;
|
||||
|
||||
CLEAR (dp);
|
||||
dp.term = term;
|
||||
dp.delta = pre_delta;
|
||||
decorr_mono_pass (samples, outsamples, num_samples > 2048 ? 2048 : num_samples, &dp, -1);
|
||||
dp.delta = delta;
|
||||
|
||||
if (tindex == 0)
|
||||
reverse_mono_decorr (&dp);
|
||||
else
|
||||
CLEAR (dp.samples_A);
|
||||
|
||||
memcpy (dppi->samples_A, dp.samples_A, sizeof (dp.samples_A));
|
||||
dppi->weight_A = dp.weight_A;
|
||||
|
||||
if (delta == 0) {
|
||||
dp.delta = 1;
|
||||
decorr_mono_pass (samples, outsamples, num_samples, &dp, 1);
|
||||
dp.delta = 0;
|
||||
memcpy (dp.samples_A, dppi->samples_A, sizeof (dp.samples_A));
|
||||
dppi->weight_A = dp.weight_A = dp.sum_A / num_samples;
|
||||
}
|
||||
|
||||
// if (memcmp (dppi, &dp, sizeof (dp)))
|
||||
// error_line ("decorr_passes don't match, delta = %d", delta);
|
||||
|
||||
decorr_mono_pass (samples, outsamples, num_samples, &dp, 1);
|
||||
}
|
||||
|
||||
static int log2overhead (int first_term, int num_terms)
|
||||
{
|
||||
#ifdef USE_OVERHEAD
|
||||
if (first_term > MAX_TERM)
|
||||
return (4 + num_terms * 2) << 11;
|
||||
else
|
||||
return (2 + num_terms * 2) << 11;
|
||||
#else
|
||||
return 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
static void recurse_mono (WavpackContext *wpc, WavpackExtraInfo *info, int depth, int delta, uint32_t input_bits)
|
||||
{
|
||||
WavpackStream *wps = wpc->streams [wpc->current_stream];
|
||||
int term, branches = ((wpc->config.extra_flags & EXTRA_BRANCHES) >> 6) - depth;
|
||||
int32_t *samples, *outsamples;
|
||||
uint32_t term_bits [22], bits;
|
||||
|
||||
if (branches < 1 || depth + 1 == info->nterms)
|
||||
branches = 1;
|
||||
|
||||
CLEAR (term_bits);
|
||||
samples = info->sampleptrs [depth];
|
||||
outsamples = info->sampleptrs [depth + 1];
|
||||
|
||||
for (term = 1; term <= 18; ++term) {
|
||||
if (term == 17 && branches == 1 && depth + 1 < info->nterms)
|
||||
continue;
|
||||
|
||||
if (term > 8 && term < 17)
|
||||
continue;
|
||||
|
||||
if ((wpc->config.flags & CONFIG_FAST_FLAG) && (term > 4 && term < 17))
|
||||
continue;
|
||||
|
||||
info->dps [depth].term = term;
|
||||
info->dps [depth].delta = delta;
|
||||
decorr_mono_buffer (samples, outsamples, wps->wphdr.block_samples, info->dps, depth);
|
||||
bits = log2buffer (outsamples, wps->wphdr.block_samples, info->log_limit);
|
||||
|
||||
if (bits != (uint32_t) -1)
|
||||
bits += log2overhead (info->dps [0].term, depth + 1);
|
||||
|
||||
if (bits < info->best_bits) {
|
||||
info->best_bits = bits;
|
||||
CLEAR (wps->decorr_passes);
|
||||
memcpy (wps->decorr_passes, info->dps, sizeof (info->dps [0]) * (depth + 1));
|
||||
memcpy (info->sampleptrs [info->nterms + 1], info->sampleptrs [depth + 1], wps->wphdr.block_samples * 4);
|
||||
}
|
||||
|
||||
term_bits [term + 3] = bits;
|
||||
}
|
||||
|
||||
while (depth + 1 < info->nterms && branches--) {
|
||||
uint32_t local_best_bits = input_bits;
|
||||
int best_term = 0, i;
|
||||
|
||||
for (i = 0; i < 22; ++i)
|
||||
if (term_bits [i] && term_bits [i] < local_best_bits) {
|
||||
local_best_bits = term_bits [i];
|
||||
// term_bits [i] = 0;
|
||||
best_term = i - 3;
|
||||
}
|
||||
|
||||
if (!best_term)
|
||||
break;
|
||||
|
||||
term_bits [best_term + 3] = 0;
|
||||
|
||||
info->dps [depth].term = best_term;
|
||||
info->dps [depth].delta = delta;
|
||||
decorr_mono_buffer (samples, outsamples, wps->wphdr.block_samples, info->dps, depth);
|
||||
|
||||
// if (log2buffer (outsamples, wps->wphdr.block_samples * 2, 0) != local_best_bits)
|
||||
// error_line ("data doesn't match!");
|
||||
|
||||
recurse_mono (wpc, info, depth + 1, delta, local_best_bits);
|
||||
}
|
||||
}
|
||||
|
||||
static void delta_mono (WavpackContext *wpc, WavpackExtraInfo *info)
|
||||
{
|
||||
WavpackStream *wps = wpc->streams [wpc->current_stream];
|
||||
int lower = FALSE, delta, d;
|
||||
uint32_t bits;
|
||||
|
||||
if (wps->decorr_passes [0].term)
|
||||
delta = wps->decorr_passes [0].delta;
|
||||
else
|
||||
return;
|
||||
|
||||
for (d = delta - 1; d >= 0; --d) {
|
||||
int i;
|
||||
|
||||
if (!d && (wps->wphdr.flags & HYBRID_FLAG))
|
||||
break;
|
||||
|
||||
for (i = 0; i < info->nterms && wps->decorr_passes [i].term; ++i) {
|
||||
info->dps [i].term = wps->decorr_passes [i].term;
|
||||
info->dps [i].delta = d;
|
||||
decorr_mono_buffer (info->sampleptrs [i], info->sampleptrs [i+1], wps->wphdr.block_samples, info->dps, i);
|
||||
}
|
||||
|
||||
bits = log2buffer (info->sampleptrs [i], wps->wphdr.block_samples, info->log_limit);
|
||||
|
||||
if (bits != (uint32_t) -1)
|
||||
bits += log2overhead (wps->decorr_passes [0].term, i);
|
||||
|
||||
if (bits < info->best_bits) {
|
||||
lower = TRUE;
|
||||
info->best_bits = bits;
|
||||
CLEAR (wps->decorr_passes);
|
||||
memcpy (wps->decorr_passes, info->dps, sizeof (info->dps [0]) * i);
|
||||
memcpy (info->sampleptrs [info->nterms + 1], info->sampleptrs [i], wps->wphdr.block_samples * 4);
|
||||
}
|
||||
else
|
||||
break;
|
||||
}
|
||||
|
||||
for (d = delta + 1; !lower && d <= 7; ++d) {
|
||||
int i;
|
||||
|
||||
for (i = 0; i < info->nterms && wps->decorr_passes [i].term; ++i) {
|
||||
info->dps [i].term = wps->decorr_passes [i].term;
|
||||
info->dps [i].delta = d;
|
||||
decorr_mono_buffer (info->sampleptrs [i], info->sampleptrs [i+1], wps->wphdr.block_samples, info->dps, i);
|
||||
}
|
||||
|
||||
bits = log2buffer (info->sampleptrs [i], wps->wphdr.block_samples, info->log_limit);
|
||||
|
||||
if (bits != (uint32_t) -1)
|
||||
bits += log2overhead (wps->decorr_passes [0].term, i);
|
||||
|
||||
if (bits < info->best_bits) {
|
||||
info->best_bits = bits;
|
||||
CLEAR (wps->decorr_passes);
|
||||
memcpy (wps->decorr_passes, info->dps, sizeof (info->dps [0]) * i);
|
||||
memcpy (info->sampleptrs [info->nterms + 1], info->sampleptrs [i], wps->wphdr.block_samples * 4);
|
||||
}
|
||||
else
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
static void sort_mono (WavpackContext *wpc, WavpackExtraInfo *info)
|
||||
{
|
||||
WavpackStream *wps = wpc->streams [wpc->current_stream];
|
||||
int reversed = TRUE;
|
||||
uint32_t bits;
|
||||
|
||||
while (reversed) {
|
||||
int ri, i;
|
||||
|
||||
memcpy (info->dps, wps->decorr_passes, sizeof (wps->decorr_passes));
|
||||
reversed = FALSE;
|
||||
|
||||
for (ri = 0; ri < info->nterms && wps->decorr_passes [ri].term; ++ri) {
|
||||
|
||||
if (ri + 1 >= info->nterms || !wps->decorr_passes [ri+1].term)
|
||||
break;
|
||||
|
||||
if (wps->decorr_passes [ri].term == wps->decorr_passes [ri+1].term) {
|
||||
decorr_mono_buffer (info->sampleptrs [ri], info->sampleptrs [ri+1], wps->wphdr.block_samples, info->dps, ri);
|
||||
continue;
|
||||
}
|
||||
|
||||
info->dps [ri] = wps->decorr_passes [ri+1];
|
||||
info->dps [ri+1] = wps->decorr_passes [ri];
|
||||
|
||||
for (i = ri; i < info->nterms && wps->decorr_passes [i].term; ++i)
|
||||
decorr_mono_buffer (info->sampleptrs [i], info->sampleptrs [i+1], wps->wphdr.block_samples, info->dps, i);
|
||||
|
||||
bits = log2buffer (info->sampleptrs [i], wps->wphdr.block_samples, info->log_limit);
|
||||
|
||||
if (bits != (uint32_t) -1)
|
||||
bits += log2overhead (wps->decorr_passes [0].term, i);
|
||||
|
||||
if (bits < info->best_bits) {
|
||||
reversed = TRUE;
|
||||
info->best_bits = bits;
|
||||
CLEAR (wps->decorr_passes);
|
||||
memcpy (wps->decorr_passes, info->dps, sizeof (info->dps [0]) * i);
|
||||
memcpy (info->sampleptrs [info->nterms + 1], info->sampleptrs [i], wps->wphdr.block_samples * 4);
|
||||
}
|
||||
else {
|
||||
info->dps [ri] = wps->decorr_passes [ri];
|
||||
info->dps [ri+1] = wps->decorr_passes [ri+1];
|
||||
decorr_mono_buffer (info->sampleptrs [ri], info->sampleptrs [ri+1], wps->wphdr.block_samples, info->dps, ri);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static const uint32_t xtable [] = { 91, 123, 187, 251 };
|
||||
|
||||
static void analyze_mono (WavpackContext *wpc, int32_t *samples, int do_samples)
|
||||
{
|
||||
WavpackStream *wps = wpc->streams [wpc->current_stream];
|
||||
WavpackExtraInfo info;
|
||||
int i;
|
||||
|
||||
#ifdef LOG_LIMIT
|
||||
info.log_limit = (((wps->wphdr.flags & MAG_MASK) >> MAG_LSB) + 4) * 256;
|
||||
|
||||
if (info.log_limit > LOG_LIMIT)
|
||||
info.log_limit = LOG_LIMIT;
|
||||
#else
|
||||
info.log_limit = 0;
|
||||
#endif
|
||||
|
||||
if (wpc->config.flags & (CONFIG_HIGH_FLAG | CONFIG_VERY_HIGH_FLAG))
|
||||
wpc->config.extra_flags = xtable [wpc->config.xmode - 4];
|
||||
else
|
||||
wpc->config.extra_flags = xtable [wpc->config.xmode - 3];
|
||||
|
||||
info.nterms = wps->num_terms;
|
||||
|
||||
for (i = 0; i < info.nterms + 2; ++i)
|
||||
info.sampleptrs [i] = malloc (wps->wphdr.block_samples * 4);
|
||||
|
||||
memcpy (info.dps, wps->decorr_passes, sizeof (info.dps));
|
||||
memcpy (info.sampleptrs [0], samples, wps->wphdr.block_samples * 4);
|
||||
|
||||
for (i = 0; i < info.nterms && info.dps [i].term; ++i)
|
||||
decorr_mono_pass (info.sampleptrs [i], info.sampleptrs [i + 1], wps->wphdr.block_samples, info.dps + i, 1);
|
||||
|
||||
info.best_bits = log2buffer (info.sampleptrs [info.nterms], wps->wphdr.block_samples, 0) * 1;
|
||||
info.best_bits += log2overhead (info.dps [0].term, i);
|
||||
memcpy (info.sampleptrs [info.nterms + 1], info.sampleptrs [i], wps->wphdr.block_samples * 4);
|
||||
|
||||
if (wpc->config.extra_flags & EXTRA_BRANCHES)
|
||||
recurse_mono (wpc, &info, 0, (int) floor (wps->delta_decay + 0.5),
|
||||
log2buffer (info.sampleptrs [0], wps->wphdr.block_samples, 0));
|
||||
|
||||
if (wpc->config.extra_flags & EXTRA_SORT_FIRST)
|
||||
sort_mono (wpc, &info);
|
||||
|
||||
if (wpc->config.extra_flags & EXTRA_TRY_DELTAS) {
|
||||
delta_mono (wpc, &info);
|
||||
|
||||
if ((wpc->config.extra_flags & EXTRA_ADJUST_DELTAS) && wps->decorr_passes [0].term)
|
||||
wps->delta_decay = (float)((wps->delta_decay * 2.0 + wps->decorr_passes [0].delta) / 3.0);
|
||||
else
|
||||
wps->delta_decay = 2.0;
|
||||
}
|
||||
|
||||
if (wpc->config.extra_flags & EXTRA_SORT_LAST)
|
||||
sort_mono (wpc, &info);
|
||||
|
||||
if (do_samples)
|
||||
memcpy (samples, info.sampleptrs [info.nterms + 1], wps->wphdr.block_samples * 4);
|
||||
|
||||
for (i = 0; i < info.nterms; ++i)
|
||||
if (!wps->decorr_passes [i].term)
|
||||
break;
|
||||
|
||||
wps->num_terms = i;
|
||||
|
||||
for (i = 0; i < info.nterms + 2; ++i)
|
||||
free (info.sampleptrs [i]);
|
||||
}
|
||||
|
||||
static void mono_add_noise (WavpackStream *wps, int32_t *lptr, int32_t *rptr)
|
||||
{
|
||||
int shaping_weight, new = wps->wphdr.flags & NEW_SHAPING;
|
||||
short *shaping_array = wps->dc.shaping_array;
|
||||
int32_t error = 0, temp, cnt;
|
||||
|
||||
scan_word (wps, rptr, wps->wphdr.block_samples, -1);
|
||||
cnt = wps->wphdr.block_samples;
|
||||
|
||||
if (wps->wphdr.flags & HYBRID_SHAPE) {
|
||||
while (cnt--) {
|
||||
if (shaping_array)
|
||||
shaping_weight = *shaping_array++;
|
||||
else
|
||||
shaping_weight = (wps->dc.shaping_acc [0] += wps->dc.shaping_delta [0]) >> 16;
|
||||
|
||||
temp = -apply_weight (shaping_weight, error);
|
||||
|
||||
if (new && shaping_weight < 0 && temp) {
|
||||
if (temp == error)
|
||||
temp = (temp < 0) ? temp + 1 : temp - 1;
|
||||
|
||||
lptr [0] += (error = nosend_word (wps, rptr [0], 0) - rptr [0] + temp);
|
||||
}
|
||||
else
|
||||
lptr [0] += (error = nosend_word (wps, rptr [0], 0) - rptr [0]) + temp;
|
||||
|
||||
lptr++;
|
||||
rptr++;
|
||||
}
|
||||
|
||||
if (!shaping_array)
|
||||
wps->dc.shaping_acc [0] -= wps->dc.shaping_delta [0] * wps->wphdr.block_samples;
|
||||
}
|
||||
else
|
||||
while (cnt--) {
|
||||
lptr [0] += nosend_word (wps, rptr [0], 0) - rptr [0];
|
||||
lptr++;
|
||||
rptr++;
|
||||
}
|
||||
}
|
||||
|
||||
void execute_mono (WavpackContext *wpc, int32_t *samples, int no_history, int do_samples)
|
||||
{
|
||||
int32_t *temp_buffer [2], *best_buffer, *noisy_buffer = NULL;
|
||||
struct decorr_pass temp_decorr_pass, save_decorr_passes [MAX_NTERMS];
|
||||
WavpackStream *wps = wpc->streams [wpc->current_stream];
|
||||
int32_t num_samples = wps->wphdr.block_samples;
|
||||
int32_t buf_size = sizeof (int32_t) * num_samples;
|
||||
uint32_t best_size = (uint32_t) -1, size;
|
||||
int log_limit, pi, i;
|
||||
|
||||
for (i = 0; i < num_samples; ++i)
|
||||
if (samples [i])
|
||||
break;
|
||||
|
||||
if (i == num_samples) {
|
||||
CLEAR (wps->decorr_passes);
|
||||
wps->num_terms = 0;
|
||||
init_words (wps);
|
||||
return;
|
||||
}
|
||||
|
||||
#ifdef LOG_LIMIT
|
||||
log_limit = (((wps->wphdr.flags & MAG_MASK) >> MAG_LSB) + 4) * 256;
|
||||
|
||||
if (log_limit > LOG_LIMIT)
|
||||
log_limit = LOG_LIMIT;
|
||||
#else
|
||||
log_limit = 0;
|
||||
#endif
|
||||
|
||||
CLEAR (save_decorr_passes);
|
||||
temp_buffer [0] = malloc (buf_size);
|
||||
temp_buffer [1] = malloc (buf_size);
|
||||
best_buffer = malloc (buf_size);
|
||||
|
||||
if (wps->num_passes > 1 && (wps->wphdr.flags & HYBRID_FLAG)) {
|
||||
CLEAR (temp_decorr_pass);
|
||||
temp_decorr_pass.delta = 2;
|
||||
temp_decorr_pass.term = 18;
|
||||
|
||||
decorr_mono_pass (samples, temp_buffer [0],
|
||||
num_samples > 2048 ? 2048 : num_samples, &temp_decorr_pass, -1);
|
||||
|
||||
reverse_mono_decorr (&temp_decorr_pass);
|
||||
decorr_mono_pass (samples, temp_buffer [0], num_samples, &temp_decorr_pass, 1);
|
||||
CLEAR (temp_decorr_pass);
|
||||
temp_decorr_pass.delta = 2;
|
||||
temp_decorr_pass.term = 17;
|
||||
|
||||
decorr_mono_pass (temp_buffer [0], temp_buffer [1],
|
||||
num_samples > 2048 ? 2048 : num_samples, &temp_decorr_pass, -1);
|
||||
|
||||
decorr_mono_pass (temp_buffer [0], temp_buffer [1], num_samples, &temp_decorr_pass, 1);
|
||||
noisy_buffer = malloc (buf_size);
|
||||
memcpy (noisy_buffer, samples, buf_size);
|
||||
mono_add_noise (wps, noisy_buffer, temp_buffer [1]);
|
||||
no_history = 1;
|
||||
}
|
||||
|
||||
if (no_history || wps->num_passes >= 7)
|
||||
wps->best_decorr = wps->mask_decorr = 0;
|
||||
|
||||
for (pi = 0; pi < wps->num_passes;) {
|
||||
const WavpackDecorrSpec *wpds;
|
||||
int nterms, c, j;
|
||||
|
||||
if (!pi)
|
||||
c = wps->best_decorr;
|
||||
else {
|
||||
if (wps->mask_decorr == 0)
|
||||
c = 0;
|
||||
else
|
||||
c = (wps->best_decorr & (wps->mask_decorr - 1)) | wps->mask_decorr;
|
||||
|
||||
if (c == wps->best_decorr) {
|
||||
wps->mask_decorr = wps->mask_decorr ? ((wps->mask_decorr << 1) & (wps->num_decorrs - 1)) : 1;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
|
||||
wpds = &wps->decorr_specs [c];
|
||||
nterms = (int) strlen (wpds->terms);
|
||||
|
||||
while (1) {
|
||||
memcpy (temp_buffer [0], noisy_buffer ? noisy_buffer : samples, buf_size);
|
||||
CLEAR (save_decorr_passes);
|
||||
|
||||
for (j = 0; j < nterms; ++j) {
|
||||
CLEAR (temp_decorr_pass);
|
||||
temp_decorr_pass.delta = wpds->delta;
|
||||
temp_decorr_pass.term = wpds->terms [j];
|
||||
|
||||
if (temp_decorr_pass.term < 0)
|
||||
temp_decorr_pass.term = 1;
|
||||
|
||||
decorr_mono_pass (temp_buffer [j&1], temp_buffer [~j&1],
|
||||
num_samples > 2048 ? 2048 : num_samples, &temp_decorr_pass, -1);
|
||||
|
||||
if (j) {
|
||||
CLEAR (temp_decorr_pass.samples_A);
|
||||
}
|
||||
else
|
||||
reverse_mono_decorr (&temp_decorr_pass);
|
||||
|
||||
memcpy (save_decorr_passes + j, &temp_decorr_pass, sizeof (struct decorr_pass));
|
||||
decorr_mono_pass (temp_buffer [j&1], temp_buffer [~j&1], num_samples, &temp_decorr_pass, 1);
|
||||
}
|
||||
|
||||
size = log2buffer (temp_buffer [j&1], num_samples, log_limit);
|
||||
|
||||
if (size == (uint32_t) -1 && nterms)
|
||||
nterms >>= 1;
|
||||
else
|
||||
break;
|
||||
}
|
||||
|
||||
size += log2overhead (wpds->terms [0], nterms);
|
||||
|
||||
if (size < best_size) {
|
||||
memcpy (best_buffer, temp_buffer [j&1], buf_size);
|
||||
memcpy (wps->decorr_passes, save_decorr_passes, sizeof (struct decorr_pass) * MAX_NTERMS);
|
||||
wps->num_terms = nterms;
|
||||
wps->best_decorr = c;
|
||||
best_size = size;
|
||||
}
|
||||
|
||||
if (pi++)
|
||||
wps->mask_decorr = wps->mask_decorr ? ((wps->mask_decorr << 1) & (wps->num_decorrs - 1)) : 1;
|
||||
}
|
||||
|
||||
if (wpc->config.xmode > 3) {
|
||||
if (noisy_buffer) {
|
||||
analyze_mono (wpc, noisy_buffer, do_samples);
|
||||
|
||||
if (do_samples)
|
||||
memcpy (samples, noisy_buffer, buf_size);
|
||||
}
|
||||
else
|
||||
analyze_mono (wpc, samples, do_samples);
|
||||
}
|
||||
else if (do_samples)
|
||||
memcpy (samples, best_buffer, buf_size);
|
||||
|
||||
if (no_history || wpc->config.xmode > 3)
|
||||
scan_word (wps, best_buffer, num_samples, -1);
|
||||
|
||||
if (noisy_buffer)
|
||||
free (noisy_buffer);
|
||||
|
||||
free (temp_buffer [1]);
|
||||
free (temp_buffer [0]);
|
||||
free (best_buffer);
|
||||
|
||||
#ifdef EXTRA_DUMP
|
||||
if (1) {
|
||||
char string [256], substring [20];
|
||||
int i;
|
||||
|
||||
sprintf (string, "M: terms =");
|
||||
|
||||
for (i = 0; i < wps->num_terms; ++i) {
|
||||
if (wps->decorr_passes [i].term) {
|
||||
if (i && wps->decorr_passes [i-1].delta == wps->decorr_passes [i].delta)
|
||||
sprintf (substring, " %d", wps->decorr_passes [i].term);
|
||||
else
|
||||
sprintf (substring, " %d->%d", wps->decorr_passes [i].term,
|
||||
wps->decorr_passes [i].delta);
|
||||
}
|
||||
else
|
||||
sprintf (substring, " *");
|
||||
|
||||
strcat (string, substring);
|
||||
}
|
||||
|
||||
error_line (string);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,371 +0,0 @@
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
// **** WAVPACK **** //
|
||||
// Hybrid Lossless Wavefile Compressor //
|
||||
// Copyright (c) 1998 - 2006 Conifer Software. //
|
||||
// All Rights Reserved. //
|
||||
// Distributed under the BSD Software License (see license.txt) //
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// float.c
|
||||
|
||||
#include "wavpack_local.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
|
||||
#ifdef DEBUG_ALLOC
|
||||
#define malloc malloc_db
|
||||
#define realloc realloc_db
|
||||
#define free free_db
|
||||
void *malloc_db (uint32_t size);
|
||||
void *realloc_db (void *ptr, uint32_t size);
|
||||
void free_db (void *ptr);
|
||||
int32_t dump_alloc (void);
|
||||
#endif
|
||||
|
||||
#ifndef NO_PACK
|
||||
|
||||
void write_float_info (WavpackStream *wps, WavpackMetadata *wpmd)
|
||||
{
|
||||
char *byteptr;
|
||||
|
||||
byteptr = wpmd->data = malloc (4);
|
||||
wpmd->id = ID_FLOAT_INFO;
|
||||
*byteptr++ = wps->float_flags;
|
||||
*byteptr++ = wps->float_shift;
|
||||
*byteptr++ = wps->float_max_exp;
|
||||
*byteptr++ = wps->float_norm_exp;
|
||||
wpmd->byte_length = (int32_t)(byteptr - (char *) wpmd->data);
|
||||
}
|
||||
|
||||
int scan_float_data (WavpackStream *wps, f32 *values, int32_t num_values)
|
||||
{
|
||||
int32_t shifted_ones = 0, shifted_zeros = 0, shifted_both = 0;
|
||||
int32_t false_zeros = 0, neg_zeros = 0;
|
||||
uint32_t ordata = 0, crc = 0xffffffff;
|
||||
int32_t count, value, shift_count;
|
||||
int max_exp = 0;
|
||||
f32 *dp;
|
||||
|
||||
wps->float_shift = wps->float_flags = 0;
|
||||
|
||||
for (dp = values, count = num_values; count--; dp++) {
|
||||
crc = crc * 27 + get_mantissa (*dp) * 9 + get_exponent (*dp) * 3 + get_sign (*dp);
|
||||
|
||||
if (get_exponent (*dp) > max_exp && get_exponent (*dp) < 255)
|
||||
max_exp = get_exponent (*dp);
|
||||
}
|
||||
|
||||
wps->crc_x = crc;
|
||||
|
||||
for (dp = values, count = num_values; count--; dp++) {
|
||||
if (get_exponent (*dp) == 255) {
|
||||
wps->float_flags |= FLOAT_EXCEPTIONS;
|
||||
value = 0x1000000;
|
||||
shift_count = 0;
|
||||
}
|
||||
else if (get_exponent (*dp)) {
|
||||
shift_count = max_exp - get_exponent (*dp);
|
||||
value = 0x800000 + get_mantissa (*dp);
|
||||
}
|
||||
else {
|
||||
shift_count = max_exp ? max_exp - 1 : 0;
|
||||
value = get_mantissa (*dp);
|
||||
|
||||
// if (get_mantissa (*dp))
|
||||
// denormals++;
|
||||
}
|
||||
|
||||
if (shift_count < 25)
|
||||
value >>= shift_count;
|
||||
else
|
||||
value = 0;
|
||||
|
||||
if (!value) {
|
||||
if (get_exponent (*dp) || get_mantissa (*dp))
|
||||
++false_zeros;
|
||||
else if (get_sign (*dp))
|
||||
++neg_zeros;
|
||||
}
|
||||
else if (shift_count) {
|
||||
int32_t mask = (1 << shift_count) - 1;
|
||||
|
||||
if (!(get_mantissa (*dp) & mask))
|
||||
shifted_zeros++;
|
||||
else if ((get_mantissa (*dp) & mask) == mask)
|
||||
shifted_ones++;
|
||||
else
|
||||
shifted_both++;
|
||||
}
|
||||
|
||||
ordata |= value;
|
||||
* (int32_t *) dp = (get_sign (*dp)) ? -value : value;
|
||||
}
|
||||
|
||||
wps->float_max_exp = max_exp;
|
||||
|
||||
if (shifted_both)
|
||||
wps->float_flags |= FLOAT_SHIFT_SENT;
|
||||
else if (shifted_ones && !shifted_zeros)
|
||||
wps->float_flags |= FLOAT_SHIFT_ONES;
|
||||
else if (shifted_ones && shifted_zeros)
|
||||
wps->float_flags |= FLOAT_SHIFT_SAME;
|
||||
else if (ordata && !(ordata & 1)) {
|
||||
while (!(ordata & 1)) {
|
||||
wps->float_shift++;
|
||||
ordata >>= 1;
|
||||
}
|
||||
|
||||
for (dp = values, count = num_values; count--; dp++)
|
||||
* (int32_t *) dp >>= wps->float_shift;
|
||||
}
|
||||
|
||||
wps->wphdr.flags &= ~MAG_MASK;
|
||||
|
||||
while (ordata) {
|
||||
wps->wphdr.flags += 1 << MAG_LSB;
|
||||
ordata >>= 1;
|
||||
}
|
||||
|
||||
if (false_zeros || neg_zeros)
|
||||
wps->float_flags |= FLOAT_ZEROS_SENT;
|
||||
|
||||
if (neg_zeros)
|
||||
wps->float_flags |= FLOAT_NEG_ZEROS;
|
||||
|
||||
// error_line ("samples = %d, max exp = %d, pre-shift = %d, denormals = %d",
|
||||
// num_values, max_exp, wps->float_shift, denormals);
|
||||
// if (wps->float_flags & FLOAT_EXCEPTIONS)
|
||||
// error_line ("exceptions!");
|
||||
// error_line ("shifted ones/zeros/both = %d/%d/%d, true/neg/false zeros = %d/%d/%d",
|
||||
// shifted_ones, shifted_zeros, shifted_both, true_zeros, neg_zeros, false_zeros);
|
||||
|
||||
return wps->float_flags & (FLOAT_EXCEPTIONS | FLOAT_ZEROS_SENT | FLOAT_SHIFT_SENT | FLOAT_SHIFT_SAME);
|
||||
}
|
||||
|
||||
void send_float_data (WavpackStream *wps, f32 *values, int32_t num_values)
|
||||
{
|
||||
int max_exp = wps->float_max_exp;
|
||||
int32_t count, value, shift_count;
|
||||
f32 *dp;
|
||||
|
||||
for (dp = values, count = num_values; count--; dp++) {
|
||||
if (get_exponent (*dp) == 255) {
|
||||
if (get_mantissa (*dp)) {
|
||||
putbit_1 (&wps->wvxbits);
|
||||
putbits (get_mantissa (*dp), 23, &wps->wvxbits);
|
||||
}
|
||||
else {
|
||||
putbit_0 (&wps->wvxbits);
|
||||
}
|
||||
|
||||
value = 0x1000000;
|
||||
shift_count = 0;
|
||||
}
|
||||
else if (get_exponent (*dp)) {
|
||||
shift_count = max_exp - get_exponent (*dp);
|
||||
value = 0x800000 + get_mantissa (*dp);
|
||||
}
|
||||
else {
|
||||
shift_count = max_exp ? max_exp - 1 : 0;
|
||||
value = get_mantissa (*dp);
|
||||
}
|
||||
|
||||
if (shift_count < 25)
|
||||
value >>= shift_count;
|
||||
else
|
||||
value = 0;
|
||||
|
||||
if (!value) {
|
||||
if (wps->float_flags & FLOAT_ZEROS_SENT) {
|
||||
if (get_exponent (*dp) || get_mantissa (*dp)) {
|
||||
putbit_1 (&wps->wvxbits);
|
||||
putbits (get_mantissa (*dp), 23, &wps->wvxbits);
|
||||
|
||||
if (max_exp >= 25) {
|
||||
putbits (get_exponent (*dp), 8, &wps->wvxbits);
|
||||
}
|
||||
|
||||
putbit (get_sign (*dp), &wps->wvxbits);
|
||||
}
|
||||
else {
|
||||
putbit_0 (&wps->wvxbits);
|
||||
|
||||
if (wps->float_flags & FLOAT_NEG_ZEROS)
|
||||
putbit (get_sign (*dp), &wps->wvxbits);
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (shift_count) {
|
||||
if (wps->float_flags & FLOAT_SHIFT_SENT) {
|
||||
int32_t data = get_mantissa (*dp) & ((1 << shift_count) - 1);
|
||||
putbits (data, shift_count, &wps->wvxbits);
|
||||
}
|
||||
else if (wps->float_flags & FLOAT_SHIFT_SAME) {
|
||||
putbit (get_mantissa (*dp) & 1, &wps->wvxbits);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#if !defined(NO_UNPACK) || defined(INFO_ONLY)
|
||||
|
||||
int read_float_info (WavpackStream *wps, WavpackMetadata *wpmd)
|
||||
{
|
||||
int bytecnt = wpmd->byte_length;
|
||||
char *byteptr = wpmd->data;
|
||||
|
||||
if (bytecnt != 4)
|
||||
return FALSE;
|
||||
|
||||
wps->float_flags = *byteptr++;
|
||||
wps->float_shift = *byteptr++;
|
||||
wps->float_max_exp = *byteptr++;
|
||||
wps->float_norm_exp = *byteptr;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef NO_UNPACK
|
||||
|
||||
static void float_values_nowvx (WavpackStream *wps, int32_t *values, int32_t num_values);
|
||||
|
||||
void float_values (WavpackStream *wps, int32_t *values, int32_t num_values)
|
||||
{
|
||||
uint32_t crc = wps->crc_x;
|
||||
|
||||
if (!bs_is_open (&wps->wvxbits)) {
|
||||
float_values_nowvx (wps, values, num_values);
|
||||
return;
|
||||
}
|
||||
|
||||
while (num_values--) {
|
||||
int shift_count = 0, exp = wps->float_max_exp;
|
||||
f32 outval = 0;
|
||||
uint32_t temp;
|
||||
|
||||
if (*values == 0) {
|
||||
if (wps->float_flags & FLOAT_ZEROS_SENT) {
|
||||
if (getbit (&wps->wvxbits)) {
|
||||
getbits (&temp, 23, &wps->wvxbits);
|
||||
set_mantissa (outval, temp);
|
||||
|
||||
if (exp >= 25) {
|
||||
getbits (&temp, 8, &wps->wvxbits);
|
||||
set_exponent (outval, temp);
|
||||
}
|
||||
|
||||
set_sign (outval, getbit (&wps->wvxbits));
|
||||
}
|
||||
else if (wps->float_flags & FLOAT_NEG_ZEROS)
|
||||
set_sign (outval, getbit (&wps->wvxbits));
|
||||
}
|
||||
}
|
||||
else {
|
||||
*values <<= wps->float_shift;
|
||||
|
||||
if (*values < 0) {
|
||||
*values = -*values;
|
||||
set_sign (outval, 1);
|
||||
}
|
||||
|
||||
if (*values == 0x1000000) {
|
||||
if (getbit (&wps->wvxbits)) {
|
||||
getbits (&temp, 23, &wps->wvxbits);
|
||||
set_mantissa (outval, temp);
|
||||
}
|
||||
|
||||
set_exponent (outval, 255);
|
||||
}
|
||||
else {
|
||||
if (exp)
|
||||
while (!(*values & 0x800000) && --exp) {
|
||||
shift_count++;
|
||||
*values <<= 1;
|
||||
}
|
||||
|
||||
if (shift_count) {
|
||||
if ((wps->float_flags & FLOAT_SHIFT_ONES) ||
|
||||
((wps->float_flags & FLOAT_SHIFT_SAME) && getbit (&wps->wvxbits)))
|
||||
*values |= ((1 << shift_count) - 1);
|
||||
else if (wps->float_flags & FLOAT_SHIFT_SENT) {
|
||||
getbits (&temp, shift_count, &wps->wvxbits);
|
||||
*values |= temp & ((1 << shift_count) - 1);
|
||||
}
|
||||
}
|
||||
|
||||
set_mantissa (outval, *values);
|
||||
set_exponent (outval, exp);
|
||||
}
|
||||
}
|
||||
|
||||
crc = crc * 27 + get_mantissa (outval) * 9 + get_exponent (outval) * 3 + get_sign (outval);
|
||||
* (f32 *) values++ = outval;
|
||||
}
|
||||
|
||||
wps->crc_x = crc;
|
||||
}
|
||||
|
||||
static void float_values_nowvx (WavpackStream *wps, int32_t *values, int32_t num_values)
|
||||
{
|
||||
while (num_values--) {
|
||||
int shift_count = 0, exp = wps->float_max_exp;
|
||||
f32 outval = 0;
|
||||
|
||||
if (*values) {
|
||||
*values <<= wps->float_shift;
|
||||
|
||||
if (*values < 0) {
|
||||
*values = -*values;
|
||||
set_sign (outval, 1);
|
||||
}
|
||||
|
||||
if (*values >= 0x1000000) {
|
||||
while (*values & 0xf000000) {
|
||||
*values >>= 1;
|
||||
++exp;
|
||||
}
|
||||
}
|
||||
else if (exp) {
|
||||
while (!(*values & 0x800000) && --exp) {
|
||||
shift_count++;
|
||||
*values <<= 1;
|
||||
}
|
||||
|
||||
if (shift_count && (wps->float_flags & FLOAT_SHIFT_ONES))
|
||||
*values |= ((1 << shift_count) - 1);
|
||||
}
|
||||
|
||||
set_mantissa (outval, *values);
|
||||
set_exponent (outval, exp);
|
||||
}
|
||||
|
||||
* (f32 *) values++ = outval;
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
void WavpackFloatNormalize (int32_t *values, int32_t num_values, int delta_exp)
|
||||
{
|
||||
f32 *fvalues = (f32 *) values;
|
||||
int exp;
|
||||
|
||||
if (!delta_exp)
|
||||
return;
|
||||
|
||||
while (num_values--) {
|
||||
if ((exp = get_exponent (*fvalues)) == 0 || exp + delta_exp <= 0)
|
||||
*fvalues = 0;
|
||||
else if (exp == 255 || (exp += delta_exp) >= 255) {
|
||||
set_exponent (*fvalues, 255);
|
||||
set_mantissa (*fvalues, 0);
|
||||
}
|
||||
else
|
||||
set_exponent (*fvalues, exp);
|
||||
|
||||
fvalues++;
|
||||
}
|
||||
}
|
||||
@@ -1,26 +0,0 @@
|
||||
|
||||
Microsoft Visual Studio Solution File, Format Version 9.00
|
||||
# Visual Studio 2005
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libwavpack", "libwavpack.vcproj", "{5CCCB9CF-0384-458F-BA08-72B73866840F}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Win32 = Debug|Win32
|
||||
Debug|x64 = Debug|x64
|
||||
Release|Win32 = Release|Win32
|
||||
Release|x64 = Release|x64
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Win32.ActiveCfg = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|Win32.Build.0 = Debug|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Debug|x64.Build.0 = Debug|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Win32.ActiveCfg = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|Win32.Build.0 = Release|Win32
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|x64.ActiveCfg = Release|x64
|
||||
{5CCCB9CF-0384-458F-BA08-72B73866840F}.Release|x64.Build.0 = Release|x64
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
@@ -1,364 +0,0 @@
|
||||
<?xml version="1.0" encoding="Windows-1252"?>
|
||||
<VisualStudioProject
|
||||
ProjectType="Visual C++"
|
||||
Version="9,00"
|
||||
Name="libwavpack"
|
||||
ProjectGUID="{5CCCB9CF-0384-458F-BA08-72B73866840F}"
|
||||
RootNamespace="libwavpack"
|
||||
Keyword="Win32Proj"
|
||||
TargetFrameworkVersion="131072"
|
||||
>
|
||||
<Platforms>
|
||||
<Platform
|
||||
Name="Win32"
|
||||
/>
|
||||
<Platform
|
||||
Name="x64"
|
||||
/>
|
||||
</Platforms>
|
||||
<ToolFiles>
|
||||
</ToolFiles>
|
||||
<Configurations>
|
||||
<Configuration
|
||||
Name="Debug|Win32"
|
||||
OutputDirectory="$(SolutionDir)..\bin\$(PlatformName)\$(ConfigurationName)"
|
||||
IntermediateDirectory="$(SolutionDir)..\obj\$(ProjectName)\$(PlatformName)\$(ConfigurationName)"
|
||||
ConfigurationType="4"
|
||||
>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="0"
|
||||
PreprocessorDefinitions="WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_DEPRECATE;OPT_MMX;NO_USE_FSTREAMS;NO_TAGS"
|
||||
MinimalRebuild="true"
|
||||
BasicRuntimeChecks="3"
|
||||
RuntimeLibrary="3"
|
||||
UsePrecompiledHeader="0"
|
||||
WarningLevel="3"
|
||||
Detect64BitPortabilityProblems="true"
|
||||
DebugInformationFormat="4"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCManagedResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCLibrarianTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCALinkTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXDCMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCBscMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCFxCopTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"
|
||||
/>
|
||||
</Configuration>
|
||||
<Configuration
|
||||
Name="Debug|x64"
|
||||
OutputDirectory="$(SolutionDir)..\bin\$(PlatformName)\$(ConfigurationName)"
|
||||
IntermediateDirectory="$(SolutionDir)..\obj\$(ProjectName)\$(PlatformName)\$(ConfigurationName)"
|
||||
ConfigurationType="4"
|
||||
>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"
|
||||
TargetEnvironment="3"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="0"
|
||||
PreprocessorDefinitions="WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_DEPRECATE;OPT_SSE2;NO_USE_FSTREAMS;NO_TAGS"
|
||||
MinimalRebuild="true"
|
||||
BasicRuntimeChecks="3"
|
||||
RuntimeLibrary="3"
|
||||
UsePrecompiledHeader="0"
|
||||
WarningLevel="3"
|
||||
Detect64BitPortabilityProblems="true"
|
||||
DebugInformationFormat="3"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCManagedResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCLibrarianTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCALinkTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXDCMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCBscMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCFxCopTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"
|
||||
/>
|
||||
</Configuration>
|
||||
<Configuration
|
||||
Name="Release|Win32"
|
||||
OutputDirectory="$(SolutionDir)..\bin\$(PlatformName)\$(ConfigurationName)"
|
||||
IntermediateDirectory="$(SolutionDir)..\obj\$(ProjectName)\$(PlatformName)\$(ConfigurationName)"
|
||||
ConfigurationType="4"
|
||||
>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
InlineFunctionExpansion="2"
|
||||
EnableIntrinsicFunctions="true"
|
||||
FavorSizeOrSpeed="1"
|
||||
OmitFramePointers="true"
|
||||
PreprocessorDefinitions="WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_DEPRECATE;OPT_MMX;NO_USE_FSTREAMS;NO_TAGS"
|
||||
StringPooling="true"
|
||||
ExceptionHandling="0"
|
||||
RuntimeLibrary="2"
|
||||
BufferSecurityCheck="false"
|
||||
EnableFunctionLevelLinking="true"
|
||||
DisableLanguageExtensions="false"
|
||||
RuntimeTypeInfo="false"
|
||||
UsePrecompiledHeader="0"
|
||||
WarningLevel="3"
|
||||
Detect64BitPortabilityProblems="true"
|
||||
DebugInformationFormat="0"
|
||||
CompileAs="0"
|
||||
OmitDefaultLibName="true"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCManagedResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCLibrarianTool"
|
||||
IgnoreAllDefaultLibraries="true"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCALinkTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXDCMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCBscMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCFxCopTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"
|
||||
/>
|
||||
</Configuration>
|
||||
<Configuration
|
||||
Name="Release|x64"
|
||||
OutputDirectory="$(SolutionDir)..\bin\$(PlatformName)\$(ConfigurationName)"
|
||||
IntermediateDirectory="$(SolutionDir)..\obj\$(ProjectName)\$(PlatformName)\$(ConfigurationName)"
|
||||
ConfigurationType="4"
|
||||
>
|
||||
<Tool
|
||||
Name="VCPreBuildEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCustomBuildTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXMLDataGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCWebServiceProxyGeneratorTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCMIDLTool"
|
||||
TargetEnvironment="3"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCCLCompilerTool"
|
||||
Optimization="3"
|
||||
InlineFunctionExpansion="2"
|
||||
EnableIntrinsicFunctions="true"
|
||||
FavorSizeOrSpeed="1"
|
||||
OmitFramePointers="true"
|
||||
WholeProgramOptimization="true"
|
||||
PreprocessorDefinitions="WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_DEPRECATE;OPT_SSE2;NO_USE_FSTREAMS;NO_TAGS"
|
||||
StringPooling="true"
|
||||
ExceptionHandling="0"
|
||||
RuntimeLibrary="2"
|
||||
BufferSecurityCheck="false"
|
||||
EnableEnhancedInstructionSet="1"
|
||||
FloatingPointModel="2"
|
||||
DisableLanguageExtensions="false"
|
||||
RuntimeTypeInfo="false"
|
||||
UsePrecompiledHeader="0"
|
||||
WarningLevel="3"
|
||||
Detect64BitPortabilityProblems="true"
|
||||
DebugInformationFormat="0"
|
||||
CompileAs="0"
|
||||
OmitDefaultLibName="true"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCManagedResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCResourceCompilerTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPreLinkEventTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCLibrarianTool"
|
||||
IgnoreAllDefaultLibraries="true"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCALinkTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCXDCMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCBscMakeTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCFxCopTool"
|
||||
/>
|
||||
<Tool
|
||||
Name="VCPostBuildEventTool"
|
||||
/>
|
||||
</Configuration>
|
||||
</Configurations>
|
||||
<References>
|
||||
</References>
|
||||
<Files>
|
||||
<Filter
|
||||
Name="Header Files"
|
||||
Filter="h;hpp;hxx;hm;inl;inc;xsd"
|
||||
UniqueIdentifier="{93995380-89BD-4b04-88EB-625FBE52EBFB}"
|
||||
>
|
||||
<File
|
||||
RelativePath=".\unpack3.h"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\wavpack_local.h"
|
||||
>
|
||||
</File>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="Resource Files"
|
||||
Filter="rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx"
|
||||
UniqueIdentifier="{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}"
|
||||
>
|
||||
</Filter>
|
||||
<Filter
|
||||
Name="Source Files"
|
||||
Filter="cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx"
|
||||
UniqueIdentifier="{4FC737F1-C7A5-4376-A066-2A32D752A2FF}"
|
||||
>
|
||||
<File
|
||||
RelativePath=".\bits.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\extra1.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\extra2.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\float.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\metadata.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\pack.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\unpack.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\unpack3.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\words.c"
|
||||
>
|
||||
</File>
|
||||
<File
|
||||
RelativePath=".\wputils.c"
|
||||
>
|
||||
</File>
|
||||
</Filter>
|
||||
</Files>
|
||||
<Globals>
|
||||
</Globals>
|
||||
</VisualStudioProject>
|
||||
@@ -1,192 +0,0 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Debug|Win32">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Debug|x64">
|
||||
<Configuration>Debug</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|x64">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<ProjectGuid>{5CCCB9CF-0384-458F-BA08-72B73866840F}</ProjectGuid>
|
||||
<TargetFrameworkVersion>v2.0</TargetFrameworkVersion>
|
||||
<RootNamespace>libwavpack</RootNamespace>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<WindowsTargetPlatformVersion>10.0.16299.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
|
||||
<ConfigurationType>StaticLibrary</ConfigurationType>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
|
||||
<ConfigurationType>StaticLibrary</ConfigurationType>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
|
||||
<ConfigurationType>StaticLibrary</ConfigurationType>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
|
||||
<ConfigurationType>StaticLibrary</ConfigurationType>
|
||||
<PlatformToolset>v141</PlatformToolset>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup>
|
||||
<_ProjectFileVersion>10.0.40219.1</_ProjectFileVersion>
|
||||
<OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(SolutionDir)..\bin\$(Platform)\$(Configuration)\</OutDir>
|
||||
<IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">$(SolutionDir)..\obj\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
|
||||
<OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">$(SolutionDir)..\bin\$(Platform)\$(Configuration)\</OutDir>
|
||||
<IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">$(SolutionDir)..\obj\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
|
||||
<OutDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(SolutionDir)..\bin\$(Platform)\$(Configuration)\</OutDir>
|
||||
<IntDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">$(SolutionDir)..\obj\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
|
||||
<OutDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">$(SolutionDir)..\bin\$(Platform)\$(Configuration)\</OutDir>
|
||||
<IntDir Condition="'$(Configuration)|$(Platform)'=='Release|x64'">$(SolutionDir)..\obj\$(ProjectName)\$(Platform)\$(Configuration)\</IntDir>
|
||||
<CodeAnalysisRuleSet Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">AllRules.ruleset</CodeAnalysisRuleSet>
|
||||
<CodeAnalysisRules Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" />
|
||||
<CodeAnalysisRuleAssemblies Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" />
|
||||
<CodeAnalysisRuleSet Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">AllRules.ruleset</CodeAnalysisRuleSet>
|
||||
<CodeAnalysisRules Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" />
|
||||
<CodeAnalysisRuleAssemblies Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" />
|
||||
<CodeAnalysisRuleSet Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">AllRules.ruleset</CodeAnalysisRuleSet>
|
||||
<CodeAnalysisRules Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" />
|
||||
<CodeAnalysisRuleAssemblies Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" />
|
||||
<CodeAnalysisRuleSet Condition="'$(Configuration)|$(Platform)'=='Release|x64'">AllRules.ruleset</CodeAnalysisRuleSet>
|
||||
<CodeAnalysisRules Condition="'$(Configuration)|$(Platform)'=='Release|x64'" />
|
||||
<CodeAnalysisRuleAssemblies Condition="'$(Configuration)|$(Platform)'=='Release|x64'" />
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
|
||||
<ClCompile>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_DEPRECATE;OPT_MMX;NO_USE_FSTREAMS;NO_TAGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<MinimalRebuild>true</MinimalRebuild>
|
||||
<BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
|
||||
<RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<DebugInformationFormat>EditAndContinue</DebugInformationFormat>
|
||||
</ClCompile>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
|
||||
<Midl>
|
||||
<TargetEnvironment>X64</TargetEnvironment>
|
||||
</Midl>
|
||||
<ClCompile>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;_LIB;_CRT_SECURE_NO_DEPRECATE;OPT_SSE2;NO_USE_FSTREAMS;NO_TAGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<MinimalRebuild>true</MinimalRebuild>
|
||||
<BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>
|
||||
<RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
</ClCompile>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile>
|
||||
<InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<FavorSizeOrSpeed>Speed</FavorSizeOrSpeed>
|
||||
<OmitFramePointers>true</OmitFramePointers>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_DEPRECATE;OPT_MMX;NO_USE_FSTREAMS;NO_TAGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<StringPooling>true</StringPooling>
|
||||
<ExceptionHandling>
|
||||
</ExceptionHandling>
|
||||
<RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
|
||||
<BufferSecurityCheck>false</BufferSecurityCheck>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<DisableLanguageExtensions>false</DisableLanguageExtensions>
|
||||
<RuntimeTypeInfo>false</RuntimeTypeInfo>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<DebugInformationFormat>
|
||||
</DebugInformationFormat>
|
||||
<CompileAs>Default</CompileAs>
|
||||
<OmitDefaultLibName>true</OmitDefaultLibName>
|
||||
</ClCompile>
|
||||
<Lib>
|
||||
<IgnoreAllDefaultLibraries>true</IgnoreAllDefaultLibraries>
|
||||
</Lib>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
||||
<Midl>
|
||||
<TargetEnvironment>X64</TargetEnvironment>
|
||||
</Midl>
|
||||
<ClCompile>
|
||||
<Optimization>Full</Optimization>
|
||||
<InlineFunctionExpansion>AnySuitable</InlineFunctionExpansion>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<FavorSizeOrSpeed>Speed</FavorSizeOrSpeed>
|
||||
<OmitFramePointers>true</OmitFramePointers>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;_LIB;_CRT_SECURE_NO_DEPRECATE;OPT_SSE2;NO_USE_FSTREAMS;NO_TAGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<StringPooling>true</StringPooling>
|
||||
<ExceptionHandling>
|
||||
</ExceptionHandling>
|
||||
<RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>
|
||||
<BufferSecurityCheck>false</BufferSecurityCheck>
|
||||
<EnableEnhancedInstructionSet>StreamingSIMDExtensions</EnableEnhancedInstructionSet>
|
||||
<FloatingPointModel>Fast</FloatingPointModel>
|
||||
<DisableLanguageExtensions>false</DisableLanguageExtensions>
|
||||
<RuntimeTypeInfo>false</RuntimeTypeInfo>
|
||||
<PrecompiledHeader>
|
||||
</PrecompiledHeader>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<DebugInformationFormat>
|
||||
</DebugInformationFormat>
|
||||
<CompileAs>Default</CompileAs>
|
||||
<OmitDefaultLibName>true</OmitDefaultLibName>
|
||||
</ClCompile>
|
||||
<Lib>
|
||||
<IgnoreAllDefaultLibraries>true</IgnoreAllDefaultLibraries>
|
||||
</Lib>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="unpack3.h" />
|
||||
<ClInclude Include="wavpack_local.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="bits.c" />
|
||||
<ClCompile Include="extra1.c" />
|
||||
<ClCompile Include="extra2.c" />
|
||||
<ClCompile Include="float.c" />
|
||||
<ClCompile Include="metadata.c" />
|
||||
<ClCompile Include="pack.c" />
|
||||
<ClCompile Include="unpack.c" />
|
||||
<ClCompile Include="unpack3.c" />
|
||||
<ClCompile Include="words.c" />
|
||||
<ClCompile Include="wputils.c" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
||||
@@ -1,313 +0,0 @@
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
// **** WAVPACK **** //
|
||||
// Hybrid Lossless Wavefile Compressor //
|
||||
// Copyright (c) 1998 - 2006 Conifer Software. //
|
||||
// All Rights Reserved. //
|
||||
// Distributed under the BSD Software License (see license.txt) //
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// metadata.c
|
||||
|
||||
// This module handles the metadata structure introduced in WavPack 4.0
|
||||
|
||||
#include "wavpack_local.h"
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
#ifdef DEBUG_ALLOC
|
||||
#define malloc malloc_db
|
||||
#define realloc realloc_db
|
||||
#define free free_db
|
||||
void *malloc_db (uint32_t size);
|
||||
void *realloc_db (void *ptr, uint32_t size);
|
||||
void free_db (void *ptr);
|
||||
int32_t dump_alloc (void);
|
||||
#endif
|
||||
|
||||
#if !defined(NO_UNPACK) || defined(INFO_ONLY)
|
||||
|
||||
int read_metadata_buff (WavpackMetadata *wpmd, uchar *blockbuff, uchar **buffptr)
|
||||
{
|
||||
WavpackHeader *wphdr = (WavpackHeader *) blockbuff;
|
||||
uchar *buffend = blockbuff + wphdr->ckSize + 8;
|
||||
|
||||
if (buffend - *buffptr < 2)
|
||||
return FALSE;
|
||||
|
||||
wpmd->id = *(*buffptr)++;
|
||||
wpmd->byte_length = *(*buffptr)++ << 1;
|
||||
|
||||
if (wpmd->id & ID_LARGE) {
|
||||
wpmd->id &= ~ID_LARGE;
|
||||
|
||||
if (buffend - *buffptr < 2)
|
||||
return FALSE;
|
||||
|
||||
wpmd->byte_length += *(*buffptr)++ << 9;
|
||||
wpmd->byte_length += *(*buffptr)++ << 17;
|
||||
}
|
||||
|
||||
if (wpmd->id & ID_ODD_SIZE) {
|
||||
wpmd->id &= ~ID_ODD_SIZE;
|
||||
wpmd->byte_length--;
|
||||
}
|
||||
|
||||
if (wpmd->byte_length) {
|
||||
if (buffend - *buffptr < wpmd->byte_length + (wpmd->byte_length & 1)) {
|
||||
wpmd->data = NULL;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
wpmd->data = *buffptr;
|
||||
(*buffptr) += wpmd->byte_length + (wpmd->byte_length & 1);
|
||||
}
|
||||
else
|
||||
wpmd->data = NULL;
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
int process_metadata (WavpackContext *wpc, WavpackMetadata *wpmd)
|
||||
{
|
||||
WavpackStream *wps = wpc->streams [wpc->current_stream];
|
||||
|
||||
switch (wpmd->id) {
|
||||
case ID_DUMMY:
|
||||
return TRUE;
|
||||
|
||||
case ID_DECORR_TERMS:
|
||||
return read_decorr_terms (wps, wpmd);
|
||||
|
||||
case ID_DECORR_WEIGHTS:
|
||||
return read_decorr_weights (wps, wpmd);
|
||||
|
||||
case ID_DECORR_SAMPLES:
|
||||
return read_decorr_samples (wps, wpmd);
|
||||
|
||||
case ID_ENTROPY_VARS:
|
||||
return read_entropy_vars (wps, wpmd);
|
||||
|
||||
case ID_HYBRID_PROFILE:
|
||||
return read_hybrid_profile (wps, wpmd);
|
||||
|
||||
case ID_SHAPING_WEIGHTS:
|
||||
return read_shaping_info (wps, wpmd);
|
||||
|
||||
case ID_FLOAT_INFO:
|
||||
return read_float_info (wps, wpmd);
|
||||
|
||||
case ID_INT32_INFO:
|
||||
return read_int32_info (wps, wpmd);
|
||||
|
||||
case ID_CHANNEL_INFO:
|
||||
return read_channel_info (wpc, wpmd);
|
||||
|
||||
case ID_CONFIG_BLOCK:
|
||||
return read_config_info (wpc, wpmd);
|
||||
|
||||
case ID_SAMPLE_RATE:
|
||||
return read_sample_rate (wpc, wpmd);
|
||||
|
||||
case ID_WV_BITSTREAM:
|
||||
return init_wv_bitstream (wps, wpmd);
|
||||
|
||||
case ID_WVC_BITSTREAM:
|
||||
return init_wvc_bitstream (wps, wpmd);
|
||||
|
||||
case ID_WVX_BITSTREAM:
|
||||
return init_wvx_bitstream (wps, wpmd);
|
||||
|
||||
case ID_RIFF_HEADER: case ID_RIFF_TRAILER:
|
||||
return read_wrapper_data (wpc, wpmd);
|
||||
|
||||
case ID_MD5_CHECKSUM:
|
||||
if (wpmd->byte_length == 16) {
|
||||
memcpy (wpc->config.md5_checksum, wpmd->data, 16);
|
||||
wpc->config.flags |= CONFIG_MD5_CHECKSUM;
|
||||
wpc->config.md5_read = 1;
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
|
||||
default:
|
||||
return (wpmd->id & ID_OPTIONAL_DATA) ? TRUE : FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
#ifndef NO_PACK
|
||||
|
||||
int copy_metadata (WavpackMetadata *wpmd, uchar *buffer_start, uchar *buffer_end)
|
||||
{
|
||||
uint32_t mdsize = wpmd->byte_length + (wpmd->byte_length & 1);
|
||||
WavpackHeader *wphdr = (WavpackHeader *) buffer_start;
|
||||
|
||||
if (wpmd->byte_length & 1)
|
||||
((char *) wpmd->data) [wpmd->byte_length] = 0;
|
||||
|
||||
mdsize += (wpmd->byte_length > 510) ? 4 : 2;
|
||||
buffer_start += wphdr->ckSize + 8;
|
||||
|
||||
if (buffer_start + mdsize >= buffer_end)
|
||||
return FALSE;
|
||||
|
||||
buffer_start [0] = wpmd->id | (wpmd->byte_length & 1 ? ID_ODD_SIZE : 0);
|
||||
buffer_start [1] = (wpmd->byte_length + 1) >> 1;
|
||||
|
||||
if (wpmd->byte_length > 510) {
|
||||
buffer_start [0] |= ID_LARGE;
|
||||
buffer_start [2] = (wpmd->byte_length + 1) >> 9;
|
||||
buffer_start [3] = (wpmd->byte_length + 1) >> 17;
|
||||
}
|
||||
|
||||
if (wpmd->data && wpmd->byte_length) {
|
||||
if (wpmd->byte_length > 510) {
|
||||
buffer_start [0] |= ID_LARGE;
|
||||
buffer_start [2] = (wpmd->byte_length + 1) >> 9;
|
||||
buffer_start [3] = (wpmd->byte_length + 1) >> 17;
|
||||
memcpy (buffer_start + 4, wpmd->data, mdsize - 4);
|
||||
}
|
||||
else
|
||||
memcpy (buffer_start + 2, wpmd->data, mdsize - 2);
|
||||
}
|
||||
|
||||
wphdr->ckSize += mdsize;
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
int add_to_metadata (WavpackContext *wpc, void *data, uint32_t bcount, uchar id)
|
||||
{
|
||||
WavpackMetadata *mdp;
|
||||
uchar *src = data;
|
||||
|
||||
while (bcount) {
|
||||
if (wpc->metacount) {
|
||||
uint32_t bc = bcount;
|
||||
|
||||
mdp = wpc->metadata + wpc->metacount - 1;
|
||||
|
||||
if (mdp->id == id) {
|
||||
if (wpc->metabytes + bcount > 1000000)
|
||||
bc = 1000000 - wpc->metabytes;
|
||||
|
||||
mdp->data = realloc (mdp->data, mdp->byte_length + bc);
|
||||
memcpy ((char *) mdp->data + mdp->byte_length, src, bc);
|
||||
mdp->byte_length += bc;
|
||||
wpc->metabytes += bc;
|
||||
bcount -= bc;
|
||||
src += bc;
|
||||
|
||||
if (wpc->metabytes >= 1000000 && !write_metadata_block (wpc))
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
if (bcount) {
|
||||
wpc->metadata = realloc (wpc->metadata, (wpc->metacount + 1) * sizeof (WavpackMetadata));
|
||||
mdp = wpc->metadata + wpc->metacount++;
|
||||
mdp->byte_length = 0;
|
||||
mdp->data = NULL;
|
||||
mdp->id = id;
|
||||
}
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
static char *write_metadata (WavpackMetadata *wpmd, char *outdata)
|
||||
{
|
||||
uchar id = wpmd->id, wordlen [3];
|
||||
|
||||
wordlen [0] = (wpmd->byte_length + 1) >> 1;
|
||||
wordlen [1] = (wpmd->byte_length + 1) >> 9;
|
||||
wordlen [2] = (wpmd->byte_length + 1) >> 17;
|
||||
|
||||
if (wpmd->byte_length & 1) {
|
||||
// ((char *) wpmd->data) [wpmd->byte_length] = 0;
|
||||
id |= ID_ODD_SIZE;
|
||||
}
|
||||
|
||||
if (wordlen [1] || wordlen [2])
|
||||
id |= ID_LARGE;
|
||||
|
||||
*outdata++ = id;
|
||||
*outdata++ = wordlen [0];
|
||||
|
||||
if (id & ID_LARGE) {
|
||||
*outdata++ = wordlen [1];
|
||||
*outdata++ = wordlen [2];
|
||||
}
|
||||
|
||||
if (wpmd->data && wpmd->byte_length) {
|
||||
memcpy (outdata, wpmd->data, wpmd->byte_length);
|
||||
outdata += wpmd->byte_length;
|
||||
|
||||
if (wpmd->byte_length & 1)
|
||||
*outdata++ = 0;
|
||||
}
|
||||
|
||||
return outdata;
|
||||
}
|
||||
|
||||
int write_metadata_block (WavpackContext *wpc)
|
||||
{
|
||||
char *block_buff, *block_ptr;
|
||||
WavpackHeader *wphdr;
|
||||
|
||||
if (wpc->metacount) {
|
||||
int metacount = wpc->metacount, block_size = sizeof (WavpackHeader);
|
||||
WavpackMetadata *wpmdp = wpc->metadata;
|
||||
|
||||
while (metacount--) {
|
||||
block_size += wpmdp->byte_length + (wpmdp->byte_length & 1);
|
||||
block_size += (wpmdp->byte_length > 510) ? 4 : 2;
|
||||
wpmdp++;
|
||||
}
|
||||
|
||||
wphdr = (WavpackHeader *) (block_buff = malloc (block_size));
|
||||
|
||||
CLEAR (*wphdr);
|
||||
memcpy (wphdr->ckID, "wvpk", 4);
|
||||
wphdr->total_samples = wpc->total_samples;
|
||||
wphdr->version = wpc->stream_version;
|
||||
wphdr->ckSize = block_size - 8;
|
||||
wphdr->block_samples = 0;
|
||||
|
||||
block_ptr = (char *)(wphdr + 1);
|
||||
|
||||
wpmdp = wpc->metadata;
|
||||
|
||||
while (wpc->metacount) {
|
||||
block_ptr = write_metadata (wpmdp, block_ptr);
|
||||
wpc->metabytes -= wpmdp->byte_length;
|
||||
free_metadata (wpmdp++);
|
||||
wpc->metacount--;
|
||||
}
|
||||
|
||||
free (wpc->metadata);
|
||||
wpc->metadata = NULL;
|
||||
native_to_little_endian ((WavpackHeader *) block_buff, WavpackHeaderFormat);
|
||||
|
||||
if (!wpc->blockout (wpc->wv_out, block_buff, block_size)) {
|
||||
free (block_buff);
|
||||
strcpy (wpc->error_message, "can't write WavPack data, disk probably full!");
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
free (block_buff);
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
void free_metadata (WavpackMetadata *wpmd)
|
||||
{
|
||||
if (wpmd->data) {
|
||||
free (wpmd->data);
|
||||
wpmd->data = NULL;
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -1,113 +0,0 @@
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
// **** WAVPACK **** //
|
||||
// Hybrid Lossless Wavefile Compressor //
|
||||
// Copyright (c) 1998 - 2006 Conifer Software. //
|
||||
// All Rights Reserved. //
|
||||
// Distributed under the BSD Software License (see license.txt) //
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// wavpack3.h
|
||||
|
||||
// This header file contains all the additional definitions required for
|
||||
// decoding old (versions 1, 2 & 3) WavPack files.
|
||||
|
||||
typedef struct {
|
||||
ushort FormatTag, NumChannels;
|
||||
uint32_t SampleRate, BytesPerSecond;
|
||||
ushort BlockAlign, BitsPerSample;
|
||||
} WaveHeader3;
|
||||
|
||||
#define WaveHeader3Format "SSLLSS"
|
||||
|
||||
typedef struct {
|
||||
char ckID [4];
|
||||
int32_t ckSize;
|
||||
short version;
|
||||
short bits; // added for version 2.00
|
||||
short flags, shift; // added for version 3.00
|
||||
int32_t total_samples, crc, crc2;
|
||||
char extension [4], extra_bc, extras [3];
|
||||
} WavpackHeader3;
|
||||
|
||||
#define WavpackHeader3Format "4LSSSSLLL4L"
|
||||
|
||||
// these flags added for version 3
|
||||
|
||||
#undef MONO_FLAG // these definitions changed for WavPack 4.0
|
||||
#undef CROSS_DECORR
|
||||
#undef JOINT_STEREO
|
||||
|
||||
#define MONO_FLAG 1 // not stereo
|
||||
#define FAST_FLAG 2 // non-adaptive predictor and stereo mode
|
||||
#define RAW_FLAG 4 // raw mode (no .wav header)
|
||||
#define CALC_NOISE 8 // calc noise in lossy mode (no longer stored)
|
||||
#define HIGH_FLAG 0x10 // high quality mode (all modes)
|
||||
#define BYTES_3 0x20 // files have 3-byte samples
|
||||
#define OVER_20 0x40 // samples are over 20 bits
|
||||
#define WVC_FLAG 0x80 // create/use .wvc (no longer stored)
|
||||
#define LOSSY_SHAPE 0x100 // noise shape (lossy mode only)
|
||||
#define VERY_FAST_FLAG 0x200 // double fast (no longer stored)
|
||||
#define NEW_HIGH_FLAG 0x400 // new high quality mode (lossless only)
|
||||
#define CANCEL_EXTREME 0x800 // cancel EXTREME_DECORR
|
||||
#define CROSS_DECORR 0x1000 // decorrelate chans (with EXTREME_DECORR flag)
|
||||
#define NEW_DECORR_FLAG 0x2000 // new high-mode decorrelator
|
||||
#define JOINT_STEREO 0x4000 // joint stereo (lossy and high lossless)
|
||||
#define EXTREME_DECORR 0x8000 // extra decorrelation (+ enables other flags)
|
||||
|
||||
#define STORED_FLAGS 0xfd77 // these are only flags that affect unpacking
|
||||
#define NOT_STORED_FLAGS (~STORED_FLAGS & 0xffff)
|
||||
|
||||
// BitStream stuff (bits.c)
|
||||
|
||||
typedef struct bs3 {
|
||||
void (*wrap)(struct bs3 *bs);
|
||||
uchar *buf, *end, *ptr;
|
||||
uint32_t bufsiz, fpos, sr;
|
||||
WavpackStreamReader *reader;
|
||||
int error, bc;
|
||||
void *id;
|
||||
} Bitstream3;
|
||||
|
||||
#define K_DEPTH 3
|
||||
#define MAX_NTERMS3 18
|
||||
|
||||
typedef struct {
|
||||
WavpackHeader3 wphdr;
|
||||
Bitstream3 wvbits, wvcbits;
|
||||
uint32_t sample_index;
|
||||
int num_terms;
|
||||
|
||||
#ifndef NO_SEEKING
|
||||
struct index_point {
|
||||
char saved;
|
||||
uint32_t sample_index;
|
||||
} index_points [256];
|
||||
|
||||
uchar *unpack_data;
|
||||
uint32_t unpack_size;
|
||||
#endif
|
||||
|
||||
struct {
|
||||
int32_t sum_level, left_level, right_level, diff_level;
|
||||
int last_extra_bits, extra_bits_count, m;
|
||||
int32_t error [2], crc;
|
||||
int32_t sample [2] [2];
|
||||
int weight [2] [1];
|
||||
} dc;
|
||||
|
||||
struct decorr_pass decorr_passes [MAX_NTERMS3];
|
||||
|
||||
struct {
|
||||
uint index [2], k_value [2], ave_k [2];
|
||||
uint32_t zeros_acc, ave_level [K_DEPTH] [2];
|
||||
} w1;
|
||||
|
||||
struct { int last_dbits [2], last_delta_sign [2], bit_limit; } w2;
|
||||
|
||||
struct { int ave_dbits [2], bit_limit; } w3;
|
||||
|
||||
struct {
|
||||
uint32_t fast_level [2], slow_level [2];
|
||||
int bits_acc [2], bitrate;
|
||||
} w4;
|
||||
} WavpackStream3;
|
||||
@@ -1,764 +0,0 @@
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
// **** WAVPACK **** //
|
||||
// Hybrid Lossless Wavefile Compressor //
|
||||
// Copyright (c) 1998 - 2006 Conifer Software. //
|
||||
// All Rights Reserved. //
|
||||
// Distributed under the BSD Software License (see license.txt) //
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// wavpack_local.h
|
||||
|
||||
#ifndef WAVPACK_LOCAL_H
|
||||
#define WAVPACK_LOCAL_H
|
||||
|
||||
#if defined(WIN32)
|
||||
#define FASTCALL __fastcall
|
||||
#else
|
||||
#define FASTCALL
|
||||
#endif
|
||||
|
||||
#if defined(WIN32) || \
|
||||
(defined(BYTE_ORDER) && defined(LITTLE_ENDIAN) && (BYTE_ORDER == LITTLE_ENDIAN))
|
||||
#define BITSTREAM_SHORTS // use "shorts" for reading/writing bitstreams
|
||||
// (only works on little-endian machines)
|
||||
#endif
|
||||
|
||||
#include <sys/types.h>
|
||||
|
||||
// This header file contains all the definitions required by WavPack.
|
||||
|
||||
#if defined(_WIN32) && !defined(__MINGW32__)
|
||||
#include <stdlib.h>
|
||||
typedef unsigned __int64 uint64_t;
|
||||
typedef unsigned __int32 uint32_t;
|
||||
typedef unsigned __int16 uint16_t;
|
||||
typedef unsigned __int8 uint8_t;
|
||||
typedef __int64 int64_t;
|
||||
typedef __int32 int32_t;
|
||||
typedef __int16 int16_t;
|
||||
typedef __int8 int8_t;
|
||||
typedef float float32_t;
|
||||
#else
|
||||
#include <inttypes.h>
|
||||
#endif
|
||||
|
||||
typedef unsigned char uchar;
|
||||
|
||||
#if !defined(__GNUC__) || defined(WIN32)
|
||||
typedef unsigned short ushort;
|
||||
typedef unsigned int uint;
|
||||
#endif
|
||||
|
||||
// Because the C99 specification states that "The order of allocation of
|
||||
// bit-fields within a unit (high-order to low-order or low-order to
|
||||
// high-order) is implementation-defined" (6.7.2.1), I decided to change
|
||||
// the representation of floating-point values from a structure of
|
||||
// bit-fields to a 32-bit integer with access macros. Note that the WavPack
|
||||
// library doesn't use any floating-point math to implement compression of
|
||||
// floating-point data (although a little floating-point math is used in
|
||||
// high-level functions unrelated to the codec).
|
||||
|
||||
typedef int32_t f32;
|
||||
|
||||
#define get_mantissa(f) ((f) & 0x7fffff)
|
||||
#define get_exponent(f) (((f) >> 23) & 0xff)
|
||||
#define get_sign(f) (((f) >> 31) & 0x1)
|
||||
|
||||
#define set_mantissa(f,v) (f) ^= (((f) ^ (v)) & 0x7fffff)
|
||||
#define set_exponent(f,v) (f) ^= (((f) ^ ((v) << 23)) & 0x7f800000)
|
||||
#define set_sign(f,v) (f) ^= (((f) ^ ((v) << 31)) & 0x80000000)
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#define FALSE 0
|
||||
#define TRUE 1
|
||||
|
||||
// ID3v1 and APEv2 TAG formats (may occur at the end of WavPack files)
|
||||
|
||||
typedef struct {
|
||||
char tag_id [3], title [30], artist [30], album [30];
|
||||
char year [4], comment [30], genre;
|
||||
} ID3_Tag;
|
||||
|
||||
typedef struct {
|
||||
char ID [8];
|
||||
int32_t version, length, item_count, flags;
|
||||
char res [8];
|
||||
} APE_Tag_Hdr;
|
||||
|
||||
#define APE_Tag_Hdr_Format "8LLLL"
|
||||
|
||||
typedef struct {
|
||||
int32_t tag_file_pos;
|
||||
ID3_Tag id3_tag;
|
||||
APE_Tag_Hdr ape_tag_hdr;
|
||||
char *ape_tag_data;
|
||||
} M_Tag;
|
||||
|
||||
// RIFF / wav header formats (these occur at the beginning of both wav files
|
||||
// and pre-4.0 WavPack files that are not in the "raw" mode)
|
||||
|
||||
typedef struct {
|
||||
char ckID [4];
|
||||
uint32_t ckSize;
|
||||
char formType [4];
|
||||
} RiffChunkHeader;
|
||||
|
||||
typedef struct {
|
||||
char ckID [4];
|
||||
uint32_t ckSize;
|
||||
} ChunkHeader;
|
||||
|
||||
#define ChunkHeaderFormat "4L"
|
||||
|
||||
typedef struct {
|
||||
ushort FormatTag, NumChannels;
|
||||
uint32_t SampleRate, BytesPerSecond;
|
||||
ushort BlockAlign, BitsPerSample;
|
||||
ushort cbSize, ValidBitsPerSample;
|
||||
int32_t ChannelMask;
|
||||
ushort SubFormat;
|
||||
char GUID [14];
|
||||
} WaveHeader;
|
||||
|
||||
#define WaveHeaderFormat "SSLLSSSSLS"
|
||||
|
||||
////////////////////////////// WavPack Header /////////////////////////////////
|
||||
|
||||
// Note that this is the ONLY structure that is written to (or read from)
|
||||
// WavPack 4.0 files, and is the preamble to every block in both the .wv
|
||||
// and .wvc files.
|
||||
|
||||
typedef struct {
|
||||
char ckID [4];
|
||||
uint32_t ckSize;
|
||||
short version;
|
||||
uchar track_no, index_no;
|
||||
uint32_t total_samples, block_index, block_samples, flags, crc;
|
||||
} WavpackHeader;
|
||||
|
||||
#define WavpackHeaderFormat "4LS2LLLLL"
|
||||
|
||||
// or-values for "flags"
|
||||
|
||||
#define BYTES_STORED 3 // 1-4 bytes/sample
|
||||
#define MONO_FLAG 4 // not stereo
|
||||
#define HYBRID_FLAG 8 // hybrid mode
|
||||
#define JOINT_STEREO 0x10 // joint stereo
|
||||
#define CROSS_DECORR 0x20 // no-delay cross decorrelation
|
||||
#define HYBRID_SHAPE 0x40 // noise shape (hybrid mode only)
|
||||
#define FLOAT_DATA 0x80 // ieee 32-bit floating point data
|
||||
|
||||
#define INT32_DATA 0x100 // special extended int handling
|
||||
#define HYBRID_BITRATE 0x200 // bitrate noise (hybrid mode only)
|
||||
#define HYBRID_BALANCE 0x400 // balance noise (hybrid stereo mode only)
|
||||
|
||||
#define INITIAL_BLOCK 0x800 // initial block of multichannel segment
|
||||
#define FINAL_BLOCK 0x1000 // final block of multichannel segment
|
||||
|
||||
#define SHIFT_LSB 13
|
||||
#define SHIFT_MASK (0x1fL << SHIFT_LSB)
|
||||
|
||||
#define MAG_LSB 18
|
||||
#define MAG_MASK (0x1fL << MAG_LSB)
|
||||
|
||||
#define SRATE_LSB 23
|
||||
#define SRATE_MASK (0xfL << SRATE_LSB)
|
||||
|
||||
#define FALSE_STEREO 0x40000000 // block is stereo, but data is mono
|
||||
|
||||
#define IGNORED_FLAGS 0x18000000 // reserved, but ignore if encountered
|
||||
#define NEW_SHAPING 0x20000000 // use IIR filter for negative shaping
|
||||
#define UNKNOWN_FLAGS 0x80000000 // also reserved, but refuse decode if
|
||||
// encountered
|
||||
|
||||
#define MONO_DATA (MONO_FLAG | FALSE_STEREO)
|
||||
|
||||
#define MIN_STREAM_VERS 0x402 // lowest stream version we'll decode
|
||||
#define MAX_STREAM_VERS 0x410 // highest stream version we'll decode or encode
|
||||
#define CUR_STREAM_VERS 0x407 // stream version we are [normally] writing now
|
||||
|
||||
|
||||
//////////////////////////// WavPack Metadata /////////////////////////////////
|
||||
|
||||
// This is an internal representation of metadata.
|
||||
|
||||
typedef struct {
|
||||
int32_t byte_length;
|
||||
void *data;
|
||||
uchar id;
|
||||
} WavpackMetadata;
|
||||
|
||||
#define ID_UNIQUE 0x3f
|
||||
#define ID_OPTIONAL_DATA 0x20
|
||||
#define ID_ODD_SIZE 0x40
|
||||
#define ID_LARGE 0x80
|
||||
|
||||
#define ID_DUMMY 0x0
|
||||
#define ID_ENCODER_INFO 0x1
|
||||
#define ID_DECORR_TERMS 0x2
|
||||
#define ID_DECORR_WEIGHTS 0x3
|
||||
#define ID_DECORR_SAMPLES 0x4
|
||||
#define ID_ENTROPY_VARS 0x5
|
||||
#define ID_HYBRID_PROFILE 0x6
|
||||
#define ID_SHAPING_WEIGHTS 0x7
|
||||
#define ID_FLOAT_INFO 0x8
|
||||
#define ID_INT32_INFO 0x9
|
||||
#define ID_WV_BITSTREAM 0xa
|
||||
#define ID_WVC_BITSTREAM 0xb
|
||||
#define ID_WVX_BITSTREAM 0xc
|
||||
#define ID_CHANNEL_INFO 0xd
|
||||
|
||||
#define ID_RIFF_HEADER (ID_OPTIONAL_DATA | 0x1)
|
||||
#define ID_RIFF_TRAILER (ID_OPTIONAL_DATA | 0x2)
|
||||
#define ID_REPLAY_GAIN (ID_OPTIONAL_DATA | 0x3)
|
||||
#define ID_CUESHEET (ID_OPTIONAL_DATA | 0x4)
|
||||
#define ID_CONFIG_BLOCK (ID_OPTIONAL_DATA | 0x5)
|
||||
#define ID_MD5_CHECKSUM (ID_OPTIONAL_DATA | 0x6)
|
||||
#define ID_SAMPLE_RATE (ID_OPTIONAL_DATA | 0x7)
|
||||
|
||||
///////////////////////// WavPack Configuration ///////////////////////////////
|
||||
|
||||
// This internal structure is used during encode to provide configuration to
|
||||
// the encoding engine and during decoding to provide fle information back to
|
||||
// the higher level functions. Not all fields are used in both modes.
|
||||
|
||||
typedef struct {
|
||||
float bitrate, shaping_weight;
|
||||
int bits_per_sample, bytes_per_sample;
|
||||
int qmode, flags, xmode, num_channels, float_norm_exp;
|
||||
int32_t block_samples, extra_flags, sample_rate, channel_mask;
|
||||
uchar md5_checksum [16], md5_read;
|
||||
int num_tag_strings;
|
||||
char **tag_strings;
|
||||
} WavpackConfig;
|
||||
|
||||
#define CONFIG_BYTES_STORED 3 // 1-4 bytes/sample
|
||||
#define CONFIG_MONO_FLAG 4 // not stereo
|
||||
#define CONFIG_HYBRID_FLAG 8 // hybrid mode
|
||||
#define CONFIG_JOINT_STEREO 0x10 // joint stereo
|
||||
#define CONFIG_CROSS_DECORR 0x20 // no-delay cross decorrelation
|
||||
#define CONFIG_HYBRID_SHAPE 0x40 // noise shape (hybrid mode only)
|
||||
#define CONFIG_FLOAT_DATA 0x80 // ieee 32-bit floating point data
|
||||
|
||||
#define CONFIG_FAST_FLAG 0x200 // fast mode
|
||||
#define CONFIG_HIGH_FLAG 0x800 // high quality mode
|
||||
#define CONFIG_VERY_HIGH_FLAG 0x1000 // very high
|
||||
#define CONFIG_BITRATE_KBPS 0x2000 // bitrate is kbps, not bits / sample
|
||||
#define CONFIG_AUTO_SHAPING 0x4000 // automatic noise shaping
|
||||
#define CONFIG_SHAPE_OVERRIDE 0x8000 // shaping mode specified
|
||||
#define CONFIG_JOINT_OVERRIDE 0x10000 // joint-stereo mode specified
|
||||
#define CONFIG_DYNAMIC_SHAPING 0x20000 // dynamic noise shaping
|
||||
#define CONFIG_CREATE_EXE 0x40000 // create executable
|
||||
#define CONFIG_CREATE_WVC 0x80000 // create correction file
|
||||
#define CONFIG_OPTIMIZE_WVC 0x100000 // maximize bybrid compression
|
||||
#define CONFIG_CALC_NOISE 0x800000 // calc noise in hybrid mode
|
||||
#define CONFIG_LOSSY_MODE 0x1000000 // obsolete (for information)
|
||||
#define CONFIG_EXTRA_MODE 0x2000000 // extra processing mode
|
||||
#define CONFIG_SKIP_WVX 0x4000000 // no wvx stream w/ floats & big ints
|
||||
#define CONFIG_MD5_CHECKSUM 0x8000000 // compute & store MD5 signature
|
||||
#define CONFIG_MERGE_BLOCKS 0x10000000 // merge blocks of equal redundancy (for lossyWAV)
|
||||
#define CONFIG_OPTIMIZE_MONO 0x80000000 // optimize for mono streams posing as stereo
|
||||
|
||||
/*
|
||||
* These config flags were never actually used, or are no longer used, or are
|
||||
* used for something else now. They may be used in the future for what they
|
||||
* say, or for something else. WavPack files in the wild *may* have some of
|
||||
* these bit set in their config flags (with these older meanings), but only
|
||||
* if the stream version is 0x410 or less than 0x407. Of course, this is not
|
||||
* very important because once the file has been encoded, the config bits are
|
||||
* just for information purposes (i.e., they do not affect decoding),
|
||||
*
|
||||
#define CONFIG_ADOBE_MODE 0x100 // "adobe" mode for 32-bit floats
|
||||
#define CONFIG_VERY_FAST_FLAG 0x400 // double fast
|
||||
#define CONFIG_COPY_TIME 0x20000 // copy file-time from source
|
||||
#define CONFIG_QUALITY_MODE 0x200000 // psychoacoustic quality mode
|
||||
#define CONFIG_RAW_FLAG 0x400000 // raw mode (not implemented yet)
|
||||
#define CONFIG_QUIET_MODE 0x10000000 // don't report progress %
|
||||
#define CONFIG_IGNORE_LENGTH 0x20000000 // ignore length in wav header
|
||||
#define CONFIG_NEW_RIFF_HEADER 0x40000000 // generate new RIFF wav header
|
||||
*
|
||||
*/
|
||||
|
||||
#define EXTRA_SCAN_ONLY 1
|
||||
#define EXTRA_STEREO_MODES 2
|
||||
#define EXTRA_TRY_DELTAS 8
|
||||
#define EXTRA_ADJUST_DELTAS 16
|
||||
#define EXTRA_SORT_FIRST 32
|
||||
#define EXTRA_BRANCHES 0x1c0
|
||||
#define EXTRA_SKIP_8TO16 512
|
||||
#define EXTRA_TERMS 0x3c00
|
||||
#define EXTRA_DUMP_TERMS 16384
|
||||
#define EXTRA_SORT_LAST 32768
|
||||
|
||||
//////////////////////////////// WavPack Stream ///////////////////////////////
|
||||
|
||||
// This internal structure contains everything required to handle a WavPack
|
||||
// "stream", which is defined as a stereo or mono stream of audio samples. For
|
||||
// multichannel audio several of these would be required. Each stream contains
|
||||
// pointers to hold a complete allocated block of WavPack data, although it's
|
||||
// possible to decode WavPack blocks without buffering an entire block.
|
||||
|
||||
typedef struct bs {
|
||||
#ifdef BITSTREAM_SHORTS
|
||||
unsigned short *buf, *end, *ptr;
|
||||
#else
|
||||
unsigned char *buf, *end, *ptr;
|
||||
#endif
|
||||
void (*wrap)(struct bs *bs);
|
||||
int error, bc;
|
||||
uint32_t sr;
|
||||
} Bitstream;
|
||||
|
||||
#define MAX_WRAPPER_BYTES 16777216
|
||||
#define MAX_STREAMS 8
|
||||
#define MAX_NTERMS 16
|
||||
#define MAX_TERM 8
|
||||
|
||||
struct decorr_pass {
|
||||
int term, delta, weight_A, weight_B;
|
||||
int32_t samples_A [MAX_TERM], samples_B [MAX_TERM];
|
||||
int32_t aweight_A, aweight_B;
|
||||
int32_t sum_A, sum_B;
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
char joint_stereo, delta, terms [MAX_NTERMS+1];
|
||||
} WavpackDecorrSpec;
|
||||
|
||||
struct entropy_data {
|
||||
uint32_t median [3], slow_level, error_limit;
|
||||
};
|
||||
|
||||
struct words_data {
|
||||
uint32_t bitrate_delta [2], bitrate_acc [2];
|
||||
uint32_t pend_data, holding_one, zeros_acc;
|
||||
int holding_zero, pend_count;
|
||||
struct entropy_data c [2];
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
WavpackHeader wphdr;
|
||||
struct words_data w;
|
||||
|
||||
uchar *blockbuff, *blockend;
|
||||
uchar *block2buff, *block2end;
|
||||
int32_t *sample_buffer;
|
||||
|
||||
int bits, num_terms, mute_error, joint_stereo, false_stereo, shift;
|
||||
int num_decorrs, num_passes, best_decorr, mask_decorr;
|
||||
uint32_t sample_index, crc, crc_x, crc_wvx;
|
||||
Bitstream wvbits, wvcbits, wvxbits;
|
||||
int init_done, wvc_skip;
|
||||
float delta_decay;
|
||||
|
||||
uchar int32_sent_bits, int32_zeros, int32_ones, int32_dups;
|
||||
uchar float_flags, float_shift, float_max_exp, float_norm_exp;
|
||||
|
||||
struct {
|
||||
int32_t shaping_acc [2], shaping_delta [2], error [2];
|
||||
double noise_sum, noise_ave, noise_max;
|
||||
short *shaping_data, *shaping_array;
|
||||
int32_t shaping_samples;
|
||||
} dc;
|
||||
|
||||
struct decorr_pass decorr_passes [MAX_NTERMS], analysis_pass;
|
||||
const WavpackDecorrSpec *decorr_specs;
|
||||
} WavpackStream;
|
||||
|
||||
// flags for float_flags:
|
||||
|
||||
#define FLOAT_SHIFT_ONES 1 // bits left-shifted into float = '1'
|
||||
#define FLOAT_SHIFT_SAME 2 // bits left-shifted into float are the same
|
||||
#define FLOAT_SHIFT_SENT 4 // bits shifted into float are sent literally
|
||||
#define FLOAT_ZEROS_SENT 8 // "zeros" are not all real zeros
|
||||
#define FLOAT_NEG_ZEROS 0x10 // contains negative zeros
|
||||
#define FLOAT_EXCEPTIONS 0x20 // contains exceptions (inf, nan, etc.)
|
||||
|
||||
/////////////////////////////// WavPack Context ///////////////////////////////
|
||||
|
||||
// This internal structure holds everything required to encode or decode WavPack
|
||||
// files. It is recommended that direct access to this structure be minimized
|
||||
// and the provided utilities used instead.
|
||||
|
||||
typedef struct {
|
||||
int32_t (*read_bytes)(void *id, void *data, int32_t bcount);
|
||||
uint32_t (*get_pos)(void *id);
|
||||
int (*set_pos_abs)(void *id, uint32_t pos);
|
||||
int (*set_pos_rel)(void *id, int32_t delta, int mode);
|
||||
int (*push_back_byte)(void *id, int c);
|
||||
uint32_t (*get_length)(void *id);
|
||||
int (*can_seek)(void *id);
|
||||
|
||||
// this callback is for writing edited tags only
|
||||
int32_t (*write_bytes)(void *id, void *data, int32_t bcount);
|
||||
} WavpackStreamReader;
|
||||
|
||||
typedef int (*WavpackBlockOutput)(void *id, void *data, int32_t bcount);
|
||||
|
||||
typedef struct {
|
||||
WavpackConfig config;
|
||||
|
||||
WavpackMetadata *metadata;
|
||||
uint32_t metabytes;
|
||||
int metacount;
|
||||
|
||||
uchar *wrapper_data;
|
||||
uint32_t wrapper_bytes;
|
||||
|
||||
WavpackBlockOutput blockout;
|
||||
void *wv_out, *wvc_out;
|
||||
|
||||
WavpackStreamReader *reader;
|
||||
void *wv_in, *wvc_in;
|
||||
|
||||
uint32_t filelen, file2len, filepos, file2pos, total_samples, crc_errors, first_flags;
|
||||
int wvc_flag, open_flags, norm_offset, reduced_channels, lossy_blocks, close_files;
|
||||
uint32_t block_samples, ave_block_samples, block_boundary, max_samples, acc_samples, initial_index;
|
||||
int riff_header_added, riff_header_created;
|
||||
M_Tag m_tag;
|
||||
|
||||
int current_stream, num_streams, stream_version;
|
||||
WavpackStream *streams [MAX_STREAMS];
|
||||
void *stream3;
|
||||
|
||||
char error_message [80];
|
||||
} WavpackContext;
|
||||
|
||||
//////////////////////// function prototypes and macros //////////////////////
|
||||
|
||||
#define CLEAR(destin) memset (&destin, 0, sizeof (destin));
|
||||
|
||||
// these macros implement the weight application and update operations
|
||||
// that are at the heart of the decorrelation loops
|
||||
|
||||
#define apply_weight_i(weight, sample) ((weight * sample + 512) >> 10)
|
||||
|
||||
#define apply_weight_f(weight, sample) (((((sample & 0xffff) * weight) >> 9) + \
|
||||
(((sample & ~0xffff) >> 9) * weight) + 1) >> 1)
|
||||
|
||||
#if 1 // PERFCOND
|
||||
#define apply_weight(weight, sample) (sample != (short) sample ? \
|
||||
apply_weight_f (weight, sample) : apply_weight_i (weight, sample))
|
||||
#else
|
||||
#define apply_weight(weight, sample) ((int32_t)((weight * (int64_t) sample + 512) >> 10))
|
||||
#endif
|
||||
|
||||
#if 1 // PERFCOND
|
||||
#define update_weight(weight, delta, source, result) \
|
||||
if (source && result) { int32_t s = (int32_t) (source ^ result) >> 31; weight = (delta ^ s) + (weight - s); }
|
||||
#elif 1
|
||||
#define update_weight(weight, delta, source, result) \
|
||||
if (source && result) weight += (((source ^ result) >> 30) | 1) * delta;
|
||||
#else
|
||||
#define update_weight(weight, delta, source, result) \
|
||||
if (source && result) (source ^ result) < 0 ? (weight -= delta) : (weight += delta);
|
||||
#endif
|
||||
|
||||
#define update_weight_d2(weight, delta, source, result) \
|
||||
if (source && result) weight -= (((source ^ result) >> 29) & 4) - 2;
|
||||
|
||||
#define update_weight_clip(weight, delta, source, result) \
|
||||
if (source && result) { \
|
||||
const int32_t s = (source ^ result) >> 31; \
|
||||
if ((weight = (weight ^ s) + (delta - s)) > 1024) weight = 1024; \
|
||||
weight = (weight ^ s) - s; \
|
||||
}
|
||||
|
||||
#define update_weight_clip_d2(weight, delta, source, result) \
|
||||
if (source && result) { \
|
||||
const int32_t s = (source ^ result) >> 31; \
|
||||
if ((weight = (weight ^ s) + (2 - s)) > 1024) weight = 1024; \
|
||||
weight = (weight ^ s) - s; \
|
||||
}
|
||||
|
||||
// bits.c
|
||||
|
||||
void bs_open_read (Bitstream *bs, void *buffer_start, void *buffer_end);
|
||||
void bs_open_write (Bitstream *bs, void *buffer_start, void *buffer_end);
|
||||
uint32_t bs_close_read (Bitstream *bs);
|
||||
uint32_t bs_close_write (Bitstream *bs);
|
||||
|
||||
int DoReadFile (FILE *hFile, void *lpBuffer, uint32_t nNumberOfBytesToRead, uint32_t *lpNumberOfBytesRead);
|
||||
int DoWriteFile (FILE *hFile, void *lpBuffer, uint32_t nNumberOfBytesToWrite, uint32_t *lpNumberOfBytesWritten);
|
||||
uint32_t DoGetFileSize (FILE *hFile), DoGetFilePosition (FILE *hFile);
|
||||
int DoSetFilePositionRelative (FILE *hFile, int32_t pos, int mode);
|
||||
int DoSetFilePositionAbsolute (FILE *hFile, uint32_t pos);
|
||||
int DoUngetc (int c, FILE *hFile), DoDeleteFile (char *filename);
|
||||
int DoCloseHandle (FILE *hFile), DoTruncateFile (FILE *hFile);
|
||||
|
||||
#define bs_is_open(bs) ((bs)->ptr != NULL)
|
||||
|
||||
#define getbit(bs) ( \
|
||||
(((bs)->bc) ? \
|
||||
((bs)->bc--, (bs)->sr & 1) : \
|
||||
(((++((bs)->ptr) != (bs)->end) ? (void) 0 : (bs)->wrap (bs)), (bs)->bc = sizeof (*((bs)->ptr)) * 8 - 1, ((bs)->sr = *((bs)->ptr)) & 1) \
|
||||
) ? \
|
||||
((bs)->sr >>= 1, 1) : \
|
||||
((bs)->sr >>= 1, 0) \
|
||||
)
|
||||
|
||||
#define getbits(value, nbits, bs) { \
|
||||
while ((nbits) > (bs)->bc) { \
|
||||
if (++((bs)->ptr) == (bs)->end) (bs)->wrap (bs); \
|
||||
(bs)->sr |= (int32_t)*((bs)->ptr) << (bs)->bc; \
|
||||
(bs)->bc += sizeof (*((bs)->ptr)) * 8; \
|
||||
} \
|
||||
*(value) = (bs)->sr; \
|
||||
if ((bs)->bc > 32) { \
|
||||
(bs)->bc -= (nbits); \
|
||||
(bs)->sr = *((bs)->ptr) >> (sizeof (*((bs)->ptr)) * 8 - (bs)->bc); \
|
||||
} \
|
||||
else { \
|
||||
(bs)->bc -= (nbits); \
|
||||
(bs)->sr >>= (nbits); \
|
||||
} \
|
||||
}
|
||||
|
||||
#define putbit(bit, bs) { if (bit) (bs)->sr |= (1 << (bs)->bc); \
|
||||
if (++((bs)->bc) == sizeof (*((bs)->ptr)) * 8) { \
|
||||
*((bs)->ptr) = (bs)->sr; \
|
||||
(bs)->sr = (bs)->bc = 0; \
|
||||
if (++((bs)->ptr) == (bs)->end) (bs)->wrap (bs); \
|
||||
}}
|
||||
|
||||
#define putbit_0(bs) { \
|
||||
if (++((bs)->bc) == sizeof (*((bs)->ptr)) * 8) { \
|
||||
*((bs)->ptr) = (bs)->sr; \
|
||||
(bs)->sr = (bs)->bc = 0; \
|
||||
if (++((bs)->ptr) == (bs)->end) (bs)->wrap (bs); \
|
||||
}}
|
||||
|
||||
#define putbit_1(bs) { (bs)->sr |= (1 << (bs)->bc); \
|
||||
if (++((bs)->bc) == sizeof (*((bs)->ptr)) * 8) { \
|
||||
*((bs)->ptr) = (bs)->sr; \
|
||||
(bs)->sr = (bs)->bc = 0; \
|
||||
if (++((bs)->ptr) == (bs)->end) (bs)->wrap (bs); \
|
||||
}}
|
||||
|
||||
#define putbits(value, nbits, bs) { \
|
||||
(bs)->sr |= (int32_t)(value) << (bs)->bc; \
|
||||
if (((bs)->bc += (nbits)) >= sizeof (*((bs)->ptr)) * 8) \
|
||||
do { \
|
||||
*((bs)->ptr) = (bs)->sr; \
|
||||
(bs)->sr >>= sizeof (*((bs)->ptr)) * 8; \
|
||||
if (((bs)->bc -= sizeof (*((bs)->ptr)) * 8) > 32 - sizeof (*((bs)->ptr)) * 8) \
|
||||
(bs)->sr |= ((value) >> ((nbits) - (bs)->bc)); \
|
||||
if (++((bs)->ptr) == (bs)->end) (bs)->wrap (bs); \
|
||||
} while ((bs)->bc >= sizeof (*((bs)->ptr)) * 8); \
|
||||
}
|
||||
|
||||
void little_endian_to_native (void *data, char *format);
|
||||
void native_to_little_endian (void *data, char *format);
|
||||
|
||||
// pack.c
|
||||
|
||||
void pack_init (WavpackContext *wpc);
|
||||
int pack_block (WavpackContext *wpc, int32_t *buffer);
|
||||
double WavpackGetEncodedNoise (WavpackContext *wpc, double *peak);
|
||||
|
||||
// unpack.c
|
||||
|
||||
int unpack_init (WavpackContext *wpc);
|
||||
int init_wv_bitstream (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int init_wvc_bitstream (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int init_wvx_bitstream (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int read_decorr_terms (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int read_decorr_weights (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int read_decorr_samples (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int read_shaping_info (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int read_float_info (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int read_int32_info (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int read_channel_info (WavpackContext *wpc, WavpackMetadata *wpmd);
|
||||
int read_config_info (WavpackContext *wpc, WavpackMetadata *wpmd);
|
||||
int read_sample_rate (WavpackContext *wpc, WavpackMetadata *wpmd);
|
||||
int read_wrapper_data (WavpackContext *wpc, WavpackMetadata *wpmd);
|
||||
int32_t unpack_samples (WavpackContext *wpc, int32_t *buffer, uint32_t sample_count);
|
||||
int check_crc_error (WavpackContext *wpc);
|
||||
|
||||
// unpack3.c
|
||||
|
||||
WavpackContext *open_file3 (WavpackContext *wpc, char *error);
|
||||
int32_t unpack_samples3 (WavpackContext *wpc, int32_t *buffer, uint32_t sample_count);
|
||||
int seek_sample3 (WavpackContext *wpc, uint32_t desired_index);
|
||||
uint32_t get_sample_index3 (WavpackContext *wpc);
|
||||
void free_stream3 (WavpackContext *wpc);
|
||||
int get_version3 (WavpackContext *wpc);
|
||||
|
||||
// metadata.c stuff
|
||||
|
||||
int read_metadata_buff (WavpackMetadata *wpmd, uchar *blockbuff, uchar **buffptr);
|
||||
int write_metadata_block (WavpackContext *wpc);
|
||||
int copy_metadata (WavpackMetadata *wpmd, uchar *buffer_start, uchar *buffer_end);
|
||||
int add_to_metadata (WavpackContext *wpc, void *data, uint32_t bcount, uchar id);
|
||||
int process_metadata (WavpackContext *wpc, WavpackMetadata *wpmd);
|
||||
void free_metadata (WavpackMetadata *wpmd);
|
||||
|
||||
// words.c stuff
|
||||
|
||||
void init_words (WavpackStream *wps);
|
||||
void word_set_bitrate (WavpackStream *wps);
|
||||
void write_entropy_vars (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
void write_hybrid_profile (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int read_entropy_vars (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int read_hybrid_profile (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int32_t FASTCALL send_word (WavpackStream *wps, int32_t value, int chan);
|
||||
void send_words_lossless (WavpackStream *wps, int32_t *buffer, int32_t nsamples);
|
||||
int32_t FASTCALL get_word (WavpackStream *wps, int chan, int32_t *correction);
|
||||
int32_t get_words_lossless (WavpackStream *wps, int32_t *buffer, int32_t nsamples);
|
||||
void flush_word (WavpackStream *wps);
|
||||
int32_t nosend_word (WavpackStream *wps, int32_t value, int chan);
|
||||
void scan_word (WavpackStream *wps, int32_t *samples, uint32_t num_samples, int dir);
|
||||
|
||||
int log2s (int32_t value);
|
||||
int32_t exp2s (int log);
|
||||
uint32_t log2buffer (int32_t *samples, uint32_t num_samples, int limit);
|
||||
|
||||
signed char store_weight (int weight);
|
||||
int restore_weight (signed char weight);
|
||||
|
||||
#define WORD_EOF ((int32_t)(1L << 31))
|
||||
|
||||
// float.c
|
||||
|
||||
void write_float_info (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
int scan_float_data (WavpackStream *wps, f32 *values, int32_t num_values);
|
||||
void send_float_data (WavpackStream *wps, f32 *values, int32_t num_values);
|
||||
int read_float_info (WavpackStream *wps, WavpackMetadata *wpmd);
|
||||
void float_values (WavpackStream *wps, int32_t *values, int32_t num_values);
|
||||
void WavpackFloatNormalize (int32_t *values, int32_t num_values, int delta_exp);
|
||||
|
||||
// extra?.c
|
||||
|
||||
// void analyze_stereo (WavpackContext *wpc, int32_t *samples);
|
||||
// void analyze_mono (WavpackContext *wpc, int32_t *samples);
|
||||
void execute_stereo (WavpackContext *wpc, int32_t *samples, int no_history, int do_samples);
|
||||
void execute_mono (WavpackContext *wpc, int32_t *samples, int no_history, int do_samples);
|
||||
|
||||
// wputils.c
|
||||
|
||||
WavpackContext *WavpackOpenFileInputEx (WavpackStreamReader *reader, void *wv_id, void *wvc_id, char *error, int flags, int norm_offset);
|
||||
WavpackContext *WavpackOpenFileInput (const wchar_t *infilename, char *error, int flags, int norm_offset);
|
||||
|
||||
#define OPEN_WVC 0x1 // open/read "correction" file
|
||||
#define OPEN_TAGS 0x2 // read ID3v1 / APEv2 tags (seekable file)
|
||||
#define OPEN_WRAPPER 0x4 // make audio wrapper available (i.e. RIFF)
|
||||
#define OPEN_2CH_MAX 0x8 // open multichannel as stereo (no downmix)
|
||||
#define OPEN_NORMALIZE 0x10 // normalize floating point data to +/- 1.0
|
||||
#define OPEN_STREAMING 0x20 // "streaming" mode blindly unpacks blocks
|
||||
// w/o regard to header file position info
|
||||
#define OPEN_EDIT_TAGS 0x40 // allow editing of tags
|
||||
|
||||
int WavpackGetMode (WavpackContext *wpc);
|
||||
|
||||
#define MODE_WVC 0x1
|
||||
#define MODE_LOSSLESS 0x2
|
||||
#define MODE_HYBRID 0x4
|
||||
#define MODE_FLOAT 0x8
|
||||
#define MODE_VALID_TAG 0x10
|
||||
#define MODE_HIGH 0x20
|
||||
#define MODE_FAST 0x40
|
||||
#define MODE_EXTRA 0x80 // extra mode used, see MODE_XMODE for possible level
|
||||
#define MODE_APETAG 0x100
|
||||
#define MODE_SFX 0x200
|
||||
#define MODE_VERY_HIGH 0x400
|
||||
#define MODE_MD5 0x800
|
||||
#define MODE_XMODE 0x7000 // mask for extra level (1-6, 0=unknown)
|
||||
#define MODE_DNS 0x8000
|
||||
|
||||
char *WavpackGetErrorMessage (WavpackContext *wpc);
|
||||
int WavpackGetVersion (WavpackContext *wpc);
|
||||
uint32_t WavpackUnpackSamples (WavpackContext *wpc, int32_t *buffer, uint32_t samples);
|
||||
uint32_t WavpackGetNumSamples (WavpackContext *wpc);
|
||||
uint32_t WavpackGetSampleIndex (WavpackContext *wpc);
|
||||
int WavpackGetNumErrors (WavpackContext *wpc);
|
||||
int WavpackLossyBlocks (WavpackContext *wpc);
|
||||
int WavpackSeekSample (WavpackContext *wpc, uint32_t sample);
|
||||
WavpackContext *WavpackCloseFile (WavpackContext *wpc);
|
||||
uint32_t WavpackGetSampleRate (WavpackContext *wpc);
|
||||
int WavpackGetBitsPerSample (WavpackContext *wpc);
|
||||
int WavpackGetBytesPerSample (WavpackContext *wpc);
|
||||
int WavpackGetNumChannels (WavpackContext *wpc);
|
||||
int WavpackGetChannelMask (WavpackContext *wpc);
|
||||
int WavpackGetReducedChannels (WavpackContext *wpc);
|
||||
int WavpackGetFloatNormExp (WavpackContext *wpc);
|
||||
int WavpackGetMD5Sum (WavpackContext *wpc, uchar data [16]);
|
||||
uint32_t WavpackGetWrapperBytes (WavpackContext *wpc);
|
||||
uchar *WavpackGetWrapperData (WavpackContext *wpc);
|
||||
void WavpackFreeWrapper (WavpackContext *wpc);
|
||||
void WavpackSeekTrailingWrapper (WavpackContext *wpc);
|
||||
double WavpackGetProgress (WavpackContext *wpc);
|
||||
uint32_t WavpackGetFileSize (WavpackContext *wpc);
|
||||
double WavpackGetRatio (WavpackContext *wpc);
|
||||
double WavpackGetAverageBitrate (WavpackContext *wpc, int count_wvc);
|
||||
double WavpackGetInstantBitrate (WavpackContext *wpc);
|
||||
int WavpackGetNumTagItems (WavpackContext *wpc);
|
||||
int WavpackGetTagItem (WavpackContext *wpc, const char *item, char *value, int size);
|
||||
int WavpackGetTagItemIndexed (WavpackContext *wpc, int index, char *item, int size);
|
||||
int WavpackAppendTagItem (WavpackContext *wpc, const char *item, const char *value, int vsize);
|
||||
int WavpackDeleteTagItem (WavpackContext *wpc, const char *item);
|
||||
int WavpackWriteTag (WavpackContext *wpc);
|
||||
|
||||
WavpackContext *WavpackOpenFileOutput (WavpackBlockOutput blockout, void *wv_id, void *wvc_id);
|
||||
int WavpackSetConfiguration (WavpackContext *wpc, WavpackConfig *config, uint32_t total_samples);
|
||||
int WavpackAddWrapper (WavpackContext *wpc, void *data, uint32_t bcount);
|
||||
int WavpackStoreMD5Sum (WavpackContext *wpc, uchar data [16]);
|
||||
int WavpackPackInit (WavpackContext *wpc);
|
||||
int WavpackPackSamples (WavpackContext *wpc, int32_t *sample_buffer, uint32_t sample_count);
|
||||
int WavpackFlushSamples (WavpackContext *wpc);
|
||||
void WavpackUpdateNumSamples (WavpackContext *wpc, void *first_block);
|
||||
void *WavpackGetWrapperLocation (void *first_block, uint32_t *size);
|
||||
|
||||
void WavpackLittleEndianToNative (void *data, char *format);
|
||||
void WavpackNativeToLittleEndian (void *data, char *format);
|
||||
|
||||
uint32_t WavpackGetLibraryVersion (void);
|
||||
const char *WavpackGetLibraryVersionString (void);
|
||||
|
||||
///////////////////////////// SIMD helper macros /////////////////////////////
|
||||
|
||||
#ifdef OPT_MMX
|
||||
|
||||
#if defined (__GNUC__) && !defined (__INTEL_COMPILER)
|
||||
//directly map to gcc's native builtins for faster code
|
||||
|
||||
#if __GNUC__ < 4
|
||||
typedef int __di __attribute__ ((__mode__ (__DI__)));
|
||||
typedef int __m64 __attribute__ ((__mode__ (__V2SI__)));
|
||||
typedef int __v4hi __attribute__ ((__mode__ (__V4HI__)));
|
||||
#define _m_paddsw(m1, m2) (__m64) __builtin_ia32_paddsw ((__v4hi) m1, (__v4hi) m2)
|
||||
#define _m_pand(m1, m2) (__m64) __builtin_ia32_pand ((__di) m1, (__di) m2)
|
||||
#define _m_pandn(m1, m2) (__m64) __builtin_ia32_pandn ((__di) m1, (__di) m2)
|
||||
#define _m_pmaddwd(m1, m2) __builtin_ia32_pmaddwd ((__v4hi) m1, (__v4hi) m2)
|
||||
#define _m_por(m1, m2) (__m64) __builtin_ia32_por ((__di) m1, (__di) m2)
|
||||
#define _m_pxor(m1, m2) (__m64) __builtin_ia32_pxor ((__di) m1, (__di) m2)
|
||||
#else
|
||||
typedef int __m64 __attribute__ ((__vector_size__ (8)));
|
||||
typedef short __m64_16 __attribute__ ((__vector_size__ (8)));
|
||||
#define _m_paddsw(m1, m2) (__m64) __builtin_ia32_paddsw ((__m64_16) m1, (__m64_16) m2)
|
||||
#define _m_pand(m1, m2) __builtin_ia32_pand (m1, m2)
|
||||
#define _m_pandn(m1, m2) __builtin_ia32_pandn (m1, m2)
|
||||
#define _m_pmaddwd(m1, m2) __builtin_ia32_pmaddwd ((__m64_16) m1, (__m64_16) m2)
|
||||
#define _m_por(m1, m2) __builtin_ia32_por (m1, m2)
|
||||
#define _m_pxor(m1, m2) __builtin_ia32_pxor (m1, m2)
|
||||
#endif
|
||||
|
||||
#define _m_paddd(m1, m2) __builtin_ia32_paddd (m1, m2)
|
||||
#define _m_pcmpeqd(m1, m2) __builtin_ia32_pcmpeqd (m1, m2)
|
||||
#define _m_pslldi(m1, m2) __builtin_ia32_pslld (m1, m2)
|
||||
#define _m_psradi(m1, m2) __builtin_ia32_psrad (m1, m2)
|
||||
#define _m_psrldi(m1, m2) __builtin_ia32_psrld (m1, m2)
|
||||
#define _m_psubd(m1, m2) __builtin_ia32_psubd (m1, m2)
|
||||
#define _m_punpckhdq(m1, m2) __builtin_ia32_punpckhdq (m1, m2)
|
||||
#define _m_punpckldq(m1, m2) __builtin_ia32_punpckldq (m1, m2)
|
||||
#define _mm_empty() __builtin_ia32_emms ()
|
||||
#define _mm_set_pi32(m1, m2) { m2, m1 }
|
||||
#define _mm_set1_pi32(m) { m, m }
|
||||
|
||||
#else
|
||||
#include <mmintrin.h>
|
||||
#endif
|
||||
|
||||
#endif //OPT_MMX
|
||||
|
||||
#endif
|
||||
@@ -1,19 +0,0 @@
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
// **** WAVPACK **** //
|
||||
// Hybrid Lossless Wavefile Compressor //
|
||||
// Copyright (c) 1998 - 2006 Conifer Software. //
|
||||
// All Rights Reserved. //
|
||||
// Distributed under the BSD Software License (see license.txt) //
|
||||
////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// wavpack_version.h
|
||||
|
||||
#ifndef WAVPACK_VERSION_H
|
||||
#define WAVPACK_VERSION_H
|
||||
|
||||
#define LIBWAVPACK_MAJOR 4
|
||||
#define LIBWAVPACK_MINOR 50
|
||||
#define LIBWAVPACK_MICRO 0
|
||||
#define LIBWAVPACK_VERSION_STRING "4.50.0"
|
||||
|
||||
#endif
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user