blob: 3df079d247d532cccceefba8dcdc7d320f269b30 [file] [log] [blame]
Ben Wagner85c6aad2017-10-18 17:34:09 -04001# Copyright 2017 Google Inc.
2#
3# Use of this source code is governed by a BSD-style license that can be
4# found in the LICENSE file.
5
6"""
7Visualize bitmaps in gdb.
8
9(gdb) source <path to this file>
10(gdb) sk_bitmap <symbol>
11
12This should pop up a window with the bitmap displayed.
13Right clicking should bring up a menu, allowing the
14bitmap to be saved to a file.
15"""
16
17import gdb
18from enum import Enum
19try:
20 from PIL import Image
21except ImportError:
22 import Image
23
24class ColorType(Enum):
25 unknown = 0
26 alpha_8 = 1
27 rgb_565 = 2
28 argb_4444 = 3
29 rgba_8888 = 4
Ben Wagner2de15fd2018-06-20 16:34:15 -040030 rgbx_8888 = 5
31 bgra_8888 = 6
32 rgba_1010102 = 7
33 rgb_101010x = 8
34 gray_8 = 9
35 rgba_F16 = 10
Ben Wagner85c6aad2017-10-18 17:34:09 -040036
37class AlphaType(Enum):
38 unknown = 0
39 opaque = 1
40 premul = 2
41 unpremul = 3
42
43class sk_bitmap(gdb.Command):
44 """Displays the content of an SkBitmap image."""
45
46 def __init__(self):
47 super(sk_bitmap, self).__init__('sk_bitmap',
48 gdb.COMMAND_SUPPORT,
49 gdb.COMPLETE_FILENAME)
50
51 def invoke(self, arg, from_tty):
52 frame = gdb.selected_frame()
53 val = frame.read_var(arg)
54 if str(val.type.strip_typedefs()) == 'SkBitmap':
Ben Wagner2de15fd2018-06-20 16:34:15 -040055 pixmap = val['fPixmap']
56 pixels = pixmap['fPixels']
57 row_bytes = pixmap['fRowBytes']
58 info = pixmap['fInfo']
59 dimensions = info['fDimensions']
60 width = dimensions['fWidth']
61 height = dimensions['fHeight']
Ben Wagner85c6aad2017-10-18 17:34:09 -040062 color_type = info['fColorType']
63 alpha_type = info['fAlphaType']
64
65 process = gdb.selected_inferior()
66 memory_data = process.read_memory(pixels, row_bytes * height)
67 size = (width, height)
68 image = None
69 # See Unpack.c for the values understood after the "raw" parameter.
70 if color_type == ColorType.bgra_8888.value:
71 if alpha_type == AlphaType.unpremul.value:
Ben Wagner2de15fd2018-06-20 16:34:15 -040072 image = Image.frombytes("RGBA", size, memory_data,
Ben Wagner85c6aad2017-10-18 17:34:09 -040073 "raw", "BGRA", row_bytes, 1)
74 elif alpha_type == AlphaType.premul.value:
75 # RGBA instead of RGBa, because Image.show() doesn't work with RGBa.
Ben Wagner2de15fd2018-06-20 16:34:15 -040076 image = Image.frombytes("RGBA", size, memory_data,
Ben Wagner85c6aad2017-10-18 17:34:09 -040077 "raw", "BGRa", row_bytes, 1)
78
79 if image:
80 # Fails on premultiplied alpha, it cannot convert to RGB.
81 image.show()
82 else:
83 print ("Need to add support for %s %s." % (
84 str(ColorType(int(color_type))),
85 str(AlphaType(int(alpha_type)))
86 ))
87
88sk_bitmap()