wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 1 | /* |
| 2 | * (C) Copyright 2002 |
| 3 | * Stäubli Faverges - <www.staubli.com> |
| 4 | * Pierre AUBERT p.aubert@staubli.com |
| 5 | * |
| 6 | * See file CREDITS for list of people who contributed to this |
| 7 | * project. |
| 8 | * |
| 9 | * This program is free software; you can redistribute it and/or |
| 10 | * modify it under the terms of the GNU General Public License as |
| 11 | * published by the Free Software Foundation; either version 2 of |
| 12 | * the License, or (at your option) any later version. |
| 13 | * |
| 14 | * This program is distributed in the hope that it will be useful, |
| 15 | * but WITHOUT ANY WARRANTY; without even the implied warranty of |
| 16 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
| 17 | * GNU General Public License for more details. |
| 18 | * |
| 19 | * You should have received a copy of the GNU General Public License |
| 20 | * along with this program; if not, write to the Free Software |
| 21 | * Foundation, Inc., 59 Temple Place, Suite 330, Boston, |
| 22 | * MA 02111-1307 USA |
| 23 | */ |
| 24 | |
| 25 | #include <common.h> |
| 26 | #include <config.h> |
| 27 | |
| 28 | #include "dos.h" |
| 29 | #include "fdos.h" |
| 30 | |
Jon Loeliger | 80eb47c | 2007-07-09 17:56:50 -0500 | [diff] [blame] | 31 | #if defined(CONFIG_CMD_FDOS) |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 32 | |
| 33 | #define NB_HEADS 2 |
| 34 | #define NB_TRACKS 80 |
| 35 | #define NB_SECTORS 18 |
| 36 | |
| 37 | |
| 38 | static int lastwhere; |
| 39 | |
| 40 | /*----------------------------------------------------------------------------- |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 41 | * dev_open -- |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 42 | *----------------------------------------------------------------------------- |
| 43 | */ |
| 44 | int dev_open (void) |
| 45 | { |
| 46 | lastwhere = 0; |
| 47 | return (0); |
| 48 | } |
| 49 | |
| 50 | /*----------------------------------------------------------------------------- |
| 51 | * dev_read -- len and where are sectors number |
| 52 | *----------------------------------------------------------------------------- |
| 53 | */ |
| 54 | int dev_read (void *buffer, int where, int len) |
| 55 | { |
| 56 | PRINTF ("dev_read (len = %d, where = %d)\n", len, where); |
| 57 | |
| 58 | /* Si on ne desire pas lire a la position courante, il faut un seek */ |
| 59 | if (where != lastwhere) { |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 60 | if (!fdc_fdos_seek (where)) { |
| 61 | PRINTF ("seek error in dev_read"); |
| 62 | lastwhere = -1; |
| 63 | return (-1); |
| 64 | } |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 65 | } |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 66 | |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 67 | if (!fdc_fdos_read (buffer, len)) { |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 68 | PRINTF ("read error\n"); |
| 69 | lastwhere = -1; |
| 70 | return (-1); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 71 | } |
| 72 | lastwhere = where + len; |
| 73 | return (0); |
| 74 | } |
| 75 | /*----------------------------------------------------------------------------- |
| 76 | * check_dev -- verify the diskette format |
| 77 | *----------------------------------------------------------------------------- |
| 78 | */ |
| 79 | int check_dev (BootSector_t *boot, Fs_t *fs) |
| 80 | { |
| 81 | unsigned int heads, sectors, tracks; |
| 82 | int BootP, Infp0, InfpX, InfTm; |
| 83 | int sect_per_track; |
| 84 | |
| 85 | /* Display Boot header */ |
| 86 | PRINTF ("Jump to boot code 0x%02x 0x%02x 0x%02x\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 87 | boot -> jump [0], boot -> jump [1], boot -> jump[2]); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 88 | PRINTF ("OEM name & version '%*.*s'\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 89 | BANNER_LG, BANNER_LG, boot -> banner ); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 90 | PRINTF ("Bytes per sector hopefully 512 %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 91 | __le16_to_cpu (boot -> secsiz)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 92 | PRINTF ("Cluster size in sectors %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 93 | boot -> clsiz); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 94 | PRINTF ("Number of reserved (boot) sectors %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 95 | __le16_to_cpu (boot -> nrsvsect)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 96 | PRINTF ("Number of FAT tables hopefully 2 %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 97 | boot -> nfat); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 98 | PRINTF ("Number of directory slots %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 99 | __le16_to_cpu (boot -> dirents)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 100 | PRINTF ("Total sectors on disk %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 101 | __le16_to_cpu (boot -> psect)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 102 | PRINTF ("Media descriptor=first byte of FAT %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 103 | boot -> descr); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 104 | PRINTF ("Sectors in FAT %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 105 | __le16_to_cpu (boot -> fatlen)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 106 | PRINTF ("Sectors/track %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 107 | __le16_to_cpu (boot -> nsect)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 108 | PRINTF ("Heads %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 109 | __le16_to_cpu (boot -> nheads)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 110 | PRINTF ("number of hidden sectors %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 111 | __le32_to_cpu (boot -> nhs)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 112 | PRINTF ("big total sectors %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 113 | __le32_to_cpu (boot -> bigsect)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 114 | PRINTF ("physical drive ? %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 115 | boot -> physdrive); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 116 | PRINTF ("reserved %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 117 | boot -> reserved); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 118 | PRINTF ("dos > 4.0 diskette %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 119 | boot -> dos4); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 120 | PRINTF ("serial number %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 121 | __le32_to_cpu (boot -> serial)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 122 | PRINTF ("disk label %*.*s\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 123 | LABEL_LG, LABEL_LG, boot -> label); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 124 | PRINTF ("FAT type %8.8s\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 125 | boot -> fat_type); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 126 | PRINTF ("reserved by 2M %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 127 | boot -> res_2m); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 128 | PRINTF ("2M checksum (not used) %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 129 | boot -> CheckSum); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 130 | PRINTF ("2MF format version %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 131 | boot -> fmt_2mf); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 132 | PRINTF ("1 if write track after format %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 133 | boot -> wt); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 134 | PRINTF ("data transfer rate on track 0 %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 135 | boot -> rate_0); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 136 | PRINTF ("data transfer rate on track<>0 %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 137 | boot -> rate_any); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 138 | PRINTF ("offset to boot program %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 139 | __le16_to_cpu (boot -> BootP)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 140 | PRINTF ("T1: information for track 0 %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 141 | __le16_to_cpu (boot -> Infp0)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 142 | PRINTF ("T2: information for track<>0 %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 143 | __le16_to_cpu (boot -> InfpX)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 144 | PRINTF ("T3: track sectors size table %d\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 145 | __le16_to_cpu (boot -> InfTm)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 146 | PRINTF ("Format date 0x%04x\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 147 | __le16_to_cpu (boot -> DateF)); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 148 | PRINTF ("Format time 0x%04x\n", |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 149 | __le16_to_cpu (boot -> TimeF)); |
| 150 | |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 151 | |
wdenk | cc1e256 | 2003-03-06 13:39:27 +0000 | [diff] [blame] | 152 | /* information is extracted from boot sector */ |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 153 | heads = __le16_to_cpu (boot -> nheads); |
| 154 | sectors = __le16_to_cpu (boot -> nsect); |
| 155 | fs -> tot_sectors = __le32_to_cpu (boot -> bigsect); |
| 156 | if (__le16_to_cpu (boot -> psect) != 0) { |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 157 | fs -> tot_sectors = __le16_to_cpu (boot -> psect); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 158 | } |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 159 | |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 160 | sect_per_track = heads * sectors; |
| 161 | tracks = (fs -> tot_sectors + sect_per_track - 1) / sect_per_track; |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 162 | |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 163 | BootP = __le16_to_cpu (boot -> BootP); |
| 164 | Infp0 = __le16_to_cpu (boot -> Infp0); |
| 165 | InfpX = __le16_to_cpu (boot -> InfpX); |
| 166 | InfTm = __le16_to_cpu (boot -> InfTm); |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 167 | |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 168 | if (boot -> dos4 == EXTENDED_BOOT && |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 169 | strncmp( boot->banner,"2M", 2 ) == 0 && |
| 170 | BootP < SZ_STD_SECTOR && |
| 171 | Infp0 < SZ_STD_SECTOR && |
| 172 | InfpX < SZ_STD_SECTOR && |
| 173 | InfTm < SZ_STD_SECTOR && |
| 174 | BootP >= InfTm + 2 && |
| 175 | InfTm >= InfpX && |
| 176 | InfpX >= Infp0 && |
| 177 | Infp0 >= 76 ) { |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 178 | |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 179 | return (-1); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 180 | } |
| 181 | |
| 182 | if (heads != NB_HEADS || |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 183 | tracks != NB_TRACKS || |
| 184 | sectors != NB_SECTORS || |
| 185 | __le16_to_cpu (boot -> secsiz) != SZ_STD_SECTOR || |
| 186 | fs -> tot_sectors == 0 || |
| 187 | (fs -> tot_sectors % sectors) != 0) { |
| 188 | return (-1); |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 189 | } |
wdenk | 57b2d80 | 2003-06-27 21:31:46 +0000 | [diff] [blame] | 190 | |
wdenk | 591dda5 | 2002-11-18 00:14:45 +0000 | [diff] [blame] | 191 | return (0); |
| 192 | } |
| 193 | |
| 194 | |
| 195 | #endif |