prodos: work on LOAD functionality

This commit is contained in:
Vince Weaver 2021-07-30 00:37:52 -04:00
parent 643aca2973
commit 7231194c5c
4 changed files with 27 additions and 126 deletions

View File

@ -13,15 +13,6 @@
static int debug=0,ignore_errors=0;
#if 0
static unsigned char get_high_byte(int value) {
return (value>>8)&0xff;
}
static unsigned char get_low_byte(int value) {
return (value&0xff);
}
#endif
/* Read volume directory into a buffer */
static int prodos_read_voldir(int fd, struct voldir_t *voldir, int interleave) {
@ -77,73 +68,25 @@ static int prodos_read_voldir(int fd, struct voldir_t *voldir, int interleave) {
/* Checks if "filename" exists */
/* returns entry/block */
static int prodos_check_file_exists(int fd,
/* returns file type */
static int prodos_check_file_exists(struct voldir_t *voldir,
char *filename,
int file_deleted) {
#if 0
int catalog_track,catalog_sector;
int i,file_track;
char file_name[31];
int result;
struct voldir_t voldir;
unsigned char catalog_buffer[PRODOS_BYTES_PER_BLOCK];
struct file_entry_t *file) {
/* read the VOLDIR into buffer */
prodos_read_voldir(fd,&voldir,interleave);
int catalog_block,catalog_offset,catalog_inode;
/* FIXME: we have a function for this */
/* get the catalog track and sector from the VTOC */
catalog_track=voldir[VTOC_CATALOG_T];
catalog_sector=voldir[VTOC_CATALOG_S];
catalog_block=PRODOS_VOLDIR_KEY_BLOCK;
catalog_offset=0; /* skip the header */
catalog_inode=(catalog_block<<8)|catalog_offset;
repeat_catalog:
/* Read in Catalog Sector */
lseek(fd,DISK_OFFSET(catalog_track,catalog_sector),SEEK_SET);
result=read(fd,catalog_buffer,PRODOS_BYTES_PER_BLOCK);
/* scan all file entries in catalog sector */
for(i=0;i<7;i++) {
file_track=catalog_buffer[CATALOG_FILE_LIST+(i*CATALOG_ENTRY_SIZE)];
/* 0xff means file deleted */
/* 0x0 means empty */
if (file_track!=0x0) {
if (file_track==0xff) {
prodos_filename_to_ascii(file_name,
catalog_buffer+(CATALOG_FILE_LIST+(i*CATALOG_ENTRY_SIZE+FILE_NAME)),29);
if (file_deleted) {
/* return if we found the file */
if (!strncmp(filename,file_name,29)) {
return ((i<<16)+(catalog_track<<8)+catalog_sector);
}
}
}
else {
prodos_filename_to_ascii(file_name,
catalog_buffer+(CATALOG_FILE_LIST+(i*CATALOG_ENTRY_SIZE+FILE_NAME)),30);
/* return if we found the file */
if (!strncmp(filename,file_name,30)) {
return ((i<<16)+(catalog_track<<8)+catalog_sector);
}
}
}
while(1) {
catalog_inode=prodos_find_next_file(catalog_inode,voldir);
if (catalog_inode==-1) break;
}
/* point to next catalog track/sector */
catalog_track=catalog_buffer[CATALOG_NEXT_T];
catalog_sector=catalog_buffer[CATALOG_NEXT_S];
if (catalog_sector!=0) goto repeat_catalog;
if (result<0) fprintf(stderr,"Error on I/O\n");
#endif
return -1;
return 0;
}
static int prodos_free_block(struct voldir_t *voldir,int block) {
@ -489,10 +432,10 @@ got_a_dentry:
}
/* load a file. fts=entry/track/sector */
static int prodos_load_file(int fd,int fts,char *filename) {
/* load a file from the disk image. */
static int prodos_load_file(struct voldir_t *voldir,
int inode,char *filename) {
#if 0
int output_fd;
int catalog_file,catalog_track,catalog_sector;
int file_type,file_size=-1,tsl_track,tsl_sector,data_t,data_s;
@ -509,24 +452,7 @@ static int prodos_load_file(int fd,int fts,char *filename) {
return -1;
}
catalog_file=fts>>16;
catalog_track=(fts>>8)&0xff;
catalog_sector=(fts&0xff);
/* Read in Catalog Sector */
lseek(fd,DISK_OFFSET(catalog_track,catalog_sector),SEEK_SET);
result=read(fd,sector_buffer,PRODOS_BYTES_PER_BLOCK);
tsl_track=sector_buffer[CATALOG_FILE_LIST+
(catalog_file*CATALOG_ENTRY_SIZE)+FILE_TS_LIST_T];
tsl_sector=sector_buffer[CATALOG_FILE_LIST+
(catalog_file*CATALOG_ENTRY_SIZE)+FILE_TS_LIST_S];
file_type=prodos_file_type(sector_buffer[CATALOG_FILE_LIST+
(catalog_file*CATALOG_ENTRY_SIZE)+FILE_TYPE]);
// printf("file_type: %c\n",file_type);
#if 0
keep_saving:
/* Read in TSL Sector */
lseek(fd,DISK_OFFSET(tsl_track,tsl_sector),SEEK_SET);
@ -838,6 +764,7 @@ int main(int argc, char **argv) {
int c;
int address=0, length=0;
struct voldir_t voldir;
struct file_entry_t file;
/* Check command line arguments */
while ((c = getopt (argc, argv,"a:i:l:t:s:dhvxy"))!=-1) {

View File

@ -106,10 +106,13 @@ int prodos_voldir_find_free_block(struct voldir_t *voldir,
int *found_block);
/* prodos_catalog.c */
unsigned char prodos_char_to_type(char type, int lock);
int prodos_find_next_file(int inode, struct voldir_t *voldir);
int prodos_populate_filedesc(unsigned char *file_desc,
struct file_entry_t *file_entry);
//unsigned char prodos_char_to_type(char type, int lock);
void prodos_catalog(int dos_fd, struct voldir_t *voldir);
char *prodos_filename_to_ascii(char *dest,unsigned char *src,int len);
unsigned char prodos_file_type(int value);
//char *prodos_filename_to_ascii(char *dest,unsigned char *src,int len);
//unsigned char prodos_file_type(int value);
/* prodos_dump.c */
int prodos_dump(struct voldir_t *voldir, int fd);

View File

@ -13,7 +13,7 @@
/* inode = block<<8|entry */
static int prodos_find_next_file(int inode, struct voldir_t *voldir) {
int prodos_find_next_file(int inode, struct voldir_t *voldir) {
int result,catalog_block,catalog_offset;
unsigned char catalog_buffer[PRODOS_BYTES_PER_BLOCK];
@ -112,7 +112,8 @@ static int prodos_print_short_filetype(int type) {
return 0;
}
static unsigned char prodos_capital_month_names[12][4]={
static unsigned char prodos_capital_month_names[13][4]={
"???",
"JAN","FEB","MAR","APR","MAY","JUN",
"JUL","AUG","SEP","OCT","NOV","DEC",
};
@ -128,7 +129,7 @@ static int prodos_text_timestamp(int t, unsigned char *timestamp) {
minute=t&0x3f;
sprintf((char *)timestamp,"%2d-%s-%02d %2d:%02d",
day,prodos_capital_month_names[month-1],year,hour,minute);
day,prodos_capital_month_names[month],year,hour,minute);
timestamp[16]=0;
return 0;

View File

@ -215,12 +215,7 @@ int prodos_dump(struct voldir_t *voldir, int fd) {
memcpy(file_desc,
catalog_buffer+4+file*PRODOS_FILE_DESC_LEN,
PRODOS_FILE_DESC_LEN);
file_entry.storage_type=(file_desc[0]>>4)&0xf;
file_entry.name_length=file_desc[0]&0xf;
memcpy(&file_entry.file_name[0],&file_desc[1],
file_entry.name_length);
file_entry.file_name[file_entry.name_length]=0;
prodos_populate_filedesc(&file_desc,&file_entry);
if (file_entry.storage_type==PRODOS_FILE_DELETED) continue;
@ -230,57 +225,32 @@ int prodos_dump(struct voldir_t *voldir, int fd) {
prodos_print_storage_type(file_entry.storage_type);
printf("\t");
file_entry.file_type=file_desc[0x10];
prodos_print_file_type(file_entry.file_type);
file_entry.key_pointer=file_desc[0x11]|
file_desc[0x12]<<8;
printf("\tKey pointer: $%x\n",file_entry.key_pointer);
file_entry.blocks_used=file_desc[0x13]|
file_desc[0x14]<<8;
printf("\tBlocks Used: %d\n",file_entry.blocks_used);
file_entry.eof=file_desc[0x15]|
file_desc[0x16]<<8|
file_desc[0x17]<<16;
printf("\tFile size (eof): %d\n",file_entry.eof);
file_entry.creation_time=(file_desc[0x18]<<16)|
(file_desc[0x19]<<24)|
(file_desc[0x1a]<<0)|
(file_desc[0x1b]<<8);
printf("\tCreation Time (%x): ",file_entry.creation_time);
prodos_print_time(file_entry.creation_time);
printf("\n");
file_entry.version=file_desc[0x1c];
printf("\tVersion: %d\n",file_entry.version);
file_entry.min_version=file_desc[0x1d];
printf("\tMin Version: %d\n",file_entry.min_version);
file_entry.access=file_desc[0x1e];
printf("\tAccess (%x): ",file_entry.access);
prodos_print_access(file_entry.access);
printf("\n");
file_entry.aux_type=file_desc[0x1f]|
file_desc[0x20]<<8;
printf("\tAux Type: %x\n",file_entry.aux_type);
file_entry.last_mod=(file_desc[0x21]<<16)|
(file_desc[0x22]<<24)|
(file_desc[0x23]<<0)|
(file_desc[0x24]<<8);
printf("\tLast mod Time: (%x) ",file_entry.last_mod);
prodos_print_time(file_entry.last_mod);
printf("\n");
file_entry.header_pointer=file_desc[0x25]|
file_desc[0x26]<<8;
printf("\tHeader pointer: %x\n",file_entry.header_pointer);
}