Index: uspace/lib/gfxfont/include/gfx/text.h
===================================================================
--- uspace/lib/gfxfont/include/gfx/text.h	(revision ead72f2a4c67f990b2a5c54abd27c70c1bfa0847)
+++ uspace/lib/gfxfont/include/gfx/text.h	(revision 9eb8d1299776320d3c0fcf343379c808b0e62866)
@@ -50,4 +50,8 @@
 extern size_t gfx_text_find_pos(gfx_font_t *, gfx_coord2_t *, gfx_text_fmt_t *,
     const char *, gfx_coord2_t *);
+extern void gfx_text_cont(gfx_font_t *, gfx_coord2_t *, gfx_text_fmt_t *,
+    const char *, gfx_coord2_t *, gfx_text_fmt_t *);
+extern void gfx_text_rect(gfx_font_t *, gfx_coord2_t *, gfx_text_fmt_t *,
+    const char *, gfx_rect_t *);
 
 #endif
Index: uspace/lib/gfxfont/src/text.c
===================================================================
--- uspace/lib/gfxfont/src/text.c	(revision ead72f2a4c67f990b2a5c54abd27c70c1bfa0847)
+++ uspace/lib/gfxfont/src/text.c	(revision 9eb8d1299776320d3c0fcf343379c808b0e62866)
@@ -174,5 +174,4 @@
  * @param str String
  * @param spos Place to store starting position
- * @return EOK on success or an error code
  */
 void gfx_text_start_pos(gfx_font_t *font, gfx_coord2_t *pos,
@@ -333,4 +332,62 @@
 }
 
+/** Get text continuation parameters.
+ *
+ * Return the anchor position and format needed to continue printing
+ * text after the specified string. It is allowed for the sources
+ * (@a pos, @a fmt) and destinations (@a cpos, @a cfmt) to point
+ * to the same objects, respectively.
+ *
+ * @param font Font
+ * @param pos Anchor position
+ * @param fmt Text formatting
+ * @param str String
+ * @param cpos Place to store anchor position for continuation
+ * @param cfmt Place to store format for continuation
+ */
+void gfx_text_cont(gfx_font_t *font, gfx_coord2_t *pos,
+    gfx_text_fmt_t *fmt, const char *str, gfx_coord2_t *cpos,
+    gfx_text_fmt_t *cfmt)
+{
+	gfx_coord2_t spos;
+	gfx_text_fmt_t tfmt;
+
+	/* Continuation should start where the current string ends */
+	gfx_text_start_pos(font, pos, fmt, str, &spos);
+	cpos->x = spos.x + gfx_text_width(font, str);
+	cpos->y = spos.y;
+
+	/*
+	 * Formatting is the same, except the text should be aligned
+	 * so that it starts at the anchor point.
+	 */
+	tfmt = *fmt;
+	tfmt.halign = gfx_halign_left;
+	tfmt.valign = gfx_valign_baseline;
+
+	*cfmt = tfmt;
+}
+
+/** Get text bounding rectangle.
+ *
+ * @param font Font
+ * @param pos Anchor position
+ * @param fmt Text formatting
+ * @param str String
+ * @param rect Place to store bounding rectangle
+ */
+void gfx_text_rect(gfx_font_t *font, gfx_coord2_t *pos,
+    gfx_text_fmt_t *fmt, const char *str, gfx_rect_t *rect)
+{
+	gfx_coord2_t spos;
+
+	gfx_text_start_pos(font, pos, fmt, str, &spos);
+
+	rect->p0.x = spos.x;
+	rect->p0.y = spos.y - font->metrics.ascent;
+	rect->p1.x = spos.x + gfx_text_width(font, str);
+	rect->p1.y = spos.y + font->metrics.descent + 1;
+}
+
 /** @}
  */
Index: uspace/lib/gfxfont/test/text.c
===================================================================
--- uspace/lib/gfxfont/test/text.c	(revision ead72f2a4c67f990b2a5c54abd27c70c1bfa0847)
+++ uspace/lib/gfxfont/test/text.c	(revision 9eb8d1299776320d3c0fcf343379c808b0e62866)
@@ -356,4 +356,96 @@
 }
 
