achoora achoora - 3 months ago 22
C Question

How can a destination buffer be opaque?

I came across implementation details of serialization functions and it is mentioned that the target memory to which the structure has to be unpacked and stored needed to be an opaque buffer.

The wiki pedia says

"Some languages, such as C, allow the declaration of opaque records (structs), whose size and fields are hidden from the client. The only thing that the client can do with an object of such a type is to take its memory address, to produce an opaque pointer."

According to this pointer to any memory address would be opaque since we have no control over the memory address at which the destination buffer would start.
So what is the point of such a classification in C with respect to buffers. I have seen that in C++ objects can be opaque which makes more sense, since we can create objects which can be prevented from changing and data abstraction is in place .

Answer

Suppose you had a library header that looks like this:

struct lib_data;

struct lib_data *new_data();
void read_data(struct lib_data *data);
void clean_data(struct lib_data *data);

There is a forward declaration of struct lib_data without specifying its contents. Your app can then do this:

struct lib_data *data = new_data();
read_data(data);
clean_data(data);

Note that you have no knowledge of what struct lib_data looks like or even what its size is. That is what is meant by opaque. But you can hold a pointer to it and pass that around.

In the library's implementation (which you may or may not have access to), the struct has a proper definition and can therefore modify its elements.

For example, the library implementation might look like this:

struct lib_data {
    int data1
    double data2;
}

struct lib_data *new_data() 
{
    struct lib_data *temp = malloc(sizeof(struct lib_data);
    temp->data1 = 1;
    temp->data2 = 3.5;
    return temp;
}

void read_data(struct lib_data *data)
{
    ...
}

void clean_data(struct lib_data *data)
{
    free(data);
}

So the library can manipulate the struct, but application that use it cannot.

Comments