#include <windows.h>
#include <stdlib.h>
#include <stdio.h>
#include <ctype.h>
#include <string.h>
#include <assert.h>
#include <math.h>
#include <stdarg.h>
#ifdef __TURBOC__
#include <alloc.h>
#else
#define huge
#endif

#define true (!false)
#define false 0
#include "dvipath.h"

#include "dviwin.h"

void metafile_fix(void );

void main_show(HWND hwnd);
void do_convert(void) ;
void do_display(void);
int32 FAR PASCAL fnmainwnd(HWND hWnd, unsigned wMessage, WORD wParam, LONG lParam);
int wprintf(char *fmt, ...);
void emsg(char *s);

void draw_file(void);
void gle_abort(char *s);
void path_send();
void path_fill(void);
void path_clip(void);
void path_send(void);
void path_stroke(void);
void path_move(int  x,int y);
void path_line(int x,int y);
void path_bezier(int x1, int y1, int x2, int y2,int x3, int y3);
void path_closepath(void);
void path_alloc(void);
void path_free(void);
void d_open(double width, double height);
void d_close(void);
void d_line(int cx,int cy,int x,int y);
void d_lwidth(int width);
void d_bezier(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3);
void d_pbezier(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3);
void d_newpath(void);
void d_pmove(int x, int y);
void d_pline(int x, int y);
void d_pclose(void);
void d_fill(void);
void d_lstyle(int cur_lstyle,int dot);
void d_setcolor(int r,int g,int b,int f);

double d_xscale, d_yscale;
int gdebug=false;
int fittobit;	/* true if picture should be scaled up to fit bitmap, wp-tiff */
void do_delay(int tm);

#define XBITS 10000
#define YBITS 10000
#define scx(v) ( ((v) * d_xscale + 1))
#define scy(v) ( ((v) * d_yscale + 1))
int debug_flag = false;
#define dbg if (debug_flag)

double devxcm,devycm;
double uxcm,uycm;

/*---------------------------------------------------------------------------*/
/*		Local stuff */
int flipit;
FILE *outbit;
FILE *inf;
#define TEMP_FILE "dviwin.tmp"
#define OUT_FILE "gle.wmf"

/*---------------------------------------------------------------------------*/
void main_usage(void)
{
	printf("Usage: dviprint [-depson | -dlj] [-old] [-hires] [-debug] [-output xx.prt]\n");
	printf("\n");
}
char outbitname[80];
char gleroot[90];
HANDLE   hInst;
HWND hwndmain;
static int use_screen;
int PASCAL WinMain(HANDLE hInstance, HANDLE hPrevInstance,
	LPSTR  lpszCmdLine,int nCmdShow)
{
	char appname[]="dviwin";
	MSG      msg;
	WNDCLASS wndclass;
	HANDLE hBorLibrary;

	hBorLibrary = LoadLibrary("bwcc.dll");

	hInst = hInstance;    // Store the application instance handle
	if(!hPrevInstance) {
      wndclass.style           = CS_HREDRAW | CS_VREDRAW;
		wndclass.lpfnWndProc     =  fnmainwnd;
      wndclass.cbClsExtra      = 0;
      wndclass.cbWndExtra      = 0;
      wndclass.hInstance       = hInstance;
      wndclass.hCursor         = LoadCursor(NULL, IDC_ARROW);
      wndclass.hIcon           = NULL;
		wndclass.hbrBackground   = CreateSolidBrush(GetSysColor(COLOR_WINDOW));
		wndclass.lpszMenuName    = "dviwin";
      wndclass.lpszClassName   = appname;

		if(!RegisterClass(&wndclass)) return FALSE;
		wndclass.lpszMenuName = NULL;
		wndclass.hbrBackground   = 0;
		wndclass.lpszClassName = "simple";
		if(!RegisterClass(&wndclass)) return FALSE;
	}

   	if(!(hwndmain = CreateWindow(appname,
                       "DVI to WINDOWS System",
                       WS_OVERLAPPEDWINDOW,
                       CW_USEDEFAULT, 0,
                       CW_USEDEFAULT, 0,
                       NULL, NULL, hInstance, NULL))) {

		return FALSE;
   	}

   	ShowWindow(hwndmain, nCmdShow);
   	UpdateWindow(hwndmain);

	while(GetMessage(&msg, NULL, 0, 0)) {
			TranslateMessage(&msg);
        DispatchMessage(&msg);
	 }
  	if(hBorLibrary > 32) FreeLibrary(hBorLibrary);
   return msg.wParam;
}