+/** gfx_text_cont() produces correct continuation parameters */
+PCUT_TEST(text_cont)
+{
+	gfx_typeface_t *tface;
+	gfx_font_t *font;
+	gfx_context_t *gc;
+	gfx_color_t *color;
+	test_gc_t tgc;
+	gfx_text_fmt_t fmt;
+	gfx_coord2_t anchor;
+	gfx_coord2_t cpos;
+	gfx_text_fmt_t cfmt;
+	errno_t rc;
+
+	rc = gfx_context_new(&test_ops, (void *)&tgc, &gc);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	rc = gfx_typeface_create(gc, &tface);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	rc = gfx_font_create_textmode(tface, &font);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	rc = gfx_color_new_rgb_i16(0, 0, 0, &color);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	anchor.x = 10;
+	anchor.y = 20;
+	gfx_text_fmt_init(&fmt);
+	fmt.color = color;
+
+	gfx_text_cont(font, &anchor, &fmt, "Abc", &cpos, &cfmt);
+
+	PCUT_ASSERT_INT_EQUALS(13, cpos.x);
+	PCUT_ASSERT_INT_EQUALS(20, cpos.y);
+	PCUT_ASSERT_EQUALS(fmt.color, cfmt.color);
+	PCUT_ASSERT_EQUALS(gfx_halign_left, cfmt.halign);
+	PCUT_ASSERT_EQUALS(gfx_valign_baseline, cfmt.valign);
+
+	gfx_font_close(font);
+	gfx_typeface_destroy(tface);
+	gfx_color_delete(color);
+
+	rc = gfx_context_delete(gc);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+}
+
+/** gfx_text_rect() computes bounding rectangle */
+PCUT_TEST(text_rect)
+{
+	gfx_typeface_t *tface;
+	gfx_font_t *font;
+	gfx_context_t *gc;
+	gfx_color_t *color;
+	test_gc_t tgc;
+	gfx_text_fmt_t fmt;
+	gfx_coord2_t anchor;
+	gfx_rect_t rect;
+	errno_t rc;
+
+	rc = gfx_context_new(&test_ops, (void *)&tgc, &gc);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	rc = gfx_typeface_create(gc, &tface);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	rc = gfx_font_create_textmode(tface, &font);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	rc = gfx_color_new_rgb_i16(0, 0, 0, &color);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	anchor.x = 10;
+	anchor.y = 20;
+	gfx_text_fmt_init(&fmt);
+	fmt.color = color;
+
+	gfx_text_rect(font, &anchor, &fmt, "Abc", &rect);
+
+	PCUT_ASSERT_INT_EQUALS(10, rect.p0.x);
+	PCUT_ASSERT_INT_EQUALS(20, rect.p0.y);
+	PCUT_ASSERT_INT_EQUALS(13, rect.p1.x);
+	PCUT_ASSERT_INT_EQUALS(21, rect.p1.y);
+
+	gfx_font_close(font);
+	gfx_typeface_destroy(tface);
+	gfx_color_delete(color);
+
+	rc = gfx_context_delete(gc);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+}
+
 static errno_t testgc_set_clip_rect(void *arg, gfx_rect_t *rect)
 {
Index: uspace/lib/ui/include/ui/entry.h
===================================================================
--- uspace/lib/ui/include/ui/entry.h	(revision ead72f2a4c67f990b2a5c54abd27c70c1bfa0847)
+++ uspace/lib/ui/include/ui/entry.h	(revision 9eb8d1299776320d3c0fcf343379c808b0e62866)
@@ -55,8 +55,8 @@
 extern void ui_entry_backspace(ui_entry_t *);
 extern void ui_entry_delete(ui_entry_t *);
-extern void ui_entry_seek_start(ui_entry_t *);
-extern void ui_entry_seek_end(ui_entry_t *);
-extern void ui_entry_seek_prev_char(ui_entry_t *);
-extern void ui_entry_seek_next_char(ui_entry_t *);
+extern void ui_entry_seek_start(ui_entry_t *, bool);
+extern void ui_entry_seek_end(ui_entry_t *, bool);
+extern void ui_entry_seek_prev_char(ui_entry_t *, bool);
+extern void ui_entry_seek_next_char(ui_entry_t *, bool);
 extern ui_evclaim_t ui_entry_kbd_event(ui_entry_t *, kbd_event_t *);
 extern ui_evclaim_t ui_entry_pos_event(ui_entry_t *, pos_event_t *);
Index: uspace/lib/ui/private/entry.h
===================================================================
--- uspace/lib/ui/private/entry.h	(revision ead72f2a4c67f990b2a5c54abd27c70c1bfa0847)
+++ uspace/lib/ui/private/entry.h	(revision 9eb8d1299776320d3c0fcf343379c808b0e62866)
@@ -60,4 +60,6 @@
 	/** Cursor position in the text (offset in bytes) */
 	unsigned pos;
+	/** Selection start position in text (offset in bytes) */
+	unsigned sel_start;
 	/** Pointer is currently inside */
 	bool pointer_inside;
@@ -78,7 +80,9 @@
 
 extern errno_t ui_entry_insert_str(ui_entry_t *, const char *);
+extern ui_evclaim_t ui_entry_key_press_shift(ui_entry_t *, kbd_event_t *);
 extern ui_evclaim_t ui_entry_key_press_unmod(ui_entry_t *, kbd_event_t *);
 extern void ui_entry_get_geom(ui_entry_t *, ui_entry_geom_t *);
 extern size_t ui_entry_find_pos(ui_entry_t *, gfx_coord2_t *);
+extern void ui_entry_delete_sel(ui_entry_t *);
 extern void ui_entry_activate(ui_entry_t *);
 extern void ui_entry_deactivate(ui_entry_t *);
Index: uspace/lib/ui/src/entry.c
===================================================================
--- uspace/lib/ui/src/entry.c	(revision ead72f2a4c67f990b2a5c54abd27c70c1bfa0847)
+++ uspace/lib/ui/src/entry.c	(revision 9eb8d1299776320d3c0fcf343379c808b0e62866)
@@ -42,4 +42,5 @@
 #include <gfx/render.h>
 #include <gfx/text.h>
+#include <macros.h>
 #include <stdlib.h>
 #include <str.h>
@@ -63,5 +64,7 @@
 	ui_entry_vpad_text = 0,
 	ui_entry_cursor_overshoot = 1,
-	ui_entry_cursor_width = 2
+	ui_entry_cursor_width = 2,
+	ui_entry_sel_hpad = 0,
+	ui_entry_sel_vpad = 2
 };
 
