summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--generic/tkText.h2
-rw-r--r--generic/tkTextImage.c23
-rw-r--r--generic/tkTextIndex.c70
-rw-r--r--generic/tkTextMark.c23
-rw-r--r--generic/tkTextWind.c23
-rw-r--r--tests/textIndex.test37
-rw-r--r--tests/textMark.test11
7 files changed, 155 insertions, 34 deletions
diff --git a/generic/tkText.h b/generic/tkText.h
index e9e6303..faa6014 100644
--- a/generic/tkText.h
+++ b/generic/tkText.h
@@ -1170,6 +1170,8 @@ MODULE_SCOPE int TkTextYviewCmd(TkText *textPtr, Tcl_Interp *interp,
MODULE_SCOPE void TkTextWinFreeClient(Tcl_HashEntry *hPtr,
TkTextEmbWindowClient *client);
MODULE_SCOPE void TkTextRunAfterSyncCmd(ClientData clientData);
+MODULE_SCOPE int TkTextIndexAdjustToStartEnd(TkText *textPtr,
+ TkTextIndex *indexPtr, int err);
#endif /* _TKTEXT */
/*
diff --git a/generic/tkTextImage.c b/generic/tkTextImage.c
index aeb5681..c5a7c84 100644
--- a/generic/tkTextImage.c
+++ b/generic/tkTextImage.c
@@ -769,9 +769,9 @@ EmbImageBboxProc(
* index corresponding to the image's position in the text.
*
* Results:
- * The return value is 1 if there is an embedded image by the given name
- * in the text widget, 0 otherwise. If the image exists, *indexPtr is
- * filled in with its index.
+ * The return value is TCL_OK if there is an embedded image by the given
+ * name in the text widget, TCL_ERROR otherwise. If the image exists,
+ * *indexPtr is filled in with its index.
*
* Side effects:
* None.
@@ -789,18 +789,29 @@ TkTextImageIndex(
TkTextSegment *eiPtr;
if (textPtr == NULL) {
- return 0;
+ return TCL_ERROR;
}
hPtr = Tcl_FindHashEntry(&textPtr->sharedTextPtr->imageTable, name);
if (hPtr == NULL) {
- return 0;
+ return TCL_ERROR;
}
eiPtr = (TkTextSegment *)Tcl_GetHashValue(hPtr);
indexPtr->tree = textPtr->sharedTextPtr->tree;
indexPtr->linePtr = eiPtr->body.ei.linePtr;
indexPtr->byteIndex = TkTextSegToOffset(eiPtr, indexPtr->linePtr);
- return 1;
+
+ /*
+ * If indexPtr refers to somewhere outside the -startline/-endline
+ * range limits of the widget, error out since the image indeed is not
+ * reachable from this text widget (it may be reachable from a peer).
+ */
+
+ if (TkTextIndexAdjustToStartEnd(textPtr, indexPtr, 1) == TCL_ERROR) {
+ return TCL_ERROR;
+ }
+
+ return TCL_OK;
}
/*
diff --git a/generic/tkTextIndex.c b/generic/tkTextIndex.c
index ade889b..bd93258 100644
--- a/generic/tkTextIndex.c
+++ b/generic/tkTextIndex.c
@@ -761,11 +761,11 @@ GetIndex(
goto done;
}
- if (TkTextWindowIndex(textPtr, string, indexPtr) != 0) {
+ if (TkTextWindowIndex(textPtr, string, indexPtr) == TCL_OK) {
goto done;
}
- if (TkTextImageIndex(textPtr, string, indexPtr) != 0) {
+ if (TkTextImageIndex(textPtr, string, indexPtr) == TCL_OK) {
goto done;
}
@@ -917,7 +917,7 @@ GetIndex(
*endOfBase = 0;
result = TkTextWindowIndex(textPtr, Tcl_DStringValue(&copy), indexPtr);
*endOfBase = c;
- if (result != 0) {
+ if (result == TCL_OK) {
goto gotBase;
}
}
@@ -954,7 +954,7 @@ GetIndex(
*endOfBase = 0;
result = TkTextImageIndex(textPtr, Tcl_DStringValue(&copy), indexPtr);
*endOfBase = c;
- if (result != 0) {
+ if (result == TCL_OK) {
goto gotBase;
}
}
@@ -997,6 +997,7 @@ GetIndex(
if (indexPtr->linePtr == NULL) {
Tcl_Panic("Bad index created");
}
+ TkTextIndexAdjustToStartEnd(textPtr, indexPtr, 0);
return TCL_OK;
error:
@@ -1009,6 +1010,67 @@ GetIndex(
/*
*---------------------------------------------------------------------------
*
+ * TkTextIndexAdjustToStartEnd --
+ *
+ * Adjust indexPtr to the -startline/-endline range, or just check
+ * if indexPtr is out of this range.
+ *
+ * Results:
+ * The return value is a standard Tcl return result. If check is true,
+ * return TCL_ERROR if indexPtr is outside the -startline/-endline
+ * range (indexPtr is not modified).
+ * If check is false, adjust indexPtr to -startline/-endline.
+ *
+ * Side effects:
+ * None.
+ *
+ *---------------------------------------------------------------------------
+ */
+
+int
+TkTextIndexAdjustToStartEnd(
+ TkText *textPtr,
+ TkTextIndex *indexPtr, /* Pointer to index. */
+ int check) /* 1 means only check indexPtr against
+ * the -startline/-endline range
+ * 0 means adjust to this range */
+{
+ int bound;
+ TkTextIndex indexBound;
+
+ if (!textPtr) {
+ return TCL_OK;
+ }
+ if (textPtr->start != NULL) {
+ bound = TkBTreeLinesTo(NULL, textPtr->start);
+ TkTextMakeByteIndex(textPtr->sharedTextPtr->tree, NULL, bound, 0,
+ &indexBound);
+ if (TkTextIndexCmp(indexPtr, &indexBound) < 0) {
+ if (check) {
+ return TCL_ERROR;
+ }
+ TkTextMakeByteIndex(textPtr->sharedTextPtr->tree, NULL, bound, 0,
+ indexPtr);
+ }
+ }
+ if (textPtr->end != NULL) {
+ bound = TkBTreeLinesTo(NULL, textPtr->end);
+ TkTextMakeByteIndex(textPtr->sharedTextPtr->tree, NULL, bound, 0,
+ &indexBound);
+ if (TkTextIndexCmp(indexPtr, &indexBound) > 0) {
+ if (check) {
+ return TCL_ERROR;
+ }
+ TkTextMakeByteIndex(textPtr->sharedTextPtr->tree, NULL, bound, 0,
+ indexPtr);
+ }
+ }
+ return TCL_OK;
+}
+
+/*
+ *---------------------------------------------------------------------------
+ *
* TkTextPrintIndex --
*
* This function generates a string description of an index, suitable for
diff --git a/generic/tkTextMark.c b/generic/tkTextMark.c
index 5d4b5d5..9efa222 100644
--- a/generic/tkTextMark.c
+++ b/generic/tkTextMark.c
@@ -434,8 +434,6 @@ TkTextMarkNameToIndex(
TkTextIndex *indexPtr) /* Index information gets stored here. */
{
TkTextSegment *segPtr;
- TkTextIndex index;
- int start, end;
if (textPtr == NULL) {
return TCL_ERROR;
@@ -456,28 +454,17 @@ TkTextMarkNameToIndex(
}
TkTextMarkSegToIndex(textPtr, segPtr, indexPtr);
- /* If indexPtr refers to somewhere outside the -startline/-endline
+ /*
+ * If indexPtr refers to somewhere outside the -startline/-endline
* range limits of the widget, error out since the mark indeed is not
* reachable from this text widget (it may be reachable from a peer)
* (bug 1630271).
*/
- if (textPtr->start != NULL) {
- start = TkBTreeLinesTo(NULL, textPtr->start);
- TkTextMakeByteIndex(textPtr->sharedTextPtr->tree, NULL, start, 0,
- &index);
- if (TkTextIndexCmp(indexPtr, &index) < 0) {
- return TCL_ERROR;
- }
- }
- if (textPtr->end != NULL) {
- end = TkBTreeLinesTo(NULL, textPtr->end);
- TkTextMakeByteIndex(textPtr->sharedTextPtr->tree, NULL, end, 0,
- &index);
- if (TkTextIndexCmp(indexPtr, &index) > 0) {
- return TCL_ERROR;
- }
+ if (TkTextIndexAdjustToStartEnd(textPtr, indexPtr, 1) == TCL_ERROR) {
+ return TCL_ERROR;
}
+
return TCL_OK;
}
diff --git a/generic/tkTextWind.c b/generic/tkTextWind.c
index adf1ad5..a43293f 100644
--- a/generic/tkTextWind.c
+++ b/generic/tkTextWind.c
@@ -1320,9 +1320,9 @@ EmbWinDelayedUnmap(
* index corresponding to the window's position in the text.
*
* Results:
- * The return value is 1 if there is an embedded window by the given name
- * in the text widget, 0 otherwise. If the window exists, *indexPtr is
- * filled in with its index.
+ * The return value is TCL_OK if there is an embedded window by the given
+ * name in the text widget, TCL_ERROR otherwise. If the window exists,
+ * *indexPtr is filled in with its index.
*
* Side effects:
* None.
@@ -1340,19 +1340,30 @@ TkTextWindowIndex(
TkTextSegment *ewPtr;
if (textPtr == NULL) {
- return 0;
+ return TCL_ERROR;
}
hPtr = Tcl_FindHashEntry(&textPtr->sharedTextPtr->windowTable, name);
if (hPtr == NULL) {
- return 0;
+ return TCL_ERROR;
}
ewPtr = (TkTextSegment *)Tcl_GetHashValue(hPtr);
indexPtr->tree = textPtr->sharedTextPtr->tree;
indexPtr->linePtr = ewPtr->body.ew.linePtr;
indexPtr->byteIndex = TkTextSegToOffset(ewPtr, indexPtr->linePtr);
- return 1;
+
+ /*
+ * If indexPtr refers to somewhere outside the -startline/-endline
+ * range limits of the widget, error out since the window indeed is not
+ * reachable from this text widget (it may be reachable from a peer).
+ */
+
+ if (TkTextIndexAdjustToStartEnd(textPtr, indexPtr, 1) == TCL_ERROR) {
+ return TCL_ERROR;
+ }
+
+ return TCL_OK;
}
/*
diff --git a/tests/textIndex.test b/tests/textIndex.test
index 2d42b8e..f2cccac 100644
--- a/tests/textIndex.test
+++ b/tests/textIndex.test
@@ -964,6 +964,43 @@ test textIndex-25.1 {IndexCountBytesOrdered, bug [3f1f79abcf]} {
destroy .t2
} {}
+test textIndex-26.1 {GetIndex restricts the returned index to -starline/-endline in peers, bug [34db75c0ac]} {
+ set res {}
+ pack [text .t2]
+ .t2 insert end "line 1\nline 2\nline 3\nline 4\nline 5\nline 6\n"
+ pack [.t2 peer create .p2 -startline 2 -endline 3]
+ lappend res [.p2 index "end"]
+ lappend res [.p2 index "end lineend"]
+ lappend res [.p2 index "end display lineend"]
+ destroy .t2 .p2
+ set res
+} {2.0 2.0 2.0}
+test textIndex-26.2 {GetIndex errors out if mark, image, window, or tag is outside peer -starline/-endline, bug [34db75c0ac]} {
+ set res {}
+ pack [text .t2]
+ .t2 insert end "line 1\nline 2\nline 3\nline 4\nline 5\nline 6\n"
+ pack [.t2 peer create .p2 -startline 2 -endline 3]
+ .p2 configure -startline 3 -endline {}
+ .t2 mark set mymark 1.0
+ catch {.p2 index mymark} msg
+ lappend res [.t2 index mymark] $msg
+ image create photo redsquare -width 5 -height 5
+ redsquare put red -to 0 0 4 4
+ .t2 image create 1.0 -image redsquare
+ catch {.p2 index redsquare} msg
+ lappend res [.t2 index redsquare] $msg
+ frame .f -width 10 -height 10 -bg blue
+ .t2 window create 1.2 -window .f
+ catch {.p2 index .f} msg
+ lappend res [.t2 index .f] $msg
+ .t2 tag add mytag 1.3
+ catch {.p2 index mytag.first} msg
+ lappend res [.t2 index mytag.first] $msg
+ destroy .t2 .p2
+ set res
+} {1.0 {bad text index "mymark"} 1.0 {bad text index "redsquare"} 1.2\
+ {bad text index ".f"} 1.3 {text doesn't contain any characters tagged with "mytag"}}
+
# cleanup
rename textimage {}
catch {destroy .t}
diff --git a/tests/textMark.test b/tests/textMark.test
index 938ce7f..bbe839f 100644
--- a/tests/textMark.test
+++ b/tests/textMark.test
@@ -182,6 +182,17 @@ test textMark-6.5 {insert and current marks in an empty peer - bug 3487407} -bod
} -cleanup {
.t configure -startline {} -endline {}
} -result {1.0}
+test textMark-6.6 {attempt to move the insert mark beyond peer -endline - bug 34db75c0ac} -body {
+ .t peer create .p -startline 1 -endline 2
+ pack .p
+ update
+ .p mark set insert 1.2
+ focus -force .p
+ event generate .p <<NextLine>> ; # shall not error out
+ set res [.p index insert]
+} -cleanup {
+ destroy .p
+} -result {1.9}
test textMark-7.1 {MarkFindNext - invalid mark name} -body {
.t mark next bogus