c - 如何将 Bus 对象读入 C S-Function 中的 C 结构 [Matlab]

标签 c matlab struct s-function

我在 Matlab 中定义了一个 Bus 对象,我将它传递给一个 C S-function,它会做一些处理。我已经在 mdlInitializeSizes 中像这样初始化了输入:

#if defined(MATLAB_MEX_FILE)
    if (ssGetSimMode(S) != SS_SIMMODE_SIZES_CALL_ONLY)
    {
        DTypeId dataTypeIdReg;

        ssRegisterTypeFromNamedObject(S, BUS_OBJ_NAME, &dataTypeIdReg);
        if(dataTypeIdReg == INVALID_DTYPE_ID) return;
        ssSetInputPortDataType(S, 0, dataTypeIdReg);
    }
#endif
ssSetInputPortWidth(S, 0, 1);
ssSetBusInputAsStruct(S, 0, 1); 
ssSetInputPortDirectFeedThrough(S, 0, 1);
ssSetInputPortRequiredContiguous(S, 0, 1);

我还自动生成了一个 C 结构,其中包含与 Bus 对象内的信号相同的变量。

Bus 中的一些信号也是总线,因此 C 结构体是递归生成的。例如:

struct myStruct
{
   uint8_t var1[8];
   uint32_t var2;
   myOtherStruct1 var3;
   myOtherStruct2 var4;
   ...
}

现在我想将 Bus 对象读入结构中。为此,我这样做:

const myStruct *busData = (const myStruct *) ssGetInputPortSignal(S, 0);

问题是 busData 没有 var4 和后续变量的正确数据。如果我打印从 ssGetInputPortSignal 收到的原始数据,我可以找到我期望的数据,但它不在数组中的正确位置;相反,它有一些填充

因此我想问:

  • 这是将 Bus 对象读入 C S-Function 结构的正确方法吗?
  • 如何禁用填充以使所有数据都是连续的?

提前致谢!

最佳答案

我遇到了同样的问题。对我有帮助的是 MathWorks 提供的以下示例:

open('sldemo_sfun_counterbus.c')
open('counterbus.h')

下面是一些代码片段,展示了如何根据上述示例获取 simulink 总线对象的信息:

// Defined localy, could also be defined in a header
typedef struct                  
{                               
    uint32_t ui32_header_val;   
    double f64_header_val;      
} YOURSTRUCT;            

static void mdlInitializeSizes(SimStruct *S)
{
    // ... your code

    // Specify I/O
    if (!ssSetNumInputPorts(S,1)) return;

    //Bus inport 
    DTypeId dataTypeIdReg;
    ssRegisterTypeFromNamedObject(S, "YOURBUS", &dataTypeIdReg);
    ssSetInputPortDataType(S, 0, dataTypeIdReg);
    ssSetBusInputAsStruct(S, 0, true);

    ssSetInputPortOverWritable(S, 0, 1);
    ssSetInputPortOptimOpts(S, 0, SS_REUSABLE_AND_LOCAL);
    // This is important !!! Specifies that the signal elements entering the specified port must occupy contiguous areas of memory
    ssSetInputPortRequiredContiguous(S, 0, 1);

    // Configure the dwork (__dtBusInfo)
    ssSetDWorkDataType(S, 0, SS_INT32);
    ssSetDWorkUsageType(S, 0, SS_DWORK_USED_AS_DWORK);
    ssSetDWorkName(S, 0, "dtBusInfo");

    // This contains the offset and sizes of your struct
    ssSetDWorkWidth(S, 0, 4);
    // The DWorker needs a depth of 4, since it stores the size of each element and its offset

    ssSetDWorkComplexSignal(S, 0, COMPLEX_NO);

    // ... your code
}

static void mdlStart(SimStruct *S)
{
    // ... your code

    // Access bus/struct information
    int32_T* __dtBusInfo = (int32_T*)ssGetDWork(S, 0);

    // Get common data type Id 
    DTypeId __YOURBUSId = ssGetDataTypeId(S, "YOURBUS");
    DTypeId __int32Id = ssGetDataTypeId(S, "int32");
    DTypeId __doubleId = ssGetDataTypeId(S, "double");

    // Get information for accessing YOURBUS.ui32_header_val
    __dtBusInfo[0] = ssGetBusElementOffset(S, __YOURBUSId, 0);
    __dtBusInfo[1] = ssGetDataTypeSize(S, __int32Id);

    // Get information for accessing YOURBUS.f64_header_val
    __dtBusInfo[2] = ssGetBusElementOffset(S, __YOURBUSId, 1);
    __dtBusInfo[3] = ssGetDataTypeSize(S, __doubleId);

    // ... your code                  

static void mdlOutputs(SimStruct *S, int_T tid)
{   
    // ... your code
    char *inputPort = (char*)(ssGetInputPortSignal(S, 0)); // Cast it to an 8Bit long Pointer here char

    YOURSTRUCT yourCStruct;

    memcpy(&yourCStruct.ui32_header_val, inputPort + __dtBusInfo[0], __dtBusInfo[1]);
    memcpy(&yourCStruct.f64_header_val,  inputPort + __dtBusInfo[2], __dtBusInfo[3]);
    // ... your code
}

关于c - 如何将 Bus 对象读入 C S-Function 中的 C 结构 [Matlab],我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34359205/

相关文章:

c++ - 128 位数字的位移位运算

c - x87 FPOP 和 FCOM 指令——它们是如何工作的?

matlab - 下面梯度下降算法的迭代实现误差是多少?

arrays - 将数组值处理到结构数组的单个字段(在 Matlab 中)

C extern struct指针动态分配

将系统的使用更改为 C 中的 Fork 和 exec

performance - MATLAB 速度优化

c# - 将未知大小的结构数组从 c# 传递到 c++ dll 并返回

objective-c - 如何在 XCode(Swift 或 Obj-C)中记录结构内的结构

c - 段错误: 11 in C Reading from External Text-file