Ejemplo n.º 1
0
static struct npa_state *npa_state_init(TALLOC_CTX *mem_ctx)
{
	struct npa_state *npa;

	npa = talloc_zero(mem_ctx, struct npa_state);
	if (npa == NULL) {
		return NULL;
	}

	npa->read_queue = tevent_queue_create(npa, "npa_cli_read");
	if (npa->read_queue == NULL) {
		DEBUG(0, ("tevent_queue_create failed\n"));
		goto fail;
	}

	npa->write_queue = tevent_queue_create(npa, "npa_cli_write");
	if (npa->write_queue == NULL) {
		DEBUG(0, ("tevent_queue_create failed\n"));
		goto fail;
	}

	return npa;
fail:
	talloc_free(npa);
	return NULL;
}
Ejemplo n.º 2
0
struct wb_context *wb_context_init(TALLOC_CTX *mem_ctx, const char* dir)
{
	struct wb_context *result;

	result = talloc_zero(mem_ctx, struct wb_context);
	if (result == NULL) {
		return NULL;
	}
	result->queue = tevent_queue_create(result, "wb_trans");
	if (result->queue == NULL) {
		TALLOC_FREE(result);
		return NULL;
	}
	result->fd = -1;
	result->is_priv = false;

	if (dir != NULL) {
		result->dir = talloc_strdup(result, dir);
	} else {
		result->dir = winbindd_socket_dir();
	}
	if (result->dir == NULL) {
		TALLOC_FREE(result);
		return NULL;
	}
	return result;
}
Ejemplo n.º 3
0
static void named_pipe_accept_done(struct tevent_req *subreq)
{
	struct auth_session_info_transport *session_info_transport;
	struct named_pipe_client *npc =
		tevent_req_callback_data(subreq, struct named_pipe_client);
	int error;
	int ret;

	ret = tstream_npa_accept_existing_recv(subreq, &error, npc,
						&npc->tstream,
						&npc->client,
						&npc->client_name,
						&npc->server,
						&npc->server_name,
						&session_info_transport);

	npc->session_info = talloc_move(npc, &session_info_transport->session_info);

	TALLOC_FREE(subreq);
	if (ret != 0) {
		DEBUG(2, ("Failed to accept named pipe connection! (%s)\n",
			  strerror(error)));
		TALLOC_FREE(npc);
		return;
	}

	ret = make_server_pipes_struct(npc,
				       npc->msg_ctx,
				       npc->pipe_name, NCACN_NP,
					false, npc->server, npc->client, npc->session_info,
					&npc->p, &error);
	if (ret != 0) {
		DEBUG(2, ("Failed to create pipes_struct! (%s)\n",
			  strerror(error)));
		goto fail;
	}

	npc->write_queue = tevent_queue_create(npc, "np_server_write_queue");
	if (!npc->write_queue) {
		DEBUG(2, ("Failed to set up write queue!\n"));
		goto fail;
	}

	/* And now start receiving and processing packets */
	subreq = dcerpc_read_ncacn_packet_send(npc, npc->ev, npc->tstream);
	if (!subreq) {
		DEBUG(2, ("Failed to start receving packets\n"));
		goto fail;
	}
	tevent_req_set_callback(subreq, named_pipe_packet_process, npc);
	return;

fail:
	DEBUG(2, ("Fatal error. Terminating client(%s) connection!\n",
		  npc->client_name));
	/* terminate client connection */
	talloc_free(npc);
	return;
}
Ejemplo n.º 4
0
Archivo: kdc.c Proyecto: Arkhont/samba
/*
  called when we get a new connection
*/
static void kdc_tcp_accept(struct stream_connection *conn)
{
	struct kdc_socket *kdc_socket;
	struct kdc_tcp_connection *kdc_conn;
	struct tevent_req *subreq;
	int rc;

	kdc_conn = talloc_zero(conn, struct kdc_tcp_connection);
	if (kdc_conn == NULL) {
		stream_terminate_connection(conn,
				"kdc_tcp_accept: out of memory");
		return;
	}

	kdc_conn->send_queue = tevent_queue_create(conn, "kdc_tcp_accept");
	if (kdc_conn->send_queue == NULL) {
		stream_terminate_connection(conn,
				"kdc_tcp_accept: out of memory");
		return;
	}

	kdc_socket = talloc_get_type(conn->private_data, struct kdc_socket);

	TALLOC_FREE(conn->event.fde);

	rc = tstream_bsd_existing_socket(kdc_conn,
			socket_get_fd(conn->socket),
			&kdc_conn->tstream);
	if (rc < 0) {
		stream_terminate_connection(conn,
				"kdc_tcp_accept: out of memory");
		return;
	}

	kdc_conn->conn = conn;
	kdc_conn->kdc_socket = kdc_socket;
	conn->private_data = kdc_conn;

	/*
	 * The krb5 tcp pdu's has the length as 4 byte (initial_read_size),
	 * packet_full_request_u32 provides the pdu length then.
	 */
	subreq = tstream_read_pdu_blob_send(kdc_conn,
					    kdc_conn->conn->event.ctx,
					    kdc_conn->tstream,
					    4, /* initial_read_size */
					    packet_full_request_u32,
					    kdc_conn);
	if (subreq == NULL) {
		kdc_tcp_terminate_connection(kdc_conn, "kdc_tcp_accept: "
				"no memory for tstream_read_pdu_blob_send");
		return;
	}
	tevent_req_set_callback(subreq, kdc_tcp_call_loop, kdc_conn);
}
Ejemplo n.º 5
0
static void wbsrv_accept(struct stream_connection *conn)
{
	struct wbsrv_listen_socket *wbsrv_socket = talloc_get_type(conn->private_data,
								   struct wbsrv_listen_socket);
	struct wbsrv_connection *wbsrv_conn;
	struct tevent_req *subreq;
	int rc;

	wbsrv_conn = talloc_zero(conn, struct wbsrv_connection);
	if (wbsrv_conn == NULL) {
		stream_terminate_connection(conn, "wbsrv_accept: out of memory");
		return;
	}

	wbsrv_conn->send_queue = tevent_queue_create(conn, "wbsrv_accept");
	if (wbsrv_conn->send_queue == NULL) {
		stream_terminate_connection(conn,
				"wbsrv_accept: out of memory");
		return;
	}

	TALLOC_FREE(conn->event.fde);

	rc = tstream_bsd_existing_socket(wbsrv_conn,
			socket_get_fd(conn->socket),
			&wbsrv_conn->tstream);
	if (rc < 0) {
		stream_terminate_connection(conn,
				"wbsrv_accept: out of memory");
		return;
	}

	wbsrv_conn->conn = conn;
	wbsrv_conn->listen_socket = wbsrv_socket;
	wbsrv_conn->lp_ctx = wbsrv_socket->service->task->lp_ctx;
	conn->private_data = wbsrv_conn;

	/*
	 * The winbind pdu's has the length as 4 byte (initial_read_size),
	 * wbsrv_samba3_packet_full_request provides the pdu length then.
	 */
	subreq = tstream_read_pdu_blob_send(wbsrv_conn,
					    wbsrv_conn->conn->event.ctx,
					    wbsrv_conn->tstream,
					    4, /* initial_read_size */
					    wbsrv_samba3_packet_full_request,
					    wbsrv_conn);
	if (subreq == NULL) {
		wbsrv_terminate_connection(wbsrv_conn, "wbsrv_accept: "
				"no memory for tstream_read_pdu_blob_send");
		return;
	}
	tevent_req_set_callback(subreq, wbsrv_call_loop, wbsrv_conn);
}
Ejemplo n.º 6
0
struct tevent_req *ctdb_conn_init_send(TALLOC_CTX *mem_ctx,
				       struct tevent_context *ev,
				       const char *sock)
{
	struct tevent_req *req, *subreq;
	struct ctdb_conn_init_state *state;

	req = tevent_req_create(mem_ctx, &state, struct ctdb_conn_init_state);
	if (req == NULL) {
		return NULL;
	}

	if (!lp_clustering()) {
		tevent_req_error(req, ENOSYS);
		return tevent_req_post(req, ev);
	}

	if (strlen(sock) >= sizeof(state->addr.sun_path)) {
		tevent_req_error(req, ENAMETOOLONG);
		return tevent_req_post(req, ev);
	}

	state->conn = talloc(state, struct ctdb_conn);
	if (tevent_req_nomem(state->conn, req)) {
		return tevent_req_post(req, ev);
	}

	state->conn->outqueue = tevent_queue_create(
		state->conn, "ctdb outqueue");
	if (tevent_req_nomem(state->conn->outqueue, req)) {
		return tevent_req_post(req, ev);
	}

	state->conn->fd = socket(AF_UNIX, SOCK_STREAM, 0);
	if (state->conn->fd == -1) {
		tevent_req_error(req, errno);
		return tevent_req_post(req, ev);
	}
	talloc_set_destructor(state->conn, ctdb_conn_destructor);

	state->addr.sun_family = AF_UNIX;
	strncpy(state->addr.sun_path, sock, sizeof(state->addr.sun_path));

	subreq = async_connect_send(state, ev, state->conn->fd,
				    (struct sockaddr *)&state->addr,
				    sizeof(state->addr), before_connect_cb,
				    after_connect_cb, NULL);
	if (tevent_req_nomem(subreq, req)) {
		return tevent_req_post(req, ev);
	}
	tevent_req_set_callback(subreq, ctdb_conn_init_done, req);
	return req;
}
Ejemplo n.º 7
0
struct wb_context *wb_context_init(TALLOC_CTX *mem_ctx)
{
	struct wb_context *result;

