Thursday, November 12, 2009

Up Front










































Up Front



Before even considering burning a flash device, make
sure you’ve made adequate preparations for the development process. The
following sections discuss some preliminary measures. Many of these
measures might seem obvious, but they are nevertheless important enough
to mention. The tips discussed in the following sections include:




  • Get involved with the hardware design




  • Get to know the hardware and be nice to the designer




  • Have local copies of all data sheets




  • Make sure the hardware is working




  • Start slowly




  • Look at what you’ve created




It is also important to consider what tools you need
for the development process and to ensure that the design is compatible
with those tools. Several hardware-based development and debugging
tools are available to assist with the embedded systems development
process, including emulators, logic analyzers, JTAG and BDM interfaces,
memulators, and logic probes. Many of these tools attach directly to
the target device.










Get Involved with the Hardware Design


First of all, make sure the boot device is
conveniently reprogrammable. This point might seem obvious, but it’s
not unusual to find systems that have the boot device soldered to the
board with no reprogramming mechanism except to unsolder the device.
Such a design can be painful, especially for the person writing the
boot firmware. Understandably, some cost-sensitive projects must avoid
sockets and other expensive components. Even so, at least one or two
early versions of the board can be built with boot device sockets or a
JTAG-like interface so that the boot device can be reprogrammed without
the need for a soldering iron.


The design should also include some mechanism that
allows the boot firmware to easily communicate with the boot firmware
designer. Ideally, this communication would be via a serial port and a
few LEDs. If the application is extremely cost sensitive and these
extra parts are out of the question for the deliverable hardware,
consider the possibility of including some expansion connector that is
not populated on the final product. During development, the connector
can provide additional interfaces for debugging. The only unit cost is
a small increase in board size. Once again, this decision hinges on
cost restrictions and other factors but providing some means of
connectivity can save a lot of time in the development process.


I mentioned JTAG in the preceding section. If the CPU
has some type of debug interface, then make sure that the associated
pins are accessible. These interfaces become quite useful, especially
if there is no other communication device tied to the processor. When
the hardware is laid out, find out what JTAG-like tools are available
for your CPU. Get the pinout for the tool you plan to use and make
certain the hardware has a connector for it.











Get to Know the Hardware and Be Nice to the Designer


Hey, I’m not kidding! A good mutual friendship
between the firmware and hardware folks can save a lot of frustration
and time over the lifetime of a project. Let me say from experience
that chances are, it’s not a hardware problem! A lot of small, sneaky
bugs might tempt you to be suspicious of the hardware but investigate
before you accuse! This advice amounts to common sense etiquette that
will improve relations in any development environment.


Getting to know the hardware doesn’t mean that you
should look over the shoulder of the hardware designers as they are
writing VHSIC Hardware Description Language (VHDL), but it certainly
does help if you are familiar with at least the CPU section of the
schematics. Take some time with the hardware designer and ask
questions. Establish a good working relationship with the designer and
the schematics. Get your own copy of the schematics and mark them up.
This is important for the target hardware as well as the target CPU
itself. You must also spend some time reading about the processor you
are trying to tame.











Have Local Copies of all Data Sheets


You must know more than just the schematic. Each
device on the schematic may come with a 200-page manual. As silicon
gets denser, more and more complexity is built into the devices. It is
vitally important for you, the firmware developer, to master the device
behavior. In this age of electronic paper, I still find it handy to
print the sections of the manual that I will be referring to the most.
Printing the manual also allows you to document errors or strange
behavior of a device.


This issue raises another point: make sure you
check with the device vendor to see if there are any errata
outstanding. It is not at all unusual to use a device that has bugs,
especially if your design uses some new device from a silicon
manufacturer. Worse than that, you may be the one that finds new
errata. This doesn’t happen often, so don’t be too quick to blame the
silicon, but it does happen.





Make Sure the Hardware is Working


If the hardware design is brand new and the board
is fresh from the factory, make certain the designer has blessed it
before you start assuming it’s valid. Our first run– time step makes
the assumption that the connection from the CPU to the flash device is
correct. If you’re using the board for the first time, make sure you
know how to connect the power supply properly. This point may sound
silly, but you sure won’t get on the good side of the hardware designer
if you toast the board on the first day by connecting the power
incorrectly.





Start Slowly


I can’t emphasize this point enough… TAKE BABY
STEPS!!! Don’t even consider testing a large program until you have
tested several small versions of the boot code. Consider the things you
haven’t proven yet:




  • Is your program mapped to the correct memory space?




  • Do you really understand how this CPU deals with a reset/powerup?




  • Is your conversion of the executable file to binary done correctly?




  • Are you sure you configured the device programmer properly?




  • If your boot memory is wider than eight bits and
    it involves more than one device, are you sure you inserted the bytes
    into the correct device? Is the odd byte the most significant byte
    (MSB) or least significant byte (LSB)?




  • Does the hardware work?




