aboutsummaryrefslogtreecommitdiffstats
path: root/fs
diff options
context:
space:
mode:
Diffstat (limited to 'fs')
-rw-r--r--fs/pipe.c155
1 files changed, 93 insertions, 62 deletions
diff --git a/fs/pipe.c b/fs/pipe.c
index 2e60e1c8815e..b1626f269a34 100644
--- a/fs/pipe.c
+++ b/fs/pipe.c
@@ -874,87 +874,118 @@ fail_inode:
874 return NULL; 874 return NULL;
875} 875}
876 876
877int do_pipe(int *fd) 877struct file *create_write_pipe(void)
878{ 878{
879 struct qstr this; 879 int err;
880 char name[32]; 880 struct inode *inode;
881 struct file *f;
881 struct dentry *dentry; 882 struct dentry *dentry;
882 struct inode * inode; 883 char name[32];
883 struct file *f1, *f2; 884 struct qstr this;
884 int error;
885 int i, j;
886
887 error = -ENFILE;
888 f1 = get_empty_filp();
889 if (!f1)
890 goto no_files;
891
892 f2 = get_empty_filp();
893 if (!f2)
894 goto close_f1;
895 885
886 f = get_empty_filp();
887 if (!f)
888 return ERR_PTR(-ENFILE);
889 err = -ENFILE;
896 inode = get_pipe_inode(); 890 inode = get_pipe_inode();
897 if (!inode) 891 if (!inode)
898 goto close_f12; 892 goto err_file;
899 893
900 error = get_unused_fd();
901 if (error < 0)
902 goto close_f12_inode;
903 i = error;
904
905 error = get_unused_fd();
906 if (error < 0)
907 goto close_f12_inode_i;
908 j = error;
909
910 error = -ENOMEM;
911 sprintf(name, "[%lu]", inode->i_ino); 894 sprintf(name, "[%lu]", inode->i_ino);
912 this.name = name; 895 this.name = name;
913 this.len = strlen(name); 896 this.len = strlen(name);
914 this.hash = inode->i_ino; /* will go */ 897 this.hash = inode->i_ino; /* will go */
898 err = -ENOMEM;
915 dentry = d_alloc(pipe_mnt->mnt_sb->s_root, &this); 899 dentry = d_alloc(pipe_mnt->mnt_sb->s_root, &this);
916 if (!dentry) 900 if (!dentry)
917 goto close_f12_inode_i_j; 901 goto err_inode;
918 902
919 dentry->d_op = &pipefs_dentry_operations; 903 dentry->d_op = &pipefs_dentry_operations;
920 d_add(dentry, inode); 904 d_add(dentry, inode);
921 f1->f_vfsmnt = f2->f_vfsmnt = mntget(mntget(pipe_mnt)); 905 f->f_vfsmnt = mntget(pipe_mnt);
922 f1->f_dentry = f2->f_dentry = dget(dentry); 906 f->f_dentry = dentry;
923 f1->f_mapping = f2->f_mapping = inode->i_mapping; 907 f->f_mapping = inode->i_mapping;
924
925 /* read file */
926 f1->f_pos = f2->f_pos = 0;
927 f1->f_flags = O_RDONLY;
928 f1->f_op = &read_pipe_fops;
929 f1->f_mode = FMODE_READ;
930 f1->f_version = 0;
931
932 /* write file */
933 f2->f_flags = O_WRONLY;
934 f2->f_op = &write_pipe_fops;
935 f2->f_mode = FMODE_WRITE;
936 f2->f_version = 0;
937
938 fd_install(i, f1);
939 fd_install(j, f2);
940 fd[0] = i;
941 fd[1] = j;
942 908
943 return 0; 909 f->f_flags = O_WRONLY;
910 f->f_op = &write_pipe_fops;
911 f->f_mode = FMODE_WRITE;
912 f->f_version = 0;
944 913
945close_f12_inode_i_j: 914 return f;
946 put_unused_fd(j); 915
947close_f12_inode_i: 916 err_inode:
948 put_unused_fd(i);
949close_f12_inode:
950 free_pipe_info(inode); 917 free_pipe_info(inode);
951 iput(inode); 918 iput(inode);
952close_f12: 919 err_file:
953 put_filp(f2); 920 put_filp(f);
954close_f1: 921 return ERR_PTR(err);
955 put_filp(f1); 922}
956no_files: 923
957 return error; 924void free_write_pipe(struct file *f)
925{
926 mntput(f->f_vfsmnt);
927 dput(f->f_dentry);
928 put_filp(f);
929}
930
931struct file *create_read_pipe(struct file *wrf)
932{
933 struct file *f = get_empty_filp();
934 if (!f)
935 return ERR_PTR(-ENFILE);
936
937 /* Grab pipe from the writer */
938 f->f_vfsmnt = mntget(wrf->f_vfsmnt);
939 f->f_dentry = dget(wrf->f_dentry);
940 f->f_mapping = wrf->f_dentry->d_inode->i_mapping;
941
942 f->f_pos = 0;
943 f->f_flags = O_RDONLY;
944 f->f_op = &read_pipe_fops;
945 f->f_mode = FMODE_READ;
946 f->f_version = 0;
947
948 return f;
949}
950
951int do_pipe(int *fd)
952{
953 struct file *fw, *fr;
954 int error;
955 int fdw, fdr;
956
957 fw = create_write_pipe();
958 if (IS_ERR(fw))
959 return PTR_ERR(fw);
960 fr = create_read_pipe(fw);
961 error = PTR_ERR(fr);
962 if (IS_ERR(fr))
963 goto err_write_pipe;
964
965 error = get_unused_fd();
966 if (error < 0)
967 goto err_read_pipe;
968 fdr = error;
969
970 error = get_unused_fd();
971 if (error < 0)
972 goto err_fdr;
973 fdw = error;
974
975 fd_install(fdr, fr);
976 fd_install(fdw, fw);
977 fd[0] = fdr;
978 fd[1] = fdw;
979
980 return 0;
981
982 err_fdr:
983 put_unused_fd(fdr);
984 err_read_pipe:
985 put_filp(fr);
986 err_write_pipe:
987 free_write_pipe(fw);
988 return error;
958} 989}
959 990
960/* 991/*