3 Copyright (C) 2010-2013 celeron55, Perttu Ahola <celeron55@gmail.com>
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU Lesser General Public License as published by
7 the Free Software Foundation; either version 2.1 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU Lesser General Public License for more details.
15 You should have received a copy of the GNU Lesser General Public License along
16 with this program; if not, write to the Free Software Foundation, Inc.,
17 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
20 #include "serialize.h"
23 #include "util/string.h"
24 #include "exceptions.h"
25 #include "irrlichttypes.h"
31 FloatType g_serialize_f32_type
= FLOATTYPE_UNKNOWN
;
38 std::string
serializeString16(const std::string
&plain
)
43 if (plain
.size() > STRING_MAX_LEN
)
44 throw SerializationError("String too long for serializeString16");
45 s
.reserve(2 + plain
.size());
47 writeU16((u8
*)&buf
[0], plain
.size());
54 std::string
deSerializeString16(std::istream
&is
)
61 throw SerializationError("deSerializeString16: size not read");
63 u16 s_size
= readU16((u8
*)buf
);
68 is
.read(&s
[0], s_size
);
69 if (is
.gcount() != s_size
)
70 throw SerializationError("deSerializeString16: couldn't read all chars");
80 std::string
serializeString32(const std::string
&plain
)
85 if (plain
.size() > LONG_STRING_MAX_LEN
)
86 throw SerializationError("String too long for serializeLongString");
87 s
.reserve(4 + plain
.size());
89 writeU32((u8
*)&buf
[0], plain
.size());
95 std::string
deSerializeString32(std::istream
&is
)
101 if (is
.gcount() != 4)
102 throw SerializationError("deSerializeLongString: size not read");
104 u32 s_size
= readU32((u8
*)buf
);
108 // We don't really want a remote attacker to force us to allocate 4GB...
109 if (s_size
> LONG_STRING_MAX_LEN
) {
110 throw SerializationError("deSerializeLongString: "
111 "string too long: " + itos(s_size
) + " bytes");
115 is
.read(&s
[0], s_size
);
116 if ((u32
)is
.gcount() != s_size
)
117 throw SerializationError("deSerializeLongString: couldn't read all chars");
126 std::string
serializeJsonString(const std::string
&plain
)
128 std::ostringstream
os(std::ios::binary
);
131 for (char c
: plain
) {
158 if (c
>= 32 && c
<= 126) {
162 os
<< "\\u" << std::hex
<< std::setw(4)
163 << std::setfill('0') << cnum
;
174 std::string
deSerializeJsonString(std::istream
&is
)
176 std::ostringstream
os(std::ios::binary
);
179 // Parse initial doublequote
182 throw SerializationError("JSON string must start with doublequote");
188 throw SerializationError("JSON string ended prematurely");
197 throw SerializationError("JSON string ended prematurely");
216 char hexdigits
[4 + 1];
218 is
.read(hexdigits
, 4);
220 throw SerializationError("JSON string ended prematurely");
223 std::istringstream
tmp_is(hexdigits
, std::ios::binary
);
224 tmp_is
>> std::hex
>> hexnumber
;
225 os
<< (char)hexnumber
;
240 std::string
serializeJsonStringIfNeeded(const std::string
&s
)
242 for (size_t i
= 0; i
< s
.size(); ++i
) {
243 if (s
[i
] <= 0x1f || s
[i
] >= 0x7f || s
[i
] == ' ' || s
[i
] == '\"')
244 return serializeJsonString(s
);
249 std::string
deSerializeJsonStringIfNeeded(std::istream
&is
)
251 std::ostringstream tmp_os
;
252 bool expect_initial_quote
= true;
253 bool is_json
= false;
254 bool was_backslash
= false;
260 if (expect_initial_quote
&& c
== '"') {
266 was_backslash
= false;
268 was_backslash
= true;
270 break; // Found end of string
280 expect_initial_quote
= false;
283 std::istringstream
tmp_is(tmp_os
.str(), std::ios::binary
);
284 return deSerializeJsonString(tmp_is
);