blob: 6720a47c0c0113dce36c22493a412211a6b2cea5 [file] [log] [blame]
Darin Petkov698d0412010-10-13 10:59:44 -07001// Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
adlr@google.com3defe6a2009-12-04 20:57:17 +00002// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#ifndef CHROMEOS_PLATFORM_UPDATE_ENGINE_FILESYSTEM_COPIER_ACTION_H__
6#define CHROMEOS_PLATFORM_UPDATE_ENGINE_FILESYSTEM_COPIER_ACTION_H__
7
8#include <sys/stat.h>
9#include <sys/types.h>
Darin Petkov698d0412010-10-13 10:59:44 -070010
adlr@google.com3defe6a2009-12-04 20:57:17 +000011#include <string>
Andrew de los Reyesc7020782010-04-28 10:46:04 -070012#include <vector>
Darin Petkov698d0412010-10-13 10:59:44 -070013
Andrew de los Reyesc7020782010-04-28 10:46:04 -070014#include <gio/gio.h>
adlr@google.com3defe6a2009-12-04 20:57:17 +000015#include <glib.h>
Darin Petkov698d0412010-10-13 10:59:44 -070016#include <gtest/gtest_prod.h> // for FRIEND_TEST
17
adlr@google.com3defe6a2009-12-04 20:57:17 +000018#include "update_engine/action.h"
19#include "update_engine/install_plan.h"
Darin Petkov698d0412010-10-13 10:59:44 -070020#include "update_engine/omaha_hash_calculator.h"
adlr@google.com3defe6a2009-12-04 20:57:17 +000021
22// This action will only do real work if it's a delta update. It will
Andrew de los Reyesc7020782010-04-28 10:46:04 -070023// copy the root partition to install partition, and then terminate.
adlr@google.com3defe6a2009-12-04 20:57:17 +000024
25namespace chromeos_update_engine {
26
27class FilesystemCopierAction;
28
29template<>
30class ActionTraits<FilesystemCopierAction> {
31 public:
32 // Takes the install plan as input
33 typedef InstallPlan InputObjectType;
34 // Passes the install plan as output
35 typedef InstallPlan OutputObjectType;
36};
37
38class FilesystemCopierAction : public Action<FilesystemCopierAction> {
39 public:
Andrew de los Reyesf9185172010-05-03 11:07:05 -070040 explicit FilesystemCopierAction(bool copying_kernel_install_path)
41 : copying_kernel_install_path_(copying_kernel_install_path),
42 src_stream_(NULL),
Andrew de los Reyesc7020782010-04-28 10:46:04 -070043 dst_stream_(NULL),
44 canceller_(NULL),
45 read_in_flight_(false),
Darin Petkov698d0412010-10-13 10:59:44 -070046 buffer_valid_size_(0),
47 filesystem_size_(kint64max) {}
adlr@google.com3defe6a2009-12-04 20:57:17 +000048 typedef ActionTraits<FilesystemCopierAction>::InputObjectType
49 InputObjectType;
50 typedef ActionTraits<FilesystemCopierAction>::OutputObjectType
51 OutputObjectType;
52 void PerformAction();
53 void TerminateProcessing();
54
55 // Used for testing, so we can copy from somewhere other than root
Andrew de los Reyes4fe15d02009-12-10 19:01:36 -080056 void set_copy_source(const std::string& path) {
adlr@google.com3defe6a2009-12-04 20:57:17 +000057 copy_source_ = path;
58 }
adlr@google.com3defe6a2009-12-04 20:57:17 +000059
60 // Debugging/logging
61 static std::string StaticType() { return "FilesystemCopierAction"; }
62 std::string Type() const { return StaticType(); }
63
64 private:
Darin Petkov698d0412010-10-13 10:59:44 -070065 friend class FilesystemCopierActionTest;
66 FRIEND_TEST(FilesystemCopierActionTest, RunAsRootDetermineFilesystemSizeTest);
67
Andrew de los Reyesc7020782010-04-28 10:46:04 -070068 // Callback from glib when the copy operation is done.
69 void AsyncReadyCallback(GObject *source_object, GAsyncResult *res);
70 static void StaticAsyncReadyCallback(GObject *source_object,
71 GAsyncResult *res,
72 gpointer user_data) {
73 reinterpret_cast<FilesystemCopierAction*>(user_data)->AsyncReadyCallback(
74 source_object, res);
adlr@google.com3defe6a2009-12-04 20:57:17 +000075 }
Darin Petkov698d0412010-10-13 10:59:44 -070076
Andrew de los Reyesc7020782010-04-28 10:46:04 -070077 // Cleans up all the variables we use for async operations and tells
78 // the ActionProcessor we're done w/ success as passed in.
79 // was_cancelled should be true if TerminateProcessing() was called.
80 void Cleanup(bool success, bool was_cancelled);
Darin Petkov698d0412010-10-13 10:59:44 -070081
82 // Determine, if possible, the source file system size to avoid copying the
83 // whole partition. Currently this supports only the root file system assuming
84 // it's ext3-compatible.
85 void DetermineFilesystemSize(int fd);
86
87 // Returns the number of bytes to read based on the size of the buffer and the
88 // filesystem size.
89 int64_t GetBytesToRead();
90
Andrew de los Reyesf9185172010-05-03 11:07:05 -070091 // If true, this action is copying to the kernel_install_path from
92 // the install plan, otherwise it's copying just to the install_path.
93 const bool copying_kernel_install_path_;
Darin Petkov698d0412010-10-13 10:59:44 -070094
Andrew de los Reyesc7020782010-04-28 10:46:04 -070095 // The path to copy from. If empty (the default), the source is from the
96 // passed in InstallPlan.
Andrew de los Reyes4fe15d02009-12-10 19:01:36 -080097 std::string copy_source_;
adlr@google.com3defe6a2009-12-04 20:57:17 +000098
Andrew de los Reyesc7020782010-04-28 10:46:04 -070099 // If non-NULL, these are GUnixInputStream objects for the opened
100 // source/destination partitions.
101 GInputStream* src_stream_;
102 GOutputStream* dst_stream_;
Darin Petkov698d0412010-10-13 10:59:44 -0700103
Andrew de los Reyesc7020782010-04-28 10:46:04 -0700104 // If non-NULL, the cancellable object for the in-flight async call.
105 GCancellable* canceller_;
Darin Petkov698d0412010-10-13 10:59:44 -0700106
Andrew de los Reyesc7020782010-04-28 10:46:04 -0700107 // True if we're waiting on a read to complete; false if we're
108 // waiting on a write.
109 bool read_in_flight_;
Darin Petkov698d0412010-10-13 10:59:44 -0700110
Andrew de los Reyesc7020782010-04-28 10:46:04 -0700111 // The buffer for storing data we read/write.
112 std::vector<char> buffer_;
113
114 // Number of valid elements in buffer_.
115 std::vector<char>::size_type buffer_valid_size_;
116
adlr@google.com3defe6a2009-12-04 20:57:17 +0000117 // The install plan we're passed in via the input pipe.
118 InstallPlan install_plan_;
Darin Petkov698d0412010-10-13 10:59:44 -0700119
120 // Calculates the hash of the copied data.
121 OmahaHashCalculator hasher_;
122
123 // Copies and hashes this many bytes from the head of the input stream. This
124 // field is initialized when the action is started and decremented as more
125 // bytes get copied.
126 int64_t filesystem_size_;
127
adlr@google.com3defe6a2009-12-04 20:57:17 +0000128 DISALLOW_COPY_AND_ASSIGN(FilesystemCopierAction);
129};
130
131} // namespace chromeos_update_engine
132
133#endif // CHROMEOS_PLATFORM_UPDATE_ENGINE_FILESYSTEM_COPIER_ACTION_H__