xref: /llvm-project/lldb/utils/lui/breakwin.py (revision 602e47c5f9fd2e14c7bfb6111e6558fa0d27c87f)
1##===-- breakwin.py ------------------------------------------*- Python -*-===##
2##
3# Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4# See https://llvm.org/LICENSE.txt for license information.
5# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6##
7##===----------------------------------------------------------------------===##
8
9import cui
10import curses
11import lldb
12import lldbutil
13import re
14
15
16class BreakWin(cui.ListWin):
17    def __init__(self, driver, x, y, w, h):
18        super(BreakWin, self).__init__(x, y, w, h)
19        self.driver = driver
20        self.update()
21        self.showDetails = {}
22
23    def handleEvent(self, event):
24        if isinstance(event, lldb.SBEvent):
25            if lldb.SBBreakpoint.EventIsBreakpointEvent(event):
26                self.update()
27        if isinstance(event, int):
28            if event == ord("d"):
29                self.deleteSelected()
30            if event == curses.ascii.NL or event == curses.ascii.SP:
31                self.toggleSelected()
32            elif event == curses.ascii.TAB:
33                if self.getSelected() != -1:
34                    target = self.driver.getTarget()
35                    if not target.IsValid():
36                        return
37                    i = target.GetBreakpointAtIndex(self.getSelected()).id
38                    self.showDetails[i] = not self.showDetails[i]
39                    self.update()
40        super(BreakWin, self).handleEvent(event)
41
42    def toggleSelected(self):
43        if self.getSelected() == -1:
44            return
45        target = self.driver.getTarget()
46        if not target.IsValid():
47            return
48        bp = target.GetBreakpointAtIndex(self.getSelected())
49        bp.SetEnabled(not bp.IsEnabled())
50
51    def deleteSelected(self):
52        if self.getSelected() == -1:
53            return
54        target = self.driver.getTarget()
55        if not target.IsValid():
56            return
57        bp = target.GetBreakpointAtIndex(self.getSelected())
58        target.BreakpointDelete(bp.id)
59
60    def update(self):
61        target = self.driver.getTarget()
62        if not target.IsValid():
63            self.win.erase()
64            self.win.noutrefresh()
65            return
66        selected = self.getSelected()
67        self.clearItems()
68        for i in range(0, target.GetNumBreakpoints()):
69            bp = target.GetBreakpointAtIndex(i)
70            if bp.IsInternal():
71                continue
72            text = lldbutil.get_description(bp)
73            # FIXME: Use an API for this, not parsing the description.
74            match = re.search("SBBreakpoint: id = ([^,]+), (.*)", text)
75            try:
76                id = match.group(1)
77                desc = match.group(2).strip()
78                if bp.IsEnabled():
79                    text = "%s: %s" % (id, desc)
80                else:
81                    text = "%s: (disabled) %s" % (id, desc)
82            except ValueError as e:
83                # bp unparsable
84                pass
85
86            if self.showDetails.setdefault(bp.id, False):
87                for location in bp:
88                    desc = lldbutil.get_description(
89                        location, lldb.eDescriptionLevelFull
90                    )
91                    text += "\n  " + desc
92            self.addItem(text)
93        self.setSelected(selected)
94