Mercurial > hg > truffle
view graal/com.oracle.max.base/src/com/sun/max/io/Files.java @ 4213:e4cfa571d8c4
Do not emit stack-to-stack moves.
author | Christian Wimmer <Christian.Wimmer@Oracle.com> |
---|---|
date | Tue, 03 Jan 2012 18:47:27 -0800 |
parents | bc8527f3071c |
children |
line wrap: on
line source
/* * Copyright (c) 2007, 2011, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License version 2 only, as * published by the Free Software Foundation. * * This code is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * version 2 for more details (a copy is included in the LICENSE file that * accompanied this code). * * You should have received a copy of the GNU General Public License version * 2 along with this work; if not, write to the Free Software Foundation, * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. * * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA * or visit www.oracle.com if you need additional information or have any * questions. */ package com.sun.max.io; import java.io.*; import java.util.*; import java.util.zip.*; import com.sun.max.program.*; import com.sun.max.util.*; /** */ public final class Files { private Files() { } public static void copy(File from, File to) throws FileNotFoundException, IOException { InputStream inputStream = null; OutputStream outputStream = null; try { inputStream = new FileInputStream(from); outputStream = new FileOutputStream(to); Streams.copy(inputStream, outputStream); } finally { if (inputStream != null) { inputStream.close(); } if (outputStream != null) { outputStream.close(); } } } public static boolean equals(File file1, File file2) throws FileNotFoundException, IOException { final long length1 = file1.length(); final long length2 = file2.length(); if (length1 != length2) { return false; } if (length1 <= 0) { return true; } InputStream inputStream1 = null; InputStream inputStream2 = null; try { inputStream1 = new BufferedInputStream(new FileInputStream(file1), (int) length1); inputStream2 = new BufferedInputStream(new FileInputStream(file2), (int) length2); return Streams.equals(inputStream1, inputStream2); } finally { if (inputStream1 != null) { inputStream1.close(); } if (inputStream2 != null) { inputStream2.close(); } } } public static boolean equals(File file, Iterator<String> lines) throws FileNotFoundException, IOException { final BufferedReader bufferedReader = new BufferedReader(new FileReader(file)); try { String line; while ((line = bufferedReader.readLine()) != null) { if (!lines.hasNext()) { return false; } if (!line.equals(lines.next())) { return false; } } } finally { bufferedReader.close(); } return !lines.hasNext(); } public static byte[] toBytes(File file) throws IOException { if (file.length() > Integer.MAX_VALUE) { throw new IOException("file is too big to read into an array: " + file); } final InputStream stream = new BufferedInputStream(new FileInputStream(file), (int) file.length()); try { return Streams.readFully(stream, new byte[(int) file.length()]); } finally { stream.close(); } } /** * Creates/overwrites a file with a given string. */ public static void fill(File file, String content) throws IOException { final BufferedWriter bufferedWriter = new BufferedWriter(new FileWriter(file)); try { bufferedWriter.write(content); } finally { bufferedWriter.close(); } } /** * Creates/overwrites a file from a reader. */ public static void fill(File file, Reader reader) throws IOException { final BufferedWriter bufferedWriter = new BufferedWriter(new FileWriter(file)); try { int ch; while ((ch = reader.read()) != -1) { bufferedWriter.write(ch); } } finally { bufferedWriter.close(); } } public static void readLines(File file, List<String> lines) throws IOException { final BufferedReader reader = new BufferedReader(new FileReader(file)); String line; while ((line = reader.readLine()) != null) { lines.add(line); } reader.close(); } public static List<String> readLines(File file) throws IOException { final List<String> lines = new ArrayList<>(); readLines(file, lines); return lines; } public static char[] toChars(File file) throws IOException { if (file.length() > Integer.MAX_VALUE) { throw new IOException("file is too big to read into an array: " + file); } int length = (int) file.length(); if (length == 0) { return new char[0]; } final Reader fileReader = new BufferedReader(new FileReader(file), length); char[] chars = new char[length]; try { chars = Streams.readFully(fileReader, chars); } catch (TruncatedInputException truncatedInputException) { // Must have been multi-byte characters in the file length = truncatedInputException.inputLength(); final char[] oldChars = chars; chars = new char[length]; System.arraycopy(oldChars, 0, chars, 0, length); } finally { fileReader.close(); } return chars; } /** * Updates the generated content part of a file. A generated content part is delimited by a line containing only * {@code start} and a line containing only {@code end}. If the given file already exists and has these delimiters, * the content between these lines is compared with {@code content} and replaced if it is different. If the file * does not exist, a new file is created with {@code content} surrounded by the specified delimiters. If the file * exists and does not currently have the specified delimiters, an IOException is thrown. * * @param file the file to be modified (or created) with some generated content * @param content the generated content * @param start the starting delimiter of the section in {@code file} to be updated with {@code content} * @param start the ending delimiter of the section in {@code file} to be updated with {@code content} * @param checkOnly if {@code true}, then {@code file} is not updated; the value returned by this method indicates * whether it would have been updated were this argument {@code true} * @return true if {@code file} was modified or created (or would have been if {@code checkOnly} was {@code false}) */ public static boolean updateGeneratedContent(File file, ReadableSource content, String start, String end, boolean checkOnly) throws IOException { if (!file.exists()) { if (checkOnly) { return true; } final PrintWriter printWriter = new PrintWriter(new BufferedWriter(new FileWriter(file))); try { final Reader reader = content.reader(true); try { printWriter.println(start); Streams.copy(reader, printWriter); printWriter.println(end); } finally { reader.close(); } } finally { printWriter.close(); } return true; } final File tempFile = File.createTempFile(file.getName() + ".", null); PrintWriter printWriter = null; BufferedReader contentReader = null; BufferedReader existingFileReader = null; try { printWriter = new PrintWriter(new BufferedWriter(new FileWriter(tempFile))); contentReader = (BufferedReader) content.reader(true); existingFileReader = new BufferedReader(new FileReader(file)); // Copy existing file up to generated content opening delimiter String line; while ((line = existingFileReader.readLine()) != null) { printWriter.println(line); if (line.equals(start)) { break; } } if (line == null) { throw new IOException("generated content starting delimiter \"" + start + "\" not found in existing file: " + file); } boolean changed = false; boolean seenEnd = false; // Copy new content, noting if it differs from existing generated content while ((line = contentReader.readLine()) != null) { if (!seenEnd) { final String existingLine = existingFileReader.readLine(); if (existingLine != null) { if (end.equals(existingLine)) { seenEnd = true; changed = true; } else { changed = changed || !line.equals(existingLine); } } } printWriter.println(line); } // Find the generated content closing delimiter if (!seenEnd) { while ((line = existingFileReader.readLine()) != null) { if (line.equals(end)) { seenEnd = true; break; } changed = true; } if (!seenEnd) { throw new IOException("generated content ending delimiter \"" + end + "\" not found in existing file: " + file); } } printWriter.println(end); // Copy existing file after generated content closing delimiter while ((line = existingFileReader.readLine()) != null) { printWriter.println(line); } printWriter.close(); printWriter = null; existingFileReader.close(); existingFileReader = null; if (changed) { if (!checkOnly) { copy(tempFile, file); } return true; } return false; } finally { quietClose(printWriter); quietClose(contentReader); quietClose(existingFileReader); if (!tempFile.delete()) { throw new IOException("could not delete file for update: " + file); } } } private static void quietClose(Closeable closeable) { if (closeable != null) { try { closeable.close(); } catch (IOException e) { e.printStackTrace(); } } } public static List<File> find(File directory, final String suffix, List<File> listing) { final Predicate<File> suffixPredicate = new Predicate<File>() { public boolean evaluate(File file) { return file.getName().endsWith(suffix); } }; return find(directory, suffixPredicate, listing); } public static List<File> find(File directory, Predicate<File> filter, List<File> listing) { assert directory.isDirectory(); return find(directory, listing == null ? new LinkedList<File>() : listing, filter); } private static List<File> find(File directory, List<File> listing, Predicate<File> filter) { assert directory.isDirectory(); final File[] entries = directory.listFiles(); if (entries != null) { for (File entry : entries) { if (!entry.isDirectory()) { if (filter == null || filter.evaluate(entry)) { listing.add(entry); } } else { find(entry, listing, filter); } } } return listing; } public static void unzip(File zip, File destDir) { if (!destDir.exists() && !destDir.mkdirs()) { throw ProgramError.unexpected("Could not make directory " + destDir); } Enumeration entries; ZipFile zipFile; try { Trace.line(2, "Extracting contents of " + zip.getAbsolutePath() + " to " + destDir); zipFile = new ZipFile(zip); entries = zipFile.entries(); while (entries.hasMoreElements()) { final ZipEntry entry = (ZipEntry) entries.nextElement(); final File parentDir; if (entry.isDirectory()) { parentDir = new File(destDir, entry.getName()); } else { final String relParentDir = new File(entry.getName()).getParent(); if (relParentDir != null) { parentDir = new File(destDir, relParentDir); } else { parentDir = destDir; } } if (!parentDir.exists() && !parentDir.mkdirs()) { throw ProgramError.unexpected("Could not make directory " + parentDir); } if (!entry.isDirectory()) { final File destFile = new File(destDir, entry.getName()); Trace.line(2, " inflating: " + entry.getName() + " ..."); FileOutputStream os = new FileOutputStream(destFile); Streams.copy(zipFile.getInputStream(entry), os); os.close(); } } zipFile.close(); } catch (IOException ioe) { throw ProgramError.unexpected("Error extracting " + zip.getAbsolutePath() + " to " + destDir, ioe); } } public static boolean compareFiles(File f1, File f2, String[] ignoredLinePatterns) { try { final BufferedReader f1Reader = new BufferedReader(new FileReader(f1)); final BufferedReader f2Reader = new BufferedReader(new FileReader(f2)); try { String line1; String line2; nextLine: while (true) { line1 = f1Reader.readLine(); line2 = f2Reader.readLine(); if (line1 == null) { if (line2 == null) { return true; } return false; } if (!line1.equals(line2)) { if (line2 == null) { return false; } if (ignoredLinePatterns != null) { for (String pattern : ignoredLinePatterns) { if (line1.contains(pattern) && line2.contains(pattern)) { continue nextLine; } } } return false; } } } finally { f1Reader.close(); f2Reader.close(); } } catch (IOException e) { return false; } } }