blob: 4dd518db00620b5aa57ecc5080b20c740ea40fd5 [file] [log] [blame]
Zhiyi Zhang08e0e982017-03-01 10:10:42 -08001/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
Davide Pesaventod4496f72019-01-19 20:23:50 -05002/*
3 * Copyright (c) 2017-2019, Regents of the University of California.
Zhiyi Zhang08e0e982017-03-01 10:10:42 -08004 *
5 * This file is part of ndncert, a certificate management system based on NDN.
6 *
7 * ndncert is free software: you can redistribute it and/or modify it under the terms
8 * of the GNU General Public License as published by the Free Software Foundation, either
9 * version 3 of the License, or (at your option) any later version.
10 *
11 * ndncert is distributed in the hope that it will be useful, but WITHOUT ANY
12 * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
13 * PARTICULAR PURPOSE. See the GNU General Public License for more details.
14 *
15 * You should have received copies of the GNU General Public License along with
16 * ndncert, e.g., in COPYING.md file. If not, see <http://www.gnu.org/licenses/>.
17 *
18 * See AUTHORS.md for complete list of ndncert authors and contributors.
19 */
20
21#include "ca-module.hpp"
Zhiyi Zhang343cdfb2018-01-17 12:04:28 -080022#include "challenge-module.hpp"
Zhiyi Zhang08e0e982017-03-01 10:10:42 -080023
Davide Pesaventod4496f72019-01-19 20:23:50 -050024#include <ndn-cxx/face.hpp>
25#include <ndn-cxx/security/v2/key-chain.hpp>
26
27#include <boost/asio/ip/tcp.hpp>
28#if BOOST_VERSION < 106700
Zhiyi Zhang343cdfb2018-01-17 12:04:28 -080029#include <boost/date_time/posix_time/posix_time_duration.hpp>
Davide Pesaventod4496f72019-01-19 20:23:50 -050030#endif
31#include <boost/program_options/options_description.hpp>
32#include <boost/program_options/parsers.hpp>
33#include <boost/program_options/variables_map.hpp>
34
35#include <iostream>
Zhiyi Zhang08e0e982017-03-01 10:10:42 -080036
37namespace ndn {
38namespace ndncert {
39
Davide Pesaventod4496f72019-01-19 20:23:50 -050040static int
Zhiyi Zhang08e0e982017-03-01 10:10:42 -080041main(int argc, char* argv[])
42{
Davide Pesaventod4496f72019-01-19 20:23:50 -050043 std::string configFilePath(SYSCONFDIR "/ndncert/ca.conf");
44 std::string repoHost("localhost");
45 std::string repoPort("7376");
46 bool wantRepoOut = false;
Zhiyi Zhang343cdfb2018-01-17 12:04:28 -080047
48 namespace po = boost::program_options;
Davide Pesaventod4496f72019-01-19 20:23:50 -050049 po::options_description optsDesc("Options");
50 optsDesc.add_options()
51 ("help,h", "print this help message and exit")
52 ("config-file,c", po::value<std::string>(&configFilePath)->default_value(configFilePath),
53 "path to configuration file")
54 ("repo-output,r", po::bool_switch(&wantRepoOut),
55 "when enabled, all issued certificates will be published to repo-ng")
56 ("repo-host,H", po::value<std::string>(&repoHost)->default_value(repoHost), "repo-ng host")
57 ("repo-port,P", po::value<std::string>(&repoPort)->default_value(repoPort), "repo-ng port");
Zhiyi Zhang343cdfb2018-01-17 12:04:28 -080058
Zhiyi Zhang08e0e982017-03-01 10:10:42 -080059 po::variables_map vm;
60 try {
Davide Pesaventod4496f72019-01-19 20:23:50 -050061 po::store(po::parse_command_line(argc, argv, optsDesc), vm);
Zhiyi Zhang08e0e982017-03-01 10:10:42 -080062 po::notify(vm);
63 }
Davide Pesaventod4496f72019-01-19 20:23:50 -050064 catch (const po::error& e) {
65 std::cerr << "ERROR: " << e.what() << std::endl;
66 return 2;
Zhiyi Zhang08e0e982017-03-01 10:10:42 -080067 }
Davide Pesaventod4496f72019-01-19 20:23:50 -050068 catch (const boost::bad_any_cast& e) {
69 std::cerr << "ERROR: " << e.what() << std::endl;
70 return 2;
71 }
72
Zhiyi Zhang08e0e982017-03-01 10:10:42 -080073 if (vm.count("help") != 0) {
Davide Pesaventod4496f72019-01-19 20:23:50 -050074 std::cout << "Usage: " << argv[0] << " [options]\n"
75 << "\n"
76 << optsDesc;
Zhiyi Zhang08e0e982017-03-01 10:10:42 -080077 return 0;
78 }
79
80 Face face;
81 security::v2::KeyChain keyChain;
82 CaModule ca(face, keyChain, configFilePath);
Zhiyi Zhang08e0e982017-03-01 10:10:42 -080083
Zhiyi Zhang1c0bd372017-12-18 18:32:55 +080084 ca.setRecommendCaHandler(Name("/ndn"),
85 [] (const std::string& input, const std::list<Name>& list) -> std::tuple<Name, std::string> {
86 Name recommendedCa;
87 std::string identity;
88 for (auto caName : list) {
89 std::string univName = readString(caName.get(-1));
90 if (input.find(univName) != std::string::npos) {
91 recommendedCa = caName;
92 identity = input.substr(0, input.find("@"));
93 break;
94 }
95 }
96 return std::make_tuple(recommendedCa, identity);
97 });
98
Davide Pesaventod4496f72019-01-19 20:23:50 -050099 if (wantRepoOut) {
100 for (const auto& caItem : ca.getCaConf().m_caItems) {
Zhiyi Zhang343cdfb2018-01-17 12:04:28 -0800101 ca.setStatusUpdateCallback(caItem.m_caName,
102 [&] (const CertificateRequest& request) {
103 if (request.getStatus() == ChallengeModule::SUCCESS) {
104 auto issuedCert = request.getCert();
Davide Pesaventod4496f72019-01-19 20:23:50 -0500105 boost::asio::ip::tcp::iostream requestStream;
Zhiyi Zhang8ce677b2018-07-13 14:44:06 -0700106#if BOOST_VERSION >= 106700
107 requestStream.expires_after(std::chrono::seconds(3));
108#else
Zhiyi Zhang343cdfb2018-01-17 12:04:28 -0800109 requestStream.expires_from_now(boost::posix_time::seconds(3));
Zhiyi Zhang8ce677b2018-07-13 14:44:06 -0700110#endif // BOOST_VERSION >= 106700
Zhiyi Zhang343cdfb2018-01-17 12:04:28 -0800111 requestStream.connect(repoHost, repoPort);
112 if (!requestStream) {
113 std::cerr << "ERROR: Cannot publish certificate to repo-ng"
Davide Pesaventod4496f72019-01-19 20:23:50 -0500114 << " (" << requestStream.error().message() << ")" << std::endl;
Zhiyi Zhang343cdfb2018-01-17 12:04:28 -0800115 return;
116 }
117 requestStream.write(reinterpret_cast<const char*>(issuedCert.wireEncode().wire()),
118 issuedCert.wireEncode().size());
119 }
Davide Pesaventod4496f72019-01-19 20:23:50 -0500120 });
Zhiyi Zhang343cdfb2018-01-17 12:04:28 -0800121 }
122 }
123
Zhiyi Zhang1c0bd372017-12-18 18:32:55 +0800124 face.processEvents();
Zhiyi Zhang08e0e982017-03-01 10:10:42 -0800125 return 0;
126}
127
128} // namespace ndncert
129} // namespace ndn
130
131int
132main(int argc, char* argv[])
133{
134 return ndn::ndncert::main(argc, argv);
135}