coreboot
coreboot is an Open Source project aimed at replacing the proprietary BIOS found in most computers.
spi.c File Reference
#include <device/mmio.h>
#include <assert.h>
#include <console/console.h>
#include <endian.h>
#include <soc/addressmap.h>
#include <soc/spi.h>
#include <soc/clock.h>
#include <spi-generic.h>
#include <spi_flash.h>
#include <timer.h>
Include dependency graph for spi.c:

Go to the source code of this file.

Data Structures

union  cavium_spi_cfg
 
union  cavium_spi_sts
 
union  cavium_spi_tx
 
struct  cavium_spi
 
struct  cavium_spi_slave
 

Macros

#define SPI_TIMEOUT_US   5000
 

Functions

 check_member (cavium_spi, cfg, 0)
 
 check_member (cavium_spi, sts, 0x8)
 
 check_member (cavium_spi, tx, 0x10)
 
 check_member (cavium_spi, dat[7], 0xb8)
 
static struct cavium_spi_slaveto_cavium_spi (const struct spi_slave *slave)
 
void spi_enable (const size_t bus)
 Enable the SPI controller. More...
 
void spi_disable (const size_t bus)
 Disable the SPI controller. More...
 
void spi_set_cs (const size_t bus, const size_t chip_select, const size_t assert_is_low)
 Set SPI Chip select line and level if asserted. More...
 
void spi_set_clock (const size_t bus, const size_t speed_hz, const size_t idle_low, const size_t idle_cycles)
 Set SPI clock frequency. More...
 
uint64_t spi_get_clock (const size_t bus)
 Get current SPI clock frequency in Hz. More...
 
void spi_set_lsbmsb (const size_t bus, const size_t lsb_first)
 Set SPI LSB/MSB first. More...
 
void spi_init_custom (const size_t bus, const size_t speed_hz, const size_t idle_low, const size_t idle_cycles, const size_t lsb_first, const size_t chip_select, const size_t assert_is_low)
 Init SPI with custom parameters and enable SPI controller. More...
 
void spi_init (void)
 Init all SPI controllers with default values and enable all SPI controller. More...
 
static int cavium_spi_wait (struct cavium_spi *regs)
 
static int do_xfer (const struct spi_slave *slave, struct spi_op *vector, int leavecs)
 
static int spi_ctrlr_xfer_vector (const struct spi_slave *slave, struct spi_op vectors[], size_t count)
 

Variables

static struct cavium_spi_slave cavium_spi_slaves []
 
static const struct spi_ctrlr spi_ctrlr
 
const struct spi_ctrlr_buses spi_ctrlr_bus_map []
 
const size_t spi_ctrlr_bus_map_count = ARRAY_SIZE(spi_ctrlr_bus_map)
 

Macro Definition Documentation

◆ SPI_TIMEOUT_US

#define SPI_TIMEOUT_US   5000

Definition at line 86 of file spi.c.

Function Documentation

◆ cavium_spi_wait()

static int cavium_spi_wait ( struct cavium_spi regs)
static

Definition at line 291 of file spi.c.

References BIOS_DEBUG, cavium_spi_sts::busy, printk, read64(), cavium_spi_sts::s, SPI_TIMEOUT_US, stopwatch_expired(), stopwatch_init_usecs_expire(), and cavium_spi_sts::u.

Referenced by do_xfer().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ check_member() [1/4]

check_member ( cavium_spi  ,
cfg  ,
 
)

◆ check_member() [2/4]

check_member ( cavium_spi  ,
dat  [7],
0xb8   
)

◆ check_member() [3/4]

check_member ( cavium_spi  ,
sts  ,
0x8   
)

◆ check_member() [4/4]

check_member ( cavium_spi  ,
tx  ,
0x10   
)

◆ do_xfer()

static int do_xfer ( const struct spi_slave slave,
struct spi_op vector,
int  leavecs 
)
static

The CN81xx SPI controller is half-duplex and has 8 data registers. If >8 bytes remain in the transfer then we must set LEAVECS = 1 so that the /CS remains asserted. Once <=8 bytes remain we must set LEAVECS = 0 so that /CS is de-asserted, thus completing the transfer.

