You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

C++中uint8_t数组转char数组适配MISRA规则:修复指针算术违规

修复MISRA规则567 S:指针算术未基于数组的问题

问题背景

需要在C++中实现uint8_t数组读取并转换为char数组,且符合MISRA规范。现有代码功能正常,但第24行的arr++触发了MISRA规则567 S(指针算术未基于数组),需修复该问题。

原代码如下:

#include <iostream>

using namespace std;

int PartNum_Read(char* arr);

int PartNum_Read(char* arr)
{
    uint32_t ret = 0U;
    uint8_t ReadPartNumer[3]={'a','b','c'}; //copy from other function, type is uint8_t
    if(arr != NULL)
        {
            for(int j = 0U; j < sizeof(ReadPartNumer); j++)
            {
                *arr = static_cast<char>(ReadPartNumer[j]);
                 arr++;
            }
            ret = (sizeof(ReadPartNumer));
        }
    cout << "PN: " << *arr << endl;
    
    return ret;
}

int main()
{
    cout<<"Hello World
";
    char PartNumer[3]={0};
    PartNum_Read(&PartNumer[0]);
    for(int i = 0U; i < 3; i++)
    {
        cout << "PN: " << PartNumer[i] << endl;
    }
    return 0;
}

修复方案

MISRA规则567 S禁止对未明确关联到数组的指针进行算术操作,核心是避免指针越界或脱离数组范围的风险。以下两种方案均可修复:

方案1:使用数组索引替代指针自增

不修改传入的arr指针,利用循环变量j作为索引定位目标位置,完全规避指针算术操作:

#include <iostream>

using namespace std;

int PartNum_Read(char* arr);

int PartNum_Read(char* arr)
{
    uint32_t ret = 0U;
    const uint8_t ReadPartNumer[3] = {'a','b','c'}; // 加const符合MISRA只读变量规范
    const size_t arr_len = sizeof(ReadPartNumer) / sizeof(ReadPartNumer[0]);
    
    if(arr != nullptr) // MISRA C++推荐用nullptr替代NULL
    {
        for(size_t j = 0U; j < arr_len; j++)
        {
            arr[j] = static_cast<char>(ReadPartNumer[j]); // 通过索引访问目标位置
        }
        ret = arr_len;
    }
    // 原代码中*arr已超出传入数组范围,建议移除该输出避免越界
    // cout << "PN: " << *arr << endl;
    
    return static_cast<int>(ret);
}

int main()
{
    cout << "Hello World" << endl;
    char PartNumer[3] = {0};
    PartNum_Read(PartNumer); // 直接传数组名,等价于&PartNumer[0],更直观
    for(size_t i = 0U; i < 3; i++)
    {
        cout << "PN: " << PartNumer[i] << endl;
    }
    return 0;
}

方案2:使用指针副本进行算术操作

若需保留指针操作逻辑,可创建指针副本执行自增,原指针始终指向数组起始位置,确保算术操作基于明确的数组范围:

#include <iostream>

using namespace std;

int PartNum_Read(char* arr);

int PartNum_Read(char* arr)
{
    uint32_t ret = 0U;
    const uint8_t ReadPartNumer[3] = {'a','b','c'};
    const size_t arr_len = sizeof(ReadPartNumer) / sizeof(ReadPartNumer[0]);
    
    if(arr != nullptr)
    {
        char* temp_arr = arr; // 创建指针副本
        for(size_t j = 0U; j < arr_len; j++)
        {
            *temp_arr = static_cast<char>(ReadPartNumer[j]);
            temp_arr++; // 仅对副本执行自增操作
        }
        ret = arr_len;
    }
    // 移除越界访问的输出语句
    // cout << "PN: " << *arr << endl;
    
    return static_cast<int>(ret);
}

int main()
{
    cout << "Hello World" << endl;
    char PartNumer[3] = {0};
    PartNum_Read(PartNumer);
    for(size_t i = 0U; i < 3; i++)
    {
        cout << "PN: " << PartNumer[i] << endl;
    }
    return 0;
}

额外MISRA合规优化点

  • 给只读的ReadPartNumer数组添加const修饰,符合MISRA对常量的规范
  • 用nullptr替代NULL,这是MISRA C++的推荐写法
  • 采用size_t作为循环变量类型,匹配数组长度的类型,避免类型不匹配
  • 移除原代码中访问数组越界的cout << *arr语句,规避未定义行为

内容的提问来源于stack exchange,提问作者Nick Lee

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.16 17:13:16