记录一次Hi3518E新添sensor的过程


原文链接: 记录一次Hi3518E新添sensor的过程

记录一次Hi3518E新添sensor的过程

向sensor原厂要这些.ini和驱动,海思SDK是不会提供的
mask地址设置时要注意

使用的sensor是海思列表没有支持的SC2235,主要需要了解到这个sensor的配置已经地址(需要向sensor原厂要驱动sc2235_cmos.c sc2235_sensor_ctl.c sc2235_1080p_line.ini vpss_attr_2235.c)编译为.so .a以供测试代码调用。

首先在ko加载时就要添加自己的sensor,./load3518e -a -sensor sc2235 -osmem 32 -total 64
在load3518e 脚本中的函数insert_sns()中添加自己sensor对应的地址。
否则会报错“Invalid sensor type”

问题1:
Unknown symbol in module, or unknown parameter(rmmod 执行失败,请忽视错误,开机第一次加载ko,会先删除rmmode,为空肯定报错)
operation not permitted
load3518e执行失败,ko插入失败
第一反应肯定是linux版本不匹配,嗯,事实上并不是,很可能是OS和MMZ的地址重叠了。
需要看你DDR内存大小,海思教程中的DDR是128MB的,如果你一样,那就跟着教程走就ok
不幸的是,我们的DDR是64MB,那么你可以参照下面的修改
setenv bootargs 'mem=32M console=ttyAMA0,115200 root=/dev/mtdblock2 rootfstype=jffs2 mtdparts=hi_sfc:1M(boot),3M(kernel),12M(rootfs)'
setenv bootcmd 'sf probe 0;sf read 0x82000000 0x100000 0x300000;bootm 0x82000000'
saveenv
上面的修改就够了,以后的都按照默认走,我也顺带贴出来
SNS_TYPE=ar0230 # sensor type

mem_total=64; # 64M, total mem
mem_start=0x80000000; # phy mem start

os_mem_size=32; # 32M, os mem
mmz_start=0x82000000; # mmz start addr
mmz_size=32M; # 32M, mmz size

MMZ地址肯定是从82000000开始的,OS最开始是从bootm 0x82000000启动的,但是启动后会回盖到0x80000000的 ,所以不用担心0x82000000重叠,正如文档所述,正常运行后的地址分配如图:

DDR:                                                           

-----|-------|  0x80000000   # Memory managed by OS.              
32M  | OS    |                                                
     |       |                                                
-----|-------|  0x82000000   # Memory managed by MMZ block anonymous.         
32 M | MMZ   |                                                
     |       |                                                
-----|-------|  0x84000000   # Memory managed by MMZ block jpeg.                       

一切顺利的话,lsmod会有如下显示:

Module Size Used by Tainted: P
hi_mipi 22587 0
hi3518e_adec 6546 0
hi3518e_aenc 46989 0
hi3518e_ao 105952 0
hi3518e_ai 109706 1 hi3518e_aenc
hi3518e_aio 28363 0
acodec 8242 0
piris 3220 0
pwm 2471 0
sensor_i2c 1501 0
hi3518e_ive 76660 0
hi3518e_jpege 51824 0
hi3518e_h264e 172210 0
hi3518e_chnl 33659 0
hi3518e_venc 216283 2 hi3518e_jpege,hi3518e_h264e
hi3518e_rc 62388 0
hifb 72068 0
hi3518e_vou 168985 1 hifb
hi3518e_vpss 261330 0
hi3518e_viu 246389 1 hi3518e_vpss
hi3518e_isp 105606 4 piris,sensor_i2c,hi3518e_vpss,hi3518e_viu
hi3518e_vgs 127198 0
hi3518e_region 66722 0
hi3518e_tde 121855 2 hifb,hi3518e_region
hi3518e_sys 62048 2 hi3518e_vpss,hi3518e_viu
hi3518e_base 58109 21 hi3518e_adec,hi3518e_aenc,hi3518e_ao,hi3518e_ai,hi3518e_aio,acodec,hi3518e_ive,hi3518e_jpege,hi3518e_h264e,hi3518e_chnl,hi3518e_venc,hi3518e_rc,hifb,hi3518e_vou,hi3518e_vpss,hi3518e_viu,hi3518e_isp,hi3518e_vgs,hi3518e_region,hi3518e_tde,hi3518e_sys
hi_media 5801 6 hi_mipi,acodec,pwm,hifb,hi3518e_tde,hi3518e_base
mmz 22400 6 hi3518e_ao,hi3518e_jpege,hi3518e_h264e,hi3518e_tde,hi3518e_sys,hi3518e_base
rtl8188eu 692341 0

