Interface I y puerto 0xef

Emuladores y aplicaciones que ayudarán a la perpetuación del Spectrum y su software en el futuro

Moderador: Sir Cilve Sinclair

zx81
Freddy Hardest
Mensajes: 619
Registrado: Vie Dic 28, 2007 2:14 pm
Ubicación: Valencia
Contactar:

Re: Interface I y puerto 0xef

Mensaje por zx81 » Vie Dic 09, 2011 5:14 pm

Después de intentar implementar una emulación precisa del MDRV con la información que me pasó Tomas Franke he llegado a la conclusión de que no es enteramente correcta ni suficiente. Tras unas cuantas horas (+10) de pegarme con la emulación y de leer el desensamblado de la ROM he conseguido una emulación decente.

La cuestión ahora es que me gustaría dejar en alguna parte constancia de lo que sé ahora para que dentro de unas semanas o meses, cuando quiera volver a recordar algo sepa donde buscarlo.... :lol:

De poner un ladrillo, donde mejor, ¿en el foro de emulación o en el de HW?. Hay ciertas cosas que me gustaría comentar con mcleod_ideafix por aquello de que llegá a nivel electrónico donde yo ni soñaría hacerlo. He pensado en varias posibilidades para lo que hace el trasto, pero no sé si tienen sentido a nivel electrónico de la ULA o no. Ni siquiera sé qué es exactamente un PLL.

También me surge la necesidad de un formato nuevo donde almacenar los datos de los microdrives. Visto que no hay forma de saber como está organizado el MDV del mundo QL, no tengo problemas en crear uno, pero si puedo cambiar opiniones con otros desarrolladores es muy probable que salga algo mejor de lo que soy capaz de sacar yo solo.

O a lo mejor el tema no interesa a nadie y mejor me evito pegar aquí un ladrillo de la repera... :oops:
Debido al fallo de un mecanismo, el lanzagranadas M203 se te podía disparar cuando menos lo esperaras, lo que te habría hecho bastante impopular entre lo que quedara de tu unidad.
Revista del ejército EE.UU. PS, agosto 1993.

Emulador JSpeccy
ZXBaremulator

speccy
Sabreman
Mensajes: 353
Registrado: Jue Sep 06, 2007 4:20 pm

Re: Interface I y puerto 0xef

Mensaje por speccy » Vie Dic 09, 2011 7:01 pm

Tu ponlo aqui, que yo lo miraré aunque no lo entienda ;)

zx81
Freddy Hardest
Mensajes: 619
Registrado: Vie Dic 28, 2007 2:14 pm
Ubicación: Valencia
Contactar:

Re: Interface I y puerto 0xef

Mensaje por zx81 » Mar Dic 13, 2011 11:22 am

Pensando en cómo funciona el IF1 y viendo que graba los bytes intercalados, algo así:

00-00-00-00
-00-00-00-00

me inclino a pensar que la ULA no puede tener un convertidor serie-paralelo, sino dos, porque cuando ha leído los primeros bits de la pista A (por llamarla de alguna forma) empiezan a llegar los bits de la pista B y de ahí en adelante va estando disponible alternativamente uno de los bytes, pero en todo momento se reciben datos de las dos pistas.

Como, además, los bits llegan de manera ininterrumpida (mentira, el espacio entre bytes tiene que ser forzosamente variable, pero no sé cómo se las arregla la ULA para bregar con esto durante la lectura) debe haber un registro de salida por cada desplazador que se carga cuando éste ha completado los 8 bits de un byte. En cada lectura se leería, alternativamente también, uno de los registros de salida. Por programación solo se ve uno, pero no veo cómo podría funcionar el invento si no tiene dos desplazadores y dos registros de salida, sinceramente.

El tema es que no puede ser verdad que el bit SYNC se ponga a "1" (cero en lógica invertida) cuando el dato leído es FF. No creo que sea casualidad que antes de leer los datos, todo sean "parejas". El principio de un sector se busca:

