요약·해설과 원문, 전문 번역을 서로 분리했습니다. API 이름, symbol, source path는 원문 표기를 사용합니다.
1. 요약·해설
원문의 핵심 논리와 kernel programming 관점의 보충 설명입니다. 아래의 전문 번역과는 별도로 작성했습니다.
2. 영어 원문 전체
번역 기준이 된 Linux v6.18.37 원문입니다. 줄 번호는 이 버전의 파일 좌표입니다.
원문 전체 펼치기
====================================
Overview of Linux kernel SPI support
====================================
02-Feb-2012
What is SPI?
------------
The "Serial Peripheral Interface" (SPI) is a synchronous four wire serial
link used to connect microcontrollers to sensors, memory, and peripherals.
It's a simple "de facto" standard, not complicated enough to acquire a
standardization body. SPI uses a host/target configuration.
The three signal wires hold a clock (SCK, often on the order of 10 MHz),
and parallel data lines with "Master Out, Slave In" (MOSI) or "Master In,
Slave Out" (MISO) signals. (Other names are also used.) There are four
clocking modes through which data is exchanged; mode-0 and mode-3 are most
commonly used. Each clock cycle shifts data out and data in; the clock
doesn't cycle except when there is a data bit to shift. Not all data bits
are used though; not every protocol uses those full duplex capabilities.
SPI hosts use a fourth "chip select" line to activate a given SPI target
device, so those three signal wires may be connected to several chips
in parallel. All SPI targets support chipselects; they are usually active
low signals, labeled nCSx for target 'x' (e.g. nCS0). Some devices have
other signals, often including an interrupt to the host.
Unlike serial busses like USB or SMBus, even low level protocols for
SPI target functions are usually not interoperable between vendors
(except for commodities like SPI memory chips).
- SPI may be used for request/response style device protocols, as with
touchscreen sensors and memory chips.
- It may also be used to stream data in either direction (half duplex),
or both of them at the same time (full duplex).
- Some devices may use eight bit words. Others may use different word
lengths, such as streams of 12-bit or 20-bit digital samples.
- Words are usually sent with their most significant bit (MSB) first,
but sometimes the least significant bit (LSB) goes first instead.
- Sometimes SPI is used to daisy-chain devices, like shift registers.
In the same way, SPI targets will only rarely support any kind of automatic
discovery/enumeration protocol. The tree of target devices accessible from
a given SPI host controller will normally be set up manually, with
configuration tables.
SPI is only one of the names used by such four-wire protocols, and
most controllers have no problem handling "MicroWire" (think of it as
half-duplex SPI, for request/response protocols), SSP ("Synchronous
Serial Protocol"), PSP ("Programmable Serial Protocol"), and other
related protocols.
Some chips eliminate a signal line by combining MOSI and MISO, and
limiting themselves to half-duplex at the hardware level. In fact
some SPI chips have this signal mode as a strapping option. These
can be accessed using the same programming interface as SPI, but of
course they won't handle full duplex transfers. You may find such
chips described as using "three wire" signaling: SCK, data, nCSx.
(That data line is sometimes called MOMI or SISO.)
Microcontrollers often support both host and target sides of the SPI
protocol. This document (and Linux) supports both the host and target
sides of SPI interactions.
Who uses it? On what kinds of systems?
---------------------------------------
Linux developers using SPI are probably writing device drivers for embedded
systems boards. SPI is used to control external chips, and it is also a
protocol supported by every MMC or SD memory card. (The older "DataFlash"
cards, predating MMC cards but using the same connectors and card shape,
support only SPI.) Some PC hardware uses SPI flash for BIOS code.
SPI target chips range from digital/analog converters used for analog
sensors and codecs, to memory, to peripherals like USB controllers
or Ethernet adapters; and more.
Most systems using SPI will integrate a few devices on a mainboard.
Some provide SPI links on expansion connectors; in cases where no
dedicated SPI controller exists, GPIO pins can be used to create a
low speed "bitbanging" adapter. Very few systems will "hotplug" an SPI
controller; the reasons to use SPI focus on low cost and simple operation,
and if dynamic reconfiguration is important, USB will often be a more
appropriate low-pincount peripheral bus.
Many microcontrollers that can run Linux integrate one or more I/O
interfaces with SPI modes. Given SPI support, they could use MMC or SD
cards without needing a special purpose MMC/SD/SDIO controller.
I'm confused. What are these four SPI "clock modes"?
-----------------------------------------------------
It's easy to be confused here, and the vendor documentation you'll
find isn't necessarily helpful. The four modes combine two mode bits:
- CPOL indicates the initial clock polarity. CPOL=0 means the
clock starts low, so the first (leading) edge is rising, and
the second (trailing) edge is falling. CPOL=1 means the clock
starts high, so the first (leading) edge is falling.
- CPHA indicates the clock phase used to sample data; CPHA=0 says
sample on the leading edge, CPHA=1 means the trailing edge.
Since the signal needs to stabilize before it's sampled, CPHA=0
implies that its data is written half a clock before the first
clock edge. The chipselect may have made it become available.
Chip specs won't always say "uses SPI mode X" in as many words,
but their timing diagrams will make the CPOL and CPHA modes clear.
In the SPI mode number, CPOL is the high order bit and CPHA is the
low order bit. So when a chip's timing diagram shows the clock
starting low (CPOL=0) and data stabilized for sampling during the
trailing clock edge (CPHA=1), that's SPI mode 1.
Note that the clock mode is relevant as soon as the chipselect goes
active. So the host must set the clock to inactive before selecting
a target, and the target can tell the chosen polarity by sampling the
clock level when its select line goes active. That's why many devices
support for example both modes 0 and 3: they don't care about polarity,
and always clock data in/out on rising clock edges.
How do these driver programming interfaces work?
------------------------------------------------
The <linux/spi/spi.h> header file includes kerneldoc, as does the
main source code, and you should certainly read that chapter of the
kernel API document. This is just an overview, so you get the big
picture before those details.
SPI requests always go into I/O queues. Requests for a given SPI device
are always executed in FIFO order, and complete asynchronously through
completion callbacks. There are also some simple synchronous wrappers
for those calls, including ones for common transaction types like writing
a command and then reading its response.
There are two types of SPI driver, here called:
Controller drivers ...
controllers may be built into System-On-Chip
processors, and often support both Controller and target roles.
These drivers touch hardware registers and may use DMA.
Or they can be PIO bitbangers, needing just GPIO pins.
Protocol drivers ...
these pass messages through the controller
driver to communicate with a target or Controller device on the
other side of an SPI link.
So for example one protocol driver might talk to the MTD layer to export
data to filesystems stored on SPI flash like DataFlash; and others might
control audio interfaces, present touchscreen sensors as input interfaces,
or monitor temperature and voltage levels during industrial processing.
And those might all be sharing the same controller driver.
A "struct spi_device" encapsulates the controller-side interface between
those two types of drivers.
There is a minimal core of SPI programming interfaces, focussing on
using the driver model to connect controller and protocol drivers using
device tables provided by board specific initialization code. SPI
shows up in sysfs in several locations::
/sys/devices/.../CTLR ... physical node for a given SPI controller
/sys/devices/.../CTLR/spiB.C ... spi_device on bus "B",
chipselect C, accessed through CTLR.
/sys/bus/spi/devices/spiB.C ... symlink to that physical
.../CTLR/spiB.C device
/sys/devices/.../CTLR/spiB.C/modalias ... identifies the driver
that should be used with this device (for hotplug/coldplug)
/sys/bus/spi/drivers/D ... driver for one or more spi*.* devices
/sys/class/spi_master/spiB ... symlink to a logical node which could hold
class related state for the SPI host controller managing bus "B".
All spiB.* devices share one physical SPI bus segment, with SCLK,
MOSI, and MISO.
/sys/devices/.../CTLR/slave ... virtual file for (un)registering the
target device for an SPI target controller.
Writing the driver name of an SPI target handler to this file
registers the target device; writing "(null)" unregisters the target
device.
Reading from this file shows the name of the target device ("(null)"
if not registered).
/sys/class/spi_slave/spiB ... symlink to a logical node which could hold
class related state for the SPI target controller on bus "B". When
registered, a single spiB.* device is present here, possible sharing
the physical SPI bus segment with other SPI target devices.
At this time, the only class-specific state is the bus number ("B" in "spiB"),
so those /sys/class entries are only useful to quickly identify busses.
How does board-specific init code declare SPI devices?
------------------------------------------------------
Linux needs several kinds of information to properly configure SPI devices.
That information is normally provided by board-specific code, even for
chips that do support some of automated discovery/enumeration.
Declare Controllers
^^^^^^^^^^^^^^^^^^^
The first kind of information is a list of what SPI controllers exist.
For System-on-Chip (SOC) based boards, these will usually be platform
devices, and the controller may need some platform_data in order to
operate properly. The "struct platform_device" will include resources
like the physical address of the controller's first register and its IRQ.
Platforms will often abstract the "register SPI controller" operation,
maybe coupling it with code to initialize pin configurations, so that
the arch/.../mach-*/board-*.c files for several boards can all share the
same basic controller setup code. This is because most SOCs have several
SPI-capable controllers, and only the ones actually usable on a given
board should normally be set up and registered.
So for example arch/.../mach-*/board-*.c files might have code like::
#include <mach/spi.h> /* for mysoc_spi_data */
/* if your mach-* infrastructure doesn't support kernels that can
* run on multiple boards, pdata wouldn't benefit from "__init".
*/
static struct mysoc_spi_data pdata __initdata = { ... };
static __init board_init(void)
{
...
/* this board only uses SPI controller #2 */
mysoc_register_spi(2, &pdata);
...
}
And SOC-specific utility code might look something like::
#include <mach/spi.h>
static struct platform_device spi2 = { ... };
void mysoc_register_spi(unsigned n, struct mysoc_spi_data *pdata)
{
struct mysoc_spi_data *pdata2;
pdata2 = kmalloc(sizeof *pdata2, GFP_KERNEL);
*pdata2 = pdata;
...
if (n == 2) {
spi2->dev.platform_data = pdata2;
register_platform_device(&spi2);
/* also: set up pin modes so the spi2 signals are
* visible on the relevant pins ... bootloaders on
* production boards may already have done this, but
* developer boards will often need Linux to do it.
*/
}
...
}
Notice how the platform_data for boards may be different, even if the
same SOC controller is used. For example, on one board SPI might use
an external clock, where another derives the SPI clock from current
settings of some master clock.
Declare target Devices
^^^^^^^^^^^^^^^^^^^^^^
The second kind of information is a list of what SPI target devices exist
on the target board, often with some board-specific data needed for the
driver to work correctly.
Normally your arch/.../mach-*/board-*.c files would provide a small table
listing the SPI devices on each board. (This would typically be only a
small handful.) That might look like::
static struct ads7846_platform_data ads_info = {
.vref_delay_usecs = 100,
.x_plate_ohms = 580,
.y_plate_ohms = 410,
};
static struct spi_board_info spi_board_info[] __initdata = {
{
.modalias = "ads7846",
.platform_data = &ads_info,
.mode = SPI_MODE_0,
.irq = GPIO_IRQ(31),
.max_speed_hz = 120000 /* max sample rate at 3V */ * 16,
.bus_num = 1,
.chip_select = 0,
},
};
Again, notice how board-specific information is provided; each chip may need
several types. This example shows generic constraints like the fastest SPI
clock to allow (a function of board voltage in this case) or how an IRQ pin
is wired, plus chip-specific constraints like an important delay that's
changed by the capacitance at one pin.
(There's also "controller_data", information that may be useful to the
controller driver. An example would be peripheral-specific DMA tuning
data or chipselect callbacks. This is stored in spi_device later.)
The board_info should provide enough information to let the system work
without the chip's driver being loaded. The most troublesome aspect of
that is likely the SPI_CS_HIGH bit in the spi_device.mode field, since
sharing a bus with a device that interprets chipselect "backwards" is
not possible until the infrastructure knows how to deselect it.
Then your board initialization code would register that table with the SPI
infrastructure, so that it's available later when the SPI host controller
driver is registered::
spi_register_board_info(spi_board_info, ARRAY_SIZE(spi_board_info));
Like with other static board-specific setup, you won't unregister those.
The widely used "card" style computers bundle memory, cpu, and little else
onto a card that's maybe just thirty square centimeters. On such systems,
your ``arch/.../mach-.../board-*.c`` file would primarily provide information
about the devices on the mainboard into which such a card is plugged. That
certainly includes SPI devices hooked up through the card connectors!
Non-static Configurations
^^^^^^^^^^^^^^^^^^^^^^^^^
When Linux includes support for MMC/SD/SDIO/DataFlash cards through SPI, those
configurations will also be dynamic. Fortunately, such devices all support
basic device identification probes, so they should hotplug normally.
How do I write an "SPI Protocol Driver"?
----------------------------------------
Most SPI drivers are currently kernel drivers, but there's also support
for userspace drivers. Here we talk only about kernel drivers.
SPI protocol drivers somewhat resemble platform device drivers::
static struct spi_driver CHIP_driver = {
.driver = {
.name = "CHIP",
.pm = &CHIP_pm_ops,
},
.probe = CHIP_probe,
.remove = CHIP_remove,
};
The driver core will automatically attempt to bind this driver to any SPI
device whose board_info gave a modalias of "CHIP". Your probe() code
might look like this unless you're creating a device which is managing
a bus (appearing under /sys/class/spi_master).
::
static int CHIP_probe(struct spi_device *spi)
{
struct CHIP *chip;
struct CHIP_platform_data *pdata;
/* assuming the driver requires board-specific data: */
pdata = &spi->dev.platform_data;
if (!pdata)
return -ENODEV;
/* get memory for driver's per-chip state */
chip = kzalloc(sizeof *chip, GFP_KERNEL);
if (!chip)
return -ENOMEM;
spi_set_drvdata(spi, chip);
... etc
return 0;
}
As soon as it enters probe(), the driver may issue I/O requests to
the SPI device using "struct spi_message". When remove() returns,
or after probe() fails, the driver guarantees that it won't submit
any more such messages.
- An spi_message is a sequence of protocol operations, executed
as one atomic sequence. SPI driver controls include:
+ when bidirectional reads and writes start ... by how its
sequence of spi_transfer requests is arranged;
+ which I/O buffers are used ... each spi_transfer wraps a
buffer for each transfer direction, supporting full duplex
(two pointers, maybe the same one in both cases) and half
duplex (one pointer is NULL) transfers;
+ optionally defining short delays after transfers ... using
the spi_transfer.delay.value setting (this delay can be the
only protocol effect, if the buffer length is zero) ...
when specifying this delay the default spi_transfer.delay.unit
is microseconds, however this can be adjusted to clock cycles
or nanoseconds if needed;
+ whether the chipselect becomes inactive after a transfer and
any delay ... by using the spi_transfer.cs_change flag;
+ hinting whether the next message is likely to go to this same
device ... using the spi_transfer.cs_change flag on the last
transfer in that atomic group, and potentially saving costs
for chip deselect and select operations.
- Follow standard kernel rules, and provide DMA-safe buffers in
your messages. That way controller drivers using DMA aren't forced
to make extra copies unless the hardware requires it (e.g. working
around hardware errata that force the use of bounce buffering).
- The basic I/O primitive is spi_async(). Async requests may be
issued in any context (irq handler, task, etc) and completion
is reported using a callback provided with the message.
After any detected error, the chip is deselected and processing
of that spi_message is aborted.
- There are also synchronous wrappers like spi_sync(), and wrappers
like spi_read(), spi_write(), and spi_write_then_read(). These
may be issued only in contexts that may sleep, and they're all
clean (and small, and "optional") layers over spi_async().
- The spi_write_then_read() call, and convenience wrappers around
it, should only be used with small amounts of data where the
cost of an extra copy may be ignored. It's designed to support
common RPC-style requests, such as writing an eight bit command
and reading a sixteen bit response -- spi_w8r16() being one its
wrappers, doing exactly that.
Some drivers may need to modify spi_device characteristics like the
transfer mode, wordsize, or clock rate. This is done with spi_setup(),
which would normally be called from probe() before the first I/O is
done to the device. However, that can also be called at any time
that no message is pending for that device.
While "spi_device" would be the bottom boundary of the driver, the
upper boundaries might include sysfs (especially for sensor readings),
the input layer, ALSA, networking, MTD, the character device framework,
or other Linux subsystems.
Note that there are two types of memory your driver must manage as part
of interacting with SPI devices.
- I/O buffers use the usual Linux rules, and must be DMA-safe.
You'd normally allocate them from the heap or free page pool.
Don't use the stack, or anything that's declared "static".
- The spi_message and spi_transfer metadata used to glue those
I/O buffers into a group of protocol transactions. These can
be allocated anywhere it's convenient, including as part of
other allocate-once driver data structures. Zero-init these.
If you like, spi_message_alloc() and spi_message_free() convenience
routines are available to allocate and zero-initialize an spi_message
with several transfers.
How do I write an "SPI Controller Driver"?
-------------------------------------------------
An SPI controller will probably be registered on the platform_bus; write
a driver to bind to the device, whichever bus is involved.
The main task of this type of driver is to provide an "spi_controller".
Use spi_alloc_host() to allocate the host controller, and
spi_controller_get_devdata() to get the driver-private data allocated for that
device.
::
struct spi_controller *ctlr;
struct CONTROLLER *c;
ctlr = spi_alloc_host(dev, sizeof *c);
if (!ctlr)
return -ENODEV;
c = spi_controller_get_devdata(ctlr);
The driver will initialize the fields of that spi_controller, including the bus
number (maybe the same as the platform device ID) and three methods used to
interact with the SPI core and SPI protocol drivers. It will also initialize
its own internal state. (See below about bus numbering and those methods.)
After you initialize the spi_controller, then use spi_register_controller() to
publish it to the rest of the system. At that time, device nodes for the
controller and any predeclared spi devices will be made available, and
the driver model core will take care of binding them to drivers.
If you need to remove your SPI controller driver, spi_unregister_controller()
will reverse the effect of spi_register_controller().
Bus Numbering
^^^^^^^^^^^^^
Bus numbering is important, since that's how Linux identifies a given
SPI bus (shared SCK, MOSI, MISO). Valid bus numbers start at zero. On
SOC systems, the bus numbers should match the numbers defined by the chip
manufacturer. For example, hardware controller SPI2 would be bus number 2,
and spi_board_info for devices connected to it would use that number.
If you don't have such hardware-assigned bus number, and for some reason
you can't just assign them, then provide a negative bus number. That will
then be replaced by a dynamically assigned number. You'd then need to treat
this as a non-static configuration (see above).
SPI Host Controller Methods
^^^^^^^^^^^^^^^^^^^^^^^^^^^
``ctlr->setup(struct spi_device *spi)``
This sets up the device clock rate, SPI mode, and word sizes.
Drivers may change the defaults provided by board_info, and then
call spi_setup(spi) to invoke this routine. It may sleep.
Unless each SPI target has its own configuration registers, don't
change them right away ... otherwise drivers could corrupt I/O
that's in progress for other SPI devices.
.. note::
BUG ALERT: for some reason the first version of
many spi_controller drivers seems to get this wrong.
When you code setup(), ASSUME that the controller
is actively processing transfers for another device.
``ctlr->cleanup(struct spi_device *spi)``
Your controller driver may use spi_device.controller_state to hold
state it dynamically associates with that device. If you do that,
be sure to provide the cleanup() method to free that state.
``ctlr->prepare_transfer_hardware(struct spi_controller *ctlr)``
This will be called by the queue mechanism to signal to the driver
that a message is coming in soon, so the subsystem requests the
driver to prepare the transfer hardware by issuing this call.
This may sleep.
``ctlr->unprepare_transfer_hardware(struct spi_controller *ctlr)``
This will be called by the queue mechanism to signal to the driver
that there are no more messages pending in the queue and it may
relax the hardware (e.g. by power management calls). This may sleep.
``ctlr->transfer_one_message(struct spi_controller *ctlr, struct spi_message *mesg)``
The subsystem calls the driver to transfer a single message while
queuing transfers that arrive in the meantime. When the driver is
finished with this message, it must call
spi_finalize_current_message() so the subsystem can issue the next
message. This may sleep.
``ctrl->transfer_one(struct spi_controller *ctlr, struct spi_device *spi, struct spi_transfer *transfer)``
The subsystem calls the driver to transfer a single transfer while
queuing transfers that arrive in the meantime. When the driver is
finished with this transfer, it must call
spi_finalize_current_transfer() so the subsystem can issue the next
transfer. This may sleep. Note: transfer_one and transfer_one_message
are mutually exclusive; when both are set, the generic subsystem does
not call your transfer_one callback.
Return values:
* negative errno: error
* 0: transfer is finished
* 1: transfer is still in progress
``ctrl->set_cs_timing(struct spi_device *spi, u8 setup_clk_cycles, u8 hold_clk_cycles, u8 inactive_clk_cycles)``
This method allows SPI client drivers to request SPI host controller
for configuring device specific CS setup, hold and inactive timing
requirements.
Deprecated Methods
^^^^^^^^^^^^^^^^^^
``ctrl->transfer(struct spi_device *spi, struct spi_message *message)``
This must not sleep. Its responsibility is to arrange that the
transfer happens and its complete() callback is issued. The two
will normally happen later, after other transfers complete, and
if the controller is idle it will need to be kickstarted. This
method is not used on queued controllers and must be NULL if
transfer_one_message() and (un)prepare_transfer_hardware() are
implemented.
SPI Message Queue
^^^^^^^^^^^^^^^^^
If you are happy with the standard queueing mechanism provided by the
SPI subsystem, just implement the queued methods specified above. Using
the message queue has the upside of centralizing a lot of code and
providing pure process-context execution of methods. The message queue
can also be elevated to realtime priority on high-priority SPI traffic.
Unless the queueing mechanism in the SPI subsystem is selected, the bulk
of the driver will be managing the I/O queue fed by the now deprecated
function transfer().
That queue could be purely conceptual. For example, a driver used only
for low-frequency sensor access might be fine using synchronous PIO.
But the queue will probably be very real, using message->queue, PIO,
often DMA (especially if the root filesystem is in SPI flash), and
execution contexts like IRQ handlers, tasklets, or workqueues (such
as keventd). Your driver can be as fancy, or as simple, as you need.
Such a transfer() method would normally just add the message to a
queue, and then start some asynchronous transfer engine (unless it's
already running).
Extensions to the SPI protocol
------------------------------
The fact that SPI doesn't have a formal specification or standard permits chip
manufacturers to implement the SPI protocol in slightly different ways. In most
cases, SPI protocol implementations from different vendors are compatible among
each other. For example, in SPI mode 0 (CPOL=0, CPHA=0) the bus lines may behave
like the following:
::
nCSx ___ ___
\_________________________________________________________________/
• •
• •
SCLK ___ ___ ___ ___ ___ ___ ___ ___
_______/ \___/ \___/ \___/ \___/ \___/ \___/ \___/ \_____
• : ; : ; : ; : ; : ; : ; : ; : ; •
• : ; : ; : ; : ; : ; : ; : ; : ; •
MOSI XXX__________ _______ _______ ________XXX
0xA5 XXX__/ 1 \_0_____/ 1 \_0_______0_____/ 1 \_0_____/ 1 \_XXX
• ; ; ; ; ; ; ; ; •
• ; ; ; ; ; ; ; ; •
MISO XXX__________ _______________________ _______ XXX
0xBA XXX__/ 1 \_____0_/ 1 1 1 \_____0__/ 1 \____0__XXX
Legend::
• marks the start/end of transmission;
: marks when data is clocked into the peripheral;
; marks when data is clocked into the controller;
X marks when line states are not specified.
In some few cases, chips extend the SPI protocol by specifying line behaviors
that other SPI protocols don't (e.g. data line state for when CS is not
asserted). Those distinct SPI protocols, modes, and configurations are supported
by different SPI mode flags.
MOSI idle state configuration
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Common SPI protocol implementations don't specify any state or behavior for the
MOSI line when the controller is not clocking out data. However, there do exist
peripherals that require specific MOSI line state when data is not being clocked
out. For example, if the peripheral expects the MOSI line to be high when the
controller is not clocking out data (``SPI_MOSI_IDLE_HIGH``), then a transfer in
SPI mode 0 would look like the following:
::
nCSx ___ ___
\_________________________________________________________________/
• •
• •
SCLK ___ ___ ___ ___ ___ ___ ___ ___
_______/ \___/ \___/ \___/ \___/ \___/ \___/ \___/ \_____
• : ; : ; : ; : ; : ; : ; : ; : ; •
• : ; : ; : ; : ; : ; : ; : ; : ; •
MOSI _____ _______ _______ _______________ ___
0x56 \_0_____/ 1 \_0_____/ 1 \_0_____/ 1 1 \_0_____/
• ; ; ; ; ; ; ; ; •
• ; ; ; ; ; ; ; ; •
MISO XXX__________ _______________________ _______ XXX
0xBA XXX__/ 1 \_____0_/ 1 1 1 \_____0__/ 1 \____0__XXX
Legend::
• marks the start/end of transmission;
: marks when data is clocked into the peripheral;
; marks when data is clocked into the controller;
X marks when line states are not specified.
In this extension to the usual SPI protocol, the MOSI line state is specified to
be kept high when CS is asserted but the controller is not clocking out data to
the peripheral and also when CS is not asserted.
Peripherals that require this extension must request it by setting the
``SPI_MOSI_IDLE_HIGH`` bit into the mode attribute of their ``struct
spi_device`` and call spi_setup(). Controllers that support this extension
should indicate it by setting ``SPI_MOSI_IDLE_HIGH`` in the mode_bits attribute
of their ``struct spi_controller``. The configuration to idle MOSI low is
analogous but uses the ``SPI_MOSI_IDLE_LOW`` mode bit.
THANKS TO
---------
Contributors to Linux-SPI discussions include (in alphabetical order,
by last name):
- Mark Brown
- David Brownell
- Russell King
- Grant Likely
- Dmitry Pervushin
- Stephen Street
- Mark Underwood
- Andrew Victor
- Linus Walleij
- Vitaly Wool
3. 한국어 전문 번역
영어 원문의 문단 순서와 의미를 유지한 전체 번역입니다. 코드, 함수명, symbol과 URL은 원문 표기를 유지합니다.
SPI의 신호와 통신 형태
1-69이 문서는 2012년 2월 2일 기준 Linux 커널의 SPI 지원을 개괄한다. Serial Peripheral Interface(SPI)는 microcontroller를 sensor, memory, peripheral에 연결하는 동기식 4선 직렬 링크다. 복잡한 공식 표준이 아니라 단순한 사실상 표준이며 host/target 구성으로 동작한다.
공유되는 세 신호선은 대개 약 10 MHz로 동작하는 clock `SCK`, host에서 target으로 보내는 `MOSI`(Master Out, Slave In), target에서 host로 보내는 `MISO`(Master In, Slave Out)다. 명칭은 구현에 따라 달라질 수 있다. 네 clock mode 가운데 mode 0과 mode 3이 가장 흔하며, clock cycle마다 입력과 출력 bit가 함께 shift된다. 이동할 data bit가 없으면 clock도 움직이지 않고, protocol에 따라 full-duplex 두 방향을 모두 사용하지 않을 수도 있다.
네 번째 신호인 chip select는 특정 target을 활성화한다. 따라서 `SCK`, `MOSI`, `MISO`는 여러 chip에 병렬 연결할 수 있다. 모든 SPI target은 보통 active-low인 chip select를 지원하며 target x의 신호를 `nCSx`, 예를 들어 `nCS0`처럼 표기한다. host로 보내는 interrupt 같은 추가 신호를 가진 장치도 있다.
USB나 SMBus와 달리 SPI target의 저수준 protocol은 SPI memory 같은 범용품을 제외하면 vendor 사이에서 대개 호환되지 않는다. SPI는 touchscreen sensor나 memory chip의 request/response, 한 방향 half-duplex stream, 양방향 full-duplex stream에 쓰인다. word 길이는 8 bit일 수도 있고 12 bit·20 bit sample stream처럼 다를 수 있으며, 전송 순서도 보통 MSB-first지만 LSB-first인 장치가 있다. shift register처럼 장치를 daisy-chain하기도 한다.
SPI target은 자동 discovery나 enumeration을 거의 제공하지 않는다. 특정 host controller에서 접근 가능한 target tree는 보통 configuration table로 수동 구성한다. 같은 4선 계열 protocol은 SPI 외에도 request/response용 half-duplex SPI로 볼 수 있는 MicroWire, SSP(Synchronous Serial Protocol), PSP(Programmable Serial Protocol) 등으로 불리며, 대다수 controller가 이들을 처리한다.
일부 chip은 MOSI와 MISO를 하나의 data line으로 합쳐 hardware 수준에서 half-duplex만 허용한다. 이 선택을 strapping option으로 제공하는 SPI chip도 있다. programming interface는 SPI와 같지만 full-duplex transfer는 불가능하며, 이런 구성을 `SCK`, data, `nCSx`로 이루어진 3선 signaling이라 부른다. 합쳐진 data line은 MOMI 또는 SISO라고도 한다. Linux와 이 문서는 microcontroller에서 흔한 SPI host와 target 양쪽 역할을 모두 지원한다.
공유 bus와 target별 선택 신호의 역할을 정리한다.
세 bus 신호는 병렬로 공유하고 각 target은 별도 chip select로 활성화한다.
protocol이 선택할 수 있는 주요 전송 특성이다.
====================================
Overview of Linux kernel SPI support
====================================
02-Feb-2012
What is SPI?
------------
The "Serial Peripheral Interface" (SPI) is a synchronous four wire serial
link used to connect microcontrollers to sensors, memory, and peripherals.
It's a simple "de facto" standard, not complicated enough to acquire a
standardization body. SPI uses a host/target configuration.
The three signal wires hold a clock (SCK, often on the order of 10 MHz),
and parallel data lines with "Master Out, Slave In" (MOSI) or "Master In,
Slave Out" (MISO) signals. (Other names are also used.) There are four
clocking modes through which data is exchanged; mode-0 and mode-3 are most
commonly used. Each clock cycle shifts data out and data in; the clock
doesn't cycle except when there is a data bit to shift. Not all data bits
are used though; not every protocol uses those full duplex capabilities.
SPI hosts use a fourth "chip select" line to activate a given SPI target
device, so those three signal wires may be connected to several chips
in parallel. All SPI targets support chipselects; they are usually active
low signals, labeled nCSx for target 'x' (e.g. nCS0). Some devices have
other signals, often including an interrupt to the host.
Unlike serial busses like USB or SMBus, even low level protocols for
SPI target functions are usually not interoperable between vendors
(except for commodities like SPI memory chips).
- SPI may be used for request/response style device protocols, as with
touchscreen sensors and memory chips.
- It may also be used to stream data in either direction (half duplex),
or both of them at the same time (full duplex).
- Some devices may use eight bit words. Others may use different word
lengths, such as streams of 12-bit or 20-bit digital samples.
- Words are usually sent with their most significant bit (MSB) first,
but sometimes the least significant bit (LSB) goes first instead.
- Sometimes SPI is used to daisy-chain devices, like shift registers.
In the same way, SPI targets will only rarely support any kind of automatic
discovery/enumeration protocol. The tree of target devices accessible from
a given SPI host controller will normally be set up manually, with
configuration tables.
SPI is only one of the names used by such four-wire protocols, and
most controllers have no problem handling "MicroWire" (think of it as
half-duplex SPI, for request/response protocols), SSP ("Synchronous
Serial Protocol"), PSP ("Programmable Serial Protocol"), and other
related protocols.
Some chips eliminate a signal line by combining MOSI and MISO, and
limiting themselves to half-duplex at the hardware level. In fact
some SPI chips have this signal mode as a strapping option. These
can be accessed using the same programming interface as SPI, but of
course they won't handle full duplex transfers. You may find such
chips described as using "three wire" signaling: SCK, data, nCSx.
(That data line is sometimes called MOMI or SISO.)
Microcontrollers often support both host and target sides of the SPI
protocol. This document (and Linux) supports both the host and target
sides of SPI interactions.
SPI가 쓰이는 시스템
70-94Linux에서 SPI를 다루는 개발자는 주로 embedded system board의 device driver를 작성한다. SPI는 외부 chip 제어뿐 아니라 모든 MMC·SD memory card가 지원하는 protocol이다. MMC보다 오래되었지만 같은 connector와 card 형태를 쓰는 DataFlash card는 SPI만 지원한다. 일부 PC hardware는 BIOS code 저장용 SPI flash를 쓴다.
SPI target은 analog sensor와 codec용 digital/analog converter, memory, USB controller, Ethernet adapter 등 매우 다양하다. 대다수 시스템은 mainboard에 소수의 SPI 장치를 통합하고, 일부는 expansion connector에 SPI link를 제공한다. 전용 controller가 없으면 GPIO pin으로 저속 bitbanging adapter를 만들 수 있다.
SPI는 낮은 비용과 단순 동작을 중시하므로 SPI controller를 hotplug하는 시스템은 드물다. 동적 재구성이 중요하다면 pin 수가 적은 peripheral bus로 USB가 더 적합한 경우가 많다. Linux를 실행하는 많은 microcontroller에는 하나 이상의 SPI mode I/O interface가 있으므로, SPI 지원만으로 전용 MMC/SD/SDIO controller 없이 MMC 또는 SD card를 사용할 수도 있다.
시스템과 target 종류별 활용 예다.
Who uses it? On what kinds of systems?
---------------------------------------
Linux developers using SPI are probably writing device drivers for embedded
systems boards. SPI is used to control external chips, and it is also a
protocol supported by every MMC or SD memory card. (The older "DataFlash"
cards, predating MMC cards but using the same connectors and card shape,
support only SPI.) Some PC hardware uses SPI flash for BIOS code.
SPI target chips range from digital/analog converters used for analog
sensors and codecs, to memory, to peripherals like USB controllers
or Ethernet adapters; and more.
Most systems using SPI will integrate a few devices on a mainboard.
Some provide SPI links on expansion connectors; in cases where no
dedicated SPI controller exists, GPIO pins can be used to create a
low speed "bitbanging" adapter. Very few systems will "hotplug" an SPI
controller; the reasons to use SPI focus on low cost and simple operation,
and if dynamic reconfiguration is important, USB will often be a more
appropriate low-pincount peripheral bus.
Many microcontrollers that can run Linux integrate one or more I/O
interfaces with SPI modes. Given SPI support, they could use MMC or SD
cards without needing a special purpose MMC/SD/SDIO controller.
CPOL·CPHA와 네 clock mode
95-127네 SPI clock mode는 두 mode bit `CPOL`과 `CPHA`의 조합이다. vendor 문서가 mode 번호를 직접 말하지 않더라도 timing diagram에서 두 값을 판별할 수 있다.
`CPOL`은 초기 clock polarity다. `CPOL=0`이면 clock이 low에서 시작해 첫 leading edge가 rising, 두 번째 trailing edge가 falling이다. `CPOL=1`이면 clock이 high에서 시작해 leading edge가 falling이 된다.
`CPHA`는 data를 sample할 clock phase다. `CPHA=0`은 leading edge, `CPHA=1`은 trailing edge에서 sample한다. signal은 sample 전에 안정되어야 하므로 `CPHA=0`에서는 첫 clock edge보다 반 cycle 앞서 data를 써야 하며, chip select가 활성화되면서 data가 준비될 수 있다.
SPI mode 번호에서 `CPOL`은 상위 bit, `CPHA`는 하위 bit다. 예를 들어 clock이 low에서 시작하고(`CPOL=0`) trailing edge에서 안정된 data를 sample하면(`CPHA=1`) mode 1이다.
clock mode는 chip select가 active가 되는 즉시 의미가 있다. host는 target을 선택하기 전에 clock을 inactive 상태로 설정해야 한다. target은 select line이 active가 될 때 clock level을 읽어 polarity를 알 수 있다. 그래서 많은 장치가 mode 0과 3을 모두 지원한다. 이들은 polarity 자체에는 무관하고 rising edge에서 data를 입력·출력한다.
mode 번호는 CPOL을 상위 bit, CPHA를 하위 bit로 조합한다.
I'm confused. What are these four SPI "clock modes"?
-----------------------------------------------------
It's easy to be confused here, and the vendor documentation you'll
find isn't necessarily helpful. The four modes combine two mode bits:
- CPOL indicates the initial clock polarity. CPOL=0 means the
clock starts low, so the first (leading) edge is rising, and
the second (trailing) edge is falling. CPOL=1 means the clock
starts high, so the first (leading) edge is falling.
- CPHA indicates the clock phase used to sample data; CPHA=0 says
sample on the leading edge, CPHA=1 means the trailing edge.
Since the signal needs to stabilize before it's sampled, CPHA=0
implies that its data is written half a clock before the first
clock edge. The chipselect may have made it become available.
Chip specs won't always say "uses SPI mode X" in as many words,
but their timing diagrams will make the CPOL and CPHA modes clear.
In the SPI mode number, CPOL is the high order bit and CPHA is the
low order bit. So when a chip's timing diagram shows the clock
starting low (CPOL=0) and data stabilized for sampling during the
trailing clock edge (CPHA=1), that's SPI mode 1.
Note that the clock mode is relevant as soon as the chipselect goes
active. So the host must set the clock to inactive before selecting
a target, and the target can tell the chosen polarity by sampling the
clock level when its select line goes active. That's why many devices
support for example both modes 0 and 3: they don't care about polarity,
and always clock data in/out on rising clock edges.
Driver interface와 sysfs 모델
128-202세부 programming interface의 kerneldoc은 `<linux/spi/spi.h>`와 주요 source code에 있으며 kernel API 문서도 읽어야 한다. 여기서는 전체 구조를 먼저 설명한다.
SPI request는 항상 I/O queue로 들어간다. 한 SPI device의 request는 FIFO 순서로 실행되고 completion callback을 통해 비동기로 완료된다. command를 쓴 뒤 response를 읽는 흔한 transaction을 포함해 간단한 synchronous wrapper도 제공된다.
SPI driver에는 controller driver와 protocol driver가 있다. Controller는 SoC에 내장될 수 있고 controller와 target 역할을 모두 지원하는 경우가 많다. 이 driver는 hardware register를 다루고 DMA를 사용할 수 있으며, GPIO만 필요한 PIO bitbanger일 수도 있다. Protocol driver는 controller driver를 통해 message를 전달해 SPI link 반대편의 target 또는 controller device와 통신한다.
예를 들어 protocol driver 하나는 MTD layer와 통신해 DataFlash 같은 SPI flash의 filesystem data를 공개하고, 다른 driver는 audio interface, touchscreen input, 산업 공정의 temperature·voltage monitor를 제공할 수 있다. 이들이 같은 controller driver를 공유할 수 있다. `struct spi_device`는 두 driver 유형 사이 controller 측 interface를 캡슐화한다.
SPI core는 driver model과 board별 초기화 code의 device table을 사용해 controller driver와 protocol driver를 연결하는 최소 interface에 집중한다. SPI는 sysfs 여러 위치에 나타난다.
bus B, chip select C, driver D에 대한 node와 symlink다.
`/sys/class/spi_master/spiB` 아래의 모든 `spiB.*` device는 `SCLK`, `MOSI`, `MISO`가 있는 하나의 physical SPI bus segment를 공유한다. `slave` 파일에 SPI target handler driver 이름을 쓰면 target device를 등록하고 `(null)`을 쓰면 해제한다. 읽으면 등록된 target 이름 또는 `(null)`이 보인다.
SPI target controller가 등록되면 `/sys/class/spi_slave/spiB`에 하나의 `spiB.*` device가 나타나며 다른 SPI target device와 physical bus segment를 공유할 수 있다. 현재 class 전용 상태는 `spiB`의 B인 bus 번호뿐이므로 `/sys/class` 항목은 bus를 빠르게 식별하는 용도다.
board data와 driver core가 controller와 protocol driver를 spi_device로 연결한다.
How do these driver programming interfaces work?
------------------------------------------------
The <linux/spi/spi.h> header file includes kerneldoc, as does the
main source code, and you should certainly read that chapter of the
kernel API document. This is just an overview, so you get the big
picture before those details.
SPI requests always go into I/O queues. Requests for a given SPI device
are always executed in FIFO order, and complete asynchronously through
completion callbacks. There are also some simple synchronous wrappers
for those calls, including ones for common transaction types like writing
a command and then reading its response.
There are two types of SPI driver, here called:
Controller drivers ...
controllers may be built into System-On-Chip
processors, and often support both Controller and target roles.
These drivers touch hardware registers and may use DMA.
Or they can be PIO bitbangers, needing just GPIO pins.
Protocol drivers ...
these pass messages through the controller
driver to communicate with a target or Controller device on the
other side of an SPI link.
So for example one protocol driver might talk to the MTD layer to export
data to filesystems stored on SPI flash like DataFlash; and others might
control audio interfaces, present touchscreen sensors as input interfaces,
or monitor temperature and voltage levels during industrial processing.
And those might all be sharing the same controller driver.
A "struct spi_device" encapsulates the controller-side interface between
those two types of drivers.
There is a minimal core of SPI programming interfaces, focussing on
using the driver model to connect controller and protocol drivers using
device tables provided by board specific initialization code. SPI
shows up in sysfs in several locations::
/sys/devices/.../CTLR ... physical node for a given SPI controller
/sys/devices/.../CTLR/spiB.C ... spi_device on bus "B",
chipselect C, accessed through CTLR.
/sys/bus/spi/devices/spiB.C ... symlink to that physical
.../CTLR/spiB.C device
/sys/devices/.../CTLR/spiB.C/modalias ... identifies the driver
that should be used with this device (for hotplug/coldplug)
/sys/bus/spi/drivers/D ... driver for one or more spi*.* devices
/sys/class/spi_master/spiB ... symlink to a logical node which could hold
class related state for the SPI host controller managing bus "B".
All spiB.* devices share one physical SPI bus segment, with SCLK,
MOSI, and MISO.
/sys/devices/.../CTLR/slave ... virtual file for (un)registering the
target device for an SPI target controller.
Writing the driver name of an SPI target handler to this file
registers the target device; writing "(null)" unregisters the target
device.
Reading from this file shows the name of the target device ("(null)"
if not registered).
/sys/class/spi_slave/spiB ... symlink to a logical node which could hold
class related state for the SPI target controller on bus "B". When
registered, a single spiB.* device is present here, possible sharing
the physical SPI bus segment with other SPI target devices.
At this time, the only class-specific state is the bus number ("B" in "spiB"),
so those /sys/class entries are only useful to quickly identify busses.
보드별 SPI controller 선언
203-272Linux가 SPI device를 올바르게 구성하려면 여러 종류의 정보가 필요하다. 일부 chip이 자동 discovery·enumeration을 지원해도 이 정보는 보통 board별 code가 제공한다.
첫 번째 정보는 존재하는 SPI controller 목록이다. SoC board에서는 보통 platform device이며 controller가 올바르게 동작하도록 `platform_data`가 필요할 수 있다. `struct platform_device`에는 controller 첫 register의 physical address와 IRQ 같은 resource가 들어간다.
Platform은 `register SPI controller` 동작을 추상화하고 pin configuration 초기화와 묶기도 한다. 그러면 여러 board의 `arch/.../mach-*/board-*.c`가 기본 controller setup code를 공유할 수 있다. 대다수 SoC는 SPI 가능한 controller를 여러 개 가지므로 해당 board에서 실제 사용할 수 있는 controller만 setup하고 등록해야 한다.
예제 board code는 `<mach/spi.h>`의 `mysoc_spi_data`를 사용하고 `board_init()`에서 이 board가 쓰는 SPI controller 2만 `mysoc_register_spi(2, &pdata)`로 등록한다. SoC helper는 platform device `spi2`를 준비하고, `platform_data`를 할당해 붙이고, device를 등록하며, 생산 board의 bootloader가 하지 않았을 수 있는 SPI2 pin mode도 설정한다. 원문의 code와 comment는 아래 원문 block에 그대로 보존된다.
같은 SoC controller를 써도 board마다 `platform_data`는 다를 수 있다. 한 board는 외부 clock을 쓰고 다른 board는 현재 master clock 설정에서 SPI clock을 만들 수 있기 때문이다.
board 초기화가 사용할 controller와 board별 data·pin mode를 준비한다.
How does board-specific init code declare SPI devices?
------------------------------------------------------
Linux needs several kinds of information to properly configure SPI devices.
That information is normally provided by board-specific code, even for
chips that do support some of automated discovery/enumeration.
Declare Controllers
^^^^^^^^^^^^^^^^^^^
The first kind of information is a list of what SPI controllers exist.
For System-on-Chip (SOC) based boards, these will usually be platform
devices, and the controller may need some platform_data in order to
operate properly. The "struct platform_device" will include resources
like the physical address of the controller's first register and its IRQ.
Platforms will often abstract the "register SPI controller" operation,
maybe coupling it with code to initialize pin configurations, so that
the arch/.../mach-*/board-*.c files for several boards can all share the
same basic controller setup code. This is because most SOCs have several
SPI-capable controllers, and only the ones actually usable on a given
board should normally be set up and registered.
So for example arch/.../mach-*/board-*.c files might have code like::
#include <mach/spi.h> /* for mysoc_spi_data */
/* if your mach-* infrastructure doesn't support kernels that can
* run on multiple boards, pdata wouldn't benefit from "__init".
*/
static struct mysoc_spi_data pdata __initdata = { ... };
static __init board_init(void)
{
...
/* this board only uses SPI controller #2 */
mysoc_register_spi(2, &pdata);
...
}
And SOC-specific utility code might look something like::
#include <mach/spi.h>
static struct platform_device spi2 = { ... };
void mysoc_register_spi(unsigned n, struct mysoc_spi_data *pdata)
{
struct mysoc_spi_data *pdata2;
pdata2 = kmalloc(sizeof *pdata2, GFP_KERNEL);
*pdata2 = pdata;
...
if (n == 2) {
spi2->dev.platform_data = pdata2;
register_platform_device(&spi2);
/* also: set up pin modes so the spi2 signals are
* visible on the relevant pins ... bootloaders on
* production boards may already have done this, but
* developer boards will often need Linux to do it.
*/
}
...
}
Notice how the platform_data for boards may be different, even if the
same SOC controller is used. For example, on one board SPI might use
an external clock, where another derives the SPI clock from current
settings of some master clock.
Target device 선언과 동적 구성
273-340두 번째 정보는 target board에 존재하는 SPI target device 목록이며, driver가 올바르게 동작하는 데 필요한 board별 data를 함께 제공하는 경우가 많다. 보통 `arch/.../mach-*/board-*.c`의 작은 table에 board의 소수 SPI device를 나열한다.
예제 `ads7846_platform_data`는 `vref_delay_usecs=100`, `x_plate_ohms=580`, `y_plate_ohms=410`을 지정한다. `spi_board_info` 항목은 `modalias=ads7846`, `platform_data=&ads_info`, `mode=SPI_MODE_0`, `irq=GPIO_IRQ(31)`, 3V에서의 최대 sample rate를 반영한 `max_speed_hz=120000 * 16`, `bus_num=1`, `chip_select=0`을 제공한다.
이처럼 각 chip에는 여러 board별 정보가 필요할 수 있다. 허용되는 가장 빠른 SPI clock이나 IRQ 배선 같은 일반 제약과, 특정 pin의 capacitance에 따라 달라지는 중요한 delay 같은 chip 전용 제약이 함께 들어간다. Controller driver에 유용한 peripheral별 DMA tuning 또는 chipselect callback은 `controller_data`로 제공하며 나중에 `spi_device`에 저장된다.
`board_info`는 chip driver가 아직 load되지 않아도 시스템이 동작할 만큼 충분해야 한다. 특히 `spi_device.mode`의 `SPI_CS_HIGH`가 중요하다. chip select 논리를 반대로 해석하는 device와 bus를 공유할 때 infrastructure가 그 device를 deselect하는 법을 알기 전에는 안전하게 공유할 수 없기 때문이다.
Board initialization은 `spi_register_board_info(spi_board_info, ARRAY_SIZE(spi_board_info))`로 table을 SPI infrastructure에 등록한다. 이후 SPI host controller driver가 등록될 때 사용할 수 있으며, 다른 static board setup과 마찬가지로 이 table은 unregister하지 않는다.
Memory와 CPU 등을 약 30제곱센티미터 card에 묶는 card형 computer에서는 `arch/.../mach-.../board-*.c`가 주로 card가 꽂히는 mainboard device 정보를 제공한다. Card connector를 거친 SPI device도 여기에 포함된다.
MMC/SD/SDIO/DataFlash card를 SPI로 지원하는 구성은 동적이다. 이 장치들은 기본 device identification probe를 지원하므로 정상적으로 hotplug할 수 있다.
ADS7846 예제에서 제공하는 board별 선언 값이다.
Declare target Devices
^^^^^^^^^^^^^^^^^^^^^^
The second kind of information is a list of what SPI target devices exist
on the target board, often with some board-specific data needed for the
driver to work correctly.
Normally your arch/.../mach-*/board-*.c files would provide a small table
listing the SPI devices on each board. (This would typically be only a
small handful.) That might look like::
static struct ads7846_platform_data ads_info = {
.vref_delay_usecs = 100,
.x_plate_ohms = 580,
.y_plate_ohms = 410,
};
static struct spi_board_info spi_board_info[] __initdata = {
{
.modalias = "ads7846",
.platform_data = &ads_info,
.mode = SPI_MODE_0,
.irq = GPIO_IRQ(31),
.max_speed_hz = 120000 /* max sample rate at 3V */ * 16,
.bus_num = 1,
.chip_select = 0,
},
};
Again, notice how board-specific information is provided; each chip may need
several types. This example shows generic constraints like the fastest SPI
clock to allow (a function of board voltage in this case) or how an IRQ pin
is wired, plus chip-specific constraints like an important delay that's
changed by the capacitance at one pin.
(There's also "controller_data", information that may be useful to the
controller driver. An example would be peripheral-specific DMA tuning
data or chipselect callbacks. This is stored in spi_device later.)
The board_info should provide enough information to let the system work
without the chip's driver being loaded. The most troublesome aspect of
that is likely the SPI_CS_HIGH bit in the spi_device.mode field, since
sharing a bus with a device that interprets chipselect "backwards" is
not possible until the infrastructure knows how to deselect it.
Then your board initialization code would register that table with the SPI
infrastructure, so that it's available later when the SPI host controller
driver is registered::
spi_register_board_info(spi_board_info, ARRAY_SIZE(spi_board_info));
Like with other static board-specific setup, you won't unregister those.
The widely used "card" style computers bundle memory, cpu, and little else
onto a card that's maybe just thirty square centimeters. On such systems,
your ``arch/.../mach-.../board-*.c`` file would primarily provide information
about the devices on the mainboard into which such a card is plugged. That
certainly includes SPI devices hooked up through the card connectors!
Non-static Configurations
^^^^^^^^^^^^^^^^^^^^^^^^^
When Linux includes support for MMC/SD/SDIO/DataFlash cards through SPI, those
configurations will also be dynamic. Fortunately, such devices all support
basic device identification probes, so they should hotplug normally.
SPI protocol driver 작성
341-466현재 대부분의 SPI driver는 kernel driver지만 userspace driver 지원도 있다. 이 절은 kernel protocol driver만 다룬다. SPI protocol driver는 platform device driver와 비슷하며 `struct spi_driver`에 `.driver.name`, power-management operation, `probe`, `remove` callback을 둔다.
Driver core는 `board_info`의 `modalias`가 `CHIP`인 SPI device에 `CHIP_driver`를 자동 bind하려 한다. Bus를 관리해 `/sys/class/spi_master` 아래 나타나는 device를 만드는 경우가 아니라면 예제 `CHIP_probe()`처럼 board별 data를 확인하고, chip별 상태 memory를 `kzalloc()`으로 할당한 뒤 `spi_set_drvdata()`로 저장한다. 필요한 data가 없으면 `-ENODEV`, memory 할당 실패면 `-ENOMEM`을 반환한다.
`probe()`에 들어온 순간부터 driver는 `struct spi_message`로 SPI I/O request를 보낼 수 있다. `remove()`가 반환하거나 `probe()`가 실패한 뒤에는 더 이상 message를 제출하지 않는다고 driver가 보장한다.
`spi_message`는 하나의 atomic sequence로 실행되는 protocol operation 묶음이다. `spi_transfer` 순서로 bidirectional read/write 시작 시점을 정하고, 각 transfer는 방향별 buffer를 감싼다. 두 pointer를 사용하면 full duplex이며 같은 buffer를 양쪽에 쓸 수도 있다. 한 pointer가 `NULL`이면 half duplex다.
각 transfer 뒤에는 `spi_transfer.delay.value`로 짧은 delay를 선택할 수 있다. Buffer 길이가 0이면 이 delay만 protocol 효과가 될 수 있다. 기본 `spi_transfer.delay.unit`은 microsecond지만 필요하면 clock cycle이나 nanosecond로 바꿀 수 있다. `spi_transfer.cs_change`는 transfer 뒤 chip select 비활성화와 delay를 제어하며, atomic group의 마지막 transfer에서 사용하면 다음 message도 같은 device일 가능성을 알려 deselect/select 비용을 줄일 수 있다.
표준 kernel 규칙에 따라 message에는 DMA-safe buffer를 제공해야 한다. 그러면 DMA controller driver가 hardware errata 때문에 bounce buffer가 필요한 경우가 아니면 불필요한 copy를 하지 않는다. 기본 I/O primitive `spi_async()`는 IRQ handler나 task 등 어떤 context에서도 호출할 수 있고 message의 callback으로 완료를 알린다. 오류를 감지하면 chip을 deselect하고 해당 `spi_message` 처리를 중단한다.
`spi_sync()`, `spi_read()`, `spi_write()`, `spi_write_then_read()` 같은 synchronous wrapper는 sleep 가능한 context에서만 호출하며 모두 `spi_async()` 위의 작고 선택적인 layer다. `spi_write_then_read()`와 convenience wrapper는 추가 copy 비용을 무시할 수 있는 적은 data에만 써야 한다. 예를 들어 `spi_w8r16()`은 8-bit command를 쓰고 16-bit response를 읽는 RPC형 request를 수행한다.
Driver가 transfer mode, word size, clock rate 같은 `spi_device` 특성을 바꿔야 하면 첫 I/O 전에 보통 `probe()`에서 `spi_setup()`을 호출한다. 해당 device에 pending message가 없는 때라면 언제든 호출할 수 있다.
`spi_device`가 driver의 아래 경계라면 위 경계는 sensor reading을 위한 sysfs, input layer, ALSA, networking, MTD, character device framework 또는 다른 Linux subsystem일 수 있다.
SPI 상호작용에서 driver가 관리할 memory는 두 종류다. I/O buffer는 일반 Linux 규칙을 따르는 DMA-safe memory여야 하므로 heap이나 free page pool에서 할당하고 stack 또는 `static` 선언 memory를 쓰지 않는다. I/O buffer를 protocol transaction으로 묶는 `spi_message`·`spi_transfer` metadata는 한 번 할당하는 다른 driver data structure 안을 포함해 편한 곳에 둘 수 있지만 zero-initialize해야 한다. 여러 transfer가 든 `spi_message`를 할당·0 초기화하고 해제하는 `spi_message_alloc()`과 `spi_message_free()`도 제공된다.
호출 context와 대표 용도를 구분한다.
여러 transfer가 하나의 atomic protocol sequence를 이룬다.
How do I write an "SPI Protocol Driver"?
----------------------------------------
Most SPI drivers are currently kernel drivers, but there's also support
for userspace drivers. Here we talk only about kernel drivers.
SPI protocol drivers somewhat resemble platform device drivers::
static struct spi_driver CHIP_driver = {
.driver = {
.name = "CHIP",
.pm = &CHIP_pm_ops,
},
.probe = CHIP_probe,
.remove = CHIP_remove,
};
The driver core will automatically attempt to bind this driver to any SPI
device whose board_info gave a modalias of "CHIP". Your probe() code
might look like this unless you're creating a device which is managing
a bus (appearing under /sys/class/spi_master).
::
static int CHIP_probe(struct spi_device *spi)
{
struct CHIP *chip;
struct CHIP_platform_data *pdata;
/* assuming the driver requires board-specific data: */
pdata = &spi->dev.platform_data;
if (!pdata)
return -ENODEV;
/* get memory for driver's per-chip state */
chip = kzalloc(sizeof *chip, GFP_KERNEL);
if (!chip)
return -ENOMEM;
spi_set_drvdata(spi, chip);
... etc
return 0;
}
As soon as it enters probe(), the driver may issue I/O requests to
the SPI device using "struct spi_message". When remove() returns,
or after probe() fails, the driver guarantees that it won't submit
any more such messages.
- An spi_message is a sequence of protocol operations, executed
as one atomic sequence. SPI driver controls include:
+ when bidirectional reads and writes start ... by how its
sequence of spi_transfer requests is arranged;
+ which I/O buffers are used ... each spi_transfer wraps a
buffer for each transfer direction, supporting full duplex
(two pointers, maybe the same one in both cases) and half
duplex (one pointer is NULL) transfers;
+ optionally defining short delays after transfers ... using
the spi_transfer.delay.value setting (this delay can be the
only protocol effect, if the buffer length is zero) ...
when specifying this delay the default spi_transfer.delay.unit
is microseconds, however this can be adjusted to clock cycles
or nanoseconds if needed;
+ whether the chipselect becomes inactive after a transfer and
any delay ... by using the spi_transfer.cs_change flag;
+ hinting whether the next message is likely to go to this same
device ... using the spi_transfer.cs_change flag on the last
transfer in that atomic group, and potentially saving costs
for chip deselect and select operations.
- Follow standard kernel rules, and provide DMA-safe buffers in
your messages. That way controller drivers using DMA aren't forced
to make extra copies unless the hardware requires it (e.g. working
around hardware errata that force the use of bounce buffering).
- The basic I/O primitive is spi_async(). Async requests may be
issued in any context (irq handler, task, etc) and completion
is reported using a callback provided with the message.
After any detected error, the chip is deselected and processing
of that spi_message is aborted.
- There are also synchronous wrappers like spi_sync(), and wrappers
like spi_read(), spi_write(), and spi_write_then_read(). These
may be issued only in contexts that may sleep, and they're all
clean (and small, and "optional") layers over spi_async().
- The spi_write_then_read() call, and convenience wrappers around
it, should only be used with small amounts of data where the
cost of an extra copy may be ignored. It's designed to support
common RPC-style requests, such as writing an eight bit command
and reading a sixteen bit response -- spi_w8r16() being one its
wrappers, doing exactly that.
Some drivers may need to modify spi_device characteristics like the
transfer mode, wordsize, or clock rate. This is done with spi_setup(),
which would normally be called from probe() before the first I/O is
done to the device. However, that can also be called at any time
that no message is pending for that device.
While "spi_device" would be the bottom boundary of the driver, the
upper boundaries might include sysfs (especially for sensor readings),
the input layer, ALSA, networking, MTD, the character device framework,
or other Linux subsystems.
Note that there are two types of memory your driver must manage as part
of interacting with SPI devices.
- I/O buffers use the usual Linux rules, and must be DMA-safe.
You'd normally allocate them from the heap or free page pool.
Don't use the stack, or anything that's declared "static".
- The spi_message and spi_transfer metadata used to glue those
I/O buffers into a group of protocol transactions. These can
be allocated anywhere it's convenient, including as part of
other allocate-once driver data structures. Zero-init these.
If you like, spi_message_alloc() and spi_message_free() convenience
routines are available to allocate and zero-initialize an spi_message
with several transfers.
SPI controller driver 등록과 bus 번호
467-516SPI controller는 대개 `platform_bus`에 등록되므로 해당 device에 bind하는 driver를 작성한다. 이 driver의 주 임무는 `spi_controller`를 제공하는 것이다. Host controller는 `spi_alloc_host()`로 할당하고 그 device에 함께 할당된 driver-private data는 `spi_controller_get_devdata()`로 얻는다.
Driver는 `spi_controller`의 bus 번호와 SPI core·protocol driver가 상호작용하는 method를 포함한 field, 그리고 자체 내부 상태를 초기화한다. 초기화 뒤 `spi_register_controller()`로 시스템에 공개하면 controller와 미리 선언된 SPI device의 node가 생성되고 driver model core가 driver binding을 처리한다. 제거할 때는 `spi_unregister_controller()`가 등록 효과를 되돌린다.
Bus 번호는 shared `SCK`, `MOSI`, `MISO`로 이루어진 특정 SPI bus를 Linux가 식별하는 값이며 0부터 유효하다. SoC에서는 chip manufacturer가 정의한 hardware controller 번호와 맞춰야 한다. 예를 들어 SPI2는 bus 2이고 여기에 연결된 device의 `spi_board_info`도 2를 쓴다.
Hardware가 정한 bus 번호가 없고 직접 고정 번호를 지정할 수도 없다면 음수 bus 번호를 제공한다. 그러면 동적으로 할당된 번호로 교체되며 이 경우 앞에서 설명한 non-static configuration으로 취급해야 한다.
할당·초기화·등록과 해제 순서다.
How do I write an "SPI Controller Driver"?
-------------------------------------------------
An SPI controller will probably be registered on the platform_bus; write
a driver to bind to the device, whichever bus is involved.
The main task of this type of driver is to provide an "spi_controller".
Use spi_alloc_host() to allocate the host controller, and
spi_controller_get_devdata() to get the driver-private data allocated for that
device.
::
struct spi_controller *ctlr;
struct CONTROLLER *c;
ctlr = spi_alloc_host(dev, sizeof *c);
if (!ctlr)
return -ENODEV;
c = spi_controller_get_devdata(ctlr);
The driver will initialize the fields of that spi_controller, including the bus
number (maybe the same as the platform device ID) and three methods used to
interact with the SPI core and SPI protocol drivers. It will also initialize
its own internal state. (See below about bus numbering and those methods.)
After you initialize the spi_controller, then use spi_register_controller() to
publish it to the rest of the system. At that time, device nodes for the
controller and any predeclared spi devices will be made available, and
the driver model core will take care of binding them to drivers.
If you need to remove your SPI controller driver, spi_unregister_controller()
will reverse the effect of spi_register_controller().
Bus Numbering
^^^^^^^^^^^^^
Bus numbering is important, since that's how Linux identifies a given
SPI bus (shared SCK, MOSI, MISO). Valid bus numbers start at zero. On
SOC systems, the bus numbers should match the numbers defined by the chip
manufacturer. For example, hardware controller SPI2 would be bus number 2,
and spi_board_info for devices connected to it would use that number.
If you don't have such hardware-assigned bus number, and for some reason
you can't just assign them, then provide a negative bus number. That will
then be replaced by a dynamically assigned number. You'd then need to treat
this as a non-static configuration (see above).
SPI host controller method
517-591`ctlr->setup(struct spi_device *spi)`는 device clock rate, SPI mode, word size를 설정한다. Driver는 `board_info` 기본값을 바꾼 뒤 `spi_setup(spi)`로 이 routine을 호출할 수 있으며 sleep할 수 있다. Target마다 전용 configuration register가 없다면 즉시 register를 바꾸면 안 된다. 다른 SPI device의 진행 중 I/O를 손상시킬 수 있기 때문이다. 특히 `setup()`을 작성할 때 controller가 다른 device의 transfer를 적극 처리 중이라고 가정해야 한다는 경고가 있다.
`ctlr->cleanup(struct spi_device *spi)`는 controller driver가 `spi_device.controller_state`에 동적으로 연결한 상태를 해제한다. 해당 field를 쓴다면 반드시 `cleanup()`을 제공해야 한다.
Queue는 message가 곧 들어올 때 `ctlr->prepare_transfer_hardware()`를 호출해 transfer hardware 준비를 요청하고, pending message가 없어지면 `ctlr->unprepare_transfer_hardware()`를 호출해 power management 등으로 hardware를 쉬게 한다. 두 method 모두 sleep할 수 있다.
`ctlr->transfer_one_message()`는 도착하는 transfer를 queue하면서 message 하나를 전송한다. 끝나면 반드시 `spi_finalize_current_message()`를 호출해 subsystem이 다음 message를 내보내게 해야 하며 sleep할 수 있다.
원문에 `ctrl->transfer_one()`으로 표기된 method는 transfer 하나를 처리하고 동시에 새 transfer를 queue한다. 완료 시 `spi_finalize_current_transfer()`를 호출한다. Sleep할 수 있으며 `transfer_one`과 `transfer_one_message`는 상호 배타적이다. 둘 다 설정되면 generic subsystem은 `transfer_one` callback을 호출하지 않는다. 반환값은 음수 errno가 오류, 0이 완료, 1이 진행 중이라는 뜻이다.
원문에 `ctrl->set_cs_timing()`으로 표기된 method는 SPI client driver가 device별 chip-select setup, hold, inactive timing을 clock cycle 단위로 host controller에 요청하게 한다.
사용 중단된 `ctrl->transfer()`는 sleep하면 안 된다. Transfer가 일어나고 `complete()` callback이 호출되도록 배치하는 책임이 있으며 보통 다른 transfer가 끝난 뒤 비동기로 일어난다. Controller가 idle이면 시작시켜야 한다. Queued controller에서는 쓰지 않으며 `transfer_one_message()`와 `(un)prepare_transfer_hardware()`를 구현했다면 `NULL`이어야 한다.
SPI core가 호출하는 주요 callback과 완료 조건이다.
SPI Host Controller Methods
^^^^^^^^^^^^^^^^^^^^^^^^^^^
``ctlr->setup(struct spi_device *spi)``
This sets up the device clock rate, SPI mode, and word sizes.
Drivers may change the defaults provided by board_info, and then
call spi_setup(spi) to invoke this routine. It may sleep.
Unless each SPI target has its own configuration registers, don't
change them right away ... otherwise drivers could corrupt I/O
that's in progress for other SPI devices.
.. note::
BUG ALERT: for some reason the first version of
many spi_controller drivers seems to get this wrong.
When you code setup(), ASSUME that the controller
is actively processing transfers for another device.
``ctlr->cleanup(struct spi_device *spi)``
Your controller driver may use spi_device.controller_state to hold
state it dynamically associates with that device. If you do that,
be sure to provide the cleanup() method to free that state.
``ctlr->prepare_transfer_hardware(struct spi_controller *ctlr)``
This will be called by the queue mechanism to signal to the driver
that a message is coming in soon, so the subsystem requests the
driver to prepare the transfer hardware by issuing this call.
This may sleep.
``ctlr->unprepare_transfer_hardware(struct spi_controller *ctlr)``
This will be called by the queue mechanism to signal to the driver
that there are no more messages pending in the queue and it may
relax the hardware (e.g. by power management calls). This may sleep.
``ctlr->transfer_one_message(struct spi_controller *ctlr, struct spi_message *mesg)``
The subsystem calls the driver to transfer a single message while
queuing transfers that arrive in the meantime. When the driver is
finished with this message, it must call
spi_finalize_current_message() so the subsystem can issue the next
message. This may sleep.
``ctrl->transfer_one(struct spi_controller *ctlr, struct spi_device *spi, struct spi_transfer *transfer)``
The subsystem calls the driver to transfer a single transfer while
queuing transfers that arrive in the meantime. When the driver is
finished with this transfer, it must call
spi_finalize_current_transfer() so the subsystem can issue the next
transfer. This may sleep. Note: transfer_one and transfer_one_message
are mutually exclusive; when both are set, the generic subsystem does
not call your transfer_one callback.
Return values:
* negative errno: error
* 0: transfer is finished
* 1: transfer is still in progress
``ctrl->set_cs_timing(struct spi_device *spi, u8 setup_clk_cycles, u8 hold_clk_cycles, u8 inactive_clk_cycles)``
This method allows SPI client drivers to request SPI host controller
for configuring device specific CS setup, hold and inactive timing
requirements.
Deprecated Methods
^^^^^^^^^^^^^^^^^^
``ctrl->transfer(struct spi_device *spi, struct spi_message *message)``
This must not sleep. Its responsibility is to arrange that the
transfer happens and its complete() callback is issued. The two
will normally happen later, after other transfers complete, and
if the controller is idle it will need to be kickstarted. This
method is not used on queued controllers and must be NULL if
transfer_one_message() and (un)prepare_transfer_hardware() are
implemented.
SPI message queue
592-616SPI subsystem의 표준 queueing mechanism을 사용할 수 있다면 앞 절의 queued method만 구현하면 된다. Message queue는 많은 code를 중앙화하고 method를 순수 process context에서 실행하게 하며, 우선순위가 높은 SPI traffic에서는 realtime priority로 높일 수도 있다.
SPI subsystem queue를 선택하지 않으면 driver 대부분이 이제는 사용 중단된 `transfer()`가 공급하는 I/O queue를 직접 관리하게 된다. 낮은 빈도의 sensor access만 처리하는 driver라면 synchronous PIO를 사용해 queue가 개념적으로만 존재할 수도 있다.
하지만 root filesystem이 SPI flash에 있는 경우처럼 실제 queue는 `message->queue`, PIO, 흔히 DMA, IRQ handler·tasklet·workqueue(예: keventd) 같은 execution context를 사용할 가능성이 크다. Driver는 필요만큼 단순하거나 정교할 수 있다. 이런 `transfer()`는 보통 message를 queue에 넣고, 이미 실행 중이 아니라면 비동기 transfer engine을 시작한다.
SPI core가 queued callback을 순서대로 실행한다.
SPI Message Queue
^^^^^^^^^^^^^^^^^
If you are happy with the standard queueing mechanism provided by the
SPI subsystem, just implement the queued methods specified above. Using
the message queue has the upside of centralizing a lot of code and
providing pure process-context execution of methods. The message queue
can also be elevated to realtime priority on high-priority SPI traffic.
Unless the queueing mechanism in the SPI subsystem is selected, the bulk
of the driver will be managing the I/O queue fed by the now deprecated
function transfer().
That queue could be purely conceptual. For example, a driver used only
for low-frequency sensor access might be fine using synchronous PIO.
But the queue will probably be very real, using message->queue, PIO,
often DMA (especially if the root filesystem is in SPI flash), and
execution contexts like IRQ handlers, tasklets, or workqueues (such
as keventd). Your driver can be as fancy, or as simple, as you need.
Such a transfer() method would normally just add the message to a
queue, and then start some asynchronous transfer engine (unless it's
already running).
SPI protocol 확장과 mode 0 파형
617-653SPI에는 공식 specification이나 standard가 없으므로 chip manufacturer가 protocol을 조금씩 다르게 구현할 수 있다. 대부분 vendor의 구현은 서로 호환된다. 일반적인 SPI mode 0은 `CPOL=0`, `CPHA=0`이며 chip select가 low인 동안 여덟 SCLK pulse로 MOSI와 MISO 한 byte를 동시에 이동한다.
원문 파형에서 `•`는 전송 시작·끝, `:`는 data가 peripheral로 clock-in되는 시점, `;`는 controller로 clock-in되는 시점, `X`는 line state가 지정되지 않은 구간을 뜻한다. 예제에서 controller는 MOSI로 `0xA5`, peripheral은 MISO로 `0xBA`를 전송한다.
드물게 chip은 CS가 assert되지 않았을 때의 data line state처럼 다른 SPI protocol이 규정하지 않는 line behavior를 추가한다. 서로 다른 protocol·mode·configuration은 각기 다른 SPI mode flag로 지원한다.
원문의 ASCII timing diagram을 edge·data 기준으로 구조화했다.
한 clock cycle마다 양방향 bit가 동시에 이동한다.
Extensions to the SPI protocol
------------------------------
The fact that SPI doesn't have a formal specification or standard permits chip
manufacturers to implement the SPI protocol in slightly different ways. In most
cases, SPI protocol implementations from different vendors are compatible among
each other. For example, in SPI mode 0 (CPOL=0, CPHA=0) the bus lines may behave
like the following:
::
nCSx ___ ___
\_________________________________________________________________/
• •
• •
SCLK ___ ___ ___ ___ ___ ___ ___ ___
_______/ \___/ \___/ \___/ \___/ \___/ \___/ \___/ \_____
• : ; : ; : ; : ; : ; : ; : ; : ; •
• : ; : ; : ; : ; : ; : ; : ; : ; •
MOSI XXX__________ _______ _______ ________XXX
0xA5 XXX__/ 1 \_0_____/ 1 \_0_______0_____/ 1 \_0_____/ 1 \_XXX
• ; ; ; ; ; ; ; ; •
• ; ; ; ; ; ; ; ; •
MISO XXX__________ _______________________ _______ XXX
0xBA XXX__/ 1 \_____0_/ 1 1 1 \_____0__/ 1 \____0__XXX
Legend::
• marks the start/end of transmission;
: marks when data is clocked into the peripheral;
; marks when data is clocked into the controller;
X marks when line states are not specified.
In some few cases, chips extend the SPI protocol by specifying line behaviors
that other SPI protocols don't (e.g. data line state for when CS is not
asserted). Those distinct SPI protocols, modes, and configurations are supported
by different SPI mode flags.
MOSI idle 상태 구성
654-699일반 SPI protocol은 controller가 data를 clock-out하지 않을 때 MOSI line의 상태나 동작을 규정하지 않는다. 하지만 idle 동안 특정 MOSI state를 요구하는 peripheral이 있다. Controller가 data를 보내지 않을 때 MOSI가 high여야 하는 장치는 `SPI_MOSI_IDLE_HIGH`를 요구한다.
원문의 mode 0 예제는 MOSI로 `0x56`, MISO로 `0xBA`를 전송한다. 일반 파형과 같은 `•`, `:`, `;`, `X` 범례를 사용하지만 MOSI는 CS가 assert된 상태에서 clock이 없는 구간과 CS가 assert되지 않은 구간 모두 high로 유지된다.
이 확장이 필요한 peripheral은 자신의 `struct spi_device`의 `mode` attribute에 `SPI_MOSI_IDLE_HIGH` bit를 설정하고 `spi_setup()`을 호출해야 한다. 이 확장을 지원하는 controller는 `struct spi_controller`의 `mode_bits`에 `SPI_MOSI_IDLE_HIGH`를 설정한다. MOSI를 low로 idle시키는 구성은 같은 방식으로 `SPI_MOSI_IDLE_LOW` mode bit를 사용한다.
두 mode bit가 clock이 없는 MOSI level을 명시한다.
Peripheral 요청과 controller 지원이 모두 mode bit로 표현된다.
MOSI idle state configuration
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Common SPI protocol implementations don't specify any state or behavior for the
MOSI line when the controller is not clocking out data. However, there do exist
peripherals that require specific MOSI line state when data is not being clocked
out. For example, if the peripheral expects the MOSI line to be high when the
controller is not clocking out data (``SPI_MOSI_IDLE_HIGH``), then a transfer in
SPI mode 0 would look like the following:
::
nCSx ___ ___
\_________________________________________________________________/
• •
• •
SCLK ___ ___ ___ ___ ___ ___ ___ ___
_______/ \___/ \___/ \___/ \___/ \___/ \___/ \___/ \_____
• : ; : ; : ; : ; : ; : ; : ; : ; •
• : ; : ; : ; : ; : ; : ; : ; : ; •
MOSI _____ _______ _______ _______________ ___
0x56 \_0_____/ 1 \_0_____/ 1 \_0_____/ 1 1 \_0_____/
• ; ; ; ; ; ; ; ; •
• ; ; ; ; ; ; ; ; •
MISO XXX__________ _______________________ _______ XXX
0xBA XXX__/ 1 \_____0_/ 1 1 1 \_____0__/ 1 \____0__XXX
Legend::
• marks the start/end of transmission;
: marks when data is clocked into the peripheral;
; marks when data is clocked into the controller;
X marks when line states are not specified.
In this extension to the usual SPI protocol, the MOSI line state is specified to
be kept high when CS is asserted but the controller is not clocking out data to
the peripheral and also when CS is not asserted.
Peripherals that require this extension must request it by setting the
``SPI_MOSI_IDLE_HIGH`` bit into the mode attribute of their ``struct
spi_device`` and call spi_setup(). Controllers that support this extension
should indicate it by setting ``SPI_MOSI_IDLE_HIGH`` in the mode_bits attribute
of their ``struct spi_controller``. The configuration to idle MOSI low is
analogous but uses the ``SPI_MOSI_IDLE_LOW`` mode bit.
기여자
700-714Linux-SPI 논의의 기여자는 성을 기준으로 알파벳순으로 Mark Brown, David Brownell, Russell King, Grant Likely, Dmitry Pervushin, Stephen Street, Mark Underwood, Andrew Victor, Linus Walleij, Vitaly Wool이다. 이름은 원문 표기를 유지한다.
원문이 감사하는 논의 기여자 목록이다.
THANKS TO
---------
Contributors to Linux-SPI discussions include (in alphabetical order,
by last name):
- Mark Brown
- David Brownell
- Russell King
- Grant Likely
- Dmitry Pervushin
- Stephen Street
- Mark Underwood
- Andrew Victor
- Linus Walleij
- Vitaly Wool
요약·해설
spi-summary.rst:1-714Linux SPI의 4선·3선 signaling, CPOL/CPHA clock mode, board별 controller·target 선언, protocol/controller driver API, message queue와 MOSI idle 확장을 설명합니다. 두 원문 timing diagram은 sample edge와 idle line 상태를 보존한 구조화 표·흐름도로 다시 구성합니다.