linux
Use of variable before initialization when !SECURITY
reiserfs_security_init() assumes that `length' will be initialized by security_old_inode_init_security(), if this succeeds. But the mockup implementation of security_old_inode_init_security() for !SECURITY succeeds and lefts `length' uninitialized. Note that `length' is a local variable hence, prior to initialization, it can hold any value.
Bug fixed by commit 30e053248da
| Type | UninitializedVariable |
| Config | "REISERFS_FS_SECURITY && !SECURITY" (2nd degree) |
| Fix-in | code |
| Location | fs/reiserfs/ |
__attribute__ ((noinline)) int nondet() { return 42; }
#ifdef CONFIG_SECURITY
int security_old_inode_init_security(int *len)
{
if (nondet()) {
*len = 0;
return 0;
}
else
return -1;
}
#else
int security_old_inode_init_security(int *len)
{
return 0;
}
#endif
int reiserfs_security_init(int *length)
{
int error;
error = security_old_inode_init_security(length); // (4) length is never written if !SECURITY
if (error) { // (5) guaranteed false if !SECURITY
*length = 0;
return error;
}
int x = *length; // (6) ERROR
return 0;
}
int reiserfs_create()
{
int retval;
int length; // (2)
retval = reiserfs_security_init(&length); // (3) length not initialized
if (retval < 0)
{
return retval;
}
return 0;
}
int main(void)
{
reiserfs_create(); // (1)
return 0;
}
diff --git a/simple/30e0532.c b/simple/30e0532.c
--- a/simple/30e0532.c
+++ b/simple/30e0532.c
@@ -1,3 +1,5 @@
+
+#define EOPNOTSUPP 95 /* Operation not supported on transport endpoint */
__attribute__ ((noinline)) int nondet() { return 42; }
@@ -14,7 +16,7 @@
#else
int security_old_inode_init_security(int *len)
{
- return 0;
+ return -EOPNOTSUPP;
}
#endif
#include <stdlib.h>
int main(int argc, char** argv) {
// reiserfs_create();
int retval;
int length;
int error;
// error = security_old_inode_init_security(length);
#ifdef CONFIG_SECURITY
if (rand() % 2) {
length = 0;
error = 0;
}
else
error = -1;
#else
error = 0;
#endif
if (error) {
length = 0;
retval = error;
}
if (length) { // ERROR
// do something
}
if (retval < 0) {
return retval;
}
return 0;
}
. call fs/reiserfs/namei.c:575:reiserfs_create() . 586: struct reiserfs_security_handle security; . 596: retval = reiserfs_security_init(dir, inode, &dentry->d_name, &security); .. call fs/reiserfs/xattr_security.c:56:reiserfs_security_init() .. 69: error = security_old_inode_init_security(inode, dir, qstr, &sec->name, &sec->value, &sec->length); .. 79: } .. ERROR 81: if (sec->length && reiserfs_xattrs_initialized(inode->i_sb))