desktop/source/lib/init.cxx | 1 + include/LibreOfficeKit/LibreOfficeKit.h | 14 ++++++++++++++ include/LibreOfficeKit/LibreOfficeKit.hxx | 21 ++++++++++++++++++++- 3 files changed, 35 insertions(+), 1 deletion(-)
New commits: commit c80eb9ff9a94899dcc582c0d85f8ed94c8c91cad Author: Tor Lillqvist <[email protected]> AuthorDate: Fri Jul 11 16:19:11 2025 +0300 Commit: Michael Stahl <[email protected]> CommitDate: Tue Dec 2 10:14:06 2025 +0100 Clarify that freeError() despite its name is a generic LOKit deallocation API Especially on Windows it is important to not call free() in your own code on a pointer returned from some random other dynamic library (like the one the desktop/source/lib/init.cxx code goes into). It might have been allocated by calling malloc() (etc) in a C runtime library that is different from the one used by your code. That will lead to a crash. One should alays call the free() in the same C runtime where the malloc() that allocated the pointer is. Add a wrapper called freeMemory() to the C++ API. Change-Id: Ibf9cf6fad2c30c4416d2a1f6badbd161c7ba18a6 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/194594 Tested-by: Jenkins CollaboraOffice <[email protected]> Reviewed-by: Michael Stahl <[email protected]> diff --git a/desktop/source/lib/init.cxx b/desktop/source/lib/init.cxx index 7cd8ad4c28ff..480f0733223b 100644 --- a/desktop/source/lib/init.cxx +++ b/desktop/source/lib/init.cxx @@ -7756,6 +7756,7 @@ static char* lo_getError (LibreOfficeKit *pThis) static void lo_freeError(char* pFree) { + // Do not try to do anything clever here. This should just call free() on the pointer. free(pFree); } diff --git a/include/LibreOfficeKit/LibreOfficeKit.h b/include/LibreOfficeKit/LibreOfficeKit.h index 7860adf3c66b..8d6ec5fa2646 100644 --- a/include/LibreOfficeKit/LibreOfficeKit.h +++ b/include/LibreOfficeKit/LibreOfficeKit.h @@ -65,6 +65,20 @@ struct _LibreOfficeKitClass const char* pURL, const char* pOptions); /// @since LibreOffice 5.2 + + /// The name "freeError" is a historical accident, actually this + /// is a generic deallocation function for dynamically allocated + /// memory returned by other LibreOfficeKit functions. + + /// Especially on Windows it is important to not call free() in + /// your own code on a pointer returned from some random other + /// dynamic library (like the one this code goes into) where it + /// might have been allocated by calling malloc() (etc) in a C + /// runtime library that is different from the one used by your + /// code. That will lead to a crash. Alays call the free() in the + /// same C runtime where the malloc() that allocated the pointer + /// is. + void (*freeError) (char* pFree); /// @since LibreOffice 6.0 diff --git a/include/LibreOfficeKit/LibreOfficeKit.hxx b/include/LibreOfficeKit/LibreOfficeKit.hxx index b6cdd929cb95..77facfb1867f 100644 --- a/include/LibreOfficeKit/LibreOfficeKit.hxx +++ b/include/LibreOfficeKit/LibreOfficeKit.hxx @@ -486,6 +486,9 @@ public: * e.g. {commandName: ".uno:StyleApply", commandValues: {"familyName1" : ["list of style names in the family1"], etc.}} * @param pCommand a UNO command for which the possible values are requested * @return {commandName: unoCmd, commandValues: {possible_values}} + * + * The return value is dynamically allocated and should be + * deallocated by calling the lok::Office::freeMemory() function. */ char* getCommandValues(const char* pCommand) { @@ -1009,7 +1012,8 @@ public: return new Document(pDoc); } - /// Returns the last error as a string, the returned pointer has to be freed by the caller. + /// Returns the last error as a string. The returned pointer has to be freed by the caller + /// by calling the freeError() member function. char* getError() { return mpThis->pClass->getError(mpThis); @@ -1018,6 +1022,10 @@ public: /** * Frees the memory pointed to by pFree. * + * Use on dynamically allocated data returned by LibreOfficeKit + * functions. In other cases than the value returned by + * getError(), call freeMemory() instead for clarity. + * * @since LibreOffice 5.2 */ void freeError(char* pFree) @@ -1316,6 +1324,17 @@ public: { return mpThis->pClass->getDocsCount(mpThis); } + + /** + * Frees the memory pointed to by pFree. + * + * Use on dynamically allocated data returned by LibreOfficeKit + * functions. Just a wrapper for freeError() with a better name. + */ + void freeMemory(char* pFree) + { + freeError(pFree); + } }; /// Factory method to create a lok::Office instance.
