diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/RpmBaseTag.java b/rpm/src/main/java/org/eclipse/packager/rpm/RpmBaseTag.java index ca17c70..e816054 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/RpmBaseTag.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/RpmBaseTag.java @@ -28,9 +28,8 @@ public interface RpmBaseTag { /** * Get the data type of the tag. * - * @param the data type * @return the class representing the data type of this tag */ - Class getDataType(); + Class getDataType(); } diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/RpmSignatureTag.java b/rpm/src/main/java/org/eclipse/packager/rpm/RpmSignatureTag.java index 83ad116..8056f03 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/RpmSignatureTag.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/RpmSignatureTag.java @@ -45,8 +45,8 @@ public Integer getValue() { } @Override - public Class getDataType() { - return (Class) this.dataType; + public Class getDataType() { + return this.dataType; } private final static Map all = new HashMap<>(RpmSignatureTag.values().length); diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/RpmTag.java b/rpm/src/main/java/org/eclipse/packager/rpm/RpmTag.java index 251132e..4c2987b 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/RpmTag.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/RpmTag.java @@ -127,8 +127,8 @@ public Integer getValue() { return this.value; } - public Class getDataType() { - return (Class) this.dataType; + public Class getDataType() { + return this.dataType; } private final static Map all = new HashMap<>(RpmTag.values().length); diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/RpmTagValue.java b/rpm/src/main/java/org/eclipse/packager/rpm/RpmTagValue.java index 5328234..74c93c6 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/RpmTagValue.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/RpmTagValue.java @@ -77,13 +77,13 @@ public Optional asString() { } if (this.value instanceof String[]) { - final String[] array = (String[]) this.value; + final String[] arr = (String[]) this.value; - if (array.length == 1) { - return Optional.of(array[0]); + if (arr.length > 0) { + return Optional.of(arr[0]); + } else { + return Optional.empty(); } - - throw new IllegalArgumentException("Array contains more than one string value"); } return Optional.empty(); @@ -139,13 +139,13 @@ public Optional asInteger() { } if (this.value instanceof Integer[]) { - final Integer[] array = (Integer[]) this.value; + final Integer[] arr = (Integer[]) this.value; - if (array.length == 1) { - return Optional.of(array[0]); + if (arr.length > 0) { + return Optional.of(arr[0]); + } else { + return Optional.empty(); } - - throw new IllegalArgumentException("Array contains more than one integer value"); } return Optional.empty(); @@ -161,13 +161,13 @@ public Optional asLong() { } if (this.value instanceof Integer[]) { - final Integer[] array = (Integer[]) this.value; + final Integer[] arr = (Integer[]) this.value; - if (array.length == 1) { - return Optional.of(toLong(array[0])); + if (arr.length > 0) { + return Optional.of(toLong(arr[0])); + } else { + return Optional.empty(); } - - throw new IllegalArgumentException("Array contains more than one integer value"); } if (this.value instanceof Long) { @@ -175,13 +175,13 @@ public Optional asLong() { } if (this.value instanceof Long[]) { - final Long[] array = (Long[]) this.value; + final Long[] arr = (Long[]) this.value; - if (array.length == 1) { - return Optional.of(array[0]); + if (arr.length > 0) { + return Optional.of(arr[0]); + } else { + return Optional.empty(); } - - throw new IllegalArgumentException("Array contains more than one long value"); } return Optional.empty(); @@ -216,8 +216,8 @@ public String toString() { } if (this.value instanceof Object[]) { - final Object[] array = (Object[]) this.value; - return array.length == 1 ? Objects.toString(array[0]) : Arrays.toString((Object[]) this.value); + final Object[] arr = (Object[]) this.value; + return arr.length == 1 ? Objects.toString(arr[0]) : Arrays.toString((Object[]) this.value); } return Objects.toString(this.value); diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/Rpms.java b/rpm/src/main/java/org/eclipse/packager/rpm/Rpms.java index 695f848..14eeb53 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/Rpms.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/Rpms.java @@ -67,7 +67,7 @@ public static String toHex(final byte[] data, final int offset, final int length return sb.toString(); } - public static String dumpValue(final HeaderValue value) { + public static String dumpValue(final HeaderValue value) { final StringBuilder sb = new StringBuilder(); dumpValue(sb, value.getValue()); return sb.toString(); diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/app/Dumper.java b/rpm/src/main/java/org/eclipse/packager/rpm/app/Dumper.java index facfd68..1236ae9 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/app/Dumper.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/app/Dumper.java @@ -123,16 +123,16 @@ private static void dumpHeader(final String string, final InputHeader>> data; + Set> data; if (sorted) { data = new TreeMap<>(header.getRawTags()).entrySet(); } else { data = header.getRawTags().entrySet(); } - for (final Map.Entry> entry : data) { + for (final Map.Entry entry : data) { final RpmBaseTag tag = func.apply(entry.getKey()); - final HeaderValue value = entry.getValue(); + final HeaderValue value = entry.getValue(); System.out.format("%20s - %s%n", tag != null ? tag : entry.getKey(), Rpms.dumpValue(value)); if (entry.getKey() == IMMUTABLE_TAG_SIGNATURE || entry.getKey() == IMMUTABLE_TAG_HEADER) { diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/deps/Dependencies.java b/rpm/src/main/java/org/eclipse/packager/rpm/deps/Dependencies.java index 96c8502..b03b535 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/deps/Dependencies.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/deps/Dependencies.java @@ -77,22 +77,52 @@ private static void putDependencies(final Header header, final Collectio Header.putIntFields(header, deps, flagsTag, dep -> RpmDependencyFlags.encode(dep.getFlags())); } + /** + *

Note that since version 0.21.0 IllegalArgumentException is thrown if an error occurs while reading the RPM header.

+ * + * @param header the RPM header + * @return the list of dependencies + */ public static List getRequirements(final ReadableHeader header) { return getDependencies(header, RpmTag.REQUIRE_NAME, RpmTag.REQUIRE_VERSION, RpmTag.REQUIRE_FLAGS); } + /** + *

Note that since version 0.21.0 IllegalArgumentException is thrown if an error occurs while reading the RPM header.

+ * + * @param header the RPM header + * @return the list of dependencies + */ public static List getProvides(final ReadableHeader header) { return getDependencies(header, RpmTag.PROVIDE_NAME, RpmTag.PROVIDE_VERSION, RpmTag.PROVIDE_FLAGS); } + /** + *

Note that since version 0.21.0 IllegalArgumentException is thrown if an error occurs while reading the RPM header.

+ * + * @param header the RPM header + * @return the list of dependencies + */ public static List getConflicts(final ReadableHeader header) { return getDependencies(header, RpmTag.CONFLICT_NAME, RpmTag.CONFLICT_VERSION, RpmTag.CONFLICT_FLAGS); } + /** + *

Note that since version 0.21.0 IllegalArgumentException is thrown if an error occurs while reading the RPM header.

+ * + * @param header the RPM header + * @return the list of dependencies + */ public static List getObsoletes(final ReadableHeader header) { return getDependencies(header, RpmTag.OBSOLETE_NAME, RpmTag.OBSOLETE_VERSION, RpmTag.OBSOLETE_FLAGS); } + /** + *

Note that since version 0.21.0 IllegalArgumentException is thrown if an error occurs while reading the RPM header.

+ * + * @param header the RPM header + * @return the list of dependencies + */ public static List getSuggests(final ReadableHeader header) { return getDependencies(header, RpmTag.SUGGEST_NAME, RpmTag.SUGGEST_VERSION, RpmTag.SUGGEST_FLAGS); } @@ -105,6 +135,12 @@ public static List getSupplements(final ReadableHeader heade return getDependencies(header, RpmTag.SUPPLEMENT_NAME, RpmTag.SUPPLEMENT_VERSION, RpmTag.SUPPLEMENT_FLAGS); } + /** + *

Note that since version 0.21.0 IllegalArgumentException is thrown if an error occurs while reading the RPM header.

+ * + * @param header the RPM header + * @return the list of dependencies + */ public static List getEnhances(final ReadableHeader header) { return getDependencies(header, RpmTag.ENHANCE_NAME, RpmTag.ENHANCE_VERSION, RpmTag.ENHANCE_FLAGS); } diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/info/RpmInformations.java b/rpm/src/main/java/org/eclipse/packager/rpm/info/RpmInformations.java index e832e2e..a52f73c 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/info/RpmInformations.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/info/RpmInformations.java @@ -69,6 +69,16 @@ public final class RpmInformations { private RpmInformations() { } + /** + * Returns the RPM information for the given RPM input stream. + * + *

Note that since version 0.21.0 IllegalArgumentException is thrown if an error occurs while reading the RPM header.

+ * + * @param in the RPM input stream + * @return the RPM information for the given RPM input stream + * @throws IOException if an error occurs while reading from the given RPM input stream + * @throws IllegalArgumentException if there are any problems reading the headers + */ public static RpmInformation makeInformation(final RpmInputStream in) throws IOException { final InputHeader header = in.getPayloadHeader(); final InputHeader signature = in.getSignatureHeader(); diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/parse/HeaderValue.java b/rpm/src/main/java/org/eclipse/packager/rpm/parse/HeaderValue.java index c1efd2a..7cbbe83 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/parse/HeaderValue.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/parse/HeaderValue.java @@ -23,10 +23,10 @@ import org.eclipse.packager.rpm.Rpms; import org.eclipse.packager.rpm.header.Type; -public class HeaderValue { +public class HeaderValue { private final int tag; - private RpmTagValue value; + private RpmTagValue value; private final int originalType; @@ -48,7 +48,7 @@ public int getTag() { return this.tag; } - public RpmTagValue getValue() { + public RpmTagValue getValue() { return this.value; } @@ -75,30 +75,30 @@ void fillFromStore(final ByteBuffer storeData) { case NULL: break; case CHAR: - this.value = (RpmTagValue) new RpmTagValue<>(this.count == 1 ? Character.valueOf((char) storeData.get()) : IntStream.range(0, this.count).mapToObj(i -> (char) storeData.get()).toArray(Character[]::new)); + this.value = new RpmTagValue<>(this.count == 1 ? Character.valueOf((char) storeData.get()) : IntStream.range(0, this.count).mapToObj(i -> (char) storeData.get()).toArray(Character[]::new)); break; case BYTE: case UNKNOWN: - this.value = (RpmTagValue) new RpmTagValue<>(this.count == 1 ? Byte.valueOf(storeData.get()) : IntStream.range(0, this.count).mapToObj(i -> storeData.get()).toArray(Byte[]::new)); + this.value = new RpmTagValue<>(this.count == 1 ? Byte.valueOf(storeData.get()) : IntStream.range(0, this.count).mapToObj(i -> storeData.get()).toArray(Byte[]::new)); break; case SHORT: - this.value = (RpmTagValue) new RpmTagValue<>(this.count == 1 ? Short.valueOf(storeData.getShort()) : IntStream.range(0, this.count).mapToObj(i -> storeData.getShort()).toArray(Short[]::new)); + this.value = new RpmTagValue<>(this.count == 1 ? Short.valueOf(storeData.getShort()) : IntStream.range(0, this.count).mapToObj(i -> storeData.getShort()).toArray(Short[]::new)); break; case INT: - this.value = (RpmTagValue) new RpmTagValue<>(this.count == 1 ? Integer.valueOf(storeData.getInt()) : IntStream.range(0, this.count).mapToObj(i -> storeData.getInt()).toArray(Integer[]::new)); + this.value = new RpmTagValue<>(this.count == 1 ? Integer.valueOf(storeData.getInt()) : IntStream.range(0, this.count).mapToObj(i -> storeData.getInt()).toArray(Integer[]::new)); break; case LONG: - this.value = (RpmTagValue) new RpmTagValue<>(this.count == 1 ? Long.valueOf(storeData.getLong()) : IntStream.range(0, this.count).mapToObj(i -> storeData.getLong()).toArray(Long[]::new)); + this.value = new RpmTagValue<>(this.count == 1 ? Long.valueOf(storeData.getLong()) : IntStream.range(0, this.count).mapToObj(i -> storeData.getLong()).toArray(Long[]::new)); break; case STRING: - this.value = (RpmTagValue) new RpmTagValue<>(makeString(storeData)); + this.value = new RpmTagValue<>(makeString(storeData)); break; case BLOB: - this.value = (RpmTagValue) new RpmTagValue<>(makeBlob(storeData)); + this.value = new RpmTagValue<>(makeBlob(storeData)); break; case STRING_ARRAY: case I18N_STRING: - this.value = (RpmTagValue) new RpmTagValue<>(IntStream.range(0, this.count).mapToObj(i -> makeString(storeData)).toArray(String[]::new)); + this.value = new RpmTagValue<>(IntStream.range(0, this.count).mapToObj(i -> makeString(storeData)).toArray(String[]::new)); break; } } diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/parse/InputHeader.java b/rpm/src/main/java/org/eclipse/packager/rpm/parse/InputHeader.java index 072ad35..d1727b9 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/parse/InputHeader.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/parse/InputHeader.java @@ -13,6 +13,7 @@ package org.eclipse.packager.rpm.parse; +import java.lang.reflect.Array; import java.util.Arrays; import java.util.Collections; import java.util.LinkedHashMap; @@ -25,15 +26,15 @@ import org.eclipse.packager.rpm.RpmTagValue; public class InputHeader implements ReadableHeader { - private final Map> entries; + private final Map entries; private final long start; private final long length; - public InputHeader(final HeaderValue[] entries, final long start, final long length) { - final Map> tags = new LinkedHashMap<>(entries.length); - for (final HeaderValue entry : entries) { + public InputHeader(final HeaderValue[] entries, final long start, final long length) { + final Map tags = new LinkedHashMap<>(entries.length); + for (final HeaderValue entry : entries) { tags.put(entry.getTag(), entry); } @@ -70,17 +71,6 @@ public boolean hasTag(final T tag) { return hasTag(tag.getValue()); } - public E get(T tag) { - Optional> optHeaderValue = getOptionalTag(tag, tag.getDataType()); - if (optHeaderValue.isPresent()) { - HeaderValue headerValue = optHeaderValue.get(); - RpmTagValue rpmTagValue = headerValue.getValue(); - return rpmTagValue.getValue(); - } - - return null; - } - @Override public String getString(T tag) { if (!String.class.isAssignableFrom(tag.getDataType()) && !String[].class.isAssignableFrom(tag.getDataType())) { @@ -148,24 +138,47 @@ public byte[] getByteArray(T tag) { return getOptionalTag(tag, byte[].class).flatMap(headerValue -> headerValue.getValue().asByteArray()).orElse(null); } - public Optional> getOptionalTag(final int tag, Class dataType) { + public Optional getOptionalTag(final int tag, Class dataType) { return getEntry(tag, dataType); } - public Optional> getOptionalTag(final T tag, Class dataType) { + public Optional getOptionalTag(final T tag, Class dataType) { return getOptionalTag(tag.getValue(), dataType); } - @SuppressWarnings("unchecked") - private Optional> getEntry(final int tag, Class dataType) { - return Optional.ofNullable((HeaderValue) this.entries.get(tag)); + private Optional getEntry(final int tag, Class dataType) { + final HeaderValue headerValue = this.entries.get(tag); + + if (headerValue == null) { + return Optional.empty(); + } + + final RpmTagValue rpmTagValue = headerValue.getValue(); + final Object value = rpmTagValue.getValue(); + Object v = value; + + if (value == null) { + return Optional.empty(); + } + + if (dataType.isArray() && !v.getClass().isArray()) { + final Class arrayType = Array.newInstance(v.getClass(), 0).getClass(); + + if (!arrayType.isAssignableFrom(dataType)) { + throw new IllegalArgumentException("Tag " + tag + " is type " + v.getClass().getSimpleName() + " which is an array, but not assignable from " + dataType.getSimpleName()); + } + } else if (!v.getClass().isAssignableFrom(dataType)) { + throw new IllegalArgumentException("Tag " + tag + " is type " + v.getClass().getSimpleName() + " which is not assignable from " + dataType.getSimpleName()); + } + + return Optional.of(headerValue); } - private Optional> getEntry(final T tag, Class dataType) { + private Optional getEntry(final T tag, Class dataType) { return getEntry(tag.getValue(), dataType); } - public Map> getRawTags() { + public Map getRawTags() { return this.entries; } } diff --git a/rpm/src/main/java/org/eclipse/packager/rpm/parse/RpmInputStream.java b/rpm/src/main/java/org/eclipse/packager/rpm/parse/RpmInputStream.java index 79a1ada..cb74078 100644 --- a/rpm/src/main/java/org/eclipse/packager/rpm/parse/RpmInputStream.java +++ b/rpm/src/main/java/org/eclipse/packager/rpm/parse/RpmInputStream.java @@ -183,7 +183,7 @@ protected InputHeader readHeader(final boolean withPad final int indexCount = this.in.readInt(); final int storeSize = this.in.readInt(); - final HeaderValue[] entries = new HeaderValue[indexCount]; + final HeaderValue[] entries = new HeaderValue[indexCount]; for (int i = 0; i < indexCount; i++) { entries[i] = readEntry(); @@ -210,13 +210,13 @@ protected InputHeader readHeader(final boolean withPad return new InputHeader<>(entries, start, end - start); } - private HeaderValue readEntry() throws IOException { + private HeaderValue readEntry() throws IOException { final int tag = this.in.readInt(); final int type = this.in.readInt(); final int offset = this.in.readInt(); final int count = this.in.readInt(); - return new HeaderValue<>(tag, type, offset, count); + return new HeaderValue(tag, type, offset, count); } private byte[] readComplete(final int size) throws IOException {