Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,8 @@
欄位 | 內容
-----|--------
學期 | 111 學年度下學期
學生 | xxx
學號末兩碼 | xx
學生 | 黃柏鈞
學號末兩碼 | 20
教師 | [陳鍾誠](https://www.nqu.edu.tw/educsie/index.php?act=blog&code=list&ids=4)
學校科系 | [金門大學資訊工程系](https://www.nqu.edu.tw/educsie/index.php)
課程內容 | https://github.com/ccc111b/sp/
11 changes: 11 additions & 0 deletions homework/Makefile
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
CC := gcc
CFLAGS = -std=c99 -O0
TARGET = compiler

all: $(TARGET)

$(TARGET): lexer.c compiler.c main.c
$(CC) $(CFLAGS) $^ -o $@

clean:
rm -f *.o *.exe
146 changes: 146 additions & 0 deletions homework/compiler.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,146 @@
#include <assert.h>
#include "compiler.h"

int E();
void STMT();
void IF();
void BLOCK();

int tempIdx = 0, labelIdx = 0;

#define nextTemp() (tempIdx++)
#define nextLabel() (labelIdx++)
#define emit printf

int isNext(char *set) {
char eset[SMAX], etoken[SMAX];
sprintf(eset, " %s ", set);
sprintf(etoken, " %s ", tokens[tokenIdx]);
return (tokenIdx < tokenTop && strstr(eset, etoken) != NULL);
}

int isEnd() {
return tokenIdx >= tokenTop;
}

char *next() {
// printf("token[%d]=%s\n", tokenIdx, tokens[tokenIdx]);
return tokens[tokenIdx++];
}

char *skip(char *set) {
if (isNext(set)) {
return next();
} else {
printf("skip(%s) got %s fail!\n", set, next());
assert(0);
}
}

// F = (E) | Number | Id
int F() {
int f;
if (isNext("(")) { // '(' E ')'
next(); // (
f = E();
next(); // )
} else { // Number | Id
f = nextTemp();
char *item = next();
emit("t%d = %s\n", f, item);
}
return f;
}

// E = F (op E)*
int E() {
int i1 = F();
while (isNext("+ - * / & | ! < > =")) {
char *op = next();
int i2 = E();
int i = nextTemp();
emit("t%d = t%d %s t%d\n", i, i1, op, i2);
i1 = i;
}
return i1;
}

// ASSIGN = id '=' E;
void ASSIGN() {
char *id = next();
skip("=");
int e = E();
skip(";");
emit("%s = t%d\n", id, e);
}

// WHILE = while (E) STMT
void WHILE() {
int whileBegin = nextLabel();
int whileEnd = nextLabel();
emit("(L%d)\n", whileBegin);
skip("while");
skip("(");
int e = E();
emit("if not T%d goto L%d\n", e, whileEnd);
skip(")");
STMT();
emit("goto L%d\n", whileBegin);
emit("(L%d)\n", whileEnd);
}

//do WHILE = STMT while (E)
void DOWHILE() {
int dowhileBegin = nextLabel();
int dowhileEnd = nextLabel();
emit("(L%d)\n", dowhileBegin);
skip("do");
STMT();
skip("while");
skip("(");
int e = E();
emit("if not T%d goto L%d\n", e, dowhileEnd);
skip(")");
skip(";");
emit("goto L%d\n", dowhileBegin);
emit("(L%d)\n", dowhileEnd);
}

// STMT = WHILE | BLOCK | ASSIGN
void STMT() {
if (isNext("while"))
WHILE();
// else if (isNext("if"))
// IF();
else if(isNext("do"))
DOWHILE();
else if (isNext("{"))
BLOCK();
else
ASSIGN();
}

// STMTS = STMT*
void STMTS() {
while (!isEnd() && !isNext("}")) {
STMT();
}
}

// BLOCK = { STMTS }
void BLOCK() {
skip("{");
STMTS();
skip("}");
}

// PROG = STMTS
void PROG() {
STMTS();
}

void parse() {
printf("============ parse =============\n");
tokenIdx = 0;
PROG();
}
27 changes: 27 additions & 0 deletions homework/compiler.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
#ifndef __COMPILER_H__
#define __COMPILER_H__

#include <stdio.h>
#include <string.h>
#include <ctype.h>

#define TMAX 10000000
#define SMAX 100000

enum { Id, Int, Keyword, Literal, Char };

extern char *typeName[];

extern char code[];
extern char strTable[], *strTableEnd;
extern char *tokens[], tokenTop, tokenIdx;
extern int types[];

#define isDigit(ch) ((ch) >= '0' && (ch) <='9')

#define isAlpha(ch) (((ch) >= 'a' && (ch) <='z') || ((ch) >= 'A' && (ch) <= 'Z'))

void lex(char *text);
void parse();

#endif
4 changes: 4 additions & 0 deletions homework/dowhile.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
i = 1;
do{
i = i + 1;
}while (i<10);
17 changes: 17 additions & 0 deletions homework/integrate.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
#include <stdio.h>

double integrate(double (*f)(double), double a, double b) {
double area = 0.0;
for(double x = a;x <= b;x += 0.001){
area += f(x) * 0.001;
}
return area;
}

double square(double x) {
return x*x;
}

int main() {
printf("integrate(square, 0.0, 2.0)=%f\n", integrate(square, 0.0, 2.0));
}
50 changes: 50 additions & 0 deletions homework/lexer.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
#include "compiler.h"

#define TMAX 10000000
#define LMAX 100

char *typeName[5] = {"Id", "Int", "Keyword", "Literal", "Char"};
char code[TMAX], *p;
char strTable[TMAX], *strTableEnd=strTable;
char *tokens[TMAX], tokenTop=0, tokenIdx=0, token[LMAX];

char *scan() {
while (isspace(*p)) p++;

char *start = p;
int type;
if (*p == '\0') return NULL;
if (*p == '"') {
p++;
while (*p != '"') p++;
p++;
type = Literal;
} else if (*p >='0' && *p <='9') { // 數字
while (*p >='0' && *p <='9') p++;
type = Int;
} else if (isAlpha(*p) || *p == '_') { // 變數名稱或關鍵字
while (isAlpha(*p) || isDigit(*p) || *p == '_') p++;
type = Id;
} else { // 單一字元
p++;
type = Char;
}
int len = p-start;
strncpy(token, start, len);
token[len] = '\0';
return token;
}

void lex(char *code) {
printf("========== lex ==============\n");
p = code;
tokenTop = 0;
while (1) {
char *tok = scan();
if (tok == NULL) break;
strcpy(strTableEnd, tok);
tokens[tokenTop++] = strTableEnd;
strTableEnd += (strlen(tok)+1);
printf("token=%s\n", tok);
}
}
25 changes: 25 additions & 0 deletions homework/main.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
#include "compiler.h"

int readText(char *fileName, char *text, int size) {
FILE *file = fopen(fileName, "r");
int len = fread(text, 1, size, file);
text[len] = '\0';
fclose(file);
return len;
}

void dump(char *strTable[], int top) {
printf("========== dump ==============\n");
for (int i=0; i<top; i++) {
printf("%d:%s\n", i, strTable[i]);
}
}

int main(int argc, char * argv[]) {
readText(argv[1], code, TMAX);
puts(code);
lex(code);
dump(tokens, tokenTop);
parse();
return 0;
}
9 changes: 9 additions & 0 deletions pp.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
#include <stdio.h>

int main() {
int a = 5;
int *p = &a;
int **pp = &p;
**pp = 10;
printf("a=%d\n", a);
}
10 changes: 10 additions & 0 deletions test.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
#include<stdio.h>
int main(void){
int a = 5;
int *b = &a;
*b = 10;

printf("%d\n", a);
printf("%p\n", b); //未設定*b的記憶體地址
printf("%p", a);
}
26 changes: 26 additions & 0 deletions 期中作業/LICENSE
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
mini-riscv-os is freely redistributable under the two-clause BSD License:

Copyright (C) 2015-2018 National Quemoy University, Taiwan.
All rights reserved.

Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions
are met:

1. Redistributions of source code must retain the above copyright notice,
this list of conditions and the following disclaimer.
2. Redistributions in binary form must reproduce the above copyright notice,
this list of conditions and the following disclaimer in the documentation
and/or other materials provided with the distribution.

THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE
LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
THE POSSIBILITY OF SUCH DAMAGE.
Loading