0% found this document useful (0 votes)
0 views

Zilog CompactFlesh Interface for eZ80Acclaim

This Application Note details the interface between eZ80Acclaim!™ MCUs and CompactFlash® Storage Cards, outlining operational modes and hardware architecture. It provides insights into the CompactFlash card's structure, including memory and I/O modes, and includes source code for implementation. The document serves as a guide for developers looking to integrate CompactFlash technology into their applications.

Uploaded by

kerandib
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
0% found this document useful (0 votes)
0 views

Zilog CompactFlesh Interface for eZ80Acclaim

This Application Note details the interface between eZ80Acclaim!™ MCUs and CompactFlash® Storage Cards, outlining operational modes and hardware architecture. It provides insights into the CompactFlash card's structure, including memory and I/O modes, and includes source code for implementation. The document serves as a guide for developers looking to integrate CompactFlash technology into their applications.

Uploaded by

kerandib
Copyright
© © All Rights Reserved
We take content rights seriously. If you suspect this is your content, claim it here.
Available Formats
Download as PDF, TXT or read online on Scribd
You are on page 1/ 65

Application Note

CompactFlash® Interface
for eZ80Acclaim!™
MCUs
AN015401-1103

ZiLOG Worldwide Headquarters • 532 Race Street • San Jose, CA 95126


Telephone: 408.558.8500 • Fax: 408.558.8300 • www.ZiLOG.com
Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

This publication is subject to replacement by a later edition. To determine whether a later edition
exists, or to request copies of publications, contact:

ZiLOG Worldwide Headquarters


532 Race Street
San Jose, CA 95126
Telephone: 408.558.8500
Fax: 408.558.8300
www.zilog.com

ZiLOG is a registered trademark of ZiLOG Inc. in the United States and in other countries.
CompactFlash is a registered trademark of Sandisk Corp. All other products and/or service names
mentioned herein may be trademarks of the companies with which they are associated.

Information Integrity
The information contained within this document has been verified according to the general
principles of electrical and mechanical engineering. Any applicable source code illustrated in the
document was either written by an authorized ZiLOG employee or licensed consultant. Permission
to use these codes in any form, besides the intended application, must be approved through a
license agreement between both parties. ZiLOG will not be responsible for any code(s) used
beyond the intended application. Contact the local ZiLOG Sales Office to obtain necessary license
agreements.

Document Disclaimer
©2003 by ZiLOG, Inc. All rights reserved. Information in this publication concerning the devices,
applications, or technology described is intended to suggest possible uses and may be
superseded. ZiLOG, INC. DOES NOT ASSUME LIABILITY FOR OR PROVIDE A
REPRESENTATION OF ACCURACY OF THE INFORMATION, DEVICES, OR TECHNOLOGY
DESCRIBED IN THIS DOCUMENT. ZiLOG ALSO DOES NOT ASSUME LIABILITY FOR
INTELLECTUAL PROPERTY INFRINGEMENT RELATED IN ANY MANNER TO USE OF
INFORMATION, DEVICES, OR TECHNOLOGY DESCRIBED HEREIN OR OTHERWISE. Except
with the express written approval ZiLOG, use of information, devices, or technology as critical
components of life support systems is not authorized. No licenses or other rights are conveyed,
implicitly or otherwise, by this document under any intellectual property rights.

AN015401-1103
Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

iii

Table of Contents
List of Figures . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . iv
List of Tables . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .v
Abstract . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 1
eZ80Acclaim!™ Flash MCU Overview . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 1
Discussion . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 1
CompactFlash® Storage Card . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 2
Modes of Operation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
Developing the CompactFlash® Interface . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
Hardware Architecture . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3
Software Implementation . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 8
Testing . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10
Setup . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10
Equipment Used . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
Test Procedure . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 11
Test Results . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 12
Appendix A—References . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
Appendix B—Flowchart . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14
Appendix C—Schematic Diagrams . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 15
Appendix D—Source Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18
C Files . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18
Assembly File . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 46
Header Files . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 48
Appendix E—API Description . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54

AN015401-1103 Table of Contents


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

iv

List of Figures
Figure 1. Structure of a CompactFlash Storage Card . . . . . . . . . . . . . . . . . . . 2
Figure 2. System Connections for the CompactFlash Interface with an
eZ80Acclaim! MCU . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4
Figure 3. Flowchart for CompactFlash APIs . . . . . . . . . . . . . . . . . . . . . . . . . . 14
Figure 4. Schematic for Connections between Development Board and
Expansion Board . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 15
Figure 5. Schematic for Interface Logic on the CompactFlash Expansion
Board . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 16
Figure 6. Schematic for CompactFlash Connector . . . . . . . . . . . . . . . . . . . . . 17

AN015401-1103 List of Figures


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

List of Tables
Table 1. eZ80F91 Address Bits and CompactFlash Pins - Connection Details 5
Table 2. Demultiplexer Logic Truth Table. . . . . . . . . . . . . . . . . . . . . . . . . . . . . 6
Table 3. Port B GPIO Interface to CompactFlash Control Signals . . . . . . . . . . 7
Table 4. Derived Addresses for the CompactFlash Registers . . . . . . . . . . . . . 7
Table 5. List of References. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13
Table 6. CompactFlash Interface APIs . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 54

AN015401-1103 List of Tables


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

Abstract
This Application Note illustrates an interface between an eZ80Acclaim!™ MCU
and a CompactFlash® Storage Card. The CompactFlash card is accessed in the
following modes of operation: the memory mode, the contiguous I/O mode, the
primary I/O mode, and the secondary I/O mode.
The AN0154-SC01.zip file contains the source code associated with this Applica-
tion Note and is available on the ZiLOG website.

eZ80Acclaim!™ Flash MCU Overview


The eZ80Acclaim! on-chip Flash Microcontrollers are an exceptional value for
customers designing high performance, 8-bit MCU-based systems. With speeds
upto 50 MHz and an on-chip Ethernet MAC (eZ80F91 only), designers have the
performance necessary to execute complex applications quickly and efficiently.
Combining Flash and SRAM, eZ80Acclaim! devices provide the memory required
to implement communication protocol stacks and achieve flexibility when perform-
ing in-system updates of application firmware.
The eZ80Acclaim! Flash MCU can operate in full 24-bit linear mode addressing
16MB without a Memory Management Unit. Additionally, support for the Z80-
compatible mode allows Z80/Z180 customers to execute legacy code within multi-
ple 64KB memory blocks with minimum modifications. With an external bus sup-
porting eZ80, Z80, Intel, and Motorola bus modes and a rich set of serial
communications peripherals, designers have several options when interfacing to
external devices.
Some of the many applications suitable for eZ80Acclaim! devices include vending
machines, point-of-sale terminals, security systems, automation, communications,
industrial control and facility monitoring, and remote control.

Discussion
The CompactFlash interface is a vendor-independent specification that can be
implemented to develop CompactFlash products that are compatible with a wide
range of user applications and across a gamut of manufacturers.
The early CompactFlash cards were meant exclusively for Flash data storage;
however, currently under the CF+ specification, they support various I/O devices,
such as Ethernet cards and fax/modem cards, to name a few.

AN015401-1103 Abstract
Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

CompactFlash® Storage Card


Figure 1 illustrates a CompactFlash Storage Card that contains a dedicated con-
troller and Flash memory module(s). The controller interfaces with a host system,
allowing data to be written to and read from the Flash memory module(s).
The host interface consists of address lines from A0:A10, data lines from D0:D15
and control signals.

CompactFlash Storage Card


HOST INTERFACE

Data In/Out Flash


Controller Module
Control

Figure 1. Structure of a CompactFlash Storage Card

The address space requirement for interfacing a CompactFlash Storage Card is


just 2 KB, irrespective of the storage capacity of the card. The data bus can be
interfaced as an 8-bit or a 16-bit bus, depending on the host support. The Flash
modules are not directly accessible to the host, even at the byte level. The control-
ler transfers the data to and from the Flash modules in blocks of 512 bytes. The
host essentially communicates with the controller, which contains control/status
registers and a data buffer mapped within the 2 KB address space of the host.

Description of the CompactFlash® Storage Card


The CompactFlash Storage Card used in this application is a 64 MB card from
Kingston Technology. Internal to the card, the memory is divided into three differ-
ent sections: the attribute memory, the command/status tuple, and the storage
memory.
Attribute Memory. The attribute memory is a set of registers that store card identi-
fication and configuration information. The card can be configured in the memory
and I/O modes using these registers. The starting address of these registers is
fixed at an offset of 0x200.
Command/Status Tuple. The command/status tuple are sequentially addressed
control registers with different starting addresses depending upon the mode of
operation. When a host writes to the tuple, it behaves as a set of registers that

AN015401-1103 CompactFlash® Storage Card


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

holds the command parameters and the command. It is essential to write the com-
mand parameters before the command because the controller executes the com-
mand according to the parameters present in other registers.
Similarly, when a host reads to the command/status tuple, the tuple behaves as a
set of registers that holds the status information about the last executed com-
mand. The start address of the command/status tuple is 0x000.The first register
at address 0x000 is for the data register, which does not contribute to the actual
command/status information.
Storage Memory. Storage memory is a large area of Flash memory. Access to this
space is handled by the controller in a manner that is transparent to the host. The
address space requirement for interfacing a CompactFlash Storage Card is just
2 KB, irrespective of the storage capacity of the card.
Note: The addresses of attribute memory, control/status, and data registers lie
within the 2 KB space.

Modes of Operation
The CompactFlash operates in several modes. Two of these modes are relevant
to this Application Note and are briefly discussed in this section.
Memory Mode. This mode is the default mode of operation for the CompactFlash.
The CompactFlash card enters this mode at Power On or RESET, if the OE pin is
held at a logic HIGH (1).
I/O Mode(s). There are three distinct I/O modes: the primary I/O mode, the sec-
ondary I/O mode, and the contiguous I/O mode. To enter into any of the I/O
modes, it is necessary to enter into the memory mode first and then modify the
card configuration register (in the attribute memory space) accordingly.

