Refactoring the algorithm to the generate the .pio_bitmap using the ioports entries and new parameters for the root-cell-config.c-tmpl.
v6: - refactor the static function of parse_ioport_tree to non-static - refactor the function of parse_ioport - add the docstring to the function of parse_ioport Signed-off-by: Xuguo Wang <[email protected]> --- tools/jailhouse-config-create | 180 +++++++++++++++++++++++++++++++++++++++--- 1 file changed, 171 insertions(+), 9 deletions(-) diff --git a/tools/jailhouse-config-create b/tools/jailhouse-config-create index dfe98db..925b0e5 100755 --- a/tools/jailhouse-config-create +++ b/tools/jailhouse-config-create @@ -1352,14 +1352,173 @@ def parse_ivrs(pcidevices, ioapics): def parse_ioports(): + """ + This function parses the file content of /proc/ioports to the data formatted + of pio_bitmap need. + + - ** parameters **: + no + - ** type **: + no + - ** return type **: + long: base address of pm_timer_base + list: contains all /proc/ioports entries + - ** return value **: + pm_timer_base: the base address of pm_timer_base + bitmap_regions: pio_bitmap list + - ** example **: + (pm_timer_base, pm_bitmap_regions) = parse_ioports() + """ pm_timer_base = None - f = input_open('/proc/ioports') - for line in f: - if line.endswith('ACPI PM_TMR\n'): - pm_timer_base = int(line.split('-')[0], 16) - break - f.close() - return pm_timer_base + bitmap_regions = [] + regions = IOPortRegionTree.parse_ioport_file().parse_ioport_tree() + + for region in regions: + # parse the ACPI PM_TMR + if region.typestr == 'ACPI PM_TMR': + pm_timer_base = region.start + continue + + # region PCI conf1 must intercept + if region.typestr == 'PCI conf1': + region.value = 0xff + if region.size() > 8: + region.value = -1 + bitmap_regions.append(region) + continue + + byte_size = region.size() / 8 + + # alignment spefication + both_aligned = 0 + both_not_aligned = 1 + tail_aligned = 2 + head_aligned = 3 + + alignment = region.alignment() + + if alignment == both_aligned: + region.value = 0 + bitmap_regions.append(region) + continue + + if alignment == both_not_aligned or alignment == tail_aligned: + round_up = (region.start % 8) + if alignment == both_not_aligned or alignment == head_aligned: + round_down = 7 - (region.stop % 8) + + if byte_size <= 1: + value_head = IOPortRegionTree.get_first_ioport_byte( + region.start, region.stop) + if alignment == head_aligned: + region.value = value_head + else: + if alignment == tail_aligned or alignment == both_not_aligned: + value_head = IOPortRegionTree.get_first_ioport_byte( + region.start, region.start + (7 - round_up)) + value_tail = IOPortRegionTree.get_first_ioport_byte( + region.stop - (region.stop % 8), region.stop) + + # adjust the region address to make the region aligned + if alignment == both_not_aligned or alignment == tail_aligned: + region.start -= round_up + if alignment == both_not_aligned or alignment == head_aligned: + region.stop += round_down + + # the region overlap with the previous region, + # so have to modify value and typestr + if alignment == tail_aligned or alignment == both_not_aligned: + if region.start - round_up < bitmap_regions[-1].stop: + region.value = bitmap_regions[-1].value & value_head + region.typestr += ', ' + bitmap_regions[-1].typestr + bitmap_regions.pop() + else: + region.value = value_head + + # append the region according to the region overlap with the + # previous region or not + if byte_size <= 1: + bitmap_regions.append(region) + elif byte_size == 2: + if alignment == tail_aligned or alignment == both_not_aligned: + stop = region.start + (7 - round_up) + value = region.value + else: + stop = region.start + 7 + value = 0 + + bitmap_regions.append(IOPortRegion( + region.start, + stop, + region.typestr, + value)) + bitmap_regions.append(IOPortRegion( + region.stop - (region.stop % 8), + region.stop, + region.typestr, + value_tail)) + else: + if alignment == tail_aligned or alignment == both_not_aligned: + stop = region.start + (7 - round_up) + value = region.value + else: + stop = region.stop - (region.stop % 8) - 1 + value = 0 + + bitmap_regions.append(IOPortRegion( + region.start, + stop, + region.typestr, + value)) + + if alignment == both_not_aligned: + bitmap_regions.append(IOPortRegion( + region.start + (7 - round_up) + 1, + region.stop - (region.stop % 8) - 1, + region.typestr, + 0)) + + if alignment == both_not_aligned or alignment == head_aligned: + start = region.stop - (region.stop % 8) + value = value_tail + else: + start = region.start + (7 - round_up) + 1 + value = 0 + + bitmap_regions.append(IOPortRegion( + start, + region.stop, + region.typestr, + value)) + + # replenishment the region hole + for region in bitmap_regions: + i = bitmap_regions.index(region) + if region.start != 0 \ + and region.stop != 0xffff \ + and region != bitmap_regions[-1]: + if region.stop + 1 != bitmap_regions[i + 1].start: + size = bitmap_regions[i + 1].start - region.stop - 1 + value = 0xff + if size > 8: + value = -1 + bitmap_regions.insert(i + 1, + IOPortRegion( + region.stop + 1, + bitmap_regions[i + 1].start - 1, + '', + value)) + + # pad with the 0xff if the last address is not 0xffff + if bitmap_regions[-1].stop != 0xffff: + start = bitmap_regions[-1].stop + 1 + stop = 0xffff + value = 0xff + if stop - start - 1 > 8: + value = -1 + bitmap_regions.append(IOPortRegion(start, stop, '', value)) + + return pm_timer_base, bitmap_regions class MMConfig: @@ -1469,7 +1628,8 @@ regions.append(inmatereg) cpucount = count_cpus() -pm_timer_base = parse_ioports() +(pm_timer_base, pm_bitmap_regions) = parse_ioports() +pm_bitmap_size = int(pm_bitmap_regions[-1].stop / 8 + 1) f = open(options.file, 'w') @@ -1487,7 +1647,9 @@ kwargs = { 'irqchips': ioapics, 'pm_timer_base': pm_timer_base, 'mmconfig': mmconfig, - 'iommu_units': iommu_units + 'iommu_units': iommu_units, + 'pm_bitmap_size': pm_bitmap_size, + 'pm_bitmap_regions': pm_bitmap_regions } f.write(tmpl.render(**kwargs)) -- 2.5.0 -- You received this message because you are subscribed to the Google Groups "Jailhouse" group. To unsubscribe from this group and stop receiving emails from it, send an email to [email protected]. For more options, visit https://groups.google.com/d/optout.
