Asterisk - The Open Source Telephony Project  18.5.0
ie.c
Go to the documentation of this file.
1 /*
2  * Chan_Misdn -- Channel Driver for Asterisk
3  *
4  * Interface to mISDN
5  *
6  * Copyright (C) 2005, Christian Richter
7  *
8  * Christian Richter <[email protected]>
9  *
10  * heaviliy patched from jollys ie.cpp, jolly gave me ALL
11  * rights for this code, i can even have my own copyright on it.
12  *
13  * This program is free software, distributed under the terms of
14  * the GNU General Public License
15  */
16 
17 /*! \file
18  * \brief Interface to mISDN
19  * \author Christian Richter <[email protected]>
20  */
21 
22 /*
23  the pointer of enc_ie_* always points to the IE itself
24  if qi is not NULL (TE-mode), offset is set
25 */
26 
27 /*** MODULEINFO
28  <support_level>extended</support_level>
29  ***/
30 
31 #include "asterisk.h"
32 
33 #include <string.h>
34 
35 #include <mISDNuser/mISDNlib.h>
36 #include <mISDNuser/isdn_net.h>
37 #include <mISDNuser/l3dss1.h>
38 #include <mISDNuser/net_l3.h>
39 #include "asterisk/localtime.h"
40 
41 
42 
43 #define MISDN_IE_DEBG 0
44 
45 /* support stuff */
46 static void strnncpy(char *dest, const char *src, size_t len, size_t dst_len)
47 {
48  if (len > dst_len-1)
49  len = dst_len-1;
50  strncpy(dest, src, len);
51  dest[len] = '\0';
52 }
53 
54 
55 /* IE_COMPLETE */
56 static void enc_ie_complete(unsigned char **ntmode, msg_t *msg, int complete, int nt, struct misdn_bchannel *bc)
57 {
58  unsigned char *p;
59  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
60 
61  if (complete<0 || complete>1)
62  {
63  printf("%s: ERROR: complete(%d) is out of range.\n", __FUNCTION__, complete);
64  return;
65  }
66 
67  if (complete)
68  if (MISDN_IE_DEBG) printf(" complete=%d\n", complete);
69 
70  if (complete)
71  {
72  p = msg_put(msg, 1);
73  if (nt)
74  {
75  *ntmode = p;
76  } else
77  qi->QI_ELEMENT(sending_complete) = p - (unsigned char *)qi - sizeof(Q931_info_t);
78 
79  p[0] = IE_COMPLETE;
80  }
81 }
82 
83 static void dec_ie_complete(unsigned char *p, Q931_info_t *qi, int *complete, int nt, struct misdn_bchannel *bc)
84 {
85  *complete = 0;
86  if (!nt)
87  {
88  if (qi->QI_ELEMENT(sending_complete))
89  *complete = 1;
90  } else
91  if (p)
92  *complete = 1;
93 
94  if (*complete)
95  if (MISDN_IE_DEBG) printf(" complete=%d\n", *complete);
96 }
97 
98 
99 /* IE_BEARER */
100 static void enc_ie_bearer(unsigned char **ntmode, msg_t *msg, int coding, int capability, int mode, int rate, int multi, int user, int nt, struct misdn_bchannel *bc)
101 {
102  unsigned char *p;
103  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
104  int l;
105 
106  if (coding<0 || coding>3)
107  {
108  printf("%s: ERROR: coding(%d) is out of range.\n", __FUNCTION__, coding);
109  return;
110  }
111  if (capability<0 || capability>31)
112  {
113  printf("%s: ERROR: capability(%d) is out of range.\n", __FUNCTION__, capability);
114  return;
115  }
116  if (mode<0 || mode>3)
117  {
118  printf("%s: ERROR: mode(%d) is out of range.\n", __FUNCTION__, mode);
119  return;
120  }
121  if (rate<0 || rate>31)
122  {
123  printf("%s: ERROR: rate(%d) is out of range.\n", __FUNCTION__, rate);
124  return;
125  }
126  if (multi>127)
127  {
128  printf("%s: ERROR: multi(%d) is out of range.\n", __FUNCTION__, multi);
129  return;
130  }
131  if (user>31)
132  {
133  printf("%s: ERROR: user L1(%d) is out of range.\n", __FUNCTION__, rate);
134  return;
135  }
136  if (rate!=24 && multi>=0)
137  {
138  printf("%s: WARNING: multi(%d) is only possible if rate(%d) would be 24.\n", __FUNCTION__, multi, rate);
139  multi = -1;
140  }
141 
142  if (MISDN_IE_DEBG) printf(" coding=%d capability=%d mode=%d rate=%d multi=%d user=%d\n", coding, capability, mode, rate, multi, user);
143 
144  l = 2 + (multi>=0) + (user>=0);
145  p = msg_put(msg, l+2);
146  if (nt)
147  *ntmode = p+1;
148  else
149  qi->QI_ELEMENT(bearer_capability) = p - (unsigned char *)qi - sizeof(Q931_info_t);
150  p[0] = IE_BEARER;
151  p[1] = l;
152  p[2] = 0x80 + (coding<<5) + capability;
153  p[3] = 0x80 + (mode<<5) + rate;
154  if (multi >= 0)
155  p[4] = 0x80 + multi;
156  if (user >= 0)
157  p[4+(multi>=0)] = 0xa0 + user;
158 }
159 
160 static void dec_ie_bearer(unsigned char *p, Q931_info_t *qi, int *coding, int *capability, int *mode, int *rate, int *multi, int *user,
161  int *async, int *urate, int *stopbits, int *dbits, int *parity, int nt, struct misdn_bchannel *bc)
162 {
163  int octet;
164  *coding = -1;
165  *capability = -1;
166  *mode = -1;
167  *rate = -1;
168  *multi = -1;
169  *user = -1;
170  *async = -1;
171  *urate = -1;
172  *stopbits = -1;
173  *dbits = -1;
174  *parity = -1;
175 
176  if (!nt)
177  {
178  p = NULL;
179 #ifdef LLC_SUPPORT
180  if (qi->QI_ELEMENT(llc)) {
181 
182  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(llc) + 1;
183  }
184 #endif
185  if (qi->QI_ELEMENT(bearer_capability))
186  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(bearer_capability) + 1;
187  }
188  if (!p)
189  return;
190 
191  if (p[0] < 2)
192  {
193  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
194  return;
195  }
196 
197  *coding = (p[1]&0x60) >> 5;
198  *capability = p[1] & 0x1f;
199  octet = 2;
200  if (!(p[1] & 0x80))
201  octet++;
202 
203  if (p[0] < octet)
204  goto done;
205 
206  *mode = (p[octet]&0x60) >> 5;
207  *rate = p[octet] & 0x1f;
208 
209  octet++;
210 
211  if (p[0] < octet)
212  goto done;
213 
214  if (*rate == 0x18) {
215  /* Rate multiplier only present if 64Kb/s base rate */
216  *multi = p[octet++] & 0x7f;
217  }
218 
219  if (p[0] < octet)
220  goto done;
221 
222  /* Start L1 info */
223  if ((p[octet] & 0x60) == 0x20) {
224  *user = p[octet] & 0x1f;
225 
226  if (p[0] <= octet)
227  goto done;
228 
229  if (p[octet++] & 0x80)
230  goto l2;
231 
232  *async = !!(p[octet] & 0x40);
233  /* 0x20 is inband negotiation */
234  *urate = p[octet] & 0x1f;
235 
236  if (p[0] <= octet)
237  goto done;
238 
239  if (p[octet++] & 0x80)
240  goto l2;
241 
242  /* Ignore next byte for now: Intermediate rate, NIC, flow control */
243 
244  if (p[0] <= octet)
245  goto done;
246 
247  if (p[octet++] & 0x80)
248  goto l2;
249 
250  /* And the next one. Header, multiframe, mode, assignor/ee, negotiation */
251 
252  if (p[0] <= octet)
253  goto done;
254 
255  if (~p[octet++] & 0x80)
256  goto l2;
257 
258  /* Wheee. V.110 speed information */
259 
260  *stopbits = (p[octet] & 0x60) >> 5;
261  *dbits = (p[octet] & 0x18) >> 3;
262  *parity = p[octet] & 7;
263 
264  octet++;
265  }
266  l2: /* Nobody seems to want the rest so we don't bother (yet) */
267  done:
268  if (MISDN_IE_DEBG) printf(" coding=%d capability=%d mode=%d rate=%d multi=%d user=%d async=%d urate=%d stopbits=%d dbits=%d parity=%d\n", *coding, *capability, *mode, *rate, *multi, *user, *async, *urate, *stopbits, *dbits, *parity);
269 }
270 
271 
272 /* IE_CALL_ID */
273 #if 0
274 static void enc_ie_call_id(unsigned char **ntmode, msg_t *msg, char *callid, int callid_len, int nt, struct misdn_bchannel *bc)
275 {
276  unsigned char *p;
277  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
278  int l;
279 
280  char debug[25];
281  int i;
282 
283  if (!callid || callid_len<=0)
284  {
285  return;
286  }
287  if (callid_len>8)
288  {
289  printf("%s: ERROR: callid_len(%d) is out of range.\n", __FUNCTION__, callid_len);
290  return;
291  }
292 
293  i = 0;
294  while(i < callid_len)
295  {
296  if (MISDN_IE_DEBG) printf(debug+(i*3), " %02hhx", (unsigned char)callid[i]);
297  i++;
298  }
299 
300  if (MISDN_IE_DEBG) printf(" callid%s\n", debug);
301 
302  l = callid_len;
303  p = msg_put(msg, l+2);
304  if (nt)
305  *ntmode = p+1;
306  else
307  qi->QI_ELEMENT(call_id) = p - (unsigned char *)qi - sizeof(Q931_info_t);
308  p[0] = IE_CALL_ID;
309  p[1] = l;
310  memcpy(p+2, callid, callid_len);
311 }
312 #endif
313 
314 #if 0
315 static void dec_ie_call_id(unsigned char *p, Q931_info_t *qi, char *callid, int *callid_len, int nt, struct misdn_bchannel *bc)
316 {
317  char debug[25];
318  int i;
319 
320  *callid_len = -1;
321 
322  if (!nt)
323  {
324  p = NULL;
325  if (qi->QI_ELEMENT(call_id))
326  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(call_id) + 1;
327  }
328  if (!p)
329  return;
330  if (p[0] > 8)
331  {
332  printf("%s: ERROR: IE too long (%d).\n", __FUNCTION__, p[0]);
333  return;
334  }
335 
336  *callid_len = p[0];
337  memcpy(callid, p+1, *callid_len);
338 
339  i = 0;
340  while(i < *callid_len)
341  {
342  if (MISDN_IE_DEBG) printf(debug+(i*3), " %02hhx", (unsigned char)callid[i]);
343  i++;
344  }
345 
346  if (MISDN_IE_DEBG) printf(" callid%s\n", debug);
347 }
348 #endif
349 
350 /* IE_CALLED_PN */
351 static void enc_ie_called_pn(unsigned char **ntmode, msg_t *msg, int type, int plan, char *number, int nt, struct misdn_bchannel *bc)
352 {
353  unsigned char *p;
354  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
355  int l;
356 
357  if (type<0 || type>7)
358  {
359  printf("%s: ERROR: type(%d) is out of range.\n", __FUNCTION__, type);
360  return;
361  }
362  if (plan<0 || plan>15)
363  {
364  printf("%s: ERROR: plan(%d) is out of range.\n", __FUNCTION__, plan);
365  return;
366  }
367  if (!number[0])
368  {
369  printf("%s: ERROR: number is not given.\n", __FUNCTION__);
370  return;
371  }
372 
373  if (MISDN_IE_DEBG) printf(" type=%d plan=%d number='%s'\n", type, plan, number);
374 
375  l = 1+strlen((char *)number);
376  p = msg_put(msg, l+2);
377  if (nt)
378  *ntmode = p+1;
379  else
380  qi->QI_ELEMENT(called_nr) = p - (unsigned char *)qi - sizeof(Q931_info_t);
381  p[0] = IE_CALLED_PN;
382  p[1] = l;
383  p[2] = 0x80 + (type<<4) + plan;
384  strncpy((char *)p+3, (char *)number, strlen((char *)number));
385 }
386 
387 static void dec_ie_called_pn(unsigned char *p, Q931_info_t *qi, int *type, int *plan, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
388 {
389  *type = -1;
390  *plan = -1;
391  *number = '\0';
392 
393  if (!nt)
394  {
395  p = NULL;
396  if (qi->QI_ELEMENT(called_nr))
397  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(called_nr) + 1;
398  }
399  if (!p)
400  return;
401  if (p[0] < 2)
402  {
403  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
404  return;
405  }
406 
407  *type = (p[1]&0x70) >> 4;
408  *plan = p[1] & 0xf;
409  strnncpy(number, (char *)p+2, p[0]-1, number_len);
410 
411  if (MISDN_IE_DEBG) printf(" type=%d plan=%d number='%s'\n", *type, *plan, number);
412 }
413 
414 
415 /* IE_CALLING_PN */
416 static void enc_ie_calling_pn(unsigned char **ntmode, msg_t *msg, int type, int plan, int present, int screen, char *number, int nt, struct misdn_bchannel *bc)
417 {
418  unsigned char *p;
419  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
420  int l;
421 
422  if (type<0 || type>7)
423  {
424  printf("%s: ERROR: type(%d) is out of range.\n", __FUNCTION__, type);
425  return;
426  }
427  if (plan<0 || plan>15)
428  {
429  printf("%s: ERROR: plan(%d) is out of range.\n", __FUNCTION__, plan);
430  return;
431  }
432  if (present>3)
433  {
434  printf("%s: ERROR: present(%d) is out of range.\n", __FUNCTION__, present);
435  return;
436  }
437  if (present >= 0) if (screen<0 || screen>3)
438  {
439  printf("%s: ERROR: screen(%d) is out of range.\n", __FUNCTION__, screen);
440  return;
441  }
442 
443  if (MISDN_IE_DEBG) printf(" type=%d plan=%d present=%d screen=%d number='%s'\n", type, plan, present, screen, number);
444 
445  l = 1;
446  if (number) if (number[0])
447  l += strlen((char *)number);
448  if (present >= 0)
449  l += 1;
450  p = msg_put(msg, l+2);
451  if (nt)
452  *ntmode = p+1;
453  else
454  qi->QI_ELEMENT(calling_nr) = p - (unsigned char *)qi - sizeof(Q931_info_t);
455  p[0] = IE_CALLING_PN;
456  p[1] = l;
457  if (present >= 0)
458  {
459  p[2] = 0x00 + (type<<4) + plan;
460  p[3] = 0x80 + (present<<5) + screen;
461  if (number) if (number[0])
462  strncpy((char *)p+4, (char *)number, strlen((char *)number));
463  } else
464  {
465  p[2] = 0x80 + (type<<4) + plan;
466  if (number) if (number[0])
467  strncpy((char *)p+3, (char *)number, strlen((char *)number));
468  }
469 }
470 
471 static void dec_ie_calling_pn(unsigned char *p, Q931_info_t *qi, int *type, int *plan, int *present, int *screen, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
472 {
473  *type = -1;
474  *plan = -1;
475  *present = -1;
476  *screen = -1;
477  *number = '\0';
478 
479  if (!nt)
480  {
481  p = NULL;
482  if (qi->QI_ELEMENT(calling_nr))
483  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(calling_nr) + 1;
484  }
485  if (!p)
486  return;
487  if (p[0] < 1)
488  {
489  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
490  return;
491  }
492 
493  *type = (p[1]&0x70) >> 4;
494  *plan = p[1] & 0xf;
495  if (!(p[1] & 0x80))
496  {
497  if (p[0] < 2)
498  {
499  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
500  return;
501  }
502  *present = (p[2]&0x60) >> 5;
503  *screen = p[2] & 0x3;
504  strnncpy(number, (char *)p+3, p[0]-2, number_len);
505  } else
506  {
507  strnncpy(number, (char *)p+2, p[0]-1, number_len);
508  /* SPECIAL workarround for IBT software bug */
509  /* if (number[0]==0x80) */
510  /* strcpy((char *)number, (char *)number+1); */
511  }
512 
513  if (MISDN_IE_DEBG) printf(" type=%d plan=%d present=%d screen=%d number='%s'\n", *type, *plan, *present, *screen, number);
514 }
515 
516 
517 /* IE_CONNECTED_PN */
518 static void enc_ie_connected_pn(unsigned char **ntmode, msg_t *msg, int type, int plan, int present, int screen, char *number, int nt, struct misdn_bchannel *bc)
519 {
520  unsigned char *p;
521  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
522  int l;
523 
524  if (type<0 || type>7)
525  {
526  printf("%s: ERROR: type(%d) is out of range.\n", __FUNCTION__, type);
527  return;
528  }
529  if (plan<0 || plan>15)
530  {
531  printf("%s: ERROR: plan(%d) is out of range.\n", __FUNCTION__, plan);
532  return;
533  }
534  if (present>3)
535  {
536  printf("%s: ERROR: present(%d) is out of range.\n", __FUNCTION__, present);
537  return;
538  }
539  if (present >= 0) if (screen<0 || screen>3)
540  {
541  printf("%s: ERROR: screen(%d) is out of range.\n", __FUNCTION__, screen);
542  return;
543  }
544 
545  if (MISDN_IE_DEBG) printf(" type=%d plan=%d present=%d screen=%d number='%s'\n", type, plan, present, screen, number);
546 
547  l = 1;
548  if (number) if (number[0])
549  l += strlen((char *)number);
550  if (present >= 0)
551  l += 1;
552  p = msg_put(msg, l+2);
553  if (nt)
554  *ntmode = p+1;
555  else
556  qi->QI_ELEMENT(connected_nr) = p - (unsigned char *)qi - sizeof(Q931_info_t);
557  p[0] = IE_CONNECT_PN;
558  p[1] = l;
559  if (present >= 0)
560  {
561  p[2] = 0x00 + (type<<4) + plan;
562  p[3] = 0x80 + (present<<5) + screen;
563  if (number) if (number[0])
564  strncpy((char *)p+4, (char *)number, strlen((char *)number));
565  } else
566  {
567  p[2] = 0x80 + (type<<4) + plan;
568  if (number) if (number[0])
569  strncpy((char *)p+3, (char *)number, strlen((char *)number));
570  }
571 }
572 
573 static void dec_ie_connected_pn(unsigned char *p, Q931_info_t *qi, int *type, int *plan, int *present, int *screen, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
574 {
575  *type = -1;
576  *plan = -1;
577  *present = -1;
578  *screen = -1;
579  *number = '\0';
580 
581  if (!nt)
582  {
583  p = NULL;
584  if (qi->QI_ELEMENT(connected_nr))
585  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(connected_nr) + 1;
586  }
587  if (!p)
588  return;
589  if (p[0] < 1)
590  {
591  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
592  return;
593  }
594 
595  *type = (p[1]&0x70) >> 4;
596  *plan = p[1] & 0xf;
597  if (!(p[1] & 0x80))
598  {
599  if (p[0] < 2)
600  {
601  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
602  return;
603  }
604  *present = (p[2]&0x60) >> 5;
605  *screen = p[2] & 0x3;
606  strnncpy(number, (char *)p+3, p[0]-2, number_len);
607  } else
608  {
609  strnncpy(number, (char *)p+2, p[0]-1, number_len);
610  }
611 
612  if (MISDN_IE_DEBG) printf(" type=%d plan=%d present=%d screen=%d number='%s'\n", *type, *plan, *present, *screen, number);
613 }
614 
615 
616 /* IE_CAUSE */
617 static void enc_ie_cause(unsigned char **ntmode, msg_t *msg, int location, int cause, int nt, struct misdn_bchannel *bc)
618 {
619  unsigned char *p;
620  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
621  int l;
622 
623  if (location<0 || location>7)
624  {
625  printf("%s: ERROR: location(%d) is out of range.\n", __FUNCTION__, location);
626  return;
627  }
628  if (cause<0 || cause>127)
629  {
630  printf("%s: ERROR: cause(%d) is out of range.\n", __FUNCTION__, cause);
631  return;
632  }
633 
634  if (MISDN_IE_DEBG) printf(" location=%d cause=%d\n", location, cause);
635 
636  l = 2;
637  p = msg_put(msg, l+2);
638  if (nt)
639  *ntmode = p+1;
640  else
641  qi->QI_ELEMENT(cause) = p - (unsigned char *)qi - sizeof(Q931_info_t);
642  p[0] = IE_CAUSE;
643  p[1] = l;
644  p[2] = 0x80 + location;
645  p[3] = 0x80 + cause;
646 }
647 
648 #if 0
649 static void enc_ie_cause_standalone(unsigned char **ntmode, msg_t *msg, int location, int cause, int nt, struct misdn_bchannel *bc)
650 {
651  unsigned char *p = msg_put(msg, 4);
652  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
653  if (ntmode)
654  *ntmode = p+1;
655  else
656  qi->QI_ELEMENT(cause) = p - (unsigned char *)qi - sizeof(Q931_info_t);
657  p[0] = IE_CAUSE;
658  p[1] = 2;
659  p[2] = 0x80 + location;
660  p[3] = 0x80 + cause;
661 }
662 #endif
663 
664 static void dec_ie_cause(unsigned char *p, Q931_info_t *qi, int *location, int *cause, int nt, struct misdn_bchannel *bc)
665 {
666  *location = -1;
667  *cause = -1;
668 
669  if (!nt)
670  {
671  p = NULL;
672  if (qi->QI_ELEMENT(cause))
673  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(cause) + 1;
674  }
675  if (!p)
676  return;
677  if (p[0] < 2)
678  {
679  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
680  return;
681  }
682 
683  *location = p[1] & 0x0f;
684  *cause = p[2] & 0x7f;
685 
686  if (MISDN_IE_DEBG) printf(" location=%d cause=%d\n", *location, *cause);
687 }
688 
689 
690 /* IE_CHANNEL_ID */
691 static void enc_ie_channel_id(unsigned char **ntmode, msg_t *msg, int exclusive, int channel, int nt, struct misdn_bchannel *bc)
692 {
693  unsigned char *p;
694  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
695  int l;
696  struct misdn_stack *stack=get_stack_by_bc(bc);
697  int pri = stack->pri;
698 
699  if (exclusive<0 || exclusive>1)
700  {
701  printf("%s: ERROR: exclusive(%d) is out of range.\n", __FUNCTION__, exclusive);
702  return;
703  }
704  if ((channel<0 || channel>0xff)
705  || (!pri && (channel>2 && channel<0xff))
706  || (pri && (channel>31 && channel<0xff))
707  || (pri && channel==16))
708  {
709  printf("%s: ERROR: channel(%d) is out of range.\n", __FUNCTION__, channel);
710  return;
711  }
712 
713  /* if (MISDN_IE_DEBG) printf(" exclusive=%d channel=%d\n", exclusive, channel); */
714 
715 
716  if (!pri)
717  {
718  /* BRI */
719  l = 1;
720  p = msg_put(msg, l+2);
721  if (nt)
722  *ntmode = p+1;
723  else
724  qi->QI_ELEMENT(channel_id) = p - (unsigned char *)qi - sizeof(Q931_info_t);
725  p[0] = IE_CHANNEL_ID;
726  p[1] = l;
727  if (channel == 0xff)
728  channel = 3;
729  p[2] = 0x80 + (exclusive<<3) + channel;
730  /* printf(" exclusive=%d channel=%d\n", exclusive, channel); */
731  } else
732  {
733  /* PRI */
734  if (channel == 0) /* no channel */
735  return; /* IE not present */
736 /* if (MISDN_IE_DEBG) printf("channel = %d\n", channel); */
737  if (channel == 0xff) /* any channel */
738  {
739  l = 1;
740  p = msg_put(msg, l+2);
741  if (nt)
742  *ntmode = p+1;
743  else
744  qi->QI_ELEMENT(channel_id) = p - (unsigned char *)qi - sizeof(Q931_info_t);
745  p[0] = IE_CHANNEL_ID;
746  p[1] = l;
747  p[2] = 0x80 + 0x20 + 0x03;
748 /* if (MISDN_IE_DEBG) printf("%02hhx\n", p[2]); */
749  return; /* end */
750  }
751  l = 3;
752  p = msg_put(msg, l+2);
753  if (nt)
754  *ntmode = p+1;
755  else
756  qi->QI_ELEMENT(channel_id) = p - (unsigned char *)qi - sizeof(Q931_info_t);
757  p[0] = IE_CHANNEL_ID;
758  p[1] = l;
759  p[2] = 0x80 + 0x20 + (exclusive<<3) + 0x01;
760  p[3] = 0x80 + 3; /* CCITT, Number, B-type */
761  p[4] = 0x80 + channel;
762 /* if (MISDN_IE_DEBG) printf("%02hhx %02hhx %02hhx\n", p[2], p[3], p[4]); */
763  }
764 }
765 
766 static void dec_ie_channel_id(unsigned char *p, Q931_info_t *qi, int *exclusive, int *channel, int nt, struct misdn_bchannel *bc)
767 {
768  struct misdn_stack *stack=get_stack_by_bc(bc);
769  int pri =stack->pri;
770 
771  *exclusive = -1;
772  *channel = -1;
773 
774  if (!nt)
775  {
776  p = NULL;
777  if (qi->QI_ELEMENT(channel_id))
778  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(channel_id) + 1;
779  }
780  if (!p)
781  return;
782  if (p[0] < 1)
783  {
784  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
785  return;
786  }
787 
788  if (p[1] & 0x40)
789  {
790  printf("%s: ERROR: refering to channels of other interfaces is not supported.\n", __FUNCTION__);
791  return;
792  }
793  if (p[1] & 0x04)
794  {
795  printf("%s: ERROR: using d-channel is not supported.\n", __FUNCTION__);
796  return;
797  }
798 
799  *exclusive = (p[1]&0x08) >> 3;
800  if (!pri)
801  {
802  /* BRI */
803  if (p[1] & 0x20)
804  {
805  printf("%s: ERROR: extended channel ID with non PRI interface.\n", __FUNCTION__);
806  return;
807  }
808  *channel = p[1] & 0x03;
809  if (*channel == 3)
810  *channel = 0xff;
811  } else
812  {
813  /* PRI */
814  if (p[0] < 1)
815  {
816  printf("%s: ERROR: IE too short for PRI (%d).\n", __FUNCTION__, p[0]);
817  return;
818  }
819  if (!(p[1] & 0x20))
820  {
821  printf("%s: ERROR: basic channel ID with PRI interface.\n", __FUNCTION__);
822  return;
823  }
824  if ((p[1]&0x03) == 0x00)
825  {
826  /* no channel */
827  *channel = 0;
828  return;
829  }
830  if ((p[1]&0x03) == 0x03)
831  {
832  /* any channel */
833  *channel = 0xff;
834  return;
835  }
836  if (p[0] < 3)
837  {
838  printf("%s: ERROR: IE too short for PRI with channel(%d).\n", __FUNCTION__, p[0]);
839  return;
840  }
841  if (p[2] & 0x10)
842  {
843  printf("%s: ERROR: channel map not supported.\n", __FUNCTION__);
844  return;
845  }
846  *channel = p[3] & 0x7f;
847  if ( (*channel<1) | (*channel==16) | (*channel>31))
848  {
849  printf("%s: ERROR: PRI interface channel out of range (%d).\n", __FUNCTION__, *channel);
850  return;
851  }
852 /* if (MISDN_IE_DEBG) printf("%02hhx %02hhx %02hhx\n", p[1], p[2], p[3]); */
853  }
854 
855  if (MISDN_IE_DEBG) printf(" exclusive=%d channel=%d\n", *exclusive, *channel);
856 }
857 
858 
859 /* IE_DATE */
860 static void enc_ie_date(unsigned char **ntmode, msg_t *msg, time_t ti, int nt, struct misdn_bchannel *bc)
861 {
862  unsigned char *p;
863  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
864  int l;
865  struct timeval tv = { ti, 0 };
866  struct ast_tm tm;
867 
868  ast_localtime(&tv, &tm, NULL);
869  if (MISDN_IE_DEBG) printf(" year=%d month=%d day=%d hour=%d minute=%d\n", tm.tm_year%100, tm.tm_mon+1, tm.tm_mday, tm.tm_hour, tm.tm_min);
870 
871  l = 5;
872  p = msg_put(msg, l+2);
873  if (nt)
874  *ntmode = p+1;
875  else
876  qi->QI_ELEMENT(date) = p - (unsigned char *)qi - sizeof(Q931_info_t);
877  p[0] = IE_DATE;
878  p[1] = l;
879  p[2] = tm.tm_year % 100;
880  p[3] = tm.tm_mon + 1;
881  p[4] = tm.tm_mday;
882  p[5] = tm.tm_hour;
883  p[6] = tm.tm_min;
884 }
885 
886 
887 /* IE_DISPLAY */
888 static void enc_ie_display(unsigned char **ntmode, msg_t *msg, char *display, int nt, struct misdn_bchannel *bc)
889 {
890  unsigned char *p;
891  Q931_info_t *qi = (Q931_info_t *) (msg->data + mISDN_HEADER_LEN);
892  int l;
893 
894  if (!display[0])
895  {
896  printf("%s: ERROR: display text not given.\n", __FUNCTION__);
897  return;
898  }
899 
900  l = strlen(display);
901  if (80 < l)
902  {
903  l = 80;
904  printf("%s: WARNING: display text too long (max %d chars), cutting.\n", __FUNCTION__, l);
905  display[l] = '\0';
906  }
907 
908  /* if (MISDN_IE_DEBG) printf(" display='%s' (len=%d)\n", display, l); */
909 
910  p = msg_put(msg, l + 2);
911  if (nt)
912  *ntmode = p + 1;
913  else
914  qi->QI_ELEMENT(display) = p - (unsigned char *) qi - sizeof(Q931_info_t);
915  p[0] = IE_DISPLAY;
916  p[1] = l;
917  strncpy((char *) p + 2, display, l);
918 }
919 
920 #if 0
921 static void dec_ie_display(unsigned char *p, Q931_info_t *qi, char *display, size_t display_len, int nt, struct misdn_bchannel *bc)
922 {
923  *display = '\0';
924 
925  if (!nt)
926  {
927  p = NULL;
928  if (qi->QI_ELEMENT(display))
929  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(display) + 1;
930  }
931  if (!p)
932  return;
933  if (p[0] < 1)
934  {
935  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
936  return;
937  }
938 
939  strnncpy(display, (char *)p+1, p[0], display_len);
940 
941  if (MISDN_IE_DEBG) printf(" display='%s'\n", display);
942 }
943 #endif
944 
945 /* IE_KEYPAD */
946 #if 1
947 static void enc_ie_keypad(unsigned char **ntmode, msg_t *msg, char *keypad, int nt, struct misdn_bchannel *bc)
948 {
949  unsigned char *p;
950  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
951  int l;
952 
953  if (!keypad[0])
954  {
955  printf("%s: ERROR: keypad info not given.\n", __FUNCTION__);
956  return;
957  }
958 
959  if (MISDN_IE_DEBG) printf(" keypad='%s'\n", keypad);
960 
961  l = strlen(keypad);
962  p = msg_put(msg, l+2);
963  if (nt)
964  *ntmode = p+1;
965  else
966  qi->QI_ELEMENT(keypad) = p - (unsigned char *)qi - sizeof(Q931_info_t);
967  p[0] = IE_KEYPAD;
968  p[1] = l;
969  strncpy((char *)p+2, keypad, strlen(keypad));
970 }
971 #endif
972 
973 static void dec_ie_keypad(unsigned char *p, Q931_info_t *qi, char *keypad, size_t keypad_len, int nt, struct misdn_bchannel *bc)
974 {
975  *keypad = '\0';
976 
977  if (!nt)
978  {
979  p = NULL;
980  if (qi->QI_ELEMENT(keypad))
981  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(keypad) + 1;
982  }
983  if (!p)
984  return;
985  if (p[0] < 1)
986  {
987  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
988  return;
989  }
990 
991  strnncpy(keypad, (char *)p+1, p[0], keypad_len);
992 
993  if (MISDN_IE_DEBG) printf(" keypad='%s'\n", keypad);
994 }
995 
996 
997 /* IE_NOTIFY */
998 static void enc_ie_notify(unsigned char **ntmode, msg_t *msg, int notify, int nt, struct misdn_bchannel *bc)
999 {
1000  unsigned char *p;
1001  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
1002  int l;
1003 
1004  if (notify<0 || notify>0x7f)
1005  {
1006  printf("%s: ERROR: notify(%d) is out of range.\n", __FUNCTION__, notify);
1007  return;
1008  }
1009 
1010  if (MISDN_IE_DEBG) printf(" notify=%d\n", notify);
1011 
1012  l = 1;
1013  p = msg_put(msg, l+2);
1014  if (nt)
1015  *ntmode = p+1;
1016  else
1017  qi->QI_ELEMENT(notify) = p - (unsigned char *)qi - sizeof(Q931_info_t);
1018  p[0] = IE_NOTIFY;
1019  p[1] = l;
1020  p[2] = 0x80 + notify;
1021 }
1022 
1023 static void dec_ie_notify(unsigned char *p, Q931_info_t *qi, int *notify, int nt, struct misdn_bchannel *bc)
1024 {
1025  *notify = -1;
1026 
1027  if (!nt)
1028  {
1029  p = NULL;
1030  if (qi->QI_ELEMENT(notify))
1031  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(notify) + 1;
1032  }
1033  if (!p)
1034  return;
1035  if (p[0] < 1)
1036  {
1037  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
1038  return;
1039  }
1040 
1041  *notify = p[1] & 0x7f;
1042 
1043  if (MISDN_IE_DEBG) printf(" notify=%d\n", *notify);
1044 }
1045 
1046 
1047 /* IE_PROGRESS */
1048 static void enc_ie_progress(unsigned char **ntmode, msg_t *msg, int coding, int location, int progress, int nt, struct misdn_bchannel *bc)
1049 {
1050  unsigned char *p;
1051  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
1052  int l;
1053 
1054  if (coding<0 || coding>0x03)
1055  {
1056  printf("%s: ERROR: coding(%d) is out of range.\n", __FUNCTION__, coding);
1057  return;
1058  }
1059  if (location<0 || location>0x0f)
1060  {
1061  printf("%s: ERROR: location(%d) is out of range.\n", __FUNCTION__, location);
1062  return;
1063  }
1064  if (progress<0 || progress>0x7f)
1065  {
1066  printf("%s: ERROR: progress(%d) is out of range.\n", __FUNCTION__, progress);
1067  return;
1068  }
1069 
1070  if (MISDN_IE_DEBG) printf(" coding=%d location=%d progress=%d\n", coding, location, progress);
1071 
1072  l = 2;
1073  p = msg_put(msg, l+2);
1074  if (nt)
1075  *ntmode = p+1;
1076  else
1077  qi->QI_ELEMENT(progress) = p - (unsigned char *)qi - sizeof(Q931_info_t);
1078  p[0] = IE_PROGRESS;
1079  p[1] = l;
1080  p[2] = 0x80 + (coding<<5) + location;
1081  p[3] = 0x80 + progress;
1082 }
1083 
1084 static void dec_ie_progress(unsigned char *p, Q931_info_t *qi, int *coding, int *location, int *progress, int nt, struct misdn_bchannel *bc)
1085 {
1086  *coding = -1;
1087  *location = -1;
1088  //*progress = -1;
1089  *progress = 0;
1090 
1091  if (!nt)
1092  {
1093  p = NULL;
1094  if (qi->QI_ELEMENT(progress))
1095  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(progress) + 1;
1096  }
1097  if (!p)
1098  return;
1099  if (p[0] < 1)
1100  {
1101  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
1102  return;
1103  }
1104 
1105  *coding = (p[1]&0x60) >> 5;
1106  *location = p[1] & 0x0f;
1107  *progress = p[2] & 0x7f;
1108 
1109  if (MISDN_IE_DEBG) printf(" coding=%d location=%d progress=%d\n", *coding, *location, *progress);
1110 }
1111 
1112 
1113 /* IE_REDIR_NR (redirecting = during MT_SETUP) */
1114 static void enc_ie_redir_nr(unsigned char **ntmode, msg_t *msg, int type, int plan, int present, int screen, int reason, char *number, int nt, struct misdn_bchannel *bc)
1115 {
1116  unsigned char *p;
1117  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
1118  int l;
1119 
1120  if (type<0 || type>7)
1121  {
1122  printf("%s: ERROR: type(%d) is out of range.\n", __FUNCTION__, type);
1123  return;
1124  }
1125  if (plan<0 || plan>15)
1126  {
1127  printf("%s: ERROR: plan(%d) is out of range.\n", __FUNCTION__, plan);
1128  return;
1129  }
1130  if (present > 3)
1131  {
1132  printf("%s: ERROR: present(%d) is out of range.\n", __FUNCTION__, present);
1133  return;
1134  }
1135  if (present >= 0) if (screen<0 || screen>3)
1136  {
1137  printf("%s: ERROR: screen(%d) is out of range.\n", __FUNCTION__, screen);
1138  return;
1139  }
1140  if (reason > 0x0f)
1141  {
1142  printf("%s: ERROR: reason(%d) is out of range.\n", __FUNCTION__, reason);
1143  return;
1144  }
1145 
1146  if (MISDN_IE_DEBG) printf(" type=%d plan=%d present=%d screen=%d readon=%d number='%s'\n", type, plan, present, screen, reason, number);
1147 
1148  l = 1;
1149  if (number)
1150  l += strlen((char *)number);
1151  if (present >= 0)
1152  {
1153  l += 1;
1154  if (reason >= 0)
1155  l += 1;
1156  }
1157  p = msg_put(msg, l+2);
1158  if (nt)
1159  *ntmode = p+1;
1160  else
1161  qi->QI_ELEMENT(redirect_nr) = p - (unsigned char *)qi - sizeof(Q931_info_t);
1162  p[0] = IE_REDIR_NR;
1163  p[1] = l;
1164  if (present >= 0)
1165  {
1166  if (reason >= 0)
1167  {
1168  p[2] = 0x00 + (type<<4) + plan;
1169  p[3] = 0x00 + (present<<5) + screen;
1170  p[4] = 0x80 + reason;
1171  if (number)
1172  strncpy((char *)p+5, (char *)number, strlen((char *)number));
1173  } else
1174  {
1175  p[2] = 0x00 + (type<<4) + plan;
1176  p[3] = 0x80 + (present<<5) + screen;
1177  if (number)
1178  strncpy((char *)p+4, (char *)number, strlen((char *)number));
1179  }
1180  } else
1181  {
1182  p[2] = 0x80 + (type<<4) + plan;
1183  if (number) if (number[0])
1184  strncpy((char *)p+3, (char *)number, strlen((char *)number));
1185  }
1186 }
1187 
1188 static void dec_ie_redir_nr(unsigned char *p, Q931_info_t *qi, int *type, int *plan, int *present, int *screen, int *reason, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
1189 {
1190  *type = -1;
1191  *plan = -1;
1192  *present = -1;
1193  *screen = -1;
1194  *reason = -1;
1195  *number = '\0';
1196 
1197  if (!nt)
1198  {
1199  p = NULL;
1200  if (qi->QI_ELEMENT(redirect_nr))
1201  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(redirect_nr) + 1;
1202  }
1203  if (!p)
1204  return;
1205  if (p[0] < 1)
1206  {
1207  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
1208  return;
1209  }
1210 
1211  *type = (p[1]&0x70) >> 4;
1212  *plan = p[1] & 0xf;
1213  if (!(p[1] & 0x80))
1214  {
1215  *present = (p[2]&0x60) >> 5;
1216  *screen = p[2] & 0x3;
1217  if (!(p[2] & 0x80))
1218  {
1219  *reason = p[3] & 0x0f;
1220  strnncpy(number, (char *)p+4, p[0]-3, number_len);
1221  } else
1222  {
1223  strnncpy(number, (char *)p+3, p[0]-2, number_len);
1224  }
1225  } else
1226  {
1227  strnncpy(number, (char *)p+2, p[0]-1, number_len);
1228  }
1229 
1230  if (MISDN_IE_DEBG) printf(" type=%d plan=%d present=%d screen=%d reason=%d number='%s'\n", *type, *plan, *present, *screen, *reason, number);
1231 }
1232 
1233 
1234 /* IE_REDIR_DN (redirection = during MT_NOTIFY) */
1235 static void enc_ie_redir_dn(unsigned char **ntmode, msg_t *msg, int type, int plan, int present, char *number, int nt, struct misdn_bchannel *bc)
1236 {
1237  unsigned char *p;
1238  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
1239  int l;
1240 
1241  if (type<0 || type>7)
1242  {
1243  printf("%s: ERROR: type(%d) is out of range.\n", __FUNCTION__, type);
1244  return;
1245  }
1246  if (plan<0 || plan>15)
1247  {
1248  printf("%s: ERROR: plan(%d) is out of range.\n", __FUNCTION__, plan);
1249  return;
1250  }
1251  if (present > 3)
1252  {
1253  printf("%s: ERROR: present(%d) is out of range.\n", __FUNCTION__, present);
1254  return;
1255  }
1256 
1257  if (MISDN_IE_DEBG) printf(" type=%d plan=%d present=%d number='%s'\n", type, plan, present, number);
1258 
1259  l = 1;
1260  if (number)
1261  l += strlen((char *)number);
1262  if (present >= 0)
1263  l += 1;
1264  p = msg_put(msg, l+2);
1265  if (nt)
1266  *ntmode = p+1;
1267  else {
1268  qi->QI_ELEMENT(redirect_dn) = p - (unsigned char *)qi - sizeof(Q931_info_t);
1269  }
1270  p[0] = IE_REDIR_DN;
1271  p[1] = l;
1272  if (present >= 0)
1273  {
1274  p[2] = 0x00 + (type<<4) + plan;
1275  p[3] = 0x80 + (present<<5);
1276  if (number)
1277  strncpy((char *)p+4, (char *)number, strlen((char *)number));
1278  } else
1279  {
1280  p[2] = 0x80 + (type<<4) + plan;
1281  if (number)
1282  strncpy((char *)p+3, (char *)number, strlen((char *)number));
1283  }
1284 }
1285 
1286 static void dec_ie_redir_dn(unsigned char *p, Q931_info_t *qi, int *type, int *plan, int *present, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
1287 {
1288  *type = -1;
1289  *plan = -1;
1290  *present = -1;
1291  *number = '\0';
1292 
1293  if (!nt)
1294  {
1295  p = NULL;
1296  if (qi->QI_ELEMENT(redirect_dn))
1297  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(redirect_dn) + 1;
1298  }
1299  if (!p)
1300  return;
1301  if (p[0] < 1)
1302  {
1303  printf("%s: ERROR: IE too short (%d).\n", __FUNCTION__, p[0]);
1304  return;
1305  }
1306 
1307  *type = (p[1]&0x70) >> 4;
1308  *plan = p[1] & 0xf;
1309  if (!(p[1] & 0x80))
1310  {
1311  *present = (p[2]&0x60) >> 5;
1312  strnncpy(number, (char *)p+3, p[0]-2, number_len);
1313  } else
1314  {
1315  strnncpy(number, (char *)p+2, p[0]-1, number_len);
1316  }
1317 
1318  if (MISDN_IE_DEBG) printf(" type=%d plan=%d present=%d number='%s'\n", *type, *plan, *present, number);
1319 }
1320 
1321 
1322 /* IE_USERUSER */
1323 #if 1
1324 static void enc_ie_useruser(unsigned char **ntmode, msg_t *msg, int protocol, char *user, int user_len, int nt, struct misdn_bchannel *bc)
1325 {
1326  unsigned char *p;
1327  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
1328  int l;
1329 
1330  if (protocol<0 || protocol>127)
1331  {
1332  printf("%s: ERROR: protocol(%d) is out of range.\n", __FUNCTION__, protocol);
1333  return;
1334  }
1335  if (!user || user_len<=0)
1336  {
1337  return;
1338  }
1339 
1340  if (MISDN_IE_DEBG) {
1341  size_t i;
1342  char debug[768];
1343 
1344  for (i = 0; i < user_len; ++i) {
1345  sprintf(debug + (i * 3), " %02hhx", (unsigned char)user[i]);
1346  }
1347  debug[i * 3] = 0;
1348  printf(" protocol=%d user-user%s\n", protocol, debug);
1349  }
1350 
1351  l = user_len+1;
1352  p = msg_put(msg, l+3);
1353  if (nt)
1354  *ntmode = p+1;
1355  else
1356  qi->QI_ELEMENT(useruser) = p - (unsigned char *)qi - sizeof(Q931_info_t);
1357  p[0] = IE_USER_USER;
1358  p[1] = l;
1359  p[2] = protocol;
1360  memcpy(p+3, user, user_len);
1361 }
1362 #endif
1363 
1364 #if 1
1365 static void dec_ie_useruser(unsigned char *p, Q931_info_t *qi, int *protocol, char *user, int *user_len, int nt, struct misdn_bchannel *bc)
1366 {
1367  *user_len = 0;
1368  *protocol = -1;
1369 
1370  if (!nt)
1371  {
1372  p = NULL;
1373  if (qi->QI_ELEMENT(useruser))
1374  p = (unsigned char *)qi + sizeof(Q931_info_t) + qi->QI_ELEMENT(useruser) + 1;
1375  }
1376  if (!p)
1377  return;
1378 
1379  *user_len = p[0]-1;
1380  if (p[0] < 1)
1381  return;
1382  *protocol = p[1];
1383  memcpy(user, p+2, (*user_len<=128)?*(user_len):128); /* clip to 128 maximum */
1384 
1385  if (MISDN_IE_DEBG) {
1386  int i;
1387  char debug[768];
1388 
1389  for (i = 0; i < *user_len; ++i) {
1390  sprintf(debug + (i * 3), " %02hhx", (unsigned char)user[i]);
1391  }
1392  debug[i * 3] = 0;
1393  printf(" protocol=%d user-user%s\n", *protocol, debug);
1394  }
1395 }
1396 #endif
1397 
1398 /* IE_DISPLAY */
1399 static void enc_ie_restart_ind(unsigned char **ntmode, msg_t *msg, unsigned char rind, int nt, struct misdn_bchannel *bc)
1400 {
1401  unsigned char *p;
1402  Q931_info_t *qi = (Q931_info_t *)(msg->data + mISDN_HEADER_LEN);
1403  /* if (MISDN_IE_DEBG) printf(" display='%s' (len=%d)\n", display, strlen((char *)display)); */
1404 
1405  p = msg_put(msg, 3);
1406  if (nt)
1407  *ntmode = p+1;
1408  else
1409  qi->QI_ELEMENT(restart_ind) = p - (unsigned char *)qi - sizeof(Q931_info_t);
1410  p[0] = IE_RESTART_IND;
1411  p[1] = 1;
1412  p[2] = rind;
1413 
1414 }
static void enc_ie_useruser(unsigned char **ntmode, msg_t *msg, int protocol, char *user, int user_len, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1324
static const char type[]
Definition: chan_ooh323.c:109
static void enc_ie_notify(unsigned char **ntmode, msg_t *msg, int notify, int nt, struct misdn_bchannel *bc)
Definition: ie.c:998
static void enc_ie_calling_pn(unsigned char **ntmode, msg_t *msg, int type, int plan, int present, int screen, char *number, int nt, struct misdn_bchannel *bc)
Definition: ie.c:416
Asterisk main include file. File version handling, generic pbx functions.
static void dec_ie_calling_pn(unsigned char *p, Q931_info_t *qi, int *type, int *plan, int *present, int *screen, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
Definition: ie.c:471
#define bc
static void dec_ie_keypad(unsigned char *p, Q931_info_t *qi, char *keypad, size_t keypad_len, int nt, struct misdn_bchannel *bc)
Definition: ie.c:973
static void dec_ie_complete(unsigned char *p, Q931_info_t *qi, int *complete, int nt, struct misdn_bchannel *bc)
Definition: ie.c:83
static int debug
Global debug status.
Definition: res_xmpp.c:435
static void enc_ie_connected_pn(unsigned char **ntmode, msg_t *msg, int type, int plan, int present, int screen, char *number, int nt, struct misdn_bchannel *bc)
Definition: ie.c:518
static void enc_ie_restart_ind(unsigned char **ntmode, msg_t *msg, unsigned char rind, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1399
#define MISDN_IE_DEBG
Definition: ie.c:43
struct ast_tm * ast_localtime(const struct timeval *timep, struct ast_tm *p_tm, const char *zone)
Timezone-independent version of localtime_r(3).
Definition: localtime.c:1739
B channel control structure.
Definition: isdn_lib.h:324
Definition: muted.c:95
#define NULL
Definition: resample.c:96
Definition: dsp.c:117
static void enc_ie_called_pn(unsigned char **ntmode, msg_t *msg, int type, int plan, char *number, int nt, struct misdn_bchannel *bc)
Definition: ie.c:351
int tm_year
Definition: localtime.h:41
static void enc_ie_channel_id(unsigned char **ntmode, msg_t *msg, int exclusive, int channel, int nt, struct misdn_bchannel *bc)
Definition: ie.c:691
static void enc_ie_keypad(unsigned char **ntmode, msg_t *msg, char *keypad, int nt, struct misdn_bchannel *bc)
Definition: ie.c:947
int done
Definition: test_amihooks.c:48
int pri
TRUE if ISDN-PRI (ISDN-BRI otherwise)
Number structure.
Definition: app_followme.c:154
Custom localtime functions for multiple timezones.
static void dec_ie_bearer(unsigned char *p, Q931_info_t *qi, int *coding, int *capability, int *mode, int *rate, int *multi, int *user, int *async, int *urate, int *stopbits, int *dbits, int *parity, int nt, struct misdn_bchannel *bc)
Definition: ie.c:160
static void dec_ie_progress(unsigned char *p, Q931_info_t *qi, int *coding, int *location, int *progress, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1084
static void strnncpy(char *dest, const char *src, size_t len, size_t dst_len)
Definition: ie.c:46
static void enc_ie_redir_dn(unsigned char **ntmode, msg_t *msg, int type, int plan, int present, char *number, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1235
static void dec_ie_called_pn(unsigned char *p, Q931_info_t *qi, int *type, int *plan, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
Definition: ie.c:387
int tm_mon
Definition: localtime.h:40
static void dec_ie_useruser(unsigned char *p, Q931_info_t *qi, int *protocol, char *user, int *user_len, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1365
int tm_mday
Definition: localtime.h:39
static void dec_ie_connected_pn(unsigned char *p, Q931_info_t *qi, int *type, int *plan, int *present, int *screen, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
Definition: ie.c:573
struct misdn_stack * get_stack_by_bc(struct misdn_bchannel *bc)
Definition: isdn_lib.c:152
static void dec_ie_cause(unsigned char *p, Q931_info_t *qi, int *location, int *cause, int nt, struct misdn_bchannel *bc)
Definition: ie.c:664
static void enc_ie_redir_nr(unsigned char **ntmode, msg_t *msg, int type, int plan, int present, int screen, int reason, char *number, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1114
static void dec_ie_notify(unsigned char *p, Q931_info_t *qi, int *notify, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1023
static int len(struct ast_channel *chan, const char *cmd, char *data, char *buf, size_t buflen)
static void dec_ie_redir_nr(unsigned char *p, Q931_info_t *qi, int *type, int *plan, int *present, int *screen, int *reason, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1188
static void enc_ie_complete(unsigned char **ntmode, msg_t *msg, int complete, int nt, struct misdn_bchannel *bc)
Definition: ie.c:56
static void enc_ie_display(unsigned char **ntmode, msg_t *msg, char *display, int nt, struct misdn_bchannel *bc)
Definition: ie.c:888
int nt
TRUE if NT side of protocol (TE otherwise)
int tm_hour
Definition: localtime.h:38
structure to hold users read from users.conf
static void enc_ie_bearer(unsigned char **ntmode, msg_t *msg, int coding, int capability, int mode, int rate, int multi, int user, int nt, struct misdn_bchannel *bc)
Definition: ie.c:100
static void enc_ie_date(unsigned char **ntmode, msg_t *msg, time_t ti, int nt, struct misdn_bchannel *bc)
Definition: ie.c:860
static void dec_ie_redir_dn(unsigned char *p, Q931_info_t *qi, int *type, int *plan, int *present, char *number, size_t number_len, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1286
static void enc_ie_cause(unsigned char **ntmode, msg_t *msg, int location, int cause, int nt, struct misdn_bchannel *bc)
Definition: ie.c:617
static void enc_ie_progress(unsigned char **ntmode, msg_t *msg, int coding, int location, int progress, int nt, struct misdn_bchannel *bc)
Definition: ie.c:1048
static void dec_ie_channel_id(unsigned char *p, Q931_info_t *qi, int *exclusive, int *channel, int nt, struct misdn_bchannel *bc)
Definition: ie.c:766
int tm_min
Definition: localtime.h:37