/* * Copyright (c) 1989, 1990, 1991 by the University of Washington * Copyright (c) 1992 by the University of Southern California * * For copying and distribution information, please see the files * and */ /* Seriously mutilated by swa@isi.edu, 9/21/92 */ #include #include #include #include /* SOLARIS doesnt have strings.h */ #include #include #include #include #include #include #include #include "dirsrv.h" int create_link(RREQ req, char **commandp, char **next_wordp, INPUT in, char client_dir[], int dir_magic_no) { VLINK clink; /* For stepping through links */ PATTRIB at; /* Attributes */ int tmp; char t_linktype; char t_fname[ARDP_PTXT_LEN_R]; char t_options[ARDP_PTXT_LEN_R]; VDIR_ST dir_st; /* Directory contents used ... */ VDIR dir = &dir_st; /* by individual lines */ int retval; vdir_init(dir); tmp = qsscanf(*next_wordp, "%'s %r", t_options, next_wordp); /* Log and return a better message */ if(tmp < 2) return error_reply(req, "Too few arguments: %'s", *commandp, 0); /* Read link info. and attributes. */ retval = in_link(in, *commandp, *next_wordp, 0, &clink, (TOKEN *) NULL); if (retval) return error_reply(req, "%s", p_err_string, 0); /* Do we need a better log message? */ plog(L_DIR_UPDATE, req,"CL %s %c %s %s %s %s %s %s", client_dir, clink->linktype, clink->name, clink->target, clink->hosttype, clink->host, clink->hsonametype,clink->hsoname,0); /* The next two tests are repeated several places throughout the code. Might be Nice if we made a function out of them. */ retval = dsrdir(client_dir,dir_magic_no,dir,NULL,0); if(retval == DSRFINFO_FORWARDED) { dforwarded(req, client_dir, dir_magic_no, dir); vlfree(clink); return PSUCCESS; } /* If not a directory, say so */ if(retval == DSRDIR_NOT_A_DIRECTORY) { creply(req,"FAILURE NOT-A-DIRECTORY\n"); plog(L_DIR_ERR, req,"Invalid directory name: %s", client_dir,0); vlfree(clink); RETURNPFAILURE; } /* If not authorized, say so */ if(!srv_check_acl(dir->dacl,NULL,req, "I",SCA_DIRECTORY,client_dir,NULL)) { creply(req,"FAILURE NOT-AUTHORIZED\n"); plog(L_AUTH_ERR,req, "Unauthorized CREATE-LINK: %s %s",client_dir, t_fname, 0); /* Free the directory links */ vlfree(clink); vdir_freelinks(dir); RETURNPFAILURE; } /* Make sure creator has all rights to link */ if(!srv_check_acl(dir->dacl,NULL,req, "alrmd", SCA_DIRECTORY,client_dir,NULL)) srv_add_client_to_acl("alrmd",req,&(clink->acl),EACL_LINK); retval = vl_insert(clink,dir,VLI_NOCONFLICT); if((retval == VL_INSERT_ALREADY_THERE) || (retval == UL_INSERT_ALREADY_THERE)) { creplyf(req,"FAILURE ALREADY-EXISTS %'s\n",clink->name); /* Free the directory links */ vdir_freelinks(dir); RETURNPFAILURE; } else if(retval == VL_INSERT_CONFLICT) { creplyf(req,"FAILURE NAME-CONFLICT %'s\n",clink->name); plog(L_DIR_ERR, req,"Conflicting link already exists: %'s %'s", client_dir, clink->name,0); /* Free the directory links */ vdir_freelinks(dir); RETURNPFAILURE; } if(!retval) retval = dswdir(client_dir,dir); /* if successful say so (need to clean this up) */ if(!retval) reply(req,"SUCCESS\n"); else creplyf(req, "FAILURE SERVER-FAILED Unable to write server directory %s\n", client_dir ); /* Free the directory links */ vdir_freelinks(dir); return(retval); }