ly_ctx_set_searchdir:
   75|      5|{
   76|      5|    int rc = LY_SUCCESS;
   77|      5|    struct stat st;
   78|      5|    char *new_dir = NULL;
   79|      5|    uint32_t i;
   80|      5|    LY_ARRAY_COUNT_TYPE u;
  ------------------
  |  |  104|      5|#define LY_ARRAY_COUNT_TYPE uint64_t
  ------------------
   81|      5|    struct lys_module *mod;
   82|       |
   83|      5|    LY_CHECK_ARG_RET(ctx, ctx, !(ctx->opts & LY_CTX_INT_IMMUTABLE), LY_EINVAL);
  ------------------
  |  |  200|      5|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  ------------------
  |  |  |  |   63|      5|#define GETMACRO7(_1, _2, _3, _4, _5, _6, _7, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  192|      5|#define LY_CHECK_ARG_RET2(CTX, ARG1, ARG2, RETVAL) LY_CHECK_ARG_RET1(CTX, ARG1, RETVAL);LY_CHECK_ARG_RET1(CTX, ARG2, RETVAL)
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  191|      5|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |               #define LY_CHECK_ARG_RET2(CTX, ARG1, ARG2, RETVAL) LY_CHECK_ARG_RET1(CTX, ARG1, RETVAL);LY_CHECK_ARG_RET1(CTX, ARG2, RETVAL)
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  191|      5|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  ------------------
   84|       |
   85|      5|    if (!search_dir) {
  ------------------
  |  Branch (85:9): [True: 0, False: 5]
  ------------------
   86|       |        /* fine, ignore */
   87|      0|        goto cleanup;
   88|      0|    }
   89|       |
   90|      5|    new_dir = realpath(search_dir, NULL);
   91|      5|    if (!new_dir) {
  ------------------
  |  Branch (91:9): [True: 5, False: 0]
  ------------------
   92|      5|        LOGERR(ctx, LY_ESYS, "Unable to use search directory \"%s\" (%s).", search_dir, strerror(errno)),
  ------------------
  |  |  142|      5|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  ------------------
   93|      5|        rc = LY_EINVAL;
   94|      5|        goto cleanup;
   95|      5|    }
   96|      0|    if (strcmp(search_dir, new_dir)) {
  ------------------
  |  Branch (96:9): [True: 0, False: 0]
  ------------------
   97|      0|        LOGVRB("Search directory string \"%s\" canonized to \"%s\".", search_dir, new_dir);
  ------------------
  |  |  144|      0|#define LOGVRB(...) ly_log(NULL, LY_LLVRB, 0, __VA_ARGS__)
  ------------------
   98|      0|    }
   99|       |
  100|      0|    if (access(new_dir, R_OK | X_OK)) {
  ------------------
  |  Branch (100:9): [True: 0, False: 0]
  ------------------
  101|      0|        LOGERR(ctx, LY_ESYS, "Unable to fully access search directory \"%s\" (%s).", new_dir, strerror(errno));
  ------------------
  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  ------------------
  102|      0|        rc = LY_EINVAL;
  103|      0|        goto cleanup;
  104|      0|    }
  105|      0|    if (stat(new_dir, &st)) {
  ------------------
  |  Branch (105:9): [True: 0, False: 0]
  ------------------
  106|      0|        LOGERR(ctx, LY_ESYS, "stat() failed for \"%s\" (%s).", new_dir, strerror(errno));
  ------------------
  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  ------------------
  107|      0|        rc = LY_ESYS;
  108|      0|        goto cleanup;
  109|      0|    }
  110|      0|    if (!S_ISDIR(st.st_mode)) {
  ------------------
  |  Branch (110:9): [True: 0, False: 0]
  ------------------
  111|      0|        LOGERR(ctx, LY_ESYS, "Given search directory \"%s\" is not a directory.", new_dir);
  ------------------
  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  ------------------
  112|      0|        rc = LY_EINVAL;
  113|      0|        goto cleanup;
  114|      0|    }
  115|       |
  116|       |    /* avoid path duplication */
  117|      0|    for (i = 0; i < ctx->search_paths.count; ++i) {
  ------------------
  |  Branch (117:17): [True: 0, False: 0]
  ------------------
  118|      0|        if (!strcmp(new_dir, ctx->search_paths.objs[i])) {
  ------------------
  |  Branch (118:13): [True: 0, False: 0]
  ------------------
  119|      0|            rc = LY_EEXIST;
  120|      0|            goto cleanup;
  121|      0|        }
  122|      0|    }
  123|      0|    if (ly_set_add(&ctx->search_paths, new_dir, 1, NULL)) {
  ------------------
  |  Branch (123:9): [True: 0, False: 0]
  ------------------
  124|      0|        rc = LY_EMEM;
  125|      0|        goto cleanup;
  126|      0|    }
  127|       |
  128|       |    /* new searchdir - reset latests flags (possibly new revisions available) */
  129|      0|    for (i = 0; i < ctx->modules.count; ++i) {
  ------------------
  |  Branch (129:17): [True: 0, False: 0]
  ------------------
  130|      0|        mod = ctx->modules.objs[i];
  131|       |
  132|      0|        mod->latest_revision &= ~LYS_MOD_LATEST_SEARCHDIRS;
  ------------------
  |  | 2289|      0|#define LYS_MOD_LATEST_SEARCHDIRS   0x02 /**< This is the latest revision of the module found in searchdirs. */
  ------------------
  133|      0|        if (mod->parsed && mod->parsed->includes) {
  ------------------
  |  Branch (133:13): [True: 0, False: 0]
  |  Branch (133:28): [True: 0, False: 0]
  ------------------
  134|      0|            for (u = 0; u < LY_ARRAY_COUNT(mod->parsed->includes); ++u) {
  ------------------
  |  |  148|      0|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  ------------------
  |  |  |  Branch (148:32): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  |  Branch (134:25): [True: 0, False: 0]
  ------------------
  135|      0|                mod->parsed->includes[u].submodule->latest_revision &= ~LYS_MOD_LATEST_SEARCHDIRS;
  ------------------
  |  | 2289|      0|#define LYS_MOD_LATEST_SEARCHDIRS   0x02 /**< This is the latest revision of the module found in searchdirs. */
  ------------------
  136|      0|            }
  137|      0|        }
  138|      0|    }
  139|       |
  140|      5|cleanup:
  141|      5|    if (rc) {
  ------------------
  |  Branch (141:9): [True: 5, False: 0]
  ------------------
  142|      5|        free(new_dir);
  143|      5|    }
  144|      5|    return rc;
  145|      0|}
ly_ctx_get_searchdirs:
  149|      5|{
  150|      5|#define LY_CTX_SEARCHDIRS_SIZE_STEP 8
  151|      5|    void **new;
  152|       |
  153|      5|    LY_CHECK_ARG_RET(ctx, ctx, NULL);
  ------------------
  |  |  200|      5|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  ------------------
  |  |  |  |   63|      5|#define GETMACRO7(_1, _2, _3, _4, _5, _6, _7, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  191|      5|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  ------------------
  154|       |
  155|      5|    if (ctx->search_paths.count == ctx->search_paths.size) {
  ------------------
  |  Branch (155:9): [True: 5, False: 0]
  ------------------
  156|       |        /* not enough space for terminating NULL byte */
  157|      5|        new = realloc(((struct ly_ctx *)ctx)->search_paths.objs,
  158|      5|                (ctx->search_paths.size + LY_CTX_SEARCHDIRS_SIZE_STEP) * sizeof *ctx->search_paths.objs);
  ------------------
  |  |  150|      5|#define LY_CTX_SEARCHDIRS_SIZE_STEP 8
  ------------------
  159|      5|        LY_CHECK_ERR_RET(!new, LOGMEM(NULL), NULL);
  ------------------
  |  |  181|      5|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  160|      5|        ((struct ly_ctx *)ctx)->search_paths.size += LY_CTX_SEARCHDIRS_SIZE_STEP;
  ------------------
  |  |  150|      5|#define LY_CTX_SEARCHDIRS_SIZE_STEP 8
  ------------------
  161|      5|        ((struct ly_ctx *)ctx)->search_paths.objs = new;
  162|      5|    }
  163|       |    /* set terminating NULL byte to the strings list */
  164|      5|    ctx->search_paths.objs[ctx->search_paths.count] = NULL;
  165|       |
  166|      5|    return (const char * const *)ctx->search_paths.objs;
  167|      5|}
