LibreOffice Module connectivity (master) 1
mysqlc_preparedstatement.cxx
Go to the documentation of this file.
1/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2/*
3 * This file is part of the LibreOffice project.
4 *
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8 *
9 * This file incorporates work covered by the following license notice:
10 *
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
18 */
19
20#include "mysqlc_general.hxx"
25
26#include <o3tl/safeint.hxx>
27#include <sal/log.hxx>
28
29#include <com/sun/star/sdbc/DataType.hpp>
30
31#include <stdio.h>
32
33using namespace connectivity::mysqlc;
34using namespace com::sun::star::uno;
35using namespace com::sun::star::lang;
36using namespace com::sun::star::beans;
37using namespace com::sun::star::sdbc;
38using namespace com::sun::star::container;
39using namespace com::sun::star::io;
40using namespace com::sun::star::util;
41using ::osl::MutexGuard;
42
43OUString OPreparedStatement::getImplementationName()
44{
45 return "com.sun.star.sdbcx.mysqlc.PreparedStatement";
46}
47
49{
50 return { "com.sun.star.sdbc.PreparedStatement" };
51}
52
54{
56}
57
58OPreparedStatement::OPreparedStatement(OConnection* _pConnection, MYSQL_STMT* pStmt)
59 : OCommonStatement(_pConnection)
60 , m_pStmt(pStmt)
61{
62 m_paramCount = mysql_stmt_param_count(m_pStmt);
63 m_binds.reserve(m_paramCount);
65 for (unsigned i = 0; i < m_paramCount; ++i)
66 {
67 m_binds.push_back(MYSQL_BIND{});
68 m_bindMetas.push_back(BindMetaData{});
69 m_binds.back().is_null = &m_bindMetas.back().is_null;
70 m_binds.back().length = &m_bindMetas.back().length;
71 m_binds.back().buffer = nullptr;
72 }
73}
74
76
78
80
82{
84 if (!aRet.hasValue())
85 {
87 }
88 return aRet;
89}
90
91Sequence<Type> SAL_CALL OPreparedStatement::getTypes()
92{
94}
95
96Reference<XResultSetMetaData> SAL_CALL OPreparedStatement::getMetaData()
97{
98 MutexGuard aGuard(m_aMutex);
100
101 if (!m_xMetaData.is())
102 {
103 MYSQL_RES* pRes = mysql_stmt_result_metadata(m_pStmt);
104 // TODO warning or error if no meta data.
106 }
107 return m_xMetaData;
108}
109
111{
112 MutexGuard aGuard(m_aMutex);
114
115 if (mysql_stmt_close(m_pStmt))
116 {
117 SAL_WARN("connectivity.mysqlc", "failed to close mysql prepared statement");
118 }
119 m_pStmt = nullptr; // it's deallocated already
123}
124
126{
127 MutexGuard aGuard(m_aMutex);
129
130 if (!m_binds.empty() && mysql_stmt_bind_param(m_pStmt, m_binds.data()))
131 {
132 MYSQL* pMysql = m_xConnection->getMysqlConnection();
134 mysql_sqlstate(pMysql), mysql_errno(pMysql),
135 *this, m_xConnection->getConnectionEncoding());
136 }
137
138 int nFail = mysql_stmt_execute(m_pStmt);
139 if (nFail != 0)
140 {
141 MYSQL* pMysql = m_xConnection->getMysqlConnection();
143 mysql_sqlstate(pMysql), mysql_errno(pMysql),
144 *this, m_xConnection->getConnectionEncoding());
145 }
146
147 return !nFail;
148}
149
151{
152 MutexGuard aGuard(m_aMutex);
154
155 if (!m_binds.empty() && mysql_stmt_bind_param(m_pStmt, m_binds.data()))
156 {
157 MYSQL* pMysql = m_xConnection->getMysqlConnection();
159 mysql_sqlstate(pMysql), mysql_errno(pMysql),
160 *this, m_xConnection->getConnectionEncoding());
161 }
162
163 int nFail = mysql_stmt_execute(m_pStmt);
164
165 if (nFail != 0)
166 {
167 MYSQL* pMysql = m_xConnection->getMysqlConnection();
169 mysql_sqlstate(pMysql), mysql_errno(pMysql),
170 *this, m_xConnection->getConnectionEncoding());
171 }
172
173 sal_Int32 affectedRows = mysql_stmt_affected_rows(m_pStmt);
174 return affectedRows;
175}
176
177void SAL_CALL OPreparedStatement::setString(sal_Int32 parameter, const OUString& x)
178{
179 MutexGuard aGuard(m_aMutex);
181 checkParameterIndex(parameter);
182
183 OString stringie(OUStringToOString(x, m_xConnection->getConnectionEncoding()));
184 const sal_Int32 nIndex = parameter - 1;
185 m_binds[nIndex].buffer_type = MYSQL_TYPE_STRING;
186 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, stringie.getStr(), MYSQL_TYPE_STRING,
187 stringie.getLength());
188 m_bindMetas[nIndex].is_null = false;
189 m_bindMetas[nIndex].length = stringie.getLength();
190}
191
192Reference<XConnection> SAL_CALL OPreparedStatement::getConnection()
193{
194 MutexGuard aGuard(m_aMutex);
196
197 return m_xConnection;
198}
199
200Reference<XResultSet> SAL_CALL OPreparedStatement::executeQuery()
201{
202 MutexGuard aGuard(m_aMutex);
204
205 if (!m_binds.empty() && mysql_stmt_bind_param(m_pStmt, m_binds.data()))
206 {
207 MYSQL* pMysql = m_xConnection->getMysqlConnection();
209 mysql_sqlstate(pMysql), mysql_errno(pMysql),
210 *this, m_xConnection->getConnectionEncoding());
211 }
212
213 int nFail = mysql_stmt_execute(m_pStmt);
214
215 if (nFail != 0)
216 {
217 MYSQL* pMysql = m_xConnection->getMysqlConnection();
219 mysql_sqlstate(pMysql), mysql_errno(pMysql),
220 *this, m_xConnection->getConnectionEncoding());
221 }
222
223 Reference<XResultSet> xResultSet = new OPreparedResultSet(*m_xConnection, this, m_pStmt);
224 return xResultSet;
225}
226
227void SAL_CALL OPreparedStatement::setBoolean(sal_Int32 parameter, sal_Bool x)
228{
229 MutexGuard aGuard(m_aMutex);
231 checkParameterIndex(parameter);
232
233 const sal_Int32 nIndex = parameter - 1;
234 m_binds[nIndex].buffer_type = MYSQL_TYPE_TINY;
235 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &x, MYSQL_TYPE_TINY);
236 m_bindMetas[nIndex].is_null = false;
237}
238
239void SAL_CALL OPreparedStatement::setByte(sal_Int32 parameter, sal_Int8 x)
240{
241 MutexGuard aGuard(m_aMutex);
243 checkParameterIndex(parameter);
244
245 const sal_Int32 nIndex = parameter - 1;
246 m_binds[nIndex].buffer_type = MYSQL_TYPE_TINY;
247 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &x, MYSQL_TYPE_TINY);
248 m_bindMetas[nIndex].is_null = false;
249}
250
251void SAL_CALL OPreparedStatement::setDate(sal_Int32 parameter, const Date& aData)
252{
253 MutexGuard aGuard(m_aMutex);
255 checkParameterIndex(parameter);
256
257 MYSQL_TIME my_time = {};
258
259 my_time.year = aData.Year;
260 my_time.month = aData.Month;
261 my_time.day = aData.Day;
262
263 const sal_Int32 nIndex = parameter - 1;
264 m_binds[nIndex].buffer_type = MYSQL_TYPE_DATE;
265 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &my_time, MYSQL_TYPE_DATE);
266 m_bindMetas[nIndex].is_null = false;
267}
268
269void SAL_CALL OPreparedStatement::setTime(sal_Int32 parameter, const Time& aVal)
270{
271 MutexGuard aGuard(m_aMutex);
273 checkParameterIndex(parameter);
274
275 MYSQL_TIME my_time = {};
276
277 my_time.hour = aVal.Hours;
278 my_time.minute = aVal.Minutes;
279 my_time.second = aVal.Seconds;
280
281 const sal_Int32 nIndex = parameter - 1;
282 m_binds[nIndex].buffer_type = MYSQL_TYPE_TIME;
283 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &my_time, MYSQL_TYPE_TIME);
284 m_bindMetas[nIndex].is_null = false;
285}
286
287void SAL_CALL OPreparedStatement::setTimestamp(sal_Int32 parameter, const DateTime& aVal)
288{
289 MutexGuard aGuard(m_aMutex);
291 checkParameterIndex(parameter);
292
293 MYSQL_TIME my_time = {};
294
295 my_time.hour = aVal.Hours;
296 my_time.minute = aVal.Minutes;
297 my_time.second = aVal.Seconds;
298 my_time.year = aVal.Year;
299 my_time.month = aVal.Month;
300 my_time.day = aVal.Day;
301
302 const sal_Int32 nIndex = parameter - 1;
303 m_binds[nIndex].buffer_type = MYSQL_TYPE_DATETIME;
304 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &my_time, MYSQL_TYPE_DATETIME);
305 m_bindMetas[nIndex].is_null = false;
306}
307
308void SAL_CALL OPreparedStatement::setDouble(sal_Int32 parameter, double x)
309{
310 MutexGuard aGuard(m_aMutex);
312 checkParameterIndex(parameter);
313
314 const sal_Int32 nIndex = parameter - 1;
315 m_binds[nIndex].buffer_type = MYSQL_TYPE_DOUBLE;
316 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &x, MYSQL_TYPE_DOUBLE);
317 m_bindMetas[nIndex].is_null = false;
318}
319
320void SAL_CALL OPreparedStatement::setFloat(sal_Int32 parameter, float x)
321{
322 MutexGuard aGuard(m_aMutex);
324 checkParameterIndex(parameter);
325
326 const sal_Int32 nIndex = parameter - 1;
327 m_binds[nIndex].buffer_type = MYSQL_TYPE_FLOAT;
328 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &x, MYSQL_TYPE_FLOAT);
329 m_bindMetas[nIndex].is_null = false;
330}
331
332void SAL_CALL OPreparedStatement::setInt(sal_Int32 parameter, sal_Int32 x)
333{
334 MutexGuard aGuard(m_aMutex);
336 checkParameterIndex(parameter);
337
338 const sal_Int32 nIndex = parameter - 1;
339 m_binds[nIndex].buffer_type = MYSQL_TYPE_LONG;
340 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &x, MYSQL_TYPE_LONG);
341 m_bindMetas[nIndex].is_null = false;
342}
343
344void SAL_CALL OPreparedStatement::setLong(sal_Int32 parameter, sal_Int64 aVal)
345{
346 MutexGuard aGuard(m_aMutex);
348 checkParameterIndex(parameter);
349
350 const sal_Int32 nIndex = parameter - 1;
351 m_binds[nIndex].buffer_type = MYSQL_TYPE_LONGLONG;
352 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &aVal, MYSQL_TYPE_LONGLONG);
353 m_bindMetas[nIndex].is_null = false;
354}
355
356void SAL_CALL OPreparedStatement::setNull(sal_Int32 parameter, sal_Int32 /*sqlType*/)
357{
358 MutexGuard aGuard(m_aMutex);
360 checkParameterIndex(parameter);
361
362 const sal_Int32 nIndex = parameter - 1;
363 m_bindMetas[nIndex].is_null = true;
364 free(m_binds[nIndex].buffer);
365 m_binds[nIndex].buffer = nullptr;
366}
367
368void SAL_CALL OPreparedStatement::setClob(sal_Int32 parameter, const Reference<XClob>& /* x */)
369{
370 MutexGuard aGuard(m_aMutex);
372 checkParameterIndex(parameter);
373
374 mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::setClob", *this);
375}
376
377void SAL_CALL OPreparedStatement::setBlob(sal_Int32 parameter, const Reference<XBlob>& /* x */)
378{
379 MutexGuard aGuard(m_aMutex);
381 checkParameterIndex(parameter);
382
383 mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::setBlob", *this);
384}
385
386void SAL_CALL OPreparedStatement::setArray(sal_Int32 parameter, const Reference<XArray>& /* x */)
387{
388 MutexGuard aGuard(m_aMutex);
390 checkParameterIndex(parameter);
391
392 mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::setArray", *this);
393}
394
395void SAL_CALL OPreparedStatement::setRef(sal_Int32 parameter, const Reference<XRef>& /* x */)
396{
397 MutexGuard aGuard(m_aMutex);
399 checkParameterIndex(parameter);
400
401 mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::setRef", *this);
402}
403
404void SAL_CALL OPreparedStatement::setObjectWithInfo(sal_Int32 parameterIndex, const Any& value,
405 sal_Int32 targetSqlType, sal_Int32 /* scale */)
406{
408 MutexGuard aGuard(m_aMutex);
409 checkParameterIndex(parameterIndex);
410
411 const sal_Int32 nIndex = parameterIndex - 1;
412 if (!value.hasValue())
413 {
414 free(m_binds[nIndex].buffer);
415 m_binds[nIndex].buffer = nullptr;
416 m_bindMetas[parameterIndex - 1].is_null = true;
417 return;
418 }
419
420 switch (targetSqlType)
421 {
422 case DataType::DECIMAL:
423 case DataType::NUMERIC:
424 {
425 double nValue(0.0);
426 OUString sValue;
427 if (value >>= nValue)
428 {
429 setDouble(parameterIndex, nValue);
430 break;
431 }
432 else if (value >>= sValue)
433 {
434 OString sAscii
435 = OUStringToOString(sValue, getOwnConnection()->getConnectionEncoding());
436 std::stringstream sStream{ std::string(sAscii) };
437 sStream >> nValue;
438 m_binds[nIndex].buffer_type = MYSQL_TYPE_DOUBLE;
439 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &nValue, MYSQL_TYPE_DOUBLE,
440 sValue.getLength());
441 m_bindMetas[nIndex].is_null = false;
442 break;
443 }
444
445 [[fallthrough]];
446 }
447
448 // TODO other types
449
450 default:
452 "OPreparedStatement::setObjectWithInfo", *this);
453 break;
454 }
455}
456
457void SAL_CALL OPreparedStatement::setObjectNull(sal_Int32 parameter, sal_Int32 /* sqlType */,
458 const OUString& /* typeName */)
459{
460 MutexGuard aGuard(m_aMutex);
462 checkParameterIndex(parameter);
463
464 mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::setObjectNull",
465 *this);
466}
467
468void SAL_CALL OPreparedStatement::setObject(sal_Int32 parameter, const Any& /* x */)
469{
470 MutexGuard aGuard(m_aMutex);
472 checkParameterIndex(parameter);
473
474 mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::setObject", *this);
475}
476
477void SAL_CALL OPreparedStatement::setShort(sal_Int32 parameter, sal_Int16 x)
478{
479 MutexGuard aGuard(m_aMutex);
481 checkParameterIndex(parameter);
482
483 const sal_Int32 nIndex = parameter - 1;
484 m_binds[nIndex].buffer_type = MYSQL_TYPE_SHORT;
485 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &x, MYSQL_TYPE_SHORT);
486 m_bindMetas[nIndex].is_null = false;
487}
488
489void SAL_CALL OPreparedStatement::setBytes(sal_Int32 parameter, const Sequence<sal_Int8>& x)
490{
491 MutexGuard aGuard(m_aMutex);
493 checkParameterIndex(parameter);
494
495 const sal_Int32 nIndex = parameter - 1;
496 m_binds[nIndex].buffer_type = MYSQL_TYPE_BLOB;
497 mysqlc_sdbc_driver::resetSqlVar(&m_binds[nIndex].buffer, &x[0], MYSQL_TYPE_BLOB, x.getLength());
498 m_bindMetas[nIndex].is_null = false;
499 m_bindMetas[nIndex].length = x.getLength();
500}
501
502void SAL_CALL OPreparedStatement::setCharacterStream(sal_Int32 parameter,
503 const Reference<XInputStream>& /* x */,
504 sal_Int32 /* length */)
505{
506 MutexGuard aGuard(m_aMutex);
508 checkParameterIndex(parameter);
509
511 "OPreparedStatement::setCharacterStream", *this);
512}
513
514void SAL_CALL OPreparedStatement::setBinaryStream(sal_Int32 parameter,
515 const Reference<XInputStream>& /* x */,
516 sal_Int32 /* length */)
517{
518 MutexGuard aGuard(m_aMutex);
520 checkParameterIndex(parameter);
521
522 mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::setBinaryStream",
523 *this);
524}
525
527{
528 MutexGuard aGuard(m_aMutex);
530
531 for (size_t i = 0; i < m_binds.size(); ++i)
532 {
533 m_bindMetas[i].is_null = true;
534 free(m_binds[i].buffer);
535 m_binds[i].buffer = nullptr;
536 }
537}
538
539// void SAL_CALL OPreparedStatement::clearBatch()
540// {
541// mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::clearBatch",
542// *this);
543// }
544
545// void SAL_CALL OPreparedStatement::addBatch()
546// {
547// mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::addBatch", *this);
548// }
549
550// Sequence<sal_Int32> SAL_CALL OPreparedStatement::executeBatch() {
551// mysqlc_sdbc_driver::throwFeatureNotImplementedException("OPreparedStatement::executeBatch", *this);
552// }
553
554void OPreparedStatement::setFastPropertyValue_NoBroadcast(sal_Int32 nHandle, const Any& rValue)
555{
556 switch (nHandle)
557 {
559 break;
561 break;
563 break;
565 break;
566 default:
567 /* XXX: Recursion ?? */
569 }
570}
571
573{
574 if (column < 1 || o3tl::make_unsigned(column) > m_paramCount)
575 {
576 throw SQLException("Parameter index out of range", *this, OUString(), 1, Any());
577 }
578}
579
580/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
constexpr OUStringLiteral sStream
void SAL_CALL acquire() noexcept override
Any SAL_CALL queryInterface(const css::uno::Type &rType) override
rtl::Reference< OConnection > m_xConnection
css::uno::Sequence< css::uno::Type > SAL_CALL getTypes() override
void SAL_CALL release() noexcept override
void SAL_CALL setArray(sal_Int32 parameter, const Reference< css::sdbc::XArray > &x) override
void SAL_CALL setObject(sal_Int32 parameter, const Any &x) override
void SAL_CALL setBoolean(sal_Int32 parameter, sal_Bool x) override
OPreparedStatement(OConnection *_pConnection, MYSQL_STMT *pStmt)
void SAL_CALL setRef(sal_Int32 parameter, const Reference< css::sdbc::XRef > &x) override
void SAL_CALL setByte(sal_Int32 parameter, sal_Int8 x) override
void SAL_CALL setBlob(sal_Int32 parameter, const Reference< css::sdbc::XBlob > &x) override
void SAL_CALL setDate(sal_Int32 parameter, const css::util::Date &x) override
Reference< css::sdbc::XResultSet > SAL_CALL executeQuery() override
void SAL_CALL setFloat(sal_Int32 parameter, float x) override
void SAL_CALL setClob(sal_Int32 parameter, const Reference< css::sdbc::XClob > &x) override
virtual css::uno::Sequence< OUString > SAL_CALL getSupportedServiceNames() override
void SAL_CALL setObjectWithInfo(sal_Int32 parameter, const Any &x, sal_Int32 targetSqlType, sal_Int32 scale) override
void SAL_CALL setObjectNull(sal_Int32 parameter, sal_Int32 sqlType, const OUString &typeName) override
void SAL_CALL setCharacterStream(sal_Int32 parameter, const Reference< css::io::XInputStream > &x, sal_Int32 length) override
void SAL_CALL setNull(sal_Int32 parameter, sal_Int32 sqlType) override
virtual sal_Bool SAL_CALL supportsService(OUString const &ServiceName) override
void SAL_CALL setBytes(sal_Int32 parameter, const css::uno::Sequence< sal_Int8 > &x) override
css::uno::Sequence< Type > SAL_CALL getTypes() override
void SAL_CALL setString(sal_Int32 parameter, const OUString &x) override
Any SAL_CALL queryInterface(const Type &rType) override
Reference< css::sdbc::XConnection > SAL_CALL getConnection() override
void SAL_CALL setBinaryStream(sal_Int32 parameter, const Reference< css::io::XInputStream > &x, sal_Int32 length) override
Reference< css::sdbc::XResultSetMetaData > SAL_CALL getMetaData() override
void SAL_CALL setFastPropertyValue_NoBroadcast(sal_Int32 nHandle, const Any &rValue) override
void SAL_CALL setLong(sal_Int32 parameter, sal_Int64 x) override
void SAL_CALL setTimestamp(sal_Int32 parameter, const css::util::DateTime &x) override
void SAL_CALL setDouble(sal_Int32 parameter, double x) override
void SAL_CALL setTime(sal_Int32 parameter, const css::util::Time &x) override
void SAL_CALL setInt(sal_Int32 parameter, sal_Int32 x) override
void SAL_CALL setShort(sal_Int32 parameter, sal_Int16 x) override
mutable::osl::Mutex m_aMutex
virtual css::uno::Any SAL_CALL queryInterface(css::uno::Type const &rType) SAL_OVERRIDE
virtual css::uno::Sequence< css::uno::Type > SAL_CALL getTypes() SAL_OVERRIDE
OBroadcastHelper & rBHelper
Any value
float x
sal_Int16 nValue
sal_Int32 nIndex
#define SAL_WARN(area, stream)
constexpr OUStringLiteral aData
Type
void checkDisposed(bool _bThrow)
css::uno::Sequence< T > concatSequences(const css::uno::Sequence< T > &_rLeft, const css::uno::Sequence< T > &_rRight)
concat two sequences
bool CPPUHELPER_DLLPUBLIC supportsService(css::lang::XServiceInfo *implementation, rtl::OUString const &name)
int i
void throwInvalidArgumentException(const char *_pAsciiFeatureName, const css::uno::Reference< XInterface > &_rxContext)
void resetSqlVar(void **target, T *pValue, enum_field_types type, sal_Int32 nSize=0)
void throwSQLExceptionWithMsg(const char *msg, const char *SQLSTATE, unsigned int errorNum, const css::uno::Reference< css::uno::XInterface > &_context, const rtl_TextEncoding encoding)
void throwFeatureNotImplementedException(const char *_pAsciiFeatureName, const css::uno::Reference< XInterface > &_rxContext)
constexpr std::enable_if_t< std::is_signed_v< T >, std::make_unsigned_t< T > > make_unsigned(T value)
OString OUStringToOString(std::u16string_view str, ConnectionSettings const *settings)
Definition: pq_tools.cxx:100
sal_Int32 nHandle
unsigned char sal_Bool
signed char sal_Int8