/*================================================
  portable.h  v1.00   Written by Scott Robert Ladd.

  _MSC_VER    Microsoft C 6.0 and later
  _QC         Microsoft Quick C 2.51 and later
  __TURBOC__  Borland Turbo C and Turbo C++
  __ZTC__     Zortech C and C++
  __WATCOMC__ WATCOM C

When using define one or more of the folowing
else nothing happens:
C:
#define P_POINTER
#define P_CONSOLE
#define P_DISP
#define P_FILE
#define P_IO
#define P_INT
#define P_MEM
#define P_SOUND
#define P_TIME
#define P_BIOS

C++:
#define P_STREAMS

=================================================*/

/* prevent multiple inclusions of this header file*/
#if !defined(__PORTABLE_H)
#define __PORTABLE_H

/* PORTABLE_TEST is only needed
   for debugging of the sections */
#undef PORTABLE_TEST

/* the following definitions are needed
   for compilation of HC*.*-project
*/
#define P_IO
#define P_TIME
#define P_STREAMS

#define ALL (defined(P_POINTER) || \
             defined(P_CONSOLE) ||\
       defined(P_DISP) || defined(P_FILE) || \
       defined(P_IO) || defined(P_MEM) || \
       defined(P_SOUND) || defined(P_TIME) || \
       defined(P_STREAMS) || defined(P_BIOS) || defined(P_INT))

#if !ALL
  #define P_POINTER
  #define P_CONSOLE
  #define P_DISP
  #define P_FILE
  #define P_IO
  #define P_MEM
  #define P_SOUND
  #define P_TIME
  #define P_BIOS
  #ifdef __cplusplus
    #define P_STREAMS
  #endif
#endif

#if defined(P_POINTER)
#ifdef PORTABLE_TEST
  #error adding portability for P_POINTER
#endif
/*------------------------------------------------
  Pointer-related macros
  MK_FP creates a far pointer
        from segment and offset values
-------------------------------------------------*/
/*------------------------------------------------
    Symbols for data-pointer-type
    __SDATA__  __LDATA__
    Symbols for code-pointer-type
    __SCODE__  __LCODE__

-------------------------------------------------*/
#ifndef __DOS_H
    #include <dos.h>
#endif
#if !defined(MK_FP)
    #define MK_FP(seg,off) \
      ((void far *)(((long)(seg)<<16)|(UINT)(off)))
#endif

#if !defined(__SDATA__) && !defined(__LDATA__)
  #if defined(__MEDIUM__) || \
      defined (__SMALL__) || \
      defined (__TINY__)

    #define __SDATA__ 1

  #endif
  #if defined(__COMPACT__) || \
      defined (__LARGE__) || \
      defined (__HUGE__)

    #define __LDATA__ 1

  #endif
#endif
#if !defined(__SCODE__) && \
    !defined(__LCODE__)

  #if defined(__COMPACT__) || \
      defined (__SMALL__) || \
      defined (__TINY__)

    #define __SCODE__ 1

  #endif
  #if defined(__MEDIUM__) || \
      defined (__LARGE__) || \
      defined (__HUGE__)

    #define __LCODE__ 1

  #endif
#endif

#ifndef NULL
  #if defined (__SDATA__)
    #define NULL 0
  #else
    #define NULL 0L
  #endif
#endif // NULL
#endif //(P_POINTER)

#if defined(P_CONSOLE)
#ifdef PORTABLE_TEST
  #error adding portability for P_CONSOLE
#endif
/*------------------------------------------------
    Console portability
-------------------------------------------------*/
#if defined(__TURBOC__)
  #include <constrea.h>
#endif
#if defined(__ZTC__)
  #include <constrea.hpp>
#endif
#ifdef _MSC_VER            
  #ifndef _INC_CONIO
    #include <conio.h>
  #endif
  //#ifndef _INC_GRAPH
  //  #include <graph.h>
  //#endif
  #define clrscr() _clearscreen(_GWINDOW)
#endif
#endif //P_CONSOLE

#if defined (P_DISP)
/*------------------------------------------------
    Subsitutes for ZORTECH Disp-Library
    disp_open()
    disp_move(x,y)
    disp_open()
    disp_printf
    disp_setattr(x)
    disp_eeop()
    disp_close()
-------------------------------------------------*/
#ifdef __ZTC__
  #include <disp.h>
