DevioLab CRYPTO TRADING AUTOMATION
LIVE
AUTOMATED CRYPTO TRADING • BINANCE
Автоматизуйте свій криптопортфель
Торгові боти DevioLab аналізують крипторинок, автоматично відкривають і закривають позиції та керують вашим портфелем на Binance 24/7.
CRYPTO 80 Bots
BINANCE Spot Trading
TRADING 24 / 7
Спробувати DevioLab
deviolab.com

Робота з симулятором машини Ноймана. Дослідження архітектури системи команд

Інформація про навчальний заклад

ВУЗ:
Національний університет Львівська політехніка
Інститут:
Інститут комп’ютерної техніки, автоматики та метрології
Факультет:
Не вказано
Кафедра:
Не вказано

Інформація про роботу

Рік:
2013
Тип роботи:
Звіт
Предмет:
Архітектура комп'ютерів

Частина тексту файла (без зображень, графіків і формул):

МІНІСТЕРСТВО ОСВІТИ І НАУКИ УКРАЇНИ НАЦІОНАЛЬНИЙ УНІВЕРСИТЕТ «ЛЬВІВСЬКА ПОЛІТЕХНІКА» ІНСТИТУТ КОМП’ЮТЕРНОЇ ТЕХНІКИ АВТОМАТИКИ ТА МЕТРОЛОГІЇ ЗВІТ ЛАБОРАТОРНОЇ РОБОТИ №4 З ПРЕДМЕТУ: «Архітектура комп’ютерів» ТЕМА: «Робота з симулятором машини Ноймана. Дослідження архітектури системи команд» Львів – 2012 Мета роботи: зрозуміти принципи виконання архітектури системи команд на симуляторі машини Ноймана, зрозуміти і дослідити виконання інструкції. Завдання: розширити архітектуру систему команд симулятора машини Ноймана, скласти програму на асемблері з розшириним набором команд, перетворити її у машинні коди, запустити симулятор, увести до нього коди машинних, проаналізувати і пояснити отримані результати, довести коректність роботи розширеного набору команд, скласти звіт з виконання лабораторних досліджень та захистити його. Хід роботи: Варіант 18 Побітове логічне І Лістинг програм: asol.c /* Assembler for LC */ #include <stdlib.h> #include <stdio.h> #include <string.h> #define MAXLINELENGTH 1000 #define MAXNUMLABELS 65536 #define MAXLABELLENGTH 7 /* includes the null character termination */ #define ADD 0 #define NAND 1 #define LW 2 #define SW 3 #define BEQ 4 #define JALR 5 #define HALT 6 #define AND 7 int readAndParse(FILE *, char *, char *, char *, char *, char *); int translateSymbol(char labelArray[MAXNUMLABELS][MAXLABELLENGTH], int labelAddress[MAXNUMLABELS], int, char *); int isNumber(char *); void testRegArg(char *); void testAddrArg(char *); int main(int argc, char *argv[]) { char *inFileString, *outFileString; FILE *inFilePtr, *outFilePtr; int address; char label[MAXLINELENGTH], opcode[MAXLINELENGTH], arg0[MAXLINELENGTH], arg1[MAXLINELENGTH], arg2[MAXLINELENGTH], argTmp[MAXLINELENGTH]; int i; int numLabels=0; int num; int addressField; char labelArray[MAXNUMLABELS][MAXLABELLENGTH]; int labelAddress[MAXNUMLABELS]; if (argc != 3) { printf("error: usage: %s <assembly-code-file> <machine-code-file>\n", argv[0]); exit(1); } inFileString = argv[1]; outFileString = argv[2]; inFilePtr = fopen(inFileString, "r"); if (inFilePtr == NULL) { printf("error in opening %s\n", inFileString); exit(1); } outFilePtr = fopen(outFileString, "w"); if (outFilePtr == NULL) { printf("error in opening %s\n", outFileString); exit(1); } /* map symbols to addresses */ /* assume address start at 0 */ for (address=0; readAndParse(inFilePtr, label, opcode, arg0, arg1, arg2); address++) { /* printf("%d: label=%s, opcode=%s, arg0=%s, arg1=%s, arg2=%s\n", address, label, opcode, arg0, arg1, arg2); */ /* check for illegal opcode */ if (strcmp(opcode, "add") && strcmp(opcode, "nand") && strcmp(opcode, "lw") && strcmp(opcode, "sw") && strcmp(opcode, "beq") && strcmp(opcode, "jalr") && strcmp(opcode, "halt") && strcmp(opcode, "and") && strcmp(opcode, ".fill") ) { printf("error: unrecognized opcode %s at address %d\n", opcode, address); exit(1); } /* check register fields */ if (!strcmp(opcode, "add") || !strcmp(opcode, "nand") || !strcmp(opcode, "lw") || !strcmp(opcode, "sw") || !strcmp(opcode, "and") || !strcmp(opcode, "beq") || !strcmp(opcode, "jalr")) { testRegArg(arg0); testRegArg(arg1); } if (!strcmp(opcode, "add") || !strcmp(opcode, "nand") || !strcmp(opcode, "and") ) { testRegArg(arg2); } /* check addressField */ if (!strcmp(opcode, "lw") || !strcmp(opcode, "sw") || !strcmp(opcode, "beq")) { testAddrArg(arg2); } if (!strcmp(opcode, ".fill")) { testAddrArg(arg0); } /* check for enough arguments */ if ( (strcmp(opcode, "halt") && strcmp(opcode, "and") && strcmp(opcode, ".fill") && strcmp(opcode, "jalr") && arg2[0]=='\0') || (!strcmp(opcode, "jalr") && arg1[0]=='\0') || (!strcmp(opcode, ".fill") && arg0[0]=='\0')) { printf("error at address %d: not enough arguments\n", address); exit(2); } if (label[0] != '\0') { /* check for labels that are too long */ if (strlen(label) >= MAXLABELLENGTH) { printf("label too long\n"); exit(2); } /* make sure label starts with letter */ if (! sscanf(label, "%[a-zA-Z]", argTmp) ) { printf("label doesn't start with letter\n"); exit(2); } /* make sure label consists of only letters and numbers */ sscanf(label, "%[a-zA-Z0-9]", argTmp); if (strcmp(argTmp, label)) { printf("label has character other than letters and numbers\n"); exit(2); } /* look for duplicate label */ for (i=0; i<numLabels; i++) { if (!strcmp(label, labelArray[i])) { printf("error: duplicate label %s at address %d\n", label, address); exit(1); } } /* see if there are too many labels */ if (numLabels >= MAXNUMLABELS) { printf("error: too many labels (label=%s)\n", label); exit(2); } strcpy(labelArray[numLabels], label); labelAddress[numLabels++] = address; } } for (i=0; i<numLabels; i++) { /* printf("%s = %d\n", labelArray[i], labelAddress[i]); */ } /* now do second pass (print machine code, with symbols filled in as addresses) */ rewind(inFilePtr); for (address=0; readAndParse(inFilePtr, label, opcode, arg0, arg1, arg2); address++) { if (!strcmp(opcode, "add")) { num = (ADD << 22) | (atoi(arg0) << 19) | (atoi(arg1) << 16) | atoi(arg2); } else if (!strcmp(opcode, "nand")) { num = (NAND << 22) | (atoi(arg0) << 19) | (atoi(arg1) << 16) | atoi(arg2); } else if (!strcmp(opcode, "jalr")) { num = (JALR << 22) | (atoi(arg0) << 19) | (atoi(arg1) << 16); } else if (!strcmp(opcode, "halt")) { num = (HALT << 22); } else if (!strcmp(opcode, "and")) { num = (AND << 22) | (atoi(arg0) << 19) | (atoi(arg1) << 16) | atoi(arg2); } else if (!strcmp(opcode, "lw") || !strcmp(opcode, "sw") || !strcmp(opcode, "beq")) { /* if arg2 is symbolic, then translate into an address */ if (!isNumber(arg2)) { addressField = translateSymbol(labelArray, labelAddress, numLabels, arg2); /* printf("%s being translated into %d\n", arg2, addressField); */ if (!strcmp(opcode, "beq")) { addressField = addressField-address-1; } } else { addressField = atoi(arg2); } if (addressField < -32768 || addressField > 32767) { printf("error: offset %d out of range\n", addressField); exit(1); } /* truncate the offset field, in case it's negative */ addressField = addressField & 0xFFFF; if (!strcmp(opcode, "beq")) { num = (BEQ << 22) | (atoi(arg0) << 19) | (atoi(arg1) << 16) | addressField; } else { /* lw or sw */ if (!strcmp(opcode, "lw")) { num = (LW << 22) | (atoi(arg0) << 19) | (atoi(arg1) << 16) | addressField; } else { num = (SW << 22) | (atoi(arg0) << 19) | (atoi(arg1) << 16) | addressField; } } } else if (!strcmp(opcode, ".fill")) { if (!isNumber(arg0)) { num = translateSymbol(labelArray, labelAddress, numLabels, arg0); } else { num = atoi(arg0); } } /* printf("(address %d): %d (hex 0x%x)\n", address, num, num); */ fprintf(outFilePtr, "%d\n", num); } exit(0); } /* * Read and parse a line of the assembly-language file. Fields are returned * in label, opcode, arg0, arg1, arg2 (these strings must have memory already * allocated to them). * * Return values: * 0 if reached end of file * 1 if all went well * * exit(1) if line is too long. */ int readAndParse(FILE *inFilePtr, char *label, char *opcode, char *arg0, char *arg1, char *arg2) { char line[MAXLINELENGTH]; char *ptr = line; /* delete prior values */ label[0] = opcode[0] = arg0[0] = arg1[0] = arg2[0] = '\0'; /* read the line from the assembly-language file */ if (fgets(line, MAXLINELENGTH, inFilePtr) == NULL) { /* reached end of file */ return(0); } /* check for line too long */ if (strlen(line) == MAXLINELENGTH-1) { printf("error: line too long\n"); exit(1); } /* is there a label? */ ptr = line; if (sscanf(ptr, "%[^\t\n ]", label)) { /* successfully read label; advance pointer over the label */ ptr += strlen(label); } /* * Parse the rest of the line. Would be nice to have real regular * expressions, but scanf will suffice. */ sscanf(ptr, "%*[\t\n\r ]%[^\t\n\r ]%*[\t\n\r ]%[^\t\n\r ]%*[\t\n\r ]%[^\t\n\r ]%*[\t\n\r ]%[^\t\n\r ]", opcode, arg0, arg1, arg2); return(1); } int translateSymbol(char labelArray[MAXNUMLABELS][MAXLABELLENGTH], int labelAddress[MAXNUMLABELS], int numLabels, char *symbol) { int i; /* search through address label table */ for (i=0; i<numLabels && strcmp(symbol, labelArray[i]); i++) { } if (i>=numLabels) { printf("error: missing label %s\n", symbol); exit(1); } return(labelAddress[i]); } int isNumber(char *string) { /* return 1 if string is a number */ int i; return( (sscanf(string, "%d", &i)) == 1); } /* * Test register argument; make sure it's in range and has no bad characters. */ void testRegArg(char *arg) { int num; char c; if (atoi(arg) < 0 || atoi(arg) > 7) { printf("error: register out of range\n"); exit(2); } if (sscanf(arg, "%d%c", &num, &c) != 1) { printf("bad character in register argument\n"); exit(2); } } /* * Test addressField argument. */ void testAddrArg(char *arg) { int num; char c; /* test numeric addressField */ if (isNumber(arg)) { if (sscanf(arg, "%d%c", &num, &c) != 1) { printf("bad character in addressField\n"); exit(2); } } } ssol.c /* * Instruction-level simulator for the LC */ #include <stdio.h> #include <stdlib.h> #include <string.h> #define NUMMEMORY 65536 /* maximum number of words in memory */ #define NUMREGS 8 /* number of machine registers */ #define MAXLINELENGTH 1000 #define ADD 0 #define NAND 1 #define LW 2 #define SW 3 #define BEQ 4 #define JALR 5 #define HALT 6 #define AND 7 typedef struct stateStruct { int pc; int mem[NUMMEMORY]; int reg[NUMREGS]; int numMemory; } stateType; void printState(stateType *); void run(stateType); int convertNum(int); int main(int argc, char *argv[]) { int i; char line[MAXLINELENGTH]; stateType state; FILE *filePtr; if (argc != 2) { printf("error: usage: %s <machine-code file>\n", argv[0]); exit(1); } /* initialize memories and registers */ for (i=0; i<NUMMEMORY; i++) { state.mem[i] = 0; } for (i=0; i<NUMREGS; i++) { state.reg[i] = 0; } state.pc=0; /* read machine-code file into instruction/data memory (starting at address 0) */ filePtr = fopen(argv[1], "r"); if (filePtr == NULL) { printf("error: can't open file %s\n", argv[1]); perror("fopen"); exit(1); } for (state.numMemory=0; fgets(line, MAXLINELENGTH, filePtr) != NULL; state.numMemory++) { if (state.numMemory >= NUMMEMORY) { printf("exceeded memory size\n"); exit(1); } if (sscanf(line, "%d", state.mem+state.numMemory) != 1) { printf("error in reading address %d\n", state.numMemory); exit(1); } printf("memory[%d]=%d\n", state.numMemory, state.mem[state.numMemory]); } printf("\n"); /* run never returns */ run(state); return(0); } void run(stateType state) { int arg0, arg1, arg2, addressField; int instructions=0; int opcode; int maxMem=-1; /* highest memory address touched during run */ for (; 1; instructions++) { /* infinite loop, exits when it executes halt */ printState(&state); if (state.pc < 0 || state.pc >= NUMMEMORY) { printf("pc went out of the memory range\n"); exit(1); } maxMem = (state.pc > maxMem)?state.pc:maxMem; /* this is to make the following code easier to read */ opcode = state.mem[state.pc] >> 22; arg0 = (state.mem[state.pc] >> 19) & 0x7; arg1 = (state.mem[state.pc] >> 16) & 0x7; arg2 = state.mem[state.pc] & 0x7; /* only for add, nand */ addressField = convertNum(state.mem[state.pc] & 0xFFFF); /* for beq, lw, sw */ state.pc++; if (opcode == ADD) { state.reg[arg2] = state.reg[arg0] + state.reg[arg1]; } else if (opcode == NAND) { state.reg[arg2] = ~(state.reg[arg0] & state.reg[arg1]); } else if (opcode == LW) { if (state.reg[arg0] + addressField < 0 || state.reg[arg0] + addressField >= NUMMEMORY) { printf("address out of bounds\n"); exit(1); } state.reg[arg1] = state.mem[state.reg[arg0] + addressField]; if (state.reg[arg0] + addressField > maxMem) { maxMem = state.reg[arg0] + addressField; } } else if (opcode == SW) { if (state.reg[arg0] + addressField < 0 || state.reg[arg0] + addressField >= NUMMEMORY) { printf("address out of bounds\n"); exit(1); } state.mem[state.reg[arg0] + addressField] = state.reg[arg1]; if (state.reg[arg0] + addressField > maxMem) { maxMem = state.reg[arg0] + addressField; } } else if (opcode == BEQ) { if (state.reg[arg0] == state.reg[arg1]) { state.pc += addressField; } } else if (opcode == JALR) { state.reg[arg1] = state.pc; if(arg0 != 0) state.pc = state.reg[arg0]; else state.pc = 0; } //////////////////////////////////////////// else if (opcode == AND) { state.reg[arg2] = (state.reg[arg0] & state.reg[arg1]); } //////////////////////////////////////////// else if (opcode == HALT) { printf("machine halted\n"); printf("total of %d instructions executed\n", instructions+1); printf("final state of machine:\n"); printState(&state); exit(0); } else { printf("error: illegal opcode 0x%x\n", opcode); exit(1); } state.reg[0] = 0; } } void printState(stateType *statePtr) { int i; printf("\n@@@\nstate:\n"); printf("\tpc %d\n", statePtr->pc); printf("\tmemory:\n"); for (i=0; i<statePtr->numMemory; i++) { printf("\t\tmem[ %d ] %d\n", i, statePtr->mem[i]); } printf("\tregisters:\n"); for (i=0; i<NUMREGS; i++) { printf("\t\treg[ %d ] %d\n", i, statePtr->reg[i]); } printf("end state\n"); } int convertNum(int num) { /* convert a 16-bit number into a 32-bit Sun integer */ if (num & (1<<15) ) { num -= (1<<16); } return(num); } Зміст файлу 1.as: start lw 0 1 var1 lw 0 2 var2 and 1 2 3 halt var1 .fill 6 var2 .fill 3 stAddr .fill start Зміст файлу 1.mc: 8454148 8519685 30015491 25165824 6 3 2 Файл report.txt memory[0]=8454148 memory[1]=8519685 memory[2]=30015491 memory[3]=25165824 memory[4]=6 memory[5]=3 memory[6]=2 @@@ state: pc 0 memory: mem[ 0 ] 8454148 mem[ 1 ] 8519685 mem[ 2 ] 30015491 mem[ 3 ] 25165824 mem[ 4 ] 6 mem[ 5 ] 3 mem[ 6 ] 2 registers: reg[ 0 ] 0 reg[ 1 ] 0 reg[ 2 ] 0 reg[ 3 ] 0 reg[ 4 ] 0 reg[ 5 ] 0 reg[ 6 ] 0 reg[ 7 ] 0 end state @@@ state: pc 1 memory: mem[ 0 ] 8454148 mem[ 1 ] 8519685 mem[ 2 ] 30015491 mem[ 3 ] 25165824 mem[ 4 ] 6 mem[ 5 ] 3 mem[ 6 ] 2 registers: reg[ 0 ] 0 reg[ 1 ] 6 reg[ 2 ] 0 reg[ 3 ] 0 reg[ 4 ] 0 reg[ 5 ] 0 reg[ 6 ] 0 reg[ 7 ] 0 end state @@@ state: pc 2 memory: mem[ 0 ] 8454148 mem[ 1 ] 8519685 mem[ 2 ] 30015491 mem[ 3 ] 25165824 mem[ 4 ] 6 mem[ 5 ] 3 mem[ 6 ] 2 registers: reg[ 0 ] 0 reg[ 1 ] 6 reg[ 2 ] 3 reg[ 3 ] 0 reg[ 4 ] 0 reg[ 5 ] 0 reg[ 6 ] 0 reg[ 7 ] 0 end state @@@ state: pc 3 memory: mem[ 0 ] 8454148 mem[ 1 ] 8519685 mem[ 2 ] 30015491 mem[ 3 ] 25165824 mem[ 4 ] 6 mem[ 5 ] 3 mem[ 6 ] 2 registers: reg[ 0 ] 0 reg[ 1 ] 6 reg[ 2 ] 3 reg[ 3 ] 2 reg[ 4 ] 0 reg[ 5 ] 0 reg[ 6 ] 0 reg[ 7 ] 0 end state machine halted total of 4 instructions executed final state of machine: @@@ state: pc 4 memory: mem[ 0 ] 8454148 mem[ 1 ] 8519685 mem[ 2 ] 30015491 mem[ 3 ] 25165824 mem[ 4 ] 6 mem[ 5 ] 3 mem[ 6 ] 2 registers: reg[ 0 ] 0 reg[ 1 ] 6 reg[ 2 ] 3 reg[ 3 ] 2 reg[ 4 ] 0 reg[ 5 ] 0 reg[ 6 ] 0 reg[ 7 ] 0 end state Висновок: виконавши дану лабораторну роботу, я зрозуміла принципи виконання архітектури системи команд на симуляторі машини Ноймана, зрозуміла і дослідила виконання інструкції.
Антиботан аватар за замовчуванням

21.10.2013 21:49

Коментарі

Ви не можете залишити коментар. Для цього, будь ласка, увійдіть або зареєструйтесь.

Ділись своїми роботами та отримуй миттєві бонуси!

Нічого не вибрано
0%

Оголошення від адміністратора

Антиботан аватар за замовчуванням

Подякувати Студентському архіву довільною сумою

Admin

26.02.2023 12:38

Дякуємо, що користуєтесь нашим архівом!