在以下设置中
typedef struct {
unsigned char data[64];
} mystruct;
int myfunc(mystruct* arg); // fills arg with data
使用指向 64 字节数组的指针调用 myfunc
是否安全?例如
unsigned char buffer[64];
myfunc((mystruct*) buffer)
在我的具体应用程序中,我使用 JNI 直接 ByteBuffer,它应该从 myfunc
填充。
unsigned char* dbbuffer = (unsigned char*) (*env)->GetDirectBufferAddress(env, jbuffer);
如果转换不安全,我必须创建一个mystruct
,调用myfunc
,然后memcopy
到dbbuffer
,我想避免。
最佳答案
从技术上讲,它是有效的,您可以使用它。正如评论中指出的,ANSI 标准的相关部分是:
6.7.2.1:结构和 union 说明符
... A pointer to a structure object, suitably converted, points to its initial member (or if that member is a bit-field, then to the unit in which it resides), and vice versa. There may be unnamed padding within a structure object, but not at its beginning.
在这种情况下,严格的别名并不重要。
严格别名规则指定在什么情况下可以通过更改另一种类型的值来更改某种类型的值。此规则的主要兴趣是标量类型,例如 int
和 float
。在您的特定情况下,很明显,通过更改结构的成员(unsigned char []
),您会更改整个结构,反之亦然。
这种情况属于严格别名规则的第 5 个子情况。为了完整起见,我引用了整个部分:
6.5 表达式,第 7 页
An object shall have its stored value accessed only by an lvalue expression that has one of the following types (The intent of this list is to specify those circumstances in which an object may or may not be aliased):
— a type compatible with the effective type of the object,
— a qualified version of a type compatible with the effective type of the object,
— a type that is the signed or unsigned type corresponding to the effective type of the object,
— a type that is the signed or unsigned type corresponding to a qualified version of the effective type of the object,
— an aggregate or union type that includes one of the aforementioned types among its members (including, recursively, a member of a subaggregate or contained union), or
— a character type
聚合类型的定义位于:
6.2.5 类型,第 21 页
Arithmetic types and pointer types are collectively called scalar types. Array and structure types are collectively called aggregate types.
关于c - 将数组转换为以一个数组作为成员的结构体是否安全?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/49063595/