lib/util_sock.c

ソースコードを見る。

データ構造

struct  smb_socket_option

列挙型

enum  SOCK_OPT_TYPES { OPT_BOOL, OPT_INT, OPT_ON }

関数

void client_setfd (int fd)
static char * get_socket_addr (int fd)
static int get_socket_port (int fd)
char * client_name (void)
char * client_addr (void)
char * client_socket_addr (void)
int client_socket_port (void)
in_addr * client_inaddr (struct sockaddr *sa)
BOOL is_a_socket (int fd)
static void print_socket_options (int s)
void set_socket_options (int fd, const char *options)
ssize_t read_udp_socket (int fd, char *buf, size_t len)
Socket routines from HEAD
maybe re enable in future
static JRA BOOL 
timeout_until (struct timeval *timeout, const struct timeval *endtime)
ssize_t read_data_until (int fd, char *buffer, size_t N, const struct timeval *endtime)
ssize_t read_socket_with_timeout (int fd, char *buf, size_t mincnt, size_t maxcnt, unsigned int time_out)
ssize_t read_data (int fd, char *buffer, size_t N)
ssize_t write_data (int fd, const char *buffer, size_t N)
BOOL send_keepalive (int client)
static ssize_t read_smb_length_return_keepalive (int fd, char *inbuf, unsigned int timeout)
ssize_t read_smb_length (int fd, char *inbuf, unsigned int timeout)
BOOL receive_smb_raw (int fd, char *buffer, size_t buflen, unsigned int timeout)
BOOL receive_smb (int fd, char *buffer, size_t buflen, unsigned int timeout)
BOOL send_smb (int fd, char *buffer)
int open_socket_in (int type, int port, int dlevel, uint32 socket_addr, BOOL rebind)
int open_socket_out (int type, struct in_addr *addr, int port, int timeout)
BOOL open_any_socket_out (struct sockaddr_in *addrs, int num_addrs, int timeout, int *fd_index, int *fd)
int open_udp_socket (const char *host, int port)
static BOOL matchname (char *remotehost, struct in_addr addr)
char * get_peer_name (int fd, BOOL force_lookup)
char * get_peer_addr (int fd)
int create_pipe_sock (const char *socket_dir, const char *socket_name, mode_t dir_perms)

変数

static int client_fd = -1
static char client_ip_string [16]
in_addr lastip
int lastport = 0
int smb_read_error = 0
static const smb_socket_option socket_options []


列挙型

enum SOCK_OPT_TYPES

列挙型の値:
OPT_BOOL 
OPT_INT 
OPT_ON 

util_sock.c131 行で定義されています。


関数

void client_setfd ( int  fd  ) 

util_sock.c32 行で定義されています。

参照先 client_fdclient_ip_stringget_peer_addr().

参照元 smbd_set_server_fd().

00033 {
00034         client_fd = fd;
00035         safe_strcpy(client_ip_string, get_peer_addr(client_fd), sizeof(client_ip_string)-1);
00036 }

static char* get_socket_addr ( int  fd  )  [static]

util_sock.c38 行で定義されています。

参照先 errnostrerror().

参照元 client_socket_addr().

00039 {
00040         struct sockaddr sa;
00041         struct sockaddr_in *sockin = (struct sockaddr_in *) (&sa);
00042         socklen_t length = sizeof(sa);
00043         static fstring addr_buf;
00044 
00045         fstrcpy(addr_buf,"0.0.0.0");
00046 
00047         if (fd == -1) {
00048                 return addr_buf;
00049         }
00050         
00051         if (getsockname(fd, &sa, &length) < 0) {
00052                 DEBUG(0,("getsockname failed. Error was %s\n", strerror(errno) ));
00053                 return addr_buf;
00054         }
00055         
00056         fstrcpy(addr_buf,(char *)inet_ntoa(sockin->sin_addr));
00057         
00058         return addr_buf;
00059 }

static int get_socket_port ( int  fd  )  [static]

util_sock.c61 行で定義されています。

参照先 errnostrerror().

参照元 client_socket_port().

00062 {
00063         struct sockaddr sa;
00064         struct sockaddr_in *sockin = (struct sockaddr_in *) (&sa);
00065         socklen_t length = sizeof(sa);
00066 
00067         if (fd == -1)
00068                 return -1;
00069         
00070         if (getsockname(fd, &sa, &length) < 0) {
00071                 DEBUG(0,("getpeername failed. Error was %s\n", strerror(errno) ));
00072                 return -1;
00073         }
00074         
00075         return ntohs(sockin->sin_port);
00076 }

char* client_name ( void   ) 

util_sock.c78 行で定義されています。

参照先 client_fdget_peer_name().

参照元 alloc_sub_basic()cups_job_submit()get_md4pw()iprint_job_submit()session_claim()smb_pam_start().

00079 {
00080         return get_peer_name(client_fd,False);
00081 }

char* client_addr ( void   ) 

util_sock.c83 行で定義されています。

参照先 client_fdget_peer_addr().

参照元 alloc_sub_basic()claim_connection()cups_job_submit()get_md4pw()iprint_job_submit()make_connection()make_connection_snum()process_smb()read_target_host()session_claim()setup_new_vc_session()smb_pam_start().

00084 {
00085         return get_peer_addr(client_fd);
00086 }

char* client_socket_addr ( void   ) 

util_sock.c88 行で定義されています。

参照先 client_fdget_socket_addr().

参照元 alloc_sub_basic()set_local_machine_name().

00089 {
00090         return get_socket_addr(client_fd);
00091 }

int client_socket_port ( void   ) 

util_sock.c93 行で定義されています。

参照先 client_fdget_socket_port().

00094 {
00095         return get_socket_port(client_fd);
00096 }

struct in_addr* client_inaddr ( struct sockaddr *  sa  ) 

util_sock.c98 行で定義されています。

参照先 client_fderrnostrerror().

参照元 session_claim().

00099 {
00100         struct sockaddr_in *sockin = (struct sockaddr_in *) (sa);
00101         socklen_t  length = sizeof(*sa);
00102         
00103         if (getpeername(client_fd, sa, &length) < 0) {
00104                 DEBUG(0,("getpeername failed. Error was %s\n", strerror(errno) ));
00105                 return NULL;
00106         }
00107         
00108         return &sockin->sin_addr;
00109 }

