// MethodProps.h
#ifndef __7Z_METHOD_PROPS_H
#define __7Z_METHOD_PROPS_H
#include "../../Common/MyString.h"
#include "../../Windows/PropVariant.h"
#include "../ICoder.h"
bool StringToBool(const UString &s, bool &res);
HRESULT PROPVARIANT_to_bool(const PROPVARIANT &prop, bool &dest);
unsigned ParseStringToUInt32(const UString &srcString, UInt32 &number);
HRESULT ParsePropToUInt32(const UString &name, const PROPVARIANT &prop, UInt32 &resValue);
HRESULT ParseMtProp(const UString &name, const PROPVARIANT &prop, UInt32 defaultNumThreads, UInt32 &numThreads);
struct CProp
{
PROPID Id;
bool IsOptional;
NWindows::NCOM::CPropVariant Value;
CProp(): IsOptional(false) {}
};
struct CProps
{
CObjectVector<CProp> Props;
void Clear() { Props.Clear(); }
bool AreThereNonOptionalProps() const
{
FOR_VECTOR (i, Props)
if (!Props[i].IsOptional)
return true;
return false;
}
void AddProp32(PROPID propid, UInt32 level);
void AddPropString(PROPID propid, const wchar_t *s)
{
CProp prop;
prop.IsOptional = true;
prop.Id = propid;
prop.Value = s;
Props.Add(prop);
}
HRESULT SetCoderProps(ICompressSetCoderProperties *scp, const UInt64 *dataSizeReduce) const;
};
class CMethodProps: public CProps
{
HRESULT SetParam(const UString &name, const UString &value);
public:
int GetLevel() const;
int Get_NumThreads() const
{
int i = FindProp(NCoderPropID::kNumThreads);
if (i >= 0)
if (Props[i].Value.vt == VT_UI4)
return (int)Props[i].Value.ulVal;
return -1;
}
bool Get_DicSize(UInt32 &res) const
{
res = 0;
int i = FindProp(NCoderPropID::kDictionarySize);
if (i >= 0)
if (Props[i].Value.vt == VT_UI4)
{
res = Props[i].Value.ulVal;
return true;
}
return false;
}
int FindProp(PROPID id) const;
UInt32 Get_Lzma_Algo() const
{
int i = FindProp(NCoderPropID::kAlgorithm);
if (i >= 0)
if (Props[i].Value.vt == VT_UI4)
return Props[i].Value.ulVal;
return GetLevel() >= 5 ? 1 : 0;
}
UInt32 Get_Lzma_DicSize() const
{
int i = FindProp(NCoderPropID::kDictionarySize);
if (i >= 0)
if (Props[i].Value.vt == VT_UI4)
return Props[i].Value.ulVal;
int level = GetLevel();
return level <= 5 ? (1 << (level * 2 + 14)) : (level == 6 ? (1 << 25) : (1 << 26));
}
UInt32 Get_Lzma_NumThreads(bool &fixedNumber) const
{
fixedNumber = false;
int numThreads = Get_NumThreads();
if (numThreads >= 0)
{
fixedNumber = true;
return numThreads < 2 ? 1 : 2;
}
return Get_Lzma_Algo() == 0 ? 1 : 2;
}
UInt32 Get_BZip2_NumThreads(bool &fixedNumber) const
{
fixedNumber = false;
int numThreads = Get_NumThreads();
if (numThreads >= 0)
{
fixedNumber = true;
if (numThreads < 1) return 1;
if (numThreads > 64) return 64;
return numThreads;
}
return 1;
}
UInt32 Get_BZip2_BlockSize() const
{
int i = FindProp(NCoderPropID::kDictionarySize);
if (i >= 0)
if (Props[i].Value.vt == VT_UI4)
{
UInt32 blockSize = Props[i].Value.ulVal;
const UInt32 kDicSizeMin = 100000;
const UInt32 kDicSizeMax = 900000;
if (blockSize < kDicSizeMin) blockSize = kDicSizeMin;
if (blockSize > kDicSizeMax) blockSize = kDicSizeMax;
return blockSize;
}
int level = GetLevel();
return 100000 * (level >= 5 ? 9 : (level >= 1 ? level * 2 - 1: 1));
}
UInt32 Get_Ppmd_MemSize() const
{
int i = FindProp(NCoderPropID::kUsedMemorySize);
if (i >= 0)
if (Props[i].Value.vt == VT_UI4)
return Props[i].Value.ulVal;
int level = GetLevel();
return level >= 9 ? (192 << 20) : ((UInt32)1 << (level + 19));
}
void AddLevelProp(UInt32 level)
{
AddProp32(NCoderPropID::kLevel, level);
}
void AddNumThreadsProp(UInt32 numThreads)
{
AddProp32(NCoderPropID::kNumThreads, numThreads);
}
HRESULT ParseParamsFromString(const UString &srcString);
HRESULT ParseParamsFromPROPVARIANT(const UString &realName, const PROPVARIANT &value);
};
class COneMethodInfo: public CMethodProps
{
public:
UString MethodName;
void Clear()
{
CMethodProps::Clear();
MethodName.Empty();
}
bool IsEmpty() const { return MethodName.IsEmpty() && Props.IsEmpty(); }
HRESULT ParseMethodFromPROPVARIANT(const UString &realName, const PROPVARIANT &value);
HRESULT ParseMethodFromString(const UString &s);
};
#endif