int32 FAR PASCAL fnmainwnd(HWND hWnd, unsigned wMessage, WORD wParam, LONG lParam)
{
	switch(wMessage) {
	case WM_COMMAND :
		if(!LOWORD(lParam)) {           // Process Menu Commands
			 switch(wParam) {           // Determine which Menu ID
				case IDM_QUIT :
	  				PostQuitMessage(0);
               break;
				case IDM_CONVERT :
            	use_screen = false;
					do_convert();
               break;
				case IDM_TEST:
            	use_screen = true;
					do_convert();
               break;
				case IDM_DISPLAY :
					do_display();
               break;
            case IDM_HELP :
					break;
             }
    	} else {
		}
      break;
     case WM_DESTROY :
		PostQuitMessage(0);
		break;
	  case WM_PAINT:
	 	main_show(hWnd);
      break;
     default :
     	return DefWindowProc(hWnd, wMessage, wParam, lParam);
   }
   return 0L;
}

void main_show(HWND hwnd)
{
	HDC hdc;
	PAINTSTRUCT ps;
	RECT rect;
	HANDLE hmf;


	hdc = BeginPaint(hwnd,&ps);
	EndPaint(hwndmain,&ps);

}

void do_convert(void)
{
	//emsg("doing conversion");
	//wprintf("Doing conversion");
	inf = fopen("out.dvi","rb");
	if (inf==NULL) {
		printf("Unable to open OUT.DVI for input, run DVIGLE first\n");
		gle_abort("");
   }
	draw_file();
	fclose(inf);
}
void do_display(void)
{
	HDC hdc;
	RECT rect;
	HANDLE hmf;

	hdc = GetDC(hwndmain);

	GetClientRect(hwndmain,&rect);
	SetMapMode(hdc,MM_ANISOTROPIC);
	SetWindowExt(hdc,XBITS,YBITS);
	SetViewportExt(hdc,rect.right,-rect.bottom);
   SetViewportOrg(hdc,0,rect.bottom);

	hmf = GetMetaFile(TEMP_FILE);
	PlayMetaFile(hdc,hmf);
   DeleteMetaFile(hmf);
	ReleaseDC(hwndmain,hdc);
}
/*---------------------------------------------------------------------------*/
/*   Path variables for bitmap */
int *path;
int npath;
int npath_alloc;

int file_end = false;
float getf(void);
int getfxy(int *x, int *y);
int getfxy(int *x, int  *y)
{
	float u,xx,yy;
	xx = getf();
	yy = uycm - getf();

	if (flipit) {
		u = yy;
		yy = uxcm - xx;
		xx = u;
	}
	/*printf("fxy %g %g \n",xx,yy); */
	*x = (int) .5+scx(xx);
	*y = (int) .5+scy(yy);
}
float getf(void)
{
	static float x;
	fread(&x,sizeof(x),1,inf);
	if (feof(inf)) file_end = true;
	return x;
}
int32 getl(void)
{
	static int32 x;
	fread(&x,sizeof(x),1,inf);
	if (feof(inf)) file_end = true;
	return x;
}


float cur_lwidth,cur_color,cur_fill,cur_dashlen;
int32 cur_lstyle;

