home *** CD-ROM | disk | FTP | other *** search
/ Liren Large Software Subsidy 5 / 05.iso / a / a011 / 2.ddi / DESXBTRV.C < prev    next >
Encoding:
C/C++ Source or Header  |  1986-12-05  |  5.3 KB  |  188 lines

  1.  
  2. /*                                    */
  3. /* DeSmet C (C-Ware) interface to the Btrieve Record Manager, version 4 */
  4. /*                                    */
  5.  
  6. struct REGVAL { int AX, BX, CX, DX, SI, DI, D_SEG, E_SEG; };
  7.  
  8. struct SEGREG { int CS, SS, DS, ES; };
  9.  
  10. segread (sreg)
  11. struct SEGREG *sreg;
  12. {
  13. #asm
  14.     mov    bx,[bp+4]    ;address of return structure
  15.     mov    [bx],cs
  16.     mov    [bx+2],ss
  17.     mov    [bx+4],ds
  18.     mov    [bx+6],es
  19. #
  20. }
  21.  
  22. peek (offset, segment)
  23. unsigned offset, segment;
  24. {
  25. #asm
  26.     push    es        ;save es
  27.     mov    bx,[bp+4]    ;offset
  28.     mov    es,[bp+6]    ;segment
  29.     mov    ax,es:[bx]    ;what's the word?
  30.     pop    es        ;restore es
  31. #
  32. }
  33.  
  34. sysint(int_vector, regs_before, regs_after)
  35. unsigned int_vector;
  36. struct REGVAL *regs_before, *regs_after;
  37.   {
  38. #asm
  39.     mov    ax,[bp+4]    ;interrupt type
  40.     mov    cs:vec_id+1,al    ;modify the INT instruction
  41.     mov    bx,[bp+6]    ;address of register contents
  42.     push    ds        ;save ds
  43.     mov    ax,[bx]     ;load ax
  44.     mov    cx,[bx+2]    ;save bx
  45.     push    cx        ; on the stack
  46.     mov    cx,[bx+4]    ;load cx
  47.     mov    dx,[bx+6]    ;load dx
  48.     mov    si,[bx+8]    ;load si
  49.     mov    di,[bx+10]    ;load di
  50.     mov    ds,[bx+12]    ;load ds
  51.     mov    es,[bx+14]    ;load es
  52.     pop    bx        ;load bx
  53. vec_id: int    00h        ;the interrupt instruction
  54.     pop    ds        ;restore ds
  55.     push    bx        ;save bx
  56.     mov    bx,[bp+8]    ;address of register contents
  57.     mov    [bx],ax     ;store ax
  58.     pop    ax        ;get saved value of bx
  59.     mov    [bx+02],ax    ;store bx
  60.     mov    [bx+04],cx    ;store cx
  61.     mov    [bx+06],dx    ;store dx
  62.     mov    [bx+08],si    ;store si
  63.     mov    [bx+10],di    ;store di
  64.     mov    [bx+12],ds    ;store ds
  65.     mov    [bx+14],es    ;store es
  66. #
  67. }
  68.  
  69. /* ProcId is used for communicating with the Multi Tasking Version of  */
  70. /* Btrieve. It contains the process id returned from BMulti and should */
  71. /* not be changed once it has been set.                    */
  72. /*                                       */
  73. int ProcId = 0;             /* initialize to no process id */
  74. char MULTI = 0;
  75. char VSet = 0;
  76.  
  77. BTRV (OP, POS_BLK, DATA_BUF, DATA_LEN, KEY_BUF, KEY_NUM)
  78.   int  OP;
  79.   char POS_BLK[];
  80.   char DATA_BUF[];
  81.   int  *DATA_LEN;
  82.   char KEY_BUF[];
  83.   int  KEY_NUM;
  84.  
  85. {
  86. #define BTR_ERR     20           /* record manager not started */
  87. #define BTR_VECTOR  0x7B * 4       /* offset for interrupt */
  88. #define VARIABLE_ID 0x6176       /* id for variable length records - 'va' */
  89. #define POS_LEN_ERR 23           /* invalid position block length */
  90.  
  91. struct REGVAL REGS;           /* register values for sysint function */
  92. struct SEGREG SREGS;           /* current contents of the segment regs */
  93.  
  94. struct BTRIEVE_PARMS           /* structure passed to Record Man */
  95.   {char *USER_BUF_OFFSET;       /* callers data buffer offset */
  96.    int    USER_BUF_SEG;           /* callers data buffer segment */
  97.    int    USER_BUF_LEN;           /* length of data buffer */
  98.    char *USER_CUR_OFFSET;       /* user position block offset */
  99.    int    USER_CUR_SEG;           /* user position block segment */
  100.    char *USER_FCB_OFFSET;       /* offset of disk FCB */
  101.    int    USER_FCB_SEG;           /* segment of disk FCB */
  102.    int    USER_FUNCTION;           /* requested function */
  103.    char *USER_KEY_OFFSET;       /* offset of user's key buffer */
  104.    int    USER_KEY_SEG;           /* segment of user's key buffer */
  105.    char USER_KEY_LENGTH;       /* length of user's key buffer */
  106.    char USER_KEY_NUMBER;       /* key of reference for request */
  107.    int    *USER_STAT_OFFSET;       /* offset of status word */
  108.    int    USER_STAT_SEG;           /* segment of status word */
  109.    int    XFACE_ID;};           /* language identifier */
  110.  
  111. struct BTRIEVE_PARMS XDATA;
  112. int    STAT;               /* status of Btrieve call */
  113.  
  114. /*                                    */
  115. /*  Check to see that the Btrieve Record Manager has been started.    */
  116. /*                                    */
  117.  
  118. REGS.AX = 0x357B;
  119. sysint (0x21, ®S, ®S);
  120. if (REGS.BX != 0x33)
  121.    return (BTR_ERR);
  122.  
  123. if (!VSet)
  124.  {
  125.   VSet = 1;
  126.   REGS.AX = 0x3000;
  127.   sysint (0x21, ®S, ®S);
  128.   if ((REGS.AX & 0x00FF) >= 3)
  129.    {
  130.     REGS.AX = 0xAB00;
  131.     sysint(0x2F, ®S, ®S);
  132.     MULTI = ((REGS.AX & 0x00FF) == 'M');
  133.    }
  134.  }
  135.  
  136. /*  Read segment registers and initialize segment part of addresses to    */
  137. /*  user's data segment.                                                */
  138. /*                                    */
  139.  
  140. segread(&SREGS);
  141. XDATA.USER_BUF_SEG = XDATA.USER_CUR_SEG = XDATA.USER_FCB_SEG =
  142.   XDATA.USER_KEY_SEG = XDATA.USER_STAT_SEG = SREGS.DS;
  143.  
  144. /*                                    */
  145. /*  Move user parameters to XDATA, the block where Btrieve expects them.*/
  146. /*                                    */
  147.  
  148. XDATA.USER_FUNCTION = OP;
  149. XDATA.USER_STAT_OFFSET = &STAT;
  150. XDATA.USER_FCB_OFFSET = POS_BLK;
  151. XDATA.USER_CUR_OFFSET = POS_BLK + 38;
  152. XDATA.USER_BUF_OFFSET = DATA_BUF;
  153. XDATA.USER_BUF_LEN    = *DATA_LEN;
  154. XDATA.USER_KEY_OFFSET = KEY_BUF;
  155. XDATA.USER_KEY_LENGTH = 255;         /* use max since we don't know */
  156. XDATA.USER_KEY_NUMBER = KEY_NUM;
  157. XDATA.XFACE_ID          = VARIABLE_ID;
  158.  
  159. /*                                      */
  160. /*  Make call to Btrieve Record Manager                   */
  161. /*                                      */
  162.  
  163. REGS.DX = (unsigned) &XDATA;   /* parameter block is expected to be in DX */
  164. REGS.D_SEG = SREGS.DS;
  165. REGS.E_SEG = SREGS.ES;
  166. if (!MULTI)
  167.   sysint(0x7b, ®S, ®S);
  168. else
  169.  {
  170.   while (1)
  171.    {
  172.     REGS.AX = 1;              /* initialize to no process id  */
  173.     if ((REGS.BX = ProcId) != 0)      /* have a process id already?   */
  174.       REGS.AX = 2;              /* yes, make sure BMulti knows  */
  175.     REGS.AX += 0xAB00;
  176.     sysint(0x2F, ®S, ®S);
  177.     if ((REGS.AX & 0x00FF) == 0) break;
  178.     REGS.AX = 0x0200;
  179.     sysint(0x7F, ®S, ®S);
  180.    }
  181.   if (ProcId == 0)              /* Did we need a PID?       */
  182.     ProcId = REGS.BX;              /* Yes, save it for next call   */
  183.  }
  184.  
  185. *DATA_LEN = XDATA.USER_BUF_LEN;
  186. return(STAT);
  187. }
  188.