/* * Unlocks the device with the passphrase specified. */ int nvm_unlock_device(const NVM_UID device_uid, const NVM_PASSPHRASE passphrase, const NVM_SIZE passphrase_len) { COMMON_LOG_ENTRY(); int rc = NVM_SUCCESS; struct device_discovery discovery; // check user has permission to make changes if (check_caller_permissions() != COMMON_SUCCESS) { rc = NVM_ERR_INVALIDPERMISSIONS; } else if (!is_supported_driver_available()) { rc = NVM_ERR_BADDRIVER; } else if ((rc = IS_NVM_FEATURE_SUPPORTED(modify_device_security)) != NVM_SUCCESS) { COMMON_LOG_ERROR("Modifying " NVM_DIMM_NAME " security is not supported."); } else if (device_uid == NULL) { COMMON_LOG_ERROR("Invalid parameter, device_uid is NULL"); rc = NVM_ERR_INVALIDPARAMETER; } else if (((rc = check_passphrase(passphrase, passphrase_len)) == NVM_SUCCESS) && ((rc = exists_and_manageable(device_uid, &discovery, 1)) == NVM_SUCCESS) && ((rc = check_unlock_device_capable(device_uid)) == NVM_SUCCESS)) { if ((rc = security_change_prepare(&discovery, passphrase, passphrase_len)) == NVM_SUCCESS) { // send a pass through command to unlock the device struct pt_payload_passphrase input_payload; memset(&input_payload, 0, sizeof (input_payload)); s_strncpy(input_payload.passphrase_current, NVM_PASSPHRASE_LEN, passphrase, passphrase_len); struct fw_cmd cmd; memset(&cmd, 0, sizeof (struct fw_cmd)); cmd.device_handle = discovery.device_handle.handle; cmd.opcode = PT_SET_SEC_INFO; cmd.sub_opcode = SUBOP_UNLOCK_UNIT; cmd.input_payload_size = sizeof (input_payload); cmd.input_payload = &input_payload; rc = ioctl_passthrough_cmd(&cmd); s_memset(&input_payload, sizeof (input_payload)); // clear any device context - security state has likely changed invalidate_devices(); } } COMMON_LOG_EXIT_RETURN_I(rc); return rc; }
/* * Erases the data on the device specified. */ int nvm_erase_device(const NVM_UID device_uid, const NVM_PASSPHRASE passphrase, const NVM_SIZE passphrase_len) { COMMON_LOG_ENTRY(); int rc = NVM_SUCCESS; struct device_discovery discovery; // check user has permission to make changes if (check_caller_permissions() != COMMON_SUCCESS) { rc = NVM_ERR_INVALIDPERMISSIONS; } else if (!is_supported_driver_available()) { rc = NVM_ERR_BADDRIVER; } else if ((rc = IS_NVM_FEATURE_SUPPORTED(modify_device_security)) != NVM_SUCCESS) { COMMON_LOG_ERROR("Modifying " NVM_DIMM_NAME " security is not supported."); } else if (device_uid == NULL) { COMMON_LOG_ERROR("Invalid parameter, device_uid is NULL"); rc = NVM_ERR_INVALIDPARAMETER; } else if ((rc = exists_and_manageable(device_uid, &discovery, 1)) == NVM_SUCCESS) { if (discovery.security_capabilities.passphrase_capable) { // check passphrase length if (check_passphrase(passphrase, passphrase_len) != NVM_SUCCESS) { rc = NVM_ERR_BADPASSPHRASE; } // verify device is in the right state to accept a secure erase else if ((rc = security_change_prepare(&discovery, passphrase, passphrase_len)) == NVM_SUCCESS) { rc = secure_erase(passphrase, passphrase_len, &discovery); // clear any device context - security state has likely changed invalidate_devices(); } } else { COMMON_LOG_ERROR("Invalid parameter. " "Crypto scramble erase is not valid in the current security state"); rc = NVM_ERR_INVALIDPARAMETER; } } COMMON_LOG_EXIT_RETURN_I(rc); return rc; }
/* * Disables data at rest security and removes the passphrase. * The device will be unlocked if it is currently locked. */ int nvm_remove_passphrase(const NVM_UID device_uid, const NVM_PASSPHRASE passphrase, const NVM_SIZE passphrase_len) { COMMON_LOG_ENTRY(); int rc = NVM_SUCCESS; struct device_discovery discovery; // check user has permission to make changes if (check_caller_permissions() != COMMON_SUCCESS) { rc = NVM_ERR_INVALIDPERMISSIONS; } else if (!is_supported_driver_available()) { rc = NVM_ERR_BADDRIVER; } else if ((rc = IS_NVM_FEATURE_SUPPORTED(modify_device_security)) != NVM_SUCCESS) { COMMON_LOG_ERROR("Modifying " NVM_DIMM_NAME " security is not supported."); } else if (device_uid == NULL) { COMMON_LOG_ERROR("Invalid parameter, device_uid is NULL"); rc = NVM_ERR_INVALIDPARAMETER; } else if (((rc = check_passphrase(passphrase, passphrase_len)) == NVM_SUCCESS) && ((rc = exists_and_manageable(device_uid, &discovery, 1)) == NVM_SUCCESS) && ((rc = check_passphrase_capable(device_uid)) == NVM_SUCCESS) && ((rc = security_change_prepare(&discovery, passphrase, passphrase_len)) == NVM_SUCCESS)) { // send a pass through command to disable security struct pt_payload_passphrase input_payload; memset(&input_payload, 0, sizeof (input_payload)); s_strncpy(input_payload.passphrase_current, NVM_PASSPHRASE_LEN, passphrase, passphrase_len); struct fw_cmd cmd; memset(&cmd, 0, sizeof (struct fw_cmd)); cmd.device_handle = discovery.device_handle.handle; cmd.opcode = PT_SET_SEC_INFO; cmd.sub_opcode = SUBOP_DISABLE_PASS; cmd.input_payload_size = sizeof (input_payload); cmd.input_payload = &input_payload; rc = ioctl_passthrough_cmd(&cmd); if (rc == NVM_SUCCESS) { // Log an event indicating we successfully removed the passphrase NVM_EVENT_ARG uid_arg; uid_to_event_arg(device_uid, uid_arg); log_mgmt_event(EVENT_SEVERITY_INFO, EVENT_CODE_MGMT_SECURITY_PASSWORD_REMOVED, device_uid, 0, // no action required uid_arg, NULL, NULL); } s_memset(&input_payload, sizeof (input_payload)); // clear any device context - security state has likely changed invalidate_devices(); } COMMON_LOG_EXIT_RETURN_I(rc); return rc; }
bool check_passphrase(ustring const& correct_hash, sstring const& passphrase, ustring const& indata) { return check_passphrase(correct_hash, sstring2ustring(passphrase), indata); }