void draw_file(void)
{
	MSG msg;
	int x2,y2,x3,y3,sx,sy;
	int x,y,cx,cy;
	int g=0;
	float fx,fy;
	int i,dot;

	for (;!file_end;) {
	 // for (;0!=PeekMessage((LPMSG) &msg,hwndmain,0,1000,PM_NOREMOVE);)
	  // {
  //	  		TranslateMessage(&msg);
	//		DispatchMessage(&msg);
		//}
	  i = getl();
	  if (file_end) break;
	  switch (i) {
		case p_size:
			dbg wprintf("#size \n");
			fx = getf(); fy = getf();
			d_open(fx,fy);
			dbg wprintf(":");
		case p_newpath:
			dbg wprintf("#newpath \n");
			npath = 0;
			break;
		case p_move:
			getfxy(&x,&y);
			cx = x; cy = y;
			dbg wprintf("#move (%d) %d %d  \n",npath,x,y);
			path_move(x,y);
			sx = cx; sy = cy;
			break;
		case p_line:
			dbg {g++; if (g>200) {printf(":"); g=0;}}
			getfxy(&x,&y);
			cx = x; cy = y;
			dbg wprintf("#line (%d) %d %d  \n",npath,x,y);
			path_line(x,y);
			break;
		case p_closepath:
			dbg wprintf("#closepath %d %d \n",sx,sy);
			path_closepath();
			cx = sx; cy = sy;
			break;
		case p_dline:
			dbg {g++; if (g>200) {wprintf(":"); g=0;}}
			getfxy(&x,&y);
			d_line(cx,cy,x,y);
			npath = 0;
			dbg wprintf("#(nopath)line %d %d %d %d  \n",cx,cy,x,y);
			cx = x; cy = y;
			break;
		case p_bezier:
			getfxy(&x,&y);
			getfxy(&x2,&y2);
			getfxy(&x3,&y3);
			path_bezier(x,y,x2,y2,x3,y3);
			dbg wprintf("#bezier (%d)\n",npath);
			cx = x3; cy = y3;
			break;
		case p_stroke:
			dbg wprintf("#stroke (%d) \n",npath);
			path_stroke();
			break;
		case p_fill:
			wprintf("#fill (%d) \n",npath);
			path_fill();
			break;
		case p_lwidth:
			dbg wprintf("#lwidth \n");
			cur_lwidth = getf();
			d_lwidth((int) scx(cur_lwidth));
			break;
		case p_dashlen:
			dbg wprintf("#dashlen \n");
			cur_dashlen = getf();
                        dot=(int)(0.5+d_yscale*cur_dashlen);
                        dot = dot > 0 ? dot : 1;
			d_lstyle(cur_lstyle,dot);
			break;
		case p_lstyle:
			dbg wprintf("#lstyle \n");
			cur_lstyle = getl();
                        dot=(int)(0.5+d_yscale*cur_dashlen);
                        dot = dot > 0 ? dot : 1;
			d_lstyle(cur_lstyle,dot);
			break;
		case p_setcolor:
			x = getl(); x2 = getl(); x3 = getl(); y = getl();
			dbg wprintf("#setcolor %d %d %d f=%d \n",x,x2,x3,y);
			d_setcolor(x,x2,x3,y); /* r,g,b,f */
			break;
		case p_clip:
			dbg wprintf("#clipcurpath \n");
			path_clip();
			break;
		case p_saveclip:
			dbg wprintf("#save clip \n");
			//d_saveclip(bb);
			break;
		case p_restoreclip:
			dbg wprintf("#restore clip \n");
			//bmp_restoreclip(bb);
			break;
		case p_null:
			dbg wprintf("Null \n");
			break;
		default:
			wprintf("Error in PATH codes in .DVI file %d\n",i);
			break;
	  }
	}
   wprintf("Finished");
	d_close();
}
void gle_abort(char *s)
{
	wprintf("%s",s);
	exit(1);
}
void path_send(void)
{
	int sx=0,sy=0,cx=0,cy=0,x1,y1,x2,y2,x3,y3;
	int i,j,p1,p2;

	d_newpath();
   dbg wprintf("=path send");
	for (i=0;i<npath;i++) {
	  switch(path[i]) {
	    case p_move:
		sx = path[++i];
		sy = path[++i];
		dbg wprintf("=path move");
		d_pmove(sx,sy);
		cx = sx; cy = sy;
		break;
		 case p_line:
		x1 = path[++i];
		y1 = path[++i];
		dbg wprintf("=pline %d %d \n",x1,y1);
		d_pline(x1,y1);
		cx = x1; cy = y1;
		break;
	    case p_bezier:
		x1 = path[++i];  y1 = path[++i];
		x2 = path[++i];  y2 = path[++i];
		x3 = path[++i];  y3 = path[++i];
		dbg wprintf("=pbezier %d %d   %d %d   %d %d\n",x1,y1,x2,y2,x3,y3);
		d_pbezier(cx,cy,x1,y1,x2,y2,x3,y3);
		cx = x3; cy = y3;
		break;
	    case p_closepath:
		dbg if (cx!=sx || cy!=sy) wprintf("=pclosepath %d %d \n",sx,sy);
		if (cx!=sx || cy!=sy) d_pline(sx,sy);
		cx = sx; cy = sy;
		break;
	    default:
		printf("Error in path_fill code path[%d] %d \n",i,path[i]);
	  }
	}
}
void path_fill(void)
{
	path_send();
   d_fill();
	//bmp_fill(bb);
}
void path_clip(void)
{
	//path_send();
	//bmp_clip(bb);
}
void path_stroke(void)
{
	int sx=0,sy=0,cx=0,cy=0,x1,y1,x2,y2,x3,y3;
	int i,j,p1,p2;

	//bmp_newpath(bb);
	for (i=0;i<npath;i++) {
	  switch(path[i]) {
	    case p_move:
		sx = path[++i];
		sy = path[++i];
		cx = sx; cy = sy;
		break;
	    case p_line:
		x1 = path[++i];
		y1 = path[++i];
		d_line(cx,cy,x1,y1);
		cx = x1; cy = y1;
		break;
	    case p_bezier:
		x1 = path[++i];  y1 = path[++i];
		x2 = path[++i];  y2 = path[++i];
		x3 = path[++i];  y3 = path[++i];
		d_bezier(cx,cy,x1,y1,x2,y2,x3,y3);
		cx = x3; cy = y3;
		break;
	    case p_closepath:
		if (cx!=sx || cy!=sy) d_line(cx,cy,sx,sy);
		cx = sx; cy = sy;
		break;
	    default:
		printf("Error in path_fill code path[%d] %d \n",i,path[i]);
	  }
	}
}
void path_move(int  x,int y)
{
	path_alloc();
	path[npath++] = p_move;
	path[npath++] = x;
	path[npath++] = y;
}
void path_line(int x,int y)
{
	path_alloc();
	path[npath++] = p_line;
	path[npath++] = x;
	path[npath++] = y;
}
void path_bezier(int x1, int y1, int x2, int y2,int x3, int y3)
{
	path_alloc();
	path[npath++] = p_bezier;
	path[npath++] = x1;	path[npath++] = y1;
	path[npath++] = x2;	path[npath++] = y2;
	path[npath++] = x3;	path[npath++] = y3;
}
void path_closepath(void)
{
	path_alloc();
	path[npath++] = p_closepath;
}
void path_alloc(void)
{
	static int npa;
	int *a;

	if (npath < (npath_alloc-10)) return;
	npath_alloc = 20 + 2 * npath;
	if (npath_alloc<300) npath_alloc = 300;
	wprintf("=== Allocate %d %d \n",npath_alloc,npath);
	a = (int *) calloc(1,npath_alloc*sizeof(int));
	if (a==NULL) {
		gle_abort("Unable to allocate memory for path \n");
	}
	if (path != NULL) {
		dbg wprintf("path reallocate, copy \n");
		memcpy(a,path,(npa)*sizeof(int));
		free(path);
	}
	npa = npath_alloc;
	path = a;
}
void path_free(void)
{
	if (path==NULL) return;
	free(path);
	path = NULL;
	npath = 0;
	npath_alloc = 0;
}

