Skip to content
项目
群组
代码片段
帮助
正在加载...
帮助
为 GitLab 提交贡献
登录/注册
切换导航
H
h2database
项目
项目
详情
活动
周期分析
仓库
仓库
文件
提交
分支
标签
贡献者
分枝图
比较
统计图
议题
0
议题
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
CI / CD
CI / CD
流水线
作业
计划
统计图
Wiki
Wiki
代码片段
代码片段
成员
成员
折叠边栏
关闭边栏
活动
分枝图
统计图
创建新议题
作业
提交
议题看板
打开侧边栏
Administrator
h2database
Commits
78a4f621
提交
78a4f621
authored
1月 08, 2013
作者:
Thomas Mueller
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Build target for the MVStore; remove DataType.getMaxLength; reduce cross-dependencies
上级
a0281dad
全部展开
隐藏空白字符变更
内嵌
并排
正在显示
43 个修改的文件
包含
682 行增加
和
716 行删除
+682
-716
mvstore.html
h2/src/docsrc/html/mvstore.html
+8
-0
LZFInputStream.java
h2/src/main/org/h2/compress/LZFInputStream.java
+2
-2
ConditionInConstantSet.java
h2/src/main/org/h2/expression/ConditionInConstantSet.java
+2
-1
Function.java
h2/src/main/org/h2/expression/Function.java
+2
-1
JdbcResultSet.java
h2/src/main/org/h2/jdbc/JdbcResultSet.java
+2
-3
DataUtils.java
h2/src/main/org/h2/mvstore/DataUtils.java
+108
-28
MVStore.java
h2/src/main/org/h2/mvstore/MVStore.java
+31
-27
MVStoreTool.java
h2/src/main/org/h2/mvstore/MVStoreTool.java
+1
-2
Page.java
h2/src/main/org/h2/mvstore/Page.java
+11
-49
StreamStore.java
h2/src/main/org/h2/mvstore/StreamStore.java
+32
-10
ValueArrayDataType.java
h2/src/main/org/h2/mvstore/db/ValueArrayDataType.java
+31
-34
SpatialDataType.java
h2/src/main/org/h2/mvstore/rtree/SpatialDataType.java
+2
-6
DataType.java
h2/src/main/org/h2/mvstore/type/DataType.java
+2
-10
ObjectDataType.java
h2/src/main/org/h2/mvstore/type/ObjectDataType.java
+294
-382
StringDataType.java
h2/src/main/org/h2/mvstore/type/StringDataType.java
+2
-6
PgServerThread.java
h2/src/main/org/h2/server/pg/PgServerThread.java
+3
-2
WebThread.java
h2/src/main/org/h2/server/web/WebThread.java
+3
-3
Data.java
h2/src/main/org/h2/store/Data.java
+7
-7
FileStoreInputStream.java
h2/src/main/org/h2/store/FileStoreInputStream.java
+2
-2
RecoverTester.java
h2/src/main/org/h2/store/RecoverTester.java
+2
-2
FilePath.java
h2/src/main/org/h2/store/fs/FilePath.java
+10
-9
FilePathCrypt.java
h2/src/main/org/h2/store/fs/FilePathCrypt.java
+21
-2
FilePathWrapper.java
h2/src/main/org/h2/store/fs/FilePathWrapper.java
+1
-2
FileUtils.java
h2/src/main/org/h2/store/fs/FileUtils.java
+2
-18
CompressTool.java
h2/src/main/org/h2/tools/CompressTool.java
+5
-5
IOUtils.java
h2/src/main/org/h2/util/IOUtils.java
+13
-0
MathUtils.java
h2/src/main/org/h2/util/MathUtils.java
+28
-49
Utils.java
h2/src/main/org/h2/util/Utils.java
+0
-26
Transfer.java
h2/src/main/org/h2/value/Transfer.java
+2
-1
ValueDecimal.java
h2/src/main/org/h2/value/ValueDecimal.java
+20
-1
ValueLob.java
h2/src/main/org/h2/value/ValueLob.java
+5
-4
ValueLobDb.java
h2/src/main/org/h2/value/ValueLobDb.java
+3
-2
ValueTimestamp.java
h2/src/main/org/h2/value/ValueTimestamp.java
+1
-1
RowDataType.java
h2/src/test/org/h2/test/store/RowDataType.java
+4
-12
TestConcurrent.java
h2/src/test/org/h2/test/store/TestConcurrent.java
+2
-0
TestMVRTree.java
h2/src/test/org/h2/test/store/TestMVRTree.java
+3
-0
TestMVStore.java
h2/src/test/org/h2/test/store/TestMVStore.java
+2
-0
TestObjectDataType.java
h2/src/test/org/h2/test/store/TestObjectDataType.java
+3
-3
TestStreamStore.java
h2/src/test/org/h2/test/store/TestStreamStore.java
+3
-0
TestClearReferences.java
h2/src/test/org/h2/test/unit/TestClearReferences.java
+1
-0
TestFileSystem.java
h2/src/test/org/h2/test/unit/TestFileSystem.java
+2
-1
TestReopen.java
h2/src/test/org/h2/test/unit/TestReopen.java
+3
-2
FileShell.java
h2/src/tools/org/h2/dev/fs/FileShell.java
+1
-1
没有找到文件。
h2/src/docsrc/html/mvstore.html
浏览文件 @
78a4f621
...
@@ -412,6 +412,14 @@ The MVStore is included in the latest H2 jar file.
...
@@ -412,6 +412,14 @@ The MVStore is included in the latest H2 jar file.
</p><p>
</p><p>
There are no special requirements to use it.
There are no special requirements to use it.
The MVStore should run on any JVM as well as on Android.
The MVStore should run on any JVM as well as on Android.
</p><p>
To build just the MVStore (without the database engine), run:
</p>
<pre>
./build.sh jarMVStore
</pre>
<p>
This will create the file
<code>
bin/h2mvstore-${version}.jar
</code>
(about 130 KB).
</p>
</p>
<!-- [close] { -->
</div></td></tr></table>
<!-- } --><!-- analytics -->
</body></html>
<!-- [close] { -->
</div></td></tr></table>
<!-- } --><!-- analytics -->
</body></html>
h2/src/main/org/h2/compress/LZFInputStream.java
浏览文件 @
78a4f621
...
@@ -9,7 +9,7 @@ package org.h2.compress;
...
@@ -9,7 +9,7 @@ package org.h2.compress;
import
java.io.IOException
;
import
java.io.IOException
;
import
java.io.InputStream
;
import
java.io.InputStream
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.
util.
Utils
;
import
org.h2.
mvstore.Data
Utils
;
/**
/**
* An input stream to read from an LZF stream.
* An input stream to read from an LZF stream.
...
@@ -32,7 +32,7 @@ public class LZFInputStream extends InputStream {
...
@@ -32,7 +32,7 @@ public class LZFInputStream extends InputStream {
}
}
private
static
byte
[]
ensureSize
(
byte
[]
buff
,
int
len
)
{
private
static
byte
[]
ensureSize
(
byte
[]
buff
,
int
len
)
{
return
buff
==
null
||
buff
.
length
<
len
?
Utils
.
newBytes
(
len
)
:
buff
;
return
buff
==
null
||
buff
.
length
<
len
?
Data
Utils
.
newBytes
(
len
)
:
buff
;
}
}
private
void
fillBuffer
()
throws
IOException
{
private
void
fillBuffer
()
throws
IOException
{
...
...
h2/src/main/org/h2/expression/ConditionInConstantSet.java
浏览文件 @
78a4f621
...
@@ -44,7 +44,7 @@ public class ConditionInConstantSet extends Condition {
...
@@ -44,7 +44,7 @@ public class ConditionInConstantSet extends Condition {
this
.
valueList
=
valueList
;
this
.
valueList
=
valueList
;
this
.
valueSet
=
new
HashSet
<
Value
>(
valueList
.
size
());
this
.
valueSet
=
new
HashSet
<
Value
>(
valueList
.
size
());
for
(
Expression
expression
:
valueList
)
{
for
(
Expression
expression
:
valueList
)
{
this
.
valueSet
.
add
(
expression
.
getValue
(
session
));
valueSet
.
add
(
expression
.
getValue
(
session
));
}
}
}
}
...
@@ -53,6 +53,7 @@ public class ConditionInConstantSet extends Condition {
...
@@ -53,6 +53,7 @@ public class ConditionInConstantSet extends Condition {
if
(
leftVal
==
ValueNull
.
INSTANCE
)
{
if
(
leftVal
==
ValueNull
.
INSTANCE
)
{
return
leftVal
;
return
leftVal
;
}
}
int
todoFix
;
Value
firstRightValue
=
null
;
Value
firstRightValue
=
null
;
for
(
Value
v
:
valueSet
)
{
for
(
Value
v
:
valueSet
)
{
if
(
v
!=
ValueNull
.
INSTANCE
)
{
if
(
v
!=
ValueNull
.
INSTANCE
)
{
...
...
h2/src/main/org/h2/expression/Function.java
浏览文件 @
78a4f621
...
@@ -30,6 +30,7 @@ import org.h2.engine.Database;
...
@@ -30,6 +30,7 @@ import org.h2.engine.Database;
import
org.h2.engine.Mode
;
import
org.h2.engine.Mode
;
import
org.h2.engine.Session
;
import
org.h2.engine.Session
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.mvstore.DataUtils
;
import
org.h2.schema.Schema
;
import
org.h2.schema.Schema
;
import
org.h2.schema.Sequence
;
import
org.h2.schema.Sequence
;
import
org.h2.security.BlockCipher
;
import
org.h2.security.BlockCipher
;
...
@@ -1334,7 +1335,7 @@ public class Function extends Expression implements FunctionCall {
...
@@ -1334,7 +1335,7 @@ public class Function extends Expression implements FunctionCall {
private
static
byte
[]
getPaddedArrayCopy
(
byte
[]
data
,
int
blockSize
)
{
private
static
byte
[]
getPaddedArrayCopy
(
byte
[]
data
,
int
blockSize
)
{
int
size
=
MathUtils
.
roundUpInt
(
data
.
length
,
blockSize
);
int
size
=
MathUtils
.
roundUpInt
(
data
.
length
,
blockSize
);
byte
[]
newData
=
Utils
.
newBytes
(
size
);
byte
[]
newData
=
Data
Utils
.
newBytes
(
size
);
System
.
arraycopy
(
data
,
0
,
newData
,
0
,
data
.
length
);
System
.
arraycopy
(
data
,
0
,
newData
,
0
,
data
.
length
);
return
newData
;
return
newData
;
}
}
...
...
h2/src/main/org/h2/jdbc/JdbcResultSet.java
浏览文件 @
78a4f621
...
@@ -40,7 +40,6 @@ import org.h2.result.ResultInterface;
...
@@ -40,7 +40,6 @@ import org.h2.result.ResultInterface;
import
org.h2.result.UpdatableRow
;
import
org.h2.result.UpdatableRow
;
import
org.h2.util.DateTimeUtils
;
import
org.h2.util.DateTimeUtils
;
import
org.h2.util.IOUtils
;
import
org.h2.util.IOUtils
;
import
org.h2.util.MathUtils
;
import
org.h2.util.New
;
import
org.h2.util.New
;
import
org.h2.util.StringUtils
;
import
org.h2.util.StringUtils
;
import
org.h2.value.CompareMode
;
import
org.h2.value.CompareMode
;
...
@@ -721,7 +720,7 @@ public class JdbcResultSet extends TraceObject implements ResultSet {
...
@@ -721,7 +720,7 @@ public class JdbcResultSet extends TraceObject implements ResultSet {
throw
DbException
.
getInvalidValueException
(
"scale"
,
scale
);
throw
DbException
.
getInvalidValueException
(
"scale"
,
scale
);
}
}
BigDecimal
bd
=
get
(
columnLabel
).
getBigDecimal
();
BigDecimal
bd
=
get
(
columnLabel
).
getBigDecimal
();
return
bd
==
null
?
null
:
MathUtils
.
setScale
(
bd
,
scale
);
return
bd
==
null
?
null
:
ValueDecimal
.
setScale
(
bd
,
scale
);
}
catch
(
Exception
e
)
{
}
catch
(
Exception
e
)
{
throw
logAndConvert
(
e
);
throw
logAndConvert
(
e
);
}
}
...
@@ -747,7 +746,7 @@ public class JdbcResultSet extends TraceObject implements ResultSet {
...
@@ -747,7 +746,7 @@ public class JdbcResultSet extends TraceObject implements ResultSet {
throw
DbException
.
getInvalidValueException
(
"scale"
,
scale
);
throw
DbException
.
getInvalidValueException
(
"scale"
,
scale
);
}
}
BigDecimal
bd
=
get
(
columnIndex
).
getBigDecimal
();
BigDecimal
bd
=
get
(
columnIndex
).
getBigDecimal
();
return
bd
==
null
?
null
:
MathUtils
.
setScale
(
bd
,
scale
);
return
bd
==
null
?
null
:
ValueDecimal
.
setScale
(
bd
,
scale
);
}
catch
(
Exception
e
)
{
}
catch
(
Exception
e
)
{
throw
logAndConvert
(
e
);
throw
logAndConvert
(
e
);
}
}
...
...
h2/src/main/org/h2/mvstore/DataUtils.java
浏览文件 @
78a4f621
...
@@ -13,12 +13,10 @@ import java.nio.ByteBuffer;
...
@@ -13,12 +13,10 @@ import java.nio.ByteBuffer;
import
java.nio.channels.FileChannel
;
import
java.nio.channels.FileChannel
;
import
java.text.MessageFormat
;
import
java.text.MessageFormat
;
import
java.util.ArrayList
;
import
java.util.ArrayList
;
import
java.util.Arrays
;
import
java.util.Collections
;
import
java.util.Collections
;
import
java.util.HashMap
;
import
java.util.HashMap
;
import
org.h2.engine.Constants
;
import
org.h2.engine.Constants
;
import
org.h2.util.New
;
import
org.h2.util.New
;
import
org.h2.util.StringUtils
;
/**
/**
* Utility methods
* Utility methods
...
@@ -72,6 +70,11 @@ public class DataUtils {
...
@@ -72,6 +70,11 @@ public class DataUtils {
*/
*/
public
static
final
int
PAGE_MEMORY_CHILD
=
16
;
public
static
final
int
PAGE_MEMORY_CHILD
=
16
;
/**
* An 0-size byte array.
*/
private
static
final
byte
[]
EMPTY_BYTES
=
{};
/**
/**
* Get the length of the variable size int.
* Get the length of the variable size int.
*
*
...
@@ -199,8 +202,10 @@ public class DataUtils {
...
@@ -199,8 +202,10 @@ public class DataUtils {
* @param buff the target buffer
* @param buff the target buffer
* @param s the string
* @param s the string
* @param len the number of characters
* @param len the number of characters
* @return the byte buffer
*/
*/
public
static
void
writeStringData
(
ByteBuffer
buff
,
String
s
,
int
len
)
{
public
static
ByteBuffer
writeStringData
(
ByteBuffer
buff
,
String
s
,
int
len
)
{
buff
=
DataUtils
.
ensureCapacity
(
buff
,
3
*
len
);
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
int
c
=
s
.
charAt
(
i
);
int
c
=
s
.
charAt
(
i
);
if
(
c
<
0x80
)
{
if
(
c
<
0x80
)
{
...
@@ -214,6 +219,7 @@ public class DataUtils {
...
@@ -214,6 +219,7 @@ public class DataUtils {
buff
.
put
((
byte
)
(
c
&
0x3f
));
buff
.
put
((
byte
)
(
c
&
0x3f
));
}
}
}
}
return
buff
;
}
}
/**
/**
...
@@ -584,7 +590,8 @@ public class DataUtils {
...
@@ -584,7 +590,8 @@ public class DataUtils {
public
static
IllegalArgumentException
newIllegalArgumentException
(
public
static
IllegalArgumentException
newIllegalArgumentException
(
String
message
,
Object
...
arguments
)
{
String
message
,
Object
...
arguments
)
{
return
initCause
(
new
IllegalArgumentException
(
return
initCause
(
new
IllegalArgumentException
(
formatMessage
(
message
,
arguments
)),
arguments
);
MessageFormat
.
format
(
message
,
arguments
)
+
getVersion
()),
arguments
);
}
}
/**
/**
...
@@ -608,7 +615,8 @@ public class DataUtils {
...
@@ -608,7 +615,8 @@ public class DataUtils {
public
static
IllegalStateException
newIllegalStateException
(
public
static
IllegalStateException
newIllegalStateException
(
String
message
,
Object
...
arguments
)
{
String
message
,
Object
...
arguments
)
{
return
initCause
(
new
IllegalStateException
(
return
initCause
(
new
IllegalStateException
(
formatMessage
(
message
,
arguments
)),
arguments
);
MessageFormat
.
format
(
message
,
arguments
)
+
getVersion
()),
arguments
);
}
}
private
static
<
T
extends
Exception
>
T
initCause
(
T
e
,
Object
...
arguments
)
{
private
static
<
T
extends
Exception
>
T
initCause
(
T
e
,
Object
...
arguments
)
{
...
@@ -622,39 +630,111 @@ public class DataUtils {
...
@@ -622,39 +630,111 @@ public class DataUtils {
return
e
;
return
e
;
}
}
private
static
String
formatMessage
(
String
pattern
,
Object
...
arguments
)
{
for
(
int
i
=
0
,
size
=
arguments
.
length
;
i
<
size
;
i
++)
{
Object
o
=
arguments
[
i
];
if
(
o
instanceof
String
)
{
arguments
[
i
]
=
StringUtils
.
quoteIdentifier
(
o
.
toString
());
}
}
return
MessageFormat
.
format
(
pattern
,
arguments
)
+
getVersion
();
}
private
static
String
getVersion
()
{
private
static
String
getVersion
()
{
return
" ["
+
Constants
.
VERSION_MAJOR
+
"."
+
return
" ["
+
Constants
.
VERSION_MAJOR
+
"."
+
Constants
.
VERSION_MINOR
+
"."
+
Constants
.
BUILD_ID
+
"]"
;
Constants
.
VERSION_MINOR
+
"."
+
Constants
.
BUILD_ID
+
"]"
;
}
}
/**
/**
* Convert a char array to a byte array. The char array is cleared after
* Convert the text to UTF-8 format. For the Unicode characters
* use.
* 0xd800-0xdfff only one byte is returned.
*
* @param s the text
* @return the UTF-8 representation
*/
public
static
byte
[]
utf8Encode
(
String
s
)
{
try
{
return
s
.
getBytes
(
Constants
.
UTF8
);
}
catch
(
Exception
e
)
{
// UnsupportedEncodingException
throw
newIllegalArgumentException
(
"UTF-8 not supported"
,
e
);
}
}
/**
* Convert a UTF-8 representation of a text to the text.
*
* @param utf8 the UTF-8 representation
* @return the text
*/
public
static
String
utf8Decode
(
byte
[]
utf8
)
{
try
{
return
new
String
(
utf8
,
Constants
.
UTF8
);
}
catch
(
Exception
e
)
{
// UnsupportedEncodingException
throw
newIllegalArgumentException
(
"UTF-8 not supported"
,
e
);
}
}
/**
* Convert a UTF-8 representation of a text to the text using the given
* offset and length.
*
* @param bytes the UTF-8 representation
* @param offset the offset in the bytes array
* @param length the number of bytes
* @return the text
*/
public
static
String
utf8Decode
(
byte
[]
bytes
,
int
offset
,
int
length
)
{
try
{
return
new
String
(
bytes
,
offset
,
length
,
Constants
.
UTF8
);
}
catch
(
Exception
e
)
{
// UnsupportedEncodingException
throw
newIllegalArgumentException
(
"UTF-8 not supported"
,
e
);
}
}
/**
* Create an array of bytes with the given size. If this is not possible
* because not enough memory is available, an OutOfMemoryError with the
* requested size in the message is thrown.
* <p>
* This method should be used if the size of the array is user defined, or
* stored in a file, so wrong size data can be distinguished from regular
* out-of-memory.
*
*
* @param
passwordChars the password characters
* @param
len the number of bytes requested
* @return the byte array
* @return the byte array
* @throws OutOfMemoryError
*/
*/
static
byte
[]
getPasswordBytes
(
char
[]
passwordChars
)
{
public
static
byte
[]
newBytes
(
int
len
)
{
// using UTF-16
if
(
len
==
0
)
{
int
len
=
passwordChars
.
length
;
return
EMPTY_BYTES
;
byte
[]
password
=
new
byte
[
len
*
2
];
}
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
try
{
char
c
=
passwordChars
[
i
];
return
new
byte
[
len
];
password
[
i
+
i
]
=
(
byte
)
(
c
>>>
8
);
}
catch
(
OutOfMemoryError
e
)
{
password
[
i
+
i
+
1
]
=
(
byte
)
c
;
Error
e2
=
new
OutOfMemoryError
(
"Requested memory: "
+
len
);
e2
.
initCause
(
e
);
throw
e2
;
}
}
Arrays
.
fill
(
passwordChars
,
(
char
)
0
);
}
return
password
;
/**
* Ensure the byte buffer has the given capacity, plus 1 KB. If not, a new,
* larger byte buffer is created and the data is copied.
*
* @param buff the byte buffer
* @param len the minimum remaining capacity
* @return the byte buffer (possibly a new one)
*/
public
static
ByteBuffer
ensureCapacity
(
ByteBuffer
buff
,
int
len
)
{
len
+=
1024
;
if
(
buff
.
remaining
()
>
len
)
{
return
buff
;
}
return
grow
(
buff
,
len
);
}
private
static
ByteBuffer
grow
(
ByteBuffer
buff
,
int
len
)
{
len
=
buff
.
remaining
()
+
len
;
int
capacity
=
buff
.
capacity
();
// grow at most 1 MB at a time
len
=
Math
.
max
(
len
,
Math
.
min
(
capacity
+
1024
*
1024
,
capacity
*
2
));
ByteBuffer
temp
=
ByteBuffer
.
allocate
(
len
);
buff
.
flip
();
temp
.
put
(
buff
);
return
temp
;
}
}
}
}
h2/src/main/org/h2/mvstore/MVStore.java
浏览文件 @
78a4f621
...
@@ -25,10 +25,9 @@ import org.h2.mvstore.cache.FilePathCache;
...
@@ -25,10 +25,9 @@ import org.h2.mvstore.cache.FilePathCache;
import
org.h2.mvstore.type.StringDataType
;
import
org.h2.mvstore.type.StringDataType
;
import
org.h2.store.fs.FilePath
;
import
org.h2.store.fs.FilePath
;
import
org.h2.store.fs.FilePathCrypt
;
import
org.h2.store.fs.FilePathCrypt
;
import
org.h2.store.fs.File
Utils
;
import
org.h2.store.fs.File
PathNio
;
import
org.h2.util.MathUtils
;
import
org.h2.util.MathUtils
;
import
org.h2.util.New
;
import
org.h2.util.New
;
import
org.h2.util.StringUtils
;
/*
/*
...
@@ -43,7 +42,6 @@ H:3,...
...
@@ -43,7 +42,6 @@ H:3,...
TODO:
TODO:
- separate jar file
- automated 'kill process' and 'power failure' test
- automated 'kill process' and 'power failure' test
- mvcc with multiple transactions
- mvcc with multiple transactions
- update checkstyle
- update checkstyle
...
@@ -53,7 +51,6 @@ TODO:
...
@@ -53,7 +51,6 @@ TODO:
- possibly split chunk data into immutable and mutable
- possibly split chunk data into immutable and mutable
- compact: avoid processing pages using a counting bloom filter
- compact: avoid processing pages using a counting bloom filter
- defragment (re-creating maps, specially those with small pages)
- defragment (re-creating maps, specially those with small pages)
- remove DataType.getMaxLength (use ByteArrayOutputStream or getMemory)
- chunk header: store changed chunk data as row; maybe after the root
- chunk header: store changed chunk data as row; maybe after the root
- chunk checksum (header, last page, 2 bytes per page?)
- chunk checksum (header, last page, 2 bytes per page?)
- is there a better name for the file header,
- is there a better name for the file header,
...
@@ -84,7 +81,7 @@ TODO:
...
@@ -84,7 +81,7 @@ TODO:
- MVStoreTool.shrink to shrink a store (create, copy, rename, delete)
- MVStoreTool.shrink to shrink a store (create, copy, rename, delete)
-- and for MVStore on Windows, auto-detect renamed file
-- and for MVStore on Windows, auto-detect renamed file
- ensure data is overwritten eventually if the system doesn't have a timer
- ensure data is overwritten eventually if the system doesn't have a timer
- SSD-friendly write (always in blocks of
128 or 256 KB
?)
- SSD-friendly write (always in blocks of
4 MB / 1 second
?)
- close the file on out of memory or disk write error (out of disk space or so)
- close the file on out of memory or disk write error (out of disk space or so)
- implement a sharded map (in one store, multiple stores)
- implement a sharded map (in one store, multiple stores)
-- to support concurrent updates and writes, and very large maps
-- to support concurrent updates and writes, and very large maps
...
@@ -178,7 +175,13 @@ public class MVStore {
...
@@ -178,7 +175,13 @@ public class MVStore {
private
boolean
closed
;
private
boolean
closed
;
MVStore
(
HashMap
<
String
,
Object
>
config
)
{
MVStore
(
HashMap
<
String
,
Object
>
config
)
{
this
.
fileName
=
(
String
)
config
.
get
(
"fileName"
);
String
f
=
(
String
)
config
.
get
(
"fileName"
);
if
(
f
!=
null
&&
!
f
.
startsWith
(
"nio:"
))
{
// nio is used by default
FilePathNio
.
class
.
getName
();
f
=
"nio:"
+
f
;
}
this
.
fileName
=
f
;
this
.
readOnly
=
"r"
.
equals
(
config
.
get
(
"openMode"
));
this
.
readOnly
=
"r"
.
equals
(
config
.
get
(
"openMode"
));
this
.
compress
=
"1"
.
equals
(
config
.
get
(
"compress"
));
this
.
compress
=
"1"
.
equals
(
config
.
get
(
"compress"
));
if
(
fileName
!=
null
)
{
if
(
fileName
!=
null
)
{
...
@@ -194,7 +197,8 @@ public class MVStore {
...
@@ -194,7 +197,8 @@ public class MVStore {
}
}
/**
/**
* Open a store in exclusive mode.
* Open a store in exclusive mode. For a file-based store, the parent
* directory must already exist.
*
*
* @param fileName the file name (null for in-memory)
* @param fileName the file name (null for in-memory)
* @return the store
* @return the store
...
@@ -370,7 +374,10 @@ public class MVStore {
...
@@ -370,7 +374,10 @@ public class MVStore {
if
(
fileName
==
null
)
{
if
(
fileName
==
null
)
{
return
;
return
;
}
}
FileUtils
.
createDirectories
(
FileUtils
.
getParent
(
fileName
));
FilePath
parent
=
FilePath
.
get
(
fileName
).
getParent
();
if
(!
parent
.
exists
())
{
throw
DataUtils
.
newIllegalArgumentException
(
"Directory does not exist: {0}"
,
parent
);
}
try
{
try
{
if
(
readOnly
)
{
if
(
readOnly
)
{
openFile
();
openFile
();
...
@@ -402,7 +409,7 @@ public class MVStore {
...
@@ -402,7 +409,7 @@ public class MVStore {
}
}
file
=
f
.
open
(
readOnly
?
"r"
:
"rw"
);
file
=
f
.
open
(
readOnly
?
"r"
:
"rw"
);
if
(
filePassword
!=
null
)
{
if
(
filePassword
!=
null
)
{
byte
[]
password
=
DataUtils
.
getPasswordBytes
(
filePassword
);
byte
[]
password
=
FilePathCrypt
.
getPasswordBytes
(
filePassword
);
file
=
new
FilePathCrypt
.
FileCrypt
(
fileName
,
password
,
file
);
file
=
new
FilePathCrypt
.
FileCrypt
(
fileName
,
password
,
file
);
}
}
file
=
FilePathCache
.
wrap
(
file
);
file
=
FilePathCache
.
wrap
(
file
);
...
@@ -496,7 +503,7 @@ public class MVStore {
...
@@ -496,7 +503,7 @@ public class MVStore {
fileReadCount
++;
fileReadCount
++;
DataUtils
.
readFully
(
file
,
0
,
buff
);
DataUtils
.
readFully
(
file
,
0
,
buff
);
for
(
int
i
=
0
;
i
<
3
*
BLOCK_SIZE
;
i
+=
BLOCK_SIZE
)
{
for
(
int
i
=
0
;
i
<
3
*
BLOCK_SIZE
;
i
+=
BLOCK_SIZE
)
{
String
s
=
String
Utils
.
utf8Decode
(
buff
.
array
(),
i
,
BLOCK_SIZE
)
String
s
=
Data
Utils
.
utf8Decode
(
buff
.
array
(),
i
,
BLOCK_SIZE
)
.
trim
();
.
trim
();
HashMap
<
String
,
String
>
m
=
DataUtils
.
parseMap
(
s
);
HashMap
<
String
,
String
>
m
=
DataUtils
.
parseMap
(
s
);
String
f
=
m
.
remove
(
"fletcher"
);
String
f
=
m
.
remove
(
"fletcher"
);
...
@@ -510,7 +517,7 @@ public class MVStore {
...
@@ -510,7 +517,7 @@ public class MVStore {
check
=
-
1
;
check
=
-
1
;
}
}
s
=
s
.
substring
(
0
,
s
.
lastIndexOf
(
"fletcher"
)
-
1
)
+
" "
;
s
=
s
.
substring
(
0
,
s
.
lastIndexOf
(
"fletcher"
)
-
1
)
+
" "
;
byte
[]
bytes
=
String
Utils
.
utf8Encode
(
s
);
byte
[]
bytes
=
Data
Utils
.
utf8Encode
(
s
);
int
checksum
=
DataUtils
.
getFletcher32
(
bytes
,
bytes
.
length
/
2
*
2
);
int
checksum
=
DataUtils
.
getFletcher32
(
bytes
,
bytes
.
length
/
2
*
2
);
if
(
check
!=
checksum
)
{
if
(
check
!=
checksum
)
{
continue
;
continue
;
...
@@ -535,10 +542,10 @@ public class MVStore {
...
@@ -535,10 +542,10 @@ public class MVStore {
fileHeader
.
put
(
"rootChunk"
,
""
+
rootChunkStart
);
fileHeader
.
put
(
"rootChunk"
,
""
+
rootChunkStart
);
fileHeader
.
put
(
"version"
,
""
+
currentVersion
);
fileHeader
.
put
(
"version"
,
""
+
currentVersion
);
DataUtils
.
appendMap
(
buff
,
fileHeader
);
DataUtils
.
appendMap
(
buff
,
fileHeader
);
byte
[]
bytes
=
String
Utils
.
utf8Encode
(
buff
.
toString
()
+
" "
);
byte
[]
bytes
=
Data
Utils
.
utf8Encode
(
buff
.
toString
()
+
" "
);
int
checksum
=
DataUtils
.
getFletcher32
(
bytes
,
bytes
.
length
/
2
*
2
);
int
checksum
=
DataUtils
.
getFletcher32
(
bytes
,
bytes
.
length
/
2
*
2
);
DataUtils
.
appendMap
(
buff
,
"fletcher"
,
Integer
.
toHexString
(
checksum
));
DataUtils
.
appendMap
(
buff
,
"fletcher"
,
Integer
.
toHexString
(
checksum
));
bytes
=
String
Utils
.
utf8Encode
(
buff
.
toString
());
bytes
=
Data
Utils
.
utf8Encode
(
buff
.
toString
());
DataUtils
.
checkArgument
(
bytes
.
length
<=
BLOCK_SIZE
,
DataUtils
.
checkArgument
(
bytes
.
length
<=
BLOCK_SIZE
,
"File header too large: {}"
,
buff
);
"File header too large: {}"
,
buff
);
return
bytes
;
return
bytes
;
...
@@ -655,7 +662,6 @@ public class MVStore {
...
@@ -655,7 +662,6 @@ public class MVStore {
chunks
.
put
(
c
.
id
,
c
);
chunks
.
put
(
c
.
id
,
c
);
meta
.
put
(
"chunk."
+
c
.
id
,
c
.
asString
());
meta
.
put
(
"chunk."
+
c
.
id
,
c
.
asString
());
int
maxLength
=
1
+
4
+
4
+
8
;
for
(
MVMap
<?,
?>
m
:
mapsChanged
.
values
())
{
for
(
MVMap
<?,
?>
m
:
mapsChanged
.
values
())
{
if
(
m
==
meta
||
!
m
.
hasUnsavedChanges
())
{
if
(
m
==
meta
||
!
m
.
hasUnsavedChanges
())
{
continue
;
continue
;
...
@@ -664,7 +670,6 @@ public class MVStore {
...
@@ -664,7 +670,6 @@ public class MVStore {
if
(
p
.
getTotalCount
()
==
0
)
{
if
(
p
.
getTotalCount
()
==
0
)
{
meta
.
put
(
"root."
+
m
.
getId
(),
"0"
);
meta
.
put
(
"root."
+
m
.
getId
(),
"0"
);
}
else
{
}
else
{
maxLength
+=
p
.
getMaxLengthTempRecursive
();
meta
.
put
(
"root."
+
m
.
getId
(),
String
.
valueOf
(
Long
.
MAX_VALUE
));
meta
.
put
(
"root."
+
m
.
getId
(),
String
.
valueOf
(
Long
.
MAX_VALUE
));
}
}
}
}
...
@@ -681,17 +686,12 @@ public class MVStore {
...
@@ -681,17 +686,12 @@ public class MVStore {
applyFreedChunks
();
applyFreedChunks
();
}
}
}
while
(
freedChunks
.
size
()
>
0
);
}
while
(
freedChunks
.
size
()
>
0
);
maxLength
+=
meta
.
getRoot
().
getMaxLengthTempRecursive
();
ByteBuffer
buff
;
ByteBuffer
buff
;
if
(
maxLength
>
16
*
1024
*
1024
)
{
if
(
writeBuffer
!=
null
)
{
buff
=
ByteBuffer
.
allocate
(
maxLength
);
buff
=
writeBuffer
;
buff
.
clear
();
}
else
{
}
else
{
if
(
writeBuffer
!=
null
&&
writeBuffer
.
capacity
()
>=
maxLength
)
{
buff
=
ByteBuffer
.
allocate
(
1024
*
1024
);
buff
=
writeBuffer
;
buff
.
clear
();
}
else
{
writeBuffer
=
buff
=
ByteBuffer
.
allocate
(
maxLength
+
128
*
1024
);
}
}
}
// need to patch the header later
// need to patch the header later
c
.
writeHeader
(
buff
);
c
.
writeHeader
(
buff
);
...
@@ -703,7 +703,8 @@ public class MVStore {
...
@@ -703,7 +703,8 @@ public class MVStore {
}
}
Page
p
=
m
.
openVersion
(
storeVersion
).
getRoot
();
Page
p
=
m
.
openVersion
(
storeVersion
).
getRoot
();
if
(
p
.
getTotalCount
()
>
0
)
{
if
(
p
.
getTotalCount
()
>
0
)
{
long
root
=
p
.
writeUnsavedRecursive
(
c
,
buff
);
buff
=
p
.
writeUnsavedRecursive
(
c
,
buff
);
long
root
=
p
.
getPos
();
meta
.
put
(
"root."
+
m
.
getId
(),
""
+
root
);
meta
.
put
(
"root."
+
m
.
getId
(),
""
+
root
);
}
}
}
}
...
@@ -718,7 +719,7 @@ public class MVStore {
...
@@ -718,7 +719,7 @@ public class MVStore {
// this will modify maxLengthLive, but
// this will modify maxLengthLive, but
// the correct value is written in the chunk header
// the correct value is written in the chunk header
meta
.
getRoot
().
writeUnsavedRecursive
(
c
,
buff
);
buff
=
meta
.
getRoot
().
writeUnsavedRecursive
(
c
,
buff
);
int
chunkLength
=
buff
.
position
();
int
chunkLength
=
buff
.
position
();
...
@@ -755,6 +756,9 @@ public class MVStore {
...
@@ -755,6 +756,9 @@ public class MVStore {
fileWriteCount
++;
fileWriteCount
++;
DataUtils
.
writeFully
(
file
,
filePos
,
buff
);
DataUtils
.
writeFully
(
file
,
filePos
,
buff
);
fileSize
=
Math
.
max
(
fileSize
,
filePos
+
buff
.
position
());
fileSize
=
Math
.
max
(
fileSize
,
filePos
+
buff
.
position
());
if
(
buff
.
capacity
()
<=
4
*
1024
*
1024
)
{
writeBuffer
=
buff
;
}
// overwrite the header if required
// overwrite the header if required
if
(!
atEnd
)
{
if
(!
atEnd
)
{
...
@@ -1440,7 +1444,7 @@ public class MVStore {
...
@@ -1440,7 +1444,7 @@ public class MVStore {
/**
/**
* Use the following file name. If the file does not exist, it is
* Use the following file name. If the file does not exist, it is
* automatically created.
* automatically created.
The parent directory already must exist.
*
*
* @param fileName the file name
* @param fileName the file name
* @return this
* @return this
...
...
h2/src/main/org/h2/mvstore/MVStoreTool.java
浏览文件 @
78a4f621
...
@@ -12,7 +12,6 @@ import java.io.Writer;
...
@@ -12,7 +12,6 @@ import java.io.Writer;
import
java.nio.ByteBuffer
;
import
java.nio.ByteBuffer
;
import
java.nio.channels.FileChannel
;
import
java.nio.channels.FileChannel
;
import
org.h2.store.fs.FilePath
;
import
org.h2.store.fs.FilePath
;
import
org.h2.store.fs.FileUtils
;
/**
/**
* Utility methods used in combination with the MVStore.
* Utility methods used in combination with the MVStore.
...
@@ -47,7 +46,7 @@ public class MVStoreTool {
...
@@ -47,7 +46,7 @@ public class MVStoreTool {
*/
*/
public
static
void
dump
(
String
fileName
,
Writer
writer
)
{
public
static
void
dump
(
String
fileName
,
Writer
writer
)
{
PrintWriter
pw
=
new
PrintWriter
(
writer
,
true
);
PrintWriter
pw
=
new
PrintWriter
(
writer
,
true
);
if
(!
File
Utils
.
exists
(
fileName
))
{
if
(!
File
Path
.
get
(
fileName
).
exists
(
))
{
pw
.
println
(
"File not found: "
+
fileName
);
pw
.
println
(
"File not found: "
+
fileName
);
return
;
return
;
}
}
...
...
h2/src/main/org/h2/mvstore/Page.java
浏览文件 @
78a4f621
...
@@ -11,7 +11,6 @@ import java.nio.channels.FileChannel;
...
@@ -11,7 +11,6 @@ import java.nio.channels.FileChannel;
import
java.util.Arrays
;
import
java.util.Arrays
;
import
org.h2.compress.Compressor
;
import
org.h2.compress.Compressor
;
import
org.h2.mvstore.type.DataType
;
import
org.h2.mvstore.type.DataType
;
import
org.h2.util.Utils
;
/**
/**
* A page (a node or a leaf).
* A page (a node or a leaf).
...
@@ -720,7 +719,7 @@ public class Page {
...
@@ -720,7 +719,7 @@ public class Page {
Compressor
compressor
=
map
.
getStore
().
getCompressor
();
Compressor
compressor
=
map
.
getStore
().
getCompressor
();
int
lenAdd
=
DataUtils
.
readVarInt
(
buff
);
int
lenAdd
=
DataUtils
.
readVarInt
(
buff
);
int
compLen
=
pageLength
+
start
-
buff
.
position
();
int
compLen
=
pageLength
+
start
-
buff
.
position
();
byte
[]
comp
=
Utils
.
newBytes
(
compLen
);
byte
[]
comp
=
Data
Utils
.
newBytes
(
compLen
);
buff
.
get
(
comp
);
buff
.
get
(
comp
);
int
l
=
compLen
+
lenAdd
;
int
l
=
compLen
+
lenAdd
;
buff
=
ByteBuffer
.
allocate
(
l
);
buff
=
ByteBuffer
.
allocate
(
l
);
...
@@ -762,8 +761,9 @@ public class Page {
...
@@ -762,8 +761,9 @@ public class Page {
*
*
* @param chunk the chunk
* @param chunk the chunk
* @param buff the target buffer
* @param buff the target buffer
* @return the target buffer
*/
*/
private
void
write
(
Chunk
chunk
,
ByteBuffer
buff
)
{
private
ByteBuffer
write
(
Chunk
chunk
,
ByteBuffer
buff
)
{
int
start
=
buff
.
position
();
int
start
=
buff
.
position
();
buff
.
putInt
(
0
);
buff
.
putInt
(
0
);
buff
.
putShort
((
byte
)
0
);
buff
.
putShort
((
byte
)
0
);
...
@@ -776,7 +776,7 @@ public class Page {
...
@@ -776,7 +776,7 @@ public class Page {
int
compressStart
=
buff
.
position
();
int
compressStart
=
buff
.
position
();
DataType
keyType
=
map
.
getKeyType
();
DataType
keyType
=
map
.
getKeyType
();
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
keyType
.
write
(
buff
,
keys
[
i
]);
buff
=
keyType
.
write
(
buff
,
keys
[
i
]);
}
}
if
(
type
==
DataUtils
.
PAGE_TYPE_NODE
)
{
if
(
type
==
DataUtils
.
PAGE_TYPE_NODE
)
{
for
(
int
i
=
0
;
i
<=
len
;
i
++)
{
for
(
int
i
=
0
;
i
<=
len
;
i
++)
{
...
@@ -788,7 +788,7 @@ public class Page {
...
@@ -788,7 +788,7 @@ public class Page {
}
else
{
}
else
{
DataType
valueType
=
map
.
getValueType
();
DataType
valueType
=
map
.
getValueType
();
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
valueType
.
write
(
buff
,
values
[
i
]);
buff
=
valueType
.
write
(
buff
,
values
[
i
]);
}
}
}
}
if
(
map
.
getStore
().
getCompress
())
{
if
(
map
.
getStore
().
getCompress
())
{
...
@@ -818,45 +818,7 @@ public class Page {
...
@@ -818,45 +818,7 @@ public class Page {
chunk
.
maxLength
+=
max
;
chunk
.
maxLength
+=
max
;
chunk
.
maxLengthLive
+=
max
;
chunk
.
maxLengthLive
+=
max
;
chunk
.
pageCount
++;
chunk
.
pageCount
++;
}
return
buff
;
/**
* Get the maximum length in bytes to store temporary records, recursively.
*
* @return the maximum length
*/
int
getMaxLengthTempRecursive
()
{
int
maxLength
=
getMaxLength
();
if
(!
isLeaf
())
{
for
(
int
i
=
0
;
i
<=
keyCount
;
i
++)
{
Page
p
=
childrenPages
[
i
];
if
(
p
!=
null
)
{
maxLength
+=
p
.
getMaxLengthTempRecursive
();
}
}
}
return
maxLength
;
}
int
getMaxLength
()
{
// length, check, map id, key length, type
int
maxLength
=
4
+
2
+
DataUtils
.
MAX_VAR_INT_LEN
+
DataUtils
.
MAX_VAR_INT_LEN
+
1
;
int
len
=
keyCount
;
DataType
keyType
=
map
.
getKeyType
();
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
maxLength
+=
keyType
.
getMaxLength
(
keys
[
i
]);
}
if
(
isLeaf
())
{
DataType
valueType
=
map
.
getValueType
();
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
maxLength
+=
valueType
.
getMaxLength
(
values
[
i
]);
}
}
else
{
maxLength
+=
8
*
len
;
maxLength
+=
DataUtils
.
MAX_VAR_LONG_LEN
*
len
;
}
return
maxLength
;
}
}
/**
/**
...
@@ -865,21 +827,21 @@ public class Page {
...
@@ -865,21 +827,21 @@ public class Page {
*
*
* @param chunk the chunk
* @param chunk the chunk
* @param buff the target buffer
* @param buff the target buffer
* @return the
page id
* @return the
target buffer
*/
*/
long
writeUnsavedRecursive
(
Chunk
chunk
,
ByteBuffer
buff
)
{
ByteBuffer
writeUnsavedRecursive
(
Chunk
chunk
,
ByteBuffer
buff
)
{
if
(!
isLeaf
())
{
if
(!
isLeaf
())
{
int
len
=
children
.
length
;
int
len
=
children
.
length
;
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
Page
p
=
childrenPages
[
i
];
Page
p
=
childrenPages
[
i
];
if
(
p
!=
null
)
{
if
(
p
!=
null
)
{
children
[
i
]
=
p
.
writeUnsavedRecursive
(
chunk
,
buff
);
buff
=
p
.
writeUnsavedRecursive
(
chunk
,
buff
);
children
[
i
]
=
p
.
getPos
();
childrenPages
[
i
]
=
null
;
childrenPages
[
i
]
=
null
;
}
}
}
}
}
}
write
(
chunk
,
buff
);
return
write
(
chunk
,
buff
);
return
pos
;
}
}
long
getVersion
()
{
long
getVersion
()
{
...
...
h2/src/main/org/h2/mvstore/StreamStore.java
浏览文件 @
78a4f621
...
@@ -11,10 +11,10 @@ import java.io.ByteArrayOutputStream;
...
@@ -11,10 +11,10 @@ import java.io.ByteArrayOutputStream;
import
java.io.IOException
;
import
java.io.IOException
;
import
java.io.InputStream
;
import
java.io.InputStream
;
import
java.nio.ByteBuffer
;
import
java.nio.ByteBuffer
;
import
java.util.Arrays
;
import
java.util.Map
;
import
java.util.Map
;
import
java.util.concurrent.atomic.AtomicLong
;
import
java.util.concurrent.atomic.AtomicLong
;
import
org.h2.util.IOUtils
;
import
java.util.concurrent.atomic.AtomicReference
;
import
org.h2.util.StringUtils
;
/**
/**
* A facility to store streams in a map. Streams are split into blocks, which
* A facility to store streams in a map. Streams are split into blocks, which
...
@@ -41,6 +41,7 @@ public class StreamStore {
...
@@ -41,6 +41,7 @@ public class StreamStore {
private
int
minBlockSize
=
256
;
private
int
minBlockSize
=
256
;
private
int
maxBlockSize
=
256
*
1024
;
private
int
maxBlockSize
=
256
*
1024
;
private
final
AtomicLong
nextKey
=
new
AtomicLong
();
private
final
AtomicLong
nextKey
=
new
AtomicLong
();
private
final
AtomicReference
<
byte
[]>
nextBuffer
=
new
AtomicReference
<
byte
[]>();
/**
/**
* Create a stream store instance.
* Create a stream store instance.
...
@@ -128,25 +129,46 @@ public class StreamStore {
...
@@ -128,25 +129,46 @@ public class StreamStore {
}
}
}
}
}
}
ByteArrayOutputStream
buffer
=
new
ByteArrayOutputStream
();
byte
[]
readBuffer
=
nextBuffer
.
getAndSet
(
null
);
int
len
=
(
int
)
IOUtils
.
copy
(
in
,
buffer
,
maxBlockSize
);
if
(
readBuffer
==
null
)
{
readBuffer
=
new
byte
[
maxBlockSize
];
}
byte
[]
buff
=
read
(
in
,
readBuffer
);
if
(
buff
!=
readBuffer
)
{
// re-use the buffer if the result was shorter
nextBuffer
.
set
(
readBuffer
);
}
int
len
=
buff
.
length
;
if
(
len
==
0
)
{
if
(
len
==
0
)
{
return
true
;
return
true
;
}
}
boolean
eof
=
len
<
maxBlockSize
;
boolean
eof
=
len
<
maxBlockSize
;
byte
[]
data
=
buffer
.
toByteArray
();
if
(
len
<
minBlockSize
)
{
if
(
len
<
minBlockSize
)
{
id
.
write
(
0
);
id
.
write
(
0
);
DataUtils
.
writeVarInt
(
id
,
len
);
DataUtils
.
writeVarInt
(
id
,
len
);
id
.
write
(
data
);
id
.
write
(
buff
);
}
else
{
}
else
{
id
.
write
(
1
);
id
.
write
(
1
);
DataUtils
.
writeVarInt
(
id
,
len
);
DataUtils
.
writeVarInt
(
id
,
len
);
DataUtils
.
writeVarLong
(
id
,
writeBlock
(
data
));
DataUtils
.
writeVarLong
(
id
,
writeBlock
(
buff
));
}
}
return
eof
;
return
eof
;
}
}
private
static
byte
[]
read
(
InputStream
in
,
byte
[]
target
)
throws
IOException
{
int
copied
=
0
;
int
remaining
=
target
.
length
;
while
(
remaining
>
0
)
{
int
len
=
in
.
read
(
target
,
copied
,
remaining
);
if
(
len
<
0
)
{
return
Arrays
.
copyOf
(
target
,
copied
);
}
copied
+=
len
;
remaining
-=
len
;
}
return
target
;
}
private
ByteArrayOutputStream
putIndirectId
(
ByteArrayOutputStream
id
)
throws
IOException
{
private
ByteArrayOutputStream
putIndirectId
(
ByteArrayOutputStream
id
)
throws
IOException
{
byte
[]
data
=
id
.
toByteArray
();
byte
[]
data
=
id
.
toByteArray
();
id
=
new
ByteArrayOutputStream
();
id
=
new
ByteArrayOutputStream
();
...
@@ -222,7 +244,7 @@ public class StreamStore {
...
@@ -222,7 +244,7 @@ public class StreamStore {
break
;
break
;
default
:
default
:
throw
DataUtils
.
newIllegalArgumentException
(
throw
DataUtils
.
newIllegalArgumentException
(
"Unsupported id {0}"
,
StringUtils
.
convertBytesToHex
(
id
));
"Unsupported id {0}"
,
Arrays
.
toString
(
id
));
}
}
}
}
}
}
...
@@ -254,7 +276,7 @@ public class StreamStore {
...
@@ -254,7 +276,7 @@ public class StreamStore {
break
;
break
;
default
:
default
:
throw
DataUtils
.
newIllegalArgumentException
(
throw
DataUtils
.
newIllegalArgumentException
(
"Unsupported id {0}"
,
StringUtils
.
convertBytesToHex
(
id
));
"Unsupported id {0}"
,
Arrays
.
toString
(
id
));
}
}
}
}
return
length
;
return
length
;
...
@@ -418,7 +440,7 @@ public class StreamStore {
...
@@ -418,7 +440,7 @@ public class StreamStore {
}
}
default
:
default
:
throw
DataUtils
.
newIllegalArgumentException
(
throw
DataUtils
.
newIllegalArgumentException
(
"Unsupported id {0}"
,
StringUtils
.
convertBytesToHex
(
idBuffer
.
array
()));
"Unsupported id {0}"
,
Arrays
.
toString
(
idBuffer
.
array
()));
}
}
}
}
return
null
;
return
null
;
...
...
h2/src/main/org/h2/mvstore/db/ValueArrayDataType.java
浏览文件 @
78a4f621
...
@@ -26,7 +26,6 @@ import org.h2.store.DataHandler;
...
@@ -26,7 +26,6 @@ import org.h2.store.DataHandler;
import
org.h2.store.LobStorage
;
import
org.h2.store.LobStorage
;
import
org.h2.tools.SimpleResultSet
;
import
org.h2.tools.SimpleResultSet
;
import
org.h2.util.DateTimeUtils
;
import
org.h2.util.DateTimeUtils
;
import
org.h2.util.Utils
;
import
org.h2.value.CompareMode
;
import
org.h2.value.CompareMode
;
import
org.h2.value.Value
;
import
org.h2.value.Value
;
import
org.h2.value.ValueArray
;
import
org.h2.value.ValueArray
;
...
@@ -136,20 +135,6 @@ public class ValueArrayDataType implements DataType {
...
@@ -136,20 +135,6 @@ public class ValueArrayDataType implements DataType {
return
a
.
compareTypeSave
(
b
,
compareMode
);
return
a
.
compareTypeSave
(
b
,
compareMode
);
}
}
public
int
getMaxLength
(
Object
obj
)
{
Value
[]
x
=
(
Value
[])
obj
;
int
len
=
x
.
length
;
int
result
=
DataUtils
.
MAX_VAR_INT_LEN
;
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
result
+=
getMaxLength
(
x
[
i
]);
}
return
result
;
}
private
int
getMaxLength
(
Value
v
)
{
return
Data
.
getValueLen
(
v
,
handler
);
}
public
int
getMemory
(
Object
obj
)
{
public
int
getMemory
(
Object
obj
)
{
Value
[]
x
=
(
Value
[])
obj
;
Value
[]
x
=
(
Value
[])
obj
;
int
len
=
x
.
length
;
int
len
=
x
.
length
;
...
@@ -173,20 +158,22 @@ public class ValueArrayDataType implements DataType {
...
@@ -173,20 +158,22 @@ public class ValueArrayDataType implements DataType {
return
x
;
return
x
;
}
}
public
void
write
(
ByteBuffer
buff
,
Object
obj
)
{
public
ByteBuffer
write
(
ByteBuffer
buff
,
Object
obj
)
{
Value
[]
x
=
(
Value
[])
obj
;
Value
[]
x
=
(
Value
[])
obj
;
int
len
=
x
.
length
;
int
len
=
x
.
length
;
DataUtils
.
writeVarInt
(
buff
,
len
);
DataUtils
.
writeVarInt
(
buff
,
len
);
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
writeValue
(
buff
,
x
[
i
]);
buff
=
DataUtils
.
ensureCapacity
(
buff
,
0
);
buff
=
writeValue
(
buff
,
x
[
i
]);
}
}
return
buff
;
}
}
private
void
writeValue
(
ByteBuffer
buff
,
Value
v
)
{
private
ByteBuffer
writeValue
(
ByteBuffer
buff
,
Value
v
)
{
int
start
=
buff
.
position
();
int
start
=
buff
.
position
();
if
(
v
==
ValueNull
.
INSTANCE
)
{
if
(
v
==
ValueNull
.
INSTANCE
)
{
buff
.
put
((
byte
)
0
);
buff
.
put
((
byte
)
0
);
return
;
return
buff
;
}
}
int
type
=
v
.
getType
();
int
type
=
v
.
getType
();
switch
(
type
)
{
switch
(
type
)
{
...
@@ -251,6 +238,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -251,6 +238,7 @@ public class ValueArrayDataType implements DataType {
writeVarInt
(
buff
,
scale
);
writeVarInt
(
buff
,
scale
);
byte
[]
bytes
=
b
.
toByteArray
();
byte
[]
bytes
=
b
.
toByteArray
();
writeVarInt
(
buff
,
bytes
.
length
);
writeVarInt
(
buff
,
bytes
.
length
);
buff
=
DataUtils
.
ensureCapacity
(
buff
,
bytes
.
length
);
buff
.
put
(
bytes
,
0
,
bytes
.
length
);
buff
.
put
(
bytes
,
0
,
bytes
.
length
);
}
}
}
}
...
@@ -305,6 +293,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -305,6 +293,7 @@ public class ValueArrayDataType implements DataType {
buff
.
put
((
byte
)
type
);
buff
.
put
((
byte
)
type
);
byte
[]
b
=
v
.
getBytesNoCopy
();
byte
[]
b
=
v
.
getBytesNoCopy
();
writeVarInt
(
buff
,
b
.
length
);
writeVarInt
(
buff
,
b
.
length
);
buff
=
DataUtils
.
ensureCapacity
(
buff
,
b
.
length
);
buff
.
put
(
b
,
0
,
b
.
length
);
buff
.
put
(
b
,
0
,
b
.
length
);
break
;
break
;
}
}
...
@@ -317,6 +306,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -317,6 +306,7 @@ public class ValueArrayDataType implements DataType {
}
else
{
}
else
{
buff
.
put
((
byte
)
type
);
buff
.
put
((
byte
)
type
);
writeVarInt
(
buff
,
b
.
length
);
writeVarInt
(
buff
,
b
.
length
);
buff
=
DataUtils
.
ensureCapacity
(
buff
,
b
.
length
);
buff
.
put
(
b
,
0
,
b
.
length
);
buff
.
put
(
b
,
0
,
b
.
length
);
}
}
break
;
break
;
...
@@ -333,17 +323,17 @@ public class ValueArrayDataType implements DataType {
...
@@ -333,17 +323,17 @@ public class ValueArrayDataType implements DataType {
int
len
=
s
.
length
();
int
len
=
s
.
length
();
if
(
len
<
32
)
{
if
(
len
<
32
)
{
buff
.
put
((
byte
)
(
STRING_0_31
+
len
));
buff
.
put
((
byte
)
(
STRING_0_31
+
len
));
writeStringWithoutLength
(
buff
,
s
,
len
);
buff
=
writeStringWithoutLength
(
buff
,
s
,
len
);
}
else
{
}
else
{
buff
.
put
((
byte
)
type
);
buff
.
put
((
byte
)
type
);
writeString
(
buff
,
s
);
buff
=
writeString
(
buff
,
s
);
}
}
break
;
break
;
}
}
case
Value
.
STRING_IGNORECASE
:
case
Value
.
STRING_IGNORECASE
:
case
Value
.
STRING_FIXED
:
case
Value
.
STRING_FIXED
:
buff
.
put
((
byte
)
type
);
buff
.
put
((
byte
)
type
);
writeString
(
buff
,
v
.
getString
());
buff
=
writeString
(
buff
,
v
.
getString
());
break
;
break
;
case
Value
.
DOUBLE
:
{
case
Value
.
DOUBLE
:
{
double
x
=
v
.
getDouble
();
double
x
=
v
.
getDouble
();
...
@@ -393,10 +383,11 @@ public class ValueArrayDataType implements DataType {
...
@@ -393,10 +383,11 @@ public class ValueArrayDataType implements DataType {
writeVarLong
(
buff
,
lob
.
getPrecision
());
writeVarLong
(
buff
,
lob
.
getPrecision
());
buff
.
put
((
byte
)
(
lob
.
useCompression
()
?
1
:
0
));
buff
.
put
((
byte
)
(
lob
.
useCompression
()
?
1
:
0
));
if
(
t
==
-
2
)
{
if
(
t
==
-
2
)
{
writeString
(
buff
,
lob
.
getFileName
());
buff
=
writeString
(
buff
,
lob
.
getFileName
());
}
}
}
else
{
}
else
{
writeVarInt
(
buff
,
small
.
length
);
writeVarInt
(
buff
,
small
.
length
);
buff
=
DataUtils
.
ensureCapacity
(
buff
,
small
.
length
);
buff
.
put
(
small
,
0
,
small
.
length
);
buff
.
put
(
small
,
0
,
small
.
length
);
}
}
}
else
{
}
else
{
...
@@ -409,6 +400,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -409,6 +400,7 @@ public class ValueArrayDataType implements DataType {
writeVarLong
(
buff
,
lob
.
getPrecision
());
writeVarLong
(
buff
,
lob
.
getPrecision
());
}
else
{
}
else
{
writeVarInt
(
buff
,
small
.
length
);
writeVarInt
(
buff
,
small
.
length
);
buff
=
DataUtils
.
ensureCapacity
(
buff
,
small
.
length
);
buff
.
put
(
small
,
0
,
small
.
length
);
buff
.
put
(
small
,
0
,
small
.
length
);
}
}
}
}
...
@@ -419,7 +411,8 @@ public class ValueArrayDataType implements DataType {
...
@@ -419,7 +411,8 @@ public class ValueArrayDataType implements DataType {
Value
[]
list
=
((
ValueArray
)
v
).
getList
();
Value
[]
list
=
((
ValueArray
)
v
).
getList
();
writeVarInt
(
buff
,
list
.
length
);
writeVarInt
(
buff
,
list
.
length
);
for
(
Value
x
:
list
)
{
for
(
Value
x
:
list
)
{
writeValue
(
buff
,
x
);
buff
=
DataUtils
.
ensureCapacity
(
buff
,
0
);
buff
=
writeValue
(
buff
,
x
);
}
}
break
;
break
;
}
}
...
@@ -432,7 +425,8 @@ public class ValueArrayDataType implements DataType {
...
@@ -432,7 +425,8 @@ public class ValueArrayDataType implements DataType {
int
columnCount
=
meta
.
getColumnCount
();
int
columnCount
=
meta
.
getColumnCount
();
writeVarInt
(
buff
,
columnCount
);
writeVarInt
(
buff
,
columnCount
);
for
(
int
i
=
0
;
i
<
columnCount
;
i
++)
{
for
(
int
i
=
0
;
i
<
columnCount
;
i
++)
{
writeString
(
buff
,
meta
.
getColumnName
(
i
+
1
));
buff
=
DataUtils
.
ensureCapacity
(
buff
,
0
);
buff
=
writeString
(
buff
,
meta
.
getColumnName
(
i
+
1
));
writeVarInt
(
buff
,
meta
.
getColumnType
(
i
+
1
));
writeVarInt
(
buff
,
meta
.
getColumnType
(
i
+
1
));
writeVarInt
(
buff
,
meta
.
getPrecision
(
i
+
1
));
writeVarInt
(
buff
,
meta
.
getPrecision
(
i
+
1
));
writeVarInt
(
buff
,
meta
.
getScale
(
i
+
1
));
writeVarInt
(
buff
,
meta
.
getScale
(
i
+
1
));
...
@@ -442,7 +436,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -442,7 +436,7 @@ public class ValueArrayDataType implements DataType {
for
(
int
i
=
0
;
i
<
columnCount
;
i
++)
{
for
(
int
i
=
0
;
i
<
columnCount
;
i
++)
{
int
t
=
org
.
h2
.
value
.
DataType
.
convertSQLTypeToValueType
(
meta
.
getColumnType
(
i
+
1
));
int
t
=
org
.
h2
.
value
.
DataType
.
convertSQLTypeToValueType
(
meta
.
getColumnType
(
i
+
1
));
Value
val
=
org
.
h2
.
value
.
DataType
.
readValue
(
null
,
rs
,
i
+
1
,
t
);
Value
val
=
org
.
h2
.
value
.
DataType
.
readValue
(
null
,
rs
,
i
+
1
,
t
);
writeValue
(
buff
,
val
);
buff
=
writeValue
(
buff
,
val
);
}
}
}
}
buff
.
put
((
byte
)
0
);
buff
.
put
((
byte
)
0
);
...
@@ -461,6 +455,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -461,6 +455,7 @@ public class ValueArrayDataType implements DataType {
.
throwInternalError
(
"value size error: got "
+
(
buff
.
position
()
-
start
)
+
" expected "
+
Data
.
getValueLen
(
v
,
handler
));
.
throwInternalError
(
"value size error: got "
+
(
buff
.
position
()
-
start
)
+
" expected "
+
Data
.
getValueLen
(
v
,
handler
));
}
}
}
}
return
buff
;
}
}
private
static
void
writeVarInt
(
ByteBuffer
buff
,
int
x
)
{
private
static
void
writeVarInt
(
ByteBuffer
buff
,
int
x
)
{
...
@@ -479,13 +474,14 @@ public class ValueArrayDataType implements DataType {
...
@@ -479,13 +474,14 @@ public class ValueArrayDataType implements DataType {
buff
.
put
((
byte
)
x
);
buff
.
put
((
byte
)
x
);
}
}
private
static
void
writeString
(
ByteBuffer
buff
,
String
s
)
{
private
static
ByteBuffer
writeString
(
ByteBuffer
buff
,
String
s
)
{
int
len
=
s
.
length
();
int
len
=
s
.
length
();
writeVarInt
(
buff
,
len
);
writeVarInt
(
buff
,
len
);
writeStringWithoutLength
(
buff
,
s
,
len
);
return
writeStringWithoutLength
(
buff
,
s
,
len
);
}
}
private
static
void
writeStringWithoutLength
(
ByteBuffer
buff
,
String
s
,
int
len
)
{
private
static
ByteBuffer
writeStringWithoutLength
(
ByteBuffer
buff
,
String
s
,
int
len
)
{
buff
=
DataUtils
.
ensureCapacity
(
buff
,
3
*
len
);
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
int
c
=
s
.
charAt
(
i
);
int
c
=
s
.
charAt
(
i
);
if
(
c
<
0x80
)
{
if
(
c
<
0x80
)
{
...
@@ -499,6 +495,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -499,6 +495,7 @@ public class ValueArrayDataType implements DataType {
buff
.
put
((
byte
)
(
c
&
0x3f
));
buff
.
put
((
byte
)
(
c
&
0x3f
));
}
}
}
}
return
buff
;
}
}
/**
/**
...
@@ -540,7 +537,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -540,7 +537,7 @@ public class ValueArrayDataType implements DataType {
case
Value
.
DECIMAL
:
{
case
Value
.
DECIMAL
:
{
int
scale
=
readVarInt
(
buff
);
int
scale
=
readVarInt
(
buff
);
int
len
=
readVarInt
(
buff
);
int
len
=
readVarInt
(
buff
);
byte
[]
buff2
=
Utils
.
newBytes
(
len
);
byte
[]
buff2
=
Data
Utils
.
newBytes
(
len
);
buff
.
get
(
buff2
,
0
,
len
);
buff
.
get
(
buff2
,
0
,
len
);
BigInteger
b
=
new
BigInteger
(
buff2
);
BigInteger
b
=
new
BigInteger
(
buff2
);
return
ValueDecimal
.
get
(
new
BigDecimal
(
b
,
scale
));
return
ValueDecimal
.
get
(
new
BigDecimal
(
b
,
scale
));
...
@@ -571,13 +568,13 @@ public class ValueArrayDataType implements DataType {
...
@@ -571,13 +568,13 @@ public class ValueArrayDataType implements DataType {
}
}
case
Value
.
BYTES
:
{
case
Value
.
BYTES
:
{
int
len
=
readVarInt
(
buff
);
int
len
=
readVarInt
(
buff
);
byte
[]
b
=
Utils
.
newBytes
(
len
);
byte
[]
b
=
Data
Utils
.
newBytes
(
len
);
buff
.
get
(
b
,
0
,
len
);
buff
.
get
(
b
,
0
,
len
);
return
ValueBytes
.
getNoCopy
(
b
);
return
ValueBytes
.
getNoCopy
(
b
);
}
}
case
Value
.
JAVA_OBJECT
:
{
case
Value
.
JAVA_OBJECT
:
{
int
len
=
readVarInt
(
buff
);
int
len
=
readVarInt
(
buff
);
byte
[]
b
=
Utils
.
newBytes
(
len
);
byte
[]
b
=
Data
Utils
.
newBytes
(
len
);
buff
.
get
(
b
,
0
,
len
);
buff
.
get
(
b
,
0
,
len
);
return
ValueJavaObject
.
getNoCopy
(
null
,
b
);
return
ValueJavaObject
.
getNoCopy
(
null
,
b
);
}
}
...
@@ -605,7 +602,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -605,7 +602,7 @@ public class ValueArrayDataType implements DataType {
case
Value
.
CLOB
:
{
case
Value
.
CLOB
:
{
int
smallLen
=
readVarInt
(
buff
);
int
smallLen
=
readVarInt
(
buff
);
if
(
smallLen
>=
0
)
{
if
(
smallLen
>=
0
)
{
byte
[]
small
=
Utils
.
newBytes
(
smallLen
);
byte
[]
small
=
Data
Utils
.
newBytes
(
smallLen
);
buff
.
get
(
small
,
0
,
smallLen
);
buff
.
get
(
small
,
0
,
smallLen
);
return
LobStorage
.
createSmallLob
(
type
,
small
);
return
LobStorage
.
createSmallLob
(
type
,
small
);
}
else
if
(
smallLen
==
-
3
)
{
}
else
if
(
smallLen
==
-
3
)
{
...
@@ -666,7 +663,7 @@ public class ValueArrayDataType implements DataType {
...
@@ -666,7 +663,7 @@ public class ValueArrayDataType implements DataType {
return
ValueLong
.
get
(
type
-
LONG_0_7
);
return
ValueLong
.
get
(
type
-
LONG_0_7
);
}
else
if
(
type
>=
BYTES_0_31
&&
type
<
BYTES_0_31
+
32
)
{
}
else
if
(
type
>=
BYTES_0_31
&&
type
<
BYTES_0_31
+
32
)
{
int
len
=
type
-
BYTES_0_31
;
int
len
=
type
-
BYTES_0_31
;
byte
[]
b
=
Utils
.
newBytes
(
len
);
byte
[]
b
=
Data
Utils
.
newBytes
(
len
);
buff
.
get
(
b
,
0
,
len
);
buff
.
get
(
b
,
0
,
len
);
return
ValueBytes
.
getNoCopy
(
b
);
return
ValueBytes
.
getNoCopy
(
b
);
}
else
if
(
type
>=
STRING_0_31
&&
type
<
STRING_0_31
+
32
)
{
}
else
if
(
type
>=
STRING_0_31
&&
type
<
STRING_0_31
+
32
)
{
...
...
h2/src/main/org/h2/mvstore/rtree/SpatialDataType.java
浏览文件 @
78a4f621
...
@@ -47,18 +47,13 @@ public class SpatialDataType implements DataType {
...
@@ -47,18 +47,13 @@ public class SpatialDataType implements DataType {
return
la
==
lb
;
return
la
==
lb
;
}
}
@Override
public
int
getMaxLength
(
Object
obj
)
{
return
1
+
dimensions
*
8
+
DataUtils
.
MAX_VAR_LONG_LEN
;
}
@Override
@Override
public
int
getMemory
(
Object
obj
)
{
public
int
getMemory
(
Object
obj
)
{
return
40
+
dimensions
*
4
;
return
40
+
dimensions
*
4
;
}
}
@Override
@Override
public
void
write
(
ByteBuffer
buff
,
Object
obj
)
{
public
ByteBuffer
write
(
ByteBuffer
buff
,
Object
obj
)
{
SpatialKey
k
=
(
SpatialKey
)
obj
;
SpatialKey
k
=
(
SpatialKey
)
obj
;
int
flags
=
0
;
int
flags
=
0
;
for
(
int
i
=
0
;
i
<
dimensions
;
i
++)
{
for
(
int
i
=
0
;
i
<
dimensions
;
i
++)
{
...
@@ -74,6 +69,7 @@ public class SpatialDataType implements DataType {
...
@@ -74,6 +69,7 @@ public class SpatialDataType implements DataType {
}
}
}
}
DataUtils
.
writeVarLong
(
buff
,
k
.
getId
());
DataUtils
.
writeVarLong
(
buff
,
k
.
getId
());
return
buff
;
}
}
@Override
@Override
...
...
h2/src/main/org/h2/mvstore/type/DataType.java
浏览文件 @
78a4f621
...
@@ -22,15 +22,6 @@ public interface DataType {
...
@@ -22,15 +22,6 @@ public interface DataType {
*/
*/
int
compare
(
Object
a
,
Object
b
);
int
compare
(
Object
a
,
Object
b
);
/**
* Get the maximum length in bytes used to store an object. In many cases,
* this method can be faster than calculating the exact length.
*
* @param obj the object
* @return the maximum length
*/
int
getMaxLength
(
Object
obj
);
/**
/**
* Estimate the used memory in bytes.
* Estimate the used memory in bytes.
*
*
...
@@ -44,8 +35,9 @@ public interface DataType {
...
@@ -44,8 +35,9 @@ public interface DataType {
*
*
* @param buff the target buffer
* @param buff the target buffer
* @param obj the value
* @param obj the value
* @return the byte buffer
*/
*/
void
write
(
ByteBuffer
buff
,
Object
obj
);
ByteBuffer
write
(
ByteBuffer
buff
,
Object
obj
);
/**
/**
* Read an object.
* Read an object.
...
...
h2/src/main/org/h2/mvstore/type/ObjectDataType.java
浏览文件 @
78a4f621
差异被折叠。
点击展开。
h2/src/main/org/h2/mvstore/type/StringDataType.java
浏览文件 @
78a4f621
...
@@ -20,10 +20,6 @@ public class StringDataType implements DataType {
...
@@ -20,10 +20,6 @@ public class StringDataType implements DataType {
return
a
.
toString
().
compareTo
(
b
.
toString
());
return
a
.
toString
().
compareTo
(
b
.
toString
());
}
}
public
int
getMaxLength
(
Object
obj
)
{
return
DataUtils
.
MAX_VAR_INT_LEN
+
3
*
obj
.
toString
().
length
();
}
public
int
getMemory
(
Object
obj
)
{
public
int
getMemory
(
Object
obj
)
{
return
24
+
2
*
obj
.
toString
().
length
();
return
24
+
2
*
obj
.
toString
().
length
();
}
}
...
@@ -33,11 +29,11 @@ public class StringDataType implements DataType {
...
@@ -33,11 +29,11 @@ public class StringDataType implements DataType {
return
DataUtils
.
readString
(
buff
,
len
);
return
DataUtils
.
readString
(
buff
,
len
);
}
}
public
void
write
(
ByteBuffer
buff
,
Object
obj
)
{
public
ByteBuffer
write
(
ByteBuffer
buff
,
Object
obj
)
{
String
s
=
obj
.
toString
();
String
s
=
obj
.
toString
();
int
len
=
s
.
length
();
int
len
=
s
.
length
();
DataUtils
.
writeVarInt
(
buff
,
len
);
DataUtils
.
writeVarInt
(
buff
,
len
);
DataUtils
.
writeStringData
(
buff
,
s
,
len
);
return
DataUtils
.
writeStringData
(
buff
,
s
,
len
);
}
}
}
}
...
...
h2/src/main/org/h2/server/pg/PgServerThread.java
浏览文件 @
78a4f621
...
@@ -35,6 +35,7 @@ import org.h2.jdbc.JdbcConnection;
...
@@ -35,6 +35,7 @@ import org.h2.jdbc.JdbcConnection;
import
org.h2.jdbc.JdbcPreparedStatement
;
import
org.h2.jdbc.JdbcPreparedStatement
;
import
org.h2.jdbc.JdbcStatement
;
import
org.h2.jdbc.JdbcStatement
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.mvstore.DataUtils
;
import
org.h2.util.IOUtils
;
import
org.h2.util.IOUtils
;
import
org.h2.util.JdbcUtils
;
import
org.h2.util.JdbcUtils
;
import
org.h2.util.ScriptReader
;
import
org.h2.util.ScriptReader
;
...
@@ -132,7 +133,7 @@ public class PgServerThread implements Runnable {
...
@@ -132,7 +133,7 @@ public class PgServerThread implements Runnable {
}
}
int
len
=
dataInRaw
.
readInt
();
int
len
=
dataInRaw
.
readInt
();
len
-=
4
;
len
-=
4
;
byte
[]
data
=
Utils
.
newBytes
(
len
);
byte
[]
data
=
Data
Utils
.
newBytes
(
len
);
dataInRaw
.
readFully
(
data
,
0
,
len
);
dataInRaw
.
readFully
(
data
,
0
,
len
);
dataIn
=
new
DataInputStream
(
new
ByteArrayInputStream
(
data
,
0
,
len
));
dataIn
=
new
DataInputStream
(
new
ByteArrayInputStream
(
data
,
0
,
len
));
switchBlock:
switch
(
x
)
{
switchBlock:
switch
(
x
)
{
...
@@ -246,7 +247,7 @@ public class PgServerThread implements Runnable {
...
@@ -246,7 +247,7 @@ public class PgServerThread implements Runnable {
int
paramCount
=
readShort
();
int
paramCount
=
readShort
();
for
(
int
i
=
0
;
i
<
paramCount
;
i
++)
{
for
(
int
i
=
0
;
i
<
paramCount
;
i
++)
{
int
paramLen
=
readInt
();
int
paramLen
=
readInt
();
byte
[]
d2
=
Utils
.
newBytes
(
paramLen
);
byte
[]
d2
=
Data
Utils
.
newBytes
(
paramLen
);
readFully
(
d2
);
readFully
(
d2
);
try
{
try
{
setParameter
(
prep
.
prep
,
i
,
d2
,
formatCodes
);
setParameter
(
prep
.
prep
,
i
,
d2
,
formatCodes
);
...
...
h2/src/main/org/h2/server/web/WebThread.java
浏览文件 @
78a4f621
...
@@ -23,10 +23,10 @@ import java.util.StringTokenizer;
...
@@ -23,10 +23,10 @@ import java.util.StringTokenizer;
import
org.h2.constant.SysProperties
;
import
org.h2.constant.SysProperties
;
import
org.h2.engine.Constants
;
import
org.h2.engine.Constants
;
import
org.h2.message.TraceSystem
;
import
org.h2.message.TraceSystem
;
import
org.h2.mvstore.DataUtils
;
import
org.h2.util.IOUtils
;
import
org.h2.util.IOUtils
;
import
org.h2.util.NetUtils
;
import
org.h2.util.NetUtils
;
import
org.h2.util.StringUtils
;
import
org.h2.util.StringUtils
;
import
org.h2.util.Utils
;
/**
/**
* For each connection to a session, an object of this class is created.
* For each connection to a session, an object of this class is created.
...
@@ -320,7 +320,7 @@ class WebThread extends WebApp implements Runnable {
...
@@ -320,7 +320,7 @@ class WebThread extends WebApp implements Runnable {
if
(
multipart
)
{
if
(
multipart
)
{
uploadMultipart
(
input
,
len
);
uploadMultipart
(
input
,
len
);
}
else
if
(
session
!=
null
&&
len
>
0
)
{
}
else
if
(
session
!=
null
&&
len
>
0
)
{
byte
[]
bytes
=
Utils
.
newBytes
(
len
);
byte
[]
bytes
=
Data
Utils
.
newBytes
(
len
);
for
(
int
pos
=
0
;
pos
<
len
;)
{
for
(
int
pos
=
0
;
pos
<
len
;)
{
pos
+=
input
.
read
(
bytes
,
pos
,
len
-
pos
);
pos
+=
input
.
read
(
bytes
,
pos
,
len
-
pos
);
}
}
...
@@ -360,7 +360,7 @@ class WebThread extends WebApp implements Runnable {
...
@@ -360,7 +360,7 @@ class WebThread extends WebApp implements Runnable {
RandomAccessFile
f
=
new
RandomAccessFile
(
file
,
"rw"
);
RandomAccessFile
f
=
new
RandomAccessFile
(
file
,
"rw"
);
int
testSize
=
(
int
)
Math
.
min
(
f
.
length
(),
Constants
.
IO_BUFFER_SIZE
);
int
testSize
=
(
int
)
Math
.
min
(
f
.
length
(),
Constants
.
IO_BUFFER_SIZE
);
f
.
seek
(
f
.
length
()
-
testSize
);
f
.
seek
(
f
.
length
()
-
testSize
);
byte
[]
bytes
=
Utils
.
newBytes
(
Constants
.
IO_BUFFER_SIZE
);
byte
[]
bytes
=
Data
Utils
.
newBytes
(
Constants
.
IO_BUFFER_SIZE
);
f
.
readFully
(
bytes
,
0
,
testSize
);
f
.
readFully
(
bytes
,
0
,
testSize
);
String
s
=
new
String
(
bytes
,
"ASCII"
);
String
s
=
new
String
(
bytes
,
"ASCII"
);
int
x
=
s
.
lastIndexOf
(
boundary
);
int
x
=
s
.
lastIndexOf
(
boundary
);
...
...
h2/src/main/org/h2/store/Data.java
浏览文件 @
78a4f621
...
@@ -24,10 +24,10 @@ import org.h2.constant.ErrorCode;
...
@@ -24,10 +24,10 @@ import org.h2.constant.ErrorCode;
import
org.h2.constant.SysProperties
;
import
org.h2.constant.SysProperties
;
import
org.h2.engine.Constants
;
import
org.h2.engine.Constants
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.mvstore.DataUtils
;
import
org.h2.tools.SimpleResultSet
;
import
org.h2.tools.SimpleResultSet
;
import
org.h2.util.DateTimeUtils
;
import
org.h2.util.DateTimeUtils
;
import
org.h2.util.MathUtils
;
import
org.h2.util.MathUtils
;
import
org.h2.util.Utils
;
import
org.h2.value.DataType
;
import
org.h2.value.DataType
;
import
org.h2.value.Value
;
import
org.h2.value.Value
;
import
org.h2.value.ValueArray
;
import
org.h2.value.ValueArray
;
...
@@ -720,7 +720,7 @@ public class Data {
...
@@ -720,7 +720,7 @@ public class Data {
case
Value
.
DECIMAL
:
{
case
Value
.
DECIMAL
:
{
int
scale
=
readVarInt
();
int
scale
=
readVarInt
();
int
len
=
readVarInt
();
int
len
=
readVarInt
();
byte
[]
buff
=
Utils
.
newBytes
(
len
);
byte
[]
buff
=
Data
Utils
.
newBytes
(
len
);
read
(
buff
,
0
,
len
);
read
(
buff
,
0
,
len
);
BigInteger
b
=
new
BigInteger
(
buff
);
BigInteger
b
=
new
BigInteger
(
buff
);
return
ValueDecimal
.
get
(
new
BigDecimal
(
b
,
scale
));
return
ValueDecimal
.
get
(
new
BigDecimal
(
b
,
scale
));
...
@@ -751,13 +751,13 @@ public class Data {
...
@@ -751,13 +751,13 @@ public class Data {
}
}
case
Value
.
BYTES
:
{
case
Value
.
BYTES
:
{
int
len
=
readVarInt
();
int
len
=
readVarInt
();
byte
[]
b
=
Utils
.
newBytes
(
len
);
byte
[]
b
=
Data
Utils
.
newBytes
(
len
);
read
(
b
,
0
,
len
);
read
(
b
,
0
,
len
);
return
ValueBytes
.
getNoCopy
(
b
);
return
ValueBytes
.
getNoCopy
(
b
);
}
}
case
Value
.
JAVA_OBJECT
:
{
case
Value
.
JAVA_OBJECT
:
{
int
len
=
readVarInt
();
int
len
=
readVarInt
();
byte
[]
b
=
Utils
.
newBytes
(
len
);
byte
[]
b
=
Data
Utils
.
newBytes
(
len
);
read
(
b
,
0
,
len
);
read
(
b
,
0
,
len
);
return
ValueJavaObject
.
getNoCopy
(
null
,
b
);
return
ValueJavaObject
.
getNoCopy
(
null
,
b
);
}
}
...
@@ -785,7 +785,7 @@ public class Data {
...
@@ -785,7 +785,7 @@ public class Data {
case
Value
.
CLOB
:
{
case
Value
.
CLOB
:
{
int
smallLen
=
readVarInt
();
int
smallLen
=
readVarInt
();
if
(
smallLen
>=
0
)
{
if
(
smallLen
>=
0
)
{
byte
[]
small
=
Utils
.
newBytes
(
smallLen
);
byte
[]
small
=
Data
Utils
.
newBytes
(
smallLen
);
read
(
small
,
0
,
smallLen
);
read
(
small
,
0
,
smallLen
);
return
LobStorage
.
createSmallLob
(
type
,
small
);
return
LobStorage
.
createSmallLob
(
type
,
small
);
}
else
if
(
smallLen
==
-
3
)
{
}
else
if
(
smallLen
==
-
3
)
{
...
@@ -846,7 +846,7 @@ public class Data {
...
@@ -846,7 +846,7 @@ public class Data {
return
ValueLong
.
get
(
type
-
LONG_0_7
);
return
ValueLong
.
get
(
type
-
LONG_0_7
);
}
else
if
(
type
>=
BYTES_0_31
&&
type
<
BYTES_0_31
+
32
)
{
}
else
if
(
type
>=
BYTES_0_31
&&
type
<
BYTES_0_31
+
32
)
{
int
len
=
type
-
BYTES_0_31
;
int
len
=
type
-
BYTES_0_31
;
byte
[]
b
=
Utils
.
newBytes
(
len
);
byte
[]
b
=
Data
Utils
.
newBytes
(
len
);
read
(
b
,
0
,
len
);
read
(
b
,
0
,
len
);
return
ValueBytes
.
getNoCopy
(
b
);
return
ValueBytes
.
getNoCopy
(
b
);
}
else
if
(
type
>=
STRING_0_31
&&
type
<
STRING_0_31
+
32
)
{
}
else
if
(
type
>=
STRING_0_31
&&
type
<
STRING_0_31
+
32
)
{
...
@@ -1260,7 +1260,7 @@ public class Data {
...
@@ -1260,7 +1260,7 @@ public class Data {
}
}
private
void
expand
(
int
plus
)
{
private
void
expand
(
int
plus
)
{
byte
[]
d
=
Utils
.
newBytes
((
data
.
length
+
plus
)
*
2
);
byte
[]
d
=
Data
Utils
.
newBytes
((
data
.
length
+
plus
)
*
2
);
// must copy everything, because pos could be 0 and data may be
// must copy everything, because pos could be 0 and data may be
// still required
// still required
System
.
arraycopy
(
data
,
0
,
d
,
0
,
data
.
length
);
System
.
arraycopy
(
data
,
0
,
d
,
0
,
data
.
length
);
...
...
h2/src/main/org/h2/store/FileStoreInputStream.java
浏览文件 @
78a4f621
...
@@ -10,8 +10,8 @@ import java.io.IOException;
...
@@ -10,8 +10,8 @@ import java.io.IOException;
import
java.io.InputStream
;
import
java.io.InputStream
;
import
org.h2.engine.Constants
;
import
org.h2.engine.Constants
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.mvstore.DataUtils
;
import
org.h2.tools.CompressTool
;
import
org.h2.tools.CompressTool
;
import
org.h2.util.Utils
;
/**
/**
* An input stream that is backed by a file store.
* An input stream that is backed by a file store.
...
@@ -114,7 +114,7 @@ public class FileStoreInputStream extends InputStream {
...
@@ -114,7 +114,7 @@ public class FileStoreInputStream extends InputStream {
page
.
readInt
();
page
.
readInt
();
if
(
compress
!=
null
)
{
if
(
compress
!=
null
)
{
int
uncompressed
=
page
.
readInt
();
int
uncompressed
=
page
.
readInt
();
byte
[]
buff
=
Utils
.
newBytes
(
remainingInBuffer
);
byte
[]
buff
=
Data
Utils
.
newBytes
(
remainingInBuffer
);
page
.
read
(
buff
,
0
,
remainingInBuffer
);
page
.
read
(
buff
,
0
,
remainingInBuffer
);
page
.
reset
();
page
.
reset
();
page
.
checkCapacity
(
uncompressed
);
page
.
checkCapacity
(
uncompressed
);
...
...
h2/src/main/org/h2/store/RecoverTester.java
浏览文件 @
78a4f621
...
@@ -100,7 +100,7 @@ public class RecoverTester implements Recorder {
...
@@ -100,7 +100,7 @@ public class RecoverTester implements Recorder {
private
synchronized
void
testDatabase
(
String
fileName
,
PrintWriter
out
)
{
private
synchronized
void
testDatabase
(
String
fileName
,
PrintWriter
out
)
{
out
.
println
(
"+ write #"
+
writeCount
+
" verify #"
+
verifyCount
);
out
.
println
(
"+ write #"
+
writeCount
+
" verify #"
+
verifyCount
);
try
{
try
{
FileUtils
.
copy
(
fileName
,
testDatabase
+
Constants
.
SUFFIX_PAGE_FILE
);
IOUtils
.
copyFiles
(
fileName
,
testDatabase
+
Constants
.
SUFFIX_PAGE_FILE
);
verifyCount
++;
verifyCount
++;
// avoid using the Engine class to avoid deadlocks
// avoid using the Engine class to avoid deadlocks
Properties
p
=
new
Properties
();
Properties
p
=
new
Properties
();
...
@@ -145,7 +145,7 @@ public class RecoverTester implements Recorder {
...
@@ -145,7 +145,7 @@ public class RecoverTester implements Recorder {
}
}
testDatabase
+=
"X"
;
testDatabase
+=
"X"
;
try
{
try
{
FileUtils
.
copy
(
fileName
,
testDatabase
+
Constants
.
SUFFIX_PAGE_FILE
);
IOUtils
.
copyFiles
(
fileName
,
testDatabase
+
Constants
.
SUFFIX_PAGE_FILE
);
// avoid using the Engine class to avoid deadlocks
// avoid using the Engine class to avoid deadlocks
Properties
p
=
new
Properties
();
Properties
p
=
new
Properties
();
ConnectionInfo
ci
=
new
ConnectionInfo
(
"jdbc:h2:"
+
testDatabase
+
";FILE_LOCK=NO"
,
p
);
ConnectionInfo
ci
=
new
ConnectionInfo
(
"jdbc:h2:"
+
testDatabase
+
";FILE_LOCK=NO"
,
p
);
...
...
h2/src/main/org/h2/store/fs/FilePath.java
浏览文件 @
78a4f621
...
@@ -15,7 +15,6 @@ import java.util.List;
...
@@ -15,7 +15,6 @@ import java.util.List;
import
java.util.Map
;
import
java.util.Map
;
import
org.h2.util.MathUtils
;
import
org.h2.util.MathUtils
;
import
org.h2.util.New
;
import
org.h2.util.New
;
import
org.h2.util.StringUtils
;
/**
/**
* A path to a file. It similar to the Java 7 <code>java.nio.file.Path</code>,
* A path to a file. It similar to the Java 7 <code>java.nio.file.Path</code>,
...
@@ -25,7 +24,7 @@ import org.h2.util.StringUtils;
...
@@ -25,7 +24,7 @@ import org.h2.util.StringUtils;
*/
*/
public
abstract
class
FilePath
{
public
abstract
class
FilePath
{
private
static
final
FilePath
DEFAULT
=
new
FilePathDisk
()
;
private
static
FilePath
defaultProvider
;
private
static
Map
<
String
,
FilePath
>
providers
;
private
static
Map
<
String
,
FilePath
>
providers
;
...
@@ -51,25 +50,26 @@ public abstract class FilePath {
...
@@ -51,25 +50,26 @@ public abstract class FilePath {
public
static
FilePath
get
(
String
path
)
{
public
static
FilePath
get
(
String
path
)
{
path
=
path
.
replace
(
'\\'
,
'/'
);
path
=
path
.
replace
(
'\\'
,
'/'
);
int
index
=
path
.
indexOf
(
':'
);
int
index
=
path
.
indexOf
(
':'
);
registerDefaultProviders
();
if
(
index
<
2
)
{
if
(
index
<
2
)
{
// use the default provider if no prefix or
// use the default provider if no prefix or
// only a single character (drive name)
// only a single character (drive name)
return
DEFAULT
.
getPath
(
path
);
return
defaultProvider
.
getPath
(
path
);
}
}
String
scheme
=
path
.
substring
(
0
,
index
);
String
scheme
=
path
.
substring
(
0
,
index
);
registerDefaultProviders
();
FilePath
p
=
providers
.
get
(
scheme
);
FilePath
p
=
providers
.
get
(
scheme
);
if
(
p
==
null
)
{
if
(
p
==
null
)
{
// provider not found - use the default
// provider not found - use the default
p
=
DEFAULT
;
p
=
defaultProvider
;
}
}
return
p
.
getPath
(
path
);
return
p
.
getPath
(
path
);
}
}
private
static
void
registerDefaultProviders
()
{
private
static
void
registerDefaultProviders
()
{
if
(
providers
==
null
)
{
if
(
providers
==
null
||
defaultProvider
==
null
)
{
Map
<
String
,
FilePath
>
map
=
Collections
.
synchronizedMap
(
New
.<
String
,
FilePath
>
hashMap
());
Map
<
String
,
FilePath
>
map
=
Collections
.
synchronizedMap
(
New
.<
String
,
FilePath
>
hashMap
());
for
(
String
c
:
new
String
[]
{
for
(
String
c
:
new
String
[]
{
"org.h2.store.fs.FilePathDisk"
,
"org.h2.store.fs.FilePathMem"
,
"org.h2.store.fs.FilePathMem"
,
"org.h2.store.fs.FilePathMemLZF"
,
"org.h2.store.fs.FilePathMemLZF"
,
"org.h2.store.fs.FilePathSplit"
,
"org.h2.store.fs.FilePathSplit"
,
...
@@ -80,6 +80,9 @@ public abstract class FilePath {
...
@@ -80,6 +80,9 @@ public abstract class FilePath {
try
{
try
{
FilePath
p
=
(
FilePath
)
Class
.
forName
(
c
).
newInstance
();
FilePath
p
=
(
FilePath
)
Class
.
forName
(
c
).
newInstance
();
map
.
put
(
p
.
getScheme
(),
p
);
map
.
put
(
p
.
getScheme
(),
p
);
if
(
defaultProvider
==
null
)
{
defaultProvider
=
p
;
}
}
catch
(
Exception
e
)
{
}
catch
(
Exception
e
)
{
// ignore - the files may be excluded in purpose
// ignore - the files may be excluded in purpose
}
}
...
@@ -267,9 +270,7 @@ public abstract class FilePath {
...
@@ -267,9 +270,7 @@ public abstract class FilePath {
*/
*/
protected
static
synchronized
String
getNextTempFileNamePart
(
boolean
newRandom
)
{
protected
static
synchronized
String
getNextTempFileNamePart
(
boolean
newRandom
)
{
if
(
newRandom
||
tempRandom
==
null
)
{
if
(
newRandom
||
tempRandom
==
null
)
{
byte
[]
prefix
=
new
byte
[
8
];
tempRandom
=
MathUtils
.
randomInt
(
Integer
.
MAX_VALUE
)
+
"."
;
MathUtils
.
randomBytes
(
prefix
);
tempRandom
=
StringUtils
.
convertBytesToHex
(
prefix
)
+
"."
;
}
}
return
tempRandom
+
tempSequence
++;
return
tempRandom
+
tempSequence
++;
}
}
...
...
h2/src/main/org/h2/store/fs/FilePathCrypt.java
浏览文件 @
78a4f621
...
@@ -19,7 +19,6 @@ import org.h2.security.AES;
...
@@ -19,7 +19,6 @@ import org.h2.security.AES;
import
org.h2.security.BlockCipher
;
import
org.h2.security.BlockCipher
;
import
org.h2.security.SHA256
;
import
org.h2.security.SHA256
;
import
org.h2.util.MathUtils
;
import
org.h2.util.MathUtils
;
import
org.h2.util.StringUtils
;
/**
/**
* An encrypted file.
* An encrypted file.
...
@@ -38,7 +37,7 @@ public class FilePathCrypt extends FilePathWrapper {
...
@@ -38,7 +37,7 @@ public class FilePathCrypt extends FilePathWrapper {
public
FileChannel
open
(
String
mode
)
throws
IOException
{
public
FileChannel
open
(
String
mode
)
throws
IOException
{
String
[]
parsed
=
parse
(
name
);
String
[]
parsed
=
parse
(
name
);
FileChannel
file
=
FileUtils
.
open
(
parsed
[
1
],
mode
);
FileChannel
file
=
FileUtils
.
open
(
parsed
[
1
],
mode
);
byte
[]
passwordBytes
=
StringUtils
.
convertHexToBytes
(
parsed
[
0
]);
byte
[]
passwordBytes
=
DataUtils
.
utf8Encode
(
parsed
[
0
]);
return
new
FileCrypt
(
name
,
passwordBytes
,
file
);
return
new
FileCrypt
(
name
,
passwordBytes
,
file
);
}
}
...
@@ -93,6 +92,26 @@ public class FilePathCrypt extends FilePathWrapper {
...
@@ -93,6 +92,26 @@ public class FilePathCrypt extends FilePathWrapper {
return
new
String
[]
{
password
,
fileName
};
return
new
String
[]
{
password
,
fileName
};
}
}
/**
* Convert a char array to a byte array. The char array is cleared after
* use.
*
* @param passwordChars the password characters
* @return the byte array
*/
public
static
byte
[]
getPasswordBytes
(
char
[]
passwordChars
)
{
// using UTF-16
int
len
=
passwordChars
.
length
;
byte
[]
password
=
new
byte
[
len
*
2
];
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
char
c
=
passwordChars
[
i
];
password
[
i
+
i
]
=
(
byte
)
(
c
>>>
8
);
password
[
i
+
i
+
1
]
=
(
byte
)
c
;
}
Arrays
.
fill
(
passwordChars
,
(
char
)
0
);
return
password
;
}
/**
/**
* An encrypted file with a read cache.
* An encrypted file with a read cache.
*/
*/
...
...
h2/src/main/org/h2/store/fs/FilePathWrapper.java
浏览文件 @
78a4f621
...
@@ -11,7 +11,6 @@ import java.io.InputStream;
...
@@ -11,7 +11,6 @@ import java.io.InputStream;
import
java.io.OutputStream
;
import
java.io.OutputStream
;
import
java.nio.channels.FileChannel
;
import
java.nio.channels.FileChannel
;
import
java.util.List
;
import
java.util.List
;
import
org.h2.message.DbException
;
/**
/**
* The base class for wrapping / delegating file systems such as
* The base class for wrapping / delegating file systems such as
...
@@ -46,7 +45,7 @@ public abstract class FilePathWrapper extends FilePath {
...
@@ -46,7 +45,7 @@ public abstract class FilePathWrapper extends FilePath {
p
.
base
=
base
;
p
.
base
=
base
;
return
p
;
return
p
;
}
catch
(
Exception
e
)
{
}
catch
(
Exception
e
)
{
throw
DbException
.
convert
(
e
);
throw
new
IllegalArgumentException
(
"Path: "
+
path
,
e
);
}
}
}
}
...
...
h2/src/main/org/h2/store/fs/FileUtils.java
浏览文件 @
78a4f621
...
@@ -13,9 +13,6 @@ import java.io.OutputStream;
...
@@ -13,9 +13,6 @@ import java.io.OutputStream;
import
java.nio.ByteBuffer
;
import
java.nio.ByteBuffer
;
import
java.nio.channels.FileChannel
;
import
java.nio.channels.FileChannel
;
import
java.util.List
;
import
java.util.List
;
import
org.h2.constant.ErrorCode
;
import
org.h2.message.DbException
;
import
org.h2.util.IOUtils
;
import
org.h2.util.New
;
import
org.h2.util.New
;
/**
/**
...
@@ -290,9 +287,8 @@ public class FileUtils {
...
@@ -290,9 +287,8 @@ public class FileUtils {
if
(
dir
!=
null
)
{
if
(
dir
!=
null
)
{
if
(
exists
(
dir
))
{
if
(
exists
(
dir
))
{
if
(!
isDirectory
(
dir
))
{
if
(!
isDirectory
(
dir
))
{
DbException
.
get
(
ErrorCode
.
FILE_CREATION_FAILED_1
,
// this will fail
"Could not create directory, "
+
createDirectory
(
dir
);
"because a file with the same name already exists: "
+
dir
);
}
}
}
else
{
}
else
{
String
parent
=
getParent
(
dir
);
String
parent
=
getParent
(
dir
);
...
@@ -302,18 +298,6 @@ public class FileUtils {
...
@@ -302,18 +298,6 @@ public class FileUtils {
}
}
}
}
/**
* Copy a file from one directory to another, or to another file.
*
* @param original the original file name
* @param copy the file name of the copy
*/
public
static
void
copy
(
String
original
,
String
copy
)
throws
IOException
{
InputStream
in
=
newInputStream
(
original
);
OutputStream
out
=
newOutputStream
(
copy
,
false
);
IOUtils
.
copyAndClose
(
in
,
out
);
}
/**
/**
* Try to delete a file (ignore errors).
* Try to delete a file (ignore errors).
*
*
...
...
h2/src/main/org/h2/tools/CompressTool.java
浏览文件 @
78a4f621
...
@@ -26,7 +26,7 @@ import org.h2.compress.LZFOutputStream;
...
@@ -26,7 +26,7 @@ import org.h2.compress.LZFOutputStream;
import
org.h2.constant.ErrorCode
;
import
org.h2.constant.ErrorCode
;
import
org.h2.engine.Constants
;
import
org.h2.engine.Constants
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.
util.
Utils
;
import
org.h2.
mvstore.Data
Utils
;
import
org.h2.util.StringUtils
;
import
org.h2.util.StringUtils
;
/**
/**
...
@@ -43,10 +43,10 @@ public class CompressTool {
...
@@ -43,10 +43,10 @@ public class CompressTool {
private
byte
[]
getBuffer
(
int
min
)
{
private
byte
[]
getBuffer
(
int
min
)
{
if
(
min
>
MAX_BUFFER_SIZE
)
{
if
(
min
>
MAX_BUFFER_SIZE
)
{
return
Utils
.
newBytes
(
min
);
return
Data
Utils
.
newBytes
(
min
);
}
}
if
(
cachedBuffer
==
null
||
cachedBuffer
.
length
<
min
)
{
if
(
cachedBuffer
==
null
||
cachedBuffer
.
length
<
min
)
{
cachedBuffer
=
Utils
.
newBytes
(
min
);
cachedBuffer
=
Data
Utils
.
newBytes
(
min
);
}
}
return
cachedBuffer
;
return
cachedBuffer
;
}
}
...
@@ -78,7 +78,7 @@ public class CompressTool {
...
@@ -78,7 +78,7 @@ public class CompressTool {
Compressor
compress
=
getCompressor
(
algorithm
);
Compressor
compress
=
getCompressor
(
algorithm
);
byte
[]
buff
=
getBuffer
((
len
<
100
?
len
+
100
:
len
)
*
2
);
byte
[]
buff
=
getBuffer
((
len
<
100
?
len
+
100
:
len
)
*
2
);
int
newLen
=
compress
(
in
,
in
.
length
,
compress
,
buff
);
int
newLen
=
compress
(
in
,
in
.
length
,
compress
,
buff
);
byte
[]
out
=
Utils
.
newBytes
(
newLen
);
byte
[]
out
=
Data
Utils
.
newBytes
(
newLen
);
System
.
arraycopy
(
buff
,
0
,
out
,
0
,
newLen
);
System
.
arraycopy
(
buff
,
0
,
out
,
0
,
newLen
);
return
out
;
return
out
;
}
}
...
@@ -108,7 +108,7 @@ public class CompressTool {
...
@@ -108,7 +108,7 @@ public class CompressTool {
try
{
try
{
int
len
=
readVariableInt
(
in
,
1
);
int
len
=
readVariableInt
(
in
,
1
);
int
start
=
1
+
getVariableIntLength
(
len
);
int
start
=
1
+
getVariableIntLength
(
len
);
byte
[]
buff
=
Utils
.
newBytes
(
len
);
byte
[]
buff
=
Data
Utils
.
newBytes
(
len
);
compress
.
expand
(
in
,
start
,
in
.
length
-
start
,
buff
,
0
,
len
);
compress
.
expand
(
in
,
start
,
in
.
length
-
start
,
buff
,
0
,
len
);
return
buff
;
return
buff
;
}
catch
(
Exception
e
)
{
}
catch
(
Exception
e
)
{
...
...
h2/src/main/org/h2/util/IOUtils.java
浏览文件 @
78a4f621
...
@@ -24,6 +24,7 @@ import java.io.Writer;
...
@@ -24,6 +24,7 @@ import java.io.Writer;
import
org.h2.constant.SysProperties
;
import
org.h2.constant.SysProperties
;
import
org.h2.engine.Constants
;
import
org.h2.engine.Constants
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.store.fs.FileUtils
;
/**
/**
* This utility class contains input/output functions.
* This utility class contains input/output functions.
...
@@ -477,4 +478,16 @@ public class IOUtils {
...
@@ -477,4 +478,16 @@ public class IOUtils {
return
new
ByteArrayInputStream
(
StringUtils
.
utf8Encode
(
s
));
return
new
ByteArrayInputStream
(
StringUtils
.
utf8Encode
(
s
));
}
}
/**
* Copy a file from one directory to another, or to another file.
*
* @param original the original file name
* @param copy the file name of the copy
*/
public
static
void
copyFiles
(
String
original
,
String
copy
)
throws
IOException
{
InputStream
in
=
FileUtils
.
newInputStream
(
original
);
OutputStream
out
=
FileUtils
.
newOutputStream
(
copy
,
false
);
copyAndClose
(
in
,
out
);
}
}
}
h2/src/main/org/h2/util/MathUtils.java
浏览文件 @
78a4f621
...
@@ -10,10 +10,8 @@ import java.io.ByteArrayOutputStream;
...
@@ -10,10 +10,8 @@ import java.io.ByteArrayOutputStream;
import
java.io.DataOutputStream
;
import
java.io.DataOutputStream
;
import
java.io.IOException
;
import
java.io.IOException
;
import
java.lang.reflect.Method
;
import
java.lang.reflect.Method
;
import
java.math.BigDecimal
;
import
java.security.SecureRandom
;
import
java.security.SecureRandom
;
import
java.util.Random
;
import
java.util.Random
;
import
org.h2.message.DbException
;
/**
/**
* This is a utility class with mathematical helper functions.
* This is a utility class with mathematical helper functions.
...
@@ -32,14 +30,37 @@ public class MathUtils {
...
@@ -32,14 +30,37 @@ public class MathUtils {
private
static
final
Random
RANDOM
=
new
Random
();
private
static
final
Random
RANDOM
=
new
Random
();
private
MathUtils
()
{
// utility class
}
/**
/**
* The maximum scale of a BigDecimal value.
* Round the value up to the next block size. The block size must be a power
* of two. As an example, using the block size of 8, the following rounding
* operations are done: 0 stays 0; values 1..8 results in 8, 9..16 results
* in 16, and so on.
*
* @param x the value to be rounded
* @param blockSizePowerOf2 the block size
* @return the rounded value
*/
*/
private
static
final
int
BIG_DECIMAL_SCALE_MAX
=
100000
;
public
static
int
roundUpInt
(
int
x
,
int
blockSizePowerOf2
)
{
return
(
x
+
blockSizePowerOf2
-
1
)
&
(-
blockSizePowerOf2
);
}
private
MathUtils
()
{
/**
// utility class
* Round the value up to the next block size. The block size must be a power
* of two. As an example, using the block size of 8, the following rounding
* operations are done: 0 stays 0; values 1..8 results in 8, 9..16 results
* in 16, and so on.
*
* @param x the value to be rounded
* @param blockSizePowerOf2 the block size
* @return the rounded value
*/
public
static
long
roundUpLong
(
long
x
,
long
blockSizePowerOf2
)
{
return
(
x
+
blockSizePowerOf2
-
1
)
&
(-
blockSizePowerOf2
);
}
}
private
static
synchronized
SecureRandom
getSecureRandom
()
{
private
static
synchronized
SecureRandom
getSecureRandom
()
{
...
@@ -198,34 +219,6 @@ public class MathUtils {
...
@@ -198,34 +219,6 @@ public class MathUtils {
}
}
}
}
/**
* Round the value up to the next block size. The block size must be a power
* of two. As an example, using the block size of 8, the following rounding
* operations are done: 0 stays 0; values 1..8 results in 8, 9..16 results
* in 16, and so on.
*
* @param x the value to be rounded
* @param blockSizePowerOf2 the block size
* @return the rounded value
*/
public
static
int
roundUpInt
(
int
x
,
int
blockSizePowerOf2
)
{
return
(
x
+
blockSizePowerOf2
-
1
)
&
(-
blockSizePowerOf2
);
}
/**
* Round the value up to the next block size. The block size must be a power
* of two. As an example, using the block size of 8, the following rounding
* operations are done: 0 stays 0; values 1..8 results in 8, 9..16 results
* in 16, and so on.
*
* @param x the value to be rounded
* @param blockSizePowerOf2 the block size
* @return the rounded value
*/
public
static
long
roundUpLong
(
long
x
,
long
blockSizePowerOf2
)
{
return
(
x
+
blockSizePowerOf2
-
1
)
&
(-
blockSizePowerOf2
);
}
/**
/**
* Get the value that is equal or higher than this value, and that is a
* Get the value that is equal or higher than this value, and that is a
* power of two.
* power of two.
...
@@ -241,20 +234,6 @@ public class MathUtils {
...
@@ -241,20 +234,6 @@ public class MathUtils {
return
(
int
)
i
;
return
(
int
)
i
;
}
}
/**
* Set the scale of a BigDecimal value.
*
* @param bd the BigDecimal value
* @param scale the new scale
* @return the scaled value
*/
public
static
BigDecimal
setScale
(
BigDecimal
bd
,
int
scale
)
{
if
(
scale
>
BIG_DECIMAL_SCALE_MAX
||
scale
<
-
BIG_DECIMAL_SCALE_MAX
)
{
throw
DbException
.
getInvalidValueException
(
"scale"
,
scale
);
}
return
bd
.
setScale
(
scale
,
BigDecimal
.
ROUND_HALF_UP
);
}
/**
/**
* Convert a long value to an int value. Values larger than the biggest int
* Convert a long value to an int value. Values larger than the biggest int
* value is converted to the biggest int value, and values smaller than the
* value is converted to the biggest int value, and values smaller than the
...
...
h2/src/main/org/h2/util/Utils.java
浏览文件 @
78a4f621
...
@@ -407,32 +407,6 @@ public class Utils {
...
@@ -407,32 +407,6 @@ public class Utils {
}
}
}
}
/**
* Create an array of bytes with the given size. If this is not possible
* because not enough memory is available, an OutOfMemoryError with the
* requested size in the message is thrown.
* <p>
* This method should be used if the size of the array is user defined, or
* stored in a file, so wrong size data can be distinguished from regular
* out-of-memory.
*
* @param len the number of bytes requested
* @return the byte array
* @throws OutOfMemoryError
*/
public
static
byte
[]
newBytes
(
int
len
)
{
if
(
len
==
0
)
{
return
EMPTY_BYTES
;
}
try
{
return
new
byte
[
len
];
}
catch
(
OutOfMemoryError
e
)
{
Error
e2
=
new
OutOfMemoryError
(
"Requested memory: "
+
len
);
e2
.
initCause
(
e
);
throw
e2
;
}
}
/**
/**
* Create an int array with the given size.
* Create an int array with the given size.
*
*
...
...
h2/src/main/org/h2/value/Transfer.java
浏览文件 @
78a4f621
...
@@ -26,6 +26,7 @@ import org.h2.engine.Constants;
...
@@ -26,6 +26,7 @@ import org.h2.engine.Constants;
import
org.h2.engine.SessionInterface
;
import
org.h2.engine.SessionInterface
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.message.TraceSystem
;
import
org.h2.message.TraceSystem
;
import
org.h2.mvstore.DataUtils
;
import
org.h2.security.SHA256
;
import
org.h2.security.SHA256
;
import
org.h2.store.Data
;
import
org.h2.store.Data
;
import
org.h2.store.DataReader
;
import
org.h2.store.DataReader
;
...
@@ -288,7 +289,7 @@ public class Transfer {
...
@@ -288,7 +289,7 @@ public class Transfer {
if
(
len
==
-
1
)
{
if
(
len
==
-
1
)
{
return
null
;
return
null
;
}
}
byte
[]
b
=
Utils
.
newBytes
(
len
);
byte
[]
b
=
Data
Utils
.
newBytes
(
len
);
in
.
readFully
(
b
);
in
.
readFully
(
b
);
return
b
;
return
b
;
}
}
...
...
h2/src/main/org/h2/value/ValueDecimal.java
浏览文件 @
78a4f621
...
@@ -45,6 +45,11 @@ public class ValueDecimal extends Value {
...
@@ -45,6 +45,11 @@ public class ValueDecimal extends Value {
private
static
final
int
DIVIDE_SCALE_ADD
=
25
;
private
static
final
int
DIVIDE_SCALE_ADD
=
25
;
/**
* The maximum scale of a BigDecimal value.
*/
private
static
final
int
BIG_DECIMAL_SCALE_MAX
=
100000
;
private
final
BigDecimal
value
;
private
final
BigDecimal
value
;
private
String
valueString
;
private
String
valueString
;
private
int
precision
;
private
int
precision
;
...
@@ -183,7 +188,7 @@ public class ValueDecimal extends Value {
...
@@ -183,7 +188,7 @@ public class ValueDecimal extends Value {
return
this
;
return
this
;
}
}
}
}
BigDecimal
bd
=
MathUtils
.
setScale
(
value
,
targetScale
);
BigDecimal
bd
=
ValueDecimal
.
setScale
(
value
,
targetScale
);
return
ValueDecimal
.
get
(
bd
);
return
ValueDecimal
.
get
(
bd
);
}
}
...
@@ -229,4 +234,18 @@ public class ValueDecimal extends Value {
...
@@ -229,4 +234,18 @@ public class ValueDecimal extends Value {
return
value
.
precision
()
+
120
;
return
value
.
precision
()
+
120
;
}
}
/**
* Set the scale of a BigDecimal value.
*
* @param bd the BigDecimal value
* @param scale the new scale
* @return the scaled value
*/
public
static
BigDecimal
setScale
(
BigDecimal
bd
,
int
scale
)
{
if
(
scale
>
BIG_DECIMAL_SCALE_MAX
||
scale
<
-
BIG_DECIMAL_SCALE_MAX
)
{
throw
DbException
.
getInvalidValueException
(
"scale"
,
scale
);
}
return
bd
.
setScale
(
scale
,
BigDecimal
.
ROUND_HALF_UP
);
}
}
}
h2/src/main/org/h2/value/ValueLob.java
浏览文件 @
78a4f621
...
@@ -17,6 +17,7 @@ import java.sql.SQLException;
...
@@ -17,6 +17,7 @@ import java.sql.SQLException;
import
org.h2.constant.SysProperties
;
import
org.h2.constant.SysProperties
;
import
org.h2.engine.Constants
;
import
org.h2.engine.Constants
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.mvstore.DataUtils
;
import
org.h2.store.DataHandler
;
import
org.h2.store.DataHandler
;
import
org.h2.store.FileStore
;
import
org.h2.store.FileStore
;
import
org.h2.store.FileStoreInputStream
;
import
org.h2.store.FileStoreInputStream
;
...
@@ -360,11 +361,11 @@ public class ValueLob extends Value {
...
@@ -360,11 +361,11 @@ public class ValueLob extends Value {
buff
=
IOUtils
.
readBytesAndClose
(
in
,
-
1
);
buff
=
IOUtils
.
readBytesAndClose
(
in
,
-
1
);
len
=
buff
.
length
;
len
=
buff
.
length
;
}
else
{
}
else
{
buff
=
Utils
.
newBytes
(
len
);
buff
=
Data
Utils
.
newBytes
(
len
);
len
=
IOUtils
.
readFully
(
in
,
buff
,
0
,
len
);
len
=
IOUtils
.
readFully
(
in
,
buff
,
0
,
len
);
}
}
if
(
len
<=
handler
.
getMaxLengthInplaceLob
())
{
if
(
len
<=
handler
.
getMaxLengthInplaceLob
())
{
byte
[]
small
=
Utils
.
newBytes
(
len
);
byte
[]
small
=
Data
Utils
.
newBytes
(
len
);
System
.
arraycopy
(
buff
,
0
,
small
,
0
,
len
);
System
.
arraycopy
(
buff
,
0
,
small
,
0
,
len
);
return
ValueLob
.
createSmallLob
(
Value
.
BLOB
,
small
);
return
ValueLob
.
createSmallLob
(
Value
.
BLOB
,
small
);
}
}
...
@@ -696,7 +697,7 @@ public class ValueLob extends Value {
...
@@ -696,7 +697,7 @@ public class ValueLob extends Value {
int
len
=
getBufferSize
(
h
,
compress
,
Long
.
MAX_VALUE
);
int
len
=
getBufferSize
(
h
,
compress
,
Long
.
MAX_VALUE
);
int
tabId
=
tableId
;
int
tabId
=
tableId
;
if
(
type
==
Value
.
BLOB
)
{
if
(
type
==
Value
.
BLOB
)
{
createFromStream
(
Utils
.
newBytes
(
len
),
0
,
getInputStream
(),
Long
.
MAX_VALUE
,
h
);
createFromStream
(
Data
Utils
.
newBytes
(
len
),
0
,
getInputStream
(),
Long
.
MAX_VALUE
,
h
);
}
else
{
}
else
{
createFromReader
(
new
char
[
len
],
0
,
getReader
(),
Long
.
MAX_VALUE
,
h
);
createFromReader
(
new
char
[
len
],
0
,
getReader
(),
Long
.
MAX_VALUE
,
h
);
}
}
...
@@ -757,7 +758,7 @@ public class ValueLob extends Value {
...
@@ -757,7 +758,7 @@ public class ValueLob extends Value {
private
static
void
copyFileTo
(
DataHandler
h
,
String
sourceFileName
,
String
targetFileName
)
{
private
static
void
copyFileTo
(
DataHandler
h
,
String
sourceFileName
,
String
targetFileName
)
{
synchronized
(
h
.
getLobSyncObject
())
{
synchronized
(
h
.
getLobSyncObject
())
{
try
{
try
{
FileUtils
.
copy
(
sourceFileName
,
targetFileName
);
IOUtils
.
copyFiles
(
sourceFileName
,
targetFileName
);
}
catch
(
IOException
e
)
{
}
catch
(
IOException
e
)
{
throw
DbException
.
convertIOException
(
e
,
null
);
throw
DbException
.
convertIOException
(
e
,
null
);
}
}
...
...
h2/src/main/org/h2/value/ValueLobDb.java
浏览文件 @
78a4f621
...
@@ -16,6 +16,7 @@ import java.sql.SQLException;
...
@@ -16,6 +16,7 @@ import java.sql.SQLException;
import
org.h2.constant.SysProperties
;
import
org.h2.constant.SysProperties
;
import
org.h2.engine.Constants
;
import
org.h2.engine.Constants
;
import
org.h2.message.DbException
;
import
org.h2.message.DbException
;
import
org.h2.mvstore.DataUtils
;
import
org.h2.store.DataHandler
;
import
org.h2.store.DataHandler
;
import
org.h2.store.FileStore
;
import
org.h2.store.FileStore
;
import
org.h2.store.FileStoreInputStream
;
import
org.h2.store.FileStoreInputStream
;
...
@@ -438,11 +439,11 @@ public class ValueLobDb extends Value implements Value.ValueClob, Value.ValueBlo
...
@@ -438,11 +439,11 @@ public class ValueLobDb extends Value implements Value.ValueClob, Value.ValueBlo
buff
=
IOUtils
.
readBytesAndClose
(
in
,
-
1
);
buff
=
IOUtils
.
readBytesAndClose
(
in
,
-
1
);
len
=
buff
.
length
;
len
=
buff
.
length
;
}
else
{
}
else
{
buff
=
Utils
.
newBytes
(
len
);
buff
=
Data
Utils
.
newBytes
(
len
);
len
=
IOUtils
.
readFully
(
in
,
buff
,
0
,
len
);
len
=
IOUtils
.
readFully
(
in
,
buff
,
0
,
len
);
}
}
if
(
len
<=
handler
.
getMaxLengthInplaceLob
())
{
if
(
len
<=
handler
.
getMaxLengthInplaceLob
())
{
byte
[]
small
=
Utils
.
newBytes
(
len
);
byte
[]
small
=
Data
Utils
.
newBytes
(
len
);
System
.
arraycopy
(
buff
,
0
,
small
,
0
,
len
);
System
.
arraycopy
(
buff
,
0
,
small
,
0
,
len
);
return
ValueLobDb
.
createSmallLob
(
Value
.
BLOB
,
small
,
small
.
length
);
return
ValueLobDb
.
createSmallLob
(
Value
.
BLOB
,
small
,
small
.
length
);
}
}
...
...
h2/src/main/org/h2/value/ValueTimestamp.java
浏览文件 @
78a4f621
...
@@ -211,7 +211,7 @@ public class ValueTimestamp extends Value {
...
@@ -211,7 +211,7 @@ public class ValueTimestamp extends Value {
long
n
=
nanos
;
long
n
=
nanos
;
BigDecimal
bd
=
BigDecimal
.
valueOf
(
n
);
BigDecimal
bd
=
BigDecimal
.
valueOf
(
n
);
bd
=
bd
.
movePointLeft
(
9
);
bd
=
bd
.
movePointLeft
(
9
);
bd
=
MathUtils
.
setScale
(
bd
,
targetScale
);
bd
=
ValueDecimal
.
setScale
(
bd
,
targetScale
);
bd
=
bd
.
movePointRight
(
9
);
bd
=
bd
.
movePointRight
(
9
);
long
n2
=
bd
.
longValue
();
long
n2
=
bd
.
longValue
();
if
(
n2
==
n
)
{
if
(
n2
==
n
)
{
...
...
h2/src/test/org/h2/test/store/RowDataType.java
浏览文件 @
78a4f621
...
@@ -46,16 +46,6 @@ public class RowDataType implements DataType {
...
@@ -46,16 +46,6 @@ public class RowDataType implements DataType {
return
0
;
return
0
;
}
}
public
int
getMaxLength
(
Object
obj
)
{
Object
[]
x
=
(
Object
[])
obj
;
int
len
=
x
.
length
;
int
result
=
DataUtils
.
MAX_VAR_INT_LEN
;
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
result
+=
types
[
i
].
getMaxLength
(
x
[
i
]);
}
return
result
;
}
public
int
getMemory
(
Object
obj
)
{
public
int
getMemory
(
Object
obj
)
{
Object
[]
x
=
(
Object
[])
obj
;
Object
[]
x
=
(
Object
[])
obj
;
int
len
=
x
.
length
;
int
len
=
x
.
length
;
...
@@ -75,13 +65,15 @@ public class RowDataType implements DataType {
...
@@ -75,13 +65,15 @@ public class RowDataType implements DataType {
return
x
;
return
x
;
}
}
public
void
write
(
ByteBuffer
buff
,
Object
obj
)
{
public
ByteBuffer
write
(
ByteBuffer
buff
,
Object
obj
)
{
Object
[]
x
=
(
Object
[])
obj
;
Object
[]
x
=
(
Object
[])
obj
;
int
len
=
x
.
length
;
int
len
=
x
.
length
;
DataUtils
.
writeVarInt
(
buff
,
len
);
DataUtils
.
writeVarInt
(
buff
,
len
);
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
for
(
int
i
=
0
;
i
<
len
;
i
++)
{
types
[
i
].
write
(
buff
,
x
[
i
]);
buff
=
DataUtils
.
ensureCapacity
(
buff
,
0
);
buff
=
types
[
i
].
write
(
buff
,
x
[
i
]);
}
}
return
buff
;
}
}
}
}
h2/src/test/org/h2/test/store/TestConcurrent.java
浏览文件 @
78a4f621
...
@@ -37,6 +37,8 @@ public class TestConcurrent extends TestMVStore {
...
@@ -37,6 +37,8 @@ public class TestConcurrent extends TestMVStore {
public
void
test
()
throws
Exception
{
public
void
test
()
throws
Exception
{
FileUtils
.
deleteRecursive
(
getBaseDir
(),
true
);
FileUtils
.
deleteRecursive
(
getBaseDir
(),
true
);
FileUtils
.
createDirectories
(
getBaseDir
());
testConcurrentOnlineBackup
();
testConcurrentOnlineBackup
();
testConcurrentMap
();
testConcurrentMap
();
testConcurrentIterate
();
testConcurrentIterate
();
...
...
h2/src/test/org/h2/test/store/TestMVRTree.java
浏览文件 @
78a4f621
...
@@ -43,6 +43,9 @@ public class TestMVRTree extends TestMVStore {
...
@@ -43,6 +43,9 @@ public class TestMVRTree extends TestMVStore {
}
}
public
void
test
()
{
public
void
test
()
{
FileUtils
.
deleteRecursive
(
getBaseDir
(),
true
);
FileUtils
.
createDirectories
(
getBaseDir
());
testExample
();
testExample
();
testMany
();
testMany
();
testSimple
();
testSimple
();
...
...
h2/src/test/org/h2/test/store/TestMVStore.java
浏览文件 @
78a4f621
...
@@ -40,6 +40,8 @@ public class TestMVStore extends TestBase {
...
@@ -40,6 +40,8 @@ public class TestMVStore extends TestBase {
public
void
test
()
throws
Exception
{
public
void
test
()
throws
Exception
{
FileUtils
.
deleteRecursive
(
getBaseDir
(),
true
);
FileUtils
.
deleteRecursive
(
getBaseDir
(),
true
);
FileUtils
.
createDirectories
(
getBaseDir
());
testEncryptedFile
();
testEncryptedFile
();
testFileFormatChange
();
testFileFormatChange
();
testRecreateMap
();
testRecreateMap
();
...
...
h2/src/test/org/h2/test/store/TestObjectDataType.java
浏览文件 @
78a4f621
...
@@ -127,14 +127,14 @@ public class TestObjectDataType extends TestBase {
...
@@ -127,14 +127,14 @@ public class TestObjectDataType extends TestBase {
assertTrue
(
ot
.
getMemory
(
x
)
>=
0
);
assertTrue
(
ot
.
getMemory
(
x
)
>=
0
);
ot
.
getMemory
(
last
);
ot
.
getMemory
(
last
);
assertTrue
(
ot
.
getM
axLength
(
x
)
>=
1
);
assertTrue
(
ot
.
getM
emory
(
x
)
>=
0
);
ot
.
getMemory
(
last
);
ot
.
getMemory
(
last
);
assertEquals
(
0
,
ot
.
compare
(
x
,
x
));
assertEquals
(
0
,
ot
.
compare
(
x
,
x
));
ByteBuffer
buff
=
ByteBuffer
.
allocate
(
ot
.
getMaxLength
(
x
)
+
1
);
ByteBuffer
buff
=
ByteBuffer
.
allocate
(
1024
);
ot
.
getMemory
(
last
);
ot
.
getMemory
(
last
);
ot
.
write
(
buff
,
x
);
buff
=
ot
.
write
(
buff
,
x
);
buff
.
put
((
byte
)
123
);
buff
.
put
((
byte
)
123
);
buff
.
flip
();
buff
.
flip
();
...
...
h2/src/test/org/h2/test/store/TestStreamStore.java
浏览文件 @
78a4f621
...
@@ -40,6 +40,9 @@ public class TestStreamStore extends TestBase {
...
@@ -40,6 +40,9 @@ public class TestStreamStore extends TestBase {
@Override
@Override
public
void
test
()
throws
IOException
{
public
void
test
()
throws
IOException
{
FileUtils
.
deleteRecursive
(
getBaseDir
(),
true
);
FileUtils
.
createDirectories
(
getBaseDir
());
testVeryLarge
();
testVeryLarge
();
testDetectIllegalId
();
testDetectIllegalId
();
testTreeStructure
();
testTreeStructure
();
...
...
h2/src/test/org/h2/test/unit/TestClearReferences.java
浏览文件 @
78a4f621
...
@@ -29,6 +29,7 @@ public class TestClearReferences extends TestBase {
...
@@ -29,6 +29,7 @@ public class TestClearReferences extends TestBase {
"org.h2.engine.SessionRemote.sessionFactory"
,
"org.h2.engine.SessionRemote.sessionFactory"
,
"org.h2.jdbcx.JdbcDataSourceFactory.cachedTraceSystem"
,
"org.h2.jdbcx.JdbcDataSourceFactory.cachedTraceSystem"
,
"org.h2.store.RecoverTester.instance"
,
"org.h2.store.RecoverTester.instance"
,
"org.h2.store.fs.FilePath.defaultProvider"
,
"org.h2.store.fs.FilePath.providers"
,
"org.h2.store.fs.FilePath.providers"
,
"org.h2.store.fs.FilePath.tempRandom"
,
"org.h2.store.fs.FilePath.tempRandom"
,
"org.h2.tools.CompressTool.cachedBuffer"
,
"org.h2.tools.CompressTool.cachedBuffer"
,
...
...
h2/src/test/org/h2/test/unit/TestFileSystem.java
浏览文件 @
78a4f621
...
@@ -31,6 +31,7 @@ import org.h2.test.utils.AssertThrows;
...
@@ -31,6 +31,7 @@ import org.h2.test.utils.AssertThrows;
import
org.h2.test.utils.FilePathDebug
;
import
org.h2.test.utils.FilePathDebug
;
import
org.h2.tools.Backup
;
import
org.h2.tools.Backup
;
import
org.h2.tools.DeleteDbFiles
;
import
org.h2.tools.DeleteDbFiles
;
import
org.h2.util.IOUtils
;
/**
/**
* Tests various file system.
* Tests various file system.
...
@@ -425,7 +426,7 @@ public class TestFileSystem extends TestBase {
...
@@ -425,7 +426,7 @@ public class TestFileSystem extends TestBase {
List
<
String
>
list
=
FileUtils
.
newDirectoryStream
(
fsBase
);
List
<
String
>
list
=
FileUtils
.
newDirectoryStream
(
fsBase
);
assertEquals
(
1
,
list
.
size
());
assertEquals
(
1
,
list
.
size
());
assertTrue
(
list
.
get
(
0
).
endsWith
(
"test"
));
assertTrue
(
list
.
get
(
0
).
endsWith
(
"test"
));
FileUtils
.
copy
(
fsBase
+
"/test"
,
fsBase
+
"/test3"
);
IOUtils
.
copyFiles
(
fsBase
+
"/test"
,
fsBase
+
"/test3"
);
FileUtils
.
moveTo
(
fsBase
+
"/test3"
,
fsBase
+
"/test2"
);
FileUtils
.
moveTo
(
fsBase
+
"/test3"
,
fsBase
+
"/test2"
);
FileUtils
.
moveTo
(
fsBase
+
"/test2"
,
fsBase
+
"/test2"
);
FileUtils
.
moveTo
(
fsBase
+
"/test2"
,
fsBase
+
"/test2"
);
assertTrue
(!
FileUtils
.
exists
(
fsBase
+
"/test3"
));
assertTrue
(!
FileUtils
.
exists
(
fsBase
+
"/test3"
));
...
...
h2/src/test/org/h2/test/unit/TestReopen.java
浏览文件 @
78a4f621
...
@@ -20,6 +20,7 @@ import org.h2.store.fs.FileUtils;
...
@@ -20,6 +20,7 @@ import org.h2.store.fs.FileUtils;
import
org.h2.store.fs.Recorder
;
import
org.h2.store.fs.Recorder
;
import
org.h2.test.TestBase
;
import
org.h2.test.TestBase
;
import
org.h2.tools.Recover
;
import
org.h2.tools.Recover
;
import
org.h2.util.IOUtils
;
import
org.h2.util.New
;
import
org.h2.util.New
;
import
org.h2.util.Profiler
;
import
org.h2.util.Profiler
;
import
org.h2.util.Utils
;
import
org.h2.util.Utils
;
...
@@ -95,7 +96,7 @@ public class TestReopen extends TestBase implements Recorder {
...
@@ -95,7 +96,7 @@ public class TestReopen extends TestBase implements Recorder {
System
.
out
.
println
(
"+ write #"
+
writeCount
+
" verify #"
+
verifyCount
);
System
.
out
.
println
(
"+ write #"
+
writeCount
+
" verify #"
+
verifyCount
);
try
{
try
{
FileUtils
.
copy
(
fileName
,
testDatabase
+
Constants
.
SUFFIX_PAGE_FILE
);
IOUtils
.
copyFiles
(
fileName
,
testDatabase
+
Constants
.
SUFFIX_PAGE_FILE
);
verifyCount
++;
verifyCount
++;
// avoid using the Engine class to avoid deadlocks
// avoid using the Engine class to avoid deadlocks
Properties
p
=
new
Properties
();
Properties
p
=
new
Properties
();
...
@@ -142,7 +143,7 @@ public class TestReopen extends TestBase implements Recorder {
...
@@ -142,7 +143,7 @@ public class TestReopen extends TestBase implements Recorder {
}
}
testDatabase
+=
"X"
;
testDatabase
+=
"X"
;
try
{
try
{
FileUtils
.
copy
(
fileName
,
testDatabase
+
Constants
.
SUFFIX_PAGE_FILE
);
IOUtils
.
copyFiles
(
fileName
,
testDatabase
+
Constants
.
SUFFIX_PAGE_FILE
);
// avoid using the Engine class to avoid deadlocks
// avoid using the Engine class to avoid deadlocks
Properties
p
=
new
Properties
();
Properties
p
=
new
Properties
();
ConnectionInfo
ci
=
new
ConnectionInfo
(
"jdbc:h2:"
+
testDatabase
+
";FILE_LOCK=NO"
,
p
);
ConnectionInfo
ci
=
new
ConnectionInfo
(
"jdbc:h2:"
+
testDatabase
+
";FILE_LOCK=NO"
,
p
);
...
...
h2/src/tools/org/h2/dev/fs/FileShell.java
浏览文件 @
78a4f621
...
@@ -200,7 +200,7 @@ public class FileShell extends Tool {
...
@@ -200,7 +200,7 @@ public class FileShell extends Tool {
String
source
=
getFile
(
list
[
i
++]);
String
source
=
getFile
(
list
[
i
++]);
String
target
=
getFile
(
list
[
i
++]);
String
target
=
getFile
(
list
[
i
++]);
end
(
list
,
i
);
end
(
list
,
i
);
FileUtils
.
copy
(
source
,
target
);
IOUtils
.
copyFiles
(
source
,
target
);
}
else
if
(
"head"
.
equals
(
c
))
{
}
else
if
(
"head"
.
equals
(
c
))
{
String
file
=
getFile
(
list
[
i
++]);
String
file
=
getFile
(
list
[
i
++]);
end
(
list
,
i
);
end
(
list
,
i
);
...
...
编写
预览
Markdown
格式
0%
重试
或
添加新文件
添加附件
取消
您添加了
0
人
到此讨论。请谨慎行事。
请先完成此评论的编辑!
取消
请
注册
或者
登录
后发表评论