summaryrefslogtreecommitdiffstats
path: root/generic/tclFCmd.c
diff options
context:
space:
mode:
Diffstat (limited to 'generic/tclFCmd.c')
-rw-r--r--generic/tclFCmd.c21
1 files changed, 12 insertions, 9 deletions
diff --git a/generic/tclFCmd.c b/generic/tclFCmd.c
index 53f955f..5850846 100644
--- a/generic/tclFCmd.c
+++ b/generic/tclFCmd.c
@@ -950,7 +950,7 @@ TclFileAttrsCmd(
int result;
CONST char ** attributeStrings;
Tcl_Obj* objStrings = NULL;
- int numObjStrings = -1;
+ int numObjStrings = -1, didAlloc = 0;
Tcl_Obj *filePtr;
if (objc < 3) {
@@ -983,9 +983,8 @@ TclFileAttrsCmd(
Tcl_AppendResult(interp, "could not read \"",
TclGetString(filePtr), "\": ", Tcl_PosixError(interp),
NULL);
- return TCL_ERROR;
}
- goto end;
+ return TCL_ERROR;
}
/*
@@ -1003,12 +1002,16 @@ TclFileAttrsCmd(
}
attributeStrings = (CONST char **) TclStackAlloc(interp,
(1+numObjStrings) * sizeof(char*));
+ didAlloc = 1;
for (index = 0; index < numObjStrings; index++) {
Tcl_ListObjIndex(interp, objStrings, index, &objPtr);
attributeStrings[index] = TclGetString(objPtr);
}
attributeStrings[index] = NULL;
+ } else if (objStrings != NULL) {
+ Tcl_Panic("must not update objPtrRef's variable and return non-NULL");
}
+
if (objc == 0) {
/*
* Get all attributes.
@@ -1069,7 +1072,7 @@ TclFileAttrsCmd(
"option", 0, &index) != TCL_OK) {
goto end;
}
- if (numObjStrings != -1) {
+ if (didAlloc) {
TclFreeIntRep(objv[0]);
}
if (Tcl_FSFileAttrsGet(interp, index, filePtr,
@@ -1096,7 +1099,7 @@ TclFileAttrsCmd(
"option", 0, &index) != TCL_OK) {
goto end;
}
- if (numObjStrings != -1) {
+ if (didAlloc) {
TclFreeIntRep(objv[i]);
}
if (i + 1 == objc) {
@@ -1113,20 +1116,20 @@ TclFileAttrsCmd(
result = TCL_OK;
end:
- if (numObjStrings != -1) {
+ if (didAlloc) {
/*
* Free up the array we allocated.
*/
TclStackFree(interp, (void *)attributeStrings);
+ }
+ if (objStrings != NULL) {
/*
* We don't need this object that was passed to us any more.
*/
- if (objStrings != NULL) {
- Tcl_DecrRefCount(objStrings);
- }
+ Tcl_DecrRefCount(objStrings);
}
return result;
}