⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 unpack.java

📁 java下操作rar文件,创建,压缩/解压缩等等.
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
	}

	private void UnpWriteArea(int startPtr, int endPtr) throws IOException
	{
		if (endPtr != startPtr) {
			unpSomeRead = true;
		}
		if (endPtr < startPtr) {
			UnpWriteData(window, startPtr, -startPtr & Compress.MAXWINMASK);
			UnpWriteData(window, 0, endPtr);
			unpAllBuf = true;
		} else {
			UnpWriteData(window, startPtr, endPtr - startPtr);
		}
	}

	private void UnpWriteData(byte[] data, int offset, int size)
			throws IOException
	{
		if (writtenFileSize >= destUnpSize) {
			return;
		}
		int writeSize = size;
		long leftToWrite = destUnpSize - writtenFileSize;
		if (writeSize > leftToWrite) {
			writeSize = (int) leftToWrite;
		}
		unpIO.unpWrite(data, offset, writeSize);

		writtenFileSize += size;

	}

	private void insertOldDist(int distance)
	{
		oldDist[3] = oldDist[2];
		oldDist[2] = oldDist[1];
		oldDist[1] = oldDist[0];
		oldDist[0] = distance;
	}

	private void insertLastMatch(int length, int distance)
	{
		lastDist = distance;
		lastLength = length;
	}

	private void copyString(int length, int distance)
	{

		int destPtr = unpPtr - distance;
	 //System.out.println(unpPtr+":"+distance);
		if (destPtr>=0&&destPtr < Compress.MAXWINSIZE - 260
				&& unpPtr < Compress.MAXWINSIZE - 260) {
			

			window[unpPtr++] = window[destPtr++];

			while (--length > 0)

				window[unpPtr++] = window[destPtr++];
		} else
			while (length-- != 0) {
				window[unpPtr] = window[destPtr++ & Compress.MAXWINMASK];
				unpPtr = (unpPtr + 1) & Compress.MAXWINMASK;
			}
	}

	protected void unpInitData(boolean solid)
	{
		if (!solid) {
			tablesRead = false;
			Arrays.fill(oldDist, 0); // memset(oldDist,0,sizeof(OldDist));

			oldDistPtr = 0;
			lastDist = 0;
			lastLength = 0;

			Arrays.fill(unpOldTable, (byte) 0);// memset(UnpOldTable,0,sizeof(UnpOldTable));

			unpPtr = 0;
			wrPtr = 0;
			ppmEscChar = 2;

			initFilters();
		}
		InitBitInput();
		ppmError = false;
		writtenFileSize = 0;
		readTop = 0;
		readBorder = 0;
		unpInitData20(solid);
	}

	private void initFilters()
	{
		oldFilterLengths.clear();
		lastFilter = 0;

		filters.clear();

		prgStack.clear();
	}

	private boolean readEndOfBlock() throws IOException, RarException
	{
		int BitField = getbits();
		boolean NewTable, NewFile = false;
		if ((BitField & 0x8000) != 0) {
			NewTable = true;
			addbits(1);
		} else {
			NewFile = true;
			NewTable = (BitField & 0x4000) != 0 ? true : false;
			addbits(2);
		}
		tablesRead = !NewTable;
		return !(NewFile || NewTable && !readTables());
	}

	private boolean readTables() throws IOException, RarException
	{
		byte[] bitLength = new byte[Compress.BC];

		byte[] table = new byte[Compress.HUFF_TABLE_SIZE];
		if (inAddr > readTop - 25) {
			if (!unpReadBuf()) {
				return (false);
			}
		}
		faddbits((8 - inBit) & 7);
		long bitField = fgetbits() & 0xffFFffFF;
		if ((bitField & 0x8000) != 0) {
			unpBlockType = BlockTypes.BLOCK_PPM;
			return (ppm.decodeInit(this, ppmEscChar));
		}
		unpBlockType = BlockTypes.BLOCK_LZ;

		prevLowDist = 0;
		lowDistRepCount = 0;

		if ((bitField & 0x4000) == 0) {
			Arrays.fill(unpOldTable, (byte) 0);// memset(UnpOldTable,0,sizeof(UnpOldTable));
		}
		faddbits(2);

		for (int i = 0; i < Compress.BC; i++) {
			int length = (fgetbits() >>> 12) & 0xFF;
			faddbits(4);
			if (length == 15) {
				int zeroCount = (fgetbits() >>> 12) & 0xFF;
				faddbits(4);
				if (zeroCount == 0) {
					bitLength[i] = 15;
				} else {
					zeroCount += 2;
					while (zeroCount-- > 0 && i < bitLength.length) {
						bitLength[i++] = 0;
					}
					i--;
				}
			} else {
				bitLength[i] = (byte) length;
			}
		}

		makeDecodeTables(bitLength, 0, BD, Compress.BC);

		int TableSize = Compress.HUFF_TABLE_SIZE;

		for (int i = 0; i < TableSize;) {
			if (inAddr > readTop - 5) {
				if (!unpReadBuf()) {
					return (false);
				}
			}
			int Number = decodeNumber(BD);
			if (Number < 16) {
				table[i] = (byte) ((Number + unpOldTable[i]) & 0xf);
				i++;
			} else if (Number < 18) {
				int N;
				if (Number == 16) {
					N = (fgetbits() >>> 13) + 3;
					faddbits(3);
				} else {
					N = (fgetbits() >>> 9) + 11;
					faddbits(7);
				}
				while (N-- > 0 && i < TableSize) {
					table[i] = table[i - 1];
					i++;
				}
			} else {
				int N;
				if (Number == 18) {
					N = (fgetbits() >>> 13) + 3;
					faddbits(3);
				} else {
					N = (fgetbits() >>> 9) + 11;
					faddbits(7);
				}
				while (N-- > 0 && i < TableSize) {
					table[i++] = 0;
				}
			}
		}
		tablesRead = true;
		if (inAddr > readTop) {
			return (false);
		}
		makeDecodeTables(table, 0, LD, Compress.NC);
		makeDecodeTables(table, Compress.NC, DD, Compress.DC);
		makeDecodeTables(table, Compress.NC + Compress.DC, LDD, Compress.LDC);
		makeDecodeTables(table, Compress.NC + Compress.DC + Compress.LDC, RD,
				Compress.RC);

		// memcpy(unpOldTable,table,sizeof(unpOldTable));
		for (int i = 0; i < unpOldTable.length; i++) {
			unpOldTable[i] = table[i];
		}
		return (true);

	}

	private boolean readVMCode() throws IOException, RarException
	{
		int FirstByte = getbits() >> 8;
		addbits(8);
		int Length = (FirstByte & 7) + 1;
		if (Length == 7) {
			Length = (getbits() >> 8) + 7;
			addbits(8);
		} else if (Length == 8) {
			Length = getbits();
			addbits(16);
		}
		List<Byte> vmCode = new ArrayList<Byte>();
		for (int I = 0; I < Length; I++) {
			if (inAddr >= readTop - 1 && !unpReadBuf() && I < Length - 1) {
				return (false);
			}
			vmCode.add(Byte.valueOf((byte) (getbits() >> 8)));
			addbits(8);
		}
		return (addVMCode(FirstByte, vmCode, Length));
	}

	private boolean readVMCodePPM() throws IOException, RarException
	{
		int FirstByte = ppm.decodeChar();
		if ((int) FirstByte == -1) {
			return (false);
		}
		int Length = (FirstByte & 7) + 1;
		if (Length == 7) {
			int B1 = ppm.decodeChar();
			if (B1 == -1) {
				return (false);
			}
			Length = B1 + 7;
		} else if (Length == 8) {
			int B1 = ppm.decodeChar();
			if (B1 == -1) {
				return (false);
			}
			int B2 = ppm.decodeChar();
			if (B2 == -1) {
				return (false);
			}
			Length = B1 * 256 + B2;
		}
		List<Byte> vmCode = new ArrayList<Byte>();
		for (int I = 0; I < Length; I++) {
			int Ch = ppm.decodeChar();
			if (Ch == -1) {
				return (false);
			}
			vmCode.add(Byte.valueOf((byte) Ch));// VMCode[I]=Ch;
		}
		return (addVMCode(FirstByte, vmCode, Length));
	}

	private boolean addVMCode(int firstByte, List<Byte> vmCode, int length)
	{
		BitInput Inp = new BitInput();
		Inp.InitBitInput();
		// memcpy(Inp.InBuf,Code,Min(BitInput::MAX_SIZE,CodeSize));
		for (int i = 0; i < Math.min(BitInput.maxSize, vmCode.size()); i++) {
			Inp.getInBuf()[i] = vmCode.get(i);
		}
		rarVM.init();

		int FiltPos;
		if ((firstByte & 0x80) != 0) {
			FiltPos = RarVM.ReadData(Inp);
			if (FiltPos == 0) {
				initFilters();
			} else {
				FiltPos--;
			}
		} else
			FiltPos = lastFilter; // use the same filter as last time

		if (FiltPos > filters.size() || FiltPos > oldFilterLengths.size()) {
			return (false);
		}
		lastFilter = FiltPos;
		boolean NewFilter = (FiltPos == filters.size());

		UnpackFilter StackFilter = new UnpackFilter(); // new filter for
		// PrgStack

		UnpackFilter Filter;
		if (NewFilter) // new filter code, never used before since VM reset
		{
			// too many different filters, corrupt archive
			if (FiltPos > 1024) {
				return (false);
			}

			// Filters[Filters.Size()-1]=Filter=new UnpackFilter;
			Filter = new UnpackFilter();
			filters.add(Filter);
			StackFilter.setParentFilter(filters.size() - 1);
			oldFilterLengths.add(0);
			Filter.setExecCount(0);
		} else // filter was used in the past
		{
			Filter = filters.get(FiltPos);
			StackFilter.setParentFilter(FiltPos);
			Filter.setExecCount(Filter.getExecCount() + 1);// ->ExecCount++;
		}

		prgStack.add(StackFilter);
		StackFilter.setExecCount(Filter.getExecCount());// ->ExecCount;

		int BlockStart = RarVM.ReadData(Inp);
		if ((firstByte & 0x40) != 0) {
			BlockStart += 258;
		}
		StackFilter.setBlockStart((BlockStart + unpPtr) & Compress.MAXWINMASK);
		if ((firstByte & 0x20) != 0) {
			StackFilter.setBlockLength(RarVM.ReadData(Inp));
		} else {
			StackFilter
					.setBlockLength(FiltPos < oldFilterLengths.size() ? oldFilterLengths
							.get(FiltPos)
							: 0);
		}
		StackFilter.setNextWindow((wrPtr != unpPtr)
				&& ((wrPtr - unpPtr) & Compress.MAXWINMASK) <= BlockStart);

		// DebugLog("\nNextWindow: UnpPtr=%08x WrPtr=%08x
		// BlockStart=%08x",UnpPtr,WrPtr,BlockStart);

		oldFilterLengths.set(FiltPos, StackFilter.getBlockLength());

		// memset(StackFilter->Prg.InitR,0,sizeof(StackFilter->Prg.InitR));
		Arrays.fill(StackFilter.getPrg().getInitR(), 0);
		StackFilter.getPrg().getInitR()[3] = RarVM.VM_GLOBALMEMADDR;// StackFilter->Prg.InitR[3]=VM_GLOBALMEMADDR;
		StackFilter.getPrg().getInitR()[4] = StackFilter.getBlockLength();// StackFilter->Prg.InitR[4]=StackFilter->BlockLength;
		StackFilter.getPrg().getInitR()[5] = StackFilter.getExecCount();// StackFilter->Prg.InitR[5]=StackFilter->ExecCount;

		if ((firstByte & 0x10) != 0) // set registers to optional parameters
		// if any
		{
			int InitMask = Inp.fgetbits() >>> 9;
			Inp.faddbits(7);
			for (int I = 0; I < 7; I++) {
				if ((InitMask & (1 << I)) != 0) {
					// StackFilter->Prg.InitR[I]=RarVM::ReadData(Inp);
					StackFilter.getPrg().getInitR()[I] = RarVM.ReadData(Inp);
				}
			}
		}

		if (NewFilter) {
			int VMCodeSize = RarVM.ReadData(Inp);
			if (VMCodeSize >= 0x10000 || VMCodeSize == 0) {
				return (false);
			}
			byte[] VMCode = new byte[VMCodeSize];
			for (int I = 0; I < VMCodeSize; I++) {
				if (Inp.Overflow(3)) {
					return (false);
				}
				VMCode[I] = (byte) (Inp.fgetbits() >> 8);
				Inp.faddbits(8);
			}
			// VM.Prepare(&VMCode[0],VMCodeSize,&Filter->Prg);
			rarVM.prepare(VMCode, VMCodeSize, Filter.getPrg());
		}
		StackFilter.getPrg().setAltCmd(Filter.getPrg().getCmd());// StackFilter->Prg.AltCmd=&Filter->Prg.Cmd[0];
		StackFilter.getPrg().setCmdCount(Filter.getPrg().getCmdCount());// StackFilter->Prg.CmdCount=Filter->Prg.CmdCount;

		int StaticDataSize = Filter.getPrg().getStaticData().size();
		if (StaticDataSize > 0 && StaticDataSize < RarVM.VM_GLOBALMEMSIZE) {
			// read statically defined data contained in DB commands
			// StackFilter->Prg.StaticData.Add(StaticDataSize);
			StackFilter.getPrg().setStaticData(Filter.getPrg().getStaticData());
			// memcpy(&StackFilter->Prg.StaticData[0],&Filter->Prg.StaticData[0],StaticDataSize);
		}

		if (StackFilter.getPrg().getGlobalData().size() < RarVM.VM_FIXEDGLOBALSIZE) {
			// StackFilter->Prg.GlobalData.Reset();
			// StackFilter->Prg.GlobalData.Add(VM_FIXEDGLOBALSIZE);
			StackFilter.getPrg().getGlobalData().clear();
			StackFilter.getPrg().getGlobalData().setSize(
					RarVM.VM_FIXEDGLOBALSIZE);
		}

		// byte *GlobalData=&StackFilter->Prg.GlobalData[0];
		Vector<Byte> globalData = StackFilter.getPrg().getGlobalData();
		for (int I = 0; I < 7; I++) {
			rarVM.setLowEndianValue(globalData, I * 4, StackFilter.getPrg()
					.getInitR()[I]);
		}

		// VM.SetLowEndianValue((uint
		// *)&GlobalData[0x1c],StackFilter->BlockLength);
		rarVM.setLowEndianValue(globalData, 0x1c, StackFilter.getBlockLength());
		// VM.SetLowEndianValue((uint *)&GlobalData[0x20],0);
		rarVM.setLowEndianValue(globalData, 0x20, 0);
		rarVM.setLowEndianValue(globalData, 0x24, 0);
		rarVM.setLowEndianValue(globalData, 0x28, 0);

		// VM.SetLowEndianValue((uint
		// *)&GlobalData[0x2c],StackFilter->ExecCount);
		rarVM.setLowEndianValue(globalData, 0x2c, StackFilter.getExecCount());
		// memset(&GlobalData[0x30],0,16);
		for (int i = 0; i < 16; i++) {
			globalData.set(0x30 + i, Byte.valueOf((byte) (0)));
		}
		if ((firstByte & 8) != 0) // put data block passed as parameter if any
		{
			if (Inp.Overflow(3)) {
				return (false);
			}
			int DataSize = RarVM.ReadData(Inp);
			if (DataSize > RarVM.VM_GLOBALMEMSIZE - RarVM.VM_FIXEDGLOBALSIZE) {
				return (false);
			}
			int CurSize = StackFilter.getPrg().getGlobalData().size();
			if (CurSize < DataSize + RarVM.VM_FIXEDGLOBALSIZE) {
				// StackFilter->Prg.GlobalData.Add(DataSize+VM_FIXEDGLOBALSIZE-CurSize);
				StackFilter.getPrg().getGlobalData().setSize(
						DataSize + RarVM.VM_FIXEDGLOBALSIZE - CurSize);
			}
			int offset = RarVM.VM_FIXEDGLOBALSIZE;
			globalData = StackFilter.getPrg().getGlobalData();
			for (int I = 0; I < DataSize; I++) {
				if (Inp.Overflow(3)) {
					return (false);
				}
				globalData.set(offset + I, Byte
						.valueOf((byte) (Inp.fgetbits() >>> 8)));
				Inp.faddbits(8);
			}
		}
		return (true);
	}

	private void ExecuteCode(VMPreparedProgram Prg)
	{
		if (Prg.getGlobalData().size() > 0) {
			// Prg->InitR[6]=int64to32(WrittenFileSize);
			Prg.getInitR()[6] = (int) (writtenFileSize);
			// rarVM.SetLowEndianValue((uint
			// *)&Prg->GlobalData[0x24],int64to32(WrittenFileSize));
			rarVM.setLowEndianValue(Prg.getGlobalData(), 0x24,
					(int) writtenFileSize);
			// rarVM.SetLowEndianValue((uint
			// *)&Prg->GlobalData[0x28],int64to32(WrittenFileSize>>32));
			rarVM.setLowEndianValue(Prg.getGlobalData(), 0x28,
					(int) (writtenFileSize >>> 32));
			rarVM.execute(Prg);
		}
	}

	private boolean ReadEndOfBlock() throws IOException, RarException
	{
		int BitField = getbits();
		boolean NewTable, NewFile = false;
		if ((BitField & 0x8000) != 0) {
			NewTable = true;
			addbits(1);
		} else {
			NewFile = true;
			NewTable = (BitField & 0x4000) != 0;
			addbits(2);
		}
		tablesRead = !NewTable;
		return !(NewFile || NewTable && !readTables());
	}

	public boolean isFileExtracted()
	{
		return fileExtracted;
	}

	public void setDestSize(long destSize)
	{
		this.destUnpSize = destSize;
		this.fileExtracted = false;
	}

	public void setSuspended(boolean suspended)
	{
		this.suspended = suspended;
	}

	public int getChar() throws IOException, RarException
	{
		if (inAddr > BitInput.maxSize - 30) {
			unpReadBuf();
		}
		return (inBuf[inAddr++]&0xff);
	}

	public int getPpmEscChar()
	{
		return ppmEscChar;
	}

	public void setPpmEscChar(int ppmEscChar)
	{
		this.ppmEscChar = ppmEscChar;
	}
	

}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -