mirror of https://github.com/BOINC/boinc.git
Page:
ValidationLowLevel
Pages
API Implementation
ATI Radeon
Account managers
AccountControl
AccountManagement
AccountManagers
Adaptive Replication
AdminAlphaTest
AdminApprovedProjects
AdminDepLibs
AdminDepLibsCurl
AdminDepLibsOpenSSL
AdminDepLibsSqlite
AdminDepLibsZlib
AdminInstallerMac
AdminInstallerUnix
AdminInstallerWin
AdminLocalize
AdminReleaseAndroid
AdminReleaseManagement
AdminRoles
AdminTasks
AdminWrappers
Advanced view
AlphaInstructions
AndroidBoinc
AndroidBoincImpl
AndroidBoincTesting
AndroidBoincTodo
AndroidBuildApp
AndroidBuildClient
AndroidBuildStatus
AndroidGuiDiscuss
Anonymous platform
AppCoprocessor
AppDebug
AppDebugAndroid
AppDebugWin
AppDev
AppFiltering
AppIntro
AppLibraries
AppMultiThread
AppPlan
AppPlanSpec
AppVersion
AppVersionNew
Apple Metal Support
AssignedWork
Assimilation introduction
Assimilators in C
Assimilators in scripting languages
AutoFlops
AutoUpdate
BOINC Client
BOINC Data directory
BOINC Help
BOINC Manager
BOINC Security
BOINC screensaver
BOINC apps (introduction)
BOINC community
BOINC events
BOINC overview
BOINC projects
BOINC software development
BOINConPhones
BackendLogic
BackendPrograms
BackendState
BackendUtilities
BadgeDoc
BadgesOld
BashCommandCompletion
BasicApi
BasicConcepts
BerkeleyTasks
BetaTest
BlackList
BoincBasics
BoincContributersCall
BoincDocker
BoincFiles
BoincGovernanceWorkingGroups
BoincIntro
BoincLite
BoincPapers
BoincPlatforms
BoincPmcPage
BoincPr
BoincProjectsCall
BoincSecurity
Boinccmd tool
BuildClientProcedure
BuildMacApp
Building BOINC on Unix
Building BOINC software
CamelCase
CancelJobs
CertSig
Changes to this Wiki
Choosing and joining projects
Client configuration
Client release notes
ClientAppConfig
ClientDataModel
ClientFiles
ClientFsm
ClientLogic
ClientOpaque
ClientSched
ClientSchedOctTen
ClientSchedOld
ClientSchedVersionFour
ClientSetupLogicWin
ClientSetupLogicWinFileLayout
ClientSetupLogicWinSix
ClientSetupLogicWinSixCleanup
ClientSetupWinSix
ClientSim
CloudServer
CodeSigning
CodingStyle
CommIntro
Command line job submission
CompileApp
CompileAppLinux
CompileAppWin
CompileClient
CompileWithWxWidgets
CompoundApps
Computation credit
Computing with BOINC
CondorBoinc
ConferenceList
Contact BOINC
ContributePage
Controlling BOINC remotely
CoreClient
CpuSched
Create a BOINC server (cookbook)
CreateProjectCookbook
Creating a skin for the BOINC Manager
Creating custom installers
CreditAlt
CreditGeneralized
CreditNew
CreditNotes
CreditOptions
CreditProposal
CreditStats
CrossProjectUserId
CudaApps
DataBase
DataFlow
DbDump
DbIds
DbPurge
DebugClientWin
DeleteFile
Deploy Linux apps using VirtualBox (cookbook)
DesignKeywords
DesktopGrid
DevMethodologies
DevProcess
DevProjects
DevProjects_New
DevQualityAssurance
Development_Workflow
DiagnosticsApi
DirHierarchy
DiskManagement
Docker and WSL
Docker app cookbook
Docker app implementation
Docker apps
Docker design alternatives
Docker universal app web interface
Docker universal app
DownloadInfo
DownloadOther
DrupalConversion
DrupalIntegration
EastCoast08
Editing computing preferences with the BOINC Manager
EmBoinc
EmailChangeNotification
EmailLists
Error handling (cookbook)
Error handling (introduction)
ErrorReference
Error_Abortingtask_Exceededdisklimit
Error_Cantdeletepreviousstatefile
Error_Givinguponupload
Error_Schedulerrequestfailed
ExampleApps
FileCompression
FileDeleter
FileList
FileUpload
FortranApps
Fossils
GPU computing
GPUApp
GSoC_13
GdprCompliance
GetFile
GetFileList
GitMigration
Global prefs override.xml
Going public
GpuSched
GpuSync
GpuWorkFetch
GraphicsApi
GraphicsApiOld
GraphicsApps
GraphicsHtml
GridIntegration
GuiRpc
GuiRpcProtocol
GuiUrls
HTMLGfx
HarzPics
Heat and energy considerations
Home
Homogeneous App Version
Homogeneous Redundancy
Host identification and merging
HostId
HostMeasurement
How BOINC works
HtmlOps
Initialization files
InstallDrupal
Installing BOINC on Debian or Ubuntu
Installing BOINC on EC2
Installing BOINC on Fedora
Installing BOINC on Gentoo
Installing BOINC on Ubuntu
Installing BOINC
Installing on Android
Installing on FreeBSD
Installing on Linux
Installing on MacOS
Installing on Windows
IntermediateUpload
JavaApps
Job processing (cookbook)
Job processing (introduction)
Job replication
JobEst
JobIn
JobIntro
JobKeywords
JobPinning
JobPrioritization
JobReplication
JobSched
JobSizeMatching
JobStage
JobStatus
JobSubmission
JobTemplates
KeySetup
LammpsRemote
LdapSupport
Linux file permissions
Linux DEB and RPM support
Linux installer
LocalityNew
LocalityScheduling
Locating stolen computers
LogExtension
LogRotate
LowLatency
MacBacktrace
MacBuild
MacDeveloper
MacDeveloperProjects
Maintain your BOINC project
MakeProject
ManagerImpl
ManagerMenus
MasterUrl
MediaWiki
MemoryManagement
Missing Linux shared libraries
MpiApps
MultiHost
MultiSize
MultiUser
MultiUserPriority
MysqlConfig
Network related problems
NetworkApps
NonCpuIntensive
Notifications
OpenCL Applications
OpenCL CPU applications
OpenId
OpenclCpu
OptionsApi
OrgGrid
OtherProjectDocs
PMC_Minutes
PMC_Minutes_2017_12_15
PMC_Minutes_2018_01_10
PageTemplates
PasswordHash
PayPalDonations
Per user file sandbox
PerAppCredit
PersFileXfer
PhpDb
PhysicalFileManagement
PlanClassFunc
PortalFeatures
PowerManagement
Preferences
PreferencesXml
Prefs2
PrefsImpl
PrefsOverride
PrefsPresets
PrefsReference
PrefsReference_Time
PrefsRemodel
PrefsUnification
PrepareLinuxBuildMachine
Process_proposals
ProfileScreen
ProjectConfigFile
ProjectDaemons
ProjectDefaults
ProjectGovernance
ProjectLaunch
ProjectMain
ProjectNews
ProjectNotices
ProjectOptions
ProjectPapers
ProjectPlan
ProjectSecurity
ProjectSelect
ProjectSkin
ProjectSpecificPrefs
ProjectSponsors
ProjectTasks
ProofOfOwnership
Proposal_ProjectSimpleAccountCreation
ProtectionFromSpam
Proxy servers
ProxyServer
PyMw
PythonAppDev
PythonApps
PythonFramework
PythonMw
PythonMysql
QuickStart
RecentChanges
Reduce_usage_of_authenticator
Reduce_usage_of_authenticator_implementation
ReleaseNotes
RemoteInputFiles
RemoteJob
RemoteJobs
RemoteLogs
RemoteOutputFiles
RemoteOverview
Reporting client bugs
ResearchProjects
RightToErasure
RpcAuth
RpcPolicy
RpcProtocol
RpmSpec
Running Linux apps on BOINC
RuntimeEstimation
SandBox
SandboxUser
SchedMatch
Scientist interface
ScreensaverEnhancements
ScreensaverLogic
SecureHttp
SecurityIssues
SendFile
Server release notes
Server trouble‐shooting
ServerComponents
ServerDirs
ServerIntro
ServerSecurity
ServerStatus
ServerTestInstructions
ServerUpdates
Simple view
Simple attach usage
SimpleAttach
SingleJob
SingleJobImpl
SkinExamples
SoftwareAddon
SoftwareDevelopment
SoftwarePrereqsUnix
SoftwareTesting
SolarisClient
SolrIntegration
Source code map
SourceCode
SourceCodeGit
SourceCodeGit_Commands
SourceCodeGit_Windows
SourceCodeGit_WindowsKeygen
SourceCodeGit_WorkFlow
SourceCodeSvn
Sporadic Applications
Standard assimilators
Standard validators
StartTool
Starting BOINC on boot (Unix)
StatsXml
StatusApi
StolenComputers
Stop or start BOINC daemon after boot
StripChart
StyleSheets
SuperHost
TeamDiscussion
TeamImport
Teams
TemplateImages
TermsOfUse
The BOINC out of box experience
The BOINC test drive
ToolUpgrade
Tools for MacOS
TranslateIntro
TranslateProject
Translate_Coordination
TranslationSystem
TreeThreader
TrickleApi
TrickleImpl
TrickleMessages
TroubleshootClient
TroubleshootClient_New
Troubleshooting
Tutorial_BOINCApplicationDevelopmentLifecycle
Tutorial_DeployingVMApplications
UnixClientPackage
UnixProjectPackage
UpdateVersions
UploadStatistics
Usage rules
User manual
UserJobs
UserOptInConsent
Using BOINC with modem, ISDN and VPN connections
UsingSvn
ValidationLowLevel
Validators in C
Validators in scripting languages
Validators
VboxApps
Vboxwrapper release notes
VersionDiff
VersionHistory
VersionPathSorter
VirtualBox Plan
VirtualBox
VirtualCampusSupercomputerCenter
VirtualMachines
Virtualbox Shared Directories
VmApps
VmCompatibility
VmServer
Volunteer
VolunteerComputing
VolunteerDataArchival
VolunteerRecruit
VolunteerStorage
WSL apps
WatchDog
Weak account key
WebCache
WebConfig
WebForum
WebResources
WebRpc
WebSubmit
WebTemplateProposal
WhyUseBoinc
WikiTodo
WinMulticore
WindowsIssues
WordPressInt
WorkDistribution
WorkFetchMaxConcurrent
WorkGeneration
WorkShop07
WorkShop07_BoincGrid
WorkShop07_BoincSched
WorkShop07_InterpretedApps
WorkShop07_PubBoincOne
WorkShop07_PubBoincTwo
WorkShop07_SecurityGroup
WorkShop07_SimplifyApp
WorkShop07_Summary
WorkShop07_VirtualMachines
WorkShop07_WebCode
WorkShop08
WorkShop08_WorkshopProceedings
WorkShop09
WorkShop09_BatchSched
WorkShop09_InterprocComm
WorkShop09_ScientistUsability
WorkShop09_UserIssues
WorkShop09_VmApps
WorkShop10
WorkShop10_VmApps
WorkShop10_VolunteerIssues
WorkShop11
WorkShop11_HackFest
WorkShop11_HackFest_Android
WorkShop11_MultiUser
WorkShop12
WorkShop12_WorkshopSummary
WorkShop13
WorkShop13_HackfestNotes
WorkShop14
WorkShop18
WorkShop19
Worker release notes
WorldWideLexicon
Wrapper release notes
WrapperApp
XaddTool
XmlFormat
XmlNotes
XmlStats
test_RunningBoinc
4
ValidationLowLevel
David Anderson edited this page 2024-01-11 12:17:08 -08:00
Table of Contents
Low-level validator framework
BOINC's simple validator framework is sufficient in almost all cases. If for some reason you need more control, you can use the low-level framework (on which the simple framework is based).
To make a validator program using the low-level framework, link validator.cpp with two application-specific functions:
int check_set(
vector<RESULT> results, DB_WORKUNIT& wu, int& canonicalid,
double& credit, bool& retry
);
- check_set() takes a set of results (all with outcome=SUCCESS). It reads and compares their output files. If there is a quorum of matching results, it selects one of them as the canonical result, returning its ID. In this case it also returns the credit to be granted for correct results for this workunit.
- If, when an output file for a result has a nonrecoverable error (e.g. the directory is there but the file isn't, or the file is present but has invalid contents), then it must set the result's outcome (in memory, not database) to outcome=RESULT_OUTCOME_VALIDATE_ERROR and validate_state=VALIDATE_STATE_INVALID.
Use BOINC's back-end utility functions (in sched/validate_util.cpp) to get file pathnames and to distinguish recoverable and nonrecoverable file-open errors.
- If a canonical result is found, check_set() must set the validate_state field of each non-ERROR result (in memory, not database) to either validate_state=VALIDATE_STATE_VALID or validate_state=VALIDATE_STATE_INVALID.
- If a recoverable error occurs while reading output files (e.g. a directory wasn't visible due to NFS mount failure) then check_set() should return retry=true. This tells the validator to arrange for this WU to be processed again in a few hours.
- check_set() should return nonzero if a major error occurs. This tells the validator to write an error message and exit.
int check_pair(RESULT& new_result, RESULT& canonical_result, bool& retry);
- check_pair() compares a new result to the canonical result. In the absence of errors, it sets the new result's validate_state to either VALIDATE_STATE_INVALID or VALIDATE_STATE_VALID.
- If it has a nonrecoverable error reading an output file of either result, or if the new result's output file is invalid, it must set the new result's outcome (in memory, not database) to VALIDATE_ERROR.
- If it has a recoverable error while reading an output file of either result, it returns retry=true, which causes the validator to arrange for the WU to be examined again in a few hours.
- check_pair() should return nonzero if a major error occurs. This tells the validator to write an error message and exit.
Neither function should delete files or access the BOINC database.
Examples of these two functions may be found in validate_util2.cpp, which implements the simple validator framework.
Pseudocode
int check_set(
vector<RESULT> 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 result's output files can be read
and one or more of those files contains erroneous or
invalid or incorrect output, i.e. bad file syntax)
{
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 three categories above. There are M of these. If the syntax pass
has been skipped, then M == N.
if (M < wu.min_quorum)
{
don't modify canonicalid;
don't 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