示例#1
0
int
get_block_n(int n)
{
    partition_map * entry;
    int rtn_value;
    
    if (the_map != NULL) {
	entry = find_entry_by_disk_address(n, the_map);
	if (entry != 0) {
	    mb = entry->data;
	    rtn_value = 1;
	} else {
	    rtn_value = 0;
	}
    } else {
	if (read_media(the_media, ((long long) n) * g, PBLOCK_SIZE, (void *)buffer) == 0) {
	    rtn_value = 0;
	} else {
	    mb = (DPME *) buffer;
	    convert_dpme(mb, 1);
	    rtn_value = 1;
	}
    }
    return rtn_value;
}
示例#2
0
int
read_block(partition_map_header *map, unsigned long num, char *buf)
{
//printf("read block %d\n", num);
    return read_media(map->m, ((long long) num) * map->logical_block,
    		PBLOCK_SIZE, (void *)buf);
}
示例#3
0
int
read_block(partition_map_header *map, unsigned long num, char *buf, int quiet)
{
    int f;

    f = map->logical_block / PBLOCK_SIZE;
    return read_media(map->fd, num*f, buf, quiet);
}
示例#4
0
//
// Routines
//
int
get_block_zero(void)
{
    int rtn_value;
    
    if (the_map != NULL) {
	b0 = the_map->misc;
	rtn_value = 1;
    } else {
	if (read_media(the_media, (long long) 0, PBLOCK_SIZE, buffer) == 0) {
	    rtn_value = 0;
	} else {
	    b0 = (Block0 *) buffer;
	    convert_block0(b0, 1);
	    rtn_value = 1;
	}
    }
    return rtn_value;
}
示例#5
0
int
read_partition_block(partition_map *entry, unsigned long num, char *buf)
{
    DPME *data;
    partition_map_header * map;
    u32 base;
    u64 offset;

    map = entry->the_map;
    data = entry->data;
    base = data->dpme_pblock_start;

    if (num >= data->dpme_pblocks) {
	return 0;
    }
    offset = ((long long) base) * map->logical_block + num * 512;

    return read_media(map->m, offset, 512, (void *)buf);
}
示例#6
0
long
write_deblock_media(MEDIA m, long long offset, unsigned long count, void *address)
{
    DEBLOCK_MEDIA a;
    long rtn_value;
    unsigned long next_size;
    unsigned long partial_offset;
    unsigned long partial_count;
    long long cur_offset;
    unsigned long remainder;
    unsigned char *addr;
    
    a = (DEBLOCK_MEDIA) m;
    rtn_value = 0;
    if (a == 0) {
	/* no media */
    } else if (a->m.kind != deblock_info.kind) {
	/* wrong kind - XXX need to error here - this is an internal problem */
    } else if (count <= 0 || count % a->m.grain != 0) {
	/* can't handle size */
    } else if (offset < 0 || offset % a->m.grain != 0) {
	/* can't handle offset */
    } else if (a->need_filtering == 0) {
	rtn_value = write_media(a->next_media, offset, count, address);
    } else {
	next_size = a->next_block_size;
	addr = address;
	cur_offset = offset;
	remainder = count;
	rtn_value = 1;

	/* write partial */
	partial_offset = cur_offset % next_size;
	if (partial_offset != 0) {
	    partial_count = next_size - partial_offset;
	    if (partial_count > remainder) {
		partial_count = remainder;
	    }
	    rtn_value = read_media(a->next_media, cur_offset - partial_offset, next_size, a->buffer);
	    if (rtn_value != 0) {
		memcpy (a->buffer + partial_offset, addr, partial_count);
		rtn_value = write_media(a->next_media, cur_offset - partial_offset, next_size, a->buffer);
		addr += partial_count;
		cur_offset += partial_count;
		remainder -= partial_count;
	    }
	}
	/* write fulls as long as needed */
	if (rtn_value != 0 && remainder > next_size) {
	    partial_count = remainder - (remainder % next_size);
	    rtn_value = write_media(a->next_media, cur_offset, partial_count, addr);
	    addr += partial_count;
	    cur_offset += partial_count;
	    remainder -= partial_count;
	}
	/* write partial */
	if (rtn_value != 0 && remainder > 0) {
	    partial_count = remainder;
	    rtn_value = read_media(a->next_media, cur_offset, next_size, a->buffer);
	    if (rtn_value != 0) {
		memcpy (a->buffer, addr, partial_count);
		rtn_value = write_media(a->next_media, cur_offset, next_size, a->buffer);
	    }
	}
    }
    /* recompute size to handle file media */
    a->m.size_in_bytes = media_total_size(a->next_media);
    return rtn_value;
}
示例#7
0
void
display_patches(partition_map *entry)
{
    long long offset;
    MEDIA m;
    static uint8_t *patch_block;
    PatchListPtr p;
    PatchDescriptorPtr q;
    uint8_t *next;
    uint8_t *s;
    int i;
    
    offset = entry->data->dpme_pblock_start;
    m = entry->the_map->m;
    offset = ((long long) entry->data->dpme_pblock_start) * entry->the_map->logical_block;
    if (patch_block == NULL) {
	patch_block = (uint8_t *) malloc(PBLOCK_SIZE);
	if (patch_block == NULL) {
	    error(errno, "can't allocate memory for patch block buffer");
	    return;
	}
    }
    if (read_media(m, (long long)offset, PBLOCK_SIZE, (char *)patch_block) == 0) {
	error(errno, "Can't read patch block");
	return;
    }
    p = (PatchListPtr) patch_block;
    if (p->numPatchBlocks != 1) {
	i = p->numPatchBlocks;
	free(patch_block);
	patch_block = (uint8_t *) malloc(PBLOCK_SIZE*i);
	if (patch_block == NULL) {
	    error(errno, "can't allocate memory for patch blocks buffer");
	    return;
	}
	s = patch_block + PBLOCK_SIZE*i;
	while (i > 0) {
	    s -= PBLOCK_SIZE;
	    i -= 1;
	    if (read_media(m, offset+i, PBLOCK_SIZE, (char *)s) == 0) {
		error(errno, "Can't read patch block %d", i);
		return;
	    }
	}
	p = (PatchListPtr) patch_block;
    }
    printf("Patch list (%d entries)\n", p->numPatches);
    q = p->thePatch;
    for (i = 0; i < p->numPatches; i++) {
	printf("%2d signature: '%.4s'\n", i+1, (char *)&q->patchSig);
	printf("     version: %d.%d\n", q->majorVers, q->minorVers);
	printf("       flags: 0x%"PRIx32"\n", q->flags);
	printf("      offset: %"PRId32"\n", q->patchOffset);
	printf("        size: %"PRId32"\n", q->patchSize);
	printf("         CRC: 0x%"PRIx32"\n", q->patchCRC);
	printf("        name: '%.*s'\n", q->patchName[0], &q->patchName[1]);
	printf("      vendor: '%.*s'\n", q->patchVendor[0], &q->patchVendor[1]);
	next = ((uint8_t *)q) + q->patchDescriptorLen;
	s = &q->patchVendor[q->patchVendor[0]+1];
	if (next > s) {
	    printf("remainder of entry -");
	    dump_block(s, next-s);
	}
	q = (PatchDescriptorPtr)next;
    }
}
示例#8
0
//
// Routines
//
partition_map_header *
open_partition_map(char *name, int *valid_file, int ask_logical_size)
{
    media *fd;
    partition_map_header * map;
    int writeable;
#ifdef __linux__
    struct stat info;
#endif
    int size;

    fd = open_media(name, (rflag)?O_RDONLY:O_RDWR);
    if (fd == 0) {
	fd = open_media(name, O_RDONLY);
	if (fd == 0) {
	    error(errno, "can't open file '%s'", name);
	    *valid_file = 0;
	    return NULL;
	} else {
	    writeable = 0;
	}
    } else {
	writeable = 1;
    }
    *valid_file = 1;

    map = (partition_map_header *) malloc(sizeof(partition_map_header));
    if (map == NULL) {
	error(errno, "can't allocate memory for open partition map");
	close_media(fd);
	return NULL;
    }
    map->fd = fd;
    map->name = name;
    map->writeable = (rflag)?0:writeable;
    map->changed = 0;
    map->disk_order = NULL;
    map->base_order = NULL;

    map->physical_block = fd->block_size;	/* preflight */
    map->misc = (Block0 *) malloc(PBLOCK_SIZE);
    if (map->misc == NULL) {
	error(errno, "can't allocate memory for block zero buffer");
	close_media(map->fd);
	free(map);
	return NULL;
    } else if (read_media(map->fd, 0, (char *)map->misc, 0) == 0
	    || convert_block0(map->misc, 1)
	    || coerce_block0(map)) {
	// if I can't read block 0 I might as well give up
	close_partition_map(map);
	return NULL;
    }
    map->physical_block = map->misc->sbBlkSize;
    // printf("physical block size is %d\n", map->physical_block);

    if (ask_logical_size && interactive) {
	size = PBLOCK_SIZE;
	printf("A logical block is %d bytes: ", size);
	flush_to_newline(0);
	get_number_argument("what should be the logical block size? ",
		(long *)&size, size);
	map->logical_block = (size / PBLOCK_SIZE) * PBLOCK_SIZE;
    } else {
	map->logical_block = PBLOCK_SIZE;
    }
    if (map->logical_block > MAXIOSIZE) {
	map->logical_block = MAXIOSIZE;
    }
    if (map->logical_block > map->physical_block) {
	map->physical_block = map->logical_block;
    }
    map->blocks_in_map = 0;
    map->maximum_in_map = -1;
    map->media_size = compute_device_size(map, map);
    sync_device_size(map);

#ifdef __linux__
    if (fstat(fd, &info) < 0) {
	error(errno, "can't stat file '%s'", name);
	map->regular_file = 0;
    } else {
	map->regular_file = S_ISREG(info.st_mode);
    }
#else
    map->regular_file = 0;
#endif

    if (read_partition_map(map) < 0) {
	// some sort of failure reading the map
    } else {
	// got it!
	;
	return map;
    }
    close_partition_map(map);
    return NULL;
}
示例#9
0
void
do_display_block(partition_map_header *map, char *alt_name)
{
    MEDIA m;
    long number;
    char *name;
    static unsigned char *display_block;
    static int display_g;
    int g;
    static long next_number = -1;

    if (map != NULL) {
    	name = 0;
	m = map->m;
	g = map->logical_block;
    } else {
	if (alt_name == 0) {
	    if (get_string_argument("Name of device: ", &name, 1) == 0) {
		bad_input("Bad name");
		return;
	    }
	} else {
	    name = strdup(alt_name);
	}
	m = open_pathname_as_media(name, O_RDONLY);
	if (m == 0) {
	    error(errno, "can't open file '%s'", name);
	    free(name);
	    return;
	}
	g = media_granularity(m);
	if (g < PBLOCK_SIZE) {
	    g = PBLOCK_SIZE;
	}
    }
    if (get_number_argument("Block number: ", &number, next_number) == 0) {
	bad_input("Bad block number");
	goto xit;
    }
    if (display_block == NULL || display_g < g) {
    	if (display_block != NULL) {
    	    free(display_block);
    	    display_g = 0;
	}
	display_block = (unsigned char *) malloc(g);
	if (display_block == NULL) {
	    error(errno, "can't allocate memory for display block buffer");
	    goto xit;
	}
	display_g = g;
    }
    if (read_media(m, ((long long)number) * g, g, (char *)display_block) != 0) {
	printf("block %ld -", number);
	dump_block((unsigned char*) display_block, g);
	next_number = number + 1;
    }

xit:
    if (name) {
	close_media(m);
	free(name);
    }
    return;
}
示例#10
0
//
// Routines
//
partition_map_header *
open_partition_map(char *name, int *valid_file, int ask_logical_size, int oflag)
{
    MEDIA m;
    partition_map_header * map;
    int writable;
    long size;

    m = open_pathname_as_media(name, oflag);
    if (m == 0) {
	m = open_pathname_as_media(name, O_RDONLY);
	if (m == 0) {
	    error(errno, "can't open file '%s'", name);
	    *valid_file = 0;
	    return NULL;
	} else {
	    writable = 0;
	}
    } else {
	writable = 1;
    }
    *valid_file = 1;

    map = (partition_map_header *) malloc(sizeof(partition_map_header));
    if (map == NULL) {
	error(errno, "can't allocate memory for open partition map");
	close_media(m);
	return NULL;
    }
    map->name = name;
    map->writable = (oflag == O_RDONLY)?0:writable;
    map->changed = 0;
    map->written = 0;
    map->disk_order = NULL;
    map->base_order = NULL;

    map->physical_block = media_granularity(m);	/* preflight */
    m = open_deblock_media(PBLOCK_SIZE, m);
    map->m = m;
    map->misc = (Block0 *) malloc(PBLOCK_SIZE);
    if (map->misc == NULL) {
	error(errno, "can't allocate memory for block zero buffer");
	close_media(map->m);
	free(map);
	return NULL;
    } else if (read_media(map->m, (long long) 0, PBLOCK_SIZE, (char *)map->misc) == 0
	    || convert_block0(map->misc, 1)
	    || coerce_block0(map)) {
	// if I can't read block 0 I might as well give up
	error(-1, "Can't read block 0 from '%s'", name);
	close_partition_map(map);
	return NULL;
    }
    map->physical_block = map->misc->sbBlkSize;
    //printf("physical block size is %d\n", map->physical_block);

    if (ask_logical_size && interactive) {
	size = PBLOCK_SIZE;
	printf("A logical block is %ld bytes: ", size);
	flush_to_newline(0);
	get_number_argument("what should be the logical block size? ",
		&size, size);
	size = (size / PBLOCK_SIZE) * PBLOCK_SIZE;
	if (size < PBLOCK_SIZE) {
	    size = PBLOCK_SIZE;
	}
	map->logical_block = size;
    } else {
	map->logical_block = PBLOCK_SIZE;
    }
    if (map->logical_block > MAXIOSIZE) {
	map->logical_block = MAXIOSIZE;
    }
    if (map->logical_block > map->physical_block) {
	map->physical_block = map->logical_block;
    }
    map->blocks_in_map = 0;
    map->maximum_in_map = -1;
    map->media_size = compute_device_size(map, map);

    if (read_partition_map(map) < 0) {
	// some sort of failure reading the map
    } else {
	// got it!
	;
	return map;
    }
    close_partition_map(map);
    return NULL;
}