Does casting a pointer back and forth from size_t or uintptr_t break strict aliasing?

喜你入骨 提交于 2020-01-13 11:32:26

问题


I'm proposing a change to a library whose public API currently looks like this:

typedef size_t enh;  /* handle */

int en_open(enh *handle)
{
    struct internal *e = malloc(...);
    *handle = (enh)e;
    return 0;
}

int en_start(enh handle)
{
    struct internal *e = (struct internal*)handle;
    return do_something(e);
}

Does this usage, casting back and forth to size_t break strict aliasing?

For the record, I'm proposing a typical opaque forward declaration of struct internal in the public API, as shown on this Programmers.SE question about the same code.


回答1:


Aliasing is about two pointers of different type being used to access the same bytes. This is not the case in your code. When you access the data members behind the handle, you always do it via a pointer of type struct internal*. So no harm here.

The only questionable thing in your code is, that you are using size_t to pass the pointer. Afaik, the standard does not guarantee that you can safely cast a pointer to size_t and back, even though any sane implementation will allow it. The correct integer type choice would be uintptr_t, but you don't even need that:

I think, you should just use an opaque pointer in the interface. I. e., just put the declaration

typedef struct internal internal;

into your public header and keep the corresponding

struct internal {
    ...
}

private (replacing internal with a sensible public name, of course). The public functions can then simply be declared as:

int en_open(internal** outHandle);
int en_close(internal* handle);

That way, you get perfect type checking in the client code, and avoid the need for any casts.



来源:https://stackoverflow.com/questions/32279720/does-casting-a-pointer-back-and-forth-from-size-t-or-uintptr-t-break-strict-alia

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!