I came across this rule in the CERT Secure Coding Standart for Java. Heap Pollution. I understand this can cause the programm throwing an exception at runtime, but i can't understand how this could cause a security issue like dos or something. Could someone explain an scenario where an attacker could exploit a heap pollution?
-
1Heap pollution seems to be related to errors in polymorphism, where a variable of one type is cast into its parent's class and then passed incorrectly on a function call. I would ask the compiler people how this could be exploited. Perhaps some of them would be on StackOverflow.– Brent KirkpatrickCommented Apr 16, 2016 at 16:21
2 Answers
I would take the similar example from the link you quoted. In the example i will get the userid (Integer) as argument and try to validate it against database.
class ListUtility {
private static void addToList(List list, Object obj) {
list.add(obj); // Unchecked warning
}
private static boolean validateUser(List list){
boolean isValidUser=false;
Statement stmt = conn.createStatement(); //conn is a jdbc Connection
String Query="SELECT userid FROM Customers WHERE userid='"+list.get(0)+"'"; //developer expects list.get(0) is a integer
ResultSet rs = stmt.executeQuery(Query);
if (rs.next()) {
System.out.println("Valid User");
isValidUser=true;
}
return isValidUser; //returns true for args[0]=something' or '1'='1
}
public static void main(String[] args) {
List<Integer> list = new ArrayList<Integer> ();
addToList(list, args[0]); //arg[0] is expected to be a valid userid of type Integer(say)
validateuser(list);
}
}
Now If i invoke the program with the argument something' or '1'='1
it will print "Valid User"
. This is a typical Sql Injection. But this has succeeded because of Heap Pollution where we added args[0]
to list
even though the type didn't match.
Heap pollution is possible in this case because the parameterized type information is discarded before execution.
The call to addToList(list,args[0])
succeeds in adding an String to list, although list is of type List<Integer>
. Also, the call to validateUser(List list)
takes the list of type List<Object>
instead of strict List<Integer>
.
This Java runtime does not throw a ClassCastException since the value list was not read with an invalid type in this example.
Because the list is never read strictly as List<Integer>
.
Very unlikely to happen, but possible:
If some programmers mishandle an unchecked warning throwing a ClassCastException
by casting some unsigned integer values into signed integer that could easily allow an attacker to bypass Integer.MIN_VALUE
and Integer.MAX_VALUE
into an integer overflow attack.