* Copyright (C) 2002 by Ron Minnich <rminnich@lanl.gov>
*
* This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2
- * as published by the Free Software Foundation.
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
}
static int
-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)
+v9fs_create(struct v9fs_session_info *v9ses, u32 pfid, char *name,
+ u32 perm, u8 mode, u32 *fidp, struct v9fs_qid *qid, u32 *iounit)
{
u32 fid;
int err;
err = v9fs_t_walk(v9ses, pfid, fid, NULL, &fcall);
if (err < 0) {
PRINT_FCALL_ERROR("clone error", fcall);
- if (fcall && fcall->id == RWALK)
- goto clunk_fid;
- else
- goto put_fid;
+ goto error;
}
kfree(fcall);
- err = v9fs_t_create(v9ses, fid, name, perm, mode, extension, &fcall);
+ err = v9fs_t_create(v9ses, fid, name, perm, mode, &fcall);
if (err < 0) {
PRINT_FCALL_ERROR("create fails", fcall);
- goto clunk_fid;
+ goto error;
}
if (iounit)
kfree(fcall);
return 0;
-clunk_fid:
- v9fs_t_clunk(v9ses, fid);
- fid = V9FS_NOFID;
-
-put_fid:
+error:
if (fid >= 0)
v9fs_put_idpool(fid, &v9ses->fidpool);
&fcall);
if (err < 0) {
- if (fcall && fcall->id == RWALK)
- goto clunk_fid;
-
PRINT_FCALL_ERROR("walk error", fcall);
v9fs_put_idpool(nfid, &v9ses->fidpool);
goto error;
return ERR_PTR(err);
}
-static struct inode *
+struct inode *
v9fs_inode_from_fid(struct v9fs_session_info *v9ses, u32 fid,
struct super_block *sb)
{
flags = O_RDWR;
err = v9fs_create(v9ses, dfid->fid, (char *) dentry->d_name.name,
- perm, v9fs_uflags2omode(flags), NULL, &fid, &qid, &iounit);
+ perm, v9fs_uflags2omode(flags), &fid, &qid, &iounit);
if (err)
goto error;
perm = unixmode2p9mode(v9ses, mode | S_IFDIR);
err = v9fs_create(v9ses, dfid->fid, (char *) dentry->d_name.name,
- perm, V9FS_OREAD, NULL, &fid, NULL, NULL);
+ perm, V9FS_OREAD, &fid, NULL, NULL);
if (err) {
dprintk(DEBUG_ERROR, "create error %d\n", err);
}
result = v9fs_t_walk(v9ses, dirfidnum, newfid,
- (char *)dentry->d_name.name, &fcall);
-
+ (char *)dentry->d_name.name, NULL);
if (result < 0) {
- if (fcall && fcall->id == RWALK)
- v9fs_t_clunk(v9ses, newfid);
- else
- v9fs_put_idpool(newfid, &v9ses->fidpool);
-
+ v9fs_put_idpool(newfid, &v9ses->fidpool);
if (result == -ENOENT) {
d_add(dentry, NULL);
dprintk(DEBUG_VFS,
"Return negative dentry %p count %d\n",
dentry, atomic_read(&dentry->d_count));
- kfree(fcall);
return NULL;
}
dprintk(DEBUG_ERROR, "walk error:%d\n", result);
goto FreeFcall;
}
- kfree(fcall);
result = v9fs_t_stat(v9ses, newfid, &fcall);
if (result < 0) {
/* copy extension buffer into buffer */
if (fcall->params.rstat.stat.extension.len < buflen)
- buflen = fcall->params.rstat.stat.extension.len + 1;
+ buflen = fcall->params.rstat.stat.extension.len;
- memmove(buffer, fcall->params.rstat.stat.extension.str, buflen - 1);
+ memcpy(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:
if (!link)
link = ERR_PTR(-ENOMEM);
else {
- len = v9fs_readlink(dentry, link, PATH_MAX);
+ len = v9fs_readlink(dentry, link, strlen(link));
if (len < 0) {
__putname(link);
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);
}
err = v9fs_create(v9ses, dfid->fid, (char *) dentry->d_name.name,
- perm, V9FS_OREAD, (char *) extension, &fid, NULL, NULL);
+ perm, V9FS_OREAD, &fid, NULL, NULL);
if (err)
goto error;
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);
}
name = __getname();
- sprintf(name, "%d\n", oldfid->fid);
+ sprintf(name, "hardlink(%d)\n", oldfid->fid);
retval = v9fs_vfs_mkspecial(dir, dentry, V9FS_DMLINK, name);
__putname(name);
return -EINVAL;
name = __getname();
- if (!name)
- return -ENOMEM;
/* build extension */
if (S_ISBLK(mode))
sprintf(name, "b %u %u", MAJOR(rdev), MINOR(rdev));