BOOL is_a_socket ( int  fd  ) 

util_sock.c123 行で定義されています。

参照元 main().

00124 {
00125         int v;
00126         socklen_t l;
00127         l = sizeof(int);
00128         return(getsockopt(fd, SOL_SOCKET, SO_TYPE, (char *)&v, &l) == 0);
00129 }

static void print_socket_options ( int  s  )  [static]

util_sock.c193 行で定義されています。

参照先 DEBUGLEVELsmb_socket_option::levelsmb_socket_option::namesmb_socket_option::optionsocket_options.

参照元 set_socket_options().

00194 {
00195         int value;
00196         socklen_t vlen = 4;
00197         const smb_socket_option *p = &socket_options[0];
00198 
00199         /* wrapped in if statement to prevent streams leak in SCO Openserver 5.0 */
00200         /* reported on samba-technical  --jerry */
00201         if ( DEBUGLEVEL >= 5 ) {
00202         for (; p->name != NULL; p++) {
00203                 if (getsockopt(s, p->level, p->option, (void *)&value, &vlen) == -1) {
00204                         DEBUG(5,("Could not test socket option %s.\n", p->name));
00205                 } else {
00206                         DEBUG(5,("socket option %s = %d\n",p->name,value));
00207                         }
00208                 }
00209         }
00210  }

void set_socket_options ( int  fd,
const char *  options 
)

util_sock.c216 行で定義されています。

参照先 errnolevelnamesmb_socket_option::namenext_token()OPT_BOOLOPT_INTOPT_ONprint_socket_options()socket_optionsstrchr_m()strequal()strerror()smb_socket_option::value.

参照元 cli_connect()cli_session_request()cli_sockopt()make_subnet()name_resolve_bcast()open_sockets()open_sockets_inetd()open_sockets_smbd()reload_services()wins_lookup_open_socket_in().

00217 {
00218         fstring tok;
00219 
00220         while (next_token(&options,tok," \t,", sizeof(tok))) {
00221                 int ret=0,i;
00222                 int value = 1;
00223                 char *p;
00224                 BOOL got_value = False;
00225 
00226                 if ((p = strchr_m(tok,'='))) {
00227                         *p = 0;
00228                         value = atoi(p+1);
00229                         got_value = True;
00230                 }
00231 
00232                 for (i=0;socket_options[i].name;i++)
00233                         if (strequal(socket_options[i].name,tok))
00234                                 break;
00235 
00236                 if (!socket_options[i].name) {
00237                         DEBUG(0,("Unknown socket option %s\n",tok));
00238                         continue;
00239                 }
00240 
00241                 switch (socket_options[i].opttype) {
00242                 case OPT_BOOL:
00243                 case OPT_INT:
00244                         ret = setsockopt(fd,socket_options[i].level,
00245                                                 socket_options[i].option,(char *)&value,sizeof(int));
00246                         break;
00247 
00248                 case OPT_ON:
00249                         if (got_value)
00250                                 DEBUG(0,("syntax error - %s does not take a value\n",tok));
00251 
00252                         {
00253                                 int on = socket_options[i].value;
00254                                 ret = setsockopt(fd,socket_options[i].level,
00255                                                         socket_options[i].option,(char *)&on,sizeof(int));
00256                         }
00257                         break;    
00258                 }
00259       
00260                 if (ret != 0)
00261                         DEBUG(0,("Failed to set socket option %s (Error %s)\n",tok, strerror(errno) ));
00262         }
00263 
00264         print_socket_options(fd);
00265 }

ssize_t read_udp_socket ( int  fd,
char *  buf,
size_t  len 
)

util_sock.c271 行で定義されています。

参照先 errnolastiplastportstrerror()sys_recvfrom().

参照元 read_packet().

00272 {
00273         ssize_t ret;
00274         struct sockaddr_in sock;
00275         socklen_t socklen = sizeof(sock);
00276 
00277         memset((char *)&sock,'\0',socklen);
00278         memset((char *)&lastip,'\0',sizeof(lastip));
00279         ret = (ssize_t)sys_recvfrom(fd,buf,len,0,(struct sockaddr *)&sock,&socklen);
00280         if (ret <= 0) {
00281                 /* Don't print a low debug error for a non-blocking socket. */
00282                 if (errno == EAGAIN) {
00283                         DEBUG(10,("read socket returned EAGAIN. ERRNO=%s\n",strerror(errno)));
00284                 } else {
00285                         DEBUG(2,("read socket failed. ERRNO=%s\n",strerror(errno)));
00286                 }
00287                 return(0);
00288         }
00289 
00290         lastip = sock.sin_addr;
00291         lastport = ntohs(sock.sin_port);
00292 
00293         DEBUG(10,("read_udp_socket: lastip %s lastport %d read: %lu\n",
00294                         inet_ntoa(lastip), lastport, (unsigned long)ret));
00295 
00296         return(ret);
00297 }

Socket routines from HEAD maybe re enable in future static JRA BOOL timeout_until ( struct timeval *  timeout,
const struct timeval *  endtime 
) [static]

util_sock.c307 行で定義されています。

参照先 GetTimeOfDay()usec_time_diff().

参照元 read_data_until().

00308 {
00309         struct timeval now;
00310         SMB_BIG_INT t_dif;
00311 
00312         GetTimeOfDay(&now);
00313 
00314         t_dif = usec_time_diff(endtime, &now);
00315         if (t_dif <= 0) {
00316                 return False;
00317         }
00318 
00319         timeout->tv_sec = (t_dif / (SMB_BIG_INT)1000000);
00320         timeout->tv_usec = (t_dif % (SMB_BIG_INT)1000000);
00321         return True;
00322 }

ssize_t read_data_until ( int  fd,
char *  buffer,
size_t  N,
const struct timeval *  endtime 
)

util_sock.c329 行で定義されています。

参照先 errnosmb_read_errorstrerror()sys_read()sys_select_intr()timeout_until()total.

