static dav_error * dav_fs_walker(dav_fs_walker_context *fsctx, int depth)
{
    const dav_walk_params *params = fsctx->params;
    apr_pool_t *pool = params->pool;
    apr_status_t status;
    dav_error *err = NULL;
    int isdir = fsctx->res1.collection;
    apr_finfo_t dirent;
    apr_dir_t *dirp;
    err = (*params->func)(&fsctx->wres,
                          isdir
                          ? DAV_CALLTYPE_COLLECTION
                          : DAV_CALLTYPE_MEMBER);
    if (err != NULL) {
        return err;
    }
    if (depth == 0 || !isdir) {
        return NULL;
    }
    dav_check_bufsize(pool, &fsctx->path1, DAV_BUFFER_PAD);
    fsctx->path1.buf[fsctx->path1.cur_len++] = '/';
    fsctx->path1.buf[fsctx->path1.cur_len] = '\0';
    if (fsctx->path2.buf != NULL) {
        dav_check_bufsize(pool, &fsctx->path2, DAV_BUFFER_PAD);
        fsctx->path2.buf[fsctx->path2.cur_len++] = '/';
        fsctx->path2.buf[fsctx->path2.cur_len] = '\0';
    }
    fsctx->res1.exists = 1;
    fsctx->res1.collection = 0;
    fsctx->res2.collection = 0;
    if ((status = apr_dir_open(&dirp, fsctx->path1.buf, pool)) != APR_SUCCESS) {
        return dav_new_error(pool, HTTP_NOT_FOUND, 0, status, NULL);
    }
    while ((apr_dir_read(&dirent, APR_FINFO_DIRENT, dirp)) == APR_SUCCESS) {
        apr_size_t len;
        len = strlen(dirent.name);
        if (dirent.name[0] == '.'
              && (len == 1 || (dirent.name[1] == '.' && len == 2))) {
            continue;
        }
        if (params->walk_type & DAV_WALKTYPE_AUTH) {
            if (!strcmp(dirent.name, DAV_FS_STATE_DIR) ||
                !strncmp(dirent.name, DAV_FS_TMP_PREFIX,
                         strlen(DAV_FS_TMP_PREFIX))) {
                continue;
            }
        }
        if (!(params->walk_type & DAV_WALKTYPE_HIDDEN)
            && (!strcmp(dirent.name, DAV_FS_STATE_DIR) ||
                !strncmp(dirent.name, DAV_FS_TMP_PREFIX,
                         strlen(DAV_FS_TMP_PREFIX)))) {
            continue;
        }
        dav_buffer_place_mem(pool, &fsctx->path1, dirent.name, len + 1, 0);
        status = apr_stat(&fsctx->info1.finfo, fsctx->path1.buf,
                          DAV_FINFO_MASK, pool);
        if (status != APR_SUCCESS && status != APR_INCOMPLETE) {
            err = dav_new_error(pool, HTTP_NOT_FOUND, 0, status, NULL);
            break;
        }
        dav_buffer_place_mem(pool, &fsctx->uri_buf, dirent.name, len + 1, 1);
        if (fsctx->path2.buf != NULL) {
            dav_buffer_place_mem(pool, &fsctx->path2, dirent.name, len + 1, 0);
        }
        fsctx->info1.pathname = fsctx->path1.buf;
        fsctx->info2.pathname = fsctx->path2.buf;
        fsctx->res1.uri = fsctx->uri_buf.buf;
        if (fsctx->info1.finfo.filetype == APR_REG) {
            if ((err = (*params->func)(&fsctx->wres,
                                       DAV_CALLTYPE_MEMBER)) != NULL) {
                break;
            }
        }
        else if (fsctx->info1.finfo.filetype == APR_DIR) {
            apr_size_t save_path_len = fsctx->path1.cur_len;
            apr_size_t save_uri_len = fsctx->uri_buf.cur_len;
            apr_size_t save_path2_len = fsctx->path2.cur_len;
            fsctx->path1.cur_len += len;
            fsctx->path2.cur_len += len;
            fsctx->uri_buf.cur_len += len + 1;
            fsctx->uri_buf.buf[fsctx->uri_buf.cur_len - 1] = '/';
            fsctx->uri_buf.buf[fsctx->uri_buf.cur_len] = '\0';
            fsctx->res1.collection = 1;
            fsctx->res2.collection = 1;
            if ((err = dav_fs_walker(fsctx, depth - 1)) != NULL) {
                break;
            }
            fsctx->path1.cur_len = save_path_len;
            fsctx->path2.cur_len = save_path2_len;
            fsctx->uri_buf.cur_len = save_uri_len;
            fsctx->res1.collection = 0;
            fsctx->res2.collection = 0;
        }
    }
    apr_dir_close(dirp);
    if (err != NULL)
        return err;
    if (params->walk_type & DAV_WALKTYPE_LOCKNULL) {
        apr_size_t offset = 0;
        fsctx->path1.buf[fsctx->path1.cur_len - 1] = '\0';
        fsctx->res1.collection = 1;
        if ((err = dav_fs_get_locknull_members(&fsctx->res1,
                                               &fsctx->locknull_buf)) != NULL) {
            return err;
        }
        fsctx->path1.buf[fsctx->path1.cur_len - 1] = '/';
        fsctx->res1.exists = 0;
        fsctx->res1.collection = 0;
        memset(&fsctx->info1.finfo, 0, sizeof(fsctx->info1.finfo));
        while (offset < fsctx->locknull_buf.cur_len) {
            apr_size_t len = strlen(fsctx->locknull_buf.buf + offset);
            dav_lock *locks = NULL;
            dav_buffer_place_mem(pool, &fsctx->path1,
                                 fsctx->locknull_buf.buf + offset, len + 1, 0);
            dav_buffer_place_mem(pool, &fsctx->uri_buf,
                                 fsctx->locknull_buf.buf + offset, len + 1, 0);
            if (fsctx->path2.buf != NULL) {
                dav_buffer_place_mem(pool, &fsctx->path2,
                                     fsctx->locknull_buf.buf + offset,
                                     len + 1, 0);
            }
            fsctx->info1.pathname = fsctx->path1.buf;
            fsctx->info2.pathname = fsctx->path2.buf;
            fsctx->res1.uri = fsctx->uri_buf.buf;
            if ((err = dav_lock_query(params->lockdb, &fsctx->res1,
                                      &locks)) != NULL) {
                return err;
            }
            if (locks != NULL &&
                (err = (*params->func)(&fsctx->wres,
                                       DAV_CALLTYPE_LOCKNULL)) != NULL) {
                return err;
            }
            offset += len + 1;
        }
        fsctx->res1.exists = 1;
    }
    if (params->walk_type & DAV_WALKTYPE_POSTFIX) {
        fsctx->path1.buf[--fsctx->path1.cur_len] = '\0';
        fsctx->uri_buf.buf[--fsctx->uri_buf.cur_len] = '\0';
        if (fsctx->path2.buf != NULL) {
            fsctx->path2.buf[--fsctx->path2.cur_len] = '\0';
        }
        fsctx->res1.collection = 1;
        return (*params->func)(&fsctx->wres, DAV_CALLTYPE_POSTFIX);
    }
    return NULL;
}
['static dav_error * dav_fs_internal_walk(const dav_walk_params *params,\n                                        int depth, int is_move,\n                                        const dav_resource *root_dst,\n                                        dav_response **response)\n{\n    dav_fs_walker_context fsctx = { 0 };\n    dav_error *err;\n    dav_fs_copymove_walk_ctx cm_ctx = { 0 };\n#if DAV_DEBUG\n    if ((params->walk_type & DAV_WALKTYPE_LOCKNULL) != 0\n        && params->lockdb == NULL) {\n        return dav_new_error(params->pool, HTTP_INTERNAL_SERVER_ERROR, 0, 0,\n                             "DESIGN ERROR: walker called to walk locknull "\n                             "resources, but a lockdb was not provided.");\n    }\n#endif\n    fsctx.params = params;\n    fsctx.wres.walk_ctx = params->walk_ctx;\n    fsctx.wres.pool = params->pool;\n    fsctx.res1 = *params->root;\n    fsctx.res1.pool = params->pool;\n    fsctx.res1.info = &fsctx.info1;\n    fsctx.info1 = *params->root->info;\n    dav_buffer_init(params->pool, &fsctx.path1, fsctx.info1.pathname);\n    fsctx.info1.pathname = fsctx.path1.buf;\n    if (root_dst != NULL) {\n        fsctx.wres.walk_ctx = &cm_ctx;\n        cm_ctx.is_move = is_move;\n        cm_ctx.res_dst = &fsctx.res2;\n        cm_ctx.root = params->root;\n        cm_ctx.pool = params->pool;\n        fsctx.res2 = *root_dst;\n        fsctx.res2.exists = 0;\n        fsctx.res2.collection = 0;\n        fsctx.res2.uri = NULL;\n        fsctx.res2.pool = params->pool;\n        fsctx.res2.info = &fsctx.info2;\n        fsctx.info2 = *root_dst->info;\n        memset(&fsctx.info2.finfo, 0, sizeof(fsctx.info2.finfo));\n        dav_buffer_init(params->pool, &fsctx.path2, fsctx.info2.pathname);\n        fsctx.info2.pathname = fsctx.path2.buf;\n    }\n    dav_buffer_init(params->pool, &fsctx.uri_buf, params->root->uri);\n    if (fsctx.res1.collection\n        && fsctx.uri_buf.buf[fsctx.uri_buf.cur_len - 1] != \'/\') {\n        fsctx.uri_buf.buf[fsctx.uri_buf.cur_len++] = \'/\';\n        fsctx.uri_buf.buf[fsctx.uri_buf.cur_len] = \'\\0\';\n    }\n    fsctx.res1.uri = fsctx.uri_buf.buf;\n    fsctx.wres.resource = &fsctx.res1;\n    err = dav_fs_walker(&fsctx, depth);\n    *response = fsctx.wres.response;\n    return err;\n}', "static dav_error * dav_fs_walker(dav_fs_walker_context *fsctx, int depth)\n{\n    const dav_walk_params *params = fsctx->params;\n    apr_pool_t *pool = params->pool;\n    apr_status_t status;\n    dav_error *err = NULL;\n    int isdir = fsctx->res1.collection;\n    apr_finfo_t dirent;\n    apr_dir_t *dirp;\n    err = (*params->func)(&fsctx->wres,\n                          isdir\n                          ? DAV_CALLTYPE_COLLECTION\n                          : DAV_CALLTYPE_MEMBER);\n    if (err != NULL) {\n        return err;\n    }\n    if (depth == 0 || !isdir) {\n        return NULL;\n    }\n    dav_check_bufsize(pool, &fsctx->path1, DAV_BUFFER_PAD);\n    fsctx->path1.buf[fsctx->path1.cur_len++] = '/';\n    fsctx->path1.buf[fsctx->path1.cur_len] = '\\0';\n    if (fsctx->path2.buf != NULL) {\n        dav_check_bufsize(pool, &fsctx->path2, DAV_BUFFER_PAD);\n        fsctx->path2.buf[fsctx->path2.cur_len++] = '/';\n        fsctx->path2.buf[fsctx->path2.cur_len] = '\\0';\n    }\n    fsctx->res1.exists = 1;\n    fsctx->res1.collection = 0;\n    fsctx->res2.collection = 0;\n    if ((status = apr_dir_open(&dirp, fsctx->path1.buf, pool)) != APR_SUCCESS) {\n        return dav_new_error(pool, HTTP_NOT_FOUND, 0, status, NULL);\n    }\n    while ((apr_dir_read(&dirent, APR_FINFO_DIRENT, dirp)) == APR_SUCCESS) {\n        apr_size_t len;\n        len = strlen(dirent.name);\n        if (dirent.name[0] == '.'\n              && (len == 1 || (dirent.name[1] == '.' && len == 2))) {\n            continue;\n        }\n        if (params->walk_type & DAV_WALKTYPE_AUTH) {\n            if (!strcmp(dirent.name, DAV_FS_STATE_DIR) ||\n                !strncmp(dirent.name, DAV_FS_TMP_PREFIX,\n                         strlen(DAV_FS_TMP_PREFIX))) {\n                continue;\n            }\n        }\n        if (!(params->walk_type & DAV_WALKTYPE_HIDDEN)\n            && (!strcmp(dirent.name, DAV_FS_STATE_DIR) ||\n                !strncmp(dirent.name, DAV_FS_TMP_PREFIX,\n                         strlen(DAV_FS_TMP_PREFIX)))) {\n            continue;\n        }\n        dav_buffer_place_mem(pool, &fsctx->path1, dirent.name, len + 1, 0);\n        status = apr_stat(&fsctx->info1.finfo, fsctx->path1.buf,\n                          DAV_FINFO_MASK, pool);\n        if (status != APR_SUCCESS && status != APR_INCOMPLETE) {\n            err = dav_new_error(pool, HTTP_NOT_FOUND, 0, status, NULL);\n            break;\n        }\n        dav_buffer_place_mem(pool, &fsctx->uri_buf, dirent.name, len + 1, 1);\n        if (fsctx->path2.buf != NULL) {\n            dav_buffer_place_mem(pool, &fsctx->path2, dirent.name, len + 1, 0);\n        }\n        fsctx->info1.pathname = fsctx->path1.buf;\n        fsctx->info2.pathname = fsctx->path2.buf;\n        fsctx->res1.uri = fsctx->uri_buf.buf;\n        if (fsctx->info1.finfo.filetype == APR_REG) {\n            if ((err = (*params->func)(&fsctx->wres,\n                                       DAV_CALLTYPE_MEMBER)) != NULL) {\n                break;\n            }\n        }\n        else if (fsctx->info1.finfo.filetype == APR_DIR) {\n            apr_size_t save_path_len = fsctx->path1.cur_len;\n            apr_size_t save_uri_len = fsctx->uri_buf.cur_len;\n            apr_size_t save_path2_len = fsctx->path2.cur_len;\n            fsctx->path1.cur_len += len;\n            fsctx->path2.cur_len += len;\n            fsctx->uri_buf.cur_len += len + 1;\n            fsctx->uri_buf.buf[fsctx->uri_buf.cur_len - 1] = '/';\n            fsctx->uri_buf.buf[fsctx->uri_buf.cur_len] = '\\0';\n            fsctx->res1.collection = 1;\n            fsctx->res2.collection = 1;\n            if ((err = dav_fs_walker(fsctx, depth - 1)) != NULL) {\n                break;\n            }\n            fsctx->path1.cur_len = save_path_len;\n            fsctx->path2.cur_len = save_path2_len;\n            fsctx->uri_buf.cur_len = save_uri_len;\n            fsctx->res1.collection = 0;\n            fsctx->res2.collection = 0;\n        }\n    }\n    apr_dir_close(dirp);\n    if (err != NULL)\n        return err;\n    if (params->walk_type & DAV_WALKTYPE_LOCKNULL) {\n        apr_size_t offset = 0;\n        fsctx->path1.buf[fsctx->path1.cur_len - 1] = '\\0';\n        fsctx->res1.collection = 1;\n        if ((err = dav_fs_get_locknull_members(&fsctx->res1,\n                                               &fsctx->locknull_buf)) != NULL) {\n            return err;\n        }\n        fsctx->path1.buf[fsctx->path1.cur_len - 1] = '/';\n        fsctx->res1.exists = 0;\n        fsctx->res1.collection = 0;\n        memset(&fsctx->info1.finfo, 0, sizeof(fsctx->info1.finfo));\n        while (offset < fsctx->locknull_buf.cur_len) {\n            apr_size_t len = strlen(fsctx->locknull_buf.buf + offset);\n            dav_lock *locks = NULL;\n            dav_buffer_place_mem(pool, &fsctx->path1,\n                                 fsctx->locknull_buf.buf + offset, len + 1, 0);\n            dav_buffer_place_mem(pool, &fsctx->uri_buf,\n                                 fsctx->locknull_buf.buf + offset, len + 1, 0);\n            if (fsctx->path2.buf != NULL) {\n                dav_buffer_place_mem(pool, &fsctx->path2,\n                                     fsctx->locknull_buf.buf + offset,\n                                     len + 1, 0);\n            }\n            fsctx->info1.pathname = fsctx->path1.buf;\n            fsctx->info2.pathname = fsctx->path2.buf;\n            fsctx->res1.uri = fsctx->uri_buf.buf;\n            if ((err = dav_lock_query(params->lockdb, &fsctx->res1,\n                                      &locks)) != NULL) {\n                return err;\n            }\n            if (locks != NULL &&\n                (err = (*params->func)(&fsctx->wres,\n                                       DAV_CALLTYPE_LOCKNULL)) != NULL) {\n                return err;\n            }\n            offset += len + 1;\n        }\n        fsctx->res1.exists = 1;\n    }\n    if (params->walk_type & DAV_WALKTYPE_POSTFIX) {\n        fsctx->path1.buf[--fsctx->path1.cur_len] = '\\0';\n        fsctx->uri_buf.buf[--fsctx->uri_buf.cur_len] = '\\0';\n        if (fsctx->path2.buf != NULL) {\n            fsctx->path2.buf[--fsctx->path2.cur_len] = '\\0';\n        }\n        fsctx->res1.collection = 1;\n        return (*params->func)(&fsctx->wres, DAV_CALLTYPE_POSTFIX);\n    }\n    return NULL;\n}"]