void perform_zone_export(int sockfd, engineconfig_type *config, const char *zone) { GOOGLE_PROTOBUF_VERIFY_VERSION; OrmConnRef conn; if (!ods_orm_connect(sockfd, config, conn)) return; // error already reported. { OrmTransaction transaction(conn); if (!transaction.started()) ODS_LOG_AND_RETURN("transaction not started"); { OrmResultRef rows; ods::keystate::KeyStateExport kexport; std::string qzone; if (!OrmQuoteStringValue(conn, std::string(zone), qzone)) ODS_LOG_AND_RETURN("quoting string value failed"); if (!OrmMessageEnumWhere(conn,kexport.zone().descriptor(), rows,"name = %s",qzone.c_str())) ODS_LOG_AND_RETURN("message enumeration failed"); for (bool next=OrmFirst(rows); next; next=OrmNext(rows)) { if (!OrmGetMessage(rows, *kexport.mutable_zone(), true)) ODS_LOG_AND_CONTINUE("reading zone from database failed"); if (!write_pb_message_to_xml_fd(kexport.mutable_zone(),sockfd)) ODS_LOG_AND_CONTINUE("writing message to xml file failed"); } } } }
void perform_keystate_ds_retract(int sockfd, engineconfig_type *config, const char *zone, const char *id, int bauto) { GOOGLE_PROTOBUF_VERIFY_VERSION; OrmConnRef conn; if (ods_orm_connect(sockfd, config, conn)) { // Evaluate parameters and retract keys from the parent when instructed to. if (zone || id || bauto) retract_keys(conn,sockfd,zone,id,config->datastore, config->delegation_signer_retract_command); else list_keys_retract(conn,sockfd,config->datastore); } }
void perform_update_hsmkeys(int sockfd, engineconfig_type *config, int bManual) { // check that we are using a compatible protobuf version. GOOGLE_PROTOBUF_VERIFY_VERSION; OrmConnRef conn; if (!ods_orm_connect(sockfd, config, conn)) return; // errors have already been reported. // Go through all the keys in HSMs and import them if they are // not already present if (bManual) { ods_printf(sockfd, "Database set to: %s\n", config->datastore); // DEPRECATED, key state import should selectively import keys. import_all_keys_from_all_hsms(sockfd,conn); } }
void perform_keystate_export(int sockfd, engineconfig_type *config, const char *zone, int bds) { #define LOG_AND_RETURN(errmsg) do { ods_log_error_and_printf(\ sockfd,module_str,errmsg); return; } while (0) #define LOG_AND_RETURN_1(errmsg,param) do { ods_log_error_and_printf(\ sockfd,module_str,errmsg,param); return; } while (0) GOOGLE_PROTOBUF_VERIFY_VERSION; OrmConnRef conn; if (!ods_orm_connect(sockfd, config, conn)) return; // error already reported. { OrmTransactionRW transaction(conn); if (!transaction.started()) LOG_AND_RETURN("transaction not started"); std::string qzone; if (!OrmQuoteStringValue(conn, std::string(zone), qzone)) LOG_AND_RETURN("quoting string value failed"); { OrmResultRef rows; ::ods::keystate::EnforcerZone enfzone; if (!OrmMessageEnumWhere(conn,enfzone.descriptor(), rows,"name = %s",qzone.c_str())) LOG_AND_RETURN("zone enumeration failed"); if (!OrmFirst(rows)) { ods_printf(sockfd,"zone %s not found\n",zone); return; } OrmContextRef context; if (!OrmGetMessage(rows, enfzone, /*zones + keys*/true, context)) LOG_AND_RETURN("retrieving zone from database failed"); // we no longer need the query result, so release it. rows.release(); // Retrieve the dnskey ttl from the policy associated with the zone. ::ods::kasp::Policy policy; if (!load_kasp_policy(conn, enfzone.policy(), policy)) LOG_AND_RETURN_1("policy %s not found",enfzone.policy().c_str()); uint32_t dnskey_ttl = policy.keys().ttl(); bool bSubmitChanged = false; bool bRetractChanged = false; bool bKeytagChanged = false; for (int k=0; k<enfzone.keys_size(); ++k) { const ::ods::keystate::KeyData &key = enfzone.keys(k); if (key.role()==::ods::keystate::ZSK) continue; if (key.ds_at_parent()!=::ods::keystate::submit && key.ds_at_parent()!=::ods::keystate::submitted && key.ds_at_parent()!=::ods::keystate::retract && key.ds_at_parent()!=::ods::keystate::retracted ) continue; std::string dnskey; uint16_t keytag = dnskey_from_id(dnskey,key.locator().c_str(), key.role(), enfzone.name().c_str(), key.algorithm(),bds, dnskey_ttl); if (keytag) { ods_writen(sockfd, dnskey.c_str(), dnskey.size()); bSubmitChanged = key.ds_at_parent()==::ods::keystate::submit; bRetractChanged = key.ds_at_parent()==::ods::keystate::retract; bKeytagChanged = key.keytag()!=keytag; if (bSubmitChanged) { ::ods::keystate::KeyData *kd = enfzone.mutable_keys(k); kd->set_ds_at_parent(::ods::keystate::submitted); } if (bRetractChanged) { ::ods::keystate::KeyData *kd = enfzone.mutable_keys(k); kd->set_ds_at_parent(::ods::keystate::retracted); } if (bKeytagChanged) { ::ods::keystate::KeyData *kd = enfzone.mutable_keys(k); kd->set_keytag(keytag); } } else LOG_AND_RETURN_1("unable to find key with id %s", key.locator().c_str()); } if (bSubmitChanged || bRetractChanged || bKeytagChanged) { // Update the zone recursively in the database as keystates // have been changed because of the export if (!OrmMessageUpdate(context)) LOG_AND_RETURN("updating zone in the database failed"); if (!transaction.commit()) LOG_AND_RETURN("committing zone to the database failed"); } } } }
void perform_zone_del(int sockfd, engineconfig_type *config, const char *zone, int need_write_xml, bool quiet) { GOOGLE_PROTOBUF_VERIFY_VERSION; OrmConnRef conn; if (!ods_orm_connect(sockfd, config, conn)) return; // error already reported. std::string qzone; bool is_del_succeed = false; if (strlen(zone) > 0) { if (!OrmQuoteStringValue(conn, std::string(zone), qzone)) { const char *emsg = "quoting zone value failed"; ods_log_error_and_printf(sockfd,module_str,emsg); return; } } { OrmTransactionRW transaction(conn); if (!transaction.started()) { const char *emsg = "could not start database transaction"; ods_log_error_and_printf(sockfd,module_str,emsg); return; } if (qzone.empty()) { OrmResultRef rows; ::ods::keystate::EnforcerZone enfzone; std::vector<std::string> del_zones; bool ok = OrmMessageEnum(conn, enfzone.descriptor(), rows); if (!ok) { transaction.rollback(); ods_log_error("[%s] enum enforcer zone failed", module_str); return; } for (bool next=OrmFirst(rows); next; next = OrmNext(rows)) { OrmContextRef context; if (!OrmGetMessage(rows, enfzone, true, context)) { rows.release(); transaction.rollback(); ods_log_error("[%s] retrieving zone from database failed"); return; } del_zones.push_back(enfzone.name()); } rows.release(); for (std::vector<std::string>::iterator it = del_zones.begin(); it != del_zones.end(); ++it) { std::string del_zone; if (!OrmQuoteStringValue(conn, std::string(*it), del_zone)) { transaction.rollback(); const char *emsg = "quoting zone value failed"; ods_log_error_and_printf(sockfd,module_str,emsg); return; } if (!OrmMessageDeleteWhere(conn, ::ods::keystate::EnforcerZone::descriptor(), "name = %s", del_zone.c_str())) { transaction.rollback(); const char *emsg = "unable to delete zone %s"; ods_log_error_and_printf(sockfd,module_str,emsg, it->c_str()); return; } is_del_succeed = true; } } else { //find the zone OrmResultRef rows; if (!OrmMessageEnumWhere(conn, ::ods::keystate::EnforcerZone::descriptor(), rows, "name = %s", qzone.c_str())) { transaction.rollback(); ods_log_error_and_printf(sockfd, module_str, "unable to find zone %s", qzone.c_str()); return; } if (!OrmFirst(rows)) { rows.release(); transaction.rollback(); ods_log_error_and_printf(sockfd, module_str, "Couldn't find zone %s", qzone.c_str()); return; } rows.release(); if (!OrmMessageDeleteWhere(conn, ::ods::keystate::EnforcerZone::descriptor(), "name = %s", qzone.c_str())) { transaction.rollback(); const char *emsg = "unable to delete zone %s"; ods_log_error_and_printf(sockfd,module_str,emsg,qzone.c_str()); return; } is_del_succeed = true; } if (!transaction.commit()) { const char *emsg = "committing delete of zone %s to database failed"; ods_log_error_and_printf(sockfd,module_str,emsg,qzone.c_str()); return; } } // Now lets write out the required files - the internal list and optionally the zonelist.xml // Note at the moment we re-export the whole file in zonelist.xml format here but this should be optimised.... if (is_del_succeed) { if (!perform_write_signzone_file(sockfd, config)) { ods_log_error_and_printf(sockfd, module_str, "failed to write internal zonelist"); } if (need_write_xml) { if (!perform_zonelist_export_to_file(config->zonelist_filename,config)) { ods_log_error_and_printf(sockfd, module_str, "failed to write zonelist.xml"); } if (!quiet) { if (qzone.empty()) { ods_printf(sockfd, "Deleted all zones in database and zonelist.xml updated.\n"); } else { ods_printf(sockfd, "Deleted zone: %s in database and zonelist.xml updated.\n", zone); } } } else if (!quiet) { if (qzone.empty()) { ods_printf(sockfd, "Deleted all zones in database only. Use the --xml flag or run \"ods-enforcer zonelist export\" if an update of zonelist.xml is required.\n", zone); } else { ods_printf(sockfd, "Deleted zone: %s in database only. Use the --xml flag or run \"ods-enforcer zonelist export\" if an update of zonelist.xml is required.\n", zone); } } } }
void perform_update_kasp(int sockfd, engineconfig_type *config) { GOOGLE_PROTOBUF_VERIFY_VERSION; std::auto_ptr< ::ods::kasp::KaspDocument > kaspDoc; if (!load_kasp_xml(sockfd, config->policy_filename, kaspDoc)) return; // errors have already been reported. OrmConnRef conn; if (!ods_orm_connect(sockfd, config, conn)) return; // errors have already been reported. //TODO: SPEED: We should create an index on the Policy.name column // Go through the list of policies from the kasp.xml file to determine // if we need to insert new policies to the policies table. for (int i=0; i<kaspDoc->kasp().policies_size(); ++i) { const ::ods::kasp::Policy &policy = kaspDoc->kasp().policies(i); { OrmTransactionRW transaction(conn); if (!transaction.started()) { ods_log_error_and_printf(sockfd, module_str, "starting a database transaction for " "updating a policy failed"); return; } std::string qpolicy; if (!OrmQuoteStringValue(conn, policy.name(), qpolicy)) { ods_log_error_and_printf(sockfd, module_str, "quoting a string failed"); return; } // delete the existing policy from the database if (!OrmMessageDeleteWhere(conn, policy.descriptor(), "name=%s",qpolicy.c_str())) { ods_log_error_and_printf(sockfd, module_str, "failed to delete policy with " "name %s",policy.name().c_str()); return; } // insert the policy we read from the kasp.xml file. pb::uint64 policyid; if (!OrmMessageInsert(conn, policy, policyid)) { ods_log_error_and_printf(sockfd, module_str, "inserting policy into the database failed"); return; } // commit the update policy to the database. if (!transaction.commit()) { ods_log_error_and_printf(sockfd, module_str, "committing policy to the database failed"); return; } } } }
void perform_keystate_list(int sockfd, engineconfig_type *config, int bverbose) { GOOGLE_PROTOBUF_VERIFY_VERSION; OrmConnRef conn; if (!ods_orm_connect(sockfd, config, conn)) return; // error already reported. { OrmTransaction transaction(conn); if (!transaction.started()) { ods_log_error("[%s] Could not start database transaction", module_str); ods_printf(sockfd, "error: Could not start database transaction\n"); return; } ::ods::keystate::EnforcerZone zone; { OrmResultRef rows; if (!OrmMessageEnum(conn, zone.descriptor(),rows)) { ods_log_error("[%s] error enumerating zones", module_str); ods_printf(sockfd, "error enumerating zones\n"); return; } ods_printf(sockfd, "Database set to: %s\n" "Keys:\n" "Zone: " "Key role: " "DS: " "DNSKEY: " "RRSIGDNSKEY: " "RRSIG: " "Pub: " "Act: " "Id:" "\n" ,config->datastore ); for (bool next=OrmFirst(rows); next; next=OrmNext(rows)) { if (!OrmGetMessage(rows, zone, true)) { ods_log_error("[%s] error reading zone", module_str); ods_printf(sockfd, "error reading zone\n"); return; } for (int k=0; k<zone.keys_size(); ++k) { const ::ods::keystate::KeyData &key = zone.keys(k); std::string keyrole = keyrole_Name(key.role()); std::string ds_rrstate = rrstate_Name(key.ds().state()); std::string dnskey_rrstate = rrstate_Name(key.dnskey().state()); std::string rrsigdnskey_rrstate = rrstate_Name(key.rrsigdnskey().state()); std::string rrsig_rrstate = rrstate_Name(key.rrsig().state()); ods_printf(sockfd, "%-31s %-13s %-12s %-12s %-12s %-12s %d %4d %s\n", zone.name().c_str(), keyrole.c_str(), ds_rrstate.c_str(), dnskey_rrstate.c_str(), rrsigdnskey_rrstate.c_str(), rrsig_rrstate.c_str(), key.publish(), key.active_ksk()||key.active_zsk(), key.locator().c_str() ); } } } } }