Esempio n. 1
0
/*
  test that a server responds correctly to attempted registrations of its name
*/
static bool nbt_register_own(struct torture_context *tctx)
{
	struct nbt_name_register io;
	NTSTATUS status;
	struct nbt_name_socket *nbtsock = nbt_name_socket_init(tctx, NULL);
	struct socket_address *socket_address;
	struct nbt_name name;
	const char *address;
	const char *myaddress;

	if (!torture_nbt_get_name(tctx, &name, &address))
		return false;

	myaddress = iface_best_ip(address);

	socket_address = socket_address_from_strings(tctx, nbtsock->sock->backend_name,
						     myaddress, 0);
	torture_assert(tctx, socket_address != NULL, "Unable to get address");

	status = socket_listen(nbtsock->sock, socket_address, 0, 0);
	torture_assert_ntstatus_ok(tctx, status, 
				"socket_listen for nbt_register_own failed");

	torture_comment(tctx, "Testing name defense to name registration\n");

	io.in.name = name;
	io.in.dest_addr = address;
	io.in.address = myaddress;
	io.in.nb_flags = NBT_NODE_B | NBT_NM_ACTIVE;
	io.in.register_demand = False;
	io.in.broadcast = True;
	io.in.multi_homed = False;
	io.in.ttl = 1234;
	io.in.timeout = 3;
	io.in.retries = 0;
	
	status = nbt_name_register(nbtsock, tctx, &io);
	torture_assert_ntstatus_ok(tctx, status, 
				talloc_asprintf(tctx, "Bad response from %s for name register",
		       address));
	
	CHECK_STRING(tctx, io.out.name.name, name.name);
	CHECK_VALUE(tctx, io.out.name.type, name.type);
	CHECK_VALUE(tctx, io.out.rcode, NBT_RCODE_ACT);

	/* check a register demand */
	io.in.address = myaddress;
	io.in.register_demand = True;

	status = nbt_name_register(nbtsock, tctx, &io);

	torture_assert_ntstatus_ok(tctx, status, 
				talloc_asprintf(tctx, "Bad response from %s for name register demand", address));
	
	CHECK_STRING(tctx, io.out.name.name, name.name);
	CHECK_VALUE(tctx, io.out.name.type, name.type);
	CHECK_VALUE(tctx, io.out.rcode, NBT_RCODE_ACT);

	return true;
}
Esempio n. 2
0
/*
  start listening on the given address
*/
static NTSTATUS nbtd_add_socket(struct nbtd_server *nbtsrv, 
				struct loadparm_context *lp_ctx,
				const char *bind_address, 
				const char *address, 
				const char *bcast, 
				const char *netmask)
{
	struct nbtd_interface *iface;
	NTSTATUS status;
	struct socket_address *bcast_address;
	struct socket_address *unicast_address;

	DEBUG(6,("nbtd_add_socket(%s, %s, %s, %s)\n", bind_address, address, bcast, netmask));

	/*
	  we actually create two sockets. One listens on the broadcast address
	  for the interface, and the other listens on our specific address. This
	  allows us to run with "bind interfaces only" while still receiving 
	  broadcast addresses, and also simplifies matching incoming requests 
	  to interfaces
	*/

	iface = talloc(nbtsrv, struct nbtd_interface);
	NT_STATUS_HAVE_NO_MEMORY(iface);

	iface->nbtsrv        = nbtsrv;
	iface->bcast_address = talloc_steal(iface, bcast);
	iface->ip_address    = talloc_steal(iface, address);
	iface->netmask       = talloc_steal(iface, netmask);
	iface->names         = NULL;
	iface->wack_queue    = NULL;

	if (strcmp(netmask, "0.0.0.0") != 0) {
		struct nbt_name_socket *bcast_nbtsock;

		/* listen for broadcasts on port 137 */
		bcast_nbtsock = nbt_name_socket_init(iface, nbtsrv->task->event_ctx, lp_iconv_convenience(nbtsrv->task->lp_ctx));
		if (!bcast_nbtsock) {
			talloc_free(iface);
			return NT_STATUS_NO_MEMORY;
		}

		bcast_address = socket_address_from_strings(bcast_nbtsock, bcast_nbtsock->sock->backend_name, 
							    bcast, lp_nbt_port(lp_ctx));
		if (!bcast_address) {
			talloc_free(iface);
			return NT_STATUS_NO_MEMORY;
		}

		status = socket_listen(bcast_nbtsock->sock, bcast_address, 0, 0);
		if (!NT_STATUS_IS_OK(status)) {
			DEBUG(0,("Failed to bind to %s:%d - %s\n", 
				 bcast, lp_nbt_port(lp_ctx), nt_errstr(status)));
			talloc_free(iface);
			return status;
		}
		talloc_free(bcast_address);

		nbt_set_incoming_handler(bcast_nbtsock, nbtd_request_handler, iface);
	}

	/* listen for unicasts on port 137 */
	iface->nbtsock = nbt_name_socket_init(iface, nbtsrv->task->event_ctx, 
					      lp_iconv_convenience(nbtsrv->task->lp_ctx));
	if (!iface->nbtsock) {
		talloc_free(iface);
		return NT_STATUS_NO_MEMORY;
	}

	unicast_address = socket_address_from_strings(iface->nbtsock, 
						      iface->nbtsock->sock->backend_name, 
						      bind_address, lp_nbt_port(lp_ctx));

	status = socket_listen(iface->nbtsock->sock, unicast_address, 0, 0);
	if (!NT_STATUS_IS_OK(status)) {
		DEBUG(0,("Failed to bind to %s:%d - %s\n", 
			 bind_address, lp_nbt_port(lp_ctx), nt_errstr(status)));
		talloc_free(iface);
		return status;
	}
	talloc_free(unicast_address);

	nbt_set_incoming_handler(iface->nbtsock, nbtd_request_handler, iface);
	nbt_set_unexpected_handler(iface->nbtsock, nbtd_unexpected_handler, iface);

	/* also setup the datagram listeners */
	status = nbtd_dgram_setup(iface, bind_address);
	if (!NT_STATUS_IS_OK(status)) {
		DEBUG(0,("Failed to setup dgram listen on %s - %s\n", 
			 bind_address, nt_errstr(status)));
		talloc_free(iface);
		return status;
	}
	
	if (strcmp(netmask, "0.0.0.0") == 0) {
		DLIST_ADD(nbtsrv->bcast_interface, iface);
	} else {
		DLIST_ADD(nbtsrv->interfaces, iface);
	}

	return NT_STATUS_OK;
}
Esempio n. 3
0
static bool process_one(struct loadparm_context *lp_ctx, struct tevent_context *ev,
			struct interface *ifaces, const char *name, int nbt_port)
{
	TALLOC_CTX *tmp_ctx = talloc_new(NULL);
	enum nbt_name_type node_type = NBT_NAME_CLIENT;
	char *node_name, *p;
	struct socket_address *all_zero_addr;
	struct nbt_name_socket *nbtsock;
	NTSTATUS status = NT_STATUS_OK;
	bool ret = true;

