Update prebuilt Clang to r416183b from Android.

https://android.googlesource.com/platform/prebuilts/clang/host/
linux-x86/+/06a71ddac05c22edb2d10b590e1769b3f8619bef

clang 12.0.5 (based on r416183b) from build 7284624.

Change-Id: I277a316abcf47307562d8b748b84870f31a72866
Signed-off-by: Olivier Deprez <olivier.deprez@arm.com>
diff --git a/linux-x64/clang/python3/lib/python3.9/curses/__init__.py b/linux-x64/clang/python3/lib/python3.9/curses/__init__.py
new file mode 100644
index 0000000..69270bf
--- /dev/null
+++ b/linux-x64/clang/python3/lib/python3.9/curses/__init__.py
@@ -0,0 +1,101 @@
+"""curses
+
+The main package for curses support for Python.  Normally used by importing
+the package, and perhaps a particular module inside it.
+
+   import curses
+   from curses import textpad
+   curses.initscr()
+   ...
+
+"""
+
+from _curses import *
+import os as _os
+import sys as _sys
+
+# Some constants, most notably the ACS_* ones, are only added to the C
+# _curses module's dictionary after initscr() is called.  (Some
+# versions of SGI's curses don't define values for those constants
+# until initscr() has been called.)  This wrapper function calls the
+# underlying C initscr(), and then copies the constants from the
+# _curses module to the curses package's dictionary.  Don't do 'from
+# curses import *' if you'll be needing the ACS_* constants.
+
+def initscr():
+    import _curses, curses
+    # we call setupterm() here because it raises an error
+    # instead of calling exit() in error cases.
+    setupterm(term=_os.environ.get("TERM", "unknown"),
+              fd=_sys.__stdout__.fileno())
+    stdscr = _curses.initscr()
+    for key, value in _curses.__dict__.items():
+        if key[0:4] == 'ACS_' or key in ('LINES', 'COLS'):
+            setattr(curses, key, value)
+
+    return stdscr
+
+# This is a similar wrapper for start_color(), which adds the COLORS and
+# COLOR_PAIRS variables which are only available after start_color() is
+# called.
+
+def start_color():
+    import _curses, curses
+    retval = _curses.start_color()
+    if hasattr(_curses, 'COLORS'):
+        curses.COLORS = _curses.COLORS
+    if hasattr(_curses, 'COLOR_PAIRS'):
+        curses.COLOR_PAIRS = _curses.COLOR_PAIRS
+    return retval
+
+# Import Python has_key() implementation if _curses doesn't contain has_key()
+
+try:
+    has_key
+except NameError:
+    from .has_key import has_key
+
+# Wrapper for the entire curses-based application.  Runs a function which
+# should be the rest of your curses-based application.  If the application
+# raises an exception, wrapper() will restore the terminal to a sane state so
+# you can read the resulting traceback.
+
+def wrapper(func, /, *args, **kwds):
+    """Wrapper function that initializes curses and calls another function,
+    restoring normal keyboard/screen behavior on error.
+    The callable object 'func' is then passed the main window 'stdscr'
+    as its first argument, followed by any other arguments passed to
+    wrapper().
+    """
+
+    try:
+        # Initialize curses
+        stdscr = initscr()
+
+        # Turn off echoing of keys, and enter cbreak mode,
+        # where no buffering is performed on keyboard input
+        noecho()
+        cbreak()
+
+        # In keypad mode, escape sequences for special keys
+        # (like the cursor keys) will be interpreted and
+        # a special value like curses.KEY_LEFT will be returned
+        stdscr.keypad(1)
+
+        # Start color, too.  Harmless if the terminal doesn't have
+        # color; user can test with has_color() later on.  The try/catch
+        # works around a minor bit of over-conscientiousness in the curses
+        # module -- the error return from C start_color() is ignorable.
+        try:
+            start_color()
+        except:
+            pass
+
+        return func(stdscr, *args, **kwds)
+    finally:
+        # Set everything back to normal
+        if 'stdscr' in locals():
+            stdscr.keypad(0)
+            echo()
+            nocbreak()
+            endwin()
diff --git a/linux-x64/clang/python3/lib/python3.9/curses/ascii.py b/linux-x64/clang/python3/lib/python3.9/curses/ascii.py
new file mode 100644
index 0000000..5b243be
--- /dev/null
+++ b/linux-x64/clang/python3/lib/python3.9/curses/ascii.py
@@ -0,0 +1,99 @@
+"""Constants and membership tests for ASCII characters"""
+
+NUL     = 0x00  # ^@
+SOH     = 0x01  # ^A
+STX     = 0x02  # ^B
+ETX     = 0x03  # ^C
+EOT     = 0x04  # ^D
+ENQ     = 0x05  # ^E
+ACK     = 0x06  # ^F
+BEL     = 0x07  # ^G
+BS      = 0x08  # ^H
+TAB     = 0x09  # ^I
+HT      = 0x09  # ^I
+LF      = 0x0a  # ^J
+NL      = 0x0a  # ^J
+VT      = 0x0b  # ^K
+FF      = 0x0c  # ^L
+CR      = 0x0d  # ^M
+SO      = 0x0e  # ^N
+SI      = 0x0f  # ^O
+DLE     = 0x10  # ^P
+DC1     = 0x11  # ^Q
+DC2     = 0x12  # ^R
+DC3     = 0x13  # ^S
+DC4     = 0x14  # ^T
+NAK     = 0x15  # ^U
+SYN     = 0x16  # ^V
+ETB     = 0x17  # ^W
+CAN     = 0x18  # ^X
+EM      = 0x19  # ^Y
+SUB     = 0x1a  # ^Z
+ESC     = 0x1b  # ^[
+FS      = 0x1c  # ^\
+GS      = 0x1d  # ^]
+RS      = 0x1e  # ^^
+US      = 0x1f  # ^_
+SP      = 0x20  # space
+DEL     = 0x7f  # delete
+
+controlnames = [
+"NUL", "SOH", "STX", "ETX", "EOT", "ENQ", "ACK", "BEL",
+"BS",  "HT",  "LF",  "VT",  "FF",  "CR",  "SO",  "SI",
+"DLE", "DC1", "DC2", "DC3", "DC4", "NAK", "SYN", "ETB",
+"CAN", "EM",  "SUB", "ESC", "FS",  "GS",  "RS",  "US",
+"SP"
+]
+
+def _ctoi(c):
+    if type(c) == type(""):
+        return ord(c)
+    else:
+        return c
+
+def isalnum(c): return isalpha(c) or isdigit(c)
+def isalpha(c): return isupper(c) or islower(c)
+def isascii(c): return 0 <= _ctoi(c) <= 127          # ?
+def isblank(c): return _ctoi(c) in (9, 32)
+def iscntrl(c): return 0 <= _ctoi(c) <= 31 or _ctoi(c) == 127
+def isdigit(c): return 48 <= _ctoi(c) <= 57
+def isgraph(c): return 33 <= _ctoi(c) <= 126
+def islower(c): return 97 <= _ctoi(c) <= 122
+def isprint(c): return 32 <= _ctoi(c) <= 126
+def ispunct(c): return isgraph(c) and not isalnum(c)
+def isspace(c): return _ctoi(c) in (9, 10, 11, 12, 13, 32)
+def isupper(c): return 65 <= _ctoi(c) <= 90
+def isxdigit(c): return isdigit(c) or \
+    (65 <= _ctoi(c) <= 70) or (97 <= _ctoi(c) <= 102)
+def isctrl(c): return 0 <= _ctoi(c) < 32
+def ismeta(c): return _ctoi(c) > 127
+
+def ascii(c):
+    if type(c) == type(""):
+        return chr(_ctoi(c) & 0x7f)
+    else:
+        return _ctoi(c) & 0x7f
+
+def ctrl(c):
+    if type(c) == type(""):
+        return chr(_ctoi(c) & 0x1f)
+    else:
+        return _ctoi(c) & 0x1f
+
+def alt(c):
+    if type(c) == type(""):
+        return chr(_ctoi(c) | 0x80)
+    else:
+        return _ctoi(c) | 0x80
+
+def unctrl(c):
+    bits = _ctoi(c)
+    if bits == 0x7f:
+        rep = "^?"
+    elif isprint(bits & 0x7f):
+        rep = chr(bits & 0x7f)
+    else:
+        rep = "^" + chr(((bits & 0x7f) | 0x20) + 0x20)
+    if bits & 0x80:
+        return "!" + rep
+    return rep
diff --git a/linux-x64/clang/python3/lib/python3.9/curses/has_key.py b/linux-x64/clang/python3/lib/python3.9/curses/has_key.py
new file mode 100644
index 0000000..4e37b48
--- /dev/null
+++ b/linux-x64/clang/python3/lib/python3.9/curses/has_key.py
@@ -0,0 +1,192 @@
+
+#
+# Emulation of has_key() function for platforms that don't use ncurses
+#
+
+import _curses
+
+# Table mapping curses keys to the terminfo capability name
+
+_capability_names = {
+    _curses.KEY_A1: 'ka1',
+    _curses.KEY_A3: 'ka3',
+    _curses.KEY_B2: 'kb2',
+    _curses.KEY_BACKSPACE: 'kbs',
+    _curses.KEY_BEG: 'kbeg',
+    _curses.KEY_BTAB: 'kcbt',
+    _curses.KEY_C1: 'kc1',
+    _curses.KEY_C3: 'kc3',
+    _curses.KEY_CANCEL: 'kcan',
+    _curses.KEY_CATAB: 'ktbc',
+    _curses.KEY_CLEAR: 'kclr',
+    _curses.KEY_CLOSE: 'kclo',
+    _curses.KEY_COMMAND: 'kcmd',
+    _curses.KEY_COPY: 'kcpy',
+    _curses.KEY_CREATE: 'kcrt',
+    _curses.KEY_CTAB: 'kctab',
+    _curses.KEY_DC: 'kdch1',
+    _curses.KEY_DL: 'kdl1',
+    _curses.KEY_DOWN: 'kcud1',
+    _curses.KEY_EIC: 'krmir',
+    _curses.KEY_END: 'kend',
+    _curses.KEY_ENTER: 'kent',
+    _curses.KEY_EOL: 'kel',
+    _curses.KEY_EOS: 'ked',
+    _curses.KEY_EXIT: 'kext',
+    _curses.KEY_F0: 'kf0',
+    _curses.KEY_F1: 'kf1',
+    _curses.KEY_F10: 'kf10',
+    _curses.KEY_F11: 'kf11',
+    _curses.KEY_F12: 'kf12',
+    _curses.KEY_F13: 'kf13',
+    _curses.KEY_F14: 'kf14',
+    _curses.KEY_F15: 'kf15',
+    _curses.KEY_F16: 'kf16',
+    _curses.KEY_F17: 'kf17',
+    _curses.KEY_F18: 'kf18',
+    _curses.KEY_F19: 'kf19',
+    _curses.KEY_F2: 'kf2',
+    _curses.KEY_F20: 'kf20',
+    _curses.KEY_F21: 'kf21',
+    _curses.KEY_F22: 'kf22',
+    _curses.KEY_F23: 'kf23',
+    _curses.KEY_F24: 'kf24',
+    _curses.KEY_F25: 'kf25',
+    _curses.KEY_F26: 'kf26',
+    _curses.KEY_F27: 'kf27',
+    _curses.KEY_F28: 'kf28',
+    _curses.KEY_F29: 'kf29',
+    _curses.KEY_F3: 'kf3',
+    _curses.KEY_F30: 'kf30',
+    _curses.KEY_F31: 'kf31',
+    _curses.KEY_F32: 'kf32',
+    _curses.KEY_F33: 'kf33',
+    _curses.KEY_F34: 'kf34',
+    _curses.KEY_F35: 'kf35',
+    _curses.KEY_F36: 'kf36',
+    _curses.KEY_F37: 'kf37',
+    _curses.KEY_F38: 'kf38',
+    _curses.KEY_F39: 'kf39',
+    _curses.KEY_F4: 'kf4',
+    _curses.KEY_F40: 'kf40',
+    _curses.KEY_F41: 'kf41',
+    _curses.KEY_F42: 'kf42',
+    _curses.KEY_F43: 'kf43',
+    _curses.KEY_F44: 'kf44',
+    _curses.KEY_F45: 'kf45',
+    _curses.KEY_F46: 'kf46',
+    _curses.KEY_F47: 'kf47',
+    _curses.KEY_F48: 'kf48',
+    _curses.KEY_F49: 'kf49',
+    _curses.KEY_F5: 'kf5',
+    _curses.KEY_F50: 'kf50',
+    _curses.KEY_F51: 'kf51',
+    _curses.KEY_F52: 'kf52',
+    _curses.KEY_F53: 'kf53',
+    _curses.KEY_F54: 'kf54',
+    _curses.KEY_F55: 'kf55',
+    _curses.KEY_F56: 'kf56',
+    _curses.KEY_F57: 'kf57',
+    _curses.KEY_F58: 'kf58',
+    _curses.KEY_F59: 'kf59',
+    _curses.KEY_F6: 'kf6',
+    _curses.KEY_F60: 'kf60',
+    _curses.KEY_F61: 'kf61',
+    _curses.KEY_F62: 'kf62',
+    _curses.KEY_F63: 'kf63',
+    _curses.KEY_F7: 'kf7',
+    _curses.KEY_F8: 'kf8',
+    _curses.KEY_F9: 'kf9',
+    _curses.KEY_FIND: 'kfnd',
+    _curses.KEY_HELP: 'khlp',
+    _curses.KEY_HOME: 'khome',
+    _curses.KEY_IC: 'kich1',
+    _curses.KEY_IL: 'kil1',
+    _curses.KEY_LEFT: 'kcub1',
+    _curses.KEY_LL: 'kll',
+    _curses.KEY_MARK: 'kmrk',
+    _curses.KEY_MESSAGE: 'kmsg',
+    _curses.KEY_MOVE: 'kmov',
+    _curses.KEY_NEXT: 'knxt',
+    _curses.KEY_NPAGE: 'knp',
+    _curses.KEY_OPEN: 'kopn',
+    _curses.KEY_OPTIONS: 'kopt',
+    _curses.KEY_PPAGE: 'kpp',
+    _curses.KEY_PREVIOUS: 'kprv',
+    _curses.KEY_PRINT: 'kprt',
+    _curses.KEY_REDO: 'krdo',
+    _curses.KEY_REFERENCE: 'kref',
+    _curses.KEY_REFRESH: 'krfr',
+    _curses.KEY_REPLACE: 'krpl',
+    _curses.KEY_RESTART: 'krst',
+    _curses.KEY_RESUME: 'kres',
+    _curses.KEY_RIGHT: 'kcuf1',
+    _curses.KEY_SAVE: 'ksav',
+    _curses.KEY_SBEG: 'kBEG',
+    _curses.KEY_SCANCEL: 'kCAN',
+    _curses.KEY_SCOMMAND: 'kCMD',
+    _curses.KEY_SCOPY: 'kCPY',
+    _curses.KEY_SCREATE: 'kCRT',
+    _curses.KEY_SDC: 'kDC',
+    _curses.KEY_SDL: 'kDL',
+    _curses.KEY_SELECT: 'kslt',
+    _curses.KEY_SEND: 'kEND',
+    _curses.KEY_SEOL: 'kEOL',
+    _curses.KEY_SEXIT: 'kEXT',
+    _curses.KEY_SF: 'kind',
+    _curses.KEY_SFIND: 'kFND',
+    _curses.KEY_SHELP: 'kHLP',
+    _curses.KEY_SHOME: 'kHOM',
+    _curses.KEY_SIC: 'kIC',
+    _curses.KEY_SLEFT: 'kLFT',
+    _curses.KEY_SMESSAGE: 'kMSG',
+    _curses.KEY_SMOVE: 'kMOV',
+    _curses.KEY_SNEXT: 'kNXT',
+    _curses.KEY_SOPTIONS: 'kOPT',
+    _curses.KEY_SPREVIOUS: 'kPRV',
+    _curses.KEY_SPRINT: 'kPRT',
+    _curses.KEY_SR: 'kri',
+    _curses.KEY_SREDO: 'kRDO',
+    _curses.KEY_SREPLACE: 'kRPL',
+    _curses.KEY_SRIGHT: 'kRIT',
+    _curses.KEY_SRSUME: 'kRES',
+    _curses.KEY_SSAVE: 'kSAV',
+    _curses.KEY_SSUSPEND: 'kSPD',
+    _curses.KEY_STAB: 'khts',
+    _curses.KEY_SUNDO: 'kUND',
+    _curses.KEY_SUSPEND: 'kspd',
+    _curses.KEY_UNDO: 'kund',
+    _curses.KEY_UP: 'kcuu1'
+    }
+
+def has_key(ch):
+    if isinstance(ch, str):
+        ch = ord(ch)
+
+    # Figure out the correct capability name for the keycode.
+    capability_name = _capability_names.get(ch)
+    if capability_name is None:
+        return False
+
+    #Check the current terminal description for that capability;
+    #if present, return true, else return false.
+    if _curses.tigetstr( capability_name ):
+        return True
+    else:
+        return False
+
+if __name__ == '__main__':
+    # Compare the output of this implementation and the ncurses has_key,
+    # on platforms where has_key is already available
+    try:
+        L = []
+        _curses.initscr()
+        for key in _capability_names.keys():
+            system = _curses.has_key(key)
+            python = has_key(key)
+            if system != python:
+                L.append( 'Mismatch for key %s, system=%i, Python=%i'
+                          % (_curses.keyname( key ), system, python) )
+    finally:
+        _curses.endwin()
+        for i in L: print(i)
diff --git a/linux-x64/clang/python3/lib/python3.9/curses/panel.py b/linux-x64/clang/python3/lib/python3.9/curses/panel.py
new file mode 100644
index 0000000..067afef
--- /dev/null
+++ b/linux-x64/clang/python3/lib/python3.9/curses/panel.py
@@ -0,0 +1,6 @@
+"""curses.panel
+
+Module for using panels with curses.
+"""
+
+from _curses_panel import *
diff --git a/linux-x64/clang/python3/lib/python3.9/curses/textpad.py b/linux-x64/clang/python3/lib/python3.9/curses/textpad.py
new file mode 100644
index 0000000..2079953
--- /dev/null
+++ b/linux-x64/clang/python3/lib/python3.9/curses/textpad.py
@@ -0,0 +1,201 @@
+"""Simple textbox editing widget with Emacs-like keybindings."""
+
+import curses
+import curses.ascii
+
+def rectangle(win, uly, ulx, lry, lrx):
+    """Draw a rectangle with corners at the provided upper-left
+    and lower-right coordinates.
+    """
+    win.vline(uly+1, ulx, curses.ACS_VLINE, lry - uly - 1)
+    win.hline(uly, ulx+1, curses.ACS_HLINE, lrx - ulx - 1)
+    win.hline(lry, ulx+1, curses.ACS_HLINE, lrx - ulx - 1)
+    win.vline(uly+1, lrx, curses.ACS_VLINE, lry - uly - 1)
+    win.addch(uly, ulx, curses.ACS_ULCORNER)
+    win.addch(uly, lrx, curses.ACS_URCORNER)
+    win.addch(lry, lrx, curses.ACS_LRCORNER)
+    win.addch(lry, ulx, curses.ACS_LLCORNER)
+
+class Textbox:
+    """Editing widget using the interior of a window object.
+     Supports the following Emacs-like key bindings:
+
+    Ctrl-A      Go to left edge of window.
+    Ctrl-B      Cursor left, wrapping to previous line if appropriate.
+    Ctrl-D      Delete character under cursor.
+    Ctrl-E      Go to right edge (stripspaces off) or end of line (stripspaces on).
+    Ctrl-F      Cursor right, wrapping to next line when appropriate.
+    Ctrl-G      Terminate, returning the window contents.
+    Ctrl-H      Delete character backward.
+    Ctrl-J      Terminate if the window is 1 line, otherwise insert newline.
+    Ctrl-K      If line is blank, delete it, otherwise clear to end of line.
+    Ctrl-L      Refresh screen.
+    Ctrl-N      Cursor down; move down one line.
+    Ctrl-O      Insert a blank line at cursor location.
+    Ctrl-P      Cursor up; move up one line.
+
+    Move operations do nothing if the cursor is at an edge where the movement
+    is not possible.  The following synonyms are supported where possible:
+
+    KEY_LEFT = Ctrl-B, KEY_RIGHT = Ctrl-F, KEY_UP = Ctrl-P, KEY_DOWN = Ctrl-N
+    KEY_BACKSPACE = Ctrl-h
+    """
+    def __init__(self, win, insert_mode=False):
+        self.win = win
+        self.insert_mode = insert_mode
+        self._update_max_yx()
+        self.stripspaces = 1
+        self.lastcmd = None
+        win.keypad(1)
+
+    def _update_max_yx(self):
+        maxy, maxx = self.win.getmaxyx()
+        self.maxy = maxy - 1
+        self.maxx = maxx - 1
+
+    def _end_of_line(self, y):
+        """Go to the location of the first blank on the given line,
+        returning the index of the last non-blank character."""
+        self._update_max_yx()
+        last = self.maxx
+        while True:
+            if curses.ascii.ascii(self.win.inch(y, last)) != curses.ascii.SP:
+                last = min(self.maxx, last+1)
+                break
+            elif last == 0:
+                break
+            last = last - 1
+        return last
+
+    def _insert_printable_char(self, ch):
+        self._update_max_yx()
+        (y, x) = self.win.getyx()
+        backyx = None
+        while y < self.maxy or x < self.maxx:
+            if self.insert_mode:
+                oldch = self.win.inch()
+            # The try-catch ignores the error we trigger from some curses
+            # versions by trying to write into the lowest-rightmost spot
+            # in the window.
+            try:
+                self.win.addch(ch)
+            except curses.error:
+                pass
+            if not self.insert_mode or not curses.ascii.isprint(oldch):
+                break
+            ch = oldch
+            (y, x) = self.win.getyx()
+            # Remember where to put the cursor back since we are in insert_mode
+            if backyx is None:
+                backyx = y, x
+
+        if backyx is not None:
+            self.win.move(*backyx)
+
+    def do_command(self, ch):
+        "Process a single editing command."
+        self._update_max_yx()
+        (y, x) = self.win.getyx()
+        self.lastcmd = ch
+        if curses.ascii.isprint(ch):
+            if y < self.maxy or x < self.maxx:
+                self._insert_printable_char(ch)
+        elif ch == curses.ascii.SOH:                           # ^a
+            self.win.move(y, 0)
+        elif ch in (curses.ascii.STX,curses.KEY_LEFT, curses.ascii.BS,curses.KEY_BACKSPACE):
+            if x > 0:
+                self.win.move(y, x-1)
+            elif y == 0:
+                pass
+            elif self.stripspaces:
+                self.win.move(y-1, self._end_of_line(y-1))
+            else:
+                self.win.move(y-1, self.maxx)
+            if ch in (curses.ascii.BS, curses.KEY_BACKSPACE):
+                self.win.delch()
+        elif ch == curses.ascii.EOT:                           # ^d
+            self.win.delch()
+        elif ch == curses.ascii.ENQ:                           # ^e
+            if self.stripspaces:
+                self.win.move(y, self._end_of_line(y))
+            else:
+                self.win.move(y, self.maxx)
+        elif ch in (curses.ascii.ACK, curses.KEY_RIGHT):       # ^f
+            if x < self.maxx:
+                self.win.move(y, x+1)
+            elif y == self.maxy:
+                pass
+            else:
+                self.win.move(y+1, 0)
+        elif ch == curses.ascii.BEL:                           # ^g
+            return 0
+        elif ch == curses.ascii.NL:                            # ^j
+            if self.maxy == 0:
+                return 0
+            elif y < self.maxy:
+                self.win.move(y+1, 0)
+        elif ch == curses.ascii.VT:                            # ^k
+            if x == 0 and self._end_of_line(y) == 0:
+                self.win.deleteln()
+            else:
+                # first undo the effect of self._end_of_line
+                self.win.move(y, x)
+                self.win.clrtoeol()
+        elif ch == curses.ascii.FF:                            # ^l
+            self.win.refresh()
+        elif ch in (curses.ascii.SO, curses.KEY_DOWN):         # ^n
+            if y < self.maxy:
+                self.win.move(y+1, x)
+                if x > self._end_of_line(y+1):
+                    self.win.move(y+1, self._end_of_line(y+1))
+        elif ch == curses.ascii.SI:                            # ^o
+            self.win.insertln()
+        elif ch in (curses.ascii.DLE, curses.KEY_UP):          # ^p
+            if y > 0:
+                self.win.move(y-1, x)
+                if x > self._end_of_line(y-1):
+                    self.win.move(y-1, self._end_of_line(y-1))
+        return 1
+
+    def gather(self):
+        "Collect and return the contents of the window."
+        result = ""
+        self._update_max_yx()
+        for y in range(self.maxy+1):
+            self.win.move(y, 0)
+            stop = self._end_of_line(y)
+            if stop == 0 and self.stripspaces:
+                continue
+            for x in range(self.maxx+1):
+                if self.stripspaces and x > stop:
+                    break
+                result = result + chr(curses.ascii.ascii(self.win.inch(y, x)))
+            if self.maxy > 0:
+                result = result + "\n"
+        return result
+
+    def edit(self, validate=None):
+        "Edit in the widget window and collect the results."
+        while 1:
+            ch = self.win.getch()
+            if validate:
+                ch = validate(ch)
+            if not ch:
+                continue
+            if not self.do_command(ch):
+                break
+            self.win.refresh()
+        return self.gather()
+
+if __name__ == '__main__':
+    def test_editbox(stdscr):
+        ncols, nlines = 9, 4
+        uly, ulx = 15, 20
+        stdscr.addstr(uly-2, ulx, "Use Ctrl-G to end editing.")
+        win = curses.newwin(nlines, ncols, uly, ulx)
+        rectangle(stdscr, uly-1, ulx-1, uly + nlines, ulx + ncols)
+        stdscr.refresh()
+        return Textbox(win).edit()
+
+    str = curses.wrapper(test_editbox)
+    print('Contents of text box:', repr(str))