xref: /onnv-gate/usr/src/lib/smbsrv/libsmb/common/smb_door_encdec.c (revision 12508:edb7861a1533)
15331Samw /*
25331Samw  * CDDL HEADER START
35331Samw  *
45331Samw  * The contents of this file are subject to the terms of the
55331Samw  * Common Development and Distribution License (the "License").
65331Samw  * You may not use this file except in compliance with the License.
75331Samw  *
85331Samw  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
95331Samw  * or http://www.opensolaris.org/os/licensing.
105331Samw  * See the License for the specific language governing permissions
115331Samw  * and limitations under the License.
125331Samw  *
135331Samw  * When distributing Covered Code, include this CDDL HEADER in each
145331Samw  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
155331Samw  * If applicable, add the following below this CDDL HEADER, with the
165331Samw  * fields enclosed by brackets "[]" replaced with your own identifying
175331Samw  * information: Portions Copyright [yyyy] [name of copyright owner]
185331Samw  *
195331Samw  * CDDL HEADER END
205331Samw  */
215331Samw /*
22*12508Samw@Sun.COM  * Copyright (c) 2007, 2010, Oracle and/or its affiliates. All rights reserved.
235331Samw  */
245331Samw 
255331Samw #include <stdlib.h>
265331Samw #include <strings.h>
275331Samw #include <rpc/xdr.h>
285331Samw #include <errno.h>
2911963SAfshin.Ardakani@Sun.COM #include <syslog.h>
305331Samw #include <smbsrv/libsmb.h>
315331Samw #include <smbsrv/smb_xdr.h>
3211963SAfshin.Ardakani@Sun.COM #include <smbsrv/smb_door.h>
3311963SAfshin.Ardakani@Sun.COM 
345331Samw 
355331Samw /*
3611963SAfshin.Ardakani@Sun.COM  * Generic XDR encoder.
375331Samw  *
3811963SAfshin.Ardakani@Sun.COM  * Returns a malloc'd, encoded buffer upon success.
3911963SAfshin.Ardakani@Sun.COM  * Otherwise, returns NULL.
4011963SAfshin.Ardakani@Sun.COM  */
4111963SAfshin.Ardakani@Sun.COM char *
smb_common_encode(void * data,xdrproc_t proc,size_t * rsize)4211963SAfshin.Ardakani@Sun.COM smb_common_encode(void *data, xdrproc_t proc, size_t *rsize)
4311963SAfshin.Ardakani@Sun.COM {
4411963SAfshin.Ardakani@Sun.COM 	XDR	xdrs;
4511963SAfshin.Ardakani@Sun.COM 	char	*buf;
4611963SAfshin.Ardakani@Sun.COM 	size_t	len;
4711963SAfshin.Ardakani@Sun.COM 
4811963SAfshin.Ardakani@Sun.COM 	if (proc == NULL || data == NULL || rsize == NULL) {
4911963SAfshin.Ardakani@Sun.COM 		syslog(LOG_ERR, "smb_common_encode: invalid parameter");
5011963SAfshin.Ardakani@Sun.COM 		return (NULL);
5111963SAfshin.Ardakani@Sun.COM 	}
5211963SAfshin.Ardakani@Sun.COM 
5311963SAfshin.Ardakani@Sun.COM 	len = xdr_sizeof(proc, data);
5411963SAfshin.Ardakani@Sun.COM 
5511963SAfshin.Ardakani@Sun.COM 	if ((buf = malloc(len)) == NULL) {
5611963SAfshin.Ardakani@Sun.COM 		syslog(LOG_ERR, "smb_common_encode: %m");
5711963SAfshin.Ardakani@Sun.COM 		*rsize = 0;
5811963SAfshin.Ardakani@Sun.COM 		return (NULL);
5911963SAfshin.Ardakani@Sun.COM 	}
6011963SAfshin.Ardakani@Sun.COM 
6111963SAfshin.Ardakani@Sun.COM 	xdrmem_create(&xdrs, buf, len, XDR_ENCODE);
6211963SAfshin.Ardakani@Sun.COM 	*rsize = len;
6311963SAfshin.Ardakani@Sun.COM 
6411963SAfshin.Ardakani@Sun.COM 	if (!proc(&xdrs, data)) {
6511963SAfshin.Ardakani@Sun.COM 		syslog(LOG_DEBUG, "smb_common_encode: encode error");
6611963SAfshin.Ardakani@Sun.COM 		free(buf);
6711963SAfshin.Ardakani@Sun.COM 		buf = NULL;
6811963SAfshin.Ardakani@Sun.COM 		*rsize = 0;
6911963SAfshin.Ardakani@Sun.COM 	}
7011963SAfshin.Ardakani@Sun.COM 
7111963SAfshin.Ardakani@Sun.COM 	xdr_destroy(&xdrs);
7211963SAfshin.Ardakani@Sun.COM 	return (buf);
7311963SAfshin.Ardakani@Sun.COM }
7411963SAfshin.Ardakani@Sun.COM 
7511963SAfshin.Ardakani@Sun.COM /*
7611963SAfshin.Ardakani@Sun.COM  * Generic XDR decoder.  Ensure that data is non-null and bzero'd.
775331Samw  */
785331Samw int
smb_common_decode(char * buf,size_t len,xdrproc_t proc,void * data)7911963SAfshin.Ardakani@Sun.COM smb_common_decode(char *buf, size_t len, xdrproc_t proc, void *data)
805331Samw {
815331Samw 	XDR xdrs;
825331Samw 	int rc = 0;
835331Samw 
8411963SAfshin.Ardakani@Sun.COM 	if (data == NULL)
855331Samw 		return (-1);
865331Samw 
875331Samw 	xdrmem_create(&xdrs, buf, len, XDR_DECODE);
887588Samw@Sun.COM 	if (!proc(&xdrs, data))
895331Samw 		rc = -1;
907588Samw@Sun.COM 
915331Samw 	xdr_destroy(&xdrs);
925331Samw 	return (rc);
935331Samw }
945331Samw 
955331Samw char *
smb_string_encode(char * s,size_t * rsize)9611963SAfshin.Ardakani@Sun.COM smb_string_encode(char *s, size_t *rsize)
975331Samw {
9811963SAfshin.Ardakani@Sun.COM 	smb_string_t	obj;
9911963SAfshin.Ardakani@Sun.COM 	XDR		xdrs;
10011963SAfshin.Ardakani@Sun.COM 	char		*buf = NULL;
10111963SAfshin.Ardakani@Sun.COM 	size_t		len;
10211963SAfshin.Ardakani@Sun.COM 
10311963SAfshin.Ardakani@Sun.COM 	if ((obj.buf = s) == NULL) {
10411963SAfshin.Ardakani@Sun.COM 		syslog(LOG_DEBUG, "smb_string_encode: invalid param");
10511963SAfshin.Ardakani@Sun.COM 		goto smb_string_encode_failed;
10611963SAfshin.Ardakani@Sun.COM 	}
10711963SAfshin.Ardakani@Sun.COM 
10811963SAfshin.Ardakani@Sun.COM 	len = xdr_sizeof(smb_string_xdr, &obj);
10911963SAfshin.Ardakani@Sun.COM 	if ((buf = calloc(len, 1)) == NULL) {
11011963SAfshin.Ardakani@Sun.COM 		syslog(LOG_DEBUG, "smb_string_encode: %m");
11111963SAfshin.Ardakani@Sun.COM 		goto smb_string_encode_failed;
11211963SAfshin.Ardakani@Sun.COM 	}
1135331Samw 
11411963SAfshin.Ardakani@Sun.COM 	xdrmem_create(&xdrs, buf, len, XDR_ENCODE);
11511963SAfshin.Ardakani@Sun.COM 
11611963SAfshin.Ardakani@Sun.COM 	if (!smb_string_xdr(&xdrs, &obj)) {
11711963SAfshin.Ardakani@Sun.COM 		syslog(LOG_DEBUG, "smb_string_encode: encode failed");
11811963SAfshin.Ardakani@Sun.COM 		xdr_destroy(&xdrs);
11911963SAfshin.Ardakani@Sun.COM 		free(buf);
12011963SAfshin.Ardakani@Sun.COM 		goto smb_string_encode_failed;
12111963SAfshin.Ardakani@Sun.COM 	}
1225331Samw 
12311963SAfshin.Ardakani@Sun.COM 	xdr_destroy(&xdrs);
12411963SAfshin.Ardakani@Sun.COM 	if (rsize)
12511963SAfshin.Ardakani@Sun.COM 		*rsize = len;
1265331Samw 	return (buf);
12711963SAfshin.Ardakani@Sun.COM 
12811963SAfshin.Ardakani@Sun.COM smb_string_encode_failed:
12911963SAfshin.Ardakani@Sun.COM 	if (rsize)
13011963SAfshin.Ardakani@Sun.COM 		*rsize = 0;
13111963SAfshin.Ardakani@Sun.COM 	return (NULL);
1325331Samw }
1335331Samw 
13411963SAfshin.Ardakani@Sun.COM int
smb_string_decode(smb_string_t * obj,char * buf,size_t buflen)13511963SAfshin.Ardakani@Sun.COM smb_string_decode(smb_string_t *obj, char *buf, size_t buflen)
1365331Samw {
13711963SAfshin.Ardakani@Sun.COM 	XDR xdrs;
13811963SAfshin.Ardakani@Sun.COM 	int rc = 0;
1395331Samw 
14011963SAfshin.Ardakani@Sun.COM 	xdrmem_create(&xdrs, (const caddr_t)buf, buflen, XDR_DECODE);
1415331Samw 
14211963SAfshin.Ardakani@Sun.COM 	bzero(obj, sizeof (smb_string_t));
14311963SAfshin.Ardakani@Sun.COM 	if (!smb_string_xdr(&xdrs, obj))
14411963SAfshin.Ardakani@Sun.COM 		rc = -1;
14511963SAfshin.Ardakani@Sun.COM 
14611963SAfshin.Ardakani@Sun.COM 	xdr_destroy(&xdrs);
14711963SAfshin.Ardakani@Sun.COM 	return (rc);
1485331Samw }
14911337SWilliam.Krier@Sun.COM 
15011337SWilliam.Krier@Sun.COM /*
15111337SWilliam.Krier@Sun.COM  * Encode an lsa_account_t into a buffer.
15211337SWilliam.Krier@Sun.COM  */
15311337SWilliam.Krier@Sun.COM int
lsa_account_encode(lsa_account_t * acct,uint8_t * buf,uint32_t buflen)15411337SWilliam.Krier@Sun.COM lsa_account_encode(lsa_account_t *acct, uint8_t *buf, uint32_t buflen)
15511337SWilliam.Krier@Sun.COM {
15611337SWilliam.Krier@Sun.COM 	XDR xdrs;
15711337SWilliam.Krier@Sun.COM 	int rc = 0;
15811337SWilliam.Krier@Sun.COM 
15911337SWilliam.Krier@Sun.COM 	xdrmem_create(&xdrs, (const caddr_t)buf, buflen, XDR_ENCODE);
16011337SWilliam.Krier@Sun.COM 
16111337SWilliam.Krier@Sun.COM 	if (!lsa_account_xdr(&xdrs, acct))
16211337SWilliam.Krier@Sun.COM 		rc = -1;
16311337SWilliam.Krier@Sun.COM 
16411337SWilliam.Krier@Sun.COM 	xdr_destroy(&xdrs);
16511337SWilliam.Krier@Sun.COM 	return (rc);
16611337SWilliam.Krier@Sun.COM }
16711337SWilliam.Krier@Sun.COM 
16811337SWilliam.Krier@Sun.COM /*
16911337SWilliam.Krier@Sun.COM  * Decode an XDR buffer into an lsa_account_t.
17011337SWilliam.Krier@Sun.COM  */
17111337SWilliam.Krier@Sun.COM int
lsa_account_decode(lsa_account_t * acct,uint8_t * buf,uint32_t buflen)17211337SWilliam.Krier@Sun.COM lsa_account_decode(lsa_account_t *acct, uint8_t *buf, uint32_t buflen)
17311337SWilliam.Krier@Sun.COM {
17411337SWilliam.Krier@Sun.COM 	XDR xdrs;
17511337SWilliam.Krier@Sun.COM 	int rc = 0;
17611337SWilliam.Krier@Sun.COM 
17711337SWilliam.Krier@Sun.COM 	xdrmem_create(&xdrs, (const caddr_t)buf, buflen, XDR_DECODE);
17811337SWilliam.Krier@Sun.COM 
17911337SWilliam.Krier@Sun.COM 	bzero(acct, sizeof (lsa_account_t));
18011337SWilliam.Krier@Sun.COM 	if (!lsa_account_xdr(&xdrs, acct))
18111337SWilliam.Krier@Sun.COM 		rc = -1;
18211337SWilliam.Krier@Sun.COM 
18311337SWilliam.Krier@Sun.COM 	xdr_destroy(&xdrs);
18411337SWilliam.Krier@Sun.COM 	return (rc);
18511337SWilliam.Krier@Sun.COM }
18611337SWilliam.Krier@Sun.COM 
18711337SWilliam.Krier@Sun.COM bool_t
lsa_account_xdr(XDR * xdrs,lsa_account_t * objp)18811337SWilliam.Krier@Sun.COM lsa_account_xdr(XDR *xdrs, lsa_account_t *objp)
18911337SWilliam.Krier@Sun.COM {
19011337SWilliam.Krier@Sun.COM 	if (!xdr_uint16_t(xdrs, &objp->a_sidtype))
19111337SWilliam.Krier@Sun.COM 		return (FALSE);
19211337SWilliam.Krier@Sun.COM 	if (!xdr_uint32_t(xdrs, &objp->a_status))
19311337SWilliam.Krier@Sun.COM 		return (FALSE);
19411337SWilliam.Krier@Sun.COM 	if (!xdr_vector(xdrs, (char *)objp->a_domain, MAXNAMELEN,
19511337SWilliam.Krier@Sun.COM 	    sizeof (char), (xdrproc_t)xdr_char))
19611337SWilliam.Krier@Sun.COM 		return (FALSE);
19711337SWilliam.Krier@Sun.COM 	if (!xdr_vector(xdrs, (char *)objp->a_name, MAXNAMELEN,
19811337SWilliam.Krier@Sun.COM 	    sizeof (char), (xdrproc_t)xdr_char))
19911337SWilliam.Krier@Sun.COM 		return (FALSE);
20011337SWilliam.Krier@Sun.COM 	if (!xdr_vector(xdrs, (char *)objp->a_sid, SMB_SID_STRSZ,
20111337SWilliam.Krier@Sun.COM 	    sizeof (char), (xdrproc_t)xdr_char))
20211337SWilliam.Krier@Sun.COM 		return (FALSE);
20311337SWilliam.Krier@Sun.COM 	return (TRUE);
20411337SWilliam.Krier@Sun.COM }
205