ly_ctx_new:
  268|      5|{
  269|      5|    struct ly_ctx *ctx = NULL;
  270|      5|    struct lys_module *module;
  271|      5|    char *search_dir_list, *sep, *dir;
  272|      5|    const char **imp_f, *all_f[] = {"*", NULL};
  273|      5|    uint32_t i;
  274|      5|    LY_ERR rc = LY_SUCCESS;
  275|      5|    struct lys_glob_unres unres = {0};
  276|      5|    ly_bool builtin_plugins_only, static_plugins_only;
  277|       |
  278|      5|    LY_CHECK_ARG_RET(NULL, new_ctx, LY_EINVAL);
  ------------------
  |  |  200|      5|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  ------------------
  |  |  |  |   63|      5|#define GETMACRO7(_1, _2, _3, _4, _5, _6, _7, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  191|      5|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  ------------------
  279|       |
  280|      5|    ctx = calloc(1, sizeof *ctx);
  281|      5|    LY_CHECK_ERR_GOTO(!ctx, LOGMEM(NULL); rc = LY_EMEM, cleanup);
  ------------------
  |  |  177|      5|#define LY_CHECK_ERR_GOTO(COND, ERR, GOTO) if ((COND)) {ERR; goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (177:48): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  282|       |
  283|       |    /* dictionary */
  284|      5|    lydict_init(&ctx->dict);
  285|       |
  286|       |    /* plugins */
  287|      5|    builtin_plugins_only = (options & LY_CTX_BUILTIN_PLUGINS_ONLY) ? 1 : 0;
  ------------------
  |  |  230|      5|#define LY_CTX_BUILTIN_PLUGINS_ONLY 0x2000 /**< Limits the context to use only built-in YANG type plugins,
  ------------------
  |  Branch (287:28): [True: 0, False: 5]
  ------------------
  288|      5|    static_plugins_only = (options & LY_CTX_STATIC_PLUGINS_ONLY) ? 1 : 0;
  ------------------
  |  |  236|      5|#define LY_CTX_STATIC_PLUGINS_ONLY 0x4000 /**< Restricts the context to load only static (built-in) plugins,
  ------------------
  |  Branch (288:27): [True: 0, False: 5]
  ------------------
  289|      5|    LY_CHECK_GOTO(rc = lyplg_init(builtin_plugins_only, static_plugins_only), cleanup);
  ------------------
  |  |  176|      5|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  290|       |
  291|       |    /* options */
  292|      5|    ctx->opts = options;
  293|       |
  294|       |    /* ctx data */
  295|      5|    rc = ly_ctx_data_add(ctx);
  296|      5|    LY_CHECK_GOTO(rc, cleanup);
  ------------------
  |  |  176|      5|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  297|       |
  298|       |    /* modules list */
  299|      5|    if (search_dir) {
  ------------------
  |  Branch (299:9): [True: 5, False: 0]
  ------------------
  300|      5|        search_dir_list = strdup(search_dir);
  301|      5|        LY_CHECK_ERR_GOTO(!search_dir_list, LOGMEM(NULL); rc = LY_EMEM, cleanup);
  ------------------
  |  |  177|      5|#define LY_CHECK_ERR_GOTO(COND, ERR, GOTO) if ((COND)) {ERR; goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (177:48): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  302|       |
  303|      5|        for (dir = search_dir_list; (sep = strchr(dir, PATH_SEPARATOR[0])) != NULL && rc == LY_SUCCESS; dir = sep + 1) {
  ------------------
  |  |   52|      5|# define PATH_SEPARATOR ":"
  ------------------
  |  Branch (303:37): [True: 0, False: 5]
  |  Branch (303:87): [True: 0, False: 0]
  ------------------
  304|      0|            *sep = 0;
  305|       |
  306|       |            /* ignore errors */
  307|      0|            ly_ctx_set_searchdir(ctx, dir);
  308|      0|        }
  309|      5|        if (*dir && (rc == LY_SUCCESS)) {
  ------------------
  |  Branch (309:13): [True: 5, False: 0]
  |  Branch (309:21): [True: 5, False: 0]
  ------------------
  310|      5|            ly_ctx_set_searchdir(ctx, dir);
  311|      5|        }
  312|      5|        free(search_dir_list);
  313|      5|    }
  314|      5|    ctx->change_count = 1;
  315|       |
  316|      5|    if (!(options & LY_CTX_EXPLICIT_COMPILE)) {
  ------------------
  |  |  210|      5|#define LY_CTX_EXPLICIT_COMPILE 0x80 /**< If this flag is set, the compiled modules and their schema nodes are
  ------------------
  |  Branch (316:9): [True: 5, False: 0]
  ------------------
  317|       |        /* use it for creating the initial context */
  318|      5|        ctx->opts |= LY_CTX_EXPLICIT_COMPILE;
  ------------------
  |  |  210|      5|#define LY_CTX_EXPLICIT_COMPILE 0x80 /**< If this flag is set, the compiled modules and their schema nodes are
  ------------------
  319|      5|    }
  320|       |
  321|       |    /* load internal modules */
  322|      5|    for (i = 0; i < ((options & LY_CTX_NO_YANGLIBRARY) ? (LY_INTERNAL_MODS_COUNT - 2) : LY_INTERNAL_MODS_COUNT); i++) {
  ------------------
  |  |  188|      5|#define LY_CTX_NO_YANGLIBRARY  0x04 /**< Do not internally implement ietf-yang-library module. The option
  ------------------
                  for (i = 0; i < ((options & LY_CTX_NO_YANGLIBRARY) ? (LY_INTERNAL_MODS_COUNT - 2) : LY_INTERNAL_MODS_COUNT); i++) {
  ------------------
  |  |   71|      0|#define LY_INTERNAL_MODS_COUNT sizeof(internal_modules) / sizeof(struct internal_modules_s)
  ------------------
                  for (i = 0; i < ((options & LY_CTX_NO_YANGLIBRARY) ? (LY_INTERNAL_MODS_COUNT - 2) : LY_INTERNAL_MODS_COUNT); i++) {
  ------------------
  |  |   71|      5|#define LY_INTERNAL_MODS_COUNT sizeof(internal_modules) / sizeof(struct internal_modules_s)
  ------------------
  |  Branch (322:17): [True: 5, False: 0]
  |  Branch (322:22): [True: 0, False: 5]
  ------------------
  323|      5|        rc = lys_parse_load(ctx, internal_modules[i].name, internal_modules[i].revision, &unres.creating, &module);
  324|      5|        LY_CHECK_GOTO(rc, cleanup);
  ------------------
  |  |  176|      5|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 5, False: 0]
  |  |  ------------------
  ------------------
  325|       |
  326|      0|        if (internal_modules[i].implemented || (ctx->opts & LY_CTX_ALL_IMPLEMENTED)) {
  ------------------
  |  |  181|      0|#define LY_CTX_ALL_IMPLEMENTED 0x01 /**< All the imported modules of the schema being parsed are implemented. */
  ------------------
  |  Branch (326:13): [True: 0, False: 0]
  |  Branch (326:48): [True: 0, False: 0]
  ------------------
  327|      0|            imp_f = (ctx->opts & LY_CTX_ENABLE_IMP_FEATURES) ? all_f : NULL;
  ------------------
  |  |  216|      0|#define LY_CTX_ENABLE_IMP_FEATURES 0x0100 /**< By default, all features of newly implemented imported modules of
  ------------------
  |  Branch (327:21): [True: 0, False: 0]
  ------------------
  328|      0|            LY_CHECK_GOTO(rc = lys_implement(module, imp_f, &unres), cleanup);
  ------------------
  |  |  176|      0|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  329|      0|        }
  330|      0|    }
  331|       |
  332|      0|    if (!(options & LY_CTX_EXPLICIT_COMPILE)) {
  ------------------
  |  |  210|      0|#define LY_CTX_EXPLICIT_COMPILE 0x80 /**< If this flag is set, the compiled modules and their schema nodes are
  ------------------
  |  Branch (332:9): [True: 0, False: 0]
  ------------------
  333|       |        /* compile now */
  334|      0|        LY_CHECK_GOTO(rc = ly_ctx_compile(ctx), cleanup);
  ------------------
  |  |  176|      0|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  335|      0|        ctx->opts &= ~LY_CTX_EXPLICIT_COMPILE;
  ------------------
  |  |  210|      0|#define LY_CTX_EXPLICIT_COMPILE 0x80 /**< If this flag is set, the compiled modules and their schema nodes are
  ------------------
  336|      0|    }
  337|       |
  338|      5|cleanup:
  339|      5|    lys_unres_glob_erase(&unres);
  340|      5|    if (rc) {
  ------------------
  |  Branch (340:9): [True: 5, False: 0]
  ------------------
  341|      5|        ly_ctx_destroy(ctx);
  342|      5|    } else {
  343|      0|        *new_ctx = ctx;
  344|      0|    }
  345|      5|    return rc;
  346|      0|}
ly_ctx_get_module:
  919|      5|{
  920|      5|    LY_CHECK_ARG_RET(ctx, ctx, name, NULL);
  ------------------
  |  |  200|      5|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  ------------------
  |  |  |  |   63|      5|#define GETMACRO7(_1, _2, _3, _4, _5, _6, _7, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  192|      5|#define LY_CHECK_ARG_RET2(CTX, ARG1, ARG2, RETVAL) LY_CHECK_ARG_RET1(CTX, ARG1, RETVAL);LY_CHECK_ARG_RET1(CTX, ARG2, RETVAL)
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  191|      5|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |               #define LY_CHECK_ARG_RET2(CTX, ARG1, ARG2, RETVAL) LY_CHECK_ARG_RET1(CTX, ARG1, RETVAL);LY_CHECK_ARG_RET1(CTX, ARG2, RETVAL)
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  191|      5|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  ------------------
  921|       |    return ly_ctx_get_module_by(ctx, name, offsetof(struct lys_module, name), revision);
  922|      5|}
ly_ctx_destroy:
 1481|      5|{
 1482|      5|    struct lys_module *mod;
 1483|      5|    uint32_t i;
 1484|      5|    LY_ARRAY_COUNT_TYPE u;
  ------------------
  |  |  104|      5|#define LY_ARRAY_COUNT_TYPE uint64_t
  ------------------
 1485|       |
 1486|      5|    if (!ctx) {
  ------------------
  |  Branch (1486:9): [True: 0, False: 5]
  ------------------
 1487|      0|        return;
 1488|      0|    }
 1489|       |
 1490|      5|    if (ctx->opts & LY_CTX_INT_IMMUTABLE) {
  ------------------
  |  |  352|      5|#define LY_CTX_INT_IMMUTABLE 0x80000000 /**< marks a context that was printed into a fixed-size memory block and
  ------------------
  |  Branch (1490:9): [True: 0, False: 5]
  ------------------
 1491|      0|        if (!ctx->parent_ctx) {
  ------------------
  |  Branch (1491:13): [True: 0, False: 0]
  ------------------
 1492|       |            /* cached patterns and ctx data */
 1493|      0|            ly_ctx_pattern_ht_erase(ctx);
 1494|      0|            ly_ctx_data_del(ctx);
 1495|      0|        }
 1496|      0|        lyplg_clean();
 1497|      0|        return;
 1498|      0|    }
 1499|       |
 1500|       |    /* free the parsed and compiled modules (both can reference ext instances, which need to be freed, so their
 1501|       |     * definitions can be freed) */
 1502|      5|    for (i = 0; i < ctx->modules.count; ++i) {
  ------------------
  |  Branch (1502:17): [True: 0, False: 5]
  ------------------
 1503|      0|        mod = ctx->modules.objs[i];
 1504|       |
 1505|      0|        lysp_module_free(ctx, mod->parsed);
 1506|      0|        mod->parsed = NULL;
 1507|      0|        if (mod->implemented) {
  ------------------
  |  Branch (1507:13): [True: 0, False: 0]
  ------------------
 1508|      0|            mod->implemented = 0;
 1509|      0|            lysc_module_free(ctx, mod->compiled);
 1510|      0|            mod->compiled = NULL;
 1511|      0|        }
 1512|       |
 1513|       |        /* even compiled ext definitions and itentities can have ext instances, free those, too */
 1514|      0|        LY_ARRAY_FOR(mod->extensions, u) {
  ------------------
  |  |  167|      0|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  ------------------
  |  |  |  |  114|      0|#define LY_ARRAY_SELECT(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  167|      0|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  141|      0|    for (INDEX = 0; \
  |  |  |  |  |  |  |  |  142|      0|         INDEX < LY_ARRAY_COUNT(ARRAY); \
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  148|      0|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (148:32): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (142:10): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  143|      0|         ++INDEX)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
 1515|      0|            FREE_ARRAY(ctx, mod->extensions[u].exts, lysc_ext_instance_free);
  ------------------
  |  |   29|      0|#define FREE_ARRAY(CTX, ARRAY, FUNC) {LY_ARRAY_COUNT_TYPE c__; LY_ARRAY_FOR(ARRAY, c__){(FUNC)(CTX, &(ARRAY)[c__]);}LY_ARRAY_FREE(ARRAY);}
  |  |  ------------------
  |  |  |  |  104|      0|#define LY_ARRAY_COUNT_TYPE uint64_t
  |  |  ------------------
  |  |               #define FREE_ARRAY(CTX, ARRAY, FUNC) {LY_ARRAY_COUNT_TYPE c__; LY_ARRAY_FOR(ARRAY, c__){(FUNC)(CTX, &(ARRAY)[c__]);}LY_ARRAY_FREE(ARRAY);}
  |  |  ------------------
  |  |  |  |  167|      0|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  ------------------
  |  |  |  |  |  |  114|      0|#define LY_ARRAY_SELECT(_1, _2, NAME, ...) NAME
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  167|      0|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  141|      0|    for (INDEX = 0; \
  |  |  |  |  |  |  |  |  |  |  142|      0|         INDEX < LY_ARRAY_COUNT(ARRAY); \
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  148|      0|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  Branch (148:32): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (142:10): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  143|      0|         ++INDEX)
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define FREE_ARRAY(CTX, ARRAY, FUNC) {LY_ARRAY_COUNT_TYPE c__; LY_ARRAY_FOR(ARRAY, c__){(FUNC)(CTX, &(ARRAY)[c__]);}LY_ARRAY_FREE(ARRAY);}
  |  |  ------------------
  |  |  |  |  232|      0|        if (ARRAY){free((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1);}
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (232:13): [True: 0, False: 0]
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
 1516|      0|            mod->extensions[u].exts = NULL;
 1517|      0|        }
 1518|      0|        LY_ARRAY_FOR(mod->identities, u) {
  ------------------
  |  |  167|      0|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  ------------------
  |  |  |  |  114|      0|#define LY_ARRAY_SELECT(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  167|      0|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  141|      0|    for (INDEX = 0; \
  |  |  |  |  |  |  |  |  142|      0|         INDEX < LY_ARRAY_COUNT(ARRAY); \
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  148|      0|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (148:32): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (142:10): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  143|      0|         ++INDEX)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
 1519|      0|            FREE_ARRAY(ctx, mod->identities[u].exts, lysc_ext_instance_free);
  ------------------
  |  |   29|      0|#define FREE_ARRAY(CTX, ARRAY, FUNC) {LY_ARRAY_COUNT_TYPE c__; LY_ARRAY_FOR(ARRAY, c__){(FUNC)(CTX, &(ARRAY)[c__]);}LY_ARRAY_FREE(ARRAY);}
  |  |  ------------------
  |  |  |  |  104|      0|#define LY_ARRAY_COUNT_TYPE uint64_t
  |  |  ------------------
  |  |               #define FREE_ARRAY(CTX, ARRAY, FUNC) {LY_ARRAY_COUNT_TYPE c__; LY_ARRAY_FOR(ARRAY, c__){(FUNC)(CTX, &(ARRAY)[c__]);}LY_ARRAY_FREE(ARRAY);}
  |  |  ------------------
  |  |  |  |  167|      0|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  ------------------
  |  |  |  |  |  |  114|      0|#define LY_ARRAY_SELECT(_1, _2, NAME, ...) NAME
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  167|      0|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  141|      0|    for (INDEX = 0; \
  |  |  |  |  |  |  |  |  |  |  142|      0|         INDEX < LY_ARRAY_COUNT(ARRAY); \
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  148|      0|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  Branch (148:32): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (142:10): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  143|      0|         ++INDEX)
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |               #define FREE_ARRAY(CTX, ARRAY, FUNC) {LY_ARRAY_COUNT_TYPE c__; LY_ARRAY_FOR(ARRAY, c__){(FUNC)(CTX, &(ARRAY)[c__]);}LY_ARRAY_FREE(ARRAY);}
  |  |  ------------------
  |  |  |  |  232|      0|        if (ARRAY){free((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1);}
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (232:13): [True: 0, False: 0]
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
 1520|      0|            mod->identities[u].exts = NULL;
 1521|      0|        }
 1522|      0|    }
 1523|       |
 1524|       |    /* free the modules */
 1525|      5|    for (i = 0; i < ctx->modules.count; ++i) {
  ------------------
  |  Branch (1525:17): [True: 0, False: 5]
  ------------------
 1526|      0|        mod = ctx->modules.objs[i];
 1527|      0|        lys_module_free(ctx, mod, 0);
 1528|      0|    }
 1529|      5|    free(ctx->modules.objs);
 1530|       |
 1531|       |    /* search paths list */
 1532|      5|    ly_set_erase(&ctx->search_paths, free);
 1533|       |
 1534|       |    /* leftover unres */
 1535|      5|    lys_unres_glob_erase(&ctx->unres);
 1536|       |
 1537|      5|    if (!ctx->parent_ctx) {
  ------------------
  |  Branch (1537:9): [True: 5, False: 0]
  ------------------
 1538|       |        /* ctx data */
 1539|      5|        ly_ctx_data_del(ctx);
 1540|      5|    }
 1541|       |
 1542|       |    /* dictionary */
 1543|      5|    lydict_clean(&ctx->dict);
 1544|       |
 1545|       |    /* context specific plugins */
 1546|      5|    ly_set_erase(&ctx->plugins_types, NULL);
 1547|      5|    ly_set_erase(&ctx->plugins_extensions, NULL);
 1548|       |
 1549|       |    /* shared plugins - will be removed only if this is the last context */
 1550|      5|    lyplg_clean();
 1551|       |
 1552|      5|    free(ctx);
 1553|      5|}
context.c:ly_ctx_get_module_by:
  889|      5|{
  890|      5|    struct lys_module *mod;
  891|      5|    uint32_t index = 0;
  892|       |
  893|      5|    while ((mod = ly_ctx_get_module_by_iter(ctx, key, 0, key_offset, &index))) {
  ------------------
  |  Branch (893:12): [True: 0, False: 5]
  ------------------
  894|      0|        if (!revision) {
  ------------------
  |  Branch (894:13): [True: 0, False: 0]
  ------------------
  895|      0|            if (!mod->revision) {
  ------------------
  |  Branch (895:17): [True: 0, False: 0]
  ------------------
  896|       |                /* found requested module without revision */
  897|      0|                return mod;
  898|      0|            }
  899|      0|        } else {
  900|      0|            if (mod->revision && !strcmp(mod->revision, revision)) {
  ------------------
  |  Branch (900:17): [True: 0, False: 0]
  |  Branch (900:34): [True: 0, False: 0]
  ------------------
  901|       |                /* found requested module of the specific revision */
  902|      0|                return mod;
  903|      0|            }
  904|      0|        }
  905|      0|    }
  906|       |
  907|      5|    return NULL;
  908|      5|}
context.c:ly_ctx_get_module_by_iter:
  861|      5|{
  862|      5|    struct lys_module *mod;
  863|      5|    const char *value;
  864|       |
  865|      5|    for ( ; *index < ctx->modules.count; ++(*index)) {
  ------------------
  |  Branch (865:13): [True: 0, False: 5]
  ------------------
  866|      0|        mod = ctx->modules.objs[*index];
  867|      0|        value = *(const char **)(((int8_t *)(mod)) + key_offset);
  868|      0|        if ((!key_size && !strcmp(key, value)) || (key_size && !strncmp(key, value, key_size) && (value[key_size] == '\0'))) {
  ------------------
  |  Branch (868:14): [True: 0, False: 0]
  |  Branch (868:27): [True: 0, False: 0]
  |  Branch (868:52): [True: 0, False: 0]
  |  Branch (868:64): [True: 0, False: 0]
  |  Branch (868:98): [True: 0, False: 0]
  ------------------
  869|       |            /* increment index for the next run */
  870|      0|            ++(*index);
  871|      0|            return mod;
  872|      0|        }
  873|      0|    }
  874|       |    /* done */
  875|      5|    return NULL;
  876|      5|}

lydict_init:
   55|     10|{
   56|     10|    LY_CHECK_ARG_RET(NULL, dict, );
  ------------------
  |  |  200|     10|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  ------------------
  |  |  |  |   63|     10|#define GETMACRO7(_1, _2, _3, _4, _5, _6, _7, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  201|     10|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  191|     10|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 10]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  201|     10|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  ------------------
   57|       |
   58|     10|    dict->hash_tab = lyht_new(LYDICT_MIN_SIZE, sizeof(struct ly_dict_rec), lydict_val_eq, NULL, 1);
  ------------------
  |  |   29|     10|#define LYDICT_MIN_SIZE 1024
  ------------------
   59|     10|    LY_CHECK_ERR_RET(!dict->hash_tab, LOGINT(NULL), );
  ------------------
  |  |  181|     10|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 10]
  |  |  ------------------
  ------------------
   60|       |    pthread_mutex_init(&dict->lock, NULL);
   61|     10|}
lydict_clean:
   65|     10|{
   66|     10|    struct ly_dict_rec *dict_rec = NULL;
   67|     10|    struct ly_ht_rec *rec = NULL;
   68|     10|    uint32_t hlist_idx;
   69|     10|    uint32_t rec_idx;
   70|       |
   71|     10|    if (!dict) {
  ------------------
  |  Branch (71:9): [True: 0, False: 10]
  ------------------
   72|      0|        return;
   73|      0|    }
   74|       |
   75|  10.2k|    LYHT_ITER_ALL_RECS(dict->hash_tab, hlist_idx, rec_idx, rec) {
  ------------------
  |  |  113|  10.2k|    for (hlist_idx = 0; hlist_idx < ht->size; hlist_idx++)           \
  |  |  ------------------
  |  |  |  Branch (113:25): [True: 10.2k, False: 10]
  |  |  ------------------
  |  |  114|  10.2k|        LYHT_ITER_HLIST_RECS(ht, hlist_idx, rec_idx, rec)
  |  |  ------------------
  |  |  |  |  105|  10.2k|    for (rec_idx = ht->hlists[hlist_idx].first,                         \
  |  |  |  |  106|  10.2k|             rec = lyht_get_rec(ht->recs, ht->rec_size, rec_idx);       \
  |  |  |  |  107|  10.2k|         rec_idx != LYHT_NO_RECORD;                                     \
  |  |  |  |  ------------------
  |  |  |  |  |  |   94|  10.2k|#define LYHT_NO_RECORD UINT32_MAX
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (107:10): [True: 0, False: 10.2k]
  |  |  |  |  ------------------
  |  |  |  |  108|  10.2k|         rec_idx = rec->next,                                           \
  |  |  |  |  109|      0|             rec = lyht_get_rec(ht->recs, ht->rec_size, rec_idx))
  |  |  ------------------
  ------------------
   76|       |        /*
   77|       |         * this should not happen, all records inserted into
   78|       |         * dictionary are supposed to be removed using lydict_remove()
   79|       |         * before calling lydict_clean()
   80|       |         */
   81|      0|        dict_rec = (struct ly_dict_rec *)rec->val;
   82|      0|        LOGWRN(NULL, "String \"%s\" not freed from the dictionary, refcount %" PRIu32 ".", dict_rec->value, dict_rec->refcount);
  ------------------
  |  |  143|      0|#define LOGWRN(ctx, ...) ly_log(ctx, LY_LLWRN, 0, __VA_ARGS__)
  ------------------
   83|       |        /* if record wasn't removed before free string allocated for that record */
   84|       |#ifdef NDEBUG
   85|       |        free(dict_rec->value);
   86|       |#endif
   87|      0|    }
   88|       |
   89|       |    /* free table and destroy mutex */
   90|       |    lyht_free(dict->hash_tab, NULL);
   91|     10|    pthread_mutex_destroy(&dict->lock);
   92|     10|}

