Index: trunk/ippTools/src/dettool.c
===================================================================
--- trunk/ippTools/src/dettool.c	(revision 7174)
+++ trunk/ippTools/src/dettool.c	(revision 7175)
@@ -504,6 +504,6 @@
         if (!valid) {
             psError(PS_ERR_UNKNOWN, true,
-        "class_id %s does not corespond to on contained in an detInputExp",
-            ((detStackedImfileRow *)stackedImfiles->data[i])->class_id);
+                "class_id %s does not corespond to a detInputExp",
+                ((detStackedImfileRow *)stackedImfiles->data[i])->class_id);
             psFree(stackedImfiles);
             psFree(valid_class_ids);
@@ -701,4 +701,12 @@
 {
     PS_ASSERT_PTR_NON_NULL(config, false);
+    
+    // det_id is required
+    bool status = false;
+    psString det_id = psMetadataLookupStr(&status, config->args, "-det_id");
+    if (!status) {
+        psError(PS_ERR_UNKNOWN, false, "failed to lookup value for -det_id");
+        return false;
+    }
 
     // find all detMasterIImfile for det_id
@@ -708,7 +716,58 @@
     if (!masterImfiles) {
         psError(PS_ERR_UNKNOWN, false, "no detMasterImfile rows found");
-        return NULL;
-    }
-
-    return true;
-}
+        return false;
+    }
+
+    // find all input class_ids
+    psArray *valid_class_ids = validDetInputClassIds(config, det_id);
+    if (!valid_class_ids) {
+        psError(PS_ERR_UNKNOWN, false, "no detInputExp imfile class_ids found");
+        return false; 
+    }
+ 
+    // check class_ids for validity
+    for (long i = 0; i < psArrayLength(masterImfiles); i++) {
+        bool valid = false;
+        for (long j = 0; j < psArrayLength(valid_class_ids); j++) {
+            if (strcmp(((detMasterImfileRow *)masterImfiles->data[i])->class_id,
+                   (char *)valid_class_ids->data[j]) == 0) {
+                valid = true;
+                if (!psArrayRemove(valid_class_ids, valid_class_ids->data[j])) {
+                    psError(PS_ERR_UNKNOWN, false, "psArrayRemove() failed");
+                    psFree(masterImfiles);
+                    psFree(valid_class_ids);
+                    return false;
+                }
+                j--; // must update loop index
+            }
+        }
+        if (!valid) {
+            psError(PS_ERR_UNKNOWN, true,
+        "class_id %s does not corespond to a detInputExp",
+            ((detMasterImfileRow *)masterImfiles->data[i])->class_id);
+            psFree(masterImfiles);
+            psFree(valid_class_ids);
+            return false;
+        }
+    }
+
+    // if we nade it this far we must have a complete frame
+
+    // print detMasterImfiles
+    psMetadata *output = psMetadataAlloc();
+    for (long i = 0; i < psArrayLength(masterImfiles); i++) {
+        psMetadata *md = detStackedImfileMetadataFromObject(
+                masterImfiles->data[i]);
+        psMetadataAddMetadata(
+            output, PS_LIST_TAIL, "detMasterImfile", PS_META_DUPLICATE_OK,
+            NULL, md
+        );
+    }
+
+    psString str = psMetadataConfigFormat(output); 
+    psFree(output);
+    fprintf(stdout, "%s\n", str);
+    psFree(str);
+
+    return true;
+}
