Skip to content
GitLab
Explore
Sign in
Primary navigation
Search or go to…
Project
I
illuna-minetest
Manage
Activity
Members
Labels
Plan
Issues
Issue boards
Milestones
Code
Merge requests
Repository
Branches
Commits
Tags
Repository graph
Compare revisions
Build
Pipelines
Jobs
Pipeline schedules
Artifacts
Deploy
Releases
Model registry
Operate
Environments
Monitor
Incidents
Service Desk
Analyze
Value stream analytics
Contributor analytics
CI/CD analytics
Repository analytics
Model experiments
Help
Help
Support
GitLab documentation
Compare GitLab plans
Community forum
Contribute to GitLab
Provide feedback
Keyboard shortcuts
?
Snippets
Groups
Projects
Show more breadcrumbs
Illuna-Minetest
illuna-minetest
Commits
6f07f79c
Commit
6f07f79c
authored
9 years ago
by
kwolekr
Browse files
Options
Downloads
Patches
Plain Diff
Add more robust error checking to deSerialize*String routines
Add serializeHexString() Clean up util/serialize.cpp
parent
b411b6f3
No related branches found
No related tags found
No related merge requests found
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
src/unittest/test_serialization.cpp
+108
-17
108 additions, 17 deletions
src/unittest/test_serialization.cpp
src/util/serialize.cpp
+178
-97
178 additions, 97 deletions
src/util/serialize.cpp
src/util/serialize.h
+6
-0
6 additions, 0 deletions
src/util/serialize.h
with
292 additions
and
114 deletions
src/unittest/test_serialization.cpp
+
108
−
17
View file @
6f07f79c
...
@@ -34,6 +34,10 @@ class TestSerialization : public TestBase {
...
@@ -34,6 +34,10 @@ class TestSerialization : public TestBase {
void
testSerializeWideString
();
void
testSerializeWideString
();
void
testSerializeLongString
();
void
testSerializeLongString
();
void
testSerializeJsonString
();
void
testSerializeJsonString
();
void
testSerializeHex
();
void
testDeSerializeString
();
void
testDeSerializeWideString
();
void
testDeSerializeLongString
();
std
::
string
teststring2
;
std
::
string
teststring2
;
std
::
wstring
teststring2_w
;
std
::
wstring
teststring2_w
;
...
@@ -47,9 +51,13 @@ void TestSerialization::runTests(IGameDef *gamedef)
...
@@ -47,9 +51,13 @@ void TestSerialization::runTests(IGameDef *gamedef)
buildTestStrings
();
buildTestStrings
();
TEST
(
testSerializeString
);
TEST
(
testSerializeString
);
TEST
(
testDeSerializeString
);
TEST
(
testSerializeWideString
);
TEST
(
testSerializeWideString
);
TEST
(
testDeSerializeWideString
);
TEST
(
testSerializeLongString
);
TEST
(
testSerializeLongString
);
TEST
(
testDeSerializeLongString
);
TEST
(
testSerializeJsonString
);
TEST
(
testSerializeJsonString
);
TEST
(
testSerializeHex
);
}
}
////////////////////////////////////////////////////////////////////////////////
////////////////////////////////////////////////////////////////////////////////
...
@@ -80,20 +88,37 @@ void TestSerialization::buildTestStrings()
...
@@ -80,20 +88,37 @@ void TestSerialization::buildTestStrings()
void
TestSerialization
::
testSerializeString
()
void
TestSerialization
::
testSerializeString
()
{
{
// Test blank string
// Test blank string
UASSERT
(
serializeString
(
"
Hello world!
"
)
==
mkstr
(
"
\0\
14
Hello world!
"
));
UASSERT
(
serializeString
(
""
)
==
mkstr
(
"
\0\
0
"
));
// Test basic string
// Test basic string
UASSERT
(
serializeString
(
""
)
==
mkstr
(
"
\0\
0
"
));
UASSERT
(
serializeString
(
"
Hello world!
"
)
==
mkstr
(
"
\0\
14
Hello world!
"
));
// Test character range
// Test character range
UASSERT
(
serializeString
(
teststring2
)
==
mkstr
(
"
\1\0
"
)
+
teststring2
);
UASSERT
(
serializeString
(
teststring2
)
==
mkstr
(
"
\1\0
"
)
+
teststring2
);
}
void
TestSerialization
::
testDeSerializeString
()
{
// Test deserialize
// Test deserialize
std
::
istringstream
is
(
serializeString
(
teststring2
),
std
::
ios
::
binary
);
{
UASSERT
(
deSerializeString
(
is
)
==
teststring2
);
std
::
istringstream
is
(
serializeString
(
teststring2
),
std
::
ios
::
binary
);
UASSERT
(
!
is
.
eof
());
UASSERT
(
deSerializeString
(
is
)
==
teststring2
);
is
.
get
();
UASSERT
(
!
is
.
eof
());
UASSERT
(
is
.
eof
());
is
.
get
();
UASSERT
(
is
.
eof
());
}
// Test deserialize an incomplete length specifier
{
std
::
istringstream
is
(
mkstr
(
"
\x53
"
),
std
::
ios
::
binary
);
EXCEPTION_CHECK
(
SerializationError
,
deSerializeString
(
is
));
}
// Test deserialize a string with incomplete data
{
std
::
istringstream
is
(
mkstr
(
"
\x00\x55
abcdefg"
),
std
::
ios
::
binary
);
EXCEPTION_CHECK
(
SerializationError
,
deSerializeString
(
is
));
}
}
}
void
TestSerialization
::
testSerializeWideString
()
void
TestSerialization
::
testSerializeWideString
()
...
@@ -108,13 +133,36 @@ void TestSerialization::testSerializeWideString()
...
@@ -108,13 +133,36 @@ void TestSerialization::testSerializeWideString()
// Test character range
// Test character range
UASSERT
(
serializeWideString
(
teststring2_w
)
==
UASSERT
(
serializeWideString
(
teststring2_w
)
==
mkstr
(
"
\1\0
"
)
+
teststring2_w_encoded
);
mkstr
(
"
\1\0
"
)
+
teststring2_w_encoded
);
}
void
TestSerialization
::
testDeSerializeWideString
()
{
// Test deserialize
// Test deserialize
std
::
istringstream
is
(
serializeWideString
(
teststring2_w
),
std
::
ios
::
binary
);
{
UASSERT
(
deSerializeWideString
(
is
)
==
teststring2_w
);
std
::
istringstream
is
(
serializeWideString
(
teststring2_w
),
std
::
ios
::
binary
);
UASSERT
(
!
is
.
eof
());
UASSERT
(
deSerializeWideString
(
is
)
==
teststring2_w
);
is
.
get
();
UASSERT
(
!
is
.
eof
());
UASSERT
(
is
.
eof
());
is
.
get
();
UASSERT
(
is
.
eof
());
}
// Test deserialize an incomplete length specifier
{
std
::
istringstream
is
(
mkstr
(
"
\x53
"
),
std
::
ios
::
binary
);
EXCEPTION_CHECK
(
SerializationError
,
deSerializeWideString
(
is
));
}
// Test deserialize a string with an incomplete character
{
std
::
istringstream
is
(
mkstr
(
"
\x00\x07\0
a
\0
b
\0
c
\0
d
\0
e
\0
f
\0
"
),
std
::
ios
::
binary
);
EXCEPTION_CHECK
(
SerializationError
,
deSerializeWideString
(
is
));
}
// Test deserialize a string with incomplete data
{
std
::
istringstream
is
(
mkstr
(
"
\x00\x08\0
a
\0
b
\0
c
\0
d
\0
e
\0
f"
),
std
::
ios
::
binary
);
EXCEPTION_CHECK
(
SerializationError
,
deSerializeWideString
(
is
));
}
}
}
void
TestSerialization
::
testSerializeLongString
()
void
TestSerialization
::
testSerializeLongString
()
...
@@ -127,15 +175,39 @@ void TestSerialization::testSerializeLongString()
...
@@ -127,15 +175,39 @@ void TestSerialization::testSerializeLongString()
// Test character range
// Test character range
UASSERT
(
serializeLongString
(
teststring2
)
==
mkstr
(
"
\0\0\1\0
"
)
+
teststring2
);
UASSERT
(
serializeLongString
(
teststring2
)
==
mkstr
(
"
\0\0\1\0
"
)
+
teststring2
);
}
void
TestSerialization
::
testDeSerializeLongString
()
{
// Test deserialize
// Test deserialize
std
::
istringstream
is
(
serializeLongString
(
teststring2
),
std
::
ios
::
binary
);
{
UASSERT
(
deSerializeLongString
(
is
)
==
teststring2
);
std
::
istringstream
is
(
serializeLongString
(
teststring2
),
std
::
ios
::
binary
);
UASSERT
(
!
is
.
eof
());
UASSERT
(
deSerializeLongString
(
is
)
==
teststring2
);
is
.
get
();
UASSERT
(
!
is
.
eof
());
UASSERT
(
is
.
eof
());
is
.
get
();
UASSERT
(
is
.
eof
());
}
// Test deserialize an incomplete length specifier
{
std
::
istringstream
is
(
mkstr
(
"
\x53
"
),
std
::
ios
::
binary
);
EXCEPTION_CHECK
(
SerializationError
,
deSerializeLongString
(
is
));
}
// Test deserialize a string with incomplete data
{
std
::
istringstream
is
(
mkstr
(
"
\x00\x00\x00\x05
abc"
),
std
::
ios
::
binary
);
EXCEPTION_CHECK
(
SerializationError
,
deSerializeLongString
(
is
));
}
// Test deserialize a string with a length too large
{
std
::
istringstream
is
(
mkstr
(
"
\xFF\xFF\xFF\xFF
blah"
),
std
::
ios
::
binary
);
EXCEPTION_CHECK
(
SerializationError
,
deSerializeLongString
(
is
));
}
}
}
void
TestSerialization
::
testSerializeJsonString
()
void
TestSerialization
::
testSerializeJsonString
()
{
{
// Test blank string
// Test blank string
...
@@ -180,3 +252,22 @@ void TestSerialization::testSerializeJsonString()
...
@@ -180,3 +252,22 @@ void TestSerialization::testSerializeJsonString()
is
.
get
();
is
.
get
();
UASSERT
(
is
.
eof
());
UASSERT
(
is
.
eof
());
}
}
void
TestSerialization
::
testSerializeHex
()
{
// Test blank string
UASSERT
(
serializeHexString
(
""
)
==
""
);
UASSERT
(
serializeHexString
(
""
,
true
)
==
""
);
// Test basic string
UASSERT
(
serializeHexString
(
"Hello world!"
)
==
"48656c6c6f20776f726c6421"
);
UASSERT
(
serializeHexString
(
"Hello world!"
,
true
)
==
"48 65 6c 6c 6f 20 77 6f 72 6c 64 21"
);
// Test binary string
UASSERT
(
serializeHexString
(
mkstr
(
"
\x00\x0a\xb0\x63\x1f\x00\xff
"
))
==
"000ab0631f00ff"
);
UASSERT
(
serializeHexString
(
mkstr
(
"
\x00\x0a\xb0\x63\x1f\x00\xff
"
),
true
)
==
"00 0a b0 63 1f 00 ff"
);
}
This diff is collapsed.
Click to expand it.
src/util/serialize.cpp
+
178
−
97
View file @
6f07f79c
...
@@ -28,76 +28,101 @@ with this program; if not, write to the Free Software Foundation, Inc.,
...
@@ -28,76 +28,101 @@ with this program; if not, write to the Free Software Foundation, Inc.,
#include
<iomanip>
#include
<iomanip>
#include
<vector>
#include
<vector>
// Creates a string with the length as the first two bytes
////
//// String
////
std
::
string
serializeString
(
const
std
::
string
&
plain
)
std
::
string
serializeString
(
const
std
::
string
&
plain
)
{
{
if
(
plain
.
size
()
>
65535
)
throw
SerializationError
(
"String too long for serializeString"
);
char
buf
[
2
];
writeU16
((
u8
*
)
&
buf
[
0
],
plain
.
size
());
std
::
string
s
;
std
::
string
s
;
s
.
append
(
buf
,
2
);
char
buf
[
2
];
s
.
append
(
plain
);
return
s
;
}
// Creates a string with the length as the first two bytes from wide string
if
(
plain
.
size
()
>
65535
)
std
::
string
serializeWideString
(
const
std
::
wstring
&
plain
)
{
if
(
plain
.
size
()
>
65535
)
throw
SerializationError
(
"String too long for serializeString"
);
throw
SerializationError
(
"String too long for serializeString"
);
char
buf
[
2
];
writeU16
((
u8
*
)
buf
,
plain
.
size
());
writeU16
((
u8
*
)
&
buf
[
0
],
plain
.
size
());
std
::
string
s
;
s
.
append
(
buf
,
2
);
s
.
append
(
buf
,
2
);
for
(
u32
i
=
0
;
i
<
plain
.
size
();
i
++
)
{
s
.
append
(
plain
);
writeU16
((
u8
*
)
buf
,
plain
[
i
]);
s
.
append
(
buf
,
2
);
}
return
s
;
return
s
;
}
}
// Reads a string with the length as the first two bytes
std
::
string
deSerializeString
(
std
::
istream
&
is
)
std
::
string
deSerializeString
(
std
::
istream
&
is
)
{
{
std
::
string
s
;
char
buf
[
2
];
char
buf
[
2
];
is
.
read
(
buf
,
2
);
is
.
read
(
buf
,
2
);
if
(
is
.
gcount
()
!=
2
)
if
(
is
.
gcount
()
!=
2
)
throw
SerializationError
(
"deSerializeString: size not read"
);
throw
SerializationError
(
"deSerializeString: size not read"
);
u16
s_size
=
readU16
((
u8
*
)
buf
);
std
::
string
s
;
u16
s_size
=
readU16
((
u8
*
)
buf
)
;
if
(
s_size
==
0
)
if
(
s_size
==
0
)
return
s
;
return
s
;
Buffer
<
char
>
buf2
(
s_size
);
Buffer
<
char
>
buf2
(
s_size
);
is
.
read
(
&
buf2
[
0
],
s_size
);
is
.
read
(
&
buf2
[
0
],
s_size
);
if
(
is
.
gcount
()
!=
s_size
)
throw
SerializationError
(
"deSerializeString: couldn't read all chars"
);
s
.
reserve
(
s_size
);
s
.
reserve
(
s_size
);
s
.
append
(
&
buf2
[
0
],
s_size
);
s
.
append
(
&
buf2
[
0
],
s_size
);
return
s
;
return
s
;
}
}
// Reads a wide string with the length as the first two bytes
////
//// Wide String
////
std
::
string
serializeWideString
(
const
std
::
wstring
&
plain
)
{
std
::
string
s
;
char
buf
[
2
];
if
(
plain
.
size
()
>
65535
)
throw
SerializationError
(
"String too long for serializeString"
);
writeU16
((
u8
*
)
buf
,
plain
.
size
());
s
.
append
(
buf
,
2
);
for
(
u32
i
=
0
;
i
<
plain
.
size
();
i
++
)
{
writeU16
((
u8
*
)
buf
,
plain
[
i
]);
s
.
append
(
buf
,
2
);
}
return
s
;
}
std
::
wstring
deSerializeWideString
(
std
::
istream
&
is
)
std
::
wstring
deSerializeWideString
(
std
::
istream
&
is
)
{
{
std
::
wstring
s
;
char
buf
[
2
];
char
buf
[
2
];
is
.
read
(
buf
,
2
);
is
.
read
(
buf
,
2
);
if
(
is
.
gcount
()
!=
2
)
if
(
is
.
gcount
()
!=
2
)
throw
SerializationError
(
"deSerializeString: size not read"
);
throw
SerializationError
(
"deSerializeString: size not read"
);
u16
s_size
=
readU16
((
u8
*
)
buf
);
std
::
wstring
s
;
u16
s_size
=
readU16
((
u8
*
)
buf
)
;
if
(
s_size
==
0
)
if
(
s_size
==
0
)
return
s
;
return
s
;
s
.
reserve
(
s_size
);
s
.
reserve
(
s_size
);
for
(
u32
i
=
0
;
i
<
s_size
;
i
++
)
for
(
u32
i
=
0
;
i
<
s_size
;
i
++
)
{
{
is
.
read
(
&
buf
[
0
],
2
);
is
.
read
(
&
buf
[
0
],
2
);
wchar_t
c16
=
readU16
((
u8
*
)
buf
);
if
(
is
.
gcount
()
!=
2
)
{
throw
SerializationError
(
"deSerializeWideString: couldn't read all chars"
);
}
wchar_t
c16
=
readU16
((
u8
*
)
buf
);
s
.
append
(
&
c16
,
1
);
s
.
append
(
&
c16
,
1
);
}
}
return
s
;
return
s
;
}
}
// Creates a string with the length as the first four bytes
////
//// Long String
////
std
::
string
serializeLongString
(
const
std
::
string
&
plain
)
std
::
string
serializeLongString
(
const
std
::
string
&
plain
)
{
{
char
buf
[
4
];
char
buf
[
4
];
...
@@ -108,62 +133,86 @@ std::string serializeLongString(const std::string &plain)
...
@@ -108,62 +133,86 @@ std::string serializeLongString(const std::string &plain)
return
s
;
return
s
;
}
}
// Reads a string with the length as the first four bytes
std
::
string
deSerializeLongString
(
std
::
istream
&
is
)
std
::
string
deSerializeLongString
(
std
::
istream
&
is
)
{
{
std
::
string
s
;
char
buf
[
4
];
char
buf
[
4
];
is
.
read
(
buf
,
4
);
is
.
read
(
buf
,
4
);
if
(
is
.
gcount
()
!=
4
)
if
(
is
.
gcount
()
!=
4
)
throw
SerializationError
(
"deSerializeLongString: size not read"
);
throw
SerializationError
(
"deSerializeLongString: size not read"
);
u32
s_size
=
readU32
((
u8
*
)
buf
);
std
::
string
s
;
u32
s_size
=
readU32
((
u8
*
)
buf
)
;
if
(
s_size
==
0
)
if
(
s_size
==
0
)
return
s
;
return
s
;
// We don't really want a remote attacker to force us to allocate 4GB...
if
(
s_size
>
LONG_STRING_MAX
)
throw
SerializationError
(
"deSerializeLongString: string too long"
);
Buffer
<
char
>
buf2
(
s_size
);
Buffer
<
char
>
buf2
(
s_size
);
is
.
read
(
&
buf2
[
0
],
s_size
);
is
.
read
(
&
buf2
[
0
],
s_size
);
if
(
is
.
gcount
()
!=
s_size
)
throw
SerializationError
(
"deSerializeString: couldn't read all chars"
);
s
.
reserve
(
s_size
);
s
.
reserve
(
s_size
);
s
.
append
(
&
buf2
[
0
],
s_size
);
s
.
append
(
&
buf2
[
0
],
s_size
);
return
s
;
return
s
;
}
}
// Creates a string encoded in JSON format (almost equivalent to a C string literal)
////
//// JSON
////
std
::
string
serializeJsonString
(
const
std
::
string
&
plain
)
std
::
string
serializeJsonString
(
const
std
::
string
&
plain
)
{
{
std
::
ostringstream
os
(
std
::
ios
::
binary
);
std
::
ostringstream
os
(
std
::
ios
::
binary
);
os
<<
"
\"
"
;
os
<<
"
\"
"
;
for
(
size_t
i
=
0
;
i
<
plain
.
size
();
i
++
)
{
for
(
size_t
i
=
0
;
i
<
plain
.
size
();
i
++
)
{
char
c
=
plain
[
i
];
char
c
=
plain
[
i
];
switch
(
c
)
switch
(
c
)
{
{
case
'"'
:
case
'"'
:
os
<<
"
\\\"
"
;
break
;
os
<<
"
\\\"
"
;
case
'\\'
:
os
<<
"
\\\\
"
;
break
;
break
;
case
'/'
:
os
<<
"
\\
/"
;
break
;
case
'\\'
:
case
'\b'
:
os
<<
"
\\
b"
;
break
;
os
<<
"
\\\\
"
;
case
'\f'
:
os
<<
"
\\
f"
;
break
;
break
;
case
'\n'
:
os
<<
"
\\
n"
;
break
;
case
'/'
:
case
'\r'
:
os
<<
"
\\
r"
;
break
;
os
<<
"
\\
/"
;
case
'\t'
:
os
<<
"
\\
t"
;
break
;
break
;
default:
case
'\b'
:
{
os
<<
"
\\
b"
;
if
(
c
>=
32
&&
c
<=
126
)
break
;
{
case
'\f'
:
os
<<
c
;
os
<<
"
\\
f"
;
}
break
;
else
case
'\n'
:
{
os
<<
"
\\
n"
;
u32
cnum
=
(
u32
)
(
u8
)
c
;
break
;
os
<<
"
\\
u"
<<
std
::
hex
<<
std
::
setw
(
4
)
<<
std
::
setfill
(
'0'
)
<<
cnum
;
case
'\r'
:
os
<<
"
\\
r"
;
break
;
case
'\t'
:
os
<<
"
\\
t"
;
break
;
default:
{
if
(
c
>=
32
&&
c
<=
126
)
{
os
<<
c
;
}
else
{
u32
cnum
=
(
u8
)
c
;
os
<<
"
\\
u"
<<
std
::
hex
<<
std
::
setw
(
4
)
<<
std
::
setfill
(
'0'
)
<<
cnum
;
}
}
break
;
break
;
}
}
}
}
}
}
os
<<
"
\"
"
;
os
<<
"
\"
"
;
return
os
.
str
();
return
os
.
str
();
}
}
// Reads a string encoded in JSON format
std
::
string
deSerializeJsonString
(
std
::
istream
&
is
)
std
::
string
deSerializeJsonString
(
std
::
istream
&
is
)
{
{
std
::
ostringstream
os
(
std
::
ios
::
binary
);
std
::
ostringstream
os
(
std
::
ios
::
binary
);
...
@@ -171,55 +220,66 @@ std::string deSerializeJsonString(std::istream &is)
...
@@ -171,55 +220,66 @@ std::string deSerializeJsonString(std::istream &is)
// Parse initial doublequote
// Parse initial doublequote
is
>>
c
;
is
>>
c
;
if
(
c
!=
'"'
)
if
(
c
!=
'"'
)
throw
SerializationError
(
"JSON string must start with doublequote"
);
throw
SerializationError
(
"JSON string must start with doublequote"
);
// Parse characters
// Parse characters
for
(;;)
for
(;;)
{
{
c
=
is
.
get
();
c
=
is
.
get
();
if
(
is
.
eof
())
if
(
is
.
eof
())
throw
SerializationError
(
"JSON string ended prematurely"
);
throw
SerializationError
(
"JSON string ended prematurely"
);
if
(
c
==
'"'
)
{
if
(
c
==
'"'
)
{
return
os
.
str
();
return
os
.
str
();
}
}
else
if
(
c
==
'\\'
)
{
else
if
(
c
==
'\\'
)
{
c2
=
is
.
get
();
c2
=
is
.
get
();
if
(
is
.
eof
())
if
(
is
.
eof
())
throw
SerializationError
(
"JSON string ended prematurely"
);
throw
SerializationError
(
"JSON string ended prematurely"
);
switch
(
c2
)
switch
(
c2
)
{
{
case
'b'
:
default:
os
<<
c2
;
break
;
os
<<
'\b'
;
case
'b'
:
os
<<
'\b'
;
break
;
break
;
case
'f'
:
os
<<
'\f'
;
break
;
case
'f'
:
case
'n'
:
os
<<
'\n'
;
break
;
os
<<
'\f'
;
case
'r'
:
os
<<
'\r'
;
break
;
break
;
case
't'
:
os
<<
'\t'
;
break
;
case
'n'
:
case
'u'
:
os
<<
'\n'
;
{
break
;
char
hexdigits
[
4
+
1
];
case
'r'
:
os
<<
'\r'
;
break
;
case
't'
:
os
<<
'\t'
;
break
;
case
'u'
:
{
int
hexnumber
;
char
hexdigits
[
4
+
1
];
is
.
read
(
hexdigits
,
4
);
is
.
read
(
hexdigits
,
4
);
if
(
is
.
eof
())
if
(
is
.
eof
())
throw
SerializationError
(
"JSON string ended prematurely"
);
throw
SerializationError
(
"JSON string ended prematurely"
);
hexdigits
[
4
]
=
0
;
hexdigits
[
4
]
=
0
;
std
::
istringstream
tmp_is
(
hexdigits
,
std
::
ios
::
binary
);
std
::
istringstream
tmp_is
(
hexdigits
,
std
::
ios
::
binary
);
int
hexnumber
;
tmp_is
>>
std
::
hex
>>
hexnumber
;
tmp_is
>>
std
::
hex
>>
hexnumber
;
os
<<
(
(
char
)
hexnumber
)
;
os
<<
(
char
)
hexnumber
;
break
;
break
;
}
}
default
:
os
<<
c2
;
break
;
}
}
}
}
else
{
else
os
<<
c
;
{
os
<<
c
;
}
}
}
}
return
os
.
str
();
return
os
.
str
();
}
}
////
//// String/Struct conversions
////
bool
deSerializeStringToStruct
(
std
::
string
valstr
,
bool
deSerializeStringToStruct
(
std
::
string
valstr
,
std
::
string
format
,
void
*
out
,
size_t
olen
)
std
::
string
format
,
void
*
out
,
size_t
olen
)
...
@@ -382,7 +442,6 @@ bool deSerializeStringToStruct(std::string valstr,
...
@@ -382,7 +442,6 @@ bool deSerializeStringToStruct(std::string valstr,
return
true
;
return
true
;
}
}
// Casts *buf to a signed or unsigned fixed-width integer of 'w' width
// Casts *buf to a signed or unsigned fixed-width integer of 'w' width
#define SIGN_CAST(w, buf) (is_unsigned ? *((u##w *) buf) : *((s##w *) buf))
#define SIGN_CAST(w, buf) (is_unsigned ? *((u##w *) buf) : *((s##w *) buf))
...
@@ -469,11 +528,33 @@ bool serializeStructToString(std::string *out,
...
@@ -469,11 +528,33 @@ bool serializeStructToString(std::string *out,
*
out
=
os
.
str
();
*
out
=
os
.
str
();
// Trim off the trailing comma and space
// Trim off the trailing comma and space
if
(
out
->
size
()
>=
2
)
{
if
(
out
->
size
()
>=
2
)
out
->
resize
(
out
->
size
()
-
2
);
out
->
resize
(
out
->
size
()
-
2
);
}
return
true
;
return
true
;
}
}
#undef SIGN_CAST
#undef SIGN_CAST
////
//// Other
////
std
::
string
serializeHexString
(
const
std
::
string
&
data
,
bool
insert_spaces
)
{
std
::
string
result
;
result
.
reserve
(
data
.
size
()
*
(
2
+
insert_spaces
));
static
const
char
hex_chars
[]
=
"0123456789abcdef"
;
const
size_t
len
=
data
.
size
();
for
(
size_t
i
=
0
;
i
!=
len
;
i
++
)
{
u8
byte
=
data
[
i
];
result
.
push_back
(
hex_chars
[(
byte
>>
4
)
&
0x0F
]);
result
.
push_back
(
hex_chars
[(
byte
>>
0
)
&
0x0F
]);
if
(
insert_spaces
&&
i
!=
len
-
1
)
result
.
push_back
(
' '
);
}
return
result
;
}
This diff is collapsed.
Click to expand it.
src/util/serialize.h
+
6
−
0
View file @
6f07f79c
...
@@ -426,6 +426,9 @@ inline video::SColor readARGB8(std::istream &is)
...
@@ -426,6 +426,9 @@ inline video::SColor readARGB8(std::istream &is)
More serialization stuff
More serialization stuff
*/
*/
// 8 MB is a conservative limit. Increase later if problematic.
#define LONG_STRING_MAX (8 * 1024 * 1024)
// Creates a string with the length as the first two bytes
// Creates a string with the length as the first two bytes
std
::
string
serializeString
(
const
std
::
string
&
plain
);
std
::
string
serializeString
(
const
std
::
string
&
plain
);
...
@@ -450,6 +453,9 @@ std::string serializeJsonString(const std::string &plain);
...
@@ -450,6 +453,9 @@ std::string serializeJsonString(const std::string &plain);
// Reads a string encoded in JSON format
// Reads a string encoded in JSON format
std
::
string
deSerializeJsonString
(
std
::
istream
&
is
);
std
::
string
deSerializeJsonString
(
std
::
istream
&
is
);
// Creates a string consisting of the hexadecimal representation of `data`
std
::
string
serializeHexString
(
const
std
::
string
&
data
,
bool
insert_spaces
=
false
);
// Creates a string containing comma delimited values of a struct whose layout is
// Creates a string containing comma delimited values of a struct whose layout is
// described by the parameter format
// described by the parameter format
bool
serializeStructToString
(
std
::
string
*
out
,
bool
serializeStructToString
(
std
::
string
*
out
,
...
...
This diff is collapsed.
Click to expand it.
Preview
0%
Loading
Try again
or
attach a new file
.
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Save comment
Cancel
Please
register
or
sign in
to comment