⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 bench1.cpp

📁 WIN32高级程序设计书附源码
💻 CPP
📖 第 1 页 / 共 3 页
字号:
//Filename: BENCH1.CPP
//"WINBENCH" Generated by WindowsMAKER Professional
//Author: Martin Heller

/* Note: This project uses MFC and it also uses threads. It doesn't use MFC from
   threads in production, however, so it is safe. When building for NT, define
   _NTWIN and WIN32, and choose the multi-threaded libraries. If you get an error
   when you link, rebuild the MFC library NAFXCW.LIB to use threads, i.e. go to
   the MFC\SRC directory and issue:
   NMAKE OPT=/MT DEBUG=0 CODEVIEW=0
   		-- MH
*/

#include <afxwin.h>
#include <afxdlgs.h>
#include "NTBENCH.H"
#include <time.h>
#include <string.h>
#include <direct.h>

WMPDEBUG
#include "BENCH1.WMC"

extern void OkMsgBox (char *szCaption, char *szFormat,...);

// user defined code
static double version = 0.82;
int bpp=0,rastercaps=0,sizepalette=0,numreserved=0;
CString MachineDescription;

struct Benchargs {
	char *bname;
	char *strp;
	void(*funcp)();
	CWnd *pDlg;
	HANDLE hWaitFor;
	};

long DoBench(char *bname,char *strp,void(*funcp)(),CWnd * pDlg)
{

  long stime;		/* Start time */
  long etime;		/* End time */
  long time;		/* Elapse time */
  int secs; 	/* Seconds */
  int hunds;		/* 1/100 seconds */
  char temp1[100],temp2[20];
  MSG msg;

  sprintf(temp1,"%4s %-22s ", bname, strp);
  stime = clock();
  (*funcp)();
  etime = clock();
  time = etime - stime;
  time = (long)(time / ((double)CLOCKS_PER_SEC/100.0));
  secs = int(time / 100);
  hunds = int(time % 100);
  sprintf(temp2,"%4d.%02d secs\n", secs, hunds);
  strcat(temp1,temp2);
  pDlg->SetDlgItemText(id_tx_status,temp1);
  TRACE(temp1);
  PeekMessage(&msg,NULL,NULL,NULL,PM_NOREMOVE); //breathe a little
  return time;
}

extern char drive[];
extern int filesize;
extern UINT blocksize;
extern char buffer[];
extern char fillchar;
extern void diskio0(void);
extern void diskio1(void);
extern void diskio2(void);
extern void diskio3(void);
extern void diskio4(void);
extern void diskio5(void);
extern int file_error;
long DiskTimes[6];

CString DoDiskBench(CWnd *pDlg,int nblocks,int nreps,char *ddrive)
{
  CString answer;
  long Wtime;
  char temp[30];

  memset(buffer,fillchar,blocksize);
  filesize = nblocks;
  strcpy(drive,ddrive);

  ASSERT(nblocks>1);
  ASSERT(nreps>0);
  ASSERT(blocksize==4096);

  //accumulate time in hundredths of a second

  Wtime = DiskTimes[0] = DoBench("I0","Create file",diskio0,pDlg);
  for(int i=0;i<nreps;i++) {
	  Wtime+= DiskTimes[1] = DoBench("I1","Sequential Write Test",diskio1,pDlg);
	  Wtime+= DiskTimes[2] = DoBench("I2","Sequential Read Test ",diskio2,pDlg);
	  Wtime+= DiskTimes[3] = DoBench("I3","Random Write Test    ",diskio3,pDlg);
	  Wtime+= DiskTimes[4] = DoBench("I4","Random Read Test     ",diskio4,pDlg);
	  }
  Wtime+= DiskTimes[5] = DoBench("I5","Delete file",diskio5,pDlg);
  if(file_error)
  	strcpy(temp,"A disk error occurred");
  else		
  	sprintf(temp,"Total Disk test time %ld.%ld s",Wtime/100,Wtime%100);
  pDlg->SetDlgItemText(id_tx_status,temp);

  //turn time into MBytes/second
  if(Wtime<=0) Wtime=1000; //protect against divide by 0
  double mbytes_per_sec =(nblocks * (double)blocksize * 0.0004 * nreps / (double)Wtime);
  if(file_error)
  	strcpy(temp,"Error");
  else
  	sprintf(temp,"%.4g",mbytes_per_sec);
  answer=temp;
  return(answer);
}

extern void video0(void);
extern void video1(void);
extern void video2(void);
extern void video3(void);
extern void video4(void);
extern void video5(void);
CWnd *pParent;
extern long vid1pix,vid2pix,vid3pix,vid4pix;
extern long screenarea;
long VideoTimes[6];

