| tHigh score file now locked properly (at least on Unix systems) - vaccinewars - be a doctor and try to vaccinate the world |
| git clone git://src.adamsgaard.dk/vaccinewars |
| Log |
| Files |
| Refs |
| README |
| LICENSE |
| --- |
| commit efe95b4aeddbb4032dc58dea10042eb47d7ef6f2 |
| parent dce44c4d5f93daa2fee494d82233ad03ce10fd94 |
| Author: Ben Webb |
| Date: Wed, 11 Apr 2001 21:33:24 +0000
High score file now locked properly (at least on Unix systems)
Diffstat:
M src/dopeos.c | 30 +++++++++++++++++++++++++++++-
M src/dopeos.h | 6 ++++++
M src/serverside.c | 6 ++++--
3 files changed, 39 insertions(+), 3 deletions(-)
--- |
| diff --git a/src/dopeos.c b/src/dopeos.c |
| t@@ -310,8 +310,14 @@ void SetReuse(SOCKET sock) {
if (setsockopt(sock,SOL_SOCKET,
SO_REUSEADDR,(char *)(&tmp),sizeof(tmp))==-1) {
perror("setsockopt"); exit(1);
+ }
}
-}
+
+/* We don't do locking under Win32 right now */
+int ReadLock(FILE *fp) { return 0; }
+int WriteLock(FILE *fp) { return 0; }
+void ReleaseLock(FILE *fp) { }
+
#endif /* NETWORKING */
#else /* Code for Unix build */
t@@ -324,6 +330,10 @@ void SetReuse(SOCKET sock) {
#include
#endif
+#ifdef HAVE_FCNTL_H
+#include
+#endif
+
int Width,Depth;
#ifdef CURSES_CLIENT
t@@ -355,6 +365,24 @@ void SetReuse(int sock) {
}
#endif /* NETWORKING */
+static int DoLock(FILE *fp,int l_type) {
+ struct flock lk;
+
+ lk.l_type = l_type;
+ lk.l_whence = lk.l_start = lk.l_len = 0;
+ lk.l_pid = 0;
+
+ while(1) {
+ if (fcntl(fileno(fp),F_SETLKW,&lk)==0) return 0;
+ else if (errno!=EINTR) return 1;
+ }
+ return 1;
+}
+
+int ReadLock(FILE *fp) { return DoLock(fp,F_RDLCK); }
+int WriteLock(FILE *fp) { return DoLock(fp,F_WRLCK); }
+void ReleaseLock(FILE *fp) { DoLock(fp,F_UNLCK); }
+
#endif /* CYGWIN */
void MicroSleep(int microsec) { |
| diff --git a/src/dopeos.h b/src/dopeos.h |
| t@@ -128,6 +128,8 @@ void SetReuse(SOCKET sock);
#include
+#include
+
#ifdef NETWORKING
#include
#include
t@@ -184,6 +186,10 @@ void SetReuse(int sock);
void MicroSleep(int microsec);
+int ReadLock(FILE *fp);
+int WriteLock(FILE *fp);
+void ReleaseLock(FILE *fp);
+
#ifndef SOCKET_ERROR
#define SOCKET_ERROR -1
#endif |
| diff --git a/src/serverside.c b/src/serverside.c |
| t@@ -903,10 +903,11 @@ int HighScoreRead(struct HISCORE *MultiScore,struct HISCORE *AntiqueScore) {
/* AntiqueScore (antique mode scores). Returns 1 on success, 0 on failure. */
memset(MultiScore,0,sizeof(struct HISCORE)*NUMHISCORE);
memset(AntiqueScore,0,sizeof(struct HISCORE)*NUMHISCORE);
- if (ScoreFP) {
+ if (ScoreFP && ReadLock(ScoreFP)==0) {
rewind(ScoreFP);
HighScoreTypeRead(AntiqueScore,ScoreFP);
HighScoreTypeRead(MultiScore,ScoreFP);
+ ReleaseLock(ScoreFP);
} else return 0;
return 1;
}
t@@ -914,11 +915,12 @@ int HighScoreRead(struct HISCORE *MultiScore,struct HISCORE *AntiqueScore) {
int HighScoreWrite(struct HISCORE *MultiScore,struct HISCORE *AntiqueScore) {
/* Writes out all the high scores from MultiScore and AntiqueScore; returns */
/* 1 on success, 0 on failure. */
- if (ScoreFP) {
+ if (ScoreFP && WriteLock(ScoreFP)==0) {
ftruncate(fileno(ScoreFP),0);
rewind(ScoreFP);
HighScoreTypeWrite(AntiqueScore,ScoreFP);
HighScoreTypeWrite(MultiScore,ScoreFP);
+ ReleaseLock(ScoreFP);
} else return 0;
return 1;
} |