⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 mem.c

📁 这是一个同样来自贝尔实验室的和UNIX有着渊源的操作系统, 其简洁的设计和实现易于我们学习和理解
💻 C
字号:
#include <u.h>#include <libc.h>#include <bio.h>#include <mach.h>#include "arm.h"extern ulong	textbase;ulongifetch(ulong addr){	uchar *va;	if(addr&3) {		Bprint(bioout, "Address error (I-fetch) vaddr %.8lux\n", addr);		longjmp(errjmp, 0);	}	if(icache.on)		updateicache(addr);	iprof[(addr-textbase)/PROFGRAN]++;	va = vaddr(addr);	va += addr&(BY2PG-1);	return va[3]<<24 | va[2]<<16 | va[1]<<8 | va[0];}ulonggetmem_4(ulong addr){	ulong val;	int i;	val = 0;	for(i = 0; i < 4; i++)		val = (val>>8) | (getmem_b(addr++)<<24);	return val;}ulonggetmem_2(ulong addr){	ulong val;	int i;	val = 0;	for(i = 0; i < 2; i++)		val = (val>>8) | (getmem_b(addr++)<<16);	return val;}ulonggetmem_w(ulong addr){	uchar *va;	ulong w;	if(addr&3) {		w = getmem_w(addr & ~3);		while(addr & 3) {			w = (w>>8) | (w<<24);			addr--;		}		return w;	}	if(membpt)		brkchk(addr, Read);	va = vaddr(addr);	va += addr&(BY2PG-1);	return va[3]<<24 | va[2]<<16 | va[1]<<8 | va[0];}ushortgetmem_h(ulong addr){	uchar *va;	ulong w;	if(addr&1) {		w = getmem_h(addr & ~1);		while(addr & 1) {			w = (w>>8) | (w<<8);			addr--;		}		return w;	}	if(membpt)		brkchk(addr, Read);	va = vaddr(addr);	va += addr&(BY2PG-1);	return va[1]<<8 | va[0];}uchargetmem_b(ulong addr){	uchar *va;	if(membpt)		brkchk(addr, Read);	va = vaddr(addr);	va += addr&(BY2PG-1);	return va[0];}voidputmem_h(ulong addr, ushort data){	uchar *va;	if(addr&1) {		Bprint(bioout, "Address error (Store) vaddr %.8lux\n", addr);		longjmp(errjmp, 0);	}	va = vaddr(addr);	va += addr&(BY2PG-1);	va[1] = data>>8;	va[0] = data;	if(membpt)		brkchk(addr, Write);}voidputmem_w(ulong addr, ulong data){	uchar *va;	if(addr&3) {		Bprint(bioout, "Address error (Store) vaddr %.8lux\n", addr);		longjmp(errjmp, 0);	}	va = vaddr(addr);	va += addr&(BY2PG-1);	va[3] = data>>24;	va[2] = data>>16;	va[1] = data>>8;	va[0] = data;	if(membpt)		brkchk(addr, Write);}voidputmem_b(ulong addr, uchar data){	uchar *va;	va = vaddr(addr);	va += addr&(BY2PG-1);	va[0] = 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 arm\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;}voiddotlb(ulong vaddr){	ulong *l, *e;	vaddr &= ~(BY2PG-1);	e = &tlb.tlbent[tlb.tlbsize];	for(l = tlb.tlbent; l < e; l++)		if(*l == vaddr) {			tlb.hit++;			return;		}	tlb.miss++;	tlb.tlbent[lnrand(tlb.tlbsize)] = vaddr;}void *vaddr(ulong addr){	Segment *s, *es;	int off, foff, l, n;	uchar **p, *a;	if(tlb.on)		dotlb(addr);	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, "User TLB miss vaddr 0x%.8lux\n", addr);	longjmp(errjmp, 0);	return 0;		/*to stop compiler whining*/}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -