From 7f43ade50b79fbfcf57710475c8bc91f914461f6 Mon Sep 17 00:00:00 2001 From: Mark Cavage Date: Tue, 30 Aug 2011 04:48:05 +0000 Subject: [PATCH] Initial DTrace prototype --- lib/dtrace.js | 34 ++++++++++-- lib/messages/result.js | 13 ++++- lib/server.js | 123 +++++++++++++++++++++++++++++++---------- 3 files changed, 135 insertions(+), 35 deletions(-) diff --git a/lib/dtrace.js b/lib/dtrace.js index c8ad3af..7b78bce 100644 --- a/lib/dtrace.js +++ b/lib/dtrace.js @@ -16,11 +16,35 @@ var SERVER_PROVIDER; */ var SERVER_PROBES = { - add: ['char "*', 'char *', 'char *'], - bind: ['char "*', 'char *', 'char *'], - unbind: ['char "*', 'char *', 'char *'], - connection: ['char *'] + // 3: attributes.length + add: ['char *', 'char *', 'char *', 'int'], + bind: ['char *', 'char *', 'char *'], + + // 3: attribute, 4: value + compare: ['char *', 'char *', 'char *', 'char *', 'char *'], + + 'delete': ['char *', 'char *', 'char *'], + + // 3: requestName, 4: requestValue + exop: ['char *', 'char *', 'char *', 'char *', 'char *'], + + // 3: changes.length + modify: ['char *', 'char *', 'char *', 'int'], + + // 3: newRdn, 4: deleteOldRdn, 5: newSuperior + modifyDN: ['char *', 'char *', 'char *', 'char *', 'int', 'char *'], + + // 3: filter, 4: scope, 5: attributes.length + search: ['char *', 'char *', 'char *', 'char *', 'char *', 'int'], + + unbind: ['char *', 'char *', 'char *'], + + // remote IP + connection: ['char *'], + + // statusCode, matchedDN, error message, remoteAddress, bindDN, req.dn + result: ['int', 'char *', 'char *', 'char *', 'char *', 'char *'] }; @@ -38,7 +62,7 @@ module.exports = { Object.keys(SERVER_PROBES).forEach(function(p) { var args = SERVER_PROBES[p].splice(0); args.unshift(p); - console.log('%j', args); + dtrace.DTraceProvider.prototype.addProbe.apply(SERVER_PROVIDER, args); }); diff --git a/lib/messages/result.js b/lib/messages/result.js index ecc20cc..8f72785 100644 --- a/lib/messages/result.js +++ b/lib/messages/result.js @@ -8,7 +8,7 @@ var asn1 = require('asn1'); var LDAPMessage = require('./message'); var Protocol = require('../protocol'); - +var dtrace = require('../dtrace').serverProvider(); ///--- Globals @@ -17,6 +17,7 @@ var Ber = asn1.Ber; var BerWriter = asn1.BerWriter; + ///--- API function LDAPResult(options) { @@ -66,11 +67,21 @@ LDAPResult.prototype.end = function(status) { this.log.debug('%s: sending: %j', this.connection.ldap.id, this.json); try { + var self = this; this.connection.write(ber); + dtrace.fire('result', function() { + return [self.status, + (self.matchedDN || ''), + (self.errorMessage || ''), + (self.connection ? self.connection.remoteAddress : ''), + (self.connection ? self.connection.ldap.bindDN.toString() : ''), + (self.requestDN ? self.requestDN.toString() : '')]; + }); } catch (e) { this.log.warn('%s failure to write message %j: %s', this.connection.ldap.id, this.json, e.toString()); } + }; diff --git a/lib/server.js b/lib/server.js index c498deb..e18fc4d 100644 --- a/lib/server.js +++ b/lib/server.js @@ -228,9 +228,12 @@ function Server(options) { c.remotePort = c.fd; } + var rdn = new dn.RDN(); + rdn.cn = 'anonymous' c.ldap = { id: c.remoteAddress + ':' + c.remotePort, - config: options + config: options, + _bindDN: new DN([rdn]) }; c.addListener('timeout', function() { log.trace('%s timed out', c.ldap.id); @@ -249,7 +252,7 @@ function Server(options) { }); c.ldap.__defineGetter__('bindDN', function() { - return c.ldap._bindDN || new DN([{cn: 'anonymous'}]); + return c.ldap._bindDN; }); c.ldap.__defineSetter__('bindDN', function(val) { if (!(val instanceof DN)) @@ -284,6 +287,9 @@ function Server(options) { return; } + res.connection = c; + res.requestDN = req.dn; + var chain = self._getHandlerChain(req); var i = 0; @@ -395,7 +401,9 @@ Server.prototype.add = function(name) { var args = Array.prototype.slice.call(arguments, 1); args.unshift(function(req, res, next) { self.dtrace.fire('add', function() { - return [c.remoteAddress, c.ldap.bindDN.toString(), c.dn.toString()]; + var c = req.connection; + return [c.remoteAddress, c.ldap.bindDN.toString(), req.dn.toString(), + req.attributes.length]; }); return next(); }); @@ -420,13 +428,13 @@ Server.prototype.bind = function(name) { var args = Array.prototype.slice.call(arguments, 1); args.unshift(function(req, res, next) { self.dtrace.fire('bind', function() { - return [c.remoteAddress, c.ldap.bindDN.toString(), c.dn.toString()]; + var c = req.connection; + return [c.remoteAddress, c.ldap.bindDN.toString(), req.dn.toString()]; }); return next(); }); return this._mount(Protocol.LDAP_REQ_BIND, name, args); - }; @@ -441,9 +449,19 @@ Server.prototype.bind = function(name) { * @throws {TypeError} on bad input */ Server.prototype.compare = function(name) { - return this._mount(Protocol.LDAP_REQ_COMPARE, - name, - Array.prototype.slice.call(arguments, 1)); + var self = this; + + var args = Array.prototype.slice.call(arguments, 1); + args.unshift(function(req, res, next) { + self.dtrace.fire('compare', function() { + var c = req.connection; + return [c.remoteAddress, c.ldap.bindDN.toString(), req.dn.toString(), + req.attribute, req.value]; + }); + return next(); + }); + + return this._mount(Protocol.LDAP_REQ_COMPARE, name, args); }; @@ -458,9 +476,18 @@ Server.prototype.compare = function(name) { * @throws {TypeError} on bad input */ Server.prototype.del = function(name) { - return this._mount(Protocol.LDAP_REQ_DELETE, - name, - Array.prototype.slice.call(arguments, 1)); + var self = this; + + var args = Array.prototype.slice.call(arguments, 1); + args.unshift(function(req, res, next) { + self.dtrace.fire('delete', function() { + var c = req.connection; + return [c.remoteAddress, c.ldap.bindDN.toString(), req.dn.toString()]; + }); + return next(); + }); + + return this._mount(Protocol.LDAP_REQ_DELETE, name, args); }; @@ -475,10 +502,19 @@ Server.prototype.del = function(name) { * @throws {TypeError} on bad input. */ Server.prototype.exop = function(name) { - return this._mount(Protocol.LDAP_REQ_EXTENSION, - name, - Array.prototype.slice.call(arguments, 1), - true); + var self = this; + + var args = Array.prototype.slice.call(arguments, 1); + args.unshift(function(req, res, next) { + self.dtrace.fire('exop', function() { + var c = req.connection; + return [c.remoteAddress, c.ldap.bindDN.toString(), req.name, + req.name, req.value]; + }); + return next(); + }); + + return this._mount(Protocol.LDAP_REQ_EXTENSION, name, args, true); }; @@ -493,9 +529,19 @@ Server.prototype.exop = function(name) { * @throws {TypeError} on bad input */ Server.prototype.modify = function(name) { - return this._mount(Protocol.LDAP_REQ_MODIFY, - name, - Array.prototype.slice.call(arguments, 1)); + var self = this; + + var args = Array.prototype.slice.call(arguments, 1); + args.unshift(function(req, res, next) { + self.dtrace.fire('modify', function() { + var c = req.connection; + return [c.remoteAddress, c.ldap.bindDN.toString(), req.dn.toString(), + req.changes.length]; + }); + return next(); + }); + + return this._mount(Protocol.LDAP_REQ_MODIFY, name, args); }; @@ -510,9 +556,20 @@ Server.prototype.modify = function(name) { * @throws {TypeError} on bad input */ Server.prototype.modifyDN = function(name) { - return this._mount(Protocol.LDAP_REQ_MODRDN, - name, - Array.prototype.slice.call(arguments, 1)); + var self = this; + + var args = Array.prototype.slice.call(arguments, 1); + args.unshift(function(req, res, next) { + self.dtrace.fire('modifyDN', function() { + var c = req.connection; + return [c.remoteAddress, c.ldap.bindDN.toString(), req.dn.toString(), + req.newRdn.toString(), (req.deleteOldRdn ? 1 : 0), + (req.newSuperior ? req.newSuperior.toString() : '')]; + }); + return next(); + }); + + return this._mount(Protocol.LDAP_REQ_MODRDN, name, args); }; @@ -527,9 +584,20 @@ Server.prototype.modifyDN = function(name) { * @throws {TypeError} on bad input */ Server.prototype.search = function(name) { - return this._mount(Protocol.LDAP_REQ_SEARCH, - name, - Array.prototype.slice.call(arguments, 1)); + var self = this; + + var args = Array.prototype.slice.call(arguments, 1); + args.unshift(function(req, res, next) { + self.dtrace.fire('search', function() { + var c = req.connection; + return [c.remoteAddress, c.ldap.bindDN.toString(), req.dn.toString(), + req.filter.toString(), req.scope, req.attributes.length]; + }); + return next(); + }); + + + return this._mount(Protocol.LDAP_REQ_SEARCH, name, args); }; @@ -545,7 +613,7 @@ Server.prototype.search = function(name) { Server.prototype.unbind = function() { var self = this; - var args = Array.prototype.slice.call(arguments, 1); + var args = Array.prototype.slice.call(arguments, 0); args.unshift(function(req, res, next) { self.dtrace.fire('unbind', function() { return [c.remoteAddress, c.ldap.bindDN.toString(), c.dn.toString()]; @@ -553,10 +621,7 @@ Server.prototype.unbind = function() { return next(); }); - return this._mount(Protocol.LDAP_REQ_UNBIND, - 'unbind', - Array.prototype.slice.call(arguments, 0), - true); + return this._mount(Protocol.LDAP_REQ_UNBIND, 'unbind', args, true); };