- Leyendo 8 veces consecutivas que el bit GAP == 0 (zona de datos)
- Leyendo 6 veces consecutivas que el bit GAP == 1 (zona sin datos)
- Esperando a que SYNC == 0
- Instrucción INIR de la Z80

En ese plan, no creo que las 6 parejas del preámbulo, 5 parejas a 0x00 y una última pareja a 0xFF sean una casualidad. No hay más que leer con atención lo que acabo de describir y aplicarlo al preámbulo para darse cuenta de que lo que dijo Tomas no funciona.

¿Te parece que tiene sentido lo que planteo mcleod_ideafix? (tb me sirven las opiniones de otras personas) :)

P.D.: El mito de que grababa los bits alternativamente en cada pista sale del "Spectrum Microdrive Book" donde el Dr. Ian Logan lo describe así. Pero en el ZX IF1, IF2 & Microdrive Service Manual dice:

2.2 The microdrive cartridge uses a continuous loop of 2 mm wide video
tape. Data is written on two tracks using a standard stereo head
arrangement and is written in bytes, one byte to each track. Data is
read from the tape in the same way. Software sees the tape as one
continuous track since hardware takes care of switching between
tracks.


y un poco más adelante:

2.9 Data is recorded on 2 tracks using a standard stereo cassette head
arrangement and is written in bytes, one byte to one track and the
next byte to the other track. It is recovered in the same way. The
tape itself is one continuous loop. Since hardware takes care of
switching between tracks the software sees the tape as one doublelength
single track.


Curiosamente, los gráficos del "Spectrum Microdrive Book" son correctos y todo cuadraría si donde dice bits dijera bytes. Tiene bemoles la cosa...
Debido al fallo de un mecanismo, el lanzagranadas M203 se te podía disparar cuando menos lo esperaras, lo que te habría hecho bastante impopular entre lo que quedara de tu unidad.
Revista del ejército EE.UU. PS, agosto 1993.

Emulador JSpeccy
ZXBaremulator

Avatar de Usuario
mcleod_ideafix
Johnny Jones
Mensajes: 3985
Registrado: Vie Sep 21, 2007 1:26 am
Ubicación: Jerez de la Frontera
Contactar:

Re: Interface I y puerto 0xef

Mensaje por mcleod_ideafix » Mar Dic 13, 2011 12:13 pm

zx81 escribió:Como, además, los bits llegan de manera ininterrumpida (mentira, el espacio entre bytes tiene que ser forzosamente variable...


Yo lo que vi en el osciloscopio (y que tú mismo puedes repasar en el hilo del subforo de QL en cuestión) es que:
- El tiempo de bit es el mismo, da igual que sea éste 1 ó 0, con lo que el tiempo de byte es el mismo siempre.
- Al terminar un byte se transmite de forma inmediata el siguiente, no hay "hueco". ¿Por qué dices que el espacio entr ebytes debe ser forzosamente variable?

zx81 escribió:pero no sé cómo se las arregla la ULA para bregar con esto durante la lectura) debe haber un registro de salida por cada desplazador que se carga cuando éste ha completado los 8 bits de un byte. En cada lectura se leería, alternativamente también, uno de los registros de salida. Por programación solo se ve uno, pero no veo cómo podría funcionar el invento si no tiene dos desplazadores y dos registros de salida, sinceramente.


Los dos registros de salida van a las entradas de un multiplexor, que va eligiendo alternativamente uno y otro. La basculación del multiplexor se realiza en cada operación de lectura. Es decir, el multiplexor, pongamos, tiene seleccionado al registro de salida A, perteneciente a lo que se ha leído en la pista A, y eso es lo que ve el Z80 cuando lee el puerto de microdrive. La misma operación de lectura hace que un biestable cuya salida va al bit de selección del multiplexor cambie y pase ahora al registor de salida B. Así, en la siguiente operación de lectura del microdrive, lo que leerá el Z80 será el registro de salida B.

