/* ***** BEGIN LICENSE BLOCK *****
 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
 *
 * The contents of this file are subject to the Mozilla Public License Version
 * 1.1 (the "License"); you may not use this file except in compliance with
 * the License. You may obtain a copy of the License at
 * http://www.mozilla.org/MPL/
 *
 * Software distributed under the License is distributed on an "AS IS" basis,
 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
 * for the specific language governing rights and limitations under the
 * License.
 *
 * The Original Code is the Netscape security libraries.
 *
 * The Initial Developer of the Original Code is
 * Netscape Communications Corporation.
 * Portions created by the Initial Developer are Copyright (C) 2000
 * the Initial Developer. All Rights Reserved.
 *
 * Contributor(s):
 *   Ian McGreer <mcgreer@netscape.com>
 *
 * Alternatively, the contents of this file may be used under the terms of
 * either the GNU General Public License Version 2 or later (the "GPL"), or
 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
 * in which case the provisions of the GPL or the LGPL are applicable instead
 * of those above. If you wish to allow use of your version of this file only
 * under the terms of either the GPL or the LGPL, and not to allow others to
 * use your version of this file under the terms of the MPL, indicate your
 * decision by deleting the provisions above and replace them with the notice
 * and other provisions required by the GPL or the LGPL. If you do not delete
 * the provisions above, a recipient may use your version of this file under
 * the terms of any one of the MPL, the GPL or the LGPL.
 *
 * ***** END LICENSE BLOCK ***** */

#include "net/third_party/mozilla_security_manager/nsPKCS12Blob.h"

#include <pk11pub.h>
#include <pkcs12.h>
#include <p12plcy.h>
#include <secerr.h>

#include "base/lazy_instance.h"
#include "base/logging.h"
#include "base/strings/string_util.h"
#include "crypto/nss_util_internal.h"
#include "net/base/net_errors.h"
#include "net/cert/x509_certificate.h"

