x400_msrcv_msg_tok_sign.c
1/* Copyright (c) 2009-2025, Isode Limited, London, England.
2 * All rights reserved.
3 *
4 * Acquisition and use of this software and related materials for any
5 * purpose requires a written licence agreement from Isode Limited,
6 * or a written licence from an organisation licenced by Isode Limited
7 * to grant such a licence.
8 *
9 */
10
11/*
12 *
13 * @VERSION@
14 *
15 * Simple example program for receiving a message from a store.
16 * The security environment is set up so that signed messages
17 * will have per message MOAC signatures and recipient Message Token
18 * signatures verified.
19 *
20 * Note that a valid Digital Identity is no longer required in order to
21 * perform verification. Instead the name of a directory containing trusted,
22 * self signed certificates in DER form can be passed in.
23 */
24
25#include "example.h"
26#include "ms_example.h"
27
28#include <isode/base/compat.h>
29
30#include <seclabel_api.h> /* For security labels */
31#include <stdio.h>
32#include <stdlib.h>
33#include <x400_msapi.h>
34
35#define XML_BUFSIZE 1024
36
37int num_unsigned_rcvd;
38int num_unverified_rcvd;
39int num_verified_rcvd;
40int num_messages_rcvd;
41int num_reports_rcvd;
42int num_ipns_rcvd;
43
44static char *optstr = "u37m:d:p:w:M:D:P:W:e:b:x:EY:U:I";
45
46static void usage(void);
47
48static int get_msg(struct X400msSession *sp);
49
50static void setup_default_new_sec_env(struct X400msSession *sp, char *sec_trusted_cert_dir);
51
52static void setup_default_old_sec_env(struct X400msSession *sp, char *id, char *dn, char *pw /* passphrase for private key in pkcs12 file */
53);
54
55static void report_msg_token_info(struct X400Recipient *rp);
56
57static int get_sec_label(struct X400msMessage *mp);
58
59static void print_sec_label(unsigned char slab_buffer[], unsigned int length);
60
61static int get_cic(struct X400Recipient *rp);
62
63static int get_4406_info(struct X400msMessage *mp);
64
65static void show_recip_certificate(struct X400Recipient *rp, int certtype, const char *tag);
66
67static void show_message_certificate(struct X400msMessage *mp, const char *tag);
68
69static void show_certificate(struct X400Certificate *cert, const char *tag);
70
71static int handle_ipn(struct X400msMessage *mp);
72
73static int handle_msg(struct X400msSession *sp, struct X400msMessage *mp);
74
75static int send_ipn(struct X400msSession *sp, struct X400msMessage *mp, struct X400msMessage **ipn);
76
77static int do_report(struct X400msSession *sp, struct X400msMessage *mp);
78
82int main(int argc, char **argv) {
83 char buffer[BUFSIZ];
84 char pa[BUFSIZ];
85 char orn[BUFSIZ];
86 int status;
87 int nummsg;
88 struct X400msSession *sp;
89 int contype;
90 char *def_oraddr;
91 char *def_dn;
92 char *def_pa;
93
94 if (get_args(argc, argv, optstr)) {
95 usage();
96 exit(-1);
97 }
98
99 printf("Connection type (0 = P7, 1 = P3 submit only, 2 = P3 both directions) [%d]: ", x400_contype);
100 contype = ic_fgetc(x400_contype, stdin);
101 if (contype != 10) {
102 ic_fgetc(x400_contype, stdin);
103 }
104
105 if (contype < '0' || '2' < contype) {
106 contype = x400_contype;
107 }
108 else {
109 contype -= '0';
110 }
111
112 if (contype == 0) {
113 def_oraddr = x400_ms_user_addr;
114 def_dn = x400_ms_user_dn;
115 def_pa = x400_ms_presentation_address;
116 }
117 else {
118 def_oraddr = x400_mta_user_addr;
119 def_dn = x400_mta_user_dn;
120 def_pa = x400_mta_presentation_address;
121 }
122
123 printf("Your ORAddress [%s] > ", def_oraddr);
124 ic_fgets(orn, sizeof orn, stdin);
125
126 if (orn[strlen(orn) - 1] == '\n') {
127 orn[strlen(orn) - 1] = '\0';
128 }
129
130 if (orn[0] == '\0') {
131 strcpy(orn, def_oraddr);
132 }
133
134 /* Prompt for password; note: reflected. */
135 printf("Password [%s]: ", contype == 0 ? x400_p7_password : x400_p3_password);
136 if (ic_fgets(buffer, sizeof buffer, stdin) == NULL) {
137 exit(1);
138 }
139
140 if (buffer[strlen(buffer) - 1] == '\n') {
141 buffer[strlen(buffer) - 1] = '\0';
142 }
143 if (buffer[0] == '\0') {
144 strcpy(buffer, contype == 0 ? x400_p7_password : x400_p3_password);
145 }
146
147 printf("Presentation Address [%s] > ", def_pa);
148 ic_fgets(pa, sizeof pa, stdin);
149
150 if (pa[strlen(pa) - 1] == '\n') {
151 pa[strlen(pa) - 1] = '\0';
152 }
153
154 if (pa[0] == '\0') {
155 strcpy(pa, def_pa);
156 }
157
158 status = X400msOpen(contype, orn, def_dn, buffer, pa, &nummsg, &sp);
159 if (status != X400_E_NOERROR) {
160 fprintf(stderr, "Error in Open: %s\n", X400msError(status));
161 exit(status);
162 }
163
164 /* setup logging from $(ETCDIR)x400api.xml or $(SHAREDIR)x400api.xml */
166
167 if (nummsg == 0) {
168 printf("no messages - waiting for a message to be delivered.....\n");
169 }
170 else {
171 printf("%d messages waiting\n", nummsg);
172 }
173
174 status = get_msg(sp);
175 if (status != X400_E_NOERROR) {
176 fprintf(stderr, "Error in getting msg: %s\n", X400msError(status));
177 exit(status);
178 }
179 fprintf(stderr, "got first\n");
180
181 do {
182 fprintf(stderr, "================================================\n");
183 status = get_msg(sp);
184 if (status != X400_E_NOERROR) {
185 fprintf(stderr, "Error in getting msg: %s\n", X400msError(status));
186 exit(status);
187 }
188 } while (until_no_more_msgs);
189
190 status = X400msClose(sp);
191 printf("%d num_messages_rcvd\n", num_messages_rcvd);
192 printf("%d num_reports_rcvd\n", num_reports_rcvd);
193 printf("%d num_unsigned_rcvd\n", num_unsigned_rcvd);
194 printf("%d num_unverified_rcvd\n", num_unverified_rcvd);
195 printf("%d num_verified_rcvd\n", num_verified_rcvd);
196 printf("%d num_ipns_rcvd\n", num_ipns_rcvd);
197 return (status);
198}
199
200static int get_msg(struct X400msSession *sp) {
201 int status;
202 int nummsg;
203 int type;
204 int seqn;
205 struct X400msMessage *mp;
206 int intparam;
207
208 printf("Waiting for new messages for 10 seconds\n");
209 status = X400msWait(sp, 10, &nummsg);
210 if (status != X400_E_NOERROR) {
211 fprintf(stderr, "Error from Wait: %s\n", X400msError(status));
212 // Tidily close the session.
213 status = X400msClose(sp);
214 printf("%d num_messagese_rcvd\n", num_messages_rcvd);
215 printf("%d num_reports_rcvd\n", num_reports_rcvd);
216 printf("%d num_unsigned_rcvd\n", num_unsigned_rcvd);
217 printf("%d num_unverified_rcvd\n", num_unverified_rcvd);
218 printf("%d num_verified_rcvd\n", num_verified_rcvd);
219 exit(status);
220 }
221
222 /* Set up the security environment.
223 *
224 * In R15.0 this need only be the name of a trusted certificate directory.
225 *
226 * Prior to R15.0, the ID is specified as a pathname, in which the
227 * subdirectory "x509" is expected to contain one or more PKCS12
228 * files. The appropriate Digital Identity is determined from the
229 * DN of the subject, and the passphrase is used to decrypt the
230 * private key. NB even though we're not going to use our cert,
231 * (as we're going to use the cert in the message to check the MOAC
232 * we need to do this due to a limitation in the underlying X.509
233 * layer.
234 */
235 if (use_new_sec_env) {
236 setup_default_new_sec_env(sp, trusted_ca_certs_dir);
237 }
238 else {
239 setup_default_old_sec_env(sp, security_id, identity_dn, passphrase);
240 }
241
242 /* Turn off legacy bahaviour in which MOAC verification failure
243 * returns X400_E_NOERROR.
244 * We will now get X400_E_X509_VERIFY_FAILURE from MsgGet
245 * if/when the verification fails
246 */
248
249 printf("Getting message\n");
250
251 status = X400msMsgGet(sp, 0, &mp, &type, &seqn);
252 switch (status) {
253 case X400_E_NOERROR:
254 fprintf(stderr, "MsgGet successfully got message\n");
255 break;
256 default:
257 fprintf(stderr, "Error from MsgGet: %s\n", X400msError(status));
258 /* tidily close the session */
259 status = X400msClose(sp);
260 exit(status);
261 break;
262 }
263
264 if (type != X400_MSG_MESSAGE) {
265 /**********************************/
266 /* Report on the received Report */
267 /**********************************/
268 status = do_report(sp, mp);
269 return (status);
270 }
271
272 /**********************************/
273 /* Report on the received Message */
274 /**********************************/
275
276 status = X400msMsgGetIntParam(mp, X400_N_IS_IPN, &intparam);
277 if (status != X400_E_NOERROR) {
278 fprintf(stderr, "Error from MsgGetIntParam (X400_N_IS_IPN): %s\n", X400msError(status));
279 }
280 else {
281 printf("Type of Message: %d\n", intparam);
282 if (intparam != 0) {
283 /**********************************/
284 /* Report on the received IPN */
285 /**********************************/
286 printf("Received an IPN\n");
287 num_ipns_rcvd++;
288 handle_ipn(mp);
289 status = X400msMsgDelete(mp, 0);
290 return status;
291 }
292 }
293 /* we have received a message */
294 num_messages_rcvd++;
295 status = handle_msg(sp, mp);
296 if (status != X400_E_NOERROR) {
297 fprintf(stderr, "Error from handle_msg: %s\n", X400msError(status));
298 return status;
299 }
300 if (gen_ipn) {
301 struct X400msMessage *ipn;
302 status = send_ipn(sp, mp, &ipn);
303 if (status != X400_E_NOERROR) {
304 fprintf(stderr, "Error from send_ipn: %s\n", X400msError(status));
305 }
306 // Deletes message in message store as well as internal copy.
307 status = X400msMsgDelete(mp, 0);
308 if (status != X400_E_NOERROR) {
309 fprintf(stderr, "Error from X400msMsgDelete (subject message)%s\n", X400msError(status));
310 }
311
312 status = X400msMsgDelete(ipn, 0);
313 if (status != X400_E_NOERROR) {
314 fprintf(stderr, "Error from X400msMsgDelete (IPN)%s\n", X400msError(status));
315 }
316 return status;
317 }
318 else {
319 // Deletes message in message store as well as internal copy.
320 status = X400msMsgDelete(mp, 0);
321 if (status != X400_E_NOERROR) {
322 fprintf(stderr, "Error from X400msMsgDelete (IPN)%s\n", X400msError(status));
323 }
324 return status;
325 }
326 return X400_E_NOERROR;
327}
328
329static int do_report(struct X400msSession *sp, struct X400msMessage *mp) {
330 char buffer[BUFSIZ];
331 size_t length;
332 int intparam;
333 char recipient_str[BUFSIZ];
334 int status;
335 int n;
336 struct X400Recipient *rp;
337
338 /**********************************/
339 /* Report on the received Report */
340 /**********************************/
341 num_reports_rcvd++;
342 fprintf(stderr, "Got a report (printing only some attributes)\n");
343
344 // Get the Message Identifier of the Subject message.
345 status = X400msMsgGetStrParam(mp, X400_S_SUBJECT_IDENTIFIER, buffer, sizeof buffer, &length);
346 if (status != X400_E_NOERROR) {
347 fprintf(stderr, "Error from MsgGetStrParam: %s\n", X400msError(status));
348 /* tidily close the session */
349 status = X400msClose(sp);
350 exit(status);
351 }
352 printf("Subject Identifier: %.*s\n", (int)length, buffer);
353
354 /* Get the primary recipients */
355 for (n = 1;; n++) {
356 status = X400msRecipGet(mp, X400_RECIP_REPORT, n, &rp);
357 if (status == X400_E_NO_RECIP) {
358 break;
359 }
360 if (status != X400_E_NOERROR) {
361 fprintf(stderr, "Error from RecipGet: %s\n", X400msError(status));
362 /* tidily close the session */
363 status = X400msClose(sp);
364 exit(status);
365 }
366
367 /* Note: recipient may not actually have an O/R address */
368 status = X400msRecipGetStrParam(rp, X400_S_OR_ADDRESS, recipient_str, sizeof recipient_str, &length);
369 if (status != X400_E_NOERROR) {
370 fprintf(stderr, "Error from RecipGetStrParam: %s\n", X400msError(status));
371 /* tidily close the session */
372 status = X400msClose(sp);
373 exit(status);
374 }
375 /* print out the O/R Address of the report */
376 printf("Delivery Report for recipient %d: %.*s\n", n, (int)length, recipient_str);
377
378 /* The original message delivery time, if this attribute exists,
379 * then the report is a positive Delivery Report */
380 status = X400msRecipGetStrParam(rp, X400_S_MESSAGE_DELIVERY_TIME, buffer, sizeof buffer, &length);
381
382 if (status == X400_E_NOERROR) {
383 /* Positive Delivery Report */
384 printf("Delivery Time: %.*s\n", (int)length, buffer);
385 }
386 else {
387 /* Negative Delivery Report */
388 printf("Negative Delivery Report for recipient %d: %.*s\n", n, (int)length, recipient_str);
389
390 /* Supplementary Info to the report */
391 status = X400msRecipGetStrParam(rp, X400_S_SUPPLEMENTARY_INFO, buffer, sizeof buffer, &length);
392 if (status != X400_E_NOERROR) {
393 fprintf(stderr, "Error from RecipGetStrParam: %s\n", X400msError(status));
394 buffer[0] = '\0';
395 }
396 printf("Supplementary Info: %.*s\n", (int)length, buffer);
397
398 /* The reason why the message was not delivered */
399 status = X400msRecipGetIntParam(rp, X400_N_NON_DELIVERY_REASON, &intparam);
400 if (status != X400_E_NOERROR) {
401 fprintf(stderr, "Error from RecipGetIntParam: %s\n", X400msError(status));
402 }
403 printf("Non-Delivery Reason: %d\n", intparam);
404
405 /* The diagnostics of the report for this recipient */
407 if (status != X400_E_NOERROR) {
408 fprintf(stderr, "Error from RecipGetIntParam: %s\n", X400msError(status));
409 }
410 printf("Non-Delivery Diagnostic: %d\n", intparam);
411 }
412 }
413
414 status = X400msMsgDelete(mp, 0);
415 if (status != X400_E_NOERROR) {
416 fprintf(stderr, "Error from X400msMsgDelete: %s\n", X400msError(status));
417 }
418 return status;
419}
420
421static int handle_ipn(struct X400msMessage *mp) {
422 struct X400Recipient *rp;
423 int status;
424 char buffer[BUFSIZ];
425 size_t length;
426 int intparam;
427
428 /* The X400_S_OR_ADDRESS in the message is the IPN originator */
429 /* not clear why X400_ORIGINATOR doesn;t work */
430 status = X400msMsgGetStrParam(mp, X400_S_OR_ADDRESS, buffer, sizeof buffer, &length);
431 if (status != X400_E_NOERROR) {
432 fprintf(stderr, "Error from MsgGetStrParam (X400_S_OR_ADDRESS): %s\n", X400msError(status));
433 }
434 else {
435 printf("IPN Originator: %.*s\n", (int)length, buffer);
436 }
437
438 /* Obtain the envelope recipient address */
439 status = X400msRecipGet(mp, X400_RECIP_ENVELOPE, 1, &rp);
440 if (status != X400_E_NOERROR) {
441 fprintf(stderr, "Error from X400msRecipGet (X400_RECIP_ENVELOPE): %s\n", X400msError(status));
442 }
443 else {
444 status = X400RecipGetStrParam(rp, X400_S_OR_ADDRESS, buffer, sizeof buffer, &length);
445 if (status != X400_E_NOERROR) {
446 fprintf(stderr, "Error from X400RecipGetStrParam (X400_S_OR_ADDRESS): %s\n", X400msError(status));
447 }
448 else {
449
450 buffer[length] = '\0';
451 printf("IPN Recipient: %.*s\n", (int)length, buffer);
452 }
453 }
454
455 /* The subject message identifier */
456 status = X400msMsgGetStrParam(mp, X400_S_SUBJECT_IPM, buffer, sizeof buffer, &length);
457 if (status != X400_E_NOERROR) {
458 fprintf(stderr, "Error from MsgGetStrParam (X400_S_SUBJECT_IPM): %s\n", X400msError(status));
459 }
460 else {
461 printf("Subject Message Identifier: %.*s\n", (int)length, buffer);
462 }
463
464 /* The conversion EITs */
465 status = X400msMsgGetStrParam(mp, X400_S_CONVERSION_EITS, buffer, sizeof buffer, &length);
466 if (status != X400_E_NOERROR) {
467 fprintf(stderr, "Error from MsgGetStrParam (X400_S_CONVERSION_EITS): %s\n", X400msError(status));
468 }
469 else {
470 printf("conversion EITs: %.*s\n", (int)length, buffer);
471 }
472
473 /* non-receipt reason */
474 status = X400msMsgGetIntParam(mp, X400_N_NON_RECEIPT_REASON, &intparam);
475 if (status == X400_E_NOERROR) {
476 printf(" non-receipt reason: %d\n", intparam);
477 }
478 else {
479 fprintf(stderr, "Error getting non-receipt reason: %s\n", X400msError(status));
480 }
481
482 /* discard reason */
483 status = X400msMsgGetIntParam(mp, X400_N_DISCARD_REASON, &intparam);
484 if (status == X400_E_NOERROR) {
485 printf("discard reason: %d\n", intparam);
486 }
487 else {
488 fprintf(stderr, "Error getting discard reason: %s\n", X400msError(status));
489 }
490
491 /* Autoforward comment */
492 status = X400msMsgGetStrParam(mp, X400_S_AUTOFORWARD_COMMENT, buffer, sizeof buffer, &length);
493 if (status != X400_E_NOERROR) {
494 fprintf(stderr, "Error from MsgGetStrParam (X400_S_AUTOFORWARD_COMMENT): %s\n", X400msError(status));
495 }
496 else {
497 printf("autoforward comment: %.*s\n", (int)length, buffer);
498 }
499
500 /* Time of receipt: UTCTime format */
501 status = X400msMsgGetStrParam(mp, X400_S_RECEIPT_TIME, buffer, sizeof buffer, &length);
502 if (status != X400_E_NOERROR) {
503 fprintf(stderr, "Error from MsgGetStrParam(X400_S_RECEIPT_TIME): %s\n", X400msError(status));
504 }
505 else {
506 printf(" Time of receipt: (UTCTime format): %.*s\n", (int)length, buffer);
507 }
508
509 /* Acknowledgement mode: 0 - manual; 1 -automatic */
510 status = X400msMsgGetIntParam(mp, X400_N_ACK_MODE, &intparam);
511 if (status == X400_E_NOERROR) {
512 printf(" Acknowledgement mode: (0 - manual; 1 -automatic): %d\n", intparam);
513 }
514 else {
515 fprintf(stderr, "Error getting Acknowledgement mode: %s\n", X400msError(status));
516 }
517
518 /* Supplementary information associated with IPN */
519 status = X400msMsgGetStrParam(mp, X400_S_SUPP_RECEIPT_INFO, buffer, sizeof buffer, &length);
520 if (status != X400_E_NOERROR) {
521 fprintf(stderr, "Error from MsgGetStrParam (X400_S_SUPP_RECEIPT_INFO): %s\n", X400msError(status));
522 /* tidily close the session */
523 /* status = X400msClose(sp);
524 exit(status);
525 */
526 }
527 else {
528 printf(" Supplementary information: %.*s\n", (int)length, buffer);
529 }
530 status = X400msMsgGetIntParam(mp, X400_N_CONTENT_TYPE, &intparam);
531 if (status != X400_E_NOERROR) {
532 fprintf(stderr, "Error from MsgGetIntParam (X400_N_CONTENT_TYPE,): %s\n", X400msError(status));
533 }
534 else {
535 printf("Content Type: %d\n", intparam);
536 }
537
538 return X400_E_NOERROR;
539}
540
541static int handle_msg(struct X400msSession *sp, struct X400msMessage *mp) {
542 int status;
543 int intparam;
544 size_t length;
545 char buffer[BUFSIZ];
546 struct X400Recipient *rp;
547 int n;
548
549 /* Size */
550 status = X400msMsgGetIntParam(mp, X400_N_CONTENT_LENGTH, &intparam);
551 if (status != X400_E_NOERROR) {
552 fprintf(stderr, "Error from MsgGetIntParam: %s\n", X400msError(status));
553 }
554 printf("Size of Message: %d\n", intparam);
555
556 /* content type */
557 status = X400msMsgGetIntParam(mp, X400_N_CONTENT_TYPE, &intparam);
558 if (status != X400_E_NOERROR) {
559 fprintf(stderr, "Error from MsgGetIntParam (X400_N_CONTENT_TYPE,): %s\n", X400msError(status));
560 }
561 else {
562 printf("Content Type: %d\n", intparam);
563 }
564
565 /* The external content type */
566 status = X400msMsgGetStrParam(mp, X400_S_EXTERNAL_CONTENT_TYPE, buffer, sizeof buffer, &length);
567 if (status != X400_E_NOERROR) {
568 fprintf(stderr, "Error from MsgGetStrParam (X400_S_EXTERNAL_CONTENT_TYPE): %s\n", X400msError(status));
569 }
570 else {
571 printf("External Content Type: %.*s\n", (int)length, buffer);
572 }
573
574 /* The message identifier */
575 status = X400msMsgGetStrParam(mp, X400_S_MESSAGE_IDENTIFIER, buffer, sizeof buffer, &length);
576 if (status != X400_E_NOERROR) {
577 fprintf(stderr, "Error from MsgGetStrParam: %s\n", X400msError(status));
578 /* tidily close the session */
579 status = X400msClose(sp);
580 exit(status);
581 }
582 printf("Message Identifier: %.*s\n", (int)length, buffer);
583
584 /* display any PCT info available */
585 get_4406_info(mp);
586
587 /* The ORADDRESS in the message is the (envelope) originator */
588 status = X400msMsgGetStrParam(mp, X400_S_OR_ADDRESS, buffer, sizeof buffer, &length);
589 if (status != X400_E_NOERROR) {
590 fprintf(stderr, "Error from MsgGetStrParam: %s\n", X400msError(status));
591 /* tidily close the session */
592 status = X400msClose(sp);
593 exit(status);
594 }
595 printf("Originator: %.*s\n", (int)length, buffer);
596
597 /* Get the envelope recipients */
598 for (n = 1;; n++) {
599 status = X400msRecipGet(mp, X400_RECIP_ENVELOPE, n, &rp);
600 if (status == X400_E_NO_RECIP) {
601 break;
602 }
603 if (status != X400_E_NOERROR) {
604 fprintf(stderr, "Error from RecipGet (envelope): %s\n", X400msError(status));
605 /* tidily close the session */
606 status = X400msClose(sp);
607 exit(status);
608 }
609
610 /* Note: recipient may not actually have an O/R address */
611 status = X400msRecipGetStrParam(rp, X400_S_OR_ADDRESS, buffer, sizeof buffer, &length);
612 if (status == X400_E_NOERROR) {
613 printf("Env Recipient %d: %.*s\n", n, (int)length, buffer);
614 }
615
616 // Get back status of the Proof Of Del Request in the recipient.
617 status = X400msRecipGetIntParam(rp, X400_N_PROOF_OF_DEL_REQ, &intparam);
618 if (status == X400_E_NOERROR) {
619 printf("Recipient proof of delivery request is %d\n", intparam);
620 }
621 else {
622 fprintf(stderr, "Error getting proof of delivery request: %s\n", X400msError(status));
623 }
624
625 /* report content integrity check info if available */
626 get_cic(rp);
627
628 /* return MessageToken info if available */
629 report_msg_token_info(rp);
630
631 /* get and display the seccurity label if available */
632 get_sec_label(mp);
633 }
634
635 /* Get the primary recipients */
636 for (n = 1;; n++) {
637 status = X400msRecipGet(mp, X400_RECIP_PRIMARY, n, &rp);
638 if (status == X400_E_NO_RECIP) {
639 break;
640 }
641 if (status != X400_E_NOERROR) {
642 fprintf(stderr, "Error from RecipGet (primary): %s\n", X400msError(status));
643 /* This is allowed, so continue reading the message */
644 break;
645 }
646
647 /* Note: recipient may not actually have an O/R address */
648 status = X400msRecipGetStrParam(rp, X400_S_OR_ADDRESS, buffer, sizeof buffer, &length);
649 if (status == X400_E_NOERROR) {
650 printf("Primary Recipient %d: %.*s\n", n, (int)length, buffer);
651 }
652
653 status = X400msRecipGetIntParam(rp, X400_N_PRECEDENCE, &intparam);
654 if (status == X400_E_NOERROR) {
655 printf("Primary Recipient Precedence %d\n", intparam);
656 }
657 else {
658 fprintf(stderr, "Error getting Primary Recipient Precedence : %s\n", X400msError(status));
659 }
660 }
661
662 /* Subject is optional */
663 status = X400msMsgGetStrParam(mp, X400_S_SUBJECT, buffer, sizeof buffer, &length);
664 if (status == X400_E_NOERROR) {
665 printf("Subject: %.*s\n", (int)length, buffer);
666 }
667
668 /* And message text (or it could be another type) */
669 status = X400msMsgGetStrParam(mp, X400_T_IA5TEXT, buffer, sizeof buffer, &length);
670 if (status == X400_E_NOERROR) {
671 printf("Text:\n%.*s\n", (int)length, buffer);
672 }
673 else {
674 printf("No IA5 Text content (%d: %s)\n", status, X400msError(status));
675 }
676
677 /* get all the attachments */
678 printf("Getting body parts\n");
679 get_body_parts(mp);
680
681 return X400_E_NOERROR;
682}
683
684static int send_ipn(struct X400msSession *sp, struct X400msMessage *mp, struct X400msMessage **ipn) {
685 int status;
686 status = X400msMsgNew(sp, X400_MSG_MESSAGE, ipn);
687 if (status != X400_E_NOERROR) {
688 fprintf(stderr, "x400msMsgNew returned error: %s\n", X400msError(status));
689 return (status);
690 }
691
692 status = X400msMakeIPN(mp, -1, ipn);
693 if (status != X400_E_NOERROR) {
694 fprintf(stderr, "Error from X400msMakeIPN: %s\n", X400msError(status));
695 return status;
696 }
697
698 /* submit */
699 status = X400msMsgSend(*ipn);
700 if (status != X400_E_NOERROR) {
701 fprintf(stderr, "x400msMsgSend returned error: %s\n", X400msError(status));
702 return (status);
703 }
704 else {
705 printf("IPN submitted successfully\n");
706 }
707
708 return status;
709}
710/*
711 * Recommended function to setup security env for verification.
712 * No digitial ID required - just a directory which contains
713 * trust anchors which are read as DER file (certificate.crt).
714 *
715 * The certificate (containing public key) is obtained from the message
716 * which is referenced in the message.
717 */
718
719static void setup_default_new_sec_env(struct X400msSession *sp, char *local_trusted_ca_certs_dir) {
720 int status;
721
722 /* Directory containing trusted CA Certificates */
723 printf(" Adding %s as trusted CA cert dir\n", trusted_ca_certs_dir);
724 status = X400msSetStrDefault(sp, X400_S_SEC_TRUSTED_CERTS_DIR, local_trusted_ca_certs_dir, -1);
725 if (status != X400_E_NOERROR) {
726 fprintf(stderr, "X400msSetStrDefault returned error: %s\n", X400msError(status));
727 exit(status);
728 }
729
730 return;
731}
732
733/*
734 * Obsolete function to use to set up the security environment. This provides a
735 * directory in which PKCS12 files are checked to find one whose subject DN
736 * matches that of this client.
737 *
738 * Any self signed certificates found in the directory are treated as
739 * trusted.
740 */
741
742static void setup_default_old_sec_env(struct X400msSession *sp, char *id, char *dn, char *pw /* passphrase for private key in pkcs12 file */
743) {
744 int status;
745
746 /* first set a default security identity. This passes in the name of a
747 * directory, which contains an x509 subdirectory in which all Identities
748 * are held */
749 /* X400msSetStrDefault(sp, X400_S_SEC_IDENTITY, "/var/isode/dsa-db/", -1);
750 * */
752
753 /* select by DN which Identity is to be used (if there are several)
754 * Currently these must be PKCS12 files */
755 status = X400msSetStrDefault(sp, X400_S_SEC_IDENTITY_DN, dn, -1);
756 if (status != X400_E_NOERROR) {
757 fprintf(stderr, "X400msSetStrDefault returned error: %s\n", X400msError(status));
758 exit(status);
759 }
760
761 /* passphrase used to open the Identity */
763 if (status != X400_E_NOERROR) {
764 fprintf(stderr, "X400msSetStrDefault returned error: %s\n", X400msError(status));
765 exit(status);
766 }
767 return;
768}
769
770static void report_msg_token_info(struct X400Recipient *rp) {
771 char buffer[BUFSIZ];
772 int status;
773 int param;
774 size_t length;
775
776 status = X400msRecipGetIntParam(rp, X400_N_MSGTOK_STATUS, &param);
777 if (status == X400_E_NO_VALUE) {
778 fprintf(stderr, "No MessageToken present in recipient\n");
779 /* no further information available */
780 return;
781 }
782 else if (status != X400_E_NOERROR) {
783 fprintf(stderr, "Error from RecipGetIntParam: %s (%d)\n", X400msError(status), X400_N_MSGTOK_STATUS);
784 fprintf(stderr, "Message Token status not available\n");
785 }
786 else {
787 fprintf(stderr, "Message Token status %d \n", param);
788 }
789
790 switch (param) {
791 case X400_E_NOERROR:
792 fprintf(stderr, "Token OK (%d)\n", param);
793 break;
794 case X400_E_X509_ENV:
795 case X400_E_X509_INIT:
796 fprintf(stderr, "Message Token validation cannot take place because the security environment is invalid (%d):\n", param);
797 /* other values will not be available */
798 return;
806 fprintf(stderr, "Message Token validation failed (%d): %s\n", param, X400msError(param));
807 break;
808 default:
809 fprintf(stderr, "Unexpected Message Token validation result (%d): %s\n", param, X400msError(param));
810 break;
811 }
812
813 //show_certificate (rp, X400_N_CERT_MSGTOK, "message-token");
814 show_recip_certificate(rp, X400_N_CERT_MSGTOK, "message-token");
815
816 status = X400msRecipGetStrParam(rp, X400_S_MSGTOK_RECIP, buffer, sizeof buffer, &length);
817 if (status != X400_E_NOERROR) {
818 fprintf(stderr, "Error from RecipGetStrParam: %s\n", X400msError(status));
819
820 fprintf(stderr, "recipient in token not available\n");
821 }
822 else {
823 fprintf(stderr, "Message Token(%u): recipient in Token '%.*s'\n", (unsigned)length, (int)length, buffer);
824 }
825
826 status = X400msRecipGetStrParam(rp, X400_S_MSGTOK_DER, buffer, sizeof buffer, &length);
827 if (status != X400_E_NOERROR) {
828 fprintf(stderr, "Error from RecipGetStrParam: %s (%d)\n", X400msError(status), X400_S_MSGTOK_DER);
829 fprintf(stderr, "Message Token DER not available\n");
830 }
831 else {
832 fprintf(stderr, "Message Token DER available (%u bytes)\n", (unsigned)length);
833 }
834
835 status = X400msRecipGetIntParam(rp, X400_N_MSGTOK_SEQ_NUM, &param);
836 if (status != X400_E_NOERROR) {
837 fprintf(stderr, "Error from RecipGetStrParam: %s (%d)\n", X400msError(status), X400_N_MSGTOK_STATUS);
838 fprintf(stderr, "Message Token seq num not available\n");
839 }
840 else {
841 fprintf(stderr, "Message Token seq num %d \n", param);
842 }
843
844 status = X400msRecipGetStrParam(rp, X400_S_MSGTOK_SEC_LAB, buffer, sizeof buffer, &length);
845 if (status != X400_E_NOERROR) {
846 fprintf(stderr, "Error from RecipGetStrParam: %s (%d)\n", X400msError(status), X400_S_MSGTOK_SEC_LAB);
847 fprintf(stderr, "Message Token Security Label DER not available\n");
848 }
849 else {
850 fprintf(stderr, "Message Token Security Label DER available (%u bytes)\n", (unsigned)length);
851 fprintf(stderr, "Security Label from Message Token is:\n");
852 print_sec_label((unsigned char *)buffer, length);
853 }
854
855 /* get back status of the Content Integrity Check in the message token */
857 if (status == X400_E_NO_VALUE) {
858 printf("No Content Integrity Check in token\n");
859 }
860 else if (status != X400_E_NOERROR) {
861 printf("Error from RecipGetIntParam: %s\n", X400msError(status));
862 }
863 else {
864
865 /* report CIC information */
866 switch (param) {
867 case X400_E_NOERROR:
868 printf("Content Integrity Check in token succeeded\n");
869 break;
870 default:
871 printf("Content Integrity Check in token error (%d): %s\n", param, X400msError(param));
872 break;
873 }
874
875 status = X400msRecipGetStrParam(rp, X400_S_MSGTOK_CIC, buffer, sizeof buffer, &length);
876 if (status != X400_E_NOERROR) {
877 fprintf(stderr, "Error from RecipGetStrParam: %s (%d)\n", X400msError(status), X400_S_MSGTOK_CIC);
878 fprintf(stderr, "Message Token Content Integrity Check DER not available\n");
879 }
880 else {
881 fprintf(stderr, "Message Token Content Integrity Check DER available (%u bytes)\n", (unsigned)length);
882 }
883
884 //show_certificate (rp, X400_N_CERT_MSGTOK_CIC, "token CIC");
885 show_recip_certificate(rp, X400_N_CERT_MSGTOK_CIC, "token CIC");
886 }
887
889 if (status != X400_E_NOERROR) {
890 fprintf(stderr, "Error from RecipGetStrParam: %s (%d)\n", X400msError(status), X400_N_MSGTOK_PODR_STATUS);
891 fprintf(stderr, "Message Token proof of delivery status not available\n");
892 }
893 else {
894 fprintf(stderr, "Message Token proof of delivery status %d \n", param);
895 }
896
898 if (status != X400_E_NOERROR) {
899 fprintf(stderr, "Error from RecipGetStrParam: %s (%d)\n", X400msError(status), X400_N_MSGTOK_SEC_LAB_STATUS);
900 fprintf(stderr, "Message Token security label status not available\n");
901 }
902 else {
903 fprintf(stderr, "Message Token security label status %d \n", param);
904 }
905
907 if (status != X400_E_NOERROR) {
908 fprintf(stderr, "Error from RecipGetStrParam: %s (%d)\n", X400msError(status), X400_N_MSGTOK_RECIP_STATUS);
909 fprintf(stderr, "Message Token recip status not available\n");
910 }
911 else {
912 fprintf(stderr, "Message Token recip status %d \n", param);
913 }
914
915 return;
916}
917
918static int get_sec_label(struct X400msMessage *mp) {
919 unsigned char slab_buffer[XML_BUFSIZE];
920 int status;
921 size_t length;
922
923 status = X400msMsgGetStrParam(mp, X400_S_SECURITY_LABEL, (char *)slab_buffer, XML_BUFSIZE, &length);
924 if (status == X400_E_NO_VALUE) {
925 printf("No security label\n");
926 }
927 else if (status != X400_E_NOERROR) {
928 fprintf(stderr, "Failed to fetch security label: %d", status);
929 return (status);
930 }
931 else {
932 fprintf(stderr, "Security Label from envelope is:\n");
933 print_sec_label(slab_buffer, length);
934 }
935 return X400_E_NOERROR;
936}
937
938static void print_sec_label(unsigned char slab_buffer[], unsigned int length) {
939
940 char xml_buffer[XML_BUFSIZE];
941 int status;
942
943 status = SecLabelInit("Example program");
944 if (status != SECLABEL_E_NOERROR) {
945 fprintf(stderr, "SecLabelInit returned error %d\n", status);
946 return;
947 }
948
949 status = SecLabelPrint(slab_buffer, length, xml_buffer, XML_BUFSIZE);
950
951 if (status != SECLABEL_E_NOERROR) {
952 fprintf(stderr, "SecLabelParse returned error %d\n", status);
953 return;
954 }
955
956 /* You could now write out the XML file, or parse it in memory..*/
957 printf("Got security label:%s\n", xml_buffer);
958 return;
959}
960
961static int get_cic(struct X400Recipient *rp) {
962 char buffer[BUFSIZ];
963 int status, cic_status;
964 int intparam;
965 size_t length;
966
967 /* get back status of the Content Integrity Check in the recipient */
968 cic_status = X400msRecipGetIntParam(rp, X400_N_RECIP_CIC_STATUS, &intparam);
969 if (cic_status == X400_E_NO_VALUE) {
970 printf("No Content Integrity Check in recipient\n");
971 return X400_E_NOERROR;
972 }
973 else if (cic_status != X400_E_NOERROR) {
974 printf("Error from RecipGetIntParam: %s\n", X400msError(cic_status));
975 return cic_status;
976 }
977
978 /* report CIC information */
979 switch (intparam) {
980 case X400_E_NOERROR:
981 printf("Content Integrity Check succeeded\n");
982 break;
983 default:
984 printf("Content Integrity Check error (%d): %s\n", intparam, X400msError(intparam));
985 break;
986 }
987
988 /* Return the Content Integrity Check */
989 status = X400msRecipGetStrParam(rp, X400_S_RECIP_CIC, buffer, sizeof buffer, &length);
990 if (status != X400_E_NOERROR) {
991 fprintf(stderr, "Error getting recipient cic: %s\n", X400msError(status));
992 }
993 else {
994 printf("Content Integrity Check found in recipient (%d)\n", (int)length);
995 }
996
997 //show_certificate (rp, X400_N_CERT_RECIP_CIC, "recipient CIC");
998 show_recip_certificate(rp, X400_N_CERT_RECIP_CIC, "recipient CIC");
999
1000 return X400_E_NOERROR;
1001}
1002
1003static int get_4406_info(struct X400msMessage *mp) {
1004 int status;
1005 int intparam;
1006 size_t length;
1007 char buffer[BUFSIZ];
1008
1009 /* get the 4406 status which tells us if it's PCT or not */
1010 status = X400msMsgGetIntParam(mp, X400_N_S4406_STATUS, &intparam);
1011 if (status == X400_E_NO_VALUE) {
1012 printf("4406 Status (X400_N_S4406_STATUS) absent so not PCT: %s\n", X400msError(status));
1013 return X400_E_NOERROR;
1014 }
1015 if (status != X400_E_NOERROR) {
1016 fprintf(stderr, "Error from MsgGetIntParam (X400_N_S4406_STATUS): %s\n", X400msError(status));
1017 }
1018 else {
1019 printf("4406 Status(X400_N_S4406_STATUS): %d\n", intparam);
1020 }
1021
1022 /* get the 4406 security elements */
1023 status = X400msMsgGetIntParam(mp, X400_N_S4406, &intparam);
1024 if (status == X400_E_NO_VALUE) {
1025 printf("4406 absent: %s\n", X400msError(status));
1026 }
1027 if (status != X400_E_NOERROR) {
1028 fprintf(stderr, "Error from MsgGetIntParam (X400_N_S4406): %s\n", X400msError(status));
1029 }
1030 else {
1031 printf("4406 (X400_N_S4406): %d\n", intparam);
1032 }
1033
1034 /* Get the Message Identifier of the Subject message */
1035 status = X400msMsgGetStrParam(mp, X400_S_S4406_STATUS_DETAIL, buffer, sizeof buffer, &length);
1036 if (status != X400_E_NOERROR) {
1037 fprintf(stderr, "Error from MsgGetStrParam (X400_S_S4406_STATUS_DETAIL): %s\n", X400msError(status));
1038 return (status);
1039 }
1040 printf("S4406 Status Detail (X400_S_S4406_STATUS_DETAIL): %.*s\n", (int)length, buffer);
1041
1042 show_message_certificate(mp, "S4406");
1043
1044 return X400_E_NOERROR;
1045}
1046
1047static void show_message_certificate(struct X400msMessage *mp, const char *tag ARGNOTUSED) {
1048 int status;
1049 struct X400Certificate *cert;
1050
1051 status = X400msMsgGetCert(mp, X400_N_S4406_CERTIFICATE, &cert);
1052 if (status != X400_E_NOERROR) {
1053 fprintf(stderr, "Error getting S4406 certificate: %s\n", X400msError(status));
1054 return;
1055 }
1056 show_certificate(cert, "X400_N_S4406_CERTIFICATE");
1057 return;
1058}
1059
1060static void show_recip_certificate(struct X400Recipient *rp, int certtype, const char *tag) {
1061 int status;
1062 struct X400Certificate *cert;
1063
1064 status = X400RecipGetCert(rp, certtype, &cert);
1065 if (status != X400_E_NOERROR) {
1066 fprintf(stderr, "Error getting %s certificate: %s\n", tag, X400msError(status));
1067 return;
1068 }
1069 show_certificate(cert, tag);
1070 return;
1071}
1072
1073static void show_certificate(struct X400Certificate *cert, const char *tag) {
1074 int status;
1075 char buffer[BUFSIZ];
1076 size_t length;
1077 int paramval;
1078
1079 // Return the subject DN from Orig cert.
1080 status = X400CertGetStrParam(cert, X400_S_CERT_SUBJECT_DN, buffer, sizeof buffer, &length);
1081 if (status != X400_E_NOERROR) {
1082 fprintf(stderr, "Error getting subject of cert used for %s: %s\n", tag, X400msError(status));
1083 }
1084 else {
1085 printf("Subject of Cert used to verify %s (%.*s)\n", tag, (int)length, buffer);
1086 }
1087
1088 // Return the issuer DN from Orig cert.
1089 status = X400CertGetStrParam(cert, X400_S_CERT_ISSUER_DN, buffer, sizeof buffer, &length);
1090 if (status != X400_E_NOERROR) {
1091 fprintf(stderr, "Error getting issuer of cert used for %s: %s\n", tag, X400msError(status));
1092 }
1093 else {
1094 printf("Issuer of Cert used to verify %s (%.*s)\n", tag, (int)length, buffer);
1095 }
1096
1097 // Return the serial number from Orig cert used to verify the Content Integrity Check.
1098 status = X400CertGetStrParam(cert, X400_S_CERT_SERIAL_NUM, buffer, sizeof buffer, &length);
1099 if (status != X400_E_NOERROR) {
1100 fprintf(stderr, "Error getting serial num of cert used for %s: %s\n", tag, X400msError(status));
1101 }
1102 else {
1103 printf("Serial Num of Cert used to verify %s (%.*s)\n", tag, (int)length, buffer);
1104 }
1105
1106 // Return the Orig cert used to verify the Content Integrity Check.
1107 status = X400CertGetStrParam(cert, X400_S_CERT_BER, buffer, sizeof buffer, &length);
1108 if (status != X400_E_NOERROR) {
1109 fprintf(stderr, "Error getting certificate BER used for %s: %s\n", tag, X400msError(status));
1110 }
1111 else {
1112 printf("Returned certificate used to verify %s (%d)\n", tag, (int)length);
1113 }
1114
1115 // Find any ORaddress SAN.
1116 status = X400CertGetStrParam(cert, X400_S_OR_ADDRESS, buffer, sizeof buffer, &length);
1117 if (status != X400_E_NOERROR) {
1118 if (status == X400_E_NO_VALUE) {
1119 fprintf(stderr, "No ORaddress SAN\n");
1120 }
1121 else {
1122 fprintf(stderr, "Error from CertGetStrParam: %s\n", X400msError(status));
1123 return;
1124 }
1125 }
1126 else {
1127 fprintf(stderr, "ORaddress SAN: '%.*s'\n", (int)length, buffer);
1128 }
1129
1130 // Find any MTAname SAN MTA and GDI parts.
1131 status = X400CertGetStrParam(cert, X400_S_CERT_MTA_NAME, buffer, sizeof buffer, &length);
1132 if (status != X400_E_NOERROR) {
1133 if (status == X400_E_NO_VALUE) {
1134 fprintf(stderr, "No MTAname SAN (MTA)\n");
1135 }
1136 else {
1137 fprintf(stderr, "Error from CertGetStrParam: %s\n", X400msError(status));
1138 return;
1139 }
1140 }
1141 else {
1142 fprintf(stderr, "MTAname SAN MTA: '%.*s'\n", (int)length, buffer);
1143 }
1144 status = X400CertGetStrParam(cert, X400_S_CERT_GDI_NAME, buffer, sizeof buffer, &length);
1145 if (status != X400_E_NOERROR) {
1146 if (status == X400_E_NO_VALUE) {
1147 fprintf(stderr, "No MTAname SAN (GDI)\n");
1148 }
1149 else {
1150 fprintf(stderr, "Error from CertGetStrParam: %s\n", X400msError(status));
1151 return;
1152 }
1153 }
1154 else {
1155 fprintf(stderr, "MTAname SAN GDI: '%.*s'\n", (int)length, buffer);
1156 }
1157
1158 // Check if the ORaddress matches.
1159 status = X400CertGetIntParam(cert, X400_N_CERT_ORADDRESS_STATUS, &paramval);
1160 // If we don't have an ORaddress, check the MTAname.
1161 if (status != X400_E_NOERROR || paramval == X400_E_NO_VALUE) {
1162 if (status != X400_E_NOERROR) {
1163 fprintf(stderr, "Error from ORaddress CertGetStrParam: %s\n", X400msError(status));
1164 }
1165 else {
1166 fprintf(stderr, "ORaddress SAN status: %s\n", X400msError(paramval));
1167 }
1168 // Check if this is server signed.
1169 status = X400CertGetIntParam(cert, X400_N_CERT_MTANAME_STATUS, &paramval);
1170 if (status != X400_E_NOERROR) {
1171 fprintf(stderr, "Error from MTAname CertGetStrParam: %s\n", X400msError(status));
1172 }
1173 else {
1174 fprintf(stderr, "MTAname SAN status: %s\n", X400msError(paramval));
1175 }
1176 }
1177 else {
1178 fprintf(stderr, "ORaddress SAN status: %s\n", X400msError(paramval));
1179 }
1180}
1181
1182static void usage(void) {
1183 printf("usage: %s\n", optstr);
1184 printf("\t where:\n");
1185 printf("\t -u : Don't prompt to override defaults \n");
1186 printf("\t -3 : Use P3 connection \n");
1187 printf("\t -7 : Use P7 connection \n");
1188 printf("\t -m : OR Address in P7 bind arg \n");
1189 printf("\t -d : DN in P7 bind arg \n");
1190 printf("\t -p : Presentation Address of P7 Store \n");
1191 printf("\t -w : P7 password of P7 user \n");
1192 printf("\t -M : OR Address in P3 bind arg \n");
1193 printf("\t -D : DN in P3 bind arg \n");
1194 printf("\t -P : Presentation Address of P3 server\n");
1195 printf("\t -W : P3 password of P3 user \n");
1196 printf("\t -e : Security Environment (dir with x509 subdir): obsolete, use -Y <p12file>\n");
1197 printf("\t -x : DN of X.509 Digital Identity\n");
1198 printf("\t -b : Passphrase for private key in PKCS12 file\n");
1199 printf("\t -E : Fetch messages until all read\n");
1200 printf("\t -Y : Filename of PKCS12 file containing Digital Identity\n");
1201 printf("\t -U : Directory containing trust anchors\n");
1202 printf("\t -I : Generate IPN from message received\n");
1203 return;
1204}
#define X400_N_CERT_ORADDRESS_STATUS
Definition x400_att.h:1561
#define X400_S_CERT_BER
Definition x400_att.h:1549
#define X400_N_CERT_MTANAME_STATUS
Definition x400_att.h:1568
#define X400_S_CERT_ISSUER_DN
Definition x400_att.h:1555
#define X400_N_CERT_MSGTOK_CIC
Definition x400_att.h:1539
#define X400_N_CERT_MSGTOK
Definition x400_att.h:1533
#define X400_N_CERT_RECIP_CIC
Definition x400_att.h:1536
#define X400_S_CERT_SUBJECT_DN
Definition x400_att.h:1552
#define X400_S_CERT_SERIAL_NUM
Definition x400_att.h:1558
#define X400_S_CERT_GDI_NAME
Definition x400_att.h:405
#define X400_S_CERT_MTA_NAME
Definition x400_att.h:408
#define X400_S_RECIP_CIC
Definition x400_att.h:1504
#define X400_N_RECIP_CIC_STATUS
Definition x400_att.h:1501
int X400CertGetStrParam(struct X400Certificate *cp, int paramtype, char *buffer, size_t buflen, size_t *paramlenp)
Return a string-valued parameter from the certificate object.
int X400RecipGetCert(struct X400Recipient *rp, int certtype, struct X400Certificate **certp)
Get certificate object from recipient This returns a certificate which was used to sign an object in ...
int X400CertGetIntParam(struct X400Certificate *cp, int paramtype, int *valp)
Return a integer-valued parameter from the certificate object.
int X400RecipGetStrParam(struct X400Recipient *rp, int paramtype, char *buffer, size_t buflen, size_t *paramlenp)
Return a string-valued parameter from the recipient object.
int X400msMsgGetCert(struct X400msMessage *mp, int certtype, struct X400Certificate **certp)
Get certificate object from message This returns a certificate which was used to sign an object in th...
int X400msRecipGet(struct X400msMessage *mp, int type, int number, struct X400Recipient **rpp)
Get recipient object from message.
int X400msMsgGetStrParam(struct X400msMessage *mp, int paramtype, char *buffer, size_t buflen, size_t *paramlenp)
Return a string-valued parameter from the message object.
int X400msMakeIPN(struct X400msMessage *mp, int non_receipt_reason, struct X400msMessage **mpp)
Make an IPN based on the subject IPM.
int X400msRecipGetStrParam(struct X400Recipient *rp, int paramtype, char *buffer, size_t buflen, size_t *paramlenp)
Return a string-valued parameter from the recipient object.
int X400msWait(struct X400msSession *sp, int seconds, int *count)
Wait for messages to be ready to be read.
int X400msMsgGet(struct X400msSession *sp, int number, struct X400msMessage **mpp, int *typep, int *seqp)
Get message object for transfer out from MS or MTA via P3.
const char * X400msError(int error)
Obtain a string describing the meaning of the given error code.
int X400msSetIntDefault(struct X400msSession *sp, int paramtype, int value)
Set a default integer parameter value in a session.
int X400msMsgSend(struct X400msMessage *mp)
Send message object.
int X400msRecipGetIntParam(struct X400Recipient *rp, int paramtype, int *valp)
Return a integer-valued parameter from the recipient object.
int X400msMsgDelete(struct X400msMessage *mp, int retain)
Delete message object.
int X400msMsgNew(struct X400msSession *sp, int type, struct X400msMessage **mpp)
Creates new message.
int X400msClose(struct X400msSession *sp)
Close a X400 Session.
int X400msSetStrDefault(struct X400msSession *sp, int paramtype, const char *value, size_t length)
Set a default string parameter value in a session.
int X400msOpen(int type, const char *oraddr, const char *dirname, const char *credentials, const char *pa, int *messages, struct X400msSession **spp)
Open a session to a Message Store (P7) or MTA (P3) in synchronous mode.
int X400msMsgGetIntParam(struct X400msMessage *mp, int paramtype, int *valp)
Return a integer-valued parameter from the message object.
#define X400_S_OR_ADDRESS
Definition x400_att.h:349
#define X400_N_PROOF_OF_DEL_REQ
Definition x400_att.h:1004
#define X400_S_SUBJECT
Definition x400_att.h:749
#define X400_T_IA5TEXT
Definition x400_att.h:825
#define X400_B_RETURN_VERIFICATION_ERRORS
Definition x400_att.h:1123
#define X400_S_LOG_CONFIGURATION_FILE
Definition x400_att.h:1116
#define X400_S_MESSAGE_DELIVERY_TIME
Definition x400_att.h:451
#define X400_N_CONTENT_TYPE
Definition x400_att.h:419
#define X400_N_CONTENT_LENGTH
Definition x400_att.h:422
#define X400_S_EXTERNAL_CONTENT_TYPE
Definition x400_att.h:456
#define X400_S_MESSAGE_IDENTIFIER
Definition x400_att.h:416
#define X400_S_SECURITY_LABEL
Definition x400_att.h:1370
#define X400_E_X509_CERT_INVALID
Definition x400_att.h:199
#define X400_E_X509_VERIFY_FAIL
Definition x400_att.h:196
#define X400_E_X509_ITEM_INVALID
Definition x400_att.h:202
#define X400_E_X509_ENV
Definition x400_att.h:175
#define X400_E_NOERROR
Definition x400_att.h:46
#define X400_E_NO_VALUE
Definition x400_att.h:100
#define X400_E_X509_VERIFY_FAIL_NO_CERT
Definition x400_att.h:184
#define X400_E_X509_VERIFY_FAIL_UNSUPPORTED_ALG
Definition x400_att.h:193
#define X400_E_X509_VERIFY_FAIL_NO_PUBKEY
Definition x400_att.h:187
#define X400_E_X509_VERIFY_FAIL_INCOMPAT_ALG
Definition x400_att.h:190
#define X400_E_X509_INIT
Definition x400_att.h:181
#define X400_E_NO_RECIP
Definition x400_att.h:109
#define X400_N_DISCARD_REASON
Definition x400_att.h:1042
#define X400_S_AUTOFORWARD_COMMENT
Definition x400_att.h:1047
#define X400_N_IS_IPN
Definition x400_att.h:1030
#define X400_N_NON_RECEIPT_REASON
Definition x400_att.h:1039
#define X400_N_ACK_MODE
Definition x400_att.h:1053
#define X400_S_SUPP_RECEIPT_INFO
Definition x400_att.h:1056
#define X400_S_RECEIPT_TIME
Definition x400_att.h:1050
#define X400_S_CONVERSION_EITS
Definition x400_att.h:1036
#define X400_S_SUBJECT_IPM
Definition x400_att.h:1033
#define X400_MSG_MESSAGE
Definition x400_att.h:29
#define X400_N_PRECEDENCE
Definition x400_att.h:712
#define X400_RECIP_PRIMARY
Definition x400_att.h:296
#define X400_RECIP_ENVELOPE
Definition x400_att.h:335
#define X400_RECIP_REPORT
Definition x400_att.h:314
#define X400_S_SUPPLEMENTARY_INFO
Definition x400_att.h:1067
#define X400_S_SUBJECT_IDENTIFIER
Definition x400_att.h:1064
#define X400_N_NON_DELIVERY_REASON
Definition x400_att.h:1076
#define X400_N_NON_DELIVERY_DIAGNOSTIC
Definition x400_att.h:1079
#define X400_N_S4406_STATUS
Definition x400_att.h:635
#define X400_S_S4406_STATUS_DETAIL
Definition x400_att.h:641
#define X400_N_S4406_CERTIFICATE
Definition x400_att.h:651
#define X400_N_MSGTOK_SEQ_NUM
Definition x400_att.h:1469
#define X400_N_MSGTOK_RECIP_STATUS
Definition x400_att.h:1484
#define X400_S_SEC_IDENTITY_DN
Definition x400_att.h:572
#define X400_S_MSGTOK_DER
Definition x400_att.h:1466
#define X400_N_S4406
Definition x400_att.h:626
#define X400_N_MSGTOK_CIC_STATUS
Definition x400_att.h:1487
#define X400_N_MSGTOK_STATUS
Definition x400_att.h:1463
#define X400_S_MSGTOK_SEC_LAB
Definition x400_att.h:1475
#define X400_N_MSGTOK_SEC_LAB_STATUS
Definition x400_att.h:1481
#define X400_S_SEC_TRUSTED_CERTS_DIR
Definition x400_att.h:603
#define X400_N_MSGTOK_PODR_STATUS
Definition x400_att.h:1478
#define X400_S_SEC_IDENTITY
Definition x400_att.h:563
#define X400_S_MSGTOK_CIC
Definition x400_att.h:1490
#define X400_S_SEC_IDENTITY_PASSPHRASE
Definition x400_att.h:569
#define X400_S_MSGTOK_RECIP
Definition x400_att.h:1472
X400 MA/MS (P3/P7) Interface.

All rights reserved © 2002 - 2024 Isode Ltd.