home *** CD-ROM | disk | FTP | other *** search
- /*
- * DiskSpeed v3.0
- * by
- * Michael Sinz
- *
- * Copyright (c) 1989 by MKSoft Development
- *
- * MKSoft Development
- * 163 Appledore Drive
- * Downingtown, PA 19335
- *
- * Yes, this is yet another disk speed testing program, but with a few
- * differences. It was designed to give the most accurate results of the
- * true disk performance in the system. For this reason many of
- * DiskSpeed's results may look either lower or higher than current disk
- * performance tests.
- *
- * This program was thrown together in a few hours because I needed more
- * accurate and consistent results for disk performance as seen from the
- * application's standpoint. This program has now served its purpose and
- * I am now giving it to the rest of the Amiga world to play with as long
- * as all of the files remain together in unmodified form. (That is, the
- * files DiskSpeed, DiskSpeed.info, DiskSpeed.c, DiskSpeedWindow.c,
- * DiskSpeedWindow.h, MakeBoxes.c, MakeBoxes.h, StandardGadgets.c,
- * StandardGadgets.h, RenderInfo.c, RenderInfo.h, DiskSpeed.doc, and
- * MakeFile)
- *
- * Version 2.0 of this program added a few features and cleaned up the
- * user interface. I hope you like this...
- *
- * Version 3.0 of this program added the performance stress and cleaned up
- * some parts of the older code. (Fix to RenderInfo.c)
- *
- ******************************************************************************
- * *
- * Reading legal mush can turn your brain into guacamole! *
- * *
- * So here is some of that legal mush: *
- * *
- * Permission is hereby granted to distribute this program's source *
- * executable, and documentation for non-commercial purposes, so long as the *
- * copyright notices are not removed from the sources, executable or *
- * documentation. This program may not be distributed for a profit without *
- * the express written consent of the author Michael Sinz. *
- * *
- * This program is not in the public domain. *
- * *
- * Fred Fish is expressly granted permission to distribute this program's *
- * source and executable as part of the "Fred Fish freely redistributable *
- * Amiga software library." *
- * *
- * Permission is expressly granted for this program and it's source to be *
- * distributed as part of the Amicus Amiga software disks, and the *
- * First Amiga User Group's Hot Mix disks. *
- * *
- ******************************************************************************
- *
- * Main code and testing sections...
- */
-
- #include <EXEC/Types.h>
- #include <EXEC/Memory.h>
- #include <Intuition/Intuition.h>
- #include <Libraries/DOS.h>
- #include <Libraries/DOSextens.h>
- #include <Graphics/RastPort.h>
- #include <Devices/Timer.h>
-
- #include <PROTO/All.h>
-
- #include <string.h>
-
- #include "RenderInfo.h"
- #include "DiskSpeedWindow.h"
-
- extern struct IntuitionBase *IntuitionBase;
- extern struct GfxBase *GfxBase;
- struct Library *TimerBase;
-
- #define TIMESCALER 256L
- #define SEEK_READ_SIZE 300L
-
- #define IO_BUFFER_SIZE 262144L
-
- /* Define the file name limits for file create/delete/open/scan */
- #define FINAL 'R'
-
- static char ErrorText1[28] ="Can't create test directory";
- static char ErrorText2[16] ="Bad device name";
- static char ErrorText3[24] ="Can't open results file";
- static char ErrorText4[19] ="Can't open printer";
-
- static char PrinterFile[5] ="PRT:";
- static char ResultFile[18] ="DiskSpeed.Results";
- static char DirectoryName[22] =" Disk Test Directory ";
- static char FileNameRoot[22] =" -- DiskTest File -- ";
-
- static char Testing_String[10] =">Testing<";
-
- /* The Wait pointer I use... */
- USHORT __chip WaitPointer[48] =
- {
- 0x0000, 0x0000, 0x6700, 0xC700, 0xCFA0, 0xCFA0, 0xBFF0, 0x3FF0,
- 0x70F8, 0x7FF8, 0x7DFC, 0x7FFC, 0xFBFC, 0xFFFC, 0x70FC, 0x7FFC,
- 0x7FFE, 0x7FFE, 0x7F0E, 0x7FFE, 0x3FDF, 0x3FFF, 0x7FBE, 0x7FFE,
- 0x3F0E, 0x3FFE, 0x1FFC, 0x1FFC, 0x07F8, 0x07F8, 0x01E0, 0x01E0,
- 0x0780, 0x0780, 0x0FE0, 0x0FE0, 0x0740, 0x0740, 0x0000, 0x0000,
- 0x0070, 0x0070, 0x0078, 0x0078, 0x0030, 0x0030, 0x0000, 0x0000,
- };
-
- /*
- * These two defines set up and clear the WaitPointer...
- */
- #define SetWait(x) SetPointer(x,WaitPointer,22L,16L,NULL,NULL)
- #define ClearWait(x) ClearPointer(x)
-
- /*
- * This does a requester on the window to tell the user something...
- */
- VOID TellUser(struct MyWindow *MyWindow,char *Text)
- {
- register struct IntuiMessage *msg;
- register SHORT flag=TRUE;
-
- MyWindow->ReqIText.LeftEdge=(MyWindow->Req.Width>>1)-(strlen(Text)<<2);
- MyWindow->ReqIText.IText=Text;
-
- Request(&(MyWindow->Req),MyWindow->Window);
- while (flag)
- {
- WaitPort(MyWindow->Window->UserPort);
- while (msg=(struct IntuiMessage *)GetMsg(MyWindow->Window->UserPort))
- {
- if (msg->Class==GADGETUP)
- {
- if (((struct Gadget *)(msg->IAddress))->GadgetID==GADGET_REQ) flag=FALSE;
- }
- ReplyMsg((struct Message *)msg);
- }
- }
- EndRequest(&(MyWindow->Req),MyWindow->Window);
- }
-
- /*
- * Returns FALSE if the user clicked on the CLOSE gadget...
- */
- SHORT Check_Quit(struct MyWindow *MyWindow)
- {
- register struct IntuiMessage *msg;
- register SHORT flag=TRUE;
-
- while(msg=(struct IntuiMessage *)GetMsg(MyWindow->Window->UserPort))
- {
- if (msg->Class==CLOSEWINDOW) flag=FALSE;
- ReplyMsg((struct Message *)msg);
- }
- return(flag);
- }
-
- /*
- * Clears a string entry to spaces...
- */
- VOID Clear_Entry(char *String)
- {
- register SHORT t;
-
- for (t=0;t<9;t++) String[t]=' ';
- String[9]='\0';
- }
-
- /*
- * Sets a string entry to the string >Testing< and does a
- * PrintIText() to display it...
- */
- VOID Set_Testing(SHORT ResultNum,struct MyWindow *MyWindow)
- {
- strcpy(MyWindow->MyResults[ResultNum].text,Testing_String);
- PrintIText(MyWindow->Window->RPort,&(MyWindow->MyResults[ResultNum].IntuiText),NULL,NULL);
- }
-
- /*
- * Sets a string entry to the value passed and does a PrintIText()
- * to display it...
- */
- VOID Set_Entry(SHORT ResultNum,LONG Value,struct MyWindow *MyWindow)
- {
- register SHORT t;
- register SHORT tmp;
- register char *String;
-
- String=MyWindow->MyResults[ResultNum].text;
- Clear_Entry(String);
- t=9;
- while (Value)
- {
- tmp=Value%10;
- Value=Value/10;
- String[--t]=(char)(tmp)+'0';
- }
- if (!String[t]) String[--t]='0';
- PrintIText(MyWindow->Window->RPort,&(MyWindow->MyResults[ResultNum].IntuiText),NULL,NULL);
- }
-
- /*
- * This gets the starting time...
- */
- VOID Timer_Start(struct MyWindow *MyWindow)
- {
- register struct timerequest *Time_Req;
-
- Time_Req=&(MyWindow->TimeReq);
-
- Time_Req->tr_node.io_Command=TR_GETSYSTIME;
- Time_Req->tr_node.io_Flags=IOF_QUICK;
- DoIO((struct IORequest *)Time_Req);
- MyWindow->StartTime=Time_Req->tr_time;
- }
-
- /*
- * This gets the ending time and finds out what the per second speed is...
- * It also does a RefreshGadgets() to display the text...
- */
- VOID Timer_Stop(struct MyWindow *MyWindow,SHORT ResultNum,LONG Number)
- {
- register struct timerequest *Time_Req;
- register LONG Value;
-
- Time_Req=&(MyWindow->TimeReq);
-
- Time_Req->tr_node.io_Command=TR_GETSYSTIME;
- Time_Req->tr_node.io_Flags=IOF_QUICK;
- DoIO((struct IORequest *)Time_Req);
- MyWindow->StopTime=Time_Req->tr_time;
-
- SubTime(&(MyWindow->StopTime),&(MyWindow->StartTime));
-
- /* Now calculate Value based on Number and the time... */
- Value=(Number*TIMESCALER) /
- ( (MyWindow->StopTime.tv_secs*TIMESCALER) +
- (MyWindow->StopTime.tv_micro/(1000000L/TIMESCALER))
- );
-
- Set_Entry(ResultNum,Value,MyWindow);
- }
-
- /*
- * File create test...
- * This creates a bunch of files in our test directory...
- * The delete test deletes these files...
- */
- VOID Do_FileCreate_Test(struct MyWindow *MyWindow)
- {
- register char *t1;
- register char *t2;
- register BPTR file;
- register LONG count=0;
-
- t1=FileNameRoot+1;
- t2=t1+1;
-
- Set_Testing(RESULTS_CREATE,MyWindow);
- Timer_Start(MyWindow);
- for (*t1='A';*t1<FINAL;(*t1)++) for (*t2='A';*t2<FINAL;(*t2)++)
- {
- if (file=Open(FileNameRoot,MODE_NEWFILE)) Close(file);
- count++;
- }
- Timer_Stop(MyWindow,RESULTS_CREATE,count);
- }
-
- /*
- * File Open/Close test...
- * This Opens/Closes a bunch of files in our test directory...
- */
- VOID Do_OpenClose_Test(struct MyWindow *MyWindow)
- {
- register char *t1;
- register char *t2;
- register BPTR file;
- register LONG count=0;
-
- t1=FileNameRoot+1;
- t2=t1+1;
-
- Set_Testing(RESULTS_OPEN_CLOSE,MyWindow);
- Timer_Start(MyWindow);
- for (*t1='A';*t1<FINAL;(*t1)++) for (*t2='A';*t2<FINAL;(*t2)++)
- {
- if (file=Open(FileNameRoot,MODE_OLDFILE)) Close(file);
- count++;
- }
- Timer_Stop(MyWindow,RESULTS_OPEN_CLOSE,count);
- }
-
- /*
- * Directory scan test... This is done by scanning the directory we
- * just created in the create test... (Three times...)
- */
- VOID Do_DirScan_Test(struct MyWindow *MyWindow)
- {
- register struct FileInfoBlock *FIB;
- register BPTR lock;
- register LONG count=0;
- register SHORT loop;
-
- lock=CurrentDir(NULL); /* Get our directory lock... */
- if (FIB=AllocMem(sizeof(struct FileInfoBlock),MEMF_PUBLIC))
- {
- Set_Testing(RESULTS_DIR_SCAN,MyWindow);
- Timer_Start(MyWindow);
- for (loop=0;loop<3;loop++)
- {
- Examine(lock,FIB);
- while (ExNext(lock,FIB)) count++;
- }
- Timer_Stop(MyWindow,RESULTS_DIR_SCAN,count);
-
- FreeMem(FIB,sizeof(struct FileInfoBlock));
- }
- CurrentDir(lock); /* Return the locked directory... */
- }
-
- /*
- * File delete test... We delete the files created in the create test...
- */
- VOID Do_FileDelete_Test(struct MyWindow *MyWindow)
- {
- register char *t1;
- register char *t2;
- register LONG count=0;
-
- t1=FileNameRoot+1;
- t2=t1+1;
-
- Set_Testing(RESULTS_DELETE,MyWindow);
- Timer_Start(MyWindow);
- for (*t1='A';*t1<FINAL;(*t1)++) for (*t2='A';*t2<FINAL;(*t2)++)
- {
- DeleteFile(FileNameRoot);
- count++;
- }
- Timer_Stop(MyWindow,RESULTS_DELETE,count);
- }
-
- /*
- * This does the seek/read test...
- */
- VOID Do_SeekRead_Test(struct MyWindow *MyWindow,char *Buffer)
- {
- register short t;
- register LONG count=0;
- register LONG pos;
- register BPTR bigfile;
-
- if (bigfile=Open(FileNameRoot,MODE_NEWFILE))
- {
- Set_Testing(RESULTS_SEEK_READ,MyWindow);
- Write(bigfile,Buffer,IO_BUFFER_SIZE);
- Timer_Start(MyWindow);
- for (t=0;t<200;t++)
- {
- Seek(bigfile,0L,OFFSET_BEGINNING);
- Read(bigfile,Buffer,SEEK_READ_SIZE);
- count++;
-
- pos=Seek(bigfile,-(2*SEEK_READ_SIZE),OFFSET_END);
- Read(bigfile,Buffer,SEEK_READ_SIZE);
- count++;
-
- Seek(bigfile,-(pos>>1),OFFSET_CURRENT);
- Read(bigfile,Buffer,SEEK_READ_SIZE);
- count++;
- }
- Timer_Stop(MyWindow,RESULTS_SEEK_READ,count);
- Close(bigfile);
- DeleteFile(FileNameRoot);
- }
- }
-
- /*
- * This does the testing at a set buffer size...
- */
- SHORT Do_File_Test(LONG BufSize,struct MyWindow *MyWindow,UBYTE *Buffer,SHORT ResultNum)
- {
- register SHORT flag=TRUE;
- register SHORT t;
- register SHORT loop;
- register LONG count;
- register LONG numblocks;
- register BPTR bigfile;
-
- if (bigfile=Open(FileNameRoot,MODE_NEWFILE))
- {
- numblocks=IO_BUFFER_SIZE/BufSize;
- if (flag&=Check_Quit(MyWindow))
- {
- count=0;
- Set_Testing(ResultNum,MyWindow);
- Timer_Start(MyWindow);
- for (t=0;t<(1<<(MyWindow->TestFlag));t++)
- {
- Close(bigfile);
- bigfile=Open(FileNameRoot,MODE_NEWFILE);
- for (loop=0;loop<numblocks;loop++) count+=Write(bigfile,Buffer,BufSize);
- }
- Timer_Stop(MyWindow,ResultNum++,count);
- }
- if (flag&=Check_Quit(MyWindow))
- {
- count=0;
- Set_Testing(ResultNum,MyWindow);
- Timer_Start(MyWindow);
- for (t=0;t<(2<<(MyWindow->TestFlag));t++)
- {
- Seek(bigfile,NULL,OFFSET_BEGINNING);
- for (loop=0;loop<numblocks;loop++) count+=Write(bigfile,Buffer,BufSize);
- }
- Timer_Stop(MyWindow,ResultNum++,count);
- }
- if (flag&=Check_Quit(MyWindow))
- {
- count=0;
- Set_Testing(ResultNum,MyWindow);
- Timer_Start(MyWindow);
- for (t=0;t<(3<<(MyWindow->TestFlag));t++)
- {
- Seek(bigfile,NULL,OFFSET_BEGINNING);
- for (loop=0;loop<numblocks;loop++) count+=Read(bigfile,Buffer,BufSize);
- }
- Timer_Stop(MyWindow,ResultNum++,count);
- }
- Close(bigfile);
- DeleteFile(FileNameRoot);
- }
- return(flag);
- }
-
- /*
- * This is the master test routine... It calles the ones above...
- */
- VOID Do_Disk_Test(struct MyWindow *MyWindow)
- {
- register BPTR lock;
- register BPTR mydir;
- register SHORT flag=TRUE;
- register UBYTE *Buffer;
- register SHORT loop;
- register struct Gadget *gad;
-
- for (loop=0;loop<NUM_GADGETS;loop++)
- {
- gad=&(MyWindow->MyGadgets[loop].Gadget);
- RemoveGadget(MyWindow->Window,gad);
- gad->Flags|=GADGDISABLED;
- AddGadget(MyWindow->Window,gad,NULL);
- RefreshGList(gad,MyWindow->Window,NULL,1L);
- }
-
- if (lock=Lock(MyWindow->DeviceName,ACCESS_READ))
- {
- lock=CurrentDir(lock);
- if (mydir=CreateDir(DirectoryName))
- {
- mydir=CurrentDir(mydir);
-
- for (loop=0;loop<NUM_RESULTS;loop++)
- {
- Clear_Entry(MyWindow->MyResults[loop].text);
- }
- RefreshGList(&(MyWindow->Detail),MyWindow->Window,NULL,1L);
-
- Stress_On(MyWindow);
-
- if (flag&=Check_Quit(MyWindow))
- {
- Do_FileCreate_Test(MyWindow);
- if (flag&=Check_Quit(MyWindow)) Do_OpenClose_Test(MyWindow);
- if (flag&=Check_Quit(MyWindow)) Do_DirScan_Test(MyWindow);
- Do_FileDelete_Test(MyWindow);
- }
- if (Buffer=AllocMem(IO_BUFFER_SIZE,MEMF_PUBLIC))
- {
- if (flag&=Check_Quit(MyWindow)) Do_SeekRead_Test(MyWindow,Buffer);
-
- if (flag&=Check_Quit(MyWindow)) flag&=Do_File_Test(512L,MyWindow,Buffer,RESULTS_512_CREATE);
- if (flag&=Check_Quit(MyWindow)) flag&=Do_File_Test(4096L,MyWindow,Buffer,RESULTS_4096_CREATE);
- if (flag&=Check_Quit(MyWindow)) flag&=Do_File_Test(32768L,MyWindow,Buffer,RESULTS_32768_CREATE);
- if (flag&=Check_Quit(MyWindow)) flag&=Do_File_Test(262144L,MyWindow,Buffer,RESULTS_262144_CREATE);
-
- FreeMem(Buffer,IO_BUFFER_SIZE);
- }
-
- Stress_Off(MyWindow);
-
- mydir=CurrentDir(mydir);
- UnLock(mydir);
- DeleteFile(DirectoryName);
- }
- else
- { /* Tell user he messed up... */
- TellUser(MyWindow,ErrorText1);
- }
-
- lock=CurrentDir(lock);
- UnLock(lock);
- }
- else
- { /* Tell user he messed up... */
- TellUser(MyWindow,ErrorText2);
- }
-
- for (loop=0;loop<NUM_GADGETS;loop++)
- {
- gad=&(MyWindow->MyGadgets[loop].Gadget);
- RemoveGadget(MyWindow->Window,gad);
- gad->Flags&=~GADGDISABLED;
- AddGadget(MyWindow->Window,gad,NULL);
- }
- RefreshGadgets(gad,MyWindow->Window,NULL);
- }
-
- /*
- * This function will open the file, append to the end of it the
- * test results and close it...
- */
- VOID Save_To_File(struct MyWindow *MyWindow)
- {
- register BPTR TheFile;
-
-
- TheFile=Open(ResultFile,MODE_OLDFILE);
- if (!TheFile) TheFile=Open(ResultFile,MODE_NEWFILE);
- if (TheFile)
- {
- Seek(TheFile,0L,OFFSET_END);
- Write_Results(MyWindow,TheFile);
- Close(TheFile);
- }
- else
- { /* Tell the user the file did not open... */
- TellUser(MyWindow,ErrorText3);
- }
- }
-
- /*
- * This function will open the printer, append to the end of it the
- * test results and close it...
- */
- VOID Save_To_Printer(struct MyWindow *MyWindow)
- {
- register BPTR TheFile;
-
- if (TheFile=Open(PrinterFile,MODE_NEWFILE))
- {
- Write_Results(MyWindow,TheFile);
- Close(TheFile);
- }
- else
- { /* Tell the user the file did not open... */
- TellUser(MyWindow,ErrorText4);
- }
- }
-
- VOID main(VOID)
- {
- register struct MyWindow *MyWindow;
- register struct Window *Window;
- register struct IntuiMessage *msg;
- register struct Gadget *gad;
- register struct timerequest *Time_Req;
- register SHORT QuitFlag=0;
- register struct Process *pr;
- register APTR Old_WindowPtr;
- register SHORT loop;
- register LONG oldpri;
- struct RenderInfo RenderInfo;
-
- pr=(struct Process *)FindTask(NULL);
- Old_WindowPtr=pr->pr_WindowPtr;
- pr->pr_WindowPtr=(APTR)(-1);
- oldpri=SetTaskPri((struct Task *)pr,1L);
-
- if (IntuitionBase=(struct IntuitionBase *)OpenLibrary("intuition.library",33L))
- {
- if (GfxBase=(struct GfxBase *)OpenLibrary("graphics.library",33L))
- {
- FillIn_RenderInfo(&RenderInfo);
- if (MyWindow=OpenMyWindow(&RenderInfo))
- {
- Window=MyWindow->Window;
- Time_Req=&(MyWindow->TimeReq);
- if (!OpenDevice(TIMERNAME,UNIT_VBLANK,(struct IORequest *)Time_Req,NULL))
- {
- Time_Req->tr_node.io_Message.mn_ReplyPort=Window->UserPort;
- TimerBase=(struct Library *)Time_Req->tr_node.io_Device;
- while (!QuitFlag)
- {
- WaitPort(Window->UserPort);
- if (msg=(struct IntuiMessage *)GetMsg(Window->UserPort))
- {
- if (msg->Class==CLOSEWINDOW) QuitFlag=TRUE;
- else if (msg->Class==ACTIVEWINDOW) ActivateGadget(&(MyWindow->DeviceGadget),Window,NULL);
- else if (msg->Class==GADGETDOWN)
- {
- gad=(struct Gadget *)msg->IAddress;
- if (gad->Flags & SELECTED)
- {
- MyWindow->TestFlag=gad->GadgetID;
- for (loop=0;loop<3;loop++)
- {
- gad=&(MyWindow->MyGadgets[loop].Gadget);
- if (MyWindow->TestFlag!=gad->GadgetID)
- {
- if (gad->Flags & SELECTED)
- {
- RemoveGadget(Window,gad);
- gad->Flags&=~SELECTED;
- AddGadget(Window,gad,NULL);
- RefreshGList(gad,Window,NULL,1L);
- }
- }
- }
- }
- else
- {
- RemoveGadget(Window,gad);
- gad->Flags|=SELECTED;
- AddGadget(Window,gad,NULL);
- RefreshGList(gad,Window,NULL,1L);
- }
- }
- else if (msg->Class==GADGETUP)
- {
- SetWait(Window);
- gad=(struct Gadget *)msg->IAddress;
- switch (gad->GadgetID)
- {
- case GADGET_STRING: ActivateGadget((struct Gadget *)gad->UserData,Window,NULL);
- break;
- case GADGET_START: Do_Disk_Test(MyWindow);
- break;
- case GADGET_SAVE: Save_To_File(MyWindow);
- break;
- case GADGET_PRINT: Save_To_Printer(MyWindow);
- break;
- }
- ClearWait(Window);
- }
- ReplyMsg((struct Message *)msg);
- }
- }
- CloseDevice((struct IORequest *)Time_Req);
- }
- CloseMyWindow(MyWindow);
- }
- CloseLibrary((struct Library *)GfxBase);
- }
- CloseLibrary((struct Library *)IntuitionBase);
- }
- oldpri=SetTaskPri((struct Task *)pr,oldpri);
- pr->pr_WindowPtr=Old_WindowPtr;
- }
-