Ejemplo n.º 1
0
bool cbm_crt_read_data(core_file* file, UINT8 *roml, UINT8 *romh)
{
	offs_t roml_offset = 0;
	offs_t romh_offset = 0;

	core_fseek(file, CRT_HEADER_LENGTH, SEEK_SET);

	while (!core_feof(file))
	{
		cbm_crt_chip chip;
		core_fread(file, &chip, CRT_CHIP_LENGTH);

		UINT16 address = pick_integer_be(chip.start_address, 0, 2);
		UINT16 size = pick_integer_be(chip.image_size, 0, 2);

		switch (address)
		{
		case 0x8000: core_fread(file, roml + roml_offset, size); roml_offset += size; break;
		case 0xa000: core_fread(file, romh + romh_offset, size); romh_offset += size; break;
		case 0xe000: core_fread(file, romh + romh_offset, size); romh_offset += size; break;
		}
	}

	return true;
}
Ejemplo n.º 2
0
bool cbm_crt_read_data(util::core_file &file, UINT8 *roml, UINT8 *romh)
{
	UINT32 roml_offset = 0;
	UINT32 romh_offset = 0;

	file.seek(CRT_HEADER_LENGTH, SEEK_SET);

	while (!file.eof())
	{
		cbm_crt_chip chip;
		file.read(&chip, CRT_CHIP_LENGTH);

		UINT16 address = pick_integer_be(chip.start_address, 0, 2);
		UINT16 size = pick_integer_be(chip.image_size, 0, 2);

		switch (address)
		{
		case 0x8000: file.read(roml + roml_offset, size); roml_offset += size; break;
		case 0xa000: file.read(romh + romh_offset, size); romh_offset += size; break;
		case 0xe000: file.read(romh + romh_offset, size); romh_offset += size; break;
		}
	}

	return true;
}
Ejemplo n.º 3
0
bool cbm_crt_read_header(core_file* file, size_t *roml_size, size_t *romh_size, int *exrom, int *game)
{
    // read the header
    cbm_crt_header header;
    core_fread(file, &header, CRT_HEADER_LENGTH);

    if (memcmp(header.signature, CRT_SIGNATURE, 16) != 0)
        return false;

    UINT16 hardware = pick_integer_be(header.hardware, 0, 2);
    *exrom = header.exrom;
    *game = header.game;

    if (LOG)
    {
        logerror("Name: %s\n", header.name);
        logerror("Hardware: %04x\n", hardware);
        logerror("Slot device: %s\n", CRT_C64_SLOT_NAMES[hardware]);
        logerror("EXROM: %u\n", header.exrom);
        logerror("GAME: %u\n", header.game);
    }

    // determine ROM region lengths
    while (!core_feof(file))
    {
        cbm_crt_chip chip;
        core_fread(file, &chip, CRT_CHIP_LENGTH);

        UINT16 address = pick_integer_be(chip.start_address, 0, 2);
        UINT16 size = pick_integer_be(chip.image_size, 0, 2);
        UINT16 type = pick_integer_be(chip.chip_type, 0, 2);

        if (LOG)
        {
            logerror("CHIP Address: %04x\n", address);
            logerror("CHIP Size: %04x\n", size);
            logerror("CHIP Type: %04x\n", type);
        }

        switch (address)
        {
        case 0x8000:
            *roml_size += size;
            break;
        case 0xa000:
            *romh_size += size;
            break;
        case 0xe000:
            *romh_size += size;
            break;
        default:
            logerror("Invalid CHIP loading address!\n");
            break;
        }

        core_fseek(file, size, SEEK_CUR);
    }

    return true;
}
Ejemplo n.º 4
0
static int os9_interpret_dirent(void *entry, char **filename, UINT32 *lsn, int *corrupt)
{
	int i;
	char *entry_b = (char *) entry;

	*filename = NULL;
	*lsn = 0;
	if (corrupt)
		*corrupt = FALSE;

	if (entry_b[28] != '\0')
	{
		if (corrupt)
			*corrupt = TRUE;
	}

	for (i = 0; (i < 28) && !(entry_b[i] & 0x80); i++)
		;
	entry_b[i] &= 0x7F;
	entry_b[i+1] = '\0';

	*lsn = pick_integer_be(entry, 29, 3);
	if (strcmp(entry_b, ".") && strcmp(entry_b, ".."))
		*filename = entry_b;
	return *filename != NULL;
}
Ejemplo n.º 5
0
const char * cbm_crt_get_card(core_file *file)
{
	// read the header
	cbm_crt_header header;
	core_fread(file, &header, CRT_HEADER_LENGTH);

	if (memcmp(header.signature, CRT_SIGNATURE, 16) == 0)
	{
		UINT16 hardware = pick_integer_be(header.hardware, 0, 2);

		return CRT_C64_SLOT_NAMES[hardware];
	}

	return NULL;
}
Ejemplo n.º 6
0
std::string cbm_crt_get_card(util::core_file &file)
{
	// read the header
	cbm_crt_header header;
	file.read(&header, CRT_HEADER_LENGTH);

	if (memcmp(header.signature, CRT_SIGNATURE, 16) == 0)
	{
		UINT16 hardware = pick_integer_be(header.hardware, 0, 2);

		return std::string(CRT_C64_SLOT_NAMES[hardware]);
	}

	return std::string();
}
Ejemplo n.º 7
0
void cbm_crt_get_card(astring &result, core_file *file)
{
	// read the header
	cbm_crt_header header;
	core_fread(file, &header, CRT_HEADER_LENGTH);

	if (memcmp(header.signature, CRT_SIGNATURE, 16) == 0)
	{
		UINT16 hardware = pick_integer_be(header.hardware, 0, 2);

		result.cpy(CRT_C64_SLOT_NAMES[hardware]);
		return;
	}

	result.reset();
}
Ejemplo n.º 8
0
static UINT32 identify_attribute(struct imgtooltest_state *state, xml_data_node *node, imgtool_attribute *value)
{
	xml_attribute_node *attr_node;
	UINT32 attribute;

	attr_node = xml_get_attribute(node, "name");
	if (!attr_node)
	{
		state->m_failed = 1;
		error_missingattribute("name");
		return 0;
	}

	if (!strcmp(attr_node->value, "mac_file_type"))
		attribute = IMGTOOLATTR_INT_MAC_TYPE;
	else if (!strcmp(attr_node->value, "mac_file_creator"))
		attribute = IMGTOOLATTR_INT_MAC_CREATOR;
	else
	{
		error_missingattribute("name");
		return 0;
	}

	attr_node = xml_get_attribute(node, "value");
	if (!attr_node)
	{
		state->m_failed = 1;
		error_missingattribute("value");
		return 0;
	}

	switch(attribute)
	{
		case IMGTOOLATTR_INT_MAC_TYPE:
		case IMGTOOLATTR_INT_MAC_CREATOR:
			if (strlen(attr_node->value) != 4)
			{
				state->m_failed = 1;
				error_missingattribute("value");
				return 0;
			}
			value->i = pick_integer_be(attr_node->value, 0, 4);
			break;
	}
	return attribute;
}
Ejemplo n.º 9
0
static imgtoolerr_t os9_decode_file_header(imgtool_image *image,
	int lsn, struct os9_fileinfo *info)
{
	imgtoolerr_t err;
	UINT32 attributes, count;
	int max_entries, i;
	const os9_diskinfo *disk_info;
	UINT8 header[256];

	disk_info = os9_get_diskinfo(image);

	err = os9_read_lsn(image, lsn, 0, header, sizeof(header));
	if (err)
		return err;

	info->lsn               = lsn;
	attributes              = pick_integer_be(header, 0, 1);
	info->owner_id          = pick_integer_be(header, 1, 2);
	info->link_count        = pick_integer_be(header, 8, 1);
	info->file_size         = pick_integer_be(header, 9, 4);
	info->directory         = (attributes & 0x80) ? 1 : 0;
	info->non_sharable      = (attributes & 0x40) ? 1 : 0;
	info->public_execute    = (attributes & 0x20) ? 1 : 0;
	info->public_write      = (attributes & 0x10) ? 1 : 0;
	info->public_read       = (attributes & 0x08) ? 1 : 0;
	info->user_execute      = (attributes & 0x04) ? 1 : 0;
	info->user_write        = (attributes & 0x02) ? 1 : 0;
	info->user_read         = (attributes & 0x01) ? 1 : 0;

	if (info->directory && (info->file_size % 32 != 0))
		return IMGTOOLERR_CORRUPTIMAGE;

	/* read all sector map entries */
	max_entries = (disk_info->sector_size - 16) / 5;
	max_entries = MIN(max_entries, ARRAY_LENGTH(info->sector_map) - 1);
	for (i = 0; i < max_entries; i++)
	{
		lsn = pick_integer_be(header, 16 + (i * 5) + 0, 3);
		count = pick_integer_be(header, 16 + (i * 5) + 3, 2);
		if (count <= 0)
			break;

		info->sector_map[i].lsn = lsn;
		info->sector_map[i].count = count;
	}
	info->sector_map[i].lsn = 0;
	info->sector_map[i].count = 0;
	return IMGTOOLERR_SUCCESS;
}
Ejemplo n.º 10
0
static imgtoolerr_t os9_diskimage_nextenum(imgtool_directory *enumeration, imgtool_dirent *ent)
{
	struct os9_direnum *os9enum;
	UINT32 lsn, index;
	imgtoolerr_t err;
	UINT8 dir_entry[32];
	char filename[29];
	struct os9_fileinfo file_info;
	imgtool_image *image;

	image = imgtool_directory_image(enumeration);
	os9enum = os9_get_dirinfo(enumeration);

	do
	{
		/* check for EOF */
		if (os9enum->index >= os9enum->dir_info.file_size)
		{
			ent->eof = 1;
			return IMGTOOLERR_SUCCESS;
		}

		/* locate the LSN and offset for this directory entry */
		index = os9enum->index;
		lsn = os9_lookup_lsn(image, &os9enum->dir_info, &index);

		/* read the directory entry out of the lSN */
		err = os9_read_lsn(image, lsn, index, dir_entry, sizeof(dir_entry));
		if (err)
			return err;

		if (dir_entry[0])
		{
			/* read the file or directory name */
			pick_string(dir_entry, 0, 28, filename);

			/* we have certain expectations of the directory contents; the
			 * first directory entry should be "..", the second ".", and
			 * subsequent entries should never be "." or ".." */
			switch(os9enum->index)
			{
				case 0:
					if (strcmp(filename, ".."))
						imgtool_warn("First entry in directory should be \"..\" and not \"%s\"", filename);
					break;

				case 32:
					if (strcmp(filename, "."))
						imgtool_warn("Second entry in directory should be \".\" and not \"%s\"", filename);
					break;

				default:
					if (!strcmp(filename, ".") || !strcmp(filename, ".."))
						imgtool_warn("Directory entry %d should not be \"%s\"", index / 32, filename);
					break;
			}

			/* if the filename is ".", the file should point to the current directory */
			if (!strcmp(filename, ".") && (pick_integer_be(dir_entry, 29, 3) != os9enum->dir_info.lsn))
			{
				imgtool_warn("Directory \".\" does not point back to same directory");
			}
		}
		else
		{
			/* no more directory entries */
			filename[0] = '\0';
		}

		/* move on to the next directory entry */
		os9enum->index += 32;
	}
	while(!filename[0] || !strcmp(filename, ".") || !strcmp(filename, ".."));

	/* read file attributes */
	lsn = pick_integer_be(dir_entry, 29, 3);
	err = os9_decode_file_header(imgtool_directory_image(enumeration), lsn, &file_info);
	if (err)
		return err;

	/* fill out imgtool_dirent structure */
	snprintf(ent->filename, ARRAY_LENGTH(ent->filename), "%s", filename);
	snprintf(ent->attr, ARRAY_LENGTH(ent->attr), "%c%c%c%c%c%c%c%c",
		file_info.directory      ? 'd' : '-',
		file_info.non_sharable   ? 's' : '-',
		file_info.public_execute ? 'x' : '-',
		file_info.public_write   ? 'w' : '-',
		file_info.public_read    ? 'r' : '-',
		file_info.user_execute   ? 'x' : '-',
		file_info.user_write     ? 'w' : '-',
		file_info.user_read      ? 'r' : '-');

	ent->directory = file_info.directory;
	ent->corrupt = (dir_entry[28] != 0);
	ent->filesize = file_info.file_size;
	return IMGTOOLERR_SUCCESS;
}
Ejemplo n.º 11
0
static imgtoolerr_t os9_diskimage_open(imgtool_image *image, imgtool_stream *stream)
{
	imgtoolerr_t err;
	floperr_t ferr;
	os9_diskinfo *info;
	UINT32 track_size_in_sectors, i; //, attributes;
	UINT8 header[256];
	UINT32 allocation_bitmap_lsns;
	UINT8 b, mask;

	info = os9_get_diskinfo(image);

	ferr = floppy_read_sector(imgtool_floppy(image), 0, 0, 1, 0, header, sizeof(header));
	if (ferr)
		return imgtool_floppy_error(ferr);

	info->total_sectors             = pick_integer_be(header,   0, 3);
	track_size_in_sectors           = pick_integer_be(header,   3, 1);
	info->allocation_bitmap_bytes   = pick_integer_be(header,   4, 2);
	info->cluster_size              = pick_integer_be(header,   6, 2);
	info->root_dir_lsn              = pick_integer_be(header,   8, 3);
	info->owner_id                  = pick_integer_be(header,  11, 2);
//  attributes                      =
	pick_integer_be(header,  13, 1);
	info->disk_id                   = pick_integer_be(header,  14, 2);
	info->format_flags              = pick_integer_be(header,  16, 1);
	info->sectors_per_track         = pick_integer_be(header,  17, 2);
	info->bootstrap_lsn             = pick_integer_be(header,  21, 3);
	info->bootstrap_size            = pick_integer_be(header,  24, 2);
	info->sector_size               = pick_integer_be(header, 104, 2);

	info->sides                 = (info->format_flags & 0x01) ? 2 : 1;
	info->double_density        = (info->format_flags & 0x02) ? 1 : 0;
	info->double_track          = (info->format_flags & 0x04) ? 1 : 0;
	info->quad_track_density    = (info->format_flags & 0x08) ? 1 : 0;
	info->octal_track_density   = (info->format_flags & 0x10) ? 1 : 0;

	pick_string(header, 31, 32, info->name);

	if (info->sector_size == 0)
		info->sector_size = 256;

	/* does the root directory and allocation bitmap collide? */
	allocation_bitmap_lsns = (info->allocation_bitmap_bytes + info->sector_size - 1) / info->sector_size;
	if (1 + allocation_bitmap_lsns > info->root_dir_lsn)
		return IMGTOOLERR_CORRUPTIMAGE;

	/* is the allocation bitmap too big? */
	info->allocation_bitmap = (UINT8*)imgtool_image_malloc(image, info->allocation_bitmap_bytes);
	if (!info->allocation_bitmap)
		return IMGTOOLERR_OUTOFMEMORY;
	memset(info->allocation_bitmap, 0, info->allocation_bitmap_bytes);

	/* sectors per track and track size don't jive? */
	if (info->sectors_per_track != track_size_in_sectors)
		return IMGTOOLERR_CORRUPTIMAGE;

	/* zero sectors per track? */
	if (info->sectors_per_track == 0)
		return IMGTOOLERR_CORRUPTIMAGE;

	/* do we have an odd number of sectors? */
	if (info->total_sectors % info->sectors_per_track)
		return IMGTOOLERR_CORRUPTIMAGE;

	/* read the allocation bitmap */
	for (i = 0; i < allocation_bitmap_lsns; i++)
	{
		err = os9_read_lsn(image, 1 + i, 0, &info->allocation_bitmap[i * info->sector_size],
			MIN(info->allocation_bitmap_bytes - (i * info->sector_size), info->sector_size));
		if (err)
			return err;
	}

	/* check to make sure that the allocation bitmap and root sector are reserved */
	for (i = 0; i <= allocation_bitmap_lsns; i++)
	{
		b = info->allocation_bitmap[i / 8];
		mask = 1 << (7 - (i % 8));
		if ((b & mask) == 0)
			return IMGTOOLERR_CORRUPTIMAGE;
	}

	return IMGTOOLERR_SUCCESS;
}
Ejemplo n.º 12
0
static imgtoolerr_t macbinary_writefile(imgtool_partition *partition, const char *filename, const char *fork, imgtool_stream *sourcef, option_resolution *opts)
{
	static const UINT32 attrs[] =
	{
		IMGTOOLATTR_TIME_CREATED,
		IMGTOOLATTR_TIME_LASTMODIFIED,
		IMGTOOLATTR_INT_MAC_TYPE,
		IMGTOOLATTR_INT_MAC_CREATOR,
		IMGTOOLATTR_INT_MAC_FINDERFLAGS,
		IMGTOOLATTR_INT_MAC_COORDX,
		IMGTOOLATTR_INT_MAC_COORDY,
		IMGTOOLATTR_INT_MAC_FINDERFOLDER,
		IMGTOOLATTR_INT_MAC_SCRIPTCODE,
		IMGTOOLATTR_INT_MAC_EXTENDEDFLAGS,
		0
	};
	imgtoolerr_t err;
	imgtool_image *image = imgtool_partition_image(partition);
	UINT8 header[128];
	UINT32 datafork_size;
	UINT32 resourcefork_size;
	UINT64 total_size;
	UINT32 creation_time;
	UINT32 lastmodified_time;
	//int version;
	imgtool_attribute attr_values[10];

	UINT32 type_code;
	UINT32 creator_code;
	UINT16 finder_flags;
	UINT16 coord_x;
	UINT16 coord_y;
	UINT16 finder_folder;
	UINT8 script_code = 0;
	UINT8 extended_flags = 0;

	/* read in the header */
	memset(header, 0, sizeof(header));
	stream_read(sourcef, header, sizeof(header));

	/* check magic and zero fill bytes */
	if (header[0] != 0x00)
		return IMGTOOLERR_CORRUPTFILE;
	if (header[74] != 0x00)
		return IMGTOOLERR_CORRUPTFILE;
	if (header[82] != 0x00)
		return IMGTOOLERR_CORRUPTFILE;

	datafork_size = pick_integer_be(header, 83, 4);
	resourcefork_size = pick_integer_be(header, 87, 4);
	total_size = stream_size(sourcef);

	/* size of a MacBinary header is always 128 bytes */
	if (total_size - pad128(datafork_size) - pad128(resourcefork_size) != 128)
		return IMGTOOLERR_CORRUPTFILE;

	/* check filename length byte */
	if ((header[1] <= 0x00) || (header[1] > 0x3F))
		return IMGTOOLERR_CORRUPTFILE;

	/* check the CRC */
	if (pick_integer_be(header, 124, 2) != ccitt_crc16(0, header, 124))
	{
		/* the CRC does not match; this file is MacBinary I */
		//version = 1;
	}
	else if (pick_integer_be(header, 102, 4) != 0x6D42494E)
	{
		/* did not see 'mBIN'; this file is MacBinary II */
		if (header[122] < 0x81)
			return IMGTOOLERR_CORRUPTFILE;
		if (header[123] < 0x81)
			return IMGTOOLERR_CORRUPTFILE;
		//version = 2;
	}
	else
	{
		/* we did see 'mBIN'; this file is MacBinary III */
		if (header[122] < 0x82)
			return IMGTOOLERR_CORRUPTFILE;
		if (header[123] < 0x81)
			return IMGTOOLERR_CORRUPTFILE;
		//version = 3;
	}

	type_code         = pick_integer_be(header, 65, 4);
	creator_code      = pick_integer_be(header, 69, 4);
	finder_flags      = pick_integer_be(header, 73, 1) << 8;
	coord_x           = pick_integer_be(header, 75, 2);
	coord_y           = pick_integer_be(header, 77, 2);
	finder_folder     = pick_integer_be(header, 79, 2);
	creation_time     = pick_integer_be(header, 91, 4);
	lastmodified_time = pick_integer_be(header, 95, 4);

	if (image)
	{
		/* write out both forks */
		err = write_fork(partition, filename, "", sourcef, sizeof(header), datafork_size, opts);
		if (err)
			return err;
		err = write_fork(partition, filename, "RESOURCE_FORK", sourcef, sizeof(header) + pad128(datafork_size), resourcefork_size, opts);
		if (err)
			return err;

		/* set up attributes */
		attr_values[0].t = mac_crack_time(creation_time);
		attr_values[1].t = mac_crack_time(lastmodified_time);
		attr_values[2].i = type_code;
		attr_values[3].i = creator_code;
		attr_values[4].i = finder_flags;
		attr_values[5].i = coord_x;
		attr_values[6].i = coord_y;
		attr_values[7].i = finder_folder;
		attr_values[8].i = script_code;
		attr_values[9].i = extended_flags;

		err = imgtool_partition_put_file_attributes(partition, filename, attrs, attr_values);
		if (err)
			return err;
	}

	return IMGTOOLERR_SUCCESS;
}