You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@couchdb.apache.org by ga...@apache.org on 2015/10/14 12:09:21 UTC
[24/52] [partial] couchdb-nmo git commit: prepare for release
http://git-wip-us.apache.org/repos/asf/couchdb-nmo/blob/753f1767/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/build/gyp-mac-tool
----------------------------------------------------------------------
diff --git a/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/build/gyp-mac-tool b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/build/gyp-mac-tool
new file mode 100755
index 0000000..976c598
--- /dev/null
+++ b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/build/gyp-mac-tool
@@ -0,0 +1,612 @@
+#!/usr/bin/env python
+# Generated by gyp. Do not edit.
+# Copyright (c) 2012 Google Inc. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+"""Utility functions to perform Xcode-style build steps.
+
+These functions are executed via gyp-mac-tool when using the Makefile generator.
+"""
+
+import fcntl
+import fnmatch
+import glob
+import json
+import os
+import plistlib
+import re
+import shutil
+import string
+import subprocess
+import sys
+import tempfile
+
+
+def main(args):
+ executor = MacTool()
+ exit_code = executor.Dispatch(args)
+ if exit_code is not None:
+ sys.exit(exit_code)
+
+
+class MacTool(object):
+ """This class performs all the Mac tooling steps. The methods can either be
+ executed directly, or dispatched from an argument list."""
+
+ def Dispatch(self, args):
+ """Dispatches a string command to a method."""
+ if len(args) < 1:
+ raise Exception("Not enough arguments")
+
+ method = "Exec%s" % self._CommandifyName(args[0])
+ return getattr(self, method)(*args[1:])
+
+ def _CommandifyName(self, name_string):
+ """Transforms a tool name like copy-info-plist to CopyInfoPlist"""
+ return name_string.title().replace('-', '')
+
+ def ExecCopyBundleResource(self, source, dest, convert_to_binary):
+ """Copies a resource file to the bundle/Resources directory, performing any
+ necessary compilation on each resource."""
+ extension = os.path.splitext(source)[1].lower()
+ if os.path.isdir(source):
+ # Copy tree.
+ # TODO(thakis): This copies file attributes like mtime, while the
+ # single-file branch below doesn't. This should probably be changed to
+ # be consistent with the single-file branch.
+ if os.path.exists(dest):
+ shutil.rmtree(dest)
+ shutil.copytree(source, dest)
+ elif extension == '.xib':
+ return self._CopyXIBFile(source, dest)
+ elif extension == '.storyboard':
+ return self._CopyXIBFile(source, dest)
+ elif extension == '.strings':
+ self._CopyStringsFile(source, dest, convert_to_binary)
+ else:
+ shutil.copy(source, dest)
+
+ def _CopyXIBFile(self, source, dest):
+ """Compiles a XIB file with ibtool into a binary plist in the bundle."""
+
+ # ibtool sometimes crashes with relative paths. See crbug.com/314728.
+ base = os.path.dirname(os.path.realpath(__file__))
+ if os.path.relpath(source):
+ source = os.path.join(base, source)
+ if os.path.relpath(dest):
+ dest = os.path.join(base, dest)
+
+ args = ['xcrun', 'ibtool', '--errors', '--warnings', '--notices',
+ '--output-format', 'human-readable-text', '--compile', dest, source]
+ ibtool_section_re = re.compile(r'/\*.*\*/')
+ ibtool_re = re.compile(r'.*note:.*is clipping its content')
+ ibtoolout = subprocess.Popen(args, stdout=subprocess.PIPE)
+ current_section_header = None
+ for line in ibtoolout.stdout:
+ if ibtool_section_re.match(line):
+ current_section_header = line
+ elif not ibtool_re.match(line):
+ if current_section_header:
+ sys.stdout.write(current_section_header)
+ current_section_header = None
+ sys.stdout.write(line)
+ return ibtoolout.returncode
+
+ def _ConvertToBinary(self, dest):
+ subprocess.check_call([
+ 'xcrun', 'plutil', '-convert', 'binary1', '-o', dest, dest])
+
+ def _CopyStringsFile(self, source, dest, convert_to_binary):
+ """Copies a .strings file using iconv to reconvert the input into UTF-16."""
+ input_code = self._DetectInputEncoding(source) or "UTF-8"
+
+ # Xcode's CpyCopyStringsFile / builtin-copyStrings seems to call
+ # CFPropertyListCreateFromXMLData() behind the scenes; at least it prints
+ # CFPropertyListCreateFromXMLData(): Old-style plist parser: missing
+ # semicolon in dictionary.
+ # on invalid files. Do the same kind of validation.
+ import CoreFoundation
+ s = open(source, 'rb').read()
+ d = CoreFoundation.CFDataCreate(None, s, len(s))
+ _, error = CoreFoundation.CFPropertyListCreateFromXMLData(None, d, 0, None)
+ if error:
+ return
+
+ fp = open(dest, 'wb')
+ fp.write(s.decode(input_code).encode('UTF-16'))
+ fp.close()
+
+ if convert_to_binary == 'True':
+ self._ConvertToBinary(dest)
+
+ def _DetectInputEncoding(self, file_name):
+ """Reads the first few bytes from file_name and tries to guess the text
+ encoding. Returns None as a guess if it can't detect it."""
+ fp = open(file_name, 'rb')
+ try:
+ header = fp.read(3)
+ except e:
+ fp.close()
+ return None
+ fp.close()
+ if header.startswith("\xFE\xFF"):
+ return "UTF-16"
+ elif header.startswith("\xFF\xFE"):
+ return "UTF-16"
+ elif header.startswith("\xEF\xBB\xBF"):
+ return "UTF-8"
+ else:
+ return None
+
+ def ExecCopyInfoPlist(self, source, dest, convert_to_binary, *keys):
+ """Copies the |source| Info.plist to the destination directory |dest|."""
+ # Read the source Info.plist into memory.
+ fd = open(source, 'r')
+ lines = fd.read()
+ fd.close()
+
+ # Insert synthesized key/value pairs (e.g. BuildMachineOSBuild).
+ plist = plistlib.readPlistFromString(lines)
+ if keys:
+ plist = dict(plist.items() + json.loads(keys[0]).items())
+ lines = plistlib.writePlistToString(plist)
+
+ # Go through all the environment variables and replace them as variables in
+ # the file.
+ IDENT_RE = re.compile(r'[/\s]')
+ for key in os.environ:
+ if key.startswith('_'):
+ continue
+ evar = '${%s}' % key
+ evalue = os.environ[key]
+ lines = string.replace(lines, evar, evalue)
+
+ # Xcode supports various suffices on environment variables, which are
+ # all undocumented. :rfc1034identifier is used in the standard project
+ # template these days, and :identifier was used earlier. They are used to
+ # convert non-url characters into things that look like valid urls --
+ # except that the replacement character for :identifier, '_' isn't valid
+ # in a URL either -- oops, hence :rfc1034identifier was born.
+ evar = '${%s:identifier}' % key
+ evalue = IDENT_RE.sub('_', os.environ[key])
+ lines = string.replace(lines, evar, evalue)
+
+ evar = '${%s:rfc1034identifier}' % key
+ evalue = IDENT_RE.sub('-', os.environ[key])
+ lines = string.replace(lines, evar, evalue)
+
+ # Remove any keys with values that haven't been replaced.
+ lines = lines.split('\n')
+ for i in range(len(lines)):
+ if lines[i].strip().startswith("<string>${"):
+ lines[i] = None
+ lines[i - 1] = None
+ lines = '\n'.join(filter(lambda x: x is not None, lines))
+
+ # Write out the file with variables replaced.
+ fd = open(dest, 'w')
+ fd.write(lines)
+ fd.close()
+
+ # Now write out PkgInfo file now that the Info.plist file has been
+ # "compiled".
+ self._WritePkgInfo(dest)
+
+ if convert_to_binary == 'True':
+ self._ConvertToBinary(dest)
+
+ def _WritePkgInfo(self, info_plist):
+ """This writes the PkgInfo file from the data stored in Info.plist."""
+ plist = plistlib.readPlist(info_plist)
+ if not plist:
+ return
+
+ # Only create PkgInfo for executable types.
+ package_type = plist['CFBundlePackageType']
+ if package_type != 'APPL':
+ return
+
+ # The format of PkgInfo is eight characters, representing the bundle type
+ # and bundle signature, each four characters. If that is missing, four
+ # '?' characters are used instead.
+ signature_code = plist.get('CFBundleSignature', '????')
+ if len(signature_code) != 4: # Wrong length resets everything, too.
+ signature_code = '?' * 4
+
+ dest = os.path.join(os.path.dirname(info_plist), 'PkgInfo')
+ fp = open(dest, 'w')
+ fp.write('%s%s' % (package_type, signature_code))
+ fp.close()
+
+ def ExecFlock(self, lockfile, *cmd_list):
+ """Emulates the most basic behavior of Linux's flock(1)."""
+ # Rely on exception handling to report errors.
+ fd = os.open(lockfile, os.O_RDONLY|os.O_NOCTTY|os.O_CREAT, 0o666)
+ fcntl.flock(fd, fcntl.LOCK_EX)
+ return subprocess.call(cmd_list)
+
+ def ExecFilterLibtool(self, *cmd_list):
+ """Calls libtool and filters out '/path/to/libtool: file: foo.o has no
+ symbols'."""
+ libtool_re = re.compile(r'^.*libtool: file: .* has no symbols$')
+ libtool_re5 = re.compile(
+ r'^.*libtool: warning for library: ' +
+ r'.* the table of contents is empty ' +
+ r'\(no object file members in the library define global symbols\)$')
+ env = os.environ.copy()
+ # Ref:
+ # http://www.opensource.apple.com/source/cctools/cctools-809/misc/libtool.c
+ # The problem with this flag is that it resets the file mtime on the file to
+ # epoch=0, e.g. 1970-1-1 or 1969-12-31 depending on timezone.
+ env['ZERO_AR_DATE'] = '1'
+ libtoolout = subprocess.Popen(cmd_list, stderr=subprocess.PIPE, env=env)
+ _, err = libtoolout.communicate()
+ for line in err.splitlines():
+ if not libtool_re.match(line) and not libtool_re5.match(line):
+ print >>sys.stderr, line
+ # Unconditionally touch the output .a file on the command line if present
+ # and the command succeeded. A bit hacky.
+ if not libtoolout.returncode:
+ for i in range(len(cmd_list) - 1):
+ if cmd_list[i] == "-o" and cmd_list[i+1].endswith('.a'):
+ os.utime(cmd_list[i+1], None)
+ break
+ return libtoolout.returncode
+
+ def ExecPackageFramework(self, framework, version):
+ """Takes a path to Something.framework and the Current version of that and
+ sets up all the symlinks."""
+ # Find the name of the binary based on the part before the ".framework".
+ binary = os.path.basename(framework).split('.')[0]
+
+ CURRENT = 'Current'
+ RESOURCES = 'Resources'
+ VERSIONS = 'Versions'
+
+ if not os.path.exists(os.path.join(framework, VERSIONS, version, binary)):
+ # Binary-less frameworks don't seem to contain symlinks (see e.g.
+ # chromium's out/Debug/org.chromium.Chromium.manifest/ bundle).
+ return
+
+ # Move into the framework directory to set the symlinks correctly.
+ pwd = os.getcwd()
+ os.chdir(framework)
+
+ # Set up the Current version.
+ self._Relink(version, os.path.join(VERSIONS, CURRENT))
+
+ # Set up the root symlinks.
+ self._Relink(os.path.join(VERSIONS, CURRENT, binary), binary)
+ self._Relink(os.path.join(VERSIONS, CURRENT, RESOURCES), RESOURCES)
+
+ # Back to where we were before!
+ os.chdir(pwd)
+
+ def _Relink(self, dest, link):
+ """Creates a symlink to |dest| named |link|. If |link| already exists,
+ it is overwritten."""
+ if os.path.lexists(link):
+ os.remove(link)
+ os.symlink(dest, link)
+
+ def ExecCompileXcassets(self, keys, *inputs):
+ """Compiles multiple .xcassets files into a single .car file.
+
+ This invokes 'actool' to compile all the inputs .xcassets files. The
+ |keys| arguments is a json-encoded dictionary of extra arguments to
+ pass to 'actool' when the asset catalogs contains an application icon
+ or a launch image.
+
+ Note that 'actool' does not create the Assets.car file if the asset
+ catalogs does not contains imageset.
+ """
+ command_line = [
+ 'xcrun', 'actool', '--output-format', 'human-readable-text',
+ '--compress-pngs', '--notices', '--warnings', '--errors',
+ ]
+ is_iphone_target = 'IPHONEOS_DEPLOYMENT_TARGET' in os.environ
+ if is_iphone_target:
+ platform = os.environ['CONFIGURATION'].split('-')[-1]
+ if platform not in ('iphoneos', 'iphonesimulator'):
+ platform = 'iphonesimulator'
+ command_line.extend([
+ '--platform', platform, '--target-device', 'iphone',
+ '--target-device', 'ipad', '--minimum-deployment-target',
+ os.environ['IPHONEOS_DEPLOYMENT_TARGET'], '--compile',
+ os.path.abspath(os.environ['CONTENTS_FOLDER_PATH']),
+ ])
+ else:
+ command_line.extend([
+ '--platform', 'macosx', '--target-device', 'mac',
+ '--minimum-deployment-target', os.environ['MACOSX_DEPLOYMENT_TARGET'],
+ '--compile',
+ os.path.abspath(os.environ['UNLOCALIZED_RESOURCES_FOLDER_PATH']),
+ ])
+ if keys:
+ keys = json.loads(keys)
+ for key, value in keys.iteritems():
+ arg_name = '--' + key
+ if isinstance(value, bool):
+ if value:
+ command_line.append(arg_name)
+ elif isinstance(value, list):
+ for v in value:
+ command_line.append(arg_name)
+ command_line.append(str(v))
+ else:
+ command_line.append(arg_name)
+ command_line.append(str(value))
+ # Note: actool crashes if inputs path are relative, so use os.path.abspath
+ # to get absolute path name for inputs.
+ command_line.extend(map(os.path.abspath, inputs))
+ subprocess.check_call(command_line)
+
+ def ExecMergeInfoPlist(self, output, *inputs):
+ """Merge multiple .plist files into a single .plist file."""
+ merged_plist = {}
+ for path in inputs:
+ plist = self._LoadPlistMaybeBinary(path)
+ self._MergePlist(merged_plist, plist)
+ plistlib.writePlist(merged_plist, output)
+
+ def ExecCodeSignBundle(self, key, resource_rules, entitlements, provisioning):
+ """Code sign a bundle.
+
+ This function tries to code sign an iOS bundle, following the same
+ algorithm as Xcode:
+ 1. copy ResourceRules.plist from the user or the SDK into the bundle,
+ 2. pick the provisioning profile that best match the bundle identifier,
+ and copy it into the bundle as embedded.mobileprovision,
+ 3. copy Entitlements.plist from user or SDK next to the bundle,
+ 4. code sign the bundle.
+ """
+ resource_rules_path = self._InstallResourceRules(resource_rules)
+ substitutions, overrides = self._InstallProvisioningProfile(
+ provisioning, self._GetCFBundleIdentifier())
+ entitlements_path = self._InstallEntitlements(
+ entitlements, substitutions, overrides)
+ subprocess.check_call([
+ 'codesign', '--force', '--sign', key, '--resource-rules',
+ resource_rules_path, '--entitlements', entitlements_path,
+ os.path.join(
+ os.environ['TARGET_BUILD_DIR'],
+ os.environ['FULL_PRODUCT_NAME'])])
+
+ def _InstallResourceRules(self, resource_rules):
+ """Installs ResourceRules.plist from user or SDK into the bundle.
+
+ Args:
+ resource_rules: string, optional, path to the ResourceRules.plist file
+ to use, default to "${SDKROOT}/ResourceRules.plist"
+
+ Returns:
+ Path to the copy of ResourceRules.plist into the bundle.
+ """
+ source_path = resource_rules
+ target_path = os.path.join(
+ os.environ['BUILT_PRODUCTS_DIR'],
+ os.environ['CONTENTS_FOLDER_PATH'],
+ 'ResourceRules.plist')
+ if not source_path:
+ source_path = os.path.join(
+ os.environ['SDKROOT'], 'ResourceRules.plist')
+ shutil.copy2(source_path, target_path)
+ return target_path
+
+ def _InstallProvisioningProfile(self, profile, bundle_identifier):
+ """Installs embedded.mobileprovision into the bundle.
+
+ Args:
+ profile: string, optional, short name of the .mobileprovision file
+ to use, if empty or the file is missing, the best file installed
+ will be used
+ bundle_identifier: string, value of CFBundleIdentifier from Info.plist
+
+ Returns:
+ A tuple containing two dictionary: variables substitutions and values
+ to overrides when generating the entitlements file.
+ """
+ source_path, provisioning_data, team_id = self._FindProvisioningProfile(
+ profile, bundle_identifier)
+ target_path = os.path.join(
+ os.environ['BUILT_PRODUCTS_DIR'],
+ os.environ['CONTENTS_FOLDER_PATH'],
+ 'embedded.mobileprovision')
+ shutil.copy2(source_path, target_path)
+ substitutions = self._GetSubstitutions(bundle_identifier, team_id + '.')
+ return substitutions, provisioning_data['Entitlements']
+
+ def _FindProvisioningProfile(self, profile, bundle_identifier):
+ """Finds the .mobileprovision file to use for signing the bundle.
+
+ Checks all the installed provisioning profiles (or if the user specified
+ the PROVISIONING_PROFILE variable, only consult it) and select the most
+ specific that correspond to the bundle identifier.
+
+ Args:
+ profile: string, optional, short name of the .mobileprovision file
+ to use, if empty or the file is missing, the best file installed
+ will be used
+ bundle_identifier: string, value of CFBundleIdentifier from Info.plist
+
+ Returns:
+ A tuple of the path to the selected provisioning profile, the data of
+ the embedded plist in the provisioning profile and the team identifier
+ to use for code signing.
+
+ Raises:
+ SystemExit: if no .mobileprovision can be used to sign the bundle.
+ """
+ profiles_dir = os.path.join(
+ os.environ['HOME'], 'Library', 'MobileDevice', 'Provisioning Profiles')
+ if not os.path.isdir(profiles_dir):
+ print >>sys.stderr, (
+ 'cannot find mobile provisioning for %s' % bundle_identifier)
+ sys.exit(1)
+ provisioning_profiles = None
+ if profile:
+ profile_path = os.path.join(profiles_dir, profile + '.mobileprovision')
+ if os.path.exists(profile_path):
+ provisioning_profiles = [profile_path]
+ if not provisioning_profiles:
+ provisioning_profiles = glob.glob(
+ os.path.join(profiles_dir, '*.mobileprovision'))
+ valid_provisioning_profiles = {}
+ for profile_path in provisioning_profiles:
+ profile_data = self._LoadProvisioningProfile(profile_path)
+ app_id_pattern = profile_data.get(
+ 'Entitlements', {}).get('application-identifier', '')
+ for team_identifier in profile_data.get('TeamIdentifier', []):
+ app_id = '%s.%s' % (team_identifier, bundle_identifier)
+ if fnmatch.fnmatch(app_id, app_id_pattern):
+ valid_provisioning_profiles[app_id_pattern] = (
+ profile_path, profile_data, team_identifier)
+ if not valid_provisioning_profiles:
+ print >>sys.stderr, (
+ 'cannot find mobile provisioning for %s' % bundle_identifier)
+ sys.exit(1)
+ # If the user has multiple provisioning profiles installed that can be
+ # used for ${bundle_identifier}, pick the most specific one (ie. the
+ # provisioning profile whose pattern is the longest).
+ selected_key = max(valid_provisioning_profiles, key=lambda v: len(v))
+ return valid_provisioning_profiles[selected_key]
+
+ def _LoadProvisioningProfile(self, profile_path):
+ """Extracts the plist embedded in a provisioning profile.
+
+ Args:
+ profile_path: string, path to the .mobileprovision file
+
+ Returns:
+ Content of the plist embedded in the provisioning profile as a dictionary.
+ """
+ with tempfile.NamedTemporaryFile() as temp:
+ subprocess.check_call([
+ 'security', 'cms', '-D', '-i', profile_path, '-o', temp.name])
+ return self._LoadPlistMaybeBinary(temp.name)
+
+ def _MergePlist(self, merged_plist, plist):
+ """Merge |plist| into |merged_plist|."""
+ for key, value in plist.iteritems():
+ if isinstance(value, dict):
+ merged_value = merged_plist.get(key, {})
+ if isinstance(merged_value, dict):
+ self._MergePlist(merged_value, value)
+ merged_plist[key] = merged_value
+ else:
+ merged_plist[key] = value
+ else:
+ merged_plist[key] = value
+
+ def _LoadPlistMaybeBinary(self, plist_path):
+ """Loads into a memory a plist possibly encoded in binary format.
+
+ This is a wrapper around plistlib.readPlist that tries to convert the
+ plist to the XML format if it can't be parsed (assuming that it is in
+ the binary format).
+
+ Args:
+ plist_path: string, path to a plist file, in XML or binary format
+
+ Returns:
+ Content of the plist as a dictionary.
+ """
+ try:
+ # First, try to read the file using plistlib that only supports XML,
+ # and if an exception is raised, convert a temporary copy to XML and
+ # load that copy.
+ return plistlib.readPlist(plist_path)
+ except:
+ pass
+ with tempfile.NamedTemporaryFile() as temp:
+ shutil.copy2(plist_path, temp.name)
+ subprocess.check_call(['plutil', '-convert', 'xml1', temp.name])
+ return plistlib.readPlist(temp.name)
+
+ def _GetSubstitutions(self, bundle_identifier, app_identifier_prefix):
+ """Constructs a dictionary of variable substitutions for Entitlements.plist.
+
+ Args:
+ bundle_identifier: string, value of CFBundleIdentifier from Info.plist
+ app_identifier_prefix: string, value for AppIdentifierPrefix
+
+ Returns:
+ Dictionary of substitutions to apply when generating Entitlements.plist.
+ """
+ return {
+ 'CFBundleIdentifier': bundle_identifier,
+ 'AppIdentifierPrefix': app_identifier_prefix,
+ }
+
+ def _GetCFBundleIdentifier(self):
+ """Extracts CFBundleIdentifier value from Info.plist in the bundle.
+
+ Returns:
+ Value of CFBundleIdentifier in the Info.plist located in the bundle.
+ """
+ info_plist_path = os.path.join(
+ os.environ['TARGET_BUILD_DIR'],
+ os.environ['INFOPLIST_PATH'])
+ info_plist_data = self._LoadPlistMaybeBinary(info_plist_path)
+ return info_plist_data['CFBundleIdentifier']
+
+ def _InstallEntitlements(self, entitlements, substitutions, overrides):
+ """Generates and install the ${BundleName}.xcent entitlements file.
+
+ Expands variables "$(variable)" pattern in the source entitlements file,
+ add extra entitlements defined in the .mobileprovision file and the copy
+ the generated plist to "${BundlePath}.xcent".
+
+ Args:
+ entitlements: string, optional, path to the Entitlements.plist template
+ to use, defaults to "${SDKROOT}/Entitlements.plist"
+ substitutions: dictionary, variable substitutions
+ overrides: dictionary, values to add to the entitlements
+
+ Returns:
+ Path to the generated entitlements file.
+ """
+ source_path = entitlements
+ target_path = os.path.join(
+ os.environ['BUILT_PRODUCTS_DIR'],
+ os.environ['PRODUCT_NAME'] + '.xcent')
+ if not source_path:
+ source_path = os.path.join(
+ os.environ['SDKROOT'],
+ 'Entitlements.plist')
+ shutil.copy2(source_path, target_path)
+ data = self._LoadPlistMaybeBinary(target_path)
+ data = self._ExpandVariables(data, substitutions)
+ if overrides:
+ for key in overrides:
+ if key not in data:
+ data[key] = overrides[key]
+ plistlib.writePlist(data, target_path)
+ return target_path
+
+ def _ExpandVariables(self, data, substitutions):
+ """Expands variables "$(variable)" in data.
+
+ Args:
+ data: object, can be either string, list or dictionary
+ substitutions: dictionary, variable substitutions to perform
+
+ Returns:
+ Copy of data where each references to "$(variable)" has been replaced
+ by the corresponding value found in substitutions, or left intact if
+ the key was not found.
+ """
+ if isinstance(data, str):
+ for key, value in substitutions.iteritems():
+ data = data.replace('$(%s)' % key, value)
+ return data
+ if isinstance(data, list):
+ return [self._ExpandVariables(v, substitutions) for v in data]
+ if isinstance(data, dict):
+ return dict((k, self._ExpandVariables(data[k],
+ substitutions)) for k in data)
+ return data
+
+if __name__ == '__main__':
+ sys.exit(main(sys.argv[1:]))
http://git-wip-us.apache.org/repos/asf/couchdb-nmo/blob/753f1767/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/build/kerberos.target.mk
----------------------------------------------------------------------
diff --git a/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/build/kerberos.target.mk b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/build/kerberos.target.mk
new file mode 100644
index 0000000..1588e99
--- /dev/null
+++ b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/build/kerberos.target.mk
@@ -0,0 +1,181 @@
+# This file is generated by gyp; do not edit.
+
+TOOLSET := target
+TARGET := kerberos
+DEFS_Debug := \
+ '-DNODE_GYP_MODULE_NAME=kerberos' \
+ '-D_DARWIN_USE_64_BIT_INODE=1' \
+ '-D_LARGEFILE_SOURCE' \
+ '-D_FILE_OFFSET_BITS=64' \
+ '-D__MACOSX_CORE__' \
+ '-DBUILDING_NODE_EXTENSION' \
+ '-DDEBUG' \
+ '-D_DEBUG'
+
+# Flags passed to all source files.
+CFLAGS_Debug := \
+ -O0 \
+ -gdwarf-2 \
+ -mmacosx-version-min=10.5 \
+ -arch x86_64 \
+ -Wall \
+ -Wendif-labels \
+ -W \
+ -Wno-unused-parameter
+
+# Flags passed to only C files.
+CFLAGS_C_Debug := \
+ -fno-strict-aliasing
+
+# Flags passed to only C++ files.
+CFLAGS_CC_Debug := \
+ -std=gnu++0x \
+ -fno-rtti \
+ -fno-threadsafe-statics \
+ -fno-strict-aliasing
+
+# Flags passed to only ObjC files.
+CFLAGS_OBJC_Debug :=
+
+# Flags passed to only ObjC++ files.
+CFLAGS_OBJCC_Debug :=
+
+INCS_Debug := \
+ -I/Users/garren/.node-gyp/4.1.2/include/node \
+ -I/Users/garren/.node-gyp/4.1.2/src \
+ -I/Users/garren/.node-gyp/4.1.2/deps/uv/include \
+ -I/Users/garren/.node-gyp/4.1.2/deps/v8/include \
+ -I$(srcdir)/node_modules/nan \
+ -I/usr/include/mit-krb5
+
+DEFS_Release := \
+ '-DNODE_GYP_MODULE_NAME=kerberos' \
+ '-D_DARWIN_USE_64_BIT_INODE=1' \
+ '-D_LARGEFILE_SOURCE' \
+ '-D_FILE_OFFSET_BITS=64' \
+ '-D__MACOSX_CORE__' \
+ '-DBUILDING_NODE_EXTENSION'
+
+# Flags passed to all source files.
+CFLAGS_Release := \
+ -Os \
+ -gdwarf-2 \
+ -mmacosx-version-min=10.5 \
+ -arch x86_64 \
+ -Wall \
+ -Wendif-labels \
+ -W \
+ -Wno-unused-parameter
+
+# Flags passed to only C files.
+CFLAGS_C_Release := \
+ -fno-strict-aliasing
+
+# Flags passed to only C++ files.
+CFLAGS_CC_Release := \
+ -std=gnu++0x \
+ -fno-rtti \
+ -fno-threadsafe-statics \
+ -fno-strict-aliasing
+
+# Flags passed to only ObjC files.
+CFLAGS_OBJC_Release :=
+
+# Flags passed to only ObjC++ files.
+CFLAGS_OBJCC_Release :=
+
+INCS_Release := \
+ -I/Users/garren/.node-gyp/4.1.2/include/node \
+ -I/Users/garren/.node-gyp/4.1.2/src \
+ -I/Users/garren/.node-gyp/4.1.2/deps/uv/include \
+ -I/Users/garren/.node-gyp/4.1.2/deps/v8/include \
+ -I$(srcdir)/node_modules/nan \
+ -I/usr/include/mit-krb5
+
+OBJS := \
+ $(obj).target/$(TARGET)/lib/kerberos.o \
+ $(obj).target/$(TARGET)/lib/worker.o \
+ $(obj).target/$(TARGET)/lib/kerberosgss.o \
+ $(obj).target/$(TARGET)/lib/base64.o \
+ $(obj).target/$(TARGET)/lib/kerberos_context.o
+
+# Add to the list of files we specially track dependencies for.
+all_deps += $(OBJS)
+
+# CFLAGS et al overrides must be target-local.
+# See "Target-specific Variable Values" in the GNU Make manual.
+$(OBJS): TOOLSET := $(TOOLSET)
+$(OBJS): GYP_CFLAGS := $(DEFS_$(BUILDTYPE)) $(INCS_$(BUILDTYPE)) $(CFLAGS_$(BUILDTYPE)) $(CFLAGS_C_$(BUILDTYPE))
+$(OBJS): GYP_CXXFLAGS := $(DEFS_$(BUILDTYPE)) $(INCS_$(BUILDTYPE)) $(CFLAGS_$(BUILDTYPE)) $(CFLAGS_CC_$(BUILDTYPE))
+$(OBJS): GYP_OBJCFLAGS := $(DEFS_$(BUILDTYPE)) $(INCS_$(BUILDTYPE)) $(CFLAGS_$(BUILDTYPE)) $(CFLAGS_C_$(BUILDTYPE)) $(CFLAGS_OBJC_$(BUILDTYPE))
+$(OBJS): GYP_OBJCXXFLAGS := $(DEFS_$(BUILDTYPE)) $(INCS_$(BUILDTYPE)) $(CFLAGS_$(BUILDTYPE)) $(CFLAGS_CC_$(BUILDTYPE)) $(CFLAGS_OBJCC_$(BUILDTYPE))
+
+# Suffix rules, putting all outputs into $(obj).
+
+$(obj).$(TOOLSET)/$(TARGET)/%.o: $(srcdir)/%.cc FORCE_DO_CMD
+ @$(call do_cmd,cxx,1)
+
+$(obj).$(TOOLSET)/$(TARGET)/%.o: $(srcdir)/%.c FORCE_DO_CMD
+ @$(call do_cmd,cc,1)
+
+# Try building from generated source, too.
+
+$(obj).$(TOOLSET)/$(TARGET)/%.o: $(obj).$(TOOLSET)/%.cc FORCE_DO_CMD
+ @$(call do_cmd,cxx,1)
+
+$(obj).$(TOOLSET)/$(TARGET)/%.o: $(obj).$(TOOLSET)/%.c FORCE_DO_CMD
+ @$(call do_cmd,cc,1)
+
+$(obj).$(TOOLSET)/$(TARGET)/%.o: $(obj)/%.cc FORCE_DO_CMD
+ @$(call do_cmd,cxx,1)
+
+$(obj).$(TOOLSET)/$(TARGET)/%.o: $(obj)/%.c FORCE_DO_CMD
+ @$(call do_cmd,cc,1)
+
+# End of this set of suffix rules
+### Rules for final target.
+LDFLAGS_Debug := \
+ -undefined dynamic_lookup \
+ -Wl,-search_paths_first \
+ -mmacosx-version-min=10.5 \
+ -arch x86_64 \
+ -L$(builddir)
+
+LIBTOOLFLAGS_Debug := \
+ -undefined dynamic_lookup \
+ -Wl,-search_paths_first
+
+LDFLAGS_Release := \
+ -undefined dynamic_lookup \
+ -Wl,-search_paths_first \
+ -mmacosx-version-min=10.5 \
+ -arch x86_64 \
+ -L$(builddir)
+
+LIBTOOLFLAGS_Release := \
+ -undefined dynamic_lookup \
+ -Wl,-search_paths_first
+
+LIBS := \
+ -lkrb5
+
+$(builddir)/kerberos.node: GYP_LDFLAGS := $(LDFLAGS_$(BUILDTYPE))
+$(builddir)/kerberos.node: LIBS := $(LIBS)
+$(builddir)/kerberos.node: GYP_LIBTOOLFLAGS := $(LIBTOOLFLAGS_$(BUILDTYPE))
+$(builddir)/kerberos.node: TOOLSET := $(TOOLSET)
+$(builddir)/kerberos.node: $(OBJS) FORCE_DO_CMD
+ $(call do_cmd,solink_module)
+
+all_deps += $(builddir)/kerberos.node
+# Add target alias
+.PHONY: kerberos
+kerberos: $(builddir)/kerberos.node
+
+# Short alias for building this executable.
+.PHONY: kerberos.node
+kerberos.node: $(builddir)/kerberos.node
+
+# Add executable to "all" target.
+.PHONY: all
+all: $(builddir)/kerberos.node
+
http://git-wip-us.apache.org/repos/asf/couchdb-nmo/blob/753f1767/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/index.js
----------------------------------------------------------------------
diff --git a/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/index.js b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/index.js
new file mode 100644
index 0000000..b8c8532
--- /dev/null
+++ b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/index.js
@@ -0,0 +1,6 @@
+// Get the Kerberos library
+module.exports = require('./lib/kerberos');
+// Set up the auth processes
+module.exports['processes'] = {
+ MongoAuthProcess: require('./lib/auth_processes/mongodb').MongoAuthProcess
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/couchdb-nmo/blob/753f1767/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/auth_processes/mongodb.js
----------------------------------------------------------------------
diff --git a/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/auth_processes/mongodb.js b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/auth_processes/mongodb.js
new file mode 100644
index 0000000..f1e9231
--- /dev/null
+++ b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/auth_processes/mongodb.js
@@ -0,0 +1,281 @@
+var format = require('util').format;
+
+var MongoAuthProcess = function(host, port, service_name) {
+ // Check what system we are on
+ if(process.platform == 'win32') {
+ this._processor = new Win32MongoProcessor(host, port, service_name);
+ } else {
+ this._processor = new UnixMongoProcessor(host, port, service_name);
+ }
+}
+
+MongoAuthProcess.prototype.init = function(username, password, callback) {
+ this._processor.init(username, password, callback);
+}
+
+MongoAuthProcess.prototype.transition = function(payload, callback) {
+ this._processor.transition(payload, callback);
+}
+
+/*******************************************************************
+ *
+ * Win32 SSIP Processor for MongoDB
+ *
+ *******************************************************************/
+var Win32MongoProcessor = function(host, port, service_name) {
+ this.host = host;
+ this.port = port
+ // SSIP classes
+ this.ssip = require("../kerberos").SSIP;
+ // Set up first transition
+ this._transition = Win32MongoProcessor.first_transition(this);
+ // Set up service name
+ service_name = service_name || "mongodb";
+ // Set up target
+ this.target = format("%s/%s", service_name, host);
+ // Number of retries
+ this.retries = 10;
+}
+
+Win32MongoProcessor.prototype.init = function(username, password, callback) {
+ var self = this;
+ // Save the values used later
+ this.username = username;
+ this.password = password;
+ // Aquire credentials
+ this.ssip.SecurityCredentials.aquire_kerberos(username, password, function(err, security_credentials) {
+ if(err) return callback(err);
+ // Save credentials
+ self.security_credentials = security_credentials;
+ // Callback with success
+ callback(null);
+ });
+}
+
+Win32MongoProcessor.prototype.transition = function(payload, callback) {
+ if(this._transition == null) return callback(new Error("Transition finished"));
+ this._transition(payload, callback);
+}
+
+Win32MongoProcessor.first_transition = function(self) {
+ return function(payload, callback) {
+ self.ssip.SecurityContext.initialize(
+ self.security_credentials,
+ self.target,
+ payload, function(err, security_context) {
+ if(err) return callback(err);
+
+ // If no context try again until we have no more retries
+ if(!security_context.hasContext) {
+ if(self.retries == 0) return callback(new Error("Failed to initialize security context"));
+ // Update the number of retries
+ self.retries = self.retries - 1;
+ // Set next transition
+ return self.transition(payload, callback);
+ }
+
+ // Set next transition
+ self._transition = Win32MongoProcessor.second_transition(self);
+ self.security_context = security_context;
+ // Return the payload
+ callback(null, security_context.payload);
+ });
+ }
+}
+
+Win32MongoProcessor.second_transition = function(self) {
+ return function(payload, callback) {
+ // Perform a step
+ self.security_context.initialize(self.target, payload, function(err, security_context) {
+ if(err) return callback(err);
+
+ // If no context try again until we have no more retries
+ if(!security_context.hasContext) {
+ if(self.retries == 0) return callback(new Error("Failed to initialize security context"));
+ // Update the number of retries
+ self.retries = self.retries - 1;
+ // Set next transition
+ self._transition = Win32MongoProcessor.first_transition(self);
+ // Retry
+ return self.transition(payload, callback);
+ }
+
+ // Set next transition
+ self._transition = Win32MongoProcessor.third_transition(self);
+ // Return the payload
+ callback(null, security_context.payload);
+ });
+ }
+}
+
+Win32MongoProcessor.third_transition = function(self) {
+ return function(payload, callback) {
+ var messageLength = 0;
+ // Get the raw bytes
+ var encryptedBytes = new Buffer(payload, 'base64');
+ var encryptedMessage = new Buffer(messageLength);
+ // Copy first byte
+ encryptedBytes.copy(encryptedMessage, 0, 0, messageLength);
+ // Set up trailer
+ var securityTrailerLength = encryptedBytes.length - messageLength;
+ var securityTrailer = new Buffer(securityTrailerLength);
+ // Copy the bytes
+ encryptedBytes.copy(securityTrailer, 0, messageLength, securityTrailerLength);
+
+ // Types used
+ var SecurityBuffer = self.ssip.SecurityBuffer;
+ var SecurityBufferDescriptor = self.ssip.SecurityBufferDescriptor;
+
+ // Set up security buffers
+ var buffers = [
+ new SecurityBuffer(SecurityBuffer.DATA, encryptedBytes)
+ , new SecurityBuffer(SecurityBuffer.STREAM, securityTrailer)
+ ];
+
+ // Set up the descriptor
+ var descriptor = new SecurityBufferDescriptor(buffers);
+
+ // Decrypt the data
+ self.security_context.decryptMessage(descriptor, function(err, security_context) {
+ if(err) return callback(err);
+
+ var length = 4;
+ if(self.username != null) {
+ length += self.username.length;
+ }
+
+ var bytesReceivedFromServer = new Buffer(length);
+ bytesReceivedFromServer[0] = 0x01; // NO_PROTECTION
+ bytesReceivedFromServer[1] = 0x00; // NO_PROTECTION
+ bytesReceivedFromServer[2] = 0x00; // NO_PROTECTION
+ bytesReceivedFromServer[3] = 0x00; // NO_PROTECTION
+
+ if(self.username != null) {
+ var authorization_id_bytes = new Buffer(self.username, 'utf8');
+ authorization_id_bytes.copy(bytesReceivedFromServer, 4, 0);
+ }
+
+ self.security_context.queryContextAttributes(0x00, function(err, sizes) {
+ if(err) return callback(err);
+
+ var buffers = [
+ new SecurityBuffer(SecurityBuffer.TOKEN, new Buffer(sizes.securityTrailer))
+ , new SecurityBuffer(SecurityBuffer.DATA, bytesReceivedFromServer)
+ , new SecurityBuffer(SecurityBuffer.PADDING, new Buffer(sizes.blockSize))
+ ]
+
+ var descriptor = new SecurityBufferDescriptor(buffers);
+
+ self.security_context.encryptMessage(descriptor, 0x80000001, function(err, security_context) {
+ if(err) return callback(err);
+ callback(null, security_context.payload);
+ });
+ });
+ });
+ }
+}
+
+/*******************************************************************
+ *
+ * UNIX MIT Kerberos processor
+ *
+ *******************************************************************/
+var UnixMongoProcessor = function(host, port, service_name) {
+ this.host = host;
+ this.port = port
+ // SSIP classes
+ this.Kerberos = require("../kerberos").Kerberos;
+ this.kerberos = new this.Kerberos();
+ service_name = service_name || "mongodb";
+ // Set up first transition
+ this._transition = UnixMongoProcessor.first_transition(this);
+ // Set up target
+ this.target = format("%s@%s", service_name, host);
+ // Number of retries
+ this.retries = 10;
+}
+
+UnixMongoProcessor.prototype.init = function(username, password, callback) {
+ var self = this;
+ this.username = username;
+ this.password = password;
+ // Call client initiate
+ this.kerberos.authGSSClientInit(
+ self.target
+ , this.Kerberos.GSS_C_MUTUAL_FLAG, function(err, context) {
+ self.context = context;
+ // Return the context
+ callback(null, context);
+ });
+}
+
+UnixMongoProcessor.prototype.transition = function(payload, callback) {
+ if(this._transition == null) return callback(new Error("Transition finished"));
+ this._transition(payload, callback);
+}
+
+UnixMongoProcessor.first_transition = function(self) {
+ return function(payload, callback) {
+ self.kerberos.authGSSClientStep(self.context, '', function(err, result) {
+ if(err) return callback(err);
+ // Set up the next step
+ self._transition = UnixMongoProcessor.second_transition(self);
+ // Return the payload
+ callback(null, self.context.response);
+ })
+ }
+}
+
+UnixMongoProcessor.second_transition = function(self) {
+ return function(payload, callback) {
+ self.kerberos.authGSSClientStep(self.context, payload, function(err, result) {
+ if(err && self.retries == 0) return callback(err);
+ // Attempt to re-establish a context
+ if(err) {
+ // Adjust the number of retries
+ self.retries = self.retries - 1;
+ // Call same step again
+ return self.transition(payload, callback);
+ }
+
+ // Set up the next step
+ self._transition = UnixMongoProcessor.third_transition(self);
+ // Return the payload
+ callback(null, self.context.response || '');
+ });
+ }
+}
+
+UnixMongoProcessor.third_transition = function(self) {
+ return function(payload, callback) {
+ // GSS Client Unwrap
+ self.kerberos.authGSSClientUnwrap(self.context, payload, function(err, result) {
+ if(err) return callback(err, false);
+
+ // Wrap the response
+ self.kerberos.authGSSClientWrap(self.context, self.context.response, self.username, function(err, result) {
+ if(err) return callback(err, false);
+ // Set up the next step
+ self._transition = UnixMongoProcessor.fourth_transition(self);
+ // Return the payload
+ callback(null, self.context.response);
+ });
+ });
+ }
+}
+
+UnixMongoProcessor.fourth_transition = function(self) {
+ return function(payload, callback) {
+ // Clean up context
+ self.kerberos.authGSSClientClean(self.context, function(err, result) {
+ if(err) return callback(err, false);
+ // Set the transition to null
+ self._transition = null;
+ // Callback with valid authentication
+ callback(null, true);
+ });
+ }
+}
+
+// Set the process
+exports.MongoAuthProcess = MongoAuthProcess;
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/couchdb-nmo/blob/753f1767/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/base64.c
----------------------------------------------------------------------
diff --git a/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/base64.c b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/base64.c
new file mode 100644
index 0000000..aca0a61
--- /dev/null
+++ b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/base64.c
@@ -0,0 +1,134 @@
+/**
+ * Copyright (c) 2006-2008 Apple Inc. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ **/
+
+#include "base64.h"
+
+#include <stdlib.h>
+#include <string.h>
+#include <stdio.h>
+#include <errno.h>
+
+void die2(const char *message) {
+ if(errno) {
+ perror(message);
+ } else {
+ printf("ERROR: %s\n", message);
+ }
+
+ exit(1);
+}
+
+// base64 tables
+static char basis_64[] =
+ "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+static signed char index_64[128] =
+{
+ -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1,
+ -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,-1,
+ -1,-1,-1,-1, -1,-1,-1,-1, -1,-1,-1,62, -1,-1,-1,63,
+ 52,53,54,55, 56,57,58,59, 60,61,-1,-1, -1,-1,-1,-1,
+ -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9,10, 11,12,13,14,
+ 15,16,17,18, 19,20,21,22, 23,24,25,-1, -1,-1,-1,-1,
+ -1,26,27,28, 29,30,31,32, 33,34,35,36, 37,38,39,40,
+ 41,42,43,44, 45,46,47,48, 49,50,51,-1, -1,-1,-1,-1
+};
+#define CHAR64(c) (((c) < 0 || (c) > 127) ? -1 : index_64[(c)])
+
+// base64_encode : base64 encode
+//
+// value : data to encode
+// vlen : length of data
+// (result) : new char[] - c-str of result
+char *base64_encode(const unsigned char *value, int vlen)
+{
+ char *result = (char *)malloc((vlen * 4) / 3 + 5);
+ if(result == NULL) die2("Memory allocation failed");
+ char *out = result;
+ while (vlen >= 3)
+ {
+ *out++ = basis_64[value[0] >> 2];
+ *out++ = basis_64[((value[0] << 4) & 0x30) | (value[1] >> 4)];
+ *out++ = basis_64[((value[1] << 2) & 0x3C) | (value[2] >> 6)];
+ *out++ = basis_64[value[2] & 0x3F];
+ value += 3;
+ vlen -= 3;
+ }
+ if (vlen > 0)
+ {
+ *out++ = basis_64[value[0] >> 2];
+ unsigned char oval = (value[0] << 4) & 0x30;
+ if (vlen > 1) oval |= value[1] >> 4;
+ *out++ = basis_64[oval];
+ *out++ = (vlen < 2) ? '=' : basis_64[(value[1] << 2) & 0x3C];
+ *out++ = '=';
+ }
+ *out = '\0';
+
+ return result;
+}
+
+// base64_decode : base64 decode
+//
+// value : c-str to decode
+// rlen : length of decoded result
+// (result) : new unsigned char[] - decoded result
+unsigned char *base64_decode(const char *value, int *rlen)
+{
+ *rlen = 0;
+ int c1, c2, c3, c4;
+
+ int vlen = strlen(value);
+ unsigned char *result =(unsigned char *)malloc((vlen * 3) / 4 + 1);
+ if(result == NULL) die2("Memory allocation failed");
+ unsigned char *out = result;
+
+ while (1)
+ {
+ if (value[0]==0)
+ return result;
+ c1 = value[0];
+ if (CHAR64(c1) == -1)
+ goto base64_decode_error;;
+ c2 = value[1];
+ if (CHAR64(c2) == -1)
+ goto base64_decode_error;;
+ c3 = value[2];
+ if ((c3 != '=') && (CHAR64(c3) == -1))
+ goto base64_decode_error;;
+ c4 = value[3];
+ if ((c4 != '=') && (CHAR64(c4) == -1))
+ goto base64_decode_error;;
+
+ value += 4;
+ *out++ = (CHAR64(c1) << 2) | (CHAR64(c2) >> 4);
+ *rlen += 1;
+ if (c3 != '=')
+ {
+ *out++ = ((CHAR64(c2) << 4) & 0xf0) | (CHAR64(c3) >> 2);
+ *rlen += 1;
+ if (c4 != '=')
+ {
+ *out++ = ((CHAR64(c3) << 6) & 0xc0) | CHAR64(c4);
+ *rlen += 1;
+ }
+ }
+ }
+
+base64_decode_error:
+ *result = 0;
+ *rlen = 0;
+ return result;
+}
http://git-wip-us.apache.org/repos/asf/couchdb-nmo/blob/753f1767/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/base64.h
----------------------------------------------------------------------
diff --git a/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/base64.h b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/base64.h
new file mode 100644
index 0000000..9152e6a
--- /dev/null
+++ b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/base64.h
@@ -0,0 +1,22 @@
+/**
+ * Copyright (c) 2006-2008 Apple Inc. All rights reserved.
+ *
+ * Licensed under the Apache License, Version 2.0 (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.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ **/
+#ifndef BASE64_H
+#define BASE64_H
+
+char *base64_encode(const unsigned char *value, int vlen);
+unsigned char *base64_decode(const char *value, int *rlen);
+
+#endif
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/couchdb-nmo/blob/753f1767/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/kerberos.cc
----------------------------------------------------------------------
diff --git a/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/kerberos.cc b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/kerberos.cc
new file mode 100644
index 0000000..5b25d74
--- /dev/null
+++ b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/kerberos.cc
@@ -0,0 +1,893 @@
+#include "kerberos.h"
+#include <stdlib.h>
+#include <errno.h>
+#include "worker.h"
+#include "kerberos_context.h"
+
+#ifndef ARRAY_SIZE
+# define ARRAY_SIZE(a) (sizeof((a)) / sizeof((a)[0]))
+#endif
+
+void die(const char *message) {
+ if(errno) {
+ perror(message);
+ } else {
+ printf("ERROR: %s\n", message);
+ }
+
+ exit(1);
+}
+
+// Call structs
+typedef struct AuthGSSClientCall {
+ uint32_t flags;
+ char *uri;
+} AuthGSSClientCall;
+
+typedef struct AuthGSSClientStepCall {
+ KerberosContext *context;
+ char *challenge;
+} AuthGSSClientStepCall;
+
+typedef struct AuthGSSClientUnwrapCall {
+ KerberosContext *context;
+ char *challenge;
+} AuthGSSClientUnwrapCall;
+
+typedef struct AuthGSSClientWrapCall {
+ KerberosContext *context;
+ char *challenge;
+ char *user_name;
+} AuthGSSClientWrapCall;
+
+typedef struct AuthGSSClientCleanCall {
+ KerberosContext *context;
+} AuthGSSClientCleanCall;
+
+typedef struct AuthGSSServerInitCall {
+ char *service;
+ bool constrained_delegation;
+ char *username;
+} AuthGSSServerInitCall;
+
+typedef struct AuthGSSServerCleanCall {
+ KerberosContext *context;
+} AuthGSSServerCleanCall;
+
+typedef struct AuthGSSServerStepCall {
+ KerberosContext *context;
+ char *auth_data;
+} AuthGSSServerStepCall;
+
+Kerberos::Kerberos() : Nan::ObjectWrap() {
+}
+
+Nan::Persistent<FunctionTemplate> Kerberos::constructor_template;
+
+void Kerberos::Initialize(Nan::ADDON_REGISTER_FUNCTION_ARGS_TYPE target) {
+ // Grab the scope of the call from Node
+ Nan::HandleScope scope;
+
+ // Define a new function template
+ Local<FunctionTemplate> t = Nan::New<FunctionTemplate>(New);
+ t->InstanceTemplate()->SetInternalFieldCount(1);
+ t->SetClassName(Nan::New<String>("Kerberos").ToLocalChecked());
+
+ // Set up method for the Kerberos instance
+ Nan::SetPrototypeMethod(t, "authGSSClientInit", AuthGSSClientInit);
+ Nan::SetPrototypeMethod(t, "authGSSClientStep", AuthGSSClientStep);
+ Nan::SetPrototypeMethod(t, "authGSSClientUnwrap", AuthGSSClientUnwrap);
+ Nan::SetPrototypeMethod(t, "authGSSClientWrap", AuthGSSClientWrap);
+ Nan::SetPrototypeMethod(t, "authGSSClientClean", AuthGSSClientClean);
+ Nan::SetPrototypeMethod(t, "authGSSServerInit", AuthGSSServerInit);
+ Nan::SetPrototypeMethod(t, "authGSSServerClean", AuthGSSServerClean);
+ Nan::SetPrototypeMethod(t, "authGSSServerStep", AuthGSSServerStep);
+
+ constructor_template.Reset(t);
+
+ // Set the symbol
+ target->ForceSet(Nan::New<String>("Kerberos").ToLocalChecked(), t->GetFunction());
+}
+
+NAN_METHOD(Kerberos::New) {
+ // Create a Kerberos instance
+ Kerberos *kerberos = new Kerberos();
+ // Return the kerberos object
+ kerberos->Wrap(info.This());
+ info.GetReturnValue().Set(info.This());
+}
+
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+// authGSSClientInit
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+static void _authGSSClientInit(Worker *worker) {
+ gss_client_state *state;
+ gss_client_response *response;
+
+ // Allocate state
+ state = (gss_client_state *)malloc(sizeof(gss_client_state));
+ if(state == NULL) die("Memory allocation failed");
+
+ // Unpack the parameter data struct
+ AuthGSSClientCall *call = (AuthGSSClientCall *)worker->parameters;
+ // Start the kerberos client
+ response = authenticate_gss_client_init(call->uri, call->flags, state);
+
+ // Release the parameter struct memory
+ free(call->uri);
+ free(call);
+
+ // If we have an error mark worker as having had an error
+ if(response->return_code == AUTH_GSS_ERROR) {
+ worker->error = TRUE;
+ worker->error_code = response->return_code;
+ worker->error_message = response->message;
+ free(state);
+ } else {
+ worker->return_value = state;
+ }
+
+ // Free structure
+ free(response);
+}
+
+static Local<Value> _map_authGSSClientInit(Worker *worker) {
+ KerberosContext *context = KerberosContext::New();
+ context->state = (gss_client_state *)worker->return_value;
+ return context->handle();
+}
+
+// Initialize method
+NAN_METHOD(Kerberos::AuthGSSClientInit) {
+ // Ensure valid call
+ if(info.Length() != 3) return Nan::ThrowError("Requires a service string uri, integer flags and a callback function");
+ if(info.Length() == 3 && (!info[0]->IsString() || !info[1]->IsInt32() || !info[2]->IsFunction()))
+ return Nan::ThrowError("Requires a service string uri, integer flags and a callback function");
+
+ Local<String> service = info[0]->ToString();
+ // Convert uri string to c-string
+ char *service_str = (char *)calloc(service->Utf8Length() + 1, sizeof(char));
+ if(service_str == NULL) die("Memory allocation failed");
+
+ // Write v8 string to c-string
+ service->WriteUtf8(service_str);
+
+ // Allocate a structure
+ AuthGSSClientCall *call = (AuthGSSClientCall *)calloc(1, sizeof(AuthGSSClientCall));
+ if(call == NULL) die("Memory allocation failed");
+ call->flags =info[1]->ToInt32()->Uint32Value();
+ call->uri = service_str;
+
+ // Unpack the callback
+ Local<Function> callbackHandle = Local<Function>::Cast(info[2]);
+ Nan::Callback *callback = new Nan::Callback(callbackHandle);
+
+ // Let's allocate some space
+ Worker *worker = new Worker();
+ worker->error = false;
+ worker->request.data = worker;
+ worker->callback = callback;
+ worker->parameters = call;
+ worker->execute = _authGSSClientInit;
+ worker->mapper = _map_authGSSClientInit;
+
+ // Schedule the worker with lib_uv
+ uv_queue_work(uv_default_loop(), &worker->request, Kerberos::Process, (uv_after_work_cb)Kerberos::After);
+ // Return no value as it's callback based
+ info.GetReturnValue().Set(Nan::Undefined());
+}
+
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+// authGSSClientStep
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+static void _authGSSClientStep(Worker *worker) {
+ gss_client_state *state;
+ gss_client_response *response;
+ char *challenge;
+
+ // Unpack the parameter data struct
+ AuthGSSClientStepCall *call = (AuthGSSClientStepCall *)worker->parameters;
+ // Get the state
+ state = call->context->state;
+ challenge = call->challenge;
+
+ // Check what kind of challenge we have
+ if(call->challenge == NULL) {
+ challenge = (char *)"";
+ }
+
+ // Perform authentication step
+ response = authenticate_gss_client_step(state, challenge);
+
+ // If we have an error mark worker as having had an error
+ if(response->return_code == AUTH_GSS_ERROR) {
+ worker->error = TRUE;
+ worker->error_code = response->return_code;
+ worker->error_message = response->message;
+ } else {
+ worker->return_code = response->return_code;
+ }
+
+ // Free up structure
+ if(call->challenge != NULL) free(call->challenge);
+ free(call);
+ free(response);
+}
+
+static Local<Value> _map_authGSSClientStep(Worker *worker) {
+ Nan::HandleScope scope;
+ // Return the return code
+ return Nan::New<Int32>(worker->return_code);
+}
+
+// Initialize method
+NAN_METHOD(Kerberos::AuthGSSClientStep) {
+ // Ensure valid call
+ if(info.Length() != 2 && info.Length() != 3) return Nan::ThrowError("Requires a GSS context, optional challenge string and callback function");
+ if(info.Length() == 2 && (!KerberosContext::HasInstance(info[0]) || !info[1]->IsFunction())) return Nan::ThrowError("Requires a GSS context, optional challenge string and callback function");
+ if(info.Length() == 3 && (!KerberosContext::HasInstance(info[0]) || !info[1]->IsString() || !info[2]->IsFunction())) return Nan::ThrowError("Requires a GSS context, optional challenge string and callback function");
+
+ // Challenge string
+ char *challenge_str = NULL;
+ // Let's unpack the parameters
+ Local<Object> object = info[0]->ToObject();
+ KerberosContext *kerberos_context = KerberosContext::Unwrap<KerberosContext>(object);
+
+ if (!kerberos_context->IsClientInstance()) {
+ return Nan::ThrowError("GSS context is not a client instance");
+ }
+
+ int callbackArg = 1;
+
+ // If we have a challenge string
+ if(info.Length() == 3) {
+ // Unpack the challenge string
+ Local<String> challenge = info[1]->ToString();
+ // Convert uri string to c-string
+ challenge_str = (char *)calloc(challenge->Utf8Length() + 1, sizeof(char));
+ if(challenge_str == NULL) die("Memory allocation failed");
+ // Write v8 string to c-string
+ challenge->WriteUtf8(challenge_str);
+
+ callbackArg = 2;
+ }
+
+ // Allocate a structure
+ AuthGSSClientStepCall *call = (AuthGSSClientStepCall *)calloc(1, sizeof(AuthGSSClientStepCall));
+ if(call == NULL) die("Memory allocation failed");
+ call->context = kerberos_context;
+ call->challenge = challenge_str;
+
+ // Unpack the callback
+ Local<Function> callbackHandle = Local<Function>::Cast(info[callbackArg]);
+ Nan::Callback *callback = new Nan::Callback(callbackHandle);
+
+ // Let's allocate some space
+ Worker *worker = new Worker();
+ worker->error = false;
+ worker->request.data = worker;
+ worker->callback = callback;
+ worker->parameters = call;
+ worker->execute = _authGSSClientStep;
+ worker->mapper = _map_authGSSClientStep;
+
+ // Schedule the worker with lib_uv
+ uv_queue_work(uv_default_loop(), &worker->request, Kerberos::Process, (uv_after_work_cb)Kerberos::After);
+
+ // Return no value as it's callback based
+ info.GetReturnValue().Set(Nan::Undefined());
+}
+
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+// authGSSClientUnwrap
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+static void _authGSSClientUnwrap(Worker *worker) {
+ gss_client_response *response;
+ char *challenge;
+
+ // Unpack the parameter data struct
+ AuthGSSClientUnwrapCall *call = (AuthGSSClientUnwrapCall *)worker->parameters;
+ challenge = call->challenge;
+
+ // Check what kind of challenge we have
+ if(call->challenge == NULL) {
+ challenge = (char *)"";
+ }
+
+ // Perform authentication step
+ response = authenticate_gss_client_unwrap(call->context->state, challenge);
+
+ // If we have an error mark worker as having had an error
+ if(response->return_code == AUTH_GSS_ERROR) {
+ worker->error = TRUE;
+ worker->error_code = response->return_code;
+ worker->error_message = response->message;
+ } else {
+ worker->return_code = response->return_code;
+ }
+
+ // Free up structure
+ if(call->challenge != NULL) free(call->challenge);
+ free(call);
+ free(response);
+}
+
+static Local<Value> _map_authGSSClientUnwrap(Worker *worker) {
+ Nan::HandleScope scope;
+ // Return the return code
+ return Nan::New<Int32>(worker->return_code);
+}
+
+// Initialize method
+NAN_METHOD(Kerberos::AuthGSSClientUnwrap) {
+ // Ensure valid call
+ if(info.Length() != 2 && info.Length() != 3) return Nan::ThrowError("Requires a GSS context, optional challenge string and callback function");
+ if(info.Length() == 2 && (!KerberosContext::HasInstance(info[0]) || !info[1]->IsFunction())) return Nan::ThrowError("Requires a GSS context, optional challenge string and callback function");
+ if(info.Length() == 3 && (!KerberosContext::HasInstance(info[0]) || !info[1]->IsString() || !info[2]->IsFunction())) return Nan::ThrowError("Requires a GSS context, optional challenge string and callback function");
+
+ // Challenge string
+ char *challenge_str = NULL;
+ // Let's unpack the parameters
+ Local<Object> object = info[0]->ToObject();
+ KerberosContext *kerberos_context = KerberosContext::Unwrap<KerberosContext>(object);
+
+ if (!kerberos_context->IsClientInstance()) {
+ return Nan::ThrowError("GSS context is not a client instance");
+ }
+
+ // If we have a challenge string
+ if(info.Length() == 3) {
+ // Unpack the challenge string
+ Local<String> challenge = info[1]->ToString();
+ // Convert uri string to c-string
+ challenge_str = (char *)calloc(challenge->Utf8Length() + 1, sizeof(char));
+ if(challenge_str == NULL) die("Memory allocation failed");
+ // Write v8 string to c-string
+ challenge->WriteUtf8(challenge_str);
+ }
+
+ // Allocate a structure
+ AuthGSSClientUnwrapCall *call = (AuthGSSClientUnwrapCall *)calloc(1, sizeof(AuthGSSClientUnwrapCall));
+ if(call == NULL) die("Memory allocation failed");
+ call->context = kerberos_context;
+ call->challenge = challenge_str;
+
+ // Unpack the callback
+ Local<Function> callbackHandle = info.Length() == 3 ? Local<Function>::Cast(info[2]) : Local<Function>::Cast(info[1]);
+ Nan::Callback *callback = new Nan::Callback(callbackHandle);
+
+ // Let's allocate some space
+ Worker *worker = new Worker();
+ worker->error = false;
+ worker->request.data = worker;
+ worker->callback = callback;
+ worker->parameters = call;
+ worker->execute = _authGSSClientUnwrap;
+ worker->mapper = _map_authGSSClientUnwrap;
+
+ // Schedule the worker with lib_uv
+ uv_queue_work(uv_default_loop(), &worker->request, Kerberos::Process, (uv_after_work_cb)Kerberos::After);
+
+ // Return no value as it's callback based
+ info.GetReturnValue().Set(Nan::Undefined());
+}
+
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+// authGSSClientWrap
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+static void _authGSSClientWrap(Worker *worker) {
+ gss_client_response *response;
+ char *user_name = NULL;
+
+ // Unpack the parameter data struct
+ AuthGSSClientWrapCall *call = (AuthGSSClientWrapCall *)worker->parameters;
+ user_name = call->user_name;
+
+ // Check what kind of challenge we have
+ if(call->user_name == NULL) {
+ user_name = (char *)"";
+ }
+
+ // Perform authentication step
+ response = authenticate_gss_client_wrap(call->context->state, call->challenge, user_name);
+
+ // If we have an error mark worker as having had an error
+ if(response->return_code == AUTH_GSS_ERROR) {
+ worker->error = TRUE;
+ worker->error_code = response->return_code;
+ worker->error_message = response->message;
+ } else {
+ worker->return_code = response->return_code;
+ }
+
+ // Free up structure
+ if(call->challenge != NULL) free(call->challenge);
+ if(call->user_name != NULL) free(call->user_name);
+ free(call);
+ free(response);
+}
+
+static Local<Value> _map_authGSSClientWrap(Worker *worker) {
+ Nan::HandleScope scope;
+ // Return the return code
+ return Nan::New<Int32>(worker->return_code);
+}
+
+// Initialize method
+NAN_METHOD(Kerberos::AuthGSSClientWrap) {
+ // Ensure valid call
+ if(info.Length() != 3 && info.Length() != 4) return Nan::ThrowError("Requires a GSS context, the result from the authGSSClientResponse after authGSSClientUnwrap, optional user name and callback function");
+ if(info.Length() == 3 && (!KerberosContext::HasInstance(info[0]) || !info[1]->IsString() || !info[2]->IsFunction())) return Nan::ThrowError("Requires a GSS context, the result from the authGSSClientResponse after authGSSClientUnwrap, optional user name and callback function");
+ if(info.Length() == 4 && (!KerberosContext::HasInstance(info[0]) || !info[1]->IsString() || !info[2]->IsString() || !info[3]->IsFunction())) return Nan::ThrowError("Requires a GSS context, the result from the authGSSClientResponse after authGSSClientUnwrap, optional user name and callback function");
+
+ // Challenge string
+ char *challenge_str = NULL;
+ char *user_name_str = NULL;
+
+ // Let's unpack the kerberos context
+ Local<Object> object = info[0]->ToObject();
+ KerberosContext *kerberos_context = KerberosContext::Unwrap<KerberosContext>(object);
+
+ if (!kerberos_context->IsClientInstance()) {
+ return Nan::ThrowError("GSS context is not a client instance");
+ }
+
+ // Unpack the challenge string
+ Local<String> challenge = info[1]->ToString();
+ // Convert uri string to c-string
+ challenge_str = (char *)calloc(challenge->Utf8Length() + 1, sizeof(char));
+ if(challenge_str == NULL) die("Memory allocation failed");
+ // Write v8 string to c-string
+ challenge->WriteUtf8(challenge_str);
+
+ // If we have a user string
+ if(info.Length() == 4) {
+ // Unpack user name
+ Local<String> user_name = info[2]->ToString();
+ // Convert uri string to c-string
+ user_name_str = (char *)calloc(user_name->Utf8Length() + 1, sizeof(char));
+ if(user_name_str == NULL) die("Memory allocation failed");
+ // Write v8 string to c-string
+ user_name->WriteUtf8(user_name_str);
+ }
+
+ // Allocate a structure
+ AuthGSSClientWrapCall *call = (AuthGSSClientWrapCall *)calloc(1, sizeof(AuthGSSClientWrapCall));
+ if(call == NULL) die("Memory allocation failed");
+ call->context = kerberos_context;
+ call->challenge = challenge_str;
+ call->user_name = user_name_str;
+
+ // Unpack the callback
+ Local<Function> callbackHandle = info.Length() == 4 ? Local<Function>::Cast(info[3]) : Local<Function>::Cast(info[2]);
+ Nan::Callback *callback = new Nan::Callback(callbackHandle);
+
+ // Let's allocate some space
+ Worker *worker = new Worker();
+ worker->error = false;
+ worker->request.data = worker;
+ worker->callback = callback;
+ worker->parameters = call;
+ worker->execute = _authGSSClientWrap;
+ worker->mapper = _map_authGSSClientWrap;
+
+ // Schedule the worker with lib_uv
+ uv_queue_work(uv_default_loop(), &worker->request, Kerberos::Process, (uv_after_work_cb)Kerberos::After);
+
+ // Return no value as it's callback based
+ info.GetReturnValue().Set(Nan::Undefined());
+}
+
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+// authGSSClientClean
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+static void _authGSSClientClean(Worker *worker) {
+ gss_client_response *response;
+
+ // Unpack the parameter data struct
+ AuthGSSClientCleanCall *call = (AuthGSSClientCleanCall *)worker->parameters;
+
+ // Perform authentication step
+ response = authenticate_gss_client_clean(call->context->state);
+
+ // If we have an error mark worker as having had an error
+ if(response->return_code == AUTH_GSS_ERROR) {
+ worker->error = TRUE;
+ worker->error_code = response->return_code;
+ worker->error_message = response->message;
+ } else {
+ worker->return_code = response->return_code;
+ }
+
+ // Free up structure
+ free(call);
+ free(response);
+}
+
+static Local<Value> _map_authGSSClientClean(Worker *worker) {
+ Nan::HandleScope scope;
+ // Return the return code
+ return Nan::New<Int32>(worker->return_code);
+}
+
+// Initialize method
+NAN_METHOD(Kerberos::AuthGSSClientClean) {
+ // Ensure valid call
+ if(info.Length() != 2) return Nan::ThrowError("Requires a GSS context and callback function");
+ if(!KerberosContext::HasInstance(info[0]) || !info[1]->IsFunction()) return Nan::ThrowError("Requires a GSS context and callback function");
+
+ // Let's unpack the kerberos context
+ Local<Object> object = info[0]->ToObject();
+ KerberosContext *kerberos_context = KerberosContext::Unwrap<KerberosContext>(object);
+
+ if (!kerberos_context->IsClientInstance()) {
+ return Nan::ThrowError("GSS context is not a client instance");
+ }
+
+ // Allocate a structure
+ AuthGSSClientCleanCall *call = (AuthGSSClientCleanCall *)calloc(1, sizeof(AuthGSSClientCleanCall));
+ if(call == NULL) die("Memory allocation failed");
+ call->context = kerberos_context;
+
+ // Unpack the callback
+ Local<Function> callbackHandle = Local<Function>::Cast(info[1]);
+ Nan::Callback *callback = new Nan::Callback(callbackHandle);
+
+ // Let's allocate some space
+ Worker *worker = new Worker();
+ worker->error = false;
+ worker->request.data = worker;
+ worker->callback = callback;
+ worker->parameters = call;
+ worker->execute = _authGSSClientClean;
+ worker->mapper = _map_authGSSClientClean;
+
+ // Schedule the worker with lib_uv
+ uv_queue_work(uv_default_loop(), &worker->request, Kerberos::Process, (uv_after_work_cb)Kerberos::After);
+
+ // Return no value as it's callback based
+ info.GetReturnValue().Set(Nan::Undefined());
+}
+
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+// authGSSServerInit
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+static void _authGSSServerInit(Worker *worker) {
+ gss_server_state *state;
+ gss_client_response *response;
+
+ // Allocate state
+ state = (gss_server_state *)malloc(sizeof(gss_server_state));
+ if(state == NULL) die("Memory allocation failed");
+
+ // Unpack the parameter data struct
+ AuthGSSServerInitCall *call = (AuthGSSServerInitCall *)worker->parameters;
+ // Start the kerberos service
+ response = authenticate_gss_server_init(call->service, call->constrained_delegation, call->username, state);
+
+ // Release the parameter struct memory
+ free(call->service);
+ free(call->username);
+ free(call);
+
+ // If we have an error mark worker as having had an error
+ if(response->return_code == AUTH_GSS_ERROR) {
+ worker->error = TRUE;
+ worker->error_code = response->return_code;
+ worker->error_message = response->message;
+ free(state);
+ } else {
+ worker->return_value = state;
+ }
+
+ // Free structure
+ free(response);
+}
+
+static Local<Value> _map_authGSSServerInit(Worker *worker) {
+ KerberosContext *context = KerberosContext::New();
+ context->server_state = (gss_server_state *)worker->return_value;
+ return context->handle();
+}
+
+// Server Initialize method
+NAN_METHOD(Kerberos::AuthGSSServerInit) {
+ // Ensure valid call
+ if(info.Length() != 4) return Nan::ThrowError("Requires a service string, constrained delegation boolean, a username string (or NULL) for S4U2Self protocol transition and a callback function");
+
+ if(!info[0]->IsString() ||
+ !info[1]->IsBoolean() ||
+ !(info[2]->IsString() || info[2]->IsNull()) ||
+ !info[3]->IsFunction()
+ ) return Nan::ThrowError("Requires a service string, constrained delegation boolean, a username string (or NULL) for S4U2Self protocol transition and a callback function");
+
+ if (!info[1]->BooleanValue() && !info[2]->IsNull()) return Nan::ThrowError("S4U2Self only possible when constrained delegation is enabled");
+
+ // Allocate a structure
+ AuthGSSServerInitCall *call = (AuthGSSServerInitCall *)calloc(1, sizeof(AuthGSSServerInitCall));
+ if(call == NULL) die("Memory allocation failed");
+
+ Local<String> service = info[0]->ToString();
+ // Convert service string to c-string
+ char *service_str = (char *)calloc(service->Utf8Length() + 1, sizeof(char));
+ if(service_str == NULL) die("Memory allocation failed");
+
+ // Write v8 string to c-string
+ service->WriteUtf8(service_str);
+
+ call->service = service_str;
+
+ call->constrained_delegation = info[1]->BooleanValue();
+
+ if (info[2]->IsNull())
+ {
+ call->username = NULL;
+ }
+ else
+ {
+ Local<String> tmpString = info[2]->ToString();
+
+ char *tmpCstr = (char *)calloc(tmpString->Utf8Length() + 1, sizeof(char));
+ if(tmpCstr == NULL) die("Memory allocation failed");
+
+ tmpString->WriteUtf8(tmpCstr);
+
+ call->username = tmpCstr;
+ }
+
+ // Unpack the callback
+ Local<Function> callbackHandle = Local<Function>::Cast(info[3]);
+ Nan::Callback *callback = new Nan::Callback(callbackHandle);
+
+ // Let's allocate some space
+ Worker *worker = new Worker();
+ worker->error = false;
+ worker->request.data = worker;
+ worker->callback = callback;
+ worker->parameters = call;
+ worker->execute = _authGSSServerInit;
+ worker->mapper = _map_authGSSServerInit;
+
+ // Schedule the worker with lib_uv
+ uv_queue_work(uv_default_loop(), &worker->request, Kerberos::Process, (uv_after_work_cb)Kerberos::After);
+ // Return no value as it's callback based
+ info.GetReturnValue().Set(Nan::Undefined());
+}
+
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+// authGSSServerClean
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+static void _authGSSServerClean(Worker *worker) {
+ gss_client_response *response;
+
+ // Unpack the parameter data struct
+ AuthGSSServerCleanCall *call = (AuthGSSServerCleanCall *)worker->parameters;
+
+ // Perform authentication step
+ response = authenticate_gss_server_clean(call->context->server_state);
+
+ // If we have an error mark worker as having had an error
+ if(response->return_code == AUTH_GSS_ERROR) {
+ worker->error = TRUE;
+ worker->error_code = response->return_code;
+ worker->error_message = response->message;
+ } else {
+ worker->return_code = response->return_code;
+ }
+
+ // Free up structure
+ free(call);
+ free(response);
+}
+
+static Local<Value> _map_authGSSServerClean(Worker *worker) {
+ Nan::HandleScope scope;
+ // Return the return code
+ return Nan::New<Int32>(worker->return_code);
+}
+
+// Initialize method
+NAN_METHOD(Kerberos::AuthGSSServerClean) {
+ // // Ensure valid call
+ if(info.Length() != 2) return Nan::ThrowError("Requires a GSS context and callback function");
+ if(!KerberosContext::HasInstance(info[0]) || !info[1]->IsFunction()) return Nan::ThrowError("Requires a GSS context and callback function");
+
+ // Let's unpack the kerberos context
+ Local<Object> object = info[0]->ToObject();
+ KerberosContext *kerberos_context = KerberosContext::Unwrap<KerberosContext>(object);
+
+ if (!kerberos_context->IsServerInstance()) {
+ return Nan::ThrowError("GSS context is not a server instance");
+ }
+
+ // Allocate a structure
+ AuthGSSServerCleanCall *call = (AuthGSSServerCleanCall *)calloc(1, sizeof(AuthGSSServerCleanCall));
+ if(call == NULL) die("Memory allocation failed");
+ call->context = kerberos_context;
+
+ // Unpack the callback
+ Local<Function> callbackHandle = Local<Function>::Cast(info[1]);
+ Nan::Callback *callback = new Nan::Callback(callbackHandle);
+
+ // Let's allocate some space
+ Worker *worker = new Worker();
+ worker->error = false;
+ worker->request.data = worker;
+ worker->callback = callback;
+ worker->parameters = call;
+ worker->execute = _authGSSServerClean;
+ worker->mapper = _map_authGSSServerClean;
+
+ // Schedule the worker with lib_uv
+ uv_queue_work(uv_default_loop(), &worker->request, Kerberos::Process, (uv_after_work_cb)Kerberos::After);
+
+ // Return no value as it's callback based
+ info.GetReturnValue().Set(Nan::Undefined());
+}
+
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+// authGSSServerStep
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+static void _authGSSServerStep(Worker *worker) {
+ gss_server_state *state;
+ gss_client_response *response;
+ char *auth_data;
+
+ // Unpack the parameter data struct
+ AuthGSSServerStepCall *call = (AuthGSSServerStepCall *)worker->parameters;
+ // Get the state
+ state = call->context->server_state;
+ auth_data = call->auth_data;
+
+ // Check if we got auth_data or not
+ if(call->auth_data == NULL) {
+ auth_data = (char *)"";
+ }
+
+ // Perform authentication step
+ response = authenticate_gss_server_step(state, auth_data);
+
+ // If we have an error mark worker as having had an error
+ if(response->return_code == AUTH_GSS_ERROR) {
+ worker->error = TRUE;
+ worker->error_code = response->return_code;
+ worker->error_message = response->message;
+ } else {
+ worker->return_code = response->return_code;
+ }
+
+ // Free up structure
+ if(call->auth_data != NULL) free(call->auth_data);
+ free(call);
+ free(response);
+}
+
+static Local<Value> _map_authGSSServerStep(Worker *worker) {
+ Nan::HandleScope scope;
+ // Return the return code
+ return Nan::New<Int32>(worker->return_code);
+}
+
+// Initialize method
+NAN_METHOD(Kerberos::AuthGSSServerStep) {
+ // Ensure valid call
+ if(info.Length() != 3) return Nan::ThrowError("Requires a GSS context, auth-data string and callback function");
+ if(!KerberosContext::HasInstance(info[0])) return Nan::ThrowError("1st arg must be a GSS context");
+ if (!info[1]->IsString()) return Nan::ThrowError("2nd arg must be auth-data string");
+ if (!info[2]->IsFunction()) return Nan::ThrowError("3rd arg must be a callback function");
+
+ // Auth-data string
+ char *auth_data_str = NULL;
+ // Let's unpack the parameters
+ Local<Object> object = info[0]->ToObject();
+ KerberosContext *kerberos_context = KerberosContext::Unwrap<KerberosContext>(object);
+
+ if (!kerberos_context->IsServerInstance()) {
+ return Nan::ThrowError("GSS context is not a server instance");
+ }
+
+ // Unpack the auth_data string
+ Local<String> auth_data = info[1]->ToString();
+ // Convert uri string to c-string
+ auth_data_str = (char *)calloc(auth_data->Utf8Length() + 1, sizeof(char));
+ if(auth_data_str == NULL) die("Memory allocation failed");
+ // Write v8 string to c-string
+ auth_data->WriteUtf8(auth_data_str);
+
+ // Allocate a structure
+ AuthGSSServerStepCall *call = (AuthGSSServerStepCall *)calloc(1, sizeof(AuthGSSServerStepCall));
+ if(call == NULL) die("Memory allocation failed");
+ call->context = kerberos_context;
+ call->auth_data = auth_data_str;
+
+ // Unpack the callback
+ Local<Function> callbackHandle = Local<Function>::Cast(info[2]);
+ Nan::Callback *callback = new Nan::Callback(callbackHandle);
+
+ // Let's allocate some space
+ Worker *worker = new Worker();
+ worker->error = false;
+ worker->request.data = worker;
+ worker->callback = callback;
+ worker->parameters = call;
+ worker->execute = _authGSSServerStep;
+ worker->mapper = _map_authGSSServerStep;
+
+ // Schedule the worker with lib_uv
+ uv_queue_work(uv_default_loop(), &worker->request, Kerberos::Process, (uv_after_work_cb)Kerberos::After);
+
+ // Return no value as it's callback based
+ info.GetReturnValue().Set(Nan::Undefined());
+}
+
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+// UV Lib callbacks
+// +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+void Kerberos::Process(uv_work_t* work_req) {
+ // Grab the worker
+ Worker *worker = static_cast<Worker*>(work_req->data);
+ // Execute the worker code
+ worker->execute(worker);
+}
+
+void Kerberos::After(uv_work_t* work_req) {
+ // Grab the scope of the call from Node
+ Nan::HandleScope scope;
+
+ // Get the worker reference
+ Worker *worker = static_cast<Worker*>(work_req->data);
+
+ // If we have an error
+ if(worker->error) {
+ Local<Value> err = v8::Exception::Error(Nan::New<String>(worker->error_message).ToLocalChecked());
+ Local<Object> obj = err->ToObject();
+ obj->Set(Nan::New<String>("code").ToLocalChecked(), Nan::New<Int32>(worker->error_code));
+ Local<Value> info[2] = { err, Nan::Null() };
+ // Execute the error
+ Nan::TryCatch try_catch;
+
+ // Call the callback
+ worker->callback->Call(ARRAY_SIZE(info), info);
+
+ // If we have an exception handle it as a fatalexception
+ if (try_catch.HasCaught()) {
+ Nan::FatalException(try_catch);
+ }
+ } else {
+ // // Map the data
+ Local<Value> result = worker->mapper(worker);
+ // Set up the callback with a null first
+ #if defined(V8_MAJOR_VERSION) && (V8_MAJOR_VERSION > 4 || \
+ (V8_MAJOR_VERSION == 4 && defined(V8_MINOR_VERSION) && V8_MINOR_VERSION >= 3))
+ Local<Value> info[2] = { Nan::Null(), result};
+ #else
+ Local<Value> info[2] = { Nan::Null(), Nan::New<v8::Value>(result)};
+ #endif
+
+ // Wrap the callback function call in a TryCatch so that we can call
+ // node's FatalException afterwards. This makes it possible to catch
+ // the exception from JavaScript land using the
+ // process.on('uncaughtException') event.
+ Nan::TryCatch try_catch;
+
+ // Call the callback
+ worker->callback->Call(ARRAY_SIZE(info), info);
+
+ // If we have an exception handle it as a fatalexception
+ if (try_catch.HasCaught()) {
+ Nan::FatalException(try_catch);
+ }
+ }
+
+ // Clean up the memory
+ delete worker->callback;
+ delete worker;
+}
+
+// Exporting function
+NAN_MODULE_INIT(init) {
+ Kerberos::Initialize(target);
+ KerberosContext::Initialize(target);
+}
+
+NODE_MODULE(kerberos, init);
http://git-wip-us.apache.org/repos/asf/couchdb-nmo/blob/753f1767/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/kerberos.h
----------------------------------------------------------------------
diff --git a/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/kerberos.h b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/kerberos.h
new file mode 100644
index 0000000..beafa4d
--- /dev/null
+++ b/node_modules/couchbulkimporter/node_modules/mongodb/node_modules/mongodb-core/node_modules/kerberos/lib/kerberos.h
@@ -0,0 +1,50 @@
+#ifndef KERBEROS_H
+#define KERBEROS_H
+
+#include <node.h>
+#include <gssapi/gssapi.h>
+#include <gssapi/gssapi_generic.h>
+#include <gssapi/gssapi_krb5.h>
+
+#include "nan.h"
+#include <node_object_wrap.h>
+#include <v8.h>
+
+extern "C" {
+ #include "kerberosgss.h"
+}
+
+using namespace v8;
+using namespace node;
+
+class Kerberos : public Nan::ObjectWrap {
+
+public:
+ Kerberos();
+ ~Kerberos() {};
+
+ // Constructor used for creating new Kerberos objects from C++
+ static Nan::Persistent<FunctionTemplate> constructor_template;
+
+ // Initialize function for the object
+ static void Initialize(Nan::ADDON_REGISTER_FUNCTION_ARGS_TYPE target);
+
+ // Method available
+ static NAN_METHOD(AuthGSSClientInit);
+ static NAN_METHOD(AuthGSSClientStep);
+ static NAN_METHOD(AuthGSSClientUnwrap);
+ static NAN_METHOD(AuthGSSClientWrap);
+ static NAN_METHOD(AuthGSSClientClean);
+ static NAN_METHOD(AuthGSSServerInit);
+ static NAN_METHOD(AuthGSSServerClean);
+ static NAN_METHOD(AuthGSSServerStep);
+
+private:
+ static NAN_METHOD(New);
+ // Handles the uv calls
+ static void Process(uv_work_t* work_req);
+ // Called after work is done
+ static void After(uv_work_t* work_req);
+};
+
+#endif