summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLuke Leighton <lkcl@samba.org>1998-10-15 05:47:29 +0000
committerLuke Leighton <lkcl@samba.org>1998-10-15 05:47:29 +0000
commita42afcdcc7ab9aa9ed193ae36d3dbb10843447f0 (patch)
treed5f55708810d375cb906e8deea7dd21e522be07f
parentba22030ed7e81749116191bce26e948ebf35e2cb (diff)
downloadsamba-a42afcdcc7ab9aa9ed193ae36d3dbb10843447f0.tar.gz
samba-a42afcdcc7ab9aa9ed193ae36d3dbb10843447f0.tar.bz2
samba-a42afcdcc7ab9aa9ed193ae36d3dbb10843447f0.zip
bug-fixing against:
AS/U: it returns dce/rpc "first" and "last" bits _clear_ in a bind/ack response, when they should be set in a (small) packet. they also, in the bind/ack do not set a secondary address string at all, so we can't check against that... Win95: client-side dce/rpc code is a bit odd. it does a "WaitNamedPipeState" and has slightly different pipe-naming (\PIPE\LANMAN is joined by \PIPE\SRVSVC, \PIPE\WINREG etc whereas nt just has \PIPE\LANMAN and \PIPE\). Win95-USRMGR.EXE: added LsaOpenPolicy (renamed existing to LsaOpenPolicy2). added SamrConnect (renamed existing to SamrConnect2). (This used to be commit a7fccd807b938cbb51002ebae8c7a48b40dbb655)
-rw-r--r--source3/include/client.h2
-rw-r--r--source3/include/ntdomain.h1
-rw-r--r--source3/include/proto.h15
-rw-r--r--source3/include/rpc_lsa.h28
-rw-r--r--source3/include/rpc_samr.h28
-rw-r--r--source3/lsarpcd/srv_lsa.c42
-rw-r--r--source3/passdb/smbpass.c2
-rw-r--r--source3/rpc_client/cli_pipe.c26
-rw-r--r--source3/rpc_client/cli_samr.c3
-rw-r--r--source3/rpc_parse/parse_lsa.c67
-rw-r--r--source3/rpc_parse/parse_samr.c73
-rw-r--r--source3/rpc_server/srv_lsa.c42
-rw-r--r--source3/rpc_server/srv_pipe_hnd.c24
-rw-r--r--source3/rpc_server/srv_samr.c115
-rw-r--r--source3/smbd/ipc.c41
15 files changed, 454 insertions, 55 deletions
diff --git a/source3/include/client.h b/source3/include/client.h
index 53674fe80a..a393ee25a8 100644
--- a/source3/include/client.h
+++ b/source3/include/client.h
@@ -126,6 +126,8 @@ struct cli_state {
fstring mach_acct; /* MYNAME$. */
fstring srv_name_slash; /* \\remote server. */
fstring clnt_name_slash; /* \\local client. */
+ uint16 max_xmit_frag;
+ uint16 max_recv_frag;
};
#endif /* _CLIENT_H */
diff --git a/source3/include/ntdomain.h b/source3/include/ntdomain.h
index c2a4170595..e540bd2ffc 100644
--- a/source3/include/ntdomain.h
+++ b/source3/include/ntdomain.h
@@ -61,6 +61,7 @@ typedef struct pipes_struct
uint16 vuid;
BOOL open; /* open connection */
uint16 device_state;
+ uint16 priority;
fstring name;
fstring pipe_srv_name;
diff --git a/source3/include/proto.h b/source3/include/proto.h
index 5e47faf5ef..411f923ba8 100644
--- a/source3/include/proto.h
+++ b/source3/include/proto.h
@@ -1339,12 +1339,18 @@ void make_lsa_trans_name(LSA_TRANS_NAME *trn, uint32 sid_name_use, char *name, u
void make_lsa_sec_qos(LSA_SEC_QOS *qos, uint16 imp_lev, uint8 ctxt, uint8 eff,
uint32 unknown);
void make_lsa_obj_attr(LSA_OBJ_ATTR *attr, uint32 attributes, LSA_SEC_QOS *qos);
-void make_q_open_pol(LSA_Q_OPEN_POL *r_q, char *server_name,
+void make_q_open_pol(LSA_Q_OPEN_POL *r_q, uint16 system_name,
uint32 attributes,
uint32 desired_access,
LSA_SEC_QOS *qos);
void lsa_io_q_open_pol(char *desc, LSA_Q_OPEN_POL *r_q, prs_struct *ps, int depth);
void lsa_io_r_open_pol(char *desc, LSA_R_OPEN_POL *r_p, prs_struct *ps, int depth);
+void make_q_open_pol2(LSA_Q_OPEN_POL2 *r_q, char *server_name,
+ uint32 attributes,
+ uint32 desired_access,
+ LSA_SEC_QOS *qos);
+void lsa_io_q_open_pol2(char *desc, LSA_Q_OPEN_POL2 *r_q, prs_struct *ps, int depth);
+void lsa_io_r_open_pol2(char *desc, LSA_R_OPEN_POL2 *r_p, prs_struct *ps, int depth);
void make_q_query(LSA_Q_QUERY_INFO *q_q, POLICY_HND *hnd, uint16 info_class);
void lsa_io_q_query(char *desc, LSA_Q_QUERY_INFO *q_q, prs_struct *ps, int depth);
void lsa_io_q_enum_trust_dom(char *desc, LSA_Q_ENUM_TRUST_DOM *q_e, prs_struct *ps, int depth);
@@ -1710,6 +1716,9 @@ void make_samr_q_connect(SAMR_Q_CONNECT *q_u,
char *srv_name, uint32 unknown_0);
void samr_io_q_connect(char *desc, SAMR_Q_CONNECT *q_u, prs_struct *ps, int depth);
void samr_io_r_connect(char *desc, SAMR_R_CONNECT *r_u, prs_struct *ps, int depth);
+void make_samr_q_connect_anon(SAMR_Q_CONNECT_ANON *q_u);
+void samr_io_q_connect_anon(char *desc, SAMR_Q_CONNECT_ANON *q_u, prs_struct *ps, int depth);
+void samr_io_r_connect_anon(char *desc, SAMR_R_CONNECT_ANON *r_u, prs_struct *ps, int depth);
void make_samr_q_open_alias(SAMR_Q_OPEN_ALIAS *q_u,
uint32 unknown_0, uint32 rid);
void samr_io_q_open_alias(char *desc, SAMR_Q_OPEN_ALIAS *q_u, prs_struct *ps, int depth);
@@ -1723,8 +1732,7 @@ void make_samr_q_unknown_13(SAMR_Q_UNKNOWN_13 *q_c,
POLICY_HND *hnd, uint16 unk_1, uint16 unk_2);
void make_samr_q_unknown_38(SAMR_Q_UNKNOWN_38 *q_u, char *srv_name);
void samr_io_q_unknown_38(char *desc, SAMR_Q_UNKNOWN_38 *q_u, prs_struct *ps, int depth);
-void make_samr_r_unknown_38(SAMR_R_UNKNOWN_38 *r_u,
- uint16 level, uint32 status);
+void make_samr_r_unknown_38(SAMR_R_UNKNOWN_38 *r_u);
void samr_io_r_unknown_38(char *desc, SAMR_R_UNKNOWN_38 *r_u, prs_struct *ps, int depth);
void make_enc_passwd(SAMR_ENC_PASSWD *pwd, char pass[512]);
void samr_io_enc_passwd(char *desc, SAMR_ENC_PASSWD *pwd, prs_struct *ps, int depth);
@@ -1860,6 +1868,7 @@ pipes_struct *open_rpc_pipe_p(char *pipe_name,
connection_struct *conn, uint16 vuid);
int write_pipe(pipes_struct *p, char *data, int n);
int read_pipe(pipes_struct *p, char *data, uint32 pos, int n);
+BOOL wait_rpc_pipe_hnd_state(pipes_struct *p, uint16 priority);
BOOL set_rpc_pipe_hnd_state(pipes_struct *p, uint16 device_state);
BOOL close_rpc_pipe_hnd(pipes_struct *p, connection_struct *conn);
pipes_struct *get_rpc_pipe_p(char *buf, int where);
diff --git a/source3/include/rpc_lsa.h b/source3/include/rpc_lsa.h
index fe4d018dbb..44758936ae 100644
--- a/source3/include/rpc_lsa.h
+++ b/source3/include/rpc_lsa.h
@@ -39,7 +39,8 @@ enum SID_NAME_USE
#define LSA_ENUMTRUSTDOM 0x0d
#define LSA_LOOKUPNAMES 0x0e
#define LSA_LOOKUPSIDS 0x0f
-#define LSA_OPENPOLICY 0x2c
+#define LSA_OPENPOLICY 0x06
+#define LSA_OPENPOLICY2 0x2c
#define LSA_OPENSECRET 0x1C
/* XXXX these are here to get a compile! */
@@ -89,9 +90,9 @@ typedef struct obj_attr_info
/* LSA_Q_OPEN_POL - LSA Query Open Policy */
typedef struct lsa_q_open_pol_info
{
- uint32 ptr; /* undocumented buffer pointer */
- UNISTR2 uni_server_name; /* server name, starting with two '\'s */
- LSA_OBJ_ATTR attr ; /* object attributes */
+ uint32 ptr; /* undocumented buffer pointer */
+ uint16 system_name; /* 0x5c - system name */
+ LSA_OBJ_ATTR attr ; /* object attributes */
uint32 des_access; /* desired access attributes */
@@ -105,6 +106,25 @@ typedef struct lsa_r_open_pol_info
} LSA_R_OPEN_POL;
+/* LSA_Q_OPEN_POL2 - LSA Query Open Policy */
+typedef struct lsa_q_open_pol2_info
+{
+ uint32 ptr; /* undocumented buffer pointer */
+ UNISTR2 uni_server_name; /* server name, starting with two '\'s */
+ LSA_OBJ_ATTR attr ; /* object attributes */
+
+ uint32 des_access; /* desired access attributes */
+
+} LSA_Q_OPEN_POL2;
+
+/* LSA_R_OPEN_POL2 - response to LSA Open Policy */
+typedef struct lsa_r_open_pol2_info
+{
+ POLICY_HND pol; /* policy handle */
+ uint32 status; /* return code */
+
+} LSA_R_OPEN_POL2;
+
/* LSA_Q_QUERY_INFO - LSA query info policy */
typedef struct lsa_query_info
{
diff --git a/source3/include/rpc_samr.h b/source3/include/rpc_samr.h
index f27dc66381..baae9a3bd9 100644
--- a/source3/include/rpc_samr.h
+++ b/source3/include/rpc_samr.h
@@ -94,6 +94,7 @@ SamrTestPrivateFunctionsUser
#define SAMR_CHGPASSWD_USER 0x37
#define SAMR_UNKNOWN_38 0x38
#define SAMR_CONNECT 0x39
+#define SAMR_CONNECT_ANON 0x00
#define SAMR_OPEN_ALIAS 0x1b
#define SAMR_QUERY_ALIASINFO 0x1c
#define SAMR_ENUM_DOM_USERS 0x0d
@@ -934,12 +935,30 @@ typedef struct q_samr_open_alias_info
/* SAMR_R_OPEN_ALIAS - probably an open */
typedef struct r_samr_open_alias_info
{
- POLICY_HND pol; /* policy handle */
+ POLICY_HND pol; /* policy handle */
uint32 status; /* return status */
} SAMR_R_OPEN_ALIAS;
+/* SAMR_Q_CONNECT_ANON - probably an open */
+typedef struct q_samr_connect_anon_info
+{
+ uint32 ptr; /* ptr? */
+ uint16 unknown_0; /* 0x005c */
+ uint16 unknown_1; /* 0x0001 */
+ uint32 unknown_2; /* 0x0000 0020 */
+
+} SAMR_Q_CONNECT_ANON;
+
+/* SAMR_R_CONNECT_ANON - probably an open */
+typedef struct r_samr_connect_anon_info
+{
+ POLICY_HND connect_pol; /* policy handle */
+ uint32 status; /* return status */
+
+} SAMR_R_CONNECT_ANON;
+
/* SAMR_Q_CONNECT - probably an open */
typedef struct q_samr_connect_info
{
@@ -971,9 +990,10 @@ typedef struct q_samr_unknown_38
/* SAMR_R_UNKNOWN_38 */
typedef struct r_samr_unknown_38
{
- LOOKUP_LEVEL level; /* 0x0006 */
- uint32 ptr_0; /* 0x0000 0000 */
- uint32 status;
+ uint16 unk_0;
+ uint16 unk_1;
+ uint16 unk_2;
+ uint16 unk_3;
} SAMR_R_UNKNOWN_38;
diff --git a/source3/lsarpcd/srv_lsa.c b/source3/lsarpcd/srv_lsa.c
index 2e5ebc9e68..93584b5acf 100644
--- a/source3/lsarpcd/srv_lsa.c
+++ b/source3/lsarpcd/srv_lsa.c
@@ -31,6 +31,28 @@ extern int DEBUGLEVEL;
extern DOM_SID global_machine_sid;
/***************************************************************************
+lsa_reply_open_policy2
+ ***************************************************************************/
+static void lsa_reply_open_policy2(prs_struct *rdata)
+{
+ int i;
+ LSA_R_OPEN_POL2 r_o;
+
+ ZERO_STRUCT(r_o);
+
+ /* set up the LSA QUERY INFO response */
+
+ for (i = 4; i < POL_HND_SIZE; i++)
+ {
+ r_o.pol.data[i] = i;
+ }
+ r_o.status = 0x0;
+
+ /* store the response in the SMB stream */
+ lsa_io_r_open_pol2("", &r_o, rdata, 0);
+}
+
+/***************************************************************************
lsa_reply_open_policy
***************************************************************************/
static void lsa_reply_open_policy(prs_struct *rdata)
@@ -282,6 +304,25 @@ static void lsa_reply_lookup_rids(prs_struct *rdata,
/***************************************************************************
api_lsa_open_policy
***************************************************************************/
+static void api_lsa_open_policy2( uint16 vuid, prs_struct *data,
+ prs_struct *rdata )
+{
+ LSA_Q_OPEN_POL2 q_o;
+
+ ZERO_STRUCT(q_o);
+
+ /* grab the server, object attributes and desired access flag...*/
+ lsa_io_q_open_pol2("", &q_o, data, 0);
+
+ /* lkclXXXX having decoded it, ignore all fields in the open policy! */
+
+ /* return a 20 byte policy handle */
+ lsa_reply_open_policy2(rdata);
+}
+
+/***************************************************************************
+api_lsa_open_policy
+ ***************************************************************************/
static void api_lsa_open_policy( uint16 vuid, prs_struct *data,
prs_struct *rdata )
{
@@ -513,6 +554,7 @@ static void api_lsa_open_secret( uint16 vuid, prs_struct *data,
***************************************************************************/
static struct api_struct api_lsa_cmds[] =
{
+ { "LSA_OPENPOLICY2" , LSA_OPENPOLICY2 , api_lsa_open_policy2 },
{ "LSA_OPENPOLICY" , LSA_OPENPOLICY , api_lsa_open_policy },
{ "LSA_QUERYINFOPOLICY" , LSA_QUERYINFOPOLICY , api_lsa_query_info },
{ "LSA_ENUMTRUSTDOM" , LSA_ENUMTRUSTDOM , api_lsa_enum_trust_dom },
diff --git a/source3/passdb/smbpass.c b/source3/passdb/smbpass.c
index 35de214425..085ece0f5e 100644
--- a/source3/passdb/smbpass.c
+++ b/source3/passdb/smbpass.c
@@ -323,6 +323,8 @@ static struct sam_passwd *getsmbfile21pwent(void *vp)
static pstring acct_desc;
static pstring workstations;
+ DEBUG(5,("getsmbfile21pwent\n"));
+
if (pw_buf == NULL) return NULL;
pwfile = getpwnam(pw_buf->smb_name);
diff --git a/source3/rpc_client/cli_pipe.c b/source3/rpc_client/cli_pipe.c
index 405b6abe66..4ea38fa828 100644
--- a/source3/rpc_client/cli_pipe.c
+++ b/source3/rpc_client/cli_pipe.c
@@ -51,7 +51,7 @@ static BOOL rpc_read(struct cli_state *cli,
prs_struct *rdata, uint32 data_to_read,
uint32 rdata_offset)
{
- int size = 0x1630;
+ int size = cli->max_recv_frag;
int file_offset = rdata_offset;
int num_read;
char *data = rdata->data->data;
@@ -249,6 +249,8 @@ static BOOL rpc_api_pipe(struct cli_state *cli, uint16 cmd,
setup[0] = cmd;
setup[1] = cli->nt_pipe_fnum; /* pipe file handle. got this from an SMBOpenX. */
+ DEBUG(5,("rpc_api_pipe: cmd:%x fnum:%x\n", cmd, cli->nt_pipe_fnum));
+
/* send the data: receive a response. */
if (!cli_api_pipe(cli, "\\PIPE\\\0\0\0", 8,
setup, 2, 0, /* Setup, length, max */
@@ -278,6 +280,16 @@ static BOOL rpc_api_pipe(struct cli_state *cli, uint16 cmd,
return False;
}
+ if (rhdr.pkt_type == RPC_BINDACK)
+ {
+ if (!last && !first)
+ {
+ DEBUG(5,("rpc_api_pipe: bug in AS/U, setting fragment first/last ON\n"));
+ first = True;
+ last = True;
+ }
+ }
+
if (rhdr.pkt_type == RPC_RESPONSE)
{
RPC_HDR_RESP rhdr_resp;
@@ -731,7 +743,7 @@ static BOOL check_bind_response(RPC_HDR_BA *hdr_ba, char *pipe_name, RPC_IFACE *
{
int i = 0;
- while ((pipe_names[i].client_pipe != NULL))
+ while ((pipe_names[i].client_pipe != NULL) && hdr_ba->addr.len > 0)
{
DEBUG(6,("bind_rpc_pipe: searching pipe name: client:%s server:%s\n",
pipe_names[i].client_pipe , pipe_names[i].server_pipe ));
@@ -746,10 +758,10 @@ static BOOL check_bind_response(RPC_HDR_BA *hdr_ba, char *pipe_name, RPC_IFACE *
}
else
{
- DEBUG(2,("bind_rpc_pipe: pipe_name %s != expected pipe %s\n",
+ DEBUG(4,("bind_rpc_pipe: pipe_name %s != expected pipe %s. oh well!\n",
pipe_names[i].server_pipe ,
hdr_ba->addr.str));
- return False;
+ break;
}
}
else
@@ -853,6 +865,12 @@ static BOOL rpc_pipe_bind(struct cli_state *cli, char *pipe_name,
valid_ack = check_bind_response(&hdr_ba, pipe_name, transfer);
}
+ if (valid_ack)
+ {
+ cli->max_xmit_frag = hdr_ba.bba.max_tsize;
+ cli->max_recv_frag = hdr_ba.bba.max_rsize;
+ }
+
if (valid_ack && ntlmssp_auth)
{
smb_io_rpc_hdr_auth("", &rhdr_auth, &rdata, 0);
diff --git a/source3/rpc_client/cli_samr.c b/source3/rpc_client/cli_samr.c
index 9fe4c0a16a..fae96b561c 100644
--- a/source3/rpc_client/cli_samr.c
+++ b/source3/rpc_client/cli_samr.c
@@ -186,13 +186,14 @@ BOOL do_samr_unknown_38(struct cli_state *cli, char *srv_name)
samr_io_r_unknown_38("", &r_e, &rdata, 0);
p = rdata.offset != 0;
+#if 0
if (p && r_e.status != 0)
{
/* report error code */
DEBUG(0,("SAMR_R_UNKNOWN_38: %s\n", get_nt_error_msg(r_e.status)));
p = False;
}
-
+#endif
if (p)
{
valid_un8 = True;
diff --git a/source3/rpc_parse/parse_lsa.c b/source3/rpc_parse/parse_lsa.c
index 40f05e0c3a..49a0951554 100644
--- a/source3/rpc_parse/parse_lsa.c
+++ b/source3/rpc_parse/parse_lsa.c
@@ -227,10 +227,11 @@ static void lsa_io_obj_attr(char *desc, LSA_OBJ_ATTR *attr, prs_struct *ps, int
}
}
+
/*******************************************************************
makes an LSA_Q_OPEN_POL structure.
********************************************************************/
-void make_q_open_pol(LSA_Q_OPEN_POL *r_q, char *server_name,
+void make_q_open_pol(LSA_Q_OPEN_POL *r_q, uint16 system_name,
uint32 attributes,
uint32 desired_access,
LSA_SEC_QOS *qos)
@@ -246,7 +247,7 @@ void make_q_open_pol(LSA_Q_OPEN_POL *r_q, char *server_name,
r_q->des_access = desired_access;
}
- make_unistr2 (&(r_q->uni_server_name), server_name, strlen(server_name));
+ r_q->system_name = system_name;
make_lsa_obj_attr(&(r_q->attr ), attributes, qos);
}
@@ -261,8 +262,9 @@ void lsa_io_q_open_pol(char *desc, LSA_Q_OPEN_POL *r_q, prs_struct *ps, int dep
depth++;
prs_uint32("ptr ", ps, depth, &(r_q->ptr ));
+ prs_uint16("system_name", ps, depth, &(r_q->system_name ));
+ prs_align ( ps );
- smb_io_unistr2 ("", &(r_q->uni_server_name), r_q->ptr, ps, depth);
lsa_io_obj_attr("", &(r_q->attr ), ps, depth);
if (r_q->attr.ptr_sec_qos == 0)
@@ -287,6 +289,65 @@ void lsa_io_r_open_pol(char *desc, LSA_R_OPEN_POL *r_p, prs_struct *ps, int dep
}
/*******************************************************************
+makes an LSA_Q_OPEN_POL2 structure.
+********************************************************************/
+void make_q_open_pol2(LSA_Q_OPEN_POL2 *r_q, char *server_name,
+ uint32 attributes,
+ uint32 desired_access,
+ LSA_SEC_QOS *qos)
+{
+ if (r_q == NULL) return;
+
+ DEBUG(5,("make_open_pol2: attr:%d da:%d\n", attributes, desired_access));
+
+ r_q->ptr = 1; /* undocumented pointer */
+
+ if (qos == NULL)
+ {
+ r_q->des_access = desired_access;
+ }
+
+ make_unistr2 (&(r_q->uni_server_name), server_name, strlen(server_name));
+ make_lsa_obj_attr(&(r_q->attr ), attributes, qos);
+}
+
+/*******************************************************************
+reads or writes an LSA_Q_OPEN_POL2 structure.
+********************************************************************/
+void lsa_io_q_open_pol2(char *desc, LSA_Q_OPEN_POL2 *r_q, prs_struct *ps, int depth)
+{
+ if (r_q == NULL) return;
+
+ prs_debug(ps, depth, desc, "lsa_io_q_open_pol2");
+ depth++;
+
+ prs_uint32("ptr ", ps, depth, &(r_q->ptr ));
+
+ smb_io_unistr2 ("", &(r_q->uni_server_name), r_q->ptr, ps, depth);
+ lsa_io_obj_attr("", &(r_q->attr ), ps, depth);
+
+ if (r_q->attr.ptr_sec_qos == 0)
+ {
+ prs_uint32("des_access", ps, depth, &(r_q->des_access));
+ }
+}
+
+/*******************************************************************
+reads or writes an LSA_R_OPEN_POL2 structure.
+********************************************************************/
+void lsa_io_r_open_pol2(char *desc, LSA_R_OPEN_POL2 *r_p, prs_struct *ps, int depth)
+{
+ if (r_p == NULL) return;
+
+ prs_debug(ps, depth, desc, "lsa_io_r_open_pol2");
+ depth++;
+
+ smb_io_pol_hnd("", &(r_p->pol), ps, depth);
+
+ prs_uint32("status", ps, depth, &(r_p->status));
+}
+
+/*******************************************************************
makes an LSA_Q_QUERY_INFO structure.
********************************************************************/
void make_q_query(LSA_Q_QUERY_INFO *q_q, POLICY_HND *hnd, uint16 info_class)
diff --git a/source3/rpc_parse/parse_samr.c b/source3/rpc_parse/parse_samr.c
index b71c209845..eb882a7564 100644
--- a/source3/rpc_parse/parse_samr.c
+++ b/source3/rpc_parse/parse_samr.c
@@ -2403,6 +2403,58 @@ void samr_io_r_connect(char *desc, SAMR_R_CONNECT *r_u, prs_struct *ps, int dep
}
/*******************************************************************
+makes a SAMR_Q_CONNECT_ANON structure.
+********************************************************************/
+void make_samr_q_connect_anon(SAMR_Q_CONNECT_ANON *q_u)
+{
+ if (q_u == NULL) return;
+
+ DEBUG(5,("make_q_connect_anon\n"));
+
+ q_u->ptr = 1;
+ q_u->unknown_0 = 0x5c;
+ q_u->unknown_1 = 0x01;
+ q_u->unknown_2 = 0x20;
+}
+
+
+/*******************************************************************
+reads or writes a structure.
+********************************************************************/
+void samr_io_q_connect_anon(char *desc, SAMR_Q_CONNECT_ANON *q_u, prs_struct *ps, int depth)
+{
+ if (q_u == NULL) return;
+
+ prs_debug(ps, depth, desc, "samr_io_q_connect_anon");
+ depth++;
+
+ prs_align(ps);
+
+ prs_uint32("ptr ", ps, depth, &(q_u->ptr ));
+ prs_uint16("unknown_0", ps, depth, &(q_u->unknown_0));
+ prs_uint16("unknown_1", ps, depth, &(q_u->unknown_1));
+ prs_uint32("unknown_2", ps, depth, &(q_u->unknown_2));
+}
+
+/*******************************************************************
+reads or writes a structure.
+********************************************************************/
+void samr_io_r_connect_anon(char *desc, SAMR_R_CONNECT_ANON *r_u, prs_struct *ps, int depth)
+{
+ if (r_u == NULL) return;
+
+ prs_debug(ps, depth, desc, "samr_io_r_connect_anon");
+ depth++;
+
+ prs_align(ps);
+
+ smb_io_pol_hnd("connect_pol", &(r_u->connect_pol), ps, depth);
+ prs_align(ps);
+
+ prs_uint32("status", ps, depth, &(r_u->status));
+}
+
+/*******************************************************************
makes a SAMR_Q_OPEN_ALIAS structure.
********************************************************************/
void make_samr_q_open_alias(SAMR_Q_OPEN_ALIAS *q_u,
@@ -2552,16 +2604,16 @@ void samr_io_q_unknown_38(char *desc, SAMR_Q_UNKNOWN_38 *q_u, prs_struct *ps, i
/*******************************************************************
makes a SAMR_R_UNKNOWN_38 structure.
********************************************************************/
-void make_samr_r_unknown_38(SAMR_R_UNKNOWN_38 *r_u,
- uint16 level, uint32 status)
+void make_samr_r_unknown_38(SAMR_R_UNKNOWN_38 *r_u)
{
if (r_u == NULL) return;
DEBUG(5,("make_r_unknown_38\n"));
- r_u->level.value = level;
- r_u->ptr_0 = 0;
- r_u->status = status;
+ r_u->unk_0 = 0;
+ r_u->unk_1 = 0;
+ r_u->unk_2 = 0;
+ r_u->unk_3 = 0;
}
/*******************************************************************
@@ -2576,9 +2628,14 @@ void samr_io_r_unknown_38(char *desc, SAMR_R_UNKNOWN_38 *r_u, prs_struct *ps, i
prs_align(ps);
- smb_io_lookup_level("level ", &(r_u->level), ps, depth);
- prs_uint32("ptr_0 ", ps, depth, &(r_u->ptr_0 ));
- prs_uint32("status", ps, depth, &(r_u->status));
+ prs_uint16("unk_0", ps, depth, &(r_u->unk_0));
+ prs_align(ps);
+ prs_uint16("unk_1", ps, depth, &(r_u->unk_1));
+ prs_align(ps);
+ prs_uint16("unk_2", ps, depth, &(r_u->unk_2));
+ prs_align(ps);
+ prs_uint16("unk_3", ps, depth, &(r_u->unk_3));
+ prs_align(ps);
}
/*******************************************************************
diff --git a/source3/rpc_server/srv_lsa.c b/source3/rpc_server/srv_lsa.c
index 2e5ebc9e68..93584b5acf 100644
--- a/source3/rpc_server/srv_lsa.c
+++ b/source3/rpc_server/srv_lsa.c
@@ -31,6 +31,28 @@ extern int DEBUGLEVEL;
extern DOM_SID global_machine_sid;
/***************************************************************************
+lsa_reply_open_policy2
+ ***************************************************************************/
+static void lsa_reply_open_policy2(prs_struct *rdata)
+{
+ int i;
+ LSA_R_OPEN_POL2 r_o;
+
+ ZERO_STRUCT(r_o);
+
+ /* set up the LSA QUERY INFO response */
+
+ for (i = 4; i < POL_HND_SIZE; i++)
+ {
+ r_o.pol.data[i] = i;
+ }
+ r_o.status = 0x0;
+
+ /* store the response in the SMB stream */
+ lsa_io_r_open_pol2("", &r_o, rdata, 0);
+}
+
+/***************************************************************************
lsa_reply_open_policy
***************************************************************************/
static void lsa_reply_open_policy(prs_struct *rdata)
@@ -282,6 +304,25 @@ static void lsa_reply_lookup_rids(prs_struct *rdata,
/***************************************************************************
api_lsa_open_policy
***************************************************************************/
+static void api_lsa_open_policy2( uint16 vuid, prs_struct *data,
+ prs_struct *rdata )
+{
+ LSA_Q_OPEN_POL2 q_o;
+
+ ZERO_STRUCT(q_o);
+
+ /* grab the server, object attributes and desired access flag...*/
+ lsa_io_q_open_pol2("", &q_o, data, 0);
+
+ /* lkclXXXX having decoded it, ignore all fields in the open policy! */
+
+ /* return a 20 byte policy handle */
+ lsa_reply_open_policy2(rdata);
+}
+
+/***************************************************************************
+api_lsa_open_policy
+ ***************************************************************************/
static void api_lsa_open_policy( uint16 vuid, prs_struct *data,
prs_struct *rdata )
{
@@ -513,6 +554,7 @@ static void api_lsa_open_secret( uint16 vuid, prs_struct *data,
***************************************************************************/
static struct api_struct api_lsa_cmds[] =
{
+ { "LSA_OPENPOLICY2" , LSA_OPENPOLICY2 , api_lsa_open_policy2 },
{ "LSA_OPENPOLICY" , LSA_OPENPOLICY , api_lsa_open_policy },
{ "LSA_QUERYINFOPOLICY" , LSA_QUERYINFOPOLICY , api_lsa_query_info },
{ "LSA_ENUMTRUSTDOM" , LSA_ENUMTRUSTDOM , api_lsa_enum_trust_dom },
diff --git a/source3/rpc_server/srv_pipe_hnd.c b/source3/rpc_server/srv_pipe_hnd.c
index 4d5fd3865e..b1aede6166 100644
--- a/source3/rpc_server/srv_pipe_hnd.c
+++ b/source3/rpc_server/srv_pipe_hnd.c
@@ -123,6 +123,7 @@ pipes_struct *open_rpc_pipe_p(char *pipe_name,
p->open = True;
p->device_state = 0;
+ p->priority = 0;
p->conn = conn;
p->vuid = vuid;
@@ -301,6 +302,29 @@ int read_pipe(pipes_struct *p, char *data, uint32 pos, int n)
/****************************************************************************
+ wait device state on a pipe. exactly what this is for is unknown...
+****************************************************************************/
+BOOL wait_rpc_pipe_hnd_state(pipes_struct *p, uint16 priority)
+{
+ if (p == NULL) return False;
+
+ if (p->open)
+ {
+ DEBUG(3,("%s Setting pipe wait state priority=%x on pipe (name=%s)\n",
+ timestring(), priority, p->name));
+
+ p->priority = priority;
+
+ return True;
+ }
+
+ DEBUG(3,("%s Error setting pipe wait state priority=%x (name=%s)\n",
+ timestring(), priority, p->name));
+ return False;
+}
+
+
+/****************************************************************************
set device state on a pipe. exactly what this is for is unknown...
****************************************************************************/
BOOL set_rpc_pipe_hnd_state(pipes_struct *p, uint16 device_state)
diff --git a/source3/rpc_server/srv_samr.c b/source3/rpc_server/srv_samr.c
index 22827f9f5c..11574be9b3 100644
--- a/source3/rpc_server/srv_samr.c
+++ b/source3/rpc_server/srv_samr.c
@@ -78,7 +78,8 @@ static BOOL get_sampwd_entries(SAM_USER_INFO_21 *pw_buf,
pw_buf[(*num_entries)].acb_info = (uint16)pwd->acct_ctrl;
DEBUG(5, ("entry idx: %d user %s, rid 0x%x, acb %x",
- (*num_entries), pwd->smb_name, pwd->user_rid, pwd->acct_ctrl));
+ (*num_entries), pwd->smb_name,
+ pwd->user_rid, pwd->acct_ctrl));
if (acb_mask == 0 || IS_BITS_SET_SOME(pwd->acct_ctrl, acb_mask))
{
@@ -451,49 +452,55 @@ static void samr_reply_query_dispinfo(SAMR_Q_QUERY_DISPINFO *q_u,
SAM_INFO_1 info1;
SAM_INFO_2 info2;
SAM_USER_INFO_21 pass[MAX_SAM_ENTRIES];
- int num_entries;
- int total_entries;
+ int num_entries = 0;
+ int total_entries = 0;
BOOL got_pwds;
uint16 switch_level = 0x0;
+ ZERO_STRUCT(r_e);
+
r_e.status = 0x0;
+ DEBUG(5,("samr_reply_query_dispinfo: %d\n", __LINE__));
+
/* find the policy handle. open a policy on it. */
if (r_e.status == 0x0 && (find_lsa_policy_by_hnd(&(q_u->pol)) == -1))
{
r_e.status = 0xC0000000 | NT_STATUS_INVALID_HANDLE;
+ DEBUG(5,("samr_reply_query_dispinfo: invalid handle\n"));
}
- DEBUG(5,("samr_reply_query_dispinfo: %d\n", __LINE__));
-
- become_root(True);
- got_pwds = get_sampwd_entries(pass, &total_entries, &num_entries, MAX_SAM_ENTRIES, 0);
- unbecome_root(True);
-
- switch (q_u->switch_level)
+ if (r_e.status == 0x0)
{
- case 0x1:
+ become_root(True);
+ got_pwds = get_sampwd_entries(pass, &total_entries, &num_entries, MAX_SAM_ENTRIES, 0);
+ unbecome_root(True);
+
+ switch (q_u->switch_level)
{
-
- /* query disp info is for users */
- switch_level = 0x1;
- make_sam_info_1(&info1, ACB_NORMAL,
- q_u->start_idx, num_entries, pass);
+ case 0x1:
+ {
+
+ /* query disp info is for users */
+ switch_level = 0x1;
+ make_sam_info_1(&info1, ACB_NORMAL,
+ q_u->start_idx, num_entries, pass);
- ctr.sam.info1 = &info1;
+ ctr.sam.info1 = &info1;
- break;
- }
- case 0x2:
- {
- /* query disp info is for servers */
- switch_level = 0x2;
- make_sam_info_2(&info2, ACB_WSTRUST,
- q_u->start_idx, num_entries, pass);
+ break;
+ }
+ case 0x2:
+ {
+ /* query disp info is for servers */
+ switch_level = 0x2;
+ make_sam_info_2(&info2, ACB_WSTRUST,
+ q_u->start_idx, num_entries, pass);
- ctr.sam.info2 = &info2;
+ ctr.sam.info2 = &info2;
- break;
+ break;
+ }
}
}
@@ -1170,6 +1177,59 @@ static void api_samr_unknown_32( uint16 vuid, prs_struct *data, prs_struct *rdat
/*******************************************************************
+ samr_reply_connect_anon
+ ********************************************************************/
+static void samr_reply_connect_anon(SAMR_Q_CONNECT_ANON *q_u,
+ prs_struct *rdata)
+{
+ SAMR_R_CONNECT_ANON r_u;
+ BOOL pol_open = False;
+
+ /* set up the SAMR connect_anon response */
+
+ r_u.status = 0x0;
+ /* get a (unique) handle. open a policy on it. */
+ if (r_u.status == 0x0 && !(pol_open = open_lsa_policy_hnd(&(r_u.connect_pol))))
+ {
+ r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
+ }
+
+ /* associate the domain SID with the (unique) handle. */
+ if (r_u.status == 0x0 && !set_lsa_policy_samr_pol_status(&(r_u.connect_pol), q_u->unknown_0))
+ {
+ /* oh, whoops. don't know what error message to return, here */
+ r_u.status = 0xC0000000 | NT_STATUS_OBJECT_NAME_NOT_FOUND;
+ }
+
+ if (r_u.status != 0 && pol_open)
+ {
+ close_lsa_policy_hnd(&(r_u.connect_pol));
+ }
+
+ DEBUG(5,("samr_connect_anon: %d\n", __LINE__));
+
+ /* store the response in the SMB stream */
+ samr_io_r_connect_anon("", &r_u, rdata, 0);
+
+ DEBUG(5,("samr_connect_anon: %d\n", __LINE__));
+
+}
+
+/*******************************************************************
+ api_samr_connect_anon
+ ********************************************************************/
+static void api_samr_connect_anon( uint16 vuid, prs_struct *data, prs_struct *rdata)
+{
+ SAMR_Q_CONNECT_ANON q_u;
+
+ /* grab the samr open policy */
+ samr_io_q_connect_anon("", &q_u, data, 0);
+
+ /* construct reply. always indicate success */
+ samr_reply_connect_anon(&q_u, rdata);
+}
+
+/*******************************************************************
samr_reply_connect
********************************************************************/
static void samr_reply_connect(SAMR_Q_CONNECT *q_u,
@@ -1283,6 +1343,7 @@ static struct api_struct api_samr_cmds [] =
{
{ "SAMR_CLOSE_HND" , SAMR_CLOSE_HND , api_samr_close_hnd },
{ "SAMR_CONNECT" , SAMR_CONNECT , api_samr_connect },
+ { "SAMR_CONNECT_ANON" , SAMR_CONNECT_ANON , api_samr_connect_anon },
{ "SAMR_ENUM_DOM_USERS" , SAMR_ENUM_DOM_USERS , api_samr_enum_dom_users },
{ "SAMR_ENUM_DOM_GROUPS" , SAMR_ENUM_DOM_GROUPS , api_samr_enum_dom_groups },
{ "SAMR_ENUM_DOM_ALIASES" , SAMR_ENUM_DOM_ALIASES , api_samr_enum_dom_aliases },
diff --git a/source3/smbd/ipc.c b/source3/smbd/ipc.c
index 646ac83331..bfd618f325 100644
--- a/source3/smbd/ipc.c
+++ b/source3/smbd/ipc.c
@@ -3125,6 +3125,29 @@ static void api_rpc_trans_reply(char *outbuf,
}
/****************************************************************************
+ WaitNamedPipeHandleState
+****************************************************************************/
+static BOOL api_WNPHS(char *outbuf, pipes_struct *p, char *param)
+{
+ uint16 priority;
+
+ if (!param) return False;
+
+ priority = param[0] + (param[1] << 8);
+ DEBUG(4,("WaitNamedPipeHandleState priority %x\n", priority));
+
+ if (wait_rpc_pipe_hnd_state(p, priority))
+ {
+ /* now send the reply */
+ send_trans_reply(outbuf, NULL, NULL, NULL, 0, p->file_offset);
+
+ return True;
+ }
+ return False;
+}
+
+
+/****************************************************************************
SetNamedPipeHandleState
****************************************************************************/
static BOOL api_SNPHS(char *outbuf, pipes_struct *p, char *param)
@@ -3134,7 +3157,7 @@ static BOOL api_SNPHS(char *outbuf, pipes_struct *p, char *param)
if (!param) return False;
id = param[0] + (param[1] << 8);
- DEBUG(4,("lsarpc SetNamedPipeHandleState to code %x\n", id));
+ DEBUG(4,("SetNamedPipeHandleState to code %x\n", id));
if (set_rpc_pipe_hnd_state(p, id))
{
@@ -3237,6 +3260,12 @@ static int api_fd_reply(connection_struct *conn,uint16 vuid,char *outbuf,
}
break;
}
+ case 0x53:
+ {
+ /* Wait Named Pipe Handle state */
+ reply = api_WNPHS(outbuf, p, params);
+ break;
+ }
case 0x01:
{
/* Set Named Pipe Handle state */
@@ -3434,6 +3463,16 @@ static int named_pipe(connection_struct *conn,uint16 vuid, char *outbuf,char *na
return api_reply(conn,vuid,outbuf,data,params,tdscnt,tpscnt,mdrcnt,mprcnt);
}
+ if (strequal(name,"WKSSVC") ||
+ strequal(name,"SRVSVC") ||
+ strequal(name,"WINREG") ||
+ strequal(name,"SAMR") ||
+ strequal(name,"LSARPC"))
+ {
+ DEBUG(4,("named pipe command from Win95 (wow!)\n"));
+ return api_fd_reply(conn,vuid,outbuf,setup,data,params,suwcnt,tdscnt,tpscnt,mdrcnt,mprcnt);
+ }
+
if (strlen(name) < 1)
{
return api_fd_reply(conn,vuid,outbuf,setup,data,params,suwcnt,tdscnt,tpscnt,mdrcnt,mprcnt);