	result = talloc(mem_ctx, struct wb_context);
	if (result == NULL) {
		return NULL;
	}
	result->queue = tevent_queue_create(result, "wb_trans");
	if (result->queue == NULL) {
		TALLOC_FREE(result);
		return NULL;
	}
	result->fd = -1;
	return result;
}
Ejemplo n.º 8
0
NTSTATUS make_internal_rpc_pipe_socketpair(
	TALLOC_CTX *mem_ctx,
	struct tevent_context *ev_ctx,
	struct messaging_context *msg_ctx,
	const char *pipe_name,
	const struct ndr_syntax_id *syntax,
	const struct tsocket_address *remote_address,
	const struct tsocket_address *local_address,
	const struct auth_session_info *session_info,
	struct npa_state **pnpa)
{
	TALLOC_CTX *tmp_ctx = talloc_stackframe();
	struct named_pipe_client *npc;
	struct tevent_req *subreq;
	struct npa_state *npa;
	NTSTATUS status;
	int error;
	int rc;

	DEBUG(4, ("Create of internal pipe %s requested\n", pipe_name));

	npa = npa_state_init(tmp_ctx);
	if (npa == NULL) {
		status = NT_STATUS_NO_MEMORY;
		goto out;
	}

	npa->file_type = FILE_TYPE_MESSAGE_MODE_PIPE;
	npa->device_state = 0xff | 0x0400 | 0x0100;
	npa->allocation_size = 4096;

	npc = named_pipe_client_init(npa,
				     ev_ctx,
				     msg_ctx,
				     pipe_name,
				     NULL, /* term_fn */
				     npa->file_type,
				     npa->device_state,
				     npa->allocation_size,
				     NULL); /* private_data */
	if (npc == NULL) {
		status = NT_STATUS_NO_MEMORY;
		goto out;
	}
	npa->private_data = (void*) npc;

	rc = tstream_npa_socketpair(npa->file_type,
				    npa,
				    &npa->stream,
				    npc,
				    &npc->tstream);
	if (rc == -1) {
		status = map_nt_error_from_unix(errno);
		goto out;
	}

	npc->remote_client_addr = tsocket_address_copy(remote_address, npc);
	if (npc->remote_client_addr == NULL) {
		status = NT_STATUS_NO_MEMORY;
		goto out;
	}

	npc->remote_client_name = tsocket_address_inet_addr_string(npc->remote_client_addr,
								   npc);
	if (npc->remote_client_name == NULL) {
		status = NT_STATUS_NO_MEMORY;
		goto out;
	}

	npc->local_server_addr = tsocket_address_copy(local_address, npc);
	if (npc->local_server_addr == NULL) {
		status = NT_STATUS_NO_MEMORY;
		goto out;
	}

	npc->local_server_name = tsocket_address_inet_addr_string(
		npc->local_server_addr, npc);
	if (npc->local_server_name == NULL) {
		status = NT_STATUS_NO_MEMORY;
		goto out;
	}

	npc->session_info = copy_session_info(npc, session_info);
	if (npc->session_info == NULL) {
		status = NT_STATUS_NO_MEMORY;
		goto out;
	}

	rc = make_server_pipes_struct(npc,
				      npc->msg_ctx,
				      npc->pipe_name,
				      NCACN_NP,
				      npc->remote_client_addr,
				      npc->local_server_addr,
				      npc->session_info,
				      &npc->p,
				      &error);
	if (rc == -1) {
		status = map_nt_error_from_unix(error);
		goto out;
	}

	npc->write_queue = tevent_queue_create(npc, "npa_server_write_queue");
	if (npc->write_queue == NULL) {
		status = NT_STATUS_NO_MEMORY;
		goto out;
	}

	subreq = dcerpc_read_ncacn_packet_send(npc, npc->ev, npc->tstream);
	if (subreq == NULL) {
		DEBUG(2, ("Failed to start receiving packets\n"));
		status = NT_STATUS_PIPE_BROKEN;
		goto out;
	}
	tevent_req_set_callback(subreq, named_pipe_packet_process, npc);

	*pnpa = talloc_steal(mem_ctx, npa);
	status = NT_STATUS_OK;
out:
	talloc_free(tmp_ctx);
	return status;
}
Ejemplo n.º 9
0
/*
  initialise a cldap_sock
*/
NTSTATUS cldap_socket_init(TALLOC_CTX *mem_ctx,
			   const struct tsocket_address *local_addr,
			   const struct tsocket_address *remote_addr,
			   struct cldap_socket **_cldap)
{
	struct cldap_socket *c = NULL;
	struct tsocket_address *any = NULL;
	NTSTATUS status;
	int ret;
	const char *fam = NULL;

	if (local_addr == NULL && remote_addr == NULL) {
		return NT_STATUS_INVALID_PARAMETER_MIX;
	}

	if (remote_addr) {
		bool is_ipv4;
		bool is_ipv6;

		is_ipv4 = tsocket_address_is_inet(remote_addr, "ipv4");
		is_ipv6 = tsocket_address_is_inet(remote_addr, "ipv6");

		if (is_ipv4) {
			fam = "ipv4";
		} else if (is_ipv6) {
			fam = "ipv6";
		} else {
			return NT_STATUS_INVALID_ADDRESS;
		}
	}

	c = talloc_zero(mem_ctx, struct cldap_socket);
	if (!c) {
		goto nomem;
	}

	if (!local_addr) {
		/*
		 * Here we know the address family of the remote address.
		 */
		if (fam == NULL) {
			return NT_STATUS_INVALID_PARAMETER_MIX;
		}

		ret = tsocket_address_inet_from_strings(c, fam,
							NULL, 0,
							&any);
		if (ret != 0) {
			status = map_nt_error_from_unix_common(errno);
			goto nterror;
		}
		local_addr = any;
	}

	c->searches.idr = idr_init(c);
	if (!c->searches.idr) {
		goto nomem;
	}

	ret = tdgram_inet_udp_socket(local_addr, remote_addr,
				     c, &c->sock);
	if (ret != 0) {
		status = map_nt_error_from_unix_common(errno);
		goto nterror;
	}
	talloc_free(any);

	if (remote_addr) {
		c->connected = true;
	}

	c->send_queue = tevent_queue_create(c, "cldap_send_queue");
	if (!c->send_queue) {
		goto nomem;
	}

	talloc_set_destructor(c, cldap_socket_destructor);

	*_cldap = c;
	return NT_STATUS_OK;

nomem:
	status = NT_STATUS_NO_MEMORY;
nterror:
	talloc_free(c);
	return status;
}
Ejemplo n.º 10
0
/*
  called when we get a new connection
*/
static void wreplsrv_accept(struct stream_connection *conn)
{
	struct wreplsrv_service *service = talloc_get_type(conn->private_data, struct wreplsrv_service);
	struct wreplsrv_in_connection *wrepl_conn;
	struct tsocket_address *peer_addr;
	char *peer_ip;
	struct tevent_req *subreq;
	int rc;

	wrepl_conn = talloc_zero(conn, struct wreplsrv_in_connection);
	if (wrepl_conn == NULL) {
		stream_terminate_connection(conn,
					    "wreplsrv_accept: out of memory");
		return;
	}

	wrepl_conn->send_queue = tevent_queue_create(conn, "wrepl_accept");
	if (wrepl_conn->send_queue == NULL) {
		stream_terminate_connection(conn,
					    "wrepl_accept: out of memory");
		return;
	}

	TALLOC_FREE(conn->event.fde);

	rc = tstream_bsd_existing_socket(wrepl_conn,
					 socket_get_fd(conn->socket),
					 &wrepl_conn->tstream);
	if (rc < 0) {
		stream_terminate_connection(conn,
					    "wrepl_accept: out of memory");
		return;
	}
	socket_set_flags(conn->socket, SOCKET_FLAG_NOCLOSE);

	wrepl_conn->conn = conn;
	wrepl_conn->service = service;

	peer_addr = conn->remote_address;

	if (!tsocket_address_is_inet(peer_addr, "ipv4")) {
		DEBUG(0,("wreplsrv_accept: non ipv4 peer addr '%s'\n",
			tsocket_address_string(peer_addr, wrepl_conn)));
		wreplsrv_terminate_in_connection(wrepl_conn, "wreplsrv_accept: "
				"invalid peer IP");
		return;
	}

	peer_ip = tsocket_address_inet_addr_string(peer_addr, wrepl_conn);
	if (peer_ip == NULL) {
		wreplsrv_terminate_in_connection(wrepl_conn, "wreplsrv_accept: "
				"could not convert peer IP into a string");
		return;
	}

	wrepl_conn->partner = wreplsrv_find_partner(service, peer_ip);
	irpc_add_name(conn->msg_ctx, "wreplsrv_connection");

	/*
	 * The wrepl pdu's has the length as 4 byte (initial_read_size),
	 * packet_full_request_u32 provides the pdu length then.
	 */
	subreq = tstream_read_pdu_blob_send(wrepl_conn,
					    wrepl_conn->conn->event.ctx,
					    wrepl_conn->tstream,
					    4, /* initial_read_size */
					    packet_full_request_u32,
					    wrepl_conn);
	if (subreq == NULL) {
		wreplsrv_terminate_in_connection(wrepl_conn, "wrepl_accept: "
				"no memory for tstream_read_pdu_blob_send");
		return;
	}
	tevent_req_set_callback(subreq, wreplsrv_call_loop, wrepl_conn);
}
Ejemplo n.º 11
0
/*
  called when we get a new connection
*/
NTSTATUS wreplsrv_in_connection_merge(struct wreplsrv_partner *partner,
				      uint32_t peer_assoc_ctx,
				      struct tstream_context **stream,
				      struct wreplsrv_in_connection **_wrepl_in)
{
	struct wreplsrv_service *service = partner->service;
	struct wreplsrv_in_connection *wrepl_in;
	const struct model_ops *model_ops;
	struct stream_connection *conn;
	struct tevent_req *subreq;
	NTSTATUS status;

	/* within the wrepl task we want to be a single process, so
	   ask for the single process model ops and pass these to the
	   stream_setup_socket() call. */
	model_ops = process_model_startup("single");
	if (!model_ops) {
		DEBUG(0,("Can't find 'single' process model_ops"));
		return NT_STATUS_INTERNAL_ERROR;
	}

	wrepl_in = talloc_zero(partner, struct wreplsrv_in_connection);
	NT_STATUS_HAVE_NO_MEMORY(wrepl_in);

	wrepl_in->service	= service;
	wrepl_in->partner	= partner;
	wrepl_in->tstream	= talloc_move(wrepl_in, stream);
	wrepl_in->assoc_ctx.peer_ctx = peer_assoc_ctx;

	status = stream_new_connection_merge(service->task->event_ctx,
					     service->task->lp_ctx,
					     model_ops,
					     &wreplsrv_stream_ops,
					     service->task->msg_ctx,
					     wrepl_in,
					     &conn);
	NT_STATUS_NOT_OK_RETURN(status);

	/*
	 * make the wreplsrv_in_connection structure a child of the
	 * stream_connection, to match the hierarchy of wreplsrv_accept
	 */
	wrepl_in->conn		= conn;
	talloc_steal(conn, wrepl_in);

	wrepl_in->send_queue = tevent_queue_create(wrepl_in, "wreplsrv_in_connection_merge");
	if (wrepl_in->send_queue == NULL) {
		stream_terminate_connection(conn,
					    "wreplsrv_in_connection_merge: out of memory");
		return NT_STATUS_NO_MEMORY;
	}

	/*
	 * The wrepl pdu's has the length as 4 byte (initial_read_size),
	 * packet_full_request_u32 provides the pdu length then.
	 */
	subreq = tstream_read_pdu_blob_send(wrepl_in,
					    wrepl_in->conn->event.ctx,
					    wrepl_in->tstream,
					    4, /* initial_read_size */
					    packet_full_request_u32,
					    wrepl_in);
	if (subreq == NULL) {
		wreplsrv_terminate_in_connection(wrepl_in, "wreplsrv_in_connection_merge: "
				"no memory for tstream_read_pdu_blob_send");
		return NT_STATUS_NO_MEMORY;
	}
	tevent_req_set_callback(subreq, wreplsrv_call_loop, wrepl_in);

