Many hyperlinks are disabled.
Use anonymous login
to enable hyperlinks.
Overview
Comment: | Stop storing FilesystemRecord in the intrep of a "path". We never use it. Store the Tcl_Filesystem instead, which is what we actually need. |
---|---|
Downloads: | Tarball | ZIP archive | SQL archive |
Timelines: | family | ancestors | descendants | both | core-8-5-branch |
Files: | files | file ages | folders |
SHA1: |
157337f9dd17f221b47569eacfd68a54 |
User & Date: | dgp 2012-06-21 17:48:37 |
Context
2012-06-22
| ||
16:43 | Revise the order of memory free, so that bugs that attempt to access freed memory are more likely to... check-in: 6e6da30161 user: dgp tags: core-8-5-branch | |
13:41 | Locale guessing of msgcat fails on (some) Windows 7 check-in: a494196214 user: jan.nijtmans tags: bug-3536888 | |
12:07 | Cygwin network pathname support Closed-Leaf check-in: 2194dfa1f7 user: jan.nijtmans tags: bug-1536227 | |
2012-06-21
| ||
18:38 | merge 8.5 check-in: f0d8295d3b user: dgp tags: bug-3024359 | |
18:03 | Stop storing FilesystemRecord in the intrep of a "path". We never use it. Store the Tcl_Filesystem i... check-in: 617b36da35 user: dgp tags: trunk | |
17:48 | Stop storing FilesystemRecord in the intrep of a "path". We never use it. Store the Tcl_Filesystem ... check-in: 157337f9dd user: dgp tags: core-8-5-branch | |
11:02 | [Bug 3362446]: possible allocation error when using UNICODE check-in: 38a393d995 user: jan.nijtmans tags: core-8-5-branch | |
Changes
Changes to generic/tclFileSystem.h.
︙ | ︙ | |||
64 65 66 67 68 69 70 | MODULE_SCOPE int TclFSCwdPointerEquals(Tcl_Obj **pathPtrPtr); MODULE_SCOPE int TclFSMakePathFromNormalized(Tcl_Interp *interp, Tcl_Obj *pathPtr); MODULE_SCOPE int TclFSNormalizeToUniquePath(Tcl_Interp *interp, Tcl_Obj *pathPtr, int startAt); MODULE_SCOPE Tcl_Obj * TclFSMakePathRelative(Tcl_Interp *interp, Tcl_Obj *pathPtr, Tcl_Obj *cwdPtr); | < < < < < | | 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 | MODULE_SCOPE int TclFSCwdPointerEquals(Tcl_Obj **pathPtrPtr); MODULE_SCOPE int TclFSMakePathFromNormalized(Tcl_Interp *interp, Tcl_Obj *pathPtr); MODULE_SCOPE int TclFSNormalizeToUniquePath(Tcl_Interp *interp, Tcl_Obj *pathPtr, int startAt); MODULE_SCOPE Tcl_Obj * TclFSMakePathRelative(Tcl_Interp *interp, Tcl_Obj *pathPtr, Tcl_Obj *cwdPtr); MODULE_SCOPE int TclFSEnsureEpochOk(Tcl_Obj *pathPtr, Tcl_Filesystem **fsPtrPtr); MODULE_SCOPE void TclFSSetPathDetails(Tcl_Obj *pathPtr, Tcl_Filesystem *fsPtr, ClientData clientData); MODULE_SCOPE Tcl_Obj * TclFSNormalizeAbsolutePath(Tcl_Interp *interp, Tcl_Obj *pathPtr); /* * Private shared variables for use by tclIOUtil.c and tclPathObj.c */ |
︙ | ︙ |
Changes to generic/tclIOUtil.c.
︙ | ︙ | |||
3809 3810 3811 3812 3813 3814 3815 | */ if (lenPtr != NULL) { TclListObjLength(NULL, result, lenPtr); } return result; } | < < < < < < < < < < < < < < < < < < < < < < < < < | 3809 3810 3811 3812 3813 3814 3815 3816 3817 3818 3819 3820 3821 3822 | */ if (lenPtr != NULL) { TclListObjLength(NULL, result, lenPtr); } return result; } /* *---------------------------------------------------------------------- * * TclGetPathType -- * * Helper function used by FSGetPathType. |
︙ | ︙ | |||
4432 4433 4434 4435 4436 4437 4438 | ClientData clientData = NULL; if ((*proc)(pathPtr, &clientData) != -1) { /* * We assume the type of pathPtr hasn't been changed by the * above call to the pathInFilesystemProc. */ | | | 4407 4408 4409 4410 4411 4412 4413 4414 4415 4416 4417 4418 4419 4420 4421 | ClientData clientData = NULL; if ((*proc)(pathPtr, &clientData) != -1) { /* * We assume the type of pathPtr hasn't been changed by the * above call to the pathInFilesystemProc. */ TclFSSetPathDetails(pathPtr, fsRecPtr->fsPtr, clientData); retVal = fsRecPtr->fsPtr; } } fsRecPtr = fsRecPtr->nextPtr; } return retVal; |
︙ | ︙ |
Changes to generic/tclPathObj.c.
︙ | ︙ | |||
88 89 90 91 92 93 94 | * below. */ ClientData nativePathPtr; /* Native representation of this path, which * is filesystem dependent. */ int filesystemEpoch; /* Used to ensure the path representation was * generated during the correct filesystem * epoch. The epoch changes when * filesystem-mounts are changed. */ | | < < | 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 | * below. */ ClientData nativePathPtr; /* Native representation of this path, which * is filesystem dependent. */ int filesystemEpoch; /* Used to ensure the path representation was * generated during the correct filesystem * epoch. The epoch changes when * filesystem-mounts are changed. */ Tcl_Filesystem *fsPtr; /* The Tcl_Filesystem that claims this path */ } FsPath; /* * Flag values for FsPath->flags. */ #define TCLPATH_APPENDED 1 |
︙ | ︙ | |||
1308 1309 1310 1311 1312 1313 1314 | fsPathPtr->translatedPathPtr = NULL; fsPathPtr->normPathPtr = Tcl_NewStringObj(addStrRep, len); Tcl_IncrRefCount(fsPathPtr->normPathPtr); fsPathPtr->cwdPtr = dirPtr; Tcl_IncrRefCount(dirPtr); fsPathPtr->nativePathPtr = NULL; | | | 1306 1307 1308 1309 1310 1311 1312 1313 1314 1315 1316 1317 1318 1319 1320 | fsPathPtr->translatedPathPtr = NULL; fsPathPtr->normPathPtr = Tcl_NewStringObj(addStrRep, len); Tcl_IncrRefCount(fsPathPtr->normPathPtr); fsPathPtr->cwdPtr = dirPtr; Tcl_IncrRefCount(dirPtr); fsPathPtr->nativePathPtr = NULL; fsPathPtr->fsPtr = NULL; fsPathPtr->filesystemEpoch = tsdPtr->filesystemEpoch; SETPATHOBJ(pathPtr, fsPathPtr); PATHFLAGS(pathPtr) = TCLPATH_APPENDED; pathPtr->typePtr = &tclFsPathType; pathPtr->bytes = NULL; pathPtr->length = 0; |
︙ | ︙ | |||
1429 1430 1431 1432 1433 1434 1435 | pathPtr = fsPathPtr->normPathPtr; /* TODO: Determine how much, if any, of this forcing * the relative path tail into the "path" Tcl_ObjType * with a recorded cwdPtr context has any actual value. * * Nothing is getting cached. Not normPathPtr, not nativePathPtr, | | | 1427 1428 1429 1430 1431 1432 1433 1434 1435 1436 1437 1438 1439 1440 1441 | pathPtr = fsPathPtr->normPathPtr; /* TODO: Determine how much, if any, of this forcing * the relative path tail into the "path" Tcl_ObjType * with a recorded cwdPtr context has any actual value. * * Nothing is getting cached. Not normPathPtr, not nativePathPtr, * nor fsPtr, so storing the cwdPtr context against which such * cached values might later be validated appears to be of no * value. Take that away, and all this code is just a mildly * optimized equivalent of a call to SetFsPathFromAny(). That * optimization may have some value, *if* these value in fact * get used as "path" values before used as something else. * If not, though, whatever cost we pay below to convert to * one of the "path" intreps is just a waste, it seems. The |
︙ | ︙ | |||
1478 1479 1480 1481 1482 1483 1484 | */ fsPathPtr->translatedPathPtr = pathPtr; fsPathPtr->normPathPtr = NULL; fsPathPtr->cwdPtr = cwdPtr; Tcl_IncrRefCount(cwdPtr); fsPathPtr->nativePathPtr = NULL; | | | 1476 1477 1478 1479 1480 1481 1482 1483 1484 1485 1486 1487 1488 1489 1490 | */ fsPathPtr->translatedPathPtr = pathPtr; fsPathPtr->normPathPtr = NULL; fsPathPtr->cwdPtr = cwdPtr; Tcl_IncrRefCount(cwdPtr); fsPathPtr->nativePathPtr = NULL; fsPathPtr->fsPtr = NULL; fsPathPtr->filesystemEpoch = tsdPtr->filesystemEpoch; SETPATHOBJ(pathPtr, fsPathPtr); PATHFLAGS(pathPtr) = 0; pathPtr->typePtr = &tclFsPathType; return pathPtr; |
︙ | ︙ | |||
1588 1589 1590 1591 1592 1593 1594 | /* * Circular reference by design. */ fsPathPtr->normPathPtr = pathPtr; fsPathPtr->cwdPtr = NULL; fsPathPtr->nativePathPtr = NULL; | | | 1586 1587 1588 1589 1590 1591 1592 1593 1594 1595 1596 1597 1598 1599 1600 | /* * Circular reference by design. */ fsPathPtr->normPathPtr = pathPtr; fsPathPtr->cwdPtr = NULL; fsPathPtr->nativePathPtr = NULL; fsPathPtr->fsPtr = NULL; fsPathPtr->filesystemEpoch = tsdPtr->filesystemEpoch; SETPATHOBJ(pathPtr, fsPathPtr); PATHFLAGS(pathPtr) = 0; pathPtr->typePtr = &tclFsPathType; return TCL_OK; |
︙ | ︙ | |||
1628 1629 1630 1631 1632 1633 1634 | */ Tcl_Obj * Tcl_FSNewNativePath( Tcl_Filesystem *fromFilesystem, ClientData clientData) { | | < | < > > | 1626 1627 1628 1629 1630 1631 1632 1633 1634 1635 1636 1637 1638 1639 1640 1641 1642 1643 1644 1645 1646 1647 | */ Tcl_Obj * Tcl_FSNewNativePath( Tcl_Filesystem *fromFilesystem, ClientData clientData) { Tcl_Obj *pathPtr = NULL; FsPath *fsPathPtr; ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&tclFsDataKey); if (fromFilesystem->internalToNormalizedProc != NULL) { pathPtr = (*fromFilesystem->internalToNormalizedProc)(clientData); } if (pathPtr == NULL) { return NULL; } /* * Free old representation; shouldn't normally be any, but best to be * safe. |
︙ | ︙ | |||
1666 1667 1668 1669 1670 1671 1672 | /* * Circular reference, by design. */ fsPathPtr->normPathPtr = pathPtr; fsPathPtr->cwdPtr = NULL; fsPathPtr->nativePathPtr = clientData; | | < | 1664 1665 1666 1667 1668 1669 1670 1671 1672 1673 1674 1675 1676 1677 1678 | /* * Circular reference, by design. */ fsPathPtr->normPathPtr = pathPtr; fsPathPtr->cwdPtr = NULL; fsPathPtr->nativePathPtr = clientData; fsPathPtr->fsPtr = fromFilesystem; fsPathPtr->filesystemEpoch = tsdPtr->filesystemEpoch; SETPATHOBJ(pathPtr, fsPathPtr); PATHFLAGS(pathPtr) = 0; pathPtr->typePtr = &tclFsPathType; return pathPtr; |
︙ | ︙ | |||
2124 2125 2126 2127 2128 2129 2130 | * this is a potentially useful feature for the future. * * Even something simple like a 'pass through' filesystem which logs all * activity and passes the calls onto the native system would be nice, but * not easily achievable with the current implementation. */ | | | | | | 2121 2122 2123 2124 2125 2126 2127 2128 2129 2130 2131 2132 2133 2134 2135 2136 2137 2138 2139 2140 2141 2142 2143 2144 2145 2146 2147 2148 2149 2150 2151 2152 2153 2154 2155 2156 2157 2158 2159 2160 2161 2162 2163 2164 2165 2166 2167 2168 2169 2170 2171 2172 2173 2174 2175 2176 2177 2178 2179 2180 | * this is a potentially useful feature for the future. * * Even something simple like a 'pass through' filesystem which logs all * activity and passes the calls onto the native system would be nice, but * not easily achievable with the current implementation. */ if (srcFsPathPtr->fsPtr == NULL) { /* * This only usually happens in wrappers like TclpStat which create a * string object and pass it to TclpObjStat. Code which calls the * Tcl_FS.. functions should always have a filesystem already set. * Whether this code path is legal or not depends on whether we decide * to allow external code to call the native filesystem directly. It * is at least safer to allow this sub-optimal routing. */ Tcl_FSGetFileSystemForPath(pathPtr); /* * If we fail through here, then the path is probably not a valid path * in the filesystsem, and is most likely to be a use of the empty * path "" via a direct call to one of the objectified interfaces * (e.g. from the Tcl testsuite). */ srcFsPathPtr = PATHOBJ(pathPtr); if (srcFsPathPtr->fsPtr == NULL) { return NULL; } } /* * There is still one possibility we should consider; if the file belongs * to a different filesystem, perhaps it is actually linked through to a * file in our own filesystem which we do care about. The way we can check * for this is we ask what filesystem this path belongs to. */ if (fsPtr != srcFsPathPtr->fsPtr) { const Tcl_Filesystem *actualFs = Tcl_FSGetFileSystemForPath(pathPtr); if (actualFs == fsPtr) { return Tcl_FSGetInternalRep(pathPtr, fsPtr); } return NULL; } if (srcFsPathPtr->nativePathPtr == NULL) { Tcl_FSCreateInternalRepProc *proc; char *nativePathPtr; proc = srcFsPathPtr->fsPtr->createInternalRepProc; if (proc == NULL) { return NULL; } nativePathPtr = (*proc)(pathPtr); srcFsPathPtr = PATHOBJ(pathPtr); srcFsPathPtr->nativePathPtr = nativePathPtr; |
︙ | ︙ | |||
2237 2238 2239 2240 2241 2242 2243 | srcFsPathPtr = PATHOBJ(pathPtr); } /* * Check whether the object is already assigned to a fs. */ | | | | 2234 2235 2236 2237 2238 2239 2240 2241 2242 2243 2244 2245 2246 2247 2248 2249 | srcFsPathPtr = PATHOBJ(pathPtr); } /* * Check whether the object is already assigned to a fs. */ if (srcFsPathPtr->fsPtr != NULL) { *fsPtrPtr = srcFsPathPtr->fsPtr; } return TCL_OK; } /* *--------------------------------------------------------------------------- * |
︙ | ︙ | |||
2262 2263 2264 2265 2266 2267 2268 | * *--------------------------------------------------------------------------- */ void TclFSSetPathDetails( Tcl_Obj *pathPtr, | | | < | 2259 2260 2261 2262 2263 2264 2265 2266 2267 2268 2269 2270 2271 2272 2273 2274 2275 2276 2277 2278 2279 2280 2281 2282 2283 2284 2285 2286 2287 2288 2289 2290 2291 2292 | * *--------------------------------------------------------------------------- */ void TclFSSetPathDetails( Tcl_Obj *pathPtr, Tcl_Filesystem *fsPtr, ClientData clientData) { ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&tclFsDataKey); FsPath *srcFsPathPtr; /* * Make sure pathPtr is of the correct type. */ if (pathPtr->typePtr != &tclFsPathType) { if (SetFsPathFromAny(NULL, pathPtr) != TCL_OK) { return; } } srcFsPathPtr = PATHOBJ(pathPtr); srcFsPathPtr->fsPtr = fsPtr; srcFsPathPtr->nativePathPtr = clientData; srcFsPathPtr->filesystemEpoch = tsdPtr->filesystemEpoch; } /* *--------------------------------------------------------------------------- * * Tcl_FSEqualPaths -- * |
︙ | ︙ | |||
2531 2532 2533 2534 2535 2536 2537 | fsPathPtr->translatedPathPtr = transPtr; if (transPtr != pathPtr) { Tcl_IncrRefCount(fsPathPtr->translatedPathPtr); } fsPathPtr->normPathPtr = NULL; fsPathPtr->cwdPtr = NULL; fsPathPtr->nativePathPtr = NULL; | | | 2527 2528 2529 2530 2531 2532 2533 2534 2535 2536 2537 2538 2539 2540 2541 | fsPathPtr->translatedPathPtr = transPtr; if (transPtr != pathPtr) { Tcl_IncrRefCount(fsPathPtr->translatedPathPtr); } fsPathPtr->normPathPtr = NULL; fsPathPtr->cwdPtr = NULL; fsPathPtr->nativePathPtr = NULL; fsPathPtr->fsPtr = NULL; fsPathPtr->filesystemEpoch = tsdPtr->filesystemEpoch; /* * Free old representation before installing our new one. */ TclFreeIntRep(pathPtr); |
︙ | ︙ | |||
2565 2566 2567 2568 2569 2570 2571 | TclDecrRefCount(fsPathPtr->normPathPtr); } fsPathPtr->normPathPtr = NULL; } if (fsPathPtr->cwdPtr != NULL) { TclDecrRefCount(fsPathPtr->cwdPtr); } | | | < < < < < < < < < < | 2561 2562 2563 2564 2565 2566 2567 2568 2569 2570 2571 2572 2573 2574 2575 2576 2577 2578 2579 2580 2581 2582 | TclDecrRefCount(fsPathPtr->normPathPtr); } fsPathPtr->normPathPtr = NULL; } if (fsPathPtr->cwdPtr != NULL) { TclDecrRefCount(fsPathPtr->cwdPtr); } if (fsPathPtr->nativePathPtr != NULL && fsPathPtr->fsPtr != NULL) { Tcl_FSFreeInternalRepProc *freeProc = fsPathPtr->fsPtr->freeInternalRepProc; if (freeProc != NULL) { (*freeProc)(fsPathPtr->nativePathPtr); fsPathPtr->nativePathPtr = NULL; } } ckfree((char *) fsPathPtr); pathPtr->typePtr = NULL; } static void |
︙ | ︙ | |||
2626 2627 2628 2629 2630 2631 2632 | copyFsPathPtr->cwdPtr = srcFsPathPtr->cwdPtr; if (copyFsPathPtr->cwdPtr != NULL) { Tcl_IncrRefCount(copyFsPathPtr->cwdPtr); } copyFsPathPtr->flags = srcFsPathPtr->flags; | | | | < < < | 2612 2613 2614 2615 2616 2617 2618 2619 2620 2621 2622 2623 2624 2625 2626 2627 2628 2629 2630 2631 2632 2633 2634 2635 2636 2637 2638 2639 2640 2641 | copyFsPathPtr->cwdPtr = srcFsPathPtr->cwdPtr; if (copyFsPathPtr->cwdPtr != NULL) { Tcl_IncrRefCount(copyFsPathPtr->cwdPtr); } copyFsPathPtr->flags = srcFsPathPtr->flags; if (srcFsPathPtr->fsPtr != NULL && srcFsPathPtr->nativePathPtr != NULL) { Tcl_FSDupInternalRepProc *dupProc = srcFsPathPtr->fsPtr->dupInternalRepProc; if (dupProc != NULL) { copyFsPathPtr->nativePathPtr = (*dupProc)(srcFsPathPtr->nativePathPtr); } else { copyFsPathPtr->nativePathPtr = NULL; } } else { copyFsPathPtr->nativePathPtr = NULL; } copyFsPathPtr->fsPtr = srcFsPathPtr->fsPtr; copyFsPathPtr->filesystemEpoch = srcFsPathPtr->filesystemEpoch; copyPtr->typePtr = &tclFsPathType; } /* *--------------------------------------------------------------------------- * |
︙ | ︙ |