pax_global_header00006660000000000000000000000064131763345160014523gustar00rootroot0000000000000052 comment=83d1a2ff93353f1e742d6429e3aba2e403fb4d92 asn1.js-5.0.0/000077500000000000000000000000001317633451600130025ustar00rootroot00000000000000asn1.js-5.0.0/.eslintrc.js000066400000000000000000000005711317633451600152440ustar00rootroot00000000000000module.exports = { 'env': { 'browser': false, 'commonjs': true, 'es6': true, 'node': true }, 'extends': 'eslint:recommended', 'rules': { 'indent': [ 'error', 2 ], 'linebreak-style': [ 'error', 'unix' ], 'quotes': [ 'error', 'single' ], 'semi': [ 'error', 'always' ] } }; asn1.js-5.0.0/.gitignore000066400000000000000000000000441317633451600147700ustar00rootroot00000000000000node_modules/ npm-debug.log test.js asn1.js-5.0.0/.npmignore000066400000000000000000000000111317633451600147710ustar00rootroot00000000000000test rfc asn1.js-5.0.0/README.md000066400000000000000000000046601317633451600142670ustar00rootroot00000000000000# ASN1.js ASN.1 DER Encoder/Decoder and DSL. ## Example Define model: ```javascript var asn = require('asn1.js'); var Human = asn.define('Human', function() { this.seq().obj( this.key('firstName').octstr(), this.key('lastName').octstr(), this.key('age').int(), this.key('gender').enum({ 0: 'male', 1: 'female' }), this.key('bio').seqof(Bio) ); }); var Bio = asn.define('Bio', function() { this.seq().obj( this.key('time').gentime(), this.key('description').octstr() ); }); ``` Encode data: ```javascript var output = Human.encode({ firstName: 'Thomas', lastName: 'Anderson', age: 28, gender: 'male', bio: [ { time: +new Date('31 March 1999'), description: 'freedom of mind' } ] }, 'der'); ``` Decode data: ```javascript var human = Human.decode(output, 'der'); console.log(human); /* { firstName: , lastName: , age: 28, gender: 'male', bio: [ { time: 922820400000, description: } ] } */ ``` ### Partial decode Its possible to parse data without stopping on first error. In order to do it, you should call: ```javascript var human = Human.decode(output, 'der', { partial: true }); console.log(human); /* { result: { ... }, errors: [ ... ] } */ ``` #### LICENSE This software is licensed under the MIT License. Copyright Fedor Indutny, 2017. Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. asn1.js-5.0.0/lib/000077500000000000000000000000001317633451600135505ustar00rootroot00000000000000asn1.js-5.0.0/lib/asn1.js000066400000000000000000000004351317633451600147520ustar00rootroot00000000000000'use strict'; const asn1 = exports; asn1.bignum = require('bn.js'); asn1.define = require('./asn1/api').define; asn1.base = require('./asn1/base'); asn1.constants = require('./asn1/constants'); asn1.decoders = require('./asn1/decoders'); asn1.encoders = require('./asn1/encoders'); asn1.js-5.0.0/lib/asn1/000077500000000000000000000000001317633451600144125ustar00rootroot00000000000000asn1.js-5.0.0/lib/asn1/api.js000066400000000000000000000027761317633451600155350ustar00rootroot00000000000000'use strict'; const asn1 = require('../asn1'); const inherits = require('inherits'); const api = exports; api.define = function define(name, body) { return new Entity(name, body); }; function Entity(name, body) { this.name = name; this.body = body; this.decoders = {}; this.encoders = {}; } Entity.prototype._createNamed = function createNamed(base) { let named; try { named = require('vm').runInThisContext( '(function ' + this.name + '(entity) {\n' + ' this._initNamed(entity);\n' + '})' ); } catch (e) { named = function (entity) { this._initNamed(entity); }; } inherits(named, base); named.prototype._initNamed = function initnamed(entity) { base.call(this, entity); }; return new named(this); }; Entity.prototype._getDecoder = function _getDecoder(enc) { enc = enc || 'der'; // Lazily create decoder if (!this.decoders.hasOwnProperty(enc)) this.decoders[enc] = this._createNamed(asn1.decoders[enc]); return this.decoders[enc]; }; Entity.prototype.decode = function decode(data, enc, options) { return this._getDecoder(enc).decode(data, options); }; Entity.prototype._getEncoder = function _getEncoder(enc) { enc = enc || 'der'; // Lazily create encoder if (!this.encoders.hasOwnProperty(enc)) this.encoders[enc] = this._createNamed(asn1.encoders[enc]); return this.encoders[enc]; }; Entity.prototype.encode = function encode(data, enc, /* internal */ reporter) { return this._getEncoder(enc).encode(data, reporter); }; asn1.js-5.0.0/lib/asn1/base/000077500000000000000000000000001317633451600153245ustar00rootroot00000000000000asn1.js-5.0.0/lib/asn1/base/buffer.js000066400000000000000000000060621317633451600171370ustar00rootroot00000000000000'use strict'; const inherits = require('inherits'); const Reporter = require('../base').Reporter; const Buffer = require('buffer').Buffer; function DecoderBuffer(base, options) { Reporter.call(this, options); if (!Buffer.isBuffer(base)) { this.error('Input not Buffer'); return; } this.base = base; this.offset = 0; this.length = base.length; } inherits(DecoderBuffer, Reporter); exports.DecoderBuffer = DecoderBuffer; DecoderBuffer.prototype.save = function save() { return { offset: this.offset, reporter: Reporter.prototype.save.call(this) }; }; DecoderBuffer.prototype.restore = function restore(save) { // Return skipped data const res = new DecoderBuffer(this.base); res.offset = save.offset; res.length = this.offset; this.offset = save.offset; Reporter.prototype.restore.call(this, save.reporter); return res; }; DecoderBuffer.prototype.isEmpty = function isEmpty() { return this.offset === this.length; }; DecoderBuffer.prototype.readUInt8 = function readUInt8(fail) { if (this.offset + 1 <= this.length) return this.base.readUInt8(this.offset++, true); else return this.error(fail || 'DecoderBuffer overrun'); }; DecoderBuffer.prototype.skip = function skip(bytes, fail) { if (!(this.offset + bytes <= this.length)) return this.error(fail || 'DecoderBuffer overrun'); const res = new DecoderBuffer(this.base); // Share reporter state res._reporterState = this._reporterState; res.offset = this.offset; res.length = this.offset + bytes; this.offset += bytes; return res; }; DecoderBuffer.prototype.raw = function raw(save) { return this.base.slice(save ? save.offset : this.offset, this.length); }; function EncoderBuffer(value, reporter) { if (Array.isArray(value)) { this.length = 0; this.value = value.map(function(item) { if (!(item instanceof EncoderBuffer)) item = new EncoderBuffer(item, reporter); this.length += item.length; return item; }, this); } else if (typeof value === 'number') { if (!(0 <= value && value <= 0xff)) return reporter.error('non-byte EncoderBuffer value'); this.value = value; this.length = 1; } else if (typeof value === 'string') { this.value = value; this.length = Buffer.byteLength(value); } else if (Buffer.isBuffer(value)) { this.value = value; this.length = value.length; } else { return reporter.error('Unsupported type: ' + typeof value); } } exports.EncoderBuffer = EncoderBuffer; EncoderBuffer.prototype.join = function join(out, offset) { if (!out) out = new Buffer(this.length); if (!offset) offset = 0; if (this.length === 0) return out; if (Array.isArray(this.value)) { this.value.forEach(function(item) { item.join(out, offset); offset += item.length; }); } else { if (typeof this.value === 'number') out[offset] = this.value; else if (typeof this.value === 'string') out.write(this.value, offset); else if (Buffer.isBuffer(this.value)) this.value.copy(out, offset); offset += this.length; } return out; }; asn1.js-5.0.0/lib/asn1/base/index.js000066400000000000000000000003451317633451600167730ustar00rootroot00000000000000'use strict'; const base = exports; base.Reporter = require('./reporter').Reporter; base.DecoderBuffer = require('./buffer').DecoderBuffer; base.EncoderBuffer = require('./buffer').EncoderBuffer; base.Node = require('./node'); asn1.js-5.0.0/lib/asn1/base/node.js000066400000000000000000000404521317633451600166140ustar00rootroot00000000000000'use strict'; const Reporter = require('../base').Reporter; const EncoderBuffer = require('../base').EncoderBuffer; const DecoderBuffer = require('../base').DecoderBuffer; const assert = require('minimalistic-assert'); // Supported tags const tags = [ 'seq', 'seqof', 'set', 'setof', 'objid', 'bool', 'gentime', 'utctime', 'null_', 'enum', 'int', 'objDesc', 'bitstr', 'bmpstr', 'charstr', 'genstr', 'graphstr', 'ia5str', 'iso646str', 'numstr', 'octstr', 'printstr', 't61str', 'unistr', 'utf8str', 'videostr' ]; // Public methods list const methods = [ 'key', 'obj', 'use', 'optional', 'explicit', 'implicit', 'def', 'choice', 'any', 'contains' ].concat(tags); // Overrided methods list const overrided = [ '_peekTag', '_decodeTag', '_use', '_decodeStr', '_decodeObjid', '_decodeTime', '_decodeNull', '_decodeInt', '_decodeBool', '_decodeList', '_encodeComposite', '_encodeStr', '_encodeObjid', '_encodeTime', '_encodeNull', '_encodeInt', '_encodeBool' ]; function Node(enc, parent) { const state = {}; this._baseState = state; state.enc = enc; state.parent = parent || null; state.children = null; // State state.tag = null; state.args = null; state.reverseArgs = null; state.choice = null; state.optional = false; state.any = false; state.obj = false; state.use = null; state.useDecoder = null; state.key = null; state['default'] = null; state.explicit = null; state.implicit = null; state.contains = null; // Should create new instance on each method if (!state.parent) { state.children = []; this._wrap(); } } module.exports = Node; const stateProps = [ 'enc', 'parent', 'children', 'tag', 'args', 'reverseArgs', 'choice', 'optional', 'any', 'obj', 'use', 'alteredUse', 'key', 'default', 'explicit', 'implicit', 'contains' ]; Node.prototype.clone = function clone() { const state = this._baseState; const cstate = {}; stateProps.forEach(function(prop) { cstate[prop] = state[prop]; }); const res = new this.constructor(cstate.parent); res._baseState = cstate; return res; }; Node.prototype._wrap = function wrap() { const state = this._baseState; methods.forEach(function(method) { this[method] = function _wrappedMethod() { const clone = new this.constructor(this); state.children.push(clone); return clone[method].apply(clone, arguments); }; }, this); }; Node.prototype._init = function init(body) { const state = this._baseState; assert(state.parent === null); body.call(this); // Filter children state.children = state.children.filter(function(child) { return child._baseState.parent === this; }, this); assert.equal(state.children.length, 1, 'Root node can have only one child'); }; Node.prototype._useArgs = function useArgs(args) { const state = this._baseState; // Filter children and args const children = args.filter(function(arg) { return arg instanceof this.constructor; }, this); args = args.filter(function(arg) { return !(arg instanceof this.constructor); }, this); if (children.length !== 0) { assert(state.children === null); state.children = children; // Replace parent to maintain backward link children.forEach(function(child) { child._baseState.parent = this; }, this); } if (args.length !== 0) { assert(state.args === null); state.args = args; state.reverseArgs = args.map(function(arg) { if (typeof arg !== 'object' || arg.constructor !== Object) return arg; const res = {}; Object.keys(arg).forEach(function(key) { if (key == (key | 0)) key |= 0; const value = arg[key]; res[value] = key; }); return res; }); } }; // // Overrided methods // overrided.forEach(function(method) { Node.prototype[method] = function _overrided() { const state = this._baseState; throw new Error(method + ' not implemented for encoding: ' + state.enc); }; }); // // Public methods // tags.forEach(function(tag) { Node.prototype[tag] = function _tagMethod() { const state = this._baseState; const args = Array.prototype.slice.call(arguments); assert(state.tag === null); state.tag = tag; this._useArgs(args); return this; }; }); Node.prototype.use = function use(item) { assert(item); const state = this._baseState; assert(state.use === null); state.use = item; return this; }; Node.prototype.optional = function optional() { const state = this._baseState; state.optional = true; return this; }; Node.prototype.def = function def(val) { const state = this._baseState; assert(state['default'] === null); state['default'] = val; state.optional = true; return this; }; Node.prototype.explicit = function explicit(num) { const state = this._baseState; assert(state.explicit === null && state.implicit === null); state.explicit = num; return this; }; Node.prototype.implicit = function implicit(num) { const state = this._baseState; assert(state.explicit === null && state.implicit === null); state.implicit = num; return this; }; Node.prototype.obj = function obj() { const state = this._baseState; const args = Array.prototype.slice.call(arguments); state.obj = true; if (args.length !== 0) this._useArgs(args); return this; }; Node.prototype.key = function key(newKey) { const state = this._baseState; assert(state.key === null); state.key = newKey; return this; }; Node.prototype.any = function any() { const state = this._baseState; state.any = true; return this; }; Node.prototype.choice = function choice(obj) { const state = this._baseState; assert(state.choice === null); state.choice = obj; this._useArgs(Object.keys(obj).map(function(key) { return obj[key]; })); return this; }; Node.prototype.contains = function contains(item) { const state = this._baseState; assert(state.use === null); state.contains = item; return this; }; // // Decoding // Node.prototype._decode = function decode(input, options) { const state = this._baseState; // Decode root node if (state.parent === null) return input.wrapResult(state.children[0]._decode(input, options)); let result = state['default']; let present = true; let prevKey = null; if (state.key !== null) prevKey = input.enterKey(state.key); // Check if tag is there if (state.optional) { let tag = null; if (state.explicit !== null) tag = state.explicit; else if (state.implicit !== null) tag = state.implicit; else if (state.tag !== null) tag = state.tag; if (tag === null && !state.any) { // Trial and Error const save = input.save(); try { if (state.choice === null) this._decodeGeneric(state.tag, input, options); else this._decodeChoice(input, options); present = true; } catch (e) { present = false; } input.restore(save); } else { present = this._peekTag(input, tag, state.any); if (input.isError(present)) return present; } } // Push object on stack let prevObj; if (state.obj && present) prevObj = input.enterObject(); if (present) { // Unwrap explicit values if (state.explicit !== null) { const explicit = this._decodeTag(input, state.explicit); if (input.isError(explicit)) return explicit; input = explicit; } const start = input.offset; // Unwrap implicit and normal values if (state.use === null && state.choice === null) { let save; if (state.any) save = input.save(); const body = this._decodeTag( input, state.implicit !== null ? state.implicit : state.tag, state.any ); if (input.isError(body)) return body; if (state.any) result = input.raw(save); else input = body; } if (options && options.track && state.tag !== null) options.track(input.path(), start, input.length, 'tagged'); if (options && options.track && state.tag !== null) options.track(input.path(), input.offset, input.length, 'content'); // Select proper method for tag if (state.any) { // no-op } else if (state.choice === null) { result = this._decodeGeneric(state.tag, input, options); } else { result = this._decodeChoice(input, options); } if (input.isError(result)) return result; // Decode children if (!state.any && state.choice === null && state.children !== null) { state.children.forEach(function decodeChildren(child) { // NOTE: We are ignoring errors here, to let parser continue with other // parts of encoded data child._decode(input, options); }); } // Decode contained/encoded by schema, only in bit or octet strings if (state.contains && (state.tag === 'octstr' || state.tag === 'bitstr')) { const data = new DecoderBuffer(result); result = this._getUse(state.contains, input._reporterState.obj) ._decode(data, options); } } // Pop object if (state.obj && present) result = input.leaveObject(prevObj); // Set key if (state.key !== null && (result !== null || present === true)) input.leaveKey(prevKey, state.key, result); else if (prevKey !== null) input.exitKey(prevKey); return result; }; Node.prototype._decodeGeneric = function decodeGeneric(tag, input, options) { const state = this._baseState; if (tag === 'seq' || tag === 'set') return null; if (tag === 'seqof' || tag === 'setof') return this._decodeList(input, tag, state.args[0], options); else if (/str$/.test(tag)) return this._decodeStr(input, tag, options); else if (tag === 'objid' && state.args) return this._decodeObjid(input, state.args[0], state.args[1], options); else if (tag === 'objid') return this._decodeObjid(input, null, null, options); else if (tag === 'gentime' || tag === 'utctime') return this._decodeTime(input, tag, options); else if (tag === 'null_') return this._decodeNull(input, options); else if (tag === 'bool') return this._decodeBool(input, options); else if (tag === 'objDesc') return this._decodeStr(input, tag, options); else if (tag === 'int' || tag === 'enum') return this._decodeInt(input, state.args && state.args[0], options); if (state.use !== null) { return this._getUse(state.use, input._reporterState.obj) ._decode(input, options); } else { return input.error('unknown tag: ' + tag); } }; Node.prototype._getUse = function _getUse(entity, obj) { const state = this._baseState; // Create altered use decoder if implicit is set state.useDecoder = this._use(entity, obj); assert(state.useDecoder._baseState.parent === null); state.useDecoder = state.useDecoder._baseState.children[0]; if (state.implicit !== state.useDecoder._baseState.implicit) { state.useDecoder = state.useDecoder.clone(); state.useDecoder._baseState.implicit = state.implicit; } return state.useDecoder; }; Node.prototype._decodeChoice = function decodeChoice(input, options) { const state = this._baseState; let result = null; let match = false; Object.keys(state.choice).some(function(key) { const save = input.save(); const node = state.choice[key]; try { const value = node._decode(input, options); if (input.isError(value)) return false; result = { type: key, value: value }; match = true; } catch (e) { input.restore(save); return false; } return true; }, this); if (!match) return input.error('Choice not matched'); return result; }; // // Encoding // Node.prototype._createEncoderBuffer = function createEncoderBuffer(data) { return new EncoderBuffer(data, this.reporter); }; Node.prototype._encode = function encode(data, reporter, parent) { const state = this._baseState; if (state['default'] !== null && state['default'] === data) return; const result = this._encodeValue(data, reporter, parent); if (result === undefined) return; if (this._skipDefault(result, reporter, parent)) return; return result; }; Node.prototype._encodeValue = function encode(data, reporter, parent) { const state = this._baseState; // Decode root node if (state.parent === null) return state.children[0]._encode(data, reporter || new Reporter()); let result = null; // Set reporter to share it with a child class this.reporter = reporter; // Check if data is there if (state.optional && data === undefined) { if (state['default'] !== null) data = state['default']; else return; } // Encode children first let content = null; let primitive = false; if (state.any) { // Anything that was given is translated to buffer result = this._createEncoderBuffer(data); } else if (state.choice) { result = this._encodeChoice(data, reporter); } else if (state.contains) { content = this._getUse(state.contains, parent)._encode(data, reporter); primitive = true; } else if (state.children) { content = state.children.map(function(child) { if (child._baseState.tag === 'null_') return child._encode(null, reporter, data); if (child._baseState.key === null) return reporter.error('Child should have a key'); const prevKey = reporter.enterKey(child._baseState.key); if (typeof data !== 'object') return reporter.error('Child expected, but input is not object'); const res = child._encode(data[child._baseState.key], reporter, data); reporter.leaveKey(prevKey); return res; }, this).filter(function(child) { return child; }); content = this._createEncoderBuffer(content); } else { if (state.tag === 'seqof' || state.tag === 'setof') { // TODO(indutny): this should be thrown on DSL level if (!(state.args && state.args.length === 1)) return reporter.error('Too many args for : ' + state.tag); if (!Array.isArray(data)) return reporter.error('seqof/setof, but data is not Array'); const child = this.clone(); child._baseState.implicit = null; content = this._createEncoderBuffer(data.map(function(item) { const state = this._baseState; return this._getUse(state.args[0], data)._encode(item, reporter); }, child)); } else if (state.use !== null) { result = this._getUse(state.use, parent)._encode(data, reporter); } else { content = this._encodePrimitive(state.tag, data); primitive = true; } } // Encode data itself if (!state.any && state.choice === null) { const tag = state.implicit !== null ? state.implicit : state.tag; const cls = state.implicit === null ? 'universal' : 'context'; if (tag === null) { if (state.use === null) reporter.error('Tag could be omitted only for .use()'); } else { if (state.use === null) result = this._encodeComposite(tag, primitive, cls, content); } } // Wrap in explicit if (state.explicit !== null) result = this._encodeComposite(state.explicit, false, 'context', result); return result; }; Node.prototype._encodeChoice = function encodeChoice(data, reporter) { const state = this._baseState; const node = state.choice[data.type]; if (!node) { assert( false, data.type + ' not found in ' + JSON.stringify(Object.keys(state.choice))); } return node._encode(data.value, reporter); }; Node.prototype._encodePrimitive = function encodePrimitive(tag, data) { const state = this._baseState; if (/str$/.test(tag)) return this._encodeStr(data, tag); else if (tag === 'objid' && state.args) return this._encodeObjid(data, state.reverseArgs[0], state.args[1]); else if (tag === 'objid') return this._encodeObjid(data, null, null); else if (tag === 'gentime' || tag === 'utctime') return this._encodeTime(data, tag); else if (tag === 'null_') return this._encodeNull(); else if (tag === 'int' || tag === 'enum') return this._encodeInt(data, state.args && state.reverseArgs[0]); else if (tag === 'bool') return this._encodeBool(data); else if (tag === 'objDesc') return this._encodeStr(data, tag); else throw new Error('Unsupported tag: ' + tag); }; Node.prototype._isNumstr = function isNumstr(str) { return /^[0-9 ]*$/.test(str); }; Node.prototype._isPrintstr = function isPrintstr(str) { return /^[A-Za-z0-9 '()+,-./:=?]*$/.test(str); }; asn1.js-5.0.0/lib/asn1/base/reporter.js000066400000000000000000000051721317633451600175310ustar00rootroot00000000000000'use strict'; const inherits = require('inherits'); function Reporter(options) { this._reporterState = { obj: null, path: [], options: options || {}, errors: [] }; } exports.Reporter = Reporter; Reporter.prototype.isError = function isError(obj) { return obj instanceof ReporterError; }; Reporter.prototype.save = function save() { const state = this._reporterState; return { obj: state.obj, pathLen: state.path.length }; }; Reporter.prototype.restore = function restore(data) { const state = this._reporterState; state.obj = data.obj; state.path = state.path.slice(0, data.pathLen); }; Reporter.prototype.enterKey = function enterKey(key) { return this._reporterState.path.push(key); }; Reporter.prototype.exitKey = function exitKey(index) { const state = this._reporterState; state.path = state.path.slice(0, index - 1); }; Reporter.prototype.leaveKey = function leaveKey(index, key, value) { const state = this._reporterState; this.exitKey(index); if (state.obj !== null) state.obj[key] = value; }; Reporter.prototype.path = function path() { return this._reporterState.path.join('/'); }; Reporter.prototype.enterObject = function enterObject() { const state = this._reporterState; const prev = state.obj; state.obj = {}; return prev; }; Reporter.prototype.leaveObject = function leaveObject(prev) { const state = this._reporterState; const now = state.obj; state.obj = prev; return now; }; Reporter.prototype.error = function error(msg) { let err; const state = this._reporterState; const inherited = msg instanceof ReporterError; if (inherited) { err = msg; } else { err = new ReporterError(state.path.map(function(elem) { return '[' + JSON.stringify(elem) + ']'; }).join(''), msg.message || msg, msg.stack); } if (!state.options.partial) throw err; if (!inherited) state.errors.push(err); return err; }; Reporter.prototype.wrapResult = function wrapResult(result) { const state = this._reporterState; if (!state.options.partial) return result; return { result: this.isError(result) ? null : result, errors: state.errors }; }; function ReporterError(path, msg) { this.path = path; this.rethrow(msg); } inherits(ReporterError, Error); ReporterError.prototype.rethrow = function rethrow(msg) { this.message = msg + ' at: ' + (this.path || '(shallow)'); if (Error.captureStackTrace) Error.captureStackTrace(this, ReporterError); if (!this.stack) { try { // IE only adds stack when thrown throw new Error(this.message); } catch (e) { this.stack = e.stack; } } return this; }; asn1.js-5.0.0/lib/asn1/constants/000077500000000000000000000000001317633451600164265ustar00rootroot00000000000000asn1.js-5.0.0/lib/asn1/constants/der.js000066400000000000000000000014511317633451600175370ustar00rootroot00000000000000'use strict'; const constants = require('../constants'); exports.tagClass = { 0: 'universal', 1: 'application', 2: 'context', 3: 'private' }; exports.tagClassByName = constants._reverse(exports.tagClass); exports.tag = { 0x00: 'end', 0x01: 'bool', 0x02: 'int', 0x03: 'bitstr', 0x04: 'octstr', 0x05: 'null_', 0x06: 'objid', 0x07: 'objDesc', 0x08: 'external', 0x09: 'real', 0x0a: 'enum', 0x0b: 'embed', 0x0c: 'utf8str', 0x0d: 'relativeOid', 0x10: 'seq', 0x11: 'set', 0x12: 'numstr', 0x13: 'printstr', 0x14: 't61str', 0x15: 'videostr', 0x16: 'ia5str', 0x17: 'utctime', 0x18: 'gentime', 0x19: 'graphstr', 0x1a: 'iso646str', 0x1b: 'genstr', 0x1c: 'unistr', 0x1d: 'charstr', 0x1e: 'bmpstr' }; exports.tagByName = constants._reverse(exports.tag); asn1.js-5.0.0/lib/asn1/constants/index.js000066400000000000000000000005601317633451600200740ustar00rootroot00000000000000'use strict'; const constants = exports; // Helper constants._reverse = function reverse(map) { const res = {}; Object.keys(map).forEach(function(key) { // Convert key to integer if it is stringified if ((key | 0) == key) key = key | 0; const value = map[key]; res[value] = key; }); return res; }; constants.der = require('./der'); asn1.js-5.0.0/lib/asn1/decoders/000077500000000000000000000000001317633451600162025ustar00rootroot00000000000000asn1.js-5.0.0/lib/asn1/decoders/der.js000066400000000000000000000175211317633451600173200ustar00rootroot00000000000000'use strict'; const inherits = require('inherits'); const asn1 = require('../../asn1'); const base = asn1.base; const bignum = asn1.bignum; // Import DER constants const der = asn1.constants.der; function DERDecoder(entity) { this.enc = 'der'; this.name = entity.name; this.entity = entity; // Construct base tree this.tree = new DERNode(); this.tree._init(entity.body); } module.exports = DERDecoder; DERDecoder.prototype.decode = function decode(data, options) { if (!(data instanceof base.DecoderBuffer)) data = new base.DecoderBuffer(data, options); return this.tree._decode(data, options); }; // Tree methods function DERNode(parent) { base.Node.call(this, 'der', parent); } inherits(DERNode, base.Node); DERNode.prototype._peekTag = function peekTag(buffer, tag, any) { if (buffer.isEmpty()) return false; const state = buffer.save(); const decodedTag = derDecodeTag(buffer, 'Failed to peek tag: "' + tag + '"'); if (buffer.isError(decodedTag)) return decodedTag; buffer.restore(state); return decodedTag.tag === tag || decodedTag.tagStr === tag || (decodedTag.tagStr + 'of') === tag || any; }; DERNode.prototype._decodeTag = function decodeTag(buffer, tag, any) { const decodedTag = derDecodeTag(buffer, 'Failed to decode tag of "' + tag + '"'); if (buffer.isError(decodedTag)) return decodedTag; let len = derDecodeLen(buffer, decodedTag.primitive, 'Failed to get length of "' + tag + '"'); // Failure if (buffer.isError(len)) return len; if (!any && decodedTag.tag !== tag && decodedTag.tagStr !== tag && decodedTag.tagStr + 'of' !== tag) { return buffer.error('Failed to match tag: "' + tag + '"'); } if (decodedTag.primitive || len !== null) return buffer.skip(len, 'Failed to match body of: "' + tag + '"'); // Indefinite length... find END tag const state = buffer.save(); const res = this._skipUntilEnd( buffer, 'Failed to skip indefinite length body: "' + this.tag + '"'); if (buffer.isError(res)) return res; len = buffer.offset - state.offset; buffer.restore(state); return buffer.skip(len, 'Failed to match body of: "' + tag + '"'); }; DERNode.prototype._skipUntilEnd = function skipUntilEnd(buffer, fail) { for (;;) { const tag = derDecodeTag(buffer, fail); if (buffer.isError(tag)) return tag; const len = derDecodeLen(buffer, tag.primitive, fail); if (buffer.isError(len)) return len; let res; if (tag.primitive || len !== null) res = buffer.skip(len); else res = this._skipUntilEnd(buffer, fail); // Failure if (buffer.isError(res)) return res; if (tag.tagStr === 'end') break; } }; DERNode.prototype._decodeList = function decodeList(buffer, tag, decoder, options) { const result = []; while (!buffer.isEmpty()) { const possibleEnd = this._peekTag(buffer, 'end'); if (buffer.isError(possibleEnd)) return possibleEnd; const res = decoder.decode(buffer, 'der', options); if (buffer.isError(res) && possibleEnd) break; result.push(res); } return result; }; DERNode.prototype._decodeStr = function decodeStr(buffer, tag) { if (tag === 'bitstr') { const unused = buffer.readUInt8(); if (buffer.isError(unused)) return unused; return { unused: unused, data: buffer.raw() }; } else if (tag === 'bmpstr') { const raw = buffer.raw(); if (raw.length % 2 === 1) return buffer.error('Decoding of string type: bmpstr length mismatch'); let str = ''; for (let i = 0; i < raw.length / 2; i++) { str += String.fromCharCode(raw.readUInt16BE(i * 2)); } return str; } else if (tag === 'numstr') { const numstr = buffer.raw().toString('ascii'); if (!this._isNumstr(numstr)) { return buffer.error('Decoding of string type: ' + 'numstr unsupported characters'); } return numstr; } else if (tag === 'octstr') { return buffer.raw(); } else if (tag === 'objDesc') { return buffer.raw(); } else if (tag === 'printstr') { const printstr = buffer.raw().toString('ascii'); if (!this._isPrintstr(printstr)) { return buffer.error('Decoding of string type: ' + 'printstr unsupported characters'); } return printstr; } else if (/str$/.test(tag)) { return buffer.raw().toString(); } else { return buffer.error('Decoding of string type: ' + tag + ' unsupported'); } }; DERNode.prototype._decodeObjid = function decodeObjid(buffer, values, relative) { let result; const identifiers = []; let ident = 0; let subident = 0; while (!buffer.isEmpty()) { subident = buffer.readUInt8(); ident <<= 7; ident |= subident & 0x7f; if ((subident & 0x80) === 0) { identifiers.push(ident); ident = 0; } } if (subident & 0x80) identifiers.push(ident); const first = (identifiers[0] / 40) | 0; const second = identifiers[0] % 40; if (relative) result = identifiers; else result = [first, second].concat(identifiers.slice(1)); if (values) { let tmp = values[result.join(' ')]; if (tmp === undefined) tmp = values[result.join('.')]; if (tmp !== undefined) result = tmp; } return result; }; DERNode.prototype._decodeTime = function decodeTime(buffer, tag) { const str = buffer.raw().toString(); let year; let mon; let day; let hour; let min; let sec; if (tag === 'gentime') { year = str.slice(0, 4) | 0; mon = str.slice(4, 6) | 0; day = str.slice(6, 8) | 0; hour = str.slice(8, 10) | 0; min = str.slice(10, 12) | 0; sec = str.slice(12, 14) | 0; } else if (tag === 'utctime') { year = str.slice(0, 2) | 0; mon = str.slice(2, 4) | 0; day = str.slice(4, 6) | 0; hour = str.slice(6, 8) | 0; min = str.slice(8, 10) | 0; sec = str.slice(10, 12) | 0; if (year < 70) year = 2000 + year; else year = 1900 + year; } else { return buffer.error('Decoding ' + tag + ' time is not supported yet'); } return Date.UTC(year, mon - 1, day, hour, min, sec, 0); }; DERNode.prototype._decodeNull = function decodeNull() { return null; }; DERNode.prototype._decodeBool = function decodeBool(buffer) { const res = buffer.readUInt8(); if (buffer.isError(res)) return res; else return res !== 0; }; DERNode.prototype._decodeInt = function decodeInt(buffer, values) { // Bigint, return as it is (assume big endian) const raw = buffer.raw(); let res = new bignum(raw); if (values) res = values[res.toString(10)] || res; return res; }; DERNode.prototype._use = function use(entity, obj) { if (typeof entity === 'function') entity = entity(obj); return entity._getDecoder('der').tree; }; // Utility methods function derDecodeTag(buf, fail) { let tag = buf.readUInt8(fail); if (buf.isError(tag)) return tag; const cls = der.tagClass[tag >> 6]; const primitive = (tag & 0x20) === 0; // Multi-octet tag - load if ((tag & 0x1f) === 0x1f) { let oct = tag; tag = 0; while ((oct & 0x80) === 0x80) { oct = buf.readUInt8(fail); if (buf.isError(oct)) return oct; tag <<= 7; tag |= oct & 0x7f; } } else { tag &= 0x1f; } const tagStr = der.tag[tag]; return { cls: cls, primitive: primitive, tag: tag, tagStr: tagStr }; } function derDecodeLen(buf, primitive, fail) { let len = buf.readUInt8(fail); if (buf.isError(len)) return len; // Indefinite form if (!primitive && len === 0x80) return null; // Definite form if ((len & 0x80) === 0) { // Short form return len; } // Long form const num = len & 0x7f; if (num > 4) return buf.error('length octect is too long'); len = 0; for (let i = 0; i < num; i++) { len <<= 8; const j = buf.readUInt8(fail); if (buf.isError(j)) return j; len |= j; } return len; } asn1.js-5.0.0/lib/asn1/decoders/index.js000066400000000000000000000001541317633451600176470ustar00rootroot00000000000000'use strict'; const decoders = exports; decoders.der = require('./der'); decoders.pem = require('./pem'); asn1.js-5.0.0/lib/asn1/decoders/pem.js000066400000000000000000000022741317633451600173260ustar00rootroot00000000000000'use strict'; const inherits = require('inherits'); const Buffer = require('buffer').Buffer; const DERDecoder = require('./der'); function PEMDecoder(entity) { DERDecoder.call(this, entity); this.enc = 'pem'; } inherits(PEMDecoder, DERDecoder); module.exports = PEMDecoder; PEMDecoder.prototype.decode = function decode(data, options) { const lines = data.toString().split(/[\r\n]+/g); const label = options.label.toUpperCase(); const re = /^-----(BEGIN|END) ([^-]+)-----$/; let start = -1; let end = -1; for (let i = 0; i < lines.length; i++) { const match = lines[i].match(re); if (match === null) continue; if (match[2] !== label) continue; if (start === -1) { if (match[1] !== 'BEGIN') break; start = i; } else { if (match[1] !== 'END') break; end = i; break; } } if (start === -1 || end === -1) throw new Error('PEM section not found for: ' + label); const base64 = lines.slice(start + 1, end).join(''); // Remove excessive symbols base64.replace(/[^a-z0-9+/=]+/gi, ''); const input = new Buffer(base64, 'base64'); return DERDecoder.prototype.decode.call(this, input, options); }; asn1.js-5.0.0/lib/asn1/encoders/000077500000000000000000000000001317633451600162145ustar00rootroot00000000000000asn1.js-5.0.0/lib/asn1/encoders/der.js000066400000000000000000000173061317633451600173330ustar00rootroot00000000000000'use strict'; const inherits = require('inherits'); const Buffer = require('buffer').Buffer; const asn1 = require('../../asn1'); const base = asn1.base; // Import DER constants const der = asn1.constants.der; function DEREncoder(entity) { this.enc = 'der'; this.name = entity.name; this.entity = entity; // Construct base tree this.tree = new DERNode(); this.tree._init(entity.body); } module.exports = DEREncoder; DEREncoder.prototype.encode = function encode(data, reporter) { return this.tree._encode(data, reporter).join(); }; // Tree methods function DERNode(parent) { base.Node.call(this, 'der', parent); } inherits(DERNode, base.Node); DERNode.prototype._encodeComposite = function encodeComposite(tag, primitive, cls, content) { const encodedTag = encodeTag(tag, primitive, cls, this.reporter); // Short form if (content.length < 0x80) { const header = new Buffer(2); header[0] = encodedTag; header[1] = content.length; return this._createEncoderBuffer([ header, content ]); } // Long form // Count octets required to store length let lenOctets = 1; for (let i = content.length; i >= 0x100; i >>= 8) lenOctets++; const header = new Buffer(1 + 1 + lenOctets); header[0] = encodedTag; header[1] = 0x80 | lenOctets; for (let i = 1 + lenOctets, j = content.length; j > 0; i--, j >>= 8) header[i] = j & 0xff; return this._createEncoderBuffer([ header, content ]); }; DERNode.prototype._encodeStr = function encodeStr(str, tag) { if (tag === 'bitstr') { return this._createEncoderBuffer([ str.unused | 0, str.data ]); } else if (tag === 'bmpstr') { const buf = new Buffer(str.length * 2); for (let i = 0; i < str.length; i++) { buf.writeUInt16BE(str.charCodeAt(i), i * 2); } return this._createEncoderBuffer(buf); } else if (tag === 'numstr') { if (!this._isNumstr(str)) { return this.reporter.error('Encoding of string type: numstr supports ' + 'only digits and space'); } return this._createEncoderBuffer(str); } else if (tag === 'printstr') { if (!this._isPrintstr(str)) { return this.reporter.error('Encoding of string type: printstr supports ' + 'only latin upper and lower case letters, ' + 'digits, space, apostrophe, left and rigth ' + 'parenthesis, plus sign, comma, hyphen, ' + 'dot, slash, colon, equal sign, ' + 'question mark'); } return this._createEncoderBuffer(str); } else if (/str$/.test(tag)) { return this._createEncoderBuffer(str); } else if (tag === 'objDesc') { return this._createEncoderBuffer(str); } else { return this.reporter.error('Encoding of string type: ' + tag + ' unsupported'); } }; DERNode.prototype._encodeObjid = function encodeObjid(id, values, relative) { if (typeof id === 'string') { if (!values) return this.reporter.error('string objid given, but no values map found'); if (!values.hasOwnProperty(id)) return this.reporter.error('objid not found in values map'); id = values[id].split(/[\s.]+/g); for (let i = 0; i < id.length; i++) id[i] |= 0; } else if (Array.isArray(id)) { id = id.slice(); for (let i = 0; i < id.length; i++) id[i] |= 0; } if (!Array.isArray(id)) { return this.reporter.error('objid() should be either array or string, ' + 'got: ' + JSON.stringify(id)); } if (!relative) { if (id[1] >= 40) return this.reporter.error('Second objid identifier OOB'); id.splice(0, 2, id[0] * 40 + id[1]); } // Count number of octets let size = 0; for (let i = 0; i < id.length; i++) { let ident = id[i]; for (size++; ident >= 0x80; ident >>= 7) size++; } const objid = new Buffer(size); let offset = objid.length - 1; for (let i = id.length - 1; i >= 0; i--) { let ident = id[i]; objid[offset--] = ident & 0x7f; while ((ident >>= 7) > 0) objid[offset--] = 0x80 | (ident & 0x7f); } return this._createEncoderBuffer(objid); }; function two(num) { if (num < 10) return '0' + num; else return num; } DERNode.prototype._encodeTime = function encodeTime(time, tag) { let str; const date = new Date(time); if (tag === 'gentime') { str = [ two(date.getFullYear()), two(date.getUTCMonth() + 1), two(date.getUTCDate()), two(date.getUTCHours()), two(date.getUTCMinutes()), two(date.getUTCSeconds()), 'Z' ].join(''); } else if (tag === 'utctime') { str = [ two(date.getFullYear() % 100), two(date.getUTCMonth() + 1), two(date.getUTCDate()), two(date.getUTCHours()), two(date.getUTCMinutes()), two(date.getUTCSeconds()), 'Z' ].join(''); } else { this.reporter.error('Encoding ' + tag + ' time is not supported yet'); } return this._encodeStr(str, 'octstr'); }; DERNode.prototype._encodeNull = function encodeNull() { return this._createEncoderBuffer(''); }; DERNode.prototype._encodeInt = function encodeInt(num, values) { if (typeof num === 'string') { if (!values) return this.reporter.error('String int or enum given, but no values map'); if (!values.hasOwnProperty(num)) { return this.reporter.error('Values map doesn\'t contain: ' + JSON.stringify(num)); } num = values[num]; } // Bignum, assume big endian if (typeof num !== 'number' && !Buffer.isBuffer(num)) { const numArray = num.toArray(); if (!num.sign && numArray[0] & 0x80) { numArray.unshift(0); } num = new Buffer(numArray); } if (Buffer.isBuffer(num)) { let size = num.length; if (num.length === 0) size++; const out = new Buffer(size); num.copy(out); if (num.length === 0) out[0] = 0; return this._createEncoderBuffer(out); } if (num < 0x80) return this._createEncoderBuffer(num); if (num < 0x100) return this._createEncoderBuffer([0, num]); let size = 1; for (let i = num; i >= 0x100; i >>= 8) size++; const out = new Array(size); for (let i = out.length - 1; i >= 0; i--) { out[i] = num & 0xff; num >>= 8; } if(out[0] & 0x80) { out.unshift(0); } return this._createEncoderBuffer(new Buffer(out)); }; DERNode.prototype._encodeBool = function encodeBool(value) { return this._createEncoderBuffer(value ? 0xff : 0); }; DERNode.prototype._use = function use(entity, obj) { if (typeof entity === 'function') entity = entity(obj); return entity._getEncoder('der').tree; }; DERNode.prototype._skipDefault = function skipDefault(dataBuffer, reporter, parent) { const state = this._baseState; let i; if (state['default'] === null) return false; const data = dataBuffer.join(); if (state.defaultBuffer === undefined) state.defaultBuffer = this._encodeValue(state['default'], reporter, parent).join(); if (data.length !== state.defaultBuffer.length) return false; for (i=0; i < data.length; i++) if (data[i] !== state.defaultBuffer[i]) return false; return true; }; // Utility methods function encodeTag(tag, primitive, cls, reporter) { let res; if (tag === 'seqof') tag = 'seq'; else if (tag === 'setof') tag = 'set'; if (der.tagByName.hasOwnProperty(tag)) res = der.tagByName[tag]; else if (typeof tag === 'number' && (tag | 0) === tag) res = tag; else return reporter.error('Unknown tag: ' + tag); if (res >= 0x1f) return reporter.error('Multi-octet tag encoding unsupported'); if (!primitive) res |= 0x20; res |= (der.tagClassByName[cls || 'universal'] << 6); return res; } asn1.js-5.0.0/lib/asn1/encoders/index.js000066400000000000000000000001541317633451600176610ustar00rootroot00000000000000'use strict'; const encoders = exports; encoders.der = require('./der'); encoders.pem = require('./pem'); asn1.js-5.0.0/lib/asn1/encoders/pem.js000066400000000000000000000011461317633451600173350ustar00rootroot00000000000000'use strict'; const inherits = require('inherits'); const DEREncoder = require('./der'); function PEMEncoder(entity) { DEREncoder.call(this, entity); this.enc = 'pem'; } inherits(PEMEncoder, DEREncoder); module.exports = PEMEncoder; PEMEncoder.prototype.encode = function encode(data, options) { const buf = DEREncoder.prototype.encode.call(this, data); const p = buf.toString('base64'); const out = [ '-----BEGIN ' + options.label + '-----' ]; for (let i = 0; i < p.length; i += 64) out.push(p.slice(i, i + 64)); out.push('-----END ' + options.label + '-----'); return out.join('\n'); }; asn1.js-5.0.0/package-lock.json000066400000000000000000001316651317633451600162320ustar00rootroot00000000000000{ "name": "asn1.js", "version": "5.0.0", "lockfileVersion": 1, "requires": true, "dependencies": { "acorn": { "version": "5.2.1", "resolved": "https://registry.npmjs.org/acorn/-/acorn-5.2.1.tgz", "integrity": "sha512-jG0u7c4Ly+3QkkW18V+NRDN+4bWHdln30NL1ZL2AvFZZmQe/BfopYCtghCKKVBUSetZ4QKcyA0pY6/4Gw8Pv8w==", "dev": true }, "acorn-jsx": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/acorn-jsx/-/acorn-jsx-3.0.1.tgz", "integrity": "sha1-r9+UiPsezvyDSPb7IvRk4ypYs2s=", "dev": true, "requires": { "acorn": "3.3.0" }, "dependencies": { "acorn": { "version": "3.3.0", "resolved": "https://registry.npmjs.org/acorn/-/acorn-3.3.0.tgz", "integrity": "sha1-ReN/s56No/JbruP/U2niu18iAXo=", "dev": true } } }, "ajv": { "version": "5.3.0", "resolved": "https://registry.npmjs.org/ajv/-/ajv-5.3.0.tgz", "integrity": "sha1-RBT/dKUIecII7l/cgm4ywwNUnto=", "dev": true, "requires": { "co": "4.6.0", "fast-deep-equal": "1.0.0", "fast-json-stable-stringify": "2.0.0", "json-schema-traverse": "0.3.1" } }, "ajv-keywords": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/ajv-keywords/-/ajv-keywords-2.1.1.tgz", "integrity": "sha1-YXmX/F9gV2iUxDX5QNgZ4TW4B2I=", "dev": true }, "ansi-escapes": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/ansi-escapes/-/ansi-escapes-3.0.0.tgz", "integrity": "sha512-O/klc27mWNUigtv0F8NJWbLF00OcegQalkqKURWdosW08YZKi4m6CnSUSvIZG1otNJbTWhN01Hhz389DW7mvDQ==", "dev": true }, "ansi-regex": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-2.1.1.tgz", "integrity": "sha1-w7M6te42DYbg5ijwRorn7yfWVN8=", "dev": true }, "ansi-styles": { "version": "2.2.1", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-2.2.1.tgz", "integrity": "sha1-tDLdM1i2NM914eRmQ2gkBTPB3b4=", "dev": true }, "argparse": { "version": "1.0.9", "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.9.tgz", "integrity": "sha1-c9g7wmP4bpf4zE9rrhsOkKfSLIY=", "dev": true, "requires": { "sprintf-js": "1.0.3" } }, "array-union": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/array-union/-/array-union-1.0.2.tgz", "integrity": "sha1-mjRBDk9OPaI96jdb5b5w8kd47Dk=", "dev": true, "requires": { "array-uniq": "1.0.3" } }, "array-uniq": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/array-uniq/-/array-uniq-1.0.3.tgz", "integrity": "sha1-r2rId6Jcx/dOBYiUdThY39sk/bY=", "dev": true }, "arrify": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/arrify/-/arrify-1.0.1.tgz", "integrity": "sha1-iYUI2iIm84DfkEcoRWhJwVAaSw0=", "dev": true }, "babel-code-frame": { "version": "6.26.0", "resolved": "https://registry.npmjs.org/babel-code-frame/-/babel-code-frame-6.26.0.tgz", "integrity": "sha1-Y/1D99weO7fONZR9uP42mj9Yx0s=", "dev": true, "requires": { "chalk": "1.1.3", "esutils": "2.0.2", "js-tokens": "3.0.2" }, "dependencies": { "chalk": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/chalk/-/chalk-1.1.3.tgz", "integrity": "sha1-qBFcVeSnAv5NFQq9OHKCKn4J/Jg=", "dev": true, "requires": { "ansi-styles": "2.2.1", "escape-string-regexp": "http://npm.paypal.com/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz", "has-ansi": "2.0.0", "strip-ansi": "3.0.1", "supports-color": "2.0.0" } }, "strip-ansi": { "version": "3.0.1", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-3.0.1.tgz", "integrity": "sha1-ajhfuIU9lS1f8F0Oiq+UJ43GPc8=", "dev": true, "requires": { "ansi-regex": "2.1.1" } }, "supports-color": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-2.0.0.tgz", "integrity": "sha1-U10EXOa2Nj+kARcIRimZXp3zJMc=", "dev": true } } }, "balanced-match": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=", "dev": true }, "bn.js": { "version": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.6.tgz", "integrity": "sha1-UzRK2xRhehP26N0s4okF0cC6MhU=" }, "brace-expansion": { "version": "1.1.8", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.8.tgz", "integrity": "sha1-wHshHHyVLsH479Uad+8NHTmQopI=", "dev": true, "requires": { "balanced-match": "1.0.0", "concat-map": "0.0.1" } }, "caller-path": { "version": "0.1.0", "resolved": "https://registry.npmjs.org/caller-path/-/caller-path-0.1.0.tgz", "integrity": "sha1-lAhe9jWB7NPaqSREqP6U6CV3dR8=", "dev": true, "requires": { "callsites": "0.2.0" } }, "callsites": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/callsites/-/callsites-0.2.0.tgz", "integrity": "sha1-r6uWJikQp/M8GaV3WCXGnzTjUMo=", "dev": true }, "chalk": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/chalk/-/chalk-2.3.0.tgz", "integrity": "sha512-Az5zJR2CBujap2rqXGaJKaPHyJ0IrUimvYNX+ncCy8PJP4ltOGTrHUIo097ZaL2zMeKYpiCdqDvS6zdrTFok3Q==", "dev": true, "requires": { "ansi-styles": "3.2.0", "escape-string-regexp": "1.0.5", "supports-color": "4.5.0" }, "dependencies": { "ansi-styles": { "version": "3.2.0", "resolved": "https://registry.npmjs.org/ansi-styles/-/ansi-styles-3.2.0.tgz", "integrity": "sha512-NnSOmMEYtVR2JVMIGTzynRkkaxtiq1xnFBcdQD/DnNCYPoEPsVJhM98BDyaoNOQIi7p4okdi3E27eN7GQbsUug==", "dev": true, "requires": { "color-convert": "1.9.0" } }, "escape-string-regexp": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", "dev": true }, "supports-color": { "version": "4.5.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.5.0.tgz", "integrity": "sha1-vnoN5ITexcXN34s9WRJQRJEvY1s=", "dev": true, "requires": { "has-flag": "2.0.0" } } } }, "circular-json": { "version": "0.3.3", "resolved": "https://registry.npmjs.org/circular-json/-/circular-json-0.3.3.tgz", "integrity": "sha512-UZK3NBx2Mca+b5LsG7bY183pHWt5Y1xts4P3Pz7ENTwGVnJOUWbRb3ocjvX7hx9tq/yTAdclXm9sZ38gNuem4A==", "dev": true }, "cli-cursor": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/cli-cursor/-/cli-cursor-2.1.0.tgz", "integrity": "sha1-s12sN2R5+sw+lHR9QdDQ9SOP/LU=", "dev": true, "requires": { "restore-cursor": "2.0.0" } }, "cli-width": { "version": "2.2.0", "resolved": "https://registry.npmjs.org/cli-width/-/cli-width-2.2.0.tgz", "integrity": "sha1-/xnt6Kml5XkyQUewwR8PvLq+1jk=", "dev": true }, "co": { "version": "4.6.0", "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=", "dev": true }, "color-convert": { "version": "1.9.0", "resolved": "https://registry.npmjs.org/color-convert/-/color-convert-1.9.0.tgz", "integrity": "sha1-Gsz5fdc5uYO/mU1W/sj5WFNkG3o=", "dev": true, "requires": { "color-name": "1.1.3" } }, "color-name": { "version": "1.1.3", "resolved": "https://registry.npmjs.org/color-name/-/color-name-1.1.3.tgz", "integrity": "sha1-p9BVi9icQveV3UIyj3QIMcpTvCU=", "dev": true }, "commander": { "version": "https://registry.npmjs.org/commander/-/commander-2.3.0.tgz", "integrity": "sha1-/UMOiJgy7DU7ms0d4hfBHLPu+HM=", "dev": true }, "concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", "dev": true }, "concat-stream": { "version": "1.6.0", "resolved": "https://registry.npmjs.org/concat-stream/-/concat-stream-1.6.0.tgz", "integrity": "sha1-CqxmL9Ur54lk1VMvaUeE5wEQrPc=", "dev": true, "requires": { "inherits": "http://npm.paypal.com/inherits/-/inherits-2.0.3.tgz", "readable-stream": "2.3.3", "typedarray": "0.0.6" } }, "core-util-is": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=", "dev": true }, "cross-spawn": { "version": "5.1.0", "resolved": "https://registry.npmjs.org/cross-spawn/-/cross-spawn-5.1.0.tgz", "integrity": "sha1-6L0O/uWPz/b4+UUQoKVUu/ojVEk=", "dev": true, "requires": { "lru-cache": "4.1.1", "shebang-command": "1.2.0", "which": "1.3.0" }, "dependencies": { "lru-cache": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/lru-cache/-/lru-cache-4.1.1.tgz", "integrity": "sha512-q4spe4KTfsAS1SUHLO0wz8Qiyf1+vMIAgpRYioFYDMNqKfHQbg+AVDH3i4fvpl71/P1L0dBl+fQi+P37UYf0ew==", "dev": true, "requires": { "pseudomap": "1.0.2", "yallist": "2.1.2" } } } }, "debug": { "version": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", "integrity": "sha1-+HBX6ZWxofauaklgZkE3vFbwOdo=", "dev": true, "requires": { "ms": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz" } }, "deep-is": { "version": "0.1.3", "resolved": "https://registry.npmjs.org/deep-is/-/deep-is-0.1.3.tgz", "integrity": "sha1-s2nW+128E+7PUk+RsHD+7cNXzzQ=", "dev": true }, "del": { "version": "2.2.2", "resolved": "https://registry.npmjs.org/del/-/del-2.2.2.tgz", "integrity": "sha1-wSyYHQZ4RshLyvhiz/kw2Qf/0ag=", "dev": true, "requires": { "globby": "5.0.0", "is-path-cwd": "1.0.0", "is-path-in-cwd": "1.0.0", "object-assign": "4.1.1", "pify": "2.3.0", "pinkie-promise": "2.0.1", "rimraf": "2.6.2" } }, "diff": { "version": "https://registry.npmjs.org/diff/-/diff-1.4.0.tgz", "integrity": "sha1-fyjS657nsVqX79ic5j3P2qPMur8=", "dev": true }, "doctrine": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/doctrine/-/doctrine-2.0.0.tgz", "integrity": "sha1-xz2NKQnSIpHhoAejlYBNqLZl/mM=", "dev": true, "requires": { "esutils": "2.0.2", "isarray": "1.0.0" } }, "escape-string-regexp": { "version": "http://npm.paypal.com/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz", "integrity": "sha1-Tbwv5nTnGUnK8/smlc5/LcHZqNE=", "dev": true }, "eslint": { "version": "4.10.0", "resolved": "https://registry.npmjs.org/eslint/-/eslint-4.10.0.tgz", "integrity": "sha512-MMVl8P/dYUFZEvolL8PYt7qc5LNdS2lwheq9BYa5Y07FblhcZqFyaUqlS8TW5QITGex21tV4Lk0a3fK8lsJIkA==", "dev": true, "requires": { "ajv": "5.3.0", "babel-code-frame": "6.26.0", "chalk": "2.3.0", "concat-stream": "1.6.0", "cross-spawn": "5.1.0", "debug": "3.1.0", "doctrine": "2.0.0", "eslint-scope": "3.7.1", "espree": "3.5.1", "esquery": "1.0.0", "estraverse": "4.2.0", "esutils": "2.0.2", "file-entry-cache": "2.0.0", "functional-red-black-tree": "1.0.1", "glob": "7.1.2", "globals": "9.18.0", "ignore": "3.3.7", "imurmurhash": "0.1.4", "inquirer": "3.3.0", "is-resolvable": "1.0.0", "js-yaml": "3.10.0", "json-stable-stringify": "1.0.1", "levn": "0.3.0", "lodash": "4.17.4", "minimatch": "3.0.4", "mkdirp": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", "natural-compare": "1.4.0", "optionator": "0.8.2", "path-is-inside": "1.0.2", "pluralize": "7.0.0", "progress": "2.0.0", "require-uncached": "1.0.3", "semver": "5.4.1", "strip-ansi": "4.0.0", "strip-json-comments": "2.0.1", "table": "4.0.2", "text-table": "0.2.0" }, "dependencies": { "debug": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", "dev": true, "requires": { "ms": "2.0.0" } }, "glob": { "version": "7.1.2", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "dev": true, "requires": { "fs.realpath": "1.0.0", "inflight": "1.0.6", "inherits": "http://npm.paypal.com/inherits/-/inherits-2.0.3.tgz", "minimatch": "3.0.4", "once": "1.4.0", "path-is-absolute": "1.0.1" } }, "minimatch": { "version": "3.0.4", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", "dev": true, "requires": { "brace-expansion": "1.1.8" } }, "ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", "dev": true } } }, "eslint-scope": { "version": "3.7.1", "resolved": "https://registry.npmjs.org/eslint-scope/-/eslint-scope-3.7.1.tgz", "integrity": "sha1-PWPD7f2gLgbgGkUq2IyqzHzctug=", "dev": true, "requires": { "esrecurse": "4.2.0", "estraverse": "4.2.0" } }, "espree": { "version": "3.5.1", "resolved": "https://registry.npmjs.org/espree/-/espree-3.5.1.tgz", "integrity": "sha1-DJiLirRttTEAoZVK5LqZXd0n2H4=", "dev": true, "requires": { "acorn": "5.2.1", "acorn-jsx": "3.0.1" } }, "esprima": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/esprima/-/esprima-4.0.0.tgz", "integrity": "sha512-oftTcaMu/EGrEIu904mWteKIv8vMuOgGYo7EhVJJN00R/EED9DCua/xxHRdYnKtcECzVg7xOWhflvJMnqcFZjw==", "dev": true }, "esquery": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/esquery/-/esquery-1.0.0.tgz", "integrity": "sha1-z7qLV9f7qT8XKYqKAGoEzaE9gPo=", "dev": true, "requires": { "estraverse": "4.2.0" } }, "esrecurse": { "version": "4.2.0", "resolved": "https://registry.npmjs.org/esrecurse/-/esrecurse-4.2.0.tgz", "integrity": "sha1-+pVo2Y04I/mkHZHpAtyrnqblsWM=", "dev": true, "requires": { "estraverse": "4.2.0", "object-assign": "4.1.1" } }, "estraverse": { "version": "4.2.0", "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-4.2.0.tgz", "integrity": "sha1-De4/7TH81GlhjOc0IJn8GvoL2xM=", "dev": true }, "esutils": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/esutils/-/esutils-2.0.2.tgz", "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=", "dev": true }, "external-editor": { "version": "2.0.5", "resolved": "https://registry.npmjs.org/external-editor/-/external-editor-2.0.5.tgz", "integrity": "sha512-Msjo64WT5W+NhOpQXh0nOHm+n0RfU1QUwDnKYvJ8dEJ8zlwLrqXNTv5mSUTJpepf41PDJGyhueTw2vNZW+Fr/w==", "dev": true, "requires": { "iconv-lite": "0.4.19", "jschardet": "1.6.0", "tmp": "0.0.33" } }, "fast-deep-equal": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-1.0.0.tgz", "integrity": "sha1-liVqO8l1WV6zbYLpkp0GDYk0Of8=", "dev": true }, "fast-json-stable-stringify": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.0.0.tgz", "integrity": "sha1-1RQsDK7msRifh9OnYREGT4bIu/I=", "dev": true }, "fast-levenshtein": { "version": "2.0.6", "resolved": "https://registry.npmjs.org/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz", "integrity": "sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=", "dev": true }, "figures": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/figures/-/figures-2.0.0.tgz", "integrity": "sha1-OrGi0qYsi/tDGgyUy3l6L84nyWI=", "dev": true, "requires": { "escape-string-regexp": "1.0.5" }, "dependencies": { "escape-string-regexp": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", "dev": true } } }, "file-entry-cache": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/file-entry-cache/-/file-entry-cache-2.0.0.tgz", "integrity": "sha1-w5KZDD5oR4PYOLjISkXYoEhFg2E=", "dev": true, "requires": { "flat-cache": "1.3.0", "object-assign": "4.1.1" } }, "flat-cache": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/flat-cache/-/flat-cache-1.3.0.tgz", "integrity": "sha1-0wMLMrOBVPTjt+nHCfSQ9++XxIE=", "dev": true, "requires": { "circular-json": "0.3.3", "del": "2.2.2", "graceful-fs": "4.1.11", "write": "0.2.1" } }, "fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", "dev": true }, "functional-red-black-tree": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/functional-red-black-tree/-/functional-red-black-tree-1.0.1.tgz", "integrity": "sha1-GwqzvVU7Kg1jmdKcDj6gslIHgyc=", "dev": true }, "glob": { "version": "http://npm.paypal.com/glob/-/glob-3.2.11.tgz", "integrity": "sha1-Spc/Y1uRkPcV0QmH1cAP0oFevj0=", "dev": true, "requires": { "inherits": "http://npm.paypal.com/inherits/-/inherits-2.0.3.tgz", "minimatch": "http://npm.paypal.com/minimatch/-/minimatch-0.3.0.tgz" } }, "globals": { "version": "9.18.0", "resolved": "https://registry.npmjs.org/globals/-/globals-9.18.0.tgz", "integrity": "sha512-S0nG3CLEQiY/ILxqtztTWH/3iRRdyBLw6KMDxnKMchrtbj2OFmehVh0WUCfW3DUrIgx/qFrJPICrq4Z4sTR9UQ==", "dev": true }, "globby": { "version": "5.0.0", "resolved": "https://registry.npmjs.org/globby/-/globby-5.0.0.tgz", "integrity": "sha1-69hGZ8oNuzMLmbz8aOrCvFQ3Dg0=", "dev": true, "requires": { "array-union": "1.0.2", "arrify": "1.0.1", "glob": "7.1.2", "object-assign": "4.1.1", "pify": "2.3.0", "pinkie-promise": "2.0.1" }, "dependencies": { "glob": { "version": "7.1.2", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "dev": true, "requires": { "fs.realpath": "1.0.0", "inflight": "1.0.6", "inherits": "http://npm.paypal.com/inherits/-/inherits-2.0.3.tgz", "minimatch": "3.0.4", "once": "1.4.0", "path-is-absolute": "1.0.1" } }, "minimatch": { "version": "3.0.4", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", "dev": true, "requires": { "brace-expansion": "1.1.8" } } } }, "graceful-fs": { "version": "4.1.11", "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.1.11.tgz", "integrity": "sha1-Dovf5NHduIVNZOBOp8AOKgJuVlg=", "dev": true }, "growl": { "version": "https://registry.npmjs.org/growl/-/growl-1.9.2.tgz", "integrity": "sha1-Dqd0NxXbjY3ixe3hd14bRayFwC8=", "dev": true }, "has-ansi": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/has-ansi/-/has-ansi-2.0.0.tgz", "integrity": "sha1-NPUEnOHs3ysGSa8+8k5F7TVBbZE=", "dev": true, "requires": { "ansi-regex": "2.1.1" } }, "has-flag": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=", "dev": true }, "iconv-lite": { "version": "0.4.19", "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.19.tgz", "integrity": "sha512-oTZqweIP51xaGPI4uPa56/Pri/480R+mo7SeU+YETByQNhDG55ycFyNLIgta9vXhILrxXDmF7ZGhqZIcuN0gJQ==", "dev": true }, "ignore": { "version": "3.3.7", "resolved": "https://registry.npmjs.org/ignore/-/ignore-3.3.7.tgz", "integrity": "sha512-YGG3ejvBNHRqu0559EOxxNFihD0AjpvHlC/pdGKd3X3ofe+CoJkYazwNJYTNebqpPKN+VVQbh4ZFn1DivMNuHA==", "dev": true }, "imurmurhash": { "version": "0.1.4", "resolved": "https://registry.npmjs.org/imurmurhash/-/imurmurhash-0.1.4.tgz", "integrity": "sha1-khi5srkoojixPcT7a21XbyMUU+o=", "dev": true }, "inflight": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", "dev": true, "requires": { "once": "1.4.0", "wrappy": "1.0.2" } }, "inherits": { "version": "http://npm.paypal.com/inherits/-/inherits-2.0.3.tgz", "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, "inquirer": { "version": "3.3.0", "resolved": "https://registry.npmjs.org/inquirer/-/inquirer-3.3.0.tgz", "integrity": "sha512-h+xtnyk4EwKvFWHrUYsWErEVR+igKtLdchu+o0Z1RL7VU/jVMFbYir2bp6bAj8efFNxWqHX0dIss6fJQ+/+qeQ==", "dev": true, "requires": { "ansi-escapes": "3.0.0", "chalk": "2.3.0", "cli-cursor": "2.1.0", "cli-width": "2.2.0", "external-editor": "2.0.5", "figures": "2.0.0", "lodash": "4.17.4", "mute-stream": "0.0.7", "run-async": "2.3.0", "rx-lite": "4.0.8", "rx-lite-aggregates": "4.0.8", "string-width": "2.1.1", "strip-ansi": "4.0.0", "through": "2.3.8" } }, "is-fullwidth-code-point": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/is-fullwidth-code-point/-/is-fullwidth-code-point-2.0.0.tgz", "integrity": "sha1-o7MKXE8ZkYMWeqq5O+764937ZU8=", "dev": true }, "is-path-cwd": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-path-cwd/-/is-path-cwd-1.0.0.tgz", "integrity": "sha1-0iXsIxMuie3Tj9p2dHLmLmXxEG0=", "dev": true }, "is-path-in-cwd": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-path-in-cwd/-/is-path-in-cwd-1.0.0.tgz", "integrity": "sha1-ZHdYK4IU1gI0YJRWcAO+ip6sBNw=", "dev": true, "requires": { "is-path-inside": "1.0.0" } }, "is-path-inside": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-path-inside/-/is-path-inside-1.0.0.tgz", "integrity": "sha1-/AbloWg/vaE95mev9xe7wQpI838=", "dev": true, "requires": { "path-is-inside": "1.0.2" } }, "is-promise": { "version": "2.1.0", "resolved": "https://registry.npmjs.org/is-promise/-/is-promise-2.1.0.tgz", "integrity": "sha1-eaKp7OfwlugPNtKy87wWwf9L8/o=", "dev": true }, "is-resolvable": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/is-resolvable/-/is-resolvable-1.0.0.tgz", "integrity": "sha1-jfV8YeouPFAUCNEA+wE8+NbgzGI=", "dev": true, "requires": { "tryit": "1.0.3" } }, "isarray": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=", "dev": true }, "isexe": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/isexe/-/isexe-2.0.0.tgz", "integrity": "sha1-6PvzdNxVb/iUehDcsFctYz8s+hA=", "dev": true }, "jade": { "version": "https://registry.npmjs.org/jade/-/jade-0.26.3.tgz", "integrity": "sha1-jxDXl32NefL2/4YqgbBRPMslaGw=", "dev": true, "requires": { "commander": "https://registry.npmjs.org/commander/-/commander-0.6.1.tgz", "mkdirp": "http://npm.paypal.com/mkdirp/-/mkdirp-0.3.0.tgz" }, "dependencies": { "commander": { "version": "https://registry.npmjs.org/commander/-/commander-0.6.1.tgz", "integrity": "sha1-+mihT2qUXVTbvlDYzbMyDp47GgY=", "dev": true }, "mkdirp": { "version": "http://npm.paypal.com/mkdirp/-/mkdirp-0.3.0.tgz", "integrity": "sha1-G79asbqCevI1dRQ0kEJkVfSB/h4=", "dev": true } } }, "js-tokens": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/js-tokens/-/js-tokens-3.0.2.tgz", "integrity": "sha1-mGbfOVECEw449/mWvOtlRDIJwls=", "dev": true }, "js-yaml": { "version": "3.10.0", "resolved": "https://registry.npmjs.org/js-yaml/-/js-yaml-3.10.0.tgz", "integrity": "sha512-O2v52ffjLa9VeM43J4XocZE//WT9N0IiwDa3KSHH7Tu8CtH+1qM8SIZvnsTh6v+4yFy5KUY3BHUVwjpfAWsjIA==", "dev": true, "requires": { "argparse": "1.0.9", "esprima": "4.0.0" } }, "jschardet": { "version": "1.6.0", "resolved": "https://registry.npmjs.org/jschardet/-/jschardet-1.6.0.tgz", "integrity": "sha512-xYuhvQ7I9PDJIGBWev9xm0+SMSed3ZDBAmvVjbFR1ZRLAF+vlXcQu6cRI9uAlj81rzikElRVteehwV7DuX2ZmQ==", "dev": true }, "json-schema-traverse": { "version": "0.3.1", "resolved": "https://registry.npmjs.org/json-schema-traverse/-/json-schema-traverse-0.3.1.tgz", "integrity": "sha1-NJptRMU6Ud6JtAgFxdXlm0F9M0A=", "dev": true }, "json-stable-stringify": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz", "integrity": "sha1-mnWdOcXy/1A/1TAGRu1EX4jE+a8=", "dev": true, "requires": { "jsonify": "0.0.0" } }, "jsonify": { "version": "0.0.0", "resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz", "integrity": "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=", "dev": true }, "levn": { "version": "0.3.0", "resolved": "https://registry.npmjs.org/levn/-/levn-0.3.0.tgz", "integrity": "sha1-OwmSTt+fCDwEkP3UwLxEIeBHZO4=", "dev": true, "requires": { "prelude-ls": "1.1.2", "type-check": "0.3.2" } }, "lodash": { "version": "4.17.4", "resolved": "https://registry.npmjs.org/lodash/-/lodash-4.17.4.tgz", "integrity": "sha1-eCA6TRwyiuHYbcpkYONptX9AVa4=", "dev": true }, "lru-cache": { "version": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", "integrity": "sha1-bUUk6LlV+V1PW1iFHOId1y+06VI=", "dev": true }, "mimic-fn": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/mimic-fn/-/mimic-fn-1.1.0.tgz", "integrity": "sha1-5md4PZLonb00KBi1IwudYqZyrRg=", "dev": true }, "minimalistic-assert": { "version": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.0.tgz", "integrity": "sha1-cCvi3aazf0g2vLP121ZkG2Sh09M=" }, "minimatch": { "version": "http://npm.paypal.com/minimatch/-/minimatch-0.3.0.tgz", "integrity": "sha1-J12O2qxPG7MyZHIInnlJyDlGmd0=", "dev": true, "requires": { "lru-cache": "https://registry.npmjs.org/lru-cache/-/lru-cache-2.7.3.tgz", "sigmund": "https://registry.npmjs.org/sigmund/-/sigmund-1.0.1.tgz" } }, "minimist": { "version": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=", "dev": true }, "mkdirp": { "version": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", "dev": true, "requires": { "minimist": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz" } }, "mocha": { "version": "https://registry.npmjs.org/mocha/-/mocha-2.5.3.tgz", "integrity": "sha1-FhvlvetJZ3HrmzV0UFC2IrWu/Fg=", "dev": true, "requires": { "commander": "https://registry.npmjs.org/commander/-/commander-2.3.0.tgz", "debug": "https://registry.npmjs.org/debug/-/debug-2.2.0.tgz", "diff": "https://registry.npmjs.org/diff/-/diff-1.4.0.tgz", "escape-string-regexp": "http://npm.paypal.com/escape-string-regexp/-/escape-string-regexp-1.0.2.tgz", "glob": "http://npm.paypal.com/glob/-/glob-3.2.11.tgz", "growl": "https://registry.npmjs.org/growl/-/growl-1.9.2.tgz", "jade": "https://registry.npmjs.org/jade/-/jade-0.26.3.tgz", "mkdirp": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", "supports-color": "https://registry.npmjs.org/supports-color/-/supports-color-1.2.0.tgz", "to-iso-string": "https://registry.npmjs.org/to-iso-string/-/to-iso-string-0.0.2.tgz" } }, "ms": { "version": "https://registry.npmjs.org/ms/-/ms-0.7.1.tgz", "integrity": "sha1-nNE8A62/8ltl7/3nzoZO6VIBcJg=", "dev": true }, "mute-stream": { "version": "0.0.7", "resolved": "https://registry.npmjs.org/mute-stream/-/mute-stream-0.0.7.tgz", "integrity": "sha1-MHXOk7whuPq0PhvE2n6BFe0ee6s=", "dev": true }, "natural-compare": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/natural-compare/-/natural-compare-1.4.0.tgz", "integrity": "sha1-Sr6/7tdUHywnrPspvbvRXI1bpPc=", "dev": true }, "object-assign": { "version": "4.1.1", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", "integrity": "sha1-IQmtx5ZYh8/AXLvUQsrIv7s2CGM=", "dev": true }, "once": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", "dev": true, "requires": { "wrappy": "1.0.2" } }, "onetime": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/onetime/-/onetime-2.0.1.tgz", "integrity": "sha1-BnQoIw/WdEOyeUsiu6UotoZ5YtQ=", "dev": true, "requires": { "mimic-fn": "1.1.0" } }, "optionator": { "version": "0.8.2", "resolved": "https://registry.npmjs.org/optionator/-/optionator-0.8.2.tgz", "integrity": "sha1-NkxeQJ0/TWMB1sC0wFu6UBgK62Q=", "dev": true, "requires": { "deep-is": "0.1.3", "fast-levenshtein": "2.0.6", "levn": "0.3.0", "prelude-ls": "1.1.2", "type-check": "0.3.2", "wordwrap": "1.0.0" } }, "os-tmpdir": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/os-tmpdir/-/os-tmpdir-1.0.2.tgz", "integrity": "sha1-u+Z0BseaqFxc/sdm/lc0VV36EnQ=", "dev": true }, "path-is-absolute": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", "dev": true }, "path-is-inside": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/path-is-inside/-/path-is-inside-1.0.2.tgz", "integrity": "sha1-NlQX3t5EQw0cEa9hAn+s8HS9/FM=", "dev": true }, "pify": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/pify/-/pify-2.3.0.tgz", "integrity": "sha1-7RQaasBDqEnqWISY59yosVMw6Qw=", "dev": true }, "pinkie": { "version": "2.0.4", "resolved": "https://registry.npmjs.org/pinkie/-/pinkie-2.0.4.tgz", "integrity": "sha1-clVrgM+g1IqXToDnckjoDtT3+HA=", "dev": true }, "pinkie-promise": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/pinkie-promise/-/pinkie-promise-2.0.1.tgz", "integrity": "sha1-ITXW36ejWMBprJsXh3YogihFD/o=", "dev": true, "requires": { "pinkie": "2.0.4" } }, "pluralize": { "version": "7.0.0", "resolved": "https://registry.npmjs.org/pluralize/-/pluralize-7.0.0.tgz", "integrity": "sha512-ARhBOdzS3e41FbkW/XWrTEtukqqLoK5+Z/4UeDaLuSW+39JPeFgs4gCGqsrJHVZX0fUrx//4OF0K1CUGwlIFow==", "dev": true }, "prelude-ls": { "version": "1.1.2", "resolved": "https://registry.npmjs.org/prelude-ls/-/prelude-ls-1.1.2.tgz", "integrity": "sha1-IZMqVJ9eUv/ZqCf1cOBL5iqX2lQ=", "dev": true }, "process-nextick-args": { "version": "1.0.7", "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-1.0.7.tgz", "integrity": "sha1-FQ4gt1ZZCtP5EJPyWk8q2L/zC6M=", "dev": true }, "progress": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/progress/-/progress-2.0.0.tgz", "integrity": "sha1-ihvjZr+Pwj2yvSPxDG/pILQ4nR8=", "dev": true }, "pseudomap": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/pseudomap/-/pseudomap-1.0.2.tgz", "integrity": "sha1-8FKijacOYYkX7wqKw0wa5aaChrM=", "dev": true }, "readable-stream": { "version": "2.3.3", "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.3.3.tgz", "integrity": "sha512-m+qzzcn7KUxEmd1gMbchF+Y2eIUbieUaxkWtptyHywrX0rE8QEYqPC07Vuy4Wm32/xE16NcdBctb8S0Xe/5IeQ==", "dev": true, "requires": { "core-util-is": "1.0.2", "inherits": "http://npm.paypal.com/inherits/-/inherits-2.0.3.tgz", "isarray": "1.0.0", "process-nextick-args": "1.0.7", "safe-buffer": "5.1.1", "string_decoder": "1.0.3", "util-deprecate": "1.0.2" } }, "require-uncached": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/require-uncached/-/require-uncached-1.0.3.tgz", "integrity": "sha1-Tg1W1slmL9MeQwEcS5WqSZVUIdM=", "dev": true, "requires": { "caller-path": "0.1.0", "resolve-from": "1.0.1" } }, "resolve-from": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-1.0.1.tgz", "integrity": "sha1-Jsv+k10a7uq7Kbw/5a6wHpPUQiY=", "dev": true }, "restore-cursor": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/restore-cursor/-/restore-cursor-2.0.0.tgz", "integrity": "sha1-n37ih/gv0ybU/RYpI9YhKe7g368=", "dev": true, "requires": { "onetime": "2.0.1", "signal-exit": "3.0.2" } }, "rimraf": { "version": "2.6.2", "resolved": "https://registry.npmjs.org/rimraf/-/rimraf-2.6.2.tgz", "integrity": "sha512-lreewLK/BlghmxtfH36YYVg1i8IAce4TI7oao75I1g245+6BctqTVQiBP3YUJ9C6DQOXJmkYR9X9fCLtCOJc5w==", "dev": true, "requires": { "glob": "7.1.2" }, "dependencies": { "glob": { "version": "7.1.2", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "dev": true, "requires": { "fs.realpath": "1.0.0", "inflight": "1.0.6", "inherits": "http://npm.paypal.com/inherits/-/inherits-2.0.3.tgz", "minimatch": "3.0.4", "once": "1.4.0", "path-is-absolute": "1.0.1" } }, "minimatch": { "version": "3.0.4", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", "dev": true, "requires": { "brace-expansion": "1.1.8" } } } }, "run-async": { "version": "2.3.0", "resolved": "https://registry.npmjs.org/run-async/-/run-async-2.3.0.tgz", "integrity": "sha1-A3GrSuC91yDUFm19/aZP96RFpsA=", "dev": true, "requires": { "is-promise": "2.1.0" } }, "rx-lite": { "version": "4.0.8", "resolved": "https://registry.npmjs.org/rx-lite/-/rx-lite-4.0.8.tgz", "integrity": "sha1-Cx4Rr4vESDbwSmQH6S2kJGe3lEQ=", "dev": true }, "rx-lite-aggregates": { "version": "4.0.8", "resolved": "https://registry.npmjs.org/rx-lite-aggregates/-/rx-lite-aggregates-4.0.8.tgz", "integrity": "sha1-dTuHqJoRyVRnxKwWJsTvxOBcZ74=", "dev": true, "requires": { "rx-lite": "4.0.8" } }, "safe-buffer": { "version": "5.1.1", "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.1.tgz", "integrity": "sha512-kKvNJn6Mm93gAczWVJg7wH+wGYWNrDHdWvpUmHyEsgCtIwwo3bqPtV4tR5tuPaUhTOo/kvhVwd8XwwOllGYkbg==", "dev": true }, "semver": { "version": "5.4.1", "resolved": "https://registry.npmjs.org/semver/-/semver-5.4.1.tgz", "integrity": "sha512-WfG/X9+oATh81XtllIo/I8gOiY9EXRdv1cQdyykeXK17YcUW3EXUAi2To4pcH6nZtJPr7ZOpM5OMyWJZm+8Rsg==", "dev": true }, "shebang-command": { "version": "1.2.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-1.2.0.tgz", "integrity": "sha1-RKrGW2lbAzmJaMOfNj/uXer98eo=", "dev": true, "requires": { "shebang-regex": "1.0.0" } }, "shebang-regex": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/shebang-regex/-/shebang-regex-1.0.0.tgz", "integrity": "sha1-2kL0l0DAtC2yypcoVxyxkMmO/qM=", "dev": true }, "sigmund": { "version": "https://registry.npmjs.org/sigmund/-/sigmund-1.0.1.tgz", "integrity": "sha1-P/IfGYytIXX587eBhT/ZTQ0ZtZA=", "dev": true }, "signal-exit": { "version": "3.0.2", "resolved": "https://registry.npmjs.org/signal-exit/-/signal-exit-3.0.2.tgz", "integrity": "sha1-tf3AjxKH6hF4Yo5BXiUTK3NkbG0=", "dev": true }, "slice-ansi": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/slice-ansi/-/slice-ansi-1.0.0.tgz", "integrity": "sha512-POqxBK6Lb3q6s047D/XsDVNPnF9Dl8JSaqe9h9lURl0OdNqy/ujDrOiIHtsqXMGbWWTIomRzAMaTyawAU//Reg==", "dev": true, "requires": { "is-fullwidth-code-point": "2.0.0" } }, "sprintf-js": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=", "dev": true }, "string-width": { "version": "2.1.1", "resolved": "https://registry.npmjs.org/string-width/-/string-width-2.1.1.tgz", "integrity": "sha512-nOqH59deCq9SRHlxq1Aw85Jnt4w6KvLKqWVik6oA9ZklXLNIOlqg4F2yrT1MVaTjAqvVwdfeZ7w7aCvJD7ugkw==", "dev": true, "requires": { "is-fullwidth-code-point": "2.0.0", "strip-ansi": "4.0.0" } }, "string_decoder": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.3.tgz", "integrity": "sha512-4AH6Z5fzNNBcH+6XDMfA/BTt87skxqJlO0lAh3Dker5zThcAxG6mKz+iGu308UKoPPQ8Dcqx/4JhujzltRa+hQ==", "dev": true, "requires": { "safe-buffer": "5.1.1" } }, "strip-ansi": { "version": "4.0.0", "resolved": "https://registry.npmjs.org/strip-ansi/-/strip-ansi-4.0.0.tgz", "integrity": "sha1-qEeQIusaw2iocTibY1JixQXuNo8=", "dev": true, "requires": { "ansi-regex": "3.0.0" }, "dependencies": { "ansi-regex": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/ansi-regex/-/ansi-regex-3.0.0.tgz", "integrity": "sha1-7QMXwyIGT3lGbAKWa922Bas32Zg=", "dev": true } } }, "strip-json-comments": { "version": "2.0.1", "resolved": "https://registry.npmjs.org/strip-json-comments/-/strip-json-comments-2.0.1.tgz", "integrity": "sha1-PFMZQukIwml8DsNEhYwobHygpgo=", "dev": true }, "supports-color": { "version": "https://registry.npmjs.org/supports-color/-/supports-color-1.2.0.tgz", "integrity": "sha1-/x7R5hFp0Gs88tWI4YixjYhH4X4=", "dev": true }, "table": { "version": "4.0.2", "resolved": "https://registry.npmjs.org/table/-/table-4.0.2.tgz", "integrity": "sha512-UUkEAPdSGxtRpiV9ozJ5cMTtYiqz7Ni1OGqLXRCynrvzdtR1p+cfOWe2RJLwvUG8hNanaSRjecIqwOjqeatDsA==", "dev": true, "requires": { "ajv": "5.3.0", "ajv-keywords": "2.1.1", "chalk": "2.3.0", "lodash": "4.17.4", "slice-ansi": "1.0.0", "string-width": "2.1.1" } }, "text-table": { "version": "0.2.0", "resolved": "https://registry.npmjs.org/text-table/-/text-table-0.2.0.tgz", "integrity": "sha1-f17oI66AUgfACvLfSoTsP8+lcLQ=", "dev": true }, "through": { "version": "2.3.8", "resolved": "https://registry.npmjs.org/through/-/through-2.3.8.tgz", "integrity": "sha1-DdTJ/6q8NXlgsbckEV1+Doai4fU=", "dev": true }, "tmp": { "version": "0.0.33", "resolved": "https://registry.npmjs.org/tmp/-/tmp-0.0.33.tgz", "integrity": "sha512-jRCJlojKnZ3addtTOjdIqoRuPEKBvNXcGYqzO6zWZX8KfKEpnGY5jfggJQ3EjKuu8D4bJRr0y+cYJFmYbImXGw==", "dev": true, "requires": { "os-tmpdir": "1.0.2" } }, "to-iso-string": { "version": "https://registry.npmjs.org/to-iso-string/-/to-iso-string-0.0.2.tgz", "integrity": "sha1-TcGeZk38y+Jb2NtQiwDG2hWCVdE=", "dev": true }, "tryit": { "version": "1.0.3", "resolved": "https://registry.npmjs.org/tryit/-/tryit-1.0.3.tgz", "integrity": "sha1-OTvnMKlEb9Hq1tpZoBQwjzbCics=", "dev": true }, "type-check": { "version": "0.3.2", "resolved": "https://registry.npmjs.org/type-check/-/type-check-0.3.2.tgz", "integrity": "sha1-WITKtRLPHTVeP7eE8wgEsrUg23I=", "dev": true, "requires": { "prelude-ls": "1.1.2" } }, "typedarray": { "version": "0.0.6", "resolved": "https://registry.npmjs.org/typedarray/-/typedarray-0.0.6.tgz", "integrity": "sha1-hnrHTjhkGHsdPUfZlqeOxciDB3c=", "dev": true }, "util-deprecate": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=", "dev": true }, "which": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/which/-/which-1.3.0.tgz", "integrity": "sha512-xcJpopdamTuY5duC/KnTTNBraPK54YwpenP4lzxU8H91GudWpFv38u0CKjclE1Wi2EH2EDz5LRcHcKbCIzqGyg==", "dev": true, "requires": { "isexe": "2.0.0" } }, "wordwrap": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/wordwrap/-/wordwrap-1.0.0.tgz", "integrity": "sha1-J1hIEIkUVqQXHI0CJkQa3pDLyus=", "dev": true }, "wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", "dev": true }, "write": { "version": "0.2.1", "resolved": "https://registry.npmjs.org/write/-/write-0.2.1.tgz", "integrity": "sha1-X8A4KOJkzqP+kUVUdvejxWbLB1c=", "dev": true, "requires": { "mkdirp": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz" } }, "yallist": { "version": "2.1.2", "resolved": "https://registry.npmjs.org/yallist/-/yallist-2.1.2.tgz", "integrity": "sha1-HBH5IY8HYImkfdUS+TxmmaaoHVI=", "dev": true } } } asn1.js-5.0.0/package.json000066400000000000000000000017751317633451600153020ustar00rootroot00000000000000{ "name": "asn1.js", "version": "5.0.0", "description": "ASN.1 encoder and decoder", "main": "lib/asn1.js", "scripts": { "lint-2560": "eslint --fix rfc/2560/*.js rfc/2560/test/*.js", "lint-5280": "eslint --fix rfc/5280/*.js rfc/5280/test/*.js", "lint": "eslint --fix lib/*.js lib/**/*.js lib/**/**/*.js && npm run lint-2560 && npm run lint-5280", "test": "mocha --reporter spec test/*-test.js && cd rfc/2560 && npm i && npm test && cd ../../rfc/5280 && npm i && npm test && cd ../../ && npm run lint" }, "repository": { "type": "git", "url": "git@github.com:indutny/asn1.js" }, "keywords": [ "asn.1", "der" ], "author": "Fedor Indutny", "license": "MIT", "bugs": { "url": "https://github.com/indutny/asn1.js/issues" }, "homepage": "https://github.com/indutny/asn1.js", "devDependencies": { "eslint": "^4.10.0", "mocha": "^2.3.4" }, "dependencies": { "bn.js": "^4.0.0", "inherits": "^2.0.1", "minimalistic-assert": "^1.0.0" } } asn1.js-5.0.0/rfc/000077500000000000000000000000001317633451600135545ustar00rootroot00000000000000asn1.js-5.0.0/rfc/2560/000077500000000000000000000000001317633451600141505ustar00rootroot00000000000000asn1.js-5.0.0/rfc/2560/.npmignore000066400000000000000000000000051317633451600161420ustar00rootroot00000000000000test asn1.js-5.0.0/rfc/2560/index.js000066400000000000000000000105251317633451600156200ustar00rootroot00000000000000'use strict'; const asn1 = require('asn1.js'); const rfc5280 = require('asn1.js-rfc5280'); const OCSPRequest = asn1.define('OCSPRequest', function() { this.seq().obj( this.key('tbsRequest').use(TBSRequest), this.key('optionalSignature').optional().explicit(0).use(Signature) ); }); exports.OCSPRequest = OCSPRequest; const TBSRequest = asn1.define('TBSRequest', function() { this.seq().obj( this.key('version').def('v1').explicit(0).use(rfc5280.Version), this.key('requestorName').optional().explicit(1).use(rfc5280.GeneralName), this.key('requestList').seqof(Request), this.key('requestExtensions').optional().explicit(2) .seqof(rfc5280.Extension) ); }); exports.TBSRequest = TBSRequest; const Signature = asn1.define('Signature', function() { this.seq().obj( this.key('signatureAlgorithm').use(rfc5280.AlgorithmIdentifier), this.key('signature').bitstr(), this.key('certs').optional().explicit(0).seqof(rfc5280.Certificate) ); }); exports.Signature = Signature; const Request = asn1.define('Request', function() { this.seq().obj( this.key('reqCert').use(CertID), this.key('singleRequestExtensions').optional().explicit(0).seqof( rfc5280.Extension) ); }); exports.Request = Request; const OCSPResponse = asn1.define('OCSPResponse', function() { this.seq().obj( this.key('responseStatus').use(ResponseStatus), this.key('responseBytes').optional().explicit(0).seq().obj( this.key('responseType').objid({ '1 3 6 1 5 5 7 48 1 1': 'id-pkix-ocsp-basic' }), this.key('response').octstr() ) ); }); exports.OCSPResponse = OCSPResponse; const ResponseStatus = asn1.define('ResponseStatus', function() { this.enum({ 0: 'successful', 1: 'malformed_request', 2: 'internal_error', 3: 'try_later', 5: 'sig_required', 6: 'unauthorized' }); }); exports.ResponseStatus = ResponseStatus; const BasicOCSPResponse = asn1.define('BasicOCSPResponse', function() { this.seq().obj( this.key('tbsResponseData').use(ResponseData), this.key('signatureAlgorithm').use(rfc5280.AlgorithmIdentifier), this.key('signature').bitstr(), this.key('certs').optional().explicit(0).seqof(rfc5280.Certificate) ); }); exports.BasicOCSPResponse = BasicOCSPResponse; const ResponseData = asn1.define('ResponseData', function() { this.seq().obj( this.key('version').def('v1').explicit(0).use(rfc5280.Version), this.key('responderID').use(ResponderID), this.key('producedAt').gentime(), this.key('responses').seqof(SingleResponse), this.key('responseExtensions').optional().explicit(0) .seqof(rfc5280.Extension) ); }); exports.ResponseData = ResponseData; const ResponderID = asn1.define('ResponderId', function() { this.choice({ byName: this.explicit(1).use(rfc5280.Name), byKey: this.explicit(2).use(KeyHash) }); }); exports.ResponderID = ResponderID; const KeyHash = asn1.define('KeyHash', function() { this.octstr(); }); exports.KeyHash = KeyHash; const SingleResponse = asn1.define('SingleResponse', function() { this.seq().obj( this.key('certId').use(CertID), this.key('certStatus').use(CertStatus), this.key('thisUpdate').gentime(), this.key('nextUpdate').optional().explicit(0).gentime(), this.key('singleExtensions').optional().explicit(1).seqof(rfc5280.Extension) ); }); exports.SingleResponse = SingleResponse; const CertStatus = asn1.define('CertStatus', function() { this.choice({ good: this.implicit(0).null_(), revoked: this.implicit(1).use(RevokedInfo), unknown: this.implicit(2).null_() }); }); exports.CertStatus = CertStatus; const RevokedInfo = asn1.define('RevokedInfo', function() { this.seq().obj( this.key('revocationTime').gentime(), this.key('revocationReason').optional().explicit(0).use(rfc5280.ReasonCode) ); }); exports.RevokedInfo = RevokedInfo; const CertID = asn1.define('CertID', function() { this.seq().obj( this.key('hashAlgorithm').use(rfc5280.AlgorithmIdentifier), this.key('issuerNameHash').octstr(), this.key('issuerKeyHash').octstr(), this.key('serialNumber').use(rfc5280.CertificateSerialNumber) ); }); exports.CertID = CertID; const Nonce = asn1.define('Nonce', function() { this.octstr(); }); exports.Nonce = Nonce; exports['id-pkix-ocsp'] = [ 1, 3, 6, 1, 5, 5, 7, 48, 1 ]; exports['id-pkix-ocsp-nonce'] = [ 1, 3, 6, 1, 5, 5, 7, 48, 1, 2 ]; asn1.js-5.0.0/rfc/2560/package-lock.json000066400000000000000000000165551317633451600174000ustar00rootroot00000000000000{ "name": "asn1.js-rfc2560", "version": "4.0.6", "lockfileVersion": 1, "requires": true, "dependencies": { "asn1.js": { "version": "4.9.1", "resolved": "https://registry.npmjs.org/asn1.js/-/asn1.js-4.9.1.tgz", "integrity": "sha1-SLokC0WpKA6UdImQull9IWYX/UA=", "requires": { "bn.js": "4.11.8", "inherits": "2.0.3", "minimalistic-assert": "1.0.0" } }, "asn1.js-rfc5280": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/asn1.js-rfc5280/-/asn1.js-rfc5280-2.0.0.tgz", "integrity": "sha1-t5Q2UMm95yL9ZDgCVhXo5m5vj2U=", "requires": { "asn1.js": "4.9.1" } }, "balanced-match": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=", "dev": true }, "bn.js": { "version": "4.11.8", "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.8.tgz", "integrity": "sha512-ItfYfPLkWHUjckQCk8xC+LwxgK8NYcXywGigJgSwOP8Y2iyWT4f2vsZnoOXTTbo+o5yXmIUJ4gn5538SO5S3gA==" }, "brace-expansion": { "version": "1.1.8", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.8.tgz", "integrity": "sha1-wHshHHyVLsH479Uad+8NHTmQopI=", "dev": true, "requires": { "balanced-match": "1.0.0", "concat-map": "0.0.1" } }, "browser-stdout": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=", "dev": true }, "commander": { "version": "2.11.0", "resolved": "https://registry.npmjs.org/commander/-/commander-2.11.0.tgz", "integrity": "sha512-b0553uYA5YAEGgyYIGYROzKQ7X5RAqedkfjiZxwi0kL1g3bOaBNNZfYkzt/CL0umgD5wc9Jec2FbB98CjkMRvQ==", "dev": true }, "concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", "dev": true }, "debug": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", "dev": true, "requires": { "ms": "2.0.0" } }, "diff": { "version": "3.3.1", "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==", "dev": true }, "escape-string-regexp": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", "dev": true }, "fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", "dev": true }, "glob": { "version": "7.1.2", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "dev": true, "requires": { "fs.realpath": "1.0.0", "inflight": "1.0.6", "inherits": "2.0.3", "minimatch": "3.0.4", "once": "1.4.0", "path-is-absolute": "1.0.1" } }, "growl": { "version": "1.10.3", "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==", "dev": true }, "has-flag": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=", "dev": true }, "he": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=", "dev": true }, "inflight": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", "dev": true, "requires": { "once": "1.4.0", "wrappy": "1.0.2" } }, "inherits": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, "minimalistic-assert": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.0.tgz", "integrity": "sha1-cCvi3aazf0g2vLP121ZkG2Sh09M=" }, "minimatch": { "version": "3.0.4", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", "dev": true, "requires": { "brace-expansion": "1.1.8" } }, "minimist": { "version": "0.0.8", "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=", "dev": true }, "mkdirp": { "version": "0.5.1", "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", "dev": true, "requires": { "minimist": "0.0.8" } }, "mocha": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.0.1.tgz", "integrity": "sha512-evDmhkoA+cBNiQQQdSKZa2b9+W2mpLoj50367lhy+Klnx9OV8XlCIhigUnn1gaTFLQCa0kdNhEGDr0hCXOQFDw==", "dev": true, "requires": { "browser-stdout": "1.3.0", "commander": "2.11.0", "debug": "3.1.0", "diff": "3.3.1", "escape-string-regexp": "1.0.5", "glob": "7.1.2", "growl": "1.10.3", "he": "1.1.1", "mkdirp": "0.5.1", "supports-color": "4.4.0" } }, "ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", "dev": true }, "once": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", "dev": true, "requires": { "wrappy": "1.0.2" } }, "path-is-absolute": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", "dev": true }, "supports-color": { "version": "4.4.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", "dev": true, "requires": { "has-flag": "2.0.0" } }, "wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", "dev": true } } } asn1.js-5.0.0/rfc/2560/package.json000066400000000000000000000012431317633451600164360ustar00rootroot00000000000000{ "name": "asn1.js-rfc2560", "version": "4.0.7", "description": "RFC2560 structures for asn1.js", "main": "index.js", "repository": { "type": "git", "url": "git@github.com:indutny/asn1.js" }, "keywords": [ "asn1", "rfc2560", "der" ], "scripts": { "test": "mocha --reporter=spec test/*-test.js" }, "author": "Fedor Indutny", "license": "MIT", "bugs": { "url": "https://github.com/indutny/asn1.js/issues" }, "homepage": "https://github.com/indutny/asn1.js", "dependencies": { "asn1.js-rfc5280": "^2.0.0" }, "peerDependencies": { "asn1.js": "^4.4.0" }, "devDependencies": { "mocha": "^4.0.1" } } asn1.js-5.0.0/rfc/2560/test/000077500000000000000000000000001317633451600151275ustar00rootroot00000000000000asn1.js-5.0.0/rfc/2560/test/basic-test.js000066400000000000000000000057221317633451600175310ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); const rfc2560 = require('..'); const Buffer = require('buffer').Buffer; describe('asn1.js RFC2560', function() { it('should decode OCSP response', function() { const data = new Buffer( '308201d40a0100a08201cd308201c906092b0601050507300101048201ba308201b630' + '819fa216041499e4405f6b145e3e05d9ddd36354fc62b8f700ac180f32303133313133' + '303037343531305a30743072304a300906052b0e03021a050004140226ee2f5fa28108' + '34dacc3380e680ace827f604041499e4405f6b145e3e05d9ddd36354fc62b8f700ac02' + '1100bb4f9a31232b1ba52a0b77af481800588000180f32303133313133303037343531' + '305aa011180f32303133313230343037343531305a300d06092a864886f70d01010505' + '00038201010027813333c9b46845dfe3d0cb6b19c03929cdfc9181c1ce823929bb911a' + 'd9de05721790fcccbab43f9fbdec1217ab8023156d07bbcc3555f25e9e472fbbb5e019' + '2835efcdc71b3dbc5e5c4c5939fc7a610fc6521d4ed7d2b685a812fa1a3a129ea87873' + '972be3be54618ba4a4d96090d7f9aaa5f70d4f07cf5cf3611d8a7b3adafe0b319459ed' + '40d456773d5f45f04c773711d86cc41d274f771a31c10d30cd6f846b587524bfab2445' + '4bbb4535cff46f6b341e50f26a242dd78e246c8dea0e2fabcac9582e000c138766f536' + 'd7f7bab81247c294454e62b710b07126de4e09685818f694df5783eb66f384ce5977f1' + '2721ff38c709f3ec580d22ff40818dd17f', 'hex'); const res = rfc2560.OCSPResponse.decode(data, 'der'); assert.equal(res.responseStatus, 'successful'); assert.equal(res.responseBytes.responseType, 'id-pkix-ocsp-basic'); const basic = rfc2560.BasicOCSPResponse.decode( res.responseBytes.response, 'der' ); assert.equal(basic.tbsResponseData.version, 'v1'); assert.equal(basic.tbsResponseData.producedAt, 1385797510000); }); it('should encode/decode OCSP response', function() { const encoded = rfc2560.OCSPResponse.encode({ responseStatus: 'malformed_request', responseBytes: { responseType: 'id-pkix-ocsp-basic', response: 'random-string' } }, 'der'); const decoded = rfc2560.OCSPResponse.decode(encoded, 'der'); assert.equal(decoded.responseStatus, 'malformed_request'); assert.equal(decoded.responseBytes.responseType, 'id-pkix-ocsp-basic'); assert.equal(decoded.responseBytes.response.toString(), 'random-string'); }); it('should encode OCSP request', function() { const tbsReq = { version: 'v1', requestList: [ { reqCert: { hashAlgorithm: { algorithm: [ 1, 3, 14, 3, 2, 26 ] }, issuerNameHash: new Buffer('01', 'hex'), issuerKeyHash: new Buffer('02', 'hex'), serialNumber: 0x2b } } ], requestExtensions: [ { extnID: [ 1, 3, 6, 1, 5, 5, 7, 48, 1, 2 ], critical: false, extnValue: new Buffer('03', 'hex') } ] }; const res = { tbsRequest: tbsReq }; rfc2560.OCSPRequest.encode(res, 'der'); }); }); asn1.js-5.0.0/rfc/5280/000077500000000000000000000000001317633451600141525ustar00rootroot00000000000000asn1.js-5.0.0/rfc/5280/.npmignore000066400000000000000000000000051317633451600161440ustar00rootroot00000000000000test asn1.js-5.0.0/rfc/5280/index.js000066400000000000000000000756551317633451600156410ustar00rootroot00000000000000'use strict'; const asn1 = require('asn1.js'); /** * RFC5280 X509 and Extension Definitions */ const rfc5280 = exports; // OIDs const x509OIDs = { '2 5 29 9': 'subjectDirectoryAttributes', '2 5 29 14': 'subjectKeyIdentifier', '2 5 29 15': 'keyUsage', '2 5 29 17': 'subjectAlternativeName', '2 5 29 18': 'issuerAlternativeName', '2 5 29 19': 'basicConstraints', '2 5 29 20': 'cRLNumber', '2 5 29 21': 'reasonCode', '2 5 29 24': 'invalidityDate', '2 5 29 27': 'deltaCRLIndicator', '2 5 29 28': 'issuingDistributionPoint', '2 5 29 29': 'certificateIssuer', '2 5 29 30': 'nameConstraints', '2 5 29 31': 'cRLDistributionPoints', '2 5 29 32': 'certificatePolicies', '2 5 29 33': 'policyMappings', '2 5 29 35': 'authorityKeyIdentifier', '2 5 29 36': 'policyConstraints', '2 5 29 37': 'extendedKeyUsage', '2 5 29 46': 'freshestCRL', '2 5 29 54': 'inhibitAnyPolicy', '1 3 6 1 5 5 7 1 1': 'authorityInformationAccess', '1 3 6 1 5 5 7 11': 'subjectInformationAccess' }; // CertificateList ::= SEQUENCE { // tbsCertList TBSCertList, // signatureAlgorithm AlgorithmIdentifier, // signature BIT STRING } const CertificateList = asn1.define('CertificateList', function() { this.seq().obj( this.key('tbsCertList').use(TBSCertList), this.key('signatureAlgorithm').use(AlgorithmIdentifier), this.key('signature').bitstr() ); }); rfc5280.CertificateList = CertificateList; // AlgorithmIdentifier ::= SEQUENCE { // algorithm OBJECT IDENTIFIER, // parameters ANY DEFINED BY algorithm OPTIONAL } const AlgorithmIdentifier = asn1.define('AlgorithmIdentifier', function() { this.seq().obj( this.key('algorithm').objid(), this.key('parameters').optional().any() ); }); rfc5280.AlgorithmIdentifier = AlgorithmIdentifier; // Certificate ::= SEQUENCE { // tbsCertificate TBSCertificate, // signatureAlgorithm AlgorithmIdentifier, // signature BIT STRING } const Certificate = asn1.define('Certificate', function() { this.seq().obj( this.key('tbsCertificate').use(TBSCertificate), this.key('signatureAlgorithm').use(AlgorithmIdentifier), this.key('signature').bitstr() ); }); rfc5280.Certificate = Certificate; // TBSCertificate ::= SEQUENCE { // version [0] Version DEFAULT v1, // serialNumber CertificateSerialNumber, // signature AlgorithmIdentifier, // issuer Name, // validity Validity, // subject Name, // subjectPublicKeyInfo SubjectPublicKeyInfo, // issuerUniqueID [1] IMPLICIT UniqueIdentifier OPTIONAL, // subjectUniqueID [2] IMPLICIT UniqueIdentifier OPTIONAL, // extensions [3] Extensions OPTIONAL const TBSCertificate = asn1.define('TBSCertificate', function() { this.seq().obj( this.key('version').def('v1').explicit(0).use(Version), this.key('serialNumber').int(), this.key('signature').use(AlgorithmIdentifier), this.key('issuer').use(Name), this.key('validity').use(Validity), this.key('subject').use(Name), this.key('subjectPublicKeyInfo').use(SubjectPublicKeyInfo), this.key('issuerUniqueID').optional().implicit(1).bitstr(), this.key('subjectUniqueID').optional().implicit(2).bitstr(), this.key('extensions').optional().explicit(3).seqof(Extension) ); }); rfc5280.TBSCertificate = TBSCertificate; // Version ::= INTEGER { v1(0), v2(1), v3(2) } const Version = asn1.define('Version', function() { this.int({ 0: 'v1', 1: 'v2', 2: 'v3' }); }); rfc5280.Version = Version; // Validity ::= SEQUENCE { // notBefore Time, // notAfter Time } const Validity = asn1.define('Validity', function() { this.seq().obj( this.key('notBefore').use(Time), this.key('notAfter').use(Time) ); }); rfc5280.Validity = Validity; // Time ::= CHOICE { // utcTime UTCTime, // generalTime GeneralizedTime } const Time = asn1.define('Time', function() { this.choice({ utcTime: this.utctime(), genTime: this.gentime() }); }); rfc5280.Time = Time; // SubjectPublicKeyInfo ::= SEQUENCE { // algorithm AlgorithmIdentifier, // subjectPublicKey BIT STRING } const SubjectPublicKeyInfo = asn1.define('SubjectPublicKeyInfo', function() { this.seq().obj( this.key('algorithm').use(AlgorithmIdentifier), this.key('subjectPublicKey').bitstr() ); }); rfc5280.SubjectPublicKeyInfo = SubjectPublicKeyInfo; // TBSCertList ::= SEQUENCE { // version Version OPTIONAL, // signature AlgorithmIdentifier, // issuer Name, // thisUpdate Time, // nextUpdate Time OPTIONAL, // revokedCertificates SEQUENCE OF SEQUENCE { // userCertificate CertificateSerialNumber, // revocationDate Time, // crlEntryExtensions Extensions OPTIONAL // } OPTIONAL, // crlExtensions [0] Extensions OPTIONAL } const TBSCertList = asn1.define('TBSCertList', function() { this.seq().obj( this.key('version').optional().int(), this.key('signature').use(AlgorithmIdentifier), this.key('issuer').use(Name), this.key('thisUpdate').use(Time), this.key('nextUpdate').use(Time), this.key('revokedCertificates').optional().seqof(RevokedCertificate), this.key('crlExtensions').explicit(0).optional().seqof(Extension) ); }); rfc5280.TBSCertList = TBSCertList; const RevokedCertificate = asn1.define('RevokedCertificate', function() { this.seq().obj( this.key('userCertificate').use(CertificateSerialNumber), this.key('revocationDate').use(Time), this.key('crlEntryExtensions').optional().seqof(Extension) ); }); // Extension ::= SEQUENCE { // extnID OBJECT IDENTIFIER, // critical BOOLEAN DEFAULT FALSE, // extnValue OCTET STRING } const Extension = asn1.define('Extension', function() { this.seq().obj( this.key('extnID').objid(x509OIDs), this.key('critical').bool().def(false), this.key('extnValue').octstr().contains(function(obj) { const out = x509Extensions[obj.extnID]; // Cope with unknown extensions return out ? out : asn1.define('OctString', function() { this.any(); }); }) ); }); rfc5280.Extension = Extension; // Name ::= CHOICE { -- only one possibility for now -- // rdnSequence RDNSequence } const Name = asn1.define('Name', function() { this.choice({ rdnSequence: this.use(RDNSequence) }); }); rfc5280.Name = Name; // GeneralName ::= CHOICE { // otherName [0] AnotherName, // rfc822Name [1] IA5String, // dNSName [2] IA5String, // x400Address [3] ORAddress, // directoryName [4] Name, // ediPartyName [5] EDIPartyName, // uniformResourceIdentifier [6] IA5String, // iPAddress [7] OCTET STRING, // registeredID [8] OBJECT IDENTIFIER } const GeneralName = asn1.define('GeneralName', function() { this.choice({ otherName: this.implicit(0).use(AnotherName), rfc822Name: this.implicit(1).ia5str(), dNSName: this.implicit(2).ia5str(), directoryName: this.explicit(4).use(Name), ediPartyName: this.implicit(5).use(EDIPartyName), uniformResourceIdentifier: this.implicit(6).ia5str(), iPAddress: this.implicit(7).octstr(), registeredID: this.implicit(8).objid() }); }); rfc5280.GeneralName = GeneralName; // GeneralNames ::= SEQUENCE SIZE (1..MAX) OF GeneralName const GeneralNames = asn1.define('GeneralNames', function() { this.seqof(GeneralName); }); rfc5280.GeneralNames = GeneralNames; // AnotherName ::= SEQUENCE { // type-id OBJECT IDENTIFIER, // value [0] EXPLICIT ANY DEFINED BY type-id } const AnotherName = asn1.define('AnotherName', function() { this.seq().obj( this.key('type-id').objid(), this.key('value').explicit(0).any() ); }); rfc5280.AnotherName = AnotherName; // EDIPartyName ::= SEQUENCE { // nameAssigner [0] DirectoryString OPTIONAL, // partyName [1] DirectoryString } const EDIPartyName = asn1.define('EDIPartyName', function() { this.seq().obj( this.key('nameAssigner').implicit(0).optional().use(DirectoryString), this.key('partyName').implicit(1).use(DirectoryString) ); }); rfc5280.EDIPartyName = EDIPartyName; // RDNSequence ::= SEQUENCE OF RelativeDistinguishedName const RDNSequence = asn1.define('RDNSequence', function() { this.seqof(RelativeDistinguishedName); }); rfc5280.RDNSequence = RDNSequence; // RelativeDistinguishedName ::= // SET SIZE (1..MAX) OF AttributeTypeAndValue const RelativeDistinguishedName = asn1.define('RelativeDistinguishedName', function() { this.setof(AttributeTypeAndValue); }); rfc5280.RelativeDistinguishedName = RelativeDistinguishedName; // AttributeTypeAndValue ::= SEQUENCE { // type AttributeType, // value AttributeValue } const AttributeTypeAndValue = asn1.define('AttributeTypeAndValue', function() { this.seq().obj( this.key('type').use(AttributeType), this.key('value').use(AttributeValue) ); }); rfc5280.AttributeTypeAndValue = AttributeTypeAndValue; // Attribute ::= SEQUENCE { // type AttributeType, // values SET OF AttributeValue } const Attribute = asn1.define('Attribute', function() { this.seq().obj( this.key('type').use(AttributeType), this.key('values').setof(AttributeValue) ); }); rfc5280.Attribute = Attribute; // AttributeType ::= OBJECT IDENTIFIER const AttributeType = asn1.define('AttributeType', function() { this.objid(); }); rfc5280.AttributeType = AttributeType; // AttributeValue ::= ANY -- DEFINED BY AttributeType const AttributeValue = asn1.define('AttributeValue', function() { this.any(); }); rfc5280.AttributeValue = AttributeValue; // DirectoryString ::= CHOICE { // teletexString TeletexString (SIZE (1..MAX)), // printableString PrintableString (SIZE (1..MAX)), // universalString UniversalString (SIZE (1..MAX)), // utf8String UTF8String (SIZE (1..MAX)), // bmpString BMPString (SIZE (1..MAX)) } const DirectoryString = asn1.define('DirectoryString', function() { this.choice({ teletexString: this.t61str(), printableString: this.printstr(), universalString: this.unistr(), utf8String: this.utf8str(), bmpString: this.bmpstr() }); }); rfc5280.DirectoryString = DirectoryString; // AuthorityKeyIdentifier ::= SEQUENCE { // keyIdentifier [0] KeyIdentifier OPTIONAL, // authorityCertIssuer [1] GeneralNames OPTIONAL, // authorityCertSerialNumber [2] CertificateSerialNumber OPTIONAL } const AuthorityKeyIdentifier = asn1.define('AuthorityKeyIdentifier', function() { this.seq().obj( this.key('keyIdentifier').implicit(0).optional().use(KeyIdentifier), this.key('authorityCertIssuer').implicit(1).optional().use(GeneralNames), this.key('authorityCertSerialNumber').implicit(2).optional() .use(CertificateSerialNumber) ); }); rfc5280.AuthorityKeyIdentifier = AuthorityKeyIdentifier; // KeyIdentifier ::= OCTET STRING const KeyIdentifier = asn1.define('KeyIdentifier', function() { this.octstr(); }); rfc5280.KeyIdentifier = KeyIdentifier; // CertificateSerialNumber ::= INTEGER const CertificateSerialNumber = asn1.define('CertificateSerialNumber', function() { this.int(); }); rfc5280.CertificateSerialNumber = CertificateSerialNumber; // ORAddress ::= SEQUENCE { // built-in-standard-attributes BuiltInStandardAttributes, // built-in-domain-defined-attributes BuiltInDomainDefinedAttributes // OPTIONAL, // extension-attributes ExtensionAttributes OPTIONAL } const ORAddress = asn1.define('ORAddress', function() { this.seq().obj( this.key('builtInStandardAttributes').use(BuiltInStandardAttributes), this.key('builtInDomainDefinedAttributes').optional() .use(BuiltInDomainDefinedAttributes), this.key('extensionAttributes').optional().use(ExtensionAttributes) ); }); rfc5280.ORAddress = ORAddress; // BuiltInStandardAttributes ::= SEQUENCE { // country-name CountryName OPTIONAL, // administration-domain-name AdministrationDomainName OPTIONAL, // network-address [0] IMPLICIT NetworkAddress OPTIONAL, // terminal-identifier [1] IMPLICIT TerminalIdentifier OPTIONAL, // private-domain-name [2] PrivateDomainName OPTIONAL, // organization-name [3] IMPLICIT OrganizationName OPTIONAL, // numeric-user-identifier [4] IMPLICIT NumericUserIdentifier OPTIONAL, // personal-name [5] IMPLICIT PersonalName OPTIONAL, // organizational-unit-names [6] IMPLICIT OrganizationalUnitNames OPTIONAL } const BuiltInStandardAttributes = asn1.define('BuiltInStandardAttributes', function() { this.seq().obj( this.key('countryName').optional().use(CountryName), this.key('administrationDomainName').optional() .use(AdministrationDomainName), this.key('networkAddress').implicit(0).optional().use(NetworkAddress), this.key('terminalIdentifier').implicit(1).optional() .use(TerminalIdentifier), this.key('privateDomainName').explicit(2).optional().use(PrivateDomainName), this.key('organizationName').implicit(3).optional().use(OrganizationName), this.key('numericUserIdentifier').implicit(4).optional() .use(NumericUserIdentifier), this.key('personalName').implicit(5).optional().use(PersonalName), this.key('organizationalUnitNames').implicit(6).optional() .use(OrganizationalUnitNames) ); }); rfc5280.BuiltInStandardAttributes = BuiltInStandardAttributes; // CountryName ::= CHOICE { // x121-dcc-code NumericString, // iso-3166-alpha2-code PrintableString } const CountryName = asn1.define('CountryName', function() { this.choice({ x121DccCode: this.numstr(), iso3166Alpha2Code: this.printstr() }); }); rfc5280.CountryName = CountryName; // AdministrationDomainName ::= CHOICE { // numeric NumericString, // printable PrintableString } const AdministrationDomainName = asn1.define('AdministrationDomainName', function() { this.choice({ numeric: this.numstr(), printable: this.printstr() }); }); rfc5280.AdministrationDomainName = AdministrationDomainName; // NetworkAddress ::= X121Address const NetworkAddress = asn1.define('NetworkAddress', function() { this.use(X121Address); }); rfc5280.NetworkAddress = NetworkAddress; // X121Address ::= NumericString const X121Address = asn1.define('X121Address', function() { this.numstr(); }); rfc5280.X121Address = X121Address; // TerminalIdentifier ::= PrintableString const TerminalIdentifier = asn1.define('TerminalIdentifier', function() { this.printstr(); }); rfc5280.TerminalIdentifier = TerminalIdentifier; // PrivateDomainName ::= CHOICE { // numeric NumericString, // printable PrintableString } const PrivateDomainName = asn1.define('PrivateDomainName', function() { this.choice({ numeric: this.numstr(), printable: this.printstr() }); }); rfc5280.PrivateDomainName = PrivateDomainName; // OrganizationName ::= PrintableString const OrganizationName = asn1.define('OrganizationName', function() { this.printstr(); }); rfc5280.OrganizationName = OrganizationName; // NumericUserIdentifier ::= NumericString const NumericUserIdentifier = asn1.define('NumericUserIdentifier', function() { this.numstr(); }); rfc5280.NumericUserIdentifier = NumericUserIdentifier; // PersonalName ::= SET { // surname [0] IMPLICIT PrintableString, // given-name [1] IMPLICIT PrintableString OPTIONAL, // initials [2] IMPLICIT PrintableString OPTIONAL, // generation-qualifier [3] IMPLICIT PrintableString OPTIONAL } const PersonalName = asn1.define('PersonalName', function() { this.set().obj( this.key('surname').implicit(0).printstr(), this.key('givenName').implicit(1).printstr(), this.key('initials').implicit(2).printstr(), this.key('generationQualifier').implicit(3).printstr() ); }); rfc5280.PersonalName = PersonalName; // OrganizationalUnitNames ::= SEQUENCE SIZE (1..ub-organizational-units) // OF OrganizationalUnitName const OrganizationalUnitNames = asn1.define('OrganizationalUnitNames', function() { this.seqof(OrganizationalUnitName); }); rfc5280.OrganizationalUnitNames = OrganizationalUnitNames; // OrganizationalUnitName ::= PrintableString (SIZE // (1..ub-organizational-unit-name-length)) const OrganizationalUnitName = asn1.define('OrganizationalUnitName', function() { this.printstr(); }); rfc5280.OrganizationalUnitName = OrganizationalUnitName; // uiltInDomainDefinedAttributes ::= SEQUENCE SIZE // (1..ub-domain-defined-attributes) // OF BuiltInDomainDefinedAttribute const BuiltInDomainDefinedAttributes = asn1.define( 'BuiltInDomainDefinedAttributes', function() { this.seqof(BuiltInDomainDefinedAttribute); }); rfc5280.BuiltInDomainDefinedAttributes = BuiltInDomainDefinedAttributes; // BuiltInDomainDefinedAttribute ::= SEQUENCE { // type PrintableString (SIZE (1..ub-domain-defined-attribute-type-length)), // value PrintableString (SIZE (1..ub-domain-defined-attribute-value-length)) //} const BuiltInDomainDefinedAttribute = asn1.define('BuiltInDomainDefinedAttribute', function() { this.seq().obj( this.key('type').printstr(), this.key('value').printstr() ); }); rfc5280.BuiltInDomainDefinedAttribute = BuiltInDomainDefinedAttribute; // ExtensionAttributes ::= SET SIZE (1..ub-extension-attributes) OF // ExtensionAttribute const ExtensionAttributes = asn1.define('ExtensionAttributes', function() { this.seqof(ExtensionAttribute); }); rfc5280.ExtensionAttributes = ExtensionAttributes; // ExtensionAttribute ::= SEQUENCE { // extension-attribute-type [0] IMPLICIT INTEGER, // extension-attribute-value [1] ANY DEFINED BY extension-attribute-type } const ExtensionAttribute = asn1.define('ExtensionAttribute', function() { this.seq().obj( this.key('extensionAttributeType').implicit(0).int(), this.key('extensionAttributeValue').any().explicit(1).int() ); }); rfc5280.ExtensionAttribute = ExtensionAttribute; // SubjectKeyIdentifier ::= KeyIdentifier const SubjectKeyIdentifier = asn1.define('SubjectKeyIdentifier', function() { this.use(KeyIdentifier); }); rfc5280.SubjectKeyIdentifier = SubjectKeyIdentifier; // KeyUsage ::= BIT STRING { // digitalSignature (0), // nonRepudiation (1), -- recent editions of X.509 have // -- renamed this bit to contentCommitment // keyEncipherment (2), // dataEncipherment (3), // keyAgreement (4), // keyCertSign (5), // cRLSign (6), // encipherOnly (7), // decipherOnly (8) } const KeyUsage = asn1.define('KeyUsage', function() { this.bitstr(); }); rfc5280.KeyUsage = KeyUsage; // CertificatePolicies ::= SEQUENCE SIZE (1..MAX) OF PolicyInformation const CertificatePolicies = asn1.define('CertificatePolicies', function() { this.seqof(PolicyInformation); }); rfc5280.CertificatePolicies = CertificatePolicies; // PolicyInformation ::= SEQUENCE { // policyIdentifier CertPolicyId, // policyQualifiers SEQUENCE SIZE (1..MAX) OF PolicyQualifierInfo // OPTIONAL } const PolicyInformation = asn1.define('PolicyInformation', function() { this.seq().obj( this.key('policyIdentifier').use(CertPolicyId), this.key('policyQualifiers').optional().use(PolicyQualifiers) ); }); rfc5280.PolicyInformation = PolicyInformation; // CertPolicyId ::= OBJECT IDENTIFIER const CertPolicyId = asn1.define('CertPolicyId', function() { this.objid(); }); rfc5280.CertPolicyId = CertPolicyId; const PolicyQualifiers = asn1.define('PolicyQualifiers', function() { this.seqof(PolicyQualifierInfo); }); rfc5280.PolicyQualifiers = PolicyQualifiers; // PolicyQualifierInfo ::= SEQUENCE { // policyQualifierId PolicyQualifierId, // qualifier ANY DEFINED BY policyQualifierId } const PolicyQualifierInfo = asn1.define('PolicyQualifierInfo', function() { this.seq().obj( this.key('policyQualifierId').use(PolicyQualifierId), this.key('qualifier').any() ); }); rfc5280.PolicyQualifierInfo = PolicyQualifierInfo; // PolicyQualifierId ::= OBJECT IDENTIFIER const PolicyQualifierId = asn1.define('PolicyQualifierId', function() { this.objid(); }); rfc5280.PolicyQualifierId = PolicyQualifierId; // PolicyMappings ::= SEQUENCE SIZE (1..MAX) OF SEQUENCE { // issuerDomainPolicy CertPolicyId, // subjectDomainPolicy CertPolicyId } const PolicyMappings = asn1.define('PolicyMappings', function() { this.seqof(PolicyMapping); }); rfc5280.PolicyMappings = PolicyMappings; const PolicyMapping = asn1.define('PolicyMapping', function() { this.seq().obj( this.key('issuerDomainPolicy').use(CertPolicyId), this.key('subjectDomainPolicy').use(CertPolicyId) ); }); rfc5280.PolicyMapping = PolicyMapping; // SubjectAltName ::= GeneralNames const SubjectAlternativeName = asn1.define('SubjectAlternativeName', function() { this.use(GeneralNames); }); rfc5280.SubjectAlternativeName = SubjectAlternativeName; // IssuerAltName ::= GeneralNames const IssuerAlternativeName = asn1.define('IssuerAlternativeName', function() { this.use(GeneralNames); }); rfc5280.IssuerAlternativeName = IssuerAlternativeName; // SubjectDirectoryAttributes ::= SEQUENCE SIZE (1..MAX) OF Attribute const SubjectDirectoryAttributes = asn1.define('SubjectDirectoryAttributes', function() { this.seqof(Attribute); }); rfc5280.SubjectDirectoryAttributes = SubjectDirectoryAttributes; // BasicConstraints ::= SEQUENCE { // cA BOOLEAN DEFAULT FALSE, // pathLenConstraint INTEGER (0..MAX) OPTIONAL } const BasicConstraints = asn1.define('BasicConstraints', function() { this.seq().obj( this.key('cA').bool().def(false), this.key('pathLenConstraint').optional().int() ); }); rfc5280.BasicConstraints = BasicConstraints; // NameConstraints ::= SEQUENCE { // permittedSubtrees [0] GeneralSubtrees OPTIONAL, // excludedSubtrees [1] GeneralSubtrees OPTIONAL } const NameConstraints = asn1.define('NameConstraints', function() { this.seq().obj( this.key('permittedSubtrees').implicit(0).optional().use(GeneralSubtrees), this.key('excludedSubtrees').implicit(1).optional().use(GeneralSubtrees) ); }); rfc5280.NameConstraints = NameConstraints; // GeneralSubtrees ::= SEQUENCE SIZE (1..MAX) OF GeneralSubtree const GeneralSubtrees = asn1.define('GeneralSubtrees', function() { this.seqof(GeneralSubtree); }); rfc5280.GeneralSubtrees = GeneralSubtrees; // GeneralSubtree ::= SEQUENCE { // base GeneralName, // minimum [0] BaseDistance DEFAULT 0, // maximum [1] BaseDistance OPTIONAL } const GeneralSubtree = asn1.define('GeneralSubtree', function() { this.seq().obj( this.key('base').use(GeneralName), this.key('minimum').implicit(0).def(0).use(BaseDistance), this.key('maximum').implicit(0).optional().use(BaseDistance) ); }); rfc5280.GeneralSubtree = GeneralSubtree; // BaseDistance ::= INTEGER const BaseDistance = asn1.define('BaseDistance', function() { this.int(); }); rfc5280.BaseDistance = BaseDistance; // PolicyConstraints ::= SEQUENCE { // requireExplicitPolicy [0] SkipCerts OPTIONAL, // inhibitPolicyMapping [1] SkipCerts OPTIONAL } const PolicyConstraints = asn1.define('PolicyConstraints', function() { this.seq().obj( this.key('requireExplicitPolicy').implicit(0).optional().use(SkipCerts), this.key('inhibitPolicyMapping').implicit(1).optional().use(SkipCerts) ); }); rfc5280.PolicyConstraints = PolicyConstraints; // SkipCerts ::= INTEGER const SkipCerts = asn1.define('SkipCerts', function() { this.int(); }); rfc5280.SkipCerts = SkipCerts; // ExtKeyUsageSyntax ::= SEQUENCE SIZE (1..MAX) OF KeyPurposeId const ExtendedKeyUsage = asn1.define('ExtendedKeyUsage', function() { this.seqof(KeyPurposeId); }); rfc5280.ExtendedKeyUsage = ExtendedKeyUsage; // KeyPurposeId ::= OBJECT IDENTIFIER const KeyPurposeId = asn1.define('KeyPurposeId', function() { this.objid(); }); rfc5280.KeyPurposeId = KeyPurposeId; // RLDistributionPoints ::= SEQUENCE SIZE (1..MAX) OF DistributionPoint const CRLDistributionPoints = asn1.define('CRLDistributionPoints', function() { this.seqof(DistributionPoint); }); rfc5280.CRLDistributionPoints = CRLDistributionPoints; // DistributionPoint ::= SEQUENCE { // distributionPoint [0] DistributionPointName OPTIONAL, // reasons [1] ReasonFlags OPTIONAL, // cRLIssuer [2] GeneralNames OPTIONAL } const DistributionPoint = asn1.define('DistributionPoint', function() { this.seq().obj( this.key('distributionPoint').optional().explicit(0) .use(DistributionPointName), this.key('reasons').optional().implicit(1).use(ReasonFlags), this.key('cRLIssuer').optional().implicit(2).use(GeneralNames) ); }); rfc5280.DistributionPoint = DistributionPoint; // DistributionPointName ::= CHOICE { // fullName [0] GeneralNames, // nameRelativeToCRLIssuer [1] RelativeDistinguishedName } const DistributionPointName = asn1.define('DistributionPointName', function() { this.choice({ fullName: this.implicit(0).use(GeneralNames), nameRelativeToCRLIssuer: this.implicit(1).use(RelativeDistinguishedName) }); }); rfc5280.DistributionPointName = DistributionPointName; // ReasonFlags ::= BIT STRING { // unused (0), // keyCompromise (1), // cACompromise (2), // affiliationChanged (3), // superseded (4), // cessationOfOperation (5), // certificateHold (6), // privilegeWithdrawn (7), // aACompromise (8) } const ReasonFlags = asn1.define('ReasonFlags', function() { this.bitstr(); }); rfc5280.ReasonFlags = ReasonFlags; // InhibitAnyPolicy ::= SkipCerts const InhibitAnyPolicy = asn1.define('InhibitAnyPolicy', function() { this.use(SkipCerts); }); rfc5280.InhibitAnyPolicy = InhibitAnyPolicy; // FreshestCRL ::= CRLDistributionPoints const FreshestCRL = asn1.define('FreshestCRL', function() { this.use(CRLDistributionPoints); }); rfc5280.FreshestCRL = FreshestCRL; // AuthorityInfoAccessSyntax ::= // SEQUENCE SIZE (1..MAX) OF AccessDescription const AuthorityInfoAccessSyntax = asn1.define('AuthorityInfoAccessSyntax', function() { this.seqof(AccessDescription); }); rfc5280.AuthorityInfoAccessSyntax = AuthorityInfoAccessSyntax; // AccessDescription ::= SEQUENCE { // accessMethod OBJECT IDENTIFIER, // accessLocation GeneralName } const AccessDescription = asn1.define('AccessDescription', function() { this.seq().obj( this.key('accessMethod').objid(), this.key('accessLocation').use(GeneralName) ); }); rfc5280.AccessDescription = AccessDescription; // SubjectInfoAccessSyntax ::= // SEQUENCE SIZE (1..MAX) OF AccessDescription const SubjectInformationAccess = asn1.define('SubjectInformationAccess', function() { this.seqof(AccessDescription); }); rfc5280.SubjectInformationAccess = SubjectInformationAccess; /** * CRL Extensions */ // CRLNumber ::= INTEGER const CRLNumber = asn1.define('CRLNumber', function() { this.int(); }); rfc5280.CRLNumber = CRLNumber; const DeltaCRLIndicator = asn1.define('DeltaCRLIndicator', function() { this.use(CRLNumber); }); rfc5280.DeltaCRLIndicator = DeltaCRLIndicator; // IssuingDistributionPoint ::= SEQUENCE { // distributionPoint [0] DistributionPointName OPTIONAL, // onlyContainsUserCerts [1] BOOLEAN DEFAULT FALSE, // onlyContainsCACerts [2] BOOLEAN DEFAULT FALSE, // onlySomeReasons [3] ReasonFlags OPTIONAL, // indirectCRL [4] BOOLEAN DEFAULT FALSE, // onlyContainsAttributeCerts [5] BOOLEAN DEFAULT FALSE } const IssuingDistributionPoint = asn1.define('IssuingDistributionPoint', function() { this.seq().obj( this.key('distributionPoint').explicit(0).optional() .use(DistributionPointName), this.key('onlyContainsUserCerts').implicit(1).def(false).bool(), this.key('onlyContainsCACerts').implicit(2).def(false).bool(), this.key('onlySomeReasons').implicit(3).optional().use(ReasonFlags), this.key('indirectCRL').implicit(4).def(false).bool(), this.key('onlyContainsAttributeCerts').implicit(5).def(false).bool() ); }); rfc5280.IssuingDistributionPoint = IssuingDistributionPoint; // CRLReason ::= ENUMERATED { // unspecified (0), // keyCompromise (1), // cACompromise (2), // affiliationChanged (3), // superseded (4), // cessationOfOperation (5), // certificateHold (6), // -- value 7 is not used // removeFromCRL (8), // privilegeWithdrawn (9), // aACompromise (10) } const ReasonCode = asn1.define('ReasonCode', function() { this.enum({ 0: 'unspecified', 1: 'keyCompromise', 2: 'cACompromise', 3: 'affiliationChanged', 4: 'superseded', 5: 'cessationOfOperation', 6: 'certificateHold', 8: 'removeFromCRL', 9: 'privilegeWithdrawn', 10: 'aACompromise' }); }); rfc5280.ReasonCode = ReasonCode; // InvalidityDate ::= GeneralizedTime const InvalidityDate = asn1.define('InvalidityDate', function() { this.gentime(); }); rfc5280.InvalidityDate = InvalidityDate; // CertificateIssuer ::= GeneralNames const CertificateIssuer = asn1.define('CertificateIssuer', function() { this.use(GeneralNames); }); rfc5280.CertificateIssuer = CertificateIssuer; // OID label to extension model mapping const x509Extensions = { subjectDirectoryAttributes: SubjectDirectoryAttributes, subjectKeyIdentifier: SubjectKeyIdentifier, keyUsage: KeyUsage, subjectAlternativeName: SubjectAlternativeName, issuerAlternativeName: IssuerAlternativeName, basicConstraints: BasicConstraints, cRLNumber: CRLNumber, reasonCode: ReasonCode, invalidityDate: InvalidityDate, deltaCRLIndicator: DeltaCRLIndicator, issuingDistributionPoint: IssuingDistributionPoint, certificateIssuer: CertificateIssuer, nameConstraints: NameConstraints, cRLDistributionPoints: CRLDistributionPoints, certificatePolicies: CertificatePolicies, policyMappings: PolicyMappings, authorityKeyIdentifier: AuthorityKeyIdentifier, policyConstraints: PolicyConstraints, extendedKeyUsage: ExtendedKeyUsage, freshestCRL: FreshestCRL, inhibitAnyPolicy: InhibitAnyPolicy, authorityInformationAccess: AuthorityInfoAccessSyntax, subjectInformationAccess: SubjectInformationAccess }; asn1.js-5.0.0/rfc/5280/package-lock.json000066400000000000000000000161501317633451600173710ustar00rootroot00000000000000{ "name": "asn1.js-rfc5280", "version": "2.0.1", "lockfileVersion": 1, "requires": true, "dependencies": { "asn1.js": { "version": "4.9.1", "resolved": "https://registry.npmjs.org/asn1.js/-/asn1.js-4.9.1.tgz", "integrity": "sha1-SLokC0WpKA6UdImQull9IWYX/UA=", "requires": { "bn.js": "4.11.8", "inherits": "2.0.3", "minimalistic-assert": "1.0.0" } }, "balanced-match": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=", "dev": true }, "bn.js": { "version": "4.11.8", "resolved": "https://registry.npmjs.org/bn.js/-/bn.js-4.11.8.tgz", "integrity": "sha512-ItfYfPLkWHUjckQCk8xC+LwxgK8NYcXywGigJgSwOP8Y2iyWT4f2vsZnoOXTTbo+o5yXmIUJ4gn5538SO5S3gA==" }, "brace-expansion": { "version": "1.1.8", "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.8.tgz", "integrity": "sha1-wHshHHyVLsH479Uad+8NHTmQopI=", "dev": true, "requires": { "balanced-match": "1.0.0", "concat-map": "0.0.1" } }, "browser-stdout": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/browser-stdout/-/browser-stdout-1.3.0.tgz", "integrity": "sha1-81HTKWnTL6XXpVZxVCY9korjvR8=", "dev": true }, "commander": { "version": "2.11.0", "resolved": "https://registry.npmjs.org/commander/-/commander-2.11.0.tgz", "integrity": "sha512-b0553uYA5YAEGgyYIGYROzKQ7X5RAqedkfjiZxwi0kL1g3bOaBNNZfYkzt/CL0umgD5wc9Jec2FbB98CjkMRvQ==", "dev": true }, "concat-map": { "version": "0.0.1", "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=", "dev": true }, "debug": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/debug/-/debug-3.1.0.tgz", "integrity": "sha512-OX8XqP7/1a9cqkxYw2yXss15f26NKWBpDXQd0/uK/KPqdQhxbPa994hnzjcE2VqQpDslf55723cKPUOGSmMY3g==", "dev": true, "requires": { "ms": "2.0.0" } }, "diff": { "version": "3.3.1", "resolved": "https://registry.npmjs.org/diff/-/diff-3.3.1.tgz", "integrity": "sha512-MKPHZDMB0o6yHyDryUOScqZibp914ksXwAMYMTHj6KO8UeKsRYNJD3oNCKjTqZon+V488P7N/HzXF8t7ZR95ww==", "dev": true }, "escape-string-regexp": { "version": "1.0.5", "resolved": "https://registry.npmjs.org/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz", "integrity": "sha1-G2HAViGQqN/2rjuyzwIAyhMLhtQ=", "dev": true }, "fs.realpath": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/fs.realpath/-/fs.realpath-1.0.0.tgz", "integrity": "sha1-FQStJSMVjKpA20onh8sBQRmU6k8=", "dev": true }, "glob": { "version": "7.1.2", "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.2.tgz", "integrity": "sha512-MJTUg1kjuLeQCJ+ccE4Vpa6kKVXkPYJ2mOCQyUuKLcLQsdrMCpBPUi8qVE6+YuaJkozeA9NusTAw3hLr8Xe5EQ==", "dev": true, "requires": { "fs.realpath": "1.0.0", "inflight": "1.0.6", "inherits": "2.0.3", "minimatch": "3.0.4", "once": "1.4.0", "path-is-absolute": "1.0.1" } }, "growl": { "version": "1.10.3", "resolved": "https://registry.npmjs.org/growl/-/growl-1.10.3.tgz", "integrity": "sha512-hKlsbA5Vu3xsh1Cg3J7jSmX/WaW6A5oBeqzM88oNbCRQFz+zUaXm6yxS4RVytp1scBoJzSYl4YAEOQIt6O8V1Q==", "dev": true }, "has-flag": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/has-flag/-/has-flag-2.0.0.tgz", "integrity": "sha1-6CB68cx7MNRGzHC3NLXovhj4jVE=", "dev": true }, "he": { "version": "1.1.1", "resolved": "https://registry.npmjs.org/he/-/he-1.1.1.tgz", "integrity": "sha1-k0EP0hsAlzUVH4howvJx80J+I/0=", "dev": true }, "inflight": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=", "dev": true, "requires": { "once": "1.4.0", "wrappy": "1.0.2" } }, "inherits": { "version": "2.0.3", "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, "minimalistic-assert": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/minimalistic-assert/-/minimalistic-assert-1.0.0.tgz", "integrity": "sha1-cCvi3aazf0g2vLP121ZkG2Sh09M=" }, "minimatch": { "version": "3.0.4", "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-3.0.4.tgz", "integrity": "sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==", "dev": true, "requires": { "brace-expansion": "1.1.8" } }, "minimist": { "version": "0.0.8", "resolved": "https://registry.npmjs.org/minimist/-/minimist-0.0.8.tgz", "integrity": "sha1-hX/Kv8M5fSYluCKCYuhqp6ARsF0=", "dev": true }, "mkdirp": { "version": "0.5.1", "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.1.tgz", "integrity": "sha1-MAV0OOrGz3+MR2fzhkjWaX11yQM=", "dev": true, "requires": { "minimist": "0.0.8" } }, "mocha": { "version": "4.0.1", "resolved": "https://registry.npmjs.org/mocha/-/mocha-4.0.1.tgz", "integrity": "sha512-evDmhkoA+cBNiQQQdSKZa2b9+W2mpLoj50367lhy+Klnx9OV8XlCIhigUnn1gaTFLQCa0kdNhEGDr0hCXOQFDw==", "dev": true, "requires": { "browser-stdout": "1.3.0", "commander": "2.11.0", "debug": "3.1.0", "diff": "3.3.1", "escape-string-regexp": "1.0.5", "glob": "7.1.2", "growl": "1.10.3", "he": "1.1.1", "mkdirp": "0.5.1", "supports-color": "4.4.0" } }, "ms": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=", "dev": true }, "once": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=", "dev": true, "requires": { "wrappy": "1.0.2" } }, "path-is-absolute": { "version": "1.0.1", "resolved": "https://registry.npmjs.org/path-is-absolute/-/path-is-absolute-1.0.1.tgz", "integrity": "sha1-F0uSaHNVNP+8es5r9TpanhtcX18=", "dev": true }, "supports-color": { "version": "4.4.0", "resolved": "https://registry.npmjs.org/supports-color/-/supports-color-4.4.0.tgz", "integrity": "sha512-rKC3+DyXWgK0ZLKwmRsrkyHVZAjNkfzeehuFWdGGcqGDTZFH73+RH6S/RDAAxl9GusSjZSUWYLmT9N5pzXFOXQ==", "dev": true, "requires": { "has-flag": "2.0.0" } }, "wrappy": { "version": "1.0.2", "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=", "dev": true } } } asn1.js-5.0.0/rfc/5280/package.json000066400000000000000000000011571317633451600164440ustar00rootroot00000000000000{ "name": "asn1.js-rfc5280", "version": "2.0.2", "description": "RFC5280 extension structures for asn1.js", "main": "index.js", "repository": { "type": "git", "url": "git@github.com:indutny/asn1.js" }, "keywords": [ "asn1", "rfc5280", "der" ], "scripts": { "test": "mocha --reporter=spec test/*-test.js" }, "author": "Felix Hanley", "license": "MIT", "bugs": { "url": "https://github.com/indutny/asn1.js/issues" }, "homepage": "https://github.com/indutny/asn1.js", "dependencies": { "asn1.js": "^4.5.0" }, "devDependencies": { "mocha": "^4.0.1" } } asn1.js-5.0.0/rfc/5280/test/000077500000000000000000000000001317633451600151315ustar00rootroot00000000000000asn1.js-5.0.0/rfc/5280/test/basic-test.js000066400000000000000000000135361317633451600175350ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); const fs = require('fs'); const asn1 = require('../../../'); const rfc5280 = require('..'); const Buffer = require('buffer').Buffer; describe('asn1.js RFC5280', function() { it('should decode Certificate', function() { const data = fs.readFileSync(__dirname + '/fixtures/cert1.crt'); const res = rfc5280.Certificate.decode(data, 'der'); const tbs = res.tbsCertificate; assert.equal(tbs.version, 'v3'); assert.deepEqual(tbs.serialNumber, new asn1.bignum('462e4256bb1194dc', 16)); assert.equal(tbs.signature.algorithm.join('.'), '1.2.840.113549.1.1.5'); assert.equal(tbs.signature.parameters.toString('hex'), '0500'); }); it('should decode ECC Certificate', function() { // Symantec Class 3 ECC 256 bit Extended Validation CA from // https://knowledge.symantec.com/support/ssl-certificates-support/index?page=content&actp=CROSSLINK&id=AR1908 const data = fs.readFileSync(__dirname + '/fixtures/cert2.crt'); const res = rfc5280.Certificate.decode(data, 'der'); const tbs = res.tbsCertificate; assert.equal(tbs.version, 'v3'); assert.deepEqual(tbs.serialNumber, new asn1.bignum('4d955d20af85c49f6925fbab7c665f89', 16)); assert.equal(tbs.signature.algorithm.join('.'), '1.2.840.10045.4.3.3'); // RFC5754 const spki = rfc5280.SubjectPublicKeyInfo.encode(tbs.subjectPublicKeyInfo, 'der'); // spki check to the output of // openssl x509 -in ecc_cert.pem -pubkey -noout | // openssl pkey -pubin -outform der | openssl base64 assert.equal(spki.toString('base64'), 'MFkwEwYHKoZIzj0CAQYIKoZIzj0DAQcDQgAE3QQ9svKQk5fG6bu8kdtR8KO' + 'G7fvG04WTMgVJ4ASDYZZR/1chrgvaDucEoX/bKhy9ypg1xXFzQM3oaqtUhE' + 'Mm4g==' ); }); it('should decode AuthorityInfoAccess', function() { const data = new Buffer('305a302b06082b06010505073002861f687474703a2f2f70' + '6b692e676f6f676c652e636f6d2f47494147322e63727430' + '2b06082b06010505073001861f687474703a2f2f636c6965' + '6e7473312e676f6f676c652e636f6d2f6f637370', 'hex'); const info = rfc5280.AuthorityInfoAccessSyntax.decode(data, 'der'); assert(info[0].accessMethod); }); it('should decode directoryName in GeneralName', function() { const data = new Buffer('a411300f310d300b06022a03160568656c6c6f', 'hex'); const name = rfc5280.GeneralName.decode(data, 'der'); assert.equal(name.type, 'directoryName'); }); it('should decode Certificate Extensions', function() { let data; let cert; let extensions = {}; data = fs.readFileSync(__dirname + '/fixtures/cert3.crt'); cert = rfc5280.Certificate.decode(data, 'der'); cert.tbsCertificate.extensions.forEach(function(e) { extensions[e.extnID] = e; }); assert.equal(extensions.basicConstraints.extnValue.cA, false); assert.equal(extensions.extendedKeyUsage.extnValue.length, 2); extensions = {}; data = fs.readFileSync(__dirname + '/fixtures/cert4.crt'); cert = rfc5280.Certificate.decode(data, 'der'); cert.tbsCertificate.extensions.forEach(function(e) { extensions[e.extnID] = e; }); assert.equal(extensions.basicConstraints.extnValue.cA, true); assert.equal(extensions.authorityInformationAccess.extnValue[0] .accessLocation.value, 'http://ocsp.godaddy.com/'); extensions = {}; data = fs.readFileSync(__dirname + '/fixtures/cert5.crt'); cert = rfc5280.Certificate.decode(data, 'der'); cert.tbsCertificate.extensions.forEach(function(e) { extensions[e.extnID] = e; }); assert.equal(extensions.basicConstraints.extnValue.cA, true); extensions = {}; data = fs.readFileSync(__dirname + '/fixtures/cert6.crt'); cert = rfc5280.Certificate.decode(data, 'der'); cert.tbsCertificate.extensions.forEach(function(e) { extensions[e.extnID] = e; }); assert.equal(extensions.basicConstraints.extnValue.cA, true); }); it('should encode/decode IssuingDistributionPoint', function() { let input = { onlyContainsUserCerts: true, onlyContainsCACerts: false, indirectCRL: true, onlyContainsAttributeCerts: false }; let data = rfc5280.IssuingDistributionPoint.encode(input); let decoded = rfc5280.IssuingDistributionPoint.decode(data); assert.deepEqual(decoded, input); input = { onlyContainsUserCerts: true, onlyContainsCACerts: false, indirectCRL: true, onlyContainsAttributeCerts: false, onlySomeReasons: { unused: 0, data: new Buffer('asdf') } }; data = rfc5280.IssuingDistributionPoint.encode(input); decoded = rfc5280.IssuingDistributionPoint.decode(data); assert.deepEqual(decoded, input); }); it('should decode Revoked Certificates', function() { let data; let crl; // Downloadable CRL (containing two certificates) from distribution point available on cert1.crt data = fs.readFileSync(__dirname + '/fixtures/cert1.crl'); crl = rfc5280.CertificateList.decode(data, 'der'); assert.equal(crl.tbsCertList.revokedCertificates.length, 2); assert.deepEqual(crl.tbsCertList.revokedCertificates[0].userCertificate, new asn1.bignum('764bedd38afd51f7', 16)); const cert1 = crl.tbsCertList.revokedCertificates[1]; assert.deepEqual(cert1.userCertificate, new asn1.bignum('31da3380182af9b2', 16)); assert.equal(cert1.crlEntryExtensions.length, 1); const ext1 = cert1.crlEntryExtensions[0]; assert.equal(ext1.extnID, 'reasonCode'); assert.equal(ext1.extnValue, 'affiliationChanged'); // Downloadable CRL (empty) from distribution point available on cert4.crt data = fs.readFileSync(__dirname + '/fixtures/cert4.crl'); crl = rfc5280.CertificateList.decode(data, 'der'); assert.equal(crl.tbsCertList.revokedCertificates, undefined); }); }); asn1.js-5.0.0/rfc/5280/test/fixtures/000077500000000000000000000000001317633451600170025ustar00rootroot00000000000000asn1.js-5.0.0/rfc/5280/test/fixtures/cert1.crl000066400000000000000000000010351317633451600205210ustar00rootroot00000000000000000  *H  0I1 0 UUS10U  Google Inc1%0#UGoogle Internet Authority G2 170127010003Z 170206010003Z0R0'vKӊQ 170113141858Z0 0 U 0'13* 160915202213Z0 0 U 00.0U#0JhvbZ/0 Ux0  *H  dVg0ҜGuLHvژ VwOP',i'eA7r&HJLSXf),u&/~y8ҹ=<_oh8A6Cbl|,bkWd“Bl~ MԞA6~Nχ3ZK[2v5^8V8;h(-Mߡb4'0ݓ}xMmXSG[NRf>3%msWasn1.js-5.0.0/rfc/5280/test/fixtures/cert1.crt000066400000000000000000000021721317633451600205340ustar00rootroot000000000000000v0^F.BV0  *H 0I1 0 UUS10U  Google Inc1%0#UGoogle Internet Authority G20 140730120440Z 141028000000Z0h1 0 UUS10U California10U Mountain View10U Google Inc10U www.google.com0"0  *H 0 Nxp6.ޮ. K qk.`*v]G( F͜TP?.:Bz瓻w?βɫho/@ }bϒ}\HJ;vϖT_~'Q2WIE{iK7F֡;x-myOA0=0U%0++0U0www.google.com0h+\0Z0++0http://pki.google.com/GIAG2.crt0++0http://clients1.google.com/ocsp0U=l | S6v(w7؈J0 U00U#0JhvbZ/0U 00  +y00U)0'0%#!http://pki.google.com/GIAG2.crl0  *H -U3a i#zM;iQSݢP78&zdfWdN +`*>yE?ҳUyឧ]o>F>%9+d>OH")T\mPҦ,e*lLǬpelr9nq.asn1.js-5.0.0/rfc/5280/test/fixtures/cert2.crt000066400000000000000000000017471317633451600205440ustar00rootroot0000000000000000jM] ği%|f_0 *H=01 0 UUS10U VeriSign, Inc.10U VeriSign Trust Network1:08U 1(c) 2007 VeriSign, Inc. - For authorized use only1E0CU-~ÜEr4پm28ՠhCEkif{Kx/Ax.@KEIk_ĥ;_Tcjm#pY$Vky!F9zWJXgM;h΄e!y[s00U00U%0++0U06U/0-0+)'%http://crl.godaddy.com/gdig2s1-49.crl0SU L0J0H `Hm0907++http://certificates.godaddy.com/repository/0v+j0h0$+0http://ocsp.godaddy.com/0@+04http://certificates.godaddy.com/repository/gdig2.crt0U#0@½'403l,0#U0 *.bitpay.com bitpay.com0UEN;@r7t8R)8~z0  *H  - ~뻭NiRSRy%8_$;aQ|wE}3x`WBRD:r\aX5''^!' *,7Mm0'O8LWoʜ HW7CõM<> "t`tJ+AJJ.npVhW^KςF]e f he,yP'asn1.js-5.0.0/rfc/5280/test/fixtures/cert4.crl000066400000000000000000000007161317633451600205310ustar00rootroot00000000000000000  *H  01 0 UUS10UArizona10U Scottsdale10U GoDaddy.com, Inc.110/U(Go Daddy Root Certificate Authority - G2 161213195959Z 171213195959Z0  *H  fs?'Ѯg(gJl8aΏ# Gu\E4w B)ў_lE`d4poաD<`Y3hsU"2r{n4Tc}/a;-{*4+[7![OW=S £BξH JX ܼn}DX2:8Yei!_ _g»`r}D.!oƬasn1.js-5.0.0/rfc/5280/test/fixtures/cert4.crt000066400000000000000000000023241317633451600205360ustar00rootroot00000000000000000  *H  01 0 UUS10UArizona10U Scottsdale10U GoDaddy.com, Inc.110/U(Go Daddy Root Certificate Authority - G20 110503070000Z 310503070000Z01 0 UUS10UArizona10U Scottsdale10U GoDaddy.com, Inc.1-0+U $http://certs.godaddy.com/repository/1301U*Go Daddy Secure Certificate Authority - G20"0  *H 0 ԯvԓb0dlb/>eϏb2 d:PJy3 9ilcRwtȹPT5KiN;I.R00U00U0U@½'403l,0U#0:g(An 04+(0&0$+0http://ocsp.godaddy.com/05U.0,0*(&$http://crl.godaddy.com/gdroot-g2.crl0FU ?0=0;U 0301+%https://certs.godaddy.com/repository/0  *H  ~l8K_Ol>PsW1/[yb jcs1H;-]״|%OV0ĶD{,^ a*}CDp `rs$"bXD%bQQ*sv6,ꮛ*Mu?A#}[KXF``}PA¡û/TD 3-v6&a܇oF(&} .0asn1.js-5.0.0/rfc/5280/test/fixtures/cert5.crt000066400000000000000000000022011317633451600205310ustar00rootroot000000000000000}0e0  *H  0c1 0 UUS1!0U The Go Daddy Group, Inc.110/U (Go Daddy Class 2 Certification Authority0 140101070000Z 310530070000Z01 0 UUS10UArizona10U Scottsdale10U GoDaddy.com, Inc.110/U(Go Daddy Root Certificate Authority - G20"0  *H 0 qbY4IX" C;I'Np2>NO/Y0"Vku9Q{5tN?j öè;F|2 f"ȍim6Ӳ`8F >]||+SbiQ%aD,C#߬:)]0 9K]2bC%4V';p*?n蜈}Sm`,X_F< I1\iFG00U00U0U:g(An 0U#0İґLqa=ݨj04+(0&0$+0http://ocsp.godaddy.com/02U+0)0'%#!http://crl.godaddy.com/gdroot.crl0FU ?0=0;U 0301+%https://certs.godaddy.com/repository/0  *H  Y S${[1lpŸnNP0(\b~3Bvە"Xu eg9  Š8#?Di'Z%:2݄*8)3g P*B7Lկ$̵^IT < RImX ٮ2(p WpZS|i H÷ TĬ]g7lʥ/17noW]$l7Lfa 0z) 4_dw@Qߌ0asn1.js-5.0.0/rfc/5280/test/fixtures/cert6.crt000066400000000000000000000020041317633451600205330ustar00rootroot00000000000000000  *H 0c1 0 UUS1!0U The Go Daddy Group, Inc.110/U (Go Daddy Class 2 Certification Authority0 040629170620Z 340629170620Z0c1 0 UUS1!0U The Go Daddy Group, Inc.110/U (Go Daddy Class 2 Certification Authority0 0  *H  0ޝWI[_HgehWq^wIp=Vco?T"Tزu=Kw>x k/j+ň~ĻE'o7X&-r6N?e*n] :-؎_=\e8E``tArbbo_BQe#jxMZ@^s wyg ݠXD{ >b(_ASX~8tit00UİґLqa=ݨj0U#0İґLqa=ݨjge0c1 0 UUS1!0U The Go Daddy Group, Inc.110/U (Go Daddy Class 2 Certification Authority0 U00  *H 2K>ơw3\= ni04cr8(1zT1Xb۔EsE$Ղ#yiML3#An 剞;p~& T%ns! l l a+r9 ͗nN&s+L&qatJWuH.Qia@LĬC Օb ψ2 +E (*ZW7۽asn1.js-5.0.0/test/000077500000000000000000000000001317633451600137615ustar00rootroot00000000000000asn1.js-5.0.0/test/der-decode-test.js000066400000000000000000000114671317633451600173000ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); const asn1 = require('..'); const Buffer = require('buffer').Buffer; describe('asn1.js DER decoder', function() { it('should propagate implicit tag', function() { const B = asn1.define('B', function() { this.seq().obj( this.key('b').octstr() ); }); const A = asn1.define('Bug', function() { this.seq().obj( this.key('a').implicit(0).use(B) ); }); const out = A.decode(new Buffer('300720050403313233', 'hex'), 'der'); assert.equal(out.a.b.toString(), '123'); }); it('should decode optional tag to undefined key', function() { const A = asn1.define('A', function() { this.seq().obj( this.key('key').bool(), this.optional().key('opt').bool() ); }); const out = A.decode(new Buffer('30030101ff', 'hex'), 'der'); assert.deepEqual(out, { 'key': true }); }); it('should decode optional tag to default value', function() { const A = asn1.define('A', function() { this.seq().obj( this.key('key').bool(), this.optional().key('opt').octstr().def('default') ); }); const out = A.decode(new Buffer('30030101ff', 'hex'), 'der'); assert.deepEqual(out, { 'key': true, 'opt': 'default' }); }); function test(name, model, inputHex, expected) { it(name, function() { const M = asn1.define('Model', model); const decoded = M.decode(new Buffer(inputHex,'hex'), 'der'); assert.deepEqual(decoded, expected); }); } test('should decode choice', function() { this.choice({ apple: this.bool(), }); }, '0101ff', { 'type': 'apple', 'value': true }); it('should decode optional and use', function() { const B = asn1.define('B', function() { this.int(); }); const A = asn1.define('A', function() { this.optional().use(B); }); const out = A.decode(new Buffer('020101', 'hex'), 'der'); assert.equal(out.toString(10), '1'); }); test('should decode indefinite length', function() { this.seq().obj( this.key('key').bool() ); }, '30800101ff0000', { 'key': true }); test('should decode objDesc', function() { this.objDesc(); }, '0703323830', new Buffer('280')); test('should decode bmpstr', function() { this.bmpstr(); }, '1e26004300650072007400690066006900630061' + '0074006500540065006d0070006c006100740065', 'CertificateTemplate'); test('should decode bmpstr with cyrillic chars', function() { this.bmpstr(); }, '1e0c041f04400438043204350442', 'Привет'); test('should properly decode objid with dots', function() { this.objid({ '1.2.398.3.10.1.1.1.2.2': 'yes' }); }, '060a2a830e030a0101010202', 'yes'); it('should decode encapsulated models', function() { const B = asn1.define('B', function() { this.seq().obj( this.key('nested').int() ); }); const A = asn1.define('A', function() { this.octstr().contains(B); }); const out = A.decode(new Buffer('04053003020105', 'hex'), 'der'); assert.equal(out.nested.toString(10), '5'); }); test('should decode IA5 string', function() { this.ia5str(); }, '160C646F6720616E6420626F6E65', 'dog and bone'); test('should decode printable string', function() { this.printstr(); }, '1310427261686D7320616E64204C69737A74', 'Brahms and Liszt'); test('should decode T61 string', function() { this.t61str(); }, '140C4F6C69766572205477697374', 'Oliver Twist'); test('should decode ISO646 string', function() { this.iso646str(); }, '1A0B7365707469632074616E6B', 'septic tank'); it('should decode optional seqof', function() { const B = asn1.define('B', function() { this.seq().obj( this.key('num').int() ); }); const A = asn1.define('A', function() { this.seq().obj( this.key('test1').seqof(B), this.key('test2').optional().seqof(B) ); }); let out = A.decode(new Buffer( '3018300A30030201013003020102300A30030201033003020104', 'hex'), 'der'); assert.equal(out.test1[0].num.toString(10), 1); assert.equal(out.test1[1].num.toString(10), 2); assert.equal(out.test2[0].num.toString(10), 3); assert.equal(out.test2[1].num.toString(10), 4); out = A.decode(new Buffer('300C300A30030201013003020102', 'hex'), 'der'); assert.equal(out.test1[0].num.toString(10), 1); assert.equal(out.test1[1].num.toString(10), 2); assert.equal(out.test2, undefined); }); it('should not require decoder param', function() { const M = asn1.define('Model', function() { this.choice({ apple: this.bool(), }); }); // Note no decoder specified, defaults to 'der' const decoded = M.decode(new Buffer('0101ff', 'hex')); assert.deepEqual(decoded, { 'type': 'apple', 'value': true }); }); }); asn1.js-5.0.0/test/der-encode-test.js000066400000000000000000000104611317633451600173030ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); const asn1 = require('..'); const BN = require('bn.js'); const Buffer = require('buffer').Buffer; describe('asn1.js DER encoder', function() { /* * Explicit value shold be wrapped with A0 | EXPLICIT tag * this adds two more bytes to resulting buffer. * */ it('should code explicit tag as 0xA2', function() { const E = asn1.define('E', function() { this.explicit(2).octstr() }); const encoded = E.encode('X', 'der'); // assert.equal(encoded.toString('hex'), 'a203040158'); assert.equal(encoded.length, 5); }) function test(name, model_definition, model_value, der_expected) { it(name, function() { let Model, derActual; Model = asn1.define('Model', model_definition); derActual = Model.encode(model_value, 'der'); assert.deepEqual(derActual, new Buffer(der_expected,'hex')); }); } test('should encode objDesc', function() { this.objDesc(); }, new Buffer('280'), '0703323830'); test('should encode choice', function() { this.choice({ apple: this.bool(), }); }, { type: 'apple', value: true }, '0101ff'); test('should encode implicit seqof', function() { const Int = asn1.define('Int', function() { this.int(); }); this.implicit(0).seqof(Int); }, [ 1 ], 'A003020101' ); test('should encode explicit seqof', function() { const Int = asn1.define('Int', function() { this.int(); }); this.explicit(0).seqof(Int); }, [ 1 ], 'A0053003020101' ); test('should encode BN(128) properly', function() { this.int(); }, new BN(128), '02020080'); test('should encode int 128 properly', function() { this.int(); }, 128, '02020080'); test('should encode 0x8011 properly', function() { this.int(); }, 0x8011, '0203008011'); test('should omit default value in DER', function() { this.seq().obj( this.key('required').def(false).bool(), this.key('value').int() ); }, {required: false, value: 1}, '3003020101'); it('should encode optional and use', function() { const B = asn1.define('B', function() { this.int(); }); const A = asn1.define('A', function() { this.optional().use(B); }); const out = A.encode(1, 'der'); assert.equal(out.toString('hex'), '020101'); }); test('should properly encode objid with dots', function() { this.objid({ '1.2.398.3.10.1.1.1.2.2': 'yes' }); }, 'yes', '060a2a830e030a0101010202'); test('should properly encode objid as array of strings', function() { this.objid(); }, '1.2.398.3.10.1.1.1.2.2'.split('.'), '060a2a830e030a0101010202'); test('should properly encode bmpstr', function() { this.bmpstr(); }, 'CertificateTemplate', '1e26004300650072007400690066006900630061' + '0074006500540065006d0070006c006100740065'); test('should properly encode bmpstr with cyrillic chars', function() { this.bmpstr(); }, 'Привет', '1e0c041f04400438043204350442'); it('should encode encapsulated models', function() { const B = asn1.define('B', function() { this.seq().obj( this.key('nested').int() ); }); const A = asn1.define('A', function() { this.octstr().contains(B); }); const out = A.encode({ nested: 5 }, 'der') assert.equal(out.toString('hex'), '04053003020105'); }); test('should properly encode IA5 string', function() { this.ia5str(); }, 'dog and bone', '160C646F6720616E6420626F6E65'); test('should properly encode printable string', function() { this.printstr(); }, 'Brahms and Liszt', '1310427261686D7320616E64204C69737A74'); test('should properly encode T61 string', function() { this.t61str(); }, 'Oliver Twist', '140C4F6C69766572205477697374'); test('should properly encode ISO646 string', function() { this.iso646str(); }, 'septic tank', '1A0B7365707469632074616E6B'); it('should not require encoder param', function() { const M = asn1.define('Model', function() { this.choice({ apple: this.bool(), }); }); // Note no encoder specified, defaults to 'der' const encoded = M.encode({ 'type': 'apple', 'value': true }); assert.deepEqual(encoded, new Buffer('0101ff', 'hex')); }); }); asn1.js-5.0.0/test/error-test.js000066400000000000000000000142311317633451600164260ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); const asn1 = require('..'); const bn = asn1.bignum; const fixtures = require('./fixtures'); const jsonEqual = fixtures.jsonEqual; const Buffer = require('buffer').Buffer; describe('asn1.js error', function() { describe('encoder', function() { function test(name, model, input, expected) { it('should support ' + name, function() { const M = asn1.define('TestModel', model); let error; assert.throws(function() { try { const encoded = M.encode(input, 'der'); } catch (e) { error = e; throw e; } }); assert(expected.test(error.stack), 'Failed to match, expected: ' + expected + ' got: ' + JSON.stringify(error.stack)); }); } describe('primitives', function() { test('int', function() { this.int(); }, 'hello', /no values map/i); test('enum', function() { this.enum({ 0: 'hello', 1: 'world' }); }, 'gosh', /contain: "gosh"/); test('objid', function() { this.objid(); }, 1, /objid\(\) should be either array or string, got: 1/); test('numstr', function() { this.numstr(); }, 'hello', /only digits and space/); test('printstr', function() { this.printstr(); }, 'hello!', /only latin upper and lower case letters/); }); describe('composite', function() { test('shallow', function() { this.seq().obj( this.key('key').int() ); }, { key: 'hello' } , /map at: \["key"\]/i); test('deep and empty', function() { this.seq().obj( this.key('a').seq().obj( this.key('b').seq().obj( this.key('c').int() ) ) ); }, { } , /input is not object at: \["a"\]\["b"\]/i); test('deep', function() { this.seq().obj( this.key('a').seq().obj( this.key('b').seq().obj( this.key('c').int() ) ) ); }, { a: { b: { c: 'hello' } } } , /map at: \["a"\]\["b"\]\["c"\]/i); test('use', function() { const S = asn1.define('S', function() { this.seq().obj( this.key('x').int() ); }); this.seq().obj( this.key('a').seq().obj( this.key('b').use(S) ) ); }, { a: { b: { x: 'hello' } } } , /map at: \["a"\]\["b"\]\["x"\]/i); }); }); describe('decoder', function() { function test(name, model, input, expected) { it('should support ' + name, function() { const M = asn1.define('TestModel', model); let error; assert.throws(function() { try { const decoded = M.decode(new Buffer(input, 'hex'), 'der'); } catch (e) { error = e; throw e; } }); const partial = M.decode(new Buffer(input, 'hex'), 'der', { partial: true }); assert(expected.test(error.stack), 'Failed to match, expected: ' + expected + ' got: ' + JSON.stringify(error.stack)); assert.equal(partial.errors.length, 1); assert(expected.test(partial.errors[0].stack), 'Failed to match, expected: ' + expected + ' got: ' + JSON.stringify(partial.errors[0].stack)); }); } describe('primitive', function() { test('int', function() { this.int(); }, '2201', /body of: "int"/); test('int', function() { this.int(); }, '', /tag of "int"/); test('bmpstr invalid length', function() { this.bmpstr(); }, '1e0b041f04400438043204350442', /bmpstr length mismatch/); test('numstr unsupported characters', function() { this.numstr(); }, '12024141', /numstr unsupported characters/); test('printstr unsupported characters', function() { this.printstr(); }, '13024121', /printstr unsupported characters/); }); describe('composite', function() { test('shallow', function() { this.seq().obj( this.key('a').seq().obj() ); }, '30', /length of "seq"/); test('deep and empty', function() { this.seq().obj( this.key('a').seq().obj( this.key('b').seq().obj( this.key('c').int() ) ) ); }, '300430023000', /tag of "int" at: \["a"\]\["b"\]\["c"\]/); test('deep and incomplete', function() { this.seq().obj( this.key('a').seq().obj( this.key('b').seq().obj( this.key('c').int() ) ) ); }, '30053003300122', /length of "int" at: \["a"\]\["b"\]\["c"\]/); }); }); describe('partial decoder', function() { function test(name, model, input, expectedObj, expectedErrs) { it('should support ' + name, function() { const M = asn1.define('TestModel', model); const decoded = M.decode(new Buffer(input, 'hex'), 'der', { partial: true }); jsonEqual(decoded.result, expectedObj); assert.equal(decoded.errors.length, expectedErrs.length); expectedErrs.forEach(function(expected, i) { assert(expected.test(decoded.errors[i].stack), 'Failed to match, expected: ' + expected + ' got: ' + JSON.stringify(decoded.errors[i].stack)); }); }); } test('last key not present', function() { this.seq().obj( this.key('a').seq().obj( this.key('b').seq().obj( this.key('c').int() ), this.key('d').int() ) ); }, '30073005300022012e', { a: { b: {}, d: new bn(46) } }, [ /"int" at: \["a"\]\["b"\]\["c"\]/ ]); test('first key not present', function() { this.seq().obj( this.key('a').seq().obj( this.key('b').seq().obj( this.key('c').int() ), this.key('d').int() ) ); }, '30073005300322012e', { a: { b: { c: new bn(46) } } }, [ /"int" at: \["a"\]\["d"\]/ ]); }); }); asn1.js-5.0.0/test/fixtures.js000066400000000000000000000003541317633451600161720ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); function jsonEqual(a, b) { assert.deepEqual(JSON.parse(JSON.stringify(a)), JSON.parse(JSON.stringify(b))); } exports.jsonEqual = jsonEqual; asn1.js-5.0.0/test/pem-test.js000066400000000000000000000030121317633451600160510ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); const asn1 = require('..'); const BN = require('bn.js'); const Buffer = require('buffer').Buffer; describe('asn1.js PEM encoder/decoder', function() { const model = asn1.define('Model', function() { this.seq().obj( this.key('a').int(), this.key('b').bitstr(), this.key('c').int() ); }); const hundred = new Buffer(100); hundred.fill('A'); it('should encode PEM', function() { const out = model.encode({ a: new BN(123), b: { data: hundred, unused: 0 }, c: new BN(456) }, 'pem', { label: 'MODEL' }); const expected = '-----BEGIN MODEL-----\n' + 'MG4CAXsDZQBBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB\n' + 'QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB\n' + 'QUFBQUFBQUFBQUFBAgIByA==\n' + '-----END MODEL-----'; assert.equal(out, expected); }); it('should decode PEM', function() { const expected = '-----BEGIN MODEL-----\n' + 'MG4CAXsDZQBBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB\n' + 'QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB\n' + 'QUFBQUFBQUFBQUFBAgIByA==\n' + '-----END MODEL-----'; const out = model.decode(expected, 'pem', { label: 'MODEL' }); assert.equal(out.a.toString(), '123'); assert.equal(out.b.data.toString(), hundred.toString()); assert.equal(out.c.toString(), '456'); }); }); asn1.js-5.0.0/test/ping-pong-test.js000066400000000000000000000102521317633451600171720ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); const asn1 = require('..'); const fixtures = require('./fixtures'); const jsonEqual = fixtures.jsonEqual; const Buffer = require('buffer').Buffer; describe('asn1.js ping/pong', function() { function test(name, model, input, expected) { it('should support ' + name, function() { const M = asn1.define('TestModel', model); const encoded = M.encode(input, 'der'); const decoded = M.decode(encoded, 'der'); jsonEqual(decoded, expected !== undefined ? expected : input); }); } describe('primitives', function() { test('bigint', function() { this.int(); }, new asn1.bignum('0102030405060708', 16)); test('enum', function() { this.enum({ 0: 'hello', 1: 'world' }); }, 'world'); test('octstr', function() { this.octstr(); }, new Buffer('hello')); test('objDesc', function() { this.objDesc() }, new Buffer('hello')); test('bitstr', function() { this.bitstr(); }, { unused: 4, data: new Buffer('hello!') }); test('ia5str', function() { this.ia5str(); }, 'hello'); test('utf8str', function() { this.utf8str(); }, 'hello'); test('bmpstr', function() { this.bmpstr(); }, 'hello'); test('numstr', function() { this.numstr(); }, '1234 5678 90'); test('printstr', function() { this.printstr(); }, 'hello'); test('gentime', function() { this.gentime(); }, 1385921175000); test('utctime', function() { this.utctime(); }, 1385921175000); test('utctime regression', function() { this.utctime(); }, 1414454400000); test('null', function() { this.null_(); }, null); test('objid', function() { this.objid({ '1 3 6 1 5 5 7 48 1 1': 'id-pkix-ocsp-basic' }); }, 'id-pkix-ocsp-basic'); test('true', function() { this.bool(); }, true); test('false', function() { this.bool(); }, false); test('any', function() { this.any(); }, new Buffer('02210081347a0d3d674aeeb563061d94a3aea5f6a7' + 'c6dc153ea90a42c1ca41929ac1b9', 'hex')); test('default explicit', function() { this.seq().obj( this.key('version').def('v1').explicit(0).int({ 0: 'v1', 1: 'v2' }) ); }, {}, {'version': 'v1'}); test('implicit', function() { this.implicit(0).int({ 0: 'v1', 1: 'v2' }); }, 'v2', 'v2'); }); describe('composite', function() { test('2x int', function() { this.seq().obj( this.key('hello').int(), this.key('world').int() ); }, { hello: 4, world: 2 }); test('enum', function() { this.seq().obj( this.key('hello').enum({ 0: 'world', 1: 'devs' }) ); }, { hello: 'devs' }); test('optionals', function() { this.seq().obj( this.key('hello').enum({ 0: 'world', 1: 'devs' }), this.key('how').optional().def('are you').enum({ 0: 'are you', 1: 'are we?!' }) ); }, { hello: 'devs', how: 'are we?!' }); test('optionals #2', function() { this.seq().obj( this.key('hello').enum({ 0: 'world', 1: 'devs' }), this.key('how').optional().def('are you').enum({ 0: 'are you', 1: 'are we?!' }) ); }, { hello: 'devs' }, { hello: 'devs', how: 'are you' }); test('optionals #3', function() { this.seq().obj( this.key('content').optional().int() ); }, {}, {}); test('optional + any', function() { this.seq().obj( this.key('content').optional().any() ); }, { content: new Buffer('0500', 'hex') }); test('seqof', function() { const S = asn1.define('S', function() { this.seq().obj( this.key('a').def('b').int({ 0: 'a', 1: 'b' }), this.key('c').def('d').int({ 2: 'c', 3: 'd' }) ); }); this.seqof(S); }, [{}, { a: 'a', c: 'c' }], [{ a: 'b', c: 'd' }, { a: 'a', c: 'c' }]); test('choice', function() { this.choice({ apple: this.bool() }); }, { type: 'apple', value: true }); }); }); asn1.js-5.0.0/test/tracking-test.js000066400000000000000000000026211317633451600170770ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); const asn1 = require('..'); const fixtures = require('./fixtures'); const jsonEqual = fixtures.jsonEqual; describe('asn1.js tracking', function() { it('should track nested offsets', () => { const B = asn1.define('B', function() { this.seq().obj( this.key('x').int(), this.key('y').int() ); }); const A = asn1.define('A', function() { this.seq().obj( this.key('a').explicit(0).use(B), this.key('b').use(B) ); }); const input = { a: { x: 1, y: 2 }, b: { x: 3, y: 4 } }; const tracked = []; const encoded = A.encode(input, 'der'); const decoded = A.decode(encoded, 'der', { track: function(path, start, end, type) { tracked.push([ type, path, start, end ]); } }); jsonEqual(input, decoded); assert.deepEqual(tracked, [ [ "tagged", "", 0, 20 ], [ "content", "", 2, 20 ], [ "tagged", "a", 4, 12 ], [ "content", "a", 6, 12 ], [ "tagged", "a/x", 6, 9 ], [ "content", "a/x", 8, 9 ], [ "tagged", "a/y", 9, 12 ], [ "content", "a/y", 11, 12 ], [ "tagged", "b", 12, 20 ], [ "content", "b", 14, 20 ], [ "tagged", "b/x", 14, 17 ], [ "content", "b/x", 16, 17 ], [ "tagged", "b/y", 17, 20 ], [ "content", "b/y", 19, 20 ] ]); }); }); asn1.js-5.0.0/test/use-test.js000066400000000000000000000074031317633451600160740ustar00rootroot00000000000000'use strict'; /* global describe it */ const assert = require('assert'); const asn1 = require('..'); const bn = asn1.bignum; const fixtures = require('./fixtures'); const jsonEqual = fixtures.jsonEqual; const Buffer = require('buffer').Buffer; describe('asn1.js models', function() { describe('plain use', function() { it('should encode submodel', function() { const SubModel = asn1.define('SubModel', function() { this.seq().obj( this.key('b').octstr() ); }); const Model = asn1.define('Model', function() { this.seq().obj( this.key('a').int(), this.key('sub').use(SubModel) ); }); const data = {a: new bn(1), sub: {b: new Buffer("XXX")}}; const wire = Model.encode(data, 'der'); assert.equal(wire.toString('hex'), '300a02010130050403585858'); const back = Model.decode(wire, 'der'); jsonEqual(back, data); }); it('should honour implicit tag from parent', function() { const SubModel = asn1.define('SubModel', function() { this.seq().obj( this.key('x').octstr() ) }); const Model = asn1.define('Model', function() { this.seq().obj( this.key('a').int(), this.key('sub').use(SubModel).implicit(0) ); }); const data = {a: new bn(1), sub: {x: new Buffer("123")}}; const wire = Model.encode(data, 'der'); assert.equal(wire.toString('hex'), '300a020101a0050403313233'); const back = Model.decode(wire, 'der'); jsonEqual(back, data); }); it('should honour explicit tag from parent', function() { const SubModel = asn1.define('SubModel', function() { this.seq().obj( this.key('x').octstr() ) }); const Model = asn1.define('Model', function() { this.seq().obj( this.key('a').int(), this.key('sub').use(SubModel).explicit(0) ); }); const data = {a: new bn(1), sub: {x: new Buffer("123")}}; const wire = Model.encode(data, 'der'); assert.equal(wire.toString('hex'), '300c020101a00730050403313233'); const back = Model.decode(wire, 'der'); jsonEqual(back, data); }); it('should get model with function call', function() { const SubModel = asn1.define('SubModel', function() { this.seq().obj( this.key('x').octstr() ) }); const Model = asn1.define('Model', function() { this.seq().obj( this.key('a').int(), this.key('sub').use(function(obj) { assert.equal(obj.a, 1); return SubModel; }) ); }); const data = {a: new bn(1), sub: {x: new Buffer("123")}}; const wire = Model.encode(data, 'der'); assert.equal(wire.toString('hex'), '300a02010130050403313233'); const back = Model.decode(wire, 'der'); jsonEqual(back, data); }); it('should support recursive submodels', function() { const PlainSubModel = asn1.define('PlainSubModel', function() { this.int(); }); const RecursiveModel = asn1.define('RecursiveModel', function() { this.seq().obj( this.key('plain').bool(), this.key('content').use(function(obj) { if(obj.plain) { return PlainSubModel; } else { return RecursiveModel; } }) ); }); const data = { 'plain': false, 'content': { 'plain': true, 'content': new bn(1) } }; const wire = RecursiveModel.encode(data, 'der'); assert.equal(wire.toString('hex'), '300b01010030060101ff020101'); const back = RecursiveModel.decode(wire, 'der'); jsonEqual(back, data); }); }); });