aboutsummaryrefslogtreecommitdiffstats
path: root/plpnfsd/main.cc
diff options
context:
space:
mode:
Diffstat (limited to 'plpnfsd/main.cc')
-rw-r--r--plpnfsd/main.cc163
1 files changed, 143 insertions, 20 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);
}