#endif
#ifdef __TURBOC__
  #ifndef __DOS_H
    #include <conio.h>
  #endif
  #define disp_open()
  #define disp_close()
  #define disp_move(x,y) gotoxy((x),(y))
  #define disp_printf cprintf
  #define disp_setattr(x) textattr((x))
  #define disp_eeop() clrscr()
#endif
#endif //P_DISP

#if defined(P_FILE)
#ifdef PORTABLE_TEST
  #error adding portability for P_FILE
#endif
/*-----------------------------------------------
  Directory search macros and data structures

  DOSFileData MS-DOS file data structure
  FIND_FIRST  MS-DOS function 0x4E
  FIND_NEXT   MS-DOS function 0x4F
------------------------------------------------*/
/* make sure the structure
   is packed on byte boundary
*/
#if defined(_MSC_VER) ||\
    defined(_QC) || \
    defined(__WATCOMC__)

      #pragma pack(1)

#elif defined(__ZTC__)

    #pragma align 1

#elif defined(__TURBOC__)

    #pragma option -a-

#endif

/* use this structure in place of
   compiler-defined file structure */

typedef struct
    {
    char     reserved[21];
    char     attrib;
    unsigned time;
    unsigned date;
    long     size;
    char     name[13];
    }
    DOSFileData;

/* set structure alignment to default */
#if defined (_MSC_VER) || \
    defined(_QC) || \
    defined(__WATCOMC__)

    #pragma pack()

#elif defined(__ZTC__)

    #pragma align

#elif defined(__TURBOC__)

    #pragma option -a.

#endif

/* include proper header files and create macros */

#if defined(_MSC_VER) || \
    defined(_QC) || \
    defined(__WATCOMC__)

    #ifndef __DIRECT_H
      #include <direct.h>
    #endif
    #define FIND_FIRST(spec, attr, buf) \
      _dos_findfirst(spec, attr, (struct find_t *)buf) 
    #define FIND_NEXT(buf) \
      _dos_findnext((struct find_t *)buf)
#elif defined(__TURBOC__)
    #ifndef __DIR_H
      #include <dir.h>
    #endif
    #define FIND_FIRST(spec, attr, buf) \
      findfirst(spec, (struct ffblk *)buf, attr)
    #define FIND_NEXT(buf) \
      findnext((struct ffblk *)buf)
#elif defined(__ZTC__)
    #ifndef __DOS_H
      #include <dos.h>
    #endif
    #define FIND_FIRST(spec, attr, buf) \
dos_findfirst(spec, attr, (struct DOS_FIND *)buf)
    #define FIND_NEXT(buf) \
      dos_findnext((struct DOS_FIND *)buf)
#endif
#endif //P_FILE

#if defined(P_IO)
#ifdef PORTABLE_TEST
  #error adding portability for P_IO
#endif
/*-----------------------------------------------
    I/O Port Macros

    IN_PORT     read  byte from I/O port
    IN_PORTW    read  word from I/O port
    OUT_PORT    write byte  to  I/O port
    OUT_PORTW   write word  to  I/O port
------------------------------------------------*/
#if defined(__TURBOC__)
    #ifndef __DOS_H
      #include <dos.h>
    #endif
    #define IN_PORT(port)       inportb(port)
    #define IN_PORTW(port)      inport(port)
    #define OUT_PORT(port,val)  outportb(port,val)
    #define OUT_PORTW(port,val) outport(port,val)
#else
    #ifndef __CONIO_H
      #include <conio.h>
    #endif

    #define IN_PORT(port)       inp(port)
    #define IN_PORTW(port)      inpw(port)
    #define OUT_PORT(port,val)  outp(port,val)
    #define OUT_PORTW(port,val) outpw(port,val)
#endif

#if defined (__TURBOC__)

    #ifdef __SDATA__
      unsigned getDS(void);
      #define POKE(ds,do,data,sz) \
        movedata(getDS(),&(data),(ds),(do),(sz))
    #endif
    #ifdef __LDATA__
      #define POKE(ds,do,data,sz) \
        movedata(FP_SEG(&data),FP_OFF(&data),(ds),(do),(sz))
    #endif

