diff --git a/linux-ramdump-parser-v2/parsers/cpr3_info.py b/linux-ramdump-parser-v2/parsers/cpr3_info.py
new file mode 100644
index 0000000000000000000000000000000000000000..fbcb5df5f18c4d38f4dc8682879ab6c1f36cbbb3
--- /dev/null
+++ b/linux-ramdump-parser-v2/parsers/cpr3_info.py
@@ -0,0 +1,584 @@
+# Copyright (c) 2015, The Linux Foundation. All rights reserved.
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License version 2 and
+# only version 2 as published by the Free Software Foundation.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+
+import linux_list
+from print_out import print_out_str
+from parser_util import register_parser, RamParser
+from collections import defaultdict
+
+
+@register_parser('--cpr3-info', 'Print CPR3 information')
+class CPR3Info(RamParser):
+    def __init__(self, *args):
+        super(CPR3Info, self).__init__(*args)
+        self.head = ''
+        self.cprinfo_fields = ['speed_bin', 'cpr_fuse_revision',
+                               'cpr_fuse_map_match', 'num_fuse_corners',
+                               'num_corners', 'corner']
+        self.voltages = ['ceiling_volt', 'open_loop_volt',
+                         'last_volt', 'floor_volt']
+        self.corner_info = ['cpr_fuse_target_quot',
+                            'quot_adjust', 'corner_map']
+        self.value_list = defaultdict(list)
+        self.attr_list = defaultdict(list)
+        self.output = []
+        self.consumer_head = ''
+
+    def get_cpr(self):
+        # Return if the cpr3_regulator_list is not available
+        cpr = self.ramdump.addr_lookup('cpr3_controller_list')
+        if cpr is None:
+            self.output_file.write(
+                "NOTE: 'cpr3_regulator_list' list " +
+                "not found to extract cpr information")
+            return
+
+        head = self.ramdump.read_word(cpr)
+        self.head = cpr
+        node_offset = self.ramdump.field_offset('struct cpr3_controller',
+                                                'list')
+        c_w = linux_list.ListWalker(self.ramdump, head, node_offset)
+        c_w.walk(head, self.cpr_walker)
+
+    def get_kryo(self):
+        kryo_addr = self.ramdump.addr_lookup('kryo_regulator_list')
+        if kryo_addr is None:
+            print(
+                "NOTE: 'kryo_regulator_list' list " +
+                "not found to extract kryo_addr information")
+            return
+        head = self.ramdump.read_word(kryo_addr)
+        self.head = kryo_addr
+        node_offset = self.ramdump.field_offset('struct kryo_regulator',
+                                                'link')
+        k_w = linux_list.ListWalker(self.ramdump, head, node_offset)
+        tmp = "=" * 80 + "\n"
+        tmp += "Kryo Regulator (LDO/BHS management)\n"
+        tmp += "=" * 80 + "\n"
+        self.output.append(tmp)
+        k_w.walk(head, self.kryo_walker)
+
+    def dump_cpr3_regulator_voltages(self, vreg_addr):
+        corner_count = self.ramdump.read_int(
+            vreg_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_regulator',
+                'corner_count'))
+        tmp = 'CPR voltages(uV) and Target Quotients\n'
+        tmp += "%-7s%-3s%-10s%-10s%-10s%-21s%-40s\n" % (
+               "Corner", "-", "Floor", "Open-Loop", "Ceiling",
+               "Cached closed-loop",
+               "Target Quotients")
+        self.output.append(tmp)
+        base_addr = self.ramdump.read_word(
+            vreg_addr +
+            self.ramdump.field_offset('struct cpr3_regulator', 'corner'))
+        size = self.ramdump.sizeof('struct cpr3_corner')
+        for i in range(corner_count):
+            corner_addr = base_addr + size * i
+            try:
+                self.dump_cpr3_corner_info(corner_addr, i + 1, 1, 1)
+            except:
+                self.output.append(
+                    "Note: Failed to dump cpr3 regulator voltage\n")
+                return
+
+    def dump_cpr3_corner_info(self, aggr_corner_addr, corner_num,
+                              print_quots, list_format):
+        if aggr_corner_addr is None:
+            return
+        ceiling = self.ramdump.read_int(
+            aggr_corner_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_corner', 'ceiling_volt'))
+        open_loop = self.ramdump.read_int(
+            aggr_corner_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_corner', 'open_loop_volt'))
+        last = self.ramdump.read_int(
+            aggr_corner_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_corner', 'last_volt'))
+        floor = self.ramdump.read_int(
+            aggr_corner_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_corner', 'floor_volt'))
+        quots = ""
+        if print_quots == 1:
+            t0 = aggr_corner_addr + self.ramdump.field_offset(
+                'struct cpr3_corner', 'target_quot')
+            size = self.ramdump.sizeof('u32')
+            num = self.ramdump.sizeof('((struct cpr3_corner*)0)->target_quot') \
+                / size
+            for i in range(num):
+                quot = self.ramdump.read_u32(t0 + i * size)
+                quots = quots + " " + str(quot)
+
+        if list_format == 0:
+            tmp = '%-30s = %d uV\n' % ("Ceiling volt", ceiling)
+            tmp += '%-30s = %d uV\n' % ("Open-loop", open_loop)
+            tmp += '%-30s = %d uV\n' % ("Cached closed-loop", last)
+            tmp += '%-30s = %d uV\n' % ("Floor", floor)
+            self.output.append(tmp)
+            if print_quots == 1:
+                tmp = "\n%-30s = %s\n" % ("Target quotients", quots)
+                self.output.append(tmp)
+            self.output.append("\n")
+        else:
+            tmp = "%-7d%-3s%-10d%-10d%-10d%-20d" % (
+                corner_num, "-", floor, open_loop, ceiling, last)
+            tmp += quots
+            tmp += "\n"
+            self.output.append(tmp)
+
+    def dump_vdd_regulator(self, ctrl_addr):
+        tmp = ""
+        vdd_reg_addr = self.ramdump.read_word(
+            ctrl_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_controller', 'vdd_regulator'))
+        if vdd_reg_addr is None:
+            return
+        rdev_addr = self.ramdump.read_word(
+            vdd_reg_addr +
+            self.ramdump.field_offset(
+                'struct regulator',
+                'rdev'))
+        reg_data_addr = self.ramdump.read_word(
+            rdev_addr +
+            self.ramdump.field_offset('struct regulator_dev', 'reg_data'))
+
+        desc_addr = self.ramdump.read_word(
+            rdev_addr +
+            self.ramdump.field_offset('struct regulator_dev', 'desc'))
+
+        desc_ops_addr = self.ramdump.read_word(
+            desc_addr +
+            self.ramdump.field_offset('struct regulator_desc', 'ops'))
+
+        name_addr = self.ramdump.read_word(
+            desc_addr +
+            self.ramdump.field_offset('struct regulator_desc', 'name'))
+
+        name = self.ramdump.read_cstring(name_addr, 48)
+        tmp += '\n%-30s = %s\n' % ("PMIC supply", name)
+        duple = self.ramdump.unwind_lookup(desc_ops_addr)
+        function_name = duple[0]
+
+        if "qpnp" in function_name:
+            # QPNP-regulator
+            set_points_addr = self.ramdump.read_word(
+                reg_data_addr + self.ramdump.field_offset(
+                    'struct qpnp_regulator',
+                    'set_points'))
+            range_addr = self.ramdump.read_word(
+                set_points_addr +
+                self.ramdump.field_offset(
+                    'struct qpnp_voltage_set_points', 'range'))
+            step_uV = self.ramdump.read_int(
+                range_addr +
+                self.ramdump.field_offset(
+                    'struct qpnp_voltage_range',
+                    'step_uV'))
+            min_uV = self.ramdump.read_int(
+                range_addr +
+                self.ramdump.field_offset(
+                    'struct qpnp_voltage_range', 'min_uV'))
+            volt_sel = self.ramdump.read_byte(
+                reg_data_addr + 1 +
+                self.ramdump.field_offset(
+                    'struct qpnp_regulator', 'ctrl_reg'))
+            volt = (volt_sel * step_uV) + min_uV
+            tmp += "%-30s = %d uV\n" % ("PMIC voltage", volt)
+        if "spm" in function_name:
+            last_set_volt = self.ramdump.read_int(
+                reg_data_addr + self.ramdump.field_offset(
+                    'struct spm_vreg', 'last_set_uV'))
+            tmp += "%-30s = %d uV\n" % ("PMIC last set voltage",
+                                        last_set_volt)
+        self.output.append(tmp)
+
+    def get_apm_threshold(self, addr_ctrl):
+        apm_addr = self.ramdump.read_word(
+            addr_ctrl + self.ramdump.field_offset('struct cpr3_controller',
+                                                  'apm'))
+        if apm_addr is None:
+            return
+        apm_thresh_volt = self.ramdump.read_int(
+            addr_ctrl + self.ramdump.field_offset(
+                'struct cpr3_controller', 'apm_threshold_volt'))
+        if apm_thresh_volt == 0:
+            return
+        tmp = '%-30s = %d uV\n' % ("APM threshold", apm_thresh_volt)
+        self.output.append(tmp)
+
+    def get_aging_info(self, ctrl_addr):
+        test = self.ramdump.field_offset(
+            'struct cpr3_controller', 'aging_required')
+        if test is None:
+            return
+        aging_required = self.ramdump.read_bool(
+            ctrl_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_controller', 'aging_required'))
+        aging_succeeded = self.ramdump.read_bool(
+            ctrl_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_controller', 'aging_succeeded'))
+        aging_failed = self.ramdump.read_bool(
+            ctrl_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_controller', 'aging_failed'))
+        tmp = ""
+        if (aging_required or aging_succeeded or aging_failed):
+            if aging_succeeded:
+                aging_ref_adjust_volt = self.ramdump.read_int(
+                    ctrl_addr +
+                    self.ramdump.field_offset(
+                        'struct cpr3_controller', 'aging_ref_adjust_volt'))
+                tmp += '%-30s = %s\n' % ("Aging measurement", "succeeded")
+                tmp += '%-30s = %d uV\n' % ("Aging adjustment voltage",
+                                            aging_ref_adjust_volt)
+            elif aging_failed:
+                tmp += '%-30s = %s\n' % ("Aging measurement",
+                                         "failed")
+            else:
+                tmp += '%-30s = %s\n' % ("Aging measurement",
+                                         "not yet executed")
+        self.output.append(tmp)
+
+    def dump_cpr3_regulator_state(self, vreg_addr):
+        tmp = ""
+        if vreg_addr is None:
+            return
+        name_addr = self.ramdump.read_word(
+            vreg_addr + self.ramdump.field_offset(
+                'struct cpr3_regulator', 'name'))
+        name = self.ramdump.read_cstring(name_addr, 48)
+        tmp += "-" * 80 + "\n"
+        tmp += "Regulator: %s\n" % name
+        tmp += "-" * 80 + "\n"
+        vreg_enabled = self.ramdump.read_bool(
+            vreg_addr + self.ramdump.field_offset(
+                'struct cpr3_regulator',
+                'vreg_enabled'))
+        current_corner = self.ramdump.read_int(
+            vreg_addr + self.ramdump.field_offset(
+                'struct cpr3_regulator', 'current_corner'))
+        corner_count = self.ramdump.read_int(
+            vreg_addr + self.ramdump.field_offset(
+                'struct cpr3_regulator',
+                'corner_count'))
+        ldo_regulator_addr = self.ramdump.read_word(
+            vreg_addr + self.ramdump.field_offset(
+                'struct cpr3_regulator', 'ldo_regulator'))
+        ldo_mode_allowed = self.ramdump.read_bool(
+            vreg_addr + self.ramdump.field_offset(
+                'struct cpr3_regulator', 'ldo_mode_allowed'))
+        cpr_rev_fuse = self.ramdump.read_int(
+            vreg_addr + self.ramdump.field_offset(
+                'struct cpr3_regulator', 'cpr_rev_fuse'))
+        if ldo_regulator_addr != 0:
+            ldo_mode_bool = self.ramdump.read_bool(
+                vreg_addr + self.ramdump.field_offset(
+                    'struct cpr3_regulator',
+                    'ldo_regulator_bypass'))
+            if ldo_mode_bool:
+                ldo_mode = "LDO"
+            else:
+                ldo_mode = "BHS"
+
+        tmp += "%-30s = %d\n" % ("CPR fuse revision", cpr_rev_fuse)
+        fuse_combo = self.ramdump.read_int(
+            vreg_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_regulator', 'fuse_combo'))
+        tmp += "%-30s = %d\n" % ("CPR fuse combo", fuse_combo)
+        speed_bin_fuse = self.ramdump.read_int(
+            vreg_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_regulator',
+                'speed_bin_fuse'))
+        tmp += "%-30s = %d\n" % ("Speed-bin fuse", speed_bin_fuse)
+
+        tmp += "\n%-30s = %d/%d\n" % ("CPR corner", current_corner + 1,
+                                      corner_count)
+        if vreg_enabled is True:
+            vreg_enabled = 1
+        else:
+            vreg_enabled = 0
+        tmp += "%-30s = %d\n" % ("Enabled", vreg_enabled)
+
+        if ldo_regulator_addr != 0:
+            if ldo_mode_allowed is True:
+                ldo_mode_allowed = 1
+            else:
+                ldo_mode_allowed = 0
+            tmp += "\n%-30s = %d\n" % ("LDO mode allowed", ldo_mode_allowed)
+            tmp += "%-30s = %s\n" % ("LDO/BHS mode", ldo_mode)
+        tmp += "\nCurrent CPR voltages:\n"
+        self.output.append(tmp)
+        tmp = ""
+        corner_addr = self.ramdump.read_word(
+            vreg_addr + self.ramdump.field_offset(
+                'struct cpr3_regulator', 'corner'))
+        size = self.ramdump.sizeof("struct cpr3_corner")
+        corner_addr = corner_addr + current_corner * size
+        self.dump_cpr3_corner_info(corner_addr, 0, 1, 0)
+        self.dump_cpr3_regulator_voltages(vreg_addr)
+
+        rdev_addr = self.ramdump.read_word(
+            vreg_addr + self.ramdump.field_offset('struct cpr3_regulator',
+                                                  'rdev'))
+        offset = self.ramdump.field_offset('struct regulator_dev',
+                                           'consumer_list')
+        self.dump_consumer(rdev_addr + offset)
+
+    def dump_cpr3_thread_state(self, thread_addr):
+        tmp = ""
+        thread_id = self.ramdump.read_u32(
+            thread_addr + self.ramdump.field_offset(
+                'struct cpr3_thread', 'thread_id'))
+        aggr_corner_addr = thread_addr + self.ramdump.field_offset(
+            'struct cpr3_thread', 'aggr_corner')
+        tmp += "-" * 80 + "\n"
+        tmp += "Thread: %d\n" % thread_id
+        tmp += "-" * 80 + "\n"
+        tmp += "CPR aggregated voltages:\n"
+        self.output.append(tmp)
+
+        self.dump_cpr3_corner_info(aggr_corner_addr, 0, 1, 0)
+        vreg_addr = self.ramdump.read_word(
+            thread_addr +
+            self.ramdump.field_offset('struct cpr3_thread', 'vreg'))
+        vreg_count = self.ramdump.read_int(
+            thread_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_thread', 'vreg_count'))
+
+        size_reg = self.ramdump.sizeof('struct cpr3_regulator')
+        for i in range(vreg_count):
+            self.dump_cpr3_regulator_state(vreg_addr + i * size_reg)
+
+    def cpr_walker(self, ctrl_addr):
+        if ctrl_addr == self.head:
+            return
+        cpr_controller_name_addr = self.ramdump.read_word(
+            ctrl_addr + self.ramdump.field_offset('struct cpr3_controller',
+                                                  'name'))
+        cpr_controller_name = self.ramdump.read_cstring(
+            cpr_controller_name_addr, 48)
+        supports_hw_closed_loop = self.ramdump.read_bool(
+            ctrl_addr + self.ramdump.field_offset(
+                'struct cpr3_controller',
+                'supports_hw_closed_loop'))
+        use_hw_closed_loop = self.ramdump.read_bool(
+            ctrl_addr + self.ramdump.field_offset(
+                'struct cpr3_controller',
+                'use_hw_closed_loop'))
+        cpr_allowed_sw = self.ramdump.read_bool(
+            ctrl_addr + self.ramdump.field_offset(
+                'struct cpr3_controller',
+                'cpr_allowed_sw'))
+        cpr_enabled = self.ramdump.read_bool(
+            ctrl_addr + self.ramdump.field_offset(
+                'struct cpr3_controller', 'cpr_enabled'))
+        if supports_hw_closed_loop == 1:
+            if cpr_allowed_sw == 0:
+                cpr_mode = "open-loop"
+            elif use_hw_closed_loop == 0:
+                cpr_mode = "SW closed-loop"
+            else:
+                cpr_mode = "HW closed-loop"
+        else:
+            if cpr_allowed_sw == 0:
+                cpr_mode = "open-loop"
+            else:
+                cpr_mode = "closed-loop"
+        tmp = ""
+        if cpr_controller_name is None:
+            return
+        tmp += "=" * 80 + "\n"
+        tmp += 'CPR3 controller state: %s\n' % cpr_controller_name
+        tmp += "=" * 80 + "\n"
+        tmp += '%-30s = %s\n' % ("CPR mode", cpr_mode)
+        tmp += '%-30s = %d\n' % ("CPR loop currently operating",
+                                 cpr_enabled)
+        self.output.append(tmp)
+        tmp = ""
+        self.get_apm_threshold(ctrl_addr)
+        self.get_aging_info(ctrl_addr)
+        self.dump_vdd_regulator(ctrl_addr)
+        if cpr_allowed_sw == 1 and use_hw_closed_loop == 1:
+            tmp = "* The actual voltage at the PMIC may be anywhere " \
+                  "between the aggregated ceiling and floor voltage when"\
+                  " using CPR HW closed-loop mode.\n"
+            self.output.append(tmp)
+            tmp = ""
+        aggr_corner_addr = ctrl_addr + self.ramdump.field_offset(
+            'struct cpr3_controller', 'aggr_corner')
+        self.output.append("\nCPR aggregated voltages:\n")
+        self.dump_cpr3_corner_info(aggr_corner_addr, 0, 0, 0)
+        thread_addr = self.ramdump.read_word(
+            ctrl_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_controller', 'thread'))
+        thread_count = self.ramdump.read_int(
+            ctrl_addr +
+            self.ramdump.field_offset(
+                'struct cpr3_controller', 'thread_count'))
+        size_thr = self.ramdump.sizeof('struct cpr3_thread')
+        for i in range(thread_count):
+            self.dump_cpr3_thread_state(thread_addr + i * size_thr)
+        # print new line for each regulator struct
+        tmp += '\n'
+        self.output.append(tmp)
+
+    def kryo_walker(self, kryo_addr):
+        if kryo_addr == self.head:
+            return
+
+        retention_mode = self.ramdump.read_int(
+            kryo_addr +
+            self.ramdump.field_offset(
+                'struct kryo_regulator', 'retention_mode'))
+        mode = self.ramdump.read_int(
+            kryo_addr + self.ramdump.field_offset('struct kryo_regulator',
+                                                  'mode'))
+        if mode == 0:
+            mode = "BHS"
+        else:
+            mode = "LDO"
+
+        if retention_mode == 0:
+            retention_mode = "BHS"
+        else:
+            retention_mode = "LDO"
+
+        volt = self.ramdump.read_int(kryo_addr + self.ramdump.field_offset(
+            'struct kryo_regulator', 'volt'))
+        retention_volt = self.ramdump.read_int(
+            kryo_addr +
+            self.ramdump.field_offset(
+                'struct kryo_regulator',
+                'retention_volt'))
+        vreg_en = self.ramdump.read_bool(
+            kryo_addr +
+            self.ramdump.field_offset(
+                'struct kryo_regulator',
+                'vreg_en'))
+        vref_func_step_volt = self.ramdump.read_int(
+            kryo_addr +
+            self.ramdump.field_offset(
+                'struct kryo_regulator',
+                'vref_func_step_volt'))
+        vref_func_min_volt = self.ramdump.read_int(
+            kryo_addr +
+            self.ramdump.field_offset(
+                'struct kryo_regulator',
+                'vref_func_min_volt'))
+        vref_func_max_volt = self.ramdump.read_int(
+            kryo_addr + self.ramdump.field_offset(
+                'struct kryo_regulator', 'vref_func_max_volt'))
+        vref_ret_step_volt = self.ramdump.read_int(
+            kryo_addr + self.ramdump.field_offset(
+                'struct kryo_regulator', 'vref_ret_step_volt'))
+        vref_ret_min_volt = self.ramdump.read_int(
+            kryo_addr + self.ramdump.field_offset(
+                'struct kryo_regulator', 'vref_ret_min_volt'))
+        vref_ret_max_volt = self.ramdump.read_int(
+            kryo_addr + self.ramdump.field_offset(
+                'struct kryo_regulator', 'vref_ret_max_volt'))
+        name_addr = self.ramdump.read_word(
+            kryo_addr +
+            self.ramdump.field_offset('struct kryo_regulator', 'name'))
+        name = self.ramdump.read_cstring(name_addr, 48)
+        tmp = ""
+        tmp += "-" * 80 + "\n"
+        tmp += "Regulator: %s\n" % name
+        tmp += "-" * 80 + "\n"
+        tmp += "%-30s = %d\n" % ("Enabled", vreg_en)
+        tmp += "%-30s = %s\n" % ("Mode", mode)
+
+        tmp += "%-30s = %d uV\n" % ("Voltage", volt)
+        tmp += "%-30s = %s\n" % ("Retention Mode", retention_mode)
+
+        tmp += "%-30s = %d uV\n" % ("Retention Voltage", retention_volt)
+        tmp += "%-30s = %d uV\n" % ("Vref Functional Step Voltage",
+                                    vref_func_step_volt)
+
+        tmp += "%-30s = %d uV\n" % ("Vref Functional Min Voltage",
+                                    vref_func_min_volt)
+
+        tmp += "%-30s = %d uV\n" % ("Vref Functional Max Voltage",
+                                    vref_func_max_volt)
+
+        tmp += "%-30s = %d uV\n" % ("Vref Retention Step Voltage",
+                                    vref_ret_step_volt)
+
+        tmp += "%-30s = %d uV\n" % ("Vref Retention Min Voltage",
+                                    vref_ret_min_volt)
+
+        tmp += "%-30s = %d uV\n" % ("Vref Retention Max Voltage",
+                                    vref_ret_max_volt)
+
+        self.output.append(tmp)
+        rdev_addr = self.ramdump.read_word(
+            kryo_addr + self.ramdump.field_offset('struct kryo_regulator',
+                                                  'rdev'))
+        offset = self.ramdump.field_offset('struct regulator_dev',
+                                           'consumer_list')
+        self.dump_consumer(rdev_addr + offset)
+
+    def dump_consumer(self, consumer_head):
+        tmp = ""
+        tmp += "\nConsumers:\n"
+        tmp += "%-48s%-10s%-10s%-10s\n" % ("Device-Supply", "EN", "Min_Uv",
+                                           "Max_Uv")
+        self.output.append(tmp)
+        node_offset = self.ramdump.field_offset('struct regulator', 'list')
+        self.consumer_head = consumer_head
+        c_w = linux_list.ListWalker(self.ramdump, consumer_head, node_offset)
+        c_w.walk(consumer_head, self.consumer_walker)
+        self.output.append("\n")
+
+    def consumer_walker(self, reg_addr):
+        if reg_addr + self.ramdump.field_offset('struct regulator', 'list') \
+           == self.consumer_head:
+            return
+        min_uV = self.ramdump.read_int(
+            reg_addr +
+            self.ramdump.field_offset('struct regulator', 'min_uV'))
+        max_uV = self.ramdump.read_int(
+            reg_addr +
+            self.ramdump.field_offset('struct regulator', 'max_uV'))
+        enabled = self.ramdump.read_int(
+            reg_addr + self.ramdump.field_offset('struct regulator',
+                                                 'enabled'))
+        if enabled == 1:
+            enabled = 'Y'
+        else:
+            enabled = 'N'
+        name_addr = self.ramdump.read_word(
+            reg_addr +
+            self.ramdump.field_offset('struct regulator', 'supply_name'))
+        name = self.ramdump.read_cstring(name_addr, 64)
+        tmp = "%-48s%-10s%-10d%-10d\n" % (name, enabled, min_uV, max_uV)
+        self.output.append(tmp)
+
+    def parse(self):
+        self.output_file = self.ramdump.open_file('cpr3_info.txt')
+        self.get_cpr()
+        self.get_kryo()
+        for i in self.output:
+            self.output_file.write(i)
+        print_out_str("--- Wrote the output to cpr3_info.txt")
+        self.output_file.close()