home *** CD-ROM | disk | FTP | other *** search
/ Power-Programmierung / CD1.mdf / basic / compiler / ubasic / ubmpqs32 / mpqshd4.asm < prev    next >
Assembly Source File  |  1990-08-05  |  18KB  |  1,177 lines

  1. ;MPQSHD4.ASM 3.2
  2. ;    MACHINE LANGUAGE SUBROUTINE
  3. ;    FOR MULTIPLE POLYNOMIAL QUADRATIC SIEVE
  4. ;    hard disk verion
  5. ;    1989/90 by YUJI KIDA
  6. ;
  7. .386p
  8.  
  9. code    segment    use16
  10.     assume    cs:code,ds:code
  11.  
  12.     org    100h
  13. start:
  14.  
  15.     INCLUDE    UBP.MAC
  16.     include    mpqshd.h
  17.  
  18.  
  19. GaussShort    macro reg
  20.     push    cx
  21.     and    reg,0000ffffh
  22.     mov    cl,[unitshift]
  23.     shl    reg,cl
  24.     add    reg,GaussShortadr
  25.     pop    cx
  26. endm    
  27.  
  28. GaussMini    macro reg
  29.     and    reg,0000ffffh
  30.     add    reg,GaussMiniadr
  31. endm    
  32.  
  33.  
  34.     JMP    start0
  35.  
  36.     align    4
  37. GaussLongadr    dd    ?
  38. unitmask    dd    0
  39. unitbytes    dd    0
  40. unitcolumns    dw    0
  41. unitwords    dw    0
  42. unitdwords    dw    0
  43. unitshift    db    0,0
  44.  
  45. start_column    dw    ?
  46. current_wordimg    dw    ?
  47. current_wordptr    dw    ?
  48. current_row    dw    ?
  49. start_row    dw    ?
  50. checking_row    dw    ?
  51. rank_now    dw    ?
  52.  
  53. primes        dw    ?
  54.  
  55. matrix_size    dw    ?
  56.  
  57. handle        dw    ?
  58. handle1        dw    ?
  59. size1        dw    ?
  60. handle2        dw    ?
  61. size2        dw    ?
  62. handle3        dw    ?
  63. size3        dw    ?
  64. handle4        dw    ?
  65.  
  66. loadallcount    dw    ?
  67.  
  68. work_seg    dw    ?
  69. ans_seg        dw    ?
  70.  
  71. P_OFF        dw    ?
  72. P_SEG        dw    ?
  73. primeadrnow    dd    ?
  74. y_off        dw    ?
  75. y_seg        dw    ?
  76.  
  77. offnow        dw    ?
  78.  
  79. refer_adr    dd    ?
  80.  
  81. allbytes    dw    0,0    ;2nd is a dummy
  82. allwords    dw    ?
  83. alldwords    dw    ?
  84. halfbytes    dw    ?
  85. halfwords    dw    ?
  86.  
  87. RWadr        dw    ?
  88. RWrow        dw    ?
  89.  
  90.  
  91. ;üÖüÖ COMMAND é╠ÉUéΦò¬é»
  92.  
  93.  
  94. START0:
  95.     MOV_AX    AR0        ;ARRAY[0] é┼âRâ}âôâhôné╡
  96.     MOV    BX,OFFSET CMD_TBL
  97.     SHL    AX,1
  98.     ADD    BX,AX
  99.     JMP    CS:[BX]
  100.  
  101. CMD_TBL:
  102.     DW    gauss_INIT,GETPRIME,Gauss,CLOSE_FILE
  103.     DW    SQUARE_ANS,GET_DIV
  104.  
  105. ;
  106. ; get and set primes
  107. ;
  108. ;command#=1
  109.  
  110. getprime:
  111.     lds    si,dword ptr cs:[P_OFF]
  112.     mov    edi,dword ptr cs:[primeadrnow]
  113.     lodsw
  114.     cmp    ax,2
  115.     je    getprime4B
  116.     xor    eax,eax
  117.     mov    ax,[si]
  118. getprime10:
  119.     mov    fs:[edi],eax
  120.     add    cs:[primeadrnow],4
  121.     mov    ax,ss
  122.     mov    ds,ax
  123.     retf
  124. getprime4B:
  125.     mov    eax,[si]
  126.     jmp    getprime10
  127.  
  128.  
  129. ;
  130. ;üÖüÖ GaussÅ┴ïÄé╔éµé┴é─ô╛éτéΩé╜ò╜ò√Éöé≡ò╘é╖
  131. ;     ans#(0) é╔ BIT PATTERN é≡ò╘é╖
  132.  
  133. ;COMMAND#=4
  134.  
  135. SQUARE_ANS:
  136.     mov    ax,cs
  137.     mov    ds,ax
  138.     mov    es,ax
  139. ans_again:
  140.     mov    ax,[start_row]
  141.     inc    ax
  142.     mov    [start_row],ax
  143.     dec    ax
  144.     cmp    ax,[matrix_size]
  145.     JAE    NO_ANS
  146.  
  147.     mov    [RWrow],ax
  148.     mov    [RWadr],offset buffer1
  149.     call    load_row
  150.     
  151.     mov    si,offset buffer1
  152.     mov    cx,[halfbytes]
  153.     add    si,cx        ;si = buffer1 + halfbytes
  154.     mov    di,si
  155.     add    di,cx        ;di = buffer1 + 2*halfbytes - 2
  156.     sub    di,2        ;   = highest word adr
  157.     shr    cx,1
  158.  
  159.     mov    ax,ds
  160.     mov    es,ax
  161.     xor    ax,ax
  162.     std
  163.     repe    scasw
  164.     cld
  165.  
  166.     je    ans_again    ;illegal answer
  167.     inc    cx        ;WORDS
  168.     mov    es,[ans_seg]
  169.     xor    di,di
  170.     MOV    AX,CX
  171.     STOSW            ;attribute
  172.     REP    MOVSW
  173. ans100:
  174.     MOV    AX,SS
  175.     MOV    DS,AX
  176.     MOV    ES,AX
  177.     RETF
  178.  
  179.  
  180. NO_ANS:
  181.     mov    bx,AR0
  182.     mov    word ptr cs:[bx],0
  183.     JMP    ANS100
  184.  
  185.  
  186. ;
  187. ;üÖüÖ Y é≡æfê÷Éöò¬ë≡é╡ï╨ÄwÉöé≡ïüé▀éΘ
  188. ; completely decomposed if no bug
  189. ; COMMAND#=5
  190. ; INPUT Y
  191. ; OUTPUT WORK%()
  192.  
  193. GET_DIV:
  194.     PUSH    BP
  195.  
  196.     LDS    SI,DWORD PTR CS:[Y_OFF]
  197.     MOV    BX,SI            ;MEMO èäéτéΩéΘÉö
  198.  
  199.     mov    edi,primeadr2+4        ;offset of 2
  200.     MOV    CS:[OFFNOW],0        ;offset in work%
  201.  
  202.     STD
  203.  
  204.     mov    ax,[bx]        ;transfer to 32bit format
  205.     test    al,1
  206.     jz    gdiv3200    ;if even words
  207.     mov    si,bx
  208.     mov    dx,ax
  209.     SHL    dX,1
  210.     add    si,dx        ;highest adr
  211.     mov    word ptr [si+2],0
  212.     inc    ax
  213. gdiv3200:
  214.     shr    ax,1
  215.     mov    [bx],ax
  216.  
  217.     MOV    CX,CS:[primes]
  218. gdiv32LP:
  219.     PUSH    CX
  220.  
  221.     MOV    eBP,fs:[eDI]    ;ebp=èäéΘÉö
  222.     add    cs:[offnow],2    ;offset in work%
  223. gdiv3210:
  224.     MOV    SI,BX
  225.     MOV    AX,[SI]
  226.     MOV    CX,AX        ;dword length
  227.     SHL    AX,2
  228.     sub    ax,2
  229.     ADD    SI,AX        ;ì┼Åπê╩
  230.     XOR    eDX,eDX    
  231. gdiv3220:
  232.     LODSd
  233.     DIV    eBP
  234.     LOOP    gdiv3220
  235.  
  236.     OR    eDX,eDX
  237.     JZ    gdiv32100        ;èäéΦÉ╪éΩé╜ÅΩìçé═û{ôûé╔èäéΘ
  238.  
  239.     add    edi,4
  240.     POP    CX
  241.     LOOP    gdiv32LP
  242.     jmp    gdivret
  243.  
  244.  
  245. gdiv32100:
  246.     MOV    AX,DS
  247.     MOV    DS,CS:[work_seg]
  248.     MOV    SI,CS:[OFFNOW]
  249.     INC    WORD PTR [SI]
  250.     MOV    DS,AX
  251.  
  252.     MOV    SI,BX
  253.     MOV    AX,[SI]
  254.     MOV    CX,AX        ;dword length
  255.     SHL    AX,2
  256.     sub    ax,2
  257.     ADD    SI,AX        ;ì┼Åπê╩
  258.     XOR    eDX,eDX    
  259.  
  260.     LODSd
  261.     DIV    eBP
  262.     PUSH    eAX        ;ì┼Åπê╩é╠Æl
  263.     JMPS    gdiv32120
  264. gdiv32110:
  265.     LODSd
  266.     DIV    eBP
  267. gdiv32120:
  268.     MOV    [SI+4],eAX
  269.     LOOP    gdiv32110
  270.  
  271.     POP    eAX        ;ì┼Åπê╩é╠Æl
  272.     OR    eAX,eAX
  273.     JNZ    gdiv32130
  274.     mov    ax,[bx]        ;ì┼Åπê╩鬠0 é╚éτé╬ LEN é≡ DEC
  275.     dec    ax
  276.     mov    [bx],ax
  277.     cmp    ax,1
  278.     jne    gdiv32130
  279.     mov    eax,[bx+2]
  280.     dec    eax
  281.     jz    gdivfin        ;already 1
  282. gdiv32130:
  283.     JMP    gdiv3210
  284.  
  285. gdivfin:
  286.     pop    cx        ;dummy
  287. gdivout:
  288.     POP    BP
  289.     CLD
  290.     MOV    AX,SS
  291.     MOV    DS,AX
  292.     MOV    ES,AX
  293.     RETF
  294.  
  295. gdivret:            ;not enter here if no bug
  296.     mov    si,bx        ;transfer to 16bit format
  297.     mov    ax,[si]
  298.     shl    ax,1
  299.     mov    cx,ax        ;word length?
  300.     shl    ax,1
  301.     add    si,ax
  302.     cmp    word ptr [si],0    ;check highest word
  303.     jne    gdiv32300
  304.     dec    cx
  305. gdiv32300:
  306.     mov    [bx],cx        
  307.     jmp    gdivout
  308.  
  309.  
  310. ;
  311. ;üÖüÖ éfé`étérérÅ┴ïÄû@
  312. ;
  313. ;COMMAND#=2
  314. ;      eliminate each 128 columns
  315.  
  316. Gauss:
  317.     mov    ax,cs
  318.     mov    ds,ax
  319.     mov    es,ax
  320.  
  321.     call    load_all
  322.     call    make_unit_matrix_1
  323.     mov    ax,[current_row]
  324.     sub    ax,[start_row]
  325.     jz    gauss_allzero
  326.     mov    [rank_now],ax
  327.     call    make_unit_matrix_2
  328.     call    erase_below
  329.     mov    ax,[rank_now]
  330.     add    [start_row],ax
  331. gauss_allzero:
  332.     mov    ax,[unitcolumns]
  333.     sub    [start_column],ax
  334.  
  335.     mov    ax,ss
  336.     mov    ds,ax
  337.     mov    es,ax
  338.     retf
  339.  
  340.  
  341. erase_below:
  342.     mov    ax,[start_row]
  343.     add    ax,[rank_now]
  344.     mov    [checking_row],ax
  345.     mov    cx,[matrix_size]
  346.     sub    cx,ax
  347.     mov    bx,ax        ;[checking_row]
  348.     GaussMini    ebx
  349.  
  350. erase_loop:
  351.     cmp    byte ptr fs:[ebx],0
  352.     je    erase_below50
  353.  
  354.     push    ebx
  355.     push    cx
  356.  
  357.     mov    ax,[checking_row]
  358.     mov    [RWrow],ax
  359.     mov    [RWadr],offset BUFFER1
  360.     call    load_row
  361.  
  362.     call    make_xor
  363.  
  364.     mov    ax,[checking_row]
  365.     mov    [RWrow],ax
  366.     mov    [RWadr],offset BUFFER1
  367.     call    save_row
  368.  
  369.     pop    cx
  370.     pop    ebx
  371.  
  372. erase_below50:
  373.     inc    ebx
  374.     inc    [checking_row]
  375.     loop    erase_loop
  376.     ret
  377.  
  378.  
  379. make_xor:
  380.     xor    ebx,ebx
  381.     mov    bx,[start_column]
  382.     shr    bx,3
  383.     and    bl,0feh
  384.  
  385.     mov    cx,[unitwords]
  386. makexor10:
  387.     push    cx
  388.     mov    dx,8000h
  389. makexor15:
  390.     test    word ptr [BUFFER1+bx],dx
  391.     jz    makexor60
  392.  
  393.     push    dx
  394.     xor    eax,eax
  395.     mov    ax,[rank_now]
  396.     dec    ax
  397.     mov    edx,dword ptr [allbytes]
  398.     mul    edx
  399.     add    eax,GaussLongadr
  400.     mov    esi,eax
  401.     pop    dx
  402. makexor20:
  403.     test    fs:[esi+ebx],dx
  404.     jnz    makexor25
  405.     sub    esi,dword ptr [allbytes]
  406.     jmp    makexor20
  407. makexor25:
  408.     xor    edi,edi
  409.     mov    cx,[alldwords]
  410. makexor30:
  411.     mov    eax,fs:[esi+edi]
  412.     xor    dword ptr [BUFFER1+di],eax
  413.     add    edi,4
  414.     loop    makexor30    
  415. makexor60:
  416.     shr    dx,1
  417.     jnc    makexor15
  418.  
  419.     sub    bx,2
  420.     pop    cx
  421.     loop    makexor10
  422.     ret
  423.  
  424.  
  425. make_unit_matrix_2:
  426.     ;rewrite RAM matrix by full image
  427.  
  428.     mov    [current_row],0
  429.  
  430.     mov    ax,[start_column]
  431.     shr    ax,3
  432.     and    al,0feh
  433.     mov    [current_wordptr],ax
  434.     mov    [current_wordimg],8000h
  435.     mov    cx,[rank_now]
  436. makeunit2_main_loop:
  437.     push    cx
  438.  
  439. ;    check current row
  440.  
  441.     xor    eax,eax
  442.     mov    ax,[current_row]
  443.     mov    [checking_row],ax
  444.     mov    edx,dword ptr [allbytes]
  445.     mul    edx
  446.     add    eax,GaussLongadr
  447.     mov    edi,eax
  448.  
  449.     xor    ebx,ebx
  450.     mov    bx,[current_wordptr]
  451.     mov    ax,[current_wordimg]
  452.     test    fs:[edi+ebx],ax
  453.     jz    makeunit2_next_column2    ;all zero
  454.  
  455.     mov    ax,[checking_row]
  456.     inc    ax
  457.     mov    [checking_row],ax
  458.     mov    cx,[rank_now]
  459.     sub    cx,ax            ;# of other rows
  460.     jz    makeunit2_next_column    ;already last row
  461.  
  462.     xor    eax,eax
  463.     mov    ax,[current_row]
  464.     mov    edx,dword ptr [allbytes]
  465.     mul    edx
  466.     add    eax,GaussLongadr
  467.     mov    esi,eax
  468.  
  469. makeunit2_110:
  470.     push    cx
  471.  
  472.     add    edi,dword ptr [allbytes]
  473.  
  474. ;    check next rows
  475.  
  476.     mov    ax,[current_wordimg]
  477.     test    fs:[edi+ebx],ax
  478.     jz    makeunit2_130        ;skip if 0
  479.  
  480. ;    if nonzero then take xor
  481.  
  482.     mov    cx,[alldwords]
  483. makeunit2_120:
  484.     mov    eax,fs:[esi]
  485.     xor    fs:[edi],eax
  486.     add    esi,4
  487.     add    edi,4
  488.     loop    makeunit2_120
  489.     sub    esi,dword ptr [allbytes]
  490.     sub    edi,dword ptr [allbytes]
  491.  
  492. makeunit2_130:
  493.     pop    cx
  494.     loop    makeunit2_110
  495.  
  496. makeunit2_next_column:
  497.     inc    [current_row]
  498.     ror    [current_wordimg],1
  499.     jnc    makeunit2_190
  500.     sub    [current_wordptr],2
  501. makeunit2_190:
  502.     pop    cx
  503.     dec    cx
  504.     jz    makeunit2_ret
  505.     jmp    makeunit2_main_loop
  506. makeunit2_ret:
  507.     ret
  508.  
  509. makeunit2_next_column2:
  510.     ror    [current_wordimg],1
  511.     jnc    makeunit2_210
  512.     sub    [current_wordptr],2
  513. makeunit2_210:
  514.     pop    cx        ;don't dec
  515.     jmp    makeunit2_main_loop
  516.  
  517.  
  518. make_unit_matrix_1:
  519.     ;rewrite RAM matrix by partial image
  520.  
  521.     mov    eax,GaussLongadr
  522.     mov    [refer_adr],eax
  523.  
  524.     ;* eliminate unitbytes*matrix_size
  525.  
  526.     mov    ax,[start_row]
  527.     mov    [current_row],ax
  528.     mov    ax,[start_column]
  529.     shr    ax,3
  530.     and    al,0feh
  531.     mov    [current_wordptr],ax
  532.     mov    [current_wordimg],8000h
  533.     mov    cx,[unitcolumns]
  534. makeunit10:
  535.     push    cx
  536.  
  537. ;    check current row
  538.  
  539.     mov    di,[current_row]
  540.     mov    [checking_row],di
  541.     GaussShort    edi
  542.  
  543.     mov    bx,[current_wordptr]
  544.     and    ebx,[unitmask]
  545.     mov    ax,[current_wordimg]
  546.     test    fs:[ebx+edi],ax
  547.     jz    makeunit20
  548.  
  549.     mov    ax,[current_row]    ;current is nonzero
  550.     mov    [RWrow],ax
  551.     mov    [RWadr],offset BUFFER2
  552.     call    load_row
  553.     jmp    makeunit60
  554.  
  555. makeunit20:
  556.     ;search nonzero
  557.  
  558.     mov    cx,[matrix_size]
  559.     sub    cx,[current_row]
  560.     dec    cx        ;# of other rows
  561. makeunit30:
  562.     inc    [checking_row]
  563.     add    edi,[unitbytes]
  564.     test    fs:[ebx+edi],ax
  565.     jnz    makeunit40        ;found nonzero
  566.     loop    makeunit30
  567.     jmp    makeunit_next_column2    ;all zero
  568.  
  569. makeunit40:
  570.     ;exchange these two
  571.     ;exchange files
  572.  
  573.     mov    ax,[current_row]
  574.     mov    [RWrow],ax
  575.     mov    [RWadr],offset BUFFER1
  576.     call    load_row
  577.  
  578.     mov    ax,[checking_row]
  579.     mov    [RWrow],ax
  580.     mov    [RWadr],offset BUFFER2
  581.     call    load_row
  582.  
  583.     mov    ax,[checking_row]
  584.     mov    [RWrow],ax
  585.     mov    [RWadr],offset BUFFER1
  586.     call    save_row
  587.  
  588.     ;exchange short works
  589.  
  590.     mov    si,[current_row]
  591.     GaussShort    esi
  592.  
  593.     mov    di,[checking_row]
  594.     GaussShort    edi
  595.  
  596.     mov    cx,[unitdwords]
  597. makeunit50:
  598.     mov    eax,fs:[esi]
  599.     xchg    eax,fs:[edi]
  600.     mov    fs:[esi],eax
  601.     add    esi,4
  602.     add    edi,4
  603.     loop    makeunit50
  604.  
  605.     ;exchange mini works
  606.  
  607.     mov    si,[current_row]
  608.     GaussMini    esi
  609.     mov    di,[checking_row]
  610.     GaussMini    edi
  611.     mov    al,fs:[esi]
  612.     xchg    al,fs:[edi]
  613.     mov    fs:[esi],al
  614.  
  615. makeunit60:
  616.     ;* store this row in RAM
  617.  
  618.     mov    si,offset BUFFER2
  619.     mov    edi,[refer_adr]
  620.     mov    cx,[alldwords]
  621. makeunit65:
  622.     lodsd
  623.     mov    fs:[edi],eax
  624.     add    edi,4
  625.     loop    makeunit65
  626.  
  627.     mov    [refer_adr],edi
  628.     
  629.     ;* erase other rows
  630.  
  631.     mov    ax,[checking_row]
  632.     inc    ax
  633.     mov    [checking_row],ax
  634.     mov    cx,[matrix_size]
  635.     sub    cx,ax            ;# of other rows
  636.     jz    makeunit_next_column    ;already last row
  637.  
  638.     mov    di,ax
  639.     GaussShort    edi
  640.  
  641.     mov    bx,[current_wordptr]
  642.     and    ebx,[unitmask]
  643. makeunit110:
  644.     push    cx
  645.  
  646. ;    check next rows
  647.  
  648.     mov    ax,[current_wordimg]
  649.     test    fs:[ebx+edi],ax
  650.     jz    makeunit130        ;skip if 0
  651.  
  652. ;    if nonzero then take xor
  653.  
  654.     mov    si,[current_row]
  655.     GaussShort    esi
  656.  
  657.     mov    cx,[unitdwords]
  658. makeunit120:
  659.     mov    eax,fs:[esi]
  660.     xor    fs:[edi],eax
  661.     add    esi,4
  662.     add    edi,4
  663.     loop    makeunit120
  664.     sub    edi,[unitbytes]
  665.  
  666. makeunit130:
  667.     inc    [checking_row]
  668.  
  669.     add    edi,[unitbytes]
  670.     pop    cx
  671.     loop    makeunit110
  672.  
  673. makeunit_next_column:
  674.     inc    [current_row]
  675. makeunit_next_column2:
  676.     ror    [current_wordimg],1
  677.     jnc    makeunit200
  678.     sub    [current_wordptr],2
  679. makeunit200:
  680.     pop    cx
  681.     dec    cx
  682.     jz    makeunit1_ret
  683.     jmp    makeunit10
  684. makeunit1_ret:
  685.     ret
  686.  
  687.  
  688.     ;get all rows by unitbytes
  689.  
  690. load_all:
  691.     mov    di,[start_row]
  692.     GaussShort    edi
  693.  
  694.     mov    ax,[start_row]
  695.     push    ax            ;*
  696.  
  697. load_all11:
  698.     cmp    ax,[size1]
  699.     jae    load_all12
  700.  
  701.     mov    bx,[handle1]
  702.     mov    [handle],bx
  703.  
  704.     mov    ax,[size1]
  705.     sub    ax,[start_row]
  706.     mov    [loadallcount],ax    
  707.     call    loadsub
  708.     mov    ax,[size1]
  709.  
  710. load_all12:
  711.     cmp    ax,[size2]
  712.     jae    load_all13
  713.  
  714.     mov    bx,[handle2]
  715.     mov    [handle],bx
  716.  
  717.     mov    bx,ax
  718.     sub    ax,[size1]
  719.     mov    [start_row],ax
  720.     mov    ax,[size2]
  721.     sub    ax,bx
  722.     mov    [loadallcount],ax
  723.     call    loadsub
  724.     mov    ax,[size2]
  725.  
  726. load_all13:
  727.     cmp    ax,[size3]
  728.     jae    load_all14
  729.  
  730.     mov    bx,[handle3]
  731.     mov    [handle],bx
  732.  
  733.     mov    bx,ax
  734.     sub    ax,[size2]
  735.     mov    [start_row],ax
  736.     mov    ax,[size3]
  737.     sub    ax,bx
  738.     mov    [loadallcount],ax
  739.     call    loadsub
  740.     mov    ax,[size3]
  741.  
  742. load_all14:
  743.     mov    bx,[handle4]
  744.     mov    [handle],bx
  745.  
  746.     mov    bx,ax
  747.     sub    ax,[size3]
  748.     mov    [start_row],ax
  749.     mov    ax,[matrix_size]
  750.     sub    ax,bx
  751.     mov    [loadallcount],ax
  752.     call    loadsub
  753.  
  754. load_all20:
  755.     pop    [start_row]        ;*
  756.  
  757.     ;check 0 or non 0, set result in GaussMiniadr
  758.  
  759.     mov    si,[start_row]
  760.     GaussShort    esi
  761.     mov    di,[start_row]
  762.     GaussMini    edi
  763.  
  764.     mov    cx,[matrix_size]
  765.     sub    cx,[start_row]
  766. load_all120:
  767.     push    cx
  768.     xor    ax,ax
  769.     mov    cx,[unitwords]
  770. load_all130:
  771.     or    ax,fs:[esi]
  772.     add    esi,2
  773.     loop    load_all130
  774.     or    al,ah
  775.     mov    fs:[edi],al
  776.     inc    edi
  777.     pop    cx
  778.     loop    load_all120
  779.     ret
  780.  
  781.  
  782. loadsub:
  783.     push    edi
  784.     mov    ax,[start_row]
  785.     mov    dx,[allbytes]
  786.     mul    dx
  787.     mov    cx,dx
  788.     push    cx
  789.     mov    dx,ax        ;cx:dx = file ptr
  790.     mov    ax,[start_column]
  791.     shr    ax,3
  792.     mov    cl,[unitshift]
  793.     shr    ax,cl        ;cut lower bits
  794.     shl    ax,cl        ;
  795.     add    dx,ax
  796.     pop    cx
  797.     adc    cx,0
  798.  
  799.     mov    ah,42h        ;move file ptr
  800.     mov    al,0        ;absolute
  801.     mov    bx,[handle]
  802.     int    21h
  803.  
  804.     pop    edi
  805.  
  806.     mov    cx,[loadallcount]
  807. loadsub10:
  808.     push    cx
  809.  
  810.     push    edi
  811.     mov    ah,3fh
  812.     mov    bx,[handle]
  813.     mov    cx,word ptr [unitbytes]
  814.     mov    dx,offset SHORTBUFFER
  815.     int    21h
  816.  
  817.     xor    cx,cx
  818.     mov    dx,[allbytes]
  819.     sub    dx,word ptr [unitbytes]
  820.     mov    ah,42h        ;move file ptr
  821.     mov    al,1        ;relative
  822.     mov    bx,[handle]
  823.     int    21h
  824.     pop    edi
  825.  
  826.     mov    si,offset SHORTBUFFER
  827.     mov    cx,[unitdwords]
  828. loadsub15:
  829.     mov    eax,[si]
  830.     mov    fs:[edi],eax
  831.     add    si,4
  832.     add    edi,4
  833.     loop    loadsub15
  834.  
  835.     pop    cx
  836.     loop    loadsub10
  837.     ret
  838.  
  839.  
  840. load_row:
  841.     mov    ax,[RWrow]
  842.     
  843.     mov    bx,[handle1]
  844.     xor    dx,dx
  845.     cmp    ax,[size1]
  846.     jb    load_row10
  847.  
  848.     mov    bx,[handle2]
  849.     mov    dx,[size1]
  850.     cmp    ax,[size2]
  851.     jb    load_row10
  852.  
  853.     mov    bx,[handle3]
  854.     mov    dx,[size2]
  855.     cmp    ax,[size3]
  856.     jb    load_row10
  857.  
  858.     mov    bx,[handle4]
  859.     mov    dx,[size3]
  860.  
  861. load_row10:
  862.     mov    [handle],bx
  863.  
  864.     sub    ax,dx
  865.     mov    dx,[allbytes]
  866.     mul    dx
  867.     mov    cx,dx
  868.     mov    dx,ax        ;cx:dx = file ptr
  869.  
  870.     mov    ah,42h        ;move file ptr
  871.     mov    al,0        ;absolute
  872.     mov    bx,[handle]
  873.     int    21h
  874.  
  875.     mov    ah,3fh        ;read
  876.     mov    bx,[handle]
  877.     mov    cx,[allbytes]
  878.     mov    dx,[RWadr]
  879.     int    21h
  880.  
  881.     ret
  882.  
  883. save_row:
  884.     mov    ax,[RWrow]
  885.     
  886.     mov    bx,[handle1]
  887.     xor    dx,dx
  888.     cmp    ax,[size1]
  889.     jb    save_row10
  890.  
  891.     mov    bx,[handle2]
  892.     mov    dx,[size1]
  893.     cmp    ax,[size2]
  894.     jb    save_row10
  895.  
  896.     mov    bx,[handle3]
  897.     mov    dx,[size2]
  898.     cmp    ax,[size3]
  899.     jb    save_row10
  900.  
  901.     mov    bx,[handle4]
  902.     mov    dx,[size3]
  903.  
  904. save_row10:
  905.     mov    [handle],bx
  906.  
  907.     sub    ax,dx
  908.     mov    dx,[allbytes]
  909.     mul    dx
  910.     mov    cx,dx
  911.     mov    dx,ax        ;cx:dx = file ptr
  912.  
  913.     mov    ah,42h        ;move file ptr
  914.     mov    al,0        ;absolute
  915.     mov    bx,[handle]
  916.     int    21h
  917.  
  918.     mov    ah,40h        ;write
  919.     mov    bx,[handle]
  920.     mov    cx,[allbytes]
  921.     mov    dx,[RWadr]
  922.     int    21h
  923.  
  924.     ret
  925.  
  926.  
  927. ;
  928. ;* Initialize for Gaussian elimination
  929. ;
  930. ;COMMAND#=0
  931. ;
  932. gauss_init:
  933.     ;get parameters
  934.  
  935.     mov    ax,cs
  936.     mov    ds,ax
  937.     mov    es,ax
  938.  
  939.     mov    bx,offset mpqshd4end
  940.     add    bx,15
  941.     shr    bx,4
  942.     add    ax,bx
  943.     cmp    ax,primeseg2
  944.     ja    lackofmainmemory
  945.  
  946.     MOV    BX,V1        ;P é╠ ADDRESS é╠É▌ÆΦ
  947.     MOV    AX,[BX]
  948.     MOV    [P_OFF],AX
  949.     MOV    AX,[BX+2]
  950.     MOV    [P_SEG],AX
  951.  
  952.     MOV_AX    V2+2        ;work%(0) é╠ SEGMENT
  953.     ADD    AX,ARRAYHEADSEG
  954.     MOV    [WORK_SEG],AX
  955.  
  956.     MOV_AX    V3+2        ;ans#(0) é╠ SEGMENT
  957.     ADD    AX,ARRAYHEADSEG
  958.     MOV    [ANS_SEG],AX
  959.  
  960.     MOV    BX,V4        ;Y é╠ ADDRESS é╠É▌ÆΦ
  961.     MOV    AX,[BX]
  962.     MOV    [Y_OFF],AX
  963.     MOV    AX,[BX+2]
  964.     MOV    [Y_SEG],AX
  965.  
  966.     mov_ax    AR1
  967.     shl    ax,1
  968.     dec    ax
  969.     mov    [primes],ax
  970.     mov    [start_column],ax
  971.     inc    ax
  972.     mov    [matrix_size],ax
  973.     shl    ax,1        ;*2
  974.     shr    ax,3        ;bits -> bytes
  975.     mov    [allbytes],ax
  976.     shr    ax,1
  977.     mov    [halfbytes],ax
  978.     mov    [allwords],ax    
  979.     shr    ax,1
  980.     mov    [halfwords],ax
  981.     mov    [alldwords],ax
  982.  
  983.     mov    [start_row],0
  984.     mov    [primeadrnow],primeadr2
  985.  
  986.     ; check extended memories
  987.  
  988.     mov    esi,GaussMiniadr-4
  989.     mov    eax,19510701h
  990.     mov    edx,00100000h        ;1Mbytes
  991. gauss_init100:
  992.     add    esi,edx
  993.     mov    fs:[esi],eax
  994.     cmp    fs:[esi],eax
  995.     je    gauss_init100
  996.     mov    eax,esi
  997.     sub    eax,edx
  998.     sub    eax,GaussShortadr-4
  999.     shl    eax,3
  1000.     xor    edx,edx
  1001.     mov    ecx,3
  1002.     div    ecx
  1003.     xor    edx,edx
  1004.     mov    cx,[matrix_size]    ;higher already 0
  1005.     div    ecx
  1006.  
  1007.     mov    edx,maxunitcolumns
  1008.     cmp    eax,edx
  1009.     jae    gauss_init140
  1010. gauss_init130:
  1011.     shr    dx,1
  1012.     test    ax,dx
  1013.     jz    gauss_init130
  1014.  
  1015. gauss_init140:
  1016.     mov    ax,dx
  1017.     mov    [unitcolumns],ax
  1018.     shr    ax,3
  1019.     mov    word ptr [unitbytes],ax
  1020.     dec    ax
  1021.     mov    word ptr [unitmask],ax
  1022.     inc    ax
  1023.     shr    ax,1
  1024.     mov    [unitwords],ax
  1025.     shr    ax,1
  1026.     mov    [unitdwords],ax
  1027.     mov    cx,1
  1028. gauss_init150:
  1029.     inc    cx
  1030.     shr    ax,1
  1031.     jnc    gauss_init150
  1032.     mov    [unitshift],cl    ;log_2(unitcolumns/8)
  1033.  
  1034.     mov    eax,[unitbytes]
  1035.     xor    ecx,ecx
  1036.     mov    cx,[matrix_size]
  1037.     mul    ecx
  1038.     add    eax,GaussShortadr
  1039.     mov    [GaussLongadr],eax
  1040.  
  1041.     ;open file
  1042.  
  1043.     mov    bx,offset MATRIXNAME1
  1044.     MOV_AX    AR2
  1045.     or    ax,ax
  1046.     jz    gauss_init170
  1047.     sub    bx,2
  1048.     add    al,'@'
  1049.     mov    [bx],al
  1050. gauss_init170:
  1051.     mov    dx,bx
  1052.     mov    ah,3dh
  1053.     mov    al,2        ;read/write
  1054.     int    21h
  1055.     jc    diskerror
  1056.     mov    [handle1],ax
  1057.     MOV_AX    AR3
  1058.     shl    ax,1
  1059.     mov    [size1],ax
  1060.  
  1061.     mov    bx,offset MATRIXNAME2
  1062.     MOV_AX    AR4
  1063.     or    ax,ax
  1064.     jz    gauss_init180
  1065.     sub    bx,2
  1066.     add    al,'@'
  1067.     mov    [bx],al
  1068. gauss_init180:
  1069.     mov    dx,bx
  1070.     mov    ah,3dh
  1071.     mov    al,2        ;read/write
  1072.     int    21h
  1073.     jc    diskerror
  1074.     mov    [handle2],ax
  1075.     MOV_AX    AR5
  1076.     shl    ax,1
  1077.     add    ax,[size1]
  1078.     mov    [size2],ax
  1079.  
  1080.     mov    bx,offset MATRIXNAME3
  1081.     MOV_AX    AR6
  1082.     or    ax,ax
  1083.     jz    gauss_init190
  1084.     sub    bx,2
  1085.     add    al,'@'
  1086.     mov    [bx],al
  1087. gauss_init190:
  1088.     mov    dx,bx
  1089.     mov    ah,3dh
  1090.     mov    al,2        ;read/write
  1091.     int    21h
  1092.     jc    diskerror
  1093.     mov    [handle3],ax
  1094.     MOV_AX    AR7
  1095.     shl    ax,1
  1096.     add    ax,[size2]
  1097.     mov    [size3],ax
  1098.  
  1099.     mov    bx,offset MATRIXNAME4
  1100.     MOV_AX    AR8
  1101.     or    ax,ax
  1102.     jz    gauss_init200
  1103.     sub    bx,2
  1104.     add    al,'@'
  1105.     mov    [bx],al
  1106. gauss_init200:
  1107.     mov    dx,bx
  1108.     mov    ah,3dh
  1109.     mov    al,2        ;read/write
  1110.     int    21h
  1111.     jc    diskerror
  1112.     mov    [handle4],ax
  1113.  
  1114.     mov    ax,[unitcolumns]
  1115.  
  1116. gauss_init_out:
  1117.     mov    bx,AR0
  1118.     mov    [bx],ax
  1119.  
  1120.     mov    bx,AR1
  1121.     mov    word ptr [bx],primeseg2-4000h
  1122.  
  1123.     mov    ax,ss
  1124.     mov    ds,ax
  1125.     mov    es,ax
  1126.     retf
  1127.  
  1128. diskerror:
  1129.     mov    ax,8001h    ;set -1
  1130.     jmp    gauss_init_out
  1131.  
  1132. lackofmainmemory:
  1133.     xor    ax,ax
  1134.     jmp    gauss_init_out
  1135.  
  1136. ;
  1137. ; * Close File
  1138. ;   Command# = 2
  1139. CLOSE_FILE:
  1140.     mov    ah,3eh
  1141.     mov    bx,cs:[handle1]
  1142.     int    21h
  1143.  
  1144.     mov    ah,3eh
  1145.     mov    bx,cs:[handle2]
  1146.     int    21h
  1147.  
  1148.     mov    ah,3eh
  1149.     mov    bx,cs:[handle3]
  1150.     int    21h
  1151.  
  1152.     mov    ah,3eh
  1153.     mov    bx,cs:[handle4]
  1154.     int    21h
  1155.     retf
  1156.  
  1157.  
  1158.         db    ' :'
  1159. MATRIXNAME1    db    'MPQSMAT1.UBD',0
  1160.         db    ' :'
  1161. MATRIXNAME2    db    'MPQSMAT2.UBD',0
  1162.         db    ' :'
  1163. MATRIXNAME3    db    'MPQSMAT3.UBD',0
  1164.         db    ' :'
  1165. MATRIXNAME4    db    'MPQSMAT4.UBD',0
  1166.  
  1167. align 4
  1168. SHORTBUFFER    db    maxunitbytes dup(0)
  1169. align 4
  1170. BUFFER1        db    maxbuffersize dup(0)
  1171. BUFFER2        db    maxbuffersize dup(0)
  1172.  
  1173. mpqshd4end:
  1174.  
  1175. CODE    ENDS
  1176. END    START
  1177.