[clang] clang_EvalResult_getAsCXString impl (PR #134551)

Aaron Ballman via cfe-commits cfe-commits at lists.llvm.org
Thu May 22 07:08:37 PDT 2025


AaronBallman wrote:

> > It means all such string accesses would require two indirections to get to the string data
> 
> I don't think that's true. Getting the pointer would be `ptr+sizeof(size_t)`.
> 
> > I also wonder if we want to be slightly less memory efficient and add a version field in case we need to make changes again in the future
> 
> Where would this go? The `Data` structure would be private API, not exposed, so it shouldn't matter when we change it.
> 
> I don't understand very well the last messages of you and [cor3ntin](https://github.com/cor3ntin), sorry.

Maybe I misunderstood your suggestion. I thought you were saying we'd end up like this:
```
typedef struct {
  const void *data;
  unsigned private_flags;
} CXString;

typedef struct {
  size_t length;
  const char buffer[];
} StringWithLength;

size_t clang_getStringLength(CXString Str) {
  if (Str.private_flags == StringWithLength) {
    StringWithLength *Data = (StringWithLength *)Str.data;
    return Data->length;
  }
  ...
}

const char *clang_getStringContents(CXString Str) {
  if (Str.private_flags == StringWithLength) {
    StringWithLength *Data = (StringWithLength *)Str.data;
    return Data->buffer;
  }
  ...
}
```
and we'd need the versioning information if we had Clang N tracking length + contents and Clang N + 1 was tracking length + contents + encoding because the newer Clang would be casting to a pointer of the wrong type if it was given a `CXString` from the older Clang.

But now that I think about it, this still runs into ABI issues like the original solution. Newer Clang would produce a `private_flags` value that older Clang couldn't handle gracefully.

https://github.com/llvm/llvm-project/pull/134551


More information about the cfe-commits mailing list