File: [local] / src / sbin / pdisk / dump.c (download)
Revision 1.75, Tue Feb 23 02:39:54 2016 UTC (8 years, 3 months ago) by krw
Branch: MAIN
CVS Tags: OPENBSD_7_5_BASE, OPENBSD_7_5, OPENBSD_7_4_BASE, OPENBSD_7_4, OPENBSD_7_3_BASE, OPENBSD_7_3, OPENBSD_7_2_BASE, OPENBSD_7_2, OPENBSD_7_1_BASE, OPENBSD_7_1, OPENBSD_7_0_BASE, OPENBSD_7_0, OPENBSD_6_9_BASE, OPENBSD_6_9, OPENBSD_6_8_BASE, OPENBSD_6_8, OPENBSD_6_7_BASE, OPENBSD_6_7, OPENBSD_6_6_BASE, OPENBSD_6_6, OPENBSD_6_5_BASE, OPENBSD_6_5, OPENBSD_6_4_BASE, OPENBSD_6_4, OPENBSD_6_3_BASE, OPENBSD_6_3, OPENBSD_6_2_BASE, OPENBSD_6_2, OPENBSD_6_1_BASE, OPENBSD_6_1, OPENBSD_6_0_BASE, OPENBSD_6_0, OPENBSD_5_9_BASE, OPENBSD_5_9, HEAD Changes since 1.74: +4 -4 lines
Fix display of pdisk partition sizes by casting the 32-bit number
of blocks to (long long) before multiplying by 512 and passing the
value to fmt_scaled().
Discovered and fix tested by rpe@.
ok rpe@ deraadt@
|
/* $OpenBSD: dump.c,v 1.75 2016/02/23 02:39:54 krw Exp $ */
/*
* dump.c - dumping partition maps
*
* Written by Eryk Vershen
*/
/*
* Copyright 1996,1997,1998 by Apple Computer, Inc.
* All Rights Reserved
*
* Permission to use, copy, modify, and distribute this software and
* its documentation for any purpose and without fee is hereby granted,
* provided that the above copyright notice appears in all copies and
* that both the copyright notice and this permission notice appear in
* supporting documentation.
*
* APPLE COMPUTER DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE
* INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
* FOR A PARTICULAR PURPOSE.
*
* IN NO EVENT SHALL APPLE COMPUTER BE LIABLE FOR ANY SPECIAL, INDIRECT, OR
* CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
* LOSS OF USE, DATA OR PROFITS, WHETHER IN ACTION OF CONTRACT,
* NEGLIGENCE, OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
* WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#include <sys/queue.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <util.h>
#include "partition_map.h"
#include "dump.h"
#include "io.h"
void dump_block(unsigned char *, int);
void dump_block_zero(struct partition_map *);
void dump_partition_entry(struct entry *, int, int, int);
int get_max_base_or_length(struct partition_map *);
int get_max_name_string_length(struct partition_map *);
int get_max_type_string_length(struct partition_map *);
void
dump_block_zero(struct partition_map *map)
{
char buf[FMT_SCALED_STRSIZE];
struct ddmap *m;
int i;
printf("\nDevice block size=%u, Number of Blocks=%u",
map->sbBlkSize, map->sbBlkCount);
if (fmt_scaled((long long)map->sbBlkCount * map->sbBlkSize, buf) == 0)
printf(" (%s)\n", buf);
else
printf("\n");
printf("DeviceType=0x%x, DeviceId=0x%x\n", map->sbDevType,
map->sbDevId);
if (map->sbDrvrCount > 0) {
printf("Drivers-\n");
m = map->sbDDMap;
for (i = 0; i < map->sbDrvrCount; i++) {
printf("%d: %3u @ %u, ", i + 1, m[i].ddSize,
m[i].ddBlock);
printf("type=0x%x\n", m[i].ddType);
}
}
printf("\n");
}
void
dump_partition_map(struct partition_map *map)
{
struct entry *entry;
int digits, max_type_length, max_name_length;
printf("\nPartition map (with %d byte blocks) on '%s'\n",
map->sbBlkSize, map->name);
digits = number_of_digits(get_max_base_or_length(map));
if (digits < 6)
digits = 6;
max_type_length = get_max_type_string_length(map);
if (max_type_length < 4)
max_type_length = 4;
max_name_length = get_max_name_string_length(map);
if (max_name_length < 6)
max_name_length = 6;
printf(" #: %*s %-*s %*s %-*s\n", max_type_length, "type",
max_name_length, "name", digits, "length", digits, "base");
LIST_FOREACH(entry, &map->disk_order, disk_entry) {
dump_partition_entry(entry, max_type_length,
max_name_length, digits);
}
dump_block_zero(map);
}
void
dump_partition_entry(struct entry *entry, int type_length, int name_length,
int digits)
{
char buf[FMT_SCALED_STRSIZE];
printf("%2ld: %*.32s", entry->disk_address, type_length,
entry->dpme_type);
printf("%c%-*.32s ", contains_driver(entry) ? '*' : ' ',
name_length, entry->dpme_name);
printf("%*u @ %-*u", digits, entry->dpme_pblocks, digits,
entry->dpme_pblock_start);
if (fmt_scaled((long long)entry->dpme_pblocks *
entry->the_map->sbBlkSize, buf) == 0)
printf("(%s)\n", buf);
else
printf("\n");
}
void
show_data_structures(struct partition_map *map)
{
struct entry *entry;
struct ddmap *m;
int i;
printf("Header:\n");
printf("map %d blocks out of %d, media %lu blocks (%d byte blocks)\n",
map->blocks_in_map, map->maximum_in_map, map->media_size,
map->sbBlkSize);
printf("Map is%s writable", rflag ? " not" : "");
printf(" and has%s been changed\n", (map->changed) ? "" : " not");
printf("\n");
printf("Block0:\n");
printf("signature 0x%x", map->sbSig);
printf("Block size=%u, Number of Blocks=%u\n", map->sbBlkSize,
map->sbBlkCount);
printf("DeviceType=0x%x, DeviceId=0x%x, sbData=0x%x\n", map->sbDevType,
map->sbDevId, map->sbData);
if (map->sbDrvrCount == 0) {
printf("No drivers\n");
} else {
printf("%u driver%s-\n", map->sbDrvrCount,
(map->sbDrvrCount > 1) ? "s" : "");
m = map->sbDDMap;
for (i = 0; i < map->sbDrvrCount; i++) {
printf("%u: @ %u for %u, type=0x%x\n", i + 1,
m[i].ddBlock, m[i].ddSize, m[i].ddType);
}
}
printf("\n");
printf(" #: type length base "
"flags ( logical )\n");
LIST_FOREACH(entry, &map->disk_order, disk_entry) {
printf("%2ld: %20.32s ", entry->disk_address, entry->dpme_type);
printf("%7u @ %-7u ", entry->dpme_pblocks,
entry->dpme_pblock_start);
printf("%c%c%c%c%c%c%c%c%c ",
(entry->dpme_flags & DPME_VALID) ? 'V' : '.',
(entry->dpme_flags & DPME_ALLOCATED) ? 'A' : '.',
(entry->dpme_flags & DPME_IN_USE) ? 'I' : '.',
(entry->dpme_flags & DPME_BOOTABLE) ? 'B' : '.',
(entry->dpme_flags & DPME_READABLE) ? 'R' : '.',
(entry->dpme_flags & DPME_WRITABLE) ? 'W' : '.',
(entry->dpme_flags & DPME_OS_PIC_CODE) ? 'P' : '.',
(entry->dpme_flags & DPME_OS_SPECIFIC_2) ? '2' : '.',
(entry->dpme_flags & DPME_OS_SPECIFIC_1) ? '1' : '.');
printf("( %7u @ %-7u )\n", entry->dpme_lblocks,
entry->dpme_lblock_start);
}
printf("\n");
printf(" #: booter bytes load_address "
"goto_address checksum processor\n");
LIST_FOREACH(entry, &map->disk_order, disk_entry) {
printf("%2ld: ", entry->disk_address);
printf("%7u ", entry->dpme_boot_block);
printf("%7u ", entry->dpme_boot_bytes);
printf("%8x ", entry->dpme_load_addr);
printf("%8x ", entry->dpme_goto_addr);
printf("%8x ", entry->dpme_checksum);
printf("%.32s", entry->dpme_processor_id);
printf("\n");
}
printf("\n");
}
void
full_dump_partition_entry(struct partition_map *map, int ix)
{
struct entry *entry;
int i;
uint32_t t;
entry = find_entry_by_disk_address(ix, map);
if (entry == NULL) {
printf("No such partition\n");
return;
}
printf(" signature: 0x%x\n", entry->dpme_signature);
printf(" number of map entries: %u\n", entry->dpme_map_entries);
printf(" physical start: %10u length: %10u\n",
entry->dpme_pblock_start, entry->dpme_pblocks);
printf(" logical start: %10u length: %10u\n",
entry->dpme_lblock_start, entry->dpme_lblocks);
printf(" flags: 0x%x\n", entry->dpme_flags);
printf(" ");
if (entry->dpme_flags & DPME_VALID)
printf("valid ");
if (entry->dpme_flags & DPME_ALLOCATED)
printf("alloc ");
if (entry->dpme_flags & DPME_IN_USE)
printf("in-use ");
if (entry->dpme_flags & DPME_BOOTABLE)
printf("boot ");
if (entry->dpme_flags & DPME_READABLE)
printf("read ");
if (entry->dpme_flags & DPME_WRITABLE)
printf("write ");
if (entry->dpme_flags & DPME_OS_PIC_CODE)
printf("pic ");
t = entry->dpme_flags >> 7;
for (i = 7; i <= 31; i++) {
if (t & 0x1)
printf("%d ", i);
t = t >> 1;
}
printf("\n");
printf(" name: '%.32s'\n", entry->dpme_name);
printf(" type: '%.32s'\n", entry->dpme_type);
printf(" boot start block: %10u\n", entry->dpme_boot_block);
printf("boot length (in bytes): %10u\n", entry->dpme_boot_bytes);
printf(" load address: 0x%08x\n", entry->dpme_load_addr);
printf(" start address: 0x%08x\n", entry->dpme_goto_addr);
printf(" checksum: 0x%08x\n", entry->dpme_checksum);
printf(" processor: '%.32s'\n", entry->dpme_processor_id);
printf("dpme_reserved_1 -");
dump_block(entry->dpme_reserved_1, sizeof(entry->dpme_reserved_1));
printf("dpme_reserved_2 -");
dump_block(entry->dpme_reserved_2, sizeof(entry->dpme_reserved_2));
printf("dpme_reserved_3 -");
dump_block(entry->dpme_reserved_3, sizeof(entry->dpme_reserved_3));
printf("dpme_reserved_4 -");
dump_block(entry->dpme_reserved_4, sizeof(entry->dpme_reserved_4));
}
void
dump_block(unsigned char *addr, int len)
{
int i, j, limit1, limit;
#define LINE_LEN 16
#define UNIT_LEN 4
#define OTHER_LEN 8
for (i = 0; i < len; i = limit) {
limit1 = i + LINE_LEN;
if (limit1 > len)
limit = len;
else
limit = limit1;
printf("\n%03x: ", i);
for (j = i; j < limit1; j++) {
if (j % UNIT_LEN == 0)
printf(" ");
if (j < limit)
printf("%02x", addr[j]);
else
printf(" ");
}
printf(" ");
for (j = i; j < limit; j++) {
if (j % OTHER_LEN == 0)
printf(" ");
if (addr[j] < ' ')
printf(".");
else
printf("%c", addr[j]);
}
}
printf("\n");
}
void
full_dump_block_zero(struct partition_map *map)
{
struct ddmap *m;
int i;
m = map->sbDDMap;
printf(" signature: 0x%x\n", map->sbSig);
printf(" size of a block: %u\n", map->sbBlkSize);
printf(" number of blocks: %u\n", map->sbBlkCount);
printf(" device type: 0x%x\n", map->sbDevType);
printf(" device id: 0x%x\n", map->sbDevId);
printf(" data: 0x%x\n", map->sbData);
printf(" driver count: %u\n", map->sbDrvrCount);
for (i = 0; i < 8; i++) {
if (m[i].ddBlock == 0 && m[i].ddSize == 0 && m[i].ddType == 0)
break;
printf(" driver %3u block: %u\n", i + 1, m[i].ddBlock);
printf(" size in blocks: %u\n", m[i].ddSize);
printf(" driver type: 0x%x\n", m[i].ddType);
}
printf("remainder of block -");
dump_block(map->sbReserved, sizeof(map->sbReserved));
}
int
get_max_type_string_length(struct partition_map *map)
{
struct entry *entry;
int max, length;
max = 0;
LIST_FOREACH(entry, &map->disk_order, disk_entry) {
length = strnlen(entry->dpme_type, DPISTRLEN);
if (length > max)
max = length;
}
return max;
}
int
get_max_name_string_length(struct partition_map *map)
{
struct entry *entry;
int max, length;
max = 0;
LIST_FOREACH(entry, &map->disk_order, disk_entry) {
length = strnlen(entry->dpme_name, DPISTRLEN);
if (length > max)
max = length;
}
return max;
}
int
get_max_base_or_length(struct partition_map *map)
{
struct entry *entry;
int max;
max = 0;
LIST_FOREACH(entry, &map->disk_order, disk_entry) {
if (entry->dpme_pblock_start > max)
max = entry->dpme_pblock_start;
if (entry->dpme_pblocks > max)
max = entry->dpme_pblocks;
}
return max;
}