/*---------------------------------------------------------------------------*/
static HDC hdc;
static HBRUSH hbrush,hbrush_old;
static HPEN hpen,hpen_old;
static COLORREF pen_color;
static HWND hwndpic;
static int pen_width;
void d_open(double width, double height)
{
	double f,f1,f2,fx,fy;
	double d_scale;
	RECT rect;
	int nxbits,nybits,wstyle;
	pen_color = RGB(0,0,0);
	hbrush = CreateSolidBrush(pen_color);


	wstyle = WS_VISIBLE  | WS_CHILDWINDOW | WS_THICKFRAME;

   if (use_screen) {
		hwndpic = CreateWindow("simple","",wstyle
			,300,200,300,200
			,hwndmain, 0, hInst, NULL);
		if (hwndpic==NULL) { emsg("create failed"); return; }
		ShowWindow(hwndpic, SW_SHOW);
   	UpdateWindow(hwndpic);
		hdc = GetDC(hwndpic);
		GetClientRect(hwndpic,&rect);
      FillRect(hdc,&rect,GetStockObject(WHITE_BRUSH));
	} else {
		hdc = CreateMetaFile(TEMP_FILE);
	}
	GetClientRect(hwndpic,&rect);
	SetMapMode(hdc,MM_ANISOTROPIC);
	SetWindowExt(hdc,XBITS,YBITS);
	if (use_screen) {
		SetViewportExt(hdc,rect.right,-rect.bottom);
   	SetViewportOrg(hdc,0,rect.bottom);
	}

	if (hdc==0) wprintf("output hdc is null\n");
	if (hbrush==0)  wprintf("hdc is null\n");
   pen_width = 1;
	hpen = CreatePen(PS_SOLID,pen_width,pen_color);
	hpen_old = SelectObject(hdc,hpen);
	hbrush_old = SelectObject(hdc,hbrush);

	{devxcm = width; devycm = height;}
	nxbits = XBITS;
	nybits = YBITS;
	uxcm = width; uycm = height;

	d_scale = devxcm / width;
	f = devycm / height;
	if (f<d_scale) d_scale = f;

	fx = devxcm / width;
	d_scale = 1;
	fy = devycm / height;
	d_xscale = fx * (nxbits-2) / devxcm;
	d_yscale = fy * (nybits-2) / devycm;
}
void d_close(void)
{
	DeleteMetaFile(CloseMetaFile(hdc));
	DeleteObject(hbrush);
	wprintf("D_CLOSE Success -------\n");
	MessageBeep(0);
	metafile_fix();	// pre-pend fixup head info.
	path_free();
}
void d_line(int cx,int cy,int x,int y)
{
	MoveTo(hdc,cx,cy);
   LineTo(hdc,x,y);
}
void d_lwidth(int width)
{
   pen_width = width;
	DeleteObject(hpen);
	hpen = CreatePen(PS_SOLID,pen_width,pen_color);
	SelectObject(hdc,hpen);
}
void d_bezier(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3)
{
	float ax,bx,cx,ay,by,cy,xxx,yyy,t,nstep,xx,yy;
	int dist,i;

	dist = abs(x3-x0) + abs(y3-y0);
	nstep = 20;
	if (dist<30) nstep = 10;
	if (dist<10) nstep = 5;
	if (dist<5) nstep = 3;
	if (dist<=2) {
		d_line(x0,y0,x3,y3);
		return;
	}
	cx = (x1-x0)*3;
	bx = (x2-x1)*3-cx;
	ax = x3-x0-cx-bx;
	cy = (y1-y0)*3;
	by = (y2-y1)*3-cy;
	ay = y3-y0-cy-by;
	xx = x0; yy = y0;
	for (i=0;i<=nstep;i++) {
		t = (float) i/nstep;
		xxx = ax*pow(t,3.0) + bx*t*t + cx*t + x0;
		yyy = ay*pow(t,3.0) + by*t*t + cy*t + y0;
		d_line((int) xx,(int) yy, (int) xxx, (int) yyy);
		xx = xxx; yy = yyy;
	}
}
void d_pbezier(int x0, int y0, int x1, int y1, int x2, int y2, int x3, int y3)
{
	float ax,bx,cx,ay,by,cy,xxx,yyy,t,nstep;
	int dist,i;



	dbg wprintf("pbezier, %d %d   %d %d   %d %d   %d %d \n",x0,y0,x1,y1,x2,y2,x3,y3);
	dist = abs(x3-x0) + abs(y3-y0);
	nstep = 20;
	if (dist<30) nstep = 10;
	if (dist<10) nstep = 5;
	if (dist<5) nstep = 3;
	if (dist<=2) {
		d_pline(x3,y3);
		return;
	}
	cx = (x1-x0)*3;
	bx = (x2-x1)*3-cx;
	ax = x3-x0-cx-bx;
	cy = (y1-y0)*3;
	by = (y2-y1)*3-cy;
	ay = y3-y0-cy-by;
	for (i=0;i<=nstep;i++) {
		t = (float) i/nstep;
		xxx = ax*pow(t,3.0) + bx*t*t + cx*t + x0;
		yyy = ay*pow(t,3.0) + by*t*t + cy*t + y0;
		d_pline((int) xxx,(int) yyy);
	}
}

