return NT_STATUS_OK;
}
+NTSTATUS openat_pathref_fsp_dot(TALLOC_CTX *mem_ctx,
+ struct files_struct *dirfsp,
+ uint32_t flags,
+ struct smb_filename **_dot)
+{
+ struct connection_struct *conn = dirfsp->conn;
+ struct files_struct *fsp = NULL;
+ struct smb_filename *full_fname = NULL;
+ struct vfs_open_how how = {
+ .flags = O_RDONLY | O_NONBLOCK | O_NOFOLLOW,
+ };
+ struct smb_filename *dot = NULL;
+ NTSTATUS status;
+ int fd;
+
+#ifdef O_DIRECTORY
+ how.flags |= O_DIRECTORY;
+#endif
+
+#ifdef O_PATH
+ how.flags = O_PATH;
+#endif
+
+ dot = synthetic_smb_fname(mem_ctx, ".", NULL, NULL, 0, flags);
+ if (dot == NULL) {
+ return NT_STATUS_NO_MEMORY;
+ }
+
+ status = fsp_new(conn, conn, &fsp);
+ if (!NT_STATUS_IS_OK(status)) {
+ DBG_DEBUG("fsp_new() failed: %s\n", nt_errstr(status));
+ return status;
+ }
+
+ GetTimeOfDay(&fsp->open_time);
+ fsp_set_gen_id(fsp);
+ ZERO_STRUCT(conn->sconn->fsp_fi_cache);
+
+ fsp->fsp_flags.is_pathref = true;
+
+ full_fname = full_path_from_dirfsp_atname(conn, dirfsp, dot);
+ if (full_fname == NULL) {
+ DBG_DEBUG("full_path_from_dirfsp_atname(%s/%s) failed\n",
+ dirfsp->fsp_name->base_name,
+ dot->base_name);
+ file_free(NULL, fsp);
+ return NT_STATUS_NO_MEMORY;
+ }
+
+ status = fsp_attach_smb_fname(fsp, &full_fname);
+ if (!NT_STATUS_IS_OK(status)) {
+ DBG_DEBUG("fsp_attach_smb_fname(fsp, %s) failed: %s\n",
+ smb_fname_str_dbg(full_fname),
+ nt_errstr(status));
+ file_free(NULL, fsp);
+ return status;
+ }
+
+ fd = SMB_VFS_OPENAT(conn, dirfsp, dot, fsp, &how);
+ if (fd == -1) {
+ status = map_nt_error_from_unix(errno);
+ DBG_DEBUG("smb_vfs_openat(%s/%s) failed: %s\n",
+ dirfsp->fsp_name->base_name,
+ dot->base_name,
+ strerror(errno));
+ file_free(NULL, fsp);
+ return status;
+ }
+
+ fsp_set_fd(fsp, fd);
+
+ status = vfs_stat_fsp(fsp);
+
+ if (!NT_STATUS_IS_OK(status)) {
+ DBG_DEBUG("vfs_stat_fsp(\"/\") failed: %s\n",
+ nt_errstr(status));
+ fd_close(fsp);
+ file_free(NULL, fsp);
+ return status;
+ }
+
+ fsp->fsp_flags.is_directory = S_ISDIR(fsp->fsp_name->st.st_ex_mode);
+ fsp->fsp_flags.posix_open =
+ ((dot->flags & SMB_FILENAME_POSIX_PATH) != 0);
+ fsp->file_id = vfs_file_id_from_sbuf(conn, &fsp->fsp_name->st);
+
+ dot->st = fsp->fsp_name->st;
+
+ status = fsp_smb_fname_link(fsp,
+ &dot->fsp_link,
+ &dot->fsp);
+ if (!NT_STATUS_IS_OK(status)) {
+ DBG_DEBUG("fsp_smb_fname_link() failed: %s\n",
+ nt_errstr(status));
+ fd_close(fsp);
+ file_free(NULL, fsp);
+ return status;
+ }
+
+ DBG_DEBUG("fsp [%s]: OK, fd=%d\n", fsp_str_dbg(fsp), fd);
+
+ talloc_set_destructor(dot, smb_fname_fsp_destructor);
+
+ *_dot = dot;
+
+ return NT_STATUS_OK;
+}
+
void smb_fname_fsp_unlink(struct smb_filename *smb_fname)
{
talloc_set_destructor(smb_fname, NULL);