Developing the CompactFlash® Interface


The hardware architecture and the software implementation to develop the Com-
pactFlash Storage Card interface for the eZ80Acclaim! MCU is described in this
section.

Hardware Architecture
The CompactFlash Storage Card consists of pins that operate according to the
mode in which the card is operated, resulting in different interfaces for different
modes. The architecture suggested in Figure 2 considers a superset of these
requirements to illustrate all the three modes with the same hardware setup. The
block diagram in Figure 2 is the basis for the schematics in the Appendix C on
page 15.

AN015401-1103 Modes of Operation


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

eZ80Acclaim!TM MCU INTERFACE CF CARD


BLOCK
A[0:10] A[0:10]

D[0:7]
D[0:7]
CS3

CE1
CE2
A[11:14]
OE
WE

PB7 IORD
PB6 IOWR
PB5
PB4

WAIT
PB3
PB2
RDY/BSY
PB1
PB0
CD1
CD2

Figure 2. System Connections for the CompactFlash Interface with an eZ80Acclaim! MCU

The hardware is designed to interface with the CompactFlash in the modes of


operation mentioned previously. It is therefore necessary to understand the hard-
ware requirements for entering and operating the different modes. These require-
ments are described under two domains: requirements common to all the modes
of operation, and requirements that vary for different modes. The common
requirements are described first, followed by the varied requirements.

Common Requirements
At the outset, it is necessary to determine that a card is present in the slot for
operation. Two signals are located at the two extremes of the CompactFlash con-
nector to facilitate card detection (-CD1, -CD2) and correct insertion. These sig-
nals are pulled low inside the card. An OR-gate (74LVC32AD) combines these
card detect signals to derive one signal that is connected to the Port B pin0 (PB0)
of the eZ80F91 MCU. PB0 is polled by the software to determine if the Compact-
Flash card is present.
The eZ80F91 data bus is byte wide, therefore the D[0:7] data bus is connected to
the corresponding data lines/pins of the CompactFlash. The CompactFlash HIGH
data bus, D[8:15], is not connected.

AN015401-1103 Hardware Architecture


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

The eZ80F91 address bus, A[0:23], is described as different groups of address


lines.
The 11 least significant bits of the eZ80F91 address bus, A[0:10], are connected
directly to A[0:10] of the CompactFlash connector. This address area defines a
space for 2 KB (2048) addresses. The address lines, A[11:14], are used in the
manner depicted in Table 1.

Table 1. eZ80F91 Address Bits and CompactFlash Pins - Connection Details

F91 Address Bit CompactFlash Pin (number)


A11 REG
A12 CE1/CE1/CS0
A13 CE2/CE2/CS1
A14 CSEL
A15 Not used

The 8 most significant bits, A[16:23], decide the chip select, providing the pro-
grammer flexibility to map the 2 KB address space anywhere within the 16 MB
area supported by the eZ80F91 device. For this CompactFlash Interface applica-
tion, the A[16:23] byte is assigned the value of 0xA8.
Finally, as per the CompactFlash specification, 10 K W resistors are used to pull up
each of the following signals to VDD:
• READY
• INPACK
• WAIT
• WP
• VS1
• VS2
• BVD1
• BVD2

Varied Requirements
Some of the control signals in the CompactFlash card are used for multiple pur-
poses while some of the signals differ for different modes. All of these signals
require additional hardware and pins from the CompactFlash host.

AN015401-1103 Hardware Architecture


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

As described in the Modes of Operation section on page 3, the change from mem-
ory mode to any of the I/O modes is achieved through the software. However,
such a mode change also requires a change in hardware. In the memory mode,
the RD and WR strobes from the host are connected to the OE and WE signals of
the CompactFlash card. In the I/O modes, the host signals are connected to IORD
and IOWR signals of the CompactFlash card.
The switching functionality is achieved through the use of a de-mux (de-multi-
plexer). The chip select (as decided by the A[16:23]) and PB7 pin control the
action of the de-mux. When the chip select is asserted, the PB7 pin is HIGH for
the memory mode, and LOW for other modes of CompactFlash operation.
For all modes other than the memory mode, the de-mux routes RD and WR sig-
nals from the eZ80F91 to IORD and IOWR, respectively. For the memory mode,
the de-mux routes the WR signal directly to the CompactFlash WE signal. The RD
signal, however, is not directly connected to the OE pin because the OE pin also
handles the other functionality, such as determining if the CompactFlash card
resets into the memory mode or the TrueIDE mode at RESET. The RD signal is
therefore routed out of the de-mux and is referred to as MEM_MODE.

Table 2. Demultiplexer Logic Truth Table

CSx PB7 WR RD Action Remarks


0 0 1 0 IORD = RD
0 0 0 1 IOWR = WR
If PB6 = 1, then
0 1 1 0 MEM_MODE = RD
OE = MEM_MODE
0 1 0 1 WE = WR

The memory mode is the default mode of operation. If the OE signal is not
grounded, this default mode of operation is functional at power ON or RESET.
However, if the OE pin is grounded, the CompactFlash card enters the True IDE
mode on RESET. Thus, the hardware must be able to perform the following oper-
ations.
To RESET the CompactFlash Storage Card at Run-time. To achieve this functional-
ity, the eZ80F91 port pin, PB4, is connected directly to the CompactFlash RESET
pin. By toggling PB4, the CompactFlash card can be RESET at any point of time.
To Control the OE pin at RESET. To achieve this functionality, the eZ80F91 port
pin, PB6, and the MEM_MODE signal issuing out of the de-multiplexer are AND-
ed, using the AND gate (74LVC08AD), to control the OE pin. The AND operation
forces a 0 (LOW) on the OE that is held at 1 (HIGH) when there are no RD trans-
actions on the CompactFlash.

AN015401-1103 Hardware Architecture


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

Thus, a mode conversion can be achieved by forcing a 0 on PB6 and toggling the
PB4 for a RESET.
The port B GPIO lines used to interface the CompactFlash control signals are
summarized in Table 3.

Table 3. Port B GPIO Interface to CompactFlash Control Signals

Bit Direction Functionality


PB7 Output To route (RD, WR) from eZ80F91 to either (OE, WE) or (IORD,
IOWR) depending on the memory or IO/IDE mode respectively.
PB6 Output To select the True IDE mode of operation for the CompactFlash
PB5 Output To indicate successful transfers/debug
PB4 Output To RESET the CompactFlash card through software – useful in
IDE Master/Slave modes.
PB3 Input BVD1/STSCHG/PDIAG
PB2 Input BVD2/SPKR/DASP
PB1 Input RDY BSY/IREQ/INTRQ
PB0 Input Combined Card Detect signal

The Interface Block


The CompactFlash card–eZ80Acclaim! interface logic comprises of a single OR-
gate, a single AND-gate and a de-mux (74LVC139AD), (see Figure 2).
Table 4 lists the derived addresses for the CompactFlash registers based on the
discussions in the sections on Common Requirements on page 4, and Varied
Requirements on page 5.

Table 4. Derived Addresses for the CompactFlash Registers

Mode A23-16 A15-12 A11-8 A7-4 A3-0 Complete Range


Memory A8h xx10 10xx xxxx 0h – 7h A82800h A82807h

Contiguous I/O A8h xx10 0x00 0000 0h – 7h A82000h A82007h

Primary I/O A8h xx10 0x01 1111 0h – 7h A821F0h A821F7h

Note: x : Indicates "don't care" condition. All 'x' are replaced by zeros
h : Indicates the preceding value to be a hexadecimal

AN015401-1103 Hardware Architecture


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

Table 4. Derived Addresses for the CompactFlash Registers (Continued)

Mode A23-16 A15-12 A11-8 A7-4 A3-0 Complete Range


Secondary I/O A8h xx10 0x01 0111 0h – 7h A82170h A82177h

Note: x : Indicates "don't care" condition. All 'x' are replaced by zeros
h : Indicates the preceding value to be a hexadecimal

Software Implementation
The CompactFlash Interface software is implemented as a set of API functions to
perform the following operations:
• Initialize and set the CompactFlash mode
• Write to a CompactFlash sector
• Identify the CompactFlash drive
• Set features for the CompactFlash card in terms of mode specifications
• Read from a CompactFlash sector
• Erase a CompactFlash sector
Refer to Appendix E on page 54 for details on the API functions. In addition to the
API functions, several supporting functions are implemented that may be useful
while using the CompactFlash card. These include –
• Software block data transfer (DMA operation)
• Delay generation (for various CompactFlash-specified delays)
• Card detection/Error checking
• Function to receive the sector, head and cylinder information
As discussed in the Command/Status Tuple section on page 2, the CompactFlash
interface works with the command tuple. The registers in the tuple are addressed
in a sequential manner. Therefore, it is sufficient to determine the address of the
first register in a specified mode. These addresses are hardware- and mode-
dependent and are hard-coded in the software for every mode.
The CompactFlash operating modes supported by the current CompactFlash
Interface application are the Memory mode and the I/O modes (contiguous/pri-
mary/secondary). When the user selects a particular mode of operation, the
addresses, being mode-dependent, are loaded into the appropriate pointer and
the user is prompted for an operation to be performed on the CompactFlash.
When the command to perform an operation is received, the corresponding regis-

AN015401-1103 Software Implementation


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

ters in the tuple are loaded with the required command parameters. This is fol-
lowed by a block transfer of data to/from the CompactFlash.
Two buffers, of 512 bytes each, are implemented in the CompactFlash Interface
software to transmit and receive data to/from the CompactFlash.

Switching between Modes


Because the default mode of operation for the CompactFlash card is the memory
mode, all the commands for this mode can be run directly. The CompactFlash
attributes are set to an 8-bit mode. They are marked as the 0th drive through the
set_features() API, such that the CompactFlash card can be switched to any
mode of operation.
To switch to any of the I/O modes, the appropriate bits are written in the configura-
tion register as follows:

