mirror of
https://github.com/samba-team/samba.git
synced 2025-07-06 08:59:08 +03:00
r3278: - rewrote the client side rpc connection code to use lib/socket/
rather than doing everything itself. This greatly simplifies the
code, although I really don't like the socket_recv() interface (it
always allocates memory for you, which means an extra memcpy in this
code)
- fixed several bugs in the socket_ipv4.c code, in particular client
side code used a non-blocking connect but didn't handle EINPROGRESS,
so it had no chance of working. Also fixed the error codes, using
map_nt_error_from_unix()
- cleaned up and expanded map_nt_error_from_unix()
- changed interpret_addr2() to not take a mem_ctx. It makes absolutely
no sense to allocate a fixed size 4 byte structure like this. Dozens
of places in the code were also using interpret_addr2() incorrectly
(precisely because the allocation made no sense)
(This used to be commit 7f2c771b0e
)
This commit is contained in:
committed by
Gerald (Jerry) Carter
parent
5ae4481161
commit
9d055846f2
@ -79,7 +79,7 @@ static NTSTATUS rpc_resolve_dc(const char *server,
|
|||||||
struct in_addr *dest_ip)
|
struct in_addr *dest_ip)
|
||||||
{
|
{
|
||||||
if (is_ipaddress(server)) {
|
if (is_ipaddress(server)) {
|
||||||
struct in_addr to_ip = *interpret_addr2(server);
|
struct in_addr to_ip = interpret_addr2(server);
|
||||||
|
|
||||||
/* we need to know the machines netbios name - this is a lousy
|
/* we need to know the machines netbios name - this is a lousy
|
||||||
way to find it, but until we have a RPC call that does this
|
way to find it, but until we have a RPC call that does this
|
||||||
|
@ -787,7 +787,7 @@ static void parse_mount_smb(int argc, char **argv)
|
|||||||
} else if(!strcmp(opts, "debug")) {
|
} else if(!strcmp(opts, "debug")) {
|
||||||
DEBUGLEVEL = val;
|
DEBUGLEVEL = val;
|
||||||
} else if(!strcmp(opts, "ip")) {
|
} else if(!strcmp(opts, "ip")) {
|
||||||
dest_ip = *interpret_addr2(opteq+1);
|
dest_ip = interpret_addr2(opteq+1);
|
||||||
if (is_zero_ip(dest_ip)) {
|
if (is_zero_ip(dest_ip)) {
|
||||||
fprintf(stderr,"Can't resolve address %s\n", opteq+1);
|
fprintf(stderr,"Can't resolve address %s\n", opteq+1);
|
||||||
exit(1);
|
exit(1);
|
||||||
|
@ -110,13 +110,11 @@ static void ldapsrv_init(struct server_service *service,
|
|||||||
add_socket(service, model_ops, ifip);
|
add_socket(service, model_ops, ifip);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
struct in_addr *ifip;
|
struct in_addr ifip;
|
||||||
|
|
||||||
/* Just bind to lp_socket_address() (usually 0.0.0.0) */
|
/* Just bind to lp_socket_address() (usually 0.0.0.0) */
|
||||||
ifip = interpret_addr2(service, lp_socket_address());
|
ifip = interpret_addr2(lp_socket_address());
|
||||||
add_socket(service, model_ops, ifip);
|
add_socket(service, model_ops, &ifip);
|
||||||
|
|
||||||
talloc_destroy(ifip);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -116,7 +116,7 @@ static void interpret_interface(TALLOC_CTX *mem_ctx, const char *token)
|
|||||||
/* maybe it is a DNS name */
|
/* maybe it is a DNS name */
|
||||||
p = strchr_m(token,'/');
|
p = strchr_m(token,'/');
|
||||||
if (!p) {
|
if (!p) {
|
||||||
ip = *interpret_addr2(mem_ctx, token);
|
ip = interpret_addr2(token);
|
||||||
for (i=0;i<total_probed;i++) {
|
for (i=0;i<total_probed;i++) {
|
||||||
if (ip.s_addr == probed_ifaces[i].ip.s_addr &&
|
if (ip.s_addr == probed_ifaces[i].ip.s_addr &&
|
||||||
!ip_equal(allones_ip, probed_ifaces[i].netmask)) {
|
!ip_equal(allones_ip, probed_ifaces[i].netmask)) {
|
||||||
@ -132,10 +132,10 @@ static void interpret_interface(TALLOC_CTX *mem_ctx, const char *token)
|
|||||||
/* parse it into an IP address/netmasklength pair */
|
/* parse it into an IP address/netmasklength pair */
|
||||||
*p++ = 0;
|
*p++ = 0;
|
||||||
|
|
||||||
ip = *interpret_addr2(mem_ctx, token);
|
ip = interpret_addr2(token);
|
||||||
|
|
||||||
if (strlen(p) > 2) {
|
if (strlen(p) > 2) {
|
||||||
nmask = *interpret_addr2(mem_ctx, p);
|
nmask = interpret_addr2(p);
|
||||||
} else {
|
} else {
|
||||||
nmask.s_addr = htonl(((ALLONES >> atoi(p)) ^ ALLONES));
|
nmask.s_addr = htonl(((ALLONES >> atoi(p)) ^ ALLONES));
|
||||||
}
|
}
|
||||||
@ -174,8 +174,8 @@ void load_interfaces(void)
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
allones_ip = *interpret_addr2(mem_ctx, "255.255.255.255");
|
allones_ip = interpret_addr2("255.255.255.255");
|
||||||
loopback_ip = *interpret_addr2(mem_ctx, "127.0.0.1");
|
loopback_ip = interpret_addr2("127.0.0.1");
|
||||||
|
|
||||||
SAFE_FREE(probed_ifaces);
|
SAFE_FREE(probed_ifaces);
|
||||||
|
|
||||||
|
@ -134,7 +134,7 @@ NTSTATUS socket_accept(struct socket_context *sock, struct socket_context **new_
|
|||||||
}
|
}
|
||||||
|
|
||||||
NTSTATUS socket_recv(struct socket_context *sock, TALLOC_CTX *mem_ctx,
|
NTSTATUS socket_recv(struct socket_context *sock, TALLOC_CTX *mem_ctx,
|
||||||
DATA_BLOB *blob, size_t wantlen, uint32_t flags)
|
DATA_BLOB *blob, size_t wantlen, uint32_t flags)
|
||||||
{
|
{
|
||||||
if (sock->type != SOCKET_TYPE_STREAM) {
|
if (sock->type != SOCKET_TYPE_STREAM) {
|
||||||
return NT_STATUS_INVALID_PARAMETER;
|
return NT_STATUS_INVALID_PARAMETER;
|
||||||
|
@ -24,8 +24,7 @@ static NTSTATUS ipv4_tcp_init(struct socket_context *sock)
|
|||||||
{
|
{
|
||||||
sock->fd = socket(PF_INET, SOCK_STREAM, 0);
|
sock->fd = socket(PF_INET, SOCK_STREAM, 0);
|
||||||
if (sock->fd == -1) {
|
if (sock->fd == -1) {
|
||||||
/* TODO: we need to map from errno to NTSTATUS here! */
|
return map_nt_error_from_unix(errno);
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return NT_STATUS_OK;
|
return NT_STATUS_OK;
|
||||||
@ -37,41 +36,34 @@ static void ipv4_tcp_close(struct socket_context *sock)
|
|||||||
}
|
}
|
||||||
|
|
||||||
static NTSTATUS ipv4_tcp_connect(struct socket_context *sock,
|
static NTSTATUS ipv4_tcp_connect(struct socket_context *sock,
|
||||||
const char *my_address, int my_port,
|
const char *my_address, int my_port,
|
||||||
const char *srv_address, int srv_port,
|
const char *srv_address, int srv_port,
|
||||||
uint32_t flags)
|
uint32_t flags)
|
||||||
{
|
{
|
||||||
struct sockaddr_in my_addr;
|
|
||||||
struct sockaddr_in srv_addr;
|
struct sockaddr_in srv_addr;
|
||||||
struct in_addr my_ip;
|
struct in_addr my_ip;
|
||||||
struct in_addr srv_ip;
|
struct in_addr srv_ip;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
ret = inet_aton(my_address, &my_ip);
|
my_ip = interpret_addr2(my_address);
|
||||||
if (ret == 0) {
|
|
||||||
/* not a valid ipv4 address */
|
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
|
||||||
|
|
||||||
ZERO_STRUCT(my_addr);
|
if (my_ip.s_addr != 0 || my_port != 0) {
|
||||||
|
struct sockaddr_in my_addr;
|
||||||
|
ZERO_STRUCT(my_addr);
|
||||||
#ifdef HAVE_SOCK_SIN_LEN
|
#ifdef HAVE_SOCK_SIN_LEN
|
||||||
my_addr.sin_len = sizeof(my_addr);
|
my_addr.sin_len = sizeof(my_addr);
|
||||||
#endif
|
#endif
|
||||||
my_addr.sin_addr = my_ip;
|
my_addr.sin_addr = my_ip;
|
||||||
my_addr.sin_port = htons(my_port);
|
my_addr.sin_port = htons(my_port);
|
||||||
my_addr.sin_family = PF_INET;
|
my_addr.sin_family = PF_INET;
|
||||||
|
|
||||||
ret = inet_aton(srv_address, &srv_ip);
|
ret = bind(sock->fd, (struct sockaddr *)&my_addr, sizeof(my_addr));
|
||||||
if (ret == 0) {
|
if (ret == -1) {
|
||||||
/* not a valid ipv4 address */
|
return map_nt_error_from_unix(errno);
|
||||||
return NT_STATUS_FOOBAR;
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = bind(sock->fd, (struct sockaddr *)&my_addr, sizeof(my_addr));
|
srv_ip = interpret_addr2(srv_address);
|
||||||
if (ret == -1) {
|
|
||||||
/* TODO: we need to map from errno to NTSTATUS here! */
|
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
|
||||||
|
|
||||||
ZERO_STRUCT(srv_addr);
|
ZERO_STRUCT(srv_addr);
|
||||||
#ifdef HAVE_SOCK_SIN_LEN
|
#ifdef HAVE_SOCK_SIN_LEN
|
||||||
@ -81,20 +73,18 @@ static NTSTATUS ipv4_tcp_connect(struct socket_context *sock,
|
|||||||
srv_addr.sin_port = htons(srv_port);
|
srv_addr.sin_port = htons(srv_port);
|
||||||
srv_addr.sin_family = PF_INET;
|
srv_addr.sin_family = PF_INET;
|
||||||
|
|
||||||
|
ret = connect(sock->fd, (const struct sockaddr *)&srv_addr, sizeof(srv_addr));
|
||||||
|
if (ret == -1) {
|
||||||
|
return map_nt_error_from_unix(errno);
|
||||||
|
}
|
||||||
|
|
||||||
if (!(flags & SOCKET_FLAG_BLOCK)) {
|
if (!(flags & SOCKET_FLAG_BLOCK)) {
|
||||||
ret = set_blocking(sock->fd, False);
|
ret = set_blocking(sock->fd, False);
|
||||||
if (ret == -1) {
|
if (ret == -1) {
|
||||||
/* TODO: we need to map from errno to NTSTATUS here! */
|
return map_nt_error_from_unix(errno);
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = connect(sock->fd, (const struct sockaddr *)&srv_addr, sizeof(srv_addr));
|
|
||||||
if (ret == -1) {
|
|
||||||
/* TODO: we need to map from errno to NTSTATUS here! */
|
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
|
||||||
|
|
||||||
sock->state = SOCKET_STATE_CLIENT_CONNECTED;
|
sock->state = SOCKET_STATE_CLIENT_CONNECTED;
|
||||||
|
|
||||||
return NT_STATUS_OK;
|
return NT_STATUS_OK;
|
||||||
@ -108,11 +98,7 @@ static NTSTATUS ipv4_tcp_listen(struct socket_context *sock,
|
|||||||
struct in_addr ip_addr;
|
struct in_addr ip_addr;
|
||||||
int ret;
|
int ret;
|
||||||
|
|
||||||
ret = inet_aton(my_address, &ip_addr);
|
ip_addr = interpret_addr2(my_address);
|
||||||
if (ret == 0) {
|
|
||||||
/* not a valid ipv4 address */
|
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
|
||||||
|
|
||||||
ZERO_STRUCT(my_addr);
|
ZERO_STRUCT(my_addr);
|
||||||
#ifdef HAVE_SOCK_SIN_LEN
|
#ifdef HAVE_SOCK_SIN_LEN
|
||||||
@ -124,21 +110,18 @@ static NTSTATUS ipv4_tcp_listen(struct socket_context *sock,
|
|||||||
|
|
||||||
ret = bind(sock->fd, (struct sockaddr *)&my_addr, sizeof(my_addr));
|
ret = bind(sock->fd, (struct sockaddr *)&my_addr, sizeof(my_addr));
|
||||||
if (ret == -1) {
|
if (ret == -1) {
|
||||||
/* TODO: we need to map from errno to NTSTATUS here! */
|
return map_nt_error_from_unix(errno);
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ret = listen(sock->fd, queue_size);
|
ret = listen(sock->fd, queue_size);
|
||||||
if (ret == -1) {
|
if (ret == -1) {
|
||||||
/* TODO: we need to map from errno to NTSTATUS here! */
|
return map_nt_error_from_unix(errno);
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!(flags & SOCKET_FLAG_BLOCK)) {
|
if (!(flags & SOCKET_FLAG_BLOCK)) {
|
||||||
ret = set_blocking(sock->fd, False);
|
ret = set_blocking(sock->fd, False);
|
||||||
if (ret == -1) {
|
if (ret == -1) {
|
||||||
/* TODO: we need to map from errno to NTSTATUS here! */
|
return map_nt_error_from_unix(errno);
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -155,8 +138,7 @@ static NTSTATUS ipv4_tcp_accept(struct socket_context *sock, struct socket_conte
|
|||||||
|
|
||||||
new_fd = accept(sock->fd, (struct sockaddr *)&cli_addr, &cli_addr_len);
|
new_fd = accept(sock->fd, (struct sockaddr *)&cli_addr, &cli_addr_len);
|
||||||
if (new_fd == -1) {
|
if (new_fd == -1) {
|
||||||
/* TODO: we need to map from errno to NTSTATUS here! */
|
return map_nt_error_from_unix(errno);
|
||||||
return NT_STATUS_FOOBAR;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* TODO: we could add a 'accept_check' hook here
|
/* TODO: we could add a 'accept_check' hook here
|
||||||
@ -257,34 +239,7 @@ static NTSTATUS ipv4_tcp_send(struct socket_context *sock, TALLOC_CTX *mem_ctx,
|
|||||||
|
|
||||||
len = send(sock->fd, blob->data, blob->length, flgs);
|
len = send(sock->fd, blob->data, blob->length, flgs);
|
||||||
if (len == -1) {
|
if (len == -1) {
|
||||||
NTSTATUS status = NT_STATUS_UNSUCCESSFUL;
|
return map_nt_error_from_unix(errno);
|
||||||
switch (errno) {
|
|
||||||
case EBADF:
|
|
||||||
case ENOTSOCK:
|
|
||||||
case EFAULT:
|
|
||||||
case EINVAL:
|
|
||||||
status = NT_STATUS_INVALID_PARAMETER;
|
|
||||||
break;
|
|
||||||
case EMSGSIZE:
|
|
||||||
status = NT_STATUS_INVALID_BUFFER_SIZE;
|
|
||||||
break;
|
|
||||||
case EAGAIN:
|
|
||||||
/*case EWOULDBLOCK: this is an alis of EAGAIN --metze */
|
|
||||||
case EINTR:
|
|
||||||
*sendlen = 0;
|
|
||||||
status = STATUS_MORE_ENTRIES;
|
|
||||||
break;
|
|
||||||
case ENOBUFS:
|
|
||||||
status = NT_STATUS_FOOBAR;
|
|
||||||
break;
|
|
||||||
case ENOMEM:
|
|
||||||
status = NT_STATUS_NO_MEMORY;
|
|
||||||
break;
|
|
||||||
case EPIPE:
|
|
||||||
status = NT_STATUS_CONNECTION_DISCONNECTED;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
return status;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
*sendlen = len;
|
*sendlen = len;
|
||||||
|
@ -30,31 +30,7 @@
|
|||||||
*/
|
*/
|
||||||
static NTSTATUS unixdom_error(int ernum)
|
static NTSTATUS unixdom_error(int ernum)
|
||||||
{
|
{
|
||||||
switch (ernum) {
|
return map_nt_error_from_unix(ernum);
|
||||||
case EBADF:
|
|
||||||
case ENOTCONN:
|
|
||||||
case ENOTSOCK:
|
|
||||||
case EFAULT:
|
|
||||||
case EINVAL:
|
|
||||||
return NT_STATUS_INVALID_PARAMETER;
|
|
||||||
case EAGAIN:
|
|
||||||
case EINTR:
|
|
||||||
return STATUS_MORE_ENTRIES;
|
|
||||||
case ECONNREFUSED:
|
|
||||||
return NT_STATUS_CONNECTION_REFUSED;
|
|
||||||
case ENOBUFS:
|
|
||||||
case ENOMEM:
|
|
||||||
return NT_STATUS_NO_MEMORY;
|
|
||||||
case ENFILE:
|
|
||||||
case EMFILE:
|
|
||||||
return NT_STATUS_INSUFFICIENT_RESOURCES;
|
|
||||||
case EPIPE:
|
|
||||||
return NT_STATUS_CONNECTION_DISCONNECTED;
|
|
||||||
case EMSGSIZE:
|
|
||||||
return NT_STATUS_INVALID_BUFFER_SIZE;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NT_STATUS_UNSUCCESSFUL;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static NTSTATUS unixdom_init(struct socket_context *sock)
|
static NTSTATUS unixdom_init(struct socket_context *sock)
|
||||||
|
@ -406,16 +406,18 @@ BOOL is_ipaddress(const char *str)
|
|||||||
/****************************************************************************
|
/****************************************************************************
|
||||||
Interpret an internet address or name into an IP address in 4 byte form.
|
Interpret an internet address or name into an IP address in 4 byte form.
|
||||||
****************************************************************************/
|
****************************************************************************/
|
||||||
|
|
||||||
uint32_t interpret_addr(const char *str)
|
uint32_t interpret_addr(const char *str)
|
||||||
{
|
{
|
||||||
struct hostent *hp;
|
struct hostent *hp;
|
||||||
uint32_t res;
|
uint32_t res;
|
||||||
|
|
||||||
if (strcmp(str,"0.0.0.0") == 0)
|
if (str == NULL ||
|
||||||
return(0);
|
strcmp(str,"0.0.0.0") == 0) {
|
||||||
if (strcmp(str,"255.255.255.255") == 0)
|
return 0;
|
||||||
return(0xFFFFFFFF);
|
}
|
||||||
|
if (strcmp(str,"255.255.255.255") == 0) {
|
||||||
|
return 0xFFFFFFFF;
|
||||||
|
}
|
||||||
|
|
||||||
/* if it's in the form of an IP address then get the lib to interpret it */
|
/* if it's in the form of an IP address then get the lib to interpret it */
|
||||||
if (is_ipaddress(str)) {
|
if (is_ipaddress(str)) {
|
||||||
@ -444,16 +446,12 @@ uint32_t interpret_addr(const char *str)
|
|||||||
/*******************************************************************
|
/*******************************************************************
|
||||||
A convenient addition to interpret_addr().
|
A convenient addition to interpret_addr().
|
||||||
******************************************************************/
|
******************************************************************/
|
||||||
|
struct in_addr interpret_addr2(const char *str)
|
||||||
struct in_addr *interpret_addr2(TALLOC_CTX *mem_ctx, const char *str)
|
|
||||||
{
|
{
|
||||||
struct in_addr *ret;
|
struct in_addr ret;
|
||||||
uint32_t a = interpret_addr(str);
|
uint32_t a = interpret_addr(str);
|
||||||
|
ret.s_addr = a;
|
||||||
ret = talloc(mem_ctx, sizeof(struct in_addr));
|
return ret;
|
||||||
if (!ret) return NULL;
|
|
||||||
ret->s_addr = a;
|
|
||||||
return(ret);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*******************************************************************
|
/*******************************************************************
|
||||||
|
@ -408,14 +408,14 @@ int open_udp_socket(const char *host, int port)
|
|||||||
int type = SOCK_DGRAM;
|
int type = SOCK_DGRAM;
|
||||||
struct sockaddr_in sock_out;
|
struct sockaddr_in sock_out;
|
||||||
int res;
|
int res;
|
||||||
struct in_addr *addr;
|
struct in_addr addr;
|
||||||
TALLOC_CTX *mem_ctx;
|
TALLOC_CTX *mem_ctx;
|
||||||
|
|
||||||
mem_ctx = talloc_init("open_udp_socket");
|
mem_ctx = talloc_init("open_udp_socket");
|
||||||
if (!mem_ctx) {
|
if (!mem_ctx) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
addr = interpret_addr2(mem_ctx, host);
|
addr = interpret_addr2(host);
|
||||||
|
|
||||||
res = socket(PF_INET, type, 0);
|
res = socket(PF_INET, type, 0);
|
||||||
if (res == -1) {
|
if (res == -1) {
|
||||||
@ -423,7 +423,7 @@ int open_udp_socket(const char *host, int port)
|
|||||||
}
|
}
|
||||||
|
|
||||||
memset((char *)&sock_out,'\0',sizeof(sock_out));
|
memset((char *)&sock_out,'\0',sizeof(sock_out));
|
||||||
putip((char *)&sock_out.sin_addr,(char *)addr);
|
putip((char *)&sock_out.sin_addr,(char *)&addr);
|
||||||
sock_out.sin_port = htons(port);
|
sock_out.sin_port = htons(port);
|
||||||
sock_out.sin_family = PF_INET;
|
sock_out.sin_family = PF_INET;
|
||||||
|
|
||||||
@ -508,7 +508,7 @@ char *get_socket_name(TALLOC_CTX *mem_ctx, int fd, BOOL force_lookup)
|
|||||||
name_buf = talloc_strdup(mem_ctx, "UNKNOWN");
|
name_buf = talloc_strdup(mem_ctx, "UNKNOWN");
|
||||||
if (fd == -1) return name_buf;
|
if (fd == -1) return name_buf;
|
||||||
|
|
||||||
addr = *interpret_addr2(mem_ctx, p);
|
addr = interpret_addr2(p);
|
||||||
|
|
||||||
/* Look up the remote host name. */
|
/* Look up the remote host name. */
|
||||||
if ((hp = gethostbyaddr((char *)&addr.s_addr, sizeof(addr.s_addr), AF_INET)) == 0) {
|
if ((hp = gethostbyaddr((char *)&addr.s_addr, sizeof(addr.s_addr), AF_INET)) == 0) {
|
||||||
|
@ -174,11 +174,11 @@ static void parse_ip(TALLOC_CTX *mem_ctx, struct tagged_ip *ip, const char *str)
|
|||||||
char *s = strchr(str, ':');
|
char *s = strchr(str, ':');
|
||||||
if (!s) {
|
if (!s) {
|
||||||
fstrcpy(ip->tag, "*");
|
fstrcpy(ip->tag, "*");
|
||||||
ip->ip = *interpret_addr2(mem_ctx, str);
|
ip->ip = interpret_addr2(str);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
ip->ip = *interpret_addr2(mem_ctx, s+1);
|
ip->ip = interpret_addr2(s+1);
|
||||||
fstrcpy(ip->tag, str);
|
fstrcpy(ip->tag, str);
|
||||||
s = strchr(ip->tag, ':');
|
s = strchr(ip->tag, ':');
|
||||||
if (s) *s = 0;
|
if (s) *s = 0;
|
||||||
|
@ -64,7 +64,7 @@ static BOOL ads_try_connect(ADS_STRUCT *ads, const char *server, uint_t port)
|
|||||||
return False;
|
return False;
|
||||||
}
|
}
|
||||||
ads->ldap_port = port;
|
ads->ldap_port = port;
|
||||||
ads->ldap_ip = *interpret_addr2(srv);
|
ads->ldap_ip = interpret_addr2(srv);
|
||||||
free(srv);
|
free(srv);
|
||||||
|
|
||||||
return True;
|
return True;
|
||||||
|
@ -522,7 +522,7 @@ BOOL getlmhostsent( TALLOC_CTX *mem_ctx,
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
*ipaddr = *interpret_addr2(mem_ctx, ip);
|
*ipaddr = interpret_addr2(ip);
|
||||||
|
|
||||||
/* Extra feature. If the name ends in '#XX', where XX is a hex number,
|
/* Extra feature. If the name ends in '#XX', where XX is a hex number,
|
||||||
then only add that name type. */
|
then only add that name type. */
|
||||||
@ -643,7 +643,7 @@ BOOL resolve_wins(TALLOC_CTX *mem_ctx, const char *name, int name_type,
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* the address we will be sending from */
|
/* the address we will be sending from */
|
||||||
src_ip = *interpret_addr2(mem_ctx, lp_socket_address());
|
src_ip = interpret_addr2(lp_socket_address());
|
||||||
|
|
||||||
/* in the worst case we will try every wins server with every
|
/* in the worst case we will try every wins server with every
|
||||||
tag! */
|
tag! */
|
||||||
@ -900,7 +900,7 @@ BOOL resolve_name(TALLOC_CTX *mem_ctx, const char *name, struct in_addr *return_
|
|||||||
int count = 0;
|
int count = 0;
|
||||||
|
|
||||||
if (is_ipaddress(name)) {
|
if (is_ipaddress(name)) {
|
||||||
*return_ip = *interpret_addr2(mem_ctx, name);
|
*return_ip = interpret_addr2(name);
|
||||||
return True;
|
return True;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1490,66 +1490,69 @@ WERROR ntstatus_to_werror(NTSTATUS error)
|
|||||||
|
|
||||||
struct unix_error_map {
|
struct unix_error_map {
|
||||||
int unix_error;
|
int unix_error;
|
||||||
int dos_class;
|
|
||||||
int dos_code;
|
|
||||||
NTSTATUS nt_error;
|
NTSTATUS nt_error;
|
||||||
};
|
};
|
||||||
|
|
||||||
const struct unix_error_map unix_dos_nt_errmap[] = {
|
const struct unix_error_map unix_nt_errmap[] = {
|
||||||
{ EPERM, ERRDOS, ERRnoaccess, NT_STATUS_ACCESS_DENIED },
|
{ EAGAIN, STATUS_MORE_ENTRIES },
|
||||||
{ EACCES, ERRDOS, ERRnoaccess, NT_STATUS_ACCESS_DENIED },
|
{ EINTR, STATUS_MORE_ENTRIES },
|
||||||
{ ENOENT, ERRDOS, ERRbadfile, NT_STATUS_OBJECT_NAME_NOT_FOUND },
|
{ EINPROGRESS, STATUS_MORE_ENTRIES },
|
||||||
{ ENOTDIR, ERRDOS, ERRbadpath, NT_STATUS_NOT_A_DIRECTORY },
|
{ EPERM, NT_STATUS_ACCESS_DENIED },
|
||||||
{ EIO, ERRHRD, ERRgeneral, NT_STATUS_IO_DEVICE_ERROR },
|
{ EACCES, NT_STATUS_ACCESS_DENIED },
|
||||||
{ EBADF, ERRSRV, ERRsrverror, NT_STATUS_INVALID_HANDLE },
|
{ ENOENT, NT_STATUS_OBJECT_NAME_NOT_FOUND },
|
||||||
{ EINVAL, ERRSRV, ERRsrverror, NT_STATUS_INVALID_HANDLE },
|
{ ENOTDIR, NT_STATUS_NOT_A_DIRECTORY },
|
||||||
{ EEXIST, ERRDOS, ERRfilexists, NT_STATUS_OBJECT_NAME_COLLISION},
|
{ EIO, NT_STATUS_IO_DEVICE_ERROR },
|
||||||
{ ENFILE, ERRDOS, ERRnofids, NT_STATUS_TOO_MANY_OPENED_FILES },
|
{ EBADF, NT_STATUS_INVALID_HANDLE },
|
||||||
{ EMFILE, ERRDOS, ERRnofids, NT_STATUS_TOO_MANY_OPENED_FILES },
|
{ EINVAL, NT_STATUS_INVALID_PARAMETER },
|
||||||
{ ENOSPC, ERRHRD, ERRdiskfull, NT_STATUS_DISK_FULL },
|
{ EEXIST, NT_STATUS_OBJECT_NAME_COLLISION},
|
||||||
{ EISDIR, ERRDOS, ERRbadpath, NT_STATUS_FILE_IS_A_DIRECTORY },
|
{ ENFILE, NT_STATUS_TOO_MANY_OPENED_FILES },
|
||||||
|
{ EMFILE, NT_STATUS_TOO_MANY_OPENED_FILES },
|
||||||
|
{ ENOSPC, NT_STATUS_DISK_FULL },
|
||||||
|
{ EISDIR, NT_STATUS_FILE_IS_A_DIRECTORY },
|
||||||
|
{ ENOTSOCK, NT_STATUS_INVALID_HANDLE },
|
||||||
|
{ EFAULT, NT_STATUS_INVALID_PARAMETER },
|
||||||
|
{ EMSGSIZE, NT_STATUS_INVALID_BUFFER_SIZE },
|
||||||
|
{ ENOBUFS, NT_STATUS_NO_MEMORY },
|
||||||
|
{ ENOMEM, NT_STATUS_NO_MEMORY },
|
||||||
|
{ EPIPE, NT_STATUS_CONNECTION_DISCONNECTED },
|
||||||
|
{ ECONNREFUSED, NT_STATUS_CONNECTION_REFUSED },
|
||||||
|
{ EBUSY, NT_STATUS_SHARING_VIOLATION },
|
||||||
#ifdef EDQUOT
|
#ifdef EDQUOT
|
||||||
{ EDQUOT, ERRHRD, ERRdiskfull, NT_STATUS_DISK_FULL },
|
{ EDQUOT, NT_STATUS_QUOTA_EXCEEDED },
|
||||||
#endif
|
#endif
|
||||||
#ifdef ENOTEMPTY
|
#ifdef ENOTEMPTY
|
||||||
{ ENOTEMPTY, ERRDOS, ERRnoaccess, NT_STATUS_DIRECTORY_NOT_EMPTY },
|
{ ENOTEMPTY, NT_STATUS_DIRECTORY_NOT_EMPTY },
|
||||||
#endif
|
#endif
|
||||||
#ifdef EXDEV
|
#ifdef EXDEV
|
||||||
{ EXDEV, ERRDOS, ERRdiffdevice, NT_STATUS_NOT_SAME_DEVICE },
|
{ EXDEV, NT_STATUS_NOT_SAME_DEVICE },
|
||||||
#endif
|
#endif
|
||||||
#ifdef EROFS
|
#ifdef EROFS
|
||||||
{ EROFS, ERRHRD, ERRnowrite, NT_STATUS_ACCESS_DENIED },
|
{ EROFS, NT_STATUS_MEDIA_WRITE_PROTECTED },
|
||||||
#endif
|
#endif
|
||||||
#ifdef ENAMETOOLONG
|
#ifdef ENAMETOOLONG
|
||||||
{ ENAMETOOLONG, ERRDOS, 206, NT_STATUS_OBJECT_NAME_INVALID },
|
{ ENAMETOOLONG, NT_STATUS_NAME_TOO_LONG },
|
||||||
#endif
|
#endif
|
||||||
#ifdef EFBIG
|
#ifdef EFBIG
|
||||||
{ EFBIG, ERRHRD, ERRdiskfull, NT_STATUS_DISK_FULL },
|
{ EFBIG, NT_STATUS_DISK_FULL },
|
||||||
#endif
|
#endif
|
||||||
#ifdef EFBIG
|
{ 0, NT_STATUS_UNSUCCESSFUL }
|
||||||
{ EBUSY, ERRDOS, ERRbadshare, NT_STATUS_SHARING_VIOLATION },
|
|
||||||
#endif
|
|
||||||
{ 0, 0, 0, NT_STATUS_OK }
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
/*********************************************************************
|
/*********************************************************************
|
||||||
Map an NT error code from a Unix error code.
|
Map an NT error code from a Unix error code.
|
||||||
*********************************************************************/
|
*********************************************************************/
|
||||||
NTSTATUS map_nt_error_from_unix(int unix_error)
|
NTSTATUS map_nt_error_from_unix(int unix_error)
|
||||||
{
|
{
|
||||||
int i = 0;
|
int i;
|
||||||
|
|
||||||
if (unix_error == 0) {
|
|
||||||
return NT_STATUS_UNSUCCESSFUL;
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Look through list */
|
/* Look through list */
|
||||||
while(unix_dos_nt_errmap[i].unix_error != 0) {
|
for (i=0;i<ARRAY_SIZE(unix_nt_errmap);i++) {
|
||||||
if (unix_dos_nt_errmap[i].unix_error == unix_error)
|
if (unix_nt_errmap[i].unix_error == unix_error) {
|
||||||
return unix_dos_nt_errmap[i].nt_error;
|
return unix_nt_errmap[i].nt_error;
|
||||||
i++;
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Default return */
|
/* Default return */
|
||||||
return NT_STATUS_ACCESS_DENIED;
|
return NT_STATUS_UNSUCCESSFUL;
|
||||||
}
|
}
|
||||||
|
@ -34,7 +34,7 @@ struct sock_blob {
|
|||||||
struct sock_private {
|
struct sock_private {
|
||||||
struct event_context *event_ctx;
|
struct event_context *event_ctx;
|
||||||
struct fd_event *fde;
|
struct fd_event *fde;
|
||||||
int fd;
|
struct socket_context *sock;
|
||||||
char *server_name;
|
char *server_name;
|
||||||
uint32_t port;
|
uint32_t port;
|
||||||
|
|
||||||
@ -55,9 +55,9 @@ static void sock_dead(struct dcerpc_pipe *p, NTSTATUS status)
|
|||||||
{
|
{
|
||||||
struct sock_private *sock = p->transport.private;
|
struct sock_private *sock = p->transport.private;
|
||||||
|
|
||||||
if (sock && sock->fd != -1) {
|
if (sock && sock->sock != NULL) {
|
||||||
close(sock->fd);
|
talloc_free(sock->sock);
|
||||||
sock->fd = -1;
|
sock->sock = NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* wipe any pending sends */
|
/* wipe any pending sends */
|
||||||
@ -81,20 +81,19 @@ static void sock_process_send(struct dcerpc_pipe *p)
|
|||||||
|
|
||||||
while (sock->pending_send) {
|
while (sock->pending_send) {
|
||||||
struct sock_blob *blob = sock->pending_send;
|
struct sock_blob *blob = sock->pending_send;
|
||||||
ssize_t ret = write(sock->fd, blob->data.data, blob->data.length);
|
NTSTATUS status;
|
||||||
if (ret == -1) {
|
size_t sent;
|
||||||
if (errno != EAGAIN && errno != EINTR) {
|
status = socket_send(sock->sock, blob, &blob->data, &sent, 0);
|
||||||
sock_dead(p, NT_STATUS_NET_WRITE_FAULT);
|
if (NT_STATUS_IS_ERR(status)) {
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (ret == 0) {
|
|
||||||
sock_dead(p, NT_STATUS_NET_WRITE_FAULT);
|
sock_dead(p, NT_STATUS_NET_WRITE_FAULT);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
if (sent == 0) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
blob->data.data += ret;
|
blob->data.data += sent;
|
||||||
blob->data.length -= ret;
|
blob->data.length -= sent;
|
||||||
|
|
||||||
if (blob->data.length != 0) {
|
if (blob->data.length != 0) {
|
||||||
break;
|
break;
|
||||||
@ -116,7 +115,8 @@ static void sock_process_send(struct dcerpc_pipe *p)
|
|||||||
static void sock_process_recv(struct dcerpc_pipe *p)
|
static void sock_process_recv(struct dcerpc_pipe *p)
|
||||||
{
|
{
|
||||||
struct sock_private *sock = p->transport.private;
|
struct sock_private *sock = p->transport.private;
|
||||||
ssize_t ret;
|
NTSTATUS status;
|
||||||
|
DATA_BLOB blob;
|
||||||
|
|
||||||
if (sock->recv.data.data == NULL) {
|
if (sock->recv.data.data == NULL) {
|
||||||
sock->recv.data = data_blob_talloc(sock, NULL, MIN_HDR_SIZE);
|
sock->recv.data = data_blob_talloc(sock, NULL, MIN_HDR_SIZE);
|
||||||
@ -126,20 +126,19 @@ static void sock_process_recv(struct dcerpc_pipe *p)
|
|||||||
if (sock->recv.received < MIN_HDR_SIZE) {
|
if (sock->recv.received < MIN_HDR_SIZE) {
|
||||||
uint32_t frag_length;
|
uint32_t frag_length;
|
||||||
|
|
||||||
ret = read(sock->fd, sock->recv.data.data,
|
status = socket_recv(sock->sock, sock, &blob, MIN_HDR_SIZE - sock->recv.received, 0);
|
||||||
MIN_HDR_SIZE - sock->recv.received);
|
if (NT_STATUS_IS_ERR(status)) {
|
||||||
if (ret == -1) {
|
|
||||||
if (errno != EAGAIN && errno != EINTR) {
|
|
||||||
sock_dead(p, NT_STATUS_NET_WRITE_FAULT);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (ret == 0) {
|
|
||||||
sock_dead(p, NT_STATUS_NET_WRITE_FAULT);
|
sock_dead(p, NT_STATUS_NET_WRITE_FAULT);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
if (blob.length == 0) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
sock->recv.received += ret;
|
memcpy(sock->recv.data.data + sock->recv.received,
|
||||||
|
blob.data, blob.length);
|
||||||
|
sock->recv.received += blob.length;
|
||||||
|
talloc_free(blob.data);
|
||||||
|
|
||||||
if (sock->recv.received != MIN_HDR_SIZE) {
|
if (sock->recv.received != MIN_HDR_SIZE) {
|
||||||
return;
|
return;
|
||||||
@ -156,20 +155,18 @@ static void sock_process_recv(struct dcerpc_pipe *p)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/* read in the rest of the packet */
|
/* read in the rest of the packet */
|
||||||
ret = read(sock->fd, sock->recv.data.data + sock->recv.received,
|
status = socket_recv(sock->sock, sock, &blob, sock->recv.data.length - sock->recv.received, 0);
|
||||||
sock->recv.data.length - sock->recv.received);
|
if (NT_STATUS_IS_ERR(status)) {
|
||||||
if (ret == -1) {
|
|
||||||
if (errno != EAGAIN && errno != EINTR) {
|
|
||||||
sock_dead(p, NT_STATUS_NET_WRITE_FAULT);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (ret == 0) {
|
|
||||||
sock_dead(p, NT_STATUS_NET_WRITE_FAULT);
|
sock_dead(p, NT_STATUS_NET_WRITE_FAULT);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
if (blob.length == 0) {
|
||||||
sock->recv.received += ret;
|
return;
|
||||||
|
}
|
||||||
|
memcpy(sock->recv.data.data + sock->recv.received,
|
||||||
|
blob.data, blob.length);
|
||||||
|
sock->recv.received += blob.length;
|
||||||
|
talloc_free(blob.data);
|
||||||
|
|
||||||
if (sock->recv.received != sock->recv.data.length) {
|
if (sock->recv.received != sock->recv.data.length) {
|
||||||
return;
|
return;
|
||||||
@ -199,7 +196,7 @@ static void sock_io_handler(struct event_context *ev, struct fd_event *fde,
|
|||||||
sock_process_send(p);
|
sock_process_send(p);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (sock->fd == -1) {
|
if (sock->sock == NULL) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -282,67 +279,50 @@ static const char *sock_peer_name(struct dcerpc_pipe *p)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
open a rpc connection to a named pipe
|
open a rpc connection using the generic socket library
|
||||||
*/
|
*/
|
||||||
NTSTATUS dcerpc_pipe_open_tcp(struct dcerpc_pipe **p,
|
static NTSTATUS dcerpc_pipe_open_socket(struct dcerpc_pipe **p,
|
||||||
const char *server,
|
const char *server,
|
||||||
uint32_t port,
|
uint32_t port,
|
||||||
int family)
|
const char *type,
|
||||||
|
enum dcerpc_transport_t transport)
|
||||||
{
|
{
|
||||||
struct sock_private *sock;
|
struct sock_private *sock;
|
||||||
int fd, gai_err;
|
struct socket_context *socket_ctx;
|
||||||
struct fd_event fde;
|
struct fd_event fde;
|
||||||
struct addrinfo hints, *res, *tmpres;
|
NTSTATUS status;
|
||||||
char portname[16];
|
|
||||||
|
|
||||||
if (port == 0) {
|
if (port == 0) {
|
||||||
port = EPMAPPER_PORT;
|
port = EPMAPPER_PORT;
|
||||||
}
|
}
|
||||||
|
|
||||||
memset(&hints, 0, sizeof(struct addrinfo));
|
|
||||||
|
|
||||||
hints.ai_family = family;
|
|
||||||
hints.ai_socktype = SOCK_STREAM;
|
|
||||||
|
|
||||||
snprintf(portname, sizeof(portname)-1, "%d", port);
|
|
||||||
|
|
||||||
gai_err = getaddrinfo(server, portname, &hints, &res);
|
|
||||||
if (gai_err < 0)
|
|
||||||
{
|
|
||||||
DEBUG(0, ("Unable to connect to %s:%d : %s\n", server, port, gai_strerror(gai_err)));
|
|
||||||
return NT_STATUS_BAD_NETWORK_NAME;
|
|
||||||
}
|
|
||||||
|
|
||||||
tmpres = res;
|
|
||||||
|
|
||||||
while (tmpres) {
|
|
||||||
fd = socket(tmpres->ai_family, tmpres->ai_socktype, tmpres->ai_protocol);
|
|
||||||
|
|
||||||
if(fd >= 0) {
|
|
||||||
if (connect(fd, tmpres->ai_addr, tmpres->ai_addrlen) == 0)
|
|
||||||
break;
|
|
||||||
fd = -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
tmpres = tmpres->ai_next;
|
|
||||||
}
|
|
||||||
|
|
||||||
freeaddrinfo(res);
|
|
||||||
|
|
||||||
if (fd == -1) {
|
|
||||||
return NT_STATUS_PORT_CONNECTION_REFUSED;
|
|
||||||
}
|
|
||||||
|
|
||||||
set_socket_options(fd, lp_socket_options());
|
|
||||||
|
|
||||||
if (!(*p = dcerpc_pipe_init())) {
|
if (!(*p = dcerpc_pipe_init())) {
|
||||||
return NT_STATUS_NO_MEMORY;
|
return NT_STATUS_NO_MEMORY;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
sock = talloc_p((*p), struct sock_private);
|
||||||
|
if (!sock) {
|
||||||
|
talloc_free(*p);
|
||||||
|
return NT_STATUS_NO_MEMORY;
|
||||||
|
}
|
||||||
|
|
||||||
|
status = socket_create(type, SOCKET_TYPE_STREAM, &socket_ctx, 0);
|
||||||
|
if (!NT_STATUS_IS_OK(status)) {
|
||||||
|
talloc_free(*p);
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
talloc_steal(sock, socket_ctx);
|
||||||
|
|
||||||
|
status = socket_connect(socket_ctx, NULL, 0, server, port, 0);
|
||||||
|
if (!NT_STATUS_IS_OK(status)) {
|
||||||
|
talloc_free(*p);
|
||||||
|
return status;
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
fill in the transport methods
|
fill in the transport methods
|
||||||
*/
|
*/
|
||||||
(*p)->transport.transport = NCACN_IP_TCP;
|
(*p)->transport.transport = transport;
|
||||||
(*p)->transport.private = NULL;
|
(*p)->transport.private = NULL;
|
||||||
|
|
||||||
(*p)->transport.send_request = sock_send_request;
|
(*p)->transport.send_request = sock_send_request;
|
||||||
@ -353,13 +333,7 @@ NTSTATUS dcerpc_pipe_open_tcp(struct dcerpc_pipe **p,
|
|||||||
(*p)->transport.shutdown_pipe = sock_shutdown_pipe;
|
(*p)->transport.shutdown_pipe = sock_shutdown_pipe;
|
||||||
(*p)->transport.peer_name = sock_peer_name;
|
(*p)->transport.peer_name = sock_peer_name;
|
||||||
|
|
||||||
sock = talloc((*p), sizeof(*sock));
|
sock->sock = socket_ctx;
|
||||||
if (!sock) {
|
|
||||||
dcerpc_pipe_close(*p);
|
|
||||||
return NT_STATUS_NO_MEMORY;
|
|
||||||
}
|
|
||||||
|
|
||||||
sock->fd = fd;
|
|
||||||
sock->server_name = talloc_strdup((*p), server);
|
sock->server_name = talloc_strdup((*p), server);
|
||||||
sock->event_ctx = event_context_init(sock);
|
sock->event_ctx = event_context_init(sock);
|
||||||
sock->pending_send = NULL;
|
sock->pending_send = NULL;
|
||||||
@ -367,7 +341,7 @@ NTSTATUS dcerpc_pipe_open_tcp(struct dcerpc_pipe **p,
|
|||||||
sock->recv.data = data_blob(NULL, 0);
|
sock->recv.data = data_blob(NULL, 0);
|
||||||
sock->recv.pending_count = 0;
|
sock->recv.pending_count = 0;
|
||||||
|
|
||||||
fde.fd = fd;
|
fde.fd = socket_get_fd(sock->sock);
|
||||||
fde.flags = 0;
|
fde.flags = 0;
|
||||||
fde.handler = sock_io_handler;
|
fde.handler = sock_io_handler;
|
||||||
fde.private = *p;
|
fde.private = *p;
|
||||||
@ -379,160 +353,40 @@ NTSTATUS dcerpc_pipe_open_tcp(struct dcerpc_pipe **p,
|
|||||||
/* ensure we don't get SIGPIPE */
|
/* ensure we don't get SIGPIPE */
|
||||||
BlockSignals(True,SIGPIPE);
|
BlockSignals(True,SIGPIPE);
|
||||||
|
|
||||||
return NT_STATUS_OK;
|
return NT_STATUS_OK;
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
open a rpc connection using tcp
|
||||||
|
*/
|
||||||
|
NTSTATUS dcerpc_pipe_open_tcp(struct dcerpc_pipe **p, const char *server, uint32_t port)
|
||||||
|
{
|
||||||
|
return dcerpc_pipe_open_socket(p, server, port, "ip", NCACN_IP_TCP);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
open a rpc connection to a unix socket
|
open a rpc connection to a unix socket
|
||||||
*/
|
*/
|
||||||
NTSTATUS dcerpc_pipe_open_unix_stream(struct dcerpc_pipe **p,
|
NTSTATUS dcerpc_pipe_open_unix_stream(struct dcerpc_pipe **p, const char *path)
|
||||||
const char *path)
|
|
||||||
{
|
{
|
||||||
struct sock_private *sock;
|
return dcerpc_pipe_open_socket(p, path, 0, "unix", NCACN_UNIX_STREAM);
|
||||||
int fd;
|
|
||||||
struct fd_event fde;
|
|
||||||
struct sockaddr_un sa;
|
|
||||||
|
|
||||||
fd = socket(PF_UNIX, SOCK_STREAM, 0);
|
|
||||||
|
|
||||||
if (fd < 0) {
|
|
||||||
return NT_STATUS_NOT_SUPPORTED;
|
|
||||||
}
|
|
||||||
|
|
||||||
sa.sun_family = AF_UNIX;
|
|
||||||
strncpy(sa.sun_path, path, sizeof(sa.sun_path));
|
|
||||||
|
|
||||||
if (connect(fd, &sa, sizeof(sa)) < 0) {
|
|
||||||
DEBUG(0, ("Unable to connect to unix socket %s: %s\n", path, strerror(errno)));
|
|
||||||
return NT_STATUS_BAD_NETWORK_NAME;
|
|
||||||
}
|
|
||||||
|
|
||||||
set_socket_options(fd, lp_socket_options());
|
|
||||||
|
|
||||||
if (!(*p = dcerpc_pipe_init())) {
|
|
||||||
return NT_STATUS_NO_MEMORY;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
fill in the transport methods
|
|
||||||
*/
|
|
||||||
(*p)->transport.transport = NCACN_UNIX_STREAM;
|
|
||||||
(*p)->transport.private = NULL;
|
|
||||||
|
|
||||||
(*p)->transport.send_request = sock_send_request;
|
|
||||||
(*p)->transport.send_read = sock_send_read;
|
|
||||||
(*p)->transport.event_context = sock_event_context;
|
|
||||||
(*p)->transport.recv_data = NULL;
|
|
||||||
|
|
||||||
(*p)->transport.shutdown_pipe = sock_shutdown_pipe;
|
|
||||||
(*p)->transport.peer_name = sock_peer_name;
|
|
||||||
|
|
||||||
sock = talloc((*p), sizeof(*sock));
|
|
||||||
if (!sock) {
|
|
||||||
dcerpc_pipe_close(*p);
|
|
||||||
return NT_STATUS_NO_MEMORY;
|
|
||||||
}
|
|
||||||
|
|
||||||
sock->fd = fd;
|
|
||||||
sock->server_name = talloc_strdup((*p), path);
|
|
||||||
sock->event_ctx = event_context_init(sock);
|
|
||||||
sock->pending_send = NULL;
|
|
||||||
sock->recv.received = 0;
|
|
||||||
sock->recv.data = data_blob(NULL, 0);
|
|
||||||
sock->recv.pending_count = 0;
|
|
||||||
|
|
||||||
fde.fd = fd;
|
|
||||||
fde.flags = 0;
|
|
||||||
fde.handler = sock_io_handler;
|
|
||||||
fde.private = *p;
|
|
||||||
|
|
||||||
sock->fde = event_add_fd(sock->event_ctx, &fde);
|
|
||||||
|
|
||||||
(*p)->transport.private = sock;
|
|
||||||
|
|
||||||
/* ensure we don't get SIGPIPE */
|
|
||||||
BlockSignals(True,SIGPIPE);
|
|
||||||
|
|
||||||
return NT_STATUS_OK;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
open a rpc connection to a named pipe
|
open a rpc connection to a named pipe
|
||||||
*/
|
*/
|
||||||
NTSTATUS dcerpc_pipe_open_pipe(struct dcerpc_pipe **p,
|
NTSTATUS dcerpc_pipe_open_pipe(struct dcerpc_pipe **p, const char *identifier)
|
||||||
const char *identifier)
|
|
||||||
{
|
{
|
||||||
struct sock_private *sock;
|
NTSTATUS status;
|
||||||
int fd;
|
|
||||||
struct fd_event fde;
|
|
||||||
struct sockaddr_un sa;
|
|
||||||
char *canon, *full_path;
|
char *canon, *full_path;
|
||||||
|
|
||||||
if (!(*p = dcerpc_pipe_init())) {
|
canon = talloc_strdup(NULL, identifier);
|
||||||
return NT_STATUS_NO_MEMORY;
|
|
||||||
}
|
|
||||||
|
|
||||||
canon = talloc_strdup(*p, identifier);
|
|
||||||
|
|
||||||
string_replace(canon, '/', '\\');
|
string_replace(canon, '/', '\\');
|
||||||
|
full_path = talloc_asprintf(canon, "%s/%s", lp_ncalrpc_dir(), canon);
|
||||||
|
|
||||||
full_path = talloc_asprintf(*p, "%s/%s", lp_ncalrpc_dir(), canon);
|
status = dcerpc_pipe_open_socket(p, full_path, 0, "unix", NCALRPC);
|
||||||
|
talloc_free(canon);
|
||||||
|
|
||||||
fd = socket(PF_UNIX, SOCK_STREAM, 0);
|
return status;
|
||||||
|
|
||||||
if (fd < 0) {
|
|
||||||
return NT_STATUS_NOT_SUPPORTED;
|
|
||||||
}
|
|
||||||
|
|
||||||
sa.sun_family = AF_UNIX;
|
|
||||||
strncpy(sa.sun_path, full_path, sizeof(sa.sun_path));
|
|
||||||
|
|
||||||
if (connect(fd, &sa, sizeof(sa)) < 0) {
|
|
||||||
DEBUG(0, ("Unable to connect to unix socket %s (%s): %s\n", full_path, identifier, strerror(errno)));
|
|
||||||
return NT_STATUS_BAD_NETWORK_NAME;
|
|
||||||
}
|
|
||||||
|
|
||||||
set_socket_options(fd, lp_socket_options());
|
|
||||||
|
|
||||||
/*
|
|
||||||
fill in the transport methods
|
|
||||||
*/
|
|
||||||
(*p)->transport.transport = NCALRPC;
|
|
||||||
(*p)->transport.private = NULL;
|
|
||||||
|
|
||||||
(*p)->transport.send_request = sock_send_request;
|
|
||||||
(*p)->transport.send_read = sock_send_read;
|
|
||||||
(*p)->transport.event_context = sock_event_context;
|
|
||||||
(*p)->transport.recv_data = NULL;
|
|
||||||
|
|
||||||
(*p)->transport.shutdown_pipe = sock_shutdown_pipe;
|
|
||||||
(*p)->transport.peer_name = sock_peer_name;
|
|
||||||
|
|
||||||
sock = talloc((*p), sizeof(*sock));
|
|
||||||
if (!sock) {
|
|
||||||
dcerpc_pipe_close(*p);
|
|
||||||
return NT_STATUS_NO_MEMORY;
|
|
||||||
}
|
|
||||||
|
|
||||||
sock->fd = fd;
|
|
||||||
sock->server_name = full_path;
|
|
||||||
sock->event_ctx = event_context_init(sock);
|
|
||||||
sock->pending_send = NULL;
|
|
||||||
sock->recv.received = 0;
|
|
||||||
sock->recv.data = data_blob(NULL, 0);
|
|
||||||
sock->recv.pending_count = 0;
|
|
||||||
|
|
||||||
fde.fd = fd;
|
|
||||||
fde.flags = 0;
|
|
||||||
fde.handler = sock_io_handler;
|
|
||||||
fde.private = *p;
|
|
||||||
|
|
||||||
sock->fde = event_add_fd(sock->event_ctx, &fde);
|
|
||||||
|
|
||||||
(*p)->transport.private = sock;
|
|
||||||
|
|
||||||
/* ensure we don't get SIGPIPE */
|
|
||||||
BlockSignals(True,SIGPIPE);
|
|
||||||
|
|
||||||
return NT_STATUS_OK;
|
|
||||||
}
|
}
|
||||||
|
@ -865,7 +865,7 @@ static NTSTATUS dcerpc_pipe_connect_ncalrpc(struct dcerpc_pipe **p,
|
|||||||
status = dcerpc_pipe_open_pipe(p, binding->endpoint);
|
status = dcerpc_pipe_open_pipe(p, binding->endpoint);
|
||||||
|
|
||||||
if (!NT_STATUS_IS_OK(status)) {
|
if (!NT_STATUS_IS_OK(status)) {
|
||||||
DEBUG(0,("Failed to open ncalrpc pipe '%s'\n", binding->endpoint));
|
DEBUG(0,("Failed to open ncalrpc pipe '%s' - %s\n", binding->endpoint, nt_errstr(status)));
|
||||||
talloc_destroy(mem_ctx);
|
talloc_destroy(mem_ctx);
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
@ -918,9 +918,10 @@ static NTSTATUS dcerpc_pipe_connect_ncacn_unix_stream(struct dcerpc_pipe **p,
|
|||||||
|
|
||||||
status = dcerpc_pipe_open_unix_stream(p, binding->endpoint);
|
status = dcerpc_pipe_open_unix_stream(p, binding->endpoint);
|
||||||
if (!NT_STATUS_IS_OK(status)) {
|
if (!NT_STATUS_IS_OK(status)) {
|
||||||
DEBUG(0,("Failed to open unix socket %s\n", binding->endpoint));
|
DEBUG(0,("Failed to open unix socket %s - %s\n",
|
||||||
|
binding->endpoint, nt_errstr(status)));
|
||||||
return status;
|
return status;
|
||||||
}
|
}
|
||||||
|
|
||||||
(*p)->flags = binding->flags;
|
(*p)->flags = binding->flags;
|
||||||
|
|
||||||
@ -974,7 +975,7 @@ static NTSTATUS dcerpc_pipe_connect_ncacn_ip_tcp(struct dcerpc_pipe **p,
|
|||||||
|
|
||||||
port = atoi(binding->endpoint);
|
port = atoi(binding->endpoint);
|
||||||
|
|
||||||
status = dcerpc_pipe_open_tcp(p, binding->host, port, AF_UNSPEC);
|
status = dcerpc_pipe_open_tcp(p, binding->host, port);
|
||||||
if (!NT_STATUS_IS_OK(status)) {
|
if (!NT_STATUS_IS_OK(status)) {
|
||||||
DEBUG(0,("Failed to connect to %s:%d\n", binding->host, port));
|
DEBUG(0,("Failed to connect to %s:%d\n", binding->host, port));
|
||||||
return status;
|
return status;
|
||||||
|
@ -29,7 +29,7 @@ struct pvfs_wait {
|
|||||||
void *private;
|
void *private;
|
||||||
struct timed_event *te;
|
struct timed_event *te;
|
||||||
int msg_type;
|
int msg_type;
|
||||||
void *msg_ctx;
|
struct messaging_context *msg_ctx;
|
||||||
struct event_context *ev;
|
struct event_context *ev;
|
||||||
struct smbsrv_request *req;
|
struct smbsrv_request *req;
|
||||||
BOOL timed_out;
|
BOOL timed_out;
|
||||||
@ -51,7 +51,7 @@ NTSTATUS pvfs_async_setup(struct ntvfs_module_context *ntvfs,
|
|||||||
/*
|
/*
|
||||||
receive a completion message for a wait
|
receive a completion message for a wait
|
||||||
*/
|
*/
|
||||||
static void pvfs_wait_dispatch(void *msg_ctx, void *private, uint32_t msg_type,
|
static void pvfs_wait_dispatch(struct messaging_context *msg, void *private, uint32_t msg_type,
|
||||||
servid_t src, DATA_BLOB *data)
|
servid_t src, DATA_BLOB *data)
|
||||||
{
|
{
|
||||||
struct pvfs_wait *pwait = private;
|
struct pvfs_wait *pwait = private;
|
||||||
|
@ -180,10 +180,9 @@ static void add_socket_rpc_tcp(struct server_service *service,
|
|||||||
add_socket_rpc_tcp_iface(service, model_ops, dce_ctx, e, ifip);
|
add_socket_rpc_tcp_iface(service, model_ops, dce_ctx, e, ifip);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
struct in_addr *ifip;
|
struct in_addr ifip;
|
||||||
ifip = interpret_addr2(dce_ctx, lp_socket_address());
|
ifip = interpret_addr2(lp_socket_address());
|
||||||
add_socket_rpc_tcp_iface(service, model_ops, dce_ctx, e, ifip);
|
add_socket_rpc_tcp_iface(service, model_ops, dce_ctx, e, &ifip);
|
||||||
talloc_free(ifip);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return;
|
return;
|
||||||
|
@ -725,18 +725,10 @@ static void smbsrv_init(struct server_service *service, const struct model_ops *
|
|||||||
add_socket(service, model_ops, NULL, ifip);
|
add_socket(service, model_ops, NULL, ifip);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
struct in_addr *ifip;
|
struct in_addr ifip;
|
||||||
TALLOC_CTX *mem_ctx = talloc_init("open_sockets_smbd");
|
|
||||||
|
|
||||||
if (!mem_ctx) {
|
|
||||||
smb_panic("No memory");
|
|
||||||
}
|
|
||||||
|
|
||||||
/* Just bind to lp_socket_address() (usually 0.0.0.0) */
|
/* Just bind to lp_socket_address() (usually 0.0.0.0) */
|
||||||
ifip = interpret_addr2(mem_ctx, lp_socket_address());
|
ifip = interpret_addr2(lp_socket_address());
|
||||||
add_socket(service, model_ops, NULL, ifip);
|
add_socket(service, model_ops, NULL, &ifip);
|
||||||
|
|
||||||
talloc_free(mem_ctx);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -231,7 +231,9 @@ static BOOL test_Lookup(struct dcerpc_pipe *p, TALLOC_CTX *mem_ctx)
|
|||||||
for (i=0;i<r.out.num_ents;i++) {
|
for (i=0;i<r.out.num_ents;i++) {
|
||||||
printf("\nFound '%s'\n", r.out.entries[i].annotation);
|
printf("\nFound '%s'\n", r.out.entries[i].annotation);
|
||||||
display_tower(mem_ctx, &r.out.entries[i].tower->tower);
|
display_tower(mem_ctx, &r.out.entries[i].tower->tower);
|
||||||
test_Map(p, mem_ctx, r.out.entries[i].tower);
|
if (r.out.entries[i].tower->tower.num_floors == 5) {
|
||||||
|
test_Map(p, mem_ctx, r.out.entries[i].tower);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} while (NT_STATUS_IS_OK(status) &&
|
} while (NT_STATUS_IS_OK(status) &&
|
||||||
r.out.result == 0 &&
|
r.out.result == 0 &&
|
||||||
|
@ -228,7 +228,7 @@ int main(int argc,char *argv[])
|
|||||||
switch (opt)
|
switch (opt)
|
||||||
{
|
{
|
||||||
case 'B':
|
case 'B':
|
||||||
bcast_addr = *interpret_addr2(optarg);
|
bcast_addr = interpret_addr2(optarg);
|
||||||
got_bcast = True;
|
got_bcast = True;
|
||||||
use_bcast = True;
|
use_bcast = True;
|
||||||
break;
|
break;
|
||||||
@ -236,7 +236,7 @@ int main(int argc,char *argv[])
|
|||||||
give_flags = True;
|
give_flags = True;
|
||||||
break;
|
break;
|
||||||
case 'U':
|
case 'U':
|
||||||
bcast_addr = *interpret_addr2(optarg);
|
bcast_addr = interpret_addr2(optarg);
|
||||||
got_bcast = True;
|
got_bcast = True;
|
||||||
use_bcast = False;
|
use_bcast = False;
|
||||||
break;
|
break;
|
||||||
@ -306,7 +306,7 @@ int main(int argc,char *argv[])
|
|||||||
if(lookup_by_ip)
|
if(lookup_by_ip)
|
||||||
{
|
{
|
||||||
fstrcpy(lookup,"*");
|
fstrcpy(lookup,"*");
|
||||||
ip = *interpret_addr2(argv[i]);
|
ip = interpret_addr2(argv[i]);
|
||||||
do_node_status(ServerFD, lookup, lookup_type, ip);
|
do_node_status(ServerFD, lookup, lookup_type, ip);
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user