NeoMutt  2025-12-11-980-ge38c27
Teaching an old dog new tricks
DOXYGEN
Loading...
Searching...
No Matches
header.h File Reference

Convenience wrapper for the send headers. More...

#include <stdbool.h>
#include <stdio.h>
#include "email/lib.h"
+ Include dependency graph for header.h:
+ This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Enumerations

enum  MuttWriteHeaderMode {
  MUTT_WRITE_HEADER_NORMAL , MUTT_WRITE_HEADER_FCC , MUTT_WRITE_HEADER_POSTPONE , MUTT_WRITE_HEADER_EDITHDRS ,
  MUTT_WRITE_HEADER_MIME
}
 Modes for mutt_rfc822_write_header() More...
 

Functions

int mutt_rfc822_write_header (FILE *fp, struct Envelope *env, struct Body *b, enum MuttWriteHeaderMode mode, bool privacy, bool hide_protected_subject, struct ConfigSubset *sub)
 Write out one RFC822 header line.
 
int mutt_write_mime_header (struct Body *b, FILE *fp, struct ConfigSubset *sub)
 Create a MIME header.
 
int mutt_write_one_header (FILE *fp, const char *tag, const char *value, const char *pfx, int wraplen, CopyHeaderFlags chflags, struct ConfigSubset *sub)
 Write one header line to a file.
 
void mutt_write_references (const struct ListHead *r, FILE *fp, size_t trim)
 Add the message references to a list.
 

Detailed Description

Convenience wrapper for the send headers.

Authors
  • Richard Russon

This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

You should have received a copy of the GNU General Public License along with this program. If not, see http://www.gnu.org/licenses/.

Definition in file header.h.

Enumeration Type Documentation

◆ MuttWriteHeaderMode

Modes for mutt_rfc822_write_header()

Enumerator
MUTT_WRITE_HEADER_NORMAL 

A normal Email, write full header + MIME headers.

MUTT_WRITE_HEADER_FCC 

fcc mode, like normal mode but for Bcc header

MUTT_WRITE_HEADER_POSTPONE 

A postponed Email, just the envelope info.

MUTT_WRITE_HEADER_EDITHDRS 

"light" mode (used for edit_hdrs)

MUTT_WRITE_HEADER_MIME 

Write protected headers.

Definition at line 36 of file header.h.

37{
43};
@ MUTT_WRITE_HEADER_FCC
fcc mode, like normal mode but for Bcc header
Definition header.h:39
@ MUTT_WRITE_HEADER_MIME
Write protected headers.
Definition header.h:42
@ MUTT_WRITE_HEADER_NORMAL
A normal Email, write full header + MIME headers.
Definition header.h:38
@ MUTT_WRITE_HEADER_POSTPONE
A postponed Email, just the envelope info.
Definition header.h:40
@ MUTT_WRITE_HEADER_EDITHDRS
"light" mode (used for edit_hdrs)
Definition header.h:41

Function Documentation

◆ mutt_rfc822_write_header()

int mutt_rfc822_write_header ( FILE * fp,
struct Envelope * env,
struct Body * b,
enum MuttWriteHeaderMode mode,
bool privacy,
bool hide_protected_subject,
struct ConfigSubset * sub )

Write out one RFC822 header line.

Parameters
fpFile to write to
envEnvelope of email
bAttachment
modeMode, see MuttWriteHeaderMode
privacyIf true, remove headers that might identify the user
hide_protected_subjectIf true, replace subject header
subConfig Subset
Return values
0Success
-1Failure
Note
All RFC2047 encoding should be done outside of this routine, except for the "real name." This will allow this routine to be used more than once, if necessary.

Likewise, all IDN processing should happen outside of this routine.

privacy true => will omit any headers which may identify the user. Output generated is suitable for being sent through anonymous remailer chains.

hide_protected_subject: replaces the Subject header with $crypt_protected_headers_subject in NORMAL or POSTPONE mode.

Definition at line 584 of file header.c.

