基于ICSim的基础实践

1、ICSim模拟环境搭建

1、安装ICSim

# 安装依赖
sudo apt install libsdl2-dev libsdl2-image-dev can-utils maven autoconf -y
# 下载ICSim
git clone https://github.com/zombieCraig/ICSim.git
# 编译安装
cd ICSim/
sudo make

img

2、安装socketcand

# 下载socketcand
git clone https://github.com/linux-can/socketcand.git
cd socketcand

# 获取缺少的文件
wget https://raw.githubusercontent.com/dschanoeh/socketcand/master/config.h.in

# 编译安装
autoconf
./configure
make clean
make
sudo make install

教程上的应该是不能用了,文件夹中不存在makrfile文件

使用官方教程安装

$ meson setup -Dlibconfig=true --buildtype=release build
$ meson compile -C build
$ meson install -C build

img

3、安装Kayak

# 下载
git clone https://github.com/dschanoeh/Kayak.git
# 安装jdk
sudo apt-get install openjdk-8-jdk
# 安装
cd Kayak
mvn clean package

img

2、启动模拟器

./icsim vcan0           #模拟器
./controls vcan0        #控制面

其控制器的按键说明如下:

功能 按键
加速 上方向键
左转向 左方向键
右转向 右方向键
开/关左车门(前)锁 右/左shift+A
开/关右车门(前)锁 右/左shift+B
开/关左车门(后)锁 右/左shift+X
开/关右车门(后)锁 右/左shift+Y
开启所有车门锁 右shift+左shift
关闭所有车门锁 左shift+右shift

1、加速

img

2、左转

img

3、前门开启

img

img

关闭

img

3、can数据分析

我们使用candump进行数据的收集

img

然后,找到与转向灯控制、车门控制、加速控制相关的CAN数据帧。

我们根据统计频率进行查找

代码如下:

import sys

def read_can_data(file_path):
    """
    读取文件并提取CAN ID和数据。
    
    参数:
        file_path (str): 文件路径。
    
    返回:
        tuple: (CAN ID 列表, CAN 数据列表)
    """
    result_id = []
    result_data = []
    
    with open(file_path, "r") as file:
        for line in file:
            parts = line.split(' ')[2]
            can_id = parts.split('#')[0]
            result_id.append(can_id)
            result_data.append(parts)
    
    return result_id, result_data

def print_id_counts(result_id):
    """
    打印每个CAN ID出现的次数。
    
    参数:
        result_id (list): CAN ID 列表。
    """
    unique_ids = set(result_id)
    for can_id in unique_ids:
        print(f"{can_id}: {result_id.count(can_id)}")

def search_data_by_id(result_data):
    """
    根据用户输入的CAN ID搜索并打印对应的数据。
    
    参数:
        result_data (list): CAN 数据列表。
    """
    while True:
        inp = input("please input id: ")
        for data in result_data:
            if inp in data.split("#")[0]:
                print(data)

def main():
    """
    主函数,执行读取数据、打印统计信息和搜索数据功能。
    """
    if len(sys.argv) < 2:
        print("Usage: python script.py <input_file>")
        return
    
    file_path = sys.argv[1]
    result_id, result_data = read_can_data(file_path)
    
    print_id_counts(result_id)
    search_data_by_id(result_data)

if __name__ == "__main__":
    main()

查找转向灯控制的帧,我只转向一次,因此形成的数据帧应当较少

频率如下

img

首先从5a1看起

img

这里没有仅一次操作的,接下来是188

img

这里有仅一次的操作

我们对其进行cansend重放,经过操作发现左转灯可以亮起

img

因此左转的帧id为

188#01000000

同理,这里对非0字段进行测试,发现仅有1,2,3分别控制左转,右转和双闪

188#02000000
开关门帧分析

我这里限制开关门次数,首先只开了前左门一次,查看频率

img

这里19B为一次,那么就是该帧,对字段进行修改,发现如下结果

img

19B#00000E000000    #前左门打开
19B#00000C000000    #前右门和前左门打开
19B#000008000000    #仅右后门关闭
19B#000000000000    #车门全开
二分法

由于加减速控制很难通过数量去分析,这里只能使用二分法来进行分析

省略前置步骤,目前加速锁定在50条数据中

img

如图所示,我们将其分割为五个文件,进行重放测试,发现只有xab触发了加速

对xab进行分割

img

发现其分割后的xab能够触发加速控制

