snprintf(dst, dstlen, "%s/%d", addr, plen);
}
+/*
+ * Helper function to generate a sequence number for legacy commands.
+ */
+static int acl_get_seq_cb(const struct lyd_node *dnode, void *arg)
+{
+ int64_t *seq = arg;
+ int64_t cur_seq = yang_dnode_get_uint32(dnode, "sequence");
+
+ if (cur_seq > *seq)
+ *seq = cur_seq;
+
+ return YANG_ITER_CONTINUE;
+}
+
+/**
+ * Helper function that iterates over the XPath `xpath` on the candidate
+ * configuration in `vty->candidate_config`.
+ *
+ * \param[in] vty shell context with the candidate configuration.
+ * \param[in] xpath the XPath to look for the sequence leaf.
+ * \returns next unused sequence number.
+ */
+static long acl_get_seq(struct vty *vty, const char *xpath)
+{
+ int64_t seq = 0;
+
+ yang_dnode_iterate(acl_get_seq_cb, &seq, vty->candidate_config->dnode,
+ "%s/entry", xpath);
+
+ return seq + 5;
+}
+
/*
* Cisco (legacy) access lists.
*/
"Wildcard bits\n"
"Any source host\n")
{
- struct access_list *acl;
- struct lyd_node *dnode;
int rv;
int64_t sseq;
char ipmask[64];
if (rv != CMD_SUCCESS)
return rv;
- /* Use access-list data structure to generate sequence. */
- dnode = yang_dnode_get(running_config->dnode, xpath);
- acl = nb_running_get_entry(dnode, NULL, true);
if (seq_str == NULL) {
- sseq = filter_new_seq_get(acl);
+ /* Use XPath to find the next sequence number. */
+ sseq = acl_get_seq(vty, xpath);
snprintf(xpath_entry, sizeof(xpath_entry),
"%s/entry[sequence='%" PRId64 "']", xpath, sseq);
} else
"Destination address to match\n"
"Any destination host\n")
{
- struct access_list *acl;
- struct lyd_node *dnode;
int rv;
int64_t sseq;
char ipmask[64];
if (rv != CMD_SUCCESS)
return rv;
- /* Use access-list data structure to generate sequence. */
- dnode = yang_dnode_get(running_config->dnode, xpath);
- acl = nb_running_get_entry(dnode, NULL, true);
if (seq_str == NULL) {
- sseq = filter_new_seq_get(acl);
+ /* Use XPath to find the next sequence number. */
+ sseq = acl_get_seq(vty, xpath);
snprintf(xpath_entry, sizeof(xpath_entry),
"%s/entry[sequence='%" PRId64 "']", xpath, sseq);
} else
"Exact match of the prefixes\n"
"Match any IPv4\n")
{
- struct access_list *acl;
- struct lyd_node *dnode;
int rv;
int64_t sseq;
char xpath[XPATH_MAXLEN];
if (rv != CMD_SUCCESS)
return rv;
- /* Use access-list data structure to generate sequence. */
- dnode = yang_dnode_get(running_config->dnode, xpath);
- acl = nb_running_get_entry(dnode, NULL, true);
if (seq_str == NULL) {
- sseq = filter_new_seq_get(acl);
+ /* Use XPath to find the next sequence number. */
+ sseq = acl_get_seq(vty, xpath);
snprintf(xpath_entry, sizeof(xpath_entry),
"%s/entry[sequence='%" PRId64 "']", xpath, sseq);
} else
"Exact match of the prefixes\n"
"Match any IPv6\n")
{
- struct access_list *acl;
- struct lyd_node *dnode;
int rv;
int64_t sseq;
char xpath[XPATH_MAXLEN];
if (rv != CMD_SUCCESS)
return rv;
- /* Use access-list data structure to generate sequence. */
- dnode = yang_dnode_get(running_config->dnode, xpath);
- acl = nb_running_get_entry(dnode, NULL, true);
if (seq_str == NULL) {
- sseq = filter_new_seq_get(acl);
+ /* Use XPath to find the next sequence number. */
+ sseq = acl_get_seq(vty, xpath);
snprintf(xpath_entry, sizeof(xpath_entry),
"%s/entry[sequence='%" PRId64 "']", xpath, sseq);
} else
"MAC address\n"
"Match any MAC address\n")
{
- struct access_list *acl;
- struct lyd_node *dnode;
int rv;
int64_t sseq;
char xpath[XPATH_MAXLEN];
if (rv != CMD_SUCCESS)
return rv;
- /* Use access-list data structure to generate sequence. */
- dnode = yang_dnode_get(running_config->dnode, xpath);
- acl = nb_running_get_entry(dnode, NULL, true);
if (seq_str == NULL) {
- sseq = filter_new_seq_get(acl);
+ /* Use XPath to find the next sequence number. */
+ sseq = acl_get_seq(vty, xpath);
snprintf(xpath_entry, sizeof(xpath_entry),
"%s/entry[sequence='%" PRId64 "']", xpath, sseq);
} else
"Maximum prefix length to be matched\n"
"Maximum prefix length\n")
{
- struct prefix_list *pl;
- struct lyd_node *dnode;
int rv;
int64_t sseq;
char xpath[XPATH_MAXLEN];
if (rv != CMD_SUCCESS)
return rv;
- /* Use prefix-list data structure to generate sequence. */
- dnode = yang_dnode_get(running_config->dnode, xpath);
- pl = nb_running_get_entry(dnode, NULL, true);
if (seq_str == NULL) {
- sseq = prefix_new_seq_get(pl);
+ /* Use XPath to find the next sequence number. */
+ sseq = acl_get_seq(vty, xpath);
snprintf(xpath_entry, sizeof(xpath_entry),
"%s/entry[sequence='%" PRId64 "']", xpath, sseq);
} else
"Minimum prefix length to be matched\n"
"Minimum prefix length\n")
{
- struct prefix_list *pl;
- struct lyd_node *dnode;
int rv;
int64_t sseq;
char xpath[XPATH_MAXLEN];
if (rv != CMD_SUCCESS)
return rv;
- /* Use prefix-list data structure to generate sequence. */
- dnode = yang_dnode_get(running_config->dnode, xpath);
- pl = nb_running_get_entry(dnode, NULL, true);
if (seq_str == NULL) {
- sseq = prefix_new_seq_get(pl);
+ /* Use XPath to find the next sequence number. */
+ sseq = acl_get_seq(vty, xpath);
snprintf(xpath_entry, sizeof(xpath_entry),
"%s/entry[sequence='%" PRId64 "']", xpath, sseq);
} else