home *** CD-ROM | disk | FTP | other *** search
- /*
- ** Verify.c
- **
- ** Check if files/drawers/programs are where they should be
- **
- ** Copyright © 1990-1996 by Olaf `Olsen' Barthel
- ** All Rights Reserved
- **
- ** :ts=4
- */
-
- #ifndef _GLOBAL_H
- #include "Global.h"
- #endif
-
- struct Path
- {
- BPTR path_Next,path_Lock;
- };
-
- /* FindPath(struct Window *Parent,STRPTR Path,BOOL CanCreate,LONG *Error):
- *
- * For the complete path of a file, this checks if the
- * path leading to the file actually exists. This is
- * primarily for files the program should create. Thus,
- * the file in question may not yet exist.
- */
-
- BOOL
- FindPath(struct Window *Parent,STRPTR Path,BOOL CanCreate,LONG *Error)
- {
- UBYTE LocalBuffer[MAX_FILENAME_LENGTH];
- STRPTR Index;
-
- strcpy(LocalBuffer,Path);
-
- Index = PathPart(LocalBuffer);
-
- *Index = 0;
-
- return(FindDrawer(Parent,LocalBuffer,CanCreate,Error));
- }
-
- /* FindDrawer(struct Window *Parent,STRPTR Drawer,BOOL CanCreate,LONG *Error):
- *
- * Check if a given drawer exists and give
- * the user the choice to create it if necessary.
- */
-
- BOOL
- FindDrawer(struct Window *Parent,STRPTR Drawer,BOOL CanCreate,LONG *Error)
- {
- LONG LocalError;
- BPTR FileLock;
- BOOL Result;
- APTR OldPtr;
-
- if(!Config->MiscConfig->ProtectiveMode)
- return(TRUE);
-
- Result = FALSE;
-
- if(!Error)
- Error = &LocalError;
-
- /* Lock out DOS requesters */
-
- DisableDOSRequesters(&OldPtr);
-
- /* Does the drawer exist? */
-
- if(FileLock = Lock(Drawer,ACCESS_READ))
- {
- D_S(struct FileInfoBlock,FileInfo);
-
- /* Take a closer look */
-
- if(Examine(FileLock,FileInfo))
- {
- /* Is this actually a file? */
-
- if(FileInfo->fib_DirEntryType < 0)
- *Error = ERR_NOT_A_DRAWER;
- else
- {
- *Error = 0;
-
- Result = TRUE;
- }
- }
- else
- *Error = IoErr();
-
- UnLock(FileLock);
- }
- else
- {
- LONG Result2 = IoErr();
-
- /* If it doesn't exist, see if we should ask the user to create it */
-
- if(Result2 == ERROR_OBJECT_NOT_FOUND && Parent && CanCreate)
- {
- UBYTE LocalBuffer[MAX_FILENAME_LENGTH];
- BOOL LocalCanCreate;
- STRPTR Index;
-
- LocalCanCreate = FALSE;
-
- /* Chop off the last path part */
-
- strcpy(LocalBuffer,Drawer);
-
- Index = PathPart(LocalBuffer);
-
- *Index = 0;
-
- /* Get a lock on the parent drawer */
-
- if(FileLock = Lock(LocalBuffer,ACCESS_READ))
- {
- D_S(struct InfoData,InfoData);
-
- /* Inquire volume information */
-
- if(Info(FileLock,InfoData))
- {
- /* Can we write to this volume? */
-
- if(InfoData->id_DiskState == ID_VALIDATED)
- LocalCanCreate = TRUE;
- }
-
- UnLock(FileLock);
- }
-
- /* Give it a try? */
-
- if(LocalCanCreate)
- {
- LT_LockWindow(Parent);
-
- /* Ask if we should create it */
-
- if(ShowRequest(Parent,LocaleString(MSG_VERIFY_NO_DRAWER_TXT),LocaleString(MSG_GLOBAL_YES_NO_TXT),Drawer))
- {
- if(FileLock = CreateDir(Drawer))
- {
- Result2 = 0;
-
- Result = TRUE;
-
- UnLock(FileLock);
- }
- else
- Result2 = IoErr();
- }
- else
- {
- Result2 = 0;
- Result = TRUE;
- }
-
- LT_UnlockWindow(Parent);
- }
- }
-
- *Error = Result2;
- }
-
- EnableDOSRequesters(OldPtr);
-
- if(Window && !Result && *Error)
- {
- LT_LockWindow(Parent);
-
- if(*Error == ERR_NOT_A_DRAWER)
- ShowError(Parent,*Error,NULL,Drawer);
- else
- ShowError(Parent,ERR_DRAWER_NOT_FOUND,*Error,Drawer);
-
- LT_UnlockWindow(Parent);
- }
-
- return(Result);
- }
-
- /* FindFile(struct Window *Parent,STRPTR File,LONG *Error):
- *
- * Try to locate a file.
- */
-
- BOOL
- FindFile(struct Window *Parent,STRPTR File,LONG *Error)
- {
- LONG LocalError;
- BPTR FileLock;
- BOOL Result;
- APTR OldPtr;
-
- if(!Config->MiscConfig->ProtectiveMode)
- return(TRUE);
-
- Result = FALSE;
-
- if(!Error)
- Error = &LocalError;
-
- /* Lock out DOS requesters */
-
- DisableDOSRequesters(&OldPtr);
-
- /* Try to get a lock on the file */
-
- if(FileLock = Lock(File,ACCESS_READ))
- {
- D_S(struct FileInfoBlock,FileInfo);
-
- /* Take a closer look */
-
- if(Examine(FileLock,FileInfo))
- {
- /* Is it actually a drawer? */
-
- if(FileInfo->fib_DirEntryType > 0)
- *Error = ERR_NOT_A_FILE;
- else
- {
- *Error = 0;
-
- Result = TRUE;
- }
- }
- else
- *Error = IoErr();
-
- UnLock(FileLock);
- }
- else
- *Error = IoErr();
-
- EnableDOSRequesters(OldPtr);
-
- if(Window && !Result && *Error)
- {
- LT_LockWindow(Parent);
-
- if(*Error == ERR_NOT_A_FILE)
- ShowError(Parent,*Error,NULL,File);
- else
- ShowError(Parent,ERR_FILE_NOT_FOUND,*Error,File);
-
- LT_UnlockWindow(Parent);
- }
-
- return(Result);
- }
-
- /* FindARexxComment(STRPTR LocalBuffer,LONG Len):
- *
- * Check for a valid ARexx file comment.
- */
-
- STATIC BOOL
- FindARexxComment(STRPTR LocalBuffer,LONG Len)
- {
- UBYTE c;
- LONG i;
-
- for(i = 0 ; i < Len - 1 ; i++)
- {
- c = LocalBuffer[i];
-
- /* Stop on invalid characters. */
-
- if((c < ' ' && c != '\r' && c != '\n' && c != '\a') || (c >= 127 && c < 160))
- break;
- else
- {
- /* Looks like the typical */
- /* introductory comment line. */
-
- if(c == '/' && LocalBuffer[i + 1] == '*')
- return(TRUE);
- }
- }
-
- return(FALSE);
- }
-
- /* FindProgram(struct Window *Parent,STRPTR Program,LONG *Error):
- *
- * Try to find a program given by name. Firstly, try to access the
- * file by its name. If unsuccessful, search the Shell path list.
- * As a last resort, search the global AmigaDOS resident program
- * list. Note that while this routine may fail program execution
- * may still work. WShell for example maintains its own internal
- * resident list.
- */
-
- BOOL
- FindProgram(struct Window *Parent,STRPTR Program,LONG *Error)
- {
- UBYTE LocalBuffer[MAX_FILENAME_LENGTH];
- BOOL Result,CanExecute;
- LONG LocalError;
- BPTR FileLock;
- APTR OldPtr;
- LONG i;
-
- if(!Config->MiscConfig->ProtectiveMode)
- return(TRUE);
-
- Result = FALSE;
- CanExecute = FALSE;
-
- if(!Error)
- Error = &LocalError;
-
- /* Chop off the program arguments */
-
- while(*Program == ' ')
- Program++;
-
- strcpy(LocalBuffer,Program);
-
- for(i = 0 ; i < strlen(LocalBuffer) ; i++)
- {
- if(LocalBuffer[i] == ' ')
- {
- LocalBuffer[i] = 0;
- break;
- }
- }
-
- Program = LocalBuffer;
-
- /* Lock out DOS requesters */
-
- DisableDOSRequesters(&OldPtr);
-
- /* Try to lock the program */
-
- if(FileLock = Lock(Program,ACCESS_READ))
- {
- D_S(struct FileInfoBlock,FileInfo);
-
- /* Take a closer look */
-
- if(Examine(FileLock,FileInfo))
- {
- /* Is it actually a drawer? */
-
- if(FileInfo->fib_DirEntryType > 0)
- *Error = ERR_NOT_A_FILE;
- else
- {
- BOOL GotIt;
-
- /* So far, so good */
-
- *Error = 0;
-
- Result = TRUE;
- GotIt = FALSE;
-
- /* Is it marked as being executable? */
-
- if(!(FileInfo->fib_Protection & FIBF_EXECUTE))
- {
- BPTR FileHandle;
- ULONG Value;
-
- /* Look at the contents */
-
- if(FileHandle = Open(Program,MODE_OLDFILE))
- {
- if(Read(FileHandle,&Value,sizeof(ULONG)) == sizeof(ULONG))
- {
- /* Not a failproof check, but better than nothing */
-
- if(Value == HUNK_HEADER)
- {
- CanExecute = TRUE;
- GotIt = TRUE;
- }
- }
-
- Close(FileHandle);
- }
- }
-
- if(!GotIt)
- {
- /* Does it have the script bit set? */
-
- if(FileInfo->fib_Protection & FIBF_SCRIPT)
- CanExecute = TRUE;
- else
- {
- BPTR FileHandle;
-
- /* Now check if it's an ARexx script. */
-
- if(FileHandle = Open(Program,MODE_OLDFILE))
- {
- UBYTE LocalBuffer[256];
- LONG Len;
-
- if((Len = Read(FileHandle,LocalBuffer,sizeof(LocalBuffer))) > 0)
- {
- if(CanExecute = FindARexxComment(LocalBuffer,Len))
- Result = TRUE;
- }
-
- Close(FileHandle);
- }
- }
- }
- }
- }
-
- UnLock(FileLock);
- }
- else
- {
- LONG Result2 = IoErr();
-
- if(Result2 == ERROR_DEVICE_NOT_MOUNTED)
- *Error = ERROR_OBJECT_NOT_FOUND;
- else
- *Error = Result2;
- }
-
- /* Give it another try */
-
- if(!Result || !CanExecute)
- {
- /* Take care */
-
- if(ThisProcess->pr_CLI)
- {
- struct CommandLineInterface *CLI;
- BOOL InitialCD,GotIt;
- BPTR StartCD,Drawer;
- struct Path *Path;
-
- CLI = BADDR(ThisProcess->pr_CLI);
- InitialCD = TRUE;
- GotIt = FALSE;
-
- /* Run down the Shell path search list */
-
- for(Path = BADDR(CLI->cli_CommandDir) ; Path && !GotIt ; Path = BADDR(Path->path_Next))
- {
- Drawer = CurrentDir(Path->path_Lock);
-
- if(InitialCD)
- {
- StartCD = Drawer;
- InitialCD = FALSE;
- }
-
- /* Try to lock the program */
-
- if(FileLock = Lock(Program,ACCESS_READ))
- {
- D_S(struct FileInfoBlock,FileInfo);
-
- /* Take a closer look */
-
- if(Examine(FileLock,FileInfo))
- {
- /* Is this a file marked as being executable? */
-
- if(FileInfo->fib_DirEntryType < 0)
- {
- if(!(FileInfo->fib_Protection & FIBF_EXECUTE))
- {
- BPTR FileHandle;
- ULONG Value;
-
- /* Look at the contents */
-
- if(FileHandle = Open(Program,MODE_OLDFILE))
- {
- if(Read(FileHandle,&Value,sizeof(ULONG)) == sizeof(ULONG))
- {
- /* Not a failproof check, but better than nothing */
-
- if(Value == HUNK_HEADER)
- GotIt = TRUE;
- }
-
- Close(FileHandle);
- }
- }
-
- if(!GotIt)
- {
- /* Does it look like a script? */
-
- if(FileInfo->fib_Protection & FIBF_SCRIPT)
- GotIt = TRUE;
- else
- {
- BPTR FileHandle;
-
- /* Now check if it's an ARexx script. */
-
- if(FileHandle = Open(Program,MODE_OLDFILE))
- {
- UBYTE LocalBuffer[256];
- LONG Len;
-
- if((Len = Read(FileHandle,LocalBuffer,sizeof(LocalBuffer))) > 0)
- {
- if(CanExecute = FindARexxComment(LocalBuffer,Len))
- GotIt = TRUE;
- }
-
- Close(FileHandle);
- }
- }
- }
- }
- }
-
- UnLock(FileLock);
- }
- }
-
- if(!GotIt)
- {
- BPTR CommandDir;
-
- if(CommandDir = Lock("C:",ACCESS_READ))
- {
- Drawer = CurrentDir(CommandDir);
-
- if(InitialCD)
- {
- StartCD = Drawer;
- InitialCD = FALSE;
- }
-
- /* Try to lock the program */
-
- if(FileLock = Lock(Program,ACCESS_READ))
- {
- D_S(struct FileInfoBlock,FileInfo);
-
- /* Take a closer look */
-
- if(Examine(FileLock,FileInfo))
- {
- /* Is this a file marked as being executable? */
-
- if(FileInfo->fib_DirEntryType < 0)
- {
- if(!(FileInfo->fib_Protection & FIBF_EXECUTE))
- {
- BPTR FileHandle;
- ULONG Value;
-
- /* Look at the contents */
-
- if(FileHandle = Open(Program,MODE_OLDFILE))
- {
- if(Read(FileHandle,&Value,sizeof(ULONG)) == sizeof(ULONG))
- {
- /* Not a failproof check, but better than nothing */
-
- if(Value == HUNK_HEADER)
- GotIt = TRUE;
- }
-
- Close(FileHandle);
- }
- }
-
- if(!GotIt)
- {
- /* Does it look like a script? */
-
- if(FileInfo->fib_Protection & FIBF_SCRIPT)
- GotIt = TRUE;
- else
- {
- BPTR FileHandle;
-
- /* Now check if it's an ARexx script. */
-
- if(FileHandle = Open(Program,MODE_OLDFILE))
- {
- UBYTE LocalBuffer[256];
- LONG Len;
-
- if((Len = Read(FileHandle,LocalBuffer,sizeof(LocalBuffer))) > 0)
- {
- if(CanExecute = FindARexxComment(LocalBuffer,Len))
- GotIt = TRUE;
- }
-
- Close(FileHandle);
- }
- }
- }
- }
- }
-
- UnLock(FileLock);
- }
-
- UnLock(CommandDir);
- }
- }
-
- if(!InitialCD)
- CurrentDir(StartCD);
-
- if(GotIt)
- {
- CanExecute = TRUE;
-
- *Error = 0;
-
- Result = TRUE;
- }
- }
- }
-
- /* As a last resort, scan the resident program list */
-
- if(!Result)
- {
- Forbid();
-
- if(FindSegment(Program,NULL,DOSFALSE) || FindSegment(Program,NULL,DOSTRUE))
- {
- CanExecute = TRUE;
-
- *Error = 0;
-
- Result = TRUE;
- }
-
- Permit();
- }
-
- /* Last check for ARexx script. */
-
- if(!Result)
- {
- UBYTE RexxName[MAX_FILENAME_LENGTH];
-
- strcpy(RexxName,"REXX:");
-
- if(AddPart(RexxName,Program,sizeof(RexxName)))
- {
- BPTR FileHandle;
-
- /* Now check if it's an ARexx script. */
-
- if(FileHandle = Open(RexxName,MODE_OLDFILE))
- {
- UBYTE LocalBuffer[256];
- LONG Len;
-
- if((Len = Read(FileHandle,LocalBuffer,sizeof(LocalBuffer))) > 0)
- {
- if(CanExecute = FindARexxComment(LocalBuffer,Len))
- Result = TRUE;
- }
-
- Close(FileHandle);
- }
- }
- }
-
- /* Last check for AmigaDOS script */
-
- if(!Result)
- {
- UBYTE ScriptName[MAX_FILENAME_LENGTH];
-
- strcpy(ScriptName,"S:");
-
- if(AddPart(ScriptName,Program,sizeof(ScriptName)))
- {
- if(FileLock = Lock(ScriptName,ACCESS_READ))
- {
- D_S(struct FileInfoBlock,FileInfo);
-
- if(Examine(FileLock,FileInfo))
- {
- if(FileInfo->fib_DirEntryType < 0 && (FileInfo->fib_Protection & FIBF_SCRIPT) && FileInfo->fib_Size > 0)
- CanExecute = Result = TRUE;
- }
-
- UnLock(FileLock);
- }
- }
- }
-
- if(!CanExecute && Result)
- {
- *Error = ERROR_NOT_EXECUTABLE;
-
- Result = FALSE;
- }
-
- EnableDOSRequesters(OldPtr);
-
- if(Window && !Result && *Error)
- {
- LT_LockWindow(Parent);
-
- if(*Error == ERR_NOT_A_FILE)
- ShowError(Parent,*Error,NULL,Program);
- else
- ShowError(Parent,ERR_PROGRAM_NOT_FOUND,*Error,Program);
-
- LT_UnlockWindow(Parent);
- }
-
- return(Result);
- }
-
- /* FindLibDev(struct Window *Parent,STRPTR File,LONG Type,LONG *Error):
- *
- * Try to locate a file.
- */
-
- BOOL
- FindLibDev(struct Window *Parent,STRPTR File,LONG Type,LONG *Error)
- {
- UBYTE LocalBuffer[MAX_FILENAME_LENGTH];
- BOOL Result,Replaced;
- STRPTR OriginalFile;
- struct Node *Node;
- LONG LocalError;
- BPTR FileLock;
- APTR OldPtr;
- BOOL NotDone;
-
- if(!Config->MiscConfig->ProtectiveMode)
- return(TRUE);
-
- Result = FALSE;
- Replaced = FALSE;
-
- if(!Error)
- Error = &LocalError;
-
- Forbid();
-
- if(Type == NT_LIBRARY)
- Node = FindName(&SysBase->LibList,PathPart(File));
- else
- Node = FindName(&SysBase->DeviceList,PathPart(File));
-
- Permit();
-
- if(Node)
- {
- *Error = 0;
-
- return(TRUE);
- }
-
- /* Lock out DOS requesters */
-
- DisableDOSRequesters(&OldPtr);
-
- do
- {
- NotDone = FALSE;
-
- /* Try to get a lock on the file */
-
- if(FileLock = Lock(File,ACCESS_READ))
- {
- D_S(struct FileInfoBlock,FileInfo);
-
- /* Take a closer look */
-
- if(Examine(FileLock,FileInfo))
- {
- /* Is it actually a drawer? */
-
- if(FileInfo->fib_DirEntryType > 0)
- *Error = ERR_NOT_A_FILE;
- else
- {
- if(ValidateFile(File,Type,NULL))
- {
- *Error = 0;
-
- Result = TRUE;
- }
- else
- *Error = ERROR_OBJECT_WRONG_TYPE;
- }
- }
- else
- *Error = IoErr();
-
- UnLock(FileLock);
- }
- else
- *Error = IoErr();
-
- if(!Result && !Replaced)
- {
- Replaced = TRUE;
-
- strcpy(LocalBuffer,Type == NT_LIBRARY ? "Libs:" : "Devs:");
-
- OriginalFile = File;
-
- if(AddPart(LocalBuffer,File,sizeof(LocalBuffer)))
- {
- File = LocalBuffer;
-
- NotDone = TRUE;
- }
- }
- }
- while(NotDone);
-
- if(Replaced)
- File = OriginalFile;
-
- EnableDOSRequesters(OldPtr);
-
- if(Window && !Result && *Error)
- {
- LT_LockWindow(Parent);
-
- if(*Error == ERR_NOT_A_FILE)
- ShowError(Parent,*Error,NULL,File);
- else
- ShowError(Parent,ERR_FILE_NOT_FOUND,*Error,File);
-
- LT_UnlockWindow(Parent);
- }
-
- return(Result);
- }
-