Some Eclipse Foundation services are deprecated, or will be soon. Please ensure you've read this important communication.
Bug 332179 - Last-Modified date is bogus if File.lastModified returns a negative value.
Summary: Last-Modified date is bogus if File.lastModified returns a negative value.
Status: RESOLVED FIXED
Alias: None
Product: Jetty
Classification: RT
Component: server (show other bugs)
Version: unspecified   Edit
Hardware: PC Linux
: P3 major (vote)
Target Milestone: 7.1.x   Edit
Assignee: Greg Wilkins CLA
QA Contact:
URL:
Whiteboard:
Keywords:
Depends on:
Blocks:
 
Reported: 2010-12-08 19:36 EST by Amin Ahmad CLA
Modified: 2010-12-13 14:19 EST (History)
2 users (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Amin Ahmad CLA 2010-12-08 19:36:33 EST
Build Identifier: Build id: M20100211-1343

A file's last modified date is Fri Jun 29 17:31:44 PDT 1956. Jetty ends up setting the Last-Modified header to "Sat, 30 Jun 1956 .-:.(:/* GMT". Here's the reason why:

1) When Jetty serves a file, it copies the files last modified date into the Last-Modified header.
2) Jetty uses java.io.File.lastModified() to retrieve the last modified date.
3) This value is negative in the sample case (specifically, -426209296000), and Jetty chokes, in the following manner:
  a) Response.setDateHeader passes the negative date into HttpFields.putDateField, which delegates formatting to the formatDate method.
  b) The local variables hours, minutes, and seconds all evaluate to negative values (algorithm is not designed to handle negative input), and when these values are passed to the methods StringUtil.append2digits, which is defined thusly:

267     public static void append2digits(StringBuffer buf,int i)
268     {
269         if (i<100)
270         {
271             buf.append((char)(i/10+'0'));
272             buf.append((char)(i%10+'0'));
273         }
274     }

the cast to char ends up producing characters below '0'. Note that the guard on line 269 really isn't sufficient: i must also be non-negative.

Reviewing the Javadoc for File.lastModified doesn't appear to rule out returning negative values (unless you read into the word "since"), so I would classify this as a Jetty bug.



Reproducible: Always

Steps to Reproduce:
1. Create a file with a last modified date before 1970.
2. Access the file via Jetty HTTP.
3. Examine the Last-Modified header. It will be invalid.
Comment 1 Greg Wilkins CLA 2010-12-13 05:32:26 EST
ooops
Comment 2 Greg Wilkins CLA 2010-12-13 05:43:01 EST
Ha! - we are not the only ones.... trying to create a test harness for this, maven gives me

[ERROR] Failed to execute goal org.apache.maven.plugins:maven-war-plugin:2.1-beta-1:war (default-war) on project test-jetty-webapp: Execution default-war of goal org.apache.maven.plugins:maven-war-plugin:2.1-beta-1:war failed: Negative time -> [Help 1]

on files

-rw-rw-r-- 1 gregw 1001 57 1900-01-01 12:00 src/main/webapp/1900.txt
-rw-rw-r-- 1 gregw 1001 73 1969-12-30 23:59 src/main/webapp/1969.txt
Comment 3 Greg Wilkins CLA 2010-12-13 06:03:42 EST
fixed r2606
Comment 4 Amin Ahmad CLA 2010-12-13 14:19:45 EST
Interesting note about Maven's inability to handle "negative" times. Thanks for looking into this so promptly.

-amin