xref: /openbsd-src/gnu/llvm/lldb/examples/scripting/tree_utils.py (revision f6aab3d83b51b91c24247ad2c2573574de475a82)
1*061da546Spatrick"""
2*061da546Spatrick# ===-- tree_utils.py ---------------------------------------*- Python -*-===//
3*061da546Spatrick#
4*061da546Spatrick# Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
5*061da546Spatrick# See https://llvm.org/LICENSE.txt for license information.
6*061da546Spatrick# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
7*061da546Spatrick#
8*061da546Spatrick# ===---------------------------------------------------------------------===//
9*061da546Spatrick
10*061da546Spatricktree_utils.py  - A set of functions for examining binary
11*061da546Spatricksearch trees, based on the example search tree defined in
12*061da546Spatrickdictionary.c.  These functions contain calls to LLDB API
13*061da546Spatrickfunctions, and assume that the LLDB Python module has been
14*061da546Spatrickimported.
15*061da546Spatrick
16*061da546SpatrickFor a thorough explanation of how the DFS function works, and
17*061da546Spatrickfor more information about dictionary.c go to
18*061da546Spatrickhttp://lldb.llvm.org/scripting.html
19*061da546Spatrick"""
20*061da546Spatrick
21*061da546Spatrick
22*061da546Spatrickdef DFS(root, word, cur_path):
23*061da546Spatrick    """
24*061da546Spatrick    Recursively traverse a binary search tree containing
25*061da546Spatrick    words sorted alphabetically, searching for a particular
26*061da546Spatrick    word in the tree.  Also maintains a string representing
27*061da546Spatrick    the path from the root of the tree to the current node.
28*061da546Spatrick    If the word is found in the tree, return the path string.
29*061da546Spatrick    Otherwise return an empty string.
30*061da546Spatrick
31*061da546Spatrick    This function assumes the binary search tree is
32*061da546Spatrick    the one defined in dictionary.c  It uses LLDB API
33*061da546Spatrick    functions to examine and traverse the tree nodes.
34*061da546Spatrick    """
35*061da546Spatrick
36*061da546Spatrick    # Get pointer field values out of node 'root'
37*061da546Spatrick
38*061da546Spatrick    root_word_ptr = root.GetChildMemberWithName("word")
39*061da546Spatrick    left_child_ptr = root.GetChildMemberWithName("left")
40*061da546Spatrick    right_child_ptr = root.GetChildMemberWithName("right")
41*061da546Spatrick
42*061da546Spatrick    # Get the word out of the word pointer and strip off
43*061da546Spatrick    # surrounding quotes (added by call to GetSummary).
44*061da546Spatrick
45*061da546Spatrick    root_word = root_word_ptr.GetSummary()
46*061da546Spatrick    end = len(root_word) - 1
47*061da546Spatrick    if root_word[0] == '"' and root_word[end] == '"':
48*061da546Spatrick        root_word = root_word[1:end]
49*061da546Spatrick    end = len(root_word) - 1
50*061da546Spatrick    if root_word[0] == '\'' and root_word[end] == '\'':
51*061da546Spatrick        root_word = root_word[1:end]
52*061da546Spatrick
53*061da546Spatrick    # Main depth first search
54*061da546Spatrick
55*061da546Spatrick    if root_word == word:
56*061da546Spatrick        return cur_path
57*061da546Spatrick    elif word < root_word:
58*061da546Spatrick
59*061da546Spatrick        # Check to see if left child is NULL
60*061da546Spatrick
61*061da546Spatrick        if left_child_ptr.GetValue() is None:
62*061da546Spatrick            return ""
63*061da546Spatrick        else:
64*061da546Spatrick            cur_path = cur_path + "L"
65*061da546Spatrick            return DFS(left_child_ptr, word, cur_path)
66*061da546Spatrick    else:
67*061da546Spatrick
68*061da546Spatrick        # Check to see if right child is NULL
69*061da546Spatrick
70*061da546Spatrick        if right_child_ptr.GetValue() is None:
71*061da546Spatrick            return ""
72*061da546Spatrick        else:
73*061da546Spatrick            cur_path = cur_path + "R"
74*061da546Spatrick            return DFS(right_child_ptr, word, cur_path)
75*061da546Spatrick
76*061da546Spatrick
77*061da546Spatrickdef tree_size(root):
78*061da546Spatrick    """
79*061da546Spatrick    Recursively traverse a binary search tree, counting
80*061da546Spatrick    the nodes in the tree.  Returns the final count.
81*061da546Spatrick
82*061da546Spatrick    This function assumes the binary search tree is
83*061da546Spatrick    the one defined in dictionary.c  It uses LLDB API
84*061da546Spatrick    functions to examine and traverse the tree nodes.
85*061da546Spatrick    """
86*061da546Spatrick    if (root.GetValue is None):
87*061da546Spatrick        return 0
88*061da546Spatrick
89*061da546Spatrick    if (int(root.GetValue(), 16) == 0):
90*061da546Spatrick        return 0
91*061da546Spatrick
92*061da546Spatrick    left_size = tree_size(root.GetChildAtIndex(1))
93*061da546Spatrick    right_size = tree_size(root.GetChildAtIndex(2))
94*061da546Spatrick
95*061da546Spatrick    total_size = left_size + right_size + 1
96*061da546Spatrick    return total_size
97*061da546Spatrick
98*061da546Spatrick
99*061da546Spatrickdef print_tree(root):
100*061da546Spatrick    """
101*061da546Spatrick    Recursively traverse a binary search tree, printing out
102*061da546Spatrick    the words at the nodes in alphabetical order (the
103*061da546Spatrick    search order for the binary tree).
104*061da546Spatrick
105*061da546Spatrick    This function assumes the binary search tree is
106*061da546Spatrick    the one defined in dictionary.c  It uses LLDB API
107*061da546Spatrick    functions to examine and traverse the tree nodes.
108*061da546Spatrick    """
109*061da546Spatrick    if (root.GetChildAtIndex(1).GetValue() is not None) and (
110*061da546Spatrick            int(root.GetChildAtIndex(1).GetValue(), 16) != 0):
111*061da546Spatrick        print_tree(root.GetChildAtIndex(1))
112*061da546Spatrick
113*061da546Spatrick    print(root.GetChildAtIndex(0).GetSummary())
114*061da546Spatrick
115*061da546Spatrick    if (root.GetChildAtIndex(2).GetValue() is not None) and (
116*061da546Spatrick            int(root.GetChildAtIndex(2).GetValue(), 16) != 0):
117*061da546Spatrick        print_tree(root.GetChildAtIndex(2))
118