static NaClValidationStatus ApplyDfaValidator_x86_64( uintptr_t guest_addr, uint8_t *data, size_t size, int stubout_mode, uint32_t flags, int readonly_text, const NaClCPUFeatures *f, const struct NaClValidationMetadata *metadata, struct NaClValidationCache *cache) { /* TODO(jfb) Use a safe cast here. */ NaClCPUFeaturesX86 *cpu_features = (NaClCPUFeaturesX86 *) f; enum NaClValidationStatus status = NaClValidationFailed; void *query = NULL; struct StubOutCallbackData callback_data; callback_data.flags = flags; callback_data.did_rewrite = 0; UNREFERENCED_PARAMETER(guest_addr); if (stubout_mode) return NaClValidationFailedNotImplemented; if (!NaClArchSupportedX86(cpu_features)) return NaClValidationFailedCpuNotSupported; if (size & kBundleMask) return NaClValidationFailed; /* * If the validation caching interface is available and it would be * inexpensive to do so, perform a query. */ if (cache != NULL && NaClCachingIsInexpensive(cache, metadata)) query = cache->CreateQuery(cache->handle); if (query != NULL) { const char validator_id[] = "x86-64 dfa"; cache->AddData(query, (uint8_t *) validator_id, sizeof(validator_id)); cache->AddData(query, (uint8_t *) cpu_features, sizeof(*cpu_features)); NaClAddCodeIdentity(data, size, metadata, cache, query); if (cache->QueryKnownToValidate(query)) { cache->DestroyQuery(query); return NaClValidationSucceeded; } } if (readonly_text) { if (ValidateChunkAMD64(data, size, 0 /*options*/, cpu_features, NaClDfaProcessValidationError, NULL)) status = NaClValidationSucceeded; } else { if (ValidateChunkAMD64(data, size, 0 /*options*/, cpu_features, NaClDfaStubOutUnsupportedInstruction, &callback_data)) status = NaClValidationSucceeded; } if (status != NaClValidationSucceeded && errno == ENOMEM) status = NaClValidationFailedOutOfMemory; /* Cache the result if validation succeeded and the code was not modified. */ if (query != NULL) { if (status == NaClValidationSucceeded && callback_data.did_rewrite == 0) cache->SetKnownToValidate(query); cache->DestroyQuery(query); } return status; }
static NaClValidationStatus ApplyValidator_x86_32( uintptr_t guest_addr, uint8_t *data, size_t size, int stubout_mode, int readonly_text, const NaClCPUFeatures *f, const struct NaClValidationMetadata *metadata, struct NaClValidationCache *cache) { /* TODO(jfb) Use a safe cast here. */ const NaClCPUFeaturesX86 *cpu_features = (NaClCPUFeaturesX86 *) f; struct NCValidatorState *vstate; int validator_result = 0; void *query = NULL; /* Check that the given parameter values are supported. */ if (stubout_mode && readonly_text) return NaClValidationFailedNotImplemented; if (!NaClArchSupportedX86(cpu_features)) return NaClValidationFailedCpuNotSupported; /* Don't cache in stubout mode. */ if (stubout_mode) cache = NULL; /* If the validation caching interface is available, perform a query. */ if (cache != NULL) query = cache->CreateQuery(cache->handle); if (query != NULL) { const char validator_id[] = "x86-32"; cache->AddData(query, (uint8_t *) validator_id, sizeof(validator_id)); cache->AddData(query, (uint8_t *) cpu_features, sizeof(*cpu_features)); NaClAddCodeIdentity(data, size, metadata, cache, query); if (cache->QueryKnownToValidate(query)) { cache->DestroyQuery(query); return NaClValidationSucceeded; } } /* Init then validator state. */ /* TODO(ncbray) make "detailed" a parameter. */ if (stubout_mode) { vstate = NCValidateInitDetailed(guest_addr, size, cpu_features); } else { vstate = NCValidateInit(guest_addr, size, readonly_text, cpu_features); } if (vstate == NULL) { if (query != NULL) cache->DestroyQuery(query); return NaClValidationFailedOutOfMemory; } NCValidateSetStubOutMode(vstate, stubout_mode); /* Validate. */ NCValidateSegment(data, guest_addr, size, vstate); validator_result = NCValidateFinish(vstate); /* Cache the result if validation succeeded and the code was not modified. */ if (query != NULL) { if (validator_result == 0 && !NCValidatorDidStubOut(vstate)) cache->SetKnownToValidate(query); cache->DestroyQuery(query); } NCValidateFreeState(&vstate); return (validator_result == 0 || stubout_mode) ? NaClValidationSucceeded : NaClValidationFailed; }