587{
588 if (((mode == MUTT_WRITE_HEADER_NORMAL) || (mode == MUTT_WRITE_HEADER_FCC) ||
589 (mode == MUTT_WRITE_HEADER_POSTPONE)) &&
590 !privacy)
591 {
592 struct Buffer *date = buf_pool_get();
593 mutt_date_make_date(date, cs_subset_bool(sub, "local_date_header"));
594 fprintf(fp, "Date: %s\n", buf_string(date));
595 buf_pool_release(&date);
596 }
597
598 /* UseFrom is not consulted here so that we can still write a From:
599 * field if the user sets it with the 'my-header' command */
600 if (!TAILQ_EMPTY(&env->from) && !privacy)
601 {
602 mutt_addrlist_write_file(&env->from, fp, "From");
603 }
604
605 if (!TAILQ_EMPTY(&env->sender) && !privacy)
606 {
607 mutt_addrlist_write_file(&env->sender, fp, "Sender");
608 }
609
610 if (!TAILQ_EMPTY(&env->to))
611 {
612 mutt_addrlist_write_file(&env->to, fp, "To");
613 }
614 else if (mode == MUTT_WRITE_HEADER_EDITHDRS)
615 {
616 if (!OptNewsSend)
617 fputs("To:\n", fp);
618 }
619
620 if (!TAILQ_EMPTY(&env->cc))
621 {
622 mutt_addrlist_write_file(&env->cc, fp, "Cc");
623 }
624 else if (mode == MUTT_WRITE_HEADER_EDITHDRS)
625 {
626 if (!OptNewsSend)
627 fputs("Cc:\n", fp);
628 }
629
630 if (!TAILQ_EMPTY(&env->bcc))
631 {
632 const bool c_write_bcc = cs_subset_bool(sub, "write_bcc");
633
634 if ((mode == MUTT_WRITE_HEADER_POSTPONE) ||
635 (mode == MUTT_WRITE_HEADER_EDITHDRS) || (mode == MUTT_WRITE_HEADER_FCC) ||
636 ((mode == MUTT_WRITE_HEADER_NORMAL) && c_write_bcc))
637 {
638 mutt_addrlist_write_file(&env->bcc, fp, "Bcc");
639 }
640 }
641 else if (mode == MUTT_WRITE_HEADER_EDITHDRS)
642 {
643 if (!OptNewsSend)
644 fputs("Bcc:\n", fp);
645 }
646
647 if (env->newsgroups)
648 fprintf(fp, "Newsgroups: %s\n", env->newsgroups);
649 else if ((mode == MUTT_WRITE_HEADER_EDITHDRS) && OptNewsSend)
650 fputs("Newsgroups:\n", fp);
651
652 if (env->followup_to)
653 fprintf(fp, "Followup-To: %s\n", env->followup_to);
654 else if ((mode == MUTT_WRITE_HEADER_EDITHDRS) && OptNewsSend)
655 fputs("Followup-To:\n", fp);
656
657 const bool c_x_comment_to = cs_subset_bool(sub, "x_comment_to");
658 if (env->x_comment_to)
659 fprintf(fp, "X-Comment-To: %s\n", env->x_comment_to);
660 else if ((mode == MUTT_WRITE_HEADER_EDITHDRS) && OptNewsSend && c_x_comment_to)
661 fputs("X-Comment-To:\n", fp);
662
663 if (env->subject)
664 {
665 if (hide_protected_subject &&
666 ((mode == MUTT_WRITE_HEADER_NORMAL) || (mode == MUTT_WRITE_HEADER_FCC) ||
668 {
669 const char *const c_crypt_protected_headers_subject = cs_subset_string(sub, "crypt_protected_headers_subject");
670 mutt_write_one_header(fp, "Subject", c_crypt_protected_headers_subject,
671 NULL, 0, CH_NONE, sub);
672 }
673 else
674 {
675 mutt_write_one_header(fp, "Subject", env->subject, NULL, 0, CH_NONE, sub);
676 }
677 }
678 else if (mode == MUTT_WRITE_HEADER_EDITHDRS)
679 {
680 fputs("Subject:\n", fp);
681 }
682
683 /* save message id if the user has set it */
684 if (env->message_id && !privacy)
685 fprintf(fp, "Message-ID: %s\n", env->message_id);
686
687 if (!TAILQ_EMPTY(&env->reply_to))
688 {
689 mutt_addrlist_write_file(&env->reply_to, fp, "Reply-To");
690 }
691 else if (mode == MUTT_WRITE_HEADER_EDITHDRS)
692 {
693 fputs("Reply-To:\n", fp);
694 }
695
696 if (!TAILQ_EMPTY(&env->mail_followup_to))
697 {
698 if (!OptNewsSend)
699 {
700 mutt_addrlist_write_file(&env->mail_followup_to, fp, "Mail-Followup-To");
701 }
702 }
703
704 /* Add any user defined headers */
705 struct UserHdrsOverride userhdrs_overrides = write_userhdrs(fp, &env->userhdrs,
706 privacy, sub);
707
708 if ((mode == MUTT_WRITE_HEADER_NORMAL) || (mode == MUTT_WRITE_HEADER_FCC) ||
710 {
711 if (!STAILQ_EMPTY(&env->references))
712 {
713 fputs("References:", fp);
714 mutt_write_references(&env->references, fp, 10);
715 fputc('\n', fp);
716 }
717
718 /* Add the MIME headers */
719 if (!userhdrs_overrides.is_overridden[USERHDRS_OVERRIDE_CONTENT_TYPE])
720 {
721 fputs("MIME-Version: 1.0\n", fp);
722 mutt_write_mime_header(b, fp, sub);
723 }
724 }
725
726 if (!STAILQ_EMPTY(&env->in_reply_to))
727 {
728 fputs("In-Reply-To:", fp);
730 fputc('\n', fp);
731 }
732
733#ifdef USE_AUTOCRYPT
734 const bool c_autocrypt = cs_subset_bool(sub, "autocrypt");
735 if (c_autocrypt)
736 {
737 if (mode == MUTT_WRITE_HEADER_NORMAL || mode == MUTT_WRITE_HEADER_FCC)
739 if (mode == MUTT_WRITE_HEADER_MIME)
741 }
742#endif
743
744 const bool c_user_agent = cs_subset_bool(sub, "user_agent");
745 if (((mode == MUTT_WRITE_HEADER_NORMAL) || (mode == MUTT_WRITE_HEADER_FCC)) && !privacy &&
746 c_user_agent && !userhdrs_overrides.is_overridden[USERHDRS_OVERRIDE_USER_AGENT])
747 {
748 /* Add a vanity header */
749 fprintf(fp, "User-Agent: NeoMutt/%s%s\n", PACKAGE_VERSION, GitVer);
750 }
751
752 return (ferror(fp) == 0) ? 0 : -1;
753}
void mutt_addrlist_write_file(const struct AddressList *al, FILE *fp, const char *header)
Wrapper for mutt_write_address()
Definition address.c:1261
int mutt_autocrypt_write_gossip_headers(struct Envelope *env, FILE *fp)
Write the Autocrypt gossip headers to a file.
Definition autocrypt.c:822
int mutt_autocrypt_write_autocrypt_header(struct Envelope *env, FILE *fp)
Write the Autocrypt header to a file.
Definition autocrypt.c:784
static const char * buf_string(const struct Buffer *buf)
Convert a buffer to a const char * "string".
Definition buffer.h:96
const char * cs_subset_string(const struct ConfigSubset *sub, const char *name)
Get a string config item by name.
Definition helpers.c:291
bool cs_subset_bool(const struct ConfigSubset *sub, const char *name)
Get a boolean config item by name.
Definition helpers.c:47
@ CH_NONE
No flags are set.
Definition copy_email.h:65
bool OptNewsSend
(pseudo) used to change behavior when posting
Definition globals.c:54
const char * GitVer
void mutt_date_make_date(struct Buffer *buf, bool local)
Write a date in RFC822 format to a buffer.
Definition date.c:400
struct Buffer * buf_pool_get(void)
Get a Buffer from the pool.
Definition pool.c:91
void buf_pool_release(struct Buffer **ptr)
Return a Buffer to the pool.
Definition pool.c:111
#define STAILQ_EMPTY(head)
Definition queue.h:382
#define TAILQ_EMPTY(head)
Definition queue.h:778
static struct UserHdrsOverride write_userhdrs(FILE *fp, const struct ListHead *userhdrs, bool privacy, struct ConfigSubset *sub)
Write user-defined headers and keep track of the interesting ones.
Definition header.c:368
@ USERHDRS_OVERRIDE_CONTENT_TYPE
Override the "Content-Type".
Definition header.c:62
@ USERHDRS_OVERRIDE_USER_AGENT
Override the "User-Agent".
Definition header.c:63
int mutt_write_mime_header(struct Body *b, FILE *fp, struct ConfigSubset *sub)
Create a MIME header.
Definition header.c:763
void mutt_write_references(const struct ListHead *r, FILE *fp, size_t trim)
Add the message references to a list.
Definition header.c:526
int mutt_write_one_header(FILE *fp, const char *tag, const char *value, const char *pfx, int wraplen, CopyHeaderFlags chflags, struct ConfigSubset *sub)
Write one header line to a file.
Definition header.c:427
String manipulation buffer.
Definition buffer.h:36
struct ListHead userhdrs
user defined headers
Definition envelope.h:85
char *const subject
Email's subject.
Definition envelope.h:70
struct AddressList to
Email's 'To' list.
Definition envelope.h:60
char * followup_to
List of 'followup-to' fields.
Definition envelope.h:80
struct AddressList reply_to
Email's 'reply-to'.
Definition envelope.h:64
char * message_id
Message ID.
Definition envelope.h:73
char * x_comment_to
List of 'X-comment-to' fields.
Definition envelope.h:81
char * newsgroups
List of newsgroups.
Definition envelope.h:78
struct AddressList mail_followup_to
Email's 'mail-followup-to'.
Definition envelope.h:65
struct AddressList cc
Email's 'Cc' list.
Definition envelope.h:61
struct AddressList sender
Email's sender.
Definition envelope.h:63
struct ListHead references
message references (in reverse order)
Definition envelope.h:83
struct ListHead in_reply_to
in-reply-to header content
Definition envelope.h:84
struct AddressList bcc
Email's 'Bcc' list.
Definition envelope.h:62
struct AddressList from
Email's 'From' list.
Definition envelope.h:59
Which headers have been overridden.
Definition header.c:70
bool is_overridden[countof(UserhdrsOverrideHeaders)]
Which email headers have been overridden.
Definition header.c:72
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_write_mime_header()

int mutt_write_mime_header ( struct Body * b,
FILE * fp,
struct ConfigSubset * sub )

Create a MIME header.

Parameters
bBody part
fpFile to write to
subConfig Subset
Return values
0Success
-1Failure

Definition at line 763 of file header.c.

764{
765 if (!b || !fp)
766 return -1;
767
768 int len;
769 int tmplen;
770 char buf[256] = { 0 };
771
772 fprintf(fp, "Content-Type: %s/%s", BODY_TYPE(b), b->subtype);
773
774 if (!TAILQ_EMPTY(&b->parameter))
775 {
776 len = 25 + mutt_str_len(b->subtype); /* approximate len. of content-type */
777
778 struct Parameter *np = NULL;
779 TAILQ_FOREACH(np, &b->parameter, entries)
780 {
781 if (!np->attribute || !np->value)
782 continue;
783
784 struct ParameterList pl_conts = TAILQ_HEAD_INITIALIZER(pl_conts);
785 rfc2231_encode_string(&pl_conts, np->attribute, np->value);
786 struct Parameter *cont = NULL;
787 TAILQ_FOREACH(cont, &pl_conts, entries)
788 {
789 fputc(';', fp);
790
791 buf[0] = 0;
792 mutt_addr_cat(buf, sizeof(buf), cont->value, MimeSpecials);
793
794 /* Dirty hack to make messages readable by Outlook Express
795 * for the Mac: force quotes around the boundary parameter
796 * even when they aren't needed. */
797 if (mutt_istr_equal(cont->attribute, "boundary") && mutt_str_equal(buf, cont->value))
798 snprintf(buf, sizeof(buf), "\"%s\"", cont->value);
799
800 tmplen = mutt_str_len(buf) + mutt_str_len(cont->attribute) + 1;
801 if ((len + tmplen + 2) > 76)
802 {
803 fputs("\n\t", fp);
804 len = tmplen + 1;
805 }
806 else
807 {
808 fputc(' ', fp);
809 len += tmplen + 1;
810 }
811
812 fprintf(fp, "%s=%s", cont->attribute, buf);
813 }
814
815 mutt_param_free(&pl_conts);
816 }
817 }
818
819 fputc('\n', fp);
820
821 if (b->content_id)
822 fprintf(fp, "Content-ID: <%s>\n", b->content_id);
823
824 if (b->language)
825 fprintf(fp, "Content-Language: %s\n", b->language);
826
827 if (b->description)
828 fprintf(fp, "Content-Description: %s\n", b->description);
829
830 if (b->disposition != DISP_NONE)
831 {
832 const char *dispstr[] = { "inline", "attachment", "form-data" };
833
834 if (b->disposition < sizeof(dispstr) / sizeof(char *))
835 {
836 fprintf(fp, "Content-Disposition: %s", dispstr[b->disposition]);
837 len = 21 + mutt_str_len(dispstr[b->disposition]);
838
839 if (b->use_disp && ((b->disposition != DISP_INLINE) || b->d_filename))
840 {
841 char *fn = b->d_filename;
842 if (!fn)
843 fn = b->filename;
844
845 if (fn)
846 {
847 /* Strip off the leading path... */
848 char *t = strrchr(fn, '/');
849 if (t)
850 t++;
851 else
852 t = fn;
853
854 struct ParameterList pl_conts = TAILQ_HEAD_INITIALIZER(pl_conts);
855 rfc2231_encode_string(&pl_conts, "filename", t);
856 struct Parameter *cont = NULL;
857 TAILQ_FOREACH(cont, &pl_conts, entries)
858 {
859 fputc(';', fp);
860 buf[0] = 0;
861 mutt_addr_cat(buf, sizeof(buf), cont->value, MimeSpecials);
862
863 tmplen = mutt_str_len(buf) + mutt_str_len(cont->attribute) + 1;
864 if ((len + tmplen + 2) > 76)
865 {
866 fputs("\n\t", fp);
867 len = tmplen + 1;
868 }
869 else
870 {
871 fputc(' ', fp);
872 len += tmplen + 1;
873 }
874
875 fprintf(fp, "%s=%s", cont->attribute, buf);
876 }
877
878 mutt_param_free(&pl_conts);
879 }
880 }
881
882 fputc('\n', fp);
883 }
884 else
885 {
886 mutt_debug(LL_DEBUG1, "ERROR: invalid content-disposition %d\n", b->disposition);
887 }
888 }
889
890 if (b->encoding != ENC_7BIT)
891 fprintf(fp, "Content-Transfer-Encoding: %s\n", ENCODING(b->encoding));
892
893 const bool c_crypt_protected_headers_write = cs_subset_bool(sub, "crypt_protected_headers_write");
894 bool c_autocrypt = false;
895#ifdef USE_AUTOCRYPT
896 c_autocrypt = cs_subset_bool(sub, "autocrypt");
897#endif
898
899 if ((c_crypt_protected_headers_write || c_autocrypt) && b->mime_headers)
900 {
902 false, false, sub);
903 }
904
905 /* Do NOT add the terminator here!!! */
906 return ferror(fp) ? -1 : 0;
907}
void mutt_addr_cat(char *buf, size_t buflen, const char *value, const char *specials)
Copy a string and wrap it in quotes if it contains special characters.
Definition address.c:715
#define mutt_debug(LEVEL,...)
Definition logging2.h:91
@ LL_DEBUG1
Log at debug level 1.
Definition logging2.h:45
const char MimeSpecials[]
Characters that need special treatment in MIME.
Definition mime.c:69
@ ENC_7BIT
7-bit text
Definition mime.h:49
#define BODY_TYPE(body)
Get the type name of a body part.
Definition mime.h:93
@ DISP_INLINE
Content is inline.
Definition mime.h:62
@ DISP_NONE
No preferred disposition.
Definition mime.h:65
#define ENCODING(x)
Get the encoding name for an encoding type.
Definition mime.h:97
bool mutt_istr_equal(const char *a, const char *b)
Compare two strings, ignoring case.
Definition string.c:678
bool mutt_str_equal(const char *a, const char *b)
Compare two strings.
Definition string.c:666
size_t mutt_str_len(const char *a)
Calculate the length of a string, safely.
Definition string.c:503
void mutt_param_free(struct ParameterList *pl)
Free a ParameterList.
Definition parameter.c:62
#define TAILQ_FOREACH(var, head, field)
Definition queue.h:782
#define TAILQ_HEAD_INITIALIZER(head)
Definition queue.h:694
size_t rfc2231_encode_string(struct ParameterList *head, const char *attribute, char *value)
Encode a string to be suitable for an RFC2231 header.
Definition rfc2231.c:357
int mutt_rfc822_write_header(FILE *fp, struct Envelope *env, struct Body *b, enum MuttWriteHeaderMode mode, bool privacy, bool hide_protected_subject, struct ConfigSubset *sub)
Write out one RFC822 header line.
Definition header.c:584
char * language
content-language (RFC8255)
Definition body.h:78
char * content_id
Content-Id (RFC2392)
Definition body.h:58
char * d_filename
filename to be used for the content-disposition header If NULL, filename is used instead.
Definition body.h:56
struct Envelope * mime_headers
Memory hole protected headers.
Definition body.h:76
struct ParameterList parameter
Parameters of the content-type.
Definition body.h:63
bool use_disp
Content-Disposition uses filename= ?
Definition body.h:47
char * description
content-description
Definition body.h:55
unsigned int disposition
content-disposition, ContentDisposition
Definition body.h:42
char * subtype
content-type subtype
Definition body.h:61
unsigned int encoding
content-transfer-encoding, ContentEncoding
Definition body.h:41
char * filename
When sending a message, this is the file to which this structure refers.
Definition body.h:59
Attribute associated with a MIME part.
Definition parameter.h:33
char * attribute
Parameter name.
Definition parameter.h:34
char * value
Parameter value.
Definition parameter.h:35
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_write_one_header()

int mutt_write_one_header ( FILE * fp,
const char * tag,
const char * value,
const char * pfx,
int wraplen,
CopyHeaderFlags chflags,
struct ConfigSubset * sub )

Write one header line to a file.

Parameters
fpFile to write to
tagHeader key, e.g. "From"
valueHeader value
pfxPrefix for header
wraplenColumn to wrap at
chflagsFlags, see CopyHeaderFlags
subConfig Subset
Return values
0Success
-1Failure

split several headers into individual ones and call write_one_header for each one

Definition at line 427 of file header.c.

430{
431 char *last = NULL;
432 char *line = NULL;
433 int max = 0;
434 int w;
435 int rc = -1;
436 int pfxw = mutt_strwidth(pfx);
437 char *v = mutt_str_dup(value);
438 bool display = (chflags & CH_DISPLAY);
439
440 const bool c_weed = cs_subset_bool(sub, "weed");
441 if (!display || c_weed)
442 v = unfold_header(v);
443
444 /* when not displaying, use sane wrap value */
445 if (!display)
446 {
447 const short c_wrap_headers = cs_subset_number(sub, "wrap_headers");
448 if ((c_wrap_headers < 78) || (c_wrap_headers > 998))
449 wraplen = 78;
450 else
451 wraplen = c_wrap_headers;
452 }
453 else if (wraplen <= 0)
454 {
455 wraplen = 78;
456 }
457
458 const size_t vlen = mutt_str_len(v);
459 if (tag)
460 {
461 /* if header is short enough, simply print it */
462 if (!display && (mutt_strwidth(tag) + 2 + pfxw + mutt_strnwidth(v, vlen) <= wraplen))
463 {
464 mutt_debug(LL_DEBUG5, "buf[%s%s: %s] is short enough\n", NONULL(pfx), tag, v);
465 if (fprintf(fp, "%s%s: %s\n", NONULL(pfx), tag, v) <= 0)
466 goto out;
467 rc = 0;
468 goto out;
469 }
470 else
471 {
472 rc = fold_one_header(fp, tag, v, vlen, pfx, wraplen, chflags);
473 goto out;
474 }
475 }
476
477 char *p = v;
478 last = v;
479 line = v;
480 while (p && *p)
481 {
482 p = strchr(p, '\n');
483
484 /* find maximum line width in current header */
485 if (p)
486 *p = '\0';
487 w = mutt_mb_width(line, 0, display);
488 if (w > max)
489 max = w;
490 if (p)
491 *p = '\n';
492
493 if (!p)
494 break;
495
496 line = ++p;
497 if ((*p != ' ') && (*p != '\t'))
498 {
499 if (write_one_header(fp, pfxw, max, wraplen, pfx, last, p, chflags) < 0)
500 goto out;
501 last = p;
502 max = 0;
503 }
504 }
505
506 if (last && *last)
507 if (write_one_header(fp, pfxw, max, wraplen, pfx, last, p, chflags) < 0)
508 goto out;
509
510 rc = 0;
511
512out:
513 FREE(&v);
514 return rc;
515}
short cs_subset_number(const struct ConfigSubset *sub, const char *name)
Get a number config item by name.
Definition helpers.c:143
@ CH_DISPLAY
Display result to user.
Definition copy_email.h:84
size_t mutt_strnwidth(const char *s, size_t n)
Measure a string's width in screen cells.
Definition curs_lib.c:462
size_t mutt_strwidth(const char *s)
Measure a string's width in screen cells.
Definition curs_lib.c:449
@ LL_DEBUG5
Log at debug level 5.
Definition logging2.h:49
int mutt_mb_width(const char *str, int col, bool indent)
Measure a string's display width (in screen columns)
Definition mbyte.c:138
#define FREE(x)
Free memory and set the pointer to NULL.
Definition memory.h:68
char * mutt_str_dup(const char *str)
Copy a string, safely.
Definition string.c:257
static int fold_one_header(FILE *fp, const char *tag, const char *value, size_t vlen, const char *pfx, int wraplen, CopyHeaderFlags chflags)
Fold one header line.
Definition header.c:132
static int write_one_header(FILE *fp, int pfxw, int max, int wraplen, const char *pfx, const char *start, const char *end, CopyHeaderFlags chflags)
Write out one header line.
Definition header.c:298
static char * unfold_header(char *s)
Unfold a wrapped email header.
Definition header.c:241
#define NONULL(x)
Definition string2.h:44
+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ mutt_write_references()

void mutt_write_references ( const struct ListHead * r,
FILE * fp,
size_t trim )

Add the message references to a list.

Parameters
rString List of references
fpFile to write to
trimTrim the list to at most this many items

Write the list in reverse because they are stored in reverse order when parsed to speed up threading.

Definition at line 526 of file header.c.

527{
528 struct ListNode *np = NULL;
529 size_t length = 0;
530
531 STAILQ_FOREACH(np, r, entries)
532 {
533 if (++length == trim)
534 break;
535 }
536
537 struct ListNode **ref = MUTT_MEM_CALLOC(length, struct ListNode *);
538
539 // store in reverse order
540 size_t tmp = length;
541 STAILQ_FOREACH(np, r, entries)
542 {
543 ref[--tmp] = np;
544 if (tmp == 0)
545 break;
546 }
547
548 for (size_t i = 0; i < length; i++)
549 {
550 fputc(' ', fp);
551 fputs(ref[i]->data, fp);
552 if (i != length - 1)
553 fputc('\n', fp);
554 }
555
556 FREE(&ref);
557}
#define MUTT_MEM_CALLOC(n, type)
Definition memory.h:52
#define STAILQ_FOREACH(var, head, field)
Definition queue.h:390
A List node for strings.
Definition list.h:37
char * data
String.
Definition list.h:38
+ Here is the caller graph for this function: