Re: [PATCH] kdb: add rdmsr and wrmsr commands for i386

Bernardo Innocenti <[email protected]>
Newsgroups gmane.linux.laptop.olpc.devel,gmane.linux.kernel.debugging
Organization http://www.codewiz.org/
Message-ID <[email protected]>
Mitch Bradley wrote:
> Bernardo Innocenti wrote:
>> The syntax is:
>>    rdmsr <addr>
>>    wrmsr <addr> <l> <h>
> 
> In the hardware documentation that I have seen, MSR values are 
> conventionally shown as 64-bit numbers.  The <l> <h> ordering will make 
> it necessary to do a mental flip.  The 32-bit pieces of MSR do not have 
> individual addresses, so considerations of endianness are not directly 
> relevant.

I reveresed the order as you asked, but, honestly, I don't like it
very much either way :-)

Here's the patch again:

From d03f36a5cbe079de855ef83625dbb26f11f3a2bf Mon Sep 17 00:00:00 2001
From: Bernardo Innocenti <[email protected]>
Date: Tue, 15 May 2007 15:29:48 -0400
Subject: [PATCH] kdb: add rdmsr and wrmsr commands for i386

The syntax is:
  rdmsr <addr>
  wrmsr <addr> <h> <l>

Signed-off-by: Bernardo Innocenti <[email protected]>
---
 arch/i386/kdb/kdbasupport.c |   48 +++++++++++++++++++++++++++++++++++++++---
 kdb/kdbmain.c               |    3 +-
 2 files changed, 45 insertions(+), 6 deletions(-)

diff --git a/arch/i386/kdb/kdbasupport.c b/arch/i386/kdb/kdbasupport.c
index 482b319..5109db9 100644
--- a/arch/i386/kdb/kdbasupport.c
+++ b/arch/i386/kdb/kdbasupport.c
@@ -223,6 +223,47 @@ kdba_removedbreg(kdb_bp_t *bp)
 	kdba_putdr7(dr7);
 }
 
+static int
+kdba_rdmsr(int argc, const char **argv)
+{
+	unsigned long addr;
+	uint64_t val;
+	int diag;
+
+	if (argc != 1) {
+		return KDB_ARGCOUNT;
+	}
+
+	if ((diag = kdbgetularg(argv[1], &addr)))
+		return diag;
+
+	kdb_printf("msr(0x%lx) = ", addr);
+	rdmsrl(addr, val);
+	kdb_printf("0x%llx\n", val);
+
+	return 0;
+}
+
+static int
+kdba_wrmsr(int argc, const char **argv)
+{
+	unsigned long addr;
+	unsigned long l, h;
+	int diag;
+
+	if (argc != 3)
+		return KDB_ARGCOUNT;
+
+	if ((diag = kdbgetularg(argv[1], &addr))
+			|| (diag = kdbgetularg(argv[2], &h))
+			|| (diag = kdbgetularg(argv[3], &l)))
+		return diag;
+
+	wrmsr(addr, l, h);
+
+	return 0;
+}
+
 
 /*
  * kdba_getregcontents
@@ -474,12 +515,11 @@ kdba_setregcontents(const char *regname,
  *	argument is NULL (struct pt_regs).   The alternate register
  *	set types supported by this function:
  *
- *	d 		Debug registers
+ *	d		Debug registers
  *	c		Control registers
  *	u		User registers at most recent entry to kernel
  *			for the process currently selected with "pid" command.
  * Following not yet implemented:
- *	m		Model Specific Registers (extra defines register #)
  *	r		Memory Type Range Registers (extra defines register)
  */
 
@@ -546,8 +586,6 @@ kdba_dumpregs(struct pt_regs *regs,
 			   cr[0], cr[1], cr[2], cr[3], cr[4]);
 		return 0;
 	}
-	case 'm':
-		break;
 	case 'r':
 		break;
 	default:
@@ -899,6 +937,8 @@ kdba_init(void)
 {
 	kdb_register("pt_regs", kdba_pt_regs, "address", "Format struct pt_regs", 0);
 	kdb_register("stackdepth", kdba_stackdepth, "[percentage]", "Print processes using >= stack percentage", 0);
+	kdb_register("rdmsr", kdba_rdmsr, "<maddr>", "Display Model Specific Register", 0);
+	kdb_register("wrmsr", kdba_wrmsr, "<maddr> <h> <l>", "Modify Model Specific Register", 0);
 
 	return;
 }
diff --git a/kdb/kdbmain.c b/kdb/kdbmain.c
index 0b2cb91..88bf14f 100644
--- a/kdb/kdbmain.c
+++ b/kdb/kdbmain.c
@@ -2596,8 +2596,7 @@ kdb_rd(int argc, const char **argv)
  *	none.
  * Remarks:
  *	Currently doesn't allow modification of control or
- *	debug registers, nor does it allow modification
- *	of model-specific registers (MSR).
+ *	debug registers.
  */
 
 static int
-- 
1.5.0.2


-- 
   // Bernardo Innocenti
 \X/  http://www.codewiz.org/
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.