-1

这将是一个大问题(至少对我来说似乎是这样),所以请耐心等待。我们正在用 C 语言制作一个 y86 模拟器,这部分任务应该打开一个文件,将其加载到内存中,执行转储,然后退出。提供了 main 方法来做这些事情,我们只是应该创建 loader.c 和 loader.h 文件来实际执行加载。如果加载成功(输入文件没有错误),加载函数返回 true(1),否则返回 false(0)。现在,我被困在加载功能上,我认为问题出在 loader.c 的第 58-67 行左右。我没有正确调用该方法,但我无法弄清楚如何正确格式化数字。这是我第一次在 C 中工作,所以对我来说仍然相当混乱。如果需要,我可以提供更多代码。到目前为止,我已经包含了 loader.c,loader.h、memory.c 和 memory.h。Bool.h 包括在内,但它只是真假的 typedef,所以我想我可以把它排除在外。如果这有点多,我很抱歉,但我完全被难住了,我不知道还能去哪里。非常感谢您提供的任何帮助,我们将不胜感激!

装载机.c:

1   #include <stdio.h>
2   #include <string.h>
3   #include "loader.h"
4   #include "bool.h"
5   #include "memory.h"
6  
7   bool checkAddressFormat (char addressArray[]);
8   bool checkDataFormat(char dataArray[]);
9   bool isDigit(char character); 
10  bool checkLine(char inputLine[]);
11 
12  int load(int argc, char *argv[]){
13 
14      if (argc != 2){
15          printf("file opening failed \nusage: yess <filename>.yo\n");
16          return 0;
17      }
18      else{
19          //Checks that all the files exist
20          FILE* file = fopen(argv[1], "r" );
21          char* ext;
22          ext = strrchr(argv[1], '.'); //Grab extension
23          if (file == 0 || strcmp(ext,".yo") != 0) {
24              printf("file opening failed \nusage: yess <filename>.yo\n");
25              return 0;
26          }
27         else{
28             char inputLine[250]; //The current line being used
29             int intLine[250];
30             int ch;
31             int i;
32             int j;
33             int k;
34             int m;
35             bool lineCheck;
36             bool memError = FALSE;
37             int byteAddress;
38             int lineNumber = 1;
39             
40             ch = fgetc(file); //Grab first character
41             while (!feof(file)) //While file is not empty
42             {
43                 while(ch != '\n'){
44                     inputLine[i] = ch;
45                     intLine[i] = ch;
46                     ch = fgetc(file);
47                 }
48                 char addressString[4];
49                 addressString[3] = '\0';
50                 for(j = 0; j < 3; j++){ //Creates char array of address on current line.
51                      addressString[j] = inputLine[j+4];
52                 }
53                 byteAddress = atoi(addressString); //Turns the array into an int to pass to putByte
54 
55                 unsigned char dataString[12];
56                 for(k = 0; k < 12; k++) {
57                      dataString[k] = (unsigned char)intLine[k+9];
58                 }
59 
60                 if(checkLine(inputLine) == FALSE){
61                     printf("Error on line %d:\n",lineNumber);
62                     printf("%s\n",inputLine);
63                     return 0;
64                 }
65                 
66                 else{
67                     for(m = 0; m < 250; m++) {
68                         putByte(byteAddress, dataString[m], &memError);
69                     }
70                     printf("call putByte");
71                 }
72 
73                 for(i = 0; i < 250; i++){
74                     inputLine[i] = ' ';
75                     intLine[i] = ' ';
76                 }
77                 printf("clear arrays");
78                 lineNumber++;
79                 ch = fgetc(file);
80             }
81         }
82         close(file);
83      }
84      return 1;
85  }
86 
87  bool checkLine(char inputLine[]){
88      
89      if(checkDataFormat(inputLine) == FALSE || checkAddressFormat(inputLine) == FALSE){
90          return FALSE;
91      }
92      else if(inputLine[22] != '|'){
93          return FALSE;
94      }
95      else {
96          return TRUE;
97      }
98 
99  }
100 bool checkDataFormat(char dataArray[]) {
101     int i;
102     bool temp;
103     int counter = 0;
104     for(i = 9; i <= 20; i++) {
105         temp = isDigit(dataArray[i]);
106         if(temp  == TRUE){
107             counter++;
108         }
109     }
110     if(counter > 12){
111         return FALSE;
112     }
113     else{
114         return TRUE;
115     }
116 }
117
118 bool checkAddressFormat(char addressArray[]) {
119     if(isDigit(addressArray[2]) == FALSE || isDigit(addressArray[4]) == FALSE || isDigit(addressArray[5])  == FALSE || isDigit(addressArray[6]) == FALSE)
120         return FALSE;
121     if(addressArray[3] != 'x')
122         return FALSE;
123     if(addressArray[7] != ':')
124         return FALSE;
125     else
126         return TRUE;
127 }
128
129 bool isDigit(char character) {
130     if(character == '0' || character == '1' || character == '2' || character == '3' ||
131        character == '4' || character == '5' || character == '6' || character == '7' ||
132        character == '8' || character == '9' || character == 'a' || character == 'b' ||
133       character == 'c' || character == 'd' || character == 'e' || character == 'f')
134       return TRUE;
135    else
136        return FALSE;
137}
138

