net-snmp 3.6.4 → 3.7.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.vscode/launch.json +18 -0
- package/README.md +22 -5
- package/index.js +156 -216
- package/package.json +1 -1
package/.vscode/launch.json
CHANGED
@@ -40,6 +40,24 @@
|
|
40
40
|
"1.3.6.1.2.1.1.1.0"
|
41
41
|
]
|
42
42
|
},
|
43
|
+
{
|
44
|
+
"type": "node",
|
45
|
+
"request": "launch",
|
46
|
+
"name": "SNMP community get bulk",
|
47
|
+
"skipFiles": [
|
48
|
+
"<node_internals>/**"
|
49
|
+
],
|
50
|
+
"program": "${workspaceFolder}/example/snmp-get-bulk.js",
|
51
|
+
"args": [
|
52
|
+
"-v", "2c",
|
53
|
+
"-c", "public",
|
54
|
+
"-o", "1",
|
55
|
+
"-r", "20",
|
56
|
+
"127.0.0.1",
|
57
|
+
"1.3.6.1.2.1.1.9",
|
58
|
+
"1.3.6.1.2.1.2"
|
59
|
+
]
|
60
|
+
},
|
43
61
|
{
|
44
62
|
"type": "node",
|
45
63
|
"request": "launch",
|
package/README.md
CHANGED
@@ -231,11 +231,16 @@ RFC 3414:
|
|
231
231
|
|
232
232
|
This object contains constants to select a supported digest algorithm for SNMPv3
|
233
233
|
messages that require authentication:
|
234
|
-
* `md5` - for MD5 message authentication
|
235
|
-
* `sha` - for SHA message authentication
|
234
|
+
* `md5` - for HMAC-MD5 message authentication
|
235
|
+
* `sha` - for HMAC-SHA-1 message authentication
|
236
|
+
* `sha224` - for HMAC-SHA-224 message authentication
|
237
|
+
* `sha256` - for HMAC-SHA-256 message authentication
|
238
|
+
* `sha384` - for HMAC-SHA-384 message authentication
|
239
|
+
* `sha512` - for HMAC-SHA-512 message authentication
|
236
240
|
|
237
|
-
|
238
|
-
|
241
|
+
MD5 and SHA (actually SHA-1) are the hash algorithms specified in the original
|
242
|
+
SNMPv3 User-Based Security Model RFC (RFC 3414); the other four were added later
|
243
|
+
in RFC 7860.
|
239
244
|
|
240
245
|
## snmp.PrivProtocols
|
241
246
|
|
@@ -310,7 +315,7 @@ Actions
|
|
310
315
|
- `4 - ECouldNotDecrypt`
|
311
316
|
- `5 - EAuthFailure`
|
312
317
|
- `6 - EReqResOidNoMatch`
|
313
|
-
- `7 -
|
318
|
+
- `7 - (no longer used)
|
314
319
|
- `8 - EOutOfOrder`
|
315
320
|
- `9 - EVersionNoMatch`
|
316
321
|
- `10 - ECommunityNoMatch`
|
@@ -3194,6 +3199,18 @@ Example programs are included under the module's `example` directory.
|
|
3194
3199
|
|
3195
3200
|
* Ignore mismatched returned OIDs by default
|
3196
3201
|
|
3202
|
+
## Version 3.7.0 - 04/06/2022
|
3203
|
+
|
3204
|
+
* Add SHA-2 authentication support (SHA-224, SHA-256, SHA-384, SHA-512)
|
3205
|
+
|
3206
|
+
## Version 3.7.1 - 05/06/2022
|
3207
|
+
|
3208
|
+
* Fix DES decrypt corruption issue
|
3209
|
+
|
3210
|
+
## Version 3.7.2 - 05/06/2022
|
3211
|
+
|
3212
|
+
* Improve getBulk response handling
|
3213
|
+
|
3197
3214
|
# License
|
3198
3215
|
|
3199
3216
|
Copyright (c) 2020 Mark Abrahams <mark@abrahams.co.nz>
|
package/index.js
CHANGED
@@ -138,7 +138,11 @@ _expandConstantObject (SecurityLevel);
|
|
138
138
|
var AuthProtocols = {
|
139
139
|
"1": "none",
|
140
140
|
"2": "md5",
|
141
|
-
"3": "sha"
|
141
|
+
"3": "sha",
|
142
|
+
"4": "sha224",
|
143
|
+
"5": "sha256",
|
144
|
+
"6": "sha384",
|
145
|
+
"7": "sha512"
|
142
146
|
};
|
143
147
|
|
144
148
|
_expandConstantObject (AuthProtocols);
|
@@ -261,7 +265,7 @@ var ResponseInvalidCode = {
|
|
261
265
|
4: "ECouldNotDecrypt",
|
262
266
|
5: "EAuthFailure",
|
263
267
|
6: "EReqResOidNoMatch",
|
264
|
-
7: "ENonRepeaterCountMismatch",
|
268
|
+
// 7: "ENonRepeaterCountMismatch", // no longer used
|
265
269
|
8: "EOutOfOrder",
|
266
270
|
9: "EVersionNoMatch",
|
267
271
|
10: "ECommunityNoMatch",
|
@@ -875,7 +879,7 @@ var readPdu = function (reader, scoped) {
|
|
875
879
|
var contextEngineID;
|
876
880
|
var contextName;
|
877
881
|
if ( scoped ) {
|
878
|
-
reader.
|
882
|
+
reader = new ber.Reader (reader.readString (ber.Sequence | ber.Constructor, true));
|
879
883
|
contextEngineID = reader.readString (ber.OctetString, true);
|
880
884
|
contextName = reader.readString ();
|
881
885
|
}
|
@@ -918,22 +922,45 @@ var createDiscoveryPdu = function (context) {
|
|
918
922
|
var Authentication = {};
|
919
923
|
|
920
924
|
Authentication.HMAC_BUFFER_SIZE = 1024*1024;
|
921
|
-
Authentication.HMAC_BLOCK_SIZE = 64;
|
922
|
-
Authentication.AUTHENTICATION_CODE_LENGTH = 12;
|
923
|
-
Authentication.AUTH_PARAMETERS_PLACEHOLDER = Buffer.from('8182838485868788898a8b8c', 'hex');
|
924
925
|
|
925
926
|
Authentication.algorithms = {};
|
926
927
|
|
927
928
|
Authentication.algorithms[AuthProtocols.md5] = {
|
928
929
|
KEY_LENGTH: 16,
|
930
|
+
AUTHENTICATION_CODE_LENGTH: 12,
|
929
931
|
CRYPTO_ALGORITHM: 'md5'
|
930
932
|
};
|
931
933
|
|
932
934
|
Authentication.algorithms[AuthProtocols.sha] = {
|
933
935
|
KEY_LENGTH: 20,
|
936
|
+
AUTHENTICATION_CODE_LENGTH: 12,
|
934
937
|
CRYPTO_ALGORITHM: 'sha1'
|
935
938
|
};
|
936
939
|
|
940
|
+
Authentication.algorithms[AuthProtocols.sha224] = {
|
941
|
+
KEY_LENGTH: 28,
|
942
|
+
AUTHENTICATION_CODE_LENGTH: 16,
|
943
|
+
CRYPTO_ALGORITHM: 'sha224'
|
944
|
+
};
|
945
|
+
|
946
|
+
Authentication.algorithms[AuthProtocols.sha256] = {
|
947
|
+
KEY_LENGTH: 32,
|
948
|
+
AUTHENTICATION_CODE_LENGTH: 24,
|
949
|
+
CRYPTO_ALGORITHM: 'sha256'
|
950
|
+
};
|
951
|
+
|
952
|
+
Authentication.algorithms[AuthProtocols.sha384] = {
|
953
|
+
KEY_LENGTH: 48,
|
954
|
+
AUTHENTICATION_CODE_LENGTH: 32,
|
955
|
+
CRYPTO_ALGORITHM: 'sha384'
|
956
|
+
};
|
957
|
+
|
958
|
+
Authentication.algorithms[AuthProtocols.sha512] = {
|
959
|
+
KEY_LENGTH: 64,
|
960
|
+
AUTHENTICATION_CODE_LENGTH: 48,
|
961
|
+
CRYPTO_ALGORITHM: 'sha512'
|
962
|
+
};
|
963
|
+
|
937
964
|
Authentication.authToKeyCache = {};
|
938
965
|
|
939
966
|
Authentication.computeCacheKey = function (authProtocol, authPasswordString, engineID) {
|
@@ -947,10 +974,6 @@ Authentication.passwordToKey = function (authProtocol, authPasswordString, engin
|
|
947
974
|
var firstDigest;
|
948
975
|
var finalDigest;
|
949
976
|
var buf;
|
950
|
-
var bufOffset = 0;
|
951
|
-
var passwordIndex = 0;
|
952
|
-
var count = 0;
|
953
|
-
var password;
|
954
977
|
var cryptoAlgorithm = Authentication.algorithms[authProtocol].CRYPTO_ALGORITHM;
|
955
978
|
|
956
979
|
var cacheKey = Authentication.computeCacheKey(authProtocol, authPasswordString, engineID);
|
@@ -958,15 +981,8 @@ Authentication.passwordToKey = function (authProtocol, authPasswordString, engin
|
|
958
981
|
return Authentication.authToKeyCache[cacheKey];
|
959
982
|
}
|
960
983
|
|
961
|
-
buf = Buffer.alloc (Authentication.HMAC_BUFFER_SIZE);
|
962
|
-
|
963
|
-
|
964
|
-
while (count < Authentication.HMAC_BUFFER_SIZE) {
|
965
|
-
for (var i = 0; i < Authentication.HMAC_BLOCK_SIZE; i++) {
|
966
|
-
buf.writeUInt8(password[passwordIndex++ % password.length], bufOffset++);
|
967
|
-
}
|
968
|
-
count += Authentication.HMAC_BLOCK_SIZE;
|
969
|
-
}
|
984
|
+
buf = Buffer.alloc (Authentication.HMAC_BUFFER_SIZE, authPasswordString);
|
985
|
+
|
970
986
|
hashAlgorithm = crypto.createHash(cryptoAlgorithm);
|
971
987
|
hashAlgorithm.update(buf);
|
972
988
|
firstDigest = hashAlgorithm.digest();
|
@@ -983,94 +999,61 @@ Authentication.passwordToKey = function (authProtocol, authPasswordString, engin
|
|
983
999
|
return finalDigest;
|
984
1000
|
};
|
985
1001
|
|
986
|
-
Authentication.
|
987
|
-
|
988
|
-
|
1002
|
+
Authentication.getParametersLength = function (authProtocol) {
|
1003
|
+
return Authentication.algorithms[authProtocol].AUTHENTICATION_CODE_LENGTH;
|
1004
|
+
};
|
989
1005
|
|
990
|
-
|
991
|
-
|
992
|
-
messageBuffer.fill (0, authenticationParametersOffset, authenticationParametersOffset + Authentication.AUTHENTICATION_CODE_LENGTH);
|
1006
|
+
Authentication.writeParameters = function (messageBuffer, authProtocol, authPassword, engineID, digestInMessage) {
|
1007
|
+
var digestToAdd;
|
993
1008
|
|
994
1009
|
digestToAdd = Authentication.calculateDigest (messageBuffer, authProtocol, authPassword, engineID);
|
995
|
-
digestToAdd.copy (
|
1010
|
+
digestToAdd.copy (digestInMessage);
|
996
1011
|
// debug ("Added Auth Parameters: " + digestToAdd.toString('hex'));
|
997
1012
|
};
|
998
1013
|
|
999
1014
|
Authentication.isAuthentic = function (messageBuffer, authProtocol, authPassword, engineID, digestInMessage) {
|
1000
|
-
var
|
1015
|
+
var savedDigest;
|
1001
1016
|
var calculatedDigest;
|
1002
1017
|
|
1018
|
+
if (digestInMessage.length !== Authentication.algorithms[authProtocol].AUTHENTICATION_CODE_LENGTH)
|
1019
|
+
return false;
|
1020
|
+
|
1021
|
+
// save original authenticationParameters field in message
|
1022
|
+
savedDigest = Buffer.from (digestInMessage);
|
1023
|
+
|
1003
1024
|
// clear the authenticationParameters field in message
|
1004
|
-
|
1005
|
-
messageBuffer.fill (0, authenticationParametersOffset, authenticationParametersOffset + Authentication.AUTHENTICATION_CODE_LENGTH);
|
1025
|
+
digestInMessage.fill (0);
|
1006
1026
|
|
1007
1027
|
calculatedDigest = Authentication.calculateDigest (messageBuffer, authProtocol, authPassword, engineID);
|
1008
1028
|
|
1009
1029
|
// replace previously cleared authenticationParameters field in message
|
1010
|
-
|
1030
|
+
savedDigest.copy (digestInMessage);
|
1011
1031
|
|
1012
1032
|
// debug ("Digest in message: " + digestInMessage.toString('hex'));
|
1013
1033
|
// debug ("Calculated digest: " + calculatedDigest.toString('hex'));
|
1014
|
-
return calculatedDigest.equals (digestInMessage
|
1034
|
+
return calculatedDigest.equals (digestInMessage);
|
1015
1035
|
};
|
1016
1036
|
|
1017
1037
|
Authentication.calculateDigest = function (messageBuffer, authProtocol, authPassword, engineID) {
|
1018
1038
|
var authKey = Authentication.passwordToKey (authProtocol, authPassword, engineID);
|
1019
1039
|
|
1020
|
-
// Adapted from RFC3147 Section 6.3.1. Processing an Outgoing Message
|
1021
|
-
var hashAlgorithm;
|
1022
|
-
var kIpad;
|
1023
|
-
var kOpad;
|
1024
|
-
var firstDigest;
|
1025
|
-
var finalDigest;
|
1026
|
-
var truncatedDigest;
|
1027
|
-
var i;
|
1028
1040
|
var cryptoAlgorithm = Authentication.algorithms[authProtocol].CRYPTO_ALGORITHM;
|
1029
|
-
|
1030
|
-
|
1031
|
-
|
1032
|
-
|
1033
|
-
authKey = hashAlgorithm.digest ();
|
1034
|
-
}
|
1035
|
-
|
1036
|
-
// MD(K XOR opad, MD(K XOR ipad, msg))
|
1037
|
-
kIpad = Buffer.alloc (Authentication.HMAC_BLOCK_SIZE);
|
1038
|
-
kOpad = Buffer.alloc (Authentication.HMAC_BLOCK_SIZE);
|
1039
|
-
for (i = 0; i < authKey.length; i++) {
|
1040
|
-
kIpad[i] = authKey[i] ^ 0x36;
|
1041
|
-
kOpad[i] = authKey[i] ^ 0x5c;
|
1042
|
-
}
|
1043
|
-
kIpad.fill (0x36, authKey.length);
|
1044
|
-
kOpad.fill (0x5c, authKey.length);
|
1045
|
-
|
1046
|
-
// inner MD
|
1047
|
-
hashAlgorithm = crypto.createHash (cryptoAlgorithm);
|
1048
|
-
hashAlgorithm.update (kIpad);
|
1049
|
-
hashAlgorithm.update (messageBuffer);
|
1050
|
-
firstDigest = hashAlgorithm.digest ();
|
1051
|
-
// outer MD
|
1052
|
-
hashAlgorithm = crypto.createHash (cryptoAlgorithm);
|
1053
|
-
hashAlgorithm.update (kOpad);
|
1054
|
-
hashAlgorithm.update (firstDigest);
|
1055
|
-
finalDigest = hashAlgorithm.digest ();
|
1056
|
-
|
1057
|
-
truncatedDigest = Buffer.alloc (Authentication.AUTHENTICATION_CODE_LENGTH);
|
1058
|
-
finalDigest.copy (truncatedDigest, 0, 0, Authentication.AUTHENTICATION_CODE_LENGTH);
|
1059
|
-
return truncatedDigest;
|
1041
|
+
var hmacAlgorithm = crypto.createHmac (cryptoAlgorithm, authKey);
|
1042
|
+
hmacAlgorithm.update (messageBuffer);
|
1043
|
+
var digest = hmacAlgorithm.digest ();
|
1044
|
+
return digest.subarray (0, Authentication.algorithms[authProtocol].AUTHENTICATION_CODE_LENGTH);
|
1060
1045
|
};
|
1061
1046
|
|
1062
1047
|
var Encryption = {};
|
1063
1048
|
|
1064
|
-
Encryption.PRIV_PARAMETERS_PLACEHOLDER = Buffer.from ('9192939495969798', 'hex');
|
1065
|
-
|
1066
1049
|
Encryption.encryptPdu = function (privProtocol, scopedPdu, privPassword, authProtocol, engine) {
|
1067
1050
|
var encryptFunction = Encryption.algorithms[privProtocol].encryptPdu;
|
1068
1051
|
return encryptFunction (scopedPdu, privProtocol, privPassword, authProtocol, engine);
|
1069
1052
|
};
|
1070
1053
|
|
1071
|
-
Encryption.decryptPdu = function (privProtocol, encryptedPdu, privParameters, privPassword, authProtocol, engine
|
1054
|
+
Encryption.decryptPdu = function (privProtocol, encryptedPdu, privParameters, privPassword, authProtocol, engine) {
|
1072
1055
|
var decryptFunction = Encryption.algorithms[privProtocol].decryptPdu;
|
1073
|
-
return decryptFunction (encryptedPdu, privProtocol, privParameters, privPassword, authProtocol, engine
|
1056
|
+
return decryptFunction (encryptedPdu, privProtocol, privParameters, privPassword, authProtocol, engine);
|
1074
1057
|
};
|
1075
1058
|
|
1076
1059
|
Encryption.debugEncrypt = function (encryptionKey, iv, plainPdu, encryptedPdu) {
|
@@ -1196,7 +1179,7 @@ Encryption.encryptPduDes = function (scopedPdu, privProtocol, privPassword, auth
|
|
1196
1179
|
};
|
1197
1180
|
};
|
1198
1181
|
|
1199
|
-
Encryption.decryptPduDes = function (encryptedPdu, privProtocol, privParameters, privPassword, authProtocol, engine
|
1182
|
+
Encryption.decryptPduDes = function (encryptedPdu, privProtocol, privParameters, privPassword, authProtocol, engine) {
|
1200
1183
|
var des = Encryption.algorithms[PrivProtocols.des];
|
1201
1184
|
var privLocalizedKey;
|
1202
1185
|
var decryptionKey;
|
@@ -1220,23 +1203,9 @@ Encryption.decryptPduDes = function (encryptedPdu, privProtocol, privParameters,
|
|
1220
1203
|
}
|
1221
1204
|
|
1222
1205
|
decipher = crypto.createDecipheriv (des.CRYPTO_ALGORITHM, decryptionKey, iv);
|
1223
|
-
|
1224
|
-
decipher.setAutoPadding(false);
|
1225
|
-
}
|
1206
|
+
decipher.setAutoPadding(false);
|
1226
1207
|
decryptedPdu = decipher.update (encryptedPdu);
|
1227
|
-
|
1228
|
-
// - where sometimes a decrypt error is thrown with decipher.final()
|
1229
|
-
// It replaces this line which should have been sufficient:
|
1230
|
-
// decryptedPdu = Buffer.concat ([decryptedPdu, decipher.final()]);
|
1231
|
-
try {
|
1232
|
-
decryptedPdu = Buffer.concat ([decryptedPdu, decipher.final()]);
|
1233
|
-
} catch (error) {
|
1234
|
-
// debug("Decrypt error: " + error);
|
1235
|
-
decipher = crypto.createDecipheriv (des.CRYPTO_ALGORITHM, decryptionKey, iv);
|
1236
|
-
decipher.setAutoPadding(false);
|
1237
|
-
decryptedPdu = decipher.update (encryptedPdu);
|
1238
|
-
decryptedPdu = Buffer.concat ([decryptedPdu, decipher.final()]);
|
1239
|
-
}
|
1208
|
+
decryptedPdu = Buffer.concat ([decryptedPdu, decipher.final()]);
|
1240
1209
|
// Encryption.debugDecrypt (decryptionKey, iv, encryptedPdu, decryptedPdu);
|
1241
1210
|
|
1242
1211
|
return decryptedPdu;
|
@@ -1301,13 +1270,6 @@ Encryption.decryptPduAes = function (encryptedPdu, privProtocol, privParameters,
|
|
1301
1270
|
return decryptedPdu;
|
1302
1271
|
};
|
1303
1272
|
|
1304
|
-
Encryption.addParametersToMessageBuffer = function (messageBuffer, msgPrivacyParameters) {
|
1305
|
-
var privacyParametersOffset;
|
1306
|
-
|
1307
|
-
privacyParametersOffset = messageBuffer.indexOf (Encryption.PRIV_PARAMETERS_PLACEHOLDER);
|
1308
|
-
msgPrivacyParameters.copy (messageBuffer, privacyParametersOffset, 0, Encryption.DES_IV_LENGTH);
|
1309
|
-
};
|
1310
|
-
|
1311
1273
|
Encryption.algorithms = {};
|
1312
1274
|
|
1313
1275
|
Encryption.algorithms[PrivProtocols.des] = {
|
@@ -1391,6 +1353,29 @@ Message.prototype.toBufferV3 = function () {
|
|
1391
1353
|
if (this.buffer)
|
1392
1354
|
return this.buffer;
|
1393
1355
|
|
1356
|
+
// ScopedPDU
|
1357
|
+
var scopedPduWriter = new ber.Writer ();
|
1358
|
+
scopedPduWriter.startSequence ();
|
1359
|
+
var contextEngineID = this.pdu.contextEngineID ? this.pdu.contextEngineID : this.msgSecurityParameters.msgAuthoritativeEngineID;
|
1360
|
+
if ( contextEngineID.length == 0 ) {
|
1361
|
+
scopedPduWriter.writeString ("");
|
1362
|
+
} else {
|
1363
|
+
scopedPduWriter.writeBuffer (contextEngineID, ber.OctetString);
|
1364
|
+
}
|
1365
|
+
scopedPduWriter.writeString (this.pdu.contextName);
|
1366
|
+
this.pdu.toBuffer (scopedPduWriter);
|
1367
|
+
scopedPduWriter.endSequence ();
|
1368
|
+
|
1369
|
+
if ( this.hasPrivacy() ) {
|
1370
|
+
var authoritativeEngine = {
|
1371
|
+
engineID: this.msgSecurityParameters.msgAuthoritativeEngineID,
|
1372
|
+
engineBoots: this.msgSecurityParameters.msgAuthoritativeEngineBoots,
|
1373
|
+
engineTime: this.msgSecurityParameters.msgAuthoritativeEngineTime,
|
1374
|
+
};
|
1375
|
+
encryptionResult = Encryption.encryptPdu (this.user.privProtocol, scopedPduWriter.buffer,
|
1376
|
+
this.user.privKey, this.user.authProtocol, authoritativeEngine);
|
1377
|
+
}
|
1378
|
+
|
1394
1379
|
var writer = new ber.Writer ();
|
1395
1380
|
|
1396
1381
|
writer.startSequence ();
|
@@ -1408,77 +1393,56 @@ Message.prototype.toBufferV3 = function () {
|
|
1408
1393
|
writer.endSequence ();
|
1409
1394
|
|
1410
1395
|
// msgSecurityParameters
|
1411
|
-
|
1412
|
-
|
1413
|
-
//
|
1396
|
+
writer.startSequence (ber.OctetString);
|
1397
|
+
writer.startSequence ();
|
1398
|
+
//writer.writeString (this.msgSecurityParameters.msgAuthoritativeEngineID);
|
1414
1399
|
// writing a zero-length buffer fails - should fix asn1-ber for this condition
|
1415
1400
|
if ( this.msgSecurityParameters.msgAuthoritativeEngineID.length == 0 ) {
|
1416
|
-
|
1401
|
+
writer.writeString ("");
|
1417
1402
|
} else {
|
1418
|
-
|
1403
|
+
writer.writeBuffer (this.msgSecurityParameters.msgAuthoritativeEngineID, ber.OctetString);
|
1419
1404
|
}
|
1420
|
-
|
1421
|
-
|
1422
|
-
|
1405
|
+
writer.writeInt (this.msgSecurityParameters.msgAuthoritativeEngineBoots);
|
1406
|
+
writer.writeInt (this.msgSecurityParameters.msgAuthoritativeEngineTime);
|
1407
|
+
writer.writeString (this.msgSecurityParameters.msgUserName);
|
1423
1408
|
|
1409
|
+
var msgAuthenticationParameters = '';
|
1424
1410
|
if ( this.hasAuthentication() ) {
|
1425
|
-
|
1426
|
-
|
1427
|
-
|
1428
|
-
msgSecurityParametersWriter.writeBuffer (this.msgSecurityParameters.msgAuthenticationParameters, ber.OctetString);
|
1411
|
+
var authParametersLength = Authentication.getParametersLength (this.user.authProtocol);
|
1412
|
+
msgAuthenticationParameters = Buffer.alloc (authParametersLength);
|
1413
|
+
writer.writeBuffer (msgAuthenticationParameters, ber.OctetString);
|
1429
1414
|
} else {
|
1430
|
-
|
1415
|
+
writer.writeString ("");
|
1431
1416
|
}
|
1417
|
+
var msgAuthenticationParametersOffset = writer._offset - msgAuthenticationParameters.length;
|
1432
1418
|
|
1433
1419
|
if ( this.hasPrivacy() ) {
|
1434
|
-
|
1435
|
-
// should never happen where msgFlags has no privacy but privacy parameters still present
|
1436
|
-
} else if ( this.msgSecurityParameters.msgPrivacyParameters.length > 0 ) {
|
1437
|
-
msgSecurityParametersWriter.writeBuffer (this.msgSecurityParameters.msgPrivacyParameters, ber.OctetString);
|
1438
|
-
} else {
|
1439
|
-
msgSecurityParametersWriter.writeString ("");
|
1440
|
-
}
|
1441
|
-
msgSecurityParametersWriter.endSequence ();
|
1442
|
-
|
1443
|
-
writer.writeBuffer (msgSecurityParametersWriter.buffer, ber.OctetString);
|
1444
|
-
|
1445
|
-
// ScopedPDU
|
1446
|
-
var scopedPduWriter = new ber.Writer ();
|
1447
|
-
scopedPduWriter.startSequence ();
|
1448
|
-
var contextEngineID = this.pdu.contextEngineID ? this.pdu.contextEngineID : this.msgSecurityParameters.msgAuthoritativeEngineID;
|
1449
|
-
if ( contextEngineID.length == 0 ) {
|
1450
|
-
scopedPduWriter.writeString ("");
|
1420
|
+
writer.writeBuffer (encryptionResult.msgPrivacyParameters, ber.OctetString);
|
1451
1421
|
} else {
|
1452
|
-
|
1422
|
+
writer.writeString ("");
|
1453
1423
|
}
|
1454
|
-
|
1455
|
-
|
1456
|
-
|
1424
|
+
msgAuthenticationParametersOffset -= writer._offset;
|
1425
|
+
writer.endSequence ();
|
1426
|
+
writer.endSequence ();
|
1427
|
+
msgAuthenticationParametersOffset += writer._offset;
|
1457
1428
|
|
1458
1429
|
if ( this.hasPrivacy() ) {
|
1459
|
-
var authoritativeEngine = {
|
1460
|
-
engineID: this.msgSecurityParameters.msgAuthoritativeEngineID,
|
1461
|
-
engineBoots: this.msgSecurityParameters.msgAuthoritativeEngineBoots,
|
1462
|
-
engineTime: this.msgSecurityParameters.msgAuthoritativeEngineTime,
|
1463
|
-
};
|
1464
|
-
encryptionResult = Encryption.encryptPdu (this.user.privProtocol, scopedPduWriter.buffer,
|
1465
|
-
this.user.privKey, this.user.authProtocol, authoritativeEngine);
|
1466
1430
|
writer.writeBuffer (encryptionResult.encryptedPdu, ber.OctetString);
|
1467
1431
|
} else {
|
1468
1432
|
writer.writeBuffer (scopedPduWriter.buffer);
|
1469
1433
|
}
|
1470
1434
|
|
1435
|
+
msgAuthenticationParametersOffset -= writer._offset;
|
1471
1436
|
writer.endSequence ();
|
1437
|
+
msgAuthenticationParametersOffset += writer._offset;
|
1472
1438
|
|
1473
1439
|
this.buffer = writer.buffer;
|
1474
1440
|
|
1475
|
-
if ( this.hasPrivacy() ) {
|
1476
|
-
Encryption.addParametersToMessageBuffer(this.buffer, encryptionResult.msgPrivacyParameters);
|
1477
|
-
}
|
1478
|
-
|
1479
1441
|
if ( this.hasAuthentication() ) {
|
1480
|
-
|
1481
|
-
|
1442
|
+
msgAuthenticationParameters = this.buffer.subarray (msgAuthenticationParametersOffset,
|
1443
|
+
msgAuthenticationParametersOffset + msgAuthenticationParameters.length);
|
1444
|
+
Authentication.writeParameters (this.buffer, this.user.authProtocol, this.user.authKey,
|
1445
|
+
this.msgSecurityParameters.msgAuthoritativeEngineID, msgAuthenticationParameters);
|
1482
1446
|
}
|
1483
1447
|
|
1484
1448
|
return this.buffer;
|
@@ -1513,23 +1477,10 @@ Message.prototype.decryptPdu = function (user, responseCb) {
|
|
1513
1477
|
decryptedPduReader = new ber.Reader (decryptedPdu);
|
1514
1478
|
this.pdu = readPdu(decryptedPduReader, true);
|
1515
1479
|
return true;
|
1516
|
-
|
1517
|
-
|
1518
|
-
|
1519
|
-
|
1520
|
-
} catch (possibleTruncationError) {
|
1521
|
-
try {
|
1522
|
-
decryptedPdu = Encryption.decryptPdu(user.privProtocol, this.encryptedPdu,
|
1523
|
-
this.msgSecurityParameters.msgPrivacyParameters, user.privKey, user.authProtocol,
|
1524
|
-
this.msgSecurityParameters.msgAuthoritativeEngineID, true);
|
1525
|
-
decryptedPduReader = new ber.Reader (decryptedPdu);
|
1526
|
-
this.pdu = readPdu(decryptedPduReader, true);
|
1527
|
-
return true;
|
1528
|
-
} catch (error) {
|
1529
|
-
responseCb (new ResponseInvalidError ("Failed to decrypt PDU: " + error,
|
1530
|
-
ResponseInvalidCode.ECouldNotDecrypt));
|
1531
|
-
return false;
|
1532
|
-
}
|
1480
|
+
} catch (error) {
|
1481
|
+
responseCb (new ResponseInvalidError ("Failed to decrypt PDU: " + error,
|
1482
|
+
ResponseInvalidCode.ECouldNotDecrypt));
|
1483
|
+
return false;
|
1533
1484
|
}
|
1534
1485
|
|
1535
1486
|
};
|
@@ -1734,7 +1685,7 @@ Message.createFromBuffer = function (buffer, user) {
|
|
1734
1685
|
message.msgSecurityParameters.msgAuthoritativeEngineBoots = msgSecurityParametersReader.readInt ();
|
1735
1686
|
message.msgSecurityParameters.msgAuthoritativeEngineTime = msgSecurityParametersReader.readInt ();
|
1736
1687
|
message.msgSecurityParameters.msgUserName = msgSecurityParametersReader.readString ();
|
1737
|
-
message.msgSecurityParameters.msgAuthenticationParameters =
|
1688
|
+
message.msgSecurityParameters.msgAuthenticationParameters = msgSecurityParametersReader.readString (ber.OctetString, true);
|
1738
1689
|
message.msgSecurityParameters.msgPrivacyParameters = Buffer.from(msgSecurityParametersReader.readString (ber.OctetString, true));
|
1739
1690
|
|
1740
1691
|
if ( message.hasPrivacy() ) {
|
@@ -1917,6 +1868,7 @@ Session.prototype.get = function (oids, responseCb) {
|
|
1917
1868
|
|
1918
1869
|
Session.prototype.getBulk = function () {
|
1919
1870
|
var oids, nonRepeaters, maxRepetitions, responseCb;
|
1871
|
+
var reportOidMismatchErrors = this.reportOidMismatchErrors;
|
1920
1872
|
var backwardsGetNexts = this.backwardsGetNexts;
|
1921
1873
|
|
1922
1874
|
if (arguments.length >= 4) {
|
@@ -1938,71 +1890,59 @@ Session.prototype.getBulk = function () {
|
|
1938
1890
|
|
1939
1891
|
function feedCb (req, message) {
|
1940
1892
|
var pdu = message.pdu;
|
1893
|
+
var reqVarbinds = req.message.pdu.varbinds;
|
1941
1894
|
var varbinds = [];
|
1942
1895
|
var i = 0;
|
1943
1896
|
|
1944
|
-
|
1945
|
-
|
1946
|
-
|
1947
|
-
|
1948
|
-
|
1949
|
-
|
1950
|
-
|
1951
|
-
|
1952
|
-
|
1953
|
-
|
1954
|
-
|
1955
|
-
|
1956
|
-
|
1957
|
-
|
1958
|
-
+ req.message.pdu.varbinds[i].oid + "' in request at "
|
1959
|
-
+ "positiion '" + i + "' does not precede "
|
1960
|
-
+ "OID '" + pdu.varbinds[i].oid + "' in response "
|
1897
|
+
for ( ; i < reqVarbinds.length && i < pdu.varbinds.length; i++) {
|
1898
|
+
if (isVarbindError (pdu.varbinds[i])) {
|
1899
|
+
if ( reportOidMismatchErrors && reqVarbinds[i].oid != pdu.varbinds[i].oid ) {
|
1900
|
+
req.responseCb (new ResponseInvalidError ("OID '" + reqVarbinds[i].oid
|
1901
|
+
+ "' in request at position '" + i + "' does not "
|
1902
|
+
+ "match OID '" + pdu.varbinds[i].oid + "' in response "
|
1903
|
+
+ "at position '" + i + "'", ResponseInvalidCode.EReqResOidNoMatch));
|
1904
|
+
return;
|
1905
|
+
}
|
1906
|
+
} else {
|
1907
|
+
if ( ! backwardsGetNexts && ! oidFollowsOid (reqVarbinds[i].oid, pdu.varbinds[i].oid)) {
|
1908
|
+
req.responseCb (new ResponseInvalidError ("OID '" + reqVarbinds[i].oid
|
1909
|
+
+ "' in request at positiion '" + i + "' does not "
|
1910
|
+
+ "precede OID '" + pdu.varbinds[i].oid + "' in response "
|
1961
1911
|
+ "at position '" + i + "'", ResponseInvalidCode.EOutOfOrder));
|
1962
1912
|
return;
|
1963
|
-
} else {
|
1964
|
-
varbinds.push (pdu.varbinds[i]);
|
1965
1913
|
}
|
1966
1914
|
}
|
1915
|
+
if (i < nonRepeaters)
|
1916
|
+
varbinds.push (pdu.varbinds[i]);
|
1917
|
+
else
|
1918
|
+
varbinds.push ([pdu.varbinds[i]]);
|
1967
1919
|
}
|
1968
1920
|
|
1969
|
-
var repeaters =
|
1921
|
+
var repeaters = reqVarbinds.length - nonRepeaters;
|
1970
1922
|
|
1971
|
-
|
1972
|
-
|
1973
|
-
|
1974
|
-
|
1975
|
-
|
1976
|
-
|
1977
|
-
|
1978
|
-
|
1979
|
-
|
1980
|
-
|
1981
|
-
|
1982
|
-
|
1983
|
-
|
1984
|
-
|
1985
|
-
|
1986
|
-
|
1987
|
-
|
1988
|
-
|
1989
|
-
|
1990
|
-
|
1991
|
-
req.responseCb (new ResponseInvalidError ("OID '"
|
1992
|
-
+ req.message.pdu.varbinds[reqIndex].oid
|
1993
|
-
+ "' in request at position '" + (reqIndex)
|
1994
|
-
+ "' does not precede OID '"
|
1995
|
-
+ pdu.varbinds[respIndex].oid
|
1996
|
-
+ "' in response at position '" + (respIndex) + "'",
|
1997
|
-
ResponseInvalidCode.EOutOfOrder));
|
1998
|
-
return;
|
1999
|
-
} else {
|
2000
|
-
if (! varbinds[reqIndex])
|
2001
|
-
varbinds[reqIndex] = [];
|
2002
|
-
varbinds[reqIndex].push (pdu.varbinds[respIndex]);
|
2003
|
-
}
|
1923
|
+
for ( ; i < pdu.varbinds.length; i++) {
|
1924
|
+
var reqIndex = (i - nonRepeaters) % repeaters + nonRepeaters;
|
1925
|
+
var prevIndex = i - repeaters;
|
1926
|
+
var prevOid = pdu.varbinds[prevIndex].oid;
|
1927
|
+
|
1928
|
+
if (isVarbindError (pdu.varbinds[i])) {
|
1929
|
+
if ( reportOidMismatchErrors && prevOid != pdu.varbinds[i].oid ) {
|
1930
|
+
req.responseCb (new ResponseInvalidError ("OID '" + prevOid
|
1931
|
+
+ "' in response at position '" + prevIndex + "' does not "
|
1932
|
+
+ "match OID '" + pdu.varbinds[i].oid + "' in response "
|
1933
|
+
+ "at position '" + i + "'", ResponseInvalidCode.EReqResOidNoMatch));
|
1934
|
+
return;
|
1935
|
+
}
|
1936
|
+
} else {
|
1937
|
+
if ( ! backwardsGetNexts && ! oidFollowsOid (prevOid, pdu.varbinds[i].oid)) {
|
1938
|
+
req.responseCb (new ResponseInvalidError ("OID '" + prevOid
|
1939
|
+
+ "' in response at positiion '" + prevIndex + "' does not "
|
1940
|
+
+ "precede OID '" + pdu.varbinds[i].oid + "' in response "
|
1941
|
+
+ "at position '" + i + "'", ResponseInvalidCode.EOutOfOrder));
|
1942
|
+
return;
|
2004
1943
|
}
|
2005
1944
|
}
|
1945
|
+
varbinds[reqIndex].push (pdu.varbinds[i]);
|
2006
1946
|
}
|
2007
1947
|
|
2008
1948
|
req.responseCb (null, varbinds);
|