diff options
Diffstat (limited to 'plpnfsd')
-rw-r--r-- | plpnfsd/main.cc | 163 | ||||
-rw-r--r-- | plpnfsd/mp_main.c | 5 | ||||
-rw-r--r-- | plpnfsd/mp_mount.c | 1 | ||||
-rw-r--r-- | plpnfsd/mp_pfs_ops.c | 45 | ||||
-rw-r--r-- | plpnfsd/rfsv_api.h | 5 |
5 files changed, 170 insertions, 49 deletions
diff --git a/plpnfsd/main.cc b/plpnfsd/main.cc index 77f178a..206d902 100644 --- a/plpnfsd/main.cc +++ b/plpnfsd/main.cc @@ -8,10 +8,12 @@ #include <stdlib.h> #include <stdio.h> #include <signal.h> +#include <syslog.h> #include "defs.h" #include "bool.h" -#include "rfsv32.h" +#include "rfsv.h" +#include "rfsvfactory.h" #include "bufferstore.h" #include "bufferarray.h" #include "ppsocket.h" @@ -19,16 +21,30 @@ extern "C" { #include "rfsv_api.h" } -static rfsv32 *a; +static rfsv *a; +static rfsvfactory *rf; +static char *a_filename; +static long a_handle; +static long a_offset; +static long a_openmode; long rfsv_isalive() { - return (a->getStatus() == 0); + if (!a) { + a = rf->create(true); + if (a != NULL) + return (a->getStatus() == 0); + } + return 0; } long rfsv_dir(const char *file, dentry **e) { bufferArray entries; dentry *tmp; - long ret = a->dir(&(*file), &entries); + long ret; + + if (!a) + return -1; + ret = a->dir(&(*file), &entries); while (!entries.empty()) { bufferStore s; s = entries.popBuffer(); @@ -46,10 +62,14 @@ long rfsv_dir(const char *file, dentry **e) { } long rfsv_dircount(const char *file, long *count) { + if (!a) + return -1; return a->dircount(&(*file), &(*count)); } long rfsv_rmdir(const char *name) { + if (!a) + return -1; return a->rmdir(name); } @@ -60,48 +80,129 @@ long rfsv_mkdir(const char *file) { } long rfsv_remove(const char *file) { + if (!a) + return -1; return a->remove(file); } long rfsv_fclose(long handle) { + if (!a) + return -1; return a->fclose(handle); } long rfsv_fopen(long attr, const char *file, long *handle) { long ph; - long ret = a->fopen(attr, file, ph); + long ret; + + if (!a) + return -1; + ret = a->fopen(a->opMode(attr), file, ph); *handle = ph; return ret; } long rfsv_fcreate(long attr, const char *file, long *handle) { long ph; - long ret = a->fcreatefile(attr, file, ph); + long ret; + + if (!a) + return -1; + ret = a->fcreatefile(attr, file, ph); *handle = ph; return ret; } -long rfsv_read(char *buf, long offset, long len, long handle) { - long ret = a->fseek(handle, offset, rfsv32::PSI_SEEK_SET); - if (ret >= 0) - ret = a->fread(handle, buf, len); +static long rfsv_opencached(const char *name, long mode) { + long ret; + int retry = 100; + + if (!a) + return -1; + while (((ret = a->fopen(a->opMode(mode), name, a_handle)) + == rfsv::E_PSI_GEN_INUSE) && retry--) + ; + if (ret) + return ret; + a_offset = 0; + a_openmode = mode; + a_filename = strdup(name); return ret; } -long rfsv_write(char *buf, long offset, long len, long handle) { - long ret = a->fseek(handle, offset, rfsv32::PSI_SEEK_SET); - if (ret >= 0) - ret = a->fwrite(handle, buf, len); +static long rfsv_closecached() { + if (!a) + return -1; + if (!a_filename) + return 0; + a->fclose(a_handle); + free(a_filename); + a_filename = 0; + return 0; +} + +long rfsv_read(char *buf, long offset, long len, char *name) { + // FIXME: this might break on RFSV16? + long ret = 0; + + if (!a) + return -1; + if (!a_filename || strcmp(a_filename, name) || a_openmode != rfsv::PSI_O_RDONLY) { + rfsv_closecached(); + if((ret = rfsv_opencached(name, rfsv::PSI_O_RDONLY))) + return ret; + } + if (a_offset != offset) + ret = a->fseek(a_handle, offset, rfsv::PSI_SEEK_SET); + if (ret >= 0) { + a_offset = offset; + ret = a->fread(a_handle, (unsigned char *)buf, len); + if (ret <= 0) + return ret; + a_offset += ret; + } + return ret; +} + +long rfsv_write(char *buf, long offset, long len, char *name) { + // FIXME: this might break on RFSV16? + long ret = 0; + + if (!a) + return -1; + + if (!a_filename || strcmp(a_filename, name) || a_openmode != rfsv::PSI_O_RDWR) { + if ((ret = rfsv_closecached())) + return ret; + if ((ret = rfsv_opencached(name, rfsv::PSI_O_RDWR))) + return ret; + } + if (a_offset != offset) + ret = a->fseek(a_handle, offset, rfsv::PSI_SEEK_SET); + if (ret >= 0) { + a_offset = offset; + ret = a->fwrite(a_handle, (unsigned char *)buf, len); + if (ret <= 0) + return ret; + a_offset += ret; + } return ret; } long rfsv_setmtime(const char *name, long time) { + if (!a) + return -1; return a->fsetmtime(name, time); } long rfsv_setsize(const char *name, long size) { long ph; - long ret = a->fopen(rfsv32::PSI_OMODE_READ_WRITE, name, ph); + long ret; + // FIXME: this might break on RFSV16? + + if (!a) + return -1; + ret = a->fopen(a->opMode(rfsv::PSI_O_RDWR), name, ph); if (!ret) { ret = a->fsetsize(ph, size); a->fclose(ph); @@ -110,10 +211,14 @@ long rfsv_setsize(const char *name, long size) { } long rfsv_setattr(const char *name, long sattr, long dattr) { + if (!a) + return -1; return a->fsetattr(name, dattr, sattr); } long rfsv_getattr(const char *name, long *attr, long *size, long *time) { + if (!a) + return -1; return a->fgeteattr(&(*name), &(*attr), &(*size), &(*time)); } @@ -122,11 +227,15 @@ long rfsv_statdev(char letter) { int devnum = letter - 'A'; char *name; - name = a->devinfo(devnum, &vfree, &vtotal, &vattr, &vuniqueid); + if (!a) + return -1; + name = a->devinfo(devnum, &vfree, &vtotal, &vattr, &vuniqueid); return (name == NULL); } long rfsv_rename(const char *oldname, const char *newname) { + if (!a) + return -1; return a->rename(oldname, newname); } @@ -136,6 +245,8 @@ long rfsv_drivelist(int *cnt, device **dlist) { long ret; int i; + if (!a) + return -1; ret = a->devlist(&devbits); if (ret == 0) for (i = 0; i<26; i++) { @@ -171,6 +282,7 @@ int main(int argc, char**argv) { char *mdir = DDIR; int sockNum = DPORT; int verbose = 0; + int status = 0; for (int i = 1; i < argc; i++) { if (!strcmp(argv[i], "-p") && i + 1 < argc) { @@ -187,10 +299,21 @@ int main(int argc, char**argv) { } else usage(); } - signal(SIGPIPE, SIG_IGN); skt = new ppsocket(); - skt->connect(NULL, sockNum); - a = new rfsv32(skt); - return mp_main(verbose, mdir, user); + if (!skt->connect(NULL, sockNum)) { + cerr << "plpnfsd: could not connect to ncpd" << endl; + status = 1; + } else { + rf = new rfsvfactory(skt); + a = rf->create(true); + openlog("plpnfsd", LOG_PID|LOG_CONS, LOG_DAEMON); + if (a != NULL) + syslog(LOG_INFO, "connected, status is %d", status); + else + syslog(LOG_INFO, "could not create rfsv object, connect delayed"); + status = mp_main(verbose, mdir, user); + delete a; + } + exit(status); } diff --git a/plpnfsd/mp_main.c b/plpnfsd/mp_main.c index 23623c6..3c3cab9 100644 --- a/plpnfsd/mp_main.c +++ b/plpnfsd/mp_main.c @@ -46,7 +46,8 @@ fattr root_fattr = {0, 0} }; -#if defined(hpux) || defined(__SVR4) || defined(__sgi) +#if defined(hpux) || defined(__SVR4) || defined(__sgi) +#ifndef sun void usleep(usec) int usec; @@ -57,7 +58,7 @@ int usec; t.tv_usec = (long) (usec % 1000000); select(0, (fd_set *) 0, (fd_set *) 0, (fd_set *) 0, &t); } - +#endif #endif /* hpux */ int diff --git a/plpnfsd/mp_mount.c b/plpnfsd/mp_mount.c index e607629..f0a82d4 100644 --- a/plpnfsd/mp_mount.c +++ b/plpnfsd/mp_mount.c @@ -589,6 +589,7 @@ mount_and_run(char *dir, void (*proc)(), nfs_fh *root_fh) get_num(cp->inode)->name, dcp->offset); clean_cache(&attrcache); query_cache = 0; /* clear the GETDENTS "cache". */ + rfsv_closecached(); } } } diff --git a/plpnfsd/mp_pfs_ops.c b/plpnfsd/mp_pfs_ops.c index 5bd0a55..669d435 100644 --- a/plpnfsd/mp_pfs_ops.c +++ b/plpnfsd/mp_pfs_ops.c @@ -729,7 +729,6 @@ nfsproc_read_2(struct readargs *ra) fattr *fp; struct cache *cp; struct dcache *dcp; - long phandle; long pattr; long psize; long ptime; @@ -752,30 +751,34 @@ nfsproc_read_2(struct readargs *ra) res.status = NFS_OK; return &res; } - if (rfsv_fopen(1, inode->name, &phandle) != 0) { - res.status = rfsv_isalive() ? NFSERR_NOENT : NO_PSION; - return &res; - } - if (rfsv_read(rop, ra->offset, - ra->count, phandle) < 0) { - rfsv_fclose(phandle); + + if(rfsv_read(rop, ra->offset, + ra->count, inode->name) < 0) { res.status = rfsv_isalive() ? NFSERR_NOENT : NO_PSION; return &res; } - rfsv_fclose(phandle); - rfsv_getattr(inode->name, &pattr, &psize, &ptime); + fp = &res.readres_u.reply.attributes; - pattr2attr(pattr, psize, ptime, fp, (unsigned char *) ra->file.data); - if (cp == 0) - cp = add_cache(&attrcache, inode->inode, fp); + if(!cp) // Problem: if an epoc process is enlarging the file, we wont recognize it + { + rfsv_getattr(inode->name, &pattr, &psize, &ptime); + pattr2attr(pattr, psize, ptime, fp, (unsigned char *) ra->file.data); + cp = add_cache(&attrcache, inode->inode, fp); + } + else + { + *fp = cp->attr; + } + + - len = fp->size - ra->offset; + len = cp->actual_size - ra->offset; if (len > ra->count) len = ra->count; - if (fp->size < ra->offset) + if (cp->actual_size < ra->offset) len = 0; if (debug > 1) - debuglog("Read: filesize %d read %d @ %d\n", fp->size, len, ra->offset); + debuglog("Read: filesize %d read %d @ %d\n", cp->actual_size,len,ra->offset); res.readres_u.reply.data.data_len = len; res.readres_u.reply.data.data_val = (char *) rop; @@ -870,7 +873,6 @@ nfsproc_write_2(writeargs *wa) struct dcache *dcp; fattr *fp; struct attrstat *gres; - long phandle; int len, dlen, doff; if (!inode) { @@ -922,18 +924,11 @@ nfsproc_write_2(writeargs *wa) debuglog("writing off: %d, len: %d, act: %d\n", dcp->offset, dcp->len, cp->actual_size); - if (rfsv_fopen(0x200, inode->name, &phandle) != 0) { - debuglog("write: open failed\n"); - res.status = rfsv_isalive() ? NFSERR_NOSPC : NO_PSION; - return &res; - } - if (rfsv_write(dcp->data, dcp->offset, dcp->len, phandle) != dcp->len) { - rfsv_fclose(phandle); + if (rfsv_write(dcp->data, dcp->offset, dcp->len, inode->name) != dcp->len) { debuglog("write: dump failed\n"); res.status = rfsv_isalive() ? NFSERR_NOSPC : NO_PSION; return &res; } - rfsv_fclose(phandle); dcp->towrite = 0; len = dcp->offset + dcp->len; if (len > cp->actual_size) diff --git a/plpnfsd/rfsv_api.h b/plpnfsd/rfsv_api.h index b1993f9..b63911d 100644 --- a/plpnfsd/rfsv_api.h +++ b/plpnfsd/rfsv_api.h @@ -18,8 +18,8 @@ extern long rfsv_rename(const char *oldname, const char *newname); extern long rfsv_fclose(long handle); extern long rfsv_fopen(long attr, const char *name, long *handle); extern long rfsv_fcreate(long attr, const char *name, long *handle); -extern long rfsv_read(char *buf, long offset, long len, long handle); -extern long rfsv_write(char *buf, long offset, long len, long handle); +extern long rfsv_read(char *buf, long offset, long len, char *name); +extern long rfsv_write(char *buf, long offset, long len, char *name); extern long rfsv_getattr(const char *name, long *attr, long *size, long *time); extern long rfsv_setattr(const char *name, long sattr, long dattr); extern long rfsv_setsize(const char *name, long size); @@ -28,5 +28,6 @@ extern long rfsv_drivelist(int *cnt, device **devlist); extern long rfsv_dircount(const char *name, long *count); extern long rfsv_statdev(char letter); extern long rfsv_isalive(); +extern long rfsv_closecached(void); #endif |