summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMichael Brown2011-01-25 01:01:25 +0100
committerMichael Brown2012-07-09 16:41:45 +0200
commit208a651c13a643919346ce52b3eacd948de28db1 (patch)
tree21b0521d5c98e71a0c03ab89cda23abcbca78b37
parent[import] Import version 4.10 (diff)
downloadmemtest86-208a651c13a643919346ce52b3eacd948de28db1.tar.gz
memtest86-208a651c13a643919346ce52b3eacd948de28db1.tar.xz
memtest86-208a651c13a643919346ce52b3eacd948de28db1.zip
[import] Import version 4.20
http://www.memtest.org/download/4.20/memtest86+-4.20.tar.gz
-rw-r--r--README2
-rw-r--r--changelog16
-rw-r--r--config.h3
-rw-r--r--controller.c201
-rw-r--r--init.c77
-rw-r--r--jedec_id.h2
-rw-r--r--linuxbios.c11
-rw-r--r--linuxbios_tables.h7
-rwxr-xr-xmakeiso.sh6
-rw-r--r--mt86+_loaderbin784 -> 784 bytes
-rw-r--r--mt86+_loader.asm4
-rwxr-xr-xprecomp.binbin165080 -> 164504 bytes
-rw-r--r--spd.c115
13 files changed, 313 insertions, 131 deletions
diff --git a/README b/README
index cbdb42e..963cfc4 100644
--- a/README
+++ b/README
@@ -1,4 +1,4 @@
-Memtest86++ v4.10
+Memtest86++ v4.20
====================
Table of Contents
diff --git a/changelog b/changelog
index 5ca01c5..d6e49d2 100644
--- a/changelog
+++ b/changelog
@@ -1,11 +1,9 @@
-Memtest86+ V4.10 changelog
+Memtest86+ V4.20 changelog
--------------------------
- - Added support for Core i7 Extreme CPU (32nm)
- - Added support for Core i5/i3 (32 nm)
- - Added support for Pentium Gxxxx (32 mn)
- - Added support for Westmere-based Xeon
- - Added preliminary support for Intel Sandy Bridge
- - Added support for AMD 6-cores CPU
- - Added detection for Intel 3200/3210
- - Many bug fixes
+ - Added failsafe mode (F1 at startup)
+ - Added support for Intel "Sandy Bridge" CPU
+ - Added support for AMD "fusion" CPU
+ - Added Coreboot "table forward" support
+ - Corrected some memory brand not detected
+ - Various bug fixes \ No newline at end of file
diff --git a/config.h b/config.h
index 8e68985..e32eef4 100644
--- a/config.h
+++ b/config.h
@@ -21,6 +21,9 @@
/* SERIAL_BAUD_RATE - Baud rate for the serial console */
#define SERIAL_BAUD_RATE 9600
+/* START_FAIL_SAFE - Default 0 = normal. Change to 1 to always start in fail safe mode */
+#define START_FAIL_SAFE 0
+
/* BEEP_MODE - Beep on error. Default off, Change to 1 to enable */
#define BEEP_MODE 0
diff --git a/controller.c b/controller.c
index 89589ab..9009996 100644
--- a/controller.c
+++ b/controller.c
@@ -3,7 +3,7 @@
* Released under version 2 of the Gnu Public License.
* By Chris Brady, cbrady@sgi.com
* ----------------------------------------------------
- * MemTest86+ V4.00 Specific code (GPL V2.0)
+ * MemTest86+ V4.20 Specific code (GPL V2.0)
* By Samuel DEMEULEMEESTER, sdemeule@memtest.org
* http://www.canardpc.com - http://www.memtest.org
*/
@@ -23,6 +23,7 @@ int nhm_bus = 0x3F;
extern ulong extclock;
extern unsigned long imc_type;
extern struct cpu_ident cpu_id;
+extern int fail_safe;
#define rdmsr(msr,val1,val2) \
__asm__ __volatile__("rdmsr" \
@@ -175,7 +176,13 @@ static void poll_timings_nothing(void)
return;
}
-
+static void poll_fsb_failsafe(void)
+{
+/* Code to run for no specific fsb detection */
+ cprint(LINE_CPU+5, 0, "Chipset/IMC : ***FAIL SAFE***FAIL SAFE***FAIL SAFE***FAIL SAFE***FAIL SAFE***");
+ cprint(LINE_CPU+6, 0, "*** Memtest86+ is running in fail safe mode. Same reliability, less details ***");
+ return;
+}
static void setup_nothing(void)
{
ctrl.cap = ECC_NONE;
@@ -1230,6 +1237,24 @@ static float getNHMmultiplier(void)
return coef;
}
+static float getSNBmultiplier(void)
+{
+ unsigned int msr_lo, msr_hi;
+ float coef;
+
+ rdmsr(0x198, msr_lo, msr_hi);
+ coef = (msr_lo >> 8) & 0xFF;
+ if(coef < 4)
+ {
+ rdmsr(0xCE, msr_lo, msr_hi);
+ coef = (msr_lo >> 16) & 0xFF;
+ }
+
+
+
+ return coef;
+}
+
void getIntelPNS(void)
{
@@ -1456,6 +1481,58 @@ static void poll_fsb_k10(void) {
}
+static void poll_fsb_k14(void) {
+
+ unsigned long temp2;
+ unsigned long dramchr;
+ double dramclock;
+ unsigned long pns_low;
+ unsigned long pns_high;
+ unsigned long msr_psn;
+
+
+ /* If ECC not enabled : display CPU name as IMC */
+ if(ctrl.mode == ECC_NONE)
+ {
+ cprint(LINE_CPU+5, 0, "IMC : ");
+ for(msr_psn = 0; msr_psn < 5; msr_psn++)
+ {
+ rdmsr(0xC0010030+msr_psn, pns_low, pns_high);
+ cprint(LINE_CPU+5, 6+(msr_psn*8), convert_hex_to_char(pns_low & 0xff));
+ cprint(LINE_CPU+5, 7+(msr_psn*8), convert_hex_to_char((pns_low >> 8) & 0xff));
+ cprint(LINE_CPU+5, 8+(msr_psn*8), convert_hex_to_char((pns_low >> 16) & 0xff));
+ cprint(LINE_CPU+5, 9+(msr_psn*8), convert_hex_to_char((pns_low >> 24) & 0xff));
+ cprint(LINE_CPU+5, 10+(msr_psn*8), convert_hex_to_char(pns_high & 0xff));
+ cprint(LINE_CPU+5, 11+(msr_psn*8), convert_hex_to_char((pns_high >> 8) & 0xff));
+ cprint(LINE_CPU+5, 12+(msr_psn*8), convert_hex_to_char((pns_high >> 16) & 0xff));
+ cprint(LINE_CPU+5, 13+(msr_psn*8), convert_hex_to_char((pns_high >> 24) & 0xff));
+ }
+ cprint(LINE_CPU+5, 41, "(ECC : Disabled)");
+ }
+
+ /* First, we need the clock ratio */
+ pci_conf_read(0, 24, 2, 0x94, 4, &dramchr);
+ temp2 = (dramchr & 0x1F);
+
+ switch (temp2) {
+ default:
+ case 6:
+ dramclock = 400;
+ break;
+ case 10:
+ dramclock = 533;
+ break;
+ case 14:
+ dramclock = 667;
+ break;
+ }
+
+
+ /* print */
+ print_fsb_info(dramclock, "RAM : ", "DDR-");
+
+}
+
static void poll_fsb_i925(void) {
double dramclock, dramratio, fsb;
@@ -2291,6 +2368,50 @@ static void poll_fsb_wmr(void) {
}
+static void poll_fsb_snb(void) {
+
+ double dramclock, dramratio, fsb;
+ unsigned long dev0, mchcfg;
+ float coef = getSNBmultiplier();
+ long *ptr;
+
+ fsb = ((extclock / 1000) / coef);
+
+ if(ctrl.mode == ECC_NONE)
+ {
+ col = 0;
+ cprint(LINE_CPU+5, col, "IMC : "); col += 6;
+ getIntelPNS();
+ //cprint(LINE_CPU+5, col, "(ECC : Disabled)");
+ //col += 16;
+ }
+
+ /* Print FSB */
+ cprint(LINE_CPU+5, col +1, "/ BCLK : ");
+ col += 10;
+ dprint(LINE_CPU+5, col, fsb, 3,0);
+ col += 3;
+ cprint(LINE_CPU+5, col +1, "MHz");
+ col += 4;
+
+ /* Find dramratio */
+ pci_conf_read( 0, 0, 0, 0x48, 4, &dev0);
+ dev0 &= 0xFFFFC000;
+ ptr=(long*)(dev0+0x5E04);
+ mchcfg = *ptr & 0xFFFF;
+ dramratio = 1;
+
+ /* Get the clock ratio */
+ dramratio = (float)(*ptr & 0x1F) * (133.34f / 100.0f);
+
+ // Compute RAM Frequency
+ dramclock = fsb * dramratio;
+
+ // Print DRAM Freq
+ print_fsb_info(dramclock, "RAM : ", "DDR3-");
+
+}
+
/* ------------------ Here the code for Timings detection ------------------ */
/* ------------------------------------------------------------------------- */
@@ -2747,6 +2868,52 @@ static void poll_timings_wmr(void) {
}
+static void poll_timings_snb(void) {
+
+ float cas;
+ int rcd, rp, ras;
+ ulong dev0, offset;
+ ulong IMC_Register, MCMain0_Register, MCMain1_Register;
+ long *ptr;
+
+ //Now, read MMR Base Address
+ pci_conf_read( 0, 0, 0, 0x48, 4, &dev0);
+ dev0 &= 0xFFFFC000;
+
+ offset = 0x0000;
+
+ ptr = (long*)(dev0+offset+0x4000);
+ IMC_Register = *ptr & 0xFFFFFFFF;
+
+ // CAS Latency (tCAS)
+ cas = (float)((IMC_Register >> 8) & 0x0F);
+
+ // RAS-To-CAS (tRCD)
+ rcd = IMC_Register & 0x0F;
+
+ // RAS Precharge (tRP)
+ rp = (IMC_Register >> 4) & 0x0F;
+
+ // RAS Active to precharge (tRAS)
+ ras = (IMC_Register >> 16) & 0xFF;
+
+ print_timings_info(cas, rcd, rp, ras);
+
+ cprint(LINE_CPU+6, col2+1, "/"); col2 +=2;
+
+ // Channels
+ ptr = (long*)(dev0+offset+0x5004);
+ MCMain0_Register = *ptr & 0xFFFF;
+ ptr = (long*)(dev0+offset+0x5008);
+ MCMain1_Register = *ptr & 0xFFFF;
+
+ if(MCMain0_Register == 0 || MCMain1_Register == 0) {
+ cprint(LINE_CPU+6, col2+1, "Single Channel");
+ } else {
+ cprint(LINE_CPU+6, col2+1, "Dual Channel");
+ }
+
+}
static void poll_timings_5400(void) {
@@ -3083,6 +3250,27 @@ static void poll_timings_k10(void) {
}
+static void poll_timings_k14(void) {
+
+ ulong dramt0, dramlow;
+ int cas, rcd, rp, rc, ras;
+
+ pci_conf_read(0, 24, 2, 0x88, 4, &dramlow);
+ pci_conf_write(0, 24, 2, 0xF0, 4, 0x00000040);
+ pci_conf_read(0, 24, 2, 0xF4, 4, &dramt0);
+
+ cas = (dramlow & 0xF) + 4;
+ rcd = (dramt0 & 0xF) + 5;
+ rp = ((dramt0 >> 8) & 0xF) + 5;
+ ras = ((dramt0 >> 16) & 0x1F) + 15;
+ rc = ((dramt0 >> 24) & 0x3F) + 16;
+
+ print_timings_info(cas, rcd, rp, ras);
+
+ cprint(LINE_CPU+6, col2, "/ DDR3 (64 bits)");
+
+}
+
static void poll_timings_EP80579(void) {
ulong drt1, drt2;
@@ -3380,9 +3568,13 @@ static struct pci_memory_controller controllers[] = {
{ 0xFFFF, 0x0001, "Core IMC", 0, poll_fsb_nhm, poll_timings_nhm, setup_nhm, poll_nothing},
{ 0xFFFF, 0x0002, "Core IMC 32nm", 0, poll_fsb_nhm32, poll_timings_nhm, setup_nhm32, poll_nothing},
{ 0xFFFF, 0x0003, "Core IMC 32nm", 0, poll_fsb_wmr, poll_timings_wmr, setup_wmr, poll_nothing},
+ { 0xFFFF, 0x0004, "SNB IMC 32nm", 0, poll_fsb_snb, poll_timings_snb, setup_wmr, poll_nothing},
{ 0xFFFF, 0x0100, "AMD K8 IMC", 0, poll_fsb_amd64, poll_timings_amd64, setup_amd64, poll_amd64 },
- { 0xFFFF, 0x0101, "AMD K10 IMC", 0, poll_fsb_k10, poll_timings_k10, setup_k10, poll_nothing }
-
+ { 0xFFFF, 0x0101, "AMD K10 IMC", 0, poll_fsb_k10, poll_timings_k10, setup_k10, poll_nothing },
+ { 0xFFFF, 0x0102, "AMD APU IMC", 0, poll_fsb_k14, poll_timings_k14, setup_nothing, poll_nothing },
+
+ /* Fail Safe */
+ { 0xFFFF, 0xFFFF, "", 0, poll_fsb_failsafe, poll_timings_nothing, setup_nothing, poll_nothing }
};
static void print_memory_controller(void)
@@ -3474,6 +3666,7 @@ void find_controller(void)
// Detect IMC by CPUID
if(imc_type) { vendor = 0xFFFF; device = imc_type; }
+ if(fail_safe) { vendor = 0xFFFF; device = 0xFFFF; }
ctrl.index = 0;
if (result == 0) {
diff --git a/init.c b/init.c
index d965ec3..f7f43c1 100644
--- a/init.c
+++ b/init.c
@@ -3,7 +3,7 @@
* Released under version 2 of the Gnu Public License.
* By Chris Brady, cbrady@sgi.com
* ----------------------------------------------------
- * MemTest86+ V4.10 Specific code (GPL V2.0)
+ * MemTest86+ V4.20 Specific code (GPL V2.0)
* By Samuel DEMEULEMEESTER, sdemeule@memtest.org
* http://www.canardpc.com - http://www.memtest.org
*/
@@ -41,7 +41,54 @@ ulong memspeed(ulong src, ulong len, int iter, int type);
static void cpu_type(void);
static void cacheable(void);
static int cpuspeed(void);
-int beepmode;
+int beepmode, fail_safe;
+
+/* Failsafe function */
+/* msec: number of ms to wait - scs: scancode expected to stop */
+void failsafe(int msec, int scs)
+{
+ int ip;
+ ulong sh, sl, l, h, t;
+ unsigned char c;
+
+ cprint(18, 22, "Press *F1* to enter Fail-Safe Mode");
+
+ ip = 0;
+ /* save the starting time */
+ asm __volatile__(
+ "rdtsc":"=a" (sl),"=d" (sh));
+
+ /* loop for n seconds */
+ while (1) {
+ asm __volatile__(
+ "rdtsc":"=a" (l),"=d" (h));
+ asm __volatile__ (
+ "subl %2,%0\n\t"
+ "sbbl %3,%1"
+ :"=a" (l), "=d" (h)
+ :"g" (sl), "g" (sh),
+ "0" (l), "1" (h));
+
+ t = h * ((unsigned)0xffffffff / v->clks_msec);
+ t += (l / v->clks_msec);
+
+ /* Is the time up? */
+ if (t >= msec) {
+ cprint(18, 22, " ");
+ break;
+ }
+
+ /* Is expected Scan code pressed? */
+ c = get_key();
+ c &= 0x7f;
+
+ if(c == scs) {
+ fail_safe = 1;
+ cprint(18, 22, " ");
+ break;
+ }
+ }
+}
static void display_init(void)
{
@@ -65,7 +112,7 @@ static void display_init(void)
for(i=0, pp=(char *)(SCREEN_ADR+1); i<TITLE_WIDTH; i++, pp+=2) {
*pp = 0x20;
}
- cprint(0, 0, " Memtest86 v4.10 ");
+ cprint(0, 0, " Memtest86 v4.20 ");
for(i=0, pp=(char *)(SCREEN_ADR+1); i<2; i++, pp+=30) {
*pp = 0xA4;
@@ -86,7 +133,7 @@ static void display_init(void)
void init(void)
{
int i;
-
+
outb(0x8, 0x3f2); /* Kill Floppy Motor */
/* Turn on cache */
@@ -94,6 +141,7 @@ void init(void)
/* Setup the display */
display_init();
+
/* Determine the memory map */
if ((firmware == FIRMWARE_UNKNOWN) &&
@@ -155,11 +203,14 @@ void init(void)
cpu_type();
+ /* Check fail safe */
+ failsafe(2000, 0x3B);
+
/* Find the memory controller */
find_controller();
/* Find Memory Specs */
- get_spd_spec();
+ if(fail_safe == 0) { get_spd_spec(); }
if (v->rdtsc) {
cacheable();
@@ -576,18 +627,25 @@ void cpu_type(void)
l3_cache = (cpu_id.cache_info[15] << 8);
l3_cache += (cpu_id.cache_info[14] >> 2);
l3_cache *= 512;
- imc_type = 0x0101;
switch(cpu_id.model) {
+ case 1:
+ imc_type = 0x0102;
+ cprint(LINE_CPU, 0, "AMD Fusion @");
+ off = 12;
+ break;
default:
case 2:
+ imc_type = 0x0101;
cprint(LINE_CPU, 0, "AMD K10 (65nm) @");
off = 16;
break;
case 4:
+ imc_type = 0x0101;
cprint(LINE_CPU, 0, "AMD K10 (45nm) @");
off = 16;
break;
case 9:
+ imc_type = 0x0101;
cprint(LINE_CPU, 0, "AMD Magny-Cours");
off = 15;
break;
@@ -913,9 +971,9 @@ void cpu_type(void)
if (((cpu_id.ext >> 16) & 0xF) != 0) {
tsc_invariable = 1;
if(((cpu_id.ext >> 16) & 0xF) > 1) {
- cprint(LINE_CPU, 0, "Intel SNB");
- imc_type = 0x0003;
- off = 9;
+ cprint(LINE_CPU, 0, "Intel Core Gen2");
+ imc_type = 0x0004;
+ off = 15;
} else {
imc_type = 0x0001;
cprint(LINE_CPU, 0, "Intel Core i7");
@@ -1491,3 +1549,4 @@ ulong correct_tsc(ulong el_org)
return el_org;
}
+
diff --git a/jedec_id.h b/jedec_id.h
index 6694c17..e62b343 100644
--- a/jedec_id.h
+++ b/jedec_id.h
@@ -621,7 +621,7 @@ struct spd_jedec_manufacturer jep106[] = {
{ 4, 0xe9, "Century Micro"},
{ 4, 0xea, "Icera Semiconductor"},
{ 4, 0x6b, "Mediaworks Integrated Systems"},
- { 4, 0xec, "O?Neil Product Development"},
+ { 4, 0xec, "O'Neil Product Development"},
{ 4, 0x6d, "Supreme Top Technology"},
{ 4, 0x6e, "MicroDisplay"},
{ 4, 0xef, "Team Group"},
diff --git a/linuxbios.c b/linuxbios.c
index fa34c6a..75d9181 100644
--- a/linuxbios.c
+++ b/linuxbios.c
@@ -115,11 +115,22 @@ int query_linuxbios(void)
struct lb_header *head;
struct lb_record *rec;
struct lb_memory *mem;
+ struct lb_forward *forward;
int i, entries;
+
head = find_lb_table();
if (!head) {
return 0;
}
+
+ /* coreboot also can forward the table to the high tables area. */
+ rec = (struct lb_record *)(((char *)head) + sizeof(*head));
+ if (rec->tag == LB_TAG_FORWARD) {
+ forward = (struct lb_forward *)rec;
+ head = (struct lb_header *)(unsigned long)(forward->forward);
+ if (!head) { return 0; }
+ }
+
mem = 0;
for_each_lbrec(head, rec) {
if (rec->tag == LB_TAG_MEMORY) {
diff --git a/linuxbios_tables.h b/linuxbios_tables.h
index d312173..38f2038 100644
--- a/linuxbios_tables.h
+++ b/linuxbios_tables.h
@@ -56,6 +56,7 @@ struct lb_record {
#define LB_TAG_UNUSED 0x0000
#define LB_TAG_MEMORY 0x0001
+#define LB_TAG_FORWARD 0x0011
struct lb_memory_range {
uint64_t start;
@@ -79,4 +80,10 @@ struct lb_hwrpb {
uint64_t hwrpb;
};
+struct lb_forward {
+ uint32_t tag;
+ uint32_t size;
+ uint64_t forward;
+};
+
#endif /* LINUXBIOS_TABLES_H */
diff --git a/makeiso.sh b/makeiso.sh
index bc1c137..0ed373e 100755
--- a/makeiso.sh
+++ b/makeiso.sh
@@ -37,9 +37,9 @@ cd cd
echo -e "There is nothing to do here\r\r\nMemtest86+ is located on the bootsector of this CD\r\r\n" > README.TXT
echo -e "Just boot from this CD and Memtest86+ will launch" >> README.TXT
-mkisofs -A "MKISOFS 1.1.2" -p "Memtest86+ 4.10" -publisher "Samuel D. <sdemeule@memtest.org>" -b boot/memtest.img -c boot/boot.catalog -V "MT410" -o memtest.iso .
-mv memtest.iso ../mt410.iso
+mkisofs -A "MKISOFS 1.1.2" -p "Memtest86+ 4.20" -publisher "Samuel D. <sdemeule@memtest.org>" -b boot/memtest.img -c boot/boot.catalog -V "MT410" -o memtest.iso .
+mv memtest.iso ../mt420.iso
cd ..
rm -rf cd
-echo "Done! Memtest86+ 4.10 ISO is mt410.iso"
+echo "Done! Memtest86+ 4.20 ISO is mt420.iso"
diff --git a/mt86+_loader b/mt86+_loader
index df62b62..6c77a6f 100644
--- a/mt86+_loader
+++ b/mt86+_loader
Binary files differ
diff --git a/mt86+_loader.asm b/mt86+_loader.asm
index a305400..600ebfa 100644
--- a/mt86+_loader.asm
+++ b/mt86+_loader.asm
@@ -12,8 +12,8 @@
; The good thing is that you get a single file which can be
; compressed, for example with http://upx.sf.net/ (UPX).
-%define fullsize (165080 + buffer - exeh)
- ; 165080 is the size of memtest86+ V4.00, adjust as needed!
+%define fullsize (164504 + buffer - exeh)
+ ; 164504 is the size of memtest86+ V4.20, adjust as needed!
%define stacksize 2048
%define stackpara ((stacksize + 15) / 16)
diff --git a/precomp.bin b/precomp.bin
index e54513b..293e15d 100755
--- a/precomp.bin
+++ b/precomp.bin
Binary files differ
diff --git a/spd.c b/spd.c
index 0cdfe1e..cef93f0 100644
--- a/spd.c
+++ b/spd.c
@@ -3,7 +3,7 @@
*
* Released under version 2 of the Gnu Puclic License
* ----------------------------------------------------
- * MemTest86+ V4.00 Specific code (GPL V2.0)
+ * MemTest86+ V4.20 Specific code (GPL V2.0)
* By Samuel DEMEULEMEESTER, sdemeule@memtest.org
* http://www.canardpc.com - http://www.memtest.org
*/
@@ -123,6 +123,7 @@ struct pci_smbus_controller {
};
static struct pci_smbus_controller smbcontrollers[] = {
+{0x8086, 0x1C22, "Intel P67", ich5_get_smb, ich5_read_spd},
{0x8086, 0x3B30, "Intel P55", ich5_get_smb, ich5_read_spd},
{0x8086, 0x3A60, "Intel ICH10B", ich5_get_smb, ich5_read_spd},
{0x8086, 0x3A30, "Intel ICH10R", ich5_get_smb, ich5_read_spd},
@@ -233,6 +234,7 @@ void get_spd_spec(void)
curcol++;
// Then print module infos (manufacturer & part number)
+ spd[117] &= 0x0F; // Parity odd or even
for (i = 0; jep106[i].cont_code < 9; i++) {
if (spd[117] == jep106[i].cont_code && spd[118] == jep106[i].hex_byte) {
// We are here if a Jedec manufacturer is detected
@@ -459,106 +461,15 @@ struct ascii_map {
char *name;
};
-struct ascii_map amap[] = {
-{ 0x20, " "},
-{ 0x21, "!"},
-{ 0x22, "'"},
-{ 0x23, "#"},
-{ 0x24, "$"},
-{ 0x25, "%"},
-{ 0x26, "&"},
-{ 0x28, "("},
-{ 0x29, ")"},
-{ 0x2A, "*"},
-{ 0x2B, "+"},
-{ 0x2C, ","},
-{ 0x2D, "-"},
-{ 0x2E, "."},
-{ 0x30, "0"},
-{ 0x31, "1"},
-{ 0x32, "2"},
-{ 0x33, "3"},
-{ 0x34, "4"},
-{ 0x35, "5"},
-{ 0x36, "6"},
-{ 0x38, "8"},
-{ 0x39, "9"},
-{ 0x3A, ":"},
-{ 0x3B, ";"},
-{ 0x3C, "<"},
-{ 0x3D, "="},
-{ 0x3E, ">"},
-{ 0x40, "@"},
-{ 0x41, "A"},
-{ 0x42, "B"},
-{ 0x43, "C"},
-{ 0x44, "D"},
-{ 0x45, "E"},
-{ 0x46, "F"},
-{ 0x47, "G"},
-{ 0x48, "H"},
-{ 0x49, "I"},
-{ 0x4A, "J"},
-{ 0x4B, "K"},
-{ 0x4C, "L"},
-{ 0x4D, "M"},
-{ 0x4E, "N"},
-{ 0x4F, "O"},
-{ 0x50, "P"},
-{ 0x51, "Q"},
-{ 0x52, "R"},
-{ 0x53, "S"},
-{ 0x54, "T"},
-{ 0x55, "U"},
-{ 0x56, "V"},
-{ 0x57, "W"},
-{ 0x58, "X"},
-{ 0x59, "Y"},
-{ 0x5A, "Z"},
-{ 0x5B, "["},
-{ 0x5C, "-"},
-{ 0x5D, "]"},
-{ 0x5E, "^"},
-{ 0x60, "`"},
-{ 0x61, "a"},
-{ 0x62, "b"},
-{ 0x63, "c"},
-{ 0x64, "d"},
-{ 0x65, "e"},
-{ 0x66, "f"},
-{ 0x68, "h"},
-{ 0x69, "i"},
-{ 0x6A, "j"},
-{ 0x6B, "k"},
-{ 0x6C, "l"},
-{ 0x6D, "m"},
-{ 0x6E, "n"},
-{ 0x6F, "o"},
-{ 0x70, "p"},
-{ 0x71, "q"},
-{ 0x72, "r"},
-{ 0x73, "s"},
-{ 0x74, "t"},
-{ 0x75, "u"},
-{ 0x76, "v"},
-{ 0x78, "x"},
-{ 0x79, "y"},
-{ 0x7A, "z"},
-{ 0x7B, "{"},
-{ 0x7C, "|"},
-{ 0x7D, "}"},
-{ 0x7E, "~"},
-{ 0, ""}
-};
-char* convert_hex_to_char(unsigned hex_org){
- int i;
-
- for (i = 0; amap[i].hex_code > 0; i++) {
- if (hex_org == amap[i].hex_code) {
- return amap[i].name;
- }
- }
- return "";
-}
+char* convert_hex_to_char(unsigned hex_org) {
+ static char buf[2] = " ";
+ if (hex_org >= 0x20 && hex_org < 0x80) {
+ buf[0] = hex_org;
+ } else {
+ //buf[0] = '\0';
+ buf[0] = ' ';
+ }
+ return buf;
+} \ No newline at end of file