@@ -144,10 +144,9 @@ The named directory must exist,
and must contain junction information.
Regular directory contents are made visible to NFS clients again by this operation.
.IP
-When removing a FedFS junction,
-existing FedFS records remain on the LDAP server.
-They can be removed by other means if it is known
-that no other junction refers to these records.
+When removing a FedFS junction, the
+.BR nfsref (8)
+command also removes FSN and FSL records referred to in the junction.
.IP
If junction deletion is successful, the
.BR nfsref (8)
@@ -108,6 +108,114 @@ nfsref_remove_nfs_basic(const char *junct_path)
}
/**
+ * Delete the FSN in a FedFS-style junction
+ *
+ * @param junct_path NUL-terminated C string containing pathname of junction
+ * @return a FedFsStatus code
+ */
+static FedFsStatus
+nfsref_remove_delete_fsn(const char *junct_path)
+{
+ char *binddn, *nce, *bindpw;
+ char *fsn_uuid = NULL;
+ unsigned int ldap_err;
+ FedFsStatus retval;
+ nsdb_t host;
+
+ retval = fedfs_get_fsn(junct_path, &fsn_uuid, &host);
+ switch (retval) {
+ case FEDFS_OK:
+ xlog(D_CALL, "%s: FSN UUID is %s", __func__, fsn_uuid);
+ break;
+ case FEDFS_ERR_NOTJUNCT:
+ xlog(L_ERROR, "%s is not an nfs-fedfs junction", junct_path);
+ goto out;
+ default:
+ xlog(L_ERROR, "Failed to read %s: %s",
+ junct_path, nsdb_display_fedfsstatus(retval));
+ goto out;
+ }
+
+ nsdb_env(NULL, NULL, &binddn, &nce, &bindpw);
+
+ retval = FEDFS_ERR_INVAL;
+ if (binddn == NULL)
+ binddn = (char *)nsdb_default_binddn(host);
+ if (binddn == NULL) {
+ fprintf(stderr, "No NDSB bind DN was specified\n");
+ goto out_free;
+ }
+ if (nce == NULL)
+ nce = (char *)nsdb_default_nce(host);
+ if (nce == NULL) {
+ fprintf(stderr, "No NCE was specified\n");
+ goto out_free;
+ }
+
+ retval = nsdb_open_nsdb(host, binddn, bindpw, &ldap_err);
+ switch (retval) {
+ case FEDFS_OK:
+ break;
+ case FEDFS_ERR_NSDB_CONN:
+ fprintf(stderr, "Failed to connect to NSDB %s:%u\n",
+ nsdb_hostname(host), nsdb_port(host));
+ goto out_free;
+ case FEDFS_ERR_NSDB_AUTH:
+ fprintf(stderr, "Failed to authenticate to NSDB %s:%u\n",
+ nsdb_hostname(host), nsdb_port(host));
+ goto out_free;
+ case FEDFS_ERR_NSDB_LDAP_VAL:
+ fprintf(stderr, "Failed to authenticate to NSDB %s:%u: %s\n",
+ nsdb_hostname(host), nsdb_port(host),
+ ldap_err2string(ldap_err));
+ goto out_free;
+ default:
+ fprintf(stderr, "Failed to bind to NSDB %s:%u: %s\n",
+ nsdb_hostname(host), nsdb_port(host),
+ nsdb_display_fedfsstatus(retval));
+ goto out_free;
+ }
+
+ retval = nsdb_delete_fsn_s(host, nce, fsn_uuid, true, &ldap_err);
+ switch (retval) {
+ case FEDFS_OK:
+ printf("Successfully deleted FSL records for FSN %s under %s\n",
+ fsn_uuid, nce);
+ break;
+ case FEDFS_ERR_NSDB_NONCE:
+ if (nce == NULL)
+ fprintf(stderr, "NSDB %s:%u has no NCE\n",
+ nsdb_hostname(host), nsdb_port(host));
+ else
+ fprintf(stderr, "NCE %s does not exist\n", nce);
+ break;
+ case FEDFS_ERR_NSDB_NOFSN:
+ fprintf(stderr, "NSDB %s:%u has no such FSN %s\n",
+ nsdb_hostname(host), nsdb_port(host), fsn_uuid);
+ break;
+ case FEDFS_ERR_NSDB_NOFSL:
+ fprintf(stderr, "FSN %s still has FSL entries\n", fsn_uuid);
+ break;
+ case FEDFS_ERR_NSDB_LDAP_VAL:
+ /* XXX: "Operation not allowed on non-leaf" means
+ * this FSN still has children FSLs. */
+ fprintf(stderr, "Failed to delete FSN %s: %s\n",
+ fsn_uuid, ldap_err2string(ldap_err));
+ break;
+ default:
+ fprintf(stderr, "Failed to delete FSN %s: %s\n",
+ fsn_uuid, nsdb_display_fedfsstatus(retval));
+ }
+
+ nsdb_close_nsdb(host);
+out_free:
+ free(fsn_uuid);
+ nsdb_free_nsdb(host);
+out:
+ return retval;
+}
+
+/**
* Remove a FedFS-style junction
*
* @param junct_path NUL-terminated C string containing pathname of junction
@@ -122,6 +230,8 @@ nfsref_remove_nfs_fedfs(const char *junct_path)
xlog(D_GENERAL, "%s: Removing FedFS junction from %s",
__func__, junct_path);
+ nfsref_remove_delete_fsn(junct_path);
+
retval = fedfs_delete_junction(junct_path);
switch (retval) {
case FEDFS_OK:
I have been told that, when removing a FedFS junction, the Solaris version of the nfsref command deletes the FSN it finds in a junction. It is assumed that in general, each junction created by the nfsref command will refer to its own FSN (ie, FSNs will not be shared by multiple nfsref- created junctions). Change the "nfsref remove" subcommand to work the way nfsref currently works on Solaris. Signed-off-by: Chuck Lever <chuck.lever@oracle.com> --- doc/man/nfsref.8 | 7 +-- src/nfsref/remove.c | 110 +++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 113 insertions(+), 4 deletions(-)