Chunk.avt

Переключить прокрутку окна
Загрузить этот исходный код

/*
    Компилятор языка программирования
    Объектно-ориентированный продвинутый векторный транслятор

    Copyright © 2021, 2024 Малик Разработчик

    Это свободная программа: вы можете перераспространять ее и/или изменять
    ее на условиях Стандартной общественной лицензии GNU в том виде,
    в каком она была опубликована Фондом свободного программного обеспечения;
    либо версии 3 лицензии, либо (по вашему выбору) любой более поздней версии.

    Эта программа распространяется в надежде, что она будет полезной,
    но БЕЗО ВСЯКИХ ГАРАНТИЙ; даже без неявной гарантии ТОВАРНОГО ВИДА
    или ПРИГОДНОСТИ ДЛЯ ОПРЕДЕЛЕННЫХ ЦЕЛЕЙ. Подробнее см. в Стандартной
    общественной лицензии GNU.

    Вы должны были получить копию Стандартной общественной лицензии GNU
    вместе с этой программой. Если это не так, см.
    <https://www.gnu.org/licenses/>.
*/

package ru.malik.elaborarer.avtoo.lang;

import avt.io.*;
import avt.io.extension.*;
import avt.lang.array.*;

public final class Chunk(Object, DataInput, Measureable)
{
    public static final int NEXT = Int.MIN_VALUE;

    private static String typeToString(int type) {
        return new String(new char[] { (char) ((type >> 0o30) & 0x5f), (char) ((type >> 0o20) & 0x5f), (char) ((type >> 0o10) & 0x5f), (char) (type & 0x5f) });
    }

    private final int fldType;
    private final int fldHash;
    private final int fldOffset;
    private final int fldLength;
    private final byte[] fldData;
    private final DataInput fldInput;
    private final String fldTypeAsString;
    private final ChunkByteArrayInputStream fldStream;

    package (int offset, int type, byte[] data, int hash) {
        if(data == null) data = new byte[0];
        ChunkByteArrayInputStream stream = new ChunkByteArrayInputStream(data);
        fldType = type;
        fldHash = hash;
        fldOffset = offset;
        fldLength = data.length >> 1;
        fldData = data;
        fldInput = (new DataInputStream(stream)).bigEndianDataInput;
        fldTypeAsString = typeToString(type);
        fldStream = stream;
    }

    public boolean equals(Object anot) {
        if(anot == this)
        {
            return true;
        }
        if(anot instanceof Chunk)
        {
            Chunk chunk = (Chunk) anot;
            if(fldType == chunk.fldType)
            {
                int length = fldLength;
                if(length == chunk.fldLength && Array.offsetOfNonEqual(fldData, 0, chunk.fldData, 0, length) == Comparable.INDEFINITE) return true;
            }
        }
        return false;
    }

    public int hashCode() { return fldHash; }

