This source file includes following definitions.
- cp_old_stat
- cp_new_stat
- sys_stat
- sys_newstat
- sys_lstat
- sys_newlstat
- sys_fstat
- sys_newfstat
- sys_readlink
1
2
3
4
5
6
7 #include <linux/errno.h>
8 #include <linux/string.h>
9 #include <linux/stat.h>
10 #include <linux/fs.h>
11 #include <linux/sched.h>
12 #include <linux/kernel.h>
13 #include <asm/segment.h>
14
15 static void cp_old_stat(struct inode * inode, struct old_stat * statbuf)
16 {
17 struct old_stat tmp;
18
19 printk("VFS: Warning: %s using old stat() call. Recompile your binary.\n",
20 current->comm);
21 tmp.st_dev = inode->i_dev;
22 tmp.st_ino = inode->i_ino;
23 tmp.st_mode = inode->i_mode;
24 tmp.st_nlink = inode->i_nlink;
25 tmp.st_uid = inode->i_uid;
26 tmp.st_gid = inode->i_gid;
27 tmp.st_rdev = inode->i_rdev;
28 tmp.st_size = inode->i_size;
29 tmp.st_atime = inode->i_atime;
30 tmp.st_mtime = inode->i_mtime;
31 tmp.st_ctime = inode->i_ctime;
32 memcpy_tofs(statbuf,&tmp,sizeof(tmp));
33 }
34
35 static void cp_new_stat(struct inode * inode, struct new_stat * statbuf)
36 {
37 struct new_stat tmp;
38 unsigned int blocks, indirect;
39
40 memset(&tmp, 0, sizeof(tmp));
41 tmp.st_dev = inode->i_dev;
42 tmp.st_ino = inode->i_ino;
43 tmp.st_mode = inode->i_mode;
44 tmp.st_nlink = inode->i_nlink;
45 tmp.st_uid = inode->i_uid;
46 tmp.st_gid = inode->i_gid;
47 tmp.st_rdev = inode->i_rdev;
48 tmp.st_size = inode->i_size;
49 tmp.st_atime = inode->i_atime;
50 tmp.st_mtime = inode->i_mtime;
51 tmp.st_ctime = inode->i_ctime;
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67 #define D_B 7
68 #define I_B (BLOCK_SIZE / sizeof(unsigned short))
69
70 if (!inode->i_blksize) {
71 blocks = (tmp.st_size + BLOCK_SIZE - 1) / BLOCK_SIZE;
72 if (blocks > D_B) {
73 indirect = (blocks - D_B + I_B - 1) / I_B;
74 blocks += indirect;
75 if (indirect > 1) {
76 indirect = (indirect - 1 + I_B - 1) / I_B;
77 blocks += indirect;
78 if (indirect > 1)
79 blocks++;
80 }
81 }
82 tmp.st_blocks = (BLOCK_SIZE / 512) * blocks;
83 tmp.st_blksize = BLOCK_SIZE;
84 } else {
85 tmp.st_blocks = inode->i_blocks;
86 tmp.st_blksize = inode->i_blksize;
87 }
88 memcpy_tofs(statbuf,&tmp,sizeof(tmp));
89 }
90
91 asmlinkage int sys_stat(char * filename, struct old_stat * statbuf)
92 {
93 struct inode * inode;
94 int error;
95
96 error = verify_area(VERIFY_WRITE,statbuf,sizeof (*statbuf));
97 if (error)
98 return error;
99 error = namei(filename,&inode);
100 if (error)
101 return error;
102 cp_old_stat(inode,statbuf);
103 iput(inode);
104 return 0;
105 }
106
107 asmlinkage int sys_newstat(char * filename, struct new_stat * statbuf)
108 {
109 struct inode * inode;
110 int error;
111
112 error = verify_area(VERIFY_WRITE,statbuf,sizeof (*statbuf));
113 if (error)
114 return error;
115 error = namei(filename,&inode);
116 if (error)
117 return error;
118 cp_new_stat(inode,statbuf);
119 iput(inode);
120 return 0;
121 }
122
123 asmlinkage int sys_lstat(char * filename, struct old_stat * statbuf)
124 {
125 struct inode * inode;
126 int error;
127
128 error = verify_area(VERIFY_WRITE,statbuf,sizeof (*statbuf));
129 if (error)
130 return error;
131 error = lnamei(filename,&inode);
132 if (error)
133 return error;
134 cp_old_stat(inode,statbuf);
135 iput(inode);
136 return 0;
137 }
138
139 asmlinkage int sys_newlstat(char * filename, struct new_stat * statbuf)
140 {
141 struct inode * inode;
142 int error;
143
144 error = verify_area(VERIFY_WRITE,statbuf,sizeof (*statbuf));
145 if (error)
146 return error;
147 error = lnamei(filename,&inode);
148 if (error)
149 return error;
150 cp_new_stat(inode,statbuf);
151 iput(inode);
152 return 0;
153 }
154
155 asmlinkage int sys_fstat(unsigned int fd, struct old_stat * statbuf)
156 {
157 struct file * f;
158 struct inode * inode;
159 int error;
160
161 error = verify_area(VERIFY_WRITE,statbuf,sizeof (*statbuf));
162 if (error)
163 return error;
164 if (fd >= NR_OPEN || !(f=current->files->fd[fd]) || !(inode=f->f_inode))
165 return -EBADF;
166 cp_old_stat(inode,statbuf);
167 return 0;
168 }
169
170 asmlinkage int sys_newfstat(unsigned int fd, struct new_stat * statbuf)
171 {
172 struct file * f;
173 struct inode * inode;
174 int error;
175
176 error = verify_area(VERIFY_WRITE,statbuf,sizeof (*statbuf));
177 if (error)
178 return error;
179 if (fd >= NR_OPEN || !(f=current->files->fd[fd]) || !(inode=f->f_inode))
180 return -EBADF;
181 cp_new_stat(inode,statbuf);
182 return 0;
183 }
184
185 asmlinkage int sys_readlink(const char * path, char * buf, int bufsiz)
186 {
187 struct inode * inode;
188 int error;
189
190 if (bufsiz <= 0)
191 return -EINVAL;
192 error = verify_area(VERIFY_WRITE,buf,bufsiz);
193 if (error)
194 return error;
195 error = lnamei(path,&inode);
196 if (error)
197 return error;
198 if (!inode->i_op || !inode->i_op->readlink) {
199 iput(inode);
200 return -EINVAL;
201 }
202 return inode->i_op->readlink(inode,buf,bufsiz);
203 }