patch-2.1.125 linux/net/rose/rose_subr.c
Next file: linux/net/sunrpc/clnt.c
Previous file: linux/net/rose/rose_route.c
Back to the patch index
Back to the overall index
- Lines: 143
- Date:
Wed Oct 7 15:52:55 1998
- Orig file:
v2.1.124/linux/net/rose/rose_subr.c
- Orig date:
Thu Feb 12 20:56:15 1998
diff -u --recursive --new-file v2.1.124/linux/net/rose/rose_subr.c linux/net/rose/rose_subr.c
@@ -251,9 +251,11 @@
return ROSE_ILLEGAL;
}
-static int rose_parse_national(unsigned char *p, struct rose_facilities *facilities, int len)
+static int rose_parse_national(unsigned char *p, struct rose_facilities_struct *facilities, int len)
{
- unsigned char l, n = 0;
+ unsigned char *pt;
+ unsigned char l, lg, n = 0;
+ int fac_national_digis_received = 0;
do {
switch (*p & 0xC0) {
@@ -280,12 +282,33 @@
case 0xC0:
l = p[1];
if (*p == FAC_NATIONAL_DEST_DIGI) {
- memcpy(&facilities->source_digi, p + 2, AX25_ADDR_LEN);
- facilities->source_ndigis = 1;
+ if (!fac_national_digis_received) {
+ memcpy(&facilities->source_digis[0], p + 2, AX25_ADDR_LEN);
+ facilities->source_ndigis = 1;
+ }
+ }
+ else if (*p == FAC_NATIONAL_SRC_DIGI) {
+ if (!fac_national_digis_received) {
+ memcpy(&facilities->dest_digis[0], p + 2, AX25_ADDR_LEN);
+ facilities->dest_ndigis = 1;
+ }
+ }
+ else if (*p == FAC_NATIONAL_FAIL_CALL) {
+ memcpy(&facilities->fail_call, p + 2, AX25_ADDR_LEN);
+ }
+ else if (*p == FAC_NATIONAL_FAIL_ADD) {
+ memcpy(&facilities->fail_addr, p + 3, ROSE_ADDR_LEN);
}
- if (*p == FAC_NATIONAL_SRC_DIGI) {
- memcpy(&facilities->dest_digi, p + 2, AX25_ADDR_LEN);
- facilities->dest_ndigis = 1;
+ else if (*p == FAC_NATIONAL_DIGIS) {
+ fac_national_digis_received = 1;
+ facilities->source_ndigis = 0;
+ facilities->dest_ndigis = 0;
+ for (pt = p + 2, lg = 0 ; lg < l ; pt += AX25_ADDR_LEN, lg += AX25_ADDR_LEN) {
+ if (pt[6] & AX25_HBIT)
+ memcpy(&facilities->dest_digis[facilities->dest_ndigis++], pt, AX25_ADDR_LEN);
+ else
+ memcpy(&facilities->source_digis[facilities->source_ndigis++], pt, AX25_ADDR_LEN);
+ }
}
p += l + 2;
n += l + 2;
@@ -297,7 +320,7 @@
return n;
}
-static int rose_parse_ccitt(unsigned char *p, struct rose_facilities *facilities, int len)
+static int rose_parse_ccitt(unsigned char *p, struct rose_facilities_struct *facilities, int len)
{
unsigned char l, n = 0;
char callsign[11];
@@ -346,17 +369,9 @@
return n;
}
-int rose_parse_facilities(struct sk_buff *skb, struct rose_facilities *facilities)
+int rose_parse_facilities(unsigned char *p, struct rose_facilities_struct *facilities)
{
int facilities_len, len;
- unsigned char *p;
-
- memset(facilities, 0x00, sizeof(struct rose_facilities));
-
- len = (((skb->data[3] >> 4) & 0x0F) + 1) / 2;
- len += (((skb->data[3] >> 0) & 0x0F) + 1) / 2;
-
- p = skb->data + len + 4;
facilities_len = *p++;
@@ -388,6 +403,7 @@
break;
}
}
+ else break; /* Error in facilities format */
}
return 1;
@@ -397,7 +413,7 @@
{
unsigned char *p = buffer + 1;
char *callsign;
- int len;
+ int len, nb;
/* National Facilities */
if (rose->rand != 0 || rose->source_ndigis == 1 || rose->dest_ndigis == 1) {
@@ -410,17 +426,40 @@
*p++ = (rose->rand >> 0) & 0xFF;
}
- if (rose->source_ndigis == 1) {
+ /* Sent before older facilities */
+ if ((rose->source_ndigis > 0) || (rose->dest_ndigis > 0)) {
+ int maxdigi = 0;
+ *p++ = FAC_NATIONAL_DIGIS;
+ *p++ = AX25_ADDR_LEN * (rose->source_ndigis + rose->dest_ndigis);
+ for (nb = 0 ; nb < rose->source_ndigis ; nb++) {
+ if (++maxdigi >= ROSE_MAX_DIGIS)
+ break;
+ memcpy(p, &rose->source_digis[nb], AX25_ADDR_LEN);
+ p[6] |= AX25_HBIT;
+ p += AX25_ADDR_LEN;
+ }
+ for (nb = 0 ; nb < rose->dest_ndigis ; nb++) {
+ if (++maxdigi >= ROSE_MAX_DIGIS)
+ break;
+ memcpy(p, &rose->dest_digis[nb], AX25_ADDR_LEN);
+ p[6] &= ~AX25_HBIT;
+ p += AX25_ADDR_LEN;
+ }
+ }
+
+ /* For compatibility */
+ if (rose->source_ndigis > 0) {
*p++ = FAC_NATIONAL_SRC_DIGI;
*p++ = AX25_ADDR_LEN;
- memcpy(p, &rose->source_digi, AX25_ADDR_LEN);
+ memcpy(p, &rose->source_digis[0], AX25_ADDR_LEN);
p += AX25_ADDR_LEN;
}
- if (rose->dest_ndigis == 1) {
+ /* For compatibility */
+ if (rose->dest_ndigis > 0) {
*p++ = FAC_NATIONAL_DEST_DIGI;
*p++ = AX25_ADDR_LEN;
- memcpy(p, &rose->dest_digi, AX25_ADDR_LEN);
+ memcpy(p, &rose->dest_digis[0], AX25_ADDR_LEN);
p += AX25_ADDR_LEN;
}
}
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen, slshen@lbl.gov