Otro flip-flop, un RS por ejemplo, se encarga de generar la señal WAIT: cuando se detecta una lectura por parte del Z80 del registro del microdrive, se envía una señal al pin R del flip-flop. Su salida Q, conectada a WAIT, se pone a 0. Cuando el registro de desplazamiento de la pista actual ha terminado de llenarse, se envía una señal al pin S, que pone WAIT a 1, desbloqueando la lectura.

zx81 escribió:En ese plan, no creo que las 6 parejas del preámbulo, 5 parejas a 0x00 y una última pareja a 0xFF sean una casualidad. No hay más que leer con atención lo que acabo de describir y aplicarlo al preámbulo para darse cuenta de que lo que dijo Tomas no funciona.


No sé qué es a lo que te refieres que dijo Tomas, pero recuerdo algo de que el preámbulo era así para que la señal resultante fuera fácil de identificar (una señal cuadrada de frecuencia fija, seguida de otra señal cuadrada de frecuencia fija, pero diferente a la anterior). A mi me recuerdan al tono piloto y al pulso de sincronismo de la carga de cassette. Se necesita algo de esto para saber dónde comienzan los bytes "de verdad" ya que una vez que comienzan, están todos juntitos (vamos, como en la cinta cassette).
Web: ZX Projects | Twitter: @zxprojects

Avatar de Usuario
mcleod_ideafix
Johnny Jones
Mensajes: 3985
Registrado: Vie Sep 21, 2007 1:26 am
Ubicación: Jerez de la Frontera
Contactar:

Re: Interface I y puerto 0xef

Mensaje por mcleod_ideafix » Mar Dic 13, 2011 12:15 pm

mcleod_ideafix escribió:
zx81 escribió:Como, además, los bits llegan de manera ininterrumpida (mentira, el espacio entre bytes tiene que ser forzosamente variable...


Yo lo que vi en el osciloscopio (y que tú mismo puedes repasar en el hilo del subforo de QL en cuestión) es que:
- El tiempo de bit es el mismo, da igual que sea éste 1 ó 0, con lo que el tiempo de byte es el mismo siempre.
- Al terminar un byte se transmite de forma inmediata el siguiente, no hay "hueco". ¿Por qué dices que el espacio entr ebytes debe ser forzosamente variable?


A ver... ¿quizás es que estás pensando en la lectura, en donde la velocidad de la cinta microdrive es variable y por tanto lo es también el flujo de información que pasa por los cabezales? Si es así, recuerda que la señal que el Microdrive genera a la ULA es Manchester diferencial, es decir, una señal con autorreloj: pueden extraerse los 0's y los 1's independientemente de la velocidad de dichos datos (dentro de un margen).
Web: ZX Projects | Twitter: @zxprojects

zx81
Freddy Hardest
Mensajes: 619
Registrado: Vie Dic 28, 2007 2:14 pm
Ubicación: Valencia
Contactar:

Re: Interface I y puerto 0xef

Mensaje por zx81 » Mar Dic 13, 2011 1:11 pm

mcleod_ideafix escribió:
zx81 escribió:Como, además, los bits llegan de manera ininterrumpida (mentira, el espacio entre bytes tiene que ser forzosamente variable...


Yo lo que vi en el osciloscopio (y que tú mismo puedes repasar en el hilo del subforo de QL en cuestión) es que:
- El tiempo de bit es el mismo, da igual que sea éste 1 ó 0, con lo que el tiempo de byte es el mismo siempre.
- Al terminar un byte se transmite de forma inmediata el siguiente, no hay "hueco". ¿Por qué dices que el espacio entre bytes debe ser forzosamente variable?


Si especulo, porque eso es lo que hago, con que es variable es porque hay otro factor olvidado que entra en juego. Aunque la ROM del IF1 no tiene ese problema, los bytes se leen/escriben desde un buffer en una zona entre el buffer de impresora y la zona de BASIC. Contended memory le llaman a eso. La instrucción INIR tiene que acceder a (HL) para sacar el byte y pueden haber hasta 7 ciclos de retraso por byte, el 4% del tiempo de lectura normal de un byte (168 ciclos), o el 21% del tiempo de lectura de un bit. Si en escritura un byte se retrasa en enviar 7 ciclos, en la lectura también llegará 7 ciclos más tarde. Salvo que vayamos por delante y rellenemos el registro interno mientras el desplazador va sacando el anterior.

mcleod_ideafix escribió:Los dos registros de salida van a las entradas de un multiplexor, que va eligiendo alternativamente uno y otro. La basculación del multiplexor se realiza en cada operación de lectura. Es decir, el multiplexor, pongamos, tiene seleccionado al registro de salida A, perteneciente a lo que se ha leído en la pista A, y eso es lo que ve el Z80 cuando lee el puerto de microdrive. La misma operación de lectura hace que un biestable cuya salida va al bit de selección del multiplexor cambie y pase ahora al registor de salida B. Así, en la siguiente operación de lectura del microdrive, lo que leerá el Z80 será el registro de salida B.

Otro flip-flop, un RS por ejemplo, se encarga de generar la señal WAIT: cuando se detecta una lectura por parte del Z80 del registro del microdrive, se envía una señal al pin R del flip-flop. Su salida Q, conectada a WAIT, se pone a 0. Cuando el registro de desplazamiento de la pista actual ha terminado de llenarse, se envía una señal al pin S, que pone WAIT a 1, desbloqueando la lectura.


Luego aquí me das la razón en que debe haber dos desplazadores y dos registros internos. En sí mismo, ello me hace feliz... :D


mcleod_ideafix escribió:
zx81 escribió:En ese plan, no creo que las 6 parejas del preámbulo, 5 parejas a 0x00 y una última pareja a 0xFF sean una casualidad. No hay más que leer con atención lo que acabo de describir y aplicarlo al preámbulo para darse cuenta de que lo que dijo Tomas no funciona.


No sé qué es a lo que te refieres que dijo Tomas, pero recuerdo algo de que el preámbulo era así para que la señal resultante fuera fácil de identificar (una señal cuadrada de frecuencia fija, seguida de otra señal cuadrada de frecuencia fija, pero diferente a la anterior). A mi me recuerdan al tono piloto y al pulso de sincronismo de la carga de cassette. Se necesita algo de esto para saber dónde comienzan los bytes "de verdad" ya que una vez que comienzan, están todos juntitos (vamos, como en la cinta cassette).


Supongamos que Tomas tiene razón y hay un comparador que comprueba si el dato que entra es 0xFF. Si lo es, pone SYNC a 0 (nivel lógico alto) y si es distinto lo pone a 1. Hagamos caso a la saga Star Wars y recordemos el use the source, Luke:

http://www.wearmouth.demon.co.uk/if1_2.htm#L15F2

esa es la rutina de lectura de un registro de cabecera o de un registro de datos, depende de por donde se entre. Pero eso es indiferente.

Código: Seleccionar todo

;; CHK-AGAIN
L15F6:  LD      B,$08           ; set gap counter to eight.

        DEC     HL              ;
        LD      A,H             ;
        OR      L               ;

        JR      Z,L15DE         ; back to SIGN-ERR

;; CHKLOOP
L15FD:  CALL    L163E           ; routine TEST-BRK

        IN      A,($EF)         ;
        AND     $04             ; isolate gap bit.
        JR      Z,L15F6         ; back to CHK-AGAIN

        DJNZ    L15FD


aquí busca una zona de datos (GAP==0). Supongamos que la encuentra:

Código: Seleccionar todo

;; CHK-AG-2
L1608:  LD      B,$06           ;
        DEC     HL              ;
        LD      A,H             ;
        OR      L               ;
        JR      Z,L15DE         ; back to SIGN-ERR


;; CHK-LP-2
L160F:  CALL    L163E           ; routine TEST-BRK
        IN      A,($EF)         ;
        AND     $04             ; isolate gap bit.
        JR      NZ,L1608        ; back to CHK-AG-2

        DJNZ    L160F           ; back to CHK-LP-2

        LD      A,$EE           ;
        OUT     ($EF),A         ;


aquí busca un hueco (GAP==1) porque sabe que inmediatamente detrás de un GAP viene un preámbulo. El último OUT es un misterio para mi y me da que innecesario (se asegura de que la unidad esté habilitada poniendo a cero el bit0). Bien, ya tenemos el GAP (==1):

Código: Seleccionar todo

;; DR-READY
L1620:  IN      A,($EF)         ;
        AND     $02             ; isolate sync bit.
        JR      Z,L162A         ; forward to READY-RE

        DJNZ    L1620           ; back to DR-READY

        JR      L15F6           ; back to CHK-AGAIN


aquí espera a que SYNC==0. Solo siete instrucciones más abajo está el INIR que hace la transferencia física. Fijémonos en que, a diferencia de los casos anteriores no hay contador. Con una sola vez que SYNC==0, saltamos a READY-RE. Analicemos el preámbulo con la hipótesis de Tomas:

00 (SYNC==1)
00 (SYNC==1)
00 (SYNC==1)
00 (SYNC==1)
00 (SYNC==1)
00 (SYNC==1)
00 (SYNC==1)
00 (SYNC==1)
00 (SYNC==1)
00 (SYNC==1)
FF (SYNC==0)
FF (INIR)

y nos comemos el segundo FF con patatas a lo pobre. La cagaste Burt Lancaster, empezaste a leer antes del fin del preámbulo.

Ahora llega el momento de la fiesta de las suposiciones. La señal SYNC es un AND de los comparadores de cada registro con FF. O bien las entradas del comparador son los dos registros de entrada y la señal SYNC la da cuando ambos registros son iguales y no cero, lo que se asemeja mucho a un AND de ambos registros y por eso es crucial que los primeros bytes sean cero y no otra cosa. O puede que SYNC se levante cuando los dos registros de entrada han conseguido un byte de datos y se baje con una NAND de los registros de entrada. Siguiendo con las posibilidades de funcionamiento podemos suponer que cabe la posibilidad de que la zona donde cayera el primer byte de preámbulo esté mal y el PLL no se enganche hasta el segundo byte. Hay que tener alguna manera de leer un número impar de bytes de preámbulo, saber que los dos registros están cargándose adecuadamente y a la vez no empezar a leer simplemente por la cuenta de bytes leídos. Para eso no sirve un 0xFF, necesitamos dos.

La cosa debe ser de un simple que te caes de culo, en línea con los precedentes de Sinclair y usando los menos transistores posibles. La señal SYNC debe indicar algún tipo de sincronía entre los registros internos, de eso estoy bastante convencido (hasta que se demuestre lo contrario). Lo que desmiente la afirmación de Tomas, lamentablemente.
Debido al fallo de un mecanismo, el lanzagranadas M203 se te podía disparar cuando menos lo esperaras, lo que te habría hecho bastante impopular entre lo que quedara de tu unidad.
Revista del ejército EE.UU. PS, agosto 1993.

Emulador JSpeccy
ZXBaremulator

zx81
Freddy Hardest
Mensajes: 619
Registrado: Vie Dic 28, 2007 2:14 pm
Ubicación: Valencia
Contactar:

Re: Interface I y puerto 0xef

Mensaje por zx81 » Jue Dic 15, 2011 11:40 am

He dejado en WoS un mensaje con la explicación de los "porqués" y la definición de un nuevo fichero de almacenamiento de cartuchos de microdrive.

Se agradecerán comentarios, aquí o allí ;)

http://www.worldofspectrum.org/forums/showthread.php?t=37039
Debido al fallo de un mecanismo, el lanzagranadas M203 se te podía disparar cuando menos lo esperaras, lo que te habría hecho bastante impopular entre lo que quedara de tu unidad.
Revista del ejército EE.UU. PS, agosto 1993.

Emulador JSpeccy
ZXBaremulator

Responder

¿Quién está conectado?

Usuarios navegando por este Foro: No hay usuarios registrados visitando el Foro y 10 invitados