c - memcpy 额外的起始字符

标签 c memcpy

我在使用 memcpy 时遇到一些问题,因为当执行 memcpy 操作时,我得到:

“ÍÍWF03-021913.datýýýý«««««««þ”

什么时候我应该得到:

“WF03-021913.datýýý ««««««««þ”

我不知道这些领先的“ÍÍ”是从哪里来的。

代码:

注意:lpszFileName = "WF03-021913.dat"

typedef struct {
    BYTE  cbRequestType;
    BYTE  cbFileName;   
    char* szFileName;      
} UFTP_GET_FILE_INFO_REQUEST;

BOOL Uftp_BuildFileInfoRequest(PUFTP_REQUEST request, LPCTSTR lpszFileName)
{
    UFTP_GET_FILE_INFO_REQUEST *fileInfo;
    int fileNameLen;

    if (lpszFileName == NULL) {
        ASSERT( 0 );
        return FALSE;
    }

    fileNameLen = strlen( lpszFileName );
    if (fileNameLen == 0)
        return FALSE;

    request->dwRequestSize = sizeof(UFTP_GET_FILE_INFO_REQUEST) - 
                             sizeof(void*) + fileNameLen;
    request->RequestBuffer = malloc( request->dwRequestSize );
    if ( !request->RequestBuffer ) {
        TRACE0("Failed to allocate RequestBuffer");
        return FALSE;
    }

    fileInfo = (UFTP_GET_FILE_INFO_REQUEST*) request->RequestBuffer;
    fileInfo->cbRequestType = UFTP_GET_FILE_INFO;
    fileInfo->cbFileName = fileNameLen;

    memcpy(&fileInfo->szFileName, lpszFileName, fileNameLen);
    return TRUE;
}

最佳答案

我只是在这里猜测,但我的猜测是 fileInfo->szFileName 是一个指针。这意味着 &fileInfo->szFileName 是一个指向指针的指针,因此您可以复制到完整的其他内存区域。

此外,您无需复制所需的终止 '\0' 字符。为此,在分配和复制时都需要 fileNameLen + 1

如果您确实希望将其全部存储在连续内存中,则可能应该更改结构以以大小为零的字符数组结尾(您的编译器可能不支持,然后使用大小为 1 的数组)并使用 sizeof(UFTP_GET_FILE_INFO_REQUEST) + fileNameLen + 1 作为要分配的大小。然后您可以将该数组用作普通字符串数组。

<小时/>

如果您解决了这些问题,那么您还会遇到另一个问题:您没有将指针初始化为指向已分配的内存。这意味着它将指向一些随机内存。

所有这些错误都会导致未定义的行为,我想说你很幸运它没有崩溃。

关于c - memcpy 额外的起始字符,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/15978115/

相关文章:

c - memcpy() 的使用

c - 在 ANSI C 中将 Int 值序列化到 char* 缓冲区

c - 字符串在 IA32 程序集中如何表示?

c# - 将复杂数据类型从纯 c 插件传递到 Unity C# 脚本

尽管已经定义了函数体,但编译器仍发出有关 "implicit declaration"的警告

c - 编译器如何为未指定维度的数组分配内存?

c - 从二进制文件中删除信息

c - memcpy 和指针

将具有不同类型成员的结构复制到缓冲区

c++ - memcpy 和 C++ 类模板——如何使用它?