This commit is contained in:
Igor Pavlov
2014-11-23 00:00:00 +00:00
committed by Kornel Lesiński
parent 83f8ddcc5b
commit f08f4dcc3c
1158 changed files with 76451 additions and 35082 deletions

0
CPP/Common/AutoPtr.h Executable file → Normal file
View File

View File

@@ -1,77 +0,0 @@
// Common/Buffer.h
#ifndef __COMMON_BUFFER_H
#define __COMMON_BUFFER_H
#include "Defs.h"
template <class T> class CBuffer
{
protected:
size_t _capacity;
T *_items;
public:
void Free()
{
delete []_items;
_items = 0;
_capacity = 0;
}
CBuffer(): _capacity(0), _items(0) {};
CBuffer(const CBuffer &buffer): _capacity(0), _items(0) { *this = buffer; }
CBuffer(size_t size): _items(0), _capacity(0) { SetCapacity(size); }
virtual ~CBuffer() { delete []_items; }
operator T *() { return _items; };
operator const T *() const { return _items; };
size_t GetCapacity() const { return _capacity; }
void SetCapacity(size_t newCapacity)
{
if (newCapacity == _capacity)
return;
T *newBuffer;
if (newCapacity > 0)
{
newBuffer = new T[newCapacity];
if (_capacity > 0)
memmove(newBuffer, _items, MyMin(_capacity, newCapacity) * sizeof(T));
}
else
newBuffer = 0;
delete []_items;
_items = newBuffer;
_capacity = newCapacity;
}
CBuffer& operator=(const CBuffer &buffer)
{
Free();
if (buffer._capacity > 0)
{
SetCapacity(buffer._capacity);
memmove(_items, buffer._items, buffer._capacity * sizeof(T));
}
return *this;
}
};
template <class T>
bool operator==(const CBuffer<T>& b1, const CBuffer<T>& b2)
{
if (b1.GetCapacity() != b2.GetCapacity())
return false;
for (size_t i = 0; i < b1.GetCapacity(); i++)
if (b1[i] != b2[i])
return false;
return true;
}
template <class T>
bool operator!=(const CBuffer<T>& b1, const CBuffer<T>& b2)
{
return !(b1 == b2);
}
typedef CBuffer<char> CCharBuffer;
typedef CBuffer<wchar_t> CWCharBuffer;
typedef CBuffer<unsigned char> CByteBuffer;
#endif

0
CPP/Common/CRC.cpp Executable file → Normal file
View File

0
CPP/Common/C_FileIO.cpp Executable file → Normal file
View File

2
CPP/Common/C_FileIO.h Executable file → Normal file
View File

@@ -6,7 +6,7 @@
#include <stdio.h>
#include <sys/types.h>
#include "Types.h"
#include "MyTypes.h"
#include "MyWindows.h"
#ifdef _WIN32

0
CPP/Common/ComTry.h Executable file → Normal file
View File

277
CPP/Common/CommandLineParser.cpp Executable file → Normal file
View File

@@ -4,6 +4,20 @@
#include "CommandLineParser.h"
static bool IsString1PrefixedByString2_NoCase(const wchar_t *u, const char *a)
{
for (;;)
{
char c = *a;
if (c == 0)
return true;
if (MyCharLower_Ascii(c) != MyCharLower_Ascii(*u))
return false;
a++;
u++;
}
}
namespace NCommandLineParser {
bool SplitCommandLine(const UString &src, UString &dest1, UString &dest2)
@@ -11,13 +25,13 @@ bool SplitCommandLine(const UString &src, UString &dest1, UString &dest2)
dest1.Empty();
dest2.Empty();
bool quoteMode = false;
int i;
for (i = 0; i < src.Length(); i++)
unsigned i;
for (i = 0; i < src.Len(); i++)
{
wchar_t c = src[i];
if (c == L' ' && !quoteMode)
if ((c == L' ' || c == L'\t') && !quoteMode)
{
dest2 = src.Mid(i + 1);
dest2 = src.Ptr(i + 1);
return i != 0;
}
if (c == L'\"')
@@ -45,21 +59,18 @@ void SplitCommandLine(const UString &s, UStringVector &parts)
}
static const wchar_t kSwitchID1 = '-';
// static const wchar_t kSwitchID2 = '/';
static const char *kStopSwitchParsing = "--";
static const wchar_t kSwitchMinus = '-';
static const wchar_t *kStopSwitchParsing = L"--";
static bool IsItSwitchChar(wchar_t c)
static bool inline IsItSwitchChar(wchar_t c)
{
return (c == kSwitchID1 /*|| c == kSwitchID2 */);
return (c == '-');
}
CParser::CParser(int numSwitches):
_numSwitches(numSwitches)
CParser::CParser(unsigned numSwitches):
_numSwitches(numSwitches),
_switches(0)
{
_switches = new CSwitchResult[_numSwitches];
_switches = new CSwitchResult[numSwitches];
}
CParser::~CParser()
@@ -67,163 +78,121 @@ CParser::~CParser()
delete []_switches;
}
void CParser::ParseStrings(const CSwitchForm *switchForms,
const UStringVector &commandStrings)
{
int numCommandStrings = commandStrings.Size();
bool stopSwitch = false;
for (int i = 0; i < numCommandStrings; i++)
{
const UString &s = commandStrings[i];
if (stopSwitch)
NonSwitchStrings.Add(s);
else
if (s == kStopSwitchParsing)
stopSwitch = true;
else
if (!ParseString(s, switchForms))
NonSwitchStrings.Add(s);
}
}
// if string contains switch then function updates switch structures
// out: (string is a switch)
// if (s) contains switch then function updates switch structures
// out: true, if (s) is a switch
bool CParser::ParseString(const UString &s, const CSwitchForm *switchForms)
{
int len = s.Length();
if (len == 0)
if (s.IsEmpty() || !IsItSwitchChar(s[0]))
return false;
int pos = 0;
if (!IsItSwitchChar(s[pos]))
return false;
while (pos < len)
{
if (IsItSwitchChar(s[pos]))
pos++;
const int kNoLen = -1;
int matchedSwitchIndex = 0; // GCC Warning
int maxLen = kNoLen;
for (int switchIndex = 0; switchIndex < _numSwitches; switchIndex++)
{
int switchLen = MyStringLen(switchForms[switchIndex].IDString);
if (switchLen <= maxLen || pos + switchLen > len)
continue;
UString temp = s + pos;
temp = temp.Left(switchLen);
if (temp.CompareNoCase(switchForms[switchIndex].IDString) == 0)
// if (_strnicmp(switchForms[switchIndex].IDString, LPCSTR(s) + pos, switchLen) == 0)
{
matchedSwitchIndex = switchIndex;
maxLen = switchLen;
}
}
if (maxLen == kNoLen)
throw "maxLen == kNoLen";
CSwitchResult &matchedSwitch = _switches[matchedSwitchIndex];
const CSwitchForm &switchForm = switchForms[matchedSwitchIndex];
if ((!switchForm.Multi) && matchedSwitch.ThereIs)
throw "switch must be single";
matchedSwitch.ThereIs = true;
pos += maxLen;
int tailSize = len - pos;
NSwitchType::EEnum type = switchForm.Type;
switch(type)
unsigned pos = 1;
unsigned switchIndex = 0;
int maxLen = -1;
for (unsigned i = 0; i < _numSwitches; i++)
{
const char *key = switchForms[i].Key;
unsigned switchLen = MyStringLen(key);
if ((int)switchLen <= maxLen || pos + switchLen > s.Len())
continue;
if (IsString1PrefixedByString2_NoCase((const wchar_t *)s + pos, key))
{
case NSwitchType::kPostMinus:
{
if (tailSize == 0)
matchedSwitch.WithMinus = false;
else
{
matchedSwitch.WithMinus = (s[pos] == kSwitchMinus);
if (matchedSwitch.WithMinus)
pos++;
}
break;
}
case NSwitchType::kPostChar:
{
if (tailSize < switchForm.MinLen)
throw "switch is not full";
UString set = switchForm.PostCharSet;
const int kEmptyCharValue = -1;
if (tailSize == 0)
matchedSwitch.PostCharIndex = kEmptyCharValue;
else
{
int index = set.Find(s[pos]);
if (index < 0)
matchedSwitch.PostCharIndex = kEmptyCharValue;
else
{
matchedSwitch.PostCharIndex = index;
pos++;
}
}
break;
}
case NSwitchType::kLimitedPostString:
case NSwitchType::kUnLimitedPostString:
{
int minLen = switchForm.MinLen;
if (tailSize < minLen)
throw "switch is not full";
if (type == NSwitchType::kUnLimitedPostString)
{
matchedSwitch.PostStrings.Add(s.Mid(pos));
return true;
}
int maxLen = switchForm.MaxLen;
UString stringSwitch = s.Mid(pos, minLen);
pos += minLen;
for (int i = minLen; i < maxLen && pos < len; i++, pos++)
{
wchar_t c = s[pos];
if (IsItSwitchChar(c))
break;
stringSwitch += c;
}
matchedSwitch.PostStrings.Add(stringSwitch);
break;
}
case NSwitchType::kSimple:
break;
switchIndex = i;
maxLen = switchLen;
}
}
if (maxLen < 0)
{
ErrorMessage = "Unknown switch:";
return false;
}
pos += maxLen;
CSwitchResult &sw = _switches[switchIndex];
const CSwitchForm &form = switchForms[switchIndex];
if (!form.Multi && sw.ThereIs)
{
ErrorMessage = "Multiple instances for switch:";
return false;
}
sw.ThereIs = true;
int rem = s.Len() - pos;
if (rem < form.MinLen)
{
ErrorMessage = "Too short switch:";
return false;
}
sw.WithMinus = false;
sw.PostCharIndex = -1;
switch (form.Type)
{
case NSwitchType::kMinus:
if (rem != 0)
{
sw.WithMinus = (s[pos] == '-');
if (sw.WithMinus)
pos++;
}
break;
case NSwitchType::kChar:
if (rem != 0)
{
wchar_t c = s[pos];
if (c <= 0x7F)
{
sw.PostCharIndex = FindCharPosInString(form.PostCharSet, (char)c);
if (sw.PostCharIndex >= 0)
pos++;
}
}
break;
case NSwitchType::kString:
sw.PostStrings.Add((const wchar_t *)s + pos);
return true;
}
if (pos != s.Len())
{
ErrorMessage = "Too long switch:";
return false;
}
return true;
}
const CSwitchResult& CParser::operator[](size_t index) const
bool CParser::ParseStrings(const CSwitchForm *switchForms, const UStringVector &commandStrings)
{
return _switches[index];
}
/////////////////////////////////
// Command parsing procedures
int ParseCommand(int numCommandForms, const CCommandForm *commandForms,
const UString &commandString, UString &postString)
{
for (int i = 0; i < numCommandForms; i++)
ErrorLine.Empty();
bool stopSwitch = false;
FOR_VECTOR (i, commandStrings)
{
const UString id = commandForms[i].IDString;
if (commandForms[i].PostStringMode)
const UString &s = commandStrings[i];
if (!stopSwitch)
{
if (commandString.Find(id) == 0)
if (s.IsEqualTo(kStopSwitchParsing))
{
postString = commandString.Mid(id.Length());
return i;
stopSwitch = true;
continue;
}
if (!s.IsEmpty() && IsItSwitchChar(s[0]))
{
if (ParseString(s, switchForms))
continue;
ErrorLine = s;
return false;
}
}
else
if (commandString == id)
{
postString.Empty();
return i;
}
NonSwitchStrings.Add(s);
}
return -1;
return true;
}
}

49
CPP/Common/CommandLineParser.h Executable file → Normal file
View File

@@ -10,63 +10,54 @@ namespace NCommandLineParser {
bool SplitCommandLine(const UString &src, UString &dest1, UString &dest2);
void SplitCommandLine(const UString &s, UStringVector &parts);
namespace NSwitchType {
namespace NSwitchType
{
enum EEnum
{
kSimple,
kPostMinus,
kLimitedPostString,
kUnLimitedPostString,
kPostChar
kMinus,
kString,
kChar
};
}
struct CSwitchForm
{
const wchar_t *IDString;
NSwitchType::EEnum Type;
const char *Key;
Byte Type;
bool Multi;
int MinLen;
int MaxLen;
const wchar_t *PostCharSet;
Byte MinLen;
// int MaxLen;
const char *PostCharSet;
};
struct CSwitchResult
{
bool ThereIs;
bool WithMinus;
UStringVector PostStrings;
int PostCharIndex;
UStringVector PostStrings;
CSwitchResult(): ThereIs(false) {};
};
class CParser
{
int _numSwitches;
unsigned _numSwitches;
CSwitchResult *_switches;
bool ParseString(const UString &s, const CSwitchForm *switchForms);
public:
UStringVector NonSwitchStrings;
CParser(int numSwitches);
AString ErrorMessage;
UString ErrorLine;
CParser(unsigned numSwitches);
~CParser();
void ParseStrings(const CSwitchForm *switchForms,
const UStringVector &commandStrings);
const CSwitchResult& operator[](size_t index) const;
bool ParseStrings(const CSwitchForm *switchForms, const UStringVector &commandStrings);
const CSwitchResult& operator[](size_t index) const { return _switches[index]; }
};
/////////////////////////////////
// Command parsing procedures
struct CCommandForm
{
const wchar_t *IDString;
bool PostStringMode;
};
// Returns: Index of form and postString; -1, if there is no match
int ParseCommand(int numCommandForms, const CCommandForm *commandForms,
const UString &commandString, UString &postString);
}
#endif

13
CPP/Common/Common.h Normal file
View File

@@ -0,0 +1,13 @@
// Common.h
#ifndef __COMMON_COMMON_H
#define __COMMON_COMMON_H
#include "../../C/Compiler.h"
#include "MyWindows.h"
#include "NewHandler.h"
#define ARRAY_SIZE(a) (sizeof(a) / sizeof((a)[1]))
#endif

111
CPP/Common/CrcReg.cpp Normal file
View File

@@ -0,0 +1,111 @@
// CrcReg.cpp
#include "StdAfx.h"
#include "../../C/7zCrc.h"
#include "../../C/CpuArch.h"
#include "../Common/MyCom.h"
#include "../7zip/ICoder.h"
#include "../7zip/Common/RegisterCodec.h"
EXTERN_C_BEGIN
typedef UInt32 (MY_FAST_CALL *CRC_FUNC)(UInt32 v, const void *data, size_t size, const UInt32 *table);
extern CRC_FUNC g_CrcUpdate;
#ifdef MY_CPU_X86_OR_AMD64
UInt32 MY_FAST_CALL CrcUpdateT8(UInt32 v, const void *data, size_t size, const UInt32 *table);
#endif
#ifndef MY_CPU_BE
UInt32 MY_FAST_CALL CrcUpdateT4(UInt32 v, const void *data, size_t size, const UInt32 *table);
#endif
EXTERN_C_END
class CCrcHasher:
public IHasher,
public ICompressSetCoderProperties,
public CMyUnknownImp
{
UInt32 _crc;
CRC_FUNC _updateFunc;
bool SetFunctions(UInt32 tSize);
public:
CCrcHasher(): _crc(CRC_INIT_VAL) { SetFunctions(0); }
MY_UNKNOWN_IMP1(ICompressSetCoderProperties)
STDMETHOD_(void, Init)();
STDMETHOD_(void, Update)(const void *data, UInt32 size);
STDMETHOD_(void, Final)(Byte *digest);
STDMETHOD_(UInt32, GetDigestSize)();
STDMETHOD(SetCoderProperties)(const PROPID *propIDs, const PROPVARIANT *props, UInt32 numProps);
};
STDMETHODIMP_(void) CCrcHasher::Init()
{
_crc = CRC_INIT_VAL;
}
STDMETHODIMP_(void) CCrcHasher::Update(const void *data, UInt32 size)
{
_crc = _updateFunc(_crc, data, size, g_CrcTable);
}
STDMETHODIMP_(void) CCrcHasher::Final(Byte *digest)
{
UInt32 val = CRC_GET_DIGEST(_crc);
SetUi32(digest, val);
}
STDMETHODIMP_(UInt32) CCrcHasher::GetDigestSize()
{
return 4;
}
bool CCrcHasher::SetFunctions(UInt32 tSize)
{
_updateFunc = g_CrcUpdate;
if (tSize == 4)
{
#ifndef MY_CPU_BE
_updateFunc = CrcUpdateT4;
#endif
}
else if (tSize == 8)
{
#ifdef MY_CPU_X86_OR_AMD64
_updateFunc = CrcUpdateT8;
#else
return false;
#endif
}
return true;
}
STDMETHODIMP CCrcHasher::SetCoderProperties(const PROPID *propIDs,
const PROPVARIANT *coderProps, UInt32 numProps)
{
for (UInt32 i = 0; i < numProps; i++)
{
const PROPVARIANT &prop = coderProps[i];
if (propIDs[i] == NCoderPropID::kDefaultProp)
{
if (prop.vt != VT_UI4)
return E_INVALIDARG;
if (!SetFunctions(prop.ulVal))
return E_NOTIMPL;
}
}
return S_OK;
}
static IHasher *CreateHasher() { return new CCrcHasher(); }
static CHasherInfo g_HasherInfo = { CreateHasher, 0x1, L"CRC32", 4 };
REGISTER_HASHER(Crc32)

0
CPP/Common/Defs.h Executable file → Normal file
View File

100
CPP/Common/DynLimBuf.cpp Normal file
View File

@@ -0,0 +1,100 @@
// Common/DynLimBuf.cpp
#include "StdAfx.h"
#ifdef _WIN32
#include <windows.h>
#include <wchar.h>
#else
#include <ctype.h>
#endif
#include "DynLimBuf.h"
#include "MyString.h"
CDynLimBuf::CDynLimBuf(size_t limit)
{
_chars = 0;
_pos = 0;
_size = 0;
_sizeLimit = limit;
_error = true;
unsigned size = 1 << 4;
if (size > limit)
size = (unsigned)limit;
_chars = (Byte *)MyAlloc(size);
if (_chars)
{
_size = size;
_error = false;
}
}
CDynLimBuf & CDynLimBuf::operator+=(char c)
{
if (_error)
return *this;
if (_size == _pos)
{
size_t n = _sizeLimit - _size;
if (n == 0)
{
_error = true;
return *this;
}
if (n > _size)
n = _size;
n += _pos;
Byte *newBuf = (Byte *)MyAlloc(n);
if (!newBuf)
{
_error = true;
return *this;
}
memcpy(newBuf, _chars, _pos);
MyFree(_chars);
_chars = newBuf;
_size = n;
}
_chars[_pos++] = c;
return *this;
}
CDynLimBuf &CDynLimBuf::operator+=(const char *s)
{
if (_error)
return *this;
unsigned len = MyStringLen(s);
size_t rem = _sizeLimit - _pos;
if (rem < len)
{
len = (unsigned)rem;
_error = true;
}
if (_size - _pos < len)
{
size_t n = _pos + len;
if (n - _size < _size)
{
size_t n = _sizeLimit;
if (n - _size > _size)
n = _size * 2;
}
Byte *newBuf = (Byte *)MyAlloc(n);
if (!newBuf)
{
_error = true;
return *this;
}
memcpy(newBuf, _chars, _pos);
MyFree(_chars);
_chars = newBuf;
_size = n;
}
memcpy(_chars + _pos, s, len);
_pos += len;
return *this;
}

36
CPP/Common/DynLimBuf.h Normal file
View File

@@ -0,0 +1,36 @@
// Common/DynLimBuf.h
#ifndef __COMMON_DYN_LIM_BUF_H
#define __COMMON_DYN_LIM_BUF_H
#include <string.h>
#include "../../C/Alloc.h"
#include "MyString.h"
class CDynLimBuf
{
Byte *_chars;
size_t _pos;
size_t _size;
size_t _sizeLimit;
bool _error;
CDynLimBuf(const CDynLimBuf &s);
public:
CDynLimBuf(size_t limit) throw();
~CDynLimBuf() { MyFree(_chars); }
size_t Len() const { return _pos; }
void Empty() { _pos = 0; }
operator const Byte *() const { return _chars; }
// const char *Ptr() const { return _chars; }
CDynLimBuf &operator+=(char c) throw();
CDynLimBuf &operator+=(const char *s) throw();
};
#endif

72
CPP/Common/DynamicBuffer.h Executable file → Normal file
View File

@@ -3,48 +3,56 @@
#ifndef __COMMON_DYNAMIC_BUFFER_H
#define __COMMON_DYNAMIC_BUFFER_H
#include "Buffer.h"
template <class T> class CDynamicBuffer: public CBuffer<T>
template <class T> class CDynamicBuffer
{
void GrowLength(size_t size)
T *_items;
size_t _size;
size_t _pos;
CDynamicBuffer(const CDynamicBuffer &buffer);
void operator=(const CDynamicBuffer &buffer);
void Grow(size_t size)
{
size_t delta;
if (this->_capacity > 64)
delta = this->_capacity / 4;
else if (this->_capacity > 8)
delta = 16;
else
delta = 4;
delta = MyMax(delta, size);
size_t newCap = this->_capacity + delta;
size_t delta = _size >= 64 ? _size : 64;
if (delta < size)
delta = size;
size_t newCap = _size + delta;
if (newCap < delta)
newCap = this->_capacity + size;
SetCapacity(newCap);
}
public:
CDynamicBuffer(): CBuffer<T>() {};
CDynamicBuffer(const CDynamicBuffer &buffer): CBuffer<T>(buffer) {};
CDynamicBuffer(size_t size): CBuffer<T>(size) {};
CDynamicBuffer& operator=(const CDynamicBuffer &buffer)
{
this->Free();
if (buffer._capacity > 0)
{
SetCapacity(buffer._capacity);
memmove(this->_items, buffer._items, buffer._capacity * sizeof(T));
newCap = _size + size;
if (newCap < size)
throw 20120116;
}
return *this;
T *newBuffer = new T[newCap];
memcpy(newBuffer, _items, _pos * sizeof(T));
delete []_items;
_items = newBuffer;
_size = newCap;
}
void EnsureCapacity(size_t capacity)
public:
CDynamicBuffer(): _items(0), _size(0), _pos(0) {}
// operator T *() { return _items; };
operator const T *() const { return _items; };
~CDynamicBuffer() { delete []_items; }
T *GetCurPtrAndGrow(size_t addSize)
{
if (this->_capacity < capacity)
GrowLength(capacity - this->_capacity);
size_t rem = _size - _pos;
if (rem < addSize)
Grow(addSize - rem);
T *res = _items + _pos;
_pos += addSize;
return res;
}
const size_t GetPos() const { return _pos; }
// void Empty() { _pos = 0; }
};
typedef CDynamicBuffer<char> CCharDynamicBuffer;
typedef CDynamicBuffer<wchar_t> CWCharDynamicBuffer;
typedef CDynamicBuffer<unsigned char> CByteDynamicBuffer;
#endif

165
CPP/Common/IntToString.cpp Executable file → Normal file
View File

@@ -4,74 +4,143 @@
#include "IntToString.h"
void ConvertUInt64ToString(UInt64 value, char *s, UInt32 base)
#define CONVERT_INT_TO_STR(charType, tempSize) \
unsigned char temp[tempSize]; unsigned i = 0; \
while (val >= 10) { temp[i++] = (unsigned char)('0' + (unsigned)(val % 10)); val /= 10; } \
*s++ = (charType)('0' + (unsigned)val); \
while (i != 0) { i--; *s++ = temp[i]; } \
*s = 0;
void ConvertUInt32ToString(UInt32 val, char *s)
{
if (base < 2 || base > 36)
CONVERT_INT_TO_STR(char, 16);
}
void ConvertUInt64ToString(UInt64 val, char *s)
{
if (val <= (UInt32)0xFFFFFFFF)
{
*s = '\0';
ConvertUInt32ToString((UInt32)val, s);
return;
}
char temp[72];
int pos = 0;
do
{
int delta = (int)(value % base);
temp[pos++] = (char)((delta < 10) ? ('0' + delta) : ('a' + (delta - 10)));
value /= base;
}
while (value != 0);
do
*s++ = temp[--pos];
while (pos > 0);
*s = '\0';
CONVERT_INT_TO_STR(char, 24);
}
void ConvertUInt64ToString(UInt64 value, wchar_t *s)
void ConvertUInt64ToOct(UInt64 val, char *s)
{
wchar_t temp[32];
int pos = 0;
UInt64 v = val;
unsigned i;
for (i = 1;; i++)
{
v >>= 3;
if (v == 0)
break;
}
s[i] = 0;
do
{
temp[pos++] = (wchar_t)(L'0' + (int)(value % 10));
value /= 10;
unsigned t = (unsigned)(val & 0x7);
val >>= 3;
s[--i] = (char)('0' + t);
}
while (value != 0);
do
*s++ = temp[--pos];
while (pos > 0);
*s = L'\0';
while (i);
}
void ConvertUInt32ToString(UInt32 value, char *s) { ConvertUInt64ToString(value, s); }
void ConvertUInt32ToString(UInt32 value, wchar_t *s) { ConvertUInt64ToString(value, s); }
void ConvertInt64ToString(Int64 value, char *s)
void ConvertUInt32ToHex(UInt32 val, char *s)
{
if (value < 0)
UInt32 v = val;
unsigned i;
for (i = 1;; i++)
{
v >>= 4;
if (v == 0)
break;
}
s[i] = 0;
do
{
unsigned t = (unsigned)((val & 0xF));
val >>= 4;
s[--i] = (char)((t < 10) ? ('0' + t) : ('A' + (t - 10)));
}
while (i);
}
void ConvertUInt64ToHex(UInt64 val, char *s)
{
UInt64 v = val;
unsigned i;
for (i = 1;; i++)
{
v >>= 4;
if (v == 0)
break;
}
s[i] = 0;
do
{
unsigned t = (unsigned)((val & 0xF));
val >>= 4;
s[--i] = (char)((t < 10) ? ('0' + t) : ('A' + (t - 10)));
}
while (i);
}
void ConvertUInt32ToHex8Digits(UInt32 val, char *s)
{
s[8] = 0;
for (int i = 7; i >= 0; i--)
{
unsigned t = val & 0xF;
val >>= 4;
s[i] = (char)(((t < 10) ? ('0' + t) : ('A' + (t - 10))));
}
}
/*
void ConvertUInt32ToHex8Digits(UInt32 val, wchar_t *s)
{
s[8] = 0;
for (int i = 7; i >= 0; i--)
{
unsigned t = val & 0xF;
val >>= 4;
s[i] = (wchar_t)(((t < 10) ? ('0' + t) : ('A' + (t - 10))));
}
}
*/
void ConvertUInt32ToString(UInt32 val, wchar_t *s)
{
CONVERT_INT_TO_STR(wchar_t, 16);
}
void ConvertUInt64ToString(UInt64 val, wchar_t *s)
{
if (val <= (UInt32)0xFFFFFFFF)
{
ConvertUInt32ToString((UInt32)val, s);
return;
}
CONVERT_INT_TO_STR(wchar_t, 24);
}
void ConvertInt64ToString(Int64 val, char *s)
{
if (val < 0)
{
*s++ = '-';
value = -value;
val = -val;
}
ConvertUInt64ToString(value, s);
ConvertUInt64ToString(val, s);
}
void ConvertInt64ToString(Int64 value, wchar_t *s)
void ConvertInt64ToString(Int64 val, wchar_t *s)
{
if (value < 0)
if (val < 0)
{
*s++ = L'-';
value = -value;
val = -val;
}
ConvertUInt64ToString(value, s);
}
void ConvertUInt32ToHexWithZeros(UInt32 value, char *s)
{
for (int i = 0; i < 8; i++)
{
int t = value & 0xF;
value >>= 4;
s[7 - i] = (char)((t < 10) ? ('0' + t) : ('A' + (t - 10)));
}
s[8] = '\0';
ConvertUInt64ToString(val, s);
}

23
CPP/Common/IntToString.h Executable file → Normal file
View File

@@ -3,17 +3,22 @@
#ifndef __COMMON_INT_TO_STRING_H
#define __COMMON_INT_TO_STRING_H
#include <stddef.h>
#include "Types.h"
#include "MyTypes.h"
void ConvertUInt64ToString(UInt64 value, char *s, UInt32 base = 10);
void ConvertUInt64ToString(UInt64 value, wchar_t *s);
void ConvertInt64ToString(Int64 value, char *s);
void ConvertInt64ToString(Int64 value, wchar_t *s);
void ConvertUInt32ToString(UInt32 value, char *s) throw();
void ConvertUInt64ToString(UInt64 value, char *s) throw();
void ConvertUInt32ToString(UInt32 value, char *s);
void ConvertUInt32ToString(UInt32 value, wchar_t *s);
void ConvertUInt32ToString(UInt32 value, wchar_t *s) throw();
void ConvertUInt64ToString(UInt64 value, wchar_t *s) throw();
void ConvertUInt32ToHexWithZeros(UInt32 value, char *s);
void ConvertUInt64ToOct(UInt64 value, char *s) throw();
void ConvertUInt32ToHex(UInt32 value, char *s) throw();
void ConvertUInt64ToHex(UInt64 value, char *s) throw();
void ConvertUInt32ToHex8Digits(UInt32 value, char *s) throw();
// void ConvertUInt32ToHex8Digits(UInt32 value, wchar_t *s) throw();
void ConvertInt64ToString(Int64 value, char *s) throw();
void ConvertInt64ToString(Int64 value, wchar_t *s) throw();
#endif

210
CPP/Common/Lang.cpp Executable file → Normal file
View File

@@ -3,54 +3,115 @@
#include "StdAfx.h"
#include "Lang.h"
#include "TextConfig.h"
#include "StringToInt.h"
#include "UTFConvert.h"
#include "../Windows/FileIO.h"
#include "UTFConvert.h"
#include "Defs.h"
static bool HexStringToNumber(const UString &s, UInt32 &value)
void CLang::Clear()
{
value = 0;
delete []_text;
_text = 0;
_ids.Clear();
_offsets.Clear();
}
static const wchar_t *kLangSignature = L";!@Lang2@!UTF-8!";
bool CLang::OpenFromString(const AString &s2)
{
UString s;
if (!ConvertUTF8ToUnicode(s2, s))
return false;
unsigned i = 0;
if (s.IsEmpty())
return false;
for (int i = 0; i < s.Length(); i++)
if (s[0] == 0xFEFF)
i++;
for (const wchar_t *p = kLangSignature;; i++)
{
wchar_t c = s[i];
int a;
if (c >= L'0' && c <= L'9')
a = c - L'0';
else if (c >= L'A' && c <= L'F')
a = 10 + c - L'A';
else if (c >= L'a' && c <= L'f')
a = 10 + c - L'a';
else
wchar_t c = *p++;
if (c == 0)
break;
if (s[i] != c)
return false;
value *= 0x10;
value += a;
}
_text = new wchar_t[s.Len() - i + 1];
wchar_t *text = _text;
Int32 id = -100;
UInt32 pos = 0;
while (i < s.Len())
{
unsigned start = pos;
do
{
wchar_t c = s[i++];
if (c == '\n')
break;
if (c == '\\')
{
if (i == s.Len())
return false;
c = s[i++];
switch (c)
{
case '\n': return false;
case 'n': c = '\n'; break;
case 't': c = '\t'; break;
case '\\': c = '\\'; break;
default: text[pos++] = L'\\'; break;
}
}
text[pos++] = c;
}
while (i < s.Len());
{
unsigned j = start;
for (; j < pos; j++)
if (text[j] != ' ')
break;
if (j == pos)
{
id++;
continue;
}
}
if (text[start] == ';')
{
pos = start;
id++;
continue;
}
text[pos++] = 0;
const wchar_t *end;
UInt32 id32 = ConvertStringToUInt32(text + start, &end);
if (*end == 0)
{
if (id32 > ((UInt32)1 << 30) || (Int32)id32 < id)
return false;
id = (Int32)id32;
pos = start;
continue;
}
if (id < 0)
return false;
_ids.Add((UInt32)id++);
_offsets.Add(start);
}
return true;
}
static bool WaitNextLine(const AString &s, int &pos)
bool CLang::Open(CFSTR fileName, const wchar_t *id)
{
for (; pos < s.Length(); pos++)
if (s[pos] == 0x0A)
return true;
return false;
}
static int CompareLangItems(void *const *elem1, void *const *elem2, void *)
{
const CLangPair &langPair1 = *(*((const CLangPair **)elem1));
const CLangPair &langPair2 = *(*((const CLangPair **)elem2));
return MyCompare(langPair1.Value, langPair2.Value);
}
bool CLang::Open(CFSTR fileName)
{
_langPairs.Clear();
Clear();
NWindows::NFile::NIO::CInFile file;
if (!file.Open(fileName))
return false;
@@ -60,71 +121,38 @@ bool CLang::Open(CFSTR fileName)
if (length > (1 << 20))
return false;
AString s;
char *p = s.GetBuffer((int)length + 1);
unsigned len = (unsigned)length;
char *p = s.GetBuffer(len);
UInt32 processed;
if (!file.Read(p, (UInt32)length, processed))
if (!file.Read(p, len, processed))
return false;
p[(UInt32)length] = 0;
s.ReleaseBuffer();
file.Close();
int pos = 0;
if (s.Length() >= 3)
if (len != processed)
return false;
char *p2 = p;
for (unsigned i = 0; i < len; i++)
{
if (Byte(s[0]) == 0xEF && Byte(s[1]) == 0xBB && Byte(s[2]) == 0xBF)
pos += 3;
char c = p[i];
if (c == 0)
break;
if (c != 0x0D)
*p2++ = c;
}
/////////////////////
// read header
AString stringID = ";!@Lang@!UTF-8!";
if (s.Mid(pos, stringID.Length()) != stringID)
return false;
pos += stringID.Length();
if (!WaitNextLine(s, pos))
return false;
CObjectVector<CTextConfigPair> pairs;
if (!GetTextConfig(s.Mid(pos), pairs))
return false;
_langPairs.Reserve(pairs.Size());
for (int i = 0; i < pairs.Size(); i++)
s.ReleaseBuffer((unsigned)(p2 - p));
if (OpenFromString(s))
{
CTextConfigPair textConfigPair = pairs[i];
CLangPair langPair;
if (!HexStringToNumber(textConfigPair.ID, langPair.Value))
return false;
langPair.String = textConfigPair.String;
_langPairs.Add(langPair);
const wchar_t *s = Get(0);
if (s && wcscmp(s, id) == 0)
return true;
}
_langPairs.Sort(CompareLangItems, NULL);
return true;
Clear();
return false;
}
int CLang::FindItem(UInt32 value) const
const wchar_t *CLang::Get(UInt32 id) const
{
int left = 0, right = _langPairs.Size();
while (left != right)
{
UInt32 mid = (left + right) / 2;
UInt32 midValue = _langPairs[mid].Value;
if (value == midValue)
return mid;
if (value < midValue)
right = mid;
else
left = mid + 1;
}
return -1;
}
bool CLang::GetMessage(UInt32 value, UString &message) const
{
int index = FindItem(value);
int index = _ids.FindInSorted(id);
if (index < 0)
return false;
message = _langPairs[index].String;
return true;
return NULL;
return _text + (size_t)_offsets[index];
}

24
CPP/Common/Lang.h Executable file → Normal file
View File

@@ -4,24 +4,20 @@
#define __COMMON_LANG_H
#include "MyString.h"
#include "Types.h"
struct CLangPair
{
UInt32 Value;
UString String;
};
class CLang
{
CObjectVector<CLangPair> _langPairs;
wchar_t *_text;
CRecordVector<UInt32> _ids;
CRecordVector<UInt32> _offsets;
bool OpenFromString(const AString &s);
public:
bool Open(CFSTR fileName);
void Clear() { _langPairs.Clear(); }
int FindItem(UInt32 value) const;
bool GetMessage(UInt32 value, UString &message) const;
CLang(): _text(0) {}
~CLang() { Clear(); };
bool Open(CFSTR fileName, const wchar_t *id);
void Clear() throw();
const wchar_t *Get(UInt32 id) const throw();
};
#endif

127
CPP/Common/ListFileUtils.cpp Executable file → Normal file
View File

@@ -2,75 +2,116 @@
#include "StdAfx.h"
#include "MyWindows.h"
#include "../../C/CpuArch.h"
#include "../Windows/FileIO.h"
#include "ListFileUtils.h"
#include "MyBuffer.h"
#include "StringConvert.h"
#include "UTFConvert.h"
static const char kQuoteChar = '\"';
static void RemoveQuote(UString &s)
static void AddName(UStringVector &strings, UString &s)
{
if (s.Length() >= 2)
if (s[0] == kQuoteChar && s.Back() == kQuoteChar)
s = s.Mid(1, s.Length() - 2);
s.Trim();
if (s.Len() >= 2 && s[0] == kQuoteChar && s.Back() == kQuoteChar)
{
s.DeleteBack();
s.Delete(0);
}
if (!s.IsEmpty())
strings.Add(s);
}
bool ReadNamesFromListFile(CFSTR fileName, UStringVector &resultStrings, UINT codePage)
bool ReadNamesFromListFile(CFSTR fileName, UStringVector &strings, UINT codePage)
{
NWindows::NFile::NIO::CInFile file;
if (!file.Open(fileName))
return false;
UInt64 length;
if (!file.GetLength(length))
UInt64 fileSize;
if (!file.GetLength(fileSize))
return false;
if (length > ((UInt32)1 << 31))
if (fileSize >= ((UInt32)1 << 31) - 32)
return false;
AString s;
char *p = s.GetBuffer((int)length + 1);
UInt32 processed;
if (!file.Read(p, (UInt32)length, processed))
return false;
p[(UInt32)length] = 0;
s.ReleaseBuffer();
file.Close();
UString u;
#ifdef CP_UTF8
if (codePage == CP_UTF8)
if (codePage == MY__CP_UTF16 || codePage == MY__CP_UTF16BE)
{
if (!ConvertUTF8ToUnicode(s, u))
if ((fileSize & 1) != 0)
return false;
CByteArr buf((size_t)fileSize);
UInt32 processed;
if (!file.Read(buf, (UInt32)fileSize, processed))
return false;
if (processed != fileSize)
return false;
file.Close();
unsigned num = (unsigned)fileSize / 2;
wchar_t *p = u.GetBuffer(num);
if (codePage == MY__CP_UTF16)
for (unsigned i = 0; i < num; i++)
{
wchar_t c = GetUi16(buf + i * 2);
if (c == 0)
return false;
p[i] = c;
}
else
for (unsigned i = 0; i < num; i++)
{
wchar_t c = (wchar_t)GetBe16(buf + i * 2);
if (c == 0)
return false;
p[i] = c;
}
u.ReleaseBuffer(num);
}
else
#endif
u = MultiByteToUnicodeString(s, codePage);
if (!u.IsEmpty())
{
if (u[0] == 0xFEFF)
u.Delete(0);
}
UString t;
for (int i = 0; i < u.Length(); i++)
{
wchar_t c = u[i];
if (c == L'\n' || c == 0xD)
AString s;
char *p = s.GetBuffer((unsigned)fileSize);
UInt32 processed;
if (!file.Read(p, (UInt32)fileSize, processed))
return false;
if (processed != fileSize)
return false;
file.Close();
p[processed] = 0;
s.ReleaseBuffer();
if (s.Len() != processed)
return false;
// #ifdef CP_UTF8
if (codePage == CP_UTF8)
{
t.Trim();
RemoveQuote(t);
if (!t.IsEmpty())
resultStrings.Add(t);
t.Empty();
if (!ConvertUTF8ToUnicode(s, u))
return false;
}
else
t += c;
// #endif
MultiByteToUnicodeString2(u, s, codePage);
}
t.Trim();
RemoveQuote(t);
if (!t.IsEmpty())
resultStrings.Add(t);
const wchar_t kGoodBOM = 0xFEFF;
const wchar_t kBadBOM = 0xFFFE;
UString s;
unsigned i = 0;
for (; i < u.Len() && u[i] == kGoodBOM; i++);
for (; i < u.Len(); i++)
{
wchar_t c = u[i];
if (c == kGoodBOM || c == kBadBOM)
return false;
if (c == L'\n' || c == 0xD)
{
AddName(strings, s);
s.Empty();
}
else
s += c;
}
AddName(strings, s);
return true;
}

5
CPP/Common/ListFileUtils.h Executable file → Normal file
View File

@@ -4,7 +4,10 @@
#define __COMMON_LIST_FILE_UTILS_H
#include "MyString.h"
#include "Types.h"
#include "MyTypes.h"
#define MY__CP_UTF16 1200
#define MY__CP_UTF16BE 1201
bool ReadNamesFromListFile(CFSTR fileName, UStringVector &strings, UINT codePage = CP_OEMCP);

237
CPP/Common/MyBuffer.h Normal file
View File

@@ -0,0 +1,237 @@
// Common/MyBuffer.h
#ifndef __COMMON_MY_BUFFER_H
#define __COMMON_MY_BUFFER_H
#include "Defs.h"
template <class T> class CBuffer
{
T *_items;
size_t _size;
void CopyToEmpty(const CBuffer &buffer)
{
if (buffer._size > 0)
{
_items = new T[buffer._size];
memcpy(_items, buffer._items, buffer._size * sizeof(T));
_size = buffer._size;
}
}
public:
void Free()
{
if (_items)
{
delete []_items;
_items = 0;
}
_size = 0;
}
CBuffer(): _items(0), _size(0) {};
CBuffer(size_t size): _items(0), _size(0) { _items = new T[size]; _size = size; }
CBuffer(const CBuffer &buffer): _items(0), _size(0) { CopyToEmpty(buffer); }
~CBuffer() { delete []_items; }
operator T *() { return _items; };
operator const T *() const { return _items; };
size_t Size() const { return _size; }
void Alloc(size_t size)
{
if (size != _size)
{
Free();
if (size != 0)
{
_items = new T[size];
_size = size;
}
}
}
void AllocAtLeast(size_t size)
{
if (size > _size)
{
Free();
_items = new T[size];
_size = size;
}
}
void CopyFrom(const T *data, size_t size)
{
Alloc(size);
memcpy(_items, data, size * sizeof(T));
}
void ChangeSize_KeepData(size_t newSize, size_t keepSize)
{
if (newSize == _size)
return;
T *newBuffer = NULL;
if (newSize > 0)
{
newBuffer = new T[newSize];
if (_size > 0)
memcpy(newBuffer, _items, MyMin(MyMin(_size, keepSize), newSize) * sizeof(T));
}
delete []_items;
_items = newBuffer;
_size = newSize;
}
CBuffer& operator=(const CBuffer &buffer)
{
Free();
CopyToEmpty(buffer);
return *this;
}
};
template <class T>
bool operator==(const CBuffer<T>& b1, const CBuffer<T>& b2)
{
size_t size1 = b1.Size();
if (size1 != b2.Size())
return false;
return memcmp(b1, b2, size1 * sizeof(T)) == 0;
}
template <class T>
bool operator!=(const CBuffer<T>& b1, const CBuffer<T>& b2)
{
size_t size1 = b1.Size();
if (size1 == b2.Size())
return false;
return memcmp(b1, b2, size1 * sizeof(T)) != 0;
}
typedef CBuffer<char> CCharBuffer;
typedef CBuffer<wchar_t> CWCharBuffer;
typedef CBuffer<unsigned char> CByteBuffer;
template <class T> class CObjArray
{
protected:
T *_items;
private:
// we disable constructors
CObjArray(const CObjArray &buffer);
void operator=(const CObjArray &buffer);
public:
void Free()
{
delete []_items;
_items = 0;
}
CObjArray(size_t size): _items(0) { if (size != 0) _items = new T[size]; }
CObjArray(): _items(0) {};
~CObjArray() { delete []_items; }
operator T *() { return _items; };
operator const T *() const { return _items; };
void Alloc(size_t newSize)
{
delete []_items;
_items = 0;
_items = new T[newSize];
}
};
typedef CObjArray<unsigned char> CByteArr;
typedef CObjArray<bool> CBoolArr;
typedef CObjArray<int> CIntArr;
// #define CRecArray CObjArray
template <class T> class CObjArray2
{
// protected:
T *_items;
unsigned _size;
CObjArray2(const CObjArray2 &buffer);
void operator=(const CObjArray2 &buffer);
public:
void Free()
{
delete []_items;
_items = 0;
_size = 0;
}
CObjArray2(): _items(0), _size(0) {};
/*
CObjArray2(const CObjArray2 &buffer): _items(0), _size(0)
{
size_t newSize = buffer._size;
if (newSize > 0)
{
T *newBuffer = new T[newSize];;
_items = newBuffer;
_size = newSize;
const T *src = buffer;
for (size_t i = 0; i < newSize; i++)
newBuffer[i] = src[i];
}
}
*/
/*
CObjArray2(size_t size): _items(0), _size(0)
{
if (size != 0)
{
_items = new T[size];
_size = size;
}
}
*/
~CObjArray2() { delete []_items; }
operator T *() { return _items; };
operator const T *() const { return _items; };
unsigned Size() const { return (unsigned)_size; }
bool IsEmpty() const { return _size == 0; }
// SetSize doesn't keep old items. It allocates new array if size is not equal
void SetSize(unsigned size)
{
if (size == _size)
return;
T *newBuffer = NULL;
if (size > 0)
newBuffer = new T[size];
delete []_items;
_items = newBuffer;
_size = size;
}
/*
CObjArray2& operator=(const CObjArray2 &buffer)
{
Free();
size_t newSize = buffer._size;
if (newSize > 0)
{
T *newBuffer = new T[newSize];;
_items = newBuffer;
_size = newSize;
const T *src = buffer;
for (size_t i = 0; i < newSize; i++)
newBuffer[i] = src[i];
}
return *this;
}
*/
};
#endif

63
CPP/Common/MyCom.h Executable file → Normal file
View File

@@ -1,9 +1,10 @@
// MyCom.h
#ifndef __MYCOM_H
#define __MYCOM_H
#ifndef __MY_COM_H
#define __MY_COM_H
#include "MyWindows.h"
#include "NewHandler.h"
#ifndef RINOK
#define RINOK(x) { HRESULT __result_ = (x); if (__result_ != S_OK) return __result_; }
@@ -14,14 +15,9 @@ class CMyComPtr
{
T* _p;
public:
// typedef T _PtrClass;
CMyComPtr() { _p = NULL;}
CMyComPtr(T* p) {if ((_p = p) != NULL) p->AddRef(); }
CMyComPtr(const CMyComPtr<T>& lp)
{
if ((_p = lp._p) != NULL)
_p->AddRef();
}
CMyComPtr(): _p(NULL) {}
CMyComPtr(T* p) throw() { if ((_p = p) != NULL) p->AddRef(); }
CMyComPtr(const CMyComPtr<T>& lp) throw() { if ((_p = lp._p) != NULL) _p->AddRef(); }
~CMyComPtr() { if (_p) _p->Release(); }
void Release() { if (_p) { _p->Release(); _p = NULL; } }
operator T*() const { return (T*)_p; }
@@ -30,7 +26,7 @@ public:
T* operator->() const { return _p; }
T* operator=(T* p)
{
if (p != 0)
if (p)
p->AddRef();
if (_p)
_p->Release();
@@ -40,7 +36,6 @@ public:
T* operator=(const CMyComPtr<T>& lp) { return (*this = lp._p); }
bool operator!() const { return (_p == NULL); }
// bool operator==(T* pT) const { return _p == pT; }
// Compare two objects for equivalence
void Attach(T* p2)
{
Release();
@@ -70,7 +65,7 @@ public:
}
*/
template <class Q>
HRESULT QueryInterface(REFGUID iid, Q** pp) const
HRESULT QueryInterface(REFGUID iid, Q** pp) const throw()
{
return _p->QueryInterface(iid, (void**)pp);
}
@@ -81,13 +76,14 @@ public:
inline HRESULT StringToBstr(LPCOLESTR src, BSTR *bstr)
{
*bstr = ::SysAllocString(src);
return (*bstr != 0) ? S_OK : E_OUTOFMEMORY;
return (*bstr != NULL) ? S_OK : E_OUTOFMEMORY;
}
class CMyComBSTR
{
public:
BSTR m_str;
public:
CMyComBSTR(): m_str(NULL) {}
CMyComBSTR(LPCOLESTR src) { m_str = ::SysAllocString(src); }
// CMyComBSTR(int nSize) { m_str = ::SysAllocStringLen(NULL, nSize); }
@@ -119,7 +115,7 @@ public:
m_str = ::SysAllocString(src);
return *this;
}
unsigned int Length() const { return ::SysStringLen(m_str); }
// unsigned Len() const { return ::SysStringLen(m_str); }
operator BSTR() const { return m_str; }
BSTR* operator&() { return &m_str; }
BSTR MyCopy() const
@@ -143,7 +139,7 @@ public:
::SysFreeString(m_str);
m_str = NULL;
}
bool operator!() const { return (m_str == NULL); }
bool operator!() const { return (m_str == NULL); }
};
//////////////////////////////////////////////////////////
@@ -156,22 +152,22 @@ public:
};
#define MY_QUERYINTERFACE_BEGIN STDMETHOD(QueryInterface) \
(REFGUID iid, void **outObject) {
(REFGUID iid, void **outObject) throw() { *outObject = NULL;
#define MY_QUERYINTERFACE_ENTRY(i) if (iid == IID_ ## i) \
{ *outObject = (void *)(i *)this; AddRef(); return S_OK; }
#define MY_QUERYINTERFACE_ENTRY(i) else if (iid == IID_ ## i) \
{ *outObject = (void *)(i *)this; }
#define MY_QUERYINTERFACE_ENTRY_UNKNOWN(i) if (iid == IID_IUnknown) \
{ *outObject = (void *)(IUnknown *)(i *)this; AddRef(); return S_OK; }
{ *outObject = (void *)(IUnknown *)(i *)this; }
#define MY_QUERYINTERFACE_BEGIN2(i) MY_QUERYINTERFACE_BEGIN \
MY_QUERYINTERFACE_ENTRY_UNKNOWN(i) \
MY_QUERYINTERFACE_ENTRY(i)
#define MY_QUERYINTERFACE_END return E_NOINTERFACE; }
#define MY_QUERYINTERFACE_END else return E_NOINTERFACE; AddRef(); return S_OK; }
#define MY_ADDREF_RELEASE \
STDMETHOD_(ULONG, AddRef)() { return ++__m_RefCount; } \
STDMETHOD_(ULONG, AddRef)() throw() { return ++__m_RefCount; } \
STDMETHOD_(ULONG, Release)() { if (--__m_RefCount != 0) \
return __m_RefCount; delete this; return 0; }
@@ -222,4 +218,25 @@ STDMETHOD_(ULONG, Release)() { if (--__m_RefCount != 0) \
MY_QUERYINTERFACE_ENTRY(i5) \
)
#define MY_UNKNOWN_IMP6(i1, i2, i3, i4, i5, i6) MY_UNKNOWN_IMP_SPEC( \
MY_QUERYINTERFACE_ENTRY_UNKNOWN(i1) \
MY_QUERYINTERFACE_ENTRY(i1) \
MY_QUERYINTERFACE_ENTRY(i2) \
MY_QUERYINTERFACE_ENTRY(i3) \
MY_QUERYINTERFACE_ENTRY(i4) \
MY_QUERYINTERFACE_ENTRY(i5) \
MY_QUERYINTERFACE_ENTRY(i6) \
)
#define MY_UNKNOWN_IMP7(i1, i2, i3, i4, i5, i6, i7) MY_UNKNOWN_IMP_SPEC( \
MY_QUERYINTERFACE_ENTRY_UNKNOWN(i1) \
MY_QUERYINTERFACE_ENTRY(i1) \
MY_QUERYINTERFACE_ENTRY(i2) \
MY_QUERYINTERFACE_ENTRY(i3) \
MY_QUERYINTERFACE_ENTRY(i4) \
MY_QUERYINTERFACE_ENTRY(i5) \
MY_QUERYINTERFACE_ENTRY(i6) \
MY_QUERYINTERFACE_ENTRY(i7) \
)
#endif

