|
@@ -255,8 +255,8 @@ struct inode *v9fs_get_inode(struct super_block *sb, int mode)
|
|
|
}
|
|
|
|
|
|
static int
|
|
|
-v9fs_create(struct v9fs_session_info *v9ses, u32 pfid, char *name,
|
|
|
- u32 perm, u8 mode, u32 *fidp, struct v9fs_qid *qid, u32 *iounit)
|
|
|
+v9fs_create(struct v9fs_session_info *v9ses, u32 pfid, char *name, u32 perm,
|
|
|
+ u8 mode, char *extension, u32 *fidp, struct v9fs_qid *qid, u32 *iounit)
|
|
|
{
|
|
|
u32 fid;
|
|
|
int err;
|
|
@@ -271,14 +271,14 @@ v9fs_create(struct v9fs_session_info *v9ses, u32 pfid, char *name,
|
|
|
err = v9fs_t_walk(v9ses, pfid, fid, NULL, &fcall);
|
|
|
if (err < 0) {
|
|
|
PRINT_FCALL_ERROR("clone error", fcall);
|
|
|
- goto error;
|
|
|
+ goto put_fid;
|
|
|
}
|
|
|
kfree(fcall);
|
|
|
|
|
|
- err = v9fs_t_create(v9ses, fid, name, perm, mode, &fcall);
|
|
|
+ err = v9fs_t_create(v9ses, fid, name, perm, mode, extension, &fcall);
|
|
|
if (err < 0) {
|
|
|
PRINT_FCALL_ERROR("create fails", fcall);
|
|
|
- goto error;
|
|
|
+ goto clunk_fid;
|
|
|
}
|
|
|
|
|
|
if (iounit)
|
|
@@ -293,7 +293,11 @@ v9fs_create(struct v9fs_session_info *v9ses, u32 pfid, char *name,
|
|
|
kfree(fcall);
|
|
|
return 0;
|
|
|
|
|
|
-error:
|
|
|
+clunk_fid:
|
|
|
+ v9fs_t_clunk(v9ses, fid);
|
|
|
+ fid = V9FS_NOFID;
|
|
|
+
|
|
|
+put_fid:
|
|
|
if (fid >= 0)
|
|
|
v9fs_put_idpool(fid, &v9ses->fidpool);
|
|
|
|
|
@@ -474,7 +478,7 @@ v9fs_vfs_create(struct inode *dir, struct dentry *dentry, int mode,
|
|
|
flags = O_RDWR;
|
|
|
|
|
|
err = v9fs_create(v9ses, dfid->fid, (char *) dentry->d_name.name,
|
|
|
- perm, v9fs_uflags2omode(flags), &fid, &qid, &iounit);
|
|
|
+ perm, v9fs_uflags2omode(flags), NULL, &fid, &qid, &iounit);
|
|
|
|
|
|
if (err)
|
|
|
goto error;
|
|
@@ -550,7 +554,7 @@ static int v9fs_vfs_mkdir(struct inode *dir, struct dentry *dentry, int mode)
|
|
|
perm = unixmode2p9mode(v9ses, mode | S_IFDIR);
|
|
|
|
|
|
err = v9fs_create(v9ses, dfid->fid, (char *) dentry->d_name.name,
|
|
|
- perm, V9FS_OREAD, &fid, NULL, NULL);
|
|
|
+ perm, V9FS_OREAD, NULL, &fid, NULL, NULL);
|
|
|
|
|
|
if (err) {
|
|
|
dprintk(DEBUG_ERROR, "create error %d\n", err);
|
|
@@ -1008,11 +1012,13 @@ static int v9fs_readlink(struct dentry *dentry, char *buffer, int buflen)
|
|
|
|
|
|
/* copy extension buffer into buffer */
|
|
|
if (fcall->params.rstat.stat.extension.len < buflen)
|
|
|
- buflen = fcall->params.rstat.stat.extension.len;
|
|
|
+ buflen = fcall->params.rstat.stat.extension.len + 1;
|
|
|
|
|
|
- memcpy(buffer, fcall->params.rstat.stat.extension.str, buflen - 1);
|
|
|
+ memmove(buffer, fcall->params.rstat.stat.extension.str, buflen - 1);
|
|
|
buffer[buflen-1] = 0;
|
|
|
|
|
|
+ dprintk(DEBUG_ERROR, "%s -> %.*s (%s)\n", dentry->d_name.name, fcall->params.rstat.stat.extension.len,
|
|
|
+ fcall->params.rstat.stat.extension.str, buffer);
|
|
|
retval = buflen;
|
|
|
|
|
|
FreeFcall:
|
|
@@ -1072,7 +1078,7 @@ static void *v9fs_vfs_follow_link(struct dentry *dentry, struct nameidata *nd)
|
|
|
if (!link)
|
|
|
link = ERR_PTR(-ENOMEM);
|
|
|
else {
|
|
|
- len = v9fs_readlink(dentry, link, strlen(link));
|
|
|
+ len = v9fs_readlink(dentry, link, PATH_MAX);
|
|
|
|
|
|
if (len < 0) {
|
|
|
__putname(link);
|
|
@@ -1109,10 +1115,7 @@ static int v9fs_vfs_mkspecial(struct inode *dir, struct dentry *dentry,
|
|
|
struct v9fs_session_info *v9ses;
|
|
|
struct v9fs_fid *dfid, *vfid;
|
|
|
struct inode *inode;
|
|
|
- struct v9fs_fcall *fcall;
|
|
|
- struct v9fs_wstat wstat;
|
|
|
|
|
|
- fcall = NULL;
|
|
|
inode = NULL;
|
|
|
vfid = NULL;
|
|
|
v9ses = v9fs_inode2v9ses(dir);
|
|
@@ -1125,7 +1128,7 @@ static int v9fs_vfs_mkspecial(struct inode *dir, struct dentry *dentry,
|
|
|
}
|
|
|
|
|
|
err = v9fs_create(v9ses, dfid->fid, (char *) dentry->d_name.name,
|
|
|
- perm, V9FS_OREAD, &fid, NULL, NULL);
|
|
|
+ perm, V9FS_OREAD, (char *) extension, &fid, NULL, NULL);
|
|
|
|
|
|
if (err)
|
|
|
goto error;
|
|
@@ -1148,23 +1151,11 @@ static int v9fs_vfs_mkspecial(struct inode *dir, struct dentry *dentry,
|
|
|
goto error;
|
|
|
}
|
|
|
|
|
|
- /* issue a Twstat */
|
|
|
- v9fs_blank_wstat(&wstat);
|
|
|
- wstat.muid = v9ses->name;
|
|
|
- wstat.extension = (char *) extension;
|
|
|
- err = v9fs_t_wstat(v9ses, vfid->fid, &wstat, &fcall);
|
|
|
- if (err < 0) {
|
|
|
- PRINT_FCALL_ERROR("wstat error", fcall);
|
|
|
- goto error;
|
|
|
- }
|
|
|
-
|
|
|
- kfree(fcall);
|
|
|
dentry->d_op = &v9fs_dentry_operations;
|
|
|
d_instantiate(dentry, inode);
|
|
|
return 0;
|
|
|
|
|
|
error:
|
|
|
- kfree(fcall);
|
|
|
if (vfid)
|
|
|
v9fs_fid_destroy(vfid);
|
|
|
|
|
@@ -1224,7 +1215,7 @@ v9fs_vfs_link(struct dentry *old_dentry, struct inode *dir,
|
|
|
}
|
|
|
|
|
|
name = __getname();
|
|
|
- sprintf(name, "hardlink(%d)\n", oldfid->fid);
|
|
|
+ sprintf(name, "%d\n", oldfid->fid);
|
|
|
retval = v9fs_vfs_mkspecial(dir, dentry, V9FS_DMLINK, name);
|
|
|
__putname(name);
|
|
|
|