1 /*
2 命令的功能 加选项-l -a -i -h
3 */
4
5 #include <stdio.h>
6 #include <sys/types.h>
7 #include <sys/stat.h>
8 #include <unistd.h>
9 #include <time.h>
10 #include <pwd.h>
11 #include <grp.h>
12 #include <stdlib.h>
13 #include <string.h>
14 #include <dirent.h>
15 #include <getopt.h>
16
17
18
19 static int show_id(const char *argv, struct stat *mystat);
20 static int show_type(const char *argv, struct stat *mystat);
21 static int show_usrerpermission(const char *argv, struct stat *mystat);
22 static int show_grperpermission(const char *argv, struct stat *mystat);
23 static int show_otherpermission(const char *argv, struct stat *mystat);
24 static int numoflink(const char *argv, struct stat *mystat);
25 static char *nameofusr(const char *argv, struct stat *mystat);
26 static char *nameofgrp(const char *argv, struct stat *mystat);
27 static int numofbit(const char *argv, struct stat *mystat);
28 static char *timeoflast_mod(const char *argv, struct stat *mystat);
29 static void name(const char *argv);
30 static int showall(const char *argv, struct stat *mystat);
31 static void show(const int argc, char **argv,struct stat *mystat);
32 static int rd(const char *argv, struct stat *mystat, char (*buf)[50], const int n);
33 static int is_dot(const char *argv);
34
35 int main(int argc, char *argv[])
36 {
37 if(argc < 3)
38 return 1;
39 struct stat mystat;
40 show(argc, argv, &mystat);
41
42 return 0;
43 }
44 // 显示全部的属性信息
45 static int showall(const char *argv, struct stat *mystat)
46 {
47 int ch;
48 int nlink, bit;
49 char *name_usr = NULL, *name_grp = NULL;
50 char *time = NULL;
51 ch = stat(argv, mystat);
52 if(ch == -1) {
53 perror("stat()");
54 return -1;
55 }
56 show_type(argv, mystat);
57
58 show_usrerpermission(argv, mystat);
59
60 show_grperpermission(argv, mystat);
61
62 show_otherpermission(argv, mystat);
63
64 nlink = numoflink(argv, mystat);
65 printf(" %3d ", nlink);
66
67 name_usr = nameofusr(argv, mystat);
68 printf("%s ", name_usr);
69
70 name_grp = nameofgrp(argv, mystat);
71 printf("%s ", name_grp);
72
73 bit = numofbit(argv, mystat);
74 printf("%5d ",bit);
75
76 time = timeoflast_mod(argv, mystat);
77 printf("%s ",time);
78 name(argv);
79
80 printf("\n");
81 return 0;
82 }
83
84 //显示 id
85 static int show_id(const char *argv, struct stat *mystat)
86 {
87 int ch ;
88
89 ch = lstat(argv, mystat);
90 if(ch == -1){
91 perror("lstat()");
92 return -1;
93 }
94 return mystat->st_ino;
95
96 }
97
98 //显示文件类型
99 static int show_type(const char *argv, struct stat *mystat)
100 {
101 int ch;
102 ch = lstat(argv, mystat);
103 if(ch == -1){
104 perror("lstat()");
105 return -1;
106 }
107 switch( mystat->st_mode & S_IFMT) {
108 case S_IFSOCK :
109 printf("s");
110 break;
111
112 case S_IFLNK :
113 printf("l");
114 break;
115 case S_IFREG :
116 printf("-");
117 break;
118 case S_IFBLK :
119 printf("b");
120 break;
121 case S_IFDIR :
122 printf("d");
123 break;
124 case S_IFCHR :
125 printf("c");
126 break;
127 case S_IFIFO :
128 printf("p");
129 break;
130 default :
131 break;
132 }
133 return 0;
134 }
135
136 //拥有者权限
137 static int show_usrerpermission(const char *argv, struct stat *mystat)
138 {
139 int ch;
140 ch = lstat(argv, mystat);
141 if(ch == -1){
142 perror("lstat()");
143 return -1;
144 }
145 if(mystat->st_mode & S_IRUSR) {
146 printf("r");
147 } else
148 printf("-");
149 if(mystat->st_mode & S_IWUSR) {
150 printf("w");
151 } else
152 printf("-");
153 if(mystat->st_mode & S_IXUSR) {
154 if(mystat->st_mode & S_ISUID){
155 printf("s");
156 } else
157 printf("x");
158 } else
159 printf("-");
160 return 0;
161 }
162
163 //所属组权限
164 static int show_grperpermission(const char *argv, struct stat *mystat)
165 {
166 int ch;
167 ch = lstat(argv, mystat);
168 if(ch == -1){
169 perror("lstat()");
170 return -1;
171 }
172 if(mystat->st_mode & S_IRGRP) {
173 printf("r");
174 } else
175 printf("-");
176 if(mystat->st_mode & S_IWGRP) {
177 printf("w");
178 } else
179 printf("-");
180 if(mystat->st_mode & S_IXGRP) {
181 if(mystat->st_mode & S_ISGID){
182 printf("s");
183 } else
184 printf("x");
185 } else
186 printf("-");
187 return 0;
188 }
189
190 //其他用户权限
191 static int show_otherpermission(const char *argv, struct stat *mystat)
192 {
193 int ch;
194 ch = lstat(argv, mystat);
195 if(ch == -1){
196 perror("lstat()");
197 return -1;
198 }
199 if(mystat->st_mode & S_IROTH) {
200 printf("r");
201 } else
202 printf("-");
203 if(mystat->st_mode & S_IWOTH) {
204 printf("w");
205 } else
206 printf("-");
207 if(mystat->st_mode & S_IXOTH) {
208 if(mystat->st_mode & S_ISVTX){
209 printf("t");
210 } else
211 printf("x");
212 } else
213 printf("-");
214 return 0;
215 }
216
217 //硬链接个数
218 static int numoflink(const char *argv, struct stat *mystat)
219 {
220 int ch;
221 int num;
222 ch = lstat(argv, mystat);
223 if(ch == -1) {
224 perror("lstat()");
225 return -1;
226 }
227 num = mystat->st_nlink;
228 return num;
229 }
230
231 //拥有者名字
232 static char *nameofusr(const char *argv, struct stat *mystat)
233 {
234 int ch;
235 struct passwd *pwd = NULL;
236 ch = lstat(argv, mystat);
237 if(ch == -1) {
238 perror("lstat()");
239 return NULL;
240 }
241 pwd = getpwuid(mystat->st_uid);
242 return pwd->pw_name;
243 }
244
245 //所属组名字
246 static char *nameofgrp(const char *argv, struct stat *mystat)
247 {
248 int ch;
249 struct group *grp = NULL;
250 ch = lstat(argv, mystat);
251 if(ch == -1) {
252 perror("lstat()");
253 return NULL;
254 }
255 grp = getgrgid(mystat->st_gid);
256 return grp->gr_name;
257 }
258
259 //文件字节大小
260 static int numofbit(const char *argv, struct stat *mystat)
261 {
262 int ch;
263 ch = lstat(argv, mystat);
264 if(ch == -1) {
265 perror("lstat()");
266 return -1;
267 }
268 return mystat->st_size;
269 }
270
271 //最后修改时间 --mtim
272 static char *timeoflast_mod(const char *argv, struct stat *mystat)
273 {
274 int ch;
275 char *buf = NULL;
276 buf = malloc(100);
277 struct tm *time = NULL;
278 ch = lstat(argv, mystat);
279 if(ch == -1) {
280 perror("lstat()");
281 return NULL;
282 }
283 time = localtime(&mystat->st_mtim.tv_sec);
284 strftime(buf, 100, "%m月 %d %H:%M", time);
285 return buf;
286
287
288 }
289
290 //文件名
291 static void name(const char *argv)
292 {
293 printf("%s ", argv);
294 }
295
296 //判断目录是不是. 和..
297 static int is_dot(const char *argv)
298 {
299 char *p = NULL;
300 p = strrchr(argv, '/');
301 if(p != NULL) {
302 if(!strcmp(p,"/.") || !strcmp(p, "/..")) {
303 return 1;
304 }
305 }
306 return 0;
307 }
308
309 //读文件
310 static int rd(const char *argv, struct stat *mystat, char (*buf)[50], const int n)
311 {
312 int ch;
313 DIR *dp = NULL;
314 struct dirent *dir = NULL;
315 int i=0;
316 ch = lstat(argv, mystat);
317 if(ch == -1) {
318 perror("lstat()");
319 return -1;
320 }
321 if( S_ISDIR(mystat->st_mode)) {
322 dp = opendir(argv);
323 if(dp == NULL) {
324 perror("opendir()");
325 return -1;
326 }
327 while(1) {
328 dir = readdir(dp);
329 if(dir == NULL)
330 break;
331 strcpy(buf[i], argv);
332 strcat(buf[i], "/");
333 strcat(buf[i], dir->d_name);
334 i++;
335 }
336 } else {
337 strcpy(buf[0],argv);
338 i++;
339 }
340 return i;
341 }
342
343 // -l -i等操作
344 static void show(const int argc, char **argv, struct stat *mystat)
345 {
346 char *optstring = "-ilha";
347 int c;
348 char buf[1024][50] = {};
349 int i, maxfile;
350 maxfile =rd(argv[2], mystat, buf, 1024);
351 while(1){
352 c = getopt(argc, argv, optstring);
353 if(c == -1)
354 break;
355 switch(c) {
356 case 'i':
357 for(i=0;i<maxfile;i++) {
358 if(is_dot(buf[i]))
359 continue;
360 printf("%d ",show_id(buf[i], mystat));
361 name(buf[i]);
362 printf("\n");
363 }
364 break;
365 case 'l':
366 for(i=0; i<maxfile; i++) {
367 if(is_dot(buf[i]))
368 continue;
369 showall(buf[i], mystat);
370 }
371 break;
372 case 'a':
373 for(i=0;i<maxfile; i++) {
374 name(buf[i]);
375 printf("\n");
376 }
377 break;
378 case 'h':
379 for(i=0; i<maxfile; i++) {
380 if(is_dot(buf[i]))
381 continue;
382 name(buf[i]);
383 printf("\n");
384 }
385 break;
386 case 1 :
387 printf("非选项参数%s\n", argv[optind-1]);
388 break;
389
390 default:
391 break;
392 }
393
394 }
395
396 }