	*_wrepl_in = wrepl_in;

	return NT_STATUS_OK;
}
Ejemplo n.º 12
0
/*
  initialise a server_context from a open socket and register a event handler
  for reading from that socket
*/
static void ldapsrv_accept(struct stream_connection *c,
			   struct auth_session_info *session_info,
			   bool is_privileged)
{
	struct ldapsrv_service *ldapsrv_service = 
		talloc_get_type(c->private_data, struct ldapsrv_service);
	struct ldapsrv_connection *conn;
	struct cli_credentials *server_credentials;
	struct socket_address *socket_address;
	NTSTATUS status;
	int port;
	int ret;
	struct tevent_req *subreq;
	struct timeval endtime;

	conn = talloc_zero(c, struct ldapsrv_connection);
	if (!conn) {
		stream_terminate_connection(c, "ldapsrv_accept: out of memory");
		return;
	}
	conn->is_privileged = is_privileged;

	conn->sockets.send_queue = tevent_queue_create(conn, "ldapsev send queue");
	if (conn->sockets.send_queue == NULL) {
		stream_terminate_connection(c,
					    "ldapsrv_accept: tevent_queue_create failed");
		return;
	}

	TALLOC_FREE(c->event.fde);

	ret = tstream_bsd_existing_socket(conn,
					  socket_get_fd(c->socket),
					  &conn->sockets.raw);
	if (ret == -1) {
		stream_terminate_connection(c,
					    "ldapsrv_accept: out of memory");
		return;
	}
	socket_set_flags(c->socket, SOCKET_FLAG_NOCLOSE);

	conn->connection  = c;
	conn->service     = ldapsrv_service;
	conn->lp_ctx      = ldapsrv_service->task->lp_ctx;

	c->private_data   = conn;

	socket_address = socket_get_my_addr(c->socket, conn);
	if (!socket_address) {
		ldapsrv_terminate_connection(conn, "ldapsrv_accept: failed to obtain local socket address!");
		return;
	}
	port = socket_address->port;
	talloc_free(socket_address);
	if (port == 3268 || port == 3269) /* Global catalog */ {
		conn->global_catalog = true;
	}

	server_credentials = cli_credentials_init(conn);
	if (!server_credentials) {
		stream_terminate_connection(c, "Failed to init server credentials\n");
		return;
	}

	cli_credentials_set_conf(server_credentials, conn->lp_ctx);
	status = cli_credentials_set_machine_account(server_credentials, conn->lp_ctx);
	if (!NT_STATUS_IS_OK(status)) {
		stream_terminate_connection(c, talloc_asprintf(conn, "Failed to obtain server credentials, perhaps a standalone server?: %s\n", nt_errstr(status)));
		return;
	}
	conn->server_credentials = server_credentials;

	conn->session_info = session_info;

	if (!NT_STATUS_IS_OK(ldapsrv_backend_Init(conn))) {
		ldapsrv_terminate_connection(conn, "backend Init failed");
		return;
	}

	/* load limits from the conf partition */
	ldapsrv_load_limits(conn); /* should we fail on error ? */

	/* register the server */	
	irpc_add_name(c->msg_ctx, "ldap_server");

	conn->sockets.active = conn->sockets.raw;

	if (port != 636 && port != 3269) {
		ldapsrv_call_read_next(conn);
		return;
	}

	endtime = timeval_current_ofs(conn->limits.conn_idle_time, 0);

	subreq = tstream_tls_accept_send(conn,
					 conn->connection->event.ctx,
					 conn->sockets.raw,
					 conn->service->tls_params);
	if (subreq == NULL) {
		ldapsrv_terminate_connection(conn, "ldapsrv_accept: "
				"no memory for tstream_tls_accept_send");
		return;
	}
	tevent_req_set_endtime(subreq,
			       conn->connection->event.ctx,
			       endtime);
	tevent_req_set_callback(subreq, ldapsrv_accept_tls_done, conn);
}
Ejemplo n.º 13
0
struct cli_state *cli_initialise_ex(int signing_state)
{
	struct cli_state *cli = NULL;
	bool allow_smb_signing = false;
	bool mandatory_signing = false;

	/* Check the effective uid - make sure we are not setuid */
	if (is_setuid_root()) {
		DEBUG(0,("libsmb based programs must *NOT* be setuid root.\n"));
		return NULL;
	}

