编译时断言以确定指针是否为数组 [英] Compile-time assertion to determine if pointer is an array

查看:76
本文介绍了编译时断言以确定指针是否为数组的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

当前,我有以下代码块可以进行安全的字符串复制(它可以正常工作):

Currently, I have the following block of code to make safe string copying (it works):

#define STRCPY(dst, src) do { assert(((void*)(dst)) == ((void*) & (dst))); \
                              strlcpy(dst, src, sizeof(dst)); } while (0)

因此,它接受如下构造:

So it accepts the construction like:

const char *src = "hello";
char dest[5];
STRCPY(dest, src); //hell

并拒绝以下内容:

void (char *dst) {
    STRCPY(dst, "heaven"); //unknown size of dst
}

问题在于代码块创建了一个断言.有没有办法在编译时执行此检查?

The problem is that the block of code creates an assertion. Is there a way to perform this check on compilation time?

所以我想在编译时出错(例如使用负数),而不是崩溃(如果可能).

So I want to have the error on compilation (like creating an array with negative size) instead of crashing code if it possible.

推荐答案

要在编译时声明 dst 是否为数组,如果C11可用,我将使用@Lundin解决方案(或 _Static_assert ).

For compile-time assertion on whether or not dst is an array, I would use @Lundin solution (or _Static_assert) in case C11 is available.

否则,我将使用以下内容:

Else, I would use the following:

#define BUILD_BUG_ON_NON_ARRAY_TYPE(e)(sizeof(struct {int:-!!(((void *)(e))!=((void *)&(e));})))

基本上采用编译时评估的表达式(((void *)(dst))==((void *)&(dst)),但不要在运行时使用它 assert 只是以编译时断言的方式使用它.

Which basically takes your compile-time evaluated expression ((void*)(dst)) == ((void*) & (dst)) but instead of using it in run time assert just use it in a compile-time assertion manner.

因此,总的来说,我会将您的宏更改为:

So, overall I would change your macro into:

#define STRCPY(dst, src) do { BUILD_BUG_ON_NON_ARRAY_TYPE(dst); \
                              strlcpy(dst, src, sizeof(dst)); } while (0)

这篇关于编译时断言以确定指针是否为数组的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