问题1:
由于是新sensor,跑海思自带的测试代码肯定会提示“This sensor type is not surpport!”
解决方案:
添加新sensor的枚举类型 到typedef enum sample_vi_mode_e {}SAMPLE_VI_MODE_E;
并根据自己sensor的参数正确命名。

问题2:
最棘手的问题,get venc stream time out, exit thread
既然是新添加sensor,那么能出现这个超时问题一定就是视频摄入有问题了,最主要的结构在sample_common_vi.c 的combo_dev_attr_t结构体。
你要对照sensor厂商给的ini配置,参照其他厂商的形式为你的sensor写一个此结构体的初始化代码。当然我们的是CMOS3V3的,直接使用如下初始化结构:
combo_dev_attr_t MIPI_CMOS3V3_ATTR =
{

/* input mode */
.input_mode = INPUT_MODE_CMOS_33V,
{

}

};

执行sample_venc之后,选择一个选项,h264的流就出现在执行目录下了,直接用vlc打开。
如果想要转为网络的rtsp流,那需要改sample代码将这些流重新打包,并使用rtsp流发布出来。

最后贴一张成像图,但是泛紫,现在正准备在ISP调试下,帖子继续更新。

应该是mask地址设错了

mask地址吗?地址是写在ini的,sample没有导入ini,把ini转化为结构体combo_dev_attr_t的初始化了。还是不清楚问题咋改

掩码查一下,原理都一样的。

谢谢楼上两位,结贴了,掩码在sample_comm_vi.c中你添加的sensor的VI_DEV_ATTR_S 结构体中,我的结构体是:

掩码低十位 0x 3ff 0000

VI_DEV_ATTR_S DEV_ATTR_SC2235_DC_720P_BASE =
{
    /* interface mode */
    VI_MODE_DIGITAL_CAMERA,
    /* multiplex mode */
    VI_WORK_MODE_1Multiplex,
    /* r_mask    g_mask    b_mask*/
    //{0xFFF0000,    0x0},
    //{0xFF00000,    0x0},
    {0x3FF0000,    0x0},
    /* progessive or interleaving */
    VI_SCAN_PROGRESSIVE,
    /*AdChnId*/
    {-1, -1, -1, -1},
    /*enDataSeq, only support yuv*/
    VI_INPUT_DATA_YUYV,

     /* synchronization information */
    {
    /*port_vsync   port_vsync_neg     port_hsync        port_hsync_neg        */
    VI_VSYNC_PULSE, VI_VSYNC_NEG_HIGH, VI_HSYNC_PULSE,VI_HSYNC_NEG_HIGH,VI_VSYNC_NORM_PULSE,VI_VSYNC_VALID_NEG_HIGH,   
   
    /*hsync_hfb    hsync_act    hsync_hhb*/
    {0,            1280,        0,
    /*vsync0_vhb vsync0_act vsync0_hhb*/
     0,            720,        0,
    /*vsync1_vhb vsync1_act vsync1_hhb*/
     0,            0,            0}
    },
    /* use interior ISP */
    VI_PATH_ISP,
    /* input data type */
    VI_DATA_TYPE_RGB,
    /* bRevert */
    HI_FALSE,
    /* stDevRect */
    {200, 20, 1280, 720}
};

`