fixed ctemp in server and client. It turns out that ctemp on NT is completely broken...
authorAndrew Tridgell <tridge@samba.org>
Mon, 17 Sep 2001 04:23:48 +0000 (04:23 +0000)
committerAndrew Tridgell <tridge@samba.org>
Mon, 17 Sep 2001 04:23:48 +0000 (04:23 +0000)
(This used to be commit 2d507ec669def6d49304559e53d6c14af9b290a9)

source3/lib/util.c
source3/libsmb/clifile.c
source3/smbd/reply.c
source3/torture/torture.c

index 3d2de63f3865e81f9fe28e7e14eb2703c9f1e874..0eaf7c01fc60705a2ae97a869b2c825d1d20f56d 100644 (file)
@@ -335,20 +335,21 @@ int set_message(char *buf,int num_words,int num_bytes,BOOL zero)
 /*******************************************************************
   setup only the byte count for a smb message
 ********************************************************************/
-void set_message_bcc(char *buf,int num_bytes)
+int set_message_bcc(char *buf,int num_bytes)
 {
        int num_words = CVAL(buf,smb_wct);
        SSVAL(buf,smb_vwv + num_words*SIZEOFWORD,num_bytes);  
        smb_setlen(buf,smb_size + num_words*2 + num_bytes - 4);
+       return (smb_size + num_words*2 + num_bytes);
 }
 
 /*******************************************************************
   setup only the byte count for a smb message, using the end of the
   message as a marker
 ********************************************************************/
-void set_message_end(void *outbuf,void *end_ptr)
+int set_message_end(void *outbuf,void *end_ptr)
 {
-       set_message_bcc((char *)outbuf,PTR_DIFF(end_ptr,smb_buf((char *)outbuf)));
+       return set_message_bcc((char *)outbuf,PTR_DIFF(end_ptr,smb_buf((char *)outbuf)));
 }
 
 /*******************************************************************
index 4e6a89a9ae100f2be82108bcc71de268c2da7b62..e9981d7205ceeca5953ffcd79f2024890dbb3656 100644 (file)
@@ -785,18 +785,20 @@ create and open a temporary file
 ****************************************************************************/
 int cli_ctemp(struct cli_state *cli, char *path, char **tmp_path)
 {
+       int len;
        char *p;
 
        memset(cli->outbuf,'\0',smb_size);
        memset(cli->inbuf,'\0',smb_size);
 
-       set_message(cli->outbuf,1,0,True);
+       set_message(cli->outbuf,3,0,True);
 
        CVAL(cli->outbuf,smb_com) = SMBctemp;
        SSVAL(cli->outbuf,smb_tid,cli->cnum);
        cli_setup_packet(cli);
 
        SSVAL(cli->outbuf,smb_vwv0,0);
+       SIVALS(cli->outbuf,smb_vwv1,-1);
 
        p = smb_buf(cli->outbuf);
        *p++ = 4;
@@ -813,10 +815,17 @@ int cli_ctemp(struct cli_state *cli, char *path, char **tmp_path)
                return -1;
        }
 
+       /* despite the spec, the result has a -1, followed by
+          length, followed by name */
+       p = smb_buf(cli->inbuf);
+       p += 4;
+       len = smb_buflen(cli->inbuf) - 4;
+       if (len <= 0) return -1;
+
        if (tmp_path) {
                pstring path2;
-               clistr_pull(cli, path2, smb_buf(cli->inbuf)+1
-                           sizeof(path2), -1, STR_TERMINATE);
+               clistr_pull(cli, path2, p
+                           sizeof(path2), len, STR_ASCII);
                *tmp_path = strdup(path2);
        }
 
index 1559cd30dfadbb8010aa8690646144e82b1e8e81..3dca20958107b1954a584748b23915a912e8487b 100644 (file)
@@ -1581,13 +1581,13 @@ int reply_ctemp(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
   int oplock_request = CORE_OPLOCK_REQUEST(inbuf);
   int tmpfd;
   SMB_STRUCT_STAT sbuf;
-  char *p;
+  char *p, *s;
 
   START_PROFILE(SMBctemp);
 
   createmode = SVAL(inbuf,smb_vwv0);
   srvstr_pull(inbuf, fname, smb_buf(inbuf)+1, sizeof(fname), -1, STR_TERMINATE);
-  pstrcat(fname,"/TMXXXXXX");
+  pstrcat(fname,"\\TMXXXXXX");
 
   RESOLVE_DFSPATH(fname, conn, inbuf, outbuf);
 
@@ -1626,17 +1626,28 @@ int reply_ctemp(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
 
   outsize = set_message(outbuf,1,0,True);
   SSVAL(outbuf,smb_vwv0,fsp->fnum);
-  CVAL(smb_buf(outbuf),0) = 4;
-  p = smb_buf(outbuf) + 1;
-  p += srvstr_push(outbuf, p, fname, -1, STR_TERMINATE);
-  set_message_end(outbuf, p);
+
+  /* the returned filename is relative to the directory */
+  s = strrchr_m(fname, '/');
+  if (!s) {
+         s = fname;
+  } else {
+         s++;
+  }
+
+  p = smb_buf(outbuf);
+  SSVALS(p, 0, -1); /* what is this? not in spec */
+  SSVAL(p, 2, strlen(s));
+  p += 4;
+  p += srvstr_push(outbuf, p, s, -1, STR_ASCII);
+  outsize = set_message_end(outbuf, p);
 
   if (oplock_request && lp_fake_oplocks(SNUM(conn))) {
-    CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
+         CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
   }
   
-  if(EXCLUSIVE_OPLOCK_TYPE(fsp->oplock_type))
-    CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
+  if (EXCLUSIVE_OPLOCK_TYPE(fsp->oplock_type))
+         CVAL(outbuf,smb_flg) |= CORE_OPLOCK_GRANTED;
 
   DEBUG( 2, ( "created temp file %s\n", fname ) );
   DEBUG( 3, ( "ctemp %s fd=%d dmode=%d umode=%o\n",
index fb581baa5ed1bb29831f108ed0ba8c0dc4383869..33260dcc544f6543426de8ace2021f6fa804d50f 100644 (file)
@@ -2639,6 +2639,7 @@ static BOOL run_opentest(int dummy)
        char buf[20];
        size_t fsize;
        BOOL correct = True;
+       char *tmp_path;
 
        printf("starting open test\n");
        
@@ -2774,16 +2775,17 @@ static BOOL run_opentest(int dummy)
 
 
        printf("testing ctemp\n");
-       {
-               char *tmp_path;
-               fnum1 = cli_ctemp(&cli1, "\\", &tmp_path);
-               if (fnum1 == -1) {
-                       printf("ctemp failed (%s)\n", cli_errstr(&cli1));
-                       return False;
-               }
-               printf("ctemp gave path %s\n", tmp_path);
-               cli_close(&cli1, fnum1);
-               cli_unlink(&cli1, tmp_path);
+       fnum1 = cli_ctemp(&cli1, "\\", &tmp_path);
+       if (fnum1 == -1) {
+               printf("ctemp failed (%s)\n", cli_errstr(&cli1));
+               return False;
+       }
+       printf("ctemp gave path %s\n", tmp_path);
+       if (!cli_close(&cli1, fnum1)) {
+               printf("close of temp failed (%s)\n", cli_errstr(&cli1));
+       }
+       if (!cli_unlink(&cli1, tmp_path)) {
+               printf("unlink of temp failed (%s)\n", cli_errstr(&cli1));
        }
        
        if (!torture_close_connection(&cli1)) {