diff --git a/utils/prodos-utils/Makefile b/utils/prodos-utils/Makefile index af8e104e..2c7aaa78 100644 --- a/utils/prodos-utils/Makefile +++ b/utils/prodos-utils/Makefile @@ -5,10 +5,12 @@ all: prodos mkprodosfs ### prodos: prodos.o \ + prodos_read.o \ prodos_catalog.o \ prodos_dump.o \ prodos_volume_bitmap.o $(CC) -o prodos prodos.o \ + prodos_read.o \ prodos_catalog.o \ prodos_dump.o \ prodos_volume_bitmap.o $(LFLAGS) @@ -19,9 +21,9 @@ prodos.o: prodos.c prodos.h ### -mkprodosfs: mkprodosfs.o prodos_volume_bitmap.o +mkprodosfs: mkprodosfs.o prodos_read.o prodos_volume_bitmap.o $(CC) $(LFLAGS) -o mkprodosfs mkprodosfs.o \ - prodos_volume_bitmap.o + prodos_read.o prodos_volume_bitmap.o mkprodosfs.o: mkprodosfs.c prodos.h $(CC) $(CFLAGS) -c mkprodosfs.c @@ -43,6 +45,11 @@ prodos_dump.o: prodos_dump.c prodos.h ### +prodos_read.o: prodos_read.c prodos.h + $(CC) $(CFLAGS) -c prodos_read.c + +### + install: cp prodos prodos_raw mkprodosfs make_b prodos_text2ascii char2hex $(INSTALL_LOC) diff --git a/utils/prodos-utils/mkprodosfs.c b/utils/prodos-utils/mkprodosfs.c index 732489df..cbc26442 100644 --- a/utils/prodos-utils/mkprodosfs.c +++ b/utils/prodos-utils/mkprodosfs.c @@ -148,6 +148,7 @@ int main(int argc, char **argv) { goto end_of_program; } +#if 0 /* zero out file */ for(i=0;i<num_tracks*num_sectors;i++) { result=write(fd,vtoc_buffer,sector_size); @@ -339,7 +340,7 @@ int main(int argc, char **argv) { fprintf(stderr,"Error writing VTOC (%s)!\n",strerror(errno)); } - +#endif close(fd); diff --git a/utils/prodos-utils/prodos.c b/utils/prodos-utils/prodos.c index b2df4b0b..32c3e780 100644 --- a/utils/prodos-utils/prodos.c +++ b/utils/prodos-utils/prodos.c @@ -21,26 +21,6 @@ static unsigned char get_low_byte(int value) { return (value&0xff); } -int prodos_read_block(int fd,unsigned char *block, int blocknum) { - - int result; - - /* Note, we need to handle interleave, etc */ - /* For now assume it's linear */ - - /* Seek to VOLDIR */ - lseek(fd,blocknum*PRODOS_BYTES_PER_BLOCK,SEEK_SET); - result=read(fd,block,PRODOS_BYTES_PER_BLOCK); - - if (result<PRODOS_BYTES_PER_BLOCK) { - fprintf(stderr,"Error reading block %d\n",blocknum); - return -1; - } - return 0; -} - - - /* Read volume directory into a buffer */ static int prodos_read_voldir(int fd, struct voldir_t *voldir) { @@ -48,13 +28,16 @@ static int prodos_read_voldir(int fd, struct voldir_t *voldir) { unsigned char voldir_buffer[PRODOS_BYTES_PER_BLOCK]; /* read in VOLDIR */ - result=prodos_read_block(fd,voldir_buffer,PRODOS_VOLDIR_BLOCK); + voldir->fd=fd; + result=prodos_read_block(voldir,voldir_buffer,PRODOS_VOLDIR_BLOCK); if (result<0) { fprintf(stderr,"Error reading VOLDIR\n"); return -1; } + voldir->fd=fd; + voldir->storage_type=(voldir_buffer[0x4]>>4)&0xf; voldir->name_length=(voldir_buffer[0x4]&0xf); if (voldir->storage_type!=0xf) { @@ -85,7 +68,7 @@ static int prodos_read_voldir(int fd, struct voldir_t *voldir) { /* Checks if "filename" exists */ /* returns entry/track/sector */ -static int dos33_check_file_exists(int fd, +static int prodos_check_file_exists(int fd, char *filename, int file_deleted) { @@ -118,7 +101,7 @@ repeat_catalog: if (file_track!=0x0) { if (file_track==0xff) { - dos33_filename_to_ascii(file_name, + prodos_filename_to_ascii(file_name, catalog_buffer+(CATALOG_FILE_LIST+(i*CATALOG_ENTRY_SIZE+FILE_NAME)),29); if (file_deleted) { @@ -129,7 +112,7 @@ repeat_catalog: } } else { - dos33_filename_to_ascii(file_name, + 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)) { @@ -150,13 +133,13 @@ repeat_catalog: return -1; } -static int dos33_free_sector(unsigned char *voldir,int fd,int track,int sector) { +static int prodos_free_sector(struct voldir_t *voldir,int fd,int track,int sector) { int result; /* mark as free in VTOC */ - dos33_vtoc_free_sector(voldir,track,sector); - + prodos_voldir_free_sector(voldir,track,sector); +#if 0 /* write modified VTOC back out */ lseek(fd,DISK_OFFSET(PRODOS_VOLDIR_TRACK,PRODOS_VOLDIR_BLOCK),SEEK_SET); result=write(fd,&voldir,PRODOS_BYTES_PER_BLOCK); @@ -164,24 +147,24 @@ static int dos33_free_sector(unsigned char *voldir,int fd,int track,int sector) if (result<0) { fprintf(stderr,"Error on I/O\n"); } - +#endif return 0; } -static int dos33_allocate_sector(int fd, unsigned char *voldir) { +static int prodos_allocate_sector(int fd, struct voldir_t *voldir) { int found_track=0,found_sector=0; int result; /* Find an empty sector */ - result=dos33_vtoc_find_free_sector(voldir,&found_track,&found_sector); + result=prodos_voldir_find_free_sector(voldir,&found_track,&found_sector); if (result<0) { - fprintf(stderr,"ERROR: dos33_allocate_sector: Disk full!\n"); + fprintf(stderr,"ERROR: prodos_allocate_sector: Disk full!\n"); return -1; } - +#if 0 /* store new track/direction info */ voldir[VTOC_LAST_ALLOC_T]=found_track; @@ -195,7 +178,7 @@ static int dos33_allocate_sector(int fd, unsigned char *voldir) { result=write(fd,voldir,PRODOS_BYTES_PER_BLOCK); if (result<0) fprintf(stderr,"Error on I/O\n"); - +#endif return ((found_track<<8)+found_sector); } @@ -272,7 +255,7 @@ static int prodos_add_file(struct voldir_t *voldir, (file_size/(122*PRODOS_BYTES_PER_BLOCK)); /* extra t/s lists */ /* Get free space on device */ - free_space=dos33_vtoc_free_space(voldir); + free_space=prodos_vtoc_free_space(voldir); /* Check for free space */ if (needed_sectors*PRODOS_BYTES_PER_BLOCK>free_space) { @@ -303,7 +286,7 @@ static int prodos_add_file(struct voldir_t *voldir, old_ts_list=ts_list; /* allocate a sector for the new list */ - ts_list=dos33_allocate_sector(fd,voldir); + ts_list=prodos_allocate_sector(fd,voldir); sectors_used++; if (ts_list<0) return -1; @@ -346,7 +329,7 @@ static int prodos_add_file(struct voldir_t *voldir, } /* allocate a sector */ - data_ts=dos33_allocate_sector(fd,voldir); + data_ts=prodos_allocate_sector(fd,voldir); sectors_used++; if (data_ts<0) return -1; @@ -453,7 +436,7 @@ got_a_dentry: catalog_buffer[CATALOG_FILE_LIST+(i*CATALOG_ENTRY_SIZE)+1]=(initial_ts_list&0xff); /* set file type */ catalog_buffer[CATALOG_FILE_LIST+(i*CATALOG_ENTRY_SIZE)+FILE_TYPE]= - dos33_char_to_type(dos_type,0); + prodos_char_to_type(dos_type,0); // printf("Pointing T/S to %x/%x\n",(initial_ts_list>>8)&0xff,initial_ts_list&0xff); @@ -485,7 +468,7 @@ got_a_dentry: /* load a file. fts=entry/track/sector */ -static int dos33_load_file(int fd,int fts,char *filename) { +static int prodos_load_file(int fd,int fts,char *filename) { int output_fd; int catalog_file,catalog_track,catalog_sector; @@ -516,7 +499,7 @@ static int dos33_load_file(int fd,int fts,char *filename) { (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=dos33_file_type(sector_buffer[CATALOG_FILE_LIST+ + file_type=prodos_file_type(sector_buffer[CATALOG_FILE_LIST+ (catalog_file*CATALOG_ENTRY_SIZE)+FILE_TYPE]); // printf("file_type: %c\n",file_type); @@ -589,7 +572,7 @@ keep_saving: } /* lock a file. fts=entry/track/sector */ -static int dos33_lock_file(int fd,int fts,int lock) { +static int prodos_lock_file(int fd,int fts,int lock) { int catalog_file,catalog_track,catalog_sector; int file_type,result; @@ -628,7 +611,7 @@ static int dos33_lock_file(int fd,int fts,int lock) { /* rename a file. fts=entry/track/sector */ /* FIXME: can we rename a locked file? */ /* FIXME: validate the new filename is valid */ -static int dos33_rename_file(int fd,int fts,char *new_name) { +static int prodos_rename_file(int fd,int fts,char *new_name) { int catalog_file,catalog_track,catalog_sector; int x,result; @@ -758,13 +741,13 @@ keep_deleting: (catalog_buffer[TSL_LIST+2*i+1]==0)) { } else { - dos33_free_sector(voldir,fd,catalog_buffer[TSL_LIST+2*i], + prodos_free_sector(voldir,fd,catalog_buffer[TSL_LIST+2*i], catalog_buffer[TSL_LIST+2*i+1]); } } /* free the t/s list */ - dos33_free_sector(voldir,fd,ts_track,ts_sector); + prodos_free_sector(voldir,fd,ts_track,ts_sector); /* Point to next t/s list */ ts_track=catalog_buffer[TSL_NEXT_TRACK]; @@ -802,7 +785,7 @@ keep_deleting: } /* ??? */ -static int dos33_rename_hello(int fd, char *new_name) { +static int prodos_rename_hello(int fd, char *new_name) { char buffer[PRODOS_BYTES_PER_BLOCK]; int i; @@ -826,7 +809,7 @@ static int dos33_rename_hello(int fd, char *new_name) { } static void display_help(char *name, int version_only) { - printf("\ndos33 version %s\n",VERSION); + printf("\nprodos version %s\n",VERSION); printf("by Vince Weaver <vince@deater.net>\n"); printf("\n"); @@ -1060,7 +1043,7 @@ int main(int argc, char **argv) { /* get the entry/track/sector for file */ - catalog_entry=dos33_check_file_exists(dos_fd, + catalog_entry=prodos_check_file_exists(dos_fd, apple_filename, DOS33_FILE_NORMAL); if (catalog_entry<0) { @@ -1069,7 +1052,7 @@ int main(int argc, char **argv) { goto exit_and_close; } - dos33_load_file(dos_fd,catalog_entry,local_filename); + prodos_load_file(dos_fd,catalog_entry,local_filename); break; @@ -1098,7 +1081,7 @@ int main(int argc, char **argv) { case COMMAND_BSAVE: if (debug) printf("\ttype=%c\n",type); - +#if 0 if (argc==optind) { fprintf(stderr,"Error! Need file_name\n"); @@ -1146,7 +1129,7 @@ int main(int argc, char **argv) { if (debug) printf("\tApple filename: %s\n",apple_filename); - catalog_entry=dos33_check_file_exists(dos_fd,apple_filename, + catalog_entry=prodos_check_file_exists(dos_fd,apple_filename, DOS33_FILE_NORMAL); if (catalog_entry>=0) { @@ -1160,7 +1143,7 @@ int main(int argc, char **argv) { } } fprintf(stderr,"Deleting previous version...\n"); - dos33_delete_file(voldir,dos_fd,catalog_entry); + prodos_delete_file(voldir,dos_fd,catalog_entry); } if (command==COMMAND_SAVE) { prodos_add_file(&voldir,dos_fd,type, @@ -1172,6 +1155,7 @@ int main(int argc, char **argv) { ADD_BINARY, address, length, local_filename,apple_filename); } +#endif break; @@ -1193,7 +1177,7 @@ int main(int argc, char **argv) { truncate_filename(apple_filename,argv[optind]); - catalog_entry=dos33_check_file_exists(dos_fd, + catalog_entry=prodos_check_file_exists(dos_fd, apple_filename, DOS33_FILE_NORMAL); if (catalog_entry<0) { @@ -1228,7 +1212,7 @@ int main(int argc, char **argv) { truncate_filename(apple_filename,argv[optind]); /* get the entry/track/sector for file */ - catalog_entry=dos33_check_file_exists(dos_fd, + catalog_entry=prodos_check_file_exists(dos_fd, apple_filename, DOS33_FILE_NORMAL); if (catalog_entry<0) { @@ -1237,7 +1221,7 @@ int main(int argc, char **argv) { goto exit_and_close; } - dos33_lock_file(dos_fd,catalog_entry,command==COMMAND_LOCK); + prodos_lock_file(dos_fd,catalog_entry,command==COMMAND_LOCK); break; @@ -1266,7 +1250,7 @@ int main(int argc, char **argv) { truncate_filename(new_filename,argv[optind]); /* get the entry/track/sector for file */ - catalog_entry=dos33_check_file_exists(dos_fd, + catalog_entry=prodos_check_file_exists(dos_fd, apple_filename, DOS33_FILE_NORMAL); if (catalog_entry<0) { @@ -1275,7 +1259,7 @@ int main(int argc, char **argv) { goto exit_and_close; } - dos33_rename_file(dos_fd,catalog_entry,new_filename); + prodos_rename_file(dos_fd,catalog_entry,new_filename); break; @@ -1294,7 +1278,7 @@ int main(int argc, char **argv) { truncate_filename(apple_filename,argv[optind]); /* get the entry/track/sector for file */ - catalog_entry=dos33_check_file_exists(dos_fd, + catalog_entry=prodos_check_file_exists(dos_fd, apple_filename, DOS33_FILE_DELETED); if (catalog_entry<0) { @@ -1317,7 +1301,7 @@ int main(int argc, char **argv) { truncate_filename(apple_filename,argv[optind]); - catalog_entry=dos33_check_file_exists(dos_fd, + catalog_entry=prodos_check_file_exists(dos_fd, apple_filename, DOS33_FILE_NORMAL); @@ -1326,11 +1310,11 @@ int main(int argc, char **argv) { "Warning! File %s does not exist\n", apple_filename); } - dos33_rename_hello(dos_fd,apple_filename); + prodos_rename_hello(dos_fd,apple_filename); break; case COMMAND_INIT: - /* use common code from mkdos33fs? */ + /* use common code from mkprodosfs? */ case COMMAND_COPY: /* use temp file? Walking a sector at a time seems a pain */ default: diff --git a/utils/prodos-utils/prodos.h b/utils/prodos-utils/prodos.h index 5ce89d1a..91644ff1 100644 --- a/utils/prodos-utils/prodos.h +++ b/utils/prodos-utils/prodos.h @@ -9,6 +9,7 @@ #define PRODOS_VOLDIR_BLOCK 2 struct voldir_t { + int fd; unsigned char storage_type; unsigned char name_length; unsigned char version; @@ -23,21 +24,6 @@ struct voldir_t { unsigned int creation_time; }; - - /* VTOC Values */ -#define VTOC_CATALOG_T 0x1 -#define VTOC_CATALOG_S 0x2 -#define VTOC_DOS_RELEASE 0x3 -#define VTOC_DISK_VOLUME 0x6 -#define VTOC_MAX_TS_PAIRS 0x27 -#define VTOC_LAST_ALLOC_T 0x30 -#define VTOC_ALLOC_DIRECT 0x31 -#define VTOC_NUM_TRACKS 0x34 -#define VTOC_S_PER_TRACK 0x35 -#define VTOC_BYTES_PER_SL 0x36 -#define VTOC_BYTES_PER_SH 0x37 -#define VTOC_FREE_BITMAPS 0x38 - /* CATALOG_VALUES */ #define CATALOG_NEXT_T 0x01 #define CATALOG_NEXT_S 0x02 @@ -74,22 +60,22 @@ struct voldir_t { #define DOS33_FILE_DELETED 1 /* prodos_volume_bitmap.c */ -int dos33_vtoc_free_space(unsigned char *vtoc); -void dos33_vtoc_free_sector(unsigned char *vtoc, int track, int sector); -void dos33_vtoc_reserve_sector(unsigned char *vtoc, int track, int sector); -void dos33_vtoc_dump_bitmap(unsigned char *vtoc, int num_tracks); -int dos33_vtoc_find_free_sector(unsigned char *vtoc, +int prodos_voldir_free_space(struct voldir_t *voldir); +void prodos_voldir_free_sector(struct voldir_t *voldir, int track, int sector); +void prodos_voldir_reserve_sector(struct voldir_t *voldir, int track, int sector); +void prodos_voldir_dump_bitmap(struct voldir_t *voldir); +int prodos_voldir_find_free_sector(struct voldir_t *voldir, int *found_track, int *found_sector); /* prodos_catalog.c */ -unsigned char dos33_char_to_type(char type, int lock); +unsigned char prodos_char_to_type(char type, int lock); void prodos_catalog(int dos_fd, struct voldir_t *voldir); -char *dos33_filename_to_ascii(char *dest,unsigned char *src,int len); -unsigned char dos33_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); int prodos_showfree(struct voldir_t *voldir, int fd); -/* prodos.c */ -int prodos_read_block(int fd,unsigned char *block, int blocknum); +/* prodos_read.c */ +int prodos_read_block(struct voldir_t *voldir,unsigned char *block, int blocknum); diff --git a/utils/prodos-utils/prodos_catalog.c b/utils/prodos-utils/prodos_catalog.c index cf4b4aa6..b34fc015 100644 --- a/utils/prodos-utils/prodos_catalog.c +++ b/utils/prodos-utils/prodos_catalog.c @@ -7,7 +7,7 @@ static int debug=0; -unsigned char dos33_file_type(int value) { +unsigned char prodos_file_type(int value) { unsigned char result; @@ -26,10 +26,10 @@ unsigned char dos33_file_type(int value) { } -unsigned char dos33_char_to_type(char type, int lock) { - - unsigned char result,temp_type; +unsigned char prodos_char_to_type(char type, int lock) { + unsigned char result=0,temp_type; +#if 0 temp_type=type; /* Covert to upper case */ if (temp_type>='a') temp_type=temp_type-0x20; @@ -46,12 +46,13 @@ unsigned char dos33_char_to_type(char type, int lock) { default: result=0x0; } if (lock) result|=0x80; +#endif return result; } - /* dos33 filenames have top bit set on ascii chars */ + /* prodos filenames have top bit set on ascii chars */ /* and are padded with spaces */ -char *dos33_filename_to_ascii(char *dest,unsigned char *src,int len) { +char *prodos_filename_to_ascii(char *dest,unsigned char *src,int len) { int i=0,last_nonspace=0; @@ -66,14 +67,15 @@ char *dos33_filename_to_ascii(char *dest,unsigned char *src,int len) { } /* Get a T/S value from a Catalog Sector */ -static int dos33_get_catalog_ts(unsigned char *voldir) { +static int prodos_get_catalog_ts(struct voldir_t *voldir) { - return TS_TO_INT(voldir[VTOC_CATALOG_T],voldir[VTOC_CATALOG_S]); +// return TS_TO_INT(voldir[VTOC_CATALOG_T],voldir[VTOC_CATALOG_S]); + return 0; } /* returns the next valid catalog entry */ /* after the one passed in */ -static int dos33_find_next_file(int fd,int catalog_tsf,unsigned char *voldir) { +static int prodos_find_next_file(int fd,int catalog_tsf,unsigned char *voldir) { int catalog_track,catalog_sector,catalog_file; int file_track,i; @@ -89,7 +91,7 @@ static int dos33_find_next_file(int fd,int catalog_tsf,unsigned char *voldir) { "CURRENT FILE=%X TRACK=%X SECTOR=%X\n", catalog_file,catalog_track,catalog_sector); } - +#if 0 catalog_loop: /* Read in Catalog Sector */ @@ -137,11 +139,11 @@ catalog_loop: } - +#endif return -1; } -static int dos33_print_file_info(int fd,int catalog_tsf) { +static int prodos_print_file_info(int fd,int catalog_tsf) { int catalog_track,catalog_sector,catalog_file,i; char temp_string[BUFSIZ]; @@ -154,7 +156,7 @@ static int dos33_print_file_info(int fd,int catalog_tsf) { if (debug) fprintf(stderr,"CATALOG FILE=%X TRACK=%X SECTOR=%X\n", catalog_file,catalog_track,catalog_sector); - +#if 0 /* Read in Catalog Sector */ lseek(fd,DISK_OFFSET(catalog_track,catalog_sector),SEEK_SET); result=read(fd,sector_buffer,PRODOS_BYTES_PER_BLOCK); @@ -166,12 +168,12 @@ static int dos33_print_file_info(int fd,int catalog_tsf) { printf(" "); } - printf("%c",dos33_file_type(sector_buffer[CATALOG_FILE_LIST+(catalog_file*CATALOG_ENTRY_SIZE)+FILE_TYPE])); + printf("%c",prodos_file_type(sector_buffer[CATALOG_FILE_LIST+(catalog_file*CATALOG_ENTRY_SIZE)+FILE_TYPE])); printf(" "); printf("%.3i ",sector_buffer[CATALOG_FILE_LIST+(catalog_file*CATALOG_ENTRY_SIZE+FILE_SIZE_L)]+ (sector_buffer[CATALOG_FILE_LIST+(catalog_file*CATALOG_ENTRY_SIZE+FILE_SIZE_H)]<<8)); - dos33_filename_to_ascii(temp_string,sector_buffer+(CATALOG_FILE_LIST+ + prodos_filename_to_ascii(temp_string,sector_buffer+(CATALOG_FILE_LIST+ (catalog_file*CATALOG_ENTRY_SIZE+FILE_NAME)),30); for(i=0;i<strlen(temp_string);i++) { @@ -186,7 +188,7 @@ static int dos33_print_file_info(int fd,int catalog_tsf) { printf("\n"); if (result<0) fprintf(stderr,"Error on I/O\n"); - +#endif return 0; } @@ -196,17 +198,17 @@ void prodos_catalog(int dos_fd, struct voldir_t *voldir) { #if 0 /* get first catalog */ - catalog_entry=dos33_get_catalog_ts(voldir); + catalog_entry=prodos_get_catalog_ts(voldir); printf("\nDISK VOLUME %i\n\n",voldir[VTOC_DISK_VOLUME]); while(catalog_entry>0) { - catalog_entry=dos33_find_next_file(dos_fd,catalog_entry,voldir); + catalog_entry=prodos_find_next_file(dos_fd,catalog_entry,voldir); if (debug) fprintf(stderr,"CATALOG entry=$%X\n",catalog_entry); if (catalog_entry>0) { - dos33_print_file_info(dos_fd,catalog_entry); + prodos_print_file_info(dos_fd,catalog_entry); /* why 1<<16 ? */ catalog_entry+=(1<<16); - /* dos33_find_next_file() handles wrapping issues */ + /* prodos_find_next_file() handles wrapping issues */ } } #endif diff --git a/utils/prodos-utils/prodos_dump.c b/utils/prodos-utils/prodos_dump.c index af18cf27..ba512a64 100644 --- a/utils/prodos-utils/prodos_dump.c +++ b/utils/prodos-utils/prodos_dump.c @@ -43,6 +43,15 @@ static void prodos_print_time(int t) { } +static void prodos_print_access(int access) { + + if (access&0x80) printf("DESTROY "); + if (access&0x40) printf("RENAME "); + if (access&0x20) printf("VOLDIR_NEW "); + if (access&0x2) printf("VOLDIR_WRITE "); + if (access&0x1) printf("VOLDIR_READ "); + +} static void dump_voldir(struct voldir_t *voldir) { unsigned char volume_name[16]; @@ -64,7 +73,9 @@ static void dump_voldir(struct voldir_t *voldir) { printf("\tVersion: %d\n",voldir->version); printf("\tMin Version: %d\n",voldir->min_version); - printf("\tAccess: %d\n",voldir->access); + printf("\tAccess: $%X ",voldir->access); + prodos_print_access(voldir->access); + printf("\n"); printf("\tEntry Length: %d\n",voldir->entry_length); printf("\tEntries per block: %d\n",voldir->entries_per_block); printf("\tFile Count: %d\n",voldir->file_count); @@ -87,14 +98,10 @@ int prodos_dump(struct voldir_t *voldir, int fd) { int result; dump_voldir(voldir); + + prodos_voldir_dump_bitmap(voldir); + #if 0 - catalog_t=voldir[VTOC_CATALOG_T]; - catalog_s=voldir[VTOC_CATALOG_S]; - ts_total=voldir[VTOC_MAX_TS_PAIRS]; - num_tracks=voldir[VTOC_NUM_TRACKS]; - - dos33_vtoc_dump_bitmap(voldir,num_tracks); - repeat_catalog: printf("\nCatalog Sector $%02X/$%02x\n",catalog_t,catalog_s); @@ -215,7 +222,7 @@ int prodos_showfree(struct voldir_t *voldir, int fd) { num_tracks=voldir[VTOC_NUM_TRACKS]; sectors_per_track=voldir[VTOC_S_PER_TRACK]; - dos33_vtoc_dump_bitmap(voldir,num_tracks); + prodos_voldir_dump_bitmap(voldir); /* Reserve DOS */ for(i=0;i<3;i++) for(j=0;j<16;j++) usage[i][j]='$'; diff --git a/utils/prodos-utils/prodos_read.c b/utils/prodos-utils/prodos_read.c new file mode 100644 index 00000000..3abbb292 --- /dev/null +++ b/utils/prodos-utils/prodos_read.c @@ -0,0 +1,44 @@ +#include <stdio.h> +#include <stdlib.h> /* exit() */ +#include <string.h> /* strncpy() */ +#include <sys/stat.h> /* struct stat */ +#include <fcntl.h> /* O_RDONLY */ +#include <unistd.h> /* lseek() */ +#include <ctype.h> /* toupper() */ +#include <errno.h> + +#include "version.h" + +#include "prodos.h" + +#if 0 +static int debug=0,ignore_errors=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 + +int prodos_read_block(struct voldir_t *voldir, + unsigned char *block, int blocknum) { + + int result; + + /* Note, we need to handle interleave, etc */ + /* For now assume it's linear */ + + /* Seek to VOLDIR */ + lseek(voldir->fd,blocknum*PRODOS_BYTES_PER_BLOCK,SEEK_SET); + result=read(voldir->fd,block,PRODOS_BYTES_PER_BLOCK); + + if (result<PRODOS_BYTES_PER_BLOCK) { + fprintf(stderr,"Error reading block %d\n",blocknum); + return -1; + } + return 0; +} + diff --git a/utils/prodos-utils/prodos_volume_bitmap.c b/utils/prodos-utils/prodos_volume_bitmap.c index 6d3b255b..da3f6c15 100644 --- a/utils/prodos-utils/prodos_volume_bitmap.c +++ b/utils/prodos-utils/prodos_volume_bitmap.c @@ -41,11 +41,18 @@ static int find_first_one(unsigned char byte) { /* Return how many bytes free in the filesystem */ /* by reading the VTOC_FREE_BITMAP */ -int dos33_vtoc_free_space(unsigned char *vtoc) { +int prodos_voldir_free_space(struct voldir_t *voldir) { + int volblocks; + unsigned char temp_block[PRODOS_BYTES_PER_BLOCK]; unsigned char bitmap[4]; int i,sectors_free=0; + volblocks=1+voldir->total_blocks/(PRODOS_BYTES_PER_BLOCK*8); + + prodos_read_block(voldir,temp_block,voldir->bit_map_pointer); + +#if 0 for(i=0;i<TRACKS_PER_DISK;i++) { bitmap[0]=vtoc[VTOC_FREE_BITMAPS+(i*4)]; bitmap[1]=vtoc[VTOC_FREE_BITMAPS+(i*4)+1]; @@ -55,13 +62,14 @@ int dos33_vtoc_free_space(unsigned char *vtoc) { sectors_free+=ones_lookup[bitmap[1]&0xf]; sectors_free+=ones_lookup[(bitmap[1]>>4)&0xf]; } - +#endif return sectors_free*PRODOS_BYTES_PER_BLOCK; } /* free a sector from the sector bitmap */ -void dos33_vtoc_free_sector(unsigned char *vtoc, int track, int sector) { +void prodos_voldir_free_sector(struct voldir_t *voldir, int track, int sector) { +#if 0 /* each bitmap is 32 bits. With 16-sector tracks only first 16 used */ /* 1 indicates free, 0 indicates used */ if (sector<8) { @@ -79,11 +87,13 @@ void dos33_vtoc_free_sector(unsigned char *vtoc, int track, int sector) { else { fprintf(stderr,"Error vtoc_free_sector! sector too big %d\n",sector); } +#endif } /* reserve a sector in the sector bitmap */ -void dos33_vtoc_reserve_sector(unsigned char *vtoc, int track, int sector) { +void prodos_voldir_reserve_sector(struct voldir_t *voldir, int track, int sector) { +#if 0 /* each bitmap is 32 bits. With 16-sector tracks only first 16 used */ /* 1 indicates free, 0 indicates used */ if (sector<8) { @@ -101,16 +111,18 @@ void dos33_vtoc_reserve_sector(unsigned char *vtoc, int track, int sector) { else { fprintf(stderr,"Error vtoc_reserve_sector! sector too big %d\n",sector); } +#endif } -void dos33_vtoc_dump_bitmap(unsigned char *vtoc, int num_tracks) { +void prodos_voldir_dump_bitmap(struct voldir_t *voldir) { int i,j; printf("\nFree sector bitmap:\n"); printf("\tU=used, .=free\n"); printf("\tTrack FEDCBA98 76543210\n"); +#if 0 for(i=0;i<num_tracks;i++) { printf("\t $%02X: ",i); for(j=0;j<8;j++) { @@ -132,17 +144,18 @@ void dos33_vtoc_dump_bitmap(unsigned char *vtoc, int num_tracks) { } printf("\n"); } +#endif } /* reserve a sector in the sector bitmap */ -int dos33_vtoc_find_free_sector(unsigned char *vtoc, +int prodos_voldir_find_free_sector(struct voldir_t *voldir, int *found_track, int *found_sector) { int start_track,track_dir,i; int bitmap; int found=0; - +#if 0 /* Originally used to keep things near center of disk for speed */ /* We can use to avoid fragmentation possibly */ start_track=vtoc[VTOC_LAST_ALLOC_T]%TRACKS_PER_DISK; @@ -195,11 +208,11 @@ int dos33_vtoc_find_free_sector(unsigned char *vtoc, if (found) { /* clear bit indicating in use */ - dos33_vtoc_reserve_sector(vtoc, *found_track, *found_sector); + prodos_voldir_reserve_sector(voldir, *found_track, *found_sector); return 0; } - +#endif /* no room */ return -1;