Definition at line 306 of file spi.c.

References BIOS_ERR, spi_op::bytesin, spi_op::bytesout, cavium_spi_wait(), cavium_spi_slave::cs, cavium_spi_tx::csid, spi_op::din, spi_op::dout, cavium_spi_tx::leavecs, MIN, printk, read64(), cavium_spi_slave::regs, cavium_spi_sts::rxnum, cavium_spi_sts::s, cavium_spi_tx::s, slave, to_cavium_spi(), cavium_spi_tx::totnum, cavium_spi_tx::txnum, cavium_spi_sts::u, cavium_spi_tx::u, and write64().

Here is the call graph for this function:

◆ spi_ctrlr_xfer_vector()

static int spi_ctrlr_xfer_vector ( const struct spi_slave slave,
struct spi_op  vectors[],
size_t  count 
)
static

Definition at line 380 of file spi.c.

◆ spi_disable()

void spi_disable ( const size_t  bus)

Disable the SPI controller.

Pins are tristated.

Parameters
busThe SPI bus to operate on

Definition at line 127 of file spi.c.

References ARRAY_SIZE, assert, cavium_spi_slaves, cavium_spi::cfg, cavium_spi_cfg::csena, cavium_spi_cfg::enable, read64(), cavium_spi_slave::regs, cavium_spi_cfg::s, cavium_spi_cfg::u, and write64().

Referenced by spi_init(), and spi_init_custom().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ spi_enable()

void spi_enable ( const size_t  bus)

Enable the SPI controller.

Pins are driven.

Parameters
busThe SPI bus to operate on

Definition at line 106 of file spi.c.

References ARRAY_SIZE, assert, cavium_spi_slaves, cavium_spi::cfg, cavium_spi_cfg::csena, cavium_spi_cfg::enable, read64(), cavium_spi_slave::regs, cavium_spi_cfg::s, cavium_spi_cfg::u, and write64().

Referenced by spi_init(), and spi_init_custom().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ spi_get_clock()

uint64_t spi_get_clock ( const size_t  bus)

Get current SPI clock frequency in Hz.

Parameters
busThe SPI bus to operate on

Definition at line 211 of file spi.c.

References ARRAY_SIZE, assert, cavium_spi_slaves, cavium_spi::cfg, cavium_spi_cfg::clkdiv, read64(), cavium_spi_slave::regs, cavium_spi_cfg::s, thunderx_get_io_clock(), and cavium_spi_cfg::u.

Referenced by mainboard_print_info().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ spi_init()

void spi_init ( void  )

Init all SPI controllers with default values and enable all SPI controller.

Definition at line 280 of file spi.c.

References ARRAY_SIZE, cavium_spi_slaves, spi_disable(), spi_enable(), spi_set_clock(), spi_set_cs(), and spi_set_lsbmsb().

Referenced by spi_init_cb().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ spi_init_custom()

void spi_init_custom ( const size_t  bus,
const size_t  speed_hz,
const size_t  idle_low,
const size_t  idle_cycles,
const size_t  lsb_first,
const size_t  chip_select,
const size_t  assert_is_low 
)

Init SPI with custom parameters and enable SPI controller.

Parameters
busThe SPI bus to operate on
speed_hzThe SPI frequency in Hz
idle_lowThe SPI clock idles low
idle_cyclesNumber of CLK cycles between two commands (0 - 3)
lsb_firstThe SPI operates LSB first
chip_selectThe chip select pin to use (0 - 3)
assert_is_lowCS pin state is low when asserted

Definition at line 261 of file spi.c.

References spi_disable(), spi_enable(), spi_set_clock(), spi_set_cs(), and spi_set_lsbmsb().

Referenced by configure_spi_flash().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ spi_set_clock()

void spi_set_clock ( const size_t  bus,
const size_t  speed_hz,
const size_t  idle_low,
const size_t  idle_cycles 
)

Set SPI clock frequency.

Parameters
busThe SPI bus to operate on
speed_hzThe SPI frequency in Hz
idle_lowThe SPI clock idles low
idle_cyclesNumber of CLK cycles between two commands (0 - 3)

