1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License (the "License").
6  * You may not use this file except in compliance with the License.
7  *
8  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9  * or http://www.opensolaris.org/os/licensing.
10  * See the License for the specific language governing permissions
11  * and limitations under the License.
12  *
13  * When distributing Covered Code, include this CDDL HEADER in each
14  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15  * If applicable, add the following below this CDDL HEADER, with the
16  * fields enclosed by brackets "[]" replaced with your own identifying
17  * information: Portions Copyright [yyyy] [name of copyright owner]
18  *
19  * CDDL HEADER END
20  */
21 
22 /*
23  * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
24  * Copyright 2020 Tintri by DDN, Inc. All rights reserved.
25  */
26 
27 /*
28  * NetLogon RPC (NETR) interface definition. This module provides
29  * the server side NETR RPC interface and the interface registration
30  * function.
31  */
32 
33 #include <strings.h>
34 
35 #include <smbsrv/libsmb.h>
36 #include <smbsrv/libmlsvc.h>
37 #include <smbsrv/ndl/netlogon.ndl>
38 #include <smbsrv/nmpipes.h>
39 #include <smbsrv/netrauth.h>
40 
41 static int netr_s_ServerReqChallenge(void *, ndr_xa_t *);
42 static int netr_s_ServerAuthenticate2(void *, ndr_xa_t *);
43 static int netr_s_ServerPasswordSet(void *, ndr_xa_t *);
44 static int netr_s_SamLogon(void *, ndr_xa_t *);
45 static int netr_s_SamLogoff(void *, ndr_xa_t *);
46 
47 static ndr_stub_table_t netr_stub_table[] = {
48 	{ netr_s_ServerReqChallenge,	NETR_OPNUM_ServerReqChallenge },
49 	{ netr_s_ServerAuthenticate2,	NETR_OPNUM_ServerAuthenticate2 },
50 	{ netr_s_ServerPasswordSet,	NETR_OPNUM_ServerPasswordSet },
51 	{ netr_s_SamLogon,		NETR_OPNUM_SamLogon },
52 	{ netr_s_SamLogoff,		NETR_OPNUM_SamLogoff },
53 	{0}
54 };
55 
56 static ndr_service_t netr_service = {
57 	"NETR",				/* name */
58 	"NetLogon",			/* desc */
59 	"\\netlogon",			/* endpoint */
60 	PIPE_LSASS,			/* sec_addr_port */
61 	"12345678-1234-abcd-ef00-01234567cffb", 1,	/* abstract */
62 	NDR_TRANSFER_SYNTAX_UUID,		2,	/* transfer */
63 	0,				/* no bind_instance_size */
64 	0,				/* no bind_req() */
65 	0,				/* no unbind_and_close() */
66 	0,				/* use generic_call_stub() */
67 	&TYPEINFO(netr_interface),	/* interface ti */
68 	netr_stub_table			/* stub_table */
69 };
70 
71 /*
72  * netr_initialize
73  *
74  * This function registers the NETR RPC interface with the RPC runtime
75  * library. It must be called in order to use either the client side
76  * or the server side functions.
77  */
78 void
netr_initialize(void)79 netr_initialize(void)
80 {
81 	uint32_t flags;
82 
83 	(void) ndr_svc_register(&netr_service);
84 
85 	flags = smb_get_netlogon_flags();
86 	netlogon_init_global(flags);
87 }
88 
89 /*
90  * netr_s_ServerReqChallenge
91  */
92 /*ARGSUSED*/
93 static int
netr_s_ServerReqChallenge(void * arg,ndr_xa_t * mxa)94 netr_s_ServerReqChallenge(void *arg, ndr_xa_t *mxa)
95 {
96 	struct netr_ServerReqChallenge *param = arg;
97 
98 	bzero(param, sizeof (struct netr_ServerReqChallenge));
99 	param->status = NT_SC_ERROR(NT_STATUS_ACCESS_DENIED);
100 	return (NDR_DRC_OK);
101 }
102 
103 /*
104  * netr_s_ServerAuthenticate2
105  */
106 /*ARGSUSED*/
107 static int
netr_s_ServerAuthenticate2(void * arg,ndr_xa_t * mxa)108 netr_s_ServerAuthenticate2(void *arg, ndr_xa_t *mxa)
109 {
110 	struct netr_ServerAuthenticate2 *param = arg;
111 
112 	bzero(param, sizeof (struct netr_ServerAuthenticate2));
113 	param->status = NT_SC_ERROR(NT_STATUS_ACCESS_DENIED);
114 	return (NDR_DRC_OK);
115 }
116 
117 /*
118  * netr_s_ServerPasswordSet
119  */
120 /*ARGSUSED*/
121 static int
netr_s_ServerPasswordSet(void * arg,ndr_xa_t * mxa)122 netr_s_ServerPasswordSet(void *arg, ndr_xa_t *mxa)
123 {
124 	struct netr_PasswordSet *param = arg;
125 
126 	bzero(param, sizeof (struct netr_PasswordSet));
127 	param->status = NT_SC_ERROR(NT_STATUS_ACCESS_DENIED);
128 	return (NDR_DRC_OK);
129 }
130 
131 /*
132  * netr_s_SamLogon
133  */
134 /*ARGSUSED*/
135 static int
netr_s_SamLogon(void * arg,ndr_xa_t * mxa)136 netr_s_SamLogon(void *arg, ndr_xa_t *mxa)
137 {
138 	struct netr_SamLogon *param = arg;
139 
140 	bzero(param, sizeof (struct netr_SamLogon));
141 	param->status = NT_SC_ERROR(NT_STATUS_ACCESS_DENIED);
142 	return (NDR_DRC_OK);
143 }
144 
145 /*
146  * netr_s_SamLogoff
147  */
148 /*ARGSUSED*/
149 static int
netr_s_SamLogoff(void * arg,ndr_xa_t * mxa)150 netr_s_SamLogoff(void *arg, ndr_xa_t *mxa)
151 {
152 	struct netr_SamLogoff *param = arg;
153 
154 	bzero(param, sizeof (struct netr_SamLogoff));
155 	param->status = NT_SC_ERROR(NT_STATUS_ACCESS_DENIED);
156 	return (NDR_DRC_OK);
157 }
158 
159 /*
160  * Declare extern references.
161  */
162 DECL_FIXUP_STRUCT(netr_validation_u);
163 DECL_FIXUP_STRUCT(netr_validation_info);
164 DECL_FIXUP_STRUCT(netr_SamLogon);
165 DECL_FIXUP_STRUCT(netr_SamLogonEx);
166 
167 /*
168  * Patch the netr_validation_info union.
169  */
170 static unsigned short
fixup_netr_validation_info(WORD level)171 fixup_netr_validation_info(WORD level)
172 {
173 	unsigned short size1 = 0;
174 	unsigned short size2 = 0;
175 
176 	switch (level) {
177 	case 3:
178 		/*
179 		 * The netr_validation_u union contains a pointer, which
180 		 * is a DWORD in NDR. So we need to set size1 to ensure
181 		 * that we can correctly decode the remaining parameters.
182 		 */
183 		size1 = sizeof (DWORD);
184 		break;
185 
186 	default:
187 		/*
188 		 * If the request is badly formed or the level is invalid,
189 		 * the server returns NT_STATUS_INVALID_INFO_CLASS. Size1
190 		 * must be zero to correctly decode the status.
191 		 */
192 		size1 = 0;
193 		break;
194 	};
195 
196 	size2 = size1 + (2 * sizeof (DWORD));
197 
198 	FIXUP_PDU_SIZE(netr_validation_u, size1);
199 	FIXUP_PDU_SIZE(netr_validation_info, size2);
200 
201 	return (size2);
202 }
203 
204 
205 /*
206  * Patch the netr_SamLogon union.
207  * This function is called from mlsvc_netr_ndr.c
208  */
209 void
fixup_netr_SamLogon(struct netr_SamLogon * arg)210 fixup_netr_SamLogon(struct netr_SamLogon *arg)
211 {
212 	unsigned short size2 = 0;
213 	unsigned short size3 = 0;
214 
215 	size2 = fixup_netr_validation_info(arg->validation_level);
216 	/* netr_valid ENC-UNION + hdr + ret_auth PTR + authoritative + status */
217 	size3 = size2 + sizeof (ndr_request_hdr_t) + 3 * sizeof (DWORD);
218 	FIXUP_PDU_SIZE(netr_SamLogon, size3);
219 }
220 
221 /*
222  * Patch the netr_SamLogonEx union.
223  * This function is called from mlsvc_netr_ndr.c
224  */
225 void
fixup_netr_SamLogonEx(struct netr_SamLogonEx * arg)226 fixup_netr_SamLogonEx(struct netr_SamLogonEx *arg)
227 {
228 	unsigned short size2 = 0;
229 	unsigned short size3 = 0;
230 
231 	size2 = fixup_netr_validation_info(arg->validation_level);
232 	/* netr_valid ENC-UNION + hdr + authoritative + flags + status */
233 	size3 = size2 + sizeof (ndr_request_hdr_t) + 3 * sizeof (DWORD);
234 
235 	FIXUP_PDU_SIZE(netr_SamLogonEx, size3);
236 }
237