lyht_new:
  115|     15|{
  116|     15|    struct ly_ht *ht;
  117|       |
  118|       |    /* check that 2^x == size (power of 2) */
  119|     45|    LY_CHECK_ARG_RET(NULL, !(size & (size - 1)), val_size, val_equal, (resize == 0) || (resize == 1), NULL);
  ------------------
  |  |  200|     15|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  ------------------
  |  |  |  |   63|     15|#define GETMACRO7(_1, _2, _3, _4, _5, _6, _7, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  200|     15|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  194|     15|#define LY_CHECK_ARG_RET4(CTX, ARG1, ARG2, ARG3, ARG4, RETVAL) LY_CHECK_ARG_RET3(CTX, ARG1, ARG2, ARG3, RETVAL);\
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  193|     15|#define LY_CHECK_ARG_RET3(CTX, ARG1, ARG2, ARG3, RETVAL) LY_CHECK_ARG_RET2(CTX, ARG1, ARG2, RETVAL);LY_CHECK_ARG_RET1(CTX, ARG3, RETVAL)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  192|     15|#define LY_CHECK_ARG_RET2(CTX, ARG1, ARG2, RETVAL) LY_CHECK_ARG_RET1(CTX, ARG1, RETVAL);LY_CHECK_ARG_RET1(CTX, ARG2, RETVAL)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  191|     15|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 15]
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |               #define LY_CHECK_ARG_RET2(CTX, ARG1, ARG2, RETVAL) LY_CHECK_ARG_RET1(CTX, ARG1, RETVAL);LY_CHECK_ARG_RET1(CTX, ARG2, RETVAL)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  191|     15|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 15]
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |               #define LY_CHECK_ARG_RET3(CTX, ARG1, ARG2, ARG3, RETVAL) LY_CHECK_ARG_RET2(CTX, ARG1, ARG2, RETVAL);LY_CHECK_ARG_RET1(CTX, ARG3, RETVAL)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  191|     15|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 15]
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  195|     15|    LY_CHECK_ARG_RET1(CTX, ARG4, RETVAL)
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  191|     30|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (191:51): [True: 0, False: 15]
  |  |  |  |  |  |  |  |  |  |  |  Branch (191:51): [True: 15, False: 0]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  201|     15|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  ------------------
  120|       |
  121|     15|    if (size < LYHT_MIN_SIZE) {
  ------------------
  |  |   39|     15|#define LYHT_MIN_SIZE 8
  ------------------
  |  Branch (121:9): [True: 0, False: 15]
  ------------------
  122|      0|        size = LYHT_MIN_SIZE;
  ------------------
  |  |   39|      0|#define LYHT_MIN_SIZE 8
  ------------------
  123|      0|    }
  124|       |
  125|     15|    ht = malloc(sizeof *ht);
  126|     15|    LY_CHECK_ERR_RET(!ht, LOGMEM(NULL), NULL);
  ------------------
  |  |  181|     15|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 15]
  |  |  ------------------
  ------------------
  127|       |
  128|     15|    ht->used = 0;
  129|     15|    ht->size = size;
  130|     15|    ht->val_equal = val_equal;
  131|     15|    ht->cb_data = cb_data;
  132|     15|    ht->resize = resize;
  133|       |
  134|     15|    ht->rec_size = SIZEOF_LY_HT_REC + val_size;
  ------------------
  |  |   51|     15|#define SIZEOF_LY_HT_REC (sizeof(struct ly_ht_rec) - 1)
  ------------------
  135|     15|    if (lyht_init_hlists_and_records(ht) != LY_SUCCESS) {
  ------------------
  |  Branch (135:9): [True: 0, False: 15]
  ------------------
  136|      0|        free(ht);
  137|      0|        return NULL;
  138|      0|    }
  139|       |
  140|     15|    return ht;
  141|     15|}
lyht_free:
  183|     20|{
  184|     20|    struct ly_ht_rec *rec;
  185|     20|    uint32_t hlist_idx;
  186|     20|    uint32_t rec_idx;
  187|       |
  188|     20|    if (!ht) {
  ------------------
  |  Branch (188:9): [True: 5, False: 15]
  ------------------
  189|      5|        return;
  190|      5|    }
  191|       |
  192|     15|    if (val_free) {
  ------------------
  |  Branch (192:9): [True: 0, False: 15]
  ------------------
  193|      0|        LYHT_ITER_ALL_RECS(ht, hlist_idx, rec_idx, rec) {
  ------------------
  |  |  113|      0|    for (hlist_idx = 0; hlist_idx < ht->size; hlist_idx++)           \
  |  |  ------------------
  |  |  |  Branch (113:25): [True: 0, False: 0]
  |  |  ------------------
  |  |  114|      0|        LYHT_ITER_HLIST_RECS(ht, hlist_idx, rec_idx, rec)
  |  |  ------------------
  |  |  |  |  105|      0|    for (rec_idx = ht->hlists[hlist_idx].first,                         \
  |  |  |  |  106|      0|             rec = lyht_get_rec(ht->recs, ht->rec_size, rec_idx);       \
  |  |  |  |  107|      0|         rec_idx != LYHT_NO_RECORD;                                     \
  |  |  |  |  ------------------
  |  |  |  |  |  |   94|      0|#define LYHT_NO_RECORD UINT32_MAX
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (107:10): [True: 0, False: 0]
  |  |  |  |  ------------------
  |  |  |  |  108|      0|         rec_idx = rec->next,                                           \
  |  |  |  |  109|      0|             rec = lyht_get_rec(ht->recs, ht->rec_size, rec_idx))
  |  |  ------------------
  ------------------
  194|      0|            val_free(&rec->val);
  195|      0|        }
  196|      0|    }
  197|     15|    free(ht->hlists);
  198|     15|    free(ht->recs);
  199|     15|    free(ht);
  200|     15|}
hash_table.c:lyht_init_hlists_and_records:
   87|     15|{
   88|     15|    struct ly_ht_rec *rec;
   89|     15|    uint32_t i;
   90|       |
   91|     15|    ht->recs = calloc(ht->size, ht->rec_size);
   92|     15|    LY_CHECK_ERR_RET(!ht->recs, LOGMEM(NULL), LY_EMEM);
  ------------------
  |  |  181|     15|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 15]
  |  |  ------------------
  ------------------
   93|  10.2k|    for (i = 0; i < ht->size; i++) {
  ------------------
  |  Branch (93:17): [True: 10.2k, False: 15]
  ------------------
   94|  10.2k|        rec = lyht_get_rec(ht->recs, ht->rec_size, i);
   95|  10.2k|        if (i != ht->size) {
  ------------------
  |  Branch (95:13): [True: 10.2k, False: 0]
  ------------------
   96|  10.2k|            rec->next = i + 1;
   97|  10.2k|        } else {
   98|      0|            rec->next = LYHT_NO_RECORD;
  ------------------
  |  |   94|      0|#define LYHT_NO_RECORD UINT32_MAX
  ------------------
   99|      0|        }
  100|  10.2k|    }
  101|       |
  102|     15|    ht->hlists = malloc(sizeof(ht->hlists[0]) * ht->size);
  103|     15|    LY_CHECK_ERR_RET(!ht->hlists, free(ht->recs); LOGMEM(NULL), LY_EMEM);
  ------------------
  |  |  181|     15|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 15]
  |  |  ------------------
  ------------------
  104|  10.2k|    for (i = 0; i < ht->size; i++) {
  ------------------
  |  Branch (104:17): [True: 10.2k, False: 15]
  ------------------
  105|  10.2k|        ht->hlists[i].first = LYHT_NO_RECORD;
  ------------------
  |  |   94|  10.2k|#define LYHT_NO_RECORD UINT32_MAX
  ------------------
  106|  10.2k|        ht->hlists[i].last = LYHT_NO_RECORD;
  ------------------
  |  |   94|  10.2k|#define LYHT_NO_RECORD UINT32_MAX
  ------------------
  107|  10.2k|    }
  108|     15|    ht->first_free_rec = 0;
  109|       |
  110|     15|    return LY_SUCCESS;
  111|     15|}

hash_table.c:lyht_get_rec:
   99|  10.2k|{
  100|  10.2k|    return (struct ly_ht_rec *)&recs[idx * rec_size];
  101|  10.2k|}
dict.c:lyht_get_rec:
   99|  10.2k|{
  100|  10.2k|    return (struct ly_ht_rec *)&recs[idx * rec_size];
  101|  10.2k|}

ly_err_free:
  208|      5|{
  209|      5|    struct ly_err_item *e, *next;
  210|       |
  211|       |    /* clean the error list */
  212|      5|    LY_LIST_FOR_SAFE(ptr, next, e) {
  ------------------
  |  |  195|      5|    for ((ELEM) = (START); \
  |  |  196|      5|         (ELEM) ? (NEXT = (ELEM)->next, 1) : 0; \
  |  |  ------------------
  |  |  |  Branch (196:10): [True: 0, False: 5]
  |  |  |  Branch (196:10): [True: 0, False: 5]
  |  |  ------------------
  |  |  197|      5|         (ELEM) = (NEXT))
  ------------------
  213|      0|        free(e->msg);
  214|      0|        free(e->data_path);
  215|      0|        free(e->schema_path);
  216|      0|        free(e->apptag);
  217|      0|        free(e);
  218|      0|    }
  219|      5|}
ly_log_options:
  263|      1|{
  264|      1|    uint32_t prev = ATOMIC_LOAD_RELAXED(ly_log_opts);
  ------------------
  |  |  133|      1|# define ATOMIC_LOAD_RELAXED(var) atomic_load_explicit(&(var), memory_order_relaxed)
  ------------------
  265|       |
  266|       |    ATOMIC_STORE_RELAXED(ly_log_opts, opts);
  ------------------
  |  |  132|      1|# define ATOMIC_STORE_RELAXED(var, x) atomic_store_explicit(&(var), x, memory_order_relaxed)
  ------------------
  267|      1|    return prev;
  268|      1|}
ly_log:
  639|     15|{
  640|     15|    va_list ap;
  641|       |
  642|     15|    va_start(ap, format);
  643|     15|    log_vprintf(ctx, level, err, 0, NULL, NULL, 0, NULL, format, ap);
  644|       |    va_end(ap);
  645|     15|}
ly_vlog:
  726|      5|{
  727|      5|    va_list ap;
  728|      5|    char *data_path = NULL, *schema_path = NULL;
  729|      5|    uint64_t line = 0;
  730|       |
  731|      5|    if (ctx) {
  ------------------
  |  Branch (731:9): [True: 5, False: 0]
  ------------------
  732|      5|        ly_vlog_build_path_line(ctx, lnode, NULL, &data_path, &schema_path, &line);
  733|      5|    }
  734|       |
  735|      5|    va_start(ap, format);
  736|       |
  737|       |    /* spends paths */
  738|      5|    log_vprintf(ctx, LY_LLERR, LY_EVALID, code, data_path, schema_path, line, apptag, format, ap);
  739|       |
  740|       |    va_end(ap);
  741|      5|}
log.c:log_vprintf:
  539|     20|{
  540|     20|    char *dyn_msg = NULL;
  541|     20|    const char *msg;
  542|     20|    ly_bool free_strs = 1, lolog, lostore;
  543|       |
  544|     20|    if (log_is_noop(&lolog, &lostore)) {
  ------------------
  |  Branch (544:9): [True: 20, False: 0]
  ------------------
  545|       |        /* do not print or store the message */
  546|     20|        goto cleanup;
  547|     20|    }
  548|       |
  549|      0|    if (err == LY_EMEM) {
  ------------------
  |  Branch (549:9): [True: 0, False: 0]
  ------------------
  550|       |        /* no not use more dynamic memory */
  551|      0|        vsnprintf(last_msg, LY_LAST_MSG_SIZE, format, args);
  ------------------
  |  |   75|      0|#define LY_LAST_MSG_SIZE 512
  ------------------
  552|      0|        msg = last_msg;
  553|      0|    } else {
  554|       |        /* print into a single message */
  555|      0|        if (vasprintf(&dyn_msg, format, args) == -1) {
  ------------------
  |  Branch (555:13): [True: 0, False: 0]
  ------------------
  556|      0|            LOGMEM(ctx);
  ------------------
  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  ------------------
  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  ------------------
  ------------------
  557|      0|            goto cleanup;
  558|      0|        }
  559|      0|        msg = dyn_msg;
  560|       |
  561|       |        /* store as the last message */
  562|      0|        strncpy(last_msg, msg, LY_LAST_MSG_SIZE - 1);
  ------------------
  |  |   75|      0|#define LY_LAST_MSG_SIZE 512
  ------------------
  563|      0|    }
  564|       |
  565|       |    /* store the error/warning in the context (if we need to store errors internally, it does not matter what are
  566|       |     * the user log options), if the message is not dynamic, it would most likely fail to store (no memory) */
  567|      0|    if ((level <= ATOMIC_LOAD_RELAXED(ly_ll)) && (level < LY_LLVRB) && ctx && lostore && dyn_msg) {
  ------------------
  |  |  133|      0|# define ATOMIC_LOAD_RELAXED(var) atomic_load_explicit(&(var), memory_order_relaxed)
  ------------------
  |  Branch (567:9): [True: 0, False: 0]
  |  Branch (567:50): [True: 0, False: 0]
  |  Branch (567:72): [True: 0, False: 0]
  |  Branch (567:79): [True: 0, False: 0]
  |  Branch (567:90): [True: 0, False: 0]
  ------------------
  568|      0|        free_strs = 0;
  569|      0|        if (log_store(ctx, level, err, vecode, dyn_msg, data_path, schema_path, line, apptag ? strdup(apptag) : NULL)) {
  ------------------
  |  Branch (569:13): [True: 0, False: 0]
  |  Branch (569:87): [True: 0, False: 0]
  ------------------
  570|      0|            goto cleanup;
  571|      0|        }
  572|      0|    }
  573|       |
  574|       |    /* if we are only storing errors internally, never print the message (yet) */
  575|      0|    if (lolog) {
  ------------------
  |  Branch (575:9): [True: 0, False: 0]
  ------------------
  576|      0|        if (temp_log_clb) {
  ------------------
  |  Branch (576:13): [True: 0, False: 0]
  ------------------
  577|      0|            temp_log_clb(level, msg, data_path, schema_path, line);
  578|      0|        } else if (log_clb) {
  ------------------
  |  Branch (578:20): [True: 0, False: 0]
  ------------------
  579|      0|            log_clb(level, msg, data_path, schema_path, line);
  580|      0|        } else if (level <= ATOMIC_LOAD_RELAXED(ly_ll)) {
  ------------------
  |  |  133|      0|# define ATOMIC_LOAD_RELAXED(var) atomic_load_explicit(&(var), memory_order_relaxed)
  ------------------
  |  Branch (580:20): [True: 0, False: 0]
  ------------------
  581|      0|            fprintf(stderr, "libyang[%d]: ", level);
  582|      0|            fprintf(stderr, "%s", msg);
  583|      0|            log_stderr_path_line(data_path, schema_path, line);
  584|      0|        }
  585|      0|    }
  586|       |
  587|     20|cleanup:
  588|     20|    if (free_strs) {
  ------------------
  |  Branch (588:9): [True: 20, False: 0]
  ------------------
  589|     20|        free(data_path);
  590|     20|        free(schema_path);
  591|     20|        free(dyn_msg);
  592|     20|    }
  593|     20|}
log.c:log_is_noop:
  500|     20|{
  501|     20|    ly_bool lolog, lostore;
  502|       |
  503|       |    /* learn effective logger options */
  504|     20|    if (temp_ly_log_opts) {
  ------------------
  |  Branch (504:9): [True: 0, False: 20]
  ------------------
  505|      0|        lolog = *temp_ly_log_opts & LY_LOLOG;
  ------------------
  |  |  119|      0|#define LY_LOLOG        0x01 /**< Log messages normally, using callback if set. If not set, messages will
  ------------------
  506|      0|        lostore = *temp_ly_log_opts & LY_LOSTORE;
  ------------------
  |  |  121|      0|#define LY_LOSTORE      0x02 /**< Store any generated errors or warnings, never verbose or debug messages.
  ------------------
  507|     20|    } else {
  508|     20|        lolog = ATOMIC_LOAD_RELAXED(ly_log_opts) & LY_LOLOG;
  ------------------
  |  |  133|     20|# define ATOMIC_LOAD_RELAXED(var) atomic_load_explicit(&(var), memory_order_relaxed)
  ------------------
                      lolog = ATOMIC_LOAD_RELAXED(ly_log_opts) & LY_LOLOG;
  ------------------
  |  |  119|     20|#define LY_LOLOG        0x01 /**< Log messages normally, using callback if set. If not set, messages will
  ------------------
  509|     20|        lostore = ATOMIC_LOAD_RELAXED(ly_log_opts) & LY_LOSTORE;
  ------------------
  |  |  133|     20|# define ATOMIC_LOAD_RELAXED(var) atomic_load_explicit(&(var), memory_order_relaxed)
  ------------------
                      lostore = ATOMIC_LOAD_RELAXED(ly_log_opts) & LY_LOSTORE;
  ------------------
  |  |  121|     20|#define LY_LOSTORE      0x02 /**< Store any generated errors or warnings, never verbose or debug messages.
  ------------------
  510|     20|    }
  511|       |
  512|     20|    if (will_log) {
  ------------------
  |  Branch (512:9): [True: 20, False: 0]
  ------------------
  513|     20|        *will_log = lolog;
  514|     20|    }
  515|     20|    if (will_store) {
  ------------------
  |  Branch (515:9): [True: 20, False: 0]
  ------------------
  516|     20|        *will_store = lostore;
  517|     20|    }
  518|       |
  519|     20|    return !lolog && !lostore;
  ------------------
  |  Branch (519:12): [True: 20, False: 0]
  |  Branch (519:22): [True: 20, False: 0]
  ------------------
  520|     20|}
log.c:ly_vlog_build_path_line:
  661|      5|{
  662|      5|    int r;
  663|      5|    char *path;
  664|       |
  665|      5|    *data_path = NULL;
  666|      5|    *schema_path = NULL;
  667|      5|    *line = 0;
  668|       |
  669|       |    /* data/schema node */
  670|      5|    if (lnode) {
  ------------------
  |  Branch (670:9): [True: 0, False: 5]
  ------------------
  671|      0|        *data_path = lyd_path(lnode, LYD_PATH_STD, NULL, 0);
  672|      0|        LY_CHECK_ERR_RET(!*data_path, LOGMEM(ctx), LY_EMEM);
  ------------------
  |  |  181|      0|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  673|       |
  674|      0|        if (!snode && log_location.scnodes.count) {
  ------------------
  |  Branch (674:13): [True: 0, False: 0]
  |  Branch (674:23): [True: 0, False: 0]
  ------------------
  675|      0|            snode = log_location.scnodes.objs[log_location.scnodes.count - 1];
  676|      0|        }
  677|      0|        if (snode && (!lnode || (lysc_data_parent(snode) == lnode->schema))) {
  ------------------
  |  | 1826|      0|#define lysc_data_parent(SCHEMA) lysc_data_node((SCHEMA) ? (SCHEMA)->parent : NULL)
  |  |  ------------------
  |  |  |  Branch (1826:49): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  |  Branch (677:13): [True: 0, False: 0]
  |  Branch (677:23): [True: 0, False: 0]
  |  Branch (677:33): [True: 0, False: 0]
  ------------------
  678|      0|            if (lyd_node_module(lnode) != snode->module) {
  ------------------
  |  Branch (678:17): [True: 0, False: 0]
  ------------------
  679|      0|                r = asprintf(&path, "%s/%s:%s", *data_path, snode->module->name, snode->name);
  680|      0|            } else {
  681|      0|                r = asprintf(&path, "%s/%s", *data_path, snode->name);
  682|      0|            }
  683|      0|            free(*data_path);
  684|      0|            LY_CHECK_ERR_RET(r == -1, LOGMEM(ctx), LY_EMEM);
  ------------------
  |  |  181|      0|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  685|      0|            *data_path = path;
  686|      0|            path = NULL;
  687|      0|        }
  688|      5|    } else if (snode) {
  ------------------
  |  Branch (688:16): [True: 0, False: 5]
  ------------------
  689|      0|        *schema_path = lysc_path(snode, LYSC_PATH_LOG, NULL, 0);
  690|      0|        LY_CHECK_ERR_RET(!*schema_path, LOGMEM(ctx), LY_EMEM);
  ------------------
  |  |  181|      0|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  691|      5|    } else if (log_location.scnodes.count) {
  ------------------
  |  Branch (691:16): [True: 0, False: 5]
  ------------------
  692|      0|        *schema_path = lysc_path(log_location.scnodes.objs[log_location.scnodes.count - 1], LYSC_PATH_LOG, NULL, 0);
  693|      0|        LY_CHECK_ERR_RET(!*schema_path, LOGMEM(ctx), LY_EMEM);
  ------------------
  |  |  181|      0|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  694|      0|    }
  695|       |
  696|      5|    if (log_location.paths.count && ((const char *)(log_location.paths.objs[log_location.paths.count - 1]))[0]) {
  ------------------
  |  Branch (696:9): [True: 0, False: 5]
  |  Branch (696:37): [True: 0, False: 0]
  ------------------
  697|       |        /* append the provided path string to data/schema path, if any */
  698|      0|        if (*data_path) {
  ------------------
  |  Branch (698:13): [True: 0, False: 0]
  ------------------
  699|      0|            r = asprintf(&path, "%s%s", *data_path, (char *)log_location.paths.objs[log_location.paths.count - 1]);
  700|      0|        } else if (*schema_path) {
  ------------------
  |  Branch (700:20): [True: 0, False: 0]
  ------------------
  701|      0|            r = asprintf(&path, "%s%s", *schema_path, (char *)log_location.paths.objs[log_location.paths.count - 1]);
  702|      0|        } else {
  703|      0|            r = asprintf(&path, "%s", (char *)log_location.paths.objs[log_location.paths.count - 1]);
  704|      0|        }
  705|      0|        LY_CHECK_ERR_RET(r == -1, LOGMEM(ctx), LY_EMEM);
  ------------------
  |  |  181|      0|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  706|       |
  707|      0|        if (*data_path) {
  ------------------
  |  Branch (707:13): [True: 0, False: 0]
  ------------------
  708|      0|            free(*data_path);
  709|      0|            *data_path = path;
  710|      0|        } else {
  711|      0|            free(*schema_path);
  712|      0|            *schema_path = path;
  713|      0|        }
  714|      0|    }
  715|       |
  716|       |    /* line */
  717|      5|    if (log_location.inputs.count) {
  ------------------
  |  Branch (717:9): [True: 0, False: 5]
  ------------------
  718|      0|        *line = ((struct ly_in *)log_location.inputs.objs[log_location.inputs.count - 1])->line;
  719|      0|    }
  720|       |
  721|      5|    return LY_SUCCESS;
  722|      5|}

ly_ctx_data_add:
  459|      5|{
  460|      5|    LY_ERR rc = LY_SUCCESS;
  461|      5|    struct ly_ctx_private_data *private_data;
  462|      5|    struct ly_ctx_shared_data *shared_data;
  463|       |
  464|       |    /* WR LOCK */
  465|      5|    pthread_rwlock_wrlock(&ly_ctx_data_rwlock);
  466|       |
  467|       |    /* check for duplicates in private context data, not allowed */
  468|      5|    private_data = _ly_ctx_private_data_get(ctx, 1);
  469|      5|    if (private_data) {
  ------------------
  |  Branch (469:9): [True: 0, False: 5]
  ------------------
  470|       |        /* ctx pointers can match only if the context is printed (they have the same memory address) */
  471|      0|        assert(private_data->ctx->opts & LY_CTX_INT_IMMUTABLE);
  ------------------
  |  Branch (471:9): [True: 0, False: 0]
  ------------------
  472|       |
  473|       |        /* use NULL as ctx to avoid RD lock while holding WR lock */
  474|      0|        LOGERR(NULL, LY_EEXIST, "Only one printed context per memory chunk and thread is allowed.");
  ------------------
  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  ------------------
  475|      0|        rc = LY_EEXIST;
  476|      0|        goto cleanup;
  477|      0|    }
  478|       |
  479|       |    /* create the private context data, freed by the caller in case we fail later on */
  480|      5|    rc = ly_ctx_private_data_create(ctx, &private_data);
  481|      5|    if (rc) {
  ------------------
  |  Branch (481:9): [True: 0, False: 5]
  ------------------
  482|       |        /* NULL to avoid infinite loop in LOGERR */
  483|      0|        LOGERR(NULL, rc, "Failed to create context private data.");
  ------------------
  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  ------------------
  484|      0|        goto cleanup;
  485|      0|    }
  486|       |
  487|       |    /* check for duplicates in shared context data */
  488|      5|    shared_data = _ly_ctx_shared_data_get(ctx);
  489|      5|    if (shared_data) {
  ------------------
  |  Branch (489:9): [True: 0, False: 5]
  ------------------
  490|       |        /* found, we can end */
  491|      0|        ATOMIC_INC_RELAXED(shared_data->refcount);
  ------------------
  |  |  134|      0|# define ATOMIC_INC_RELAXED(var) atomic_fetch_add_explicit(&(var), 1, memory_order_relaxed)
  ------------------
  492|      0|        goto cleanup;
  493|      0|    }
  494|       |
  495|       |    /* create the shared context data */
  496|      5|    rc = ly_ctx_shared_data_create(ctx, NULL);
  497|      5|    if (rc) {
  ------------------
  |  Branch (497:9): [True: 0, False: 5]
  ------------------
  498|       |        /* NULL to avoid infinite loop in LOGERR */
  499|      0|        LOGERR(NULL, rc, "Failed to create context shared data.");
  ------------------
  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  ------------------
  500|      0|        goto cleanup;
  501|      0|    }
  502|       |
  503|      5|cleanup:
  504|       |    /* WR UNLOCK */
  505|      5|    pthread_rwlock_unlock(&ly_ctx_data_rwlock);
  506|      5|    return rc;
  507|      5|}
ly_ctx_data_del:
  511|      5|{
  512|      5|    struct ly_ctx_private_data *private_data;
  513|      5|    struct ly_ctx_shared_data *shared_data;
  514|       |
  515|       |    /* WR LOCK */
  516|      5|    pthread_rwlock_wrlock(&ly_ctx_data_rwlock);
  517|       |
  518|       |    /* free private data of all the threads for this context */
  519|     10|    while ((private_data = _ly_ctx_private_data_get(ctx, 0))) {
  ------------------
  |  Branch (519:12): [True: 5, False: 5]
  ------------------
  520|       |        /* free the private data */
  521|      5|        ly_ctx_private_data_remove_and_free(private_data);
  522|      5|    }
  523|       |
  524|       |    /* get the shared context data */
  525|      5|    shared_data = _ly_ctx_shared_data_get(ctx);
  526|      5|    if (!shared_data) {
  ------------------
  |  Branch (526:9): [True: 0, False: 5]
  ------------------
  527|       |        /* not found, nothing to do */
  528|      0|        goto cleanup;
  529|      0|    }
  530|      5|    assert(ATOMIC_LOAD_RELAXED(shared_data->refcount));
  ------------------
  |  Branch (530:5): [True: 5, False: 0]
  ------------------
  531|       |
  532|       |    /* decrease refcount */
  533|      5|    ATOMIC_DEC_RELAXED(shared_data->refcount);
  ------------------
  |  |  136|      5|# define ATOMIC_DEC_RELAXED(var) atomic_fetch_sub_explicit(&(var), 1, memory_order_relaxed)
  ------------------
  534|      5|    if (ATOMIC_LOAD_RELAXED(shared_data->refcount)) {
  ------------------
  |  |  133|      5|# define ATOMIC_LOAD_RELAXED(var) atomic_load_explicit(&(var), memory_order_relaxed)
  |  |  ------------------
  |  |  |  Branch (133:35): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  535|      0|        goto cleanup;
  536|      0|    }
  537|       |
  538|       |    /* free the shared members */
  539|      5|    ly_ctx_shared_data_remove_and_free(shared_data);
  540|       |
  541|      5|cleanup:
  542|       |    /* WR UNLOCK */
  543|      5|    pthread_rwlock_unlock(&ly_ctx_data_rwlock);
  544|      5|}
ly_common.c:_ly_ctx_private_data_get:
  232|     15|{
  233|     15|    struct ly_ctx_private_data **iter;
  234|     15|    ly_bool found = 0;
  235|     15|    pthread_t tid = pthread_self();
  236|       |
  237|     15|    LY_ARRAY_FOR(ly_private_ctx_data, struct ly_ctx_private_data *, iter) {
  ------------------
  |  |  167|     15|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  ------------------
  |  |  |  |  114|     15|#define LY_ARRAY_SELECT(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  167|     15|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  126|     15|    for (ITER = ARRAY; \
  |  |  |  |  |  |  |  |  127|     15|         (ARRAY) && ((char *)ITER - (char *)ARRAY)/(sizeof(TYPE)) < (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)); \
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (127:10): [True: 5, False: 10]
  |  |  |  |  |  |  |  |  |  Branch (127:21): [True: 5, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  128|     15|         ITER = (TYPE*)ITER + 1)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  238|       |        /* either own - ctx and tid match, or "context's" - thread does not matter */
  239|      5|        if (((*iter)->ctx == ctx) && (!own_data_only || pthread_equal((*iter)->tid, tid))) {
  ------------------
  |  Branch (239:13): [True: 5, False: 0]
  |  Branch (239:39): [True: 5, False: 0]
  |  Branch (239:57): [True: 0, False: 0]
  ------------------
  240|      5|            found = 1;
  241|      5|            break;
  242|      5|        }
  243|      5|    }
  244|       |
  245|     15|    return found ? *iter : NULL;
  ------------------
  |  Branch (245:12): [True: 5, False: 10]
  ------------------
  246|     15|}
ly_common.c:ly_ctx_private_data_create:
  197|      5|{
  198|      5|    pthread_t tid = pthread_self();
  199|      5|    struct ly_ctx_private_data **priv_data = NULL;
  200|      5|    LY_ERR rc = LY_SUCCESS;
  201|       |
  202|      5|    *private_data = NULL;
  203|       |
  204|       |    /* create the private context data */
  205|      5|    LY_ARRAY_NEW_GOTO(ctx, ly_private_ctx_data, priv_data, rc, cleanup);
  ------------------
  |  |  113|      5|    LY_ARRAY_NEW(CTX, ARRAY, RET = LY_EMEM; goto GOTO); \
  |  |  ------------------
  |  |  |  |   61|      5|    { \
  |  |  |  |   62|      5|        char *p__; \
  |  |  |  |   63|      5|        if (ARRAY) { \
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (63:13): [True: 0, False: 5]
  |  |  |  |  ------------------
  |  |  |  |   64|      0|            ++(*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)); \
  |  |  |  |   65|      0|            p__ = (char *)realloc(((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1), \
  |  |  |  |   66|      0|                    sizeof(LY_ARRAY_COUNT_TYPE) + (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1) * sizeof *(ARRAY))); \
  |  |  |  |   67|      0|            if (!p__) { \
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (67:17): [True: 0, False: 0]
  |  |  |  |  ------------------
  |  |  |  |   68|      0|                --(*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)); \
  |  |  |  |   69|      0|                LOGMEM(CTX); \
  |  |  |  |  ------------------
  |  |  |  |  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  |  |   70|      0|                EACTION; \
  |  |  |  |   71|      0|            } \
  |  |  |  |   72|      5|        } else { \
  |  |  |  |   73|      5|            p__ = (char *)malloc(sizeof(LY_ARRAY_COUNT_TYPE) + sizeof *(ARRAY)); \
  |  |  |  |   74|      5|            if (!p__) { \
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (74:17): [True: 0, False: 5]
  |  |  |  |  ------------------
  |  |  |  |   75|      0|                LOGMEM(CTX); \
  |  |  |  |  ------------------
  |  |  |  |  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  |  |   76|      0|                EACTION; \
  |  |  |  |   77|      0|            } \
  |  |  |  |   78|      5|            *((LY_ARRAY_COUNT_TYPE*)(p__)) = 1; \
  |  |  |  |   79|      5|        } \
  |  |  |  |   80|      5|        p__ = (char *)((LY_ARRAY_COUNT_TYPE*)(p__) + 1); \
  |  |  |  |   81|      5|        memcpy(&(ARRAY), &p__, sizeof p__); \
  |  |  |  |   82|      5|    }
  |  |  ------------------
  |  |  114|      5|    (NEW_ITEM) = &(ARRAY)[*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1) - 1]; \
  |  |  115|      5|    memset(NEW_ITEM, 0, sizeof *(NEW_ITEM))
  ------------------
  206|      5|    *priv_data = calloc(1, sizeof **priv_data);
  207|      5|    LY_CHECK_ERR_GOTO(!*priv_data, LOGMEM(ctx); rc = LY_EMEM, cleanup);
  ------------------
  |  |  177|      5|#define LY_CHECK_ERR_GOTO(COND, ERR, GOTO) if ((COND)) {ERR; goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (177:48): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  208|       |
  209|       |    /* fill */
  210|      5|    (*priv_data)->tid = tid;
  211|      5|    (*priv_data)->ctx = ctx;
  212|      5|    (*priv_data)->errs = NULL;
  213|       |
  214|      5|    *private_data = *priv_data;
  215|       |
  216|      5|cleanup:
  217|      5|    if (rc && priv_data) {
  ------------------
  |  Branch (217:9): [True: 0, False: 5]
  |  Branch (217:15): [True: 0, False: 0]
  ------------------
  218|      0|        ly_ctx_private_data_remove_and_free(*priv_data);
  219|      0|    }
  220|      5|    return rc;
  221|      5|}
ly_common.c:_ly_ctx_shared_data_get:
  408|     10|{
  409|     10|    struct ly_ctx_shared_data **iter;
  410|     10|    ly_bool found = 0;
  411|       |
  412|     10|    LY_ARRAY_FOR(ly_shared_ctx_data, struct ly_ctx_shared_data *, iter) {
  ------------------
  |  |  167|     10|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  ------------------
  |  |  |  |  114|     10|#define LY_ARRAY_SELECT(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  167|     10|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  126|     10|    for (ITER = ARRAY; \
  |  |  |  |  |  |  |  |  127|     10|         (ARRAY) && ((char *)ITER - (char *)ARRAY)/(sizeof(TYPE)) < (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)); \
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (127:10): [True: 5, False: 5]
  |  |  |  |  |  |  |  |  |  Branch (127:21): [True: 5, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  128|     10|         ITER = (TYPE*)ITER + 1)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  413|      5|        if ((*iter)->ctx == ctx) {
  ------------------
  |  Branch (413:13): [True: 5, False: 0]
  ------------------
  414|      5|            found = 1;
  415|      5|            break;
  416|      5|        }
  417|      5|    }
  418|       |
  419|     10|    return found ? *iter : NULL;
  ------------------
  |  Branch (419:12): [True: 5, False: 5]
  ------------------
  420|     10|}
ly_common.c:ly_ctx_shared_data_create:
  340|      5|{
  341|      5|    LY_ERR rc = LY_SUCCESS;
  342|      5|    struct ly_ctx_shared_data **shrd_data = NULL;
  343|      5|    pthread_mutexattr_t attr;
  344|       |
  345|      5|    if (shared_data) {
  ------------------
  |  Branch (345:9): [True: 0, False: 5]
  ------------------
  346|      0|        *shared_data = NULL;
  347|      0|    }
  348|       |
  349|       |    /* create the shared context data */
  350|      5|    LY_ARRAY_NEW_GOTO(ctx, ly_shared_ctx_data, shrd_data, rc, cleanup);
  ------------------
  |  |  113|      5|    LY_ARRAY_NEW(CTX, ARRAY, RET = LY_EMEM; goto GOTO); \
  |  |  ------------------
  |  |  |  |   61|      5|    { \
  |  |  |  |   62|      5|        char *p__; \
  |  |  |  |   63|      5|        if (ARRAY) { \
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (63:13): [True: 0, False: 5]
  |  |  |  |  ------------------
  |  |  |  |   64|      0|            ++(*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)); \
  |  |  |  |   65|      0|            p__ = (char *)realloc(((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1), \
  |  |  |  |   66|      0|                    sizeof(LY_ARRAY_COUNT_TYPE) + (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1) * sizeof *(ARRAY))); \
  |  |  |  |   67|      0|            if (!p__) { \
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (67:17): [True: 0, False: 0]
  |  |  |  |  ------------------
  |  |  |  |   68|      0|                --(*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)); \
  |  |  |  |   69|      0|                LOGMEM(CTX); \
  |  |  |  |  ------------------
  |  |  |  |  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  |  |   70|      0|                EACTION; \
  |  |  |  |   71|      0|            } \
  |  |  |  |   72|      5|        } else { \
  |  |  |  |   73|      5|            p__ = (char *)malloc(sizeof(LY_ARRAY_COUNT_TYPE) + sizeof *(ARRAY)); \
  |  |  |  |   74|      5|            if (!p__) { \
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (74:17): [True: 0, False: 5]
  |  |  |  |  ------------------
  |  |  |  |   75|      0|                LOGMEM(CTX); \
  |  |  |  |  ------------------
  |  |  |  |  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  |  |   76|      0|                EACTION; \
  |  |  |  |   77|      0|            } \
  |  |  |  |   78|      5|            *((LY_ARRAY_COUNT_TYPE*)(p__)) = 1; \
  |  |  |  |   79|      5|        } \
  |  |  |  |   80|      5|        p__ = (char *)((LY_ARRAY_COUNT_TYPE*)(p__) + 1); \
  |  |  |  |   81|      5|        memcpy(&(ARRAY), &p__, sizeof p__); \
  |  |  |  |   82|      5|    }
  |  |  ------------------
  |  |  114|      5|    (NEW_ITEM) = &(ARRAY)[*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1) - 1]; \
  |  |  115|      5|    memset(NEW_ITEM, 0, sizeof *(NEW_ITEM))
  ------------------
  351|      5|    *shrd_data = calloc(1, sizeof **shrd_data);
  352|      5|    LY_CHECK_ERR_GOTO(!*shrd_data, LOGMEM(ctx); rc = LY_EMEM, cleanup);
  ------------------
  |  |  177|      5|#define LY_CHECK_ERR_GOTO(COND, ERR, GOTO) if ((COND)) {ERR; goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (177:48): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  353|       |
  354|       |    /* fill */
  355|      5|    (*shrd_data)->ctx = ctx;
  356|       |
  357|       |    /* pattern hash table */
  358|      5|    (*shrd_data)->pattern_ht = lyht_new(LYHT_MIN_SIZE, sizeof(struct ly_pattern_ht_rec),
  ------------------
  |  |   39|      5|#define LYHT_MIN_SIZE 8
  ------------------
  359|      5|            ly_ctx_ht_pattern_equal_cb, NULL, 1);
  360|      5|    LY_CHECK_ERR_GOTO(!(*shrd_data)->pattern_ht, rc = LY_EMEM, cleanup);
  ------------------
  |  |  177|      5|#define LY_CHECK_ERR_GOTO(COND, ERR, GOTO) if ((COND)) {ERR; goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (177:48): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  361|       |
  362|       |    /* data dictionary */
  363|      5|    (*shrd_data)->data_dict = malloc(sizeof *(*shrd_data)->data_dict);
  364|      5|    LY_CHECK_ERR_GOTO(!(*shrd_data)->data_dict, rc = LY_EMEM, cleanup);
  ------------------
  |  |  177|      5|#define LY_CHECK_ERR_GOTO(COND, ERR, GOTO) if ((COND)) {ERR; goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (177:48): [True: 0, False: 5]
  |  |  ------------------
  ------------------
  365|      5|    lydict_init((*shrd_data)->data_dict);
  366|       |
  367|       |    /* leafref set */
  368|      5|    if (ctx->opts & LY_CTX_LEAFREF_LINKING) {
  ------------------
  |  |  226|      5|#define LY_CTX_LEAFREF_LINKING 0x1000 /**< Link valid leafref nodes with its target during validation if leafref node is not using
  ------------------
  |  Branch (368:9): [True: 0, False: 5]
  ------------------
  369|       |        /**
  370|       |         * storing the pointer instead of record itself is needed to avoid invalid memory reads. Hash table can reallocate
  371|       |         * its memory completely during various manipulation function (e.g. remove, insert). In case of using pointers, the
  372|       |         * pointer can be reallocated safely, while record itself remains untouched and can be accessed/modified freely
  373|       |         * */
  374|      0|        (*shrd_data)->leafref_links_ht = lyht_new(1, sizeof(struct lyd_leafref_links_rec *),
  375|      0|                ly_ctx_ht_leafref_links_equal_cb, NULL, 1);
  376|      0|        LY_CHECK_ERR_GOTO(!(*shrd_data)->leafref_links_ht, rc = LY_EMEM, cleanup);
  ------------------
  |  |  177|      0|#define LY_CHECK_ERR_GOTO(COND, ERR, GOTO) if ((COND)) {ERR; goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (177:48): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  377|      0|    }
  378|       |
  379|       |    /* ext clb and leafref links locks */
  380|      5|    pthread_mutexattr_init(&attr);
  381|      5|    pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE);
  382|      5|    pthread_mutex_init(&(*shrd_data)->ext_clb_lock, &attr);
  383|      5|    pthread_mutexattr_destroy(&attr);
  384|      5|    pthread_mutex_init(&(*shrd_data)->leafref_links_lock, NULL);
  385|       |
  386|       |    /* refcount */
  387|      5|    ATOMIC_STORE_RELAXED((*shrd_data)->refcount, 1);
  ------------------
  |  |  132|      5|# define ATOMIC_STORE_RELAXED(var, x) atomic_store_explicit(&(var), x, memory_order_relaxed)
  ------------------
  388|       |
  389|      5|    if (shared_data) {
  ------------------
  |  Branch (389:9): [True: 0, False: 5]
  ------------------
  390|      0|        *shared_data = *shrd_data;
  391|      0|    }
  392|       |
  393|      5|cleanup:
  394|      5|    if (rc && shrd_data) {
  ------------------
  |  Branch (394:9): [True: 0, False: 5]
  |  Branch (394:15): [True: 0, False: 0]
  ------------------
  395|      0|        ly_ctx_shared_data_remove_and_free(*shrd_data);
  396|      0|    }
  397|      5|    return rc;
  398|      5|}
ly_common.c:ly_ctx_private_data_remove_and_free:
  161|      5|{
  162|      5|    LY_ARRAY_COUNT_TYPE u;
  ------------------
  |  |  104|      5|#define LY_ARRAY_COUNT_TYPE uint64_t
  ------------------
  163|       |
  164|      5|    if (!private_data) {
  ------------------
  |  Branch (164:9): [True: 0, False: 5]
  ------------------
  165|      0|        return;
  166|      0|    }
  167|       |
  168|       |    /* free members */
  169|      5|    ly_err_free(private_data->errs);
  170|      5|    free(private_data);
  171|       |
  172|       |    /* find */
  173|      5|    LY_ARRAY_FOR(ly_private_ctx_data, u) {
  ------------------
  |  |  167|      5|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  ------------------
  |  |  |  |  114|      5|#define LY_ARRAY_SELECT(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  167|      5|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  141|      5|    for (INDEX = 0; \
  |  |  |  |  |  |  |  |  142|      5|         INDEX < LY_ARRAY_COUNT(ARRAY); \
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  148|      5|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (148:32): [True: 5, False: 0]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (142:10): [True: 5, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  143|      5|         ++INDEX)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  174|      5|        if (ly_private_ctx_data[u] == private_data) {
  ------------------
  |  Branch (174:13): [True: 5, False: 0]
  ------------------
  175|      5|            break;
  176|      5|        }
  177|      5|    }
  178|      5|    assert(u < LY_ARRAY_COUNT(ly_private_ctx_data));
  ------------------
  |  Branch (178:5): [True: 5, False: 0]
  |  Branch (178:5): [True: 5, False: 0]
  ------------------
  179|       |
  180|       |    /* remove */
  181|      5|    if (u < LY_ARRAY_COUNT(ly_private_ctx_data) - 1) {
  ------------------
  |  |  148|      5|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  ------------------
  |  |  |  Branch (148:32): [True: 5, False: 0]
  |  |  ------------------
  ------------------
  |  Branch (181:9): [True: 0, False: 5]
  ------------------
  182|       |        /* replace the private data with the last one if it even was added */
  183|      0|        ly_private_ctx_data[u] = ly_private_ctx_data[LY_ARRAY_COUNT(ly_private_ctx_data) - 1];
  ------------------
  |  |  148|      0|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  ------------------
  |  |  |  Branch (148:32): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  184|      0|    }
  185|       |    LY_ARRAY_DECREMENT_FREE(ly_private_ctx_data);
  ------------------
  |  |  218|      5|        --(*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)); \
  |  |  219|      5|        if (!LY_ARRAY_COUNT(ARRAY)) { \
  |  |  ------------------
  |  |  |  |  148|      5|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (148:32): [True: 5, False: 0]
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  |  Branch (219:13): [True: 5, False: 0]
  |  |  ------------------
  |  |  220|      5|            LY_ARRAY_FREE(ARRAY); \
  |  |  ------------------
  |  |  |  |  232|      5|        if (ARRAY){free((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1);}
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (232:13): [True: 5, False: 0]
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  221|      5|            (ARRAY) = NULL; \
  |  |  222|      5|        }
  ------------------
  186|      5|}
ly_common.c:ly_ctx_shared_data_remove_and_free:
  296|      5|{
  297|      5|    LY_ARRAY_COUNT_TYPE u;
  ------------------
  |  |  104|      5|#define LY_ARRAY_COUNT_TYPE uint64_t
  ------------------
  298|       |
  299|      5|    if (!shared_data) {
  ------------------
  |  Branch (299:9): [True: 0, False: 5]
  ------------------
  300|      0|        return;
  301|      0|    }
  302|       |
  303|       |    /* all the patterns must have been removed already,
  304|       |     * either while free compiled modules (standard behavior)
  305|       |     * or when assigning a parent to a context, it's shared data will be used (schema mount) */
  306|      5|    assert(shared_data->pattern_ht->used == 0);
  ------------------
  |  Branch (306:5): [True: 5, False: 0]
  ------------------
  307|      5|    lyht_free(shared_data->pattern_ht, NULL);
  308|       |
  309|       |    /* free rest of the members */
  310|      5|    lydict_clean(shared_data->data_dict);
  311|      5|    free(shared_data->data_dict);
  312|      5|    lyht_free(shared_data->leafref_links_ht, ly_ctx_ht_leafref_links_rec_free);
  313|      5|    free(shared_data);
  314|       |
  315|       |    /* find */
  316|      5|    LY_ARRAY_FOR(ly_shared_ctx_data, u) {
  ------------------
  |  |  167|      5|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  ------------------
  |  |  |  |  114|      5|#define LY_ARRAY_SELECT(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  167|      5|#define LY_ARRAY_FOR(ARRAY, ...) LY_ARRAY_SELECT(__VA_ARGS__, LY_ARRAY_FOR_ITER, LY_ARRAY_FOR_INDEX, LY_UNDEF)(ARRAY, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  141|      5|    for (INDEX = 0; \
  |  |  |  |  |  |  |  |  142|      5|         INDEX < LY_ARRAY_COUNT(ARRAY); \
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  148|      5|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  Branch (148:32): [True: 5, False: 0]
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (142:10): [True: 5, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  143|      5|         ++INDEX)
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  317|      5|        if (ly_shared_ctx_data[u] == shared_data) {
  ------------------
  |  Branch (317:13): [True: 5, False: 0]
  ------------------
  318|      5|            break;
  319|      5|        }
  320|      5|    }
  321|      5|    assert(u < LY_ARRAY_COUNT(ly_shared_ctx_data));
  ------------------
  |  Branch (321:5): [True: 5, False: 0]
  |  Branch (321:5): [True: 5, False: 0]
  ------------------
  322|       |
  323|       |    /* remove */
  324|      5|    if (u < LY_ARRAY_COUNT(ly_shared_ctx_data) - 1) {
  ------------------
  |  |  148|      5|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  ------------------
  |  |  |  Branch (148:32): [True: 5, False: 0]
  |  |  ------------------
  ------------------
  |  Branch (324:9): [True: 0, False: 5]
  ------------------
  325|       |        /* replace the shared data with the last one */
  326|      0|        ly_shared_ctx_data[u] = ly_shared_ctx_data[LY_ARRAY_COUNT(ly_shared_ctx_data) - 1];
  ------------------
  |  |  148|      0|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  ------------------
  |  |  |  Branch (148:32): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  327|      0|    }
  328|       |    LY_ARRAY_DECREMENT_FREE(ly_shared_ctx_data);
  ------------------
  |  |  218|      5|        --(*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)); \
  |  |  219|      5|        if (!LY_ARRAY_COUNT(ARRAY)) { \
  |  |  ------------------
  |  |  |  |  148|      5|#define LY_ARRAY_COUNT(ARRAY) (ARRAY ? (*((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1)) : 0)
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (148:32): [True: 5, False: 0]
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  |  Branch (219:13): [True: 5, False: 0]
  |  |  ------------------
  |  |  220|      5|            LY_ARRAY_FREE(ARRAY); \
  |  |  ------------------
  |  |  |  |  232|      5|        if (ARRAY){free((LY_ARRAY_COUNT_TYPE*)(ARRAY) - 1);}
  |  |  |  |  ------------------
  |  |  |  |  |  Branch (232:13): [True: 5, False: 0]
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  221|      5|            (ARRAY) = NULL; \
  |  |  222|      5|        }
  ------------------
  329|      5|}

lyplg_clean:
  380|      5|{
  381|       |#ifndef STATIC
  382|       |    pthread_mutex_lock(&plugins_guard);
  383|       |    lyplg_clean_();
  384|       |    pthread_mutex_unlock(&plugins_guard);
  385|       |#endif
  386|      5|}
lyplg_init:
  573|      5|{
  574|      5|    LY_ERR ret;
  575|       |
  576|       |    /* let only the first context to initiate plugins, but let others wait for finishing the initiation */
  577|      5|    pthread_mutex_lock(&plugins_guard);
  578|       |
  579|      5|    if (context_refcount++) {
  ------------------
  |  Branch (579:9): [True: 4, False: 1]
  ------------------
  580|       |        /* already initiated */
  581|      4|        pthread_mutex_unlock(&plugins_guard);
  582|      4|        return LY_SUCCESS;
  583|      4|    }
  584|       |
  585|       |    /* internal types */
  586|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_binary), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  587|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_bits), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  588|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_boolean), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  589|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_decimal64), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  590|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_empty), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  591|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_enumeration), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  592|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_identityref), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  593|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_instanceid), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  594|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_integer), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  595|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_leafref), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  596|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_string), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  597|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_union), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  598|       |
  599|       |    /* metadata and lyds_tree, which requires them */
  600|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_EXTENSION, plugins_metadata), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  601|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_lyds_tree), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  602|       |
  603|      1|    if (!builtin_type_plugins_only) {
  ------------------
  |  Branch (603:9): [True: 1, False: 0]
  ------------------
  604|       |        /* yang */
  605|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_instanceid_keys), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  606|       |
  607|       |        /* ietf-inet-types */
  608|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_ipv4_address), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  609|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_ipv4_address_no_zone), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  610|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_ipv6_address), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  611|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_ipv6_address_no_zone), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  612|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_ipv4_address_prefix), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  613|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_ipv6_address_prefix), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  614|       |
  615|       |        /* ietf-yang-types */
  616|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_date_and_time), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  617|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_date), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  618|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_time), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  619|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_hex_string), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  620|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_xpath10), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  621|       |
  622|       |        /* libnetconf2-netconf-server */
  623|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_time_period), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  624|       |
  625|       |        /* ietf-netconf-acm */
  626|      1|        LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_TYPE, plugins_node_instanceid), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  627|      1|    }
  628|       |
  629|       |    /* internal extensions */
  630|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_EXTENSION, plugins_nacm), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  631|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_EXTENSION, plugins_yangdata), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  632|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_EXTENSION, plugins_schema_mount), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  633|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_EXTENSION, plugins_structure), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  634|      1|    LY_CHECK_GOTO(ret = plugins_insert(NULL, LYPLG_EXTENSION, plugins_openconfig), error);
  ------------------
  |  |  176|      1|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 1]
  |  |  ------------------
  ------------------
  635|       |
  636|       |    /* the global plugin sets contain only static plugins at this point, so assign to the counters here.
  637|       |     * the counters are used to determine whether a plugin is static or not */
  638|      1|    ly_static_type_plugins_count = ly_plugins_types.count;
  639|      1|    ly_static_ext_plugins_count = ly_plugins_extensions.count;
  640|       |
  641|      1|    (void)static_plugins_only;
  642|       |#ifndef STATIC
  643|       |    if (!static_plugins_only) {
  644|       |        /* external types */
  645|       |        LY_CHECK_GOTO(ret = plugins_insert_dir(LYPLG_TYPE), error);
  646|       |
  647|       |        /* external extensions */
  648|       |        LY_CHECK_GOTO(ret = plugins_insert_dir(LYPLG_EXTENSION), error);
  649|       |    }
  650|       |#endif
  651|       |
  652|       |    /* initiation done, wake-up possibly waiting threads creating another contexts */
  653|      1|    pthread_mutex_unlock(&plugins_guard);
  654|       |
  655|      1|    return LY_SUCCESS;
  656|       |
  657|      0|error:
  658|       |    /* initiation was not successful - cleanup (and let others to try) */
  659|       |#ifndef STATIC
  660|       |    lyplg_clean_();
  661|       |#endif
  662|      0|    pthread_mutex_unlock(&plugins_guard);
  663|       |
  664|      0|    if (ret == LY_EINVAL) {
  ------------------
  |  Branch (664:9): [True: 0, False: 0]
  ------------------
  665|       |        /* all the plugins here are internal, invalid record actually means an internal libyang error */
  666|      0|        ret = LY_EINT;
  667|      0|    }
  668|      0|    return ret;
  669|      1|}
plugins.c:plugins_insert:
  320|     33|{
  321|     33|    struct ly_set *plugins;
  322|     33|    const struct lyplg_ext_record *rec_ext;
  323|     33|    const struct lyplg_type_record *rec_type;
  324|     33|    uint32_t i;
  325|       |
  326|     33|    if (!recs) {
  ------------------
  |  Branch (326:9): [True: 0, False: 33]
  ------------------
  327|      0|        return LY_SUCCESS;
  328|      0|    }
  329|       |
  330|     33|    if (type == LYPLG_EXTENSION) {
  ------------------
  |  Branch (330:9): [True: 6, False: 27]
  ------------------
  331|      6|        rec_ext = (const struct lyplg_ext_record *)recs;
  332|      6|        plugins = ctx ? &ctx->plugins_extensions : &ly_plugins_extensions;
  ------------------
  |  Branch (332:19): [True: 0, False: 6]
  ------------------
  333|       |
  334|     17|        for (i = 0; rec_ext[i].name; i++) {
  ------------------
  |  Branch (334:21): [True: 11, False: 6]
  ------------------
  335|     11|            if (rec_ext[i].plugin.snode && !rec_ext[i].plugin.validate) {
  ------------------
  |  Branch (335:17): [True: 3, False: 8]
  |  Branch (335:44): [True: 0, False: 3]
  ------------------
  336|      0|                LOGERR(ctx, LY_EINT, "Ext plugin \"%s\" has no validate() callback defined.", rec_ext[i].name);
  ------------------
  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  ------------------
  337|      0|                return LY_EINT;
  338|      0|            }
  339|       |
  340|     11|            LY_CHECK_RET(ly_set_add(plugins, (void *)&rec_ext[i], 0, NULL));
  ------------------
  |  |  180|     11|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  ------------------
  |  |  |  |   58|     11|#define GETMACRO2(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  180|     11|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  178|     11|#define LY_CHECK_RET1(RETVAL) {LY_ERR ret__ = RETVAL;if (ret__ != LY_SUCCESS) {return ret__;}}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (178:58): [True: 0, False: 11]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  341|     11|        }
  342|     27|    } else { /* LYPLG_TYPE */
  343|     27|        rec_type = (const struct lyplg_type_record *)recs;
  344|     27|        plugins = ctx ? &ctx->plugins_types : &ly_plugins_types;
  ------------------
  |  Branch (344:19): [True: 0, False: 27]
  ------------------
  345|       |
  346|     71|        for (i = 0; rec_type[i].name; i++) {
  ------------------
  |  Branch (346:21): [True: 44, False: 27]
  ------------------
  347|     44|            LY_CHECK_RET(ly_set_add(plugins, (void *)&rec_type[i], 0, NULL));
  ------------------
  |  |  180|     44|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  ------------------
  |  |  |  |   58|     44|#define GETMACRO2(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  180|     44|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  178|     44|#define LY_CHECK_RET1(RETVAL) {LY_ERR ret__ = RETVAL;if (ret__ != LY_SUCCESS) {return ret__;}}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (178:58): [True: 0, False: 44]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  348|     44|        }
  349|     27|    }
  350|       |
  351|     33|    return LY_SUCCESS;
  352|     33|}

ly_set_new:
   26|      5|{
   27|      5|    LY_CHECK_ARG_RET(NULL, set_p, LY_EINVAL);
  ------------------
  |  |  200|      5|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  ------------------
  |  |  |  |   63|      5|#define GETMACRO7(_1, _2, _3, _4, _5, _6, _7, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  191|      5|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  ------------------
   28|       |
   29|      5|    *set_p = calloc(1, sizeof **set_p);
   30|      5|    LY_CHECK_ERR_RET(!(*set_p), LOGMEM(NULL), LY_EMEM);
  ------------------
  |  |  181|      5|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 5]
  |  |  ------------------
  ------------------
   31|       |
   32|      5|    return LY_SUCCESS;
   33|      5|}
ly_set_clean:
   37|     60|{
   38|     60|    uint32_t u;
   39|       |
   40|     60|    if (!set) {
  ------------------
  |  Branch (40:9): [True: 0, False: 60]
  ------------------
   41|      0|        return;
   42|      0|    }
   43|       |
   44|     60|    if (destructor) {
  ------------------
  |  Branch (44:9): [True: 10, False: 50]
  ------------------
   45|     10|        for (u = 0; u < set->count; ++u) {
  ------------------
  |  Branch (45:21): [True: 0, False: 10]
  ------------------
   46|      0|            destructor(set->objs[u]);
   47|      0|        }
   48|     10|    }
   49|     60|    set->count = 0;
   50|     60|}
ly_set_erase:
   54|     60|{
   55|     60|    if (!set) {
  ------------------
  |  Branch (55:9): [True: 0, False: 60]
  ------------------
   56|      0|        return;
   57|      0|    }
   58|       |
   59|     60|    ly_set_clean(set, destructor);
   60|       |
   61|     60|    free(set->objs);
   62|     60|    set->size = 0;
   63|       |    set->objs = NULL;
   64|     60|}
ly_set_free:
   68|      5|{
   69|      5|    if (!set) {
  ------------------
  |  Branch (69:9): [True: 0, False: 5]
  ------------------
   70|      0|        return;
   71|      0|    }
   72|       |
   73|      5|    ly_set_erase(set, destructor);
   74|       |
   75|      5|    free(set);
   76|      5|}
ly_set_add:
  130|     60|{
  131|     60|    void **new;
  132|       |
  133|     60|    LY_CHECK_ARG_RET(NULL, set, LY_EINVAL);
  ------------------
  |  |  200|     60|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  ------------------
  |  |  |  |   63|     60|#define GETMACRO7(_1, _2, _3, _4, _5, _6, _7, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  201|     60|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  191|     60|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 60]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  201|     60|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  ------------------
  134|       |
  135|     60|    if (!list) {
  ------------------
  |  Branch (135:9): [True: 60, False: 0]
  ------------------
  136|       |        /* search for duplication */
  137|  1.06k|        for (uint32_t i = 0; i < set->count; i++) {
  ------------------
  |  Branch (137:30): [True: 1.00k, False: 60]
  ------------------
  138|  1.00k|            if (set->objs[i] == object) {
  ------------------
  |  Branch (138:17): [True: 0, False: 1.00k]
  ------------------
  139|       |                /* already in set */
  140|      0|                if (index_p) {
  ------------------
  |  Branch (140:21): [True: 0, False: 0]
  ------------------
  141|      0|                    *index_p = i;
  142|      0|                }
  143|      0|                return LY_SUCCESS;
  144|      0|            }
  145|  1.00k|        }
  146|     60|    }
  147|       |
  148|     60|    if (set->size == set->count) {
  ------------------
  |  Branch (148:9): [True: 13, False: 47]
  ------------------
  149|     13|#define SET_SIZE_STEP 8
  150|     13|        new = realloc(set->objs, (set->size + SET_SIZE_STEP) * sizeof *(set->objs));
  ------------------
  |  |  149|     13|#define SET_SIZE_STEP 8
  ------------------
  151|     13|        LY_CHECK_ERR_RET(!new, LOGMEM(NULL), LY_EMEM);
  ------------------
  |  |  181|     13|#define LY_CHECK_ERR_RET(COND, ERR, RETVAL) if ((COND)) {ERR; return RETVAL;}
  |  |  ------------------
  |  |  |  Branch (181:49): [True: 0, False: 13]
  |  |  ------------------
  ------------------
  152|     13|        set->size += SET_SIZE_STEP;
  ------------------
  |  |  149|     13|#define SET_SIZE_STEP 8
  ------------------
  153|     13|        set->objs = new;
  154|     13|#undef SET_SIZE_STEP
  155|     13|    }
  156|       |
  157|     60|    if (index_p) {
  ------------------
  |  Branch (157:9): [True: 0, False: 60]
  ------------------
  158|      0|        *index_p = set->count;
  159|      0|    }
  160|     60|    set->objs[set->count++] = (void *)object;
  161|       |
  162|     60|    return LY_SUCCESS;
  163|     60|}

lys_unres_glob_erase:
 1349|     10|{
 1350|     10|    uint32_t i;
 1351|       |
 1352|     10|    for (i = 0; i < unres->dep_sets.count; ++i) {
  ------------------
  |  Branch (1352:17): [True: 0, False: 10]
  ------------------
 1353|      0|        ly_set_free(unres->dep_sets.objs[i], NULL);
 1354|      0|    }
 1355|     10|    ly_set_erase(&unres->dep_sets, NULL);
 1356|     10|    ly_set_erase(&unres->implementing, NULL);
 1357|     10|    ly_set_erase(&unres->compiling, NULL);
 1358|     10|    ly_set_erase(&unres->creating, NULL);
 1359|       |
 1360|     10|    assert(!unres->ds_unres.whens.count);
  ------------------
  |  Branch (1360:5): [True: 10, False: 0]
  ------------------
 1361|     10|    assert(!unres->ds_unres.musts.count);
  ------------------
  |  Branch (1361:5): [True: 10, False: 0]
  ------------------
 1362|     10|    assert(!unres->ds_unres.leafrefs.count);
  ------------------
  |  Branch (1362:5): [True: 10, False: 0]
  ------------------
 1363|     10|    assert(!unres->ds_unres.disabled_leafrefs.count);
  ------------------
  |  Branch (1363:5): [True: 10, False: 0]
  ------------------
 1364|     10|    assert(!unres->ds_unres.dflts.count);
  ------------------
  |  Branch (1364:5): [True: 10, False: 0]
  ------------------
 1365|     10|    assert(!unres->ds_unres.disabled.count);
  ------------------
  |  Branch (1365:5): [True: 10, False: 0]
  ------------------
 1366|     10|}
lys_search_localfile:
 3001|      5|{
 3002|      5|    LY_ERR ret = LY_EMEM;
 3003|      5|    size_t len, flen, match_len = 0, dir_len;
 3004|      5|    ly_bool implicit_cwd = 0, skip;
 3005|      5|    char *wd;
 3006|      5|    DIR *dir = NULL;
 3007|      5|    struct dirent *file;
 3008|      5|    char *match_name = NULL;
 3009|      5|    LYS_INFORMAT format_aux, match_format = 0;
 3010|      5|    struct ly_set *dirs;
 3011|       |
 3012|      5|    LY_CHECK_ARG_RET(NULL, localfile, LY_EINVAL);
  ------------------
  |  |  200|      5|#define LY_CHECK_ARG_RET(CTX, ...) GETMACRO7(__VA_ARGS__, LY_CHECK_ARG_RET6, LY_CHECK_ARG_RET5, LY_CHECK_ARG_RET4, \
  |  |  ------------------
  |  |  |  |   63|      5|#define GETMACRO7(_1, _2, _3, _4, _5, _6, _7, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  191|      5|#define LY_CHECK_ARG_RET1(CTX, ARG, RETVAL) if (!(ARG)) {LOGARG(CTX, ARG);return RETVAL;}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  165|      0|#define LOGARG(CTX, ARG) LOGERR(CTX, LY_EINVAL, "Invalid argument %s (%s()).", #ARG, __func__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (191:49): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  |  |  201|      5|    LY_CHECK_ARG_RET3, LY_CHECK_ARG_RET2, LY_CHECK_ARG_RET1, DUMMY) (CTX, __VA_ARGS__)
  ------------------
 3013|       |
 3014|       |    /* start to fill the dir fifo with the context's search path (if set)
 3015|       |     * and the current working directory */
 3016|      5|    LY_CHECK_RET(ly_set_new(&dirs));
  ------------------
  |  |  180|      5|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  ------------------
  |  |  |  |   58|      5|#define GETMACRO2(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  180|      5|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  178|      5|#define LY_CHECK_RET1(RETVAL) {LY_ERR ret__ = RETVAL;if (ret__ != LY_SUCCESS) {return ret__;}}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (178:58): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
 3017|       |
 3018|      5|    len = strlen(name);
 3019|      5|    if (cwd) {
  ------------------
  |  Branch (3019:9): [True: 5, False: 0]
  ------------------
 3020|      5|        wd = get_current_dir_name();
 3021|      5|        if (!wd) {
  ------------------
  |  Branch (3021:13): [True: 0, False: 5]
  ------------------
 3022|      0|            LOGMEM(NULL);
  ------------------
  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  ------------------
  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  ------------------
  ------------------
 3023|      0|            goto cleanup;
 3024|      5|        } else {
 3025|       |            /* add implicit current working directory (./) to be searched,
 3026|       |             * this directory is not searched recursively */
 3027|      5|            ret = ly_set_add(dirs, wd, 0, NULL);
 3028|      5|            LY_CHECK_GOTO(ret, cleanup);
  ------------------
  |  |  176|      5|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 5]
  |  |  ------------------
  ------------------
 3029|      5|            implicit_cwd = 1;
 3030|      5|        }
 3031|      5|    }
 3032|      5|    if (searchpaths) {
  ------------------
  |  Branch (3032:9): [True: 5, False: 0]
  ------------------
 3033|      5|        for (uint64_t i = 0; searchpaths[i]; i++) {
  ------------------
  |  Branch (3033:30): [True: 0, False: 5]
  ------------------
 3034|       |            /* check for duplicities with the implicit current working directory */
 3035|      0|            if (implicit_cwd && !strcmp(dirs->objs[0], searchpaths[i])) {
  ------------------
  |  Branch (3035:17): [True: 0, False: 0]
  |  Branch (3035:33): [True: 0, False: 0]
  ------------------
 3036|      0|                implicit_cwd = 0;
 3037|      0|                continue;
 3038|      0|            }
 3039|      0|            wd = strdup(searchpaths[i]);
 3040|      0|            if (!wd) {
  ------------------
  |  Branch (3040:17): [True: 0, False: 0]
  ------------------
 3041|      0|                LOGMEM(NULL);
  ------------------
  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  ------------------
  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  ------------------
  ------------------
 3042|      0|                goto cleanup;
 3043|      0|            } else {
 3044|      0|                ret = ly_set_add(dirs, wd, 0, NULL);
 3045|      0|                LY_CHECK_GOTO(ret, cleanup);
  ------------------
  |  |  176|      0|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 0]
  |  |  ------------------
  ------------------
 3046|      0|            }
 3047|      0|        }
 3048|      5|    }
 3049|      5|    wd = NULL;
 3050|       |
 3051|       |    /* start searching */
 3052|     10|    while (dirs->count) {
  ------------------
  |  Branch (3052:12): [True: 5, False: 5]
  ------------------
 3053|      5|        free(wd);
 3054|       |
 3055|      5|        dirs->count--;
 3056|      5|        wd = (char *)dirs->objs[dirs->count];
 3057|      5|        dirs->objs[dirs->count] = NULL;
 3058|      5|        LOGVRB("Searching for \"%s\" in \"%s\".", name, wd);
  ------------------
  |  |  144|      5|#define LOGVRB(...) ly_log(NULL, LY_LLVRB, 0, __VA_ARGS__)
  ------------------
 3059|       |
 3060|      5|        if (dir) {
  ------------------
  |  Branch (3060:13): [True: 0, False: 5]
  ------------------
 3061|      0|            closedir(dir);
 3062|      0|        }
 3063|      5|        dir = opendir(wd);
 3064|      5|        dir_len = strlen(wd);
 3065|      5|        if (!dir) {
  ------------------
  |  Branch (3065:13): [True: 0, False: 5]
  ------------------
 3066|      0|            LOGWRN(NULL, "Unable to open directory \"%s\" for searching (sub)modules (%s).", wd, strerror(errno));
  ------------------
  |  |  143|      0|#define LOGWRN(ctx, ...) ly_log(ctx, LY_LLWRN, 0, __VA_ARGS__)
  ------------------
 3067|      0|            continue;
 3068|      0|        }
 3069|       |
 3070|       |        /* search the directory */
 3071|    125|        while ((file = readdir(dir))) {
  ------------------
  |  Branch (3071:16): [True: 120, False: 5]
  ------------------
 3072|    120|            if (!strcmp(".", file->d_name) || !strcmp("..", file->d_name)) {
  ------------------
  |  Branch (3072:17): [True: 5, False: 115]
  |  Branch (3072:47): [True: 5, False: 110]
  ------------------
 3073|       |                /* skip . and .. */
 3074|     10|                continue;
 3075|     10|            }
 3076|       |
 3077|       |            /* check whether file type is */
 3078|    110|            if ((ret = lys_search_localfile_file_type(file, wd, dirs, implicit_cwd, &skip))) {
  ------------------
  |  Branch (3078:17): [True: 0, False: 110]
  ------------------
 3079|      0|                goto cleanup;
 3080|      0|            }
 3081|       |
 3082|       |            /* here we know that the item is a file which can contain a module */
 3083|    110|            if (strncmp(name, file->d_name, len) || ((file->d_name[len] != '.') && (file->d_name[len] != '@'))) {
  ------------------
  |  Branch (3083:17): [True: 110, False: 0]
  |  Branch (3083:54): [True: 0, False: 0]
  |  Branch (3083:84): [True: 0, False: 0]
  ------------------
 3084|       |                /* different filename than the module we search for */
 3085|    110|                continue;
 3086|    110|            }
 3087|       |
 3088|       |            /* get type according to filename suffix */
 3089|      0|            flen = strlen(file->d_name);
 3090|      0|            if ((flen >= LY_YANG_SUFFIX_LEN + 1) && !strcmp(&file->d_name[flen - LY_YANG_SUFFIX_LEN], LY_YANG_SUFFIX)) {
  ------------------
  |  |   29|      0|#define LY_YANG_SUFFIX_LEN 5
  ------------------
                          if ((flen >= LY_YANG_SUFFIX_LEN + 1) && !strcmp(&file->d_name[flen - LY_YANG_SUFFIX_LEN], LY_YANG_SUFFIX)) {
  ------------------
  |  |   29|      0|#define LY_YANG_SUFFIX_LEN 5
  ------------------
                          if ((flen >= LY_YANG_SUFFIX_LEN + 1) && !strcmp(&file->d_name[flen - LY_YANG_SUFFIX_LEN], LY_YANG_SUFFIX)) {
  ------------------
  |  |   28|      0|#define LY_YANG_SUFFIX ".yang"
  ------------------
  |  Branch (3090:17): [True: 0, False: 0]
  |  Branch (3090:53): [True: 0, False: 0]
  ------------------
 3091|      0|                format_aux = LYS_IN_YANG;
 3092|      0|            } else if ((flen >= LY_YIN_SUFFIX_LEN + 1) && !strcmp(&file->d_name[flen - LY_YIN_SUFFIX_LEN], LY_YIN_SUFFIX)) {
  ------------------
  |  |   31|      0|#define LY_YIN_SUFFIX_LEN 4
  ------------------
                          } else if ((flen >= LY_YIN_SUFFIX_LEN + 1) && !strcmp(&file->d_name[flen - LY_YIN_SUFFIX_LEN], LY_YIN_SUFFIX)) {
  ------------------
  |  |   31|      0|#define LY_YIN_SUFFIX_LEN 4
  ------------------
                          } else if ((flen >= LY_YIN_SUFFIX_LEN + 1) && !strcmp(&file->d_name[flen - LY_YIN_SUFFIX_LEN], LY_YIN_SUFFIX)) {
  ------------------
  |  |   30|      0|#define LY_YIN_SUFFIX ".yin"
  ------------------
  |  Branch (3092:24): [True: 0, False: 0]
  |  Branch (3092:59): [True: 0, False: 0]
  ------------------
 3093|      0|                format_aux = LYS_IN_YIN;
 3094|      0|            } else {
 3095|       |                /* not supported suffix/file format */
 3096|      0|                continue;
 3097|      0|            }
 3098|       |
 3099|      0|            if (revision) {
  ------------------
  |  Branch (3099:17): [True: 0, False: 0]
  ------------------
 3100|       |                /* we look for the specific revision, try to get it from the filename */
 3101|      0|                if (file->d_name[len] == '@') {
  ------------------
  |  Branch (3101:21): [True: 0, False: 0]
  ------------------
 3102|       |                    /* check revision from the filename */
 3103|      0|                    if (strncmp(revision, &file->d_name[len + 1], strlen(revision))) {
  ------------------
  |  Branch (3103:25): [True: 0, False: 0]
  ------------------
 3104|       |                        /* another revision */
 3105|      0|                        continue;
 3106|      0|                    } else {
 3107|       |                        /* exact revision */
 3108|      0|                        free(match_name);
 3109|      0|                        if (asprintf(&match_name, "%s/%s", wd, file->d_name) == -1) {
  ------------------
  |  Branch (3109:29): [True: 0, False: 0]
  ------------------
 3110|      0|                            LOGMEM(NULL);
  ------------------
  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  ------------------
  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  ------------------
  ------------------
 3111|      0|                            goto cleanup;
 3112|      0|                        }
 3113|      0|                        match_len = dir_len + 1 + len;
 3114|      0|                        match_format = format_aux;
 3115|      0|                        goto success;
 3116|      0|                    }
 3117|      0|                } else {
 3118|       |                    /* continue trying to find exact revision match, use this only if not found */
 3119|      0|                    free(match_name);
 3120|      0|                    if (asprintf(&match_name, "%s/%s", wd, file->d_name) == -1) {
  ------------------
  |  Branch (3120:25): [True: 0, False: 0]
  ------------------
 3121|      0|                        LOGMEM(NULL);
  ------------------
  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  ------------------
  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  ------------------
  ------------------
 3122|      0|                        goto cleanup;
 3123|      0|                    }
 3124|      0|                    match_len = dir_len + 1 + len;
 3125|      0|                    match_format = format_aux;
 3126|      0|                    continue;
 3127|      0|                }
 3128|      0|            } else {
 3129|       |                /* remember the revision and try to find the newest one */
 3130|      0|                if (match_name) {
  ------------------
  |  Branch (3130:21): [True: 0, False: 0]
  ------------------
 3131|      0|                    if ((file->d_name[len] != '@') ||
  ------------------
  |  Branch (3131:25): [True: 0, False: 0]
  ------------------
 3132|      0|                            lys_check_date(NULL, &file->d_name[len + 1],
  ------------------
  |  Branch (3132:29): [True: 0, False: 0]
  ------------------
 3133|      0|                            flen - ((format_aux == LYS_IN_YANG) ? LY_YANG_SUFFIX_LEN : LY_YIN_SUFFIX_LEN) - len - 1, "revision")) {
  ------------------
  |  |   29|      0|#define LY_YANG_SUFFIX_LEN 5
  ------------------
                                          flen - ((format_aux == LYS_IN_YANG) ? LY_YANG_SUFFIX_LEN : LY_YIN_SUFFIX_LEN) - len - 1, "revision")) {
  ------------------
  |  |   31|      0|#define LY_YIN_SUFFIX_LEN 4
  ------------------
  |  Branch (3133:37): [True: 0, False: 0]
  ------------------
 3134|      0|                        continue;
 3135|      0|                    } else if ((match_name[match_len] == '@') &&
  ------------------
  |  Branch (3135:32): [True: 0, False: 0]
  ------------------
 3136|      0|                            (strncmp(&match_name[match_len + 1], &file->d_name[len + 1], LY_REV_SIZE - 1) >= 0)) {
  ------------------
  |  |  228|      0|#define LY_REV_SIZE 11   /**< revision data string length (including terminating NULL byte) */
  ------------------
  |  Branch (3136:29): [True: 0, False: 0]
  ------------------
 3137|      0|                        continue;
 3138|      0|                    }
 3139|      0|                    free(match_name);
 3140|      0|                }
 3141|       |
 3142|      0|                if (asprintf(&match_name, "%s/%s", wd, file->d_name) == -1) {
  ------------------
  |  Branch (3142:21): [True: 0, False: 0]
  ------------------
 3143|      0|                    LOGMEM(NULL);
  ------------------
  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  ------------------
  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  ------------------
  ------------------
 3144|      0|                    goto cleanup;
 3145|      0|                }
 3146|      0|                match_len = dir_len + 1 + len;
 3147|      0|                match_format = format_aux;
 3148|      0|                continue;
 3149|      0|            }
 3150|      0|        }
 3151|      5|    }
 3152|       |
 3153|      5|success:
 3154|      5|    (*localfile) = match_name;
 3155|      5|    match_name = NULL;
 3156|      5|    if (format) {
  ------------------
  |  Branch (3156:9): [True: 5, False: 0]
  ------------------
 3157|      5|        (*format) = match_format;
 3158|      5|    }
 3159|      5|    ret = LY_SUCCESS;
 3160|       |
 3161|      5|cleanup:
 3162|      5|    free(wd);
 3163|      5|    if (dir) {
  ------------------
  |  Branch (3163:9): [True: 5, False: 0]
  ------------------
 3164|      5|        closedir(dir);
 3165|      5|    }
 3166|      5|    free(match_name);
 3167|      5|    ly_set_free(dirs, free);
 3168|       |
 3169|      5|    return ret;
 3170|      5|}
