Go to most recent revision | Details | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
2365 | konopa | 1 | /* This file contains the procedures for support directory operations. */ |
2 | |||
3 | /* Methods: |
||
4 | * do_sum: return total number of directory entries |
||
5 | * do_readentry: fill in the user buffer with directory entry specified by number |
||
6 | */ |
||
7 | |||
8 | |||
9 | #include <stdio.h> |
||
10 | #include "fs.h" |
||
11 | #include "dir.h" |
||
12 | #include "block.h" |
||
13 | #include "inode.h" |
||
14 | #include "param.h" |
||
15 | |||
16 | |||
17 | int do_sum() |
||
18 | { |
||
19 | |||
20 | /* Perform dsum system call. */ |
||
21 | |||
22 | inode_t *rip; |
||
23 | int dir_count; |
||
24 | offset_t dir_size; |
||
25 | |||
26 | rip = fp->fp_workdir; |
||
27 | dir_size = rip->i_size; |
||
28 | |||
29 | /* We must calculate with both versions of directory entry sizes. */ |
||
30 | if (rip->i_sp->s_extend) { |
||
31 | dir_count = dir_size/DIR_ENTRY_SIZE; |
||
32 | } |
||
33 | else { |
||
34 | dir_count = dir_size/DIR_ENTRY_SIZE_EX; |
||
35 | } |
||
36 | if (dir_size % DIR_ENTRY_SIZE_EX != 0) { |
||
37 | print_console("dir_size % DIR_ENTRY_SIZE_EX != 0\n"); |
||
38 | } |
||
39 | |||
40 | return dir_count; |
||
41 | } |
||
42 | |||
43 | |||
44 | int do_readentry() |
||
45 | { |
||
46 | |||
47 | /* Perform readentry(numb, buffer) system call. */ |
||
48 | |||
49 | int actual_sum, extend; |
||
50 | offset_t pos; |
||
51 | inode_t *rip; |
||
52 | block_num_t b; |
||
53 | block_t *bp; |
||
54 | register int r; |
||
55 | direct_t *dir; |
||
56 | directex_t *direx; |
||
57 | |||
58 | /* Get actual number of directory entries within the block. */ |
||
59 | actual_sum = do_sum(); |
||
60 | if (entry_number < 0 || actual_sum <= entry_number) |
||
61 | return FS_EINVAL; |
||
62 | |||
63 | rip = fp->fp_workdir; |
||
64 | extend = rip->i_sp->s_extend; |
||
65 | |||
66 | if (extend) { |
||
67 | pos = entry_number * DIR_ENTRY_SIZE_EX; |
||
68 | } |
||
69 | else { |
||
70 | pos = entry_number * DIR_ENTRY_SIZE; |
||
71 | } |
||
72 | |||
73 | /* Get number of block within the entry is. */ |
||
74 | b = read_map(rip, pos); |
||
75 | if (b == NO_BLOCK) |
||
76 | return 0; |
||
77 | |||
78 | bp = get_block(b); |
||
79 | |||
80 | /* Copy the entry data into address space of actual consument. */ |
||
81 | if (extend) { |
||
82 | direx = &bp->b.b__direx[entry_number]; |
||
83 | memcpy(fp->buffer, (void*)direx, DIR_ENTRY_SIZE_EX); |
||
84 | } |
||
85 | else { |
||
86 | dir = &bp->b.b__dir[entry_number]; |
||
87 | memcpy(fp->buffer, (void*)dir, DIR_ENTRY_SIZE); |
||
88 | } |
||
89 | |||
90 | r = (extend ? DIR_ENTRY_SIZE_EX : DIR_ENTRY_SIZE); |
||
91 | |||
92 | return r; |
||
93 | } |
||
94 | |||
95 |