装载机.h:

1    #ifndef LOADER_H
2    #define LOADER_H
3
4    int load(int argc, char *argv[]);
5
6    #endif

内存.c:

1   #define MEMSIZE 1024     //1024 words of memory
2   #ifndef MEMORY_H
3   #define MEMORY_H
4   #include "bool.h"
5 
6   static unsigned int memArray[MEMSIZE];
7 
8 
9   unsigned int fetch(int address, bool * memError){
10   
11      if(address < 0 || address > 1024)
12          (*memError) = TRUE;
13      else{
14          (*memError) = FALSE;
15          return memArray[address];
16      }
17  }
18
19  void store(int address, unsigned int value, bool * memError){
20      if(address < 0 || address > 1024)
21          (*memError) = TRUE;
22      else{
23          (*memError) = FALSE;
24          memArray[address] = value;
25      }
26  }
27
28  unsigned char getByte(int byteAddress, bool * memError){
29      if(byteAddress < 0 || byteAddress > 4095){
30          (*memError) = TRUE;
31          return 0;
32      }
33      else{
34          (*memError) = FALSE;
35          int wordAddress = fetch((byteAddress/4), memError);
36          char * x = (char*)&wordAddress;
37          char temp = x[(byteAddress%4)];
38          return temp;
39      }
40  }
41  void putByte(int byteAddress, unsigned char value, bool * memError){
42      if(byteAddress < 0 || byteAddress > 4095)
43          (*memError) = TRUE;
44      else{
45          (*memError) = FALSE;
46          int wordAddress = fetch((byteAddress/4), memError);
47          char * x = (char*)&wordAddress;
48          x[(byteAddress%4)] = value;
49          store(byteAddress/4, wordAddress, memError);
50      }
51  }
52  void clearMemory(){
53
54      int i;
55      for(i=0;i<MEMSIZE;i++){
56          memArray[i] = 0;
57      }
58
59  }
60  //Address must be multiple of 4
61  unsigned int getWord(int byteAddress, bool * memError){
62
63      if(byteAddress < 0 || byteAddress > 4095 || (byteAddress%4) != 0){
64          (*memError) = TRUE;
65          return 0;
66      }
67      else{
68          int word = fetch(byteAddress/4, memError);
69          (*memError) = FALSE;
70          return word;
71      }
72  }
73  //Address must be multiple of 4
74  void putWord(int byteAddress, unsigned int value, bool * memError){
75
76     if(byteAddress < 0 || byteAddress > 4095 || (byteAddress%4) != 0){
77          (*memError) = TRUE;
78      }
79      else{
80          store((byteAddress/4), value, memError);
81          (*memError) = FALSE;
82      }
83   
84
85  }
86  #endif
87
88

内存.h:

1   #define MEMSIZE 1024     //1024 words of memory
2   #ifndef MEMORY_H
3   #define MEMORY_H
4 
5   unsigned int fetch(int address, bool * memError);
6   void store(int address, unsigned int value, bool * memError);
7   unsigned char getByte(int byteAddress, bool * memError);
8   void putByte(int byteAddress, unsigned char value, bool * memError);
9   void clearMemory();
10  unsigned int getWord(int byteAddress, bool * memError);
11  void putWord(int byteAddress, unsigned int value, bool * memError);
12  #endif 
4

1 回答 1

0

你应该仔细检查你的数组。到目前为止,最常见的错误是(a)它们不够长,或者(b)您正在调用一个假定您的字符串/数组为零(null)终止的函数,但尚未添加零. C 中的字符串以空值结尾,任何 C 字符串函数都可以工作。

几个示例问题点...

47                 char addressString[3];
48                 for(j = 0; j < 3; j++){ //Creates char array of address on current line.
49                      addressString[j] = inputLine[j+4];
50                 }
51                 byteAddress = atoi(addressString); //Turns the array into an int to pass to putByte

您正在将输入行中的 3 个字节复制到addressString. 但是这个数组只有足够的空间来保存字符并且没​​有空终止。因此,随后的atoi调用可能会进入永无止境(潜在的段错误)。

这里,dataString是一个字符数组:

53                 unsigned char dataString[12];
54                 for(k = 0; k < 12; k++) {
55                      dataString[k] = (unsigned char)intLine[k+9];
56                 }
57 

在这里,您将dataString其视为单个字符:

58                 unsigned char data = dataString;
59 
60                 if(checkLine(inputLine) == FALSE){
61                     printf("Error on line %d:\n",lineNumber);
62                     printf("%s\n",inputLine);
63                     return 0;
64                 }
65                 
66                 else{
67                     putByte(byteAddress, dataString, &memError);
68                 }

这可能不会导致段错误,但肯定是不正确的。

于 2014-03-24T16:32:38.057 回答