tree_schema.c:lys_search_localfile_file_type:
 2931|    110|{
 2932|    110|    LY_ERR rc = LY_SUCCESS;
 2933|    110|    char *str = NULL;
 2934|    110|    ly_bool is_dir = 0, is_reg = 0, need_stat = 1;
 2935|    110|    struct stat st;
 2936|       |
 2937|    110|    *skip = 0;
 2938|       |
 2939|    110|#ifdef HAVE_DIRENT_D_TYPE
 2940|    110|    if (file->d_type == DT_DIR) {
  ------------------
  |  Branch (2940:9): [True: 55, False: 55]
  ------------------
 2941|       |        /* dirent - dir */
 2942|     55|        is_dir = 1;
 2943|     55|        need_stat = 0;
 2944|     55|    } else if (file->d_type == DT_REG) {
  ------------------
  |  Branch (2944:16): [True: 55, False: 0]
  ------------------
 2945|       |        /* dirent - file */
 2946|     55|        is_reg = 1;
 2947|     55|        need_stat = 0;
 2948|     55|    } else if ((file->d_type != DT_UNKNOWN) && (file->d_type != DT_LNK)) {
  ------------------
  |  Branch (2948:16): [True: 0, False: 0]
  |  Branch (2948:48): [True: 0, False: 0]
  ------------------
 2949|       |        /* it is a known type, but not dir or regular file, so trust d_type and just skip it */
 2950|      0|        need_stat = 0;
 2951|      0|    }
 2952|    110|#endif // HAVE_DIRENT_D_TYPE
 2953|       |
 2954|    110|    if (need_stat) {
  ------------------
  |  Branch (2954:9): [True: 0, False: 110]
  ------------------
 2955|       |        /* need to use stat to determine the file type */
 2956|      0|        if (asprintf(&str, "%s/%s", wd, file->d_name) == -1) {
  ------------------
  |  Branch (2956:13): [True: 0, False: 0]
  ------------------
 2957|      0|            LOGMEM(NULL);
  ------------------
  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  ------------------
  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  ------------------
  ------------------
 2958|      0|            rc = LY_EMEM;
 2959|      0|            goto cleanup;
 2960|      0|        }
 2961|      0|        if (stat(str, &st)) {
  ------------------
  |  Branch (2961:13): [True: 0, False: 0]
  ------------------
 2962|      0|            LOGWRN(NULL, "Unable to get information about \"%s\" file in \"%s\" when searching for (sub)modules (%s)",
  ------------------
  |  |  143|      0|#define LOGWRN(ctx, ...) ly_log(ctx, LY_LLWRN, 0, __VA_ARGS__)
  ------------------
 2963|      0|                    file->d_name, wd, strerror(errno));
 2964|      0|        } else if (S_ISDIR(st.st_mode)) {
  ------------------
  |  Branch (2964:20): [True: 0, False: 0]
  ------------------
 2965|       |            /* stat - dir */
 2966|      0|            is_dir = 1;
 2967|      0|        } else if (S_ISREG(st.st_mode)) {
  ------------------
  |  Branch (2967:20): [True: 0, False: 0]
  ------------------
 2968|       |            /* stat - file */
 2969|      0|            is_reg = 1;
 2970|      0|        }
 2971|      0|    }
 2972|       |
 2973|    110|    if (is_dir && (dirs->count || !implicit_cwd)) {
  ------------------
  |  Branch (2973:9): [True: 55, False: 55]
  |  Branch (2973:20): [True: 0, False: 55]
  |  Branch (2973:35): [True: 0, False: 55]
  ------------------
 2974|       |        /* we have another subdirectory in searchpath to explore,
 2975|       |         * subdirectories are not taken into account in current working dir (dirs->set.g[0]) */
 2976|      0|        if (!str && (asprintf(&str, "%s/%s", wd, file->d_name) == -1)) {
  ------------------
  |  Branch (2976:13): [True: 0, False: 0]
  |  Branch (2976:21): [True: 0, False: 0]
  ------------------
 2977|      0|            LOGMEM(NULL);
  ------------------
  |  |  162|      0|#define LOGMEM(CTX) LOGERR(CTX, LY_EMEM, "Memory allocation failed (%s()).", __func__)
  |  |  ------------------
  |  |  |  |  142|      0|#define LOGERR(ctx, errno, ...) ly_log(ctx, LY_LLERR, errno, __VA_ARGS__)
  |  |  ------------------
  ------------------
 2978|      0|            rc = LY_EMEM;
 2979|      0|            goto cleanup;
 2980|      0|        }
 2981|      0|        if ((rc = ly_set_add(dirs, str, 0, NULL))) {
  ------------------
  |  Branch (2981:13): [True: 0, False: 0]
  ------------------
 2982|      0|            goto cleanup;
 2983|      0|        }
 2984|      0|        str = NULL;
 2985|       |
 2986|       |        /* continue with the next item in current directory */
 2987|      0|        *skip = 1;
 2988|    110|    } else if (!is_reg) {
  ------------------
  |  Branch (2988:16): [True: 55, False: 55]
  ------------------
 2989|       |        /* not a regular file (note that we see the target of symlinks instead of symlinks */
 2990|     55|        *skip = 1;
 2991|     55|    }
 2992|       |
 2993|    110|cleanup:
 2994|    110|    free(str);
 2995|    110|    return rc;
 2996|    110|}

lys_parse_load:
  940|      5|{
  941|      5|    struct lys_module *mod_latest = NULL;
  942|       |
  943|      5|    assert(mod && new_mods);
  ------------------
  |  Branch (943:5): [True: 5, False: 0]
  |  Branch (943:5): [True: 5, False: 0]
  ------------------
  944|       |
  945|       |    /*
  946|       |     * Try to get the module from the context.
  947|       |     */
  948|      5|    if (revision) {
  ------------------
  |  Branch (948:9): [True: 5, False: 0]
  ------------------
  949|       |        /* Get the specific revision. */
  950|      5|        *mod = ly_ctx_get_module(ctx, name, revision);
  951|      5|    } else {
  952|       |        /* Get the requested module in a suitable revision in the context. */
  953|      0|        *mod = lys_get_module_without_revision(ctx, name);
  954|      0|        if (*mod && !(*mod)->implemented && !((*mod)->latest_revision & LYS_MOD_IMPORTED_REV)) {
  ------------------
  |  | 2290|      0|#define LYS_MOD_IMPORTED_REV        0x04 /**< This is the module revision used when importing the module without
  ------------------
  |  Branch (954:13): [True: 0, False: 0]
  |  Branch (954:21): [True: 0, False: 0]
  |  Branch (954:45): [True: 0, False: 0]
  ------------------
  955|       |            /* Let us now search with callback and searchpaths to check
  956|       |             * if there is newer revision outside the context.
  957|       |             */
  958|      0|            mod_latest = *mod;
  959|      0|            *mod = NULL;
  960|      0|        }
  961|      0|    }
  962|       |
  963|      5|    if (!*mod) {
  ------------------
  |  Branch (963:9): [True: 5, False: 0]
  ------------------
  964|       |        /* No suitable module in the context, try to load it. */
  965|      5|        LY_CHECK_RET(lys_load_mod_from_clb_or_file(ctx, name, revision, mod_latest, new_mods, mod));
  ------------------
  |  |  180|      5|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  ------------------
  |  |  |  |   58|      5|#define GETMACRO2(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  180|      5|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  178|      5|#define LY_CHECK_RET1(RETVAL) {LY_ERR ret__ = RETVAL;if (ret__ != LY_SUCCESS) {return ret__;}}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (178:58): [True: 5, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  966|       |
  967|       |        /* Update the latest_revision flag - here we have selected the latest available schema,
  968|       |         * consider that even the callback provides correct latest revision.
  969|       |         */
  970|      0|        if (!*mod) {
  ------------------
  |  Branch (970:13): [True: 0, False: 0]
  ------------------
  971|      0|            LOGVRB("Newer revision than \"%s@%s\" not found, using this as the latest revision.",
  ------------------
  |  |  144|      0|#define LOGVRB(...) ly_log(NULL, LY_LLVRB, 0, __VA_ARGS__)
  ------------------
  972|      0|                    mod_latest->name, mod_latest->revision);
  973|      0|            assert(mod_latest->latest_revision & LYS_MOD_LATEST_REV);
  ------------------
  |  Branch (973:13): [True: 0, False: 0]
  ------------------
  974|      0|            mod_latest->latest_revision |= LYS_MOD_LATEST_SEARCHDIRS;
  ------------------
  |  | 2289|      0|#define LYS_MOD_LATEST_SEARCHDIRS   0x02 /**< This is the latest revision of the module found in searchdirs. */
  ------------------
  975|      0|            *mod = mod_latest;
  976|      0|        } else if (*mod && !revision && ((*mod)->latest_revision & LYS_MOD_LATEST_REV)) {
  ------------------
  |  | 2288|      0|#define LYS_MOD_LATEST_REV          0x01 /**< This is the latest revision of the module in the current context. */
  ------------------
  |  Branch (976:20): [True: 0, False: 0]
  |  Branch (976:28): [True: 0, False: 0]
  |  Branch (976:41): [True: 0, False: 0]
  ------------------
  977|      0|            (*mod)->latest_revision |= LYS_MOD_LATEST_SEARCHDIRS;
  ------------------
  |  | 2289|      0|#define LYS_MOD_LATEST_SEARCHDIRS   0x02 /**< This is the latest revision of the module found in searchdirs. */
  ------------------
  978|      0|        }
  979|      0|    }
  980|       |
  981|       |    /* Checking the circular dependence of imported modules. */
  982|      0|    LY_CHECK_RET(lys_check_circular_dependency(ctx, mod));
  ------------------
  |  |  180|      0|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  ------------------
  |  |  |  |   58|      0|#define GETMACRO2(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  180|      0|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  178|      0|#define LY_CHECK_RET1(RETVAL) {LY_ERR ret__ = RETVAL;if (ret__ != LY_SUCCESS) {return ret__;}}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (178:58): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  983|       |
  984|      0|    return LY_SUCCESS;
  985|      0|}
