|
|
1.1 ! root 1: /* ! 2: * GRUB -- GRand Unified Bootloader ! 3: * Copyright (C) 2001 Free Software Foundation, Inc. ! 4: * ! 5: * This program is free software; you can redistribute it and/or modify ! 6: * it under the terms of the GNU General Public License as published by ! 7: * the Free Software Foundation; either version 2 of the License, or ! 8: * (at your option) any later version. ! 9: * ! 10: * This program is distributed in the hope that it will be useful, ! 11: * but WITHOUT ANY WARRANTY; without even the implied warranty of ! 12: * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ! 13: * GNU General Public License for more details. ! 14: * ! 15: * You should have received a copy of the GNU General Public License ! 16: * along with this program; if not, write to the Free Software ! 17: * Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston, ! 18: * MA 02110-1301, USA. ! 19: */ ! 20: ! 21: #ifdef FSYS_VSTAFS ! 22: ! 23: #include "shared.h" ! 24: #include "filesys.h" ! 25: #include "vstafs.h" ! 26: ! 27: ! 28: static void get_file_info (int sector); ! 29: static struct dir_entry *vstafs_readdir (long sector); ! 30: static struct dir_entry *vstafs_nextdir (void); ! 31: ! 32: ! 33: #define FIRST_SECTOR ((struct first_sector *) FSYS_BUF) ! 34: #define FILE_INFO ((struct fs_file *) (long) FIRST_SECTOR + 8192) ! 35: #define DIRECTORY_BUF ((struct dir_entry *) (long) FILE_INFO + 512) ! 36: ! 37: #define ROOT_SECTOR 1 ! 38: ! 39: /* ! 40: * In f_sector we store the sector number in which the information about ! 41: * the found file is. ! 42: */ ! 43: static int f_sector; ! 44: ! 45: int ! 46: vstafs_mount (void) ! 47: { ! 48: int retval = 1; ! 49: ! 50: if( (((current_drive & 0x80) || (current_slice != 0)) ! 51: && current_slice != PC_SLICE_TYPE_VSTAFS) ! 52: || ! devread (0, 0, BLOCK_SIZE, (char *) FSYS_BUF) ! 53: || FIRST_SECTOR->fs_magic != 0xDEADFACE) ! 54: retval = 0; ! 55: ! 56: return retval; ! 57: } ! 58: ! 59: static void ! 60: get_file_info (int sector) ! 61: { ! 62: devread (sector, 0, BLOCK_SIZE, (char *) FILE_INFO); ! 63: } ! 64: ! 65: static int curr_ext, current_direntry, current_blockpos; ! 66: static struct alloc *a1; ! 67: ! 68: static struct dir_entry * ! 69: vstafs_readdir (long sector) ! 70: { ! 71: /* ! 72: * Get some information from the current directory ! 73: */ ! 74: get_file_info (sector); ! 75: if (FILE_INFO->type != 2) ! 76: { ! 77: errnum = ERR_FILE_NOT_FOUND; ! 78: return NULL; ! 79: } ! 80: ! 81: a1 = FILE_INFO->blocks; ! 82: curr_ext = 0; ! 83: devread (a1[curr_ext].a_start, 0, 512, (char *) DIRECTORY_BUF); ! 84: current_direntry = 11; ! 85: current_blockpos = 0; ! 86: ! 87: return &DIRECTORY_BUF[10]; ! 88: } ! 89: ! 90: static struct dir_entry * ! 91: vstafs_nextdir (void) ! 92: { ! 93: if (current_direntry > 15) ! 94: { ! 95: current_direntry = 0; ! 96: if (++current_blockpos > (a1[curr_ext].a_len - 1)) ! 97: { ! 98: current_blockpos = 0; ! 99: curr_ext++; ! 100: } ! 101: ! 102: if (curr_ext < FILE_INFO->extents) ! 103: { ! 104: devread (a1[curr_ext].a_start + current_blockpos, 0, ! 105: 512, (char *) DIRECTORY_BUF); ! 106: } ! 107: else ! 108: { ! 109: /* errnum =ERR_FILE_NOT_FOUND; */ ! 110: return NULL; ! 111: } ! 112: } ! 113: ! 114: return &DIRECTORY_BUF[current_direntry++]; ! 115: } ! 116: ! 117: int ! 118: vstafs_dir (char *dirname) ! 119: { ! 120: char *fn, ch; ! 121: struct dir_entry *d; ! 122: /* int l, i, s; */ ! 123: ! 124: /* ! 125: * Read in the entries of the current directory. ! 126: */ ! 127: f_sector = ROOT_SECTOR; ! 128: do ! 129: { ! 130: if (! (d = vstafs_readdir (f_sector))) ! 131: { ! 132: return 0; ! 133: } ! 134: ! 135: /* ! 136: * Find the file in the path ! 137: */ ! 138: while (*dirname == '/') dirname++; ! 139: fn = dirname; ! 140: while ((ch = *fn) && ch != '/' && ! isspace (ch)) fn++; ! 141: *fn = 0; ! 142: ! 143: do ! 144: { ! 145: if (d->name[0] == 0 || d->name[0] & 0x80) ! 146: continue; ! 147: ! 148: #ifndef STAGE1_5 ! 149: if (print_possibilities && ch != '/' ! 150: && (! *dirname || strcmp (dirname, d->name) <= 0)) ! 151: { ! 152: if (print_possibilities > 0) ! 153: print_possibilities = -print_possibilities; ! 154: ! 155: printf (" %s", d->name); ! 156: } ! 157: #endif ! 158: if (! grub_strcmp (dirname, d->name)) ! 159: { ! 160: f_sector = d->start; ! 161: get_file_info (f_sector); ! 162: filemax = FILE_INFO->len; ! 163: break; ! 164: } ! 165: } ! 166: while ((d =vstafs_nextdir ())); ! 167: ! 168: *(dirname = fn) = ch; ! 169: if (! d) ! 170: { ! 171: if (print_possibilities < 0) ! 172: { ! 173: #ifndef STAGE1_5 ! 174: putchar ('\n'); ! 175: #endif ! 176: return 1; ! 177: } ! 178: ! 179: errnum = ERR_FILE_NOT_FOUND; ! 180: return 0; ! 181: } ! 182: } ! 183: while (*dirname && ! isspace (ch)); ! 184: ! 185: return 1; ! 186: } ! 187: ! 188: int ! 189: vstafs_read (char *addr, int len) ! 190: { ! 191: struct alloc *a2; ! 192: int size, ret = 0, offset, curr_len = 0; ! 193: int curr_ext2; ! 194: char extent; ! 195: int ext_size; ! 196: char *curr_pos; ! 197: ! 198: get_file_info (f_sector); ! 199: size = FILE_INFO->len-VSTAFS_START_DATA; ! 200: a2 = FILE_INFO->blocks; ! 201: ! 202: if (filepos > 0) ! 203: { ! 204: if (filepos < a2[0].a_len * 512 - VSTAFS_START_DATA) ! 205: { ! 206: offset = filepos + VSTAFS_START_DATA; ! 207: extent = 0; ! 208: curr_len = a2[0].a_len * 512 - offset - filepos; ! 209: } ! 210: else ! 211: { ! 212: ext_size = a2[0].a_len * 512 - VSTAFS_START_DATA; ! 213: offset = filepos - ext_size; ! 214: extent = 1; ! 215: do ! 216: { ! 217: curr_len -= ext_size; ! 218: offset -= ext_size; ! 219: ext_size = a2[extent+1].a_len * 512; ! 220: } ! 221: while (extent < FILE_INFO->extents && offset>ext_size); ! 222: } ! 223: } ! 224: else ! 225: { ! 226: offset = VSTAFS_START_DATA; ! 227: extent = 0; ! 228: curr_len = a2[0].a_len * 512 - offset; ! 229: } ! 230: ! 231: curr_pos = addr; ! 232: if (curr_len > len) ! 233: curr_len = len; ! 234: ! 235: for (curr_ext2=extent; ! 236: curr_ext2 < FILE_INFO->extents; ! 237: curr_len = a2[curr_ext].a_len * 512, curr_pos += curr_len, curr_ext2++) ! 238: { ! 239: ret += curr_len; ! 240: size -= curr_len; ! 241: if (size < 0) ! 242: { ! 243: ret += size; ! 244: curr_len += size; ! 245: } ! 246: ! 247: devread (a2[curr_ext2].a_start,offset, curr_len, curr_pos); ! 248: offset = 0; ! 249: } ! 250: ! 251: return ret; ! 252: } ! 253: ! 254: #endif /* FSYS_VSTAFS */
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.