#ifndef __CLIENT_H__
#define __CLIENT_H__

/* 
 * Copyright (C) 1995 under GPL: Wayne Meissner
 * 
 * $Author$
 * $Date$
 * $Source$
 * $Revision$
 * 
 */

#include <unistd.h>
#include <sys/shm.h>
#include "client_server.h"

extern int server_init (void);
extern void server_exit (void);
extern struct daemon_server * server;
extern int server_fd;

/* use all the LWORD, HI, LO, REG macros from cpu.h from dosemu */
#if 0
#include "cpu.h"
#else
/* the following are from dosemu's cpu.h */

/* this is used like: REG(eax) = 0xFFFFFFF */
#define REG(reg) (REGS.##reg)

/* these are used like:  LO(ax) = 2 (sets al to 2) */
#define LO(reg)  (*(unsigned char *)&REG(e##reg))
#define HI(reg)  (*((unsigned char *)&REG(e##reg) + 1))

#define _LO(reg) (*(unsigned char *)&(scp->e##reg))
#define _HI(reg) (*((unsigned char *)&(scp->e##reg) + 1))

/* these are used like: LWORD(eax) = 65535 (sets ax to 65535) */
#define LWORD(reg)      (*((unsigned short *)&REG(reg)))
#define HWORD(reg)      (*((unsigned short *)&REG(reg) + 1))

#define _LWORD(reg)     (*((unsigned short *)&(scp->##reg)))
#define _HWORD(reg)     (*((unsigned short *)&(scp->##reg) + 1))

/* this is used like: SEG_ADR((char *), es, bx) */
#define SEG_ADR(type, seg, reg)  type((LWORD(seg) << 4) + LWORD(e##reg))
#endif

#undef REGS
#define REGS server->regs

inline void signal_server (void) {
  static DataHeader hdr;
  static int len = sizeof (hdr.len);
  hdr.len = 0;
//  cerr << "signalling server" << endl;
  write (server_fd, &hdr, len);
}

inline void wait_server (void) {
  static DataHeader hdr;
  static int len = sizeof (hdr.len);
//  cerr << "waiting for server" << endl;
  read (server_fd, &hdr, len);
}
  
inline void call_dosemu (void) {
  signal_server ();
  wait_server();
}

extern int32 Daemon_int86 (uint16 ivec);
extern int32 Daemon_int86 (uint16 ivec, vm86_regs * in, vm86_regs * out);
extern int32 Daemon_putmem (uint16 dseg, uint16 doff, const void * src, uint32 len);
extern int32 Daemon_putmem (DaemonMemInfo * dest, const void * src);
extern int32 Daemon_getmem (void * dest, uint16 sseg, uint16 soff, uint32 len);
extern int32 Daemon_getmem (void * dest, DaemonMemInfo * src);
extern void Daemon_spawn (char * cmd);

#ifndef offsetof
#define offsetof(type, member) ((size_t)&((type *)0)->member)
#endif

#define DOS_AX LWORD(eax)
#define DOS_BX LWORD(ebx)
#define DOS_CX LWORD(ecx)
#define DOS_DX LWORD(edx)
#define DOS_SI LWORD(esi)
#define DOS_DI LWORD(edi)
#define DOS_DS LWORD(ds)
#define DOS_ES LWORD(es)
#define DOSREGS REGS

#define CARRY_SET ((LWORD(eflags) & 0x1) == 0x1)
#define DOS_FL LWORD(eflags)
#define DOS_ARG server->daemon_comm.arg
#define DOS_CMD server->daemon_comm.command
#define DOS_BUFFER server->daemon_comm.buf

#endif /* __CLIENT_H__ */