CString DoVideoBench(CWnd *pDlg,int nreps)
{
  CString answer;
  long Wtime;
  long TotalPixels;
  char temp[30];

  ASSERT(nreps>0);
  pParent=pDlg;

  //accumulate time in hundredths of a second

  Wtime = VideoTimes[0] = DoBench("V0","Create Window",video0,pDlg);
  for(int i=0;i<nreps;i++) {
	  Wtime+= VideoTimes[1] = DoBench("V1","Character Scrolling Test",video1,pDlg);
	  Wtime+= VideoTimes[2] = DoBench("V2","Line/Curve Drawing Test ",video2,pDlg);
	  Wtime+= VideoTimes[3] = DoBench("V3","Filled Object Test      ",video3,pDlg);
				 VideoTimes[4] = DoBench("V4","Color Display Test      ",video4,pDlg);
	  //color display excluded from total time
	  }
  Wtime+= VideoTimes[5] = DoBench("V5","Destroy Window",video5,pDlg);
  sprintf(temp,"Total Video test time %ld.%ld s",Wtime/100,Wtime%100);
  pDlg->SetDlgItemText(id_tx_status,temp);

  //turn time into KPixels/second
  if(Wtime<=0) Wtime=1000; //protect against divide by 0
  //count 1 screen each for window creation and destruction, plus
  //routines' record of number of pixels written
  TotalPixels=2L*screenarea + vid1pix*nreps //multiply by nreps since vid1pix reset each rep
		+ vid2pix*nreps + vid3pix*nreps
		/* + vid4pix*nreps*/;	//color display excluded from total pixels
  double mpixels_per_sec =(1.0e-6 * TotalPixels / ((double)Wtime/100.0));
  sprintf(temp,"%.4g",mpixels_per_sec);
  answer=temp;
  return(answer);
}

#ifdef WIN32
unsigned long DoBenchThread(void *bargs)
{
	long TTime;
	Benchargs *args = (Benchargs *)bargs;

	DWORD rc=WaitForSingleObject(args->hWaitFor,10000);
	TRACE("DoBenchThread: done waiting for event, rc %d\n",rc);
	TTime=DoBench(args->bname,args->strp,args->funcp,args->pDlg);
	TRACE("DoBenchThread: bench done, time is %d\n",TTime);
	ExitThread(TTime);
	return(TTime);
}
#endif

extern "C" void whetd(void);
const MAXTHREADS = 63;

CString DoWhetstone(CWnd *pDlg,int nthreads,int nreps)
{
  char temp[30];
  CString answer;
  long Wtime=0;
#ifdef WIN32
  MSG msg;
  DWORD dw;

  if(nthreads>1) {
	  HANDLE hWait,hThread[MAXTHREADS];
	  unsigned long id[MAXTHREADS];
	  Benchargs args;
	  hWait=CreateEvent(NULL,TRUE,FALSE,NULL); //manual reset, initially false
	  ASSERT(hWait);
	  args.bname="WD";
	  args.strp="Whetstone (double)";
	  args.funcp=whetd;
	  args.pDlg=pDlg;
	  args.hWaitFor=hWait;

	  for(int i=0;i<nreps;i++) {
		long avg;
		unsigned long exitcode;

		for(int j=0; j<nthreads; j++)
			hThread[j]=CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)DoBenchThread,&args,NULL,&id[j]);
		PeekMessage(&msg,NULL,NULL,NULL,PM_NOREMOVE);
		Sleep(1000);					//allow time for thread creation
		PeekMessage(&msg,NULL,NULL,NULL,PM_NOREMOVE);
		BOOL rc=SetEvent(hWait);	//release all threads at once
		ASSERT(rc);

		//Wait for all threads to complete and get their results
		TRACE("DoWhetstone: about to wait for threads\n");

		for(j=0; j<nthreads; j++) {
			do
				{
				PeekMessage(&msg,NULL,NULL,NULL,PM_NOREMOVE);
				dw=WaitForSingleObject(hThread[j],200);
				}
			while (dw);
			}
		TRACE("DoWhetstone: done waiting for threads, dw %d\n",dw);

		avg = 0;
		for(j=0; j<nthreads; j++) {
			GetExitCodeThread(hThread[j],&exitcode);
			avg += exitcode;
			}
		avg /= nthreads;
		Wtime += avg;
		ResetEvent(hWait);

		} //for nreps

	  sprintf(temp,"%.4g",(nreps * nthreads * 10.0 / (Wtime/100.0)));
	  answer=temp;
	  return(answer);

	  } //if nthreads>1
