2016-04-20 15:49:00 +00:00
|
|
|
diff --git a/lib/nss/config.mk b/lib/nss/config.mk
|
|
|
|
--- a/lib/nss/config.mk
|
|
|
|
+++ b/lib/nss/config.mk
|
|
|
|
@@ -95,8 +95,12 @@ SHARED_LIBRARY_DIRS = \
|
|
|
|
ifeq (,$(filter-out WINNT WIN95,$(OS_TARGET)))
|
|
|
|
ifndef NS_USE_GCC
|
|
|
|
# Export 'mktemp' to be backward compatible with NSS 3.2.x and 3.3.x
|
|
|
|
# but do not put it in the import library. See bug 142575.
|
|
|
|
DEFINES += -DWIN32_NSS3_DLL_COMPAT
|
2016-03-24 22:18:49 +00:00
|
|
|
DLLFLAGS += -EXPORT:mktemp=nss_mktemp,PRIVATE
|
|
|
|
endif
|
|
|
|
endif
|
|
|
|
+
|
|
|
|
+ifdef POLICY_FILE
|
|
|
|
+DEFINES += -DPOLICY_FILE=\"$(POLICY_FILE)\" -DPOLICY_PATH=\"$(POLICY_PATH)\"
|
|
|
|
+endif
|
2016-04-20 15:49:00 +00:00
|
|
|
diff --git a/lib/nss/nssinit.c b/lib/nss/nssinit.c
|
|
|
|
--- a/lib/nss/nssinit.c
|
|
|
|
+++ b/lib/nss/nssinit.c
|
|
|
|
@@ -330,47 +330,47 @@ nss_FindExternalRoot(const char *dbpath,
|
|
|
|
|
|
|
|
/*
|
|
|
|
* see nss_Init for definitions of the various options.
|
|
|
|
*
|
|
|
|
* this function builds a moduleSpec string from the options and previously
|
2016-03-24 22:18:49 +00:00
|
|
|
* set statics (from PKCS11_Configure, for instance), and uses it to kick off
|
|
|
|
* the loading of the various PKCS #11 modules.
|
|
|
|
*/
|
|
|
|
-static SECStatus
|
|
|
|
+static SECMODModule *
|
|
|
|
nss_InitModules(const char *configdir, const char *certPrefix,
|
|
|
|
const char *keyPrefix, const char *secmodName,
|
|
|
|
const char *updateDir, const char *updCertPrefix,
|
2016-04-20 15:49:00 +00:00
|
|
|
const char *updKeyPrefix, const char *updateID,
|
|
|
|
const char *updateName, char *configName, char *configStrings,
|
|
|
|
PRBool pwRequired, PRBool readOnly, PRBool noCertDB,
|
2016-03-24 22:18:49 +00:00
|
|
|
PRBool noModDB, PRBool forceOpen, PRBool optimizeSpace,
|
|
|
|
PRBool isContextInit)
|
|
|
|
{
|
|
|
|
- SECStatus rv = SECFailure;
|
|
|
|
+ SECMODModule *module = NULL;
|
|
|
|
char *moduleSpec = NULL;
|
|
|
|
char *flags = NULL;
|
|
|
|
char *lconfigdir = NULL;
|
2016-04-20 15:49:00 +00:00
|
|
|
char *lcertPrefix = NULL;
|
|
|
|
char *lkeyPrefix = NULL;
|
|
|
|
char *lsecmodName = NULL;
|
|
|
|
char *lupdateDir = NULL;
|
|
|
|
char *lupdCertPrefix = NULL;
|
|
|
|
char *lupdKeyPrefix = NULL;
|
|
|
|
char *lupdateID = NULL;
|
|
|
|
char *lupdateName = NULL;
|
2016-03-24 22:18:49 +00:00
|
|
|
|
|
|
|
if (NSS_InitializePRErrorTable() != SECSuccess) {
|
|
|
|
PORT_SetError(SEC_ERROR_NO_MEMORY);
|
|
|
|
- return rv;
|
|
|
|
+ return NULL;
|
|
|
|
}
|
|
|
|
|
|
|
|
flags = nss_makeFlags(readOnly,noCertDB,noModDB,forceOpen,
|
|
|
|
pwRequired, optimizeSpace);
|
|
|
|
- if (flags == NULL) return rv;
|
|
|
|
+ if (flags == NULL) return NULL;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* configdir is double nested, and Windows uses the same character
|
2016-04-20 15:49:00 +00:00
|
|
|
* for file seps as we use for escapes! (sigh).
|
|
|
|
*/
|
|
|
|
lconfigdir = NSSUTIL_DoubleEscape(configdir, '\'', '\"');
|
|
|
|
if (lconfigdir == NULL) {
|
|
|
|
goto loser;
|
|
|
|
@@ -427,24 +427,26 @@ loser:
|
|
|
|
if (lsecmodName) PORT_Free(lsecmodName);
|
|
|
|
if (lupdateDir) PORT_Free(lupdateDir);
|
|
|
|
if (lupdCertPrefix) PORT_Free(lupdCertPrefix);
|
|
|
|
if (lupdKeyPrefix) PORT_Free(lupdKeyPrefix);
|
|
|
|
if (lupdateID) PORT_Free(lupdateID);
|
2016-03-24 22:18:49 +00:00
|
|
|
if (lupdateName) PORT_Free(lupdateName);
|
|
|
|
|
|
|
|
if (moduleSpec) {
|
|
|
|
- SECMODModule *module = SECMOD_LoadModule(moduleSpec,NULL,PR_TRUE);
|
|
|
|
+ module = SECMOD_LoadModule(moduleSpec,NULL,PR_TRUE);
|
|
|
|
PR_smprintf_free(moduleSpec);
|
|
|
|
if (module) {
|
|
|
|
- if (module->loaded) rv=SECSuccess;
|
|
|
|
- SECMOD_DestroyModule(module);
|
|
|
|
+ if (!module->loaded) {
|
|
|
|
+ SECMOD_DestroyModule(module);
|
|
|
|
+ module = NULL;
|
|
|
|
+ }
|
|
|
|
}
|
|
|
|
}
|
|
|
|
- return rv;
|
|
|
|
+ return module;
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
2016-04-20 15:49:00 +00:00
|
|
|
* OK there are now lots of options here, lets go through them all:
|
|
|
|
*
|
|
|
|
* configdir - base directory where all the cert, key, and module datbases live.
|
|
|
|
* certPrefix - prefix added to the beginning of the cert database example: "
|
|
|
|
* "https-server1-"
|
|
|
|
@@ -520,17 +522,17 @@ nss_Init(const char *configdir, const ch
|
|
|
|
NSSInitContext ** initContextPtr,
|
|
|
|
NSSInitParameters *initParams,
|
|
|
|
PRBool readOnly, PRBool noCertDB,
|
|
|
|
PRBool noModDB, PRBool forceOpen, PRBool noRootInit,
|
|
|
|
PRBool optimizeSpace, PRBool noSingleThreadedModules,
|
2016-03-24 22:18:49 +00:00
|
|
|
PRBool allowAlreadyInitializedModules,
|
|
|
|
PRBool dontFinalizeModules)
|
|
|
|
{
|
|
|
|
- SECStatus rv = SECFailure;
|
|
|
|
+ SECMODModule *parent = NULL;
|
|
|
|
PKIX_UInt32 actualMinorVersion = 0;
|
|
|
|
PKIX_Error *pkixError = NULL;
|
|
|
|
PRBool isReallyInitted;
|
2016-04-20 15:49:00 +00:00
|
|
|
char *configStrings = NULL;
|
|
|
|
char *configName = NULL;
|
|
|
|
PRBool passwordRequired = PR_FALSE;
|
|
|
|
|
|
|
|
/* if we are trying to init with a traditional NSS_Init call, maintain
|
|
|
|
@@ -630,23 +632,23 @@ nss_Init(const char *configdir, const ch
|
|
|
|
configStrings = pk11_config_strings;
|
|
|
|
configName = pk11_config_name;
|
|
|
|
passwordRequired = pk11_password_required;
|
|
|
|
}
|
|
|
|
|
2016-03-24 22:18:49 +00:00
|
|
|
/* Skip the module init if we are already initted and we are trying
|
|
|
|
* to init with noCertDB and noModDB */
|
|
|
|
if (!(isReallyInitted && noCertDB && noModDB)) {
|
|
|
|
- rv = nss_InitModules(configdir, certPrefix, keyPrefix, secmodName,
|
|
|
|
+ parent = nss_InitModules(configdir, certPrefix, keyPrefix, secmodName,
|
|
|
|
updateDir, updCertPrefix, updKeyPrefix, updateID,
|
|
|
|
updateName, configName, configStrings, passwordRequired,
|
|
|
|
readOnly, noCertDB, noModDB, forceOpen, optimizeSpace,
|
|
|
|
(initContextPtr != NULL));
|
|
|
|
|
|
|
|
- if (rv != SECSuccess) {
|
|
|
|
+ if (parent == NULL) {
|
|
|
|
goto loser;
|
|
|
|
}
|
|
|
|
}
|
2016-04-20 15:49:00 +00:00
|
|
|
|
|
|
|
|
|
|
|
/* finish up initialization */
|
|
|
|
if (!isReallyInitted) {
|
|
|
|
if (SECOID_Init() != SECSuccess) {
|
|
|
|
@@ -675,17 +677,34 @@ nss_Init(const char *configdir, const ch
|
|
|
|
* path. Skip it */
|
|
|
|
dbpath = NULL;
|
|
|
|
}
|
|
|
|
if (dbpath) {
|
|
|
|
nss_FindExternalRoot(dbpath, secmodName);
|
2016-03-24 22:18:49 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
-
|
|
|
|
+#ifdef POLICY_FILE
|
|
|
|
+ if (PR_Access(POLICY_PATH "/" POLICY_FILE, PR_ACCESS_READ_OK) == PR_SUCCESS ) {
|
|
|
|
+ SECMODModule *module = SECMOD_LoadModule(
|
|
|
|
+ "name=\"Policy File\" "
|
|
|
|
+ "parameters=\"configdir='sql:" POLICY_PATH "' "
|
|
|
|
+ "secmod='" POLICY_FILE "' "
|
|
|
|
+ "flags=readOnly,noCertDB,forceSecmodChoice,forceOpen\" "
|
|
|
|
+ "NSS=\"flags=internal,moduleDB,skipFirst,moduleDBOnly,critical\"",
|
|
|
|
+ parent, PR_TRUE);
|
|
|
|
+ if (module) {
|
|
|
|
+ PRBool isLoaded = module->loaded;
|
|
|
|
+ SECMOD_DestroyModule(module);
|
|
|
|
+ if (!isLoaded) {
|
|
|
|
+ goto loser;
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+ }
|
|
|
|
+#endif
|
|
|
|
pk11sdr_Init();
|
|
|
|
cert_CreateSubjectKeyIDHashTable();
|
|
|
|
|
2016-04-20 15:49:00 +00:00
|
|
|
pkixError = PKIX_Initialize
|
|
|
|
(PKIX_FALSE, PKIX_MAJOR_VERSION, PKIX_MINOR_VERSION,
|
|
|
|
PKIX_MINOR_VERSION, &actualMinorVersion, &plContext);
|
|
|
|
|
|
|
|
if (pkixError != NULL) {
|
|
|
|
@@ -716,32 +735,38 @@ nss_Init(const char *configdir, const ch
|
|
|
|
nssIsInInit--;
|
|
|
|
/* now that we are inited, all waiters can move forward */
|
|
|
|
PZ_NotifyAllCondVar(nssInitCondition);
|
|
|
|
PZ_Unlock(nssInitLock);
|
|
|
|
|
2016-03-24 22:18:49 +00:00
|
|
|
if (initContextPtr && configStrings) {
|
|
|
|
PR_smprintf_free(configStrings);
|
|
|
|
}
|
|
|
|
+ if (parent) {
|
|
|
|
+ SECMOD_DestroyModule(parent);
|
|
|
|
+ }
|
|
|
|
|
|
|
|
return SECSuccess;
|
|
|
|
|
2016-04-20 15:49:00 +00:00
|
|
|
loser:
|
|
|
|
if (initContextPtr && *initContextPtr) {
|
|
|
|
PORT_Free(*initContextPtr);
|
|
|
|
*initContextPtr = NULL;
|
|
|
|
if (configStrings) {
|
|
|
|
PR_smprintf_free(configStrings);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
PZ_Lock(nssInitLock);
|
|
|
|
nssIsInInit--;
|
2016-03-24 22:18:49 +00:00
|
|
|
/* We failed to init, allow one to move forward */
|
|
|
|
PZ_NotifyCondVar(nssInitCondition);
|
|
|
|
PZ_Unlock(nssInitLock);
|
|
|
|
+ if (parent) {
|
|
|
|
+ SECMOD_DestroyModule(parent);
|
|
|
|
+ }
|
|
|
|
return SECFailure;
|
|
|
|
}
|
|
|
|
|
2016-04-20 15:49:00 +00:00
|
|
|
|
|
|
|
SECStatus
|
|
|
|
NSS_Init(const char *configdir)
|
|
|
|
{
|
|
|
|
return nss_Init(configdir, "", "", SECMOD_DB, "", "", "", "", "", NULL,
|
|
|
|
diff --git a/lib/pk11wrap/pk11pars.c b/lib/pk11wrap/pk11pars.c
|
|
|
|
--- a/lib/pk11wrap/pk11pars.c
|
|
|
|
+++ b/lib/pk11wrap/pk11pars.c
|
|
|
|
@@ -105,16 +105,17 @@ secmod_NewModule(void)
|
|
|
|
* This allows system NSS to delegate those changes to the user's module DB,
|
|
|
|
* preserving the user's ability to load new PKCS #11 modules (which only
|
|
|
|
* affect him), from existing applications like Firefox.
|
|
|
|
*/
|
|
|
|
#define SECMOD_FLAG_MODULE_DB_IS_MODULE_DB 0x01 /* must be set if any of the
|
2016-03-24 22:18:49 +00:00
|
|
|
*other flags are set */
|
|
|
|
#define SECMOD_FLAG_MODULE_DB_SKIP_FIRST 0x02
|
|
|
|
#define SECMOD_FLAG_MODULE_DB_DEFAULT_MODDB 0x04
|
|
|
|
+#define SECMOD_FLAG_MODULE_DB_POLICY_ONLY 0x08
|
|
|
|
|
|
|
|
|
|
|
|
/* private flags for internal (field in SECMODModule). */
|
2016-04-20 15:49:00 +00:00
|
|
|
/* The meaing of these flags is as follows:
|
|
|
|
*
|
|
|
|
* SECMOD_FLAG_INTERNAL_IS_INTERNAL - This is a marks the the module is
|
|
|
|
* the internal module (that is, softoken). This bit is the same as the
|
|
|
|
* already existing meaning of internal = PR_TRUE. None of the other
|
|
|
|
@@ -699,16 +700,19 @@ SECMOD_CreateModuleEx(const char *librar
|
|
|
|
if (mod->isModuleDB) {
|
|
|
|
char flags = SECMOD_FLAG_MODULE_DB_IS_MODULE_DB;
|
|
|
|
if (NSSUTIL_ArgHasFlag("flags","skipFirst",nssc)) {
|
|
|
|
flags |= SECMOD_FLAG_MODULE_DB_SKIP_FIRST;
|
|
|
|
}
|
2016-03-24 22:18:49 +00:00
|
|
|
if (NSSUTIL_ArgHasFlag("flags","defaultModDB",nssc)) {
|
|
|
|
flags |= SECMOD_FLAG_MODULE_DB_DEFAULT_MODDB;
|
|
|
|
}
|
2016-04-20 15:49:00 +00:00
|
|
|
+ if (NSSUTIL_ArgHasFlag("flags", "policyOnly", nssc)) {
|
2016-03-24 22:18:49 +00:00
|
|
|
+ flags |= SECMOD_FLAG_MODULE_DB_POLICY_ONLY;
|
|
|
|
+ }
|
|
|
|
/* additional moduleDB flags could be added here in the future */
|
|
|
|
mod->isModuleDB = (PRBool) flags;
|
|
|
|
}
|
2016-04-20 15:49:00 +00:00
|
|
|
|
|
|
|
if (mod->internal) {
|
|
|
|
char flags = SECMOD_FLAG_INTERNAL_IS_INTERNAL;
|
|
|
|
|
|
|
|
if (NSSUTIL_ArgHasFlag("flags", "internalKeySlot", nssc)) {
|
|
|
|
@@ -738,16 +742,24 @@ PRBool
|
|
|
|
SECMOD_GetDefaultModDBFlag(SECMODModule *mod)
|
|
|
|
{
|
|
|
|
char flags = (char) mod->isModuleDB;
|
|
|
|
|
|
|
|
return (flags & SECMOD_FLAG_MODULE_DB_DEFAULT_MODDB) ? PR_TRUE : PR_FALSE;
|
2016-03-24 22:18:49 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
PRBool
|
|
|
|
+secmod_PolicyOnly(SECMODModule *mod)
|
|
|
|
+{
|
|
|
|
+ char flags = (char) mod->isModuleDB;
|
|
|
|
+
|
|
|
|
+ return (flags & SECMOD_FLAG_MODULE_DB_POLICY_ONLY) ? PR_TRUE : PR_FALSE;
|
|
|
|
+}
|
|
|
|
+
|
|
|
|
+PRBool
|
|
|
|
secmod_IsInternalKeySlot(SECMODModule *mod)
|
|
|
|
{
|
|
|
|
char flags = (char) mod->internal;
|
2016-04-20 15:49:00 +00:00
|
|
|
|
|
|
|
return (flags & SECMOD_FLAG_INTERNAL_KEY_SLOT) ? PR_TRUE : PR_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
@@ -1521,16 +1533,22 @@ SECMOD_LoadModule(char *modulespec,SECMO
|
|
|
|
if (library) PORT_Free(library);
|
|
|
|
if (moduleName) PORT_Free(moduleName);
|
|
|
|
if (parameters) PORT_Free(parameters);
|
|
|
|
if (nss) PORT_Free(nss);
|
|
|
|
if (config) PORT_Free(config);
|
2016-03-24 22:18:49 +00:00
|
|
|
if (!module) {
|
|
|
|
goto loser;
|
|
|
|
}
|
|
|
|
+
|
|
|
|
+ /* a policy only stanza doesn't actually get 'loaded'. policy has already
|
|
|
|
+ * been parsed as a side effect of the CreateModuleEx call */
|
|
|
|
+ if (secmod_PolicyOnly(module)) {
|
|
|
|
+ return module;
|
|
|
|
+ }
|
|
|
|
if (parent) {
|
|
|
|
module->parent = SECMOD_ReferenceModule(parent);
|
|
|
|
if (module->internal && secmod_IsInternalKeySlot(parent)) {
|
2016-04-20 15:49:00 +00:00
|
|
|
module->internal = parent->internal;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
/* load it */
|
|
|
|
diff --git a/lib/util/utilpars.c b/lib/util/utilpars.c
|
|
|
|
--- a/lib/util/utilpars.c
|
|
|
|
+++ b/lib/util/utilpars.c
|
|
|
|
@@ -1139,17 +1139,18 @@ char *
|
|
|
|
*dbType = NSS_DB_TYPE_SQL;
|
|
|
|
PORT_Free(*filename);
|
|
|
|
*filename = NULL;
|
|
|
|
*rw = PR_FALSE;
|
|
|
|
}
|
|
|
|
|
|
|
|
/* only use the renamed secmod for legacy databases */
|
|
|
|
if ((*dbType != NSS_DB_TYPE_LEGACY) &&
|
|
|
|
- (*dbType != NSS_DB_TYPE_MULTIACCESS)) {
|
|
|
|
+ (*dbType != NSS_DB_TYPE_MULTIACCESS) &&
|
|
|
|
+ !NSSUTIL_ArgHasFlag("flags", "forceSecmodChoice", save_params)) {
|
|
|
|
secmodName="pkcs11.txt";
|
|
|
|
}
|
|
|
|
|
|
|
|
if (noModDB) {
|
|
|
|
value = NULL;
|
|
|
|
} else if (lconfigdir && lconfigdir[0] != '\0') {
|
|
|
|
value = PR_smprintf("%s" NSSUTIL_PATH_SEPARATOR "%s",
|
|
|
|
lconfigdir,secmodName);
|