home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Club Amiga de Montreal - CAM
/
CAM_CD_1.iso
/
files
/
447.lha
/
addtools_v1.1
/
addtools.c
< prev
next >
Wrap
C/C++ Source or Header
|
1990-12-08
|
7KB
|
281 lines
/**********************************************************************/
/* */
/* AddTools - Adds menu items to the Workbench Tools menu. */
/* */
/* Version 1.1 */
/* */
/* by Steve Tibbett */
/* */
/**********************************************************************/
// 2.0 includes required
#include <exec/types.h>
#include <exec/ports.h>
#include <workbench/workbench.h>
#include <workbench/startup.h>
#include <intuition/intuition.h>
#include <dos/dos.h>
#include <dos/dosextens.h>
#include <dos/dostags.h>
#include <exec/memory.h>
#include <string.h>
#include <proto/wb.h>
#include <proto/dos.h>
#include <proto/intuition.h>
#include <proto/exec.h>
struct Library *WorkbenchBase;
struct Library *IntuitionBase;
struct AppMenuItem *AppList[32];
BPTR AppListDirs[32];
char *AppListNames[32];
char *AppListCommands[32];
struct Remember *Remember=0;
struct MsgPort *port;
int NumApps=0;
/**********************************************************************/
/* Lattice C Cleanup Routine */
/**********************************************************************/
void
CleanupRoutine(void)
{
while (NumApps)
{
NumApps--;
if (AppListDirs[NumApps])
UnLock(AppListDirs[NumApps]);
RemoveAppMenuItem(AppList[NumApps]);
};
if (Remember) FreeRemember(&Remember, TRUE);
if (port) DeletePort(port);
if (WorkbenchBase) CloseLibrary(WorkbenchBase);
if (IntuitionBase) CloseLibrary(IntuitionBase);
}
/**********************************************************************/
/* Start a command with an output window from a WBArg list. */
/* The Cmd string that is passed is the template the filenames, */
/* if any, will be added to. If there are no arguments, the */
/* file is invoked directly. If one argument, it is just appended */
/* and run (if the Cmd contains %s or %l). If more than one */
/* argument, %s will be replaced with one filename and the */
/* executable will be invoked once for each argument, and a %l will */
/* be replaced with a list of filenames and the executable invoked */
/* only once. */
/**********************************************************************/
void
RunCommandFromWBArgs(char *OrigCmd, BPTR DefDir, long NumWBArgs, struct WBArg *WArgs)
{
BPTR CurDir;
struct Remember *Remember=0;
struct WBArg *WA;
char *CLine, *ExecuteMe, *Cmd, *ConsoleName;
long BufLen=0, NumArgs;
APTR ConsoleTask=0;
static ULONG ConIOTags[] =
{ SYS_Output, 0, SYS_Input, 0, SYS_Asynch, 1, SYS_UserShell, 1, TAG_DONE };
static ULONG NoIOTags[] =
{ SYS_Asynch, 1, SYS_UserShell, 1, TAG_DONE, };
// If only one arg is expected, recursively call until done.
if ((NumWBArgs>1) && (strstr(OrigCmd, "%s")))
{
WA=WArgs;
while (NumWBArgs)
{
RunCommandFromWBArgs(OrigCmd, DefDir, 1, WA);
WA++;
};
return;
};
// If %l passed, copy string and replace with %s
if (strstr(OrigCmd, "%l"))
{
char *p;
Cmd=(char *)AllocRemember(&Remember, strlen(OrigCmd)+1, MEMF_CLEAR);
if (Cmd==0) return;
strcpy(Cmd, OrigCmd);
p=strstr(Cmd, "%l");
if (p) p[1]='s'; // change %l to %s
} else Cmd=OrigCmd;
ExecuteMe=Cmd;
if (NumWBArgs==0 && strstr(Cmd, "%s"))
{
char *p;
ExecuteMe=(char *)AllocRemember(&Remember, strlen(Cmd)+8, MEMF_CLEAR);
if (ExecuteMe==0) { FreeRemember(&Remember, TRUE); return; };
sprintf(ExecuteMe, Cmd, "");
};
if (NumWBArgs && strstr(Cmd, "%s"))
{
WA=WArgs;
NumArgs=NumWBArgs;
BufLen=strlen(Cmd)+4;
while (NumArgs--)
{
char PathName[512];
NameFromLock(WA->wa_Lock, PathName, 512);
BufLen+=6+strlen(WA->wa_Name)+strlen(PathName);
WA++;
};
CLine=(char *)AllocRemember(&Remember, BufLen, MEMF_CLEAR);
if (CLine)
{
WA=WArgs;
NumArgs=NumWBArgs;
while (NumArgs--)
{
char TempBuff[255], c;
strcat(CLine, " \"");
NameFromLock(WA->wa_Lock, TempBuff, 255);
strcat(CLine, TempBuff);
c=CLine[strlen(CLine)-1];
if (c!=':' && c!='/')
strcat(CLine, "/");
strcat(CLine, WA->wa_Name);
strcat(CLine, "\"");
WA++;
};
ExecuteMe=(char *)AllocRemember(&Remember, strlen(CLine)+strlen(Cmd)+8, MEMF_CLEAR);
if (ExecuteMe==0)
{
FreeRemember(&Remember, TRUE);
return;
};
sprintf(ExecuteMe, Cmd, CLine);
};
};
ConIOTags[1]=0;
ConsoleName=(char *)AllocRemember(&Remember, strlen(ExecuteMe)+50, MEMF_CLEAR);
if (ConsoleName)
{
char *buff=AllocRemember(&Remember, strlen(Cmd)+1, MEMF_CLEAR);
if (buff)
{
sprintf(buff, Cmd, "");
if (buff[strlen(buff)-1]==32)
buff[strlen(buff)-1]=0;
sprintf(ConsoleName, "CON:10/25/550/150/%s Output/AUTO/CLOSE/WAIT", buff);
ConIOTags[1]=Open(ConsoleName, MODE_NEWFILE);
if (ConIOTags[1])
{
struct Process *Proc=((struct Process *)FindTask(0L));
struct FileHandle *FH;
ConsoleTask=Proc->pr_ConsoleTask;
FH=BADDR(ConIOTags[1]);
SetConsoleTask(FH->fh_Type);
ConIOTags[3]=Open("*", MODE_OLDFILE);
};
};
};
if (DefDir)
CurDir=CurrentDir(DefDir);
if (ConIOTags[1])
System(ExecuteMe, (ULONG *)&ConIOTags);
else System(ExecuteMe, (ULONG *)&NoIOTags);
if (DefDir)
CurrentDir(CurDir);
if (ConsoleTask)
SetConsoleTask(ConsoleTask);
FreeRemember(&Remember, TRUE);
}
/**********************************************************************/
/* It all happens here */
/**********************************************************************/
int
main(void)
{
BPTR FP;
struct AppMessage *msg;
onexit(CleanupRoutine);
if ((WorkbenchBase = OpenLibrary("workbench.library",36))==0)
return(0);
if ((IntuitionBase = OpenLibrary("intuition.library", 33))==0)
return(0);
if ((port = CreatePort(0,0))==0)
return(0);
if ((FP=(LONG)Open("S:ToolsList", MODE_OLDFILE))==0)
return(0);
while (TRUE)
{
char buff[255];
char otherbuff[255];
char dirbuff[255];
if (FGets(FP, buff, 255)==0) break;
if (isspace(buff[0]) || buff[0]==';' || buff[0]=='-') continue;
if (FGets(FP, otherbuff, 255)==0) break;
if (FGets(FP, dirbuff, 255)==0) break;
if (buff[0]) buff[strlen(buff)-1]=0;
if (otherbuff[0]) otherbuff[strlen(otherbuff)-1]=0;
if (dirbuff[0]) dirbuff[strlen(dirbuff)-1]=0;
AppListNames[NumApps]=(char *)AllocRemember(&Remember, strlen(buff)+1, MEMF_CLEAR);
AppListCommands[NumApps]=(char *)AllocRemember(&Remember, strlen(otherbuff)+1, MEMF_CLEAR);
if (AppListCommands[NumApps]==0 || AppListNames[NumApps]==0)
return(0);
AppListDirs[NumApps]=Lock(dirbuff, ACCESS_READ);
strcpy(AppListCommands[NumApps], otherbuff);
strcpy(AppListNames[NumApps], buff);
AppList[NumApps] = (struct AppMenuItem *)AddAppMenuItemA(NumApps,NumApps,AppListNames[NumApps],port,NULL);
NumApps++;
}
Close(FP);
while (TRUE)
{
ULONG ID;
Wait((1<<port->mp_SigBit)|SIGBREAKF_CTRL_F);
// If no message arrived, it must be a CTRL_F
if ((msg = (struct AppMessage *) GetMsg(port))==0)
break;
ID=msg->am_ID;
RunCommandFromWBArgs(AppListCommands[ID], AppListDirs[ID], msg->am_NumArgs, msg->am_ArgList);
ReplyMsg((struct Message *) msg);
}
}