Line data Source code
1 : /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
2 : * vim: set ts=8 sts=4 et sw=4 tw=99:
3 : * This Source Code Form is subject to the terms of the Mozilla Public
4 : * License, v. 2.0. If a copy of the MPL was not distributed with this
5 : * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 :
7 : #include "js/UbiNodeShortestPaths.h"
8 :
9 : #include "mozilla/Maybe.h"
10 : #include "mozilla/Move.h"
11 :
12 : #include "jsstr.h"
13 :
14 : namespace JS {
15 : namespace ubi {
16 :
17 : JS_PUBLIC_API(BackEdge::Ptr)
18 0 : BackEdge::clone() const
19 : {
20 0 : BackEdge::Ptr clone(js_new<BackEdge>());
21 0 : if (!clone)
22 0 : return nullptr;
23 :
24 0 : clone->predecessor_ = predecessor();
25 0 : if (name()) {
26 0 : clone->name_ = js::DuplicateString(name().get());
27 0 : if (!clone->name_)
28 0 : return nullptr;
29 : }
30 0 : return mozilla::Move(clone);
31 : }
32 :
33 : #ifdef DEBUG
34 :
35 : static void
36 0 : dumpNode(const JS::ubi::Node& node)
37 : {
38 0 : fprintf(stderr, " %p ", (void*) node.identifier());
39 0 : js_fputs(node.typeName(), stderr);
40 0 : if (node.coarseType() == JS::ubi::CoarseType::Object) {
41 0 : if (const char* clsName = node.jsObjectClassName())
42 0 : fprintf(stderr, " [object %s]", clsName);
43 : }
44 0 : fputc('\n', stderr);
45 0 : }
46 :
47 : JS_PUBLIC_API(void)
48 0 : dumpPaths(JSContext* cx, Node node, uint32_t maxNumPaths /* = 10 */)
49 : {
50 0 : mozilla::Maybe<AutoCheckCannotGC> nogc;
51 :
52 0 : JS::ubi::RootList rootList(cx, nogc, true);
53 0 : MOZ_ASSERT(rootList.init());
54 :
55 0 : NodeSet targets;
56 0 : bool ok = targets.init() && targets.putNew(node);
57 0 : MOZ_ASSERT(ok);
58 :
59 0 : auto paths = ShortestPaths::Create(cx, nogc.ref(), maxNumPaths, &rootList, mozilla::Move(targets));
60 0 : MOZ_ASSERT(paths.isSome());
61 :
62 0 : int i = 0;
63 0 : ok = paths->forEachPath(node, [&](Path& path) {
64 0 : fprintf(stderr, "Path %d:\n", i++);
65 0 : for (auto backEdge : path) {
66 0 : dumpNode(backEdge->predecessor());
67 0 : fprintf(stderr, " |\n");
68 0 : fprintf(stderr, " |\n");
69 0 : fprintf(stderr, " '");
70 :
71 0 : const char16_t* name = backEdge->name().get();
72 0 : if (!name)
73 0 : name = u"<no edge name>";
74 0 : js_fputs(name, stderr);
75 0 : fprintf(stderr, "'\n");
76 :
77 0 : fprintf(stderr, " |\n");
78 0 : fprintf(stderr, " V\n");
79 : }
80 :
81 0 : dumpNode(node);
82 0 : fputc('\n', stderr);
83 0 : return true;
84 0 : });
85 0 : MOZ_ASSERT(ok);
86 :
87 0 : if (i == 0)
88 0 : fprintf(stderr, "No retaining paths found.\n");
89 0 : }
90 : #endif
91 :
92 : } // namespace ubi
93 : } // namespace JS
|