getting closer to a final version
This commit is contained in:
parent
33783a4bb2
commit
406774a382
|
|
@ -14,6 +14,7 @@ RM := rm -rf
|
||||||
OBJS += \
|
OBJS += \
|
||||||
main.o \
|
main.o \
|
||||||
mmc.o \
|
mmc.o \
|
||||||
|
mmc_perf.o \
|
||||||
uart.o \
|
uart.o \
|
||||||
wdc_if_pio.o \
|
wdc_if_pio.o \
|
||||||
wdc_if_sdcard.o \
|
wdc_if_sdcard.o \
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* $Id: wdc_config.h,v 1.11 2012/06/09 00:22:28 olivleh1 Exp $
|
* $Id: wdc_config.h,v 1.12 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -81,4 +81,6 @@
|
||||||
#define MEASURE_SDCARD_TIME 1
|
#define MEASURE_SDCARD_TIME 1
|
||||||
#undef MEASURE_SDCARD_TIME
|
#undef MEASURE_SDCARD_TIME
|
||||||
|
|
||||||
|
#define DEBUG 0
|
||||||
|
|
||||||
#endif /* CONFIG_H_ */
|
#endif /* CONFIG_H_ */
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* $Id: wdc_drv_mmc.c,v 1.15 2012/06/09 00:22:28 olivleh1 Exp $
|
* $Id: wdc_drv_mmc.c,v 1.16 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <avr/io.h>
|
#include <avr/io.h>
|
||||||
|
|
@ -39,8 +39,8 @@
|
||||||
#define send_dummy_byte() SPDR = 0xFF; wait_till_send_done()
|
#define send_dummy_byte() SPDR = 0xFF; wait_till_send_done()
|
||||||
#define recv_byte() SPDR
|
#define recv_byte() SPDR
|
||||||
#define xmit_byte(x) SPDR = x
|
#define xmit_byte(x) SPDR = x
|
||||||
#define MMC_Disable() PORT_MMC|= (1<<PIN_MMC_CS);
|
#define mmc_disable() PORT_MMC|= (1<<PIN_MMC_CS);
|
||||||
#define MMC_Enable() PORT_MMC=~(1<<PIN_MMC_CS);
|
#define mmc_enable() PORT_MMC=~(1<<PIN_MMC_CS);
|
||||||
#define nop() __asm__ __volatile__ ("nop" ::)
|
#define nop() __asm__ __volatile__ ("nop" ::)
|
||||||
|
|
||||||
#define CMD0 (0x40 + 0)
|
#define CMD0 (0x40 + 0)
|
||||||
|
|
@ -195,13 +195,13 @@ uint8_t mmc_init ()
|
||||||
SPCR = ( 1 << SPE ) | ( 1 << MSTR ) | ( 1 << SPR0 ) | ( 1 << SPR1 ); /* Enable SPI, SPI in Master Mode */
|
SPCR = ( 1 << SPE ) | ( 1 << MSTR ) | ( 1 << SPR0 ) | ( 1 << SPR1 ); /* Enable SPI, SPI in Master Mode */
|
||||||
SPSR = ( 0 << SPI2X );
|
SPSR = ( 0 << SPI2X );
|
||||||
|
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
|
|
||||||
for ( a = 0; a < 0x0f; a++ ) {
|
for ( a = 0; a < 0x0f; a++ ) {
|
||||||
send_dummy_byte();
|
send_dummy_byte();
|
||||||
}
|
}
|
||||||
|
|
||||||
MMC_Enable();
|
mmc_enable();
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* send CMD0
|
* send CMD0
|
||||||
|
|
@ -209,7 +209,7 @@ uint8_t mmc_init ()
|
||||||
uint8_t cmd[] = {CMD0, 0x00, 0x00, 0x00, 0x00, 0x95};
|
uint8_t cmd[] = {CMD0, 0x00, 0x00, 0x00, 0x00, 0x95};
|
||||||
while ( mmc_cmd ( cmd ) != 1 ) {
|
while ( mmc_cmd ( cmd ) != 1 ) {
|
||||||
if ( t16++ > 1000 ) {
|
if ( t16++ > 1000 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 1 );
|
return ( 1 );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -254,7 +254,7 @@ uint8_t mmc_init ()
|
||||||
while ( mmc_cmd ( cmd ) != 0 ) {
|
while ( mmc_cmd ( cmd ) != 0 ) {
|
||||||
send_dummy_byte();
|
send_dummy_byte();
|
||||||
if ( t16++ > 1000 ) {
|
if ( t16++ > 1000 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 2 );
|
return ( 2 );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -269,7 +269,7 @@ uint8_t mmc_init ()
|
||||||
mmc_enable_crc ( 1 );
|
mmc_enable_crc ( 1 );
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 0 );
|
return ( 0 );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -310,7 +310,7 @@ uint8_t mmc_write_sector ( uint32_t addr, uint8_t *buffer )
|
||||||
uint8_t crcl, crch;
|
uint8_t crcl, crch;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
MMC_Enable();
|
mmc_enable();
|
||||||
wait_till_card_ready();
|
wait_till_card_ready();
|
||||||
|
|
||||||
/* convert blocks to bytes */
|
/* convert blocks to bytes */
|
||||||
|
|
@ -327,7 +327,7 @@ uint8_t mmc_write_sector ( uint32_t addr, uint8_t *buffer )
|
||||||
*/
|
*/
|
||||||
tmp = mmc_cmd ( cmd );
|
tmp = mmc_cmd ( cmd );
|
||||||
if ( tmp != 0 ) {
|
if ( tmp != 0 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( tmp );
|
return ( tmp );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -363,11 +363,11 @@ uint8_t mmc_write_sector ( uint32_t addr, uint8_t *buffer )
|
||||||
/* check for errors */
|
/* check for errors */
|
||||||
send_dummy_byte();
|
send_dummy_byte();
|
||||||
if ( ( recv_byte() & 0x1F ) != 0x05 ) {
|
if ( ( recv_byte() & 0x1F ) != 0x05 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 2 );
|
return ( 2 );
|
||||||
}
|
}
|
||||||
|
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
|
|
||||||
return ( 0 );
|
return ( 0 );
|
||||||
}
|
}
|
||||||
|
|
@ -380,12 +380,12 @@ uint8_t mmc_read_block ( uint8_t *cmd, uint8_t *buffer, uint16_t bytes )
|
||||||
uint16_t crc;
|
uint16_t crc;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
MMC_Enable();
|
mmc_enable();
|
||||||
wait_till_card_ready();
|
wait_till_card_ready();
|
||||||
|
|
||||||
/* send command */
|
/* send command */
|
||||||
if ( mmc_cmd ( cmd ) != 0 ) {
|
if ( mmc_cmd ( cmd ) != 0 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 1 );
|
return ( 1 );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -421,14 +421,14 @@ uint8_t mmc_read_block ( uint8_t *cmd, uint8_t *buffer, uint16_t bytes )
|
||||||
wait_till_send_done();
|
wait_till_send_done();
|
||||||
crc |= recv_byte();
|
crc |= recv_byte();
|
||||||
if ( crc != crc16 ( buffer, bytes ) ) {
|
if ( crc != crc16 ( buffer, bytes ) ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 3 );
|
return ( 3 );
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
send_dummy_byte();
|
send_dummy_byte();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
|
|
||||||
return ( 0 );
|
return ( 0 );
|
||||||
}
|
}
|
||||||
|
|
@ -465,7 +465,7 @@ uint8_t mmc_read_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
uint16_t crc;
|
uint16_t crc;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
MMC_Enable();
|
mmc_enable();
|
||||||
|
|
||||||
#ifdef MMC_MULTIBLOCK
|
#ifdef MMC_MULTIBLOCK
|
||||||
#ifdef MMC_PRESET_MULTIBLOCKCOUNT
|
#ifdef MMC_PRESET_MULTIBLOCKCOUNT
|
||||||
|
|
@ -507,7 +507,7 @@ uint8_t mmc_read_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
*/
|
*/
|
||||||
resp = mmc_cmd ( cmd );
|
resp = mmc_cmd ( cmd );
|
||||||
if ( resp > 1 ) {
|
if ( resp > 1 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 1 );
|
return ( 1 );
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
|
|
@ -528,7 +528,7 @@ uint8_t mmc_read_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
*/
|
*/
|
||||||
resp = mmc_cmd ( cmd );
|
resp = mmc_cmd ( cmd );
|
||||||
if ( resp > 1 ) {
|
if ( resp > 1 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 1 );
|
return ( 1 );
|
||||||
}
|
}
|
||||||
x.value32 += MMC_BLOCKLEN;
|
x.value32 += MMC_BLOCKLEN;
|
||||||
|
|
@ -561,7 +561,7 @@ uint8_t mmc_read_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
send_dummy_byte();
|
send_dummy_byte();
|
||||||
crc |= recv_byte();
|
crc |= recv_byte();
|
||||||
if ( crc != crc16 ( buffer, MMC_BLOCKLEN ) ) {
|
if ( crc != crc16 ( buffer, MMC_BLOCKLEN ) ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 3 );
|
return ( 3 );
|
||||||
}
|
}
|
||||||
buffer = buffer + MMC_BLOCKLEN;
|
buffer = buffer + MMC_BLOCKLEN;
|
||||||
|
|
@ -585,7 +585,7 @@ uint8_t mmc_read_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
|
|
||||||
/* TODO: Apacer Card I have sends 0x7f after some reads - No idea why - CRC was correct
|
/* TODO: Apacer Card I have sends 0x7f after some reads - No idea why - CRC was correct
|
||||||
if ( resp > 1 ) {
|
if ( resp > 1 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 2 );
|
return ( 2 );
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
|
|
@ -593,7 +593,7 @@ uint8_t mmc_read_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
send_dummy_byte();
|
send_dummy_byte();
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
MMC_Disable()
|
mmc_disable()
|
||||||
|
|
||||||
return ( 0 );
|
return ( 0 );
|
||||||
}
|
}
|
||||||
|
|
@ -610,7 +610,7 @@ uint8_t mmc_write_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
uint8_t crcl, crch;
|
uint8_t crcl, crch;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
MMC_Enable();
|
mmc_enable();
|
||||||
wait_till_card_ready();
|
wait_till_card_ready();
|
||||||
#ifdef MMC_MULTIBLOCK
|
#ifdef MMC_MULTIBLOCK
|
||||||
#ifdef MMC_PRESET_MULTIBLOCKCOUNT
|
#ifdef MMC_PRESET_MULTIBLOCKCOUNT
|
||||||
|
|
@ -648,7 +648,7 @@ uint8_t mmc_write_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
*/
|
*/
|
||||||
resp = mmc_cmd ( cmd );
|
resp = mmc_cmd ( cmd );
|
||||||
if ( resp > 1 ) {
|
if ( resp > 1 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 1 );
|
return ( 1 );
|
||||||
}
|
}
|
||||||
#else
|
#else
|
||||||
|
|
@ -668,7 +668,7 @@ uint8_t mmc_write_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
*/
|
*/
|
||||||
resp = mmc_cmd ( cmd );
|
resp = mmc_cmd ( cmd );
|
||||||
if ( resp != 0 ) {
|
if ( resp != 0 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( resp );
|
return ( resp );
|
||||||
}
|
}
|
||||||
x.value32 += MMC_BLOCKLEN;
|
x.value32 += MMC_BLOCKLEN;
|
||||||
|
|
@ -718,7 +718,7 @@ uint8_t mmc_write_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
|
|
||||||
send_dummy_byte();
|
send_dummy_byte();
|
||||||
if ( ( recv_byte() & 0x1F ) != 0x05 ) {
|
if ( ( recv_byte() & 0x1F ) != 0x05 ) {
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
return ( 2 );
|
return ( 2 );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -738,7 +738,7 @@ uint8_t mmc_write_multiblock ( uint32_t addr, uint8_t *buffer, uint8_t numblocks
|
||||||
/* Pad 8 */
|
/* Pad 8 */
|
||||||
send_dummy_byte();
|
send_dummy_byte();
|
||||||
#endif
|
#endif
|
||||||
MMC_Disable();
|
mmc_disable();
|
||||||
|
|
||||||
return ( 0 );
|
return ( 0 );
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* $Id: wdc_if_disk.c,v 1.10 2012/06/09 00:22:28 olivleh1 Exp $
|
* $Id: wdc_if_disk.c,v 1.11 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
|
@ -36,14 +36,7 @@
|
||||||
|
|
||||||
uint8_t wdc_init_sdcard()
|
uint8_t wdc_init_sdcard()
|
||||||
{
|
{
|
||||||
uint8_t errorcode;
|
return mmc_init();
|
||||||
|
|
||||||
errorcode=mmc_init();
|
|
||||||
if ( errorcode ) {
|
|
||||||
uart_putc_hex ( errorcode );
|
|
||||||
uart_putc ( '\n' );
|
|
||||||
}
|
|
||||||
return errorcode;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t wdc_sector2sdblock ( uint16_t req_cylinder, uint8_t req_head, uint8_t req_sector )
|
uint32_t wdc_sector2sdblock ( uint16_t req_cylinder, uint8_t req_head, uint8_t req_sector )
|
||||||
|
|
|
||||||
|
|
@ -1,8 +1,32 @@
|
||||||
/*
|
/*-
|
||||||
* mmc_perf.c
|
* Copyright (c) 2012 Oliver Lehmann
|
||||||
|
* All rights reserved.
|
||||||
*
|
*
|
||||||
* Created: 07.06.2012 21:42:41
|
* Redistribution and use in source and binary forms, with or without
|
||||||
* Author: olivleh1
|
* modification, are permitted provided that the following conditions
|
||||||
|
* are met:
|
||||||
|
* 1. Redistributions of source code must retain the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer
|
||||||
|
* in this position and unchanged.
|
||||||
|
* 2. Redistributions in binary form must reproduce the above copyright
|
||||||
|
* notice, this list of conditions and the following disclaimer in the
|
||||||
|
* documentation and/or other materials provided with the distribution.
|
||||||
|
*
|
||||||
|
* THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR
|
||||||
|
* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
|
||||||
|
* OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
|
||||||
|
* IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
|
||||||
|
* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
|
||||||
|
* NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
|
||||||
|
* DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
|
||||||
|
* THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
* (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
|
||||||
|
* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* $Id: wdc_if_disk_perf.c,v 1.4 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <avr/io.h>
|
#include <avr/io.h>
|
||||||
|
|
|
||||||
|
|
@ -26,13 +26,15 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* $Id: wdc_if_p8000.c,v 1.5 2012/06/07 18:01:02 olivleh1 Exp $
|
* $Id: wdc_if_p8000.c,v 1.6 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "config.h"
|
#include "config.h"
|
||||||
#include <avr/pgmspace.h>
|
#include <avr/pgmspace.h>
|
||||||
#include <util/delay.h>
|
#include <util/delay.h>
|
||||||
#include "wdc_if_pio.h"
|
#include "wdc_if_pio.h"
|
||||||
|
#include "wdc_par.h"
|
||||||
|
#include "uart.h"
|
||||||
|
|
||||||
#define nop() __asm__ __volatile__ ("nop" ::)
|
#define nop() __asm__ __volatile__ ("nop" ::)
|
||||||
|
|
||||||
|
|
@ -55,11 +57,12 @@ void wdc_wait_for_reset()
|
||||||
while ( !isset_info_reset() ) {
|
while ( !isset_info_reset() ) {
|
||||||
port_data_set ( DATA_CLEAR );
|
port_data_set ( DATA_CLEAR );
|
||||||
port_info_set ( INFO_CLEAR );
|
port_info_set ( INFO_CLEAR );
|
||||||
|
wdc_set_initialized ( 1 );
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void wdc_read_data_from_p8k ( uint8_t *buffer, uint16_t count, uint8_t wdc_status )
|
uint8_t wdc_read_data_from_p8k ( uint8_t *buffer, uint16_t count, uint8_t wdc_status )
|
||||||
{
|
{
|
||||||
uint16_t datacnt;
|
uint16_t datacnt;
|
||||||
|
|
||||||
|
|
@ -68,7 +71,9 @@ void wdc_read_data_from_p8k ( uint8_t *buffer, uint16_t count, uint8_t wdc_statu
|
||||||
configure_port_data_read();
|
configure_port_data_read();
|
||||||
datacnt = 0;
|
datacnt = 0;
|
||||||
port_info_set ( wdc_status );
|
port_info_set ( wdc_status );
|
||||||
while ( !isset_info_te() );
|
while ( !isset_info_te() )
|
||||||
|
if ( !isset_info_reset() )
|
||||||
|
return 0;
|
||||||
while ( !isset_info_wdardy() );
|
while ( !isset_info_wdardy() );
|
||||||
do {
|
do {
|
||||||
while ( isset_info_wdardy() );
|
while ( isset_info_wdardy() );
|
||||||
|
|
@ -80,6 +85,7 @@ void wdc_read_data_from_p8k ( uint8_t *buffer, uint16_t count, uint8_t wdc_statu
|
||||||
} while ( datacnt < count );
|
} while ( datacnt < count );
|
||||||
port_info_set ( INFO_CLEAR );
|
port_info_set ( INFO_CLEAR );
|
||||||
|
|
||||||
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
void wdc_write_data_to_p8k ( uint8_t *buffer, uint16_t count, uint8_t wdc_status )
|
void wdc_write_data_to_p8k ( uint8_t *buffer, uint16_t count, uint8_t wdc_status )
|
||||||
|
|
@ -104,7 +110,6 @@ void wdc_write_data_to_p8k ( uint8_t *buffer, uint16_t count, uint8_t wdc_status
|
||||||
while ( isset_info_wdardy() );
|
while ( isset_info_wdardy() );
|
||||||
port_info_set ( INFO_TR | INFO_ASTB | wdc_status );
|
port_info_set ( INFO_TR | INFO_ASTB | wdc_status );
|
||||||
nop();
|
nop();
|
||||||
nop();
|
|
||||||
port_info_set ( INFO_TR | wdc_status );
|
port_info_set ( INFO_TR | wdc_status );
|
||||||
configure_port_data_read();
|
configure_port_data_read();
|
||||||
while ( !isset_info_wdardy() );
|
while ( !isset_info_wdardy() );
|
||||||
|
|
@ -112,12 +117,12 @@ void wdc_write_data_to_p8k ( uint8_t *buffer, uint16_t count, uint8_t wdc_status
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void wdc_receive_cmd ( uint8_t *buffer, uint16_t count )
|
uint8_t wdc_receive_cmd ( uint8_t *buffer, uint16_t count )
|
||||||
{
|
{
|
||||||
wdc_read_data_from_p8k ( buffer
|
return wdc_read_data_from_p8k ( buffer
|
||||||
, count
|
, count
|
||||||
, INFO_STAT_GCMD
|
, INFO_STAT_GCMD
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
void wdc_receive_data ( uint8_t *buffer, uint16_t count )
|
void wdc_receive_data ( uint8_t *buffer, uint16_t count )
|
||||||
|
|
@ -137,10 +142,15 @@ void wdc_send_data ( uint8_t *buffer, uint16_t count )
|
||||||
}
|
}
|
||||||
|
|
||||||
void wdc_send_error()
|
void wdc_send_error()
|
||||||
|
{
|
||||||
|
wdc_send_errorcode ( 0x01 );
|
||||||
|
}
|
||||||
|
|
||||||
|
void wdc_send_errorcode ( uint8_t error )
|
||||||
{
|
{
|
||||||
uint8_t buffer[1];
|
uint8_t buffer[1];
|
||||||
|
|
||||||
buffer[0] = 0x01;
|
buffer[0] = error;
|
||||||
|
|
||||||
wdc_write_data_to_p8k ( buffer
|
wdc_write_data_to_p8k ( buffer
|
||||||
, 1
|
, 1
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* $Id: wdc_if_p8000.h,v 1.7 2012/06/09 00:22:28 olivleh1 Exp $
|
* $Id: wdc_if_p8000.h,v 1.8 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef WDC_IF_PIO_H_
|
#ifndef WDC_IF_PIO_H_
|
||||||
|
|
@ -69,9 +69,10 @@
|
||||||
|
|
||||||
extern void wdc_init_ports();
|
extern void wdc_init_ports();
|
||||||
extern void wdc_wait_for_reset();
|
extern void wdc_wait_for_reset();
|
||||||
extern void wdc_receive_cmd ( uint8_t *buffer, uint16_t count );
|
extern uint8_t wdc_receive_cmd ( uint8_t *buffer, uint16_t count );
|
||||||
extern void wdc_receive_data ( uint8_t *buffer, uint16_t count );
|
extern void wdc_receive_data ( uint8_t *buffer, uint16_t count );
|
||||||
extern void wdc_send_data ( uint8_t *buffer, uint16_t count );
|
extern void wdc_send_data ( uint8_t *buffer, uint16_t count );
|
||||||
extern void wdc_send_error();
|
extern void wdc_send_error();
|
||||||
|
extern void wdc_send_errorcode ( uint8_t error );
|
||||||
|
|
||||||
#endif /* WDC_IF_PIO_H_ */
|
#endif /* WDC_IF_PIO_H_ */
|
||||||
|
|
@ -29,20 +29,11 @@
|
||||||
/*
|
/*
|
||||||
* P8000 WDC Emulator
|
* P8000 WDC Emulator
|
||||||
*
|
*
|
||||||
* $Id: wdc_main.c,v 1.23 2012/06/09 00:22:28 olivleh1 Exp $
|
* $Id: wdc_main.c,v 1.24 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*
|
*
|
||||||
* TODO: - Different Errorcodes in the MMC layer (use defines)
|
* TODO: - right now, BTT entries are not taken into account
|
||||||
* - errorchecking in several places
|
|
||||||
* - Prio 2: check if BTT is really cleaned when sa.format gets called all the time with a real drive
|
|
||||||
* ----------> no the old BTT from the previous formatting is shown
|
|
||||||
* ----------> check if after formatting, no BTT is written to the disk, the old BTT is still there
|
|
||||||
* - Prio 2: respect BTT entries when calculating the block number to use.
|
|
||||||
* - Prio 3: work out how PAR+BTT where originally stored on the harddisks and store them the same way
|
|
||||||
* - Prio 3: put the whole par_table handling from wdc_ram.[ch] into wdc_par.[ch]
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#define DEBUG 1
|
|
||||||
|
|
||||||
#include <avr/io.h>
|
#include <avr/io.h>
|
||||||
#include <avr/interrupt.h>
|
#include <avr/interrupt.h>
|
||||||
|
|
||||||
|
|
@ -50,6 +41,7 @@
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <avr/pgmspace.h>
|
#include <avr/pgmspace.h>
|
||||||
#include <avr/sleep.h>
|
#include <avr/sleep.h>
|
||||||
|
#include "config.h"
|
||||||
#include "main.h"
|
#include "main.h"
|
||||||
#ifdef DEBUG
|
#ifdef DEBUG
|
||||||
#include "uart.h"
|
#include "uart.h"
|
||||||
|
|
@ -58,7 +50,7 @@
|
||||||
#include "wdc_par.h"
|
#include "wdc_par.h"
|
||||||
#include "wdc_if_pio.h"
|
#include "wdc_if_pio.h"
|
||||||
#include "wdc_if_sdcard.h"
|
#include "wdc_if_sdcard.h"
|
||||||
#include "config.h"
|
|
||||||
|
|
||||||
void atmega_setup ( void );
|
void atmega_setup ( void );
|
||||||
|
|
||||||
|
|
@ -91,7 +83,7 @@ main ( void )
|
||||||
#endif
|
#endif
|
||||||
atmega_setup();
|
atmega_setup();
|
||||||
|
|
||||||
uart_puts_p ( PSTR ( "P8000 WDC Emulator 0.01\n" ) );
|
uart_puts_p ( PSTR ( "P8000 WDC Emulator 0.90\n" ) );
|
||||||
|
|
||||||
#ifdef MEASURE_SDCARD_TIME
|
#ifdef MEASURE_SDCARD_TIME
|
||||||
measure_performance();
|
measure_performance();
|
||||||
|
|
@ -121,278 +113,299 @@ main ( void )
|
||||||
|
|
||||||
wdc_wait_for_reset();
|
wdc_wait_for_reset();
|
||||||
|
|
||||||
wdc_receive_cmd ( cmd_buffer
|
if ( wdc_receive_cmd ( cmd_buffer
|
||||||
, cmd_counter
|
, cmd_counter
|
||||||
);
|
) ) {
|
||||||
|
|
||||||
#if DEBUG >= 2
|
#if DEBUG >= 2
|
||||||
#if DEBUG >= 3
|
#if DEBUG >= 3
|
||||||
uart_puts_p ( PSTR ( " CMD:" ) );
|
uart_puts_p ( PSTR ( " CMD:" ) );
|
||||||
#endif
|
#endif
|
||||||
uart_putc_hex ( cmd_buffer[0] );
|
uart_putc_hex ( cmd_buffer[0] );
|
||||||
#if DEBUG >= 3
|
#if DEBUG >= 3
|
||||||
uart_putc_hex ( cmd_buffer[1] );
|
uart_putc_hex ( cmd_buffer[1] );
|
||||||
uart_putc_hex ( cmd_buffer[2] );
|
uart_putc_hex ( cmd_buffer[2] );
|
||||||
uart_putc_hex ( cmd_buffer[3] );
|
uart_putc_hex ( cmd_buffer[3] );
|
||||||
uart_putc_hex ( cmd_buffer[4] );
|
uart_putc_hex ( cmd_buffer[4] );
|
||||||
uart_putc_hex ( cmd_buffer[5] );
|
uart_putc_hex ( cmd_buffer[5] );
|
||||||
uart_putc_hex ( cmd_buffer[6] );
|
uart_putc_hex ( cmd_buffer[6] );
|
||||||
uart_putc_hex ( cmd_buffer[7] );
|
uart_putc_hex ( cmd_buffer[7] );
|
||||||
uart_putc_hex ( cmd_buffer[8] );
|
uart_putc_hex ( cmd_buffer[8] );
|
||||||
uart_putc ( '\n' );
|
uart_putc ( '\n' );
|
||||||
#endif
|
#endif
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* if the disk is not valid, only maintenance commands are allowed */
|
/* no drive attached */
|
||||||
if ( ! wdc_get_disk_valid()
|
if ( wdc_get_initialized() && wdc_get_num_of_drvs() == 0 ) {
|
||||||
&& cmd_buffer[0] != CMD_RD_WDC_RAM
|
if ( cmd_buffer[0] == CMD_WR_WDC_RAM
|
||||||
&& cmd_buffer[0] != CMD_FMTRD_TRACK
|
|| cmd_buffer[0] == CMD_RD_BLOCK ) {
|
||||||
&& cmd_buffer[0] != CMD_WR_WDC_RAM
|
wdc_send_errorcode ( 0xc1 );
|
||||||
&& cmd_buffer[0] != CMD_FMTBTT_TRACK
|
} else if ( cmd_buffer[0] == CMD_RD_WDC_RAM ) {
|
||||||
&& cmd_buffer[0] != CMD_RD_PARTAB
|
wdc_send_errorcode ( ERR_NO_DRIVE_READY );
|
||||||
&& cmd_buffer[0] != CMD_RD_WDCERR
|
wdc_set_initialized ( 0 );
|
||||||
&& cmd_buffer[0] != CMD_VER_TRACK
|
}
|
||||||
&& cmd_buffer[0] != CMD_DL_BTTAB
|
/* WDC freshly initialized after RESET, the disk is not valid */
|
||||||
&& cmd_buffer[0] != CMD_RD_BTTAB
|
} else if ( wdc_get_initialized()
|
||||||
&& cmd_buffer[0] != CMD_WR_BTTAB
|
&& ! wdc_get_disk_valid()
|
||||||
&& cmd_buffer[0] != CMD_WR_PARTAB
|
&& ( cmd_buffer[0] == CMD_WR_WDC_RAM || cmd_buffer[0] == CMD_RD_BLOCK ) ) {
|
||||||
&& cmd_buffer[0] != CMD_ST_PARBTT
|
wdc_send_errorcode ( ERR_CYL0_NOT_READABLE );
|
||||||
) {
|
wdc_set_initialized ( 0 );
|
||||||
wdc_send_error();
|
/* if the disk is not valid, only maintenance commands are allowed */
|
||||||
} else {
|
} else if ( ! wdc_get_disk_valid()
|
||||||
|
&& cmd_buffer[0] != CMD_RD_WDC_RAM
|
||||||
|
&& cmd_buffer[0] != CMD_FMTRD_TRACK
|
||||||
|
&& cmd_buffer[0] != CMD_WR_WDC_RAM
|
||||||
|
&& cmd_buffer[0] != CMD_FMTBTT_TRACK
|
||||||
|
&& cmd_buffer[0] != CMD_RD_PARTAB
|
||||||
|
&& cmd_buffer[0] != CMD_RD_WDCERR
|
||||||
|
&& cmd_buffer[0] != CMD_VER_TRACK
|
||||||
|
&& cmd_buffer[0] != CMD_DL_BTTAB
|
||||||
|
&& cmd_buffer[0] != CMD_RD_BTTAB
|
||||||
|
&& cmd_buffer[0] != CMD_WR_BTTAB
|
||||||
|
&& cmd_buffer[0] != CMD_WR_PARTAB
|
||||||
|
&& cmd_buffer[0] != CMD_ST_PARBTT
|
||||||
|
) {
|
||||||
|
if ( cmd_buffer[0] == CMD_RD_BLOCK )
|
||||||
|
wdc_send_errorcode ( ERR_SECT_N_ON_SURFACE );
|
||||||
|
else
|
||||||
|
wdc_send_error();
|
||||||
|
} else {
|
||||||
|
|
||||||
switch ( cmd_buffer[0] ) {
|
switch ( cmd_buffer[0] ) {
|
||||||
case CMD_WR_BLOCK:
|
case CMD_WR_BLOCK:
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
blockno = wdc_p8kblock2sdblock ( ( ( uint32_t ) cmd_buffer[5] << 24 ) | ( ( uint32_t ) cmd_buffer[4] << 16 ) | ( ( uint16_t ) cmd_buffer[3] << 8 ) | cmd_buffer[2] );
|
blockno = wdc_p8kblock2sdblock ( ( ( uint32_t ) cmd_buffer[5] << 24 ) | ( ( uint32_t ) cmd_buffer[4] << 16 ) | ( ( uint16_t ) cmd_buffer[3] << 8 ) | cmd_buffer[2] );
|
||||||
wdc_receive_data ( data_buffer
|
wdc_receive_data ( data_buffer
|
||||||
, data_counter
|
, data_counter
|
||||||
);
|
);
|
||||||
errorcode = 1;
|
errorcode = 1;
|
||||||
if ( data_counter == WDC_BLOCKLEN ) {
|
if ( data_counter == WDC_BLOCKLEN ) {
|
||||||
errorcode = wdc_write_sector ( blockno, data_buffer );
|
errorcode = wdc_write_sector ( blockno, data_buffer );
|
||||||
} else {
|
} else {
|
||||||
errorcode = wdc_write_multiblock ( blockno, data_buffer, data_counter / WDC_BLOCKLEN );
|
errorcode = wdc_write_multiblock ( blockno, data_buffer, data_counter / WDC_BLOCKLEN );
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( errorcode )
|
if ( errorcode )
|
||||||
wdc_send_error();
|
wdc_send_error();
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case CMD_RD_BLOCK:
|
case CMD_RD_BLOCK:
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
blockno = wdc_p8kblock2sdblock ( ( ( uint32_t ) cmd_buffer[5] << 24 ) | ( ( uint32_t ) cmd_buffer[4] << 16 ) | ( ( uint16_t ) cmd_buffer[3] << 8 ) | cmd_buffer[2] );
|
blockno = wdc_p8kblock2sdblock ( ( ( uint32_t ) cmd_buffer[5] << 24 ) | ( ( uint32_t ) cmd_buffer[4] << 16 ) | ( ( uint16_t ) cmd_buffer[3] << 8 ) | cmd_buffer[2] );
|
||||||
|
|
||||||
errorcode = 1;
|
errorcode = 1;
|
||||||
if ( data_counter == WDC_BLOCKLEN ) {
|
if ( data_counter == WDC_BLOCKLEN ) {
|
||||||
errorcode = wdc_read_sector ( blockno, data_buffer );
|
errorcode = wdc_read_sector ( blockno, data_buffer );
|
||||||
} else {
|
} else {
|
||||||
errorcode = wdc_read_multiblock ( blockno, data_buffer, data_counter / WDC_BLOCKLEN );
|
errorcode = wdc_read_multiblock ( blockno, data_buffer, data_counter / WDC_BLOCKLEN );
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ( errorcode ) {
|
||||||
|
wdc_send_error();
|
||||||
|
} else {
|
||||||
|
wdc_send_data ( data_buffer
|
||||||
|
, data_counter
|
||||||
|
);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CMD_WR_WDC_RAM:
|
||||||
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
|
wdc_receive_data ( data_buffer
|
||||||
|
, data_counter
|
||||||
|
);
|
||||||
|
|
||||||
|
wdc_write_data_to_ram ( data_buffer
|
||||||
|
, convert_ram_address ( ( cmd_buffer[2] << 8 ) | cmd_buffer[1] )
|
||||||
|
, data_counter
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CMD_RD_WDC_RAM:
|
||||||
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
|
wdc_read_data_from_ram ( data_buffer
|
||||||
|
, convert_ram_address ( ( cmd_buffer[2] << 8 ) | cmd_buffer[1] )
|
||||||
|
, data_counter
|
||||||
|
);
|
||||||
|
|
||||||
if ( errorcode ) {
|
|
||||||
wdc_send_error();
|
|
||||||
} else {
|
|
||||||
wdc_send_data ( data_buffer
|
wdc_send_data ( data_buffer
|
||||||
, data_counter
|
, data_counter
|
||||||
);
|
);
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_WR_WDC_RAM:
|
wdc_set_initialized ( 0 );
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
|
||||||
|
|
||||||
wdc_receive_data ( data_buffer
|
|
||||||
, data_counter
|
|
||||||
);
|
|
||||||
|
|
||||||
wdc_write_data_to_ram ( data_buffer
|
|
||||||
, convert_ram_address ( ( cmd_buffer[2] << 8 ) | cmd_buffer[1] )
|
|
||||||
, data_counter
|
|
||||||
);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_RD_WDC_RAM:
|
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
|
||||||
|
|
||||||
wdc_read_data_from_ram ( data_buffer
|
|
||||||
, convert_ram_address ( ( cmd_buffer[2] << 8 ) | cmd_buffer[1] )
|
|
||||||
, data_counter
|
|
||||||
);
|
|
||||||
|
|
||||||
wdc_send_data ( data_buffer
|
|
||||||
, data_counter
|
|
||||||
);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_RD_PARTAB:
|
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
|
||||||
|
|
||||||
wdc_read_par_table ( data_buffer
|
|
||||||
, data_counter );
|
|
||||||
|
|
||||||
wdc_send_data ( data_buffer
|
|
||||||
, data_counter
|
|
||||||
);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_WR_PARTAB:
|
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
|
||||||
|
|
||||||
wdc_receive_data ( data_buffer
|
|
||||||
, data_counter
|
|
||||||
);
|
|
||||||
|
|
||||||
wdc_write_wdc_par ( data_buffer
|
|
||||||
, data_counter );
|
|
||||||
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_DL_BTTAB:
|
|
||||||
wdc_del_wdc_btt();
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_RD_BTTAB:
|
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
|
||||||
|
|
||||||
wdc_read_wdc_btt ( data_buffer
|
|
||||||
, data_counter );
|
|
||||||
|
|
||||||
wdc_send_data ( data_buffer
|
|
||||||
, data_counter
|
|
||||||
);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_WR_BTTAB:
|
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
|
||||||
|
|
||||||
wdc_receive_data ( data_buffer
|
|
||||||
, data_counter
|
|
||||||
);
|
|
||||||
|
|
||||||
wdc_write_wdc_btt ( data_buffer
|
|
||||||
, data_counter );
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_FMTRD_TRACK:
|
|
||||||
case CMD_FMTBTT_TRACK:
|
|
||||||
|
|
||||||
/* no cylinder 0 formatting if command is CMD_FMTBTT_TRACK */
|
|
||||||
if ( cmd_buffer[0] == CMD_FMTBTT_TRACK && ( cmd_buffer[2] | ( cmd_buffer[3] << 8 ) ) == 0 )
|
|
||||||
break;
|
break;
|
||||||
|
|
||||||
data_counter = WDC_BLOCKLEN;
|
case CMD_RD_PARTAB:
|
||||||
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
memset ( &data_buffer[0], 0x00, data_counter );
|
wdc_read_par_table ( data_buffer
|
||||||
blockno = wdc_sector2sdblock ( cmd_buffer[2] | ( cmd_buffer[3] << 8 )
|
, data_counter );
|
||||||
, cmd_buffer[4]
|
|
||||||
, cmd_buffer[5]
|
|
||||||
);
|
|
||||||
|
|
||||||
errorcode = 1;
|
wdc_send_data ( data_buffer
|
||||||
for ( i8 = 0; i8 < wdc_get_hdd_sectors(); i8++ ) {
|
, data_counter
|
||||||
errorcode = wdc_write_sector ( blockno, data_buffer );
|
);
|
||||||
if ( errorcode ) break;
|
break;
|
||||||
blockno++;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
case CMD_WR_PARTAB:
|
||||||
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
if ( errorcode ) {
|
wdc_receive_data ( data_buffer
|
||||||
if ( cmd_buffer[0] == CMD_FMTRD_TRACK ) {
|
, data_counter
|
||||||
wdc_send_error();
|
);
|
||||||
} else {
|
|
||||||
if ( wdc_add_btt_entry ( cmd_buffer[2] | ( cmd_buffer[3] << 8 ), cmd_buffer[4] ) ) {
|
wdc_write_wdc_par ( data_buffer
|
||||||
|
, data_counter );
|
||||||
|
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CMD_DL_BTTAB:
|
||||||
|
wdc_del_wdc_btt();
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CMD_RD_BTTAB:
|
||||||
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
|
wdc_read_wdc_btt ( data_buffer
|
||||||
|
, data_counter );
|
||||||
|
|
||||||
|
wdc_send_data ( data_buffer
|
||||||
|
, data_counter
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CMD_WR_BTTAB:
|
||||||
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
|
wdc_receive_data ( data_buffer
|
||||||
|
, data_counter
|
||||||
|
);
|
||||||
|
|
||||||
|
wdc_write_wdc_btt ( data_buffer
|
||||||
|
, data_counter );
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CMD_FMTRD_TRACK:
|
||||||
|
case CMD_FMTBTT_TRACK:
|
||||||
|
|
||||||
|
/* no cylinder 0 formatting if command is CMD_FMTBTT_TRACK */
|
||||||
|
if ( cmd_buffer[0] == CMD_FMTBTT_TRACK && ( cmd_buffer[2] | ( cmd_buffer[3] << 8 ) ) == 0 )
|
||||||
|
break;
|
||||||
|
|
||||||
|
data_counter = WDC_BLOCKLEN;
|
||||||
|
|
||||||
|
memset ( &data_buffer[0], 0x00, data_counter );
|
||||||
|
blockno = wdc_sector2sdblock ( cmd_buffer[2] | ( cmd_buffer[3] << 8 )
|
||||||
|
, cmd_buffer[4]
|
||||||
|
, cmd_buffer[5]
|
||||||
|
);
|
||||||
|
|
||||||
|
errorcode = 1;
|
||||||
|
for ( i8 = 0; i8 < wdc_get_hdd_sectors(); i8++ ) {
|
||||||
|
errorcode = wdc_write_sector ( blockno, data_buffer );
|
||||||
|
if ( errorcode ) break;
|
||||||
|
blockno++;
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( errorcode ) {
|
||||||
|
if ( cmd_buffer[0] == CMD_FMTRD_TRACK ) {
|
||||||
wdc_send_error();
|
wdc_send_error();
|
||||||
} else {
|
} else {
|
||||||
data_buffer[0] = cmd_buffer[2]; /* Track Low */
|
errorcode = wdc_add_btt_entry ( cmd_buffer[2] | ( cmd_buffer[3] << 8 ), cmd_buffer[4] );
|
||||||
data_buffer[1] = cmd_buffer[3]; /* Track High */
|
if ( errorcode ) {
|
||||||
data_buffer[2] = cmd_buffer[4]; /* Head */
|
wdc_send_errorcode ( errorcode );
|
||||||
|
} else {
|
||||||
|
data_buffer[0] = cmd_buffer[2]; /* Track Low */
|
||||||
|
data_buffer[1] = cmd_buffer[3]; /* Track High */
|
||||||
|
data_buffer[2] = cmd_buffer[4]; /* Head */
|
||||||
|
|
||||||
wdc_send_data ( data_buffer
|
wdc_send_data ( data_buffer
|
||||||
, 3
|
, 3
|
||||||
);
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
break;
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_ST_PARBTT:
|
case CMD_ST_PARBTT:
|
||||||
data_counter = WDC_BLOCKLEN;
|
data_counter = WDC_BLOCKLEN;
|
||||||
|
|
||||||
blockno = 0;
|
blockno = 0;
|
||||||
wdc_set_disk_valid();
|
wdc_set_disk_valid();
|
||||||
wdc_read_par_table ( data_buffer
|
wdc_read_par_table ( data_buffer
|
||||||
, data_counter );
|
, data_counter );
|
||||||
|
|
||||||
errorcode = wdc_write_sector ( blockno, data_buffer );
|
|
||||||
if ( errorcode )
|
|
||||||
wdc_send_error();
|
|
||||||
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_RD_WDCERR:
|
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
|
||||||
|
|
||||||
memset ( &data_buffer[0], 0x00, data_counter );
|
|
||||||
wdc_send_data ( data_buffer
|
|
||||||
, data_counter
|
|
||||||
);
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_VER_TRACK:
|
|
||||||
data_counter = WDC_BLOCKLEN;
|
|
||||||
|
|
||||||
blockno = wdc_sector2sdblock ( cmd_buffer[2] | ( cmd_buffer[3] << 8 )
|
|
||||||
, cmd_buffer[4]
|
|
||||||
, cmd_buffer[5]
|
|
||||||
);
|
|
||||||
errorcode = 1;
|
|
||||||
for ( i8 = 0; i8 < wdc_get_hdd_sectors(); i8++ ) {
|
|
||||||
errorcode = wdc_read_sector ( blockno, data_buffer );
|
|
||||||
if ( errorcode ) break;
|
|
||||||
blockno++;
|
|
||||||
}
|
|
||||||
if ( errorcode )
|
|
||||||
wdc_send_error();
|
|
||||||
break;
|
|
||||||
|
|
||||||
case CMD_RD_SECTOR:
|
|
||||||
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
|
||||||
|
|
||||||
blockno = wdc_sector2sdblock ( cmd_buffer[2] | ( cmd_buffer[3] << 8 )
|
|
||||||
, cmd_buffer[4]
|
|
||||||
, cmd_buffer[5]
|
|
||||||
);
|
|
||||||
errorcode = 1;
|
|
||||||
|
|
||||||
if ( data_counter == WDC_BLOCKLEN ) {
|
|
||||||
errorcode = wdc_write_sector ( blockno, data_buffer );
|
errorcode = wdc_write_sector ( blockno, data_buffer );
|
||||||
} else {
|
if ( errorcode )
|
||||||
errorcode = wdc_write_multiblock ( blockno, data_buffer, data_counter / WDC_BLOCKLEN );
|
wdc_send_error();
|
||||||
}
|
|
||||||
|
|
||||||
if ( errorcode )
|
break;
|
||||||
wdc_send_error();
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
case CMD_RD_WDCERR:
|
||||||
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
|
memset ( &data_buffer[0], 0x00, data_counter );
|
||||||
|
wdc_send_data ( data_buffer
|
||||||
|
, data_counter
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CMD_VER_TRACK:
|
||||||
|
data_counter = WDC_BLOCKLEN;
|
||||||
|
|
||||||
|
blockno = wdc_sector2sdblock ( cmd_buffer[2] | ( cmd_buffer[3] << 8 )
|
||||||
|
, cmd_buffer[4]
|
||||||
|
, cmd_buffer[5]
|
||||||
|
);
|
||||||
|
errorcode = 1;
|
||||||
|
for ( i8 = 0; i8 < wdc_get_hdd_sectors(); i8++ ) {
|
||||||
|
errorcode = wdc_read_sector ( blockno, data_buffer );
|
||||||
|
if ( errorcode ) break;
|
||||||
|
blockno++;
|
||||||
|
}
|
||||||
|
if ( errorcode )
|
||||||
|
wdc_send_error();
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CMD_RD_SECTOR:
|
||||||
|
data_counter = ( cmd_buffer[7] << 8 ) | cmd_buffer[6];
|
||||||
|
|
||||||
|
blockno = wdc_sector2sdblock ( cmd_buffer[2] | ( cmd_buffer[3] << 8 )
|
||||||
|
, cmd_buffer[4]
|
||||||
|
, cmd_buffer[5]
|
||||||
|
);
|
||||||
|
errorcode = 1;
|
||||||
|
|
||||||
|
if ( data_counter == WDC_BLOCKLEN ) {
|
||||||
|
errorcode = wdc_write_sector ( blockno, data_buffer );
|
||||||
|
} else {
|
||||||
|
errorcode = wdc_write_multiblock ( blockno, data_buffer, data_counter / WDC_BLOCKLEN );
|
||||||
|
}
|
||||||
|
|
||||||
|
if ( errorcode )
|
||||||
|
wdc_send_error();
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
#if DEBUG >= 1
|
#if DEBUG >= 1
|
||||||
uart_puts_p ( PSTR ( " Unknown command:" ) );
|
uart_puts_p ( PSTR ( " Unknown command:" ) );
|
||||||
uart_putc_hex ( cmd_buffer[0] );
|
uart_putc_hex ( cmd_buffer[0] );
|
||||||
uart_putc_hex ( cmd_buffer[1] );
|
uart_putc_hex ( cmd_buffer[1] );
|
||||||
uart_putc_hex ( cmd_buffer[2] );
|
uart_putc_hex ( cmd_buffer[2] );
|
||||||
uart_putc_hex ( cmd_buffer[3] );
|
uart_putc_hex ( cmd_buffer[3] );
|
||||||
uart_putc_hex ( cmd_buffer[4] );
|
uart_putc_hex ( cmd_buffer[4] );
|
||||||
uart_putc_hex ( cmd_buffer[5] );
|
uart_putc_hex ( cmd_buffer[5] );
|
||||||
uart_putc_hex ( cmd_buffer[6] );
|
uart_putc_hex ( cmd_buffer[6] );
|
||||||
uart_putc_hex ( cmd_buffer[7] );
|
uart_putc_hex ( cmd_buffer[7] );
|
||||||
uart_putc_hex ( cmd_buffer[8] );
|
uart_putc_hex ( cmd_buffer[8] );
|
||||||
uart_putc ( '\n' );
|
uart_putc ( '\n' );
|
||||||
#endif
|
#endif
|
||||||
wdc_send_error();
|
wdc_send_error();
|
||||||
break;
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* $Id: wdc_main.h,v 1.11 2012/06/09 00:22:28 olivleh1 Exp $
|
* $Id: wdc_main.h,v 1.12 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
|
@ -59,4 +59,10 @@
|
||||||
#define ___CMD_WRRD_BLOCK 0xa2 /* write and reread block */
|
#define ___CMD_WRRD_BLOCK 0xa2 /* write and reread block */
|
||||||
#define CMD_ST_PARBTT 0xc2 /* store PAR and BTT on hard disk */
|
#define CMD_ST_PARBTT 0xc2 /* store PAR and BTT on hard disk */
|
||||||
|
|
||||||
|
#define ERR_STANDARD 0x01
|
||||||
|
#define ERR_SECT_N_ON_SURFACE 0x0A
|
||||||
|
#define ERR_BTT_FULL 0x16
|
||||||
|
#define ERR_NO_DRIVE_READY 0x27
|
||||||
|
#define ERR_CYL0_NOT_READABLE 0x31
|
||||||
|
|
||||||
#endif /* MAIN_H_ */
|
#endif /* MAIN_H_ */
|
||||||
|
|
|
||||||
|
|
@ -26,11 +26,13 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* $Id: wdc_par.c,v 1.3 2012/06/09 00:22:28 olivleh1 Exp $
|
* $Id: wdc_par.c,v 1.4 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include <avr/pgmspace.h>
|
#include <avr/pgmspace.h>
|
||||||
|
#include "main.h"
|
||||||
#include "wdc_par.h"
|
#include "wdc_par.h"
|
||||||
|
#include "uart.h"
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* unformatted ST138
|
* unformatted ST138
|
||||||
|
|
@ -97,6 +99,7 @@ par_tab_no_dsk[128] = {'W', 'D', 'C', '_', '4', '.', '2', 0x81, 0x81, 0x
|
||||||
};
|
};
|
||||||
|
|
||||||
uint8_t valid_disk = 1;
|
uint8_t valid_disk = 1;
|
||||||
|
uint8_t initialized;
|
||||||
|
|
||||||
void wdc_read_par_table ( uint8_t *buffer, uint16_t count )
|
void wdc_read_par_table ( uint8_t *buffer, uint16_t count )
|
||||||
{
|
{
|
||||||
|
|
@ -182,7 +185,7 @@ uint8_t wdc_add_btt_entry ( uint16_t cylinder, uint8_t head )
|
||||||
wdc_set_btt_count ( btt_count );
|
wdc_set_btt_count ( btt_count );
|
||||||
return ( 0 );
|
return ( 0 );
|
||||||
} else {
|
} else {
|
||||||
return ( 1 );
|
return ( ERR_BTT_FULL );
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -252,3 +255,13 @@ uint8_t wdc_get_num_of_drvs()
|
||||||
{
|
{
|
||||||
return par_table[49];
|
return par_table[49];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void wdc_set_initialized(uint8_t num)
|
||||||
|
{
|
||||||
|
initialized=num;
|
||||||
|
}
|
||||||
|
|
||||||
|
uint8_t wdc_get_initialized()
|
||||||
|
{
|
||||||
|
return initialized;
|
||||||
|
}
|
||||||
|
|
@ -26,7 +26,7 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* $Id: wdc_par.h,v 1.3 2012/06/09 00:22:29 olivleh1 Exp $
|
* $Id: wdc_par.h,v 1.4 2012/06/09 19:47:31 olivleh1 Exp $
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef WDC_PAR_H_
|
#ifndef WDC_PAR_H_
|
||||||
|
|
@ -43,16 +43,15 @@ extern void wdc_read_wdc_btt ( uint8_t *buffer, uint16_t count );
|
||||||
extern void wdc_write_wdc_btt ( uint8_t *buffer, uint16_t count );
|
extern void wdc_write_wdc_btt ( uint8_t *buffer, uint16_t count );
|
||||||
extern uint16_t wdc_get_btt_count();
|
extern uint16_t wdc_get_btt_count();
|
||||||
extern uint8_t wdc_add_btt_entry ( uint16_t cylinder, uint8_t head );
|
extern uint8_t wdc_add_btt_entry ( uint16_t cylinder, uint8_t head );
|
||||||
|
|
||||||
extern uint8_t wdc_get_hdd_sectors();
|
extern uint8_t wdc_get_hdd_sectors();
|
||||||
extern uint8_t wdc_get_hdd_heads();
|
extern uint8_t wdc_get_hdd_heads();
|
||||||
|
extern void wdc_set_disk_invalid();
|
||||||
void wdc_set_disk_invalid();
|
extern void wdc_set_disk_valid();
|
||||||
void wdc_set_disk_valid();
|
extern uint8_t wdc_get_disk_valid();
|
||||||
uint8_t wdc_get_disk_valid();
|
extern void wdc_set_no_disk();
|
||||||
|
extern uint8_t wdc_get_num_of_drvs();
|
||||||
void wdc_set_no_disk();
|
extern void wdc_set_initialized ( uint8_t num );
|
||||||
uint8_t wdc_get_num_of_drvs();
|
extern uint8_t wdc_get_initialized ();
|
||||||
|
|
||||||
#define POS_PAR_VERSION 0
|
#define POS_PAR_VERSION 0
|
||||||
#define POS_PAR_WDC_PAR 8
|
#define POS_PAR_WDC_PAR 8
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue