blob: dc10a6e5687e7e14d6bf5f0962b7dbe99e860380 [file] [log] [blame]
Mike Frysinger8155d082012-04-06 15:23:18 -04001// Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
Thieu Le5c7d9752010-12-15 16:09:28 -08002// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include <sys/types.h>
6#include <sys/stat.h>
7#include <fcntl.h>
8
9#include <string>
10#include <vector>
11
12#include <base/string_util.h>
Mike Frysinger8155d082012-04-06 15:23:18 -040013#include <base/stringprintf.h>
Thieu Le5c7d9752010-12-15 16:09:28 -080014#include <gtest/gtest.h>
15
16#include "update_engine/graph_types.h"
17#include "update_engine/delta_diff_generator.h"
18#include "update_engine/metadata.h"
19#include "update_engine/test_utils.h"
20#include "update_engine/utils.h"
21
22using std::string;
23using std::vector;
24
25namespace chromeos_update_engine {
26
27typedef DeltaDiffGenerator::Block Block;
28
29class MetadataTest : public ::testing::Test {
30};
31
32TEST_F(MetadataTest, RunAsRootReadMetadataDissimilarFileSystems) {
33 string a_img, b_img;
34 EXPECT_TRUE(utils::MakeTempFile("/tmp/a_img.XXXXXX", &a_img, NULL));
35 ScopedPathUnlinker a_img_unlinker(a_img);
36 EXPECT_TRUE(utils::MakeTempFile("/tmp/b_img.XXXXXX", &b_img, NULL));
37 ScopedPathUnlinker b_img_unlinker(b_img);
38
39 CreateEmptyExtImageAtPath(a_img, 10485759, 4096);
40 CreateEmptyExtImageAtPath(b_img, 11534336, 4096);
41
42 Graph graph;
43 vector<Block> blocks;
44 EXPECT_TRUE(Metadata::DeltaReadMetadata(&graph,
45 &blocks,
46 a_img,
47 b_img,
48 0,
49 NULL));
50 EXPECT_EQ(graph.size(), 0);
51
52 CreateEmptyExtImageAtPath(a_img, 10485759, 4096);
53 CreateEmptyExtImageAtPath(b_img, 10485759, 8192);
54
55 graph.clear();
56 blocks.clear();
57 EXPECT_TRUE(Metadata::DeltaReadMetadata(&graph,
58 &blocks,
59 a_img,
60 b_img,
61 0,
62 NULL));
63 EXPECT_EQ(graph.size(), 0);
64}
65
66TEST_F(MetadataTest, RunAsRootReadMetadata) {
67 string a_img, b_img, data_file;
68 EXPECT_TRUE(utils::MakeTempFile("/tmp/a_img.XXXXXX", &a_img, NULL));
69 ScopedPathUnlinker a_img_unlinker(a_img);
70 EXPECT_TRUE(utils::MakeTempFile("/tmp/b_img.XXXXXX", &b_img, NULL));
71 ScopedPathUnlinker b_img_unlinker(b_img);
72 EXPECT_TRUE(utils::MakeTempFile("/tmp/data_file.XXXXXX", &data_file, NULL));
73 ScopedPathUnlinker data_file_unlinker(data_file);
74
75 const size_t image_size = (256 * 1024 * 1024); // Enough for 2 block groups
76 const int block_size = 4096;
77 CreateEmptyExtImageAtPath(a_img, image_size, block_size);
78
79 // Create a file large enough to create an indirect block
80 {
81 string a_img_mnt;
82 ScopedLoopMounter a_img_mount(a_img, &a_img_mnt, 0);
83 System(StringPrintf("dd if=/dev/zero of=%s/test_file bs=%d count=%d",
84 a_img_mnt.c_str(), block_size, EXT2_NDIR_BLOCKS + 1));
85 }
86
87 System(StringPrintf("cp %s %s", a_img.c_str(), b_img.c_str()));
88
89 int fd = open(data_file.c_str(), O_RDWR | O_CREAT, S_IRWXU);
90 EXPECT_NE(fd, -1);
91 ScopedFdCloser fd_closer(&fd);
92
93 Graph graph;
94 vector<Block> blocks(image_size / block_size);
95 off_t data_file_size;
96 EXPECT_TRUE(Metadata::DeltaReadMetadata(&graph,
97 &blocks,
98 a_img,
99 b_img,
100 fd,
101 &data_file_size));
102
103 // There are 12 metadata that we look for:
104 // - Block group 0 metadata (superblock, group descriptor, bitmaps, etc)
105 // - Chunk 0, 1, 2, 3
106 // - Block group 1 metadata
107 // - Chunk 0, 1, 2, 3
108 // - Root directory (inode 2)
109 // - Journal (inode 8)
110 // - lost+found directory (inode 11)
111 // - test_file indirect block (inode 12)
112 struct {
113 string metadata_name;
114 off_t start_block; // Set to -1 to skip start block verification
115 off_t num_blocks; // Set to -1 to skip num blocks verification
116 } exp_results[] =
Thieu Lef6502192011-01-05 14:34:22 -0800117 {{"<rootfs-bg-0-0-metadata>", 0, 104},
118 {"<rootfs-bg-0-1-metadata>", 104, 104},
119 {"<rootfs-bg-0-2-metadata>", 208, 104},
120 {"<rootfs-bg-0-3-metadata>", 312, 104},
121 {"<rootfs-bg-0-4-metadata>", 416, 104},
122 {"<rootfs-bg-0-5-metadata>", 520, 104},
123 {"<rootfs-bg-0-6-metadata>", 624, 104},
124 {"<rootfs-bg-0-7-metadata>", 728, 104},
125 {"<rootfs-bg-0-8-metadata>", 832, 104},
126 {"<rootfs-bg-0-9-metadata>", 936, 107},
127 {"<rootfs-bg-1-0-metadata>", 32768, 104},
128 {"<rootfs-bg-1-1-metadata>", 32872, 104},
129 {"<rootfs-bg-1-2-metadata>", 32976, 104},
130 {"<rootfs-bg-1-3-metadata>", 33080, 104},
131 {"<rootfs-bg-1-4-metadata>", 33184, 104},
132 {"<rootfs-bg-1-5-metadata>", 33288, 104},
133 {"<rootfs-bg-1-6-metadata>", 33392, 104},
134 {"<rootfs-bg-1-7-metadata>", 33496, 104},
135 {"<rootfs-bg-1-8-metadata>", 33600, 104},
136 {"<rootfs-bg-1-9-metadata>", 33704, 107},
Thieu Le5c7d9752010-12-15 16:09:28 -0800137 {"<rootfs-inode-2-metadata>", -1, 1},
138 {"<rootfs-inode-8-metadata>", -1, 4101},
139 {"<rootfs-inode-11-metadata>", -1, 4},
140 {"<rootfs-inode-12-metadata>", -1, 1}};
141
142 int num_exp_results = sizeof(exp_results) / sizeof(exp_results[0]);
143 EXPECT_EQ(graph.size(), num_exp_results);
144
145 for (int i = 0; i < num_exp_results; i++) {
146 Vertex& vertex = graph[i];
147 DeltaArchiveManifest_InstallOperation& op = vertex.op;
148
149 EXPECT_STRCASEEQ(vertex.file_name.c_str(),
150 exp_results[i].metadata_name.c_str());
151
152 EXPECT_EQ(op.src_extents().size(), op.dst_extents().size());
153 for (int e = 0; e < op.src_extents().size(); e++) {
154 EXPECT_EQ(op.src_extents(e).start_block(),
155 op.dst_extents(e).start_block());
156 EXPECT_EQ(op.src_extents(e).num_blocks(),
157 op.dst_extents(e).num_blocks());
158 }
159
160 if (exp_results[i].start_block != -1) {
161 EXPECT_EQ(op.src_extents(0).start_block(), exp_results[i].start_block);
162 }
163
164 if (exp_results[i].num_blocks != -1) {
165 EXPECT_EQ(op.src_extents(0).num_blocks(), exp_results[i].num_blocks);
166 }
167 }
168}
169
170} // namespace chromeos_update_engine