Проблемы с чтением CF через int13h на некоторых старых BIOS

Описания, советы, ремонт, эксплуатация старых IBM PC-совместимых ПК
i8088
Advanced Member
Сообщения: 3057
Зарегистрирован: 30.01.2015,17:06
Откуда: г. Баку, Азербайджан

Конкурсы

Вклад в сообщество

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение i8088 » 30.07.2020,13:48

Gleb, большое спасибо, пригодится!

Можно еще дизассемблировать существующий POWER IDE и second.exe, посмотреть, как точно там
сделано. Ну это потом, на будущее.

i8088
Advanced Member
Сообщения: 3057
Зарегистрирован: 30.01.2015,17:06
Откуда: г. Баку, Азербайджан

Конкурсы

Вклад в сообщество

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение i8088 » 31.07.2020,16:04

Gleb, к вопросу о перехвате int 13h, вот что я нашел в исходниках DOS 6

; there is a bug in some versions of ibm's at rom bios.
; interrupts are not disabled during read operations.
;
; use: this program should be chained in line with the disk
; interupt 13h, it intercepts read calls to the hard disk
; and handles them appropriately. for other functions it
; passes controll to old13, which should contain the
; address of the at rom disk routine. the entry point for
; this program is ibm_disk_io.

Там же есть указание
cli ;disable interrupts (bug was forgetting this)

; M062 -- some of these old machines have intermittent failures
; when the read is done at full speed. Instead of using
; a string rep instruction, we'll use a loop. There is
; a slight performance hit, but it only affects these
; very old machines with an exact date code match, and
; it makes said machines more reliable
;
;M062 repz insw ;read in sector

rsct_loop: ; M062
insw ; M062 read in sector
loop rsct_loop ; M062

sti
Во многих старых BIOS REP не используют, но в том что я дорабатывал (D286)
уже REP.

И возвращаясь к тому, что Вы упоминали (извините за настырность, просто хочется разобраться).
Gleb писал(а):
29.07.2020,13:52
Как минимум для буферизации на старых системах, где установлены диски с низким числом секторов на дорожку, и для чтения большого количества секторов за один вызов int13h, нужно переключать не только головки, но и цилиндры. БИОС этого не делал.

А после подмены вектоа ДОСом становится возможным считывать большее количество секторов за раз (до 127 [7Fh]).
И если при написании собственного обработчика int13h исключить из цепочки этот обработчик DOS, а передавать прямо в оригинальный БИОС-овский int13h, то можно столкнуться с ситуацией, когда маленькие файлы читаются, а большие нет.
Столкнулся с этим на XT с классическим 17-ти секторным MFM диском.
В более современных системах это возможно иррелевантно, не проверял.
Вообще говоря, BIOS не должен заниматься переключением цилиндров, головок, он только подает ATA
команду, и сколько секторов должно быть записано/прочитано, это просто часть операции
подготовки task_file, регистр 1F2. Может быть Ваш MFM контроллер имел баг (или особенность такую,
типа как у FDC)? Я когда делал поддержку MFM для FreeBSD (с 16-битным контроллером WD) ничего
такого не заметил. Или может такая особенность у старых 8-битных контроллеров?

i8088
Advanced Member
Сообщения: 3057
Зарегистрирован: 30.01.2015,17:06
Откуда: г. Баку, Азербайджан

Конкурсы

Вклад в сообщество

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение i8088 » 31.07.2020,16:13

Я доделал резидент на int13h, для работы CF. В основном эта программа нужна для отладки, чтобы
попробовать реализовать основную идею. Но вдруг пригодится кому, если устроит старт с FDD, или
в системе есть и HDD и CF.

Программа встает резидентом, подменяя адрес оригинального int13h (70h:b4h). но я пробовал
вставать и сразу на int13h, при этом DOS-patch обходится, так тоже работало. Код обработчика
можно еще основательно оптимзировать, и переместить часть кода в верхнюю часть PSP, что
уменьшит занимаемую память. Исходник для MASM6 тоже прилагается.

проверял на AMI 89 года с CF багом и древнем AWARD 3.01
Вложения
cfrfix05.zip
(4.39 КБ) 9 скачиваний

Gleb
Member
Сообщения: 165
Зарегистрирован: 30.10.2016,20:46
Откуда: Прага

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение Gleb » 31.07.2020,17:01

i8088 писал(а):
31.07.2020,16:04
И возвращаясь к тому, что Вы упоминали (извините за настырность, просто хочется разобраться).

Вообще говоря, BIOS не должен заниматься переключением цилиндров, головок, он только подает ATA
команду, и сколько секторов должно быть записано/прочитано, это просто часть операции
подготовки task_file, регистр 1F2. Может быть Ваш MFM контроллер имел баг (или особенность такую,
типа как у FDC)? Я когда делал поддержку MFM для FreeBSD (с 16-битным контроллером WD) ничего
такого не заметил. Или может такая особенность у старых 8-битных контроллеров?

Вы не так поняли. Я как раз писал, что БИОС этого не делает, а вот ДОС, после подмены int13h "начинает делать". В кавычках потому что сам ДОС непосредственно ничего не переключает, просто он разбивает один вызов на несколько обращений к БИОС - см. ниже.

Я выделил это в своей цитате:
Gleb писал(а):
29.07.2020,13:52
Как минимум для буферизации на старых системах, где установлены диски с низким числом секторов на дорожку, и для чтения большого количества секторов за один вызов int13h, нужно переключать не только головки, но и цилиндры. БИОС этого не делал.

А после подмены вектора ДОСом становится возможным считывать большее количество секторов за раз (до 127 [7Fh]).
И если при написании собственного обработчика int13h исключить из цепочки этот обработчик DOS, а передавать прямо в оригинальный БИОС-овский int13h, то можно столкнуться с ситуацией, когда маленькие файлы читаются, а большие нет.
Столкнулся с этим на XT с классическим 17-ти секторным MFM диском.
В более современных системах это возможно иррелевантно, не проверял.

Я описываю то, с чем столкнулся лично.
Конкретный пример: если обратиться напрямую к оригинальному БИОС с просьбой прочитать 127 секторов подряд, то как минимум на XT (8 бит) с классическим MFM контроллером (порты 32х, не 1Fх) с подключенным к нему 17-ти секторным диском он вернет ошибку.
Но если вызвать int13h (который к тому моменту уже перехватил ДОС), то один такой вызов int13h с запросом на 127 секторов до оригинального БИОС дойдет как последовательность нескольких вызовов, каждый из которых не превысит 17 секторов. Потом ДОС у себя их "склеит" и вернет, как результат одного вызова int13h.

А ДОС при чтении длинных файлов просит сразу много секторов (если файл лежит подряд, ДОС знает это из FAT). Это видно любым интерсептором.

Это я имел в виду под буферизацией, это один из доводов, зачем ДОС забирает int13h. Но не единственный, поэтому я и писал "как минимум". Еще один Вы привели выше из ДОС6. Есть скорее всего и другие доводы.

i8088
Advanced Member
Сообщения: 3057
Зарегистрирован: 30.01.2015,17:06
Откуда: г. Баку, Азербайджан

Конкурсы

Вклад в сообщество

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение i8088 » 31.07.2020,17:14

Gleb, спасибо! Я еще раз уточню на AT (порты 1Fx), сколько можно прочитать
секторов за раз. Хотя это должно зависеть исключительно от контроллера HDD,
который для ATA дисков совмещен с механикой. Скорее всего эта проблема только
для XT 8-битных контроллеров.

Gleb
Member
Сообщения: 165
Зарегистрирован: 30.10.2016,20:46
Откуда: Прага

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение Gleb » 31.07.2020,17:27

Насчет портов 1Fx (IDE, ATA) - наверное Вы правы. Но точно не скажу, если и знал - то не помню, давно это было.

Дело в том, что ХТ-шными вещами я снова начал заниматься сейчас из интереса, поэтому и вспомнилось многое, а вещи поновее XT пока так и остались в прошлом.

i8088
Advanced Member
Сообщения: 3057
Зарегистрирован: 30.01.2015,17:06
Откуда: г. Баку, Азербайджан

Конкурсы

Вклад в сообщество

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение i8088 » 01.08.2020,08:41

Gleb, я проверил на 286 AMI BIOS 89года - прочиталось максимум 128 секторов с ST3660A и CF
(больше просто размер буфера ES:BX не позволяет). Впрочем это заслуга IDE HDD, а не BIOS конечно.

А вот что я нашел еще в исходнике (MSINT13.ASM), разработчики страхуются от прерывания длинных
запросов в случае ECC и DMA ошибок (последнее для 286 не актуально, тк AT диск всегда PIO)

Код: Выделить всё

; check_wrap is a routine that adjusts the starting sector, starting head
; and starting cylinder for an int 13 request that requests i/o of a lot
; of sectors. it only does this for fixed disks. it is used in the sections
; of code that handle ecc errors and dma errors. it is necessary, because
; ordinarily the rom would take care of wraps around heads and cylinders,
; but we break down a request when we get an ecc or dma error into several
; i/o of one or more sectors. in this case, we may already be beyond the
; number of sectors on a track on the medium, and the request would fail.
;
; input conditions:
;	all registers set up for an int 13 request.
;
; output:
;	dh - contains starting head number for request
;	cx - contains starting sector and cylinder numbers
;	(the above may or may not have been changed, and are 0-based)
;	all other registers preserved.

check_wrap proc	near
	assume	ds:Bios_Data,es:nothing

	push	ax
	push	bx
	push	es
	push	di

	call	find_bds		; get pointer to bds for drive in dl
	jc	no_wrap 		;  finished if DOS doesn't use it

	test	es:[di].bds_flags,fnon_removable
	jz	no_wrap 		; no wrapping for removable media

	mov	bx,es:[di].BDS_BPB.BPB_SECTORSPERTRACK
	mov	ax,cx
	and	ax,3fh			; extract sector number
	cmp	ax,bx			; are we going to wrap?
	jbe	no_wrap
	div	bl			; ah=new sector #, al=# of head wraps

; we need to be careful here. if the new sector # is 0, then we are on the
; last sector on that track.

	or	ah,ah
	jnz	not_on_bound

	mov	ah,bl			; set sector=BDS_BPB.BPB_SECTORSPERTRACK if on boundary
	dec	al			; also decrement # of head wraps

not_on_bound:
	and	cl,0c0h 		; zero out sector #
	or	cl,ah			; or in new sector #
	xor	ah,ah			; ax = # of head wraps
	inc	ax
	add	al,dh			; add in starting head #
	adc	ah,0			; catch any carry
	cmp	ax,es:[di].BDS_BPB.BPB_HEADS		; are we going to wrap around a head?
	jbe	no_wrap_head		; do not lose new head number!!

	push	dx			; preserve drive number and head number
	xor	dx,dx
	mov	bx,es:[di].BDS_BPB.BPB_HEADS
	div	bx			; dx=new head #, ax=# of cylinder wraps

; careful here! if new head # is 0, then we are on the last head.

	or	dx,dx
	jnz	no_head_bound
	mov	dx,bx			; on boundary. set to BDS_BPB.BPB_HEADS

; if we had some cylinder wraps, we need to reduce them by one!!

	or	ax,ax
	jz	no_head_bound
	dec	ax			; reduce number of cylinder wraps
no_head_bound:
	mov	bh,dl			; bh has new head number
	pop	dx			; restore drive number and head number
	dec	bh			; get it 0-based
	mov	dh,bh			; set up new head number in dh
	mov	bh,cl
	and	bh,3fh			; preserve sector number
	mov	bl,6
	xchg	cl,bl
	shr	bl,cl			; get ms cylinder bits to ls end
	add	ch,al			; add in cylinder wrap
	adc	bl,ah			; add in high byte
	shl	bl,cl			; move up to ms end
	xchg	bl,cl			; restore cylinder bits into cl
	or	cl,bh			; or in sector number

no_wrap:
	clc
	pop	di
	pop	es
	pop	bx
	pop	ax
	ret

no_wrap_head:
	mov	dh,al			; do not lose new head number
	dec	dh			; get it 0-based
	jmp	short no_wrap
check_wrap	endp
Перенос делается, если номер запрошенного сектора больше SECTORSPERTRACK. Те можно
одинаково работать с дисками, имеющими разный SECTORSPERTRACK. И с HEAD примерно похоже.

Но это правда не часть int13h, а подготовка для int 13 request, хотя там есть еще
патчи для PS2 машин, патч ecc bug Жаль нет исходников старого DOS, вот там
должно быть wrap в патче обработчика.

Gleb
Member
Сообщения: 165
Зарегистрирован: 30.10.2016,20:46
Откуда: Прага

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение Gleb » 01.08.2020,18:19

Любопытно, спасибо за информацию.

Насколько старого ДОС интересуют исходники ?
Я думаю, что первая и вторая версии не интересны, хотя они опубликованы официально.

Для DOS 3.30 в сети есть неофициальные исходники. Если не найдете - скажите, выложу.

i8088
Advanced Member
Сообщения: 3057
Зарегистрирован: 30.01.2015,17:06
Откуда: г. Баку, Азербайджан

Конкурсы

Вклад в сообщество

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение i8088 » 02.08.2020,07:26

Gleb писал(а):
01.08.2020,18:19
Насколько старого ДОС интересуют исходники ?
Я думаю, что первая и вторая версии не интересны, хотя они опубликованы официально.

Для DOS 3.30 в сети есть неофициальные исходники. Если не найдете - скажите, выложу.
Исходники любой старой версии до 5 включительно интересны. А где опубликованы
исходники 1 и 2 версии? И да, если можно, я бы хотел посмотреть исходники MS-DOS 3.3

А исходники 6 версии у Вас есть? Если нет, я выложу.

upd. 1.25 и 2 нашел на archive.org
3.3 скачать не получается

Gleb
Member
Сообщения: 165
Зарегистрирован: 30.10.2016,20:46
Откуда: Прага

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение Gleb » 02.08.2020,13:41

Официально они на github-е, но вы уже нашли. (https://www.3dnews.ru/976247)

3.30 я выложил у себя: https://www.gleb.cz/ES1841/Soft/MSDOS33 ... pdated.zip

Шестерка у меня есть такая : https://www.gleb.cz/ES1841/Soft/MS-DOS-600-With-SRC.zip
Если у вас другая - было бы любопытно взглянуть.

У меня разбросаны по архивам исходники разных ОС, когда-то интересовался. Кроме MS там был и PTS (физтехсофт) DOS - на мой взгляд один из достойных клонов. И какие-то винды (по моему nt4.0 и 2к).
Но архивы в порядок так и не привел, в одно место все не сложил.
Если это реально интересно - могу как-нибудь попробовать найти все что есть.

i8088
Advanced Member
Сообщения: 3057
Зарегистрирован: 30.01.2015,17:06
Откуда: г. Баку, Азербайджан

Конкурсы

Вклад в сообщество

Проблемы с чтением CF через int13h на некоторых старых BIOS

Сообщение i8088 » 03.08.2020,08:35

Gleb, спасибо большое, посмотрю!

А вот то что у меня есть (скорее всего то-же самое, но нужно внимательно посмотреть).


NT4 и 2K я тоже находил.

Да, и int12h в 3-х основных BIOS -AMI, AWARD и PHOENIX - просто чтение 40h:13h,
я думаю декремента этой ячейки должно быть достаточно

Ответить