aboutsummaryrefslogtreecommitdiffstats
path: root/arch/cris
diff options
context:
space:
mode:
Diffstat (limited to 'arch/cris')
-rw-r--r--arch/cris/arch-v10/kernel/kgdb.c257
1 files changed, 2 insertions, 255 deletions
diff --git a/arch/cris/arch-v10/kernel/kgdb.c b/arch/cris/arch-v10/kernel/kgdb.c
index 0e799073498d..22d846bfc570 100644
--- a/arch/cris/arch-v10/kernel/kgdb.c
+++ b/arch/cris/arch-v10/kernel/kgdb.c
@@ -341,16 +341,6 @@ static int consistency_status = SUCCESS;
341 in order to provide access mainly for 'g', 'G' and 'P'. 341 in order to provide access mainly for 'g', 'G' and 'P'.
342*/ 342*/
343 343
344#ifdef PROCESS_SUPPORT
345/* Need two task id pointers in order to handle Hct and Hgt commands. */
346static int current_thread_c = 0;
347static int current_thread_g = 0;
348
349/* Need two register images in order to handle Hct and Hgt commands. The
350 variable reg_g is in addition to cris_reg above. */
351static registers reg_g;
352#endif /* PROCESS_SUPPORT */
353
354/********************************** Breakpoint *******************************/ 344/********************************** Breakpoint *******************************/
355/* Use an internal stack in the breakpoint and interrupt response routines */ 345/* Use an internal stack in the breakpoint and interrupt response routines */
356#define INTERNAL_STACK_SIZE 1024 346#define INTERNAL_STACK_SIZE 1024
@@ -608,55 +598,6 @@ putDebugString (const unsigned char *str, int length)
608} 598}
609 599
610/********************************* Register image ****************************/ 600/********************************* Register image ****************************/
611#ifdef PROCESS_SUPPORT
612/* Copy the content of a register image into another. The size n is
613 the size of the register image. Due to struct assignment generation of
614 memcpy in libc. */
615static void
616copy_registers (registers *dptr, registers *sptr, int n)
617{
618 unsigned char *dreg;
619 unsigned char *sreg;
620
621 for (dreg = (unsigned char*)dptr, sreg = (unsigned char*)sptr; n > 0; n--)
622 *dreg++ = *sreg++;
623}
624
625/* Copy the stored registers from the stack. Put the register contents
626 of thread thread_id in the struct reg. */
627static void
628copy_registers_from_stack (int thread_id, registers *regptr)
629{
630 int j;
631 stack_registers *s = (stack_registers *)stack_list[thread_id];
632 unsigned int *d = (unsigned int *)regptr;
633
634 for (j = 13; j >= 0; j--)
635 *d++ = s->r[j];
636 regptr->sp = (unsigned int)stack_list[thread_id];
637 regptr->pc = s->pc;
638 regptr->dccr = s->dccr;
639 regptr->srp = s->srp;
640}
641
642/* Copy the registers to the stack. Put the register contents of thread
643 thread_id from struct reg to the stack. */
644static void
645copy_registers_to_stack (int thread_id, registers *regptr)
646{
647 int i;
648 stack_registers *d = (stack_registers *)stack_list[thread_id];
649 unsigned int *s = (unsigned int *)regptr;
650
651 for (i = 0; i < 14; i++) {
652 d->r[i] = *s++;
653 }
654 d->pc = regptr->pc;
655 d->dccr = regptr->dccr;
656 d->srp = regptr->srp;
657}
658#endif
659
660/* Write a value to a specified register in the register image of the current 601/* Write a value to a specified register in the register image of the current
661 thread. Returns status code SUCCESS, E02 or E05. */ 602 thread. Returns status code SUCCESS, E02 or E05. */
662static int 603static int
@@ -692,40 +633,6 @@ write_register (int regno, char *val)
692 return status; 633 return status;
693} 634}
694 635
695#ifdef PROCESS_SUPPORT
696/* Write a value to a specified register in the stack of a thread other
697 than the current thread. Returns status code SUCCESS or E07. */
698static int
699write_stack_register (int thread_id, int regno, char *valptr)
700{
701 int status = SUCCESS;
702 stack_registers *d = (stack_registers *)stack_list[thread_id];
703 unsigned int val;
704
705 hex2mem ((unsigned char *)&val, valptr, sizeof(unsigned int));
706 if (regno >= R0 && regno < SP) {
707 d->r[regno] = val;
708 }
709 else if (regno == SP) {
710 stack_list[thread_id] = val;
711 }
712 else if (regno == PC) {
713 d->pc = val;
714 }
715 else if (regno == SRP) {
716 d->srp = val;
717 }
718 else if (regno == DCCR) {
719 d->dccr = val;
720 }
721 else {
722 /* Do not support registers in the current thread. */
723 status = E07;
724 }
725 return status;
726}
727#endif
728
729/* Read a value from a specified register in the register image. Returns the 636/* Read a value from a specified register in the register image. Returns the
730 value in the register or -1 for non-implemented registers. 637 value in the register or -1 for non-implemented registers.
731 Should check consistency_status after a call which may be E05 after changes 638 Should check consistency_status after a call which may be E05 after changes
@@ -811,26 +718,6 @@ stub_is_stopped(int sigval)
811 718
812 } 719 }
813 720
814#ifdef PROCESS_SUPPORT
815 /* Store the registers of the executing thread. Assume that both step,
816 continue, and register content requests are with respect to this
817 thread. The executing task is from the operating system scheduler. */
818
819 current_thread_c = executing_task;
820 current_thread_g = executing_task;
821
822 /* A struct assignment translates into a libc memcpy call. Avoid
823 all libc functions in order to prevent recursive break points. */
824 copy_registers (&reg_g, &cris_reg, sizeof(registers));
825
826 /* Store thread:r...; with the executing task TID. */
827 gdb_cris_strcpy (&remcomOutBuffer[pos], "thread:");
828 pos += gdb_cris_strlen ("thread:");
829 remcomOutBuffer[pos++] = hex_asc_hi(executing_task);
830 remcomOutBuffer[pos++] = hex_asc_lo(executing_task);
831 gdb_cris_strcpy (&remcomOutBuffer[pos], ";");
832#endif
833
834 /* null-terminate and send it off */ 721 /* null-terminate and send it off */
835 722
836 *ptr = 0; 723 *ptr = 0;
@@ -865,19 +752,7 @@ handle_exception (int sigval)
865 in a register are in the same order the machine uses. 752 in a register are in the same order the machine uses.
866 Failure: void. */ 753 Failure: void. */
867 754
868 { 755 mem2hex(remcomOutBuffer, (char *)&cris_reg, sizeof(registers));
869#ifdef PROCESS_SUPPORT
870 /* Use the special register content in the executing thread. */
871 copy_registers (&reg_g, &cris_reg, sizeof(registers));
872 /* Replace the content available on the stack. */
873 if (current_thread_g != executing_task) {
874 copy_registers_from_stack (current_thread_g, &reg_g);
875 }
876 mem2hex ((unsigned char *)remcomOutBuffer, (unsigned char *)&reg_g, sizeof(registers));
877#else
878 mem2hex(remcomOutBuffer, (char *)&cris_reg, sizeof(registers));
879#endif
880 }
881 break; 756 break;
882 757
883 case 'G': 758 case 'G':
@@ -885,17 +760,7 @@ handle_exception (int sigval)
885 Each byte of register data is described by two hex digits. 760 Each byte of register data is described by two hex digits.
886 Success: OK 761 Success: OK
887 Failure: void. */ 762 Failure: void. */
888#ifdef PROCESS_SUPPORT
889 hex2mem ((unsigned char *)&reg_g, &remcomInBuffer[1], sizeof(registers));
890 if (current_thread_g == executing_task) {
891 copy_registers (&cris_reg, &reg_g, sizeof(registers));
892 }
893 else {
894 copy_registers_to_stack(current_thread_g, &reg_g);
895 }
896#else
897 hex2mem((char *)&cris_reg, &remcomInBuffer[1], sizeof(registers)); 763 hex2mem((char *)&cris_reg, &remcomInBuffer[1], sizeof(registers));
898#endif
899 gdb_cris_strcpy (remcomOutBuffer, "OK"); 764 gdb_cris_strcpy (remcomOutBuffer, "OK");
900 break; 765 break;
901 766
@@ -911,12 +776,7 @@ handle_exception (int sigval)
911 char *suffix; 776 char *suffix;
912 int regno = gdb_cris_strtol (&remcomInBuffer[1], &suffix, 16); 777 int regno = gdb_cris_strtol (&remcomInBuffer[1], &suffix, 16);
913 int status; 778 int status;
914#ifdef PROCESS_SUPPORT 779 status = write_register (regno, suffix+1);
915 if (current_thread_g != executing_task)
916 status = write_stack_register (current_thread_g, regno, suffix+1);
917 else
918#endif
919 status = write_register (regno, suffix+1);
920 780
921 switch (status) { 781 switch (status) {
922 case E02: 782 case E02:
@@ -1051,119 +911,6 @@ handle_exception (int sigval)
1051 Not supported: E04 */ 911 Not supported: E04 */
1052 gdb_cris_strcpy (remcomOutBuffer, error_message[E04]); 912 gdb_cris_strcpy (remcomOutBuffer, error_message[E04]);
1053 break; 913 break;
1054#ifdef PROCESS_SUPPORT
1055
1056 case 'T':
1057 /* Thread alive. TXX
1058 Is thread XX alive?
1059 Success: OK, thread XX is alive.
1060 Failure: E03, thread XX is dead. */
1061 {
1062 int thread_id = (int)gdb_cris_strtol (&remcomInBuffer[1], 0, 16);
1063 /* Cannot tell whether it is alive or not. */
1064 if (thread_id >= 0 && thread_id < number_of_tasks)
1065 gdb_cris_strcpy (remcomOutBuffer, "OK");
1066 }
1067 break;
1068
1069 case 'H':
1070 /* Set thread for subsequent operations: Hct
1071 c = 'c' for thread used in step and continue;
1072 t can be -1 for all threads.
1073 c = 'g' for thread used in other operations.
1074 t = 0 means pick any thread.
1075 Success: OK
1076 Failure: E01 */
1077 {
1078 int thread_id = gdb_cris_strtol (&remcomInBuffer[2], 0, 16);
1079 if (remcomInBuffer[1] == 'c') {
1080 /* c = 'c' for thread used in step and continue */
1081 /* Do not change current_thread_c here. It would create a mess in
1082 the scheduler. */
1083 gdb_cris_strcpy (remcomOutBuffer, "OK");
1084 }
1085 else if (remcomInBuffer[1] == 'g') {
1086 /* c = 'g' for thread used in other operations.
1087 t = 0 means pick any thread. Impossible since the scheduler does
1088 not allow that. */
1089 if (thread_id >= 0 && thread_id < number_of_tasks) {
1090 current_thread_g = thread_id;
1091 gdb_cris_strcpy (remcomOutBuffer, "OK");
1092 }
1093 else {
1094 /* Not expected - send an error message. */
1095 gdb_cris_strcpy (remcomOutBuffer, error_message[E01]);
1096 }
1097 }
1098 else {
1099 /* Not expected - send an error message. */
1100 gdb_cris_strcpy (remcomOutBuffer, error_message[E01]);
1101 }
1102 }
1103 break;
1104
1105 case 'q':
1106 case 'Q':
1107 /* Query of general interest. qXXXX
1108 Set general value XXXX. QXXXX=yyyy */
1109 {
1110 int pos;
1111 int nextpos;
1112 int thread_id;
1113
1114 switch (remcomInBuffer[1]) {
1115 case 'C':
1116 /* Identify the remote current thread. */
1117 gdb_cris_strcpy (&remcomOutBuffer[0], "QC");
1118 remcomOutBuffer[2] = hex_asc_hi(current_thread_c);
1119 remcomOutBuffer[3] = hex_asc_lo(current_thread_c);
1120 remcomOutBuffer[4] = '\0';
1121 break;
1122 case 'L':
1123 gdb_cris_strcpy (&remcomOutBuffer[0], "QM");
1124 /* Reply with number of threads. */
1125 if (os_is_started()) {
1126 remcomOutBuffer[2] = hex_asc_hi(number_of_tasks);
1127 remcomOutBuffer[3] = hex_asc_lo(number_of_tasks);
1128 }
1129 else {
1130 remcomOutBuffer[2] = hex_asc_hi(0);
1131 remcomOutBuffer[3] = hex_asc_lo(1);
1132 }
1133 /* Done with the reply. */
1134 remcomOutBuffer[4] = hex_asc_lo(1);
1135 pos = 5;
1136 /* Expects the argument thread id. */
1137 for (; pos < (5 + HEXCHARS_IN_THREAD_ID); pos++)
1138 remcomOutBuffer[pos] = remcomInBuffer[pos];
1139 /* Reply with the thread identifiers. */
1140 if (os_is_started()) {
1141 /* Store the thread identifiers of all tasks. */
1142 for (thread_id = 0; thread_id < number_of_tasks; thread_id++) {
1143 nextpos = pos + HEXCHARS_IN_THREAD_ID - 1;
1144 for (; pos < nextpos; pos ++)
1145 remcomOutBuffer[pos] = hex_asc_lo(0);
1146 remcomOutBuffer[pos++] = hex_asc_lo(thread_id);
1147 }
1148 }
1149 else {
1150 /* Store the thread identifier of the boot task. */
1151 nextpos = pos + HEXCHARS_IN_THREAD_ID - 1;
1152 for (; pos < nextpos; pos ++)
1153 remcomOutBuffer[pos] = hex_asc_lo(0);
1154 remcomOutBuffer[pos++] = hex_asc_lo(current_thread_c);
1155 }
1156 remcomOutBuffer[pos] = '\0';
1157 break;
1158 default:
1159 /* Not supported: "" */
1160 /* Request information about section offsets: qOffsets. */
1161 remcomOutBuffer[0] = 0;
1162 break;
1163 }
1164 }
1165 break;
1166#endif /* PROCESS_SUPPORT */
1167 914
1168 default: 915 default:
1169 /* The stub should ignore other request and send an empty 916 /* The stub should ignore other request and send an empty