001/* 002 * Licensed to the Apache Software Foundation (ASF) under one or more 003 * contributor license agreements. See the NOTICE file distributed with 004 * this work for additional information regarding copyright ownership. 005 * The ASF licenses this file to You under the Apache License, Version 2.0 006 * (the "License"); you may not use this file except in compliance with 007 * the License. You may obtain a copy of the License at 008 * 009 * http://www.apache.org/licenses/LICENSE-2.0 010 * 011 * Unless required by applicable law or agreed to in writing, software 012 * distributed under the License is distributed on an "AS IS" BASIS, 013 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 014 * See the License for the specific language governing permissions and 015 * limitations under the License. 016 */ 017package org.apache.commons.compress.archivers.zip; 018 019import java.io.Serializable; 020 021import org.apache.commons.compress.utils.ByteUtils; 022 023/** 024 * Utility class that represents a two byte integer with conversion 025 * rules for the little endian byte order of ZIP files. 026 * @Immutable 027 */ 028public final class ZipShort implements Cloneable, Serializable { 029 /** 030 * ZipShort with a value of 0. 031 * @since 1.14 032 */ 033 public static final ZipShort ZERO = new ZipShort(0); 034 035 private static final long serialVersionUID = 1L; 036 037 /** 038 * Get value as two bytes in big endian byte order. 039 * @param value the Java int to convert to bytes 040 * @return the converted int as a byte array in big endian byte order 041 */ 042 public static byte[] getBytes(final int value) { 043 final byte[] result = new byte[2]; 044 putShort(value, result, 0); 045 return result; 046 } 047 048 /** 049 * Helper method to get the value as a java int from a two-byte array 050 * @param bytes the array of bytes 051 * @return the corresponding java int value 052 */ 053 public static int getValue(final byte[] bytes) { 054 return getValue(bytes, 0); 055 } 056 057 /** 058 * Helper method to get the value as a java int from two bytes starting at given array offset 059 * @param bytes the array of bytes 060 * @param offset the offset to start 061 * @return the corresponding java int value 062 */ 063 public static int getValue(final byte[] bytes, final int offset) { 064 return (int) ByteUtils.fromLittleEndian(bytes, offset, 2); 065 } 066 067 /** 068 * put the value as two bytes in big endian byte order. 069 * @param value the Java int to convert to bytes 070 * @param buf the output buffer 071 * @param offset 072 * The offset within the output buffer of the first byte to be written. 073 * must be non-negative and no larger than {@code buf.length-2} 074 */ 075 public static void putShort(final int value, final byte[] buf, final int offset) { 076 ByteUtils.toLittleEndian(buf, value, offset, 2); 077 } 078 079 private final int value; 080 081 /** 082 * Create instance from bytes. 083 * @param bytes the bytes to store as a ZipShort 084 */ 085 public ZipShort(final byte[] bytes) { 086 this(bytes, 0); 087 } 088 089 /** 090 * Create instance from the two bytes starting at offset. 091 * @param bytes the bytes to store as a ZipShort 092 * @param offset the offset to start 093 */ 094 public ZipShort(final byte[] bytes, final int offset) { 095 value = ZipShort.getValue(bytes, offset); 096 } 097 098 /** 099 * Create instance from a number. 100 * @param value the int to store as a ZipShort 101 */ 102 public ZipShort(final int value) { 103 this.value = value; 104 } 105 106 @Override 107 public Object clone() { 108 try { 109 return super.clone(); 110 } catch (final CloneNotSupportedException cnfe) { 111 // impossible 112 throw new UnsupportedOperationException(cnfe); //NOSONAR 113 } 114 } 115 116 /** 117 * Override to make two instances with same value equal. 118 * @param o an object to compare 119 * @return true if the objects are equal 120 */ 121 @Override 122 public boolean equals(final Object o) { 123 if (!(o instanceof ZipShort)) { 124 return false; 125 } 126 return value == ((ZipShort) o).getValue(); 127 } 128 129 /** 130 * Get value as two bytes in big endian byte order. 131 * @return the value as a two byte array in big endian byte order 132 */ 133 public byte[] getBytes() { 134 final byte[] result = new byte[2]; 135 ByteUtils.toLittleEndian(result, value, 0, 2); 136 return result; 137 } 138 139 /** 140 * Get value as Java int. 141 * @return value as a Java int 142 */ 143 public int getValue() { 144 return value; 145 } 146 147 /** 148 * Override to make two instances with same value equal. 149 * @return the value stored in the ZipShort 150 */ 151 @Override 152 public int hashCode() { 153 return value; 154 } 155 156 @Override 157 public String toString() { 158 return "ZipShort value: " + value; 159 } 160}