C CODE Generation - Why does my code not terminate?
4 次查看(过去 30 天)
显示 更早的评论
Hello,
I generated some C code with the Matlab coder. I wrote a main script to run the functions I generated. I dont get any error messages while running my code. However the code wont terminate. I know this question is possibly very diffcult to ask, but did someone face similar difficulties and what are possible reasons that a generated code wont terminate while I did not had any problems with the orignal code in MATLAB? I generated more then 30 functions. I dont think, its a good idea to attach all of them here.
This is my main script:
void main(void)
{
static double x_data[1024];
double Results[18];
double dv[6];
double maxP_tmp;
int Fs;
double tol;
int x_size[1];
int i;
int j;
/* Initialize function 'EV_Code' input arguments. */
/* Initialize function input argument 'x'. */
for (i = 0; i <1024; i++) {
x_data[i] = 1;
}
x_data[3] = 1.2;
x_data[230] = 1.3;
x_data[443] = 1.7;
x_data[354] = 1.9;
x_data[146] = 1.6;
x_size[0]= 2;
maxP_tmp = 1.1;
dv[0] = 114.5;
dv[1] = 90.81;
dv[2] = 73.72;
dv[3] = 87.76;
dv[4] = 72.78;
dv[5] = 59.65;
Fs = 1000;
tol = 0.04;
EV_Code_X(x_data, x_size, maxP_tmp, Fs, dv, tol, Results);
EV_Code_X_terminate();
// return 0;
}
8 个评论
Geoff Hayes
2021-2-11
编辑:Walter Roberson
2021-3-8
HF - what do the functions EV_Code_X and EV_Code_X_terminate do? Is it in these functions that you are getting "stuck"?
HF
2021-2-11
EV_Code_X is the function where the computation is done.
EV_Code_X_terminate looks like this:
void EV_Code_X_terminate(void)
{
/* (no terminate code required) */
}
HF
2021-2-11
My code is getting stucked in this particular line
for (i = 0; i <= coffset; i++) {
Xm0_data[i] = Xm0->data[(aoffset + 30 * i) - 1];
}
Geoff Hayes
2021-2-11
编辑:Walter Roberson
2021-3-8
HF- what do you mean by "getting stuck" in the above line? Note that your code has a while loop
while (exitg1 == 0);
though it does appear that your code does have a maximum number of iterations of 100.
HF
2021-2-11
I paused the simulation after 1 000 000 and 2 000 000 instructions. The program was still executing this particular line.
That is the reason why I am quite confused because I had implemented a condition of maximum number of iteration for the while loop.
回答(1 个)
Geoff Hayes
2021-2-12
编辑:Walter Roberson
2021-3-8
HF - the code that you mention
for (i = 0; i <= coffset; i++) {
Xm0_data[i] = Xm0->data[(aoffset + 30 * i) - 1];
}
occurs before the while loop so the while isn't the problem. In this case, what is coffset initialized to? Is it a valid or reasonable integer? It seems to get initialized via Xm0 but all I see for this variable is that it is defined as
emxArray_real_T *Xm0;
and later initialized as
emxInit_real_T(&Xm0, 2);
but is that sufficient for
i = Xm0->size[0] * Xm0->size[1];
Xm0->size[0] = 30;
Xm0->size[1] = x_size[0] + 29;
emxEnsureCapacity_real_T(Xm0, i);
? Since i is being initialized before the size, I wonder if that is somehow corrupting the object.
30 个评论
Walter Roberson
2021-2-12
If the code for emxInit_real_T is the same as at https://www.mathworks.com/matlabcentral/answers/399098-i-am-getting-an-exception-running-c-code-generated-by-matlab-coder then the ->size would have been initialized as 0 and so i would have been initialized as 0.
HF
2021-2-12
Its the same code. "i" has to be initialized before right? Otherwise I wont be able to assign a value.
void emxInit_real_T(emxArray_real_T **pEmxArray, int numDimensions)
{
emxArray_real_T *emxArray;
int i;
*pEmxArray = (emxArray_real_T *)malloc(sizeof(emxArray_real_T));
emxArray = *pEmxArray;
emxArray->data = (double *)NULL;
emxArray->numDimensions = numDimensions;
emxArray->size = (int *)malloc(sizeof(int) * numDimensions);
emxArray->allocatedSize = 0;
emxArray->canFreeData = true;
for (i = 0; i < numDimensions; i++) {
emxArray->size[i] = 0;
}
}
HF
2021-2-12
Do you think I have to switch the order like this?
Xm0->size[0] = 30;
Xm0->size[1] = x_size[0] + 29;
i = Xm0->size[0] * Xm0->size[1];
Walter Roberson
2021-2-12
In C and C++, printf() does not emit a space or newline, and %d format uses only the minimum number of characters needed to represent the value. Therefore if you printf("%d",3); printf("%d",4) then the output would be 34 and not 3 4 or 3<newline>4<newline>
Geoff Hayes
2021-2-12
Try using \n as
printf("%d\n",x_data[3]);
for each printf so that the output is written to a new line.
Geoff Hayes
2021-2-12
Wait, try printing it out as a double or as a float since your x_data array is defined as a double. Use f or lf if supported:
printf("%f\n",x_data[3]);
Walter Roberson
2021-2-12
fprintf('%d.%d\n', (int)floor(x_data[3]), (int)10*(x_data[3]-floor(x_data[3])));
Walter Roberson
2021-2-12
printf('%d.%d\n', (int)floor(x_data[3]), (int)10*(x_data[3]-floor(x_data[3])));
Walter Roberson
2021-2-12
printf("%d.%d\n", (int)floor(x_data[3]), (int)10*(x_data[3]-floor(x_data[3])));
Walter Roberson
2021-2-12
At the moment I do not know how x_data[3]-floor(x_data[3]) came out negative when x_data[3] must have been positive or else there would have been a leading - as well.
Walter Roberson
2021-2-12
Your ->size are integer; you do not need to floor() them. And if you made int i then no need to (int) either.
Walter Roberson
2021-2-12
You assigned x_size[0] = 2. You set Xm0->size[1] to x_size[0]+29 and so that should give you 31. Why are you expecting 59? 59 would be Xm0->size[0] + 29 but you are grabbing x_size[0] not Xm0->size[0]
Geoff Hayes
2021-2-12
编辑:Walter Roberson
2021-3-8
HF- perhaps clarify what the problem might be or is it still the same as before. Are you still getting stuck in that loop. If so, have you written out what the upper bound on the loop is?
HF
2021-2-12
编辑:HF
2021-2-12
Exactly, so I still get stucked in the loop I mentioned before.
for (i = 0; i <= coffset; i++) {
Xm0_data[i] = Xm0->data[(aoffset + 30 * i) - 1];
}
Coffset has a value of 4000000 which does not make sense. As you can see from the snapshots before, the calculation of several equations are incorrect. Now I am trying to figure out why this might be the case.
HF
2021-2-12
My main approach is to display every value after an equation. As you can see in the snapshot the first results of the function EV_Code_X does not make sense.
I hope this clarifies my problem.
Geoff Hayes
2021-2-12
Out of curiosity, where or when is memory allocated to Xm0->data? It seems that it is initialized as
emxArray->data = (double *)NULL;
(in the emxInit_real_T function) but where is the memory for it allocated? Since the code seems to read and write data to this array I wonder if the writing to this array before memory has been allocated is corrupting the other data in this object...
Geoff Hayes
2021-2-12
编辑:Geoff Hayes
2021-2-12
Or is that what emxEnsureCapacity_real_T does, and if so, are we passing in the correct capacity i? From this code
// i = Xm0->size[0] * Xm0->size[1];
Xm0->size[0] = 30; // 30
printf("%d\n", (Xm0->size[0])); //H
Xm0->size[1] = x_size[0] + 29; // 31 (assuming x_size[0] is 2)
printf("%d\n", Xm0->size[1]); //H
i = Xm0->size[0] * Xm0->size[1]; // 30 * 31 = 930
printf("%d\n", (i));//H
emxEnsureCapacity_real_T(Xm0, i); // allocated for 930 elements
loop_ub = 30 * (x_size[0] + 29); // 30 * (2+29) = 930
for (i = 0; i < loop_ub; i++) {
Xm0->data[i] = 0.0; // this "seems" fine
}
/* y = f*x where x is padded */
for (aoffset = 0; aoffset < 30; aoffset++) {
if (aoffset + 1 == 1) {
if (1 > N) {
loop_ub = 0;
} else {
loop_ub = N; // N is 2?
}
// this occurs on first iteration of loop
for (i = 0; i < loop_ub; i++) {
Xm0->data[30 * i] = x_data[i]; // i is 0 or 30
}
// etc.
HF
2021-2-12
Xm0->data is initialized in the following line (in the beginning of the function EV_X_Code):
for (i = 0; i < loop_ub; i++) {
Xm0->data[i] = 0.0;
}
HF
2021-2-12
We are passing the right capacit of i. I mean everything before emxEnsureCapacity_real_T(Xm0, i); should work correclty. However printf("%d\n", (i));//H does not display the correct value.
To your comments: N = 2, i is 0 for the first loop.
Geoff Hayes
2021-2-12
The passing of i in emxEnsureCapacity_real_T(Xm0, i) may be irrelevant because of
if (emxArray->data != NULL) {
and this should be null because it is initialized to null in the other function at
emxArray->data = (double *)NULL;
So there is no data to copy into the newly allocated array, so this parameter of i is unimportant.
But in this capacity function, look at this code
newNumel = 1;
for (i = 0; i < emxArray->numDimensions; i++) {
newNumel *= emxArray->size[i];
}
if (newNumel > emxArray->allocatedSize) {
i = emxArray->allocatedSize;
if (i < 16) {
i = 16;
}
while (i < newNumel) {
if (i > 1073741823) {
i = MAX_int32_T;
} else {
i *= 2;
}
}
newData = calloc((unsigned int)i, sizeof(double));
Given what we already know, newNumel should be 30*31=930. The emxArray->allocatedSize is 0 so i is initialized to 16. Then in the while loop we multiply i by 2 on each iteration until it is greater than newNumel and so should be initialized to 1024 which you should be able to confirm with Xm0->allocatedSize. So you should have enough memory allocated in your array. Can you confirm that this allocatedSize is 1024?
Geoff Hayes
2021-2-14
Why do you think that the program skipped the call to emxEnsureCapacity_real_T? Check the Xm0->allocatedSize to see what this value is. (I don't have the MATLAB coder so cannot test out your files.)
另请参阅
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!发生错误
由于页面发生更改,无法完成操作。请重新加载页面以查看其更新后的状态。
您也可以从以下列表中选择网站:
如何获得最佳网站性能
选择中国网站(中文或英文)以获得最佳网站性能。其他 MathWorks 国家/地区网站并未针对您所在位置的访问进行优化。
美洲
- América Latina (Español)
- Canada (English)
- United States (English)
欧洲
- Belgium (English)
- Denmark (English)
- Deutschland (Deutsch)
- España (Español)
- Finland (English)
- France (Français)
- Ireland (English)
- Italia (Italiano)
- Luxembourg (English)
- Netherlands (English)
- Norway (English)
- Österreich (Deutsch)
- Portugal (English)
- Sweden (English)
- Switzerland
- United Kingdom(English)
亚太
- Australia (English)
- India (English)
- New Zealand (English)
- 中国
- 日本Japanese (日本語)
- 한국Korean (한국어)