#endif

  for(int i=0;i<nreps;i++) {
	  Wtime += DoBench("WD","Whetstone (double)",whetd,pDlg);
	  }
  if(Wtime<=0) Wtime=1000; //protect against divide by 0
  sprintf(temp,"%.4g",(nreps * 10.0 / (Wtime/100.0)));
  answer=temp;
  return(answer);
}

extern "C" void dhry(void);

CString DoDhrystone(CWnd *pDlg,int nthreads,int nreps)
{
  char temp[30];
  CString answer;
  long Wtime=0;
#ifdef WIN32
  MSG msg;
  DWORD dw;

  if(nthreads>1) {
	  HANDLE hWait,hThread[MAXTHREADS];
	  unsigned long id[MAXTHREADS];
	  Benchargs args;
	  hWait=CreateEvent(NULL,TRUE,FALSE,NULL); //manual reset, initially false
	  ASSERT(hWait);
	  args.bname="DR";
	  args.strp="Dhrystone";
	  args.funcp=dhry;
	  args.pDlg=pDlg;
	  args.hWaitFor=hWait;

	  for(int i=0;i<nreps;i++) {
		long avg;
		unsigned long exitcode;

		for(int j=0; j<nthreads; j++)
			hThread[j]=CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)DoBenchThread,&args,NULL,&id[j]);
		PeekMessage(&msg,NULL,NULL,NULL,PM_NOREMOVE);
		Sleep(1000);					//allow time for thread creation
		PeekMessage(&msg,NULL,NULL,NULL,PM_NOREMOVE);
		BOOL rc=SetEvent(hWait);	//release all threads at once
		ASSERT(rc);

		//Wait for all threads to complete and get their results
		TRACE("DoDhrystone: about to wait for threads\n");

		for(j=0; j<nthreads; j++) {
			do
				{
				PeekMessage(&msg,NULL,NULL,NULL,PM_NOREMOVE);
				dw=WaitForSingleObject(hThread[j],200);
				}
			while (dw);
			}
		TRACE("DoDhrystone: done waiting for threads, dw %d\n",dw);

		avg = 0;
		for(j=0; j<nthreads; j++) {
			GetExitCodeThread(hThread[j],&exitcode);
			avg += exitcode;
			}
		avg /= nthreads;
		Wtime += avg;
		ResetEvent(hWait);

		} //for nreps

	  sprintf(temp,"%.4g",(nreps * nthreads * 200.0 / (Wtime/100.0)));
	  answer=temp;
	  return(answer);

	  } //if nthreads>1
#endif

  for(int i=0;i<nreps;i++) {
	  Wtime += DoBench("DR","Dhrystone",dhry,pDlg);
	  }
#ifdef WIN32
  double mulfact=200.0;
#else
  double mulfact=32.0;
#endif
  if(Wtime<=0) Wtime=1000; //protect against divide by 0
  sprintf(temp,"%.4g",(nreps * mulfact / (Wtime/100.0)));
  answer=temp;
  return(answer);
}

static int ResultThreads;
static int ResultBlocks;
static int ResultReps;
static char ResultDrive[4];
static CString ResultKDhrys;
static CString ResultKWhets;
static CString ResultKBytes;
static CString ResultKVideo;

BOOL RunBenchMarks(CWnd *pWnd, BOOL fDhry, BOOL fWhet, BOOL fDisk, BOOL fVideo)
{
	char ddrive[4]="";
	int nthreads,nblocks,nreps;
	CString KDhrys,KWhets,KBytes,KVideo;

	//get handle for dialog window (child of main window)
	CWnd *pDlg = pWnd->GetTopWindow();
	if(!pDlg)
		OkMsgBox("Error","GetTopWindow failed");

	//get stuff from controls

	int status=pDlg->DlgDirSelect(ddrive,id_cb_drive);
	if(!status)
		OkMsgBox("Error","DlgDirSelect failed");
	if(!lstrlen(ddrive)) {
		OkMsgBox("Error","DlgDirSelect did not update drive string, using C:");
		lstrcpy(ddrive,"c:");
		}

/* NOTE: MFC Version 2.1 has a bug in CWnd::DlgDirSelect that will cause it to
   fail. To fix the bug, edit AFXWIN2.INL: in the definition for CWnd::DlgDirSelect,
   change INT_MAX to MAX_PATH. Then recompile BENCH1.CPP --mh */

//	OkMsgBox("DEBUG","ddrive is <%s>",ddrive);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -