change the semantics of hosts allow/hosts deny so that a global
authorAndrew Tridgell <tridge@samba.org>
Thu, 2 Oct 1997 03:14:32 +0000 (03:14 +0000)
committerAndrew Tridgell <tridge@samba.org>
Thu, 2 Oct 1997 03:14:32 +0000 (03:14 +0000)
setting applies to all shares regardless of any settings on other
shares. This allows us to immediately drop a connection if it does not
come from a allowed host, without even parsing the first SMB
packet. The next time we get a nasty security hole we can offer people
the option of just setting their hosts allow line.

If we drop a connection in this way we generate a "Not listening for
calling name" response and then exit.

add a per share "oplocks" option in smb.conf. I think its important to
be able to disable oplocks on a per-share basis as there are occasions
then they are definately not wanted, for example when sharing data
between a windows box and a unix application. This also allows us to
tell people "try disabling oplocks" when diagnosing problems.

fix a bug in process_smb(). It was taking the length of the packet
from outbuf, not inbuf (this bug was introduced with the oplocks
code). Jeremy, I assume this wasn't deliberate?
(This used to be commit 44bc9f239aa0b3cdf6cf9ad8d3911e397eba7335)

docs/manpages/smb.conf.5
source3/include/proto.h
source3/param/loadparm.c
source3/smbd/server.c

index 869dbf9ffd8503f6ce72897256ef8d8af80d83ec..989a395c159c981e121dbbc769191789680e6eef 100644 (file)
@@ -724,10 +724,11 @@ then the "load printers" option is easier.
 A synonym for this parameter is 'hosts allow'.
 
 This parameter is a comma delimited set of hosts which are permitted to access
-a services. If specified in the [global] section, matching hosts will be
-allowed access to any service that does not specifically exclude them from
-access. Specific services my have their own list, which override those
-specified in the [global] section.
+a service. 
+
+If specified in the [global] section then it will apply to all
+services, regardless of whether the individual service has a different
+setting. 
 
 You can specify the hosts by name or IP number. For example, you could
 restrict access to only the hosts on a Class C subnet with something like
index ac81f8cb370b1d768be13b34fa3115d97527a1f3..51433333c5084804db3ed85fb98c5bb5467950e9 100644 (file)
@@ -248,6 +248,7 @@ BOOL lp_map_archive(int );
 BOOL lp_locking(int );
 BOOL lp_strict_locking(int );
 BOOL lp_share_modes(int );
+BOOL lp_oplocks(int );
 BOOL lp_onlyuser(int );
 BOOL lp_manglednames(int );
 BOOL lp_widelinks(int );
index 1a9771df229a4df4050bf56d7599e0ebb8230f6f..fb656aa627fe8e34e53b9b0353bcace9de0db093 100644 (file)
@@ -257,6 +257,7 @@ typedef struct
   BOOL bLocking;
   BOOL bStrictLocking;
   BOOL bShareModes;
+  BOOL bOpLocks;
   BOOL bOnlyUser;
   BOOL bMangledNames;
   BOOL bWidelinks;
@@ -338,6 +339,7 @@ static service sDefault =
   True,  /* bLocking */
   False,  /* bStrictLocking */
   True,  /* bShareModes */
+  True,  /* bOpLocks */
   False, /* bOnlyUser */
   True,  /* bMangledNames */
   True,  /* bWidelinks */
@@ -541,6 +543,7 @@ struct parm_struct
   {"locking",          P_BOOL,    P_LOCAL,  &sDefault.bLocking,         NULL},
   {"strict locking",   P_BOOL,    P_LOCAL,  &sDefault.bStrictLocking,   NULL},
   {"share modes",      P_BOOL,    P_LOCAL,  &sDefault.bShareModes,      NULL},
+  {"oplocks",          P_BOOL,    P_LOCAL,  &sDefault.bOpLocks,         NULL},
   {"only user",        P_BOOL,    P_LOCAL,  &sDefault.bOnlyUser,        NULL},
   {"wide links",       P_BOOL,    P_LOCAL,  &sDefault.bWidelinks,       NULL},
   {"follow symlinks",  P_BOOL,    P_LOCAL,  &sDefault.bSymlinks,        NULL},
@@ -935,6 +938,7 @@ FN_LOCAL_BOOL(lp_map_archive,bMap_archive)
 FN_LOCAL_BOOL(lp_locking,bLocking)
 FN_LOCAL_BOOL(lp_strict_locking,bStrictLocking)
 FN_LOCAL_BOOL(lp_share_modes,bShareModes)
+FN_LOCAL_BOOL(lp_oplocks,bOpLocks)
 FN_LOCAL_BOOL(lp_onlyuser,bOnlyUser)
 FN_LOCAL_BOOL(lp_manglednames,bMangledNames)
 FN_LOCAL_BOOL(lp_widelinks,bWidelinks)
@@ -1138,6 +1142,8 @@ BOOL lp_add_printer(char *pszPrintername, int iDefaultService)
   iSERVICE(i).bRead_only = False;
   /* No share modes on printer services. */
   iSERVICE(i).bShareModes = False;
+  /* No oplocks on printer services. */
+  iSERVICE(i).bOpLocks = False;
   /* Printer services must be printable. */
   iSERVICE(i).bPrint_ok = True;
   
index b9bdbaa65537c281bd980e9f25241c1f5d6e775d..7b04d228c32e3d6c1846423e5f829531f3f4db6e 100644 (file)
@@ -1841,7 +1841,7 @@ dev = %x, inode = %x\n", old_shares[i].op_type, fname, dev, inode));
          be extended to level II oplocks (multiple reader
          oplocks). */
 
-      if(oplock_request && (num_share_modes == 0))
+      if(oplock_request && (num_share_modes == 0) && lp_oplocks(SNUM(cnum)))
       {
         fs_p->granted_oplock = True;
         global_oplocks_open++;
@@ -2412,12 +2412,27 @@ static BOOL open_sockets(BOOL is_daemon,int port)
 static void process_smb(char *inbuf, char *outbuf)
 {
   extern int Client;
-  static int trans_num = 0;
-
+  static int trans_num;
   int msg_type = CVAL(inbuf,0);
-  int32 len = smb_len(outbuf);
+  int32 len = smb_len(inbuf);
   int nread = len + 4;
 
+  if (trans_num == 0) {
+         /* on the first packet, check the global hosts allow/ hosts
+            deny parameters before doing any parsing of the packet
+            passed to us by the client.  This prevents attacks on our
+            parsing code from hosts not in the hosts allow list */
+         if (!check_access(-1)) {
+                 /* send a negative session response "not listining on calling
+                  name" */
+                 static unsigned char buf[5] = {0x83, 0, 0, 1, 0x81};
+                 DEBUG(1,("%s Connection denied from %s\n",
+                          timestring(),client_addr()));
+                 send_smb(Client,buf);
+                 exit_server("connection denied");
+         }
+  }
+
   DEBUG(6,("got message type 0x%x of len 0x%x\n",msg_type,len));
   DEBUG(3,("%s Transaction %d of length %d\n",timestring(),trans_num,nread));