Allow multiple hash values in the file reference database
authorAndreas Steffen <andreas.steffen@strongswan.org>
Tue, 10 Jun 2014 13:10:21 +0000 (15:10 +0200)
committerAndreas Steffen <andreas.steffen@strongswan.org>
Tue, 10 Jun 2014 14:48:15 +0000 (16:48 +0200)
src/libpts/pts/pts_database.c
src/libpts/pts/pts_file_meas.c

index f2e2c9c..d7b85c1 100644 (file)
@@ -101,20 +101,20 @@ METHOD(pts_database_t, create_file_hash_enumerator, enumerator_t*,
        if (is_dir)
        {
                e = this->db->query(this->db,
-                               "SELECT f.name, fh.hash FROM file_hashes AS fh "
+                               "SELECT f.id, f.name, fh.hash FROM file_hashes AS fh "
                                "JOIN files AS f ON f.id = fh.file "
                                "JOIN directories as d ON d.id = f.dir "
                                "WHERE fh.product = ? AND fh.algo = ? AND d.id = ? "
                                "ORDER BY f.name",
-                               DB_INT, pid, DB_INT, algo, DB_INT, id, DB_TEXT, DB_BLOB);
+                               DB_INT, pid, DB_INT, algo, DB_INT, id, DB_INT, DB_TEXT, DB_BLOB);
        }
        else
        {
                e = this->db->query(this->db,
-                               "SELECT f.name, fh.hash FROM file_hashes AS fh "
+                               "SELECT f.id, f.name, fh.hash FROM file_hashes AS fh "
                                "JOIN files AS f ON f.id = fh.file "
                                "WHERE fh.product = ? AND fh.algo = ? AND fh.file = ?",
-                               DB_INT, pid, DB_INT, algo, DB_INT, id, DB_TEXT, DB_BLOB);
+                               DB_INT, pid, DB_INT, algo, DB_INT, id, DB_INT, DB_TEXT, DB_BLOB);
        }
        return e;
 }
index 4112d0c..478892a 100644 (file)
@@ -184,47 +184,75 @@ METHOD(pts_file_meas_t, check, bool,
 METHOD(pts_file_meas_t, verify, bool,
        private_pts_file_meas_t *this, enumerator_t *e_hash, bool is_dir)
 {
+       int fid, fid_last = 0;
        char *filename;
        chunk_t measurement;
        entry_t *entry;
-       enumerator_t *enumerator;
-       bool found, success = TRUE;
+       enumerator_t *enumerator = NULL;
+       bool found = FALSE, match = FALSE, success = TRUE;
 
-       while (e_hash->enumerate(e_hash, &filename, &measurement))
+       while (e_hash->enumerate(e_hash, &fid, &filename, &measurement))
        {
-               found = FALSE;
-
-               enumerator = this->list->create_enumerator(this->list);
-               while (enumerator->enumerate(enumerator, &entry))
+               if (fid != fid_last)
                {
-                       if (!is_dir || streq(filename, entry->filename))
+                       if (found && !match)
                        {
-                               found = TRUE;
-                               break;
+                               /* no matching hash value found for last filename */
+                               success = FALSE;
+                               DBG1(DBG_PTS, "  %#B for '%s' is incorrect",
+                                        &entry->measurement, entry->filename);
+                               enumerator->destroy(enumerator);
                        }
-               }
-               enumerator->destroy(enumerator);
 
-               if (!found)
-               {
-                       DBG1(DBG_PTS, "  no measurement found for '%s'", filename);
-                       success = FALSE;
-                       continue;
-               }
-               if (chunk_equals(measurement, entry->measurement))
-               {
-                       DBG2(DBG_PTS, "  %#B for '%s' is ok", &measurement, filename);
-               }
-               else
-               {
-                       DBG1(DBG_PTS, "  %#B for '%s' is incorrect", &measurement, filename);
-                       success = FALSE;
+                       /* get a new filename from the database */
+                       found = FALSE;
+                       match = FALSE;
+                       fid_last = fid;
+
+                       /**
+                        * check if we find an entry for this filename
+                        * in the PTS measurement list
+                       */
+                       enumerator = this->list->create_enumerator(this->list);
+                       while (enumerator->enumerate(enumerator, &entry))
+                       {
+                               if (!is_dir || streq(filename, entry->filename))
+                               {
+                                       found = TRUE;
+                                       break;
+                               }
+                       }
+
+                       /* no PTS measurement returned for this filename */ 
+                       if (!found)
+                       {
+                               success = FALSE;
+                               DBG1(DBG_PTS, "  no measurement found for '%s'", filename);
+                               enumerator->destroy(enumerator);
+                       }
                }
-               if (!is_dir)
+
+               if (found && !match)
                {
-                       break;
+                       if (chunk_equals(measurement, entry->measurement))
+                       {
+                               match = TRUE;
+                               DBG2(DBG_PTS, "  %#B for '%s' is ok",
+                                        &entry->measurement, entry->filename);
+                               enumerator->destroy(enumerator);
+                       }
                }
        }
+
+       if (found && !match)
+       {
+               /* no matching hash value found for the very last filename */
+               success = FALSE;
+               DBG1(DBG_PTS, "  %#B for '%s' is incorrect",
+                        &entry->measurement, entry->filename);
+                       enumerator->destroy(enumerator);
+       }
+       
        return success;
 }