• R/O
  • HTTP
  • SSH
  • HTTPS

提交

标签
No Tags

Frequently used words (click to add to your profile)

javac++androidlinuxc#windowsobjective-ccocoa誰得qtpythonphprubygameguibathyscaphec計画中(planning stage)翻訳omegatframeworktwitterdomtestvb.netdirectxゲームエンジンbtronarduinopreviewer

Commit MetaInfo

修订版e4fe345de00bbcd56ad3a242ac6c95fda7085109 (tree)
时间2014-07-05 19:32:30
作者hikarupsp <hikarupsp@user...>
Commiterhikarupsp

Log Message

起動時にレジスタにファイルをデータとして割り付けることができるようになった(-bd)
-bd 30 30 10 0 src.txt でHello, worldができる。

更改概述

差异

--- a/chncpu.xcodeproj/project.pbxproj
+++ b/chncpu.xcodeproj/project.pbxproj
@@ -12,6 +12,8 @@
1212 17478D01193F3D0000293791 /* ch4.c in Sources */ = {isa = PBXBuildFile; fileRef = 17478D00193F3D0000293791 /* ch4.c */; };
1313 17478D041940B66700293791 /* opcode.c in Sources */ = {isa = PBXBuildFile; fileRef = 17478D031940B66700293791 /* opcode.c */; };
1414 1786B0941956C18800FD4F7B /* label.c in Sources */ = {isa = PBXBuildFile; fileRef = 1786B0931956C18800FD4F7B /* label.c */; };
15+ 17DD55BB1967992200DA7D82 /* args.c in Sources */ = {isa = PBXBuildFile; fileRef = 17DD55BA1967992200DA7D82 /* args.c */; };
16+ 17E5092A1967F7B00091A22A /* src.txt in CopyFiles */ = {isa = PBXBuildFile; fileRef = 17E509291967F7770091A22A /* src.txt */; };
1517 17F95C01194C8DA70064E1B6 /* bios.c in Sources */ = {isa = PBXBuildFile; fileRef = 17F95C00194C8DA70064E1B6 /* bios.c */; };
1618 /* End PBXBuildFile section */
1719
@@ -22,6 +24,7 @@
2224 dstPath = "";
2325 dstSubfolderSpec = 16;
2426 files = (
27+ 17E5092A1967F7B00091A22A /* src.txt in CopyFiles */,
2528 17478CFE193E2DEB00293791 /* test.hex in CopyFiles */,
2629 );
2730 runOnlyForDeploymentPostprocessing = 0;
@@ -37,6 +40,8 @@
3740 17478D02193F586100293791 /* ch4.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ch4.h; sourceTree = "<group>"; usesTabs = 1; };
3841 17478D031940B66700293791 /* opcode.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = opcode.c; sourceTree = "<group>"; usesTabs = 1; };
3942 1786B0931956C18800FD4F7B /* label.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = label.c; sourceTree = "<group>"; };
43+ 17DD55BA1967992200DA7D82 /* args.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = args.c; sourceTree = "<group>"; };
44+ 17E509291967F7770091A22A /* src.txt */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = src.txt; sourceTree = "<group>"; };
4045 17F95C00194C8DA70064E1B6 /* bios.c */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.c; path = bios.c; sourceTree = "<group>"; };
4146 /* End PBXFileReference section */
4247
@@ -72,6 +77,7 @@
7277 isa = PBXGroup;
7378 children = (
7479 17478CF3193E2A4900293791 /* chncpu.c */,
80+ 17DD55BA1967992200DA7D82 /* args.c */,
7581 17478CFC193E2A7800293791 /* chncpu.h */,
7682 17478D00193F3D0000293791 /* ch4.c */,
7783 17478D02193F586100293791 /* ch4.h */,
@@ -79,6 +85,7 @@
7985 17478D031940B66700293791 /* opcode.c */,
8086 17F95C00194C8DA70064E1B6 /* bios.c */,
8187 1786B0931956C18800FD4F7B /* label.c */,
88+ 17E509291967F7770091A22A /* src.txt */,
8289 );
8390 path = chncpu;
8491 sourceTree = "<group>";
@@ -136,6 +143,7 @@
136143 files = (
137144 1786B0941956C18800FD4F7B /* label.c in Sources */,
138145 17F95C01194C8DA70064E1B6 /* bios.c in Sources */,
146+ 17DD55BB1967992200DA7D82 /* args.c in Sources */,
139147 17478D041940B66700293791 /* opcode.c in Sources */,
140148 17478CF4193E2A4900293791 /* chncpu.c in Sources */,
141149 17478D01193F3D0000293791 /* ch4.c in Sources */,
--- a/chncpu.xcodeproj/xcuserdata/hikaru.xcuserdatad/xcschemes/chncpu.xcscheme
+++ b/chncpu.xcodeproj/xcuserdata/hikaru.xcuserdatad/xcschemes/chncpu.xcscheme
@@ -63,6 +63,10 @@
6363 isEnabled = "YES">
6464 </CommandLineArgument>
6565 <CommandLineArgument
66+ argument = "-bd 30 30 10 0 src.txt "
67+ isEnabled = "YES">
68+ </CommandLineArgument>
69+ <CommandLineArgument
6670 argument = "-f i"
6771 isEnabled = "NO">
6872 </CommandLineArgument>
--- /dev/null
+++ b/chncpu/args.c
@@ -0,0 +1,167 @@
1+//
2+// args.c
3+// chncpu
4+//
5+// Created by 西田 耀 on 2014/07/05.
6+// Copyright (c) 2014年 CHNOSProject. All rights reserved.
7+//
8+
9+#include "chncpu.h"
10+
11+CHNCPU_VMArgs *bindVMArgs(int argc, const char *argv[])
12+{
13+ int nextIndex = 1;
14+ int i;
15+ const char *s;
16+ CHNCPU_VMArgs *args = malloc(sizeof(CHNCPU_VMArgs));
17+ CHNCPU_VMArgs_BindDataTag *bdTag;
18+ if(!args){
19+ puts("bindVMArgs: malloc error.");
20+ exit(EXIT_FAILURE);
21+ }
22+
23+ args->appPath = NULL;
24+ args->VMFlags = 0;
25+ args->bindDatas = 0;
26+
27+ for(; nextIndex < argc;){
28+ s = CHNCPU_VMArgs_GetNextAsString(argc, argv, &nextIndex);
29+ if(strcmp("-e", s) == 0){
30+ args->appPath = CHNCPU_VMArgs_GetNextAsString(argc, argv, &nextIndex);
31+ } else if(strcmp("-f", s) == 0){
32+ s = CHNCPU_VMArgs_GetNextAsString(argc, argv, &nextIndex);
33+ for(;*s != '\0'; s++){
34+ if(*s == 'i'){
35+ args->VMFlags |= CHNCPU_VM_FLAG_PRINT_OPLIST;
36+ } else{
37+ printf("bindVMArgs: unknown flag %c.\n", *s);
38+ argc = 0;
39+ continue;
40+ }
41+ }
42+ } else if(strcmp("-bd", s) == 0){
43+ if(args->bindDatas < sizeof(args->bindData)){
44+ bdTag = &args->bindData[args->bindDatas];
45+ bdTag->pReg = CHNCPU_VMArgs_GetNextAsPRegNum(argc, argv, &nextIndex);
46+ bdTag->iReg = CHNCPU_VMArgs_GetNextAsIRegNum(argc, argv, &nextIndex);
47+ i = CHNCPU_VMArgs_GetNextAsSignedHexValue(argc, argv, &nextIndex);
48+ bdTag->flags = CHNCPU_VMArgs_GetNextAsUnsignedHexValue(argc, argv, &nextIndex);
49+ s = CHNCPU_VMArgs_GetNextAsString(argc, argv, &nextIndex);
50+ bdTag->dataOPTag = CHNCPU_Op_DATA_CreateDataFromFileAsPType(s, i);
51+ if(bdTag->pReg < 0 || bdTag->iReg < 0 || bdTag->flags < 0 || !bdTag->dataOPTag){
52+ puts("Invalid data option (-bd) args.");
53+ argc = 0;
54+ continue;
55+ } else{
56+ args->bindDatas++;
57+ }
58+ } else{
59+ puts("Too many bind data options (-bd).");
60+ argc = 0;
61+ continue;
62+ }
63+ } else{
64+ argc = 0;
65+ continue;
66+ }
67+ }
68+
69+ if(argc < 3){
70+ puts("chncpu:Usage > chncpu [-e appPath] [-f flags] [-bd PRegID IRegID PType flags dataPath]");
71+ exit(EXIT_FAILURE);
72+ }
73+
74+ return args;
75+}
76+
77+int CHNCPU_VMArgs_BindDataToRuntimeEnv(CHNCPU_RuntimeEnvironment *env, CHNCPU_VMArgs *args)
78+{
79+ CHNCPU_VMArgs_BindDataTag *bdTag;
80+ int i;
81+
82+ for(i = 0; i < args->bindDatas; i++){
83+ bdTag = &args->bindData[i];
84+ // データサイズを指定されたIRegに格納
85+ env->iReg[bdTag->iReg] = CHNCPU_Op_DATA_GetDataCount(bdTag->dataOPTag);
86+ env->iRegBits[bdTag->iReg] = CHNCPU_BITS_MAX;
87+ // データタグを指定されたPRegに格納
88+ env->pReg[bdTag->pReg].mindex = CHNCPU_MemoryIndex_INVALID;
89+ env->pReg[bdTag->pReg].opTag = bdTag->dataOPTag;
90+ env->pReg[bdTag->pReg].pindex = 0;
91+ env->pReg[bdTag->pReg].type = CHNCPU_Op_DATA_GetDataType(bdTag->dataOPTag);
92+
93+ }
94+
95+ return 0;
96+}
97+
98+const char *CHNCPU_VMArgs_GetNextAsString(int argc, const char *argv[], int *nextIndex)
99+{
100+ const char *s;
101+ if(*nextIndex < argc){
102+ s = argv[*nextIndex];
103+ (*nextIndex)++;
104+ return s;
105+ }
106+ return NULL;
107+}
108+
109+int CHNCPU_VMArgs_GetNextAsPRegNum(int argc, const char *argv[], int *nextIndex)
110+{
111+ int regNum;
112+
113+ regNum = CHNCPU_VMArgs_GetNextAsUnsignedHexValue(argc, argv, nextIndex);
114+ if(regNum >= 0){
115+ if(regNum < CHNCPU_NUMBER_OF_PREG){
116+ return regNum;
117+ }
118+ (*nextIndex)--;
119+ }
120+ return -1;
121+}
122+
123+int CHNCPU_VMArgs_GetNextAsIRegNum(int argc, const char *argv[], int *nextIndex)
124+{
125+ int regNum;
126+
127+ regNum = CHNCPU_VMArgs_GetNextAsUnsignedHexValue(argc, argv, nextIndex);
128+ if(regNum >= 0){
129+ if(regNum < CHNCPU_NUMBER_OF_IREG){
130+ return regNum;
131+ }
132+ (*nextIndex)--;
133+ }
134+ return -1;
135+}
136+
137+int CHNCPU_VMArgs_GetNextAsUnsignedHexValue(int argc, const char *argv[], int *nextIndex)
138+{
139+ int val;
140+ char *p;
141+
142+ if(*nextIndex < argc){
143+ val = (int)strtol(argv[*nextIndex], &p, 16);
144+ if(argv[*nextIndex] == p || *p != '\0' || val < 0){
145+ return -1;
146+ }
147+ (*nextIndex)++;
148+ return val;
149+ }
150+ return -1;
151+}
152+
153+int CHNCPU_VMArgs_GetNextAsSignedHexValue(int argc, const char *argv[], int *nextIndex)
154+{
155+ int val;
156+ char *p;
157+
158+ if(*nextIndex < argc){
159+ val = (int)strtol(argv[*nextIndex], &p, 16);
160+ if(argv[*nextIndex] == p || *p != '\0'){
161+ return 0;
162+ }
163+ (*nextIndex)++;
164+ return val;
165+ }
166+ return 0;
167+}
--- a/chncpu/chncpu.c
+++ b/chncpu/chncpu.c
@@ -22,6 +22,7 @@ int main(int argc, const char *argv[])
2222 }
2323
2424 CHNCPU_LoadBinaryFromHexStringFilePath(env, vmArgs->appPath);
25+ CHNCPU_VMArgs_BindDataToRuntimeEnv(env, vmArgs);
2526 if(!env->errFlags){
2627 CHNCPU_Execute(env);
2728 }
@@ -29,54 +30,6 @@ int main(int argc, const char *argv[])
2930 return 0;
3031 }
3132
32-CHNCPU_VMArgs *bindVMArgs(int argc, const char *argv[])
33-{
34- int i;
35- const char *s;
36- CHNCPU_VMArgs *args = malloc(sizeof(CHNCPU_VMArgs));
37- if(!args){
38- puts("bindVMArgs: malloc error.");
39- exit(EXIT_FAILURE);
40- }
41-
42- args->appPath = NULL;
43- args->VMFlags = 0;
44-
45- for(i = 0; i < argc; i++){
46- s = argv[i];
47- if(strcmp("-e", s) == 0){
48- i++;
49- if(i < argc){
50- args->appPath = argv[i];
51- } else{
52- argc = 0;
53- }
54- } else if(strcmp("-f", s) == 0){
55- i++;
56- if(i < argc){
57- s = argv[i];
58- for(;*s != '\0'; s++){
59- if(*s == 'i'){
60- args->VMFlags |= CHNCPU_VM_FLAG_PRINT_OPLIST;
61- } else{
62- printf("bindVMArgs: unknown flag %c.\n", *s);
63- argc = 0;
64- }
65- }
66- } else{
67- argc = 0;
68- }
69- }
70- }
71-
72- if(argc < 3){
73- puts("chncpu:Usage > chncpu [-e appPath] [-f flags]");
74- exit(EXIT_FAILURE);
75- }
76-
77- return args;
78-}
79-
8033 void printOpTableWikiDoc(CHNCPU_RuntimeEnvironment *env)
8134 {
8235 int i;
@@ -201,6 +154,7 @@ CHNCPU_RuntimeEnvironment *CHNCPU_CreateRuntimeEnvironment(CHNCPU_OpTableSet *op
201154 env->pReg[i].type = 0;
202155 env->pReg[i].mindex = 0;
203156 env->pReg[i].pindex = 0;
157+ env->pReg[i].opTag = NULL;
204158 }
205159
206160 // ラベル管理初期化
@@ -407,11 +361,16 @@ int CHNCPU_Execute(CHNCPU_RuntimeEnvironment *env)
407361 puts("INVALID-X: Invalid pointer type.");
408362 }
409363 }
410-
411-#if DEBUG_PRINT_IREG_AFTER_EXECUTION
364+
365+#if (DEBUG_PRINT_IREG_AFTER_EXECUTION || DEBUG_PRINT_PREG_AFTER_EXECUTION)
412366 puts("\n< End of execution >");
367+#endif
368+#if DEBUG_PRINT_IREG_AFTER_EXECUTION
413369 CHNCPU_DumpIReg(env);
414370 #endif
371+#if DEBUG_PRINT_PREG_AFTER_EXECUTION
372+ CHNCPU_DumpPReg(env);
373+#endif
415374
416375
417376 return count;
@@ -450,6 +409,28 @@ void CHNCPU_DumpIReg(CHNCPU_RuntimeEnvironment *env)
450409 }
451410 }
452411
412+void CHNCPU_DumpPReg(CHNCPU_RuntimeEnvironment *env)
413+{
414+ int i, regs = 0;
415+
416+ puts(">>> Pointer registers");
417+
418+ for(i = 0; i < CHNCPU_NUMBER_OF_PREG; i++){
419+ if(env->pReg[i].type != CHNCPU_PType_Undefined){
420+ if(env->pReg[i].mindex != CHNCPU_MemoryIndex_INVALID){
421+ printf("P%02X: Type:%2X mem[%d][%d]", i, env->pReg[i].type, env->pReg[i].mindex, env->pReg[i].pindex);
422+ } else{
423+ printf("P%02X: Type:%2X 0x%08X[%d]", i, env->pReg[i].type, (unsigned int)env->pReg[i].opTag, env->pReg[i].pindex);
424+ }
425+ putchar('\n');
426+ regs++;
427+ }
428+ }
429+ if(((regs - 1) & 0xF) != 0xF){
430+ putchar('\n');
431+ }
432+}
433+
453434 int CHNCPU_CHK_IsAvailableBits(CHNCPU_RuntimeEnvironment *env, ch4_uint bits)
454435 {
455436 if(bits > 32){
--- a/chncpu/chncpu.h
+++ b/chncpu/chncpu.h
@@ -17,6 +17,7 @@
1717 // DEBUG Flag
1818 #define DEBUG_PRINT_APPBIN_BEFORE_EXECUTION 0
1919 #define DEBUG_PRINT_IREG_AFTER_EXECUTION 0
20+#define DEBUG_PRINT_PREG_AFTER_EXECUTION 0
2021 #define DEBUG_PRINT_OP_BINDING 0
2122 #define DEBUG_PRINT_OP_EXECUTING 0
2223
@@ -35,6 +36,7 @@
3536 #define CHNCPU_LENGTH_OF_MAIN_MEMORY (64 * 1024) // per Op
3637 #define CHNCPU_SIZE_APPBIN (1024 * 1024 * 1)
3738 #define CHNCPU_OPCODE_INVALID (-1)
39+#define CHNCPU_MemoryIndex_INVALID (-1)
3840 #define CHNCPU_PREFIX_MAX 31
3941
4042 // ErrorCode at compile
@@ -91,6 +93,7 @@ typedef struct _CHNCPU_LABEL_SET CHNCPU_LabelSet;
9193 typedef struct _CHNCPU_POINTER_TAG CHNCPU_PointerTag;
9294 typedef struct _CHNCPU_RUN_TIME_ENVIRONMENT CHNCPU_RuntimeEnvironment;
9395 typedef struct _CHNCPU_VM_ARGS CHNCPU_VMArgs;
96+typedef struct _CHNCPU_VM_ARGS_BIND_DATA_TAG CHNCPU_VMArgs_BindDataTag;
9497
9598 struct _CHNCPU_OP_TAG {
9699 int opCode;
@@ -124,8 +127,9 @@ struct _CHNCPU_LABEL_SET {
124127
125128 struct _CHNCPU_POINTER_TAG {
126129 ch4_sint type; // CHNCPU_PType_xx
127- int mindex;
130+ int mindex; // for label
128131 int pindex;
132+ CHNCPU_OpTag *opTag;
129133 };
130134
131135 struct _CHNCPU_RUN_TIME_ENVIRONMENT {
@@ -144,13 +148,22 @@ struct _CHNCPU_RUN_TIME_ENVIRONMENT {
144148 ch4_uint currentLabel;
145149 };
146150
151+struct _CHNCPU_VM_ARGS_BIND_DATA_TAG {
152+ int pReg, iReg;
153+ int flags;
154+ CHNCPU_OpTag *dataOPTag;
155+};
156+
147157 struct _CHNCPU_VM_ARGS {
148158 const char *appPath;
149159 unsigned int VMFlags;
160+ CHNCPU_VMArgs_BindDataTag bindData[2];
161+ int bindDatas;
150162 };
151163
164+
165+
152166 // @chncpu.c
153-CHNCPU_VMArgs *bindVMArgs(int argc, const char *argv[]);
154167 void printOpTableWikiDoc(CHNCPU_RuntimeEnvironment *env);
155168 int decodeHexString(char *src0, char *src1, unsigned char *dst0, unsigned char *dst1);
156169 CHNCPU_RuntimeEnvironment *CHNCPU_CreateRuntimeEnvironment(CHNCPU_OpTableSet *opSet, CHNCPU_BIOS *bios);
@@ -159,9 +172,19 @@ int CHNCPU_PrepareBinaryForExecution(CHNCPU_RuntimeEnvironment *env);
159172 int CHNCPU_Execute(CHNCPU_RuntimeEnvironment *env);
160173 void CHNCPU_DumpAppBin(CHNCPU_RuntimeEnvironment *env);
161174 void CHNCPU_DumpIReg(CHNCPU_RuntimeEnvironment *env);
175+void CHNCPU_DumpPReg(CHNCPU_RuntimeEnvironment *env);
162176 int CHNCPU_CHK_IsAvailableBits(CHNCPU_RuntimeEnvironment *env, ch4_uint bits);
163177 int CHNCPU_AdjustValueForBit(CHNCPU_RuntimeEnvironment *env, int *value, ch4_uint bit, int prefix);
164178
179+// @args.c
180+CHNCPU_VMArgs *bindVMArgs(int argc, const char *argv[]);
181+int CHNCPU_VMArgs_BindDataToRuntimeEnv(CHNCPU_RuntimeEnvironment *env, CHNCPU_VMArgs *args);
182+const char *CHNCPU_VMArgs_GetNextAsString(int argc, const char *argv[], int *nextIndex);
183+int CHNCPU_VMArgs_GetNextAsPRegNum(int argc, const char *argv[], int *nextIndex);
184+int CHNCPU_VMArgs_GetNextAsIRegNum(int argc, const char *argv[], int *nextIndex);
185+int CHNCPU_VMArgs_GetNextAsUnsignedHexValue(int argc, const char *argv[], int *nextIndex);
186+int CHNCPU_VMArgs_GetNextAsSignedHexValue(int argc, const char *argv[], int *nextIndex);
187+
165188 // @opcode.c
166189 CHNCPU_OpTableSet *CHNCPU_CreateOpTableSet(void);
167190 int CHNCPU_Op_Init(CHNCPU_OpTableSet *env);
@@ -213,7 +236,10 @@ int CHNCPU_Op_DATA_BindOperand(CHNCPU_RuntimeEnvironment *env, CHNCPU_OpTag *op,
213236 int CHNCPU_Op_DATA_Execute(CHNCPU_RuntimeEnvironment *env, CHNCPU_OpTag *op);
214237 int CHNCPU_Op_DATA_PrintCode(CHNCPU_RuntimeEnvironment *env, CHNCPU_OpTag *op, FILE *file);
215238 int CHNCPU_Op_DATA_PrintWikiDoc(int opCode, FILE *file);
239+CHNCPU_OpTag *CHNCPU_Op_DATA_CreateDataFromFileAsPType(const char dataPath[], ch4_sint pType);
216240 int CHNCPU_Op_DATA_ReadAtIndex(CHNCPU_RuntimeEnvironment *env, CHNCPU_OpTag *op, int index);
241+int CHNCPU_Op_DATA_GetDataCount(CHNCPU_OpTag *op);
242+int CHNCPU_Op_DATA_GetDataType(CHNCPU_OpTag *op);
217243 //
218244 int CHNCPU_Op_Prefix2F_PrintWikiDoc(int opCode, FILE *file);
219245
--- a/chncpu/opcode.c
+++ b/chncpu/opcode.c
@@ -304,8 +304,13 @@ int CHNCPU_Op_PLIMM_Execute(CHNCPU_RuntimeEnvironment *env, CHNCPU_OpTag *op)
304304 return -1;
305305 }
306306
307- env->pReg[opCache->r].mindex = label->mindex;
308307 env->pReg[opCache->r].type = label->pType;
308+ env->pReg[opCache->r].mindex = label->mindex;
309+ env->pReg[opCache->r].pindex = 0;
310+
311+ if(0 <= label->mindex && label->mindex < CHNCPU_LENGTH_OF_MAIN_MEMORY){
312+ env->pReg[opCache->r].opTag = &env->mainmemory[label->mindex];
313+ }
309314
310315 if(opCache->r == 0x3F){
311316 if(env->pReg[0x3F].type == CHNCPU_PType_Label){
@@ -523,7 +528,7 @@ int CHNCPU_Op_LMEM_Execute(CHNCPU_RuntimeEnvironment *env, CHNCPU_OpTag *op)
523528 return -1;
524529 }
525530
526- value = CHNCPU_Op_DATA_ReadAtIndex(env, &env->mainmemory[p->mindex], p->pindex);
531+ value = CHNCPU_Op_DATA_ReadAtIndex(env, p->opTag, p->pindex);
527532 if(env->errFlags){
528533 return -1;
529534 }
@@ -1021,16 +1026,75 @@ int CHNCPU_Op_DATA_PrintWikiDoc(int opCode, FILE *file)
10211026
10221027 return 0;
10231028 }
1029+CHNCPU_OpTag *CHNCPU_Op_DATA_CreateDataFromFileAsPType(const char dataPath[], ch4_sint pType)
1030+{
1031+ FILE *fp;
1032+ CHNCPU_OpTag *op;
1033+ CHNCPU_OpCache_DATA *opCache;
1034+ int i;
1035+
1036+ op = malloc(sizeof(CHNCPU_OpTag));
1037+ if(!op){
1038+ return NULL;
1039+ }
1040+ opCache = malloc(sizeof(CHNCPU_OpCache_DATA));
1041+ if(!opCache){
1042+ free(op);
1043+ return NULL;
1044+ }
1045+
1046+ op->opCode = CHNCPU_OP_DATA;
1047+ op->opCache = opCache;
1048+
1049+ opCache->labelID = 0;
1050+ opCache->labelOpt = 0;
1051+ opCache->dataType = pType;
1052+
1053+ fp = fopen(dataPath, "rb");
1054+ if(!fp){
1055+ return NULL;
1056+ }
1057+ fseek(fp, 0, SEEK_END);
1058+
1059+ opCache->rawDataByteSize = (int)ftell(fp);
1060+
1061+ fseek(fp, 0, SEEK_SET);
1062+
1063+ opCache->rawData = malloc(opCache->rawDataByteSize);
1064+ if(!opCache->rawData){
1065+ fclose(fp);
1066+ free(opCache);
1067+ free(op);
1068+ return NULL;
1069+ }
1070+
1071+ if(opCache->dataType == CHNCPU_PType_UINT8){
1072+ opCache->dataCount = opCache->rawDataByteSize;
1073+ for(i = 0; i < opCache->dataCount; i++){
1074+ ((unsigned char *)opCache->rawData)[i] = (unsigned char)fgetc(fp);
1075+ }
1076+ } else{
1077+ free(opCache->rawData);
1078+ fclose(fp);
1079+ free(opCache);
1080+ free(op);
1081+ return NULL;
1082+ }
1083+ fclose(fp);
1084+
1085+ return op;
1086+}
10241087 int CHNCPU_Op_DATA_ReadAtIndex(CHNCPU_RuntimeEnvironment *env, CHNCPU_OpTag *op, int index)
10251088 {
10261089 int retv;
10271090 CHNCPU_OpCache_DATA *opCache;
10281091
1029- opCache = op->opCache;
1030- if(op->opCode != 0x2E || index < 0 || index >= opCache->dataCount){
1092+
1093+ if(!op || op->opCode != CHNCPU_OP_DATA || index < 0 || index >= ((CHNCPU_OpCache_DATA *)op->opCache)->dataCount){
10311094 env->errFlags |= CHNCPU_ERR_X_BAD_ACCESS;
10321095 return 0;
10331096 }
1097+ opCache = op->opCache;
10341098
10351099 if(opCache->dataType == CHNCPU_PType_UINT8){
10361100 retv = ((unsigned char *)opCache->rawData)[index];
@@ -1041,6 +1105,20 @@ int CHNCPU_Op_DATA_ReadAtIndex(CHNCPU_RuntimeEnvironment *env, CHNCPU_OpTag *op,
10411105
10421106 return retv;
10431107 }
1108+int CHNCPU_Op_DATA_GetDataCount(CHNCPU_OpTag *op)
1109+{
1110+ if(!op || op->opCode != CHNCPU_OP_DATA || !op->opCache){
1111+ return -1;
1112+ }
1113+ return ((CHNCPU_OpCache_DATA *)op->opCache)->dataCount;
1114+}
1115+int CHNCPU_Op_DATA_GetDataType(CHNCPU_OpTag *op)
1116+{
1117+ if(!op || op->opCode != CHNCPU_OP_DATA || !op->opCache){
1118+ return 0;
1119+ }
1120+ return ((CHNCPU_OpCache_DATA *)op->opCache)->dataType;
1121+}
10441122
10451123 //
10461124 // Prefix2F
--- /dev/null
+++ b/chncpu/src.txt
@@ -0,0 +1 @@
1+Hello, world!
--- a/chncpu/test.hex
+++ b/chncpu/test.hex
@@ -1,12 +1,9 @@
1-AE 4 0 90 6 "Hello!"
21 2 0 0 90
32 2 1 1 90
4-2 86 2 90
5-3 4 0
63 1 1 0
7-88 0 90 1 bf 90
4+88 c30 90 1 bf 90
85 5 0 bf
96 94 0 1 0 90
10-a2 0 2 90 bf 90
7+a2 0 c30 90 bf 90
118 4 bf
129 3 1 bf