Skip to content

Commit

Permalink
latent_entropy: Fix wrong gcc code generation with 64 bit variables
Browse files Browse the repository at this point in the history
The stack frame size could grow too large when the plugin used long long
on 32-bit architectures when the given function had too many basic blocks.

The gcc warning was:

drivers/pci/hotplug/ibmphp_ebda.c: In function 'ibmphp_access_ebda':
drivers/pci/hotplug/ibmphp_ebda.c:409:1: warning: the frame size of 1108 bytes is larger than 1024 bytes [-Wframe-larger-than=]

This switches latent_entropy from u64 to unsigned long.

Thanks to PaX Team and Emese Revfy for the patch.

Signed-off-by: Kees Cook <keescook@chromium.org>
  • Loading branch information
Kees Cook committed Oct 31, 2016
1 parent da7389a commit 58bea41
Show file tree
Hide file tree
Showing 2 changed files with 10 additions and 11 deletions.
2 changes: 1 addition & 1 deletion mm/page_alloc.c
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ int _node_numa_mem_[MAX_NUMNODES];
#endif

#ifdef CONFIG_GCC_PLUGIN_LATENT_ENTROPY
volatile u64 latent_entropy __latent_entropy;
volatile unsigned long latent_entropy __latent_entropy;
EXPORT_SYMBOL(latent_entropy);
#endif

Expand Down
19 changes: 9 additions & 10 deletions scripts/gcc-plugins/latent_entropy_plugin.c
Original file line number Diff line number Diff line change
Expand Up @@ -340,7 +340,7 @@ static enum tree_code get_op(tree *rhs)
break;
}
if (rhs)
*rhs = build_int_cstu(unsigned_intDI_type_node, random_const);
*rhs = build_int_cstu(long_unsigned_type_node, random_const);
return op;
}

Expand Down Expand Up @@ -372,7 +372,7 @@ static void __perturb_latent_entropy(gimple_stmt_iterator *gsi,
enum tree_code op;

/* 1. create temporary copy of latent_entropy */
temp = create_var(unsigned_intDI_type_node, "tmp_latent_entropy");
temp = create_var(long_unsigned_type_node, "temp_latent_entropy");

/* 2. read... */
add_referenced_var(latent_entropy_decl);
Expand Down Expand Up @@ -459,13 +459,13 @@ static void init_local_entropy(basic_block bb, tree local_entropy)
gsi_insert_before(&gsi, call, GSI_NEW_STMT);
update_stmt(call);

udi_frame_addr = fold_convert(unsigned_intDI_type_node, frame_addr);
udi_frame_addr = fold_convert(long_unsigned_type_node, frame_addr);
assign = gimple_build_assign(local_entropy, udi_frame_addr);
gsi_insert_after(&gsi, assign, GSI_NEW_STMT);
update_stmt(assign);

/* 3. create temporary copy of latent_entropy */
tmp = create_var(unsigned_intDI_type_node, "tmp_latent_entropy");
tmp = create_var(long_unsigned_type_node, "temp_latent_entropy");

/* 4. read the global entropy variable into local entropy */
add_referenced_var(latent_entropy_decl);
Expand All @@ -480,7 +480,7 @@ static void init_local_entropy(basic_block bb, tree local_entropy)
update_stmt(assign);

rand_cst = get_random_const();
rand_const = build_int_cstu(unsigned_intDI_type_node, rand_cst);
rand_const = build_int_cstu(long_unsigned_type_node, rand_cst);
op = get_op(NULL);
assign = create_assign(op, local_entropy, local_entropy, rand_const);
gsi_insert_after(&gsi, assign, GSI_NEW_STMT);
Expand Down Expand Up @@ -529,7 +529,7 @@ static unsigned int latent_entropy_execute(void)
}

/* 1. create the local entropy variable */
local_entropy = create_var(unsigned_intDI_type_node, "local_entropy");
local_entropy = create_var(long_unsigned_type_node, "local_entropy");

/* 2. initialize the local entropy variable */
init_local_entropy(bb, local_entropy);
Expand Down Expand Up @@ -561,10 +561,9 @@ static void latent_entropy_start_unit(void *gcc_data __unused,
if (in_lto_p)
return;

/* extern volatile u64 latent_entropy */
gcc_assert(TYPE_PRECISION(long_long_unsigned_type_node) == 64);
quals = TYPE_QUALS(long_long_unsigned_type_node) | TYPE_QUAL_VOLATILE;
type = build_qualified_type(long_long_unsigned_type_node, quals);
/* extern volatile unsigned long latent_entropy */
quals = TYPE_QUALS(long_unsigned_type_node) | TYPE_QUAL_VOLATILE;
type = build_qualified_type(long_unsigned_type_node, quals);
id = get_identifier("latent_entropy");
latent_entropy_decl = build_decl(UNKNOWN_LOCATION, VAR_DECL, id, type);

Expand Down

0 comments on commit 58bea41

Please sign in to comment.