diff sip-manual-out/uac.c @ 71:d74b545a3c2a

sip-manual-out: new test program
author Mychaela Falconia <falcon@freecalypso.org>
date Tue, 20 Sep 2022 10:14:18 -0800
parents
children d7b6b8973a83
line wrap: on
line diff
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/sip-manual-out/uac.c	Tue Sep 20 10:14:18 2022 -0800
@@ -0,0 +1,124 @@
+/*
+ * Here we implement processing of SIP responses to the requests we sent out.
+ */
+
+#include <sys/types.h>
+#include <sys/socket.h>
+#include <netinet/in.h>
+#include <arpa/inet.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <strings.h>
+#include "../libsip/parse.h"
+#include "../libsip/out_msg.h"
+
+#define	MAX_TO_TAG	63
+
+extern char *get_single_header();
+
+extern struct in_addr sip_bind_ip;
+extern unsigned sip_bind_port;
+extern char call_id[], from_uri[], to_uri[];
+
+char to_tag[MAX_TO_TAG+1];
+
+add_req_boilerplate(msg, cseq)
+	struct sip_msg_out *msg;
+	char *cseq;
+{
+	char strbuf[256];
+	int rc;
+
+	sprintf(strbuf, "SIP/2.0/UDP %s:%u",
+		inet_ntoa(sip_bind_ip), sip_bind_port);
+	rc = out_msg_add_header(msg, "Via", strbuf);
+	if (rc < 0)
+		return rc;
+	rc = out_msg_add_header(msg, "From", from_uri);
+	if (rc < 0)
+		return rc;
+	if (to_tag[0]) {
+		sprintf(strbuf, "<%s>;tag=%s", to_uri, to_tag);
+		rc = out_msg_add_header(msg, "To", strbuf);
+	} else
+		rc = out_msg_add_header(msg, "To", to_uri);
+	if (rc < 0)
+		return rc;
+	rc = out_msg_add_header(msg, "Call-ID", call_id);
+	if (rc < 0)
+		return rc;
+	rc = out_msg_add_header(msg, "CSeq", cseq);
+	if (rc < 0)
+		return rc;
+	return out_msg_add_header(msg, "Max-Forwards", "70");
+}
+
+add_contact_header(msg)
+	struct sip_msg_out *msg;
+{
+	char strbuf[80];
+
+	sprintf(strbuf, "<sip:%s:%u;transport=udp>",
+		inet_ntoa(sip_bind_ip), sip_bind_port);
+	return out_msg_add_header(msg, "Contact", strbuf);
+}
+
+static void
+send_ack(sin)
+	struct sockaddr_in *sin;
+{
+	struct sip_msg_out msg;
+	int rc;
+
+	rc = start_request_out_msg(&msg, "ACK", to_uri);
+	if (rc < 0) {
+msg_size_err:	fprintf(stderr, "composing ACK message: size error\n");
+		return;
+	}
+	rc = add_req_boilerplate(&msg, "1 ACK");
+	if (rc < 0)
+		goto msg_size_err;
+	out_msg_finish(&msg);
+	sip_tx_packet(&msg, sin);
+}
+
+static void
+handle_invite_response(msg, sin)
+	struct sip_pkt_rx *msg;
+	struct sockaddr_in *sin;
+{
+	printf("Response to INVITE: %s\n", msg->status_str);
+	if (msg->status_code >= 200) {
+		printf("Sending ACK\n");
+		send_ack(sin);
+	}
+}
+
+void
+process_sip_response(msg, sin)
+	struct sip_pkt_rx *msg;
+	struct sockaddr_in *sin;
+{
+	char *call_id_hdr, *cseq_hdr;
+
+	call_id_hdr = get_single_header(msg, "Call-ID", "i", (int *) 0);
+	if (!call_id_hdr) {
+		printf("Got SIP response w/o Call-ID header\n");
+		return;
+	}
+	if (strcmp(call_id_hdr, call_id)) {
+		printf("Got SIP response with wrong Call-ID\n");
+		return;
+	}
+	cseq_hdr = get_single_header(msg, "CSeq", (char *) 0, (int *) 0);
+	if (!cseq_hdr) {
+		printf("Got SIP response w/o CSeq header\n");
+		return;
+	}
+	if (!strcmp(cseq_hdr, "1 INVITE"))
+		handle_invite_response(msg, sin);
+	else
+		printf("Got SIP resp for our Call-ID with unknown CSeq %s\n",
+			cseq_hdr);
+}