12 #define DBG_MAGIC (0x47114711L)
14 static void DI_register (void *arg);
15 static void DI_deregister (pDbgHandle hDbg);
16 static void DI_format (int do_lock, word id, int type, char *format, va_list ap);
17 static void DI_format_locked (word id, int type, char *format, va_list argument_list);
18 static void DI_format_old (word id, char *format, va_list ap) { }
19 static void DiProcessEventLog (word id, dword msgID, va_list ap) { }
20 static void single_p (byte * P, word * PLength, byte Id);
21 static void diva_maint_xdi_cb (ENTITY* e);
22 static word SuperTraceCreateReadReq (byte* P, const char* path);
23 void diva_mnt_internal_dprintf (dword drv_id, dword type, char* p, ...);
25 static dword MaxDumpSize = 256 ;
26 static dword MaxXlogSize = 2 + 128 ;
28 typedef struct _diva_maint_client {
39 diva_strace_library_interface_t* pIdiLib;
41 char xbuffer[2048+512];
44 } diva_maint_client_t;
45 static diva_maint_client_t clients[64];
47 static void diva_change_management_debug_mask (diva_maint_client_t* pC, dword old_mask);
49 static void diva_maint_error (void* user_context,
50 diva_strace_library_interface_t* hLib,
55 static void diva_maint_state_change_notify (void* user_context,
56 diva_strace_library_interface_t* hLib,
58 diva_trace_line_state_t* channel,
60 static void diva_maint_trace_notify (void* user_context,
61 diva_strace_library_interface_t* hLib,
68 typedef struct MSG_QUEUE {
69 dword Size; /* total size of queue (constant) */
70 byte *Base; /* lowest address (constant) */
71 byte *High; /* Base + Size (constant) */
72 byte *Head; /* first message in queue (if any) */
73 byte *Tail; /* first free position */
74 byte *Wrap; /* current wraparound position */
75 dword Count; /* current no of bytes in queue */
78 typedef struct MSG_HEAD {
79 volatile dword Size; /* size of data following MSG_HEAD */
80 #define MSG_INCOMPLETE 0x8000 /* ored to Size until queueCompleteMsg */
83 #define queueCompleteMsg(p) do{ ((MSG_HEAD *)p - 1)->Size &= ~MSG_INCOMPLETE; }while(0)
84 #define queueCount(q) ((q)->Count)
85 #define MSG_NEED(size) \
86 ( (sizeof(MSG_HEAD) + size + sizeof(dword) - 1) & ~(sizeof(dword) - 1) )
88 static void queueInit (MSG_QUEUE *Q, byte *Buffer, dword sizeBuffer) {
90 Q->Base = Q->Head = Q->Tail = Buffer;
91 Q->High = Buffer + sizeBuffer;
96 static byte *queueAllocMsg (MSG_QUEUE *Q, word size) {
97 /* Allocate 'size' bytes at tail of queue which will be filled later
98 * directly with callers own message header info and/or message.
99 * An 'alloced' message is marked incomplete by oring the 'Size' field
100 * with MSG_INCOMPLETE.
101 * This must be reset via queueCompleteMsg() after the message is filled.
102 * As long as a message is marked incomplete queuePeekMsg() will return
103 * a 'queue empty' condition when it reaches such a message. */
106 word need = MSG_NEED(size);
108 if (Q->Tail == Q->Head) {
109 if (Q->Wrap || need > Q->Size) {
110 return NULL; /* full */
112 goto alloc; /* empty */
115 if (Q->Tail > Q->Head) {
116 if (Q->Tail + need <= Q->High) goto alloc; /* append */
117 if (Q->Base + need > Q->Head) {
118 return NULL; /* too much */
120 /* wraparound the queue (but not the message) */
126 if (Q->Tail + need > Q->Head) {
127 return NULL; /* too much */
131 Msg = (MSG_HEAD *)Q->Tail;
133 Msg->Size = size | MSG_INCOMPLETE;
140 return ((byte*)(Msg + 1));
143 static void queueFreeMsg (MSG_QUEUE *Q) {
144 /* Free the message at head of queue */
146 word size = ((MSG_HEAD *)Q->Head)->Size & ~MSG_INCOMPLETE;
148 Q->Head += MSG_NEED(size);
152 if (Q->Head >= Q->Wrap) {
156 } else if (Q->Head >= Q->Tail) {
157 Q->Head = Q->Tail = Q->Base;
161 static byte *queuePeekMsg (MSG_QUEUE *Q, word *size) {
162 /* Show the first valid message in queue BUT DON'T free the message.
163 * After looking on the message contents it can be freed queueFreeMsg()
164 * or simply remain in message queue. */
166 MSG_HEAD *Msg = (MSG_HEAD *)Q->Head;
168 if (((byte *)Msg == Q->Tail && !Q->Wrap) ||
169 (Msg->Size & MSG_INCOMPLETE)) {
173 return ((byte *)(Msg + 1));
180 static MSG_QUEUE* dbg_queue;
181 static byte* dbg_base;
182 static int external_dbg_queue;
183 static diva_os_spin_lock_t dbg_q_lock;
184 static diva_os_spin_lock_t dbg_adapter_lock;
185 static int dbg_q_busy;
186 static volatile dword dbg_sequence;
187 static dword start_sec;
188 static dword start_usec;
192 Initialize run time queue structures.
193 base: base of the message queue
194 length: length of the message queue
195 do_init: perfor queue reset
197 return: zero on success, -1 on error
199 int diva_maint_init (byte* base, unsigned long length, int do_init) {
200 if (dbg_queue || (!base) || (length < (4096*4))) {
206 diva_os_get_time (&start_sec, &start_usec);
208 *(dword*)base = (dword)DBG_MAGIC; /* Store Magic */
209 base += sizeof(dword);
210 length -= sizeof(dword);
212 *(dword*)base = 2048; /* Extension Field Length */
213 base += sizeof(dword);
214 length -= sizeof(dword);
216 strcpy (base, "KERNEL MODE BUFFER\n");
220 *(dword*)base = 0; /* Terminate extension */
221 base += sizeof(dword);
222 length -= sizeof(dword);
224 *(void**)base = (void*)(base+sizeof(void*)); /* Store Base */
225 base += sizeof(void*);
226 length -= sizeof(void*);
228 dbg_queue = (MSG_QUEUE*)base;
229 queueInit (dbg_queue, base + sizeof(MSG_QUEUE), length - sizeof(MSG_QUEUE) - 512);
230 external_dbg_queue = 0;
233 external_dbg_queue = 1; /* memory was located on the external device */
237 if (diva_os_initialize_spin_lock (&dbg_q_lock, "dbg_init")) {
240 external_dbg_queue = 0;
244 if (diva_os_initialize_spin_lock (&dbg_adapter_lock, "dbg_init")) {
245 diva_os_destroy_spin_lock(&dbg_q_lock, "dbg_init");
248 external_dbg_queue = 0;
259 return address of internal queue or zero if queue
262 void* diva_maint_finit (void) {
263 void* ret = (void*)dbg_base;
270 diva_os_destroy_spin_lock(&dbg_q_lock, "dbg_finit");
271 diva_os_destroy_spin_lock(&dbg_adapter_lock, "dbg_finit");
274 if (external_dbg_queue) {
277 external_dbg_queue = 0;
279 for (i = 1; i < (sizeof(clients)/sizeof(clients[0])); i++) {
280 if (clients[i].pmem) {
281 diva_os_free (0, clients[i].pmem);
290 Return amount of messages in debug queue
292 dword diva_dbg_q_length (void) {
293 return (dbg_queue ? queueCount(dbg_queue) : 0);
298 Lock message queue and return the pointer to the first
301 diva_dbg_entry_head_t* diva_maint_get_message (word* size,
302 diva_os_spin_lock_magic_t* old_irql) {
303 diva_dbg_entry_head_t* pmsg = NULL;
305 diva_os_enter_spin_lock_hard (&dbg_q_lock, old_irql, "read");
307 diva_os_leave_spin_lock_hard (&dbg_q_lock, old_irql, "read_busy");
312 if (!(pmsg = (diva_dbg_entry_head_t*)queuePeekMsg (dbg_queue, size))) {
314 diva_os_leave_spin_lock_hard (&dbg_q_lock, old_irql, "read_empty");
322 acknowledge last message and unlock queue
324 void diva_maint_ack_message (int do_release,
325 diva_os_spin_lock_magic_t* old_irql) {
330 queueFreeMsg (dbg_queue);
333 diva_os_leave_spin_lock_hard (&dbg_q_lock, old_irql, "read_ack");
339 PRT COMP function used to register
340 with MAINT adapter or log in compatibility
341 mode in case older driver version is connected too
343 void diva_maint_prtComp (char *format, ...) {
350 va_start(ap, format);
353 register to new log driver functions
355 if ((format[0] == 0) && ((unsigned char)format[1] == 255)) {
356 hDbg = va_arg(ap, void *); /* ptr to DbgHandle */
363 static void DI_register (void *arg) {
364 diva_os_spin_lock_magic_t old_irql;
367 int id, free_id = -1, best_id = 0;
369 diva_os_get_time (&sec, &usec);
371 hDbg = (pDbgHandle)arg ;
373 Check for bad args, specially for the old obsolete debug handle
375 if ((hDbg == NULL) ||
376 ((hDbg->id == 0) && (((_OldDbgHandle_ *)hDbg)->id == -1)) ||
377 (hDbg->Registered != 0)) {
381 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "register");
383 for (id = 1; id < (sizeof(clients)/sizeof(clients[0])); id++) {
384 if (clients[id].hDbg == hDbg) {
386 driver already registered
388 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "register");
391 if (clients[id].hDbg) { /* slot is busy */
395 if (!strcmp (clients[id].drvName, hDbg->drvName)) {
397 This driver was already registered with this name
398 and slot is still free - reuse it
403 if (!clients[id].hDbg) { /* slot is busy */
409 diva_dbg_entry_head_t* pmsg = NULL;
415 Register new driver with id == free_id
417 clients[free_id].hDbg = hDbg;
418 clients[free_id].sec = sec;
419 clients[free_id].usec = usec;
420 strcpy (clients[free_id].drvName, hDbg->drvName);
422 clients[free_id].dbgMask = hDbg->dbgMask;
424 hDbg->dbgMask |= clients[free_id].last_dbgMask;
426 clients[free_id].last_dbgMask = 0;
429 hDbg->Registered = DBG_HANDLE_REG_NEW ;
430 hDbg->id = (byte)free_id;
431 hDbg->dbg_end = DI_deregister;
432 hDbg->dbg_prt = DI_format_locked;
433 hDbg->dbg_ev = DiProcessEventLog;
434 hDbg->dbg_irq = DI_format_locked;
435 if (hDbg->Version > 0) {
436 hDbg->dbg_old = DI_format_old;
438 hDbg->next = (pDbgHandle)DBG_MAGIC;
441 Log driver register, MAINT driver ID is '0'
443 len = sprintf (tmp, "DIMAINT - drv # %d = '%s' registered",
444 free_id, hDbg->drvName);
446 while (!(pmsg = (diva_dbg_entry_head_t*)queueAllocMsg (dbg_queue,
447 (word)(len+1+sizeof(*pmsg))))) {
448 if ((pmsg = (diva_dbg_entry_head_t*)queuePeekMsg (dbg_queue, &size))) {
449 queueFreeMsg (dbg_queue);
456 pmsg->sequence = dbg_sequence++;
457 pmsg->time_sec = sec;
458 pmsg->time_usec = usec;
459 pmsg->facility = MSG_TYPE_STRING;
461 pmsg->drv_id = 0; /* id 0 - DIMAINT */
463 pmsg->data_length = len+1;
465 memcpy (&pmsg[1], tmp, len+1);
466 queueCompleteMsg (pmsg);
467 diva_maint_wakeup_read();
471 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "register");
474 static void DI_deregister (pDbgHandle hDbg) {
475 diva_os_spin_lock_magic_t old_irql, old_irql1;
481 diva_os_get_time (&sec, &usec);
483 diva_os_enter_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "read");
484 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "read");
486 for (i = 1; i < (sizeof(clients)/sizeof(clients[0])); i++) {
487 if (clients[i].hDbg == hDbg) {
488 diva_dbg_entry_head_t* pmsg;
492 clients[i].hDbg = NULL;
496 hDbg->dbg_end = NULL;
497 hDbg->dbg_prt = NULL;
498 hDbg->dbg_irq = NULL;
499 if (hDbg->Version > 0)
500 hDbg->dbg_old = NULL;
501 hDbg->Registered = 0;
504 if (clients[i].pIdiLib) {
505 (*(clients[i].pIdiLib->DivaSTraceLibraryFinit))(clients[i].pIdiLib->hLib);
506 clients[i].pIdiLib = NULL;
508 pmem = clients[i].pmem;
509 clients[i].pmem = NULL;
513 Log driver register, MAINT driver ID is '0'
515 len = sprintf (tmp, "DIMAINT - drv # %d = '%s' de-registered",
518 while (!(pmsg = (diva_dbg_entry_head_t*)queueAllocMsg (dbg_queue,
519 (word)(len+1+sizeof(*pmsg))))) {
520 if ((pmsg = (diva_dbg_entry_head_t*)queuePeekMsg (dbg_queue, &size))) {
521 queueFreeMsg (dbg_queue);
528 pmsg->sequence = dbg_sequence++;
529 pmsg->time_sec = sec;
530 pmsg->time_usec = usec;
531 pmsg->facility = MSG_TYPE_STRING;
533 pmsg->drv_id = 0; /* id 0 - DIMAINT */
535 pmsg->data_length = len+1;
537 memcpy (&pmsg[1], tmp, len+1);
538 queueCompleteMsg (pmsg);
539 diva_maint_wakeup_read();
546 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "read_ack");
547 diva_os_leave_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "read_ack");
550 diva_os_free (0, pmem);
554 static void DI_format_locked (unsigned short id,
557 va_list argument_list) {
558 DI_format (1, id, type, format, argument_list);
561 static void DI_format (int do_lock,
566 diva_os_spin_lock_magic_t old_irql;
568 diva_dbg_entry_head_t* pmsg = NULL;
571 static char fmtBuf[MSG_FRAME_MAX_SIZE+sizeof(*pmsg)+1];
578 diva_os_get_time (&sec, &usec);
581 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "format");
589 if (!(length = va_arg(ap, unsigned long))) {
592 if (length > MaxDumpSize) {
593 length = MaxDumpSize;
595 while (!(pmsg = (diva_dbg_entry_head_t*)queueAllocMsg (dbg_queue,
596 (word)length+sizeof(*pmsg)))) {
597 if ((pmsg = (diva_dbg_entry_head_t*)queuePeekMsg (dbg_queue, &size))) {
598 queueFreeMsg (dbg_queue);
604 memcpy (&pmsg[1], format, length);
605 pmsg->sequence = dbg_sequence++;
606 pmsg->time_sec = sec;
607 pmsg->time_usec = usec;
608 pmsg->facility = MSG_TYPE_BINARY ;
609 pmsg->dli = type; /* DLI_XXX */
610 pmsg->drv_id = id; /* driver MAINT id */
612 pmsg->data_length = length;
613 queueCompleteMsg (pmsg);
619 data = va_arg(ap, char*);
620 code = (unsigned short)va_arg(ap, unsigned int);
621 length = (unsigned long) va_arg(ap, unsigned int);
623 if (length > MaxXlogSize)
624 length = MaxXlogSize;
626 while (!(pmsg = (diva_dbg_entry_head_t*)queueAllocMsg (dbg_queue,
627 (word)length+sizeof(*pmsg)+2))) {
628 if ((pmsg = (diva_dbg_entry_head_t*)queuePeekMsg (dbg_queue, &size))) {
629 queueFreeMsg (dbg_queue);
636 p[0] = (char)(code) ;
637 p[1] = (char)(code >> 8) ;
638 if (data && length) {
639 memcpy (&p[2], &data[0], length) ;
643 pmsg->sequence = dbg_sequence++;
644 pmsg->time_sec = sec;
645 pmsg->time_usec = usec;
646 pmsg->facility = MSG_TYPE_BINARY ;
647 pmsg->dli = type; /* DLI_XXX */
648 pmsg->drv_id = id; /* driver MAINT id */
650 pmsg->data_length = length;
651 queueCompleteMsg (pmsg);
672 if ((length = (unsigned long)vsprintf (&fmtBuf[0], format, ap)) > 0) {
673 length += (sizeof(*pmsg)+1);
675 while (!(pmsg = (diva_dbg_entry_head_t*)queueAllocMsg (dbg_queue,
677 if ((pmsg = (diva_dbg_entry_head_t*)queuePeekMsg (dbg_queue, &size))) {
678 queueFreeMsg (dbg_queue);
684 pmsg->sequence = dbg_sequence++;
685 pmsg->time_sec = sec;
686 pmsg->time_usec = usec;
687 pmsg->facility = MSG_TYPE_STRING;
688 pmsg->dli = type; /* DLI_XXX */
689 pmsg->drv_id = id; /* driver MAINT id */
691 pmsg->data_length = length - sizeof(*pmsg);
693 memcpy (&pmsg[1], fmtBuf, pmsg->data_length);
694 queueCompleteMsg (pmsg);
701 if (queueCount(dbg_queue)) {
702 diva_maint_wakeup_read();
706 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "format");
711 Write driver ID and driver revision to callers buffer
713 int diva_get_driver_info (dword id, byte* data, int data_length) {
714 diva_os_spin_lock_magic_t old_irql;
718 if (!data || !id || (data_length < 17) ||
719 (id >= (sizeof(clients)/sizeof(clients[0])))) {
723 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "driver info");
725 if (clients[id].hDbg) {
727 *p++ = (byte)clients[id].sec; /* save seconds */
728 *p++ = (byte)(clients[id].sec >> 8);
729 *p++ = (byte)(clients[id].sec >> 16);
730 *p++ = (byte)(clients[id].sec >> 24);
732 *p++ = (byte)(clients[id].usec/1000); /* save mseconds */
733 *p++ = (byte)((clients[id].usec/1000) >> 8);
734 *p++ = (byte)((clients[id].usec/1000) >> 16);
735 *p++ = (byte)((clients[id].usec/1000) >> 24);
739 if ((to_copy = MIN(strlen(clients[id].drvName), data_length-1))) {
740 memcpy (p, clients[id].drvName, to_copy);
742 data_length -= to_copy;
743 if ((data_length >= 4) && clients[id].hDbg->drvTag[0]) {
746 if ((to_copy = MIN(strlen(clients[id].hDbg->drvTag), data_length-2))) {
747 memcpy (p, clients[id].hDbg->drvTag, to_copy);
749 data_length -= to_copy;
750 if (data_length >= 2) {
760 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "driver info");
765 int diva_get_driver_dbg_mask (dword id, byte* data) {
766 diva_os_spin_lock_magic_t old_irql;
769 if (!data || !id || (id >= (sizeof(clients)/sizeof(clients[0])))) {
772 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "driver info");
774 if (clients[id].hDbg) {
776 *data++= (byte)(clients[id].hDbg->dbgMask);
777 *data++= (byte)(clients[id].hDbg->dbgMask >> 8);
778 *data++= (byte)(clients[id].hDbg->dbgMask >> 16);
779 *data++= (byte)(clients[id].hDbg->dbgMask >> 24);
782 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "driver info");
787 int diva_set_driver_dbg_mask (dword id, dword mask) {
788 diva_os_spin_lock_magic_t old_irql, old_irql1;
792 if (!id || (id >= (sizeof(clients)/sizeof(clients[0])))) {
796 diva_os_enter_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "dbg mask");
797 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "dbg mask");
799 if (clients[id].hDbg) {
800 dword old_mask = clients[id].hDbg->dbgMask;
802 clients[id].hDbg->dbgMask = mask;
803 clients[id].last_dbgMask = (clients[id].hDbg->dbgMask | clients[id].dbgMask);
805 diva_change_management_debug_mask (&clients[id], old_mask);
809 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "dbg mask");
811 if (clients[id].request_pending) {
812 clients[id].request_pending = 0;
813 (*(clients[id].request))((ENTITY*)(*(clients[id].pIdiLib->DivaSTraceGetHandle))(clients[id].pIdiLib->hLib));
816 diva_os_leave_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "dbg mask");
821 static int diva_get_idi_adapter_info (IDI_CALL request, dword* serial, dword* logical) {
822 IDI_SYNC_REQ sync_req;
824 sync_req.xdi_logical_adapter_number.Req = 0;
825 sync_req.xdi_logical_adapter_number.Rc = IDI_SYNC_REQ_XDI_GET_LOGICAL_ADAPTER_NUMBER;
826 (*request)((ENTITY *)&sync_req);
827 *logical = sync_req.xdi_logical_adapter_number.info.logical_adapter_number;
829 sync_req.GetSerial.Req = 0;
830 sync_req.GetSerial.Rc = IDI_SYNC_REQ_GET_SERIAL;
831 sync_req.GetSerial.serial = 0;
832 (*request)((ENTITY *)&sync_req);
833 *serial = sync_req.GetSerial.serial;
839 Register XDI adapter as MAINT compatible driver
841 void diva_mnt_add_xdi_adapter (const DESCRIPTOR* d) {
842 diva_os_spin_lock_magic_t old_irql, old_irql1;
843 dword sec, usec, logical, serial, org_mask;
844 int id, best_id = 0, free_id = -1;
846 diva_dbg_entry_head_t* pmsg = NULL;
851 diva_os_get_time (&sec, &usec);
852 diva_get_idi_adapter_info (d->request, &serial, &logical);
853 if (serial & 0xff000000) {
854 sprintf (tmp, "ADAPTER:%d SN:%d-%d",
857 (byte)(((serial & 0xff000000) >> 24) + 1));
859 sprintf (tmp, "ADAPTER:%d SN:%d", (int)logical, serial);
862 if (!(pmem = diva_os_malloc (0, DivaSTraceGetMemotyRequirement (d->channels)))) {
865 memset (pmem, 0x00, DivaSTraceGetMemotyRequirement (d->channels));
867 diva_os_enter_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "register");
868 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "register");
870 for (id = 1; id < (sizeof(clients)/sizeof(clients[0])); id++) {
871 if (clients[id].hDbg && (clients[id].request == d->request)) {
872 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "register");
873 diva_os_leave_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "register");
876 if (clients[id].hDbg) { /* slot is busy */
882 if (!strcmp (clients[id].drvName, tmp)) {
884 This driver was already registered with this name
885 and slot is still free - reuse it
894 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "register");
895 diva_os_leave_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "register");
896 diva_os_free (0, pmem);
901 clients[id].request = d->request;
902 clients[id].request_pending = 0;
903 clients[id].hDbg = &clients[id].Dbg;
904 clients[id].sec = sec;
905 clients[id].usec = usec;
906 strcpy (clients[id].drvName, tmp);
907 strcpy (clients[id].Dbg.drvName, tmp);
908 clients[id].Dbg.drvTag[0] = 0;
909 clients[id].logical = (int)logical;
910 clients[id].channels = (int)d->channels;
912 clients[id].Dbg.dbgMask = 0;
913 clients[id].dbgMask = clients[id].Dbg.dbgMask;
915 clients[id].Dbg.dbgMask |= clients[free_id].last_dbgMask;
917 clients[id].last_dbgMask = 0;
919 clients[id].Dbg.Registered = DBG_HANDLE_REG_NEW;
920 clients[id].Dbg.id = (byte)id;
921 clients[id].Dbg.dbg_end = DI_deregister;
922 clients[id].Dbg.dbg_prt = DI_format_locked;
923 clients[id].Dbg.dbg_ev = DiProcessEventLog;
924 clients[id].Dbg.dbg_irq = DI_format_locked;
925 clients[id].Dbg.next = (pDbgHandle)DBG_MAGIC;
928 diva_trace_library_user_interface_t diva_maint_user_ifc = { &clients[id],
929 diva_maint_state_change_notify,
930 diva_maint_trace_notify,
934 Attach to adapter management interface
936 if ((clients[id].pIdiLib =
937 DivaSTraceLibraryCreateInstance ((int)logical, &diva_maint_user_ifc, pmem))) {
938 if (((*(clients[id].pIdiLib->DivaSTraceLibraryStart))(clients[id].pIdiLib->hLib))) {
939 diva_mnt_internal_dprintf (0, DLI_ERR, "Adapter(%d) Start failed", (int)logical);
940 (*(clients[id].pIdiLib->DivaSTraceLibraryFinit))(clients[id].pIdiLib->hLib);
941 clients[id].pIdiLib = NULL;
944 diva_mnt_internal_dprintf (0, DLI_ERR, "A(%d) management init failed", (int)logical);
948 if (!clients[id].pIdiLib) {
949 clients[id].request = NULL;
950 clients[id].request_pending = 0;
951 clients[id].hDbg = NULL;
952 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "register");
953 diva_os_leave_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "register");
954 diva_os_free (0, pmem);
959 Log driver register, MAINT driver ID is '0'
961 len = sprintf (tmp, "DIMAINT - drv # %d = '%s' registered",
962 id, clients[id].Dbg.drvName);
964 while (!(pmsg = (diva_dbg_entry_head_t*)queueAllocMsg (dbg_queue,
965 (word)(len+1+sizeof(*pmsg))))) {
966 if ((pmsg = (diva_dbg_entry_head_t*)queuePeekMsg (dbg_queue, &size))) {
967 queueFreeMsg (dbg_queue);
974 pmsg->sequence = dbg_sequence++;
975 pmsg->time_sec = sec;
976 pmsg->time_usec = usec;
977 pmsg->facility = MSG_TYPE_STRING;
979 pmsg->drv_id = 0; /* id 0 - DIMAINT */
981 pmsg->data_length = len+1;
983 memcpy (&pmsg[1], tmp, len+1);
984 queueCompleteMsg (pmsg);
985 diva_maint_wakeup_read();
988 org_mask = clients[id].Dbg.dbgMask;
989 clients[id].Dbg.dbgMask = 0;
991 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "register");
993 if (clients[id].request_pending) {
994 clients[id].request_pending = 0;
995 (*(clients[id].request))((ENTITY*)(*(clients[id].pIdiLib->DivaSTraceGetHandle))(clients[id].pIdiLib->hLib));
998 diva_os_leave_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "register");
1000 diva_set_driver_dbg_mask (id, org_mask);
1004 De-Register XDI adapter
1006 void diva_mnt_remove_xdi_adapter (const DESCRIPTOR* d) {
1007 diva_os_spin_lock_magic_t old_irql, old_irql1;
1013 diva_os_get_time (&sec, &usec);
1015 diva_os_enter_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "read");
1016 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "read");
1018 for (i = 1; i < (sizeof(clients)/sizeof(clients[0])); i++) {
1019 if (clients[i].hDbg && (clients[i].request == d->request)) {
1020 diva_dbg_entry_head_t* pmsg;
1024 if (clients[i].pIdiLib) {
1025 (*(clients[i].pIdiLib->DivaSTraceLibraryFinit))(clients[i].pIdiLib->hLib);
1026 clients[i].pIdiLib = NULL;
1028 pmem = clients[i].pmem;
1029 clients[i].pmem = NULL;
1032 clients[i].hDbg = NULL;
1033 clients[i].request = NULL;
1034 clients[i].request_pending = 0;
1037 Log driver register, MAINT driver ID is '0'
1039 len = sprintf (tmp, "DIMAINT - drv # %d = '%s' de-registered",
1040 i, clients[i].Dbg.drvName);
1042 memset (&clients[i].Dbg, 0x00, sizeof(clients[i].Dbg));
1044 while (!(pmsg = (diva_dbg_entry_head_t*)queueAllocMsg (dbg_queue,
1045 (word)(len+1+sizeof(*pmsg))))) {
1046 if ((pmsg = (diva_dbg_entry_head_t*)queuePeekMsg (dbg_queue, &size))) {
1047 queueFreeMsg (dbg_queue);
1054 pmsg->sequence = dbg_sequence++;
1055 pmsg->time_sec = sec;
1056 pmsg->time_usec = usec;
1057 pmsg->facility = MSG_TYPE_STRING;
1058 pmsg->dli = DLI_REG;
1059 pmsg->drv_id = 0; /* id 0 - DIMAINT */
1061 pmsg->data_length = len+1;
1063 memcpy (&pmsg[1], tmp, len+1);
1064 queueCompleteMsg (pmsg);
1065 diva_maint_wakeup_read();
1072 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "read_ack");
1073 diva_os_leave_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "read_ack");
1076 diva_os_free (0, pmem);
1080 /* ----------------------------------------------------------------
1081 Low level interface for management interface client
1082 ---------------------------------------------------------------- */
1084 Return handle to client structure
1086 void* SuperTraceOpenAdapter (int AdapterNumber) {
1089 for (i = 1; i < (sizeof(clients)/sizeof(clients[0])); i++) {
1090 if (clients[i].hDbg && clients[i].request && (clients[i].logical == AdapterNumber)) {
1091 return (&clients[i]);
1098 int SuperTraceCloseAdapter (void* AdapterHandle) {
1102 int SuperTraceReadRequest (void* AdapterHandle, const char* name, byte* data) {
1103 diva_maint_client_t* pC = (diva_maint_client_t*)AdapterHandle;
1105 if (pC && pC->pIdiLib && pC->request) {
1106 ENTITY* e = (ENTITY*)(*(pC->pIdiLib->DivaSTraceGetHandle))(pC->pIdiLib->hLib);
1107 byte* xdata = (byte*)&pC->xbuffer[0];
1111 if (!strcmp(name, "\\")) { /* Read ROOT */
1114 length = SuperTraceCreateReadReq (xdata, name);
1115 single_p (xdata, &length, 0); /* End Of Message */
1119 e->X->PLength = length;
1120 e->X->P = (byte*)xdata;
1122 pC->request_pending = 1;
1130 int SuperTraceGetNumberOfChannels (void* AdapterHandle) {
1131 if (AdapterHandle) {
1132 diva_maint_client_t* pC = (diva_maint_client_t*)AdapterHandle;
1134 return (pC->channels);
1140 int SuperTraceASSIGN (void* AdapterHandle, byte* data) {
1141 diva_maint_client_t* pC = (diva_maint_client_t*)AdapterHandle;
1143 if (pC && pC->pIdiLib && pC->request) {
1144 ENTITY* e = (ENTITY*)(*(pC->pIdiLib->DivaSTraceGetHandle))(pC->pIdiLib->hLib);
1147 e->callback = diva_maint_xdi_cb;
1153 e->X->P = (byte*)&pC->xbuffer[0];
1156 pC->request_pending = 1;
1164 int SuperTraceREMOVE (void* AdapterHandle) {
1165 diva_maint_client_t* pC = (diva_maint_client_t*)AdapterHandle;
1167 if (pC && pC->pIdiLib && pC->request) {
1168 ENTITY* e = (ENTITY*)(*(pC->pIdiLib->DivaSTraceGetHandle))(pC->pIdiLib->hLib);
1175 e->X->P = (byte*)&pC->xbuffer[0];
1178 pC->request_pending = 1;
1186 int SuperTraceTraceOnRequest(void* hAdapter, const char* name, byte* data) {
1187 diva_maint_client_t* pC = (diva_maint_client_t*)hAdapter;
1189 if (pC && pC->pIdiLib && pC->request) {
1190 ENTITY* e = (ENTITY*)(*(pC->pIdiLib->DivaSTraceGetHandle))(pC->pIdiLib->hLib);
1191 byte* xdata = (byte*)&pC->xbuffer[0];
1195 if (!strcmp(name, "\\")) { /* Read ROOT */
1198 length = SuperTraceCreateReadReq (xdata, name);
1199 single_p (xdata, &length, 0); /* End Of Message */
1200 e->Req = MAN_EVENT_ON;
1202 e->X->PLength = length;
1203 e->X->P = (byte*)xdata;
1205 pC->request_pending = 1;
1213 int SuperTraceWriteVar (void* AdapterHandle,
1219 diva_maint_client_t* pC = (diva_maint_client_t*)AdapterHandle;
1221 if (pC && pC->pIdiLib && pC->request) {
1222 ENTITY* e = (ENTITY*)(*(pC->pIdiLib->DivaSTraceGetHandle))(pC->pIdiLib->hLib);
1223 diva_man_var_header_t* pVar = (diva_man_var_header_t*)&pC->xbuffer[0];
1224 word length = SuperTraceCreateReadReq ((byte*)pVar, name);
1226 memcpy (&pC->xbuffer[length], var, var_length);
1227 length += var_length;
1228 pVar->length += var_length;
1229 pVar->value_length = var_length;
1231 single_p ((byte*)pVar, &length, 0); /* End Of Message */
1235 e->X->PLength = length;
1236 e->X->P = (byte*)pVar;
1238 pC->request_pending = 1;
1246 int SuperTraceExecuteRequest (void* AdapterHandle,
1249 diva_maint_client_t* pC = (diva_maint_client_t*)AdapterHandle;
1251 if (pC && pC->pIdiLib && pC->request) {
1252 ENTITY* e = (ENTITY*)(*(pC->pIdiLib->DivaSTraceGetHandle))(pC->pIdiLib->hLib);
1253 byte* xdata = (byte*)&pC->xbuffer[0];
1256 length = SuperTraceCreateReadReq (xdata, name);
1257 single_p (xdata, &length, 0); /* End Of Message */
1259 e->Req = MAN_EXECUTE;
1261 e->X->PLength = length;
1262 e->X->P = (byte*)xdata;
1264 pC->request_pending = 1;
1272 static word SuperTraceCreateReadReq (byte* P, const char* path) {
1276 var_length = (byte)strlen (path);
1280 *P++ = 0x80; /* MAN_IE */
1281 *P++ = 0x00; /* Type */
1282 *P++ = 0x00; /* Attribute */
1283 *P++ = 0x00; /* Status */
1284 *P++ = 0x00; /* Variable Length */
1286 memcpy (P, path, var_length);
1288 *plen = var_length + 0x06;
1290 return ((word)(var_length + 0x08));
1293 static void single_p (byte * P, word * PLength, byte Id) {
1294 P[(*PLength)++] = Id;
1297 static void diva_maint_xdi_cb (ENTITY* e) {
1298 diva_strace_context_t* pLib = DIVAS_CONTAINING_RECORD(e,diva_strace_context_t,e);
1299 diva_maint_client_t* pC;
1300 diva_os_spin_lock_magic_t old_irql, old_irql1;
1303 diva_os_enter_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "xdi_cb");
1304 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "xdi_cb");
1306 pC = (diva_maint_client_t*)pLib->hAdapter;
1308 if ((*(pLib->instance.DivaSTraceMessageInput))(&pLib->instance)) {
1309 diva_mnt_internal_dprintf (0, DLI_ERR, "Trace internal library error");
1312 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "xdi_cb");
1315 if (pC->request_pending) {
1316 pC->request_pending = 0;
1317 (*(pC->request))(e);
1320 diva_os_leave_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "xdi_cb");
1324 static void diva_maint_error (void* user_context,
1325 diva_strace_library_interface_t* hLib,
1330 diva_mnt_internal_dprintf (0, DLI_ERR,
1331 "Trace library error(%d) A(%d) %s %d", error, Adapter, file, line);
1334 static void print_ie (diva_trace_ie_t* ie, char* buffer, int length) {
1340 for (i = 0; ((i < ie->length) && (length > 3)); i++) {
1341 sprintf (buffer, "%02x", ie->data[i]);
1344 if (i < (ie->length-1)) {
1345 strcpy (buffer, " ");
1353 static void diva_maint_state_change_notify (void* user_context,
1354 diva_strace_library_interface_t* hLib,
1356 diva_trace_line_state_t* channel,
1357 int notify_subject) {
1358 diva_maint_client_t* pC = (diva_maint_client_t*)user_context;
1359 diva_trace_fax_state_t* fax = &channel->fax;
1360 diva_trace_modem_state_t* modem = &channel->modem;
1367 switch (notify_subject) {
1368 case DIVA_SUPER_TRACE_NOTIFY_LINE_CHANGE:
1369 if (pC->hDbg->dbgMask & DIVA_MGT_DBG_LINE_EVENTS) {
1370 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L Ch = %d",
1371 (int)channel->ChannelNumber);
1372 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L Status = <%s>", &channel->Line[0]);
1373 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L Layer1 = <%s>", &channel->Framing[0]);
1374 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L Layer2 = <%s>", &channel->Layer2[0]);
1375 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L Layer3 = <%s>", &channel->Layer3[0]);
1376 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L RAddr = <%s>",
1377 &channel->RemoteAddress[0]);
1378 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L RSAddr = <%s>",
1379 &channel->RemoteSubAddress[0]);
1380 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L LAddr = <%s>",
1381 &channel->LocalAddress[0]);
1382 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L LSAddr = <%s>",
1383 &channel->LocalSubAddress[0]);
1384 print_ie(&channel->call_BC, tmp, sizeof(tmp));
1385 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L BC = <%s>", tmp);
1386 print_ie(&channel->call_HLC, tmp, sizeof(tmp));
1387 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L HLC = <%s>", tmp);
1388 print_ie(&channel->call_LLC, tmp, sizeof(tmp));
1389 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L LLC = <%s>", tmp);
1390 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L CR = 0x%x", channel->CallReference);
1391 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L Disc = 0x%x",
1392 channel->LastDisconnecCause);
1393 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT, "L Owner = <%s>", &channel->UserID[0]);
1397 case DIVA_SUPER_TRACE_NOTIFY_MODEM_CHANGE:
1398 if (pC->hDbg->dbgMask & DIVA_MGT_DBG_MDM_PROGRESS) {
1399 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM Ch = %lu",
1400 (int)modem->ChannelNumber);
1401 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM Event = %lu", modem->Event);
1402 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM Norm = %lu", modem->Norm);
1403 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM Opts. = 0x%08x", modem->Options);
1404 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM Tx = %lu Bps", modem->TxSpeed);
1405 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM Rx = %lu Bps", modem->RxSpeed);
1406 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM RT = %lu mSec",
1407 modem->RoundtripMsec);
1408 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM Sr = %lu", modem->SymbolRate);
1409 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM Rxl = %d dBm", modem->RxLeveldBm);
1410 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM El = %d dBm", modem->EchoLeveldBm);
1411 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM SNR = %lu dB", modem->SNRdb);
1412 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM MAE = %lu", modem->MAE);
1413 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM LRet = %lu",
1414 modem->LocalRetrains);
1415 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM RRet = %lu",
1416 modem->RemoteRetrains);
1417 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM LRes = %lu", modem->LocalResyncs);
1418 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "MDM RRes = %lu",
1419 modem->RemoteResyncs);
1420 if (modem->Event == 3) {
1421 diva_mnt_internal_dprintf(pC->hDbg->id,DLI_STAT,"MDM Disc = %lu", modem->DiscReason);
1424 if ((modem->Event == 3) && (pC->hDbg->dbgMask & DIVA_MGT_DBG_MDM_STATISTICS)) {
1425 (*(pC->pIdiLib->DivaSTraceGetModemStatistics))(pC->pIdiLib);
1429 case DIVA_SUPER_TRACE_NOTIFY_FAX_CHANGE:
1430 if (pC->hDbg->dbgMask & DIVA_MGT_DBG_FAX_PROGRESS) {
1431 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Ch = %lu",(int)fax->ChannelNumber);
1432 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Event = %lu", fax->Event);
1433 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Pages = %lu", fax->Page_Counter);
1434 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Feat. = 0x%08x", fax->Features);
1435 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX ID = <%s>", &fax->Station_ID[0]);
1436 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Saddr = <%s>", &fax->Subaddress[0]);
1437 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Pwd = <%s>", &fax->Password[0]);
1438 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Speed = %lu", fax->Speed);
1439 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Res. = 0x%08x", fax->Resolution);
1440 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Width = %lu", fax->Paper_Width);
1441 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Length= %lu", fax->Paper_Length);
1442 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX SLT = %lu", fax->Scanline_Time);
1443 if (fax->Event == 3) {
1444 diva_mnt_internal_dprintf(pC->hDbg->id, DLI_STAT, "FAX Disc = %lu", fax->Disc_Reason);
1447 if ((fax->Event == 3) && (pC->hDbg->dbgMask & DIVA_MGT_DBG_FAX_STATISTICS)) {
1448 (*(pC->pIdiLib->DivaSTraceGetFaxStatistics))(pC->pIdiLib);
1452 case DIVA_SUPER_TRACE_INTERFACE_CHANGE:
1453 if (pC->hDbg->dbgMask & DIVA_MGT_DBG_IFC_EVENTS) {
1454 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT,
1455 "Layer 1 -> [%s]", channel->pInterface->Layer1);
1456 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_STAT,
1457 "Layer 2 -> [%s]", channel->pInterface->Layer2);
1461 case DIVA_SUPER_TRACE_NOTIFY_STAT_CHANGE:
1462 if (pC->hDbg->dbgMask & DIVA_MGT_DBG_IFC_STATISTICS) {
1466 if (channel->pInterfaceStat->inc.Calls) {
1467 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1468 "Inc Calls =%lu", channel->pInterfaceStat->inc.Calls);
1470 if (channel->pInterfaceStat->inc.Connected) {
1471 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1472 "Inc Connected =%lu", channel->pInterfaceStat->inc.Connected);
1474 if (channel->pInterfaceStat->inc.User_Busy) {
1475 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1476 "Inc Busy =%lu", channel->pInterfaceStat->inc.User_Busy);
1478 if (channel->pInterfaceStat->inc.Call_Rejected) {
1479 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1480 "Inc Rejected =%lu", channel->pInterfaceStat->inc.Call_Rejected);
1482 if (channel->pInterfaceStat->inc.Wrong_Number) {
1483 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1484 "Inc Wrong Nr =%lu", channel->pInterfaceStat->inc.Wrong_Number);
1486 if (channel->pInterfaceStat->inc.Incompatible_Dst) {
1487 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1488 "Inc Incomp. Dest =%lu", channel->pInterfaceStat->inc.Incompatible_Dst);
1490 if (channel->pInterfaceStat->inc.Out_of_Order) {
1491 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1492 "Inc Out of Order =%lu", channel->pInterfaceStat->inc.Out_of_Order);
1494 if (channel->pInterfaceStat->inc.Ignored) {
1495 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1496 "Inc Ignored =%lu", channel->pInterfaceStat->inc.Ignored);
1502 if (channel->pInterfaceStat->outg.Calls) {
1503 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1504 "Outg Calls =%lu", channel->pInterfaceStat->outg.Calls);
1506 if (channel->pInterfaceStat->outg.Connected) {
1507 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1508 "Outg Connected =%lu", channel->pInterfaceStat->outg.Connected);
1510 if (channel->pInterfaceStat->outg.User_Busy) {
1511 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1512 "Outg Busy =%lu", channel->pInterfaceStat->outg.User_Busy);
1514 if (channel->pInterfaceStat->outg.No_Answer) {
1515 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1516 "Outg No Answer =%lu", channel->pInterfaceStat->outg.No_Answer);
1518 if (channel->pInterfaceStat->outg.Wrong_Number) {
1519 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1520 "Outg Wrong Nr =%lu", channel->pInterfaceStat->outg.Wrong_Number);
1522 if (channel->pInterfaceStat->outg.Call_Rejected) {
1523 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1524 "Outg Rejected =%lu", channel->pInterfaceStat->outg.Call_Rejected);
1526 if (channel->pInterfaceStat->outg.Other_Failures) {
1527 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1528 "Outg Other Failures =%lu", channel->pInterfaceStat->outg.Other_Failures);
1533 case DIVA_SUPER_TRACE_NOTIFY_MDM_STAT_CHANGE:
1534 if (channel->pInterfaceStat->mdm.Disc_Normal) {
1535 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1536 "MDM Disc Normal = %lu", channel->pInterfaceStat->mdm.Disc_Normal);
1538 if (channel->pInterfaceStat->mdm.Disc_Unspecified) {
1539 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1540 "MDM Disc Unsp. = %lu", channel->pInterfaceStat->mdm.Disc_Unspecified);
1542 if (channel->pInterfaceStat->mdm.Disc_Busy_Tone) {
1543 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1544 "MDM Disc Busy Tone = %lu", channel->pInterfaceStat->mdm.Disc_Busy_Tone);
1546 if (channel->pInterfaceStat->mdm.Disc_Congestion) {
1547 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1548 "MDM Disc Congestion = %lu", channel->pInterfaceStat->mdm.Disc_Congestion);
1550 if (channel->pInterfaceStat->mdm.Disc_Carr_Wait) {
1551 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1552 "MDM Disc Carrier Wait = %lu", channel->pInterfaceStat->mdm.Disc_Carr_Wait);
1554 if (channel->pInterfaceStat->mdm.Disc_Trn_Timeout) {
1555 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1556 "MDM Disc Trn. T.o. = %lu", channel->pInterfaceStat->mdm.Disc_Trn_Timeout);
1558 if (channel->pInterfaceStat->mdm.Disc_Incompat) {
1559 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1560 "MDM Disc Incompatible = %lu", channel->pInterfaceStat->mdm.Disc_Incompat);
1562 if (channel->pInterfaceStat->mdm.Disc_Frame_Rej) {
1563 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1564 "MDM Disc Frame Reject = %lu", channel->pInterfaceStat->mdm.Disc_Frame_Rej);
1566 if (channel->pInterfaceStat->mdm.Disc_V42bis) {
1567 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1568 "MDM Disc V.42bis = %lu", channel->pInterfaceStat->mdm.Disc_V42bis);
1572 case DIVA_SUPER_TRACE_NOTIFY_FAX_STAT_CHANGE:
1573 if (channel->pInterfaceStat->fax.Disc_Normal) {
1574 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1575 "FAX Disc Normal = %lu", channel->pInterfaceStat->fax.Disc_Normal);
1577 if (channel->pInterfaceStat->fax.Disc_Not_Ident) {
1578 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1579 "FAX Disc Not Ident. = %lu", channel->pInterfaceStat->fax.Disc_Not_Ident);
1581 if (channel->pInterfaceStat->fax.Disc_No_Response) {
1582 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1583 "FAX Disc No Response = %lu", channel->pInterfaceStat->fax.Disc_No_Response);
1585 if (channel->pInterfaceStat->fax.Disc_Retries) {
1586 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1587 "FAX Disc Max Retries = %lu", channel->pInterfaceStat->fax.Disc_Retries);
1589 if (channel->pInterfaceStat->fax.Disc_Unexp_Msg) {
1590 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1591 "FAX Unexp. Msg. = %lu", channel->pInterfaceStat->fax.Disc_Unexp_Msg);
1593 if (channel->pInterfaceStat->fax.Disc_No_Polling) {
1594 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1595 "FAX Disc No Polling = %lu", channel->pInterfaceStat->fax.Disc_No_Polling);
1597 if (channel->pInterfaceStat->fax.Disc_Training) {
1598 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1599 "FAX Disc Training = %lu", channel->pInterfaceStat->fax.Disc_Training);
1601 if (channel->pInterfaceStat->fax.Disc_Unexpected) {
1602 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1603 "FAX Disc Unexpected = %lu", channel->pInterfaceStat->fax.Disc_Unexpected);
1605 if (channel->pInterfaceStat->fax.Disc_Application) {
1606 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1607 "FAX Disc Application = %lu", channel->pInterfaceStat->fax.Disc_Application);
1609 if (channel->pInterfaceStat->fax.Disc_Incompat) {
1610 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1611 "FAX Disc Incompatible = %lu", channel->pInterfaceStat->fax.Disc_Incompat);
1613 if (channel->pInterfaceStat->fax.Disc_No_Command) {
1614 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1615 "FAX Disc No Command = %lu", channel->pInterfaceStat->fax.Disc_No_Command);
1617 if (channel->pInterfaceStat->fax.Disc_Long_Msg) {
1618 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1619 "FAX Disc Long Msg. = %lu", channel->pInterfaceStat->fax.Disc_Long_Msg);
1621 if (channel->pInterfaceStat->fax.Disc_Supervisor) {
1622 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1623 "FAX Disc Supervisor = %lu", channel->pInterfaceStat->fax.Disc_Supervisor);
1625 if (channel->pInterfaceStat->fax.Disc_SUB_SEP_PWD) {
1626 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1627 "FAX Disc SUP SEP PWD = %lu", channel->pInterfaceStat->fax.Disc_SUB_SEP_PWD);
1629 if (channel->pInterfaceStat->fax.Disc_Invalid_Msg) {
1630 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1631 "FAX Disc Invalid Msg. = %lu", channel->pInterfaceStat->fax.Disc_Invalid_Msg);
1633 if (channel->pInterfaceStat->fax.Disc_Page_Coding) {
1634 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1635 "FAX Disc Page Coding = %lu", channel->pInterfaceStat->fax.Disc_Page_Coding);
1637 if (channel->pInterfaceStat->fax.Disc_App_Timeout) {
1638 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1639 "FAX Disc Appl. T.o. = %lu", channel->pInterfaceStat->fax.Disc_App_Timeout);
1641 if (channel->pInterfaceStat->fax.Disc_Unspecified) {
1642 diva_mnt_internal_dprintf (pC->hDbg->id, DLI_LOG,
1643 "FAX Disc Unspec. = %lu", channel->pInterfaceStat->fax.Disc_Unspecified);
1650 Receive trace information from the Management Interface and store it in the
1651 internal trace buffer with MSG_TYPE_MLOG as is, without any filtering.
1652 Event Filtering and formatting is done in Management Interface self.
1654 static void diva_maint_trace_notify (void* user_context,
1655 diva_strace_library_interface_t* hLib,
1659 diva_maint_client_t* pC = (diva_maint_client_t*)user_context;
1660 diva_dbg_entry_head_t* pmsg;
1664 diva_os_get_time (&sec, &usec);
1666 while (!(pmsg = (diva_dbg_entry_head_t*)queueAllocMsg (dbg_queue,
1667 (word)length+sizeof(*pmsg)))) {
1668 if ((pmsg = (diva_dbg_entry_head_t*)queuePeekMsg (dbg_queue, &size))) {
1669 queueFreeMsg (dbg_queue);
1675 memcpy (&pmsg[1], xlog_buffer, length);
1676 pmsg->sequence = dbg_sequence++;
1677 pmsg->time_sec = sec;
1678 pmsg->time_usec = usec;
1679 pmsg->facility = MSG_TYPE_MLOG;
1680 pmsg->dli = pC->logical;
1681 pmsg->drv_id = pC->hDbg->id;
1683 pmsg->data_length = length;
1684 queueCompleteMsg (pmsg);
1685 if (queueCount(dbg_queue)) {
1686 diva_maint_wakeup_read();
1693 Convert MAINT trace mask to management interface trace mask/work/facility and
1694 issue command to management interface
1696 static void diva_change_management_debug_mask (diva_maint_client_t* pC, dword old_mask) {
1697 if (pC->request && pC->hDbg && pC->pIdiLib) {
1698 dword changed = pC->hDbg->dbgMask ^ old_mask;
1700 if (changed & DIVA_MGT_DBG_TRACE) {
1701 (*(pC->pIdiLib->DivaSTraceSetInfo))(pC->pIdiLib,
1702 (pC->hDbg->dbgMask & DIVA_MGT_DBG_TRACE) != 0);
1704 if (changed & DIVA_MGT_DBG_DCHAN) {
1705 (*(pC->pIdiLib->DivaSTraceSetDChannel))(pC->pIdiLib,
1706 (pC->hDbg->dbgMask & DIVA_MGT_DBG_DCHAN) != 0);
1708 if (changed & DIVA_MGT_DBG_IFC_BCHANNEL) {
1709 int i, state = ((pC->hDbg->dbgMask & DIVA_MGT_DBG_IFC_BCHANNEL) != 0);
1711 for (i = 0; i < pC->channels; i++) {
1712 (*(pC->pIdiLib->DivaSTraceSetBChannel))(pC->pIdiLib, i+1, state);
1715 if (changed & DIVA_MGT_DBG_IFC_AUDIO) {
1716 int i, state = ((pC->hDbg->dbgMask & DIVA_MGT_DBG_IFC_AUDIO) != 0);
1718 for (i = 0; i < pC->channels; i++) {
1719 (*(pC->pIdiLib->DivaSTraceSetAudioTap))(pC->pIdiLib, i+1, state);
1726 void diva_mnt_internal_dprintf (dword drv_id, dword type, char* fmt, ...) {
1730 DI_format (0, (word)drv_id, (int)type, fmt, ap);
1735 Shutdown all adapters before driver removal
1737 int diva_mnt_shutdown_xdi_adapters (void) {
1738 diva_os_spin_lock_magic_t old_irql, old_irql1;
1743 for (i = 1; i < (sizeof(clients)/sizeof(clients[0])); i++) {
1746 diva_os_enter_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "unload");
1747 diva_os_enter_spin_lock_hard (&dbg_q_lock, &old_irql, "unload");
1749 if (clients[i].hDbg && clients[i].pIdiLib && clients[i].request) {
1750 if ((*(clients[i].pIdiLib->DivaSTraceLibraryStop))(clients[i].pIdiLib) == 1) {
1752 Adapter removal complete
1754 if (clients[i].pIdiLib) {
1755 (*(clients[i].pIdiLib->DivaSTraceLibraryFinit))(clients[i].pIdiLib->hLib);
1756 clients[i].pIdiLib = NULL;
1758 pmem = clients[i].pmem;
1759 clients[i].pmem = NULL;
1761 clients[i].hDbg = NULL;
1762 clients[i].request = NULL;
1763 clients[i].request_pending = 0;
1769 diva_os_leave_spin_lock_hard (&dbg_q_lock, &old_irql, "unload");
1770 if (clients[i].hDbg && clients[i].pIdiLib && clients[i].request && clients[i].request_pending) {
1771 clients[i].request_pending = 0;
1772 (*(clients[i].request))((ENTITY*)(*(clients[i].pIdiLib->DivaSTraceGetHandle))(clients[i].pIdiLib->hLib));
1774 diva_os_leave_spin_lock_hard (&dbg_adapter_lock, &old_irql1, "unload");
1777 diva_os_free (0, pmem);