/src/util-linux/libblkid/src/superblocks/sysv.c
Line | Count | Source (jump to first uncovered line) |
1 | | /* |
2 | | * Copyright (C) 2008 Karel Zak <kzak@redhat.com> |
3 | | * |
4 | | * This is written from scratch according to Linux kernel fs/sysv/super.c file. |
5 | | * It seems that sysv probing code in libvolume_id and also in the original |
6 | | * blkid is useless. |
7 | | * |
8 | | * This file may be redistributed under the terms of the |
9 | | * GNU Lesser General Public License. |
10 | | */ |
11 | | #include <stdio.h> |
12 | | #include <stdlib.h> |
13 | | #include <unistd.h> |
14 | | #include <stdint.h> |
15 | | #include <stddef.h> |
16 | | |
17 | | #include "superblocks.h" |
18 | | |
19 | | #define XENIX_NICINOD 100 |
20 | | #define XENIX_NICFREE 100 |
21 | | |
22 | | struct xenix_super_block { |
23 | | uint16_t s_isize; |
24 | | uint32_t s_fsize; |
25 | | uint16_t s_nfree; |
26 | | uint32_t s_free[XENIX_NICFREE]; |
27 | | uint16_t s_ninode; |
28 | | uint16_t s_inode[XENIX_NICINOD]; |
29 | | uint8_t s_flock; |
30 | | uint8_t s_ilock; |
31 | | uint8_t s_fmod; |
32 | | uint8_t s_ronly; |
33 | | uint32_t s_time; |
34 | | uint32_t s_tfree; |
35 | | uint16_t s_tinode; |
36 | | uint16_t s_dinfo[4]; |
37 | | uint8_t s_fname[6]; |
38 | | uint8_t s_fpack[6]; |
39 | | uint8_t s_clean; |
40 | | uint8_t s_fill[371]; |
41 | | uint32_t s_magic; |
42 | | uint32_t s_type; |
43 | | } __attribute__((packed)); |
44 | | |
45 | | |
46 | | #define SYSV_NICINOD 100 |
47 | | #define SYSV_NICFREE 50 |
48 | | |
49 | | struct sysv_super_block |
50 | | { |
51 | | uint16_t s_isize; |
52 | | uint16_t s_pad0; |
53 | | uint32_t s_fsize; |
54 | | uint16_t s_nfree; |
55 | | uint16_t s_pad1; |
56 | | uint32_t s_free[SYSV_NICFREE]; |
57 | | uint16_t s_ninode; |
58 | | uint16_t s_pad2; |
59 | | uint16_t s_inode[SYSV_NICINOD]; |
60 | | uint8_t s_flock; |
61 | | uint8_t s_ilock; |
62 | | uint8_t s_fmod; |
63 | | uint8_t s_ronly; |
64 | | uint32_t s_time; |
65 | | uint16_t s_dinfo[4]; |
66 | | uint32_t s_tfree; |
67 | | uint16_t s_tinode; |
68 | | uint16_t s_pad3; |
69 | | uint8_t s_fname[6]; |
70 | | uint8_t s_fpack[6]; |
71 | | uint32_t s_fill[12]; |
72 | | uint32_t s_state; |
73 | | uint32_t s_magic; |
74 | | uint32_t s_type; |
75 | | }; |
76 | | |
77 | | static int probe_xenix(blkid_probe pr, const struct blkid_idmag *mag) |
78 | 3 | { |
79 | 3 | const struct xenix_super_block *sb; |
80 | | |
81 | 3 | sb = blkid_probe_get_sb(pr, mag, struct xenix_super_block); |
82 | 3 | if (!sb) |
83 | 0 | return errno ? -errno : 1; |
84 | 3 | blkid_probe_set_label(pr, sb->s_fname, sizeof(sb->s_fname)); |
85 | 3 | return 0; |
86 | 3 | } |
87 | | |
88 | 19.1k | #define SYSV_BLOCK_SIZE 1024 |
89 | | |
90 | | /* Note that we don't probe for Coherent FS, this FS does not have |
91 | | * magic string. (It requires to probe fname/fpack field..) |
92 | | */ |
93 | | static int probe_sysv(blkid_probe pr, |
94 | | const struct blkid_idmag *mag __attribute__((__unused__))) |
95 | 3.58k | { |
96 | 3.58k | struct sysv_super_block *sb; |
97 | 3.58k | int blocks[] = {0, 9, 15, 18}; |
98 | 3.58k | size_t i; |
99 | | |
100 | 10.6k | for (i = 0; i < ARRAY_SIZE(blocks); i++) { |
101 | 9.55k | int off = blocks[i] * SYSV_BLOCK_SIZE + SYSV_BLOCK_SIZE/2; |
102 | | |
103 | 9.55k | sb = (struct sysv_super_block *) |
104 | 9.55k | blkid_probe_get_buffer(pr, |
105 | 9.55k | off, |
106 | 9.55k | sizeof(struct sysv_super_block)); |
107 | 9.55k | if (!sb) |
108 | 2.47k | return errno ? -errno : 1; |
109 | | |
110 | 7.07k | if (sb->s_magic == cpu_to_le32(0xfd187e20) || |
111 | 7.07k | sb->s_magic == cpu_to_be32(0xfd187e20)) { |
112 | | |
113 | 12 | if (blkid_probe_set_label(pr, sb->s_fname, |
114 | 12 | sizeof(sb->s_fname))) |
115 | 0 | return 1; |
116 | | |
117 | 12 | if (blkid_probe_set_magic(pr, |
118 | 12 | off + offsetof(struct sysv_super_block, |
119 | 12 | s_magic), |
120 | 12 | sizeof(sb->s_magic), |
121 | 12 | (unsigned char *) &sb->s_magic)) |
122 | 0 | return 1; |
123 | | |
124 | 12 | return 0; |
125 | 12 | } |
126 | 7.07k | } |
127 | 1.09k | return 1; |
128 | 3.58k | } |
129 | | |
130 | | const struct blkid_idinfo xenix_idinfo = |
131 | | { |
132 | | .name = "xenix", |
133 | | .usage = BLKID_USAGE_FILESYSTEM, |
134 | | .probefunc = probe_xenix, |
135 | | .magics = |
136 | | { |
137 | | { .magic = "\x2b\x55\x44", .len = 3, .kboff = 1, .sboff = 0x400 }, |
138 | | { .magic = "\x44\x55\x2b", .len = 3, .kboff = 1, .sboff = 0x400 }, |
139 | | { NULL } |
140 | | } |
141 | | }; |
142 | | |
143 | | const struct blkid_idinfo sysv_idinfo = |
144 | | { |
145 | | .name = "sysv", |
146 | | .usage = BLKID_USAGE_FILESYSTEM, |
147 | | .probefunc = probe_sysv, |
148 | | |
149 | | /* SYSV is BE and LE, and superblock could be one of four positions. |
150 | | * So it's simpler to probe for the magic string via .probefunc(). |
151 | | */ |
152 | | .magics = BLKID_NONE_MAGIC |
153 | | }; |
154 | | |