00330 {
00331         ssize_t ret;
00332         size_t total=0;
00333 
00334         smb_read_error = 0;
00335 
00336         while (total < N) {
00337 
00338                 if (endtime != NULL) {
00339                         fd_set r_fds;
00340                         struct timeval timeout;
00341                         int selrtn;
00342 
00343                         if (!timeout_until(&timeout, endtime)) {
00344                                 DEBUG(10,("read_data_until: read timed out\n"));
00345                                 smb_read_error = READ_TIMEOUT;
00346                                 return -1;
00347                         }
00348 
00349                         FD_ZERO(&r_fds);
00350                         FD_SET(fd, &r_fds);
00351 
00352                         /* Select but ignore EINTR. */
00353                         selrtn = sys_select_intr(fd+1, &r_fds, NULL, NULL, &timeout);
00354                         if (selrtn == -1) {
00355                                 /* something is wrong. Maybe the socket is dead? */
00356                                 DEBUG(0,("read_data_until: select error = %s.\n", strerror(errno) ));
00357                                 smb_read_error = READ_ERROR;
00358                                 return -1;
00359                         }
00360 
00361                         /* Did we timeout ? */
00362                         if (selrtn == 0) {
00363                                 DEBUG(10,("read_data_until: select timed out.\n"));
00364                                 smb_read_error = READ_TIMEOUT;
00365                                 return -1;
00366                         }
00367                 }
00368 
00369                 ret = sys_read(fd,buffer + total,N - total);
00370 
00371                 if (ret == 0) {
00372                         DEBUG(10,("read_data_until: read of %d returned 0. Error = %s\n", (int)(N - total), strerror(errno) ));
00373                         smb_read_error = READ_EOF;
00374                         return 0;
00375                 }
00376 
00377                 if (ret == -1) {
00378                         if (errno == EAGAIN) {
00379                                 /* Non-blocking socket with no data available. Try select again. */
00380                                 continue;
00381                         }
00382                         DEBUG(0,("read_data_until: read failure for %d. Error = %s\n", (int)(N - total), strerror(errno) ));
00383                         smb_read_error = READ_ERROR;
00384                         return -1;
00385                 }
00386                 total += ret;
00387         }
00388         return (ssize_t)total;
00389 }

ssize_t read_socket_with_timeout ( int  fd,
char *  buf,
size_t  mincnt,
size_t  maxcnt,
unsigned int  time_out 
)

util_sock.c399 行で定義されています。

参照先 client_fdclient_ip_stringerrnosmb_read_errorstrerror()sys_read()sys_select_intr().

参照元 expect()read_smb_length_return_keepalive()receive_smb_raw().

00400 {
00401         fd_set fds;
00402         int selrtn;
00403         ssize_t readret;
00404         size_t nread = 0;
00405         struct timeval timeout;
00406         
00407         /* just checking .... */
00408         if (maxcnt <= 0)
00409                 return(0);
00410         
00411         smb_read_error = 0;
00412         
00413         /* Blocking read */
00414         if (time_out == 0) {
00415                 if (mincnt == 0) {
00416                         mincnt = maxcnt;
00417                 }
00418                 
00419                 while (nread < mincnt) {
00420                         readret = sys_read(fd, buf + nread, maxcnt - nread);
00421                         
00422                         if (readret == 0) {
00423                                 DEBUG(5,("read_socket_with_timeout: blocking read. EOF from client.\n"));
00424                                 smb_read_error = READ_EOF;
00425                                 return -1;
00426                         }
00427                         
00428                         if (readret == -1) {
00429                                 if (fd == client_fd) {
00430                                         /* Try and give an error message saying what client failed. */
00431                                         DEBUG(0,("read_socket_with_timeout: client %s read error = %s.\n",
00432                                                 client_ip_string, strerror(errno) ));
00433                                 } else {
00434                                         DEBUG(0,("read_socket_with_timeout: read error = %s.\n", strerror(errno) ));
00435                                 }
00436                                 smb_read_error = READ_ERROR;
00437                                 return -1;
00438                         }
00439                         nread += readret;
00440                 }
00441                 return((ssize_t)nread);
00442         }
00443         
00444         /* Most difficult - timeout read */
00445         /* If this is ever called on a disk file and 
00446            mincnt is greater then the filesize then
00447            system performance will suffer severely as 
00448            select always returns true on disk files */
00449         
00450         /* Set initial timeout */
00451         timeout.tv_sec = (time_t)(time_out / 1000);
00452         timeout.tv_usec = (long)(1000 * (time_out % 1000));
00453         
00454         for (nread=0; nread < mincnt; ) {      
00455                 FD_ZERO(&fds);
00456                 FD_SET(fd,&fds);
00457                 
00458                 selrtn = sys_select_intr(fd+1,&fds,NULL,NULL,&timeout);
00459                 
00460                 /* Check if error */
00461                 if (selrtn == -1) {
00462                         /* something is wrong. Maybe the socket is dead? */
00463                         if (fd == client_fd) {
00464                                 /* Try and give an error message saying what client failed. */
00465                                 DEBUG(0,("read_socket_with_timeout: timeout read for client %s. select error = %s.\n",
00466                                         client_ip_string, strerror(errno) ));
00467                         } else {
00468                                 DEBUG(0,("read_socket_with_timeout: timeout read. select error = %s.\n", strerror(errno) ));
00469                         }
00470                         smb_read_error = READ_ERROR;
00471                         return -1;
00472                 }
00473                 
00474                 /* Did we timeout ? */
00475                 if (selrtn == 0) {
00476                         DEBUG(10,("read_socket_with_timeout: timeout read. select timed out.\n"));
00477                         smb_read_error = READ_TIMEOUT;
00478                         return -1;
00479                 }
00480                 
00481                 readret = sys_read(fd, buf+nread, maxcnt-nread);
00482                 
00483                 if (readret == 0) {
00484                         /* we got EOF on the file descriptor */
00485                         DEBUG(5,("read_socket_with_timeout: timeout read. EOF from client.\n"));
00486                         smb_read_error = READ_EOF;
00487                         return -1;
00488                 }
00489                 
00490                 if (readret == -1) {
00491                         /* the descriptor is probably dead */
00492                         if (fd == client_fd) {
00493                                 /* Try and give an error message saying what client failed. */
00494                                 DEBUG(0,("read_socket_with_timeout: timeout read to client %s. read error = %s.\n",
00495                                         client_ip_string, strerror(errno) ));
00496                         } else {
00497                                 DEBUG(0,("read_socket_with_timeout: timeout read. read error = %s.\n", strerror(errno) ));
00498                         }
00499                         smb_read_error = READ_ERROR;
00500                         return -1;
00501                 }
00502                 
00503                 nread += readret;
00504         }
00505         
00506         /* Return the number we got */
00507         return (ssize_t)nread;
00508 }

ssize_t read_data ( int  fd,
char *  buffer,
size_t  N 
)

util_sock.c514 行で定義されています。

参照先 client_fdclient_ip_stringerrnosmb_read_errorstrerror()sys_read()total.

参照元 asyncdns_process()child_read_request()read_smb_length_return_keepalive()receive_smb_raw()reply_writebraw()run_dns_queue().

00515 {
00516         ssize_t ret;
00517         size_t total=0;  
00518  
00519         smb_read_error = 0;
00520 
00521         while (total < N) {
00522                 ret = sys_read(fd,buffer + total,N - total);
00523 
00524                 if (ret == 0) {
00525                         DEBUG(10,("read_data: read of %d returned 0. Error = %s\n", (int)(N - total), strerror(errno) ));
00526                         smb_read_error = READ_EOF;
00527                         return 0;
00528                 }
00529 
00530                 if (ret == -1) {
00531                         if (fd == client_fd) {
00532                                 /* Try and give an error message saying what client failed. */
00533                                 DEBUG(0,("read_data: read failure for %d bytes to client %s. Error = %s\n",
00534                                         (int)(N - total), client_ip_string, strerror(errno) ));
00535                         } else {
00536                                 DEBUG(0,("read_data: read failure for %d. Error = %s\n", (int)(N - total), strerror(errno) ));
00537                         }
00538                         smb_read_error = READ_ERROR;
00539                         return -1;
00540                 }
00541                 total += ret;
00542         }
00543         return (ssize_t)total;
00544 }

ssize_t write_data ( int  fd,
const char *  buffer,
size_t  N 
)

util_sock.c550 行で定義されています。

参照先 client_fdclient_ip_stringerrnostrerror()sys_write()total.

参照元 asyncdns_process()fake_sendfile()reply_readbraw()send_file_readbraw()send_keepalive()send_smb()write_child()write_data_at_offset()write_socket().

00551 {
00552         size_t total=0;
00553         ssize_t ret;
00554 
00555         while (total < N) {
00556                 ret = sys_write(fd,buffer + total,N - total);
00557 
00558                 if (ret == -1) {
00559                         if (fd == client_fd) {
00560                                 /* Try and give an error message saying what client failed. */
00561                                 DEBUG(0,("write_data: write failure in writing to client %s. Error %s\n",
00562                                         client_ip_string, strerror(errno) ));
00563                         } else {
00564                                 DEBUG(0,("write_data: write failure. Error = %s\n", strerror(errno) ));
00565                         }
00566                         return -1;
00567                 }
00568 
00569                 if (ret == 0) {
00570                         return total;
00571                 }
00572 
00573                 total += ret;
00574         }
00575         return (ssize_t)total;
00576 }

BOOL send_keepalive ( int  client  ) 

util_sock.c582 行で定義されています。

参照先 bufwrite_data().

参照元 cli_send_keepalive()reply_writebraw()send_server_keepalive()timeout_processing().

00583 {
00584         unsigned char buf[4];
00585 
00586         buf[0] = SMBkeepalive;
00587         buf[1] = buf[2] = buf[3] = 0;
00588 
00589         return(write_data(client,(char *)buf,4) == 4);
00590 }

static ssize_t read_smb_length_return_keepalive ( int  fd,
char *  inbuf,
unsigned int  timeout 
) [static]

util_sock.c601 行で定義されています。

参照先 lenread_data()read_socket_with_timeout().

参照元 read_smb_length()receive_smb_raw().

00602 {
00603         ssize_t len=0;
00604         int msg_type;
00605         BOOL ok = False;
00606 
00607         while (!ok) {
00608                 if (timeout > 0)
00609                         ok = (read_socket_with_timeout(fd,inbuf,4,4,timeout) == 4);
00610                 else 
00611                         ok = (read_data(fd,inbuf,4) == 4);
00612 
00613                 if (!ok)
00614                         return(-1);
00615 
00616                 len = smb_len(inbuf);
00617                 msg_type = CVAL(inbuf,0);
00618 
00619                 if (msg_type == SMBkeepalive) 
00620                         DEBUG(5,("Got keepalive packet\n"));
00621         }
00622 
00623         DEBUG(10,("got smb length of %lu\n",(unsigned long)len));
00624 
00625         return(len);
00626 }

ssize_t read_smb_length ( int  fd,
char *  inbuf,
unsigned int  timeout 
)

util_sock.c635 行で定義されています。

参照先 lenread_smb_length_return_keepalive().

参照元 reply_writebraw().

00636 {
00637         ssize_t len;
00638 
00639         for(;;) {
00640                 len = read_smb_length_return_keepalive(fd, inbuf, timeout);
00641 
00642                 if(len < 0)
00643                         return len;
00644 
00645                 /* Ignore session keepalives. */
00646                 if(CVAL(inbuf,0) != SMBkeepalive)
00647                         break;
00648         }
00649 
00650         DEBUG(10,("read_smb_length: got smb length of %lu\n",
00651                   (unsigned long)len));
00652 
00653         return len;
00654 }

BOOL receive_smb_raw ( int  fd,
char *  buffer,
size_t  buflen,
unsigned int  timeout 
)

util_sock.c663 行で定義されています。

参照先 lenread_data()read_smb_length_return_keepalive()read_socket_with_timeout()smb_read_error.

参照元 client_receive_smb()receive_smb().

00664 {
00665         ssize_t len,ret;
00666 
00667         smb_read_error = 0;
00668 
00669         len = read_smb_length_return_keepalive(fd,buffer,timeout);
00670         if (len < 0) {
00671                 DEBUG(10,("receive_smb_raw: length < 0!\n"));
00672 
00673                 /*
00674                  * Correct fix. smb_read_error may have already been
00675                  * set. Only set it here if not already set. Global
00676                  * variables still suck :-). JRA.
00677                  */
00678 
00679                 if (smb_read_error == 0)
00680                         smb_read_error = READ_ERROR;
00681                 return False;
00682         }
00683 
00684         if (len > buflen) {
00685                 DEBUG(0,("Invalid packet length! (%lu bytes).\n",(unsigned long)len));
00686 
00687                 /*
00688                  * smb_read_error may have already been
00689                  * set. Only set it here if not already set. Global
00690                  * variables still suck :-). JRA.
00691                  */
00692 
00693                 if (smb_read_error == 0)
00694                         smb_read_error = READ_ERROR;
00695                 return False;
00696         }
00697 
00698         if(len > 0) {
00699                 if (timeout > 0) {
00700                         ret = read_socket_with_timeout(fd,buffer+4,len,len,timeout);
00701                 } else {
00702                         ret = read_data(fd,buffer+4,len);
00703                 }
00704 
00705                 if (ret != len) {
00706                         if (smb_read_error == 0) {
00707                                 smb_read_error = READ_ERROR;
00708                         }
00709                         return False;
00710                 }
00711                 
00712                 /* not all of samba3 properly checks for packet-termination of strings. This
00713                    ensures that we don't run off into empty space. */
00714                 SSVAL(buffer+4,len, 0);
00715         }
00716 
00717         return True;
00718 }

BOOL receive_smb ( int  fd,
char *  buffer,
size_t  buflen,
unsigned int  timeout 
)

util_sock.c725 行で定義されています。

参照先 receive_smb_raw()smb_read_errorsrv_check_sign_mac().

参照元 filter_child()readline_callback()receive_message_or_smb().

00726 {
00727         if (!receive_smb_raw(fd, buffer, buflen, timeout)) {
00728                 return False;
00729         }
00730 
00731         /* Check the incoming SMB signature. */
00732         if (!srv_check_sign_mac(buffer, True)) {
00733                 DEBUG(0, ("receive_smb: SMB Signature verification failed on incoming packet!\n"));
00734                 if (smb_read_error == 0)
00735                         smb_read_error = READ_BAD_SIG;
00736                 return False;
00737         };
00738 
00739         return(True);
00740 }

BOOL send_smb ( int  fd,
char *  buffer 
)

util_sock.c746 行で定義されています。

参照先 errnolensrv_calculate_sign_mac()strerror()write_data().

参照元 blocking_lock_reply_error()change_notify_reply_packet()filter_child()generic_blocking_lock_error()handle_aio_read_complete()handle_aio_write_complete()process_kernel_oplock_break()process_oplock_async_level2_break_message()process_oplock_break_message()process_smb()reply_echo()reply_readbmpx()reply_sesssetup_blob()reply_writebmpx()reply_writebraw()schedule_aio_write_and_X()send_blocking_reply()send_nt_replies()send_trans2_replies()send_trans_reply().

00747 {
00748         size_t len;
00749         size_t nwritten=0;
00750         ssize_t ret;
00751 
00752         /* Sign the outgoing packet if required. */
00753         srv_calculate_sign_mac(buffer);
00754 
00755         len = smb_len(buffer) + 4;
00756 
00757         while (nwritten < len) {
00758                 ret = write_data(fd,buffer+nwritten,len - nwritten);
00759                 if (ret <= 0) {
00760                         DEBUG(0,("Error writing %d bytes to client. %d. (%s)\n",
00761                                 (int)len,(int)ret, strerror(errno) ));
00762                         return False;
00763                 }
00764                 nwritten += ret;
00765         }
00766 
00767         return True;
00768 }

int open_socket_in ( int  type,
int  port,
int  dlevel,
uint32  socket_addr,
BOOL  rebind 
)

util_sock.c774 行で定義されています。

参照先 dbgtext()errnostrerror().

参照元 make_subnet()name_resolve_bcast()name_status_find()nmbd_running()open_sockets()open_sockets_smbd()resolve_wins()start_filter().

00775 {
00776         struct sockaddr_in sock;
00777         int res;
00778 
00779         memset( (char *)&sock, '\0', sizeof(sock) );
00780 
00781 #ifdef HAVE_SOCK_SIN_LEN
00782         sock.sin_len         = sizeof(sock);
00783 #endif
00784         sock.sin_port        = htons( port );
00785         sock.sin_family      = AF_INET;
00786         sock.sin_addr.s_addr = socket_addr;
00787 
00788         res = socket( AF_INET, type, 0 );
00789         if( res == -1 ) {
00790                 if( DEBUGLVL(0) ) {
00791                         dbgtext( "open_socket_in(): socket() call failed: " );
00792                         dbgtext( "%s\n", strerror( errno ) );
00793                 }
00794                 return -1;
00795         }
00796 
00797         /* This block sets/clears the SO_REUSEADDR and possibly SO_REUSEPORT. */
00798         {
00799                 int val = rebind ? 1 : 0;
00800                 if( setsockopt(res,SOL_SOCKET,SO_REUSEADDR,(char *)&val,sizeof(val)) == -1 ) {
00801                         if( DEBUGLVL( dlevel ) ) {
00802                                 dbgtext( "open_socket_in(): setsockopt: " );
00803                                 dbgtext( "SO_REUSEADDR = %s ", val?"True":"False" );
00804                                 dbgtext( "on port %d failed ", port );
00805                                 dbgtext( "with error = %s\n", strerror(errno) );
00806                         }
00807                 }
00808 #ifdef SO_REUSEPORT
00809                 if( setsockopt(res,SOL_SOCKET,SO_REUSEPORT,(char *)&val,sizeof(val)) == -1 ) {
00810                         if( DEBUGLVL( dlevel ) ) {
00811                                 dbgtext( "open_socket_in(): setsockopt: ");
00812                                 dbgtext( "SO_REUSEPORT = %s ", val?"True":"False" );
00813                                 dbgtext( "on port %d failed ", port );
00814                                 dbgtext( "with error = %s\n", strerror(errno) );
00815                         }
00816                 }
00817 #endif /* SO_REUSEPORT */
00818         }
00819 
00820         /* now we've got a socket - we need to bind it */
00821         if( bind( res, (struct sockaddr *)&sock, sizeof(sock) ) == -1 ) {
00822                 if( DEBUGLVL(dlevel) && (port == SMB_PORT1 || port == SMB_PORT2 || port == NMB_PORT) ) {
00823                         dbgtext( "bind failed on port %d ", port );
00824                         dbgtext( "socket_addr = %s.\n", inet_ntoa( sock.sin_addr ) );
00825                         dbgtext( "Error = %s\n", strerror(errno) );
00826                 }
00827                 close( res ); 
00828                 return( -1 ); 
00829         }
00830 
00831         DEBUG( 10, ( "bind succeeded on port %d\n", port ) );
00832 
00833         return( res );
00834  }

