AU: propagate a deadline form the update check response to Chrome.

Currently, this is done through the file system.

BUG=3284
TEST=unit tests

Change-Id: I0e579ef6ccd7832ca22a248e71f2689c27159056

TBR=resubmitting due to git issues
diff --git a/omaha_request_action.cc b/omaha_request_action.cc
index cb9cd63..ecee25e 100644
--- a/omaha_request_action.cc
+++ b/omaha_request_action.cc
@@ -412,6 +412,7 @@
   output_object.prompt = XmlGetProperty(updatecheck_node, "Prompt") == "true";
   output_object.is_delta =
       XmlGetProperty(updatecheck_node, "IsDelta") == "true";
+  output_object.deadline = XmlGetProperty(updatecheck_node, "deadline");
   SetOutputObject(output_object);
 }
 
diff --git a/omaha_request_action.h b/omaha_request_action.h
index 1f72025..b65d3f8 100644
--- a/omaha_request_action.h
+++ b/omaha_request_action.h
@@ -46,6 +46,7 @@
   std::string codebase;
   std::string more_info_url;
   std::string hash;
+  std::string deadline;
   off_t size;
   bool needs_admin;
   bool prompt;
diff --git a/omaha_request_action_unittest.cc b/omaha_request_action_unittest.cc
index 8b15a86..f822357 100755
--- a/omaha_request_action_unittest.cc
+++ b/omaha_request_action_unittest.cc
@@ -62,7 +62,8 @@
                          const string& codebase,
                          const string& hash,
                          const string& needsadmin,
-                         const string& size) {
+                         const string& size,
+                         const string& deadline) {
   return string("<?xml version=\"1.0\" encoding=\"UTF-8\"?><gupdate "
                 "xmlns=\"http://www.google.com/update2/response\" "
                 "protocol=\"2.0\"><app "
@@ -72,7 +73,8 @@
       "IsDelta=\"true\" "
       "codebase=\"" + codebase + "\" hash=\"not-applicable\" "
       "sha256=\"" + hash + "\" needsadmin=\"" + needsadmin + "\" "
-      "size=\"" + size + "\" status=\"ok\"/></app></gupdate>";
+      "size=\"" + size + "\" deadline=\"" + deadline +
+      "\" status=\"ok\"/></app></gupdate>";
 }
 
 class OmahaRequestActionTestProcessorDelegate : public ActionProcessorDelegate {
@@ -232,7 +234,8 @@
                                         "http://code/base",  // dl url
                                         "HASH1234=",  // checksum
                                         "false",  // needs admin
-                                        "123"),  // size
+                                        "123",  // size
+                                        "20101020"),  // deadline
                       kActionCodeSuccess,
                       &response,
                       NULL));
@@ -245,6 +248,7 @@
   EXPECT_EQ(123, response.size);
   EXPECT_FALSE(response.needs_admin);
   EXPECT_TRUE(response.prompt);
+  EXPECT_EQ("20101020", response.deadline);
 }
 
 TEST(OmahaRequestActionTest, NoOutputPipeTest) {
@@ -355,6 +359,7 @@
   EXPECT_EQ(123, response.size);
   EXPECT_TRUE(response.needs_admin);
   EXPECT_FALSE(response.prompt);
+  EXPECT_TRUE(response.deadline.empty());
 }
 
 namespace {
@@ -448,13 +453,15 @@
                                         "testthe&amp;codebase",  // dl url
                                         "HASH1234=", // checksum
                                         "false",  // needs admin
-                                        "123"),  // size
+                                        "123",  // size
+                                        "&lt;20110101"),  // deadline
                       kActionCodeSuccess,
                       &response,
                       NULL));
 
   EXPECT_EQ(response.more_info_url, "testthe<url");
   EXPECT_EQ(response.codebase, "testthe&codebase");
+  EXPECT_EQ(response.deadline, "<20110101");
 }
 
 TEST(OmahaRequestActionTest, ParseIntTest) {
@@ -470,7 +477,8 @@
                                         "HASH1234=", // checksum
                                         "false",  // needs admin
                                         // overflows int32:
-                                        "123123123123123"),  // size
+                                        "123123123123123",  // size
+                                        "deadline"),
                       kActionCodeSuccess,
                       &response,
                       NULL));