	cli = TALLOC_ZERO_P(NULL, struct cli_state);
	if (!cli) {
		return NULL;
	}

	cli->dfs_mountpoint = talloc_strdup(cli, "");
	if (!cli->dfs_mountpoint) {
		goto error;
	}
	cli->port = 0;
	cli->fd = -1;
	cli->cnum = -1;
	cli->pid = (uint16)sys_getpid();
	cli->mid = 1;
	cli->vuid = UID_FIELD_INVALID;
	cli->protocol = PROTOCOL_NT1;
	cli->timeout = 20000; /* Timeout is in milliseconds. */
	cli->bufsize = CLI_BUFFER_SIZE+4;
	cli->max_xmit = cli->bufsize;
	cli->outbuf = (char *)SMB_MALLOC(cli->bufsize+SAFETY_MARGIN);
	cli->seqnum = 0;
	cli->inbuf = (char *)SMB_MALLOC(cli->bufsize+SAFETY_MARGIN);
	cli->oplock_handler = cli_oplock_ack;
	cli->case_sensitive = false;
	cli->smb_rw_error = SMB_READ_OK;

	cli->use_spnego = lp_client_use_spnego();

	cli->capabilities = CAP_UNICODE | CAP_STATUS32 | CAP_DFS;

	/* Set the CLI_FORCE_DOSERR environment variable to test
	   client routines using DOS errors instead of STATUS32
	   ones.  This intended only as a temporary hack. */	
	if (getenv("CLI_FORCE_DOSERR"))
		cli->force_dos_errors = true;

	if (lp_client_signing()) {
		allow_smb_signing = true;
	}

	if (lp_client_signing() == Required) {
		mandatory_signing = true;
	}

	if (signing_state != Undefined) {
		allow_smb_signing = true;
	}

	if (signing_state == false) {
		allow_smb_signing = false;
		mandatory_signing = false;
	}

	if (signing_state == Required) {
		mandatory_signing = true;
	}

	if (!cli->outbuf || !cli->inbuf)
                goto error;

	memset(cli->outbuf, 0, cli->bufsize);
	memset(cli->inbuf, 0, cli->bufsize);


#if defined(DEVELOPER)
	/* just because we over-allocate, doesn't mean it's right to use it */
	clobber_region(FUNCTION_MACRO, __LINE__, cli->outbuf+cli->bufsize, SAFETY_MARGIN);
	clobber_region(FUNCTION_MACRO, __LINE__, cli->inbuf+cli->bufsize, SAFETY_MARGIN);
#endif

	/* initialise signing */
	cli->signing_state = smb_signing_init(cli,
					      allow_smb_signing,
					      mandatory_signing);
	if (!cli->signing_state) {
		goto error;
	}

	cli->outgoing = tevent_queue_create(cli, "cli_outgoing");
	if (cli->outgoing == NULL) {
		goto error;
	}
	cli->pending = NULL;

	cli->initialised = 1;

	return cli;

        /* Clean up after malloc() error */

 error:

        SAFE_FREE(cli->inbuf);
        SAFE_FREE(cli->outbuf);
	TALLOC_FREE(cli);
        return NULL;
}
struct composite_context *wb_init_domain_send(TALLOC_CTX *mem_ctx,
					      struct wbsrv_service *service,
					      struct wb_dom_info *dom_info)
{
	struct composite_context *result, *ctx;
	struct init_domain_state *state;

	result = composite_create(mem_ctx, service->task->event_ctx);
	if (result == NULL) goto failed;

	state = talloc_zero(result, struct init_domain_state);
	if (state == NULL) goto failed;
	state->ctx = result;
	result->private_data = state;

	state->service = service;

	state->domain = talloc(state, struct wbsrv_domain);
	if (state->domain == NULL) goto failed;

	state->domain->service = service;

	state->domain->info = talloc_reference(state->domain, dom_info);
	if (state->domain->info == NULL) goto failed;

	state->domain->dc_name = dom_info->dc->name;
	state->domain->dc_address = dom_info->dc->address;

	state->domain->libnet_ctx = libnet_context_init(service->task->event_ctx, 
							service->task->lp_ctx);
	if (state->domain->libnet_ctx == NULL) goto failed;
	talloc_steal(state->domain, state->domain->libnet_ctx);

