Diffstat (limited to 'kmicromail/libetpan/tests/readmsg-common.c') (more/less context) (ignore whitespace changes)
-rw-r--r-- | kmicromail/libetpan/tests/readmsg-common.c | 720 |
1 files changed, 720 insertions, 0 deletions
diff --git a/kmicromail/libetpan/tests/readmsg-common.c b/kmicromail/libetpan/tests/readmsg-common.c new file mode 100644 index 0000000..060497d --- a/dev/null +++ b/kmicromail/libetpan/tests/readmsg-common.c @@ -0,0 +1,720 @@ +#include "readmsg-common.h" + +#include <sys/stat.h> +#include <sys/mman.h> +#include <fcntl.h> +#include <unistd.h> +#include <string.h> +#include <stdlib.h> + +/* returns TRUE is given MIME part is a text part */ + +int etpan_mime_is_text(struct mailmime * build_info) +{ + if (build_info->mm_type == MAILMIME_SINGLE) { + if (build_info->mm_content_type != NULL) { + if (build_info->mm_content_type->ct_type->tp_type == + MAILMIME_TYPE_DISCRETE_TYPE) { + if (build_info->mm_content_type->ct_type->tp_data.tp_discrete_type->dt_type == + MAILMIME_DISCRETE_TYPE_TEXT) + return 1; + } + } + else + return 1; + } + + return 0; +} + + +/* display content type */ + +int show_part_info(FILE * f, + struct mailmime_single_fields * mime_fields, + struct mailmime_content * content) +{ + char * description; + char * filename; + int col; + int r; + + description = mime_fields->fld_description; + filename = mime_fields->fld_disposition_filename; + + col = 0; + + r = fprintf(f, " [ Part "); + if (r < 0) + goto err; + + if (content != NULL) { + r = mailmime_content_type_write(f, &col, content); + if (r != MAILIMF_NO_ERROR) + goto err; + } + + if (filename != NULL) { + r = fprintf(f, " (%s)", filename); + if (r < 0) + goto err; + } + + if (description != NULL) { + r = fprintf(f, " : %s", description); + if (r < 0) + goto err; + } + + r = fprintf(f, " ]\n\n"); + if (r < 0) + goto err; + + return NO_ERROR; + + err: + return ERROR_FILE; +} + +/* + fetch the data of the mailmime_data structure whether it is a file + or a string. + + data must be freed with mmap_string_unref() +*/ + +#if 0 +static int fetch_data(struct mailmime_data * data, + char ** result, size_t * result_len) +{ + int fd; + int r; + char * text; + struct stat buf; + int res; + MMAPString * mmapstr; + + switch (data->dt_type) { + case MAILMIME_DATA_TEXT: + mmapstr = mmap_string_new_len(data->dt_data.dt_text.dt_data, + data->dt_data.dt_text.dt_length); + if (mmapstr == NULL) { + res = ERROR_MEMORY; + goto err; + } + + * result = mmapstr->str; + * result_len = mmapstr->len; + + return NO_ERROR; + + case MAILMIME_DATA_FILE: + fd = open(data->dt_data.dt_filename, O_RDONLY); + if (fd < 0) { + res = ERROR_FILE; + goto err; + } + + r = fstat(fd, &buf); + if (r < 0) { + res = ERROR_FILE; + goto close; + } + + if (buf.st_size != 0) { + text = mmap(NULL, buf.st_size, PROT_READ, MAP_SHARED, fd, 0); + if (text == MAP_FAILED) { + res = ERROR_FILE; + goto close; + } + + mmapstr = mmap_string_new_len(text, buf.st_size); + if (mmapstr == NULL) { + res = r; + goto unmap; + } + + munmap(text, buf.st_size); + } + else { + mmapstr = mmap_string_new(""); + if (mmapstr == NULL) { + res = r; + goto close; + } + } + + close(fd); + + * result = mmapstr->str; + * result_len = mmapstr->len; + + return NO_ERROR; + + default: + return ERROR_INVAL; + } + + unmap: + munmap(text, buf.st_size); + close: + close(fd); + err: + return res; +} +#endif + +/* fetch message and decode if it is base64 or quoted-printable */ + +int etpan_fetch_message(mailmessage * msg_info, + struct mailmime * mime_part, + struct mailmime_single_fields * fields, + char ** result, size_t * result_len) +{ + char * data; + size_t len; + int r; + int encoding; + char * decoded; + size_t decoded_len; + size_t cur_token; + int res; + int encoded; + + encoded = 0; + + r = mailmessage_fetch_section(msg_info, + mime_part, &data, &len); + if (r != MAIL_NO_ERROR) { + res = ERROR_FETCH; + goto err; + } + + encoded = 1; + + /* decode message */ + + if (encoded) { + if (fields->fld_encoding != NULL) + encoding = fields->fld_encoding->enc_type; + else + encoding = MAILMIME_MECHANISM_8BIT; + } + else { + encoding = MAILMIME_MECHANISM_8BIT; + } + + cur_token = 0; + r = mailmime_part_parse(data, len, &cur_token, + encoding, &decoded, &decoded_len); + if (r != MAILIMF_NO_ERROR) { + res = ERROR_FETCH; + goto free; + } + + mailmessage_fetch_result_free(msg_info, data); + + * result = decoded; + * result_len = decoded_len; + + return NO_ERROR; + + free: + mailmessage_fetch_result_free(msg_info, data); + err: + return res; +} + + +/* fetch fields */ + +struct mailimf_fields * fetch_fields(mailmessage * msg_info, + struct mailmime * mime) +{ + char * data; + size_t len; + int r; + size_t cur_token; + struct mailimf_fields * fields; + + r = mailmessage_fetch_section_header(msg_info, mime, &data, &len); + if (r != MAIL_NO_ERROR) + return NULL; + + cur_token = 0; + r = mailimf_fields_parse(data, len, &cur_token, &fields); + if (r != MAILIMF_NO_ERROR) { + mailmessage_fetch_result_free(msg_info, data); + return NULL; + } + + mailmessage_fetch_result_free(msg_info, data); + + return fields; +} + + + +#define MAX_MAIL_COL 72 + +/* write decoded mailbox */ + +static int +etpan_mailbox_write(FILE * f, int * col, + struct mailimf_mailbox * mb) +{ + int r; + + if (* col > 1) { + + if (* col + strlen(mb->mb_addr_spec) >= MAX_MAIL_COL) { + r = mailimf_string_write(f, col, "\r\n ", 3); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + * col = 1; + } + } + + if (mb->mb_display_name) { + char * decoded_from; + size_t cur_token; + + cur_token = 0; + r = mailmime_encoded_phrase_parse(DEST_CHARSET, + mb->mb_display_name, strlen(mb->mb_display_name), + &cur_token, DEST_CHARSET, + &decoded_from); + if (r != MAILIMF_NO_ERROR) { + decoded_from = strdup(mb->mb_display_name); + if (decoded_from == NULL) + return ERROR_MEMORY; + } + + r = mailimf_quoted_string_write(f, col, decoded_from, + strlen(decoded_from)); + if (r != MAILIMF_NO_ERROR) { + free(decoded_from); + return ERROR_FILE; + } + + if (* col > 1) { + + if (* col + strlen(decoded_from) + 3 >= MAX_MAIL_COL) { + r = mailimf_string_write(f, col, "\r\n ", 3); + if (r != MAILIMF_NO_ERROR) { + free(decoded_from); + return r; + } + * col = 1; + } + } + + free(decoded_from); + + r = mailimf_string_write(f, col, " <", 2); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + + r = mailimf_string_write(f, col, + mb->mb_addr_spec, strlen(mb->mb_addr_spec)); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + + r = mailimf_string_write(f, col, ">", 1); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + } + else { + r = mailimf_string_write(f, col, + mb->mb_addr_spec, strlen(mb->mb_addr_spec)); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + } + + + return NO_ERROR; + +} + +/* write decoded mailbox list */ + +int +etpan_mailbox_list_write(FILE * f, int * col, + struct mailimf_mailbox_list * mb_list) +{ + clistiter * cur; + int r; + int first; + + first = 1; + + for(cur = clist_begin(mb_list->mb_list) ; cur != NULL ; + cur = clist_next(cur)) { + struct mailimf_mailbox * mb; + + mb = cur->data; + + if (!first) { + r = mailimf_string_write(f, col, ", ", 2); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + } + else { + first = 0; + } + + r = etpan_mailbox_write(f, col, mb); + if (r != NO_ERROR) + return r; + } + + return NO_ERROR; +} + +/* write decoded group */ + +static int +etpan_group_write(FILE * f, int * col, + struct mailimf_group * group) +{ + int r; + + r = mailimf_string_write(f, col, group->grp_display_name, + strlen(group->grp_display_name)); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + + r = mailimf_string_write(f, col, ": ", 2); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + + if (group->grp_mb_list != NULL) { + r = etpan_mailbox_list_write(f, col, group->grp_mb_list); + if (r != NO_ERROR) + return r; + } + + r = mailimf_string_write(f, col, ";", 1); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + + return NO_ERROR; +} + +/* write decoded address */ + +int +etpan_address_write(FILE * f, int * col, + struct mailimf_address * addr) +{ + int r; + + switch(addr->ad_type) { + case MAILIMF_ADDRESS_MAILBOX: + r = etpan_mailbox_write(f, col, addr->ad_data.ad_mailbox); + if (r != NO_ERROR) + return r; + + break; + + case MAILIMF_ADDRESS_GROUP: + r = etpan_group_write(f, col, addr->ad_data.ad_group); + if (r != NO_ERROR) + return r; + + break; + } + + return MAILIMF_NO_ERROR; +} + +/* write decoded address list */ + +int +etpan_address_list_write(FILE * f, int * col, + struct mailimf_address_list * addr_list) +{ + clistiter * cur; + int r; + int first; + + first = 1; + + for(cur = clist_begin(addr_list->ad_list) ; cur != NULL ; + cur = clist_next(cur)) { + struct mailimf_address * addr; + + addr = clist_content(cur); + + if (!first) { + r = mailimf_string_write(f, col, ", ", 2); + if (r != MAILIMF_NO_ERROR) + return ERROR_FILE; + } + else { + first = 0; + } + + r = etpan_address_write(f, col, addr); + if (r != NO_ERROR) + return r; + } + + return NO_ERROR; +} + +/* write decoded subject */ + +static int etpan_subject_write(FILE * f, int * col, + char * subject) +{ + int r; + char * decoded_subject; + size_t cur_token; + + r = mailimf_string_write(f, col, "Subject: ", 9); + if (r != MAILIMF_NO_ERROR) { + return ERROR_FILE; + } + + cur_token = 0; + r = mailmime_encoded_phrase_parse(DEST_CHARSET, + subject, strlen(subject), + &cur_token, DEST_CHARSET, + &decoded_subject); + if (r != MAILIMF_NO_ERROR) { + decoded_subject = strdup(subject); + if (decoded_subject == NULL) + return ERROR_MEMORY; + } + + r = mailimf_string_write(f, col, decoded_subject, strlen(decoded_subject)); + if (r != MAILIMF_NO_ERROR) { + free(decoded_subject); + return ERROR_FILE; + } + + free(decoded_subject); + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) { + return ERROR_FILE; + } + * col = 0; + + return NO_ERROR; +} + +/* write decoded fields */ + +int fields_write(FILE * f, int * col, + struct mailimf_fields * fields) +{ + clistiter * cur; + int r; + + for(cur = clist_begin(fields->fld_list) ; cur != NULL ; + cur = clist_next(cur)) { + struct mailimf_field * field; + + field = clist_content(cur); + + switch (field->fld_type) { + case MAILIMF_FIELD_FROM: + r = mailimf_string_write(f, col, "From: ", 6); + if (r != MAILIMF_NO_ERROR) + goto err; + + r = etpan_mailbox_list_write(f, col, + field->fld_data.fld_from->frm_mb_list); + if (r != NO_ERROR) + goto err; + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) + goto err; + * col = 0; + + break; + + case MAILIMF_FIELD_REPLY_TO: + r = mailimf_string_write(f, col, "Reply-To: ", 10); + if (r != MAILIMF_NO_ERROR) + goto err; + + r = etpan_address_list_write(f, col, + field->fld_data.fld_reply_to->rt_addr_list); + if (r != NO_ERROR) + goto err; + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) + goto err; + * col = 0; + + break; + + case MAILIMF_FIELD_TO: + r = mailimf_string_write(f, col, "To: ", 4); + if (r != MAILIMF_NO_ERROR) + goto err; + + r = etpan_address_list_write(f, col, + field->fld_data.fld_to->to_addr_list); + if (r != NO_ERROR) + goto err; + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) + goto err; + * col = 0; + + break; + + case MAILIMF_FIELD_CC: + r = mailimf_string_write(f, col, "Cc: ", 4); + if (r != MAILIMF_NO_ERROR) + goto err; + + r = etpan_address_list_write(f, col, + field->fld_data.fld_cc->cc_addr_list); + if (r != NO_ERROR) + goto err; + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) + goto err; + * col = 0; + + break; + + case MAILIMF_FIELD_BCC: + r = mailimf_string_write(f, col, "Bcc: ", 10); + if (r != MAILIMF_NO_ERROR) + goto err; + + if (field->fld_data.fld_bcc->bcc_addr_list != NULL) { + r = etpan_address_list_write(f, col, + field->fld_data.fld_bcc->bcc_addr_list); + if (r != NO_ERROR) + goto err; + } + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) + goto err; + * col = 0; + + break; + + case MAILIMF_FIELD_SUBJECT: + r = etpan_subject_write(f, col, field->fld_data.fld_subject->sbj_value); + if (r != MAILIMF_NO_ERROR) + goto err; + break; + + case MAILIMF_FIELD_RESENT_FROM: + r = mailimf_string_write(f, col, "Resent-From: ", 13); + if (r != MAILIMF_NO_ERROR) + goto err; + + r = etpan_mailbox_list_write(f, col, + field->fld_data.fld_resent_from->frm_mb_list); + if (r != NO_ERROR) + goto err; + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) + goto err; + * col = 0; + break; + + case MAILIMF_FIELD_RESENT_TO: + r = mailimf_string_write(f, col, "Resent-To: ", 11); + if (r != MAILIMF_NO_ERROR) + goto err; + + r = etpan_address_list_write(f, col, + field->fld_data.fld_resent_to->to_addr_list); + if (r != NO_ERROR) + goto err; + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) + goto err; + * col = 0; + + break; + case MAILIMF_FIELD_RESENT_CC: + r = mailimf_string_write(f, col, "Resent-Cc: ", 11); + if (r != MAILIMF_NO_ERROR) + goto err; + + r = etpan_address_list_write(f, col, + field->fld_data.fld_resent_cc->cc_addr_list); + if (r != NO_ERROR) + goto err; + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) + goto err; + * col = 0; + + break; + case MAILIMF_FIELD_RESENT_BCC: + r = mailimf_string_write(f, col, "Resent-Bcc: ", 12); + if (r != MAILIMF_NO_ERROR) + goto err; + + if (field->fld_data.fld_resent_bcc->bcc_addr_list != NULL) { + r = etpan_address_list_write(f, col, + field->fld_data.fld_resent_bcc->bcc_addr_list); + if (r != NO_ERROR) + goto err; + } + + r = mailimf_string_write(f, col, "\r\n", 2); + if (r != MAILIMF_NO_ERROR) + goto err; + * col = 0; + + break; + + case MAILIMF_FIELD_ORIG_DATE: + case MAILIMF_FIELD_RESENT_DATE: + r = mailimf_field_write(f, col, field); + if (r != MAILIMF_NO_ERROR) + goto err; + break; + + case MAILIMF_FIELD_OPTIONAL_FIELD: + if ((strcasecmp(field->fld_data.fld_optional_field->fld_name, + "X-Mailer") == 0) + || (strncasecmp(field->fld_data.fld_optional_field->fld_name, + "Resent-", 7) == 0) + || (strcasecmp(field->fld_data.fld_optional_field->fld_name, + "Newsgroups") == 0) + || (strcasecmp(field->fld_data.fld_optional_field->fld_name, + "Followup-To") == 0) + || (strcasecmp(field->fld_data.fld_optional_field->fld_name, + "User-Agent") == 0)) { + r = mailimf_field_write(f, col, field); + if (r != MAILIMF_NO_ERROR) + goto err; + } + break; + + case MAILIMF_FIELD_MESSAGE_ID: + case MAILIMF_FIELD_SENDER: + case MAILIMF_FIELD_IN_REPLY_TO: + case MAILIMF_FIELD_REFERENCES: + default: + break; + } + } + + return NO_ERROR; + + err: + return ERROR_FILE; +} |