Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in / Register
Toggle navigation
N
node-acp
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Service Desk
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Operations
Operations
Incidents
Environments
Packages & Registries
Packages & Registries
Container Registry
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Samuel Elliott
node-acp
Commits
aea9d8b8
Verified
Commit
aea9d8b8
authored
Nov 10, 2018
by
Samuel Elliott
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Clean up
parent
5880a6eb
Changes
5
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
133 additions
and
145 deletions
+133
-145
src/client.js
src/client.js
+46
-43
src/keystream.js
src/keystream.js
+5
-5
src/message.js
src/message.js
+44
-45
src/property.js
src/property.js
+26
-24
src/session.js
src/session.js
+12
-28
No files found.
src/client.js
View file @
aea9d8b8
import
Session
from
'
./session
'
;
import
Message
from
'
./message
'
;
import
Property
,
{
elementHeaderSize
}
from
'
./property
'
;
// import { CFLBinaryPListParser }
from './cflbinary';
import
Message
,
{
HEADER_SIZE
as
MESSAGE_HEADER_SIZE
}
from
'
./message
'
;
import
Property
,
{
HEADER_SIZE
as
ELEMENT_HEADER_SIZE
}
from
'
./property
'
;
import
CFLBinaryPList
from
'
./cflbinary
'
;
export
default
class
Client
{
constructor
(
host
,
port
,
password
)
{
...
...
@@ -30,57 +30,61 @@ export default class Client {
}
receiveMessageHeader
()
{
return
this
.
receive
(
M
essage
.
headerSize
);
return
this
.
receive
(
M
ESSAGE_HEADER_SIZE
);
}
receivePropertyElementHeader
()
{
return
this
.
receive
(
elementHeaderSize
);
return
this
.
receive
(
ELEMENT_HEADER_SIZE
);
}
/**
* Gets properties from the AirPort device.
*
* Client: GetProp {...Property}
* Server: GetProp
* Server: ...Property
*/
async
getProperties
(
prop_names
)
{
let
payload
=
''
;
for
(
let
name
of
prop_names
)
{
payload
+=
Property
.
composeRawElement
(
0
,
new
Property
(
name
));
payload
+=
Property
.
composeRawElement
(
0
,
n
ame
instanceof
Property
?
name
:
n
ew
Property
(
name
));
}
const
request
=
Message
.
composeGetPropCommand
(
4
,
this
.
password
,
payload
);
await
this
.
send
(
request
);
const
reply
=
await
this
.
receiveMessageHeader
();
const
replyHeader
=
await
Message
.
parseRaw
(
reply
);
console
.
debug
(
'
Reply:
'
,
{
reply
,
replyHeader
,
});
const
reply_header
=
await
Message
.
parseRaw
(
reply
);
if
(
replyHeader
.
errorCode
!==
0
)
{
console
.
log
(
'
Client.getProperties error code:
'
,
replyHeader
.
errorCode
);
return
[];
if
(
reply_header
.
error_code
!==
0
)
{
throw
new
Error
(
'
Error
'
.
reply_header
.
error_code
);
}
const
props
=
[];
while
(
true
)
{
const
propHeader
=
await
this
.
receivePropertyElementHeader
();
console
.
debug
(
'
Received property element header:
'
,
propHeader
);
const
{
name
,
flags
,
size
}
=
await
Property
.
parseRawElementHeader
(
propHeader
);
const
prop_header
=
await
this
.
receivePropertyElementHeader
();
console
.
debug
(
'
Received property element header:
'
,
prop_header
);
const
data
=
await
Property
.
parseRawElementHeader
(
prop_header
);
console
.
debug
(
data
);
const
{
name
,
flags
,
size
}
=
data
;
const
propData
=
await
this
.
receive
(
size
);
const
value
=
await
this
.
receive
(
size
);
if
(
flags
&
1
)
{
const
errorCode
=
Buffer
.
from
(
propData
,
'
binary
'
).
readInt32BE
(
0
);
console
.
log
(
'
error requesting value for property
'
,
name
,
'
-
'
,
errorCode
);
continue
;
const
error_code
=
Buffer
.
from
(
value
,
'
binary
'
).
readInt32BE
(
0
);
throw
new
Error
(
'
Error requesting value for property "
'
+
name
+
'
":
'
+
error_code
);
}
const
prop
=
new
Property
(
name
,
propData
);
console
.
debug
(
'
prop
'
,
prop
);
const
prop
=
new
Property
(
name
,
value
);
if
(
typeof
prop
.
name
===
'
undefined
'
&&
typeof
prop
.
value
===
'
undefined
'
)
{
console
.
debug
(
'
found empty prop end marker
'
);
break
;
}
console
.
debug
(
'
Prop
'
,
prop
);
props
.
push
(
prop
);
}
...
...
@@ -97,27 +101,26 @@ export default class Client {
const
request
=
Message
.
composeSetPropCommand
(
0
,
this
.
password
,
payload
);
await
this
.
send
(
request
);
const
raw
R
eply
=
await
this
.
receiveMessageHeader
();
const
reply
Header
=
await
Message
.
parseRaw
(
rawR
eply
);
const
raw
_r
eply
=
await
this
.
receiveMessageHeader
();
const
reply
_header
=
await
Message
.
parseRaw
(
raw_r
eply
);
if
(
reply
Header
.
errorC
ode
!==
0
)
{
console
.
log
(
'
set properties error code
'
,
reply
Header
.
errorC
ode
);
if
(
reply
_header
.
error_c
ode
!==
0
)
{
console
.
log
(
'
set properties error code
'
,
reply
_header
.
error_c
ode
);
return
;
}
const
prop
H
eader
=
await
this
.
receivePropertyElementHeader
();
const
{
name
,
flags
,
size
}
=
await
Property
.
parseRawElementHeader
(
prop
H
eader
);
const
prop
_h
eader
=
await
this
.
receivePropertyElementHeader
();
const
{
name
,
flags
,
size
}
=
await
Property
.
parseRawElementHeader
(
prop
_h
eader
);
const
propData
=
await
this
.
receive
(
size
);
const
value
=
await
this
.
receive
(
size
);
if
(
flags
)
{
const
errorCode
=
Buffer
.
from
(
propData
,
'
binary
'
).
readUInt32BE
(
0
);
console
.
log
(
'
error setting value for property
'
,
name
,
'
-
'
,
errorCode
);
return
;
if
(
flags
&
1
)
{
const
error_code
=
Buffer
.
from
(
value
,
'
binary
'
).
readUInt32BE
(
0
);
throw
new
Error
(
'
Error setting value for property "
'
+
name
+
'
":
'
+
error_code
);
}
const
prop
=
new
Property
(
name
,
propData
);
console
.
debug
(
'
p
rop
'
,
prop
);
const
prop
=
new
Property
(
name
,
value
);
console
.
debug
(
'
P
rop
'
,
prop
);
if
(
typeof
prop
.
name
===
'
undefined
'
&&
typeof
prop
.
value
===
'
undefined
'
)
{
console
.
debug
(
'
found empty prop end marker
'
);
...
...
@@ -125,15 +128,15 @@ export default class Client {
}
async
getFeatures
()
{
this
.
send
(
Message
.
composeFeatCommand
(
0
));
const
reply
Header
=
await
Message
.
parseRaw
(
this
.
receiveMessageHeader
());
const
reply
=
await
this
.
receive
(
reply
Header
.
bodyS
ize
);
return
CFLBinaryPList
Parser
.
parse
(
reply
);
await
this
.
send
(
Message
.
composeFeatCommand
(
0
));
const
reply
_header
=
await
Message
.
parseRaw
(
await
this
.
receiveMessageHeader
());
const
reply
=
await
this
.
receive
(
reply
_header
.
body_s
ize
);
return
CFLBinaryPList
.
parse
(
reply
);
}
async
flashPrimary
(
payload
)
{
this
.
send
(
Message
.
composeFlashPrimaryCommand
(
0
,
this
.
password
,
payload
));
const
reply
H
eader
=
await
Message
.
parseRaw
(
this
.
receiveMessageHeader
());
return
await
this
.
receive
(
reply
Header
.
bodyS
ize
);
const
reply
_h
eader
=
await
Message
.
parseRaw
(
this
.
receiveMessageHeader
());
return
await
this
.
receive
(
reply
_header
.
body_s
ize
);
}
}
src/keystream.js
View file @
aea9d8b8
...
...
@@ -7,15 +7,15 @@ export const ACP_STATIC_KEY = Buffer.from('5b6faf5d9d5b0e1351f2da1de7e8d673', 'h
export
function
generateACPKeystream
(
length
)
{
let
key
=
''
;
let
key_
idx
=
0
;
let
idx
=
0
;
while
(
key_
idx
<
length
)
{
while
(
idx
<
length
)
{
key
+=
String
.
fromCharCode
(
(
key_
idx
+
0x55
&
0xFF
)
^
ACP_STATIC_KEY
.
charCodeAt
(
key_
idx
%
ACP_STATIC_KEY
.
length
)
(
idx
+
0x55
&
0xFF
)
^
ACP_STATIC_KEY
.
charCodeAt
(
idx
%
ACP_STATIC_KEY
.
length
)
);
key_
idx
++
;
idx
++
;
}
return
key
;
...
...
src/message.js
View file @
aea9d8b8
...
...
@@ -3,7 +3,9 @@
* ACP message composition and parsing
*/
import
Property
from
'
./property
'
;
import
{
generateACPKeystream
}
from
'
./keystream
'
;
import
adler32
from
'
adler32
'
;
/**
...
...
@@ -13,35 +15,36 @@ import adler32 from 'adler32';
* @return {String} Encrypted password of proper length for the header field
*/
export
function
generateACPHeaderKey
(
password
)
{
const
passwordLength
=
0x20
;
const
passwordKey
=
generateACPKeystream
(
passwordLength
);
const
password_length
=
0x20
;
const
password_key
=
generateACPKeystream
(
password_length
);
const
password_buffer
=
password
.
substr
(
0
,
password_length
).
padEnd
(
password_length
,
'
\
x00
'
);
let
encrypted_password_buffer
=
''
;
const
passwordBuffer
=
password
.
substr
(
0
,
passwordLength
).
padEnd
(
passwordLength
,
'
\
x00
'
);
let
encryptedPasswordBuffer
=
''
;
for
(
let
i
=
0
;
i
<
passwordLength
;
i
++
)
{
encryptedPasswordBuffer
+=
String
.
fromCharCode
(
passwordKey
.
charCodeAt
(
i
)
^
passwordBuffer
.
charCodeAt
(
i
));
for
(
let
i
=
0
;
i
<
password_length
;
i
++
)
{
encrypted_password_buffer
+=
String
.
fromCharCode
(
password_key
.
charCodeAt
(
i
)
^
password_buffer
.
charCodeAt
(
i
));
}
return
encrypted
PasswordB
uffer
;
return
encrypted
_password_b
uffer
;
}
export
const
headerMagic
=
'
acpp
'
;
export
const
headerSize
=
128
;
export
const
HEADER_MAGIC
=
'
acpp
'
;
export
const
HEADER_SIZE
=
128
;
export
default
class
Message
{
constructor
(
version
,
flags
,
unused
,
command
,
error
Code
,
key
,
body
,
bodyS
ize
)
{
constructor
(
version
,
flags
,
unused
,
command
,
error
_code
,
key
,
body
,
body_s
ize
)
{
this
.
version
=
version
;
this
.
flags
=
flags
;
this
.
unused
=
unused
;
this
.
command
=
command
;
this
.
error
Code
=
errorC
ode
;
this
.
error
_code
=
error_c
ode
;
if
(
typeof
body
===
'
undefined
'
)
{
this
.
body
Size
=
typeof
bodySize
!==
'
undefined
'
?
bodyS
ize
:
-
1
;
this
.
body
C
hecksum
=
1
;
this
.
body
_size
=
typeof
body_size
!==
'
undefined
'
?
body_s
ize
:
-
1
;
this
.
body
_c
hecksum
=
1
;
}
else
{
this
.
body
Size
=
typeof
bodySize
!==
'
undefined
'
?
bodyS
ize
:
body
.
length
;
this
.
body
C
hecksum
=
adler32
.
sum
(
Buffer
.
from
(
body
,
'
binary
'
));
this
.
body
_size
=
typeof
body_size
!==
'
undefined
'
?
body_s
ize
:
body
.
length
;
this
.
body
_c
hecksum
=
adler32
.
sum
(
Buffer
.
from
(
body
,
'
binary
'
));
}
this
.
key
=
key
;
...
...
@@ -49,20 +52,18 @@ export default class Message {
}
toString
()
{
let
s
=
'
ACP message:
\n
'
+
'
Body checksum:
'
+
this
.
bodyChecksum
+
'
Body size:
'
+
this
.
bodySize
return
'
ACP message:
\n
'
+
'
Body checksum:
'
+
this
.
body_checksum
+
'
Body size:
'
+
this
.
body_size
+
'
Flags:
'
+
this
.
flags
+
'
Unused:
'
+
this
.
unused
+
'
Command:
'
+
this
.
command
+
'
Error code:
'
+
this
.
error
C
ode
+
'
Error code:
'
+
this
.
error
_c
ode
+
'
Key:
'
+
this
.
key
;
return
s
;
}
static
unpackHeader
(
header_data
)
{
if
(
header_data
.
length
!==
headerSize
)
throw
new
Error
(
'
Header data must be 128 characters
'
);
if
(
header_data
.
length
!==
HEADER_SIZE
)
throw
new
Error
(
'
Header data must be 128 characters
'
);
const
buffer
=
Buffer
.
from
(
header_data
,
'
binary
'
);
...
...
@@ -88,7 +89,7 @@ export default class Message {
buffer
.
write
(
magic
,
0
,
4
);
buffer
.
writeInt32BE
(
version
,
4
);
buffer
.
writeInt32BE
(
header_checksum
,
8
);
buffer
.
write
U
Int32BE
(
header_checksum
,
8
);
buffer
.
writeInt32BE
(
body_checksum
,
12
);
buffer
.
writeInt32BE
(
body_size
,
16
);
buffer
.
writeInt32BE
(
flags
,
20
);
...
...
@@ -99,22 +100,20 @@ export default class Message {
buffer
.
write
(
key
,
48
,
48
+
32
,
'
binary
'
);
buffer
.
write
(
pad2
||
''
.
padEnd
(
48
,
'
\
u0000
'
),
80
,
80
+
48
,
'
binary
'
);
const
packed
=
buffer
.
toString
(
'
binary
'
);
console
.
log
(
'
Packed
'
,
packed
);
return
packed
;
return
buffer
.
toString
(
'
binary
'
);
}
static
async
parseRaw
(
data
)
{
if
(
headerSize
>
data
.
length
)
{
throw
new
Error
(
`
Need to pass at least
${
headerSize
}
bytes
`
);
if
(
HEADER_SIZE
>
data
.
length
)
{
throw
new
Error
(
`
Need to pass at least
${
HEADER_SIZE
}
bytes
`
);
}
const
header_data
=
data
.
substr
(
0
,
headerSize
);
const
body_data
=
data
.
length
>
headerSize
?
data
.
substr
(
headerSize
)
:
undefined
;
const
header_data
=
data
.
substr
(
0
,
HEADER_SIZE
);
const
body_data
=
data
.
length
>
HEADER_SIZE
?
data
.
substr
(
HEADER_SIZE
)
:
undefined
;
const
{
magic
,
version
,
header_checksum
,
body_checksum
,
body_size
,
flags
,
unused
,
command
,
error_code
,
key
,
pad1
,
pad2
}
=
this
.
unpackHeader
(
header_data
);
if
(
magic
!==
headerMagic
)
{
if
(
magic
!==
HEADER_MAGIC
)
{
throw
new
Error
(
'
Bad header magic
'
);
}
...
...
@@ -130,8 +129,8 @@ export default class Message {
pad1
,
pad2
,
});
const
expected
HeaderC
hecksum
=
adler32
.
sum
(
Buffer
.
from
(
tmphdr
,
'
binary
'
));
if
(
header_checksum
!==
expected
HeaderC
hecksum
)
{
const
expected
_header_c
hecksum
=
adler32
.
sum
(
Buffer
.
from
(
tmphdr
,
'
binary
'
));
if
(
header_checksum
!==
expected
_header_c
hecksum
)
{
throw
new
Error
(
'
Header checksum does not match
'
);
}
...
...
@@ -215,8 +214,8 @@ export default class Message {
return
message
.
composeRawPacket
();
}
static
composeMessageEx
(
cls
,
version
,
flags
,
unused
,
command
,
errorCode
,
password
,
payload
,
payloadS
ize
)
{
const
message
=
new
Message
(
version
,
flags
,
unused
,
command
,
error
Code
,
generateACPHeaderKey
(
password
),
payload
,
payloadS
ize
);
static
composeMessageEx
(
version
,
flags
,
unused
,
command
,
error_code
,
password
,
payload
,
payload_s
ize
)
{
const
message
=
new
Message
(
version
,
flags
,
unused
,
command
,
error
_code
,
generateACPHeaderKey
(
password
),
payload
,
payload_s
ize
);
return
message
.
composeRawPacket
();
}
...
...
@@ -230,26 +229,26 @@ export default class Message {
composeHeader
()
{
const
tmphdr
=
this
.
constructor
.
packHeader
({
magic
:
headerMagic
,
version
:
this
.
version
,
header_checksum
:
0
,
body_checksum
:
this
.
body
Checksum
,
body_size
:
this
.
bodyS
ize
,
flags
:
this
.
flags
,
unused
:
this
.
unused
,
command
:
this
.
command
,
error_code
:
this
.
error
C
ode
,
key
:
this
.
key
,
magic
:
HEADER_MAGIC
,
version
:
this
.
version
,
header_checksum
:
0
,
body_checksum
:
this
.
body
_checksum
,
body_size
:
this
.
body_s
ize
,
flags
:
this
.
flags
,
unused
:
this
.
unused
,
command
:
this
.
command
,
error_code
:
this
.
error
_c
ode
,
key
:
this
.
key
,
});
const
header
=
this
.
constructor
.
packHeader
({
magic
:
headerMagic
,
version
:
this
.
version
,
magic
:
HEADER_MAGIC
,
version
:
this
.
version
,
header_checksum
:
adler32
.
sum
(
Buffer
.
from
(
tmphdr
,
'
binary
'
)),
body_checksum
:
this
.
body
Checksum
,
body_size
:
this
.
bodyS
ize
,
flags
:
this
.
flags
,
unused
:
this
.
unused
,
command
:
this
.
command
,
error_code
:
this
.
error
C
ode
,
key
:
this
.
key
,
body_checksum
:
this
.
body
_checksum
,
body_size
:
this
.
body_s
ize
,
flags
:
this
.
flags
,
unused
:
this
.
unused
,
command
:
this
.
command
,
error_code
:
this
.
error
_c
ode
,
key
:
this
.
key
,
});
return
header
;
}
static
get
headerMagic
()
{
return
headerMagic
;
static
get
HEADER_MAGIC
()
{
return
HEADER_MAGIC
;
}
static
get
headerSize
()
{
return
headerSize
;
static
get
HEADER_SIZE
()
{
return
HEADER_SIZE
;
}
}
src/property.js
View file @
aea9d8b8
import
acpProperties
from
'
./properties
'
;
import
CFLBinaryPList
from
'
./cflbinary
'
;
import
acp_properties
from
'
./properties
'
;
export
function
generateACPProperties
()
{
const
props
=
[];
for
(
let
prop
of
acp
P
roperties
)
{
const
[
name
,
type
,
description
,
validat
e
]
=
prop
;
for
(
let
prop
of
acp
_p
roperties
)
{
const
[
name
,
type
,
description
,
validat
or
]
=
prop
;
if
(
name
.
length
!==
4
)
throw
new
Error
(
'
Bad name in ACP properties list:
'
+
name
);
...
...
@@ -14,7 +15,7 @@ export function generateACPProperties() {
if
(
!
description
)
throw
new
Error
(
'
Missing description in ACP properties list for name:
'
+
name
);
props
.
push
({
name
,
type
,
description
,
validat
e
});
props
.
push
({
name
,
type
,
description
,
validat
or
});
}
return
props
;
...
...
@@ -22,7 +23,7 @@ export function generateACPProperties() {
export
const
props
=
generateACPProperties
();
export
const
elementHeaderSize
=
12
;
export
const
HEADER_SIZE
=
12
;
export
default
class
Property
{
constructor
(
name
,
value
)
{
...
...
@@ -36,19 +37,15 @@ export default class Property {
}
if
(
value
)
{
const
prop
T
ype
=
this
.
constructor
.
getPropertyInfoString
(
name
,
'
type
'
);
const
init
HandlerName
=
`
__init_
${
propT
ype
}
`
;
const
prop
_t
ype
=
this
.
constructor
.
getPropertyInfoString
(
name
,
'
type
'
);
const
init
_handler_name
=
`
__init_
${
prop_t
ype
}
`
;
if
(
!
this
[
init
HandlerName
])
throw
new
Error
(
`
Missing handler for
${
propT
ype
}
property type
`
);
if
(
!
this
[
init
_handler_name
])
throw
new
Error
(
`
Missing handler for
${
prop_t
ype
}
property type
`
);
try
{
value
=
this
[
initHandlerName
](
value
);
}
catch
(
err
)
{
throw
new
Error
(
JSON
.
stringify
(
err
,
null
,
4
)
+
'
provided for
'
+
propType
+
'
property type
'
+
value
);
}
value
=
this
[
init_handler_name
](
value
);
const
validat
e
=
this
.
constructor
.
getPropertyInfoString
(
name
,
'
validate
'
);
if
(
validat
e
&&
!
validate
(
valu
e
))
{
const
validat
or
=
this
.
constructor
.
getPropertyInfoString
(
name
,
'
validator
'
);
if
(
validat
or
&&
!
validator
(
value
,
nam
e
))
{
throw
new
Error
(
'
Invalid value passed to validator for property
'
+
name
+
'
- type:
'
+
typeof
value
);
}
}
...
...
@@ -61,7 +58,7 @@ export default class Property {
if
(
typeof
value
===
'
number
'
)
{
return
value
;
}
else
if
(
typeof
value
===
'
string
'
)
{
return
Buffer
.
from
(
value
,
'
binary
'
).
readUInt
32BE
(
0
);
return
Buffer
.
from
(
value
,
'
binary
'
).
readUInt
BE
(
0
,
value
.
length
);
}
else
{
throw
new
Error
(
'
Invalid number value:
'
+
value
);
}
...
...
@@ -144,24 +141,29 @@ export default class Property {
__format_mac
(
value
)
{
const
mac_bytes
=
[];
value
=
Buffer
.
from
(
value
,
'
binary
'
).
toString
(
'
hex
'
);
for
(
let
i
=
0
;
i
<
6
;
i
++
)
{
mac_bytes
.
push
(
value
.
substr
(
i
,
1
));
mac_bytes
.
push
(
value
.
substr
(
i
,
2
));
}
return
implode
(
'
:
'
,
mac_bytes
);
return
mac_bytes
.
join
(
'
:
'
);
}
__format_bin
(
value
)
{
return
value
.
toString
(
);
return
Buffer
.
from
(
value
,
'
binary
'
).
toString
(
'
hex
'
);
}
__format_cfb
(
value
)
{
return
value
.
toString
(
);
return
CFLBinaryPList
.
parse
(
value
);
}
__format_log
(
value
)
{
return
value
.
toString
();
return
value
.
split
(
'
\
x00
'
).
map
(
line
=>
line
.
trim
()
+
'
\n
'
).
join
(
''
);
}
__format_str
(
value
)
{
return
Buffer
.
from
(
value
,
'
binary
'
).
toString
(
'
utf8
'
);
}
toString
()
{
...
...
@@ -192,9 +194,9 @@ export default class Property {
static
async
parseRawElement
(
data
)
{
// eslint-disable-next-line no-unused-vars
const
{
name
,
flags
,
size
}
=
await
this
.
parseRawElementHeader
(
data
.
substr
(
0
,
elementHeaderSize
));
const
{
name
,
flags
,
size
}
=
await
this
.
parseRawElementHeader
(
data
.
substr
(
0
,
HEADER_SIZE
));
// TODO: handle flags
return
new
this
(
name
,
data
.
substr
(
elementHeaderSize
));
return
new
this
(
name
,
data
.
substr
(
HEADER_SIZE
));
}
static
async
parseRawElementHeader
(
data
)
{
...
...
@@ -238,7 +240,7 @@ export default class Property {
}
static
unpackHeader
(
header_data
)
{
if
(
header_data
.
length
!==
elementHeaderSize
)
{
if
(
header_data
.
length
!==
HEADER_SIZE
)
{
throw
new
Error
(
'
Header data must be 12 characters
'
);
}
...
...
src/session.js
View file @
aea9d8b8
// import Encryption from './encryption';
// import {ClientEncryption, ServerEncryption} from './encryption';
import
net
from
'
net
'
;
export
default
class
Session
{
...
...
@@ -12,9 +13,7 @@ export default class Session {
this
.
buffer
=
''
;
this
.
reading
=
0
;
this
.
encryptionContext
=
undefined
;
this
.
encryptionMethod
=
undefined
;
this
.
decryptionMethod
=
undefined
;
this
.
encryption
=
undefined
;
}
connect
(
_timeout
=
10000
)
{
...
...
@@ -48,6 +47,7 @@ export default class Session {
if
(
!
this
.
socket
)
return
;
this
.
socket
.
end
();
return
new
Promise
((
resolve
,
reject
)
=>
{
this
.
socket
.
on
(
'
close
'
,
resolve
);
});
...
...
@@ -56,13 +56,7 @@ export default class Session {
async
sendAndReceive
(
data
,
size
,
timeout
=
10000
)
{
await
this
.
send
(
data
);
data
=
await
this
.
receiveSize
(
size
,
timeout
);
if
(
this
.
decryptionMethod
)
{
data
=
this
.
decryptionMethod
(
data
);
}
return
data
;
return
await
this
.
receive
(
size
,
timeout
);
}
send
(
data
)
{
...
...
@@ -70,8 +64,8 @@ export default class Session {
data
=
Buffer
.
from
(
data
,
'
binary
'
);
}
if
(
this
.
encryption
Method
)
{
data
=
this
.
encryption
Method
(
data
);
if
(
this
.
encryption
)
{
data
=
this
.
encryption
.
encrypt
(
data
);
}
if
(
!
this
.
socket
)
return
;
...
...
@@ -143,28 +137,18 @@ export default class Session {
async
receive
(
size
,
timeout
=
10000
)
{
let
data
=
await
this
.
receiveSize
(
size
,
timeout
);
if
(
this
.
decryptionMethod
)
{
data
=
this
.
decryptionMethod
(
data
);
if
(
this
.
encryption
)
{
data
=
this
.
encryption
.
decrypt
(
data
);
}
return
data
;
}
}
export
class
ClientSession
extends
Session
{
enableEncryption
(
key
,
client_iv
,
server_iv
)
{
this
.
encryptionContext
=
new
Encryption
(
key
,
client_iv
,
server_iv
);
this
.
encryptionMethod
=
this
.
encryptionContext
.
clientEncrypt
;
this
.
decryptionMethod
=
this
.
encryptionContext
.
serverDecrypt
;
this
.
encryption_context
=
new
ClientEncryption
(
key
,
client_iv
,
server_iv
);
}
}
export
class
ServerSession
extends
Session
{
enableEncryption
(
key
,
client_iv
,
server_iv
)
{
this
.
encryptionContext
=
new
Encryption
(
key
,
client_iv
,
server_iv
);
this
.
encryptionMethod
=
this
.
encryptionContext
.
serverEncrypt
;
this
.
decryptionMethod
=
this
.
encryptionContext
.
clientDecrypt
;
enableServerEncryption
(
key
,
client_iv
,
server_iv
)
{
this
.
encryption_context
=
new
ServerEncryption
(
key
,
client_iv
,
server_iv
)
;
}
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment