return -1;
if (DestSize > 0)
- while (NewSize < DestSize)
+ while (NewSize <= DestSize)
NewSize *= 2;
NewBuf= (char*) malloc(NewSize);
*/
int FlushStrBuf(StrBuf *buf)
{
+ if (buf == NULL)
+ return -1;
if (buf->ConstBuf)
return -1;
buf->buf[0] ='\0';
*/
long StrTol(const StrBuf *Buf)
{
+ if (Buf == NULL)
+ return 0;
if(Buf->BufUsed > 0)
return atol(Buf->buf);
else
*/
int StrToi(const StrBuf *Buf)
{
- if(Buf->BufUsed > 0)
+ if (Buf == NULL)
+ return 0;
+ if (Buf->BufUsed > 0)
return atoi(Buf->buf);
else
return 0;
void StrBufAppendBufPlain(StrBuf *Buf, const char *AppendBuf, long AppendSize, size_t Offset)
{
long aps;
+ long BufSizeRequired;
if ((AppendBuf == NULL) || (Buf == NULL))
return;
else
aps = AppendSize - Offset;
- if (Buf->BufSize < Buf->BufUsed + aps)
- IncreaseBuf(Buf, (Buf->BufUsed > 0), Buf->BufUsed + aps);
+ BufSizeRequired = Buf->BufUsed + aps + 1;
+ if (Buf->BufSize <= BufSizeRequired)
+ IncreaseBuf(Buf, (Buf->BufUsed > 0), BufSizeRequired);
memcpy(Buf->buf + Buf->BufUsed,
AppendBuf + Offset,
bptr += 5;
Target->BufUsed += 5;
}
- else if (*aptr == '\"') {
+ else if (*aptr == '"') {
memcpy(bptr, """, 6);
bptr += 6;
Target->BufUsed += 6;
Buf->buf[Buf->BufUsed] = '\0';
}
+/**
+ * \brief Cut the string after n Chars
+ * \param Buf Buffer to modify
+ * \param AfternChars after how many chars should we trunkate the string?
+ * \param At if non-null and points inside of our string, cut it there.
+ */
+void StrBufCutAt(StrBuf *Buf, int AfternChars, const char *At)
+{
+ if (At != NULL){
+ AfternChars = At - Buf->buf;
+ }
+
+ if ((AfternChars < 0) || (AfternChars >= Buf->BufUsed))
+ return;
+ Buf->BufUsed = AfternChars;
+ Buf->buf[Buf->BufUsed] = '\0';
+}
+
/*
* Strip leading and trailing spaces from a string; with premeasured and adjusted length.
}
+void StrBufLowerCase(StrBuf *Buf)
+{
+ char *pch, *pche;
+
+ pch = Buf->buf;
+ pche = pch + Buf->BufUsed;
+ while (pch < pche) {
+ *pch = tolower(*pch);
+ pch ++;
+ }
+}
+
+
/**
* \brief unhide special chars hidden to the HTML escaper
* \param target buffer to put the unescaped string in
* tocode Target encoding
* fromcode Source encoding
*/
-static iconv_t ctdl_iconv_open(const char *tocode, const char *fromcode)
+void ctdl_iconv_open(const char *tocode, const char *fromcode, void *pic)
{
+#ifdef HAVE_ICONV
iconv_t ic = (iconv_t)(-1) ;
ic = iconv_open(tocode, fromcode);
if (ic == (iconv_t)(-1) ) {
ic = iconv_open(tocode, alias_fromcode);
}
}
- return(ic);
+ *(iconv_t *)pic = ic;
+#endif
}
-#ifdef HAVE_ICONV
-static inline char *FindNextEnd (StrBuf *Buf, char *bptr)
+static inline char *FindNextEnd (const StrBuf *Buf, char *bptr)
{
char * end;
/* Find the next ?Q? */
}
+void StrBufConvert(StrBuf *ConvertBuf, StrBuf *TmpBuf, void *pic)
+{
+#ifdef HAVE_ICONV
+ int BufSize;
+ iconv_t ic;
+ char *ibuf; /**< Buffer of characters to be converted */
+ char *obuf; /**< Buffer for converted characters */
+ size_t ibuflen; /**< Length of input buffer */
+ size_t obuflen; /**< Length of output buffer */
+
+
+ if (ConvertBuf->BufUsed > TmpBuf->BufSize)
+ IncreaseBuf(TmpBuf, 0, ConvertBuf->BufUsed);
+
+ ic = *(iconv_t*)pic;
+ ibuf = ConvertBuf->buf;
+ ibuflen = ConvertBuf->BufUsed;
+ obuf = TmpBuf->buf;
+ obuflen = TmpBuf->BufSize;
+
+ iconv(ic, &ibuf, &ibuflen, &obuf, &obuflen);
+
+ /* little card game: wheres the red lady? */
+ ibuf = ConvertBuf->buf;
+ BufSize = ConvertBuf->BufSize;
+
+ ConvertBuf->buf = TmpBuf->buf;
+ ConvertBuf->BufSize = TmpBuf->BufSize;
+ ConvertBuf->BufUsed = TmpBuf->BufSize - obuflen;
+ ConvertBuf->buf[ConvertBuf->BufUsed] = '\0';
+
+ TmpBuf->buf = ibuf;
+ TmpBuf->BufSize = BufSize;
+ TmpBuf->BufUsed = 0;
+ TmpBuf->buf[0] = '\0';
+#endif
+}
+
+
+
inline static void DecodeSegment(StrBuf *Target,
- StrBuf *DecodeMe,
+ const StrBuf *DecodeMe,
char *SegmentStart,
char *SegmentEnd,
StrBuf *ConvertBuf,
- StrBuf *ConvertBuf2)
+ StrBuf *ConvertBuf2,
+ StrBuf *FoundCharset)
{
StrBuf StaticBuf;
char charset[128];
char encoding[16];
iconv_t ic = (iconv_t)(-1);
- char *ibuf; /**< Buffer of characters to be converted */
- char *obuf; /**< Buffer for converted characters */
- size_t ibuflen; /**< Length of input buffer */
- size_t obuflen; /**< Length of output buffer */
/* Now we handle foreign character sets properly encoded
* in RFC2047 format.
StaticBuf.BufUsed = SegmentEnd - SegmentStart;
StaticBuf.BufSize = DecodeMe->BufSize - (SegmentStart - DecodeMe->buf);
extract_token(charset, SegmentStart, 1, '?', sizeof charset);
+ if (FoundCharset != NULL) {
+ FlushStrBuf(FoundCharset);
+ StrBufAppendBufPlain(FoundCharset, charset, -1, 0);
+ }
extract_token(encoding, SegmentStart, 2, '?', sizeof encoding);
StrBufExtract_token(ConvertBuf, &StaticBuf, 3, '?');
- if (!strcasecmp(encoding, "B")) { /**< base64 */
+ *encoding = toupper(*encoding);
+ if (*encoding == 'B') { /**< base64 */
ConvertBuf2->BufUsed = CtdlDecodeBase64(ConvertBuf2->buf,
ConvertBuf->buf,
ConvertBuf->BufUsed);
}
- else if (!strcasecmp(encoding, "Q")) { /**< quoted-printable */
+ else if (*encoding == 'Q') { /**< quoted-printable */
long pos;
pos = 0;
else {
StrBufAppendBuf(ConvertBuf2, ConvertBuf, 0);
}
-
- ic = ctdl_iconv_open("UTF-8", charset);
- if (ic != (iconv_t)(-1) ) {
- ibuf = ConvertBuf2->buf;
- obuf = ConvertBuf->buf;
- ibuf = ConvertBuf2->buf;
- obuflen = ConvertBuf->BufSize;
- ibuflen = ConvertBuf2->BufUsed;
-
- iconv(ic, &ibuf, &ibuflen, &obuf, &obuflen);
- ConvertBuf->BufUsed = ConvertBuf->BufSize - obuflen;
- ConvertBuf->buf[ConvertBuf->BufUsed] = '\0';
-
- StrBufAppendBuf(Target, ConvertBuf, 0);
+
+ ctdl_iconv_open("UTF-8", charset, &ic);
+ if (ic != (iconv_t)(-1) ) {
+ StrBufConvert(ConvertBuf2, ConvertBuf, &ic);
+ StrBufAppendBuf(Target, ConvertBuf2, 0);
iconv_close(ic);
}
else {
* Handle subjects with RFC2047 encoding such as:
* =?koi8-r?B?78bP0s3Mxc7JxSDXz9rE1dvO2c3JINvB0sHNySDP?=
*/
-void StrBuf_RFC822_to_Utf8(StrBuf *Target, StrBuf *DecodeMe, const StrBuf* DefaultCharset)
+void StrBuf_RFC822_to_Utf8(StrBuf *Target, const StrBuf *DecodeMe, const StrBuf* DefaultCharset, StrBuf *FoundCharset)
{
StrBuf *ConvertBuf, *ConvertBuf2;
- char *start, *end, *next, *nextend, *ptr;
+ char *start, *end, *next, *nextend, *ptr = NULL;
iconv_t ic = (iconv_t)(-1) ;
- char *ibuf; /**< Buffer of characters to be converted */
- char *obuf; /**< Buffer for converted characters */
- size_t ibuflen; /**< Length of input buffer */
- size_t obuflen; /**< Length of output buffer */
-
const char *eptr;
int passes = 0;
int i, len, delta;
}
ConvertBuf = NewStrBufPlain(NULL, StrLength(DecodeMe));
- if (illegal_non_rfc2047_encoding) {
- if ( (strcasecmp(ChrPtr(DefaultCharset), "UTF-8")) &&
- (strcasecmp(ChrPtr(DefaultCharset), "us-ascii")) ) {
- ic = ctdl_iconv_open("UTF-8", ChrPtr(DefaultCharset));
- if (ic != (iconv_t)(-1) ) {
- long BufSize;
- ibuf = DecodeMe->buf;
- obuf = ConvertBuf->buf;
- ibuflen = DecodeMe->BufUsed;
- obuflen = ConvertBuf->BufSize;
-
- iconv(ic, &ibuf, &ibuflen, &obuf, &obuflen);
- /* little card game: wheres the red lady? */
- ibuf = DecodeMe->buf;
- BufSize = DecodeMe->BufSize;
- DecodeMe->buf = ConvertBuf->buf;
- DecodeMe->BufSize = ConvertBuf->BufSize;
- DecodeMe->BufUsed = ConvertBuf->BufSize - obuflen;
- DecodeMe->buf[DecodeMe->BufUsed] = '\0';
-
- ConvertBuf->buf = ibuf;
- ConvertBuf->BufSize = BufSize;
- ConvertBuf->BufUsed = 0;
- ConvertBuf->buf[0] = '\0';
-
- iconv_close(ic);
- }
+ if ((illegal_non_rfc2047_encoding) &&
+ (strcasecmp(ChrPtr(DefaultCharset), "UTF-8")) &&
+ (strcasecmp(ChrPtr(DefaultCharset), "us-ascii")) )
+ {
+ ctdl_iconv_open("UTF-8", ChrPtr(DefaultCharset), &ic);
+ if (ic != (iconv_t)(-1) ) {
+ StrBufConvert((StrBuf*)DecodeMe, ConvertBuf, &ic);///TODO: don't void const?
+ iconv_close(ic);
}
}
ConvertBuf2 = NewStrBufPlain(NULL, StrLength(DecodeMe));
+ if (start != DecodeMe->buf)
+ StrBufAppendBufPlain(Target, DecodeMe->buf, start - DecodeMe->buf, 0);
/*
* Since spammers will go to all sorts of absurd lengths to get their
* messages through, there are LOTS of corrupt headers out there.
start,
end,
ConvertBuf,
- ConvertBuf2);
+ ConvertBuf2,
+ FoundCharset);
next = strstr(end, "=?");
nextend = NULL;
len - (next - start));
/* now terminate the gab at the end */
- delta = (next - end) - 2;
- DecodeMe->BufUsed -= delta;
- DecodeMe->buf[DecodeMe->BufUsed] = '\0';
+ delta = (next - end) - 2; ////TODO: const!
+ ((StrBuf*)DecodeMe)->BufUsed -= delta;
+ ((StrBuf*)DecodeMe)->buf[DecodeMe->BufUsed] = '\0';
/* move next to its new location. */
next -= delta;
}
}
/* our next-pair is our new first pair now. */
+ ptr = end + 2;
start = next;
end = nextend;
}
+ end = ptr;
+ nextend = DecodeMe->buf + DecodeMe->BufUsed;
+ if ((end != NULL) && (end < nextend)) {
+ ptr = end;
+ while ( (ptr < nextend) &&
+ (isspace(*ptr) ||
+ (*ptr == '\r') ||
+ (*ptr == '\n') ||
+ (*ptr == '\t')))
+ ptr ++;
+ if (ptr < nextend)
+ StrBufAppendBufPlain(Target, end, nextend - end, 0);
+ }
FreeStrBuf(&ConvertBuf);
FreeStrBuf(&ConvertBuf2);
}
-#else
-void StrBuf_RFC822_to_Utf8(StrBuf **Buf, const StrBuf* DefaultCharset) {};
-
-#endif
}
return Buf->BufUsed;
}
+
+
+
+int StrBufSipLine(StrBuf *LineBuf, StrBuf *Buf, const char **Ptr)
+{
+ const char *aptr, *ptr, *eptr;
+ char *optr, *xptr;
+
+ if (Buf == NULL)
+ return 0;
+
+ if (*Ptr==NULL)
+ ptr = aptr = Buf->buf;
+ else
+ ptr = aptr = *Ptr;
+
+ optr = LineBuf->buf;
+ eptr = Buf->buf + Buf->BufUsed;
+ xptr = LineBuf->buf + LineBuf->BufSize;
+
+ while ((*ptr != '\n') &&
+ (*ptr != '\r') &&
+ (ptr < eptr))
+ {
+ *optr = *ptr;
+ optr++; ptr++;
+ if (optr == xptr) {
+ LineBuf->BufUsed = optr - LineBuf->buf;
+ IncreaseBuf(LineBuf, 1, LineBuf->BufUsed + 1);
+ optr = LineBuf->buf + LineBuf->BufUsed;
+ xptr = LineBuf->buf + LineBuf->BufSize;
+ }
+ }
+ LineBuf->BufUsed = optr - LineBuf->buf;
+ *optr = '\0';
+ if (*ptr == '\r')
+ ptr ++;
+ if (*ptr == '\n')
+ ptr ++;
+
+ *Ptr = ptr;
+
+ return Buf->BufUsed - (ptr - Buf->buf);
+}