You are viewing an old version of this page. View the current version.

Compare with Current View Page History

« Previous Version 8 Next »

Temporary files are frequently created in shared directories and have several uses:

  • Share data between processes
  • Store auxiliary program data (to save memory)
  • Construct and/or load classes, JAR files and native libraries dynamically

An adversary can cause a program to incorrectly interpret the temporary data if temporary files are not created safely or beget a denial of service if the file is not deleted after use. For instance, if the name of the file can be predetermined, an attacker can use the time-of-check-to-time-of-use (TOCTOU) condition to create a file with the same name leading to either a failure in creating the temporary file from within program code or the program reading a crafted file determined by the attacker.

A recently identified bug manifests in JRE and JDK version 6.0 and prior, wherein an attacker can predict the names of the temporary files and thus write malicious JAR files via unknown vectors [[CVE 08]]. Denial of Service attacks are also possible if unclaimed temporary resources cause rapid disk space exhaustion [Secunia Advisory 20132].

Noncompliant Code Example

This noncompliant code example suffers from several pitfalls. First, the name of the temporary file is hardcoded which implies that it is predictable. Second, even though there is a built-in check to detect whether a file still exists after creation, a TOCTOU condition exists that can prevent a program from making use of the temporary file. Third, the output stream has not been closed after use which violates FIO32-J. Ensure all resources are properly closed when they are no longer needed. Finally, no measure to delete the file after use has been considered.

class TempFile{
  public static void main(String[] args) throws IOException{
    File f=new File("tempnam.tmp");
    FileOutputStream fop=new FileOutputStream(f);
    String str = "Data";
    
    if(f.exists()){
      fop.write(str.getBytes());
    } else { System.out.println("This file does not exist"); }
  }      
}

Noncompliant Code Example

This noncompliant example improves by demonstrating how the method File.createTempFile can be used to generate a unique temporary filename based on two parameters, a prefix and an extension. Currently, this is the only method that is designed for producing unique file names but quite unfortunately, the names produced are not hard to predict. It is recommended that the prefix be generated using a good random number generator.

According to [[API 06]] Class File, method deleteOnExit documentation:

Deletion will be attempted only for normal termination of the virtual machine, as defined by the Java Language Specification. Once deletion has been requested, it is not possible to cancel the request. This method should therefore be used with care.
Note: this method should not be used for file-locking, as the resulting protocol cannot be made to work reliably.

This implies that the file would not be deleted if the JVM terminates unexpectedly. Another longstanding bug that remains unresolved violates the temporary file deletion contract provided by the deleteOnExit method. If a stream or a RandomAccessFile is left unclosed before calling deleteOnExit, the file would not be deleted on Win32 based systems [Bug ID: 4171239].

class TempFile{
  public static void main(String[] args) throws IOException{
    File f = File.createTempFile("tempnam",".tmp");
    FileOutputStream fop=new FileOutputStream(f);
    String str = "Data";
    try {
      fop.write(str.getBytes());
      fop.flush();        
    }finally {
      // Stream/file closing not performed first, file will not be deleted
      f.deleteOnExit(); // Delete the file when the JVM terminates
    }
  }       
}

Compliant Solution

<TODO> depending on bug fixes. As a workaround to the file/stream termination issue, always try to terminate the resource first. This should have been done using fop.close(); in the above noncompliant example. It is also recommended that File.io.delete be used to immediately delete the file to avoid improper JVM termination related issues. Moreover, although unreliable, System.gc() may be invoked to free up related resources. Sometimes, it is not possible to close the resources on which the delete operation has to be invoked [Bug ID: 4635827]. Currently, there is no way to handle this case.

Risk Assessment

Not following the best practices while creating, using and deleting temporary files can lead to denial of service vulnerabilities, misinterpretations and alterations in control flow.

Rule

Severity

Likelihood

Remediation Cost

Priority

Level

FIO37-J

medium

probable

high

P4

L3

Automated Detection

TODO

Related Vulnerabilities

Search for vulnerabilities resulting from the violation of this rule on the CERT website.

Other Languages

This rule appears in the C Secure Coding Standard as FIO43-C. Do not create temporary files in shared directories.

This rule appears in the C++ Secure Coding Standard as FIO43-CPP. Do not create temporary files in shared directories.

References

[[API 06]] Class File, methods createTempFile, delete, deleteOnExit
[[Darwin 04]] 11.5 Creating a Transient File
[[SDN 08]] Bug IDs: 4171239, 4405521, 4635827, 4631820
[[Secunia 08]] Secunia Advisory 20132
[[CVE 08]] CVE-2008-5354
[[MITRE 09]] CWE ID 459 "Incomplete Cleanup", CWE ID 377 "Insecure Temporary File"


MSC31-J. Never hardcode sensitive information      08. Input Output (FIO)      08. Input Output (FIO)

  • No labels