1 /*************************************************************************
3 * Copyright 2020 highstreet technologies GmbH and others
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
16 ***************************************************************************/
20 #include "nc_config.h"
21 #include "utils/log_utils.h"
22 #include "utils/sys_utils.h"
23 #include "utils/http_client.h"
30 #include <libyang/libyang.h>
31 #include "core/session.h"
32 #include "core/framework.h"
34 #define GEN_KEY_SCRIPT "/home/netconf/.ssh/generate-ssh-keys.sh"
35 #define KS_CERT_NAME "melacon_server_cert"
36 #define SERVER_PRIVATE_KEY_PATH "/home/netconf/.ssh/melacon.server.key"
37 #define SERVER_PUBLIC_KEY_PATH "/home/netconf/.ssh/melacon.server.key.pub.pem"
38 #define SERVER_CERT_PATH "/home/netconf/.ssh/melacon.server.crt"
39 #define CA_CERT_PATH "/home/netconf/.ssh/ca.pem"
41 static int nc_config_netconf_port = STANDARD_NETCONF_PORT;
43 static int load_ssh_keys(sr_session_ctx_t *session);
44 static int load_trusted_certificates(sr_session_ctx_t *session);
45 static int configure_nacm(sr_session_ctx_t *session);
46 static int create_ssh_listen_endpoints(struct lyd_node *netconf_node, int ssh_connections);
47 static int create_tls_listen_endpoints(struct lyd_node *netconf_node, int tls_connections);
48 static int configure_endpoints_connections(sr_session_ctx_t *session);
50 int netconf_configure(void) {
53 nc_config_netconf_port = STANDARD_NETCONF_PORT;
55 //check if was already ran
57 rc = sr_get_item(session_running, "/ietf-keystore:keystore", 0, &val);
59 log_error("sr_get_item failed\n");
60 return NTS_ERR_FAILED;
63 bool already_done = (val->dflt == false);
67 log_add_verbose(2, "netconf_configure() already ran, skipping...\n");
71 // generate and load private keys
72 log_add_verbose(1, "ietf-keystore startup datastore configuration...");
73 rc = load_ssh_keys(session_running);
75 log_error("could not load SSH keys\n");
76 return NTS_ERR_FAILED;
78 log_add(1, LOG_COLOR_BOLD_GREEN"done\n"LOG_COLOR_RESET);
80 // load trusted certificates
81 log_add_verbose(1, "ietf-truststore startup datastore configuration...");
82 rc = load_trusted_certificates(session_running);
84 log_error("could not load trusted certificates\n");
85 return NTS_ERR_FAILED;
87 log_add(1, LOG_COLOR_BOLD_GREEN"done\n"LOG_COLOR_RESET);
90 log_add_verbose(1, "configuring NACM...");
91 rc = configure_nacm(session_running);
93 log_error("could not configure NACM\n");
94 return NTS_ERR_FAILED;
96 log_add(1, LOG_COLOR_BOLD_GREEN"done\n"LOG_COLOR_RESET);
98 // configure SSH connections
99 log_add_verbose(1, "Configuring connection endpoints...");
100 rc = configure_endpoints_connections(session_running);
102 log_error("could not configure endpoint connections forNETCONF Server\n");
103 return NTS_ERR_FAILED;
105 log_add(1, LOG_COLOR_BOLD_GREEN"done\n"LOG_COLOR_RESET);
110 static int load_ssh_keys(sr_session_ctx_t *session) {
115 struct lyd_node *rcl = 0;
117 rc = system(GEN_KEY_SCRIPT);
119 log_error("could not generate the SSH keys\n");
120 return NTS_ERR_FAILED;
123 struct lys_module *module;
124 module = (struct lys_module *)ly_ctx_get_module(session_context, "ietf-keystore", 0, 0);
126 log_error("could not get module %s from context\n", "ietf-keystore");
127 return NTS_ERR_FAILED;
130 struct lyd_node *keystore_node = 0;
131 keystore_node = lyd_new(NULL, module, "keystore");
132 if(keystore_node == 0) {
133 log_error("could not create a new lyd_node\n");
134 return NTS_ERR_FAILED;
137 sprintf(xpath, "/ietf-keystore:keystore/asymmetric-keys/asymmetric-key[name='%s']/algorithm", KS_KEY_NAME);
138 rcl = lyd_new_path(keystore_node, 0, xpath, "rsa2048", 0, LYD_PATH_OPT_NOPARENTRET);
140 log_error("could not created yang path\n");
141 return NTS_ERR_FAILED;
144 char *private_key = read_key(SERVER_PRIVATE_KEY_PATH);
145 if(private_key == 0) {
146 log_error("could not read the private key from path=%s\n", SERVER_PRIVATE_KEY_PATH);
147 return NTS_ERR_FAILED;
149 log_add_verbose(2, "Private Key that was built: \n%s\n", private_key);
151 sprintf(xpath, "/ietf-keystore:keystore/asymmetric-keys/asymmetric-key[name='%s']/private-key", KS_KEY_NAME);
152 rcl = lyd_new_path(keystore_node, 0, xpath, private_key, 0, LYD_PATH_OPT_NOPARENTRET);
154 log_error("could not created yang path\n");
155 return NTS_ERR_FAILED;
160 char *public_key = read_key(SERVER_PUBLIC_KEY_PATH);
161 if(public_key == 0) {
162 log_error("could not read the public key from path=%s\n", SERVER_PUBLIC_KEY_PATH);
163 return NTS_ERR_FAILED;
165 log_add_verbose(2, "Public Key that was built: \n%s\n", public_key);
167 sprintf(xpath, "/ietf-keystore:keystore/asymmetric-keys/asymmetric-key[name='%s']/public-key", KS_KEY_NAME);
168 rcl = lyd_new_path(keystore_node, 0, xpath, public_key, 0, LYD_PATH_OPT_NOPARENTRET);
170 log_error("could not created yang path\n");
171 return NTS_ERR_FAILED;
176 char *certificate = read_key(SERVER_CERT_PATH);
177 if(certificate == 0) {
178 log_error("could not read the certificate from path=%s\n", SERVER_CERT_PATH);
179 return NTS_ERR_FAILED;
181 log_add_verbose(2, "Certificate that was built: \n%s\n", certificate);
183 sprintf(xpath, "/ietf-keystore:keystore/asymmetric-keys/asymmetric-key[name='%s']/certificates/certificate[name='%s']/cert", KS_KEY_NAME, KS_CERT_NAME);
184 rcl = lyd_new_path(keystore_node, 0, xpath, certificate, 0, LYD_PATH_OPT_NOPARENTRET);
186 log_error("could not created yang path\n");
187 return NTS_ERR_FAILED;
192 rc = sr_edit_batch(session, keystore_node, "replace");
193 if(rc != SR_ERR_OK) {
194 log_error("could not edit batch on datastore\n");
195 return NTS_ERR_FAILED;
198 rc = sr_validate(session, "ietf-keystore", 0);
199 if(rc != SR_ERR_OK) {
200 struct ly_err_item *err = ly_err_first(session_context);
201 log_error("sr_validate issues on STARTUP: %s\n", err->msg);
205 rc = sr_apply_changes(session, 0, 0);
206 if(rc != SR_ERR_OK) {
207 log_error("could not apply changes on datastore\n");
208 return NTS_ERR_FAILED;
214 static int load_trusted_certificates(sr_session_ctx_t *session) {
218 struct lyd_node *rcl = 0;
220 struct lyd_node *trusted_certificate_node = 0;
221 struct lys_module *module;
222 module = (struct lys_module *)ly_ctx_get_module(session_context, "ietf-truststore", 0, 0);
224 log_error("could not get module %s from context\n", "ietf-truststore");
225 return NTS_ERR_FAILED;
228 trusted_certificate_node = lyd_new(NULL, module, "truststore");
229 if(trusted_certificate_node == 0) {
230 log_error("could not create a new lyd_node\n");
231 return NTS_ERR_FAILED;
236 sprintf(xpath, "/ietf-truststore:truststore/certificates[name='clientcerts']/certificate[name='clientcert']/cert");
237 char *client_cert = read_key(CLIENT_CERT_PATH);
238 rcl = lyd_new_path(trusted_certificate_node, 0, xpath, client_cert, 0, LYD_PATH_OPT_NOPARENTRET);
240 log_error("could not created yang path\n");
241 return NTS_ERR_FAILED;
245 sprintf(xpath, "/ietf-truststore:truststore/certificates[name='cacerts']/certificate[name='cacert']/cert");
246 char *ca_cert = read_key(CA_CERT_PATH);
247 rcl = lyd_new_path(trusted_certificate_node, 0, xpath, ca_cert, 0, LYD_PATH_OPT_NOPARENTRET);
249 log_error("could not created yang path\n");
250 return NTS_ERR_FAILED;
254 rc = sr_edit_batch(session, trusted_certificate_node, "replace");
255 if(rc != SR_ERR_OK) {
256 log_error("could not edit batch on datastore\n");
257 return NTS_ERR_FAILED;
260 rc = sr_validate(session, "ietf-truststore", 0);
261 if(rc != SR_ERR_OK) {
262 struct ly_err_item *err = ly_err_first(session_context);
263 log_error("sr_validate issues on STARTUP: %s\n", err->msg);
264 return NTS_ERR_FAILED;
267 rc = sr_apply_changes(session, 0, 0);
268 if(rc != SR_ERR_OK) {
269 log_error("could not apply changes on datastore\n");
270 return NTS_ERR_FAILED;
276 static int configure_nacm(sr_session_ctx_t *session) {
280 struct lyd_node *rcl = 0;
283 struct lys_module *module = 0;
284 module = (struct lys_module *) ly_ctx_get_module(session_context, "ietf-netconf-acm", 0, 0);
286 log_error("could not get module %s from context\n", "ietf-netconf-acm");
287 return NTS_ERR_FAILED;
290 struct lyd_node *nacm_node = 0;
291 nacm_node = lyd_new(NULL, module, "nacm");
293 log_error("could not create a new lyd_node\n");
294 return NTS_ERR_FAILED;
297 sprintf(xpath, "/ietf-netconf-acm:nacm/enable-nacm");
298 rcl = lyd_new_path(nacm_node, 0, xpath, "true", 0, LYD_PATH_OPT_NOPARENTRET);
300 log_error("could not create yang path\n");
301 return NTS_ERR_FAILED;
304 sprintf(xpath, "/ietf-netconf-acm:nacm/groups/group[name='sudo']/user-name");
305 // we hardcoded here the username to be used
306 rcl = lyd_new_path(nacm_node, 0, xpath, "netconf", 0, LYD_PATH_OPT_NOPARENTRET);
308 log_error("could not create yang path\n");
309 return NTS_ERR_FAILED;
312 sprintf(xpath, "/ietf-netconf-acm:nacm/rule-list[name='sudo-rules']/group");
313 rcl = lyd_new_path(nacm_node, 0, xpath, "sudo", 0, LYD_PATH_OPT_NOPARENTRET);
315 log_error("could not create yang path\n");
316 return NTS_ERR_FAILED;
319 sprintf(xpath, "/ietf-netconf-acm:nacm/rule-list[name='sudo-rules']/rule[name='allow-all-sudo']/module-name");
320 rcl = lyd_new_path(nacm_node, 0, xpath, "*", 0, LYD_PATH_OPT_NOPARENTRET);
322 log_error("could not create yang path\n");
323 return NTS_ERR_FAILED;
326 sprintf(xpath, "/ietf-netconf-acm:nacm/rule-list[name='sudo-rules']/rule[name='allow-all-sudo']/path");
327 rcl = lyd_new_path(nacm_node, 0, xpath, "/", 0, LYD_PATH_OPT_NOPARENTRET);
329 log_error("could not create yang path\n");
330 return NTS_ERR_FAILED;
333 sprintf(xpath, "/ietf-netconf-acm:nacm/rule-list[name='sudo-rules']/rule[name='allow-all-sudo']/access-operations");
334 rcl = lyd_new_path(nacm_node, 0, xpath, "*", 0, LYD_PATH_OPT_NOPARENTRET);
336 log_error("could not create yang path\n");
337 return NTS_ERR_FAILED;
340 sprintf(xpath, "/ietf-netconf-acm:nacm/rule-list[name='sudo-rules']/rule[name='allow-all-sudo']/action");
341 rcl = lyd_new_path(nacm_node, 0, xpath, "permit", 0, LYD_PATH_OPT_NOPARENTRET);
343 log_error("could not create yang path\n");
344 return NTS_ERR_FAILED;
347 sprintf(xpath, "/ietf-netconf-acm:nacm/rule-list[name='sudo-rules']/rule[name='allow-all-sudo']/comment");
348 rcl = lyd_new_path(nacm_node, 0, xpath, "Corresponds all the rules under the sudo group as defined in O-RAN.WG4.MP.0-v05.00", 0, LYD_PATH_OPT_NOPARENTRET);
350 log_error("could not create yang path\n");
351 return NTS_ERR_FAILED;
354 rc = sr_edit_batch(session, nacm_node, "replace");
355 if(rc != SR_ERR_OK) {
356 log_error("could not edit batch on datastore\n");
357 return NTS_ERR_FAILED;
360 rc = sr_validate(session, "ietf-netconf-acm", 0);
361 if(rc != SR_ERR_OK) {
362 struct ly_err_item *err = ly_err_first(session_context);
363 log_error("sr_validate issues on STARTUP: %s\n", err->msg);
364 return NTS_ERR_FAILED;
367 rc = sr_apply_changes(session, 0, 0);
368 if(rc != SR_ERR_OK) {
369 log_error("could not apply changes on datastore\n");
370 return NTS_ERR_FAILED;
376 static int create_ssh_listen_endpoints(struct lyd_node *netconf_node, int ssh_connections) {
377 assert(netconf_node);
381 struct lyd_node *rcl = 0;
384 if(framework_environment.settings.ip_v6_enabled) {
385 sprintf(local_ip, "::");
388 sprintf(local_ip, "0.0.0.0");
391 char *public_ssh_key = read_key(SERVER_PUBLIC_SSH_KEY_PATH);
392 if(public_ssh_key == 0) {
393 log_error("could not read the public ssh key from file %s\n", SERVER_PUBLIC_SSH_KEY_PATH);
394 return NTS_ERR_FAILED;
397 char *ssh_key_string;
399 ssh_key_string = strtok(public_ssh_key, " ");
400 ssh_key_string = strtok(NULL, " ");
402 for(int i = 0; i < ssh_connections; ++i) {
403 char endpoint_name[100];
404 sprintf(endpoint_name, "mng-ssh-%d", i);
406 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/tcp-server-parameters/local-address", endpoint_name);
407 rcl = lyd_new_path(netconf_node, 0, xpath, local_ip, 0, LYD_PATH_OPT_NOPARENTRET);
409 log_error("could not created yang path\n");
410 return NTS_ERR_FAILED;
414 sprintf(local_port, "%d", nc_config_netconf_port++);
415 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/tcp-server-parameters/local-port", endpoint_name);
416 rcl = lyd_new_path(netconf_node, 0, xpath, local_port, 0, LYD_PATH_OPT_NOPARENTRET);
418 log_error("could not created yang path\n");
419 return NTS_ERR_FAILED;
422 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/tcp-server-parameters/keepalives/idle-time", endpoint_name);
423 rcl = lyd_new_path(netconf_node, 0, xpath, "1", 0, LYD_PATH_OPT_NOPARENTRET);
425 log_error("could not created yang path\n");
426 return NTS_ERR_FAILED;
429 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/tcp-server-parameters/keepalives/max-probes", endpoint_name);
430 rcl = lyd_new_path(netconf_node, 0, xpath, "10", 0, LYD_PATH_OPT_NOPARENTRET);
432 log_error("could not created yang path\n");
433 return NTS_ERR_FAILED;
436 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/tcp-server-parameters/keepalives/probe-interval", endpoint_name);
437 rcl = lyd_new_path(netconf_node, 0, xpath, "5", 0, LYD_PATH_OPT_NOPARENTRET);
439 log_error("could not created yang path\n");
440 return NTS_ERR_FAILED;
443 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/ssh-server-parameters/server-identity/host-key[name='default-key']/public-key/keystore-reference", endpoint_name);
444 rcl = lyd_new_path(netconf_node, 0, xpath, KS_KEY_NAME, 0, LYD_PATH_OPT_NOPARENTRET);
446 log_error("could not created yang path\n");
447 return NTS_ERR_FAILED;
450 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/ssh-server-parameters/client-authentication/supported-authentication-methods/publickey", endpoint_name);
451 rcl = lyd_new_path(netconf_node, 0, xpath, "", 0, LYD_PATH_OPT_NOPARENTRET);
453 log_error("could not created yang path\n");
454 return NTS_ERR_FAILED;
457 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/ssh-server-parameters/client-authentication/supported-authentication-methods/passsword", endpoint_name);
458 rcl = lyd_new_path(netconf_node, 0, xpath, "", 0, LYD_PATH_OPT_NOPARENTRET);
460 log_error("could not created yang path\n");
461 return NTS_ERR_FAILED;
464 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/ssh-server-parameters/client-authentication/supported-authentication-methods/other", endpoint_name);
465 rcl = lyd_new_path(netconf_node, 0, xpath, "interactive", 0, LYD_PATH_OPT_NOPARENTRET);
467 log_error("could not created yang path\n");
468 return NTS_ERR_FAILED;
471 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/ssh-server-parameters/client-authentication/users/user[name='netconf']/authorized-key[name='%s']/algorithm", endpoint_name, KS_KEY_NAME);
472 rcl = lyd_new_path(netconf_node, 0, xpath, "ssh-rsa", 0, LYD_PATH_OPT_NOPARENTRET);
474 log_error("could not created yang path\n");
475 return NTS_ERR_FAILED;
478 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/ssh/ssh-server-parameters/client-authentication/users/user[name='netconf']/authorized-key[name='%s']/key-data", endpoint_name, KS_KEY_NAME);
479 rcl = lyd_new_path(netconf_node, 0, xpath, ssh_key_string, 0, LYD_PATH_OPT_NOPARENTRET);
481 log_error("could not created yang path\n");
482 return NTS_ERR_FAILED;
486 free(public_ssh_key);
491 static int create_tls_listen_endpoints(struct lyd_node *netconf_node, int tls_connections) {
492 assert(netconf_node);
494 struct lyd_node *rcl = 0;
498 if(framework_environment.settings.ip_v6_enabled) {
499 sprintf(local_ip, "::");
502 sprintf(local_ip, "0.0.0.0");
505 for(int i = 0; i < tls_connections + 1; ++i) {
506 char endpoint_name[100];
511 if(i == tls_connections) {
512 //manager connection port
513 sprintf(endpoint_name, "manger-tls-internal");
514 sprintf(local_port, "%d", CLIENT_CONFIG_TLS_PORT);
517 sprintf(endpoint_name, "mng-tls-%d", i);
518 sprintf(local_port, "%d", nc_config_netconf_port++);
521 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tcp-server-parameters/local-address", endpoint_name);
522 rcl = lyd_new_path(netconf_node, 0, xpath, local_ip, 0, LYD_PATH_OPT_NOPARENTRET);
524 log_error("could not created yang path\n");
525 return NTS_ERR_FAILED;
528 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tcp-server-parameters/local-port", endpoint_name);
529 rcl = lyd_new_path(netconf_node, 0, xpath, local_port, 0, LYD_PATH_OPT_NOPARENTRET);
531 log_error("could not created yang path\n");
532 return NTS_ERR_FAILED;
535 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tcp-server-parameters/keepalives/idle-time", endpoint_name);
536 rcl = lyd_new_path(netconf_node, 0, xpath, "1", 0, LYD_PATH_OPT_NOPARENTRET);
538 log_error("could not created yang path\n");
539 return NTS_ERR_FAILED;
542 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tcp-server-parameters/keepalives/max-probes", endpoint_name);
543 rcl = lyd_new_path(netconf_node, 0, xpath, "10", 0, LYD_PATH_OPT_NOPARENTRET);
545 log_error("could not created yang path\n");
546 return NTS_ERR_FAILED;
549 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tcp-server-parameters/keepalives/probe-interval", endpoint_name);
550 rcl = lyd_new_path(netconf_node, 0, xpath, "5", 0, LYD_PATH_OPT_NOPARENTRET);
552 log_error("could not created yang path\n");
553 return NTS_ERR_FAILED;
556 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tls-server-parameters/server-identity/keystore-reference/asymmetric-key", endpoint_name);
557 rcl = lyd_new_path(netconf_node, 0, xpath, KS_KEY_NAME, 0, LYD_PATH_OPT_NOPARENTRET);
559 log_error("could not created yang path\n");
560 return NTS_ERR_FAILED;
563 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tls-server-parameters/server-identity/keystore-reference/certificate", endpoint_name);
564 rcl = lyd_new_path(netconf_node, 0, xpath, KS_CERT_NAME, 0, LYD_PATH_OPT_NOPARENTRET);
566 log_error("could not created yang path\n");
567 return NTS_ERR_FAILED;
570 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tls-server-parameters/client-authentication/required", endpoint_name);
571 rcl = lyd_new_path(netconf_node, 0, xpath, "", 0, LYD_PATH_OPT_NOPARENTRET);
573 log_error("could not created yang path\n");
574 return NTS_ERR_FAILED;
577 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tls-server-parameters/client-authentication/ca-certs", endpoint_name);
578 rcl = lyd_new_path(netconf_node, 0, xpath, "cacerts", 0, LYD_PATH_OPT_NOPARENTRET);
580 log_error("could not created yang path\n");
581 return NTS_ERR_FAILED;
584 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tls-server-parameters/client-authentication/client-certs", endpoint_name);
585 rcl = lyd_new_path(netconf_node, 0, xpath, "clientcerts", 0, LYD_PATH_OPT_NOPARENTRET);
587 log_error("could not created yang path\n");
588 return NTS_ERR_FAILED;
591 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tls-server-parameters/client-authentication/cert-maps/cert-to-name[id='1']/fingerprint", endpoint_name);
592 rcl = lyd_new_path(netconf_node, 0, xpath, "02:E9:38:1F:F6:8B:62:DE:0A:0B:C5:03:81:A8:03:49:A0:00:7F:8B:F3", 0, LYD_PATH_OPT_NOPARENTRET);
594 log_error("could not created yang path\n");
595 return NTS_ERR_FAILED;
598 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tls-server-parameters/client-authentication/cert-maps/cert-to-name[id='1']/map-type", endpoint_name);
599 rcl = lyd_new_path(netconf_node, session_context, xpath, "ietf-x509-cert-to-name:specified", 0, LYD_PATH_OPT_NOPARENTRET);
601 log_error("could not created yang path\n");
602 return NTS_ERR_FAILED;
605 sprintf(xpath, "/ietf-netconf-server:netconf-server/listen/endpoint[name='%s']/tls/tls-server-parameters/client-authentication/cert-maps/cert-to-name[id='1']/name", endpoint_name);
606 rcl = lyd_new_path(netconf_node, 0, xpath, "netconf-tls", 0, LYD_PATH_OPT_NOPARENTRET);
608 log_error("could not created yang path\n");
609 return NTS_ERR_FAILED;
616 static int configure_endpoints_connections(sr_session_ctx_t *session) {
621 struct lys_module *module = 0;
622 module = (struct lys_module *)ly_ctx_get_module(session_context, "ietf-netconf-server", 0, 0);
624 log_error("could not get module %s from context\n", "ietf-netconf-server");
625 return NTS_ERR_FAILED;
629 struct lyd_node *netconf_node = 0;
630 netconf_node = lyd_new_path(NULL, session_context, "/ietf-netconf-server:netconf-server", 0, 0, 0);
631 if(netconf_node == 0) {
632 log_error("could not create a new lyd_node\n");
633 return NTS_ERR_FAILED;
636 // create the SSH endpoints in ietf-netconf-server
637 int ssh_connections = 0;
638 if(framework_arguments.nts_mode == NTS_MODE_MANAGER) {
642 ssh_connections = framework_environment.settings.ssh_connections;
645 if(ssh_connections == 0) {
646 log_error("ssh_connections must be at least 1\n");
647 return NTS_ERR_FAILED;
650 rc = create_ssh_listen_endpoints(netconf_node, ssh_connections);
651 if(rc != NTS_ERR_OK) {
652 log_error("could not create %d SSH Listen endpoints on the NETCONF Server\n", ssh_connections);
653 return NTS_ERR_FAILED;
656 // create the TLS endpoints in ietf-netconf-server
657 if(framework_arguments.nts_mode != NTS_MODE_MANAGER) {
658 rc = create_tls_listen_endpoints(netconf_node, framework_environment.settings.tls_connections);
659 if(rc != NTS_ERR_OK) {
660 log_error("could not create %d TLS Listen endpoints on the NETCONF Server\n", framework_environment.settings.tls_connections);
661 return NTS_ERR_FAILED;
665 rc = sr_edit_batch(session, netconf_node, "replace");
666 if(rc != SR_ERR_OK) {
667 log_error("could not edit batch on datastore\n");
668 return NTS_ERR_FAILED;
671 rc = sr_validate(session, "ietf-netconf-server", 0);
672 if(rc != SR_ERR_OK) {
673 struct ly_err_item *err = ly_err_first(session_context);
674 log_error("sr_validate issues on STARTUP: %s\n", err->msg);
675 return NTS_ERR_FAILED;
678 rc = sr_apply_changes(session, 0, 0);
679 if(rc != SR_ERR_OK) {
680 log_error("could not apply changes on datastore\n");
681 return NTS_ERR_FAILED;