xpath FEATURE ignore when state for lyd_find_xpath

New flag defined for the purpose.
diff --git a/src/tree_data.c b/src/tree_data.c
index 5d6c63c..2706378 100644
--- a/src/tree_data.c
+++ b/src/tree_data.c
@@ -3344,7 +3344,7 @@
     LY_CHECK_GOTO(ret, cleanup);
 
     /* evaluate expression */
-    ret = lyxp_eval(exp, NULL, LY_PREF_JSON, NULL, ctx_node, ctx_node, &xp_set, 0);
+    ret = lyxp_eval(exp, NULL, LY_PREF_JSON, NULL, ctx_node, ctx_node, &xp_set, LYXP_IGNORE_WHEN);
     LY_CHECK_GOTO(ret, cleanup);
 
     /* allocate return set */
diff --git a/src/tree_schema.h b/src/tree_schema.h
index f9c3205..9458541 100644
--- a/src/tree_schema.h
+++ b/src/tree_schema.h
@@ -1928,8 +1928,8 @@
  * Options to modify behavior of ::lys_find_xpath() and ::lys_find_xpath_atoms() searching for schema nodes in schema tree.
  * @{
  */
-#define LYS_FIND_XP_SCHEMA 0x04 /**< Apply node access restrictions defined for 'when' and 'must' evaluation. */
-#define LYS_FIND_XP_OUTPUT 0x08 /**< Search RPC/action output nodes instead of input ones. */
+#define LYS_FIND_XP_SCHEMA 0x08 /**< Apply node access restrictions defined for 'when' and 'must' evaluation. */
+#define LYS_FIND_XP_OUTPUT 0x10 /**< Search RPC/action output nodes instead of input ones. */
 /** @} findxpathoptions */
 
 /**
diff --git a/src/xpath.c b/src/xpath.c
index 67d6342..874065c 100644
--- a/src/xpath.c
+++ b/src/xpath.c
@@ -5334,32 +5334,6 @@
 }
 
 /**
- * @brief Check whether a node has some unresolved "when".
- *
- * @param[in] node Node to check.
- * @return LY_ERR value (LY_EINCOMPLETE if there are some unresolved "when")
- */
-static LY_ERR
-moveto_when_check(const struct lyd_node *node)
-{
-    const struct lysc_node *schema;
-
-    if (!node) {
-        return LY_SUCCESS;
-    }
-
-    schema = node->schema;
-    do {
-        if (schema->when && !(node->flags & LYD_WHEN_TRUE)) {
-            return LY_EINCOMPLETE;
-        }
-        schema = schema->parent;
-    } while (schema && (schema->nodetype & (LYS_CASE | LYS_CHOICE)));
-
-    return LY_SUCCESS;
-}
-
-/**
  * @brief Check @p node as a part of NameTest processing.
  *
  * @param[in] node Node to check.
@@ -5367,12 +5341,13 @@
  * @param[in] set Set to read general context from.
  * @param[in] node_name Node name in the dictionary to move to, NULL for any node.
  * @param[in] moveto_mod Expected module of the node, NULL for no prefix.
+ * @param[in] options XPath options.
  * @return LY_ERR (LY_ENOT if node does not match, LY_EINCOMPLETE on unresolved when,
  * LY_EINVAL if netither node nor any children match)
  */
 static LY_ERR
 moveto_node_check(const struct lyd_node *node, const struct lyd_node *ctx_node, const struct lyxp_set *set,
-        const char *node_name, const struct lys_module *moveto_mod)
+        const char *node_name, const struct lys_module *moveto_mod, uint32_t options)
 {
     if (!moveto_mod && (!node_name || strcmp(node_name, "*"))) {
         switch (set->format) {
@@ -5413,7 +5388,7 @@
     }
 
     /* when check */
-    if (moveto_when_check(node)) {
+    if (!(options & LYXP_IGNORE_WHEN) && lyd_has_when(node) && !(node->flags & LYD_WHEN_TRUE)) {
         return LY_EINCOMPLETE;
     }
 
@@ -5482,10 +5457,11 @@
  * @param[in,out] set Set to use.
  * @param[in] moveto_mod Matching node module, NULL for no prefix.
  * @param[in] ncname Matching node name in the dictionary, NULL for any.
+ * @param[in] options XPath options.
  * @return LY_ERR (LY_EINCOMPLETE on unresolved when)
  */
 static LY_ERR
-moveto_node(struct lyxp_set *set, const struct lys_module *moveto_mod, const char *ncname)
+moveto_node(struct lyxp_set *set, const struct lys_module *moveto_mod, const char *ncname, uint32_t options)
 {
     uint32_t i;
     const struct lyd_node *siblings, *sub, *ctx_node;
@@ -5516,7 +5492,7 @@
         }
 
         for (sub = siblings; sub; sub = sub->next) {
-            rc = moveto_node_check(sub, ctx_node, set, ncname, moveto_mod);
+            rc = moveto_node_check(sub, ctx_node, set, ncname, moveto_mod, options);
             if (rc == LY_SUCCESS) {
                 if (!replaced) {
                     set_replace_node(set, sub, 0, LYXP_NODE_ELEM, i);
@@ -5546,10 +5522,12 @@
  * @param[in,out] set Set to use.
  * @param[in] scnode Matching node schema.
  * @param[in] predicates If @p scnode is ::LYS_LIST or ::LYS_LEAFLIST, the predicates specifying a single instance.
+ * @param[in] options XPath options.
  * @return LY_ERR (LY_EINCOMPLETE on unresolved when)
  */
 static LY_ERR
-moveto_node_hash(struct lyxp_set *set, const struct lysc_node *scnode, const struct ly_path_predicate *predicates)
+moveto_node_hash(struct lyxp_set *set, const struct lysc_node *scnode, const struct ly_path_predicate *predicates,
+        uint32_t options)
 {
     LY_ERR ret = LY_SUCCESS;
     uint32_t i;
@@ -5606,7 +5584,7 @@
         }
 
         /* when check */
-        if (sub && moveto_when_check(sub)) {
+        if (!(options & LYXP_IGNORE_WHEN) && sub && lyd_has_when(sub) && !(sub->flags & LYD_WHEN_TRUE)) {
             ret = LY_EINCOMPLETE;
             goto cleanup;
         }
@@ -5731,10 +5709,11 @@
  * @param[in] set Set to use.
  * @param[in] moveto_mod Matching node module, NULL for no prefix.
  * @param[in] ncname Matching node name in the dictionary, NULL for any.
+ * @param[in] options XPath options.
  * @return LY_ERR (LY_EINCOMPLETE on unresolved when)
  */
 static LY_ERR
-moveto_node_alldesc(struct lyxp_set *set, const struct lys_module *moveto_mod, const char *ncname)
+moveto_node_alldesc(struct lyxp_set *set, const struct lys_module *moveto_mod, const char *ncname, uint32_t options)
 {
     uint32_t i;
     const struct lyd_node *next, *elem, *start;
@@ -5751,7 +5730,7 @@
     }
 
     /* replace the original nodes (and throws away all text and meta nodes, root is replaced by a child) */
-    rc = moveto_node(set, NULL, NULL);
+    rc = moveto_node(set, NULL, NULL, options);
     LY_CHECK_RET(rc);
 
     /* this loop traverses all the nodes in the set and adds/keeps only those that match qname */
@@ -5761,7 +5740,7 @@
         /* TREE DFS */
         start = set->val.nodes[i].node;
         for (elem = next = start; elem; elem = next) {
-            rc = moveto_node_check(elem, start, set, ncname, moveto_mod);
+            rc = moveto_node_check(elem, start, set, ncname, moveto_mod, options);
             if (!rc) {
                 /* add matching node into result set */
                 set_insert_node(&ret_set, elem, 0, LYXP_NODE_ELEM, ret_set.used);
@@ -6013,10 +5992,11 @@
  * @param[in,out] set Set to use.
  * @param[in] mod Matching metadata module, NULL for any.
  * @param[in] ncname Matching metadata name in the dictionary, NULL for any.
+ * @param[in] options XPath options.
  * @return LY_ERR (LY_EINCOMPLETE on unresolved when)
  */
 static int
-moveto_attr_alldesc(struct lyxp_set *set, const struct lys_module *mod, const char *ncname)
+moveto_attr_alldesc(struct lyxp_set *set, const struct lys_module *mod, const char *ncname, uint32_t options)
 {
     struct lyd_meta *sub;
     struct lyxp_set *set_all_desc = NULL;
@@ -6036,7 +6016,7 @@
     /* copy the context */
     set_all_desc = set_copy(set);
     /* get all descendant nodes (the original context nodes are removed) */
-    rc = moveto_node_alldesc(set_all_desc, NULL, NULL);
+    rc = moveto_node_alldesc(set_all_desc, NULL, NULL, options);
     if (rc != LY_SUCCESS) {
         lyxp_set_free(set_all_desc);
         return rc;
@@ -6136,7 +6116,7 @@
         }
 
         /* when check */
-        if (moveto_when_check(iter)) {
+        if (!(options & LYXP_IGNORE_WHEN) && lyd_has_when(iter) && !(iter->flags & LYD_WHEN_TRUE)) {
             return LY_EINCOMPLETE;
         }
 
@@ -6345,7 +6325,7 @@
         }
 
         /* when check */
-        if (moveto_when_check(new_node)) {
+        if (!(options & LYXP_IGNORE_WHEN) && lyd_has_when(new_node) && !(new_node->flags & LYD_WHEN_TRUE)) {
             return LY_EINCOMPLETE;
         }
 
@@ -7152,7 +7132,7 @@
             set_scnode_clear_ctx(set);
         } else {
             if (all_desc) {
-                rc = moveto_attr_alldesc(set, moveto_mod, ncname_dict);
+                rc = moveto_attr_alldesc(set, moveto_mod, ncname_dict, options);
             } else {
                 rc = moveto_attr(set, moveto_mod, ncname_dict);
             }
@@ -7182,13 +7162,13 @@
             }
         } else {
             if (all_desc) {
-                rc = moveto_node_alldesc(set, moveto_mod, ncname_dict);
+                rc = moveto_node_alldesc(set, moveto_mod, ncname_dict, options);
             } else {
                 if (scnode) {
                     /* we can find the nodes using hashes */
-                    rc = moveto_node_hash(set, scnode, predicates);
+                    rc = moveto_node_hash(set, scnode, predicates, options);
                 } else {
-                    rc = moveto_node(set, moveto_mod, ncname_dict);
+                    rc = moveto_node(set, moveto_mod, ncname_dict, options);
                 }
             }
             LY_CHECK_GOTO(rc, cleanup);
diff --git a/src/xpath.h b/src/xpath.h
index 7c54b43..5b04457 100644
--- a/src/xpath.h
+++ b/src/xpath.h
@@ -308,11 +308,12 @@
         const struct lysc_node *ctx_scnode, struct lyxp_set *set, uint32_t options);
 
 /* used only internally, maps with @ref findxpathoptions */
-#define LYXP_SCHEMA 0x01                      /**< Apply data node access restrictions defined for 'when' and 'must' evaluation. */
-#define LYXP_SCNODE 0x02                      /**< No special tree access modifiers. */
-#define LYXP_SCNODE_SCHEMA LYS_FIND_XP_SCHEMA /**< Apply node access restrictions defined for 'when' and 'must' evaluation. */
-#define LYXP_SCNODE_OUTPUT LYS_FIND_XP_OUTPUT /**< Search RPC/action output nodes instead of input ones. */
-#define LYXP_SCNODE_ALL 0x0E                  /**< mask for all the LYXP_* values */
+#define LYXP_IGNORE_WHEN    0x01    /**< Ignore unevaluated when in data nodes and do not return ::LY_EINCOMPLETE. */
+#define LYXP_SCHEMA         0x02    /**< Apply data node access restrictions defined for 'when' and 'must' evaluation. */
+#define LYXP_SCNODE         0x04    /**< No special tree access modifiers. */
+#define LYXP_SCNODE_SCHEMA  LYS_FIND_XP_SCHEMA  /**< Apply node access restrictions defined for 'when' and 'must' evaluation. */
+#define LYXP_SCNODE_OUTPUT  LYS_FIND_XP_OUTPUT  /**< Search RPC/action output nodes instead of input ones. */
+#define LYXP_SCNODE_ALL     0x1C    /**< mask for all the LYXP_* values */
 
 /**
  * @brief Cast XPath set to another type.