#endif // __TURBOC__

#if defined (__ZTC__)
  #define poke POKE
#endif // __ZTC__
#endif //P_IO

#if defined(P_MEM)
#ifdef PORTABLE_TEST
  #error adding portability for P_MEM
#endif
/*------------------------------------------------
    memory access Port Macros
-------------------------------------------------*/
#if defined (__TURBOC__)

    #ifdef __SDATA__
      unsigned getDS(void);
      #define poke(ds,do,data,sz) \
        movedata(getDS(),&(data),(ds),(do),(sz))
    #endif
    #ifdef __LDATA__
      #define poke(ds,do,data,sz) \
        movedata(FP_SEG(&data),FP_OFF(&data),(ds),(do),(sz))
    #endif

  #endif // __TURBOC__

#if defined (__TURBOC__)
  #if !defined(__MEM_H) && !defined(__STRING_H)
    #include <mem.h>
  #endif
  #ifdef __SDATA__
    #define poke(ds,do,data,sz) \
      movedata(getDS(),(unsigned)(data),(ds),(do),(sz))
  #endif
  #ifdef __LDATA__
    #define poke(ds,do,data,sz) \
      movedata(FP_SEG(&data),FP_OFF(&data),(ds),(do),(sz))
  #endif

#endif // __TURBOC__
#endif //P_MEM

#if defined(P_SOUND)
#ifdef PORTABLE_TEST
  #error adding portability for P_SOUND
#endif
/*-----------------------------------------------
    Subsitutes for ZORTECH Sound-Library
    sound_beep(x)
    sound_click()
------------------------------------------------*/

#ifdef __ZTC__
  #include <sound.h>
#else
  #ifdef __TURBOC__
    #ifndef __DOS_H
      #include <dos.h>
    #endif
    #define sound_beep(x) \
      sound((x));delay(300);nosound()
    #define sound_click() \
      sound(100);delay(10);nosound()
  #endif
#endif
#endif //P_SOUND

#if defined(P_TIME)
#ifdef PORTABLE_TEST
  #error adding portability for P_TIME
#endif
/*-----------------------------------------------
    time Port Macros
------------------------------------------------*/
#if defined (__TURBOC__)
#endif

#if defined (__ZTC__)
  #define delay(x) msleep(x)
#endif
#if defined (_MSC_VER)
  #ifndef _INC_DOS
    #include <dos.h>
  #endif
  void delay(unsigned ms)
  {                      
    union _REGS r;
    unsigned long us = ms * 1024L;
    r.h.ah = 0x86;
    r.h.al = 0;
    r.x.cx = (unsigned)(us/65536L);
    r.x.dx = (unsigned)(us%65536L);
    _int86(0x15,&r,&r);
  }
#endif
#endif //P_TIMER


#if defined(P_INT)
#ifdef PORTABLE_TEST
  #error adding portability for P_INT
#endif
/*-----------------------------------------------
    int Port Macros
------------------------------------------------*/
#if defined (__TURBOC__)
#endif

#if defined (_MSC_VER)
  #define setvect _dos_setvect
  #define getvect _dos_getvect
  #define disable _disable
  #define enable _enable
  #define asm __asm
#endif
#endif //P_INT


#if defined(P_BIOS)
#ifdef PORTABLE_TEST
  #error adding portability for P_TIME
#endif
/*-----------------------------------------------
    BIOS Port Macros
------------------------------------------------*/
#if defined (__TURBOC__)
#endif

#if defined (_MSC_VER)
  #define bioskey  _bios_keybrd
#endif
#endif //P_BIOS


#ifdef __cplusplus

#if defined(P_STREAMS)
#ifdef PORTABLE_TEST
  #error adding portability for P_STREAMS
#endif
/*-----------------------------------------------
    Portable Streams

------------------------------------------------*/
#if defined(__TURBOC__)
  #include <iostream.h>
  #include <iomanip.h>
#endif
#if defined (__ZTC__)
  #include <iostream.hpp>
#endif
#endif //P_STREAMS

#endif //__cpluscplus

//#endif
#endif // __PORTABLE_H