    public long hashCodeAsLong() { return ####fldHash; }

    public String toString() { return String.format(package.getResourceString("chunk.string"), new Object[] { fldTypeAsString, Int.toString(fldLength) }); }

    public void readFully(byte[] dst) throws IOException {
        throw new UnsupportedOperationException(package.getResourceString("chunk.read"));
    }

    public void readFully(byte[] dst, int offset, int length) throws IOException {
        throw new UnsupportedOperationException(package.getResourceString("chunk.read"));
    }

    public boolean readBoolean() throws IOException { return fldInput.readShort() != 0; }

    public char readChar() throws IOException { return fldInput.readChar(); }

    public int readUnsignedByte() throws IOException { return fldInput.readShort() & 0xff; }

    public int readUnsignedShort() throws IOException { return fldInput.readUnsignedShort(); }

    public int readByte() throws IOException { return (byte) fldInput.readShort(); }

    public int readShort() throws IOException { return fldInput.readShort(); }

    public int readInt() throws IOException { return fldInput.readInt(); }

    public int2 readUnsignedByte2() throws IOException { return fldInput.readUnsignedByte2(); }

    public int2 readUnsignedShort2() throws IOException { return fldInput.readUnsignedShort2(); }

    public int2 readByte2() throws IOException { return fldInput.readByte2(); }

    public int2 readShort2() throws IOException { return fldInput.readShort2(); }

    public int2 readInt2() throws IOException { return fldInput.readInt2(); }

    public int4 readUnsignedByte4() throws IOException { return fldInput.readUnsignedByte4(); }

    public int4 readUnsignedShort4() throws IOException { return fldInput.readUnsignedShort4(); }

    public int4 readByte4() throws IOException { return fldInput.readByte4(); }

    public int4 readShort4() throws IOException { return fldInput.readShort4(); }

    public int4 readInt4() throws IOException { return fldInput.readInt4(); }

    public int8 readUnsignedByte8() throws IOException { return fldInput.readUnsignedByte8(); }

    public int8 readUnsignedShort8() throws IOException { return fldInput.readUnsignedShort8(); }

    public int8 readByte8() throws IOException { return fldInput.readByte8(); }

    public int8 readShort8() throws IOException { return fldInput.readShort8(); }

    public int8 readInt8() throws IOException { return fldInput.readInt8(); }

    public long readLong() throws IOException { return fldInput.readLong(); }

    public long2 readLong2() throws IOException { return fldInput.readLong2(); }

    public long4 readLong4() throws IOException { return fldInput.readLong4(); }

    public long8 readLong8() throws IOException { return fldInput.readLong8(); }

    public float readFloat() throws IOException { return fldInput.readFloat(); }

    public float2 readFloat2() throws IOException { return fldInput.readFloat2(); }

    public float4 readFloat4() throws IOException { return fldInput.readFloat4(); }

    public float8 readFloat8() throws IOException { return fldInput.readFloat8(); }

    public double readDouble() throws IOException { return fldInput.readDouble(); }

    public double2 readDouble2() throws IOException { return fldInput.readDouble2(); }

    public double4 readDouble4() throws IOException { return fldInput.readDouble4(); }

    public double8 readDouble8() throws IOException { return fldInput.readDouble8(); }

    public real readReal() throws IOException { return fldInput.readReal(); }

    public String readUTF() throws IOException {
        throw new UnsupportedOperationException(package.getResourceString("chunk.read"));
    }

    public String readln() throws IOException {
        throw new UnsupportedOperationException(package.getResourceString("chunk.read"));
    }

    public String read() throws IOException {
        throw new UnsupportedOperationException(package.getResourceString("chunk.read"));
    }

    public void readFully(char[] dst) throws IOException { readFully(dst, 0, dst == null ? 0 : dst.length); }

    public void readFully(char[] dst, int offset, int length) throws IOException {
        if(dst == null)
        {
            throw new NullPointerException(String.format(avt.lang.package.getResourceString("null-pointer.argument"), new Object[] { "dst" }));
        }
        Array.checkBounds(dst, offset, length);
        if(fldStream.position > fldLength - length)
        {
            throw new EndOfStreamException(avt.io.package.getResourceString("end-of-stream"));
        }
        with(fldInput) while(length-- > 0) dst[offset++] = readChar();
    }

    public int readIndex() throws IOException {
        with(fldInput)
        {
            int result = readShort();
            return result >= 0 ? result : result << 0x10 & Int.MAX_VALUE | readUnsignedShort();
        }
    }

    public int readLabel() throws IOException {
        with(fldInput)
        {
            int result = readUnsignedShort();
            return AVTOORecompilable.isNext(result) ? NEXT : AVTOORecompilable.decodeUsing(!AVTOORecompilable.isLongNumber(result) ? result : result << 0x10 | readUnsignedShort());
        }
    }

    public int dataOffsetToSourceOffset(int offset) { return fldOffset + (offset + 2 << 1); }

    public int available() { return fldLength - fldStream.position; }

    public int seek(int offset, int from) {
        int position;
        int length = fldLength;
        ChunkByteArrayInputStream stream = fldStream;
        switch(from)
        {
        case SeekExtension.BEGIN:
            position = offset;
            break;
        case SeekExtension.END:
            position = offset + length;
            break;
        case SeekExtension.CURRENT:
            position = offset + stream.position;
            break;
        default:
            throw new IllegalArgumentException(String.format(avt.lang.package.getResourceString("illegal-argument"), new Object[] { "from" }));
        }
        if(position < 0) position = 0;
        if(position > length) position = length;
        return stream.position = position;
    }

    public String typeToString() { return fldTypeAsString; }

    public int length { read = fldLength }

    public int position { read = fldStream.position, write = setPosition }

    public int offset { read = fldOffset }

    public int type { read = fldType }

    private void setPosition(int newPosition) {
        int length = fldLength;
        if(newPosition < 0) newPosition = 0;
        if(newPosition > length) newPosition = length;
        fldStream.position = newPosition;
    }
}

class ChunkByteArrayInputStream(ByteArrayInputStream)
{
    public (byte[] array): super(array) {  }

    public int position { read = fldPosition >> 1, write = fldPosition = value << 1 }
}