/src/mozilla-central/xpcom/build/Omnijar.cpp
Line | Count | Source (jump to first uncovered line) |
1 | | /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ |
2 | | /* vim: set ts=8 sts=2 et sw=2 tw=80: */ |
3 | | /* This Source Code Form is subject to the terms of the Mozilla Public |
4 | | * License, v. 2.0. If a copy of the MPL was not distributed with this |
5 | | * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ |
6 | | |
7 | | #include "Omnijar.h" |
8 | | |
9 | | #include "nsDirectoryService.h" |
10 | | #include "nsDirectoryServiceDefs.h" |
11 | | #include "nsIFile.h" |
12 | | #include "nsZipArchive.h" |
13 | | #include "nsNetUtil.h" |
14 | | |
15 | | namespace mozilla { |
16 | | |
17 | | StaticRefPtr<nsIFile> Omnijar::sPath[2]; |
18 | | StaticRefPtr<nsZipArchive> Omnijar::sReader[2]; |
19 | | StaticRefPtr<nsZipArchive> Omnijar::sOuterReader[2]; |
20 | | bool Omnijar::sInitialized = false; |
21 | | bool Omnijar::sIsUnified = false; |
22 | | |
23 | | static const char* sProp[2] = { |
24 | | NS_GRE_DIR, NS_XPCOM_CURRENT_PROCESS_DIR |
25 | | }; |
26 | | |
27 | 6 | #define SPROP(Type) ((Type == mozilla::Omnijar::GRE) ? sProp[GRE] : sProp[APP]) |
28 | | |
29 | | void |
30 | | Omnijar::CleanUpOne(Type aType) |
31 | 3 | { |
32 | 3 | if (sReader[aType]) { |
33 | 0 | sReader[aType]->CloseArchive(); |
34 | 0 | sReader[aType] = nullptr; |
35 | 0 | } |
36 | 3 | if (sOuterReader[aType]) { |
37 | 0 | sOuterReader[aType]->CloseArchive(); |
38 | 0 | sOuterReader[aType] = nullptr; |
39 | 0 | } |
40 | 3 | sPath[aType] = nullptr; |
41 | 3 | } |
42 | | |
43 | | void |
44 | | Omnijar::InitOne(nsIFile* aPath, Type aType) |
45 | 6 | { |
46 | 6 | nsCOMPtr<nsIFile> file; |
47 | 6 | if (aPath) { |
48 | 0 | file = aPath; |
49 | 6 | } else { |
50 | 6 | nsCOMPtr<nsIFile> dir; |
51 | 6 | nsDirectoryService::gService->Get(SPROP(aType), NS_GET_IID(nsIFile), |
52 | 6 | getter_AddRefs(dir)); |
53 | 6 | NS_NAMED_LITERAL_CSTRING(kOmnijarName, NS_STRINGIFY(OMNIJAR_NAME)); |
54 | 6 | if (NS_FAILED(dir->Clone(getter_AddRefs(file))) || |
55 | 6 | NS_FAILED(file->AppendNative(kOmnijarName))) { |
56 | 0 | return; |
57 | 0 | } |
58 | 6 | } |
59 | 6 | bool isFile; |
60 | 6 | if (NS_FAILED(file->IsFile(&isFile)) || !isFile) { |
61 | 0 | // If we're not using an omni.jar for GRE, and we don't have an |
62 | 0 | // omni.jar for APP, check if both directories are the same. |
63 | 0 | if ((aType == APP) && (!sPath[GRE])) { |
64 | 0 | nsCOMPtr<nsIFile> greDir, appDir; |
65 | 0 | bool equals; |
66 | 0 | nsDirectoryService::gService->Get(sProp[GRE], NS_GET_IID(nsIFile), |
67 | 0 | getter_AddRefs(greDir)); |
68 | 0 | nsDirectoryService::gService->Get(sProp[APP], NS_GET_IID(nsIFile), |
69 | 0 | getter_AddRefs(appDir)); |
70 | 0 | if (NS_SUCCEEDED(greDir->Equals(appDir, &equals)) && equals) { |
71 | 0 | sIsUnified = true; |
72 | 0 | } |
73 | 0 | } |
74 | 0 | return; |
75 | 0 | } |
76 | 6 | |
77 | 6 | bool equals; |
78 | 6 | if ((aType == APP) && (sPath[GRE]) && |
79 | 6 | NS_SUCCEEDED(sPath[GRE]->Equals(file, &equals)) && equals) { |
80 | 3 | // If we're using omni.jar on both GRE and APP and their path |
81 | 3 | // is the same, we're in the unified case. |
82 | 3 | sIsUnified = true; |
83 | 3 | return; |
84 | 3 | } |
85 | 3 | |
86 | 3 | RefPtr<nsZipArchive> zipReader = new nsZipArchive(); |
87 | 3 | if (NS_FAILED(zipReader->OpenArchive(file))) { |
88 | 0 | return; |
89 | 0 | } |
90 | 3 | |
91 | 3 | RefPtr<nsZipArchive> outerReader; |
92 | 3 | RefPtr<nsZipHandle> handle; |
93 | 3 | if (NS_SUCCEEDED(nsZipHandle::Init(zipReader, NS_STRINGIFY(OMNIJAR_NAME), |
94 | 3 | getter_AddRefs(handle)))) { |
95 | 0 | outerReader = zipReader; |
96 | 0 | zipReader = new nsZipArchive(); |
97 | 0 | if (NS_FAILED(zipReader->OpenArchive(handle))) { |
98 | 0 | return; |
99 | 0 | } |
100 | 3 | } |
101 | 3 | |
102 | 3 | CleanUpOne(aType); |
103 | 3 | sReader[aType] = zipReader; |
104 | 3 | sOuterReader[aType] = outerReader; |
105 | 3 | sPath[aType] = file; |
106 | 3 | } |
107 | | |
108 | | void |
109 | | Omnijar::Init(nsIFile* aGrePath, nsIFile* aAppPath) |
110 | 3 | { |
111 | 3 | InitOne(aGrePath, GRE); |
112 | 3 | InitOne(aAppPath, APP); |
113 | 3 | sInitialized = true; |
114 | 3 | } |
115 | | |
116 | | void |
117 | | Omnijar::CleanUp() |
118 | 0 | { |
119 | 0 | CleanUpOne(GRE); |
120 | 0 | CleanUpOne(APP); |
121 | 0 | sInitialized = false; |
122 | 0 | } |
123 | | |
124 | | already_AddRefed<nsZipArchive> |
125 | | Omnijar::GetReader(nsIFile* aPath) |
126 | 1 | { |
127 | 1 | MOZ_ASSERT(IsInitialized(), "Omnijar not initialized"); |
128 | 1 | |
129 | 1 | bool equals; |
130 | 1 | nsresult rv; |
131 | 1 | |
132 | 1 | if (sPath[GRE]) { |
133 | 1 | rv = sPath[GRE]->Equals(aPath, &equals); |
134 | 1 | if (NS_SUCCEEDED(rv) && equals) { |
135 | 1 | return IsNested(GRE) ? GetOuterReader(GRE) : GetReader(GRE); |
136 | 1 | } |
137 | 0 | } |
138 | 0 | if (sPath[APP]) { |
139 | 0 | rv = sPath[APP]->Equals(aPath, &equals); |
140 | 0 | if (NS_SUCCEEDED(rv) && equals) { |
141 | 0 | return IsNested(APP) ? GetOuterReader(APP) : GetReader(APP); |
142 | 0 | } |
143 | 0 | } |
144 | 0 | return nullptr; |
145 | 0 | } |
146 | | |
147 | | nsresult |
148 | | Omnijar::GetURIString(Type aType, nsACString& aResult) |
149 | 19 | { |
150 | 19 | MOZ_ASSERT(IsInitialized(), "Omnijar not initialized"); |
151 | 19 | |
152 | 19 | aResult.Truncate(); |
153 | 19 | |
154 | 19 | // Return an empty string for APP in the unified case. |
155 | 19 | if ((aType == APP) && sIsUnified) { |
156 | 8 | return NS_OK; |
157 | 8 | } |
158 | 11 | |
159 | 11 | nsAutoCString omniJarSpec; |
160 | 11 | if (sPath[aType]) { |
161 | 11 | nsresult rv = NS_GetURLSpecFromActualFile(sPath[aType], omniJarSpec); |
162 | 11 | if (NS_WARN_IF(NS_FAILED(rv))) { |
163 | 0 | return rv; |
164 | 0 | } |
165 | 11 | |
166 | 11 | aResult = "jar:"; |
167 | 11 | if (IsNested(aType)) { |
168 | 0 | aResult += "jar:"; |
169 | 0 | } |
170 | 11 | aResult += omniJarSpec; |
171 | 11 | aResult += "!"; |
172 | 11 | if (IsNested(aType)) { |
173 | 0 | aResult += "/" NS_STRINGIFY(OMNIJAR_NAME) "!"; |
174 | 0 | } |
175 | 11 | } else { |
176 | 0 | nsCOMPtr<nsIFile> dir; |
177 | 0 | nsDirectoryService::gService->Get(SPROP(aType), NS_GET_IID(nsIFile), |
178 | 0 | getter_AddRefs(dir)); |
179 | 0 | nsresult rv = NS_GetURLSpecFromActualFile(dir, aResult); |
180 | 0 | if (NS_WARN_IF(NS_FAILED(rv))) { |
181 | 0 | return rv; |
182 | 0 | } |
183 | 11 | } |
184 | 11 | aResult += "/"; |
185 | 11 | return NS_OK; |
186 | 11 | } |
187 | | |
188 | | } /* namespace mozilla */ |