Hi everyone,
maybe some people react like me whenever they take a look at mime.c, the
code is REALLY crude.
A long time ago I started to rewrite it, but never had the time to
finish, because a lot of other things happened. But currently I've some
spare time and looked over the code again and .... it still looks the
same. ;)
So here is a first patch for mime_decode_qp_char, i took it from my old
changes against 4.5X, but AFAICT the code still works the same way.
Over the next days, whenever I find some time, I will send more patches
I just need some more time for testing. ;)
Nico
--- mime.c.org 2006-08-07 13:12:23.000000000 +0200
+++ mime.c 2006-08-07 13:14:08.000000000 +0200
@@ -41,80 +41,41 @@
0-255 - char to write
*/
-unsigned int mime_qp_hstr_i(uschar *cptr) {
- unsigned int i, j = 0;
- while (cptr && *cptr && isxdigit(*cptr)) {
- i = *cptr++ - '0';
- if (9 < i) i -= 7;
- j <<= 4;
- j |= (i & 0x0f);
- }
- return(j);
-}
-uschar *mime_decode_qp_char(uschar *qp_p,int *c) {
- uschar hex[] = {0,0,0};
- int nan = 0;
+uschar *mime_decode_qp_char(uschar *qp_p, int *c) {
uschar *initial_pos = qp_p;
/* advance one char */
qp_p++;
- REPEAT_FIRST:
- if ( (*qp_p == '\t') || (*qp_p == ' ') || (*qp_p == '\r') ) {
- /* tab or whitespace may follow
- just ignore it, but remember
- that this is not a valid hex
- encoding any more */
- nan = 1;
+ /* Check for two hex digits and decode them */
+ if (isxdigit(*qp_p) && isxdigit(qp_p[1])) {
+ /* Do hex conversion */
+ if (isdigit(*qp_p)) {*c = *qp_p - '0';}
+ else {*c = toupper(*qp_p) - 'A' + 10;};
+ *c <<= 4;
+ if (isdigit(qp_p[1])) {*c |= qp_p[1] - '0';}
+ else {*c |= toupper(qp_p[1]) - 'A' + 10;};
+ return qp_p + 2;
+ };
+
+ /* tab or whitespace may follow just ignore it */
+ while (*qp_p == '\t' || *qp_p == ' ' || *qp_p == '\r')
qp_p++;
- goto REPEAT_FIRST;
- }
- else if ( (('0' <= *qp_p) && (*qp_p <= '9')) || (('A' <= *qp_p) && (*qp_p <= 'F')) || (('a' <= *qp_p) && (*qp_p <= 'f')) ) {
- /* this is a valid hex char, if nan is unset */
- if (nan) {
- /* this is illegal */
- *c = -2;
- return initial_pos;
- }
- else {
- hex[0] = *qp_p;
- qp_p++;
- };
- }
- else if (*qp_p == '\n') {
+
+ if (*qp_p == '\n') {
/* hit soft line break already, continue */
*c = -1;
return qp_p;
- }
- else {
- /* illegal char here */
- *c = -2;
- return initial_pos;
};
- if ( (('0' <= *qp_p) && (*qp_p <= '9')) || (('A' <= *qp_p) && (*qp_p <= 'F')) || (('a' <= *qp_p) && (*qp_p <= 'f')) ) {
- if (hex[0] > 0) {
- hex[1] = *qp_p;
- /* do hex conversion */
- *c = mime_qp_hstr_i(hex);
- qp_p++;
- return qp_p;
- }
- else {
- /* huh ? */
- *c = -2;
- return initial_pos;
- };
- }
- else {
- /* illegal char */
- *c = -2;
- return initial_pos;
- };
+ /* illegal char here */
+ *c = -2;
+ return initial_pos;
}
+
uschar *mime_parse_line(uschar *buffer, uschar *data, uschar *encoding, int *num_decoded) {
if (encoding == NULL) {