Commit a1859394 authored by Lucas Russo's avatar Lucas Russo

sm_io/*/ops/sm_pr_spi.c: fix SPI bidirectional CHARLEN/BIDIR register

If we are using SPI in bidir mode, the character
length should be copied to the 7 LSB of
"SPI_PROTO_REG_CFG_BIDIR" and not
"SPI_PROTO_REG_CTRL"
parent 79303448
......@@ -57,14 +57,14 @@
#define SPI_PROTO_CTRL_GO_BSY WBGEN2_GEN_MASK(8, 1)
#define SPI_PROTO_CTRL_BSY WBGEN2_GEN_MASK(8, 1)
#define SPI_PROTO_CTRL_CHAR_LEN_SIZE 7
#define SPI_PROTO_CTRL_CHAR_LEN_SHIFT 0
#define SPI_PROTO_CTRL_CHAR_LEN_MASK WBGEN2_GEN_MASK(SPI_PROTO_CTRL_CHAR_LEN_SHIFT, \
SPI_PROTO_CTRL_CHAR_LEN_SIZE)
#define SPI_PROTO_CTRL_CHAR_LEN_W(value) WBGEN2_GEN_WRITE(value, SPI_PROTO_CTRL_CHAR_LEN_SHIFT, \
SPI_PROTO_CTRL_CHAR_LEN_SIZE)
#define SPI_PROTO_CTRL_CHAR_LEN_R(reg) WBGEN2_GEN_READ(reg, SPI_PROTO_CTRL_CHAR_LEN_SHIFT, \
SPI_PROTO_CTRL_CHAR_LEN_SIZE)
#define SPI_PROTO_CTRL_CHARLEN_SIZE 7
#define SPI_PROTO_CTRL_CHARLEN_SHIFT 0
#define SPI_PROTO_CTRL_CHARLEN_MASK WBGEN2_GEN_MASK(SPI_PROTO_CTRL_CHARLEN_SHIFT, \
SPI_PROTO_CTRL_CHARLEN_SIZE)
#define SPI_PROTO_CTRL_CHARLEN_W(value) WBGEN2_GEN_WRITE(value, SPI_PROTO_CTRL_CHARLEN_SHIFT, \
SPI_PROTO_CTRL_CHARLEN_SIZE)
#define SPI_PROTO_CTRL_CHARLEN_R(reg) WBGEN2_GEN_READ(reg, SPI_PROTO_CTRL_CHARLEN_SHIFT, \
SPI_PROTO_CTRL_CHARLEN_SIZE)
/* read-write whole register */
#define SPI_PROTO_CTRL_SIZE 16
......@@ -101,14 +101,19 @@
#define SPI_PROTO_REG_CFG_BIDIR 0x0000001C
/* Definitions for SPI_PROTO_REG_CFG_BIDIR */
#define SPI_PROTO_CFG_BIDIR_SIZE 1
#define SPI_PROTO_CFG_BIDIR_SHIFT 0
#define SPI_PROTO_CFG_BIDIR_MASK WBGEN2_GEN_MASK(SPI_PROTO_CFG_BIDIR_SHIFT, \
SPI_PROTO_CFG_BIDIR_SIZE)
#define SPI_PROTO_CFG_BIDIR_W(value) WBGEN2_GEN_WRITE(value, SPI_PROTO_CFG_BIDIR_SHIFT, \
SPI_PROTO_CFG_BIDIR_SIZE)
#define SPI_PROTO_CFG_BIDIR_R(reg) WBGEN2_GEN_READ(reg, SPI_PROTO_CFG_BIDIR_SHIFT, \
SPI_PROTO_CFG_BIDIR_SIZE)
#define SPI_PROTO_CFG_BIDIR_CHARLEN_SIZE 7
#define SPI_PROTO_CFG_BIDIR_CHARLEN_SHIFT 0
#define SPI_PROTO_CFG_BIDIR_CHARLEN_MASK WBGEN2_GEN_MASK(SPI_PROTO_CFG_BIDIR_CHARLEN_SHIFT, \
SPI_PROTO_CFG_BIDIR_CHARLEN_SIZE)
#define SPI_PROTO_CFG_BIDIR_CHARLEN_W(value) WBGEN2_GEN_WRITE(value, SPI_PROTO_CFG_BIDIR_CHARLEN_SHIFT, \
SPI_PROTO_CFG_BIDIR_CHARLEN_SIZE)
#define SPI_PROTO_CFG_BIDIR_CHARLEN_R(reg) WBGEN2_GEN_READ(reg, SPI_PROTO_CFG_BIDIR_CHARLEN_SHIFT, \
SPI_PROTO_CFG_BIDIR_CHARLEN_SIZE)
#define SPI_PROTO_CFG_BIDIR_EN_SIZE 1
#define SPI_PROTO_CFG_BIDIR_EN_SHIFT 7
#define SPI_PROTO_CFG_BIDIR_EN WBGEN2_GEN_MASK(SPI_PROTO_CFG_BIDIR_EN_SHIFT, \
SPI_PROTO_CFG_BIDIR_EN_SIZE)
/* For RX data from MISO (single line) */
#define SPI_PROTO_REG_RX0_SINGLE 0x00000020
......
......@@ -293,27 +293,6 @@ static smpr_err_e _spi_init (smpr_t *self)
err_exit, SMPR_ERR_RW_SMIO);
#endif
uint32_t bidir = spi_proto->bidir;
/* Configure BIDIR register */
DBE_DEBUG (DBG_SM_PR | DBG_LVL_TRACE,
"[sm_pr:spi] SPI bidir register = 0x%08X\n", bidir);
rw_err = SET_PARAM(parent, sm_pr_spi, spi_proto->base, SPI_PROTO, CFG_BIDIR, /* field = NULL */,
MULT_BIT_PARAM, /* value */ bidir, /* min */, /* max */,
NO_CHK_FUNC, SET_FIELD);
ASSERT_TEST(rw_err == RW_OK, "Could not set bidir parameter", err_exit,
SMPR_ERR_RW_SMIO);
#ifdef SM_PR_READBACK
/* Readback test */
uint32_t bidir_rb;
smio_thsafe_client_read_32 (parent, spi_proto->base | SPI_PROTO_REG_CFG_BIDIR,
&bidir_rb);
DBE_DEBUG (DBG_SM_PR | DBG_LVL_TRACE,
"[sm_pr:spi] SPI bidir readback value = 0x%08X\n", bidir_rb);
ASSERT_TEST(bidir_rb == bidir, "[sm_pr:spi] SPI Bidirectional readback failed",
err_exit, SMPR_ERR_RW_SMIO);
#endif
err_exit:
err_proto_handler:
return err;
......@@ -329,7 +308,7 @@ static ssize_t _spi_read_write_generic (smpr_t *self, uint8_t *data,
ssize_t num_bytes = 0;
RW_REPLY_TYPE rw_err = RW_OK;
ASSERT_TEST(size > 0 && size*SMPR_BYTE_2_BIT /* bits */ <
SPI_PROTO_CTRL_CHAR_LEN_MASK+1+1, "Invalid size for spi transfer",
SPI_PROTO_CTRL_CHARLEN_MASK+1+1, "Invalid size for spi transfer",
err_inv_size, -1);
smio_t *parent = smpr_get_parent (self);
......@@ -362,13 +341,26 @@ static ssize_t _spi_read_write_generic (smpr_t *self, uint8_t *data,
charlen = 0;
}
rw_err = SET_PARAM(parent, sm_pr_spi, spi_proto->base, SPI_PROTO, CTRL, CHAR_LEN,
MULT_BIT_PARAM, /* value */ charlen, /* min */ , /* max */,
NO_CHK_FUNC, SET_FIELD);
ASSERT_TEST(rw_err == RW_OK, "Could not set CHAR_LEN parameter", err_exit, -1);
/* If we are using the reguler four-mode SPI, the character length register
* used if the regular SPI_PROTO_REG_CTRL. Otherwise, it is the 7 LSB of
* SPI_PROTO_REG_CFG_BIDIR */
if (!spi_proto->bidir) {
rw_err = SET_PARAM(parent, sm_pr_spi, spi_proto->base, SPI_PROTO, CTRL, CHARLEN,
MULT_BIT_PARAM, /* value */ charlen, /* min */ , /* max */,
NO_CHK_FUNC, SET_FIELD);
}
else {
rw_err = SET_PARAM(parent, sm_pr_spi, spi_proto->base, SPI_PROTO, CFG_BIDIR, CHARLEN,
MULT_BIT_PARAM, /* value */ charlen, /* min */ , /* max */,
NO_CHK_FUNC, SET_FIELD);
rw_err |= SET_PARAM(parent, sm_pr_spi, spi_proto->base, SPI_PROTO, CFG_BIDIR, EN,
SINGLE_BIT_PARAM, /* value */ 0x1, /* min */ , /* max */,
NO_CHK_FUNC, SET_FIELD);
}
ASSERT_TEST(rw_err == RW_OK, "Could not set CHARLEN/BIDIR parameter", err_exit, -1);
DBE_DEBUG (DBG_SM_PR | DBG_LVL_TRACE,
"[sm_pr:spi] _spi_rw_generic: Charecter Length = 0x%08X\n",
charlen);
"[sm_pr:spi] _spi_rw_generic: Charecter Length = 0x%08X, Bidir = 0x%08X\n",
charlen, spi_proto->bidir);
/* Write data to TX regs */
if (mode == SPI_MODE_WRITE || mode == SPI_MODE_WRITE_READ) {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment