xpcom/build/Omnijar.cpp

changeset 0
6474c204b198
     1.1 --- /dev/null	Thu Jan 01 00:00:00 1970 +0000
     1.2 +++ b/xpcom/build/Omnijar.cpp	Wed Dec 31 06:09:35 2014 +0100
     1.3 @@ -0,0 +1,169 @@
     1.4 +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
     1.5 + * This Source Code Form is subject to the terms of the Mozilla Public
     1.6 + * License, v. 2.0. If a copy of the MPL was not distributed with this
     1.7 + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
     1.8 +
     1.9 +#include "Omnijar.h"
    1.10 +
    1.11 +#include "nsDirectoryService.h"
    1.12 +#include "nsDirectoryServiceDefs.h"
    1.13 +#include "nsIFile.h"
    1.14 +#include "nsZipArchive.h"
    1.15 +#include "nsNetUtil.h"
    1.16 +
    1.17 +namespace mozilla {
    1.18 +
    1.19 +nsIFile *Omnijar::sPath[2] = { nullptr, nullptr };
    1.20 +nsZipArchive *Omnijar::sReader[2] = { nullptr, nullptr };
    1.21 +bool Omnijar::sInitialized = false;
    1.22 +static bool sIsUnified = false;
    1.23 +static bool sIsNested[2] = { false, false };
    1.24 +
    1.25 +static const char *sProp[2] =
    1.26 +    { NS_GRE_DIR, NS_XPCOM_CURRENT_PROCESS_DIR };
    1.27 +
    1.28 +#define SPROP(Type) ((Type == mozilla::Omnijar::GRE) ? sProp[GRE] : sProp[APP])
    1.29 +
    1.30 +void
    1.31 +Omnijar::CleanUpOne(Type aType)
    1.32 +{
    1.33 +    if (sReader[aType]) {
    1.34 +        sReader[aType]->CloseArchive();
    1.35 +        NS_IF_RELEASE(sReader[aType]);
    1.36 +    }
    1.37 +    sReader[aType] = nullptr;
    1.38 +    NS_IF_RELEASE(sPath[aType]);
    1.39 +}
    1.40 +
    1.41 +void
    1.42 +Omnijar::InitOne(nsIFile *aPath, Type aType)
    1.43 +{
    1.44 +    nsCOMPtr<nsIFile> file;
    1.45 +    if (aPath) {
    1.46 +        file = aPath;
    1.47 +    } else {
    1.48 +        nsCOMPtr<nsIFile> dir;
    1.49 +        nsDirectoryService::gService->Get(SPROP(aType), NS_GET_IID(nsIFile), getter_AddRefs(dir));
    1.50 +        NS_NAMED_LITERAL_CSTRING (kOmnijarName, NS_STRINGIFY(OMNIJAR_NAME));
    1.51 +        if (NS_FAILED(dir->Clone(getter_AddRefs(file))) ||
    1.52 +            NS_FAILED(file->AppendNative(kOmnijarName)))
    1.53 +            return;
    1.54 +    }
    1.55 +    bool isFile;
    1.56 +    if (NS_FAILED(file->IsFile(&isFile)) || !isFile) {
    1.57 +        // If we're not using an omni.jar for GRE, and we don't have an
    1.58 +        // omni.jar for APP, check if both directories are the same.
    1.59 +        if ((aType == APP) && (!sPath[GRE])) {
    1.60 +            nsCOMPtr<nsIFile> greDir, appDir;
    1.61 +            bool equals;
    1.62 +            nsDirectoryService::gService->Get(SPROP(GRE), NS_GET_IID(nsIFile), getter_AddRefs(greDir));
    1.63 +            nsDirectoryService::gService->Get(SPROP(APP), NS_GET_IID(nsIFile), getter_AddRefs(appDir));
    1.64 +            if (NS_SUCCEEDED(greDir->Equals(appDir, &equals)) && equals)
    1.65 +                sIsUnified = true;
    1.66 +        }
    1.67 +        return;
    1.68 +    }
    1.69 +
    1.70 +    bool equals;
    1.71 +    if ((aType == APP) && (sPath[GRE]) &&
    1.72 +        NS_SUCCEEDED(sPath[GRE]->Equals(file, &equals)) && equals) {
    1.73 +        // If we're using omni.jar on both GRE and APP and their path
    1.74 +        // is the same, we're in the unified case.
    1.75 +        sIsUnified = true;
    1.76 +        return;
    1.77 +    }
    1.78 +
    1.79 +    nsRefPtr<nsZipArchive> zipReader = new nsZipArchive();
    1.80 +    if (NS_FAILED(zipReader->OpenArchive(file))) {
    1.81 +        return;
    1.82 +    }
    1.83 +
    1.84 +    nsRefPtr<nsZipHandle> handle;
    1.85 +    if (NS_SUCCEEDED(nsZipHandle::Init(zipReader, NS_STRINGIFY(OMNIJAR_NAME), getter_AddRefs(handle)))) {
    1.86 +        zipReader = new nsZipArchive();
    1.87 +        if (NS_FAILED(zipReader->OpenArchive(handle)))
    1.88 +            return;
    1.89 +        sIsNested[aType] = true;
    1.90 +    }
    1.91 +
    1.92 +    CleanUpOne(aType);
    1.93 +    sReader[aType] = zipReader;
    1.94 +    NS_IF_ADDREF(sReader[aType]);
    1.95 +    sPath[aType] = file;
    1.96 +    NS_IF_ADDREF(sPath[aType]);
    1.97 +}
    1.98 +
    1.99 +void
   1.100 +Omnijar::Init(nsIFile *aGrePath, nsIFile *aAppPath)
   1.101 +{
   1.102 +    InitOne(aGrePath, GRE);
   1.103 +    InitOne(aAppPath, APP);
   1.104 +    sInitialized = true;
   1.105 +}
   1.106 +
   1.107 +void
   1.108 +Omnijar::CleanUp()
   1.109 +{
   1.110 +    CleanUpOne(GRE);
   1.111 +    CleanUpOne(APP);
   1.112 +    sInitialized = false;
   1.113 +}
   1.114 +
   1.115 +already_AddRefed<nsZipArchive>
   1.116 +Omnijar::GetReader(nsIFile *aPath)
   1.117 +{
   1.118 +    NS_ABORT_IF_FALSE(IsInitialized(), "Omnijar not initialized");
   1.119 +
   1.120 +    bool equals;
   1.121 +    nsresult rv;
   1.122 +
   1.123 +    if (sPath[GRE] && !sIsNested[GRE]) {
   1.124 +        rv = sPath[GRE]->Equals(aPath, &equals);
   1.125 +        if (NS_SUCCEEDED(rv) && equals)
   1.126 +            return GetReader(GRE);
   1.127 +    }
   1.128 +    if (sPath[APP] && !sIsNested[APP]) {
   1.129 +        rv = sPath[APP]->Equals(aPath, &equals);
   1.130 +        if (NS_SUCCEEDED(rv) && equals)
   1.131 +            return GetReader(APP);
   1.132 +    }
   1.133 +    return nullptr;
   1.134 +}
   1.135 +
   1.136 +nsresult
   1.137 +Omnijar::GetURIString(Type aType, nsACString &result)
   1.138 +{
   1.139 +    NS_ABORT_IF_FALSE(IsInitialized(), "Omnijar not initialized");
   1.140 +
   1.141 +    result.Truncate();
   1.142 +
   1.143 +    // Return an empty string for APP in the unified case.
   1.144 +    if ((aType == APP) && sIsUnified) {
   1.145 +        return NS_OK;
   1.146 +    }
   1.147 +
   1.148 +    nsAutoCString omniJarSpec;
   1.149 +    if (sPath[aType]) {
   1.150 +        nsresult rv = NS_GetURLSpecFromActualFile(sPath[aType], omniJarSpec);
   1.151 +        if (NS_WARN_IF(NS_FAILED(rv)))
   1.152 +            return rv;
   1.153 +
   1.154 +        result = "jar:";
   1.155 +        if (sIsNested[aType])
   1.156 +            result += "jar:";
   1.157 +        result += omniJarSpec;
   1.158 +        result += "!";
   1.159 +        if (sIsNested[aType])
   1.160 +            result += "/" NS_STRINGIFY(OMNIJAR_NAME) "!";
   1.161 +    } else {
   1.162 +        nsCOMPtr<nsIFile> dir;
   1.163 +        nsDirectoryService::gService->Get(SPROP(aType), NS_GET_IID(nsIFile), getter_AddRefs(dir));
   1.164 +        nsresult rv = NS_GetURLSpecFromActualFile(dir, result);
   1.165 +        if (NS_WARN_IF(NS_FAILED(rv)))
   1.166 +            return rv;
   1.167 +    }
   1.168 +    result += "/";
   1.169 +    return NS_OK;
   1.170 +}
   1.171 +
   1.172 +} /* namespace mozilla */

mercurial