public LZXDecoder(int window) throws LZXException {
		long wndsize = 1 << window; // uint
		int posn_slots;

		if (window < 15 || window > 21) throw new LZXException("UnsupportedWindowSizeRange");

		m_state = new LZXState();
		m_state.actual_size = 0;
		m_state.window = new int[(int)wndsize]; // byte[]
		for (int i = 0; i < wndsize; i++)
			m_state.window[i] = 0xDC;
		m_state.actual_size = wndsize;
		m_state.window_size = wndsize;
		m_state.window_posn = 0;

		/* initialize static tables */
		if (extra_bits == null) {
			extra_bits = new int[52]; // byte[]
			for (int i = 0, j = 0; i <= 50; i += 2) {
				extra_bits[i] = extra_bits[i + 1] = j; // byte
				if ((i != 0) && (j < 17)) j++;
			}
		}
		if (position_base == null) {
			position_base = new long[51]; // uint
			for (int i = 0, j = 0; i <= 50; i++) {
				position_base[i] = j; // uint
				j += 1 << extra_bits[i];
			}
		}

		/* calculate required position slots */
		if (window == 20) posn_slots = 42;
		else if (window == 21) posn_slots = 50;
		else posn_slots = window << 1;

		m_state.R0 = m_state.R1 = m_state.R2 = 1;
		m_state.main_elements = LZXConstants.NUM_CHARS + (posn_slots << 3); // ushort
		m_state.header_read = 0;
		m_state.frames_read = 0;
		m_state.block_remaining = 0;
		m_state.block_type = LZXConstants.BLOCKTYPE.INVALID;
		m_state.intel_curpos = 0;
		m_state.intel_started = 0;

		// yo dawg i herd u liek arrays so we put arrays in ur arrays so u can array while u array
		m_state.PRETREE_table = new int[(1 << LZXConstants.PRETREE_TABLEBITS) + (LZXConstants.PRETREE_MAXSYMBOLS << 1)]; // ushort[]
		m_state.PRETREE_len = new int[LZXConstants.PRETREE_MAXSYMBOLS + LZXConstants.LENTABLE_SAFETY]; // byte[]
		m_state.MAINTREE_table = new int[(1 << LZXConstants.MAINTREE_TABLEBITS) + (LZXConstants.MAINTREE_MAXSYMBOLS << 1)]; // ushort[]
		m_state.MAINTREE_len = new int[LZXConstants.MAINTREE_MAXSYMBOLS + LZXConstants.LENTABLE_SAFETY]; // byte[]
		m_state.LENGTH_table = new int[(1 << LZXConstants.LENGTH_TABLEBITS) + (LZXConstants.LENGTH_MAXSYMBOLS << 1)]; // ushort[]
		m_state.LENGTH_len = new int[LZXConstants.LENGTH_MAXSYMBOLS + LZXConstants.LENTABLE_SAFETY]; // byte[]
		m_state.ALIGNED_table = new int[(1 << LZXConstants.ALIGNED_TABLEBITS) + (LZXConstants.ALIGNED_MAXSYMBOLS << 1)]; // ushort[]
		m_state.ALIGNED_len = new int[LZXConstants.ALIGNED_MAXSYMBOLS + LZXConstants.LENTABLE_SAFETY]; // byte[]
		/* initialise tables to 0 (because deltas will be applied to them) */
		for (int i = 0; i < LZXConstants.MAINTREE_MAXSYMBOLS; i++)
			m_state.MAINTREE_len[i] = 0;
		for (int i = 0; i < LZXConstants.LENGTH_MAXSYMBOLS; i++)
			m_state.LENGTH_len[i] = 0;
	}