Go to the documentation of this file.00001 
00002 
00003 
00004 
00005 
00006 
00007 
00008 
00009 
00010 
00011 
00012 
00013 
00014 
00015 
00016 
00017 
00018 
00019 
00020 
00021 
00022 
00023 
00024 
00025 
00026 
00027 
00028 
00029 
00030 
00031 
00032 
00061 #include <errno.h>
00062 
00063 #include <fs/phatfs.h>
00064 #include <fs/phatvol.h>
00065 #include <fs/phatio.h>
00066 
00071 
00083 static void PhatTableLoc(PHATVOL * vol, uint32_t clust, int tabnum, uint32_t * sect, uint32_t * pos)
00084 {
00085     uint32_t tabpos = clust + (clust / 2);
00086 
00087     *sect = vol->vol_tab_sect[tabnum] + tabpos / vol->vol_sectsz;
00088     *pos = tabpos % vol->vol_sectsz;
00089 }
00090 
00100 int Phat12GetClusterLink(NUTDEVICE * dev, uint32_t clust, uint32_t * link)
00101 {
00102     uint32_t sect;
00103     uint32_t pos;
00104     int sbn;
00105     PHATVOL *vol = (PHATVOL *) dev->dev_dcb;
00106 
00107     
00108     if (clust >= (PHATEOC & PHAT12CMASK)) {
00109         return -1;
00110     }
00111 
00112     
00113     PhatTableLoc(vol, clust, 0, §, &pos);
00114     if ((sbn = PhatSectorLoad(dev, sect)) < 0) {
00115         return -1;
00116     }
00117 
00118     
00119     *link = vol->vol_buf[sbn].sect_data[pos++];
00120     if (pos >= vol->vol_sectsz) {
00121         if ((sbn = PhatSectorLoad(dev, sect + 1)) < 0) {
00122             return -1;
00123         }
00124         pos = 0;
00125     }
00126     *link += (uint32_t)(vol->vol_buf[sbn].sect_data[pos]) << 8;
00127 
00128     
00129     if (clust & 1) {
00130         *link >>= 4;
00131     }
00132     *link &= PHAT12CMASK;
00133 
00134     return 0;
00135 }
00136 
00146 int Phat12SetClusterLink(NUTDEVICE * dev, uint32_t clust, uint32_t link)
00147 {
00148     int tabnum;
00149     uint32_t sect;
00150     uint32_t pos;
00151     uint32_t tval;
00152     int sbn;
00153     PHATVOL *vol = (PHATVOL *) dev->dev_dcb;
00154 
00155     for (tabnum = 0; tabnum < 2 && vol->vol_tab_sect[tabnum]; tabnum++) {
00156 
00157         
00158         PhatTableLoc(vol, clust, tabnum, §, &pos);
00159         if ((sbn = PhatSectorLoad(dev, sect)) < 0) {
00160             return -1;
00161         }
00162 
00163         
00164 
00165         tval = vol->vol_buf[sbn].sect_data[pos];
00166         if (pos + 1 < vol->vol_sectsz) {
00167             tval += (uint32_t)(vol->vol_buf[sbn].sect_data[pos + 1]) << 8;
00168         } else {
00169             if ((sbn = PhatSectorLoad(dev, sect + 1)) < 0) {
00170                 return -1;
00171             }
00172             tval += (uint32_t)(vol->vol_buf[sbn].sect_data[0]) << 8;
00173         }
00174 
00175         link &= PHAT12CMASK;
00176         if (clust & 1) {
00177             tval &= 0x000F;
00178             link <<= 4;
00179         } else {
00180             tval &= 0xF000;
00181         }
00182         tval |= link;
00183 
00184         
00185         if (pos + 1 < vol->vol_sectsz) {
00186             vol->vol_buf[sbn].sect_data[pos + 1] = (uint8_t) (tval >> 8);
00187         } else {
00188             vol->vol_buf[sbn].sect_data[0] = (uint8_t) (tval >> 8);
00189             vol->vol_buf[sbn].sect_dirty = 1;
00190             if ((sbn = PhatSectorLoad(dev, sect)) < 0) {
00191                 return -1;
00192             }
00193         }
00194         vol->vol_buf[sbn].sect_data[pos] = (uint8_t) tval;
00195         vol->vol_buf[sbn].sect_dirty = 1;
00196     }
00197 
00198     return 0;
00199 }
00200 
00209 int Phat12ReleaseChain(NUTDEVICE * dev, uint32_t first)
00210 {
00211     uint32_t next;
00212     PHATVOL *vol = (PHATVOL *) dev->dev_dcb;
00213 
00214     while (first < (PHATEOC & PHAT12CMASK)) {
00215         if (Phat12GetClusterLink(dev, first, &next)) {
00216             
00217             return -1;
00218         }
00219         if (next < 2) {
00220             
00221             break;
00222         }
00223         if (Phat12SetClusterLink(dev, first, 0)) {
00224             
00225             return -1;
00226         }
00227         vol->vol_numfree++;
00228         first = next;
00229     }
00230     return 0;
00231 }
00232