msdos filesystem now works on big-endian machines.
This commit is contained in:
parent
7b734f94ec
commit
7c687a255f
|
@ -13,7 +13,7 @@
|
|||
*
|
||||
* October 1992
|
||||
*
|
||||
* $Id: bpb.h,v 1.1 1993/08/13 11:35:30 cgd Exp $
|
||||
* $Id: bpb.h,v 1.2 1994/03/03 00:51:30 paulus Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
|
@ -57,15 +57,29 @@ struct bpb50 {
|
|||
* and longs are just character arrays of the appropriate length. This is
|
||||
* because the compiler forces shorts and longs to align on word or
|
||||
* halfword boundaries.
|
||||
*
|
||||
* XXX The little-endian code here assumes that the processor can access
|
||||
* 16-bit and 32-bit quantities on byte boundaries. If this is not true,
|
||||
* use the macros for the big-endian case.
|
||||
*/
|
||||
#include <machine/endian.h>
|
||||
#if BYTE_ORDER == LITTLE_ENDIAN
|
||||
#if BYTE_ORDER == LITTLE_ENDIAN /* && can do unaligned accesses */
|
||||
#define getushort(x) *((u_short *)(x))
|
||||
#define getulong(x) *((u_long *)(x))
|
||||
#define putushort(p, v) (*((u_short *)(p)) = (v))
|
||||
#define putulong(p, v) (*((u_long *)(p)) = (v))
|
||||
#else
|
||||
|
||||
#else
|
||||
#define getushort(x) (((u_char *)(x))[0] + (((u_char *)(x))[1] << 8))
|
||||
#define getulong(x) (((u_char *)(x))[0] + (((u_char *)(x))[1] << 8) \
|
||||
+ (((u_char *)(x))[2] << 16) \
|
||||
+ (((u_char *)(x))[3] << 24))
|
||||
#define putushort(p, v) (((u_char *)(p))[0] = (v), \
|
||||
((u_char *)(p))[1] = (v) >> 8)
|
||||
#define putulong(p, v) (((u_char *)(p))[0] = (v), \
|
||||
((u_char *)(p))[1] = (v) >> 8, \
|
||||
((u_char *)(p))[2] = (v) >> 16,\
|
||||
((u_char *)(p))[3] = (v) >> 24)
|
||||
#endif
|
||||
|
||||
/*
|
||||
|
|
|
@ -13,16 +13,16 @@
|
|||
*
|
||||
* October 1992
|
||||
*
|
||||
* $Id: denode.h,v 1.2 1993/09/07 15:41:31 ws Exp $
|
||||
* $Id: denode.h,v 1.3 1994/03/03 00:51:31 paulus Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
* This is the pc filesystem specific portion of the vnode structure. To
|
||||
* describe a file uniquely the de_dirclust, de_diroffset, and
|
||||
* de_de.deStartCluster fields are used. de_dirclust contains the cluster
|
||||
* de_StartCluster fields are used. de_dirclust contains the cluster
|
||||
* number of the directory cluster containing the entry for a file or
|
||||
* directory. de_diroffset is the index into the cluster for the entry
|
||||
* describing a file or directory. de_de.deStartCluster is the number of
|
||||
* describing a file or directory. de_StartCluster is the number of
|
||||
* the first cluster of the file or directory. Now to describe the quirks
|
||||
* of the pc filesystem. - Clusters 0 and 1 are reserved. - The first
|
||||
* allocatable cluster is 2. - The root directory is of fixed size and all
|
||||
|
@ -105,7 +105,14 @@ struct denode {
|
|||
struct lockf *de_lockf; /* byte level lock list */
|
||||
long de_spare0; /* current lock holder */
|
||||
long de_spare1; /* lock wanter */
|
||||
struct direntry de_de; /* the actual directory entry */
|
||||
/* the next two fields must be contiguous in memory... */
|
||||
u_char de_Name[8]; /* name, from directory entry */
|
||||
u_char de_Extension[3]; /* extension, from directory entry */
|
||||
u_char de_Attributes; /* attributes, from directory entry */
|
||||
u_short de_Time; /* creation time */
|
||||
u_short de_Date; /* creation date */
|
||||
u_short de_StartCluster; /* starting cluster of file */
|
||||
u_long de_FileSize; /* size of file in bytes */
|
||||
struct fatcache de_fc[FC_SIZE]; /* fat cache */
|
||||
};
|
||||
|
||||
|
@ -122,17 +129,26 @@ struct denode {
|
|||
#define DEMOD 0x0080 /* denode wants to be written back to disk */
|
||||
|
||||
/*
|
||||
* Shorthand macros used to reference fields in the direntry contained in
|
||||
* the denode structure.
|
||||
* Transfer directory entries between internal and external form.
|
||||
* dep is a struct denode * (internal form),
|
||||
* dp is a struct direntry * (external form).
|
||||
*/
|
||||
#define de_Name de_de.deName
|
||||
#define de_Extension de_de.deExtension
|
||||
#define de_Attributes de_de.deAttributes
|
||||
#define de_Reserved de_de.deReserved
|
||||
#define de_Time de_de.deTime
|
||||
#define de_Date de_de.deDate
|
||||
#define de_StartCluster de_de.deStartCluster
|
||||
#define de_FileSize de_de.deFileSize
|
||||
#define DE_INTERNALIZE(dep, dp) \
|
||||
(bcopy((dp)->deName, (dep)->de_Name, 11), \
|
||||
(dep)->de_Attributes = (dp)->deAttributes, \
|
||||
(dep)->de_Time = getushort((dp)->deTime), \
|
||||
(dep)->de_Date = getushort((dp)->deDate), \
|
||||
(dep)->de_StartCluster = getushort((dp)->deStartCluster), \
|
||||
(dep)->de_FileSize = getulong((dp)->deFileSize))
|
||||
|
||||
#define DE_EXTERNALIZE(dp, dep) \
|
||||
(bcopy((dep)->de_Name, (dp)->deName, 11), \
|
||||
(dp)->deAttributes = (dep)->de_Attributes, \
|
||||
putushort((dp)->deTime, (dep)->de_Time), \
|
||||
putushort((dp)->deDate, (dep)->de_Date), \
|
||||
putushort((dp)->deStartCluster, (dep)->de_StartCluster), \
|
||||
putulong((dp)->deFileSize, (dep)->de_FileSize))
|
||||
|
||||
#define de_forw de_chain[0]
|
||||
#define de_back de_chain[1]
|
||||
|
||||
|
@ -151,8 +167,7 @@ struct denode {
|
|||
#define DETIMES(dep, t) \
|
||||
if (dep->de_flag & DEUPD) { \
|
||||
(dep)->de_flag |= DEMOD; \
|
||||
unix2dostime(t, (union dosdate *)&dep->de_Date, \
|
||||
(union dostime *)&dep->de_Time); \
|
||||
unix2dostime(t, &dep->de_Date, &dep->de_Time); \
|
||||
(dep)->de_flag &= ~DEUPD; \
|
||||
}
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
*
|
||||
* October 1992
|
||||
*
|
||||
* $Id: direntry.h,v 1.1 1993/08/13 11:35:32 cgd Exp $
|
||||
* $Id: direntry.h,v 1.2 1994/03/03 00:51:32 paulus Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
|
@ -33,44 +33,36 @@ struct direntry {
|
|||
#define ATTR_VOLUME 0x08 /* entry is a volume label */
|
||||
#define ATTR_DIRECTORY 0x10 /* entry is a directory name */
|
||||
#define ATTR_ARCHIVE 0x20 /* file is new or modified */
|
||||
char deReserved[10]; /* reserved */
|
||||
u_short deTime; /* create/last update time */
|
||||
u_short deDate; /* create/last update date */
|
||||
u_short deStartCluster; /* starting cluster of file */
|
||||
u_long deFileSize; /* size of file in bytes */
|
||||
u_char deReserved[10]; /* reserved */
|
||||
u_char deTime[2]; /* create/last update time */
|
||||
u_char deDate[2]; /* create/last update date */
|
||||
u_char deStartCluster[2]; /* starting cluster of file */
|
||||
u_char deFileSize[4]; /* size of file in bytes */
|
||||
};
|
||||
|
||||
/*
|
||||
* This is the format of the contents of the deTime field in the direntry
|
||||
* structure.
|
||||
* We don't use bitfields because we don't know how compilers for
|
||||
* arbitrary machines will lay them out.
|
||||
*/
|
||||
struct DOStime {
|
||||
u_short
|
||||
dt_2seconds:5, /* seconds divided by 2 */
|
||||
dt_minutes:6, /* minutes */
|
||||
dt_hours:5; /* hours */
|
||||
};
|
||||
#define DT_2SECONDS_MASK 0x1F /* seconds divided by 2 */
|
||||
#define DT_2SECONDS_SHIFT 0
|
||||
#define DT_MINUTES_MASK 0x7E0 /* minutes */
|
||||
#define DT_MINUTES_SHIFT 5
|
||||
#define DT_HOURS_MASK 0xF800 /* hours */
|
||||
#define DT_HOURS_SHIFT 11
|
||||
|
||||
/*
|
||||
* This is the format of the contents of the deDate field in the direntry
|
||||
* structure.
|
||||
*/
|
||||
struct DOSdate {
|
||||
u_short
|
||||
dd_day:5, /* day of month */
|
||||
dd_month:4, /* month */
|
||||
dd_year:7; /* years since 1980 */
|
||||
};
|
||||
|
||||
union dostime {
|
||||
struct DOStime dts;
|
||||
u_short dti;
|
||||
};
|
||||
|
||||
union dosdate {
|
||||
struct DOSdate dds;
|
||||
u_short ddi;
|
||||
};
|
||||
#define DD_DAY_MASK 0x1F /* day of month */
|
||||
#define DD_DAY_SHIFT 0
|
||||
#define DD_MONTH_MASK 0x1E0 /* month */
|
||||
#define DD_MONTH_SHIFT 5
|
||||
#define DD_YEAR_MASK 0xFE00 /* year - 1980 */
|
||||
#define DD_YEAR_SHIFT 9
|
||||
|
||||
/*
|
||||
* The following defines are used to rename fields in the ufs_specific
|
||||
|
@ -82,8 +74,8 @@ union dosdate {
|
|||
#define msdosfs_cluster ufs_ino
|
||||
|
||||
#if defined(KERNEL)
|
||||
void unix2dostime __P((struct timeval * tvp, union dosdate * ddp, union dostime * dtp));
|
||||
void dos2unixtime __P((union dosdate * ddp, union dostime * dtp, struct timeval * tvp));
|
||||
void unix2dostime __P((struct timeval * tvp, u_short * ddp, u_short * dtp));
|
||||
void dos2unixtime __P((u_short dd, u_short dt, struct timeval * tvp));
|
||||
int dos2unixfn __P((u_char dn[11], u_char * un));
|
||||
void unix2dosfn __P((u_char * un, u_char dn[11], int unlen));
|
||||
#endif /* defined(KERNEL) */
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
*
|
||||
* October 1992
|
||||
*
|
||||
* $Id: msdosfs_conv.c,v 1.2 1993/12/18 00:50:38 mycroft Exp $
|
||||
* $Id: msdosfs_conv.c,v 1.3 1994/03/03 00:51:33 paulus Exp $
|
||||
*/
|
||||
|
||||
/*
|
||||
|
@ -50,8 +50,8 @@ u_short leapyear[] = {
|
|||
*/
|
||||
u_long lasttime;
|
||||
u_long lastday;
|
||||
union dosdate lastddate;
|
||||
union dostime lastdtime;
|
||||
u_short lastddate;
|
||||
u_short lastdtime;
|
||||
|
||||
/*
|
||||
* Convert the unix version of time to dos's idea of time to be used in
|
||||
|
@ -60,9 +60,10 @@ union dostime lastdtime;
|
|||
void
|
||||
unix2dostime(tvp, ddp, dtp)
|
||||
struct timeval *tvp;
|
||||
union dosdate *ddp;
|
||||
union dostime *dtp;
|
||||
u_short *ddp;
|
||||
u_short *dtp;
|
||||
{
|
||||
u_long t;
|
||||
u_long days;
|
||||
u_long inc;
|
||||
u_long year;
|
||||
|
@ -73,19 +74,20 @@ unix2dostime(tvp, ddp, dtp)
|
|||
* If the time from the last conversion is the same as now, then
|
||||
* skip the computations and use the saved result.
|
||||
*/
|
||||
if (lasttime != tvp->tv_sec) {
|
||||
lasttime = tvp->tv_sec - (tz.tz_minuteswest * 60)
|
||||
/* +- daylight savings time correction */ ;
|
||||
lastdtime.dts.dt_2seconds = (lasttime % 60) >> 1;
|
||||
lastdtime.dts.dt_minutes = (lasttime / 60) % 60;
|
||||
lastdtime.dts.dt_hours = (lasttime / (60 * 60)) % 24;
|
||||
t = tvp->tv_sec - (tz.tz_minuteswest * 60)
|
||||
/* +- daylight savings time correction */ ;
|
||||
if (lasttime != t) {
|
||||
lasttime = t;
|
||||
lastdtime = (((t % 60) >> 1) << DT_2SECONDS_SHIFT)
|
||||
+ (((t / 60) % 60) << DT_MINUTES_SHIFT)
|
||||
+ (((t / 3600) % 24) << DT_HOURS_SHIFT);
|
||||
|
||||
/*
|
||||
* If the number of days since 1970 is the same as the last
|
||||
* time we did the computation then skip all this leap year
|
||||
* and month stuff.
|
||||
*/
|
||||
days = lasttime / (24 * 60 * 60);
|
||||
days = t / (24 * 60 * 60);
|
||||
if (days != lastday) {
|
||||
lastday = days;
|
||||
for (year = 1970;; year++) {
|
||||
|
@ -100,19 +102,20 @@ unix2dostime(tvp, ddp, dtp)
|
|||
break;
|
||||
days -= months[month];
|
||||
}
|
||||
lastddate.dds.dd_day = days + 1;
|
||||
lastddate.dds.dd_month = month + 1;
|
||||
lastddate = ((days + 1) << DD_DAY_SHIFT)
|
||||
+ ((month + 1) << DD_MONTH_SHIFT);
|
||||
/*
|
||||
* Remember dos's idea of time is relative to 1980.
|
||||
* unix's is relative to 1970. If somehow we get a
|
||||
* time before 1980 then don't give totally crazy
|
||||
* results.
|
||||
*/
|
||||
lastddate.dds.dd_year = year < 1980 ? 0 : year - 1980;
|
||||
if (year > 1980)
|
||||
lastddate += (year - 1980) << DD_YEAR_SHIFT;
|
||||
}
|
||||
}
|
||||
dtp->dti = lastdtime.dti;
|
||||
ddp->ddi = lastddate.ddi;
|
||||
*dtp = lastdtime;
|
||||
*ddp = lastddate;
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -121,7 +124,7 @@ unix2dostime(tvp, ddp, dtp)
|
|||
*/
|
||||
#define SECONDSTO1980 (((8 * 365) + (2 * 366)) * (24 * 60 * 60))
|
||||
|
||||
union dosdate lastdosdate;
|
||||
u_short lastdosdate;
|
||||
u_long lastseconds;
|
||||
|
||||
/*
|
||||
|
@ -130,44 +133,46 @@ u_long lastseconds;
|
|||
* not be too efficient.
|
||||
*/
|
||||
void
|
||||
dos2unixtime(ddp, dtp, tvp)
|
||||
union dosdate *ddp;
|
||||
union dostime *dtp;
|
||||
dos2unixtime(dd, dt, tvp)
|
||||
u_short dd;
|
||||
u_short dt;
|
||||
struct timeval *tvp;
|
||||
{
|
||||
u_long seconds;
|
||||
u_long month;
|
||||
u_long yr;
|
||||
u_long m, month;
|
||||
u_long y, year;
|
||||
u_long days;
|
||||
u_short *months;
|
||||
|
||||
seconds = (dtp->dts.dt_2seconds << 1) +
|
||||
(dtp->dts.dt_minutes * 60) +
|
||||
(dtp->dts.dt_hours * 60 * 60);
|
||||
seconds = ((dt & DT_2SECONDS_MASK) >> DT_2SECONDS_SHIFT)
|
||||
+ ((dt & DT_MINUTES_MASK) >> DT_MINUTES_SHIFT) * 60
|
||||
+ ((dt & DT_HOURS_MASK) >> DT_HOURS_SHIFT) * 3600;
|
||||
/*
|
||||
* If the year, month, and day from the last conversion are the
|
||||
* same then use the saved value.
|
||||
*/
|
||||
if (lastdosdate.ddi != ddp->ddi) {
|
||||
lastdosdate.ddi = ddp->ddi;
|
||||
if (lastdosdate != dd) {
|
||||
lastdosdate = dd;
|
||||
days = 0;
|
||||
for (yr = 0; yr < ddp->dds.dd_year; yr++) {
|
||||
days += yr & 0x03 ? 365 : 366;
|
||||
year = (dd & DD_YEAR_MASK) >> DD_YEAR_SHIFT;
|
||||
for (y = 0; y < year; y++) {
|
||||
days += y & 0x03 ? 365 : 366;
|
||||
}
|
||||
months = yr & 0x03 ? regyear : leapyear;
|
||||
months = year & 0x03 ? regyear : leapyear;
|
||||
/*
|
||||
* Prevent going from 0 to 0xffffffff in the following
|
||||
* loop.
|
||||
*/
|
||||
if (ddp->dds.dd_month == 0) {
|
||||
month = (dd & DD_MONTH_MASK) >> DD_MONTH_SHIFT;
|
||||
if (month == 0) {
|
||||
printf("dos2unixtime(): month value out of range (%d)\n",
|
||||
ddp->dds.dd_month);
|
||||
ddp->dds.dd_month = 1;
|
||||
month);
|
||||
month = 1;
|
||||
}
|
||||
for (month = 0; month < ddp->dds.dd_month - 1; month++) {
|
||||
days += months[month];
|
||||
for (m = 0; m < month - 1; m++) {
|
||||
days += months[m];
|
||||
}
|
||||
days += ddp->dds.dd_day - 1;
|
||||
days += ((dd & DD_DAY_MASK) >> DD_DAY_SHIFT) - 1;
|
||||
lastseconds = (days * 24 * 60 * 60) + SECONDSTO1980;
|
||||
}
|
||||
tvp->tv_sec = seconds + lastseconds + (tz.tz_minuteswest * 60)
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
*
|
||||
* October 1992
|
||||
*
|
||||
* $Id: msdosfs_denode.c,v 1.2 1993/12/18 00:50:51 mycroft Exp $
|
||||
* $Id: msdosfs_denode.c,v 1.3 1994/03/03 00:51:34 paulus Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
|
@ -96,7 +96,7 @@ deget(pmp, dirclust, diroffset, direntptr, depp)
|
|||
* canonical form
|
||||
*/
|
||||
if (direntptr && (direntptr->deAttributes & ATTR_DIRECTORY)) {
|
||||
dirclust = direntptr->deStartCluster;
|
||||
dirclust = getushort(direntptr->deStartCluster);
|
||||
if (dirclust == MSDOSFSROOT)
|
||||
diroffset = MSDOSFSROOT_OFS;
|
||||
else
|
||||
|
@ -185,7 +185,8 @@ loop:
|
|||
* denode
|
||||
*/
|
||||
ldep->de_Time = 0x0000; /* 00:00:00 */
|
||||
ldep->de_Date = (0 << 9) | (1 << 5) | (1 << 0);
|
||||
ldep->de_Date = (0 << DD_YEAR_SHIFT) | (1 << DD_MONTH_SHIFT)
|
||||
| (1 << DD_DAY_SHIFT);
|
||||
/* Jan 1, 1980 */
|
||||
/* leave the other fields as garbage */
|
||||
}
|
||||
|
@ -193,11 +194,11 @@ loop:
|
|||
bp = NULL;
|
||||
if (!direntptr) {
|
||||
error = readep(pmp, dirclust, diroffset, &bp,
|
||||
&direntptr);
|
||||
&direntptr);
|
||||
if (error)
|
||||
return error;
|
||||
}
|
||||
ldep->de_de = *direntptr;
|
||||
DE_INTERNALIZE(ldep, direntptr);
|
||||
if (bp)
|
||||
brelse(bp);
|
||||
}
|
||||
|
@ -291,15 +292,14 @@ deupdat(dep, tp, waitfor)
|
|||
/*
|
||||
* Put the passed in time into the directory entry.
|
||||
*/
|
||||
unix2dostime(&time, (union dosdate *) & dep->de_Date,
|
||||
(union dostime *) & dep->de_Time);
|
||||
unix2dostime(&time, &dep->de_Date, &dep->de_Time);
|
||||
dep->de_flag &= ~DEUPD;
|
||||
|
||||
/*
|
||||
* Copy the directory entry out of the denode into the cluster it
|
||||
* came from.
|
||||
*/
|
||||
*dirp = dep->de_de; /* structure copy */
|
||||
DE_EXTERNALIZE(dirp, dep);
|
||||
|
||||
/*
|
||||
* Write the cluster back to disk. If they asked for us to wait
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
*
|
||||
* October 1992
|
||||
*
|
||||
* $Id: msdosfs_lookup.c,v 1.7 1994/02/14 21:47:57 mycroft Exp $
|
||||
* $Id: msdosfs_lookup.c,v 1.8 1994/03/03 00:51:35 paulus Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
|
@ -106,10 +106,10 @@ msdosfs_lookup(vdp, ndp, p)
|
|||
|
||||
if (error == ENOENT)
|
||||
return error;
|
||||
#ifdef DIAGNOSTIC
|
||||
#ifdef PARANOID
|
||||
if (vdp == ndp->ni_rootdir && ndp->ni_isdotdot)
|
||||
panic("msdosfs_lookup: .. thru root");
|
||||
#endif
|
||||
#endif /* PARANOID */
|
||||
pdp = dp;
|
||||
vdp = ndp->ni_vp;
|
||||
dp = VTODE(vdp);
|
||||
|
@ -160,7 +160,7 @@ msdosfs_lookup(vdp, ndp, p)
|
|||
#if defined(MSDOSFSDEBUG)
|
||||
printf("msdosfs_lookup(): looking for . or .. in root directory\n");
|
||||
#endif /* defined(MSDOSFSDEBUG) */
|
||||
cluster == MSDOSFSROOT;
|
||||
cluster = MSDOSFSROOT;
|
||||
diroff = MSDOSFSROOT_OFS;
|
||||
goto foundroot;
|
||||
}
|
||||
|
@ -314,7 +314,7 @@ found: ;
|
|||
* this point.
|
||||
*/
|
||||
isadir = dep->deAttributes & ATTR_DIRECTORY;
|
||||
scn = dep->deStartCluster;
|
||||
scn = getushort(dep->deStartCluster);
|
||||
|
||||
foundroot:;
|
||||
/*
|
||||
|
@ -482,7 +482,8 @@ createde(dep, ndp, depp)
|
|||
if (error)
|
||||
return error;
|
||||
}
|
||||
*ndep = dep->de_de;
|
||||
DE_EXTERNALIZE(ndep, dep);
|
||||
|
||||
/*
|
||||
* If they want us to return with the denode gotten.
|
||||
*/
|
||||
|
@ -672,15 +673,16 @@ doscheckpath(source, target)
|
|||
error = ENOTDIR;
|
||||
break;
|
||||
}
|
||||
if (ep->deStartCluster == source->de_StartCluster) {
|
||||
scn = getushort(ep->deStartCluster);
|
||||
if (scn == source->de_StartCluster) {
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
if (ep->deStartCluster == MSDOSFSROOT)
|
||||
if (scn == MSDOSFSROOT)
|
||||
break;
|
||||
deput(dep);
|
||||
/* NOTE: deget() clears dep on error */
|
||||
error = deget(pmp, ep->deStartCluster, 0, ep, &dep);
|
||||
error = deget(pmp, scn, 0, ep, &dep);
|
||||
brelse(bp);
|
||||
bp = NULL;
|
||||
if (error)
|
||||
|
|
|
@ -67,7 +67,6 @@ msdosfs_create(ndp, vap, p)
|
|||
struct proc *p;
|
||||
{
|
||||
struct denode ndirent;
|
||||
struct direntry *ndirp = &ndirent.de_de;
|
||||
struct denode *dep;
|
||||
struct denode *pdep = VTODE(ndp->ni_dvp);
|
||||
int error;
|
||||
|
@ -83,12 +82,11 @@ msdosfs_create(ndp, vap, p)
|
|||
* readonly.
|
||||
*/
|
||||
bzero(&ndirent, sizeof(ndirent));
|
||||
unix2dostime(&time, (union dosdate *) & ndirp->deDate,
|
||||
(union dostime *) & ndirp->deTime);
|
||||
unix2dosfn((u_char *) ndp->ni_ptr, ndirp->deName, ndp->ni_namelen);
|
||||
ndirp->deAttributes = (vap->va_mode & VWRITE) ? 0 : ATTR_READONLY;
|
||||
ndirp->deStartCluster = 0;
|
||||
ndirp->deFileSize = 0;
|
||||
unix2dostime(&time, &ndirent.de_Date, &ndirent.de_Time);
|
||||
unix2dosfn((u_char *) ndp->ni_ptr, ndirent.de_Name, ndp->ni_namelen);
|
||||
ndirent.de_Attributes = (vap->va_mode & VWRITE) ? 0 : ATTR_READONLY;
|
||||
ndirent.de_StartCluster = 0;
|
||||
ndirent.de_FileSize = 0;
|
||||
ndirent.de_pmp = pdep->de_pmp;
|
||||
ndirent.de_dev = pdep->de_dev;
|
||||
ndirent.de_devvp = pdep->de_devvp;
|
||||
|
@ -226,8 +224,7 @@ msdosfs_getattr(vp, vap, cred, p)
|
|||
vap->va_rdev = 0;
|
||||
vap->va_size = dep->de_FileSize;
|
||||
vap->va_size_rsv = 0;
|
||||
dos2unixtime((union dosdate *) & dep->de_Date,
|
||||
(union dostime *) & dep->de_Time, &vap->va_atime);
|
||||
dos2unixtime(dep->de_Date, dep->de_Time, &vap->va_atime);
|
||||
vap->va_atime.tv_usec = 0;
|
||||
vap->va_mtime.tv_sec = vap->va_atime.tv_sec;
|
||||
vap->va_mtime.tv_usec = 0;
|
||||
|
@ -590,6 +587,7 @@ msdosfs_ioctl(vp, com, data, fflag, cred, p)
|
|||
struct vnode *vp;
|
||||
int com;
|
||||
caddr_t data;
|
||||
int fflag;
|
||||
struct ucred *cred;
|
||||
struct proc *p;
|
||||
{
|
||||
|
@ -1031,7 +1029,7 @@ msdosfs_rename(fndp, tndp, p)
|
|||
goto bad;
|
||||
}
|
||||
dotdotp = (struct direntry *) bp->b_un.b_addr + 1;
|
||||
dotdotp->deStartCluster = tddep->de_StartCluster;
|
||||
putushort(dotdotp->deStartCluster, tddep->de_StartCluster);
|
||||
error = bwrite(bp);
|
||||
DEUNLOCK(fdep);
|
||||
if (error) {
|
||||
|
@ -1060,15 +1058,15 @@ struct {
|
|||
". ", " ", /* the . entry */
|
||||
ATTR_DIRECTORY, /* file attribute */
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* resevered */
|
||||
1234, 1234, /* time and date */
|
||||
0, /* startcluster */
|
||||
0, /* filesize */
|
||||
210, 4, 210, 4, /* time and date */
|
||||
0, 0, /* startcluster */
|
||||
0, 0, 0, 0, /* filesize */
|
||||
".. ", " ", /* the .. entry */
|
||||
ATTR_DIRECTORY, /* file attribute */
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* resevered */
|
||||
1234, 1234, /* time and date */
|
||||
0, /* startcluster */
|
||||
0, /* filesize */
|
||||
4, 210, 4, 210, /* time and date */
|
||||
0, 0, /* startcluster */
|
||||
0, 0, 0, 0, /* filesize */
|
||||
};
|
||||
|
||||
int
|
||||
|
@ -1087,6 +1085,7 @@ msdosfs_mkdir(ndp, vap, p)
|
|||
struct denode ndirent;
|
||||
struct msdosfsmount *pmp;
|
||||
struct buf *bp;
|
||||
u_short dDate, dTime;
|
||||
|
||||
pvp = ndp->ni_dvp;
|
||||
pdep = VTODE(pvp);
|
||||
|
@ -1123,13 +1122,14 @@ msdosfs_mkdir(ndp, vap, p)
|
|||
bzero(bp->b_un.b_addr, pmp->pm_bpcluster);
|
||||
bcopy(&dosdirtemplate, bp->b_un.b_addr, sizeof dosdirtemplate);
|
||||
denp = (struct direntry *) bp->b_un.b_addr;
|
||||
denp->deStartCluster = newcluster;
|
||||
unix2dostime(&time, (union dosdate *) & denp->deDate,
|
||||
(union dostime *) & denp->deTime);
|
||||
putushort(denp->deStartCluster, newcluster);
|
||||
unix2dostime(&time, &dDate, &dTime);
|
||||
putushort(denp->deDate, dDate);
|
||||
putushort(denp->deTime, dTime);
|
||||
denp++;
|
||||
denp->deStartCluster = pdep->de_StartCluster;
|
||||
unix2dostime(&time, (union dosdate *) & denp->deDate,
|
||||
(union dostime *) & denp->deTime);
|
||||
putushort(denp->deStartCluster, pdep->de_StartCluster);
|
||||
putushort(denp->deDate, dDate);
|
||||
putushort(denp->deTime, dTime);
|
||||
if (error = bwrite(bp)) {
|
||||
clusterfree(pmp, newcluster, NULL);
|
||||
free(ndp->ni_pnbuf, M_NAMEI);
|
||||
|
@ -1145,8 +1145,7 @@ msdosfs_mkdir(ndp, vap, p)
|
|||
ndep = &ndirent;
|
||||
bzero(ndep, sizeof(*ndep));
|
||||
unix2dosfn((u_char *) ndp->ni_ptr, ndep->de_Name, ndp->ni_namelen);
|
||||
unix2dostime(&time, (union dosdate *) & ndep->de_Date,
|
||||
(union dostime *) & ndep->de_Time);
|
||||
unix2dostime(&time, &ndep->de_Date, &ndep->de_Time);
|
||||
ndep->de_StartCluster = newcluster;
|
||||
ndep->de_Attributes = ATTR_DIRECTORY;
|
||||
ndep->de_pmp = pmp; /* createde() needs this */
|
||||
|
@ -1435,7 +1434,8 @@ msdosfs_readdir(vp, uio, cred, eofflagp, cookies, ncookies)
|
|||
*/
|
||||
if (dentp->deAttributes & ATTR_DIRECTORY) {
|
||||
/* if this is the root directory */
|
||||
if ((fileno = dentp->deStartCluster) == MSDOSFSROOT)
|
||||
fileno = getushort(dentp->deStartCluster);
|
||||
if (fileno == MSDOSFSROOT)
|
||||
fileno = 1;
|
||||
}
|
||||
else {
|
||||
|
|
Loading…
Reference in New Issue