#define MAXPTS 8000
static POINT pts[MAXPTS];
static int ptscnt[100];
static int nptscnt,npts;
void d_newpath(void)
{
	nptscnt = 0;
   npts = 0;
}
static int startx,starty,inaline=false;
void d_pmove(int x, int y)
{
   if (inaline) if (npts>0) d_pclose();
	startx = x; starty = y;
	pts[npts].x = x;
	pts[npts++].y = y;
}
void d_pline(int x, int y)
{
	inaline = true;
	if (npts > (MAXPTS+20)) {wprintf("Too many points in path"); return;}
	pts[npts].x = x;
	pts[npts++].y = y;
}
void d_pclose(void)
{
   int diff;
	if (nptscnt==0) {
		diff = npts;
	} else {
		diff = npts-ptscnt[nptscnt-1];
	}
	if (diff>0)	{
		if ((startx != pts[npts-1].x) || (starty!=pts[npts-1].y)) {
      	   d_pline(startx,starty);
      }
		ptscnt[nptscnt++] = diff;
	}
   inaline = false;
}
void d_fill(void)
{
	if (inaline) d_pclose();
	wprintf("Polygon nptscnt %d  %d  x=%d y=%d",nptscnt,ptscnt[0],pts[0].x,pts[0].y);

	PolyPolygon(hdc,pts,ptscnt,nptscnt);
}
void d_lstyle(int cur_lstyle,int dot)
{
}
void d_setcolor(int r,int g,int b,int f) /* r,g,b,f */
{
	pen_color = RGB(r,g,b);

	SelectObject(hdc,hpen_old);
	SelectObject(hdc,hbrush_old);
	DeleteObject(hpen);
	DeleteObject(hbrush);

	hbrush = CreateSolidBrush(pen_color);
	hpen = CreatePen(PS_SOLID,pen_width,pen_color);
	SelectObject(hdc,hpen);
	SelectObject(hdc,hbrush);
}