Bit I/O Mode


1 Contiguous I/O
2 Primary I/O,
3 Secondary I/O

While switching to the I/O mode, the RD and WR signals from the eZ80F91 must
be connected to the IORD and IOWR signals of the CompactFlash card.
To revert to the memory mode, a 0x00 is written to the configuration register.

Processing the Commands


Commands are issued to the CompactFlash card when it is in the required mode.
The user provides the starting sector, cylinder, and head for the read_sectors()
and write_sectors() APIs. These APIs feed the values provided by the user
into appropriate command tuple registers and write the command word (0x20 for
READ and 0x30 for WRITE) in the command register.
For the READ command, the CompactFlash interface fills the buffer with one sec-
tor of data (512 bytes) and prompts the user for action through the status regis-
ters. The CompactFlash features a FIFO like structure that requires the host
(eZ80F91) to read the data from the same location repeatedly.
For a WRITE command, the entire data is first written to the CompactFlash buffer
before the CompactFlash interface starts writing the data in the designated sector.
When the data is completely written into the sector, the CompactFlash interface
informs the host through its status registers.

AN015401-1103 Software Implementation


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

10

The algorithm for the read_sector() API, which is the sequence of events for
reading from a sector, is outlined below.
1. Select the CompactFlash mode
2. Load the pointers for command/status tuple, and read buffers
3. Get the sector, cylinder, and head from where reading must begin on the
CompactFlash card
4. Load values from 5 to the appropriate command registers in the command
tuple
5. Load the read command in the command register
6. Wait for the CompactFlash card to be ready
7. Read 512 bytes from the CompactFlash data register
8. Indicate success/error

The algorithm for the write_sector() API, which is the sequence of events for
writing to a sector, is outlined below.
1. Select the CompactFlash mode
2. Load the pointers for command/status tuple, and write buffers
3. Get the data in the write buffer
4. Get the sector, cylinder, and head from where writing must begin on the
CompactFlash card
5. Load values from 5 to the appropriate command registers in the command
tuple
6. Load the write command in the command register
7. Wait for the CompactFlash card to be ready
8. Write 512 bytes from the CompactFlash data register
9. Indicate success/error

Testing
This section describes the setup, requirements, and the procedure followed to
demonstrate the CompactFlash Interface application using the eZ80F91 MCU.

Setup
The CompactFlash Storage Card is mounted on the CompactFlash Expansion
Board connectors of the eZ80F91 Development Kit (connectors J6 and J8). The

AN015401-1103 Testing
Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

11

EX_SEL jumper (J19) on the eZ80 Development Board is connected in order to


short MEM_EN2 to CS_EX.
The schematics for the connections between the eZ80 Development Board, the
CompactFlash Expansion Board, and the CompactFlash connector are presented
in Appendix C on page 15.

Equipment Used
• eZ80F91 Development Kit (eZ80F910200ZC0)
• CompactFlash Interface Expansion Board (developed indigenously)
• ZDSII-IDE for eZ80Acclaim! MCUs, v4.6.0
• CompactFlash Storage Card from Kingston technology with 64 MB memory
• PC with HyperTerminal; HyperTerminal is configured for 9600bps, 8 bit, no-
parity, 1 Stop bit, and No flow control.

Test Procedure
The procedure to demonstrate the CompactFlash Interface application is outlined
below.
1. The connections between the Development Board, the CompactFlash
Expansion Board, and the CompactFlash Connector are made according to
the schematics (Refer to Appendix C on page 15).
2. The CompactFlash Storage Card is fitted into the CompactFlash Connector.
3. The PC is connected to the eZ80 Development Board through ZPAKII.
4. Launch the ZDSII-IDE, build the program using the application code
(AN0154-SC01.zip file), and download the resulting .hex file to the
eZ80F91 on-chip Flash.
5. Launch the HyperTerminal. The command menu appears below the CF>>
prompt.
6. Enter m to select the mode. From the sub-menu, enter the appropriate
character for the required mode. The mode is selected and the command
menu appears again.
7. Enter i to identify the CompactFlash Storage Card. This operation tests the
identify_drive() API, which reads the CompactFlash parameters and
compares them with the CompactFlash datasheet.
8. At the CF>> prompt, enter w to write to a CompactFlash sector. This
operation tests the write_sector() API. The write sub-menu appears.
9. Enter values for Track, Head, and Sector within the prompted range.

AN015401-1103 Equipment Used


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

12

10. At the CF>> prompt, enter r to read to a CompactFlash sector. This


operation tests the read_sector() API. The read sub-menu appears.
11. Enter the same values as in step 9. The data that was previously written to
the CompactFlash sector is read by the eZ80F91 processor and displayed
on the HyperTerminal.

Test Results
The CompactFlash card was identified with the identify_drive() API. The for-
mat of the information received was found to be in agreement with CompactFlash
specification. Data transfer to and from the CompactFlash card was performed
and found to be error free.

Summary
This Application Note illustrates an interface between an eZ80Acclaim! MCU and
the CompactFlash Storage Card. It provides a designer with the basic building
block to develop a slew of applications using the eZ80Acclaim! as a webserver.
The user can benefit from all the advantages that the CompactFlash technology
offers, namely a power efficient and flexible way of storing digital data such as
web-pages, audio/video files, or simple log data.

AN015401-1103 Test Results


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

13

Appendix A—References
Further information regarding eZ80Acclaim! Flash Microcontrollers, and the Com-
pactFlash can be found in the references listed in Table 5.

Table 5. List of References

Topic Document Name & Document ID


eZ80Acclaim! eZ80F92/eZ80F93 Flash Module Product Specification, PS0189
eZ80F91 Flash MCU with Ethernet MAC Product Specification, PS0192
CompactFlash Specification CF+ and CompactFlash Specification Revision 1.4, available at
www.compactflash.org
CompactFlash Storage Card Kingston CompactFlash, MKF-260, available at www.kingston.com/
products/cf_white_paper.pdf

CompactFlash Storage Card, THNCF064MM, available at


www.toshiba.com/taec

AN015401-1103 Appendix A—References


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

14

Appendix B—Flowchart
The flowchart for CompactFlash Interface APIs is illustrated in Figure 3.

API START

Load the specific command parameters in to the command Tuple Registers 1-6

Load the command word in command Tuple Register 7

Wait for the CF storage card to become READY or generate Error

Transfer data to and from the CF storage card

Wait for the CF storage card to become READY or generate Error

Inform the API calling function of the Status/ Error

API RETURN

Figure 3. Flowchart for CompactFlash APIs

AN015401-1103 Appendix B—Flowchart


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

15

Appendix C—Schematic Diagrams


Figure 4 is a schematic diagram for connections between the eZ80F91 Development Board and the CompactFlash Expansion Board.

J1

GND
GND FROM PG 1 OF 3
1
TO PG 2 OF 3 -CD1
26
D3 J8-46
2
27
3
D4 J8-47
28
4 J8-48 A14
29 D5 A13
5 J8-49 A12
30 D6 A11
6
D7 J8-50
31
7 A12 J8-17 PB4
A13 -CE1/-CE 1/ -CS 0 PB3
J8-18 -CE2/-CE2/-CS1
32
PB2
A10 J8-15
8
FROM PG 2 OF 3 -VS1 33 PB1
-O E/ -O E/-A TA _S EL FROM PG 2 OF 3
9
FROM PG 2 OF 3 34 VDD
-IORD VDD GND
A09 J8-14
10
FROM PG 2 OF 3 35 GND
-IOWR
A08 J8-13
11
FROM PG 2 OF 3 -WE
36
A07 J8-10
12
J6-52 PB1 37
RDY-BSY/IREQ/INT RQ VDD
VDD FROM PG 1 OF 3
13
VDD 38
FROM PG 1 OF 3 VDD
A06 J8-9
14 VDD
A14 39
J8-19 -CSEL
A05 J8-8
15
40 VDD
FROM PG 2 OF 3 -VS2
A04 J8-7
16
J6-46 PB4 41
RESET /RESET /-RESET
A03 J8-6
17 C13 C14 C15
J6-13 -WAIT /-WAIT /IORDY
42
A02 J8-5
18 10uF 0.1uF 0.1uF
-INPACK 43
GND
A01 J8-4
19
J8-16 A11 44
-REG
A00 J8-3
20
J6-50 PB2 45
BVD2/-SPKR/-DASP
D0 J8-43
21
J6-48 PB3 46
BVD1/-ST SCHG/-PDIAG 22 J8-44
47 D1
23
D2 J8-45
48
24
49 WP/-IOIS16/-IOIS16
25
-CD2 TO PG 2 OF 3
FROM PG 1 OF 3 GND 50
GND

Compact Flash Connec tor

Title
CompactFlash Interface for eZ80Acclaim! MCU
Size Document Number: AN0154 Rev
A
Date: THURSDAY JULY 24, 2003 Sheet 3 OF 3

Figure 4. Schematic for Connections between Development Board and Expansion Board

AN015401-1103 Appendix C—Schematic Diagrams


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

16

Figure 5 is the schematic diagram for the Interface Logic on the CompactFlash Expansion Board.

J8

VDD 1 2 GND J6
A0 0 3 4 A0 1 J1-19 VDD 1 2
J1-20
A0 2 5 6 A0 3 J1-17 3 4

Connects to eZ80 eval board 60 pin header (J8)


J1-18
A0 4 7 8 A0 5 J1-15 VDD 5 6

Connects to eZ80 eval board 60 pin header (J6)