namespace mozilla_security_manager {

namespace {

// unicodeToItem
//
// For the NSS PKCS#12 library, must convert PRUnichars (shorts) to
// a buffer of octets.  Must handle byte order correctly.
// TODO: Is there a Mozilla way to do this?  In the string lib?
void unicodeToItem(const PRUnichar *uni, SECItem *item)
{
  int len = 0;
  while (uni[len++] != 0);
  SECITEM_AllocItem(NULL, item, sizeof(PRUnichar) * len);
#ifdef IS_LITTLE_ENDIAN
  int i = 0;
  for (i=0; i<len; i++) {
    item->data[2*i  ] = (unsigned char )(uni[i] << 8);
    item->data[2*i+1] = (unsigned char )(uni[i]);
  }
#else
  memcpy(item->data, uni, item->len);
#endif
}

// write_export_data
// write bytes to the exported PKCS#12 data buffer
void write_export_data(void* arg, const char* buf, unsigned long len) {
  std::string* dest = reinterpret_cast<std::string*>(arg);
  dest->append(buf, len);
}

// nickname_collision
// what to do when the nickname collides with one already in the db.
// Based on P12U_NicknameCollisionCallback from nss/cmd/pk12util/pk12util.c
SECItem* PR_CALLBACK
nickname_collision(SECItem *old_nick, PRBool *cancel, void *wincx)
{
  char           *nick     = NULL;
  SECItem        *ret_nick = NULL;
  CERTCertificate* cert    = (CERTCertificate*)wincx;

  if (!cancel || !cert) {
    // pk12util calls this error user cancelled?
    return NULL;
  }

  if (!old_nick)
    VLOG(1) << "no nickname for cert in PKCS12 file.";

  nick = CERT_MakeCANickname(cert);
  if (!nick) {
    return NULL;
  }

  if(old_nick && old_nick->data && old_nick->len &&
     PORT_Strlen(nick) == old_nick->len &&
     !PORT_Strncmp((char *)old_nick->data, nick, old_nick->len)) {
    PORT_Free(nick);
    PORT_SetError(SEC_ERROR_IO);
    return NULL;
  }

  VLOG(1) << "using nickname " << nick;
  ret_nick = PORT_ZNew(SECItem);
  if(ret_nick == NULL) {
    PORT_Free(nick);
    return NULL;
  }

  ret_nick->data = (unsigned char *)nick;
  ret_nick->len = PORT_Strlen(nick);

  return ret_nick;
}

// pip_ucs2_ascii_conversion_fn
// required to be set by NSS (to do PKCS#12), but since we've already got
// unicode make this a no-op.
PRBool
pip_ucs2_ascii_conversion_fn(PRBool toUnicode,
                             unsigned char *inBuf,
                             unsigned int inBufLen,
                             unsigned char *outBuf,
                             unsigned int maxOutBufLen,
                             unsigned int *outBufLen,
                             PRBool swapBytes)
{
  CHECK_GE(maxOutBufLen, inBufLen);
  // do a no-op, since I've already got Unicode.  Hah!
  *outBufLen = inBufLen;
  memcpy(outBuf, inBuf, inBufLen);
  return PR_TRUE;
}

// Based on nsPKCS12Blob::ImportFromFileHelper.
int
nsPKCS12Blob_ImportHelper(const char* pkcs12_data,
                          size_t pkcs12_len,
                          const base::string16& password,
                          bool is_extractable,
                          bool try_zero_length_secitem,
                          PK11SlotInfo *slot,
                          net::CertificateList* imported_certs)
{
  DCHECK(pkcs12_data);
  DCHECK(slot);
  int import_result = net::ERR_PKCS12_IMPORT_FAILED;
  SECStatus srv = SECSuccess;
  SEC_PKCS12DecoderContext *dcx = NULL;
  SECItem unicodePw;
  SECItem attribute_value;
  CK_BBOOL attribute_data = CK_FALSE;
  const SEC_PKCS12DecoderItem* decoder_item = NULL;

  unicodePw.type = siBuffer;
  unicodePw.len = 0;
  unicodePw.data = NULL;
  if (!try_zero_length_secitem) {
    unicodeToItem(password.c_str(), &unicodePw);
  }

  // Initialize the decoder
  dcx = SEC_PKCS12DecoderStart(&unicodePw, slot,
                               // wincx
                               NULL,
                               // dOpen, dClose, dRead, dWrite, dArg: NULL
                               // specifies default impl using memory buffer.
                               NULL, NULL, NULL, NULL, NULL);
  if (!dcx) {
    srv = SECFailure;
    goto finish;
  }
  // feed input to the decoder
  srv = SEC_PKCS12DecoderUpdate(dcx,
                                (unsigned char*)pkcs12_data,
                                pkcs12_len);
  if (srv) goto finish;
  // verify the blob
  srv = SEC_PKCS12DecoderVerify(dcx);
  if (srv) goto finish;
  // validate bags
  srv = SEC_PKCS12DecoderValidateBags(dcx, nickname_collision);
  if (srv) goto finish;
  // import certificate and key
  srv = SEC_PKCS12DecoderImportBags(dcx);
  if (srv) goto finish;

  attribute_value.data = &attribute_data;
  attribute_value.len = sizeof(attribute_data);

  srv = SEC_PKCS12DecoderIterateInit(dcx);
  if (srv) goto finish;

  if (imported_certs)
    imported_certs->clear();

  // Collect the list of decoded certificates, and mark private keys
  // non-extractable if needed.
  while (SEC_PKCS12DecoderIterateNext(dcx, &decoder_item) == SECSuccess) {
    if (decoder_item->type != SEC_OID_PKCS12_V1_CERT_BAG_ID)
      continue;

    CERTCertificate* cert = PK11_FindCertFromDERCertItem(
        slot, decoder_item->der,
        NULL);  // wincx
    if (!cert) {
      LOG(ERROR) << "Could not grab a handle to the certificate in the slot "
                 << "from the corresponding PKCS#12 DER certificate.";
      continue;
    }

    // Add the cert to the list
    if (imported_certs) {
      // Empty list of intermediates.
      net::X509Certificate::OSCertHandles intermediates;
      imported_certs->push_back(
          net::X509Certificate::CreateFromHandle(cert, intermediates));
    }

    // Once we have determined that the imported certificate has an
    // associated private key too, only then can we mark the key as
    // non-extractable.
    if (!decoder_item->hasKey) {
      CERT_DestroyCertificate(cert);
      continue;
    }

    // Iterate through all the imported PKCS12 items and mark any accompanying
    // private keys as non-extractable.
    if (!is_extractable) {
      SECKEYPrivateKey* privKey = PK11_FindPrivateKeyFromCert(slot, cert,
                                                              NULL);  // wincx
      if (privKey) {
        // Mark the private key as non-extractable.
        srv = PK11_WriteRawAttribute(PK11_TypePrivKey, privKey, CKA_EXTRACTABLE,
                                     &attribute_value);
        SECKEY_DestroyPrivateKey(privKey);
        if (srv) {
          LOG(ERROR) << "Could not set CKA_EXTRACTABLE attribute on private "
                     << "key.";
          CERT_DestroyCertificate(cert);
          break;
        }
      }
    }
    CERT_DestroyCertificate(cert);
    if (srv) goto finish;
  }
  import_result = net::OK;
finish:
  // If srv != SECSuccess, NSS probably set a specific error code.
  // We should use that error code instead of inventing a new one
  // for every error possible.
  if (srv != SECSuccess) {
    int error = PORT_GetError();
    LOG(ERROR) << "PKCS#12 import failed with error " << error;
    switch (error) {
      case SEC_ERROR_BAD_PASSWORD:
      case SEC_ERROR_PKCS12_PRIVACY_PASSWORD_INCORRECT:
        import_result = net::ERR_PKCS12_IMPORT_BAD_PASSWORD;
        break;
      case SEC_ERROR_PKCS12_INVALID_MAC:
        import_result = net::ERR_PKCS12_IMPORT_INVALID_MAC;
        break;
      case SEC_ERROR_BAD_DER:
      case SEC_ERROR_PKCS12_DECODING_PFX:
      case SEC_ERROR_PKCS12_CORRUPT_PFX_STRUCTURE:
        import_result = net::ERR_PKCS12_IMPORT_INVALID_FILE;
        break;
      case SEC_ERROR_PKCS12_UNSUPPORTED_MAC_ALGORITHM:
      case SEC_ERROR_PKCS12_UNSUPPORTED_TRANSPORT_MODE:
      case SEC_ERROR_PKCS12_UNSUPPORTED_PBE_ALGORITHM:
      case SEC_ERROR_PKCS12_UNSUPPORTED_VERSION:
        import_result = net::ERR_PKCS12_IMPORT_UNSUPPORTED;
        break;
      default:
        import_result = net::ERR_PKCS12_IMPORT_FAILED;
        break;
    }
  }
  // Finish the decoder
  if (dcx)
    SEC_PKCS12DecoderFinish(dcx);
  SECITEM_ZfreeItem(&unicodePw, PR_FALSE);
  return import_result;
}


// Attempt to read the CKA_EXTRACTABLE attribute on a private key inside
// a token. On success, store the attribute in |extractable| and return
// SECSuccess.
SECStatus
isExtractable(SECKEYPrivateKey *privKey, PRBool *extractable)
{
  SECItem value;
  SECStatus rv;

  rv=PK11_ReadRawAttribute(PK11_TypePrivKey, privKey, CKA_EXTRACTABLE, &value);
  if (rv != SECSuccess)
    return rv;

  if ((value.len == 1) && (value.data != NULL))
    *extractable = !!(*(CK_BBOOL*)value.data);
  else
    rv = SECFailure;
  SECITEM_FreeItem(&value, PR_FALSE);
  return rv;
}

class PKCS12InitSingleton {
 public:
  // From the PKCS#12 section of nsNSSComponent::InitializeNSS in
  // nsNSSComponent.cpp.
  PKCS12InitSingleton() {
    // Enable ciphers for PKCS#12
    SEC_PKCS12EnableCipher(PKCS12_RC4_40, 1);
    SEC_PKCS12EnableCipher(PKCS12_RC4_128, 1);
    SEC_PKCS12EnableCipher(PKCS12_RC2_CBC_40, 1);
    SEC_PKCS12EnableCipher(PKCS12_RC2_CBC_128, 1);
    SEC_PKCS12EnableCipher(PKCS12_DES_56, 1);
    SEC_PKCS12EnableCipher(PKCS12_DES_EDE3_168, 1);
    SEC_PKCS12SetPreferredCipher(PKCS12_DES_EDE3_168, 1);

    // Set no-op ascii-ucs2 conversion function to work around weird NSS
    // interface.  Thankfully, PKCS12 appears to be the only thing in NSS that
    // uses PORT_UCS2_ASCIIConversion, so this doesn't break anything else.
    PORT_SetUCS2_ASCIIConversionFunction(pip_ucs2_ascii_conversion_fn);
  }
};

// Leaky so it can be initialized on worker threads and because there is no
// cleanup necessary.
static base::LazyInstance<PKCS12InitSingleton>::Leaky g_pkcs12_init_singleton =
    LAZY_INSTANCE_INITIALIZER;

}  // namespace

void EnsurePKCS12Init() {
  g_pkcs12_init_singleton.Get();
}

// Based on nsPKCS12Blob::ImportFromFile.
int nsPKCS12Blob_Import(PK11SlotInfo* slot,
                        const char* pkcs12_data,
                        size_t pkcs12_len,
                        const base::string16& password,
                        bool is_extractable,
                        net::CertificateList* imported_certs) {

  int rv = nsPKCS12Blob_ImportHelper(pkcs12_data, pkcs12_len, password,
                                     is_extractable, false, slot,
                                     imported_certs);

  // When the user entered a zero length password:
  //   An empty password should be represented as an empty
  //   string (a SECItem that contains a single terminating
  //   NULL UTF16 character), but some applications use a
  //   zero length SECItem.
  //   We try both variations, zero length item and empty string,
  //   without giving a user prompt when trying the different empty password
  //   flavors.
  if (rv == net::ERR_PKCS12_IMPORT_BAD_PASSWORD && password.empty()) {
    rv = nsPKCS12Blob_ImportHelper(pkcs12_data, pkcs12_len, password,
                                   is_extractable, true, slot, imported_certs);
  }
  return rv;
}

// Based on nsPKCS12Blob::ExportToFile
//
// Having already loaded the certs, form them into a blob (loading the keys
// also), encode the blob, and stuff it into the file.
//
// TODO: handle slots correctly
//       mirror "slotToUse" behavior from PSM 1.x
//       verify the cert array to start off with?
//       set appropriate error codes
int
nsPKCS12Blob_Export(std::string* output,
                    const net::CertificateList& certs,
                    const base::string16& password)
{
  int return_count = 0;
  SECStatus srv = SECSuccess;
  SEC_PKCS12ExportContext *ecx = NULL;
  SEC_PKCS12SafeInfo *certSafe = NULL, *keySafe = NULL;
  SECItem unicodePw;
  unicodePw.type = siBuffer;
  unicodePw.len = 0;
  unicodePw.data = NULL;

  int numCertsExported = 0;

  // get file password (unicode)
  unicodeToItem(password.c_str(), &unicodePw);

  // what about slotToUse in psm 1.x ???
  // create export context
  ecx = SEC_PKCS12CreateExportContext(NULL, NULL, NULL /*slot*/, NULL);
  if (!ecx) {
    srv = SECFailure;
    goto finish;
  }
  // add password integrity
  srv = SEC_PKCS12AddPasswordIntegrity(ecx, &unicodePw, SEC_OID_SHA1);
  if (srv) goto finish;

  for (size_t i=0; i<certs.size(); i++) {
    DCHECK(certs[i].get());
    CERTCertificate* nssCert = certs[i]->os_cert_handle();
    DCHECK(nssCert);

    // We only allow certificate and private key extraction if the corresponding
    // CKA_EXTRACTABLE private key attribute is set to CK_TRUE. Most hardware
    // tokens including smartcards enforce this behavior. An internal (soft)
    // token may ignore this attribute (and hence still be able to export) but
    // we still refuse to attempt an export.
    // In addition, some tokens may not support this attribute, in which case
    // we still attempt the export and let the token implementation dictate
    // the export behavior.
    if (nssCert->slot) {
      SECKEYPrivateKey *privKey=PK11_FindKeyByDERCert(nssCert->slot,
                                                      nssCert,
                                                      NULL);  // wincx
       if (privKey) {
        PRBool privKeyIsExtractable = PR_FALSE;
        SECStatus rv = isExtractable(privKey, &privKeyIsExtractable);
        SECKEY_DestroyPrivateKey(privKey);

        if (rv == SECSuccess && !privKeyIsExtractable) {
          LOG(ERROR) << "Private key is not extractable";
          continue;
        }
      }
    }

    // XXX this is why, to verify the slot is the same
    // PK11_FindObjectForCert(nssCert, NULL, slot);
    // create the cert and key safes
    keySafe = SEC_PKCS12CreateUnencryptedSafe(ecx);
    if (!SEC_PKCS12IsEncryptionAllowed() || PK11_IsFIPS()) {
      certSafe = keySafe;
    } else {
      certSafe = SEC_PKCS12CreatePasswordPrivSafe(ecx, &unicodePw,
                           SEC_OID_PKCS12_V2_PBE_WITH_SHA1_AND_40_BIT_RC2_CBC);
    }
    if (!certSafe || !keySafe) {
      LOG(ERROR) << "!certSafe || !keySafe " << certSafe << " " << keySafe;
      srv = SECFailure;
      goto finish;
    }
    // add the cert and key to the blob
    srv = SEC_PKCS12AddCertAndKey(ecx, certSafe, NULL, nssCert,
                                  CERT_GetDefaultCertDB(),
                                  keySafe, NULL, PR_TRUE, &unicodePw,
                      SEC_OID_PKCS12_V2_PBE_WITH_SHA1_AND_3KEY_TRIPLE_DES_CBC);
    if (srv) goto finish;
    ++numCertsExported;
  }

  if (!numCertsExported) goto finish;

  // encode and write
  srv = SEC_PKCS12Encode(ecx, write_export_data, output);
  if (srv) goto finish;
  return_count = numCertsExported;
finish:
  if (srv)
    LOG(ERROR) << "PKCS#12 export failed with error " << PORT_GetError();
  if (ecx)
    SEC_PKCS12DestroyExportContext(ecx);
  SECITEM_ZfreeItem(&unicodePw, PR_FALSE);
  return return_count;
}

}  // namespace mozilla_security_manager
