0000: 2f 2a 0a 20 2a 20 43 6f 70 79 72 69 67 68 74 20 /*. * Copyright
0010: 28 63 29 20 32 30 31 34 2c 20 32 30 31 35 20 20 (c) 2014, 2015
0020: 52 6f 79 20 4b 65 65 6e 65 0a 20 2a 0a 20 2a 20 Roy Keene. *. *
0030: 50 65 72 6d 69 73 73 69 6f 6e 20 69 73 20 68 65 Permission is he
0040: 72 65 62 79 20 67 72 61 6e 74 65 64 2c 20 66 72 reby granted, fr
0050: 65 65 20 6f 66 20 63 68 61 72 67 65 2c 20 74 6f ee of charge, to
0060: 20 61 6e 79 20 70 65 72 73 6f 6e 20 6f 62 74 61 any person obta
0070: 69 6e 69 6e 67 20 61 20 63 6f 70 79 0a 20 2a 20 ining a copy. *
0080: 6f 66 20 74 68 69 73 20 73 6f 66 74 77 61 72 65 of this software
0090: 20 61 6e 64 20 61 73 73 6f 63 69 61 74 65 64 20 and associated
00a0: 64 6f 63 75 6d 65 6e 74 61 74 69 6f 6e 20 66 69 documentation fi
00b0: 6c 65 73 20 28 74 68 65 20 22 53 6f 66 74 77 61 les (the "Softwa
00c0: 72 65 22 29 2c 20 74 6f 20 64 65 61 6c 0a 20 2a re"), to deal. *
00d0: 20 69 6e 20 74 68 65 20 53 6f 66 74 77 61 72 65 in the Software
00e0: 20 77 69 74 68 6f 75 74 20 72 65 73 74 72 69 63 without restric
00f0: 74 69 6f 6e 2c 20 69 6e 63 6c 75 64 69 6e 67 20 tion, including
0100: 77 69 74 68 6f 75 74 20 6c 69 6d 69 74 61 74 69 without limitati
0110: 6f 6e 20 74 68 65 20 72 69 67 68 74 73 0a 20 2a on the rights. *
0120: 20 74 6f 20 75 73 65 2c 20 63 6f 70 79 2c 20 6d to use, copy, m
0130: 6f 64 69 66 79 2c 20 6d 65 72 67 65 2c 20 70 75 odify, merge, pu
0140: 62 6c 69 73 68 2c 20 64 69 73 74 72 69 62 75 74 blish, distribut
0150: 65 2c 20 73 75 62 6c 69 63 65 6e 73 65 2c 20 61 e, sublicense, a
0160: 6e 64 2f 6f 72 20 73 65 6c 6c 0a 20 2a 20 63 6f nd/or sell. * co
0170: 70 69 65 73 20 6f 66 20 74 68 65 20 53 6f 66 74 pies of the Soft
0180: 77 61 72 65 2c 20 61 6e 64 20 74 6f 20 70 65 72 ware, and to per
0190: 6d 69 74 20 70 65 72 73 6f 6e 73 20 74 6f 20 77 mit persons to w
01a0: 68 6f 6d 20 74 68 65 20 53 6f 66 74 77 61 72 65 hom the Software
01b0: 20 69 73 0a 20 2a 20 66 75 72 6e 69 73 68 65 64 is. * furnished
01c0: 20 74 6f 20 64 6f 20 73 6f 2c 20 73 75 62 6a 65 to do so, subje
01d0: 63 74 20 74 6f 20 74 68 65 20 66 6f 6c 6c 6f 77 ct to the follow
01e0: 69 6e 67 20 63 6f 6e 64 69 74 69 6f 6e 73 3a 0a ing conditions:.
01f0: 20 2a 0a 20 2a 20 54 68 65 20 61 62 6f 76 65 20 *. * The above
0200: 63 6f 70 79 72 69 67 68 74 20 6e 6f 74 69 63 65 copyright notice
0210: 20 61 6e 64 20 74 68 69 73 20 70 65 72 6d 69 73 and this permis
0220: 73 69 6f 6e 20 6e 6f 74 69 63 65 20 73 68 61 6c sion notice shal
0230: 6c 20 62 65 20 69 6e 63 6c 75 64 65 64 20 69 6e l be included in
0240: 0a 20 2a 20 61 6c 6c 20 63 6f 70 69 65 73 20 6f . * all copies o
0250: 72 20 73 75 62 73 74 61 6e 74 69 61 6c 20 70 6f r substantial po
0260: 72 74 69 6f 6e 73 20 6f 66 20 74 68 65 20 53 6f rtions of the So
0270: 66 74 77 61 72 65 2e 0a 20 2a 0a 20 2a 20 54 48 ftware.. *. * TH
0280: 45 20 53 4f 46 54 57 41 52 45 20 49 53 20 50 52 E SOFTWARE IS PR
0290: 4f 56 49 44 45 44 20 22 41 53 20 49 53 22 2c 20 OVIDED "AS IS",
02a0: 57 49 54 48 4f 55 54 20 57 41 52 52 41 4e 54 59 WITHOUT WARRANTY
02b0: 20 4f 46 20 41 4e 59 20 4b 49 4e 44 2c 20 45 58 OF ANY KIND, EX
02c0: 50 52 45 53 53 20 4f 52 0a 20 2a 20 49 4d 50 4c PRESS OR. * IMPL
02d0: 49 45 44 2c 20 49 4e 43 4c 55 44 49 4e 47 20 42 IED, INCLUDING B
02e0: 55 54 20 4e 4f 54 20 4c 49 4d 49 54 45 44 20 54 UT NOT LIMITED T
02f0: 4f 20 54 48 45 20 57 41 52 52 41 4e 54 49 45 53 O THE WARRANTIES
0300: 20 4f 46 20 4d 45 52 43 48 41 4e 54 41 42 49 4c OF MERCHANTABIL
0310: 49 54 59 2c 0a 20 2a 20 46 49 54 4e 45 53 53 20 ITY,. * FITNESS
0320: 46 4f 52 20 41 20 50 41 52 54 49 43 55 4c 41 52 FOR A PARTICULAR
0330: 20 50 55 52 50 4f 53 45 20 41 4e 44 20 4e 4f 4e PURPOSE AND NON
0340: 49 4e 46 52 49 4e 47 45 4d 45 4e 54 2e 20 49 4e INFRINGEMENT. IN
0350: 20 4e 4f 20 45 56 45 4e 54 20 53 48 41 4c 4c 20 NO EVENT SHALL
0360: 54 48 45 0a 20 2a 20 41 55 54 48 4f 52 53 20 4f THE. * AUTHORS O
0370: 52 20 43 4f 50 59 52 49 47 48 54 20 48 4f 4c 44 R COPYRIGHT HOLD
0380: 45 52 53 20 42 45 20 4c 49 41 42 4c 45 20 46 4f ERS BE LIABLE FO
0390: 52 20 41 4e 59 20 43 4c 41 49 4d 2c 20 44 41 4d R ANY CLAIM, DAM
03a0: 41 47 45 53 20 4f 52 20 4f 54 48 45 52 0a 20 2a AGES OR OTHER. *
03b0: 20 4c 49 41 42 49 4c 49 54 59 2c 20 57 48 45 54 LIABILITY, WHET
03c0: 48 45 52 20 49 4e 20 41 4e 20 41 43 54 49 4f 4e HER IN AN ACTION
03d0: 20 4f 46 20 43 4f 4e 54 52 41 43 54 2c 20 54 4f OF CONTRACT, TO
03e0: 52 54 20 4f 52 20 4f 54 48 45 52 57 49 53 45 2c RT OR OTHERWISE,
03f0: 20 41 52 49 53 49 4e 47 20 46 52 4f 4d 2c 0a 20 ARISING FROM,.
0400: 2a 20 4f 55 54 20 4f 46 20 4f 52 20 49 4e 20 43 * OUT OF OR IN C
0410: 4f 4e 4e 45 43 54 49 4f 4e 20 57 49 54 48 20 54 ONNECTION WITH T
0420: 48 45 20 53 4f 46 54 57 41 52 45 20 4f 52 20 54 HE SOFTWARE OR T
0430: 48 45 20 55 53 45 20 4f 52 20 4f 54 48 45 52 20 HE USE OR OTHER
0440: 44 45 41 4c 49 4e 47 53 20 49 4e 0a 20 2a 20 54 DEALINGS IN. * T
0450: 48 45 20 53 4f 46 54 57 41 52 45 2e 0a 20 2a 2f HE SOFTWARE.. */
0460: 0a 23 64 65 66 69 6e 65 20 46 55 53 45 5f 55 53 .#define FUSE_US
0470: 45 5f 56 45 52 53 49 4f 4e 20 32 36 0a 0a 23 69 E_VERSION 26..#i
0480: 6e 63 6c 75 64 65 20 3c 73 79 73 2f 72 65 73 6f nclude <sys/reso
0490: 75 72 63 65 2e 68 3e 20 20 0a 23 69 6e 63 6c 75 urce.h> .#inclu
04a0: 64 65 20 3c 73 79 73 2f 66 73 75 69 64 2e 68 3e de <sys/fsuid.h>
04b0: 0a 23 69 6e 63 6c 75 64 65 20 3c 73 79 73 2f 74 .#include <sys/t
04c0: 79 70 65 73 2e 68 3e 0a 23 69 6e 63 6c 75 64 65 ypes.h>.#include
04d0: 20 3c 73 79 73 2f 74 69 6d 65 2e 68 3e 0a 23 69 <sys/time.h>.#i
04e0: 6e 63 6c 75 64 65 20 3c 70 74 68 72 65 61 64 2e nclude <pthread.
04f0: 68 3e 0a 23 69 6e 63 6c 75 64 65 20 3c 73 69 67 h>.#include <sig
0500: 6e 61 6c 2e 68 3e 0a 23 69 6e 63 6c 75 64 65 20 nal.h>.#include
0510: 3c 6c 69 6d 69 74 73 2e 68 3e 0a 23 69 6e 63 6c <limits.h>.#incl
0520: 75 64 65 20 3c 73 74 72 69 6e 67 2e 68 3e 0a 23 ude <string.h>.#
0530: 69 6e 63 6c 75 64 65 20 3c 73 74 64 61 72 67 2e include <stdarg.
0540: 68 3e 0a 23 69 6e 63 6c 75 64 65 20 3c 73 74 64 h>.#include <std
0550: 6c 69 62 2e 68 3e 0a 23 69 6e 63 6c 75 64 65 20 lib.h>.#include
0560: 3c 75 6e 69 73 74 64 2e 68 3e 0a 23 69 6e 63 6c <unistd.h>.#incl
0570: 75 64 65 20 3c 65 72 72 6e 6f 2e 68 3e 0a 23 69 ude <errno.h>.#i
0580: 6e 63 6c 75 64 65 20 3c 66 63 6e 74 6c 2e 68 3e nclude <fcntl.h>
0590: 0a 23 69 6e 63 6c 75 64 65 20 3c 73 74 64 69 6f .#include <stdio
05a0: 2e 68 3e 0a 23 69 6e 63 6c 75 64 65 20 3c 66 75 .h>.#include <fu
05b0: 73 65 2e 68 3e 0a 23 69 6e 63 6c 75 64 65 20 3c se.h>.#include <
05c0: 70 77 64 2e 68 3e 0a 23 69 6e 63 6c 75 64 65 20 pwd.h>.#include
05d0: 3c 74 63 6c 2e 68 3e 0a 0a 2f 2a 0a 20 2a 20 44 <tcl.h>../*. * D
05e0: 65 66 61 75 6c 74 20 63 61 63 68 65 20 64 69 72 efault cache dir
05f0: 65 63 74 6f 72 79 0a 20 2a 2f 0a 23 69 66 6e 64 ectory. */.#ifnd
0600: 65 66 20 41 50 50 46 53 5f 43 41 43 48 45 44 49 ef APPFS_CACHEDI
0610: 52 0a 23 64 65 66 69 6e 65 20 41 50 50 46 53 5f R.#define APPFS_
0620: 43 41 43 48 45 44 49 52 20 22 2f 76 61 72 2f 63 CACHEDIR "/var/c
0630: 61 63 68 65 2f 61 70 70 66 73 22 0a 23 65 6e 64 ache/appfs".#end
0640: 69 66 0a 0a 2f 2a 20 44 65 62 75 67 67 69 6e 67 if../* Debugging
0650: 20 6d 61 63 72 6f 73 20 2a 2f 0a 23 69 66 64 65 macros */.#ifde
0660: 66 20 44 45 42 55 47 0a 69 6e 74 20 61 70 70 66 f DEBUG.int appf
0670: 73 5f 64 65 62 75 67 5f 66 64 20 3d 20 53 54 44 s_debug_fd = STD
0680: 45 52 52 5f 46 49 4c 45 4e 4f 3b 0a 23 64 65 66 ERR_FILENO;.#def
0690: 69 6e 65 20 41 50 50 46 53 5f 44 45 42 55 47 28 ine APPFS_DEBUG(
06a0: 78 2e 2e 2e 29 20 7b 20 5c 0a 09 63 68 61 72 20 x...) { \..char
06b0: 62 75 66 5b 38 31 39 32 5d 3b 20 5c 0a 09 69 6e buf[8192]; \..in
06c0: 74 20 62 75 66 6f 66 66 20 3d 20 30 3b 20 5c 0a t bufoff = 0; \.
06d0: 09 69 66 20 28 61 70 70 66 73 5f 64 65 62 75 67 .if (appfs_debug
06e0: 5f 66 64 20 3d 3d 20 2d 31 29 20 7b 20 5c 0a 09 _fd == -1) { \..
06f0: 09 61 70 70 66 73 5f 64 65 62 75 67 5f 66 64 20 .appfs_debug_fd
0700: 3d 20 6f 70 65 6e 28 22 2f 74 6d 70 2f 61 70 70 = open("/tmp/app
0710: 66 73 64 2e 6c 6f 67 22 2c 20 4f 5f 57 52 4f 4e fsd.log", O_WRON
0720: 4c 59 20 7c 20 4f 5f 41 50 50 45 4e 44 20 7c 20 LY | O_APPEND |
0730: 4f 5f 43 52 45 41 54 2c 20 30 36 30 30 29 3b 20 O_CREAT, 0600);
0740: 5c 0a 09 7d 3b 20 5c 0a 09 62 75 66 6f 66 66 20 \..}; \..bufoff
0750: 3d 20 73 6e 70 72 69 6e 74 66 28 62 75 66 2c 20 = snprintf(buf,
0760: 73 69 7a 65 6f 66 28 62 75 66 29 2c 20 22 5b 64 sizeof(buf), "[d
0770: 65 62 75 67 5d 20 5b 74 3d 25 6c 6c 78 5d 20 25 ebug] [t=%llx] %
0780: 73 3a 25 69 3a 25 73 3a 20 22 2c 20 28 75 6e 73 s:%i:%s: ", (uns
0790: 69 67 6e 65 64 20 6c 6f 6e 67 20 6c 6f 6e 67 29 igned long long)
07a0: 20 70 74 68 72 65 61 64 5f 73 65 6c 66 28 29 2c pthread_self(),
07b0: 20 5f 5f 46 49 4c 45 5f 5f 2c 20 5f 5f 4c 49 4e __FILE__, __LIN
07c0: 45 5f 5f 2c 20 5f 5f 66 75 6e 63 5f 5f 29 3b 20 E__, __func__);
07d0: 5c 0a 09 69 66 20 28 62 75 66 6f 66 66 20 3c 20 \..if (bufoff <
07e0: 73 69 7a 65 6f 66 28 62 75 66 29 29 20 7b 20 5c sizeof(buf)) { \
07f0: 0a 09 09 62 75 66 6f 66 66 20 2b 3d 20 73 6e 70 ...bufoff += snp
0800: 72 69 6e 74 66 28 62 75 66 20 2b 20 62 75 66 6f rintf(buf + bufo
0810: 66 66 2c 20 73 69 7a 65 6f 66 28 62 75 66 29 20 ff, sizeof(buf)
0820: 2d 20 62 75 66 6f 66 66 2c 20 78 29 3b 20 5c 0a - bufoff, x); \.
0830: 09 7d 3b 20 5c 0a 09 69 66 20 28 62 75 66 6f 66 .}; \..if (bufof
0840: 66 20 3c 20 73 69 7a 65 6f 66 28 62 75 66 29 29 f < sizeof(buf))
0850: 20 7b 20 5c 0a 09 09 62 75 66 6f 66 66 20 2b 3d { \...bufoff +=
0860: 20 73 6e 70 72 69 6e 74 66 28 62 75 66 20 2b 20 snprintf(buf +
0870: 62 75 66 6f 66 66 2c 20 73 69 7a 65 6f 66 28 62 bufoff, sizeof(b
0880: 75 66 29 20 2d 20 62 75 66 6f 66 66 2c 20 22 5c uf) - bufoff, "\
0890: 6e 22 29 3b 5c 0a 09 7d 20 5c 0a 09 69 66 20 28 n");\..} \..if (
08a0: 62 75 66 6f 66 66 20 3e 20 73 69 7a 65 6f 66 28 bufoff > sizeof(
08b0: 62 75 66 29 29 20 7b 20 5c 0a 09 09 62 75 66 6f buf)) { \...bufo
08c0: 66 66 20 3d 20 73 69 7a 65 6f 66 28 62 75 66 29 ff = sizeof(buf)
08d0: 3b 20 5c 0a 09 7d 3b 20 5c 0a 09 77 72 69 74 65 ; \..}; \..write
08e0: 28 61 70 70 66 73 5f 64 65 62 75 67 5f 66 64 2c (appfs_debug_fd,
08f0: 20 62 75 66 2c 20 62 75 66 6f 66 66 29 3b 20 5c buf, bufoff); \
0900: 0a 7d 0a 23 65 6c 73 65 0a 23 64 65 66 69 6e 65 .}.#else.#define
0910: 20 41 50 50 46 53 5f 44 45 42 55 47 28 78 2e 2e APPFS_DEBUG(x..
0920: 2e 29 20 2f 2a 2a 2f 0a 23 65 6e 64 69 66 0a 0a .) /**/.#endif..
0930: 2f 2a 0a 20 2a 20 53 48 41 31 20 54 63 6c 20 50 /*. * SHA1 Tcl P
0940: 61 63 6b 61 67 65 20 69 6e 69 74 69 61 6c 69 7a ackage initializ
0950: 65 72 2c 20 66 72 6f 6d 20 73 68 61 31 2e 6f 0a er, from sha1.o.
0960: 20 2a 2f 0a 69 6e 74 20 53 68 61 31 5f 49 6e 69 */.int Sha1_Ini
0970: 74 28 54 63 6c 5f 49 6e 74 65 72 70 20 2a 69 6e t(Tcl_Interp *in
0980: 74 65 72 70 29 3b 0a 0a 2f 2a 0a 20 2a 20 54 68 terp);../*. * Th
0990: 72 65 61 64 20 53 70 65 63 69 66 69 63 20 44 61 read Specific Da
09a0: 74 61 20 28 54 53 44 29 20 66 6f 72 20 54 63 6c ta (TSD) for Tcl
09b0: 20 49 6e 74 65 72 70 72 65 74 65 72 20 66 6f 72 Interpreter for
09c0: 20 74 68 65 20 63 75 72 72 65 6e 74 20 74 68 72 the current thr
09d0: 65 61 64 0a 20 2a 2f 0a 73 74 61 74 69 63 20 70 ead. */.static p
09e0: 74 68 72 65 61 64 5f 6b 65 79 5f 74 20 69 6e 74 thread_key_t int
09f0: 65 72 70 4b 65 79 3b 0a 0a 2f 2a 0a 20 2a 20 47 erpKey;../*. * G
0a00: 6c 6f 62 61 6c 20 76 61 72 69 61 62 6c 65 73 2c lobal variables,
0a10: 20 6e 65 65 64 65 64 20 66 6f 72 20 61 6c 6c 20 needed for all
0a20: 74 68 72 65 61 64 73 20 62 75 74 20 6f 6e 6c 79 threads but only
0a30: 20 69 6e 69 74 69 61 6c 69 7a 65 64 20 62 65 66 initialized bef
0a40: 6f 72 65 20 61 6e 79 0a 20 2a 20 46 55 53 45 20 ore any. * FUSE
0a50: 74 68 72 65 61 64 73 20 61 72 65 20 63 72 65 61 threads are crea
0a60: 74 65 64 0a 20 2a 2f 0a 63 6f 6e 73 74 20 63 68 ted. */.const ch
0a70: 61 72 20 2a 61 70 70 66 73 5f 63 61 63 68 65 64 ar *appfs_cached
0a80: 69 72 3b 0a 74 69 6d 65 5f 74 20 61 70 70 66 73 ir;.time_t appfs
0a90: 5f 62 6f 6f 74 74 69 6d 65 3b 0a 69 6e 74 20 61 _boottime;.int a
0aa0: 70 70 66 73 5f 66 75 73 65 5f 73 74 61 72 74 65 ppfs_fuse_starte
0ab0: 64 20 3d 20 30 3b 0a 69 6e 74 20 61 70 70 66 73 d = 0;.int appfs
0ac0: 5f 74 68 72 65 61 64 65 64 5f 74 63 6c 3b 0a 0a _threaded_tcl;..
0ad0: 2f 2a 0a 20 2a 20 47 6c 6f 62 61 6c 20 76 61 72 /*. * Global var
0ae0: 69 61 62 6c 65 73 20 66 6f 72 20 41 70 70 46 53 iables for AppFS
0af0: 20 63 61 63 68 69 6e 67 0a 20 2a 2f 0a 70 74 68 caching. */.pth
0b00: 72 65 61 64 5f 6d 75 74 65 78 5f 74 20 61 70 70 read_mutex_t app
0b10: 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 fs_path_info_cac
0b20: 68 65 5f 6d 75 74 65 78 20 3d 20 50 54 48 52 45 he_mutex = PTHRE
0b30: 41 44 5f 4d 55 54 45 58 5f 49 4e 49 54 49 41 4c AD_MUTEX_INITIAL
0b40: 49 5a 45 52 3b 0a 69 6e 74 20 61 70 70 66 73 5f IZER;.int appfs_
0b50: 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5f path_info_cache_
0b60: 73 69 7a 65 20 3d 20 38 32 30 39 3b 0a 73 74 72 size = 8209;.str
0b70: 75 63 74 20 61 70 70 66 73 5f 70 61 74 68 69 6e uct appfs_pathin
0b80: 66 6f 20 2a 61 70 70 66 73 5f 70 61 74 68 5f 69 fo *appfs_path_i
0b90: 6e 66 6f 5f 63 61 63 68 65 20 3d 20 4e 55 4c 4c nfo_cache = NULL
0ba0: 3b 0a 0a 23 69 66 6e 64 65 66 20 54 43 4c 5f 54 ;..#ifndef TCL_T
0bb0: 48 52 45 41 44 53 0a 2f 2a 0a 20 2a 20 48 61 6e HREADS./*. * Han
0bc0: 64 6c 65 20 75 6e 74 68 72 65 61 64 65 64 20 54 dle unthreaded T
0bd0: 63 6c 0a 20 2a 2f 0a 70 74 68 72 65 61 64 5f 6d cl. */.pthread_m
0be0: 75 74 65 78 5f 74 20 61 70 70 66 73 5f 74 63 6c utex_t appfs_tcl
0bf0: 5f 62 69 67 5f 67 6c 6f 62 61 6c 5f 6c 6f 63 6b _big_global_lock
0c00: 20 3d 20 50 54 48 52 45 41 44 5f 4d 55 54 45 58 = PTHREAD_MUTEX
0c10: 5f 49 4e 49 54 49 41 4c 49 5a 45 52 3b 0a 23 64 _INITIALIZER;.#d
0c20: 65 66 69 6e 65 20 61 70 70 66 73 5f 63 61 6c 6c efine appfs_call
0c30: 5f 6c 69 62 74 63 6c 5f 65 6e 74 65 72 20 70 74 _libtcl_enter pt
0c40: 68 72 65 61 64 5f 6d 75 74 65 78 5f 6c 6f 63 6b hread_mutex_lock
0c50: 28 26 61 70 70 66 73 5f 74 63 6c 5f 62 69 67 5f (&appfs_tcl_big_
0c60: 67 6c 6f 62 61 6c 5f 6c 6f 63 6b 29 3b 0a 23 64 global_lock);.#d
0c70: 65 66 69 6e 65 20 61 70 70 66 73 5f 63 61 6c 6c efine appfs_call
0c80: 5f 6c 69 62 74 63 6c 5f 65 78 69 74 20 70 74 68 _libtcl_exit pth
0c90: 72 65 61 64 5f 6d 75 74 65 78 5f 75 6e 6c 6f 63 read_mutex_unloc
0ca0: 6b 28 26 61 70 70 66 73 5f 74 63 6c 5f 62 69 67 k(&appfs_tcl_big
0cb0: 5f 67 6c 6f 62 61 6c 5f 6c 6f 63 6b 29 3b 0a 23 _global_lock);.#
0cc0: 65 6c 73 65 0a 23 64 65 66 69 6e 65 20 61 70 70 else.#define app
0cd0: 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 5f 65 fs_call_libtcl_e
0ce0: 6e 74 65 72 20 2f 2a 2a 2f 0a 23 64 65 66 69 6e nter /**/.#defin
0cf0: 65 20 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 e appfs_call_lib
0d00: 74 63 6c 5f 65 78 69 74 20 2f 2a 2a 2f 0a 23 65 tcl_exit /**/.#e
0d10: 6e 64 69 66 0a 23 64 65 66 69 6e 65 20 61 70 70 ndif.#define app
0d20: 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 78 fs_call_libtcl(x
0d30: 2e 2e 2e 29 20 61 70 70 66 73 5f 63 61 6c 6c 5f ...) appfs_call_
0d40: 6c 69 62 74 63 6c 5f 65 6e 74 65 72 20 78 20 61 libtcl_enter x a
0d50: 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c ppfs_call_libtcl
0d60: 5f 65 78 69 74 0a 0a 2f 2a 0a 20 2a 20 47 6c 6f _exit../*. * Glo
0d70: 62 61 6c 20 76 61 72 69 61 62 6c 65 73 20 66 6f bal variables fo
0d80: 72 20 41 70 70 46 53 20 54 63 6c 20 49 6e 74 65 r AppFS Tcl Inte
0d90: 72 70 72 65 74 65 72 20 72 65 73 74 61 72 74 69 rpreter restarti
0da0: 6e 67 0a 20 2a 2f 0a 69 6e 74 20 69 6e 74 65 72 ng. */.int inter
0db0: 70 5f 72 65 73 65 74 5f 6b 65 79 20 3d 20 30 3b p_reset_key = 0;
0dc0: 0a 0a 2f 2a 0a 20 2a 20 41 70 70 46 53 20 50 61 ../*. * AppFS Pa
0dd0: 74 68 20 54 79 70 65 3a 20 20 44 65 73 63 72 69 th Type: Descri
0de0: 62 65 73 20 74 68 65 20 74 79 70 65 20 6f 66 20 bes the type of
0df0: 70 61 74 68 20 61 20 67 69 76 65 6e 20 66 69 6c path a given fil
0e00: 65 20 69 73 0a 20 2a 2f 0a 74 79 70 65 64 65 66 e is. */.typedef
0e10: 20 65 6e 75 6d 20 7b 0a 09 41 50 50 46 53 5f 50 enum {..APPFS_P
0e20: 41 54 48 54 59 50 45 5f 49 4e 56 41 4c 49 44 2c ATHTYPE_INVALID,
0e30: 0a 09 41 50 50 46 53 5f 50 41 54 48 54 59 50 45 ..APPFS_PATHTYPE
0e40: 5f 44 4f 45 53 5f 4e 4f 54 5f 45 58 49 53 54 2c _DOES_NOT_EXIST,
0e50: 0a 09 41 50 50 46 53 5f 50 41 54 48 54 59 50 45 ..APPFS_PATHTYPE
0e60: 5f 46 49 4c 45 2c 0a 09 41 50 50 46 53 5f 50 41 _FILE,..APPFS_PA
0e70: 54 48 54 59 50 45 5f 44 49 52 45 43 54 4f 52 59 THTYPE_DIRECTORY
0e80: 2c 0a 09 41 50 50 46 53 5f 50 41 54 48 54 59 50 ,..APPFS_PATHTYP
0e90: 45 5f 53 59 4d 4c 49 4e 4b 2c 0a 09 41 50 50 46 E_SYMLINK,..APPF
0ea0: 53 5f 50 41 54 48 54 59 50 45 5f 53 4f 43 4b 45 S_PATHTYPE_SOCKE
0eb0: 54 2c 0a 09 41 50 50 46 53 5f 50 41 54 48 54 59 T,..APPFS_PATHTY
0ec0: 50 45 5f 46 49 46 4f 2c 0a 7d 20 61 70 70 66 73 PE_FIFO,.} appfs
0ed0: 5f 70 61 74 68 74 79 70 65 5f 74 3b 0a 0a 2f 2a _pathtype_t;../*
0ee0: 0a 20 2a 20 41 70 70 46 53 20 50 61 74 68 20 49 . * AppFS Path I
0ef0: 6e 66 6f 72 6d 61 74 69 6f 6e 3a 0a 20 2a 20 20 nformation:. *
0f00: 20 20 20 20 20 20 20 43 6f 6d 70 6c 65 74 65 6c Completel
0f10: 79 20 64 65 73 63 72 69 62 65 73 20 61 20 73 70 y describes a sp
0f20: 65 63 69 66 69 63 20 70 61 74 68 2c 20 68 6f 77 ecific path, how
0f30: 20 69 74 20 73 68 6f 75 6c 64 20 62 65 20 72 65 it should be re
0f40: 74 75 72 6e 65 64 20 74 6f 0a 20 2a 20 20 20 20 turned to. *
0f50: 20 20 20 20 20 74 6f 20 74 68 65 20 6b 65 72 6e to the kern
0f60: 65 6c 0a 20 2a 2f 0a 73 74 72 75 63 74 20 61 70 el. */.struct ap
0f70: 70 66 73 5f 70 61 74 68 69 6e 66 6f 20 7b 0a 09 pfs_pathinfo {..
0f80: 61 70 70 66 73 5f 70 61 74 68 74 79 70 65 5f 74 appfs_pathtype_t
0f90: 20 74 79 70 65 3b 0a 09 74 69 6d 65 5f 74 20 74 type;..time_t t
0fa0: 69 6d 65 3b 0a 09 63 68 61 72 20 68 6f 73 74 6e ime;..char hostn
0fb0: 61 6d 65 5b 32 35 36 5d 3b 0a 09 69 6e 74 20 70 ame[256];..int p
0fc0: 61 63 6b 61 67 65 64 3b 0a 09 75 6e 73 69 67 6e ackaged;..unsign
0fd0: 65 64 20 6c 6f 6e 67 20 6c 6f 6e 67 20 69 6e 6f ed long long ino
0fe0: 64 65 3b 0a 09 75 6e 69 6f 6e 20 7b 0a 09 09 73 de;..union {...s
0ff0: 74 72 75 63 74 20 7b 0a 09 09 09 69 6e 74 20 63 truct {....int c
1000: 68 69 6c 64 63 6f 75 6e 74 3b 0a 09 09 7d 20 64 hildcount;...} d
1010: 69 72 3b 0a 09 09 73 74 72 75 63 74 20 7b 0a 09 ir;...struct {..
1020: 09 09 69 6e 74 20 65 78 65 63 75 74 61 62 6c 65 ..int executable
1030: 3b 0a 09 09 09 69 6e 74 20 73 75 69 64 52 6f 6f ;....int suidRoo
1040: 74 3b 0a 09 09 09 69 6e 74 20 77 6f 72 6c 64 61 t;....int worlda
1050: 63 63 65 73 73 69 62 6c 65 3b 0a 09 09 09 6f 66 ccessible;....of
1060: 66 5f 74 20 73 69 7a 65 3b 0a 09 09 7d 20 66 69 f_t size;...} fi
1070: 6c 65 3b 0a 09 09 73 74 72 75 63 74 20 7b 0a 09 le;...struct {..
1080: 09 09 6f 66 66 5f 74 20 73 69 7a 65 3b 0a 09 09 ..off_t size;...
1090: 09 63 68 61 72 20 73 6f 75 72 63 65 5b 32 35 36 .char source[256
10a0: 5d 3b 0a 09 09 7d 20 73 79 6d 6c 69 6e 6b 3b 0a ];...} symlink;.
10b0: 09 7d 20 74 79 70 65 69 6e 66 6f 3b 0a 0a 09 2f .} typeinfo;.../
10c0: 2a 20 41 74 74 72 69 62 75 74 65 73 20 75 73 65 * Attributes use
10d0: 64 20 6f 6e 6c 79 20 66 6f 72 20 63 61 63 68 69 d only for cachi
10e0: 6e 67 20 65 6e 74 72 69 65 73 20 2a 2f 0a 09 63 ng entries */..c
10f0: 68 61 72 20 2a 5f 63 61 63 68 65 5f 70 61 74 68 har *_cache_path
1100: 3b 0a 09 75 69 64 5f 74 20 5f 63 61 63 68 65 5f ;..uid_t _cache_
1110: 75 69 64 3b 0a 7d 3b 0a 0a 2f 2a 0a 20 2a 20 43 uid;.};../*. * C
1120: 72 65 61 74 65 20 61 20 6e 65 77 20 54 63 6c 20 reate a new Tcl
1130: 69 6e 74 65 72 70 72 65 74 65 72 20 61 6e 64 20 interpreter and
1140: 63 6f 6d 70 6c 65 74 65 6c 79 20 69 6e 69 74 69 completely initi
1150: 61 6c 69 7a 65 20 69 74 0a 20 2a 2f 0a 73 74 61 alize it. */.sta
1160: 74 69 63 20 54 63 6c 5f 49 6e 74 65 72 70 20 2a tic Tcl_Interp *
1170: 61 70 70 66 73 5f 63 72 65 61 74 65 5f 54 63 6c appfs_create_Tcl
1180: 49 6e 74 65 72 70 28 63 68 61 72 20 2a 2a 65 72 Interp(char **er
1190: 72 6f 72 5f 73 74 72 69 6e 67 29 20 7b 0a 09 54 ror_string) {..T
11a0: 63 6c 5f 49 6e 74 65 72 70 20 2a 69 6e 74 65 72 cl_Interp *inter
11b0: 70 3b 0a 09 69 6e 74 20 74 63 6c 5f 72 65 74 3b p;..int tcl_ret;
11c0: 0a 09 63 6f 6e 73 74 20 63 68 61 72 20 2a 74 63 ..const char *tc
11d0: 6c 5f 73 65 74 76 61 72 5f 72 65 74 3b 0a 0a 09 l_setvar_ret;...
11e0: 41 50 50 46 53 5f 44 45 42 55 47 28 22 43 72 65 APPFS_DEBUG("Cre
11f0: 61 74 69 6e 67 20 6e 65 77 20 54 63 6c 20 69 6e ating new Tcl in
1200: 74 65 72 70 72 65 74 65 72 20 66 6f 72 20 54 49 terpreter for TI
1210: 44 20 3d 20 30 78 25 6c 6c 78 22 2c 20 28 75 6e D = 0x%llx", (un
1220: 73 69 67 6e 65 64 20 6c 6f 6e 67 20 6c 6f 6e 67 signed long long
1230: 29 20 70 74 68 72 65 61 64 5f 73 65 6c 66 28 29 ) pthread_self()
1240: 29 3b 0a 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f );...appfs_call_
1250: 6c 69 62 74 63 6c 28 0a 09 09 69 6e 74 65 72 70 libtcl(...interp
1260: 20 3d 20 54 63 6c 5f 43 72 65 61 74 65 49 6e 74 = Tcl_CreateInt
1270: 65 72 70 28 29 3b 0a 09 29 0a 09 69 66 20 28 69 erp();..)..if (i
1280: 6e 74 65 72 70 20 3d 3d 20 4e 55 4c 4c 29 20 7b nterp == NULL) {
1290: 0a 09 09 66 70 72 69 6e 74 66 28 73 74 64 65 72 ...fprintf(stder
12a0: 72 2c 20 22 55 6e 61 62 6c 65 20 74 6f 20 63 72 r, "Unable to cr
12b0: 65 61 74 65 20 54 63 6c 20 49 6e 74 65 72 70 72 eate Tcl Interpr
12c0: 65 74 65 72 2e 20 20 41 62 6f 72 74 69 6e 67 2e eter. Aborting.
12d0: 5c 6e 22 29 3b 0a 0a 09 09 69 66 20 28 65 72 72 \n");....if (err
12e0: 6f 72 5f 73 74 72 69 6e 67 29 20 7b 0a 09 09 09 or_string) {....
12f0: 2a 65 72 72 6f 72 5f 73 74 72 69 6e 67 20 3d 20 *error_string =
1300: 73 74 72 64 75 70 28 22 55 6e 61 62 6c 65 20 74 strdup("Unable t
1310: 6f 20 63 72 65 61 74 65 20 54 63 6c 20 69 6e 74 o create Tcl int
1320: 65 72 70 72 65 74 65 72 2e 22 29 3b 0a 09 09 7d erpreter.");...}
1330: 0a 0a 09 09 72 65 74 75 72 6e 28 4e 55 4c 4c 29 ....return(NULL)
1340: 3b 0a 09 7d 0a 0a 09 61 70 70 66 73 5f 63 61 6c ;..}...appfs_cal
1350: 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 50 72 65 l_libtcl(Tcl_Pre
1360: 73 65 72 76 65 28 69 6e 74 65 72 70 29 3b 29 0a serve(interp);).
1370: 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 ..appfs_call_lib
1380: 74 63 6c 28 0a 09 09 74 63 6c 5f 72 65 74 20 3d tcl(...tcl_ret =
1390: 20 54 63 6c 5f 49 6e 69 74 28 69 6e 74 65 72 70 Tcl_Init(interp
13a0: 29 3b 0a 09 29 0a 09 69 66 20 28 74 63 6c 5f 72 );..)..if (tcl_r
13b0: 65 74 20 21 3d 20 54 43 4c 5f 4f 4b 29 20 7b 0a et != TCL_OK) {.
13c0: 09 09 66 70 72 69 6e 74 66 28 73 74 64 65 72 72 ..fprintf(stderr
13d0: 2c 20 22 55 6e 61 62 6c 65 20 74 6f 20 69 6e 69 , "Unable to ini
13e0: 74 69 61 6c 69 7a 65 20 54 63 6c 2e 20 20 41 62 tialize Tcl. Ab
13f0: 6f 72 74 69 6e 67 2e 5c 6e 22 29 3b 0a 09 09 61 orting.\n");...a
1400: 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c ppfs_call_libtcl
1410: 28 0a 09 09 09 66 70 72 69 6e 74 66 28 73 74 64 (....fprintf(std
1420: 65 72 72 2c 20 22 54 63 6c 20 45 72 72 6f 72 20 err, "Tcl Error
1430: 69 73 3a 20 25 73 5c 6e 22 2c 20 54 63 6c 5f 47 is: %s\n", Tcl_G
1440: 65 74 53 74 72 69 6e 67 52 65 73 75 6c 74 28 69 etStringResult(i
1450: 6e 74 65 72 70 29 29 3b 0a 09 09 29 0a 0a 09 09 nterp));...)....
1460: 69 66 20 28 65 72 72 6f 72 5f 73 74 72 69 6e 67 if (error_string
1470: 29 20 7b 0a 09 09 09 61 70 70 66 73 5f 63 61 6c ) {....appfs_cal
1480: 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 09 09 2a 65 l_libtcl(.....*e
1490: 72 72 6f 72 5f 73 74 72 69 6e 67 20 3d 20 73 74 rror_string = st
14a0: 72 64 75 70 28 54 63 6c 5f 47 65 74 53 74 72 69 rdup(Tcl_GetStri
14b0: 6e 67 52 65 73 75 6c 74 28 69 6e 74 65 72 70 29 ngResult(interp)
14c0: 29 3b 0a 09 09 09 29 0a 09 09 7d 0a 0a 09 09 61 );....)...}....a
14d0: 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c ppfs_call_libtcl
14e0: 28 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e 74 (Tcl_Release(int
14f0: 65 72 70 29 3b 29 0a 0a 09 09 41 50 50 46 53 5f erp);)....APPFS_
1500: 44 45 42 55 47 28 22 54 65 72 6d 69 6e 61 74 69 DEBUG("Terminati
1510: 6e 67 20 54 63 6c 20 69 6e 74 65 72 70 72 65 74 ng Tcl interpret
1520: 65 72 2e 22 29 3b 0a 0a 09 09 61 70 70 66 73 5f er.");....appfs_
1530: 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f call_libtcl(Tcl_
1540: 44 65 6c 65 74 65 49 6e 74 65 72 70 28 69 6e 74 DeleteInterp(int
1550: 65 72 70 29 3b 29 0a 0a 09 09 72 65 74 75 72 6e erp);)....return
1560: 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 61 70 70 (NULL);..}...app
1570: 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a fs_call_libtcl(.
1580: 09 09 74 63 6c 5f 72 65 74 20 3d 20 54 63 6c 5f ..tcl_ret = Tcl_
1590: 45 76 61 6c 28 69 6e 74 65 72 70 2c 20 22 70 61 Eval(interp, "pa
15a0: 63 6b 61 67 65 20 69 66 6e 65 65 64 65 64 20 73 ckage ifneeded s
15b0: 68 61 31 20 31 2e 30 20 5b 6c 69 73 74 20 6c 6f ha1 1.0 [list lo
15c0: 61 64 20 7b 7d 20 73 68 61 31 5d 22 29 3b 0a 09 ad {} sha1]");..
15d0: 29 0a 09 69 66 20 28 74 63 6c 5f 72 65 74 20 21 )..if (tcl_ret !
15e0: 3d 20 54 43 4c 5f 4f 4b 29 20 7b 0a 09 09 66 70 = TCL_OK) {...fp
15f0: 72 69 6e 74 66 28 73 74 64 65 72 72 2c 20 22 55 rintf(stderr, "U
1600: 6e 61 62 6c 65 20 74 6f 20 69 6e 69 74 69 61 6c nable to initial
1610: 69 7a 65 20 54 63 6c 20 53 48 41 31 2e 20 20 41 ize Tcl SHA1. A
1620: 62 6f 72 74 69 6e 67 2e 5c 6e 22 29 3b 0a 09 09 borting.\n");...
1630: 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 appfs_call_libtc
1640: 6c 28 0a 09 09 09 66 70 72 69 6e 74 66 28 73 74 l(....fprintf(st
1650: 64 65 72 72 2c 20 22 54 63 6c 20 45 72 72 6f 72 derr, "Tcl Error
1660: 20 69 73 3a 20 25 73 5c 6e 22 2c 20 54 63 6c 5f is: %s\n", Tcl_
1670: 47 65 74 53 74 72 69 6e 67 52 65 73 75 6c 74 28 GetStringResult(
1680: 69 6e 74 65 72 70 29 29 3b 0a 09 09 29 0a 0a 09 interp));...)...
1690: 09 69 66 20 28 65 72 72 6f 72 5f 73 74 72 69 6e .if (error_strin
16a0: 67 29 20 7b 0a 09 09 09 61 70 70 66 73 5f 63 61 g) {....appfs_ca
16b0: 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 09 09 2a ll_libtcl(.....*
16c0: 65 72 72 6f 72 5f 73 74 72 69 6e 67 20 3d 20 73 error_string = s
16d0: 74 72 64 75 70 28 54 63 6c 5f 47 65 74 53 74 72 trdup(Tcl_GetStr
16e0: 69 6e 67 52 65 73 75 6c 74 28 69 6e 74 65 72 70 ingResult(interp
16f0: 29 29 3b 0a 09 09 09 29 0a 09 09 7d 0a 0a 09 09 ));....)...}....
1700: 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 appfs_call_libtc
1710: 6c 28 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e l(Tcl_Release(in
1720: 74 65 72 70 29 3b 29 0a 0a 09 09 41 50 50 46 53 terp);)....APPFS
1730: 5f 44 45 42 55 47 28 22 54 65 72 6d 69 6e 61 74 _DEBUG("Terminat
1740: 69 6e 67 20 54 63 6c 20 69 6e 74 65 72 70 72 65 ing Tcl interpre
1750: 74 65 72 2e 22 29 3b 0a 0a 09 09 61 70 70 66 73 ter.");....appfs
1760: 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c _call_libtcl(Tcl
1770: 5f 44 65 6c 65 74 65 49 6e 74 65 72 70 28 69 6e _DeleteInterp(in
1780: 74 65 72 70 29 3b 29 0a 0a 09 09 72 65 74 75 72 terp);)....retur
1790: 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 61 70 n(NULL);..}...ap
17a0: 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 pfs_call_libtcl(
17b0: 0a 09 09 74 63 6c 5f 72 65 74 20 3d 20 54 63 6c ...tcl_ret = Tcl
17c0: 5f 45 76 61 6c 28 69 6e 74 65 72 70 2c 20 22 70 _Eval(interp, "p
17d0: 61 63 6b 61 67 65 20 69 66 6e 65 65 64 65 64 20 ackage ifneeded
17e0: 61 70 70 66 73 64 20 31 2e 30 20 5b 6c 69 73 74 appfsd 1.0 [list
17f0: 20 6c 6f 61 64 20 7b 7d 20 61 70 70 66 73 64 5d load {} appfsd]
1800: 22 29 3b 0a 09 29 0a 09 69 66 20 28 74 63 6c 5f ");..)..if (tcl_
1810: 72 65 74 20 21 3d 20 54 43 4c 5f 4f 4b 29 20 7b ret != TCL_OK) {
1820: 0a 09 09 66 70 72 69 6e 74 66 28 73 74 64 65 72 ...fprintf(stder
1830: 72 2c 20 22 55 6e 61 62 6c 65 20 74 6f 20 69 6e r, "Unable to in
1840: 69 74 69 61 6c 69 7a 65 20 54 63 6c 20 41 70 70 itialize Tcl App
1850: 46 53 20 50 61 63 6b 61 67 65 2e 20 20 41 62 6f FS Package. Abo
1860: 72 74 69 6e 67 2e 5c 6e 22 29 3b 0a 09 09 61 70 rting.\n");...ap
1870: 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 pfs_call_libtcl(
1880: 0a 09 09 09 66 70 72 69 6e 74 66 28 73 74 64 65 ....fprintf(stde
1890: 72 72 2c 20 22 54 63 6c 20 45 72 72 6f 72 20 69 rr, "Tcl Error i
18a0: 73 3a 20 25 73 5c 6e 22 2c 20 54 63 6c 5f 47 65 s: %s\n", Tcl_Ge
18b0: 74 53 74 72 69 6e 67 52 65 73 75 6c 74 28 69 6e tStringResult(in
18c0: 74 65 72 70 29 29 3b 0a 09 09 29 0a 0a 09 09 69 terp));...)....i
18d0: 66 20 28 65 72 72 6f 72 5f 73 74 72 69 6e 67 29 f (error_string)
18e0: 20 7b 0a 09 09 09 61 70 70 66 73 5f 63 61 6c 6c {....appfs_call
18f0: 5f 6c 69 62 74 63 6c 28 0a 09 09 09 09 2a 65 72 _libtcl(.....*er
1900: 72 6f 72 5f 73 74 72 69 6e 67 20 3d 20 73 74 72 ror_string = str
1910: 64 75 70 28 54 63 6c 5f 47 65 74 53 74 72 69 6e dup(Tcl_GetStrin
1920: 67 52 65 73 75 6c 74 28 69 6e 74 65 72 70 29 29 gResult(interp))
1930: 3b 0a 09 09 09 29 0a 09 09 7d 0a 0a 09 09 61 70 ;....)...}....ap
1940: 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 pfs_call_libtcl(
1950: 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e 74 65 Tcl_Release(inte
1960: 72 70 29 3b 29 0a 0a 09 09 41 50 50 46 53 5f 44 rp);)....APPFS_D
1970: 45 42 55 47 28 22 54 65 72 6d 69 6e 61 74 69 6e EBUG("Terminatin
1980: 67 20 54 63 6c 20 69 6e 74 65 72 70 72 65 74 65 g Tcl interprete
1990: 72 2e 22 29 3b 0a 0a 09 09 61 70 70 66 73 5f 63 r.");....appfs_c
19a0: 61 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 44 all_libtcl(Tcl_D
19b0: 65 6c 65 74 65 49 6e 74 65 72 70 28 69 6e 74 65 eleteInterp(inte
19c0: 72 70 29 3b 29 0a 0a 09 09 72 65 74 75 72 6e 28 rp);)....return(
19d0: 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 2f 2a 0a 09 NULL);..}.../*..
19e0: 20 2a 20 4c 6f 61 64 20 22 70 6b 69 2e 74 63 6c * Load "pki.tcl
19f0: 22 20 69 6e 20 74 68 65 20 73 61 6d 65 20 77 61 " in the same wa
1a00: 79 20 61 73 20 61 70 70 66 73 64 2e 74 63 6c 20 y as appfsd.tcl
1a10: 28 73 65 65 20 62 65 6c 6f 77 29 0a 09 20 2a 2f (see below).. */
1a20: 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 ..appfs_call_lib
1a30: 74 63 6c 5f 65 6e 74 65 72 0a 09 09 74 63 6c 5f tcl_enter...tcl_
1a40: 72 65 74 20 3d 20 54 63 6c 5f 45 76 61 6c 28 69 ret = Tcl_Eval(i
1a50: 6e 74 65 72 70 2c 20 22 22 0a 23 69 6e 63 6c 75 nterp, "".#inclu
1a60: 64 65 20 22 70 6b 69 2e 74 63 6c 2e 68 22 0a 09 de "pki.tcl.h"..
1a70: 09 22 22 29 3b 0a 09 61 70 70 66 73 5f 63 61 6c ."");..appfs_cal
1a80: 6c 5f 6c 69 62 74 63 6c 5f 65 78 69 74 0a 09 69 l_libtcl_exit..i
1a90: 66 20 28 74 63 6c 5f 72 65 74 20 21 3d 20 54 43 f (tcl_ret != TC
1aa0: 4c 5f 4f 4b 29 20 7b 0a 09 09 66 70 72 69 6e 74 L_OK) {...fprint
1ab0: 66 28 73 74 64 65 72 72 2c 20 22 55 6e 61 62 6c f(stderr, "Unabl
1ac0: 65 20 74 6f 20 69 6e 69 74 69 61 6c 69 7a 65 20 e to initialize
1ad0: 54 63 6c 20 50 4b 49 2e 20 20 41 62 6f 72 74 69 Tcl PKI. Aborti
1ae0: 6e 67 2e 5c 6e 22 29 3b 0a 09 09 61 70 70 66 73 ng.\n");...appfs
1af0: 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 _call_libtcl(...
1b00: 09 66 70 72 69 6e 74 66 28 73 74 64 65 72 72 2c .fprintf(stderr,
1b10: 20 22 54 63 6c 20 45 72 72 6f 72 20 69 73 3a 20 "Tcl Error is:
1b20: 25 73 5c 6e 22 2c 20 54 63 6c 5f 47 65 74 53 74 %s\n", Tcl_GetSt
1b30: 72 69 6e 67 52 65 73 75 6c 74 28 69 6e 74 65 72 ringResult(inter
1b40: 70 29 29 3b 0a 09 09 29 0a 0a 09 09 69 66 20 28 p));...)....if (
1b50: 65 72 72 6f 72 5f 73 74 72 69 6e 67 29 20 7b 0a error_string) {.
1b60: 09 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 ...appfs_call_li
1b70: 62 74 63 6c 28 0a 09 09 09 09 2a 65 72 72 6f 72 btcl(.....*error
1b80: 5f 73 74 72 69 6e 67 20 3d 20 73 74 72 64 75 70 _string = strdup
1b90: 28 54 63 6c 5f 47 65 74 53 74 72 69 6e 67 52 65 (Tcl_GetStringRe
1ba0: 73 75 6c 74 28 69 6e 74 65 72 70 29 29 3b 0a 09 sult(interp));..
1bb0: 09 09 29 0a 09 09 7d 0a 0a 09 09 61 70 70 66 73 ..)...}....appfs
1bc0: 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c _call_libtcl(Tcl
1bd0: 5f 52 65 6c 65 61 73 65 28 69 6e 74 65 72 70 29 _Release(interp)
1be0: 3b 29 0a 0a 09 09 41 50 50 46 53 5f 44 45 42 55 ;)....APPFS_DEBU
1bf0: 47 28 22 54 65 72 6d 69 6e 61 74 69 6e 67 20 54 G("Terminating T
1c00: 63 6c 20 69 6e 74 65 72 70 72 65 74 65 72 2e 22 cl interpreter."
1c10: 29 3b 0a 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c );....appfs_call
1c20: 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 44 65 6c 65 _libtcl(Tcl_Dele
1c30: 74 65 49 6e 74 65 72 70 28 69 6e 74 65 72 70 29 teInterp(interp)
1c40: 3b 29 0a 0a 09 09 72 65 74 75 72 6e 28 4e 55 4c ;)....return(NUL
1c50: 4c 29 3b 0a 09 7d 0a 0a 09 2f 2a 0a 09 20 2a 20 L);..}.../*.. *
1c60: 4c 6f 61 64 20 74 68 65 20 22 61 70 70 66 73 64 Load the "appfsd
1c70: 2e 74 63 6c 22 20 73 63 72 69 70 74 2c 20 77 68 .tcl" script, wh
1c80: 69 63 68 20 69 73 20 22 63 6f 6d 70 69 6c 65 64 ich is "compiled
1c90: 22 20 69 6e 74 6f 20 61 20 43 20 68 65 61 64 65 " into a C heade
1ca0: 72 0a 09 20 2a 20 73 6f 20 74 68 61 74 20 69 74 r.. * so that it
1cb0: 20 64 6f 65 73 20 6e 6f 74 20 6e 65 65 64 20 74 does not need t
1cc0: 6f 20 65 78 69 73 74 20 6f 6e 20 74 68 65 20 66 o exist on the f
1cd0: 69 6c 65 73 79 73 74 65 6d 20 61 6e 64 20 63 61 ilesystem and ca
1ce0: 6e 20 62 65 0a 09 20 2a 20 64 69 72 65 63 74 6c n be.. * directl
1cf0: 79 20 65 76 61 6c 75 61 74 65 64 2e 0a 09 20 2a y evaluated... *
1d00: 2f 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 /..appfs_call_li
1d10: 62 74 63 6c 5f 65 6e 74 65 72 0a 09 09 74 63 6c btcl_enter...tcl
1d20: 5f 72 65 74 20 3d 20 54 63 6c 5f 45 76 61 6c 28 _ret = Tcl_Eval(
1d30: 69 6e 74 65 72 70 2c 20 22 22 0a 23 69 6e 63 6c interp, "".#incl
1d40: 75 64 65 20 22 61 70 70 66 73 64 2e 74 63 6c 2e ude "appfsd.tcl.
1d50: 68 22 0a 09 09 22 22 29 3b 0a 09 61 70 70 66 73 h"..."");..appfs
1d60: 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 5f 65 78 69 _call_libtcl_exi
1d70: 74 0a 09 69 66 20 28 74 63 6c 5f 72 65 74 20 21 t..if (tcl_ret !
1d80: 3d 20 54 43 4c 5f 4f 4b 29 20 7b 0a 09 09 66 70 = TCL_OK) {...fp
1d90: 72 69 6e 74 66 28 73 74 64 65 72 72 2c 20 22 55 rintf(stderr, "U
1da0: 6e 61 62 6c 65 20 74 6f 20 69 6e 69 74 69 61 6c nable to initial
1db0: 69 7a 65 20 54 63 6c 20 41 70 70 46 53 20 73 63 ize Tcl AppFS sc
1dc0: 72 69 70 74 2e 20 20 41 62 6f 72 74 69 6e 67 2e ript. Aborting.
1dd0: 5c 6e 22 29 3b 0a 09 09 61 70 70 66 73 5f 63 61 \n");...appfs_ca
1de0: 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 09 66 70 ll_libtcl(....fp
1df0: 72 69 6e 74 66 28 73 74 64 65 72 72 2c 20 22 54 rintf(stderr, "T
1e00: 63 6c 20 45 72 72 6f 72 20 69 73 3a 20 25 73 5c cl Error is: %s\
1e10: 6e 22 2c 20 54 63 6c 5f 47 65 74 53 74 72 69 6e n", Tcl_GetStrin
1e20: 67 52 65 73 75 6c 74 28 69 6e 74 65 72 70 29 29 gResult(interp))
1e30: 3b 0a 09 09 29 0a 0a 09 09 69 66 20 28 65 72 72 ;...)....if (err
1e40: 6f 72 5f 73 74 72 69 6e 67 29 20 7b 0a 09 09 09 or_string) {....
1e50: 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 appfs_call_libtc
1e60: 6c 28 0a 09 09 09 09 2a 65 72 72 6f 72 5f 73 74 l(.....*error_st
1e70: 72 69 6e 67 20 3d 20 73 74 72 64 75 70 28 54 63 ring = strdup(Tc
1e80: 6c 5f 47 65 74 53 74 72 69 6e 67 52 65 73 75 6c l_GetStringResul
1e90: 74 28 69 6e 74 65 72 70 29 29 3b 0a 09 09 09 29 t(interp));....)
1ea0: 0a 09 09 7d 0a 0a 09 09 61 70 70 66 73 5f 63 61 ...}....appfs_ca
1eb0: 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 52 65 ll_libtcl(Tcl_Re
1ec0: 6c 65 61 73 65 28 69 6e 74 65 72 70 29 3b 29 0a lease(interp);).
1ed0: 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 ...APPFS_DEBUG("
1ee0: 54 65 72 6d 69 6e 61 74 69 6e 67 20 54 63 6c 20 Terminating Tcl
1ef0: 69 6e 74 65 72 70 72 65 74 65 72 2e 22 29 3b 0a interpreter.");.
1f00: 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 ...appfs_call_li
1f10: 62 74 63 6c 28 54 63 6c 5f 44 65 6c 65 74 65 49 btcl(Tcl_DeleteI
1f20: 6e 74 65 72 70 28 69 6e 74 65 72 70 29 3b 29 0a nterp(interp);).
1f30: 0a 09 09 72 65 74 75 72 6e 28 4e 55 4c 4c 29 3b ...return(NULL);
1f40: 0a 09 7d 0a 0a 09 2f 2a 0a 09 20 2a 20 53 65 74 ..}.../*.. * Set
1f50: 20 67 6c 6f 62 61 6c 20 76 61 72 69 61 62 6c 65 global variable
1f60: 73 20 66 72 6f 6d 20 43 20 74 6f 20 54 63 6c 0a s from C to Tcl.
1f70: 09 20 2a 2f 0a 09 61 70 70 66 73 5f 63 61 6c 6c . */..appfs_call
1f80: 5f 6c 69 62 74 63 6c 28 0a 09 09 74 63 6c 5f 73 _libtcl(...tcl_s
1f90: 65 74 76 61 72 5f 72 65 74 20 3d 20 54 63 6c 5f etvar_ret = Tcl_
1fa0: 53 65 74 56 61 72 28 69 6e 74 65 72 70 2c 20 22 SetVar(interp, "
1fb0: 3a 3a 61 70 70 66 73 3a 3a 63 61 63 68 65 64 69 ::appfs::cachedi
1fc0: 72 22 2c 20 61 70 70 66 73 5f 63 61 63 68 65 64 r", appfs_cached
1fd0: 69 72 2c 20 54 43 4c 5f 47 4c 4f 42 41 4c 5f 4f ir, TCL_GLOBAL_O
1fe0: 4e 4c 59 29 3b 0a 09 29 0a 09 69 66 20 28 74 63 NLY);..)..if (tc
1ff0: 6c 5f 73 65 74 76 61 72 5f 72 65 74 20 3d 3d 20 l_setvar_ret ==
2000: 4e 55 4c 4c 29 20 7b 0a 09 09 66 70 72 69 6e 74 NULL) {...fprint
2010: 66 28 73 74 64 65 72 72 2c 20 22 55 6e 61 62 6c f(stderr, "Unabl
2020: 65 20 74 6f 20 73 65 74 20 63 61 63 68 65 20 64 e to set cache d
2030: 69 72 65 63 74 6f 72 79 2e 20 20 54 68 69 73 20 irectory. This
2040: 73 68 6f 75 6c 64 20 6e 65 76 65 72 20 66 61 69 should never fai
2050: 6c 2e 5c 6e 22 29 3b 0a 0a 09 09 69 66 20 28 65 l.\n");....if (e
2060: 72 72 6f 72 5f 73 74 72 69 6e 67 29 20 7b 0a 09 rror_string) {..
2070: 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 ..appfs_call_lib
2080: 74 63 6c 28 0a 09 09 09 09 2a 65 72 72 6f 72 5f tcl(.....*error_
2090: 73 74 72 69 6e 67 20 3d 20 73 74 72 64 75 70 28 string = strdup(
20a0: 54 63 6c 5f 47 65 74 53 74 72 69 6e 67 52 65 73 Tcl_GetStringRes
20b0: 75 6c 74 28 69 6e 74 65 72 70 29 29 3b 0a 09 09 ult(interp));...
20c0: 09 29 0a 09 09 7d 0a 0a 09 09 61 70 70 66 73 5f .)...}....appfs_
20d0: 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f call_libtcl(Tcl_
20e0: 52 65 6c 65 61 73 65 28 69 6e 74 65 72 70 29 3b Release(interp);
20f0: 29 0a 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 )....APPFS_DEBUG
2100: 28 22 54 65 72 6d 69 6e 61 74 69 6e 67 20 54 63 ("Terminating Tc
2110: 6c 20 69 6e 74 65 72 70 72 65 74 65 72 2e 22 29 l interpreter.")
2120: 3b 0a 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f ;....appfs_call_
2130: 6c 69 62 74 63 6c 28 54 63 6c 5f 44 65 6c 65 74 libtcl(Tcl_Delet
2140: 65 49 6e 74 65 72 70 28 69 6e 74 65 72 70 29 3b eInterp(interp);
2150: 29 0a 0a 09 09 72 65 74 75 72 6e 28 4e 55 4c 4c )....return(NULL
2160: 29 3b 0a 09 7d 0a 0a 09 2f 2a 0a 09 20 2a 20 49 );..}.../*.. * I
2170: 6e 69 74 69 61 6c 69 7a 65 20 74 68 65 20 22 61 nitialize the "a
2180: 70 70 66 73 64 2e 74 63 6c 22 20 65 6e 76 69 72 ppfsd.tcl" envir
2190: 6f 6e 6d 65 6e 74 2c 20 77 68 69 63 68 20 6d 75 onment, which mu
21a0: 73 74 20 62 65 20 64 6f 6e 65 20 61 66 74 65 72 st be done after
21b0: 0a 09 20 2a 20 67 6c 6f 62 61 6c 20 76 61 72 69 .. * global vari
21c0: 61 62 6c 65 73 20 61 72 65 20 73 65 74 2e 0a 09 ables are set...
21d0: 20 2a 2f 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f */..appfs_call_
21e0: 6c 69 62 74 63 6c 28 0a 09 09 74 63 6c 5f 72 65 libtcl(...tcl_re
21f0: 74 20 3d 20 54 63 6c 5f 45 76 61 6c 28 69 6e 74 t = Tcl_Eval(int
2200: 65 72 70 2c 20 22 3a 3a 61 70 70 66 73 3a 3a 69 erp, "::appfs::i
2210: 6e 69 74 22 29 3b 0a 09 29 0a 09 69 66 20 28 74 nit");..)..if (t
2220: 63 6c 5f 72 65 74 20 21 3d 20 54 43 4c 5f 4f 4b cl_ret != TCL_OK
2230: 29 20 7b 0a 09 09 66 70 72 69 6e 74 66 28 73 74 ) {...fprintf(st
2240: 64 65 72 72 2c 20 22 55 6e 61 62 6c 65 20 74 6f derr, "Unable to
2250: 20 69 6e 69 74 69 61 6c 69 7a 65 20 54 63 6c 20 initialize Tcl
2260: 41 70 70 46 53 20 73 63 72 69 70 74 20 28 3a 3a AppFS script (::
2270: 61 70 70 66 73 3a 3a 69 6e 69 74 29 2e 20 20 41 appfs::init). A
2280: 62 6f 72 74 69 6e 67 2e 5c 6e 22 29 3b 0a 09 09 borting.\n");...
2290: 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 appfs_call_libtc
22a0: 6c 28 0a 09 09 09 66 70 72 69 6e 74 66 28 73 74 l(....fprintf(st
22b0: 64 65 72 72 2c 20 22 54 63 6c 20 45 72 72 6f 72 derr, "Tcl Error
22c0: 20 69 73 3a 20 25 73 5c 6e 22 2c 20 54 63 6c 5f is: %s\n", Tcl_
22d0: 47 65 74 53 74 72 69 6e 67 52 65 73 75 6c 74 28 GetStringResult(
22e0: 69 6e 74 65 72 70 29 29 3b 0a 09 09 29 0a 0a 09 interp));...)...
22f0: 09 69 66 20 28 65 72 72 6f 72 5f 73 74 72 69 6e .if (error_strin
2300: 67 29 20 7b 0a 09 09 09 61 70 70 66 73 5f 63 61 g) {....appfs_ca
2310: 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 09 09 2a ll_libtcl(.....*
2320: 65 72 72 6f 72 5f 73 74 72 69 6e 67 20 3d 20 73 error_string = s
2330: 74 72 64 75 70 28 54 63 6c 5f 47 65 74 53 74 72 trdup(Tcl_GetStr
2340: 69 6e 67 52 65 73 75 6c 74 28 69 6e 74 65 72 70 ingResult(interp
2350: 29 29 3b 0a 09 09 09 29 0a 09 09 7d 0a 0a 09 09 ));....)...}....
2360: 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 appfs_call_libtc
2370: 6c 28 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e l(Tcl_Release(in
2380: 74 65 72 70 29 3b 29 0a 0a 09 09 41 50 50 46 53 terp);)....APPFS
2390: 5f 44 45 42 55 47 28 22 54 65 72 6d 69 6e 61 74 _DEBUG("Terminat
23a0: 69 6e 67 20 54 63 6c 20 69 6e 74 65 72 70 72 65 ing Tcl interpre
23b0: 74 65 72 2e 22 29 3b 0a 0a 09 09 61 70 70 66 73 ter.");....appfs
23c0: 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c _call_libtcl(Tcl
23d0: 5f 44 65 6c 65 74 65 49 6e 74 65 72 70 28 69 6e _DeleteInterp(in
23e0: 74 65 72 70 29 3b 29 0a 0a 09 09 72 65 74 75 72 terp);)....retur
23f0: 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 2f 2a n(NULL);..}.../*
2400: 0a 09 20 2a 20 48 69 64 65 20 73 6f 6d 65 20 54 .. * Hide some T
2410: 63 6c 20 63 6f 6d 6d 61 6e 64 73 20 74 68 61 74 cl commands that
2420: 20 77 65 20 64 6f 20 6e 6f 74 20 63 61 72 65 20 we do not care
2430: 74 6f 20 75 73 65 20 61 6e 64 20 77 68 69 63 68 to use and which
2440: 20 6d 61 79 0a 09 20 2a 20 73 6c 6f 77 20 64 6f may.. * slow do
2450: 77 6e 20 72 75 6e 2d 74 69 6d 65 20 6f 70 65 72 wn run-time oper
2460: 61 74 69 6f 6e 73 2e 0a 09 20 2a 2f 0a 09 61 70 ations... */..ap
2470: 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 pfs_call_libtcl(
2480: 0a 09 09 54 63 6c 5f 48 69 64 65 43 6f 6d 6d 61 ...Tcl_HideComma
2490: 6e 64 28 69 6e 74 65 72 70 2c 20 22 61 75 74 6f nd(interp, "auto
24a0: 5f 6c 6f 61 64 5f 69 6e 64 65 78 22 2c 20 22 61 _load_index", "a
24b0: 75 74 6f 5f 6c 6f 61 64 5f 69 6e 64 65 78 22 29 uto_load_index")
24c0: 3b 0a 09 09 54 63 6c 5f 48 69 64 65 43 6f 6d 6d ;...Tcl_HideComm
24d0: 61 6e 64 28 69 6e 74 65 72 70 2c 20 22 75 6e 6b and(interp, "unk
24e0: 6e 6f 77 6e 22 2c 20 22 75 6e 6b 6e 6f 77 6e 22 nown", "unknown"
24f0: 29 3b 0a 09 09 54 63 6c 5f 48 69 64 65 43 6f 6d );...Tcl_HideCom
2500: 6d 61 6e 64 28 69 6e 74 65 72 70 2c 20 22 65 78 mand(interp, "ex
2510: 69 74 22 2c 20 22 65 78 69 74 22 29 3b 0a 09 29 it", "exit");..)
2520: 0a 0a 09 2f 2a 0a 09 20 2a 20 52 65 6c 65 61 73 .../*.. * Releas
2530: 65 20 74 68 65 20 68 6f 6c 64 20 77 65 20 68 61 e the hold we ha
2540: 76 65 20 6f 6e 20 74 68 65 20 69 6e 74 65 72 70 ve on the interp
2550: 72 65 74 65 72 20 73 6f 20 74 68 61 74 20 69 74 reter so that it
2560: 20 6d 61 79 20 62 65 0a 09 20 2a 20 64 65 6c 65 may be.. * dele
2570: 74 65 64 20 69 66 20 6e 65 65 64 65 64 0a 09 20 ted if needed..
2580: 2a 2f 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c */..appfs_call_l
2590: 69 62 74 63 6c 28 54 63 6c 5f 52 65 6c 65 61 73 ibtcl(Tcl_Releas
25a0: 65 28 69 6e 74 65 72 70 29 3b 29 0a 0a 09 2f 2a e(interp);).../*
25b0: 0a 09 20 2a 20 52 65 74 75 72 6e 20 74 68 65 20 .. * Return the
25c0: 63 6f 6d 70 6c 65 74 65 6c 79 20 69 6e 69 74 69 completely initi
25d0: 61 6c 69 7a 65 64 20 69 6e 74 65 72 70 72 65 74 alized interpret
25e0: 65 72 0a 09 20 2a 2f 0a 09 72 65 74 75 72 6e 28 er.. */..return(
25f0: 69 6e 74 65 72 70 29 3b 0a 7d 0a 0a 2f 2a 0a 20 interp);.}../*.
2600: 2a 20 52 65 74 75 72 6e 20 74 68 65 20 74 68 72 * Return the thr
2610: 65 61 64 2d 73 70 65 63 69 66 69 63 20 54 63 6c ead-specific Tcl
2620: 20 69 6e 74 65 72 70 72 65 74 65 72 2c 20 63 72 interpreter, cr
2630: 65 61 74 69 6e 67 20 69 74 20 69 66 20 6e 65 65 eating it if nee
2640: 64 65 64 0a 20 2a 2f 0a 73 74 61 74 69 63 20 54 ded. */.static T
2650: 63 6c 5f 49 6e 74 65 72 70 20 2a 61 70 70 66 73 cl_Interp *appfs
2660: 5f 54 63 6c 49 6e 74 65 72 70 28 76 6f 69 64 29 _TclInterp(void)
2670: 20 7b 0a 09 54 63 6c 5f 49 6e 74 65 72 70 20 2a {..Tcl_Interp *
2680: 69 6e 74 65 72 70 3b 0a 09 69 6e 74 20 70 74 68 interp;..int pth
2690: 72 65 61 64 5f 72 65 74 3b 0a 09 73 74 61 74 69 read_ret;..stati
26a0: 63 20 5f 5f 74 68 72 65 61 64 20 69 6e 74 20 74 c __thread int t
26b0: 68 72 65 61 64 5f 69 6e 74 65 72 70 5f 72 65 73 hread_interp_res
26c0: 65 74 5f 6b 65 79 20 3d 20 30 3b 0a 09 69 6e 74 et_key = 0;..int
26d0: 20 67 6c 6f 62 61 6c 5f 69 6e 74 65 72 70 5f 72 global_interp_r
26e0: 65 73 65 74 5f 6b 65 79 3b 0a 0a 09 67 6c 6f 62 eset_key;...glob
26f0: 61 6c 5f 69 6e 74 65 72 70 5f 72 65 73 65 74 5f al_interp_reset_
2700: 6b 65 79 20 3d 20 5f 5f 73 79 6e 63 5f 66 65 74 key = __sync_fet
2710: 63 68 5f 61 6e 64 5f 61 64 64 28 26 69 6e 74 65 ch_and_add(&inte
2720: 72 70 5f 72 65 73 65 74 5f 6b 65 79 2c 20 30 29 rp_reset_key, 0)
2730: 3b 0a 0a 09 69 6e 74 65 72 70 20 3d 20 70 74 68 ;...interp = pth
2740: 72 65 61 64 5f 67 65 74 73 70 65 63 69 66 69 63 read_getspecific
2750: 28 69 6e 74 65 72 70 4b 65 79 29 3b 0a 09 69 66 (interpKey);..if
2760: 20 28 69 6e 74 65 72 70 20 21 3d 20 4e 55 4c 4c (interp != NULL
2770: 20 26 26 20 74 68 72 65 61 64 5f 69 6e 74 65 72 && thread_inter
2780: 70 5f 72 65 73 65 74 5f 6b 65 79 20 21 3d 20 67 p_reset_key != g
2790: 6c 6f 62 61 6c 5f 69 6e 74 65 72 70 5f 72 65 73 lobal_interp_res
27a0: 65 74 5f 6b 65 79 29 20 7b 0a 09 09 41 50 50 46 et_key) {...APPF
27b0: 53 5f 44 45 42 55 47 28 22 54 65 72 6d 69 6e 61 S_DEBUG("Termina
27c0: 74 69 6e 67 20 6f 6c 64 20 69 6e 74 65 72 70 72 ting old interpr
27d0: 65 74 65 72 20 61 6e 64 20 72 65 73 74 61 72 74 eter and restart
27e0: 69 6e 67 20 64 75 65 20 74 6f 20 72 65 73 65 74 ing due to reset
27f0: 20 72 65 71 75 65 73 74 2e 22 29 3b 0a 0a 09 09 request.");....
2800: 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 appfs_call_libtc
2810: 6c 28 54 63 6c 5f 44 65 6c 65 74 65 49 6e 74 65 l(Tcl_DeleteInte
2820: 72 70 28 69 6e 74 65 72 70 29 3b 29 0a 0a 09 09 rp(interp);)....
2830: 69 6e 74 65 72 70 20 3d 20 4e 55 4c 4c 3b 0a 0a interp = NULL;..
2840: 09 09 70 74 68 72 65 61 64 5f 72 65 74 20 3d 20 ..pthread_ret =
2850: 70 74 68 72 65 61 64 5f 73 65 74 73 70 65 63 69 pthread_setspeci
2860: 66 69 63 28 69 6e 74 65 72 70 4b 65 79 2c 20 69 fic(interpKey, i
2870: 6e 74 65 72 70 29 3b 0a 09 7d 0a 0a 09 69 66 20 nterp);..}...if
2880: 28 67 6c 6f 62 61 6c 5f 69 6e 74 65 72 70 5f 72 (global_interp_r
2890: 65 73 65 74 5f 6b 65 79 20 3d 3d 20 2d 31 29 20 eset_key == -1)
28a0: 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 {...APPFS_DEBUG(
28b0: 22 52 65 74 75 72 6e 69 6e 67 20 4e 55 4c 4c 20 "Returning NULL
28c0: 73 69 6e 63 65 20 77 65 20 61 72 65 20 69 6e 20 since we are in
28d0: 74 68 65 20 70 72 6f 63 65 73 73 20 6f 66 20 74 the process of t
28e0: 65 72 6d 69 6e 61 74 69 6e 67 20 61 6c 6c 20 74 erminating all t
28f0: 68 72 65 61 64 73 2e 22 29 3b 0a 0a 09 09 72 65 hreads.");....re
2900: 74 75 72 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a turn(NULL);..}..
2910: 09 74 68 72 65 61 64 5f 69 6e 74 65 72 70 5f 72 .thread_interp_r
2920: 65 73 65 74 5f 6b 65 79 20 3d 20 67 6c 6f 62 61 eset_key = globa
2930: 6c 5f 69 6e 74 65 72 70 5f 72 65 73 65 74 5f 6b l_interp_reset_k
2940: 65 79 3b 0a 0a 09 69 66 20 28 69 6e 74 65 72 70 ey;...if (interp
2950: 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 69 6e == NULL) {...in
2960: 74 65 72 70 20 3d 20 61 70 70 66 73 5f 63 72 65 terp = appfs_cre
2970: 61 74 65 5f 54 63 6c 49 6e 74 65 72 70 28 4e 55 ate_TclInterp(NU
2980: 4c 4c 29 3b 0a 0a 09 09 69 66 20 28 69 6e 74 65 LL);....if (inte
2990: 72 70 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 rp == NULL) {...
29a0: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 43 72 .APPFS_DEBUG("Cr
29b0: 65 61 74 65 20 69 6e 74 65 72 70 20 66 61 69 6c eate interp fail
29c0: 65 64 2c 20 72 65 74 75 72 6e 69 6e 67 20 69 6e ed, returning in
29d0: 20 66 61 69 6c 75 72 65 2e 22 29 3b 0a 0a 09 09 failure.");....
29e0: 09 72 65 74 75 72 6e 28 4e 55 4c 4c 29 3b 0a 09 .return(NULL);..
29f0: 09 7d 0a 0a 09 09 70 74 68 72 65 61 64 5f 72 65 .}....pthread_re
2a00: 74 20 3d 20 70 74 68 72 65 61 64 5f 73 65 74 73 t = pthread_sets
2a10: 70 65 63 69 66 69 63 28 69 6e 74 65 72 70 4b 65 pecific(interpKe
2a20: 79 2c 20 69 6e 74 65 72 70 29 3b 0a 09 09 69 66 y, interp);...if
2a30: 20 28 70 74 68 72 65 61 64 5f 72 65 74 20 21 3d (pthread_ret !=
2a40: 20 30 29 20 7b 0a 09 09 09 41 50 50 46 53 5f 44 0) {....APPFS_D
2a50: 45 42 55 47 28 22 70 74 68 72 65 61 64 5f 73 65 EBUG("pthread_se
2a60: 74 73 70 65 63 69 66 69 63 28 29 20 66 61 69 6c tspecific() fail
2a70: 65 64 2e 20 20 54 65 72 6d 69 6e 61 74 69 6e 67 ed. Terminating
2a80: 20 54 63 6c 20 69 6e 74 65 72 70 72 65 74 65 72 Tcl interpreter
2a90: 2e 22 29 3b 0a 0a 09 09 09 61 70 70 66 73 5f 63 .");.....appfs_c
2aa0: 61 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 44 all_libtcl(Tcl_D
2ab0: 65 6c 65 74 65 49 6e 74 65 72 70 28 69 6e 74 65 eleteInterp(inte
2ac0: 72 70 29 3b 29 0a 0a 09 09 09 72 65 74 75 72 6e rp);).....return
2ad0: 28 4e 55 4c 4c 29 3b 0a 09 09 7d 0a 09 7d 0a 0a (NULL);...}..}..
2ae0: 09 72 65 74 75 72 6e 28 69 6e 74 65 72 70 29 3b .return(interp);
2af0: 0a 7d 0a 0a 2f 2a 0a 20 2a 20 45 76 61 6c 75 61 .}../*. * Evalua
2b00: 74 65 20 61 20 54 63 6c 20 73 63 72 69 70 74 20 te a Tcl script
2b10: 63 6f 6e 73 74 72 75 63 74 65 64 20 62 79 20 63 constructed by c
2b20: 6f 6e 63 61 74 65 6e 61 74 69 6e 67 20 61 20 62 oncatenating a b
2b30: 75 6e 63 68 20 6f 66 20 43 20 73 74 72 69 6e 67 unch of C string
2b40: 73 0a 20 2a 20 74 6f 67 65 74 68 65 72 2e 0a 20 s. * together..
2b50: 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 61 70 */.static int ap
2b60: 70 66 73 5f 54 63 6c 5f 45 76 61 6c 28 54 63 6c pfs_Tcl_Eval(Tcl
2b70: 5f 49 6e 74 65 72 70 20 2a 69 6e 74 65 72 70 2c _Interp *interp,
2b80: 20 69 6e 74 20 6f 62 6a 63 2c 20 63 6f 6e 73 74 int objc, const
2b90: 20 63 68 61 72 20 2a 63 6d 64 2c 20 2e 2e 2e 29 char *cmd, ...)
2ba0: 20 7b 0a 09 54 63 6c 5f 4f 62 6a 20 2a 2a 6f 62 {..Tcl_Obj **ob
2bb0: 6a 76 3b 0a 09 63 6f 6e 73 74 20 63 68 61 72 20 jv;..const char
2bc0: 2a 61 72 67 3b 0a 09 76 61 5f 6c 69 73 74 20 61 *arg;..va_list a
2bd0: 72 67 70 3b 0a 09 69 6e 74 20 72 65 74 76 61 6c rgp;..int retval
2be0: 3b 0a 09 69 6e 74 20 69 3b 0a 0a 09 69 66 20 28 ;..int i;...if (
2bf0: 69 6e 74 65 72 70 20 3d 3d 20 4e 55 4c 4c 29 20 interp == NULL)
2c00: 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 {...APPFS_DEBUG(
2c10: 22 49 6e 76 61 6c 69 64 20 69 6e 74 65 72 70 72 "Invalid interpr
2c20: 65 74 65 72 20 70 61 73 73 65 64 20 69 6e 2c 20 eter passed in,
2c30: 72 65 74 75 72 6e 69 6e 67 20 69 6e 20 66 61 69 returning in fai
2c40: 6c 75 72 65 2e 22 29 3b 0a 0a 09 09 72 65 74 75 lure.");....retu
2c50: 72 6e 28 54 43 4c 5f 45 52 52 4f 52 29 3b 0a 09 rn(TCL_ERROR);..
2c60: 7d 0a 0a 09 6f 62 6a 76 20 3d 20 28 76 6f 69 64 }...objv = (void
2c70: 20 2a 29 20 63 6b 61 6c 6c 6f 63 28 73 69 7a 65 *) ckalloc(size
2c80: 6f 66 28 2a 6f 62 6a 76 29 20 2a 20 6f 62 6a 63 of(*objv) * objc
2c90: 29 3b 0a 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f );...appfs_call_
2ca0: 6c 69 62 74 63 6c 28 0a 09 09 6f 62 6a 76 5b 30 libtcl(...objv[0
2cb0: 5d 20 3d 20 54 63 6c 5f 4e 65 77 53 74 72 69 6e ] = Tcl_NewStrin
2cc0: 67 4f 62 6a 28 63 6d 64 2c 20 2d 31 29 3b 0a 0a gObj(cmd, -1);..
2cd0: 09 09 54 63 6c 5f 49 6e 63 72 52 65 66 43 6f 75 ..Tcl_IncrRefCou
2ce0: 6e 74 28 6f 62 6a 76 5b 30 5d 29 3b 0a 0a 09 09 nt(objv[0]);....
2cf0: 76 61 5f 73 74 61 72 74 28 61 72 67 70 2c 20 63 va_start(argp, c
2d00: 6d 64 29 3b 0a 09 09 66 6f 72 20 28 69 20 3d 20 md);...for (i =
2d10: 31 3b 20 69 20 3c 20 6f 62 6a 63 3b 20 69 2b 2b 1; i < objc; i++
2d20: 29 20 7b 0a 09 09 09 61 72 67 20 3d 20 76 61 5f ) {....arg = va_
2d30: 61 72 67 28 61 72 67 70 2c 20 63 6f 6e 73 74 20 arg(argp, const
2d40: 63 68 61 72 20 2a 29 3b 0a 0a 09 09 09 6f 62 6a char *);.....obj
2d50: 76 5b 69 5d 20 3d 20 54 63 6c 5f 4e 65 77 53 74 v[i] = Tcl_NewSt
2d60: 72 69 6e 67 4f 62 6a 28 61 72 67 2c 20 2d 31 29 ringObj(arg, -1)
2d70: 3b 0a 0a 09 09 09 54 63 6c 5f 49 6e 63 72 52 65 ;.....Tcl_IncrRe
2d80: 66 43 6f 75 6e 74 28 6f 62 6a 76 5b 69 5d 29 3b fCount(objv[i]);
2d90: 0a 09 09 7d 0a 09 09 76 61 5f 65 6e 64 28 61 72 ...}...va_end(ar
2da0: 67 70 29 3b 0a 09 29 0a 0a 09 61 70 70 66 73 5f gp);..)...appfs_
2db0: 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 72 call_libtcl(...r
2dc0: 65 74 76 61 6c 20 3d 20 54 63 6c 5f 45 76 61 6c etval = Tcl_Eval
2dd0: 4f 62 6a 76 28 69 6e 74 65 72 70 2c 20 6f 62 6a Objv(interp, obj
2de0: 63 2c 20 6f 62 6a 76 2c 20 30 29 3b 0a 09 29 0a c, objv, 0);..).
2df0: 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 ..appfs_call_lib
2e00: 74 63 6c 28 0a 09 09 66 6f 72 20 28 69 20 3d 20 tcl(...for (i =
2e10: 30 3b 20 69 20 3c 20 6f 62 6a 63 3b 20 69 2b 2b 0; i < objc; i++
2e20: 29 20 7b 0a 09 09 09 54 63 6c 5f 44 65 63 72 52 ) {....Tcl_DecrR
2e30: 65 66 43 6f 75 6e 74 28 6f 62 6a 76 5b 69 5d 29 efCount(objv[i])
2e40: 3b 0a 09 09 7d 0a 09 29 0a 0a 09 63 6b 66 72 65 ;...}..)...ckfre
2e50: 65 28 28 76 6f 69 64 20 2a 29 20 6f 62 6a 76 29 e((void *) objv)
2e60: 3b 0a 0a 09 69 66 20 28 72 65 74 76 61 6c 20 21 ;...if (retval !
2e70: 3d 20 54 43 4c 5f 4f 4b 29 20 7b 0a 09 09 61 70 = TCL_OK) {...ap
2e80: 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 pfs_call_libtcl(
2e90: 0a 09 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 ....APPFS_DEBUG(
2ea0: 22 54 63 6c 20 63 6f 6d 6d 61 6e 64 20 66 61 69 "Tcl command fai
2eb0: 6c 65 64 2c 20 3a 3a 65 72 72 6f 72 49 6e 66 6f led, ::errorInfo
2ec0: 20 63 6f 6e 74 61 69 6e 73 3a 20 25 73 5c 6e 22 contains: %s\n"
2ed0: 2c 20 54 63 6c 5f 47 65 74 56 61 72 28 69 6e 74 , Tcl_GetVar(int
2ee0: 65 72 70 2c 20 22 3a 3a 65 72 72 6f 72 49 6e 66 erp, "::errorInf
2ef0: 6f 22 2c 20 30 29 29 3b 0a 09 09 29 0a 09 7d 0a o", 0));...)..}.
2f00: 0a 09 72 65 74 75 72 6e 28 72 65 74 76 61 6c 29 ..return(retval)
2f10: 3b 0a 7d 0a 0a 2f 2a 0a 20 2a 20 52 65 71 75 65 ;.}../*. * Reque
2f20: 73 74 20 61 6c 6c 20 54 63 6c 20 69 6e 74 65 72 st all Tcl inter
2f30: 70 72 65 74 65 72 73 20 72 65 73 74 61 72 74 0a preters restart.
2f40: 20 2a 2f 0a 73 74 61 74 69 63 20 76 6f 69 64 20 */.static void
2f50: 61 70 70 66 73 5f 74 63 6c 5f 52 65 73 65 74 49 appfs_tcl_ResetI
2f60: 6e 74 65 72 70 73 28 76 6f 69 64 29 20 7b 0a 09 nterps(void) {..
2f70: 41 50 50 46 53 5f 44 45 42 55 47 28 22 52 65 71 APPFS_DEBUG("Req
2f80: 75 65 73 74 69 6e 67 20 72 65 73 65 74 20 6f 66 uesting reset of
2f90: 20 61 6c 6c 20 69 6e 74 65 72 70 72 65 74 65 72 all interpreter
2fa0: 73 2e 22 29 3b 0a 0a 09 5f 5f 73 79 6e 63 5f 61 s.");...__sync_a
2fb0: 64 64 5f 61 6e 64 5f 66 65 74 63 68 28 26 69 6e dd_and_fetch(&in
2fc0: 74 65 72 70 5f 72 65 73 65 74 5f 6b 65 79 2c 20 terp_reset_key,
2fd0: 31 29 3b 0a 0a 09 72 65 74 75 72 6e 3b 0a 7d 0a 1);...return;.}.
2fe0: 0a 2f 2a 0a 20 2a 20 44 65 74 65 72 6d 69 6e 65 ./*. * Determine
2ff0: 20 74 68 65 20 55 49 44 20 66 6f 72 20 74 68 65 the UID for the
3000: 20 75 73 65 72 20 6d 61 6b 69 6e 67 20 74 68 65 user making the
3010: 20 63 75 72 72 65 6e 74 20 46 55 53 45 20 66 69 current FUSE fi
3020: 6c 65 73 79 73 74 65 6d 20 72 65 71 75 65 73 74 lesystem request
3030: 2e 0a 20 2a 20 54 68 69 73 20 77 69 6c 6c 20 62 .. * This will b
3040: 65 20 75 73 65 64 20 74 6f 20 6c 6f 6f 6b 75 70 e used to lookup
3050: 20 74 68 65 20 75 73 65 72 27 73 20 68 6f 6d 65 the user's home
3060: 20 64 69 72 65 63 74 6f 72 79 20 73 6f 20 77 65 directory so we
3070: 20 63 61 6e 20 73 65 61 72 63 68 20 66 6f 72 0a can search for.
3080: 20 2a 20 6c 6f 63 61 6c 6c 79 20 6d 6f 64 69 66 * locally modif
3090: 69 65 64 20 66 69 6c 65 73 2e 0a 20 2a 2f 0a 73 ied files.. */.s
30a0: 74 61 74 69 63 20 75 69 64 5f 74 20 61 70 70 66 tatic uid_t appf
30b0: 73 5f 67 65 74 5f 66 73 75 69 64 28 76 6f 69 64 s_get_fsuid(void
30c0: 29 20 7b 0a 09 73 74 72 75 63 74 20 66 75 73 65 ) {..struct fuse
30d0: 5f 63 6f 6e 74 65 78 74 20 2a 63 74 78 3b 0a 0a _context *ctx;..
30e0: 09 69 66 20 28 21 61 70 70 66 73 5f 66 75 73 65 .if (!appfs_fuse
30f0: 5f 73 74 61 72 74 65 64 29 20 7b 0a 09 09 72 65 _started) {...re
3100: 74 75 72 6e 28 67 65 74 75 69 64 28 29 29 3b 0a turn(getuid());.
3110: 09 7d 0a 0a 09 63 74 78 20 3d 20 66 75 73 65 5f .}...ctx = fuse_
3120: 67 65 74 5f 63 6f 6e 74 65 78 74 28 29 3b 0a 09 get_context();..
3130: 69 66 20 28 63 74 78 20 3d 3d 20 4e 55 4c 4c 29 if (ctx == NULL)
3140: 20 7b 0a 09 09 2f 2a 20 55 6e 61 62 6c 65 20 74 {.../* Unable t
3150: 6f 20 6c 6f 6f 6b 75 70 20 75 73 65 72 20 66 6f o lookup user fo
3160: 72 20 73 6f 6d 65 20 72 65 61 73 6f 6e 20 2a 2f r some reason */
3170: 0a 09 09 2f 2a 20 52 65 74 75 72 6e 20 61 6e 20 .../* Return an
3180: 75 6e 70 72 69 76 69 6c 65 67 65 64 20 75 73 65 unprivileged use
3190: 72 20 49 44 20 2a 2f 0a 09 09 41 50 50 46 53 5f r ID */...APPFS_
31a0: 44 45 42 55 47 28 22 55 6e 61 62 6c 65 20 74 6f DEBUG("Unable to
31b0: 20 6c 6f 6f 6b 75 70 20 75 73 65 72 20 66 6f 72 lookup user for
31c0: 20 73 6f 6d 65 20 72 65 61 73 6f 6e 2c 20 72 65 some reason, re
31d0: 74 75 72 6e 69 6e 6e 67 20 75 73 65 72 20 49 44 turninng user ID
31e0: 20 6f 66 20 31 22 29 3b 0a 0a 09 09 72 65 74 75 of 1");....retu
31f0: 72 6e 28 31 29 3b 0a 09 7d 0a 0a 09 72 65 74 75 rn(1);..}...retu
3200: 72 6e 28 63 74 78 2d 3e 75 69 64 29 3b 0a 7d 0a rn(ctx->uid);.}.
3210: 0a 2f 2a 0a 20 2a 20 44 65 74 65 72 6d 69 6e 65 ./*. * Determine
3220: 20 74 68 65 20 47 49 44 20 66 6f 72 20 74 68 65 the GID for the
3230: 20 75 73 65 72 20 6d 61 6b 69 6e 67 20 74 68 65 user making the
3240: 20 63 75 72 72 65 6e 74 20 46 55 53 45 20 66 69 current FUSE fi
3250: 6c 65 73 79 73 74 65 6d 20 72 65 71 75 65 73 74 lesystem request
3260: 2e 0a 20 2a 2f 0a 73 74 61 74 69 63 20 67 69 64 .. */.static gid
3270: 5f 74 20 61 70 70 66 73 5f 67 65 74 5f 66 73 67 _t appfs_get_fsg
3280: 69 64 28 76 6f 69 64 29 20 7b 0a 09 73 74 72 75 id(void) {..stru
3290: 63 74 20 66 75 73 65 5f 63 6f 6e 74 65 78 74 20 ct fuse_context
32a0: 2a 63 74 78 3b 0a 0a 09 69 66 20 28 21 61 70 70 *ctx;...if (!app
32b0: 66 73 5f 66 75 73 65 5f 73 74 61 72 74 65 64 29 fs_fuse_started)
32c0: 20 7b 0a 09 09 72 65 74 75 72 6e 28 67 65 74 67 {...return(getg
32d0: 69 64 28 29 29 3b 0a 09 7d 0a 0a 09 63 74 78 20 id());..}...ctx
32e0: 3d 20 66 75 73 65 5f 67 65 74 5f 63 6f 6e 74 65 = fuse_get_conte
32f0: 78 74 28 29 3b 0a 09 69 66 20 28 63 74 78 20 3d xt();..if (ctx =
3300: 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 2f 2a 20 55 = NULL) {.../* U
3310: 6e 61 62 6c 65 20 74 6f 20 6c 6f 6f 6b 75 70 20 nable to lookup
3320: 75 73 65 72 20 66 6f 72 20 73 6f 6d 65 20 72 65 user for some re
3330: 61 73 6f 6e 20 2a 2f 0a 09 09 2f 2a 20 52 65 74 ason */.../* Ret
3340: 75 72 6e 20 61 6e 20 75 6e 70 72 69 76 69 6c 65 urn an unprivile
3350: 67 65 64 20 75 73 65 72 20 49 44 20 2a 2f 0a 09 ged user ID */..
3360: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 55 6e .APPFS_DEBUG("Un
3370: 61 62 6c 65 20 74 6f 20 6c 6f 6f 6b 75 70 20 67 able to lookup g
3380: 72 6f 75 70 20 66 6f 72 20 73 6f 6d 65 20 72 65 roup for some re
3390: 61 73 6f 6e 2c 20 72 65 74 75 72 6e 69 6e 6e 67 ason, returninng
33a0: 20 67 72 6f 75 70 20 49 44 20 6f 66 20 31 22 29 group ID of 1")
33b0: 3b 0a 0a 09 09 72 65 74 75 72 6e 28 31 29 3b 0a ;....return(1);.
33c0: 09 7d 0a 0a 09 72 65 74 75 72 6e 28 63 74 78 2d .}...return(ctx-
33d0: 3e 67 69 64 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 >gid);.}..static
33e0: 20 76 6f 69 64 20 61 70 70 66 73 5f 73 69 6d 75 void appfs_simu
33f0: 6c 61 74 65 5f 75 73 65 72 5f 66 73 5f 65 6e 74 late_user_fs_ent
3400: 65 72 28 76 6f 69 64 29 20 7b 0a 09 73 65 74 66 er(void) {..setf
3410: 73 75 69 64 28 61 70 70 66 73 5f 67 65 74 5f 66 suid(appfs_get_f
3420: 73 75 69 64 28 29 29 3b 0a 09 73 65 74 66 73 67 suid());..setfsg
3430: 69 64 28 61 70 70 66 73 5f 67 65 74 5f 66 73 67 id(appfs_get_fsg
3440: 69 64 28 29 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 id());.}..static
3450: 20 76 6f 69 64 20 61 70 70 66 73 5f 73 69 6d 75 void appfs_simu
3460: 6c 61 74 65 5f 75 73 65 72 5f 66 73 5f 6c 65 61 late_user_fs_lea
3470: 76 65 28 76 6f 69 64 29 20 7b 0a 09 73 65 74 66 ve(void) {..setf
3480: 73 75 69 64 28 30 29 3b 0a 09 73 65 74 66 73 67 suid(0);..setfsg
3490: 69 64 28 30 29 3b 0a 7d 0a 0a 2f 2a 0a 20 2a 20 id(0);.}../*. *
34a0: 4c 6f 6f 6b 20 75 70 20 74 68 65 20 68 6f 6d 65 Look up the home
34b0: 20 64 69 72 65 63 74 6f 72 79 20 66 6f 72 20 61 directory for a
34c0: 20 67 69 76 65 6e 20 55 49 44 0a 20 2a 20 20 20 given UID. *
34d0: 20 20 20 20 20 52 65 74 75 72 6e 73 20 61 20 43 Returns a C
34e0: 20 73 74 72 69 6e 67 20 63 6f 6e 74 61 69 6e 69 string containi
34f0: 6e 67 20 74 68 65 20 75 73 65 72 27 73 20 68 6f ng the user's ho
3500: 6d 65 20 64 69 72 65 63 74 6f 72 79 20 6f 72 20 me directory or
3510: 4e 55 4c 4c 20 69 66 0a 20 2a 20 20 20 20 20 20 NULL if. *
3520: 20 20 74 68 65 20 75 73 65 72 27 73 20 68 6f 6d the user's hom
3530: 65 20 64 69 72 65 63 74 6f 72 79 20 64 6f 65 73 e directory does
3540: 20 6e 6f 74 20 65 78 69 73 74 20 6f 72 20 69 73 not exist or is
3550: 20 6e 6f 74 20 63 6f 72 72 65 63 74 6c 79 0a 20 not correctly.
3560: 2a 20 20 20 20 20 20 20 20 63 6f 6e 66 69 67 75 * configu
3570: 72 65 64 0a 20 2a 2f 0a 73 74 61 74 69 63 20 63 red. */.static c
3580: 68 61 72 20 2a 61 70 70 66 73 5f 67 65 74 5f 68 har *appfs_get_h
3590: 6f 6d 65 64 69 72 28 75 69 64 5f 74 20 66 73 75 omedir(uid_t fsu
35a0: 69 64 29 20 7b 0a 09 73 74 72 75 63 74 20 70 61 id) {..struct pa
35b0: 73 73 77 64 20 65 6e 74 72 79 2c 20 2a 72 65 73 sswd entry, *res
35c0: 75 6c 74 3b 0a 09 73 74 72 75 63 74 20 73 74 61 ult;..struct sta
35d0: 74 20 73 74 62 75 66 3b 0a 09 63 68 61 72 20 62 t stbuf;..char b
35e0: 75 66 5b 31 30 32 34 5d 2c 20 2a 72 65 74 76 61 uf[1024], *retva
35f0: 6c 3b 0a 09 69 6e 74 20 67 70 75 5f 72 65 74 2c l;..int gpu_ret,
3600: 20 73 74 61 74 5f 72 65 74 3b 0a 0a 09 67 70 75 stat_ret;...gpu
3610: 5f 72 65 74 20 3d 20 67 65 74 70 77 75 69 64 5f _ret = getpwuid_
3620: 72 28 66 73 75 69 64 2c 20 26 65 6e 74 72 79 2c r(fsuid, &entry,
3630: 20 62 75 66 2c 20 73 69 7a 65 6f 66 28 62 75 66 buf, sizeof(buf
3640: 29 2c 20 26 72 65 73 75 6c 74 29 3b 0a 09 69 66 ), &result);..if
3650: 20 28 67 70 75 5f 72 65 74 20 21 3d 20 30 29 20 (gpu_ret != 0)
3660: 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 {...APPFS_DEBUG(
3670: 22 67 65 74 70 77 75 69 64 5f 72 28 25 6c 6c 75 "getpwuid_r(%llu
3680: 2c 20 2e 2e 2e 29 20 72 65 74 75 72 6e 65 64 20 , ...) returned
3690: 69 6e 20 66 61 69 6c 75 72 65 22 2c 20 28 75 6e in failure", (un
36a0: 73 69 67 6e 65 64 20 6c 6f 6e 67 20 6c 6f 6e 67 signed long long
36b0: 29 20 66 73 75 69 64 29 3b 0a 0a 09 09 72 65 74 ) fsuid);....ret
36c0: 75 72 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 urn(NULL);..}...
36d0: 69 66 20 28 72 65 73 75 6c 74 20 3d 3d 20 4e 55 if (result == NU
36e0: 4c 4c 29 20 7b 0a 09 09 41 50 50 46 53 5f 44 45 LL) {...APPFS_DE
36f0: 42 55 47 28 22 67 65 74 70 77 75 69 64 5f 72 28 BUG("getpwuid_r(
3700: 25 6c 6c 75 2c 20 2e 2e 2e 29 20 72 65 74 75 72 %llu, ...) retur
3710: 6e 65 64 20 4e 55 4c 4c 20 72 65 73 75 6c 74 22 ned NULL result"
3720: 2c 20 28 75 6e 73 69 67 6e 65 64 20 6c 6f 6e 67 , (unsigned long
3730: 20 6c 6f 6e 67 29 20 66 73 75 69 64 29 3b 0a 0a long) fsuid);..
3740: 09 09 72 65 74 75 72 6e 28 4e 55 4c 4c 29 3b 0a ..return(NULL);.
3750: 09 7d 0a 0a 09 69 66 20 28 72 65 73 75 6c 74 2d .}...if (result-
3760: 3e 70 77 5f 64 69 72 20 3d 3d 20 4e 55 4c 4c 29 >pw_dir == NULL)
3770: 20 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 {...APPFS_DEBUG
3780: 28 22 67 65 74 70 77 75 69 64 5f 72 28 25 6c 6c ("getpwuid_r(%ll
3790: 75 2c 20 2e 2e 2e 29 20 72 65 74 75 72 6e 65 64 u, ...) returned
37a0: 20 4e 55 4c 4c 20 68 6f 6d 65 20 64 69 72 65 63 NULL home direc
37b0: 74 6f 72 79 22 2c 20 28 75 6e 73 69 67 6e 65 64 tory", (unsigned
37c0: 20 6c 6f 6e 67 20 6c 6f 6e 67 29 20 66 73 75 69 long long) fsui
37d0: 64 29 3b 0a 0a 09 09 72 65 74 75 72 6e 28 4e 55 d);....return(NU
37e0: 4c 4c 29 3b 0a 09 7d 0a 0a 09 73 74 61 74 5f 72 LL);..}...stat_r
37f0: 65 74 20 3d 20 73 74 61 74 28 72 65 73 75 6c 74 et = stat(result
3800: 2d 3e 70 77 5f 64 69 72 2c 20 26 73 74 62 75 66 ->pw_dir, &stbuf
3810: 29 3b 0a 09 69 66 20 28 73 74 61 74 5f 72 65 74 );..if (stat_ret
3820: 20 21 3d 20 30 29 20 7b 0a 09 09 41 50 50 46 53 != 0) {...APPFS
3830: 5f 44 45 42 55 47 28 22 73 74 61 74 28 25 73 29 _DEBUG("stat(%s)
3840: 20 72 65 74 75 72 6e 65 64 20 69 6e 20 66 61 69 returned in fai
3850: 6c 75 72 65 22 2c 20 72 65 73 75 6c 74 2d 3e 70 lure", result->p
3860: 77 5f 64 69 72 29 3b 0a 0a 09 09 72 65 74 75 72 w_dir);....retur
3870: 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 69 66 n(NULL);..}...if
3880: 20 28 73 74 62 75 66 2e 73 74 5f 75 69 64 20 21 (stbuf.st_uid !
3890: 3d 20 66 73 75 69 64 29 20 7b 0a 09 09 41 50 50 = fsuid) {...APP
38a0: 46 53 5f 44 45 42 55 47 28 22 55 49 44 20 6d 69 FS_DEBUG("UID mi
38b0: 73 2d 6d 61 74 63 68 20 6f 6e 20 75 73 65 72 20 s-match on user
38c0: 25 6c 6c 75 27 73 20 68 6f 6d 65 20 64 69 72 65 %llu's home dire
38d0: 63 74 6f 72 79 20 28 25 73 29 2e 20 20 49 74 27 ctory (%s). It'
38e0: 73 20 6f 77 6e 65 64 20 62 79 20 25 6c 6c 75 2e s owned by %llu.
38f0: 22 2c 0a 09 09 20 20 20 20 28 75 6e 73 69 67 6e ",... (unsign
3900: 65 64 20 6c 6f 6e 67 20 6c 6f 6e 67 29 20 66 73 ed long long) fs
3910: 75 69 64 2c 0a 09 09 20 20 20 20 72 65 73 75 6c uid,... resul
3920: 74 2d 3e 70 77 5f 64 69 72 2c 0a 09 09 20 20 20 t->pw_dir,...
3930: 20 28 75 6e 73 69 67 6e 65 64 20 6c 6f 6e 67 20 (unsigned long
3940: 6c 6f 6e 67 29 20 73 74 62 75 66 2e 73 74 5f 75 long) stbuf.st_u
3950: 69 64 0a 09 09 29 3b 0a 0a 09 09 72 65 74 75 72 id...);....retur
3960: 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 72 65 n(NULL);..}...re
3970: 74 76 61 6c 20 3d 20 73 74 72 64 75 70 28 72 65 tval = strdup(re
3980: 73 75 6c 74 2d 3e 70 77 5f 64 69 72 29 3b 0a 0a sult->pw_dir);..
3990: 09 72 65 74 75 72 6e 28 72 65 74 76 61 6c 29 3b .return(retval);
39a0: 0a 7d 0a 0a 2f 2a 0a 20 2a 20 47 65 6e 65 72 61 .}../*. * Genera
39b0: 74 65 20 61 6e 20 69 6e 6f 64 65 20 66 6f 72 20 te an inode for
39c0: 61 20 67 69 76 65 6e 20 70 61 74 68 2e 20 20 54 a given path. T
39d0: 68 65 20 69 6e 6f 64 65 20 73 68 6f 75 6c 64 20 he inode should
39e0: 62 65 20 63 6f 6d 70 75 74 65 64 20 69 6e 20 73 be computed in s
39f0: 75 63 68 0a 20 2a 20 61 20 77 61 79 20 74 68 61 uch. * a way tha
3a00: 74 20 69 74 20 69 73 20 75 6e 6c 69 6b 65 6c 79 t it is unlikely
3a10: 20 74 6f 20 62 65 20 64 75 70 6c 69 63 61 74 65 to be duplicate
3a20: 64 20 61 6e 64 20 72 65 6d 61 69 6e 73 20 74 68 d and remains th
3a30: 65 20 73 61 6d 65 20 66 6f 72 20 61 20 67 69 76 e same for a giv
3a40: 65 6e 0a 20 2a 20 66 69 6c 65 0a 20 2a 0a 20 2a en. * file. *. *
3a50: 20 43 75 72 72 65 6e 74 20 69 6d 70 6c 65 6d 65 Current impleme
3a60: 6e 74 61 74 69 6f 6e 20 69 73 20 61 6e 20 46 4e ntation is an FN
3a70: 56 2d 31 61 20 33 32 2d 62 69 74 0a 20 2a 2f 0a V-1a 32-bit. */.
3a80: 23 69 66 20 55 49 4e 54 5f 4d 41 58 20 3c 20 34 #if UINT_MAX < 4
3a90: 32 39 34 39 36 37 32 39 35 0a 23 65 72 72 6f 72 294967295.#error
3aa0: 20 49 6e 74 65 67 65 72 20 73 69 7a 65 20 69 73 Integer size is
3ab0: 20 74 6f 6f 20 73 6d 61 6c 6c 20 0a 23 65 6e 64 too small .#end
3ac0: 69 66 0a 73 74 61 74 69 63 20 75 6e 73 69 67 6e if.static unsign
3ad0: 65 64 20 6c 6f 6e 67 20 6c 6f 6e 67 20 61 70 70 ed long long app
3ae0: 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 6e 6f 64 fs_get_path_inod
3af0: 65 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 70 61 e(const char *pa
3b00: 74 68 2c 20 69 6e 74 20 75 69 64 29 20 7b 0a 09 th, int uid) {..
3b10: 75 6e 73 69 67 6e 65 64 20 69 6e 74 20 72 65 74 unsigned int ret
3b20: 76 61 6c 3b 0a 09 63 6f 6e 73 74 20 75 6e 73 69 val;..const unsi
3b30: 67 6e 65 64 20 63 68 61 72 20 2a 70 3b 0a 0a 09 gned char *p;...
3b40: 72 65 74 76 61 6c 20 3d 20 32 31 36 36 31 33 36 retval = 2166136
3b50: 32 36 31 55 3b 20 2f 2a 20 46 4e 56 2d 31 61 20 261U; /* FNV-1a
3b60: 33 32 2d 62 69 74 20 6f 66 66 73 65 74 5f 62 61 32-bit offset_ba
3b70: 73 69 73 20 2a 2f 0a 0a 09 66 6f 72 20 28 70 20 sis */...for (p
3b80: 3d 20 28 75 6e 73 69 67 6e 65 64 20 63 68 61 72 = (unsigned char
3b90: 20 2a 29 20 70 61 74 68 3b 20 2a 70 3b 20 70 2b *) path; *p; p+
3ba0: 2b 29 20 7b 0a 09 09 72 65 74 76 61 6c 20 5e 3d +) {...retval ^=
3bb0: 20 28 69 6e 74 29 20 2a 70 3b 0a 23 69 66 20 30 (int) *p;.#if 0
3bc0: 0a 09 09 72 65 74 76 61 6c 20 2a 3d 20 31 36 37 ...retval *= 167
3bd0: 37 37 36 31 39 3b 20 2f 2a 20 46 4e 56 2d 31 61 77619; /* FNV-1a
3be0: 20 33 32 2d 62 69 74 20 70 72 69 6d 65 20 2a 2f 32-bit prime */
3bf0: 0a 23 65 6c 73 65 0a 09 09 2f 2a 20 47 43 43 20 .#else.../* GCC
3c00: 4f 70 74 69 6d 69 7a 65 64 20 72 65 70 6c 61 63 Optimized replac
3c10: 65 6d 65 6e 74 20 2a 2f 0a 09 09 72 65 74 76 61 ement */...retva
3c20: 6c 20 2b 3d 20 28 72 65 74 76 61 6c 20 3c 3c 20 l += (retval <<
3c30: 31 29 20 2b 20 28 72 65 74 76 61 6c 20 3c 3c 20 1) + (retval <<
3c40: 34 29 20 2b 20 28 72 65 74 76 61 6c 20 3c 3c 20 4) + (retval <<
3c50: 37 29 20 2b 20 28 72 65 74 76 61 6c 20 3c 3c 20 7) + (retval <<
3c60: 38 29 20 2b 20 28 72 65 74 76 61 6c 20 3c 3c 20 8) + (retval <<
3c70: 32 34 29 3b 0a 23 65 6e 64 69 66 0a 09 7d 0a 0a 24);.#endif..}..
3c80: 09 69 66 20 28 75 69 64 20 3e 3d 20 30 29 20 7b .if (uid >= 0) {
3c90: 0a 09 09 72 65 74 76 61 6c 20 2b 3d 20 75 69 64 ...retval += uid
3ca0: 3b 0a 09 09 72 65 74 76 61 6c 2b 2b 3b 0a 09 7d ;...retval++;..}
3cb0: 0a 0a 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 ...APPFS_DEBUG("
3cc0: 4c 6f 6f 6b 65 64 20 75 70 20 69 6e 6f 64 65 20 Looked up inode
3cd0: 6e 75 6d 62 65 72 20 66 6f 72 20 70 61 74 68 3d number for path=
3ce0: 25 73 2c 75 69 64 3d 25 69 3a 20 25 75 22 2c 20 %s,uid=%i: %u",
3cf0: 70 61 74 68 2c 20 75 69 64 2c 20 72 65 74 76 61 path, uid, retva
3d00: 6c 29 3b 0a 0a 09 72 65 74 75 72 6e 28 72 65 74 l);...return(ret
3d10: 76 61 6c 29 3b 0a 7d 0a 0a 2f 2a 0a 20 2a 20 43 val);.}../*. * C
3d20: 61 63 68 65 20 47 65 74 20 50 61 74 68 20 49 6e ache Get Path In
3d30: 66 6f 20 6c 6f 6f 6b 75 70 73 20 66 6f 72 20 73 fo lookups for s
3d40: 70 65 65 64 0a 20 2a 2f 0a 73 74 61 74 69 63 20 peed. */.static
3d50: 69 6e 74 20 61 70 70 66 73 5f 67 65 74 5f 70 61 int appfs_get_pa
3d60: 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5f 67 65 th_info_cache_ge
3d70: 74 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 70 61 t(const char *pa
3d80: 74 68 2c 20 75 69 64 5f 74 20 75 69 64 2c 20 73 th, uid_t uid, s
3d90: 74 72 75 63 74 20 61 70 70 66 73 5f 70 61 74 68 truct appfs_path
3da0: 69 6e 66 6f 20 2a 70 61 74 68 69 6e 66 6f 29 20 info *pathinfo)
3db0: 7b 0a 09 75 6e 73 69 67 6e 65 64 20 69 6e 74 20 {..unsigned int
3dc0: 68 61 73 68 5f 69 64 78 3b 0a 09 69 6e 74 20 70 hash_idx;..int p
3dd0: 74 68 72 65 61 64 5f 72 65 74 3b 0a 09 69 6e 74 thread_ret;..int
3de0: 20 72 65 74 76 61 6c 3b 0a 0a 09 72 65 74 76 61 retval;...retva
3df0: 6c 20 3d 20 31 3b 0a 0a 09 70 74 68 72 65 61 64 l = 1;...pthread
3e00: 5f 72 65 74 20 3d 20 70 74 68 72 65 61 64 5f 6d _ret = pthread_m
3e10: 75 74 65 78 5f 6c 6f 63 6b 28 26 61 70 70 66 73 utex_lock(&appfs
3e20: 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 _path_info_cache
3e30: 5f 6d 75 74 65 78 29 3b 0a 09 69 66 20 28 70 74 _mutex);..if (pt
3e40: 68 72 65 61 64 5f 72 65 74 20 21 3d 20 30 29 20 hread_ret != 0)
3e50: 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 {...APPFS_DEBUG(
3e60: 22 55 6e 61 62 6c 65 20 74 6f 20 6c 6f 63 6b 20 "Unable to lock
3e70: 70 61 74 68 5f 69 6e 66 6f 20 63 61 63 68 65 20 path_info cache
3e80: 6d 75 74 65 78 20 21 22 29 3b 0a 0a 09 09 72 65 mutex !");....re
3e90: 74 75 72 6e 28 2d 31 29 3b 0a 09 7d 0a 0a 09 41 turn(-1);..}...A
3ea0: 50 50 46 53 5f 44 45 42 55 47 28 22 4c 6f 6f 6b PPFS_DEBUG("Look
3eb0: 69 6e 67 20 75 70 20 63 61 63 68 65 20 65 6e 74 ing up cache ent
3ec0: 72 79 20 66 6f 72 20 70 61 74 68 3d 25 73 2c 75 ry for path=%s,u
3ed0: 69 64 3d 25 6c 6c 69 2e 2e 2e 22 2c 20 70 61 74 id=%lli...", pat
3ee0: 68 2c 20 28 6c 6f 6e 67 20 6c 6f 6e 67 29 20 75 h, (long long) u
3ef0: 69 64 29 3b 0a 0a 09 69 66 20 28 61 70 70 66 73 id);...if (appfs
3f00: 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 _path_info_cache
3f10: 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 68 61 != NULL) {...ha
3f20: 73 68 5f 69 64 78 20 3d 20 28 61 70 70 66 73 5f sh_idx = (appfs_
3f30: 67 65 74 5f 70 61 74 68 5f 69 6e 6f 64 65 28 70 get_path_inode(p
3f40: 61 74 68 2c 20 75 69 64 29 29 20 25 20 61 70 70 ath, uid)) % app
3f50: 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 fs_path_info_cac
3f60: 68 65 5f 73 69 7a 65 3b 0a 0a 09 09 69 66 20 28 he_size;....if (
3f70: 61 70 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f appfs_path_info_
3f80: 63 61 63 68 65 5b 68 61 73 68 5f 69 64 78 5d 2e cache[hash_idx].
3f90: 5f 63 61 63 68 65 5f 70 61 74 68 20 21 3d 20 4e _cache_path != N
3fa0: 55 4c 4c 29 20 7b 0a 09 09 09 69 66 20 28 73 74 ULL) {....if (st
3fb0: 72 63 6d 70 28 61 70 70 66 73 5f 70 61 74 68 5f rcmp(appfs_path_
3fc0: 69 6e 66 6f 5f 63 61 63 68 65 5b 68 61 73 68 5f info_cache[hash_
3fd0: 69 64 78 5d 2e 5f 63 61 63 68 65 5f 70 61 74 68 idx]._cache_path
3fe0: 2c 20 70 61 74 68 29 20 3d 3d 20 30 20 26 26 20 , path) == 0 &&
3ff0: 61 70 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f appfs_path_info_
4000: 63 61 63 68 65 5b 68 61 73 68 5f 69 64 78 5d 2e cache[hash_idx].
4010: 5f 63 61 63 68 65 5f 75 69 64 20 3d 3d 20 75 69 _cache_uid == ui
4020: 64 29 20 7b 0a 09 09 09 09 72 65 74 76 61 6c 20 d) {.....retval
4030: 3d 20 30 3b 0a 0a 09 09 09 09 6d 65 6d 63 70 79 = 0;......memcpy
4040: 28 70 61 74 68 69 6e 66 6f 2c 20 26 61 70 70 66 (pathinfo, &appf
4050: 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 s_path_info_cach
4060: 65 5b 68 61 73 68 5f 69 64 78 5d 2c 20 73 69 7a e[hash_idx], siz
4070: 65 6f 66 28 2a 70 61 74 68 69 6e 66 6f 29 29 3b eof(*pathinfo));
4080: 0a 09 09 09 09 70 61 74 68 69 6e 66 6f 2d 3e 5f .....pathinfo->_
4090: 63 61 63 68 65 5f 70 61 74 68 20 3d 20 4e 55 4c cache_path = NUL
40a0: 4c 3b 0a 09 09 09 7d 0a 09 09 7d 0a 09 7d 0a 0a L;....}...}..}..
40b0: 09 70 74 68 72 65 61 64 5f 72 65 74 20 3d 20 70 .pthread_ret = p
40c0: 74 68 72 65 61 64 5f 6d 75 74 65 78 5f 75 6e 6c thread_mutex_unl
40d0: 6f 63 6b 28 26 61 70 70 66 73 5f 70 61 74 68 5f ock(&appfs_path_
40e0: 69 6e 66 6f 5f 63 61 63 68 65 5f 6d 75 74 65 78 info_cache_mutex
40f0: 29 3b 0a 09 69 66 20 28 70 74 68 72 65 61 64 5f );..if (pthread_
4100: 72 65 74 20 21 3d 20 30 29 20 7b 0a 09 09 41 50 ret != 0) {...AP
4110: 50 46 53 5f 44 45 42 55 47 28 22 55 6e 61 62 6c PFS_DEBUG("Unabl
4120: 65 20 74 6f 20 75 6e 6c 6f 63 6b 20 70 61 74 68 e to unlock path
4130: 5f 69 6e 66 6f 20 63 61 63 68 65 20 6d 75 74 65 _info cache mute
4140: 78 20 21 22 29 3b 0a 0a 09 09 72 65 74 75 72 6e x !");....return
4150: 28 2d 31 29 3b 0a 09 7d 0a 0a 09 69 66 20 28 72 (-1);..}...if (r
4160: 65 74 76 61 6c 20 3d 3d 20 30 29 20 7b 0a 09 09 etval == 0) {...
4170: 41 50 50 46 53 5f 44 45 42 55 47 28 22 43 61 63 APPFS_DEBUG("Cac
4180: 68 65 20 68 69 74 20 6f 6e 20 70 61 74 68 3d 25 he hit on path=%
4190: 73 2c 75 69 64 3d 25 6c 6c 69 22 2c 20 70 61 74 s,uid=%lli", pat
41a0: 68 2c 20 28 6c 6f 6e 67 20 6c 6f 6e 67 29 20 75 h, (long long) u
41b0: 69 64 29 3b 0a 09 7d 20 65 6c 73 65 20 7b 0a 09 id);..} else {..
41c0: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 43 61 .APPFS_DEBUG("Ca
41d0: 63 68 65 20 6d 69 73 73 20 6f 6e 20 70 61 74 68 che miss on path
41e0: 3d 25 73 2c 75 69 64 3d 25 6c 6c 69 22 2c 20 70 =%s,uid=%lli", p
41f0: 61 74 68 2c 20 28 6c 6f 6e 67 20 6c 6f 6e 67 29 ath, (long long)
4200: 20 75 69 64 29 3b 0a 09 7d 0a 0a 09 72 65 74 75 uid);..}...retu
4210: 72 6e 28 72 65 74 76 61 6c 29 3b 0a 7d 0a 0a 73 rn(retval);.}..s
4220: 74 61 74 69 63 20 76 6f 69 64 20 61 70 70 66 73 tatic void appfs
4230: 5f 67 65 74 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 _get_path_info_c
4240: 61 63 68 65 5f 61 64 64 28 63 6f 6e 73 74 20 63 ache_add(const c
4250: 68 61 72 20 2a 70 61 74 68 2c 20 75 69 64 5f 74 har *path, uid_t
4260: 20 75 69 64 2c 20 73 74 72 75 63 74 20 61 70 70 uid, struct app
4270: 66 73 5f 70 61 74 68 69 6e 66 6f 20 2a 70 61 74 fs_pathinfo *pat
4280: 68 69 6e 66 6f 29 20 7b 0a 09 75 6e 73 69 67 6e hinfo) {..unsign
4290: 65 64 20 69 6e 74 20 68 61 73 68 5f 69 64 78 3b ed int hash_idx;
42a0: 0a 09 69 6e 74 20 70 74 68 72 65 61 64 5f 72 65 ..int pthread_re
42b0: 74 3b 0a 0a 09 70 74 68 72 65 61 64 5f 72 65 74 t;...pthread_ret
42c0: 20 3d 20 70 74 68 72 65 61 64 5f 6d 75 74 65 78 = pthread_mutex
42d0: 5f 6c 6f 63 6b 28 26 61 70 70 66 73 5f 70 61 74 _lock(&appfs_pat
42e0: 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5f 6d 75 74 h_info_cache_mut
42f0: 65 78 29 3b 0a 09 69 66 20 28 70 74 68 72 65 61 ex);..if (pthrea
4300: 64 5f 72 65 74 20 21 3d 20 30 29 20 7b 0a 09 09 d_ret != 0) {...
4310: 41 50 50 46 53 5f 44 45 42 55 47 28 22 55 6e 61 APPFS_DEBUG("Una
4320: 62 6c 65 20 74 6f 20 6c 6f 63 6b 20 70 61 74 68 ble to lock path
4330: 5f 69 6e 66 6f 20 63 61 63 68 65 20 6d 75 74 65 _info cache mute
4340: 78 20 21 22 29 3b 0a 0a 09 09 72 65 74 75 72 6e x !");....return
4350: 3b 0a 09 7d 0a 0a 09 69 66 20 28 61 70 70 66 73 ;..}...if (appfs
4360: 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 _path_info_cache
4370: 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 61 70 == NULL) {...ap
4380: 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 pfs_path_info_ca
4390: 63 68 65 20 3d 20 63 61 6c 6c 6f 63 28 61 70 70 che = calloc(app
43a0: 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 fs_path_info_cac
43b0: 68 65 5f 73 69 7a 65 2c 20 73 69 7a 65 6f 66 28 he_size, sizeof(
43c0: 2a 61 70 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f *appfs_path_info
43d0: 5f 63 61 63 68 65 29 29 3b 0a 09 7d 0a 0a 09 68 _cache));..}...h
43e0: 61 73 68 5f 69 64 78 20 3d 20 28 61 70 70 66 73 ash_idx = (appfs
43f0: 5f 67 65 74 5f 70 61 74 68 5f 69 6e 6f 64 65 28 _get_path_inode(
4400: 70 61 74 68 2c 20 75 69 64 29 29 20 25 20 61 70 path, uid)) % ap
4410: 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 pfs_path_info_ca
4420: 63 68 65 5f 73 69 7a 65 3b 0a 0a 09 69 66 20 28 che_size;...if (
4430: 61 70 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f appfs_path_info_
4440: 63 61 63 68 65 5b 68 61 73 68 5f 69 64 78 5d 2e cache[hash_idx].
4450: 5f 63 61 63 68 65 5f 70 61 74 68 20 21 3d 20 4e _cache_path != N
4460: 55 4c 4c 29 20 7b 0a 09 09 66 72 65 65 28 61 70 ULL) {...free(ap
4470: 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 pfs_path_info_ca
4480: 63 68 65 5b 68 61 73 68 5f 69 64 78 5d 2e 5f 63 che[hash_idx]._c
4490: 61 63 68 65 5f 70 61 74 68 29 3b 0a 09 7d 0a 0a ache_path);..}..
44a0: 09 6d 65 6d 63 70 79 28 26 61 70 70 66 73 5f 70 .memcpy(&appfs_p
44b0: 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5b 68 ath_info_cache[h
44c0: 61 73 68 5f 69 64 78 5d 2c 20 70 61 74 68 69 6e ash_idx], pathin
44d0: 66 6f 2c 20 73 69 7a 65 6f 66 28 2a 70 61 74 68 fo, sizeof(*path
44e0: 69 6e 66 6f 29 29 3b 0a 0a 09 61 70 70 66 73 5f info));...appfs_
44f0: 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5b path_info_cache[
4500: 68 61 73 68 5f 69 64 78 5d 2e 5f 63 61 63 68 65 hash_idx]._cache
4510: 5f 70 61 74 68 20 3d 20 73 74 72 64 75 70 28 70 _path = strdup(p
4520: 61 74 68 29 3b 0a 09 61 70 70 66 73 5f 70 61 74 ath);..appfs_pat
4530: 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5b 68 61 73 h_info_cache[has
4540: 68 5f 69 64 78 5d 2e 5f 63 61 63 68 65 5f 75 69 h_idx]._cache_ui
4550: 64 20 20 3d 20 75 69 64 3b 0a 0a 09 70 74 68 72 d = uid;...pthr
4560: 65 61 64 5f 72 65 74 20 3d 20 70 74 68 72 65 61 ead_ret = pthrea
4570: 64 5f 6d 75 74 65 78 5f 75 6e 6c 6f 63 6b 28 26 d_mutex_unlock(&
4580: 61 70 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f appfs_path_info_
4590: 63 61 63 68 65 5f 6d 75 74 65 78 29 3b 0a 09 69 cache_mutex);..i
45a0: 66 20 28 70 74 68 72 65 61 64 5f 72 65 74 20 21 f (pthread_ret !
45b0: 3d 20 30 29 20 7b 0a 09 09 41 50 50 46 53 5f 44 = 0) {...APPFS_D
45c0: 45 42 55 47 28 22 55 6e 61 62 6c 65 20 74 6f 20 EBUG("Unable to
45d0: 75 6e 6c 6f 63 6b 20 70 61 74 68 5f 69 6e 66 6f unlock path_info
45e0: 20 63 61 63 68 65 20 6d 75 74 65 78 20 21 22 29 cache mutex !")
45f0: 3b 0a 0a 09 09 72 65 74 75 72 6e 3b 0a 09 7d 0a ;....return;..}.
4600: 0a 09 72 65 74 75 72 6e 3b 0a 7d 0a 0a 73 74 61 ..return;.}..sta
4610: 74 69 63 20 76 6f 69 64 20 61 70 70 66 73 5f 67 tic void appfs_g
4620: 65 74 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 et_path_info_cac
4630: 68 65 5f 72 6d 28 63 6f 6e 73 74 20 63 68 61 72 he_rm(const char
4640: 20 2a 70 61 74 68 2c 20 75 69 64 5f 74 20 75 69 *path, uid_t ui
4650: 64 29 20 7b 0a 09 75 6e 73 69 67 6e 65 64 20 69 d) {..unsigned i
4660: 6e 74 20 68 61 73 68 5f 69 64 78 3b 0a 09 69 6e nt hash_idx;..in
4670: 74 20 70 74 68 72 65 61 64 5f 72 65 74 3b 0a 0a t pthread_ret;..
4680: 09 70 74 68 72 65 61 64 5f 72 65 74 20 3d 20 70 .pthread_ret = p
4690: 74 68 72 65 61 64 5f 6d 75 74 65 78 5f 6c 6f 63 thread_mutex_loc
46a0: 6b 28 26 61 70 70 66 73 5f 70 61 74 68 5f 69 6e k(&appfs_path_in
46b0: 66 6f 5f 63 61 63 68 65 5f 6d 75 74 65 78 29 3b fo_cache_mutex);
46c0: 0a 09 69 66 20 28 70 74 68 72 65 61 64 5f 72 65 ..if (pthread_re
46d0: 74 20 21 3d 20 30 29 20 7b 0a 09 09 41 50 50 46 t != 0) {...APPF
46e0: 53 5f 44 45 42 55 47 28 22 55 6e 61 62 6c 65 20 S_DEBUG("Unable
46f0: 74 6f 20 6c 6f 63 6b 20 70 61 74 68 5f 69 6e 66 to lock path_inf
4700: 6f 20 63 61 63 68 65 20 6d 75 74 65 78 20 21 22 o cache mutex !"
4710: 29 3b 0a 0a 09 09 72 65 74 75 72 6e 3b 0a 09 7d );....return;..}
4720: 0a 0a 09 69 66 20 28 61 70 70 66 73 5f 70 61 74 ...if (appfs_pat
4730: 68 5f 69 6e 66 6f 5f 63 61 63 68 65 20 21 3d 20 h_info_cache !=
4740: 4e 55 4c 4c 29 20 7b 0a 09 09 68 61 73 68 5f 69 NULL) {...hash_i
4750: 64 78 20 3d 20 28 61 70 70 66 73 5f 67 65 74 5f dx = (appfs_get_
4760: 70 61 74 68 5f 69 6e 6f 64 65 28 70 61 74 68 2c path_inode(path,
4770: 20 75 69 64 29 29 20 25 20 61 70 70 66 73 5f 70 uid)) % appfs_p
4780: 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5f 73 ath_info_cache_s
4790: 69 7a 65 3b 0a 0a 09 09 69 66 20 28 61 70 70 66 ize;....if (appf
47a0: 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 s_path_info_cach
47b0: 65 5b 68 61 73 68 5f 69 64 78 5d 2e 5f 63 61 63 e[hash_idx]._cac
47c0: 68 65 5f 70 61 74 68 20 21 3d 20 4e 55 4c 4c 29 he_path != NULL)
47d0: 20 7b 0a 09 09 09 66 72 65 65 28 61 70 70 66 73 {....free(appfs
47e0: 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 _path_info_cache
47f0: 5b 68 61 73 68 5f 69 64 78 5d 2e 5f 63 61 63 68 [hash_idx]._cach
4800: 65 5f 70 61 74 68 29 3b 0a 0a 09 09 09 61 70 70 e_path);.....app
4810: 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 fs_path_info_cac
4820: 68 65 5b 68 61 73 68 5f 69 64 78 5d 2e 5f 63 61 he[hash_idx]._ca
4830: 63 68 65 5f 70 61 74 68 20 3d 20 4e 55 4c 4c 3b che_path = NULL;
4840: 0a 09 09 7d 0a 09 7d 0a 0a 09 70 74 68 72 65 61 ...}..}...pthrea
4850: 64 5f 72 65 74 20 3d 20 70 74 68 72 65 61 64 5f d_ret = pthread_
4860: 6d 75 74 65 78 5f 75 6e 6c 6f 63 6b 28 26 61 70 mutex_unlock(&ap
4870: 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 pfs_path_info_ca
4880: 63 68 65 5f 6d 75 74 65 78 29 3b 0a 09 69 66 20 che_mutex);..if
4890: 28 70 74 68 72 65 61 64 5f 72 65 74 20 21 3d 20 (pthread_ret !=
48a0: 30 29 20 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 0) {...APPFS_DEB
48b0: 55 47 28 22 55 6e 61 62 6c 65 20 74 6f 20 75 6e UG("Unable to un
48c0: 6c 6f 63 6b 20 70 61 74 68 5f 69 6e 66 6f 20 63 lock path_info c
48d0: 61 63 68 65 20 6d 75 74 65 78 20 21 22 29 3b 0a ache mutex !");.
48e0: 0a 09 09 72 65 74 75 72 6e 3b 0a 09 7d 0a 0a 09 ...return;..}...
48f0: 72 65 74 75 72 6e 3b 0a 7d 0a 0a 73 74 61 74 69 return;.}..stati
4900: 63 20 76 6f 69 64 20 61 70 70 66 73 5f 67 65 74 c void appfs_get
4910: 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 _path_info_cache
4920: 5f 66 6c 75 73 68 28 75 69 64 5f 74 20 75 69 64 _flush(uid_t uid
4930: 2c 20 69 6e 74 20 6e 65 77 5f 73 69 7a 65 29 20 , int new_size)
4940: 7b 0a 09 75 6e 73 69 67 6e 65 64 20 69 6e 74 20 {..unsigned int
4950: 69 64 78 3b 0a 09 69 6e 74 20 70 74 68 72 65 61 idx;..int pthrea
4960: 64 5f 72 65 74 3b 0a 0a 09 41 50 50 46 53 5f 44 d_ret;...APPFS_D
4970: 45 42 55 47 28 22 46 6c 75 73 68 69 6e 67 20 41 EBUG("Flushing A
4980: 70 70 46 53 20 63 61 63 68 65 20 28 75 69 64 20 ppFS cache (uid
4990: 3d 20 25 6c 6c 69 2c 20 6e 65 77 5f 73 69 7a 65 = %lli, new_size
49a0: 20 3d 20 25 69 29 22 2c 20 28 6c 6f 6e 67 20 6c = %i)", (long l
49b0: 6f 6e 67 29 20 75 69 64 2c 20 6e 65 77 5f 73 69 ong) uid, new_si
49c0: 7a 65 29 3b 0a 0a 09 70 74 68 72 65 61 64 5f 72 ze);...pthread_r
49d0: 65 74 20 3d 20 70 74 68 72 65 61 64 5f 6d 75 74 et = pthread_mut
49e0: 65 78 5f 6c 6f 63 6b 28 26 61 70 70 66 73 5f 70 ex_lock(&appfs_p
49f0: 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5f 6d ath_info_cache_m
4a00: 75 74 65 78 29 3b 0a 09 69 66 20 28 70 74 68 72 utex);..if (pthr
4a10: 65 61 64 5f 72 65 74 20 21 3d 20 30 29 20 7b 0a ead_ret != 0) {.
4a20: 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 55 ..APPFS_DEBUG("U
4a30: 6e 61 62 6c 65 20 74 6f 20 6c 6f 63 6b 20 70 61 nable to lock pa
4a40: 74 68 5f 69 6e 66 6f 20 63 61 63 68 65 20 6d 75 th_info cache mu
4a50: 74 65 78 20 21 22 29 3b 0a 0a 09 09 72 65 74 75 tex !");....retu
4a60: 72 6e 3b 0a 09 7d 0a 0a 09 69 66 20 28 61 70 70 rn;..}...if (app
4a70: 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 fs_path_info_cac
4a80: 68 65 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 he != NULL) {...
4a90: 66 6f 72 20 28 69 64 78 20 3d 20 30 3b 20 69 64 for (idx = 0; id
4aa0: 78 20 3c 20 61 70 70 66 73 5f 70 61 74 68 5f 69 x < appfs_path_i
4ab0: 6e 66 6f 5f 63 61 63 68 65 5f 73 69 7a 65 3b 20 nfo_cache_size;
4ac0: 69 64 78 2b 2b 29 20 7b 0a 09 09 09 69 66 20 28 idx++) {....if (
4ad0: 61 70 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f appfs_path_info_
4ae0: 63 61 63 68 65 5b 69 64 78 5d 2e 5f 63 61 63 68 cache[idx]._cach
4af0: 65 5f 70 61 74 68 20 21 3d 20 4e 55 4c 4c 29 20 e_path != NULL)
4b00: 7b 0a 09 09 09 09 69 66 20 28 75 69 64 20 21 3d {.....if (uid !=
4b10: 20 28 28 75 69 64 5f 74 29 20 2d 31 29 29 20 7b ((uid_t) -1)) {
4b20: 0a 09 09 09 09 09 69 66 20 28 61 70 70 66 73 5f ......if (appfs_
4b30: 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5b path_info_cache[
4b40: 69 64 78 5d 2e 5f 63 61 63 68 65 5f 75 69 64 20 idx]._cache_uid
4b50: 21 3d 20 75 69 64 29 20 7b 0a 09 09 09 09 09 09 != uid) {.......
4b60: 63 6f 6e 74 69 6e 75 65 3b 0a 09 09 09 09 09 7d continue;......}
4b70: 0a 09 09 09 09 7d 0a 0a 09 09 09 09 66 72 65 65 .....}......free
4b80: 28 61 70 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f (appfs_path_info
4b90: 5f 63 61 63 68 65 5b 69 64 78 5d 2e 5f 63 61 63 _cache[idx]._cac
4ba0: 68 65 5f 70 61 74 68 29 3b 0a 0a 09 09 09 09 61 he_path);......a
4bb0: 70 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 ppfs_path_info_c
4bc0: 61 63 68 65 5b 69 64 78 5d 2e 5f 63 61 63 68 65 ache[idx]._cache
4bd0: 5f 70 61 74 68 20 3d 20 4e 55 4c 4c 3b 0a 09 09 _path = NULL;...
4be0: 09 7d 0a 09 09 7d 0a 09 7d 0a 0a 09 69 66 20 28 .}...}..}...if (
4bf0: 75 69 64 20 3d 3d 20 28 28 75 69 64 5f 74 29 20 uid == ((uid_t)
4c00: 2d 31 29 29 20 7b 0a 09 09 66 72 65 65 28 61 70 -1)) {...free(ap
4c10: 70 66 73 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 pfs_path_info_ca
4c20: 63 68 65 29 3b 0a 0a 09 09 61 70 70 66 73 5f 70 che);....appfs_p
4c30: 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 20 3d ath_info_cache =
4c40: 20 4e 55 4c 4c 3b 0a 0a 09 09 69 66 20 28 6e 65 NULL;....if (ne
4c50: 77 5f 73 69 7a 65 20 21 3d 20 2d 31 29 20 7b 0a w_size != -1) {.
4c60: 09 09 09 61 70 70 66 73 5f 70 61 74 68 5f 69 6e ...appfs_path_in
4c70: 66 6f 5f 63 61 63 68 65 5f 73 69 7a 65 20 3d 20 fo_cache_size =
4c80: 6e 65 77 5f 73 69 7a 65 3b 0a 09 09 7d 0a 09 7d new_size;...}..}
4c90: 0a 0a 09 70 74 68 72 65 61 64 5f 72 65 74 20 3d ...pthread_ret =
4ca0: 20 70 74 68 72 65 61 64 5f 6d 75 74 65 78 5f 75 pthread_mutex_u
4cb0: 6e 6c 6f 63 6b 28 26 61 70 70 66 73 5f 70 61 74 nlock(&appfs_pat
4cc0: 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5f 6d 75 74 h_info_cache_mut
4cd0: 65 78 29 3b 0a 09 69 66 20 28 70 74 68 72 65 61 ex);..if (pthrea
4ce0: 64 5f 72 65 74 20 21 3d 20 30 29 20 7b 0a 09 09 d_ret != 0) {...
4cf0: 41 50 50 46 53 5f 44 45 42 55 47 28 22 55 6e 61 APPFS_DEBUG("Una
4d00: 62 6c 65 20 74 6f 20 75 6e 6c 6f 63 6b 20 70 61 ble to unlock pa
4d10: 74 68 5f 69 6e 66 6f 20 63 61 63 68 65 20 6d 75 th_info cache mu
4d20: 74 65 78 20 21 22 29 3b 0a 0a 09 09 72 65 74 75 tex !");....retu
4d30: 72 6e 3b 0a 09 7d 0a 0a 09 72 65 74 75 72 6e 3b rn;..}...return;
4d40: 0a 7d 0a 0a 2f 2a 20 47 65 74 20 69 6e 66 6f 72 .}../* Get infor
4d50: 6d 61 74 69 6f 6e 20 61 62 6f 75 74 20 61 20 70 mation about a p
4d60: 61 74 68 2c 20 61 6e 64 20 6f 70 74 69 6f 6e 61 ath, and optiona
4d70: 6c 6c 79 20 6c 69 73 74 20 63 68 69 6c 64 72 65 lly list childre
4d80: 6e 20 2a 2f 0a 73 74 61 74 69 63 20 69 6e 74 20 n */.static int
4d90: 61 70 70 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 appfs_get_path_i
4da0: 6e 66 6f 28 63 6f 6e 73 74 20 63 68 61 72 20 2a nfo(const char *
4db0: 70 61 74 68 2c 20 73 74 72 75 63 74 20 61 70 70 path, struct app
4dc0: 66 73 5f 70 61 74 68 69 6e 66 6f 20 2a 70 61 74 fs_pathinfo *pat
4dd0: 68 69 6e 66 6f 29 20 7b 0a 09 54 63 6c 5f 49 6e hinfo) {..Tcl_In
4de0: 74 65 72 70 20 2a 69 6e 74 65 72 70 3b 0a 09 54 terp *interp;..T
4df0: 63 6c 5f 4f 62 6a 20 2a 61 74 74 72 73 5f 64 69 cl_Obj *attrs_di
4e00: 63 74 2c 20 2a 61 74 74 72 5f 76 61 6c 75 65 3b ct, *attr_value;
4e10: 0a 09 63 6f 6e 73 74 20 63 68 61 72 20 2a 61 74 ..const char *at
4e20: 74 72 5f 76 61 6c 75 65 5f 73 74 72 2c 20 2a 61 tr_value_str, *a
4e30: 74 74 72 5f 76 61 6c 75 65 5f 73 74 72 5f 69 3b ttr_value_str_i;
4e40: 0a 09 54 63 6c 5f 57 69 64 65 49 6e 74 20 61 74 ..Tcl_WideInt at
4e50: 74 72 5f 76 61 6c 75 65 5f 77 69 64 65 3b 0a 09 tr_value_wide;..
4e60: 69 6e 74 20 61 74 74 72 5f 76 61 6c 75 65 5f 69 int attr_value_i
4e70: 6e 74 3b 0a 09 73 74 61 74 69 63 20 5f 5f 74 68 nt;..static __th
4e80: 72 65 61 64 20 54 63 6c 5f 4f 62 6a 20 2a 61 74 read Tcl_Obj *at
4e90: 74 72 5f 6b 65 79 5f 74 79 70 65 20 3d 20 4e 55 tr_key_type = NU
4ea0: 4c 4c 2c 20 2a 61 74 74 72 5f 6b 65 79 5f 70 65 LL, *attr_key_pe
4eb0: 72 6d 73 20 3d 20 4e 55 4c 4c 2c 20 2a 61 74 74 rms = NULL, *att
4ec0: 72 5f 6b 65 79 5f 73 69 7a 65 20 3d 20 4e 55 4c r_key_size = NUL
4ed0: 4c 2c 20 2a 61 74 74 72 5f 6b 65 79 5f 74 69 6d L, *attr_key_tim
4ee0: 65 20 3d 20 4e 55 4c 4c 2c 20 2a 61 74 74 72 5f e = NULL, *attr_
4ef0: 6b 65 79 5f 73 6f 75 72 63 65 20 3d 20 4e 55 4c key_source = NUL
4f00: 4c 2c 20 2a 61 74 74 72 5f 6b 65 79 5f 63 68 69 L, *attr_key_chi
4f10: 6c 64 63 6f 75 6e 74 20 3d 20 4e 55 4c 4c 2c 20 ldcount = NULL,
4f20: 2a 61 74 74 72 5f 6b 65 79 5f 70 61 63 6b 61 67 *attr_key_packag
4f30: 65 64 20 3d 20 4e 55 4c 4c 3b 0a 09 69 6e 74 20 ed = NULL;..int
4f40: 63 61 63 68 65 5f 72 65 74 3b 0a 09 69 6e 74 20 cache_ret;..int
4f50: 74 63 6c 5f 72 65 74 3b 0a 09 69 6e 74 20 72 65 tcl_ret;..int re
4f60: 74 76 61 6c 3b 0a 09 75 69 64 5f 74 20 66 73 75 tval;..uid_t fsu
4f70: 69 64 3b 0a 0a 09 72 65 74 76 61 6c 20 3d 20 30 id;...retval = 0
4f80: 3b 0a 0a 09 66 73 75 69 64 20 3d 20 61 70 70 66 ;...fsuid = appf
4f90: 73 5f 67 65 74 5f 66 73 75 69 64 28 29 3b 0a 0a s_get_fsuid();..
4fa0: 09 63 61 63 68 65 5f 72 65 74 20 3d 20 61 70 70 .cache_ret = app
4fb0: 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 6e 66 6f fs_get_path_info
4fc0: 5f 63 61 63 68 65 5f 67 65 74 28 70 61 74 68 2c _cache_get(path,
4fd0: 20 66 73 75 69 64 2c 20 70 61 74 68 69 6e 66 6f fsuid, pathinfo
4fe0: 29 3b 0a 09 69 66 20 28 63 61 63 68 65 5f 72 65 );..if (cache_re
4ff0: 74 20 3d 3d 20 30 29 20 7b 0a 09 09 69 66 20 28 t == 0) {...if (
5000: 70 61 74 68 69 6e 66 6f 2d 3e 74 79 70 65 20 3d pathinfo->type =
5010: 3d 20 41 50 50 46 53 5f 50 41 54 48 54 59 50 45 = APPFS_PATHTYPE
5020: 5f 44 4f 45 53 5f 4e 4f 54 5f 45 58 49 53 54 29 _DOES_NOT_EXIST)
5030: 20 7b 0a 09 09 09 41 50 50 46 53 5f 44 45 42 55 {....APPFS_DEBU
5040: 47 28 22 52 65 74 75 72 6e 69 6e 67 20 66 72 6f G("Returning fro
5050: 6d 20 63 61 63 68 65 3a 20 64 6f 65 73 20 6e 6f m cache: does no
5060: 74 20 65 78 69 73 74 20 5c 22 25 73 5c 22 22 2c t exist \"%s\"",
5070: 20 70 61 74 68 29 3b 0a 0a 09 09 09 72 65 74 75 path);.....retu
5080: 72 6e 28 2d 45 4e 4f 45 4e 54 29 3b 0a 09 09 7d rn(-ENOENT);...}
5090: 0a 0a 09 09 69 66 20 28 70 61 74 68 69 6e 66 6f ....if (pathinfo
50a0: 2d 3e 74 79 70 65 20 3d 3d 20 41 50 50 46 53 5f ->type == APPFS_
50b0: 50 41 54 48 54 59 50 45 5f 49 4e 56 41 4c 49 44 PATHTYPE_INVALID
50c0: 29 20 7b 0a 09 09 09 41 50 50 46 53 5f 44 45 42 ) {....APPFS_DEB
50d0: 55 47 28 22 52 65 74 75 72 6e 69 6e 67 20 66 72 UG("Returning fr
50e0: 6f 6d 20 63 61 63 68 65 3a 20 69 6e 76 61 6c 69 om cache: invali
50f0: 64 20 6f 62 6a 65 63 74 20 5c 22 25 73 5c 22 22 d object \"%s\""
5100: 2c 20 70 61 74 68 29 3b 0a 0a 09 09 09 72 65 74 , path);.....ret
5110: 75 72 6e 28 2d 45 49 4f 29 3b 0a 09 09 7d 0a 0a urn(-EIO);...}..
5120: 09 09 72 65 74 75 72 6e 28 30 29 3b 0a 09 7d 0a ..return(0);..}.
5130: 0a 09 69 6e 74 65 72 70 20 3d 20 61 70 70 66 73 ..interp = appfs
5140: 5f 54 63 6c 49 6e 74 65 72 70 28 29 3b 0a 09 69 _TclInterp();..i
5150: 66 20 28 69 6e 74 65 72 70 20 3d 3d 20 4e 55 4c f (interp == NUL
5160: 4c 29 20 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 L) {...APPFS_DEB
5170: 55 47 28 22 65 72 72 6f 72 3a 20 55 6e 61 62 6c UG("error: Unabl
5180: 65 20 74 6f 20 67 65 74 20 61 6e 20 69 6e 74 65 e to get an inte
5190: 72 70 72 65 74 65 72 22 29 3b 0a 0a 09 09 72 65 rpreter");....re
51a0: 74 75 72 6e 28 2d 45 49 4f 29 3b 0a 09 7d 0a 0a turn(-EIO);..}..
51b0: 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 .appfs_call_libt
51c0: 63 6c 28 54 63 6c 5f 50 72 65 73 65 72 76 65 28 cl(Tcl_Preserve(
51d0: 69 6e 74 65 72 70 29 3b 29 0a 0a 09 74 63 6c 5f interp);)...tcl_
51e0: 72 65 74 20 3d 20 61 70 70 66 73 5f 54 63 6c 5f ret = appfs_Tcl_
51f0: 45 76 61 6c 28 69 6e 74 65 72 70 2c 20 32 2c 20 Eval(interp, 2,
5200: 22 3a 3a 61 70 70 66 73 3a 3a 67 65 74 61 74 74 "::appfs::getatt
5210: 72 22 2c 20 70 61 74 68 29 3b 0a 09 69 66 20 28 r", path);..if (
5220: 74 63 6c 5f 72 65 74 20 21 3d 20 54 43 4c 5f 4f tcl_ret != TCL_O
5230: 4b 29 20 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 K) {...APPFS_DEB
5240: 55 47 28 22 3a 3a 61 70 70 66 73 3a 3a 67 65 74 UG("::appfs::get
5250: 61 74 74 72 28 25 73 29 20 66 61 69 6c 65 64 2e attr(%s) failed.
5260: 22 2c 20 70 61 74 68 29 3b 0a 09 09 61 70 70 66 ", path);...appf
5270: 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 s_call_libtcl(..
5280: 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 54 ..APPFS_DEBUG("T
5290: 63 6c 20 45 72 72 6f 72 20 69 73 3a 20 25 73 22 cl Error is: %s"
52a0: 2c 20 54 63 6c 5f 47 65 74 53 74 72 69 6e 67 52 , Tcl_GetStringR
52b0: 65 73 75 6c 74 28 69 6e 74 65 72 70 29 29 3b 0a esult(interp));.
52c0: 09 09 29 0a 0a 09 09 70 61 74 68 69 6e 66 6f 2d ..)....pathinfo-
52d0: 3e 74 79 70 65 20 3d 20 41 50 50 46 53 5f 50 41 >type = APPFS_PA
52e0: 54 48 54 59 50 45 5f 44 4f 45 53 5f 4e 4f 54 5f THTYPE_DOES_NOT_
52f0: 45 58 49 53 54 3b 0a 0a 09 09 61 70 70 66 73 5f EXIST;....appfs_
5300: 67 65 74 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 get_path_info_ca
5310: 63 68 65 5f 61 64 64 28 70 61 74 68 2c 20 66 73 che_add(path, fs
5320: 75 69 64 2c 20 70 61 74 68 69 6e 66 6f 29 3b 0a uid, pathinfo);.
5330: 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 ...appfs_call_li
5340: 62 74 63 6c 28 54 63 6c 5f 52 65 6c 65 61 73 65 btcl(Tcl_Release
5350: 28 69 6e 74 65 72 70 29 3b 29 0a 0a 09 09 72 65 (interp);)....re
5360: 74 75 72 6e 28 2d 45 4e 4f 45 4e 54 29 3b 0a 09 turn(-ENOENT);..
5370: 7d 0a 0a 09 69 66 20 28 61 74 74 72 5f 6b 65 79 }...if (attr_key
5380: 5f 74 79 70 65 20 3d 3d 20 4e 55 4c 4c 29 20 7b _type == NULL) {
5390: 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 ...appfs_call_li
53a0: 62 74 63 6c 28 0a 09 09 09 61 74 74 72 5f 6b 65 btcl(....attr_ke
53b0: 79 5f 74 79 70 65 20 20 20 20 20 20 20 3d 20 54 y_type = T
53c0: 63 6c 5f 4e 65 77 53 74 72 69 6e 67 4f 62 6a 28 cl_NewStringObj(
53d0: 22 74 79 70 65 22 2c 20 2d 31 29 3b 0a 09 09 09 "type", -1);....
53e0: 61 74 74 72 5f 6b 65 79 5f 70 65 72 6d 73 20 20 attr_key_perms
53f0: 20 20 20 20 3d 20 54 63 6c 5f 4e 65 77 53 74 72 = Tcl_NewStr
5400: 69 6e 67 4f 62 6a 28 22 70 65 72 6d 73 22 2c 20 ingObj("perms",
5410: 2d 31 29 3b 0a 09 09 09 61 74 74 72 5f 6b 65 79 -1);....attr_key
5420: 5f 73 69 7a 65 20 20 20 20 20 20 20 3d 20 54 63 _size = Tc
5430: 6c 5f 4e 65 77 53 74 72 69 6e 67 4f 62 6a 28 22 l_NewStringObj("
5440: 73 69 7a 65 22 2c 20 2d 31 29 3b 0a 09 09 09 61 size", -1);....a
5450: 74 74 72 5f 6b 65 79 5f 74 69 6d 65 20 20 20 20 ttr_key_time
5460: 20 20 20 3d 20 54 63 6c 5f 4e 65 77 53 74 72 69 = Tcl_NewStri
5470: 6e 67 4f 62 6a 28 22 74 69 6d 65 22 2c 20 2d 31 ngObj("time", -1
5480: 29 3b 0a 09 09 09 61 74 74 72 5f 6b 65 79 5f 73 );....attr_key_s
5490: 6f 75 72 63 65 20 20 20 20 20 3d 20 54 63 6c 5f ource = Tcl_
54a0: 4e 65 77 53 74 72 69 6e 67 4f 62 6a 28 22 73 6f NewStringObj("so
54b0: 75 72 63 65 22 2c 20 2d 31 29 3b 0a 09 09 09 61 urce", -1);....a
54c0: 74 74 72 5f 6b 65 79 5f 63 68 69 6c 64 63 6f 75 ttr_key_childcou
54d0: 6e 74 20 3d 20 54 63 6c 5f 4e 65 77 53 74 72 69 nt = Tcl_NewStri
54e0: 6e 67 4f 62 6a 28 22 63 68 69 6c 64 63 6f 75 6e ngObj("childcoun
54f0: 74 22 2c 20 2d 31 29 3b 0a 09 09 09 61 74 74 72 t", -1);....attr
5500: 5f 6b 65 79 5f 70 61 63 6b 61 67 65 64 20 20 20 _key_packaged
5510: 3d 20 54 63 6c 5f 4e 65 77 53 74 72 69 6e 67 4f = Tcl_NewStringO
5520: 62 6a 28 22 70 61 63 6b 61 67 65 64 22 2c 20 2d bj("packaged", -
5530: 31 29 3b 0a 0a 09 09 09 54 63 6c 5f 49 6e 63 72 1);.....Tcl_Incr
5540: 52 65 66 43 6f 75 6e 74 28 61 74 74 72 5f 6b 65 RefCount(attr_ke
5550: 79 5f 74 79 70 65 29 3b 0a 09 09 09 54 63 6c 5f y_type);....Tcl_
5560: 49 6e 63 72 52 65 66 43 6f 75 6e 74 28 61 74 74 IncrRefCount(att
5570: 72 5f 6b 65 79 5f 70 65 72 6d 73 29 3b 0a 09 09 r_key_perms);...
5580: 09 54 63 6c 5f 49 6e 63 72 52 65 66 43 6f 75 6e .Tcl_IncrRefCoun
5590: 74 28 61 74 74 72 5f 6b 65 79 5f 73 69 7a 65 29 t(attr_key_size)
55a0: 3b 0a 09 09 09 54 63 6c 5f 49 6e 63 72 52 65 66 ;....Tcl_IncrRef
55b0: 43 6f 75 6e 74 28 61 74 74 72 5f 6b 65 79 5f 74 Count(attr_key_t
55c0: 69 6d 65 29 3b 0a 09 09 09 54 63 6c 5f 49 6e 63 ime);....Tcl_Inc
55d0: 72 52 65 66 43 6f 75 6e 74 28 61 74 74 72 5f 6b rRefCount(attr_k
55e0: 65 79 5f 73 6f 75 72 63 65 29 3b 0a 09 09 09 54 ey_source);....T
55f0: 63 6c 5f 49 6e 63 72 52 65 66 43 6f 75 6e 74 28 cl_IncrRefCount(
5600: 61 74 74 72 5f 6b 65 79 5f 63 68 69 6c 64 63 6f attr_key_childco
5610: 75 6e 74 29 3b 0a 09 09 09 54 63 6c 5f 49 6e 63 unt);....Tcl_Inc
5620: 72 52 65 66 43 6f 75 6e 74 28 61 74 74 72 5f 6b rRefCount(attr_k
5630: 65 79 5f 70 61 63 6b 61 67 65 64 29 3b 0a 09 09 ey_packaged);...
5640: 29 0a 09 7d 0a 0a 09 61 70 70 66 73 5f 63 61 6c )..}...appfs_cal
5650: 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 61 74 74 72 l_libtcl(...attr
5660: 73 5f 64 69 63 74 20 3d 20 54 63 6c 5f 47 65 74 s_dict = Tcl_Get
5670: 4f 62 6a 52 65 73 75 6c 74 28 69 6e 74 65 72 70 ObjResult(interp
5680: 29 3b 0a 09 09 74 63 6c 5f 72 65 74 20 3d 20 54 );...tcl_ret = T
5690: 63 6c 5f 44 69 63 74 4f 62 6a 47 65 74 28 69 6e cl_DictObjGet(in
56a0: 74 65 72 70 2c 20 61 74 74 72 73 5f 64 69 63 74 terp, attrs_dict
56b0: 2c 20 61 74 74 72 5f 6b 65 79 5f 74 79 70 65 2c , attr_key_type,
56c0: 20 26 61 74 74 72 5f 76 61 6c 75 65 29 3b 0a 09 &attr_value);..
56d0: 29 0a 09 69 66 20 28 74 63 6c 5f 72 65 74 20 21 )..if (tcl_ret !
56e0: 3d 20 54 43 4c 5f 4f 4b 29 20 7b 0a 09 09 41 50 = TCL_OK) {...AP
56f0: 50 46 53 5f 44 45 42 55 47 28 22 5b 64 69 63 74 PFS_DEBUG("[dict
5700: 20 67 65 74 20 5c 22 74 79 70 65 5c 22 5d 20 66 get \"type\"] f
5710: 61 69 6c 65 64 22 29 3b 0a 09 09 61 70 70 66 73 ailed");...appfs
5720: 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 _call_libtcl(...
5730: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 54 63 .APPFS_DEBUG("Tc
5740: 6c 20 45 72 72 6f 72 20 69 73 3a 20 25 73 22 2c l Error is: %s",
5750: 20 54 63 6c 5f 47 65 74 53 74 72 69 6e 67 52 65 Tcl_GetStringRe
5760: 73 75 6c 74 28 69 6e 74 65 72 70 29 29 3b 0a 09 sult(interp));..
5770: 09 29 0a 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c .)....appfs_call
5780: 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 52 65 6c 65 _libtcl(Tcl_Rele
5790: 61 73 65 28 69 6e 74 65 72 70 29 3b 29 0a 0a 09 ase(interp);)...
57a0: 09 72 65 74 75 72 6e 28 2d 45 49 4f 29 3b 0a 09 .return(-EIO);..
57b0: 7d 0a 0a 09 69 66 20 28 61 74 74 72 5f 76 61 6c }...if (attr_val
57c0: 75 65 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 ue == NULL) {...
57d0: 41 50 50 46 53 5f 44 45 42 55 47 28 22 65 72 72 APPFS_DEBUG("err
57e0: 6f 72 3a 20 55 6e 61 62 6c 65 20 74 6f 20 67 65 or: Unable to ge
57f0: 74 20 74 79 70 65 20 66 6f 72 20 5c 22 25 73 5c t type for \"%s\
5800: 22 20 66 72 6f 6d 20 54 63 6c 22 2c 20 70 61 74 " from Tcl", pat
5810: 68 29 3b 0a 0a 09 09 61 70 70 66 73 5f 63 61 6c h);....appfs_cal
5820: 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 52 65 6c l_libtcl(Tcl_Rel
5830: 65 61 73 65 28 69 6e 74 65 72 70 29 3b 29 0a 0a ease(interp);)..
5840: 09 09 72 65 74 75 72 6e 28 2d 45 49 4f 29 3b 0a ..return(-EIO);.
5850: 09 7d 0a 0a 09 70 61 74 68 69 6e 66 6f 2d 3e 70 .}...pathinfo->p
5860: 61 63 6b 61 67 65 64 20 3d 20 30 3b 0a 0a 09 61 ackaged = 0;...a
5870: 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c ppfs_call_libtcl
5880: 28 0a 09 09 61 74 74 72 5f 76 61 6c 75 65 5f 73 (...attr_value_s
5890: 74 72 20 3d 20 54 63 6c 5f 47 65 74 53 74 72 69 tr = Tcl_GetStri
58a0: 6e 67 28 61 74 74 72 5f 76 61 6c 75 65 29 3b 0a ng(attr_value);.
58b0: 0a 09 09 73 77 69 74 63 68 20 28 61 74 74 72 5f ...switch (attr_
58c0: 76 61 6c 75 65 5f 73 74 72 5b 30 5d 29 20 7b 0a value_str[0]) {.
58d0: 09 09 09 63 61 73 65 20 27 64 27 3a 20 2f 2a 20 ...case 'd': /*
58e0: 64 69 72 65 63 74 6f 72 79 20 2a 2f 0a 09 09 09 directory */....
58f0: 09 70 61 74 68 69 6e 66 6f 2d 3e 74 79 70 65 20 .pathinfo->type
5900: 3d 20 41 50 50 46 53 5f 50 41 54 48 54 59 50 45 = APPFS_PATHTYPE
5910: 5f 44 49 52 45 43 54 4f 52 59 3b 0a 09 09 09 09 _DIRECTORY;.....
5920: 70 61 74 68 69 6e 66 6f 2d 3e 74 79 70 65 69 6e pathinfo->typein
5930: 66 6f 2e 64 69 72 2e 63 68 69 6c 64 63 6f 75 6e fo.dir.childcoun
5940: 74 20 3d 20 30 3b 0a 0a 09 09 09 09 54 63 6c 5f t = 0;......Tcl_
5950: 44 69 63 74 4f 62 6a 47 65 74 28 69 6e 74 65 72 DictObjGet(inter
5960: 70 2c 20 61 74 74 72 73 5f 64 69 63 74 2c 20 61 p, attrs_dict, a
5970: 74 74 72 5f 6b 65 79 5f 63 68 69 6c 64 63 6f 75 ttr_key_childcou
5980: 6e 74 2c 20 26 61 74 74 72 5f 76 61 6c 75 65 29 nt, &attr_value)
5990: 3b 0a 09 09 09 09 69 66 20 28 61 74 74 72 5f 76 ;.....if (attr_v
59a0: 61 6c 75 65 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a alue != NULL) {.
59b0: 09 09 09 09 09 74 63 6c 5f 72 65 74 20 3d 20 54 .....tcl_ret = T
59c0: 63 6c 5f 47 65 74 57 69 64 65 49 6e 74 46 72 6f cl_GetWideIntFro
59d0: 6d 4f 62 6a 28 4e 55 4c 4c 2c 20 61 74 74 72 5f mObj(NULL, attr_
59e0: 76 61 6c 75 65 2c 20 26 61 74 74 72 5f 76 61 6c value, &attr_val
59f0: 75 65 5f 77 69 64 65 29 3b 0a 09 09 09 09 09 69 ue_wide);......i
5a00: 66 20 28 74 63 6c 5f 72 65 74 20 3d 3d 20 54 43 f (tcl_ret == TC
5a10: 4c 5f 4f 4b 29 20 7b 0a 09 09 09 09 09 09 70 61 L_OK) {.......pa
5a20: 74 68 69 6e 66 6f 2d 3e 74 79 70 65 69 6e 66 6f thinfo->typeinfo
5a30: 2e 64 69 72 2e 63 68 69 6c 64 63 6f 75 6e 74 20 .dir.childcount
5a40: 3d 20 61 74 74 72 5f 76 61 6c 75 65 5f 77 69 64 = attr_value_wid
5a50: 65 3b 0a 09 09 09 09 09 7d 0a 09 09 09 09 7d 0a e;......}.....}.
5a60: 0a 09 09 09 09 62 72 65 61 6b 3b 0a 09 09 09 63 .....break;....c
5a70: 61 73 65 20 27 66 27 3a 20 2f 2a 20 66 69 6c 65 ase 'f': /* file
5a80: 20 2a 2f 0a 09 09 09 09 70 61 74 68 69 6e 66 6f */.....pathinfo
5a90: 2d 3e 74 79 70 65 20 3d 20 41 50 50 46 53 5f 50 ->type = APPFS_P
5aa0: 41 54 48 54 59 50 45 5f 46 49 4c 45 3b 0a 09 09 ATHTYPE_FILE;...
5ab0: 09 09 70 61 74 68 69 6e 66 6f 2d 3e 74 79 70 65 ..pathinfo->type
5ac0: 69 6e 66 6f 2e 66 69 6c 65 2e 73 69 7a 65 20 3d info.file.size =
5ad0: 20 30 3b 0a 09 09 09 09 70 61 74 68 69 6e 66 6f 0;.....pathinfo
5ae0: 2d 3e 74 79 70 65 69 6e 66 6f 2e 66 69 6c 65 2e ->typeinfo.file.
5af0: 65 78 65 63 75 74 61 62 6c 65 20 3d 20 30 3b 0a executable = 0;.
5b00: 09 09 09 09 70 61 74 68 69 6e 66 6f 2d 3e 74 79 ....pathinfo->ty
5b10: 70 65 69 6e 66 6f 2e 66 69 6c 65 2e 73 75 69 64 peinfo.file.suid
5b20: 52 6f 6f 74 20 3d 20 30 3b 0a 09 09 09 09 70 61 Root = 0;.....pa
5b30: 74 68 69 6e 66 6f 2d 3e 74 79 70 65 69 6e 66 6f thinfo->typeinfo
5b40: 2e 66 69 6c 65 2e 77 6f 72 6c 64 61 63 63 65 73 .file.worldacces
5b50: 73 69 62 6c 65 20 3d 20 30 3b 0a 0a 09 09 09 09 sible = 0;......
5b60: 54 63 6c 5f 44 69 63 74 4f 62 6a 47 65 74 28 69 Tcl_DictObjGet(i
5b70: 6e 74 65 72 70 2c 20 61 74 74 72 73 5f 64 69 63 nterp, attrs_dic
5b80: 74 2c 20 61 74 74 72 5f 6b 65 79 5f 73 69 7a 65 t, attr_key_size
5b90: 2c 20 26 61 74 74 72 5f 76 61 6c 75 65 29 3b 0a , &attr_value);.
5ba0: 09 09 09 09 69 66 20 28 61 74 74 72 5f 76 61 6c ....if (attr_val
5bb0: 75 65 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 ue != NULL) {...
5bc0: 09 09 09 74 63 6c 5f 72 65 74 20 3d 20 54 63 6c ...tcl_ret = Tcl
5bd0: 5f 47 65 74 57 69 64 65 49 6e 74 46 72 6f 6d 4f _GetWideIntFromO
5be0: 62 6a 28 4e 55 4c 4c 2c 20 61 74 74 72 5f 76 61 bj(NULL, attr_va
5bf0: 6c 75 65 2c 20 26 61 74 74 72 5f 76 61 6c 75 65 lue, &attr_value
5c00: 5f 77 69 64 65 29 3b 0a 09 09 09 09 09 69 66 20 _wide);......if
5c10: 28 74 63 6c 5f 72 65 74 20 3d 3d 20 54 43 4c 5f (tcl_ret == TCL_
5c20: 4f 4b 29 20 7b 0a 09 09 09 09 09 09 70 61 74 68 OK) {.......path
5c30: 69 6e 66 6f 2d 3e 74 79 70 65 69 6e 66 6f 2e 66 info->typeinfo.f
5c40: 69 6c 65 2e 73 69 7a 65 20 3d 20 61 74 74 72 5f ile.size = attr_
5c50: 76 61 6c 75 65 5f 77 69 64 65 3b 0a 09 09 09 09 value_wide;.....
5c60: 09 7d 0a 09 09 09 09 7d 0a 0a 09 09 09 09 54 63 .}.....}......Tc
5c70: 6c 5f 44 69 63 74 4f 62 6a 47 65 74 28 69 6e 74 l_DictObjGet(int
5c80: 65 72 70 2c 20 61 74 74 72 73 5f 64 69 63 74 2c erp, attrs_dict,
5c90: 20 61 74 74 72 5f 6b 65 79 5f 70 65 72 6d 73 2c attr_key_perms,
5ca0: 20 26 61 74 74 72 5f 76 61 6c 75 65 29 3b 0a 09 &attr_value);..
5cb0: 09 09 09 69 66 20 28 61 74 74 72 5f 76 61 6c 75 ...if (attr_valu
5cc0: 65 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 09 e != NULL) {....
5cd0: 09 09 61 74 74 72 5f 76 61 6c 75 65 5f 73 74 72 ..attr_value_str
5ce0: 20 3d 20 54 63 6c 5f 47 65 74 53 74 72 69 6e 67 = Tcl_GetString
5cf0: 28 61 74 74 72 5f 76 61 6c 75 65 29 3b 0a 09 09 (attr_value);...
5d00: 09 09 09 66 6f 72 20 28 61 74 74 72 5f 76 61 6c ...for (attr_val
5d10: 75 65 5f 73 74 72 5f 69 20 3d 20 26 61 74 74 72 ue_str_i = &attr
5d20: 5f 76 61 6c 75 65 5f 73 74 72 5b 30 5d 3b 20 2a _value_str[0]; *
5d30: 61 74 74 72 5f 76 61 6c 75 65 5f 73 74 72 5f 69 attr_value_str_i
5d40: 20 21 3d 20 27 5c 30 27 3b 20 61 74 74 72 5f 76 != '\0'; attr_v
5d50: 61 6c 75 65 5f 73 74 72 5f 69 2b 2b 29 20 7b 0a alue_str_i++) {.
5d60: 09 09 09 09 09 09 73 77 69 74 63 68 20 28 2a 61 ......switch (*a
5d70: 74 74 72 5f 76 61 6c 75 65 5f 73 74 72 5f 69 29 ttr_value_str_i)
5d80: 20 7b 0a 09 09 09 09 09 09 09 63 61 73 65 20 27 {........case '
5d90: 78 27 3a 0a 09 09 09 09 09 09 09 09 70 61 74 68 x':.........path
5da0: 69 6e 66 6f 2d 3e 74 79 70 65 69 6e 66 6f 2e 66 info->typeinfo.f
5db0: 69 6c 65 2e 65 78 65 63 75 74 61 62 6c 65 20 3d ile.executable =
5dc0: 20 31 3b 0a 0a 09 09 09 09 09 09 09 09 62 72 65 1;..........bre
5dd0: 61 6b 3b 0a 09 09 09 09 09 09 09 63 61 73 65 20 ak;........case
5de0: 27 55 27 3a 0a 09 09 09 09 09 09 09 09 70 61 74 'U':.........pat
5df0: 68 69 6e 66 6f 2d 3e 74 79 70 65 69 6e 66 6f 2e hinfo->typeinfo.
5e00: 66 69 6c 65 2e 73 75 69 64 52 6f 6f 74 20 3d 20 file.suidRoot =
5e10: 31 3b 0a 0a 09 09 09 09 09 09 09 09 62 72 65 61 1;..........brea
5e20: 6b 3b 0a 09 09 09 09 09 09 09 63 61 73 65 20 27 k;........case '
5e30: 2d 27 3a 0a 09 09 09 09 09 09 09 09 70 61 74 68 -':.........path
5e40: 69 6e 66 6f 2d 3e 74 79 70 65 69 6e 66 6f 2e 66 info->typeinfo.f
5e50: 69 6c 65 2e 77 6f 72 6c 64 61 63 63 65 73 73 69 ile.worldaccessi
5e60: 62 6c 65 20 3d 20 31 3b 0a 0a 09 09 09 09 09 09 ble = 1;........
5e70: 09 09 62 72 65 61 6b 3b 0a 09 09 09 09 09 09 7d ..break;.......}
5e80: 0a 09 09 09 09 09 7d 0a 09 09 09 09 7d 0a 09 09 ......}.....}...
5e90: 09 09 62 72 65 61 6b 3b 0a 09 09 09 63 61 73 65 ..break;....case
5ea0: 20 27 73 27 3a 20 2f 2a 20 73 79 6d 6c 69 6e 6b 's': /* symlink
5eb0: 20 2a 2f 0a 09 09 09 09 70 61 74 68 69 6e 66 6f */.....pathinfo
5ec0: 2d 3e 74 79 70 65 20 3d 20 41 50 50 46 53 5f 50 ->type = APPFS_P
5ed0: 41 54 48 54 59 50 45 5f 53 59 4d 4c 49 4e 4b 3b ATHTYPE_SYMLINK;
5ee0: 0a 09 09 09 09 70 61 74 68 69 6e 66 6f 2d 3e 74 .....pathinfo->t
5ef0: 79 70 65 69 6e 66 6f 2e 73 79 6d 6c 69 6e 6b 2e ypeinfo.symlink.
5f00: 73 69 7a 65 20 3d 20 30 3b 0a 09 09 09 09 70 61 size = 0;.....pa
5f10: 74 68 69 6e 66 6f 2d 3e 74 79 70 65 69 6e 66 6f thinfo->typeinfo
5f20: 2e 73 79 6d 6c 69 6e 6b 2e 73 6f 75 72 63 65 5b .symlink.source[
5f30: 30 5d 20 3d 20 27 5c 30 27 3b 0a 0a 09 09 09 09 0] = '\0';......
5f40: 54 63 6c 5f 44 69 63 74 4f 62 6a 47 65 74 28 69 Tcl_DictObjGet(i
5f50: 6e 74 65 72 70 2c 20 61 74 74 72 73 5f 64 69 63 nterp, attrs_dic
5f60: 74 2c 20 61 74 74 72 5f 6b 65 79 5f 73 6f 75 72 t, attr_key_sour
5f70: 63 65 2c 20 26 61 74 74 72 5f 76 61 6c 75 65 29 ce, &attr_value)
5f80: 3b 0a 09 09 09 09 69 66 20 28 61 74 74 72 5f 76 ;.....if (attr_v
5f90: 61 6c 75 65 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a alue != NULL) {.
5fa0: 09 09 09 09 09 61 74 74 72 5f 76 61 6c 75 65 5f .....attr_value_
5fb0: 73 74 72 20 3d 20 54 63 6c 5f 47 65 74 53 74 72 str = Tcl_GetStr
5fc0: 69 6e 67 46 72 6f 6d 4f 62 6a 28 61 74 74 72 5f ingFromObj(attr_
5fd0: 76 61 6c 75 65 2c 20 26 61 74 74 72 5f 76 61 6c value, &attr_val
5fe0: 75 65 5f 69 6e 74 29 3b 20 0a 0a 09 09 09 09 09 ue_int); .......
5ff0: 69 66 20 28 28 61 74 74 72 5f 76 61 6c 75 65 5f if ((attr_value_
6000: 69 6e 74 20 2b 20 31 29 20 3c 3d 20 73 69 7a 65 int + 1) <= size
6010: 6f 66 28 70 61 74 68 69 6e 66 6f 2d 3e 74 79 70 of(pathinfo->typ
6020: 65 69 6e 66 6f 2e 73 79 6d 6c 69 6e 6b 2e 73 6f einfo.symlink.so
6030: 75 72 63 65 29 29 20 7b 0a 09 09 09 09 09 09 70 urce)) {.......p
6040: 61 74 68 69 6e 66 6f 2d 3e 74 79 70 65 69 6e 66 athinfo->typeinf
6050: 6f 2e 73 79 6d 6c 69 6e 6b 2e 73 69 7a 65 20 3d o.symlink.size =
6060: 20 61 74 74 72 5f 76 61 6c 75 65 5f 69 6e 74 3b attr_value_int;
6070: 0a 09 09 09 09 09 09 70 61 74 68 69 6e 66 6f 2d .......pathinfo-
6080: 3e 74 79 70 65 69 6e 66 6f 2e 73 79 6d 6c 69 6e >typeinfo.symlin
6090: 6b 2e 73 6f 75 72 63 65 5b 61 74 74 72 5f 76 61 k.source[attr_va
60a0: 6c 75 65 5f 69 6e 74 5d 20 3d 20 27 5c 30 27 3b lue_int] = '\0';
60b0: 0a 0a 09 09 09 09 09 09 6d 65 6d 63 70 79 28 70 ........memcpy(p
60c0: 61 74 68 69 6e 66 6f 2d 3e 74 79 70 65 69 6e 66 athinfo->typeinf
60d0: 6f 2e 73 79 6d 6c 69 6e 6b 2e 73 6f 75 72 63 65 o.symlink.source
60e0: 2c 20 61 74 74 72 5f 76 61 6c 75 65 5f 73 74 72 , attr_value_str
60f0: 2c 20 61 74 74 72 5f 76 61 6c 75 65 5f 69 6e 74 , attr_value_int
6100: 29 3b 0a 09 09 09 09 09 7d 0a 09 09 09 09 7d 0a );......}.....}.
6110: 09 09 09 09 62 72 65 61 6b 3b 0a 09 09 09 63 61 ....break;....ca
6120: 73 65 20 27 46 27 3a 20 2f 2a 20 70 69 70 65 2f se 'F': /* pipe/
6130: 66 69 66 6f 20 2a 2f 0a 09 09 09 09 70 61 74 68 fifo */.....path
6140: 69 6e 66 6f 2d 3e 74 79 70 65 20 3d 20 41 50 50 info->type = APP
6150: 46 53 5f 50 41 54 48 54 59 50 45 5f 46 49 46 4f FS_PATHTYPE_FIFO
6160: 3b 0a 09 09 09 09 62 72 65 61 6b 3b 0a 09 09 09 ;.....break;....
6170: 63 61 73 65 20 27 53 27 3a 20 2f 2a 20 55 4e 49 case 'S': /* UNI
6180: 58 20 64 6f 6d 61 69 6e 20 73 6f 63 6b 65 74 20 X domain socket
6190: 2a 2f 0a 09 09 09 09 70 61 74 68 69 6e 66 6f 2d */.....pathinfo-
61a0: 3e 74 79 70 65 20 3d 20 41 50 50 46 53 5f 50 41 >type = APPFS_PA
61b0: 54 48 54 59 50 45 5f 53 4f 43 4b 45 54 3b 0a 09 THTYPE_SOCKET;..
61c0: 09 09 09 62 72 65 61 6b 3b 0a 09 09 09 64 65 66 ...break;....def
61d0: 61 75 6c 74 3a 0a 09 09 09 09 72 65 74 76 61 6c ault:.....retval
61e0: 20 3d 20 2d 45 49 4f 3b 0a 09 09 7d 0a 0a 09 09 = -EIO;...}....
61f0: 54 63 6c 5f 44 69 63 74 4f 62 6a 47 65 74 28 69 Tcl_DictObjGet(i
6200: 6e 74 65 72 70 2c 20 61 74 74 72 73 5f 64 69 63 nterp, attrs_dic
6210: 74 2c 20 61 74 74 72 5f 6b 65 79 5f 70 61 63 6b t, attr_key_pack
6220: 61 67 65 64 2c 20 26 61 74 74 72 5f 76 61 6c 75 aged, &attr_valu
6230: 65 29 3b 0a 09 09 69 66 20 28 61 74 74 72 5f 76 e);...if (attr_v
6240: 61 6c 75 65 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a alue != NULL) {.
6250: 09 09 09 70 61 74 68 69 6e 66 6f 2d 3e 70 61 63 ...pathinfo->pac
6260: 6b 61 67 65 64 20 3d 20 31 3b 0a 09 09 7d 0a 0a kaged = 1;...}..
6270: 09 09 54 63 6c 5f 44 69 63 74 4f 62 6a 47 65 74 ..Tcl_DictObjGet
6280: 28 69 6e 74 65 72 70 2c 20 61 74 74 72 73 5f 64 (interp, attrs_d
6290: 69 63 74 2c 20 61 74 74 72 5f 6b 65 79 5f 74 69 ict, attr_key_ti
62a0: 6d 65 2c 20 26 61 74 74 72 5f 76 61 6c 75 65 29 me, &attr_value)
62b0: 3b 0a 09 09 69 66 20 28 61 74 74 72 5f 76 61 6c ;...if (attr_val
62c0: 75 65 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 ue != NULL) {...
62d0: 09 74 63 6c 5f 72 65 74 20 3d 20 54 63 6c 5f 47 .tcl_ret = Tcl_G
62e0: 65 74 57 69 64 65 49 6e 74 46 72 6f 6d 4f 62 6a etWideIntFromObj
62f0: 28 4e 55 4c 4c 2c 20 61 74 74 72 5f 76 61 6c 75 (NULL, attr_valu
6300: 65 2c 20 26 61 74 74 72 5f 76 61 6c 75 65 5f 77 e, &attr_value_w
6310: 69 64 65 29 3b 0a 09 09 09 69 66 20 28 74 63 6c ide);....if (tcl
6320: 5f 72 65 74 20 3d 3d 20 54 43 4c 5f 4f 4b 29 20 _ret == TCL_OK)
6330: 7b 0a 09 09 09 09 70 61 74 68 69 6e 66 6f 2d 3e {.....pathinfo->
6340: 74 69 6d 65 20 3d 20 61 74 74 72 5f 76 61 6c 75 time = attr_valu
6350: 65 5f 77 69 64 65 3b 0a 09 09 09 7d 0a 09 09 7d e_wide;....}...}
6360: 20 65 6c 73 65 20 7b 0a 09 09 09 70 61 74 68 69 else {....pathi
6370: 6e 66 6f 2d 3e 74 69 6d 65 20 3d 20 61 70 70 66 nfo->time = appf
6380: 73 5f 62 6f 6f 74 74 69 6d 65 3b 0a 09 09 7d 0a s_boottime;...}.
6390: 0a 09 09 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 ...Tcl_Release(i
63a0: 6e 74 65 72 70 29 3b 0a 09 29 0a 0a 09 69 66 20 nterp);..)...if
63b0: 28 70 61 74 68 69 6e 66 6f 2d 3e 70 61 63 6b 61 (pathinfo->packa
63c0: 67 65 64 29 20 7b 0a 09 09 70 61 74 68 69 6e 66 ged) {...pathinf
63d0: 6f 2d 3e 69 6e 6f 64 65 20 3d 20 61 70 70 66 73 o->inode = appfs
63e0: 5f 67 65 74 5f 70 61 74 68 5f 69 6e 6f 64 65 28 _get_path_inode(
63f0: 70 61 74 68 2c 20 2d 31 29 3b 0a 09 7d 20 65 6c path, -1);..} el
6400: 73 65 20 7b 0a 09 09 70 61 74 68 69 6e 66 6f 2d se {...pathinfo-
6410: 3e 69 6e 6f 64 65 20 3d 20 61 70 70 66 73 5f 67 >inode = appfs_g
6420: 65 74 5f 70 61 74 68 5f 69 6e 6f 64 65 28 70 61 et_path_inode(pa
6430: 74 68 2c 20 66 73 75 69 64 29 3b 0a 09 7d 0a 0a th, fsuid);..}..
6440: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 43 61 .APPFS_DEBUG("Ca
6450: 63 68 69 6e 67 20 69 6e 6f 64 65 20 66 6f 72 20 ching inode for
6460: 70 61 74 68 3d 25 73 2c 75 69 64 3d 25 6c 6c 69 path=%s,uid=%lli
6470: 20 61 73 20 25 6c 6c 75 20 28 70 61 63 6b 61 67 as %llu (packag
6480: 65 64 20 3d 20 25 69 29 22 2c 20 70 61 74 68 2c ed = %i)", path,
6490: 20 28 6c 6f 6e 67 20 6c 6f 6e 67 29 20 66 73 75 (long long) fsu
64a0: 69 64 2c 20 70 61 74 68 69 6e 66 6f 2d 3e 69 6e id, pathinfo->in
64b0: 6f 64 65 2c 20 70 61 74 68 69 6e 66 6f 2d 3e 70 ode, pathinfo->p
64c0: 61 63 6b 61 67 65 64 29 3b 0a 0a 09 69 66 20 28 ackaged);...if (
64d0: 72 65 74 76 61 6c 20 3d 3d 20 30 29 20 7b 0a 09 retval == 0) {..
64e0: 09 61 70 70 66 73 5f 67 65 74 5f 70 61 74 68 5f .appfs_get_path_
64f0: 69 6e 66 6f 5f 63 61 63 68 65 5f 61 64 64 28 70 info_cache_add(p
6500: 61 74 68 2c 20 66 73 75 69 64 2c 20 70 61 74 68 ath, fsuid, path
6510: 69 6e 66 6f 29 3b 0a 09 7d 20 65 6c 73 65 20 7b info);..} else {
6520: 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 ...APPFS_DEBUG("
6530: 65 72 72 6f 72 3a 20 49 6e 76 61 6c 69 64 20 74 error: Invalid t
6540: 79 70 65 20 66 6f 72 20 5c 22 25 73 5c 22 20 66 ype for \"%s\" f
6550: 72 6f 6d 20 54 63 6c 22 2c 20 70 61 74 68 29 3b rom Tcl", path);
6560: 0a 09 7d 0a 0a 09 72 65 74 75 72 6e 28 72 65 74 ..}...return(ret
6570: 76 61 6c 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 val);.}..static
6580: 63 68 61 72 20 2a 61 70 70 66 73 5f 70 72 65 70 char *appfs_prep
6590: 61 72 65 5f 74 6f 5f 63 72 65 61 74 65 28 63 6f are_to_create(co
65a0: 6e 73 74 20 63 68 61 72 20 2a 70 61 74 68 29 20 nst char *path)
65b0: 7b 0a 09 54 63 6c 5f 49 6e 74 65 72 70 20 2a 69 {..Tcl_Interp *i
65c0: 6e 74 65 72 70 3b 0a 09 63 6f 6e 73 74 20 63 68 nterp;..const ch
65d0: 61 72 20 2a 72 65 61 6c 5f 70 61 74 68 3b 0a 09 ar *real_path;..
65e0: 69 6e 74 20 74 63 6c 5f 72 65 74 3b 0a 0a 09 61 int tcl_ret;...a
65f0: 70 70 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 6e ppfs_get_path_in
6600: 66 6f 5f 63 61 63 68 65 5f 66 6c 75 73 68 28 61 fo_cache_flush(a
6610: 70 70 66 73 5f 67 65 74 5f 66 73 75 69 64 28 29 ppfs_get_fsuid()
6620: 2c 20 2d 31 29 3b 0a 0a 09 69 6e 74 65 72 70 20 , -1);...interp
6630: 3d 20 61 70 70 66 73 5f 54 63 6c 49 6e 74 65 72 = appfs_TclInter
6640: 70 28 29 3b 0a 09 69 66 20 28 69 6e 74 65 72 70 p();..if (interp
6650: 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 72 65 == NULL) {...re
6660: 74 75 72 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a turn(NULL);..}..
6670: 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 .appfs_call_libt
6680: 63 6c 28 54 63 6c 5f 50 72 65 73 65 72 76 65 28 cl(Tcl_Preserve(
6690: 69 6e 74 65 72 70 29 3b 29 0a 0a 09 61 70 70 66 interp);)...appf
66a0: 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 s_call_libtcl(..
66b0: 09 74 63 6c 5f 72 65 74 20 3d 20 61 70 70 66 73 .tcl_ret = appfs
66c0: 5f 54 63 6c 5f 45 76 61 6c 28 69 6e 74 65 72 70 _Tcl_Eval(interp
66d0: 2c 20 32 2c 20 22 3a 3a 61 70 70 66 73 3a 3a 70 , 2, "::appfs::p
66e0: 72 65 70 61 72 65 5f 74 6f 5f 63 72 65 61 74 65 repare_to_create
66f0: 22 2c 20 70 61 74 68 29 3b 0a 09 29 0a 09 69 66 ", path);..)..if
6700: 20 28 74 63 6c 5f 72 65 74 20 21 3d 20 54 43 4c (tcl_ret != TCL
6710: 5f 4f 4b 29 20 7b 0a 09 09 41 50 50 46 53 5f 44 _OK) {...APPFS_D
6720: 45 42 55 47 28 22 3a 3a 61 70 70 66 73 3a 3a 70 EBUG("::appfs::p
6730: 72 65 70 61 72 65 5f 74 6f 5f 63 72 65 61 74 65 repare_to_create
6740: 28 25 73 29 20 66 61 69 6c 65 64 2e 22 2c 20 70 (%s) failed.", p
6750: 61 74 68 29 3b 0a 09 09 61 70 70 66 73 5f 63 61 ath);...appfs_ca
6760: 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 09 41 50 ll_libtcl(....AP
6770: 50 46 53 5f 44 45 42 55 47 28 22 54 63 6c 20 45 PFS_DEBUG("Tcl E
6780: 72 72 6f 72 20 69 73 3a 20 25 73 22 2c 20 54 63 rror is: %s", Tc
6790: 6c 5f 47 65 74 53 74 72 69 6e 67 52 65 73 75 6c l_GetStringResul
67a0: 74 28 69 6e 74 65 72 70 29 29 3b 0a 09 09 29 0a t(interp));...).
67b0: 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 ...appfs_call_li
67c0: 62 74 63 6c 28 54 63 6c 5f 52 65 6c 65 61 73 65 btcl(Tcl_Release
67d0: 28 69 6e 74 65 72 70 29 3b 29 0a 0a 09 09 72 65 (interp);)....re
67e0: 74 75 72 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a turn(NULL);..}..
67f0: 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 .appfs_call_libt
6800: 63 6c 28 0a 09 09 72 65 61 6c 5f 70 61 74 68 20 cl(...real_path
6810: 3d 20 54 63 6c 5f 47 65 74 53 74 72 69 6e 67 52 = Tcl_GetStringR
6820: 65 73 75 6c 74 28 69 6e 74 65 72 70 29 3b 0a 09 esult(interp);..
6830: 29 0a 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c )...appfs_call_l
6840: 69 62 74 63 6c 28 54 63 6c 5f 52 65 6c 65 61 73 ibtcl(Tcl_Releas
6850: 65 28 69 6e 74 65 72 70 29 3b 29 0a 0a 09 69 66 e(interp);)...if
6860: 20 28 72 65 61 6c 5f 70 61 74 68 20 3d 3d 20 4e (real_path == N
6870: 55 4c 4c 29 20 7b 0a 09 09 72 65 74 75 72 6e 28 ULL) {...return(
6880: 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 72 65 74 75 NULL);..}...retu
6890: 72 6e 28 73 74 72 64 75 70 28 72 65 61 6c 5f 70 rn(strdup(real_p
68a0: 61 74 68 29 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 ath));.}..static
68b0: 20 63 68 61 72 20 2a 61 70 70 66 73 5f 6c 6f 63 char *appfs_loc
68c0: 61 6c 70 61 74 68 28 63 6f 6e 73 74 20 63 68 61 alpath(const cha
68d0: 72 20 2a 70 61 74 68 29 20 7b 0a 09 54 63 6c 5f r *path) {..Tcl_
68e0: 49 6e 74 65 72 70 20 2a 69 6e 74 65 72 70 3b 0a Interp *interp;.
68f0: 09 63 6f 6e 73 74 20 63 68 61 72 20 2a 72 65 61 .const char *rea
6900: 6c 5f 70 61 74 68 3b 0a 09 69 6e 74 20 74 63 6c l_path;..int tcl
6910: 5f 72 65 74 3b 0a 0a 09 69 6e 74 65 72 70 20 3d _ret;...interp =
6920: 20 61 70 70 66 73 5f 54 63 6c 49 6e 74 65 72 70 appfs_TclInterp
6930: 28 29 3b 0a 09 69 66 20 28 69 6e 74 65 72 70 20 ();..if (interp
6940: 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 72 65 74 == NULL) {...ret
6950: 75 72 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 urn(NULL);..}...
6960: 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 appfs_call_libtc
6970: 6c 28 54 63 6c 5f 50 72 65 73 65 72 76 65 28 69 l(Tcl_Preserve(i
6980: 6e 74 65 72 70 29 3b 29 0a 0a 09 61 70 70 66 73 nterp);)...appfs
6990: 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 _call_libtcl(...
69a0: 74 63 6c 5f 72 65 74 20 3d 20 61 70 70 66 73 5f tcl_ret = appfs_
69b0: 54 63 6c 5f 45 76 61 6c 28 69 6e 74 65 72 70 2c Tcl_Eval(interp,
69c0: 20 32 2c 20 22 3a 3a 61 70 70 66 73 3a 3a 6c 6f 2, "::appfs::lo
69d0: 63 61 6c 70 61 74 68 22 2c 20 70 61 74 68 29 3b calpath", path);
69e0: 0a 09 29 0a 09 69 66 20 28 74 63 6c 5f 72 65 74 ..)..if (tcl_ret
69f0: 20 21 3d 20 54 43 4c 5f 4f 4b 29 20 7b 0a 09 09 != TCL_OK) {...
6a00: 41 50 50 46 53 5f 44 45 42 55 47 28 22 3a 3a 61 APPFS_DEBUG("::a
6a10: 70 70 66 73 3a 3a 6c 6f 63 61 6c 70 61 74 68 28 ppfs::localpath(
6a20: 25 73 29 20 66 61 69 6c 65 64 2e 22 2c 20 70 61 %s) failed.", pa
6a30: 74 68 29 3b 0a 09 09 61 70 70 66 73 5f 63 61 6c th);...appfs_cal
6a40: 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 09 41 50 50 l_libtcl(....APP
6a50: 46 53 5f 44 45 42 55 47 28 22 54 63 6c 20 45 72 FS_DEBUG("Tcl Er
6a60: 72 6f 72 20 69 73 3a 20 25 73 22 2c 20 54 63 6c ror is: %s", Tcl
6a70: 5f 47 65 74 53 74 72 69 6e 67 52 65 73 75 6c 74 _GetStringResult
6a80: 28 69 6e 74 65 72 70 29 29 3b 0a 09 09 29 0a 0a (interp));...)..
6a90: 09 09 72 65 74 75 72 6e 28 4e 55 4c 4c 29 3b 0a ..return(NULL);.
6aa0: 09 7d 0a 0a 09 61 70 70 66 73 5f 63 61 6c 6c 5f .}...appfs_call_
6ab0: 6c 69 62 74 63 6c 28 0a 09 09 72 65 61 6c 5f 70 libtcl(...real_p
6ac0: 61 74 68 20 3d 20 54 63 6c 5f 47 65 74 53 74 72 ath = Tcl_GetStr
6ad0: 69 6e 67 52 65 73 75 6c 74 28 69 6e 74 65 72 70 ingResult(interp
6ae0: 29 3b 0a 09 29 0a 0a 09 61 70 70 66 73 5f 63 61 );..)...appfs_ca
6af0: 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 52 65 ll_libtcl(Tcl_Re
6b00: 6c 65 61 73 65 28 69 6e 74 65 72 70 29 3b 29 0a lease(interp);).
6b10: 0a 09 69 66 20 28 72 65 61 6c 5f 70 61 74 68 20 ..if (real_path
6b20: 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 72 65 74 == NULL) {...ret
6b30: 75 72 6e 28 4e 55 4c 4c 29 3b 0a 09 7d 0a 0a 09 urn(NULL);..}...
6b40: 72 65 74 75 72 6e 28 73 74 72 64 75 70 28 72 65 return(strdup(re
6b50: 61 6c 5f 70 61 74 68 29 29 3b 0a 7d 0a 0a 23 69 al_path));.}..#i
6b60: 66 20 28 64 65 66 69 6e 65 64 28 44 45 42 55 47 f (defined(DEBUG
6b70: 29 20 26 26 20 64 65 66 69 6e 65 64 28 41 50 50 ) && defined(APP
6b80: 46 53 5f 45 58 49 54 5f 50 41 54 48 29 29 20 7c FS_EXIT_PATH)) |
6b90: 7c 20 64 65 66 69 6e 65 64 28 41 50 50 46 53 5f | defined(APPFS_
6ba0: 45 58 49 54 5f 50 41 54 48 5f 45 4e 41 42 4c 45 EXIT_PATH_ENABLE
6bb0: 5f 4d 41 4a 4f 52 5f 53 45 43 55 52 49 54 59 5f _MAJOR_SECURITY_
6bc0: 48 4f 4c 45 29 0a 73 74 61 74 69 63 20 76 6f 69 HOLE).static voi
6bd0: 64 20 61 70 70 66 73 5f 65 78 69 74 28 76 6f 69 d appfs_exit(voi
6be0: 64 29 20 7b 0a 09 69 6e 74 20 67 6c 6f 62 61 6c d) {..int global
6bf0: 5f 69 6e 74 65 72 70 5f 72 65 73 65 74 5f 6b 65 _interp_reset_ke
6c00: 79 3b 0a 0a 09 67 6c 6f 62 61 6c 5f 69 6e 74 65 y;...global_inte
6c10: 72 70 5f 72 65 73 65 74 5f 6b 65 79 20 3d 20 5f rp_reset_key = _
6c20: 5f 73 79 6e 63 5f 66 65 74 63 68 5f 61 6e 64 5f _sync_fetch_and_
6c30: 61 64 64 28 26 69 6e 74 65 72 70 5f 72 65 73 65 add(&interp_rese
6c40: 74 5f 6b 65 79 2c 20 30 29 3b 0a 09 5f 5f 73 79 t_key, 0);..__sy
6c50: 6e 63 5f 66 65 74 63 68 5f 61 6e 64 5f 73 75 62 nc_fetch_and_sub
6c60: 28 26 69 6e 74 65 72 70 5f 72 65 73 65 74 5f 6b (&interp_reset_k
6c70: 65 79 2c 20 67 6c 6f 62 61 6c 5f 69 6e 74 65 72 ey, global_inter
6c80: 70 5f 72 65 73 65 74 5f 6b 65 79 29 3b 0a 0a 09 p_reset_key);...
6c90: 77 68 69 6c 65 20 28 5f 5f 73 79 6e 63 5f 73 75 while (__sync_su
6ca0: 62 5f 61 6e 64 5f 66 65 74 63 68 28 26 69 6e 74 b_and_fetch(&int
6cb0: 65 72 70 5f 72 65 73 65 74 5f 6b 65 79 2c 20 31 erp_reset_key, 1
6cc0: 29 20 3e 3d 20 30 29 20 7b 0a 09 09 2f 2a 20 42 ) >= 0) {.../* B
6cd0: 75 73 79 20 4c 6f 6f 70 20 2a 2f 0a 09 7d 0a 0a usy Loop */..}..
6ce0: 09 67 6c 6f 62 61 6c 5f 69 6e 74 65 72 70 5f 72 .global_interp_r
6cf0: 65 73 65 74 5f 6b 65 79 20 3d 20 5f 5f 73 79 6e eset_key = __syn
6d00: 63 5f 66 65 74 63 68 5f 61 6e 64 5f 61 64 64 28 c_fetch_and_add(
6d10: 26 69 6e 74 65 72 70 5f 72 65 73 65 74 5f 6b 65 &interp_reset_ke
6d20: 79 2c 20 30 29 3b 0a 09 69 66 20 28 67 6c 6f 62 y, 0);..if (glob
6d30: 61 6c 5f 69 6e 74 65 72 70 5f 72 65 73 65 74 5f al_interp_reset_
6d40: 6b 65 79 20 21 3d 20 2d 31 29 20 7b 0a 09 09 41 key != -1) {...A
6d50: 50 50 46 53 5f 44 45 42 55 47 28 22 45 72 72 6f PPFS_DEBUG("Erro
6d60: 72 20 73 65 6e 64 69 6e 67 20 6b 69 6c 6c 20 73 r sending kill s
6d70: 69 67 6e 61 6c 20 74 6f 20 61 6c 6c 20 74 68 72 ignal to all thr
6d80: 65 61 64 73 2c 20 61 62 6f 72 74 69 6e 67 20 61 eads, aborting a
6d90: 6e 79 77 61 79 2e 22 29 3b 0a 09 7d 0a 0a 09 61 nyway.");..}...a
6da0: 70 70 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 6e ppfs_get_path_in
6db0: 66 6f 5f 63 61 63 68 65 5f 66 6c 75 73 68 28 2d fo_cache_flush(-
6dc0: 31 2c 20 2d 31 29 3b 0a 0a 09 66 75 73 65 5f 65 1, -1);...fuse_e
6dd0: 78 69 74 28 66 75 73 65 5f 67 65 74 5f 63 6f 6e xit(fuse_get_con
6de0: 74 65 78 74 28 29 2d 3e 66 75 73 65 29 3b 0a 0a text()->fuse);..
6df0: 09 72 65 74 75 72 6e 3b 0a 7d 0a 0a 23 65 6e 64 .return;.}..#end
6e00: 69 66 0a 0a 23 69 66 20 64 65 66 69 6e 65 64 28 if..#if defined(
6e10: 41 50 50 46 53 5f 45 58 45 43 5f 50 41 54 48 5f APPFS_EXEC_PATH_
6e20: 45 4e 41 42 4c 45 5f 4d 41 4a 4f 52 5f 53 45 43 ENABLE_MAJOR_SEC
6e30: 55 52 49 54 59 5f 48 4f 4c 45 29 0a 73 74 61 74 URITY_HOLE).stat
6e40: 69 63 20 76 6f 69 64 20 61 70 70 66 73 5f 72 75 ic void appfs_ru
6e50: 6e 54 63 6c 28 63 6f 6e 73 74 20 63 68 61 72 20 nTcl(const char
6e60: 2a 73 63 72 69 70 74 2c 20 73 69 7a 65 5f 74 20 *script, size_t
6e70: 73 63 72 69 70 74 4c 65 6e 29 20 7b 0a 09 54 63 scriptLen) {..Tc
6e80: 6c 5f 49 6e 74 65 72 70 20 2a 69 6e 74 65 72 70 l_Interp *interp
6e90: 3b 0a 09 54 63 6c 5f 4f 62 6a 20 2a 73 63 72 69 ;..Tcl_Obj *scri
6ea0: 70 74 4f 62 6a 3b 0a 09 69 6e 74 20 74 63 6c 5f ptObj;..int tcl_
6eb0: 72 65 74 3b 0a 0a 09 69 6e 74 65 72 70 20 3d 20 ret;...interp =
6ec0: 61 70 70 66 73 5f 54 63 6c 49 6e 74 65 72 70 28 appfs_TclInterp(
6ed0: 29 3b 0a 09 69 66 20 28 69 6e 74 65 72 70 20 3d );..if (interp =
6ee0: 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 41 50 50 46 = NULL) {...APPF
6ef0: 53 5f 44 45 42 55 47 28 22 45 72 72 6f 72 20 63 S_DEBUG("Error c
6f00: 72 65 61 74 69 6e 67 20 61 6e 20 69 6e 74 65 72 reating an inter
6f10: 70 72 65 74 65 72 2e 22 29 3b 0a 0a 09 09 72 65 preter.");....re
6f20: 74 75 72 6e 3b 0a 09 7d 0a 0a 09 61 70 70 66 73 turn;..}...appfs
6f30: 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 73 63 72 _call_libtcl(scr
6f40: 69 70 74 4f 62 6a 20 3d 20 54 63 6c 5f 4e 65 77 iptObj = Tcl_New
6f50: 53 74 72 69 6e 67 4f 62 6a 28 73 63 72 69 70 74 StringObj(script
6f60: 2c 20 73 63 72 69 70 74 4c 65 6e 29 3b 29 0a 0a , scriptLen);)..
6f70: 09 69 66 20 28 73 63 72 69 70 74 4f 62 6a 20 3d .if (scriptObj =
6f80: 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 41 50 50 46 = NULL) {...APPF
6f90: 53 5f 44 45 42 55 47 28 22 45 72 72 6f 72 20 63 S_DEBUG("Error c
6fa0: 72 65 61 74 69 6e 67 20 61 20 73 63 72 69 70 74 reating a script
6fb0: 20 6f 62 6a 65 63 74 2e 22 29 3b 0a 0a 09 09 72 object.");....r
6fc0: 65 74 75 72 6e 3b 0a 09 7d 0a 0a 09 61 70 70 66 eturn;..}...appf
6fd0: 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 74 63 s_call_libtcl(tc
6fe0: 6c 5f 72 65 74 20 3d 20 54 63 6c 5f 45 76 61 6c l_ret = Tcl_Eval
6ff0: 4f 62 6a 45 78 28 69 6e 74 65 72 70 2c 20 73 63 ObjEx(interp, sc
7000: 72 69 70 74 4f 62 6a 2c 20 54 43 4c 5f 45 56 41 riptObj, TCL_EVA
7010: 4c 5f 44 49 52 45 43 54 29 3b 29 0a 09 69 66 20 L_DIRECT);)..if
7020: 28 74 63 6c 5f 72 65 74 20 21 3d 20 54 43 4c 5f (tcl_ret != TCL_
7030: 4f 4b 29 20 7b 0a 09 09 61 70 70 66 73 5f 63 61 OK) {...appfs_ca
7040: 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 09 41 50 ll_libtcl(....AP
7050: 50 46 53 5f 44 45 42 55 47 28 22 53 63 72 69 70 PFS_DEBUG("Scrip
7060: 74 20 72 65 74 75 72 6e 65 64 20 65 72 72 6f 72 t returned error
7070: 20 25 69 3a 20 25 73 22 2c 20 74 63 6c 5f 72 65 %i: %s", tcl_re
7080: 74 2c 20 54 63 6c 5f 47 65 74 53 74 72 69 6e 67 t, Tcl_GetString
7090: 52 65 73 75 6c 74 28 69 6e 74 65 72 70 29 29 3b Result(interp));
70a0: 0a 09 09 29 0a 09 7d 0a 0a 09 72 65 74 75 72 6e ...)..}...return
70b0: 3b 0a 7d 0a 23 65 6e 64 69 66 0a 0a 73 74 61 74 ;.}.#endif..stat
70c0: 69 63 20 69 6e 74 20 61 70 70 66 73 5f 66 75 73 ic int appfs_fus
70d0: 65 5f 72 65 61 64 6c 69 6e 6b 28 63 6f 6e 73 74 e_readlink(const
70e0: 20 63 68 61 72 20 2a 70 61 74 68 2c 20 63 68 61 char *path, cha
70f0: 72 20 2a 62 75 66 2c 20 73 69 7a 65 5f 74 20 73 r *buf, size_t s
7100: 69 7a 65 29 20 7b 0a 09 73 74 72 75 63 74 20 61 ize) {..struct a
7110: 70 70 66 73 5f 70 61 74 68 69 6e 66 6f 20 70 61 ppfs_pathinfo pa
7120: 74 68 69 6e 66 6f 3b 0a 09 69 6e 74 20 72 65 74 thinfo;..int ret
7130: 76 61 6c 20 3d 20 30 3b 0a 0a 09 41 50 50 46 53 val = 0;...APPFS
7140: 5f 44 45 42 55 47 28 22 45 6e 74 65 72 20 28 70 _DEBUG("Enter (p
7150: 61 74 68 20 3d 20 25 73 2c 20 2e 2e 2e 29 22 2c ath = %s, ...)",
7160: 20 70 61 74 68 29 3b 0a 0a 09 70 61 74 68 69 6e path);...pathin
7170: 66 6f 2e 74 79 70 65 20 3d 20 41 50 50 46 53 5f fo.type = APPFS_
7180: 50 41 54 48 54 59 50 45 5f 49 4e 56 41 4c 49 44 PATHTYPE_INVALID
7190: 3b 0a 0a 09 72 65 74 76 61 6c 20 3d 20 61 70 70 ;...retval = app
71a0: 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 6e 66 6f fs_get_path_info
71b0: 28 70 61 74 68 2c 20 26 70 61 74 68 69 6e 66 6f (path, &pathinfo
71c0: 29 3b 0a 09 69 66 20 28 72 65 74 76 61 6c 20 21 );..if (retval !
71d0: 3d 20 30 29 20 7b 0a 09 09 72 65 74 75 72 6e 28 = 0) {...return(
71e0: 72 65 74 76 61 6c 29 3b 0a 09 7d 0a 0a 09 69 66 retval);..}...if
71f0: 20 28 70 61 74 68 69 6e 66 6f 2e 74 79 70 65 20 (pathinfo.type
7200: 21 3d 20 41 50 50 46 53 5f 50 41 54 48 54 59 50 != APPFS_PATHTYP
7210: 45 5f 53 59 4d 4c 49 4e 4b 29 20 7b 0a 09 09 72 E_SYMLINK) {...r
7220: 65 74 75 72 6e 28 2d 45 49 4e 56 41 4c 29 3b 0a eturn(-EINVAL);.
7230: 09 7d 0a 0a 09 69 66 20 28 28 73 74 72 6c 65 6e .}...if ((strlen
7240: 28 70 61 74 68 69 6e 66 6f 2e 74 79 70 65 69 6e (pathinfo.typein
7250: 66 6f 2e 73 79 6d 6c 69 6e 6b 2e 73 6f 75 72 63 fo.symlink.sourc
7260: 65 29 20 2b 20 31 29 20 3e 20 73 69 7a 65 29 20 e) + 1) > size)
7270: 7b 0a 09 09 72 65 74 75 72 6e 28 2d 45 4e 41 4d {...return(-ENAM
7280: 45 54 4f 4f 4c 4f 4e 47 29 3b 0a 09 7d 0a 0a 09 ETOOLONG);..}...
7290: 6d 65 6d 63 70 79 28 62 75 66 2c 20 70 61 74 68 memcpy(buf, path
72a0: 69 6e 66 6f 2e 74 79 70 65 69 6e 66 6f 2e 73 79 info.typeinfo.sy
72b0: 6d 6c 69 6e 6b 2e 73 6f 75 72 63 65 2c 20 73 74 mlink.source, st
72c0: 72 6c 65 6e 28 70 61 74 68 69 6e 66 6f 2e 74 79 rlen(pathinfo.ty
72d0: 70 65 69 6e 66 6f 2e 73 79 6d 6c 69 6e 6b 2e 73 peinfo.symlink.s
72e0: 6f 75 72 63 65 29 20 2b 20 31 29 3b 0a 0a 09 72 ource) + 1);...r
72f0: 65 74 75 72 6e 28 30 29 3b 0a 7d 0a 0a 73 74 61 eturn(0);.}..sta
7300: 74 69 63 20 69 6e 74 20 61 70 70 66 73 5f 66 75 tic int appfs_fu
7310: 73 65 5f 67 65 74 61 74 74 72 28 63 6f 6e 73 74 se_getattr(const
7320: 20 63 68 61 72 20 2a 70 61 74 68 2c 20 73 74 72 char *path, str
7330: 75 63 74 20 73 74 61 74 20 2a 73 74 62 75 66 29 uct stat *stbuf)
7340: 20 7b 0a 09 73 74 72 75 63 74 20 61 70 70 66 73 {..struct appfs
7350: 5f 70 61 74 68 69 6e 66 6f 20 70 61 74 68 69 6e _pathinfo pathin
7360: 66 6f 3b 0a 09 69 6e 74 20 63 68 61 6e 67 65 4f fo;..int changeO
7370: 77 6e 65 72 54 6f 55 73 65 72 49 66 50 61 63 6b wnerToUserIfPack
7380: 61 67 65 64 3b 0a 09 69 6e 74 20 72 65 74 76 61 aged;..int retva
7390: 6c 3b 0a 0a 09 72 65 74 76 61 6c 20 3d 20 30 3b l;...retval = 0;
73a0: 0a 0a 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 ...APPFS_DEBUG("
73b0: 45 6e 74 65 72 20 28 70 61 74 68 20 3d 20 25 73 Enter (path = %s
73c0: 2c 20 2e 2e 2e 29 22 2c 20 70 61 74 68 29 3b 0a , ...)", path);.
73d0: 0a 23 69 66 20 28 64 65 66 69 6e 65 64 28 44 45 .#if (defined(DE
73e0: 42 55 47 29 20 26 26 20 64 65 66 69 6e 65 64 28 BUG) && defined(
73f0: 41 50 50 46 53 5f 45 58 49 54 5f 50 41 54 48 29 APPFS_EXIT_PATH)
7400: 29 20 7c 7c 20 64 65 66 69 6e 65 64 28 41 50 50 ) || defined(APP
7410: 46 53 5f 45 58 49 54 5f 50 41 54 48 5f 45 4e 41 FS_EXIT_PATH_ENA
7420: 42 4c 45 5f 4d 41 4a 4f 52 5f 53 45 43 55 52 49 BLE_MAJOR_SECURI
7430: 54 59 5f 48 4f 4c 45 29 0a 09 2f 2a 0a 09 20 2a TY_HOLE)../*.. *
7440: 20 54 68 69 73 20 69 73 20 61 20 6d 61 6a 6f 72 This is a major
7450: 20 73 65 63 75 72 69 74 79 20 69 73 73 75 65 20 security issue
7460: 73 6f 20 77 65 20 63 61 6e 6e 6f 74 20 6c 65 74 so we cannot let
7470: 20 69 74 20 62 65 20 63 6f 6d 70 69 6c 65 64 20 it be compiled
7480: 69 6e 74 6f 0a 09 20 2a 20 61 6e 79 20 72 65 6c into.. * any rel
7490: 65 61 73 65 0a 09 20 2a 2f 0a 09 69 66 20 28 73 ease.. */..if (s
74a0: 74 72 63 6d 70 28 70 61 74 68 2c 20 22 2f 65 78 trcmp(path, "/ex
74b0: 69 74 22 29 20 3d 3d 20 30 29 20 7b 0a 09 09 61 it") == 0) {...a
74c0: 70 70 66 73 5f 65 78 69 74 28 29 3b 0a 09 7d 0a ppfs_exit();..}.
74d0: 23 65 6e 64 69 66 0a 23 69 66 20 64 65 66 69 6e #endif.#if defin
74e0: 65 64 28 41 50 50 46 53 5f 45 58 45 43 5f 50 41 ed(APPFS_EXEC_PA
74f0: 54 48 5f 45 4e 41 42 4c 45 5f 4d 41 4a 4f 52 5f TH_ENABLE_MAJOR_
7500: 53 45 43 55 52 49 54 59 5f 48 4f 4c 45 29 0a 09 SECURITY_HOLE)..
7510: 69 66 20 28 73 74 72 63 6d 70 28 70 61 74 68 2c if (strcmp(path,
7520: 20 22 2f 65 78 65 63 22 29 20 3d 3d 20 30 29 20 "/exec") == 0)
7530: 7b 0a 09 09 6d 65 6d 73 65 74 28 73 74 62 75 66 {...memset(stbuf
7540: 2c 20 30 2c 20 73 69 7a 65 6f 66 28 73 74 72 75 , 0, sizeof(stru
7550: 63 74 20 73 74 61 74 29 29 3b 0a 0a 09 09 73 74 ct stat));....st
7560: 62 75 66 2d 3e 73 74 5f 6d 74 69 6d 65 20 3d 20 buf->st_mtime =
7570: 30 3b 0a 09 09 73 74 62 75 66 2d 3e 73 74 5f 63 0;...stbuf->st_c
7580: 74 69 6d 65 20 3d 20 30 3b 0a 09 09 73 74 62 75 time = 0;...stbu
7590: 66 2d 3e 73 74 5f 61 74 69 6d 65 20 3d 20 30 3b f->st_atime = 0;
75a0: 0a 09 09 73 74 62 75 66 2d 3e 73 74 5f 69 6e 6f ...stbuf->st_ino
75b0: 20 20 20 3d 20 33 3b 0a 09 09 73 74 62 75 66 2d = 3;...stbuf-
75c0: 3e 73 74 5f 6d 6f 64 65 20 20 3d 20 30 3b 0a 09 >st_mode = 0;..
75d0: 09 73 74 62 75 66 2d 3e 73 74 5f 6d 6f 64 65 20 .stbuf->st_mode
75e0: 20 3d 20 53 5f 49 46 52 45 47 20 7c 20 30 36 30 = S_IFREG | 060
75f0: 30 3b 0a 09 09 73 74 62 75 66 2d 3e 73 74 5f 6e 0;...stbuf->st_n
7600: 6c 69 6e 6b 20 3d 20 31 3b 0a 09 09 73 74 62 75 link = 1;...stbu
7610: 66 2d 3e 73 74 5f 73 69 7a 65 20 20 3d 20 30 3b f->st_size = 0;
7620: 0a 0a 09 09 72 65 74 75 72 6e 28 72 65 74 76 61 ....return(retva
7630: 6c 29 3b 0a 09 7d 0a 23 65 6e 64 69 66 0a 0a 09 l);..}.#endif...
7640: 70 61 74 68 69 6e 66 6f 2e 74 79 70 65 20 3d 20 pathinfo.type =
7650: 41 50 50 46 53 5f 50 41 54 48 54 59 50 45 5f 49 APPFS_PATHTYPE_I
7660: 4e 56 41 4c 49 44 3b 0a 0a 09 72 65 74 76 61 6c NVALID;...retval
7670: 20 3d 20 61 70 70 66 73 5f 67 65 74 5f 70 61 74 = appfs_get_pat
7680: 68 5f 69 6e 66 6f 28 70 61 74 68 2c 20 26 70 61 h_info(path, &pa
7690: 74 68 69 6e 66 6f 29 3b 0a 09 69 66 20 28 72 65 thinfo);..if (re
76a0: 74 76 61 6c 20 21 3d 20 30 29 20 7b 0a 09 09 69 tval != 0) {...i
76b0: 66 20 28 72 65 74 76 61 6c 20 3d 3d 20 2d 45 4e f (retval == -EN
76c0: 4f 45 4e 54 29 20 7b 0a 09 09 09 41 50 50 46 53 OENT) {....APPFS
76d0: 5f 44 45 42 55 47 28 22 67 65 74 5f 70 61 74 68 _DEBUG("get_path
76e0: 5f 69 6e 66 6f 20 72 65 74 75 72 6e 65 64 20 45 _info returned E
76f0: 4e 4f 45 4e 54 2c 20 72 65 74 75 72 6e 69 6e 67 NOENT, returning
7700: 20 69 74 20 61 73 20 77 65 6c 6c 2e 22 29 3b 0a it as well.");.
7710: 09 09 7d 20 65 6c 73 65 20 7b 0a 09 09 09 41 50 ..} else {....AP
7720: 50 46 53 5f 44 45 42 55 47 28 22 65 72 72 6f 72 PFS_DEBUG("error
7730: 3a 20 67 65 74 5f 70 61 74 68 5f 69 6e 66 6f 20 : get_path_info
7740: 66 61 69 6c 65 64 22 29 3b 0a 09 09 7d 0a 0a 09 failed");...}...
7750: 09 72 65 74 75 72 6e 28 72 65 74 76 61 6c 29 3b .return(retval);
7760: 0a 09 7d 0a 0a 09 6d 65 6d 73 65 74 28 73 74 62 ..}...memset(stb
7770: 75 66 2c 20 30 2c 20 73 69 7a 65 6f 66 28 73 74 uf, 0, sizeof(st
7780: 72 75 63 74 20 73 74 61 74 29 29 3b 0a 0a 09 73 ruct stat));...s
7790: 74 62 75 66 2d 3e 73 74 5f 6d 74 69 6d 65 20 3d tbuf->st_mtime =
77a0: 20 70 61 74 68 69 6e 66 6f 2e 74 69 6d 65 3b 0a pathinfo.time;.
77b0: 09 73 74 62 75 66 2d 3e 73 74 5f 63 74 69 6d 65 .stbuf->st_ctime
77c0: 20 3d 20 70 61 74 68 69 6e 66 6f 2e 74 69 6d 65 = pathinfo.time
77d0: 3b 0a 09 73 74 62 75 66 2d 3e 73 74 5f 61 74 69 ;..stbuf->st_ati
77e0: 6d 65 20 3d 20 70 61 74 68 69 6e 66 6f 2e 74 69 me = pathinfo.ti
77f0: 6d 65 3b 0a 09 73 74 62 75 66 2d 3e 73 74 5f 69 me;..stbuf->st_i
7800: 6e 6f 20 20 20 3d 20 70 61 74 68 69 6e 66 6f 2e no = pathinfo.
7810: 69 6e 6f 64 65 3b 0a 09 73 74 62 75 66 2d 3e 73 inode;..stbuf->s
7820: 74 5f 6d 6f 64 65 20 20 3d 20 30 3b 0a 0a 09 63 t_mode = 0;...c
7830: 68 61 6e 67 65 4f 77 6e 65 72 54 6f 55 73 65 72 hangeOwnerToUser
7840: 49 66 50 61 63 6b 61 67 65 64 20 3d 20 31 3b 0a IfPackaged = 1;.
7850: 0a 09 73 77 69 74 63 68 20 28 70 61 74 68 69 6e ..switch (pathin
7860: 66 6f 2e 74 79 70 65 29 20 7b 0a 09 09 63 61 73 fo.type) {...cas
7870: 65 20 41 50 50 46 53 5f 50 41 54 48 54 59 50 45 e APPFS_PATHTYPE
7880: 5f 44 49 52 45 43 54 4f 52 59 3a 0a 09 09 09 73 _DIRECTORY:....s
7890: 74 62 75 66 2d 3e 73 74 5f 6d 6f 64 65 20 3d 20 tbuf->st_mode =
78a0: 53 5f 49 46 44 49 52 20 7c 20 30 35 35 35 3b 0a S_IFDIR | 0555;.
78b0: 09 09 09 73 74 62 75 66 2d 3e 73 74 5f 6e 6c 69 ...stbuf->st_nli
78c0: 6e 6b 20 3d 20 32 20 2b 20 70 61 74 68 69 6e 66 nk = 2 + pathinf
78d0: 6f 2e 74 79 70 65 69 6e 66 6f 2e 64 69 72 2e 63 o.typeinfo.dir.c
78e0: 68 69 6c 64 63 6f 75 6e 74 3b 0a 09 09 09 62 72 hildcount;....br
78f0: 65 61 6b 3b 0a 09 09 63 61 73 65 20 41 50 50 46 eak;...case APPF
7900: 53 5f 50 41 54 48 54 59 50 45 5f 46 49 4c 45 3a S_PATHTYPE_FILE:
7910: 0a 09 09 09 73 74 62 75 66 2d 3e 73 74 5f 6d 6f ....stbuf->st_mo
7920: 64 65 20 3d 20 53 5f 49 46 52 45 47 20 7c 20 30 de = S_IFREG | 0
7930: 34 34 34 3b 0a 0a 09 09 09 69 66 20 28 70 61 74 444;.....if (pat
7940: 68 69 6e 66 6f 2e 74 79 70 65 69 6e 66 6f 2e 66 hinfo.typeinfo.f
7950: 69 6c 65 2e 65 78 65 63 75 74 61 62 6c 65 29 20 ile.executable)
7960: 7b 0a 09 09 09 09 73 74 62 75 66 2d 3e 73 74 5f {.....stbuf->st_
7970: 6d 6f 64 65 20 7c 3d 20 30 31 31 31 3b 0a 09 09 mode |= 0111;...
7980: 09 7d 0a 0a 09 09 09 69 66 20 28 70 61 74 68 69 .}.....if (pathi
7990: 6e 66 6f 2e 70 61 63 6b 61 67 65 64 29 20 7b 0a nfo.packaged) {.
79a0: 09 09 09 09 69 66 20 28 70 61 74 68 69 6e 66 6f ....if (pathinfo
79b0: 2e 74 79 70 65 69 6e 66 6f 2e 66 69 6c 65 2e 73 .typeinfo.file.s
79c0: 75 69 64 52 6f 6f 74 29 20 7b 0a 09 09 09 09 09 uidRoot) {......
79d0: 63 68 61 6e 67 65 4f 77 6e 65 72 54 6f 55 73 65 changeOwnerToUse
79e0: 72 49 66 50 61 63 6b 61 67 65 64 20 3d 20 30 3b rIfPackaged = 0;
79f0: 0a 0a 09 09 09 09 09 73 74 62 75 66 2d 3e 73 74 .......stbuf->st
7a00: 5f 6d 6f 64 65 20 7c 3d 20 30 34 30 30 30 3b 0a _mode |= 04000;.
7a10: 09 09 09 09 7d 0a 09 09 09 7d 0a 0a 09 09 09 69 ....}....}.....i
7a20: 66 20 28 70 61 74 68 69 6e 66 6f 2e 74 79 70 65 f (pathinfo.type
7a30: 69 6e 66 6f 2e 66 69 6c 65 2e 77 6f 72 6c 64 61 info.file.worlda
7a40: 63 63 65 73 73 69 62 6c 65 29 20 7b 0a 09 09 09 ccessible) {....
7a50: 09 73 74 62 75 66 2d 3e 73 74 5f 6d 6f 64 65 20 .stbuf->st_mode
7a60: 26 3d 20 7e 30 37 37 3b 0a 09 09 09 7d 0a 0a 09 &= ~077;....}...
7a70: 09 09 73 74 62 75 66 2d 3e 73 74 5f 6e 6c 69 6e ..stbuf->st_nlin
7a80: 6b 20 3d 20 31 3b 0a 09 09 09 73 74 62 75 66 2d k = 1;....stbuf-
7a90: 3e 73 74 5f 73 69 7a 65 20 3d 20 70 61 74 68 69 >st_size = pathi
7aa0: 6e 66 6f 2e 74 79 70 65 69 6e 66 6f 2e 66 69 6c nfo.typeinfo.fil
7ab0: 65 2e 73 69 7a 65 3b 0a 0a 09 09 09 62 72 65 61 e.size;.....brea
7ac0: 6b 3b 0a 09 09 63 61 73 65 20 41 50 50 46 53 5f k;...case APPFS_
7ad0: 50 41 54 48 54 59 50 45 5f 53 59 4d 4c 49 4e 4b PATHTYPE_SYMLINK
7ae0: 3a 0a 09 09 09 73 74 62 75 66 2d 3e 73 74 5f 6d :....stbuf->st_m
7af0: 6f 64 65 20 3d 20 53 5f 49 46 4c 4e 4b 20 7c 20 ode = S_IFLNK |
7b00: 30 35 35 35 3b 0a 09 09 09 73 74 62 75 66 2d 3e 0555;....stbuf->
7b10: 73 74 5f 6e 6c 69 6e 6b 20 3d 20 31 3b 0a 09 09 st_nlink = 1;...
7b20: 09 73 74 62 75 66 2d 3e 73 74 5f 73 69 7a 65 20 .stbuf->st_size
7b30: 3d 20 70 61 74 68 69 6e 66 6f 2e 74 79 70 65 69 = pathinfo.typei
7b40: 6e 66 6f 2e 73 79 6d 6c 69 6e 6b 2e 73 69 7a 65 nfo.symlink.size
7b50: 3b 0a 09 09 09 62 72 65 61 6b 3b 0a 09 09 63 61 ;....break;...ca
7b60: 73 65 20 41 50 50 46 53 5f 50 41 54 48 54 59 50 se APPFS_PATHTYP
7b70: 45 5f 53 4f 43 4b 45 54 3a 0a 09 09 09 73 74 62 E_SOCKET:....stb
7b80: 75 66 2d 3e 73 74 5f 6d 6f 64 65 20 3d 20 53 5f uf->st_mode = S_
7b90: 49 46 53 4f 43 4b 20 7c 20 30 35 35 35 3b 0a 09 IFSOCK | 0555;..
7ba0: 09 09 73 74 62 75 66 2d 3e 73 74 5f 6e 6c 69 6e ..stbuf->st_nlin
7bb0: 6b 20 3d 20 31 3b 0a 09 09 09 73 74 62 75 66 2d k = 1;....stbuf-
7bc0: 3e 73 74 5f 73 69 7a 65 20 3d 20 30 3b 0a 09 09 >st_size = 0;...
7bd0: 09 62 72 65 61 6b 3b 0a 09 09 63 61 73 65 20 41 .break;...case A
7be0: 50 50 46 53 5f 50 41 54 48 54 59 50 45 5f 46 49 PPFS_PATHTYPE_FI
7bf0: 46 4f 3a 0a 09 09 09 73 74 62 75 66 2d 3e 73 74 FO:....stbuf->st
7c00: 5f 6d 6f 64 65 20 3d 20 53 5f 49 46 49 46 4f 20 _mode = S_IFIFO
7c10: 7c 20 30 35 35 35 3b 0a 09 09 09 73 74 62 75 66 | 0555;....stbuf
7c20: 2d 3e 73 74 5f 6e 6c 69 6e 6b 20 3d 20 31 3b 0a ->st_nlink = 1;.
7c30: 09 09 09 73 74 62 75 66 2d 3e 73 74 5f 73 69 7a ...stbuf->st_siz
7c40: 65 20 3d 20 30 3b 0a 09 09 09 62 72 65 61 6b 3b e = 0;....break;
7c50: 0a 09 09 63 61 73 65 20 41 50 50 46 53 5f 50 41 ...case APPFS_PA
7c60: 54 48 54 59 50 45 5f 44 4f 45 53 5f 4e 4f 54 5f THTYPE_DOES_NOT_
7c70: 45 58 49 53 54 3a 0a 09 09 09 72 65 74 76 61 6c EXIST:....retval
7c80: 20 3d 20 2d 45 4e 4f 45 4e 54 3b 0a 0a 09 09 09 = -ENOENT;.....
7c90: 62 72 65 61 6b 3b 0a 09 09 63 61 73 65 20 41 50 break;...case AP
7ca0: 50 46 53 5f 50 41 54 48 54 59 50 45 5f 49 4e 56 PFS_PATHTYPE_INV
7cb0: 41 4c 49 44 3a 0a 09 09 09 72 65 74 76 61 6c 20 ALID:....retval
7cc0: 3d 20 2d 45 49 4f 3b 0a 0a 09 09 09 62 72 65 61 = -EIO;.....brea
7cd0: 6b 3b 0a 09 7d 0a 0a 09 69 66 20 28 28 70 61 74 k;..}...if ((pat
7ce0: 68 69 6e 66 6f 2e 70 61 63 6b 61 67 65 64 20 26 hinfo.packaged &
7cf0: 26 20 63 68 61 6e 67 65 4f 77 6e 65 72 54 6f 55 & changeOwnerToU
7d00: 73 65 72 49 66 50 61 63 6b 61 67 65 64 29 20 7c serIfPackaged) |
7d10: 7c 20 28 21 70 61 74 68 69 6e 66 6f 2e 70 61 63 | (!pathinfo.pac
7d20: 6b 61 67 65 64 29 29 20 7b 0a 09 09 73 74 62 75 kaged)) {...stbu
7d30: 66 2d 3e 73 74 5f 75 69 64 20 20 20 3d 20 61 70 f->st_uid = ap
7d40: 70 66 73 5f 67 65 74 5f 66 73 75 69 64 28 29 3b pfs_get_fsuid();
7d50: 0a 09 09 73 74 62 75 66 2d 3e 73 74 5f 67 69 64 ...stbuf->st_gid
7d60: 20 20 20 3d 20 61 70 70 66 73 5f 67 65 74 5f 66 = appfs_get_f
7d70: 73 67 69 64 28 29 3b 0a 09 09 73 74 62 75 66 2d sgid();...stbuf-
7d80: 3e 73 74 5f 6d 6f 64 65 20 7c 3d 20 30 32 30 30 >st_mode |= 0200
7d90: 3b 0a 09 7d 0a 0a 09 72 65 74 75 72 6e 28 72 65 ;..}...return(re
7da0: 74 76 61 6c 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 tval);.}..static
7db0: 20 69 6e 74 20 61 70 70 66 73 5f 66 75 73 65 5f int appfs_fuse_
7dc0: 72 65 61 64 64 69 72 28 63 6f 6e 73 74 20 63 68 readdir(const ch
7dd0: 61 72 20 2a 70 61 74 68 2c 20 76 6f 69 64 20 2a ar *path, void *
7de0: 62 75 66 2c 20 66 75 73 65 5f 66 69 6c 6c 5f 64 buf, fuse_fill_d
7df0: 69 72 5f 74 20 66 69 6c 6c 65 72 2c 20 6f 66 66 ir_t filler, off
7e00: 5f 74 20 6f 66 66 73 65 74 2c 20 73 74 72 75 63 _t offset, struc
7e10: 74 20 66 75 73 65 5f 66 69 6c 65 5f 69 6e 66 6f t fuse_file_info
7e20: 20 2a 66 69 29 20 7b 0a 09 54 63 6c 5f 49 6e 74 *fi) {..Tcl_Int
7e30: 65 72 70 20 2a 69 6e 74 65 72 70 3b 0a 09 54 63 erp *interp;..Tc
7e40: 6c 5f 4f 62 6a 20 2a 2a 63 68 69 6c 64 72 65 6e l_Obj **children
7e50: 3b 0a 09 69 6e 74 20 63 68 69 6c 64 72 65 6e 5f ;..int children_
7e60: 63 6f 75 6e 74 2c 20 69 64 78 3b 0a 09 69 6e 74 count, idx;..int
7e70: 20 74 63 6c 5f 72 65 74 3b 0a 0a 09 41 50 50 46 tcl_ret;...APPF
7e80: 53 5f 44 45 42 55 47 28 22 45 6e 74 65 72 20 28 S_DEBUG("Enter (
7e90: 70 61 74 68 20 3d 20 25 73 2c 20 2e 2e 2e 29 22 path = %s, ...)"
7ea0: 2c 20 70 61 74 68 29 3b 0a 0a 09 69 6e 74 65 72 , path);...inter
7eb0: 70 20 3d 20 61 70 70 66 73 5f 54 63 6c 49 6e 74 p = appfs_TclInt
7ec0: 65 72 70 28 29 3b 0a 09 69 66 20 28 69 6e 74 65 erp();..if (inte
7ed0: 72 70 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 rp == NULL) {...
7ee0: 41 50 50 46 53 5f 44 45 42 55 47 28 22 65 72 72 APPFS_DEBUG("err
7ef0: 6f 72 3a 20 55 6e 61 62 6c 65 20 74 6f 20 67 65 or: Unable to ge
7f00: 74 20 61 6e 20 69 6e 74 65 72 70 72 65 74 65 72 t an interpreter
7f10: 22 29 3b 0a 0a 09 09 72 65 74 75 72 6e 28 30 29 ");....return(0)
7f20: 3b 0a 09 7d 0a 0a 09 61 70 70 66 73 5f 63 61 6c ;..}...appfs_cal
7f30: 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 50 72 65 l_libtcl(Tcl_Pre
7f40: 73 65 72 76 65 28 69 6e 74 65 72 70 29 3b 29 0a serve(interp);).
7f50: 0a 09 66 69 6c 6c 65 72 28 62 75 66 2c 20 22 2e ..filler(buf, ".
7f60: 22 2c 20 4e 55 4c 4c 2c 20 30 29 3b 0a 09 66 69 ", NULL, 0);..fi
7f70: 6c 6c 65 72 28 62 75 66 2c 20 22 2e 2e 22 2c 20 ller(buf, "..",
7f80: 4e 55 4c 4c 2c 20 30 29 3b 0a 0a 09 74 63 6c 5f NULL, 0);...tcl_
7f90: 72 65 74 20 3d 20 61 70 70 66 73 5f 54 63 6c 5f ret = appfs_Tcl_
7fa0: 45 76 61 6c 28 69 6e 74 65 72 70 2c 20 32 2c 20 Eval(interp, 2,
7fb0: 22 3a 3a 61 70 70 66 73 3a 3a 67 65 74 63 68 69 "::appfs::getchi
7fc0: 6c 64 72 65 6e 22 2c 20 70 61 74 68 29 3b 0a 09 ldren", path);..
7fd0: 69 66 20 28 74 63 6c 5f 72 65 74 20 21 3d 20 54 if (tcl_ret != T
7fe0: 43 4c 5f 4f 4b 29 20 7b 0a 09 09 41 50 50 46 53 CL_OK) {...APPFS
7ff0: 5f 44 45 42 55 47 28 22 3a 3a 61 70 70 66 73 3a _DEBUG("::appfs:
8000: 3a 67 65 74 63 68 69 6c 64 72 65 6e 28 25 73 29 :getchildren(%s)
8010: 20 66 61 69 6c 65 64 2e 22 2c 20 70 61 74 68 29 failed.", path)
8020: 3b 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c ;...appfs_call_l
8030: 69 62 74 63 6c 28 0a 09 09 09 41 50 50 46 53 5f ibtcl(....APPFS_
8040: 44 45 42 55 47 28 22 54 63 6c 20 45 72 72 6f 72 DEBUG("Tcl Error
8050: 20 69 73 3a 20 25 73 22 2c 20 54 63 6c 5f 47 65 is: %s", Tcl_Ge
8060: 74 53 74 72 69 6e 67 52 65 73 75 6c 74 28 69 6e tStringResult(in
8070: 74 65 72 70 29 29 3b 0a 09 09 29 0a 0a 09 09 61 terp));...)....a
8080: 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c ppfs_call_libtcl
8090: 28 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e 74 (Tcl_Release(int
80a0: 65 72 70 29 3b 29 0a 0a 09 09 72 65 74 75 72 6e erp);)....return
80b0: 28 30 29 3b 0a 09 7d 0a 0a 09 61 70 70 66 73 5f (0);..}...appfs_
80c0: 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 74 call_libtcl(...t
80d0: 63 6c 5f 72 65 74 20 3d 20 54 63 6c 5f 4c 69 73 cl_ret = Tcl_Lis
80e0: 74 4f 62 6a 47 65 74 45 6c 65 6d 65 6e 74 73 28 tObjGetElements(
80f0: 69 6e 74 65 72 70 2c 20 54 63 6c 5f 47 65 74 4f interp, Tcl_GetO
8100: 62 6a 52 65 73 75 6c 74 28 69 6e 74 65 72 70 29 bjResult(interp)
8110: 2c 20 26 63 68 69 6c 64 72 65 6e 5f 63 6f 75 6e , &children_coun
8120: 74 2c 20 26 63 68 69 6c 64 72 65 6e 29 3b 0a 09 t, &children);..
8130: 29 0a 09 69 66 20 28 74 63 6c 5f 72 65 74 20 21 )..if (tcl_ret !
8140: 3d 20 54 43 4c 5f 4f 4b 29 20 7b 0a 09 09 41 50 = TCL_OK) {...AP
8150: 50 46 53 5f 44 45 42 55 47 28 22 50 61 72 73 69 PFS_DEBUG("Parsi
8160: 6e 67 20 6c 69 73 74 20 6f 66 20 63 68 69 6c 64 ng list of child
8170: 72 65 6e 20 6f 6e 20 70 61 74 68 20 25 73 20 66 ren on path %s f
8180: 61 69 6c 65 64 2e 22 2c 20 70 61 74 68 29 3b 0a ailed.", path);.
8190: 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 ..appfs_call_lib
81a0: 74 63 6c 28 0a 09 09 09 41 50 50 46 53 5f 44 45 tcl(....APPFS_DE
81b0: 42 55 47 28 22 54 63 6c 20 45 72 72 6f 72 20 69 BUG("Tcl Error i
81c0: 73 3a 20 25 73 22 2c 20 54 63 6c 5f 47 65 74 53 s: %s", Tcl_GetS
81d0: 74 72 69 6e 67 52 65 73 75 6c 74 28 69 6e 74 65 tringResult(inte
81e0: 72 70 29 29 3b 0a 09 09 29 0a 0a 09 09 61 70 70 rp));...)....app
81f0: 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 54 fs_call_libtcl(T
8200: 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e 74 65 72 cl_Release(inter
8210: 70 29 3b 29 0a 0a 09 09 72 65 74 75 72 6e 28 30 p);)....return(0
8220: 29 3b 0a 09 7d 0a 0a 09 66 6f 72 20 28 69 64 78 );..}...for (idx
8230: 20 3d 20 30 3b 20 69 64 78 20 3c 20 63 68 69 6c = 0; idx < chil
8240: 64 72 65 6e 5f 63 6f 75 6e 74 3b 20 69 64 78 2b dren_count; idx+
8250: 2b 29 20 7b 0a 09 09 61 70 70 66 73 5f 63 61 6c +) {...appfs_cal
8260: 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 09 66 69 6c l_libtcl(....fil
8270: 6c 65 72 28 62 75 66 2c 20 54 63 6c 5f 47 65 74 ler(buf, Tcl_Get
8280: 53 74 72 69 6e 67 28 63 68 69 6c 64 72 65 6e 5b String(children[
8290: 69 64 78 5d 29 2c 20 4e 55 4c 4c 2c 20 30 29 3b idx]), NULL, 0);
82a0: 0a 09 09 29 0a 09 7d 0a 0a 09 61 70 70 66 73 5f ...)..}...appfs_
82b0: 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 54 63 6c 5f call_libtcl(Tcl_
82c0: 52 65 6c 65 61 73 65 28 69 6e 74 65 72 70 29 3b Release(interp);
82d0: 29 0a 0a 09 72 65 74 75 72 6e 28 30 29 3b 0a 7d )...return(0);.}
82e0: 0a 0a 73 74 61 74 69 63 20 69 6e 74 20 61 70 70 ..static int app
82f0: 66 73 5f 66 75 73 65 5f 6f 70 65 6e 28 63 6f 6e fs_fuse_open(con
8300: 73 74 20 63 68 61 72 20 2a 70 61 74 68 2c 20 73 st char *path, s
8310: 74 72 75 63 74 20 66 75 73 65 5f 66 69 6c 65 5f truct fuse_file_
8320: 69 6e 66 6f 20 2a 66 69 29 20 7b 0a 09 54 63 6c info *fi) {..Tcl
8330: 5f 49 6e 74 65 72 70 20 2a 69 6e 74 65 72 70 3b _Interp *interp;
8340: 0a 09 73 74 72 75 63 74 20 61 70 70 66 73 5f 70 ..struct appfs_p
8350: 61 74 68 69 6e 66 6f 20 70 61 74 68 69 6e 66 6f athinfo pathinfo
8360: 3b 0a 09 63 6f 6e 73 74 20 63 68 61 72 20 2a 72 ;..const char *r
8370: 65 61 6c 5f 70 61 74 68 2c 20 2a 6d 6f 64 65 3b eal_path, *mode;
8380: 0a 09 69 6e 74 20 67 70 69 5f 72 65 74 2c 20 74 ..int gpi_ret, t
8390: 63 6c 5f 72 65 74 3b 0a 09 69 6e 74 20 66 68 3b cl_ret;..int fh;
83a0: 0a 0a 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 ...APPFS_DEBUG("
83b0: 45 6e 74 65 72 20 28 70 61 74 68 20 3d 20 25 73 Enter (path = %s
83c0: 2c 20 2e 2e 2e 29 22 2c 20 70 61 74 68 29 3b 0a , ...)", path);.
83d0: 0a 23 69 66 20 64 65 66 69 6e 65 64 28 41 50 50 .#if defined(APP
83e0: 46 53 5f 45 58 45 43 5f 50 41 54 48 5f 45 4e 41 FS_EXEC_PATH_ENA
83f0: 42 4c 45 5f 4d 41 4a 4f 52 5f 53 45 43 55 52 49 BLE_MAJOR_SECURI
8400: 54 59 5f 48 4f 4c 45 29 0a 09 69 66 20 28 73 74 TY_HOLE)..if (st
8410: 72 63 6d 70 28 70 61 74 68 2c 20 22 2f 65 78 65 rcmp(path, "/exe
8420: 63 22 29 20 3d 3d 20 30 29 20 7b 0a 09 09 66 69 c") == 0) {...fi
8430: 2d 3e 66 68 20 3d 20 30 3b 0a 0a 09 09 72 65 74 ->fh = 0;....ret
8440: 75 72 6e 28 30 29 3b 0a 09 7d 0a 23 65 6e 64 69 urn(0);..}.#endi
8450: 66 0a 0a 09 67 70 69 5f 72 65 74 20 3d 20 61 70 f...gpi_ret = ap
8460: 70 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 6e 66 pfs_get_path_inf
8470: 6f 28 70 61 74 68 2c 20 26 70 61 74 68 69 6e 66 o(path, &pathinf
8480: 6f 29 3b 0a 0a 09 69 66 20 28 28 66 69 2d 3e 66 o);...if ((fi->f
8490: 6c 61 67 73 20 26 20 28 4f 5f 57 52 4f 4e 4c 59 lags & (O_WRONLY
84a0: 7c 4f 5f 43 52 45 41 54 29 29 20 3d 3d 20 28 4f |O_CREAT)) == (O
84b0: 5f 43 52 45 41 54 7c 4f 5f 57 52 4f 4e 4c 59 29 _CREAT|O_WRONLY)
84c0: 29 20 7b 0a 09 09 2f 2a 20 54 68 65 20 66 69 6c ) {.../* The fil
84d0: 65 20 77 69 6c 6c 20 62 65 20 63 72 65 61 74 65 e will be create
84e0: 64 20 69 66 20 69 74 20 64 6f 65 73 20 6e 6f 74 d if it does not
84f0: 20 65 78 69 73 74 20 2a 2f 0a 09 09 69 66 20 28 exist */...if (
8500: 67 70 69 5f 72 65 74 20 21 3d 20 30 20 26 26 20 gpi_ret != 0 &&
8510: 67 70 69 5f 72 65 74 20 21 3d 20 2d 45 4e 4f 45 gpi_ret != -ENOE
8520: 4e 54 29 20 7b 0a 09 09 09 41 50 50 46 53 5f 44 NT) {....APPFS_D
8530: 45 42 55 47 28 22 65 72 72 6f 72 3a 20 67 65 74 EBUG("error: get
8540: 5f 70 61 74 68 5f 69 6e 66 6f 20 66 61 69 6c 65 _path_info faile
8550: 64 22 29 3b 0a 0a 09 09 09 72 65 74 75 72 6e 28 d");.....return(
8560: 67 70 69 5f 72 65 74 29 3b 0a 09 09 7d 0a 0a 09 gpi_ret);...}...
8570: 09 6d 6f 64 65 20 3d 20 22 63 72 65 61 74 65 22 .mode = "create"
8580: 3b 0a 0a 09 09 2f 2a 0a 09 09 20 2a 20 57 65 20 ;..../*... * We
8590: 68 61 76 65 20 74 6f 20 63 6c 65 61 72 20 74 68 have to clear th
85a0: 65 20 63 61 63 68 65 20 68 65 72 65 20 73 6f 20 e cache here so
85b0: 74 68 61 74 20 74 68 65 20 6e 75 6d 62 65 72 20 that the number
85c0: 6f 66 0a 09 09 20 2a 20 6c 69 6e 6b 73 20 67 65 of... * links ge
85d0: 74 73 20 6d 61 69 6e 74 61 69 6e 65 64 20 6f 6e ts maintained on
85e0: 20 74 68 65 20 70 61 72 65 6e 74 20 64 69 72 65 the parent dire
85f0: 63 74 6f 72 79 0a 09 09 20 2a 2f 0a 09 09 61 70 ctory... */...ap
8600: 70 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 6e 66 pfs_get_path_inf
8610: 6f 5f 63 61 63 68 65 5f 66 6c 75 73 68 28 61 70 o_cache_flush(ap
8620: 70 66 73 5f 67 65 74 5f 66 73 75 69 64 28 29 2c pfs_get_fsuid(),
8630: 20 2d 31 29 3b 0a 09 7d 20 65 6c 73 65 20 7b 0a -1);..} else {.
8640: 09 09 2f 2a 20 54 68 65 20 66 69 6c 65 20 6d 75 ../* The file mu
8650: 73 74 20 61 6c 72 65 61 64 79 20 65 78 69 73 74 st already exist
8660: 20 2a 2f 0a 09 09 69 66 20 28 67 70 69 5f 72 65 */...if (gpi_re
8670: 74 20 21 3d 20 30 29 20 7b 0a 09 09 09 41 50 50 t != 0) {....APP
8680: 46 53 5f 44 45 42 55 47 28 22 65 72 72 6f 72 3a FS_DEBUG("error:
8690: 20 67 65 74 5f 70 61 74 68 5f 69 6e 66 6f 20 66 get_path_info f
86a0: 61 69 6c 65 64 22 29 3b 0a 0a 09 09 09 72 65 74 ailed");.....ret
86b0: 75 72 6e 28 67 70 69 5f 72 65 74 29 3b 0a 09 09 urn(gpi_ret);...
86c0: 7d 0a 0a 09 09 6d 6f 64 65 20 3d 20 22 22 3b 0a }....mode = "";.
86d0: 0a 09 09 69 66 20 28 28 66 69 2d 3e 66 6c 61 67 ...if ((fi->flag
86e0: 73 20 26 20 4f 5f 57 52 4f 4e 4c 59 29 20 3d 3d s & O_WRONLY) ==
86f0: 20 4f 5f 57 52 4f 4e 4c 59 29 20 7b 0a 09 09 09 O_WRONLY) {....
8700: 6d 6f 64 65 20 3d 20 22 77 72 69 74 65 22 3b 0a mode = "write";.
8710: 09 09 7d 0a 09 7d 0a 0a 09 69 66 20 28 70 61 74 ..}..}...if (pat
8720: 68 69 6e 66 6f 2e 74 79 70 65 20 3d 3d 20 41 50 hinfo.type == AP
8730: 50 46 53 5f 50 41 54 48 54 59 50 45 5f 44 49 52 PFS_PATHTYPE_DIR
8740: 45 43 54 4f 52 59 29 20 7b 0a 09 09 41 50 50 46 ECTORY) {...APPF
8750: 53 5f 44 45 42 55 47 28 22 65 72 72 6f 72 3a 20 S_DEBUG("error:
8760: 41 73 6b 65 64 20 74 6f 20 6f 70 65 6e 20 61 20 Asked to open a
8770: 64 69 72 65 63 74 6f 72 79 2e 22 29 3b 0a 0a 09 directory.");...
8780: 09 72 65 74 75 72 6e 28 2d 45 49 53 44 49 52 29 .return(-EISDIR)
8790: 3b 0a 09 7d 0a 0a 09 69 6e 74 65 72 70 20 3d 20 ;..}...interp =
87a0: 61 70 70 66 73 5f 54 63 6c 49 6e 74 65 72 70 28 appfs_TclInterp(
87b0: 29 3b 0a 09 69 66 20 28 69 6e 74 65 72 70 20 3d );..if (interp =
87c0: 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 41 50 50 46 = NULL) {...APPF
87d0: 53 5f 44 45 42 55 47 28 22 65 72 72 6f 72 3a 20 S_DEBUG("error:
87e0: 55 6e 61 62 6c 65 20 74 6f 20 67 65 74 20 61 6e Unable to get an
87f0: 20 69 6e 74 65 72 70 72 65 74 65 72 22 29 3b 0a interpreter");.
8800: 0a 09 09 72 65 74 75 72 6e 28 2d 45 49 4f 29 3b ...return(-EIO);
8810: 0a 09 7d 0a 0a 09 61 70 70 66 73 5f 63 61 6c 6c ..}...appfs_call
8820: 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 50 72 65 73 _libtcl(Tcl_Pres
8830: 65 72 76 65 28 69 6e 74 65 72 70 29 3b 29 0a 0a erve(interp);)..
8840: 09 74 63 6c 5f 72 65 74 20 3d 20 61 70 70 66 73 .tcl_ret = appfs
8850: 5f 54 63 6c 5f 45 76 61 6c 28 69 6e 74 65 72 70 _Tcl_Eval(interp
8860: 2c 20 33 2c 20 22 3a 3a 61 70 70 66 73 3a 3a 6f , 3, "::appfs::o
8870: 70 65 6e 70 61 74 68 22 2c 20 70 61 74 68 2c 20 penpath", path,
8880: 6d 6f 64 65 29 3b 0a 09 69 66 20 28 74 63 6c 5f mode);..if (tcl_
8890: 72 65 74 20 21 3d 20 54 43 4c 5f 4f 4b 29 20 7b ret != TCL_OK) {
88a0: 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 ...APPFS_DEBUG("
88b0: 3a 3a 61 70 70 66 73 3a 3a 6f 70 65 6e 70 61 74 ::appfs::openpat
88c0: 68 28 25 73 2c 20 25 73 29 20 66 61 69 6c 65 64 h(%s, %s) failed
88d0: 2e 22 2c 20 70 61 74 68 2c 20 6d 6f 64 65 29 3b .", path, mode);
88e0: 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 ...appfs_call_li
88f0: 62 74 63 6c 28 0a 09 09 09 41 50 50 46 53 5f 44 btcl(....APPFS_D
8900: 45 42 55 47 28 22 54 63 6c 20 45 72 72 6f 72 20 EBUG("Tcl Error
8910: 69 73 3a 20 25 73 22 2c 20 54 63 6c 5f 47 65 74 is: %s", Tcl_Get
8920: 53 74 72 69 6e 67 52 65 73 75 6c 74 28 69 6e 74 StringResult(int
8930: 65 72 70 29 29 3b 0a 09 09 29 0a 0a 09 09 61 70 erp));...)....ap
8940: 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 pfs_call_libtcl(
8950: 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e 74 65 Tcl_Release(inte
8960: 72 70 29 3b 29 0a 0a 09 09 72 65 74 75 72 6e 28 rp);)....return(
8970: 2d 45 49 4f 29 3b 0a 09 7d 0a 0a 09 61 70 70 66 -EIO);..}...appf
8980: 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a 09 s_call_libtcl(..
8990: 09 72 65 61 6c 5f 70 61 74 68 20 3d 20 54 63 6c .real_path = Tcl
89a0: 5f 47 65 74 53 74 72 69 6e 67 52 65 73 75 6c 74 _GetStringResult
89b0: 28 69 6e 74 65 72 70 29 3b 0a 09 29 0a 0a 09 61 (interp);..)...a
89c0: 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c ppfs_call_libtcl
89d0: 28 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e 74 (Tcl_Release(int
89e0: 65 72 70 29 3b 29 0a 0a 09 69 66 20 28 72 65 61 erp);)...if (rea
89f0: 6c 5f 70 61 74 68 20 3d 3d 20 4e 55 4c 4c 29 20 l_path == NULL)
8a00: 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 {...APPFS_DEBUG(
8a10: 22 65 72 72 6f 72 3a 20 72 65 61 6c 5f 70 61 74 "error: real_pat
8a20: 68 20 77 61 73 20 4e 55 4c 4c 2e 22 29 0a 0a 09 h was NULL.")...
8a30: 09 72 65 74 75 72 6e 28 2d 45 49 4f 29 3b 0a 09 .return(-EIO);..
8a40: 7d 0a 0a 09 41 50 50 46 53 5f 44 45 42 55 47 28 }...APPFS_DEBUG(
8a50: 22 54 72 61 6e 73 6c 61 74 65 64 20 72 65 71 75 "Translated requ
8a60: 65 73 74 20 74 6f 20 6f 70 65 6e 20 25 73 20 74 est to open %s t
8a70: 6f 20 6f 70 65 6e 69 6e 67 20 25 73 20 28 6d 6f o opening %s (mo
8a80: 64 65 20 3d 20 5c 22 25 73 5c 22 29 22 2c 20 70 de = \"%s\")", p
8a90: 61 74 68 2c 20 72 65 61 6c 5f 70 61 74 68 2c 20 ath, real_path,
8aa0: 6d 6f 64 65 29 3b 0a 0a 09 66 68 20 3d 20 6f 70 mode);...fh = op
8ab0: 65 6e 28 72 65 61 6c 5f 70 61 74 68 2c 20 66 69 en(real_path, fi
8ac0: 2d 3e 66 6c 61 67 73 2c 20 30 36 30 30 29 3b 0a ->flags, 0600);.
8ad0: 0a 09 69 66 20 28 66 68 20 3c 20 30 29 20 7b 0a ..if (fh < 0) {.
8ae0: 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 65 ..APPFS_DEBUG("e
8af0: 72 72 6f 72 3a 20 6f 70 65 6e 20 66 61 69 6c 65 rror: open faile
8b00: 64 22 29 3b 0a 0a 09 09 72 65 74 75 72 6e 28 65 d");....return(e
8b10: 72 72 6e 6f 20 2a 20 2d 31 29 3b 0a 09 7d 0a 0a rrno * -1);..}..
8b20: 09 66 69 2d 3e 66 68 20 3d 20 66 68 3b 0a 0a 09 .fi->fh = fh;...
8b30: 41 50 50 46 53 5f 44 45 42 55 47 28 22 4f 70 65 APPFS_DEBUG("Ope
8b40: 6e 65 64 20 5c 22 25 73 5c 22 20 28 66 6f 72 20 ned \"%s\" (for
8b50: 5c 22 25 73 5c 22 29 20 77 69 74 68 20 66 69 6c \"%s\") with fil
8b60: 65 20 64 65 73 63 72 69 70 74 6f 72 20 25 69 22 e descriptor %i"
8b70: 2c 20 72 65 61 6c 5f 70 61 74 68 2c 20 70 61 74 , real_path, pat
8b80: 68 2c 20 66 68 29 3b 0a 0a 09 72 65 74 75 72 6e h, fh);...return
8b90: 28 30 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 69 (0);.}..static i
8ba0: 6e 74 20 61 70 70 66 73 5f 66 75 73 65 5f 63 6c nt appfs_fuse_cl
8bb0: 6f 73 65 28 63 6f 6e 73 74 20 63 68 61 72 20 2a ose(const char *
8bc0: 70 61 74 68 2c 20 73 74 72 75 63 74 20 66 75 73 path, struct fus
8bd0: 65 5f 66 69 6c 65 5f 69 6e 66 6f 20 2a 66 69 29 e_file_info *fi)
8be0: 20 7b 0a 09 69 6e 74 20 63 6c 6f 73 65 5f 72 65 {..int close_re
8bf0: 74 3b 0a 0a 09 41 50 50 46 53 5f 44 45 42 55 47 t;...APPFS_DEBUG
8c00: 28 22 45 6e 74 65 72 20 28 70 61 74 68 20 3d 20 ("Enter (path =
8c10: 25 73 2c 20 2e 2e 2e 29 22 2c 20 70 61 74 68 29 %s, ...)", path)
8c20: 3b 0a 0a 23 69 66 20 64 65 66 69 6e 65 64 28 41 ;..#if defined(A
8c30: 50 50 46 53 5f 45 58 45 43 5f 50 41 54 48 5f 45 PPFS_EXEC_PATH_E
8c40: 4e 41 42 4c 45 5f 4d 41 4a 4f 52 5f 53 45 43 55 NABLE_MAJOR_SECU
8c50: 52 49 54 59 5f 48 4f 4c 45 29 0a 09 69 66 20 28 RITY_HOLE)..if (
8c60: 73 74 72 63 6d 70 28 70 61 74 68 2c 20 22 2f 65 strcmp(path, "/e
8c70: 78 65 63 22 29 20 3d 3d 20 30 29 20 7b 0a 09 09 xec") == 0) {...
8c80: 72 65 74 75 72 6e 28 30 29 3b 0a 09 7d 0a 23 65 return(0);..}.#e
8c90: 6e 64 69 66 0a 0a 09 61 70 70 66 73 5f 67 65 74 ndif...appfs_get
8ca0: 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 _path_info_cache
8cb0: 5f 72 6d 28 70 61 74 68 2c 20 61 70 70 66 73 5f _rm(path, appfs_
8cc0: 67 65 74 5f 66 73 75 69 64 28 29 29 3b 0a 0a 09 get_fsuid());...
8cd0: 63 6c 6f 73 65 5f 72 65 74 20 3d 20 63 6c 6f 73 close_ret = clos
8ce0: 65 28 66 69 2d 3e 66 68 29 3b 0a 09 69 66 20 28 e(fi->fh);..if (
8cf0: 63 6c 6f 73 65 5f 72 65 74 20 21 3d 20 30 29 20 close_ret != 0)
8d00: 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 {...APPFS_DEBUG(
8d10: 22 65 72 72 6f 72 3a 20 63 6c 6f 73 65 20 66 61 "error: close fa
8d20: 69 6c 65 64 22 29 3b 0a 0a 09 09 72 65 74 75 72 iled");....retur
8d30: 6e 28 65 72 72 6e 6f 20 2a 20 2d 31 29 3b 0a 09 n(errno * -1);..
8d40: 7d 0a 0a 09 72 65 74 75 72 6e 28 30 29 3b 0a 7d }...return(0);.}
8d50: 0a 0a 73 74 61 74 69 63 20 69 6e 74 20 61 70 70 ..static int app
8d60: 66 73 5f 66 75 73 65 5f 72 65 61 64 28 63 6f 6e fs_fuse_read(con
8d70: 73 74 20 63 68 61 72 20 2a 70 61 74 68 2c 20 63 st char *path, c
8d80: 68 61 72 20 2a 62 75 66 2c 20 73 69 7a 65 5f 74 har *buf, size_t
8d90: 20 73 69 7a 65 2c 20 6f 66 66 5f 74 20 6f 66 66 size, off_t off
8da0: 73 65 74 2c 20 73 74 72 75 63 74 20 66 75 73 65 set, struct fuse
8db0: 5f 66 69 6c 65 5f 69 6e 66 6f 20 2a 66 69 29 20 _file_info *fi)
8dc0: 7b 0a 09 73 73 69 7a 65 5f 74 20 72 65 61 64 5f {..ssize_t read_
8dd0: 72 65 74 3b 0a 09 69 6e 74 20 72 65 74 76 61 6c ret;..int retval
8de0: 3b 0a 0a 09 41 50 50 46 53 5f 44 45 42 55 47 28 ;...APPFS_DEBUG(
8df0: 22 45 6e 74 65 72 20 28 70 61 74 68 20 3d 20 25 "Enter (path = %
8e00: 73 2c 20 62 75 66 2c 20 73 69 7a 65 20 3d 20 25 s, buf, size = %
8e10: 6c 6c 69 2c 20 6f 66 66 73 65 74 20 3d 20 25 6c lli, offset = %l
8e20: 6c 69 2c 20 66 64 20 3d 20 25 6c 6c 69 29 22 2c li, fd = %lli)",
8e30: 20 70 61 74 68 2c 20 28 6c 6f 6e 67 20 6c 6f 6e path, (long lon
8e40: 67 29 20 73 69 7a 65 2c 20 28 6c 6f 6e 67 20 6c g) size, (long l
8e50: 6f 6e 67 29 20 6f 66 66 73 65 74 2c 20 28 6c 6f ong) offset, (lo
8e60: 6e 67 20 6c 6f 6e 67 29 20 66 69 2d 3e 66 68 29 ng long) fi->fh)
8e70: 3b 0a 0a 09 72 65 74 76 61 6c 20 3d 20 30 3b 0a ;...retval = 0;.
8e80: 0a 09 77 68 69 6c 65 20 28 73 69 7a 65 20 21 3d ..while (size !=
8e90: 20 30 29 20 7b 0a 09 09 72 65 61 64 5f 72 65 74 0) {...read_ret
8ea0: 20 3d 20 70 72 65 61 64 28 66 69 2d 3e 66 68 2c = pread(fi->fh,
8eb0: 20 62 75 66 2c 20 73 69 7a 65 2c 20 6f 66 66 73 buf, size, offs
8ec0: 65 74 29 3b 0a 0a 09 09 69 66 20 28 72 65 61 64 et);....if (read
8ed0: 5f 72 65 74 20 3c 20 30 29 20 7b 0a 09 09 09 41 _ret < 0) {....A
8ee0: 50 50 46 53 5f 44 45 42 55 47 28 22 65 72 72 6f PPFS_DEBUG("erro
8ef0: 72 3a 20 72 65 61 64 20 66 61 69 6c 65 64 22 29 r: read failed")
8f00: 3b 0a 0a 09 09 09 72 65 74 75 72 6e 28 65 72 72 ;.....return(err
8f10: 6e 6f 20 2a 20 2d 31 29 3b 0a 09 09 7d 0a 0a 09 no * -1);...}...
8f20: 09 69 66 20 28 72 65 61 64 5f 72 65 74 20 3d 3d .if (read_ret ==
8f30: 20 30 29 20 7b 0a 09 09 09 62 72 65 61 6b 3b 0a 0) {....break;.
8f40: 09 09 7d 0a 0a 09 09 73 69 7a 65 20 2d 3d 20 72 ..}....size -= r
8f50: 65 61 64 5f 72 65 74 3b 0a 09 09 62 75 66 20 20 ead_ret;...buf
8f60: 2b 3d 20 72 65 61 64 5f 72 65 74 3b 0a 09 09 6f += read_ret;...o
8f70: 66 66 73 65 74 20 2b 3d 20 72 65 61 64 5f 72 65 ffset += read_re
8f80: 74 3b 0a 09 09 72 65 74 76 61 6c 20 2b 3d 20 72 t;...retval += r
8f90: 65 61 64 5f 72 65 74 3b 0a 09 7d 0a 0a 09 69 66 ead_ret;..}...if
8fa0: 20 28 73 69 7a 65 20 21 3d 20 30 29 20 7b 0a 09 (size != 0) {..
8fb0: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 65 72 .APPFS_DEBUG("er
8fc0: 72 6f 72 3a 20 69 6e 63 6f 6d 70 6c 65 74 65 20 ror: incomplete
8fd0: 72 65 61 64 20 28 74 68 69 73 20 6d 69 67 68 74 read (this might
8fe0: 20 62 65 20 61 6e 20 65 72 72 6f 72 20 62 65 63 be an error bec
8ff0: 61 75 73 65 20 46 55 53 45 20 77 69 6c 6c 20 72 ause FUSE will r
9000: 65 71 75 65 73 74 20 74 68 65 20 65 78 61 63 74 equest the exact
9010: 20 6c 65 6e 67 74 68 20 6f 66 20 74 68 65 20 66 length of the f
9020: 69 6c 65 29 22 29 3b 0a 09 7d 0a 0a 09 41 50 50 ile)");..}...APP
9030: 46 53 5f 44 45 42 55 47 28 22 52 65 74 75 72 6e FS_DEBUG("Return
9040: 69 6e 67 3a 20 25 69 22 2c 20 72 65 74 76 61 6c ing: %i", retval
9050: 29 3b 0a 0a 09 72 65 74 75 72 6e 28 72 65 74 76 );...return(retv
9060: 61 6c 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 69 al);.}..static i
9070: 6e 74 20 61 70 70 66 73 5f 66 75 73 65 5f 77 72 nt appfs_fuse_wr
9080: 69 74 65 28 63 6f 6e 73 74 20 63 68 61 72 20 2a ite(const char *
9090: 70 61 74 68 2c 20 63 6f 6e 73 74 20 63 68 61 72 path, const char
90a0: 20 2a 62 75 66 2c 20 73 69 7a 65 5f 74 20 73 69 *buf, size_t si
90b0: 7a 65 2c 20 6f 66 66 5f 74 20 6f 66 66 73 65 74 ze, off_t offset
90c0: 2c 20 73 74 72 75 63 74 20 66 75 73 65 5f 66 69 , struct fuse_fi
90d0: 6c 65 5f 69 6e 66 6f 20 2a 66 69 29 20 7b 0a 09 le_info *fi) {..
90e0: 73 73 69 7a 65 5f 74 20 77 72 69 74 65 5f 72 65 ssize_t write_re
90f0: 74 3b 0a 09 69 6e 74 20 72 65 74 76 61 6c 3b 0a t;..int retval;.
9100: 0a 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 45 ..APPFS_DEBUG("E
9110: 6e 74 65 72 20 28 70 61 74 68 20 3d 20 25 73 2c nter (path = %s,
9120: 20 2e 2e 2e 29 22 2c 20 70 61 74 68 29 3b 0a 0a ...)", path);..
9130: 23 69 66 20 64 65 66 69 6e 65 64 28 41 50 50 46 #if defined(APPF
9140: 53 5f 45 58 45 43 5f 50 41 54 48 5f 45 4e 41 42 S_EXEC_PATH_ENAB
9150: 4c 45 5f 4d 41 4a 4f 52 5f 53 45 43 55 52 49 54 LE_MAJOR_SECURIT
9160: 59 5f 48 4f 4c 45 29 0a 09 69 66 20 28 73 74 72 Y_HOLE)..if (str
9170: 63 6d 70 28 70 61 74 68 2c 20 22 2f 65 78 65 63 cmp(path, "/exec
9180: 22 29 20 3d 3d 20 30 29 20 7b 0a 09 09 61 70 70 ") == 0) {...app
9190: 66 73 5f 72 75 6e 54 63 6c 28 62 75 66 2c 20 73 fs_runTcl(buf, s
91a0: 69 7a 65 29 3b 0a 0a 09 09 72 65 74 75 72 6e 28 ize);....return(
91b0: 73 69 7a 65 29 3b 0a 09 7d 0a 23 65 6e 64 69 66 size);..}.#endif
91c0: 0a 0a 09 61 70 70 66 73 5f 67 65 74 5f 70 61 74 ...appfs_get_pat
91d0: 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5f 72 6d 28 h_info_cache_rm(
91e0: 70 61 74 68 2c 20 61 70 70 66 73 5f 67 65 74 5f path, appfs_get_
91f0: 66 73 75 69 64 28 29 29 3b 0a 0a 09 72 65 74 76 fsuid());...retv
9200: 61 6c 20 3d 20 30 3b 0a 0a 09 77 68 69 6c 65 20 al = 0;...while
9210: 28 73 69 7a 65 20 21 3d 20 30 29 20 7b 0a 09 09 (size != 0) {...
9220: 77 72 69 74 65 5f 72 65 74 20 3d 20 70 77 72 69 write_ret = pwri
9230: 74 65 28 66 69 2d 3e 66 68 2c 20 62 75 66 2c 20 te(fi->fh, buf,
9240: 73 69 7a 65 2c 20 6f 66 66 73 65 74 29 3b 0a 0a size, offset);..
9250: 09 09 69 66 20 28 77 72 69 74 65 5f 72 65 74 20 ..if (write_ret
9260: 3c 20 30 29 20 7b 0a 09 09 09 41 50 50 46 53 5f < 0) {....APPFS_
9270: 44 45 42 55 47 28 22 65 72 72 6f 72 3a 20 77 72 DEBUG("error: wr
9280: 69 74 65 20 66 61 69 6c 65 64 22 29 3b 0a 0a 09 ite failed");...
9290: 09 09 72 65 74 75 72 6e 28 65 72 72 6e 6f 20 2a ..return(errno *
92a0: 20 2d 31 29 3b 0a 09 09 7d 0a 0a 09 09 69 66 20 -1);...}....if
92b0: 28 77 72 69 74 65 5f 72 65 74 20 3d 3d 20 30 29 (write_ret == 0)
92c0: 20 7b 0a 09 09 09 62 72 65 61 6b 3b 0a 09 09 7d {....break;...}
92d0: 0a 0a 09 09 73 69 7a 65 20 2d 3d 20 77 72 69 74 ....size -= writ
92e0: 65 5f 72 65 74 3b 0a 09 09 62 75 66 20 20 2b 3d e_ret;...buf +=
92f0: 20 77 72 69 74 65 5f 72 65 74 3b 0a 09 09 6f 66 write_ret;...of
9300: 66 73 65 74 20 2b 3d 20 77 72 69 74 65 5f 72 65 fset += write_re
9310: 74 3b 0a 09 09 72 65 74 76 61 6c 20 2b 3d 20 77 t;...retval += w
9320: 72 69 74 65 5f 72 65 74 3b 0a 09 7d 0a 0a 09 69 rite_ret;..}...i
9330: 66 20 28 73 69 7a 65 20 21 3d 20 30 29 20 7b 0a f (size != 0) {.
9340: 09 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 65 ..APPFS_DEBUG("e
9350: 72 72 6f 72 3a 20 69 6e 63 6f 6d 70 6c 65 74 65 rror: incomplete
9360: 20 77 72 69 74 65 22 29 3b 0a 09 7d 0a 0a 09 72 write");..}...r
9370: 65 74 75 72 6e 28 72 65 74 76 61 6c 29 3b 0a 7d eturn(retval);.}
9380: 0a 0a 73 74 61 74 69 63 20 69 6e 74 20 61 70 70 ..static int app
9390: 66 73 5f 66 75 73 65 5f 6d 6b 6e 6f 64 28 63 6f fs_fuse_mknod(co
93a0: 6e 73 74 20 63 68 61 72 20 2a 70 61 74 68 2c 20 nst char *path,
93b0: 6d 6f 64 65 5f 74 20 6d 6f 64 65 2c 20 64 65 76 mode_t mode, dev
93c0: 5f 74 20 64 65 76 69 63 65 29 20 7b 0a 09 63 68 _t device) {..ch
93d0: 61 72 20 2a 72 65 61 6c 5f 70 61 74 68 3b 0a 09 ar *real_path;..
93e0: 69 6e 74 20 6d 6b 6e 6f 64 5f 72 65 74 3b 0a 0a int mknod_ret;..
93f0: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 45 6e .APPFS_DEBUG("En
9400: 74 65 72 20 28 70 61 74 68 20 3d 20 25 73 2c 20 ter (path = %s,
9410: 2e 2e 2e 29 22 2c 20 70 61 74 68 29 3b 0a 0a 09 ...)", path);...
9420: 69 66 20 28 28 6d 6f 64 65 20 26 20 53 5f 49 46 if ((mode & S_IF
9430: 43 48 52 29 20 3d 3d 20 53 5f 49 46 43 48 52 29 CHR) == S_IFCHR)
9440: 20 7b 0a 09 09 72 65 74 75 72 6e 28 2d 45 50 45 {...return(-EPE
9450: 52 4d 29 3b 0a 09 7d 0a 0a 09 69 66 20 28 28 6d RM);..}...if ((m
9460: 6f 64 65 20 26 20 53 5f 49 46 42 4c 4b 29 20 3d ode & S_IFBLK) =
9470: 3d 20 53 5f 49 46 42 4c 4b 29 20 7b 0a 09 09 72 = S_IFBLK) {...r
9480: 65 74 75 72 6e 28 2d 45 50 45 52 4d 29 3b 0a 09 eturn(-EPERM);..
9490: 7d 0a 0a 09 72 65 61 6c 5f 70 61 74 68 20 3d 20 }...real_path =
94a0: 61 70 70 66 73 5f 70 72 65 70 61 72 65 5f 74 6f appfs_prepare_to
94b0: 5f 63 72 65 61 74 65 28 70 61 74 68 29 3b 0a 09 _create(path);..
94c0: 69 66 20 28 72 65 61 6c 5f 70 61 74 68 20 3d 3d if (real_path ==
94d0: 20 4e 55 4c 4c 29 20 7b 0a 09 09 72 65 74 75 72 NULL) {...retur
94e0: 6e 28 2d 45 49 4f 29 3b 0a 09 7d 0a 0a 09 61 70 n(-EIO);..}...ap
94f0: 70 66 73 5f 73 69 6d 75 6c 61 74 65 5f 75 73 65 pfs_simulate_use
9500: 72 5f 66 73 5f 65 6e 74 65 72 28 29 3b 0a 0a 09 r_fs_enter();...
9510: 6d 6b 6e 6f 64 5f 72 65 74 20 3d 20 6d 6b 6e 6f mknod_ret = mkno
9520: 64 28 72 65 61 6c 5f 70 61 74 68 2c 20 6d 6f 64 d(real_path, mod
9530: 65 2c 20 64 65 76 69 63 65 29 3b 0a 0a 09 61 70 e, device);...ap
9540: 70 66 73 5f 73 69 6d 75 6c 61 74 65 5f 75 73 65 pfs_simulate_use
9550: 72 5f 66 73 5f 6c 65 61 76 65 28 29 3b 0a 0a 09 r_fs_leave();...
9560: 66 72 65 65 28 72 65 61 6c 5f 70 61 74 68 29 3b free(real_path);
9570: 0a 0a 09 69 66 20 28 6d 6b 6e 6f 64 5f 72 65 74 ...if (mknod_ret
9580: 20 21 3d 20 30 29 20 7b 0a 09 09 72 65 74 75 72 != 0) {...retur
9590: 6e 28 65 72 72 6e 6f 20 2a 20 2d 31 29 3b 0a 09 n(errno * -1);..
95a0: 7d 0a 0a 09 72 65 74 75 72 6e 28 30 29 3b 0a 7d }...return(0);.}
95b0: 0a 0a 73 74 61 74 69 63 20 69 6e 74 20 61 70 70 ..static int app
95c0: 66 73 5f 66 75 73 65 5f 63 72 65 61 74 65 28 63 fs_fuse_create(c
95d0: 6f 6e 73 74 20 63 68 61 72 20 2a 70 61 74 68 2c onst char *path,
95e0: 20 6d 6f 64 65 5f 74 20 6d 6f 64 65 2c 20 73 74 mode_t mode, st
95f0: 72 75 63 74 20 66 75 73 65 5f 66 69 6c 65 5f 69 ruct fuse_file_i
9600: 6e 66 6f 20 2a 66 69 29 20 7b 0a 09 63 68 61 72 nfo *fi) {..char
9610: 20 2a 72 65 61 6c 5f 70 61 74 68 3b 0a 09 69 6e *real_path;..in
9620: 74 20 66 64 3b 0a 0a 09 41 50 50 46 53 5f 44 45 t fd;...APPFS_DE
9630: 42 55 47 28 22 45 6e 74 65 72 20 28 70 61 74 68 BUG("Enter (path
9640: 20 3d 20 25 73 2c 20 2e 2e 2e 29 22 2c 20 70 61 = %s, ...)", pa
9650: 74 68 29 3b 0a 0a 09 69 66 20 28 28 6d 6f 64 65 th);...if ((mode
9660: 20 26 20 53 5f 49 46 43 48 52 29 20 3d 3d 20 53 & S_IFCHR) == S
9670: 5f 49 46 43 48 52 29 20 7b 0a 09 09 72 65 74 75 _IFCHR) {...retu
9680: 72 6e 28 2d 45 50 45 52 4d 29 3b 0a 09 7d 0a 0a rn(-EPERM);..}..
9690: 09 69 66 20 28 28 6d 6f 64 65 20 26 20 53 5f 49 .if ((mode & S_I
96a0: 46 42 4c 4b 29 20 3d 3d 20 53 5f 49 46 42 4c 4b FBLK) == S_IFBLK
96b0: 29 20 7b 0a 09 09 72 65 74 75 72 6e 28 2d 45 50 ) {...return(-EP
96c0: 45 52 4d 29 3b 0a 09 7d 0a 0a 09 72 65 61 6c 5f ERM);..}...real_
96d0: 70 61 74 68 20 3d 20 61 70 70 66 73 5f 70 72 65 path = appfs_pre
96e0: 70 61 72 65 5f 74 6f 5f 63 72 65 61 74 65 28 70 pare_to_create(p
96f0: 61 74 68 29 3b 0a 09 69 66 20 28 72 65 61 6c 5f ath);..if (real_
9700: 70 61 74 68 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a path == NULL) {.
9710: 09 09 72 65 74 75 72 6e 28 2d 45 49 4f 29 3b 0a ..return(-EIO);.
9720: 09 7d 0a 0a 09 61 70 70 66 73 5f 73 69 6d 75 6c .}...appfs_simul
9730: 61 74 65 5f 75 73 65 72 5f 66 73 5f 65 6e 74 65 ate_user_fs_ente
9740: 72 28 29 3b 0a 0a 09 66 64 20 3d 20 63 72 65 61 r();...fd = crea
9750: 74 28 72 65 61 6c 5f 70 61 74 68 2c 20 6d 6f 64 t(real_path, mod
9760: 65 29 3b 0a 0a 09 61 70 70 66 73 5f 73 69 6d 75 e);...appfs_simu
9770: 6c 61 74 65 5f 75 73 65 72 5f 66 73 5f 6c 65 61 late_user_fs_lea
9780: 76 65 28 29 3b 0a 0a 09 66 72 65 65 28 72 65 61 ve();...free(rea
9790: 6c 5f 70 61 74 68 29 3b 0a 0a 09 69 66 20 28 66 l_path);...if (f
97a0: 64 20 3c 20 30 29 20 7b 0a 09 09 72 65 74 75 72 d < 0) {...retur
97b0: 6e 28 65 72 72 6e 6f 20 2a 20 2d 31 29 3b 0a 09 n(errno * -1);..
97c0: 7d 0a 0a 09 66 69 2d 3e 66 68 20 3d 20 66 64 3b }...fi->fh = fd;
97d0: 0a 0a 09 72 65 74 75 72 6e 28 30 29 3b 0a 7d 0a ...return(0);.}.
97e0: 0a 73 74 61 74 69 63 20 69 6e 74 20 61 70 70 66 .static int appf
97f0: 73 5f 66 75 73 65 5f 74 72 75 6e 63 61 74 65 28 s_fuse_truncate(
9800: 63 6f 6e 73 74 20 63 68 61 72 20 2a 70 61 74 68 const char *path
9810: 2c 20 6f 66 66 5f 74 20 73 69 7a 65 29 20 7b 0a , off_t size) {.
9820: 09 63 68 61 72 20 2a 72 65 61 6c 5f 70 61 74 68 .char *real_path
9830: 3b 0a 09 69 6e 74 20 74 72 75 6e 63 61 74 65 5f ;..int truncate_
9840: 72 65 74 3b 0a 0a 09 41 50 50 46 53 5f 44 45 42 ret;...APPFS_DEB
9850: 55 47 28 22 45 6e 74 65 72 20 28 70 61 74 68 20 UG("Enter (path
9860: 3d 20 25 73 2c 20 2e 2e 2e 29 22 2c 20 70 61 74 = %s, ...)", pat
9870: 68 29 3b 0a 0a 23 69 66 20 64 65 66 69 6e 65 64 h);..#if defined
9880: 28 41 50 50 46 53 5f 45 58 45 43 5f 50 41 54 48 (APPFS_EXEC_PATH
9890: 5f 45 4e 41 42 4c 45 5f 4d 41 4a 4f 52 5f 53 45 _ENABLE_MAJOR_SE
98a0: 43 55 52 49 54 59 5f 48 4f 4c 45 29 0a 09 69 66 CURITY_HOLE)..if
98b0: 20 28 73 74 72 63 6d 70 28 70 61 74 68 2c 20 22 (strcmp(path, "
98c0: 2f 65 78 65 63 22 29 20 3d 3d 20 30 29 20 7b 0a /exec") == 0) {.
98d0: 09 09 72 65 74 75 72 6e 28 30 29 3b 0a 09 7d 0a ..return(0);..}.
98e0: 23 65 6e 64 69 66 0a 0a 09 72 65 61 6c 5f 70 61 #endif...real_pa
98f0: 74 68 20 3d 20 61 70 70 66 73 5f 6c 6f 63 61 6c th = appfs_local
9900: 70 61 74 68 28 70 61 74 68 29 3b 0a 09 69 66 20 path(path);..if
9910: 28 72 65 61 6c 5f 70 61 74 68 20 3d 3d 20 4e 55 (real_path == NU
9920: 4c 4c 29 20 7b 0a 09 09 72 65 74 75 72 6e 28 2d LL) {...return(-
9930: 45 49 4f 29 3b 0a 09 7d 0a 0a 09 61 70 70 66 73 EIO);..}...appfs
9940: 5f 67 65 74 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 _get_path_info_c
9950: 61 63 68 65 5f 72 6d 28 70 61 74 68 2c 20 61 70 ache_rm(path, ap
9960: 70 66 73 5f 67 65 74 5f 66 73 75 69 64 28 29 29 pfs_get_fsuid())
9970: 3b 0a 0a 09 61 70 70 66 73 5f 73 69 6d 75 6c 61 ;...appfs_simula
9980: 74 65 5f 75 73 65 72 5f 66 73 5f 65 6e 74 65 72 te_user_fs_enter
9990: 28 29 3b 0a 0a 09 74 72 75 6e 63 61 74 65 5f 72 ();...truncate_r
99a0: 65 74 20 3d 20 74 72 75 6e 63 61 74 65 28 72 65 et = truncate(re
99b0: 61 6c 5f 70 61 74 68 2c 20 73 69 7a 65 29 3b 0a al_path, size);.
99c0: 0a 09 61 70 70 66 73 5f 73 69 6d 75 6c 61 74 65 ..appfs_simulate
99d0: 5f 75 73 65 72 5f 66 73 5f 6c 65 61 76 65 28 29 _user_fs_leave()
99e0: 3b 0a 0a 09 66 72 65 65 28 72 65 61 6c 5f 70 61 ;...free(real_pa
99f0: 74 68 29 3b 0a 0a 09 69 66 20 28 74 72 75 6e 63 th);...if (trunc
9a00: 61 74 65 5f 72 65 74 20 21 3d 20 30 29 20 7b 0a ate_ret != 0) {.
9a10: 09 09 72 65 74 75 72 6e 28 65 72 72 6e 6f 20 2a ..return(errno *
9a20: 20 2d 31 29 3b 0a 09 7d 0a 0a 09 72 65 74 75 72 -1);..}...retur
9a30: 6e 28 30 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 n(0);.}..static
9a40: 69 6e 74 20 61 70 70 66 73 5f 66 75 73 65 5f 75 int appfs_fuse_u
9a50: 6e 6c 69 6e 6b 5f 72 6d 64 69 72 28 63 6f 6e 73 nlink_rmdir(cons
9a60: 74 20 63 68 61 72 20 2a 70 61 74 68 29 20 7b 0a t char *path) {.
9a70: 09 54 63 6c 5f 49 6e 74 65 72 70 20 2a 69 6e 74 .Tcl_Interp *int
9a80: 65 72 70 3b 0a 09 69 6e 74 20 74 63 6c 5f 72 65 erp;..int tcl_re
9a90: 74 3b 0a 0a 09 41 50 50 46 53 5f 44 45 42 55 47 t;...APPFS_DEBUG
9aa0: 28 22 45 6e 74 65 72 20 28 70 61 74 68 20 3d 20 ("Enter (path =
9ab0: 25 73 2c 20 2e 2e 2e 29 22 2c 20 70 61 74 68 29 %s, ...)", path)
9ac0: 3b 0a 0a 09 61 70 70 66 73 5f 67 65 74 5f 70 61 ;...appfs_get_pa
9ad0: 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5f 66 6c th_info_cache_fl
9ae0: 75 73 68 28 61 70 70 66 73 5f 67 65 74 5f 66 73 ush(appfs_get_fs
9af0: 75 69 64 28 29 2c 20 2d 31 29 3b 0a 0a 09 69 6e uid(), -1);...in
9b00: 74 65 72 70 20 3d 20 61 70 70 66 73 5f 54 63 6c terp = appfs_Tcl
9b10: 49 6e 74 65 72 70 28 29 3b 0a 09 69 66 20 28 69 Interp();..if (i
9b20: 6e 74 65 72 70 20 3d 3d 20 4e 55 4c 4c 29 20 7b nterp == NULL) {
9b30: 0a 09 09 72 65 74 75 72 6e 28 2d 45 49 4f 29 3b ...return(-EIO);
9b40: 0a 09 7d 0a 0a 09 61 70 70 66 73 5f 63 61 6c 6c ..}...appfs_call
9b50: 5f 6c 69 62 74 63 6c 28 54 63 6c 5f 50 72 65 73 _libtcl(Tcl_Pres
9b60: 65 72 76 65 28 69 6e 74 65 72 70 29 3b 29 0a 0a erve(interp);)..
9b70: 09 74 63 6c 5f 72 65 74 20 3d 20 61 70 70 66 73 .tcl_ret = appfs
9b80: 5f 54 63 6c 5f 45 76 61 6c 28 69 6e 74 65 72 70 _Tcl_Eval(interp
9b90: 2c 20 32 2c 20 22 3a 3a 61 70 70 66 73 3a 3a 75 , 2, "::appfs::u
9ba0: 6e 6c 69 6e 6b 70 61 74 68 22 2c 20 70 61 74 68 nlinkpath", path
9bb0: 29 3b 0a 09 69 66 20 28 74 63 6c 5f 72 65 74 20 );..if (tcl_ret
9bc0: 21 3d 20 54 43 4c 5f 4f 4b 29 20 7b 0a 09 09 41 != TCL_OK) {...A
9bd0: 50 50 46 53 5f 44 45 42 55 47 28 22 3a 3a 61 70 PPFS_DEBUG("::ap
9be0: 70 66 73 3a 3a 75 6e 6c 69 6e 6b 70 61 74 68 28 pfs::unlinkpath(
9bf0: 25 73 29 20 66 61 69 6c 65 64 2e 22 2c 20 70 61 %s) failed.", pa
9c00: 74 68 29 3b 0a 09 09 61 70 70 66 73 5f 63 61 6c th);...appfs_cal
9c10: 6c 5f 6c 69 62 74 63 6c 28 0a 09 09 09 41 50 50 l_libtcl(....APP
9c20: 46 53 5f 44 45 42 55 47 28 22 54 63 6c 20 45 72 FS_DEBUG("Tcl Er
9c30: 72 6f 72 20 69 73 3a 20 25 73 22 2c 20 54 63 6c ror is: %s", Tcl
9c40: 5f 47 65 74 53 74 72 69 6e 67 52 65 73 75 6c 74 _GetStringResult
9c50: 28 69 6e 74 65 72 70 29 29 3b 0a 09 09 29 0a 0a (interp));...)..
9c60: 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 ..appfs_call_lib
9c70: 74 63 6c 28 54 63 6c 5f 52 65 6c 65 61 73 65 28 tcl(Tcl_Release(
9c80: 69 6e 74 65 72 70 29 3b 29 0a 0a 09 09 72 65 74 interp);)....ret
9c90: 75 72 6e 28 2d 45 49 4f 29 3b 0a 09 7d 0a 0a 09 urn(-EIO);..}...
9ca0: 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 appfs_call_libtc
9cb0: 6c 28 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e l(Tcl_Release(in
9cc0: 74 65 72 70 29 3b 29 0a 0a 09 72 65 74 75 72 6e terp);)...return
9cd0: 28 30 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 69 (0);.}..static i
9ce0: 6e 74 20 61 70 70 66 73 5f 66 75 73 65 5f 6d 6b nt appfs_fuse_mk
9cf0: 64 69 72 28 63 6f 6e 73 74 20 63 68 61 72 20 2a dir(const char *
9d00: 70 61 74 68 2c 20 6d 6f 64 65 5f 74 20 6d 6f 64 path, mode_t mod
9d10: 65 29 20 7b 0a 09 63 68 61 72 20 2a 72 65 61 6c e) {..char *real
9d20: 5f 70 61 74 68 3b 0a 09 69 6e 74 20 6d 6b 64 69 _path;..int mkdi
9d30: 72 5f 72 65 74 3b 0a 0a 09 41 50 50 46 53 5f 44 r_ret;...APPFS_D
9d40: 45 42 55 47 28 22 45 6e 74 65 72 20 28 70 61 74 EBUG("Enter (pat
9d50: 68 20 3d 20 25 73 2c 20 2e 2e 2e 29 22 2c 20 70 h = %s, ...)", p
9d60: 61 74 68 29 3b 0a 0a 09 72 65 61 6c 5f 70 61 74 ath);...real_pat
9d70: 68 20 3d 20 61 70 70 66 73 5f 70 72 65 70 61 72 h = appfs_prepar
9d80: 65 5f 74 6f 5f 63 72 65 61 74 65 28 70 61 74 68 e_to_create(path
9d90: 29 3b 0a 09 69 66 20 28 72 65 61 6c 5f 70 61 74 );..if (real_pat
9da0: 68 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 72 h == NULL) {...r
9db0: 65 74 75 72 6e 28 2d 45 49 4f 29 3b 0a 09 7d 0a eturn(-EIO);..}.
9dc0: 0a 09 61 70 70 66 73 5f 73 69 6d 75 6c 61 74 65 ..appfs_simulate
9dd0: 5f 75 73 65 72 5f 66 73 5f 65 6e 74 65 72 28 29 _user_fs_enter()
9de0: 3b 0a 0a 09 6d 6b 64 69 72 5f 72 65 74 20 3d 20 ;...mkdir_ret =
9df0: 6d 6b 64 69 72 28 72 65 61 6c 5f 70 61 74 68 2c mkdir(real_path,
9e00: 20 6d 6f 64 65 29 3b 0a 0a 09 61 70 70 66 73 5f mode);...appfs_
9e10: 73 69 6d 75 6c 61 74 65 5f 75 73 65 72 5f 66 73 simulate_user_fs
9e20: 5f 6c 65 61 76 65 28 29 3b 0a 0a 09 66 72 65 65 _leave();...free
9e30: 28 72 65 61 6c 5f 70 61 74 68 29 3b 0a 0a 09 69 (real_path);...i
9e40: 66 20 28 6d 6b 64 69 72 5f 72 65 74 20 21 3d 20 f (mkdir_ret !=
9e50: 30 29 20 7b 0a 09 09 69 66 20 28 65 72 72 6e 6f 0) {...if (errno
9e60: 20 21 3d 20 45 45 58 49 53 54 29 20 7b 0a 09 09 != EEXIST) {...
9e70: 09 72 65 74 75 72 6e 28 65 72 72 6e 6f 20 2a 20 .return(errno *
9e80: 2d 31 29 3b 0a 09 09 7d 0a 09 7d 0a 0a 09 72 65 -1);...}..}...re
9e90: 74 75 72 6e 28 30 29 3b 0a 7d 0a 0a 73 74 61 74 turn(0);.}..stat
9ea0: 69 63 20 69 6e 74 20 61 70 70 66 73 5f 66 75 73 ic int appfs_fus
9eb0: 65 5f 63 68 6d 6f 64 28 63 6f 6e 73 74 20 63 68 e_chmod(const ch
9ec0: 61 72 20 2a 70 61 74 68 2c 20 6d 6f 64 65 5f 74 ar *path, mode_t
9ed0: 20 6d 6f 64 65 29 20 7b 0a 09 54 63 6c 5f 49 6e mode) {..Tcl_In
9ee0: 74 65 72 70 20 2a 69 6e 74 65 72 70 3b 0a 09 63 terp *interp;..c
9ef0: 6f 6e 73 74 20 63 68 61 72 20 2a 72 65 61 6c 5f onst char *real_
9f00: 70 61 74 68 3b 0a 09 69 6e 74 20 74 63 6c 5f 72 path;..int tcl_r
9f10: 65 74 2c 20 63 68 6d 6f 64 5f 72 65 74 3b 0a 0a et, chmod_ret;..
9f20: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 45 6e .APPFS_DEBUG("En
9f30: 74 65 72 20 28 70 61 74 68 20 3d 20 25 73 2c 20 ter (path = %s,
9f40: 2e 2e 2e 29 22 2c 20 70 61 74 68 29 3b 0a 0a 09 ...)", path);...
9f50: 61 70 70 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 appfs_get_path_i
9f60: 6e 66 6f 5f 63 61 63 68 65 5f 72 6d 28 70 61 74 nfo_cache_rm(pat
9f70: 68 2c 20 61 70 70 66 73 5f 67 65 74 5f 66 73 75 h, appfs_get_fsu
9f80: 69 64 28 29 29 3b 0a 0a 09 69 6e 74 65 72 70 20 id());...interp
9f90: 3d 20 61 70 70 66 73 5f 54 63 6c 49 6e 74 65 72 = appfs_TclInter
9fa0: 70 28 29 3b 0a 09 69 66 20 28 69 6e 74 65 72 70 p();..if (interp
9fb0: 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 72 65 == NULL) {...re
9fc0: 74 75 72 6e 28 2d 45 49 4f 29 3b 0a 09 7d 0a 0a turn(-EIO);..}..
9fd0: 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 .appfs_call_libt
9fe0: 63 6c 28 54 63 6c 5f 50 72 65 73 65 72 76 65 28 cl(Tcl_Preserve(
9ff0: 69 6e 74 65 72 70 29 3b 29 0a 0a 09 74 63 6c 5f interp);)...tcl_
a000: 72 65 74 20 3d 20 61 70 70 66 73 5f 54 63 6c 5f ret = appfs_Tcl_
a010: 45 76 61 6c 28 69 6e 74 65 72 70 2c 20 33 2c 20 Eval(interp, 3,
a020: 22 3a 3a 61 70 70 66 73 3a 3a 6f 70 65 6e 70 61 "::appfs::openpa
a030: 74 68 22 2c 20 70 61 74 68 2c 20 22 77 72 69 74 th", path, "writ
a040: 65 22 29 3b 0a 09 69 66 20 28 74 63 6c 5f 72 65 e");..if (tcl_re
a050: 74 20 21 3d 20 54 43 4c 5f 4f 4b 29 20 7b 0a 09 t != TCL_OK) {..
a060: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 3a 3a .APPFS_DEBUG("::
a070: 61 70 70 66 73 3a 3a 6f 70 65 6e 70 61 74 68 28 appfs::openpath(
a080: 25 73 2c 20 25 73 29 20 66 61 69 6c 65 64 2e 22 %s, %s) failed."
a090: 2c 20 70 61 74 68 2c 20 22 77 72 69 74 65 22 29 , path, "write")
a0a0: 3b 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c ;...appfs_call_l
a0b0: 69 62 74 63 6c 28 0a 09 09 09 41 50 50 46 53 5f ibtcl(....APPFS_
a0c0: 44 45 42 55 47 28 22 54 63 6c 20 45 72 72 6f 72 DEBUG("Tcl Error
a0d0: 20 69 73 3a 20 25 73 22 2c 20 54 63 6c 5f 47 65 is: %s", Tcl_Ge
a0e0: 74 53 74 72 69 6e 67 52 65 73 75 6c 74 28 69 6e tStringResult(in
a0f0: 74 65 72 70 29 29 3b 0a 09 09 29 0a 0a 09 09 61 terp));...)....a
a100: 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c ppfs_call_libtcl
a110: 28 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e 74 (Tcl_Release(int
a120: 65 72 70 29 3b 29 0a 0a 09 09 72 65 74 75 72 6e erp);)....return
a130: 28 2d 45 49 4f 29 3b 0a 09 7d 0a 0a 09 61 70 70 (-EIO);..}...app
a140: 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 6c 28 0a fs_call_libtcl(.
a150: 09 09 72 65 61 6c 5f 70 61 74 68 20 3d 20 54 63 ..real_path = Tc
a160: 6c 5f 47 65 74 53 74 72 69 6e 67 52 65 73 75 6c l_GetStringResul
a170: 74 28 69 6e 74 65 72 70 29 3b 0a 09 29 0a 0a 09 t(interp);..)...
a180: 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 63 appfs_call_libtc
a190: 6c 28 54 63 6c 5f 52 65 6c 65 61 73 65 28 69 6e l(Tcl_Release(in
a1a0: 74 65 72 70 29 3b 29 0a 0a 09 69 66 20 28 72 65 terp);)...if (re
a1b0: 61 6c 5f 70 61 74 68 20 3d 3d 20 4e 55 4c 4c 29 al_path == NULL)
a1c0: 20 7b 0a 09 09 72 65 74 75 72 6e 28 2d 45 49 4f {...return(-EIO
a1d0: 29 3b 0a 09 7d 0a 0a 09 61 70 70 66 73 5f 73 69 );..}...appfs_si
a1e0: 6d 75 6c 61 74 65 5f 75 73 65 72 5f 66 73 5f 65 mulate_user_fs_e
a1f0: 6e 74 65 72 28 29 3b 0a 0a 09 63 68 6d 6f 64 5f nter();...chmod_
a200: 72 65 74 20 3d 20 63 68 6d 6f 64 28 72 65 61 6c ret = chmod(real
a210: 5f 70 61 74 68 2c 20 6d 6f 64 65 29 3b 0a 0a 09 _path, mode);...
a220: 61 70 70 66 73 5f 73 69 6d 75 6c 61 74 65 5f 75 appfs_simulate_u
a230: 73 65 72 5f 66 73 5f 6c 65 61 76 65 28 29 3b 0a ser_fs_leave();.
a240: 0a 09 72 65 74 75 72 6e 28 63 68 6d 6f 64 5f 72 ..return(chmod_r
a250: 65 74 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 69 et);.}..static i
a260: 6e 74 20 61 70 70 66 73 5f 66 75 73 65 5f 73 79 nt appfs_fuse_sy
a270: 6d 6c 69 6e 6b 28 63 6f 6e 73 74 20 63 68 61 72 mlink(const char
a280: 20 2a 6f 6c 64 70 61 74 68 2c 20 63 6f 6e 73 74 *oldpath, const
a290: 20 63 68 61 72 20 2a 6e 65 77 70 61 74 68 29 20 char *newpath)
a2a0: 7b 0a 09 63 68 61 72 20 2a 72 65 61 6c 5f 70 61 {..char *real_pa
a2b0: 74 68 3b 0a 09 69 6e 74 20 73 79 6d 6c 69 6e 6b th;..int symlink
a2c0: 5f 72 65 74 3b 0a 0a 09 41 50 50 46 53 5f 44 45 _ret;...APPFS_DE
a2d0: 42 55 47 28 22 45 6e 74 65 72 20 28 70 61 74 68 BUG("Enter (path
a2e0: 20 3d 20 25 73 2c 20 25 73 29 22 2c 20 6f 6c 64 = %s, %s)", old
a2f0: 70 61 74 68 2c 20 6e 65 77 70 61 74 68 29 3b 0a path, newpath);.
a300: 0a 09 72 65 61 6c 5f 70 61 74 68 20 3d 20 61 70 ..real_path = ap
a310: 70 66 73 5f 70 72 65 70 61 72 65 5f 74 6f 5f 63 pfs_prepare_to_c
a320: 72 65 61 74 65 28 6e 65 77 70 61 74 68 29 3b 0a reate(newpath);.
a330: 09 69 66 20 28 72 65 61 6c 5f 70 61 74 68 20 3d .if (real_path =
a340: 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 72 65 74 75 = NULL) {...retu
a350: 72 6e 28 2d 45 49 4f 29 3b 0a 09 7d 0a 0a 09 61 rn(-EIO);..}...a
a360: 70 70 66 73 5f 73 69 6d 75 6c 61 74 65 5f 75 73 ppfs_simulate_us
a370: 65 72 5f 66 73 5f 65 6e 74 65 72 28 29 3b 0a 0a er_fs_enter();..
a380: 09 73 79 6d 6c 69 6e 6b 5f 72 65 74 20 3d 20 73 .symlink_ret = s
a390: 79 6d 6c 69 6e 6b 28 6f 6c 64 70 61 74 68 2c 20 ymlink(oldpath,
a3a0: 72 65 61 6c 5f 70 61 74 68 29 3b 0a 0a 09 61 70 real_path);...ap
a3b0: 70 66 73 5f 73 69 6d 75 6c 61 74 65 5f 75 73 65 pfs_simulate_use
a3c0: 72 5f 66 73 5f 6c 65 61 76 65 28 29 3b 0a 0a 09 r_fs_leave();...
a3d0: 66 72 65 65 28 72 65 61 6c 5f 70 61 74 68 29 3b free(real_path);
a3e0: 0a 0a 09 69 66 20 28 73 79 6d 6c 69 6e 6b 5f 72 ...if (symlink_r
a3f0: 65 74 20 21 3d 20 30 29 20 7b 0a 09 09 72 65 74 et != 0) {...ret
a400: 75 72 6e 28 65 72 72 6e 6f 20 2a 20 2d 31 29 3b urn(errno * -1);
a410: 0a 09 7d 0a 0a 09 72 65 74 75 72 6e 28 30 29 3b ..}...return(0);
a420: 0a 7d 0a 0a 2f 2a 0a 20 2a 20 53 51 4c 69 74 65 .}../*. * SQLite
a430: 33 20 6d 6f 64 65 3a 20 45 78 65 63 75 74 65 20 3 mode: Execute
a440: 72 61 77 20 53 51 4c 20 61 6e 64 20 72 65 74 75 raw SQL and retu
a450: 72 6e 20 73 75 63 63 65 73 73 20 6f 72 20 66 61 rn success or fa
a460: 69 6c 75 72 65 0a 20 2a 2f 0a 73 74 61 74 69 63 ilure. */.static
a470: 20 69 6e 74 20 61 70 70 66 73 5f 73 71 6c 69 74 int appfs_sqlit
a480: 65 33 28 63 6f 6e 73 74 20 63 68 61 72 20 2a 73 e3(const char *s
a490: 71 6c 29 20 7b 0a 09 54 63 6c 5f 49 6e 74 65 72 ql) {..Tcl_Inter
a4a0: 70 20 2a 69 6e 74 65 72 70 3b 0a 09 63 6f 6e 73 p *interp;..cons
a4b0: 74 20 63 68 61 72 20 2a 73 71 6c 5f 72 65 74 3b t char *sql_ret;
a4c0: 0a 09 69 6e 74 20 74 63 6c 5f 72 65 74 3b 0a 0a ..int tcl_ret;..
a4d0: 09 69 6e 74 65 72 70 20 3d 20 61 70 70 66 73 5f .interp = appfs_
a4e0: 63 72 65 61 74 65 5f 54 63 6c 49 6e 74 65 72 70 create_TclInterp
a4f0: 28 4e 55 4c 4c 29 3b 0a 09 69 66 20 28 69 6e 74 (NULL);..if (int
a500: 65 72 70 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 erp == NULL) {..
a510: 09 66 70 72 69 6e 74 66 28 73 74 64 65 72 72 2c .fprintf(stderr,
a520: 20 22 55 6e 61 62 6c 65 20 74 6f 20 63 72 65 61 "Unable to crea
a530: 74 65 20 61 20 54 63 6c 20 69 6e 74 65 72 70 72 te a Tcl interpr
a540: 65 74 65 72 2e 20 20 41 62 6f 72 74 69 6e 67 2e eter. Aborting.
a550: 5c 6e 22 29 3b 0a 0a 09 09 72 65 74 75 72 6e 28 \n");....return(
a560: 31 29 3b 0a 09 7d 0a 0a 09 74 63 6c 5f 72 65 74 1);..}...tcl_ret
a570: 20 3d 20 61 70 70 66 73 5f 54 63 6c 5f 45 76 61 = appfs_Tcl_Eva
a580: 6c 28 69 6e 74 65 72 70 2c 20 35 2c 20 22 3a 3a l(interp, 5, "::
a590: 61 70 70 66 73 3a 3a 64 62 22 2c 20 22 65 76 61 appfs::db", "eva
a5a0: 6c 22 2c 20 73 71 6c 2c 20 22 72 6f 77 22 2c 20 l", sql, "row",
a5b0: 22 75 6e 73 65 74 20 2d 6e 6f 63 6f 6d 70 6c 61 "unset -nocompla
a5c0: 69 6e 20 72 6f 77 28 2a 29 3b 20 70 61 72 72 61 in row(*); parra
a5d0: 79 20 72 6f 77 3b 20 70 75 74 73 20 5c 22 2d 2d y row; puts \"--
a5e0: 2d 2d 5c 22 22 29 3b 0a 09 73 71 6c 5f 72 65 74 --\"");..sql_ret
a5f0: 20 3d 20 54 63 6c 5f 47 65 74 53 74 72 69 6e 67 = Tcl_GetString
a600: 52 65 73 75 6c 74 28 69 6e 74 65 72 70 29 3b 0a Result(interp);.
a610: 0a 09 69 66 20 28 74 63 6c 5f 72 65 74 20 21 3d ..if (tcl_ret !=
a620: 20 54 43 4c 5f 4f 4b 29 20 7b 0a 09 09 66 70 72 TCL_OK) {...fpr
a630: 69 6e 74 66 28 73 74 64 65 72 72 2c 20 22 5b 65 intf(stderr, "[e
a640: 72 72 6f 72 5d 20 25 73 5c 6e 22 2c 20 73 71 6c rror] %s\n", sql
a650: 5f 72 65 74 29 3b 0a 0a 09 09 72 65 74 75 72 6e _ret);....return
a660: 28 31 29 3b 0a 09 7d 0a 0a 09 69 66 20 28 73 71 (1);..}...if (sq
a670: 6c 5f 72 65 74 20 26 26 20 73 71 6c 5f 72 65 74 l_ret && sql_ret
a680: 5b 30 5d 20 21 3d 20 27 5c 30 27 29 20 7b 0a 09 [0] != '\0') {..
a690: 09 70 72 69 6e 74 66 28 22 25 73 5c 6e 22 2c 20 .printf("%s\n",
a6a0: 73 71 6c 5f 72 65 74 29 3b 0a 09 7d 0a 0a 09 72 sql_ret);..}...r
a6b0: 65 74 75 72 6e 28 30 29 3b 0a 7d 0a 0a 2f 2a 0a eturn(0);.}../*.
a6c0: 20 2a 20 54 63 6c 20 6d 6f 64 65 3a 20 45 78 65 * Tcl mode: Exe
a6d0: 63 75 74 65 20 72 61 77 20 54 63 6c 20 61 6e 64 cute raw Tcl and
a6e0: 20 72 65 74 75 72 6e 20 73 75 63 63 65 73 73 20 return success
a6f0: 6f 72 20 66 61 69 6c 75 72 65 0a 20 2a 2f 0a 73 or failure. */.s
a700: 74 61 74 69 63 20 69 6e 74 20 61 70 70 66 73 5f tatic int appfs_
a710: 74 63 6c 28 63 6f 6e 73 74 20 63 68 61 72 20 2a tcl(const char *
a720: 74 63 6c 29 20 7b 0a 09 54 63 6c 5f 49 6e 74 65 tcl) {..Tcl_Inte
a730: 72 70 20 2a 69 6e 74 65 72 70 3b 0a 09 63 6f 6e rp *interp;..con
a740: 73 74 20 63 68 61 72 20 2a 74 63 6c 5f 72 65 73 st char *tcl_res
a750: 75 6c 74 3b 0a 09 69 6e 74 20 74 63 6c 5f 72 65 ult;..int tcl_re
a760: 74 3b 0a 0a 09 69 6e 74 65 72 70 20 3d 20 61 70 t;...interp = ap
a770: 70 66 73 5f 63 72 65 61 74 65 5f 54 63 6c 49 6e pfs_create_TclIn
a780: 74 65 72 70 28 4e 55 4c 4c 29 3b 0a 09 69 66 20 terp(NULL);..if
a790: 28 69 6e 74 65 72 70 20 3d 3d 20 4e 55 4c 4c 29 (interp == NULL)
a7a0: 20 7b 0a 09 09 66 70 72 69 6e 74 66 28 73 74 64 {...fprintf(std
a7b0: 65 72 72 2c 20 22 55 6e 61 62 6c 65 20 74 6f 20 err, "Unable to
a7c0: 63 72 65 61 74 65 20 61 20 54 63 6c 20 69 6e 74 create a Tcl int
a7d0: 65 72 70 72 65 74 65 72 2e 20 20 41 62 6f 72 74 erpreter. Abort
a7e0: 69 6e 67 2e 5c 6e 22 29 3b 0a 0a 09 09 72 65 74 ing.\n");....ret
a7f0: 75 72 6e 28 31 29 3b 0a 09 7d 0a 0a 09 74 63 6c urn(1);..}...tcl
a800: 5f 72 65 74 20 3d 20 54 63 6c 5f 45 76 61 6c 28 _ret = Tcl_Eval(
a810: 69 6e 74 65 72 70 2c 20 74 63 6c 29 3b 0a 09 74 interp, tcl);..t
a820: 63 6c 5f 72 65 73 75 6c 74 20 3d 20 54 63 6c 5f cl_result = Tcl_
a830: 47 65 74 53 74 72 69 6e 67 52 65 73 75 6c 74 28 GetStringResult(
a840: 69 6e 74 65 72 70 29 3b 0a 0a 09 69 66 20 28 74 interp);...if (t
a850: 63 6c 5f 72 65 74 20 21 3d 20 54 43 4c 5f 4f 4b cl_ret != TCL_OK
a860: 29 20 7b 0a 09 09 66 70 72 69 6e 74 66 28 73 74 ) {...fprintf(st
a870: 64 65 72 72 2c 20 22 5b 65 72 72 6f 72 5d 20 25 derr, "[error] %
a880: 73 5c 6e 22 2c 20 54 63 6c 5f 47 65 74 56 61 72 s\n", Tcl_GetVar
a890: 28 69 6e 74 65 72 70 2c 20 22 65 72 72 6f 72 49 (interp, "errorI
a8a0: 6e 66 6f 22 2c 20 54 43 4c 5f 47 4c 4f 42 41 4c nfo", TCL_GLOBAL
a8b0: 5f 4f 4e 4c 59 29 29 3b 0a 0a 09 09 72 65 74 75 _ONLY));....retu
a8c0: 72 6e 28 31 29 3b 0a 09 7d 0a 0a 09 69 66 20 28 rn(1);..}...if (
a8d0: 74 63 6c 5f 72 65 73 75 6c 74 20 26 26 20 74 63 tcl_result && tc
a8e0: 6c 5f 72 65 73 75 6c 74 5b 30 5d 20 21 3d 20 27 l_result[0] != '
a8f0: 5c 30 27 29 20 7b 0a 09 09 70 72 69 6e 74 66 28 \0') {...printf(
a900: 22 25 73 5c 6e 22 2c 20 74 63 6c 5f 72 65 73 75 "%s\n", tcl_resu
a910: 6c 74 29 3b 0a 09 7d 0a 0a 09 72 65 74 75 72 6e lt);..}...return
a920: 28 30 29 3b 0a 7d 0a 0a 2f 2a 0a 20 2a 20 41 70 (0);.}../*. * Ap
a930: 70 46 53 64 20 50 61 63 6b 61 67 65 20 66 6f 72 pFSd Package for
a940: 20 54 63 6c 3a 0a 20 2a 20 20 20 20 20 20 20 20 Tcl:. *
a950: 20 42 72 69 64 67 65 20 66 6f 72 20 49 2f 4f 20 Bridge for I/O
a960: 6f 70 65 72 61 74 69 6f 6e 73 20 74 6f 20 72 65 operations to re
a970: 71 75 65 73 74 20 69 6e 66 6f 72 6d 61 74 69 6f quest informatio
a980: 6e 20 61 62 6f 75 74 20 74 68 65 20 63 75 72 72 n about the curr
a990: 65 6e 74 0a 20 2a 20 20 20 20 20 20 20 20 20 74 ent. * t
a9a0: 72 61 6e 73 61 63 74 69 6f 6e 0a 20 2a 2f 0a 2f ransaction. */./
a9b0: 2a 0a 20 2a 20 54 63 6c 20 69 6e 74 65 72 66 61 *. * Tcl interfa
a9c0: 63 65 20 74 6f 20 67 65 74 20 74 68 65 20 68 6f ce to get the ho
a9d0: 6d 65 20 64 69 72 65 63 74 6f 72 79 20 66 6f 72 me directory for
a9e0: 20 74 68 65 20 75 73 65 72 20 6d 61 6b 69 6e 67 the user making
a9f0: 20 74 68 65 20 22 63 75 72 72 65 6e 74 22 0a 20 the "current".
aa00: 2a 20 46 55 53 45 20 49 2f 4f 20 72 65 71 75 65 * FUSE I/O reque
aa10: 73 74 0a 20 2a 2f 0a 73 74 61 74 69 63 20 69 6e st. */.static in
aa20: 74 20 74 63 6c 5f 61 70 70 66 73 5f 67 65 74 5f t tcl_appfs_get_
aa30: 68 6f 6d 65 64 69 72 28 43 6c 69 65 6e 74 44 61 homedir(ClientDa
aa40: 74 61 20 63 64 2c 20 54 63 6c 5f 49 6e 74 65 72 ta cd, Tcl_Inter
aa50: 70 20 2a 69 6e 74 65 72 70 2c 20 69 6e 74 20 6f p *interp, int o
aa60: 62 6a 63 2c 20 54 63 6c 5f 4f 62 6a 20 2a 43 4f bjc, Tcl_Obj *CO
aa70: 4e 53 54 20 6f 62 6a 76 5b 5d 29 20 7b 0a 09 63 NST objv[]) {..c
aa80: 68 61 72 20 2a 68 6f 6d 65 64 69 72 3b 0a 09 54 har *homedir;..T
aa90: 63 6c 5f 4f 62 6a 20 2a 68 6f 6d 65 64 69 72 5f cl_Obj *homedir_
aaa0: 6f 62 6a 3b 0a 09 75 69 64 5f 74 20 66 73 75 69 obj;..uid_t fsui
aab0: 64 3b 0a 09 73 74 61 74 69 63 20 5f 5f 74 68 72 d;..static __thr
aac0: 65 61 64 20 54 63 6c 5f 4f 62 6a 20 2a 6c 61 73 ead Tcl_Obj *las
aad0: 74 5f 68 6f 6d 65 64 69 72 5f 6f 62 6a 20 3d 20 t_homedir_obj =
aae0: 4e 55 4c 4c 3b 0a 09 73 74 61 74 69 63 20 5f 5f NULL;..static __
aaf0: 74 68 72 65 61 64 20 75 69 64 5f 74 20 6c 61 73 thread uid_t las
ab00: 74 5f 66 73 75 69 64 20 3d 20 2d 31 3b 0a 0a 20 t_fsuid = -1;..
ab10: 20 20 20 20 20 20 20 69 66 20 28 6f 62 6a 63 20 if (objc
ab20: 21 3d 20 31 29 20 7b 0a 20 20 20 20 20 20 20 20 != 1) {.
ab30: 20 20 20 20 20 20 20 20 54 63 6c 5f 57 72 6f 6e Tcl_Wron
ab40: 67 4e 75 6d 41 72 67 73 28 69 6e 74 65 72 70 2c gNumArgs(interp,
ab50: 20 31 2c 20 6f 62 6a 76 2c 20 4e 55 4c 4c 29 3b 1, objv, NULL);
ab60: 0a 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 .
ab70: 20 72 65 74 75 72 6e 28 54 43 4c 5f 45 52 52 4f return(TCL_ERRO
ab80: 52 29 3b 0a 20 20 20 20 20 20 20 20 7d 0a 0a 09 R);. }...
ab90: 66 73 75 69 64 20 3d 20 61 70 70 66 73 5f 67 65 fsuid = appfs_ge
aba0: 74 5f 66 73 75 69 64 28 29 3b 0a 0a 09 69 66 20 t_fsuid();...if
abb0: 28 66 73 75 69 64 20 3d 3d 20 6c 61 73 74 5f 66 (fsuid == last_f
abc0: 73 75 69 64 20 26 26 20 6c 61 73 74 5f 68 6f 6d suid && last_hom
abd0: 65 64 69 72 5f 6f 62 6a 20 21 3d 20 4e 55 4c 4c edir_obj != NULL
abe0: 29 20 7b 0a 09 09 68 6f 6d 65 64 69 72 5f 6f 62 ) {...homedir_ob
abf0: 6a 20 3d 20 6c 61 73 74 5f 68 6f 6d 65 64 69 72 j = last_homedir
ac00: 5f 6f 62 6a 3b 0a 0a 09 09 54 63 6c 5f 49 6e 63 _obj;....Tcl_Inc
ac10: 72 52 65 66 43 6f 75 6e 74 28 68 6f 6d 65 64 69 rRefCount(homedi
ac20: 72 5f 6f 62 6a 29 3b 0a 09 7d 20 65 6c 73 65 20 r_obj);..} else
ac30: 7b 0a 09 09 68 6f 6d 65 64 69 72 20 3d 20 61 70 {...homedir = ap
ac40: 70 66 73 5f 67 65 74 5f 68 6f 6d 65 64 69 72 28 pfs_get_homedir(
ac50: 61 70 70 66 73 5f 67 65 74 5f 66 73 75 69 64 28 appfs_get_fsuid(
ac60: 29 29 3b 0a 0a 09 09 69 66 20 28 68 6f 6d 65 64 ));....if (homed
ac70: 69 72 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 09 ir == NULL) {...
ac80: 09 72 65 74 75 72 6e 28 54 43 4c 5f 45 52 52 4f .return(TCL_ERRO
ac90: 52 29 3b 0a 09 09 7d 0a 0a 09 09 68 6f 6d 65 64 R);...}....homed
aca0: 69 72 5f 6f 62 6a 20 3d 20 54 63 6c 5f 4e 65 77 ir_obj = Tcl_New
acb0: 53 74 72 69 6e 67 4f 62 6a 28 68 6f 6d 65 64 69 StringObj(homedi
acc0: 72 2c 20 2d 31 29 3b 0a 0a 09 09 66 72 65 65 28 r, -1);....free(
acd0: 68 6f 6d 65 64 69 72 29 3b 0a 0a 09 09 54 63 6c homedir);....Tcl
ace0: 5f 49 6e 63 72 52 65 66 43 6f 75 6e 74 28 68 6f _IncrRefCount(ho
acf0: 6d 65 64 69 72 5f 6f 62 6a 29 3b 0a 0a 09 09 69 medir_obj);....i
ad00: 66 20 28 6c 61 73 74 5f 68 6f 6d 65 64 69 72 5f f (last_homedir_
ad10: 6f 62 6a 20 21 3d 20 4e 55 4c 4c 29 20 7b 0a 09 obj != NULL) {..
ad20: 09 09 54 63 6c 5f 44 65 63 72 52 65 66 43 6f 75 ..Tcl_DecrRefCou
ad30: 6e 74 28 6c 61 73 74 5f 68 6f 6d 65 64 69 72 5f nt(last_homedir_
ad40: 6f 62 6a 29 3b 0a 09 09 7d 0a 0a 09 09 6c 61 73 obj);...}....las
ad50: 74 5f 68 6f 6d 65 64 69 72 5f 6f 62 6a 20 3d 20 t_homedir_obj =
ad60: 68 6f 6d 65 64 69 72 5f 6f 62 6a 3b 0a 09 09 6c homedir_obj;...l
ad70: 61 73 74 5f 66 73 75 69 64 20 3d 20 66 73 75 69 ast_fsuid = fsui
ad80: 64 3b 0a 0a 09 09 54 63 6c 5f 49 6e 63 72 52 65 d;....Tcl_IncrRe
ad90: 66 43 6f 75 6e 74 28 68 6f 6d 65 64 69 72 5f 6f fCount(homedir_o
ada0: 62 6a 29 3b 0a 09 7d 0a 0a 20 20 20 20 20 20 20 bj);..}..
adb0: 09 54 63 6c 5f 53 65 74 4f 62 6a 52 65 73 75 6c .Tcl_SetObjResul
adc0: 74 28 69 6e 74 65 72 70 2c 20 68 6f 6d 65 64 69 t(interp, homedi
add0: 72 5f 6f 62 6a 29 3b 0a 0a 09 54 63 6c 5f 44 65 r_obj);...Tcl_De
ade0: 63 72 52 65 66 43 6f 75 6e 74 28 68 6f 6d 65 64 crRefCount(homed
adf0: 69 72 5f 6f 62 6a 29 3b 0a 0a 20 20 20 20 20 20 ir_obj);..
ae00: 20 20 72 65 74 75 72 6e 28 54 43 4c 5f 4f 4b 29 return(TCL_OK)
ae10: 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 69 6e 74 20 ;.}..static int
ae20: 74 63 6c 5f 61 70 70 66 73 5f 73 69 6d 75 6c 61 tcl_appfs_simula
ae30: 74 65 5f 75 73 65 72 5f 66 73 5f 65 6e 74 65 72 te_user_fs_enter
ae40: 28 43 6c 69 65 6e 74 44 61 74 61 20 63 64 2c 20 (ClientData cd,
ae50: 54 63 6c 5f 49 6e 74 65 72 70 20 2a 69 6e 74 65 Tcl_Interp *inte
ae60: 72 70 2c 20 69 6e 74 20 6f 62 6a 63 2c 20 54 63 rp, int objc, Tc
ae70: 6c 5f 4f 62 6a 20 2a 43 4f 4e 53 54 20 6f 62 6a l_Obj *CONST obj
ae80: 76 5b 5d 29 20 7b 0a 09 61 70 70 66 73 5f 73 69 v[]) {..appfs_si
ae90: 6d 75 6c 61 74 65 5f 75 73 65 72 5f 66 73 5f 65 mulate_user_fs_e
aea0: 6e 74 65 72 28 29 3b 0a 0a 09 72 65 74 75 72 6e nter();...return
aeb0: 28 54 43 4c 5f 4f 4b 29 3b 0a 7d 0a 0a 73 74 61 (TCL_OK);.}..sta
aec0: 74 69 63 20 69 6e 74 20 74 63 6c 5f 61 70 70 66 tic int tcl_appf
aed0: 73 5f 73 69 6d 75 6c 61 74 65 5f 75 73 65 72 5f s_simulate_user_
aee0: 66 73 5f 6c 65 61 76 65 28 43 6c 69 65 6e 74 44 fs_leave(ClientD
aef0: 61 74 61 20 63 64 2c 20 54 63 6c 5f 49 6e 74 65 ata cd, Tcl_Inte
af00: 72 70 20 2a 69 6e 74 65 72 70 2c 20 69 6e 74 20 rp *interp, int
af10: 6f 62 6a 63 2c 20 54 63 6c 5f 4f 62 6a 20 2a 43 objc, Tcl_Obj *C
af20: 4f 4e 53 54 20 6f 62 6a 76 5b 5d 29 20 7b 0a 09 ONST objv[]) {..
af30: 61 70 70 66 73 5f 73 69 6d 75 6c 61 74 65 5f 75 appfs_simulate_u
af40: 73 65 72 5f 66 73 5f 6c 65 61 76 65 28 29 3b 0a ser_fs_leave();.
af50: 0a 09 72 65 74 75 72 6e 28 54 43 4c 5f 4f 4b 29 ..return(TCL_OK)
af60: 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 69 6e 74 20 ;.}..static int
af70: 74 63 6c 5f 61 70 70 66 73 5f 67 65 74 5f 66 73 tcl_appfs_get_fs
af80: 75 69 64 28 43 6c 69 65 6e 74 44 61 74 61 20 63 uid(ClientData c
af90: 64 2c 20 54 63 6c 5f 49 6e 74 65 72 70 20 2a 69 d, Tcl_Interp *i
afa0: 6e 74 65 72 70 2c 20 69 6e 74 20 6f 62 6a 63 2c nterp, int objc,
afb0: 20 54 63 6c 5f 4f 62 6a 20 2a 43 4f 4e 53 54 20 Tcl_Obj *CONST
afc0: 6f 62 6a 76 5b 5d 29 20 7b 0a 09 75 69 64 5f 74 objv[]) {..uid_t
afd0: 20 66 73 75 69 64 3b 0a 0a 09 66 73 75 69 64 20 fsuid;...fsuid
afe0: 3d 20 61 70 70 66 73 5f 67 65 74 5f 66 73 75 69 = appfs_get_fsui
aff0: 64 28 29 3b 0a 0a 20 20 20 20 20 20 20 09 54 63 d();.. .Tc
b000: 6c 5f 53 65 74 4f 62 6a 52 65 73 75 6c 74 28 69 l_SetObjResult(i
b010: 6e 74 65 72 70 2c 20 54 63 6c 5f 4e 65 77 57 69 nterp, Tcl_NewWi
b020: 64 65 49 6e 74 4f 62 6a 28 66 73 75 69 64 29 29 deIntObj(fsuid))
b030: 3b 0a 0a 09 72 65 74 75 72 6e 28 54 43 4c 5f 4f ;...return(TCL_O
b040: 4b 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 69 6e K);.}..static in
b050: 74 20 74 63 6c 5f 61 70 70 66 73 5f 67 65 74 5f t tcl_appfs_get_
b060: 66 73 67 69 64 28 43 6c 69 65 6e 74 44 61 74 61 fsgid(ClientData
b070: 20 63 64 2c 20 54 63 6c 5f 49 6e 74 65 72 70 20 cd, Tcl_Interp
b080: 2a 69 6e 74 65 72 70 2c 20 69 6e 74 20 6f 62 6a *interp, int obj
b090: 63 2c 20 54 63 6c 5f 4f 62 6a 20 2a 43 4f 4e 53 c, Tcl_Obj *CONS
b0a0: 54 20 6f 62 6a 76 5b 5d 29 20 7b 0a 09 67 69 64 T objv[]) {..gid
b0b0: 5f 74 20 66 73 67 69 64 3b 0a 0a 09 66 73 67 69 _t fsgid;...fsgi
b0c0: 64 20 3d 20 61 70 70 66 73 5f 67 65 74 5f 66 73 d = appfs_get_fs
b0d0: 67 69 64 28 29 3b 0a 0a 20 20 20 20 20 20 20 09 gid();.. .
b0e0: 54 63 6c 5f 53 65 74 4f 62 6a 52 65 73 75 6c 74 Tcl_SetObjResult
b0f0: 28 69 6e 74 65 72 70 2c 20 54 63 6c 5f 4e 65 77 (interp, Tcl_New
b100: 57 69 64 65 49 6e 74 4f 62 6a 28 66 73 67 69 64 WideIntObj(fsgid
b110: 29 29 3b 0a 0a 09 72 65 74 75 72 6e 28 54 43 4c ));...return(TCL
b120: 5f 4f 4b 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 _OK);.}..static
b130: 69 6e 74 20 74 63 6c 5f 61 70 70 66 73 5f 67 65 int tcl_appfs_ge
b140: 74 5f 70 61 74 68 5f 69 6e 66 6f 5f 63 61 63 68 t_path_info_cach
b150: 65 5f 66 6c 75 73 68 28 43 6c 69 65 6e 74 44 61 e_flush(ClientDa
b160: 74 61 20 63 64 2c 20 54 63 6c 5f 49 6e 74 65 72 ta cd, Tcl_Inter
b170: 70 20 2a 69 6e 74 65 72 70 2c 20 69 6e 74 20 6f p *interp, int o
b180: 62 6a 63 2c 20 54 63 6c 5f 4f 62 6a 20 2a 43 4f bjc, Tcl_Obj *CO
b190: 4e 53 54 20 6f 62 6a 76 5b 5d 29 20 7b 0a 09 69 NST objv[]) {..i
b1a0: 6e 74 20 74 63 6c 5f 72 65 74 3b 0a 09 69 6e 74 nt tcl_ret;..int
b1b0: 20 6e 65 77 5f 73 69 7a 65 3b 0a 0a 09 6e 65 77 new_size;...new
b1c0: 5f 73 69 7a 65 20 3d 20 2d 31 3b 0a 0a 09 69 66 _size = -1;...if
b1d0: 20 28 6f 62 6a 63 20 3d 3d 20 32 29 20 7b 0a 09 (objc == 2) {..
b1e0: 09 74 63 6c 5f 72 65 74 20 3d 20 54 63 6c 5f 47 .tcl_ret = Tcl_G
b1f0: 65 74 49 6e 74 46 72 6f 6d 4f 62 6a 28 69 6e 74 etIntFromObj(int
b200: 65 72 70 2c 20 6f 62 6a 76 5b 31 5d 2c 20 26 6e erp, objv[1], &n
b210: 65 77 5f 73 69 7a 65 29 3b 0a 09 09 69 66 20 28 ew_size);...if (
b220: 74 63 6c 5f 72 65 74 20 21 3d 20 54 43 4c 5f 4f tcl_ret != TCL_O
b230: 4b 29 20 7b 0a 09 09 09 72 65 74 75 72 6e 28 74 K) {....return(t
b240: 63 6c 5f 72 65 74 29 3b 0a 09 09 7d 0a 09 7d 20 cl_ret);...}..}
b250: 65 6c 73 65 20 69 66 20 28 6f 62 6a 63 20 3e 20 else if (objc >
b260: 32 20 7c 7c 20 6f 62 6a 63 20 3c 20 31 29 20 7b 2 || objc < 1) {
b270: 0a 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 .
b280: 20 54 63 6c 5f 57 72 6f 6e 67 4e 75 6d 41 72 67 Tcl_WrongNumArg
b290: 73 28 69 6e 74 65 72 70 2c 20 31 2c 20 6f 62 6a s(interp, 1, obj
b2a0: 76 2c 20 22 3f 6e 65 77 5f 63 61 63 68 65 5f 73 v, "?new_cache_s
b2b0: 69 7a 65 3f 22 29 3b 0a 09 09 72 65 74 75 72 6e ize?");...return
b2c0: 28 54 43 4c 5f 45 52 52 4f 52 29 3b 0a 09 7d 0a (TCL_ERROR);..}.
b2d0: 0a 09 61 70 70 66 73 5f 67 65 74 5f 70 61 74 68 ..appfs_get_path
b2e0: 5f 69 6e 66 6f 5f 63 61 63 68 65 5f 66 6c 75 73 _info_cache_flus
b2f0: 68 28 2d 31 2c 20 6e 65 77 5f 73 69 7a 65 29 3b h(-1, new_size);
b300: 0a 0a 09 72 65 74 75 72 6e 28 54 43 4c 5f 4f 4b ...return(TCL_OK
b310: 29 3b 0a 7d 0a 0a 73 74 61 74 69 63 20 69 6e 74 );.}..static int
b320: 20 41 70 70 66 73 64 5f 49 6e 69 74 28 54 63 6c Appfsd_Init(Tcl
b330: 5f 49 6e 74 65 72 70 20 2a 69 6e 74 65 72 70 29 _Interp *interp)
b340: 20 7b 0a 23 69 66 64 65 66 20 55 53 45 5f 54 43 {.#ifdef USE_TC
b350: 4c 5f 53 54 55 42 53 0a 09 69 66 20 28 54 63 6c L_STUBS..if (Tcl
b360: 5f 49 6e 69 74 53 74 75 62 73 28 69 6e 74 65 72 _InitStubs(inter
b370: 70 2c 20 54 43 4c 5f 56 45 52 53 49 4f 4e 2c 20 p, TCL_VERSION,
b380: 30 29 20 3d 3d 20 30 4c 29 20 7b 0a 09 09 72 65 0) == 0L) {...re
b390: 74 75 72 6e 28 54 43 4c 5f 45 52 52 4f 52 29 3b turn(TCL_ERROR);
b3a0: 0a 09 7d 0a 23 65 6e 64 69 66 0a 0a 09 54 63 6c ..}.#endif...Tcl
b3b0: 5f 43 72 65 61 74 65 4f 62 6a 43 6f 6d 6d 61 6e _CreateObjComman
b3c0: 64 28 69 6e 74 65 72 70 2c 20 22 61 70 70 66 73 d(interp, "appfs
b3d0: 64 3a 3a 67 65 74 5f 68 6f 6d 65 64 69 72 22 2c d::get_homedir",
b3e0: 20 74 63 6c 5f 61 70 70 66 73 5f 67 65 74 5f 68 tcl_appfs_get_h
b3f0: 6f 6d 65 64 69 72 2c 20 4e 55 4c 4c 2c 20 4e 55 omedir, NULL, NU
b400: 4c 4c 29 3b 0a 09 54 63 6c 5f 43 72 65 61 74 65 LL);..Tcl_Create
b410: 4f 62 6a 43 6f 6d 6d 61 6e 64 28 69 6e 74 65 72 ObjCommand(inter
b420: 70 2c 20 22 61 70 70 66 73 64 3a 3a 67 65 74 5f p, "appfsd::get_
b430: 66 73 75 69 64 22 2c 20 74 63 6c 5f 61 70 70 66 fsuid", tcl_appf
b440: 73 5f 67 65 74 5f 66 73 75 69 64 2c 20 4e 55 4c s_get_fsuid, NUL
b450: 4c 2c 20 4e 55 4c 4c 29 3b 0a 09 54 63 6c 5f 43 L, NULL);..Tcl_C
b460: 72 65 61 74 65 4f 62 6a 43 6f 6d 6d 61 6e 64 28 reateObjCommand(
b470: 69 6e 74 65 72 70 2c 20 22 61 70 70 66 73 64 3a interp, "appfsd:
b480: 3a 67 65 74 5f 66 73 67 69 64 22 2c 20 74 63 6c :get_fsgid", tcl
b490: 5f 61 70 70 66 73 5f 67 65 74 5f 66 73 67 69 64 _appfs_get_fsgid
b4a0: 2c 20 4e 55 4c 4c 2c 20 4e 55 4c 4c 29 3b 0a 09 , NULL, NULL);..
b4b0: 54 63 6c 5f 43 72 65 61 74 65 4f 62 6a 43 6f 6d Tcl_CreateObjCom
b4c0: 6d 61 6e 64 28 69 6e 74 65 72 70 2c 20 22 61 70 mand(interp, "ap
b4d0: 70 66 73 64 3a 3a 73 69 6d 75 6c 61 74 65 5f 75 pfsd::simulate_u
b4e0: 73 65 72 5f 66 73 5f 65 6e 74 65 72 22 2c 20 74 ser_fs_enter", t
b4f0: 63 6c 5f 61 70 70 66 73 5f 73 69 6d 75 6c 61 74 cl_appfs_simulat
b500: 65 5f 75 73 65 72 5f 66 73 5f 65 6e 74 65 72 2c e_user_fs_enter,
b510: 20 4e 55 4c 4c 2c 20 4e 55 4c 4c 29 3b 0a 09 54 NULL, NULL);..T
b520: 63 6c 5f 43 72 65 61 74 65 4f 62 6a 43 6f 6d 6d cl_CreateObjComm
b530: 61 6e 64 28 69 6e 74 65 72 70 2c 20 22 61 70 70 and(interp, "app
b540: 66 73 64 3a 3a 73 69 6d 75 6c 61 74 65 5f 75 73 fsd::simulate_us
b550: 65 72 5f 66 73 5f 6c 65 61 76 65 22 2c 20 74 63 er_fs_leave", tc
b560: 6c 5f 61 70 70 66 73 5f 73 69 6d 75 6c 61 74 65 l_appfs_simulate
b570: 5f 75 73 65 72 5f 66 73 5f 6c 65 61 76 65 2c 20 _user_fs_leave,
b580: 4e 55 4c 4c 2c 20 4e 55 4c 4c 29 3b 0a 09 54 63 NULL, NULL);..Tc
b590: 6c 5f 43 72 65 61 74 65 4f 62 6a 43 6f 6d 6d 61 l_CreateObjComma
b5a0: 6e 64 28 69 6e 74 65 72 70 2c 20 22 61 70 70 66 nd(interp, "appf
b5b0: 73 64 3a 3a 67 65 74 5f 70 61 74 68 5f 69 6e 66 sd::get_path_inf
b5c0: 6f 5f 63 61 63 68 65 5f 66 6c 75 73 68 22 2c 20 o_cache_flush",
b5d0: 74 63 6c 5f 61 70 70 66 73 5f 67 65 74 5f 70 61 tcl_appfs_get_pa
b5e0: 74 68 5f 69 6e 66 6f 5f 63 61 63 68 65 5f 66 6c th_info_cache_fl
b5f0: 75 73 68 2c 20 4e 55 4c 4c 2c 20 4e 55 4c 4c 29 ush, NULL, NULL)
b600: 3b 0a 0a 09 54 63 6c 5f 50 6b 67 50 72 6f 76 69 ;...Tcl_PkgProvi
b610: 64 65 28 69 6e 74 65 72 70 2c 20 22 61 70 70 66 de(interp, "appf
b620: 73 64 22 2c 20 22 31 2e 30 22 29 3b 0a 0a 09 72 sd", "1.0");...r
b630: 65 74 75 72 6e 28 54 43 4c 5f 4f 4b 29 3b 0a 7d eturn(TCL_OK);.}
b640: 0a 0a 2f 2a 0a 20 2a 20 48 6f 74 2d 72 65 73 74 ../*. * Hot-rest
b650: 61 72 74 20 73 75 70 70 6f 72 74 0a 20 2a 2f 0a art support. */.
b660: 2f 2a 20 49 6e 69 74 69 61 74 65 20 61 20 68 6f /* Initiate a ho
b670: 74 2d 72 65 73 74 61 72 74 20 2a 2f 0a 73 74 61 t-restart */.sta
b680: 74 69 63 20 76 6f 69 64 20 61 70 70 66 73 5f 68 tic void appfs_h
b690: 6f 74 5f 72 65 73 74 61 72 74 28 76 6f 69 64 29 ot_restart(void)
b6a0: 20 7b 0a 09 41 50 50 46 53 5f 44 45 42 55 47 28 {..APPFS_DEBUG(
b6b0: 22 41 73 6b 65 64 20 74 6f 20 69 6e 69 74 69 61 "Asked to initia
b6c0: 74 65 20 68 6f 74 20 72 65 73 74 61 72 74 22 29 te hot restart")
b6d0: 3b 0a 0a 09 61 70 70 66 73 5f 74 63 6c 5f 52 65 ;...appfs_tcl_Re
b6e0: 73 65 74 49 6e 74 65 72 70 73 28 29 3b 0a 0a 09 setInterps();...
b6f0: 61 70 70 66 73 5f 67 65 74 5f 70 61 74 68 5f 69 appfs_get_path_i
b700: 6e 66 6f 5f 63 61 63 68 65 5f 66 6c 75 73 68 28 nfo_cache_flush(
b710: 2d 31 2c 20 2d 31 29 3b 0a 0a 09 72 65 74 75 72 -1, -1);...retur
b720: 6e 3b 0a 7d 0a 0a 2f 2a 0a 20 2a 20 53 69 67 6e n;.}../*. * Sign
b730: 61 6c 20 68 61 6e 64 6c 65 72 0a 20 2a 20 20 20 al handler. *
b740: 20 20 20 20 20 20 53 49 47 48 55 50 20 69 6e 69 SIGHUP ini
b750: 74 69 61 74 65 73 20 61 20 68 6f 74 20 72 65 73 tiates a hot res
b760: 74 61 72 74 0a 20 2a 2f 0a 73 74 61 74 69 63 20 tart. */.static
b770: 76 6f 69 64 20 61 70 70 66 73 5f 73 69 67 6e 61 void appfs_signa
b780: 6c 5f 68 61 6e 64 6c 65 72 28 69 6e 74 20 73 69 l_handler(int si
b790: 67 29 20 7b 0a 09 2f 2a 20 44 6f 20 6e 6f 74 20 g) {../* Do not
b7a0: 68 61 6e 64 6c 65 20 73 69 67 6e 61 6c 73 20 75 handle signals u
b7b0: 6e 74 69 6c 20 46 55 53 45 20 68 61 73 20 62 65 ntil FUSE has be
b7c0: 65 6e 20 73 74 61 72 74 65 64 20 2a 2f 0a 09 69 en started */..i
b7d0: 66 20 28 21 61 70 70 66 73 5f 66 75 73 65 5f 73 f (!appfs_fuse_s
b7e0: 74 61 72 74 65 64 29 20 7b 0a 09 09 72 65 74 75 tarted) {...retu
b7f0: 72 6e 3b 0a 09 7d 0a 0a 09 2f 2a 20 52 65 71 75 rn;..}.../* Requ
b800: 65 73 74 20 74 6f 20 70 65 72 66 6f 72 6d 20 61 est to perform a
b810: 20 22 68 6f 74 22 20 72 65 73 74 61 72 74 20 2a "hot" restart *
b820: 2f 0a 09 69 66 20 28 73 69 67 20 3d 3d 20 53 49 /..if (sig == SI
b830: 47 48 55 50 29 20 7b 0a 09 09 61 70 70 66 73 5f GHUP) {...appfs_
b840: 68 6f 74 5f 72 65 73 74 61 72 74 28 29 3b 0a 09 hot_restart();..
b850: 7d 0a 0a 09 72 65 74 75 72 6e 3b 0a 7d 0a 0a 2f }...return;.}../
b860: 2a 0a 20 2a 20 54 65 72 6d 69 6e 61 74 65 20 61 *. * Terminate a
b870: 20 74 68 72 65 61 64 0a 20 2a 2f 0a 73 74 61 74 thread. */.stat
b880: 69 63 20 76 6f 69 64 20 61 70 70 66 73 5f 74 65 ic void appfs_te
b890: 72 6d 69 6e 61 74 65 5f 69 6e 74 65 72 70 5f 61 rminate_interp_a
b8a0: 6e 64 5f 74 68 72 65 61 64 28 76 6f 69 64 20 2a nd_thread(void *
b8b0: 5f 69 6e 74 65 72 70 29 20 7b 0a 09 54 63 6c 5f _interp) {..Tcl_
b8c0: 49 6e 74 65 72 70 20 2a 69 6e 74 65 72 70 3b 0a Interp *interp;.
b8d0: 0a 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 43 ..APPFS_DEBUG("C
b8e0: 61 6c 6c 65 64 3a 20 5f 69 6e 74 65 72 70 20 3d alled: _interp =
b8f0: 20 25 70 22 2c 20 5f 69 6e 74 65 72 70 29 3b 0a %p", _interp);.
b900: 0a 09 69 66 20 28 5f 69 6e 74 65 72 70 20 21 3d ..if (_interp !=
b910: 20 4e 55 4c 4c 29 20 7b 0a 09 09 69 6e 74 65 72 NULL) {...inter
b920: 70 20 3d 20 5f 69 6e 74 65 72 70 3b 0a 0a 09 09 p = _interp;....
b930: 41 50 50 46 53 5f 44 45 42 55 47 28 22 54 65 72 APPFS_DEBUG("Ter
b940: 6d 69 6e 61 74 69 6e 67 20 69 6e 74 65 72 70 72 minating interpr
b950: 65 74 65 72 20 64 75 65 20 74 6f 20 74 68 72 65 eter due to thre
b960: 61 64 20 74 65 72 6d 69 6e 61 74 69 6f 6e 22 29 ad termination")
b970: 3b 0a 0a 09 09 61 70 70 66 73 5f 63 61 6c 6c 5f ;....appfs_call_
b980: 6c 69 62 74 63 6c 28 0a 09 09 09 54 63 6c 5f 44 libtcl(....Tcl_D
b990: 65 6c 65 74 65 49 6e 74 65 72 70 28 69 6e 74 65 eleteInterp(inte
b9a0: 72 70 29 3b 0a 09 09 29 0a 09 7d 20 65 6c 73 65 rp);...)..} else
b9b0: 20 7b 0a 09 09 41 50 50 46 53 5f 44 45 42 55 47 {...APPFS_DEBUG
b9c0: 28 22 54 65 72 6d 69 6e 61 74 69 6e 67 20 74 68 ("Terminating th
b9d0: 72 65 61 64 20 77 69 74 68 20 6e 6f 20 69 6e 74 read with no int
b9e0: 65 72 70 72 65 74 65 72 22 29 3b 0a 09 7d 0a 0a erpreter");..}..
b9f0: 09 61 70 70 66 73 5f 63 61 6c 6c 5f 6c 69 62 74 .appfs_call_libt
ba00: 63 6c 28 0a 09 09 54 63 6c 5f 46 69 6e 61 6c 69 cl(...Tcl_Finali
ba10: 7a 65 54 68 72 65 61 64 28 29 3b 0a 09 29 0a 0a zeThread();..)..
ba20: 09 72 65 74 75 72 6e 3b 0a 7d 0a 0a 2f 2a 0a 20 .return;.}../*.
ba30: 2a 20 43 6f 6d 6d 61 6e 64 2d 6c 69 6e 65 20 70 * Command-line p
ba40: 61 72 73 69 6e 67 20 74 6f 6f 6c 73 0a 20 2a 2f arsing tools. */
ba50: 0a 73 74 61 74 69 63 20 76 6f 69 64 20 61 70 70 .static void app
ba60: 66 73 5f 70 72 69 6e 74 5f 68 65 6c 70 28 46 49 fs_print_help(FI
ba70: 4c 45 20 2a 63 68 61 6e 6e 65 6c 29 20 7b 0a 09 LE *channel) {..
ba80: 66 70 72 69 6e 74 66 28 63 68 61 6e 6e 65 6c 2c fprintf(channel,
ba90: 20 22 55 73 61 67 65 3a 20 7b 61 70 70 66 73 64 "Usage: {appfsd
baa0: 7c 6d 6f 75 6e 74 2e 61 70 70 66 73 7d 20 5b 2d |mount.appfs} [-
bab0: 6f 20 3c 6f 70 74 69 6f 6e 3e 5d 20 5b 2d 64 66 o <option>] [-df
bac0: 73 68 5d 20 3c 63 61 63 68 65 64 69 72 3e 20 3c sh] <cachedir> <
bad0: 6d 6f 75 6e 74 70 6f 69 6e 74 3e 5c 6e 22 29 3b mountpoint>\n");
bae0: 0a 09 66 70 72 69 6e 74 66 28 63 68 61 6e 6e 65 ..fprintf(channe
baf0: 6c 2c 20 22 5c 6e 22 29 3b 0a 09 66 70 72 69 6e l, "\n");..fprin
bb00: 74 66 28 63 68 61 6e 6e 65 6c 2c 20 22 4f 70 74 tf(channel, "Opt
bb10: 69 6f 6e 73 3a 5c 6e 22 29 3b 0a 09 66 70 72 69 ions:\n");..fpri
bb20: 6e 74 66 28 63 68 61 6e 6e 65 6c 2c 20 22 20 20 ntf(channel, "
bb30: 2d 64 20 20 20 20 20 20 20 20 20 20 20 20 20 20 -d
bb40: 45 6e 61 62 6c 65 20 46 55 53 45 20 64 65 62 75 Enable FUSE debu
bb50: 67 20 6d 6f 64 65 2e 5c 6e 22 29 3b 0a 09 66 70 g mode.\n");..fp
bb60: 72 69 6e 74 66 28 63 68 61 6e 6e 65 6c 2c 20 22 rintf(channel, "
bb70: 20 20 2d 66 20 20 20 20 20 20 20 20 20 20 20 20 -f
bb80: 20 20 52 75 6e 20 69 6e 20 66 6f 72 65 67 72 6f Run in foregro
bb90: 75 6e 64 2e 5c 6e 22 29 3b 0a 09 66 70 72 69 6e und.\n");..fprin
bba0: 74 66 28 63 68 61 6e 6e 65 6c 2c 20 22 20 20 2d tf(channel, " -
bbb0: 73 20 20 20 20 20 20 20 20 20 20 20 20 20 20 45 s E
bbc0: 6e 61 62 6c 65 20 73 69 6e 67 6c 65 20 74 68 72 nable single thr
bbd0: 65 61 64 65 64 20 6d 6f 64 65 2e 5c 6e 22 29 3b eaded mode.\n");
bbe0: 0a 09 66 70 72 69 6e 74 66 28 63 68 61 6e 6e 65 ..fprintf(channe
bbf0: 6c 2c 20 22 20 20 2d 68 20 20 20 20 20 20 20 20 l, " -h
bc00: 20 20 20 20 20 20 47 69 76 65 20 74 68 69 73 20 Give this
bc10: 68 65 6c 70 2e 5c 6e 22 29 3b 0a 09 66 70 72 69 help.\n");..fpri
bc20: 6e 74 66 28 63 68 61 6e 6e 65 6c 2c 20 22 20 20 ntf(channel, "
bc30: 2d 6f 20 6e 6f 74 68 72 65 61 64 73 20 20 20 20 -o nothreads
bc40: 45 6e 61 62 6c 65 20 73 69 6e 67 6c 65 20 74 68 Enable single th
bc50: 72 65 61 64 65 64 20 6d 6f 64 65 2e 5c 6e 22 29 readed mode.\n")
bc60: 3b 0a 09 66 70 72 69 6e 74 66 28 63 68 61 6e 6e ;..fprintf(chann
bc70: 65 6c 2c 20 22 20 20 2d 6f 20 61 6c 6c 6f 77 5f el, " -o allow_
bc80: 6f 74 68 65 72 20 20 41 6c 6c 6f 77 20 6f 74 68 other Allow oth
bc90: 65 72 20 75 73 65 72 73 20 74 6f 20 61 63 63 65 er users to acce
bca0: 73 73 20 74 68 69 73 20 6d 6f 75 6e 74 70 6f 69 ss this mountpoi
bcb0: 6e 74 20 28 64 65 66 61 75 6c 74 5c 6e 22 29 3b nt (default\n");
bcc0: 0a 09 66 70 72 69 6e 74 66 28 63 68 61 6e 6e 65 ..fprintf(channe
bcd0: 6c 2c 20 22 20 20 20 20 20 20 20 20 20 20 20 20 l, "
bce0: 20 20 20 20 20 20 69 66 20 72 6f 6f 74 29 2e 5c if root).\
bcf0: 6e 22 29 3b 0a 0a 09 72 65 74 75 72 6e 3b 0a 7d n");...return;.}
bd00: 0a 0a 73 74 61 74 69 63 20 69 6e 74 20 61 70 70 ..static int app
bd10: 66 73 5f 6f 70 74 5f 70 61 72 73 65 28 69 6e 74 fs_opt_parse(int
bd20: 20 61 72 67 63 2c 20 63 68 61 72 20 2a 2a 61 72 argc, char **ar
bd30: 67 76 2c 20 20 73 74 72 75 63 74 20 66 75 73 65 gv, struct fuse
bd40: 5f 61 72 67 73 20 2a 61 72 67 73 29 20 7b 0a 09 _args *args) {..
bd50: 69 6e 74 20 63 68 3b 0a 09 63 68 61 72 20 2a 6f int ch;..char *o
bd60: 70 74 73 74 72 2c 20 2a 6f 70 74 73 74 72 5f 6e ptstr, *optstr_n
bd70: 65 78 74 2c 20 2a 6f 70 74 73 74 72 5f 73 3b 0a ext, *optstr_s;.
bd80: 09 63 68 61 72 20 66 61 6b 65 5f 61 72 67 5b 33 .char fake_arg[3
bd90: 5d 20 3d 20 7b 27 2d 27 2c 20 30 2c 20 30 7d 3b ] = {'-', 0, 0};
bda0: 0a 0a 09 2f 2a 0a 09 20 2a 20 44 65 66 61 75 6c .../*.. * Defaul
bdb0: 74 20 76 61 6c 75 65 73 0a 09 20 2a 2f 0a 23 69 t values.. */.#i
bdc0: 66 64 65 66 20 54 43 4c 5f 54 48 52 45 41 44 53 fdef TCL_THREADS
bdd0: 0a 09 61 70 70 66 73 5f 74 68 72 65 61 64 65 64 ..appfs_threaded
bde0: 5f 74 63 6c 20 3d 20 31 3b 0a 23 65 6c 73 65 0a _tcl = 1;.#else.
bdf0: 09 61 70 70 66 73 5f 74 68 72 65 61 64 65 64 5f .appfs_threaded_
be00: 74 63 6c 20 3d 20 30 3b 0a 23 65 6e 64 69 66 0a tcl = 0;.#endif.
be10: 0a 09 2f 2a 2a 0a 09 20 2a 2a 20 41 64 64 20 46 ../**.. ** Add F
be20: 55 53 45 20 61 72 67 75 6d 65 6e 74 73 20 77 68 USE arguments wh
be30: 69 63 68 20 77 65 20 61 6c 77 61 79 73 20 73 75 ich we always su
be40: 70 70 6c 79 0a 09 20 2a 2a 2f 0a 09 66 75 73 65 pply.. **/..fuse
be50: 5f 6f 70 74 5f 61 64 64 5f 61 72 67 28 61 72 67 _opt_add_arg(arg
be60: 73 2c 20 22 2d 6f 64 65 66 61 75 6c 74 5f 70 65 s, "-odefault_pe
be70: 72 6d 69 73 73 69 6f 6e 73 2c 66 73 6e 61 6d 65 rmissions,fsname
be80: 3d 61 70 70 66 73 2c 73 75 62 74 79 70 65 3d 61 =appfs,subtype=a
be90: 70 70 66 73 64 2c 75 73 65 5f 69 6e 6f 2c 65 6e ppfsd,use_ino,en
bea0: 74 72 79 5f 74 69 6d 65 6f 75 74 3d 30 2c 61 74 try_timeout=0,at
beb0: 74 72 5f 74 69 6d 65 6f 75 74 3d 30 2c 62 69 67 tr_timeout=0,big
bec0: 5f 77 72 69 74 65 73 2c 69 6e 74 72 2c 68 61 72 _writes,intr,har
bed0: 64 5f 72 65 6d 6f 76 65 22 29 3b 0a 0a 09 69 66 d_remove");...if
bee0: 20 28 67 65 74 75 69 64 28 29 20 3d 3d 20 30 29 (getuid() == 0)
bef0: 20 7b 0a 09 09 66 75 73 65 5f 6f 70 74 5f 70 61 {...fuse_opt_pa
bf00: 72 73 65 28 61 72 67 73 2c 20 4e 55 4c 4c 2c 20 rse(args, NULL,
bf10: 4e 55 4c 4c 2c 20 4e 55 4c 4c 29 3b 0a 09 09 66 NULL, NULL);...f
bf20: 75 73 65 5f 6f 70 74 5f 61 64 64 5f 61 72 67 28 use_opt_add_arg(
bf30: 61 72 67 73 2c 20 22 2d 6f 61 6c 6c 6f 77 5f 6f args, "-oallow_o
bf40: 74 68 65 72 22 29 3b 0a 0a 09 09 2f 2a 0a 09 09 ther");..../*...
bf50: 20 2a 20 54 68 69 73 20 73 68 6f 75 6c 64 20 67 * This should g
bf60: 65 6e 65 72 61 6c 6c 79 20 62 65 20 61 76 6f 69 enerally be avoi
bf70: 64 65 64 2c 20 62 75 74 20 69 66 20 74 68 65 72 ded, but if ther
bf80: 65 20 61 72 65 20 73 65 63 75 72 69 74 79 0a 09 e are security..
bf90: 09 20 2a 20 63 6f 6e 63 65 72 6e 73 20 73 75 69 . * concerns sui
bfa0: 64 20 63 61 6e 20 62 65 20 64 69 73 61 62 6c 65 d can be disable
bfb0: 64 20 63 6f 6d 70 6c 65 74 65 6c 79 20 6f 6e 20 d completely on
bfc0: 74 68 65 20 63 6f 6d 6d 61 6e 64 6c 69 6e 65 0a the commandline.
bfd0: 09 09 20 2a 2f 0a 09 09 66 75 73 65 5f 6f 70 74 .. */...fuse_opt
bfe0: 5f 70 61 72 73 65 28 61 72 67 73 2c 20 4e 55 4c _parse(args, NUL
bff0: 4c 2c 20 4e 55 4c 4c 2c 20 4e 55 4c 4c 29 3b 0a L, NULL, NULL);.
c000: 09 09 66 75 73 65 5f 6f 70 74 5f 61 64 64 5f 61 ..fuse_opt_add_a
c010: 72 67 28 61 72 67 73 2c 20 22 2d 6f 73 75 69 64 rg(args, "-osuid
c020: 22 29 3b 0a 09 7d 0a 0a 09 77 68 69 6c 65 20 28 ");..}...while (
c030: 28 63 68 20 3d 20 67 65 74 6f 70 74 28 61 72 67 (ch = getopt(arg
c040: 63 2c 20 61 72 67 76 2c 20 22 64 66 73 68 76 6f c, argv, "dfshvo
c050: 3a 22 29 29 20 21 3d 20 2d 31 29 20 7b 0a 09 09 :")) != -1) {...
c060: 73 77 69 74 63 68 20 28 63 68 29 20 7b 0a 09 09 switch (ch) {...
c070: 09 63 61 73 65 20 27 76 27 3a 0a 09 09 09 09 2f .case 'v':...../
c080: 2a 20 49 67 6e 6f 72 65 64 20 2a 2f 0a 09 09 09 * Ignored */....
c090: 09 62 72 65 61 6b 3b 0a 09 09 09 63 61 73 65 20 .break;....case
c0a0: 27 6f 27 3a 0a 09 09 09 09 6f 70 74 73 74 72 5f 'o':.....optstr_
c0b0: 6e 65 78 74 20 3d 20 6f 70 74 73 74 72 20 3d 20 next = optstr =
c0c0: 6f 70 74 73 74 72 5f 73 20 3d 20 73 74 72 64 75 optstr_s = strdu
c0d0: 70 28 6f 70 74 61 72 67 29 3b 0a 0a 09 09 09 09 p(optarg);......
c0e0: 77 68 69 6c 65 20 28 31 29 20 7b 0a 09 09 09 09 while (1) {.....
c0f0: 09 6f 70 74 73 74 72 20 3d 20 6f 70 74 73 74 72 .optstr = optstr
c100: 5f 6e 65 78 74 3b 0a 0a 09 09 09 09 09 69 66 20 _next;.......if
c110: 28 21 6f 70 74 73 74 72 29 20 7b 0a 09 09 09 09 (!optstr) {.....
c120: 09 09 62 72 65 61 6b 3b 0a 09 09 09 09 09 7d 0a ..break;......}.
c130: 0a 09 09 09 09 09 6f 70 74 73 74 72 5f 6e 65 78 ......optstr_nex
c140: 74 20 3d 20 73 74 72 63 68 72 28 6f 70 74 73 74 t = strchr(optst
c150: 72 2c 20 27 2c 27 29 3b 0a 09 09 09 09 09 69 66 r, ',');......if
c160: 20 28 6f 70 74 73 74 72 5f 6e 65 78 74 29 20 7b (optstr_next) {
c170: 0a 09 09 09 09 09 09 2a 6f 70 74 73 74 72 5f 6e .......*optstr_n
c180: 65 78 74 20 3d 20 27 5c 30 27 3b 0a 09 09 09 09 ext = '\0';.....
c190: 09 09 6f 70 74 73 74 72 5f 6e 65 78 74 2b 2b 3b ..optstr_next++;
c1a0: 0a 09 09 09 09 09 7d 0a 0a 09 09 09 09 09 69 66 ......}.......if
c1b0: 20 28 73 74 72 63 6d 70 28 6f 70 74 73 74 72 2c (strcmp(optstr,
c1c0: 20 22 6e 6f 74 68 72 65 61 64 73 22 29 20 3d 3d "nothreads") ==
c1d0: 20 30 29 20 7b 0a 09 09 09 09 09 09 41 50 50 46 0) {.......APPF
c1e0: 53 5f 44 45 42 55 47 28 22 50 61 73 73 69 6e 67 S_DEBUG("Passing
c1f0: 20 6f 70 74 69 6f 6e 20 74 6f 20 46 55 53 45 3a option to FUSE:
c200: 20 2d 73 22 29 3b 0a 0a 09 09 09 09 09 09 66 75 -s");........fu
c210: 73 65 5f 6f 70 74 5f 70 61 72 73 65 28 61 72 67 se_opt_parse(arg
c220: 73 2c 20 4e 55 4c 4c 2c 20 4e 55 4c 4c 2c 20 4e s, NULL, NULL, N
c230: 55 4c 4c 29 3b 0a 09 09 09 09 09 09 66 75 73 65 ULL);.......fuse
c240: 5f 6f 70 74 5f 61 64 64 5f 61 72 67 28 61 72 67 _opt_add_arg(arg
c250: 73 2c 20 22 2d 73 22 29 3b 0a 0a 09 09 09 09 09 s, "-s");.......
c260: 09 61 70 70 66 73 5f 74 68 72 65 61 64 65 64 5f .appfs_threaded_
c270: 74 63 6c 20 3d 20 30 3b 0a 09 09 09 09 09 7d 20 tcl = 0;......}
c280: 65 6c 73 65 20 69 66 20 28 73 74 72 63 6d 70 28 else if (strcmp(
c290: 6f 70 74 73 74 72 2c 20 22 61 6c 6c 6f 77 5f 6f optstr, "allow_o
c2a0: 74 68 65 72 22 29 20 3d 3d 20 30 29 20 7b 0a 09 ther") == 0) {..
c2b0: 09 09 09 09 09 41 50 50 46 53 5f 44 45 42 55 47 .....APPFS_DEBUG
c2c0: 28 22 50 61 73 73 69 6e 67 20 6f 70 74 69 6f 6e ("Passing option
c2d0: 20 74 6f 20 46 55 53 45 3a 20 2d 6f 20 61 6c 6c to FUSE: -o all
c2e0: 6f 77 5f 6f 74 68 65 72 22 29 3b 0a 0a 09 09 09 ow_other");.....
c2f0: 09 09 09 66 75 73 65 5f 6f 70 74 5f 70 61 72 73 ...fuse_opt_pars
c300: 65 28 61 72 67 73 2c 20 4e 55 4c 4c 2c 20 4e 55 e(args, NULL, NU
c310: 4c 4c 2c 20 4e 55 4c 4c 29 3b 0a 09 09 09 09 09 LL, NULL);......
c320: 09 66 75 73 65 5f 6f 70 74 5f 61 64 64 5f 61 72 .fuse_opt_add_ar
c330: 67 28 61 72 67 73 2c 20 22 2d 6f 61 6c 6c 6f 77 g(args, "-oallow
c340: 5f 6f 74 68 65 72 22 29 3b 0a 09 09 09 09 09 7d _other");......}
c350: 20 65 6c 73 65 20 69 66 20 28 73 74 72 63 6d 70 else if (strcmp
c360: 28 6f 70 74 73 74 72 2c 20 22 72 77 22 29 20 3d (optstr, "rw") =
c370: 3d 20 30 29 20 7b 0a 09 09 09 09 09 09 2f 2a 20 = 0) {......./*
c380: 49 67 6e 6f 72 65 64 20 2a 2f 0a 09 09 09 09 09 Ignored */......
c390: 7d 20 65 6c 73 65 20 7b 0a 09 09 09 09 09 09 66 } else {.......f
c3a0: 70 72 69 6e 74 66 28 73 74 64 65 72 72 2c 20 22 printf(stderr, "
c3b0: 61 70 70 66 73 64 3a 20 69 6e 76 61 6c 69 64 20 appfsd: invalid
c3c0: 6f 70 74 69 6f 6e 3a 20 5c 22 2d 6f 20 25 73 5c option: \"-o %s\
c3d0: 22 5c 6e 22 2c 20 6f 70 74 73 74 72 29 3b 0a 0a "\n", optstr);..
c3e0: 09 09 09 09 09 09 66 72 65 65 28 6f 70 74 73 74 ......free(optst
c3f0: 72 5f 73 29 3b 0a 0a 09 09 09 09 09 09 72 65 74 r_s);........ret
c400: 75 72 6e 28 31 29 3b 0a 09 09 09 09 09 7d 0a 09 urn(1);......}..
c410: 09 09 09 7d 0a 0a 09 09 09 09 66 72 65 65 28 6f ...}......free(o
c420: 70 74 73 74 72 5f 73 29 3b 0a 0a 09 09 09 09 62 ptstr_s);......b
c430: 72 65 61 6b 3b 0a 09 09 09 63 61 73 65 20 27 64 reak;....case 'd
c440: 27 3a 0a 09 09 09 63 61 73 65 20 27 66 27 3a 0a ':....case 'f':.
c450: 09 09 09 63 61 73 65 20 27 73 27 3a 0a 09 09 09 ...case 's':....
c460: 09 69 66 20 28 63 68 20 3d 3d 20 27 73 27 29 20 .if (ch == 's')
c470: 7b 0a 09 09 09 09 09 61 70 70 66 73 5f 74 68 72 {......appfs_thr
c480: 65 61 64 65 64 5f 74 63 6c 20 3d 20 30 3b 0a 09 eaded_tcl = 0;..
c490: 09 09 09 7d 0a 0a 09 09 09 09 66 61 6b 65 5f 61 ...}......fake_a
c4a0: 72 67 5b 31 5d 20 3d 20 63 68 3b 0a 0a 09 09 09 rg[1] = ch;.....
c4b0: 09 41 50 50 46 53 5f 44 45 42 55 47 28 22 50 61 .APPFS_DEBUG("Pa
c4c0: 73 73 69 6e 67 20 6f 70 74 69 6f 6e 20 74 6f 20 ssing option to
c4d0: 46 55 53 45 3a 20 25 73 22 2c 20 66 61 6b 65 5f FUSE: %s", fake_
c4e0: 61 72 67 29 3b 0a 0a 09 09 09 09 66 75 73 65 5f arg);......fuse_
c4f0: 6f 70 74 5f 70 61 72 73 65 28 61 72 67 73 2c 20 opt_parse(args,
c500: 4e 55 4c 4c 2c 20 4e 55 4c 4c 2c 20 4e 55 4c 4c NULL, NULL, NULL
c510: 29 3b 0a 09 09 09 09 66 75 73 65 5f 6f 70 74 5f );.....fuse_opt_
c520: 61 64 64 5f 61 72 67 28 61 72 67 73 2c 20 66 61 add_arg(args, fa
c530: 6b 65 5f 61 72 67 29 3b 0a 09 09 09 09 62 72 65 ke_arg);.....bre
c540: 61 6b 3b 0a 09 09 09 63 61 73 65 20 27 68 27 3a ak;....case 'h':
c550: 0a 09 09 09 09 61 70 70 66 73 5f 70 72 69 6e 74 .....appfs_print
c560: 5f 68 65 6c 70 28 73 74 64 6f 75 74 29 3b 0a 0a _help(stdout);..
c570: 09 09 09 09 72 65 74 75 72 6e 28 2d 31 29 3b 0a ....return(-1);.
c580: 09 09 09 63 61 73 65 20 27 3a 27 3a 0a 09 09 09 ...case ':':....
c590: 63 61 73 65 20 27 3f 27 3a 0a 09 09 09 64 65 66 case '?':....def
c5a0: 61 75 6c 74 3a 0a 09 09 09 09 61 70 70 66 73 5f ault:.....appfs_
c5b0: 70 72 69 6e 74 5f 68 65 6c 70 28 73 74 64 65 72 print_help(stder
c5c0: 72 29 3b 0a 0a 09 09 09 09 72 65 74 75 72 6e 28 r);......return(
c5d0: 31 29 3b 0a 09 09 7d 0a 09 7d 0a 0a 09 69 66 20 1);...}..}...if
c5e0: 28 28 6f 70 74 69 6e 64 20 2b 20 32 29 20 21 3d ((optind + 2) !=
c5f0: 20 61 72 67 63 29 20 7b 0a 09 09 69 66 20 28 28 argc) {...if ((
c600: 6f 70 74 69 6e 64 20 2b 20 32 29 20 3c 20 61 72 optind + 2) < ar
c610: 67 63 29 20 7b 0a 09 09 09 66 70 72 69 6e 74 66 gc) {....fprintf
c620: 28 73 74 64 65 72 72 2c 20 22 54 6f 6f 20 6d 61 (stderr, "Too ma
c630: 6e 79 20 61 72 67 75 6d 65 6e 74 73 5c 6e 22 29 ny arguments\n")
c640: 3b 0a 09 09 7d 20 65 6c 73 65 20 7b 0a 09 09 09 ;...} else {....
c650: 66 70 72 69 6e 74 66 28 73 74 64 65 72 72 2c 20 fprintf(stderr,
c660: 22 4d 69 73 73 69 6e 67 20 63 61 63 68 65 64 69 "Missing cachedi
c670: 72 20 6f 72 20 6d 6f 75 6e 74 70 6f 69 6e 74 5c r or mountpoint\
c680: 6e 22 29 3b 0a 09 09 7d 0a 0a 09 09 61 70 70 66 n");...}....appf
c690: 73 5f 70 72 69 6e 74 5f 68 65 6c 70 28 73 74 64 s_print_help(std
c6a0: 65 72 72 29 3b 0a 0a 09 09 72 65 74 75 72 6e 28 err);....return(
c6b0: 31 29 3b 0a 09 7d 0a 0a 09 2f 2a 0a 09 20 2a 20 1);..}.../*.. *
c6c0: 53 65 74 20 63 61 63 68 65 20 64 69 72 20 61 73 Set cache dir as
c6d0: 20 66 69 72 73 74 20 61 72 67 75 6d 65 6e 74 20 first argument
c6e0: 28 74 68 65 20 22 64 65 76 69 63 65 22 2c 20 65 (the "device", e
c6f0: 73 73 65 6e 74 69 61 6c 6c 79 29 0a 09 20 2a 2f ssentially).. */
c700: 0a 09 61 70 70 66 73 5f 63 61 63 68 65 64 69 72 ..appfs_cachedir
c710: 20 3d 20 61 72 67 76 5b 6f 70 74 69 6e 64 5d 3b = argv[optind];
c720: 0a 0a 09 2f 2a 0a 09 20 2a 20 50 61 73 73 20 74 .../*.. * Pass t
c730: 68 65 20 72 65 6d 61 69 6e 69 6e 67 20 61 72 67 he remaining arg
c740: 75 6d 65 6e 74 20 74 6f 20 46 55 53 45 20 61 73 ument to FUSE as
c750: 20 74 68 65 20 64 69 72 65 63 74 6f 72 79 0a 09 the directory..
c760: 20 2a 2f 0a 09 66 75 73 65 5f 6f 70 74 5f 70 61 */..fuse_opt_pa
c770: 72 73 65 28 61 72 67 73 2c 20 4e 55 4c 4c 2c 20 rse(args, NULL,
c780: 4e 55 4c 4c 2c 20 4e 55 4c 4c 29 3b 0a 09 66 75 NULL, NULL);..fu
c790: 73 65 5f 6f 70 74 5f 61 64 64 5f 61 72 67 28 61 se_opt_add_arg(a
c7a0: 72 67 73 2c 20 61 72 67 76 5b 6f 70 74 69 6e 64 rgs, argv[optind
c7b0: 20 2b 20 31 5d 29 3b 0a 0a 09 72 65 74 75 72 6e + 1]);...return
c7c0: 28 30 29 3b 0a 7d 0a 0a 0a 2f 2a 0a 20 2a 20 46 (0);.}.../*. * F
c7d0: 55 53 45 20 6f 70 65 72 61 74 69 6f 6e 73 20 73 USE operations s
c7e0: 74 72 75 63 74 75 72 65 0a 20 2a 2f 0a 73 74 61 tructure. */.sta
c7f0: 74 69 63 20 73 74 72 75 63 74 20 66 75 73 65 5f tic struct fuse_
c800: 6f 70 65 72 61 74 69 6f 6e 73 20 61 70 70 66 73 operations appfs
c810: 5f 6f 70 65 72 61 74 69 6f 6e 73 20 3d 20 7b 0a _operations = {.
c820: 09 2e 67 65 74 61 74 74 72 20 20 20 3d 20 61 70 ..getattr = ap
c830: 70 66 73 5f 66 75 73 65 5f 67 65 74 61 74 74 72 pfs_fuse_getattr
c840: 2c 0a 09 2e 72 65 61 64 64 69 72 20 20 20 3d 20 ,...readdir =
c850: 61 70 70 66 73 5f 66 75 73 65 5f 72 65 61 64 64 appfs_fuse_readd
c860: 69 72 2c 0a 09 2e 72 65 61 64 6c 69 6e 6b 20 20 ir,...readlink
c870: 3d 20 61 70 70 66 73 5f 66 75 73 65 5f 72 65 61 = appfs_fuse_rea
c880: 64 6c 69 6e 6b 2c 0a 09 2e 6f 70 65 6e 20 20 20 dlink,...open
c890: 20 20 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f = appfs_fuse_
c8a0: 6f 70 65 6e 2c 0a 09 2e 72 65 6c 65 61 73 65 20 open,...release
c8b0: 20 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f 63 = appfs_fuse_c
c8c0: 6c 6f 73 65 2c 0a 09 2e 72 65 61 64 20 20 20 20 lose,...read
c8d0: 20 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f 72 = appfs_fuse_r
c8e0: 65 61 64 2c 0a 09 2e 77 72 69 74 65 20 20 20 20 ead,...write
c8f0: 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f 77 72 = appfs_fuse_wr
c900: 69 74 65 2c 0a 09 2e 6d 6b 6e 6f 64 20 20 20 20 ite,...mknod
c910: 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f 6d 6b = appfs_fuse_mk
c920: 6e 6f 64 2c 0a 09 2e 63 72 65 61 74 65 20 20 20 nod,...create
c930: 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f 63 72 = appfs_fuse_cr
c940: 65 61 74 65 2c 0a 09 2e 74 72 75 6e 63 61 74 65 eate,...truncate
c950: 20 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f 74 = appfs_fuse_t
c960: 72 75 6e 63 61 74 65 2c 0a 09 2e 75 6e 6c 69 6e runcate,...unlin
c970: 6b 20 20 20 20 3d 20 61 70 70 66 73 5f 66 75 73 k = appfs_fus
c980: 65 5f 75 6e 6c 69 6e 6b 5f 72 6d 64 69 72 2c 0a e_unlink_rmdir,.
c990: 09 2e 72 6d 64 69 72 20 20 20 20 20 3d 20 61 70 ..rmdir = ap
c9a0: 70 66 73 5f 66 75 73 65 5f 75 6e 6c 69 6e 6b 5f pfs_fuse_unlink_
c9b0: 72 6d 64 69 72 2c 0a 09 2e 6d 6b 64 69 72 20 20 rmdir,...mkdir
c9c0: 20 20 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f = appfs_fuse_
c9d0: 6d 6b 64 69 72 2c 0a 09 2e 63 68 6d 6f 64 20 20 mkdir,...chmod
c9e0: 20 20 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f = appfs_fuse_
c9f0: 63 68 6d 6f 64 2c 0a 09 2e 73 79 6d 6c 69 6e 6b chmod,...symlink
ca00: 20 20 20 3d 20 61 70 70 66 73 5f 66 75 73 65 5f = appfs_fuse_
ca10: 73 79 6d 6c 69 6e 6b 2c 0a 7d 3b 0a 0a 2f 2a 0a symlink,.};../*.
ca20: 20 2a 20 45 6e 74 72 79 20 70 6f 69 6e 74 20 69 * Entry point i
ca30: 6e 74 6f 20 74 68 69 73 20 70 72 6f 67 72 61 6d nto this program
ca40: 2e 0a 20 2a 2f 0a 69 6e 74 20 6d 61 69 6e 28 69 .. */.int main(i
ca50: 6e 74 20 61 72 67 63 2c 20 63 68 61 72 20 2a 2a nt argc, char **
ca60: 61 72 67 76 29 20 7b 0a 09 54 63 6c 5f 49 6e 74 argv) {..Tcl_Int
ca70: 65 72 70 20 2a 74 65 73 74 5f 69 6e 74 65 72 70 erp *test_interp
ca80: 3b 0a 09 63 68 61 72 20 2a 74 65 73 74 5f 69 6e ;..char *test_in
ca90: 74 65 72 70 5f 65 72 72 6f 72 3b 0a 09 73 74 72 terp_error;..str
caa0: 75 63 74 20 66 75 73 65 5f 61 72 67 73 20 61 72 uct fuse_args ar
cab0: 67 73 20 3d 20 46 55 53 45 5f 41 52 47 53 5f 49 gs = FUSE_ARGS_I
cac0: 4e 49 54 28 30 2c 20 4e 55 4c 4c 29 3b 0a 09 73 NIT(0, NULL);..s
cad0: 74 72 75 63 74 20 72 6c 69 6d 69 74 20 6e 75 6d truct rlimit num
cae0: 62 65 72 5f 6f 70 65 6e 5f 66 69 6c 65 73 3b 0a ber_open_files;.
caf0: 09 69 6e 74 20 70 74 68 72 65 61 64 5f 72 65 74 .int pthread_ret
cb00: 2c 20 61 6f 70 5f 72 65 74 2c 20 72 6c 69 6d 69 , aop_ret, rlimi
cb10: 74 5f 72 65 74 3b 0a 09 76 6f 69 64 20 2a 73 69 t_ret;..void *si
cb20: 67 6e 61 6c 5f 72 65 74 3b 0a 09 63 68 61 72 20 gnal_ret;..char
cb30: 2a 61 72 67 76 30 3b 0a 09 72 6c 69 6d 5f 74 20 *argv0;..rlim_t
cb40: 6e 75 6d 62 65 72 5f 6f 70 65 6e 5f 66 69 6c 65 number_open_file
cb50: 73 5f 6d 61 78 3b 0a 0a 09 2f 2a 0a 09 20 2a 20 s_max;.../*.. *
cb60: 53 6b 69 70 20 70 61 73 73 65 64 20 70 72 6f 67 Skip passed prog
cb70: 72 61 6d 20 6e 61 6d 65 0a 09 20 2a 2f 0a 09 69 ram name.. */..i
cb80: 66 20 28 61 72 67 63 20 3d 3d 20 30 20 7c 7c 20 f (argc == 0 ||
cb90: 61 72 67 76 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a argv == NULL) {.
cba0: 09 09 72 65 74 75 72 6e 28 31 29 3b 0a 09 7d 0a ..return(1);..}.
cbb0: 0a 09 61 72 67 76 30 20 3d 20 61 72 67 76 5b 30 ..argv0 = argv[0
cbc0: 5d 3b 0a 0a 09 61 72 67 63 2d 2d 3b 0a 09 61 72 ];...argc--;..ar
cbd0: 67 76 2b 2b 3b 0a 0a 09 2f 2a 0a 09 20 2a 20 53 gv++;.../*.. * S
cbe0: 65 74 20 61 70 70 72 6f 70 72 69 61 74 65 20 75 et appropriate u
cbf0: 6d 61 73 6b 0a 09 20 2a 2f 0a 09 75 6d 61 73 6b mask.. */..umask
cc00: 28 30 32 32 29 3b 0a 0a 09 2f 2a 0a 09 20 2a 20 (022);.../*.. *
cc10: 53 65 74 20 67 6c 6f 62 61 6c 20 76 61 72 69 61 Set global varia
cc20: 62 6c 65 73 2c 20 74 68 65 73 65 20 73 68 6f 75 bles, these shou
cc30: 6c 64 20 62 65 20 63 6f 6e 66 69 67 75 72 61 74 ld be configurat
cc40: 69 6f 6e 20 6f 70 74 69 6f 6e 73 2e 0a 09 20 2a ion options... *
cc50: 2f 0a 09 61 70 70 66 73 5f 63 61 63 68 65 64 69 /..appfs_cachedi
cc60: 72 20 3d 20 41 50 50 46 53 5f 43 41 43 48 45 44 r = APPFS_CACHED
cc70: 49 52 3b 0a 0a 09 2f 2a 0a 09 20 2a 20 53 65 74 IR;.../*.. * Set
cc80: 20 67 6c 6f 62 61 6c 20 76 61 72 69 61 62 6c 65 global variable
cc90: 20 66 6f 72 20 22 62 6f 6f 74 20 74 69 6d 65 22 for "boot time"
cca0: 20 74 6f 20 73 65 74 20 61 20 74 69 6d 65 20 6f to set a time o
ccb0: 6e 20 64 69 72 65 63 74 6f 72 69 65 73 0a 09 20 n directories..
ccc0: 2a 20 74 68 61 74 20 77 65 20 66 61 6b 65 2e 0a * that we fake..
ccd0: 09 20 2a 2f 0a 09 61 70 70 66 73 5f 62 6f 6f 74 . */..appfs_boot
cce0: 74 69 6d 65 20 3d 20 74 69 6d 65 28 4e 55 4c 4c time = time(NULL
ccf0: 29 3b 0a 0a 09 2f 2a 0a 09 20 2a 20 52 65 67 69 );.../*.. * Regi
cd00: 73 74 65 72 20 22 73 68 61 31 22 20 61 6e 64 20 ster "sha1" and
cd10: 22 61 70 70 66 73 64 22 20 70 61 63 6b 61 67 65 "appfsd" package
cd20: 20 77 69 74 68 20 6c 69 62 74 63 6c 20 73 6f 20 with libtcl so
cd30: 74 68 61 74 20 61 6e 79 20 6e 65 77 0a 09 20 2a that any new.. *
cd40: 20 69 6e 74 65 72 70 72 65 74 65 72 73 20 63 72 interpreters cr
cd50: 65 61 74 65 64 20 28 77 68 69 63 68 20 61 72 65 eated (which are
cd60: 20 64 6f 6e 65 20 64 79 6e 61 6d 69 63 61 6c 6c done dynamicall
cd70: 79 20 62 79 20 46 55 53 45 29 20 63 61 6e 20 68 y by FUSE) can h
cd80: 61 76 65 0a 09 20 2a 20 74 68 65 20 61 70 70 72 ave.. * the appr
cd90: 6f 70 72 69 61 74 65 20 63 6f 6e 66 69 67 75 72 opriate configur
cda0: 61 74 69 6f 6e 20 64 6f 6e 65 20 61 75 74 6f 6d ation done autom
cdb0: 61 74 69 63 61 6c 6c 79 2e 0a 09 20 2a 2f 0a 09 atically... */..
cdc0: 54 63 6c 5f 53 74 61 74 69 63 50 61 63 6b 61 67 Tcl_StaticPackag
cdd0: 65 28 4e 55 4c 4c 2c 20 22 73 68 61 31 22 2c 20 e(NULL, "sha1",
cde0: 53 68 61 31 5f 49 6e 69 74 2c 20 4e 55 4c 4c 29 Sha1_Init, NULL)
cdf0: 3b 0a 09 54 63 6c 5f 53 74 61 74 69 63 50 61 63 ;..Tcl_StaticPac
ce00: 6b 61 67 65 28 4e 55 4c 4c 2c 20 22 61 70 70 66 kage(NULL, "appf
ce10: 73 64 22 2c 20 41 70 70 66 73 64 5f 49 6e 69 74 sd", Appfsd_Init
ce20: 2c 20 4e 55 4c 4c 29 3b 0a 0a 09 2f 2a 0a 09 20 , NULL);.../*..
ce30: 2a 20 43 72 65 61 74 65 20 61 20 74 68 72 65 61 * Create a threa
ce40: 64 2d 73 70 65 63 69 66 69 63 2d 64 61 74 61 20 d-specific-data
ce50: 28 54 53 44 29 20 6b 65 79 20 66 6f 72 20 65 61 (TSD) key for ea
ce60: 63 68 20 74 68 72 65 61 64 20 74 6f 20 72 65 66 ch thread to ref
ce70: 65 72 0a 09 20 2a 20 74 6f 20 69 74 73 20 6f 77 er.. * to its ow
ce80: 6e 20 54 63 6c 20 69 6e 74 65 72 70 72 65 74 65 n Tcl interprete
ce90: 72 2e 20 20 54 63 6c 20 69 6e 74 65 72 70 72 65 r. Tcl interpre
cea0: 74 65 72 73 20 6d 75 73 74 20 62 65 20 75 6e 69 ters must be uni
ceb0: 71 75 65 20 70 65 72 0a 09 20 2a 20 74 68 72 65 que per.. * thre
cec0: 61 64 20 61 6e 64 20 6e 65 77 20 74 68 72 65 61 ad and new threa
ced0: 64 73 20 61 72 65 20 64 79 6e 61 6d 69 63 61 6c ds are dynamical
cee0: 6c 79 20 63 72 65 61 74 65 64 20 62 79 20 46 55 ly created by FU
cef0: 53 45 2e 0a 09 20 2a 2f 0a 09 70 74 68 72 65 61 SE... */..pthrea
cf00: 64 5f 72 65 74 20 3d 20 70 74 68 72 65 61 64 5f d_ret = pthread_
cf10: 6b 65 79 5f 63 72 65 61 74 65 28 26 69 6e 74 65 key_create(&inte
cf20: 72 70 4b 65 79 2c 20 61 70 70 66 73 5f 74 65 72 rpKey, appfs_ter
cf30: 6d 69 6e 61 74 65 5f 69 6e 74 65 72 70 5f 61 6e minate_interp_an
cf40: 64 5f 74 68 72 65 61 64 29 3b 0a 09 69 66 20 28 d_thread);..if (
cf50: 70 74 68 72 65 61 64 5f 72 65 74 20 21 3d 20 30 pthread_ret != 0
cf60: 29 20 7b 0a 09 09 66 70 72 69 6e 74 66 28 73 74 ) {...fprintf(st
cf70: 64 65 72 72 2c 20 22 55 6e 61 62 6c 65 20 74 6f derr, "Unable to
cf80: 20 63 72 65 61 74 65 20 54 53 44 20 6b 65 79 20 create TSD key
cf90: 66 6f 72 20 54 63 6c 2e 20 20 41 62 6f 72 74 69 for Tcl. Aborti
cfa0: 6e 67 2e 5c 6e 22 29 3b 0a 0a 09 09 72 65 74 75 ng.\n");....retu
cfb0: 72 6e 28 31 29 3b 0a 09 7d 0a 0a 09 2f 2a 0a 09 rn(1);..}.../*..
cfc0: 20 2a 20 4d 61 6e 75 61 6c 6c 79 20 73 70 65 63 * Manually spec
cfd0: 69 66 79 20 63 61 63 68 65 20 64 69 72 65 63 74 ify cache direct
cfe0: 6f 72 79 2c 20 77 69 74 68 6f 75 74 20 46 55 53 ory, without FUS
cff0: 45 20 63 61 6c 6c 62 61 63 6b 0a 09 20 2a 20 54 E callback.. * T
d000: 68 69 73 20 6f 70 74 69 6f 6e 20 6f 6e 6c 79 20 his option only
d010: 77 6f 72 6b 73 20 77 68 65 6e 20 6e 6f 74 20 75 works when not u
d020: 73 69 6e 67 20 46 55 53 45 2c 20 73 69 6e 63 65 sing FUSE, since
d030: 20 77 65 0a 09 20 2a 20 64 6f 20 6e 6f 74 20 70 we.. * do not p
d040: 72 6f 63 65 73 73 20 69 74 20 77 69 74 68 20 46 rocess it with F
d050: 55 53 45 73 20 6f 70 74 69 6f 6e 20 70 72 6f 63 USEs option proc
d060: 65 73 73 69 6e 67 2e 0a 09 20 2a 2f 0a 09 69 66 essing... */..if
d070: 20 28 61 72 67 63 20 3e 3d 20 32 29 20 7b 0a 09 (argc >= 2) {..
d080: 09 69 66 20 28 73 74 72 63 6d 70 28 61 72 67 76 .if (strcmp(argv
d090: 5b 30 5d 2c 20 22 2d 2d 63 61 63 68 65 64 69 72 [0], "--cachedir
d0a0: 22 29 20 3d 3d 20 30 29 20 7b 0a 09 09 09 61 70 ") == 0) {....ap
d0b0: 70 66 73 5f 63 61 63 68 65 64 69 72 20 3d 20 73 pfs_cachedir = s
d0c0: 74 72 64 75 70 28 61 72 67 76 5b 31 5d 29 3b 0a trdup(argv[1]);.
d0d0: 0a 09 09 09 61 72 67 63 20 2d 3d 20 32 3b 0a 09 ....argc -= 2;..
d0e0: 09 09 61 72 67 76 20 2b 3d 20 32 3b 0a 09 09 7d ..argv += 2;...}
d0f0: 0a 09 7d 0a 0a 09 2f 2a 0a 09 20 2a 20 53 51 4c ..}.../*.. * SQL
d100: 69 74 65 33 20 6d 6f 64 65 2c 20 66 6f 72 20 72 ite3 mode, for r
d110: 75 6e 6e 69 6e 67 20 72 61 77 20 53 51 4c 20 61 unning raw SQL a
d120: 67 61 69 6e 73 74 20 74 68 65 20 63 61 63 68 65 gainst the cache
d130: 20 64 61 74 61 62 61 73 65 0a 09 20 2a 2f 0a 09 database.. */..
d140: 69 66 20 28 61 72 67 63 20 3d 3d 20 32 20 26 26 if (argc == 2 &&
d150: 20 73 74 72 63 6d 70 28 61 72 67 76 5b 30 5d 2c strcmp(argv[0],
d160: 20 22 2d 2d 73 71 6c 69 74 65 33 22 29 20 3d 3d "--sqlite3") ==
d170: 20 30 29 20 7b 0a 09 09 72 65 74 75 72 6e 28 61 0) {...return(a
d180: 70 70 66 73 5f 73 71 6c 69 74 65 33 28 61 72 67 ppfs_sqlite3(arg
d190: 76 5b 31 5d 29 29 3b 0a 09 7d 0a 0a 09 2f 2a 0a v[1]));..}.../*.
d1a0: 09 20 2a 20 54 63 6c 20 6d 6f 64 65 2c 20 66 6f . * Tcl mode, fo
d1b0: 72 20 72 75 6e 6e 69 6e 67 20 72 61 77 20 54 63 r running raw Tc
d1c0: 6c 20 69 6e 20 74 68 65 20 73 61 6d 65 20 65 6e l in the same en
d1d0: 76 69 72 6f 6e 6d 65 6e 74 20 41 70 70 46 53 64 vironment AppFSd
d1e0: 20 77 6f 75 6c 64 0a 09 20 2a 20 72 75 6e 20 63 would.. * run c
d1f0: 6f 64 65 2e 0a 09 20 2a 2f 0a 09 69 66 20 28 61 ode... */..if (a
d200: 72 67 63 20 3d 3d 20 32 20 26 26 20 73 74 72 63 rgc == 2 && strc
d210: 6d 70 28 61 72 67 76 5b 30 5d 2c 20 22 2d 2d 74 mp(argv[0], "--t
d220: 63 6c 22 29 20 3d 3d 20 30 29 20 7b 0a 09 09 72 cl") == 0) {...r
d230: 65 74 75 72 6e 28 61 70 70 66 73 5f 74 63 6c 28 eturn(appfs_tcl(
d240: 61 72 67 76 5b 31 5d 29 29 3b 0a 09 7d 0a 0a 09 argv[1]));..}...
d250: 2f 2a 0a 09 20 2a 20 52 65 67 69 73 74 65 72 20 /*.. * Register
d260: 61 20 73 69 67 6e 61 6c 20 68 61 6e 64 6c 65 72 a signal handler
d270: 20 66 6f 72 20 68 6f 74 2d 72 65 73 74 61 72 74 for hot-restart
d280: 20 72 65 71 75 65 73 74 73 0a 09 20 2a 2f 0a 09 requests.. */..
d290: 73 69 67 6e 61 6c 5f 72 65 74 20 3d 20 73 69 67 signal_ret = sig
d2a0: 6e 61 6c 28 53 49 47 48 55 50 2c 20 61 70 70 66 nal(SIGHUP, appf
d2b0: 73 5f 73 69 67 6e 61 6c 5f 68 61 6e 64 6c 65 72 s_signal_handler
d2c0: 29 3b 0a 09 69 66 20 28 73 69 67 6e 61 6c 5f 72 );..if (signal_r
d2d0: 65 74 20 3d 3d 20 53 49 47 5f 45 52 52 29 20 7b et == SIG_ERR) {
d2e0: 0a 09 09 66 70 72 69 6e 74 66 28 73 74 64 65 72 ...fprintf(stder
d2f0: 72 2c 20 22 55 6e 61 62 6c 65 20 74 6f 20 69 6e r, "Unable to in
d300: 73 74 61 6c 6c 20 73 69 67 6e 61 6c 20 68 61 6e stall signal han
d310: 64 6c 65 72 20 66 6f 72 20 68 6f 74 2d 72 65 73 dler for hot-res
d320: 74 61 72 74 5c 6e 22 29 3b 0a 09 09 66 70 72 69 tart\n");...fpri
d330: 6e 74 66 28 73 74 64 65 72 72 2c 20 22 48 6f 74 ntf(stderr, "Hot
d340: 2d 72 65 73 74 61 72 74 20 77 69 6c 6c 20 6e 6f -restart will no
d350: 74 20 62 65 20 61 76 61 69 6c 61 62 6c 65 2e 5c t be available.\
d360: 6e 22 29 3b 0a 09 7d 0a 0a 09 2f 2a 0a 09 20 2a n");..}.../*.. *
d370: 20 50 61 72 73 65 20 63 6f 6d 6d 61 6e 64 20 6c Parse command l
d380: 69 6e 65 20 61 72 67 75 6d 65 6e 74 73 0a 09 20 ine arguments..
d390: 2a 2f 0a 09 2f 2a 2a 0a 09 20 2a 2a 20 52 65 73 */../**.. ** Res
d3a0: 74 6f 72 65 20 61 72 67 63 2f 61 72 67 76 20 74 tore argc/argv t
d3b0: 6f 20 6f 72 69 67 69 6e 61 6c 20 76 61 6c 75 65 o original value
d3c0: 73 2c 20 72 65 70 6c 61 63 69 6e 67 20 61 72 67 s, replacing arg
d3d0: 76 5b 30 5d 20 69 6e 20 63 61 73 65 0a 09 20 2a v[0] in case.. *
d3e0: 2a 20 69 74 20 77 61 73 20 6d 6f 69 66 69 65 64 * it was moified
d3f0: 20 62 79 20 2d 2d 63 61 63 68 65 64 69 72 20 6f by --cachedir o
d400: 70 74 69 6f 6e 2e 0a 09 20 2a 2a 2f 0a 09 61 72 ption... **/..ar
d410: 67 63 2b 2b 3b 0a 09 61 72 67 76 2d 2d 3b 0a 09 gc++;..argv--;..
d420: 61 72 67 76 5b 30 5d 20 3d 20 61 72 67 76 30 3b argv[0] = argv0;
d430: 0a 0a 09 2f 2a 2a 0a 09 20 2a 2a 20 50 65 72 66 .../**.. ** Perf
d440: 6f 72 6d 20 74 68 65 20 61 72 67 75 6d 65 6e 74 orm the argument
d450: 20 70 61 72 73 69 6e 67 0a 09 20 2a 2a 2f 0a 09 parsing.. **/..
d460: 61 6f 70 5f 72 65 74 20 3d 20 61 70 70 66 73 5f aop_ret = appfs_
d470: 6f 70 74 5f 70 61 72 73 65 28 61 72 67 63 2c 20 opt_parse(argc,
d480: 61 72 67 76 2c 20 26 61 72 67 73 29 3b 0a 09 69 argv, &args);..i
d490: 66 20 28 61 6f 70 5f 72 65 74 20 21 3d 20 30 29 f (aop_ret != 0)
d4a0: 20 7b 0a 09 09 69 66 20 28 61 6f 70 5f 72 65 74 {...if (aop_ret
d4b0: 20 3c 20 30 29 20 7b 0a 09 09 09 72 65 74 75 72 < 0) {....retur
d4c0: 6e 28 30 29 3b 0a 09 09 7d 0a 0a 09 09 72 65 74 n(0);...}....ret
d4d0: 75 72 6e 28 61 6f 70 5f 72 65 74 29 3b 0a 09 7d urn(aop_ret);..}
d4e0: 0a 0a 09 2f 2a 0a 09 20 2a 20 43 72 65 61 74 65 .../*.. * Create
d4f0: 20 61 20 54 63 6c 20 69 6e 74 65 72 70 72 65 74 a Tcl interpret
d500: 65 72 20 6a 75 73 74 20 74 6f 20 76 65 72 69 66 er just to verif
d510: 79 20 74 68 61 74 20 74 68 69 6e 67 73 20 61 72 y that things ar
d520: 65 20 69 6e 20 77 6f 72 6b 69 6e 67 20 0a 09 20 e in working ..
d530: 2a 20 6f 72 64 65 72 20 62 65 66 6f 72 65 20 77 * order before w
d540: 65 20 62 65 63 6f 6d 65 20 61 20 64 61 65 6d 6f e become a daemo
d550: 6e 2e 0a 09 20 2a 2f 0a 09 74 65 73 74 5f 69 6e n... */..test_in
d560: 74 65 72 70 20 3d 20 61 70 70 66 73 5f 63 72 65 terp = appfs_cre
d570: 61 74 65 5f 54 63 6c 49 6e 74 65 72 70 28 26 74 ate_TclInterp(&t
d580: 65 73 74 5f 69 6e 74 65 72 70 5f 65 72 72 6f 72 est_interp_error
d590: 29 3b 0a 09 69 66 20 28 74 65 73 74 5f 69 6e 74 );..if (test_int
d5a0: 65 72 70 20 3d 3d 20 4e 55 4c 4c 29 20 7b 0a 09 erp == NULL) {..
d5b0: 09 69 66 20 28 74 65 73 74 5f 69 6e 74 65 72 70 .if (test_interp
d5c0: 5f 65 72 72 6f 72 20 3d 3d 20 4e 55 4c 4c 29 20 _error == NULL)
d5d0: 7b 0a 09 09 09 74 65 73 74 5f 69 6e 74 65 72 70 {....test_interp
d5e0: 5f 65 72 72 6f 72 20 3d 20 22 55 6e 6b 6e 6f 77 _error = "Unknow
d5f0: 6e 20 65 72 72 6f 72 22 3b 0a 09 09 7d 0a 0a 09 n error";...}...
d600: 09 66 70 72 69 6e 74 66 28 73 74 64 65 72 72 2c .fprintf(stderr,
d610: 20 22 55 6e 61 62 6c 65 20 74 6f 20 69 6e 69 74 "Unable to init
d620: 69 61 6c 69 7a 65 20 54 63 6c 20 69 6e 74 65 72 ialize Tcl inter
d630: 70 72 65 74 65 72 20 66 6f 72 20 41 70 70 46 53 preter for AppFS
d640: 64 3a 5c 6e 22 29 3b 0a 09 09 66 70 72 69 6e 74 d:\n");...fprint
d650: 66 28 73 74 64 65 72 72 2c 20 22 25 73 5c 6e 22 f(stderr, "%s\n"
d660: 2c 20 74 65 73 74 5f 69 6e 74 65 72 70 5f 65 72 , test_interp_er
d670: 72 6f 72 29 3b 0a 0a 09 09 72 65 74 75 72 6e 28 ror);....return(
d680: 31 29 3b 0a 09 7d 0a 0a 09 54 63 6c 5f 44 65 6c 1);..}...Tcl_Del
d690: 65 74 65 49 6e 74 65 72 70 28 74 65 73 74 5f 69 eteInterp(test_i
d6a0: 6e 74 65 72 70 29 3b 0a 0a 09 69 66 20 28 61 70 nterp);...if (ap
d6b0: 70 66 73 5f 74 68 72 65 61 64 65 64 5f 74 63 6c pfs_threaded_tcl
d6c0: 29 20 7b 0a 09 09 54 63 6c 5f 46 69 6e 61 6c 69 ) {...Tcl_Finali
d6d0: 7a 65 4e 6f 74 69 66 69 65 72 28 4e 55 4c 4c 29 zeNotifier(NULL)
d6e0: 3b 0a 09 7d 0a 0a 09 2f 2a 0a 09 20 2a 20 49 6e ;..}.../*.. * In
d6f0: 63 72 65 61 73 65 20 72 65 73 6f 75 72 63 65 20 crease resource
d700: 6c 69 6d 69 74 73 20 66 6f 72 20 6e 75 6d 62 65 limits for numbe
d710: 72 20 6f 66 20 6f 70 65 6e 20 66 69 6c 65 73 0a r of open files.
d720: 09 20 2a 20 74 6f 20 74 68 65 20 6d 61 78 69 6d . * to the maxim
d730: 75 6d 20 76 61 6c 75 65 73 2c 20 73 69 6e 63 65 um values, since
d740: 20 77 65 20 6d 61 79 20 62 65 20 61 73 6b 65 64 we may be asked
d750: 20 74 6f 0a 09 20 2a 20 68 6f 6c 64 20 6f 70 65 to.. * hold ope
d760: 6e 20 6d 61 6e 79 20 66 69 6c 65 73 20 6f 6e 20 n many files on
d770: 62 65 68 61 6c 66 20 6f 66 20 6d 61 6e 79 20 6f behalf of many o
d780: 74 68 65 72 20 70 72 6f 63 65 73 73 65 73 0a 09 ther processes..
d790: 20 2a 2f 0a 09 6e 75 6d 62 65 72 5f 6f 70 65 6e */..number_open
d7a0: 5f 66 69 6c 65 73 2e 72 6c 69 6d 5f 63 75 72 20 _files.rlim_cur
d7b0: 3d 20 6e 75 6d 62 65 72 5f 6f 70 65 6e 5f 66 69 = number_open_fi
d7c0: 6c 65 73 2e 72 6c 69 6d 5f 6d 61 78 20 3d 20 52 les.rlim_max = R
d7d0: 4c 49 4d 5f 49 4e 46 49 4e 49 54 59 3b 0a 0a 09 LIM_INFINITY;...
d7e0: 72 6c 69 6d 69 74 5f 72 65 74 20 3d 20 73 65 74 rlimit_ret = set
d7f0: 72 6c 69 6d 69 74 28 52 4c 49 4d 49 54 5f 4e 4f rlimit(RLIMIT_NO
d800: 46 49 4c 45 2c 20 26 6e 75 6d 62 65 72 5f 6f 70 FILE, &number_op
d810: 65 6e 5f 66 69 6c 65 73 29 3b 0a 0a 09 69 66 20 en_files);...if
d820: 28 72 6c 69 6d 69 74 5f 72 65 74 20 21 3d 20 30 (rlimit_ret != 0
d830: 29 20 7b 0a 09 09 72 6c 69 6d 69 74 5f 72 65 74 ) {...rlimit_ret
d840: 20 3d 20 67 65 74 72 6c 69 6d 69 74 28 52 4c 49 = getrlimit(RLI
d850: 4d 49 54 5f 4e 4f 46 49 4c 45 2c 20 26 6e 75 6d MIT_NOFILE, &num
d860: 62 65 72 5f 6f 70 65 6e 5f 66 69 6c 65 73 29 3b ber_open_files);
d870: 0a 09 09 69 66 20 28 72 6c 69 6d 69 74 5f 72 65 ...if (rlimit_re
d880: 74 20 3d 3d 20 30 29 20 7b 0a 09 09 09 6e 75 6d t == 0) {....num
d890: 62 65 72 5f 6f 70 65 6e 5f 66 69 6c 65 73 5f 6d ber_open_files_m
d8a0: 61 78 20 3d 20 6e 75 6d 62 65 72 5f 6f 70 65 6e ax = number_open
d8b0: 5f 66 69 6c 65 73 2e 72 6c 69 6d 5f 6d 61 78 3b _files.rlim_max;
d8c0: 0a 0a 09 09 09 69 66 20 28 6e 75 6d 62 65 72 5f .....if (number_
d8d0: 6f 70 65 6e 5f 66 69 6c 65 73 5f 6d 61 78 20 3c open_files_max <
d8e0: 20 28 31 30 32 34 20 2a 20 31 30 32 34 29 29 20 (1024 * 1024))
d8f0: 7b 0a 09 09 09 09 6e 75 6d 62 65 72 5f 6f 70 65 {.....number_ope
d900: 6e 5f 66 69 6c 65 73 2e 72 6c 69 6d 5f 63 75 72 n_files.rlim_cur
d910: 20 3d 20 6e 75 6d 62 65 72 5f 6f 70 65 6e 5f 66 = number_open_f
d920: 69 6c 65 73 2e 72 6c 69 6d 5f 6d 61 78 20 3d 20 iles.rlim_max =
d930: 31 30 32 34 20 2a 20 31 30 32 34 3b 0a 0a 09 09 1024 * 1024;....
d940: 09 09 72 6c 69 6d 69 74 5f 72 65 74 20 3d 20 73 ..rlimit_ret = s
d950: 65 74 72 6c 69 6d 69 74 28 52 4c 49 4d 49 54 5f etrlimit(RLIMIT_
d960: 4e 4f 46 49 4c 45 2c 20 26 6e 75 6d 62 65 72 5f NOFILE, &number_
d970: 6f 70 65 6e 5f 66 69 6c 65 73 29 3b 0a 09 09 09 open_files);....
d980: 7d 20 65 6c 73 65 20 7b 0a 09 09 09 09 6e 75 6d } else {.....num
d990: 62 65 72 5f 6f 70 65 6e 5f 66 69 6c 65 73 2e 72 ber_open_files.r
d9a0: 6c 69 6d 5f 63 75 72 20 3d 20 6e 75 6d 62 65 72 lim_cur = number
d9b0: 5f 6f 70 65 6e 5f 66 69 6c 65 73 2e 72 6c 69 6d _open_files.rlim
d9c0: 5f 6d 61 78 3b 0a 09 09 09 7d 0a 0a 09 09 09 72 _max;....}.....r
d9d0: 6c 69 6d 69 74 5f 72 65 74 20 3d 20 73 65 74 72 limit_ret = setr
d9e0: 6c 69 6d 69 74 28 52 4c 49 4d 49 54 5f 4e 4f 46 limit(RLIMIT_NOF
d9f0: 49 4c 45 2c 20 26 6e 75 6d 62 65 72 5f 6f 70 65 ILE, &number_ope
da00: 6e 5f 66 69 6c 65 73 29 3b 0a 0a 09 09 09 69 66 n_files);.....if
da10: 20 28 72 6c 69 6d 69 74 5f 72 65 74 20 21 3d 20 (rlimit_ret !=
da20: 30 20 26 26 20 6e 75 6d 62 65 72 5f 6f 70 65 6e 0 && number_open
da30: 5f 66 69 6c 65 73 2e 72 6c 69 6d 5f 63 75 72 20 _files.rlim_cur
da40: 21 3d 20 6e 75 6d 62 65 72 5f 6f 70 65 6e 5f 66 != number_open_f
da50: 69 6c 65 73 5f 6d 61 78 29 20 7b 0a 09 09 09 09 iles_max) {.....
da60: 6e 75 6d 62 65 72 5f 6f 70 65 6e 5f 66 69 6c 65 number_open_file
da70: 73 2e 72 6c 69 6d 5f 63 75 72 20 3d 20 6e 75 6d s.rlim_cur = num
da80: 62 65 72 5f 6f 70 65 6e 5f 66 69 6c 65 73 2e 72 ber_open_files.r
da90: 6c 69 6d 5f 6d 61 78 20 3d 20 6e 75 6d 62 65 72 lim_max = number
daa0: 5f 6f 70 65 6e 5f 66 69 6c 65 73 5f 6d 61 78 3b _open_files_max;
dab0: 0a 0a 09 09 09 09 73 65 74 72 6c 69 6d 69 74 28 ......setrlimit(
dac0: 52 4c 49 4d 49 54 5f 4e 4f 46 49 4c 45 2c 20 26 RLIMIT_NOFILE, &
dad0: 6e 75 6d 62 65 72 5f 6f 70 65 6e 5f 66 69 6c 65 number_open_file
dae0: 73 29 3b 0a 09 09 09 7d 0a 09 09 7d 0a 09 7d 0a s);....}...}..}.
daf0: 0a 0a 09 2f 2a 0a 09 20 2a 20 45 6e 74 65 72 20 .../*.. * Enter
db00: 74 68 65 20 46 55 53 45 20 6d 61 69 6e 20 6c 6f the FUSE main lo
db10: 6f 70 20 2d 2d 20 74 68 69 73 20 77 69 6c 6c 20 op -- this will
db20: 70 72 6f 63 65 73 73 20 61 6e 79 20 61 72 67 75 process any argu
db30: 6d 65 6e 74 73 0a 09 20 2a 20 61 6e 64 20 73 74 ments.. * and st
db40: 61 72 74 20 73 65 72 76 69 63 69 6e 67 20 72 65 art servicing re
db50: 71 75 65 73 74 73 2e 0a 09 20 2a 2f 0a 09 61 70 quests... */..ap
db60: 70 66 73 5f 66 75 73 65 5f 73 74 61 72 74 65 64 pfs_fuse_started
db70: 20 3d 20 31 3b 0a 09 72 65 74 75 72 6e 28 66 75 = 1;..return(fu
db80: 73 65 5f 6d 61 69 6e 28 61 72 67 73 2e 61 72 67 se_main(args.arg
db90: 63 2c 20 61 72 67 73 2e 61 72 67 76 2c 20 26 61 c, args.argv, &a
dba0: 70 70 66 73 5f 6f 70 65 72 61 74 69 6f 6e 73 2c ppfs_operations,
dbb0: 20 4e 55 4c 4c 29 29 3b 0a 7d 0a NULL));.}.