123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187 |
- #pragma once
- typedef struct {
- char year[4];
- char month[2];
- char day[2];
- char hour[2];
- char minute[2];
- char second[2];
- char hundredths[2];
- int8_t timezone;
- } __attribute__((packed)) iso_9660_datetime_t;
- typedef struct {
- uint8_t year;
- uint8_t month;
- uint8_t day;
- uint8_t hour;
- uint8_t minute;
- uint8_t second;
- int8_t timezone;
- } __attribute__((packed)) iso_9660_rec_date_t;
- typedef struct {
- uint8_t length;
- uint8_t ext_length;
- uint32_t extent_start_LSB;
- uint32_t extent_start_MSB;
- uint32_t extent_length_LSB;
- uint32_t extent_length_MSB;
- iso_9660_rec_date_t record_date;
- uint8_t flags;
- uint8_t interleave_units;
- uint8_t interleave_gap;
- uint16_t volume_seq_LSB;
- uint16_t volume_seq_MSB;
- uint8_t name_len;
- char name[];
- } __attribute__((packed)) iso_9660_directory_entry_t;
- typedef struct {
- uint8_t type; /* 0x01 */
- char id[5]; /* CD001 */
- uint8_t version;
- uint8_t _unused0;
- char system_id[32];
- char volume_id[32];
- uint8_t _unused1[8];
- uint32_t volume_space_LSB;
- uint32_t volume_space_MSB;
- uint8_t _unused2[32];
- uint16_t volume_set_LSB;
- uint16_t volume_set_MSB;
- uint16_t volume_seq_LSB;
- uint16_t volume_seq_MSB;
- uint16_t logical_block_size_LSB;
- uint16_t logical_block_size_MSB;
- uint32_t path_table_size_LSB;
- uint32_t path_table_size_MSB;
- uint32_t path_table_LSB;
- uint32_t optional_path_table_LSB;
- uint32_t path_table_MSB;
- uint32_t optional_path_table_MSB;
- /* iso_9660_directory_entry_t */
- char root[34];
- char volume_set_id[128];
- char volume_publisher[128];
- char data_preparer[128];
- char application_id[128];
- char copyright_file[38];
- char abstract_file[36];
- char bibliographic_file[37];
- iso_9660_datetime_t creation;
- iso_9660_datetime_t modification;
- iso_9660_datetime_t expiration;
- iso_9660_datetime_t effective;
- uint8_t file_structure_version;
- uint8_t _unused_3;
- char application_use[];
- } __attribute__((packed)) iso_9660_volume_descriptor_t;
- #define ISO_SECTOR_SIZE 2048
- #define FLAG_HIDDEN 0x01
- #define FLAG_DIRECTORY 0x02
- #define FLAG_ASSOCIATED 0x04
- #define FLAG_EXTENDED 0x08
- #define FLAG_PERMISSIONS 0x10
- #define FLAG_CONTINUES 0x80
- static int root_sector = 0;
- static iso_9660_volume_descriptor_t * root = (iso_9660_volume_descriptor_t *)((uint8_t *)0x20000);
- static iso_9660_directory_entry_t * dir_entry = (iso_9660_directory_entry_t *)((uint8_t *)0x20800);
- static uint8_t * mod_dir = (uint8_t *)0x21000;
- static uint8_t * dir_entries = (uint8_t *)(0x30000);
- static struct ata_device * device = 0;
- static int navigate(char * name) {
- memset(dir_entries, 2048, 0xA5);
- //print("reading from sector ");
- //print_hex(dir_entry->extent_start_LSB);
- //print("\n");
- ata_device_read_sector_atapi(device, dir_entry->extent_start_LSB, dir_entries);
- ata_device_read_sector_atapi(device, dir_entry->extent_start_LSB+1, dir_entries + 2048);
- ata_device_read_sector_atapi(device, dir_entry->extent_start_LSB+2, dir_entries + 4096);
- long offset = 0;
- while (1) {
- iso_9660_directory_entry_t * dir = (iso_9660_directory_entry_t *)(dir_entries + offset);
- if (dir->length == 0) {
- if (offset < dir_entry->extent_length_LSB) {
- offset += 1; // this->block_size - ((uintptr_t)offset % this->block_size);
- goto try_again;
- }
- break;
- }
- if (!(dir->flags & FLAG_HIDDEN)) {
- char file_name[dir->name_len + 1];
- memcpy(file_name, dir->name, dir->name_len);
- file_name[dir->name_len] = 0;
- char * s = strchr(file_name,';');
- if (s) {
- *s = '\0';
- }
- #if 0
- print("Found a file: ");
- print(" Name: ");
- print(file_name); print("\n");
- #endif
- if (!strcmp(file_name, name)) {
- memcpy(dir_entry, dir, sizeof(iso_9660_directory_entry_t));
- return 1;
- }
- }
- offset += dir->length;
- try_again:
- if ((long)(offset) > dir_entry->extent_length_LSB) break;
- }
- return 0;
- }
- static void restore_root(void) {
- memcpy(dir_entry, (iso_9660_directory_entry_t *)&root->root, sizeof(iso_9660_directory_entry_t));
- #if 0
- print("Root restored.");
- print("\n Entry len: "); print_hex( dir_entry->length);
- print("\n File start: "); print_hex( dir_entry->extent_start_LSB);
- print("\n File len: "); print_hex( dir_entry->extent_length_LSB);
- print("\n");
- #endif
- }
- static void restore_mod(void) {
- memcpy(dir_entry, (iso_9660_directory_entry_t *)mod_dir, sizeof(iso_9660_directory_entry_t));
- #if 0
- print("mod restored.");
- print("\n Entry len: "); print_hex( dir_entry->length);
- print("\n File start: "); print_hex( dir_entry->extent_start_LSB);
- print("\n File len: "); print_hex( dir_entry->extent_length_LSB);
- print("\n");
- #endif
- }
|