Subversion Repositories NedoOS

Rev

Rev 787 | Rev 816 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download

  1.  
  2. ;NVOLUMES=8
  3. MAXFILES=16;8
  4. vol_trdos=4 ;'A'..'D'
  5. vol_pipe=25 ;'Z'
  6.  
  7. TRDOSADD40=0x40
  8. PIPEADD80=0x80
  9.  
  10. MAXPIPES=8
  11. PIPEBUF_SZ=255
  12. PIPEDESC_SZ=PIPEBUF_SZ+1
  13.  
  14. ;предполагается, что юзер не имеет стек ниже 0x3b00, иначе он затрёт систему
  15.  
  16. ;FCB и имя можно передавать в любой области userspace
  17. ;DTA может быть в любой области userspace
  18. fatfs_org=0x4000
  19. ;CurrVol=0X4000+26
  20. ;CurrDir=CurrVol+1
  21.  
  22.         MACRO GETVOLUME
  23.         ;ld a,(CurrVol)
  24.         ;ld a,(iy+app.dir+DIR.ID)
  25.          ld a,(iy+app.vol)
  26.         ENDM
  27.         MACRO SETVOLUME
  28.         ;ld a,(CurrVol)
  29.         ;ld a,(iy+app.dir+DIR.ID)
  30.          ld (iy+app.vol),a
  31.         ENDM
  32.  
  33.         MACRO CHECKVOLUMETRDOS
  34.         GETVOLUME
  35.         cp vol_trdos
  36.         ENDM
  37.  
  38. BDOS_setpgtrdosfs
  39.         ld a,pgtrdosfs
  40.         jr sys_setpg4000
  41.         ;ld bc,memport4000
  42.         ;ld (sys_curpg4000),a
  43.         ;out (c),a
  44.         ;ret
  45.  
  46. BDOS_setpgfatfs
  47.         ld a,pgfatfs
  48. sys_setpg4000
  49.         ld bc,memport4000
  50.         ld (sys_curpg4000),a ;для sys_sysint
  51.         out (c),a
  52.         ret
  53.  
  54. blocksize=128 ;сколько байтов читать в CP/M операциях
  55.  
  56. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  57. BDOS_wiznetopen
  58.         BDOSSETPGW5300 ;портит bc
  59.         jp wiznet_open
  60.  
  61. BDOS_wiznetclose
  62.         BDOSSETPGW5300 ;портит bc
  63.         jp wiznet_close
  64.  
  65. BDOS_wiznetread
  66. ;de=pointer, hl=buffer size
  67. ;out: hl=size
  68.         call BDOS_preparedepage
  69.         call BDOS_setdepage
  70. ;DE = Pointer to physical data
  71.         BDOSSETPGW5300
  72.         jp wiznet_read
  73.  
  74. BDOS_wiznetwrite
  75. ;de=pointer, hl=size
  76.         call BDOS_preparedepage
  77.         call BDOS_setdepage
  78. ;DE = Pointer to physical data
  79.         BDOSSETPGW5300
  80.         jp wiznet_write
  81.  
  82. ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
  83.  
  84. BDOS_setmusic
  85. muzpid=$+1
  86.         ld a,0
  87.         or a
  88.         call z,killmuz
  89.         ex af,af' ;'
  90.         ld (muzpg),a
  91.         ld (muzcall),hl
  92.         ld a,(iy+app.id)
  93.         ld (muzpid),a
  94. ;страницы для 8000, c000 берём из текущей юзерской карты памяти
  95.         ld a,(iy+app.mainpg)
  96.         call sys_setpg8000
  97.         ld a,(curpg32klow+0x8000)
  98.         ld (muzpg8000),a
  99.         ld a,(curpg32khigh+0x8000)
  100.         ld (muzpgc000),a
  101.         ret
  102.        
  103. killmuz
  104.         xor a
  105.         ld (muzpid),a
  106.         ld de,sys_reter
  107.         ld (muzcall),de
  108.         ld a,0xfe
  109.         call shut1ay
  110.         ld a,0xff
  111. shut1ay
  112.         ld bc,0xfffd
  113.         out (c),a
  114.         ld de,0x0e00
  115. shutay0
  116.         dec d
  117.         ld b,0xff
  118.         out (c),d
  119.         ld b,0xbf
  120.         out (c),e
  121.         jr nz,shutay0
  122.         ret
  123.  
  124. BDOS_setmainpage
  125.         ;ld iy,(appaddr)
  126. ;e=page for 0x0000
  127.         ld (iy+app.mainpg),e
  128.         ret
  129.        
  130. BDOS_setborder
  131.         ;ld iy,(appaddr)
  132. ;e=border=0..15
  133.         ld (iy+app.border),e
  134.         ret
  135.        
  136. BDOS_setscreen
  137.         ;ld iy,(appaddr)
  138. ;e=screen=0..1
  139.         ld a,e
  140.         add a,a
  141.         add a,a
  142.         add a,a
  143.         ld d,a
  144.         or fd_user
  145.         ld (iy+app.screen),a
  146.         ;xor a ;success
  147.         ret;jr rest_exit
  148.  
  149. BDOS_getappmainpages
  150. ;e=id
  151. ;out: d,e,h,l=pages in 0000,4000,8000,c000, c=flags, a=error
  152.         call BDOS_findapp
  153.         jp nz,BDOS_fail
  154. BDOS_getmainpages
  155.         ;ld iy,(appaddr)
  156. ;out: dehl=номера страниц в 0000,4000,8000,c000, c=flags, b=id
  157. BDOS_getmainpages_iy
  158.         call setmainpg_c000
  159.         ld d,a
  160.         ld a,(curpg16k+0xc000)
  161.         ld e,a
  162.         ld a,(curpg32klow+0xc000)
  163.         ld hl,(curpg32khigh+0xc000)
  164.         ld h,a
  165.         ld c,(iy+app.flags)
  166.         ld b,(iy+app.id)
  167.         xor a
  168.         ret
  169.  
  170. BDOS_preparedepage
  171. ;de=userspace addr
  172. ;out: de>=0x8000, включены нужные страницы в 8000,c000
  173.         ;ld iy,(appaddr)
  174.         ld a,(iy+app.mainpg)
  175.         call sys_setpg8000
  176.         bit 7,d
  177.         jr nz,BDOS_preparedepage8000_c000
  178.         bit 6,d
  179.         jr nz,BDOS_preparedepage4000_8000
  180.         set 7,d
  181.         ld (depage8000),a
  182.         ld a,(curpg16k+0x8000)
  183.         ;ld bc,memportc000
  184.         ;out (c),a
  185.         ld (depagec000),a
  186.         ret
  187. BDOS_preparedepage4000_8000
  188.         ld a,d
  189.         add a,0x40
  190.         ld d,a
  191.         ld a,(curpg32klow+0x8000)
  192.         ;call sys_setpgc000
  193.         ld (depagec000),a
  194.         ld a,(curpg16k+0x8000)
  195.         ;call sys_setpg8000
  196.         ld (depage8000),a
  197.         ret
  198. BDOS_preparedepage8000_c000
  199.         ld a,(curpg32khigh+0x8000)
  200.         ;call sys_setpgc000
  201.         ld (depagec000),a
  202.         ld a,(curpg32klow+0x8000)
  203.         ;call sys_setpg8000
  204.         ld (depage8000),a
  205.         ret
  206.  
  207. BDOS_setdepage
  208. ;keep de,hl
  209. depagec000=$+1
  210.         ld a,0
  211.         call sys_setpgc000
  212. depage8000=$+1
  213.         ld a,0
  214. sys_setpg8000
  215.         ld (sys_curpg8000),a
  216.         ld bc,memport8000
  217.         out (c),a
  218.         ret
  219.  
  220. BDOS_setpal
  221.         call BDOS_preparedepage
  222.         call BDOS_setdepage
  223. ;de=палитра (выше 0xc000)
  224.         push iy
  225.         pop hl
  226.         ld bc,app.pal
  227.         add hl,bc
  228.         ex de,hl
  229.         ld bc,32
  230.         ldir
  231.         ;call setpalettechanged
  232.         ;xor a
  233.         ;ret
  234. setpalettechanged
  235.         ld a,55+128 ;"or a"
  236.         ld (palettechanged),a
  237.         ret
  238.        
  239. BDOS_scroll_prepare
  240.         ld a,l
  241.         srl a
  242.         ld (BDOS_scrollpagelinelayer_wid),a
  243.         ld b,h
  244.         dec b
  245. BDOS_countxy
  246. ;keeps bc
  247.         ld a,d ;y
  248.         sub -0x87&0xff ;0xe1c0*4=0x8700
  249.         rra
  250.         ld h,a
  251.          ld a,0;16
  252.         rra
  253.         sra h
  254.         rra
  255.         ld l,e ;x
  256.         srl l
  257.         jr c,$+4
  258.         res 5,h
  259.         add a,l
  260.         ld l,a
  261.         ret
  262.  
  263. BDOS_getxy
  264. ;out: de=yx ;GET CURSOR POSITION
  265.         ;ld hl,(pr_textmode_curaddr)
  266.         ld l,(iy+app.textcuraddr)
  267.         ld h,(iy+app.textcuraddr+1)
  268.         ld a,h
  269.         rla
  270.         rla
  271.         rla ;bit5
  272.         ld a,l
  273.         rla
  274.         and 0x7f
  275.         ld e,a ;x
  276.         add hl,hl
  277.         add hl,hl ;h=y*4 + const + n*0x80
  278.         ld a,h
  279.         sub 0x87 ;0xe1c0*4=0x8700
  280.         and 0x1f
  281.         ld d,a ;y
  282.         xor a ;success
  283.         ret
  284.  
  285. BDOS_countattraddr
  286.         BDOSSETPGSSCR
  287.         ;ld hl,(pr_textmode_curaddr)
  288.         ld l,(iy+app.textcuraddr)
  289.         ld h,(iy+app.textcuraddr+1)
  290.         ld a,h
  291.         xor 0x60 ;attr + 0x20
  292.         ld h,a
  293.          and 0x20
  294.         jr nz,$+3
  295.         inc l
  296.         ret
  297.        
  298. BDOS_prattr
  299. ;e=color byte
  300.          ld hl,(appaddr)
  301.          ld bc,(focusappaddr)
  302.          or a
  303.          sbc hl,bc
  304.          ret nz
  305.         call BDOS_countattraddr
  306.         ld (hl),e
  307.         ret
  308.  
  309. BDOS_getattr
  310. ;out: a=color byte
  311.         call BDOS_countattraddr
  312.         ld a,(hl)
  313.         ret
  314.  
  315. BDOS_setxy
  316. ;de=yx
  317.         call BDOS_countxy
  318. BDOS_settextcuraddr
  319.         ;ld (pr_textmode_curaddr),hl
  320.         ld (iy+app.textcuraddr),l
  321.         ld (iy+app.textcuraddr+1),h
  322.         xor a ;success
  323.         ret
  324.        
  325. BDOS_prchar_controlcode
  326.         cp 0x0a
  327.         jr z,BDOS_prchar_lf
  328.         cp 0x0d
  329.         jp nz,BDOS_prchar_nocontrolcode
  330.         ;jr z,BDOS_prchar_cr
  331. BDOS_prchar_cr
  332.         ld a,l
  333.         and 0xc0
  334.         ld l,a
  335.         res 5,h
  336.         jr BDOS_settextcuraddr
  337.         ;jp BDOS_prchar_q
  338.        
  339. BDOS_prchar_lf
  340.         ld a,l
  341.         add a,0x40
  342.         ld l,a
  343.         jr nc,BDOS_settextcuraddr ;BDOS_prchar_q ;ret nc
  344.         jr BDOS_prchar_lf_q
  345.  
  346. BDOS_prchar
  347. ;e=char
  348.         ld a,e
  349. BDOS_prchar_a
  350. ;портит только 0xc000+, но сама восстанавливает там pgkillable (для быстрого вызова через rst)
  351.          ld hl,(appaddr)
  352.          ld bc,(focusappaddr)
  353.          or a
  354.          sbc hl,bc
  355.          ret nz ;no focus - no print
  356.  
  357.         ld h,trecode/256
  358.         ld l,a
  359.         ld a,(hl)
  360. ;pr_textmode_curaddr=$+1
  361.         ;ld hl,0xc1c0
  362.         ld l,(iy+app.textcuraddr)
  363.         ld h,(iy+app.textcuraddr+1)
  364.         cp 0x0e
  365.         jr c,BDOS_prchar_controlcode
  366. BDOS_prchar_nocontrolcode
  367.          ;push hl
  368.          ;ld hl,(appaddr)
  369.          ;ld bc,(focusappaddr)
  370.          ;or a
  371.          ;sbc hl,bc
  372.          ;pop hl
  373.          ;jr nz,BDOS_prchar_skip
  374.         ;ld de,pgscr0_1*256+pgscr0_0
  375.         ;ld bc,memportc000
  376.         ;out (c),d ;text
  377.         ;ld (hl),a
  378.         ;out (c),e ;attr
  379.         ld e,a
  380.         ld a,pgscr0_1
  381.         call sys_setpgc000
  382.         ld (hl),e
  383.         ld a,pgscr0_0
  384.         call sys_setpgc000
  385. ;BDOS_prchar_skip        
  386.  
  387.         ;ld de,0x2000 + pgkillable
  388.        
  389.          ;push af
  390.  
  391.         ld a,h
  392.         xor 0x20;d;0x20 ;attr + 0x20
  393.         ld h,a
  394.         and 0x20;d;0x20
  395.         jr nz,$+3
  396.         inc l
  397.  
  398.          ;pop af
  399.          ;jr nz,BDOS_prchar_skipattr
  400. ;pr_textmode_curcolor=$+1
  401.         ;ld (hl),7
  402.         ld a,(iy+app.curcolor)
  403.         ld (hl),a
  404.        
  405.         ;set 6,h ;attr -> next char
  406.  
  407.         ;;ld e,pgkillable
  408.         ;out (c),e ;pgkillable
  409.         ld a,pgkillable
  410.         call sys_setpgc000
  411. ;BDOS_prchar_skipattr
  412.  
  413.         ld a,l
  414.         and 0x3f
  415.         cp 80/2
  416.         ;ld (pr_textmode_curaddr),hl
  417.         ld (iy+app.textcuraddr),l
  418.         ld (iy+app.textcuraddr+1),h
  419.         ret nz ;jr nz,BDOS_prchar_q ;ret nz ;нет переноса строки
  420.         ld a,l
  421.         and 0xc0
  422.         add a,0x40
  423.         ld l,a
  424.         jr nc,BDOS_settextcuraddr ;BDOS_prchar_q ;ret nc
  425. BDOS_prchar_lf_q
  426.         inc h
  427.         bit 3,h
  428.         jr z,BDOS_settextcuraddr ;BDOS_prchar_q ;нет выхода за последнюю строку
  429. BDOS_scrolllock0
  430.         ld a,0xfe
  431.         in a,(0xfe)
  432.         rra ;Caps Shift
  433.         jr nc,BDOS_scrolllock0
  434.         ld hl,(appaddr)
  435.         ld de,(focusappaddr)
  436.         or a
  437.         sbc hl,de
  438.         jr nz,BDOS_prchar_skipscroll
  439. ;scroll+clear bottom line
  440.         call BDOS_scrollpage ;attr
  441.         ld a,pgscr0_1 ;text
  442.         ;ld bc,memportc000
  443.         ;out (c),a
  444.         call sys_setpgc000
  445.         call BDOS_cllastline
  446.         ld a,pgscr0_0 ;attr
  447.         ;ld bc,memportc000
  448.         ;out (c),a
  449.         call sys_setpgc000
  450.         call BDOS_cllastline
  451.         ld a,pgkillable
  452.         ;ld bc,memportc000
  453.         ;out (c),a
  454.         call sys_setpgc000
  455. BDOS_prchar_skipscroll
  456.         ld hl,0xc7c0
  457. BDOS_prchar_q
  458.         jp BDOS_settextcuraddr
  459.         ;;ld (pr_textmode_curaddr),hl
  460.         ;ld (iy+app.textcuraddr),l
  461.         ;ld (iy+app.textcuraddr+1),h
  462.         ;ret
  463.        
  464. BDOS_scrollpage
  465.         ld a,40
  466.         ld (BDOS_scrollpagelinelayer_wid),a
  467.         ld hl,0xc1c0
  468.         ld b,24
  469. BDOS_scrollpage0
  470.         push bc
  471.         ld d,h
  472.         ld e,l
  473.         ld bc,64
  474.         add hl,bc
  475.         call BDOS_scrollpageline
  476.         pop bc
  477.         djnz BDOS_scrollpage0
  478.         ret
  479. BDOS_scrollpageline
  480.         ld a,pgscr0_1 ;text
  481.         or a
  482.         call BDOS_scrollpagelinelayers ;text
  483.         ld a,pgscr0_0 ;attr
  484.         scf
  485. BDOS_scrollpagelinelayers
  486.         ;ld bc,memportc000
  487.         ;out (c),a
  488.         call sys_setpgc000
  489.         push af
  490.         push de
  491.         push hl
  492.         set 5,h
  493.         set 5,d
  494.         or a
  495.         call BDOS_scrollpagelinelayer
  496.         pop hl
  497.         pop de
  498.         pop af
  499. BDOS_scrollpagelinelayer
  500.         push de
  501.         push hl
  502.         jr nc,$+4
  503.         inc hl
  504.         inc de
  505. BDOS_scrollpagelinelayer_wid=$+1
  506.         ld bc,39;40
  507.         ldir
  508.         pop hl
  509.         pop de
  510.         ret
  511.  
  512. BDOS_scrolldown
  513. ;de=topyx, hl=hgt,wid
  514. ;x, wid even
  515.          ;push hl
  516.          ;ld hl,(appaddr)
  517.          ;ld bc,(focusappaddr)
  518.          ;or a
  519.          ;sbc hl,bc
  520.          ;pop hl
  521.          ;ret nz
  522.         ld a,d
  523.         add a,h
  524.         dec a
  525.         ld d,a ;ybottom
  526.         call BDOS_scroll_prepare
  527. BDOS_scrolldown0
  528.         push bc
  529.         ld d,h
  530.         ld e,l
  531.         ld bc,-64
  532.         add hl,bc
  533.         call BDOS_scrollpageline
  534.         pop bc
  535.         djnz BDOS_scrolldown0
  536.         ret
  537.  
  538. BDOS_scrollup
  539. ;de=topyx, hl=hgt,wid
  540. ;x, wid even
  541.          ;push hl
  542.          ;ld hl,(appaddr)
  543.          ;ld bc,(focusappaddr)
  544.          ;or a
  545.          ;sbc hl,bc
  546.          ;pop hl
  547.          ;ret nz
  548.         call BDOS_scroll_prepare
  549.         jp BDOS_scrollpage0
  550.        
  551. BDOS_cllastline
  552.         ld hl,0xc7c0
  553.         call BDOS_scrollpage_clline
  554.         ;ld de,0xc7c1
  555.         ;ld bc,64-1
  556.         ;ld (hl),b
  557.         ;ldir
  558.         ld hl,0xe7c0
  559. BDOS_scrollpage_clline        
  560.         ld d,h
  561.         ld e,l
  562.         inc e
  563.         ld bc,64-1
  564.         ld (hl),b
  565.         ldir ;clear bottom line
  566.         ret
  567.        
  568. BDOS_setcolor
  569. ;e=color byte
  570.         ;ld a,e
  571.         ;ld (pr_textmode_curcolor),a
  572.         ld (iy+app.curcolor),e
  573.         ret
  574. ;BDOS_getcolor
  575. ;       ld e,(iy+app.curcolor)
  576. ;       ret
  577.        
  578. BDOS_cls
  579.          ld hl,(appaddr)
  580.          ld bc,(focusappaddr)
  581.          or a
  582.          sbc hl,bc
  583.          ret nz
  584.         ;ld iy,(appaddr)
  585. ;e=color byte
  586.         BDOSSETPGSSCR
  587.  
  588.         if 1==1
  589.         ld a,(iy+app.gfxmode)
  590.         and 7
  591.         ;jr z,BDOS_cls_EGA(0)
  592.          sub 3 ;MC hires(2)
  593.         ld a,e ;attr byte
  594.          jr c,BDOS_cls_EGA ;TODO отдельную очистку для MC hires
  595.          ;dec a ;6912(3)
  596. ;textmode (6)
  597.          ld hl,0xc000
  598.          ld bc,0x1aff
  599.          jr z,BDOS_cls_textmode_ldirbc ;6912(3)
  600.         ld h,0x81;c0
  601.         call BDOS_cls_textmode_ldir
  602.         ld h,0xa1;c0
  603.         call BDOS_cls_textmode_ldir
  604.         endif
  605.        
  606.         ;ld de,0
  607.         ld d,b
  608.         ld e,b ;0
  609.         call BDOS_setxy
  610.        
  611.         if 1==1
  612.         xor a
  613.         ld h,0xc1;c0
  614.         call BDOS_cls_textmode_ldir
  615.         ld h,0xe1;c0
  616. BDOS_cls_textmode_ldir
  617.         ld l,0xc0
  618.         ld bc,25*64-1
  619. BDOS_cls_textmode_ldirbc
  620.         ld d,h
  621.         ld e,l
  622.         inc de
  623.         ld (hl),a
  624.         ldir
  625.         ret
  626. BDOS_cls_EGA
  627.         endif
  628.        
  629.         ;ld a,e
  630. scrbase=0x8000
  631. ;чистим через стек, кроме первых байтов (иначе прерывание может запортить два байта перед экраном)
  632.         ld (clssp),sp
  633.         ld hl,scrbase+(200*40) ;чистим с конца, потому что прерывание портит стек
  634.         ld b,200-1
  635.         scf
  636. clsline0
  637.         ld d,a
  638.         ld e,a
  639.        
  640.         ;ld c,2
  641. clsline1  
  642.         ld sp,hl
  643.         dup 20
  644.         push de
  645.         edup
  646.         set 5,h
  647.         ld sp,hl
  648.         dup 20
  649.         push de
  650.         edup
  651.         res 5,h
  652.        
  653.         set 6,h
  654.         ;dec c
  655.         ;jp nz,clsline1
  656.         ccf
  657.         jp nc,clsline1
  658.        
  659.         ;ld sp,hl
  660.         ;dup 20
  661.         ;push de
  662.         ;edup
  663.         ;res 5,h
  664.         ;ld sp,hl
  665.         ;dup 20
  666.         ;push de
  667.         ;edup
  668.         ;res 6,h
  669.         ld de,-40-0x4000
  670.         add hl,de ;CY=1!!!
  671.         djnz clsline0
  672. clssp=$+1
  673.         ld sp,0
  674.         ld hl,0x0000 + scrbase
  675.         call clslayer2
  676.         ;ld hl,0x2000 + scrbase
  677.         ;call clslayer
  678. clslayer2
  679.         ;ld hl,0x4000 + scrbase
  680.         call clslayer
  681.         ;ld hl,0x6000 + scrbase
  682. clslayer
  683.         ld d,h
  684.         ld e,l
  685.         inc de
  686.         ld  c,40-1;8000-1
  687.         ld (hl),a
  688.         ldir
  689.         ld de,0x2000-(40-1)
  690.         add hl,de
  691.         ret
  692.  
  693. BDOS_playcovox
  694. ;hl=data (0xc000+), ends with 0x00
  695. ;de=pagetable (0x0000+)
  696. ;hx=delay
  697.         set 7,d ;de=pagetable (0x8000+)
  698.         ld a,(iy+app.mainpg)
  699.         call sys_setpg8000 ;pagetable in mainpg
  700.         di
  701.         ld a,(iy+app.gfxmode)
  702.         and 0xf7 ;noturbo
  703.         ld bc,0xbd77
  704.         out (c),a
  705.         push bc
  706. ;hx=delay
  707. ;hl=data
  708. ;de=pagetable (0x8000+)
  709.         ld bc,memportc000
  710.         ld a,(de)
  711.         out (c),a
  712. BDOS_playcovox0
  713.         xor a ;4
  714. BDOS_playcovox0_a0
  715.         or (hl) ;7
  716.         out (0xfb),a    ;11
  717.         jr z,BDOS_playcovoxdone ;7/12
  718.         inc hl          ;6
  719.         bit 6,h         ;8
  720.         jr z,BDOS_playcovoxpage ;7/12
  721. BDOS_playcovoxdelay
  722.         ld a,hx         ;4+4
  723.         dec a           ;4
  724.         jp nz,$-1       ;10
  725.         jp BDOS_playcovox0_a0           ;10=78t при d=1, шаг задержки 14 тактов
  726. BDOS_playcovoxpage
  727. ;тут и раньше была неточная задержка
  728.         ld h,0xc0
  729.         inc de
  730.         ld a,(de)
  731.         out (c),a
  732.         jp BDOS_playcovoxdelay
  733. BDOS_playcovoxdone
  734.         ld a,(iy+app.gfxmode) ;turbo
  735.         pop bc
  736.         out (c),a
  737.         ei
  738.         ret
  739.  
  740. BDOShandler
  741.         push hl
  742.         ld a,c
  743.         ld hl,tbdoscmds
  744.         push bc
  745.         ld bc,nbdoscmds
  746.         cpir
  747.         jp nz,BDOS_pop2fail
  748. ;bc=nbdoscmds-(cmdnumber+1) = 0..(nbdoscmds-1)
  749.         add hl,bc
  750. ;hl=tbdoscmds+nbdoscmds
  751.         add hl,bc
  752.         add hl,bc
  753. ;hl=tbdoscmds+nbdoscmds+ 2*(nbdoscmds-(cmdnumber+1))
  754.         pop bc
  755.         ld a,(hl)
  756.         inc hl
  757.         ld h,(hl)
  758.         ld l,a
  759.         ;hl=jump addr
  760.         ex (sp),hl
  761.         ret
  762.  
  763. tbdoscmds
  764.          db CMD_WRITEHANDLE
  765.          db CMD_WIZNETREAD
  766.          db CMD_YIELDKEEP
  767.          db CMD_YIELD
  768.          db CMD_READHANDLE
  769.           db CMD_GETKEYMATRIX
  770.           db CMD_GETTIMER
  771.           db CMD_WAITPID
  772.           db CMD_SETSCREEN
  773.          db CMD_PRATTR
  774.          db CMD_SETXY
  775.          db CMD_SETCOLOR
  776.          db CMD_PRCHAR
  777.          db CMD_GETATTR
  778.         db CMD_SETDTA;0x1a
  779.         db CMD_FOPEN;0x0f
  780.         db CMD_FREAD;0x14
  781.         db CMD_FCLOSE;0x10
  782.         db CMD_FDEL;0x13 ;DEPRECATED!!!!!
  783.         db CMD_FCREATE;0x16
  784.         db CMD_FWRITE;0x15
  785.         db CMD_FSEARCHFIRST;0x11
  786.         db CMD_FSEARCHNEXT;0x12
  787.         db CMD_OPENDIR
  788.         db CMD_READDIR
  789.         db CMD_SETDRV
  790.         db CMD_PARSEFNAME;0x5c
  791.         db CMD_CHDIR
  792.         db CMD_GETPATH
  793.         db CMD_RUNAPP
  794.         db CMD_NEWAPP
  795.         db CMD_CLS
  796.         db CMD_SETGFX
  797.         db CMD_SETPAL
  798.         db CMD_GETMAINPAGES
  799.         db CMD_NEWPAGE
  800.         db CMD_DELPAGE
  801.         db CMD_MOUNT
  802.         db CMD_FREEZEAPP
  803.         db CMD_MKDIR
  804.         db CMD_RENAME
  805.         db CMD_SETSYSDRV
  806.         ;db CMD_FWRITE_NBYTES
  807.         db CMD_SCROLLUP
  808.         db CMD_SCROLLDOWN
  809.         db CMD_OPENHANDLE
  810.         db CMD_CREATEHANDLE
  811.         db CMD_CLOSEHANDLE
  812.         db CMD_SEEKHANDLE
  813.         db CMD_TELLHANDLE
  814.         db CMD_SETFILETIME
  815.         db CMD_GETFILETIME
  816.         db CMD_GETTIME
  817.         db CMD_GETXY
  818.         db CMD_GETAPPMAINPAGES
  819.         db CMD_DROPAPP
  820.         db CMD_WIZNETOPEN
  821.         db CMD_WIZNETCLOSE
  822.         db CMD_WIZNETWRITE
  823.         db CMD_GETFILESIZE
  824.         db CMD_DELETE
  825.         db CMD_SETWAITING
  826.         db CMD_SETBORDER
  827.         db CMD_READSECTORS
  828.         db CMD_WRITESECTORS
  829.         db CMD_SETMAINPAGE
  830.         db CMD_SETMUSIC
  831.         db CMD_PLAYCOVOX
  832.         db CMD_GETSTDINOUT
  833.         db CMD_SETSTDINOUT
  834.         db CMD_HIDEFROMPARENT
  835.         db CMD_RNDRD
  836.         db CMD_RNDWR
  837.         db CMD_GETFILINFO
  838. nbdoscmds=$-tbdoscmds
  839.         dw BDOS_getfilinfo
  840.         dw BDOS_rndwr
  841.         dw BDOS_rndrd
  842.         dw BDOS_hidefromparent
  843.         dw BDOS_setstdinout
  844.         dw BDOS_getstdinout
  845.         dw BDOS_playcovox
  846.         dw BDOS_setmusic
  847.         dw BDOS_setmainpage
  848.         dw BDOS_writesectors
  849.         dw BDOS_readsectors
  850.         dw BDOS_setborder
  851.         dw BDOS_setwaiting
  852.         dw BDOS_delete
  853.         dw BDOS_getfilesize
  854.         dw BDOS_wiznetwrite
  855.         dw BDOS_wiznetclose
  856.         dw BDOS_wiznetopen
  857.         dw BDOS_dropapp
  858.         dw BDOS_getappmainpages
  859.         dw BDOS_getxy
  860.         dw BDOS_gettime
  861.         dw BDOS_getfiletime
  862.         dw BDOS_setfiletime
  863.         dw BDOS_tellhandle
  864.         dw BDOS_seekhandle
  865.         dw BDOS_closehandle
  866.         dw BDOS_createhandle
  867.         dw BDOS_openhandle
  868.         dw BDOS_scrolldown
  869.         dw BDOS_scrollup
  870.         ;dw BDOS_fwrite_nbytes
  871.         dw BDOS_setsysdrv
  872.         dw BDOS_rename
  873.         dw BDOS_mkdir
  874.         dw BDOS_freezeapp
  875.         dw BDOS_mount
  876.         dw BDOS_delpage
  877.         dw BDOS_newpage
  878.         dw BDOS_getmainpages
  879.         dw BDOS_setpal
  880.         dw BDOS_setgfx
  881.         dw BDOS_cls
  882.         dw BDOS_newapp
  883.         dw BDOS_runapp
  884.         dw BDOS_getpath
  885.         dw BDOS_chdir
  886.         dw BDOS_parse_filename
  887.         dw BDOS_setdrv
  888.         dw BDOS_readdir
  889.         dw BDOS_opendir
  890.         dw BDOS_fsearchnext
  891.         dw BDOS_fsearchfirst
  892.         dw BDOS_fwrite
  893.         dw BDOS_fcreate
  894.         dw BDOS_fdel ;DEPRECATED!!!!!
  895.         dw BDOS_fclose
  896.         dw BDOS_fread
  897.         dw BDOS_fopen
  898.         dw BDOS_setdta
  899.          dw BDOS_getattr
  900.          dw BDOS_prchar
  901.          dw BDOS_setcolor
  902.          dw BDOS_setxy
  903.          dw BDOS_prattr
  904.           dw BDOS_setscreen
  905.           dw BDOS_waitpid
  906.           dw BDOS_gettimer
  907.           dw BDOS_getkeymatrix
  908.          dw BDOS_readhandle
  909.          dw BDOS_yield
  910.          dw BDOS_yieldkeep
  911.          dw BDOS_wiznetread
  912.          dw BDOS_writehandle
  913.  
  914. BDOS_hidefromparent
  915.         if 1==1
  916. ;просто разбудить родителя
  917. activateparent
  918.          ld e,(iy+app.parentid)
  919.          ld a,e
  920.          dec a
  921.          ret z ;idle
  922.          ld (iy+app.parentid),1 ;чтобы после закрытия задачи не пришлось будить родителя (он может уже не существовать)
  923.          call BDOS_findapp ;iy=found app
  924.          set factive,(iy+app.flags)
  925.          ret
  926.         else
  927.         push iy
  928.         call sys_findfreeid ;портит iy        
  929.         pop iy
  930.         ld c,a
  931. ;перезахватить страницы
  932.         ld hl,tsys_pages
  933.         ld a,(iy+app.id)
  934.         ld (iy+app.id),c
  935.         ld b,sys_npages&0xff
  936. BDOS_hidefromparent0
  937.         cp (hl) ;id задачи, которой принадлежит страница
  938.         jr nz,$+4
  939.         ld (hl),c ;заменили страницу
  940.         inc hl
  941.         djnz BDOS_hidefromparent0
  942.         endif
  943.         ret
  944.  
  945. BDOS_setstdinout
  946. ;b=id, e=stdin, d=stdout, h=stderr
  947.         push de
  948.         ld e,b
  949.         call BDOS_findapp
  950.         pop de
  951.         ld (iy+app.stdin),e
  952.         ld (iy+app.stdout),d
  953.         ld (iy+app.stderr),h
  954.         ret
  955.  
  956. BDOS_getstdinout
  957. ;e=stdin, d=stdout, h=stderr
  958.         ld e,(iy+app.stdin)
  959.         ld d,(iy+app.stdout)
  960.         ld h,(iy+app.stderr)
  961.         ret
  962.  
  963. BDOS_getkeymatrix
  964. ;out: bcdehlix = полуряды cs...space
  965.         ld hl,(appaddr)
  966.         ld de,(focusappaddr)
  967.         or a
  968.         sbc hl,de
  969.         jr nz,BDOS_getkeymatrix_fail
  970.         ld bc,0x7ffe
  971.         in a,(c)
  972.         ld lx,a  ;lx=%???bnmS_
  973.         ld b,0xbf
  974.         in a,(c)
  975.         ld hx,a  ;hx=%???hjklE
  976.         ld b,0xdf
  977.         in l,(c)  ;l=%???yuiop
  978.         ld b,0xef
  979.         in h,(c)  ;h=%???67890
  980.         ld b,0xf7
  981.         in e,(c)  ;e=%???54321
  982.         ld b,0xfb
  983.         in d,(c)  ;d=%???trewq
  984.         ld a,0xfd
  985.         in a,(0xfe);c=%???gfdsa
  986.         ld b,c;0xfe
  987.         in b,(c)  ;b=%???vcxzC
  988.         ld c,a
  989.          xor a ;z
  990.         ret
  991. BDOS_getkeymatrix_fail
  992. ;nz
  993.         ld bc,0xffff
  994.         ld d,c
  995.         ld e,c
  996.         ld h,c
  997.         ld l,c
  998.         push bc
  999.         pop ix
  1000.         ret
  1001.  
  1002. BDOS_gettimerX
  1003. BDOS_gettimer
  1004.         ld hl,(sys_timer+2) ;ok
  1005.         ld de,(sys_timer) ;ok
  1006.          ld a,(sys_timer+2) ;ok
  1007.          sub l
  1008.          jr nz,BDOS_gettimerX ;для атомарности
  1009.         ret ;a=0
  1010.        
  1011. ;BDOS_yield
  1012. ;        ex af,af'
  1013. ;        or a
  1014. ;        jr z,BDOS_yieldnokeep
  1015. ;        ;dec (iy+app.lasttime)
  1016. BDOS_yieldkeep
  1017.          ld a,(sys_timer) ;ok
  1018.          dec a
  1019.          jr BDOS_yieldgo
  1020.          ;ld (iy+app.lasttime),a
  1021. ;BDOS_yieldnokeep
  1022. BDOS_yield
  1023.          ld a,(sys_timer) ;ok
  1024. BDOS_yieldgo
  1025.          ld (iy+app.lasttime),a
  1026. ;регистры не сохраняем, т.к. нам не важно, что на выходе из yield
  1027.         if 1==1
  1028. ;но надо:
  1029. ;взять адрес стека для выхода из CALLBDOS и записать его в ld sp на выходе из обработчика прерываний
  1030. ;взять адрес возврата из CALLBDOS и записать его в jp на выходе из обработчика прерываний
  1031. ;на выходе надо вручную выставить везде pgkillable!
  1032.         ;ld iy,(appaddr)
  1033.        
  1034.         if bdosstack_sz==0
  1035.         ld hl,(callbdos_sp)
  1036.         else
  1037.         ;ld l,(iy+app.callbdos_sp)
  1038.         ;ld h,(iy+app.callbdos_sp+1)
  1039.         exx
  1040.         endif
  1041.  
  1042.         ;call setmainpg_c000
  1043.          ;halt ;проверка на вшивость
  1044.         ;ld (intsp+0xc000),hl
  1045.  
  1046.         ;ex de,hl
  1047.         ld de,-6
  1048.         add hl,de ;место в стеке под 3 рег.пары (а потом адрес возврата из bdos)
  1049.         ld (iy-2),l
  1050.         ld (iy-1),h ;sp в описателе текущей задачи
  1051.         ;call BDOS_preparedepage
  1052.         ;call BDOS_setdepage ;включается сразу 2 страницы на случай sp на границе страниц
  1053.         ;ex de,hl
  1054.          ;halt ;проверка на вшивость        
  1055.         ;ld e,(hl)
  1056.         ;inc hl
  1057.         ;ld d,(hl) ;вместо адреса возврата из bdos
  1058.  
  1059.         ;call setmainpg_c000
  1060.          ;halt ;проверка на вшивость
  1061.         ;ld (intjp+0xc000),de ;TODO при многозадачности в кернале это надо делать атомарно вместе с записью sp!
  1062.         endif
  1063.        
  1064.         ;ld a,pgkillable
  1065.         ;call sys_setpgc000
  1066.         ;call sys_setpg8000
  1067.         ;call setpgs_killable
  1068.        
  1069.         if bdosstack_sz !=0
  1070.         ld a,0xc0
  1071.         ld (callbdos_mutex),a ;то же самое делают те функции BDOS, которые не собираются возвращаться
  1072.         endif
  1073.  
  1074. ;не выходим из CALLBDOS, взамен шедулим и выходим через конец обработчика прерываний
  1075.  
  1076. BDOS_yield_q
  1077.  
  1078. ;        push iy
  1079.         call schedule ;out: iy=app ;можно с включенными прерываниями, пока системный обработчик не умеет шедулить
  1080.         call setpgs_killable ;во всех случаях!
  1081.          ;halt ;проверка на вшивость
  1082. ;        pop de
  1083. ;        or a
  1084. ;        sbc hl,de
  1085. ;        jr nz,BDOS_yield_nosame
  1086. ;        ld iy,app1 ;idle (TODO вместо этого сделать полноценные приоритеты)
  1087. ;        ld (appaddr),iy
  1088. ;BDOS_yield_nosame
  1089.        
  1090.         ;di ;TODO critical section
  1091.        
  1092.         jp sys_int_popregs ;там ei
  1093.        
  1094. BDOS_newapp
  1095. ;пока структура не заполнена до конца, нельзя делать runapp
  1096. ;out: b=id, dehl=номера страниц в 0000,4000,8000,c000 нового приложения, a=error
  1097.         BDOSSETPGTRDOSFS
  1098.         jp sys_newapp_forBDOS
  1099.  
  1100. BDOS_findapp
  1101. ;nz=error
  1102.         ld iy,app1
  1103.         ld a,e
  1104.         ld de,app_sz
  1105.         ld b,MAXAPPS
  1106. BDOS_findapp0
  1107.         cp (iy+app.id)
  1108.         ret z
  1109.         add iy,de
  1110.         djnz BDOS_findapp0
  1111.         ret ;nz
  1112.        
  1113. BDOS_dropapp
  1114. ;e=id
  1115.         call BDOS_findapp
  1116.         jp nz,BDOS_fail ;BDOS_popfail
  1117.         push iy
  1118.         call BDOS_freezeapp_go
  1119.         pop iy
  1120. BDOS_delapppages
  1121.          push iy
  1122.          call activateparent
  1123.          pop iy
  1124.         ld hl,tsys_pages
  1125.         ld a,(iy+app.id)
  1126.         ld b,sys_npages&0xff
  1127. sys_quit_delpages0
  1128.         cp (hl) ;страница снимаемой задачи
  1129.         jr nz,$+4
  1130.         ld (hl),0 ;освободили страницу
  1131.         inc hl
  1132.         djnz sys_quit_delpages0
  1133.                 if INETDRV
  1134.                 BDOSSETPGW5300
  1135.                 call w53_drop_socs
  1136.                 endif
  1137.         if 1==1
  1138.         call BDOS_setpgstructs
  1139.         ld ix,ffilearray
  1140.         ld b,MAXFILES
  1141. BDOS_dropapp_closefiles0
  1142.         ld de,FIL_sz
  1143.         ld a,(ix+FIL.PAD1)
  1144.         cp (iy+app.id)
  1145.         jr nz,BDOS_dropapp_closefiles_skip
  1146.         push bc
  1147.         push ix
  1148.         pop de
  1149.         push de
  1150.         F_CLOS_CURDRV
  1151.         pop ix
  1152.         pop bc
  1153. BDOS_dropapp_closefiles_skip
  1154.         add ix,de
  1155.         djnz BDOS_dropapp_closefiles0
  1156.         endif
  1157.         ld a,(muzpid)
  1158.         cp (iy+app.id)
  1159.         call z,killmuz
  1160.         xor a ;ok
  1161.         ld (iy+app.id),a ;b;0 ;освободили место
  1162.         ret
  1163.        
  1164. open_keeppid
  1165.         push af
  1166.         push de
  1167.         inc de
  1168.         inc de
  1169.         inc de
  1170.         inc de
  1171.         inc de
  1172.     push bc
  1173.     call BDOS_setpgstructs
  1174.     pop bc
  1175.         ld a,(iy+app.id)
  1176.         ld (de),a
  1177.         pop de
  1178.         pop af
  1179.         ret
  1180.  
  1181. BDOS_runapp
  1182. ;e=id
  1183.         ;push iy
  1184.         call BDOS_findapp
  1185.         jp nz,BDOS_fail ;BDOS_popfail
  1186.         set factive,(iy+app.flags)
  1187.         ;pop iy
  1188.         xor a
  1189.         ret
  1190.  
  1191. BDOS_setwaiting
  1192.          ;set fwaiting,(iy+app.flags)
  1193.          res factive,(iy+app.flags)
  1194.         ret
  1195.  
  1196. ;TODO remove?
  1197. BDOS_waitpid
  1198. ;e=id
  1199. ;check for app close (a=0 and reset waiting, or else a!=0)
  1200.          push iy
  1201.          ;set fwaiting,(iy+app.flags)
  1202.         ld c,(iy+app.id) ;my (parent's) id ;caller is the parent
  1203.         push bc
  1204.         call BDOS_findapp ;iy=found app
  1205.         pop bc
  1206.         ld a,(iy+app.parentid)
  1207.          pop iy
  1208.         jr nz,BDOS_waitpid_OK ;app doesn't exist = OK
  1209.         cp c ;parent id
  1210.         jp z,BDOS_fail ;existing app = fail
  1211. BDOS_waitpid_OK
  1212.          ;res fwaiting,(iy+app.flags)
  1213.         xor a
  1214.         ret
  1215.  
  1216. BDOS_setgfx
  1217.         ;ld iy,(appaddr)
  1218. ;e=0:EGA, e=2:MC, e=3:6912, e=6:text ;+8 = noturbo ;+128=keep screen
  1219. ;e=-1: disable gfx (out: e=old gfxmode)
  1220.         push de
  1221.         bit 7,(iy+app.gfxkeep)
  1222.         jr z,BDOS_setgfx_nkept
  1223.         ld e,(iy+app.scr0low)
  1224.         call BDOS_delpage
  1225.         ld e,(iy+app.scr0high)
  1226.         call BDOS_delpage
  1227.         ld e,(iy+app.scr1low)
  1228.         call BDOS_delpage
  1229.         ld e,(iy+app.scr1high)
  1230.         call BDOS_delpage        
  1231. BDOS_setgfx_nkept
  1232.         pop de
  1233.         ld a,e
  1234.         cp -1
  1235.         jr z,BDOS_setgfx_gfxoff;BDOS_gfxoff_givefocus
  1236.                 IFDEF NOTURBO
  1237.                 ELSE
  1238.         xor 0x08;%00001000 ;+8 = noturbo
  1239.                 ENDIF
  1240.         ld (iy+app.gfxkeep),a ;b7 = keep gfx pages
  1241.         push af
  1242.         rla
  1243.         jr nc,BDOS_setgfx_nokeep
  1244. ;TODO return error if error
  1245.         call BDOS_newpage_iy ;out: a=0 (OK)/0xff (fail), e=page
  1246.         ld (iy+app.scr0low),e
  1247.         call BDOS_newpage_iy ;out: a=0 (OK)/0xff (fail), e=page
  1248.         ld (iy+app.scr0high),e
  1249.         call BDOS_newpage_iy ;out: a=0 (OK)/0xff (fail), e=page
  1250.         ld (iy+app.scr1low),e
  1251.         call BDOS_newpage_iy ;out: a=0 (OK)/0xff (fail), e=page
  1252.         ld (iy+app.scr1high),e        
  1253. BDOS_setgfx_nokeep
  1254.         pop af
  1255.         or 0xa0;%10100000
  1256.         ld (iy+app.gfxmode),a
  1257.  
  1258.         call enablescreeninapp_nokeep ;enablescreeninapp_setc000
  1259.        
  1260. ;кладём фокус в стек, только если не два раза setgfx в одной задаче:
  1261.         ld hl,(focusappaddr)
  1262.         push iy
  1263.         pop de
  1264.         or a
  1265.         sbc hl,de
  1266.         jr z,BDOS_setgfx_nopushfocus
  1267.         ;jr $
  1268.         add hl,de
  1269.         push de;iy
  1270.         push hl
  1271.         pop iy
  1272.         call disablescrpgs_setc000 ;у старой focusapp отключить экран в переменных и в памяти
  1273.         pop iy
  1274.        
  1275.          ld hl,(oldfocusappaddr)
  1276.          ld (oldoldfocusappaddr),hl ;TODO стек фокусов (чтобы после закрытия задачи вернуть фокус вызвавшей)
  1277.         ld hl,(focusappaddr)
  1278.         ld (oldfocusappaddr),hl ;TODO стек фокусов (чтобы после закрытия задачи вернуть фокус вызвавшей)
  1279.         ld (focusappaddr),iy
  1280.         call setpalettechanged
  1281. BDOS_setgfx_nopushfocus        
  1282.         set fgfx,(iy+app.flags)
  1283.         ld e,(iy+app.gfxmode)
  1284.         ;xor a ;success
  1285.         ret
  1286. BDOS_setgfx_gfxoff
  1287.         call disablescrpgs_setc000 ;у старой focusapp отключить экран в переменных и в памяти
  1288.         ld e,(iy+app.gfxmode)
  1289.         push de
  1290.         call BDOS_gfxoff_givefocus ;spoils iy!
  1291.         pop de
  1292.         ret
  1293. disablescreeninapp_setc000
  1294.         call setmainpg_c000
  1295. disablescreeninapp
  1296.         ld a,pgkillable
  1297.         ld (0xc000+user_scr0_low),a
  1298.         ld (0xc000+user_scr0_high),a
  1299.         ld (0xc000+user_scr1_low),a
  1300.         ld (0xc000+user_scr1_high),a
  1301.         ret
  1302. enablescreeninapp_setc000
  1303.         bit 7,(iy+app.gfxkeep)
  1304.         jr z,enablescreeninapp_nokeep
  1305.         ld e,pgscr0_0
  1306.         ld a,(iy+app.scr0low)
  1307.         call copypage_a_to_e
  1308.         ld e,pgscr0_1
  1309.         ld a,(iy+app.scr0high)
  1310.         call copypage_a_to_e
  1311.         ld e,pgscr1_0
  1312.         ld a,(iy+app.scr1low)
  1313.         call copypage_a_to_e
  1314.         ld e,pgscr1_1
  1315.         ld a,(iy+app.scr1high)
  1316.         call copypage_a_to_e
  1317. enablescreeninapp_nokeep
  1318.         call setmainpg_c000
  1319.         ld a,pgscr0_0
  1320.         ld (0xc000+user_scr0_low),a
  1321.         ld a,pgscr0_1
  1322.         ld (0xc000+user_scr0_high),a
  1323.         ld a,pgscr1_0
  1324.         ld (0xc000+user_scr1_low),a
  1325.         ld a,pgscr1_1
  1326.         ld (0xc000+user_scr1_high),a
  1327.         ret
  1328.        
  1329. BDOS_freezeapp
  1330. ;e=id
  1331.         ;push iy
  1332.         call BDOS_findapp
  1333.         jp nz,BDOS_fail ;BDOS_popfail
  1334. BDOS_freezeapp_go
  1335.         ;ld (iy+app.flags),0 ;пока тут 0, задачу никто не будет трогать
  1336.         res factive,(iy+app.flags)
  1337. BDOS_gfxoff_givefocus
  1338.         res fgfx,(iy+app.flags) ;если в конце, то по дороге могут вручную переключить фокус, а если в начале, то ...
  1339. ;если фокус у этой задачи, то дать фокус какой-нибудь графической задаче
  1340.         push iy
  1341.         pop hl
  1342.         ld de,(focusappaddr)
  1343.         xor a
  1344.         sbc hl,de
  1345.         ret nz ;jr nz,sys_quit_findgfxapp_fail ;фокус не у этой задачи
  1346.        
  1347.          ;jr $
  1348. oldfocusappaddr=$+1
  1349.         ld hl,app1
  1350. oldoldfocusappaddr=$+1
  1351.          ld de,app1
  1352.          ld (oldfocusappaddr),de
  1353.         bit fgfx,(hl)
  1354.         jr nz,sys_quit_findgfxappq ;TODO стек фокусов (чтобы после закрытия задачи вернуть фокус вызвавшей)
  1355.        
  1356.         ld hl,app1
  1357.         ld bc,-app_last;app_afterlast
  1358.         ld de,app_last+app_sz;app_sz
  1359. sys_quit_findgfxapp0
  1360.         add hl,bc
  1361.         jr c,sys_quit_findgfxapp_fail ;уже проверили app_last, у него нет фокуса - некому давать фокус
  1362.         add hl,de
  1363.         bit fgfx,(hl)
  1364.         jr z,sys_quit_findgfxapp0
  1365. sys_quit_findgfxappq
  1366.         ld (focusappaddr),hl
  1367.         call setpalettechanged
  1368.         push hl
  1369.         pop iy
  1370.         call enablescreeninapp_setc000 ;включить экран в переменные этой задачи
  1371.        
  1372.          ;ld a,key_redraw
  1373.          ;ld (curkey),a
  1374.          ;ld bc,key_redraw
  1375.          ; ld (keyqueueput_codenolang),bc
  1376.          ;call KEYQUEUEPUT
  1377.          call KEY_PUTREDRAW
  1378. sys_quit_findgfxapp_fail
  1379.         ;pop iy
  1380.         xor a
  1381.         ret
  1382.  
  1383. BDOS_newpage
  1384.         ;ld iy,(appaddr)
  1385. BDOS_newpage_iy
  1386. ;out: a=0 (OK)/0xff (fail), e=page
  1387.        if TOPDOWNMEM
  1388.         ld hl,tsys_pages +sys_npages-1
  1389.         ld bc,sys_npages
  1390.         xor a
  1391.         cpdr
  1392.         jr nz,BDOS_fail
  1393.         inc hl
  1394.         ld a,(iy+app.id)
  1395.         ld (hl),a
  1396.         ld a,pagexor;0x7f
  1397.         sub c ;c=0..sys_npages-1
  1398.        else
  1399.         ld hl,tsys_pages
  1400.         ;push hl
  1401.         ld bc,sys_npages
  1402.         xor a
  1403.         cpir
  1404.         ;pop de
  1405.         jr nz,BDOS_fail
  1406.         dec hl
  1407.         ld a,(iy+app.id)
  1408.         ld (hl),a
  1409.          ;or a
  1410.          ;sbc hl,de ;hl=(0..sys_npages-1)
  1411.         ;ld a,pagexor;0x7f
  1412.         ;sub l ;l=0..sys_npages-1
  1413.         ld a,0xff&(pagexor-(sys_npages-1))
  1414.         add a,c
  1415.        endif
  1416.         ld e,a ;page
  1417. BDOS_OK
  1418.         xor a
  1419.         ret ;a=0 (OK), e=page
  1420.  
  1421. BDOS_pop2fail
  1422.         pop af
  1423. BDOS_popfail
  1424.         pop af
  1425. BDOS_fail
  1426.         ld a,0xff
  1427.         ret
  1428.  
  1429. BDOS_delpage
  1430. ;e=page
  1431. ;не портит de
  1432.         ld a,e
  1433.         call addrpage
  1434.         ld (hl),b ;0
  1435.         ret ;a=0
  1436.  
  1437. addrpage
  1438.         xor pagexor;0x7f
  1439.         ld c,a
  1440.         ld hl,tsys_pages
  1441.         xor a
  1442.         ld b,a
  1443.         add hl,bc
  1444.         ret
  1445.  
  1446. ;DEPRECATED!!!!!
  1447. BDOS_fdel
  1448.         call BDOS_preparedepage
  1449.         call BDOS_setdepage ;TODO убрать в драйвер
  1450. ;DE = Pointer to unopened FCB
  1451.         CHECKVOLUMETRDOS
  1452.         jr c,BDOS_fdel_noFATFS
  1453.  
  1454.         call get_name
  1455.         ld de,mfil
  1456.         F_UNLINK_CURDRV
  1457.         ;or a:jp z,fexit
  1458.         ;ld a,0xff
  1459.         ret;jp fexit
  1460. BDOS_fdel_noFATFS
  1461.         BDOSSETPGTRDOSFS
  1462. ;DE = Pointer to unopened FCB
  1463.         jp nfdel
  1464.  
  1465. BDOS_rndrdwrseek
  1466. ;DE = Pointer to opened FCB
  1467.        push de
  1468.         ld hl,0x21 ;outsize FCB_sz!!!
  1469.         add hl,de
  1470.         ld c,(hl)
  1471.         inc hl
  1472.         ld b,(hl)
  1473.         push bc ;record number BC
  1474.         call getFILfromFCB ;hl=FIL
  1475.         ex de,hl ;de=fil (2 words in stack = shift)        
  1476.         push de
  1477.         call BDOS_getfilesize_filde
  1478.          ;jr $
  1479. ;dehl=filesize (no more than 8M in CP/M finction)
  1480. ;highest record number = dehl/128???
  1481.         add hl,hl
  1482.         rl e
  1483.         ld l,h
  1484.         ld h,e
  1485. ;highest record number = dehl/128-1??? wrong!
  1486.         ;add hl,hl
  1487.         ;rl e
  1488.         ;ld l,h
  1489.         ;ld h,e
  1490.         ; ld a,h
  1491.         ; or l
  1492.         ; jr z,$+3
  1493.         ; dec hl
  1494. ;highest record number = (dehl-1)/128??? wrong!
  1495.         ;ld a,h
  1496.         ;or l
  1497.         ;dec hl
  1498.         ;jr nz,$+3
  1499.         ;dec de
  1500.         ;add hl,hl
  1501.         ;rl e
  1502.         ;ld l,h
  1503.         ;ld h,e
  1504.         ; ld a,h
  1505.         ; and l
  1506.         ; inc a
  1507.         ; jr nz,$+3
  1508.         ; inc hl
  1509.         pop de
  1510.         pop bc ;record number BC
  1511.         call minhl_bc_tobc        
  1512.         ld l,b ;HSB from BC
  1513.         ld h,0
  1514.         srl l
  1515.         push hl ;HSW
  1516.         ld b,c
  1517.         ld c,h;0
  1518.         rr b
  1519.         rr c
  1520.         push bc ;LSW
  1521.         F_LSEEK_CURDRV        
  1522.         pop bc
  1523.         pop bc
  1524.        pop de
  1525.         ret
  1526.  
  1527. ;TODO TR-DOS???
  1528. BDOS_rndrd
  1529.         call BDOS_preparedepage
  1530.         call BDOS_setdepage
  1531. ;DE = Pointer to opened FCB
  1532.         call BDOS_rndrdwrseek
  1533.          call BDOS_setdepage
  1534.         jr BDOS_fread_gofatfs
  1535.  
  1536. ;TODO TR-DOS???
  1537. BDOS_rndwr
  1538.         call BDOS_preparedepage
  1539.         call BDOS_setdepage
  1540. ;DE = Pointer to opened FCB
  1541.         call BDOS_rndrdwrseek
  1542.          call BDOS_setdepage
  1543.         jr BDOS_fwrite_gofatfs
  1544.  
  1545. BDOS_fread
  1546.         call BDOS_preparedepage
  1547.         call BDOS_setdepage ;TODO убрать в драйвер
  1548. ;DE = Pointer to opened FCB
  1549.         ;CHECKVOLUMETRDOS
  1550.         ld a,(de)
  1551.         cp vol_trdos
  1552.         jr c,BDOS_fread_noFATFS
  1553. BDOS_fread_gofatfs
  1554. ;достать из него адрес ffile
  1555.         call getFILfromFCB ;hl=FIL
  1556.         call BDOS_getdta ;de = disk transfer address
  1557.        push de
  1558.         call BDOS_preparedepage
  1559.         call BDOS_setdepage ;TODO убрать в драйвер
  1560.         ld b,d
  1561.         ld c,e
  1562.         ld de,blocksize
  1563.          push de ;blocksize
  1564.         ld ix,fres
  1565.         push ix ;fres
  1566.         push de ;blocksize
  1567.         ex de,hl;ld de,ffile
  1568.         F_READ_CURDRV
  1569. BDOS_fread_fatfsq        
  1570.         pop bc
  1571.         pop bc
  1572.         ld a,(bc)
  1573.          pop bc ;blocksize
  1574.        pop de ;de = disk transfer address
  1575.         ;call movedma_addr ;+bc ;TODO remove!!!
  1576.         xor 0x80 ;!=, если прочитали не 128 байт ;TODO remove!!!
  1577. ;a=0: OK (прочитали 128 байт)
  1578. ;a=128: fail (прочитали 0 байт)
  1579. ;a=???: OK (последний блок файла меньше 128 байт)
  1580.         ret z
  1581.         cp 0x80
  1582.         ret z ;fail
  1583. ;for CP/M compatibility: fill unused part of sector with 0x1a
  1584.         push af
  1585.         ;call BDOS_getdta ;de = disk transfer address
  1586.         call BDOS_preparedepage
  1587.         call BDOS_setdepage ;нельзя надеяться на включение выше, если будет убрано в драйвер (т.к. это могло быть не последнее включение страницы)
  1588.         pop af
  1589.         push af
  1590. ;a=128+bytes loaded
  1591.         neg
  1592. ;a=128-bytes loaded
  1593.         ld b,a
  1594.         ld a,e
  1595.         add a,127
  1596.         ld e,a
  1597.         adc a,d
  1598.         sub e
  1599.         ld d,a ;de= Point to buffer end
  1600.         ld a,0x1a
  1601.         ld (de),a
  1602.         dec de
  1603.         djnz $-2
  1604.         pop af
  1605.         ret;jp fexit
  1606. BDOS_fread_noFATFS
  1607.         BDOSSETPGTRDOSFS
  1608. ;DE = Pointer to opened FCB (0x8000+/0xc000+)
  1609.         jp trdos_fread
  1610.  
  1611. BDOS_fwrite
  1612.         call BDOS_preparedepage
  1613.         call BDOS_setdepage ;TODO убрать в драйвер
  1614. ;DE = Pointer to opened FCB
  1615.         ;CHECKVOLUMETRDOS
  1616.         ld a,(de)
  1617.         cp vol_trdos
  1618.         jr c,BDOS_fwrite_noFATFS
  1619. BDOS_fwrite_gofatfs
  1620. ;достать из него адрес ffile
  1621.         call getFILfromFCB ;hl=FIL
  1622.         call BDOS_getdta ;de = disk transfer address
  1623.        push de
  1624.         call BDOS_preparedepage
  1625.         call BDOS_setdepage ;TODO убрать в драйвер
  1626.         ld b,d
  1627.         ld c,e
  1628.         ld de,blocksize
  1629.          push de ;blocksize
  1630.         ld ix,fres
  1631.         push ix ;fres
  1632.         push de ;blocksize
  1633.         ex de,hl;ld de,ffile
  1634.         F_WRITE_CURDRV
  1635.         jr BDOS_fread_fatfsq
  1636. BDOS_fwrite_noFATFS
  1637.         BDOSSETPGTRDOSFS
  1638. ;DE = Pointer to opened FCB
  1639.         jp trdos_fwrite
  1640.  
  1641.         if 1==0
  1642. BDOS_fwrite_nbytes
  1643.         call BDOS_preparedepage
  1644.         call BDOS_setdepage ;TODO убрать в драйвер
  1645. ;DE = Pointer to opened FCB
  1646. ;hl = bytes
  1647.         ;CHECKVOLUMETRDOS
  1648.         ld a,(de)
  1649.         cp vol_trdos
  1650.         jr c,BDOS_fwrite_nbytes_noFATFS
  1651. ;достать из него адрес ffile
  1652.          push hl ;bytes
  1653.         call getFILfromFCB ;hl=FIL
  1654.  
  1655.         call BDOS_getdta ;de = disk transfer address
  1656.         call BDOS_preparedepage
  1657.         call BDOS_setdepage ;TODO убрать в драйвер
  1658.         ld b,d
  1659.         ld c,e
  1660.         ;ld de,blocksize
  1661.          pop de ;bytes
  1662.          push de ;blocksize
  1663.         ld ix,fres
  1664.         push ix ;fres
  1665.         push de ;blocksize
  1666.         ex de,hl;ld de,ffile
  1667.         F_WRITE_CURDRV
  1668.         jr BDOS_fread_fatfsq
  1669. BDOS_fwrite_nbytes_noFATFS
  1670.         BDOSSETPGTRDOSFS
  1671. ;DE = Pointer to opened FCB
  1672. ;hl = bytes
  1673.         ld b,h
  1674.         ld c,l
  1675.         jp trdos_fwrite_nbytes
  1676.         endif
  1677.  
  1678. ;de=path
  1679. ;hl=FILINFO buffer
  1680. BDOS_getfilinfo
  1681.         push hl ;FILINFO buffer
  1682.         call BDOS_preparedepage
  1683.         call BDOS_setdepage
  1684.         call countfiledrive
  1685.         pop bc
  1686.         F_STAT
  1687.         ret
  1688.        
  1689. count_fdir
  1690.         push iy
  1691.         pop de
  1692.         ld hl,app.dir
  1693.         add hl,de
  1694.         ex de,hl
  1695.         ret
  1696.  
  1697. ;de=path
  1698. BDOS_opendir
  1699.         call BDOS_preparedepage
  1700.         call BDOS_setdepage
  1701.         call countfiledrive
  1702.         ld b,d
  1703.         ld c,e
  1704.         CHECKVOLUMETRDOS
  1705.         jr c,BDOS_opendir_noFATFS
  1706. BDOS_opencurdir
  1707.         call count_fdir ;LD de,fdir
  1708.         F_OPDIR_CURDRV
  1709.         ret
  1710.  
  1711. BDOS_opendir_noFATFS
  1712.        push af
  1713.         BDOSSETPGTRDOSFS
  1714.        pop af
  1715.        ld (trdoscurdrive),a
  1716.         ld hl,trdos_catbuf
  1717.         call writedircluster_hl        
  1718.         ld de,0x0000 ;track,sector
  1719.        ld (hl),e;0
  1720.         ld bc,0x0905 ;read 9 sectors
  1721.         call iodos.
  1722.         xor a ;no error
  1723.         ret
  1724.  
  1725. ;de=buf for FILINFO, 0x00 in FILINFO_FNAME = end dir
  1726. BDOS_readdir
  1727.         call BDOS_preparedepage
  1728.         call BDOS_setdepage
  1729.         ld b,d
  1730.         ld c,e
  1731.         CHECKVOLUMETRDOS
  1732.         jr c,BDOS_readdir_noFATFS
  1733.         call count_fdir ;LD de,fdir
  1734.         F_RDIR_CURDRV
  1735.         ret
  1736.        
  1737. BDOS_readdir_noFATFS
  1738. ;bc=addrto
  1739.         push bc
  1740.         BDOSSETPGTRDOSFS
  1741.         ld l,(iy+app.dircluster)
  1742.         ld h,(iy+app.dircluster+1)
  1743.         ld de,fcb2+FCB_FNAME
  1744.         call trdos_searchnext
  1745.         jp z,BDOS_popfail ;fsearchnext_nofile;BDOS_fsearch_loadloop_noFATFS_empty
  1746.         call writedircluster_hl
  1747.         pop de
  1748. ;de=addrto
  1749.         ld hl,fcb2+FCB_FSIZE
  1750.         ld bc,4
  1751.         ldir
  1752.         ld hl,fcb2+FCB_FDATE
  1753.         ld c,2
  1754.         ldir
  1755.         ld hl,fcb2+FCB_FTIME
  1756.         ld c,2
  1757.         ldir
  1758.         ld hl,fcb2+FCB_FATTRIB
  1759.         ldi
  1760.         ld hl,fcb2+FCB_FNAME
  1761.         call get_name_hltode ;делает из имени без точки имя с точкой
  1762.         ld h,d
  1763.         ld l,e
  1764.         ld bc,12
  1765.         xor a ;no error
  1766.         ld (hl),a
  1767.                 inc de
  1768.         ldir ;независимо от длины короткого имени он длинное затирает
  1769.         ret
  1770. ;FILINFO_FSIZE=0;               DWORD           ;/* FILE SIZE */
  1771. ;FILINFO_FDATE=4;               WORD            ;/* LAST MODIFIED DATE */
  1772. ;FILINFO_FTIME=6;               WORD            ;/* LAST MODIFIED TIME */
  1773. ;FILINFO_FATTRIB=8;             BYTE            ;/* ATTRIBUTE */
  1774. ;FILINFO_FNAME=9;               BLOCK 13,0      ;/* SHORT FILE NAME (8.3 FORMAT with dot and terminator) */
  1775. ;FILINFO_LNAME=22;              BLOCK DIRMAXFILENAME64,0        ;/* LONG FILE NAME (ASCIIZ) */
  1776. ;FILINFO_sz=FILINFO_LNAME+DIRMAXFILENAME64
  1777.  
  1778.  
  1779. ;SEARCH FOR FIRST [FCB] (11H)
  1780. ;     Parameters:    C = 11H (_SFIRST)
  1781. ;                   DE = Pointer to unopened FCB
  1782. ;     Results:     L=A = 0FFH if file not found
  1783. ;                      =   0  if file found.
  1784. ;The filename may be ambiguous (containing "?" characters) in which case the first match will be found.
  1785. ;The low byte of the extent field will be used, and a file will only be found if it is big enough
  1786. ;to contain this extent number. Normally the extent field will be set to zero by the program before
  1787. ;calling this function. System file and sub-directory entries will not be found.
  1788. ;If a suitable match is found (A=0) then the directory entry will be copied to the DTA address,
  1789. ;preceded by the drive number. This can be used directly as an FCB for an OPEN function call if desired.
  1790. ;The extent number will be set to the low byte of the extent from the search FCB, and the record count
  1791. ;will be initialized appropriately (as for OPEN). The attributes byte from the directory entry will be
  1792. ;stored in the S1 byte position, since its normal position (immediately after the filename extension field)
  1793. ;is used for the extent byte.
  1794. BDOS_fsearchfirst
  1795.         call BDOS_preparedepage
  1796.         call BDOS_setdepage ;TODO убрать в драйвер
  1797.          push de ;DE = Pointer to unopened FCB (0x8000+/0xc000+)
  1798.         CHECKVOLUMETRDOS
  1799.         jr c,BDOS_fsearchfirst_noFATFS
  1800.                 ld bc,0 ; TCHAR *path   /* Pointer to the directory path */
  1801.         call BDOS_opencurdir
  1802.  
  1803.          pop de ;DE = Pointer to unopened FCB (0x8000+/0xc000+)
  1804.         or a
  1805.         ret nz;jp nz,fexit
  1806.         jr BDOS_fsearch_goloadloop
  1807. BDOS_fsearchfirst_noFATFS
  1808. ;TR-DOS
  1809.        push af
  1810.         BDOSSETPGTRDOSFS
  1811.        pop af
  1812.        ld (trdoscurdrive),a
  1813.         ld hl,trdos_catbuf
  1814.         ;ld (BDOS_fsearch_loadloop_trdosaddr),hl ;TODO где хранить для многозадачности? возвращать в FCB_DIRPOS?
  1815.         call writedircluster_hl
  1816.        
  1817.         ld de,0x0000 ;track,sector
  1818.        ld (hl),e;0
  1819.         ld bc,0x0905 ;read 9 sectors
  1820.         call iodos.
  1821.          pop de ;DE = Pointer to unopened FCB (0x8000+/0xc000+)
  1822.         jr BDOS_fsearch_goloadloop
  1823.        
  1824. ;SEARCH FOR NEXT [FCB] (12H)
  1825. ;     Parameters:    C = 12H (_SNEXT)
  1826. ;     Results:     L=A = 0FFH if file not found
  1827. ;                      =   0  if file found.
  1828. BDOS_fsearchnext
  1829. ;(not CP/M!!!) для многозадачности принимать тут de = Pointer to unopened FCB
  1830.         call BDOS_preparedepage
  1831.         call BDOS_setdepage ;TODO убрать в драйвер
  1832. BDOS_fsearch_goloadloop
  1833.         inc de
  1834.         ld (fsearchnext_filename),de
  1835. BDOS_fsearch_loadloop
  1836.         ld iy,(appaddr) ;т.к. ffs портит iy
  1837.         CHECKVOLUMETRDOS
  1838.         jr c,BDOS_fsearch_loadloop_noFATFS
  1839.  
  1840.         call count_fdir ;LD de,fdir
  1841.         LD bc,mfilinfo
  1842.         F_RDIR_CURDRV
  1843.          or a
  1844.          jp nz,BDOS_fail ;fsearchnext_nofile ;иначе после удаления файла каталог не заканчивается
  1845.  
  1846. ;переделать структуру FILINFO (которую мы сейчас считали) в структуру FCB
  1847.         ld de,mfilinfo+FILINFO_FNAME
  1848.         ld a,(de)
  1849.         or a
  1850.         jp z,BDOS_fail ;fsearchnext_nofile
  1851.         BDOSSETPGTRDOSFS
  1852.         call trdosgetdirfcb
  1853.         jr BDOS_fsearch_loadloop_FATFSq
  1854. BDOS_fsearch_loadloop_noFATFS
  1855. ;TR-DOS
  1856.         BDOSSETPGTRDOSFS
  1857.         ld l,(iy+app.dircluster)
  1858.         ld h,(iy+app.dircluster+1)
  1859.         ld de,fcb2+FCB_FNAME
  1860.         call trdos_searchnext
  1861.         jp z,BDOS_fail ;fsearchnext_nofile;BDOS_fsearch_loadloop_noFATFS_empty
  1862.         call writedircluster_hl
  1863.         jr BDOS_fsearch_loadloop_FATFSq
  1864. BDOS_fsearch_loadloop_FATFSq
  1865.         ld hl,fcb2+FCB_FNAME ;прочитанное имя
  1866. fsearchnext_filename=$+1
  1867.         ld de,0 ;образец
  1868.        
  1869. ;проверить имя файла hl == de (игнорировать (de)=='?')
  1870.         ld bc,11*256;0x0a00 ;b=bytes to compare, c=errors
  1871. fsearchnext_cp00
  1872.         ld a,[de]
  1873.         cp '?'
  1874.         jr z,fsearchnext_cpskip
  1875.         sub [hl]
  1876.         or c
  1877.         ld c,a ;errors
  1878. fsearchnext_cpskip
  1879.         inc hl
  1880.         inc de
  1881.         djnz fsearchnext_cp00
  1882.        
  1883. ;если не совпало, зациклить
  1884.         ld a,c
  1885.         or a
  1886.         jp nz,BDOS_fsearch_loadloop
  1887. fsearchnext_nofileq
  1888. ;иначе записать в dma
  1889.         ld iy,(appaddr)
  1890.         ld hl,fcb2
  1891.         call BDOS_getdta ;de = disk transfer address
  1892.         call BDOS_preparedepage
  1893.         call BDOS_setdepage ;TODO убрать в драйвер
  1894.         ld bc,FCB_sz;32;16
  1895.          push bc
  1896.         ldir
  1897.          pop bc
  1898.         call movedma_addr ;+bc
  1899.         xor a ;success
  1900.         ret;jp rest_exit
  1901.  
  1902. BDOS_getfiletime
  1903. ;de=Drive/path/file ASCIIZ string
  1904. ;out: ix=date, hl=time
  1905.         call BDOS_preparedepage
  1906.         call BDOS_setdepage ;TODO убрать в драйвер
  1907.         call countfiledrive ;a=volume, de=path without drive, c=1: drive in path, CY=TR-DOS
  1908.         jr c,BDOS_getfiletime_zero
  1909.                 ;push af
  1910.                 ;pop af
  1911.         ld bc,fres
  1912. ;de=name
  1913. ;bc=pointer to time,date
  1914.                 F_GETUTIME
  1915.         ld hl,(fres)
  1916.         ld ix,(fres+2)
  1917.         ;xor a
  1918.         ret
  1919. BDOS_getfiletime_zero
  1920.         ;xor a
  1921.         ;ld l,a
  1922.         ;ld h,a
  1923.         ;push hl
  1924.         ;pop ix
  1925. BDOS_gettime
  1926. ;out: ix=date, hl=time
  1927.                 if atm==1
  1928.                         call readtime
  1929.                 endif
  1930.         ld hl,(sys_time_date) ;ok
  1931.         ld ix,(sys_time_date+2) ;ok
  1932.         ret
  1933.        
  1934.  
  1935. BDOS_setfiletime
  1936. ;de=Drive/path/file ASCIIZ string, ix=date, hl=time
  1937.         call BDOS_preparedepage
  1938.         call BDOS_setdepage ;TODO убрать в драйвер
  1939.         push hl ;time
  1940.         push ix ;date
  1941.         pop bc ;date
  1942. ;de=name
  1943. ;bc=date
  1944. ;stack=time
  1945.         F_UTIME_CURDRV
  1946.         pop bc
  1947.         ret
  1948.        
  1949. BDOS_seekhandle
  1950. ;                    B = File handle
  1951. ;                    [A = Method code: 0=begin,1=cur,2=end]
  1952. ;                DE:HL = Signed offset
  1953. ;     Results:       A = Error
  1954. ;                DE:HL = New file pointer
  1955.         bit 6,b
  1956.         jr nz,BDOS_seekhandle_noFATFS
  1957.         push de ;HSW
  1958.         push hl ;LSW
  1959.         call BDOS_number_to_fil ;de=fil
  1960.         F_LSEEK_CURDRV        
  1961.         pop bc
  1962.         pop bc
  1963.         ret
  1964. BDOS_seekhandle_noFATFS
  1965.         push bc
  1966.         BDOSSETPGTRDOSFS
  1967.         pop bc
  1968.         jp trdos_seekhandle
  1969.  
  1970. BDOS_getfilesize
  1971. ;b=handle
  1972. ;out: dehl=filesize
  1973.         bit 6,b
  1974.         jr nz,BDOS_getfilesize_noFATFS
  1975.         call BDOS_number_to_fil ;de=fil
  1976. BDOS_getfilesize_filde
  1977.         ld hl,FIL.FSIZE
  1978.         jr BDOS_tellhandleq
  1979.         ;add hl,de
  1980.         ;ld e,(hl)
  1981.         ;inc hl
  1982.         ;ld d,(hl)
  1983.         ;inc hl
  1984.         ;ld a,(hl)
  1985.         ;inc hl
  1986.         ;ld h,(hl)
  1987.         ;ld l,a
  1988.         ;ex de,hl
  1989.         ;xor a
  1990.         ;ret
  1991. BDOS_getfilesize_noFATFS
  1992.         push bc
  1993.         BDOSSETPGTRDOSFS
  1994.         pop bc
  1995.         jp trdos_getfilesize ;dehl=filesize
  1996.  
  1997. BDOS_tellhandle
  1998. ;b=file handle, out: dehl=offset
  1999. ;TODO TR-DOS
  2000.         call BDOS_number_to_fil ;de=fil
  2001.         ld hl,FIL.FPTR
  2002. BDOS_tellhandleq
  2003.         call BDOS_setpgstructs
  2004.         add hl,de
  2005.         ld c,(hl)
  2006.         inc hl
  2007.         ld b,(hl)
  2008.         inc hl
  2009.         ld e,(hl)
  2010.         inc hl
  2011.         ld d,(hl)
  2012.         ld h,b
  2013.         ld l,c
  2014.         xor a
  2015.         ret
  2016.        
  2017. BDOS_createhandle
  2018. ;DE = Drive/path/file ASCIIZ string
  2019. ;A = Open mode. b0 set => no write, b1 set => no read, b2 set => inheritable, b3..b7   -  must be clear
  2020. ;B = b0..b6 = Required attributes, b7 = Create new flag
  2021. ;out: B = new file handle, A=error
  2022.         ld c,a
  2023.         ld a,'w'
  2024.         LD HL,FA_READ|FA_WRITE|FA_CREATE_ALWAYS
  2025.         jr BDOS_openorcreatehandle
  2026.  
  2027. BDOS_openhandle
  2028. ;DE = Drive/path/file ASCIIZ string
  2029. ;[A = Open mode. b0 set => no write, b1 set => no read, b2 set => inheritable, b3..b7   -  must be clear]
  2030. ;out: B = new file handle, A=error
  2031.         ld c,a
  2032.         ld a,'r'
  2033.         ld hl,FA_READ|FA_WRITE
  2034. BDOS_openorcreatehandle
  2035.         ld (BDOS_openorcreatehandle_trdosmode),a
  2036.         ld (.mode),hl
  2037.         call BDOS_preparedepage
  2038.         call BDOS_setdepage ;TODO убрать в драйвер
  2039. ;DE = Drive/path/file ASCIIZ string
  2040.         call countfiledrive ;a=volume, de=path without drive, c=1: drive in path, CY=TR-DOS
  2041.         jr c,BDOS_openhandle_noFATFS
  2042.         cp vol_pipe
  2043.         jr z,BDOS_openhandle_pipe
  2044.                 ld (.store_a),a
  2045.         push de
  2046.          ;dec c ;was c=1: drive in path
  2047.          ;call z,BDOS_setvol_rootdir ;drive specified in path
  2048.         call findfreeffile
  2049.          jr nz,$ ;TODO error
  2050.         push bc
  2051.         call BDOS_setdepage ;TODO убрать в драйвер????
  2052.         pop bc
  2053.         ld a,b
  2054.         ex de,hl ;a=fil number, de=poi to FIL
  2055.         pop bc
  2056.         push af
  2057. .mode=$+1
  2058.         LD HL,FA_READ|FA_WRITE
  2059. .store_a=$+1
  2060.                 ld a,0
  2061.         F_OP
  2062.         pop bc ;b=fil number=new file handle
  2063.          ret
  2064.  
  2065. BDOS_openhandle_noFATFS
  2066. ;a=drive
  2067. ;recode file name
  2068.         ;pop af ;z=drive in path
  2069.        push af ;drive
  2070.         BDOSSETPGTRDOSFS
  2071.         ex de,hl ;hl=path
  2072.         call findlastslash. ;de=after last slash or beginning of path
  2073.         ld hl,BDOS_parse_filename_cpmnamebuf
  2074.         push hl
  2075.         call dotname_to_cpmname ;de -> hl ;out: de=pointer to termination character, hl=buffer filled in
  2076.         ;BDOSSETPGTRDOSFS
  2077.         pop de
  2078. BDOS_openorcreatehandle_trdosmode=$+1
  2079.         ld c,'r'
  2080.        pop af ;drive
  2081.         call nfopen ;hl=trdosfcb
  2082.         ld b,h ;new file handle
  2083.         ret
  2084.  
  2085. BDOS_openhandle_pipe
  2086. ;find free pipe
  2087.         ld hl,freepipes
  2088.         xor a
  2089.         ld bc,MAXPIPES
  2090.         cpir
  2091.         jp nz,BDOS_fail
  2092.         dec hl
  2093.          inc (hl)
  2094.         inc (hl) ;opened once, used as stdin and as stdout, closed twice
  2095.         ld a,l
  2096.         add a,0xff&(-freepipes+PIPEADD80)
  2097.         push af ;a=handle
  2098. ;a = PIPEADD80+pipeindex
  2099.         call findpipe_byhandle ;hl=pipe
  2100.         xor a
  2101.         ld (hl),a ;size=0
  2102.         pop bc ;b=handle
  2103. ;b=new pipe handle
  2104.         ret
  2105.  
  2106. BDOS_number_to_fil
  2107. ;b = file handle = 0..
  2108. ;out: de=fil
  2109.         inc b
  2110.         ld hl,ffilearray-FIL_sz
  2111.         ld de,FIL_sz
  2112. BDOS_number_to_fil0
  2113.         add hl,de
  2114.         djnz BDOS_number_to_fil0
  2115.         ex de,hl
  2116.         ret
  2117.        
  2118. BDOS_closehandle
  2119. ;B = file handle
  2120. ;out: A=error
  2121.         bit 7,b
  2122.         jr nz,BDOS_closehandle_pipe
  2123.         bit 6,b
  2124.         jr nz,BDOS_closehandle_noFATFS
  2125.         call BDOS_number_to_fil
  2126. ;de=fil
  2127.         F_CLOS_CURDRV
  2128.         ret
  2129. BDOS_closehandle_noFATFS
  2130.         ld h,b
  2131.         ld l,0
  2132.         BDOSSETPGTRDOSFS
  2133.         jp trdos_fclose_hl
  2134.  
  2135. BDOS_closehandle_pipe
  2136. ;B = file handle
  2137.         inc b
  2138.         ret z ;0xff=rnd
  2139.         ld hl,freepipes-1-PIPEADD80
  2140.         ld c,b
  2141.         xor a
  2142.         ld b,a
  2143.         add hl,bc
  2144.         dec (hl)
  2145.         ret p
  2146.         inc (hl) ;чтобы терминал не думал, а закрывал оба пайпа дважды
  2147.         ret
  2148. freepipes
  2149.         ds MAXPIPES
  2150.  
  2151.        
  2152. BDOS_readwritehandleprepare
  2153. ;b=handle, hl=number of bytes, de=addr
  2154. ;out: hl=fil, de=number of bytes, bc=addr(0x8000+)
  2155.         push hl ;Number of bytes to read
  2156.         push de ;Buffer address
  2157.         call BDOS_number_to_fil ;de=fil
  2158.         ex de,hl ;hl=FIL
  2159.         pop de ;Buffer address
  2160.         call BDOS_preparedepage
  2161.          call BDOS_setdepage ;TODO убрать в драйвер (или уже убрано?)
  2162.         ld b,d
  2163.         ld c,e
  2164.         pop de ;Number of bytes to read
  2165.         ret
  2166.        
  2167. BDOS_readhandle
  2168. ;B = file handle
  2169. ;DE = Buffer address
  2170. ;HL = Number of bytes to read
  2171. ;out: HL = Number of bytes actually read, A=error
  2172.         dec hl
  2173.          ld a,h
  2174.         inc hl
  2175.          cp 0x40
  2176.          jr c,BDOS_readhandlego
  2177.         push hl
  2178.         ld hl,BDOS_readhandlego
  2179. BDOS_readwritehandle
  2180.         ld (BDOS_readwritehandle_proc),hl
  2181.         pop hl
  2182.         ld (BDOS_readwritehandle_oldaddr),de
  2183. BDOS_readwritehandle0
  2184.         push bc
  2185.         push hl
  2186.         push de ;addr
  2187.          dec hl
  2188.          ld a,h
  2189.          inc hl
  2190.          cp 0x40
  2191.          jr c,$+5 ;<=0x4000
  2192.          ld hl,0x4000
  2193.          push hl ;bytes to process
  2194.         ;call BDOS_readwritehandlego ;hl=processed bytes
  2195. BDOS_readwritehandle_proc=$+1
  2196.         call BDOS_readhandlego
  2197. ;TODO что делать, если возвратилось hl==0 или a!=0?
  2198.         ;ex af,af' ;error
  2199.         ;jr $
  2200.          pop bc ;bytes to process
  2201.          or a
  2202.          sbc hl,bc
  2203.          ld a,h
  2204.          or l
  2205.          add hl,bc ;z=all bytes were processed
  2206.         ld b,h
  2207.         ld c,l
  2208.         pop hl ;addr
  2209.         add hl,bc ;+processed bytes
  2210.         ex de,hl ;de = new addr
  2211.         pop hl
  2212.         or a
  2213.         sbc hl,bc ;-processed bytes
  2214.         pop bc
  2215.         jr z,BDOS_readwritehandleq ;0 bytes remain
  2216.         jr c,BDOS_readwritehandleq ;less than 0 bytes remain
  2217.         ;jr nc,BDOS_readwritehandle0 ;no less than 0 bytes remain
  2218.          or a
  2219.         jr z,BDOS_readwritehandle0 ;all bytes were processed
  2220. BDOS_readwritehandleq
  2221. ;0 bytes remain
  2222. ;de=end address
  2223.         ld h,d
  2224.         ld l,e
  2225. BDOS_readwritehandle_oldaddr=$+1
  2226.         ld bc,0
  2227.         xor a ;no error
  2228.         sbc hl,bc ;hl=processed bytes
  2229.         ;ex af,af' ;error
  2230.         jr BDOS_readhandle_errorfromEOF ;ret
  2231. ;BDOS_readwritehandlego
  2232. ;BDOS_readwritehandle_proc=$+1
  2233. ;        jp BDOS_readhandlego
  2234. BDOS_readhandlego
  2235. ;b=handle
  2236.         bit 7,b
  2237.         jr nz,BDOS_readhandle_pipe
  2238.         bit 6,b
  2239.         jr nz,BDOS_readhandle_noFATFS
  2240.         call BDOS_readwritehandleprepare
  2241. ;hl=fil, de=number of bytes, bc=addr(0x8000+)
  2242.         ld ix,fres
  2243.         push ix ;fres
  2244.         push de ;blocksize
  2245.         ex de,hl;ld de,ffile
  2246.         F_READ_CURDRV
  2247.         pop bc
  2248.         pop bc ;fres
  2249.         ld hl,(fres) ;hl=total processed bytes
  2250. BDOS_readhandle_errorfromEOF
  2251.         ;xor a ;no error
  2252.          ld a,h
  2253.          or l
  2254.          ld a,0
  2255.          ret nz
  2256.          dec a
  2257.         ret
  2258. BDOS_readhandle_noFATFS
  2259.         push bc
  2260.         BDOSSETPGTRDOSFS
  2261.         pop bc
  2262.         jp trdos_fread_b ;hl=total processed bytes, A=error
  2263.  
  2264. BDOS_writehandle
  2265. ;B = file handle
  2266. ;DE = Buffer address
  2267. ;HL = Number of bytes to write
  2268. ;out: HL = Number of bytes actually written, A=error
  2269.          ld a,h
  2270.          cp 0x40
  2271.          jr c,BDOS_writehandlego
  2272.         push hl
  2273.         ld hl,BDOS_writehandlego
  2274.         jr BDOS_readwritehandle
  2275. BDOS_writehandlego
  2276. ;B = file handle
  2277. ;DE = Buffer address
  2278. ;HL = Number of bytes to write <= 0x4000
  2279. ;out: HL = Number of bytes actually written, A=error
  2280.         bit 7,b
  2281.         jp nz,BDOS_writehandle_pipe
  2282.         bit 6,b
  2283.         jr nz,BDOS_writehandle_noFATFS
  2284.         call BDOS_readwritehandleprepare
  2285.         ld ix,fres
  2286.         push ix ;fres
  2287.         push de ;blocksize
  2288.         ex de,hl;ld de,ffile
  2289.         F_WRITE_CURDRV
  2290.         pop bc
  2291.         pop bc ;fres
  2292.         ld hl,(fres) ;hl=total processed bytes
  2293.         xor a ;a=0: no error
  2294.         ret
  2295. BDOS_writehandle_noFATFS
  2296.         push bc
  2297.         BDOSSETPGTRDOSFS
  2298.         pop bc
  2299.         jp trdos_fwrite_b ;hl=total processed bytes, a=0: no error
  2300.  
  2301. BDOS_readhandle_pipe
  2302. ;B = file handle
  2303. ;DE = Buffer address
  2304. ;HL = Number of bytes to write <= 0x4000
  2305. ;out: HL = Number of bytes actually written, A=error
  2306. ;TODO check EOF (input closed)
  2307.         push bc
  2308.         call BDOS_preparedepage
  2309.         call BDOS_setdepage
  2310.         pop af ;a=handle
  2311.         cp 0xff
  2312.         jr nz,BDOS_readhandle_pipe_nrnd
  2313.         ld a,r
  2314.         ld (de),a
  2315.         ld hl,1
  2316.         xor a ;no error
  2317.         ret
  2318. BDOS_readhandle_pipe_nrnd
  2319. ;a = PIPEADD80+pipeindex
  2320.          ld (BDOS_readhandle_pipe_handle),a
  2321.         call findpipe_byhandle ;bc=number of bytes
  2322. ;читаем из текущей головы столько байт, сколько есть, но не больше number of bytes
  2323. ;пока делаем, что вся очередь лежит в начале (не атомарно)
  2324.          ld (BDOS_readhandle_pipe_addr),hl
  2325.         ld a,(hl) ;cur_size
  2326.         inc hl
  2327.        push hl ;buf start
  2328.         ld l,a
  2329.         ld h,0
  2330.         call minhl_bc_tobc ;to_user_size=bc<=hl
  2331.        pop hl ;buf start
  2332. ;
  2333.         ex af,af'
  2334.        ld a,b
  2335.        or c
  2336.        jr z,BDOS_readhandle_pipe_empty
  2337.        ex af,af'
  2338.        push bc ;to_user_size
  2339.         ldir ;to user
  2340.        pop bc ;to_user_size
  2341.         ex de,hl
  2342.         ld l,a
  2343.         xor a
  2344.         ld h,a
  2345.        push bc ;to_user_size
  2346. ;bc=cur_size-to_user_size
  2347.         sbc hl,bc
  2348.         ld b,h
  2349.         ld c,l
  2350.         ex de,hl
  2351. BDOS_readhandle_pipe_addr=$+1
  2352.         ld de,0
  2353.          ld a,c
  2354.          ld (de),a
  2355.          inc de
  2356.         jr z,$+4
  2357.         ldir ;на начало очереди
  2358.        pop hl ;to_user_size ;возвращаем, сколько реально прочитано
  2359.         xor a ;no error
  2360.         ret
  2361. BDOS_readhandle_pipe_empty
  2362. ;проверяем, что нет EOF (т.е. не закрыла пишущая сторона)
  2363.         ld hl,freepipes-PIPEADD80
  2364. BDOS_readhandle_pipe_handle=$+1
  2365.         ld bc,0 ;PIPEADD80+pipeindex
  2366.         add hl,bc
  2367.         ld a,(hl) ;2=both sides open, 1=one side closed
  2368.         sub 2 ;a=error
  2369.         ld h,b
  2370.         ld l,b ;0 ;возвращаем, сколько реально прочитано
  2371.         ret
  2372.        
  2373. findpipe_byhandle
  2374.         sub PIPEADD80-1
  2375.         ld b,a
  2376.         push hl ;number of bytes
  2377.         push de ;user space
  2378.         ld de,PIPEDESC_SZ
  2379.         ld hl,pipebufs-PIPEDESC_SZ
  2380.         add hl,de
  2381.         djnz $-1
  2382.         pop de ;user space
  2383.         pop bc ;bc=number of bytes
  2384.         ret
  2385.  
  2386. BDOS_writehandle_pipe
  2387. ;b=handle, hl=number of bytes, de=addr
  2388.         push bc
  2389.         call BDOS_preparedepage
  2390.         call BDOS_setdepage
  2391.         pop af ;a=handle
  2392.         cp 0xff
  2393.         ret z ;rnd - fail
  2394. ;a = PIPEADD80+pipeindex
  2395.          ld (BDOS_writehandle_pipe_handle),a
  2396.         call findpipe_byhandle ;bc=number of bytes
  2397. ;добавляем в текущий хвост столько байт, сколько есть, но чтобы не превысило размер буфера
  2398. ;пока делаем, что вся очередь лежит в начале (не атомарно)
  2399.          ld (BDOS_writehandle_pipe_addr),hl
  2400.         ld a,(hl) ;cur_size
  2401.         inc hl
  2402.         push af
  2403.         add a,l
  2404.         ld l,a
  2405.         jr nc,$+3
  2406.         inc h
  2407.         pop af
  2408.         push hl ;tail
  2409.         ld hl,PIPEBUF_SZ
  2410.         push bc ;bc=number of bytes
  2411.         ld c,a
  2412.         xor a
  2413.         ld b,a
  2414.         sbc hl,bc ;оставшееся место в буфере
  2415.         pop bc ;bc=number of bytes
  2416.         call minhl_bc_tobc ;from_user_size=bc<=hl
  2417. BDOS_writehandle_pipe_addr=$+1
  2418.          ld hl,0
  2419.          ld a,(hl) ;cur_size
  2420.          add a,c ;from_user_size
  2421.          ld (hl),a ;cur_size
  2422.         ex de,hl ;hl=user space
  2423.         pop de ;tail
  2424.         ld a,b
  2425.         or c
  2426.         jr z,BDOS_readhandle_pipe_full
  2427.         push bc ;from_user_size
  2428.         ldir ;from user
  2429.         pop hl ;from_user_size ;возвращаем, сколько реально записано
  2430.         xor a ;no error
  2431.         ret
  2432. BDOS_readhandle_pipe_full
  2433. ;проверяем, что не закрыла читающая сторона
  2434.         ld hl,freepipes-PIPEADD80
  2435. BDOS_writehandle_pipe_handle=$+1
  2436.         ld bc,0 ;PIPEADD80+pipeindex
  2437.         add hl,bc
  2438.         ld a,(hl) ;2=both sides open, 1=one side closed
  2439.         sub 2 ;a=error
  2440.         ld h,b
  2441.         ld l,b ;0 ;возвращаем, сколько реально записано
  2442.         ret
  2443.        
  2444. minhl_bc_tobc
  2445.         or a
  2446.         sbc hl,bc
  2447.         add hl,bc
  2448.         ret nc ;bc<=hl
  2449.         ld b,h
  2450.         ld c,l
  2451.         ret
  2452.  
  2453.  
  2454. BDOS_fopen_getname_fil
  2455. ;out: de=poi to FIL, bc=mfil
  2456.         push de
  2457.         call get_name ;->mfil
  2458.         pop de
  2459.         call findfreeffile
  2460.          jr nz,$ ;TODO error
  2461.         ex de,hl ;de=poi to FIL
  2462.         LD bc,mfil
  2463.         jp nz,BDOS_pop2fail ;снимаем адрес возврата и FCB
  2464.         ret
  2465.        
  2466. BDOS_fopen
  2467.         call BDOS_preparedepage
  2468.         call BDOS_setdepage ;TODO убрать в драйвер
  2469. ;de = pointer to unopened FCB
  2470.         GETVOLUME
  2471.         ld (de),a ;volume
  2472.         cp vol_trdos ;CHECKVOLUMETRDOS
  2473.         jr c,BDOS_fopen_noFATFS
  2474.         push de ;FCB
  2475.         call BDOS_fopen_getname_fil ;de=poi to FIL, bc=mfil
  2476.         LD HL,FA_READ|FA_WRITE
  2477.         jr BDOS_fopen_go
  2478. BDOS_fopen_noFATFS
  2479. ;a=drive
  2480.        push af
  2481.         BDOSSETPGTRDOSFS
  2482.        pop af
  2483.         jp trdos_fopen
  2484.  
  2485. BDOS_fcreate
  2486.         call BDOS_preparedepage
  2487.         call BDOS_setdepage ;TODO убрать в драйвер
  2488. ;DE = Pointer to unopened FCB
  2489.         GETVOLUME
  2490.         ld (de),a ;volume
  2491.         cp vol_trdos ;CHECKVOLUMETRDOS
  2492.         jr c,BDOS_fcreate_noFATFS
  2493.         push de ;FCB
  2494.         call BDOS_fopen_getname_fil ;de=poi to FIL, bc=mfil
  2495.         LD HL,FA_READ|FA_WRITE|FA_CREATE_ALWAYS
  2496. BDOS_fopen_go
  2497.         ;F_OPEN ffile,mfil,FA_READ|FA_WRITE|FA_CREATE_ALWAYS
  2498.         ;LD de,ffile
  2499.         push de ;FIL
  2500.         F_OPEN_CURDRV
  2501.         pop de ;FIL
  2502.         pop bc ;FCB
  2503.         or a
  2504.         ret nz ;error
  2505. ;BDOS_fopen_OK
  2506. ;de=ffile (FIL)
  2507. ;bc=FCB
  2508.         ;ld iy,(appaddr)
  2509.         ;GETVOLUME
  2510.         ;ld (bc),a ;volume
  2511.         ld hl,FCB_FFSFCB
  2512.         add hl,bc
  2513.         push af
  2514.         call BDOS_setdepage
  2515.         pop af
  2516.         ld (hl),e
  2517.         inc hl
  2518.         ld (hl),d
  2519.         ret
  2520. BDOS_fcreate_noFATFS
  2521.        push af
  2522.         BDOSSETPGTRDOSFS
  2523.        pop af
  2524.         jp trdos_fcreate
  2525.  
  2526. getFILfromFCB
  2527. ;de=FCB (страницы уже включены)
  2528. ;out: hl=FIL
  2529.         ld hl,FCB_FFSFCB
  2530.         add hl,de
  2531.         ld a,(hl)
  2532.         inc hl
  2533.         ld h,(hl)
  2534.         ld l,a ;hl = poi to FIL
  2535.         ret
  2536.        
  2537. BDOS_fclose
  2538.         call BDOS_preparedepage
  2539.         call BDOS_setdepage ;TODO убрать в драйвер
  2540. ;DE = Pointer to opened FCB (для FATFS придётся игнорировать, брать текущий ffile - TODO искать подходящий ffile)
  2541.         ;CHECKVOLUMETRDOS
  2542.         ld a,(de)
  2543.         cp vol_trdos
  2544.         jr c,BDOS_fclose_noFATFS
  2545.         ;F_CLOSE ffile ;сам освобождает FIL
  2546.         call getFILfromFCB
  2547.         ex de,hl
  2548.         F_CLOS_CURDRV
  2549. ;TODO убрать poi to FIL из FCB?
  2550.         ;or a:jp z,fexit
  2551.         ;ld a,0xff
  2552.         ret;jp fexit
  2553. BDOS_fclose_noFATFS
  2554.         BDOSSETPGTRDOSFS
  2555.         jp trdos_fclose
  2556.  
  2557.  
  2558. call_ffs_curvol
  2559.                 GETVOLUME
  2560. call_ffs        ;A=логический раздел, HL=функция
  2561. ;портит iy! но нельзя двигать стек! в нём параметры!
  2562.                 push hl
  2563.                 push bc
  2564.         ld hl,fatfsarray ;вычисляем указатель на структуру fatfs
  2565.                 sub vol_trdos
  2566.         ;or a
  2567.         jr z,.fix_vol_dir
  2568.         ld bc,FATFS_sz
  2569. .calcfatfs
  2570.         add hl,bc
  2571.         dec a
  2572.         jr nz,.calcfatfs
  2573. .fix_vol_dir    ;устанавливаем текущие fatfs и директорию
  2574.                 BDOSSETPGFATFS
  2575.         ld (fatfs_org+FFS_DRV.curr_fatfs),hl
  2576.          ld l,(iy+app.dircluster)
  2577.          ld h,(iy+app.dircluster+1)
  2578.         ld (fatfs_org+FFS_DRV.curr_dir0),hl
  2579.          ld l,(iy+app.dircluster+2)
  2580.          ld h,(iy+app.dircluster+3)
  2581.         ld (fatfs_org+FFS_DRV.curr_dir2),hl
  2582.                 call BDOS_setpgstructs 
  2583.                 pop bc
  2584.                 ret             ;уходим в фатфс
  2585.  
  2586.                
  2587. BDOS_mount
  2588. ;e=logical volume(char A-Z)
  2589. ;out: a!=0 => not mounted
  2590.                 ld a,e
  2591.                 and 0xdf
  2592.                 sub 'A'
  2593.                 ret c
  2594.                 cp 26
  2595.                 ret nc
  2596.                 sub vol_trdos
  2597.         jr c,.noFATFS
  2598.                 ld e,a
  2599.         BDOSSETPGFATFS
  2600.                 call BDOS_setpgstructs
  2601.         ld hl,fatfsarray ;вычисляем указатель на структуру fatfs
  2602.         ld a,e
  2603.                 or a
  2604.         jr z,.fix_ffs
  2605.         ld bc,FATFS_sz
  2606. .calcfatfs
  2607.         add hl,bc
  2608.         dec a
  2609.         jr nz,.calcfatfs
  2610. .fix_ffs
  2611.         ld (fatfs_org+FFS_DRV.curr_fatfs),hl ;l
  2612.                 inc hl
  2613.                 ld a,e
  2614.                 cp 8
  2615.                 jr c,.isHDD
  2616.                 sub 6
  2617.                 ld (hl),a       ;номер драйва
  2618.                 xor a
  2619.                 jr .f_mnt
  2620. .isHDD         
  2621.                 srl e
  2622.                 srl e
  2623.                 ld (hl),e       ;номер драйва
  2624.                 and %00000011
  2625. .f_mnt
  2626.                 inc hl
  2627.                 ld (hl),a       ;номер раздела
  2628.                 F_MNT
  2629.                 ret
  2630. .noFATFS
  2631.         xor a ;xor a ;NC:success, CY:fail
  2632.         ret;jr rest_exit
  2633. BDOS_setsysdrv
  2634. SYSDRV_VAL=$+1
  2635.         ld e,SYSDRV
  2636.          call BDOS_setdrv
  2637.          ld de,syspath
  2638.          jp setpath
  2639.  
  2640. BDOS_preparereadwritesectors_FATFS
  2641.         sub vol_trdos ;получаем физический номер устройства (HDD master, HDD slave, SD...)
  2642.         push af
  2643.         BDOSSETPGFATFS
  2644.         call BDOS_setdepage
  2645.         pop af
  2646.         push ix
  2647.         pop bc
  2648.         ex de,hl ;bcde=sector number, hl=buffer
  2649. ;hl=buffer
  2650. ;a=drive
  2651. ;bcde=sector
  2652. ;a'=count
  2653.         ret
  2654.  
  2655. BDOS_preparereadwritesectors_TRDOSFS
  2656.          push af
  2657.         BDOSSETPGTRDOSFS
  2658.          pop af
  2659.         ld (trdoscurdrive),a
  2660.         ld a,l
  2661.         add hl,hl
  2662.         add hl,hl
  2663.         add hl,hl
  2664.         add hl,hl
  2665.         ex de,hl ;hl=buffer, d=track
  2666.         and 0x0f
  2667.         ld e,a ;e=sector
  2668.         ex af,af' ;'
  2669.         ld b,a ;count
  2670. ;hl=buffer
  2671. ;d=track
  2672. ;e=sector
  2673. ;b=count
  2674.         ret
  2675.  
  2676. BDOS_readsectors
  2677. ;b=drive(0..), de=buffer, ixhl=sector number, a'=count
  2678. ;передавать логический volume (букву) и пересчитать в номер драйвера (в смещение раздела, наверно, бессмысленно)?
  2679.         push bc
  2680.         call BDOS_preparedepage
  2681.         call BDOS_setdepage
  2682.         pop af
  2683.         cp vol_trdos
  2684.         jr c,BDOS_readsectors_TRDOS
  2685.         call BDOS_preparereadwritesectors_FATFS
  2686.         jp devices_read_go_regs
  2687. BDOS_readsectors_TRDOS
  2688.         call BDOS_preparereadwritesectors_TRDOSFS
  2689.         jp rdsectors. ;out: a=error?
  2690.  
  2691. BDOS_writesectors
  2692. ;b=drive(0..), de=buffer, ixhl=sector number, a'=count
  2693. ;передавать логический volume (букву) и пересчитать в номер драйвера (в смещение раздела, наверно, бессмысленно)?
  2694.         push bc
  2695.         call BDOS_preparedepage
  2696.         call BDOS_setdepage
  2697.         pop af
  2698.         cp vol_trdos
  2699.         jr c,BDOS_writesectors_TRDOS
  2700.         call BDOS_preparereadwritesectors_FATFS
  2701.         jp devices_write_go_regs
  2702. BDOS_writesectors_TRDOS
  2703.         call BDOS_preparereadwritesectors_TRDOSFS
  2704.         jp wrsectors. ;out: a=error?
  2705.  
  2706. BDOS_setdrv
  2707. ;e=volume
  2708. ;out: a!=0 => not mounted (TODO), [l=number of volumes]
  2709. ;мы не должны монтировать, просто должны указать volume, текущий для данной задачи, и сбросить path, текущий для данной задачи
  2710.         ld a,e
  2711.         ;call BDOS_setvol_rootdir
  2712.         ;call BDOS_opencurdir ;эта операция нужна для определения смонтированности (F_MNT всегда возвращает 0)
  2713.         ;or a
  2714.         ;jr nc,BDOS_setdrvnfail
  2715.         ; ld (iy+app.vol),d
  2716. ;BDOS_setdrvnfail
  2717.          
  2718.         ;ld l,NVOLUMES ;доступно 8 драйвов???
  2719.         ;xor a ;success
  2720.         ;ret;jr rest_exit
  2721.        
  2722. ;BDOS_setvol_rootdir
  2723. ;установлена страница PGFATFS
  2724.           ld d,(iy+app.vol)
  2725.          ld (iy+app.vol),a
  2726. ;BDOS_setrootdir
  2727. ;не установлена страница PGFATFS
  2728. ;CY=error (при NC a=0) - TODO убрать?
  2729.          xor a
  2730.          ld h,a
  2731.          ld l,a
  2732.          call writedircluster_hl
  2733.          ;ld (iy+app.dircluster),a
  2734.          ;ld (iy+app.dircluster+1),a
  2735.          ld (iy+app.dircluster+2),a
  2736.          ld (iy+app.dircluster+3),a
  2737.         CHECKVOLUMETRDOS
  2738.         push de
  2739.         ;sbc a,a; ld a,0
  2740.         jr c,BDOS_setrootdir_trdos ;ret c ;NC=no error, A=0
  2741.                 ld bc,0 ; TCHAR *path   /* Pointer to the directory path */
  2742.         call BDOS_opencurdir ;эта операция нужна для определения смонтированности (F_MNT всегда возвращает 0)
  2743. BDOS_setrootdir_q
  2744.         pop de
  2745.         or a
  2746.         ret z ;NC=no error, A=0
  2747.          ld (iy+app.vol),d
  2748.          scf
  2749.         ret ;CY=error
  2750. BDOS_setrootdir_trdos
  2751.         push af
  2752.         BDOSSETPGTRDOSFS
  2753.         pop af
  2754.         call iodos_setdrive
  2755.         ;ld a,(eRR2) ;0=OK, 0xff=Abort
  2756.         jr BDOS_setrootdir_q
  2757.        
  2758. BDOS_delete
  2759. ;DE = Drive/path/file ASCIIZ string
  2760.         call BDOS_preparedepage
  2761.         call BDOS_setdepage ;TODO убрать в драйвер
  2762. ;DE = Pointer to ASCIIZ string
  2763.         call countfiledrive ;a=volume, de=path without drive, c=1: drive in path, CY=TR-DOS
  2764.         ;call eatdrive ;TODO keep and restore curdrv,curdir!!!
  2765.         jr c,BDOS_delete_nofatfs
  2766.         ;call keepvoldir
  2767.         ; dec c ;was c=1: drive in path
  2768.         ; push de
  2769.         ; call z,BDOS_setvol_rootdir ;drive specified in path
  2770.         ; pop de
  2771.         F_UNLINK
  2772.         ret        
  2773. BDOS_delete_nofatfs
  2774.         BDOSSETPGTRDOSFS
  2775.         jp trdos_delete
  2776.        
  2777. BDOS_rename
  2778. ;DE = Drive/path/file ASCIIZ string, HL = New filename ASCIIZ string (can contain drive/path! NOT MSXDOS)
  2779.         ex de,hl
  2780.         call BDOS_preparedepage ;TODO разные страницы hl,de (т.е. надо копировать отсюда в буфер)
  2781.         call BDOS_setdepage ;TODO убрать в драйвер
  2782.         ex de,hl
  2783.         call BDOS_preparedepage
  2784.         call BDOS_setdepage ;TODO убрать в драйвер
  2785.         CHECKVOLUMETRDOS
  2786.         jr c,BDOS_rename_nofatfs
  2787.         ld b,h
  2788.         ld c,l
  2789. ;DE = Drive/path/file ASCIIZ string, BC = New filename ASCIIZ string
  2790.         F_RENAME
  2791.         ret
  2792. BDOS_rename_nofatfs
  2793.         BDOSSETPGTRDOSFS
  2794.         jp trdos_rename
  2795.  
  2796. countfiledrive
  2797. ;DE = Drive/path/file ASCIIZ string
  2798. ;out: a=volume, de=path without drive, c=1: drive in path, CY=TR-DOS
  2799.         inc de
  2800.         ld a,(de)
  2801.         cp ':'
  2802.         dec de
  2803.          ld c,0
  2804.         ;push af ;z=drive in path
  2805.         GETVOLUME
  2806.         jr nz,BDOS_openhandle_nodriveinpath ;drive not specified in path
  2807.          ld a,(de)
  2808.          and 0xdf
  2809.          sub 'A'
  2810.          inc de
  2811.          inc de
  2812.         ;cp a ;z
  2813.          inc c
  2814. BDOS_openhandle_nodriveinpath
  2815. ;a=volume, de=path without drive, c=1: drive in path
  2816.         cp vol_trdos
  2817.         ret
  2818.        
  2819. BDOS_mkdir
  2820.         call BDOS_preparedepage
  2821.         call BDOS_setdepage ;TODO убрать в драйвер
  2822. ;DE = Pointer to ASCIIZ string
  2823.         call countfiledrive ;call eatdrive
  2824.         jp c,BDOS_fail
  2825. ;DE = Pointer to ASCIIZ string
  2826.         ;call keepvoldir
  2827.         ; dec c ;was c=1: drive in path
  2828.         ; push de
  2829.         ; call z,BDOS_setvol_rootdir ;drive specified in path
  2830.         ; pop de
  2831.         F_MKDIR
  2832.         ret
  2833.                
  2834. BDOS_chdir
  2835.         call BDOS_preparedepage
  2836.         call BDOS_setdepage ;TODO убрать в драйвер
  2837. ;DE = Pointer to ASCIIZ string
  2838.  
  2839. setpath
  2840. ;установлена страница PGFATFS
  2841. ;DE = Pointer to ASCIIZ string
  2842.         call countfiledrive ;call eatdrive
  2843.         jr c,BDOS_chdir_trdos
  2844.         push af
  2845.         ; dec c ;was c=1: drive in path
  2846.         ; call z,BDOS_setvol_rootdir ;drive specified in path
  2847.         F_CHDIR
  2848.         pop hl
  2849.         or a
  2850.         ret nz
  2851.                 ld (iy+app.vol),h
  2852.          ld hl,(fatfs_org+FFS_DRV.curr_dir2)
  2853.          ld (iy+app.dircluster+2),l
  2854.          ld (iy+app.dircluster+3),h
  2855.                  ;xor a
  2856.          ld hl,(fatfs_org+FFS_DRV.curr_dir0)
  2857.          ;ld (iy+app.dircluster),l
  2858.          ;ld (iy+app.dircluster+1),h
  2859.          ;ret
  2860. writedircluster_hl
  2861.         ld (iy+app.dircluster),l
  2862.         ld (iy+app.dircluster+1),h
  2863.         ret
  2864.        
  2865. BDOS_chdir_trdos
  2866.                 ld (iy+app.vol),a
  2867.                 xor a
  2868.         ;ld a,(de) ;путь пустой?
  2869.         ;or a
  2870.         ;jp nz,BDOS_fail ;непустой
  2871.         ret
  2872.  
  2873.         if 1==0
  2874. strlen
  2875. ;hl=str
  2876. ;out: hl=length
  2877.         xor a
  2878.         ld b,a
  2879.         ld c,a ;bc=0 ;чтобы точно найти терминатор
  2880.         cpir ;найдём обязательно, если длина=0, то bc=-1 и т.д.
  2881.         ld hl,-1
  2882.         ;or a
  2883.         sbc hl,bc
  2884.         ret
  2885.         endif
  2886.  
  2887. ;GET WHOLE PATH STRING (5EH)
  2888. ;     Parameters:    C = 5EH (_WPATH)
  2889. ;                   DE = Pointer to 64 byte (MAXPATH_sz!) buffer
  2890. ;     Results:       A = Error
  2891. ;                   DE = Filled in with whole path string
  2892. ;                   HL = Pointer to start of last item
  2893. ;This function simply copies an ASCIIZ path string from an internal buffer into the user's buffer. The string represents the whole path and filename, from the root ;directory, of a file or sub-directory located by a previous "find first entry" or "find new entry" function. [MSXDOS: The returned string will not include a drive, or an; ;initial "\" character.] Register HL will point at the first character of the last item on the string, exactly as for the "parse path" function (function 5Bh).
  2894. ;in NedoOS: DRIVE:/PATH/ !!!
  2895. BDOS_getpath
  2896.         push de ;нельзя после BDOS_preparedepage
  2897.         call BDOS_preparedepage
  2898.         call BDOS_setdepage ;TODO убрать в драйвер
  2899.         push de ;DE = Pointer to 64 byte (MAXPATH_sz!) buffer (0x8000+/0xc000+!)
  2900.  
  2901.         push de ;Pointer to 64 byte (MAXPATH_sz!) buffer (0x8000+/0xc000+!)
  2902.        
  2903.         GETVOLUME
  2904.         add a,'A'
  2905.         ex de,hl
  2906.         ld (hl),a
  2907.         inc hl
  2908.         ld (hl),':'
  2909.         inc hl
  2910.         ld (hl),'/'
  2911.         inc hl
  2912.         ld (hl),0
  2913.         cp vol_trdos+'A'
  2914.         jr c,BDOS_getpath_FATq
  2915.         ex de,hl
  2916. BDOS_getpath_FAT
  2917.         ;DE=TCHAR *path,        /* Pointer to the directory path */ буфер
  2918.         ld bc,MAXPATH_sz;64 ;BC=UINT sz_path    /* Size of path */) размер буфера
  2919.         F_GETCWD_CURDRV
  2920. BDOS_getpath_FATq
  2921.         pop hl ;Pointer to 64 byte (MAXPATH_sz!) buffer (0x8000+/0xc000+!)
  2922.         call findlastslash. ;NC!!!
  2923.         ex de,hl ;HL = Pointer to start of last item (0x8000+/0xc000+!)
  2924.        
  2925.         pop de ;DE = Pointer to 64 byte (MAXPATH_sz!) buffer (0x8000+/0xc000+!)
  2926.         ;or a
  2927.         sbc hl,de ;hl=расстояние до последнего слэша
  2928.         pop de ;DE = Pointer to 64 byte (MAXPATH_sz!) buffer
  2929.         add hl,de ;HL = Pointer to start of last item
  2930.         ret
  2931.  
  2932. ;hl = poi to filename in string
  2933. findlastslash.
  2934. ;hl=path string
  2935. ;out: de = after last slash (or start of path) ;NC!!!
  2936. nfopenfnslash.
  2937.         ld d,h
  2938.         ld e,l ;de = after last slash
  2939. ;find last slash
  2940. nfopenfnslash0.
  2941.         ld a,[hl]
  2942.         inc hl
  2943.         or a
  2944.         ret z;jr z,nfopenfnslashq. ;NC!!!
  2945.         cp '/'
  2946.         jr nz,nfopenfnslash0.
  2947.         jr nfopenfnslash.
  2948.  
  2949. ;PARSE FILENAME (5CH) - MSX-DOS
  2950. ;     Parameters:    C = 5CH (_PFILE)
  2951. ;                   DE = ASCIIZ string for parsing
  2952. ;                   HL = Pointer to 11 byte buffer
  2953. ;     Results:       A = Error (always zero)
  2954. ;                   DE = Pointer to termination character
  2955. ;                   HL = Preserved, buffer filled in
  2956. ;                    B = Parse flags (TODO)
  2957. ;b0 - set if any characters parsed other than drive name
  2958. ;b1 - set if any directory path specified
  2959. ;b2 - set if drive name specified
  2960. ;b3 - set if main filename specified in last item
  2961. ;b4 - set if filename extension specified in last item
  2962. ;b5 - set if last item is ambiguous
  2963. ;b6 - set if last item is "." or ".."
  2964. ;b7 - set if last item is ".."
  2965. BDOS_parse_filename
  2966.         BDOSSETPGTRDOSFS
  2967. ;делает из имени с точкой имя без точки (для CP/M)
  2968.         push hl ;Pointer to 11 byte buffer
  2969.  
  2970.         push de ;ASCIIZ string for parsing
  2971.         call BDOS_preparedepage
  2972.         call BDOS_setdepage ;TODO убрать в драйвер
  2973.         push de ;ASCIIZ string for parsing (0x8000+/0xc000+)
  2974.         ld hl,BDOS_parse_filename_cpmnamebuf
  2975.         call dotname_to_cpmname ;de -> hl
  2976.         ex de,hl ;de=Pointer to termination character (0x8000+/0xc000+)
  2977.         pop bc ;ASCIIZ string for parsing (0x8000+/0xc000+)
  2978.         or a
  2979.         sbc hl,bc ;hl=расстояние до терминатора
  2980.         pop bc ;ASCIIZ string for parsing
  2981.         add hl,bc ;Pointer to termination character
  2982.  
  2983.         pop de ;Pointer to 11 byte buffer
  2984.         push hl ;Pointer to termination character
  2985.  
  2986.         push de ;Pointer to 11 byte buffer
  2987.         call BDOS_preparedepage
  2988.         call BDOS_setdepage ;TODO убрать в драйвер
  2989.         ld hl,BDOS_parse_filename_cpmnamebuf
  2990.         ld bc,11
  2991.         ldir
  2992.         pop hl ;HL = Pointer to 11 byte buffer
  2993.  
  2994.         pop de ;DE = Pointer to termination character
  2995.         xor a
  2996.         ret
  2997.  
  2998. get_name
  2999. ;делает из имени без точки имя с точкой (для FATFS и для печати)
  3000. ;de(FCB)->hl
  3001.         inc de
  3002.         ex hl,de
  3003.         ld de,mfil
  3004. get_name_hltode
  3005.         ld b,7
  3006.         ld a,' '
  3007. get_name1
  3008.         ldi
  3009.         cp (hl)
  3010.         jr z,get_name_skipspaces
  3011.         djnz get_name1
  3012.         ldi
  3013.         jr get_name_findext ;скопировали 8 символов, пробел не нашли
  3014. get_name_skipspaces
  3015.         inc hl
  3016.         djnz $-1;1b ;пропускаем оставшиеся пробелы
  3017. get_name_findext
  3018.         cp (hl)
  3019.         jr z,get_name1f ;на месте расширения пробел - не ставим точку
  3020.         ex hl,de
  3021.         ld (hl),'.'
  3022.         inc hl
  3023.         ex hl,de
  3024.         ldi
  3025.         cp (hl)
  3026.         jr z,get_name1f
  3027.         ldi
  3028.         cp (hl)
  3029.         jr z,get_name1f
  3030.         ldi
  3031. get_name1f
  3032.         xor a
  3033.         ld (de),a
  3034.         ret
  3035.  
  3036. findfreeffile
  3037. ;out: nz=fail, hl=FIL, b=fil number
  3038.         call BDOS_setpgstructs
  3039.         ld hl,ffilearray
  3040.         ld de,FIL_sz
  3041.         ld b,0
  3042. findfreeffile0
  3043.         inc hl
  3044.         ld a,(hl) ;FS(HSB)
  3045.         dec hl
  3046.         or a
  3047.         ret z ;OK
  3048.         add hl,de
  3049.         inc b
  3050.         ;ld a,b
  3051.         ;cp MAXFILES
  3052.         ;jr nz,findfreeffile0
  3053.         ;or a ;nz
  3054.          ld a,MAXFILES-1
  3055.          cp b
  3056.          jr nc,findfreeffile0
  3057.          ;or a ;nz
  3058.         ret
  3059.        
  3060. movedma_addr
  3061.         ld iy,(appaddr)
  3062.         ;ld hl,(dma_addr) ;оригинальный, не пересчитанный адрес
  3063.         call BDOS_getdta
  3064.         ex de,hl
  3065.         add hl,bc
  3066.         ex de,hl
  3067.         ;ld (dma_addr),hl
  3068.         ;ret
  3069. BDOS_setdta
  3070.         ld (iy+app.dta),e
  3071.         ld (iy+app.dta+1),d
  3072.         ;ret
  3073. BDOS_getdta
  3074.         ld e,(iy+app.dta)
  3075.         ld d,(iy+app.dta+1)
  3076.         ret
  3077.  
  3078. ;***********************ЗАГЛУШКИ**************************     
  3079.  
  3080. ;копирование строки из\в юзерспейса в\из либу фатфс
  3081. strcpy_lib2usp  ;DE - dst, BC - src
  3082. strcpy_usp2lib
  3083.         push bc
  3084.         call BDOS_setdepage
  3085.         pop bc
  3086. strcpy_lib2usp0
  3087.         ld a,(bc)
  3088.         ld (de),a
  3089.         inc de
  3090.         inc bc
  3091.         or a
  3092.         jr nz,strcpy_lib2usp0
  3093.         ;BDOSSETPGFATFS
  3094.         ;jp BDOS_setpgstructs
  3095. BDOS_setpgstructs
  3096.         ld a,pgfatfs2
  3097.         jr sys_setpgc000
  3098.  
  3099. setmainpg_c000
  3100.         ld a,(iy+app.mainpg)
  3101.         jr sys_setpgc000
  3102.  
  3103. sys_setpgsscr
  3104.         ld a,(iy+app.screen)
  3105.         bit 3,a
  3106.         ld a,pgscr0_0
  3107.         jr z,$+4
  3108.         ld a,pgscr1_0
  3109.         ;ld bc,memport8000
  3110.         ;out (c),a
  3111.         call sys_setpg8000
  3112.         xor pgscr0_1^pgscr0_0 ;ld a,pgscr0_1
  3113.         ;ld b,memportc000_hi;0xff
  3114.         ;out (c),a
  3115.         jr sys_setpgc000
  3116.  
  3117. setpgs_killable
  3118.         ld a,pgkillable
  3119.         ld bc,memport4000
  3120.         ld (sys_curpg4000),a
  3121.         out (c),a
  3122.         ;ld b,memport8000_hi;0xbf
  3123.         ;out (c),a
  3124.         ;ld b,memportc000_hi;0xff
  3125.         ;out (c),a
  3126.         ;ret
  3127.         call sys_setpg8000
  3128. sys_setpgc000
  3129.         ld (sys_curpgc000),a
  3130.         ld bc,memportc000
  3131.         out (c),a
  3132.         ret
  3133.  
  3134. ;копирование в\из юзерспейса в\из структуру
  3135. memcpy_buf2usp  ;DE - dst, BC - src, на стеке count
  3136.         res 7,b ;src=buf
  3137.         jr memcpy_buf_go
  3138. memcpy_usp2buf
  3139.         res 7,d ;dst=buf
  3140. memcpy_buf_go
  3141.         push bc
  3142.         ld a,pgfatfs2;=pgstructs
  3143.         call sys_setpg4000
  3144.         pop bc
  3145.         jr memcpy_loop
  3146. ;копирование в\из юзерспейса в\из либу фатфс
  3147. memcpy_lib2usp  ;DE - dst, BC - src, на стеке count
  3148. memcpy_usp2lib
  3149. memcpy_loop
  3150.         push bc
  3151.         call BDOS_setdepage
  3152.         pop hl;bc
  3153.         ;ld h,b
  3154.         ;ld l,c
  3155.         pop af
  3156.         pop bc
  3157.         push bc
  3158.         push af
  3159.         ldir
  3160.         BDOSSETPGFATFS ;4000
  3161.         jp BDOS_setpgstructs
  3162.  
  3163. ;по числу драйвов FatFS (для TR-DOS не надо)
  3164. fatfsarray=0xc000
  3165.         ;display "fatfsarray=",fatfsarray
  3166.         ;ds 4*FATFS_sz
  3167.  
  3168. ffilearray=fatfsarray+(13*FATFS_sz)
  3169.         display "ffilearray_end=",ffilearray+(MAXFILES*FIL_sz)
  3170.         ;ds MAXFILES*FIL_sz
  3171.         ;dw 0x100 ;признак конца ffilearray
  3172.        
  3173. mfil    db "12345678.123",0 ;нужно только на время операции, которая принимает имя файла (может быть с путём?)
  3174.  
  3175. mfilinfo ds FILINFO_sz ;FILINFO ;нужно только на время findnext
  3176.  
  3177. fcb2    ds FCB_sz ;нужно только на время findnext
  3178.  
  3179. fres    dw 0 ;структура для возврата результата FatFS (число прочитанных/записанных байт)
  3180.         dw 0 ;для возврата даты
  3181.  
  3182. syspath
  3183.         db "bin",0
  3184.        
  3185. ;для TASiS: не используются страницы ОЗУ 0x00, 0x1B, 0x1C, 0x1D, 0x1E, 0x1F
  3186. ;для избежания гибернации: не используются страницы ОЗУ 128K
  3187. tsys_pages
  3188.         ds 8,0xff ;системные страницы 128K
  3189.         if TOPDOWNMEM
  3190.         db 0,0,0,0
  3191.         else
  3192.         db 0xff,0xff,0xff,0xff ;системные страницы
  3193.         endif
  3194.         db 0,0,0,0 ;0x08..0x0f
  3195.         db 0,0,0,0,0,0,0,0 ;0x10..0x17
  3196.         db 0,0,0,0xff,0xff,0xff,0xff,0xff ;0x18..0x1f for resident
  3197.         ds sys_npages-32-4 ;0=empty, or else process number
  3198.         if TOPDOWNMEM
  3199.         db 0xff,0xff,0xff,0xff ;системные страницы
  3200.         else
  3201.         db 0,0,0,0
  3202.         endif
  3203.  
  3204. pipebufs
  3205.         ds PIPEDESC_SZ*MAXPIPES
  3206.  
  3207.         display "$ before align=",$
  3208. ;TODO хранить прямо в текстовом экране? а если затрут, то восстанавливать? по какому событию?
  3209.         align 256
  3210. trecode
  3211.         incbin "../_sdk/codepage/866toatm"
  3212.