2 * linux/fs/hpfs/namei.c
4 * Mikulas Patocka (mikulas@artax.karlin.mff.cuni.cz), 1998-1999
6 * adding & removing files & directories
8 #include <linux/sched.h>
11 static void hpfs_update_directory_times(struct inode
*dir
)
13 time_t t
= get_seconds();
14 if (t
== dir
->i_mtime
.tv_sec
&&
15 t
== dir
->i_ctime
.tv_sec
)
17 dir
->i_mtime
.tv_sec
= dir
->i_ctime
.tv_sec
= t
;
18 dir
->i_mtime
.tv_nsec
= dir
->i_ctime
.tv_nsec
= 0;
19 hpfs_write_inode_nolock(dir
);
22 static int hpfs_mkdir(struct inode
*dir
, struct dentry
*dentry
, umode_t mode
)
24 const unsigned char *name
= dentry
->d_name
.name
;
25 unsigned len
= dentry
->d_name
.len
;
26 struct quad_buffer_head qbh0
;
27 struct buffer_head
*bh
;
28 struct hpfs_dirent
*de
;
35 struct hpfs_dirent dee
;
37 if ((err
= hpfs_chk_name(name
, &len
))) return err
==-ENOENT
? -EINVAL
: err
;
40 fnode
= hpfs_alloc_fnode(dir
->i_sb
, hpfs_i(dir
)->i_dno
, &fno
, &bh
);
43 dnode
= hpfs_alloc_dnode(dir
->i_sb
, fno
, &dno
, &qbh0
);
46 memset(&dee
, 0, sizeof dee
);
48 if (!(mode
& 0222)) dee
.read_only
= 1;
50 dee
.hidden
= name
[0] == '.';
51 dee
.fnode
= cpu_to_le32(fno
);
52 dee
.creation_date
= dee
.write_date
= dee
.read_date
= cpu_to_le32(gmt_to_local(dir
->i_sb
, get_seconds()));
53 result
= new_inode(dir
->i_sb
);
56 hpfs_init_inode(result
);
58 hpfs_i(result
)->i_parent_dir
= dir
->i_ino
;
59 hpfs_i(result
)->i_dno
= dno
;
60 result
->i_ctime
.tv_sec
= result
->i_mtime
.tv_sec
= result
->i_atime
.tv_sec
= local_to_gmt(dir
->i_sb
, le32_to_cpu(dee
.creation_date
));
61 result
->i_ctime
.tv_nsec
= 0;
62 result
->i_mtime
.tv_nsec
= 0;
63 result
->i_atime
.tv_nsec
= 0;
64 hpfs_i(result
)->i_ea_size
= 0;
65 result
->i_mode
|= S_IFDIR
;
66 result
->i_op
= &hpfs_dir_iops
;
67 result
->i_fop
= &hpfs_dir_ops
;
69 result
->i_size
= 2048;
72 result
->i_mode
&= ~0222;
74 r
= hpfs_add_dirent(dir
, name
, len
, &dee
);
82 memcpy(fnode
->name
, name
, len
> 15 ? 15 : len
);
83 fnode
->up
= cpu_to_le32(dir
->i_ino
);
84 fnode
->flags
|= FNODE_dir
;
85 fnode
->btree
.n_free_nodes
= 7;
86 fnode
->btree
.n_used_nodes
= 1;
87 fnode
->btree
.first_free
= cpu_to_le16(0x14);
88 fnode
->u
.external
[0].disk_secno
= cpu_to_le32(dno
);
89 fnode
->u
.external
[0].file_secno
= cpu_to_le32(-1);
90 dnode
->root_dnode
= 1;
91 dnode
->up
= cpu_to_le32(fno
);
92 de
= hpfs_add_de(dir
->i_sb
, dnode
, "\001\001", 2, 0);
93 de
->creation_date
= de
->write_date
= de
->read_date
= cpu_to_le32(gmt_to_local(dir
->i_sb
, get_seconds()));
94 if (!(mode
& 0222)) de
->read_only
= 1;
95 de
->first
= de
->directory
= 1;
96 /*de->hidden = de->system = 0;*/
97 de
->fnode
= cpu_to_le32(fno
);
98 mark_buffer_dirty(bh
);
100 hpfs_mark_4buffers_dirty(&qbh0
);
103 insert_inode_hash(result
);
105 if (!uid_eq(result
->i_uid
, current_fsuid()) ||
106 !gid_eq(result
->i_gid
, current_fsgid()) ||
107 result
->i_mode
!= (mode
| S_IFDIR
)) {
108 result
->i_uid
= current_fsuid();
109 result
->i_gid
= current_fsgid();
110 result
->i_mode
= mode
| S_IFDIR
;
111 hpfs_write_inode_nolock(result
);
113 hpfs_update_directory_times(dir
);
114 d_instantiate(dentry
, result
);
115 hpfs_unlock(dir
->i_sb
);
121 hpfs_free_dnode(dir
->i_sb
, dno
);
124 hpfs_free_sectors(dir
->i_sb
, fno
, 1);
126 hpfs_unlock(dir
->i_sb
);
130 static int hpfs_create(struct inode
*dir
, struct dentry
*dentry
, umode_t mode
, bool excl
)
132 const unsigned char *name
= dentry
->d_name
.name
;
133 unsigned len
= dentry
->d_name
.len
;
134 struct inode
*result
= NULL
;
135 struct buffer_head
*bh
;
139 struct hpfs_dirent dee
;
141 if ((err
= hpfs_chk_name(name
, &len
)))
142 return err
==-ENOENT
? -EINVAL
: err
;
143 hpfs_lock(dir
->i_sb
);
145 fnode
= hpfs_alloc_fnode(dir
->i_sb
, hpfs_i(dir
)->i_dno
, &fno
, &bh
);
148 memset(&dee
, 0, sizeof dee
);
149 if (!(mode
& 0222)) dee
.read_only
= 1;
151 dee
.hidden
= name
[0] == '.';
152 dee
.fnode
= cpu_to_le32(fno
);
153 dee
.creation_date
= dee
.write_date
= dee
.read_date
= cpu_to_le32(gmt_to_local(dir
->i_sb
, get_seconds()));
155 result
= new_inode(dir
->i_sb
);
159 hpfs_init_inode(result
);
161 result
->i_mode
|= S_IFREG
;
162 result
->i_mode
&= ~0111;
163 result
->i_op
= &hpfs_file_iops
;
164 result
->i_fop
= &hpfs_file_ops
;
165 set_nlink(result
, 1);
166 hpfs_i(result
)->i_parent_dir
= dir
->i_ino
;
167 result
->i_ctime
.tv_sec
= result
->i_mtime
.tv_sec
= result
->i_atime
.tv_sec
= local_to_gmt(dir
->i_sb
, le32_to_cpu(dee
.creation_date
));
168 result
->i_ctime
.tv_nsec
= 0;
169 result
->i_mtime
.tv_nsec
= 0;
170 result
->i_atime
.tv_nsec
= 0;
171 hpfs_i(result
)->i_ea_size
= 0;
173 result
->i_mode
&= ~0222;
174 result
->i_blocks
= 1;
176 result
->i_data
.a_ops
= &hpfs_aops
;
177 hpfs_i(result
)->mmu_private
= 0;
179 r
= hpfs_add_dirent(dir
, name
, len
, &dee
);
187 memcpy(fnode
->name
, name
, len
> 15 ? 15 : len
);
188 fnode
->up
= cpu_to_le32(dir
->i_ino
);
189 mark_buffer_dirty(bh
);
192 insert_inode_hash(result
);
194 if (!uid_eq(result
->i_uid
, current_fsuid()) ||
195 !gid_eq(result
->i_gid
, current_fsgid()) ||
196 result
->i_mode
!= (mode
| S_IFREG
)) {
197 result
->i_uid
= current_fsuid();
198 result
->i_gid
= current_fsgid();
199 result
->i_mode
= mode
| S_IFREG
;
200 hpfs_write_inode_nolock(result
);
202 hpfs_update_directory_times(dir
);
203 d_instantiate(dentry
, result
);
204 hpfs_unlock(dir
->i_sb
);
211 hpfs_free_sectors(dir
->i_sb
, fno
, 1);
213 hpfs_unlock(dir
->i_sb
);
217 static int hpfs_mknod(struct inode
*dir
, struct dentry
*dentry
, umode_t mode
, dev_t rdev
)
219 const unsigned char *name
= dentry
->d_name
.name
;
220 unsigned len
= dentry
->d_name
.len
;
221 struct buffer_head
*bh
;
225 struct hpfs_dirent dee
;
226 struct inode
*result
= NULL
;
228 if ((err
= hpfs_chk_name(name
, &len
))) return err
==-ENOENT
? -EINVAL
: err
;
229 if (hpfs_sb(dir
->i_sb
)->sb_eas
< 2) return -EPERM
;
230 if (!new_valid_dev(rdev
))
232 hpfs_lock(dir
->i_sb
);
234 fnode
= hpfs_alloc_fnode(dir
->i_sb
, hpfs_i(dir
)->i_dno
, &fno
, &bh
);
237 memset(&dee
, 0, sizeof dee
);
238 if (!(mode
& 0222)) dee
.read_only
= 1;
240 dee
.hidden
= name
[0] == '.';
241 dee
.fnode
= cpu_to_le32(fno
);
242 dee
.creation_date
= dee
.write_date
= dee
.read_date
= cpu_to_le32(gmt_to_local(dir
->i_sb
, get_seconds()));
244 result
= new_inode(dir
->i_sb
);
248 hpfs_init_inode(result
);
250 hpfs_i(result
)->i_parent_dir
= dir
->i_ino
;
251 result
->i_ctime
.tv_sec
= result
->i_mtime
.tv_sec
= result
->i_atime
.tv_sec
= local_to_gmt(dir
->i_sb
, le32_to_cpu(dee
.creation_date
));
252 result
->i_ctime
.tv_nsec
= 0;
253 result
->i_mtime
.tv_nsec
= 0;
254 result
->i_atime
.tv_nsec
= 0;
255 hpfs_i(result
)->i_ea_size
= 0;
256 result
->i_uid
= current_fsuid();
257 result
->i_gid
= current_fsgid();
258 set_nlink(result
, 1);
260 result
->i_blocks
= 1;
261 init_special_inode(result
, mode
, rdev
);
263 r
= hpfs_add_dirent(dir
, name
, len
, &dee
);
271 memcpy(fnode
->name
, name
, len
> 15 ? 15 : len
);
272 fnode
->up
= cpu_to_le32(dir
->i_ino
);
273 mark_buffer_dirty(bh
);
275 insert_inode_hash(result
);
277 hpfs_write_inode_nolock(result
);
278 hpfs_update_directory_times(dir
);
279 d_instantiate(dentry
, result
);
281 hpfs_unlock(dir
->i_sb
);
287 hpfs_free_sectors(dir
->i_sb
, fno
, 1);
289 hpfs_unlock(dir
->i_sb
);
293 static int hpfs_symlink(struct inode
*dir
, struct dentry
*dentry
, const char *symlink
)
295 const unsigned char *name
= dentry
->d_name
.name
;
296 unsigned len
= dentry
->d_name
.len
;
297 struct buffer_head
*bh
;
301 struct hpfs_dirent dee
;
302 struct inode
*result
;
304 if ((err
= hpfs_chk_name(name
, &len
))) return err
==-ENOENT
? -EINVAL
: err
;
305 hpfs_lock(dir
->i_sb
);
306 if (hpfs_sb(dir
->i_sb
)->sb_eas
< 2) {
307 hpfs_unlock(dir
->i_sb
);
311 fnode
= hpfs_alloc_fnode(dir
->i_sb
, hpfs_i(dir
)->i_dno
, &fno
, &bh
);
314 memset(&dee
, 0, sizeof dee
);
316 dee
.hidden
= name
[0] == '.';
317 dee
.fnode
= cpu_to_le32(fno
);
318 dee
.creation_date
= dee
.write_date
= dee
.read_date
= cpu_to_le32(gmt_to_local(dir
->i_sb
, get_seconds()));
320 result
= new_inode(dir
->i_sb
);
324 hpfs_init_inode(result
);
325 hpfs_i(result
)->i_parent_dir
= dir
->i_ino
;
326 result
->i_ctime
.tv_sec
= result
->i_mtime
.tv_sec
= result
->i_atime
.tv_sec
= local_to_gmt(dir
->i_sb
, le32_to_cpu(dee
.creation_date
));
327 result
->i_ctime
.tv_nsec
= 0;
328 result
->i_mtime
.tv_nsec
= 0;
329 result
->i_atime
.tv_nsec
= 0;
330 hpfs_i(result
)->i_ea_size
= 0;
331 result
->i_mode
= S_IFLNK
| 0777;
332 result
->i_uid
= current_fsuid();
333 result
->i_gid
= current_fsgid();
334 result
->i_blocks
= 1;
335 set_nlink(result
, 1);
336 result
->i_size
= strlen(symlink
);
337 result
->i_op
= &page_symlink_inode_operations
;
338 result
->i_data
.a_ops
= &hpfs_symlink_aops
;
340 r
= hpfs_add_dirent(dir
, name
, len
, &dee
);
348 memcpy(fnode
->name
, name
, len
> 15 ? 15 : len
);
349 fnode
->up
= cpu_to_le32(dir
->i_ino
);
350 hpfs_set_ea(result
, fnode
, "SYMLINK", symlink
, strlen(symlink
));
351 mark_buffer_dirty(bh
);
354 insert_inode_hash(result
);
356 hpfs_write_inode_nolock(result
);
357 hpfs_update_directory_times(dir
);
358 d_instantiate(dentry
, result
);
359 hpfs_unlock(dir
->i_sb
);
365 hpfs_free_sectors(dir
->i_sb
, fno
, 1);
367 hpfs_unlock(dir
->i_sb
);
371 static int hpfs_unlink(struct inode
*dir
, struct dentry
*dentry
)
373 const unsigned char *name
= dentry
->d_name
.name
;
374 unsigned len
= dentry
->d_name
.len
;
375 struct quad_buffer_head qbh
;
376 struct hpfs_dirent
*de
;
377 struct inode
*inode
= dentry
->d_inode
;
382 hpfs_lock(dir
->i_sb
);
383 hpfs_adjust_length(name
, &len
);
386 de
= map_dirent(dir
, hpfs_i(dir
)->i_dno
, name
, len
, &dno
, &qbh
);
398 r
= hpfs_remove_dirent(dir
, dno
, de
, &qbh
, 1);
401 hpfs_error(dir
->i_sb
, "there was error when removing dirent");
404 case 2: /* no space for deleting */
417 hpfs_update_directory_times(dir
);
418 hpfs_unlock(dir
->i_sb
);
422 static int hpfs_rmdir(struct inode
*dir
, struct dentry
*dentry
)
424 const unsigned char *name
= dentry
->d_name
.name
;
425 unsigned len
= dentry
->d_name
.len
;
426 struct quad_buffer_head qbh
;
427 struct hpfs_dirent
*de
;
428 struct inode
*inode
= dentry
->d_inode
;
434 hpfs_adjust_length(name
, &len
);
435 hpfs_lock(dir
->i_sb
);
437 de
= map_dirent(dir
, hpfs_i(dir
)->i_dno
, name
, len
, &dno
, &qbh
);
449 hpfs_count_dnodes(dir
->i_sb
, hpfs_i(inode
)->i_dno
, NULL
, NULL
, &n_items
);
454 r
= hpfs_remove_dirent(dir
, dno
, de
, &qbh
, 1);
457 hpfs_error(dir
->i_sb
, "there was error when removing dirent");
473 hpfs_update_directory_times(dir
);
474 hpfs_unlock(dir
->i_sb
);
478 static int hpfs_symlink_readpage(struct file
*file
, struct page
*page
)
480 char *link
= kmap(page
);
481 struct inode
*i
= page
->mapping
->host
;
483 struct buffer_head
*bh
;
488 if (!(fnode
= hpfs_map_fnode(i
->i_sb
, i
->i_ino
, &bh
)))
490 err
= hpfs_read_ea(i
->i_sb
, fnode
, "SYMLINK", link
, PAGE_SIZE
);
494 hpfs_unlock(i
->i_sb
);
495 SetPageUptodate(page
);
501 hpfs_unlock(i
->i_sb
);
508 const struct address_space_operations hpfs_symlink_aops
= {
509 .readpage
= hpfs_symlink_readpage
512 static int hpfs_rename(struct inode
*old_dir
, struct dentry
*old_dentry
,
513 struct inode
*new_dir
, struct dentry
*new_dentry
)
515 const unsigned char *old_name
= old_dentry
->d_name
.name
;
516 unsigned old_len
= old_dentry
->d_name
.len
;
517 const unsigned char *new_name
= new_dentry
->d_name
.name
;
518 unsigned new_len
= new_dentry
->d_name
.len
;
519 struct inode
*i
= old_dentry
->d_inode
;
520 struct inode
*new_inode
= new_dentry
->d_inode
;
521 struct quad_buffer_head qbh
, qbh1
;
522 struct hpfs_dirent
*dep
, *nde
;
523 struct hpfs_dirent de
;
526 struct buffer_head
*bh
;
530 if ((err
= hpfs_chk_name(new_name
, &new_len
))) return err
;
532 hpfs_adjust_length(old_name
, &old_len
);
535 /* order doesn't matter, due to VFS exclusion */
537 /* Erm? Moving over the empty non-busy directory is perfectly legal */
538 if (new_inode
&& S_ISDIR(new_inode
->i_mode
)) {
543 if (!(dep
= map_dirent(old_dir
, hpfs_i(old_dir
)->i_dno
, old_name
, old_len
, &dno
, &qbh
))) {
544 hpfs_error(i
->i_sb
, "lookup succeeded but map dirent failed");
549 de
.hidden
= new_name
[0] == '.';
553 if ((r
= hpfs_remove_dirent(old_dir
, dno
, dep
, &qbh
, 1)) != 2) {
554 if ((nde
= map_dirent(new_dir
, hpfs_i(new_dir
)->i_dno
, new_name
, new_len
, NULL
, &qbh1
))) {
555 clear_nlink(new_inode
);
557 memcpy(nde
->name
, new_name
, new_len
);
558 hpfs_mark_4buffers_dirty(&qbh1
);
562 hpfs_error(new_dir
->i_sb
, "hpfs_rename: could not find dirent");
566 err
= r
== 2 ? -ENOSPC
: r
== 1 ? -EFSERROR
: 0;
570 if (new_dir
== old_dir
) hpfs_brelse4(&qbh
);
572 if ((r
= hpfs_add_dirent(new_dir
, new_name
, new_len
, &de
))) {
573 if (r
== -1) hpfs_error(new_dir
->i_sb
, "hpfs_rename: dirent already exists!");
574 err
= r
== 1 ? -ENOSPC
: -EFSERROR
;
575 if (new_dir
!= old_dir
) hpfs_brelse4(&qbh
);
579 if (new_dir
== old_dir
)
580 if (!(dep
= map_dirent(old_dir
, hpfs_i(old_dir
)->i_dno
, old_name
, old_len
, &dno
, &qbh
))) {
581 hpfs_error(i
->i_sb
, "lookup succeeded but map dirent failed at #2");
586 if ((r
= hpfs_remove_dirent(old_dir
, dno
, dep
, &qbh
, 0))) {
587 hpfs_error(i
->i_sb
, "hpfs_rename: could not remove dirent");
588 err
= r
== 2 ? -ENOSPC
: -EFSERROR
;
593 hpfs_i(i
)->i_parent_dir
= new_dir
->i_ino
;
594 if (S_ISDIR(i
->i_mode
)) {
598 if ((fnode
= hpfs_map_fnode(i
->i_sb
, i
->i_ino
, &bh
))) {
599 fnode
->up
= cpu_to_le32(new_dir
->i_ino
);
600 fnode
->len
= new_len
;
601 memcpy(fnode
->name
, new_name
, new_len
>15?15:new_len
);
602 if (new_len
< 15) memset(&fnode
->name
[new_len
], 0, 15 - new_len
);
603 mark_buffer_dirty(bh
);
608 hpfs_update_directory_times(old_dir
);
609 hpfs_update_directory_times(new_dir
);
611 hpfs_unlock(i
->i_sb
);
615 const struct inode_operations hpfs_dir_iops
=
617 .create
= hpfs_create
,
618 .lookup
= hpfs_lookup
,
619 .unlink
= hpfs_unlink
,
620 .symlink
= hpfs_symlink
,
624 .rename
= hpfs_rename
,
625 .setattr
= hpfs_setattr
,