Add SPI_tools spi_ctl Function

main
jianglk.darker 4 months ago
parent a2ed455462
commit 70a66d9bf5

@ -120,4 +120,86 @@ cc_binary {
"-O2",
],
clang: true,
}
}
cc_binary {
name: "spi_tools",
vendor: true,
srcs: [
"spi_tools.c",
],
include_dirs: [
"vendor/platform/secure_c/include",
],
header_libs: [
"libuapi_spi_headers",
"drv_generic_headers",
"drv_spi_headers",
"libuapi_common_headers",
],
shared_libs: [
"liblog",
"libuapi_securec",
"libuapi_spi",
"libuapi_common",
],
cflags: [
"-DCONFIG_SOCT_LOG_SUPPORT",
"-Wformat",
"-Wlong-long",
"-Wpointer-arith",
"-Werror",
"-fstack-protector-all",
"-fPIC",
"-D_FORTIFY_SOURCE=2",
"-Wall",
"-O2",
],
clang: true,
}
cc_binary {
name: "spi_ctl",
vendor: true,
srcs: [
"spi_ctl.c",
],
include_dirs: [
"vendor/platform/secure_c/include",
],
header_libs: [
"libuapi_spi_headers",
"drv_generic_headers",
"drv_spi_headers",
"libuapi_common_headers",
],
shared_libs: [
"liblog",
"libuapi_securec",
"libuapi_spi",
"libuapi_common",
],
cflags: [
"-DCONFIG_SOCT_LOG_SUPPORT",
"-Wformat",
"-Wlong-long",
"-Wpointer-arith",
"-Werror",
"-fstack-protector-all",
"-fPIC",
"-D_FORTIFY_SOURCE=2",
"-Wall",
"-O2",
],
clang: true,
}

@ -16,7 +16,7 @@ CFLAGS := -I$(USR_DIR)/include \
-I$(USR_DIR)/securec \
-I$(SAMPLE_DIR)/common
SAMPLE_IMAGES := sample_spi_write sample_spi_loopback sample_spi_read
SAMPLE_IMAGES := sample_spi_write sample_spi_loopback sample_spi_read spi_tools spi_ctl
DEPEND_LIBS := -luapi_memory -luapi_common -luapi_securec

@ -1,3 +1,5 @@
PRODUCT_PACKAGES += \
sample_spi_write \
sample_spi_loopback
sample_spi_loopback \
spi_tools \
spi_ctl

