/** * just prints the to headers, and cc headers if available **/ static void printToHeaders(dlist to, dlist cc, dstrbuf *msg) { struct addr *a = (struct addr *)dlGetNext(to); dsbPrintf(msg, "To: "); while (a) { dstrbuf *tmp = formatEmailAddr(a->name, a->email); dsbPrintf(msg, "%s", tmp->str); dsbDestroy(tmp); a = (struct addr *)dlGetNext(to); if (a != NULL) { dsbPrintf(msg, ", "); } else { dsbPrintf(msg, "\r\n"); } } if (cc != NULL) { dsbPrintf(msg, "Cc: "); a = (struct addr *)dlGetNext(cc); while (a) { dstrbuf *tmp = formatEmailAddr(a->name, a->email); dsbPrintf(msg, "%s", tmp->str); dsbDestroy(tmp); a = (struct addr *)dlGetNext(cc); if (a != NULL) { dsbPrintf(msg, ", "); } else { dsbPrintf(msg, "\r\n"); } } } }
static void printExtraHeaders(dlist headers, dstrbuf *msg) { char *hdr=NULL; while ((hdr = (char *)dlGetNext(headers)) != NULL) { dsbPrintf(msg, "%s\r\n", hdr); } }
/** * Transverse the list provided in search of the key. */ static dhashval * getValueFromList(dlist top, const char *key) { dhashval *keyval = NULL; while ((keyval = (dhashval *)dlGetNext(top))) { if (strcmp(keyval->key, key) == 0) { break; } } return keyval; }
/** * set up the appropriate MIME and Base64 headers for * the attachment of file specified in Mopts.attach **/ static int attachFiles(const char *boundary, dstrbuf *out) { dstrbuf *file_name = NULL; dstrbuf *file_type = NULL; char *next_file = NULL; /* * What we will do here is parse Mopts.attach for comma delimited file * names. If there was only one file specified with no comma, then strtok() * will just return that file and the next call to strtok() will be NULL * which will allow use to break out of our loop of attaching base64 stuff. */ while ((next_file = (char *)dlGetNext(Mopts.attach)) != NULL) { FILE *current = fopen(next_file, "r"); if (!current) { #if 1 //Ren: to skip nonexistent file fprintf(stderr, "email: skip %s\n", next_file); continue; #else fatal("Could not open attachment: %s", next_file); return (ERROR); #endif } /* If the user specified an absolute path, just get the file name */ file_type = mimeFiletype(next_file); file_name = mimeFilename(next_file); /* Set our MIME headers */ dsbPrintf(out, "\r\n--%s\r\n", boundary); dsbPrintf(out, "Content-Transfer-Encoding: base64\r\n"); dsbPrintf(out, "Content-Type: %s; name=\"%s\"\r\n", file_type->str, file_name->str); dsbPrintf(out, "Content-Disposition: attachment; filename=\"%s\"\r\n", file_name->str); dsbPrintf(out, "\r\n"); /* Encode to 'out' */ mimeB64EncodeFile(current, out); dsbDestroy(file_type); dsbDestroy(file_name); } return SUCCESS; }
/** * Free all allocated memory in the hashed array * * Params * table - The hash table to free */ void dhDestroy(dhash table) { uint i; dhashval *next; if (table) { for (i=0; i < table->tableSize; i++) { dlist this = table->hashed[i]; while ((next = (dhashval *)dlGetNext(this))) { xfree(next->key); if (table->destroy) { table->destroy(next->val); } xfree(next); } dlDestroy(this); } xfree(table->hashed); xfree(table); } }
/** * This function will take the FILE and process it via a * Remote SMTP server... **/ int processRemote(const char *smtp_serv, int smtp_port, dstrbuf *msg) { dsocket *sd; int retval=0, bytes; char *smtp_auth=NULL; char *email_addr=NULL; char *use_tls=NULL; char *user=NULL, *pass=NULL; struct prbar *bar=NULL; char nodename[MAXBUF] = { 0 }; char *ptr = msg->str; struct addr *next=NULL; email_addr = getConfValue("MY_EMAIL"); if (gethostname(nodename, sizeof(nodename) - 1) < 0) { snprintf(nodename, sizeof(nodename) - 1, "geek"); } /* Get other possible configuration values */ smtp_auth = getConfValue("SMTP_AUTH"); if (smtp_auth) { user = getConfValue("SMTP_AUTH_USER"); if (!user) { fatal("You must set SMTP_AUTH_USER in order to user SMTP_AUTH\n"); return ERROR; } pass = getSmtpPass(); if (!pass) { fatal("Failed to get SMTP Password.\n"); return ERROR; } } bar = prbarInit(msg->len); if (Mopts.verbose) { printf("Connecting to server %s on port %d\n", smtp_serv, smtp_port); } sd = dnetConnect(smtp_serv, smtp_port); if (sd == NULL) { fatal("Could not connect to server: %s on port: %d", smtp_serv, smtp_port); return ERROR; } /* Start SMTP Communications */ if (smtpInit(sd, nodename) == ERROR) { printSmtpError(); goto end; } /* Use TLS? */ use_tls = getConfValue("USE_TLS"); #ifndef HAVE_LIBSSL if (use_tls) { warning("No SSL support compiled in. Disabling TLS.\n"); use_tls = NULL; } #endif if (use_tls && strcasecmp(use_tls, "true") == 0) { if (smtpStartTls(sd) != ERROR) { dnetUseTls(sd); dnetVerifyCert(sd); if (smtpInitAfterTLS(sd, nodename) == ERROR) { printSmtpError(); goto end; } } else { printSmtpError(); goto end; } } /* See if we're using SMTP_AUTH. */ if (smtp_auth) { retval = smtpInitAuth(sd, smtp_auth, user, pass); if (retval == ERROR) { printSmtpError(); goto end; } } retval = smtpSetMailFrom(sd, email_addr); if (retval == ERROR) { printSmtpError(); goto end; } while ((next = (struct addr *)dlGetNext(Mopts.to)) != NULL) { retval = smtpSetRcpt(sd, next->email); if (retval == ERROR) { printSmtpError(); goto end; } } while ((next = (struct addr *)dlGetNext(Mopts.cc)) != NULL) { retval = smtpSetRcpt(sd, next->email); if (retval == ERROR) { printSmtpError(); goto end; } } while ((next = (struct addr *)dlGetNext(Mopts.bcc)) != NULL) { retval = smtpSetRcpt(sd, next->email); if (retval == ERROR) { printSmtpError(); goto end; } } retval = smtpStartData(sd); if (retval == ERROR) { printSmtpError(); goto end; } while (*ptr != '\0') { bytes = strlen(ptr); if (bytes > CHUNK_BYTES) { bytes = CHUNK_BYTES; } retval = smtpSendData(sd, ptr, bytes); if (retval == ERROR) { goto end; } if (Mopts.verbose && bar != NULL) { prbarPrint(bytes, bar); } ptr += bytes; } retval = smtpEndData(sd); if (retval != ERROR) { retval = smtpQuit(sd); } end: prbarDestroy(bar); dnetClose(sd); return retval; }