ruby-lzma 0.4.1
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +6 -0
- data/README.markdown +15 -0
- data/Rakefile +53 -0
- data/VERSION +1 -0
- data/ext/Alloc.cpp +118 -0
- data/ext/Alloc.h +29 -0
- data/ext/BinTree.h +55 -0
- data/ext/BinTree2.h +12 -0
- data/ext/BinTree3.h +16 -0
- data/ext/BinTree3Z.h +16 -0
- data/ext/BinTree4.h +18 -0
- data/ext/BinTree4b.h +20 -0
- data/ext/BinTreeMain.h +444 -0
- data/ext/BranchX86.c +101 -0
- data/ext/BranchX86.h +19 -0
- data/ext/CRC.cpp +61 -0
- data/ext/CRC.h +36 -0
- data/ext/C_FileIO.h +45 -0
- data/ext/CommandLineParser.h +82 -0
- data/ext/Defs.h +20 -0
- data/ext/FileStreams.h +98 -0
- data/ext/HC.h +55 -0
- data/ext/HC2.h +13 -0
- data/ext/HC3.h +17 -0
- data/ext/HC4.h +19 -0
- data/ext/HC4b.h +21 -0
- data/ext/HCMain.h +350 -0
- data/ext/ICoder.h +156 -0
- data/ext/IMatchFinder.h +63 -0
- data/ext/IStream.h +62 -0
- data/ext/InBuffer.cpp +80 -0
- data/ext/InBuffer.h +76 -0
- data/ext/LZInWindow.cpp +102 -0
- data/ext/LZInWindow.h +84 -0
- data/ext/LZMA.h +82 -0
- data/ext/LZMADecoder.h +248 -0
- data/ext/LZMAEncoder.cpp +1504 -0
- data/ext/LZMAEncoder.h +416 -0
- data/ext/LZOutWindow.cpp +17 -0
- data/ext/LZOutWindow.h +66 -0
- data/ext/LzmaBench.h +11 -0
- data/ext/LzmaDecode.c +588 -0
- data/ext/LzmaDecode.h +131 -0
- data/ext/LzmaRam.cpp +228 -0
- data/ext/LzmaRam.h +46 -0
- data/ext/LzmaRamDecode.c +79 -0
- data/ext/LzmaRamDecode.h +55 -0
- data/ext/MyCom.h +203 -0
- data/ext/MyGuidDef.h +54 -0
- data/ext/MyInitGuid.h +13 -0
- data/ext/MyString.h +631 -0
- data/ext/MyUnknown.h +24 -0
- data/ext/MyWindows.h +183 -0
- data/ext/OutBuffer.cpp +117 -0
- data/ext/OutBuffer.h +64 -0
- data/ext/Pat.h +318 -0
- data/ext/Pat2.h +22 -0
- data/ext/Pat2H.h +24 -0
- data/ext/Pat2R.h +20 -0
- data/ext/Pat3H.h +24 -0
- data/ext/Pat4H.h +24 -0
- data/ext/PatMain.h +989 -0
- data/ext/RangeCoder.h +205 -0
- data/ext/RangeCoderBit.cpp +80 -0
- data/ext/RangeCoderBit.h +120 -0
- data/ext/RangeCoderBitTree.h +161 -0
- data/ext/RangeCoderOpt.h +31 -0
- data/ext/StdAfx.h +8 -0
- data/ext/StreamUtils.cpp +44 -0
- data/ext/StreamUtils.h +11 -0
- data/ext/StringConvert.h +71 -0
- data/ext/StringToInt.h +17 -0
- data/ext/Types.h +19 -0
- data/ext/Vector.h +211 -0
- data/ext/extconf.rb +7 -0
- data/ext/lzma_ruby.cpp +51 -0
- data/ext/lzmalib.h +64 -0
- data/ext/mylib.cpp +81 -0
- data/java/SevenZip/CRC.java +52 -0
- data/java/SevenZip/Compression/LZ/BinTree.java +382 -0
- data/java/SevenZip/Compression/LZ/InWindow.java +131 -0
- data/java/SevenZip/Compression/LZ/OutWindow.java +85 -0
- data/java/SevenZip/Compression/LZMA/Base.java +88 -0
- data/java/SevenZip/Compression/LZMA/Decoder.java +329 -0
- data/java/SevenZip/Compression/LZMA/Encoder.java +1415 -0
- data/java/SevenZip/Compression/RangeCoder/BitTreeDecoder.java +55 -0
- data/java/SevenZip/Compression/RangeCoder/BitTreeEncoder.java +99 -0
- data/java/SevenZip/Compression/RangeCoder/Decoder.java +88 -0
- data/java/SevenZip/Compression/RangeCoder/Encoder.java +151 -0
- data/java/SevenZip/ICodeProgress.java +6 -0
- data/java/SevenZip/LzmaAlone.java +253 -0
- data/java/SevenZip/LzmaBench.java +391 -0
- data/java/com/ephemeronindustries/lzma/LZMA.java +104 -0
- data/lib/lzma.rb +32 -0
- data/ruby-lzma.gemspec +136 -0
- data/test/test_lzma.rb +42 -0
- metadata +157 -0
data/ext/LzmaRamDecode.h
ADDED
@@ -0,0 +1,55 @@
|
|
1
|
+
/* LzmaRamDecode.h */
|
2
|
+
|
3
|
+
#ifndef __LzmaRamDecode_h
|
4
|
+
#define __LzmaRamDecode_h
|
5
|
+
|
6
|
+
#include <stdlib.h>
|
7
|
+
|
8
|
+
/*
|
9
|
+
LzmaRamGetUncompressedSize:
|
10
|
+
In:
|
11
|
+
inBuffer - input data
|
12
|
+
inSize - input data size
|
13
|
+
Out:
|
14
|
+
outSize - uncompressed size
|
15
|
+
Return code:
|
16
|
+
0 - OK
|
17
|
+
1 - Error in headers
|
18
|
+
*/
|
19
|
+
|
20
|
+
int LzmaRamGetUncompressedSize(
|
21
|
+
const unsigned char *inBuffer,
|
22
|
+
size_t inSize,
|
23
|
+
size_t *outSize);
|
24
|
+
|
25
|
+
|
26
|
+
/*
|
27
|
+
LzmaRamDecompress:
|
28
|
+
In:
|
29
|
+
inBuffer - input data
|
30
|
+
inSize - input data size
|
31
|
+
outBuffer - output data
|
32
|
+
outSize - output size
|
33
|
+
allocFunc - alloc function (can be malloc)
|
34
|
+
freeFunc - free function (can be free)
|
35
|
+
Out:
|
36
|
+
outSizeProcessed - processed size
|
37
|
+
Return code:
|
38
|
+
0 - OK
|
39
|
+
1 - Error in headers / data stream
|
40
|
+
2 - Memory allocating error
|
41
|
+
|
42
|
+
Memory requirements depend from properties of LZMA stream.
|
43
|
+
With default lzma settings it's about 16 KB.
|
44
|
+
*/
|
45
|
+
|
46
|
+
int LzmaRamDecompress(
|
47
|
+
const unsigned char *inBuffer,
|
48
|
+
size_t inSize,
|
49
|
+
unsigned char *outBuffer,
|
50
|
+
size_t outSize,
|
51
|
+
size_t *outSizeProcessed,
|
52
|
+
void * (*allocFunc)(size_t size),
|
53
|
+
void (*freeFunc)(void *));
|
54
|
+
|
55
|
+
#endif
|
data/ext/MyCom.h
ADDED
@@ -0,0 +1,203 @@
|
|
1
|
+
// MyCom.h
|
2
|
+
|
3
|
+
#ifndef __MYCOM_H
|
4
|
+
#define __MYCOM_H
|
5
|
+
|
6
|
+
#include "MyWindows.h"
|
7
|
+
|
8
|
+
#define RINOK(x) { HRESULT __result_ = (x); if(__result_ != S_OK) return __result_; }
|
9
|
+
|
10
|
+
template <class T>
|
11
|
+
class CMyComPtr
|
12
|
+
{
|
13
|
+
T* _p;
|
14
|
+
public:
|
15
|
+
// typedef T _PtrClass;
|
16
|
+
CMyComPtr() { _p = NULL;}
|
17
|
+
CMyComPtr(T* p) {if ((_p = p) != NULL) p->AddRef(); }
|
18
|
+
CMyComPtr(const CMyComPtr<T>& lp)
|
19
|
+
{
|
20
|
+
if ((_p = lp._p) != NULL)
|
21
|
+
_p->AddRef();
|
22
|
+
}
|
23
|
+
~CMyComPtr() { if (_p) _p->Release(); }
|
24
|
+
void Release() { if (_p) { _p->Release(); _p = NULL; } }
|
25
|
+
operator T*() const { return (T*)_p; }
|
26
|
+
// T& operator*() const { return *_p; }
|
27
|
+
T** operator&() { return &_p; }
|
28
|
+
T* operator->() const { return _p; }
|
29
|
+
T* operator=(T* p)
|
30
|
+
{
|
31
|
+
if (p != 0)
|
32
|
+
p->AddRef();
|
33
|
+
if (_p)
|
34
|
+
_p->Release();
|
35
|
+
_p = p;
|
36
|
+
return p;
|
37
|
+
}
|
38
|
+
T* operator=(const CMyComPtr<T>& lp) { return (*this = lp._p); }
|
39
|
+
bool operator!() const { return (_p == NULL); }
|
40
|
+
// bool operator==(T* pT) const { return _p == pT; }
|
41
|
+
// Compare two objects for equivalence
|
42
|
+
void Attach(T* p2)
|
43
|
+
{
|
44
|
+
Release();
|
45
|
+
_p = p2;
|
46
|
+
}
|
47
|
+
T* Detach()
|
48
|
+
{
|
49
|
+
T* pt = _p;
|
50
|
+
_p = NULL;
|
51
|
+
return pt;
|
52
|
+
}
|
53
|
+
#ifdef _WIN32
|
54
|
+
HRESULT CoCreateInstance(REFCLSID rclsid, REFIID iid, LPUNKNOWN pUnkOuter = NULL, DWORD dwClsContext = CLSCTX_ALL)
|
55
|
+
{
|
56
|
+
return ::CoCreateInstance(rclsid, pUnkOuter, dwClsContext, iid, (void**)&_p);
|
57
|
+
}
|
58
|
+
#endif
|
59
|
+
/*
|
60
|
+
HRESULT CoCreateInstance(LPCOLESTR szProgID, LPUNKNOWN pUnkOuter = NULL, DWORD dwClsContext = CLSCTX_ALL)
|
61
|
+
{
|
62
|
+
CLSID clsid;
|
63
|
+
HRESULT hr = CLSIDFromProgID(szProgID, &clsid);
|
64
|
+
ATLASSERT(_p == NULL);
|
65
|
+
if (SUCCEEDED(hr))
|
66
|
+
hr = ::CoCreateInstance(clsid, pUnkOuter, dwClsContext, __uuidof(T), (void**)&_p);
|
67
|
+
return hr;
|
68
|
+
}
|
69
|
+
*/
|
70
|
+
template <class Q>
|
71
|
+
HRESULT QueryInterface(REFGUID iid, Q** pp) const
|
72
|
+
{
|
73
|
+
return _p->QueryInterface(iid, (void**)pp);
|
74
|
+
}
|
75
|
+
};
|
76
|
+
|
77
|
+
//////////////////////////////////////////////////////////
|
78
|
+
|
79
|
+
class CMyComBSTR
|
80
|
+
{
|
81
|
+
public:
|
82
|
+
BSTR m_str;
|
83
|
+
CMyComBSTR() { m_str = NULL; }
|
84
|
+
CMyComBSTR(LPCOLESTR pSrc) { m_str = ::SysAllocString(pSrc); }
|
85
|
+
// CMyComBSTR(int nSize) { m_str = ::SysAllocStringLen(NULL, nSize); }
|
86
|
+
// CMyComBSTR(int nSize, LPCOLESTR sz) { m_str = ::SysAllocStringLen(sz, nSize); }
|
87
|
+
CMyComBSTR(const CMyComBSTR& src) { m_str = src.MyCopy(); }
|
88
|
+
/*
|
89
|
+
CMyComBSTR(REFGUID src)
|
90
|
+
{
|
91
|
+
LPOLESTR szGuid;
|
92
|
+
StringFromCLSID(src, &szGuid);
|
93
|
+
m_str = ::SysAllocString(szGuid);
|
94
|
+
CoTaskMemFree(szGuid);
|
95
|
+
}
|
96
|
+
*/
|
97
|
+
~CMyComBSTR() { ::SysFreeString(m_str); }
|
98
|
+
CMyComBSTR& operator=(const CMyComBSTR& src)
|
99
|
+
{
|
100
|
+
if (m_str != src.m_str)
|
101
|
+
{
|
102
|
+
if (m_str)
|
103
|
+
::SysFreeString(m_str);
|
104
|
+
m_str = src.MyCopy();
|
105
|
+
}
|
106
|
+
return *this;
|
107
|
+
}
|
108
|
+
CMyComBSTR& operator=(LPCOLESTR pSrc)
|
109
|
+
{
|
110
|
+
::SysFreeString(m_str);
|
111
|
+
m_str = ::SysAllocString(pSrc);
|
112
|
+
return *this;
|
113
|
+
}
|
114
|
+
unsigned int Length() const { return ::SysStringLen(m_str); }
|
115
|
+
operator BSTR() const { return m_str; }
|
116
|
+
BSTR* operator&() { return &m_str; }
|
117
|
+
BSTR MyCopy() const
|
118
|
+
{
|
119
|
+
int byteLen = ::SysStringByteLen(m_str);
|
120
|
+
BSTR res = ::SysAllocStringByteLen(NULL, byteLen);
|
121
|
+
memmove(res, m_str, byteLen);
|
122
|
+
return res;
|
123
|
+
}
|
124
|
+
void Attach(BSTR src) { m_str = src; }
|
125
|
+
BSTR Detach()
|
126
|
+
{
|
127
|
+
BSTR s = m_str;
|
128
|
+
m_str = NULL;
|
129
|
+
return s;
|
130
|
+
}
|
131
|
+
void Empty()
|
132
|
+
{
|
133
|
+
::SysFreeString(m_str);
|
134
|
+
m_str = NULL;
|
135
|
+
}
|
136
|
+
bool operator!() const { return (m_str == NULL); }
|
137
|
+
};
|
138
|
+
|
139
|
+
|
140
|
+
//////////////////////////////////////////////////////////
|
141
|
+
|
142
|
+
class CMyUnknownImp
|
143
|
+
{
|
144
|
+
public:
|
145
|
+
ULONG __m_RefCount;
|
146
|
+
CMyUnknownImp(): __m_RefCount(0) {}
|
147
|
+
};
|
148
|
+
|
149
|
+
#define MY_QUERYINTERFACE_BEGIN STDMETHOD(QueryInterface) \
|
150
|
+
(REFGUID iid, void **outObject) {
|
151
|
+
|
152
|
+
#define MY_QUERYINTERFACE_ENTRY(i) if (iid == IID_ ## i) \
|
153
|
+
{ *outObject = (void *)(i *)this; AddRef(); return S_OK; }
|
154
|
+
|
155
|
+
#define MY_QUERYINTERFACE_END return E_NOINTERFACE; }
|
156
|
+
|
157
|
+
#define MY_ADDREF_RELEASE \
|
158
|
+
STDMETHOD_(ULONG, AddRef)() { return ++__m_RefCount; } \
|
159
|
+
STDMETHOD_(ULONG, Release)() { if (--__m_RefCount != 0) \
|
160
|
+
return __m_RefCount; delete this; return 0; }
|
161
|
+
|
162
|
+
#define MY_UNKNOWN_IMP_SPEC(i) \
|
163
|
+
MY_QUERYINTERFACE_BEGIN \
|
164
|
+
i \
|
165
|
+
MY_QUERYINTERFACE_END \
|
166
|
+
MY_ADDREF_RELEASE
|
167
|
+
|
168
|
+
|
169
|
+
#define MY_UNKNOWN_IMP STDMETHOD(QueryInterface)(REFGUID, void **) { \
|
170
|
+
MY_QUERYINTERFACE_END \
|
171
|
+
MY_ADDREF_RELEASE
|
172
|
+
|
173
|
+
#define MY_UNKNOWN_IMP1(i) MY_UNKNOWN_IMP_SPEC( \
|
174
|
+
MY_QUERYINTERFACE_ENTRY(i) \
|
175
|
+
)
|
176
|
+
|
177
|
+
#define MY_UNKNOWN_IMP2(i1, i2) MY_UNKNOWN_IMP_SPEC( \
|
178
|
+
MY_QUERYINTERFACE_ENTRY(i1) \
|
179
|
+
MY_QUERYINTERFACE_ENTRY(i2) \
|
180
|
+
)
|
181
|
+
|
182
|
+
#define MY_UNKNOWN_IMP3(i1, i2, i3) MY_UNKNOWN_IMP_SPEC( \
|
183
|
+
MY_QUERYINTERFACE_ENTRY(i1) \
|
184
|
+
MY_QUERYINTERFACE_ENTRY(i2) \
|
185
|
+
MY_QUERYINTERFACE_ENTRY(i3) \
|
186
|
+
)
|
187
|
+
|
188
|
+
#define MY_UNKNOWN_IMP4(i1, i2, i3, i4) MY_UNKNOWN_IMP_SPEC( \
|
189
|
+
MY_QUERYINTERFACE_ENTRY(i1) \
|
190
|
+
MY_QUERYINTERFACE_ENTRY(i2) \
|
191
|
+
MY_QUERYINTERFACE_ENTRY(i3) \
|
192
|
+
MY_QUERYINTERFACE_ENTRY(i4) \
|
193
|
+
)
|
194
|
+
|
195
|
+
#define MY_UNKNOWN_IMP5(i1, i2, i3, i4, i5) MY_UNKNOWN_IMP_SPEC( \
|
196
|
+
MY_QUERYINTERFACE_ENTRY(i1) \
|
197
|
+
MY_QUERYINTERFACE_ENTRY(i2) \
|
198
|
+
MY_QUERYINTERFACE_ENTRY(i3) \
|
199
|
+
MY_QUERYINTERFACE_ENTRY(i4) \
|
200
|
+
MY_QUERYINTERFACE_ENTRY(i5) \
|
201
|
+
)
|
202
|
+
|
203
|
+
#endif
|
data/ext/MyGuidDef.h
ADDED
@@ -0,0 +1,54 @@
|
|
1
|
+
// Common/MyGuidDef.h
|
2
|
+
|
3
|
+
#ifndef GUID_DEFINED
|
4
|
+
#define GUID_DEFINED
|
5
|
+
|
6
|
+
#include "Types.h"
|
7
|
+
|
8
|
+
typedef struct {
|
9
|
+
UInt32 Data1;
|
10
|
+
UInt16 Data2;
|
11
|
+
UInt16 Data3;
|
12
|
+
unsigned char Data4[8];
|
13
|
+
} GUID;
|
14
|
+
|
15
|
+
#ifdef __cplusplus
|
16
|
+
#define REFGUID const GUID &
|
17
|
+
#else
|
18
|
+
#define REFGUID const GUID *
|
19
|
+
#endif
|
20
|
+
|
21
|
+
#define REFCLSID REFGUID
|
22
|
+
#define REFIID REFGUID
|
23
|
+
|
24
|
+
#ifdef __cplusplus
|
25
|
+
inline bool operator==(REFGUID g1, REFGUID g2)
|
26
|
+
{
|
27
|
+
for (int i = 0; i < (int)sizeof(g1); i++)
|
28
|
+
if (((unsigned char *)&g1)[i] != ((unsigned char *)&g2)[i])
|
29
|
+
return false;
|
30
|
+
return true;
|
31
|
+
}
|
32
|
+
inline bool operator!=(REFGUID g1, REFGUID g2) { return !(g1 == g2); }
|
33
|
+
#endif
|
34
|
+
|
35
|
+
#ifdef __cplusplus
|
36
|
+
#define MY_EXTERN_C extern "C"
|
37
|
+
#else
|
38
|
+
#define MY_EXTERN_C extern
|
39
|
+
#endif
|
40
|
+
|
41
|
+
#endif // GUID_DEFINED
|
42
|
+
|
43
|
+
|
44
|
+
#ifdef DEFINE_GUID
|
45
|
+
#undef DEFINE_GUID
|
46
|
+
#endif
|
47
|
+
|
48
|
+
#ifdef INITGUID
|
49
|
+
#define DEFINE_GUID(name, l, w1, w2, b1, b2, b3, b4, b5, b6, b7, b8) \
|
50
|
+
MY_EXTERN_C const GUID name = { l, w1, w2, { b1, b2, b3, b4, b5, b6, b7, b8 } }
|
51
|
+
#else
|
52
|
+
#define DEFINE_GUID(name, l, w1, w2, b1, b2, b3, b4, b5, b6, b7, b8) \
|
53
|
+
MY_EXTERN_C const GUID name
|
54
|
+
#endif
|
data/ext/MyInitGuid.h
ADDED
data/ext/MyString.h
ADDED
@@ -0,0 +1,631 @@
|
|
1
|
+
// Common/MyString.h
|
2
|
+
|
3
|
+
#ifndef __COMMON_STRING_H
|
4
|
+
#define __COMMON_STRING_H
|
5
|
+
|
6
|
+
#include <string.h>
|
7
|
+
// #include <wchar.h>
|
8
|
+
|
9
|
+
#include "Vector.h"
|
10
|
+
|
11
|
+
#ifdef _WIN32
|
12
|
+
#include "MyWindows.h"
|
13
|
+
#endif
|
14
|
+
|
15
|
+
static const char *kTrimDefaultCharSet = " \n\t";
|
16
|
+
|
17
|
+
template <class T>
|
18
|
+
inline int MyStringLen(const T *s)
|
19
|
+
{
|
20
|
+
int i;
|
21
|
+
for (i = 0; s[i] != '\0'; i++);
|
22
|
+
return i;
|
23
|
+
}
|
24
|
+
|
25
|
+
template <class T>
|
26
|
+
inline T * MyStringCopy(T *dest, const T *src)
|
27
|
+
{
|
28
|
+
T *destStart = dest;
|
29
|
+
while((*dest++ = *src++) != 0);
|
30
|
+
return destStart;
|
31
|
+
}
|
32
|
+
|
33
|
+
inline wchar_t* MyStringGetNextCharPointer(wchar_t *p)
|
34
|
+
{ return (p + 1); }
|
35
|
+
inline const wchar_t* MyStringGetNextCharPointer(const wchar_t *p)
|
36
|
+
{ return (p + 1); }
|
37
|
+
inline wchar_t* MyStringGetPrevCharPointer(const wchar_t *, wchar_t *p)
|
38
|
+
{ return (p - 1); }
|
39
|
+
inline const wchar_t* MyStringGetPrevCharPointer(const wchar_t *, const wchar_t *p)
|
40
|
+
{ return (p - 1); }
|
41
|
+
|
42
|
+
#ifdef _WIN32
|
43
|
+
|
44
|
+
inline char* MyStringGetNextCharPointer(char *p)
|
45
|
+
{ return CharNextA(p); }
|
46
|
+
inline const char* MyStringGetNextCharPointer(const char *p)
|
47
|
+
{ return CharNextA(p); }
|
48
|
+
|
49
|
+
inline char* MyStringGetPrevCharPointer(char *base, char *p)
|
50
|
+
{ return CharPrevA(base, p); }
|
51
|
+
inline const char* MyStringGetPrevCharPointer(const char *base, const char *p)
|
52
|
+
{ return CharPrevA(base, p); }
|
53
|
+
|
54
|
+
inline char MyCharUpper(char c)
|
55
|
+
{ return (char)(unsigned int)CharUpperA((LPSTR)(unsigned int)(unsigned char)c); }
|
56
|
+
#ifdef _UNICODE
|
57
|
+
inline wchar_t MyCharUpper(wchar_t c)
|
58
|
+
{ return (wchar_t)CharUpperW((LPWSTR)c); }
|
59
|
+
#else
|
60
|
+
wchar_t MyCharUpper(wchar_t c);
|
61
|
+
#endif
|
62
|
+
|
63
|
+
inline char MyCharLower(char c)
|
64
|
+
{ return (char)(unsigned int)CharLowerA((LPSTR)(unsigned int)(unsigned char)c); }
|
65
|
+
#ifdef _UNICODE
|
66
|
+
inline wchar_t MyCharLower(wchar_t c)
|
67
|
+
{ return (wchar_t)CharLowerW((LPWSTR)c); }
|
68
|
+
#else
|
69
|
+
wchar_t MyCharLower(wchar_t c);
|
70
|
+
#endif
|
71
|
+
|
72
|
+
inline char * MyStringUpper(char *s) { return CharUpperA(s); }
|
73
|
+
#ifdef _UNICODE
|
74
|
+
inline wchar_t * MyStringUpper(wchar_t *s) { return CharUpperW(s); }
|
75
|
+
#else
|
76
|
+
wchar_t * MyStringUpper(wchar_t *s);
|
77
|
+
#endif
|
78
|
+
|
79
|
+
inline char * MyStringLower(char *s) { return CharLowerA(s); }
|
80
|
+
#ifdef _UNICODE
|
81
|
+
inline wchar_t * MyStringLower(wchar_t *s) { return CharLowerW(s); }
|
82
|
+
#else
|
83
|
+
wchar_t * MyStringLower(wchar_t *s);
|
84
|
+
#endif
|
85
|
+
|
86
|
+
#else // Standard-C
|
87
|
+
wchar_t MyCharUpper(wchar_t c);
|
88
|
+
#endif
|
89
|
+
|
90
|
+
//////////////////////////////////////
|
91
|
+
// Compare
|
92
|
+
|
93
|
+
/*
|
94
|
+
#ifndef _WIN32_WCE
|
95
|
+
int MyStringCollate(const char *s1, const char *s2);
|
96
|
+
int MyStringCollateNoCase(const char *s1, const char *s2);
|
97
|
+
#endif
|
98
|
+
int MyStringCollate(const wchar_t *s1, const wchar_t *s2);
|
99
|
+
int MyStringCollateNoCase(const wchar_t *s1, const wchar_t *s2);
|
100
|
+
*/
|
101
|
+
|
102
|
+
int MyStringCompare(const char *s1, const char *s2);
|
103
|
+
int MyStringCompare(const wchar_t *s1, const wchar_t *s2);
|
104
|
+
|
105
|
+
#ifdef _WIN32
|
106
|
+
int MyStringCompareNoCase(const char *s1, const char *s2);
|
107
|
+
#endif
|
108
|
+
|
109
|
+
int MyStringCompareNoCase(const wchar_t *s1, const wchar_t *s2);
|
110
|
+
|
111
|
+
template <class T>
|
112
|
+
class CStringBase
|
113
|
+
{
|
114
|
+
void TrimLeftWithCharSet(const CStringBase &charSet)
|
115
|
+
{
|
116
|
+
const T *p = _chars;
|
117
|
+
while (charSet.Find(*p) >= 0 && (*p != 0))
|
118
|
+
p = GetNextCharPointer(p);
|
119
|
+
Delete(0, (int)(p - _chars));
|
120
|
+
}
|
121
|
+
void TrimRightWithCharSet(const CStringBase &charSet)
|
122
|
+
{
|
123
|
+
const T *p = _chars;
|
124
|
+
const T *pLast = NULL;
|
125
|
+
while (*p != 0)
|
126
|
+
{
|
127
|
+
if (charSet.Find(*p) >= 0)
|
128
|
+
{
|
129
|
+
if (pLast == NULL)
|
130
|
+
pLast = p;
|
131
|
+
}
|
132
|
+
else
|
133
|
+
pLast = NULL;
|
134
|
+
p = GetNextCharPointer(p);
|
135
|
+
}
|
136
|
+
if(pLast != NULL)
|
137
|
+
{
|
138
|
+
int i = (int)(pLast - _chars);
|
139
|
+
Delete(i, _length - i);
|
140
|
+
}
|
141
|
+
|
142
|
+
}
|
143
|
+
void MoveItems(int destIndex, int srcIndex)
|
144
|
+
{
|
145
|
+
memmove(_chars + destIndex, _chars + srcIndex,
|
146
|
+
sizeof(T) * (_length - srcIndex + 1));
|
147
|
+
}
|
148
|
+
|
149
|
+
void InsertSpace(int &index, int size)
|
150
|
+
{
|
151
|
+
CorrectIndex(index);
|
152
|
+
GrowLength(size);
|
153
|
+
MoveItems(index + size, index);
|
154
|
+
}
|
155
|
+
|
156
|
+
static T *GetNextCharPointer(T *p)
|
157
|
+
{ return MyStringGetNextCharPointer(p); }
|
158
|
+
static const T *GetNextCharPointer(const T *p)
|
159
|
+
{ return MyStringGetNextCharPointer(p); }
|
160
|
+
static T *GetPrevCharPointer(T *base, T *p)
|
161
|
+
{ return MyStringGetPrevCharPointer(base, p); }
|
162
|
+
static const T *GetPrevCharPointer(const T *base, const T *p)
|
163
|
+
{ return MyStringGetPrevCharPointer(base, p); }
|
164
|
+
protected:
|
165
|
+
T *_chars;
|
166
|
+
int _length;
|
167
|
+
int _capacity;
|
168
|
+
|
169
|
+
void SetCapacity(int newCapacity)
|
170
|
+
{
|
171
|
+
int realCapacity = newCapacity + 1;
|
172
|
+
if(realCapacity == _capacity)
|
173
|
+
return;
|
174
|
+
/*
|
175
|
+
const int kMaxStringSize = 0x20000000;
|
176
|
+
#ifndef _WIN32_WCE
|
177
|
+
if(newCapacity > kMaxStringSize || newCapacity < _length)
|
178
|
+
throw 1052337;
|
179
|
+
#endif
|
180
|
+
*/
|
181
|
+
T *newBuffer = new T[realCapacity];
|
182
|
+
if(_capacity > 0)
|
183
|
+
{
|
184
|
+
for (int i = 0; i < (_length + 1); i++)
|
185
|
+
newBuffer[i] = _chars[i];
|
186
|
+
delete []_chars;
|
187
|
+
_chars = newBuffer;
|
188
|
+
}
|
189
|
+
else
|
190
|
+
{
|
191
|
+
_chars = newBuffer;
|
192
|
+
_chars[0] = 0;
|
193
|
+
}
|
194
|
+
_capacity = realCapacity;
|
195
|
+
}
|
196
|
+
|
197
|
+
void GrowLength(int n)
|
198
|
+
{
|
199
|
+
int freeSize = _capacity - _length - 1;
|
200
|
+
if (n <= freeSize)
|
201
|
+
return;
|
202
|
+
int delta;
|
203
|
+
if (_capacity > 64)
|
204
|
+
delta = _capacity / 2;
|
205
|
+
else if (_capacity > 8)
|
206
|
+
delta = 16;
|
207
|
+
else
|
208
|
+
delta = 4;
|
209
|
+
if (freeSize + delta < n)
|
210
|
+
delta = n - freeSize;
|
211
|
+
SetCapacity(_capacity + delta);
|
212
|
+
}
|
213
|
+
|
214
|
+
void CorrectIndex(int &index) const
|
215
|
+
{
|
216
|
+
if (index > _length)
|
217
|
+
index = _length;
|
218
|
+
}
|
219
|
+
|
220
|
+
public:
|
221
|
+
CStringBase(): _chars(0), _length(0), _capacity(0)
|
222
|
+
{ SetCapacity(16 - 1); }
|
223
|
+
CStringBase(T c): _chars(0), _length(0), _capacity(0)
|
224
|
+
{
|
225
|
+
SetCapacity(1);
|
226
|
+
_chars[0] = c;
|
227
|
+
_chars[1] = 0;
|
228
|
+
_length = 1;
|
229
|
+
}
|
230
|
+
CStringBase(const T *chars): _chars(0), _length(0), _capacity(0)
|
231
|
+
{
|
232
|
+
int length = MyStringLen(chars);
|
233
|
+
SetCapacity(length);
|
234
|
+
MyStringCopy(_chars, chars); // can be optimized by memove()
|
235
|
+
_length = length;
|
236
|
+
}
|
237
|
+
CStringBase(const CStringBase &s): _chars(0), _length(0), _capacity(0)
|
238
|
+
{
|
239
|
+
SetCapacity(s._length);
|
240
|
+
MyStringCopy(_chars, s._chars);
|
241
|
+
_length = s._length;
|
242
|
+
}
|
243
|
+
~CStringBase() { delete []_chars; }
|
244
|
+
|
245
|
+
operator const T*() const { return _chars;}
|
246
|
+
|
247
|
+
// The minimum size of the character buffer in characters.
|
248
|
+
// This value does not include space for a null terminator.
|
249
|
+
T* GetBuffer(int minBufLength)
|
250
|
+
{
|
251
|
+
if(minBufLength >= _capacity)
|
252
|
+
SetCapacity(minBufLength + 1);
|
253
|
+
return _chars;
|
254
|
+
}
|
255
|
+
void ReleaseBuffer() { ReleaseBuffer(MyStringLen(_chars)); }
|
256
|
+
void ReleaseBuffer(int newLength)
|
257
|
+
{
|
258
|
+
/*
|
259
|
+
#ifndef _WIN32_WCE
|
260
|
+
if(newLength >= _capacity)
|
261
|
+
throw 282217;
|
262
|
+
#endif
|
263
|
+
*/
|
264
|
+
_chars[newLength] = 0;
|
265
|
+
_length = newLength;
|
266
|
+
}
|
267
|
+
|
268
|
+
CStringBase& operator=(T c)
|
269
|
+
{
|
270
|
+
Empty();
|
271
|
+
SetCapacity(1);
|
272
|
+
_chars[0] = c;
|
273
|
+
_chars[1] = 0;
|
274
|
+
_length = 1;
|
275
|
+
return *this;
|
276
|
+
}
|
277
|
+
CStringBase& operator=(const T *chars)
|
278
|
+
{
|
279
|
+
Empty();
|
280
|
+
int length = MyStringLen(chars);
|
281
|
+
SetCapacity(length);
|
282
|
+
MyStringCopy(_chars, chars);
|
283
|
+
_length = length;
|
284
|
+
return *this;
|
285
|
+
}
|
286
|
+
CStringBase& operator=(const CStringBase& s)
|
287
|
+
{
|
288
|
+
if(&s == this)
|
289
|
+
return *this;
|
290
|
+
Empty();
|
291
|
+
SetCapacity(s._length);
|
292
|
+
MyStringCopy(_chars, s._chars);
|
293
|
+
_length = s._length;
|
294
|
+
return *this;
|
295
|
+
}
|
296
|
+
|
297
|
+
CStringBase& operator+=(T c)
|
298
|
+
{
|
299
|
+
GrowLength(1);
|
300
|
+
_chars[_length] = c;
|
301
|
+
_chars[++_length] = 0;
|
302
|
+
return *this;
|
303
|
+
}
|
304
|
+
CStringBase& operator+=(const T *s)
|
305
|
+
{
|
306
|
+
int len = MyStringLen(s);
|
307
|
+
GrowLength(len);
|
308
|
+
MyStringCopy(_chars + _length, s);
|
309
|
+
_length += len;
|
310
|
+
return *this;
|
311
|
+
}
|
312
|
+
CStringBase& operator+=(const CStringBase &s)
|
313
|
+
{
|
314
|
+
GrowLength(s._length);
|
315
|
+
MyStringCopy(_chars + _length, s._chars);
|
316
|
+
_length += s._length;
|
317
|
+
return *this;
|
318
|
+
}
|
319
|
+
void Empty()
|
320
|
+
{
|
321
|
+
_length = 0;
|
322
|
+
_chars[0] = 0;
|
323
|
+
}
|
324
|
+
int Length() const { return _length; }
|
325
|
+
bool IsEmpty() const { return (_length == 0); }
|
326
|
+
|
327
|
+
CStringBase Mid(int startIndex) const
|
328
|
+
{ return Mid(startIndex, _length - startIndex); }
|
329
|
+
CStringBase Mid(int startIndex, int count ) const
|
330
|
+
{
|
331
|
+
if (startIndex + count > _length)
|
332
|
+
count = _length - startIndex;
|
333
|
+
|
334
|
+
if (startIndex == 0 && startIndex + count == _length)
|
335
|
+
return *this;
|
336
|
+
|
337
|
+
CStringBase<T> result;
|
338
|
+
result.SetCapacity(count);
|
339
|
+
// MyStringNCopy(result._chars, _chars + startIndex, count);
|
340
|
+
for (int i = 0; i < count; i++)
|
341
|
+
result._chars[i] = _chars[startIndex + i];
|
342
|
+
result._chars[count] = 0;
|
343
|
+
result._length = count;
|
344
|
+
return result;
|
345
|
+
}
|
346
|
+
CStringBase Left(int count) const
|
347
|
+
{ return Mid(0, count); }
|
348
|
+
CStringBase Right(int count) const
|
349
|
+
{
|
350
|
+
if (count > _length)
|
351
|
+
count = _length;
|
352
|
+
return Mid(_length - count, count);
|
353
|
+
}
|
354
|
+
|
355
|
+
void MakeUpper()
|
356
|
+
{ MyStringUpper(_chars); }
|
357
|
+
void MakeLower()
|
358
|
+
{ MyStringLower(_chars); }
|
359
|
+
|
360
|
+
int Compare(const CStringBase& s) const
|
361
|
+
{ return MyStringCompare(_chars, s._chars); }
|
362
|
+
|
363
|
+
int CompareNoCase(const CStringBase& s) const
|
364
|
+
{ return MyStringCompareNoCase(_chars, s._chars); }
|
365
|
+
/*
|
366
|
+
int Collate(const CStringBase& s) const
|
367
|
+
{ return MyStringCollate(_chars, s._chars); }
|
368
|
+
int CollateNoCase(const CStringBase& s) const
|
369
|
+
{ return MyStringCollateNoCase(_chars, s._chars); }
|
370
|
+
*/
|
371
|
+
|
372
|
+
int Find(T c) const { return Find(c, 0); }
|
373
|
+
int Find(T c, int startIndex) const
|
374
|
+
{
|
375
|
+
T *p = _chars + startIndex;
|
376
|
+
while (true)
|
377
|
+
{
|
378
|
+
if (*p == c)
|
379
|
+
return (int)(p - _chars);
|
380
|
+
if (*p == 0)
|
381
|
+
return -1;
|
382
|
+
p = GetNextCharPointer(p);
|
383
|
+
}
|
384
|
+
}
|
385
|
+
int Find(const CStringBase &s) const { return Find(s, 0); }
|
386
|
+
int Find(const CStringBase &s, int startIndex) const
|
387
|
+
{
|
388
|
+
if (s.IsEmpty())
|
389
|
+
return startIndex;
|
390
|
+
for (; startIndex < _length; startIndex++)
|
391
|
+
{
|
392
|
+
int j;
|
393
|
+
for (j = 0; j < s._length && startIndex + j < _length; j++)
|
394
|
+
if (_chars[startIndex+j] != s._chars[j])
|
395
|
+
break;
|
396
|
+
if (j == s._length)
|
397
|
+
return startIndex;
|
398
|
+
}
|
399
|
+
return -1;
|
400
|
+
}
|
401
|
+
int ReverseFind(T c) const
|
402
|
+
{
|
403
|
+
if (_length == 0)
|
404
|
+
return -1;
|
405
|
+
T *p = _chars + _length - 1;
|
406
|
+
while (true)
|
407
|
+
{
|
408
|
+
if (*p == c)
|
409
|
+
return (int)(p - _chars);
|
410
|
+
if (p == _chars)
|
411
|
+
return -1;
|
412
|
+
p = GetPrevCharPointer(_chars, p);
|
413
|
+
}
|
414
|
+
}
|
415
|
+
int FindOneOf(const CStringBase &s) const
|
416
|
+
{
|
417
|
+
for(int i = 0; i < _length; i++)
|
418
|
+
if (s.Find(_chars[i]) >= 0)
|
419
|
+
return i;
|
420
|
+
return -1;
|
421
|
+
}
|
422
|
+
|
423
|
+
void TrimLeft(T c)
|
424
|
+
{
|
425
|
+
const T *p = _chars;
|
426
|
+
while (c == *p)
|
427
|
+
p = GetNextCharPointer(p);
|
428
|
+
Delete(0, p - _chars);
|
429
|
+
}
|
430
|
+
private:
|
431
|
+
CStringBase GetTrimDefaultCharSet()
|
432
|
+
{
|
433
|
+
CStringBase<T> charSet;
|
434
|
+
for(int i = 0; i < (int)(sizeof(kTrimDefaultCharSet) /
|
435
|
+
sizeof(kTrimDefaultCharSet[0])); i++)
|
436
|
+
charSet += (T)kTrimDefaultCharSet[i];
|
437
|
+
return charSet;
|
438
|
+
}
|
439
|
+
public:
|
440
|
+
|
441
|
+
void TrimLeft()
|
442
|
+
{
|
443
|
+
TrimLeftWithCharSet(GetTrimDefaultCharSet());
|
444
|
+
}
|
445
|
+
void TrimRight()
|
446
|
+
{
|
447
|
+
TrimRightWithCharSet(GetTrimDefaultCharSet());
|
448
|
+
}
|
449
|
+
void TrimRight(T c)
|
450
|
+
{
|
451
|
+
const T *p = _chars;
|
452
|
+
const T *pLast = NULL;
|
453
|
+
while (*p != 0)
|
454
|
+
{
|
455
|
+
if (*p == c)
|
456
|
+
{
|
457
|
+
if (pLast == NULL)
|
458
|
+
pLast = p;
|
459
|
+
}
|
460
|
+
else
|
461
|
+
pLast = NULL;
|
462
|
+
p = GetNextCharPointer(p);
|
463
|
+
}
|
464
|
+
if(pLast != NULL)
|
465
|
+
{
|
466
|
+
int i = pLast - _chars;
|
467
|
+
Delete(i, _length - i);
|
468
|
+
}
|
469
|
+
}
|
470
|
+
void Trim()
|
471
|
+
{
|
472
|
+
TrimRight();
|
473
|
+
TrimLeft();
|
474
|
+
}
|
475
|
+
|
476
|
+
int Insert(int index, T c)
|
477
|
+
{
|
478
|
+
InsertSpace(index, 1);
|
479
|
+
_chars[index] = c;
|
480
|
+
_length++;
|
481
|
+
return _length;
|
482
|
+
}
|
483
|
+
int Insert(int index, const CStringBase &s)
|
484
|
+
{
|
485
|
+
CorrectIndex(index);
|
486
|
+
if (s.IsEmpty())
|
487
|
+
return _length;
|
488
|
+
int numInsertChars = s.Length();
|
489
|
+
InsertSpace(index, numInsertChars);
|
490
|
+
for(int i = 0; i < numInsertChars; i++)
|
491
|
+
_chars[index + i] = s[i];
|
492
|
+
_length += numInsertChars;
|
493
|
+
return _length;
|
494
|
+
}
|
495
|
+
|
496
|
+
// !!!!!!!!!!!!!!! test it if newChar = '\0'
|
497
|
+
int Replace(T oldChar, T newChar)
|
498
|
+
{
|
499
|
+
if (oldChar == newChar)
|
500
|
+
return 0;
|
501
|
+
int number = 0;
|
502
|
+
int pos = 0;
|
503
|
+
while (pos < Length())
|
504
|
+
{
|
505
|
+
pos = Find(oldChar, pos);
|
506
|
+
if (pos < 0)
|
507
|
+
break;
|
508
|
+
_chars[pos] = newChar;
|
509
|
+
pos++;
|
510
|
+
number++;
|
511
|
+
}
|
512
|
+
return number;
|
513
|
+
}
|
514
|
+
int Replace(const CStringBase &oldString, const CStringBase &newString)
|
515
|
+
{
|
516
|
+
if (oldString.IsEmpty())
|
517
|
+
return 0;
|
518
|
+
if (oldString == newString)
|
519
|
+
return 0;
|
520
|
+
int oldStringLength = oldString.Length();
|
521
|
+
int newStringLength = newString.Length();
|
522
|
+
int number = 0;
|
523
|
+
int pos = 0;
|
524
|
+
while (pos < _length)
|
525
|
+
{
|
526
|
+
pos = Find(oldString, pos);
|
527
|
+
if (pos < 0)
|
528
|
+
break;
|
529
|
+
Delete(pos, oldStringLength);
|
530
|
+
Insert(pos, newString);
|
531
|
+
pos += newStringLength;
|
532
|
+
number++;
|
533
|
+
}
|
534
|
+
return number;
|
535
|
+
}
|
536
|
+
int Delete(int index, int count = 1 )
|
537
|
+
{
|
538
|
+
if (index + count > _length)
|
539
|
+
count = _length - index;
|
540
|
+
if (count > 0)
|
541
|
+
{
|
542
|
+
MoveItems(index, index + count);
|
543
|
+
_length -= count;
|
544
|
+
}
|
545
|
+
return _length;
|
546
|
+
}
|
547
|
+
};
|
548
|
+
|
549
|
+
template <class T>
|
550
|
+
CStringBase<T> operator+(const CStringBase<T>& s1, const CStringBase<T>& s2)
|
551
|
+
{
|
552
|
+
CStringBase<T> result(s1);
|
553
|
+
result += s2;
|
554
|
+
return result;
|
555
|
+
}
|
556
|
+
|
557
|
+
template <class T>
|
558
|
+
CStringBase<T> operator+(const CStringBase<T>& s, T c)
|
559
|
+
{
|
560
|
+
CStringBase<T> result(s);
|
561
|
+
result += c;
|
562
|
+
return result;
|
563
|
+
}
|
564
|
+
|
565
|
+
template <class T>
|
566
|
+
CStringBase<T> operator+(T c, const CStringBase<T>& s)
|
567
|
+
{
|
568
|
+
CStringBase<T> result(c);
|
569
|
+
result += s;
|
570
|
+
return result;
|
571
|
+
}
|
572
|
+
|
573
|
+
template <class T>
|
574
|
+
CStringBase<T> operator+(const CStringBase<T>& s, const T * chars)
|
575
|
+
{
|
576
|
+
CStringBase<T> result(s);
|
577
|
+
result += chars;
|
578
|
+
return result;
|
579
|
+
}
|
580
|
+
|
581
|
+
template <class T>
|
582
|
+
CStringBase<T> operator+(const T * chars, const CStringBase<T>& s)
|
583
|
+
{
|
584
|
+
CStringBase<T> result(chars);
|
585
|
+
result += s;
|
586
|
+
return result;
|
587
|
+
}
|
588
|
+
|
589
|
+
template <class T>
|
590
|
+
bool operator==(const CStringBase<T>& s1, const CStringBase<T>& s2)
|
591
|
+
{ return (s1.Compare(s2) == 0); }
|
592
|
+
|
593
|
+
template <class T>
|
594
|
+
bool operator<(const CStringBase<T>& s1, const CStringBase<T>& s2)
|
595
|
+
{ return (s1.Compare(s2) < 0); }
|
596
|
+
|
597
|
+
template <class T>
|
598
|
+
bool operator==(const T *s1, const CStringBase<T>& s2)
|
599
|
+
{ return (s2.Compare(s1) == 0); }
|
600
|
+
|
601
|
+
template <class T>
|
602
|
+
bool operator==(const CStringBase<T>& s1, const T *s2)
|
603
|
+
{ return (s1.Compare(s2) == 0); }
|
604
|
+
|
605
|
+
template <class T>
|
606
|
+
bool operator!=(const CStringBase<T>& s1, const CStringBase<T>& s2)
|
607
|
+
{ return (s1.Compare(s2) != 0); }
|
608
|
+
|
609
|
+
template <class T>
|
610
|
+
bool operator!=(const T *s1, const CStringBase<T>& s2)
|
611
|
+
{ return (s2.Compare(s1) != 0); }
|
612
|
+
|
613
|
+
template <class T>
|
614
|
+
bool operator!=(const CStringBase<T>& s1, const T *s2)
|
615
|
+
{ return (s1.Compare(s2) != 0); }
|
616
|
+
|
617
|
+
typedef CStringBase<char> AString;
|
618
|
+
typedef CStringBase<wchar_t> UString;
|
619
|
+
|
620
|
+
typedef CObjectVector<AString> AStringVector;
|
621
|
+
typedef CObjectVector<UString> UStringVector;
|
622
|
+
|
623
|
+
#ifdef _UNICODE
|
624
|
+
typedef UString CSysString;
|
625
|
+
#else
|
626
|
+
typedef AString CSysString;
|
627
|
+
#endif
|
628
|
+
|
629
|
+
typedef CObjectVector<CSysString> CSysStringVector;
|
630
|
+
|
631
|
+
#endif
|