Fossil with Commonmark

Hex Artifact Content
Login

Artifact 8e85e61f94faf64efd92db024e19d83cf30ac0a1:


0000: 2f 2a 0a 2a 2a 20 43 6f 70 79 72 69 67 68 74 20  /*.** Copyright 
0010: 28 63 29 20 32 30 30 36 20 44 2e 20 52 69 63 68  (c) 2006 D. Rich
0020: 61 72 64 20 48 69 70 70 0a 2a 2a 0a 2a 2a 20 54  ard Hipp.**.** T
0030: 68 69 73 20 70 72 6f 67 72 61 6d 20 69 73 20 66  his program is f
0040: 72 65 65 20 73 6f 66 74 77 61 72 65 3b 20 79 6f  ree software; yo
0050: 75 20 63 61 6e 20 72 65 64 69 73 74 72 69 62 75  u can redistribu
0060: 74 65 20 69 74 20 61 6e 64 2f 6f 72 0a 2a 2a 20  te it and/or.** 
0070: 6d 6f 64 69 66 79 20 69 74 20 75 6e 64 65 72 20  modify it under 
0080: 74 68 65 20 74 65 72 6d 73 20 6f 66 20 74 68 65  the terms of the
0090: 20 53 69 6d 70 6c 69 66 69 65 64 20 42 53 44 20   Simplified BSD 
00a0: 4c 69 63 65 6e 73 65 20 28 61 6c 73 6f 0a 2a 2a  License (also.**
00b0: 20 6b 6e 6f 77 6e 20 61 73 20 74 68 65 20 22 32   known as the "2
00c0: 2d 43 6c 61 75 73 65 20 4c 69 63 65 6e 73 65 22  -Clause License"
00d0: 20 6f 72 20 22 46 72 65 65 42 53 44 20 4c 69 63   or "FreeBSD Lic
00e0: 65 6e 73 65 22 2e 29 0a 0a 2a 2a 20 54 68 69 73  ense".)..** This
00f0: 20 70 72 6f 67 72 61 6d 20 69 73 20 64 69 73 74   program is dist
0100: 72 69 62 75 74 65 64 20 69 6e 20 74 68 65 20 68  ributed in the h
0110: 6f 70 65 20 74 68 61 74 20 69 74 20 77 69 6c 6c  ope that it will
0120: 20 62 65 20 75 73 65 66 75 6c 2c 0a 2a 2a 20 62   be useful,.** b
0130: 75 74 20 77 69 74 68 6f 75 74 20 61 6e 79 20 77  ut without any w
0140: 61 72 72 61 6e 74 79 3b 20 77 69 74 68 6f 75 74  arranty; without
0150: 20 65 76 65 6e 20 74 68 65 20 69 6d 70 6c 69 65   even the implie
0160: 64 20 77 61 72 72 61 6e 74 79 20 6f 66 0a 2a 2a  d warranty of.**
0170: 20 6d 65 72 63 68 61 6e 74 61 62 69 6c 69 74 79   merchantability
0180: 20 6f 72 20 66 69 74 6e 65 73 73 20 66 6f 72 20   or fitness for 
0190: 61 20 70 61 72 74 69 63 75 6c 61 72 20 70 75 72  a particular pur
01a0: 70 6f 73 65 2e 0a 2a 2a 0a 2a 2a 20 41 75 74 68  pose..**.** Auth
01b0: 6f 72 20 63 6f 6e 74 61 63 74 20 69 6e 66 6f 72  or contact infor
01c0: 6d 61 74 69 6f 6e 3a 0a 2a 2a 20 20 20 64 72 68  mation:.**   drh
01d0: 40 68 77 61 63 69 2e 63 6f 6d 0a 2a 2a 20 20 20  @hwaci.com.**   
01e0: 68 74 74 70 3a 2f 2f 77 77 77 2e 68 77 61 63 69  http://www.hwaci
01f0: 2e 63 6f 6d 2f 64 72 68 2f 0a 2a 2a 0a 2a 2a 2a  .com/drh/.**.***
0200: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0210: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0220: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0230: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a  ****************
0240: 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 2a 0a 2a 2a 0a  ************.**.
0250: 2a 2a 20 46 69 6c 65 20 75 74 69 6c 69 74 69 65  ** File utilitie
0260: 73 2e 0a 2a 2a 0a 2a 2a 20 46 75 6e 63 74 69 6f  s..**.** Functio
0270: 6e 73 20 6e 61 6d 65 64 20 66 69 6c 65 5f 2a 20  ns named file_* 
0280: 61 72 65 20 67 65 6e 65 72 69 63 20 66 75 6e 63  are generic func
0290: 74 69 6f 6e 73 20 74 68 61 74 20 61 6c 77 61 79  tions that alway
02a0: 73 20 66 6f 6c 6c 6f 77 20 73 79 6d 6c 69 6e 6b  s follow symlink
02b0: 73 2e 0a 2a 2a 0a 2a 2a 20 46 75 6e 63 74 69 6f  s..**.** Functio
02c0: 6e 73 20 6e 61 6d 65 64 20 66 69 6c 65 5f 77 64  ns named file_wd
02d0: 5f 2a 20 61 72 65 20 74 6f 20 62 65 20 75 73 65  _* are to be use
02e0: 64 20 66 6f 72 20 66 69 6c 65 73 20 69 6e 73 69  d for files insi
02f0: 64 65 20 77 6f 72 6b 69 6e 67 0a 2a 2a 20 64 69  de working.** di
0300: 72 65 63 74 6f 72 69 65 73 2e 20 54 68 65 79 20  rectories. They 
0310: 66 6f 6c 6c 6f 77 20 73 79 6d 6c 69 6e 6b 73 20  follow symlinks 
0320: 64 65 70 65 6e 64 69 6e 67 20 6f 6e 20 27 61 6c  depending on 'al
0330: 6c 6f 77 2d 73 79 6d 6c 69 6e 6b 73 27 20 73 65  low-symlinks' se
0340: 74 74 69 6e 67 2e 0a 2a 2f 0a 23 69 6e 63 6c 75  tting..*/.#inclu
0350: 64 65 20 22 63 6f 6e 66 69 67 2e 68 22 0a 23 69  de "config.h".#i
0360: 6e 63 6c 75 64 65 20 3c 73 79 73 2f 74 79 70 65  nclude <sys/type
0370: 73 2e 68 3e 0a 23 69 6e 63 6c 75 64 65 20 3c 73  s.h>.#include <s
0380: 79 73 2f 73 74 61 74 2e 68 3e 0a 23 69 6e 63 6c  ys/stat.h>.#incl
0390: 75 64 65 20 3c 75 6e 69 73 74 64 2e 68 3e 0a 23  ude <unistd.h>.#
03a0: 69 6e 63 6c 75 64 65 20 3c 73 74 64 69 6f 2e 68  include <stdio.h
03b0: 3e 0a 23 69 6e 63 6c 75 64 65 20 3c 73 74 72 69  >.#include <stri
03c0: 6e 67 2e 68 3e 0a 23 69 6e 63 6c 75 64 65 20 3c  ng.h>.#include <
03d0: 65 72 72 6e 6f 2e 68 3e 0a 23 69 6e 63 6c 75 64  errno.h>.#includ
03e0: 65 20 22 66 69 6c 65 2e 68 22 0a 0a 2f 2a 0a 2a  e "file.h"../*.*
03f0: 2a 20 4f 6e 20 57 69 6e 64 6f 77 73 2c 20 69 6e  * On Windows, in
0400: 63 6c 75 64 65 20 74 68 65 20 50 6c 61 74 66 6f  clude the Platfo
0410: 72 6d 20 53 44 4b 20 68 65 61 64 65 72 20 66 69  rm SDK header fi
0420: 6c 65 2e 0a 2a 2f 0a 23 69 66 64 65 66 20 5f 57  le..*/.#ifdef _W
0430: 49 4e 33 32 0a 23 20 69 6e 63 6c 75 64 65 20 3c  IN32.# include <
0440: 64 69 72 65 63 74 2e 68 3e 0a 23 20 69 6e 63 6c  direct.h>.# incl
0450: 75 64 65 20 3c 77 69 6e 64 6f 77 73 2e 68 3e 0a  ude <windows.h>.
0460: 23 20 69 6e 63 6c 75 64 65 20 3c 73 79 73 2f 75  # include <sys/u
0470: 74 69 6d 65 2e 68 3e 0a 23 65 6c 73 65 0a 23 20  time.h>.#else.# 
0480: 69 6e 63 6c 75 64 65 20 3c 73 79 73 2f 74 69 6d  include <sys/tim
0490: 65 2e 68 3e 0a 23 65 6e 64 69 66 0a 0a 23 69 66  e.h>.#endif..#if
04a0: 20 49 4e 54 45 52 46 41 43 45 0a 0a 23 69 6e 63   INTERFACE..#inc
04b0: 6c 75 64 65 20 3c 64 69 72 65 6e 74 2e 68 3e 0a  lude <dirent.h>.
04c0: 23 69 66 20 64 65 66 69 6e 65 64 28 5f 57 49 4e  #if defined(_WIN
04d0: 33 32 29 0a 23 20 64 65 66 69 6e 65 20 44 49 52  32).# define DIR
04e0: 20 5f 57 44 49 52 0a 23 20 64 65 66 69 6e 65 20   _WDIR.# define 
04f0: 64 69 72 65 6e 74 20 5f 77 64 69 72 65 6e 74 0a  dirent _wdirent.
0500: 23 20 64 65 66 69 6e 65 20 6f 70 65 6e 64 69 72  # define opendir
0510: 20 5f 77 6f 70 65 6e 64 69 72 0a 23 20 64 65 66   _wopendir.# def
0520: 69 6e 65 20 72 65 61 64 64 69 72 20 5f 77 72 65  ine readdir _wre
0530: 61 64 64 69 72 0a 23 20 64 65 66 69 6e 65 20 63  addir.# define c
0540: 6c 6f 73 65 64 69 72 20 5f 77 63 6c 6f 73 65 64  losedir _wclosed
0550: 69 72 0a 23 65 6e 64 69 66 20 2f 2a 20 5f 57 49  ir.#endif /* _WI
0560: 4e 33 32 20 2a 2f 0a 0a 23 69 66 20 64 65 66 69  N32 */..#if defi
0570: 6e 65 64 28 5f 57 49 4e 33 32 29 20 26 26 20 28  ned(_WIN32) && (
0580: 64 65 66 69 6e 65 64 28 5f 5f 4d 53 56 43 52 54  defined(__MSVCRT
0590: 5f 5f 29 20 7c 7c 20 64 65 66 69 6e 65 64 28 5f  __) || defined(_
05a0: 4d 53 43 5f 56 45 52 29 29 0a 73 74 72 75 63 74  MSC_VER)).struct
05b0: 20 66 6f 73 73 69 6c 53 74 61 74 20 7b 0a 20 20   fossilStat {.  
05c0: 20 20 69 36 34 20 73 74 5f 73 69 7a 65 3b 0a 20    i64 st_size;. 
05d0: 20 20 20 69 36 34 20 73 74 5f 6d 74 69 6d 65 3b     i64 st_mtime;
05e0: 0a 20 20 20 20 69 6e 74 20 73 74 5f 6d 6f 64 65  .    int st_mode
05f0: 3b 0a 7d 3b 0a 23 65 6e 64 69 66 0a 0a 23 69 66  ;.};.#endif..#if
0600: 20 64 65 66 69 6e 65 64 28 5f 57 49 4e 33 32 29   defined(_WIN32)
0610: 20 7c 7c 20 64 65 66 69 6e 65 64 28 5f 5f 43 59   || defined(__CY
0620: 47 57 49 4e 5f 5f 29 0a 23 20 64 65 66 69 6e 65  GWIN__).# define
0630: 20 66 6f 73 73 69 6c 5f 69 73 64 69 72 73 65 70   fossil_isdirsep
0640: 28 61 29 20 20 20 20 28 28 28 61 29 20 3d 3d 20  (a)    (((a) == 
0650: 27 2f 27 29 20 7c 7c 20 28 28 61 29 20 3d 3d 20  '/') || ((a) == 
0660: 27 5c 5c 27 29 29 0a 23 65 6c 73 65 0a 23 20 64  '\\')).#else.# d
0670: 65 66 69 6e 65 20 66 6f 73 73 69 6c 5f 69 73 64  efine fossil_isd
0680: 69 72 73 65 70 28 61 29 20 20 20 20 28 28 61 29  irsep(a)    ((a)
0690: 20 3d 3d 20 27 2f 27 29 0a 23 65 6e 64 69 66 0a   == '/').#endif.
06a0: 0a 23 65 6e 64 69 66 20 2f 2a 20 49 4e 54 45 52  .#endif /* INTER
06b0: 46 41 43 45 20 2a 2f 0a 0a 23 69 66 20 21 64 65  FACE */..#if !de
06c0: 66 69 6e 65 64 28 5f 57 49 4e 33 32 29 20 7c 7c  fined(_WIN32) ||
06d0: 20 21 28 64 65 66 69 6e 65 64 28 5f 5f 4d 53 56   !(defined(__MSV
06e0: 43 52 54 5f 5f 29 20 7c 7c 20 64 65 66 69 6e 65  CRT__) || define
06f0: 64 28 5f 4d 53 43 5f 56 45 52 29 29 0a 23 20 64  d(_MSC_VER)).# d
0700: 65 66 69 6e 65 20 66 6f 73 73 69 6c 53 74 61 74  efine fossilStat
0710: 20 73 74 61 74 0a 23 65 6e 64 69 66 0a 0a 2f 2a   stat.#endif../*
0720: 0a 2a 2a 20 4f 6e 20 57 69 6e 64 6f 77 73 20 53  .** On Windows S
0730: 5f 49 53 4c 4e 4b 20 61 6c 77 61 79 73 20 72 65  _ISLNK always re
0740: 74 75 72 6e 73 20 46 41 4c 53 45 2e 0a 2a 2f 0a  turns FALSE..*/.
0750: 23 69 66 20 21 64 65 66 69 6e 65 64 28 53 5f 49  #if !defined(S_I
0760: 53 4c 4e 4b 29 0a 23 20 64 65 66 69 6e 65 20 53  SLNK).# define S
0770: 5f 49 53 4c 4e 4b 28 78 29 20 28 30 29 0a 23 65  _ISLNK(x) (0).#e
0780: 6e 64 69 66 0a 73 74 61 74 69 63 20 69 6e 74 20  ndif.static int 
0790: 66 69 6c 65 53 74 61 74 56 61 6c 69 64 20 3d 20  fileStatValid = 
07a0: 30 3b 0a 73 74 61 74 69 63 20 73 74 72 75 63 74  0;.static struct
07b0: 20 66 6f 73 73 69 6c 53 74 61 74 20 66 69 6c 65   fossilStat file
07c0: 53 74 61 74 3b 0a 0a 2f 2a 0a 2a 2a 20 46 69 6c  Stat;../*.** Fil
07d0: 6c 20 73 74 61 74 20 62 75 66 20 77 69 74 68 20  l stat buf with 
07e0: 69 6e 66 6f 72 6d 61 74 69 6f 6e 20 72 65 63 65  information rece
07f0: 69 76 65 64 20 66 72 6f 6d 20 73 74 61 74 28 29  ived from stat()
0800: 20 6f 72 20 6c 73 74 61 74 28 29 2e 0a 2a 2a 20   or lstat()..** 
0810: 6c 73 74 61 74 28 29 20 69 73 20 63 61 6c 6c 65  lstat() is calle
0820: 64 20 6f 6e 20 55 6e 69 78 20 69 66 20 69 73 57  d on Unix if isW
0830: 64 20 69 73 20 54 52 55 45 20 61 6e 64 20 61 6c  d is TRUE and al
0840: 6c 6f 77 2d 73 79 6d 6c 69 6e 6b 73 20 73 65 74  low-symlinks set
0850: 74 69 6e 67 20 69 73 20 6f 6e 2e 0a 2a 2a 0a 2a  ting is on..**.*
0860: 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 66 6f 73  /.static int fos
0870: 73 69 6c 5f 73 74 61 74 28 63 6f 6e 73 74 20 63  sil_stat(const c
0880: 68 61 72 20 2a 7a 46 69 6c 65 6e 61 6d 65 2c 20  har *zFilename, 
0890: 73 74 72 75 63 74 20 66 6f 73 73 69 6c 53 74 61  struct fossilSta
08a0: 74 20 2a 62 75 66 2c 20 69 6e 74 20 69 73 57 64  t *buf, int isWd
08b0: 29 7b 0a 20 20 69 6e 74 20 72 63 3b 0a 20 20 76  ){.  int rc;.  v
08c0: 6f 69 64 20 2a 7a 4d 62 63 73 20 3d 20 66 6f 73  oid *zMbcs = fos
08d0: 73 69 6c 5f 75 74 66 38 5f 74 6f 5f 70 61 74 68  sil_utf8_to_path
08e0: 28 7a 46 69 6c 65 6e 61 6d 65 2c 20 30 29 3b 0a  (zFilename, 0);.
08f0: 23 69 66 20 21 64 65 66 69 6e 65 64 28 5f 57 49  #if !defined(_WI
0900: 4e 33 32 29 0a 20 20 69 66 28 20 69 73 57 64 20  N32).  if( isWd 
0910: 26 26 20 67 2e 61 6c 6c 6f 77 53 79 6d 6c 69 6e  && g.allowSymlin
0920: 6b 73 20 29 7b 0a 20 20 20 20 72 63 20 3d 20 6c  ks ){.    rc = l
0930: 73 74 61 74 28 7a 4d 62 63 73 2c 20 62 75 66 29  stat(zMbcs, buf)
0940: 3b 0a 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 72  ;.  }else{.    r
0950: 63 20 3d 20 73 74 61 74 28 7a 4d 62 63 73 2c 20  c = stat(zMbcs, 
0960: 62 75 66 29 3b 0a 20 20 7d 0a 23 65 6c 73 65 0a  buf);.  }.#else.
0970: 20 20 72 63 20 3d 20 77 69 6e 33 32 5f 73 74 61    rc = win32_sta
0980: 74 28 7a 4d 62 63 73 2c 20 62 75 66 2c 20 69 73  t(zMbcs, buf, is
0990: 57 64 29 3b 0a 23 65 6e 64 69 66 0a 20 20 66 6f  Wd);.#endif.  fo
09a0: 73 73 69 6c 5f 70 61 74 68 5f 66 72 65 65 28 7a  ssil_path_free(z
09b0: 4d 62 63 73 29 3b 0a 20 20 72 65 74 75 72 6e 20  Mbcs);.  return 
09c0: 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 46 69 6c  rc;.}../*.** Fil
09d0: 6c 20 69 6e 20 74 68 65 20 66 69 6c 65 53 74 61  l in the fileSta
09e0: 74 20 76 61 72 69 61 62 6c 65 20 66 6f 72 20 74  t variable for t
09f0: 68 65 20 66 69 6c 65 20 6e 61 6d 65 64 20 7a 46  he file named zF
0a00: 69 6c 65 6e 61 6d 65 2e 0a 2a 2a 20 49 66 20 7a  ilename..** If z
0a10: 46 69 6c 65 6e 61 6d 65 3d 3d 30 2c 20 74 68 65  Filename==0, the
0a20: 6e 20 75 73 65 20 74 68 65 20 70 72 65 76 69 6f  n use the previo
0a30: 75 73 20 76 61 6c 75 65 20 6f 66 20 66 69 6c 65  us value of file
0a40: 53 74 61 74 20 69 66 0a 2a 2a 20 74 68 65 72 65  Stat if.** there
0a50: 20 69 73 20 61 20 70 72 65 76 69 6f 75 73 20 76   is a previous v
0a60: 61 6c 75 65 2e 0a 2a 2a 0a 2a 2a 20 49 66 20 69  alue..**.** If i
0a70: 73 57 64 20 69 73 20 54 52 55 45 2c 20 64 6f 20  sWd is TRUE, do 
0a80: 6c 73 74 61 74 28 29 20 69 6e 73 74 65 61 64 20  lstat() instead 
0a90: 6f 66 20 73 74 61 74 28 29 20 69 66 20 61 6c 6c  of stat() if all
0aa0: 6f 77 2d 73 79 6d 6c 69 6e 6b 73 20 69 73 20 6f  ow-symlinks is o
0ab0: 6e 2e 0a 2a 2a 0a 2a 2a 20 52 65 74 75 72 6e 20  n..**.** Return 
0ac0: 74 68 65 20 6e 75 6d 62 65 72 20 6f 66 20 65 72  the number of er
0ad0: 72 6f 72 73 2e 20 20 4e 6f 20 65 72 72 6f 72 20  rors.  No error 
0ae0: 6d 65 73 73 61 67 65 73 20 61 72 65 20 67 65 6e  messages are gen
0af0: 65 72 61 74 65 64 2e 0a 2a 2f 0a 73 74 61 74 69  erated..*/.stati
0b00: 63 20 69 6e 74 20 67 65 74 53 74 61 74 28 63 6f  c int getStat(co
0b10: 6e 73 74 20 63 68 61 72 20 2a 7a 46 69 6c 65 6e  nst char *zFilen
0b20: 61 6d 65 2c 20 69 6e 74 20 69 73 57 64 29 7b 0a  ame, int isWd){.
0b30: 20 20 69 6e 74 20 72 63 20 3d 20 30 3b 0a 20 20    int rc = 0;.  
0b40: 69 66 28 20 7a 46 69 6c 65 6e 61 6d 65 3d 3d 30  if( zFilename==0
0b50: 20 29 7b 0a 20 20 20 20 69 66 28 20 66 69 6c 65   ){.    if( file
0b60: 53 74 61 74 56 61 6c 69 64 3d 3d 30 20 29 20 72  StatValid==0 ) r
0b70: 63 20 3d 20 31 3b 0a 20 20 7d 65 6c 73 65 7b 0a  c = 1;.  }else{.
0b80: 20 20 20 20 69 66 28 20 66 6f 73 73 69 6c 5f 73      if( fossil_s
0b90: 74 61 74 28 7a 46 69 6c 65 6e 61 6d 65 2c 20 26  tat(zFilename, &
0ba0: 66 69 6c 65 53 74 61 74 2c 20 69 73 57 64 29 21  fileStat, isWd)!
0bb0: 3d 30 20 29 7b 0a 20 20 20 20 20 20 66 69 6c 65  =0 ){.      file
0bc0: 53 74 61 74 56 61 6c 69 64 20 3d 20 30 3b 0a 20  StatValid = 0;. 
0bd0: 20 20 20 20 20 72 63 20 3d 20 31 3b 0a 20 20 20       rc = 1;.   
0be0: 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 66 69   }else{.      fi
0bf0: 6c 65 53 74 61 74 56 61 6c 69 64 20 3d 20 31 3b  leStatValid = 1;
0c00: 0a 20 20 20 20 20 20 72 63 20 3d 20 30 3b 0a 20  .      rc = 0;. 
0c10: 20 20 20 7d 0a 20 20 7d 0a 20 20 72 65 74 75 72     }.  }.  retur
0c20: 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 52  n rc;.}../*.** R
0c30: 65 74 75 72 6e 20 74 68 65 20 73 69 7a 65 20 6f  eturn the size o
0c40: 66 20 61 20 66 69 6c 65 20 69 6e 20 62 79 74 65  f a file in byte
0c50: 73 2e 20 20 52 65 74 75 72 6e 20 2d 31 20 69 66  s.  Return -1 if
0c60: 20 74 68 65 20 66 69 6c 65 20 64 6f 65 73 20 6e   the file does n
0c70: 6f 74 0a 2a 2a 20 65 78 69 73 74 2e 20 20 49 66  ot.** exist.  If
0c80: 20 7a 46 69 6c 65 6e 61 6d 65 20 69 73 20 4e 55   zFilename is NU
0c90: 4c 4c 2c 20 72 65 74 75 72 6e 20 74 68 65 20 73  LL, return the s
0ca0: 69 7a 65 20 6f 66 20 74 68 65 20 6d 6f 73 74 20  ize of the most 
0cb0: 72 65 63 65 6e 74 6c 79 0a 2a 2a 20 73 74 61 74  recently.** stat
0cc0: 2d 65 64 20 66 69 6c 65 2e 0a 2a 2f 0a 69 36 34  -ed file..*/.i64
0cd0: 20 66 69 6c 65 5f 73 69 7a 65 28 63 6f 6e 73 74   file_size(const
0ce0: 20 63 68 61 72 20 2a 7a 46 69 6c 65 6e 61 6d 65   char *zFilename
0cf0: 29 7b 0a 20 20 72 65 74 75 72 6e 20 67 65 74 53  ){.  return getS
0d00: 74 61 74 28 7a 46 69 6c 65 6e 61 6d 65 2c 20 30  tat(zFilename, 0
0d10: 29 20 3f 20 2d 31 20 3a 20 66 69 6c 65 53 74 61  ) ? -1 : fileSta
0d20: 74 2e 73 74 5f 73 69 7a 65 3b 0a 7d 0a 0a 2f 2a  t.st_size;.}../*
0d30: 0a 2a 2a 20 53 61 6d 65 20 61 73 20 66 69 6c 65  .** Same as file
0d40: 5f 73 69 7a 65 28 29 2c 20 62 75 74 20 74 61 6b  _size(), but tak
0d50: 65 73 20 69 6e 74 6f 20 61 63 63 6f 75 6e 74 20  es into account 
0d60: 73 79 6d 6c 69 6e 6b 73 2e 0a 2a 2f 0a 69 36 34  symlinks..*/.i64
0d70: 20 66 69 6c 65 5f 77 64 5f 73 69 7a 65 28 63 6f   file_wd_size(co
0d80: 6e 73 74 20 63 68 61 72 20 2a 7a 46 69 6c 65 6e  nst char *zFilen
0d90: 61 6d 65 29 7b 0a 20 20 72 65 74 75 72 6e 20 67  ame){.  return g
0da0: 65 74 53 74 61 74 28 7a 46 69 6c 65 6e 61 6d 65  etStat(zFilename
0db0: 2c 20 31 29 20 3f 20 2d 31 20 3a 20 66 69 6c 65  , 1) ? -1 : file
0dc0: 53 74 61 74 2e 73 74 5f 73 69 7a 65 3b 0a 7d 0a  Stat.st_size;.}.
0dd0: 0a 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 74 68  ./*.** Return th
0de0: 65 20 6d 6f 64 69 66 69 63 61 74 69 6f 6e 20 74  e modification t
0df0: 69 6d 65 20 66 6f 72 20 61 20 66 69 6c 65 2e 20  ime for a file. 
0e00: 20 52 65 74 75 72 6e 20 2d 31 20 69 66 20 74 68   Return -1 if th
0e10: 65 20 66 69 6c 65 0a 2a 2a 20 64 6f 65 73 20 6e  e file.** does n
0e20: 6f 74 20 65 78 69 73 74 2e 20 20 49 66 20 7a 46  ot exist.  If zF
0e30: 69 6c 65 6e 61 6d 65 20 69 73 20 4e 55 4c 4c 20  ilename is NULL 
0e40: 72 65 74 75 72 6e 20 74 68 65 20 73 69 7a 65 20  return the size 
0e50: 6f 66 20 74 68 65 20 6d 6f 73 74 0a 2a 2a 20 72  of the most.** r
0e60: 65 63 65 6e 74 6c 79 20 73 74 61 74 2d 65 64 20  ecently stat-ed 
0e70: 66 69 6c 65 2e 0a 2a 2f 0a 69 36 34 20 66 69 6c  file..*/.i64 fil
0e80: 65 5f 6d 74 69 6d 65 28 63 6f 6e 73 74 20 63 68  e_mtime(const ch
0e90: 61 72 20 2a 7a 46 69 6c 65 6e 61 6d 65 29 7b 0a  ar *zFilename){.
0ea0: 20 20 72 65 74 75 72 6e 20 67 65 74 53 74 61 74    return getStat
0eb0: 28 7a 46 69 6c 65 6e 61 6d 65 2c 20 30 29 20 3f  (zFilename, 0) ?
0ec0: 20 2d 31 20 3a 20 66 69 6c 65 53 74 61 74 2e 73   -1 : fileStat.s
0ed0: 74 5f 6d 74 69 6d 65 3b 0a 7d 0a 0a 2f 2a 0a 2a  t_mtime;.}../*.*
0ee0: 2a 20 53 61 6d 65 20 61 73 20 66 69 6c 65 5f 6d  * Same as file_m
0ef0: 74 69 6d 65 28 29 2c 20 62 75 74 20 74 61 6b 65  time(), but take
0f00: 73 20 69 6e 74 6f 20 61 63 63 6f 75 6e 74 20 73  s into account s
0f10: 79 6d 6c 69 6e 6b 73 2e 0a 2a 2f 0a 69 36 34 20  ymlinks..*/.i64 
0f20: 66 69 6c 65 5f 77 64 5f 6d 74 69 6d 65 28 63 6f  file_wd_mtime(co
0f30: 6e 73 74 20 63 68 61 72 20 2a 7a 46 69 6c 65 6e  nst char *zFilen
0f40: 61 6d 65 29 7b 0a 20 20 72 65 74 75 72 6e 20 67  ame){.  return g
0f50: 65 74 53 74 61 74 28 7a 46 69 6c 65 6e 61 6d 65  etStat(zFilename
0f60: 2c 20 31 29 20 3f 20 2d 31 20 3a 20 66 69 6c 65  , 1) ? -1 : file
0f70: 53 74 61 74 2e 73 74 5f 6d 74 69 6d 65 3b 0a 7d  Stat.st_mtime;.}
0f80: 0a 0a 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 54  ../*.** Return T
0f90: 52 55 45 20 69 66 20 74 68 65 20 6e 61 6d 65 64  RUE if the named
0fa0: 20 66 69 6c 65 20 69 73 20 61 6e 20 6f 72 64 69   file is an ordi
0fb0: 6e 61 72 79 20 66 69 6c 65 20 6f 72 20 73 79 6d  nary file or sym
0fc0: 6c 69 6e 6b 0a 2a 2a 20 61 6e 64 20 73 79 6d 6c  link.** and syml
0fd0: 69 6e 6b 73 20 61 72 65 20 61 6c 6c 6f 77 65 64  inks are allowed
0fe0: 2e 0a 2a 2a 20 52 65 74 75 72 6e 20 66 61 6c 73  ..** Return fals
0ff0: 65 20 66 6f 72 20 64 69 72 65 63 74 6f 72 69 65  e for directorie
1000: 73 2c 20 64 65 76 69 63 65 73 2c 20 66 69 66 6f  s, devices, fifo
1010: 73 2c 20 65 74 63 2e 0a 2a 2f 0a 69 6e 74 20 66  s, etc..*/.int f
1020: 69 6c 65 5f 77 64 5f 69 73 66 69 6c 65 5f 6f 72  ile_wd_isfile_or
1030: 5f 6c 69 6e 6b 28 63 6f 6e 73 74 20 63 68 61 72  _link(const char
1040: 20 2a 7a 46 69 6c 65 6e 61 6d 65 29 7b 0a 20 20   *zFilename){.  
1050: 72 65 74 75 72 6e 20 67 65 74 53 74 61 74 28 7a  return getStat(z
1060: 46 69 6c 65 6e 61 6d 65 2c 20 31 29 20 3f 20 30  Filename, 1) ? 0
1070: 20 3a 20 53 5f 49 53 52 45 47 28 66 69 6c 65 53   : S_ISREG(fileS
1080: 74 61 74 2e 73 74 5f 6d 6f 64 65 29 20 7c 7c 0a  tat.st_mode) ||.
1090: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
10a0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
10b0: 20 20 20 20 20 53 5f 49 53 4c 4e 4b 28 66 69 6c       S_ISLNK(fil
10c0: 65 53 74 61 74 2e 73 74 5f 6d 6f 64 65 29 3b 0a  eStat.st_mode);.
10d0: 7d 0a 0a 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20  }../*.** Return 
10e0: 54 52 55 45 20 69 66 20 74 68 65 20 6e 61 6d 65  TRUE if the name
10f0: 64 20 66 69 6c 65 20 69 73 20 61 6e 20 6f 72 64  d file is an ord
1100: 69 6e 61 72 79 20 66 69 6c 65 2e 20 20 52 65 74  inary file.  Ret
1110: 75 72 6e 20 66 61 6c 73 65 0a 2a 2a 20 66 6f 72  urn false.** for
1120: 20 64 69 72 65 63 74 6f 72 69 65 73 2c 20 64 65   directories, de
1130: 76 69 63 65 73 2c 20 66 69 66 6f 73 2c 20 73 79  vices, fifos, sy
1140: 6d 6c 69 6e 6b 73 2c 20 65 74 63 2e 0a 2a 2f 0a  mlinks, etc..*/.
1150: 69 6e 74 20 66 69 6c 65 5f 69 73 66 69 6c 65 28  int file_isfile(
1160: 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46 69 6c  const char *zFil
1170: 65 6e 61 6d 65 29 7b 0a 20 20 72 65 74 75 72 6e  ename){.  return
1180: 20 67 65 74 53 74 61 74 28 7a 46 69 6c 65 6e 61   getStat(zFilena
1190: 6d 65 2c 20 30 29 20 3f 20 30 20 3a 20 53 5f 49  me, 0) ? 0 : S_I
11a0: 53 52 45 47 28 66 69 6c 65 53 74 61 74 2e 73 74  SREG(fileStat.st
11b0: 5f 6d 6f 64 65 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a  _mode);.}../*.**
11c0: 20 53 61 6d 65 20 61 73 20 66 69 6c 65 5f 69 73   Same as file_is
11d0: 66 69 6c 65 28 29 2c 20 62 75 74 20 74 61 6b 65  file(), but take
11e0: 73 20 69 6e 74 6f 20 61 63 63 6f 75 6e 74 20 73  s into account s
11f0: 79 6d 6c 69 6e 6b 73 2e 0a 2a 2f 0a 69 6e 74 20  ymlinks..*/.int 
1200: 66 69 6c 65 5f 77 64 5f 69 73 66 69 6c 65 28 63  file_wd_isfile(c
1210: 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46 69 6c 65  onst char *zFile
1220: 6e 61 6d 65 29 7b 0a 20 20 72 65 74 75 72 6e 20  name){.  return 
1230: 67 65 74 53 74 61 74 28 7a 46 69 6c 65 6e 61 6d  getStat(zFilenam
1240: 65 2c 20 31 29 20 3f 20 30 20 3a 20 53 5f 49 53  e, 1) ? 0 : S_IS
1250: 52 45 47 28 66 69 6c 65 53 74 61 74 2e 73 74 5f  REG(fileStat.st_
1260: 6d 6f 64 65 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20  mode);.}../*.** 
1270: 43 72 65 61 74 65 20 73 79 6d 6c 69 6e 6b 20 74  Create symlink t
1280: 6f 20 66 69 6c 65 20 6f 6e 20 55 6e 69 78 2c 20  o file on Unix, 
1290: 6f 72 20 70 6c 61 69 6e 2d 74 65 78 74 20 66 69  or plain-text fi
12a0: 6c 65 20 77 69 74 68 0a 2a 2a 20 73 79 6d 6c 69  le with.** symli
12b0: 6e 6b 20 74 61 72 67 65 74 20 69 66 20 22 61 6c  nk target if "al
12c0: 6c 6f 77 2d 73 79 6d 6c 69 6e 6b 73 22 20 69 73  low-symlinks" is
12d0: 20 6f 66 66 20 6f 72 20 77 65 27 72 65 20 6f 6e   off or we're on
12e0: 20 57 69 6e 64 6f 77 73 2e 0a 2a 2a 0a 2a 2a 20   Windows..**.** 
12f0: 41 72 67 75 6d 65 6e 74 73 3a 20 74 61 72 67 65  Arguments: targe
1300: 74 20 66 69 6c 65 20 28 73 79 6d 6c 69 6e 6b 20  t file (symlink 
1310: 77 69 6c 6c 20 70 6f 69 6e 74 20 74 6f 20 69 74  will point to it
1320: 29 2c 20 6c 69 6e 6b 20 66 69 6c 65 0a 2a 2a 2f  ), link file.**/
1330: 0a 76 6f 69 64 20 73 79 6d 6c 69 6e 6b 5f 63 72  .void symlink_cr
1340: 65 61 74 65 28 63 6f 6e 73 74 20 63 68 61 72 20  eate(const char 
1350: 2a 7a 54 61 72 67 65 74 46 69 6c 65 2c 20 63 6f  *zTargetFile, co
1360: 6e 73 74 20 63 68 61 72 20 2a 7a 4c 69 6e 6b 46  nst char *zLinkF
1370: 69 6c 65 29 7b 0a 23 69 66 20 21 64 65 66 69 6e  ile){.#if !defin
1380: 65 64 28 5f 57 49 4e 33 32 29 0a 20 20 69 66 28  ed(_WIN32).  if(
1390: 20 67 2e 61 6c 6c 6f 77 53 79 6d 6c 69 6e 6b 73   g.allowSymlinks
13a0: 20 29 7b 0a 20 20 20 20 69 6e 74 20 69 2c 20 6e   ){.    int i, n
13b0: 4e 61 6d 65 3b 0a 20 20 20 20 63 68 61 72 20 2a  Name;.    char *
13c0: 7a 4e 61 6d 65 2c 20 7a 42 75 66 5b 31 30 30 30  zName, zBuf[1000
13d0: 5d 3b 0a 0a 20 20 20 20 6e 4e 61 6d 65 20 3d 20  ];..    nName = 
13e0: 73 74 72 6c 65 6e 28 7a 4c 69 6e 6b 46 69 6c 65  strlen(zLinkFile
13f0: 29 3b 0a 20 20 20 20 69 66 28 20 6e 4e 61 6d 65  );.    if( nName
1400: 3e 3d 73 69 7a 65 6f 66 28 7a 42 75 66 29 20 29  >=sizeof(zBuf) )
1410: 7b 0a 20 20 20 20 20 20 7a 4e 61 6d 65 20 3d 20  {.      zName = 
1420: 6d 70 72 69 6e 74 66 28 22 25 73 22 2c 20 7a 4c  mprintf("%s", zL
1430: 69 6e 6b 46 69 6c 65 29 3b 0a 20 20 20 20 7d 65  inkFile);.    }e
1440: 6c 73 65 7b 0a 20 20 20 20 20 20 7a 4e 61 6d 65  lse{.      zName
1450: 20 3d 20 7a 42 75 66 3b 0a 20 20 20 20 20 20 6d   = zBuf;.      m
1460: 65 6d 63 70 79 28 7a 4e 61 6d 65 2c 20 7a 4c 69  emcpy(zName, zLi
1470: 6e 6b 46 69 6c 65 2c 20 6e 4e 61 6d 65 2b 31 29  nkFile, nName+1)
1480: 3b 0a 20 20 20 20 7d 0a 20 20 20 20 6e 4e 61 6d  ;.    }.    nNam
1490: 65 20 3d 20 66 69 6c 65 5f 73 69 6d 70 6c 69 66  e = file_simplif
14a0: 79 5f 6e 61 6d 65 28 7a 4e 61 6d 65 2c 20 6e 4e  y_name(zName, nN
14b0: 61 6d 65 2c 20 30 29 3b 0a 20 20 20 20 66 6f 72  ame, 0);.    for
14c0: 28 69 3d 31 3b 20 69 3c 6e 4e 61 6d 65 3b 20 69  (i=1; i<nName; i
14d0: 2b 2b 29 7b 0a 20 20 20 20 20 20 69 66 28 20 7a  ++){.      if( z
14e0: 4e 61 6d 65 5b 69 5d 3d 3d 27 2f 27 20 29 7b 0a  Name[i]=='/' ){.
14f0: 20 20 20 20 20 20 20 20 7a 4e 61 6d 65 5b 69 5d          zName[i]
1500: 20 3d 20 30 3b 0a 20 20 20 20 20 20 20 20 20 20   = 0;.          
1510: 69 66 28 20 66 69 6c 65 5f 6d 6b 64 69 72 28 7a  if( file_mkdir(z
1520: 4e 61 6d 65 2c 20 31 29 20 29 7b 0a 20 20 20 20  Name, 1) ){.    
1530: 20 20 20 20 20 20 20 20 66 6f 73 73 69 6c 5f 66          fossil_f
1540: 61 74 61 6c 5f 72 65 63 75 72 73 69 76 65 28 22  atal_recursive("
1550: 75 6e 61 62 6c 65 20 74 6f 20 63 72 65 61 74 65  unable to create
1560: 20 64 69 72 65 63 74 6f 72 79 20 25 73 22 2c 20   directory %s", 
1570: 7a 4e 61 6d 65 29 3b 0a 20 20 20 20 20 20 20 20  zName);.        
1580: 20 20 20 20 72 65 74 75 72 6e 3b 0a 20 20 20 20      return;.    
1590: 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 20 20        }.        
15a0: 7a 4e 61 6d 65 5b 69 5d 20 3d 20 27 2f 27 3b 0a  zName[i] = '/';.
15b0: 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 20 20        }.    }.  
15c0: 20 20 69 66 28 20 73 79 6d 6c 69 6e 6b 28 7a 54    if( symlink(zT
15d0: 61 72 67 65 74 46 69 6c 65 2c 20 7a 4e 61 6d 65  argetFile, zName
15e0: 29 21 3d 30 20 29 7b 0a 20 20 20 20 20 20 66 6f  )!=0 ){.      fo
15f0: 73 73 69 6c 5f 66 61 74 61 6c 5f 72 65 63 75 72  ssil_fatal_recur
1600: 73 69 76 65 28 22 75 6e 61 62 6c 65 20 74 6f 20  sive("unable to 
1610: 63 72 65 61 74 65 20 73 79 6d 6c 69 6e 6b 20 5c  create symlink \
1620: 22 25 73 5c 22 22 2c 20 7a 4e 61 6d 65 29 3b 0a  "%s\"", zName);.
1630: 20 20 20 20 7d 0a 20 20 20 20 69 66 28 20 7a 4e      }.    if( zN
1640: 61 6d 65 21 3d 7a 42 75 66 20 29 20 66 72 65 65  ame!=zBuf ) free
1650: 28 7a 4e 61 6d 65 29 3b 0a 20 20 7d 65 6c 73 65  (zName);.  }else
1660: 0a 23 65 6e 64 69 66 0a 20 20 7b 0a 20 20 20 20  .#endif.  {.    
1670: 42 6c 6f 62 20 63 6f 6e 74 65 6e 74 3b 0a 20 20  Blob content;.  
1680: 20 20 62 6c 6f 62 5f 73 65 74 28 26 63 6f 6e 74    blob_set(&cont
1690: 65 6e 74 2c 20 7a 54 61 72 67 65 74 46 69 6c 65  ent, zTargetFile
16a0: 29 3b 0a 20 20 20 20 62 6c 6f 62 5f 77 72 69 74  );.    blob_writ
16b0: 65 5f 74 6f 5f 66 69 6c 65 28 26 63 6f 6e 74 65  e_to_file(&conte
16c0: 6e 74 2c 20 7a 4c 69 6e 6b 46 69 6c 65 29 3b 0a  nt, zLinkFile);.
16d0: 20 20 20 20 62 6c 6f 62 5f 72 65 73 65 74 28 26      blob_reset(&
16e0: 63 6f 6e 74 65 6e 74 29 3b 0a 20 20 7d 0a 7d 0a  content);.  }.}.
16f0: 0a 2f 2a 0a 2a 2a 20 43 6f 70 79 20 73 79 6d 62  ./*.** Copy symb
1700: 6f 6c 69 63 20 6c 69 6e 6b 20 66 72 6f 6d 20 7a  olic link from z
1710: 46 72 6f 6d 20 74 6f 20 7a 54 6f 2e 0a 2a 2f 0a  From to zTo..*/.
1720: 76 6f 69 64 20 73 79 6d 6c 69 6e 6b 5f 63 6f 70  void symlink_cop
1730: 79 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46  y(const char *zF
1740: 72 6f 6d 2c 20 63 6f 6e 73 74 20 63 68 61 72 20  rom, const char 
1750: 2a 7a 54 6f 29 7b 0a 20 20 42 6c 6f 62 20 63 6f  *zTo){.  Blob co
1760: 6e 74 65 6e 74 3b 0a 20 20 62 6c 6f 62 5f 72 65  ntent;.  blob_re
1770: 61 64 5f 6c 69 6e 6b 28 26 63 6f 6e 74 65 6e 74  ad_link(&content
1780: 2c 20 7a 46 72 6f 6d 29 3b 0a 20 20 73 79 6d 6c  , zFrom);.  syml
1790: 69 6e 6b 5f 63 72 65 61 74 65 28 62 6c 6f 62 5f  ink_create(blob_
17a0: 73 74 72 28 26 63 6f 6e 74 65 6e 74 29 2c 20 7a  str(&content), z
17b0: 54 6f 29 3b 0a 20 20 62 6c 6f 62 5f 72 65 73 65  To);.  blob_rese
17c0: 74 28 26 63 6f 6e 74 65 6e 74 29 3b 0a 7d 0a 0a  t(&content);.}..
17d0: 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 66 69 6c  /*.** Return fil
17e0: 65 20 70 65 72 6d 69 73 73 69 6f 6e 73 20 28 6e  e permissions (n
17f0: 6f 72 6d 61 6c 2c 20 65 78 65 63 75 74 61 62 6c  ormal, executabl
1800: 65 2c 20 6f 72 20 73 79 6d 6c 69 6e 6b 29 3a 0a  e, or symlink):.
1810: 2a 2a 20 20 20 2d 20 50 45 52 4d 5f 45 58 45 20  **   - PERM_EXE 
1820: 6f 6e 20 55 6e 69 78 20 69 66 20 66 69 6c 65 20  on Unix if file 
1830: 69 73 20 65 78 65 63 75 74 61 62 6c 65 3b 0a 2a  is executable;.*
1840: 2a 20 20 20 2d 20 50 45 52 4d 5f 4c 4e 4b 20 6f  *   - PERM_LNK o
1850: 6e 20 55 6e 69 78 20 69 66 20 66 69 6c 65 20 69  n Unix if file i
1860: 73 20 73 79 6d 6c 69 6e 6b 20 61 6e 64 20 61 6c  s symlink and al
1870: 6c 6f 77 2d 73 79 6d 6c 69 6e 6b 73 20 6f 70 74  low-symlinks opt
1880: 69 6f 6e 20 69 73 20 6f 6e 3b 0a 2a 2a 20 20 20  ion is on;.**   
1890: 2d 20 50 45 52 4d 5f 52 45 47 20 66 6f 72 20 61  - PERM_REG for a
18a0: 6c 6c 20 6f 74 68 65 72 20 63 61 73 65 73 20 28  ll other cases (
18b0: 72 65 67 75 6c 61 72 20 66 69 6c 65 2c 20 64 69  regular file, di
18c0: 72 65 63 74 6f 72 79 2c 20 66 69 66 6f 2c 20 65  rectory, fifo, e
18d0: 74 63 29 2e 0a 2a 2f 0a 69 6e 74 20 66 69 6c 65  tc)..*/.int file
18e0: 5f 77 64 5f 70 65 72 6d 28 63 6f 6e 73 74 20 63  _wd_perm(const c
18f0: 68 61 72 20 2a 7a 46 69 6c 65 6e 61 6d 65 29 7b  har *zFilename){
1900: 0a 23 69 66 20 21 64 65 66 69 6e 65 64 28 5f 57  .#if !defined(_W
1910: 49 4e 33 32 29 0a 20 20 69 66 28 20 21 67 65 74  IN32).  if( !get
1920: 53 74 61 74 28 7a 46 69 6c 65 6e 61 6d 65 2c 20  Stat(zFilename, 
1930: 31 29 20 29 7b 0a 20 20 20 20 20 69 66 28 20 53  1) ){.     if( S
1940: 5f 49 53 52 45 47 28 66 69 6c 65 53 74 61 74 2e  _ISREG(fileStat.
1950: 73 74 5f 6d 6f 64 65 29 20 26 26 20 28 28 53 5f  st_mode) && ((S_
1960: 49 58 55 53 52 29 26 66 69 6c 65 53 74 61 74 2e  IXUSR)&fileStat.
1970: 73 74 5f 6d 6f 64 65 29 21 3d 30 20 29 0a 20 20  st_mode)!=0 ).  
1980: 20 20 20 20 72 65 74 75 72 6e 20 50 45 52 4d 5f      return PERM_
1990: 45 58 45 3b 0a 20 20 20 20 65 6c 73 65 20 69 66  EXE;.    else if
19a0: 28 20 67 2e 61 6c 6c 6f 77 53 79 6d 6c 69 6e 6b  ( g.allowSymlink
19b0: 73 20 26 26 20 53 5f 49 53 4c 4e 4b 28 66 69 6c  s && S_ISLNK(fil
19c0: 65 53 74 61 74 2e 73 74 5f 6d 6f 64 65 29 20 29  eStat.st_mode) )
19d0: 0a 20 20 20 20 20 20 72 65 74 75 72 6e 20 50 45  .      return PE
19e0: 52 4d 5f 4c 4e 4b 3b 0a 20 20 7d 0a 23 65 6e 64  RM_LNK;.  }.#end
19f0: 69 66 0a 20 20 72 65 74 75 72 6e 20 50 45 52 4d  if.  return PERM
1a00: 5f 52 45 47 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 52  _REG;.}../*.** R
1a10: 65 74 75 72 6e 20 54 52 55 45 20 69 66 20 74 68  eturn TRUE if th
1a20: 65 20 6e 61 6d 65 64 20 66 69 6c 65 20 69 73 20  e named file is 
1a30: 61 6e 20 65 78 65 63 75 74 61 62 6c 65 2e 20 20  an executable.  
1a40: 52 65 74 75 72 6e 20 66 61 6c 73 65 0a 2a 2a 20  Return false.** 
1a50: 66 6f 72 20 64 69 72 65 63 74 6f 72 69 65 73 2c  for directories,
1a60: 20 64 65 76 69 63 65 73 2c 20 66 69 66 6f 73 2c   devices, fifos,
1a70: 20 73 79 6d 6c 69 6e 6b 73 2c 20 65 74 63 2e 0a   symlinks, etc..
1a80: 2a 2f 0a 69 6e 74 20 66 69 6c 65 5f 77 64 5f 69  */.int file_wd_i
1a90: 73 65 78 65 28 63 6f 6e 73 74 20 63 68 61 72 20  sexe(const char 
1aa0: 2a 7a 46 69 6c 65 6e 61 6d 65 29 7b 0a 20 20 72  *zFilename){.  r
1ab0: 65 74 75 72 6e 20 66 69 6c 65 5f 77 64 5f 70 65  eturn file_wd_pe
1ac0: 72 6d 28 7a 46 69 6c 65 6e 61 6d 65 29 3d 3d 50  rm(zFilename)==P
1ad0: 45 52 4d 5f 45 58 45 3b 0a 7d 0a 0a 2f 2a 0a 2a  ERM_EXE;.}../*.*
1ae0: 2a 20 52 65 74 75 72 6e 20 54 52 55 45 20 69 66  * Return TRUE if
1af0: 20 74 68 65 20 6e 61 6d 65 64 20 66 69 6c 65 20   the named file 
1b00: 69 73 20 61 20 73 79 6d 6c 69 6e 6b 20 61 6e 64  is a symlink and
1b10: 20 73 79 6d 6c 69 6e 6b 73 20 61 72 65 20 61 6c   symlinks are al
1b20: 6c 6f 77 65 64 2e 0a 2a 2a 20 52 65 74 75 72 6e  lowed..** Return
1b30: 20 66 61 6c 73 65 20 66 6f 72 20 61 6c 6c 20 6f   false for all o
1b40: 74 68 65 72 20 63 61 73 65 73 2e 0a 2a 2a 0a 2a  ther cases..**.*
1b50: 2a 20 4f 6e 20 57 69 6e 64 6f 77 73 2c 20 61 6c  * On Windows, al
1b60: 77 61 79 73 20 72 65 74 75 72 6e 20 46 61 6c 73  ways return Fals
1b70: 65 2e 0a 2a 2f 0a 69 6e 74 20 66 69 6c 65 5f 77  e..*/.int file_w
1b80: 64 5f 69 73 6c 69 6e 6b 28 63 6f 6e 73 74 20 63  d_islink(const c
1b90: 68 61 72 20 2a 7a 46 69 6c 65 6e 61 6d 65 29 7b  har *zFilename){
1ba0: 0a 20 20 72 65 74 75 72 6e 20 66 69 6c 65 5f 77  .  return file_w
1bb0: 64 5f 70 65 72 6d 28 7a 46 69 6c 65 6e 61 6d 65  d_perm(zFilename
1bc0: 29 3d 3d 50 45 52 4d 5f 4c 4e 4b 3b 0a 7d 0a 0a  )==PERM_LNK;.}..
1bd0: 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 31 20 69  /*.** Return 1 i
1be0: 66 20 7a 46 69 6c 65 6e 61 6d 65 20 69 73 20 61  f zFilename is a
1bf0: 20 64 69 72 65 63 74 6f 72 79 2e 20 20 52 65 74   directory.  Ret
1c00: 75 72 6e 20 30 20 69 66 20 7a 46 69 6c 65 6e 61  urn 0 if zFilena
1c10: 6d 65 0a 2a 2a 20 64 6f 65 73 20 6e 6f 74 20 65  me.** does not e
1c20: 78 69 73 74 2e 20 20 52 65 74 75 72 6e 20 32 20  xist.  Return 2 
1c30: 69 66 20 7a 46 69 6c 65 6e 61 6d 65 20 65 78 69  if zFilename exi
1c40: 73 74 73 20 62 75 74 20 69 73 20 73 6f 6d 65 74  sts but is somet
1c50: 68 69 6e 67 0a 2a 2a 20 6f 74 68 65 72 20 74 68  hing.** other th
1c60: 61 6e 20 61 20 64 69 72 65 63 74 6f 72 79 2e 0a  an a directory..
1c70: 2a 2f 0a 69 6e 74 20 66 69 6c 65 5f 69 73 64 69  */.int file_isdi
1c80: 72 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46  r(const char *zF
1c90: 69 6c 65 6e 61 6d 65 29 7b 0a 20 20 69 6e 74 20  ilename){.  int 
1ca0: 72 63 3b 0a 0a 20 20 69 66 28 20 7a 46 69 6c 65  rc;..  if( zFile
1cb0: 6e 61 6d 65 20 29 7b 0a 20 20 20 20 63 68 61 72  name ){.    char
1cc0: 20 2a 7a 46 4e 20 3d 20 6d 70 72 69 6e 74 66 28   *zFN = mprintf(
1cd0: 22 25 73 22 2c 20 7a 46 69 6c 65 6e 61 6d 65 29  "%s", zFilename)
1ce0: 3b 0a 20 20 20 20 66 69 6c 65 5f 73 69 6d 70 6c  ;.    file_simpl
1cf0: 69 66 79 5f 6e 61 6d 65 28 7a 46 4e 2c 20 2d 31  ify_name(zFN, -1
1d00: 2c 20 30 29 3b 0a 20 20 20 20 72 63 20 3d 20 67  , 0);.    rc = g
1d10: 65 74 53 74 61 74 28 7a 46 4e 2c 20 30 29 3b 0a  etStat(zFN, 0);.
1d20: 20 20 20 20 66 72 65 65 28 7a 46 4e 29 3b 0a 20      free(zFN);. 
1d30: 20 7d 65 6c 73 65 7b 0a 20 20 20 20 72 63 20 3d   }else{.    rc =
1d40: 20 67 65 74 53 74 61 74 28 30 2c 20 30 29 3b 0a   getStat(0, 0);.
1d50: 20 20 7d 0a 20 20 72 65 74 75 72 6e 20 72 63 20    }.  return rc 
1d60: 3f 20 30 20 3a 20 28 53 5f 49 53 44 49 52 28 66  ? 0 : (S_ISDIR(f
1d70: 69 6c 65 53 74 61 74 2e 73 74 5f 6d 6f 64 65 29  ileStat.st_mode)
1d80: 20 3f 20 31 20 3a 20 32 29 3b 0a 7d 0a 0a 2f 2a   ? 1 : 2);.}../*
1d90: 0a 2a 2a 20 53 61 6d 65 20 61 73 20 66 69 6c 65  .** Same as file
1da0: 5f 69 73 64 69 72 28 29 2c 20 62 75 74 20 74 61  _isdir(), but ta
1db0: 6b 65 73 20 69 6e 74 6f 20 61 63 63 6f 75 6e 74  kes into account
1dc0: 20 73 79 6d 6c 69 6e 6b 73 2e 0a 2a 2f 0a 69 6e   symlinks..*/.in
1dd0: 74 20 66 69 6c 65 5f 77 64 5f 69 73 64 69 72 28  t file_wd_isdir(
1de0: 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46 69 6c  const char *zFil
1df0: 65 6e 61 6d 65 29 7b 0a 20 20 69 6e 74 20 72 63  ename){.  int rc
1e00: 3b 0a 0a 20 20 69 66 28 20 7a 46 69 6c 65 6e 61  ;..  if( zFilena
1e10: 6d 65 20 29 7b 0a 20 20 20 20 63 68 61 72 20 2a  me ){.    char *
1e20: 7a 46 4e 20 3d 20 6d 70 72 69 6e 74 66 28 22 25  zFN = mprintf("%
1e30: 73 22 2c 20 7a 46 69 6c 65 6e 61 6d 65 29 3b 0a  s", zFilename);.
1e40: 20 20 20 20 66 69 6c 65 5f 73 69 6d 70 6c 69 66      file_simplif
1e50: 79 5f 6e 61 6d 65 28 7a 46 4e 2c 20 2d 31 2c 20  y_name(zFN, -1, 
1e60: 30 29 3b 0a 20 20 20 20 72 63 20 3d 20 67 65 74  0);.    rc = get
1e70: 53 74 61 74 28 7a 46 4e 2c 20 31 29 3b 0a 20 20  Stat(zFN, 1);.  
1e80: 20 20 66 72 65 65 28 7a 46 4e 29 3b 0a 20 20 7d    free(zFN);.  }
1e90: 65 6c 73 65 7b 0a 20 20 20 20 72 63 20 3d 20 67  else{.    rc = g
1ea0: 65 74 53 74 61 74 28 30 2c 20 31 29 3b 0a 20 20  etStat(0, 1);.  
1eb0: 7d 0a 20 20 72 65 74 75 72 6e 20 72 63 20 3f 20  }.  return rc ? 
1ec0: 30 20 3a 20 28 53 5f 49 53 44 49 52 28 66 69 6c  0 : (S_ISDIR(fil
1ed0: 65 53 74 61 74 2e 73 74 5f 6d 6f 64 65 29 20 3f  eStat.st_mode) ?
1ee0: 20 31 20 3a 20 32 29 3b 0a 7d 0a 0a 0a 2f 2a 0a   1 : 2);.}.../*.
1ef0: 2a 2a 20 57 72 61 70 70 65 72 20 61 72 6f 75 6e  ** Wrapper aroun
1f00: 64 20 74 68 65 20 61 63 63 65 73 73 28 29 20 73  d the access() s
1f10: 79 73 74 65 6d 20 63 61 6c 6c 2e 0a 2a 2f 0a 69  ystem call..*/.i
1f20: 6e 74 20 66 69 6c 65 5f 61 63 63 65 73 73 28 63  nt file_access(c
1f30: 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46 69 6c 65  onst char *zFile
1f40: 6e 61 6d 65 2c 20 69 6e 74 20 66 6c 61 67 73 29  name, int flags)
1f50: 7b 0a 20 20 69 6e 74 20 72 63 3b 0a 20 20 76 6f  {.  int rc;.  vo
1f60: 69 64 20 2a 7a 4d 62 63 73 20 3d 20 66 6f 73 73  id *zMbcs = foss
1f70: 69 6c 5f 75 74 66 38 5f 74 6f 5f 70 61 74 68 28  il_utf8_to_path(
1f80: 7a 46 69 6c 65 6e 61 6d 65 2c 20 30 29 3b 0a 23  zFilename, 0);.#
1f90: 69 66 64 65 66 20 5f 57 49 4e 33 32 0a 20 20 72  ifdef _WIN32.  r
1fa0: 63 20 3d 20 77 69 6e 33 32 5f 61 63 63 65 73 73  c = win32_access
1fb0: 28 7a 4d 62 63 73 2c 20 66 6c 61 67 73 29 3b 0a  (zMbcs, flags);.
1fc0: 23 65 6c 73 65 0a 20 20 72 63 20 3d 20 61 63 63  #else.  rc = acc
1fd0: 65 73 73 28 7a 4d 62 63 73 2c 20 66 6c 61 67 73  ess(zMbcs, flags
1fe0: 29 3b 0a 23 65 6e 64 69 66 0a 20 20 66 6f 73 73  );.#endif.  foss
1ff0: 69 6c 5f 70 61 74 68 5f 66 72 65 65 28 7a 4d 62  il_path_free(zMb
2000: 63 73 29 3b 0a 20 20 72 65 74 75 72 6e 20 72 63  cs);.  return rc
2010: 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 57 72 61 70 70  ;.}../*.** Wrapp
2020: 65 72 20 61 72 6f 75 6e 64 20 74 68 65 20 63 68  er around the ch
2030: 64 69 72 28 29 20 73 79 73 74 65 6d 20 63 61 6c  dir() system cal
2040: 6c 2e 0a 2a 2a 20 49 66 20 62 43 68 72 6f 6f 74  l..** If bChroot
2050: 3d 31 2c 20 64 6f 20 61 20 63 68 72 6f 6f 74 20  =1, do a chroot 
2060: 74 6f 20 74 68 69 73 20 64 69 72 20 61 73 20 77  to this dir as w
2070: 65 6c 6c 0a 2a 2a 20 28 55 4e 49 58 20 6f 6e 6c  ell.** (UNIX onl
2080: 79 29 0a 2a 2f 0a 69 6e 74 20 66 69 6c 65 5f 63  y).*/.int file_c
2090: 68 64 69 72 28 63 6f 6e 73 74 20 63 68 61 72 20  hdir(const char 
20a0: 2a 7a 43 68 44 69 72 2c 20 69 6e 74 20 62 43 68  *zChDir, int bCh
20b0: 72 6f 6f 74 29 7b 0a 20 20 69 6e 74 20 72 63 3b  root){.  int rc;
20c0: 0a 20 20 76 6f 69 64 20 2a 7a 50 61 74 68 20 3d  .  void *zPath =
20d0: 20 66 6f 73 73 69 6c 5f 75 74 66 38 5f 74 6f 5f   fossil_utf8_to_
20e0: 70 61 74 68 28 7a 43 68 44 69 72 2c 20 31 29 3b  path(zChDir, 1);
20f0: 0a 23 69 66 64 65 66 20 5f 57 49 4e 33 32 0a 20  .#ifdef _WIN32. 
2100: 20 72 63 20 3d 20 77 69 6e 33 32 5f 63 68 64 69   rc = win32_chdi
2110: 72 28 7a 50 61 74 68 2c 20 62 43 68 72 6f 6f 74  r(zPath, bChroot
2120: 29 3b 0a 23 65 6c 73 65 0a 20 20 72 63 20 3d 20  );.#else.  rc = 
2130: 63 68 64 69 72 28 7a 50 61 74 68 29 3b 0a 20 20  chdir(zPath);.  
2140: 69 66 28 20 21 72 63 20 26 26 20 62 43 68 72 6f  if( !rc && bChro
2150: 6f 74 20 29 7b 0a 20 20 20 20 72 63 20 3d 20 63  ot ){.    rc = c
2160: 68 72 6f 6f 74 28 7a 50 61 74 68 29 3b 0a 20 20  hroot(zPath);.  
2170: 20 20 69 66 28 20 21 72 63 20 29 20 72 63 20 3d    if( !rc ) rc =
2180: 20 63 68 64 69 72 28 22 2f 22 29 3b 0a 20 20 7d   chdir("/");.  }
2190: 0a 23 65 6e 64 69 66 0a 20 20 66 6f 73 73 69 6c  .#endif.  fossil
21a0: 5f 70 61 74 68 5f 66 72 65 65 28 7a 50 61 74 68  _path_free(zPath
21b0: 29 3b 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a  );.  return rc;.
21c0: 7d 0a 0a 2f 2a 0a 2a 2a 20 46 69 6e 64 20 61 6e  }../*.** Find an
21d0: 20 75 6e 75 73 65 64 20 66 69 6c 65 6e 61 6d 65   unused filename
21e0: 20 73 69 6d 69 6c 61 72 20 74 6f 20 7a 42 61 73   similar to zBas
21f0: 65 20 77 69 74 68 20 7a 53 75 66 66 69 78 20 61  e with zSuffix a
2200: 70 70 65 6e 64 65 64 2e 0a 2a 2a 0a 2a 2a 20 4d  ppended..**.** M
2210: 61 6b 65 20 74 68 65 20 6e 61 6d 65 20 72 65 6c  ake the name rel
2220: 61 74 69 76 65 20 74 6f 20 74 68 65 20 77 6f 72  ative to the wor
2230: 6b 69 6e 67 20 64 69 72 65 63 74 6f 72 79 20 69  king directory i
2240: 66 20 72 65 6c 46 6c 61 67 20 69 73 20 74 72 75  f relFlag is tru
2250: 65 2e 0a 2a 2a 0a 2a 2a 20 53 70 61 63 65 20 74  e..**.** Space t
2260: 6f 20 68 6f 6c 64 20 74 68 65 20 6e 65 77 20 66  o hold the new f
2270: 69 6c 65 6e 61 6d 65 20 69 73 20 6f 62 74 61 69  ilename is obtai
2280: 6e 65 64 20 66 6f 72 6d 20 6d 70 72 69 6e 74 66  ned form mprintf
2290: 28 29 20 61 6e 64 20 73 68 6f 75 6c 64 0a 2a 2a  () and should.**
22a0: 20 62 65 20 66 72 65 65 64 20 62 79 20 74 68 65   be freed by the
22b0: 20 63 61 6c 6c 65 72 2e 0a 2a 2f 0a 63 68 61 72   caller..*/.char
22c0: 20 2a 66 69 6c 65 5f 6e 65 77 6e 61 6d 65 28 63   *file_newname(c
22d0: 6f 6e 73 74 20 63 68 61 72 20 2a 7a 42 61 73 65  onst char *zBase
22e0: 2c 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 53  , const char *zS
22f0: 75 66 66 69 78 2c 20 69 6e 74 20 72 65 6c 46 6c  uffix, int relFl
2300: 61 67 29 7b 0a 20 20 63 68 61 72 20 2a 7a 20 3d  ag){.  char *z =
2310: 20 30 3b 0a 20 20 69 6e 74 20 63 6e 74 20 3d 20   0;.  int cnt = 
2320: 30 3b 0a 20 20 7a 20 3d 20 6d 70 72 69 6e 74 66  0;.  z = mprintf
2330: 28 22 25 73 2d 25 73 22 2c 20 7a 42 61 73 65 2c  ("%s-%s", zBase,
2340: 20 7a 53 75 66 66 69 78 29 3b 0a 20 20 77 68 69   zSuffix);.  whi
2350: 6c 65 28 20 66 69 6c 65 5f 73 69 7a 65 28 7a 29  le( file_size(z)
2360: 3e 3d 30 20 29 7b 0a 20 20 20 20 66 6f 73 73 69  >=0 ){.    fossi
2370: 6c 5f 66 72 65 65 28 7a 29 3b 0a 20 20 20 20 7a  l_free(z);.    z
2380: 20 3d 20 6d 70 72 69 6e 74 66 28 22 25 73 2d 25   = mprintf("%s-%
2390: 73 2d 25 64 22 2c 20 7a 42 61 73 65 2c 20 7a 53  s-%d", zBase, zS
23a0: 75 66 66 69 78 2c 20 63 6e 74 2b 2b 29 3b 0a 20  uffix, cnt++);. 
23b0: 20 7d 0a 20 20 69 66 28 20 72 65 6c 46 6c 61 67   }.  if( relFlag
23c0: 20 29 7b 0a 20 20 20 20 42 6c 6f 62 20 78 3b 0a   ){.    Blob x;.
23d0: 20 20 20 20 66 69 6c 65 5f 72 65 6c 61 74 69 76      file_relativ
23e0: 65 5f 6e 61 6d 65 28 7a 2c 20 26 78 2c 20 30 29  e_name(z, &x, 0)
23f0: 3b 0a 20 20 20 20 66 6f 73 73 69 6c 5f 66 72 65  ;.    fossil_fre
2400: 65 28 7a 29 3b 0a 20 20 20 20 7a 20 3d 20 62 6c  e(z);.    z = bl
2410: 6f 62 5f 73 74 72 28 26 78 29 3b 0a 20 20 7d 0a  ob_str(&x);.  }.
2420: 20 20 72 65 74 75 72 6e 20 7a 3b 0a 7d 0a 0a 2f    return z;.}../
2430: 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 74 68 65 20  *.** Return the 
2440: 74 61 69 6c 20 6f 66 20 61 20 66 69 6c 65 20 70  tail of a file p
2450: 61 74 68 6e 61 6d 65 2e 20 20 54 68 65 20 74 61  athname.  The ta
2460: 69 6c 20 69 73 20 74 68 65 20 6c 61 73 74 20 63  il is the last c
2470: 6f 6d 70 6f 6e 65 6e 74 0a 2a 2a 20 6f 66 20 74  omponent.** of t
2480: 68 65 20 70 61 74 68 2e 20 20 46 6f 72 20 65 78  he path.  For ex
2490: 61 6d 70 6c 65 2c 20 74 68 65 20 74 61 69 6c 20  ample, the tail 
24a0: 6f 66 20 22 2f 61 2f 62 2f 63 2e 64 22 20 69 73  of "/a/b/c.d" is
24b0: 20 22 63 2e 64 22 2e 0a 2a 2f 0a 63 6f 6e 73 74   "c.d"..*/.const
24c0: 20 63 68 61 72 20 2a 66 69 6c 65 5f 74 61 69 6c   char *file_tail
24d0: 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 29 7b  (const char *z){
24e0: 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  .  const char *z
24f0: 54 61 69 6c 20 3d 20 7a 3b 0a 20 20 69 66 28 20  Tail = z;.  if( 
2500: 21 7a 54 61 69 6c 20 29 20 72 65 74 75 72 6e 20  !zTail ) return 
2510: 30 3b 0a 20 20 77 68 69 6c 65 28 20 7a 5b 30 5d  0;.  while( z[0]
2520: 20 29 7b 0a 20 20 20 20 69 66 28 20 66 6f 73 73   ){.    if( foss
2530: 69 6c 5f 69 73 64 69 72 73 65 70 28 7a 5b 30 5d  il_isdirsep(z[0]
2540: 29 20 29 20 7a 54 61 69 6c 20 3d 20 26 7a 5b 31  ) ) zTail = &z[1
2550: 5d 3b 0a 20 20 20 20 7a 2b 2b 3b 0a 20 20 7d 0a  ];.    z++;.  }.
2560: 20 20 72 65 74 75 72 6e 20 7a 54 61 69 6c 3b 0a    return zTail;.
2570: 7d 0a 0a 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20  }../*.** Return 
2580: 74 68 65 20 64 69 72 65 63 74 6f 72 79 20 6f 66  the directory of
2590: 20 61 20 66 69 6c 65 20 70 61 74 68 20 6e 61 6d   a file path nam
25a0: 65 2e 20 20 54 68 65 20 64 69 72 65 63 74 6f 72  e.  The director
25b0: 79 20 69 73 20 61 6c 6c 20 63 6f 6d 70 6f 6e 65  y is all compone
25c0: 6e 74 73 0a 2a 2a 20 65 78 63 65 70 74 20 74 68  nts.** except th
25d0: 65 20 6c 61 73 74 20 6f 6e 65 2e 20 20 46 6f 72  e last one.  For
25e0: 20 65 78 61 6d 70 6c 65 2c 20 74 68 65 20 64 69   example, the di
25f0: 72 65 63 74 6f 72 79 20 6f 66 20 22 2f 61 2f 62  rectory of "/a/b
2600: 2f 63 2e 64 22 20 69 73 20 22 2f 61 2f 62 22 2e  /c.d" is "/a/b".
2610: 0a 2a 2a 20 49 66 20 74 68 65 72 65 20 69 73 20  .** If there is 
2620: 6e 6f 20 64 69 72 65 63 74 6f 72 79 2c 20 4e 55  no directory, NU
2630: 4c 4c 20 69 73 20 72 65 74 75 72 6e 65 64 3b 20  LL is returned; 
2640: 6f 74 68 65 72 77 69 73 65 2c 20 74 68 65 20 72  otherwise, the r
2650: 65 74 75 72 6e 65 64 20 6d 65 6d 6f 72 79 0a 2a  eturned memory.*
2660: 2a 20 73 68 6f 75 6c 64 20 62 65 20 66 72 65 65  * should be free
2670: 64 20 76 69 61 20 66 6f 73 73 69 6c 5f 66 72 65  d via fossil_fre
2680: 65 28 29 2e 0a 2a 2f 0a 63 68 61 72 20 2a 66 69  e()..*/.char *fi
2690: 6c 65 5f 64 69 72 6e 61 6d 65 28 63 6f 6e 73 74  le_dirname(const
26a0: 20 63 68 61 72 20 2a 7a 29 7b 0a 20 20 63 6f 6e   char *z){.  con
26b0: 73 74 20 63 68 61 72 20 2a 7a 54 61 69 6c 20 3d  st char *zTail =
26c0: 20 66 69 6c 65 5f 74 61 69 6c 28 7a 29 3b 0a 20   file_tail(z);. 
26d0: 20 69 66 28 20 7a 54 61 69 6c 20 26 26 20 7a 54   if( zTail && zT
26e0: 61 69 6c 21 3d 7a 20 29 7b 0a 20 20 20 20 72 65  ail!=z ){.    re
26f0: 74 75 72 6e 20 6d 70 72 69 6e 74 66 28 22 25 2e  turn mprintf("%.
2700: 2a 73 22 2c 20 28 69 6e 74 29 28 7a 54 61 69 6c  *s", (int)(zTail
2710: 2d 7a 2d 31 29 2c 20 7a 29 3b 0a 20 20 7d 65 6c  -z-1), z);.  }el
2720: 73 65 7b 0a 20 20 20 20 72 65 74 75 72 6e 20 30  se{.    return 0
2730: 3b 0a 20 20 7d 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 52  ;.  }.}../*.** R
2740: 65 6e 61 6d 65 20 61 20 66 69 6c 65 20 6f 72 20  ename a file or 
2750: 64 69 72 65 63 74 6f 72 79 2e 0a 2a 2a 20 52 65  directory..** Re
2760: 74 75 72 6e 73 20 7a 65 72 6f 20 75 70 6f 6e 20  turns zero upon 
2770: 73 75 63 63 65 73 73 2e 0a 2a 2f 0a 69 6e 74 20  success..*/.int 
2780: 66 69 6c 65 5f 72 65 6e 61 6d 65 28 0a 20 20 63  file_rename(.  c
2790: 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46 72 6f 6d  onst char *zFrom
27a0: 2c 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a  ,.  const char *
27b0: 7a 54 6f 2c 0a 20 20 69 6e 74 20 69 73 46 72 6f  zTo,.  int isFro
27c0: 6d 44 69 72 2c 0a 20 20 69 6e 74 20 69 73 54 6f  mDir,.  int isTo
27d0: 44 69 72 0a 29 7b 0a 20 20 69 6e 74 20 72 63 3b  Dir.){.  int rc;
27e0: 0a 23 69 66 20 64 65 66 69 6e 65 64 28 5f 57 49  .#if defined(_WI
27f0: 4e 33 32 29 0a 20 20 77 63 68 61 72 5f 74 20 2a  N32).  wchar_t *
2800: 7a 4d 62 63 73 46 72 6f 6d 20 3d 20 66 6f 73 73  zMbcsFrom = foss
2810: 69 6c 5f 75 74 66 38 5f 74 6f 5f 70 61 74 68 28  il_utf8_to_path(
2820: 7a 46 72 6f 6d 2c 20 69 73 46 72 6f 6d 44 69 72  zFrom, isFromDir
2830: 29 3b 0a 20 20 77 63 68 61 72 5f 74 20 2a 7a 4d  );.  wchar_t *zM
2840: 62 63 73 54 6f 20 3d 20 66 6f 73 73 69 6c 5f 75  bcsTo = fossil_u
2850: 74 66 38 5f 74 6f 5f 70 61 74 68 28 7a 54 6f 2c  tf8_to_path(zTo,
2860: 20 69 73 54 6f 44 69 72 29 3b 0a 20 20 72 63 20   isToDir);.  rc 
2870: 3d 20 5f 77 72 65 6e 61 6d 65 28 7a 4d 62 63 73  = _wrename(zMbcs
2880: 46 72 6f 6d 2c 20 7a 4d 62 63 73 54 6f 29 3b 0a  From, zMbcsTo);.
2890: 23 65 6c 73 65 0a 20 20 63 68 61 72 20 2a 7a 4d  #else.  char *zM
28a0: 62 63 73 46 72 6f 6d 20 3d 20 66 6f 73 73 69 6c  bcsFrom = fossil
28b0: 5f 75 74 66 38 5f 74 6f 5f 70 61 74 68 28 7a 46  _utf8_to_path(zF
28c0: 72 6f 6d 2c 20 69 73 46 72 6f 6d 44 69 72 29 3b  rom, isFromDir);
28d0: 0a 20 20 63 68 61 72 20 2a 7a 4d 62 63 73 54 6f  .  char *zMbcsTo
28e0: 20 3d 20 66 6f 73 73 69 6c 5f 75 74 66 38 5f 74   = fossil_utf8_t
28f0: 6f 5f 70 61 74 68 28 7a 54 6f 2c 20 69 73 54 6f  o_path(zTo, isTo
2900: 44 69 72 29 3b 0a 20 20 72 63 20 3d 20 72 65 6e  Dir);.  rc = ren
2910: 61 6d 65 28 7a 4d 62 63 73 46 72 6f 6d 2c 20 7a  ame(zMbcsFrom, z
2920: 4d 62 63 73 54 6f 29 3b 0a 23 65 6e 64 69 66 0a  MbcsTo);.#endif.
2930: 20 20 66 6f 73 73 69 6c 5f 70 61 74 68 5f 66 72    fossil_path_fr
2940: 65 65 28 7a 4d 62 63 73 54 6f 29 3b 0a 20 20 66  ee(zMbcsTo);.  f
2950: 6f 73 73 69 6c 5f 70 61 74 68 5f 66 72 65 65 28  ossil_path_free(
2960: 7a 4d 62 63 73 46 72 6f 6d 29 3b 0a 20 20 72 65  zMbcsFrom);.  re
2970: 74 75 72 6e 20 72 63 3b 0a 7d 0a 0a 2f 2a 0a 2a  turn rc;.}../*.*
2980: 2a 20 43 6f 70 79 20 74 68 65 20 63 6f 6e 74 65  * Copy the conte
2990: 6e 74 20 6f 66 20 61 20 66 69 6c 65 20 66 72 6f  nt of a file fro
29a0: 6d 20 6f 6e 65 20 70 6c 61 63 65 20 74 6f 20 61  m one place to a
29b0: 6e 6f 74 68 65 72 2e 0a 2a 2f 0a 76 6f 69 64 20  nother..*/.void 
29c0: 66 69 6c 65 5f 63 6f 70 79 28 63 6f 6e 73 74 20  file_copy(const 
29d0: 63 68 61 72 20 2a 7a 46 72 6f 6d 2c 20 63 6f 6e  char *zFrom, con
29e0: 73 74 20 63 68 61 72 20 2a 7a 54 6f 29 7b 0a 20  st char *zTo){. 
29f0: 20 46 49 4c 45 20 2a 69 6e 2c 20 2a 6f 75 74 3b   FILE *in, *out;
2a00: 0a 20 20 69 6e 74 20 67 6f 74 3b 0a 20 20 63 68  .  int got;.  ch
2a10: 61 72 20 7a 42 75 66 5b 38 31 39 32 5d 3b 0a 20  ar zBuf[8192];. 
2a20: 20 69 6e 20 3d 20 66 6f 73 73 69 6c 5f 66 6f 70   in = fossil_fop
2a30: 65 6e 28 7a 46 72 6f 6d 2c 20 22 72 62 22 29 3b  en(zFrom, "rb");
2a40: 0a 20 20 69 66 28 20 69 6e 3d 3d 30 20 29 20 66  .  if( in==0 ) f
2a50: 6f 73 73 69 6c 5f 66 61 74 61 6c 28 22 63 61 6e  ossil_fatal("can
2a60: 6e 6f 74 20 6f 70 65 6e 20 5c 22 25 73 5c 22 20  not open \"%s\" 
2a70: 66 6f 72 20 72 65 61 64 69 6e 67 22 2c 20 7a 46  for reading", zF
2a80: 72 6f 6d 29 3b 0a 20 20 66 69 6c 65 5f 6d 6b 66  rom);.  file_mkf
2a90: 6f 6c 64 65 72 28 7a 54 6f 2c 20 30 2c 20 30 29  older(zTo, 0, 0)
2aa0: 3b 0a 20 20 6f 75 74 20 3d 20 66 6f 73 73 69 6c  ;.  out = fossil
2ab0: 5f 66 6f 70 65 6e 28 7a 54 6f 2c 20 22 77 62 22  _fopen(zTo, "wb"
2ac0: 29 3b 0a 20 20 69 66 28 20 6f 75 74 3d 3d 30 20  );.  if( out==0 
2ad0: 29 20 66 6f 73 73 69 6c 5f 66 61 74 61 6c 28 22  ) fossil_fatal("
2ae0: 63 61 6e 6e 6f 74 20 6f 70 65 6e 20 5c 22 25 73  cannot open \"%s
2af0: 5c 22 20 66 6f 72 20 77 72 69 74 69 6e 67 22 2c  \" for writing",
2b00: 20 7a 54 6f 29 3b 0a 20 20 77 68 69 6c 65 28 20   zTo);.  while( 
2b10: 28 67 6f 74 3d 66 72 65 61 64 28 7a 42 75 66 2c  (got=fread(zBuf,
2b20: 20 31 2c 20 73 69 7a 65 6f 66 28 7a 42 75 66 29   1, sizeof(zBuf)
2b30: 2c 20 69 6e 29 29 3e 30 20 29 7b 0a 20 20 20 20  , in))>0 ){.    
2b40: 66 77 72 69 74 65 28 7a 42 75 66 2c 20 31 2c 20  fwrite(zBuf, 1, 
2b50: 67 6f 74 2c 20 6f 75 74 29 3b 0a 20 20 7d 0a 20  got, out);.  }. 
2b60: 20 66 63 6c 6f 73 65 28 69 6e 29 3b 0a 20 20 66   fclose(in);.  f
2b70: 63 6c 6f 73 65 28 6f 75 74 29 3b 0a 7d 0a 0a 2f  close(out);.}../
2b80: 2a 0a 2a 2a 20 43 4f 4d 4d 41 4e 44 3a 20 74 65  *.** COMMAND: te
2b90: 73 74 2d 66 69 6c 65 2d 63 6f 70 79 0a 2a 2a 0a  st-file-copy.**.
2ba0: 2a 2a 20 55 73 61 67 65 3a 20 25 66 6f 73 73 69  ** Usage: %fossi
2bb0: 6c 20 74 65 73 74 2d 66 69 6c 65 2d 63 6f 70 79  l test-file-copy
2bc0: 20 53 4f 55 52 43 45 20 44 45 53 54 49 4e 41 54   SOURCE DESTINAT
2bd0: 49 4f 4e 0a 2a 2a 0a 2a 2a 20 4d 61 6b 65 20 61  ION.**.** Make a
2be0: 20 63 6f 70 79 20 6f 66 20 74 68 65 20 66 69 6c   copy of the fil
2bf0: 65 20 61 74 20 53 4f 55 52 43 45 20 69 6e 74 6f  e at SOURCE into
2c00: 20 61 20 6e 65 77 20 6e 61 6d 65 20 44 45 53 54   a new name DEST
2c10: 49 4e 41 54 49 4f 4e 2e 20 20 41 6e 79 0a 2a 2a  INATION.  Any.**
2c20: 20 64 69 72 65 63 74 6f 72 69 65 73 20 69 6e 20   directories in 
2c30: 74 68 65 20 70 61 74 68 20 6c 65 61 64 69 6e 67  the path leading
2c40: 20 75 70 20 74 6f 20 44 45 53 54 49 4e 41 54 49   up to DESTINATI
2c50: 4f 4e 20 74 68 61 74 20 64 6f 20 6e 6f 74 20 61  ON that do not a
2c60: 6c 72 65 61 64 79 0a 2a 2a 20 65 78 69 73 74 20  lready.** exist 
2c70: 61 72 65 20 63 72 65 61 74 65 64 20 61 75 74 6f  are created auto
2c80: 6d 61 74 69 63 61 6c 6c 79 2e 0a 2a 2f 0a 76 6f  matically..*/.vo
2c90: 69 64 20 74 65 73 74 5f 66 69 6c 65 5f 63 6f 70  id test_file_cop
2ca0: 79 28 76 6f 69 64 29 7b 0a 20 20 69 66 28 20 67  y(void){.  if( g
2cb0: 2e 61 72 67 63 21 3d 34 20 29 7b 0a 20 20 20 20  .argc!=4 ){.    
2cc0: 66 6f 73 73 69 6c 5f 66 61 74 61 6c 28 22 55 73  fossil_fatal("Us
2cd0: 61 67 65 3a 20 25 73 20 74 65 73 74 2d 66 69 6c  age: %s test-fil
2ce0: 65 2d 63 6f 70 79 20 53 4f 55 52 43 45 20 44 45  e-copy SOURCE DE
2cf0: 53 54 49 4e 41 54 49 4f 4e 22 2c 20 67 2e 61 72  STINATION", g.ar
2d00: 67 76 5b 30 5d 29 3b 0a 20 20 7d 0a 20 20 66 69  gv[0]);.  }.  fi
2d10: 6c 65 5f 63 6f 70 79 28 67 2e 61 72 67 76 5b 32  le_copy(g.argv[2
2d20: 5d 2c 20 67 2e 61 72 67 76 5b 33 5d 29 3b 0a 7d  ], g.argv[3]);.}
2d30: 0a 0a 2f 2a 0a 2a 2a 20 53 65 74 20 6f 72 20 63  ../*.** Set or c
2d40: 6c 65 61 72 20 74 68 65 20 65 78 65 63 75 74 65  lear the execute
2d50: 20 62 69 74 20 6f 6e 20 61 20 66 69 6c 65 2e 20   bit on a file. 
2d60: 20 52 65 74 75 72 6e 20 74 72 75 65 20 69 66 20   Return true if 
2d70: 61 20 63 68 61 6e 67 65 0a 2a 2a 20 6f 63 63 75  a change.** occu
2d80: 72 72 65 64 20 61 6e 64 20 66 61 6c 73 65 20 69  rred and false i
2d90: 66 20 74 68 69 73 20 72 6f 75 74 69 6e 65 20 69  f this routine i
2da0: 73 20 61 20 6e 6f 2d 6f 70 2e 0a 2a 2f 0a 69 6e  s a no-op..*/.in
2db0: 74 20 66 69 6c 65 5f 77 64 5f 73 65 74 65 78 65  t file_wd_setexe
2dc0: 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46 69  (const char *zFi
2dd0: 6c 65 6e 61 6d 65 2c 20 69 6e 74 20 6f 6e 6f 66  lename, int onof
2de0: 66 29 7b 0a 20 20 69 6e 74 20 72 63 20 3d 20 30  f){.  int rc = 0
2df0: 3b 0a 23 69 66 20 21 64 65 66 69 6e 65 64 28 5f  ;.#if !defined(_
2e00: 57 49 4e 33 32 29 0a 20 20 73 74 72 75 63 74 20  WIN32).  struct 
2e10: 73 74 61 74 20 62 75 66 3b 0a 20 20 69 66 28 20  stat buf;.  if( 
2e20: 66 6f 73 73 69 6c 5f 73 74 61 74 28 7a 46 69 6c  fossil_stat(zFil
2e30: 65 6e 61 6d 65 2c 20 26 62 75 66 2c 20 31 29 21  ename, &buf, 1)!
2e40: 3d 30 20 7c 7c 20 53 5f 49 53 4c 4e 4b 28 62 75  =0 || S_ISLNK(bu
2e50: 66 2e 73 74 5f 6d 6f 64 65 29 20 29 20 72 65 74  f.st_mode) ) ret
2e60: 75 72 6e 20 30 3b 0a 20 20 69 66 28 20 6f 6e 6f  urn 0;.  if( ono
2e70: 66 66 20 29 7b 0a 20 20 20 20 69 6e 74 20 74 61  ff ){.    int ta
2e80: 72 67 65 74 4d 6f 64 65 20 3d 20 28 62 75 66 2e  rgetMode = (buf.
2e90: 73 74 5f 6d 6f 64 65 20 26 20 30 34 34 34 29 3e  st_mode & 0444)>
2ea0: 3e 32 3b 0a 20 20 20 20 69 66 28 20 28 62 75 66  >2;.    if( (buf
2eb0: 2e 73 74 5f 6d 6f 64 65 20 26 20 30 31 30 30 29  .st_mode & 0100)
2ec0: 20 3d 3d 20 30 20 29 7b 0a 20 20 20 20 20 20 63   == 0 ){.      c
2ed0: 68 6d 6f 64 28 7a 46 69 6c 65 6e 61 6d 65 2c 20  hmod(zFilename, 
2ee0: 62 75 66 2e 73 74 5f 6d 6f 64 65 20 7c 20 74 61  buf.st_mode | ta
2ef0: 72 67 65 74 4d 6f 64 65 29 3b 0a 20 20 20 20 20  rgetMode);.     
2f00: 20 72 63 20 3d 20 31 3b 0a 20 20 20 20 7d 0a 20   rc = 1;.    }. 
2f10: 20 7d 65 6c 73 65 7b 0a 20 20 20 20 69 66 28 20   }else{.    if( 
2f20: 28 62 75 66 2e 73 74 5f 6d 6f 64 65 20 26 20 30  (buf.st_mode & 0
2f30: 31 30 30 29 20 21 3d 20 30 20 29 7b 0a 20 20 20  100) != 0 ){.   
2f40: 20 20 20 63 68 6d 6f 64 28 7a 46 69 6c 65 6e 61     chmod(zFilena
2f50: 6d 65 2c 20 62 75 66 2e 73 74 5f 6d 6f 64 65 20  me, buf.st_mode 
2f60: 26 20 7e 30 31 31 31 29 3b 0a 20 20 20 20 20 20  & ~0111);.      
2f70: 72 63 20 3d 20 31 3b 0a 20 20 20 20 7d 0a 20 20  rc = 1;.    }.  
2f80: 7d 0a 23 65 6e 64 69 66 20 2f 2a 20 5f 57 49 4e  }.#endif /* _WIN
2f90: 33 32 20 2a 2f 0a 20 20 72 65 74 75 72 6e 20 72  32 */.  return r
2fa0: 63 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 53 65 74 20  c;.}../*.** Set 
2fb0: 74 68 65 20 6d 74 69 6d 65 20 66 6f 72 20 61 20  the mtime for a 
2fc0: 66 69 6c 65 2e 0a 2a 2f 0a 76 6f 69 64 20 66 69  file..*/.void fi
2fd0: 6c 65 5f 73 65 74 5f 6d 74 69 6d 65 28 63 6f 6e  le_set_mtime(con
2fe0: 73 74 20 63 68 61 72 20 2a 7a 46 69 6c 65 6e 61  st char *zFilena
2ff0: 6d 65 2c 20 69 36 34 20 6e 65 77 4d 54 69 6d 65  me, i64 newMTime
3000: 29 7b 0a 23 69 66 20 21 64 65 66 69 6e 65 64 28  ){.#if !defined(
3010: 5f 57 49 4e 33 32 29 0a 20 20 63 68 61 72 20 2a  _WIN32).  char *
3020: 7a 4d 62 63 73 3b 0a 20 20 73 74 72 75 63 74 20  zMbcs;.  struct 
3030: 74 69 6d 65 76 61 6c 20 74 76 5b 32 5d 3b 0a 20  timeval tv[2];. 
3040: 20 6d 65 6d 73 65 74 28 74 76 2c 20 30 2c 20 73   memset(tv, 0, s
3050: 69 7a 65 6f 66 28 74 76 5b 30 5d 29 2a 32 29 3b  izeof(tv[0])*2);
3060: 0a 20 20 74 76 5b 30 5d 2e 74 76 5f 73 65 63 20  .  tv[0].tv_sec 
3070: 3d 20 6e 65 77 4d 54 69 6d 65 3b 0a 20 20 74 76  = newMTime;.  tv
3080: 5b 31 5d 2e 74 76 5f 73 65 63 20 3d 20 6e 65 77  [1].tv_sec = new
3090: 4d 54 69 6d 65 3b 0a 20 20 7a 4d 62 63 73 20 3d  MTime;.  zMbcs =
30a0: 20 66 6f 73 73 69 6c 5f 75 74 66 38 5f 74 6f 5f   fossil_utf8_to_
30b0: 70 61 74 68 28 7a 46 69 6c 65 6e 61 6d 65 2c 20  path(zFilename, 
30c0: 30 29 3b 0a 20 20 75 74 69 6d 65 73 28 7a 4d 62  0);.  utimes(zMb
30d0: 63 73 2c 20 74 76 29 3b 0a 23 65 6c 73 65 0a 20  cs, tv);.#else. 
30e0: 20 73 74 72 75 63 74 20 5f 75 74 69 6d 62 75 66   struct _utimbuf
30f0: 20 74 62 3b 0a 20 20 77 63 68 61 72 5f 74 20 2a   tb;.  wchar_t *
3100: 7a 4d 62 63 73 20 3d 20 66 6f 73 73 69 6c 5f 75  zMbcs = fossil_u
3110: 74 66 38 5f 74 6f 5f 70 61 74 68 28 7a 46 69 6c  tf8_to_path(zFil
3120: 65 6e 61 6d 65 2c 20 30 29 3b 0a 20 20 74 62 2e  ename, 0);.  tb.
3130: 61 63 74 69 6d 65 20 3d 20 6e 65 77 4d 54 69 6d  actime = newMTim
3140: 65 3b 0a 20 20 74 62 2e 6d 6f 64 74 69 6d 65 20  e;.  tb.modtime 
3150: 3d 20 6e 65 77 4d 54 69 6d 65 3b 0a 20 20 5f 77  = newMTime;.  _w
3160: 75 74 69 6d 65 28 7a 4d 62 63 73 2c 20 26 74 62  utime(zMbcs, &tb
3170: 29 3b 0a 23 65 6e 64 69 66 0a 20 20 66 6f 73 73  );.#endif.  foss
3180: 69 6c 5f 70 61 74 68 5f 66 72 65 65 28 7a 4d 62  il_path_free(zMb
3190: 63 73 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 43 4f  cs);.}../*.** CO
31a0: 4d 4d 41 4e 44 3a 20 74 65 73 74 2d 73 65 74 2d  MMAND: test-set-
31b0: 6d 74 69 6d 65 0a 2a 2a 0a 2a 2a 20 55 73 61 67  mtime.**.** Usag
31c0: 65 3a 20 25 66 6f 73 73 69 6c 20 74 65 73 74 2d  e: %fossil test-
31d0: 73 65 74 2d 6d 74 69 6d 65 20 46 49 4c 45 4e 41  set-mtime FILENA
31e0: 4d 45 20 44 41 54 45 2f 54 49 4d 45 0a 2a 2a 0a  ME DATE/TIME.**.
31f0: 2a 2a 20 53 65 74 73 20 74 68 65 20 6d 74 69 6d  ** Sets the mtim
3200: 65 20 6f 66 20 74 68 65 20 6e 61 6d 65 64 20 66  e of the named f
3210: 69 6c 65 20 74 6f 20 74 68 65 20 64 61 74 65 2f  ile to the date/
3220: 74 69 6d 65 20 73 68 6f 77 6e 2e 0a 2a 2f 0a 76  time shown..*/.v
3230: 6f 69 64 20 74 65 73 74 5f 73 65 74 5f 6d 74 69  oid test_set_mti
3240: 6d 65 28 76 6f 69 64 29 7b 0a 20 20 63 6f 6e 73  me(void){.  cons
3250: 74 20 63 68 61 72 20 2a 7a 46 69 6c 65 3b 0a 20  t char *zFile;. 
3260: 20 63 68 61 72 20 2a 7a 44 61 74 65 3b 0a 20 20   char *zDate;.  
3270: 69 36 34 20 69 4d 54 69 6d 65 3b 0a 20 20 69 66  i64 iMTime;.  if
3280: 28 20 67 2e 61 72 67 63 21 3d 34 20 29 7b 0a 20  ( g.argc!=4 ){. 
3290: 20 20 20 75 73 61 67 65 28 22 46 49 4c 45 4e 41     usage("FILENA
32a0: 4d 45 20 44 41 54 45 2f 54 49 4d 45 22 29 3b 0a  ME DATE/TIME");.
32b0: 20 20 7d 0a 20 20 64 62 5f 6f 70 65 6e 5f 6f 72    }.  db_open_or
32c0: 5f 61 74 74 61 63 68 28 22 3a 6d 65 6d 6f 72 79  _attach(":memory
32d0: 3a 22 2c 20 22 6d 65 6d 22 2c 20 30 29 3b 0a 20  :", "mem", 0);. 
32e0: 20 69 4d 54 69 6d 65 20 3d 20 64 62 5f 69 6e 74   iMTime = db_int
32f0: 36 34 28 30 2c 20 22 53 45 4c 45 43 54 20 73 74  64(0, "SELECT st
3300: 72 66 74 69 6d 65 28 27 25 25 73 27 2c 25 51 29  rftime('%%s',%Q)
3310: 22 2c 20 67 2e 61 72 67 76 5b 33 5d 29 3b 0a 20  ", g.argv[3]);. 
3320: 20 7a 46 69 6c 65 20 3d 20 67 2e 61 72 67 76 5b   zFile = g.argv[
3330: 32 5d 3b 0a 20 20 66 69 6c 65 5f 73 65 74 5f 6d  2];.  file_set_m
3340: 74 69 6d 65 28 7a 46 69 6c 65 2c 20 69 4d 54 69  time(zFile, iMTi
3350: 6d 65 29 3b 0a 20 20 69 4d 54 69 6d 65 20 3d 20  me);.  iMTime = 
3360: 66 69 6c 65 5f 77 64 5f 6d 74 69 6d 65 28 7a 46  file_wd_mtime(zF
3370: 69 6c 65 29 3b 0a 20 20 7a 44 61 74 65 20 3d 20  ile);.  zDate = 
3380: 64 62 5f 74 65 78 74 28 30 2c 20 22 53 45 4c 45  db_text(0, "SELE
3390: 43 54 20 64 61 74 65 74 69 6d 65 28 25 6c 6c 64  CT datetime(%lld
33a0: 2c 20 27 75 6e 69 78 65 70 6f 63 68 27 29 22 2c  , 'unixepoch')",
33b0: 20 69 4d 54 69 6d 65 29 3b 0a 20 20 66 6f 73 73   iMTime);.  foss
33c0: 69 6c 5f 70 72 69 6e 74 28 22 53 65 74 20 6d 74  il_print("Set mt
33d0: 69 6d 65 20 6f 66 20 5c 22 25 73 5c 22 20 74 6f  ime of \"%s\" to
33e0: 20 25 73 20 28 25 6c 6c 64 29 5c 6e 22 2c 20 7a   %s (%lld)\n", z
33f0: 46 69 6c 65 2c 20 7a 44 61 74 65 2c 20 69 4d 54  File, zDate, iMT
3400: 69 6d 65 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 44  ime);.}../*.** D
3410: 65 6c 65 74 65 20 61 20 66 69 6c 65 2e 0a 2a 2a  elete a file..**
3420: 0a 2a 2a 20 52 65 74 75 72 6e 73 20 7a 65 72 6f  .** Returns zero
3430: 20 75 70 6f 6e 20 73 75 63 63 65 73 73 2e 0a 2a   upon success..*
3440: 2f 0a 69 6e 74 20 66 69 6c 65 5f 64 65 6c 65 74  /.int file_delet
3450: 65 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46  e(const char *zF
3460: 69 6c 65 6e 61 6d 65 29 7b 0a 20 20 69 6e 74 20  ilename){.  int 
3470: 72 63 3b 0a 23 69 66 64 65 66 20 5f 57 49 4e 33  rc;.#ifdef _WIN3
3480: 32 0a 20 20 77 63 68 61 72 5f 74 20 2a 7a 20 3d  2.  wchar_t *z =
3490: 20 66 6f 73 73 69 6c 5f 75 74 66 38 5f 74 6f 5f   fossil_utf8_to_
34a0: 70 61 74 68 28 7a 46 69 6c 65 6e 61 6d 65 2c 20  path(zFilename, 
34b0: 30 29 3b 0a 20 20 72 63 20 3d 20 5f 77 75 6e 6c  0);.  rc = _wunl
34c0: 69 6e 6b 28 7a 29 3b 0a 23 65 6c 73 65 0a 20 20  ink(z);.#else.  
34d0: 63 68 61 72 20 2a 7a 20 3d 20 66 6f 73 73 69 6c  char *z = fossil
34e0: 5f 75 74 66 38 5f 74 6f 5f 70 61 74 68 28 7a 46  _utf8_to_path(zF
34f0: 69 6c 65 6e 61 6d 65 2c 20 30 29 3b 0a 20 20 72  ilename, 0);.  r
3500: 63 20 3d 20 75 6e 6c 69 6e 6b 28 7a 46 69 6c 65  c = unlink(zFile
3510: 6e 61 6d 65 29 3b 0a 23 65 6e 64 69 66 0a 20 20  name);.#endif.  
3520: 66 6f 73 73 69 6c 5f 70 61 74 68 5f 66 72 65 65  fossil_path_free
3530: 28 7a 29 3b 0a 20 20 72 65 74 75 72 6e 20 72 63  (z);.  return rc
3540: 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 43 72 65 61 74  ;.}../*.** Creat
3550: 65 20 74 68 65 20 64 69 72 65 63 74 6f 72 79 20  e the directory 
3560: 6e 61 6d 65 64 20 69 6e 20 74 68 65 20 61 72 67  named in the arg
3570: 75 6d 65 6e 74 2c 20 69 66 20 69 74 20 64 6f 65  ument, if it doe
3580: 73 20 6e 6f 74 20 61 6c 72 65 61 64 79 0a 2a 2a  s not already.**
3590: 20 65 78 69 73 74 2e 20 20 49 66 20 66 6f 72 63   exist.  If forc
35a0: 65 46 6c 61 67 20 69 73 20 31 2c 20 64 65 6c 65  eFlag is 1, dele
35b0: 74 65 20 61 6e 79 20 70 72 69 6f 72 20 6e 6f 6e  te any prior non
35c0: 2d 64 69 72 65 63 74 6f 72 79 20 6f 62 6a 65 63  -directory objec
35d0: 74 0a 2a 2a 20 77 69 74 68 20 74 68 65 20 73 61  t.** with the sa
35e0: 6d 65 20 6e 61 6d 65 2e 0a 2a 2a 0a 2a 2a 20 52  me name..**.** R
35f0: 65 74 75 72 6e 20 74 68 65 20 6e 75 6d 62 65 72  eturn the number
3600: 20 6f 66 20 65 72 72 6f 72 73 2e 0a 2a 2f 0a 69   of errors..*/.i
3610: 6e 74 20 66 69 6c 65 5f 6d 6b 64 69 72 28 63 6f  nt file_mkdir(co
3620: 6e 73 74 20 63 68 61 72 20 2a 7a 4e 61 6d 65 2c  nst char *zName,
3630: 20 69 6e 74 20 66 6f 72 63 65 46 6c 61 67 29 7b   int forceFlag){
3640: 0a 20 20 69 6e 74 20 72 63 20 3d 20 66 69 6c 65  .  int rc = file
3650: 5f 77 64 5f 69 73 64 69 72 28 7a 4e 61 6d 65 29  _wd_isdir(zName)
3660: 3b 0a 20 20 69 66 28 20 72 63 3d 3d 32 20 29 7b  ;.  if( rc==2 ){
3670: 0a 20 20 20 20 69 66 28 20 21 66 6f 72 63 65 46  .    if( !forceF
3680: 6c 61 67 20 29 20 72 65 74 75 72 6e 20 31 3b 0a  lag ) return 1;.
3690: 20 20 20 20 66 69 6c 65 5f 64 65 6c 65 74 65 28      file_delete(
36a0: 7a 4e 61 6d 65 29 3b 0a 20 20 7d 0a 20 20 69 66  zName);.  }.  if
36b0: 28 20 72 63 21 3d 31 20 29 7b 0a 23 69 66 20 64  ( rc!=1 ){.#if d
36c0: 65 66 69 6e 65 64 28 5f 57 49 4e 33 32 29 0a 20  efined(_WIN32). 
36d0: 20 20 20 77 63 68 61 72 5f 74 20 2a 7a 4d 62 63     wchar_t *zMbc
36e0: 73 20 3d 20 66 6f 73 73 69 6c 5f 75 74 66 38 5f  s = fossil_utf8_
36f0: 74 6f 5f 70 61 74 68 28 7a 4e 61 6d 65 2c 20 31  to_path(zName, 1
3700: 29 3b 0a 20 20 20 20 72 63 20 3d 20 5f 77 6d 6b  );.    rc = _wmk
3710: 64 69 72 28 7a 4d 62 63 73 29 3b 0a 23 65 6c 73  dir(zMbcs);.#els
3720: 65 0a 20 20 20 20 63 68 61 72 20 2a 7a 4d 62 63  e.    char *zMbc
3730: 73 20 3d 20 66 6f 73 73 69 6c 5f 75 74 66 38 5f  s = fossil_utf8_
3740: 74 6f 5f 70 61 74 68 28 7a 4e 61 6d 65 2c 20 31  to_path(zName, 1
3750: 29 3b 0a 20 20 20 20 72 63 20 3d 20 6d 6b 64 69  );.    rc = mkdi
3760: 72 28 7a 4e 61 6d 65 2c 20 30 37 35 35 29 3b 0a  r(zName, 0755);.
3770: 23 65 6e 64 69 66 0a 20 20 20 20 66 6f 73 73 69  #endif.    fossi
3780: 6c 5f 70 61 74 68 5f 66 72 65 65 28 7a 4d 62 63  l_path_free(zMbc
3790: 73 29 3b 0a 20 20 20 20 72 65 74 75 72 6e 20 72  s);.    return r
37a0: 63 3b 0a 20 20 7d 0a 20 20 72 65 74 75 72 6e 20  c;.  }.  return 
37b0: 30 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 43 72 65 61  0;.}../*.** Crea
37c0: 74 65 20 74 68 65 20 74 72 65 65 20 6f 66 20 64  te the tree of d
37d0: 69 72 65 63 74 6f 72 69 65 73 20 69 6e 20 77 68  irectories in wh
37e0: 69 63 68 20 7a 46 69 6c 65 6e 61 6d 65 20 62 65  ich zFilename be
37f0: 6c 6f 6e 67 73 2c 20 69 66 20 74 68 61 74 20 73  longs, if that s
3800: 65 71 75 65 6e 63 65 0a 2a 2a 20 6f 66 20 64 69  equence.** of di
3810: 72 65 63 74 6f 72 69 65 73 20 64 6f 65 73 20 6e  rectories does n
3820: 6f 74 20 61 6c 72 65 61 64 79 20 65 78 69 73 74  ot already exist
3830: 2e 0a 2a 2a 0a 2a 2a 20 4f 6e 20 73 75 63 63 65  ..**.** On succe
3840: 73 73 2c 20 72 65 74 75 72 6e 20 7a 65 72 6f 2e  ss, return zero.
3850: 20 20 4f 6e 20 65 72 72 6f 72 2c 20 72 65 74 75    On error, retu
3860: 72 6e 20 65 72 72 6f 72 52 65 74 75 72 6e 20 69  rn errorReturn i
3870: 66 20 70 6f 73 69 74 69 76 65 2c 20 6f 74 68 65  f positive, othe
3880: 72 77 69 73 65 0a 2a 2a 20 70 72 69 6e 74 20 61  rwise.** print a
3890: 6e 20 65 72 72 6f 72 20 6d 65 73 73 61 67 65 20  n error message 
38a0: 61 6e 64 20 61 62 6f 72 74 2e 0a 2a 2f 0a 69 6e  and abort..*/.in
38b0: 74 20 66 69 6c 65 5f 6d 6b 66 6f 6c 64 65 72 28  t file_mkfolder(
38c0: 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 46 69 6c  const char *zFil
38d0: 65 6e 61 6d 65 2c 20 69 6e 74 20 66 6f 72 63 65  ename, int force
38e0: 46 6c 61 67 2c 20 69 6e 74 20 65 72 72 6f 72 52  Flag, int errorR
38f0: 65 74 75 72 6e 29 7b 0a 20 20 69 6e 74 20 69 2c  eturn){.  int i,
3900: 20 6e 4e 61 6d 65 2c 20 72 63 20 3d 20 30 3b 0a   nName, rc = 0;.
3910: 20 20 63 68 61 72 20 2a 7a 4e 61 6d 65 3b 0a 0a    char *zName;..
3920: 20 20 6e 4e 61 6d 65 20 3d 20 73 74 72 6c 65 6e    nName = strlen
3930: 28 7a 46 69 6c 65 6e 61 6d 65 29 3b 0a 20 20 7a  (zFilename);.  z
3940: 4e 61 6d 65 20 3d 20 6d 70 72 69 6e 74 66 28 22  Name = mprintf("
3950: 25 73 22 2c 20 7a 46 69 6c 65 6e 61 6d 65 29 3b  %s", zFilename);
3960: 0a 20 20 6e 4e 61 6d 65 20 3d 20 66 69 6c 65 5f  .  nName = file_
3970: 73 69 6d 70 6c 69 66 79 5f 6e 61 6d 65 28 7a 4e  simplify_name(zN
3980: 61 6d 65 2c 20 6e 4e 61 6d 65 2c 20 30 29 3b 0a  ame, nName, 0);.
3990: 20 20 66 6f 72 28 69 3d 31 3b 20 69 3c 6e 4e 61    for(i=1; i<nNa
39a0: 6d 65 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 69 66  me; i++){.    if
39b0: 28 20 7a 4e 61 6d 65 5b 69 5d 3d 3d 27 2f 27 20  ( zName[i]=='/' 
39c0: 29 7b 0a 20 20 20 20 20 20 7a 4e 61 6d 65 5b 69  ){.      zName[i
39d0: 5d 20 3d 20 30 3b 0a 23 69 66 20 64 65 66 69 6e  ] = 0;.#if defin
39e0: 65 64 28 5f 57 49 4e 33 32 29 20 7c 7c 20 64 65  ed(_WIN32) || de
39f0: 66 69 6e 65 64 28 5f 5f 43 59 47 57 49 4e 5f 5f  fined(__CYGWIN__
3a00: 29 0a 20 20 20 20 20 20 2f 2a 0a 20 20 20 20 20  ).      /*.     
3a10: 20 2a 2a 20 4f 6e 20 57 69 6e 64 6f 77 73 2c 20   ** On Windows, 
3a20: 6c 6f 63 61 6c 20 70 61 74 68 20 6c 6f 6f 6b 73  local path looks
3a30: 20 6c 69 6b 65 3a 20 43 3a 2f 64 65 76 65 6c 6f   like: C:/develo
3a40: 70 2f 70 72 6f 6a 65 63 74 2f 66 69 6c 65 2e 74  p/project/file.t
3a50: 78 74 0a 20 20 20 20 20 20 2a 2a 20 54 68 65 20  xt.      ** The 
3a60: 69 66 20 73 74 6f 70 73 20 75 73 20 66 72 6f 6d  if stops us from
3a70: 20 74 72 79 69 6e 67 20 74 6f 20 63 72 65 61 74   trying to creat
3a80: 65 20 61 20 64 69 72 65 63 74 6f 72 79 20 6f 66  e a directory of
3a90: 20 61 20 64 72 69 76 65 20 6c 65 74 74 65 72 0a   a drive letter.
3aa0: 20 20 20 20 20 20 2a 2a 20 43 3a 20 69 6e 20 74        ** C: in t
3ab0: 68 69 73 20 65 78 61 6d 70 6c 65 2e 0a 20 20 20  his example..   
3ac0: 20 20 20 2a 2f 0a 20 20 20 20 20 20 69 66 28 20     */.      if( 
3ad0: 21 28 69 3d 3d 32 20 26 26 20 7a 4e 61 6d 65 5b  !(i==2 && zName[
3ae0: 31 5d 3d 3d 27 3a 27 29 20 29 7b 0a 23 65 6e 64  1]==':') ){.#end
3af0: 69 66 0a 20 20 20 20 20 20 20 20 69 66 28 20 66  if.        if( f
3b00: 69 6c 65 5f 6d 6b 64 69 72 28 7a 4e 61 6d 65 2c  ile_mkdir(zName,
3b10: 20 66 6f 72 63 65 46 6c 61 67 29 20 26 26 20 66   forceFlag) && f
3b20: 69 6c 65 5f 69 73 64 69 72 28 7a 4e 61 6d 65 29  ile_isdir(zName)
3b30: 21 3d 31 20 29 7b 0a 20 20 20 20 20 20 20 20 20  !=1 ){.         
3b40: 20 69 66 20 28 65 72 72 6f 72 52 65 74 75 72 6e   if (errorReturn
3b50: 20 3c 3d 20 30 29 20 7b 0a 20 20 20 20 20 20 20   <= 0) {.       
3b60: 20 20 20 20 20 66 6f 73 73 69 6c 5f 66 61 74 61       fossil_fata
3b70: 6c 5f 72 65 63 75 72 73 69 76 65 28 22 75 6e 61  l_recursive("una
3b80: 62 6c 65 20 74 6f 20 63 72 65 61 74 65 20 64 69  ble to create di
3b90: 72 65 63 74 6f 72 79 20 25 73 22 2c 20 7a 4e 61  rectory %s", zNa
3ba0: 6d 65 29 3b 0a 20 20 20 20 20 20 20 20 20 20 7d  me);.          }
3bb0: 0a 20 20 20 20 20 20 20 20 20 20 72 63 20 3d 20  .          rc = 
3bc0: 65 72 72 6f 72 52 65 74 75 72 6e 3b 0a 20 20 20  errorReturn;.   
3bd0: 20 20 20 20 20 20 20 62 72 65 61 6b 3b 0a 20 20         break;.  
3be0: 20 20 20 20 20 20 7d 0a 23 69 66 20 64 65 66 69        }.#if defi
3bf0: 6e 65 64 28 5f 57 49 4e 33 32 29 20 7c 7c 20 64  ned(_WIN32) || d
3c00: 65 66 69 6e 65 64 28 5f 5f 43 59 47 57 49 4e 5f  efined(__CYGWIN_
3c10: 5f 29 0a 20 20 20 20 20 20 7d 0a 23 65 6e 64 69  _).      }.#endi
3c20: 66 0a 20 20 20 20 20 20 7a 4e 61 6d 65 5b 69 5d  f.      zName[i]
3c30: 20 3d 20 27 2f 27 3b 0a 20 20 20 20 7d 0a 20 20   = '/';.    }.  
3c40: 7d 0a 20 20 66 72 65 65 28 7a 4e 61 6d 65 29 3b  }.  free(zName);
3c50: 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a  .  return rc;.}.
3c60: 0a 2f 2a 0a 2a 2a 20 52 65 6d 6f 76 65 73 20 74  ./*.** Removes t
3c70: 68 65 20 64 69 72 65 63 74 6f 72 79 20 6e 61 6d  he directory nam
3c80: 65 64 20 69 6e 20 74 68 65 20 61 72 67 75 6d 65  ed in the argume
3c90: 6e 74 2c 20 69 66 20 69 74 20 65 78 69 73 74 73  nt, if it exists
3ca0: 2e 20 20 54 68 65 20 64 69 72 65 63 74 6f 72 79  .  The directory
3cb0: 0a 2a 2a 20 6d 75 73 74 20 62 65 20 65 6d 70 74  .** must be empt
3cc0: 79 20 61 6e 64 20 63 61 6e 6e 6f 74 20 62 65 20  y and cannot be 
3cd0: 74 68 65 20 63 75 72 72 65 6e 74 20 64 69 72 65  the current dire
3ce0: 63 74 6f 72 79 20 6f 72 20 74 68 65 20 72 6f 6f  ctory or the roo
3cf0: 74 20 64 69 72 65 63 74 6f 72 79 2e 0a 2a 2a 0a  t directory..**.
3d00: 2a 2a 20 52 65 74 75 72 6e 73 20 7a 65 72 6f 20  ** Returns zero 
3d10: 75 70 6f 6e 20 73 75 63 63 65 73 73 2e 0a 2a 2f  upon success..*/
3d20: 0a 69 6e 74 20 66 69 6c 65 5f 72 6d 64 69 72 28  .int file_rmdir(
3d30: 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 4e 61 6d  const char *zNam
3d40: 65 29 7b 0a 20 20 69 6e 74 20 72 63 20 3d 20 66  e){.  int rc = f
3d50: 69 6c 65 5f 77 64 5f 69 73 64 69 72 28 7a 4e 61  ile_wd_isdir(zNa
3d60: 6d 65 29 3b 0a 20 20 69 66 28 20 72 63 3d 3d 32  me);.  if( rc==2
3d70: 20 29 20 72 65 74 75 72 6e 20 31 3b 20 2f 2a 20   ) return 1; /* 
3d80: 63 61 6e 6e 6f 74 20 72 65 6d 6f 76 65 20 6e 6f  cannot remove no
3d90: 72 6d 61 6c 20 66 69 6c 65 20 2a 2f 0a 20 20 69  rmal file */.  i
3da0: 66 28 20 72 63 3d 3d 31 20 29 7b 0a 23 69 66 20  f( rc==1 ){.#if 
3db0: 64 65 66 69 6e 65 64 28 5f 57 49 4e 33 32 29 0a  defined(_WIN32).
3dc0: 20 20 20 20 77 63 68 61 72 5f 74 20 2a 7a 4d 62      wchar_t *zMb
3dd0: 63 73 20 3d 20 66 6f 73 73 69 6c 5f 75 74 66 38  cs = fossil_utf8
3de0: 5f 74 6f 5f 70 61 74 68 28 7a 4e 61 6d 65 2c 20  _to_path(zName, 
3df0: 31 29 3b 0a 20 20 20 20 72 63 20 3d 20 5f 77 72  1);.    rc = _wr
3e00: 6d 64 69 72 28 7a 4d 62 63 73 29 3b 0a 23 65 6c  mdir(zMbcs);.#el
3e10: 73 65 0a 20 20 20 20 63 68 61 72 20 2a 7a 4d 62  se.    char *zMb
3e20: 63 73 20 3d 20 66 6f 73 73 69 6c 5f 75 74 66 38  cs = fossil_utf8
3e30: 5f 74 6f 5f 70 61 74 68 28 7a 4e 61 6d 65 2c 20  _to_path(zName, 
3e40: 31 29 3b 0a 20 20 20 20 72 63 20 3d 20 72 6d 64  1);.    rc = rmd
3e50: 69 72 28 7a 4e 61 6d 65 29 3b 0a 23 65 6e 64 69  ir(zName);.#endi
3e60: 66 0a 20 20 20 20 66 6f 73 73 69 6c 5f 70 61 74  f.    fossil_pat
3e70: 68 5f 66 72 65 65 28 7a 4d 62 63 73 29 3b 0a 20  h_free(zMbcs);. 
3e80: 20 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 20 20     return rc;.  
3e90: 7d 0a 20 20 72 65 74 75 72 6e 20 30 3b 0a 7d 0a  }.  return 0;.}.
3ea0: 0a 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 74 72  ./*.** Return tr
3eb0: 75 65 20 69 66 20 74 68 65 20 66 69 6c 65 6e 61  ue if the filena
3ec0: 6d 65 20 67 69 76 65 6e 20 69 73 20 61 20 76 61  me given is a va
3ed0: 6c 69 64 20 66 69 6c 65 6e 61 6d 65 20 66 6f 72  lid filename for
3ee0: 0a 2a 2a 20 61 20 66 69 6c 65 20 69 6e 20 61 20  .** a file in a 
3ef0: 72 65 70 6f 73 69 74 6f 72 79 2e 20 20 56 61 6c  repository.  Val
3f00: 69 64 20 66 69 6c 65 6e 61 6d 65 73 20 66 6f 6c  id filenames fol
3f10: 6c 6f 77 20 61 6c 6c 20 6f 66 20 74 68 65 0a 2a  low all of the.*
3f20: 2a 20 66 6f 6c 6c 6f 77 69 6e 67 20 72 75 6c 65  * following rule
3f30: 73 3a 0a 2a 2a 0a 2a 2a 20 20 20 20 20 2a 20 20  s:.**.**     *  
3f40: 44 6f 65 73 20 6e 6f 74 20 62 65 67 69 6e 20 77  Does not begin w
3f50: 69 74 68 20 22 2f 22 0a 2a 2a 20 20 20 20 20 2a  ith "/".**     *
3f60: 20 20 44 6f 65 73 20 6e 6f 74 20 63 6f 6e 74 61    Does not conta
3f70: 69 6e 20 61 6e 79 20 70 61 74 68 20 65 6c 65 6d  in any path elem
3f80: 65 6e 74 20 6e 61 6d 65 64 20 22 2e 22 20 6f 72  ent named "." or
3f90: 20 22 2e 2e 22 0a 2a 2a 20 20 20 20 20 2a 20 20   "..".**     *  
3fa0: 44 6f 65 73 20 6e 6f 74 20 63 6f 6e 74 61 69 6e  Does not contain
3fb0: 20 61 6e 79 20 6f 66 20 74 68 65 73 65 20 63 68   any of these ch
3fc0: 61 72 61 63 74 65 72 73 20 69 6e 20 74 68 65 20  aracters in the 
3fd0: 70 61 74 68 3a 20 22 5c 22 0a 2a 2a 20 20 20 20  path: "\".**    
3fe0: 20 2a 20 20 44 6f 65 73 20 6e 6f 74 20 65 6e 64   *  Does not end
3ff0: 20 77 69 74 68 20 22 2f 22 2e 0a 2a 2a 20 20 20   with "/"..**   
4000: 20 20 2a 20 20 44 6f 65 73 20 6e 6f 74 20 63 6f    *  Does not co
4010: 6e 74 61 69 6e 20 74 77 6f 20 6f 72 20 6d 6f 72  ntain two or mor
4020: 65 20 22 2f 22 20 63 68 61 72 61 63 74 65 72 73  e "/" characters
4030: 20 69 6e 20 61 20 72 6f 77 2e 0a 2a 2a 20 20 20   in a row..**   
4040: 20 20 2a 20 20 43 6f 6e 74 61 69 6e 73 20 61 74    *  Contains at
4050: 20 6c 65 61 73 74 20 6f 6e 65 20 63 68 61 72 61   least one chara
4060: 63 74 65 72 0a 2a 2a 0a 2a 2a 20 49 6e 76 61 6c  cter.**.** Inval
4070: 69 64 20 55 54 46 38 20 63 68 61 72 61 63 74 65  id UTF8 characte
4080: 72 73 20 72 65 73 75 6c 74 20 69 6e 20 61 20 66  rs result in a f
4090: 61 6c 73 65 20 72 65 74 75 72 6e 20 69 66 20 62  alse return if b
40a0: 53 74 72 69 63 74 55 74 66 38 20 69 73 0a 2a 2a  StrictUtf8 is.**
40b0: 20 74 72 75 65 2e 20 20 49 66 20 62 53 74 72 69   true.  If bStri
40c0: 63 74 55 74 66 38 20 69 73 20 66 61 6c 73 65 2c  ctUtf8 is false,
40d0: 20 69 6e 76 61 6c 69 64 20 55 54 46 38 20 63 68   invalid UTF8 ch
40e0: 61 72 61 63 74 65 72 73 20 61 72 65 20 73 69 6c  aracters are sil
40f0: 65 6e 74 6c 79 0a 2a 2a 20 69 67 6e 6f 72 65 64  ently.** ignored
4100: 2e 20 53 65 65 20 68 74 74 70 3a 2f 2f 65 6e 2e  . See http://en.
4110: 77 69 6b 69 70 65 64 69 61 2e 6f 72 67 2f 77 69  wikipedia.org/wi
4120: 6b 69 2f 55 54 46 2d 38 23 49 6e 76 61 6c 69 64  ki/UTF-8#Invalid
4130: 5f 62 79 74 65 5f 73 65 71 75 65 6e 63 65 73 0a  _byte_sequences.
4140: 2a 2a 20 61 6e 64 20 68 74 74 70 3a 2f 2f 65 6e  ** and http://en
4150: 2e 77 69 6b 69 70 65 64 69 61 2e 6f 72 67 2f 77  .wikipedia.org/w
4160: 69 6b 69 2f 55 6e 69 63 6f 64 65 20 28 66 6f 72  iki/Unicode (for
4170: 20 74 68 65 20 6e 6f 6e 63 68 61 72 61 63 74 65   the noncharacte
4180: 72 73 29 0a 2a 2a 0a 2a 2a 20 54 68 65 20 62 53  rs).**.** The bS
4190: 74 72 69 63 74 55 74 66 38 20 66 6c 61 67 20 69  trictUtf8 flag i
41a0: 73 20 74 72 75 65 20 66 6f 72 20 6e 65 77 20 69  s true for new i
41b0: 6e 70 75 74 73 2c 20 62 75 74 20 69 73 20 66 61  nputs, but is fa
41c0: 6c 73 65 20 77 68 65 6e 20 70 61 72 73 69 6e 67  lse when parsing
41d0: 0a 2a 2a 20 6c 65 67 61 63 79 20 6d 61 6e 69 66  .** legacy manif
41e0: 65 73 74 73 2c 20 66 6f 72 20 62 61 63 6b 77 61  ests, for backwa
41f0: 72 64 73 20 63 6f 6d 70 61 74 69 62 69 6c 69 74  rds compatibilit
4200: 79 2e 0a 2a 2f 0a 69 6e 74 20 66 69 6c 65 5f 69  y..*/.int file_i
4210: 73 5f 73 69 6d 70 6c 65 5f 70 61 74 68 6e 61 6d  s_simple_pathnam
4220: 65 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 2c  e(const char *z,
4230: 20 69 6e 74 20 62 53 74 72 69 63 74 55 74 66 38   int bStrictUtf8
4240: 29 7b 0a 20 20 69 6e 74 20 69 3b 0a 20 20 75 6e  ){.  int i;.  un
4250: 73 69 67 6e 65 64 20 63 68 61 72 20 63 20 3d 20  signed char c = 
4260: 28 75 6e 73 69 67 6e 65 64 20 63 68 61 72 29 20  (unsigned char) 
4270: 7a 5b 30 5d 3b 0a 20 20 63 68 61 72 20 6d 61 73  z[0];.  char mas
4280: 6b 4e 6f 6e 41 73 63 69 69 20 3d 20 62 53 74 72  kNonAscii = bStr
4290: 69 63 74 55 74 66 38 20 3f 20 30 78 38 30 20 3a  ictUtf8 ? 0x80 :
42a0: 20 30 78 30 30 3b 0a 20 20 69 66 28 20 63 3d 3d   0x00;.  if( c==
42b0: 27 2f 27 20 7c 7c 20 63 3d 3d 30 20 29 20 72 65  '/' || c==0 ) re
42c0: 74 75 72 6e 20 30 3b 0a 20 20 69 66 28 20 63 3d  turn 0;.  if( c=
42d0: 3d 27 2e 27 20 29 7b 0a 20 20 20 20 69 66 28 20  ='.' ){.    if( 
42e0: 7a 5b 31 5d 3d 3d 27 2f 27 20 7c 7c 20 7a 5b 31  z[1]=='/' || z[1
42f0: 5d 3d 3d 30 20 29 20 72 65 74 75 72 6e 20 30 3b  ]==0 ) return 0;
4300: 0a 20 20 20 20 69 66 28 20 7a 5b 31 5d 3d 3d 27  .    if( z[1]=='
4310: 2e 27 20 26 26 20 28 7a 5b 32 5d 3d 3d 27 2f 27  .' && (z[2]=='/'
4320: 20 7c 7c 20 7a 5b 32 5d 3d 3d 30 29 20 29 20 72   || z[2]==0) ) r
4330: 65 74 75 72 6e 20 30 3b 0a 20 20 7d 0a 20 20 66  eturn 0;.  }.  f
4340: 6f 72 28 69 3d 30 3b 20 28 63 3d 28 75 6e 73 69  or(i=0; (c=(unsi
4350: 67 6e 65 64 20 63 68 61 72 29 7a 5b 69 5d 29 21  gned char)z[i])!
4360: 3d 30 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 69 66  =0; i++){.    if
4370: 28 20 63 20 26 20 6d 61 73 6b 4e 6f 6e 41 73 63  ( c & maskNonAsc
4380: 69 69 20 29 7b 0a 20 20 20 20 20 20 69 66 28 20  ii ){.      if( 
4390: 28 7a 5b 2b 2b 69 5d 26 30 78 63 30 29 21 3d 30  (z[++i]&0xc0)!=0
43a0: 78 38 30 20 29 7b 0a 20 20 20 20 20 20 20 20 2f  x80 ){.        /
43b0: 2a 20 49 6e 76 61 6c 69 64 20 66 69 72 73 74 20  * Invalid first 
43c0: 63 6f 6e 74 69 6e 75 61 74 69 6f 6e 20 62 79 74  continuation byt
43d0: 65 20 2a 2f 0a 20 20 20 20 20 20 20 20 72 65 74  e */.        ret
43e0: 75 72 6e 20 30 3b 0a 20 20 20 20 20 20 7d 0a 20  urn 0;.      }. 
43f0: 20 20 20 20 20 69 66 28 20 63 3c 30 78 63 32 20       if( c<0xc2 
4400: 29 7b 0a 20 20 20 20 20 20 20 20 2f 2a 20 49 6e  ){.        /* In
4410: 76 61 6c 69 64 20 31 2d 62 79 74 65 20 55 54 46  valid 1-byte UTF
4420: 2d 38 20 73 65 71 75 65 6e 63 65 2c 20 6f 72 20  -8 sequence, or 
4430: 32 2d 62 79 74 65 20 6f 76 65 72 6c 6f 6e 67 20  2-byte overlong 
4440: 66 6f 72 6d 2e 20 2a 2f 0a 20 20 20 20 20 20 20  form. */.       
4450: 20 72 65 74 75 72 6e 20 30 3b 0a 20 20 20 20 20   return 0;.     
4460: 20 7d 65 6c 73 65 20 69 66 28 20 28 63 26 30 78   }else if( (c&0x
4470: 65 30 29 3d 3d 30 78 65 30 20 29 7b 0a 20 20 20  e0)==0xe0 ){.   
4480: 20 20 20 20 20 2f 2a 20 33 2d 62 79 74 65 20 6f       /* 3-byte o
4490: 72 20 6d 6f 72 65 20 2a 2f 0a 20 20 20 20 20 20  r more */.      
44a0: 20 20 69 6e 74 20 75 6e 69 63 6f 64 65 3b 0a 20    int unicode;. 
44b0: 20 20 20 20 20 20 20 69 66 28 20 63 26 30 78 31         if( c&0x1
44c0: 30 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 2f  0 ){.          /
44d0: 2a 20 55 6e 69 63 6f 64 65 20 63 68 61 72 61 63  * Unicode charac
44e0: 74 65 72 73 20 3e 20 55 2b 46 46 46 46 20 61 72  ters > U+FFFF ar
44f0: 65 20 6e 6f 74 20 73 75 70 70 6f 72 74 65 64 2e  e not supported.
4500: 0a 20 20 20 20 20 20 20 20 20 20 20 2a 20 57 69  .           * Wi
4510: 6e 64 6f 77 73 20 58 50 20 61 6e 64 20 65 61 72  ndows XP and ear
4520: 6c 69 65 72 20 63 61 6e 6e 6f 74 20 68 61 6e 64  lier cannot hand
4530: 6c 65 20 74 68 65 6d 2e 0a 20 20 20 20 20 20 20  le them..       
4540: 20 20 20 20 2a 2f 0a 20 20 20 20 20 20 20 20 20      */.         
4550: 20 72 65 74 75 72 6e 20 30 3b 0a 20 20 20 20 20   return 0;.     
4560: 20 20 20 7d 0a 20 20 20 20 20 20 20 20 2f 2a 20     }.        /* 
4570: 54 68 69 73 20 69 73 20 61 20 33 2d 62 79 74 65  This is a 3-byte
4580: 20 55 54 46 2d 38 20 63 68 61 72 61 63 74 65 72   UTF-8 character
4590: 20 2a 2f 0a 20 20 20 20 20 20 20 20 75 6e 69 63   */.        unic
45a0: 6f 64 65 20 3d 20 28 28 63 26 30 78 30 66 29 3c  ode = ((c&0x0f)<
45b0: 3c 31 32 29 20 2b 20 28 28 7a 5b 69 5d 26 30 78  <12) + ((z[i]&0x
45c0: 33 66 29 3c 3c 36 29 20 2b 20 28 7a 5b 69 2b 31  3f)<<6) + (z[i+1
45d0: 5d 26 30 78 33 66 29 3b 0a 20 20 20 20 20 20 20  ]&0x3f);.       
45e0: 20 69 66 28 20 75 6e 69 63 6f 64 65 20 3c 3d 20   if( unicode <= 
45f0: 30 78 30 37 66 66 20 29 7b 0a 20 20 20 20 20 20  0x07ff ){.      
4600: 20 20 20 20 2f 2a 20 6f 76 65 72 6c 6f 6e 67 20      /* overlong 
4610: 66 6f 72 6d 20 2a 2f 0a 20 20 20 20 20 20 20 20  form */.        
4620: 20 20 72 65 74 75 72 6e 20 30 3b 0a 20 20 20 20    return 0;.    
4630: 20 20 20 20 7d 65 6c 73 65 20 69 66 28 20 75 6e      }else if( un
4640: 69 63 6f 64 65 3e 3d 30 78 65 30 30 30 20 29 7b  icode>=0xe000 ){
4650: 0a 20 20 20 20 20 20 20 20 20 20 2f 2a 20 55 2b  .          /* U+
4660: 45 30 30 30 2e 2e 55 2b 46 46 46 46 20 2a 2f 0a  E000..U+FFFF */.
4670: 20 20 20 20 20 20 20 20 20 20 69 66 28 20 28 75            if( (u
4680: 6e 69 63 6f 64 65 3c 3d 30 78 66 38 66 66 29 20  nicode<=0xf8ff) 
4690: 7c 7c 20 28 75 6e 69 63 6f 64 65 3e 3d 30 78 66  || (unicode>=0xf
46a0: 66 66 65 29 20 29 7b 0a 20 20 20 20 20 20 20 20  ffe) ){.        
46b0: 20 20 20 20 2f 2a 20 55 2b 45 30 30 30 2e 2e 55      /* U+E000..U
46c0: 2b 46 38 46 46 20 61 72 65 20 66 6f 72 20 70 72  +F8FF are for pr
46d0: 69 76 61 74 65 20 75 73 65 2e 0a 20 20 20 20 20  ivate use..     
46e0: 20 20 20 20 20 20 20 20 2a 20 55 2b 46 46 46 45          * U+FFFE
46f0: 2e 2e 55 2b 46 46 46 46 20 61 72 65 20 6e 6f 6e  ..U+FFFF are non
4700: 63 68 61 72 61 63 74 65 72 73 2e 20 2a 2f 0a 20  characters. */. 
4710: 20 20 20 20 20 20 20 20 20 20 20 72 65 74 75 72             retur
4720: 6e 20 30 3b 0a 20 20 20 20 20 20 20 20 20 20 7d  n 0;.          }
4730: 20 65 6c 73 65 20 69 66 28 20 28 75 6e 69 63 6f   else if( (unico
4740: 64 65 3e 3d 30 78 66 64 64 30 29 20 26 26 20 28  de>=0xfdd0) && (
4750: 75 6e 69 63 6f 64 65 3c 3d 30 78 66 64 65 66 29  unicode<=0xfdef)
4760: 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20 20 20   ){.            
4770: 2f 2a 20 55 2b 46 44 44 30 2e 2e 55 2b 46 44 45  /* U+FDD0..U+FDE
4780: 46 20 61 72 65 20 6e 6f 6e 63 68 61 72 61 63 74  F are noncharact
4790: 65 72 73 2e 20 2a 2f 0a 20 20 20 20 20 20 20 20  ers. */.        
47a0: 20 20 20 20 72 65 74 75 72 6e 20 30 3b 0a 20 20      return 0;.  
47b0: 20 20 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20          }.      
47c0: 20 20 7d 65 6c 73 65 20 69 66 28 20 28 75 6e 69    }else if( (uni
47d0: 63 6f 64 65 3e 3d 30 78 64 38 30 30 29 20 26 26  code>=0xd800) &&
47e0: 20 28 75 6e 69 63 6f 64 65 3c 3d 30 78 64 66 66   (unicode<=0xdff
47f0: 66 29 20 29 7b 0a 20 20 20 20 20 20 20 20 20 20  f) ){.          
4800: 2f 2a 20 55 2b 44 38 30 30 2e 2e 55 2b 44 46 46  /* U+D800..U+DFF
4810: 46 20 61 72 65 20 66 6f 72 20 73 75 72 72 6f 67  F are for surrog
4820: 61 74 65 20 70 61 69 72 73 2e 20 2a 2f 0a 20 20  ate pairs. */.  
4830: 20 20 20 20 20 20 20 20 72 65 74 75 72 6e 20 30          return 0
4840: 3b 0a 20 20 20 20 20 20 20 20 7d 0a 20 20 20 20  ;.        }.    
4850: 20 20 20 20 69 66 28 20 28 7a 5b 2b 2b 69 5d 26      if( (z[++i]&
4860: 30 78 63 30 29 21 3d 30 78 38 30 20 29 7b 0a 20  0xc0)!=0x80 ){. 
4870: 20 20 20 20 20 20 20 20 20 2f 2a 20 49 6e 76 61           /* Inva
4880: 6c 69 64 20 73 65 63 6f 6e 64 20 63 6f 6e 74 69  lid second conti
4890: 6e 75 61 74 69 6f 6e 20 62 79 74 65 20 2a 2f 0a  nuation byte */.
48a0: 20 20 20 20 20 20 20 20 20 20 72 65 74 75 72 6e            return
48b0: 20 30 3b 0a 20 20 20 20 20 20 20 20 7d 0a 20 20   0;.        }.  
48c0: 20 20 20 20 7d 0a 20 20 20 20 7d 65 6c 73 65 20      }.    }else 
48d0: 69 66 28 20 62 53 74 72 69 63 74 55 74 66 38 20  if( bStrictUtf8 
48e0: 26 26 20 28 63 3d 3d 27 5c 5c 27 29 20 29 7b 0a  && (c=='\\') ){.
48f0: 20 20 20 20 20 20 72 65 74 75 72 6e 20 30 3b 0a        return 0;.
4900: 20 20 20 20 7d 0a 20 20 20 20 69 66 28 20 63 3d      }.    if( c=
4910: 3d 27 2f 27 20 29 7b 0a 20 20 20 20 20 20 69 66  ='/' ){.      if
4920: 28 20 7a 5b 69 2b 31 5d 3d 3d 27 2f 27 20 29 20  ( z[i+1]=='/' ) 
4930: 72 65 74 75 72 6e 20 30 3b 0a 20 20 20 20 20 20  return 0;.      
4940: 69 66 28 20 7a 5b 69 2b 31 5d 3d 3d 27 2e 27 20  if( z[i+1]=='.' 
4950: 29 7b 0a 20 20 20 20 20 20 20 20 69 66 28 20 7a  ){.        if( z
4960: 5b 69 2b 32 5d 3d 3d 27 2f 27 20 7c 7c 20 7a 5b  [i+2]=='/' || z[
4970: 69 2b 32 5d 3d 3d 30 20 29 20 72 65 74 75 72 6e  i+2]==0 ) return
4980: 20 30 3b 0a 20 20 20 20 20 20 20 20 69 66 28 20   0;.        if( 
4990: 7a 5b 69 2b 32 5d 3d 3d 27 2e 27 20 26 26 20 28  z[i+2]=='.' && (
49a0: 7a 5b 69 2b 33 5d 3d 3d 27 2f 27 20 7c 7c 20 7a  z[i+3]=='/' || z
49b0: 5b 69 2b 33 5d 3d 3d 30 29 20 29 20 72 65 74 75  [i+3]==0) ) retu
49c0: 72 6e 20 30 3b 0a 20 20 20 20 20 20 7d 0a 20 20  rn 0;.      }.  
49d0: 20 20 7d 0a 20 20 7d 0a 20 20 69 66 28 20 7a 5b    }.  }.  if( z[
49e0: 69 2d 31 5d 3d 3d 27 2f 27 20 29 20 72 65 74 75  i-1]=='/' ) retu
49f0: 72 6e 20 30 3b 0a 20 20 72 65 74 75 72 6e 20 31  rn 0;.  return 1
4a00: 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 49 66 20 74 68  ;.}../*.** If th
4a10: 65 20 6c 61 73 74 20 63 6f 6d 70 6f 6e 65 6e 74  e last component
4a20: 20 6f 66 20 74 68 65 20 70 61 74 68 6e 61 6d 65   of the pathname
4a30: 20 69 6e 20 7a 5b 30 5d 2e 2e 7a 5b 6a 2d 31 5d   in z[0]..z[j-1]
4a40: 20 69 73 20 73 6f 6d 65 74 68 69 6e 67 0a 2a 2a   is something.**
4a50: 20 6f 74 68 65 72 20 74 68 61 6e 20 22 2e 2e 22   other than ".."
4a60: 20 74 68 65 6e 20 62 61 63 6b 20 69 74 20 6f 75   then back it ou
4a70: 74 20 61 6e 64 20 72 65 74 75 72 6e 20 74 72 75  t and return tru
4a80: 65 2e 20 20 49 66 20 74 68 65 20 6c 61 73 74 0a  e.  If the last.
4a90: 2a 2a 20 63 6f 6d 70 6f 6e 65 6e 74 20 69 73 20  ** component is 
4aa0: 65 6d 70 74 79 20 6f 72 20 69 66 20 69 74 20 69  empty or if it i
4ab0: 73 20 22 2e 2e 22 20 74 68 65 6e 20 72 65 74 75  s ".." then retu
4ac0: 72 6e 20 66 61 6c 73 65 2e 0a 2a 2f 0a 73 74 61  rn false..*/.sta
4ad0: 74 69 63 20 69 6e 74 20 62 61 63 6b 75 70 5f 64  tic int backup_d
4ae0: 69 72 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  ir(const char *z
4af0: 2c 20 69 6e 74 20 2a 70 4a 29 7b 0a 20 20 69 6e  , int *pJ){.  in
4b00: 74 20 6a 20 3d 20 2a 70 4a 3b 0a 20 20 69 6e 74  t j = *pJ;.  int
4b10: 20 69 3b 0a 20 20 69 66 28 20 6a 3c 3d 30 20 29   i;.  if( j<=0 )
4b20: 20 72 65 74 75 72 6e 20 30 3b 0a 20 20 66 6f 72   return 0;.  for
4b30: 28 69 3d 6a 2d 31 3b 20 69 3e 30 20 26 26 20 7a  (i=j-1; i>0 && z
4b40: 5b 69 2d 31 5d 21 3d 27 2f 27 3b 20 69 2d 2d 29  [i-1]!='/'; i--)
4b50: 7b 7d 0a 20 20 69 66 28 20 7a 5b 69 5d 3d 3d 27  {}.  if( z[i]=='
4b60: 2e 27 20 26 26 20 69 3d 3d 6a 2d 32 20 26 26 20  .' && i==j-2 && 
4b70: 7a 5b 69 2b 31 5d 3d 3d 27 2e 27 20 29 20 72 65  z[i+1]=='.' ) re
4b80: 74 75 72 6e 20 30 3b 0a 20 20 2a 70 4a 20 3d 20  turn 0;.  *pJ = 
4b90: 69 2d 31 3b 0a 20 20 72 65 74 75 72 6e 20 31 3b  i-1;.  return 1;
4ba0: 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 53 69 6d 70 6c 69  .}../*.** Simpli
4bb0: 66 79 20 61 20 66 69 6c 65 6e 61 6d 65 20 62 79  fy a filename by
4bc0: 0a 2a 2a 0a 2a 2a 20 20 2a 20 52 65 6d 6f 76 65  .**.**  * Remove
4bd0: 20 65 78 74 65 6e 64 65 64 20 70 61 74 68 20 70   extended path p
4be0: 72 65 66 69 78 20 6f 6e 20 77 69 6e 64 6f 77 73  refix on windows
4bf0: 20 61 6e 64 20 63 79 67 77 69 6e 0a 2a 2a 20 20   and cygwin.**  
4c00: 2a 20 43 6f 6e 76 65 72 74 20 61 6c 6c 20 5c 20  * Convert all \ 
4c10: 69 6e 74 6f 20 2f 20 6f 6e 20 77 69 6e 64 6f 77  into / on window
4c20: 73 20 61 6e 64 20 63 79 67 77 69 6e 0a 2a 2a 20  s and cygwin.** 
4c30: 20 2a 20 72 65 6d 6f 76 69 6e 67 20 61 6e 79 20   * removing any 
4c40: 74 72 61 69 6c 69 6e 67 20 61 6e 64 20 64 75 70  trailing and dup
4c50: 6c 69 63 61 74 65 20 2f 0a 2a 2a 20 20 2a 20 72  licate /.**  * r
4c60: 65 6d 6f 76 69 6e 67 20 2f 2e 2f 0a 2a 2a 20 20  emoving /./.**  
4c70: 2a 20 72 65 6d 6f 76 69 6e 67 20 2f 41 2f 2e 2e  * removing /A/..
4c80: 2f 0a 2a 2a 0a 2a 2a 20 43 68 61 6e 67 65 73 20  /.**.** Changes 
4c90: 61 72 65 20 6d 61 64 65 20 69 6e 2d 70 6c 61 63  are made in-plac
4ca0: 65 2e 20 20 52 65 74 75 72 6e 20 74 68 65 20 6e  e.  Return the n
4cb0: 65 77 20 6e 61 6d 65 20 6c 65 6e 67 74 68 2e 0a  ew name length..
4cc0: 2a 2a 20 49 66 20 74 68 65 20 73 6c 61 73 68 20  ** If the slash 
4cd0: 70 61 72 61 6d 65 74 65 72 20 69 73 20 6e 6f 6e  parameter is non
4ce0: 2d 7a 65 72 6f 2c 20 74 68 65 20 74 72 61 69 6c  -zero, the trail
4cf0: 69 6e 67 20 73 6c 61 73 68 2c 20 69 66 20 61 6e  ing slash, if an
4d00: 79 2c 0a 2a 2a 20 69 73 20 72 65 74 61 69 6e 65  y,.** is retaine
4d10: 64 2e 0a 2a 2f 0a 69 6e 74 20 66 69 6c 65 5f 73  d..*/.int file_s
4d20: 69 6d 70 6c 69 66 79 5f 6e 61 6d 65 28 63 68 61  implify_name(cha
4d30: 72 20 2a 7a 2c 20 69 6e 74 20 6e 2c 20 69 6e 74  r *z, int n, int
4d40: 20 73 6c 61 73 68 29 7b 0a 20 20 69 6e 74 20 69   slash){.  int i
4d50: 20 3d 20 31 2c 20 6a 3b 0a 20 20 69 66 28 20 6e   = 1, j;.  if( n
4d60: 3c 30 20 29 20 6e 20 3d 20 73 74 72 6c 65 6e 28  <0 ) n = strlen(
4d70: 7a 29 3b 0a 0a 20 20 2f 2a 20 4f 6e 20 77 69 6e  z);..  /* On win
4d80: 64 6f 77 73 20 61 6e 64 20 63 79 67 77 69 6e 20  dows and cygwin 
4d90: 63 6f 6e 76 65 72 74 20 61 6c 6c 20 5c 20 63 68  convert all \ ch
4da0: 61 72 61 63 74 65 72 73 20 74 6f 20 2f 0a 20 20  aracters to /.  
4db0: 20 2a 20 61 6e 64 20 72 65 6d 6f 76 65 20 65 78   * and remove ex
4dc0: 74 65 6e 64 65 64 20 70 61 74 68 20 70 72 65 66  tended path pref
4dd0: 69 78 20 69 66 20 70 72 65 73 65 6e 74 20 2a 2f  ix if present */
4de0: 0a 23 69 66 20 64 65 66 69 6e 65 64 28 5f 57 49  .#if defined(_WI
4df0: 4e 33 32 29 20 7c 7c 20 64 65 66 69 6e 65 64 28  N32) || defined(
4e00: 5f 5f 43 59 47 57 49 4e 5f 5f 29 0a 20 20 66 6f  __CYGWIN__).  fo
4e10: 72 28 6a 3d 30 3b 20 6a 3c 6e 3b 20 6a 2b 2b 29  r(j=0; j<n; j++)
4e20: 7b 0a 20 20 20 20 69 66 28 20 7a 5b 6a 5d 3d 3d  {.    if( z[j]==
4e30: 27 5c 5c 27 20 29 20 7a 5b 6a 5d 20 3d 20 27 2f  '\\' ) z[j] = '/
4e40: 27 3b 0a 20 20 7d 0a 20 20 69 66 28 20 6e 3e 33  ';.  }.  if( n>3
4e50: 20 26 26 20 21 6d 65 6d 63 6d 70 28 7a 2c 20 22   && !memcmp(z, "
4e60: 2f 2f 3f 2f 22 2c 20 34 29 20 29 7b 0a 20 20 20  //?/", 4) ){.   
4e70: 20 69 66 28 20 66 6f 73 73 69 6c 5f 73 74 72 6e   if( fossil_strn
4e80: 69 63 6d 70 28 7a 2b 34 2c 22 55 4e 43 22 2c 20  icmp(z+4,"UNC", 
4e90: 33 29 20 29 7b 0a 20 20 20 20 20 20 69 20 2b 3d  3) ){.      i +=
4ea0: 20 34 3b 0a 20 20 20 20 20 20 7a 5b 30 5d 20 3d   4;.      z[0] =
4eb0: 20 7a 5b 34 5d 3b 0a 20 20 20 20 7d 65 6c 73 65   z[4];.    }else
4ec0: 7b 0a 20 20 20 20 20 20 69 20 2b 3d 20 36 3b 0a  {.      i += 6;.
4ed0: 20 20 20 20 20 20 7a 5b 30 5d 20 3d 20 27 2f 27        z[0] = '/'
4ee0: 3b 0a 20 20 20 20 7d 0a 20 20 7d 0a 23 65 6e 64  ;.    }.  }.#end
4ef0: 69 66 0a 0a 20 20 2f 2a 20 52 65 6d 6f 76 69 6e  if..  /* Removin
4f00: 67 20 74 72 61 69 6c 69 6e 67 20 22 2f 22 20 63  g trailing "/" c
4f10: 68 61 72 61 63 74 65 72 73 20 2a 2f 0a 20 20 69  haracters */.  i
4f20: 66 28 20 21 73 6c 61 73 68 20 29 7b 0a 20 20 20  f( !slash ){.   
4f30: 20 77 68 69 6c 65 28 20 6e 3e 31 20 26 26 20 7a   while( n>1 && z
4f40: 5b 6e 2d 31 5d 3d 3d 27 2f 27 20 29 7b 20 6e 2d  [n-1]=='/' ){ n-
4f50: 2d 3b 20 7d 0a 20 20 7d 0a 0a 20 20 2f 2a 20 52  -; }.  }..  /* R
4f60: 65 6d 6f 76 65 20 64 75 70 6c 69 63 61 74 65 20  emove duplicate 
4f70: 27 2f 27 20 63 68 61 72 61 63 74 65 72 73 2e 20  '/' characters. 
4f80: 20 45 78 63 65 70 74 2c 20 74 77 6f 20 2f 2f 20   Except, two // 
4f90: 61 74 20 74 68 65 20 62 65 67 69 6e 6e 69 6e 67  at the beginning
4fa0: 0a 20 20 2a 2a 20 6f 66 20 61 20 70 61 74 68 6e  .  ** of a pathn
4fb0: 61 6d 65 20 69 73 20 61 6c 6c 6f 77 65 64 20 73  ame is allowed s
4fc0: 69 6e 63 65 20 74 68 69 73 20 69 73 20 69 6d 70  ince this is imp
4fd0: 6f 72 74 61 6e 74 20 6f 6e 20 77 69 6e 64 6f 77  ortant on window
4fe0: 73 2e 20 2a 2f 0a 20 20 66 6f 72 28 6a 3d 31 3b  s. */.  for(j=1;
4ff0: 20 69 3c 6e 3b 20 69 2b 2b 29 7b 0a 20 20 20 20   i<n; i++){.    
5000: 7a 5b 6a 2b 2b 5d 20 3d 20 7a 5b 69 5d 3b 0a 20  z[j++] = z[i];. 
5010: 20 20 20 77 68 69 6c 65 28 20 7a 5b 69 5d 3d 3d     while( z[i]==
5020: 27 2f 27 20 26 26 20 69 3c 6e 2d 31 20 26 26 20  '/' && i<n-1 && 
5030: 7a 5b 69 2b 31 5d 3d 3d 27 2f 27 20 29 20 69 2b  z[i+1]=='/' ) i+
5040: 2b 3b 0a 20 20 7d 0a 20 20 6e 20 3d 20 6a 3b 0a  +;.  }.  n = j;.
5050: 0a 20 20 2f 2a 20 53 6b 69 70 20 6f 76 65 72 20  .  /* Skip over 
5060: 7a 65 72 6f 20 6f 72 20 6d 6f 72 65 20 69 6e 69  zero or more ini
5070: 74 69 61 6c 20 22 2e 2f 22 20 73 65 71 75 65 6e  tial "./" sequen
5080: 63 65 73 20 2a 2f 0a 20 20 66 6f 72 28 69 3d 30  ces */.  for(i=0
5090: 3b 20 69 3c 6e 2d 31 20 26 26 20 7a 5b 69 5d 3d  ; i<n-1 && z[i]=
50a0: 3d 27 2e 27 20 26 26 20 7a 5b 69 2b 31 5d 3d 3d  ='.' && z[i+1]==
50b0: 27 2f 27 3b 20 69 2b 3d 32 29 7b 7d 0a 0a 20 20  '/'; i+=2){}..  
50c0: 2f 2a 20 42 65 67 69 6e 20 63 6f 70 79 69 6e 67  /* Begin copying
50d0: 20 66 72 6f 6d 20 7a 5b 69 5d 20 62 61 63 6b 20   from z[i] back 
50e0: 74 6f 20 7a 5b 6a 5d 2e 2e 2e 20 2a 2f 0a 20 20  to z[j]... */.  
50f0: 66 6f 72 28 6a 3d 30 3b 20 69 3c 6e 3b 20 69 2b  for(j=0; i<n; i+
5100: 2b 29 7b 0a 20 20 20 20 69 66 28 20 7a 5b 69 5d  +){.    if( z[i]
5110: 3d 3d 27 2f 27 20 29 7b 0a 20 20 20 20 20 20 2f  =='/' ){.      /
5120: 2a 20 53 6b 69 70 20 6f 76 65 72 20 69 6e 74 65  * Skip over inte
5130: 72 6e 61 6c 20 22 2f 2e 22 20 64 69 72 65 63 74  rnal "/." direct
5140: 6f 72 79 20 63 6f 6d 70 6f 6e 65 6e 74 73 20 2a  ory components *
5150: 2f 0a 20 20 20 20 20 20 69 66 28 20 7a 5b 69 2b  /.      if( z[i+
5160: 31 5d 3d 3d 27 2e 27 20 26 26 20 28 69 2b 32 3d  1]=='.' && (i+2=
5170: 3d 6e 20 7c 7c 20 7a 5b 69 2b 32 5d 3d 3d 27 2f  =n || z[i+2]=='/
5180: 27 29 20 29 7b 0a 20 20 20 20 20 20 20 20 69 20  ') ){.        i 
5190: 2b 3d 20 31 3b 0a 20 20 20 20 20 20 20 20 63 6f  += 1;.        co
51a0: 6e 74 69 6e 75 65 3b 0a 20 20 20 20 20 20 7d 0a  ntinue;.      }.
51b0: 0a 20 20 20 20 20 20 2f 2a 20 49 66 20 74 68 69  .      /* If thi
51c0: 73 20 69 73 20 61 20 22 2f 2e 2e 22 20 64 69 72  s is a "/.." dir
51d0: 65 63 74 6f 72 79 20 63 6f 6d 70 6f 6e 65 6e 74  ectory component
51e0: 20 74 68 65 6e 20 62 61 63 6b 20 6f 75 74 20 74   then back out t
51f0: 68 65 0a 20 20 20 20 20 20 2a 2a 20 70 72 65 76  he.      ** prev
5200: 69 6f 75 73 20 74 65 72 6d 20 6f 66 20 74 68 65  ious term of the
5210: 20 64 69 72 65 63 74 6f 72 79 20 69 66 20 69 74   directory if it
5220: 20 69 73 20 73 6f 6d 65 74 68 69 6e 67 20 6f 74   is something ot
5230: 68 65 72 20 74 68 61 6e 20 22 2e 2e 22 0a 20 20  her than "..".  
5240: 20 20 20 20 2a 2a 20 6f 72 20 22 2e 22 0a 20 20      ** or ".".  
5250: 20 20 20 20 2a 2f 0a 20 20 20 20 20 20 69 66 28      */.      if(
5260: 20 7a 5b 69 2b 31 5d 3d 3d 27 2e 27 20 26 26 20   z[i+1]=='.' && 
5270: 69 2b 32 3c 6e 20 26 26 20 7a 5b 69 2b 32 5d 3d  i+2<n && z[i+2]=
5280: 3d 27 2e 27 20 26 26 20 28 69 2b 33 3d 3d 6e 20  ='.' && (i+3==n 
5290: 7c 7c 20 7a 5b 69 2b 33 5d 3d 3d 27 2f 27 29 0a  || z[i+3]=='/').
52a0: 20 20 20 20 20 20 20 26 26 20 62 61 63 6b 75 70         && backup
52b0: 5f 64 69 72 28 7a 2c 20 26 6a 29 0a 20 20 20 20  _dir(z, &j).    
52c0: 20 20 29 7b 0a 20 20 20 20 20 20 20 20 69 20 2b    ){.        i +
52d0: 3d 20 32 3b 0a 20 20 20 20 20 20 20 20 63 6f 6e  = 2;.        con
52e0: 74 69 6e 75 65 3b 0a 20 20 20 20 20 20 7d 0a 20  tinue;.      }. 
52f0: 20 20 20 7d 0a 20 20 20 20 69 66 28 20 6a 3e 3d     }.    if( j>=
5300: 30 20 29 20 7a 5b 6a 5d 20 3d 20 7a 5b 69 5d 3b  0 ) z[j] = z[i];
5310: 0a 20 20 20 20 6a 2b 2b 3b 0a 20 20 7d 0a 20 20  .    j++;.  }.  
5320: 69 66 28 20 6a 3d 3d 30 20 29 20 7a 5b 6a 2b 2b  if( j==0 ) z[j++
5330: 5d 20 3d 20 27 2f 27 3b 0a 20 20 7a 5b 6a 5d 20  ] = '/';.  z[j] 
5340: 3d 20 30 3b 0a 20 20 72 65 74 75 72 6e 20 6a 3b  = 0;.  return j;
5350: 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 43 4f 4d 4d 41 4e  .}../*.** COMMAN
5360: 44 3a 20 74 65 73 74 2d 73 69 6d 70 6c 69 66 79  D: test-simplify
5370: 2d 6e 61 6d 65 0a 2a 2a 0a 2a 2a 20 55 73 61 67  -name.**.** Usag
5380: 65 3a 20 25 66 6f 73 73 69 6c 20 74 65 73 74 2d  e: %fossil test-
5390: 73 69 6d 70 6c 69 66 79 2d 6e 61 6d 65 20 46 49  simplify-name FI
53a0: 4c 45 4e 41 4d 45 2e 2e 2e 0a 2a 2a 0a 2a 2a 20  LENAME....**.** 
53b0: 50 72 69 6e 74 20 74 68 65 20 73 69 6d 70 6c 69  Print the simpli
53c0: 66 69 65 64 20 76 65 72 73 69 6f 6e 73 20 6f 66  fied versions of
53d0: 20 65 61 63 68 20 46 49 4c 45 4e 41 4d 45 2e 0a   each FILENAME..
53e0: 2a 2f 0a 76 6f 69 64 20 63 6d 64 5f 74 65 73 74  */.void cmd_test
53f0: 5f 73 69 6d 70 6c 69 66 79 5f 6e 61 6d 65 28 76  _simplify_name(v
5400: 6f 69 64 29 7b 0a 20 20 69 6e 74 20 69 3b 0a 20  oid){.  int i;. 
5410: 20 63 68 61 72 20 2a 7a 3b 0a 20 20 66 6f 72 28   char *z;.  for(
5420: 69 3d 32 3b 20 69 3c 67 2e 61 72 67 63 3b 20 69  i=2; i<g.argc; i
5430: 2b 2b 29 7b 0a 20 20 20 20 7a 20 3d 20 6d 70 72  ++){.    z = mpr
5440: 69 6e 74 66 28 22 25 73 22 2c 20 67 2e 61 72 67  intf("%s", g.arg
5450: 76 5b 69 5d 29 3b 0a 20 20 20 20 66 6f 73 73 69  v[i]);.    fossi
5460: 6c 5f 70 72 69 6e 74 28 22 5b 25 73 5d 20 2d 3e  l_print("[%s] ->
5470: 20 22 2c 20 7a 29 3b 0a 20 20 20 20 66 69 6c 65   ", z);.    file
5480: 5f 73 69 6d 70 6c 69 66 79 5f 6e 61 6d 65 28 7a  _simplify_name(z
5490: 2c 20 2d 31 2c 20 30 29 3b 0a 20 20 20 20 66 6f  , -1, 0);.    fo
54a0: 73 73 69 6c 5f 70 72 69 6e 74 28 22 5b 25 73 5d  ssil_print("[%s]
54b0: 5c 6e 22 2c 20 7a 29 3b 0a 20 20 20 20 66 6f 73  \n", z);.    fos
54c0: 73 69 6c 5f 66 72 65 65 28 7a 29 3b 0a 20 20 7d  sil_free(z);.  }
54d0: 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 47 65 74 20 74 68  .}../*.** Get th
54e0: 65 20 63 75 72 72 65 6e 74 20 77 6f 72 6b 69 6e  e current workin
54f0: 67 20 64 69 72 65 63 74 6f 72 79 2e 0a 2a 2a 0a  g directory..**.
5500: 2a 2a 20 4f 6e 20 77 69 6e 64 6f 77 73 2c 20 74  ** On windows, t
5510: 68 65 20 6e 61 6d 65 20 69 73 20 63 6f 6e 76 65  he name is conve
5520: 72 74 65 64 20 66 72 6f 6d 20 75 6e 69 63 6f 64  rted from unicod
5530: 65 20 74 6f 20 55 54 46 38 20 61 6e 64 20 61 6c  e to UTF8 and al
5540: 6c 20 27 5c 5c 27 0a 2a 2a 20 63 68 61 72 61 63  l '\\'.** charac
5550: 74 65 72 73 20 61 72 65 20 63 6f 6e 76 65 72 74  ters are convert
5560: 65 64 20 74 6f 20 27 2f 27 2e 20 20 4e 6f 20 63  ed to '/'.  No c
5570: 6f 6e 76 65 72 73 69 6f 6e 73 20 61 72 65 20 6e  onversions are n
5580: 65 65 64 65 64 20 6f 6e 0a 2a 2a 20 75 6e 69 78  eeded on.** unix
5590: 2e 0a 2a 2f 0a 76 6f 69 64 20 66 69 6c 65 5f 67  ..*/.void file_g
55a0: 65 74 63 77 64 28 63 68 61 72 20 2a 7a 42 75 66  etcwd(char *zBuf
55b0: 2c 20 69 6e 74 20 6e 42 75 66 29 7b 0a 23 69 66  , int nBuf){.#if
55c0: 64 65 66 20 5f 57 49 4e 33 32 0a 20 20 77 69 6e  def _WIN32.  win
55d0: 33 32 5f 67 65 74 63 77 64 28 7a 42 75 66 2c 20  32_getcwd(zBuf, 
55e0: 6e 42 75 66 29 3b 0a 23 65 6c 73 65 0a 20 20 69  nBuf);.#else.  i
55f0: 66 28 20 67 65 74 63 77 64 28 7a 42 75 66 2c 20  f( getcwd(zBuf, 
5600: 6e 42 75 66 2d 31 29 3d 3d 30 20 29 7b 0a 20 20  nBuf-1)==0 ){.  
5610: 20 20 69 66 28 20 65 72 72 6e 6f 3d 3d 45 52 41    if( errno==ERA
5620: 4e 47 45 20 29 7b 0a 20 20 20 20 20 20 66 6f 73  NGE ){.      fos
5630: 73 69 6c 5f 66 61 74 61 6c 28 22 70 77 64 20 74  sil_fatal("pwd t
5640: 6f 6f 20 62 69 67 3a 20 6d 61 78 20 25 64 5c 6e  oo big: max %d\n
5650: 22 2c 20 6e 42 75 66 2d 31 29 3b 0a 20 20 20 20  ", nBuf-1);.    
5660: 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 66 6f 73  }else{.      fos
5670: 73 69 6c 5f 66 61 74 61 6c 28 22 63 61 6e 6e 6f  sil_fatal("canno
5680: 74 20 66 69 6e 64 20 63 75 72 72 65 6e 74 20 77  t find current w
5690: 6f 72 6b 69 6e 67 20 64 69 72 65 63 74 6f 72 79  orking directory
56a0: 3b 20 25 73 22 2c 0a 20 20 20 20 20 20 20 20 20  ; %s",.         
56b0: 20 20 20 20 20 20 20 20 20 20 73 74 72 65 72 72            strerr
56c0: 6f 72 28 65 72 72 6e 6f 29 29 3b 0a 20 20 20 20  or(errno));.    
56d0: 7d 0a 20 20 7d 0a 23 65 6e 64 69 66 0a 7d 0a 0a  }.  }.#endif.}..
56e0: 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 74 72 75  /*.** Return tru
56f0: 65 20 69 66 20 7a 50 61 74 68 20 69 73 20 61 6e  e if zPath is an
5700: 20 61 62 73 6f 6c 75 74 65 20 70 61 74 68 6e 61   absolute pathna
5710: 6d 65 2e 20 20 52 65 74 75 72 6e 20 66 61 6c 73  me.  Return fals
5720: 65 0a 2a 2a 20 69 66 20 69 74 20 69 73 20 72 65  e.** if it is re
5730: 6c 61 74 69 76 65 2e 0a 2a 2f 0a 69 6e 74 20 66  lative..*/.int f
5740: 69 6c 65 5f 69 73 5f 61 62 73 6f 6c 75 74 65 5f  ile_is_absolute_
5750: 70 61 74 68 28 63 6f 6e 73 74 20 63 68 61 72 20  path(const char 
5760: 2a 7a 50 61 74 68 29 7b 0a 20 20 69 66 28 20 66  *zPath){.  if( f
5770: 6f 73 73 69 6c 5f 69 73 64 69 72 73 65 70 28 7a  ossil_isdirsep(z
5780: 50 61 74 68 5b 30 5d 29 0a 23 69 66 20 64 65 66  Path[0]).#if def
5790: 69 6e 65 64 28 5f 57 49 4e 33 32 29 20 7c 7c 20  ined(_WIN32) || 
57a0: 64 65 66 69 6e 65 64 28 5f 5f 43 59 47 57 49 4e  defined(__CYGWIN
57b0: 5f 5f 29 0a 20 20 20 20 20 20 7c 7c 20 28 66 6f  __).      || (fo
57c0: 73 73 69 6c 5f 69 73 61 6c 70 68 61 28 7a 50 61  ssil_isalpha(zPa
57d0: 74 68 5b 30 5d 29 20 26 26 20 7a 50 61 74 68 5b  th[0]) && zPath[
57e0: 31 5d 3d 3d 27 3a 27 0a 20 20 20 20 20 20 20 20  1]==':'.        
57f0: 20 20 20 26 26 20 28 66 6f 73 73 69 6c 5f 69 73     && (fossil_is
5800: 64 69 72 73 65 70 28 7a 50 61 74 68 5b 32 5d 29  dirsep(zPath[2])
5810: 20 7c 7c 20 7a 50 61 74 68 5b 32 5d 3d 3d 27 5c   || zPath[2]=='\
5820: 30 27 29 29 0a 23 65 6e 64 69 66 0a 20 20 29 7b  0')).#endif.  ){
5830: 0a 20 20 20 20 72 65 74 75 72 6e 20 31 3b 0a 20  .    return 1;. 
5840: 20 7d 65 6c 73 65 7b 0a 20 20 20 20 72 65 74 75   }else{.    retu
5850: 72 6e 20 30 3b 0a 20 20 7d 0a 7d 0a 0a 2f 2a 0a  rn 0;.  }.}../*.
5860: 2a 2a 20 43 6f 6d 70 75 74 65 20 61 20 63 61 6e  ** Compute a can
5870: 6f 6e 69 63 61 6c 20 70 61 74 68 6e 61 6d 65 20  onical pathname 
5880: 66 6f 72 20 61 20 66 69 6c 65 20 6f 72 20 64 69  for a file or di
5890: 72 65 63 74 6f 72 79 2e 0a 2a 2a 20 4d 61 6b 65  rectory..** Make
58a0: 20 74 68 65 20 6e 61 6d 65 20 61 62 73 6f 6c 75   the name absolu
58b0: 74 65 20 69 66 20 69 74 20 69 73 20 72 65 6c 61  te if it is rela
58c0: 74 69 76 65 2e 0a 2a 2a 20 52 65 6d 6f 76 65 20  tive..** Remove 
58d0: 72 65 64 75 6e 64 61 6e 74 20 2f 20 63 68 61 72  redundant / char
58e0: 61 63 74 65 72 73 0a 2a 2a 20 52 65 6d 6f 76 65  acters.** Remove
58f0: 20 61 6c 6c 20 2f 2e 2f 20 70 61 74 68 20 65 6c   all /./ path el
5900: 65 6d 65 6e 74 73 2e 0a 2a 2a 20 43 6f 6e 76 65  ements..** Conve
5910: 72 74 20 2f 41 2f 2e 2e 2f 20 74 6f 20 6a 75 73  rt /A/../ to jus
5920: 74 20 2f 0a 2a 2a 20 49 66 20 74 68 65 20 73 6c  t /.** If the sl
5930: 61 73 68 20 70 61 72 61 6d 65 74 65 72 20 69 73  ash parameter is
5940: 20 6e 6f 6e 2d 7a 65 72 6f 2c 20 74 68 65 20 74   non-zero, the t
5950: 72 61 69 6c 69 6e 67 20 73 6c 61 73 68 2c 20 69  railing slash, i
5960: 66 20 61 6e 79 2c 0a 2a 2a 20 69 73 20 72 65 74  f any,.** is ret
5970: 61 69 6e 65 64 2e 0a 2a 2f 0a 76 6f 69 64 20 66  ained..*/.void f
5980: 69 6c 65 5f 63 61 6e 6f 6e 69 63 61 6c 5f 6e 61  ile_canonical_na
5990: 6d 65 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  me(const char *z
59a0: 4f 72 69 67 4e 61 6d 65 2c 20 42 6c 6f 62 20 2a  OrigName, Blob *
59b0: 70 4f 75 74 2c 20 69 6e 74 20 73 6c 61 73 68 29  pOut, int slash)
59c0: 7b 0a 20 20 62 6c 6f 62 5f 7a 65 72 6f 28 70 4f  {.  blob_zero(pO
59d0: 75 74 29 3b 0a 20 20 69 66 28 20 66 69 6c 65 5f  ut);.  if( file_
59e0: 69 73 5f 61 62 73 6f 6c 75 74 65 5f 70 61 74 68  is_absolute_path
59f0: 28 7a 4f 72 69 67 4e 61 6d 65 29 20 29 7b 0a 20  (zOrigName) ){. 
5a00: 20 20 20 62 6c 6f 62 5f 61 70 70 65 6e 64 66 28     blob_appendf(
5a10: 70 4f 75 74 2c 20 22 25 2f 22 2c 20 7a 4f 72 69  pOut, "%/", zOri
5a20: 67 4e 61 6d 65 29 3b 0a 20 20 7d 65 6c 73 65 7b  gName);.  }else{
5a30: 0a 20 20 20 20 63 68 61 72 20 7a 50 77 64 5b 32  .    char zPwd[2
5a40: 30 30 30 5d 3b 0a 20 20 20 20 66 69 6c 65 5f 67  000];.    file_g
5a50: 65 74 63 77 64 28 7a 50 77 64 2c 20 73 69 7a 65  etcwd(zPwd, size
5a60: 6f 66 28 7a 50 77 64 29 2d 73 74 72 6c 65 6e 28  of(zPwd)-strlen(
5a70: 7a 4f 72 69 67 4e 61 6d 65 29 29 3b 0a 20 20 20  zOrigName));.   
5a80: 20 69 66 28 20 7a 50 77 64 5b 30 5d 3d 3d 27 2f   if( zPwd[0]=='/
5a90: 27 20 26 26 20 73 74 72 6c 65 6e 28 7a 50 77 64  ' && strlen(zPwd
5aa0: 29 3d 3d 31 20 29 7b 0a 20 20 20 20 20 20 2f 2a  )==1 ){.      /*
5ab0: 20 77 68 65 6e 20 6f 6e 20 27 2f 27 2c 20 64 6f   when on '/', do
5ac0: 6e 27 74 20 61 64 64 20 61 6e 20 65 78 74 72 61  n't add an extra
5ad0: 20 27 2f 27 20 2a 2f 0a 20 20 20 20 20 20 69 66   '/' */.      if
5ae0: 28 20 7a 4f 72 69 67 4e 61 6d 65 5b 30 5d 3d 3d  ( zOrigName[0]==
5af0: 27 2e 27 20 26 26 20 73 74 72 6c 65 6e 28 7a 4f  '.' && strlen(zO
5b00: 72 69 67 4e 61 6d 65 29 3d 3d 31 20 29 7b 0a 20  rigName)==1 ){. 
5b10: 20 20 20 20 20 20 20 2f 2a 20 27 2e 27 20 77 68         /* '.' wh
5b20: 65 6e 20 6f 6e 20 27 2f 27 20 6d 65 61 6e 20 27  en on '/' mean '
5b30: 2f 27 20 2a 2f 0a 20 20 20 20 20 20 20 20 62 6c  /' */.        bl
5b40: 6f 62 5f 61 70 70 65 6e 64 66 28 70 4f 75 74 2c  ob_appendf(pOut,
5b50: 20 22 25 2f 22 2c 20 7a 50 77 64 29 3b 0a 20 20   "%/", zPwd);.  
5b60: 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20      }else{.     
5b70: 20 20 20 62 6c 6f 62 5f 61 70 70 65 6e 64 66 28     blob_appendf(
5b80: 70 4f 75 74 2c 20 22 25 2f 25 2f 22 2c 20 7a 50  pOut, "%/%/", zP
5b90: 77 64 2c 20 7a 4f 72 69 67 4e 61 6d 65 29 3b 0a  wd, zOrigName);.
5ba0: 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 65 6c 73        }.    }els
5bb0: 65 7b 0a 20 20 20 20 20 20 62 6c 6f 62 5f 61 70  e{.      blob_ap
5bc0: 70 65 6e 64 66 28 70 4f 75 74 2c 20 22 25 2f 2f  pendf(pOut, "%//
5bd0: 25 2f 22 2c 20 7a 50 77 64 2c 20 7a 4f 72 69 67  %/", zPwd, zOrig
5be0: 4e 61 6d 65 29 3b 0a 20 20 20 20 7d 0a 20 20 7d  Name);.    }.  }
5bf0: 0a 23 69 66 20 64 65 66 69 6e 65 64 28 5f 57 49  .#if defined(_WI
5c00: 4e 33 32 29 20 7c 7c 20 64 65 66 69 6e 65 64 28  N32) || defined(
5c10: 5f 5f 43 59 47 57 49 4e 5f 5f 29 0a 20 20 7b 0a  __CYGWIN__).  {.
5c20: 20 20 20 20 63 68 61 72 20 2a 7a 4f 75 74 3b 0a      char *zOut;.
5c30: 20 20 20 20 2f 2a 0a 20 20 20 20 2a 2a 20 4f 6e      /*.    ** On
5c40: 20 57 69 6e 64 6f 77 73 2f 63 79 67 77 69 6e 2c   Windows/cygwin,
5c50: 20 6e 6f 72 6d 61 6c 69 7a 65 20 74 68 65 20 64   normalize the d
5c60: 72 69 76 65 20 6c 65 74 74 65 72 20 74 6f 20 75  rive letter to u
5c70: 70 70 65 72 20 63 61 73 65 2e 0a 20 20 20 20 2a  pper case..    *
5c80: 2f 0a 20 20 20 20 7a 4f 75 74 20 3d 20 62 6c 6f  /.    zOut = blo
5c90: 62 5f 73 74 72 28 70 4f 75 74 29 3b 0a 20 20 20  b_str(pOut);.   
5ca0: 20 69 66 28 20 66 6f 73 73 69 6c 5f 69 73 6c 6f   if( fossil_islo
5cb0: 77 65 72 28 7a 4f 75 74 5b 30 5d 29 20 26 26 20  wer(zOut[0]) && 
5cc0: 7a 4f 75 74 5b 31 5d 3d 3d 27 3a 27 20 26 26 20  zOut[1]==':' && 
5cd0: 7a 4f 75 74 5b 32 5d 3d 3d 27 2f 27 20 29 7b 0a  zOut[2]=='/' ){.
5ce0: 20 20 20 20 20 20 7a 4f 75 74 5b 30 5d 20 3d 20        zOut[0] = 
5cf0: 66 6f 73 73 69 6c 5f 74 6f 75 70 70 65 72 28 7a  fossil_toupper(z
5d00: 4f 75 74 5b 30 5d 29 3b 0a 20 20 20 20 7d 0a 20  Out[0]);.    }. 
5d10: 20 7d 0a 23 65 6e 64 69 66 0a 20 20 62 6c 6f 62   }.#endif.  blob
5d20: 5f 72 65 73 69 7a 65 28 70 4f 75 74 2c 20 66 69  _resize(pOut, fi
5d30: 6c 65 5f 73 69 6d 70 6c 69 66 79 5f 6e 61 6d 65  le_simplify_name
5d40: 28 62 6c 6f 62 5f 62 75 66 66 65 72 28 70 4f 75  (blob_buffer(pOu
5d50: 74 29 2c 0a 20 20 20 20 20 20 20 20 20 20 20 20  t),.            
5d60: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
5d70: 20 20 20 20 20 20 20 20 20 20 20 62 6c 6f 62 5f             blob_
5d80: 73 69 7a 65 28 70 4f 75 74 29 2c 20 73 6c 61 73  size(pOut), slas
5d90: 68 29 29 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 43 4f  h));.}../*.** CO
5da0: 4d 4d 41 4e 44 3a 20 74 65 73 74 2d 63 61 6e 6f  MMAND: test-cano
5db0: 6e 69 63 61 6c 2d 6e 61 6d 65 0a 2a 2a 20 0a 2a  nical-name.** .*
5dc0: 2a 20 55 73 61 67 65 3a 20 25 66 6f 73 73 69 6c  * Usage: %fossil
5dd0: 20 74 65 73 74 2d 63 61 6e 6f 6e 69 63 61 6c 2d   test-canonical-
5de0: 6e 61 6d 65 20 46 49 4c 45 4e 41 4d 45 2e 2e 2e  name FILENAME...
5df0: 0a 2a 2a 0a 2a 2a 20 54 65 73 74 20 74 68 65 20  .**.** Test the 
5e00: 6f 70 65 72 61 74 69 6f 6e 20 6f 66 20 74 68 65  operation of the
5e10: 20 63 61 6e 6f 6e 69 63 61 6c 20 6e 61 6d 65 20   canonical name 
5e20: 67 65 6e 65 72 61 74 6f 72 2e 0a 2a 2a 20 41 6c  generator..** Al
5e30: 73 6f 20 74 65 73 74 20 46 6f 73 73 69 6c 27 73  so test Fossil's
5e40: 20 61 62 69 6c 69 74 79 20 74 6f 20 6d 65 61 73   ability to meas
5e50: 75 72 65 20 61 74 74 72 69 62 75 74 65 73 20 6f  ure attributes o
5e60: 66 20 61 20 66 69 6c 65 2e 0a 2a 2f 0a 76 6f 69  f a file..*/.voi
5e70: 64 20 63 6d 64 5f 74 65 73 74 5f 63 61 6e 6f 6e  d cmd_test_canon
5e80: 69 63 61 6c 5f 6e 61 6d 65 28 76 6f 69 64 29 7b  ical_name(void){
5e90: 0a 20 20 69 6e 74 20 69 3b 0a 20 20 42 6c 6f 62  .  int i;.  Blob
5ea0: 20 78 3b 0a 20 20 69 6e 74 20 73 6c 61 73 68 46   x;.  int slashF
5eb0: 6c 61 67 20 3d 20 66 69 6e 64 5f 6f 70 74 69 6f  lag = find_optio
5ec0: 6e 28 22 73 6c 61 73 68 22 2c 30 2c 30 29 21 3d  n("slash",0,0)!=
5ed0: 30 3b 0a 20 20 62 6c 6f 62 5f 7a 65 72 6f 28 26  0;.  blob_zero(&
5ee0: 78 29 3b 0a 20 20 66 6f 72 28 69 3d 32 3b 20 69  x);.  for(i=2; i
5ef0: 3c 67 2e 61 72 67 63 3b 20 69 2b 2b 29 7b 0a 20  <g.argc; i++){. 
5f00: 20 20 20 63 68 61 72 20 7a 42 75 66 5b 31 30 30     char zBuf[100
5f10: 5d 3b 0a 20 20 20 20 63 6f 6e 73 74 20 63 68 61  ];.    const cha
5f20: 72 20 2a 7a 4e 61 6d 65 20 3d 20 67 2e 61 72 67  r *zName = g.arg
5f30: 76 5b 69 5d 3b 0a 20 20 20 20 66 69 6c 65 5f 63  v[i];.    file_c
5f40: 61 6e 6f 6e 69 63 61 6c 5f 6e 61 6d 65 28 7a 4e  anonical_name(zN
5f50: 61 6d 65 2c 20 26 78 2c 20 73 6c 61 73 68 46 6c  ame, &x, slashFl
5f60: 61 67 29 3b 0a 20 20 20 20 66 6f 73 73 69 6c 5f  ag);.    fossil_
5f70: 70 72 69 6e 74 28 22 5b 25 73 5d 20 2d 3e 20 5b  print("[%s] -> [
5f80: 25 73 5d 5c 6e 22 2c 20 7a 4e 61 6d 65 2c 20 62  %s]\n", zName, b
5f90: 6c 6f 62 5f 62 75 66 66 65 72 28 26 78 29 29 3b  lob_buffer(&x));
5fa0: 0a 20 20 20 20 62 6c 6f 62 5f 72 65 73 65 74 28  .    blob_reset(
5fb0: 26 78 29 3b 0a 20 20 20 20 73 71 6c 69 74 65 33  &x);.    sqlite3
5fc0: 5f 73 6e 70 72 69 6e 74 66 28 73 69 7a 65 6f 66  _snprintf(sizeof
5fd0: 28 7a 42 75 66 29 2c 20 7a 42 75 66 2c 20 22 25  (zBuf), zBuf, "%
5fe0: 6c 6c 64 22 2c 20 66 69 6c 65 5f 77 64 5f 73 69  lld", file_wd_si
5ff0: 7a 65 28 7a 4e 61 6d 65 29 29 3b 0a 20 20 20 20  ze(zName));.    
6000: 66 6f 73 73 69 6c 5f 70 72 69 6e 74 28 22 20 20  fossil_print("  
6010: 66 69 6c 65 5f 73 69 7a 65 20 20 20 3d 20 25 73  file_size   = %s
6020: 5c 6e 22 2c 20 7a 42 75 66 29 3b 0a 20 20 20 20  \n", zBuf);.    
6030: 73 71 6c 69 74 65 33 5f 73 6e 70 72 69 6e 74 66  sqlite3_snprintf
6040: 28 73 69 7a 65 6f 66 28 7a 42 75 66 29 2c 20 7a  (sizeof(zBuf), z
6050: 42 75 66 2c 20 22 25 6c 6c 64 22 2c 20 66 69 6c  Buf, "%lld", fil
6060: 65 5f 77 64 5f 6d 74 69 6d 65 28 7a 4e 61 6d 65  e_wd_mtime(zName
6070: 29 29 3b 0a 20 20 20 20 66 6f 73 73 69 6c 5f 70  ));.    fossil_p
6080: 72 69 6e 74 28 22 20 20 66 69 6c 65 5f 6d 74 69  rint("  file_mti
6090: 6d 65 20 20 3d 20 25 73 5c 6e 22 2c 20 7a 42 75  me  = %s\n", zBu
60a0: 66 29 3b 0a 20 20 20 20 66 6f 73 73 69 6c 5f 70  f);.    fossil_p
60b0: 72 69 6e 74 28 22 20 20 66 69 6c 65 5f 69 73 66  rint("  file_isf
60c0: 69 6c 65 20 3d 20 25 64 5c 6e 22 2c 20 66 69 6c  ile = %d\n", fil
60d0: 65 5f 77 64 5f 69 73 66 69 6c 65 28 7a 4e 61 6d  e_wd_isfile(zNam
60e0: 65 29 29 3b 0a 20 20 20 20 66 6f 73 73 69 6c 5f  e));.    fossil_
60f0: 70 72 69 6e 74 28 22 20 20 66 69 6c 65 5f 69 73  print("  file_is
6100: 66 69 6c 65 5f 6f 72 5f 6c 69 6e 6b 20 3d 20 25  file_or_link = %
6110: 64 5c 6e 22 2c 66 69 6c 65 5f 77 64 5f 69 73 66  d\n",file_wd_isf
6120: 69 6c 65 5f 6f 72 5f 6c 69 6e 6b 28 7a 4e 61 6d  ile_or_link(zNam
6130: 65 29 29 3b 0a 20 20 20 20 66 6f 73 73 69 6c 5f  e));.    fossil_
6140: 70 72 69 6e 74 28 22 20 20 66 69 6c 65 5f 69 73  print("  file_is
6150: 6c 69 6e 6b 20 3d 20 25 64 5c 6e 22 2c 20 66 69  link = %d\n", fi
6160: 6c 65 5f 77 64 5f 69 73 6c 69 6e 6b 28 7a 4e 61  le_wd_islink(zNa
6170: 6d 65 29 29 3b 0a 20 20 20 20 66 6f 73 73 69 6c  me));.    fossil
6180: 5f 70 72 69 6e 74 28 22 20 20 66 69 6c 65 5f 69  _print("  file_i
6190: 73 65 78 65 20 20 3d 20 25 64 5c 6e 22 2c 20 66  sexe  = %d\n", f
61a0: 69 6c 65 5f 77 64 5f 69 73 65 78 65 28 7a 4e 61  ile_wd_isexe(zNa
61b0: 6d 65 29 29 3b 0a 20 20 20 20 66 6f 73 73 69 6c  me));.    fossil
61c0: 5f 70 72 69 6e 74 28 22 20 20 66 69 6c 65 5f 69  _print("  file_i
61d0: 73 64 69 72 20 20 3d 20 25 64 5c 6e 22 2c 20 66  sdir  = %d\n", f
61e0: 69 6c 65 5f 77 64 5f 69 73 64 69 72 28 7a 4e 61  ile_wd_isdir(zNa
61f0: 6d 65 29 29 3b 0a 20 20 7d 0a 7d 0a 0a 2f 2a 0a  me));.  }.}../*.
6200: 2a 2a 20 52 65 74 75 72 6e 20 54 52 55 45 20 69  ** Return TRUE i
6210: 66 20 74 68 65 20 67 69 76 65 6e 20 66 69 6c 65  f the given file
6220: 6e 61 6d 65 20 69 73 20 63 61 6e 6f 6e 69 63 61  name is canonica
6230: 6c 2e 0a 2a 2a 0a 2a 2a 20 43 61 6e 6f 6e 69 63  l..**.** Canonic
6240: 61 6c 20 6e 61 6d 65 73 20 61 72 65 20 66 75 6c  al names are ful
6250: 6c 20 70 61 74 68 6e 61 6d 65 73 20 75 73 69 6e  l pathnames usin
6260: 67 20 22 2f 22 20 6e 6f 74 20 22 5c 22 20 61 6e  g "/" not "\" an
6270: 64 20 77 68 69 63 68 0a 2a 2a 20 63 6f 6e 74 61  d which.** conta
6280: 69 6e 20 6e 6f 20 22 2f 2e 2f 22 20 6f 72 20 22  in no "/./" or "
6290: 2f 2e 2e 2f 22 20 74 65 72 6d 73 2e 0a 2a 2f 0a  /../" terms..*/.
62a0: 69 6e 74 20 66 69 6c 65 5f 69 73 5f 63 61 6e 6f  int file_is_cano
62b0: 6e 69 63 61 6c 28 63 6f 6e 73 74 20 63 68 61 72  nical(const char
62c0: 20 2a 7a 29 7b 0a 20 20 69 6e 74 20 69 3b 0a 20   *z){.  int i;. 
62d0: 20 69 66 28 20 7a 5b 30 5d 21 3d 27 2f 27 0a 23   if( z[0]!='/'.#
62e0: 69 66 20 64 65 66 69 6e 65 64 28 5f 57 49 4e 33  if defined(_WIN3
62f0: 32 29 20 7c 7c 20 64 65 66 69 6e 65 64 28 5f 5f  2) || defined(__
6300: 43 59 47 57 49 4e 5f 5f 29 0a 20 20 20 20 26 26  CYGWIN__).    &&
6310: 20 28 21 66 6f 73 73 69 6c 5f 69 73 75 70 70 65   (!fossil_isuppe
6320: 72 28 7a 5b 30 5d 29 20 7c 7c 20 7a 5b 31 5d 21  r(z[0]) || z[1]!
6330: 3d 27 3a 27 20 7c 7c 20 7a 5b 32 5d 21 3d 27 2f  =':' || z[2]!='/
6340: 27 29 0a 23 65 6e 64 69 66 0a 20 20 29 20 72 65  ').#endif.  ) re
6350: 74 75 72 6e 20 30 3b 0a 0a 20 20 66 6f 72 28 69  turn 0;..  for(i
6360: 3d 30 3b 20 7a 5b 69 5d 3b 20 69 2b 2b 29 7b 0a  =0; z[i]; i++){.
6370: 20 20 20 20 69 66 28 20 7a 5b 69 5d 3d 3d 27 5c      if( z[i]=='\
6380: 5c 27 20 29 20 72 65 74 75 72 6e 20 30 3b 0a 20  \' ) return 0;. 
6390: 20 20 20 69 66 28 20 7a 5b 69 5d 3d 3d 27 2f 27     if( z[i]=='/'
63a0: 20 29 7b 0a 20 20 20 20 20 20 69 66 28 20 7a 5b   ){.      if( z[
63b0: 69 2b 31 5d 3d 3d 27 2e 27 20 29 7b 0a 20 20 20  i+1]=='.' ){.   
63c0: 20 20 20 20 20 69 66 28 20 7a 5b 69 2b 32 5d 3d       if( z[i+2]=
63d0: 3d 27 2f 27 20 7c 7c 20 7a 5b 69 2b 32 5d 3d 3d  ='/' || z[i+2]==
63e0: 30 20 29 20 72 65 74 75 72 6e 20 30 3b 0a 20 20  0 ) return 0;.  
63f0: 20 20 20 20 20 20 69 66 28 20 7a 5b 69 2b 32 5d        if( z[i+2]
6400: 3d 3d 27 2e 27 20 26 26 20 28 7a 5b 69 2b 33 5d  =='.' && (z[i+3]
6410: 3d 3d 27 2f 27 20 7c 7c 20 7a 5b 69 2b 33 5d 3d  =='/' || z[i+3]=
6420: 3d 30 29 20 29 20 72 65 74 75 72 6e 20 30 3b 0a  =0) ) return 0;.
6430: 20 20 20 20 20 20 7d 0a 20 20 20 20 7d 0a 20 20        }.    }.  
6440: 7d 0a 20 20 72 65 74 75 72 6e 20 31 3b 0a 7d 0a  }.  return 1;.}.
6450: 0a 2f 2a 0a 2a 2a 20 52 65 74 75 72 6e 20 61 20  ./*.** Return a 
6460: 70 6f 69 6e 74 65 72 20 74 6f 20 74 68 65 20 66  pointer to the f
6470: 69 72 73 74 20 63 68 61 72 61 63 74 65 72 20 69  irst character i
6480: 6e 20 61 20 70 61 74 68 6e 61 6d 65 20 70 61 73  n a pathname pas
6490: 74 20 74 68 65 0a 2a 2a 20 64 72 69 76 65 20 6c  t the.** drive l
64a0: 65 74 74 65 72 2e 20 20 54 68 69 73 20 72 6f 75  etter.  This rou
64b0: 74 69 6e 65 20 69 73 20 61 20 6e 6f 2d 6f 70 20  tine is a no-op 
64c0: 6f 6e 20 75 6e 69 78 2e 0a 2a 2f 0a 63 68 61 72  on unix..*/.char
64d0: 20 2a 66 69 6c 65 5f 77 69 74 68 6f 75 74 5f 64   *file_without_d
64e0: 72 69 76 65 5f 6c 65 74 74 65 72 28 63 68 61 72  rive_letter(char
64f0: 20 2a 7a 49 6e 29 7b 0a 23 69 66 64 65 66 20 5f   *zIn){.#ifdef _
6500: 57 49 4e 33 32 0a 20 20 69 66 28 20 66 6f 73 73  WIN32.  if( foss
6510: 69 6c 5f 69 73 61 6c 70 68 61 28 7a 49 6e 5b 30  il_isalpha(zIn[0
6520: 5d 29 20 26 26 20 7a 49 6e 5b 31 5d 3d 3d 27 3a  ]) && zIn[1]==':
6530: 27 20 29 20 7a 49 6e 20 2b 3d 20 32 3b 0a 23 65  ' ) zIn += 2;.#e
6540: 6e 64 69 66 0a 20 20 72 65 74 75 72 6e 20 7a 49  ndif.  return zI
6550: 6e 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 43 6f 6d 70  n;.}../*.** Comp
6560: 75 74 65 20 61 20 70 61 74 68 6e 61 6d 65 20 66  ute a pathname f
6570: 6f 72 20 61 20 66 69 6c 65 20 6f 72 20 64 69 72  or a file or dir
6580: 65 63 74 6f 72 79 20 74 68 61 74 20 69 73 20 72  ectory that is r
6590: 65 6c 61 74 69 76 65 0a 2a 2a 20 74 6f 20 74 68  elative.** to th
65a0: 65 20 63 75 72 72 65 6e 74 20 64 69 72 65 63 74  e current direct
65b0: 6f 72 79 2e 20 20 49 66 20 74 68 65 20 73 6c 61  ory.  If the sla
65c0: 73 68 20 70 61 72 61 6d 65 74 65 72 20 69 73 20  sh parameter is 
65d0: 6e 6f 6e 2d 7a 65 72 6f 2c 0a 2a 2a 20 74 68 65  non-zero,.** the
65e0: 20 74 72 61 69 6c 69 6e 67 20 73 6c 61 73 68 2c   trailing slash,
65f0: 20 69 66 20 61 6e 79 2c 20 69 73 20 72 65 74 61   if any, is reta
6600: 69 6e 65 64 2e 0a 2a 2f 0a 76 6f 69 64 20 66 69  ined..*/.void fi
6610: 6c 65 5f 72 65 6c 61 74 69 76 65 5f 6e 61 6d 65  le_relative_name
6620: 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 4f 72  (const char *zOr
6630: 69 67 4e 61 6d 65 2c 20 42 6c 6f 62 20 2a 70 4f  igName, Blob *pO
6640: 75 74 2c 20 69 6e 74 20 73 6c 61 73 68 29 7b 0a  ut, int slash){.
6650: 20 20 63 68 61 72 20 2a 7a 50 61 74 68 3b 0a 20    char *zPath;. 
6660: 20 62 6c 6f 62 5f 73 65 74 28 70 4f 75 74 2c 20   blob_set(pOut, 
6670: 7a 4f 72 69 67 4e 61 6d 65 29 3b 0a 20 20 62 6c  zOrigName);.  bl
6680: 6f 62 5f 72 65 73 69 7a 65 28 70 4f 75 74 2c 20  ob_resize(pOut, 
6690: 66 69 6c 65 5f 73 69 6d 70 6c 69 66 79 5f 6e 61  file_simplify_na
66a0: 6d 65 28 62 6c 6f 62 5f 62 75 66 66 65 72 28 70  me(blob_buffer(p
66b0: 4f 75 74 29 2c 0a 20 20 20 20 20 20 20 20 20 20  Out),.          
66c0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
66d0: 20 20 20 20 20 20 20 20 20 20 20 20 20 62 6c 6f               blo
66e0: 62 5f 73 69 7a 65 28 70 4f 75 74 29 2c 20 73 6c  b_size(pOut), sl
66f0: 61 73 68 29 29 3b 0a 20 20 7a 50 61 74 68 20 3d  ash));.  zPath =
6700: 20 66 69 6c 65 5f 77 69 74 68 6f 75 74 5f 64 72   file_without_dr
6710: 69 76 65 5f 6c 65 74 74 65 72 28 62 6c 6f 62 5f  ive_letter(blob_
6720: 62 75 66 66 65 72 28 70 4f 75 74 29 29 3b 0a 20  buffer(pOut));. 
6730: 20 69 66 28 20 7a 50 61 74 68 5b 30 5d 3d 3d 27   if( zPath[0]=='
6740: 2f 27 20 29 7b 0a 20 20 20 20 69 6e 74 20 69 2c  /' ){.    int i,
6750: 20 6a 3b 0a 20 20 20 20 42 6c 6f 62 20 74 6d 70   j;.    Blob tmp
6760: 3b 0a 20 20 20 20 63 68 61 72 20 2a 7a 50 77 64  ;.    char *zPwd
6770: 3b 0a 20 20 20 20 63 68 61 72 20 7a 42 75 66 5b  ;.    char zBuf[
6780: 32 30 30 30 5d 3b 0a 20 20 20 20 7a 50 77 64 20  2000];.    zPwd 
6790: 3d 20 7a 42 75 66 3b 0a 20 20 20 20 66 69 6c 65  = zBuf;.    file
67a0: 5f 67 65 74 63 77 64 28 7a 42 75 66 2c 20 73 69  _getcwd(zBuf, si
67b0: 7a 65 6f 66 28 7a 42 75 66 29 2d 32 30 29 3b 0a  zeof(zBuf)-20);.
67c0: 20 20 20 20 7a 50 77 64 20 3d 20 66 69 6c 65 5f      zPwd = file_
67d0: 77 69 74 68 6f 75 74 5f 64 72 69 76 65 5f 6c 65  without_drive_le
67e0: 74 74 65 72 28 7a 42 75 66 29 3b 0a 20 20 20 20  tter(zBuf);.    
67f0: 69 20 3d 20 31 3b 0a 23 69 66 20 64 65 66 69 6e  i = 1;.#if defin
6800: 65 64 28 5f 57 49 4e 33 32 29 20 7c 7c 20 64 65  ed(_WIN32) || de
6810: 66 69 6e 65 64 28 5f 5f 43 59 47 57 49 4e 5f 5f  fined(__CYGWIN__
6820: 29 0a 20 20 20 20 77 68 69 6c 65 28 20 7a 50 61  ).    while( zPa
6830: 74 68 5b 69 5d 20 26 26 20 66 6f 73 73 69 6c 5f  th[i] && fossil_
6840: 74 6f 6c 6f 77 65 72 28 7a 50 77 64 5b 69 5d 29  tolower(zPwd[i])
6850: 3d 3d 66 6f 73 73 69 6c 5f 74 6f 6c 6f 77 65 72  ==fossil_tolower
6860: 28 7a 50 61 74 68 5b 69 5d 29 20 29 20 69 2b 2b  (zPath[i]) ) i++
6870: 3b 0a 23 65 6c 73 65 0a 20 20 20 20 77 68 69 6c  ;.#else.    whil
6880: 65 28 20 7a 50 61 74 68 5b 69 5d 20 26 26 20 7a  e( zPath[i] && z
6890: 50 77 64 5b 69 5d 3d 3d 7a 50 61 74 68 5b 69 5d  Pwd[i]==zPath[i]
68a0: 20 29 20 69 2b 2b 3b 0a 23 65 6e 64 69 66 0a 20   ) i++;.#endif. 
68b0: 20 20 20 69 66 28 20 7a 50 61 74 68 5b 69 5d 3d     if( zPath[i]=
68c0: 3d 30 20 29 7b 0a 20 20 20 20 20 20 6d 65 6d 63  =0 ){.      memc
68d0: 70 79 28 26 74 6d 70 2c 20 70 4f 75 74 2c 20 73  py(&tmp, pOut, s
68e0: 69 7a 65 6f 66 28 74 6d 70 29 29 3b 0a 20 20 20  izeof(tmp));.   
68f0: 20 20 20 69 66 28 20 7a 50 77 64 5b 69 5d 3d 3d     if( zPwd[i]==
6900: 30 20 29 7b 0a 20 20 20 20 20 20 20 20 62 6c 6f  0 ){.        blo
6910: 62 5f 73 65 74 28 70 4f 75 74 2c 20 22 2e 22 29  b_set(pOut, ".")
6920: 3b 0a 20 20 20 20 20 20 7d 65 6c 73 65 7b 0a 20  ;.      }else{. 
6930: 20 20 20 20 20 20 20 62 6c 6f 62 5f 73 65 74 28         blob_set(
6940: 70 4f 75 74 2c 20 22 2e 2e 22 29 3b 0a 20 20 20  pOut, "..");.   
6950: 20 20 20 20 20 66 6f 72 28 6a 3d 69 2b 31 3b 20       for(j=i+1; 
6960: 7a 50 77 64 5b 6a 5d 3b 20 6a 2b 2b 29 7b 0a 20  zPwd[j]; j++){. 
6970: 20 20 20 20 20 20 20 20 20 69 66 28 20 7a 50 77           if( zPw
6980: 64 5b 6a 5d 3d 3d 27 2f 27 20 29 7b 0a 20 20 20  d[j]=='/' ){.   
6990: 20 20 20 20 20 20 20 20 20 62 6c 6f 62 5f 61 70           blob_ap
69a0: 70 65 6e 64 28 70 4f 75 74 2c 20 22 2f 2e 2e 22  pend(pOut, "/.."
69b0: 2c 20 33 29 3b 0a 20 20 20 20 20 20 20 20 20 20  , 3);.          
69c0: 7d 0a 20 20 20 20 20 20 20 20 7d 0a 20 20 20 20  }.        }.    
69d0: 20 20 20 20 77 68 69 6c 65 28 20 69 3e 30 20 26      while( i>0 &
69e0: 26 20 28 7a 50 77 64 5b 69 5d 21 3d 27 2f 27 29  & (zPwd[i]!='/')
69f0: 29 20 2d 2d 69 3b 0a 20 20 20 20 20 20 20 20 62  ) --i;.        b
6a00: 6c 6f 62 5f 61 70 70 65 6e 64 28 70 4f 75 74 2c  lob_append(pOut,
6a10: 20 7a 50 61 74 68 2b 69 2c 20 6a 2d 69 29 3b 0a   zPath+i, j-i);.
6a20: 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 69 66        }.      if
6a30: 28 20 73 6c 61 73 68 20 26 26 20 69 3e 30 20 26  ( slash && i>0 &
6a40: 26 20 7a 50 61 74 68 5b 73 74 72 6c 65 6e 28 7a  & zPath[strlen(z
6a50: 50 61 74 68 29 2d 31 5d 3d 3d 27 2f 27 29 7b 0a  Path)-1]=='/'){.
6a60: 20 20 20 20 20 20 20 20 62 6c 6f 62 5f 61 70 70          blob_app
6a70: 65 6e 64 28 70 4f 75 74 2c 20 22 2f 22 2c 20 31  end(pOut, "/", 1
6a80: 29 3b 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 20  );.      }.     
6a90: 20 62 6c 6f 62 5f 72 65 73 65 74 28 26 74 6d 70   blob_reset(&tmp
6aa0: 29 3b 0a 20 20 20 20 20 20 72 65 74 75 72 6e 3b  );.      return;
6ab0: 0a 20 20 20 20 7d 0a 20 20 20 20 69 66 28 20 7a  .    }.    if( z
6ac0: 50 77 64 5b 69 5d 3d 3d 30 20 26 26 20 7a 50 61  Pwd[i]==0 && zPa
6ad0: 74 68 5b 69 5d 3d 3d 27 2f 27 20 29 7b 0a 20 20  th[i]=='/' ){.  
6ae0: 20 20 20 20 6d 65 6d 63 70 79 28 26 74 6d 70 2c      memcpy(&tmp,
6af0: 20 70 4f 75 74 2c 20 73 69 7a 65 6f 66 28 74 6d   pOut, sizeof(tm
6b00: 70 29 29 3b 0a 20 20 20 20 20 20 62 6c 6f 62 5f  p));.      blob_
6b10: 73 65 74 28 70 4f 75 74 2c 20 22 2e 2f 22 29 3b  set(pOut, "./");
6b20: 0a 20 20 20 20 20 20 62 6c 6f 62 5f 61 70 70 65  .      blob_appe
6b30: 6e 64 28 70 4f 75 74 2c 20 26 7a 50 61 74 68 5b  nd(pOut, &zPath[
6b40: 69 2b 31 5d 2c 20 2d 31 29 3b 0a 20 20 20 20 20  i+1], -1);.     
6b50: 20 62 6c 6f 62 5f 72 65 73 65 74 28 26 74 6d 70   blob_reset(&tmp
6b60: 29 3b 0a 20 20 20 20 20 20 72 65 74 75 72 6e 3b  );.      return;
6b70: 0a 20 20 20 20 7d 0a 20 20 20 20 77 68 69 6c 65  .    }.    while
6b80: 28 20 7a 50 61 74 68 5b 69 2d 31 5d 21 3d 27 2f  ( zPath[i-1]!='/
6b90: 27 20 29 7b 20 69 2d 2d 3b 20 7d 0a 20 20 20 20  ' ){ i--; }.    
6ba0: 69 66 28 20 7a 50 77 64 5b 30 5d 3d 3d 27 2f 27  if( zPwd[0]=='/'
6bb0: 20 26 26 20 73 74 72 6c 65 6e 28 7a 50 77 64 29   && strlen(zPwd)
6bc0: 3d 3d 31 20 29 7b 0a 20 20 20 20 20 20 2f 2a 20  ==1 ){.      /* 
6bd0: 49 66 20 6f 6e 20 27 2f 27 2c 20 64 6f 6e 27 74  If on '/', don't
6be0: 20 67 6f 20 74 6f 20 68 69 67 68 65 72 20 6c 65   go to higher le
6bf0: 76 65 6c 20 2a 2f 0a 20 20 20 20 20 20 62 6c 6f  vel */.      blo
6c00: 62 5f 7a 65 72 6f 28 26 74 6d 70 29 3b 0a 20 20  b_zero(&tmp);.  
6c10: 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 20 20 62    }else{.      b
6c20: 6c 6f 62 5f 73 65 74 28 26 74 6d 70 2c 20 22 2e  lob_set(&tmp, ".
6c30: 2e 2f 22 29 3b 0a 20 20 20 20 7d 0a 20 20 20 20  ./");.    }.    
6c40: 66 6f 72 28 6a 3d 69 3b 20 7a 50 77 64 5b 6a 5d  for(j=i; zPwd[j]
6c50: 3b 20 6a 2b 2b 29 7b 0a 20 20 20 20 20 20 69 66  ; j++){.      if
6c60: 28 20 7a 50 77 64 5b 6a 5d 3d 3d 27 2f 27 20 29  ( zPwd[j]=='/' )
6c70: 7b 0a 20 20 20 20 20 20 20 20 62 6c 6f 62 5f 61  {.        blob_a
6c80: 70 70 65 6e 64 28 26 74 6d 70 2c 20 22 2e 2e 2f  ppend(&tmp, "../
6c90: 22 2c 20 33 29 3b 0a 20 20 20 20 20 20 7d 0a 20  ", 3);.      }. 
6ca0: 20 20 20 7d 0a 20 20 20 20 62 6c 6f 62 5f 61 70     }.    blob_ap
6cb0: 70 65 6e 64 28 26 74 6d 70 2c 20 26 7a 50 61 74  pend(&tmp, &zPat
6cc0: 68 5b 69 5d 2c 20 2d 31 29 3b 0a 20 20 20 20 62  h[i], -1);.    b
6cd0: 6c 6f 62 5f 72 65 73 65 74 28 70 4f 75 74 29 3b  lob_reset(pOut);
6ce0: 0a 20 20 20 20 6d 65 6d 63 70 79 28 70 4f 75 74  .    memcpy(pOut
6cf0: 2c 20 26 74 6d 70 2c 20 73 69 7a 65 6f 66 28 74  , &tmp, sizeof(t
6d00: 6d 70 29 29 3b 0a 20 20 7d 0a 7d 0a 0a 2f 2a 0a  mp));.  }.}../*.
6d10: 2a 2a 20 43 4f 4d 4d 41 4e 44 3a 20 74 65 73 74  ** COMMAND: test
6d20: 2d 72 65 6c 61 74 69 76 65 2d 6e 61 6d 65 0a 2a  -relative-name.*
6d30: 2a 0a 2a 2a 20 54 65 73 74 20 74 68 65 20 6f 70  *.** Test the op
6d40: 65 72 61 74 69 6f 6e 20 6f 66 20 74 68 65 20 72  eration of the r
6d50: 65 6c 61 74 69 76 65 20 6e 61 6d 65 20 67 65 6e  elative name gen
6d60: 65 72 61 74 6f 72 2e 0a 2a 2f 0a 76 6f 69 64 20  erator..*/.void 
6d70: 63 6d 64 5f 74 65 73 74 5f 72 65 6c 61 74 69 76  cmd_test_relativ
6d80: 65 5f 6e 61 6d 65 28 76 6f 69 64 29 7b 0a 20 20  e_name(void){.  
6d90: 69 6e 74 20 69 3b 0a 20 20 42 6c 6f 62 20 78 3b  int i;.  Blob x;
6da0: 0a 20 20 69 6e 74 20 73 6c 61 73 68 46 6c 61 67  .  int slashFlag
6db0: 20 3d 20 66 69 6e 64 5f 6f 70 74 69 6f 6e 28 22   = find_option("
6dc0: 73 6c 61 73 68 22 2c 30 2c 30 29 21 3d 30 3b 0a  slash",0,0)!=0;.
6dd0: 20 20 62 6c 6f 62 5f 7a 65 72 6f 28 26 78 29 3b    blob_zero(&x);
6de0: 0a 20 20 66 6f 72 28 69 3d 32 3b 20 69 3c 67 2e  .  for(i=2; i<g.
6df0: 61 72 67 63 3b 20 69 2b 2b 29 7b 0a 20 20 20 20  argc; i++){.    
6e00: 66 69 6c 65 5f 72 65 6c 61 74 69 76 65 5f 6e 61  file_relative_na
6e10: 6d 65 28 67 2e 61 72 67 76 5b 69 5d 2c 20 26 78  me(g.argv[i], &x
6e20: 2c 20 73 6c 61 73 68 46 6c 61 67 29 3b 0a 20 20  , slashFlag);.  
6e30: 20 20 66 6f 73 73 69 6c 5f 70 72 69 6e 74 28 22    fossil_print("
6e40: 25 73 5c 6e 22 2c 20 62 6c 6f 62 5f 62 75 66 66  %s\n", blob_buff
6e50: 65 72 28 26 78 29 29 3b 0a 20 20 20 20 62 6c 6f  er(&x));.    blo
6e60: 62 5f 72 65 73 65 74 28 26 78 29 3b 0a 20 20 7d  b_reset(&x);.  }
6e70: 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 43 6f 6d 70 75 74  .}../*.** Comput
6e80: 65 20 61 20 66 75 6c 6c 20 70 61 74 68 20 6e 61  e a full path na
6e90: 6d 65 20 66 6f 72 20 61 20 66 69 6c 65 20 69 6e  me for a file in
6ea0: 20 74 68 65 20 6c 6f 63 61 6c 20 74 72 65 65 2e   the local tree.
6eb0: 20 20 49 66 0a 2a 2a 20 74 68 65 20 61 62 73 6f    If.** the abso
6ec0: 6c 75 74 65 20 66 6c 61 67 20 69 73 20 6e 6f 6e  lute flag is non
6ed0: 2d 7a 65 72 6f 2c 20 74 68 65 20 63 6f 6d 70 75  -zero, the compu
6ee0: 74 65 64 20 70 61 74 68 20 77 69 6c 6c 20 62 65  ted path will be
6ef0: 0a 2a 2a 20 61 62 73 6f 6c 75 74 65 2c 20 73 74  .** absolute, st
6f00: 61 72 74 69 6e 67 20 77 69 74 68 20 74 68 65 20  arting with the 
6f10: 72 6f 6f 74 20 70 61 74 68 20 6f 66 20 74 68 65  root path of the
6f20: 20 6c 6f 63 61 6c 20 74 72 65 65 3b 0a 2a 2a 20   local tree;.** 
6f30: 6f 74 68 65 72 77 69 73 65 2c 20 69 74 20 77 69  otherwise, it wi
6f40: 6c 6c 20 62 65 20 72 65 6c 61 74 69 76 65 20 74  ll be relative t
6f50: 6f 20 74 68 65 20 72 6f 6f 74 20 6f 66 20 74 68  o the root of th
6f60: 65 20 6c 6f 63 61 6c 0a 2a 2a 20 74 72 65 65 2e  e local.** tree.
6f70: 20 20 49 6e 20 62 6f 74 68 20 63 61 73 65 73 2c    In both cases,
6f80: 20 74 68 65 20 72 6f 6f 74 20 6f 66 20 74 68 65   the root of the
6f90: 20 6c 6f 63 61 6c 20 74 72 65 65 20 69 73 20 64   local tree is d
6fa0: 65 66 69 6e 65 64 0a 2a 2a 20 62 79 20 74 68 65  efined.** by the
6fb0: 20 67 2e 7a 4c 6f 63 61 6c 52 6f 6f 74 20 76 61   g.zLocalRoot va
6fc0: 72 69 61 62 6c 65 2e 20 20 52 65 74 75 72 6e 20  riable.  Return 
6fd0: 54 52 55 45 20 6f 6e 20 73 75 63 63 65 73 73 2e  TRUE on success.
6fe0: 20 20 4f 6e 0a 2a 2a 20 66 61 69 6c 75 72 65 2c    On.** failure,
6ff0: 20 70 72 69 6e 74 20 61 6e 64 20 65 72 72 6f 72   print and error
7000: 20 6d 65 73 73 61 67 65 20 61 6e 64 20 71 75 69   message and qui
7010: 74 20 69 66 20 74 68 65 20 65 72 72 46 61 74 61  t if the errFata
7020: 6c 0a 2a 2a 20 66 6c 61 67 20 69 73 20 74 72 75  l.** flag is tru
7030: 65 2e 20 20 49 66 20 65 72 72 46 61 74 61 6c 20  e.  If errFatal 
7040: 69 73 20 66 61 6c 73 65 2c 20 74 68 65 6e 20 73  is false, then s
7050: 69 6d 70 6c 79 20 72 65 74 75 72 6e 20 30 2e 0a  imply return 0..
7060: 2a 2f 0a 69 6e 74 20 66 69 6c 65 5f 74 72 65 65  */.int file_tree
7070: 5f 6e 61 6d 65 28 0a 20 20 63 6f 6e 73 74 20 63  _name(.  const c
7080: 68 61 72 20 2a 7a 4f 72 69 67 4e 61 6d 65 2c 0a  har *zOrigName,.
7090: 20 20 42 6c 6f 62 20 2a 70 4f 75 74 2c 0a 20 20    Blob *pOut,.  
70a0: 69 6e 74 20 61 62 73 6f 6c 75 74 65 2c 0a 20 20  int absolute,.  
70b0: 69 6e 74 20 65 72 72 46 61 74 61 6c 0a 29 7b 0a  int errFatal.){.
70c0: 20 20 42 6c 6f 62 20 6c 6f 63 61 6c 52 6f 6f 74    Blob localRoot
70d0: 3b 0a 20 20 69 6e 74 20 6e 4c 6f 63 61 6c 52 6f  ;.  int nLocalRo
70e0: 6f 74 3b 0a 20 20 63 68 61 72 20 2a 7a 4c 6f 63  ot;.  char *zLoc
70f0: 61 6c 52 6f 6f 74 3b 0a 20 20 42 6c 6f 62 20 66  alRoot;.  Blob f
7100: 75 6c 6c 3b 0a 20 20 69 6e 74 20 6e 46 75 6c 6c  ull;.  int nFull
7110: 3b 0a 20 20 63 68 61 72 20 2a 7a 46 75 6c 6c 3b  ;.  char *zFull;
7120: 0a 20 20 69 6e 74 20 28 2a 78 43 6d 70 29 28 63  .  int (*xCmp)(c
7130: 6f 6e 73 74 20 63 68 61 72 2a 2c 63 6f 6e 73 74  onst char*,const
7140: 20 63 68 61 72 2a 2c 69 6e 74 29 3b 0a 0a 20 20   char*,int);..  
7150: 62 6c 6f 62 5f 7a 65 72 6f 28 70 4f 75 74 29 3b  blob_zero(pOut);
7160: 0a 20 20 69 66 28 20 21 67 2e 6c 6f 63 61 6c 4f  .  if( !g.localO
7170: 70 65 6e 20 29 7b 0a 20 20 20 20 69 66 28 20 61  pen ){.    if( a
7180: 62 73 6f 6c 75 74 65 20 26 26 20 21 66 69 6c 65  bsolute && !file
7190: 5f 69 73 5f 61 62 73 6f 6c 75 74 65 5f 70 61 74  _is_absolute_pat
71a0: 68 28 7a 4f 72 69 67 4e 61 6d 65 29 20 29 7b 0a  h(zOrigName) ){.
71b0: 20 20 20 20 20 20 69 66 28 20 65 72 72 46 61 74        if( errFat
71c0: 61 6c 20 29 7b 0a 20 20 20 20 20 20 20 20 66 6f  al ){.        fo
71d0: 73 73 69 6c 5f 66 61 74 61 6c 28 22 72 65 6c 61  ssil_fatal("rela
71e0: 74 69 76 65 20 74 6f 20 61 62 73 6f 6c 75 74 65  tive to absolute
71f0: 20 6e 65 65 64 73 20 6f 70 65 6e 20 63 68 65 63   needs open chec
7200: 6b 6f 75 74 20 74 72 65 65 3a 20 25 73 22 2c 0a  kout tree: %s",.
7210: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
7220: 20 20 20 20 20 7a 4f 72 69 67 4e 61 6d 65 29 3b       zOrigName);
7230: 0a 20 20 20 20 20 20 7d 0a 20 20 20 20 20 20 72  .      }.      r
7240: 65 74 75 72 6e 20 30 3b 0a 20 20 20 20 7d 65 6c  eturn 0;.    }el
7250: 73 65 7b 0a 20 20 20 20 20 20 2f 2a 0a 20 20 20  se{.      /*.   
7260: 20 20 20 2a 2a 20 54 68 65 20 6f 72 69 67 69 6e     ** The origin
7270: 61 6c 20 70 61 74 68 20 6d 61 79 20 62 65 20 72  al path may be r
7280: 65 6c 61 74 69 76 65 20 6f 72 20 61 62 73 6f 6c  elative or absol
7290: 75 74 65 3b 20 68 6f 77 65 76 65 72 2c 20 77 69  ute; however, wi
72a0: 74 68 6f 75 74 0a 20 20 20 20 20 20 2a 2a 20 61  thout.      ** a
72b0: 6e 20 6f 70 65 6e 20 63 68 65 63 6b 6f 75 74 20  n open checkout 
72c0: 74 72 65 65 2c 20 74 68 65 20 6f 6e 6c 79 20 74  tree, the only t
72d0: 68 69 6e 67 73 20 77 65 20 63 61 6e 20 64 6f 20  hings we can do 
72e0: 61 74 20 74 68 69 73 20 70 6f 69 6e 74 0a 20 20  at this point.  
72f0: 20 20 20 20 2a 2a 20 69 73 20 72 65 74 75 72 6e      ** is return
7300: 20 69 74 20 76 65 72 62 61 74 69 6d 20 6f 72 20   it verbatim or 
7310: 67 65 6e 65 72 61 74 65 20 61 20 66 61 74 61 6c  generate a fatal
7320: 20 65 72 72 6f 72 2e 20 20 54 68 65 20 63 61 6c   error.  The cal
7330: 6c 65 72 20 69 73 0a 20 20 20 20 20 20 2a 2a 20  ler is.      ** 
7340: 70 72 6f 62 61 62 6c 79 20 65 78 70 65 63 74 69  probably expecti
7350: 6e 67 20 61 20 74 72 65 65 2d 72 65 6c 61 74 69  ng a tree-relati
7360: 76 65 20 70 61 74 68 20 6e 61 6d 65 20 77 69 6c  ve path name wil
7370: 6c 20 62 65 20 72 65 74 75 72 6e 65 64 3b 0a 20  l be returned;. 
7380: 20 20 20 20 20 2a 2a 20 68 6f 77 65 76 65 72 2c       ** however,
7390: 20 6d 6f 73 74 20 70 6c 61 63 65 73 20 77 68 65   most places whe
73a0: 72 65 20 74 68 69 73 20 66 75 6e 63 74 69 6f 6e  re this function
73b0: 20 69 73 20 63 61 6c 6c 65 64 20 61 6c 72 65 61   is called alrea
73c0: 64 79 20 63 68 65 63 6b 0a 20 20 20 20 20 20 2a  dy check.      *
73d0: 2a 20 69 66 20 74 68 65 20 6c 6f 63 61 6c 20 63  * if the local c
73e0: 68 65 63 6b 6f 75 74 20 74 72 65 65 20 69 73 20  heckout tree is 
73f0: 6f 70 65 6e 2c 20 65 69 74 68 65 72 20 64 69 72  open, either dir
7400: 65 63 74 6c 79 20 6f 72 20 69 6e 64 69 72 65 63  ectly or indirec
7410: 74 6c 79 2c 0a 20 20 20 20 20 20 2a 2a 20 77 68  tly,.      ** wh
7420: 69 63 68 20 77 6f 75 6c 64 20 6d 61 6b 65 20 74  ich would make t
7430: 68 69 73 20 73 69 74 75 61 74 69 6f 6e 20 69 6d  his situation im
7440: 70 6f 73 73 69 62 6c 65 2e 20 20 41 6c 74 65 72  possible.  Alter
7450: 6e 61 74 69 76 65 6c 79 2c 20 74 68 65 79 0a 20  natively, they. 
7460: 20 20 20 20 20 2a 2a 20 63 6f 75 6c 64 20 63 68       ** could ch
7470: 65 63 6b 20 74 68 65 20 72 65 74 75 72 6e 65 64  eck the returned
7480: 20 70 61 74 68 20 75 73 69 6e 67 20 74 68 65 20   path using the 
7490: 66 69 6c 65 5f 69 73 5f 61 62 73 6f 6c 75 74 65  file_is_absolute
74a0: 5f 70 61 74 68 28 29 0a 20 20 20 20 20 20 2a 2a  _path().      **
74b0: 20 66 75 6e 63 74 69 6f 6e 2e 0a 20 20 20 20 20   function..     
74c0: 20 2a 2f 0a 20 20 20 20 20 20 62 6c 6f 62 5f 61   */.      blob_a
74d0: 70 70 65 6e 64 66 28 70 4f 75 74 2c 20 22 25 73  ppendf(pOut, "%s
74e0: 22 2c 20 7a 4f 72 69 67 4e 61 6d 65 29 3b 0a 20  ", zOrigName);. 
74f0: 20 20 20 20 20 72 65 74 75 72 6e 20 31 3b 0a 20       return 1;. 
7500: 20 20 20 7d 0a 20 20 7d 0a 20 20 66 69 6c 65 5f     }.  }.  file_
7510: 63 61 6e 6f 6e 69 63 61 6c 5f 6e 61 6d 65 28 67  canonical_name(g
7520: 2e 7a 4c 6f 63 61 6c 52 6f 6f 74 2c 20 26 6c 6f  .zLocalRoot, &lo
7530: 63 61 6c 52 6f 6f 74 2c 20 31 29 3b 0a 20 20 6e  calRoot, 1);.  n
7540: 4c 6f 63 61 6c 52 6f 6f 74 20 3d 20 62 6c 6f 62  LocalRoot = blob
7550: 5f 73 69 7a 65 28 26 6c 6f 63 61 6c 52 6f 6f 74  _size(&localRoot
7560: 29 3b 0a 20 20 7a 4c 6f 63 61 6c 52 6f 6f 74 20  );.  zLocalRoot 
7570: 3d 20 62 6c 6f 62 5f 62 75 66 66 65 72 28 26 6c  = blob_buffer(&l
7580: 6f 63 61 6c 52 6f 6f 74 29 3b 0a 20 20 61 73 73  ocalRoot);.  ass
7590: 65 72 74 28 20 6e 4c 6f 63 61 6c 52 6f 6f 74 3e  ert( nLocalRoot>
75a0: 30 20 26 26 20 7a 4c 6f 63 61 6c 52 6f 6f 74 5b  0 && zLocalRoot[
75b0: 6e 4c 6f 63 61 6c 52 6f 6f 74 2d 31 5d 3d 3d 27  nLocalRoot-1]=='
75c0: 2f 27 20 29 3b 0a 20 20 66 69 6c 65 5f 63 61 6e  /' );.  file_can
75d0: 6f 6e 69 63 61 6c 5f 6e 61 6d 65 28 7a 4f 72 69  onical_name(zOri
75e0: 67 4e 61 6d 65 2c 20 26 66 75 6c 6c 2c 20 30 29  gName, &full, 0)
75f0: 3b 0a 20 20 6e 46 75 6c 6c 20 3d 20 62 6c 6f 62  ;.  nFull = blob
7600: 5f 73 69 7a 65 28 26 66 75 6c 6c 29 3b 0a 20 20  _size(&full);.  
7610: 7a 46 75 6c 6c 20 3d 20 62 6c 6f 62 5f 62 75 66  zFull = blob_buf
7620: 66 65 72 28 26 66 75 6c 6c 29 3b 0a 20 20 69 66  fer(&full);.  if
7630: 28 20 66 69 6c 65 6e 61 6d 65 73 5f 61 72 65 5f  ( filenames_are_
7640: 63 61 73 65 5f 73 65 6e 73 69 74 69 76 65 28 29  case_sensitive()
7650: 20 29 7b 0a 20 20 20 20 78 43 6d 70 20 3d 20 66   ){.    xCmp = f
7660: 6f 73 73 69 6c 5f 73 74 72 6e 63 6d 70 3b 0a 20  ossil_strncmp;. 
7670: 20 7d 65 6c 73 65 7b 0a 20 20 20 20 78 43 6d 70   }else{.    xCmp
7680: 20 3d 20 66 6f 73 73 69 6c 5f 73 74 72 6e 69 63   = fossil_strnic
7690: 6d 70 3b 0a 20 20 7d 0a 0a 20 20 2f 2a 20 53 70  mp;.  }..  /* Sp
76a0: 65 63 69 61 6c 20 63 61 73 65 2e 20 20 7a 4f 72  ecial case.  zOr
76b0: 69 67 4e 61 6d 65 20 72 65 66 65 72 73 20 74 6f  igName refers to
76c0: 20 67 2e 7a 4c 6f 63 61 6c 52 6f 6f 74 20 64 69   g.zLocalRoot di
76d0: 72 65 63 74 6f 72 79 2e 20 2a 2f 0a 20 20 69 66  rectory. */.  if
76e0: 28 20 28 6e 46 75 6c 6c 3d 3d 6e 4c 6f 63 61 6c  ( (nFull==nLocal
76f0: 52 6f 6f 74 2d 31 20 26 26 20 78 43 6d 70 28 7a  Root-1 && xCmp(z
7700: 4c 6f 63 61 6c 52 6f 6f 74 2c 20 7a 46 75 6c 6c  LocalRoot, zFull
7710: 2c 20 6e 46 75 6c 6c 29 3d 3d 30 29 0a 20 20 20  , nFull)==0).   
7720: 20 20 20 7c 7c 20 28 6e 46 75 6c 6c 3d 3d 31 20     || (nFull==1 
7730: 26 26 20 7a 46 75 6c 6c 5b 30 5d 3d 3d 27 2f 27  && zFull[0]=='/'
7740: 20 26 26 20 6e 4c 6f 63 61 6c 52 6f 6f 74 3d 3d   && nLocalRoot==
7750: 31 20 26 26 20 7a 4c 6f 63 61 6c 52 6f 6f 74 5b  1 && zLocalRoot[
7760: 30 5d 3d 3d 27 2f 27 29 20 29 7b 0a 20 20 20 20  0]=='/') ){.    
7770: 69 66 28 20 61 62 73 6f 6c 75 74 65 20 29 7b 0a  if( absolute ){.
7780: 20 20 20 20 20 20 62 6c 6f 62 5f 61 70 70 65 6e        blob_appen
7790: 64 28 70 4f 75 74 2c 20 7a 4c 6f 63 61 6c 52 6f  d(pOut, zLocalRo
77a0: 6f 74 2c 20 6e 4c 6f 63 61 6c 52 6f 6f 74 29 3b  ot, nLocalRoot);
77b0: 0a 20 20 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20  .    }else{.    
77c0: 20 20 62 6c 6f 62 5f 61 70 70 65 6e 64 28 70 4f    blob_append(pO
77d0: 75 74 2c 20 22 2e 22 2c 20 31 29 3b 0a 20 20 20  ut, ".", 1);.   
77e0: 20 7d 0a 20 20 20 20 62 6c 6f 62 5f 72 65 73 65   }.    blob_rese
77f0: 74 28 26 6c 6f 63 61 6c 52 6f 6f 74 29 3b 0a 20  t(&localRoot);. 
7800: 20 20 20 62 6c 6f 62 5f 72 65 73 65 74 28 26 66     blob_reset(&f
7810: 75 6c 6c 29 3b 0a 20 20 20 20 72 65 74 75 72 6e  ull);.    return
7820: 20 31 3b 0a 20 20 7d 0a 0a 20 20 69 66 28 20 6e   1;.  }..  if( n
7830: 46 75 6c 6c 3c 3d 6e 4c 6f 63 61 6c 52 6f 6f 74  Full<=nLocalRoot
7840: 20 7c 7c 20 78 43 6d 70 28 7a 4c 6f 63 61 6c 52   || xCmp(zLocalR
7850: 6f 6f 74 2c 20 7a 46 75 6c 6c 2c 20 6e 4c 6f 63  oot, zFull, nLoc
7860: 61 6c 52 6f 6f 74 29 20 29 7b 0a 20 20 20 20 62  alRoot) ){.    b
7870: 6c 6f 62 5f 72 65 73 65 74 28 26 6c 6f 63 61 6c  lob_reset(&local
7880: 52 6f 6f 74 29 3b 0a 20 20 20 20 62 6c 6f 62 5f  Root);.    blob_
7890: 72 65 73 65 74 28 26 66 75 6c 6c 29 3b 0a 20 20  reset(&full);.  
78a0: 20 20 69 66 28 20 65 72 72 46 61 74 61 6c 20 29    if( errFatal )
78b0: 7b 0a 20 20 20 20 20 20 66 6f 73 73 69 6c 5f 66  {.      fossil_f
78c0: 61 74 61 6c 28 22 66 69 6c 65 20 6f 75 74 73 69  atal("file outsi
78d0: 64 65 20 6f 66 20 63 68 65 63 6b 6f 75 74 20 74  de of checkout t
78e0: 72 65 65 3a 20 25 73 22 2c 20 7a 4f 72 69 67 4e  ree: %s", zOrigN
78f0: 61 6d 65 29 3b 0a 20 20 20 20 7d 0a 20 20 20 20  ame);.    }.    
7900: 72 65 74 75 72 6e 20 30 3b 0a 20 20 7d 0a 20 20  return 0;.  }.  
7910: 69 66 28 20 61 62 73 6f 6c 75 74 65 20 29 7b 0a  if( absolute ){.
7920: 20 20 20 20 69 66 28 20 21 66 69 6c 65 5f 69 73      if( !file_is
7930: 5f 61 62 73 6f 6c 75 74 65 5f 70 61 74 68 28 7a  _absolute_path(z
7940: 4f 72 69 67 4e 61 6d 65 29 20 29 7b 0a 20 20 20  OrigName) ){.   
7950: 20 20 20 62 6c 6f 62 5f 61 70 70 65 6e 64 28 70     blob_append(p
7960: 4f 75 74 2c 20 7a 4c 6f 63 61 6c 52 6f 6f 74 2c  Out, zLocalRoot,
7970: 20 6e 4c 6f 63 61 6c 52 6f 6f 74 29 3b 0a 20 20   nLocalRoot);.  
7980: 20 20 7d 0a 20 20 20 20 62 6c 6f 62 5f 61 70 70    }.    blob_app
7990: 65 6e 64 28 70 4f 75 74 2c 20 7a 4f 72 69 67 4e  end(pOut, zOrigN
79a0: 61 6d 65 2c 20 2d 31 29 3b 0a 20 20 20 20 62 6c  ame, -1);.    bl
79b0: 6f 62 5f 72 65 73 69 7a 65 28 70 4f 75 74 2c 20  ob_resize(pOut, 
79c0: 66 69 6c 65 5f 73 69 6d 70 6c 69 66 79 5f 6e 61  file_simplify_na
79d0: 6d 65 28 62 6c 6f 62 5f 62 75 66 66 65 72 28 70  me(blob_buffer(p
79e0: 4f 75 74 29 2c 0a 20 20 20 20 20 20 20 20 20 20  Out),.          
79f0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
7a00: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 62                 b
7a10: 6c 6f 62 5f 73 69 7a 65 28 70 4f 75 74 29 2c 20  lob_size(pOut), 
7a20: 30 29 29 3b 0a 20 20 7d 65 6c 73 65 7b 0a 20 20  0));.  }else{.  
7a30: 20 20 62 6c 6f 62 5f 61 70 70 65 6e 64 28 70 4f    blob_append(pO
7a40: 75 74 2c 20 26 7a 46 75 6c 6c 5b 6e 4c 6f 63 61  ut, &zFull[nLoca
7a50: 6c 52 6f 6f 74 5d 2c 20 6e 46 75 6c 6c 2d 6e 4c  lRoot], nFull-nL
7a60: 6f 63 61 6c 52 6f 6f 74 29 3b 0a 20 20 7d 0a 20  ocalRoot);.  }. 
7a70: 20 62 6c 6f 62 5f 72 65 73 65 74 28 26 6c 6f 63   blob_reset(&loc
7a80: 61 6c 52 6f 6f 74 29 3b 0a 20 20 62 6c 6f 62 5f  alRoot);.  blob_
7a90: 72 65 73 65 74 28 26 66 75 6c 6c 29 3b 0a 20 20  reset(&full);.  
7aa0: 72 65 74 75 72 6e 20 31 3b 0a 7d 0a 0a 2f 2a 0a  return 1;.}../*.
7ab0: 2a 2a 20 43 4f 4d 4d 41 4e 44 3a 20 74 65 73 74  ** COMMAND: test
7ac0: 2d 74 72 65 65 2d 6e 61 6d 65 0a 2a 2a 0a 2a 2a  -tree-name.**.**
7ad0: 20 54 65 73 74 20 74 68 65 20 6f 70 65 72 61 74   Test the operat
7ae0: 69 6f 6e 20 6f 66 20 74 68 65 20 74 72 65 65 20  ion of the tree 
7af0: 6e 61 6d 65 20 67 65 6e 65 72 61 74 6f 72 2e 0a  name generator..
7b00: 2a 2a 0a 2a 2a 20 4f 70 74 69 6f 6e 73 3a 0a 2a  **.** Options:.*
7b10: 2a 20 20 20 2d 2d 61 62 73 6f 6c 75 74 65 20 20  *   --absolute  
7b20: 20 20 20 20 20 20 20 20 20 52 65 74 75 72 6e 20           Return 
7b30: 61 6e 20 61 62 73 6f 6c 75 74 65 20 70 61 74 68  an absolute path
7b40: 20 69 6e 73 74 65 61 64 20 6f 66 20 61 20 72 65   instead of a re
7b50: 6c 61 74 69 76 65 20 6f 6e 65 2e 0a 2a 2a 20 20  lative one..**  
7b60: 20 2d 2d 63 61 73 65 2d 73 65 6e 73 69 74 69 76   --case-sensitiv
7b70: 65 20 42 20 20 20 45 6e 61 62 6c 65 20 6f 72 20  e B   Enable or 
7b80: 64 69 73 61 62 6c 65 20 63 61 73 65 2d 73 65 6e  disable case-sen
7b90: 73 69 74 69 76 65 20 66 69 6c 65 6e 61 6d 65 73  sitive filenames
7ba0: 2e 20 20 42 20 69 73 0a 2a 2a 20 20 20 20 20 20  .  B is.**      
7bb0: 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20                  
7bc0: 20 20 61 20 62 6f 6f 6c 65 61 6e 3a 20 22 79 65    a boolean: "ye
7bd0: 73 22 2c 20 22 6e 6f 22 2c 20 22 74 72 75 65 22  s", "no", "true"
7be0: 2c 20 22 66 61 6c 73 65 22 2c 20 65 74 63 2e 0a  , "false", etc..
7bf0: 2a 2f 0a 76 6f 69 64 20 63 6d 64 5f 74 65 73 74  */.void cmd_test
7c00: 5f 74 72 65 65 5f 6e 61 6d 65 28 76 6f 69 64 29  _tree_name(void)
7c10: 7b 0a 20 20 69 6e 74 20 69 3b 0a 20 20 42 6c 6f  {.  int i;.  Blo
7c20: 62 20 78 3b 0a 20 20 69 6e 74 20 61 62 73 6f 6c  b x;.  int absol
7c30: 75 74 65 46 6c 61 67 20 3d 20 66 69 6e 64 5f 6f  uteFlag = find_o
7c40: 70 74 69 6f 6e 28 22 61 62 73 6f 6c 75 74 65 22  ption("absolute"
7c50: 2c 30 2c 30 29 21 3d 30 3b 0a 20 20 64 62 5f 66  ,0,0)!=0;.  db_f
7c60: 69 6e 64 5f 61 6e 64 5f 6f 70 65 6e 5f 72 65 70  ind_and_open_rep
7c70: 6f 73 69 74 6f 72 79 28 30 2c 30 29 3b 0a 20 20  ository(0,0);.  
7c80: 62 6c 6f 62 5f 7a 65 72 6f 28 26 78 29 3b 0a 20  blob_zero(&x);. 
7c90: 20 66 6f 72 28 69 3d 32 3b 20 69 3c 67 2e 61 72   for(i=2; i<g.ar
7ca0: 67 63 3b 20 69 2b 2b 29 7b 0a 20 20 20 20 69 66  gc; i++){.    if
7cb0: 28 20 66 69 6c 65 5f 74 72 65 65 5f 6e 61 6d 65  ( file_tree_name
7cc0: 28 67 2e 61 72 67 76 5b 69 5d 2c 20 26 78 2c 20  (g.argv[i], &x, 
7cd0: 61 62 73 6f 6c 75 74 65 46 6c 61 67 2c 20 31 29  absoluteFlag, 1)
7ce0: 20 29 7b 0a 20 20 20 20 20 20 66 6f 73 73 69 6c   ){.      fossil
7cf0: 5f 70 72 69 6e 74 28 22 25 73 5c 6e 22 2c 20 62  _print("%s\n", b
7d00: 6c 6f 62 5f 62 75 66 66 65 72 28 26 78 29 29 3b  lob_buffer(&x));
7d10: 0a 20 20 20 20 20 20 62 6c 6f 62 5f 72 65 73 65  .      blob_rese
7d20: 74 28 26 78 29 3b 0a 20 20 20 20 7d 0a 20 20 7d  t(&x);.    }.  }
7d30: 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 50 61 72 73 65 20  .}../*.** Parse 
7d40: 61 20 55 52 49 20 69 6e 74 6f 20 73 63 68 65 6d  a URI into schem
7d50: 65 2c 20 68 6f 73 74 2c 20 70 6f 72 74 2c 20 61  e, host, port, a
7d60: 6e 64 20 70 61 74 68 2e 0a 2a 2f 0a 76 6f 69 64  nd path..*/.void
7d70: 20 66 69 6c 65 5f 70 61 72 73 65 5f 75 72 69 28   file_parse_uri(
7d80: 0a 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a  .  const char *z
7d90: 55 72 69 2c 0a 20 20 42 6c 6f 62 20 2a 70 53 63  Uri,.  Blob *pSc
7da0: 68 65 6d 65 2c 0a 20 20 42 6c 6f 62 20 2a 70 48  heme,.  Blob *pH
7db0: 6f 73 74 2c 0a 20 20 69 6e 74 20 2a 70 50 6f 72  ost,.  int *pPor
7dc0: 74 2c 0a 20 20 42 6c 6f 62 20 2a 70 50 61 74 68  t,.  Blob *pPath
7dd0: 0a 29 7b 0a 20 20 69 6e 74 20 69 2c 20 6a 3b 0a  .){.  int i, j;.
7de0: 0a 20 20 66 6f 72 28 69 3d 30 3b 20 7a 55 72 69  .  for(i=0; zUri
7df0: 5b 69 5d 20 26 26 20 7a 55 72 69 5b 69 5d 3e 3d  [i] && zUri[i]>=
7e00: 27 61 27 20 26 26 20 7a 55 72 69 5b 69 5d 3c 3d  'a' && zUri[i]<=
7e10: 27 7a 27 3b 20 69 2b 2b 29 7b 7d 0a 20 20 69 66  'z'; i++){}.  if
7e20: 28 20 7a 55 72 69 5b 69 5d 21 3d 27 3a 27 20 29  ( zUri[i]!=':' )
7e30: 7b 0a 20 20 20 20 62 6c 6f 62 5f 7a 65 72 6f 28  {.    blob_zero(
7e40: 70 53 63 68 65 6d 65 29 3b 0a 20 20 20 20 62 6c  pScheme);.    bl
7e50: 6f 62 5f 7a 65 72 6f 28 70 48 6f 73 74 29 3b 0a  ob_zero(pHost);.
7e60: 20 20 20 20 62 6c 6f 62 5f 73 65 74 28 70 50 61      blob_set(pPa
7e70: 74 68 2c 20 7a 55 72 69 29 3b 0a 20 20 20 20 72  th, zUri);.    r
7e80: 65 74 75 72 6e 3b 0a 20 20 7d 0a 20 20 62 6c 6f  eturn;.  }.  blo
7e90: 62 5f 69 6e 69 74 28 70 53 63 68 65 6d 65 2c 20  b_init(pScheme, 
7ea0: 7a 55 72 69 2c 20 69 29 3b 0a 20 20 69 2b 2b 3b  zUri, i);.  i++;
7eb0: 0a 20 20 69 66 28 20 7a 55 72 69 5b 69 5d 3d 3d  .  if( zUri[i]==
7ec0: 27 2f 27 20 26 26 20 7a 55 72 69 5b 69 2b 31 5d  '/' && zUri[i+1]
7ed0: 3d 3d 27 2f 27 20 29 7b 0a 20 20 20 20 69 20 2b  =='/' ){.    i +
7ee0: 3d 20 32 3b 0a 20 20 20 20 6a 20 3d 20 69 3b 0a  = 2;.    j = i;.
7ef0: 20 20 20 20 77 68 69 6c 65 28 20 7a 55 72 69 5b      while( zUri[
7f00: 69 5d 20 26 26 20 7a 55 72 69 5b 69 5d 21 3d 27  i] && zUri[i]!='
7f10: 2f 27 20 26 26 20 7a 55 72 69 5b 69 5d 21 3d 27  /' && zUri[i]!='
7f20: 3a 27 20 29 7b 20 69 2b 2b 3b 20 7d 0a 20 20 20  :' ){ i++; }.   
7f30: 20 62 6c 6f 62 5f 69 6e 69 74 28 70 48 6f 73 74   blob_init(pHost
7f40: 2c 20 26 7a 55 72 69 5b 6a 5d 2c 20 69 2d 6a 29  , &zUri[j], i-j)
7f50: 3b 0a 20 20 20 20 69 66 28 20 7a 55 72 69 5b 69  ;.    if( zUri[i
7f60: 5d 3d 3d 27 3a 27 20 29 7b 0a 20 20 20 20 20 20  ]==':' ){.      
7f70: 69 2b 2b 3b 0a 20 20 20 20 20 20 2a 70 50 6f 72  i++;.      *pPor
7f80: 74 20 3d 20 61 74 6f 69 28 26 7a 55 72 69 5b 69  t = atoi(&zUri[i
7f90: 5d 29 3b 0a 20 20 20 20 20 20 77 68 69 6c 65 28  ]);.      while(
7fa0: 20 7a 55 72 69 5b 69 5d 20 26 26 20 7a 55 72 69   zUri[i] && zUri
7fb0: 5b 69 5d 21 3d 27 2f 27 20 29 7b 20 69 2b 2b 3b  [i]!='/' ){ i++;
7fc0: 20 7d 0a 20 20 20 20 7d 0a 20 20 7d 65 6c 73 65   }.    }.  }else
7fd0: 7b 0a 20 20 20 20 62 6c 6f 62 5f 7a 65 72 6f 28  {.    blob_zero(
7fe0: 70 48 6f 73 74 29 3b 0a 20 20 7d 0a 20 20 69 66  pHost);.  }.  if
7ff0: 28 20 7a 55 72 69 5b 69 5d 3d 3d 27 2f 27 20 29  ( zUri[i]=='/' )
8000: 7b 0a 20 20 20 20 62 6c 6f 62 5f 73 65 74 28 70  {.    blob_set(p
8010: 50 61 74 68 2c 20 26 7a 55 72 69 5b 69 5d 29 3b  Path, &zUri[i]);
8020: 0a 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 62 6c  .  }else{.    bl
8030: 6f 62 5f 73 65 74 28 70 50 61 74 68 2c 20 22 2f  ob_set(pPath, "/
8040: 22 29 3b 0a 20 20 7d 0a 7d 0a 0a 2f 2a 0a 2a 2a  ");.  }.}../*.**
8050: 20 43 6f 6e 73 74 72 75 63 74 20 61 20 72 61 6e   Construct a ran
8060: 64 6f 6d 20 74 65 6d 70 6f 72 61 72 79 20 66 69  dom temporary fi
8070: 6c 65 6e 61 6d 65 20 69 6e 74 6f 20 7a 42 75 66  lename into zBuf
8080: 5b 5d 2e 0a 2a 2f 0a 76 6f 69 64 20 66 69 6c 65  []..*/.void file
8090: 5f 74 65 6d 70 6e 61 6d 65 28 69 6e 74 20 6e 42  _tempname(int nB
80a0: 75 66 2c 20 63 68 61 72 20 2a 7a 42 75 66 29 7b  uf, char *zBuf){
80b0: 0a 23 69 66 20 64 65 66 69 6e 65 64 28 5f 57 49  .#if defined(_WI
80c0: 4e 33 32 29 0a 20 20 63 6f 6e 73 74 20 63 68 61  N32).  const cha
80d0: 72 20 2a 61 7a 44 69 72 73 5b 5d 20 3d 20 7b 0a  r *azDirs[] = {.
80e0: 20 20 20 20 20 30 2c 20 2f 2a 20 47 65 74 54 65       0, /* GetTe
80f0: 6d 70 50 61 74 68 20 2a 2f 0a 20 20 20 20 20 30  mpPath */.     0
8100: 2c 20 2f 2a 20 54 45 4d 50 20 2a 2f 0a 20 20 20  , /* TEMP */.   
8110: 20 20 30 2c 20 2f 2a 20 54 4d 50 20 2a 2f 0a 20    0, /* TMP */. 
8120: 20 20 20 20 22 2e 22 2c 0a 20 20 7d 3b 0a 23 65      ".",.  };.#e
8130: 6c 73 65 0a 20 20 73 74 61 74 69 63 20 63 6f 6e  lse.  static con
8140: 73 74 20 63 68 61 72 20 2a 63 6f 6e 73 74 20 61  st char *const a
8150: 7a 44 69 72 73 5b 5d 20 3d 20 7b 0a 20 20 20 20  zDirs[] = {.    
8160: 20 22 2f 76 61 72 2f 74 6d 70 22 2c 0a 20 20 20   "/var/tmp",.   
8170: 20 20 22 2f 75 73 72 2f 74 6d 70 22 2c 0a 20 20    "/usr/tmp",.  
8180: 20 20 20 22 2f 74 6d 70 22 2c 0a 20 20 20 20 20     "/tmp",.     
8190: 22 2f 74 65 6d 70 22 2c 0a 20 20 20 20 20 22 2e  "/temp",.     ".
81a0: 22 2c 0a 20 20 7d 3b 0a 23 65 6e 64 69 66 0a 20  ",.  };.#endif. 
81b0: 20 73 74 61 74 69 63 20 63 6f 6e 73 74 20 75 6e   static const un
81c0: 73 69 67 6e 65 64 20 63 68 61 72 20 7a 43 68 61  signed char zCha
81d0: 72 73 5b 5d 20 3d 0a 20 20 20 20 22 61 62 63 64  rs[] =.    "abcd
81e0: 65 66 67 68 69 6a 6b 6c 6d 6e 6f 70 71 72 73 74  efghijklmnopqrst
81f0: 75 76 77 78 79 7a 22 0a 20 20 20 20 22 41 42 43  uvwxyz".    "ABC
8200: 44 45 46 47 48 49 4a 4b 4c 4d 4e 4f 50 51 52 53  DEFGHIJKLMNOPQRS
8210: 54 55 56 57 58 59 5a 22 0a 20 20 20 20 22 30 31  TUVWXYZ".    "01
8220: 32 33 34 35 36 37 38 39 22 3b 0a 20 20 75 6e 73  23456789";.  uns
8230: 69 67 6e 65 64 20 69 6e 74 20 69 2c 20 6a 3b 0a  igned int i, j;.
8240: 20 20 63 6f 6e 73 74 20 63 68 61 72 20 2a 7a 44    const char *zD
8250: 69 72 20 3d 20 22 2e 22 3b 0a 20 20 69 6e 74 20  ir = ".";.  int 
8260: 63 6e 74 20 3d 20 30 3b 0a 0a 23 69 66 20 64 65  cnt = 0;..#if de
8270: 66 69 6e 65 64 28 5f 57 49 4e 33 32 29 0a 20 20  fined(_WIN32).  
8280: 77 63 68 61 72 5f 74 20 7a 54 6d 70 50 61 74 68  wchar_t zTmpPath
8290: 5b 4d 41 58 5f 50 41 54 48 5d 3b 0a 0a 20 20 69  [MAX_PATH];..  i
82a0: 66 28 20 47 65 74 54 65 6d 70 50 61 74 68 57 28  f( GetTempPathW(
82b0: 4d 41 58 5f 50 41 54 48 2c 20 7a 54 6d 70 50 61  MAX_PATH, zTmpPa
82c0: 74 68 29 20 29 7b 0a 20 20 20 20 61 7a 44 69 72  th) ){.    azDir
82d0: 73 5b 30 5d 20 3d 20 66 6f 73 73 69 6c 5f 70 61  s[0] = fossil_pa
82e0: 74 68 5f 74 6f 5f 75 74 66 38 28 7a 54 6d 70 50  th_to_utf8(zTmpP
82f0: 61 74 68 29 3b 0a 20 20 7d 0a 0a 20 20 61 7a 44  ath);.  }..  azD
8300: 69 72 73 5b 31 5d 20 3d 20 66 6f 73 73 69 6c 5f  irs[1] = fossil_
8310: 67 65 74 65 6e 76 28 22 54 45 4d 50 22 29 3b 0a  getenv("TEMP");.
8320: 20 20 61 7a 44 69 72 73 5b 32 5d 20 3d 20 66 6f    azDirs[2] = fo
8330: 73 73 69 6c 5f 67 65 74 65 6e 76 28 22 54 4d 50  ssil_getenv("TMP
8340: 22 29 3b 0a 23 65 6e 64 69 66 0a 0a 0a 20 20 66  ");.#endif...  f
8350: 6f 72 28 69 3d 30 3b 20 69 3c 73 69 7a 65 6f 66  or(i=0; i<sizeof
8360: 28 61 7a 44 69 72 73 29 2f 73 69 7a 65 6f 66 28  (azDirs)/sizeof(
8370: 61 7a 44 69 72 73 5b 30 5d 29 3b 20 69 2b 2b 29  azDirs[0]); i++)
8380: 7b 0a 20 20 20 20 69 66 28 20 61 7a 44 69 72 73  {.    if( azDirs
8390: 5b 69 5d 3d 3d 30 20 29 20 63 6f 6e 74 69 6e 75  [i]==0 ) continu
83a0: 65 3b 0a 20 20 20 20 69 66 28 20 21 66 69 6c 65  e;.    if( !file
83b0: 5f 69 73 64 69 72 28 61 7a 44 69 72 73 5b 69 5d  _isdir(azDirs[i]
83c0: 29 20 29 20 63 6f 6e 74 69 6e 75 65 3b 0a 20 20  ) ) continue;.  
83d0: 20 20 7a 44 69 72 20 3d 20 61 7a 44 69 72 73 5b    zDir = azDirs[
83e0: 69 5d 3b 0a 20 20 20 20 62 72 65 61 6b 3b 0a 20  i];.    break;. 
83f0: 20 7d 0a 0a 20 20 2f 2a 20 43 68 65 63 6b 20 74   }..  /* Check t
8400: 68 61 74 20 74 68 65 20 6f 75 74 70 75 74 20 62  hat the output b
8410: 75 66 66 65 72 20 69 73 20 6c 61 72 67 65 20 65  uffer is large e
8420: 6e 6f 75 67 68 20 66 6f 72 20 74 68 65 20 74 65  nough for the te
8430: 6d 70 6f 72 61 72 79 20 66 69 6c 65 0a 20 20 2a  mporary file.  *
8440: 2a 20 6e 61 6d 65 2e 20 49 66 20 69 74 20 69 73  * name. If it is
8450: 20 6e 6f 74 2c 20 72 65 74 75 72 6e 20 53 51 4c   not, return SQL
8460: 49 54 45 5f 45 52 52 4f 52 2e 0a 20 20 2a 2f 0a  ITE_ERROR..  */.
8470: 20 20 69 66 28 20 28 73 74 72 6c 65 6e 28 7a 44    if( (strlen(zD
8480: 69 72 29 20 2b 20 31 37 29 20 3e 3d 20 28 73 69  ir) + 17) >= (si
8490: 7a 65 5f 74 29 6e 42 75 66 20 29 7b 0a 20 20 20  ze_t)nBuf ){.   
84a0: 20 66 6f 73 73 69 6c 5f 66 61 74 61 6c 28 22 69   fossil_fatal("i
84b0: 6e 73 75 66 66 69 63 69 65 6e 74 20 73 70 61 63  nsufficient spac
84c0: 65 20 66 6f 72 20 74 65 6d 70 6f 72 61 72 79 20  e for temporary 
84d0: 66 69 6c 65 6e 61 6d 65 22 29 3b 0a 20 20 7d 0a  filename");.  }.
84e0: 0a 20 20 64 6f 7b 0a 20 20 20 20 69 66 28 20 63  .  do{.    if( c
84f0: 6e 74 2b 2b 3e 32 30 20 29 20 66 6f 73 73 69 6c  nt++>20 ) fossil
8500: 5f 70 61 6e 69 63 28 22 63 61 6e 6e 6f 74 20 67  _panic("cannot g
8510: 65 6e 65 72 61 74 65 20 61 20 74 65 6d 70 6f 72  enerate a tempor
8520: 61 72 79 20 66 69 6c 65 6e 61 6d 65 22 29 3b 0a  ary filename");.
8530: 20 20 20 20 73 71 6c 69 74 65 33 5f 73 6e 70 72      sqlite3_snpr
8540: 69 6e 74 66 28 6e 42 75 66 2d 31 37 2c 20 7a 42  intf(nBuf-17, zB
8550: 75 66 2c 20 22 25 73 2f 22 2c 20 7a 44 69 72 29  uf, "%s/", zDir)
8560: 3b 0a 20 20 20 20 6a 20 3d 20 28 69 6e 74 29 73  ;.    j = (int)s
8570: 74 72 6c 65 6e 28 7a 42 75 66 29 3b 0a 20 20 20  trlen(zBuf);.   
8580: 20 73 71 6c 69 74 65 33 5f 72 61 6e 64 6f 6d 6e   sqlite3_randomn
8590: 65 73 73 28 31 35 2c 20 26 7a 42 75 66 5b 6a 5d  ess(15, &zBuf[j]
85a0: 29 3b 0a 20 20 20 20 66 6f 72 28 69 3d 30 3b 20  );.    for(i=0; 
85b0: 69 3c 31 35 3b 20 69 2b 2b 2c 20 6a 2b 2b 29 7b  i<15; i++, j++){
85c0: 0a 20 20 20 20 20 20 7a 42 75 66 5b 6a 5d 20 3d  .      zBuf[j] =
85d0: 20 28 63 68 61 72 29 7a 43 68 61 72 73 5b 20 28   (char)zChars[ (
85e0: 28 75 6e 73 69 67 6e 65 64 20 63 68 61 72 29 7a  (unsigned char)z
85f0: 42 75 66 5b 6a 5d 29 25 28 73 69 7a 65 6f 66 28  Buf[j])%(sizeof(
8600: 7a 43 68 61 72 73 29 2d 31 29 20 5d 3b 0a 20 20  zChars)-1) ];.  
8610: 20 20 7d 0a 20 20 20 20 7a 42 75 66 5b 6a 5d 20    }.    zBuf[j] 
8620: 3d 20 30 3b 0a 20 20 7d 77 68 69 6c 65 28 20 66  = 0;.  }while( f
8630: 69 6c 65 5f 73 69 7a 65 28 7a 42 75 66 29 3e 3d  ile_size(zBuf)>=
8640: 30 20 29 3b 0a 0a 23 69 66 20 64 65 66 69 6e 65  0 );..#if define
8650: 64 28 5f 57 49 4e 33 32 29 0a 20 20 66 6f 73 73  d(_WIN32).  foss
8660: 69 6c 5f 70 61 74 68 5f 66 72 65 65 28 28 63 68  il_path_free((ch
8670: 61 72 20 2a 29 61 7a 44 69 72 73 5b 30 5d 29 3b  ar *)azDirs[0]);
8680: 0a 20 20 66 6f 73 73 69 6c 5f 70 61 74 68 5f 66  .  fossil_path_f
8690: 72 65 65 28 28 63 68 61 72 20 2a 29 61 7a 44 69  ree((char *)azDi
86a0: 72 73 5b 31 5d 29 3b 0a 20 20 66 6f 73 73 69 6c  rs[1]);.  fossil
86b0: 5f 70 61 74 68 5f 66 72 65 65 28 28 63 68 61 72  _path_free((char
86c0: 20 2a 29 61 7a 44 69 72 73 5b 32 5d 29 3b 0a 23   *)azDirs[2]);.#
86d0: 65 6e 64 69 66 0a 7d 0a 0a 0a 2f 2a 0a 2a 2a 20  endif.}.../*.** 
86e0: 52 65 74 75 72 6e 20 74 72 75 65 20 69 66 20 61  Return true if a
86f0: 20 66 69 6c 65 20 6e 61 6d 65 64 20 7a 4e 61 6d   file named zNam
8700: 65 20 65 78 69 73 74 73 20 61 6e 64 20 68 61 73  e exists and has
8710: 20 69 64 65 6e 74 69 63 61 6c 20 63 6f 6e 74 65   identical conte
8720: 6e 74 0a 2a 2a 20 74 6f 20 74 68 65 20 62 6c 6f  nt.** to the blo
8730: 62 20 70 43 6f 6e 74 65 6e 74 2e 20 20 49 66 20  b pContent.  If 
8740: 7a 4e 61 6d 65 20 64 6f 65 73 20 6e 6f 74 20 65  zName does not e
8750: 78 69 73 74 20 6f 72 20 69 66 20 74 68 65 20 63  xist or if the c
8760: 6f 6e 74 65 6e 74 20 69 73 0a 2a 2a 20 64 69 66  ontent is.** dif
8770: 66 65 72 65 6e 74 20 69 6e 20 61 6e 79 20 77 61  ferent in any wa
8780: 79 2c 20 74 68 65 6e 20 72 65 74 75 72 6e 20 66  y, then return f
8790: 61 6c 73 65 2e 0a 2a 2f 0a 69 6e 74 20 66 69 6c  alse..*/.int fil
87a0: 65 5f 69 73 5f 74 68 65 5f 73 61 6d 65 28 42 6c  e_is_the_same(Bl
87b0: 6f 62 20 2a 70 43 6f 6e 74 65 6e 74 2c 20 63 6f  ob *pContent, co
87c0: 6e 73 74 20 63 68 61 72 20 2a 7a 4e 61 6d 65 29  nst char *zName)
87d0: 7b 0a 20 20 69 36 34 20 69 53 69 7a 65 3b 0a 20  {.  i64 iSize;. 
87e0: 20 69 6e 74 20 72 63 3b 0a 20 20 42 6c 6f 62 20   int rc;.  Blob 
87f0: 6f 6e 44 69 73 6b 3b 0a 0a 20 20 69 53 69 7a 65  onDisk;..  iSize
8800: 20 3d 20 66 69 6c 65 5f 77 64 5f 73 69 7a 65 28   = file_wd_size(
8810: 7a 4e 61 6d 65 29 3b 0a 20 20 69 66 28 20 69 53  zName);.  if( iS
8820: 69 7a 65 3c 30 20 29 20 72 65 74 75 72 6e 20 30  ize<0 ) return 0
8830: 3b 0a 20 20 69 66 28 20 69 53 69 7a 65 21 3d 62  ;.  if( iSize!=b
8840: 6c 6f 62 5f 73 69 7a 65 28 70 43 6f 6e 74 65 6e  lob_size(pConten
8850: 74 29 20 29 20 72 65 74 75 72 6e 20 30 3b 0a 20  t) ) return 0;. 
8860: 20 69 66 28 20 66 69 6c 65 5f 77 64 5f 69 73 6c   if( file_wd_isl
8870: 69 6e 6b 28 7a 4e 61 6d 65 29 20 29 7b 0a 20 20  ink(zName) ){.  
8880: 20 20 62 6c 6f 62 5f 72 65 61 64 5f 6c 69 6e 6b    blob_read_link
8890: 28 26 6f 6e 44 69 73 6b 2c 20 7a 4e 61 6d 65 29  (&onDisk, zName)
88a0: 3b 0a 20 20 7d 65 6c 73 65 7b 0a 20 20 20 20 62  ;.  }else{.    b
88b0: 6c 6f 62 5f 72 65 61 64 5f 66 72 6f 6d 5f 66 69  lob_read_from_fi
88c0: 6c 65 28 26 6f 6e 44 69 73 6b 2c 20 7a 4e 61 6d  le(&onDisk, zNam
88d0: 65 29 3b 0a 20 20 7d 0a 20 20 72 63 20 3d 20 62  e);.  }.  rc = b
88e0: 6c 6f 62 5f 63 6f 6d 70 61 72 65 28 26 6f 6e 44  lob_compare(&onD
88f0: 69 73 6b 2c 20 70 43 6f 6e 74 65 6e 74 29 3b 0a  isk, pContent);.
8900: 20 20 62 6c 6f 62 5f 72 65 73 65 74 28 26 6f 6e    blob_reset(&on
8910: 44 69 73 6b 29 3b 0a 20 20 72 65 74 75 72 6e 20  Disk);.  return 
8920: 72 63 3d 3d 30 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20  rc==0;.}../*.** 
8930: 52 65 74 75 72 6e 20 74 68 65 20 76 61 6c 75 65  Return the value
8940: 20 6f 66 20 61 6e 20 65 6e 76 69 72 6f 6e 6d 65   of an environme
8950: 6e 74 20 76 61 72 69 61 62 6c 65 20 61 73 20 55  nt variable as U
8960: 54 46 38 2e 0a 2a 2a 20 55 73 65 20 66 6f 73 73  TF8..** Use foss
8970: 69 6c 5f 70 61 74 68 5f 66 72 65 65 28 29 20 74  il_path_free() t
8980: 6f 20 72 65 6c 65 61 73 65 20 72 65 73 6f 75 72  o release resour
8990: 63 65 73 2e 0a 2a 2f 0a 63 68 61 72 20 2a 66 6f  ces..*/.char *fo
89a0: 73 73 69 6c 5f 67 65 74 65 6e 76 28 63 6f 6e 73  ssil_getenv(cons
89b0: 74 20 63 68 61 72 20 2a 7a 4e 61 6d 65 29 7b 0a  t char *zName){.
89c0: 23 69 66 64 65 66 20 5f 57 49 4e 33 32 0a 20 20  #ifdef _WIN32.  
89d0: 77 63 68 61 72 5f 74 20 2a 75 4e 61 6d 65 20 3d  wchar_t *uName =
89e0: 20 66 6f 73 73 69 6c 5f 75 74 66 38 5f 74 6f 5f   fossil_utf8_to_
89f0: 75 6e 69 63 6f 64 65 28 7a 4e 61 6d 65 29 3b 0a  unicode(zName);.
8a00: 20 20 76 6f 69 64 20 2a 7a 56 61 6c 75 65 20 3d    void *zValue =
8a10: 20 5f 77 67 65 74 65 6e 76 28 75 4e 61 6d 65 29   _wgetenv(uName)
8a20: 3b 0a 20 20 66 6f 73 73 69 6c 5f 75 6e 69 63 6f  ;.  fossil_unico
8a30: 64 65 5f 66 72 65 65 28 75 4e 61 6d 65 29 3b 0a  de_free(uName);.
8a40: 23 65 6c 73 65 0a 20 20 63 68 61 72 20 2a 7a 56  #else.  char *zV
8a50: 61 6c 75 65 20 3d 20 67 65 74 65 6e 76 28 7a 4e  alue = getenv(zN
8a60: 61 6d 65 29 3b 0a 23 65 6e 64 69 66 0a 20 20 69  ame);.#endif.  i
8a70: 66 28 20 7a 56 61 6c 75 65 20 29 20 7a 56 61 6c  f( zValue ) zVal
8a80: 75 65 20 3d 20 66 6f 73 73 69 6c 5f 70 61 74 68  ue = fossil_path
8a90: 5f 74 6f 5f 75 74 66 38 28 7a 56 61 6c 75 65 29  _to_utf8(zValue)
8aa0: 3b 0a 20 20 72 65 74 75 72 6e 20 7a 56 61 6c 75  ;.  return zValu
8ab0: 65 3b 0a 7d 0a 0a 2f 2a 0a 2a 2a 20 53 65 74 73  e;.}../*.** Sets
8ac0: 20 74 68 65 20 76 61 6c 75 65 20 6f 66 20 61 6e   the value of an
8ad0: 20 65 6e 76 69 72 6f 6e 6d 65 6e 74 20 76 61 72   environment var
8ae0: 69 61 62 6c 65 20 61 73 20 55 54 46 38 2e 0a 2a  iable as UTF8..*
8af0: 2f 0a 69 6e 74 20 66 6f 73 73 69 6c 5f 73 65 74  /.int fossil_set
8b00: 65 6e 76 28 63 6f 6e 73 74 20 63 68 61 72 20 2a  env(const char *
8b10: 7a 4e 61 6d 65 2c 20 63 6f 6e 73 74 20 63 68 61  zName, const cha
8b20: 72 20 2a 7a 56 61 6c 75 65 29 7b 0a 20 20 69 6e  r *zValue){.  in
8b30: 74 20 72 63 3b 0a 20 20 63 68 61 72 20 2a 7a 53  t rc;.  char *zS
8b40: 74 72 69 6e 67 20 3d 20 6d 70 72 69 6e 74 66 28  tring = mprintf(
8b50: 22 25 73 3d 25 73 22 2c 20 7a 4e 61 6d 65 2c 20  "%s=%s", zName, 
8b60: 7a 56 61 6c 75 65 29 3b 0a 23 69 66 64 65 66 20  zValue);.#ifdef 
8b70: 5f 57 49 4e 33 32 0a 20 20 77 63 68 61 72 5f 74  _WIN32.  wchar_t
8b80: 20 2a 75 53 74 72 69 6e 67 20 3d 20 66 6f 73 73   *uString = foss
8b90: 69 6c 5f 75 74 66 38 5f 74 6f 5f 75 6e 69 63 6f  il_utf8_to_unico
8ba0: 64 65 28 7a 53 74 72 69 6e 67 29 3b 0a 20 20 72  de(zString);.  r
8bb0: 63 20 3d 20 5f 77 70 75 74 65 6e 76 28 75 53 74  c = _wputenv(uSt
8bc0: 72 69 6e 67 29 3b 0a 20 20 66 6f 73 73 69 6c 5f  ring);.  fossil_
8bd0: 75 6e 69 63 6f 64 65 5f 66 72 65 65 28 75 53 74  unicode_free(uSt
8be0: 72 69 6e 67 29 3b 0a 20 20 66 6f 73 73 69 6c 5f  ring);.  fossil_
8bf0: 66 72 65 65 28 7a 53 74 72 69 6e 67 29 3b 0a 23  free(zString);.#
8c00: 65 6c 73 65 0a 20 20 72 63 20 3d 20 70 75 74 65  else.  rc = pute
8c10: 6e 76 28 7a 53 74 72 69 6e 67 29 3b 0a 20 20 2f  nv(zString);.  /
8c20: 2a 20 4e 4f 54 45 3a 20 43 61 6e 6e 6f 74 20 66  * NOTE: Cannot f
8c30: 72 65 65 20 74 68 65 20 73 74 72 69 6e 67 20 6f  ree the string o
8c40: 6e 20 50 4f 53 49 58 2e 20 2a 2f 0a 20 20 2f 2a  n POSIX. */.  /*
8c50: 20 66 6f 73 73 69 6c 5f 66 72 65 65 28 7a 53 74   fossil_free(zSt
8c60: 72 69 6e 67 29 3b 20 2a 2f 0a 23 65 6e 64 69 66  ring); */.#endif
8c70: 0a 20 20 72 65 74 75 72 6e 20 72 63 3b 0a 7d 0a  .  return rc;.}.
8c80: 0a 2f 2a 0a 2a 2a 20 4c 69 6b 65 20 66 6f 70 65  ./*.** Like fope
8c90: 6e 28 29 20 62 75 74 20 61 6c 77 61 79 73 20 74  n() but always t
8ca0: 61 6b 65 73 20 61 20 55 54 46 38 20 61 72 67 75  akes a UTF8 argu
8cb0: 6d 65 6e 74 2e 0a 2a 2f 0a 46 49 4c 45 20 2a 66  ment..*/.FILE *f
8cc0: 6f 73 73 69 6c 5f 66 6f 70 65 6e 28 63 6f 6e 73  ossil_fopen(cons
8cd0: 74 20 63 68 61 72 20 2a 7a 4e 61 6d 65 2c 20 63  t char *zName, c
8ce0: 6f 6e 73 74 20 63 68 61 72 20 2a 7a 4d 6f 64 65  onst char *zMode
8cf0: 29 7b 0a 23 69 66 64 65 66 20 5f 57 49 4e 33 32  ){.#ifdef _WIN32
8d00: 0a 20 20 77 63 68 61 72 5f 74 20 2a 75 4d 6f 64  .  wchar_t *uMod
8d10: 65 20 3d 20 66 6f 73 73 69 6c 5f 75 74 66 38 5f  e = fossil_utf8_
8d20: 74 6f 5f 75 6e 69 63 6f 64 65 28 7a 4d 6f 64 65  to_unicode(zMode
8d30: 29 3b 0a 20 20 77 63 68 61 72 5f 74 20 2a 75 4e  );.  wchar_t *uN
8d40: 61 6d 65 20 3d 20 66 6f 73 73 69 6c 5f 75 74 66  ame = fossil_utf
8d50: 38 5f 74 6f 5f 70 61 74 68 28 7a 4e 61 6d 65 2c  8_to_path(zName,
8d60: 20 30 29 3b 0a 20 20 46 49 4c 45 20 2a 66 20 3d   0);.  FILE *f =
8d70: 20 5f 77 66 6f 70 65 6e 28 75 4e 61 6d 65 2c 20   _wfopen(uName, 
8d80: 75 4d 6f 64 65 29 3b 0a 20 20 66 6f 73 73 69 6c  uMode);.  fossil
8d90: 5f 70 61 74 68 5f 66 72 65 65 28 75 4e 61 6d 65  _path_free(uName
8da0: 29 3b 0a 20 20 66 6f 73 73 69 6c 5f 75 6e 69 63  );.  fossil_unic
8db0: 6f 64 65 5f 66 72 65 65 28 75 4d 6f 64 65 29 3b  ode_free(uMode);
8dc0: 0a 23 65 6c 73 65 0a 20 20 46 49 4c 45 20 2a 66  .#else.  FILE *f
8dd0: 20 3d 20 66 6f 70 65 6e 28 7a 4e 61 6d 65 2c 20   = fopen(zName, 
8de0: 7a 4d 6f 64 65 29 3b 0a 23 65 6e 64 69 66 0a 20  zMode);.#endif. 
8df0: 20 72 65 74 75 72 6e 20 66 3b 0a 7d 0a            return f;.}.