	/* Create a credentials structure */
	state->domain->libnet_ctx->cred = cli_credentials_init(state->domain);
	if (state->domain->libnet_ctx->cred == NULL) goto failed;

	cli_credentials_set_conf(state->domain->libnet_ctx->cred, service->task->lp_ctx);

	/* Connect the machine account to the credentials */
	state->ctx->status =
		cli_credentials_set_machine_account(state->domain->libnet_ctx->cred, state->domain->libnet_ctx->lp_ctx);
	if (!NT_STATUS_IS_OK(state->ctx->status)) goto failed;

	state->domain->netlogon_binding = init_domain_binding(state, &ndr_table_netlogon);

	state->domain->netlogon_pipe = NULL;

	state->domain->netlogon_queue = tevent_queue_create(state->domain,
							    "netlogon_queue");
	if (state->domain->netlogon_queue == NULL) goto failed;

	/* We start the queue when the connection is usable */
	tevent_queue_stop(state->domain->netlogon_queue);

	if ((!cli_credentials_is_anonymous(state->domain->libnet_ctx->cred)) &&
	    ((lpcfg_server_role(service->task->lp_ctx) == ROLE_DOMAIN_MEMBER) ||
	     (lpcfg_server_role(service->task->lp_ctx) == ROLE_ACTIVE_DIRECTORY_DC)) &&
	    (dom_sid_equal(state->domain->info->sid,
			   state->service->primary_sid))) {
		uint32_t flags = DCERPC_SCHANNEL | DCERPC_SCHANNEL_AUTO;

		/* For debugging, it can be a real pain if all the traffic is encrypted */
		if (lpcfg_winbind_sealed_pipes(service->task->lp_ctx)) {
			flags |= DCERPC_SIGN | DCERPC_SEAL;
		} else {
			flags |= DCERPC_SIGN;
		}
		state->ctx->status = dcerpc_binding_set_flags(state->domain->netlogon_binding,
							      flags, 0);
		if (!NT_STATUS_IS_OK(state->ctx->status)) goto failed;
	}

	/* No encryption on anonymous pipes */

	ctx = dcerpc_pipe_connect_b_send(state, state->domain->netlogon_binding, 
					 &ndr_table_netlogon,
					 state->domain->libnet_ctx->cred,
					 service->task->event_ctx,
					 service->task->lp_ctx);
	
	if (composite_nomem(ctx, state->ctx)) {
		goto failed;
	}
	
	composite_continue(state->ctx, ctx, init_domain_recv_netlogonpipe,
			   state);
	return result;
 failed:
	talloc_free(result);
	return NULL;
}
Ejemplo n.º 15
0
Archivo: cldap.c Proyecto: gojdic/samba
/*
  initialise a cldap_sock
*/
NTSTATUS cldap_socket_init(TALLOC_CTX *mem_ctx,
			   struct tevent_context *ev,
			   const struct tsocket_address *local_addr,
			   const struct tsocket_address *remote_addr,
			   struct cldap_socket **_cldap)
{
	struct cldap_socket *c = NULL;
	struct tsocket_address *any = NULL;
	NTSTATUS status;
	int ret;

	c = talloc_zero(mem_ctx, struct cldap_socket);
	if (!c) {
		goto nomem;
	}

	if (!ev) {
		ev = tevent_context_init(c);
		if (!ev) {
			goto nomem;
		}
		c->event.allow_poll = true;
	}
	c->event.ctx = ev;

	if (!local_addr) {
		ret = tsocket_address_inet_from_strings(c, "ipv4",
							NULL, 0,
							&any);
		if (ret != 0) {
			status = map_nt_error_from_unix(errno);
			goto nterror;
		}
		local_addr = any;
	}

	c->searches.idr = idr_init(c);
	if (!c->searches.idr) {
		goto nomem;
	}

	ret = tdgram_inet_udp_socket(local_addr, remote_addr,
				     c, &c->sock);
	if (ret != 0) {
		status = map_nt_error_from_unix(errno);
		goto nterror;
	}
	talloc_free(any);

	if (remote_addr) {
		c->connected = true;
	}

	c->send_queue = tevent_queue_create(c, "cldap_send_queue");
	if (!c->send_queue) {
		goto nomem;
	}

	talloc_set_destructor(c, cldap_socket_destructor);

	*_cldap = c;
	return NT_STATUS_OK;

nomem:
	status = NT_STATUS_NO_MEMORY;
nterror:
	talloc_free(c);
	return status;
}