Package com.aelitis.azureus.core.devices.impl

Source Code of com.aelitis.azureus.core.devices.impl.DeviceDriveManager

/*
* Created on Jul 31, 2009
* Created by Paul Gardner
*
* Copyright 2009 Vuze, Inc.  All rights reserved.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; version 2 of the License only.
*
* This program 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 for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307, USA.
*/


package com.aelitis.azureus.core.devices.impl;

import java.io.*;
import java.util.*;

import org.gudy.azureus2.core3.util.AERunnable;
import org.gudy.azureus2.core3.util.AsyncDispatcher;

import com.aelitis.azureus.core.devices.Device;
import com.aelitis.azureus.core.devices.DeviceManagerListener;
import com.aelitis.azureus.core.devices.DeviceMediaRenderer;
import com.aelitis.azureus.core.devices.DeviceTemplate;
import com.aelitis.azureus.core.drivedetector.DriveDetectedInfo;
import com.aelitis.azureus.core.drivedetector.DriveDetectedListener;
import com.aelitis.azureus.core.drivedetector.DriveDetectorFactory;
import com.aelitis.azureus.util.MapUtils;

public class
DeviceDriveManager
  implements DriveDetectedListener
{
  private DeviceManagerImpl    manager;
 
  private Map<String,DeviceMediaRendererManual>  device_map = new HashMap<String, DeviceMediaRendererManual>();
 
  private AsyncDispatcher  async_dispatcher = new AsyncDispatcher();
 
  private boolean  listener_added;
 
  protected
  DeviceDriveManager(
    DeviceManagerImpl    _manager )
  {
    manager = _manager;
   
    manager.addListener(
      new DeviceManagerListener()
      {
        public void
        deviceAdded(
          Device    device )
        { 
        }
       
        public void
        deviceChanged(
          Device    device )
        {
        }
       
        public void
        deviceAttentionRequest(
          Device    device )
        {
        }
       
        public void
        deviceRemoved(
          Device    device )
        {
          synchronized( device_map ){
           
            Iterator<Map.Entry<String,DeviceMediaRendererManual>> it = device_map.entrySet().iterator();
           
            while( it.hasNext()){
             
              Map.Entry<String,DeviceMediaRendererManual> entry = it.next();
             
              if ( entry.getValue() == device ){
               
                it.remove();
              }
            }
          }
        }

        public void
        deviceManagerLoaded()
        {
        }
      });
   
    if ( manager.getAutoSearch()){
     
      listener_added = true;
     
      DriveDetectorFactory.getDeviceDetector().addListener( this );
    }
  }
 
  protected void
  search()
  {
    async_dispatcher.dispatch(
      new AERunnable()
      {
        public void
        runSupport()
        {
          if ( listener_added ){
           
            DriveDetectedInfo[] info = DriveDetectorFactory.getDeviceDetector().getDetectedDriveInfo();
           
            for ( DriveDetectedInfo i: info ){
             
              driveRemoved( i );
             
              driveDetected( i );
            }
           
            return;
          }
         
          try{
              // this should synchronously first any discovered drives
           
            DriveDetectorFactory.getDeviceDetector().addListener( DeviceDriveManager.this );

          }finally{
           
            DriveDetectorFactory.getDeviceDetector().removeListener( DeviceDriveManager.this );
          }
        }
      });
  }
 
  public void
  driveDetected(
    final DriveDetectedInfo info )
{
    //System.out.println("DD " + info.getLocation() + " via " + Debug.getCompressedStackTrace());
    async_dispatcher.dispatch(new AERunnable() {
      public void runSupport() {
       
        Map<String, Object> infoMap = info.getInfoMap();

        boolean isWritableUSB = MapUtils.getMapBoolean(infoMap, "isWritableUSB", false);
       
        File root = info.getLocation();

        String sProdID = MapUtils.getMapString(infoMap, "ProductID",
            MapUtils.getMapString(infoMap, "Product Name", "")).trim();
        String sVendor = MapUtils.getMapString(infoMap, "VendorID",
            MapUtils.getMapString(infoMap, "Vendor Name", "")).trim();

        // Historically, we gave IDs to Motorola, Samsung, and HTC phones
        // based on their vendor and product id only.  We need to maintain
        // this ID in order to not create duplicates.
        // Fortunately, both Motorola and Samsung include their model id in the
        // sProdID.  HTC doesn't, however, their PID doesn't identify unique
        // models anyway, so including that wouldn't have helped anyway
        if ((sVendor.equalsIgnoreCase("htc") && sProdID.equalsIgnoreCase("android phone"))
            || (sVendor.toLowerCase().contains("motorola") && sProdID.length() > 0)
            || sVendor.equalsIgnoreCase("samsung")) {
         
          if (isWritableUSB && sVendor.equalsIgnoreCase("samsung")) {
            // Samsungs that start with Y are MP3 players
            // Samsungs that don't have a dash aren't smart phones (none that we know of anyway..)
            // Fake not writable so we remove the device instead of adding it
            isWritableUSB = !sProdID.startsWith("Y")
                && sProdID.matches(".*[A-Z]-.*");
          }

          String name = sProdID.startsWith(sVendor) ? "" : sVendor;
          if (sVendor.length() > 0) {
            name += " ";
          }
          name += sProdID;

          String id = "android.";
          id += sProdID.replaceAll(" ", ".").toLowerCase();
          if (sVendor.length() > 0) {
            id += "." + sVendor.replaceAll(" ", ".").toLowerCase();
          }
         
          if (isWritableUSB) {
            addDevice(name, id, root, new File(root, "videos"), true);
          } else {
            //Fixup old bug where we were adding Samsung hard drives as devices
            Device existingDevice = getDeviceMediaRendererByClassification(id);
            if (existingDevice != null) {
              existingDevice.remove();
            }
          }
          return;
        } else if (isWritableUSB && sVendor.toLowerCase().equals("rim")) {
          String name = sVendor;
          if (name.length() > 0) {
            name += " ";
          }
          name += sProdID;
          String id = "";
          id += sProdID.replaceAll(" ", ".").toLowerCase();
          if (sVendor.length() > 0) {
            id += "." + sVendor.replaceAll(" ", ".").toLowerCase();
          }
          DeviceMediaRendererManual device = addDevice(name, id, root, new File(root, "videos"), false);
          if (device != null) {
            device.setImageID("bb");
          }
          return;
        }
       
        if (!isWritableUSB) {
          return;
        }

        if (root.exists()) {

          File[] folders = root.listFiles();

          if (folders != null) {

            Set<String> names = new HashSet<String>();

            for (File file : folders) {

              names.add(file.getName().toLowerCase());
            }

            if (names.contains("psp") && names.contains("video")) {
              addDevice("PSP", "sony.PSP", root, new File(root, "VIDEO"), false);
              return;
            }
          }
        }
       
        String pid = MapUtils.getMapString(infoMap, "PID", null);
        String vid = MapUtils.getMapString(infoMap, "VID", null);
        if (pid != null && vid != null) {
          String name = sProdID.startsWith(sVendor) ? "" : sVendor;
          if (name.length() > 0) {
            name += " ";
          }
          name += sProdID;

          String id = "";
          id += sProdID.replaceAll(" ", ".").toLowerCase();
          id += "." + pid.toLowerCase();
          if (sVendor.length() > 0) {
            id += "." + sVendor.replaceAll(" ", ".").toLowerCase();
          }
          id += "." + vid.toLowerCase();
         
          // cheap hack to detect the PSP when it has no psp or video dir
          if (id.equals("\"psp\".ms.02d2.sony.054c")
              || id.equals("\"psp\".ms.0381.sony.054c")) {
            if (addDevice("PSP", "sony.PSP", root, new File(root, "VIDEO"), false) != null) {
              return;
            }
          }
         
          addDevice(name, id, root, new File(root, "video"), true);
        }
      }
    });
  }
 
  protected DeviceMediaRenderer getDeviceMediaRendererByClassification(String target_classification) {
    DeviceImpl[] devices = manager.getDevices();
   
    for ( DeviceImpl device: devices ){
     
      if ( device instanceof DeviceMediaRenderer ){
     
        DeviceMediaRenderer renderer = (DeviceMediaRenderer)device;
       
        String classification = renderer.getClassification();
     
        if ( classification.equalsIgnoreCase( target_classification )){
                               
          return renderer;
        }
      }
    }

    return null;
  }

  protected DeviceMediaRendererManual addDevice(
      String target_name,
      String target_classification,
      File root,
      File target_directory,
      boolean generic)
  {
   
    DeviceMediaRenderer existingDevice = getDeviceMediaRendererByClassification(target_classification);
    if (existingDevice instanceof DeviceMediaRendererManual ) {
      mapDevice( (DeviceMediaRendererManual) existingDevice, root, target_directory );
     
      existingDevice.setGenericUSB(generic);
      return (DeviceMediaRendererManual) existingDevice;
    }
   
    DeviceTemplate[] templates = manager.getDeviceTemplates( Device.DT_MEDIA_RENDERER );
   
    DeviceMediaRendererManual  renderer = null;
   
    for ( DeviceTemplate template: templates ){
     
      if ( template.getClassification().equalsIgnoreCase( target_classification )){
       
        try{
          renderer = (DeviceMediaRendererManual)template.createInstance( target_name );

          break;
         
        }catch( Throwable e ){
         
          log( "Failed to add device", e );
        }
      }
    }
   
    if ( renderer == null ){
     
        // damn, the above doesn't work until devices is turned on...
     
      try{
        renderer = (DeviceMediaRendererManual)manager.createDevice( Device.DT_MEDIA_RENDERER, null, target_classification, target_name, true );
       
      }catch( Throwable e ){
       
        log( "Failed to add device", e );
      }
    }
   
    if ( renderer != null ){
     
      try{
        renderer.setAutoCopyToFolder( true );
        // This will cause a change event
        renderer.setGenericUSB(generic);
       
        mapDevice( renderer, root, target_directory );
       
        return renderer;
       
      }catch( Throwable e ){
       
        log( "Failed to add device", e );
      }
    }
    return renderer;
  }

  public void
  driveRemoved(
    final DriveDetectedInfo info )
  {
    async_dispatcher.dispatch(
      new AERunnable()
      {
        public void
        runSupport()
        {
          unMapDevice( info.getLocation());
        }
      });
  }
 
  protected void
  mapDevice(
    DeviceMediaRendererManual    renderer,
    File              root,
    File              copy_to )
  {
    DeviceMediaRendererManual  existing;
   
    synchronized( device_map ){
     
      existing = device_map.put( root.getAbsolutePath(), renderer );
    }
   
    if ( existing != null && existing != renderer ){
     
      log( "Unmapped " + existing.getName() + " from " + root );
     
      existing.setCopyToFolder( null );
    }
   
    log( "Mapped " + renderer.getName() + " to " + root );

    renderer.setCopyToFolder( copy_to );
   
    renderer.setLivenessDetectable( true );
   
    renderer.alive();
  }
 
  protected void
  unMapDevice(
    File              root )
  {
    DeviceMediaRendererManual existing;
   
    synchronized( device_map ){
     
      existing = device_map.remove( root.getAbsolutePath());
    }
   
    if ( existing != null ){
     
      log( "Unmapped " + existing.getName() + " from " + root );

      existing.setCopyToFolder( null );
     
      existing.dead();
    }
  }
 
  protected void
  log(
    String str )
  {
    manager.log( "DriveMan: " + str );
  }
 
  protected void
  log(
    String     str,
    Throwable   e )
  {
    manager.log( "DriveMan: " + str, e );
  }
}
TOP

Related Classes of com.aelitis.azureus.core.devices.impl.DeviceDriveManager

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.