tree_schema_common.c:lys_load_mod_from_clb_or_file:
  802|      5|{
  803|      5|    LY_ERR r;
  804|      5|    const char *module_data = NULL;
  805|      5|    LYS_INFORMAT format = LYS_IN_UNKNOWN;
  806|      5|    ly_bool clb_used, searchdirs_used, found = 0;
  807|       |
  808|      5|    void (*module_data_free)(void *module_data, void *user_data) = NULL;
  809|      5|    struct lysp_load_module_data mod_data = {0};
  810|      5|    struct ly_in *in;
  811|       |
  812|      5|    *mod = NULL;
  813|       |
  814|      5|    if (!ctx->imp_clb) {
  ------------------
  |  Branch (814:9): [True: 5, False: 0]
  ------------------
  815|       |        /* no callback to call */
  816|      5|        clb_used = 1;
  817|      5|    } else if (mod_latest && (mod_latest->latest_revision & LYS_MOD_LATEST_IMPCLB)) {
  ------------------
  |  | 2293|      0|#define LYS_MOD_LATEST_IMPCLB       0x08 /**< This is the latest revision of the module obtained from import callback. */
  ------------------
  |  Branch (817:16): [True: 0, False: 0]
  |  Branch (817:30): [True: 0, False: 0]
  ------------------
  818|       |        /* already have the latest revision returned by the callback */
  819|      0|        clb_used = 1;
  820|      0|    } else {
  821|      0|        clb_used = 0;
  822|      0|    }
  823|       |
  824|      5|    if (ctx->opts & LY_CTX_DISABLE_SEARCHDIRS) {
  ------------------
  |  |  194|      5|#define LY_CTX_DISABLE_SEARCHDIRS 0x08  /**< Do not search for schemas in context's searchdirs neither in current
  ------------------
  |  Branch (824:9): [True: 0, False: 5]
  ------------------
  825|       |        /* searchdirs disabled */
  826|      0|        searchdirs_used = 1;
  827|      5|    } else if (mod_latest && (mod_latest->latest_revision & LYS_MOD_LATEST_SEARCHDIRS)) {
  ------------------
  |  | 2289|      0|#define LYS_MOD_LATEST_SEARCHDIRS   0x02 /**< This is the latest revision of the module found in searchdirs. */
  ------------------
  |  Branch (827:16): [True: 0, False: 5]
  |  Branch (827:30): [True: 0, False: 0]
  ------------------
  828|       |        /* already have the latest revision found in the searchdirs */
  829|      0|        searchdirs_used = 1;
  830|      5|    } else {
  831|      5|        searchdirs_used = 0;
  832|      5|    }
  833|       |
  834|     10|    while (!found && (!clb_used || !searchdirs_used)) {
  ------------------
  |  Branch (834:12): [True: 10, False: 0]
  |  Branch (834:23): [True: 0, False: 10]
  |  Branch (834:36): [True: 5, False: 5]
  ------------------
  835|      5|        if ((!(ctx->opts & LY_CTX_PREFER_SEARCHDIRS) || searchdirs_used) && !clb_used) {
  ------------------
  |  |  201|      5|#define LY_CTX_PREFER_SEARCHDIRS 0x20 /**< When searching for schema, prefer searchdirs instead of user callback. */
  ------------------
  |  Branch (835:14): [True: 5, False: 0]
  |  Branch (835:57): [True: 0, False: 0]
  |  Branch (835:77): [True: 0, False: 5]
  ------------------
  836|      0|            if (!ctx->imp_clb(name, revision, NULL, NULL, ctx->imp_clb_data, &format, &module_data, &module_data_free)) {
  ------------------
  |  Branch (836:17): [True: 0, False: 0]
  ------------------
  837|       |                /* parse the module returned by the callback */
  838|      0|                LY_CHECK_RET(ly_in_new_memory(module_data, &in));
  ------------------
  |  |  180|      0|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  ------------------
  |  |  |  |   58|      0|#define GETMACRO2(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  180|      0|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  178|      0|#define LY_CHECK_RET1(RETVAL) {LY_ERR ret__ = RETVAL;if (ret__ != LY_SUCCESS) {return ret__;}}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (178:58): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  839|      0|                mod_data.name = name;
  840|      0|                mod_data.revision = revision;
  841|      0|                r = lys_parse_in(ctx, in, format, &mod_data, new_mods, mod);
  842|      0|                ly_in_free(in, 0);
  843|      0|                if (module_data_free) {
  ------------------
  |  Branch (843:21): [True: 0, False: 0]
  ------------------
  844|      0|                    module_data_free((void *)module_data, ctx->imp_clb_data);
  845|      0|                }
  846|      0|                LY_CHECK_RET(r);
  ------------------
  |  |  180|      0|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  ------------------
  |  |  |  |   58|      0|#define GETMACRO2(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  180|      0|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  178|      0|#define LY_CHECK_RET1(RETVAL) {LY_ERR ret__ = RETVAL;if (ret__ != LY_SUCCESS) {return ret__;}}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (178:58): [True: 0, False: 0]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  847|       |
  848|      0|                found = 1;
  849|      0|            }
  850|      0|            clb_used = 1;
  851|       |
  852|      0|            if (*mod && !revision) {
  ------------------
  |  Branch (852:17): [True: 0, False: 0]
  |  Branch (852:25): [True: 0, False: 0]
  ------------------
  853|       |                /* we got the latest revision module from the callback */
  854|      0|                (*mod)->latest_revision |= LYS_MOD_LATEST_IMPCLB;
  ------------------
  |  | 2293|      0|#define LYS_MOD_LATEST_IMPCLB       0x08 /**< This is the latest revision of the module obtained from import callback. */
  ------------------
  855|      0|            }
  856|      5|        } else if (!searchdirs_used) {
  ------------------
  |  Branch (856:20): [True: 5, False: 0]
  ------------------
  857|      5|            LY_CHECK_RET(lys_parse_localfile(ctx, name, revision, NULL, NULL, new_mods, &found, (void **)mod));
  ------------------
  |  |  180|      5|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  ------------------
  |  |  |  |   58|      5|#define GETMACRO2(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  180|      5|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  178|      5|#define LY_CHECK_RET1(RETVAL) {LY_ERR ret__ = RETVAL;if (ret__ != LY_SUCCESS) {return ret__;}}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (178:58): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  858|      5|            searchdirs_used = 1;
  859|       |
  860|      5|            if (*mod && !revision) {
  ------------------
  |  Branch (860:17): [True: 0, False: 5]
  |  Branch (860:25): [True: 0, False: 0]
  ------------------
  861|       |                /* we got the latest revision module in the searchdirs */
  862|      0|                (*mod)->latest_revision |= LYS_MOD_LATEST_SEARCHDIRS;
  ------------------
  |  | 2289|      0|#define LYS_MOD_LATEST_SEARCHDIRS   0x02 /**< This is the latest revision of the module found in searchdirs. */
  ------------------
  863|      0|            }
  864|      5|        }
  865|      5|    }
  866|       |
  867|      5|    if (!*mod && !mod_latest) {
  ------------------
  |  Branch (867:9): [True: 5, False: 0]
  |  Branch (867:18): [True: 5, False: 0]
  ------------------
  868|      5|        LOGVAL(ctx, NULL, LYVE_REFERENCE, "Loading \"%s@%s\" module failed, not found.", name, revision ? revision : "<any>");
  ------------------
  |  |  166|     10|#define LOGVAL(CTX, LNODE, ...) ly_vlog(CTX, NULL, LNODE, __VA_ARGS__)
  |  |  ------------------
  |  |  |  Branch (166:59): [True: 5, False: 0]
  |  |  ------------------
  ------------------
  869|      5|        return LY_ENOTFOUND;
  870|      5|    }
  871|       |
  872|      0|    return LY_SUCCESS;
  873|      5|}
tree_schema_common.c:lys_parse_localfile:
  743|      5|{
  744|      5|    struct ly_in *in;
  745|      5|    char *filepath = NULL;
  746|      5|    LYS_INFORMAT format = 0;
  747|      5|    void *mod = NULL;
  748|      5|    LY_ERR ret = LY_SUCCESS;
  749|      5|    struct lysp_load_module_data mod_data = {0};
  750|       |
  751|      5|    *found = 0;
  752|      5|    *result = NULL;
  753|       |
  754|      5|    LY_CHECK_RET(lys_search_localfile(ly_ctx_get_searchdirs(ctx), !(ctx->opts & LY_CTX_DISABLE_SEARCHDIR_CWD), name,
  ------------------
  |  |  180|      5|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  ------------------
  |  |  |  |   58|      5|#define GETMACRO2(_1, _2, NAME, ...) NAME
  |  |  |  |  ------------------
  |  |  |  |  |  |  180|      5|#define LY_CHECK_RET(...) GETMACRO2(__VA_ARGS__, LY_CHECK_RET2, LY_CHECK_RET1, DUMMY)(__VA_ARGS__)
  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  178|      5|#define LY_CHECK_RET1(RETVAL) {LY_ERR ret__ = RETVAL;if (ret__ != LY_SUCCESS) {return ret__;}}
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  |  |  |  Branch (178:58): [True: 0, False: 5]
  |  |  |  |  |  |  |  |  ------------------
  |  |  |  |  |  |  ------------------
  |  |  |  |  ------------------
  |  |  ------------------
  ------------------
  755|      5|            revision, &filepath, &format));
  756|      5|    if (!filepath) {
  ------------------
  |  Branch (756:9): [True: 5, False: 0]
  ------------------
  757|      5|        LOGVRB("Module \"%s%s%s\" not found in local searchdirs.", name, revision ? "@" : "", revision ? revision : "");
  ------------------
  |  |  144|     20|#define LOGVRB(...) ly_log(NULL, LY_LLVRB, 0, __VA_ARGS__)
  |  |  ------------------
  |  |  |  Branch (144:47): [True: 5, False: 0]
  |  |  |  Branch (144:47): [True: 5, False: 0]
  |  |  ------------------
  ------------------
  758|      5|        goto cleanup;
  759|      5|    }
  760|       |
  761|      0|    LOGVRB("Loading schema from \"%s\" file.", filepath);
  ------------------
  |  |  144|      0|#define LOGVRB(...) ly_log(NULL, LY_LLVRB, 0, __VA_ARGS__)
  ------------------
  762|       |
  763|       |    /* get the (sub)module */
  764|      0|    LY_CHECK_ERR_GOTO(ret = ly_in_new_filepath(filepath, 0, &in),
  ------------------
  |  |  177|      0|#define LY_CHECK_ERR_GOTO(COND, ERR, GOTO) if ((COND)) {ERR; goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (177:48): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  765|      0|            LOGERR(ctx, ret, "Unable to create input handler for filepath %s.", filepath), cleanup);
  766|      0|    mod_data.name = name;
  767|      0|    mod_data.revision = revision;
  768|      0|    mod_data.path = filepath;
  769|      0|    mod_data.submoduleof = main_name;
  770|      0|    if (main_ctx) {
  ------------------
  |  Branch (770:9): [True: 0, False: 0]
  ------------------
  771|      0|        ret = lys_parse_submodule(ctx, in, format, main_ctx, &mod_data, 1, new_mods, (struct lysp_submodule **)&mod);
  772|      0|    } else {
  773|      0|        ret = lys_parse_in(ctx, in, format, &mod_data, new_mods, (struct lys_module **)&mod);
  774|       |
  775|      0|    }
  776|      0|    ly_in_free(in, 1);
  777|      0|    LY_CHECK_GOTO(ret, cleanup);
  ------------------
  |  |  176|      0|#define LY_CHECK_GOTO(COND, GOTO) if ((COND)) {goto GOTO;}
  |  |  ------------------
  |  |  |  Branch (176:39): [True: 0, False: 0]
  |  |  ------------------
  ------------------
  778|       |
  779|      0|    *found = 1;
  780|      0|    *result = mod;
  781|       |
  782|      5|cleanup:
  783|      5|    free(filepath);
  784|      5|    return ret;
  785|      0|}

LLVMFuzzerTestOneInput:
   11|      5|{
   12|      5|    struct ly_ctx *ctx = NULL;
   13|      5|    struct lyd_node *tree = NULL;
   14|      5|    FILE *input = NULL;
   15|      5|    static bool log = false;
   16|      5|    const char *schema =
   17|      5|            "module fuzz-lyb {namespace urn:tests:fuzz-lyb;prefix fl;"
   18|      5|            "container c {leaf s {type string;} leaf u16 {type uint16;}"
   19|      5|            "leaf-list bits {type bits {bit zero; bit one;}}}}";
   20|       |
   21|      5|    if (!log) {
  ------------------
  |  Branch (21:9): [True: 1, False: 4]
  ------------------
   22|      1|        ly_log_options(0);
   23|      1|        log = true;
   24|      1|    }
   25|       |
   26|      5|    if (ly_ctx_new(LY_SRC_DIR "/modules", 0, &ctx) != LY_SUCCESS) {
  ------------------
  |  |   44|      5|#define LY_SRC_DIR "/src/libyang"
  ------------------
  |  Branch (26:9): [True: 5, False: 0]
  ------------------
   27|      5|        return 0;
   28|      5|    }
   29|       |
   30|      0|    if (lys_parse_mem(ctx, schema, LYS_IN_YANG, NULL) != LY_SUCCESS) {
  ------------------
  |  Branch (30:9): [True: 0, False: 0]
  ------------------
   31|      0|        goto cleanup;
   32|      0|    }
   33|       |
   34|      0|    input = tmpfile();
   35|      0|    if (!input) {
  ------------------
  |  Branch (35:9): [True: 0, False: 0]
  ------------------
   36|      0|        goto cleanup;
   37|      0|    }
   38|       |
   39|      0|    if (len && (fwrite(buf, 1, len, input) != len)) {
  ------------------
  |  Branch (39:9): [True: 0, False: 0]
  |  Branch (39:16): [True: 0, False: 0]
  ------------------
   40|      0|        goto cleanup;
   41|      0|    }
   42|      0|    fflush(input);
   43|      0|    if (lseek(fileno(input), 0, SEEK_SET) == -1) {
  ------------------
  |  Branch (43:9): [True: 0, False: 0]
  ------------------
   44|      0|        goto cleanup;
   45|      0|    }
   46|       |
   47|      0|    lyd_parse_data_fd(ctx, fileno(input), LYD_LYB, LYD_PARSE_STRICT, LYD_VALIDATE_PRESENT, &tree);
  ------------------
  |  |  147|      0|#define LYD_PARSE_STRICT    0x020000        /**< Instead of silently ignoring data without schema definition raise an error.
  ------------------
                  lyd_parse_data_fd(ctx, fileno(input), LYD_LYB, LYD_PARSE_STRICT, LYD_VALIDATE_PRESENT, &tree);
  ------------------
  |  |  213|      0|#define LYD_VALIDATE_PRESENT    0x0002      /**< Validate only modules whose data actually exist. */
  ------------------
   48|       |
   49|      0|cleanup:
   50|      0|    lyd_free_all(tree);
   51|      0|    if (input) {
  ------------------
  |  Branch (51:9): [True: 0, False: 0]
  ------------------
   52|      0|        fclose(input);
   53|      0|    }
   54|      0|    ly_ctx_destroy(ctx);
   55|      0|    return 0;
   56|      0|}