A little humility here is likely to save you a lot of
extra loader passes. Search the CPU manufacturer’s website for example
boot code. In almost all cases, you will find something. Check out user
groups. Do some web hunting. If possible, get some hardware assistance.
If you don’t know how to use an oscilloscope or logic analyzer, then
get cushy with someone who does. These are priceless tools at this
stage of the game.






Note 

While a logic probe is somewhat limited in
capability, its convenience and price make it worth mentioning. A logic
probe is an very inexpensive, hand-held instrument that allows you to
read the logic level (high or low) at the probed connection. Most logic
probes also support the ability to detect a clock. A logic probe is a
simple pencil-like gizmo (usually with power and ground connections)
that you clip onto appropriate sources. You read a pin’s logic level by
touching the pin with the tip of this “pencil.” A readout (often just
LEDs) on the probe will then indicate whether the pin is logical high
or low, high impedance, or changing. A logic probe is very handy if you
have already verified that the hardware is stable and you are just
writing code to wiggle some PIO pins or a chip select.






Look at What You’ve Created


The build tools allow you to dump a memory map.
See if the memory map makes sense for your target. Look at the actual
S-record or binary file before you write it to the flash device. Does
it make sense? Even the file size can give you a clue. If your program
consists of only a very tight busy loop in assembly language, the final
binary file should be very small.


Find some tool (I use elvis)
that allows you to visually display a binary file in some ASCII format.
You can use this tool to confirm certain aspects of the build process.
For example, to prove that flash-resident code is being placed
correctly, you can modify the source to insert some easily recognized
pattern at what should be the base of the flash memory (see Listing 2.8).
After converting the source to binary (using the normal build process),
use your dump tool to examine the file. You should find the marker
pattern at the offset corresponding to the beginning for your flash
memory.



Listing 2.8: “Marking” Code to Confirm Position.






coldstart:
.byte 0x31, 0x32, 0x33, 0x34
assembler code here














Listing 2.9 is a sample dump from the elvis vi
clone that displays the offset into the file, the data in
ASCII-coded-hexadecimal, and the data in regular ASCII (if printable).
Hence, the flash memory begins at offset 0x0000.




Listing 2.9: Sample Dump






OFFSET     ASCII_CODED_HEX_DATA                                ASCII_DATA
000000: 31 32 33 34 ff fd 78 14 38 60 00 30 4b fc 00 0e 1234..x.8`.0K"..
000010: 38 80 00 00 38 a0 00 00 38 c0 00 00 3c e0 00 04 8C..8a..*l..<x..














The only thing you need to see in Listing 2.9 is that the first four bytes of the file are as you expected (0x31, 0x32, 0x33, and 0x34).






Note 

This binary dump is also very useful if you have
to split your data into separate files so you can program multiple
devices that are in parallel in the hardware. Before the split, you
have what is shown in Listing 2.9,
and, after the split (assume a split into two files), one file is as
shown in the display labeled “Split A” and the other file is as shown
in “Split B”, clearly indicating that the single file was properly
split.



Split A



OFFSET   ASCII_CODED_HEX_DATA                              ASCII_DATA
000000: 31 33 ff 78 38 00 4b 00 38 00 38 00 38 00 3c 00 13.x8.K.8.8.*.<.


Split B



OFFSET   ASCII_CODED_HEX_DATA                              ASCII_DATA
000000: 32 34 fd 14 60 30 fc 0e 80 00 a0 00 c0 00 e0 04 24..`0".C.a.l.x.












Figure 2.4: Flash Relative vs. CPU Relative Address Space.


Since memory devices usually span only a portion of the
processor address space, the absolute addresses in an object format
(like S-records) might need to be adjusted to be interpreted correctly
by the device programmer. This requirement is because the device
programmer often knows only about the memory device’s address space not
the processor’s.


Referring to Figure 2.4,
in the case of Configuration 1, where the boot device resides at
location zero of CPU-relative memory, the S-record CPU-relative
addresses also correspond to flash device addresses, so all works well.


Configuration 2 however, does not work. Here the
CPU boots from some location other than zero, so offset zero within the
flash device no longer corresponds to physical address zero. Assume
that this CPU boots at 0x8F000000, so the S-record file has AAAA… fields starting at 0x8F000000
because that’s where the CPU sees the instructions. However, when I
step away from the hardware design and go program the flash device, I
must adjust the S-record address of 0x8F000000 to 0x0000000 because 0x8F000000 in CPU address space is the same as 0x00000000
in the flash device’s address space. This adjustment to the S-record
address can be performed in some post-processing step or in the
programmer if it supports the ability to adjust the base. My personal
preference is to avoid this complexity by using raw binary files
instead of S-records.





































No comments:

Post a Comment