@@ -181,4 +184,5 @@
 	entry->text = tcopy;
 	entry->pos = str_size(text);
+	entry->sel_start = entry->pos;
 
 	return EOK;
@@ -259,5 +263,10 @@
 	gfx_text_fmt_t fmt;
 	gfx_coord2_t pos;
+	gfx_text_fmt_t cfmt;
+	gfx_coord2_t cpos;
 	gfx_rect_t inside;
+	unsigned off1, off2;
+	gfx_rect_t sel;
+	char c;
 	errno_t rc;
 
@@ -296,5 +305,57 @@
 		goto error;
 
+	off1 = min(entry->pos, entry->sel_start);
+	off2 = max(entry->pos, entry->sel_start);
+
+	/* Render initial segment before start of selection */
+	c = entry->text[off1];
+	entry->text[off1] = '\0';
+
 	rc = gfx_puttext(res->font, &pos, &fmt, entry->text);
+	if (rc != EOK) {
+		(void) gfx_set_clip_rect(res->gc, NULL);
+		goto error;
+	}
+
+	gfx_text_cont(res->font, &pos, &fmt, entry->text, &cpos, &cfmt);
+	entry->text[off1] = c;
+
+	/* Render selected text */
+
+	if (off1 != off2) {
+		c = entry->text[off2];
+		entry->text[off2] = '\0';
+		cfmt.color = res->entry_bg_color;
+
+		gfx_text_rect(res->font, &cpos, &cfmt, entry->text + off1, &sel);
+		sel.p0.x -= ui_entry_sel_hpad;
+		sel.p0.y -= ui_entry_sel_vpad;
+		sel.p1.x += ui_entry_sel_hpad;
+		sel.p1.y += ui_entry_sel_vpad;
+
+		rc = gfx_set_color(res->gc, res->entry_fg_color);
+		if (rc != EOK)
+			goto error;
+
+		rc = gfx_fill_rect(res->gc, &sel);
+		if (rc != EOK)
+			goto error;
+
+		rc = gfx_puttext(res->font, &cpos, &cfmt, entry->text + off1);
+		if (rc != EOK) {
+			(void) gfx_set_clip_rect(res->gc, NULL);
+			goto error;
+		}
+
+		gfx_text_cont(res->font, &cpos, &cfmt, entry->text + off1,
+		    &cpos, &cfmt);
+
+		entry->text[off2] = c;
+	}
+
+	/* Render trailing, non-selected text */
+	cfmt.color = res->entry_fg_color;
+
+	rc = gfx_puttext(res->font, &cpos, &cfmt, entry->text + off2);
 	if (rc != EOK) {
 		(void) gfx_set_clip_rect(res->gc, NULL);
@@ -373,4 +434,24 @@
 }
 