0
CPP/Common/MyException.h Executable file → Normal file
View File

2
CPP/Common/MyGuidDef.h Executable file → Normal file
View File

@@ -3,7 +3,7 @@
#ifndef GUID_DEFINED
#define GUID_DEFINED
#include "Types.h"
#include "MyTypes.h"
typedef struct {
UInt32 Data1;

0
CPP/Common/MyInitGuid.h Executable file → Normal file
View File

14
CPP/Common/MyMap.cpp Executable file → Normal file
View File

@@ -6,7 +6,7 @@
static const unsigned kNumBitsMax = sizeof(UInt32) * 8;
static UInt32 GetSubBits(UInt32 value, unsigned startPos, unsigned numBits)
static UInt32 GetSubBits(UInt32 value, unsigned startPos, unsigned numBits) throw()
{
if (startPos == sizeof(value) * 8)
return 0;
@@ -33,7 +33,7 @@ bool CMap32::Find(UInt32 key, UInt32 &valueRes) const
}
}
int cur = 0;
unsigned cur = 0;
unsigned bitPos = kNumBitsMax;
for (;;)
{
@@ -47,7 +47,7 @@ bool CMap32::Find(UInt32 key, UInt32 &valueRes) const
valueRes = n.Values[bit];
return (key == n.Keys[bit]);
}
cur = (int)n.Keys[bit];
cur = (unsigned)n.Keys[bit];
}
}
@@ -74,7 +74,7 @@ bool CMap32::Set(UInt32 key, UInt32 value)
return true;
}
unsigned i = kNumBitsMax - 1;
for (;GetSubBit(key, i) == GetSubBit(n.Key, i); i--);
for (; GetSubBit(key, i) == GetSubBit(n.Key, i); i--);
n.Len = (UInt16)(kNumBitsMax - (1 + i));
unsigned newBit = GetSubBit(key, i);
n.Values[newBit] = value;
@@ -83,7 +83,7 @@ bool CMap32::Set(UInt32 key, UInt32 value)
}
}
int cur = 0;
unsigned cur = 0;
unsigned bitPos = kNumBitsMax;
for (;;)
{
@@ -117,7 +117,7 @@ bool CMap32::Set(UInt32 key, UInt32 value)
return true;
}
unsigned i = bitPos - 1;
for (;GetSubBit(key, i) == GetSubBit(n.Keys[bit], i); i--);
for (; GetSubBit(key, i) == GetSubBit(n.Keys[bit], i); i--);
CNode e2;
@@ -135,6 +135,6 @@ bool CMap32::Set(UInt32 key, UInt32 value)
Nodes.Add(e2);
return false;
}
cur = (int)n.Keys[bit];
cur = (unsigned)n.Keys[bit];
}
}

4
CPP/Common/MyMap.h Executable file → Normal file
View File

@@ -3,8 +3,8 @@
#ifndef __COMMON_MYMAP_H
#define __COMMON_MYMAP_H
#include "MyTypes.h"
#include "MyVector.h"
#include "Types.h"
class CMap32
{
@@ -21,7 +21,7 @@ class CMap32
public:
void Clear() { Nodes.Clear(); }
bool Find(UInt32 key, UInt32 &valueRes) const;
bool Find(UInt32 key, UInt32 &valueRes) const throw();
bool Set(UInt32 key, UInt32 value); // returns true, if there is such key already
};

1146
CPP/Common/MyString.cpp Executable file → Normal file
View File

File diff suppressed because it is too large Load Diff

868
CPP/Common/MyString.h Executable file → Normal file
View File

