1 // MethodProps.h 2 3 #ifndef __7Z_METHOD_PROPS_H 4 #define __7Z_METHOD_PROPS_H 5 6 #include "../../Common/MyString.h" 7 #include "../../Common/Defs.h" 8 9 #include "../../Windows/Defs.h" 10 11 #include "../../Windows/PropVariant.h" 12 13 #include "../ICoder.h" 14 15 bool StringToBool(const wchar_t *s, bool &res); 16 HRESULT PROPVARIANT_to_bool(const PROPVARIANT &prop, bool &dest); 17 unsigned ParseStringToUInt32(const UString &srcString, UInt32 &number); 18 HRESULT ParsePropToUInt32(const UString &name, const PROPVARIANT &prop, UInt32 &resValue); 19 20 HRESULT ParseMtProp(const UString &name, const PROPVARIANT &prop, UInt32 defaultNumThreads, UInt32 &numThreads); 21 22 struct CProp 23 { 24 PROPID Id; 25 bool IsOptional; 26 NWindows::NCOM::CPropVariant Value; 27 CProp(): IsOptional(false) {} 28 }; 29 30 struct CProps 31 { 32 CObjectVector<CProp> Props; 33 34 void Clear() { Props.Clear(); } 35 36 bool AreThereNonOptionalProps() const 37 { 38 FOR_VECTOR (i, Props) 39 if (!Props[i].IsOptional) 40 return true; 41 return false; 42 } 43 44 void AddProp32(PROPID propid, UInt32 val); 45 46 void AddPropBool(PROPID propid, bool val); 47 48 void AddProp_Ascii(PROPID propid, const char *s) 49 { 50 CProp &prop = Props.AddNew(); 51 prop.IsOptional = true; 52 prop.Id = propid; 53 prop.Value = s; 54 } 55 56 HRESULT SetCoderProps(ICompressSetCoderProperties *scp, const UInt64 *dataSizeReduce) const; 57 }; 58 59 class CMethodProps: public CProps 60 { 61 HRESULT SetParam(const UString &name, const UString &value); 62 public: 63 int GetLevel() const; 64 int Get_NumThreads() const 65 { 66 int i = FindProp(NCoderPropID::kNumThreads); 67 if (i >= 0) 68 if (Props[i].Value.vt == VT_UI4) 69 return (int)Props[i].Value.ulVal; 70 return -1; 71 } 72 73 bool Get_DicSize(UInt32 &res) const 74 { 75 res = 0; 76 int i = FindProp(NCoderPropID::kDictionarySize); 77 if (i >= 0) 78 if (Props[i].Value.vt == VT_UI4) 79 { 80 res = Props[i].Value.ulVal; 81 return true; 82 } 83 return false; 84 } 85 86 int FindProp(PROPID id) const; 87 88 UInt32 Get_Lzma_Algo() const 89 { 90 int i = FindProp(NCoderPropID::kAlgorithm); 91 if (i >= 0) 92 if (Props[i].Value.vt == VT_UI4) 93 return Props[i].Value.ulVal; 94 return GetLevel() >= 5 ? 1 : 0; 95 } 96 97 UInt32 Get_Lzma_DicSize() const 98 { 99 int i = FindProp(NCoderPropID::kDictionarySize); 100 if (i >= 0) 101 if (Props[i].Value.vt == VT_UI4) 102 return Props[i].Value.ulVal; 103 int level = GetLevel(); 104 return level <= 5 ? (1 << (level * 2 + 14)) : (level == 6 ? (1 << 25) : (1 << 26)); 105 } 106 107 bool Get_Lzma_Eos() const 108 { 109 int i = FindProp(NCoderPropID::kEndMarker); 110 if (i >= 0) 111 { 112 const NWindows::NCOM::CPropVariant &val = Props[i].Value; 113 if (val.vt == VT_BOOL) 114 return VARIANT_BOOLToBool(val.boolVal); 115 } 116 return false; 117 } 118 119 bool Are_Lzma_Model_Props_Defined() const 120 { 121 if (FindProp(NCoderPropID::kPosStateBits) >= 0) return true; 122 if (FindProp(NCoderPropID::kLitContextBits) >= 0) return true; 123 if (FindProp(NCoderPropID::kLitPosBits) >= 0) return true; 124 return false; 125 } 126 127 UInt32 Get_Lzma_NumThreads() const 128 { 129 if (Get_Lzma_Algo() == 0) 130 return 1; 131 int numThreads = Get_NumThreads(); 132 if (numThreads >= 0) 133 return numThreads < 2 ? 1 : 2; 134 return 2; 135 } 136 137 int Get_Xz_NumThreads(UInt32 &lzmaThreads) const 138 { 139 lzmaThreads = 1; 140 int numThreads = Get_NumThreads(); 141 if (numThreads >= 0 && numThreads <= 1) 142 return 1; 143 if (Get_Lzma_Algo() != 0) 144 lzmaThreads = 2; 145 return numThreads; 146 } 147 148 UInt64 GetProp_BlockSize(PROPID id) const 149 { 150 int i = FindProp(id); 151 if (i >= 0) 152 { 153 const NWindows::NCOM::CPropVariant &val = Props[i].Value; 154 if (val.vt == VT_UI4) { return val.ulVal; } 155 if (val.vt == VT_UI8) { return val.uhVal.QuadPart; } 156 } 157 return 0; 158 } 159 160 UInt64 Get_Xz_BlockSize() const 161 { 162 { 163 UInt64 blockSize1 = GetProp_BlockSize(NCoderPropID::kBlockSize); 164 UInt64 blockSize2 = GetProp_BlockSize(NCoderPropID::kBlockSize2); 165 UInt64 minSize = MyMin(blockSize1, blockSize2); 166 if (minSize != 0) 167 return minSize; 168 UInt64 maxSize = MyMax(blockSize1, blockSize2); 169 if (maxSize != 0) 170 return maxSize; 171 } 172 const UInt32 kMinSize = (UInt32)1 << 20; 173 const UInt32 kMaxSize = (UInt32)1 << 28; 174 UInt32 dictSize = Get_Lzma_DicSize(); 175 UInt64 blockSize = (UInt64)dictSize << 2; 176 if (blockSize < kMinSize) blockSize = kMinSize; 177 if (blockSize > kMaxSize) blockSize = kMaxSize; 178 if (blockSize < dictSize) blockSize = dictSize; 179 blockSize += (kMinSize - 1); 180 blockSize &= ~(UInt64)(kMinSize - 1); 181 return blockSize; 182 } 183 184 185 UInt32 Get_BZip2_NumThreads(bool &fixedNumber) const 186 { 187 fixedNumber = false; 188 int numThreads = Get_NumThreads(); 189 if (numThreads >= 0) 190 { 191 fixedNumber = true; 192 if (numThreads < 1) return 1; 193 const unsigned kNumBZip2ThreadsMax = 64; 194 if (numThreads > kNumBZip2ThreadsMax) return kNumBZip2ThreadsMax; 195 return numThreads; 196 } 197 return 1; 198 } 199 200 UInt32 Get_BZip2_BlockSize() const 201 { 202 int i = FindProp(NCoderPropID::kDictionarySize); 203 if (i >= 0) 204 if (Props[i].Value.vt == VT_UI4) 205 { 206 UInt32 blockSize = Props[i].Value.ulVal; 207 const UInt32 kDicSizeMin = 100000; 208 const UInt32 kDicSizeMax = 900000; 209 if (blockSize < kDicSizeMin) blockSize = kDicSizeMin; 210 if (blockSize > kDicSizeMax) blockSize = kDicSizeMax; 211 return blockSize; 212 } 213 int level = GetLevel(); 214 return 100000 * (level >= 5 ? 9 : (level >= 1 ? level * 2 - 1: 1)); 215 } 216 217 UInt32 Get_Ppmd_MemSize() const 218 { 219 int i = FindProp(NCoderPropID::kUsedMemorySize); 220 if (i >= 0) 221 if (Props[i].Value.vt == VT_UI4) 222 return Props[i].Value.ulVal; 223 int level = GetLevel(); 224 return level >= 9 ? (192 << 20) : ((UInt32)1 << (level + 19)); 225 } 226 227 void AddProp_Level(UInt32 level) 228 { 229 AddProp32(NCoderPropID::kLevel, level); 230 } 231 232 void AddProp_NumThreads(UInt32 numThreads) 233 { 234 AddProp32(NCoderPropID::kNumThreads, numThreads); 235 } 236 237 void AddProp_EndMarker_if_NotFound(bool eos) 238 { 239 if (FindProp(NCoderPropID::kEndMarker) < 0) 240 AddPropBool(NCoderPropID::kEndMarker, eos); 241 } 242 243 HRESULT ParseParamsFromString(const UString &srcString); 244 HRESULT ParseParamsFromPROPVARIANT(const UString &realName, const PROPVARIANT &value); 245 }; 246 247 class COneMethodInfo: public CMethodProps 248 { 249 public: 250 AString MethodName; 251 UString PropsString; 252 253 void Clear() 254 { 255 CMethodProps::Clear(); 256 MethodName.Empty(); 257 PropsString.Empty(); 258 } 259 bool IsEmpty() const { return MethodName.IsEmpty() && Props.IsEmpty(); } 260 HRESULT ParseMethodFromPROPVARIANT(const UString &realName, const PROPVARIANT &value); 261 HRESULT ParseMethodFromString(const UString &s); 262 }; 263 264 #endif 265