summaryrefslogtreecommitdiff
path: root/sys/src/cmd/ki/mem.c
diff options
context:
space:
mode:
authorTaru Karttunen <taruti@taruti.net>2011-03-30 15:46:40 +0300
committerTaru Karttunen <taruti@taruti.net>2011-03-30 15:46:40 +0300
commite5888a1ffdae813d7575f5fb02275c6bb07e5199 (patch)
treed8d51eac403f07814b9e936eed0c9a79195e2450 /sys/src/cmd/ki/mem.c
Import sources from 2011-03-30 iso image
Diffstat (limited to 'sys/src/cmd/ki/mem.c')
-rwxr-xr-xsys/src/cmd/ki/mem.c240
1 files changed, 240 insertions, 0 deletions
diff --git a/sys/src/cmd/ki/mem.c b/sys/src/cmd/ki/mem.c
new file mode 100755
index 000000000..0ab7d580b
--- /dev/null
+++ b/sys/src/cmd/ki/mem.c
@@ -0,0 +1,240 @@
+#include <u.h>
+#include <libc.h>
+#include <bio.h>
+#include <mach.h>
+#define Extern extern
+#include "sparc.h"
+
+extern ulong textbase;
+
+ulong
+ifetch(ulong addr)
+{
+ uchar *va;
+
+ if(addr&3) {
+ Bprint(bioout, "instruction_address_not_aligned [addr %.8lux]\n", addr);
+ longjmp(errjmp, 0);
+ }
+
+ if(icache.on)
+ updateicache(addr);
+
+ va = vaddr(addr);
+ iprof[(addr-textbase)/PROFGRAN]++;
+
+ va += addr&(BY2PG-1);
+
+ return va[0]<<24 | va[1]<<16 | va[2]<<8 | va[3];
+}
+
+ulong
+getmem_4(ulong addr)
+{
+ ulong val;
+ int i;
+
+ val = 0;
+ for(i = 0; i < 4; i++)
+ val = val<<8 | getmem_b(addr++);
+ return val;
+}
+
+ulong
+getmem_2(ulong addr)
+{
+ ulong val;
+
+ val = getmem_b(addr);
+ val = val<<8 | getmem_b(addr+1);
+
+ return val;
+}
+
+ulong
+getmem_w(ulong addr)
+{
+ uchar *va;
+
+ if(addr&3) {
+ Bprint(bioout, "mem_address_not_aligned [load addr %.8lux]\n", addr);
+ longjmp(errjmp, 0);
+ }
+ if(membpt)
+ brkchk(addr, Read);
+
+ va = vaddr(addr);
+ va += addr&(BY2PG-1);
+
+ return va[0]<<24 | va[1]<<16 | va[2]<<8 | va[3];;
+}
+
+ushort
+getmem_h(ulong addr)
+{
+ uchar *va;
+
+ if(addr&1) {
+ Bprint(bioout, "mem_address_not_aligned [load addr %.8lux]\n", addr);
+ longjmp(errjmp, 0);
+ }
+ if(membpt)
+ brkchk(addr, Read);
+
+ va = vaddr(addr);
+ va += addr&(BY2PG-1);
+
+ return va[0]<<8 | va[1];
+}
+
+uchar
+getmem_b(ulong addr)
+{
+ uchar *va;
+
+ if(membpt)
+ brkchk(addr, Read);
+
+ va = vaddr(addr);
+ va += addr&(BY2PG-1);
+ return va[0];
+}
+
+void
+putmem_w(ulong addr, ulong data)
+{
+ uchar *va;
+
+ if(addr&3) {
+ Bprint(bioout, "mem_address_not_aligned [store addr %.8lux]\n", addr);
+ longjmp(errjmp, 0);
+ }
+
+ va = vaddr(addr);
+ va += addr&(BY2PG-1);
+
+ va[0] = data>>24;
+ va[1] = data>>16;
+ va[2] = data>>8;
+ va[3] = data;
+ if(membpt)
+ brkchk(addr, Write);
+}
+void
+putmem_b(ulong addr, uchar data)
+{
+ uchar *va;
+
+ va = vaddr(addr);
+ va += addr&(BY2PG-1);
+ va[0] = data;
+ if(membpt)
+ brkchk(addr, Write);
+}
+
+void
+putmem_h(ulong addr, short data)
+{
+ uchar *va;
+
+ if(addr&1) {
+ Bprint(bioout, "mem_address_not_aligned [store addr %.8lux]\n", addr);
+ longjmp(errjmp, 0);
+ }
+
+ va = vaddr(addr);
+ va += addr&(BY2PG-1);
+ va[0] = data>>8;
+ va[1] = data;
+ if(membpt)
+ brkchk(addr, Write);
+}
+
+char *
+memio(char *mb, ulong mem, int size, int dir)
+{
+ int i;
+ char *buf, c;
+
+ if(mb == 0)
+ mb = emalloc(size);
+
+ buf = mb;
+ switch(dir) {
+ default:
+ fatal(0, "memio");
+ case MemRead:
+ while(size--)
+ *mb++ = getmem_b(mem++);
+ break;
+ case MemReadstring:
+ for(;;) {
+ if(size-- == 0) {
+ Bprint(bioout, "memio: user/kernel copy too long for mipsim\n");
+ longjmp(errjmp, 0);
+ }
+ c = getmem_b(mem++);
+ *mb++ = c;
+ if(c == '\0')
+ break;
+ }
+ break;
+ case MemWrite:
+ for(i = 0; i < size; i++)
+ putmem_b(mem++, *mb++);
+ break;
+ }
+ return buf;
+}
+
+void *
+vaddr(ulong addr)
+{
+ Segment *s, *es;
+ int off, foff, l, n;
+ uchar **p, *a;
+
+ es = &memory.seg[Nseg];
+ for(s = memory.seg; s < es; s++) {
+ if(addr >= s->base && addr < s->end) {
+ s->refs++;
+ off = (addr-s->base)/BY2PG;
+ p = &s->table[off];
+ if(*p)
+ return *p;
+ s->rss++;
+ switch(s->type) {
+ default:
+ fatal(0, "vaddr");
+ case Text:
+ *p = emalloc(BY2PG);
+ if(seek(text, s->fileoff+(off*BY2PG), 0) < 0)
+ fatal(1, "vaddr text seek");
+ if(read(text, *p, BY2PG) < 0)
+ fatal(1, "vaddr text read");
+ return *p;
+ case Data:
+ *p = emalloc(BY2PG);
+ foff = s->fileoff+(off*BY2PG);
+ if(seek(text, foff, 0) < 0)
+ fatal(1, "vaddr text seek");
+ n = read(text, *p, BY2PG);
+ if(n < 0)
+ fatal(1, "vaddr text read");
+ if(foff + n > s->fileend) {
+ l = BY2PG - (s->fileend-foff);
+ a = *p+(s->fileend-foff);
+ memset(a, 0, l);
+ }
+ return *p;
+ case Bss:
+ case Stack:
+ *p = emalloc(BY2PG);
+ return *p;
+ }
+ }
+ }
+ Bprint(bioout, "data_access_MMU_miss [addr 0x%.8lux]\n", addr);
+ longjmp(errjmp, 0);
+ return 0; /*to stop compiler whining*/
+}