@@ -5,552 +5,468 @@
#include <string.h>
#include "Types.h"
#ifndef _WIN32
#include <wctype.h>
#include <wchar.h>
#endif
#include "MyTypes.h"
#include "MyVector.h"
template <class T>
inline int MyStringLen(const T *s)
inline unsigned MyStringLen(const char *s)
{
int i;
for (i = 0; s[i] != '\0'; i++);
unsigned i;
for (i = 0; s[i] != 0; i++);
return i;
}
template <class T>
inline void MyStringCopy(T *dest, const T *src)
inline void MyStringCopy(char *dest, const char *src)
{
while ((*dest++ = *src++) != 0);
}
int FindCharPosInString(const char *s, char c);
int FindCharPosInString(const wchar_t *s, wchar_t c);
inline wchar_t* MyStringGetNextCharPointer(wchar_t *p)
{ return (p + 1); }
inline const wchar_t* MyStringGetNextCharPointer(const wchar_t *p)
{ return (p + 1); }
inline wchar_t* MyStringGetPrevCharPointer(const wchar_t *, wchar_t *p)
{ return (p - 1); }
inline const wchar_t* MyStringGetPrevCharPointer(const wchar_t *, const wchar_t *p)
{ return (p - 1); }
wchar_t MyCharUpper(wchar_t c);
// wchar_t MyCharLower(wchar_t c);
char *MyStringUpper(char *s);
char *MyStringLower(char *s);
wchar_t *MyStringUpper(wchar_t *s);
wchar_t *MyStringLower(wchar_t *s);
const char* MyStringGetNextCharPointer(const char *p);
const char* MyStringGetPrevCharPointer(const char *base, const char *p);
//////////////////////////////////////
// Compare
int MyStringCompare(const char *s1, const char *s2);
int MyStringCompare(const wchar_t *s1, const wchar_t *s2);
int MyStringCompareNoCase(const char *s1, const char *s2);
int MyStringCompareNoCase(const wchar_t *s1, const wchar_t *s2);
template <class T>
class CStringBase
inline char *MyStpCpy(char *dest, const char *src)
{
void TrimLeftWithCharSet(const CStringBase &charSet)
for (;;)
{
const T *p = _chars;
while (charSet.Find(*p) >= 0 && (*p != 0))
p = GetNextCharPointer(p);
Delete(0, (int)(p - _chars));
Byte c = *src;
*dest = c;
if (c == 0)
return dest;
src++;
dest++;
}
void TrimRightWithCharSet(const CStringBase &charSet)
{
const T *p = _chars;
const T *pLast = NULL;
while (*p != 0)
{
if (charSet.Find(*p) >= 0)
{
if (pLast == NULL)
pLast = p;
}
else
pLast = NULL;
p = GetNextCharPointer(p);
}
if (pLast != NULL)
{
int i = (int)(pLast - _chars);
Delete(i, _length - i);
}
}
}
void MoveItems(int destIndex, int srcIndex)
inline unsigned MyStringLen(const wchar_t *s)
{
unsigned i;
for (i = 0; s[i] != 0; i++);
return i;
}
inline void MyStringCopy(wchar_t *dest, const wchar_t *src)
{
while ((*dest++ = *src++) != 0);
}
int FindCharPosInString(const char *s, char c) throw();
int FindCharPosInString(const wchar_t *s, wchar_t c) throw();
#ifdef _WIN32
#ifndef _UNICODE
#define STRING_UNICODE_THROW
#endif
#endif
#ifndef STRING_UNICODE_THROW
#define STRING_UNICODE_THROW throw()
#endif
/*
inline char MyCharUpper_Ascii(char c)
{
if (c >= 'a' && c <= 'z')
return (char)(c - 0x20);
return c;
}
inline wchar_t MyCharUpper_Ascii(wchar_t c)
{
if (c >= 'a' && c <= 'z')
return (wchar_t)(c - 0x20);
return c;
}
*/
inline char MyCharLower_Ascii(char c)
{
if (c >= 'A' && c <= 'Z')
return (char)(c + 0x20);
return c;
}
inline wchar_t MyCharLower_Ascii(wchar_t c)
{
if (c >= 'A' && c <= 'Z')
return (wchar_t)(c + 0x20);
return c;
}
wchar_t MyCharUpper_WIN(wchar_t c) throw();
inline wchar_t MyCharUpper(wchar_t c) throw()
{
if (c < 'a') return c;
if (c <= 'z') return (wchar_t)(c - 0x20);
if (c <= 0x7F) return c;
#ifdef _WIN32
#ifdef _UNICODE
return (wchar_t)(unsigned)(UINT_PTR)CharUpperW((LPWSTR)(UINT_PTR)(unsigned)c);
#else
return (wchar_t)MyCharUpper_WIN(c);
#endif
#else
return (wchar_t)towupper(c);
#endif
}
/*
wchar_t MyCharLower_WIN(wchar_t c) throw();
inline wchar_t MyCharLower(wchar_t c) throw()
{
if (c < 'A') return c;
if (c <= 'Z') return (wchar_t)(c + 0x20);
if (c <= 0x7F) return c;
#ifdef _WIN32
#ifdef _UNICODE
return (wchar_t)(unsigned)(UINT_PTR)CharLowerW((LPWSTR)(UINT_PTR)(unsigned)c);
#else
return (wchar_t)MyCharLower_WIN(c);
#endif
#else
return (wchar_t)tolower(c);
#endif
}
*/
// char *MyStringUpper(char *s) throw();
// char *MyStringLower(char *s) throw();
// void MyStringUpper_Ascii(wchar_t *s) throw();
void MyStringLower_Ascii(wchar_t *s) throw();
// wchar_t *MyStringUpper(wchar_t *s) STRING_UNICODE_THROW;
// wchar_t *MyStringLower(wchar_t *s) STRING_UNICODE_THROW;
bool StringsAreEqualNoCase(const wchar_t *s1, const wchar_t *s2) throw();
bool IsString1PrefixedByString2(const char *s1, const char *s2) throw();
bool IsString1PrefixedByString2(const wchar_t *s1, const wchar_t *s2) throw();
int MyStringCompareNoCase(const wchar_t *s1, const wchar_t *s2) throw();
int MyStringCompareNoCase_N(const wchar_t *s1, const wchar_t *s2, unsigned num) throw();
// ---------- ASCII ----------
// char values in ASCII strings must be less then 128
bool StringsAreEqual_Ascii(const wchar_t *u, const char *a) throw();
bool StringsAreEqualNoCase_Ascii(const char *s1, const char *s2) throw();
bool StringsAreEqualNoCase_Ascii(const wchar_t *s1, const char *s2) throw();
bool StringsAreEqualNoCase_Ascii(const wchar_t *s1, const wchar_t *s2) throw();
#define MY_STRING_DELETE(_p_) delete []_p_;
// #define MY_STRING_DELETE(_p_) my_delete(_p_);
class AString
{
char *_chars;
unsigned _len;
unsigned _limit;
void MoveItems(unsigned dest, unsigned src)
{
memmove(_chars + destIndex, _chars + srcIndex,
sizeof(T) * (_length - srcIndex + 1));
memmove(_chars + dest, _chars + src, (size_t)(_len - src + 1) * sizeof(char));
}
void InsertSpace(int &index, int size)
{
CorrectIndex(index);
GrowLength(size);
MoveItems(index + size, index);
}
static const T *GetNextCharPointer(const T *p)
{ return MyStringGetNextCharPointer(p); }
static const T *GetPrevCharPointer(const T *base, const T *p)
{ return MyStringGetPrevCharPointer(base, p); }
protected:
T *_chars;
int _length;
int _capacity;
void InsertSpace(unsigned &index, unsigned size);
void SetCapacity(int newCapacity)
{
int realCapacity = newCapacity + 1;
if (realCapacity == _capacity)
return;
/*
const int kMaxStringSize = 0x20000000;
if (newCapacity > kMaxStringSize || newCapacity < _length)
throw 1052337;
*/
T *newBuffer = new T[realCapacity];
if (_capacity > 0)
{
for (int i = 0; i < _length; i++)
newBuffer[i] = _chars[i];
delete []_chars;
}
_chars = newBuffer;
_chars[_length] = 0;
_capacity = realCapacity;
}
void ReAlloc(unsigned newLimit);
void SetStartLen(unsigned len);
void Grow_1();
void Grow(unsigned n);
void GrowLength(int n)
{
int freeSize = _capacity - _length - 1;
if (n <= freeSize)
return;
int delta;
if (_capacity > 64)
delta = _capacity / 2;
else if (_capacity > 8)
delta = 16;
else
delta = 4;
if (freeSize + delta < n)
delta = n - freeSize;
SetCapacity(_capacity + delta);
}
// AString(unsigned num, const char *s);
AString(unsigned num, const AString &s);
AString(const AString &s, char c); // it's for String + char
AString(const char *s1, unsigned num1, const char *s2, unsigned num2);
void CorrectIndex(int &index) const
{
if (index > _length)
index = _length;
}
friend AString operator+(const AString &s, char c) { return AString(s, c); } ;
// friend AString operator+(char c, const AString &s); // is not supported
friend AString operator+(const AString &s1, const AString &s2);
friend AString operator+(const AString &s1, const char *s2);
friend AString operator+(const char *s1, const AString &s2);
public:
CStringBase(): _chars(0), _length(0), _capacity(0) { SetCapacity(3); }
CStringBase(T c): _chars(0), _length(0), _capacity(0)
{
SetCapacity(1);
_chars[0] = c;
_chars[1] = 0;
_length = 1;
}
CStringBase(const T *chars): _chars(0), _length(0), _capacity(0)
{
int length = MyStringLen(chars);
SetCapacity(length);
MyStringCopy(_chars, chars); // can be optimized by memove()
_length = length;
}
CStringBase(const CStringBase &s): _chars(0), _length(0), _capacity(0)
{
SetCapacity(s._length);
MyStringCopy(_chars, s._chars);
_length = s._length;
}
~CStringBase() { delete []_chars; }
AString();
AString(char c);
AString(const char *s);
AString(const AString &s);
~AString() { MY_STRING_DELETE(_chars); }
operator const T*() const { return _chars;}
unsigned Len() const { return _len; }
bool IsEmpty() const { return _len == 0; }
void Empty() { _len = 0; _chars[0] = 0; }
T Back() const { return _chars[_length - 1]; }
operator const char *() const { return _chars; }
const char *Ptr() const { return _chars; }
const char *Ptr(unsigned pos) const { return _chars + pos; }
const char *RightPtr(unsigned num) const { return _chars + _len - num; }
char Back() const { return _chars[_len - 1]; }
void ReplaceOneCharAtPos(unsigned pos, char c) { _chars[pos] = c; }
// The minimum size of the character buffer in characters.
// This value does not include space for a null terminator.
T* GetBuffer(int minBufLength)
char *GetBuffer(unsigned minBufLen)
{
if (minBufLength >= _capacity)
SetCapacity(minBufLength);
if (minBufLen > _limit)
ReAlloc(minBufLen);
return _chars;
}
void ReleaseBuffer() { ReleaseBuffer(MyStringLen(_chars)); }
void ReleaseBuffer(int newLength)
{
/*
if (newLength >= _capacity)
throw 282217;
*/
_chars[newLength] = 0;
_length = newLength;
}
void ReleaseBuffer(unsigned newLen) { _len = newLen; _chars[newLen] = 0; }
CStringBase& operator=(T c)
AString &operator=(char c);
AString &operator=(const char *s);
AString &operator=(const AString &s);
AString &operator+=(char c)
{
Empty();
SetCapacity(1);
_chars[0] = c;
_chars[1] = 0;
_length = 1;
if (_limit == _len)
Grow_1();
unsigned len = _len;
char *chars = _chars;
chars[len++] = c;
chars[len] = 0;
_len = len;
return *this;
}
CStringBase& operator=(const T *chars)
{
Empty();
int length = MyStringLen(chars);
SetCapacity(length);
MyStringCopy(_chars, chars);
_length = length;
return *this;
}
CStringBase& operator=(const CStringBase& s)
{
if (&s == this)
return *this;
Empty();
SetCapacity(s._length);
MyStringCopy(_chars, s._chars);
_length = s._length;
return *this;
}
CStringBase& operator+=(T c)
{
GrowLength(1);
_chars[_length] = c;
_chars[++_length] = 0;
return *this;
}
CStringBase& operator+=(const T *s)
{
int len = MyStringLen(s);
GrowLength(len);
MyStringCopy(_chars + _length, s);
_length += len;
return *this;
}
CStringBase& operator+=(const CStringBase &s)
{
GrowLength(s._length);
MyStringCopy(_chars + _length, s._chars);
_length += s._length;
return *this;
}
void Empty()
{
_length = 0;
_chars[0] = 0;
}
int Length() const { return _length; }
bool IsEmpty() const { return (_length == 0); }
CStringBase Mid(int startIndex) const
{ return Mid(startIndex, _length - startIndex); }
CStringBase Mid(int startIndex, int count) const
{
if (startIndex + count > _length)
count = _length - startIndex;
if (startIndex == 0 && startIndex + count == _length)
return *this;
CStringBase<T> result;
result.SetCapacity(count);
// MyStringNCopy(result._chars, _chars + startIndex, count);
for (int i = 0; i < count; i++)
result._chars[i] = _chars[startIndex + i];
result._chars[count] = 0;
result._length = count;
return result;
}
CStringBase Left(int count) const
{ return Mid(0, count); }
CStringBase Right(int count) const
{
if (count > _length)
count = _length;
return Mid(_length - count, count);
}
AString &operator+=(const char *s);
AString &operator+=(const AString &s);
void MakeUpper() { MyStringUpper(_chars); }
void MakeLower() { MyStringLower(_chars); }
void SetFrom(const char *s, unsigned len); // no check
// AString Mid(unsigned startIndex, unsigned count) const { return AString(count, _chars + startIndex); }
AString Left(unsigned count) const { return AString(count, *this); }
int Compare(const CStringBase& s) const
{ return MyStringCompare(_chars, s._chars); }
// void MakeUpper() { MyStringUpper(_chars); }
// void MakeLower() { MyStringLower(_chars); }
int Compare(const T *s) const
{ return MyStringCompare(_chars, s); }
int CompareNoCase(const CStringBase& s) const
{ return MyStringCompareNoCase(_chars, s._chars); }
int CompareNoCase(const T *s) const
{ return MyStringCompareNoCase(_chars, s); }
/*
int Collate(const CStringBase& s) const
{ return MyStringCollate(_chars, s._chars); }
int CollateNoCase(const CStringBase& s) const
{ return MyStringCollateNoCase(_chars, s._chars); }
*/
int Find(T c) const { return FindCharPosInString(_chars, c); }
int Find(T c, int startIndex) const
// int Compare(const char *s) const { return MyStringCompare(_chars, s); }
// int Compare(const AString &s) const { return MyStringCompare(_chars, s._chars); }
// int CompareNoCase(const char *s) const { return MyStringCompareNoCase(_chars, s); }
// int CompareNoCase(const AString &s) const { return MyStringCompareNoCase(_chars, s._chars); }
bool IsPrefixedBy(const char *s) const { return IsString1PrefixedByString2(_chars, s); }
bool IsPrefixedBy_Ascii_NoCase(const char *s) const;
int Find(char c) const { return FindCharPosInString(_chars, c); }
int Find(char c, unsigned startIndex) const
{
int pos = FindCharPosInString(_chars + startIndex, c);
return pos < 0 ? -1 : pos + startIndex;
}
int Find(const CStringBase &s) const { return Find(s, 0); }
int Find(const CStringBase &s, int startIndex) const
{
if (s.IsEmpty())
return startIndex;
for (; startIndex < _length; startIndex++)
{
int j;
for (j = 0; j < s._length && startIndex + j < _length; j++)
if (_chars[startIndex+j] != s._chars[j])
break;
if (j == s._length)
return startIndex;
}
return -1;
}
int ReverseFind(T c) const
{
if (_length == 0)
return -1;
const T *p = _chars + _length - 1;
for (;;)
{
if (*p == c)
return (int)(p - _chars);
if (p == _chars)
return -1;
p = GetPrevCharPointer(_chars, p);
}
}
int FindOneOf(const CStringBase &s) const
{
for (int i = 0; i < _length; i++)
if (s.Find(_chars[i]) >= 0)
return i;
return -1;
return pos < 0 ? -1 : (int)startIndex + pos;
}
int ReverseFind(char c) const throw();
int Find(const AString &s) const { return Find(s, 0); }
int Find(const AString &s, unsigned startIndex) const throw();
void TrimLeft(T c)
{
const T *p = _chars;
while (c == *p)
p = GetNextCharPointer(p);
Delete(0, p - _chars);
}
private:
CStringBase GetTrimDefaultCharSet()
{
CStringBase<T> charSet;
charSet += (T)' ';
charSet += (T)'\n';
charSet += (T)'\t';
return charSet;
}
public:
void TrimLeft()
{
TrimLeftWithCharSet(GetTrimDefaultCharSet());
}
void TrimRight()
{
TrimRightWithCharSet(GetTrimDefaultCharSet());
}
void TrimRight(T c)
{
const T *p = _chars;
const T *pLast = NULL;
while (*p != 0)
{
if (*p == c)
{
if (pLast == NULL)
pLast = p;
}
else
pLast = NULL;
p = GetNextCharPointer(p);
}
if (pLast != NULL)
{
int i = pLast - _chars;
Delete(i, _length - i);
}
}
void TrimLeft() throw();
void TrimRight() throw();
void Trim()
{
TrimRight();
TrimLeft();
}
int Insert(int index, T c)
{
InsertSpace(index, 1);
_chars[index] = c;
_length++;
return _length;
}
int Insert(int index, const CStringBase &s)
{
CorrectIndex(index);
if (s.IsEmpty())
return _length;
int numInsertChars = s.Length();
InsertSpace(index, numInsertChars);
for (int i = 0; i < numInsertChars; i++)
_chars[index + i] = s[i];
_length += numInsertChars;
return _length;
}
void InsertAtFront(char c);
// void Insert(unsigned index, char c);
void Insert(unsigned index, const char *s);
void Insert(unsigned index, const AString &s);
// !!!!!!!!!!!!!!! test it if newChar = '\0'
int Replace(T oldChar, T newChar)
void RemoveChar(char ch) throw();
void Replace(char oldChar, char newChar) throw();
void Replace(const AString &oldString, const AString &newString);
void Delete(unsigned index) throw();
void Delete(unsigned index, unsigned count) throw();
void DeleteFrontal(unsigned num) throw();
void DeleteBack() { _chars[--_len] = 0; }
void DeleteFrom(unsigned index)
{
if (oldChar == newChar)
return 0;
int number = 0;
int pos = 0;
while (pos < Length())
if (index < _len)
{
pos = Find(oldChar, pos);
if (pos < 0)
break;
_chars[pos] = newChar;
pos++;
number++;
_len = index;
_chars[index] = 0;
}
return number;
}
int Replace(const CStringBase &oldString, const CStringBase &newString)
{
if (oldString.IsEmpty())
return 0;
if (oldString == newString)
return 0;
int oldStringLength = oldString.Length();
int newStringLength = newString.Length();
int number = 0;
int pos = 0;
while (pos < _length)
{
pos = Find(oldString, pos);
if (pos < 0)
break;
Delete(pos, oldStringLength);
Insert(pos, newString);
pos += newStringLength;
number++;
}
return number;
}
int Delete(int index, int count = 1)
{
if (index + count > _length)
count = _length - index;
if (count > 0)
{
MoveItems(index, index + count);
_length -= count;
}
return _length;
}
void DeleteBack() { Delete(_length - 1); }
};
template <class T>
CStringBase<T> operator+(const CStringBase<T>& s1, const CStringBase<T>& s2)
bool operator<(const AString &s1, const AString &s2);
bool operator>(const AString &s1, const AString &s2);
/*
bool operator==(const AString &s1, const AString &s2);
bool operator==(const AString &s1, const char *s2);
bool operator==(const char *s1, const AString &s2);
bool operator!=(const AString &s1, const AString &s2);
bool operator!=(const AString &s1, const char *s2);
bool operator!=(const char *s1, const AString &s2);
*/
inline bool operator==(const AString &s1, const AString &s2) { return s1.Len() == s2.Len() && strcmp(s1, s2) == 0; }
inline bool operator==(const AString &s1, const char *s2) { return strcmp(s1, s2) == 0; }
inline bool operator==(const char *s1, const AString &s2) { return strcmp(s1, s2) == 0; }
inline bool operator!=(const AString &s1, const AString &s2) { return s1.Len() != s2.Len() || strcmp(s1, s2) != 0; }
inline bool operator!=(const AString &s1, const char *s2) { return strcmp(s1, s2) != 0; }
inline bool operator!=(const char *s1, const AString &s2) { return strcmp(s1, s2) != 0; }
class UString
{
CStringBase<T> result(s1);
result += s2;
return result;
}
wchar_t *_chars;
unsigned _len;
unsigned _limit;
template <class T>
CStringBase<T> operator+(const CStringBase<T>& s, T c)
{
CStringBase<T> result(s);
result += c;
return result;
}
void MoveItems(unsigned dest, unsigned src)
{
memmove(_chars + dest, _chars + src, (size_t)(_len - src + 1) * sizeof(wchar_t));
}
void InsertSpace(unsigned index, unsigned size);
void ReAlloc(unsigned newLimit);
void SetStartLen(unsigned len);
void Grow_1();
void Grow(unsigned n);
template <class T>
CStringBase<T> operator+(T c, const CStringBase<T>& s)
{
CStringBase<T> result(c);
result += s;
return result;
}
UString(unsigned num, const wchar_t *s); // for Mid
UString(unsigned num, const UString &s); // for Left
UString(const UString &s, wchar_t c); // it's for String + char
UString(const wchar_t *s1, unsigned num1, const wchar_t *s2, unsigned num2);
template <class T>
CStringBase<T> operator+(const CStringBase<T>& s, const T * chars)
{
CStringBase<T> result(s);
result += chars;
return result;
}
friend UString operator+(const UString &s, wchar_t c) { return UString(s, c); } ;
// friend UString operator+(wchar_t c, const UString &s); // is not supported
template <class T>
CStringBase<T> operator+(const T * chars, const CStringBase<T>& s)
{
CStringBase<T> result(chars);
result += s;
return result;
}
friend UString operator+(const UString &s1, const UString &s2);
friend UString operator+(const UString &s1, const wchar_t *s2);
friend UString operator+(const wchar_t *s1, const UString &s2);
template <class T>
bool operator==(const CStringBase<T>& s1, const CStringBase<T>& s2)
{ return (s1.Compare(s2) == 0); }
public:
UString();
UString(wchar_t c);
UString(const wchar_t *s);
UString(const UString &s);
~UString() { MY_STRING_DELETE(_chars); }
template <class T>
bool operator<(const CStringBase<T>& s1, const CStringBase<T>& s2)
{ return (s1.Compare(s2) < 0); }
unsigned Len() const { return _len; }
bool IsEmpty() const { return _len == 0; }
void Empty() { _len = 0; _chars[0] = 0; }
template <class T>
bool operator==(const T *s1, const CStringBase<T>& s2)
{ return (s2.Compare(s1) == 0); }
operator const wchar_t *() const { return _chars; }
const wchar_t *Ptr() const { return _chars; }
const wchar_t *Ptr(unsigned pos) const { return _chars + pos; }
const wchar_t *RightPtr(unsigned num) const { return _chars + _len - num; }
wchar_t Back() const { return _chars[_len - 1]; }
template <class T>
bool operator==(const CStringBase<T>& s1, const T *s2)
{ return (s1.Compare(s2) == 0); }
void ReplaceOneCharAtPos(unsigned pos, wchar_t c) { _chars[pos] = c; }
template <class T>
bool operator!=(const CStringBase<T>& s1, const CStringBase<T>& s2)
{ return (s1.Compare(s2) != 0); }
// The minimum size of the character buffer in characters.
// This value does not include space for a null terminator.
wchar_t *GetBuffer(unsigned minBufLen)
{
if (minBufLen > _limit)
ReAlloc(minBufLen);
return _chars;
}
void ReleaseBuffer() { ReleaseBuffer(MyStringLen(_chars)); }
void ReleaseBuffer(unsigned newLen) { _len = newLen; _chars[newLen] = 0; }
template <class T>
bool operator!=(const T *s1, const CStringBase<T>& s2)
{ return (s2.Compare(s1) != 0); }
UString &operator=(wchar_t c);
UString &operator=(const wchar_t *s);
UString &operator=(const UString &s);
template <class T>
bool operator!=(const CStringBase<T>& s1, const T *s2)
{ return (s1.Compare(s2) != 0); }
UString &operator+=(wchar_t c)
{
if (_limit == _len)
Grow_1();
unsigned len = _len;
wchar_t *chars = _chars;
chars[len++] = c;
chars[len] = 0;
_len = len;
return *this;
}
UString &operator+=(const wchar_t *s);
UString &operator+=(const UString &s);
void SetFrom(const wchar_t *s, unsigned len); // no check
void SetFromAscii(const char *s);
void AddAsciiStr(const char *s);
UString Mid(unsigned startIndex, unsigned count) const { return UString(count, _chars + startIndex); }
UString Left(unsigned count) const { return UString(count, *this); }
// void MakeUpper() { MyStringUpper(_chars); }
// void MakeUpper() { MyStringUpper_Ascii(_chars); }
// void MakeUpper_Ascii() { MyStringUpper_Ascii(_chars); }
void MakeLower_Ascii() { MyStringLower_Ascii(_chars); }
bool IsEqualTo(const char *s) const { return StringsAreEqual_Ascii(_chars, s); }
bool IsEqualToNoCase(const wchar_t *s) const { return StringsAreEqualNoCase(_chars, s); }
int Compare(const wchar_t *s) const { return wcscmp(_chars, s); }
// int Compare(const UString &s) const { return MyStringCompare(_chars, s._chars); }
// int CompareNoCase(const wchar_t *s) const { return MyStringCompareNoCase(_chars, s); }
// int CompareNoCase(const UString &s) const { return MyStringCompareNoCase(_chars, s._chars); }
bool IsPrefixedBy(const wchar_t *s) const { return IsString1PrefixedByString2(_chars, s); };
bool IsPrefixedBy_Ascii_NoCase(const char *s) const;
int Find(wchar_t c) const { return FindCharPosInString(_chars, c); }
int Find(wchar_t c, unsigned startIndex) const
{
int pos = FindCharPosInString(_chars + startIndex, c);
return pos < 0 ? -1 : (int)startIndex + pos;
}
int Find(const UString &s) const { return Find(s, 0); }
int Find(const UString &s, unsigned startIndex) const throw();
int ReverseFind(wchar_t c) const throw();
void TrimLeft() throw();
void TrimRight() throw();
void Trim()
{
TrimRight();
TrimLeft();
}
void InsertAtFront(wchar_t c);
// void Insert(unsigned index, wchar_t c);
void Insert(unsigned index, const wchar_t *s);
void Insert(unsigned index, const UString &s);
void RemoveChar(wchar_t ch) throw();
void Replace(wchar_t oldChar, wchar_t newChar) throw();
void Replace(const UString &oldString, const UString &newString);
void Delete(unsigned index) throw();
void Delete(unsigned index, unsigned count) throw();
void DeleteFrontal(unsigned num) throw();
void DeleteBack() { _chars[--_len] = 0; }
void DeleteFrom(unsigned index)
{
if (index < _len)
{
_len = index;
_chars[index] = 0;
}
}
};
bool operator<(const UString &s1, const UString &s2);
bool operator>(const UString &s1, const UString &s2);
inline bool operator==(const UString &s1, const UString &s2) { return s1.Len() == s2.Len() && wcscmp(s1, s2) == 0; }
inline bool operator==(const UString &s1, const wchar_t *s2) { return wcscmp(s1, s2) == 0; }
inline bool operator==(const wchar_t *s1, const UString &s2) { return wcscmp(s1, s2) == 0; }
inline bool operator!=(const UString &s1, const UString &s2) { return s1.Len() != s2.Len() || wcscmp(s1, s2) != 0; }
inline bool operator!=(const UString &s1, const wchar_t *s2) { return wcscmp(s1, s2) != 0; }
inline bool operator!=(const wchar_t *s1, const UString &s2) { return wcscmp(s1, s2) != 0; }
typedef CStringBase<char> AString;
typedef CStringBase<wchar_t> UString;
typedef CObjectVector<AString> AStringVector;
typedef CObjectVector<UString> UStringVector;

30
CPP/Common/MyTypes.h Normal file
View File

@@ -0,0 +1,30 @@
// Common/MyTypes.h
#ifndef __COMMON_MY_TYPES_H
#define __COMMON_MY_TYPES_H
#include "../../C/7zTypes.h"
typedef int HRes;
struct CBoolPair
{
bool Val;
bool Def;
CBoolPair(): Val(false), Def(false) {}
void Init()
{
Val = false;
Def = false;
}
void SetTrueTrue()
{
Val = true;
Def = true;
}
};
#endif

0
CPP/Common/MyUnknown.h Executable file → Normal file
View File

84
CPP/Common/MyVector.cpp Executable file → Normal file
View File

@@ -1,87 +1,3 @@
// Common/MyVector.cpp
#include "StdAfx.h"
#include <string.h>
#include "MyVector.h"
CBaseRecordVector::~CBaseRecordVector() { ClearAndFree(); }
void CBaseRecordVector::ClearAndFree()
{
Clear();
delete []((unsigned char *)_items);
_capacity = 0;
_size = 0;
_items = 0;
}
void CBaseRecordVector::Clear() { DeleteFrom(0); }
void CBaseRecordVector::DeleteBack() { Delete(_size - 1); }
void CBaseRecordVector::DeleteFrom(int index) { Delete(index, _size - index); }
void CBaseRecordVector::ReserveOnePosition()
{
if (_size != _capacity)
return;
unsigned delta = 1;
if (_capacity >= 64)
delta = (unsigned)_capacity / 4;
else if (_capacity >= 8)
delta = 8;
Reserve(_capacity + (int)delta);
}
void CBaseRecordVector::Reserve(int newCapacity)
{
// if (newCapacity <= _capacity)
if (newCapacity == _capacity)
return;
if ((unsigned)newCapacity >= ((unsigned)1 << (sizeof(unsigned) * 8 - 1)))
throw 1052353;
size_t newSize = (size_t)(unsigned)newCapacity * _itemSize;
if (newSize / _itemSize != (size_t)(unsigned)newCapacity)
throw 1052354;
unsigned char *p = NULL;
if (newSize > 0)
{
p = new unsigned char[newSize];
if (p == 0)
throw 1052355;
int numRecordsToMove = (_size < newCapacity ? _size : newCapacity);
memcpy(p, _items, _itemSize * numRecordsToMove);
}
delete [](unsigned char *)_items;
_items = p;
_capacity = newCapacity;
}
void CBaseRecordVector::ReserveDown()
{
Reserve(_size);
}
void CBaseRecordVector::MoveItems(int destIndex, int srcIndex)
{
memmove(((unsigned char *)_items) + destIndex * _itemSize,
((unsigned char *)_items) + srcIndex * _itemSize,
_itemSize * (_size - srcIndex));
}
void CBaseRecordVector::InsertOneItem(int index)
{
ReserveOnePosition();
MoveItems(index + 1, index);
_size++;
}
void CBaseRecordVector::Delete(int index, int num)
{
TestIndexAndCorrectNum(index, num);
if (num > 0)
{
MoveItems(index, index + num);
_size -= num;
}
}

599
CPP/Common/MyVector.h Executable file → Normal file
View File