int open_socket_out ( int  type,
struct in_addr *  addr,
int  port,
int  timeout 
)

util_sock.c840 行で定義されています。

参照先 errnoset_blocking()smb_msleep()strerror().

参照元 cli_connect()cli_session_request()do_krb5_kpasswd_request()filter_child().

00841 {
00842         struct sockaddr_in sock_out;
00843         int res,ret;
00844         int connect_loop = 10;
00845         int increment = 10;
00846 
00847         /* create a socket to write to */
00848         res = socket(PF_INET, type, 0);
00849         if (res == -1) {
00850                 DEBUG(0,("socket error (%s)\n", strerror(errno)));
00851                 return -1;
00852         }
00853 
00854         if (type != SOCK_STREAM)
00855                 return(res);
00856   
00857         memset((char *)&sock_out,'\0',sizeof(sock_out));
00858         putip((char *)&sock_out.sin_addr,(char *)addr);
00859   
00860         sock_out.sin_port = htons( port );
00861         sock_out.sin_family = PF_INET;
00862 
00863         /* set it non-blocking */
00864         set_blocking(res,False);
00865 
00866         DEBUG(3,("Connecting to %s at port %d\n",inet_ntoa(*addr),port));
00867   
00868         /* and connect it to the destination */
00869   connect_again:
00870 
00871         ret = connect(res,(struct sockaddr *)&sock_out,sizeof(sock_out));
00872 
00873         /* Some systems return EAGAIN when they mean EINPROGRESS */
00874         if (ret < 0 && (errno == EINPROGRESS || errno == EALREADY ||
00875                         errno == EAGAIN) && (connect_loop < timeout) ) {
00876                 smb_msleep(connect_loop);
00877                 timeout -= connect_loop;
00878                 connect_loop += increment;
00879                 if (increment < 250) {
00880                         /* After 8 rounds we end up at a max of 255 msec */
00881                         increment *= 1.5;
00882                 }
00883                 goto connect_again;
00884         }
00885 
00886         if (ret < 0 && (errno == EINPROGRESS || errno == EALREADY ||
00887                         errno == EAGAIN)) {
00888                 DEBUG(1,("timeout connecting to %s:%d\n",inet_ntoa(*addr),port));
00889                 close(res);
00890                 return -1;
00891         }
00892 
00893 #ifdef EISCONN
00894 
00895         if (ret < 0 && errno == EISCONN) {
00896                 errno = 0;
00897                 ret = 0;
00898         }
00899 #endif
00900 
00901         if (ret < 0) {
00902                 DEBUG(2,("error connecting to %s:%d (%s)\n",
00903                                 inet_ntoa(*addr),port,strerror(errno)));
00904                 close(res);
00905                 return -1;
00906         }
00907 
00908         /* set it blocking again */
00909         set_blocking(res,True);
00910 
00911         return res;
00912 }

BOOL open_any_socket_out ( struct sockaddr_in *  addrs,
int  num_addrs,
int  timeout,
int *  fd_index,
int *  fd 
)

util_sock.c920 行で定義されています。

参照先 endiferrnoset_blocking()socketssys_select_intr().

参照元 cm_open_connection()find_new_dc().

00922 {
00923         int i, resulting_index, res;
00924         int *sockets;
00925         BOOL good_connect;
00926 
00927         fd_set r_fds, wr_fds;
00928         struct timeval tv;
00929         int maxfd;
00930 
00931         int connect_loop = 10000; /* 10 milliseconds */
00932 
00933         timeout *= 1000;        /* convert to microseconds */
00934 
00935         sockets = SMB_MALLOC_ARRAY(int, num_addrs);
00936 
00937         if (sockets == NULL)
00938                 return False;
00939 
00940         resulting_index = -1;
00941 
00942         for (i=0; i<num_addrs; i++)
00943                 sockets[i] = -1;
00944 
00945         for (i=0; i<num_addrs; i++) {
00946                 sockets[i] = socket(PF_INET, SOCK_STREAM, 0);
00947                 if (sockets[i] < 0)
00948                         goto done;
00949                 set_blocking(sockets[i], False);
00950         }
00951 
00952  connect_again:
00953         good_connect = False;
00954 
00955         for (i=0; i<num_addrs; i++) {
00956 
00957                 if (sockets[i] == -1)
00958                         continue;
00959 
00960                 if (connect(sockets[i], (struct sockaddr *)&(addrs[i]),
00961                             sizeof(*addrs)) == 0) {
00962                         /* Rather unlikely as we are non-blocking, but it
00963                          * might actually happen. */
00964                         resulting_index = i;
00965                         goto done;
00966                 }
00967 
00968                 if (errno == EINPROGRESS || errno == EALREADY ||
00969 #ifdef EISCONN
00970                         errno == EISCONN ||
00971 #endif
00972                     errno == EAGAIN || errno == EINTR) {
00973                         /* These are the error messages that something is
00974                            progressing. */
00975                         good_connect = True;
00976                 } else if (errno != 0) {
00977                         /* There was a direct error */
00978                         close(sockets[i]);
00979                         sockets[i] = -1;
00980                 }
00981         }
00982 
00983         if (!good_connect) {
00984                 /* All of the connect's resulted in real error conditions */
00985                 goto done;
00986         }
00987 
00988         /* Lets see if any of the connect attempts succeeded */
00989 
00990         maxfd = 0;
00991         FD_ZERO(&wr_fds);
00992         FD_ZERO(&r_fds);
00993 
00994         for (i=0; i<num_addrs; i++) {
00995                 if (sockets[i] == -1)
00996                         continue;
00997                 FD_SET(sockets[i], &wr_fds);
00998                 FD_SET(sockets[i], &r_fds);
00999                 if (sockets[i]>maxfd)
01000                         maxfd = sockets[i];
01001         }
01002 
01003         tv.tv_sec = 0;
01004         tv.tv_usec = connect_loop;
01005 
01006         res = sys_select_intr(maxfd+1, &r_fds, &wr_fds, NULL, &tv);
01007 
01008         if (res < 0)
01009                 goto done;
01010 
01011         if (res == 0)
01012                 goto next_round;
01013 
01014         for (i=0; i<num_addrs; i++) {
01015 
01016                 if (sockets[i] == -1)
01017                         continue;
01018 
01019                 /* Stevens, Network Programming says that if there's a
01020                  * successful connect, the socket is only writable. Upon an
01021                  * error, it's both readable and writable. */
01022 
01023                 if (FD_ISSET(sockets[i], &r_fds) &&
01024                     FD_ISSET(sockets[i], &wr_fds)) {
01025                         /* readable and writable, so it's an error */
01026                         close(sockets[i]);
01027                         sockets[i] = -1;
01028                         continue;
01029                 }
01030 
01031                 if (!FD_ISSET(sockets[i], &r_fds) &&
01032                     FD_ISSET(sockets[i], &wr_fds)) {
01033                         /* Only writable, so it's connected */
01034                         resulting_index = i;
01035                         goto done;
01036                 }
01037         }
01038 
01039  next_round:
01040 
01041         timeout -= connect_loop;
01042         if (timeout <= 0)
01043                 goto done;
01044         connect_loop *= 1.5;
01045         if (connect_loop > timeout)
01046                 connect_loop = timeout;
01047         goto connect_again;
01048 
01049  done:
01050         for (i=0; i<num_addrs; i++) {
01051                 if (i == resulting_index)
01052                         continue;
01053                 if (sockets[i] >= 0)
01054                         close(sockets[i]);
01055         }
01056 
01057         if (resulting_index >= 0) {
01058                 *fd_index = resulting_index;
01059                 *fd = sockets[*fd_index];
01060                 set_blocking(*fd, True);
01061         }
01062 
01063         free(sockets);
01064 
01065         return (resulting_index >= 0);
01066 }

