Skip to content

Commit ae46135

Browse files
smilczekigcbot
authored andcommitted
Use data structures in STB_TranslateOutputArgs.
This commit changes STB_TranslateOutputArgs to use data structures instead of pointers to arrays of char. This is done for the purpose of preventing memory leaks. For `pOutput` field, llvm::SmallVector is used, as it works with ZEBinaryBuilder::getBinaryObject(llvm::raw_pwrite_stream).
1 parent d53ffdd commit ae46135

File tree

10 files changed

+113
-257
lines changed

10 files changed

+113
-257
lines changed

IGC/AdaptorOCL/OCL/TB/igc_tb.h

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -22,8 +22,6 @@ class CIGCTranslationBlock : public CTranslationBlock {
2222

2323
virtual bool Translate(const STB_TranslateInputArgs *pInputArgs, STB_TranslateOutputArgs *pOutputArgs);
2424

25-
virtual bool FreeAllocations(STB_TranslateOutputArgs *pOutputArgs);
26-
2725
protected:
2826
CIGCTranslationBlock() = default;
2927

IGC/AdaptorOCL/TranslationBlock.h

Lines changed: 11 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,15 @@ SPDX-License-Identifier: MIT
88

99
#pragma once
1010

11+
#include "CommonMacros.h"
12+
13+
#include "common/LLVMWarningsPush.hpp"
14+
#include <llvm/ADT/SmallVector.h>
15+
#include "common/LLVMWarningsPop.hpp"
16+
1117
#include <stdint.h>
1218
#include <stddef.h>
13-
#include "CommonMacros.h"
19+
#include <string>
1420

1521
#if defined(_WIN32)
1622
// INSIDE_PLUGIN must be defined in the pre-processor definitions of the
@@ -204,22 +210,11 @@ struct STB_TranslateInputArgs {
204210
Structure used to hold data returned from the translation block
205211
206212
\******************************************************************************/
213+
typedef llvm::SmallVector<char, 0> OutBufferType;
207214
struct STB_TranslateOutputArgs {
208-
char *pOutput; // pointer to translated data buffer
209-
uint32_t OutputSize; // translated data buffer size (bytes)
210-
char *pErrorString; // string to print if translate fails
211-
uint32_t ErrorStringSize; // size of error string
212-
char *pDebugData; // pointer to translated debug data buffer
213-
uint32_t DebugDataSize; // translated debug data data size (bytes)
214-
215-
STB_TranslateOutputArgs() {
216-
pOutput = NULL;
217-
OutputSize = 0;
218-
pErrorString = NULL;
219-
ErrorStringSize = 0;
220-
pDebugData = NULL;
221-
DebugDataSize = 0;
222-
}
215+
OutBufferType Output; // translated data buffer
216+
std::string ErrorString; // string to print if translate fails
217+
OutBufferType DebugData; // translated debug data buffer
223218
};
224219

225220
struct TranslationBlockVersion {
@@ -239,8 +234,6 @@ class CTranslationBlock {
239234
public:
240235
virtual bool Translate(const STB_TranslateInputArgs *pInput, STB_TranslateOutputArgs *pOutput) = 0;
241236

242-
virtual bool FreeAllocations(STB_TranslateOutputArgs *pOutput) = 0;
243-
244237
virtual bool GetOpcodes(void *pOpcodes, uint32_t pOpcodesSize) {
245238
IGC_UNUSED(pOpcodes);
246239
IGC_UNUSED(pOpcodesSize);

IGC/AdaptorOCL/dllInterfaceCompute.cpp

Lines changed: 42 additions & 83 deletions
Original file line numberDiff line numberDiff line change
@@ -145,13 +145,9 @@ static std::mutex llvm_mutex;
145145

146146
void UnlockMutex() { llvm_mutex.unlock(); }
147147

148-
extern bool ProcessElfInput(STB_TranslateInputArgs &InputArgs, STB_TranslateOutputArgs &OutputArgs,
149-
IGC::OpenCLProgramContext &Context, PLATFORM &platform, const TB_DATA_FORMAT &outType,
150-
float profilingTimerResolution);
151-
152-
extern bool ParseInput(llvm::Module *&pKernelModule, const STB_TranslateInputArgs *pInputArgs,
153-
STB_TranslateOutputArgs *pOutputArgs, IGC::OpenCLProgramContext &oclContext,
154-
TB_DATA_FORMAT inputDataFormatTemp);
148+
bool ProcessElfInput(STB_TranslateInputArgs &InputArgs, STB_TranslateOutputArgs &OutputArgs,
149+
IGC::OpenCLProgramContext &Context, PLATFORM &platform, const TB_DATA_FORMAT &outType,
150+
float profilingTimerResolution);
155151

156152
bool TranslateBuild(const STB_TranslateInputArgs *pInputArgs, STB_TranslateOutputArgs *pOutputArgs,
157153
TB_DATA_FORMAT inputDataFormatTemp, const IGC::CPlatform &IGCPlatform,
@@ -162,18 +158,16 @@ bool CIGCTranslationBlock::ProcessElfInput(STB_TranslateInputArgs &InputArgs, ST
162158
return TC::ProcessElfInput(InputArgs, OutputArgs, Context, m_Platform, m_DataFormatOutput, ProfilingTimerResolution);
163159
}
164160

165-
static void SetOutputMessage(const std::string &OutputMessage, STB_TranslateOutputArgs &pOutputArgs) {
166-
pOutputArgs.ErrorStringSize = OutputMessage.size() + 1;
167-
pOutputArgs.pErrorString = new char[pOutputArgs.ErrorStringSize];
168-
memcpy_s(pOutputArgs.pErrorString, pOutputArgs.ErrorStringSize, OutputMessage.c_str(), pOutputArgs.ErrorStringSize);
161+
static void SetOutputMessage(const std::string &OutputMessage, STB_TranslateOutputArgs &OutputArgs) {
162+
OutputArgs.ErrorString = OutputMessage;
169163
}
170164

171-
static void SetWarningMessage(const std::string &OutputMessage, STB_TranslateOutputArgs &pOutputArgs) {
172-
SetOutputMessage("warning: " + OutputMessage, pOutputArgs);
165+
static void SetWarningMessage(const std::string &OutputMessage, STB_TranslateOutputArgs &OutputArgs) {
166+
SetOutputMessage("warning: " + OutputMessage, OutputArgs);
173167
}
174168

175-
static void SetErrorMessage(const std::string &OutputMessage, STB_TranslateOutputArgs &pOutputArgs) {
176-
SetOutputMessage("error: " + OutputMessage, pOutputArgs);
169+
static void SetErrorMessage(const std::string &OutputMessage, STB_TranslateOutputArgs &OutputArgs) {
170+
SetOutputMessage("error: " + OutputMessage, OutputArgs);
177171
}
178172

179173
static bool IsDeviceBinaryFormat(const TB_DATA_FORMAT &format) {
@@ -208,12 +202,9 @@ bool CIGCTranslationBlock::Translate(const STB_TranslateInputArgs *pInputArgs, S
208202
IGC::SetWorkaroundTable(&m_SkuTable, &IGCPlatform);
209203
IGC::SetCompilerCaps(&m_SkuTable, &IGCPlatform);
210204

211-
pOutputArgs->pOutput = nullptr;
212-
pOutputArgs->OutputSize = 0;
213-
pOutputArgs->pErrorString = nullptr;
214-
pOutputArgs->ErrorStringSize = 0;
215-
pOutputArgs->pDebugData = nullptr;
216-
pOutputArgs->DebugDataSize = 0;
205+
pOutputArgs->Output.clear();
206+
pOutputArgs->ErrorString.clear();
207+
pOutputArgs->DebugData.clear();
217208

218209
try {
219210
if (m_DataFormatInput == TB_DATA_FORMAT_ELF) {
@@ -243,12 +234,12 @@ bool CIGCTranslationBlock::Translate(const STB_TranslateInputArgs *pInputArgs, S
243234
return false;
244235
}
245236
} catch (std::exception &e) {
246-
if (pOutputArgs->ErrorStringSize == 0 && pOutputArgs->pErrorString == nullptr) {
237+
if (pOutputArgs->ErrorString.empty()) {
247238
SetErrorMessage(std::string("IGC: ") + e.what(), *pOutputArgs);
248239
}
249240
return false;
250241
} catch (...) {
251-
if (pOutputArgs->ErrorStringSize == 0 && pOutputArgs->pErrorString == nullptr) {
242+
if (pOutputArgs->ErrorString.empty()) {
252243
SetErrorMessage("IGC: Internal Compiler Error", *pOutputArgs);
253244
}
254245
return false;
@@ -654,27 +645,18 @@ bool ProcessElfInput(STB_TranslateInputArgs &InputArgs, STB_TranslateOutputArgs
654645
if (success == true) {
655646
// Now that the output modules are linked the resulting module needs to be
656647
// serialized out
657-
std::string OutputString;
658-
llvm::raw_string_ostream OStream(OutputString);
648+
IGC_ASSERT(OutputArgs.Output.empty()); // Make sure we're not overwriting anything here.
649+
llvm::raw_svector_ostream OStream(OutputArgs.Output);
659650
if (OutputModule.get()) {
660651
llvm::WriteBitcodeToFile(*OutputModule.get(), OStream);
661-
OStream.flush();
662652
} else {
663653
// OutputModule can be null only if we use visa linking.
664654
IGC_ASSERT(hasVISALinking);
665655
}
666656

667657
if (outType == TB_DATA_FORMAT_LLVM_BINARY) {
668658
// Create a copy of the string to return to the caller.
669-
char *pBufResult = static_cast<char *>(operator new(OutputString.size(), std::nothrow));
670-
if (pBufResult != NULL) {
671-
memcpy_s(pBufResult, OutputString.size(), OutputString.data(), OutputString.size());
672-
// The buffer is returned to the runtime. When the buffer is not
673-
// needed anymore the runtime ir responsible to call the module for
674-
// destroying it
675-
OutputArgs.OutputSize = OutputString.size();
676-
OutputArgs.pOutput = pBufResult;
677-
659+
if (!OutputArgs.Output.empty()) {
678660
#if defined(IGC_SPIRV_ENABLED)
679661
if (IGC_IS_FLAG_ENABLED(ShaderDumpEnable)) {
680662
// This part renames the previously dumped SPIR-V files
@@ -686,7 +668,8 @@ bool ProcessElfInput(STB_TranslateInputArgs &InputArgs, STB_TranslateOutputArgs
686668
oss1 << std::hex << std::setfill('0') << std::setw(sizeof(prevAsmHash) * CHAR_BIT / 4) << prevAsmHash;
687669
const std::string prevHashString = oss1.str();
688670

689-
QWORD newAsmHash = ShaderHashOCL((const UINT *)OutputArgs.pOutput, OutputArgs.OutputSize / 4).getAsmHash();
671+
QWORD newAsmHash =
672+
ShaderHashOCL((const UINT *)OutputArgs.Output.data(), OutputArgs.Output.size() / 4).getAsmHash();
690673
std::ostringstream oss2(std::ostringstream::ate);
691674
oss2 << std::hex << std::setfill('0') << std::setw(sizeof(newAsmHash) * CHAR_BIT / 4) << newAsmHash;
692675
const std::string newHashString = oss2.str();
@@ -723,7 +706,7 @@ bool ProcessElfInput(STB_TranslateInputArgs &InputArgs, STB_TranslateOutputArgs
723706
// dump the buffer
724707
FILE *file = fopen(dumpFileName.c_str(), "wb");
725708
if (file != NULL) {
726-
fwrite(pBufResult, OutputString.size(), 1, file);
709+
fwrite(OutputArgs.Output.data(), OutputArgs.Output.size(), 1, file);
727710
fclose(file);
728711
}
729712
} else {
@@ -750,8 +733,10 @@ bool ProcessElfInput(STB_TranslateInputArgs &InputArgs, STB_TranslateOutputArgs
750733
return false;
751734
}
752735
} else {
753-
InputArgs.pInput = OutputString.data();
754-
InputArgs.InputSize = OutputString.size();
736+
auto OutputIsTheNewInput = std::move(OutputArgs.Output);
737+
InputArgs.pInput = OutputIsTheNewInput.data();
738+
InputArgs.InputSize = OutputIsTheNewInput.size();
739+
OutputArgs.Output = OutBufferType(); // Reinitialize pOutput after moving it to InputArgs as pInput.
755740
success = TC::TranslateBuild(&InputArgs, &OutputArgs, TB_DATA_FORMAT_LLVM_BINARY, Context.platform,
756741
profilingTimerResolution);
757742
InputArgs.pInput = nullptr;
@@ -767,9 +752,8 @@ bool ProcessElfInput(STB_TranslateInputArgs &InputArgs, STB_TranslateOutputArgs
767752
return success;
768753
}
769754

770-
bool ParseInput(llvm::Module *&pKernelModule, const STB_TranslateInputArgs *pInputArgs,
771-
STB_TranslateOutputArgs *pOutputArgs, llvm::LLVMContext &oclContext, TB_DATA_FORMAT inputDataFormatTemp,
772-
const IGC::CPlatform &IGCPlatform) {
755+
bool ParseInput(llvm::Module *&pKernelModule, const STB_TranslateInputArgs *pInputArgs, std::string &errorString,
756+
llvm::LLVMContext &oclContext, TB_DATA_FORMAT inputDataFormatTemp, const IGC::CPlatform &IGCPlatform) {
773757
pKernelModule = nullptr;
774758

775759
// Parse the module we want to compile
@@ -796,7 +780,7 @@ bool ParseInput(llvm::Module *&pKernelModule, const STB_TranslateInputArgs *pInp
796780
}
797781

798782
if (isLLVM27IR || isLLVM30IR) {
799-
SetErrorMessage("Old LLVM IR (possibly from legacy binary) : not supported!", *pOutputArgs);
783+
errorString = "Old LLVM IR (possibly from legacy binary) : not supported!";
800784
return false;
801785
}
802786
}
@@ -815,15 +799,13 @@ bool ParseInput(llvm::Module *&pKernelModule, const STB_TranslateInputArgs *pInp
815799
} else if (inputDataFormatTemp == TB_DATA_FORMAT_SPIR_V) {
816800
#if defined(IGC_SPIRV_ENABLED)
817801
// convert SPIR-V binary to LLVM module
818-
std::string stringErrMsg;
819802
bool success =
820-
TranslateSPIRVToLLVM(*pInputArgs, oclContext, strInput, pKernelModule, stringErrMsg, (PLATFORM &)IGCPlatform);
803+
TranslateSPIRVToLLVM(*pInputArgs, oclContext, strInput, pKernelModule, errorString, (PLATFORM &)IGCPlatform);
821804
#else
822805
std::string stringErrMsg{"SPIRV consumption not enabled for the TARGET."};
823806
bool success = false;
824807
#endif
825808
if (!success) {
826-
SetErrorMessage(stringErrMsg, *pOutputArgs);
827809
return false;
828810
}
829811
} else {
@@ -836,9 +818,7 @@ bool ParseInput(llvm::Module *&pKernelModule, const STB_TranslateInputArgs *pInp
836818
if (pKernelModule == nullptr) {
837819
err.print(nullptr, llvm::errs(), false);
838820
IGC_ASSERT_MESSAGE(0, "Parsing module failed!");
839-
}
840-
if (pKernelModule == nullptr) {
841-
SetErrorMessage("Parsing llvm module failed!", *pOutputArgs);
821+
errorString = "Parsing llvm module failed!";
842822
return false;
843823
}
844824

@@ -900,7 +880,7 @@ bool ReadSpecConstantsFromSPIRV(std::istream &IS, std::vector<std::pair<uint32_t
900880
}
901881
#endif
902882

903-
void overrideOCLProgramBinary(OpenCLProgramContext &Ctx, char *&binaryOutput, size_t &binarySize) {
883+
void overrideOCLProgramBinary(OpenCLProgramContext &Ctx, OutBufferType &binaryOutput) {
904884
auto name =
905885
DumpName(IGC::Debug::GetShaderOutputName()).Hash(Ctx.hash).Type(ShaderType::OPENCL_SHADER).Extension("progbin");
906886

@@ -916,14 +896,10 @@ void overrideOCLProgramBinary(OpenCLProgramContext &Ctx, char *&binaryOutput, si
916896
size_t newBinarySize = (size_t)f.tellg();
917897
f.seekg(0, f.beg);
918898

919-
char *newBinaryOutput = new char[newBinarySize];
920-
f.read(newBinaryOutput, newBinarySize);
899+
binaryOutput.resize(newBinarySize);
900+
f.read(binaryOutput.data(), newBinarySize);
921901

922902
IGC_ASSERT_MESSAGE(f.good(), "Not fully read!");
923-
924-
delete[] binaryOutput;
925-
binaryOutput = newBinaryOutput;
926-
binarySize = newBinarySize;
927903
}
928904

929905
void dumpOCLProgramBinary(const char *fileName, const char *binaryOutput, size_t binarySize) {
@@ -1103,7 +1079,8 @@ bool TranslateBuildSPMD(const STB_TranslateInputArgs *pInputArgs, STB_TranslateO
11031079
DumpShaderFile(pOutputFolder, outputstr.str().c_str(), outputstr.str().size(), hash, "_cmd.txt");
11041080
}
11051081

1106-
if (!ParseInput(pKernelModule, pInputArgs, pOutputArgs, *llvmContext, inputDataFormatTemp, IGCPlatform)) {
1082+
if (!ParseInput(pKernelModule, pInputArgs, pOutputArgs->ErrorString, *llvmContext, inputDataFormatTemp,
1083+
IGCPlatform)) {
11071084
return false;
11081085
}
11091086
CDriverInfoOCLNEO driverInfoOCL;
@@ -1232,7 +1209,7 @@ bool TranslateBuildSPMD(const STB_TranslateInputArgs *pInputArgs, STB_TranslateO
12321209
SetOutputMessage("IGC: Out Of Memory", *pOutputArgs);
12331210
return false;
12341211
} catch (std::exception &e) {
1235-
if (pOutputArgs->ErrorStringSize == 0 && pOutputArgs->pErrorString == nullptr) {
1212+
if (pOutputArgs->ErrorString.empty()) {
12361213
std::string message = "IGC: ";
12371214
message += oclContext.GetErrorAndWarning();
12381215
message += '\n';
@@ -1255,8 +1232,8 @@ bool TranslateBuildSPMD(const STB_TranslateInputArgs *pInputArgs, STB_TranslateO
12551232

12561233
IGC::Debug::RegisterComputeErrHandlers(*oclContext.getLLVMContext());
12571234

1258-
if (!ParseInput(pKernelModule, pInputArgs, pOutputArgs, *oclContext.getLLVMContext(), inputDataFormatTemp,
1259-
IGCPlatform)) {
1235+
if (!ParseInput(pKernelModule, pInputArgs, pOutputArgs->ErrorString, *oclContext.getLLVMContext(),
1236+
inputDataFormatTemp, IGCPlatform)) {
12601237
return false;
12611238
}
12621239
oclContext.setModule(pKernelModule);
@@ -1311,11 +1288,7 @@ bool TranslateBuildSPMD(const STB_TranslateInputArgs *pInputArgs, STB_TranslateO
13111288

13121289
// FIXME: zebin currently only support program output itself, will add debug info
13131290
// into it
1314-
size_t binarySize = 0;
1315-
char *binaryOutput = nullptr;
1316-
1317-
llvm::SmallVector<char, 64> buf;
1318-
llvm::raw_svector_ostream llvm_os(buf);
1291+
llvm::raw_svector_ostream llvm_os(pOutputArgs->Output);
13191292
const bool excludeIRFromZEBinary =
13201293
IGC_IS_FLAG_ENABLED(ExcludeIRFromZEBinary) || oclContext.getModuleMetaData()->compOpt.ExcludeIRFromZEBinary;
13211294
const char *spv_data = nullptr;
@@ -1332,24 +1305,16 @@ bool TranslateBuildSPMD(const STB_TranslateInputArgs *pInputArgs, STB_TranslateO
13321305
unsigned PtrSzInBits = pKernelModule->getDataLayout().getPointerSizeInBits();
13331306
unsigned int pointerSizeInBytes = (PtrSzInBits == 64) ? 8 : 4;
13341307
oclContext.m_programOutput.GetZEBinary(llvm_os, pointerSizeInBytes, spv_data, spv_size, metricData, metricDataSize,
1335-
pInputArgs->pOptions, pInputArgs->OptionsSize);
1336-
1337-
// FIXME: try to avoid memory copy here
1338-
binarySize = buf.size();
1339-
binaryOutput = new char[binarySize];
1340-
memcpy_s(binaryOutput, binarySize, buf.data(), buf.size());
1308+
pInputArgs->pOptions, pInputArgs->OptionsSize);
13411309

13421310
if (IGC_IS_FLAG_ENABLED(ShaderDumpEnable))
1343-
dumpOCLProgramBinary(oclContext, binaryOutput, binarySize);
1311+
dumpOCLProgramBinary(oclContext, pOutputArgs->Output.data(), pOutputArgs->Output.size());
13441312

13451313
if (const char *progbinCustomFN = IGC_GET_REGKEYSTRING(ProgbinDumpFileName))
1346-
dumpOCLProgramBinary(progbinCustomFN, binaryOutput, binarySize);
1314+
dumpOCLProgramBinary(progbinCustomFN, pOutputArgs->Output.data(), pOutputArgs->Output.size());
13471315

13481316
if (IGC_IS_FLAG_ENABLED(ShaderOverride))
1349-
overrideOCLProgramBinary(oclContext, binaryOutput, binarySize);
1350-
1351-
pOutputArgs->OutputSize = binarySize;
1352-
pOutputArgs->pOutput = binaryOutput;
1317+
overrideOCLProgramBinary(oclContext, pOutputArgs->Output);
13531318

13541319
COMPILER_TIME_END(&oclContext, TIME_TOTAL);
13551320

@@ -1435,12 +1400,6 @@ bool TranslateBuild(const STB_TranslateInputArgs *pInputArgs, STB_TranslateOutpu
14351400
return ret;
14361401
}
14371402

1438-
bool CIGCTranslationBlock::FreeAllocations(STB_TranslateOutputArgs *pOutputArgs) {
1439-
IGC_ASSERT(pOutputArgs);
1440-
delete[] pOutputArgs->pOutput;
1441-
return true;
1442-
}
1443-
14441403
bool CIGCTranslationBlock::Initialize(const STB_CreateArgs *pCreateArgs) {
14451404
const SGlobalData *pCreateArgsGlobalData = static_cast<const SGlobalData *>(pCreateArgs->pCreateData);
14461405

IGC/AdaptorOCL/ocl_igc_interface/impl/fcl_ocl_translation_ctx_impl.h

Lines changed: 8 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -116,22 +116,18 @@ CIF_DECLARE_INTERFACE_PIMPL(FclOclTranslationCtx) : CIF::PimplBase {
116116
bool dataCopiedSuccessfuly = true;
117117
if (success) {
118118
dataCopiedSuccessfuly &=
119-
outputInterface->GetImpl()->AddWarning(outputArgs.pErrorString, outputArgs.ErrorStringSize);
119+
outputInterface->GetImpl()->AddWarning(outputArgs.ErrorString.data(), outputArgs.ErrorString.size());
120120
dataCopiedSuccessfuly &=
121-
outputInterface->GetImpl()->CloneDebugData(outputArgs.pDebugData, outputArgs.DebugDataSize);
121+
outputInterface->GetImpl()->CloneDebugData(outputArgs.DebugData.data(), outputArgs.DebugData.size());
122122
dataCopiedSuccessfuly &=
123-
outputInterface->GetImpl()->SetSuccessfulAndCloneOutput(outputArgs.pOutput, outputArgs.OutputSize);
123+
outputInterface->GetImpl()->SetSuccessfulAndCloneOutput(outputArgs.Output.data(), outputArgs.Output.size());
124124
} else {
125125
dataCopiedSuccessfuly &=
126-
outputInterface->GetImpl()->SetError(TranslationErrorType::FailedCompilation, outputArgs.pErrorString);
126+
outputInterface->GetImpl()->SetError(TranslationErrorType::FailedCompilation, outputArgs.ErrorString.data());
127127
}
128128

129-
if (dataCopiedSuccessfuly == false) {
130-
legacyInterface->FreeAllocations(&outputArgs);
131-
return nullptr; // OOM
132-
}
133-
134-
legacyInterface->FreeAllocations(&outputArgs);
129+
if (!dataCopiedSuccessfuly)
130+
return nullptr;
135131

136132
return outputInterface.release();
137133
}
@@ -176,8 +172,8 @@ CIF_DECLARE_INTERFACE_PIMPL(FclOclTranslationCtx) : CIF::PimplBase {
176172
bool success;
177173
success = TC::CClangTranslationBlock::Create(&createArgs, &outputArgs, legacyInterface);
178174
if (!success && err != nullptr) {
179-
const char *pErrorMsg = outputArgs.pErrorString;
180-
uint32_t pErrorMsgSize = outputArgs.ErrorStringSize;
175+
const char *pErrorMsg = outputArgs.ErrorString.data();
176+
uint32_t pErrorMsgSize = outputArgs.ErrorString.size();
181177
err->PushBackRawBytes(pErrorMsg, pErrorMsgSize);
182178
}
183179
if (legacyInterface == nullptr) {

0 commit comments

Comments
 (0)