int check_set( vector results, DB_WORKUNIT& wu, int& canonicalid, double& credit, bool& retry ); Define N := length of result vector, and let M := N. check_set() will ALWAYS be called with N>=wu.min_quorum. check_set() will ALWAYS be called with ALL results satisfying result.outcome == RESULT_OUTCOME_SUCCESS result.validate_state == VALIDATE_STATE_INIT check_set() should NEVER modify wu [although it is not declared const] [1] Syntax pass (optional) for (all N results) { if (one or more of the output files can be read and one or more of those files contains erroneous or invalid or incorrect output, i.e. the file syntax is wrong) { set result.outcome=RESULT_OUTCOME_VALIDATE_ERROR; set result.validate_state=VALIDATE_STATE_INVALID; decrement counter: M = M-1; } // erroneous or incorrect or invalid output files else if (result has a potentially recoverable error, i.e. NFS directory not mounted, server is unreachable, upload server unreachable) { dont not modify result.validate_state; dont not modify result.outcome; decrement counter M = M-1; set retry=true; } // recoverable error else if (every output file of the result is unreadable or fails to exist) { set result.outcome=RESULT_OUTCOME_VALIDATE_ERROR; set result.validate_state=VALIDATE_STATE_INIT; decrement counter: M = M-1; } // all result output files unreadable or nonexistent } // end of syntax pass loop over all N results Define REMAINING RESULTS to be those that do NOT fall into one of the two categories above. There are M of these. If the syntax pass has been skipped, then M == N. if (M < wu.min_quorum) { dont modify canonicalid; dont modify credit; leave retry as set above; leave result.outcome unchanged for M remaining results; leave result.validate_state unchanged for M remaining results; return 0; } // fewer than min_quorum results remain At any point in this process, if a major error occurs, check_set should return nonzero. This will cause the validator to exit. If this happens, it does not matter how you have set or modified result.outcome, result.validate_state, retry, credit, or canonicalid. // END OF OPTIONAL SYNTAX PASS [2] Comparison pass (required). We have M>=wu.min_quorum REMAINING RESULTS results with result.outcome == RESULT_OUTCOME_SUCCESS result.validate_state == VALIDATE_STATE_INIT All the output files of all of these results are readable. All of the output files for a given result are, when taken "in isolation" apparently valid. If these conditions are not met then you must do the "syntax pass" above. if (one of these results is determined to be THE correct [canonical] result) { for correct result { set result.validate_state=VALIDATE_STATE_VALID; set canonicalid=result.id; } // canonical result for (the REMAINING M - 1 results) { // NOTE: what is below can be done by calling // check_pair(result, canonical_result) if (result is correct, matches canonical) { result.validate_state=VALIDATE_STATE_VALID; } else { result.validate_state=VALIDATE_STATE_INVALID; } } // loop over remaining M-1 results set credit; leave retry as set from the syntax pass above; return 0; } // found canonical result else { // You are UNABLE to determine if one of the M REMAINING RESULTS // is correct, so: do not modify result.outcome for ANY of M remaining results; do not modify result.validate_state for ANY of M remaining results; do not set credit; do not set canonicalid; leave retry as set from the syntax pass; return 0; } // did not find canonical result At any point in this process, if a major error occurs, check_set should return nonzero. This will cause the validator to exit. If this happens, it does not matter how you have set result.outcome, result.validate_state, retry, credit, or canonicalid for ANY of the results. // end of Comparison pass