You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何实现结构体内存连续分配?使QUESTION成员按指定顺序连续存储

How to Store QUESTION Data Contiguously in a Buffer

Got it, let's tackle this problem. The core issue with your current setup is that qname is a pointer—when you use malloc() for it, you're allocating memory outside your buf array, which breaks the contiguous storage you want. Instead, we need to directly place the qname string, followed by qtype and qclass, all inside buf without any external pointers.

Here are two straightforward approaches to achieve this:

Approach 1: Manual Buffer Layout (No Struct Modification)

If you want to keep your original QUESTION struct but still get contiguous storage in buf, you can manually copy each component into the buffer in order. This gives you full control over the memory layout:

#include <string.h>
#include <arpa/inet.h> // For htons() if working with network byte order

unsigned char buf[65536];
const char *your_qname = "example.com"; // Your target qname string
unsigned short qtype = 1; // A record, for example
unsigned short qclass = 1; // IN class, for example

// Calculate the length of qname (add 1 for null terminator; adjust if using DNS-style 0-terminated labels)
size_t qname_len = strlen(your_qname) + 1;
unsigned char *current_ptr = buf;

// 1. Copy qname into the buffer
memcpy(current_ptr, your_qname, qname_len);
current_ptr += qname_len;

// 2. Write qtype (convert to network byte order if needed, e.g., for DNS)
*(unsigned short *)current_ptr = htons(qtype);
current_ptr += sizeof(unsigned short);

// 3. Write qclass (same byte order note applies)
*(unsigned short *)current_ptr = htons(qclass);
current_ptr += sizeof(unsigned short);

// Now buf contains: [full qname string][qtype][qclass] contiguously

Key Notes:

  • Byte Order: If this is for a network protocol like DNS, qtype and qclass are required to be in big-endian (network byte order). Use htons() to convert from host byte order to network byte order.
  • Qname Format: If your qname uses DNS's label-based format (each label prefixed with length, ending with 0), adjust qname_len and the copy logic to match that instead of using strlen().

Approach 2: Use a Flexible Array Struct (Cleaner Layout)

If you prefer a structured approach, you can define a custom struct with a flexible array for qname, then overlay this struct onto your buf. This lets you access the fields directly while keeping everything contiguous:

#include <string.h>
#include <arpa/inet.h>

// Define a struct with a flexible array for qname (must be the last member)
typedef struct {
    unsigned char qname[]; // Flexible array to hold the qname string
    unsigned short qtype;
    unsigned short qclass;
} ContiguousQUESTION;

unsigned char buf[65536];
const char *your_qname = "example.com";
unsigned short qtype = 1;
unsigned short qclass = 1;

size_t qname_len = strlen(your_qname) + 1;
size_t total_required_size = qname_len + sizeof(unsigned short) + sizeof(unsigned short);

// Ensure we don't overflow the buffer
if (total_required_size > sizeof(buf)) {
    // Handle error (buffer too small)
    return -1;
}

// Overlay the struct onto the buffer
ContiguousQUESTION *question = (ContiguousQUESTION *)buf;

// Copy qname into the flexible array
memcpy(question->qname, your_qname, qname_len);

// Set qtype and qclass (again, handle byte order if needed)
question->qtype = htons(qtype);
question->qclass = htons(qclass);

// Now you can access question->qname, question->qtype, etc., all within buf

Why This Works:

Flexible arrays in C ([] as the last struct member) allow the struct to dynamically accommodate variable-length data. By casting buf to this struct type, we're telling the compiler to treat the start of buf as the struct's base, with qname taking up the first qname_len bytes, followed immediately by qtype and qclass.

Why Your Original Approach Failed

Your original QUESTION struct uses a pointer unsigned char *qname. When you malloc() for it, you're creating a new block of memory separate from buf—the pointer just stores the address of that external block. To get contiguous storage, we need to embed the actual string data directly into buf, not just a pointer to it.

内容的提问来源于stack exchange,提问作者Petr Marek

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.14 08:18:17