Make sure the str argument to sscanf() is a 0 terminated C-string. Fixes Bug #447.

v0.27.3
Andreas Huggel 20 years ago
parent 59f891d88c
commit fc11d18013

@ -41,6 +41,7 @@ EXIV2_RCSID("@(#) $Id$");
#include <iomanip> #include <iomanip>
#include <sstream> #include <sstream>
#include <cassert> #include <cassert>
#include <cstring>
#include <ctime> #include <ctime>
// ***************************************************************************** // *****************************************************************************
@ -393,9 +394,11 @@ namespace Exiv2 {
#endif #endif
return 1; return 1;
} }
int scanned = sscanf(reinterpret_cast<const char*>(buf), // Make the buffer a 0 terminated C-string for sscanf
"%4d%2d%2d", char b[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0 };
&date_.year, &date_.month, &date_.day); memcpy(b, reinterpret_cast<const char*>(buf), 8);
int scanned = sscanf(b, "%4d%2d%2d",
&date_.year, &date_.month, &date_.day);
if (scanned != 3) { if (scanned != 3) {
#ifndef SUPPRESS_WARNINGS #ifndef SUPPRESS_WARNINGS
std::cerr << Error(29) << "\n"; std::cerr << Error(29) << "\n";
@ -414,9 +417,8 @@ namespace Exiv2 {
#endif #endif
return 1; return 1;
} }
int scanned = sscanf(buf.data(), int scanned = sscanf(buf.c_str(), "%4d-%d-%d",
"%4d-%d-%d", &date_.year, &date_.month, &date_.day);
&date_.year, &date_.month, &date_.day);
if (scanned != 3) { if (scanned != 3) {
#ifndef SUPPRESS_WARNINGS #ifndef SUPPRESS_WARNINGS
std::cerr << Error(29) << "\n"; std::cerr << Error(29) << "\n";
@ -496,16 +498,17 @@ namespace Exiv2 {
int TimeValue::read(const byte* buf, long len, ByteOrder /*byteOrder*/) int TimeValue::read(const byte* buf, long len, ByteOrder /*byteOrder*/)
{ {
// Make the buffer a 0 terminated C-string for scanTime[36]
char b[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
memcpy(b, reinterpret_cast<const char*>(buf), (len < 12 ? len : 11));
// Hard coded to read HHMMSS or Iptc style times // Hard coded to read HHMMSS or Iptc style times
int rc = 1; int rc = 1;
if (len == 6) { if (len == 6) {
// Try to read (non-standard) HHMMSS format // Try to read (non-standard) HHMMSS format
rc = scanTime3(reinterpret_cast<const char*>(buf), rc = scanTime3(b, "%2d%2d%2d");
"%2d%2d%2d");
} }
if (len == 11) { if (len == 11) {
rc = scanTime6(reinterpret_cast<const char*>(buf), rc = scanTime6(b, "%2d%2d%2d%1c%2d%2d");
"%2d%2d%2d%1c%2d%2d");
} }
#ifndef SUPPRESS_WARNINGS #ifndef SUPPRESS_WARNINGS
if (rc) { if (rc) {
@ -521,10 +524,10 @@ namespace Exiv2 {
int rc = 1; int rc = 1;
if (buf.length() < 9) { if (buf.length() < 9) {
// Try to read (non-standard) H:M:S format // Try to read (non-standard) H:M:S format
rc = scanTime3(buf.data(), "%d:%d:%d"); rc = scanTime3(buf.c_str(), "%d:%d:%d");
} }
else { else {
rc = scanTime6(buf.data(), "%d:%d:%d%1c%d:%d"); rc = scanTime6(buf.c_str(), "%d:%d:%d%1c%d:%d");
} }
#ifndef SUPPRESS_WARNINGS #ifndef SUPPRESS_WARNINGS
if (rc) { if (rc) {

@ -807,9 +807,27 @@ namespace Exiv2 {
private: private:
//! @name Manipulators //! @name Manipulators
//@{ //@{
//! Set time from \em buf if it conforms to \em format (3 input items) /*!
@brief Set time from \em buf if it conforms to \em format
(3 input items).
This function only sets the hour, minute and second parts of time_.
@param buf A 0 terminated C-string containing the time to parse.
@param format Format string for sscanf().
@return 0 if successful, else 1.
*/
int scanTime3(const char* buf, const char* format); int scanTime3(const char* buf, const char* format);
//! Set time from \em buf if it conforms to \em format (6 input items) /*!
@brief Set time from \em buf if it conforms to \em format
(6 input items).
This function sets all parts of time_.
@param buf A 0 terminated C-string containing the time to parse.
@param format Format string for sscanf().
@return 0 if successful, else 1.
*/
int scanTime6(const char* buf, const char* format); int scanTime6(const char* buf, const char* format);
//@} //@}

@ -46,6 +46,10 @@ filename=`prep_file $num`
$binpath/exiv2 -v -M'set Exif.Photo.UserComment A comment' $filename $binpath/exiv2 -v -M'set Exif.Photo.UserComment A comment' $filename
$binpath/exiv2 -pt $filename $binpath/exiv2 -pt $filename
num=447 # Problem only visible in Valgrind
filename=`prep_file $num`
$binpath/exiv2 -pi $filename
) > $results 2>&1 ) > $results 2>&1
diff -q $diffargs $results $good diff -q $diffargs $results $good

@ -201,3 +201,7 @@ Exif.Thumbnail.YResolution Rational 1 180
Exif.Thumbnail.ResolutionUnit Short 1 inch Exif.Thumbnail.ResolutionUnit Short 1 inch
Exif.Thumbnail.JPEGInterchangeFormat Long 1 0 Exif.Thumbnail.JPEGInterchangeFormat Long 1 0
Exif.Thumbnail.JPEGInterchangeFormatLength Long 1 5448 Exif.Thumbnail.JPEGInterchangeFormatLength Long 1 5448
------> Bug 447 <-------
Iptc.Application2.Caption String 0
Iptc.Application2.DateCreated Date 8 2005-08-09
Iptc.Application2.TimeCreated Time 11 01:28:31-07:00

Binary file not shown.

After

Width:  |  Height:  |  Size: 11 KiB

Loading…
Cancel
Save