client
import "github.com/TheManticoreProject/Manticore/network/dcerpc/v5/client"
Package client implements the high-level connection-oriented DCE/RPC client: it binds to an interface and issues calls over a transport.
The flow follows [C706] chapter 12 and [MS-RPCE]:
- Bind sends a bind PDU proposing the transport’s max_xmit_frag / max_recv_frag, a single presentation context (the target abstract syntax with the NDR 2.0 transfer syntax), and records the server’s negotiated fragment sizes from the bind_ack.
- Call serializes a request, fragments it so that no fragment exceeds the negotiated send size (PFC_FIRST_FRAG on the first, PFC_LAST_FRAG on the last, both on a single fragment), writes every fragment, then reassembles the response fragments until PFC_LAST_FRAG. A fault PDU is returned as an error.
The call_id is constant across the fragments of one call and is incremented for each new call, as required by [C706] section 12.6.2.
References:
- [C706] chapter 12 (connection-oriented protocol), “Fragmentation and Reassembly”: https://pubs.opengroup.org/onlinepubs/9629399/chap12.htm
- [MS-RPCE] 3.3.1.5.3 Bind Time Feature Negotiation and 2.2.2 PDU definitions: https://learn.microsoft.com/en-us/openspecs/windows_protocols/ms-rpce/87964b3c-1785-4aae-a993-734999441ed3
- [MS-RPCE] 2.1.1.2 SMB (NCACN_NP): https://learn.microsoft.com/en-us/openspecs/windows_protocols/ms-rpce/7063c7bd-b48b-42e7-9154-3c2ec4113c0d
Index
- type Client
- func NewClient(t transport.Transport) *Client
- func (c *Client) Bind(abstractSyntax syntax.SyntaxID) error
- func (c *Client) Call(opnum uint16, stub []byte) ([]byte, error)
- func (c *Client) Close() error
- func (c *Client) Invoke(in ndr.Call, out any) error
- func (c *Client) NegotiatedSyntax() ndr.Syntax
- func (c *Client) PreferNDR64(enable bool)
- func (c *Client) SetAuth(authType, authLevel uint8, creds *credentials.Credentials) error
type Client
Client is a connection-oriented DCE/RPC client bound to a single presentation context on a transport.
type Client struct {
// contains filtered or unexported fields
}
func NewClient
func NewClient(t transport.Transport) *Client
NewClient returns a DCE/RPC client over the supplied transport. The transport must be ready to Connect (for ncacn_np, its SMB session and IPC$ tree connect are already established).
func (*Client) Bind
func (c *Client) Bind(abstractSyntax syntax.SyntaxID) error
Bind connects the transport and binds to the interface identified by abstractSyntax. It proposes the NDR 2.0 transfer syntax in presentation context 0, and — when PreferNDR64 is enabled — NDR64 in a second context (the established negotiation pattern: one transfer syntax per context, [MS-RPCE] 2.2.2.4). The transfer syntax the server accepts is recorded for subsequent calls, preferring NDR64 when both are accepted. It returns an error if the server rejects the bind (bind_nak) or accepts no context.
func (*Client) Call
func (c *Client) Call(opnum uint16, stub []byte) ([]byte, error)
Call invokes the method identified by opnum, sending stub as its marshalled arguments and returning the marshalled results. A fault PDU is returned as a *pdu.Fault error.
func (*Client) Close
func (c *Client) Close() error
Close closes the underlying transport.
func (*Client) Invoke
func (c *Client) Invoke(in ndr.Call, out any) error
Invoke is the declarative counterpart to Call: it marshals the NDR request structure in (whose Opnum selects the method and whose exported fields are the [in] parameters), issues the call, and unmarshals the response into out (a pointer to the [out] parameter structure). out may be nil when the response carries no data. A fault PDU is returned as a *pdu.Fault error, as with Call.
func (*Client) NegotiatedSyntax
func (c *Client) NegotiatedSyntax() ndr.Syntax
NegotiatedSyntax reports the transfer syntax the server accepted at Bind. It is meaningful only after a successful Bind.
func (*Client) PreferNDR64
func (c *Client) PreferNDR64(enable bool)
PreferNDR64 controls whether Bind proposes the NDR64 transfer syntax in addition to NDR 2.0 and uses it when the server accepts it. It must be called before Bind. The default is false (NDR 2.0 only).
func (*Client) SetAuth
func (c *Client) SetAuth(authType, authLevel uint8, creds *credentials.Credentials) error
SetAuth enables RPC-level authentication for subsequent binds. authType selects the security provider (only NTLM, pdu.AuthTypeNTLMSSP, is supported) and authLevel the protection applied to each PDU: pdu.AuthLevelConnect authenticates the bind only; pdu.AuthLevelCall and pdu.AuthLevelPkt attach a per-PDU authenticity verifier; pdu.AuthLevelPktIntegrity additionally signs the request data; and pdu.AuthLevelPktPrivacy signs and seals it. creds may carry a cleartext password or, for pass-the-hash, an NT hash with no password. It must be called before Bind.
AuthLevelCall is promoted to AuthLevelPkt: it has no distinct meaning for the connection-oriented protocol, where the runtime uses packet-level protection instead ([MS-RPCE] 2.2.1.1.8).