summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorjdike <jdike>2003-02-06 18:38:19 +0000
committerjdike <jdike>2003-02-06 18:38:19 +0000
commit359d92f5a5a641a813a8a195d30cbb738db856cc (patch)
tree5d4b963b82e4cd214156fbccb94712042ae284f9
parentbc04c4f93dcf904ab404e617be9d16f09511bed3 (diff)
downloaduml-history-359d92f5a5a641a813a8a195d30cbb738db856cc.tar.gz
UML now locks the ubd files to avoid booting two UMLs on the same image.v_2_4_19_50
Accordingly, the os interface now has os_lock_file.
-rw-r--r--arch/um/drivers/ubd_user.c9
-rw-r--r--arch/um/include/os.h1
-rw-r--r--arch/um/os-Linux/file.c26
3 files changed, 35 insertions, 1 deletions
diff --git a/arch/um/drivers/ubd_user.c b/arch/um/drivers/ubd_user.c
index a756059..39c183f 100644
--- a/arch/um/drivers/ubd_user.c
+++ b/arch/um/drivers/ubd_user.c
@@ -346,6 +346,13 @@ int open_ubd_file(char *file, struct openflags *openflags,
if((fd = os_open_file(file, *openflags, mode)) < 0)
return(fd);
}
+
+ err = os_lock_file(fd, openflags->w);
+ if(err){
+ printk("Failed to lock '%s', errno = %d\n", file, -err);
+ goto error;
+ }
+
if(backing_file_out == NULL) return(fd);
err = read_cow_header(fd, &magic, &backing_file, &mtime, &size,
@@ -381,7 +388,7 @@ int open_ubd_file(char *file, struct openflags *openflags,
return(fd);
error:
- close(fd);
+ os_close_file(fd);
return(err);
}
diff --git a/arch/um/include/os.h b/arch/um/include/os.h
index b495b5b..e3f9dcb 100644
--- a/arch/um/include/os.h
+++ b/arch/um/include/os.h
@@ -107,6 +107,7 @@ extern int create_unix_socket(char *file, int len);
extern int os_connect_socket(char *name);
extern int os_file_type(char *file);
extern int os_file_mode(char *file, struct openflags *mode_out);
+extern int os_lock_file(int fd, int excl);
extern unsigned long os_process_pc(int pid);
extern int os_process_parent(int pid);
diff --git a/arch/um/os-Linux/file.c b/arch/um/os-Linux/file.c
index 61da438..7919020 100644
--- a/arch/um/os-Linux/file.c
+++ b/arch/um/os-Linux/file.c
@@ -346,6 +346,32 @@ void os_flush_stdout(void)
fflush(stdout);
}
+int os_lock_file(int fd, int excl)
+{
+ int type = excl ? F_WRLCK : F_RDLCK;
+ struct flock lock = ((struct flock) { .l_type = type,
+ .l_whence = SEEK_SET,
+ .l_start = 0,
+ .l_len = 0 } );
+ int err, save;
+
+ err = fcntl(fd, F_SETLK, &lock);
+ if(!err)
+ goto out;
+
+ save = -errno;
+ err = fcntl(fd, F_GETLK, &lock);
+ if(err){
+ err = -errno;
+ goto out;
+ }
+
+ printk("F_SETLK failed, file already locked by pid %d\n", lock.l_pid);
+ err = save;
+ out:
+ return(err);
+}
+
/*
* Overrides for Emacs so that we follow Linus's tabbing style.
* Emacs will notice this stuff at the end of the file and automatically