+/** Delete selected text.
+ *
+ * @param entry Text entry
+ */
+void ui_entry_delete_sel(ui_entry_t *entry)
+{
+	size_t off1;
+	size_t off2;
+
+	off1 = min(entry->sel_start, entry->pos);
+	off2 = max(entry->sel_start, entry->pos);
+
+	memmove(entry->text + off1, entry->text + off2,
+	    str_size(entry->text + off2) + 1);
+
+	entry->pos = off1;
+	entry->sel_start = off1;
+	ui_entry_paint(entry);
+}
+
 /** Insert string at cursor position.
  *
@@ -387,4 +468,8 @@
 	int rc;
 
+	/* Do we have a selection? */
+	if (entry->sel_start != entry->pos)
+		ui_entry_delete_sel(entry);
+
 	tmp = entry->text[entry->pos];
 	entry->text[entry->pos] = '\0';
@@ -407,4 +492,5 @@
 	free(ltext);
 
+	entry->sel_start = entry->pos;
 	ui_entry_paint(entry);
 
@@ -419,4 +505,10 @@
 {
 	size_t off;
+
+	/* Do we have a selection? */
+	if (entry->sel_start != entry->pos) {
+		ui_entry_delete_sel(entry);
+		return;
+	}
 
 	if (entry->pos == 0)
@@ -431,4 +523,5 @@
 	    str_size(entry->text + entry->pos) + 1);
 	entry->pos = off;
+	entry->sel_start = off;
 
 	ui_entry_paint(entry);
@@ -443,5 +536,11 @@
 	size_t off;
 
-	/* Find offset where character after cursor end */
+	/* Do we have a selection? */
+	if (entry->sel_start != entry->pos) {
+		ui_entry_delete_sel(entry);
+		return;
+	}
+
+	/* Find offset where character after cursor ends */
 	off = entry->pos;
 	(void) str_decode(entry->text, &off,
@@ -478,17 +577,51 @@
 
 	case KC_HOME:
-		ui_entry_seek_start(entry);
+		ui_entry_seek_start(entry, false);
 		break;
 
 	case KC_END:
-		ui_entry_seek_end(entry);
+		ui_entry_seek_end(entry, false);
 		break;
 
 	case KC_LEFT:
-		ui_entry_seek_prev_char(entry);
+		ui_entry_seek_prev_char(entry, false);
 		break;
 
 	case KC_RIGHT:
-		ui_entry_seek_next_char(entry);
+		ui_entry_seek_next_char(entry, false);
+		break;
+
+	default:
+		break;
+	}
+
+	return ui_claimed;
+}
+
+/** Handle text entry key press with shift modifier.
+ *
+ * @param entry Text entry
+ * @param kbd_event Keyboard event
+ * @return @c ui_claimed iff the event is claimed
+ */
+ui_evclaim_t ui_entry_key_press_shift(ui_entry_t *entry, kbd_event_t *event)
+{
+	assert(event->type == KEY_PRESS);
+
+	switch (event->key) {
+	case KC_HOME:
+		ui_entry_seek_start(entry, true);
+		break;
+
+	case KC_END:
+		ui_entry_seek_end(entry, true);
+		break;
+
+	case KC_LEFT:
+		ui_entry_seek_prev_char(entry, true);
+		break;
+
+	case KC_RIGHT:
+		ui_entry_seek_next_char(entry, true);
 		break;
 
@@ -527,4 +660,9 @@
 	    (event->mods & (KM_CTRL | KM_ALT | KM_SHIFT)) == 0)
 		return ui_entry_key_press_unmod(entry, event);
+
+	if (event->type == KEY_PRESS &&
+	    (event->mods & KM_SHIFT) != 0 &&
+	    (event->mods & (KM_CTRL | KM_ALT)) == 0)
+		return ui_entry_key_press_shift(entry, event);
 
 	return ui_claimed;
@@ -569,4 +707,5 @@
 		if (gfx_pix_inside_rect(&pos, &entry->rect)) {
 			entry->pos = ui_entry_find_pos(entry, &pos);
+			entry->sel_start = entry->pos;
 			if (entry->active)
 				ui_entry_paint(entry);
@@ -680,8 +819,12 @@
  *
  * @param entry Text entry
- */
-void ui_entry_seek_start(ui_entry_t *entry)
+ * @param shift @c true iff shift key is pressed
+ */
+void ui_entry_seek_start(ui_entry_t *entry, bool shift)
 {
 	entry->pos = 0;
+
+	if (!shift)
+		entry->sel_start = entry->pos;
 	(void) ui_entry_paint(entry);
 }
@@ -690,8 +833,12 @@
  *
  * @param entry Text entry
- */
-void ui_entry_seek_end(ui_entry_t *entry)
+ * @param shift @c true iff shift key is pressed
+ */
+void ui_entry_seek_end(ui_entry_t *entry, bool shift)
 {
 	entry->pos = str_size(entry->text);
+
+	if (!shift)
+		entry->sel_start = entry->pos;
 	(void) ui_entry_paint(entry);
 }
@@ -700,6 +847,7 @@
  *
  * @param entry Text entry
- */
-void ui_entry_seek_prev_char(ui_entry_t *entry)
+ * @param shift @c true iff shift key is pressed
+ */
+void ui_entry_seek_prev_char(ui_entry_t *entry, bool shift)
 {
 	size_t off;
@@ -709,4 +857,7 @@
 	    str_size(entry->text));
 	entry->pos = off;
+
+	if (!shift)
+		entry->sel_start = entry->pos;
 	(void) ui_entry_paint(entry);
 }
@@ -715,6 +866,7 @@
  *
  * @param entry Text entry
- */
-void ui_entry_seek_next_char(ui_entry_t *entry)
+ * @param shift @c true iff shift key is pressed
+ */
+void ui_entry_seek_next_char(ui_entry_t *entry, bool shift)
 {
 	size_t off;
@@ -724,4 +876,7 @@
 	    str_size(entry->text));
 	entry->pos = off;
+
+	if (!shift)
+		entry->sel_start = entry->pos;
 	(void) ui_entry_paint(entry);
 }
@@ -741,4 +896,5 @@
 
 	entry->active = false;
+	entry->sel_start = entry->pos;
 	(void) ui_entry_paint(entry);
 
Index: uspace/lib/ui/test/entry.c
===================================================================
--- uspace/lib/ui/test/entry.c	(revision ead72f2a4c67f990b2a5c54abd27c70c1bfa0847)
+++ uspace/lib/ui/test/entry.c	(revision 9eb8d1299776320d3c0fcf343379c808b0e62866)
@@ -190,4 +190,45 @@
 }
 
+/** ui_entry_delete_sel() deletes selected text */
+PCUT_TEST(delete_sel)
+{
+	errno_t rc;
+	ui_t *ui = NULL;
+	ui_window_t *window = NULL;
+	ui_wnd_params_t params;
+	ui_entry_t *entry;
+
+	rc = ui_create_disp(NULL, &ui);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	ui_wnd_params_init(&params);
+	params.caption = "Hello";
+
+	rc = ui_window_create(ui, &params, &window);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+	PCUT_ASSERT_NOT_NULL(window);
+
+	rc = ui_entry_create(window, "ABCDEF", &entry);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	PCUT_ASSERT_STR_EQUALS("ABCDEF", entry->text);
+
+	ui_entry_activate(entry);
+
+	/* Select all but first and last character */
+	ui_entry_seek_start(entry, false);
+	ui_entry_seek_next_char(entry, false);
+	ui_entry_seek_end(entry, true);
+	ui_entry_seek_prev_char(entry, true);
+
+	ui_entry_delete_sel(entry);
+
+	PCUT_ASSERT_STR_EQUALS("AF", entry->text);
+
+	ui_entry_destroy(entry);
+	ui_window_destroy(window);
+	ui_destroy(ui);
+}
+
 /** ui_entry_insert_str() inserts string at cursor. */
 PCUT_TEST(insert_str)
@@ -214,6 +255,6 @@
 	PCUT_ASSERT_STR_EQUALS("A", entry->text);
 
-	/* This moves the cursor to the end of the text */
 	ui_entry_activate(entry);
+	ui_entry_seek_end(entry, false);
 
 	rc = ui_entry_insert_str(entry, "B");
@@ -228,8 +269,50 @@
 
 	entry->pos = 2;
+	entry->sel_start = 2;
 	rc = ui_entry_insert_str(entry, "CD");
 	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
 
 	PCUT_ASSERT_STR_EQUALS("ABCDEF", entry->text);
+
+	ui_entry_destroy(entry);
+	ui_window_destroy(window);
+	ui_destroy(ui);
+}
+
+/** ui_entry_insert_str() deletes selection before inserting string */
+PCUT_TEST(insert_str_with_sel)
+{
+	errno_t rc;
+	ui_t *ui = NULL;
+	ui_window_t *window = NULL;
+	ui_wnd_params_t params;
+	ui_entry_t *entry;
+
+	rc = ui_create_disp(NULL, &ui);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	ui_wnd_params_init(&params);
+	params.caption = "Hello";
+
+	rc = ui_window_create(ui, &params, &window);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+	PCUT_ASSERT_NOT_NULL(window);
+
+	rc = ui_entry_create(window, "ABCDE", &entry);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	PCUT_ASSERT_STR_EQUALS("ABCDE", entry->text);
+
+	/* Select all but the first and last character */
+	ui_entry_activate(entry);
+	ui_entry_seek_start(entry, false);
+	ui_entry_seek_next_char(entry, false);
+	ui_entry_seek_end(entry, true);
+	ui_entry_seek_prev_char(entry, true);
+
+	rc = ui_entry_insert_str(entry, "123");
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	PCUT_ASSERT_STR_EQUALS("A123E", entry->text);
 
 	ui_entry_destroy(entry);
@@ -262,4 +345,5 @@
 	PCUT_ASSERT_STR_EQUALS("ABCD", entry->text);
 	entry->pos = 3;
+	entry->sel_start = 3;
 
 	ui_entry_backspace(entry);
@@ -280,4 +364,44 @@
 }
 
+/** ui_entry_backspace() with selected text deletes selection. */
+PCUT_TEST(backspace_with_sel)
+{
+	errno_t rc;
+	ui_t *ui = NULL;
+	ui_window_t *window = NULL;
+	ui_wnd_params_t params;
+	ui_entry_t *entry;
+
+	rc = ui_create_disp(NULL, &ui);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	ui_wnd_params_init(&params);
+	params.caption = "Hello";
+
+	rc = ui_window_create(ui, &params, &window);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+	PCUT_ASSERT_NOT_NULL(window);
+
+	rc = ui_entry_create(window, "ABCDE", &entry);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	PCUT_ASSERT_STR_EQUALS("ABCDE", entry->text);
+
+	/* Select all but the first and last character */
+	ui_entry_activate(entry);
+	ui_entry_seek_start(entry, false);
+	ui_entry_seek_next_char(entry, false);
+	ui_entry_seek_end(entry, true);
+	ui_entry_seek_prev_char(entry, true);
+
+	ui_entry_backspace(entry);
+
+	PCUT_ASSERT_STR_EQUALS("AE", entry->text);
+
+	ui_entry_destroy(entry);
+	ui_window_destroy(window);
+	ui_destroy(ui);
+}
+
 /** ui_entry_delete() deletes character after cursor. */
 PCUT_TEST(delete)
@@ -304,4 +428,5 @@
 	PCUT_ASSERT_STR_EQUALS("ABCD", entry->text);
 	entry->pos = 1;
+	entry->sel_start = 1;
 
 	ui_entry_delete(entry);
@@ -322,4 +447,44 @@
 }
 
+/** ui_entry_delete() with selected text deletes selection. */
+PCUT_TEST(delete_with_sel)
+{
+	errno_t rc;
+	ui_t *ui = NULL;
+	ui_window_t *window = NULL;
+	ui_wnd_params_t params;
+	ui_entry_t *entry;
+
+	rc = ui_create_disp(NULL, &ui);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	ui_wnd_params_init(&params);
+	params.caption = "Hello";
+
+	rc = ui_window_create(ui, &params, &window);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+	PCUT_ASSERT_NOT_NULL(window);
+
+	rc = ui_entry_create(window, "ABCDE", &entry);
+	PCUT_ASSERT_ERRNO_VAL(EOK, rc);
+
+	PCUT_ASSERT_STR_EQUALS("ABCDE", entry->text);
+
+	/* Select all but the first and last character */
+	ui_entry_activate(entry);
+	ui_entry_seek_start(entry, false);
+	ui_entry_seek_next_char(entry, false);
+	ui_entry_seek_end(entry, true);
+	ui_entry_seek_prev_char(entry, true);
+
+	ui_entry_delete(entry);
+
+	PCUT_ASSERT_STR_EQUALS("AE", entry->text);
+
+	ui_entry_destroy(entry);
+	ui_window_destroy(window);
+	ui_destroy(ui);
+}
+
 /** ui_entry_seek_start() moves cursor to beginning of text */
 PCUT_TEST(seek_start)
@@ -346,7 +511,13 @@
 	PCUT_ASSERT_STR_EQUALS("ABCD", entry->text);
 	entry->pos = 2;
-
-	ui_entry_seek_start(entry);
+	entry->sel_start = 2;
+
+	ui_entry_seek_start(entry, true);
 	PCUT_ASSERT_INT_EQUALS(0, entry->pos);
+	PCUT_ASSERT_INT_EQUALS(2, entry->sel_start);
+
+	ui_entry_seek_start(entry, false);
+	PCUT_ASSERT_INT_EQUALS(0, entry->pos);
+	PCUT_ASSERT_INT_EQUALS(0, entry->sel_start);
 
 	ui_entry_destroy(entry);
@@ -379,7 +550,12 @@
 	PCUT_ASSERT_STR_EQUALS("ABCD", entry->text);
 	entry->pos = 2;
-
-	ui_entry_seek_end(entry);
+	entry->sel_start = 2;
+
+	ui_entry_seek_end(entry, true);
 	PCUT_ASSERT_INT_EQUALS(4, entry->pos);
+	PCUT_ASSERT_INT_EQUALS(2, entry->sel_start);
+	ui_entry_seek_end(entry, false);
+	PCUT_ASSERT_INT_EQUALS(4, entry->pos);
+	PCUT_ASSERT_INT_EQUALS(4, entry->sel_start);
 
 	ui_entry_destroy(entry);
@@ -411,8 +587,14 @@
 
 	PCUT_ASSERT_STR_EQUALS("ABCD", entry->text);
-	entry->pos = 2;
-
-	ui_entry_seek_prev_char(entry);
+	entry->pos = 3;
+	entry->sel_start = 3;
+
+	ui_entry_seek_prev_char(entry, true);
+	PCUT_ASSERT_INT_EQUALS(2, entry->pos);
+	PCUT_ASSERT_INT_EQUALS(3, entry->sel_start);
+
+	ui_entry_seek_prev_char(entry, false);
 	PCUT_ASSERT_INT_EQUALS(1, entry->pos);
+	PCUT_ASSERT_INT_EQUALS(1, entry->sel_start);
 
 	ui_entry_destroy(entry);
@@ -444,8 +626,13 @@
 
 	PCUT_ASSERT_STR_EQUALS("ABCD", entry->text);
-	entry->pos = 2;
-
-	ui_entry_seek_next_char(entry);
+	entry->pos = 1;
+	entry->sel_start = 1;
+
+	ui_entry_seek_next_char(entry, true);
+	PCUT_ASSERT_INT_EQUALS(2, entry->pos);
+	PCUT_ASSERT_INT_EQUALS(1, entry->sel_start);
+	ui_entry_seek_next_char(entry, false);
 	PCUT_ASSERT_INT_EQUALS(3, entry->pos);
+	PCUT_ASSERT_INT_EQUALS(3, entry->sel_start);
 
 	ui_entry_destroy(entry);