diff --git a/omaha_response_handler_action.cc b/omaha_response_handler_action.cc
index 5159733..fdbd80a 100644
--- a/omaha_response_handler_action.cc
+++ b/omaha_response_handler_action.cc
@@ -16,6 +16,9 @@
 
 namespace chromeos_update_engine {
 
+const char OmahaResponseHandlerAction::kDeadlineFile[] =
+    "/tmp/update-check-response-deadline";
+
 void OmahaResponseHandlerAction::PerformAction() {
   CHECK(HasInputObject());
   ScopedActionCompleter completer(processor_, this);
@@ -53,6 +56,18 @@
   LOG(INFO) << "Using this install plan:";
   install_plan_.Dump();
 
+  // Send the deadline data (if any) to Chrome through a file. This is a pretty
+  // hacky solution but should be OK for now.
+  //
+  // TODO(petkov): Rearchitect this to avoid communication through a
+  // file. Ideallly, we would include this information in D-Bus's GetStatus
+  // method and UpdateStatus signal. A potential issue is that update_engine may
+  // be unresponsive during an update download.
+  utils::WriteFile(kDeadlineFile,
+                   response.deadline.data(),
+                   response.deadline.size());
+  chmod(kDeadlineFile, S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH);
+
   completer.set_code(kActionCodeSuccess);
 }
 
diff --git a/omaha_response_handler_action.h b/omaha_response_handler_action.h
index 2845df5..25c57e0 100644
--- a/omaha_response_handler_action.h
+++ b/omaha_response_handler_action.h
@@ -27,6 +27,8 @@
 
 class OmahaResponseHandlerAction : public Action<OmahaResponseHandlerAction> {
  public:
+  static const char kDeadlineFile[];
+
   OmahaResponseHandlerAction(PrefsInterface* prefs)
       : prefs_(prefs),
         got_no_update_response_(false) {}
diff --git a/omaha_response_handler_action_unittest.cc b/omaha_response_handler_action_unittest.cc
index 10be7d6..0db21be 100644
--- a/omaha_response_handler_action_unittest.cc
+++ b/omaha_response_handler_action_unittest.cc
@@ -87,6 +87,8 @@
 }
 
 TEST_F(OmahaResponseHandlerActionTest, SimpleTest) {
+  ScopedPathUnlinker deadline_unlinker(
+      OmahaResponseHandlerAction::kDeadlineFile);
   {
     OmahaResponse in;
     in.update_exists = true;
@@ -98,12 +100,23 @@
     in.needs_admin = true;
     in.prompt = false;
     in.is_delta = false;
+    in.deadline = "20101020";
     InstallPlan install_plan;
     EXPECT_TRUE(DoTest(in, "/dev/sda3", &install_plan));
     EXPECT_TRUE(install_plan.is_full_update);
     EXPECT_EQ(in.codebase, install_plan.download_url);
     EXPECT_EQ(in.hash, install_plan.download_hash);
     EXPECT_EQ("/dev/sda5", install_plan.install_path);
+    string deadline;
+    EXPECT_TRUE(utils::ReadFileToString(
+        OmahaResponseHandlerAction::kDeadlineFile,
+        &deadline));
+    EXPECT_EQ("20101020", deadline);
+    struct stat deadline_stat;
+    EXPECT_EQ(0, stat(OmahaResponseHandlerAction::kDeadlineFile,
+                      &deadline_stat));
+    EXPECT_EQ(S_IFREG | S_IRUSR | S_IWUSR | S_IRGRP | S_IROTH,
+              deadline_stat.st_mode);
   }
   {
     OmahaResponse in;
@@ -122,6 +135,10 @@
     EXPECT_EQ(in.codebase, install_plan.download_url);
     EXPECT_EQ(in.hash, install_plan.download_hash);
     EXPECT_EQ("/dev/sda3", install_plan.install_path);
+    string deadline;
+    EXPECT_TRUE(utils::ReadFileToString(
+        OmahaResponseHandlerAction::kDeadlineFile,
+        &deadline) && deadline.empty());
   }
   {
     OmahaResponse in;
@@ -134,12 +151,18 @@
     in.needs_admin = true;
     in.prompt = true;
     in.is_delta = false;
+    in.deadline = "some-deadline";
     InstallPlan install_plan;
     EXPECT_TRUE(DoTest(in, "/dev/sda3", &install_plan));
     EXPECT_TRUE(install_plan.is_full_update);
     EXPECT_EQ(in.codebase, install_plan.download_url);
     EXPECT_EQ(in.hash, install_plan.download_hash);
     EXPECT_EQ("/dev/sda5", install_plan.install_path);
+    string deadline;
+    EXPECT_TRUE(utils::ReadFileToString(
+        OmahaResponseHandlerAction::kDeadlineFile,
+        &deadline));
+    EXPECT_EQ("some-deadline", deadline);
   }
 }