[PATCH] Simplification of file structures initialization

Juan Perez-Sanchez <[email protected]>
Newsgroups gmane.linux.ports.x8086
Message-ID <CAD6VGuZgCAF4t+bKqf+hUxU0_9jGAexW5L1OZSrtCAqt-XNxaA@mail.gmail.com>
Hi,

    Functions sys_execve(), get_pipe_inode(), sys_open(), close_fp()
and get_fd() repeated a lot of code. Now most of the work is done in
the new functions
open_filp() and close_filp().

The new kernel was tested under QEMU and a PentiumPro PC booting from floppy.

There was a reduction of 176 bytes in code size.

Greetings,

Juan
elks-2l.patch (text/x-patch, 15.1 KB)
diff -Nur elks.orig/arch/i86/drivers/char/dircon.c elks/arch/i86/drivers/char/dircon.c
--- elks.orig/arch/i86/drivers/char/dircon.c	2014-12-08 07:24:41.000000000 -0600
+++ elks/arch/i86/drivers/char/dircon.c	2015-01-23 18:03:06.000000000 -0600
@@ -105,8 +105,6 @@
 };
 #endif
 
-static void ClearRange(register Console * C, int x, int y, int xx, int yy);
-
 #ifdef CONFIG_DCON_VT52
 
 static void ScrollDown(register Console * C, int st, int en);
@@ -138,6 +136,20 @@
     }
 }
 