	if (!options.case_sensitive) {
		name = strupper_talloc(tmp_ctx, name);
	}
	
	if (options.find_master) {
		node_type = NBT_NAME_MASTER;
		if (*name == '-' || *name == '_') {
			name = "\01\02__MSBROWSE__\02";
			node_type = NBT_NAME_MS;
		}
	}

	p = strchr(name, '#');
	if (p) {
		node_name = talloc_strndup(tmp_ctx, name, PTR_DIFF(p,name));
		node_type = (enum nbt_name_type)strtol(p+1, NULL, 16);
	} else {
		node_name = talloc_strdup(tmp_ctx, name);
	}

	nbtsock = nbt_name_socket_init(tmp_ctx, ev, lp_iconv_convenience(lp_ctx));
	
	if (options.root_port) {
		all_zero_addr = socket_address_from_strings(tmp_ctx, nbtsock->sock->backend_name, 
							    "0.0.0.0", NBT_NAME_SERVICE_PORT);
		
		if (!all_zero_addr) {
			talloc_free(tmp_ctx);
			return false;
		}

		status = socket_listen(nbtsock->sock, all_zero_addr, 0, 0);
		if (!NT_STATUS_IS_OK(status)) {
			printf("Failed to bind to local port 137 - %s\n", nt_errstr(status));
			talloc_free(tmp_ctx);
			return false;
		}
	}

	if (options.lookup_by_ip) {
		ret = do_node_status(nbtsock, name, nbt_port);
		talloc_free(tmp_ctx);
		return ret;
	}

	if (options.broadcast_address) {
		status = do_node_query(nbtsock, options.broadcast_address, nbt_port,
				       node_name, node_type, true);
	} else if (options.unicast_address) {
		status = do_node_query(nbtsock, options.unicast_address, 
				       nbt_port, node_name, node_type, false);
	} else {
		int i, num_interfaces;

		num_interfaces = iface_count(ifaces);
		for (i=0;i<num_interfaces;i++) {
			const char *bcast = iface_n_bcast(ifaces, i);
			if (bcast == NULL) continue;
			status = do_node_query(nbtsock, bcast, nbt_port, 
					       node_name, node_type, true);
			if (NT_STATUS_IS_OK(status)) break;
		}
	}

	if (!NT_STATUS_IS_OK(status)) {
		printf("Lookup failed - %s\n", nt_errstr(status));
		ret = false;
	}

	talloc_free(tmp_ctx);
	return ret;
}
Esempio n. 4
0
struct nbt_name_socket *torture_init_nbt_socket(struct torture_context *tctx)
{
	return nbt_name_socket_init(tctx, tctx->ev);
}