home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
OS/2 Shareware BBS: 6 File
/
06-File.zip
/
ramfs102.zip
/
src
/
util.c
< prev
next >
Wrap
C/C++ Source or Header
|
2002-09-28
|
8KB
|
336 lines
#include "includes.h"
#include <stdarg.h>
#include <stdio.h>
#include <dos.h>
#define MIN(a,b) ((a) < (b) ? (a) : (b))
#ifndef MK_FP
#define MK_FP(seg,ofs) ((void FAR *)(((unsigned long)seg<<16)+(unsigned long)ofs))
#endif
PFN near DevHlp;
PGINFOSEG near pGiseg;
void _cdecl abort (void) {}
void _cdecl _RealCvtVector (void) {}
void _cdecl _ScanTodVector (void) {}
char _cdecl _cvtfak = 0;
unsigned char _cdecl inportb( unsigned __portid );
void _cdecl outportb( unsigned __portid, unsigned char __value );
/* static */
volatile char InRamfs = FALSE;
#ifdef DEBUG
char debugging = TRUE;
int _cdecl debug_printf (const char _ds *format, ...)
{
va_list args;
char buf [256];
int len;
int i;
if (!debugging)
return 0;
va_start (args, format);
len = vsprintf (buf, format, args);
for (i=0; i<len; i++)
{
while (!(inportb (0x2FD) & 0x20))
;
outportb (0x2F8, buf[i]);
}
va_end (args);
return len;
}
#endif
ULONG UtilGetDateTime (void)
{
USHORT dateNow;
USHORT timeNow;
do
{
dateNow = ((pGiseg->year-1980) << 9) |
(pGiseg->month << 5) |
(pGiseg->day << 0);
timeNow = (pGiseg->hour << 11) |
(pGiseg->minutes << 5) |
(pGiseg->seconds >> 1);
}
while
(
dateNow != (((pGiseg->year-1980) << 9) |
(pGiseg->month << 5) |
(pGiseg->day << 0))
||
timeNow != ((pGiseg->hour << 11) |
(pGiseg->minutes << 5) |
(pGiseg->seconds >> 1))
);
return dateNow + ((ULONG)timeNow << 16);
}
/* static */
int UtilScanDir (FLAT flatBlkDir, FLAT _ss *pflatEntry, PDIRENTRY pEntry,
char *pachName, int cbName)
{
BLOCK BlkDir;
FLAT flatEnd;
char szUpName[256];
char szUpCurName[256];
int cbCurName;
int rc;
memcpy (szUpName, pachName, cbName);
szUpName[cbName] = '\0';
FSH_UPPERCASE (szUpName, 256, szUpName);
VMReadBlk (&BlkDir, flatBlkDir);
*pflatEntry = BlkDir.flatAddr + DIR_DOTSSIZE;
flatEnd = BlkDir.flatAddr + BlkDir.cbSize;
while (*pflatEntry < flatEnd)
{
cbCurName = VMReadUChar (*pflatEntry);
VMRead (pEntry, *pflatEntry, sizeof(DIRENTRY)-sizeof(pEntry->achName) + cbCurName);
pEntry->achName[cbCurName] = '\0';
FSH_UPPERCASE (pEntry->achName, 256, szUpCurName);
rc = memcmp (szUpName, szUpCurName, MIN(cbName,cbCurName));
if (!rc && cbName == cbCurName)
return NO_ERROR;
if (rc < 0)
return ERROR_FILE_NOT_FOUND;
*pflatEntry += sizeof(DIRENTRY)-sizeof(pEntry->achName) + cbCurName;
}
#ifdef DEBUG
if (*pflatEntry != flatEnd)
{
debugging = TRUE;
DEBUG_PRINTF2 ("\r\n!!! UtilScanDir flatAddr = 0x%08lX cbSize = 0x%08lX\r\n",
BlkDir.flatAddr, BlkDir.cbSize);
INT3;
}
#endif
return ERROR_FILE_NOT_FOUND;
}
int UtilLocate (FLAT _ss *pflatBlkDir, FLAT _ss *pflatEntry, PDIRENTRY pEntry,
PSZ pszPath)
{
int cbPath;
int cbComp;
unsigned char *pchMatch;
static char achSeparator[2] = { '\\', '/' };
cbPath = strlen (pszPath);
while (1)
{
pchMatch = pszPath;
if (FSH_FINDCHAR (2, achSeparator, &pchMatch) == ERROR_CHAR_NOT_FOUND)
break;
/* not reached the end of the path yet, this path component is a subdir */
cbComp = (int)pchMatch - (int)pszPath;
if (UtilScanDir (*pflatBlkDir, pflatEntry, pEntry, pszPath, cbComp))
return LOC_NOPATH;
if ((pEntry->fDOSattr & DOSATTR_DIRECTORY) == 0)
return LOC_NOPATH;
*pflatBlkDir = *pflatEntry + FIELDOFFSET(DIRENTRY,fblkFile);
pszPath += cbComp+1;
cbPath -= cbComp+1;
}
/* no more backslashes in pszPath, we have reached the name component */
cbComp = cbPath;
if (UtilScanDir (*pflatBlkDir, pflatEntry, pEntry, pszPath, cbComp))
{
/* name doesn't exist, let's initialize cbName and achName in case this
file is about to be created */
pEntry->cbName = cbComp;
memcpy (pEntry->achName, pszPath, cbComp+1);
return LOC_NOENTRY;
}
if (pEntry->fDOSattr & DOSATTR_DIRECTORY)
return LOC_DIRENTRY;
else
return LOC_FILEENTRY;
}
int UtilAttrMatch (USHORT usPattern, USHORT usAttr)
{
USHORT usMusthave;
USHORT usMayhave;
usMusthave = usPattern >> 8;
usMayhave = usPattern & 0x00FF;
if (usMusthave == 0)
usMayhave |= (DOSATTR_READONLY | DOSATTR_ARCHIVED);
if (usAttr & ~usMayhave)
return ERROR_FILE_NOT_FOUND;
if (usMusthave & ~usAttr)
return ERROR_FILE_NOT_FOUND;
return NO_ERROR;
}
int UtilInsertEntry (PVOLUME pVolume, FLAT flatBlkDir, PDIRENTRY pEntry,
FLAT _ss *pflatEntry)
{
ULONG cbEntry;
ULONG ofsEntry;
ULONG ofsOldBlkEnd;
BLOCK BlkDir;
VMReadBlk (&BlkDir, flatBlkDir);
#ifdef DEBUG
if (*pflatEntry < BlkDir.flatAddr + DIR_DOTSSIZE ||
*pflatEntry > BlkDir.flatAddr + BlkDir.cbSize)
{
debugging = TRUE;
DEBUG_PRINTF3 ("\r\n!!! UtilInsertEntry 0x%08lX <= 0x%08lX <= 0x%08lX\r\n",
BlkDir.flatAddr + DIR_DOTSSIZE,
*pflatEntry,
BlkDir.flatAddr + BlkDir.cbSize);
INT3;
}
#endif
ofsEntry = *pflatEntry - BlkDir.flatAddr;
cbEntry = sizeof(DIRENTRY)-sizeof(pEntry->achName) + pEntry->cbName;
ofsOldBlkEnd = BlkDir.cbSize;
/* grow the dir block */
if (BlockReallocDir (pVolume, &BlkDir, BlkDir.cbSize + cbEntry))
return ERROR_DISK_FULL;
*pflatEntry = BlkDir.flatAddr + ofsEntry;
/* insert the new entry */
BlockDirCopy (pVolume, BlkDir.flatAddr + ofsEntry + cbEntry,
BlkDir.flatAddr + ofsEntry, ofsOldBlkEnd - ofsEntry);
VMWrite (*pflatEntry, pEntry, cbEntry);
VMWriteBlk (flatBlkDir, &BlkDir);
return NO_ERROR;
}
void UtilDeleteEntry (PVOLUME pVolume, FLAT flatBlkDir, PDIRENTRY pEntry,
FLAT flatEntry)
{
ULONG cbEntry;
ULONG ofsEntry;
ULONG ofsOldBlkEnd;
FLAT flatOldBlk;
BLOCK BlkDir;
VMReadBlk (&BlkDir, flatBlkDir);
#ifdef DEBUG
if (flatEntry < BlkDir.flatAddr + DIR_DOTSSIZE ||
flatEntry >= BlkDir.flatAddr + BlkDir.cbSize)
{
debugging = TRUE;
DEBUG_PRINTF3 ("\r\n!!! UtilDeleteEntry 0x%08lX <= 0x%08lX < 0x%08lX\r\n",
BlkDir.flatAddr + DIR_DOTSSIZE,
flatEntry,
BlkDir.flatAddr + BlkDir.cbSize);
INT3;
}
#endif
ofsEntry = flatEntry - BlkDir.flatAddr;
cbEntry = sizeof(DIRENTRY)-sizeof(pEntry->achName) + pEntry->cbName;
flatOldBlk = BlkDir.flatAddr;
ofsOldBlkEnd = BlkDir.cbSize;
BlockDirCopy (pVolume, flatOldBlk+ofsEntry, flatOldBlk+ofsEntry+cbEntry,
ofsOldBlkEnd-ofsEntry-cbEntry);
if (BlockReallocDir (pVolume, &BlkDir, ofsOldBlkEnd-cbEntry))
{
#ifdef DEBUG
debugging = TRUE;
DEBUG_PRINTF0 ("\r\n!!! UtilDeleteEntry Realloc error too difficult to handle\r\n");
#endif
INT3;
}
VMWriteBlk (flatBlkDir, &BlkDir);
}
void UtilEnterRamfs (void)
{
while (InRamfs)
{
DEBUG_PRINTF0 ("\r\n\r\n>>> UtilEnterRamfs Conflict\r\n");
/* Sleep for one tick */
_asm
{
mov ax, 0xFEDE
mov bx, 0xEBBE
sub di, di
mov cx, 1
mov dx, 0x104
}
(*DevHlp)();
}
InRamfs = TRUE;
}
void UtilExitRamfs (void)
{
#ifdef DEBUG
if (!InRamfs)
{
debugging = TRUE;
DEBUG_PRINTF0 ("\r\n\a!!! Bad UtilExitRamfs\r\n");
INT3;
}
#endif
InRamfs = FALSE;
}