1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
|
#ifndef _ADFS_FS_H
#define _ADFS_FS_H
#include <linux/types.h>
/*
* Structures of data on the disk
*/
/*
* Disc Record at disc address 0xc00
*/
struct adfs_discrecord {
unsigned char log2secsize;
unsigned char secspertrack;
unsigned char heads;
unsigned char density;
unsigned char idlen;
unsigned char log2bpmb;
unsigned char skew;
unsigned char bootoption;
unsigned char lowsector;
unsigned char nzones;
unsigned short zone_spare;
unsigned long root;
unsigned long disc_size;
unsigned short disc_id;
unsigned char disc_name[10];
unsigned long disc_type;
unsigned long disc_size_high;
unsigned char log2sharesize:4;
unsigned char unused:4;
unsigned char big_flag:1;
};
#define ADFS_DISCRECORD (0xc00)
#define ADFS_DR_OFFSET (0x1c0)
#define ADFS_DR_SIZE 60
#define ADFS_SUPER_MAGIC 0xadf5
#define ADFS_FREE_FRAG 0
#define ADFS_BAD_FRAG 1
#define ADFS_ROOT_FRAG 2
/*
* Directory header
*/
struct adfs_dirheader {
unsigned char startmasseq;
unsigned char startname[4];
};
#define ADFS_NEWDIR_SIZE 2048
#define ADFS_OLDDIR_SIZE 1024
#define ADFS_NUM_DIR_ENTRIES 77
/*
* Directory entries
*/
struct adfs_direntry {
char dirobname[10];
#define ADFS_NAME_LEN 10
__u8 dirload[4];
__u8 direxec[4];
__u8 dirlen[4];
__u8 dirinddiscadd[3];
__u8 newdiratts;
#define ADFS_NDA_OWNER_READ (1 << 0)
#define ADFS_NDA_OWNER_WRITE (1 << 1)
#define ADFS_NDA_LOCKED (1 << 2)
#define ADFS_NDA_DIRECTORY (1 << 3)
#define ADFS_NDA_EXECUTE (1 << 4)
#define ADFS_NDA_PUBLIC_READ (1 << 5)
#define ADFS_NDA_PUBLIC_WRITE (1 << 6)
};
#define ADFS_MAX_NAME_LEN 255
struct adfs_idir_entry {
__u32 inode_no; /* Address */
__u32 file_id; /* file id */
__u32 name_len; /* name length */
__u32 size; /* size */
__u32 mtime; /* modification time */
__u32 filetype; /* RiscOS file type */
__u8 mode; /* internal mode */
char name[ADFS_MAX_NAME_LEN]; /* file name */
};
/*
* Directory tail
*/
union adfs_dirtail {
struct {
unsigned char dirlastmask;
char dirname[10];
unsigned char dirparent[3];
char dirtitle[19];
unsigned char reserved[14];
unsigned char endmasseq;
unsigned char endname[4];
unsigned char dircheckbyte;
} old;
struct {
unsigned char dirlastmask;
unsigned char reserved[2];
unsigned char dirparent[3];
char dirtitle[19];
char dirname[10];
unsigned char endmasseq;
unsigned char endname[4];
unsigned char dircheckbyte;
} new;
};
#ifdef __KERNEL__
/*
* Calculate the boot block checksum on an ADFS drive. Note that this will
* appear to be correct if the sector contains all zeros, so also check that
* the disk size is non-zero!!!
*/
extern inline int adfs_checkbblk(unsigned char *ptr)
{
unsigned int result = 0;
unsigned char *p = ptr + 511;
do {
result = (result & 0xff) + (result >> 8);
result = result + *--p;
} while (p != ptr);
return (result & 0xff) != ptr[511];
}
/* dir.c */
extern unsigned int adfs_val (unsigned char *p, int len);
extern int adfs_dir_read_parent (struct inode *inode, struct buffer_head **bhp);
extern int adfs_dir_read (struct inode *inode, struct buffer_head **bhp);
extern int adfs_dir_check (struct inode *inode, struct buffer_head **bhp,
int buffers, union adfs_dirtail *dtp);
extern void adfs_dir_free (struct buffer_head **bhp, int buffers);
extern int adfs_dir_get (struct super_block *sb, struct buffer_head **bhp,
int buffers, int pos, unsigned long parent_object_id,
struct adfs_idir_entry *ide);
extern int adfs_dir_find_entry (struct super_block *sb, struct buffer_head **bhp,
int buffers, unsigned int index,
struct adfs_idir_entry *ide);
/* inode.c */
extern int adfs_inode_validate (struct inode *inode);
extern unsigned long adfs_inode_generate (unsigned long parent_id, int diridx);
extern unsigned long adfs_inode_objid (struct inode *inode);
extern unsigned int adfs_parent_bmap (struct inode *inode, int block);
extern int adfs_bmap (struct inode *inode, int block);
extern void adfs_read_inode (struct inode *inode);
/* map.c */
extern int adfs_map_lookup (struct super_block *sb, int frag_id, int offset);
/* namei.c */
extern struct dentry *adfs_lookup (struct inode *dir, struct dentry *dentry);
/* super.c */
extern int init_adfs_fs (void);
extern void adfs_error (struct super_block *, const char *, const char *, ...);
/*
* Inodes and file operations
*/
/* dir.c */
extern struct inode_operations adfs_dir_inode_operations;
/* file.c */
extern struct inode_operations adfs_file_inode_operations;
#endif
#endif
|