+static void ClearRange(register Console * C, int x, int y, int xx, int yy)
+{
+    __u16 en, ClrW;
+    register char *ofsp;
+
+    ClrW = (__u16) ((A_DEFAULT << 8) + ' ');
+    en = (__u16) ((xx + yy * Width) << 1);
+    ofsp = (char *)((__u16) ((x + y * Width) << 1));
+    while (((__u16)ofsp) < en) {
+	pokew((__u16) C->vseg, (__u16) ofsp, ClrW);
+	ofsp += 2;
+    }
+}
+
 static void ScrollUp(register Console * C, int st, int en)
 {
     unsigned rdofs, wrofs;
@@ -253,20 +265,6 @@
 
 #endif
 
-static void ClearRange(register Console * C, int x, int y, int xx, int yy)
-{
-    __u16 en, ClrW;
-    register char *ofsp;
-
-    ClrW = (__u16) ((A_DEFAULT << 8) + ' ');
-    en = (__u16) ((xx + yy * Width) << 1);
-    ofsp = (char *)((__u16) ((x + y * Width) << 1));
-    while (((__u16)ofsp) < en) {
-	pokew((__u16) C->vseg, (__u16) ofsp, ClrW);
-	ofsp += 2;
-    }
-}
-
 #ifdef CONFIG_DCON_VT52
 
 void Vt52Cmd(register Console * C, char c)
diff -Nur elks.orig/fs/exec.c elks/fs/exec.c
--- elks.orig/fs/exec.c	2015-01-21 18:26:30.000000000 -0600
+++ elks/fs/exec.c	2015-01-16 15:17:02.000000000 -0600
@@ -56,8 +56,8 @@
 {
     void *ptr;
     struct inode *inode;
-    register struct file *filp;
-    __registers *tregs;
+    struct file *filp;
+    register __registers *tregs;
     unsigned int suidfile, sgidfile;
     int retval;
     __u16 ds;
@@ -84,24 +84,11 @@
     /*
      *      Get a reading file handle
      */
-    retval = -ENFILE;
-    filp = get_empty_filp(O_RDONLY);
-    if(!filp) {
-	debug("\nNo filps\n");
+    if((retval = open_filp(O_RDONLY, inode, &filp)))
 	goto error_exec2;
-    }
-    filp->f_inode = inode;
-
-#ifdef BLOAT_FS
-    filp->f_reada = 0;
-#endif
-
-    filp->f_op = inode->i_op->default_file_ops;
     retval = -ENOEXEC;
-    if ((!filp->f_op)
-	|| ((filp->f_op->open) && (filp->f_op->open(inode, filp)))
-	|| (!filp->f_op->read))
-	goto normal_out;
+    if(!(filp->f_op) || !(filp->f_op->read))
+	goto error_exec3;
 
     debug1("EXEC: Inode dev = 0x%x opened OK.\n", inode->i_dev);
 
@@ -348,9 +335,7 @@
   error_exec3:
     tregs->ds = ds;
   normal_out:
-    if(filp->f_op->release)
-	filp->f_op->release(inode, filp);
-    filp->f_count--;
+    close_filp(inode, filp);
 
   error_exec2:
     if(retval)
diff -Nur elks.orig/fs/file_table.c elks/fs/file_table.c
--- elks.orig/fs/file_table.c	2014-12-08 07:24:41.000000000 -0600
+++ elks/fs/file_table.c	2015-01-15 17:11:35.000000000 -0600
@@ -8,6 +8,7 @@
 #include <linuxmt/config.h>
 #include <linuxmt/fs.h>
 #include <linuxmt/fcntl.h>
+#include <linuxmt/stat.h>
 #include <linuxmt/string.h>
 #include <linuxmt/mm.h>
 
@@ -24,23 +25,70 @@
  * we run out of memory.
  */
 
-struct file *get_empty_filp(unsigned short flags)
+int open_filp(unsigned short flags, struct inode *inode, struct file **fp)
 {
+    int result = 0;
     register struct file *f = file_array;
+    register struct file_operations *fop;
 
     do {
-	if (!f->f_count) {	/* TODO: is nr_file const? */
-	    memset(f, 0, sizeof(struct file));
-	    f->f_flags = flags;
-	    f->f_mode = (mode_t) ((flags + 1) & O_ACCMODE);
-	    f->f_count = 1;
-	    f->f_pos = 0;	/* FIXME - should call lseek */
+	if (!f->f_count)
+	    goto found_unused_fp;
+    } while(++f < &file_array[NR_FILE]);	/* TODO: is nr_file const? */
+    result = -ENFILE;
+    printk("\nNo filps\n");
+    goto exit_open_filp;
+
+  found_unused_fp:
+    memset(f, 0, sizeof(struct file));
+    f->f_flags = flags;
+    f->f_mode = (mode_t) ((flags + 1) & O_ACCMODE);
+    f->f_count = 1;
+    f->f_pos = 0;	/* FIXME - should call lseek */
 #ifdef BLOAT_FS
-	    f->f_version = ++event;
+    f->f_version = ++event;
 #endif
-	    return f;
-	}
-    } while(++f < &file_array[NR_FILE]);
+    f->f_inode = inode;
+#ifdef BLOAT_FS
+    if (f->f_mode & FMODE_WRITE) {
+	result = get_write_access(inode);
+	if (result)
+	    goto cleanup_file;
+    }
+#endif
+
+#ifdef BLOAT_FS
+    f->f_reada = 0;
+#endif
+
+    if(inode->i_op)
+	f->f_op = inode->i_op->default_file_ops;
+    fop = f->f_op;
+    if(fop && fop->open && (result = fop->open(inode, f))) {
+#ifdef BLOAT_FS
+	if(f->f_mode & FMODE_WRITE)
+	    put_write_access(inode);
+      cleanup_file:
+#endif
+	f->f_count--;
+    }
+    *fp = f;
 
-    return NULL;
+  exit_open_filp:
+    return result;
+}
+
+void close_filp(struct inode *inode, struct file *f)
+{
+    register struct file_operations *fop;
+
+    fop = f->f_op;
+    if(fop && fop->release)
+	fop->release(inode, f);
+
+#ifdef BLOAT_FS
+    if(f->f_mode & FMODE_WRITE)
+	put_write_access(inode);
+#endif
+    f->f_count--;
 }
diff -Nur elks.orig/fs/inode.c elks/fs/inode.c
--- elks.orig/fs/inode.c	2015-01-21 17:05:29.000000000 -0600
+++ elks/fs/inode.c	2015-01-23 18:44:01.000000000 -0600
@@ -432,7 +432,7 @@
     extern struct inode_operations pipe_inode_operations;
 
     if ((inode = get_empty_inode())) {
-	inode->i_mode |= S_IFIFO | S_IRUSR | S_IWUSR;
+	inode->i_mode = S_IFIFO | S_IRUSR | S_IWUSR;
 	inode->i_op = &pipe_inode_operations;
 	inode->i_gid = (__u8) current->egid;
 	inode->i_atime = inode->i_mtime = inode->i_ctime = CURRENT_TIME;
@@ -444,7 +444,7 @@
 	inode->i_pipe = 1;
 	PIPE_START(*inode) = PIPE_LEN(*inode) = 0;
 	PIPE_RD_OPENERS(*inode) = PIPE_WR_OPENERS(*inode) = 0;
-	PIPE_READERS(*inode) = PIPE_WRITERS(*inode) = 1;
+	PIPE_READERS(*inode) = PIPE_WRITERS(*inode) = 0;
 	PIPE_LOCK(*inode) = 0;
 
 #if 0
diff -Nur elks.orig/fs/minix/inode.c elks/fs/minix/inode.c
--- elks.orig/fs/minix/inode.c	2014-12-08 07:24:41.000000000 -0600
+++ elks/fs/minix/inode.c	2014-12-19 10:28:01.000000000 -0600
@@ -26,7 +26,6 @@
 static void minix_commit_super(register struct super_block *);
 static void minix_read_inode(register struct inode *);
 static struct buffer_head *minix_update_inode(register struct inode *);
-extern struct inode_operations pipe_inode_operations;
 
 /* Function definitions */
 
@@ -413,7 +412,7 @@
 	&blkdev_inode_operations,
 	&minix_file_inode_operations,
 	&minix_symlink_inode_operations,
-	NULL,				/* Socket */
+	&sock_inode_operations,		/* Socket */
     };
 
     inode->i_op = inop[(int)tabc[(inode->i_mode & S_IFMT) >> 12]];
diff -Nur elks.orig/fs/open.c elks/fs/open.c
--- elks.orig/fs/open.c	2014-12-08 07:24:41.000000000 -0600
+++ elks/fs/open.c	2015-01-15 17:26:25.000000000 -0600
@@ -369,76 +369,36 @@
 int sys_open(char *filename, int flags, int mode)
 {
     struct inode *inode;
-    register struct file *f;
-    int error, fd, flag;
+    struct file *f;
+    int error, flag;
 
-    f = get_empty_filp(flags);
-    if (!f) {
-	printk("\nNo filps\n");
-	return -ENFILE;
-    }
     flag = flags;
-    if (f->f_mode)
+    if ((mode_t)((flags + 1) & O_ACCMODE))
 	flag++;
     if (flag & (O_TRUNC | O_CREAT))
-	flag |= 2;
+	flag |= FMODE_WRITE;
+
     error = open_namei(filename, flag, mode, &inode, NULL);
+    if(error)
+	goto exit_open;
 
-    if (!error) {
+    error = open_filp(flags, inode, &f);
+    if(error)
+	goto cleanup_inode;
+    f->f_flags &= ~(O_CREAT | O_EXCL | O_NOCTTY | O_TRUNC);
+
+    /*
+     * We have to do this last, because we mustn't export
+     * an incomplete fd to other processes which may share
+     * the same file table with us.
+     */
+    if ((error = get_unused_fd(f)) > -1)
+	goto exit_open;
+    close_filp(inode, f);
 
-#ifdef BLOAT_FS
-	if (f->f_mode & FMODE_WRITE) {
-	    error = get_write_access(inode);
-	    if (error)
-		goto cleanup_inode;
-	}
-#endif
-
-	f->f_inode = inode;
-
-#ifdef BLOAT_FS
-	f->f_reada = 0;
-#endif
-
-	f->f_op = NULL;
-	{
-	    register struct inode_operations *iop = inode->i_op;
-	    if (iop)
-		f->f_op = iop->default_file_ops;
-	}
-	{
-	    register struct file_operations *fop = f->f_op;
-	    if (fop && fop->open) {
-		error = fop->open(inode, f);
-		if (error) {
-		    goto cleanup_all;
-		}
-	    }
-	    f->f_flags &= ~(O_CREAT | O_EXCL | O_NOCTTY | O_TRUNC);
-
-	    /*
-	     * We have to do this last, because we mustn't export
-	     * an incomplete fd to other processes which may share
-	     * the same file table with us.
-	     */
-	    if ((fd = get_unused_fd()) > -1) {
-		current->files.fd[fd] = f;
-		return fd;
-	    }
-	    error = -EMFILE;
-	    if (fop && fop->release)
-		fop->release(inode, f);
-	}
-      cleanup_all:
-#ifdef BLOAT_FS
-	if (f->f_mode & FMODE_WRITE)
-	    put_write_access(inode);
-      cleanup_inode:
-#endif
-	iput(inode);
-    }
-  cleanup_file:
-    f->f_count--;
+  cleanup_inode:
+    iput(inode);
+  exit_open:
     return error;
 }
 
@@ -446,25 +406,16 @@
 {
     register struct inode *inode;
 
-    if (filp->f_count == 0) {
+    if (filp->f_count < 1)
 	printk("VFS: Close: file count is 0\n");
-	goto cfp_end;
-    }
-    if (filp->f_count > 1) {
+    else if (filp->f_count > 1)
 	filp->f_count--;
-	goto cfp_end;
+    else {
+	inode = filp->f_inode;
+	close_filp(inode, filp);
+	filp->f_inode = NULL;
+	iput(inode);
     }
-    inode = filp->f_inode;
-    if (filp->f_op && filp->f_op->release)
-	filp->f_op->release(inode, filp);
-    filp->f_count--;
-    filp->f_inode = NULL;
-#ifdef BLOAT_FS
-    if (filp->f_mode & FMODE_WRITE)
-	put_write_access(inode);
-#endif
-    iput(inode);
-  cfp_end:
     return 0;
 }
 
diff -Nur elks.orig/fs/pipe.c elks/fs/pipe.c
--- elks.orig/fs/pipe.c	2015-01-21 17:28:26.000000000 -0600
+++ elks/fs/pipe.c	2015-01-23 17:17:42.000000000 -0600
@@ -28,13 +28,14 @@
 
 #define MAX_PIPES 8
 
-int get_unused_fd(void)
+int get_unused_fd(struct file *f)
 {
     register char *pfd = 0;
     register struct file_struct *cfs = &current->files;
 
     do {
 	if (!cfs->fd[(unsigned int) pfd]) {
+	    cfs->fd[(unsigned int) pfd] = f;
 	    clear_bit((unsigned int) pfd,
 			     &cfs->close_on_exec);
 	    return (int) pfd;
@@ -183,6 +184,7 @@
     return written;
 }
 
+#ifdef STRICT_PIPES
 static void pipe_read_release(register struct inode *inode, struct file *filp)
 {
     debug("PIPE: read_release called.\n");
@@ -196,6 +198,7 @@
     (inode->u.pipe_i.writers)--;
     wake_up_interruptible(&(inode->u.pipe_i.wait));
 }
+#endif
 
 static void pipe_rdwr_release(register struct inode *inode,
 			      register struct file *filp)
@@ -211,6 +214,7 @@
     wake_up_interruptible(&(inode->u.pipe_i.wait));
 }
 
+#ifdef STRICT_PIPES
 static int pipe_read_open(struct inode *inode, struct file *filp)
 {
     debug("PIPE: read_open called.\n");
@@ -226,6 +230,7 @@
 
     return 0;
 }
+#endif
 
 static int pipe_rdwr_open(register struct inode *inode,
 			  register struct file *filp)
@@ -241,6 +246,7 @@
     return 0;
 }
 
+#ifdef STRICT_PIPES
 static size_t bad_pipe_rw(struct inode *inode, struct file *filp,
 		       char *buf, int count)
 {
@@ -268,6 +274,7 @@
     pipe_write_open,
     pipe_write_release,
 };
+#endif
 
 struct file_operations rdwr_pipe_fops = {
     pipe_lseek,
@@ -304,9 +311,9 @@
 
 int do_pipe(int *fd)
 {
-    struct inode *inode;
-    register struct file *f1;
-    register struct file *f2;
+    register struct inode *inode;
+    struct file *f1;
+    struct file *f2;
     int error = -ENOMEM;
     int i;
 
@@ -315,48 +322,34 @@
 	goto no_inodes;
 
     /* read file */
-    error = -ENFILE;
-    f1 = get_empty_filp(O_RDONLY);
-    if (!f1)
+    if((error = open_filp(O_RDONLY, inode, &f1)))
 	goto no_files;
 
-    f1->f_inode = inode;
-    f1->f_op = &read_pipe_fops;
-
-    error = get_unused_fd();
-    if (error < 0)
+    if ((error = get_unused_fd(f1)) < 0)
 	goto close_f1;
-    current->files.fd[error] = f1;
     fd[0] = error;
     i = error;
 
     (inode->i_count)++;		/* Increase inode usage count */
     /* write file */
-    error = -ENFILE;
-    f2 = get_empty_filp(O_WRONLY);
-    if (!f2)
+    if((error = open_filp(O_WRONLY, inode, &f2)))
 	goto close_f1_i;
 
-    f2->f_inode = inode;
-    f2->f_op = &write_pipe_fops;
-
-    error = get_unused_fd();
-    if (error < 0)
+    if ((error = get_unused_fd(f2)) < 0)
 	goto close_f12;
-    current->files.fd[error] = f2;
     fd[1] = error;
 
     return 0;
 
   close_f12:
-    f2->f_count--;
+    close_filp(inode, f2);
 
   close_f1_i:
     current->files.fd[i] = NULL;
     inode->i_count--;
 
   close_f1:
-    f1->f_count--;
+    close_filp(inode, f1);
 
   no_files:
     iput(inode);
diff -Nur elks.orig/include/linuxmt/fs.h elks/include/linuxmt/fs.h
--- elks.orig/include/linuxmt/fs.h	2015-01-21 16:42:52.000000000 -0600
+++ elks/include/linuxmt/fs.h	2015-01-15 16:49:43.000000000 -0600
@@ -415,6 +415,10 @@
 extern struct file_operations read_pipe_fops;
 extern struct file_operations write_pipe_fops;
 extern struct file_operations rdwr_pipe_fops;
+extern struct inode_operations pipe_inode_operations;
+
+extern struct file_operations socket_file_ops;
+extern struct inode_operations sock_inode_operations;
 
 extern struct file_system_type *get_fs_type(char *);
 
@@ -461,7 +465,8 @@
 extern void insert_inode_hash(struct inode *);
 extern void clear_inode(struct inode *);
 extern struct inode *get_pipe_inode(void);
-extern struct file *get_empty_filp(unsigned short);
+extern int open_filp(unsigned short, struct inode *, struct file **);
+extern void close_filp(struct inode *, struct file *);
 
 extern struct buffer_head *get_hash_table(kdev_t,block_t);
 extern struct buffer_head *getblk(kdev_t,block_t);
@@ -509,7 +514,7 @@
 
 extern struct buffer_head *bread(dev_t,block_t);
 
-extern int get_unused_fd(void);
+extern int get_unused_fd(struct file *);
 extern char *get_pipe_mem(void);
 extern void free_pipe_mem(char *buf);
 
diff -Nur elks.orig/net/socket.c elks/net/socket.c
--- elks.orig/net/socket.c	2014-12-08 07:24:41.000000000 -0600
+++ elks/net/socket.c	2015-01-15 18:04:28.000000000 -0600
@@ -103,6 +103,7 @@
 	return NULL;
 
     inode->i_mode = S_IFSOCK;
+    inode->i_op = &sock_inode_operations;
     inode->i_gid = (__u8) current->egid;
     inode->i_sock = 1;
 
@@ -401,25 +402,42 @@
 #endif
 };
 
+struct inode_operations sock_inode_operations = {
+    &socket_file_ops, NULL,	/* create */
+    NULL,			/* lookup */
+    NULL,			/* link */
+    NULL,			/* unlink */
+    NULL,			/* symlink */
+    NULL,			/* mkdir */
+    NULL,			/* rmdir */
+    NULL,			/* mknod */
+    NULL,			/* readlink */
+    NULL,			/* follow_link */
+#ifdef BLOAT_FS
+    NULL,			/* bmap */
+#endif
+    NULL,			/* truncate */
+#ifdef BLOAT_FS
+    NULL			/* permission */
+#endif
+};
+
 /*@+type@*/
 
-int get_fd(register struct inode *inode)
+static int get_fd(register struct inode *inode)
 {
     int fd;
+    struct file *file;
 
-    fd = get_unused_fd();
-    if (fd >= 0) {
-	struct file *file = get_empty_filp(O_RDWR);
-	if (!file) {
-	    return -ENFILE;
-	}
-
-	file->f_inode = inode;
-	file->f_op = &socket_file_ops;
-	if (inode)
-	    inode->i_count++;
-	current->files.fd[fd] = file;
+    if((fd = open_filp(O_RDWR, inode, &file)))
+	goto no_files;
+    if ((fd = get_unused_fd(file)) > -1) {
+	inode->i_count++;		/*FIXME: Really needed?*/
+	goto no_files;
     }
+
+    close_filp(inode, file);
+  no_files:
     return fd;
 }
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.