编译器错误:从 int* 到 unsigned int* 的无效转换 [-fpermissive]

Boo*_*oom 5 c++ pointers integer compiler-errors unsigned-integer

我今天遇到了最奇怪的问题。我正在使用一个在线示例,令我惊讶的是,它不起作用(他们几乎从不这样做)。我自己去修复它,但我似乎被这个错误困住了:

Error: Invalid Conversion from int* to unsigned int* [-fpermissive]
Run Code Online (Sandbox Code Playgroud)

我明白这一点。我正在提供一个int*,它想要一个unsigned int*. 不过,我真的不知道为什么int*产生的。

这是引发问题的片段代码:

unsigned char md_value[EVP_MAX_MD_SIZE];
int md_length;

EVP_DigestFinal_ex(md_ctx, md_value, &md_length);
Run Code Online (Sandbox Code Playgroud)

该函数调用的第三个参数&md_length导致了问题。查看该函数调用的文档(来自 OpenSSL,如果重要的话),它希望参数是unsigned int*类型的,因为它需要一个地址(或者至少我正在使用的示例是如何使用的)它)

有趣的是,我认为&操作员返回了一个unsigned int*,因为返回一个int*没有意义,因为计算机的内存中没有负地址。

这是我正在遵循的示例,如果您想看一看:https : //www.openssl.org/docs/crypto/EVP_DigestInit.html

下面是源代码,如果你想自己尝试一下。我怀疑你真的需要阅读它来解决这个问题,但把它放在这里不会有什么坏处。

源代码:

//* Description *//
// Title: Example
// Author: Boom Blockhead
// Example Program to Test OpenSSL

//* Libraries *//
#include <stdio.h>
#include <cstring>
#include <openssl/evp.h>

//* Namespaces *//
using namespace std;

//* Main Method *//
// Runs the Program and Interprets the Command Line
int main(int argc, char* argv[])
{
    // Initialize the Messages
    char msg1[] = "Test Message\n";
    char msg2[] = "Hello World\n";

    // Validate Argument Count
    if(argc != 2)
    {
        printf("Usage: %s digestname\n", argv[0]);
        exit(1);
    }

    // Determine Message Digest by Name
    OpenSSL_add_all_digests();
    const EVP_MD* md = EVP_get_digestbyname(argv[1]);

    // Make sure a Message Digest Type was Found
    if(md == 0)
    {
        printf("Unknown Message Digest %s\n", argv[1]);
        exit(1);
    }

    // Create the Message Digest Context
    EVP_MD_CTX* md_ctx = EVP_MD_CTX_create();

    // Setup the Message Digest Type
    EVP_DigestInit_ex(md_ctx, md, NULL);

    // Add the Messages to be Digested
    EVP_DigestUpdate(md_ctx, msg1, strlen(msg1));
    EVP_DigestUpdate(md_ctx, msg2, strlen(msg2));

    // Digest the Message
    unsigned char md_value[EVP_MAX_MD_SIZE];
    int md_length;

    EVP_DigestFinal_ex(md_ctx, md_value, &md_length); // <--- ERROR

    // Destroy the Message Digest Context
    EVP_MD_CTX_destroy(md_ctx);

    // Print the Digested Text
    printf("Digest is: ");

    for(int i = 0; i < md_length; i++)
        printf("%02x", md_value[i]);

    printf("\n");

    // Clean up the Message Digest
    EVP_cleanup();

    // Exit the Program
    exit(0);
    return 0;
}
Run Code Online (Sandbox Code Playgroud)

此外,将显式转换为(unsigned int*)似乎只会让事情变得更糟,因为我会收到以下错误:

example.cpp:(.text+0x91): undefined reference to `OpenSSl_add_all_digests`
...
example.cpp:(.text+0x1ec): undefined reference to `EVP_cleanup`
Run Code Online (Sandbox Code Playgroud)

基本上,它抱怨所有 OpenSSL 功能。

最后,(同样,这只是为了给你们提供你可能需要的一切)我没有向编译器发送任何有趣的参数。我只是在使用:

gcc example.cpp -o example.out
Run Code Online (Sandbox Code Playgroud)

由于存在错误,因此example.out实际上从未创建过。

Lig*_*ica 4

有趣的是,我认为 & 运算符返回一个无符号 int*,因为返回 int* 没有意义,因为计算机的内存中没有负地址。

这不好笑”; 这是错误的。

应用于类型对象的取址运算符T会给出类型为 的指针T*

时期。

T无符号类型还是有符号类型并不涉及其中,并且与有关计算机是否可能具有负地址的哲学辩论无关。事实上,指针通常有符号的,因为如果没有符号,当您尝试获取两个地址之间的差异或在地址空间中向后行走时,您很快就会陷入困境。

unsigned但这与代码中使用该术语无关。