1 /*******************************************************************************
2 * Copyright (c) 2004, 2015 IBM Corporation and others.
3 * All rights reserved. This program and the accompanying materials
4 * are made available under the terms of the Eclipse Public License v1.0
5 * which accompanies this distribution, and is available at
6 * http://www.eclipse.org/legal/epl-v10.html
9 * IBM Corporation - initial API and implementation
10 * Remy Chi Jian Suen <remy.suen@gmail.com> - Bug 243347 TarFile should not throw NPE in finalize()
11 * Marc-Andre Laperle <marc-andre.laperle@ericsson.com> - Bug 463633
12 * Marc-Andre Laperle <marc-andre.laperle@ericsson.com> - Copied to Trace Compass to work around bug 501379
13 *******************************************************************************/
15 package org
.eclipse
.tracecompass
.internal
.tmf
.ui
.project
.wizards
.importtrace
;
18 import java
.io
.FileInputStream
;
19 import java
.io
.IOException
;
20 import java
.io
.InputStream
;
21 import java
.util
.Enumeration
;
23 import org
.apache
.commons
.compress
.archivers
.tar
.TarArchiveEntry
;
24 import org
.apache
.commons
.compress
.archivers
.tar
.TarArchiveInputStream
;
25 import org
.apache
.commons
.compress
.compressors
.gzip
.GzipCompressorInputStream
;
29 * Reads a .tar or .tar.gz archive file, providing an index enumeration
30 * and allows for accessing an InputStream for arbitrary files in the
33 public class TarFile
{
35 private TarArchiveInputStream entryEnumerationStream
;
36 private TarArchiveEntry curEntry
;
37 private TarArchiveInputStream entryStream
;
39 private InputStream internalEntryStream
;
40 // This field is just to prevent try with resources error and keep the code
41 // similar to the original
42 private InputStream fInputStream
;
45 * Create a new TarFile for the given file.
47 * @param file the file
48 * @throws IOException on i/o error (bad format, etc)
50 public TarFile(File file
) throws IOException
{
53 fInputStream
= new FileInputStream(file
);
54 // First, check if it's a GZIPInputStream.
56 fInputStream
= new GzipCompressorInputStream(fInputStream
);
57 } catch (IOException e
) {
58 //If it is not compressed we close
59 //the old one and recreate
61 fInputStream
= new FileInputStream(file
);
63 entryEnumerationStream
= new TarArchiveInputStream(fInputStream
);
65 curEntry
= (TarArchiveEntry
) entryEnumerationStream
.getNextEntry();
66 } catch (IOException e
) {
73 * Close the tar file input stream.
75 * @throws IOException if the file cannot be successfully closed
77 public void close() throws IOException
{
78 if (entryEnumerationStream
!= null) {
79 entryEnumerationStream
.close();
81 if (internalEntryStream
!= null) {
82 internalEntryStream
.close();
87 * Create a new TarFile for the given path name.
89 * @param filename the file name to create the TarFile from
90 * @throws IOException on i/o error (bad format, etc)
92 public TarFile(String filename
) throws IOException
{
93 this(new File(filename
));
97 * Returns an enumeration cataloguing the tar archive.
99 * @return enumeration of all files in the archive
101 public Enumeration
<TarArchiveEntry
> entries() {
102 return new Enumeration
<TarArchiveEntry
>() {
104 public boolean hasMoreElements() {
105 return (curEntry
!= null);
109 public TarArchiveEntry
nextElement() {
110 TarArchiveEntry oldEntry
= curEntry
;
112 curEntry
= (TarArchiveEntry
) entryEnumerationStream
.getNextEntry();
113 } catch(IOException e
) {
122 * Returns a new InputStream for the given file in the tar archive.
124 * @param entry the entry to get the InputStream from
125 * @return an input stream for the given file
126 * @throws IOException on i/o error (bad format, etc)
128 public InputStream
getInputStream(TarArchiveEntry entry
) throws IOException
{
129 if(entryStream
== null || !skipToEntry(entryStream
, entry
)) {
130 if (internalEntryStream
!= null) {
131 internalEntryStream
.close();
133 internalEntryStream
= new FileInputStream(file
);
134 // First, check if it's a GzipCompressorInputStream.
136 internalEntryStream
= new GzipCompressorInputStream(internalEntryStream
);
137 } catch(IOException e
) {
138 //If it is not compressed we close
139 //the old one and recreate
140 internalEntryStream
.close();
141 internalEntryStream
= new FileInputStream(file
);
143 entryStream
= new TarArchiveInputStream(internalEntryStream
) {
145 public void close() {
146 // Ignore close() since we want to reuse the stream.
149 skipToEntry(entryStream
, entry
);
154 private static boolean skipToEntry(TarArchiveInputStream entryStream
, TarArchiveEntry entry
) throws IOException
{
155 TarArchiveEntry e
= entryStream
.getNextTarEntry();
157 if (e
.equals(entry
)) {
161 e
= entryStream
.getNextTarEntry();
168 * Returns the path name of the file this archive represents.
172 public String
getName() {
173 return file
.getPath();
177 protected void finalize() throws Throwable
{