Library.java

/*
 * Created on 2010/06/11
 * Copyright (C) 2010 Koga Laboratory. All rights reserved.
 *
 */
package org.mklab.cga.platform;

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;

import org.mklab.cga.round.FPU;


/**
 * ネイティブライブラリのロードを行うクラスです。
 * 
 * @author nakashima
 * @version $Revision$, 2010/06/11
 */
public class Library {

  /**
   * ライブラリをロードします。
   * 
   * @param libname ネイティブライブラリ名
   * @throws IOException ロードに失敗した場合
   */
  public static void loadlibrary(String libname) throws IOException {
    try {
      System.loadLibrary(libname);
    } catch (UnsatisfiedLinkError e) {
      final String path = System.getProperty("java.io.tmpdir") + File.separator + "cga"; //$NON-NLS-1$ //$NON-NLS-2$
      final File dir = new File(path);
      dir.deleteOnExit();
      if (!dir.exists() || dir.isDirectory()) dir.mkdir();
      final String lib = System.mapLibraryName(libname);
      try {
        extract(path + File.separator + lib, lib);
      } catch (IOException e1) {
        throw e1;
      } finally {
        if (dir.exists()) dir.delete();
      }
    }
  }

  /**
   * ライブラリを作成してロードします。
   * 
   * @param fileName ネイティブライブラリのパス
   * @param mappedName ネイティブライブラリ名
   * @throws IOException ロードに失敗した場合
   */
  private static void extract(String fileName, String mappedName) throws IOException {
    FileOutputStream outstrm = null;
    InputStream instrm = null;
    final File file = new File(fileName);
    file.deleteOnExit();
    boolean extracted = false;
    try {
      if (!file.exists()) {
        instrm = FPU.class.getResourceAsStream(mappedName);
        if (instrm != null) {
          extracted = true;
          int read;
          final byte[] buffer = new byte[4096];
          outstrm = new FileOutputStream(fileName);
          while ((read = instrm.read(buffer)) != -1) {
            outstrm.write(buffer, 0, read);
          }
          outstrm.close();
          instrm.close();
        }
      }
      System.load(fileName);
    } catch (IOException e) {
      throw e;
    } catch (Throwable e) {
      throw new RuntimeException(e);
    } finally {
      if (outstrm != null) outstrm.close();
      if (instrm != null) instrm.close();
      if (extracted && file.exists()) file.delete();
    }
  }
}