int wprintf(char *fmt, ...)
{
   va_list argptr;
   int cnt;
	char buffer[2000],*s;
	HDC hdcm;
   int wstyle;
	static HWND hwndmsg;
   RECT rect;

   va_start(argptr, fmt);
   cnt = vsprintf(buffer, fmt, argptr);
   va_end(argptr);
//	MessageBox(hwndmain, buffer, "Debug", MB_OK);


	if (hwndmsg == 0) {
		wstyle = WS_VISIBLE  | WS_CHILDWINDOW | WS_THICKFRAME;
		hwndmsg = CreateWindow("simple","",wstyle
			,0,200,300,300
			,hwndmain, 0, hInst, NULL);
		if (hwndmsg==NULL) { emsg("create failed"); return; }
		ShowWindow(hwndmsg, SW_SHOW);
   	UpdateWindow(hwndmsg);
		hdcm = GetDC(hwndmsg);
		GetClientRect(hwndmsg,&rect);
      FillRect(hdcm,&rect,GetStockObject(WHITE_BRUSH));
		ReleaseDC(hwndmsg,hdcm);
	}

	ScrollWindow(hwndmsg,0,15,NULL,NULL);
	hdcm = GetDC(hwndmsg);
	s = strchr(buffer,'\n');
   if (s!=NULL) *s = 0;
   strcat(buffer,"                            ");
	TextOut(hdcm,0,0,buffer,strlen(buffer));
	ReleaseDC(hwndmsg,hdcm);

	return(cnt);
}


// pre-pend fixup header info.
typedef struct {
	DWORD key; HANDLE hmf;
	RECT bbox; WORD inch;
	DWORD reserved; WORD checksum;
} METAFILEHEADER;
void metafile_fix(void )
{
	WORD *w,xor=0;
   METAFILEHEADER mh;
	int i;
	HFILE hout,hin;
  	int sz; char buff[1001];

	mh.key = 0x9ac6cdd7L;
	mh.hmf = 0;
	mh.bbox.left = 0;
	mh.bbox.right = XBITS;
	mh.bbox.top = 0;
	mh.bbox.bottom = YBITS;
	mh.inch = 1000;
   mh.reserved = 0;
	w = &mh;
	for (i=0; i<10; i++,w++) {
		xor = xor ^ *w;
   }
   mh.checksum = xor;

	hout = _lcreat(OUT_FILE,0);
	if (hout == -1) { wprintf("Couldn't open output file "); return;}
	hin = _lopen(TEMP_FILE,OF_READ);
	if (hin == -1) { wprintf("Couldn't open input file"); return;}


	_lwrite(hout,&mh,sizeof(mh));
	for (;;) {
		sz = _lread(hin,buff,1000);
		_lwrite(hout,buff,sz);
		if (sz<1000) break;
   }
	if (_lclose(hin)) wprintf("Couldn't close input file");
	if (_lclose(hout)) wprintf("Couldn't close output file");
}

char emsg_saved[200];
void emsg(char *s)
{
	int i,j=0;
      wprintf("%s",s);
      return;

		for (i=0; i<10000; i++)
			for (j=0; j<1000; j++) ;

}
void do_delay(int tm)
{
	int i,j=0,k;
   	for (k=0; k<tm; k++)
		for (i=0; i<1000; i++)
			for (j=0; j<1000; j++) ;

}
