Source code for crash.subsystem.filesystem.decoders

# -*- coding: utf-8 -*-
# vim:set shiftwidth=4 softtabstop=4 expandtab textwidth=79:

from typing import Any

from crash.util.symbols import Types
from crash.subsystem.storage import block_device_name
from crash.subsystem.storage.decoders import Decoder, decode_bh
from crash.subsystem.filesystem import super_fstype

import gdb

[docs]class DIOBioDecoder(Decoder): """ Decodes a bio used for direct i/o. This method decodes a bio generated by the direct-io component of the file system subsystem. The bio can either have been submitted directly or asynchronously. Args: bio: The struct bio to be decoded, generated by the direct i/o component. The value must be of type ``struct bio``. Attributes: bio (:obj:`gdb.Value`): The bio. The value is of type ``struct bio``. dio (:obj:`gdb.Value`): ``struct dio *`` that represents the direct i/o operation fstype (str): the name of the file system type dev (str): the name of the underlying device offset (str): the starting offset on disk """ _types = Types(['struct dio *']) __endio__ = ['dio_bio_end_io', 'dio_bio_end_io'] _description = "{:x} bio: Direct I/O for {} inode {}, sector {} on {}" def __init__(self, bio: gdb.Value) -> None: super().__init__() self.bio = bio
[docs] def interpret(self) -> None: """Interprets a direct i/o bio to populate its attributes""" # pylint: disable=attribute-defined-outside-init self.dio = self.bio['bi_private'].cast(self._types.dio_p_type) self.fstype = super_fstype(self.dio['inode']['i_sb']) self.dev = block_device_name(self.dio['inode']['i_sb']['s_bdev']) self.offset = self.dio['block_in_file'] << self.dio['blkbits']
def __str__(self) -> str: return self._description.format(int(self.bio), self.fstype, self.dio['inode']['i_ino'], self.bio['bi_sector'], self.dev) def __next__(self) -> Any: return None
DIOBioDecoder.register()
[docs]class DecodeMPage(Decoder): """ Decodes a bio used for multipage i/o. This method decodes a bio generated by the mpage component of the file system subsystem. Args: bio: The struct bio to be decoded, generated by the mpage component. The value must be of type ``struct bio``. Attributes: bio (:obj:`gdb.Value`): The bio. The value is of type ``struct bio``. inode (:obj:`gdb.Value`): The inode associated with this bio. The value is of type ``struct inode``. fstype (str): the name of the file system type """ __endio__ = 'mpage_end_io' description = "{:x} bio: Multipage I/O: inode {}, type {}, dev {}" def __init__(self, bio: gdb.Value) -> None: super().__init__() self.bio = bio
[docs] def interpret(self) -> None: """Interpret the multipage bio to populate its attributes""" # pylint: disable=attribute-defined-outside-init self.inode = self.bio['bi_io_vec'][0]['bv_page']['mapping']['host'] self.fstype = super_fstype(self.inode['i_sb'])
def __str__(self) -> str: return self.description.format(int(self.bio), self.inode['i_ino'], self.fstype, block_device_name(self.bio['bi_bdev']))
DecodeMPage.register()
[docs]class DecodeBioBH(Decoder): """ Decodes a bio used to perform i/o for buffer_heads This method decodes a bio generated by buffer head submission. Args: bio: The struct bio to be decoded, generated by buffer head submission. The value must be of type ``struct bio``. Attributes: bio (:obj:`gdb.Value`): The bio. The value is of type ``struct bio``. bh (:obj:`gdb.Value`): The struct buffer_head associated with this bio. The value is of type ``struct buffer_head``. """ _types = Types(['struct buffer_head *']) __endio__ = 'end_bio_bh_io_sync' _description = "{:x} bio: Bio representation of buffer head" def __init__(self, bio: gdb.Value) -> None: super().__init__() self.bio = bio
[docs] def interpret(self) -> None: """Interpret the buffer_head bio to populate its attributes""" # pylint: disable=attribute-defined-outside-init self.bh = self.bio['bi_private'].cast(self._types.buffer_head_p_type)
def __str__(self) -> str: return self._description.format(int(self.bio)) def __next__(self) -> Any: return decode_bh(self.bh)
DecodeBioBH.register()
[docs]class DecodeSyncWBBH(Decoder): """ Decodes a struct buffer_head submitted by file systems for routine synchronous writeback. Args: bio: The ``struct buffer_head`` to be decoded. The value must be of ``struct buffer_head``. Attributes: bh (:obj:`gdb.Value`): The ``struct buffer_head`` being decoded. The value is of type ``struct buffer_head``. """ __endio__ = 'end_buffer_write_sync' _description = "{:x} buffer_head: for dev {}, block {}, size {} (unassociated)" def __init__(self, bh: gdb.Value) -> None: super().__init__() self.bh = bh def __str__(self) -> str: return self._description.format(block_device_name(self.bh['b_bdev']), self.bh['b_blocknr'], self.bh['b_size'])
DecodeSyncWBBH.register()