无法将DWORD转换为无符号长整型

Cannot convert DWORD to long unsigned int

本文关键字:无符号 长整型 转换 DWORD      更新时间:2023-10-16

Error: Cannot convert DWORD* {aka unsigned int*} to 'long unsigned int*' for argument 1 to int tea_encrypt(long unsigned int*,)

这是代码:

bool CLZObject::Encrypt(DWORD * pdwKey)
{
    if (!m_bCompressed)
    {
        assert(!"not compressed yet");
        return false;
    }
    BYTE * pbBuffer = m_pbBuffer + sizeof(THeader);
    m_pHeader->dwEncryptSize = tea_encrypt((DWORD *) pbBuffer, (const DWORD *) pbBuffer, pdwKey, m_pHeader->dwCompressedSize + 19);
    return true;
}

要理解您所面临的问题,您必须理解两种类型在概念上永远不会相同(除非它只是typedef)。CCD_ 3和CCD_。尽管您的实现可能具有相同大小的它们,但它们不必在所有实现中都相同。如果您的目标是可移植代码,那么假设它们的大小相等会导致问题。怎样

假设我们有一个实现,其中sizeof(int)4sizeof(long)8

int i = 0;
long *l = &i;   // good that the compiler rejects this

如果这是允许的,那么你就会有不明确的行为。假设i位于内存位置2000,因为它是4字节大小的,允许访问直到2003,因为此内存归程序所有。除此之外的内容对程序(mer)来说是未知的,因此是不可访问的。

|<------------- i ------------->|
+-------+-------+-------+-------+-------+-------+-------+-------+
| 0x00  | 0x00  | 0x00  | 0x00  |unknown|unknown|unknown|unknown|
+-------+-------+-------+-------+-------+-------+-------+-------+
  2000    2001    2002    2003    2004    2005    2006    2007
|<---------------------------- *l ----------------------------->|  // oops!

由于long的大小为8,使l指向i的地址(2000)意味着它将指向2000,如果您取消引用指针,即执行*l读取其中的内容,它将尝试读取8大小的long,方法是尝试访问2004到2007,而不是读取2000到2003。从而导致你的行为不明确。

避免像显式转换(类型转换)这样的技巧,以干净的方式进行。使用临时的。

void need_long(long *data) { /* some code */ }
int i = 0;
long l = i;     // temporary long to pass it to need_long
need_long(&l);

如果您同意不可移植,并且确信intlong大小相同,那么在您的实现中,您可以额外传递-fpermissive以允许GCC默认禁止的这种转换。

检查函数tea_encrypt。这个函数很可能期望unsigned long是32位(因为DWORD在Windows上,甚至在Win64上),而unsigned long在您的系统上可能是64位。你应该修复这个函数。最好的方法是将要加密的缓冲器的类型unsigned long更改为uint32_t,以明确地固定该类型的32位。uint32_t *应该与DWORD*兼容,即使在您的系统上也是如此。

从错误消息中,int0的第一个参数的类型为long unsigned int *。CCD_ 32显式地将CCD_ 33转换为CCD_。

虽然long unsigned intunsigned int是可能的,但这不是标准所要求的。如果它们与您的实现(即本例中的编译器)不是等效类型,则指向其中一个的指针无法隐式转换为指向另一个的指示器。

为了将第一个参数传递给函数,需要进行隐式转换(从unsigned int *long unsigned int *)。编译器正在抱怨,因为不允许隐式转换。

至于您要做什么,显而易见的是用long0替换(DWORD *)(即将pbBuffer的值转换为函数期望的指针)。这将使您的代码得以编译。

代码是否会正确运行则另当别论。你没有为任何人提供足够的背景来确定这一点。