34#ifndef QORE_QORE_STRING_PRIVATE_H
35#define QORE_QORE_STRING_PRIVATE_H
39#define MAX_INT_STRING_LEN 48
40#define MAX_BIGINT_STRING_LEN 48
41#define MAX_FLOAT_STRING_LEN 48
42#define STR_CLASS_BLOCK (0x10 * 4)
43#define STR_CLASS_EXTRA (0x10 * 3)
45#define MIN_SPRINTF_BUFSIZE 64
51typedef std::vector<int> intvec_t;
53hashdecl qore_string_private {
60 DLLLOCAL qore_string_private() {
63 DLLLOCAL qore_string_private(
const qore_string_private &p) {
64 allocated = p.len + STR_CLASS_EXTRA;
65 allocated = (allocated / 0x10 + 1) * 0x10;
66 buf = (
char*)malloc(
sizeof(
char) * allocated);
69 memcpy(buf, p.buf, len);
71 encoding = p.getEncoding();
74 DLLLOCAL ~qore_string_private() {
80 DLLLOCAL
void check_char(
size_t i) {
83 allocated = i + (d < STR_CLASS_BLOCK ? STR_CLASS_BLOCK : d);
84 allocated = (allocated / 0x10 + 1) * 0x10;
85 buf = (
char*)realloc(buf, allocated *
sizeof(
char));
91 offset = len + offset;
92 return offset < 0 ? 0 : offset;
95 return ((
size_t)offset > len) ? len : offset;
99 n_offset = check_offset(offset);
102 num = len + num - n_offset;
121 if (!(p = strchr(buf + pos, c)))
137 const char* p = buf + pos;
158 if (!(p = strstr(buf + pos, str))) {
175 const char* p = buf + pos;
177 for (
const char* t = str; *t; ++t) {
187 DLLLOCAL
static qore_offset_t index_simple(
const char* haystack,
size_t hlen,
const char* needle,
size_t nlen,
189 const char* start = haystack + pos;
190 void* ptr =
q_memmem(start, hlen - pos, needle, nlen);
194 return reinterpret_cast<const char*
>(ptr) - start + pos;
204 if (!getEncoding()->isMultiByte()) {
214 return index_simple(buf, len, needle->c_str(), needle->size(), pos);
218 if (findByteOffset(pos, xsink))
225 qore_offset_t ind = index_simple(buf + pos, len - pos, needle->c_str(), needle->size());
227 ind = getEncoding()->getCharPos(buf, buf + pos + ind, xsink);
236 if (needle.
strlen() + pos > len)
239 return bindex(needle.
c_str(), pos, needle.
size());
243 if (needle.size() + pos > len)
246 return bindex(needle.c_str(), pos, needle.size());
260 nsize = strlen(needle);
262 return index_simple(buf, len, needle, nsize, pos);
267 DLLLOCAL
static qore_offset_t rindex_simple(
const char* haystack,
size_t hlen,
const char* needle,
279 void* ptr =
q_memrmem(haystack, pos + 1, needle, nlen);
283 return static_cast<qore_offset_t>(
reinterpret_cast<const char*
>(ptr) -
284 reinterpret_cast<const char*
>(haystack));
290 assert(getEncoding()->isMultiByte());
296 size_t clen = getEncoding()->getLength(buf + start, buf + len, xsink);
302 pos = getEncoding()->getByteLen(buf + start, buf + len, pos, xsink);
303 return *xsink ? -1 : 0;
312 if (!getEncoding()->isMultiByte()) {
319 return rindex_simple(buf, len, needle->c_str(), needle->size(), pos);
323 if (findByteOffset(pos, xsink))
329 qore_offset_t ind = rindex_simple(buf, len, needle->c_str(), needle->size(), pos);
332 if (ind && ind != -1) {
333 ind = getEncoding()->getCharPos(buf, buf + ind, xsink);
346 return brindex(needle.c_str(), needle.size(), pos);
359 if (pos == -1 && !len && !needle_len) {
365 if (needle_len + (len - pos) > len) {
369 return rindex_simple(buf, len, needle, needle_len, pos);
372 DLLLOCAL
bool startsWith(
const char* str,
size_t ssize)
const {
373 return !strncmp(str, buf, ssize);
376 DLLLOCAL
bool endsWith(
const char* str,
size_t ssize)
const {
380 return !strncmp(str, buf + len - ssize, ssize);
383 DLLLOCAL
bool isDataPrintableAscii()
const {
384 for (
size_t i = 0; i < len; ++i) {
385 if (buf[i] < 32 || buf[i] > 126)
391 DLLLOCAL
bool isDataAscii()
const {
392 for (
size_t i = 0; i < len; ++i) {
393 if ((
unsigned char)(buf[i]) > 127)
399 DLLLOCAL
void concat_intern(
const char* p,
size_t plen) {
402 check_char(len + plen);
403 memcpy(buf + len, p, plen);
408 DLLLOCAL
void concat_simple(
const qore_string_private& str,
qore_offset_t pos) {
417 concat_intern(str.buf + pos, str.len - pos);
421 assert(str.getEncoding() == getEncoding());
423 if (!getEncoding()->isMultiByte()) {
424 concat_simple(str, pos);
430 if (str.findByteOffset(pos, xsink))
438 concat_intern(str.buf + pos, str.len - pos);
451 plen = str.len + plen;
457 concat_intern(str.buf + pos, plen);
461 assert(str.getEncoding() == getEncoding());
464 if (!getEncoding()->isMultiByte()) {
465 concat_simple(str, pos);
471 if (str.findByteOffset(pos, xsink))
480 if (str.findByteOffset(plen, xsink, pos))
487 concat_intern(str.buf + pos, plen);
495 rc = getEncoding()->getByteLen(buf, buf + len, i, xsink);
503 DLLLOCAL
size_t removeBytes(
size_t num) {
508 memmove(buf, buf + num, len - num);
513 DLLLOCAL
void clear() {
520 DLLLOCAL
void concat(
char c) {
528 allocated = STR_CLASS_BLOCK;
530 buf = (
char*)malloc(
sizeof(
char) * allocated);
535 DLLLOCAL
void concat(
const qore_string_private* str) {
536 assert(!str || (str->encoding == encoding) || !str->encoding);
539 if (str && str->len) {
541 check_char(str->len + len + STR_CLASS_EXTRA);
543 memcpy(buf + len, str->buf, str->len);
549 DLLLOCAL
void concat(
const char *str) {
558 buf[len++] = str[i++];
570 DLLLOCAL
int vsprintf(
const char *fmt, va_list args) {
571 size_t fmtlen = ::strlen(fmt);
573 if ((allocated - len - fmtlen) < MIN_SPRINTF_BUFSIZE) {
574 allocated += fmtlen + MIN_SPRINTF_BUFSIZE;
575 allocated = (allocated / 0x10 + 1) * 0x10;
577 buf = (
char*)realloc(buf, allocated *
sizeof(
char));
583 int i = ::vsnprintf(buf + len, free, fmt, args);
591 allocated += STR_CLASS_EXTRA;
592 allocated = (allocated / 0x10 + 1) * 0x10;
593 buf = (
char*)realloc(buf,
sizeof(
char) * allocated);
602 allocated = len + i + STR_CLASS_EXTRA;
603 allocated = (allocated / 0x10 + 1) * 0x10;
604 buf = (
char*)realloc(buf,
sizeof(
char) * allocated);
614 DLLLOCAL
int sprintf(
const char *fmt, ...) {
618 int rc = vsprintf(fmt, args);
626 DLLLOCAL
void concatUTF8FromUnicode(
unsigned code);
628 DLLLOCAL
int concatUnicode(
unsigned code,
ExceptionSink *xsink) {
631 concatUTF8FromUnicode(code);
636 tmp.concatUTF8FromUnicode(code);
637 TempString ns(tmp.convertEncoding(getEncoding(), xsink));
644 DLLLOCAL
void setRegexBaseOpts(QoreRegexBase& re,
int opts);
646 DLLLOCAL
void setRegexOpts(QoreRegexSubst& re,
int opts);
648 DLLLOCAL
void splice_simple(
size_t offset,
size_t length,
QoreString* extract =
nullptr);
649 DLLLOCAL
void splice_simple(
size_t offset,
size_t length,
const char* str,
size_t str_len,
662 DLLLOCAL
int trimLeading(
ExceptionSink* xsink,
const intvec_t& vec);
663 DLLLOCAL
int trimLeading(
ExceptionSink* xsink,
const qore_string_private* chars);
664 DLLLOCAL
int trimTrailing(
ExceptionSink* xsink,
const intvec_t& vec);
665 DLLLOCAL
int trimTrailing(
ExceptionSink* xsink,
const qore_string_private* chars);
667 DLLLOCAL
void terminate(
size_t size);
669 DLLLOCAL
int concatUnicode(
unsigned code);
671 DLLLOCAL
int concatDecodeUriIntern(
ExceptionSink* xsink,
const qore_string_private& str,
672 bool detect_query =
false);
674 DLLLOCAL
int concatEncodeUriRequest(
ExceptionSink* xsink,
const qore_string_private& str);
676 DLLLOCAL
unsigned int getUnicodePointFromBytePos(
size_t offset,
unsigned& len,
ExceptionSink* xsink)
const;
681 DLLLOCAL
int getUnicodeCharArray(intvec_t& vec,
ExceptionSink* xsink)
const {
685 int c = getUnicodePointFromBytePos((
qore_offset_t)j, clen, xsink);
694 DLLLOCAL
int allocate(
unsigned requested_size) {
695 if ((
unsigned)allocated >= requested_size)
697 requested_size = (requested_size / 0x10 + 1) * 0x10;
698 char* aux = (
char*)realloc(buf, requested_size *
sizeof(
char));
705 allocated = requested_size;
715 DLLLOCAL
void concatBase64(
const char* bbuf,
size_t size,
size_t maxlinelen,
bool url_encode =
false);
717 DLLLOCAL
static bool inVector(
int c,
const intvec_t& vec) {
718 for (
unsigned j = 0; j < vec.size(); ++j) {
719 if ((
int)vec[j] == c)
725 DLLLOCAL
static qore_string_private* get(
QoreString& str) {
729 DLLLOCAL
static int getHex(
const char*& p) {
730 if (*p ==
'%' && isxdigit(*(p + 1)) && isxdigit(*(p + 2))) {
731 char x[3] = { *(p + 1), *(p + 2),
'\0' };
733 return strtol(x, 0, 16);
738 DLLLOCAL
static int convert_encoding_intern(
const char* src,
size_t src_len,
const QoreEncoding* from,
753 qore_string_private *p =
new qore_string_private;
754 p->len = b->size() - 1;
755 p->buf = (
char*)b->giveBuffer();
762 if (p->buf[p->len]) {
764 p->buf = (
char*)realloc(p->buf, p->len + 1);
765 p->buf[p->len] =
'\0';
768 p->allocated = p->len + 1;
DLLEXPORT const QoreEncoding * QCS_UTF8
UTF-8 multi-byte encoding (only UTF-8 and UTF-16 are multi-byte encodings)
Definition QoreEncoding.h:247
DLLEXPORT const QoreEncoding * QCS_USASCII
ascii encoding
Definition QoreEncoding.h:246
DLLEXPORT void * q_memrmem(const void *big, size_t big_len, const void *little, size_t little_len)
finds a memory sequence in a larger memory sequence searching from the end of the sequence
DLLEXPORT void * q_memmem(const void *big, size_t big_len, const void *little, size_t little_len)
finds a memory sequence in a larger memory sequence
holds arbitrary binary data
Definition BinaryNode.h:41
container for holding Qore-language exception information and also for registering a "thread_exit" ca...
Definition ExceptionSink.h:50
defines string encoding functions in Qore
Definition QoreEncoding.h:83
Qore's string type supported by the QoreEncoding class.
Definition QoreString.h:93
DLLEXPORT const char * c_str() const
returns the string's buffer; this data should not be changed
DLLEXPORT size_t strlen() const
returns number of bytes in the string (not including the null pointer)
DLLEXPORT const char * getBuffer() const
returns the string's buffer; this data should not be changed
DLLEXPORT size_t size() const
returns number of bytes in the string (not including the null pointer)
hashdecl qore_string_private * priv
the private implementation of QoreString
Definition QoreString.h:1100
Qore's string value type, reference counted, dynamically-allocated only.
Definition QoreStringNode.h:50
manages a reference count of a pointer to a class that takes a simple "deref()" call with no argument...
Definition ReferenceHolder.h:127
use this class to manage strings where the character encoding must be specified and may be different ...
Definition QoreString.h:1198
class used to hold a possibly temporary QoreString pointer, stack only, cannot be dynamically allocat...
Definition QoreString.h:1139
intptr_t qore_offset_t
used for offsets that could be negative
Definition common.h:82
#define CD_ALL
code for decoding everything
Definition QoreString.h:73
#define CE_XHTML
code for encoding XHTML entities
Definition QoreString.h:55