remote_gdb.cc (11793:ef606668d247) | remote_gdb.cc (12019:65939e37768a) |
---|---|
1/* 2 * Copyright 2015 LabWare 3 * Copyright 2014 Google, Inc. 4 * Copyright (c) 2002-2005 The Regents of The University of Michigan 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions are --- 111 unchanged lines hidden (view full) --- 120 */ 121 122#include "base/remote_gdb.hh" 123 124#include <sys/signal.h> 125#include <unistd.h> 126 127#include <csignal> | 1/* 2 * Copyright 2015 LabWare 3 * Copyright 2014 Google, Inc. 4 * Copyright (c) 2002-2005 The Regents of The University of Michigan 5 * All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that the following conditions are --- 111 unchanged lines hidden (view full) --- 120 */ 121 122#include "base/remote_gdb.hh" 123 124#include <sys/signal.h> 125#include <unistd.h> 126 127#include <csignal> |
128#include <cstdint> |
|
128#include <cstdio> 129#include <string> 130 131#include "arch/vtophys.hh" 132#include "base/intmath.hh" 133#include "base/socket.hh" 134#include "base/trace.hh" 135#include "config/the_isa.hh" --- 227 unchanged lines hidden (view full) --- 363 default: return "KGDB_UNKNOWN"; 364 } 365} 366 367///////////////////////// 368// 369// 370 | 129#include <cstdio> 130#include <string> 131 132#include "arch/vtophys.hh" 133#include "base/intmath.hh" 134#include "base/socket.hh" 135#include "base/trace.hh" 136#include "config/the_isa.hh" --- 227 unchanged lines hidden (view full) --- 364 default: return "KGDB_UNKNOWN"; 365 } 366} 367 368///////////////////////// 369// 370// 371 |
371uint8_t 372BaseRemoteGDB::getbyte() | 372bool 373BaseRemoteGDB::getbyte(uint8_t &b) |
373{ | 374{ |
374 uint8_t b; 375 if (::read(fd, &b, 1) != 1) 376 warn("could not read byte from debugger"); 377 return b; | 375 if (::read(fd, &b, sizeof(b)) == sizeof(b)) { 376 return true; 377 } else { 378 warn("Couldn't read data from debugger, detaching."); 379 detach(); 380 return false; 381 } |
378} 379 | 382} 383 |
380void | 384bool |
381BaseRemoteGDB::putbyte(uint8_t b) 382{ | 385BaseRemoteGDB::putbyte(uint8_t b) 386{ |
383 if (::write(fd, &b, 1) != 1) 384 warn("could not write byte to debugger"); | 387 if (::write(fd, &b, sizeof(b)) == sizeof(b)) { 388 return true; 389 } else { 390 warn("Couldn't write data to the debugger, detaching."); 391 detach(); 392 return false; 393 } |
385} 386 387// Send a packet to gdb | 394} 395 396// Send a packet to gdb |
388void | 397ssize_t |
389BaseRemoteGDB::send(const char *bp) 390{ 391 const char *p; 392 uint8_t csum, c; 393 394 DPRINTF(GDBSend, "send: %s\n", bp); 395 396 do { 397 p = bp; 398 //Start sending a packet | 398BaseRemoteGDB::send(const char *bp) 399{ 400 const char *p; 401 uint8_t csum, c; 402 403 DPRINTF(GDBSend, "send: %s\n", bp); 404 405 do { 406 p = bp; 407 //Start sending a packet |
399 putbyte(GDBStart); | 408 if (!putbyte(GDBStart)) 409 return -1; |
400 //Send the contents, and also keep a check sum. 401 for (csum = 0; (c = *p); p++) { | 410 //Send the contents, and also keep a check sum. 411 for (csum = 0; (c = *p); p++) { |
402 putbyte(c); | 412 if (!putbyte(c)) 413 return -1; |
403 csum += c; 404 } | 414 csum += c; 415 } |
405 //Send the ending character. 406 putbyte(GDBEnd); 407 //Sent the checksum. 408 putbyte(i2digit(csum >> 4)); 409 putbyte(i2digit(csum)); 410 //Try transmitting over and over again until the other end doesn't send an 411 //error back. 412 } while ((c = getbyte() & 0x7f) == GDBBadP); | 416 if (//Send the ending character. 417 !putbyte(GDBEnd) || 418 //Sent the checksum. 419 !putbyte(i2digit(csum >> 4)) || 420 !putbyte(i2digit(csum))) { 421 return -1; 422 } 423 //Try transmitting over and over again until the other end doesn't 424 //send an error back. 425 if (!getbyte(c)) 426 return -1; 427 } while ((c & 0x7f) == GDBBadP); 428 return 0; |
413} 414 415// Receive a packet from gdb 416int 417BaseRemoteGDB::recv(char *bp, int maxlen) 418{ 419 char *p; | 429} 430 431// Receive a packet from gdb 432int 433BaseRemoteGDB::recv(char *bp, int maxlen) 434{ 435 char *p; |
420 int c, csum; | 436 uint8_t c; 437 int csum; |
421 int len; 422 423 do { 424 p = bp; 425 csum = len = 0; 426 //Find the beginning of a packet | 438 int len; 439 440 do { 441 p = bp; 442 csum = len = 0; 443 //Find the beginning of a packet |
427 while ((c = getbyte()) != GDBStart) 428 ; | 444 do { 445 if (!getbyte(c)) 446 return -1; 447 } while (c != GDBStart); |
429 430 //Read until you find the end of the data in the packet, and keep 431 //track of the check sum. | 448 449 //Read until you find the end of the data in the packet, and keep 450 //track of the check sum. |
432 while ((c = getbyte()) != GDBEnd && len < maxlen) { | 451 while (len < maxlen) { 452 if (!getbyte(c)) 453 return -1; 454 if (c == GDBEnd) 455 break; |
433 c &= 0x7f; 434 csum += c; 435 *p++ = c; 436 len++; 437 } 438 439 //Mask the check sum, and terminate the command string. 440 csum &= 0xff; 441 *p = '\0'; 442 443 //If the command was too long, report an error. 444 if (len >= maxlen) { | 456 c &= 0x7f; 457 csum += c; 458 *p++ = c; 459 len++; 460 } 461 462 //Mask the check sum, and terminate the command string. 463 csum &= 0xff; 464 *p = '\0'; 465 466 //If the command was too long, report an error. 467 if (len >= maxlen) { |
445 putbyte(GDBBadP); | 468 if (!putbyte(GDBBadP)) 469 return -1; |
446 continue; 447 } 448 449 //Bring in the checksum. If the check sum matches, csum will be 0. | 470 continue; 471 } 472 473 //Bring in the checksum. If the check sum matches, csum will be 0. |
450 csum -= digit2i(getbyte()) * 16; 451 csum -= digit2i(getbyte()); | 474 uint8_t csum1, csum2; 475 if (!getbyte(csum1) || !getbyte(csum2)) 476 return -1; 477 csum -= digit2i(csum1) * 16; 478 csum -= digit2i(csum2); |
452 453 //If the check sum was correct 454 if (csum == 0) { 455 //Report that the packet was received correctly | 479 480 //If the check sum was correct 481 if (csum == 0) { 482 //Report that the packet was received correctly |
456 putbyte(GDBGoodP); | 483 if (!putbyte(GDBGoodP)) 484 return -1; |
457 // Sequence present? 458 if (bp[2] == ':') { | 485 // Sequence present? 486 if (bp[2] == ':') { |
459 putbyte(bp[0]); 460 putbyte(bp[1]); | 487 if (!putbyte(bp[0]) || !putbyte(bp[1])) 488 return -1; |
461 len -= 3; 462 memcpy(bp, bp+3, len); 463 } 464 break; 465 } 466 //Otherwise, report that there was a mistake. | 489 len -= 3; 490 memcpy(bp, bp+3, len); 491 } 492 break; 493 } 494 //Otherwise, report that there was a mistake. |
467 putbyte(GDBBadP); | 495 if (!putbyte(GDBBadP)) 496 return -1; |
468 } while (1); 469 470 DPRINTF(GDBRecv, "recv: %s: %s\n", gdb_command(*bp), bp); 471 472 return (len); 473} 474 475// Read bytes from kernel address space for debugger. --- 217 unchanged lines hidden (view full) --- 693// makes sense to use POSIX errno values, because that is what the 694// gdb/remote.c functions want to return. 695bool 696BaseRemoteGDB::trap(int type) 697{ 698 uint64_t val; 699 size_t datalen, len; 700 char data[GDBPacketBufLen + 1]; | 497 } while (1); 498 499 DPRINTF(GDBRecv, "recv: %s: %s\n", gdb_command(*bp), bp); 500 501 return (len); 502} 503 504// Read bytes from kernel address space for debugger. --- 217 unchanged lines hidden (view full) --- 722// makes sense to use POSIX errno values, because that is what the 723// gdb/remote.c functions want to return. 724bool 725BaseRemoteGDB::trap(int type) 726{ 727 uint64_t val; 728 size_t datalen, len; 729 char data[GDBPacketBufLen + 1]; |
701 char *buffer; | |
702 size_t bufferSize; 703 const char *p; 704 char command, subcmd; 705 string var; 706 bool ret; 707 708 if (!attached) 709 return false; 710 711 unique_ptr<BaseRemoteGDB::BaseGdbRegCache> regCache(gdbRegs()); 712 713 bufferSize = regCache->size() * 2 + 256; | 730 size_t bufferSize; 731 const char *p; 732 char command, subcmd; 733 string var; 734 bool ret; 735 736 if (!attached) 737 return false; 738 739 unique_ptr<BaseRemoteGDB::BaseGdbRegCache> regCache(gdbRegs()); 740 741 bufferSize = regCache->size() * 2 + 256; |
714 buffer = (char*)malloc(bufferSize); | 742 unique_ptr<char[]> buffer_mem(new char[bufferSize]); 743 char *buffer = buffer_mem.get(); |
715 716 DPRINTF(GDBMisc, "trap: PC=%s\n", context->pcState()); 717 718 clearSingleStep(); 719 720 /* 721 * The first entry to this function is normally through 722 * a breakpoint trap in kgdb_connect(), in which case we --- 4 unchanged lines hidden (view full) --- 727 * After the debugger is "active" (connected) it will be 728 * waiting for a "signaled" message from us. 729 */ 730 if (!active) { 731 active = true; 732 } else { 733 // Tell remote host that an exception has occurred. 734 snprintf(buffer, bufferSize, "S%02x", type); | 744 745 DPRINTF(GDBMisc, "trap: PC=%s\n", context->pcState()); 746 747 clearSingleStep(); 748 749 /* 750 * The first entry to this function is normally through 751 * a breakpoint trap in kgdb_connect(), in which case we --- 4 unchanged lines hidden (view full) --- 756 * After the debugger is "active" (connected) it will be 757 * waiting for a "signaled" message from us. 758 */ 759 if (!active) { 760 active = true; 761 } else { 762 // Tell remote host that an exception has occurred. 763 snprintf(buffer, bufferSize, "S%02x", type); |
735 send(buffer); | 764 if (send(buffer) < 0) 765 return true; |
736 } 737 738 // Stick frame regs into our reg cache. 739 regCache->getRegs(context); 740 741 for (;;) { | 766 } 767 768 // Stick frame regs into our reg cache. 769 regCache->getRegs(context); 770 771 for (;;) { |
742 datalen = recv(data, sizeof(data)); | 772 int recved = recv(data, sizeof(data)); 773 if (recved < 0) 774 return true; 775 datalen = recved; |
743 data[sizeof(data) - 1] = 0; // Sentinel 744 command = data[0]; 745 subcmd = 0; 746 p = data + 1; 747 switch (command) { 748 749 case GDBSignal: 750 // if this command came from a running gdb, answer it -- 751 // the other guy has no way of knowing if we're in or out 752 // of this loop when he issues a "remote-signal". 753 snprintf(buffer, bufferSize, 754 "S%02x", type); | 776 data[sizeof(data) - 1] = 0; // Sentinel 777 command = data[0]; 778 subcmd = 0; 779 p = data + 1; 780 switch (command) { 781 782 case GDBSignal: 783 // if this command came from a running gdb, answer it -- 784 // the other guy has no way of knowing if we're in or out 785 // of this loop when he issues a "remote-signal". 786 snprintf(buffer, bufferSize, 787 "S%02x", type); |
755 send(buffer); | 788 if (send(buffer) < 0) 789 return true; |
756 continue; 757 758 case GDBRegR: 759 if (2 * regCache->size() > bufferSize) 760 panic("buffer too small"); 761 762 mem2hex(buffer, regCache->data(), regCache->size()); | 790 continue; 791 792 case GDBRegR: 793 if (2 * regCache->size() > bufferSize) 794 panic("buffer too small"); 795 796 mem2hex(buffer, regCache->data(), regCache->size()); |
763 send(buffer); | 797 if (send(buffer) < 0) 798 return true; |
764 continue; 765 766 case GDBRegW: 767 p = hex2mem(regCache->data(), p, regCache->size()); | 799 continue; 800 801 case GDBRegW: 802 p = hex2mem(regCache->data(), p, regCache->size()); |
768 if (p == NULL || *p != '\0') 769 send("E01"); 770 else { | 803 if (p == NULL || *p != '\0') { 804 if (send("E01") < 0) 805 return true; 806 } else { |
771 regCache->setRegs(context); | 807 regCache->setRegs(context); |
772 send("OK"); | 808 if (send("OK") < 0) 809 return true; |
773 } 774 continue; 775 776 case GDBMemR: 777 val = hex2i(&p); 778 if (*p++ != ',') { | 810 } 811 continue; 812 813 case GDBMemR: 814 val = hex2i(&p); 815 if (*p++ != ',') { |
779 send("E02"); | 816 if (send("E02") < 0) 817 return true; |
780 continue; 781 } 782 len = hex2i(&p); 783 if (*p != '\0') { | 818 continue; 819 } 820 len = hex2i(&p); 821 if (*p != '\0') { |
784 send("E03"); | 822 if (send("E03") < 0) 823 return true; |
785 continue; 786 } 787 if (len > bufferSize) { | 824 continue; 825 } 826 if (len > bufferSize) { |
788 send("E04"); | 827 if (send("E04") < 0) 828 return true; |
789 continue; 790 } 791 if (!acc(val, len)) { | 829 continue; 830 } 831 if (!acc(val, len)) { |
792 send("E05"); | 832 if (send("E05") < 0) 833 return true; |
793 continue; 794 } 795 796 if (read(val, (size_t)len, buffer)) { 797 // variable length array would be nice, but C++ doesn't 798 // officially support those... 799 char *temp = new char[2*len+1]; 800 mem2hex(temp, buffer, len); | 834 continue; 835 } 836 837 if (read(val, (size_t)len, buffer)) { 838 // variable length array would be nice, but C++ doesn't 839 // officially support those... 840 char *temp = new char[2*len+1]; 841 mem2hex(temp, buffer, len); |
801 send(temp); | 842 if (send(temp) < 0) { 843 delete [] temp; 844 return true; 845 } |
802 delete [] temp; 803 } else { | 846 delete [] temp; 847 } else { |
804 send("E05"); | 848 if (send("E05") < 0) 849 return true; |
805 } 806 continue; 807 808 case GDBMemW: 809 val = hex2i(&p); 810 if (*p++ != ',') { | 850 } 851 continue; 852 853 case GDBMemW: 854 val = hex2i(&p); 855 if (*p++ != ',') { |
811 send("E06"); | 856 if (send("E06") < 0) 857 return true; |
812 continue; 813 } 814 len = hex2i(&p); 815 if (*p++ != ':') { | 858 continue; 859 } 860 len = hex2i(&p); 861 if (*p++ != ':') { |
816 send("E07"); | 862 if (send("E07") < 0) 863 return true; |
817 continue; 818 } 819 if (len > datalen - (p - data)) { | 864 continue; 865 } 866 if (len > datalen - (p - data)) { |
820 send("E08"); | 867 if (send("E08") < 0) 868 return true; |
821 continue; 822 } 823 p = hex2mem(buffer, p, bufferSize); 824 if (p == NULL) { | 869 continue; 870 } 871 p = hex2mem(buffer, p, bufferSize); 872 if (p == NULL) { |
825 send("E09"); | 873 if (send("E09") < 0) 874 return true; |
826 continue; 827 } 828 if (!acc(val, len)) { | 875 continue; 876 } 877 if (!acc(val, len)) { |
829 send("E0A"); | 878 if (send("E0A") < 0) 879 return true; |
830 continue; 831 } | 880 continue; 881 } |
832 if (write(val, (size_t)len, buffer)) 833 send("OK"); 834 else 835 send("E0B"); | 882 if (write(val, (size_t)len, buffer)) { 883 if (send("OK") < 0) 884 return true; 885 } else { 886 if (send("E0B") < 0) 887 return true; 888 } |
836 continue; 837 838 case GDBSetThread: 839 subcmd = *p++; 840 val = hex2i(&p); | 889 continue; 890 891 case GDBSetThread: 892 subcmd = *p++; 893 val = hex2i(&p); |
841 if (val == 0) 842 send("OK"); 843 else 844 send("E01"); | 894 if (val == 0) { 895 if (send("OK") < 0) 896 return true; 897 } else { 898 if (send("E01") < 0) 899 return true; 900 } |
845 continue; 846 847 case GDBDetach: 848 case GDBKill: 849 active = false; 850 clearSingleStep(); 851 detach(); | 901 continue; 902 903 case GDBDetach: 904 case GDBKill: 905 active = false; 906 clearSingleStep(); 907 detach(); |
852 goto out; | 908 return true; |
853 854 case GDBAsyncCont: 855 subcmd = hex2i(&p); 856 if (*p++ == ';') { 857 val = hex2i(&p); 858 context->pcState(val); 859 } 860 clearSingleStep(); | 909 910 case GDBAsyncCont: 911 subcmd = hex2i(&p); 912 if (*p++ == ';') { 913 val = hex2i(&p); 914 context->pcState(val); 915 } 916 clearSingleStep(); |
861 goto out; | 917 return true; |
862 863 case GDBCont: 864 if (p - data < (ptrdiff_t)datalen) { 865 val = hex2i(&p); 866 context->pcState(val); 867 } 868 clearSingleStep(); | 918 919 case GDBCont: 920 if (p - data < (ptrdiff_t)datalen) { 921 val = hex2i(&p); 922 context->pcState(val); 923 } 924 clearSingleStep(); |
869 goto out; | 925 return true; |
870 871 case GDBAsyncStep: 872 subcmd = hex2i(&p); 873 if (*p++ == ';') { 874 val = hex2i(&p); 875 context->pcState(val); 876 } 877 setSingleStep(); | 926 927 case GDBAsyncStep: 928 subcmd = hex2i(&p); 929 if (*p++ == ';') { 930 val = hex2i(&p); 931 context->pcState(val); 932 } 933 setSingleStep(); |
878 goto out; | 934 return true; |
879 880 case GDBStep: 881 if (p - data < (ptrdiff_t)datalen) { 882 val = hex2i(&p); 883 context->pcState(val); 884 } 885 setSingleStep(); | 935 936 case GDBStep: 937 if (p - data < (ptrdiff_t)datalen) { 938 val = hex2i(&p); 939 context->pcState(val); 940 } 941 setSingleStep(); |
886 goto out; | 942 return true; |
887 888 case GDBClrHwBkpt: 889 subcmd = *p++; | 943 944 case GDBClrHwBkpt: 945 subcmd = *p++; |
890 if (*p++ != ',') send("E0D"); | 946 if (*p++ != ',' && send("E0D") < 0) 947 return true; |
891 val = hex2i(&p); | 948 val = hex2i(&p); |
892 if (*p++ != ',') send("E0D"); | 949 if (*p++ != ',' && send("E0D") < 0) 950 return true; |
893 len = hex2i(&p); 894 895 DPRINTF(GDBMisc, "clear %s, addr=%#x, len=%d\n", 896 break_type(subcmd), val, len); 897 898 ret = false; 899 900 switch (subcmd) { --- 4 unchanged lines hidden (view full) --- 905 case '1': // hardware breakpoint 906 ret = removeHardBreak(val, len); 907 break; 908 909 case '2': // write watchpoint 910 case '3': // read watchpoint 911 case '4': // access watchpoint 912 default: // unknown | 951 len = hex2i(&p); 952 953 DPRINTF(GDBMisc, "clear %s, addr=%#x, len=%d\n", 954 break_type(subcmd), val, len); 955 956 ret = false; 957 958 switch (subcmd) { --- 4 unchanged lines hidden (view full) --- 963 case '1': // hardware breakpoint 964 ret = removeHardBreak(val, len); 965 break; 966 967 case '2': // write watchpoint 968 case '3': // read watchpoint 969 case '4': // access watchpoint 970 default: // unknown |
913 send(""); | 971 if (send("") < 0) 972 return true; |
914 break; 915 } 916 | 973 break; 974 } 975 |
917 send(ret ? "OK" : "E0C"); | 976 if (send(ret ? "OK" : "E0C") < 0) 977 return true; |
918 continue; 919 920 case GDBSetHwBkpt: 921 subcmd = *p++; | 978 continue; 979 980 case GDBSetHwBkpt: 981 subcmd = *p++; |
922 if (*p++ != ',') send("E0D"); | 982 if (*p++ != ',' && send("E0D") < 0) 983 return true; |
923 val = hex2i(&p); | 984 val = hex2i(&p); |
924 if (*p++ != ',') send("E0D"); | 985 if (*p++ != ',' && send("E0D") < 0) 986 return true; |
925 len = hex2i(&p); 926 927 DPRINTF(GDBMisc, "set %s, addr=%#x, len=%d\n", 928 break_type(subcmd), val, len); 929 930 ret = false; 931 932 switch (subcmd) { --- 4 unchanged lines hidden (view full) --- 937 case '1': // hardware breakpoint 938 ret = insertHardBreak(val, len); 939 break; 940 941 case '2': // write watchpoint 942 case '3': // read watchpoint 943 case '4': // access watchpoint 944 default: // unknown | 987 len = hex2i(&p); 988 989 DPRINTF(GDBMisc, "set %s, addr=%#x, len=%d\n", 990 break_type(subcmd), val, len); 991 992 ret = false; 993 994 switch (subcmd) { --- 4 unchanged lines hidden (view full) --- 999 case '1': // hardware breakpoint 1000 ret = insertHardBreak(val, len); 1001 break; 1002 1003 case '2': // write watchpoint 1004 case '3': // read watchpoint 1005 case '4': // access watchpoint 1006 default: // unknown |
945 send(""); | 1007 if (send("") < 0) 1008 return true; |
946 break; 947 } 948 | 1009 break; 1010 } 1011 |
949 send(ret ? "OK" : "E0C"); | 1012 if (send(ret ? "OK" : "E0C") < 0) 1013 return true; |
950 continue; 951 952 case GDBQueryVar: 953 var = string(p, datalen - 1); | 1014 continue; 1015 1016 case GDBQueryVar: 1017 var = string(p, datalen - 1); |
954 if (var == "C") 955 send("QC0"); 956 else 957 send(""); | 1018 if (var == "C") { 1019 if (send("QC0") < 0) 1020 return true; 1021 } else { 1022 if (send("") < 0) 1023 return true; 1024 } |
958 continue; 959 960 case GDBSetBaud: 961 case GDBSetBreak: 962 case GDBDebug: 963 case GDBCycleStep: 964 case GDBSigCycleStep: 965 case GDBReadReg: 966 case GDBSetVar: 967 case GDBReset: 968 case GDBThreadAlive: 969 case GDBTargetExit: 970 case GDBBinaryDload: 971 // Unsupported command 972 DPRINTF(GDBMisc, "Unsupported command: %s\n", 973 gdb_command(command)); 974 DDUMP(GDBMisc, (uint8_t *)data, datalen); | 1025 continue; 1026 1027 case GDBSetBaud: 1028 case GDBSetBreak: 1029 case GDBDebug: 1030 case GDBCycleStep: 1031 case GDBSigCycleStep: 1032 case GDBReadReg: 1033 case GDBSetVar: 1034 case GDBReset: 1035 case GDBThreadAlive: 1036 case GDBTargetExit: 1037 case GDBBinaryDload: 1038 // Unsupported command 1039 DPRINTF(GDBMisc, "Unsupported command: %s\n", 1040 gdb_command(command)); 1041 DDUMP(GDBMisc, (uint8_t *)data, datalen); |
975 send(""); | 1042 if (send("") < 0) 1043 return true; |
976 continue; 977 978 default: 979 // Unknown command. 980 DPRINTF(GDBMisc, "Unknown command: %c(%#x)\n", 981 command, command); | 1044 continue; 1045 1046 default: 1047 // Unknown command. 1048 DPRINTF(GDBMisc, "Unknown command: %c(%#x)\n", 1049 command, command); |
982 send(""); | 1050 if (send("") < 0) 1051 return true; |
983 continue; 984 985 986 } 987 } 988 | 1052 continue; 1053 1054 1055 } 1056 } 1057 |
989 out: 990 free(buffer); | |
991 return true; 992} 993 994// Convert a hex digit into an integer. 995// This returns -1 if the argument passed is no valid hex digit. 996int 997BaseRemoteGDB::digit2i(char c) 998{ --- 73 unchanged lines hidden --- | 1058 return true; 1059} 1060 1061// Convert a hex digit into an integer. 1062// This returns -1 if the argument passed is no valid hex digit. 1063int 1064BaseRemoteGDB::digit2i(char c) 1065{ --- 73 unchanged lines hidden --- |