Definition at line 180 of file spi.c.

References ARRAY_SIZE, assert, BIOS_DEBUG, cavium_spi_slaves, cavium_spi::cfg, cavium_spi_cfg::clk_cont, cavium_spi_cfg::clkdiv, cavium_spi_cfg::csena, cavium_spi_cfg::idleclks, cavium_spi_cfg::idlelow, MIN, printk, read64(), cavium_spi_slave::regs, cavium_spi_cfg::s, thunderx_get_io_clock(), cavium_spi_cfg::u, and write64().

Referenced by spi_init(), and spi_init_custom().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ spi_set_cs()

void spi_set_cs ( const size_t  bus,
const size_t  chip_select,
const size_t  assert_is_low 
)

Set SPI Chip select line and level if asserted.

Parameters
busThe SPI bus to operate on
chip_selectThe chip select pin to use (0 - 3)
assert_is_lowCS pin state is low when asserted

Definition at line 150 of file spi.c.

References ARRAY_SIZE, assert, cavium_spi_slaves, cavium_spi::cfg, cavium_spi_slave::cs, cavium_spi_cfg::csena, cavium_spi_cfg::cshi, read64(), cavium_spi_slave::regs, cavium_spi_cfg::s, cavium_spi_cfg::u, and write64().

Referenced by spi_init(), and spi_init_custom().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ spi_set_lsbmsb()

void spi_set_lsbmsb ( const size_t  bus,
const size_t  lsb_first 
)

Set SPI LSB/MSB first.

Parameters
busThe SPI bus to operate on
lsb_firstThe SPI operates LSB first

Definition at line 234 of file spi.c.

References ARRAY_SIZE, assert, cavium_spi_slaves, cavium_spi::cfg, cavium_spi_cfg::csena, cavium_spi_cfg::lsbfirst, read64(), cavium_spi_slave::regs, cavium_spi_cfg::s, cavium_spi_cfg::u, and write64().

Referenced by spi_init(), and spi_init_custom().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ to_cavium_spi()

static struct cavium_spi_slave* to_cavium_spi ( const struct spi_slave slave)
static

Definition at line 95 of file spi.c.

References ARRAY_SIZE, assert, spi_slave::bus, cavium_spi_slaves, and slave.

Referenced by do_xfer().

Here is the caller graph for this function:

Variable Documentation

◆ cavium_spi_slaves

struct cavium_spi_slave cavium_spi_slaves[]
static
Initial value:
= {
{
.regs = (struct cavium_spi *)MPI_PF_BAR0,
.cs = 0,
},
}
#define MPI_PF_BAR0
Definition: addressmap.h:116
Definition: spi.c:62

Definition at line 79 of file spi.c.

Referenced by spi_disable(), spi_enable(), spi_get_clock(), spi_init(), spi_set_clock(), spi_set_cs(), spi_set_lsbmsb(), and to_cavium_spi().

◆ spi_ctrlr

const struct spi_ctrlr spi_ctrlr
static
Initial value:
= {
.xfer_vector = spi_ctrlr_xfer_vector,
}
static int spi_ctrlr_xfer_vector(const struct spi_slave *slave, struct spi_op vectors[], size_t count)
Definition: spi.c:380
#define SPI_CTRLR_DEFAULT_MAX_XFER_SIZE
Definition: spi-generic.h:102

Definition at line 380 of file spi.c.

◆ spi_ctrlr_bus_map

const struct spi_ctrlr_buses spi_ctrlr_bus_map[]
Initial value:
= {
{
.ctrlr = &spi_ctrlr,
.bus_start = 0,
.bus_end = ARRAY_SIZE(cavium_spi_slaves) - 1,
},
}
#define ARRAY_SIZE(a)
Definition: helpers.h:12
static struct cavium_spi_slave cavium_spi_slaves[]
Definition: spi.c:88
static const struct spi_ctrlr spi_ctrlr
Definition: spi.c:395

Definition at line 380 of file spi.c.

◆ spi_ctrlr_bus_map_count

const size_t spi_ctrlr_bus_map_count = ARRAY_SIZE(spi_ctrlr_bus_map)

Definition at line 408 of file spi.c.