expected expression before '{' token
Asked Answered
I

4

12

I am getting: "error: expected expression before '{' token" for the line I've commented before. If the struct is already defined why would it need a "{" before token. Thanks for any help you can provide.

struct sdram_timing {
    u32 wrdtr;
    u32 clktr;
};

int calibration(void);
unsigned char read_i2c_cal(void);
static unsigned int eepcal[15];

main() {
    DQS_autocalibration();
}

int calibration(void)
{
    struct sdram_timing scan_list[30];

    read_i2c_cal();
    if(eepcal[0] == 0){

       scan_list = {{eepcal[1], eepcal[2]}, {-1, -1}}; // <-- PROBLEM LINE

        }
        else {
            //foo
        }

    return 0;
}

unsigned char read_i2c_cal(void) {
    eepcal[0] = 0;
    eepcal[1] = 02;
    eepcal[2] = 03;
}
Incest answered 7/11, 2012 at 18:21 Comment(0)
L
24

The error is because you can't assign an array that way, that only works to initialize it.

int arr[4] = {0}; // this works
int arr2[4];

arr2 = {0};// this doesn't and will cause an error

arr2[0] = 0; // that's OK
memset(arr2, 0, 4*sizeof(int)); // that is too

So applying this to your specific example:

struct sdram_timing scan_list[30];
scan_list[0].wrdtr = 0;
scan_list[0].clktr = 0;

or you could use memset the same way, but instead of sizeof(int) you need size of your structure. That doesn't always work... but given your structure, it will.

Lotze answered 7/11, 2012 at 18:28 Comment(3)
so after it is initialized using "struct sdram_timing scan_list[30];" how can I assign values to scan_list?Incest
@Incest - What I gave you was the generic way to do it. I edited my post to give you a specific example using your code.Lotze
This also happens when trying to assign a struct (e.g. struct { int a; int b; } foo; foo = {1, 2};)... +1 for differentiating assignment and initialization in a way that gave me a quick answer.Tuberose
M
6

Arrays in C language are not assignable. You can't assign anything to the entire array, regardless of what syntax you use. In other words, this

scan_list = { { eepcal[1], eepcal[2] }, {-1, -1} };

is not possible.

In C89/90 you'd have to spell out your assignments line by line

scan_list[0].wrdtr = eepcal[1];
scan_list[0].clktr = eepcal[2];
scan_list[1].wrdtr = -1;
scan_list[1].clktr = -1;

In modern C (post-C99) you can use compound literals to assign entire structs

scan_list[0] = (struct sdram_timing) { eepcal[1], eepcal[2] };
scan_list[1] = (struct sdram_timing) { -1, -1 };

Finally, in modern C you can use memcpy and compound literals to copy data to the array

memcpy(scan_list, (struct sdram_timing[]) { { eepcal[1], eepcal[2] }, {-1, -1} },
  2 * sizeof *scan_list);

The last variant, albeit not very elegant, is the closest way to "emulate" array assignment.

Melano answered 7/11, 2012 at 18:37 Comment(0)
K
1

You can only use an initializer list in the declaration of the variable, not after the fact.

Kumquat answered 7/11, 2012 at 18:27 Comment(0)
L
1

Initializer list can only be used to initialize an array. You cannot use it afterwards.

However if you use GCC, you can use Compound Literal extension:

scan_list = (struct sdram_timing[30]){{eepcal[1], eepcal[2]}, {-1, -1}};

You might need to change scan_list type to be struct sdram_timing *

Loudermilk answered 7/11, 2012 at 18:31 Comment(4)
Compound literals do exist in C99, but that doesn't mean that arrays are assignable in C99. They are not. Your code will not compile.Melano
what if I want to modify values of scan_list after it is initialized?Incest
@AndreyT I just realized. Array variables cannot stand alone as a lvalue. Need to change to a pointerLoudermilk
@Incest the code above is showing you how to change it after initialization.Loudermilk

© 2022 - 2024 — McMap. All rights reserved.