home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Inside Multimedia 1995 July
/
IMM0795.ISO
/
share
/
os2
/
sysbench
/
src
/
pmb_dive.c
< prev
next >
Wrap
C/C++ Source or Header
|
1994-11-05
|
16KB
|
618 lines
// SysBench DIVE test module
// made for the warp II beta toolkit. Must probably be modified to run on OS/2 3.0
#define INCL_WIN
#define INCL_GPI
#define INCL_DOS
#include <os2.h>
#include <stdlib.h>
#include <string.h>
#define _MEERROR_H_
#include "mmioos2.h" /* It is from MMPM toolkit */
#include "dive.h"
#include "fourcc.h"
#include "pmb.h"
#include "types.h"
#define ID_WINDOW 8000
#define PMB_DIVE_CLASS "SysBench dive winclass"
#define MIN_DIVE_TIME 10.0
#define MIN_DIVE2_TIME 1.0
#define MIN_MEASURE 0.1
#define MARGINAL 1.1
#define PI 3.14159265358979323846
//static HAB hab;
extern double cos(double);
extern double sin(double);
extern void err(char* s);
extern void warn(char* s);
extern void log(char* s);
//extern HAB anchorblock(void);
extern double rtime(void); // real time in seconds
extern double dtime(void); // used CPU time in seconds
extern double test_time;
VOID APIENTRY paint_videobw(ULONG unused);
VOID APIENTRY paint_rot(ULONG unused);
VOID APIENTRY paint_ms11(ULONG unused);
VOID APIENTRY paint_ms12(ULONG unused);
VOID APIENTRY paint_ms125(ULONG unused);
static MRESULT EXPENTRY DiveWindowProc( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 );
static void Open(void *paintfun);
static void Close(void);
_Inline void clr_lines(s32 y, s32 lines);
_Inline void disp_lines(u8* buf, s32 y, s32 lines);
_Inline void disp_lines2(u8* src, u8* dest, s32 yin, s32 yout);
_Inline s32 fun(s32 x, double param);
static HWND hwndClient = NULLHANDLE; /* Client area window handle */
static HWND hwndFrame = NULLHANDLE; /* Frame window handle */
static HMQ hmq;
static ULONG flCreate; /* Window creation control flags*/
static HAB bkHab;
static TID paint_tid;
static double result;
static char* framebuf; // the main framebuffer
static DIVE_CAPS dc;
static void Open(void *paintfun) {
s32 w,h, x,y;
RECTL rctl, rctlScreen;
QMSG qmsg; /* Message from message queue */
RECTL rect;
hwndClient = NULLHANDLE; /* Client area window handle */
hwndFrame = NULLHANDLE; /* Frame window handle */
// hab = anchorblock();
if ((bkHab = WinInitialize(0)) == 0L) /* Initialize PM */
err("Can't get anchor block handle for background thread");
if ((hmq = WinCreateMsgQueue( bkHab, 0 )) == 0L)/* Create a msg queue */
err("Can't create message queue for graphics test window");
if (!WinRegisterClass(bkHab, (PSZ)PMB_DIVE_CLASS, (PFNWP)DiveWindowProc, 0, 0)) {
err("DIVE test error: can't register class for child test window");
}
flCreate = FCF_TASKLIST;
if ((hwndFrame = WinCreateStdWindow(
HWND_DESKTOP, /* Desktop window is parent */
0, /* window styles */
&flCreate, /* Frame control flag */
PMB_DIVE_CLASS, /* Client window class name */
"SysBench dive test window", /* window text */
0, /* No special class style */
(HMODULE)0L, /* Resource is in .EXE file */
ID_WINDOW, /* Frame window identifier */
&hwndClient /* Client window handle */
)) == 0L)
err("Can't create dive test window");
WinQueryWindowRect(HWND_DESKTOP, &rect);
WinSetWindowPos(hwndFrame, HWND_TOP, rect.xLeft, rect.yBottom,
rect.xRight-rect.xLeft+1, rect.yTop-rect.yBottom+1, SWP_SIZE | SWP_MOVE | SWP_ACTIVATE | SWP_SHOW | SWP_ZORDER);
DosCreateThread(&paint_tid, (PFNTHREAD)paintfun, 0, 0, 64000);
while( WinGetMsg( bkHab, &qmsg, 0L, 0, 0 ) )
WinDispatchMsg( bkHab, &qmsg );
}
static void Close(void) {
WinDestroyWindow(hwndFrame); /* Tidy up... */
WinDestroyMsgQueue( hmq ); /* Tidy up... */
WinTerminate(bkHab);
}
double pmb_dive_bw(void) {
Open((void*)paint_videobw);
Close();
return result;
}
double pmb_dive_rot(void) {
Open((void*)paint_rot);
Close();
return result;
}
double pmb_dive_ms11(void) {
Open((void*)paint_ms12);
Close();
return result;
}
double pmb_dive_ms12(void) {
Open((void*)paint_ms12);
Close();
return result;
}
double pmb_dive_ms125(void) {
Open((void*)paint_ms12);
Close();
return result;
}
static MRESULT EXPENTRY
DiveWindowProc( HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2 )
{
switch( msg )
{
case WM_CREATE:
break;
case WM_COMMAND:
break;
case WM_ERASEBACKGROUND:
return (MRESULT)( FALSE ); // TRUE -> yes, erase the background
case WM_PAINT:
{
HPS hps;
RECTL rc;
POINTL pt;
hps = WinBeginPaint( hwnd, 0L, &rc );
GpiSetColor( hps, CLR_BLACK ); // colour of the text,
GpiSetBackColor( hps, CLR_BLACK ); // its background and
GpiSetBackMix( hps, BM_OVERPAINT ); // how it mixes,
GpiSetMix( hps, FM_OVERPAINT ); // how it mixes,
// WinFillRect(hps, &rc, CLR_BLACK);
WinEndPaint( hps ); // Drawing is complete
break;
}
case WM_CLOSE:
exit(1); //WinPostMsg( hwnd, WM_QUIT, (MPARAM)0,(MPARAM)0 );
break;
default:
return WinDefWindowProc( hwnd, msg, mp1, mp2 );
}
return (MRESULT)FALSE;
}
VOID APIENTRY paint_videobw(ULONG unused) {
HPS hps;
POINTL p1, p2;
double t1, t2;
RECTL rc;
HDIVE hDive;
PVOID apa;
ULONG ret;
PDIVE_CAPS pdc;
s32 i, j, c, runs, runs_10, framesize, sh, scanlen, frames;
RECTL rect;
char* framecopy;
memset(&dc, 0, sizeof(dc));
dc.ulStructLen = sizeof(dc);
dc.ulFormatLength = 0;
ret = DiveQueryCaps(&dc, DIVE_BUFFER_SCREEN);
if (DIVE_SUCCESS != ret) {
if (ret == DIVE_ERR_INSUFFICIENT_LENGTH) {
dc.pFormatData = calloc(dc.ulFormatLength,1);
ret = DiveQueryCaps(&dc, DIVE_BUFFER_SCREEN); // let's try again
if (DIVE_SUCCESS != ret) {
err("Error in call to DiveQueryCaps()");
}
} else {
err("Error in call to DiveQueryCaps()");
}
}
if (DiveOpen(&hDive, FALSE, &apa)) {
WinPostMsg( hwndClient, WM_QUIT, (MPARAM)0,(MPARAM)0 );
err("Error in DiveOpen() call");
}
framebuf = (char*)apa;
WinQueryWindowRect(HWND_DESKTOP, &rect);
ret = DiveAcquireFrameBuffer(hDive, &rect);
if (ret != DIVE_SUCCESS) {
err("Error in DiveAcquireFrameBuffer()");
}
framesize = dc.ulVerticalResolution * dc.ulScanLineBytes;
framecopy = malloc(framesize);
if (framecopy == null) {
err("Can't get memory for copy of frame buffer");
}
memcpy(framecopy, framebuf, framesize);
frames = 0;
sh = dc.ulVerticalResolution;
scanlen = dc.ulScanLineBytes;
runs = 10;
while (1) {
frames = 0;
t1 = dtime();
for (i = 0; i < runs; i++) {
frames++;
j = i % (sh-1) + 1;
memcpy(framebuf, framecopy+(sh-j)*scanlen, j*scanlen);
memcpy(framebuf + j*scanlen, framecopy, (sh-j)*scanlen);
}
t2 = dtime();
if ((t2 - t1) < MIN_DIVE_TIME) {
if ((t2 - t1) < MIN_MEASURE) {
runs = MIN_DIVE_TIME/MIN_MEASURE*runs;
} else {
runs = MIN_DIVE_TIME*MARGINAL/(t2-t1)*runs;
}
} else {
break;
}
}
result = ((double) frames * scanlen * sh) / (t2-t1);
test_time = (t2-t1);
DiveDeacquireFrameBuffer(hDive);
DiveClose(hDive);
free(dc.pFormatData);
WinPostMsg( hwndClient, WM_QUIT, (MPARAM)0,(MPARAM)0 );
}
VOID APIENTRY paint_rot(ULONG unused) {
HPS hps;
POINTL p1, p2;
double t1, t2;
RECTL rc;
HDIVE hDive;
PVOID apa;
ULONG ret;
PDIVE_CAPS pdc;
s32 i, j, c, runs, runs_10, framesize, sh, scanlen, frames, yin, yout, x, y;
RECTL rect;
char* framecopy;
s32 speed, rev, arg_nrev, sh2, wh, wh2;
double phase = 0.0, phase_steps, c1, c2, c3, c4, c5, c6, c7, c8;
bool forw;
memset(&dc, 0, sizeof(dc));
dc.ulStructLen = sizeof(dc);
dc.ulFormatLength = 0;
ret = DiveQueryCaps(&dc, DIVE_BUFFER_SCREEN);
if (DIVE_SUCCESS != ret) {
if (ret == DIVE_ERR_INSUFFICIENT_LENGTH) {
dc.pFormatData = calloc(dc.ulFormatLength,1);
ret = DiveQueryCaps(&dc, DIVE_BUFFER_SCREEN); // let's try again
if (DIVE_SUCCESS != ret) {
err("Error in call to DiveQueryCaps()");
}
} else {
err("Error in call to DiveQueryCaps()");
}
}
if (DiveOpen(&hDive, FALSE, &apa)) {
WinPostMsg( hwndClient, WM_QUIT, (MPARAM)0,(MPARAM)0 );
err("Error in DiveOpen() call");
}
framebuf = (char*)apa;
WinQueryWindowRect(HWND_DESKTOP, &rect);
ret = DiveAcquireFrameBuffer(hDive, &rect);
if (ret != DIVE_SUCCESS) {
err("Error in DiveAcquireFrameBuffer()");
}
framesize = dc.ulVerticalResolution * dc.ulScanLineBytes;
framecopy = malloc(framesize);
if (framecopy == null) {
err("Can't get memory for copy of frame buffer");
}
memcpy(framecopy, framebuf, framesize);
frames = 0;
sh = dc.ulVerticalResolution;
scanlen = dc.ulScanLineBytes;
runs = 10;
// First, find out the approximate speed of this display
while (1) {
frames = 0;
t1 = dtime();
for (i = 0; i < runs; i++) {
frames++;
memcpy(framebuf, framecopy, sh*scanlen);
}
t2 = dtime();
if ((t2 - t1) < MIN_DIVE2_TIME) {
if ((t2 - t1) < MIN_MEASURE) {
runs = MIN_DIVE2_TIME/MIN_MEASURE*runs;
} else {
runs = MIN_DIVE2_TIME*MARGINAL/(t2-t1)*runs;
}
} else {
break;
}
}
// speed = ((double) frames * scanlen * sh) / (t2-t1); // MB/s
speed = ((double)frames)/(t2-t1); // fps
sh = dc.ulVerticalResolution;
sh2 = sh/2;
phase_steps = .35/speed;
arg_nrev = 1;
t1 = dtime();
frames = 0;
goto lab1;
lab1:
for (rev = 0; rev < arg_nrev; rev++) {
for (phase = 0.0; phase < 2.0*PI; phase += phase_steps) {
frames++;
wh2 = sh2 * cos(phase);
if (wh2 < 0) {
forw = false;
wh2 = -wh2;
} else {
forw = true;
}
wh = wh2 << 1;
if (forw) {
clr_lines(0, sh2-wh2);
for (i = 0; i < wh; i++) {
disp_lines(framecopy+((i*sh)/wh)*dc.ulScanLineBytes, i+sh2-wh2, 1);
}
clr_lines(sh2+wh2, sh2-wh2);
} else {
clr_lines(0, sh2-wh2);
for (i = 0; i < wh; i++) {
disp_lines(framecopy+(((wh-1-i)*sh)/wh)*dc.ulScanLineBytes, i+sh2-wh2, 1);
}
clr_lines(sh2+wh2, sh2-wh2);
}
}
}
phase_steps *= 1.4; // a little faster than the rotation
c1 = 24.0 * (double)dc.ulVerticalResolution / 768.0;
c2 = 2.0 * (double)dc.ulVerticalResolution / 768.0;
c3 = 4.0/(dc.ulVerticalResolution/6.0/PI);
c4 = .7/(dc.ulVerticalResolution/6.0/PI);
c5 = 1.0;
c6 = 2.3;
c7 = 0.0;
c8 = 1.0;
for (rev = 0; rev < arg_nrev; rev++) {
for (phase = 0.0; phase < 2.0*PI; phase += phase_steps) {
frames++;
for (yin = 0; yin < sh; yin++) {
yout = ((double)yin) + c1 * sin(phase * c5 + c7 + yin * c4) +
c2 * sin(phase * c6 + c8 + yin * c3);
if (yout < 0 || yout >= dc.ulHorizontalResolution) {
clr_lines(yin, 1);
} else {
disp_lines2(framecopy, framebuf, yout, yin);
}
}
}
}
/*
for (i = 0; i < 40; i++) {
frames++;
c = 20;
for (x = 0; x < 1024/2; x++) {
j = -((c * (x - 1024/2)) / (1024/2)) * scanlen;
for (y = 0; y < 768*scanlen-j; y += scanlen)
*(framebuf + x + y) = *(framebuf + x + y + j);
}
for (x = 1024/2; x < 1024; x++) {
j = ((c * (x - 1024/2)) / (1024/2)) * scanlen;
for (y = 767*scanlen; y >= j; y -= scanlen)
*(framebuf + x + y) = *(framebuf + x + y - j);
}
for (y = 0; y < 768/2; y++) {
j = (c * (768/2 - y)) / (768/2);
memmove(framebuf + j + y*scanlen, framebuf + y*scanlen, scanlen - j);
}
for (y = 768/2; y < 768; y++) {
j = -(c * (768/2 - y)) / (768/2);
memmove(framebuf + y*scanlen, framebuf + j + y*scanlen, scanlen - j);
}
}
*/
t2 = dtime();
result = ((double) frames ) / (t2-t1);
test_time = (t2-t1);
DiveDeacquireFrameBuffer(hDive);
DiveClose(hDive);
free(dc.pFormatData);
WinPostMsg( hwndClient, WM_QUIT, (MPARAM)0,(MPARAM)0 );
}
_Inline void
clr_lines(s32 y, s32 lines) {
s32 n = (lines*dc.ulScanLineBytes) >> 4;
u32* p = (u32*)(framebuf + y*dc.ulScanLineBytes);
s32 i;
for(i = 0; i < n; i++) {
*p++ = 0; // speed man...
*p++ = 0;
*p++ = 0;
*p++ = 0;
}
}
_Inline void
disp_lines(u8* buf, s32 y, s32 lines) {
memcpy(framebuf + y*dc.ulScanLineBytes, buf, lines*dc.ulScanLineBytes);
/*
s32 n = (lines*dc.ulScanLineBytes) >> 4;
u32* p = (u32*)(framebuf + y*dc.ulScanLineBytes);
u32* p2 = (u32*)buf;
s32 i;
for(i = 0; i < n; i++) {
*p++ = *p2++;
*p++ = *p2++;
*p++ = *p2++;
*p++ = *p2++;
}
*/
}
_Inline void
disp_lines2(u8* src, u8* dest, s32 yin, s32 yout) {
s32 scanlen;
scanlen = dc.ulScanLineBytes;
memcpy(dest + yout * scanlen, src + yin * scanlen, scanlen);
}
/*
inline static void
disp_lines2(u8* src, u8* dest, s32 yin, s32 yout, s32 offs) {
s32 scanlen;
scanlen = dc.ulScanLineBytes;
offs = (offs * (s32)dc.ulScanLineBytes) / (s32)dc.ulHorizontalResolution;
if (offs > 0 && offs < scanlen) {
memcpy(dest + yout * scanlen + offs, src + yin * scanlen, scanlen - offs);
memset(dest + yout * scanlen, 0, offs);
} else if (offs < 0 && offs > -scanlen) {
memcpy(dest + yout * scanlen, src + yin * scanlen - offs, scanlen + offs);
memset(dest + yout * scanlen + (scanlen + offs), 0, -offs);
} else {
memcpy(dest + yout * scanlen, src + yin * scanlen, scanlen);
}
}
*/
_Inline s32
fun(s32 x, double param) {
s32 yout;
yout = ((double)x) + 20.0 * sin(param+x/(dc.ulVerticalResolution/6.0/PI)) +
10.0 * sin(param*2.3+1.0+3*x/(dc.ulVerticalResolution/6.0/PI));
if (yout < 0 || yout >= dc.ulHorizontalResolution)
yout = -1;
return yout;
}
// this function is NOT ready! It is under construction
VOID APIENTRY paint_ms12(ULONG unused) {
HPS hps;
POINTL p1, p2;
double t1, t2;
RECTL rc;
HDIVE hDive;
PVOID apa;
ULONG ret;
PDIVE_CAPS pdc;
s32 i, j, c, runs, runs_10, framesize, sh, scanlen, frames;
RECTL rect;
char* framecopy;
memset(&dc, 0, sizeof(dc));
dc.ulStructLen = sizeof(dc);
dc.ulFormatLength = 0;
ret = DiveQueryCaps(&dc, DIVE_BUFFER_SCREEN);
if (DIVE_SUCCESS != ret) {
if (ret == DIVE_ERR_INSUFFICIENT_LENGTH) {
dc.pFormatData = calloc(dc.ulFormatLength,1);
ret = DiveQueryCaps(&dc, DIVE_BUFFER_SCREEN); // let's try again
if (DIVE_SUCCESS != ret) {
err("Error in call to DiveQueryCaps()");
}
} else {
err("Error in call to DiveQueryCaps()");
}
}
if (DiveOpen(&hDive, FALSE, &apa)) {
WinPostMsg( hwndClient, WM_QUIT, (MPARAM)0,(MPARAM)0 );
err("Error in DiveOpen() call");
}
framebuf = (char*)apa;
/* WinQueryWindowRect(HWND_DESKTOP, &rect);
ret = DiveAcquireFrameBuffer(hDive, &rect);
if (ret != DIVE_SUCCESS) {
err("Error in DiveAcquireFrameBuffer()");
}
*/
framesize = dc.ulVerticalResolution * dc.ulScanLineBytes;
framecopy = malloc(framesize);
if (framecopy == null) {
err("Can't get memory for copy of frame buffer");
}
memcpy(framecopy, framebuf, framesize);
frames = 0;
sh = dc.ulVerticalResolution;
scanlen = dc.ulScanLineBytes;
runs = 10;
while (1) {
frames = 0;
t1 = dtime();
for (i = 0; i < runs; i++) {
frames++;
j = i % (sh-1) + 1;
memcpy(framebuf, framecopy+(sh-j)*scanlen, j*scanlen);
memcpy(framebuf + j*scanlen, framecopy, (sh-j)*scanlen);
}
t2 = dtime();
if ((t2 - t1) < MIN_DIVE_TIME) {
if ((t2 - t1) < MIN_MEASURE) {
runs = MIN_DIVE_TIME/MIN_MEASURE*runs;
} else {
runs = MIN_DIVE_TIME*MARGINAL/(t2-t1)*runs;
}
} else {
break;
}
}
result = ((double) frames * scanlen * sh) / (t2-t1);
test_time = (t2-t1);
// DiveDeacquireFrameBuffer(hDive);
DiveClose(hDive);
free(dc.pFormatData);
WinPostMsg( hwndClient, WM_QUIT, (MPARAM)0,(MPARAM)0 );
}