Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

UBIFS: endian handling fixes and annotations

Noticed by sparse:
fs/ubifs/file.c:75:2: warning: restricted __le64 degrades to integer
fs/ubifs/file.c:629:4: warning: restricted __le64 degrades to integer
fs/ubifs/dir.c:431:3: warning: restricted __le64 degrades to integer

This should be checked to ensure the ubifs_assert is working as
intended, I've done the suggested annotation in this patch.

fs/ubifs/sb.c:298:6: warning: incorrect type in assignment (different base types)
fs/ubifs/sb.c:298:6: expected int [signed] [assigned] tmp
fs/ubifs/sb.c:298:6: got restricted __le64 [usertype] <noident>
fs/ubifs/sb.c:299:19: warning: incorrect type in assignment (different base types)
fs/ubifs/sb.c:299:19: expected restricted __le64 [usertype] atime_sec
fs/ubifs/sb.c:299:19: got int [signed] [assigned] tmp
fs/ubifs/sb.c:300:19: warning: incorrect type in assignment (different base types)
fs/ubifs/sb.c:300:19: expected restricted __le64 [usertype] ctime_sec
fs/ubifs/sb.c:300:19: got int [signed] [assigned] tmp
fs/ubifs/sb.c:301:19: warning: incorrect type in assignment (different base types)
fs/ubifs/sb.c:301:19: expected restricted __le64 [usertype] mtime_sec
fs/ubifs/sb.c:301:19: got int [signed] [assigned] tmp

This looks like a bugfix as your tmp was a u32 so there was truncation in
the atime, mtime, ctime value, probably not intentional, add a tmp_le64
and use it here.

fs/ubifs/key.h:348:9: warning: cast to restricted __le32
fs/ubifs/key.h:348:9: warning: cast to restricted __le32
fs/ubifs/key.h:419:9: warning: cast to restricted __le32

Read from the annotated union member instead.

fs/ubifs/recovery.c:175:13: warning: incorrect type in assignment (different base types)
fs/ubifs/recovery.c:175:13: expected unsigned int [unsigned] [usertype] save_flags
fs/ubifs/recovery.c:175:13: got restricted __le32 [usertype] flags
fs/ubifs/recovery.c:186:13: warning: incorrect type in assignment (different base types)
fs/ubifs/recovery.c:186:13: expected restricted __le32 [usertype] flags
fs/ubifs/recovery.c:186:13: got unsigned int [unsigned] [usertype] save_flags

Do byteshifting at compile time of the flag value. Annotate the saved_flags
as le32.

fs/ubifs/debug.c:368:10: warning: cast to restricted __le32
fs/ubifs/debug.c:368:10: warning: cast from restricted __le64

Should be checked if the truncation was intentional, I've changed the
printk to print the full width.

Signed-off-by: Harvey Harrison <harvey.harrison@gmail.com>
Signed-off-by: Artem Bityutskiy <Artem.Bityutskiy@nokia.com>

authored by

Harvey Harrison and committed by
Artem Bityutskiy
0ecb9529 069782a1

+15 -13
+2 -2
fs/ubifs/debug.c
··· 364 364 le32_to_cpu(mst->ihead_lnum)); 365 365 printk(KERN_DEBUG "\tihead_offs %u\n", 366 366 le32_to_cpu(mst->ihead_offs)); 367 - printk(KERN_DEBUG "\tindex_size %u\n", 368 - le32_to_cpu(mst->index_size)); 367 + printk(KERN_DEBUG "\tindex_size %llu\n", 368 + (unsigned long long)le64_to_cpu(mst->index_size)); 369 369 printk(KERN_DEBUG "\tlpt_lnum %u\n", 370 370 le32_to_cpu(mst->lpt_lnum)); 371 371 printk(KERN_DEBUG "\tlpt_offs %u\n",
+2 -1
fs/ubifs/dir.c
··· 428 428 dbg_gen("feed '%s', ino %llu, new f_pos %#x", 429 429 dent->name, (unsigned long long)le64_to_cpu(dent->inum), 430 430 key_hash_flash(c, &dent->key)); 431 - ubifs_assert(dent->ch.sqnum > ubifs_inode(dir)->creat_sqnum); 431 + ubifs_assert(le64_to_cpu(dent->ch.sqnum) > 432 + ubifs_inode(dir)->creat_sqnum); 432 433 433 434 nm.len = le16_to_cpu(dent->nlen); 434 435 over = filldir(dirent, dent->name, nm.len, file->f_pos,
+2 -2
fs/ubifs/file.c
··· 72 72 return err; 73 73 } 74 74 75 - ubifs_assert(dn->ch.sqnum > ubifs_inode(inode)->creat_sqnum); 75 + ubifs_assert(le64_to_cpu(dn->ch.sqnum) > ubifs_inode(inode)->creat_sqnum); 76 76 77 77 len = le32_to_cpu(dn->size); 78 78 if (len <= 0 || len > UBIFS_BLOCK_SIZE) ··· 626 626 627 627 dn = bu->buf + (bu->zbranch[nn].offs - offs); 628 628 629 - ubifs_assert(dn->ch.sqnum > 629 + ubifs_assert(le64_to_cpu(dn->ch.sqnum) > 630 630 ubifs_inode(inode)->creat_sqnum); 631 631 632 632 len = le32_to_cpu(dn->size);
+2 -2
fs/ubifs/key.h
··· 345 345 { 346 346 const union ubifs_key *key = k; 347 347 348 - return le32_to_cpu(key->u32[1]) >> UBIFS_S_KEY_BLOCK_BITS; 348 + return le32_to_cpu(key->j32[1]) >> UBIFS_S_KEY_BLOCK_BITS; 349 349 } 350 350 351 351 /** ··· 416 416 { 417 417 const union ubifs_key *key = k; 418 418 419 - return le32_to_cpu(key->u32[1]) & UBIFS_S_KEY_BLOCK_MASK; 419 + return le32_to_cpu(key->j32[1]) & UBIFS_S_KEY_BLOCK_MASK; 420 420 } 421 421 422 422 /**
+2 -2
fs/ubifs/recovery.c
··· 168 168 struct ubifs_mst_node *mst) 169 169 { 170 170 int err = 0, lnum = UBIFS_MST_LNUM, sz = c->mst_node_alsz; 171 - uint32_t save_flags; 171 + __le32 save_flags; 172 172 173 173 dbg_rcvry("recovery"); 174 174 175 175 save_flags = mst->flags; 176 - mst->flags = cpu_to_le32(le32_to_cpu(mst->flags) | UBIFS_MST_RCVRY); 176 + mst->flags |= cpu_to_le32(UBIFS_MST_RCVRY); 177 177 178 178 ubifs_prepare_node(c, mst, UBIFS_MST_NODE_SZ, 1); 179 179 err = ubi_leb_change(c->ubi, lnum, mst, sz, UBI_SHORTTERM);
+5 -4
fs/ubifs/sb.c
··· 81 81 int lpt_lebs, lpt_first, orph_lebs, big_lpt, ino_waste, sup_flags = 0; 82 82 int min_leb_cnt = UBIFS_MIN_LEB_CNT; 83 83 uint64_t tmp64, main_bytes; 84 + __le64 tmp_le64; 84 85 85 86 /* Some functions called from here depend on the @c->key_len filed */ 86 87 c->key_len = UBIFS_SK_LEN; ··· 296 295 ino->ch.node_type = UBIFS_INO_NODE; 297 296 ino->creat_sqnum = cpu_to_le64(++c->max_sqnum); 298 297 ino->nlink = cpu_to_le32(2); 299 - tmp = cpu_to_le64(CURRENT_TIME_SEC.tv_sec); 300 - ino->atime_sec = tmp; 301 - ino->ctime_sec = tmp; 302 - ino->mtime_sec = tmp; 298 + tmp_le64 = cpu_to_le64(CURRENT_TIME_SEC.tv_sec); 299 + ino->atime_sec = tmp_le64; 300 + ino->ctime_sec = tmp_le64; 301 + ino->mtime_sec = tmp_le64; 303 302 ino->atime_nsec = 0; 304 303 ino->ctime_nsec = 0; 305 304 ino->mtime_nsec = 0;