@@ -1,92 +1,247 @@
// Common/Vector.h
// Common/MyVector.h
#ifndef __COMMON_VECTOR_H
#define __COMMON_VECTOR_H
#include "Defs.h"
class CBaseRecordVector
{
void MoveItems(int destIndex, int srcIndex);
protected:
int _capacity;
int _size;
void *_items;
size_t _itemSize;
void ReserveOnePosition();
void InsertOneItem(int index);
void TestIndexAndCorrectNum(int index, int &num) const
{ if (index + num > _size) num = _size - index; }
public:
CBaseRecordVector(size_t itemSize): _capacity(0), _size(0), _items(0), _itemSize(itemSize) {}
virtual ~CBaseRecordVector();
void ClearAndFree();
int Size() const { return _size; }
bool IsEmpty() const { return (_size == 0); }
void Reserve(int newCapacity);
void ReserveDown();
virtual void Delete(int index, int num = 1);
void Clear();
void DeleteFrom(int index);
void DeleteBack();
};
#ifndef __COMMON_MY_VECTOR_H
#define __COMMON_MY_VECTOR_H
template <class T>
class CRecordVector: public CBaseRecordVector
class CRecordVector
{
T *_items;
unsigned _size;
unsigned _capacity;
void MoveItems(unsigned destIndex, unsigned srcIndex)
{
memmove(_items + destIndex, _items + srcIndex, (size_t)(_size - srcIndex) * (size_t)sizeof(T));
}
void ReserveOnePosition()
{
if (_size == _capacity)
{
unsigned newCapacity = _capacity + (_capacity >> 2) + 1;
T *p = new T[newCapacity];
memcpy(p, _items, (size_t)_size * (size_t)sizeof(T));
delete []_items;
_items = p;
_capacity = newCapacity;
}
}
public:
CRecordVector(): CBaseRecordVector(sizeof(T)){};
CRecordVector(const CRecordVector &v): CBaseRecordVector(sizeof(T)) { *this = v; }
CRecordVector& operator=(const CRecordVector &v)
CRecordVector(): _items(0), _size(0), _capacity(0) {}
CRecordVector(const CRecordVector &v): _items(0), _size(0), _capacity(0)
{
unsigned size = v.Size();
if (size != 0)
{
_items = new T[size];
_size = size;
_capacity = size;
memcpy(_items, v._items, (size_t)size * (size_t)sizeof(T));
}
}
unsigned Size() const { return _size; }
bool IsEmpty() const { return _size == 0; }
void ConstructReserve(unsigned size)
{
if (size != 0)
{
_items = new T[size];
_capacity = size;
}
}
void Reserve(unsigned newCapacity)
{
if (newCapacity > _capacity)
{
T *p = new T[newCapacity];
memcpy(p, _items, (size_t)_size * (size_t)sizeof(T));
delete []_items;
_items = p;
_capacity = newCapacity;
}
}
void ClearAndReserve(unsigned newCapacity)
{
Clear();
return (*this += v);
if (newCapacity > _capacity)
{
delete []_items;
_items = NULL;
_capacity = 0;
_items = new T[newCapacity];
_capacity = newCapacity;
}
}
CRecordVector& operator+=(const CRecordVector &v)
void ClearAndSetSize(unsigned newSize)
{
int size = v.Size();
Reserve(Size() + size);
for (int i = 0; i < size; i++)
Add(v[i]);
ClearAndReserve(newSize);
_size = newSize;
}
void ChangeSize_KeepData(unsigned newSize)
{
if (newSize > _capacity)
{
T *p = new T[newSize];
memcpy(p, _items, (size_t)_size * (size_t)sizeof(T));
delete []_items;
_items = p;
_capacity = newSize;
}
_size = newSize;
}
void ReserveDown()
{
if (_size == _capacity)
return;
T *p = NULL;
if (_size != 0)
{
p = new T[_size];
memcpy(p, _items, (size_t)_size * (size_t)sizeof(T));
}
delete []_items;
_items = p;
_capacity = _size;
}
~CRecordVector() { delete []_items; }
void ClearAndFree()
{
delete []_items;
_items = NULL;
_size = 0;
_capacity = 0;
}
void Clear() { _size = 0; }
void DeleteBack() { _size--; }
void DeleteFrom(unsigned index)
{
// if (index <= _size)
_size = index;
}
void DeleteFrontal(unsigned num)
{
if (num != 0)
{
MoveItems(0, num);
_size -= num;
}
}
void Delete(unsigned index)
{
MoveItems(index, index + 1);
_size -= 1;
}
/*
void Delete(unsigned index, unsigned num)
{
if (num > 0)
{
MoveItems(index, index + num);
_size -= num;
}
}
*/
CRecordVector& operator=(const CRecordVector &v)
{
unsigned size = v.Size();
if (size > _capacity)
{
delete []_items;
_capacity = 0;
_size = 0;
_items = NULL;
_items = new T[size];
_capacity = size;
}
_size = size;
memcpy(_items, v._items, (size_t)size * (size_t)sizeof(T));
return *this;
}
int Add(T item)
CRecordVector& operator+=(const CRecordVector &v)
{
unsigned size = v.Size();
Reserve(_size + size);
memcpy(_items + _size, v._items, (size_t)size * (size_t)sizeof(T));
_size += size;
return *this;
}
unsigned Add(const T item)
{
ReserveOnePosition();
((T *)_items)[_size] = item;
_items[_size] = item;
return _size++;
}
void Insert(int index, T item)
{
InsertOneItem(index);
((T *)_items)[index] = item;
}
// T* GetPointer() const { return (T*)_items; }
// operator const T *() const { return _items; };
const T& operator[](int index) const { return ((T *)_items)[index]; }
T& operator[](int index) { return ((T *)_items)[index]; }
const T& Front() const { return operator[](0); }
T& Front() { return operator[](0); }
const T& Back() const { return operator[](_size - 1); }
T& Back() { return operator[](_size - 1); }
void Swap(int i, int j)
void AddInReserved(const T item)
{
T temp = operator[](i);
operator[](i) = operator[](j);
operator[](j) = temp;
_items[_size++] = item;
}
int FindInSorted(const T& item, int left, int right) const
void Insert(unsigned index, const T item)
{
ReserveOnePosition();
MoveItems(index + 1, index);
_items[index] = item;
_size++;
}
void MoveToFront(unsigned index)
{
if (index != 0)
{
T temp = _items[index];
memmove(_items + 1, _items, (size_t)index * (size_t)sizeof(T));
_items[0] = temp;
}
}
const T& operator[](unsigned index) const { return _items[index]; }
T& operator[](unsigned index) { return _items[index]; }
const T& Front() const { return _items[0]; }
T& Front() { return _items[0]; }
const T& Back() const { return _items[_size - 1]; }
T& Back() { return _items[_size - 1]; }
/*
void Swap(unsigned i, unsigned j)
{
T temp = _items[i];
_items[i] = _items[j];
_items[j] = temp;
}
*/
int FindInSorted(const T item, unsigned left, unsigned right) const
{
while (left != right)
{
int mid = (left + right) / 2;
const T& midValue = (*this)[mid];
if (item == midValue)
unsigned mid = (left + right) / 2;
const T midVal = (*this)[mid];
if (item == midVal)
return mid;
if (item < midValue)
if (item < midVal)
right = mid;
else
left = mid + 1;
@@ -94,16 +249,16 @@ public:
return -1;
}
int FindInSorted(const T& item) const
int FindInSorted2(const T &item, unsigned left, unsigned right) const
{
int left = 0, right = Size();
while (left != right)
{
int mid = (left + right) / 2;
const T& midValue = (*this)[mid];
if (item == midValue)
unsigned mid = (left + right) / 2;
const T& midVal = (*this)[mid];
int comp = item.Compare(midVal);
if (comp == 0)
return mid;
if (item < midValue)
if (comp < 0)
right = mid;
else
left = mid + 1;
@@ -111,16 +266,26 @@ public:
return -1;
}
int AddToUniqueSorted(const T& item)
int FindInSorted(const T item) const
{
int left = 0, right = Size();
return FindInSorted(item, 0, _size);
}
int FindInSorted2(const T &item) const
{
return FindInSorted2(item, 0, _size);
}
unsigned AddToUniqueSorted(const T item)
{
unsigned left = 0, right = _size;
while (left != right)
{
int mid = (left + right) / 2;
const T& midValue = (*this)[mid];
if (item == midValue)
unsigned mid = (left + right) / 2;
const T midVal = (*this)[mid];
if (item == midVal)
return mid;
if (item < midValue)
if (item < midVal)
right = mid;
else
left = mid + 1;
@@ -129,12 +294,31 @@ public:
return right;
}
static void SortRefDown(T* p, int k, int size, int (*compare)(const T*, const T*, void *), void *param)
unsigned AddToUniqueSorted2(const T &item)
{
unsigned left = 0, right = _size;
while (left != right)
{
unsigned mid = (left + right) / 2;
const T& midVal = (*this)[mid];
int comp = item.Compare(midVal);
if (comp == 0)
return mid;
if (comp < 0)
right = mid;
else
left = mid + 1;
}
Insert(right, item);
return right;
}
static void SortRefDown(T* p, unsigned k, unsigned size, int (*compare)(const T*, const T*, void *), void *param)
{
T temp = p[k];
for (;;)
{
int s = (k << 1);
unsigned s = (k << 1);
if (s > size)
break;
if (s < size && compare(p + s + 1, p + s, param) > 0)
@@ -149,12 +333,12 @@ public:
void Sort(int (*compare)(const T*, const T*, void *), void *param)
{
int size = _size;
unsigned size = _size;
if (size <= 1)
return;
T* p = (&Front()) - 1;
{
int i = size / 2;
unsigned i = size >> 1;
do
SortRefDown(p, i, size, compare, param);
while (--i != 0);
@@ -168,6 +352,46 @@ public:
}
while (size > 1);
}
static void SortRefDown2(T* p, unsigned k, unsigned size)
{
T temp = p[k];
for (;;)
{
unsigned s = (k << 1);
if (s > size)
break;
if (s < size && p[s + 1].Compare(p[s]) > 0)
s++;
if (temp.Compare(p[s]) >= 0)
break;
p[k] = p[s];
k = s;
}
p[k] = temp;
}
void Sort2()
{
unsigned size = _size;
if (size <= 1)
return;
T* p = (&Front()) - 1;
{
unsigned i = size >> 1;
do
SortRefDown2(p, i, size);
while (--i != 0);
}
do
{
T temp = p[size];
p[size--] = p[1];
p[1] = temp;
SortRefDown2(p, 1, size);
}
while (size > 1);
}
};
typedef CRecordVector<int> CIntVector;
@@ -177,76 +401,174 @@ typedef CRecordVector<unsigned char> CByteVector;
typedef CRecordVector<void *> CPointerVector;
template <class T>
class CObjectVector: public CPointerVector
class CObjectVector
{
CPointerVector _v;
public:
unsigned Size() const { return _v.Size(); }
bool IsEmpty() const { return _v.IsEmpty(); }
void ReserveDown() { _v.ReserveDown(); }
// void Reserve(unsigned newCapacity) { _v.Reserve(newCapacity); }
void ClearAndReserve(unsigned newCapacity) { Clear(); _v.ClearAndReserve(newCapacity); }
CObjectVector() {};
~CObjectVector() { Clear(); };
CObjectVector(const CObjectVector &v): CPointerVector() { *this = v; }
CObjectVector(const CObjectVector &v)
{
unsigned size = v.Size();
_v.ConstructReserve(size);
for (unsigned i = 0; i < size; i++)
_v.AddInReserved(new T(v[i]));
}
CObjectVector& operator=(const CObjectVector &v)
{
Clear();
return (*this += v);
}
CObjectVector& operator+=(const CObjectVector &v)
{
int size = v.Size();
Reserve(Size() + size);
for (int i = 0; i < size; i++)
Add(v[i]);
unsigned size = v.Size();
_v.Reserve(size);
for (unsigned i = 0; i < size; i++)
_v.AddInReserved(new T(v[i]));
return *this;
}
const T& operator[](int index) const { return *((T *)CPointerVector::operator[](index)); }
T& operator[](int index) { return *((T *)CPointerVector::operator[](index)); }
T& Front() { return operator[](0); }
const T& Front() const { return operator[](0); }
T& Back() { return operator[](_size - 1); }
const T& Back() const { return operator[](_size - 1); }
int Add(const T& item) { return CPointerVector::Add(new T(item)); }
void Insert(int index, const T& item) { CPointerVector::Insert(index, new T(item)); }
virtual void Delete(int index, int num = 1)
CObjectVector& operator+=(const CObjectVector &v)
{
TestIndexAndCorrectNum(index, num);
for (int i = 0; i < num; i++)
delete (T *)(((void **)_items)[index + i]);
CPointerVector::Delete(index, num);
unsigned size = v.Size();
_v.Reserve(Size() + size);
for (unsigned i = 0; i < size; i++)
_v.AddInReserved(new T(v[i]));
return *this;
}
const T& operator[](unsigned index) const { return *((T *)_v[index]); }
T& operator[](unsigned index) { return *((T *)_v[index]); }
const T& Front() const { return operator[](0); }
T& Front() { return operator[](0); }
const T& Back() const { return operator[](_v.Size() - 1); }
T& Back() { return operator[](_v.Size() - 1); }
void MoveToFront(unsigned index) { _v.MoveToFront(index); }
unsigned Add(const T& item) { return _v.Add(new T(item)); }
void AddInReserved(const T& item) { _v.AddInReserved(new T(item)); }
T& AddNew()
{
T *p = new T;
_v.Add(p);
return *p;
}
T& AddNewInReserved()
{
T *p = new T;
_v.AddInReserved(p);
return *p;
}
void Insert(unsigned index, const T& item) { _v.Insert(index, new T(item)); }
T& InsertNew(unsigned index)
{
T *p = new T;
_v.Insert(index, p);
return *p;
}
~CObjectVector()
{
for (unsigned i = _v.Size(); i != 0;)
delete (T *)_v[--i];
}
void ClearAndFree()
{
Clear();
_v.ClearAndFree();
}
void Clear()
{
for (unsigned i = _v.Size(); i != 0;)
delete (T *)_v[--i];
_v.Clear();
}
void DeleteFrom(unsigned index)
{
unsigned size = _v.Size();
for (unsigned i = index; i < size; i++)
delete (T *)_v[i];
_v.DeleteFrom(index);
}
void DeleteFrontal(unsigned num)
{
for (unsigned i = 0; i < num; i++)
delete (T *)_v[i];
_v.DeleteFrontal(num);
}
void DeleteBack()
{
delete (T *)_v[_v.Size() - 1];
_v.DeleteBack();
}
void Delete(unsigned index)
{
delete (T *)_v[index];
_v.Delete(index);
}
/*
void Delete(unsigned index, unsigned num)
{
for (unsigned i = 0; i < num; i++)
delete (T *)_v[index + i];
_v.Delete(index, num);
}
*/
/*
int Find(const T& item) const
{
for (int i = 0; i < Size(); i++)
unsigned size = Size();
for (unsigned i = 0; i < size; i++)
if (item == (*this)[i])
return i;
return -1;
}
*/
int FindInSorted(const T& item) const
{
int left = 0, right = Size();
unsigned left = 0, right = Size();
while (left != right)
{
int mid = (left + right) / 2;
const T& midValue = (*this)[mid];
if (item == midValue)
unsigned mid = (left + right) / 2;
const T& midVal = (*this)[mid];
int comp = item.Compare(midVal);
if (comp == 0)
return mid;
if (item < midValue)
if (comp < 0)
right = mid;
else
left = mid + 1;
}
return -1;
}
int AddToSorted(const T& item)
unsigned AddToUniqueSorted(const T& item)
{
int left = 0, right = Size();
unsigned left = 0, right = Size();
while (left != right)
{
int mid = (left + right) / 2;
const T& midValue = (*this)[mid];
if (item == midValue)
{
right = mid + 1;
break;
}
if (item < midValue)
unsigned mid = (left + right) / 2;
const T& midVal = (*this)[mid];
int comp = item.Compare(midVal);
if (comp == 0)
return mid;
if (comp < 0)
right = mid;
else
left = mid + 1;
@@ -255,12 +577,39 @@ public:
return right;
}
/*
unsigned AddToSorted(const T& item)
{
unsigned left = 0, right = Size();
while (left != right)
{
unsigned mid = (left + right) / 2;
const T& midVal = (*this)[mid];
int comp = item.Compare(midVal);
if (comp == 0)
{
right = mid + 1;
break;
}
if (comp < 0)
right = mid;
else
left = mid + 1;
}
Insert(right, item);
return right;
}
*/
void Sort(int (*compare)(void *const *, void *const *, void *), void *param)
{ CPointerVector::Sort(compare, param); }
{ _v.Sort(compare, param); }
static int CompareObjectItems(void *const *a1, void *const *a2, void * /* param */)
{ return MyCompare(*(*((const T **)a1)), *(*((const T **)a2))); }
void Sort() { CPointerVector::Sort(CompareObjectItems, 0); }
{ return (*(*((const T **)a1))).Compare(*(*((const T **)a2))); }
void Sort() { _v.Sort(CompareObjectItems, 0); }
};
#define FOR_VECTOR(_i_, _v_) for (unsigned _i_ = 0; _i_ < (_v_).Size(); _i_++)
#endif

24
CPP/Common/MyWindows.cpp Executable file → Normal file
View File

@@ -28,7 +28,7 @@ BSTR SysAllocStringByteLen(LPCSTR psz, UINT len)
BSTR bstr = (BSTR)((UINT *)p + 1);
if (psz)
{
memmove(bstr, psz, len);
memcpy(bstr, psz, len);
Byte *pb = ((Byte *)bstr) + len;
for (unsigned i = 0; i < sizeof(OLECHAR) * 2; i++)
pb[i] = 0;
@@ -36,6 +36,22 @@ BSTR SysAllocStringByteLen(LPCSTR psz, UINT len)
return bstr;
}
BSTR SysAllocStringLen(const OLECHAR *sz, UINT len)
{
int realLen = sizeof(UINT) + len * sizeof(OLECHAR) + sizeof(OLECHAR);
void *p = AllocateForBSTR(realLen);
if (p == 0)
return 0;
*(UINT *)p = len * sizeof(OLECHAR);
BSTR bstr = (BSTR)((UINT *)p + 1);
if (sz)
{
memcpy(bstr, sz, len * sizeof(OLECHAR));
bstr[len] = 0;
}
return bstr;
}
BSTR SysAllocString(const OLECHAR *sz)
{
if (sz == 0)
@@ -45,9 +61,9 @@ BSTR SysAllocString(const OLECHAR *sz)
void *p = AllocateForBSTR(len + sizeof(UINT));
if (p == 0)
return 0;
*(UINT *)p = strLen;
*(UINT *)p = strLen * sizeof(OLECHAR);
BSTR bstr = (BSTR)((UINT *)p + 1);
memmove(bstr, sz, len);
memcpy(bstr, sz, len);
return bstr;
}
@@ -77,7 +93,7 @@ HRESULT VariantClear(VARIANTARG *prop)
return S_OK;
}
HRESULT VariantCopy(VARIANTARG *dest, VARIANTARG *src)
HRESULT VariantCopy(VARIANTARG *dest, const VARIANTARG *src)
{
HRESULT res = ::VariantClear(dest);
if (res != S_OK)

15
CPP/Common/MyWindows.h Executable file → Normal file
View File

@@ -7,6 +7,11 @@
#include <windows.h>
#ifdef UNDER_CE
#undef VARIANT_TRUE
#define VARIANT_TRUE ((VARIANT_BOOL)-1)
#endif
#else
#include <stddef.h> // for wchar_t
@@ -14,6 +19,8 @@
#include "MyGuidDef.h"
#define WINAPI
typedef char CHAR;
typedef unsigned char UCHAR;
@@ -145,8 +152,6 @@ typedef WORD PROPVAR_PAD1;
typedef WORD PROPVAR_PAD2;
typedef WORD PROPVAR_PAD3;
#ifdef __cplusplus
typedef struct tagPROPVARIANT
{
VARTYPE vt;
@@ -177,7 +182,7 @@ typedef tagVARIANT VARIANT;
typedef VARIANT VARIANTARG;
MY_EXTERN_C HRESULT VariantClear(VARIANTARG *prop);
MY_EXTERN_C HRESULT VariantCopy(VARIANTARG *dest, VARIANTARG *src);
MY_EXTERN_C HRESULT VariantCopy(VARIANTARG *dest, const VARIANTARG *src);
typedef struct tagSTATPROPSTG
{
@@ -186,9 +191,8 @@ typedef struct tagSTATPROPSTG
VARTYPE vt;
} STATPROPSTG;
#endif
MY_EXTERN_C BSTR SysAllocStringByteLen(LPCSTR psz, UINT len);
MY_EXTERN_C BSTR SysAllocStringLen(const OLECHAR *sz, UINT len);
MY_EXTERN_C BSTR SysAllocString(const OLECHAR *sz);
MY_EXTERN_C void SysFreeString(BSTR bstr);
MY_EXTERN_C UINT SysStringByteLen(BSTR bstr);
@@ -199,6 +203,7 @@ MY_EXTERN_C LONG CompareFileTime(const FILETIME* ft1, const FILETIME* ft2);
#define CP_ACP 0
#define CP_OEMCP 1
#define CP_UTF8 65001
typedef enum tagSTREAM_SEEK
{

267
CPP/Common/MyXml.cpp Executable file → Normal file
View File

@@ -18,52 +18,19 @@ static bool IsSpaceChar(char c)
return (c == ' ' || c == '\t' || c == 0x0D || c == 0x0A);
}
#define SKIP_SPACES(s, pos) while (IsSpaceChar(s[pos])) pos++;
#define SKIP_SPACES(s) while (IsSpaceChar(*s)) s++;
static bool ReadProperty(const AString &s, int &pos, CXmlProp &prop)
int CXmlItem::FindProp(const AString &propName) const
{
prop.Name.Empty();
prop.Value.Empty();
for (; pos < s.Length(); pos++)
{
char c = s[pos];
if (!IsValidChar(c))
break;
prop.Name += c;
}
if (prop.Name.IsEmpty())
return false;
SKIP_SPACES(s, pos);
if (s[pos++] != '=')
return false;
SKIP_SPACES(s, pos);
if (s[pos++] != '\"')
return false;
while (pos < s.Length())
{
char c = s[pos++];
if (c == '\"')
return true;
prop.Value += c;
}
return false;
}
int CXmlItem::FindProperty(const AString &propName) const
{
for (int i = 0; i < Props.Size(); i++)
FOR_VECTOR (i, Props)
if (Props[i].Name == propName)
return i;
return -1;
}
AString CXmlItem::GetPropertyValue(const AString &propName) const
AString CXmlItem::GetPropVal(const AString &propName) const
{
int index = FindProperty(propName);
int index = FindProp(propName);
if (index >= 0)
return Props[index].Value;
return AString();
@@ -76,7 +43,7 @@ bool CXmlItem::IsTagged(const AString &tag) const
int CXmlItem::FindSubTag(const AString &tag) const
{
for (int i = 0; i < SubItems.Size(); i++)
FOR_VECTOR (i, SubItems)
if (SubItems[i].IsTagged(tag))
return i;
return -1;
@@ -93,6 +60,17 @@ AString CXmlItem::GetSubString() const
return AString();
}
const AString * CXmlItem::GetSubStringPtr() const
{
if (SubItems.Size() == 1)
{
const CXmlItem &item = SubItems[0];
if (!item.IsTag)
return &item.Name;
}
return NULL;
}
AString CXmlItem::GetSubStringForTag(const AString &tag) const
{
int index = FindSubTag(tag);
@@ -101,100 +79,169 @@ AString CXmlItem::GetSubStringForTag(const AString &tag) const
return AString();
}
bool CXmlItem::ParseItems(const AString &s, int &pos, int numAllowedLevels)
const char * CXmlItem::ParseItem(const char *s, int numAllowedLevels)
{
if (numAllowedLevels == 0)
return false;
SubItems.Clear();
AString finishString = "</";
SKIP_SPACES(s);
const char *beg = s;
for (;;)
{
SKIP_SPACES(s, pos);
if (s.Mid(pos, finishString.Length()) == finishString)
return true;
CXmlItem item;
if (!item.ParseItem(s, pos, numAllowedLevels - 1))
return false;
SubItems.Add(item);
char c;
c = *s; if (c == 0 || c == '<') break; s++;
c = *s; if (c == 0 || c == '<') break; s++;
}
}
bool CXmlItem::ParseItem(const AString &s, int &pos, int numAllowedLevels)
{
SKIP_SPACES(s, pos);
int pos2 = s.Find('<', pos);
if (pos2 < 0)
return false;
if (pos2 != pos)
if (*s == 0)
return NULL;
if (s != beg)
{
IsTag = false;
Name += s.Mid(pos, pos2 - pos);
pos = pos2;
return true;
Name.SetFrom(beg, (unsigned)(s - beg));
return s;
}
IsTag = true;
pos++;
SKIP_SPACES(s, pos);
s++;
SKIP_SPACES(s);
for (; pos < s.Length(); pos++)
{
char c = s[pos];
if (!IsValidChar(c))
beg = s;
for (;; s++)
if (!IsValidChar(*s))
break;
Name += c;
}
if (Name.IsEmpty() || pos == s.Length())
return false;
if (s == beg || *s == 0)
return NULL;
Name.SetFrom(beg, (unsigned)(s - beg));
int posTemp = pos;
for (;;)
{
SKIP_SPACES(s, pos);
if (s[pos] == '/')
beg = s;
SKIP_SPACES(s);
if (*s == '/')
{
pos++;
// SKIP_SPACES(s, pos);
return (s[pos++] == '>');
s++;
// SKIP_SPACES(s);
if (*s != '>')
return NULL;
return s + 1;
}
if (s[pos] == '>')
if (*s == '>')
{
if (!ParseItems(s, ++pos, numAllowedLevels))
return false;
AString finishString = AString("</") + Name + AString(">");
if (s.Mid(pos, finishString.Length()) != finishString)
return false;
pos += finishString.Length();
return true;
}
if (posTemp == pos)
return false;
s++;
if (numAllowedLevels == 0)
return NULL;
SubItems.Clear();
for (;;)
{
SKIP_SPACES(s);
if (s[0] == '<' && s[1] == '/')
break;
CXmlItem &item = SubItems.AddNew();
s = item.ParseItem(s, numAllowedLevels - 1);
if (!s)
return NULL;
}
CXmlProp prop;
if (!ReadProperty(s, pos, prop))
return false;
Props.Add(prop);
posTemp = pos;
s += 2;
unsigned len = Name.Len();
for (unsigned i = 0; i < len; i++)
if (s[i] != Name[i])
return NULL;
s += len;
if (s[0] != '>')
return NULL;
return s + 1;
}
if (beg == s)
return NULL;
// ReadProperty
CXmlProp &prop = Props.AddNew();
beg = s;
for (;; s++)
{
char c = *s;
if (!IsValidChar(c))
break;
}
if (s == beg)
return NULL;
prop.Name.SetFrom(beg, (unsigned)(s - beg));
SKIP_SPACES(s);
if (*s != '=')
return NULL;
s++;
SKIP_SPACES(s);
if (*s != '\"')
return NULL;
s++;
beg = s;
for (;;)
{
char c = *s;
if (c == 0)
return NULL;
if (c == '\"')
break;
s++;
}
prop.Value.SetFrom(beg, (unsigned)(s - beg));
s++;
}
}
static bool SkipHeader(const AString &s, int &pos, const AString &startString, const AString &endString)
static bool SkipHeader(const AString &s, int &pos, const char *startString, const char *endString)
{
SKIP_SPACES(s, pos);
if (s.Mid(pos, startString.Length()) == startString)
while (IsSpaceChar(s[pos]))
pos++;
if (IsString1PrefixedByString2(s.Ptr(pos), startString))
{
pos = s.Find(endString, pos);
const AString es = endString;
pos = s.Find(es, pos);
if (pos < 0)
return false;
pos += endString.Length();
SKIP_SPACES(s, pos);
pos += es.Len();
}
return true;
}
void CXmlItem::AppendTo(AString &s) const
{
if (IsTag)
s += '<';
s += Name;
if (IsTag)
{
FOR_VECTOR (i, Props)
{
const CXmlProp &prop = Props[i];
s += ' ';
s += prop.Name;
s += '=';
s += '\"';
s += prop.Value;
s += '\"';
}
s += '>';
}
FOR_VECTOR (i, SubItems)
{
const CXmlItem &item = SubItems[i];
if (i != 0 && !SubItems[i - 1].IsTag)
s += ' ';
item.AppendTo(s);
}
if (IsTag)
{
s += '<';
s += '/';
s += Name;
s += '>';
}
}
bool CXml::Parse(const AString &s)
{
int pos = 0;
@@ -202,8 +249,14 @@ bool CXml::Parse(const AString &s)
return false;
if (!SkipHeader(s, pos, "<!DOCTYPE", ">"))
return false;
if (!Root.ParseItem(s, pos, 1000))
const char *ptr = Root.ParseItem(s.Ptr(pos), 1000);
if (!ptr || !Root.IsTag)
return false;
SKIP_SPACES(s, pos);
return (pos == s.Length() && Root.IsTag);
SKIP_SPACES(ptr);
return *ptr == 0;
}
void CXml::AppendTo(AString &s) const
{
Root.AppendTo(s);
}

23
CPP/Common/MyXml.h Executable file → Normal file
View File

@@ -1,7 +1,7 @@
// MyXml.h
#ifndef __MYXML_H
#define __MYXML_H
#ifndef __MY_XML_H
#define __MY_XML_H
#include "MyString.h"
@@ -13,28 +13,31 @@ struct CXmlProp
class CXmlItem
{
bool ParseItems(const AString &s, int &pos, int numAllowedLevels);
public:
AString Name;
bool IsTag;
CObjectVector<CXmlProp> Props;
CObjectVector<CXmlItem> SubItems;
bool ParseItem(const AString &s, int &pos, int numAllowedLevels);
bool IsTagged(const AString &tag) const;
int FindProperty(const AString &propName) const;
AString GetPropertyValue(const AString &propName) const;
const char * ParseItem(const char *s, int numAllowedLevels);
bool IsTagged(const AString &tag) const throw();
int FindProp(const AString &propName) const throw();
AString GetPropVal(const AString &propName) const;
AString GetSubString() const;
int FindSubTag(const AString &tag) const;
const AString * GetSubStringPtr() const throw();
int FindSubTag(const AString &tag) const throw();
AString GetSubStringForTag(const AString &tag) const;
void AppendTo(AString &s) const;
};
struct CXml
{
CXmlItem Root;
bool Parse(const AString &s);
void AppendTo(AString &s) const;
};
#endif

66
CPP/Common/NewHandler.cpp Executable file → Normal file
View File

@@ -11,6 +11,32 @@
#ifndef DEBUG_MEMORY_LEAK
#ifdef _WIN32
/*
void * my_new(size_t size)
{
// void *p = ::HeapAlloc(::GetProcessHeap(), 0, size);
void *p = ::malloc(size);
if (p == 0)
throw CNewException();
return p;
}
void my_delete(void *p) throw()
{
// if (p == 0) return; ::HeapFree(::GetProcessHeap(), 0, p);
::free(p);
}
void * my_Realloc(void *p, size_t newSize, size_t oldSize)
{
void *newBuf = my_new(newSize);
memcpy(newBuf, p, oldSize);
my_delete(p);
return newBuf;
}
*/
void *
#ifdef _MSC_VER
__cdecl
@@ -30,18 +56,42 @@ __cdecl
#endif
operator delete(void *p) throw()
{
/*
if (p == 0)
return;
::HeapFree(::GetProcessHeap(), 0, p);
*/
// if (p == 0) return; ::HeapFree(::GetProcessHeap(), 0, p);
::free(p);
}
/*
void *
#ifdef _MSC_VER
__cdecl
#endif
operator new[](size_t size)
{
// void *p = ::HeapAlloc(::GetProcessHeap(), 0, size);
void *p = ::malloc(size);
if (p == 0)
throw CNewException();
return p;
}
void
#ifdef _MSC_VER
__cdecl
#endif
operator delete[](void *p) throw()
{
// if (p == 0) return; ::HeapFree(::GetProcessHeap(), 0, p);
::free(p);
}
*/
#endif
#else
#pragma init_seg(lib)
#include <stdio.h>
// #pragma init_seg(lib)
const int kDebugSize = 1000000;
static void *a[kDebugSize];
static int index = 0;
@@ -51,10 +101,6 @@ void * __cdecl operator new(size_t size)
{
numAllocs++;
void *p = HeapAlloc(GetProcessHeap(), 0, size);
if (index == 40)
{
int t = 1;
}
if (index < kDebugSize)
{
a[index] = p;

58
CPP/Common/NewHandler.h Executable file → Normal file
View File

@@ -1,16 +1,68 @@
// Common/NewHandler.h
#ifndef __COMMON_NEWHANDLER_H
#define __COMMON_NEWHANDLER_H
#ifndef __COMMON_NEW_HANDLER_H
#define __COMMON_NEW_HANDLER_H
/*
This file must be included before any code that uses operators "delete" or "new".
Also you must compile and link "NewHandler.cpp", if you use MSVC 6.0.
The operator "new" in MSVC 6.0 doesn't throw exception "bad_alloc".
So we define another version of operator "new" that throws "CNewException" on failure.
If you use compiler that throws exception in "new" operator (GCC or new version of MSVC),
you can compile without "NewHandler.cpp". So standard exception "bad_alloc" will be used.
It's still allowed to use redefined version of operator "new" from "NewHandler.cpp"
with any compiler. 7-Zip's code can work with "bad_alloc" and "CNewException" exceptions.
But if you use some additional code (outside of 7-Zip's code), you must check
that redefined version of operator "new" (that throws CNewException) is not
problem for your code.
Also we declare delete(void *p) throw() that creates smaller code.
*/
class CNewException {};
#ifdef WIN32
// We can compile my_new and my_delete with _fastcall
/*
void * my_new(size_t size);
void my_delete(void *p) throw();
// void * my_Realloc(void *p, size_t newSize, size_t oldSize);
*/
#endif
#ifdef _WIN32
void *
#ifdef _MSC_VER
__cdecl
#endif
operator new(size_t size);
void
#ifdef _MSC_VER
__cdecl
#endif
operator delete(void *p) throw();
#endif
#endif
/*
#ifdef _WIN32
void *
#ifdef _MSC_VER
__cdecl
#endif
operator new[](size_t size);
void
#ifdef _MSC_VER
__cdecl
#endif
operator delete[](void *p) throw();
#endif
*/
#endif

0
CPP/Common/Random.cpp Executable file → Normal file
View File

0
CPP/Common/Random.h Executable file → Normal file
View File

52
CPP/Common/Sha256Reg.cpp Normal file
View File

@@ -0,0 +1,52 @@
// Sha256Reg.cpp
#include "StdAfx.h"
#include "../../C/Sha256.h"
#include "../Common/MyCom.h"
#include "../7zip/ICoder.h"
#include "../7zip/Common/RegisterCodec.h"
class CSha256Hasher:
public IHasher,
public CMyUnknownImp
{
CSha256 _sha;
public:
CSha256Hasher() { Init(); };
MY_UNKNOWN_IMP
STDMETHOD_(void, Init)();
STDMETHOD_(void, Update)(const void *data, UInt32 size);
STDMETHOD_(void, Final)(Byte *digest);
STDMETHOD_(UInt32, GetDigestSize)();
};
STDMETHODIMP_(void) CSha256Hasher::Init()
{
Sha256_Init(&_sha);
}
STDMETHODIMP_(void) CSha256Hasher::Update(const void *data, UInt32 size)
{
Sha256_Update(&_sha, (const Byte *)data, size);
}
STDMETHODIMP_(void) CSha256Hasher::Final(Byte *digest)
{
Sha256_Final(&_sha, digest);
}
STDMETHODIMP_(UInt32) CSha256Hasher::GetDigestSize()
{
return SHA256_DIGEST_SIZE;
}
static IHasher *CreateHasher() { return new CSha256Hasher; }
static CHasherInfo g_HasherInfo = { CreateHasher, 0xA, L"SHA256", SHA256_DIGEST_SIZE };
REGISTER_HASHER(Sha256)

3
CPP/Common/StdAfx.h Executable file → Normal file
View File

@@ -3,7 +3,6 @@
#ifndef __STDAFX_H
#define __STDAFX_H
// #include "MyWindows.h"
#include "NewHandler.h"
#include "Common.h"
#endif

19
CPP/Common/StdInStream.cpp Executable file → Normal file
View File

@@ -8,12 +8,6 @@
#include "StringConvert.h"
#include "UTFConvert.h"
#ifdef _MSC_VER
// "was declared deprecated" disabling
#pragma warning(disable : 4996 )
#endif
static const char kIllegalChar = '\0';
static const char kNewLineChar = '\n';
static const char *kEOFMessage = "Unexpected end of input stream";
@@ -42,11 +36,6 @@ bool CStdInStream::Close()
return !_streamIsOpen;
}
CStdInStream::~CStdInStream()
{
Close();
}
AString CStdInStream::ScanStringUntilNewLine(bool allowEOF)
{
AString s;
@@ -59,8 +48,8 @@ AString CStdInStream::ScanStringUntilNewLine(bool allowEOF)
break;
throw kEOFMessage;
}
char c = char(intChar);
if (c == kIllegalChar)
char c = (char)intChar;
if (c == 0)
throw kIllegalCharMessage;
if (c == kNewLineChar)
break;
@@ -88,7 +77,7 @@ void CStdInStream::ReadToString(AString &resultString)
resultString.Empty();
int c;
while ((c = GetChar()) != EOF)
resultString += char(c);
resultString += (char)c;
}
bool CStdInStream::Eof()
@@ -103,5 +92,3 @@ int CStdInStream::GetChar()
throw kReadErrorMessage;
return c;
}

21
CPP/Common/StdInStream.h Executable file → Normal file
View File

@@ -1,29 +1,30 @@
// Common/StdInStream.h
#ifndef __COMMON_STDINSTREAM_H
#define __COMMON_STDINSTREAM_H
#ifndef __COMMON_STD_IN_STREAM_H
#define __COMMON_STD_IN_STREAM_H
#include <stdio.h>
#include "MyString.h"
#include "Types.h"
#include "MyTypes.h"
class CStdInStream
{
bool _streamIsOpen;
FILE *_stream;
bool _streamIsOpen;
public:
CStdInStream(): _streamIsOpen(false) {};
CStdInStream(FILE *stream): _streamIsOpen(false), _stream(stream) {};
~CStdInStream();
bool Open(LPCTSTR fileName);
bool Close();
CStdInStream(): _stream(0), _streamIsOpen(false) {};
CStdInStream(FILE *stream): _stream(stream), _streamIsOpen(false) {};
~CStdInStream() { Close(); }
bool Open(LPCTSTR fileName) throw();
bool Close() throw();
AString ScanStringUntilNewLine(bool allowEOF = false);
void ReadToString(AString &resultString);
UString ScanUStringUntilNewLine();
bool Eof();
bool Eof() throw();
int GetChar();
};

58
CPP/Common/StdOutStream.cpp Executable file → Normal file
View File

@@ -9,19 +9,14 @@
#include "StringConvert.h"
#include "UTFConvert.h"
#ifdef _MSC_VER
// "was declared deprecated" disabling
#pragma warning(disable : 4996 )
#endif
static const char kNewLineChar = '\n';
static const char *kFileOpenMode = "wt";
extern int g_CodePage;
CStdOutStream g_StdOut(stdout);
CStdOutStream g_StdErr(stderr);
CStdOutStream g_StdOut(stdout);
CStdOutStream g_StdErr(stderr);
bool CStdOutStream::Open(const char *fileName)
{
@@ -47,14 +42,9 @@ bool CStdOutStream::Flush()
return (fflush(_stream) == 0);
}
CStdOutStream::~CStdOutStream ()
CStdOutStream & CStdOutStream::operator<<(CStdOutStream & (*func)(CStdOutStream &))
{
Close();
}
CStdOutStream & CStdOutStream::operator<<(CStdOutStream & (*aFunction)(CStdOutStream &))
{
(*aFunction)(*this);
(*func)(*this);
return *this;
}
@@ -83,22 +73,48 @@ CStdOutStream & CStdOutStream::operator<<(const wchar_t *s)
return *this;
}
void CStdOutStream::PrintUString(const UString &s, AString &temp)
{
int codePage = g_CodePage;
if (codePage == -1)
codePage = CP_OEMCP;
if (codePage == CP_UTF8)
ConvertUnicodeToUTF8(s, temp);
else
UnicodeStringToMultiByte2(temp, s, (UINT)codePage);
*this << (const char *)temp;
}
CStdOutStream & CStdOutStream::operator<<(char c)
{
fputc(c, _stream);
return *this;
}
CStdOutStream & CStdOutStream::operator<<(int number)
CStdOutStream & CStdOutStream::operator<<(Int32 number)
{
char textString[32];
ConvertInt64ToString(number, textString);
return operator<<(textString);
char s[32];
ConvertInt64ToString(number, s);
return operator<<(s);
}
CStdOutStream & CStdOutStream::operator<<(Int64 number)
{
char s[32];
ConvertInt64ToString(number, s);
return operator<<(s);
}
CStdOutStream & CStdOutStream::operator<<(UInt32 number)
{
char s[16];
ConvertUInt32ToString(number, s);
return operator<<(s);
}
CStdOutStream & CStdOutStream::operator<<(UInt64 number)
{
char textString[32];
ConvertUInt64ToString(number, textString);
return operator<<(textString);
char s[32];
ConvertUInt64ToString(number, s);
return operator<<(s);
}

41
CPP/Common/StdOutStream.h Executable file → Normal file
View File

@@ -1,33 +1,40 @@
// Common/StdOutStream.h
#ifndef __COMMON_STDOUTSTREAM_H
#define __COMMON_STDOUTSTREAM_H
#ifndef __COMMON_STD_OUT_STREAM_H
#define __COMMON_STD_OUT_STREAM_H
#include <stdio.h>
#include "Types.h"
#include "MyString.h"
#include "MyTypes.h"
class CStdOutStream
{
bool _streamIsOpen;
FILE *_stream;
bool _streamIsOpen;
public:
CStdOutStream (): _streamIsOpen(false), _stream(0) {};
CStdOutStream (FILE *stream): _streamIsOpen(false), _stream(stream) {};
~CStdOutStream ();
CStdOutStream(): _stream(0), _streamIsOpen(false) {};
CStdOutStream(FILE *stream): _stream(stream), _streamIsOpen(false) {};
~CStdOutStream() { Close(); }
operator FILE *() { return _stream; }
bool Open(const char *fileName);
bool Close();
bool Flush();
CStdOutStream & operator<<(CStdOutStream & (* aFunction)(CStdOutStream &));
CStdOutStream & operator<<(const char *string);
CStdOutStream & operator<<(const wchar_t *string);
CStdOutStream & operator<<(char c);
CStdOutStream & operator<<(int number);
CStdOutStream & operator<<(UInt64 number);
bool Open(const char *fileName) throw();
bool Close() throw();
bool Flush() throw();
CStdOutStream & operator<<(CStdOutStream & (* func)(CStdOutStream &));
CStdOutStream & operator<<(const char *s) throw();
CStdOutStream & operator<<(char c) throw();
CStdOutStream & operator<<(Int32 number) throw();
CStdOutStream & operator<<(Int64 number) throw();
CStdOutStream & operator<<(UInt32 number) throw();
CStdOutStream & operator<<(UInt64 number) throw();
CStdOutStream & operator<<(const wchar_t *s);
void PrintUString(const UString &s, AString &temp);
};
CStdOutStream & endl(CStdOutStream & outStream);
CStdOutStream & endl(CStdOutStream & outStream) throw();
extern CStdOutStream g_StdOut;
extern CStdOutStream g_StdErr;

90
CPP/Common/StringConvert.cpp Executable file → Normal file
View File

@@ -15,8 +15,8 @@ UString MultiByteToUnicodeString(const AString &srcString, UINT codePage)
if (!srcString.IsEmpty())
{
int numChars = MultiByteToWideChar(codePage, 0, srcString,
srcString.Length(), resultString.GetBuffer(srcString.Length()),
srcString.Length() + 1);
srcString.Len(), resultString.GetBuffer(srcString.Len()),
srcString.Len() + 1);
if (numChars == 0)
throw 282228;
resultString.ReleaseBuffer(numChars);
@@ -24,15 +24,83 @@ UString MultiByteToUnicodeString(const AString &srcString, UINT codePage)
return resultString;
}
void MultiByteToUnicodeString2(UString &dest, const AString &srcString, UINT codePage)
{
dest.Empty();
if (!srcString.IsEmpty())
{
wchar_t *destBuf = dest.GetBuffer(srcString.Len());
const char *sp = (const char *)srcString;
unsigned i;
for (i = 0;;)
{
char c = sp[i];
if ((Byte)c >= 0x80 || c == 0)
break;
destBuf[i++] = (wchar_t)c;
}
if (i != srcString.Len())
{
unsigned numChars = MultiByteToWideChar(codePage, 0, sp + i,
srcString.Len() - i, destBuf + i,
srcString.Len() + 1 - i);
if (numChars == 0)
throw 282228;
i += numChars;
}
dest.ReleaseBuffer(i);
}
}
void UnicodeStringToMultiByte2(AString &dest, const UString &s, UINT codePage, char defaultChar, bool &defaultCharWasUsed)
{
dest.Empty();
defaultCharWasUsed = false;
if (!s.IsEmpty())
{
unsigned numRequiredBytes = s.Len() * 2;
char *destBuf = dest.GetBuffer(numRequiredBytes);
unsigned i;
const wchar_t *sp = (const wchar_t *)s;
for (i = 0;;)
{
wchar_t c = sp[i];
if (c >= 0x80 || c == 0)
break;
destBuf[i++] = (char)c;
}
defaultCharWasUsed = false;
if (i != s.Len())
{
BOOL defUsed;
unsigned numChars = WideCharToMultiByte(codePage, 0, sp + i, s.Len() - i,
destBuf + i, numRequiredBytes + 1 - i,
&defaultChar, &defUsed);
defaultCharWasUsed = (defUsed != FALSE);
if (numChars == 0)
throw 282229;
i += numChars;
}
dest.ReleaseBuffer(i);
}
}
void UnicodeStringToMultiByte2(AString &dest, const UString &srcString, UINT codePage)
{
bool defaultCharWasUsed;
UnicodeStringToMultiByte2(dest, srcString, codePage, '_', defaultCharWasUsed);
}
AString UnicodeStringToMultiByte(const UString &s, UINT codePage, char defaultChar, bool &defaultCharWasUsed)
{
AString dest;
defaultCharWasUsed = false;
if (!s.IsEmpty())
{
int numRequiredBytes = s.Length() * 2;
unsigned numRequiredBytes = s.Len() * 2;
BOOL defUsed;
int numChars = WideCharToMultiByte(codePage, 0, s, s.Length(),
int numChars = WideCharToMultiByte(codePage, 0, s, s.Len(),
dest.GetBuffer(numRequiredBytes), numRequiredBytes + 1,
&defaultChar, &defUsed);
defaultCharWasUsed = (defUsed != FALSE);
@@ -53,7 +121,7 @@ AString UnicodeStringToMultiByte(const UString &srcString, UINT codePage)
AString SystemStringToOemString(const CSysString &srcString)
{
AString result;
CharToOem(srcString, result.GetBuffer(srcString.Length() * 2));
CharToOem(srcString, result.GetBuffer(srcString.Len() * 2));
result.ReleaseBuffer();
return result;
}
@@ -64,12 +132,12 @@ AString SystemStringToOemString(const CSysString &srcString)
UString MultiByteToUnicodeString(const AString &srcString, UINT codePage)
{
UString resultString;
for (int i = 0; i < srcString.Length(); i++)
resultString += wchar_t(srcString[i]);
for (unsigned i = 0; i < srcString.Len(); i++)
resultString += (wchar_t)srcString[i];
/*
if (!srcString.IsEmpty())
{
int numChars = mbstowcs(resultString.GetBuffer(srcString.Length()), srcString, srcString.Length() + 1);
int numChars = mbstowcs(resultString.GetBuffer(srcString.Len()), srcString, srcString.Len() + 1);
if (numChars < 0) throw "Your environment does not support UNICODE";
resultString.ReleaseBuffer(numChars);
}
@@ -80,12 +148,12 @@ UString MultiByteToUnicodeString(const AString &srcString, UINT codePage)
AString UnicodeStringToMultiByte(const UString &srcString, UINT codePage)
{
AString resultString;
for (int i = 0; i < srcString.Length(); i++)
resultString += char(srcString[i]);
for (unsigned i = 0; i < srcString.Len(); i++)
resultString += (char)srcString[i];
/*
if (!srcString.IsEmpty())
{
int numRequiredBytes = srcString.Length() * 6 + 1;
int numRequiredBytes = srcString.Len() * 6 + 1;
int numChars = wcstombs(resultString.GetBuffer(numRequiredBytes), srcString, numRequiredBytes);
if (numChars < 0) throw "Your environment does not support UNICODE";
resultString.ReleaseBuffer(numChars);

10
CPP/Common/StringConvert.h Executable file → Normal file
View File

@@ -3,15 +3,19 @@
#ifndef __COMMON_STRING_CONVERT_H
#define __COMMON_STRING_CONVERT_H
#include "MyWindows.h"
#include "MyString.h"
#include "Types.h"
#include "MyWindows.h"
UString MultiByteToUnicodeString(const AString &srcString, UINT codePage = CP_ACP);
// optimized versions that work faster for ASCII strings
void MultiByteToUnicodeString2(UString &dest, const AString &srcString, UINT codePage = CP_ACP);
void UnicodeStringToMultiByte2(AString &dest, const UString &s, UINT codePage, char defaultChar, bool &defaultCharWasUsed);
void UnicodeStringToMultiByte2(AString &dest, const UString &srcString, UINT codePage);
AString UnicodeStringToMultiByte(const UString &srcString, UINT codePage, char defaultChar, bool &defaultCharWasUsed);
AString UnicodeStringToMultiByte(const UString &srcString, UINT codePage = CP_ACP);
inline const wchar_t* GetUnicodeString(const wchar_t* unicodeString)
{ return unicodeString; }
inline const UString& GetUnicodeString(const UString &unicodeString)

148
CPP/Common/StringToInt.cpp Executable file → Normal file
View File

@@ -4,94 +4,140 @@
#include "StringToInt.h"
UInt64 ConvertStringToUInt64(const char *s, const char **end)
static const UInt32 k_UInt32_max = 0xFFFFFFFF;
static const UInt64 k_UInt64_max = 0xFFFFFFFFFFFFFFFF;
#define CONVERT_STRING_TO_UINT_FUNC(uintType, charType) \
uintType ConvertStringTo ## uintType(const charType *s, const charType **end) { \
if (end) *end = s; \
uintType res = 0; \
for (;; s++) { \
charType c = *s; \
if (c < '0' || c > '9') { if (end) *end = s; return res; } \
if (res > (k_ ## uintType ## _max) / 10) return 0; \
res *= 10; \
unsigned v = (c - '0'); \
if (res > (k_ ## uintType ## _max) - v) return 0; \
res += v; }}
CONVERT_STRING_TO_UINT_FUNC(UInt32, char)
CONVERT_STRING_TO_UINT_FUNC(UInt32, wchar_t)
CONVERT_STRING_TO_UINT_FUNC(UInt64, char)
CONVERT_STRING_TO_UINT_FUNC(UInt64, wchar_t)
Int32 ConvertStringToInt32(const wchar_t *s, const wchar_t **end)
{
UInt64 result = 0;
for (;;)
if (end)
*end = s;
const wchar_t *s2 = s;
if (*s == '-')
s2++;
if (*s2 == 0)
return 0;
const wchar_t *end2;
UInt32 res = ConvertStringToUInt32(s2, &end2);
if (*s == '-')
{
if (res > ((UInt32)1 << (32 - 1)))
return 0;
}
else if ((res & ((UInt32)1 << (32 - 1))) != 0)
return 0;
if (end)
*end = end2;
if (*s == '-')
return -(Int32)res;
return (Int32)res;
}
UInt32 ConvertOctStringToUInt32(const char *s, const char **end)
{
if (end)
*end = s;
UInt32 res = 0;
for (;; s++)
{
char c = *s;
if (c < '0' || c > '9')
if (c < '0' || c > '7')
{
if (end != NULL)
if (end)
*end = s;
return result;
return res;
}
result *= 10;
result += (c - '0');
s++;
if ((res & (UInt32)7 << (32 - 3)) != 0)
return 0;
res <<= 3;
res |= (unsigned)(c - '0');
}
}
UInt64 ConvertOctStringToUInt64(const char *s, const char **end)
{
UInt64 result = 0;
for (;;)
if (end)
*end = s;
UInt64 res = 0;
for (;; s++)
{
char c = *s;
if (c < '0' || c > '7')
{
if (end != NULL)
if (end)
*end = s;
return result;
return res;
}
result <<= 3;
result += (c - '0');
s++;
if ((res & (UInt64)7 << (64 - 3)) != 0)
return 0;
res <<= 3;
res |= (unsigned)(c - '0');
}
}
UInt64 ConvertHexStringToUInt64(const char *s, const char **end)
UInt32 ConvertHexStringToUInt32(const char *s, const char **end)
{
UInt64 result = 0;
for (;;)
if (end)
*end = s;
UInt32 res = 0;
for (;; s++)
{
char c = *s;
UInt32 v;
unsigned v;
if (c >= '0' && c <= '9') v = (c - '0');
else if (c >= 'A' && c <= 'F') v = 10 + (c - 'A');
else if (c >= 'a' && c <= 'f') v = 10 + (c - 'a');
else
{
if (end != NULL)
if (end)
*end = s;
return result;
return res;
}
result <<= 4;
result |= v;
s++;
if ((res & (UInt32)0xF << (32 - 4)) != 0)
return 0;
res <<= 4;
res |= v;
}
}
UInt64 ConvertStringToUInt64(const wchar_t *s, const wchar_t **end)
UInt64 ConvertHexStringToUInt64(const char *s, const char **end)
{
UInt64 result = 0;
for (;;)
if (end)
*end = s;
UInt64 res = 0;
for (;; s++)
{
wchar_t c = *s;
if (c < '0' || c > '9')
char c = *s;
unsigned v;
if (c >= '0' && c <= '9') v = (c - '0');
else if (c >= 'A' && c <= 'F') v = 10 + (c - 'A');
else if (c >= 'a' && c <= 'f') v = 10 + (c - 'a');
else
{
if (end != NULL)
if (end)
*end = s;
return result;
return res;
}
result *= 10;
result += (c - '0');
s++;
if ((res & (UInt64)0xF << (64 - 4)) != 0)
return 0;
res <<= 4;
res |= v;
}
}
Int64 ConvertStringToInt64(const char *s, const char **end)
{
if (*s == '-')
return -(Int64)ConvertStringToUInt64(s + 1, end);
return ConvertStringToUInt64(s, end);
}
Int64 ConvertStringToInt64(const wchar_t *s, const wchar_t **end)
{
if (*s == L'-')
return -(Int64)ConvertStringToUInt64(s + 1, end);
return ConvertStringToUInt64(s, end);
}

19
CPP/Common/StringToInt.h Executable file → Normal file
View File

@@ -3,14 +3,19 @@
#ifndef __COMMON_STRING_TO_INT_H
#define __COMMON_STRING_TO_INT_H
#include "Types.h"
#include "MyTypes.h"
UInt64 ConvertStringToUInt64(const char *s, const char **end);
UInt64 ConvertOctStringToUInt64(const char *s, const char **end);
UInt64 ConvertHexStringToUInt64(const char *s, const char **end);
UInt64 ConvertStringToUInt64(const wchar_t *s, const wchar_t **end);
UInt32 ConvertStringToUInt32(const char *s, const char **end) throw();
UInt64 ConvertStringToUInt64(const char *s, const char **end) throw();
UInt32 ConvertStringToUInt32(const wchar_t *s, const wchar_t **end) throw();
UInt64 ConvertStringToUInt64(const wchar_t *s, const wchar_t **end) throw();
Int64 ConvertStringToInt64(const char *s, const char **end);
Int64 ConvertStringToInt64(const wchar_t *s, const wchar_t **end);
Int32 ConvertStringToInt32(const wchar_t *s, const wchar_t **end) throw();
UInt32 ConvertOctStringToUInt32(const char *s, const char **end) throw();
UInt64 ConvertOctStringToUInt64(const char *s, const char **end) throw();
UInt32 ConvertHexStringToUInt32(const char *s, const char **end) throw();
UInt64 ConvertHexStringToUInt64(const char *s, const char **end) throw();
#endif

74
CPP/Common/TextConfig.cpp Executable file → Normal file
View File

@@ -3,22 +3,19 @@
#include "StdAfx.h"
#include "TextConfig.h"
#include "Defs.h"
#include "UTFConvert.h"
static bool IsDelimitChar(char c)
static inline bool IsDelimitChar(char c)
{
return (c == ' ' || c == 0x0A || c == 0x0D ||
c == '\0' || c == '\t');
return (c == ' ' || c == 0x0A || c == 0x0D || c == '\0' || c == '\t');
}
static AString GetIDString(const char *string, int &finishPos)
static AString GetIDString(const char *s, unsigned &finishPos)
{
AString result;
for (finishPos = 0; ; finishPos++)
{
char c = string[finishPos];
char c = s[finishPos];
if (IsDelimitChar(c) || c == '=')
break;
result += c;
@@ -26,89 +23,78 @@ static AString GetIDString(const char *string, int &finishPos)
return result;
}
static bool WaitNextLine(const AString &string, int &pos)
static bool WaitNextLine(const AString &s, unsigned &pos)
{
for (;pos < string.Length(); pos++)
if (string[pos] == 0x0A)
for (; pos < s.Len(); pos++)
if (s[pos] == 0x0A)
return true;
return false;
}
static bool SkipSpaces(const AString &string, int &pos)
static bool SkipSpaces(const AString &s, unsigned &pos)
{
for (;pos < string.Length(); pos++)
for (; pos < s.Len(); pos++)
{
char c = string[pos];
char c = s[pos];
if (!IsDelimitChar(c))
{
if (c != ';')
return true;
if (!WaitNextLine(string, pos))
if (!WaitNextLine(s, pos))
return false;
}
}
return false;
}
bool GetTextConfig(const AString &string, CObjectVector<CTextConfigPair> &pairs)
bool GetTextConfig(const AString &s, CObjectVector<CTextConfigPair> &pairs)
{
pairs.Clear();
int pos = 0;
unsigned pos = 0;
/////////////////////
// read strings
for (;;)
{
if (!SkipSpaces(string, pos))
if (!SkipSpaces(s, pos))
break;
CTextConfigPair pair;
int finishPos;
AString temp = GetIDString(((const char *)string) + pos, finishPos);
unsigned finishPos;
AString temp = GetIDString(((const char *)s) + pos, finishPos);
if (!ConvertUTF8ToUnicode(temp, pair.ID))
return false;
if (finishPos == 0)
return false;
pos += finishPos;
if (!SkipSpaces(string, pos))
if (!SkipSpaces(s, pos))
return false;
if (string[pos] != '=')
if (s[pos] != '=')
return false;
pos++;
if (!SkipSpaces(string, pos))
if (!SkipSpaces(s, pos))
return false;
if (string[pos] != '\"')
if (s[pos] != '\"')
return false;
pos++;
AString message;
for (;;)
{
if (pos >= string.Length())
if (pos >= s.Len())
return false;
char c = string[pos++];
char c = s[pos++];
if (c == '\"')
break;
if (c == '\\')
{
char c = string[pos++];
char c = s[pos++];
switch(c)
{
case 'n':
message += '\n';
break;
case 't':
message += '\t';
break;
case '\\':
message += '\\';
break;
case '\"':
message += '\"';
break;
default:
message += '\\';
message += c;
break;
case 'n': message += '\n'; break;
case 't': message += '\t'; break;
case '\\': message += '\\'; break;
case '\"': message += '\"'; break;
default: message += '\\'; message += c; break;
}
}
else
@@ -123,8 +109,8 @@ bool GetTextConfig(const AString &string, CObjectVector<CTextConfigPair> &pairs)
int FindTextConfigItem(const CObjectVector<CTextConfigPair> &pairs, const UString &id)
{
for (int i = 0; i < pairs.Size(); i++)
if (pairs[i].ID.Compare(id) == 0)
FOR_VECTOR (i, pairs)
if (pairs[i].ID == id)
return i;
return -1;
}

7
CPP/Common/TextConfig.h Executable file → Normal file
View File

@@ -1,9 +1,8 @@
// Common/TextConfig.h
#ifndef __COMMON_TEXTCONFIG_H
#define __COMMON_TEXTCONFIG_H
#ifndef __COMMON_TEXT_CONFIG_H
#define __COMMON_TEXT_CONFIG_H
#include "MyVector.h"
#include "MyString.h"
struct CTextConfigPair
@@ -14,7 +13,7 @@ struct CTextConfigPair
bool GetTextConfig(const AString &text, CObjectVector<CTextConfigPair> &pairs);
int FindTextConfigItem(const CObjectVector<CTextConfigPair> &pairs, const UString &id);
int FindTextConfigItem(const CObjectVector<CTextConfigPair> &pairs, const UString &id) throw();
UString GetTextConfigValue(const CObjectVector<CTextConfigPair> &pairs, const UString &id);
#endif

View File

@@ -1,11 +0,0 @@
// Common/Types.h
#ifndef __COMMON_TYPES_H
#define __COMMON_TYPES_H
#include "../../C/Types.h"
typedef int HRes;
#endif

59
CPP/Common/UTFConvert.cpp Executable file → Normal file
View File

@@ -2,18 +2,53 @@
#include "StdAfx.h"
#include "MyTypes.h"
#include "UTFConvert.h"
#include "Types.h"
static const Byte kUtf8Limits[5] = { 0xC0, 0xE0, 0xF0, 0xF8, 0xFC };
static Bool Utf8_To_Utf16(wchar_t *dest, size_t *destLen, const char *src, size_t srcLen)
bool CheckUTF8(const char *src)
{
for (;;)
{
Byte c;
unsigned numAdds;
c = *src++;
if (c == 0)
return true;
if (c < 0x80)
continue;
if (c < 0xC0)
return false;
for (numAdds = 1; numAdds < 5; numAdds++)
if (c < kUtf8Limits[numAdds])
break;
UInt32 value = (c - kUtf8Limits[numAdds - 1]);
do
{
Byte c2 = *src++;
if (c2 < 0x80 || c2 >= 0xC0)
return false;
value <<= 6;
value |= (c2 - 0x80);
}
while (--numAdds);
if (value >= 0x110000)
return false;
}
}
static Bool Utf8_To_Utf16(wchar_t *dest, size_t *destLen, const char *src, size_t srcLen) throw()
{
size_t destPos = 0, srcPos = 0;
for (;;)
{
Byte c;
int numAdds;
unsigned numAdds;
if (srcPos == srcLen)
{
*destLen = destPos;
@@ -46,7 +81,7 @@ static Bool Utf8_To_Utf16(wchar_t *dest, size_t *destLen, const char *src, size_
value <<= 6;
value |= (c2 - 0x80);
}
while (--numAdds != 0);
while (--numAdds);
if (value < 0x10000)
{
@@ -124,11 +159,9 @@ bool ConvertUTF8ToUnicode(const AString &src, UString &dest)
{
dest.Empty();
size_t destLen = 0;
Utf8_To_Utf16(NULL, &destLen, src, src.Length());
wchar_t *p = dest.GetBuffer((int)destLen);
Bool res = Utf8_To_Utf16(p, &destLen, src, src.Length());
p[destLen] = 0;
dest.ReleaseBuffer();
Utf8_To_Utf16(NULL, &destLen, src, src.Len());
Bool res = Utf8_To_Utf16(dest.GetBuffer((unsigned)destLen), &destLen, src, src.Len());
dest.ReleaseBuffer((unsigned)destLen);
return res ? true : false;
}
@@ -136,10 +169,8 @@ bool ConvertUnicodeToUTF8(const UString &src, AString &dest)
{
dest.Empty();
size_t destLen = 0;
Utf16_To_Utf8(NULL, &destLen, src, src.Length());
char *p = dest.GetBuffer((int)destLen);
Bool res = Utf16_To_Utf8(p, &destLen, src, src.Length());
p[destLen] = 0;
dest.ReleaseBuffer();
Utf16_To_Utf8(NULL, &destLen, src, src.Len());
Bool res = Utf16_To_Utf8(dest.GetBuffer((unsigned)destLen), &destLen, src, src.Len());
dest.ReleaseBuffer((unsigned)destLen);
return res ? true : false;
}

5
CPP/Common/UTFConvert.h Executable file → Normal file
View File

@@ -1,10 +1,11 @@
// Common/UTFConvert.h
#ifndef __COMMON_UTFCONVERT_H
#define __COMMON_UTFCONVERT_H
#ifndef __COMMON_UTF_CONVERT_H
#define __COMMON_UTF_CONVERT_H
#include "MyString.h"
bool CheckUTF8(const char *src) throw();
bool ConvertUTF8ToUnicode(const AString &utfString, UString &resultString);
bool ConvertUnicodeToUTF8(const UString &unicodeString, AString &resultString);

401
CPP/Common/Wildcard.cpp Executable file → Normal file
View File

@@ -2,8 +2,6 @@
#include "StdAfx.h"
#include "../../C/Types.h"
#include "Wildcard.h"
bool g_CaseSensitive =
@@ -13,38 +11,44 @@ bool g_CaseSensitive =
true;
#endif
static const wchar_t kAnyCharsChar = L'*';
static const wchar_t kAnyCharChar = L'?';
#ifdef _WIN32
static const wchar_t kDirDelimiter1 = L'\\';
#endif
static const wchar_t kDirDelimiter2 = L'/';
static const UString kWildCardCharSet = L"?*";
static const UString kIllegalWildCardFileNameChars=
L"\x1\x2\x3\x4\x5\x6\x7\x8\x9\xA\xB\xC\xD\xE\xF"
L"\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1A\x1B\x1C\x1D\x1E\x1F"
L"\"/:<>\\|";
static inline bool IsCharDirLimiter(wchar_t c)
{
return (
#ifdef _WIN32
c == kDirDelimiter1 ||
#endif
c == kDirDelimiter2);
}
int CompareFileNames(const UString &s1, const UString &s2)
bool IsPath1PrefixedByPath2(const wchar_t *s1, const wchar_t *s2)
{
if (g_CaseSensitive)
return s1.Compare(s2);
return s1.CompareNoCase(s2);
{
for (;;)
{
wchar_t c2 = *s2++; if (c2 == 0) return true;
wchar_t c1 = *s1++;
if (MyCharUpper(c1) !=
MyCharUpper(c2))
return false;
}
}
for (;;)
{
wchar_t c2 = *s2++; if (c2 == 0) return true;
wchar_t c1 = *s1++; if (c1 != c2) return false;
}
}
int CompareFileNames(const wchar_t *s1, const wchar_t *s2)
{
if (g_CaseSensitive)
return wcscmp(s1, s2);
return MyStringCompareNoCase(s1, s2);
}
#ifndef USE_UNICODE_FSTRING
int CompareFileNames(const char *s1, const char *s2)
{
if (g_CaseSensitive)
return wcscmp(fs2us(s1), fs2us(s2));
return MyStringCompareNoCase(fs2us(s1), fs2us(s2));
}
#endif
// -----------------------------------------
// this function compares name with mask
// ? - any char
@@ -58,7 +62,7 @@ static bool EnhancedMaskTest(const wchar_t *mask, const wchar_t *name)
wchar_t c = *name;
if (m == 0)
return (c == 0);
if (m == kAnyCharsChar)
if (m == '*')
{
if (EnhancedMaskTest(mask + 1, name))
return true;
@@ -67,7 +71,7 @@ static bool EnhancedMaskTest(const wchar_t *mask, const wchar_t *name)
}
else
{
if (m == kAnyCharChar)
if (m == '?')
{
if (c == 0)
return false;
@@ -87,61 +91,84 @@ static bool EnhancedMaskTest(const wchar_t *mask, const wchar_t *name)
void SplitPathToParts(const UString &path, UStringVector &pathParts)
{
pathParts.Clear();
UString name;
int len = path.Length();
unsigned len = path.Len();
if (len == 0)
return;
for (int i = 0; i < len; i++)
{
wchar_t c = path[i];
if (IsCharDirLimiter(c))
UString name;
unsigned prev = 0;
for (unsigned i = 0; i < len; i++)
if (IsCharDirLimiter(path[i]))
{
name.SetFrom(path.Ptr(prev), i - prev);
pathParts.Add(name);
name.Empty();
prev = i + 1;
}
else
name += c;
}
name.SetFrom(path.Ptr(prev), len - prev);
pathParts.Add(name);
}
void SplitPathToParts(const UString &path, UString &dirPrefix, UString &name)
void SplitPathToParts_2(const UString &path, UString &dirPrefix, UString &name)
{
int i;
for (i = path.Length() - 1; i >= 0; i--)
if (IsCharDirLimiter(path[i]))
const wchar_t *start = path;
const wchar_t *p = start + path.Len();
for (; p != start; p--)
if (IsCharDirLimiter(*(p - 1)))
break;
dirPrefix = path.Left(i + 1);
name = path.Mid(i + 1);
dirPrefix.SetFrom(path, (unsigned)(p - start));
name = p;
}
void SplitPathToParts_Smart(const UString &path, UString &dirPrefix, UString &name)
{
const wchar_t *start = path;
const wchar_t *p = start + path.Len();
if (p != start)
{
if (IsCharDirLimiter(*(p - 1)))
p--;
for (; p != start; p--)
if (IsCharDirLimiter(*(p - 1)))
break;
}
dirPrefix.SetFrom(path, (unsigned)(p - start));
name = p;
}
UString ExtractDirPrefixFromPath(const UString &path)
{
int i;
for (i = path.Length() - 1; i >= 0; i--)
if (IsCharDirLimiter(path[i]))
const wchar_t *start = path;
const wchar_t *p = start + path.Len();
for (; p != start; p--)
if (IsCharDirLimiter(*(p - 1)))
break;
return path.Left(i + 1);
return path.Left((unsigned)(p - start));
}
UString ExtractFileNameFromPath(const UString &path)
{
int i;
for (i = path.Length() - 1; i >= 0; i--)
if (IsCharDirLimiter(path[i]))
const wchar_t *start = path;
const wchar_t *p = start + path.Len();
for (; p != start; p--)
if (IsCharDirLimiter(*(p - 1)))
break;
return path.Mid(i + 1);
return p;
}
bool CompareWildCardWithName(const UString &mask, const UString &name)
bool DoesWildcardMatchName(const UString &mask, const UString &name)
{
return EnhancedMaskTest(mask, name);
}
bool DoesNameContainWildCard(const UString &path)
bool DoesNameContainWildcard(const UString &path)
{
return (path.FindOneOf(kWildCardCharSet) >= 0);
for (unsigned i = 0; i < path.Len(); i++)
{
wchar_t c = path[i];
if (c == '*' || c == '?')
return true;
}
return false;
}
@@ -151,22 +178,36 @@ bool DoesNameContainWildCard(const UString &path)
namespace NWildcard {
#ifdef _WIN32
bool IsDriveColonName(const wchar_t *s)
{
wchar_t c = s[0];
return c != 0 && s[1] == ':' && s[2] == 0 && (c >= 'a' && c <= 'z' || c >= 'A' && c <= 'Z');
}
#endif
/*
M = MaskParts.Size();
N = TestNameParts.Size();
File Dir
ForFile req M<=N [N-M, N) -
nonreq M=N [0, M) -
ForFile rec M<=N [N-M, N) -
!ForDir nonrec M=N [0, M) -
ForDir req M<N [0, M) ... [N-M-1, N-1) same as ForBoth-File
nonreq [0, M) same as ForBoth-File
ForDir rec M<N [0, M) ... [N-M-1, N-1) same as ForBoth-File
!ForFile nonrec [0, M) same as ForBoth-File
ForBoth req m<=N [0, M) ... [N-M, N) same as ForBoth-File
nonreq [0, M) same as ForBoth-File
ForFile rec m<=N [0, M) ... [N-M, N) same as ForBoth-File
ForDir nonrec [0, M) same as ForBoth-File
*/
bool CItem::AreAllAllowed() const
{
return ForFile && ForDir && WildcardMatching && PathParts.Size() == 1 && PathParts.Front() == L"*";
}
bool CItem::CheckPath(const UStringVector &pathParts, bool isFile) const
{
if (!isFile && !ForDir)
@@ -176,36 +217,62 @@ bool CItem::CheckPath(const UStringVector &pathParts, bool isFile) const
return false;
int start = 0;
int finish = 0;
if (isFile)
{
if (!ForDir && !Recursive && delta !=0)
return false;
if (!ForDir)
{
if (Recursive)
start = delta;
else if (delta !=0)
return false;
}
if (!ForFile && delta == 0)
return false;
if (!ForDir && Recursive)
start = delta;
}
if (Recursive)
{
finish = delta;
if (isFile && !ForFile)
finish = delta - 1;
}
for (int d = start; d <= finish; d++)
{
int i;
unsigned i;
for (i = 0; i < PathParts.Size(); i++)
if (!CompareWildCardWithName(PathParts[i], pathParts[i + d]))
break;
{
if (WildcardMatching)
{
if (!DoesWildcardMatchName(PathParts[i], pathParts[i + d]))
break;
}
else
{
if (CompareFileNames(PathParts[i], pathParts[i + d]) != 0)
break;
}
}
if (i == PathParts.Size())
return true;
}
return false;
}
bool CCensorNode::AreAllAllowed() const
{
if (!Name.IsEmpty() ||
!SubNodes.IsEmpty() ||
!ExcludeItems.IsEmpty() ||
IncludeItems.Size() != 1)
return false;
return IncludeItems.Front().AreAllAllowed();
}
int CCensorNode::FindSubNode(const UString &name) const
{
for (int i = 0; i < SubNodes.Size(); i++)
FOR_VECTOR (i, SubNodes)
if (CompareFileNames(SubNodes[i].Name, name) == 0)
return i;
return -1;
@@ -223,11 +290,19 @@ void CCensorNode::AddItem(bool include, CItem &item)
{
if (item.PathParts.Size() <= 1)
{
if (item.PathParts.Size() != 0 && item.WildcardMatching)
{
if (!DoesNameContainWildcard(item.PathParts.Front()))
item.WildcardMatching = false;
}
AddItemSimple(include, item);
return;
}
const UString &front = item.PathParts.Front();
if (DoesNameContainWildCard(front))
// We can't ignore wildcard, since we don't allow wildcard in SubNodes[].Name
// if (item.Wildcard)
if (DoesNameContainWildcard(front))
{
AddItemSimple(include, item);
return;
@@ -239,19 +314,20 @@ void CCensorNode::AddItem(bool include, CItem &item)
SubNodes[index].AddItem(include, item);
}
void CCensorNode::AddItem(bool include, const UString &path, bool recursive, bool forFile, bool forDir)
void CCensorNode::AddItem(bool include, const UString &path, bool recursive, bool forFile, bool forDir, bool wildcardMatching)
{
CItem item;
SplitPathToParts(path, item.PathParts);
item.Recursive = recursive;
item.ForFile = forFile;
item.ForDir = forDir;
item.WildcardMatching = wildcardMatching;
AddItem(include, item);
}
bool CCensorNode::NeedCheckSubDirs() const
{
for (int i = 0; i < IncludeItems.Size(); i++)
FOR_VECTOR (i, IncludeItems)
{
const CItem &item = IncludeItems[i];
if (item.Recursive || item.PathParts.Size() > 1)
@@ -264,7 +340,7 @@ bool CCensorNode::AreThereIncludeItems() const
{
if (IncludeItems.Size() > 0)
return true;
for (int i = 0; i < SubNodes.Size(); i++)
FOR_VECTOR (i, SubNodes)
if (SubNodes[i].AreThereIncludeItems())
return true;
return false;
@@ -273,13 +349,13 @@ bool CCensorNode::AreThereIncludeItems() const
bool CCensorNode::CheckPathCurrent(bool include, const UStringVector &pathParts, bool isFile) const
{
const CObjectVector<CItem> &items = include ? IncludeItems : ExcludeItems;
for (int i = 0; i < items.Size(); i++)
FOR_VECTOR (i, items)
if (items[i].CheckPath(pathParts, isFile))
return true;
return false;
}
bool CCensorNode::CheckPath(UStringVector &pathParts, bool isFile, bool &include) const
bool CCensorNode::CheckPathVect(const UStringVector &pathParts, bool isFile, bool &include) const
{
if (CheckPathCurrent(false, pathParts, isFile))
{
@@ -288,30 +364,45 @@ bool CCensorNode::CheckPath(UStringVector &pathParts, bool isFile, bool &include
}
include = true;
bool finded = CheckPathCurrent(true, pathParts, isFile);
if (pathParts.Size() == 1)
if (pathParts.Size() <= 1)
return finded;
int index = FindSubNode(pathParts.Front());
if (index >= 0)
{
UStringVector pathParts2 = pathParts;
pathParts2.Delete(0);
if (SubNodes[index].CheckPath(pathParts2, isFile, include))
if (SubNodes[index].CheckPathVect(pathParts2, isFile, include))
return true;
}
return finded;
}
bool CCensorNode::CheckPath(const UString &path, bool isFile, bool &include) const
bool CCensorNode::CheckPath2(bool isAltStream, const UString &path, bool isFile, bool &include) const
{
UStringVector pathParts;
SplitPathToParts(path, pathParts);
return CheckPath(pathParts, isFile, include);
if (CheckPathVect(pathParts, isFile, include))
{
if (!include || !isAltStream)
return true;
}
if (isAltStream && !pathParts.IsEmpty())
{
UString &back = pathParts.Back();
int pos = back.Find(L':');
if (pos > 0)
{
back.DeleteFrom(pos);
return CheckPathVect(pathParts, isFile, include);
}
}
return false;
}
bool CCensorNode::CheckPath(const UString &path, bool isFile) const
bool CCensorNode::CheckPath(bool isAltStream, const UString &path, bool isFile) const
{
bool include;
if (CheckPath(path, isFile, include))
if (CheckPath2(isAltStream, path, isFile, include))
return include;
return false;
}
@@ -335,7 +426,7 @@ bool CCensorNode::CheckPathToRoot(bool include, const UString &path, bool isFile
}
*/
void CCensorNode::AddItem2(bool include, const UString &path, bool recursive)
void CCensorNode::AddItem2(bool include, const UString &path, bool recursive, bool wildcardMatching)
{
if (path.IsEmpty())
return;
@@ -347,13 +438,13 @@ void CCensorNode::AddItem2(bool include, const UString &path, bool recursive)
path2.DeleteBack();
forFile = false;
}
AddItem(include, path2, recursive, forFile, forFolder);
AddItem(include, path2, recursive, forFile, forFolder, wildcardMatching);
}
void CCensorNode::ExtendExclude(const CCensorNode &fromNodes)
{
ExcludeItems += fromNodes.ExcludeItems;
for (int i = 0; i < fromNodes.SubNodes.Size(); i++)
FOR_VECTOR (i, fromNodes.SubNodes)
{
const CCensorNode &node = fromNodes.SubNodes[i];
int subNodeIndex = FindSubNode(node.Name);
@@ -365,13 +456,13 @@ void CCensorNode::ExtendExclude(const CCensorNode &fromNodes)
int CCensor::FindPrefix(const UString &prefix) const
{
for (int i = 0; i < Pairs.Size(); i++)
FOR_VECTOR (i, Pairs)
if (CompareFileNames(Pairs[i].Prefix, prefix) == 0)
return i;
return -1;
}
void CCensor::AddItem(bool include, const UString &path, bool recursive)
void CCensor::AddItem(ECensorPathMode pathMode, bool include, const UString &path, bool recursive, bool wildcardMatching)
{
UStringVector pathParts;
if (path.IsEmpty())
@@ -383,40 +474,82 @@ void CCensor::AddItem(bool include, const UString &path, bool recursive)
forFile = false;
pathParts.DeleteBack();
}
const UString &front = pathParts.Front();
bool isAbs = false;
if (front.IsEmpty())
isAbs = true;
else if (front.Length() == 2 && front[1] == L':')
isAbs = true;
else
{
for (int i = 0; i < pathParts.Size(); i++)
{
const UString &part = pathParts[i];
if (part == L".." || part == L".")
{
isAbs = true;
break;
}
}
}
int numAbsParts = 0;
if (isAbs)
if (pathParts.Size() > 1)
numAbsParts = pathParts.Size() - 1;
else
numAbsParts = 1;
UString prefix;
for (int i = 0; i < numAbsParts; i++)
if (pathMode != k_AbsPath)
{
const UString &front = pathParts.Front();
if (DoesNameContainWildCard(front))
break;
prefix += front;
prefix += WCHAR_PATH_SEPARATOR;
pathParts.Delete(0);
bool isAbs = false;
if (front.IsEmpty())
isAbs = true;
else
{
#ifdef _WIN32
if (IsDriveColonName(front))
isAbs = true;
else
#endif
FOR_VECTOR (i, pathParts)
{
const UString &part = pathParts[i];
if (part == L".." || part == L".")
{
isAbs = true;
break;
}
}
}
unsigned numAbsParts = 0;
if (isAbs)
if (pathParts.Size() > 1)
numAbsParts = pathParts.Size() - 1;
else
numAbsParts = 1;
#ifdef _WIN32
// \\?\ case
if (numAbsParts >= 3)
{
if (pathParts[0].IsEmpty() &&
pathParts[1].IsEmpty() &&
pathParts[2] == L"?")
{
prefix =
WSTRING_PATH_SEPARATOR
WSTRING_PATH_SEPARATOR L"?"
WSTRING_PATH_SEPARATOR;
numAbsParts -= 3;
pathParts.DeleteFrontal(3);
}
}
#endif
if (numAbsParts > 1 && pathMode == k_FullPath)
numAbsParts = 1;
// We can't ignore wildcard, since we don't allow wildcard in SubNodes[].Name
// if (wildcardMatching)
for (unsigned i = 0; i < numAbsParts; i++)
{
{
const UString &front = pathParts.Front();
if (DoesNameContainWildcard(front))
break;
prefix += front;
prefix += WCHAR_PATH_SEPARATOR;
}
pathParts.Delete(0);
}
}
int index = FindPrefix(prefix);
if (index < 0)
index = Pairs.Add(CPair(prefix));
@@ -426,16 +559,17 @@ void CCensor::AddItem(bool include, const UString &path, bool recursive)
item.ForDir = true;
item.ForFile = forFile;
item.Recursive = recursive;
item.WildcardMatching = wildcardMatching;
Pairs[index].Head.AddItem(include, item);
}
bool CCensor::CheckPath(const UString &path, bool isFile) const
bool CCensor::CheckPath(bool isAltStream, const UString &path, bool isFile) const
{
bool finded = false;
for (int i = 0; i < Pairs.Size(); i++)
FOR_VECTOR (i, Pairs)
{
bool include;
if (Pairs[i].Head.CheckPath(path, isFile, include))
if (Pairs[i].Head.CheckPath2(isAltStream, path, isFile, include))
{
if (!include)
return false;
@@ -447,16 +581,35 @@ bool CCensor::CheckPath(const UString &path, bool isFile) const
void CCensor::ExtendExclude()
{
int i;
unsigned i;
for (i = 0; i < Pairs.Size(); i++)
if (Pairs[i].Prefix.IsEmpty())
break;
if (i == Pairs.Size())
return;
int index = i;
unsigned index = i;
for (i = 0; i < Pairs.Size(); i++)
if (index != i)
Pairs[i].Head.ExtendExclude(Pairs[index].Head);
}
void CCensor::AddPathsToCensor(ECensorPathMode censorPathMode)
{
FOR_VECTOR(i, CensorPaths)
{
const CCensorPath &cp = CensorPaths[i];
AddItem(censorPathMode, cp.Include, cp.Path, cp.Recursive, cp.WildcardMatching);
}
CensorPaths.Clear();
}
void CCensor::AddPreItem(bool include, const UString &path, bool recursive, bool wildcardMatching)
{
CCensorPath &cp = CensorPaths.AddNew();
cp.Path = path;
cp.Include = include;
cp.Recursive = recursive;
cp.WildcardMatching = wildcardMatching;
}
}

101
CPP/Common/Wildcard.h Executable file → Normal file
View File

@@ -5,51 +5,90 @@
#include "MyString.h"
int CompareFileNames(const UString &s1, const UString &s2);
int CompareFileNames(const wchar_t *s1, const wchar_t *s2) STRING_UNICODE_THROW;
#ifndef USE_UNICODE_FSTRING
int CompareFileNames(const char *s1, const char *s2);
#endif
bool IsPath1PrefixedByPath2(const wchar_t *s1, const wchar_t *s2);
inline bool IsCharDirLimiter(wchar_t c)
{
return c == WCHAR_PATH_SEPARATOR
#ifdef _WIN32
|| c == L'/'
#endif
;
}
void SplitPathToParts(const UString &path, UStringVector &pathParts);
void SplitPathToParts(const UString &path, UString &dirPrefix, UString &name);
void SplitPathToParts_2(const UString &path, UString &dirPrefix, UString &name);
void SplitPathToParts_Smart(const UString &path, UString &dirPrefix, UString &name); // ignores dir delimiter at the end of (path)
UString ExtractDirPrefixFromPath(const UString &path);
UString ExtractFileNameFromPath(const UString &path);
bool DoesNameContainWildCard(const UString &path);
bool CompareWildCardWithName(const UString &mask, const UString &name);
bool DoesNameContainWildcard(const UString &path);
bool DoesWildcardMatchName(const UString &mask, const UString &name);
namespace NWildcard {
#ifdef _WIN32
// returns true, if name is like "a:", "c:", ...
bool IsDriveColonName(const wchar_t *s);
#endif
struct CItem
{
UStringVector PathParts;
bool Recursive;
bool ForFile;
bool ForDir;
bool WildcardMatching;
#ifdef _WIN32
bool IsDriveItem() const
{
return PathParts.Size() == 1 && !ForFile && ForDir && IsDriveColonName(PathParts[0]);
}
#endif
// CItem(): WildcardMatching(true) {}
bool AreAllAllowed() const;
bool CheckPath(const UStringVector &pathParts, bool isFile) const;
};
class CCensorNode
{
CCensorNode *Parent;
bool CheckPathCurrent(bool include, const UStringVector &pathParts, bool isFile) const;
void AddItemSimple(bool include, CItem &item);
bool CheckPath(UStringVector &pathParts, bool isFile, bool &include) const;
bool CheckPathVect(const UStringVector &pathParts, bool isFile, bool &include) const;
public:
CCensorNode(): Parent(0) { };
CCensorNode(const UString &name, CCensorNode *parent): Name(name), Parent(parent) { };
UString Name;
UString Name; // wildcard is not allowed here
CObjectVector<CCensorNode> SubNodes;
CObjectVector<CItem> IncludeItems;
CObjectVector<CItem> ExcludeItems;
bool AreAllAllowed() const;
int FindSubNode(const UString &path) const;
void AddItem(bool include, CItem &item);
void AddItem(bool include, const UString &path, bool recursive, bool forFile, bool forDir);
void AddItem2(bool include, const UString &path, bool recursive);
void AddItem(bool include, const UString &path, bool recursive, bool forFile, bool forDir, bool wildcardMatching);
void AddItem2(bool include, const UString &path, bool recursive, bool wildcardMatching);
bool NeedCheckSubDirs() const;
bool AreThereIncludeItems() const;
bool CheckPath(const UString &path, bool isFile, bool &include) const;
bool CheckPath(const UString &path, bool isFile) const;
bool CheckPath2(bool isAltStream, const UString &path, bool isFile, bool &include) const;
bool CheckPath(bool isAltStream, const UString &path, bool isFile) const;
bool CheckPathToRoot(bool include, UStringVector &pathParts, bool isFile) const;
// bool CheckPathToRoot(const UString &path, bool isFile, bool include) const;
@@ -60,21 +99,59 @@ struct CPair
{
UString Prefix;
CCensorNode Head;
CPair(const UString &prefix): Prefix(prefix) { };
};
enum ECensorPathMode
{
k_RelatPath, // absolute prefix as Prefix, remain path in Tree
k_FullPath, // drive prefix as Prefix, remain path in Tree
k_AbsPath // full path in Tree
};
struct CCensorPath
{
UString Path;
bool Include;
bool Recursive;
bool WildcardMatching;
CCensorPath():
Include(true),
Recursive(false),
WildcardMatching(true)
{}
};
class CCensor
{
int FindPrefix(const UString &prefix) const;
public:
CObjectVector<CPair> Pairs;
CObjectVector<NWildcard::CCensorPath> CensorPaths;
bool AllAreRelative() const
{ return (Pairs.Size() == 1 && Pairs.Front().Prefix.IsEmpty()); }
void AddItem(bool include, const UString &path, bool recursive);
bool CheckPath(const UString &path, bool isFile) const;
void AddItem(ECensorPathMode pathMode, bool include, const UString &path, bool recursive, bool wildcardMatching);
bool CheckPath(bool isAltStream, const UString &path, bool isFile) const;
void ExtendExclude();
void AddPathsToCensor(NWildcard::ECensorPathMode censorPathMode);
void AddPreItem(bool include, const UString &path, bool recursive, bool wildcardMatching);
void AddPreItem(const UString &path)
{
AddPreItem(true, path, false, false);
}
void AddPreItem_Wildcard()
{
AddPreItem(true, L"*", false, true);
}
};
}
#endif

54
CPP/Common/XzCrc64Reg.cpp Normal file
View File

@@ -0,0 +1,54 @@
// XzCrc64Reg.cpp
#include "StdAfx.h"
#include "../../C/CpuArch.h"
#include "../../C/XzCrc64.h"
#include "../Common/MyCom.h"
#include "../7zip/ICoder.h"
#include "../7zip/Common/RegisterCodec.h"
class CXzCrc64Hasher:
public IHasher,
public CMyUnknownImp
{
UInt64 _crc;
public:
CXzCrc64Hasher(): _crc(CRC64_INIT_VAL) {}
MY_UNKNOWN_IMP
STDMETHOD_(void, Init)();
STDMETHOD_(void, Update)(const void *data, UInt32 size);
STDMETHOD_(void, Final)(Byte *digest);
STDMETHOD_(UInt32, GetDigestSize)();
};
STDMETHODIMP_(void) CXzCrc64Hasher::Init()
{
_crc = CRC64_INIT_VAL;
}
STDMETHODIMP_(void) CXzCrc64Hasher::Update(const void *data, UInt32 size)
{
_crc = Crc64Update(_crc, data, size);
}
STDMETHODIMP_(void) CXzCrc64Hasher::Final(Byte *digest)
{
UInt64 val = CRC64_GET_DIGEST(_crc);
SetUi64(digest, val);
}
STDMETHODIMP_(UInt32) CXzCrc64Hasher::GetDigestSize()
{
return 8;
}
static IHasher *CreateHasher() { return new CXzCrc64Hasher; }
static CHasherInfo g_HasherInfo = { CreateHasher, 0x4, L"CRC64", 8 };
REGISTER_HASHER(Crc64)