blob: 367e5bfc4d51c3719a77ef861a4d75cad6dcb626 [file] [log] [blame]
Brian Carlstromb7bbba42011-10-13 14:58:47 -07001// Copyright 2011 Google Inc. All Rights Reserved.
2
3#include <stdio.h>
4#include <stdlib.h>
5
6#include "dex_file.h"
7#include "file.h"
8#include "logging.h"
9#include "oat_file.h"
10#include "os.h"
11#include "UniquePtr.h"
12#include "zip_archive.h"
13
14namespace art {
15
16int ProcessZipFile(int zip_fd, int cache_fd, const char* zip_name, const char *flags) {
17 // TODO: need to read/write to installd opened file descriptors
18 if (false) {
19 UniquePtr<ZipArchive> zip_archive(ZipArchive::Open(zip_fd));
20 if (zip_archive.get() == NULL) {
21 LOG(ERROR) << "Failed to open " << zip_name << " when looking for classes.dex";
22 return -1;
23 }
24
25 UniquePtr<ZipEntry> zip_entry(zip_archive->Find(DexFile::kClassesDex));
26 if (zip_entry.get() == NULL) {
27 LOG(ERROR) << "Failed to find classes.dex within " << zip_name;
28 return -1;
29 }
30
31 UniquePtr<File> file(OS::FileFromFd("oatopt cache file descriptor", cache_fd));
32 bool success = zip_entry->Extract(*file);
33 if (!success) {
34 LOG(ERROR) << "Failed to extract classes.dex from " << zip_name;
35 return -1;
36 }
37 }
38
39 // Opening a zip file for a dex will extract to art-cache
40 UniquePtr<const DexFile> dex_file(DexFile::Open(zip_name, ""));
41 if (dex_file.get() == NULL) {
42 LOG(ERROR) << "Failed to open " << zip_name;
43 return -1;
44 }
45
46 std::string dex_file_option("--dex-file=");
47 dex_file_option += zip_name;
48
49 std::string oat_file_option("--oat=");
50 oat_file_option += GetArtCacheOatFilenameOrDie(OatFile::DexFileToOatFilename(*dex_file.get()));
51
52 execl("/system/bin/dex2oatd",
53 "/system/bin/dex2oatd",
54 "-Xms64m",
55 "-Xmx64m",
56 "--boot-image=/data/art-cache/boot.art",
57 dex_file_option.c_str(),
58 oat_file_option.c_str(),
59 NULL);
60 PLOG(FATAL) << "execl(dex2oatd) failed";
61 return -1;
62}
63
64// Parse arguments. We want:
65// 0. (name of command -- ignored)
66// 1. "--zip"
67// 2. zip fd (input, read-only)
68// 3. cache fd (output, read-write, locked with flock)
69// 4. filename of zipfile
70// 5. flags
71int FromZip(const int argc, const char* const argv[]) {
72 if (argc != 6) {
73 LOG(ERROR) << "Wrong number of args for --zip (found " << argc << ")";
74 return -1;
75 }
76
77 // ignore program name
78
79 // verify --zip
80 CHECK_STREQ(argv[1], "--zip");
81
82 char* zip_end;
83 int zip_fd = strtol(argv[2], &zip_end, 0);
84 if (*zip_end != '\0') {
85 LOG(ERROR) << "bad zip fd: " << argv[2];
86 return -1;
87 }
88#ifndef NDEBUG
89 LOG(INFO) << "zip_fd=" << zip_fd;
90#endif
91
92 char* cache_end;
93 int cache_fd = strtol(argv[3], &cache_end, 0);
94 if (*cache_end != '\0') {
95 LOG(ERROR) << "bad cache fd: " << argv[3];
96 return -1;
97 }
98#ifndef NDEBUG
99 LOG(INFO) << "cache_fd=" << cache_fd;
100#endif
101
102 const char* zip_name = argv[4];
103#ifndef NDEBUG
104 LOG(INFO) << "zip_name=" << zip_name;
105#endif
106
107 const char* flags = argv[5];
108#ifndef NDEBUG
109 LOG(INFO) << "flags=" << flags;
110#endif
111
112 return ProcessZipFile(zip_fd, cache_fd, zip_name, flags);
113}
114
115int oatopt(int argc, char** argv) {
116
117 setvbuf(stdout, NULL, _IONBF, 0);
118
119 if (true) {
120 for (int i = 0; i < argc; ++i) {
121 LOG(INFO) << "oatopt: option[" << i << "]=" << argv[i];
122 }
123 }
124
125 if (argc > 1) {
126 if (strcmp(argv[1], "--zip") == 0) {
127 return FromZip(argc, argv);
128 }
129 }
130
131 fprintf(stderr,
132 "Usage:\n\n"
133 "Short version: Don't use this.\n\n"
134 "Slightly longer version: This system-internal tool is used to extract\n"
135 "dex files and produce oat files. See the source code for details.\n");
136
137 return 1;
138}
139
140} // namespace art
141
142int main(int argc, char** argv) {
143 return art::oatopt(argc, argv);
144}