int open_udp_socket ( const char *  host,
int  port 
)

util_sock.c1071 行で定義されています。

参照先 interpret_addr2()type.

参照元 ads_cldap_netlogon()do_krb5_kpasswd_request().

01072 {
01073         int type = SOCK_DGRAM;
01074         struct sockaddr_in sock_out;
01075         int res;
01076         struct in_addr *addr;
01077 
01078         addr = interpret_addr2(host);
01079 
01080         res = socket(PF_INET, type, 0);
01081         if (res == -1) {
01082                 return -1;
01083         }
01084 
01085         memset((char *)&sock_out,'\0',sizeof(sock_out));
01086         putip((char *)&sock_out.sin_addr,(char *)addr);
01087         sock_out.sin_port = htons(port);
01088         sock_out.sin_family = PF_INET;
01089 
01090         if (connect(res,(struct sockaddr *)&sock_out,sizeof(sock_out))) {
01091                 close(res);
01092                 return -1;
01093         }
01094 
01095         return res;
01096 }

static BOOL matchname ( char *  remotehost,
struct in_addr  addr 
) [static]

util_sock.c1104 行で定義されています。

参照先 strequal()sys_gethostbyname().

参照元 get_peer_name().

01105 {
01106         struct hostent *hp;
01107         int     i;
01108         
01109         if ((hp = sys_gethostbyname(remotehost)) == 0) {
01110                 DEBUG(0,("sys_gethostbyname(%s): lookup failure.\n", remotehost));
01111                 return False;
01112         } 
01113 
01114         /*
01115          * Make sure that gethostbyname() returns the "correct" host name.
01116          * Unfortunately, gethostbyname("localhost") sometimes yields
01117          * "localhost.domain". Since the latter host name comes from the
01118          * local DNS, we just have to trust it (all bets are off if the local
01119          * DNS is perverted). We always check the address list, though.
01120          */
01121         
01122         if (!strequal(remotehost, hp->h_name)
01123             && !strequal(remotehost, "localhost")) {
01124                 DEBUG(0,("host name/name mismatch: %s != %s\n",
01125                          remotehost, hp->h_name));
01126                 return False;
01127         }
01128         
01129         /* Look up the host address in the address list we just got. */
01130         for (i = 0; hp->h_addr_list[i]; i++) {
01131                 if (memcmp(hp->h_addr_list[i], (char *) & addr, sizeof(addr)) == 0)
01132                         return True;
01133         }
01134         
01135         /*
01136          * The host name does not map to the original host address. Perhaps
01137          * someone has compromised a name server. More likely someone botched
01138          * it, but that could be dangerous, too.
01139          */
01140         
01141         DEBUG(0,("host name/address mismatch: %s != %s\n",
01142                  inet_ntoa(addr), hp->h_name));
01143         return False;
01144 }

char* get_peer_name ( int  fd,
BOOL  force_lookup 
)

util_sock.c1150 行で定義されています。

参照先 get_peer_addr()interpret_addr2()matchname().

参照元 cgi_remote_host()check_access()client_name().

01151 {
01152         static pstring name_buf;
01153         pstring tmp_name;
01154         static fstring addr_buf;
01155         struct hostent *hp;
01156         struct in_addr addr;
01157         char *p;
01158 
01159         /* reverse lookups can be *very* expensive, and in many
01160            situations won't work because many networks don't link dhcp
01161            with dns. To avoid the delay we avoid the lookup if
01162            possible */
01163         if (!lp_hostname_lookups() && (force_lookup == False)) {
01164                 return get_peer_addr(fd);
01165         }
01166         
01167         p = get_peer_addr(fd);
01168 
01169         /* it might be the same as the last one - save some DNS work */
01170         if (strcmp(p, addr_buf) == 0) 
01171                 return name_buf;
01172 
01173         pstrcpy(name_buf,"UNKNOWN");
01174         if (fd == -1) 
01175                 return name_buf;
01176 
01177         fstrcpy(addr_buf, p);
01178 
01179         addr = *interpret_addr2(p);
01180         
01181         /* Look up the remote host name. */
01182         if ((hp = gethostbyaddr((char *)&addr.s_addr, sizeof(addr.s_addr), AF_INET)) == 0) {
01183                 DEBUG(1,("Gethostbyaddr failed for %s\n",p));
01184                 pstrcpy(name_buf, p);
01185         } else {
01186                 pstrcpy(name_buf,(char *)hp->h_name);
01187                 if (!matchname(name_buf, addr)) {
01188                         DEBUG(0,("Matchname failed on %s %s\n",name_buf,p));
01189                         pstrcpy(name_buf,"UNKNOWN");
01190                 }
01191         }
01192 
01193         /* can't pass the same source and dest strings in when you 
01194            use --enable-developer or the clobber_region() call will 
01195            get you */
01196         
01197         pstrcpy( tmp_name, name_buf );
01198         alpha_strcpy(name_buf, tmp_name, "_-.", sizeof(name_buf));
01199         if (strstr(name_buf,"..")) {
01200                 pstrcpy(name_buf, "UNKNOWN");
01201         }
01202 
01203         return name_buf;
01204 }

