From d13e08c9b5726148cb8124922c660262e8b414ca Mon Sep 17 00:00:00 2001 From: Eric Fischer Date: Fri, 27 Oct 2017 17:38:07 -0700 Subject: [PATCH] Guard against null keys and values in tileset metadata --- decode.cpp | 5 +++++ mbtiles.cpp | 11 +++++++++-- tile-join.cpp | 37 +++++++++++++++++++++++++------------ 3 files changed, 39 insertions(+), 14 deletions(-) diff --git a/decode.cpp b/decode.cpp index 7079a98..3173eee 100644 --- a/decode.cpp +++ b/decode.cpp @@ -192,6 +192,11 @@ void decode(char *fname, int z, unsigned x, unsigned y, std::set co const unsigned char *name = sqlite3_column_text(stmt2, 0); const unsigned char *value = sqlite3_column_text(stmt2, 1); + if (name == NULL || value == NULL) { + fprintf(stderr, "Corrupt mbtiles file: null metadata\n"); + exit(EXIT_FAILURE); + } + fprintq(stdout, (char *) name); printf(": "); fprintq(stdout, (char *) value); diff --git a/mbtiles.cpp b/mbtiles.cpp index 8bc1eb3..812b0c0 100644 --- a/mbtiles.cpp +++ b/mbtiles.cpp @@ -501,8 +501,15 @@ void mbtiles_write_metadata(sqlite3 *outdb, const char *outdir, const char *fnam while (sqlite3_step(stmt) == SQLITE_ROW) { std::string key, value; - quote(key, (const char *) sqlite3_column_text(stmt, 0)); - quote(value, (const char *) sqlite3_column_text(stmt, 1)); + const char *k = (const char *) sqlite3_column_text(stmt, 0); + const char *v = (const char *) sqlite3_column_text(stmt, 1); + if (k == NULL || v == NULL) { + fprintf(stderr, "Corrupt mbtiles file: null metadata\n"); + exit(EXIT_FAILURE); + } + + quote(key, k); + quote(value, v); if (!first) { fprintf(fp, ",\n"); diff --git a/tile-join.cpp b/tile-join.cpp index 65100b8..f44ac60 100644 --- a/tile-join.cpp +++ b/tile-join.cpp @@ -837,28 +837,39 @@ void decode(struct reader *readers, char *map, std::mapdb, "SELECT value from metadata where name = 'center'", -1, &r->stmt, NULL) == SQLITE_OK) { if (sqlite3_step(r->stmt) == SQLITE_ROW) { const unsigned char *s = sqlite3_column_text(r->stmt, 0); - sscanf((char *) s, "%lf,%lf", &st->midlon, &st->midlat); + if (s != NULL) { + sscanf((char *) s, "%lf,%lf", &st->midlon, &st->midlat); + } } sqlite3_finalize(r->stmt); } if (sqlite3_prepare_v2(r->db, "SELECT value from metadata where name = 'attribution'", -1, &r->stmt, NULL) == SQLITE_OK) { if (sqlite3_step(r->stmt) == SQLITE_ROW) { - attribution = std::string((char *) sqlite3_column_text(r->stmt, 0)); + const unsigned char *s = sqlite3_column_text(r->stmt, 0); + if (s != NULL) { + attribution = std::string((char *) s); + } } sqlite3_finalize(r->stmt); } if (sqlite3_prepare_v2(r->db, "SELECT value from metadata where name = 'description'", -1, &r->stmt, NULL) == SQLITE_OK) { if (sqlite3_step(r->stmt) == SQLITE_ROW) { - description = std::string((char *) sqlite3_column_text(r->stmt, 0)); + const unsigned char *s = sqlite3_column_text(r->stmt, 0); + if (s != NULL) { + description = std::string((char *) s); + } } sqlite3_finalize(r->stmt); } if (sqlite3_prepare_v2(r->db, "SELECT value from metadata where name = 'name'", -1, &r->stmt, NULL) == SQLITE_OK) { if (sqlite3_step(r->stmt) == SQLITE_ROW) { - if (name.size() == 0) { - name = std::string((char *) sqlite3_column_text(r->stmt, 0)); - } else { - name += " + " + std::string((char *) sqlite3_column_text(r->stmt, 0)); + const unsigned char *s = sqlite3_column_text(r->stmt, 0); + if (s != NULL) { + if (name.size() == 0) { + name = std::string((char *) s); + } else { + name += " + " + std::string((char *) s); + } } } sqlite3_finalize(r->stmt); @@ -866,11 +877,13 @@ void decode(struct reader *readers, char *map, std::mapdb, "SELECT value from metadata where name = 'bounds'", -1, &r->stmt, NULL) == SQLITE_OK) { if (sqlite3_step(r->stmt) == SQLITE_ROW) { const unsigned char *s = sqlite3_column_text(r->stmt, 0); - if (sscanf((char *) s, "%lf,%lf,%lf,%lf", &minlon, &minlat, &maxlon, &maxlat) == 4) { - st->minlon = min(minlon, st->minlon); - st->maxlon = max(maxlon, st->maxlon); - st->minlat = min(minlat, st->minlat); - st->maxlat = max(maxlat, st->maxlat); + if (s != NULL) { + if (sscanf((char *) s, "%lf,%lf,%lf,%lf", &minlon, &minlat, &maxlon, &maxlat) == 4) { + st->minlon = min(minlon, st->minlon); + st->maxlon = max(maxlon, st->maxlon); + st->minlat = min(minlat, st->minlat); + st->maxlat = max(maxlat, st->maxlat); + } } } sqlite3_finalize(r->stmt);