Sometimes null
is returned intentionally to account for zero available instancesSome APIs intentionally return a null reference to indicate that instances are unavailable. This practice can lead to denial-of-service vulnerabilities when the client code does not fails to explicitly handle the null return value case.
Non-Compliant Code Example
. A null value is an example of an in-band error indicator, which is discouraged by ERR52-J. Avoid in-band error indicators. For methods that return a set of values using an array or collection, returning an empty array or collection is an excellent alternative to returning a null value, as most callers are better equipped to handle and empty set than a null value.
Noncompliant Code Example
This noncompliant code example returns a null ArrayList
when the size of the ArrayList
is 0. The class Inventory
contains a getStock()
method that constructs a list of items that have 0 inventory and returns the list of items to the caller. The erroneous behavior is caused due to the server returning null
while the client forgets to add in a check for such a values. This non-compliant example shows how the check item != null
is missing from the condition in class Client
.
Code Block | ||
---|---|---|
| ||
class Inventory { private static int[] itemfinal Hashtable<String, Integer> items; public Inventory() { itemitems = new int[20] Hashtable<String, Integer>(); } public static int[] getStock() { List<String> getStock() { List<String> stock = new ArrayList<String>(); Enumeration itemKeys = items.keys(); while (itemKeys.hasMoreElements()) { Object value = itemKeys.nextElement(); if((items.get(value)) == 0) { stock.add((String)value); } } if(itemitems.lengthsize() == 0) { return null; } else { return itemstock; } } } public class Client { public static void main(String[] args) { Inventory ivinv = new Inventory(); List<String> items int[] item = Inventoryinv.getStock(); if (item[1] == 1 ) { System.out.println("Almost out of stock!" + itemitems.size()); } } } |
Compliant Solution
}
|
When the size of this list is 0, a null value is returned with the assumption that the client will install the necessary checks. In this code example, the client lacks any null value check, causing a NullPointerException
at runtime.
Compliant Solution
Instead of returning a null value, this compliant solution simply returns the List
, even when it is empty.
Code Block | ||
---|---|---|
| ||
class Inventory { private final static int[] itemHashtable<String, Integer> items; public Inventory() { itemitems = new int[20]Hashtable<String, Integer>(); } public static int[] getStock() { if(item.lengthList<String> getStock() { List<String> stock = new ArrayList<String>(); Integer noOfItems; // Number of items left in the inventory Enumeration itemKeys = items.keys(); while (itemKeys.hasMoreElements()) { Object value = itemKeys.nextElement(); if((noOfItems = items.get(value)) == 0) { //handle error stock.add((String)value); else} } return itemstock; //even ifReturn itlist is(possibly zero-length, return as is) } } public class Client { public static void main(String[] args) { Inventory inv = new Inventory iv = new Inventory(); List<String> items = inv.getStock(); System.out.println(items.size()); } } |
The client can handle this situation effectively without being interrupted by runtime exceptions. When returning arrays rather than collections, ensure that the client avoids attempts to access individual elements of a zero-length array. This prevents an ArrayOutOfBoundsException
from being thrown.
Compliant Solution
This compliant solution returns an explicit empty list, which is an equivalent, permissible technique.
Code Block | ||
---|---|---|
| ||
public List<String> getStock() { List<String> stock = new ArrayList<String>(); Integer noOfItems; // Number of items left in the inventory Enumeration itemKeys = items.keys(); while (itemKeys.hasMoreElements()) { int[]Object itemvalue = InventoryitemKeys.getStocknextElement(); if((noOfItems = (item[1]items.get(value)) == 1 0) { stock.add((String)value); } System.out.println("Almost out of stock!" + item); } } } } if(l.isEmpty()) { return Collections.EMPTY_LIST; // Always zero-length } else { return stock; // Return list } } // Class Client ... |
Applicability
Returning a null value rather than a zero-length array or collection may lead to denial-of-service vulnerabilities when the client code fails to handle null return values properly.
Automatic detection is straightforward; fixing the problem typically requires programmer intervention.
Automated Detection
Bibliography
[Bloch 2008] | Item 43, "Return Empty Arrays or Collections, Not Nulls" |
...