char* get_peer_addr ( int  fd  ) 

util_sock.c1210 行で定義されています。

参照先 errnostrerror().

参照元 cgi_remote_addr()check_access()client_addr()client_setfd()get_peer_name()open_sockets_smbd().

01211 {
01212         struct sockaddr sa;
01213         struct sockaddr_in *sockin = (struct sockaddr_in *) (&sa);
01214         socklen_t length = sizeof(sa);
01215         static fstring addr_buf;
01216 
01217         fstrcpy(addr_buf,"0.0.0.0");
01218 
01219         if (fd == -1) {
01220                 return addr_buf;
01221         }
01222         
01223         if (getpeername(fd, &sa, &length) < 0) {
01224                 DEBUG(0,("getpeername failed. Error was %s\n", strerror(errno) ));
01225                 return addr_buf;
01226         }
01227         
01228         fstrcpy(addr_buf,(char *)inet_ntoa(sockin->sin_addr));
01229         
01230         return addr_buf;
01231 }

int create_pipe_sock ( const char *  socket_dir,
const char *  socket_name,
mode_t  dir_perms 
)

util_sock.c1241 行で定義されています。

参照先 errnopstr_sprintf()sec_initial_uid()strerror().

参照元 open_winbindd_priv_socket()open_winbindd_socket().

01244 {
01245 #ifdef HAVE_UNIXSOCKET
01246         struct sockaddr_un sunaddr;
01247         struct stat st;
01248         int sock;
01249         mode_t old_umask;
01250         pstring path;
01251         
01252         old_umask = umask(0);
01253         
01254         /* Create the socket directory or reuse the existing one */
01255         
01256         if (lstat(socket_dir, &st) == -1) {
01257                 if (errno == ENOENT) {
01258                         /* Create directory */
01259                         if (mkdir(socket_dir, dir_perms) == -1) {
01260                                 DEBUG(0, ("error creating socket directory "
01261                                         "%s: %s\n", socket_dir, 
01262                                         strerror(errno)));
01263                                 goto out_umask;
01264                         }
01265                 } else {
01266                         DEBUG(0, ("lstat failed on socket directory %s: %s\n",
01267                                 socket_dir, strerror(errno)));
01268                         goto out_umask;
01269                 }
01270         } else {
01271                 /* Check ownership and permission on existing directory */
01272                 if (!S_ISDIR(st.st_mode)) {
01273                         DEBUG(0, ("socket directory %s isn't a directory\n",
01274                                 socket_dir));
01275                         goto out_umask;
01276                 }
01277                 if ((st.st_uid != sec_initial_uid()) || 
01278                                 ((st.st_mode & 0777) != dir_perms)) {
01279                         DEBUG(0, ("invalid permissions on socket directory "
01280                                 "%s\n", socket_dir));
01281                         goto out_umask;
01282                 }
01283         }
01284         
01285         /* Create the socket file */
01286         
01287         sock = socket(AF_UNIX, SOCK_STREAM, 0);
01288         
01289         if (sock == -1) {
01290                 perror("socket");
01291                 goto out_umask;
01292         }
01293         
01294         pstr_sprintf(path, "%s/%s", socket_dir, socket_name);
01295         
01296         unlink(path);
01297         memset(&sunaddr, 0, sizeof(sunaddr));
01298         sunaddr.sun_family = AF_UNIX;
01299         safe_strcpy(sunaddr.sun_path, path, sizeof(sunaddr.sun_path)-1);
01300         
01301         if (bind(sock, (struct sockaddr *)&sunaddr, sizeof(sunaddr)) == -1) {
01302                 DEBUG(0, ("bind failed on pipe socket %s: %s\n", path,
01303                         strerror(errno)));
01304                 goto out_close;
01305         }
01306         
01307         if (listen(sock, 5) == -1) {
01308                 DEBUG(0, ("listen failed on pipe socket %s: %s\n", path,
01309                         strerror(errno)));
01310                 goto out_close;
01311         }
01312         
01313         umask(old_umask);
01314         return sock;
01315 
01316 out_close:
01317         close(sock);
01318 
01319 out_umask:
01320         umask(old_umask);
01321         return -1;
01322 
01323 #else
01324         DEBUG(0, ("create_pipe_sock: No Unix sockets on this system\n"));
01325         return -1;
01326 #endif /* HAVE_UNIXSOCKET */
01327 }


変数

int client_fd = -1 [static]

util_sock.c28 行で定義されています。

参照元 client_addr()client_inaddr()client_name()client_setfd()client_socket_addr()client_socket_port()read_data()read_socket_with_timeout()write_data().

char client_ip_string[16] [static]

util_sock.c30 行で定義されています。

参照元 client_setfd()read_data()read_socket_with_timeout()write_data().

struct in_addr lastip

util_sock.c112 行で定義されています。

参照元 parse_packet()read_udp_socket().

int lastport = 0

util_sock.c115 行で定義されています。

参照元 parse_packet()read_udp_socket().

int smb_read_error = 0

util_sock.c117 行で定義されています。

参照元 cli_receive_smb()irix_oplock_receive_message()read_data()read_data_until()read_socket_with_timeout()receive_message_or_smb()receive_smb()receive_smb_raw()timeout_processing().

const smb_socket_option socket_options[] [static]

util_sock.c141 行で定義されています。

参照元 print_socket_options()set_socket_options().


Sambaに対してSat Aug 29 21:23:40 2009に生成されました。  doxygen 1.4.7