J1-16
J1-14 A0 6 9 10 A0 7 J1-12 GND VDD GND 7 8
GND 11 12 GND GND 9 10
J1-11 A0 8 13 14 A0 9 J1-10 MWAIT 11 12
J1-08 A1 0 15 16 A1 1 J1-44 - WAIT/- WAIT/IORDY 13 14 GND
J1-07 A1 2 17 18 A1 3 J1-32 J1-42 15 16
J1-39 A1 4 19 20 GND 17 18
GND 21 22 GND 19 20 GND
23 24 21 22
25 26 23 24
27 28 25 26
29 30 27 28
VDD 31 32 VDD 29 30
PG 2 of 3 - RD 33 34 - WR PG 2 of 3 31 32
35 36 33 34
37 38 GND 35 36
39 40 37 38 GND
J1-21
GND 41 42 GND 39 40 PB7
PG 2 of 3
D0 43 44 D1 J1-22 41 42 PB6
J1-23 D2 45 46 D3 J1-2 43 44 PB5 PG 2 of 3
J1-3 D4 47 48 D5 J1-4 45 46 PB4 PG 2 of 3
J1-5 D6 49 50 D7 J1-6 47 48 PB3 J1-41
GND 51 52 GND 49 50 PB2 J1-46
53 54 51 52 PB1 J1-45
55 56 - CSX PG 2 of 3 53 54 PB0 J1-37
GND GND PG 2 of 3
57 58 GND 55 56 GND
VDD 59 60 GND GND 57 58 GND
59 60
Header 30x2 HEADER 30X2

VDD VDD

VDD
VDD

C11 C7 C8 C12 C9 C10


10uF 0.1uF 0.1uF
10uF 0.1uF 0.1uF
GND
GND

Title
COMPACT FLASH INTERFACE FOR eZ80Acclaim! MCUs
Size Doc ument Numbe r: AN0154 Rev
A
Date:Thursday July 24, ,2003 Sheet: 1 of 3

Figure 5. Schematic for Interface Logic on the CompactFlash Expansion Board

AN015401-1103 Appendix C—Schematic Diagrams


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

17

Figure 6 is the schematic diagram for the CompactFlash Connector.

CF Spec requirements
PB7 = 1 is for Memory m ode.
Interface Logic PB7 = 0 is for IO mode.
VDD
VDD VCC 74LVC139/SO
GND VDD
GND J8-34 - WR 1 7
-WR EN Y3 6
THE I C FOOTPRI NT CONNEC TS J8-56 - CSX 3 Y2 5 - WE J1-36
-CSX PB7 2 A1 Y1 4 - IOWR -WE
R1 R2 R3 R4 R5 R6 R7 R8 TO VC C AND NOT VDD. J6-40 PB7 A0 Y0 -IOWR J1-35

U4A
10K
10K
10K
10K
10K
10K
10K
10K
74LVC139/SO

J8-33 -RD
- RD 15 9
EN Y3 10
PB3 J6-48 J8-56 - CSX 13 Y2 11 - MEM_MODE
BVD1/-STSCHG/-PDIAG J6-40 PB7 14 A1 Y1 12 - IOR D J1-34
PB2 A0 Y0 -IORD
BVD2/-SPKR/-DASP J6-50
J1-33 U4B SOJ.0 50/16/WB. 300/L.425
-VS1
-VS2 J1-40
U2A
PB1 J6-52 74LVC08/SO
RDY-BSY/IREQ/INTRQ
J1-43 - MEM_MODE 1
-INPACK 3
MWAIT PB6 2 -OE/-OE/-ATA_SEL
-WAIT/-WAIT /IORDY J6-13 J6-42 PB6
WP/-IOIS16/-IOIS16 J1-24 VDD J1-9

Indicators/ Test Points


R13 R14
U3A 10K 10K
VDD 74LVC32/SO
1 - CD1
-CD1 J1-26
PB0 3
PB0 2 - CD2 J1-25
-CD2
J6-54
R9 R10 R11 R12 VDD VDD VDD
470E 470E 470E 470E

C1 C2 C3 C4 C5 C6
0.1uF 0.1uF 0.1uF 0.1uF 0.1uF 0.1uF
LED LED LED LED
D1 D2 D3 D4
Success Power
PB5
J6-44
PB1 Title
PB1
COMPACT FLASH INTERFACE FOR eZ80Acclaim! MCUs
Activity - Memory modeJ6-52
PB0 Size Doc ume ntN umbe r: AN0154 Rev
A
Card Present J6-54
Date : Thursday July 24, 2003 Sh eet: 2 of 3

Figure 6. Schematic for CompactFlash Connector

AN015401-1103 Appendix C—Schematic Diagrams


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

18

Appendix D—Source Code


This appendix provides a listing of the source code associated with the Compact-
Flash Interface application described in the document. The source code file,
AN0154-SC01.zip is available along with this Application Note, on the ZiLOG
website.

C Files
The following C files are listed in this section:
• CF-interface.c
• Z_FNC_CF.c
• Z_API_CF.c
• Z_CF_SUPPORT.c
• UserIf.c
• utility.c
/*
*********************************************************
* File : CF-interface.c
* Description : Contains main() function.
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.
***********************************************************
*/

include <ez80F91.h>
#include <stdio.h>
#include <sio.h>
#include "UserIF.h"
#include "Z_API_CF.h"

AN015401-1103 Appendix D—Source Code


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

19

void init_F91(void); // Initializes CSx registers


// and Port B
void init_UserIF(void); // Initializes the UART and
// UserIF related portion
// This can be removed if
// HyperTerminal is not used
void init_parameters(void); // Initializes the data
// structures and global
// variables

extern char current_mode;