draw@draw-ubuntu:~/Desktop$ cat xab
(1753163620.410724) vcan0 244#00000015B6
(1753163620.411180) vcan0 095#800007F400000026
(1753163620.411201) vcan0 166#D0320036
(1753163620.411209) vcan0 158#0000000000000037
(1753163620.411212) vcan0 161#000005500108003A

对其逐个测试

img

发现该帧能够触发加速控制,所以速度控制的帧id为244

4、SavvyCAN使用

首先需要安装qt环境,这里我使用5.14.2版本(https://download.qt.io/archive/qt/5.14/5.14.2/)(savvyCAN环境要求>=5.14.0版本),下载".run"的在线安装程序,然后其赋予执行权限(chmod 755 qt-xxx.run),使用"./qt-xxx.run"进行安装,这里我安装完毕后的目录为"~/Qt5.14.2/5.14.2"。

img

git clone https://github.com/collin80/SavvyCAN.git
sudo apt install libqt5serialbus5-dev libqt5serialport5-dev qtdeclarative5-dev qttools5-dev
cd SavvyCAN
~/Qt5.14.2/5.14.2/gcc_64/bin/qmake
make

img

使用该命令启动工具

./savvyCAN

界面如下:

img

我们需要先连接vcan0才能进行下一步操作。点击Connection然后点击"open Connection Window"。

img

点击"Add New Device Connection - QT SerialBus Device-socketcan-vcan0",然后点击"Create New Connections",最后"Save Bus Settings"就创建好连接了。

img

savvyCAN工具部分功能与我们上面使用的can-utils工具相同,下图为RE tools中的sniffer功能,与我们上面操作使用的cansniffer功能相同,但是savvyCAN中变化的数据使用了颜色进行标记,更便于我们辨识数据。

然后启动模拟器

img

这里能看到许多帧

1、RE Tools
Detailed frame data

img

左侧:Frame IDs ,当前捕获数据中出现的所有唯一的 CAN 帧 ID

然后是details,其中有如下信息

帧数量,数据长度,对每位数据的统计

img

例如该图中,该位数据的范围是0x00-0x2B,且给出每种数据的帧数

Bitfield Histogram****直方图

img

统计该帧 ID 所有数据字节中,每个比特位 (Bit) 出现 0 1 的频数

Flow view

img

该工具在特定的frame id下,以时间线为顺序,逐帧显示变化的bit位,按下->按钮

img

在这里,红色代表之前为1的位置,绿色代表当前为1的bit位置

下方的->按钮则是自动按照时间顺序进行帧播放

5、通过其FUZZ功能筛选灯控、门控、加速的关键数据帧。

(1)这里通过fuzz进行筛选控制帧

这里设置 id=0x244,bit选择random

img

开始fuzz以后,速度变化非常快(车门在fuzz前打开)

所以速度控制的canid=0x244

得到id以后,对其控制字段进行fuzz,首先设置第一个字节为00

img

这里状态不发生变化,依照此原理,进行修改

直到第四个字节设置以后,速度不发生变化,那么,该帧为控制字段

img

然后,设置单bit进行fuzz

将首bit设置为0时

img

img

将单bit设置为1时

img

img

对比发现,当首bit=0时,是从0速度开始加速的,而首bit=1时,是从最大速度进行减速的,因此该字段应当是控制加减字段

进行测试,我们设置后7字段为固定值1010101

img

img

因此,该值为控制加减速字段

而后,测试后续字段

设置为00010101

img

设置00110100

img

经过测试该字段应当是控制加速/减速力度

因此加速控制如下:

canid#000000[control_bit(1)|speed_bits(7)]00

(2)通过fuzz筛选转向控制帧

设置id=0x188,依然选择random,开始fuzz

img

转向灯快速变化,因此转向控制canid=0x188

步骤如上,测试字节位置

img

因此控制字段在首字节

然后测试bit,经过测试

0x01为左转控制

img

0x02为右转控制

img

左转:188#01000000

右转:188#02000000

双闪:188#03000000

(3)通过fuzz筛选门控帧

设置id=0x19B,依然选择random,开始fuzz

img

img

img

在这里车门状态快速变换,因此车门控制canid=0x19B

步骤同上,测试第三个字节为控制字段

img

经过测试,是由低四个bit来控制车门打开关闭

0000表示车门全开

img

0001表示仅左前车门关闭

img

0010表示仅右前车门关闭

img

步骤同上,测试完成

posted @ 2025-10-23 21:24  dr4w  阅读(3)  评论(0)    收藏  举报