2021-03-25 19:19:30 +00:00
|
|
|
'use strict';
|
|
|
|
|
|
|
|
const {
|
|
|
|
ObjectSetPrototypeOf,
|
|
|
|
Symbol,
|
|
|
|
} = primordials;
|
|
|
|
|
|
|
|
const {
|
|
|
|
SocketAddress: _SocketAddress,
|
|
|
|
AF_INET,
|
|
|
|
AF_INET6,
|
|
|
|
} = internalBinding('block_list');
|
|
|
|
|
|
|
|
const {
|
|
|
|
validateObject,
|
|
|
|
validateString,
|
|
|
|
validatePort,
|
|
|
|
validateUint32,
|
|
|
|
} = require('internal/validators');
|
|
|
|
|
|
|
|
const {
|
|
|
|
codes: {
|
|
|
|
ERR_INVALID_ARG_VALUE,
|
|
|
|
},
|
|
|
|
} = require('internal/errors');
|
|
|
|
|
|
|
|
const {
|
|
|
|
customInspectSymbol: kInspect,
|
2022-12-31 07:33:39 +00:00
|
|
|
kEmptyObject,
|
2021-03-25 19:19:30 +00:00
|
|
|
} = require('internal/util');
|
|
|
|
|
|
|
|
const { inspect } = require('internal/util/inspect');
|
|
|
|
|
|
|
|
const {
|
2023-07-07 17:00:00 +00:00
|
|
|
markTransferMode,
|
2021-03-25 19:19:30 +00:00
|
|
|
kClone,
|
|
|
|
kDeserialize,
|
|
|
|
} = require('internal/worker/js_transferable');
|
|
|
|
|
|
|
|
const kHandle = Symbol('kHandle');
|
|
|
|
const kDetail = Symbol('kDetail');
|
|
|
|
|
2023-07-07 17:00:00 +00:00
|
|
|
class SocketAddress {
|
2021-03-25 19:19:30 +00:00
|
|
|
static isSocketAddress(value) {
|
|
|
|
return value?.[kHandle] !== undefined;
|
|
|
|
}
|
|
|
|
|
2022-12-31 07:33:39 +00:00
|
|
|
constructor(options = kEmptyObject) {
|
2023-07-07 17:00:00 +00:00
|
|
|
markTransferMode(this, true, false);
|
|
|
|
|
2021-03-25 19:19:30 +00:00
|
|
|
validateObject(options, 'options');
|
2021-03-25 20:27:03 +00:00
|
|
|
let { family = 'ipv4' } = options;
|
2021-03-25 19:19:30 +00:00
|
|
|
const {
|
|
|
|
address = (family === 'ipv4' ? '127.0.0.1' : '::'),
|
|
|
|
port = 0,
|
|
|
|
flowlabel = 0,
|
|
|
|
} = options;
|
|
|
|
|
|
|
|
let type;
|
2021-03-25 20:27:03 +00:00
|
|
|
if (typeof family?.toLowerCase === 'function')
|
|
|
|
family = family.toLowerCase();
|
2021-03-25 19:19:30 +00:00
|
|
|
switch (family) {
|
|
|
|
case 'ipv4':
|
|
|
|
type = AF_INET;
|
|
|
|
break;
|
|
|
|
case 'ipv6':
|
|
|
|
type = AF_INET6;
|
|
|
|
break;
|
|
|
|
default:
|
2021-03-25 20:27:03 +00:00
|
|
|
throw new ERR_INVALID_ARG_VALUE('options.family', options.family);
|
2021-03-25 19:19:30 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
validateString(address, 'options.address');
|
|
|
|
validatePort(port, 'options.port');
|
|
|
|
validateUint32(flowlabel, 'options.flowlabel', false);
|
|
|
|
|
|
|
|
this[kHandle] = new _SocketAddress(address, port, type, flowlabel);
|
|
|
|
this[kDetail] = this[kHandle].detail({
|
|
|
|
address: undefined,
|
|
|
|
port: undefined,
|
|
|
|
family: undefined,
|
|
|
|
flowlabel: undefined,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
get address() {
|
|
|
|
return this[kDetail].address;
|
|
|
|
}
|
|
|
|
|
|
|
|
get port() {
|
|
|
|
return this[kDetail].port;
|
|
|
|
}
|
|
|
|
|
|
|
|
get family() {
|
|
|
|
return this[kDetail].family === AF_INET ? 'ipv4' : 'ipv6';
|
|
|
|
}
|
|
|
|
|
|
|
|
get flowlabel() {
|
|
|
|
// The flow label can be changed internally.
|
|
|
|
return this[kHandle].flowlabel();
|
|
|
|
}
|
|
|
|
|
|
|
|
[kInspect](depth, options) {
|
|
|
|
if (depth < 0)
|
|
|
|
return this;
|
|
|
|
|
|
|
|
const opts = {
|
|
|
|
...options,
|
2023-02-26 10:34:02 +00:00
|
|
|
depth: options.depth == null ? null : options.depth - 1,
|
2021-03-25 19:19:30 +00:00
|
|
|
};
|
|
|
|
|
|
|
|
return `SocketAddress ${inspect(this.toJSON(), opts)}`;
|
|
|
|
}
|
|
|
|
|
|
|
|
[kClone]() {
|
|
|
|
const handle = this[kHandle];
|
|
|
|
return {
|
|
|
|
data: { handle },
|
|
|
|
deserializeInfo: 'internal/socketaddress:InternalSocketAddress',
|
|
|
|
};
|
|
|
|
}
|
|
|
|
|
|
|
|
[kDeserialize]({ handle }) {
|
|
|
|
this[kHandle] = handle;
|
|
|
|
this[kDetail] = handle.detail({
|
|
|
|
address: undefined,
|
|
|
|
port: undefined,
|
|
|
|
family: undefined,
|
|
|
|
flowlabel: undefined,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
|
|
|
|
toJSON() {
|
|
|
|
return {
|
|
|
|
address: this.address,
|
|
|
|
port: this.port,
|
|
|
|
family: this.family,
|
|
|
|
flowlabel: this.flowlabel,
|
|
|
|
};
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-07-07 17:00:00 +00:00
|
|
|
class InternalSocketAddress {
|
2021-03-25 19:19:30 +00:00
|
|
|
constructor(handle) {
|
2023-07-07 17:00:00 +00:00
|
|
|
markTransferMode(this, true, false);
|
|
|
|
|
2021-03-25 19:19:30 +00:00
|
|
|
this[kHandle] = handle;
|
2022-09-15 16:13:03 +00:00
|
|
|
this[kDetail] = this[kHandle]?.detail({
|
|
|
|
address: undefined,
|
|
|
|
port: undefined,
|
|
|
|
family: undefined,
|
|
|
|
flowlabel: undefined,
|
|
|
|
});
|
2021-03-25 19:19:30 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
InternalSocketAddress.prototype.constructor =
|
2021-04-07 07:41:21 +00:00
|
|
|
SocketAddress.prototype.constructor;
|
2021-03-25 19:19:30 +00:00
|
|
|
ObjectSetPrototypeOf(InternalSocketAddress.prototype, SocketAddress.prototype);
|
|
|
|
|
|
|
|
module.exports = {
|
|
|
|
SocketAddress,
|
|
|
|
InternalSocketAddress,
|
2021-03-25 20:27:03 +00:00
|
|
|
kHandle,
|
2021-03-25 19:19:30 +00:00
|
|
|
};
|