main()
{
char command, result;

init_F91(); // Initializes the CSx registers and Port B


init_parameters(); // Initializes the data structures and
// global variables
init_UserIF(); // Initializes the UART
// and UserIF related portion

welcome();
display_mode(current_mode); // Displays current mode of CF
// operation
while(1)
{
display_menu(); // Displays all the options
// or commands supported
display_prompt(); // Prompts user to enter
// a command

command = getch(); // Wait for User input


// and store the same
putch(command); // echo

switch (command)
{
case 'm' : fn_mode_select(); // Function Mode selection
break;
case 'i' : fn_identify_drive(); // Function Identify Drive
break;
case 's' : fn_

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

20

(); // Function Set Features


break;
case 'r' : fn_read_sectors(); // Function Read Sector
break;
case 'w' : fn_write_sectors(); // Function Write Sector
break;
case 'e' : fn_erase_sectors(); // Function Erase Sector
break;
default : printf("\n Command not known.\n Please enter
from m,i,s,r,w,e\n");
break;
}
}
}
/*********************************************************
***************** end of file ****************************
*********************************************************/

/*
*********************************************************
* File : Z_FNC_CF.c
* Description :
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.
***********************************************************
*/

#include <stdio.h>
#include "Z_API_CF.h"
#include "UserIF.h"
#include "utility.h"

// Referring to the assembly code

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

21

// Defining data buffers

extern char rd_buffer[]; // From RD_WR_BUF_ADDR to +511


extern char wr_buffer[]; // From +512 to +1023
extern char cmd_tuple[]; // From +1023 to +1031
extern char sta_tuple[]; // From +1032 to +1039

extern char current_mode; // Global mode code

// Move such definitions to the .h files.

extern int blkcopy(char *, char *, int);


extern char attr_mem, current_mode;

/* ********************************
** Main Functions are listed here
*********************************** */

void fn_mode_select(void)
{
char mode, result;

display_mode(current_mode); // First display the curent mode


display_mode_select(); // Next, offer different modes
// for selection
display_prompt(); // Prompt the user

mode = getch(); // Get user selection

//current_mode = load_CF_mode(mode); // This is the API.It can


// be used sans the display
result = load_CF_mode(mode); // This is the API.It can
// be used sans the display

if (result == SUCCESS)
{
display_mode(current_mode); // Reflect the new
// current_mode
}
else
{
proc_result(result); // Find and display
// appropriate Error
}

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

22

// *********************************************************
void fn_identify_drive(void)
{
char result;

result = identify_drive();

if (result == SUCCESS)
{

// -------------------------------------------------------------
// Parse the read Buffer for useful information
// Note: Only some information is extracted as an illustration
// --------------------------------------------------------------
s_temp = POINTER_FOR_SHORT;

d_cylinders = *(s_temp + 1); // This is taking just


// one byte
d_heads = *(s_temp + 3);
d_sect_per_trk = *(s_temp + 6);

d_sect_per_card_1 = *(s_temp + 7); // MSW of a long word


d_sect_per_card_1 &= 0x0000FFFF;
d_sect_per_card_2 = *(s_temp + 8); // LSW of a long word
d_sect_per_card_2 &= 0x0000FFFF;
d_sect_per_card = ((d_sect_per_card_1 << 16)|(d_sect_per_card_2));

c_cylinders = *(s_temp + 54);


c_heads = *(s_temp + 55);
c_sect_per_trk = *(s_temp + 56);

c_capacity_1 = *(s_temp + 57); // MSW of a double


// word variable
c_capacity_1 &= 0x0000FFFF;
c_capacity_2 = *(s_temp + 58); // LSW of a double
// word variable
c_capacity_2 &= 0x0000FFFF;
c_capacity = ((c_capacity_1 << 16) | (c_capacity_2));

// -----------------------------------
// Display the information extracted

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

23

printf("\n ------------------------------------------- \n");

printf("\n\r Default number of cylinders = %d \t", d_cylinders);


printf("\n\r Default number of heads = %d \t", d_heads);
printf("\n\r Default sectors per Track = %d \t", d_sect_per_trk);
printf("\n\r Default sectors per card = %d \t", d_sect_per_card);

printf("\n\r Current number of cylinders = %d \t", c_cylinders);


printf("\n\r Current number of heads = %d \t", c_heads);
printf("\n\r Current sectors per Track = %d \t", c_sect_per_trk);
printf("\n\r Current capacity in sectors = %d \t", c_capacity);

printf("\n ------------------------------------------- \n");


}
else
{
proc_result(result); // Find and display
// appropriate Error
}
}

// *********************************************************

void fn_set_features(void)
{
// -------------
// Settings required are -
// 8-bit data transfers: Enable / Disable
// Power Level 1 commands: Enable / Disable
// POR defaults with soft reset: Enable / Disable
// --------------
// Since most of the features are default and can NOT be altered
// for the present hardware, we will skip this API for time being.
//
char result;
result = set_features();

if (result == SUCCESS)
{
printf("\n *** 8-bit data, Drive# = 0. \n");
}
else
{

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

24

proc_result(result); // Find and display appropriate error


}
}

// *********************************************************
void fn_read_sectors(void)
{

char result;
int sector, head, track;

// Get the starting sector


do
{
printf("\n\r Please enter the starting sector (0x01-0x20):\t");
sector = ScanHex(2); // Use HyperTerminal Echo in
// place of printing
} while (sector < 0x01 || sector > 0x20);

// Get the Head information


do
{
printf("\n\r Please enter the Head Number (0x0-0x3):\t");
head = ScanHex(1); // Use HyperTerminal Echo in
// place of printing
} while (head > 0x03);

// Get the Track


do
{
printf("\n\r Please enter the Track number
(0x000-0x3d2):\t");
track = ScanHex(3); // Use HyperTerminal Echo in
// place of printing
} while (track > 0x3d2);

// Call API with this info.

result = read_sectors(sector, head, track); // API Call

if (result == SUCCESS)
{
display_read_buffer();
}

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

25

else
{
proc_result(result); // Find and display
// appropriate Error
}
}

// *********************************************************
void fn_write_sectors(void)
{
volatile char result;
int sector, head, track;

char test_array[] = "ZiLOG India is a software design center with the


charter to fulfill the software needs of ZiLOG, Inc and those of it's
customers by enabling creative, comprehensive solutions using ZiLOG
semiconductor family offerings for new and traditional markets. ZiLOG
India provides state of art embedded software solutions that complement
ZiLOG semiconductor solutions with the specific goals of improving
productivity, time-to-market, affordability, quality and other such
major concerns of our customers worldwide.- ZiLOG";

result = blkcopy(wr_buffer, test_array, 512);

// Prepare to call API.


// Get the starting sector; Check for Error
do
{
printf("\n\r Please enter the starting sector (0x01-0x20):\t");
sector = ScanHex(2); // Use HyperTerminal Echo
// in place of printing
} while (sector < 0x01 || sector > 0x20);

// Get the Head information; Check for Error


do
{
printf("\n\r Please enter the Head Number (0x0-0x3):\t");
head = ScanHex(1); // Use HyperTerminal Echo
// in place of printing
} while (head > 0x03);

// Get the Track information; Check for Error


do
{

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

26

printf("\n\r Please enter the Track number (0x000-0x3d2):\t");


track = ScanHex(3); // Use HyperTerminal Echo
// in place of printing
} while (track > 0x3d2);

// With the information obtained call the API


result = write_sectors(sector, head, track); // API Call

if (result == SUCCESS)
{
display_write_buffer();
}
else
{
// printf("\n FNC result \t %x \t %d \n",result, result);
proc_result(result); // Find and display appropriate Error
}
}

// *********************************************************
void fn_erase_sectors(void)
{
volatile char result;
int sector, head, track;

// Prepare to call API.


// Get the starting sector; Check for Error
do
{
printf("\n\r Please enter the starting sector (0x01-0x20):\t");
sector = ScanHex(2); // Use HyperTerminal Echo
// in place of printing
} while (sector < 0x01 || sector > 0x20);

// Get the Head information; Check for Error


do
{
printf("\n\r Please enter the Head Number (0x0-0x3):\t");
head = ScanHex(1); // Use HyperTerminal Echo
// in place of printing
} while (head > 0x03);

// Get the Track information; Check for Error


do

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

27

{
printf("\n\r Please enter the Track number (0x000-0x3d2):\t");
track = ScanHex(3); // Use HyperTerminal Echo
// in place of printing
} while (track > 0x3d2);

// With the information obtained call the API


result = erase_sectors(sector, head, track); // API Call

if (result == SUCCESS)
{
printf("\n Sector erase complete \n");
}
else
{
proc_result(result); // Find and display
// appropriate Error
}
}

/*********************************************************
***************** end of file ***************************
*********************************************************/

/*
*********************************************************
* File : Z_API_CF.c
* Description :
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.
***********************************************************
*/

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

28

#include <stdio.h>
#include <ez80F91.h>
#include "Z_API_CF.h"
#include "UserIF.h"

// ---------------------------------------------------
// Refer to the assembly code in data_structure_def.s
// ---------------------------------------------------

extern char rd_buffer[]; // From RD_WR_BUF_ADDR to +511


extern char wr_buffer[]; // From +512 to +1023
extern char cmd_tuple[]; // From +1023 to +1031
extern char sta_tuple[]; // From +1032 to +1039

char *cmd_dest; // cmd_dest is a pointer to a character.


char *attr_mem;
extern char current_mode;

/* ********************* **
** APIs are listed here.
************************* */
char load_CF_mode(char mode)
{
//
// This API does not interact with the CF. It loads tuple pointers with
// appropriate addresses.
// Returns 1 for success, or error_code otherwise. Updates the
// current_mode global variable.
//

char result;
int i;

result = check_card(); // Check presence


// of the card
if (result == 1) return (NO_CARD); // Card not found - Send
// Error code

attr_mem = ATTRIBUTE_MEMORY;

switch(mode)
{

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

29

case 'm' : // Memory mode


PB_DR = 0xE0; // Set ~OE to 1 through PB6; PB7
// = 1 for MUX control
cmd_dest = MEMORY_MODE_REG0;
// Mode dependent, global, presently Memory mode

*(attr_mem) = 0x80; // Soft Reset started


*(attr_mem) = 0x00; // Soft Reset finished

// Wait for busy to start and clear


while ((PB_DR & 0x02) == SET); // Wait till CF
// starts the RESET
while ((PB_DR & 0x02) == RESET); // Wait till CF
// completes RESET
for (i = 1; i > 20000; i++);

*(attr_mem + 0x00) = 0x00;

// Load Memory mode if required from IO mode


current_mode = *(attr_mem); // read the config
// register -OE reqd
current_mode &= 0x3F; // Get the specific in

PB_DR =0xC0; // PB5 for test only


break;

case 'c': // Contiguous IO mode


// First switch mode from memory to I/O
// Then load pointers for IO mode
PB_DR = 0xE0; // ~OE = 1, RD/WR = OE/WE
cmd_dest = MEMORY_MODE_REG0; // Mode dependent, global

*(attr_mem) = 0x80; // Soft Reset started


*(attr_mem) = 0x00; // Soft Reset finished

// Wait for busy to start and clear


while ((PB_DR & 0x02) == SET); // Wait till CF starts
// the RESET
while ((PB_DR & 0x02) == RESET); // Wait till the CF
// completes RESET
for (i = 1; i > 20000; i++);

*(attr_mem + 0x00) = 0x01; // Load Contiguous IO mode


// to Attribute Memory

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

30

current_mode = *(attr_mem); // read the config register


// -OE reqd
current_mode &= 0x3F; // Get the specific in
PB_DR = 0x40; // Switch Mux output to
// ~IORD, ~IOWR
cmd_dest = CON_IO_MODE_REG0; // Loading base pointer for
// the IO mode
break;

case 'p': // Primary IO mode


// First switch mode from memory to I/O
// Then load pointers for IO mode
PB_DR = 0xE0; // ~OE = 1, RD/WR = OE/WE
cmd_dest = MEMORY_MODE_REG0; // Mode dependent, global

*(attr_mem) = 0x80; // Start RESET


*(attr_mem) = 0x00; // End RESET
// Wait for busy to start and clear
while ((PB_DR & 0x02) == SET); // Wait till CF starts
// the RESET
while ((PB_DR & 0x02) == RESET); // Wait till the CF
// completes RESET
for (i = 1; i > 20000; i++);

*(attr_mem) = 0x02; // Load Primary IO mode to


// Attribute Memory
current_mode = *(attr_mem); // read the config register
// -OE reqd
current_mode &= 0x3F; // Get the specific in
PB_DR = 0x40; // Switch Mux output to ~IORD, ~IOWR
cmd_dest = PRI_IO_MODE_REG0; // Loading base pointer for
// the IO mode
break;

case 's': // Secondary IO mode


// First switch mode from memory to I/O
// Then load pointers for IO mode
PB_DR = 0xE0; // ~OE = 1, RD/WR = OE/WE
cmd_dest = MEMORY_MODE_REG0; // Mode dependent, global

*(attr_mem) = 0x80; // Start RESET


*(attr_mem) = 0x00; // End RESET
// Wait for busy to start and clear
while ((PB_DR & 0x02) == SET); // Wait till CF starts

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

31

// the RESET
while ((PB_DR & 0x02) == RESET); // Wait till the CF
// completes RESET
for (i = 1; i > 20000; i++);
*(attr_mem) = 0x03; // Load Secondary IO mode
// to Attribute Memory
current_mode = *(attr_mem); // read the config register
// -OE reqd
current_mode &= 0x3F; // Get the specific in
PB_DR = 0x40; // Switch Mux output to ~IORD, ~IOWR
cmd_dest = SEC_IO_MODE_REG0; // Loading base pointer for
// the IO mode
break;

default:printf("\n Mode not known.\n Please enter from m,c,p,s\n");


break;
}
for (i = 1; i > 20000; i++);
result = *(cmd_dest + 1);
return(SUCCESS); // Inform upper layer of completion/failure
}

// *********************************************************

char identify_drive(void)
{

//
// This command does not take any parameters.
// After execution by the CF card, the CF buffer is read.
// Later, the information in the buffer is analyzed and results
// are displayed on HyperTerminal through a Support Function.
//

char result, error;


int i;

unsigned short d_cylinders, d_heads, d_sect_per_trk;


unsigned long d_sect_per_card;
unsigned short c_cylinders, c_heads, c_sect_per_trk;
unsigned long c_capacity;

long d_sect_per_card_1, d_sect_per_card_2, d_sect_per_card_3,


d_sect_per_card_4;

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

32

long c_capacity_1, c_capacity_2, c_capacity_3, c_capacity_4;

short *s_temp; // POINTER_FOR_SHORT; short is 2 bytes.

// Check presence of the card.


result = check_card(); // Check presence of the card
if (result == 1) return (NO_CARD); // Card not found - Send
// Error code

*(cmd_dest + 6) = 0x00; // Drive is zero


*(cmd_dest + 7) = 0xEC; // Command code 0xEC is Identify
// Drive

wait(cmd_dest); // wait for DRQ and BUSY, abort


// if any Error
for (i = 0; i < BUF_SIZE; i++)
{
*(rd_buffer+i) = *(cmd_dest); // Read from same address,
// increment destination
}

error = *(cmd_dest + 1); // Debug only


return(error); // Inform upper layer of
// completion/failure

/*
// -------------------------------------------------------------
// The Buffer is read from CF into the SRAM
// Now we need to parse it for useful information.
// Note: Only some information is extracted as an illustration.
// --------------------------------------------------------------

s_temp = POINTER_FOR_SHORT;

d_cylinders = *(s_temp + 1); // This is taking just one


// byte
d_heads = *(s_temp + 3);
d_sect_per_trk = *(s_temp + 6);

d_sect_per_card_1 = *(s_temp + 7); // MSW of a long word


d_sect_per_card_1 & = 0x0000FFFF;
d_sect_per_card_2 = *(s_temp + 8); // LSW of a long word
d_sect_per_card_2 & = 0x0000FFFF;

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

33

d_sect_per_card = ((d_sect_per_card_1 << 16)|(d_sect_per_card_2));

c_cylinders = *(s_temp + 54);


c_heads = *(s_temp + 55);
c_sect_per_trk = *(s_temp + 56);
c_capacity_1 = *(s_temp + 57); // MSW of a double word variable
c_capacity_1 & = 0x0000FFFF;
c_capacity_2 = *(s_temp + 58); // LSW of a double word variable
c_capacity_2 & = 0x0000FFFF;
c_capacity = ((c_capacity_1 << 16) | (c_capacity_2));

// -----------------------------------
// Display the information extracted.

printf("\n -------------------------------------------- \n");

printf("\n\r Default number of cylinders = %d \t", d_cylinders);


printf("\n\r Default number of heads = %d \t", d_heads);
printf("\n\r Default sectors per Track = %d \t", d_sect_per_trk);
printf("\n\r Default sectors per card = %d \t", d_sect_per_card);

printf("\n\r Current number of cylinders = %d \t", c_cylinders);


printf("\n\r Current number of heads = %d \t", c_heads);
printf("\n\r Current sectors per Track = %d \t", c_sect_per_trk);
printf("\n\r Current capacity in sectors = %d \t", c_capacity);

printf("\n -------------------------------------------- \n");

return(error) ; // Indicate successful completion


*/
}

// *********************************************************
char set_features(void)
{

char result, error;


int i;

result = check_card(); // Check presence of the card


if (result == 1) return (NO_CARD); // Card not found - Send
// Error code

// Card found, Load command tuple

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

34

*(cmd_dest + 1) = 0x69; // Enable 8-bit data transfer


// FEATURES
*(cmd_dest + 6) = 0x00; // Drive is zero
*(cmd_dest + 7) = 0xEF; // Command code 0xEF is set
// features

// Wait for busy to start and clear


while ((PB_DR & 0x02) == SET); // Wait till CF sets BUSY to
// avoid false trigger
while ((PB_DR & 0x02) == RESET); // Wait till the BUSY is
// RESET, CF is ready now.

for (i = 1; i < 20000; i++);

error = *(cmd_dest + 1);

//printf("\n API error %x \t %d \n", error, error); // Debug only

return(error); // Inform upper layer of


// completion/ failure
}
// *********************************************************

char read_sectors(int sector, int head, int track)


{
int cylinder_low, cylinder_high;
volatile char result, error;
int i;

result = check_card(); // Check presence of the card


if (result == 1) return (NO_CARD); // Card not found - Send
// Error code

// Prepare command data


cylinder_low = track & 0x00F; // Get the lower byte from Tracks
cylinder_high = track >> 8; // Get the higher byte from the
// Tracks
// Load command data to command tuple
*(cmd_dest + 2) = 0x01; // Most of the CF cards support
// one sector per request
*(cmd_dest + 3) = sector; // Starting sector as received
// from the API call
*(cmd_dest + 4) = cylinder_low;
*(cmd_dest + 5) = cylinder_high;

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

35

*(cmd_dest + 6) = (0xA0 | head);// No LBA, Drive 0, Head as


// received from API call
*(cmd_dest + 7) = 0x20; // Command code 0x20 or 0x21 is
// Read Sectors

wait(cmd_dest); // wait for DRQ and BUSY, abort if in Error


for (i = 0; i < BUF_SIZE; i++)
{
*(rd_buffer+i) = *(cmd_dest); // Read from same address,
// increment destination
}

error = *(cmd_dest + 1); // Debug only


return(error); // Inform upper layer of completion/ failure
}

// *********************************************************

char write_sectors(int sector, int head, int track)


{
int cylinder_low, cylinder_high;
volatile char result, error;
int i;

result = check_card(); // Check presence of the card.


if (result == 1) return (NO_CARD); // Card not found - Send
// Error code

// Prepare command data


cylinder_low = track & 0x00F; // Get the lower byte from Tracks
cylinder_high = track >> 8; // Get the higher byte from the
// Tracks
// Load command data to command tuple
*(cmd_dest + 2) = 0x01; // Number of sectors is 1
*(cmd_dest + 3) = sector; // Starting sector
*(cmd_dest + 4) = cylinder_low; // Cylinder Low
*(cmd_dest + 5) = cylinder_high; // Cylinder High
*(cmd_dest + 6) = (0xA0 | head); // No LBA, Drive 0, Head as
// received from API call
*(cmd_dest + 7) = 0x30; // Command code 0x30 or 0x31 is
// Write Sectors

//error = *(cmd_dest + 1);

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

36

//error &= 0xFF;


//printf("\n API 1st error \t %x \t %d \n", error, error);

wait(cmd_dest); // wait for DRQ and BUSY, abort


// if in Error
for (i = 0; i < BUF_SIZE; i++)
{ // As CF controller implements a
// FIFO, Data is written to the
*(cmd_dest) = *(wr_buffer + i); // same address and source
// is incremented
}

//Wait for busy to start and clear


while ((PB_DR & 0x02) == SET); // Wait till CF sets BUSY to
// avoid false trigger
while ((PB_DR & 0x02) == RESET); // Wait till the BUSY is RESET,
// CF is ready now

for (i = 1; i < 20000; i++);


error = *(cmd_dest + 1); // Read CF error register
error &= 0xFF;
//printf("\n API 2nd error \t %x \t %d \n", error, error);
return(error); // Inform upper layer of completion/ failure
}

// *********************************************************

char erase_sectors(int sector, int head, int track)


{
// Same as write sectors fills the sector with 0xFF

int cylinder_low, cylinder_high;


volatile char result, error;
int i;

result = check_card(); // Check presence of the card


if (result == 1) return (NO_CARD); // Card not found - Send Error
// code

// Prepare command data


cylinder_low = track & 0x00F; // Get the lower byte from
// Tracks
cylinder_high = track >> 8; // Get the higher byte from
// the Tracks

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

37

// Load command data to command tuple


*(cmd_dest + 2) = 0x01; // Number of sectors is 1
*(cmd_dest + 3) = sector; // Starting sector
*(cmd_dest + 4) = cylinder_low; // Cylinder Low
*(cmd_dest + 5) = cylinder_high; // Cylinder High
*(cmd_dest + 6) = (0xA0 | head); // No LBA, Drive 0, Head as
// received from API call
*(cmd_dest + 7) = 0x30; // Command code 0x30 or 0x31
// is Write Sectors

error = *(cmd_dest + 1);


//error &= 0xFF;
//printf("\n API 1st error \t %x \t %d \n", error, error);

wait(cmd_dest); // wait for DRQ and BUSY, abort if in Error


for (i = 0; i < BUF_SIZE; i++)
{
*(cmd_dest) = 0xFF; // Write to the same address
// constant data of 0xFF
}

//Wait for busy to start and clear


while ((PB_DR & 0x02) == SET); // Wait till CF sets BUSY to
// avoid false trigger
while ((PB_DR & 0x02) == RESET); // Wait till the BUSY is RESET,
// CF is ready now
for (i = 1; i < 20000; i++);
error = *(cmd_dest + 1);
//error &= 0xFF;
//printf("\n API 2nd error \t %x \t %d \n", error, error);
return(error); // Inform upper layer of
// completion/ failure

}
/*********************************************************
***************** end of file ***************************
*********************************************************/

/*
*********************************************************
* File : Z_CF_SUPPORT.c
* Description :
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

38

*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.
***********************************************************
*/

#include <stdio.h>
#include "Z_API_CF.h"
#include "UserIF.h"
#include "utility.h"
#include <ez80F91.h>

// Referring to the assembly code


extern char rd_buffer[]; // From RD_WR_BUF_ADDR to +511
extern char wr_buffer[]; // From +512 to +1023
extern char cmd_tuple[]; // From +1023 to +1031
extern char sta_tuple[]; // From +1032 to +1039
extern char *cmd_dest;

char current_mode;

void init_F91(void)
{
// Initialize Port B for CF application.
PB_ALT1 = 0x00; // RESET default
PB_ALT2 = 0x00; // RESET default
PB_DDR = 0x0F; // Upper nibble as output, lower nibble as input
PB_DR = 0xE0; // This is for CF Memory mode. 0b1110----
}

void init_parameters(void)
{
// Initialize the parameters/flags required for this appnote.
current_mode = 0xFF; // current_mode is global. Initialize
// to memory mode (0)
cmd_dest = MEMORY_MODE_REG0; // Mode dependent, global

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

39

char check_card(void)
{

char card_detect;

card_detect = (PB_DR & 0x01); // Check PB0 for "~CD1 OR ~CD2"


// If card is present
// then the PB0 is ZERO.
return (card_detect); // 0 = present; 1 = absent
}

void wait(char *cmd_dest)


{
char wait, wait_busy, wait_drq, error;

do
{
wait = *(cmd_dest + 0x07); // Read status register
error = wait & 0x01;
if (error == 1) return; // Error occurred, abort wait
wait_busy = wait & 0x80; // Wait for BUSY to RESET
} while (wait_busy == 0x80);

do
{
wait = *(cmd_dest + 0x07); // Read status register
error = wait & 0x01;
if (error == 1) return; // Error occurred, abort wait.
wait_drq = wait & 0x08; // Wait for DRQ to SET
} while (wait_drq == 0x00);

void proc_result(char result)


{
volatile char error;

if (result == NO_CARD)
printf("\n ! Card not found \n");

error = result & 0x80;

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

40

if (error == 0x80) printf("\n Bad block detected. ");

error = result & 0x40;


if (error == 0x40)
printf("\n Uncorrectable Error Encountered.");

error = result & 0x10;


if (error == 0x10)
printf("\n Wrong Sector ID or Sector not found.");

error = result & 0x01;


if (error == 0x01)
printf("\n General Error.");

error = result & 0x04;


if (error == 0x04)
printf("\n Command Aborted \n");

// printf("Error Code:\t %x \n", result);


// printf("Error Code:\t %d \n", result);
// putchar(result);

}
/*********************************************************
***************** end of file ***************************
*********************************************************/

/*
*********************************************************
* File : UserIf.c
* Description :
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

41

***********************************************************
*/

#include <stdio.h>
#include <ez80F91.h>
#include "Z_API_CF.h"
#include "UserIF.h"
#include "utility.h"
#include "SIO.h"

// -----------------------------------
char mode_select(void);
void display_error(char);
void welcome (void);
// -----------------------------------
extern char rd_buffer[]; // From RD_WR_BUF_ADDR to +511
extern char wr_buffer[]; // From +512 to +1023
extern char cmd_tuple[]; // From +1023 to +1031
extern char sta_tuple[]; // From +1032 to +1039
// -----------------------------------

void welcome(void)
{
printf("\n \n \n-----------------------\n");
printf("Welcome to eZ80 Acclaim!\n");
printf("Compact Flash Interface\n");
printf("-----------------------\n");
}

void display_menu(void)
{
printf("%s\n", menu0); // Mode Select
printf("%s\n", menu1); // Identify Drive
printf("%s\n", menu2); // Set Features
printf("%s\n", menu3); // Read Sector
printf("%s\n", menu4); // Write Sector
printf("%s\n", menu5); // Erase sector
//printf("%s\n", menu6);
//printf("%s\n", menu7);
}

void display_prompt(void)
{
printf(prompt);

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

42

void display_mode_select(void)
{
printf("%s\n", mode0); // Memory mode
printf("%s\n", mode1); // Contiguous I/O mode
printf("%s\n", mode2); // Primary I/O
printf("%s\n", mode3); // Secondary I/O
//printf("%s\n", mode4); // True IDE
}

void display_read_buffer(void)
{
int j;
printf("\n\n ------- Read buffer ----------\n");
for (j = 0; j < BUF_SIZE; j++)
{
putchar(*(rd_buffer+j));
}
printf("\n ------- Read buffer ----------\n\n");

void display_write_buffer(void)
{
int j;

printf("\n\n ------- Write buffer ----------\n");


for (j = 0; j < BUF_SIZE; j++)
{
putchar(*(wr_buffer+j));
}
printf("\n ------- Write buffer ----------\n\n");

void display_mode(char mode)


{
switch (mode)
{
case 0: printf("\n Current mode is: \t Memory mode \n");
break;
case 1: printf("\n Current mode is: \t Contiguous IO mode \n");
break;

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

43

case 2: printf("\n Current mode is: \t Primary IO mode \n");


break;
case 3: printf("\n Current mode is: \t Secondary IO mode \n");
break;
case 4: printf("\n Current mode is: \t True IDE mode \n");
break;
default:printf("\n Current mode is: Default - Memory");
break;
}

}
/*********************************************************
***************** end of file ***************************
*********************************************************/

/*
*********************************************************
* File : utility.c
* Description :
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.
***********************************************************
*/

#include "SIO.h"
#include <ez80F91.h>

int ascii_to_hex(int chr)


{
if((chr >= '0') && (chr <= '9'))
return chr - '0';
else if((chr >= 'A') && (chr <= 'F'))
return chr - 'A' + 10;

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

44

else if((chr >= 'a') && (chr <= 'f'))


return chr - 'a' + 10;
else
return -1;
}

void printhex(unsigned int num)


{
unsigned char i=5;
unsigned char str[6];
str[5] = '\0';
do
{
int temp = num & 0x00000F;
if(temp < 10)
temp += '0';
else
temp += 'A'-10;
str[--i] = temp;
num >>= 4;
}
while (num);
while (i < 6)
putch(str[i++]);
}

unsigned int ScanHex (unsigned char num)


{
unsigned char ch;
unsigned int addr;
int temp1, temp2, temp3, temp4, temp5;

do
{
ch=getch(); // Get pressed key from keyboard
temp1 = ascii_to_hex(ch);
} while (temp1 < 0); // Ignore invalid keypress
printhex(temp1);
if (num == 1)
{
ch = temp1 & 0x0F;
return (ch);
}
do

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

45

{
ch=getch();
temp2 = ascii_to_hex(ch);
} while (temp2 < 0);
printhex(temp2);
if (num == 2)
{
ch = (temp1 << 4) & 0xF0;
ch = (ch | temp2) & 0xFF; // why & ???
return (ch);
}
do
{
ch=getch();
temp3 = ascii_to_hex(ch);
} while (temp3 < 0);
printhex(temp3);
if (num == 3)
{
addr = 0x0000;
addr = (temp1 << 4) & 0x00F0;
addr = (addr | temp2);
addr = (addr << 4) & 0x0FF0;
addr = (addr | temp3) & 0x0FFF;
return (addr);
}
do
{
ch=getch();
temp4 = ascii_to_hex(ch);
} while (temp4 < 0);
printhex(temp4);
if (num == 4)
{
addr = 0x0000;
addr = (temp1 << 4) & 0x00F0;
addr = (addr | temp2);
addr = (addr << 4) & 0x0FF0;
addr = (addr | temp3);
addr = (addr << 4) & 0xFFF0;
addr = (addr | temp4) & 0xFFFF;
return (addr);
}
do

AN015401-1103 Appendix D—C Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

46

{
ch=getch();
temp5 = ascii_to_hex(ch);
} while (temp5 < 0);
printhex(temp5);
addr = 0x000000;
addr = (temp1 << 4) & 0x0000F0;
addr = (addr | temp2);
addr = (addr << 4) & 0x000FF0;
addr = (addr | temp3);
addr = (addr << 4) & 0x00FFF0;
addr = (addr | temp4) & 0x00FFFF;
addr = (addr << 4) & 0x0FFFF0;
addr = (addr | temp5) & 0x0FFFFF;
return (addr);
}
/*********************************************************
***************** end of file ***************************
*********************************************************/

Assembly File
The following assembly file is listed in this section:
• data_structure_def.s
/*
*********************************************************
* File : data_structure_def.s
* Description :
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.
***********************************************************
*/

AN015401-1103 Appendix D—Assembly File


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

47

; public__exit
; extern_main
;
; .include"ez80F91.inc"
;
RD_WR_BUF_ADDR: .equ %C30000 ; This is the starting address of the
; buffer section. These map to CS1 mapped
; RAM located on the Module board. The RAM
; is 512KBytes and we are reserving
;1040 bytes here

;*********************************************************************
;* Define global arrays for read and write data buffers.
;* Define global arrays for command/status Tuple data
;*********************************************************************

define _buffer_section, SPACE =RAM, ORG = RD_WR_BUF_ADDR


segment _buffer_section
xdef _rd_buffer, _wr_buffer, _cmd_tuple, _sta_tuple

_rd_buffer: ds 512 ; From RD_WR_BUF_ADDR to +511


_wr_buffer: ds 512 ; From +512 to +1023
_cmd_tuple: ds 8 ; From +1023 to +1031
_sta_tuple: ds 8 ; From +1032 to +1039
;
;
;
.assume adl = 1
segment CODE ;, SPACE = ROM

.def _blkcopy
XDEF _blkcopy

;***C Function Prototype:


; int blkcopy( BYTE * p_dest, BYTE * p_source, TRIO Length );
; return OK (1) if successful
;

_blkcopy:
push ix
ld ix, 0
add ix, sp

ld de, (ix+6)

AN015401-1103 Appendix D—Assembly File


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

48

ld hl, (ix+9)
ld bc, (ix+12)

push hl
ld hl, 0
or a , a
adc hl, bc
pop hl
jr z, done_copy

ldir
ld hl,1

done_copy:

ld sp, ix
pop ix
ret
;
/*********************************************************
***************** end of assembly file *******************
*********************************************************/

Header Files
The following header files are listed in this section:
• userif.h
/*
*********************************************************
* File : userif.h
* Description : Function Prototypes
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*

AN015401-1103 Appendix D—Header Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

49

* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.


***********************************************************
*/

void display_prompt(void);
void display_mode(char);
void display_menu(void);
void display_error(char);

// Function prototypes for individual sub-command menu


void display_mode_select(void);

void display_read_buffer(void);
void display_write_buffer(void);

void welcome (void);

/* *************************************
** Define various string constants here
**************************************** */
static const char menu0[] = "\n\r m.\tMode Select";
static const char menu1[] = "\n\r i.\tIdentify Drive";
static const char menu2[] = "\n\r s.\tSet Features";
static const char menu3[] = "\n\r r.\tRead Sector";
static const char menu4[] = "\n\r w.\tWrite Sector";
static const char menu5[] = "\n\r e.\tErase Sector";
// static const char menu6[] = "\n\r 6.\tDisplay Read Buffer";
// static const char menu7[] = "\n\r 7.\tDisplay Write Buffer";

static const char mode0[] = "\n\r m.\tMemory Mode";


static const char mode1[] = "\n\r c.\tContiguous I/O mode";
static const char mode2[] = "\n\r p.\tPrimary I/O mode";
static const char mode3[] = "\n\r s.\tSecondary I/O mode";
// static const char mode4[] = "\n\r t.\tTrue IDE mode";

static const char prompt[] = "\nCF >>\t";

// Error messages

/***************************************************************
******************* End of userif.h file *********************
***************************************************************/

AN015401-1103 Appendix D—Header Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

50

/*
*********************************************************
* File : Z_API_CF.h
* Description : Function Prototypes
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.
***********************************************************
*/

void test_temp(void);
void fn_mode_select(void);
void fn_identify_drive(void);
void fn_set_features(void);
void fn_read_sectors(void);
void fn_write_sectors(void);
void fn_erase_sectors(void);

// API declarations
char load_CF_mode(char);
char identify_drive(void);
char read_sectors(int,int,int);
char write_sectors(int,int,int);
char erase_sectors(int,int,int);
char set_features(void);

// Support function declarations


char load_CF_command(char);
char process_result(char);
char load_CF_command(char);
void init_F91(void);
void command_select(void);
void init_parameters(void);

AN015401-1103 Appendix D—Header Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

51

void proc_result(char);

char check_card(void);
// char check_busy(void);
void wait(char *);

/* ******************************************************
Store starting address of command tuple in various modes
********************************************************* */

// #define ATTRIBUTE_MEMORY (char *)0xA82800


// #define ATTRIBUTE_MEMORY (char *)0xA82A00

#define ATTRIBUTE_MEMORY (char *)0xA82200; // -REG(A-11) is zero

// -------------------------------------------
#define MEMORY_MODE_REG0(char *)0xA82800; // -REG(A-11) is one.
#define CON_IO_MODE_REG0(char *)0xA82000; // -REG(A-11) is zero
#define PRI_IO_MODE_REG0(char *)0xA821F0; // -REG(A-11) is zero
#define SEC_IO_MODE_REG0(char *)0xA82170; // -REG(A-11) is zero

/*
#define CON_IO_MODE_REG0(char *)0xA82800
#define PRI_IO_MODE_REG0(char *)0xA829F0
#define SEC_IO_MODE_REG0(char *)0xA82970
*/
// -------------------------------------------
#define IDE_MODE_REG0 (char *)0xA82800// -REG(A-11) is one. A3-A10 are
'0'

#define POINTER_FOR_SHORT (short *)0xC30000


#define POINTER_FOR_LONG (long *)0xC30000

/* *********************************
* Miscellaneous information storage
********************************* */
#define BUF_SIZE 512

/* ************************************************************
Error codes are defined here.
************************************************************ */

#define UNKNOWN_COMMAND 0xFF


#define UNKNOWN_MODE 0xFF

AN015401-1103 Appendix D—Header Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

52

//#define RESELECT_MODE 0x00


//#define RESELECT_COMMAND 0x00
#define NO_CARD 0xFE
#define SUCCESS 0x00 // Success is equivalent to
// error = 0

/* ************************************
** Command parameters are defined here.
*************************************** */
#define DRIVE_ID 0xAA
#define SET 0x01
#define RESET 0x00

/***************************************************************
******************* End of Z_API_CF.h file *******************
***************************************************************/

/*
*********************************************************
* File : utility.h
* Description : Prototype Definitions
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.
***********************************************************
*/

void clear_screen (void);


unsigned int ScanHex (unsigned char num);
int ascii_to_hex(int chr);
void printhex(unsigned int num);
void myputs(const char* mystring);

/***************************************************************

AN015401-1103 Appendix D—Header Files


Application Note
CompactFlash® Interface for eZ80Acclaim!™ MCUs

53

******************* End of utility.h file *******************


***************************************************************/

/*
*********************************************************
* File : sio.h
* Description : Function Prototypes
*
* Copyright 2003 ZiLOG Inc. ALL RIGHTS RESERVED.
*
* The source code in this file was written by an
* authorized ZiLOG employee or a licensed consultant.
* The source code has been verified to the fullest
* extent possible.
*
* Permission to use this code is granted on a royalty-free
* basis. However users are cautioned to authenticate the
* code contained herein.
*
* ZiLOG DOES NOT GUARANTEE THE VERACITY OF THE SOFTWARE.
***********************************************************
*/
void init_UserIF(void);
char putch(char c);
int kbhit(void);
char getch(void);

/***************************************************************
******************* End of sio.h file ************************
***************************************************************/

AN015401-1103 Appendix D—Header Files


Application Note
CompactFlash Interface for eZ80Acclaim!™ MCUs

54

Appendix E—API Description


This appendix provides a description of the APIs used to interface the eZ80F91
MCU with the CompactFlash interface described in this Application Note.
Table 6 presents a list of CompactFlash Interface APIs for quick reference. Details
are provided in this section—use the hyperlinks below to jump quickly to one of
these APIs.

Table 6. CompactFlash Interface APIs

API Name Description


char load_CF_mode() Selects the CompactFlash mode
char identify_drive() Identifies the CompactFlash card
char read_sectors() Reads specified sector on the CompactFlash card
char write_sectors() Writes to a specified sector on the CompactFlash card
char erase_sectors() Erases specified sector on the CompactFlash card
char set_features() Displays/sets features for the CompactFlash card

In general, all of the above mentioned APIs receive relevant information from cor-
responding calling functions from the host, and load the CompactFlash command
tuple with the received parameters and command words. The APIs handle the
data transfer (when required) between the CompactFlash card and the
eZ80Acclaim! microcontroller. Finally the APIs check the error register and report
the success and failure of the operation to the calling function.
Descriptions for the CompactFlash Interface APIs begin on the next page.

AN015401-0903 Appendix E—API Description


Application Note
CompactFlash Interface for eZ80Acclaim!™ MCUs

55

char load_CF_mode()
char load_CF_mode(char mode)

Description
The load_CF_mode() API initializes the CompactFlash card in a specified mode
of operation. It also modifies the pointers to the command tuple.
The mode parameter takes m, c, p, or s as values to reset the CompactFlash
card to the memory mode, the contiguous I/O mode, the primary I/O mode or the
secondary I/O mode, respectively.

Parameters

char mode The mode to which the CompactFlash is to be reset

Returns

0 On Success
error_codes On Failure

Usage

result = load_CF_mode(mode);

AN015401-0903 Appendix E—API Description


Application Note
CompactFlash Interface for eZ80Acclaim!™ MCUs

56

char identify_drive()
char identify_drive(void)

Description
The identify_drive() API reads the CompactFlash memory structure (num-
ber of heads, sectors, tracks and so on) and the manufacturer’s information from
the CompactFlash Storage Card and copies the information into the read buffer
for the host to use. The host calling function parses the read buffer and displays
the information on the HyperTerminal.

Parameters

void

Returns

0 On Success
error_codes On Failure

Usage
result = identify_drive();

AN015401-0903 Appendix E—API Description


Application Note
CompactFlash Interface for eZ80Acclaim!™ MCUs

57

char read_sectors()
char read_sectors(int sector,int head,int track)

Description
The read_sectors() API receives the track, head, and sector number of the
sector to be read from the host. The API then transfers the data residing in the
specified location from the CompactFlash card to the host's read buffer. On com-
pleting the operation, the API returns a success or a failure.

Parameters

int sector The sector number from where data is to be read


int head The head number from where data is to be read
int track The track number from where data is to be read

Returns

0 On Success
error_code On Failure

Usage
result = read_sectors(sector,head,track);

AN015401-0903 Appendix E—API Description


Application Note
CompactFlash Interface for eZ80Acclaim!™ MCUs

58

char write_sectors()
char write_sectors(int sector,int head,int track)

Description
The write_sectors() API receives the track, head, and sector number of the
sector where the host requires to write the data. The API then transfers the data
from the host’s write buffer to the CompactFlash card. On completing the opera-
tion, the API returns a success or a failure.

Parameters

int sector The sector number where data is to be written on the CompactFlash card
int head The head number where data is to be written on the CompactFlash card
int track The track number where data is to be written on the CompactFlash card

Returns:

0 On Success
error_code On Failure

Usage
result = write_sectors(sector,head,track);

AN015401-0903 Appendix E—API Description


Application Note
CompactFlash Interface for eZ80Acclaim!™ MCUs

59

char erase_sectors()
char erase_sectors(int sector,int head,int track)

Description
The erase_sectors() API is used to erase previously written data in a specified
sector. Functionally, this API is similar to the write_sectors() API, except that
instead of the transferring data from the host buffer to the specified sector, the
erase_sector() API populates the specified sector with 0xFF.

Parameters

int sector The sector number from where data is to be erased


int head The head number from where data is to be erased
int track The track number from where data is to be erased

Returns

0 On Success
error_code On Failure

Usage
result = erase_sectors(sector,head,track);

AN015401-0903 Appendix E—API Description


Application Note
CompactFlash Interface for eZ80Acclaim!™ MCUs

60

char set_features()
char set_features(void)

Description
The set_features() API is used by the host to establish or select certain fea-
tures of the CompactFlash card.

Parameters

void

Returns

0 On Success
error_code On Failure

Usage
result = set_features();

AN015401-0903 Appendix E—API Description

You might also like