1 /*
2 * JFFS2 -- Journalling Flash File System, Version 2.
3 *
4 * Copyright © 2001-2007 Red Hat, Inc.
5 * Copyright © 2004-2010 David Woodhouse <dwmw2@infradead.org>
6 *
7 * Created by David Woodhouse <dwmw2@infradead.org>
8 *
9 * For licensing information, see the file 'LICENCE' in this directory.
10 *
11 */
12
13 #include <linux/delay.h>
14 #include "nodelist.h"
15 #include "os-linux.h"
16 #include "los_crc32.h"
17 #include "jffs2_hash.h"
18 #include "capability_type.h"
19 #include "capability_api.h"
20
jffs2_setattr(struct jffs2_inode * inode,struct IATTR * attr)21 int jffs2_setattr (struct jffs2_inode *inode, struct IATTR *attr)
22 {
23 struct jffs2_full_dnode *old_metadata, *new_metadata;
24 struct jffs2_inode_info *f = JFFS2_INODE_INFO(inode);
25 struct jffs2_sb_info *c = JFFS2_SB_INFO(inode->i_sb);
26 struct jffs2_raw_inode *ri;
27 unsigned int ivalid;
28 mode_t tmp_mode;
29 uint c_uid = OsCurrUserGet()->effUserID;
30 uint c_gid = OsCurrUserGet()->effGid;
31 uint32_t alloclen;
32 int ret;
33 int alloc_type = ALLOC_NORMAL;
34
35 jffs2_dbg(1, "%s(): ino #%lu\n", __func__, inode->i_ino);
36 ri = jffs2_alloc_raw_inode();
37 if (!ri) {
38 return -ENOMEM;
39 }
40
41 ret = jffs2_reserve_space(c, sizeof(*ri), &alloclen, ALLOC_NORMAL, JFFS2_SUMMARY_INODE_SIZE);
42
43 if (ret) {
44 jffs2_free_raw_inode(ri);
45 return ret;
46 }
47 mutex_lock(&f->sem);
48 ivalid = attr->attr_chg_valid;
49 tmp_mode = inode->i_mode;
50
51 ri->magic = cpu_to_je16(JFFS2_MAGIC_BITMASK);
52 ri->nodetype = cpu_to_je16(JFFS2_NODETYPE_INODE);
53 ri->totlen = cpu_to_je32(sizeof(*ri));
54 ri->hdr_crc = cpu_to_je32(crc32(0, ri, (sizeof(struct jffs2_unknown_node)-4)));
55
56 ri->ino = cpu_to_je32(inode->i_ino);
57 ri->version = cpu_to_je32(++f->highest_version);
58 ri->uid = cpu_to_je16(inode->i_uid);
59 ri->gid = cpu_to_je16(inode->i_gid);
60
61 if (ivalid & CHG_UID) {
62 if (((c_uid != inode->i_uid) || (attr->attr_chg_uid != inode->i_uid)) && (!IsCapPermit(CAP_CHOWN))) {
63 jffs2_complete_reservation(c);
64 jffs2_free_raw_inode(ri);
65 mutex_unlock(&f->sem);
66 return -EPERM;
67 } else {
68 ri->uid = cpu_to_je16(attr->attr_chg_uid);
69 }
70 }
71
72 if (ivalid & CHG_GID) {
73 if (((c_gid != inode->i_gid) || (attr->attr_chg_gid != inode->i_gid)) && (!IsCapPermit(CAP_CHOWN))) {
74 jffs2_complete_reservation(c);
75 jffs2_free_raw_inode(ri);
76 mutex_unlock(&f->sem);
77 return -EPERM;
78 } else {
79 ri->gid = cpu_to_je16(attr->attr_chg_gid);
80 }
81 }
82
83 if (ivalid & CHG_MODE) {
84 if (!IsCapPermit(CAP_FOWNER) && (c_uid != inode->i_uid)) {
85 jffs2_complete_reservation(c);
86 jffs2_free_raw_inode(ri);
87 mutex_unlock(&f->sem);
88 return -EPERM;
89 } else {
90 attr->attr_chg_mode &= ~S_IFMT; // delete file type
91 tmp_mode &= S_IFMT;
92 tmp_mode = attr->attr_chg_mode | tmp_mode; // add old file type
93 }
94 }
95
96 if (ivalid & CHG_ATIME) {
97 if ((c_uid != inode->i_uid) || (attr->attr_chg_uid != inode->i_uid)) {
98 return -EPERM;
99 } else {
100 ri->atime = cpu_to_je32(attr->attr_chg_atime);
101 }
102 } else {
103 ri->atime = cpu_to_je32(inode->i_atime);
104 }
105
106 if (ivalid & CHG_MTIME) {
107 if ((c_uid != inode->i_uid) || (attr->attr_chg_uid != inode->i_uid)) {
108 return -EPERM;
109 } else {
110 ri->mtime = cpu_to_je32(attr->attr_chg_mtime);
111 }
112 } else {
113 ri->mtime = cpu_to_je32(Jffs2CurSec());
114 }
115 ri->mode = cpu_to_jemode(tmp_mode);
116
117 ri->isize = cpu_to_je32((ivalid & CHG_SIZE) ? attr->attr_chg_size : inode->i_size);
118 ri->ctime = cpu_to_je32(Jffs2CurSec());
119
120 ri->offset = cpu_to_je32(0);
121 ri->csize = ri->dsize = cpu_to_je32(0);
122 ri->compr = JFFS2_COMPR_NONE;
123 if (ivalid & CHG_SIZE && inode->i_size < attr->attr_chg_size) {
124 /* It's an extension. Make it a hole node */
125 ri->compr = JFFS2_COMPR_ZERO;
126 ri->dsize = cpu_to_je32(attr->attr_chg_size - inode->i_size);
127 ri->offset = cpu_to_je32(inode->i_size);
128 } else if (ivalid & CHG_SIZE && !attr->attr_chg_size) {
129 /* For truncate-to-zero, treat it as deletion because
130 it'll always be obsoleting all previous nodes */
131 alloc_type = ALLOC_DELETION;
132 }
133 ri->node_crc = cpu_to_je32(crc32(0, ri, (sizeof(*ri)-8)));
134 ri->data_crc = cpu_to_je32(0);
135 new_metadata = jffs2_write_dnode(c, f, ri, NULL, 0, alloc_type);
136 if (IS_ERR(new_metadata)) {
137 jffs2_complete_reservation(c);
138 jffs2_free_raw_inode(ri);
139 mutex_unlock(&f->sem);
140 return PTR_ERR(new_metadata);
141 }
142 /* It worked. Update the inode */
143 inode->i_atime = je32_to_cpu(ri->atime);
144 inode->i_ctime = je32_to_cpu(ri->ctime);
145 inode->i_mtime = je32_to_cpu(ri->mtime);
146 inode->i_mode = jemode_to_cpu(ri->mode);
147 inode->i_uid = je16_to_cpu(ri->uid);
148 inode->i_gid = je16_to_cpu(ri->gid);
149
150 old_metadata = f->metadata;
151 if (ivalid & CHG_SIZE && inode->i_size > attr->attr_chg_size)
152 jffs2_truncate_fragtree (c, &f->fragtree, attr->attr_chg_size);
153
154 if (ivalid & CHG_SIZE && inode->i_size < attr->attr_chg_size) {
155 jffs2_add_full_dnode_to_inode(c, f, new_metadata);
156 inode->i_size = attr->attr_chg_size;
157 f->metadata = NULL;
158 } else {
159 f->metadata = new_metadata;
160 }
161 if (old_metadata) {
162 jffs2_mark_node_obsolete(c, old_metadata->raw);
163 jffs2_free_full_dnode(old_metadata);
164 }
165 jffs2_free_raw_inode(ri);
166
167 mutex_unlock(&f->sem);
168 jffs2_complete_reservation(c);
169
170 /* We have to do the truncate_setsize() without f->sem held, since
171 some pages may be locked and waiting for it in readpage().
172 We are protected from a simultaneous write() extending i_size
173 back past iattr->ia_size, because do_truncate() holds the
174 generic inode semaphore. */
175 if (ivalid & CHG_SIZE && inode->i_size > attr->attr_chg_size) {
176 inode->i_size = attr->attr_chg_size; // truncate_setsize
177 }
178
179 return 0;
180 }
181
jffs2_clear_inode(struct jffs2_inode * inode)182 static void jffs2_clear_inode (struct jffs2_inode *inode)
183 {
184 /* We can forget about this inode for now - drop all
185 * the nodelists associated with it, etc.
186 */
187 struct jffs2_sb_info *c = JFFS2_SB_INFO(inode->i_sb);
188 struct jffs2_inode_info *f = JFFS2_INODE_INFO(inode);
189
190 jffs2_do_clear_inode(c, f);
191 }
192
ilookup(struct super_block * sb,uint32_t ino)193 static struct jffs2_inode *ilookup(struct super_block *sb, uint32_t ino)
194 {
195 struct jffs2_inode *node = NULL;
196
197 if (sb->s_root == NULL) {
198 return NULL;
199 }
200
201 // Check for this inode in the cache
202 Jffs2NodeLock();
203 (void)Jffs2HashGet(&sb->s_node_hash_lock, &sb->s_node_hash[0], sb, ino, &node);
204 Jffs2NodeUnlock();
205 return node;
206 }
207
new_inode(struct super_block * sb)208 struct jffs2_inode *new_inode(struct super_block *sb)
209 {
210 struct jffs2_inode *inode = NULL;
211
212 inode = zalloc(sizeof (struct jffs2_inode));
213 if (inode == NULL)
214 return 0;
215
216 D2(PRINTK("malloc new_inode %x ####################################\n",
217 inode));
218
219 inode->i_sb = sb;
220 inode->i_ino = 1;
221 inode->i_nlink = 1; // Let JFFS2 manage the link count
222 inode->i_size = 0;
223 LOS_ListInit((&(inode->i_hashlist)));
224
225 return inode;
226 }
227
jffs2_iget(struct super_block * sb,uint32_t ino)228 struct jffs2_inode *jffs2_iget(struct super_block *sb, uint32_t ino)
229 {
230 struct jffs2_inode_info *f;
231 struct jffs2_sb_info *c;
232 struct jffs2_raw_inode latest_node;
233 struct jffs2_inode *inode;
234 int ret;
235
236 Jffs2NodeLock();
237 inode = ilookup(sb, ino);
238 if (inode) {
239 Jffs2NodeUnlock();
240 return inode;
241 }
242 inode = new_inode(sb);
243 if (inode == NULL) {
244 Jffs2NodeUnlock();
245 return (struct jffs2_inode *)-ENOMEM;
246 }
247
248 inode->i_ino = ino;
249 f = JFFS2_INODE_INFO(inode);
250 c = JFFS2_SB_INFO(inode->i_sb);
251
252 (void)mutex_init(&f->sem);
253 (void)mutex_lock(&f->sem);
254
255 ret = jffs2_do_read_inode(c, f, inode->i_ino, &latest_node);
256 if (ret) {
257 (void)mutex_unlock(&f->sem);
258 inode->i_nlink = 0;
259 free(inode);
260 Jffs2NodeUnlock();
261 return (struct jffs2_inode *)ret;
262 }
263
264 inode->i_mode = jemode_to_cpu(latest_node.mode);
265 inode->i_uid = je16_to_cpu(latest_node.uid);
266 inode->i_gid = je16_to_cpu(latest_node.gid);
267 inode->i_size = je32_to_cpu(latest_node.isize);
268 inode->i_atime = je32_to_cpu(latest_node.atime);
269 inode->i_mtime = je32_to_cpu(latest_node.mtime);
270 inode->i_ctime = je32_to_cpu(latest_node.ctime);
271 inode->i_nlink = f->inocache->pino_nlink;
272
273 (void)mutex_unlock(&f->sem);
274
275 (void)Jffs2HashInsert(&sb->s_node_hash_lock, &sb->s_node_hash[0], inode, ino);
276
277 jffs2_dbg(1, "jffs2_read_inode() returning\n");
278 Jffs2NodeUnlock();
279
280 return inode;
281 }
282
283
284 // -------------------------------------------------------------------------
285 // Decrement the reference count on an inode. If this makes the ref count
286 // zero, then this inode can be freed.
287
jffs2_iput(struct jffs2_inode * i)288 int jffs2_iput(struct jffs2_inode *i)
289 {
290 // Called in jffs2_find
291 // (and jffs2_open and jffs2_ops_mkdir?)
292 // super.c jffs2_fill_super,
293 // and gc.c jffs2_garbage_collect_pass
294 struct jffs2_inode_info *f = NULL;
295
296 Jffs2NodeLock();
297 if (!i || i->i_nlink) {
298 // and let it fault...
299 Jffs2NodeUnlock();
300 return -EBUSY;
301 }
302
303 jffs2_clear_inode(i);
304 f = JFFS2_INODE_INFO(i);
305 (void)mutex_destroy(&(f->sem));
306 (void)Jffs2HashRemove(&i->i_sb->s_node_hash_lock, i);
307 (void)memset_s(i, sizeof(*i), 0x5a, sizeof(*i));
308 free(i);
309 Jffs2NodeUnlock();
310
311 return 0;
312 }
313
314
315 /* jffs2_new_inode: allocate a new inode and inocache, add it to the hash,
316 fill in the raw_inode while you're at it. */
jffs2_new_inode(struct jffs2_inode * dir_i,int mode,struct jffs2_raw_inode * ri)317 struct jffs2_inode *jffs2_new_inode (struct jffs2_inode *dir_i, int mode, struct jffs2_raw_inode *ri)
318 {
319 struct jffs2_inode *inode;
320 struct super_block *sb = dir_i->i_sb;
321 struct jffs2_sb_info *c;
322 struct jffs2_inode_info *f;
323 int ret;
324
325 c = JFFS2_SB_INFO(sb);
326
327 Jffs2NodeLock();
328 inode = new_inode(sb);
329
330 if (!inode)
331 return (struct jffs2_inode *)-ENOMEM;
332
333 f = JFFS2_INODE_INFO(inode);
334 (void)mutex_init(&f->sem);
335 (void)mutex_lock(&f->sem);;
336
337 memset(ri, 0, sizeof(*ri));
338 /* Set OS-specific defaults for new inodes */
339 ri->uid = cpu_to_je16(OsCurrUserGet()->effUserID);
340 ri->gid = cpu_to_je16(OsCurrUserGet()->effGid);
341
342 ret = jffs2_do_new_inode (c, f, mode, ri);
343 if (ret) {
344 mutex_unlock(&(f->sem));
345 jffs2_clear_inode(inode);
346 (void)mutex_destroy(&(f->sem));
347 (void)memset_s(inode, sizeof(*inode), 0x6a, sizeof(*inode));
348 free(inode);
349 Jffs2NodeUnlock();
350 return (struct jffs2_inode *)ret;
351
352 }
353 inode->i_nlink = 1;
354 inode->i_ino = je32_to_cpu(ri->ino);
355 inode->i_mode = jemode_to_cpu(ri->mode);
356 inode->i_gid = je16_to_cpu(ri->gid);
357 inode->i_uid = je16_to_cpu(ri->uid);
358 inode->i_atime = inode->i_ctime = inode->i_mtime = Jffs2CurSec();
359 ri->atime = ri->mtime = ri->ctime = cpu_to_je32(inode->i_mtime);
360
361 inode->i_size = 0;
362
363 (void)Jffs2HashInsert(&sb->s_node_hash_lock, &sb->s_node_hash[0], inode, inode->i_ino);
364 Jffs2NodeUnlock();
365
366 return inode;
367 }
368
calculate_inocache_hashsize(uint32_t flash_size)369 int calculate_inocache_hashsize(uint32_t flash_size)
370 {
371 /*
372 * Pick a inocache hash size based on the size of the medium.
373 * Count how many megabytes we're dealing with, apply a hashsize twice
374 * that size, but rounding down to the usual big powers of 2. And keep
375 * to sensible bounds.
376 */
377
378 int size_mb = flash_size / 1024 / 1024;
379 int hashsize = (size_mb * 2) & ~0x3f;
380
381 if (hashsize < INOCACHE_HASHSIZE_MIN)
382 return INOCACHE_HASHSIZE_MIN;
383 if (hashsize > INOCACHE_HASHSIZE_MAX)
384 return INOCACHE_HASHSIZE_MAX;
385
386 return hashsize;
387 }
388
jffs2_gc_release_inode(struct jffs2_sb_info * c,struct jffs2_inode_info * f)389 void jffs2_gc_release_inode(struct jffs2_sb_info *c,
390 struct jffs2_inode_info *f)
391 {
392 struct jffs2_inode *node = OFNI_EDONI_2SFFJ(f);
393 jffs2_iput(node);
394 }
395
jffs2_gc_fetch_inode(struct jffs2_sb_info * c,int inum,int unlinked)396 struct jffs2_inode_info *jffs2_gc_fetch_inode(struct jffs2_sb_info *c,
397 int inum, int unlinked)
398 {
399 struct jffs2_inode *inode;
400 struct jffs2_inode_cache *ic;
401
402 if (unlinked) {
403 /* The inode has zero nlink but its nodes weren't yet marked
404 obsolete. This has to be because we're still waiting for
405 the final (close() and) iput() to happen.
406
407 There's a possibility that the final iput() could have
408 happened while we were contemplating. In order to ensure
409 that we don't cause a new read_inode() (which would fail)
410 for the inode in question, we use ilookup() in this case
411 instead of iget().
412
413 The nlink can't _become_ zero at this point because we're
414 holding the alloc_sem, and jffs2_do_unlink() would also
415 need that while decrementing nlink on any inode.
416 */
417 inode = ilookup(OFNI_BS_2SFFJ(c), inum);
418 if (!inode) {
419 jffs2_dbg(1, "ilookup() failed for ino #%u; inode is probably deleted.\n",
420 inum);
421
422 spin_lock(&c->inocache_lock);
423 ic = jffs2_get_ino_cache(c, inum);
424 if (!ic) {
425 jffs2_dbg(1, "Inode cache for ino #%u is gone\n",
426 inum);
427 spin_unlock(&c->inocache_lock);
428 return NULL;
429 }
430 if (ic->state != INO_STATE_CHECKEDABSENT) {
431 /* Wait for progress. Don't just loop */
432 jffs2_dbg(1, "Waiting for ino #%u in state %d\n",
433 ic->ino, ic->state);
434 sleep_on_spinunlock(&c->inocache_wq, &c->inocache_lock);
435 } else {
436 spin_unlock(&c->inocache_lock);
437 }
438
439 return NULL;
440 }
441 } else {
442 /* Inode has links to it still; they're not going away because
443 jffs2_do_unlink() would need the alloc_sem and we have it.
444 Just iget() it, and if read_inode() is necessary that's OK.
445 */
446 inode = jffs2_iget(OFNI_BS_2SFFJ(c), inum);
447 if (inode <= 0)
448 return (struct jffs2_inode_info *)inode;
449 }
450
451 return JFFS2_INODE_INFO(inode);
452 }
453