diff --git a/libcobj/src/jp/osscons/opensourcecobol/libcobj/call/CobolResolve.java b/libcobj/src/jp/osscons/opensourcecobol/libcobj/call/CobolResolve.java index 76f2e197..947fca5d 100644 --- a/libcobj/src/jp/osscons/opensourcecobol/libcobj/call/CobolResolve.java +++ b/libcobj/src/jp/osscons/opensourcecobol/libcobj/call/CobolResolve.java @@ -41,13 +41,17 @@ public class CobolResolve { /** プログラム名とCobolRunnableインスタンスの対応表 */ private static Map callTable; + /** ポインタ(UUID)のCobolRunnableインスタンスの対応表 */ private static Map pointerTable; + /** 名前の変換方法(小文字か大文字)を示す変数 */ private static int name_convert; + // TODO resolve_pathsの利用方法 /** システムで設定された区切り文字で区切られた0個以上のパス 動的に読み込むクラスファイルを検索する場所を示す. */ private static List resolve_paths; + /** システムで設定された区切り文字で区切られた0個以上のパス 動的に読み込むクラスファイルを検索するパッケージ名を示す. */ private static List package_paths; diff --git a/libcobj/src/jp/osscons/opensourcecobol/libcobj/common/CobolIntrinsic.java b/libcobj/src/jp/osscons/opensourcecobol/libcobj/common/CobolIntrinsic.java index a89c25c3..b5e348fe 100755 --- a/libcobj/src/jp/osscons/opensourcecobol/libcobj/common/CobolIntrinsic.java +++ b/libcobj/src/jp/osscons/opensourcecobol/libcobj/common/CobolIntrinsic.java @@ -32,6 +32,7 @@ import jp.osscons.opensourcecobol.libcobj.exceptions.CobolExceptionId; import jp.osscons.opensourcecobol.libcobj.exceptions.CobolRuntimeException; import jp.osscons.opensourcecobol.libcobj.exceptions.CobolStopRunException; +import jp.osscons.opensourcecobol.libcobj.file.CobolFile; public class CobolIntrinsic { @@ -45,6 +46,8 @@ public class CobolIntrinsic { private static AbstractCobolField currField = null; private static AbstractCobolField[] calcField = new AbstractCobolField[DEPTH_LEVEL]; private static Random random = new Random(); + private static byte[] localeBuff; + private static final byte[] byteArray00 = "00".getBytes(); /** libcob/intrinsicのmake_double_entryの実装 */ private static void makeDoubleEntry() { @@ -1892,4 +1895,87 @@ public static AbstractCobolField funcDayToYyyyddd(int params, AbstractCobolField currField.setInt(year); return currField; } + + /** + * cob_intr_exception_fileの実装 + * + * @return + */ + public static AbstractCobolField funcExceptionFile() { + int flen; + byte[] data; + + CobolFieldAttribute attr = + new CobolFieldAttribute(CobolFieldAttribute.COB_TYPE_ALPHANUMERIC, 0, 0, 0, null); + AbstractCobolField field = CobolFieldFactory.makeCobolField(0, (CobolDataStorage) null, attr); + if (CobolRuntimeException.getException() == 0 + || (CobolRuntimeException.getExceptionCode() & 0x0500) != 0x0500) { + field.setSize(2); + makeFieldEntry(field); + currField.memcpy(byteArray00, 2); + } else { + flen = CobolFile.errorFile.getSelectName().length(); + field.setSize(flen + 2); + makeFieldEntry(field); + data = new byte[2 + flen]; + System.arraycopy(CobolFile.errorFile.getFileStatus(), 0, data, 0, 2); + System.arraycopy(CobolFile.errorFile.getSelectName().getBytes(), 0, data, 2, flen); + currField.setDataStorage(new CobolDataStorage(data)); + } + return currField; + } + + /** + * cob_intr_exception_locationの実装 + * + * @return + */ + public static AbstractCobolField funcExceptionLocation() { + String buff; + + CobolFieldAttribute attr = + new CobolFieldAttribute(CobolFieldAttribute.COB_TYPE_ALPHANUMERIC, 0, 0, 0, null); + AbstractCobolField field = CobolFieldFactory.makeCobolField(0, (CobolDataStorage) null, attr); + currField = field; + if (CobolRuntimeException.getException() != 1 + || CobolRuntimeException.getOrigProgramId() == null) { + field.setSize(1); + makeFieldEntry(field); + currField.getDataStorage().setByte(0, ' '); + return currField; + } + if (CobolRuntimeException.getOrigSection() != null + && CobolRuntimeException.getOrigParagragh() != null) { + buff = + String.format( + "%s; %s OF %s; %d", + CobolRuntimeException.getOrigProgramId(), + CobolRuntimeException.getOrigParagragh(), + CobolRuntimeException.getOrigSection(), + CobolRuntimeException.getOrigLine()); + } else if (CobolRuntimeException.getOrigSection() != null) { + buff = + String.format( + "%s; %s; %d", + CobolRuntimeException.getOrigProgramId(), + CobolRuntimeException.getOrigSection(), + CobolRuntimeException.getOrigLine()); + } else if (CobolRuntimeException.getOrigParagragh() != null) { + buff = + String.format( + "%s; %s; %d", + CobolRuntimeException.getOrigProgramId(), + CobolRuntimeException.getOrigParagragh(), + CobolRuntimeException.getOrigLine()); + } else { + buff = + String.format( + "%s; ; %d", + CobolRuntimeException.getOrigProgramId(), CobolRuntimeException.getOrigLine()); + } + localeBuff = buff.getBytes(); + field.setSize(localeBuff.length); + currField.setDataStorage(new CobolDataStorage(localeBuff)); + return currField; + } } diff --git a/libcobj/src/jp/osscons/opensourcecobol/libcobj/common/CobolUtil.java b/libcobj/src/jp/osscons/opensourcecobol/libcobj/common/CobolUtil.java old mode 100644 new mode 100755 index abfc1abc..55cbd122 --- a/libcobj/src/jp/osscons/opensourcecobol/libcobj/common/CobolUtil.java +++ b/libcobj/src/jp/osscons/opensourcecobol/libcobj/common/CobolUtil.java @@ -61,6 +61,9 @@ public class CobolUtil { public static String sourceFile; public static int sourceLine; + public static String currProgramId; + public static String currSection; + public static String currParagraph; abstract class HandlerList { public HandlerList next = null; @@ -691,6 +694,10 @@ public static void setLocation( String progId, String sfile, int sline, String csect, String cpara, String cstatement) { CobolUtil.sourceFile = sfile; CobolUtil.sourceLine = sline; + currProgramId = progId; + currSection = csect; + currParagraph = cpara; + sourceLine = sline; if (CobolUtil.lineTrace) { System.err.println( String.format( @@ -741,4 +748,20 @@ public static byte[] stringToBytes(String s) { public static byte[] toBytes(byte... bytes) { return bytes; } + + public static String getCurrProgramId() { + return currProgramId; + } + + public static String getCurrSection() { + return currSection; + } + + public static String getCurrParagraph() { + return currParagraph; + } + + public static int getSourceLine() { + return sourceLine; + } } diff --git a/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/AbstractCobolField.java b/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/AbstractCobolField.java index 81e32732..1a73b4a4 100644 --- a/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/AbstractCobolField.java +++ b/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/AbstractCobolField.java @@ -31,8 +31,10 @@ public abstract class AbstractCobolField { /** データを格納に使用するバイト配列の長さ */ protected int size; + /** データを格納するバイト配列を扱うオブジェクト */ protected CobolDataStorage dataStorage; + /** 変数に関する様々な情報を保持するオブジェクト(符号付か,COMP-3指定かなど) */ protected CobolFieldAttribute attribute; diff --git a/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/CobolDataStorage.java b/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/CobolDataStorage.java index 900d3ce0..4ab8779a 100644 --- a/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/CobolDataStorage.java +++ b/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/CobolDataStorage.java @@ -28,6 +28,7 @@ public class CobolDataStorage { /** データを保存するバイト配列 */ private byte[] data; + /** このクラスの扱うデータが保存する領域のバイト配列中での相対位置 */ private int index; diff --git a/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/CobolFieldAttribute.java b/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/CobolFieldAttribute.java index 484fd5f2..0d30e9ef 100644 --- a/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/CobolFieldAttribute.java +++ b/libcobj/src/jp/osscons/opensourcecobol/libcobj/data/CobolFieldAttribute.java @@ -56,12 +56,16 @@ public class CobolFieldAttribute { /** 変数の種類 */ private int type; + /** 数値の時,桁数を示す */ private int digits; + /** 数値の時,スケールを示す */ private int scale; + /** 様々なフラグ */ private int flags; + /** PICTURE句の文字列 */ private String pic; diff --git a/libcobj/src/jp/osscons/opensourcecobol/libcobj/exceptions/CobolRuntimeException.java b/libcobj/src/jp/osscons/opensourcecobol/libcobj/exceptions/CobolRuntimeException.java old mode 100644 new mode 100755 index 65b7c2b5..c42f5c0b --- a/libcobj/src/jp/osscons/opensourcecobol/libcobj/exceptions/CobolRuntimeException.java +++ b/libcobj/src/jp/osscons/opensourcecobol/libcobj/exceptions/CobolRuntimeException.java @@ -19,10 +19,16 @@ package jp.osscons.opensourcecobol.libcobj.exceptions; import java.util.List; +import jp.osscons.opensourcecobol.libcobj.common.CobolUtil; /** 実行時エラーを示す例外 */ public class CobolRuntimeException extends RuntimeException { public static int code; + public static int cob_got_exception = 0; + public static String cob_orig_program_id; + public static String cob_orig_section; + public static String cob_orig_paragraph; + public static int cob_orig_line = 0; public static final int COBOL_FITAL_ERROR = 9000; @@ -30,6 +36,7 @@ public class CobolRuntimeException extends RuntimeException { /** エラー番号 */ private int errorCode; + /** エラーメッセージ */ private String message; @@ -70,6 +77,35 @@ public void printStackTrace() { public static void setException(int id) { code = CobolExceptionTabCode.code[id]; + cob_got_exception = 1; + cob_orig_line = CobolUtil.getSourceLine(); + cob_orig_program_id = CobolUtil.getCurrProgramId(); + cob_orig_section = CobolUtil.getCurrSection(); + cob_orig_paragraph = CobolUtil.getCurrParagraph(); // TODO common.c実装に残りをやる } + + public static int getExceptionCode() { + return code; + } + + public static int getException() { + return cob_got_exception; + } + + public static String getOrigProgramId() { + return cob_orig_program_id; + } + + public static String getOrigSection() { + return cob_orig_section; + } + + public static String getOrigParagragh() { + return cob_orig_paragraph; + } + + public static int getOrigLine() { + return cob_orig_line; + } } diff --git a/libcobj/src/jp/osscons/opensourcecobol/libcobj/file/CobolFile.java b/libcobj/src/jp/osscons/opensourcecobol/libcobj/file/CobolFile.java old mode 100644 new mode 100755 index 9d9a7814..3851ee49 --- a/libcobj/src/jp/osscons/opensourcecobol/libcobj/file/CobolFile.java +++ b/libcobj/src/jp/osscons/opensourcecobol/libcobj/file/CobolFile.java @@ -184,7 +184,7 @@ public class CobolFile { CobolExceptionId.COB_EC_I_O, CobolExceptionId.COB_EC_I_O_IMP }; - protected String select_name; + public String select_name; public byte[] file_status; protected AbstractCobolField assign; protected AbstractCobolField record; @@ -219,6 +219,8 @@ public class CobolFile { protected char file_version; protected static String runtime_buffer; + protected static String name; + protected static byte[] status; public Linage getLinorkeyptr() { return this.linorkeyptr; @@ -747,6 +749,7 @@ public void open(int mode, int sharing, AbstractCobolField fnstatus) { return; } } + // protected long start; // protected long end; @@ -1519,4 +1522,14 @@ public void cob_delete_file(AbstractCobolField fnstatus) { } } } + + public String getSelectName() { + // CobolFile cobolFile = new CobolFile(); + return this.select_name; + } + + public byte[] getFileStatus() { + // CobolFile cobolFile = new CobolFile(); + return this.file_status; + } } diff --git a/libcobj/src/jp/osscons/opensourcecobol/libcobj/file/IndexedCursor.java b/libcobj/src/jp/osscons/opensourcecobol/libcobj/file/IndexedCursor.java index 6b313632..d919bae0 100644 --- a/libcobj/src/jp/osscons/opensourcecobol/libcobj/file/IndexedCursor.java +++ b/libcobj/src/jp/osscons/opensourcecobol/libcobj/file/IndexedCursor.java @@ -57,24 +57,34 @@ enum CursorReadOption { public final class IndexedCursor { /** a cursor to the top direction */ private Optional backwardCursor; + /** a cursor to the bottom direction */ private Optional forwardCursor; + /** a connection to the SQLite database */ private Connection conn; + /** firstFetch is true if and only if the cursor has not read any data yet */ private boolean firstFetch; + /** a position in buffers that stores the read data */ private int cursorIndex; + /** one of COB_EQ, COB_LT, COB_LE, COB_GT, COB_GE in CobolIndexedFile.java */ private int comparator; + /** isDuplicate is true if and only if the table key allows duplicates */ private boolean isDuplicate; + /** a key */ private byte[] key; + /** forwardBuffer stores data located to the bottom direction from the first read position */ List forwardBuffer; + /** bakckwardBuffer stores data located to the first direction from the first read position */ List backwardBuffer; + /** the index of the table */ private int tableIndex; diff --git a/tests/run.src/functions.at b/tests/run.src/functions.at index 8ae8594d..08000ffe 100644 --- a/tests/run.src/functions.at +++ b/tests/run.src/functions.at @@ -373,8 +373,7 @@ AT_CHECK([java prog], [0], AT_CLEANUP -AT_SETUP([FUNCTION EXCEPTION-FILE]) -AT_CHECK([${SKIP_TEST}]) +AT_SETUP([FUNCTION EXCEPTION-FILE (no text)]) AT_DATA([prog.cob], [ IDENTIFICATION DIVISION. @@ -404,8 +403,38 @@ AT_CHECK([java prog], [0], AT_CLEANUP -AT_SETUP([FUNCTION EXCEPTION-LOCATION]) -AT_CHECK([${SKIP_TEST}]) +AT_SETUP([FUNCTION EXCEPTION-FILE (existing text)]) + +AT_DATA([prog.cob], [ + IDENTIFICATION DIVISION. + PROGRAM-ID. prog. + ENVIRONMENT DIVISION. + INPUT-OUTPUT SECTION. + FILE-CONTROL. + SELECT TEST-FILE ASSIGN "TEXIST" + FILE STATUS IS TEST-STATUS. + DATA DIVISION. + FILE SECTION. + FD TEST-FILE. + 01 TEST-REC PIC X(4). + WORKING-STORAGE SECTION. + 01 TEST-STATUS PIC XX. + PROCEDURE DIVISION. + OPEN OUTPUT TEST-FILE. + DISPLAY FUNCTION EXCEPTION-FILE + END-DISPLAY. + CLOSE TEST-FILE. + STOP RUN. +]) + +AT_CHECK([${COMPILE} prog.cob]) +AT_CHECK([java prog], [0], +[00 +]) + +AT_CLEANUP + +AT_SETUP([FUNCTION EXCEPTION-LOCATION (no text)]) AT_DATA([prog.cob], [ IDENTIFICATION DIVISION. @@ -439,6 +468,41 @@ AT_CHECK([java prog], [0], AT_CLEANUP +AT_SETUP([FUNCTION EXCEPTION-LOCATION (existing text)]) + +AT_DATA([prog.cob], [ + IDENTIFICATION DIVISION. + PROGRAM-ID. prog. + ENVIRONMENT DIVISION. + INPUT-OUTPUT SECTION. + FILE-CONTROL. + SELECT TEST-FILE ASSIGN "TEXIST" + FILE STATUS IS TEST-STATUS. + DATA DIVISION. + FILE SECTION. + FD TEST-FILE. + 01 TEST-REC PIC X(4). + WORKING-STORAGE SECTION. + 01 TEST-STATUS PIC XX. + PROCEDURE DIVISION. + A00-MAIN SECTION. + A00. + OPEN OUTPUT TEST-FILE. + B00-MAIN SECTION. + B00. + DISPLAY FUNCTION EXCEPTION-LOCATION + NO ADVANCING + END-DISPLAY. + CLOSE TEST-FILE. + STOP RUN. +]) + +AT_CHECK([${COMPILE} -debug prog.cob]) +AT_CHECK([java prog], [0], +[ ]) + +AT_CLEANUP + AT_SETUP([FUNCTION EXCEPTION-STATEMENT]) AT_CHECK([${SKIP_TEST}])