@ -0,0 +1,397 @@
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <string.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>
#include <sys/ioctl.h>
#define SPI_SUCCESS 0
#define SPI_FAIL -1
typedef struct {
uint32_t ch;
int32_t handle;
}spi_property_desc;
typedef void *HANDLE;
#define HI_SPI_NODE_PATH "/dev/soc_spi"
#define MAX_CH 2
#define SPI_HANDLE(handle) ((spi_property_desc *)handle)
typedef struct {
uint8_t dev_id;
uint8_t *s_data;
uint32_t s_data_cnt;
} spi_data_s;
typedef struct {
uint8_t dev_id;
uint32_t s_data;
uint32_t s_data_cnt;
} spi_data_compat_s;
typedef struct {
uint8_t dev_id;
uint8_t *s_data;
uint32_t s_data_cnt;
uint8_t *r_data;
uint32_t r_data_cnt;
} spi_dataex_s;
typedef struct {
uint8_t dev_id;
uint32_t s_data;
uint32_t s_data_cnt;
uint32_t r_data;
uint32_t r_data_cnt;
} spi_dataex_compat_s;
typedef struct {
uint8_t dev_id;
uint8_t mode;
uint8_t spo;
uint8_t sph;
uint8_t dss;
uint8_t cscfg;
} spi_fform_s;
typedef struct {
uint8_t dev_id;
uint32_t set_bend;
} spi_blend_s;
typedef struct {
uint8_t dev_id;
uint8_t set_loop;
} spi_loop_s;
#define MAX_SPI_CHANNEL 4
#define SOC_ID_SPI 23
#define CMD_SPI_READ _IOWR(SOC_ID_SPI, 0x1, spi_data_s)
#define CMD_COMPAT_SPI_READ _IOWR(SOC_ID_SPI, 0x1, spi_data_compat_s)
#define CMD_SPI_WRITE _IOWR(SOC_ID_SPI, 0x2, spi_data_s)
#define CMD_COMPAT_SPI_WRITE _IOWR(SOC_ID_SPI, 0x2, spi_data_compat_s)
#define CMD_SPI_SET_ATTR _IOWR(SOC_ID_SPI, 0x3, spi_fform_s)
#define CMD_SPI_GET_ATTR _IOWR(SOC_ID_SPI, 0x4, spi_fform_s)
#define CMD_SPI_OPEN _IOW (SOC_ID_SPI, 0x5, uint32_t)
#define CMD_SPI_CLOSE _IOW (SOC_ID_SPI, 0x6, uint32_t)
#define CMD_SPI_SET_BLEND _IOWR(SOC_ID_SPI, 0x7, spi_blend_s)
#define CMD_SPI_GET_BLEND _IOWR(SOC_ID_SPI, 0x8, spi_blend_s)
#define CMD_SPI_SET_CLK _IOW (SOC_ID_SPI, 0x9, uint32_t)
#define CMD_SPI_READEX _IOWR(SOC_ID_SPI, 0xa, spi_dataex_s)
#define CMD_COMPAT_SPI_READEX _IOWR(SOC_ID_SPI, 0xa, spi_dataex_compat_s)
#define CMD_SPI_SET_LOOP _IOW (SOC_ID_SPI, 0xb, spi_loop_s)
#define CMD_SPI_RW_LOOP _IOWR(SOC_ID_SPI, 0xc, spi_dataex_s)
#define CMD_COMPAT_SPI_RW_LOOP _IOWR(SOC_ID_SPI, 0xc, spi_dataex_compat_s)
HANDLE spi_init(uint32_t ch)
{
spi_property_desc *handle = malloc(sizeof(spi_property_desc));
if(handle == NULL) return NULL;
handle->handle = open(HI_SPI_NODE_PATH, O_RDWR,0);
if(handle->handle < 0)
{
printf("open dev %s fail.errno:%d,errstr:%s\n",HI_SPI_NODE_PATH,errno,strerror(errno));
free(handle);
return NULL;
}
if(ch >= MAX_CH)
{
printf("spi init fail. ch:%d is invalid\n",ch);
close(handle->handle);
free(handle);
return NULL;
}
handle->ch = ch;
if(ioctl(handle->handle, CMD_SPI_OPEN, ch)!=0)
{
printf("spi init fail. open spi%d fail.errno:%d,errstr:%s\n",ch,errno,strerror(errno));
close(handle->handle);
free(handle);
return NULL;
}
spi_fform_s fform = {0};
fform.dev_id = ch;
fform.mode = 0;
fform.spo = 0;
fform.sph = 1;
fform.dss = 16;
fform.cscfg = 0;
if(ioctl(handle->handle, CMD_SPI_SET_ATTR, &fform)!=0)
{
printf("spi init fail. open spi%d set attr fail.errno:%d,errstr:%s\n",ch,errno,strerror(errno));
close(handle->handle);
free(handle);
return NULL;
}
spi_blend_s bigend = {0};
bigend.dev_id = ch;
bigend.set_bend = 1;
if(ioctl(handle->handle, CMD_SPI_SET_BLEND, &bigend)!=0)
{
printf("spi init fail. open spi%d set blend fail.errno:%d,errstr:%s\n",ch,errno,strerror(errno));
close(handle->handle);
free(handle);
return NULL;
}
return handle;
}
void spi_deinit(HANDLE handle)
{
if(handle == NULL) return;
ioctl(SPI_HANDLE(handle)->handle, CMD_SPI_CLOSE, SPI_HANDLE(handle)->ch);
close(SPI_HANDLE(handle)->handle);
free(handle);
handle = NULL;
}
int8_t spi_read(HANDLE handle,uint8_t *data,uint32_t len)
{
if(handle == NULL) return -1;
spi_data_s spi_data = {0};
spi_data.dev_id = SPI_HANDLE(handle)->ch;
spi_data.s_data = data;
spi_data.s_data_cnt = len;
if(ioctl(SPI_HANDLE(handle)->handle,CMD_SPI_READ,&data) != 0)
{
printf("spi read fail.errno:%d,errstr:%s\n",errno,strerror(errno));
return -1;
}
return 0;
}
int8_t spi_write(HANDLE handle,uint8_t *data,uint32_t len)
{
if(handle == NULL) return -1;
spi_data_s spi_data = {0};
spi_data.dev_id = SPI_HANDLE(handle)->ch;
spi_data.s_data = data;
spi_data.s_data_cnt = len;
if(ioctl(SPI_HANDLE(handle)->handle,CMD_SPI_WRITE,&data) != 0)
{
printf("spi write fail.errno:%d,errstr:%s\n",errno,strerror(errno));
return -1;
}
return 0;
}
int8_t spi_transmit(HANDLE handle,uint8_t *w_data,uint32_t w_len,uint8_t *r_data,uint32_t r_len)
{
if(handle == NULL) return -1;
spi_dataex_s data = {0};
data.dev_id = SPI_HANDLE(handle)->ch;
data.s_data = w_data;
data.s_data_cnt = w_len;
data.r_data = r_data;
data.r_data_cnt = r_len;
if(ioctl(SPI_HANDLE(handle)->handle,CMD_SPI_READEX,&data) != 0)
{
printf("spi transmit fail.errno:%d,errstr:%s\n",errno,strerror(errno));
return -1;
}
return 0;
}
//spi_ctl 0 type
void PrintUsage()
{
printf("Usage: spi_ctl <ch> <type>\n");
printf("\t type r:<read_number>\n");
printf("\t type w:<write_number> <write_data0> <write_data n>\n");
printf("\t type t:<write_number> <read_number> <write_data0> <write_data n>\n");
}
#define CMD_TYPE_R "r"
#define CMD_TYPE_W "w"
#define CMD_TYPE_T "t"
int main(int argc,char **argv)
{
if(argc < 2)
{
printf("invalid parameter.\n");
PrintUsage();
return 0;
}
uint32_t ch =(uint32_t)strtol(argv[1], NULL, 0);
HANDLE handle = spi_init(ch);
if(handle == NULL)
return 0;
char *type = argv[2];
if(strcmp(type,CMD_TYPE_R)==0)
{
if(argc < 3)
{
printf("invalid parameter.\n");
PrintUsage();
spi_deinit(handle);
return 0;
}
uint32_t r_len = (uint32_t)strtol(argv[3], NULL, 0);
uint8_t *r_data = (uint8_t *)malloc(r_len);
if(r_data == NULL)
{
printf("malloc r_data size %d fail.\n",r_len);
PrintUsage();
spi_deinit(handle);
return 0;
}
memset(r_data,0,r_len);
if(spi_read(handle,r_data,r_len)!=SPI_SUCCESS)
{
free(r_data);
PrintUsage();
spi_deinit(handle);
printf("recv bytes:\n");
for(int i=0;i<r_len;i++) printf("<0x%02X>",r_data[i]);
printf("\n");
return 0;
}
printf("recv bytes:\n");
for(int i=0;i<r_len;i++) printf("<0x%02X>",r_data[i]);
printf("\n");
free(r_data);
}
else if(strcmp(type,CMD_TYPE_W)==0)
{
if(argc < 3)
{
printf("invalid parameter.\n");
PrintUsage();
spi_deinit(handle);
return 0;
}
uint32_t w_len = (uint32_t)strtol(argv[3], NULL, 0);
uint8_t *w_data = (uint8_t *)malloc(w_len);
if(w_data == NULL)
{
printf("malloc w_data size %d fail.\n",w_len);
PrintUsage();
spi_deinit(handle);
return 0;
}
memset(w_data,0,w_len);
for(int i=0;i<w_len;i++) w_data[i] = (uint8_t)strtol(argv[4+i], NULL, 0);
if(spi_write(handle,w_data,w_len)!=SPI_SUCCESS)
{
free(w_data);
PrintUsage();
spi_deinit(handle);
return 0;
}
printf("spi%d write data success.\n",ch);
free(w_data);
}
else if(strcmp(type,CMD_TYPE_T)==0)
{
if(argc < 4)
{
printf("invalid parameter.\n");
PrintUsage();
spi_deinit(handle);
return 0;
}
uint32_t w_len = (uint32_t)strtol(argv[3], NULL, 0);
uint32_t r_len = (uint32_t)strtol(argv[4], NULL, 0);
uint8_t *w_data = (uint8_t *)malloc(w_len);
if(w_data == NULL)
{
printf("malloc w_data size %d fail.\n",w_len);
PrintUsage();
spi_deinit(handle);
return 0;
}
memset(w_data,0,w_len);
uint8_t *r_data = (uint8_t *)malloc(r_len);
if(r_data == NULL)
{
printf("malloc r_data size %d fail.\n",r_len);
free(w_data);
PrintUsage();
spi_deinit(handle);
return 0;
}
memset(r_data,0,r_len);
for(int i=0;i<w_len;i++) w_data[i] = (uint8_t)strtol(argv[5+i], NULL, 0);
printf("ready write bytes:\n");
for(int i=0;i<w_len;i++) printf("<0x%02X>",w_data[i]);
printf("\n");
if(spi_transmit(handle,w_data,w_len, r_data,r_len)!=SPI_SUCCESS)
{
free(w_data);
free(r_data);
PrintUsage();
spi_deinit(handle);
return 0;
}
printf("recv bytes:\n");
for(int i=0;i<r_len;i++) printf("<0x%02X>",r_data[i]);
printf("\n");
free(w_data);
free(r_data);
}
else
{
printf("invalid parameter.\n");
PrintUsage();
spi_deinit(handle);
return 0;
}
spi_deinit(handle);
return 0;
}

@ -0,0 +1,253 @@
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <string.h>
#include "uapi_spi.h"
#include "uapi_system.h"
void PrintUsage()
{
printf("Usage: spi_tools <ch> <baud> <type>\n");
printf("\t type r:<read_number>\n");
printf("\t type w:<write_number> <write_data0> <write_data n>\n");
printf("\t type t:<write_number> <read_number> <write_data0> <write_data n>\n");
}
#define CMD_TYPE_R "r"
#define CMD_TYPE_W "w"
#define CMD_TYPE_T "t"
int8_t spi_init(uint32_t ch,uint32_t baud,uint32_t dss)
{
uapi_spi_attr attr={0};
if(uapi_spi_init() != TD_SUCCESS)
{
printf("uapi_spi_init failed.\n");
return -1;
}
if(uapi_spi_open(ch)!= TD_SUCCESS)
{
printf("uapi_spi_open failed.\n");
return -1;
}
attr.device = ch;
attr.baud = baud;
attr.cs_cfg = UAPI_SPI_LOGIC_CS;
attr.is_bigend = TD_TRUE;
attr.frame_format = UAPI_SPI_FORMAT_MOTO;
attr.dss = dss;
attr.ext_attr.motorola.spo = UAPI_SPI_SPO_0;
attr.ext_attr.motorola.sph = UAPI_SPI_SPH_1;
if(uapi_spi_set_attr(ch,&attr) != TD_SUCCESS)
{
printf("uapi_spi_set_attr failed.\n");
return -1;
}
return 0;
}
void spi_deinit(uint32_t ch)
{
uapi_spi_deinit();
uapi_spi_close(ch);
}
uint8_t spi_write(uint32_t ch,uint8_t *buf,uint32_t len)
{
if(uapi_spi_write(ch,buf,len)!= TD_SUCCESS)
{
printf("uapi_spi_write failed.\n");
return -1;
}
return 0;
}
uint8_t spi_read(uint32_t ch,uint8_t *buf,uint32_t len)
{
if(uapi_spi_read(ch,buf,len)!= TD_SUCCESS)
{
printf("uapi_spi_write failed.\n");
return -1;
}
return 0;
}
uint8_t spi_transfer(uint32_t ch,uint8_t *wbuf,uint32_t wb,uint8_t *rbuf,uint32_t rb)
{
if(uapi_spi_transmit(ch,wbuf,wb,rbuf,rb)!=TD_SUCCESS)
{
printf("uapi_spi_write failed.\n");
return -1;
}
return 0;
}
int main(int argc,char **argv)
{
if(argc < 3)
{
printf("invalid parameter.\n");
PrintUsage();
return 0;
}
if(uapi_sys_init() != TD_SUCCESS)
{
printf("upai_sys_init failed.\n");
return 0;
}
uint32_t spi_ch = (uint32_t)strtol(argv[1], NULL, 0);
//uint32_t baud = (uint32_t)strtol(argv[2], NULL, 0);
uint32_t baud=16;
uint32_t dss = (uint32_t)strtol(argv[2], NULL, 0);
if(spi_init(spi_ch,baud,dss)!=0)
{
return 0;
}
char *type = argv[3];
if(strcmp(type,CMD_TYPE_R)==0)
{
if(argc < 4)
{
printf("invalid parameter.\n");
PrintUsage();
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
uint32_t rb = (uint32_t)strtol(argv[4], NULL, 0);
uint8_t *rbuf = (uint8_t *)malloc(rb);
if(rbuf == NULL)
{
printf("malloc fail.\n");
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
memset(rbuf,0,rb);
if(spi_read(spi_ch,rbuf,rb)!=0)
{
free(rbuf);
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
for(int i=0;i<rb;i++) printf("%02x ",rbuf[i]);
free(rbuf);
}
else if(strcmp(type,CMD_TYPE_W)==0)
{
if(argc < 4)
{
printf("invalid parameter.\n");
PrintUsage();
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
uint32_t wb = (uint32_t)strtol(argv[4], NULL, 0);
uint8_t *wbuf = (uint8_t *)malloc(wb);
if(wbuf == NULL)
{
printf("malloc fail.\n");
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
memset(wbuf,0,wb);
for(uint32_t i=0;i<wb;i++) wbuf[i] = (uint8_t)strtol(argv[5+i],NULL,0);
if(spi_write(spi_ch,wbuf,wb)!=0)
{
free(wbuf);
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
free(wbuf);
printf("write success.\n");
}
else if(strcmp(type,CMD_TYPE_T)==0)
{
if(argc < 5)
{
printf("invalid parameter.\n");
PrintUsage();
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
uint32_t twb = (uint32_t)strtol(argv[4], NULL, 0);
uint32_t trb = (uint32_t)strtol(argv[5], NULL, 0);
uint8_t *twbuf = (uint8_t *)malloc(twb);
if(twbuf == NULL)
{
printf("twbuf malloc fail.\n");
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
memset(twbuf,0,twb);
uint8_t *trbuf = (uint8_t *)malloc(trb);
if(trbuf == NULL)
{
free(twbuf);
printf("trbuf malloc fail.\n");
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
memset(trbuf,0,trb);
for(uint32_t i=0;i<twb;i++) twbuf[i] = (uint8_t)strtol(argv[6+i],NULL,0);
if(spi_transfer(spi_ch,twbuf,twb,trbuf,trb)!=0)
{
free(twbuf);
free(trbuf);
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
printf("recv:");
for(int i=0;i<trb;i++) printf("[0x%02X]",trbuf[i]);
printf("\n");
free(twbuf);
free(trbuf);
printf("tranfer success.\n");
}
else
{
printf("unkown type %s\n",type);
PrintUsage();
spi_deinit(spi_ch);
uapi_sys_deinit();
}
spi_deinit(spi_ch);
uapi_sys_deinit();
return 0;
}
Loading…
Cancel
Save