@@ -138,7 +138,29 @@ inline static void decodePrefixedString(
138138}
139139/* * Free the string duplicated by duplicateStringValue()/duplicateAndPrefixStringValue().
140140 */
141- static inline void releaseStringValue (char * value) { free (value); }
141+ #if JSONCPP_USING_SECURE_MEMORY
142+ static inline void releasePrefixedStringValue (char * value) {
143+ unsigned length = 0 ;
144+ char const * valueDecoded;
145+ decodePrefixedString (true , value, &length, &valueDecoded);
146+ size_t const size = sizeof (unsigned ) + length + 1U ;
147+ memset (value, 0 , size);
148+ free (value);
149+ }
150+ static inline void releaseStringValue (char * value, unsigned length) {
151+ // length==0 => we allocated the strings memory
152+ size_t size = (length==0 ) ? strlen (value) : length;
153+ memset (value, 0 , size);
154+ free (value);
155+ }
156+ #else // !JSONCPP_USING_SECURE_MEMORY
157+ static inline void releasePrefixedStringValue (char * value) {
158+ free (value);
159+ }
160+ static inline void releaseStringValue (char * value, unsigned length) {
161+ free (value);
162+ }
163+ #endif // JSONCPP_USING_SECURE_MEMORY
142164
143165} // namespace Json
144166
@@ -193,12 +215,12 @@ Value::CommentInfo::CommentInfo() : comment_(0)
193215
194216Value::CommentInfo::~CommentInfo () {
195217 if (comment_)
196- releaseStringValue (comment_);
218+ releaseStringValue (comment_, 0u );
197219}
198220
199221void Value::CommentInfo::setComment (const char * text, size_t len) {
200222 if (comment_) {
201- releaseStringValue (comment_);
223+ releaseStringValue (comment_, 0u );
202224 comment_ = 0 ;
203225 }
204226 JSON_ASSERT (text != 0 );
@@ -229,10 +251,10 @@ Value::CZString::CZString(char const* str, unsigned ulength, DuplicationPolicy a
229251 storage_.length_ = ulength & 0x3FFFFFFF ;
230252}
231253
232- Value::CZString::CZString (const CZString& other)
233- : cstr_ (other.storage_.policy_ != noDuplication && other.cstr_ != 0
234- ? duplicateStringValue(other.cstr_, other.storage_.length_)
235- : other.cstr_) {
254+ Value::CZString::CZString (const CZString& other) {
255+ cstr_ = (other.storage_ .policy_ != noDuplication && other.cstr_ != 0
256+ ? duplicateStringValue (other.cstr_ , other.storage_ .length_ )
257+ : other.cstr_ );
236258 storage_.policy_ = static_cast <unsigned >(other.cstr_
237259 ? (static_cast <DuplicationPolicy>(other.storage_ .policy_ ) == noDuplication
238260 ? noDuplication : duplicate)
@@ -248,8 +270,9 @@ Value::CZString::CZString(CZString&& other)
248270#endif
249271
250272Value::CZString::~CZString () {
251- if (cstr_ && storage_.policy_ == duplicate)
252- releaseStringValue (const_cast <char *>(cstr_));
273+ if (cstr_ && storage_.policy_ == duplicate) {
274+ releaseStringValue (const_cast <char *>(cstr_), storage_.length_ + 1u ); // +1 for null terminating character for sake of completeness but not actually necessary
275+ }
253276}
254277
255278void Value::CZString::swap (CZString& other) {
@@ -455,7 +478,7 @@ Value::~Value() {
455478 break ;
456479 case stringValue:
457480 if (allocated_)
458- releaseStringValue (value_.string_ );
481+ releasePrefixedStringValue (value_.string_ );
459482 break ;
460483 case arrayValue:
461484 case objectValue:
@@ -467,6 +490,8 @@ Value::~Value() {
467490
468491 if (comments_)
469492 delete[] comments_;
493+
494+ value_.uint_ = 0 ;
470495}
471496
472497Value& Value::operator =(Value other) {
@@ -611,6 +636,18 @@ const char* Value::asCString() const {
611636 return this_str;
612637}
613638
639+ #if JSONCPP_USING_SECURE_MEMORY
640+ unsigned Value::getCStringLength () const {
641+ JSON_ASSERT_MESSAGE (type_ == stringValue,
642+ " in Json::Value::asCString(): requires stringValue" );
643+ if (value_.string_ == 0 ) return 0 ;
644+ unsigned this_len;
645+ char const * this_str;
646+ decodePrefixedString (this ->allocated_ , this ->value_ .string_ , &this_len, &this_str);
647+ return this_len;
648+ }
649+ #endif
650+
614651bool Value::getString (char const ** str, char const ** cend) const {
615652 if (type_ != stringValue) return false ;
616653 if (value_.string_ == 0 ) return false ;
0 commit comments