You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@cloudstack.apache.org by al...@apache.org on 2012/07/04 02:35:29 UTC

[15/50] [abbrv] moving out NetApp code to plugins/file-systems/netapp

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/plugins/file-systems/netapp/src/com/cloud/netapp/NetappManagerImpl.java
----------------------------------------------------------------------
diff --git a/plugins/file-systems/netapp/src/com/cloud/netapp/NetappManagerImpl.java b/plugins/file-systems/netapp/src/com/cloud/netapp/NetappManagerImpl.java
new file mode 100644
index 0000000..7dcb9d3
--- /dev/null
+++ b/plugins/file-systems/netapp/src/com/cloud/netapp/NetappManagerImpl.java
@@ -0,0 +1,1040 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package com.cloud.netapp;
+
+import java.io.IOException;
+import java.net.UnknownHostException;
+import java.rmi.ServerException;
+import java.util.ArrayList;
+import java.util.ConcurrentModificationException;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+import java.util.StringTokenizer;
+
+import javax.ejb.Local;
+import javax.naming.ConfigurationException;
+
+import netapp.manage.NaAPIFailedException;
+import netapp.manage.NaAuthenticationException;
+import netapp.manage.NaElement;
+import netapp.manage.NaException;
+import netapp.manage.NaProtocolException;
+import netapp.manage.NaServer;
+
+import org.apache.log4j.Logger;
+
+import com.cloud.exception.InvalidParameterValueException;
+import com.cloud.exception.ResourceAllocationException;
+import com.cloud.exception.ResourceInUseException;
+import com.cloud.netapp.dao.LunDao;
+import com.cloud.netapp.dao.PoolDao;
+import com.cloud.netapp.dao.VolumeDao;
+import com.cloud.utils.component.Inject;
+import com.cloud.utils.db.DB;
+import com.cloud.utils.db.Transaction;
+import com.cloud.utils.exception.CloudRuntimeException;
+
+@Local(value = { NetappManager.class })
+public class NetappManagerImpl implements NetappManager
+{   
+	public enum Algorithm { roundrobin,leastfull }
+
+    protected String _name;
+    
+    public static final Logger s_logger = Logger.getLogger(NetappManagerImpl.class.getName());
+    @Inject public VolumeDao _volumeDao;
+    @Inject public PoolDao _poolDao;
+    @Inject public LunDao _lunDao;
+    private NetappAllocator _netappAllocator = null;
+    
+    /**
+     * Default constructor
+     */
+    public NetappManagerImpl(){
+    }
+    
+    @Override
+    public  void createPool(String poolName, String algorithm) throws InvalidParameterValueException
+    {	
+		if(s_logger.isDebugEnabled())
+			s_logger.debug("Request --> createPool ");
+		
+    	PoolVO pool = null;
+    	validAlgorithm(algorithm);
+    	try {
+    		pool = new PoolVO(poolName, algorithm);
+    		_poolDao.persist(pool); 
+    		
+    		if(s_logger.isDebugEnabled())
+    			s_logger.debug("Response --> createPool:success");
+    		
+    	} catch (CloudRuntimeException cre){
+    		pool = _poolDao.findPool(poolName);
+        	if (pool != null) {
+        		throw new InvalidParameterValueException("Duplicate Pool Name");
+        	} else {
+        		throw cre;
+        	}
+    	}
+    }
+    
+    /**
+     * This method validates the algorithm used for allocation of the volume
+     * @param algorithm -- algorithm type
+     * @throws InvalidParameterValueException
+     */
+    private void validAlgorithm(String algorithm) throws InvalidParameterValueException {
+    	//TODO: use enum
+    	if(!algorithm.equalsIgnoreCase("roundrobin") && !algorithm.equalsIgnoreCase("leastfull")){
+    		throw new InvalidParameterValueException("Unknown algorithm " + algorithm);
+    	}
+    }
+    
+    /**
+     * Utility method to get the netapp server object
+     * @param serverIp -- ip address of netapp box
+     * @param userName -- username
+     * @param password -- password
+     * @return
+     * @throws UnknownHostException
+     */
+    private NaServer getServer(String serverIp, String userName, String password) throws UnknownHostException {
+    	//Initialize connection to server, and
+		//request version 1.3 of the API set
+    	NaServer s = new NaServer(serverIp, 1, 3); 
+		s.setStyle(NaServer.STYLE_LOGIN_PASSWORD);
+		s.setAdminUser(userName, password); 
+    	
+		return s;
+    }
+    
+    @Override
+    public void modifyPool(String poolName, String algorithm) throws InvalidParameterValueException
+    {	
+    	validAlgorithm(algorithm);
+    	PoolVO pool = _poolDao.findPool(poolName);
+    	
+    	if(pool == null){
+    		throw new InvalidParameterValueException("Cannot find pool " + poolName);
+    	}
+    	
+    	validAlgorithm(algorithm);
+    	
+    	pool.setAlgorithm(algorithm);
+    	pool.setName(poolName);
+    	
+    	_poolDao.update(pool.getId(), pool);
+    }
+    
+    @Override
+    public void deletePool(String poolName) throws InvalidParameterValueException, ResourceInUseException
+    {
+		if(s_logger.isDebugEnabled())
+			s_logger.debug("Request --> deletePool ");
+		
+    	PoolVO pool = _poolDao.findPool(poolName);
+    	if(pool == null){
+    		throw new InvalidParameterValueException("Cannot find pool " + poolName);
+    	}
+    	//check if pool is empty
+    	int volCount = _volumeDao.listVolumes(poolName).size();
+
+    	if(volCount==0){
+    		_poolDao.remove(pool.getId());
+		if(s_logger.isDebugEnabled())
+			s_logger.debug("Request --> deletePool: Success ");
+    		
+    	} else {
+    		throw new ResourceInUseException("Cannot delete non-empty pool");
+    	}
+    }
+    
+    @Override
+    public List<PoolVO> listPools(){
+    	return _poolDao.listAll();
+    }
+    
+    /**
+     * This method destroys the volume on netapp filer
+     * @param ipAddress -- ip address of filer
+     * @param aggrName -- name of containing aggregate
+     * @param volName -- name of volume to destroy
+     * @throws ResourceInUseException 
+     * @throws NaException
+     * @throws IOException
+     * @throws NaProtocolException 
+     * @throws NaAPIFailedException 
+     * @throws NaAuthenticationException 
+     */
+    @Override
+    @DB
+    public void destroyVolumeOnFiler(String ipAddress, String aggrName, String volName) throws ServerException, InvalidParameterValueException, ResourceInUseException{
+		NaElement xi0;
+    	NaElement xi1;
+ 		NetappVolumeVO volume = null;
+		
+ 		volume = _volumeDao.findVolume(ipAddress, aggrName, volName);
+ 		
+ 		if(volume==null)
+ 		{
+ 			s_logger.warn("The volume does not exist in our system");
+ 			throw new InvalidParameterValueException("The given tuple:"+ipAddress+","+aggrName+","+volName+" doesn't exist in our system");
+ 		}
+
+ 		List<LunVO> lunsOnVol = _lunDao.listLunsByVolId(volume.getId());
+ 		
+ 		if(lunsOnVol!=null && lunsOnVol.size()>0)
+ 		{
+ 			s_logger.warn("There are luns on the volume");
+ 			throw new ResourceInUseException("There are luns on the volume");
+ 		}
+ 		
+ 		final Transaction txn = Transaction.currentTxn();
+ 		txn.start();
+ 		PoolVO pool = _poolDao.findById(volume.getPoolId());
+ 		if (pool == null) {
+ 			throw new InvalidParameterValueException("Failed to find pool for given volume");
+ 			//FIXME: choose a better exception. this is a db integrity exception
+ 		}
+ 		pool = _poolDao.acquireInLockTable(pool.getId());
+ 		if (pool == null) {
+ 			throw new ConcurrentModificationException("Failed to acquire lock on pool " + volume.getPoolId());
+ 		}
+		NaServer s = null;
+		try 
+		{
+			s = getServer(volume.getIpAddress(), volume.getUsername(), volume.getPassword());
+			//bring the volume down
+			xi0 = new NaElement("volume-offline");
+			xi0.addNewChild("name",volName);
+			s.invokeElem(xi0);
+
+			//now destroy it
+			xi1 = new NaElement("volume-destroy");
+			xi1.addNewChild("name",volName);
+			s.invokeElem(xi1);
+
+			//now delete from our records
+			_volumeDao.remove(volume.getId());
+			txn.commit();
+
+		} catch (UnknownHostException uhe) {
+			s_logger.warn("Unable to delete volume on filer " , uhe);
+			throw new ServerException("Unable to delete volume on filer", uhe);
+		}catch (NaAPIFailedException naf) {
+			s_logger.warn("Unable to delete volume on filer " , naf);
+			if( naf.getErrno() == 13040 ){
+				s_logger.info("Deleting the volume: " + volName);
+				_volumeDao.remove(volume.getId());
+				txn.commit();
+			}
+			
+			throw new ServerException("Unable to delete volume on filer", naf);
+		} 
+		catch (NaException nae) {
+			txn.rollback();
+			s_logger.warn("Unable to delete volume on filer " , nae);
+			throw new ServerException("Unable to delete volume on filer", nae);
+		} catch (IOException ioe) {
+			txn.rollback();
+			s_logger.warn("Unable to delete volume on filer " , ioe);
+			throw new ServerException("Unable to delete volume on filer", ioe);
+		}
+		finally
+		{
+			if (pool != null) {
+				_poolDao.releaseFromLockTable(pool.getId());
+			}
+			if (s != null)
+				s.close();
+		}
+
+
+			
+    }
+    
+    /**
+     * This method creates a volume on netapp filer
+     * @param ipAddress -- ip address of the filer
+     * @param aggName -- name of aggregate
+     * @param poolName -- name of pool
+     * @param volName -- name of volume
+     * @param volSize -- size of volume to be created
+     * @param snapshotPolicy -- associated snapshot policy for volume
+     * @param snapshotReservation -- associated reservation for snapshots
+     * @param username -- username
+     * @param password -- password
+     * @throws UnknownHostException
+     * @throws InvalidParameterValueException 
+     */
+    @Override
+    @DB
+	public void createVolumeOnFiler(String ipAddress, String aggName, String poolName, String volName, String volSize, String snapshotPolicy, Integer snapshotReservation, String username, String password) throws  UnknownHostException,  ServerException, InvalidParameterValueException 
+	{
+  
+		if(s_logger.isDebugEnabled())
+			s_logger.debug("Request --> createVolume "+"serverIp:"+ipAddress);
+		
+		boolean snapPolicy = false;
+		boolean snapshotRes = false;
+		boolean volumeCreated = false;
+		
+		NaServer s = getServer(ipAddress, username, password); 
+		
+		NaElement xi = new NaElement("volume-create");
+		xi.addNewChild("volume", volName);
+		xi.addNewChild("containing-aggr-name",aggName);
+		xi.addNewChild("size",volSize);
+		
+		NaElement xi1 = new NaElement("snapshot-set-reserve");
+		if(snapshotReservation!=null)
+		{
+			snapshotRes = true;
+			xi1.addNewChild("percentage",snapshotReservation.toString());
+			xi1.addNewChild("volume",volName);
+		}
+		
+		NaElement xi2 = new NaElement("snapshot-set-schedule");
+		
+		if(snapshotPolicy!=null)
+		{
+			snapPolicy = true;
+			
+			String weeks = null;
+			String days = null;
+			String hours = null;
+			String whichHours = null;
+			String minutes = null;
+			String whichMinutes = null;
+			
+			StringTokenizer s1 = new StringTokenizer(snapshotPolicy," ");
+			
+			//count=4: weeks days hours@csi mins@csi
+			//count=3: weeks days hours@csi
+			//count=2: weeks days
+			//count=1: weeks
+	
+			if(s1.hasMoreTokens())
+			{
+				weeks = s1.nextToken();
+			}
+			if(weeks!=null && s1.hasMoreTokens())
+			{
+				days = s1.nextToken();
+			}
+			if(days!=null && s1.hasMoreTokens())
+			{
+				String[] hoursArr = s1.nextToken().split("@");
+				hours = hoursArr[0];
+				whichHours = hoursArr[1];
+			}
+			if(hours!=null && s1.hasMoreTokens())
+			{
+				String[] minsArr = s1.nextToken().split("@");
+				minutes = minsArr[0];
+				whichMinutes = minsArr[1];
+			}
+			
+			if(weeks!=null)
+				xi2.addNewChild("weeks",weeks);
+			if(days!=null)
+				xi2.addNewChild("days",days);
+			if(hours!=null)
+				xi2.addNewChild("hours",hours);
+			if(minutes!=null)
+				xi2.addNewChild("minutes",minutes);
+			xi2.addNewChild("volume",volName);
+			
+			if(whichHours!=null)
+				xi2.addNewChild("which-hours",whichHours);
+			if(whichMinutes!=null)
+				xi2.addNewChild("which-minutes",whichMinutes);
+		}
+		Long volumeId = null;
+		
+		final Transaction txn = Transaction.currentTxn();
+		txn.start();
+		NetappVolumeVO volume = null;
+		volume = _volumeDao.findVolume(ipAddress, aggName, volName);
+		
+		if(volume != null) {
+			throw new InvalidParameterValueException("The volume for the given ipAddress/aggregateName/volumeName tuple already exists");
+		}
+		PoolVO pool = _poolDao.findPool(poolName);
+		if (pool == null) {
+			throw new InvalidParameterValueException("Cannot find pool " + poolName);
+		}
+		pool = _poolDao.acquireInLockTable(pool.getId());
+		if (pool == null) {
+			s_logger.warn("Failed to acquire lock on pool " + poolName);
+			throw new ConcurrentModificationException("Failed to acquire lock on pool " + poolName);
+		}
+		volume = new NetappVolumeVO(ipAddress, aggName, pool.getId(), volName, volSize, "", 0, username, password,0,pool.getName());
+		volume = _volumeDao.persist(volume);
+		
+		volumeId = volume.getId();
+		try {
+			s.invokeElem(xi);
+			volumeCreated = true;
+			
+			if(snapshotRes)
+			{
+				s.invokeElem(xi1);
+				volume.setSnapshotReservation(snapshotReservation);
+				_volumeDao.update(volumeId, volume);
+			}
+
+			if(snapPolicy)
+			{
+				s.invokeElem(xi2);
+				volume.setSnapshotPolicy(snapshotPolicy);
+				_volumeDao.update(volumeId, volume);
+			}	
+			txn.commit();
+		} catch (NaException nae) {
+			//zapi call failed, log and throw e
+			s_logger.warn("Failed to create volume on the netapp filer:", nae);
+			txn.rollback();
+			if(volumeCreated) {
+				try {
+					deleteRogueVolume(volName, s);//deletes created volume on filer
+				} catch (NaException e) {
+					s_logger.warn("Failed to cleanup created volume whilst rolling back on the netapp filer:", e);
+					throw new ServerException("Unable to create volume via cloudtools."+"Failed to cleanup created volume on netapp filer whilst rolling back on the cloud db:", e);
+				} catch (IOException e) {
+					s_logger.warn("Failed to cleanup created volume whilst rolling back on the netapp filer:", e);
+					throw new ServerException("Unable to create volume via cloudtools."+"Failed to cleanup created volume on netapp filer whilst rolling back on the cloud db:", e);
+				}
+			}
+			throw new ServerException("Unable to create volume", nae);
+		} catch (IOException ioe) {
+			s_logger.warn("Failed to create volume on the netapp filer:", ioe);
+			txn.rollback();
+			if(volumeCreated) {
+				try {
+					deleteRogueVolume(volName, s);//deletes created volume on filer
+				} catch (NaException e) {
+					s_logger.warn("Failed to cleanup created volume whilst rolling back on the netapp filer:", e);
+					throw new ServerException("Unable to create volume via cloudtools."+"Failed to cleanup created volume on netapp filer whilst rolling back on the cloud db:", e);
+				} catch (IOException e) {
+					s_logger.warn("Failed to cleanup created volume whilst rolling back on the netapp filer:", e);
+					throw new ServerException("Unable to create volume via cloudtools."+"Failed to cleanup created volume on netapp filer whilst rolling back on the cloud db:", e);
+				}
+			}
+			throw new ServerException("Unable to create volume", ioe);
+		}
+		finally{
+			if (s != null) 
+				s.close();
+			if (pool != null) 
+				_poolDao.releaseFromLockTable(pool.getId());
+			
+		}
+	}
+	
+    /**
+     * This method is primarily used to cleanup volume created on the netapp filer, when createVol api command fails at snapshot reservation. 
+     * We roll back the db record, but the record on the netapp box still exists. We clean up that record using this helper method.
+     * @param volName
+     * @param s -- server reference
+     * @throws NaException
+     * @throws IOException
+     */
+    private void deleteRogueVolume(String volName, NaServer s) throws NaException, IOException {
+		//bring the volume down
+		NaElement xi0 = new NaElement("volume-offline");
+		xi0.addNewChild("name",volName);
+		s.invokeElem(xi0);
+
+		//now destroy it
+		NaElement xi1 = new NaElement("volume-destroy");
+		xi1.addNewChild("name",volName);
+		s.invokeElem(xi1);
+    }
+    
+	/**
+	 * This method lists all the volumes by pool name
+	 * @param poolName
+	 * @return -- volumes in that pool
+	 */
+    @Override
+	public List<NetappVolumeVO> listVolumesOnFiler(String poolName){
+		
+    	List<NetappVolumeVO> vols = _volumeDao.listVolumesAscending(poolName);
+    	
+    	for(NetappVolumeVO vol : vols){
+    		try {
+				String snapScheduleOnFiler = returnSnapshotSchedule(vol);
+				vol.setSnapshotPolicy(snapScheduleOnFiler);
+				
+			} catch (ServerException e) {
+				s_logger.warn("Error trying to get snapshot schedule for volume"+vol.getVolumeName());
+			}
+    	}
+		return vols;
+	}
+
+    
+    /**
+     * Utility method to return snapshot schedule for a volume
+     * @param vol -- volume for the snapshot schedule creation
+     * @return -- the snapshot schedule
+     * @throws ServerException
+     */
+    private String returnSnapshotSchedule(NetappVolumeVO vol) throws ServerException{
+
+		NaElement xi = new NaElement("snapshot-get-schedule");
+		xi.addNewChild("volume", vol.getVolumeName());
+		NaServer s = null;
+		try {
+			s = getServer(vol.getIpAddress(), vol.getUsername(), vol.getPassword());
+			NaElement xo = s.invokeElem(xi);
+			String weeks = xo.getChildContent("weeks");
+			String days = xo.getChildContent("days");
+			String hours = xo.getChildContent("hours");
+			String minutes = xo.getChildContent("minutes");
+			String whichHours = xo.getChildContent("which-hours");
+			String whichMinutes = xo.getChildContent("which-minutes");
+			
+			StringBuilder sB = new StringBuilder();
+			sB.append(weeks).append(" ").append(days).append(" ").append(hours).append("@").append(whichHours).append(" ").append(minutes).append("@").append(whichMinutes);
+			return sB.toString();
+		} catch (NaException nae) {
+			s_logger.warn("Failed to get volume size ", nae);
+			throw new ServerException("Failed to get volume size", nae);
+		} catch (IOException ioe) {
+			s_logger.warn("Failed to get volume size ", ioe);
+			throw new ServerException("Failed to get volume size", ioe);
+		}
+		finally{
+			if (s != null)
+				s.close();
+		}
+    }
+	/**
+	 * This method returns the ascending order list of volumes based on their ids
+	 * @param poolName -- name of pool
+	 * @return -- ascending ordered list of volumes based on ids
+	 */
+    @Override
+	public List<NetappVolumeVO> listVolumesAscending(String poolName){
+		return _volumeDao.listVolumesAscending(poolName);
+	}
+	
+	/**
+	 * This method returns the available size on the volume in terms of bytes
+	 * @param volName -- name of volume
+	 * @param userName -- username
+	 * @param password -- password
+	 * @param serverIp -- ip address of filer
+	 * @throws UnknownHostException 
+	 * @return-- available size on the volume in terms of bytes; return -1 if volume is offline
+	 * @throws ServerException
+	 */
+    @Override
+	public long returnAvailableVolumeSize(String volName, String userName, String password, String serverIp) throws ServerException {	
+		long availableSize = 0;
+
+		NaElement xi = new NaElement("volume-list-info");
+		xi.addNewChild("volume", volName);
+		NaServer s = null;
+		String volumeState = null;
+		try {
+			s = getServer(serverIp, userName, password);
+			NaElement xo = s.invokeElem(xi);
+			List volList = xo.getChildByName("volumes").getChildren();
+			Iterator volIter = volList.iterator();
+			while(volIter.hasNext()){
+				NaElement volInfo=(NaElement)volIter.next();
+				availableSize = volInfo.getChildLongValue("size-available", -1);
+				volumeState = volInfo.getChildContent("state");
+			}
+			
+			if (volumeState != null) {
+				return volumeState.equalsIgnoreCase("online") ? availableSize : -1; //return -1 if volume is offline
+			}
+			else {
+				//catch all
+				//volume state unreported
+				return -1; // as good as volume offline
+			}
+				
+			
+		} catch (NaException nae) {
+			s_logger.warn("Failed to get volume size ", nae);
+			throw new ServerException("Failed to get volume size", nae);
+		} catch (IOException ioe) {
+			s_logger.warn("Failed to get volume size ", ioe);
+			throw new ServerException("Failed to get volume size", ioe);
+		}
+		finally{
+			if (s != null)
+				s.close();
+		}
+	}
+
+	/**
+	 * This method creates a lun on the netapp filer
+	 * @param poolName -- name of the pool
+	 * @param lunSize -- size of the lun to be created
+	 * @return -- lun path 
+	 * @throws IOException
+	 * @throws ResourceAllocationException 
+	 * @throws NaException
+	 */
+    @Override
+    @DB
+	public String[] createLunOnFiler(String poolName, Long lunSize) throws  ServerException, InvalidParameterValueException, ResourceAllocationException {
+    	String[] result = new String[3];
+		StringBuilder lunName = new StringBuilder("lun-");
+		LunVO lun = null;
+    	final Transaction txn = Transaction.currentTxn();
+		txn.start();
+    	PoolVO pool = _poolDao.findPool(poolName);
+    	
+    	if(pool == null){
+    		throw new InvalidParameterValueException("Cannot find pool " + poolName);
+    	}
+
+    	if (lunSize <= 0) {
+    		throw new InvalidParameterValueException("Please specify a valid lun size in Gb");
+    	}
+    	
+    	String algorithm = pool.getAlgorithm();
+    	NetappVolumeVO selectedVol = null;
+
+    	//sanity check
+    	int numVolsInPool = _volumeDao.listVolumes(poolName).size();
+
+    	if (numVolsInPool == 0)
+    	{
+    		throw new InvalidParameterValueException("No volumes exist in the given pool");
+    	}
+    	pool = _poolDao.acquireInLockTable(pool.getId());
+    	if (pool == null) {
+    		s_logger.warn("Failed to acquire lock on the pool " + poolName);
+    		return result;
+    	}
+    	NaServer s = null;
+
+    	try 
+    	{
+    		if(algorithm == null || algorithm.equals(Algorithm.roundrobin.toString()))
+    		{
+    			selectedVol = _netappAllocator.chooseVolumeFromPool(poolName, lunSize);
+    		}
+    		else if(algorithm.equals(Algorithm.leastfull.toString()))
+    		{
+
+    			selectedVol = _netappAllocator.chooseLeastFullVolumeFromPool(poolName, lunSize);
+    		}
+
+    		if(selectedVol == null)
+    		{
+    			throw new ServerException("Could not find a suitable volume to create lun on");
+    		}
+
+    		if(s_logger.isDebugEnabled())
+    			s_logger.debug("Request --> createLun "+"serverIp:"+selectedVol.getIpAddress());
+    		
+    		StringBuilder exportPath = new StringBuilder("/vol/");
+    		exportPath.append(selectedVol.getVolumeName());
+    		exportPath.append("/");
+
+    		lun = new LunVO(exportPath.toString(), selectedVol.getId(), lunSize, "","");
+    		lun = _lunDao.persist(lun);
+    		
+    		//Lun id created: 6 digits right justified eg. 000045
+    		String lunIdStr = lun.getId().toString();
+    		String zeroStr = "000000";
+    		int length = lunIdStr.length();
+    		int offset = 6-length;
+    		StringBuilder lunIdOnPath = new StringBuilder();
+    		lunIdOnPath.append(zeroStr.substring(0, offset));
+    		lunIdOnPath.append(lunIdStr);
+    		exportPath.append("lun-").append(lunIdOnPath.toString());
+    		
+    		lunName.append(lunIdOnPath.toString());
+    		
+    		//update lun name
+    		lun.setLunName(lunName.toString());
+    		_lunDao.update(lun.getId(), lun);
+    		
+    		NaElement xi;
+    		NaElement xi1;
+
+    		long lSizeBytes = 1L*lunSize*1024*1024*1024; //This prevents integer overflow
+    		Long lunSizeBytes = new Long(lSizeBytes);
+    		
+    		s = getServer(selectedVol.getIpAddress(), selectedVol.getUsername(),selectedVol.getPassword()); 
+
+    		//create lun
+    		xi = new NaElement("lun-create-by-size");
+    		xi.addNewChild("ostype","linux");
+    		xi.addNewChild("path",exportPath.toString());
+    		xi.addNewChild("size", (lunSizeBytes.toString()));
+    		
+    		s.invokeElem(xi);	
+
+    		try
+    		{
+	    		//now create an igroup
+				xi1 = new NaElement("igroup-create");
+				xi1.addNewChild("initiator-group-name", lunName .toString());
+				xi1.addNewChild("initiator-group-type", "iscsi");
+				xi1.addNewChild("os-type", "linux");
+				s.invokeElem(xi1);
+    		}catch(NaAPIFailedException e)
+    		{
+    			if(e.getErrno() == 9004)
+    			{
+    				//igroup already exists hence no error
+    				s_logger.warn("Igroup already exists");
+    			}
+    		}
+
+    		//get target iqn
+			NaElement xi4 = new NaElement("iscsi-node-get-name");
+			NaElement xo = s.invokeElem(xi4);
+			String iqn = xo.getChildContent("node-name");
+			
+			lun.setTargetIqn(iqn);
+			_lunDao.update(lun.getId(), lun);
+			
+			//create lun mapping
+			//now map the lun to the igroup
+			NaElement xi3 = new NaElement("lun-map");
+			xi3.addNewChild("force", "true");
+			xi3.addNewChild("initiator-group", lunName.toString());
+			xi3.addNewChild("path", lun.getPath() + lun.getLunName());
+			
+			xi3.addNewChild("lun-id", lunIdStr);
+			s.invokeElem(xi3);
+    		
+    		txn.commit();
+    		//set the result
+    		result[0] = lunName.toString();//lunname
+    		result[1] = iqn;//iqn
+    		result[2] =  selectedVol.getIpAddress();
+    		
+    		return result;
+    		
+    	}
+    	catch (NaAPIFailedException naf)
+    	{
+			if(naf.getErrno() == 9023){ //lun is already mapped to this group
+				result[0] = lunName.toString();//lunname;
+				result[1] = lun.getTargetIqn();//iqn
+				result[2] = selectedVol.getIpAddress();
+				return result;
+			}			
+			if(naf.getErrno() == 9024){ //another lun mapped at this group
+				result[0] = lunName.toString();//lunname;
+				result[1] = lun.getTargetIqn();//iqn
+				result[2] = selectedVol.getIpAddress();
+				return result;
+			}	
+    	}
+    	catch (NaException nae) 
+    	{
+    		txn.rollback();
+    		throw new ServerException("Unable to create LUN", nae);
+    	} 
+    	catch (IOException ioe) 
+    	{
+    		txn.rollback();
+    		throw new ServerException("Unable to create LUN", ioe);
+    	}
+    	finally
+    	{
+    		if (pool != null) {
+    			_poolDao.releaseFromLockTable(pool.getId());
+    		}
+    		if (s != null) {
+    			s.close();
+    		}
+    	}
+
+    	return result;
+	}
+	
+	/**
+	 * This method destroys a lun on the netapp filer
+	 * @param lunName -- name of the lun to be destroyed
+	 */
+    @Override
+    @DB
+	public void destroyLunOnFiler(String lunName) throws InvalidParameterValueException, ServerException{
+		
+		final Transaction txn = Transaction.currentTxn();
+		txn.start();
+		
+		LunVO lun = _lunDao.findByName(lunName);
+		
+		if(lun == null)
+			throw new InvalidParameterValueException("Cannot find lun");
+		
+		NetappVolumeVO vol = _volumeDao.acquireInLockTable(lun.getVolumeId());
+		if (vol == null) {
+			s_logger.warn("Failed to lock volume id= " + lun.getVolumeId());
+			return;
+		}
+		NaServer s = null;
+		try {
+			s = getServer(vol.getIpAddress(), vol.getUsername(), vol.getPassword()); 
+			
+			if(s_logger.isDebugEnabled())
+				s_logger.debug("Request --> destroyLun "+":serverIp:"+vol.getIpAddress());
+			
+			try {
+				//Unmap lun
+				NaElement xi2 = new NaElement("lun-unmap");
+				xi2.addNewChild("initiator-group", lunName);
+				xi2.addNewChild("path", lun.getPath()+lun.getLunName());
+				s.invokeElem(xi2);
+			} catch (NaAPIFailedException naf) {
+				if(naf.getErrno()==9016)
+					s_logger.warn("no map exists excpn 9016 caught in deletelun, continuing with delete");
+			}
+
+			//destroy lun
+			NaElement xi = new NaElement("lun-destroy");
+			xi.addNewChild("force","true");
+			xi.addNewChild("path", lun.getPath()+lun.getLunName());
+			s.invokeElem(xi);
+			
+			//destroy igroup
+			NaElement xi1 = new NaElement("igroup-destroy");
+			//xi1.addNewChild("force","true");
+			xi1.addNewChild("initiator-group-name",lunName);
+			s.invokeElem(xi1);
+			
+			_lunDao.remove(lun.getId());
+			txn.commit();
+		} catch(UnknownHostException uhe) {
+			txn.rollback();
+			s_logger.warn("Failed to delete lun", uhe);
+			throw new ServerException("Failed to delete lun", uhe);
+		} catch ( IOException ioe) {
+			txn.rollback();
+			s_logger.warn("Failed to delete lun", ioe);
+			throw new ServerException("Failed to delete lun", ioe);
+		}catch (NaAPIFailedException naf) {
+			if(naf.getErrno() == 9017){//no such group exists excpn
+				s_logger.warn("no such group exists excpn 9017 caught in deletelun, continuing with delete");
+				_lunDao.remove(lun.getId());
+				txn.commit();
+			}else if(naf.getErrno() == 9029){//LUN maps for this initiator group exist
+				s_logger.warn("LUN maps for this initiator group exist errno 9029 caught in deletelun, continuing with delete");
+				_lunDao.remove(lun.getId());
+				txn.commit();
+			}else{
+				txn.rollback();
+				s_logger.warn("Failed to delete lun", naf);
+				throw new ServerException("Failed to delete lun", naf);
+			}
+
+		} 
+		catch (NaException nae) {
+			txn.rollback();
+			s_logger.warn("Failed to delete lun", nae);
+			throw new ServerException("Failed to delete lun", nae);
+		}
+		finally{
+			if (vol != null) {
+				_volumeDao.releaseFromLockTable(vol.getId());
+			}
+			if (s != null)
+				s.close();
+		}
+
+	}
+	
+	/**
+	 * This method lists the luns on the netapp filer
+	 * @param volId -- id of the containing volume
+	 * @return -- list of netapp luns
+	 * @throws NaException
+	 * @throws IOException
+	 */
+    @Override
+    public List<LunVO> listLunsOnFiler(String poolName)
+	{
+		if(s_logger.isDebugEnabled())
+			s_logger.debug("Request --> listLunsOnFiler ");
+		
+    	List<LunVO> luns = new ArrayList<LunVO>();
+    	
+    	List<NetappVolumeVO> vols = _volumeDao.listVolumes(poolName);
+    	
+    	for(NetappVolumeVO vol : vols)
+    	{
+    		luns.addAll(_lunDao.listLunsByVolId(vol.getId()));
+    	}
+    
+		if(s_logger.isDebugEnabled())
+			s_logger.debug("Response --> listLunsOnFiler:success");
+    	
+    	return luns;
+	}
+	
+
+	/**
+	 * This method disassociates a lun from the igroup on the filer
+	 * @param iGroup -- igroup name
+	 * @param lunName -- lun name
+	 */
+    @Override
+	public void disassociateLun(String iGroup, String lunName) throws ServerException, InvalidParameterValueException
+	{
+		NaElement xi;
+		LunVO lun = _lunDao.findByName(lunName);
+		
+		if(lun == null)
+			throw new InvalidParameterValueException("Cannot find LUN " + lunName);
+		
+		NetappVolumeVO vol = _volumeDao.findById(lun.getVolumeId());
+		NaServer s = null;
+		try {
+			s = getServer(vol.getIpAddress(), vol.getUsername(), vol.getPassword());
+			
+			if(s_logger.isDebugEnabled())
+				s_logger.debug("Request --> disassociateLun "+":serverIp:"+vol.getIpAddress());
+			
+			xi = new NaElement("igroup-remove");
+			xi.addNewChild("force", "true");
+			xi.addNewChild("initiator", iGroup);
+			xi.addNewChild("initiator-group-name", lunName);		
+			s.invokeElem(xi);
+			
+		} catch(UnknownHostException uhe) {
+			throw new ServerException("Failed to disassociate lun", uhe);
+		} catch ( IOException ioe) {
+			throw new ServerException("Failed to disassociate lun", ioe);
+		} catch (NaException nae) {
+			throw new ServerException("Failed to disassociate lun", nae);
+		} finally{
+			if (s != null)
+				s.close();
+		}
+		
+	}
+	
+	/**
+	 * This method associates a lun to a particular igroup
+	 * @param iqn
+	 * @param iGroup
+	 * @param lunName
+	 */
+    @Override
+	public String[] associateLun(String guestIqn, String lunName) throws ServerException, InvalidParameterValueException
+
+	{
+		NaElement xi2;
+
+		//get lun id from path
+		String[] splitLunName = lunName.split("-");
+		String[] returnVal = new String[3];
+		if(splitLunName.length != 2)
+			throw new InvalidParameterValueException("The lun id is malformed");
+		
+		String lunIdStr = splitLunName[1]; 
+
+		Long lId = new Long(lunIdStr);
+		
+		LunVO lun = _lunDao.findById(lId);
+		
+		if(lun == null)
+			throw new InvalidParameterValueException("Cannot find LUN " + lunName);
+		
+		NetappVolumeVO vol = _volumeDao.findById(lun.getVolumeId());
+
+		//assert(vol != null);
+		
+		returnVal[0] = lunIdStr;
+		returnVal[1] = lun.getTargetIqn();
+		returnVal[2] = vol.getIpAddress();
+		
+		NaServer s = null;
+		
+		try
+		{
+			s = getServer(vol.getIpAddress(), vol.getUsername(), vol.getPassword()); 
+			
+			if(s_logger.isDebugEnabled())
+				s_logger.debug("Request --> associateLun "+":serverIp:"+vol.getIpAddress());
+			
+			//add iqn to the group
+			xi2 = new NaElement("igroup-add");
+			xi2.addNewChild("force", "true");
+			xi2.addNewChild("initiator", guestIqn);
+			xi2.addNewChild("initiator-group-name", lunName);		
+			s.invokeElem(xi2);
+						
+			return returnVal;
+		}  catch (UnknownHostException uhe) {
+			s_logger.warn("Unable to associate LUN " , uhe);
+			throw new ServerException("Unable to associate LUN", uhe);
+		}catch (NaAPIFailedException naf){
+			if(naf.getErrno() == 9008){ //initiator group already contains node				
+				return returnVal;
+			}			
+			s_logger.warn("Unable to associate LUN " , naf);
+			throw new ServerException("Unable to associate LUN", naf);
+		}
+		catch (NaException nae) {
+			s_logger.warn("Unable to associate LUN " , nae);
+			throw new ServerException("Unable to associate LUN", nae);
+		} catch (IOException ioe) {
+			s_logger.warn("Unable to associate LUN " , ioe);
+			throw new ServerException("Unable to associate LUN", ioe);
+		}
+		finally{
+			if (s != null)
+				s.close();
+		}
+		
+	}
+
+	@Override
+	public boolean configure(String name, Map<String, Object> params)
+			throws ConfigurationException {
+
+       _name = name;
+       
+       _netappAllocator = new NetappDefaultAllocatorImpl( this );
+
+		return true;
+	}
+
+	@Override
+	public String getName() {
+		return _name;
+	}
+
+	@Override
+	public boolean start() {
+		return true;
+	}
+
+	@Override
+	public boolean stop() {
+		return true;
+	}
+	
+}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/plugins/file-systems/netapp/src/com/cloud/netapp/NetappVolumeVO.java
----------------------------------------------------------------------
diff --git a/plugins/file-systems/netapp/src/com/cloud/netapp/NetappVolumeVO.java b/plugins/file-systems/netapp/src/com/cloud/netapp/NetappVolumeVO.java
new file mode 100644
index 0000000..04318d0
--- /dev/null
+++ b/plugins/file-systems/netapp/src/com/cloud/netapp/NetappVolumeVO.java
@@ -0,0 +1,183 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package com.cloud.netapp;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Table;
+
+@Entity
+@Table(name="netapp_volume")
+public class NetappVolumeVO {
+	
+	@Id
+    @GeneratedValue(strategy=GenerationType.IDENTITY)
+    @Column(name="id")
+    private Long id;
+	
+	@Column(name="ip_address")
+    private String ipAddress;
+
+    @Column(name="aggregate_name")
+	private String aggregateName;
+
+    @Column(name="pool_id")
+    private Long poolId;
+
+	@Column(name="pool_name")
+    private String poolName;
+	
+	@Column(name="volume_name")
+    private String volumeName;
+
+	@Column(name="username")
+    private String username;
+    
+    @Column(name="password")
+    private String password;
+
+    @Column(name="snapshot_policy")
+    private String snapshotPolicy;
+    
+    @Column(name="snapshot_reservation")
+    private Integer snapshotReservation;
+    
+    @Column(name="volume_size")
+    private String volumeSize;
+    
+    @Column(name="round_robin_marker")
+    private int roundRobinMarker;
+
+	public NetappVolumeVO(){
+		
+	}
+	
+	public NetappVolumeVO(String ipAddress, String aggName, Long poolId, String volName, String volSize, String snapshotPolicy, int snapshotReservation, String username, String password, int roundRobinMarker, String poolName) {
+		this.ipAddress = ipAddress;
+		this.aggregateName = aggName;
+		this.poolId = poolId;
+		this.username = username;
+		this.password = password;
+		this.volumeName = volName;
+		this.volumeSize = volSize;
+		this.snapshotPolicy = snapshotPolicy;
+		this.snapshotReservation = snapshotReservation;
+		this.roundRobinMarker = roundRobinMarker;
+		this.poolName = poolName;
+	}
+	
+	
+    public String getPoolName() {
+		return poolName;
+	}
+
+	public void setPoolName(String poolName) {
+		this.poolName = poolName;
+	}
+
+	public int getRoundRobinMarker() {
+		return roundRobinMarker;
+	}
+
+	public void setRoundRobinMarker(int roundRobinMarker) {
+		this.roundRobinMarker = roundRobinMarker;
+	}
+
+    public String getVolumeName() {
+		return volumeName;
+	}
+
+	public void setVolumeName(String volumeName) {
+		this.volumeName = volumeName;
+	}
+
+	public String getSnapshotPolicy() {
+		return snapshotPolicy;
+	}
+
+	public void setSnapshotPolicy(String snapshotPolicy) {
+		this.snapshotPolicy = snapshotPolicy;
+	}
+
+	public Integer getSnapshotReservation() {
+		return snapshotReservation;
+	}
+
+	public void setSnapshotReservation(Integer snapshotReservation) {
+		this.snapshotReservation = snapshotReservation;
+	}
+
+	public String getVolumeSize() {
+		return volumeSize;
+	}
+
+	public void setVolumeSize(String volumeSize) {
+		this.volumeSize = volumeSize;
+	}
+	
+    public Long getId() {
+		return id;
+	}
+
+	public void setId(Long id) {
+		this.id = id;
+	}
+
+	public String getIpAddress() {
+		return ipAddress;
+	}
+
+	public void setIpAddress(String ipAddress) {
+		this.ipAddress = ipAddress;
+	}
+
+	public String getAggregateName() {
+		return aggregateName;
+	}
+
+	public void setAggregateName(String aggregateName) {
+		this.aggregateName = aggregateName;
+	}
+
+	public Long getPoolId() {
+		return poolId;
+	}
+
+	public void setPoolId(Long poolId) {
+		this.poolId = poolId;
+	}
+
+    public String getUsername() {
+		return username;
+	}
+
+	public void setUsername(String username) {
+		this.username = username;
+	}
+
+	public String getPassword() {
+		return password;
+	}
+
+	public void setPassword(String password) {
+		this.password = password;
+	}
+
+}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/plugins/file-systems/netapp/src/com/cloud/netapp/PoolVO.java
----------------------------------------------------------------------
diff --git a/plugins/file-systems/netapp/src/com/cloud/netapp/PoolVO.java b/plugins/file-systems/netapp/src/com/cloud/netapp/PoolVO.java
new file mode 100644
index 0000000..713db46
--- /dev/null
+++ b/plugins/file-systems/netapp/src/com/cloud/netapp/PoolVO.java
@@ -0,0 +1,74 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package com.cloud.netapp;
+
+import javax.persistence.Column;
+import javax.persistence.Entity;
+import javax.persistence.GeneratedValue;
+import javax.persistence.GenerationType;
+import javax.persistence.Id;
+import javax.persistence.Table;
+
+@Entity
+@Table(name="netapp_pool")
+public class PoolVO {
+	
+	public Long getId() {
+		return id;
+	}
+
+	public void setId(Long id) {
+		this.id = id;
+	}
+
+	public String getName() {
+		return name;
+	}
+
+	public void setName(String name) {
+		this.name = name;
+	}
+
+	public String getAlgorithm() {
+		return algorithm;
+	}
+
+	public void setAlgorithm(String algorithm) {
+		this.algorithm = algorithm;
+	}
+
+	@Id
+    @GeneratedValue(strategy=GenerationType.IDENTITY)
+    @Column(name="id")
+    private Long id;
+	
+	@Column(name="name")
+    private String name;
+
+    @Column(name="algorithm")
+	private String algorithm;
+
+	public PoolVO(){
+		
+	}
+	
+	public PoolVO(String name, String algorithm) {
+		this.name = name;
+		this.algorithm = algorithm;
+	}
+
+}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/plugins/file-systems/netapp/src/com/cloud/netapp/dao/LunDao.java
----------------------------------------------------------------------
diff --git a/plugins/file-systems/netapp/src/com/cloud/netapp/dao/LunDao.java b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/LunDao.java
new file mode 100644
index 0000000..24086ef
--- /dev/null
+++ b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/LunDao.java
@@ -0,0 +1,31 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package com.cloud.netapp.dao;
+
+import java.util.List;
+
+import com.cloud.netapp.LunVO;
+import com.cloud.netapp.NetappVolumeVO;
+import com.cloud.netapp.PoolVO;
+import com.cloud.utils.db.GenericDao;
+
+public interface LunDao extends GenericDao<LunVO, Long> {
+
+	List<LunVO> listLunsByVolId(Long volId);
+
+	LunVO findByName(String name);
+}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/plugins/file-systems/netapp/src/com/cloud/netapp/dao/LunDaoImpl.java
----------------------------------------------------------------------
diff --git a/plugins/file-systems/netapp/src/com/cloud/netapp/dao/LunDaoImpl.java b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/LunDaoImpl.java
new file mode 100644
index 0000000..9cc67b7
--- /dev/null
+++ b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/LunDaoImpl.java
@@ -0,0 +1,70 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package com.cloud.netapp.dao;
+
+import java.util.List;
+
+import javax.ejb.Local;
+
+import org.apache.log4j.Logger;
+
+import com.cloud.netapp.LunVO;
+import com.cloud.netapp.NetappVolumeVO;
+import com.cloud.netapp.PoolVO;
+import com.cloud.utils.db.Filter;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+@Local(value={LunDao.class})
+public class LunDaoImpl extends GenericDaoBase<LunVO, Long> implements LunDao {
+    private static final Logger s_logger = Logger.getLogger(PoolDaoImpl.class);
+		
+    protected final SearchBuilder<LunVO> LunSearch;    
+    protected final SearchBuilder<LunVO> LunNameSearch;    
+    	    
+	protected LunDaoImpl() {
+        
+        LunSearch = createSearchBuilder();
+        LunSearch.and("volumeId", LunSearch.entity().getVolumeId(), SearchCriteria.Op.EQ);
+        LunSearch.done();
+
+        LunNameSearch = createSearchBuilder();
+        LunNameSearch.and("name", LunNameSearch.entity().getLunName(), SearchCriteria.Op.EQ);
+        LunNameSearch.done();
+        
+	}
+
+	@Override
+    public List<LunVO> listLunsByVolId(Long volId) {
+		Filter searchFilter = new Filter(LunVO.class, "id", Boolean.TRUE, Long.valueOf(0), Long.valueOf(10000));
+		
+        SearchCriteria sc = LunSearch.create();
+        sc.setParameters("volumeId", volId);
+        List<LunVO> lunList = listBy(sc,searchFilter);
+        
+        return lunList;
+    }
+
+
+	@Override
+    public LunVO findByName(String name) {
+        SearchCriteria sc = LunNameSearch.create();
+        sc.setParameters("name", name);
+        return findOneBy(sc);
+    }
+}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/plugins/file-systems/netapp/src/com/cloud/netapp/dao/PoolDao.java
----------------------------------------------------------------------
diff --git a/plugins/file-systems/netapp/src/com/cloud/netapp/dao/PoolDao.java b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/PoolDao.java
new file mode 100644
index 0000000..18cebe9
--- /dev/null
+++ b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/PoolDao.java
@@ -0,0 +1,28 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package com.cloud.netapp.dao;
+
+import java.util.List;
+
+import com.cloud.netapp.PoolVO;
+import com.cloud.utils.db.GenericDao;
+
+public interface PoolDao extends GenericDao<PoolVO, Long> {
+
+	PoolVO findPool(String poolName);
+	List<PoolVO> listPools();
+}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/plugins/file-systems/netapp/src/com/cloud/netapp/dao/PoolDaoImpl.java
----------------------------------------------------------------------
diff --git a/plugins/file-systems/netapp/src/com/cloud/netapp/dao/PoolDaoImpl.java b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/PoolDaoImpl.java
new file mode 100644
index 0000000..3e23644
--- /dev/null
+++ b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/PoolDaoImpl.java
@@ -0,0 +1,67 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package com.cloud.netapp.dao;
+
+import java.util.List;
+
+import javax.ejb.Local;
+
+import org.apache.log4j.Logger;
+
+import com.cloud.netapp.PoolVO;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+@Local(value={PoolDao.class})
+public class PoolDaoImpl extends GenericDaoBase<PoolVO, Long> implements PoolDao {
+    private static final Logger s_logger = Logger.getLogger(PoolDaoImpl.class);
+		
+    protected final SearchBuilder<PoolVO> PoolSearch;
+    	    
+	protected PoolDaoImpl() {
+        
+        PoolSearch = createSearchBuilder();
+        PoolSearch.and("name", PoolSearch.entity().getName(), SearchCriteria.Op.EQ);
+        PoolSearch.done();
+        
+	}
+
+	@Override
+    public PoolVO findPool(String poolName) {
+        SearchCriteria sc = PoolSearch.create();
+        sc.setParameters("name", poolName);
+        List<PoolVO> poolList = listBy(sc);
+        
+        return(poolList.size()>0?poolList.get(0):null);
+    }
+
+	@Override
+	public List<PoolVO> listPools() {
+		// TODO Auto-generated method stub
+		return null;
+	}
+
+    
+//    @Override
+//    public List<NetappStoragePoolVO> listVolumes(String poolName) {
+//        SearchCriteria sc = NetappListVolumeSearch.create();
+//        sc.setParameters("poolName", poolName);
+//        return listBy(sc);
+//    }
+    
+}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/plugins/file-systems/netapp/src/com/cloud/netapp/dao/VolumeDao.java
----------------------------------------------------------------------
diff --git a/plugins/file-systems/netapp/src/com/cloud/netapp/dao/VolumeDao.java b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/VolumeDao.java
new file mode 100644
index 0000000..7f92c3c
--- /dev/null
+++ b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/VolumeDao.java
@@ -0,0 +1,30 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package com.cloud.netapp.dao;
+
+import java.util.List;
+
+import com.cloud.netapp.NetappVolumeVO;
+import com.cloud.utils.db.GenericDao;
+
+public interface VolumeDao extends GenericDao<NetappVolumeVO, Long> {
+
+	NetappVolumeVO findVolume(String ipAddress, String aggregateName, String volumeName);
+	List<NetappVolumeVO> listVolumes(String poolName);
+	NetappVolumeVO returnRoundRobinMarkerInPool(String poolName,int roundRobinMarker);
+	List<NetappVolumeVO> listVolumesAscending(String poolName);
+}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/plugins/file-systems/netapp/src/com/cloud/netapp/dao/VolumeDaoImpl.java
----------------------------------------------------------------------
diff --git a/plugins/file-systems/netapp/src/com/cloud/netapp/dao/VolumeDaoImpl.java b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/VolumeDaoImpl.java
new file mode 100644
index 0000000..9c23410
--- /dev/null
+++ b/plugins/file-systems/netapp/src/com/cloud/netapp/dao/VolumeDaoImpl.java
@@ -0,0 +1,99 @@
+// Licensed to the Apache Software Foundation (ASF) under one
+// or more contributor license agreements.  See the NOTICE file
+// distributed with this work for additional information
+// regarding copyright ownership.  The ASF licenses this file
+// to you under the Apache License, Version 2.0 (the
+// "License"); you may not use this file except in compliance
+// with the License.  You may obtain a copy of the License at
+//
+//   http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing,
+// software distributed under the License is distributed on an
+// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+// KIND, either express or implied.  See the License for the
+// specific language governing permissions and limitations
+// under the License.
+package com.cloud.netapp.dao;
+
+import java.util.List;
+
+import javax.ejb.Local;
+
+import org.apache.log4j.Logger;
+
+import com.cloud.netapp.NetappVolumeVO;
+import com.cloud.utils.db.Filter;
+import com.cloud.utils.db.GenericDaoBase;
+import com.cloud.utils.db.SearchBuilder;
+import com.cloud.utils.db.SearchCriteria;
+
+@Local(value={VolumeDao.class})
+public class VolumeDaoImpl extends GenericDaoBase<NetappVolumeVO, Long> implements VolumeDao {
+    private static final Logger s_logger = Logger.getLogger(VolumeDaoImpl.class);
+		
+    protected final SearchBuilder<NetappVolumeVO> NetappVolumeSearch;
+    protected final SearchBuilder<NetappVolumeVO> NetappListVolumeSearch;
+    protected final SearchBuilder<NetappVolumeVO> NetappRoundRobinMarkerSearch;
+    
+    @Override
+    public NetappVolumeVO findVolume(String ipAddress, String aggregateName, String volumeName) {
+        SearchCriteria<NetappVolumeVO> sc = NetappVolumeSearch.create();
+        sc.setParameters("ipAddress", ipAddress);
+        sc.setParameters("aggregateName", aggregateName);
+        sc.setParameters("volumeName", volumeName);
+        
+        List<NetappVolumeVO>volList = listBy(sc);
+        
+        return(volList.size()==0?null:volList.get(0));
+    }
+	    
+	protected VolumeDaoImpl() {
+        NetappVolumeSearch = createSearchBuilder();
+        NetappVolumeSearch.and("ipAddress", NetappVolumeSearch.entity().getIpAddress(), SearchCriteria.Op.EQ);
+        NetappVolumeSearch.and("aggregateName", NetappVolumeSearch.entity().getAggregateName(), SearchCriteria.Op.EQ);
+        NetappVolumeSearch.and("volumeName", NetappVolumeSearch.entity().getVolumeName(), SearchCriteria.Op.EQ);
+        NetappVolumeSearch.done();
+        
+        NetappListVolumeSearch = createSearchBuilder();
+        NetappListVolumeSearch.and("poolName", NetappListVolumeSearch.entity().getPoolName(), SearchCriteria.Op.EQ);
+        NetappListVolumeSearch.done();
+        
+        NetappRoundRobinMarkerSearch = createSearchBuilder();
+        NetappRoundRobinMarkerSearch.and("roundRobinMarker", NetappRoundRobinMarkerSearch.entity().getRoundRobinMarker(), SearchCriteria.Op.EQ);
+        NetappRoundRobinMarkerSearch.and("poolName", NetappRoundRobinMarkerSearch.entity().getPoolName(), SearchCriteria.Op.EQ);
+        NetappRoundRobinMarkerSearch.done();
+	}
+
+    @Override
+    public List<NetappVolumeVO> listVolumes(String poolName) {
+        SearchCriteria<NetappVolumeVO> sc = NetappListVolumeSearch.create();
+        sc.setParameters("poolName", poolName);
+        return listBy(sc);
+    }
+    
+    @Override
+    public NetappVolumeVO returnRoundRobinMarkerInPool(String poolName, int roundRobinMarker) {
+        SearchCriteria<NetappVolumeVO> sc = NetappRoundRobinMarkerSearch.create();
+        sc.setParameters("roundRobinMarker", roundRobinMarker);
+        sc.setParameters("poolName", poolName);
+        
+        List<NetappVolumeVO> marker = listBy(sc);
+        
+        if(marker.size()>0)
+        	return marker.get(0);
+        else
+        	return null;
+    }
+    
+    @Override
+    public List<NetappVolumeVO> listVolumesAscending(String poolName)
+    {
+        Filter searchFilter = new Filter(NetappVolumeVO.class, "id", Boolean.TRUE, Long.valueOf(0), Long.valueOf(10000));
+
+        SearchCriteria<NetappVolumeVO> sc = NetappListVolumeSearch.create();
+        sc.setParameters("poolName", poolName);
+        
+        return listBy(sc, searchFilter);
+    }
+}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/server/src/com/cloud/api/commands/netapp/AssociateLunCmd.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/commands/netapp/AssociateLunCmd.java b/server/src/com/cloud/api/commands/netapp/AssociateLunCmd.java
deleted file mode 100644
index db317e0..0000000
--- a/server/src/com/cloud/api/commands/netapp/AssociateLunCmd.java
+++ /dev/null
@@ -1,100 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements.  See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership.  The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License.  You may obtain a copy of the License at
-//
-//   http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied.  See the License for the
-// specific language governing permissions and limitations
-// under the License.
-package com.cloud.api.commands.netapp;
-
-import java.rmi.ServerException;
-
-import org.apache.log4j.Logger;
-
-import com.cloud.api.ApiConstants;
-import com.cloud.api.BaseCmd;
-import com.cloud.api.Implementation;
-import com.cloud.api.Parameter;
-import com.cloud.api.ServerApiException;
-import com.cloud.exception.InvalidParameterValueException;
-import com.cloud.netapp.NetappManager;
-import com.cloud.server.ManagementService;
-import com.cloud.server.api.response.netapp.AssociateLunCmdResponse;
-import com.cloud.utils.component.ComponentLocator;
-
-@Implementation(description="Associate a LUN with a guest IQN", responseObject = AssociateLunCmdResponse.class)
-public class AssociateLunCmd extends BaseCmd {
-	public static final Logger s_logger = Logger.getLogger(AssociateLunCmd.class.getName());
-    private static final String s_name = "associatelunresponse";
-
-	/////////////////////////////////////////////////////
-    //////////////// API parameters /////////////////////
-    /////////////////////////////////////////////////////
-    
-    @Parameter(name=ApiConstants.NAME, type=CommandType.STRING, required = true, description="LUN name.")
-	private String lunName;
-    
-    @Parameter(name=ApiConstants.IQN, type=CommandType.STRING, required = true, description="Guest IQN to which the LUN associate.")
-	private String guestIqn;
-    
-    
-    ///////////////////////////////////////////////////
-	/////////////////// Accessors ///////////////////////
-	/////////////////////////////////////////////////////
-	 
-    
-    public String getLunName() {
-        return lunName;
-    }
-    
-    public String getGuestIQN() {
-    	return guestIqn;
-    }
-    
-	/////////////////////////////////////////////////////
-	/////////////// API Implementation///////////////////
-	/////////////////////////////////////////////////////
-
-	@Override
-	public String getCommandName() {
-		return s_name;
-	}
-	
-    @Override
-    public void execute(){
-    	ComponentLocator locator = ComponentLocator.getLocator(ManagementService.Name);
-    	NetappManager netappMgr = locator.getManager(NetappManager.class);
-    	
-    	try {
-    		AssociateLunCmdResponse response = new AssociateLunCmdResponse();
-    		String returnVals[] = null;
-    		returnVals = netappMgr.associateLun(getGuestIQN(), getLunName());
-    		response.setLun(returnVals[0]);
-    		response.setIpAddress(returnVals[2]);
-    		response.setTargetIQN(returnVals[1]);
-    		response.setObjectName("lun");
-    		response.setResponseName(getCommandName());
-    		this.setResponseObject(response);
-    	} catch (ServerException e) {
-    		throw new ServerApiException(BaseCmd.PARAM_ERROR, e.toString());
-    	} catch (InvalidParameterValueException e) {
-    		throw new ServerApiException(BaseCmd.INTERNAL_ERROR, e.toString());
-    	}
-    }
-
-	@Override
-	public long getEntityOwnerId() {
-		// TODO Auto-generated method stub
-		return 0;
-	}
-    
-}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/server/src/com/cloud/api/commands/netapp/CreateLunCmd.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/commands/netapp/CreateLunCmd.java b/server/src/com/cloud/api/commands/netapp/CreateLunCmd.java
deleted file mode 100644
index 2e0eb86..0000000
--- a/server/src/com/cloud/api/commands/netapp/CreateLunCmd.java
+++ /dev/null
@@ -1,98 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements.  See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership.  The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License.  You may obtain a copy of the License at
-//
-//   http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied.  See the License for the
-// specific language governing permissions and limitations
-// under the License.
-package com.cloud.api.commands.netapp;
-
-import java.rmi.ServerException;
-
-import org.apache.log4j.Logger;
-
-import com.cloud.api.ApiConstants;
-import com.cloud.api.BaseCmd;
-import com.cloud.api.Implementation;
-import com.cloud.api.Parameter;
-import com.cloud.api.ServerApiException;
-import com.cloud.exception.ConcurrentOperationException;
-import com.cloud.exception.InsufficientCapacityException;
-import com.cloud.exception.InvalidParameterValueException;
-import com.cloud.exception.ResourceAllocationException;
-import com.cloud.exception.ResourceUnavailableException;
-import com.cloud.netapp.NetappManager;
-import com.cloud.server.ManagementService;
-import com.cloud.server.api.response.netapp.CreateLunCmdResponse;
-import com.cloud.utils.component.ComponentLocator;
-
-@Implementation(description="Create a LUN from a pool", responseObject = CreateLunCmdResponse.class)
-public class CreateLunCmd extends BaseCmd {
-	public static final Logger s_logger = Logger.getLogger(CreateLunCmd.class.getName());
-    private static final String s_name = "createlunresponse";
-    
-    /////////////////////////////////////////////////////
-    //////////////// API parameters /////////////////////
-    /////////////////////////////////////////////////////
-    
-    @Parameter(name=ApiConstants.NAME, type=CommandType.STRING, required = true, description="pool name.")
-	private String poolName;
-    
-    @Parameter(name=ApiConstants.SIZE, type=CommandType.LONG, required = true, description="LUN size.")
-    private long size;
-    
-    public String getPoolName() {
-    	return poolName;
-    }
-    
-    public long getLunSize() {
-    	return size;
-    }
-
-	@Override
-	public void execute() throws ResourceUnavailableException,
-			InsufficientCapacityException, ServerApiException,
-			ConcurrentOperationException, ResourceAllocationException {
-		ComponentLocator locator = ComponentLocator.getLocator(ManagementService.Name);
-    	NetappManager netappMgr = locator.getManager(NetappManager.class);
-    	
-    	try {
-    		CreateLunCmdResponse response = new CreateLunCmdResponse();
-    		String returnVals[] = null;
-    		returnVals = netappMgr.createLunOnFiler(getPoolName(), getLunSize());
-    		response.setPath(returnVals[0]);
-    		response.setIqn(returnVals[1]);
-    		response.setIpAddress(returnVals[2]);
-    		response.setObjectName("lun");
-    		response.setResponseName(getCommandName());
-    		this.setResponseObject(response);
-    	} catch (ServerException e) {
-    		throw new ServerApiException(BaseCmd.PARAM_ERROR, e.toString());
-    	} catch (InvalidParameterValueException e) {
-    		throw new ServerApiException(BaseCmd.INTERNAL_ERROR, e.toString());
-    	}
-		
-	}
-
-	@Override
-	public String getCommandName() {
-		// TODO Auto-generated method stub
-		return s_name;
-	}
-
-	@Override
-	public long getEntityOwnerId() {
-		// TODO Auto-generated method stub
-		return 0;
-	}
-    
-}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/server/src/com/cloud/api/commands/netapp/CreateVolumeOnFilerCmd.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/commands/netapp/CreateVolumeOnFilerCmd.java b/server/src/com/cloud/api/commands/netapp/CreateVolumeOnFilerCmd.java
deleted file mode 100644
index a301dee..0000000
--- a/server/src/com/cloud/api/commands/netapp/CreateVolumeOnFilerCmd.java
+++ /dev/null
@@ -1,146 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements.  See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership.  The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License.  You may obtain a copy of the License at
-//
-//   http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied.  See the License for the
-// specific language governing permissions and limitations
-// under the License.
-package com.cloud.api.commands.netapp;
-
-import java.net.UnknownHostException;
-import java.rmi.ServerException;
-
-import com.cloud.api.ApiConstants;
-import com.cloud.api.BaseCmd;
-import com.cloud.api.Implementation;
-import com.cloud.api.Parameter;
-import com.cloud.api.ServerApiException;
-import com.cloud.exception.ConcurrentOperationException;
-import com.cloud.exception.InsufficientCapacityException;
-import com.cloud.exception.InvalidParameterValueException;
-import com.cloud.exception.ResourceAllocationException;
-import com.cloud.exception.ResourceUnavailableException;
-import com.cloud.netapp.NetappManager;
-import com.cloud.server.ManagementService;
-import com.cloud.server.api.response.netapp.CreateVolumeOnFilerCmdResponse;
-import com.cloud.utils.component.ComponentLocator;
-
-@Implementation(description="Create a volume", responseObject = CreateVolumeOnFilerCmdResponse.class)
-public class CreateVolumeOnFilerCmd extends BaseCmd {
-    private static final String s_name = "createvolumeresponse";
-
-    @Parameter(name=ApiConstants.IP_ADDRESS, type=CommandType.STRING, required = true, description="ip address.")
-	private String ipAddress;
-    
-    @Parameter(name=ApiConstants.AGGREGATE_NAME, type=CommandType.STRING, required = true, description="aggregate name.")
-	private String aggrName;
-
-    @Parameter(name=ApiConstants.POOL_NAME, type=CommandType.STRING, required = true, description="pool name.")
-	private String poolName;
-    
-    @Parameter(name=ApiConstants.VOLUME_NAME, type=CommandType.STRING, required = true, description="volume name.")
-	private String volName;
-    
-    @Parameter(name=ApiConstants.SIZE, type=CommandType.INTEGER, required = true, description="volume size.")
-	private Integer volSize;
-    
-    @Parameter(name=ApiConstants.SNAPSHOT_POLICY, type=CommandType.STRING, required = false, description="snapshot policy.")
-	private String snapshotPolicy;
-    
-    @Parameter(name=ApiConstants.SNAPSHOT_RESERVATION, type=CommandType.INTEGER, required = false, description="snapshot reservation.")
-	private Integer snapshotReservation;
-    
-    @Parameter(name=ApiConstants.USERNAME, type=CommandType.STRING, required = true, description="user name.")
-	private String userName;
-    
-    @Parameter(name=ApiConstants.PASSWORD, type=CommandType.STRING, required = true, description="password.")
-	private String password;
-    
-
-    public String getIpAddress() {
-    	return ipAddress;
-    }
-    
-    public String getAggrName() {
-    	return aggrName;
-    }
-    
-    public String getPoolName() {
-    	return poolName;
-    }
-    
-    public String volName() {
-    	return volName;
-    }
-    
-    public Integer getVolSize() {
-    	return volSize;
-    }
-    
-    public String getSnapshotPolicy() {
-    	return snapshotPolicy;
-    }
-    
-    public Integer getSnapshotReservation() {
-    	return snapshotReservation;
-    }
-    
-    public String getUserName() {
-    	return userName;
-    }
-    
-    public String getPassword() {
-    	return password;
-    }
-
-	@Override
-	public void execute() throws ResourceUnavailableException,
-			InsufficientCapacityException, ServerApiException,
-			ConcurrentOperationException, ResourceAllocationException {
-		//param checks
-		if(snapshotReservation != null && (snapshotReservation<0 || snapshotReservation>100))
-			throw new InvalidParameterValueException("Invalid snapshot reservation");
-		
-		ComponentLocator locator = ComponentLocator.getLocator(ManagementService.Name);
-    	NetappManager netappMgr = locator.getManager(NetappManager.class);
-    	
-		StringBuilder s = new StringBuilder(getVolSize().toString());
-		s.append("g");
-	
-		try {
-			netappMgr.createVolumeOnFiler(ipAddress, aggrName, poolName, volName, s.toString(), snapshotPolicy, snapshotReservation, userName, password);
-			CreateVolumeOnFilerCmdResponse response = new CreateVolumeOnFilerCmdResponse();
-			response.setResponseName(getCommandName());
-			this.setResponseObject(response);
-		} catch (ServerException e) {
-			throw new ServerApiException(BaseCmd.INTERNAL_ERROR, e.toString());
-		} catch (InvalidParameterValueException e) {
-			throw new ServerApiException(BaseCmd.PARAM_ERROR, e.toString());
-		} catch (UnknownHostException e) {
-			throw new ServerApiException(BaseCmd.PARAM_ERROR, e.toString());
-		}
-		
-	}
-
-	@Override
-	public String getCommandName() {
-		// TODO Auto-generated method stub
-		return s_name;
-	}
-
-	@Override
-	public long getEntityOwnerId() {
-		// TODO Auto-generated method stub
-		return 0;
-	}
-    
-}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/server/src/com/cloud/api/commands/netapp/CreateVolumePoolCmd.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/commands/netapp/CreateVolumePoolCmd.java b/server/src/com/cloud/api/commands/netapp/CreateVolumePoolCmd.java
deleted file mode 100644
index 020493b..0000000
--- a/server/src/com/cloud/api/commands/netapp/CreateVolumePoolCmd.java
+++ /dev/null
@@ -1,84 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements.  See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership.  The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License.  You may obtain a copy of the License at
-//
-//   http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied.  See the License for the
-// specific language governing permissions and limitations
-// under the License.
-package com.cloud.api.commands.netapp;
-
-import org.apache.log4j.Logger;
-
-import com.cloud.api.ApiConstants;
-import com.cloud.api.BaseCmd;
-import com.cloud.api.Implementation;
-import com.cloud.api.Parameter;
-import com.cloud.api.ServerApiException;
-import com.cloud.exception.ConcurrentOperationException;
-import com.cloud.exception.InsufficientCapacityException;
-import com.cloud.exception.InvalidParameterValueException;
-import com.cloud.exception.ResourceAllocationException;
-import com.cloud.exception.ResourceUnavailableException;
-import com.cloud.netapp.NetappManager;
-import com.cloud.server.ManagementService;
-import com.cloud.server.api.response.netapp.CreateVolumePoolCmdResponse;
-import com.cloud.utils.component.ComponentLocator;
-
-@Implementation(description="Create a pool", responseObject = CreateVolumePoolCmdResponse.class)
-public class CreateVolumePoolCmd extends BaseCmd {
-	public static final Logger s_logger = Logger.getLogger(CreateVolumePoolCmd.class.getName());
-    private static final String s_name = "createpoolresponse";
-
-    @Parameter(name=ApiConstants.NAME, type=CommandType.STRING, required = true, description="pool name.")
-	private String poolName;
-    @Parameter(name=ApiConstants.ALGORITHM, type=CommandType.STRING, required = true, description="algorithm.")
-	private String algorithm;
-    
-    public String getPoolName() {
-    	return poolName;
-    }
-    
-    public String getAlgorithm() {
-    	return algorithm;
-    }
-
-	@Override
-	public void execute() throws ResourceUnavailableException,
-			InsufficientCapacityException, ServerApiException,
-			ConcurrentOperationException, ResourceAllocationException {
-		ComponentLocator locator = ComponentLocator.getLocator(ManagementService.Name);
-    	NetappManager netappMgr = locator.getManager(NetappManager.class);
-    	
-    	try {
-    		CreateVolumePoolCmdResponse response = new CreateVolumePoolCmdResponse();
-    		netappMgr.createPool(getPoolName(), getAlgorithm());
-    		response.setResponseName(getCommandName());
-    		this.setResponseObject(response);
-    	} catch (InvalidParameterValueException e) {
-    		throw new ServerApiException(BaseCmd.INTERNAL_ERROR, e.toString());
-    	}
-		
-	}
-
-	@Override
-	public String getCommandName() {
-		// TODO Auto-generated method stub
-		return s_name;
-	}
-
-	@Override
-	public long getEntityOwnerId() {
-		// TODO Auto-generated method stub
-		return 0;
-	}
-    
-}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/server/src/com/cloud/api/commands/netapp/DeleteVolumePoolCmd.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/commands/netapp/DeleteVolumePoolCmd.java b/server/src/com/cloud/api/commands/netapp/DeleteVolumePoolCmd.java
deleted file mode 100644
index de12511..0000000
--- a/server/src/com/cloud/api/commands/netapp/DeleteVolumePoolCmd.java
+++ /dev/null
@@ -1,76 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements.  See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership.  The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License.  You may obtain a copy of the License at
-//
-//   http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied.  See the License for the
-// specific language governing permissions and limitations
-// under the License.
-package com.cloud.api.commands.netapp;
-
-
-import org.apache.log4j.Logger;
-
-import com.cloud.api.ApiConstants;
-import com.cloud.api.BaseCmd;
-import com.cloud.api.Implementation;
-import com.cloud.api.Parameter;
-import com.cloud.api.ServerApiException;
-import com.cloud.exception.ConcurrentOperationException;
-import com.cloud.exception.InsufficientCapacityException;
-import com.cloud.exception.InvalidParameterValueException;
-import com.cloud.exception.ResourceAllocationException;
-import com.cloud.exception.ResourceInUseException;
-import com.cloud.exception.ResourceUnavailableException;
-import com.cloud.netapp.NetappManager;
-import com.cloud.server.ManagementService;
-import com.cloud.server.api.response.netapp.DeleteVolumePoolCmdResponse;
-import com.cloud.utils.component.ComponentLocator;
-
-@Implementation(description="Delete a pool", responseObject = DeleteVolumePoolCmdResponse.class)
-public class DeleteVolumePoolCmd extends BaseCmd {
-	public static final Logger s_logger = Logger.getLogger(DeleteVolumePoolCmd.class.getName());
-    private static final String s_name = "deletepoolresponse";
-    
-    @Parameter(name=ApiConstants.POOL_NAME, type=CommandType.STRING, required = true, description="pool name.")
-	private String poolName;
-
-	@Override
-	public void execute() throws ResourceUnavailableException,
-			InsufficientCapacityException, ServerApiException,
-			ConcurrentOperationException, ResourceAllocationException {
-		ComponentLocator locator = ComponentLocator.getLocator(ManagementService.Name);
-    	NetappManager netappMgr = locator.getManager(NetappManager.class);
-    	try {
-			netappMgr.deletePool(poolName);
-			DeleteVolumePoolCmdResponse response = new DeleteVolumePoolCmdResponse();
-			response.setResponseName(getCommandName());
-			this.setResponseObject(response);
-		} catch (InvalidParameterValueException e) {
-			throw new ServerApiException(BaseCmd.PARAM_ERROR, e.toString());
-		} catch (ResourceInUseException e) {
-			throw new ServerApiException(BaseCmd.RESOURCE_IN_USE_ERROR, e.toString());
-		}
-	}
-
-	@Override
-	public String getCommandName() {
-		// TODO Auto-generated method stub
-		return s_name;
-	}
-
-	@Override
-	public long getEntityOwnerId() {
-		// TODO Auto-generated method stub
-		return 0;
-	}
-    
-}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/server/src/com/cloud/api/commands/netapp/DestroyLunCmd.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/commands/netapp/DestroyLunCmd.java b/server/src/com/cloud/api/commands/netapp/DestroyLunCmd.java
deleted file mode 100644
index 76ccd0e..0000000
--- a/server/src/com/cloud/api/commands/netapp/DestroyLunCmd.java
+++ /dev/null
@@ -1,78 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements.  See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership.  The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License.  You may obtain a copy of the License at
-//
-//   http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied.  See the License for the
-// specific language governing permissions and limitations
-// under the License.
-package com.cloud.api.commands.netapp;
-
-import java.rmi.ServerException;
-
-import org.apache.log4j.Logger;
-
-import com.cloud.api.ApiConstants;
-import com.cloud.api.BaseCmd;
-import com.cloud.api.Implementation;
-import com.cloud.api.Parameter;
-import com.cloud.api.ServerApiException;
-import com.cloud.exception.ConcurrentOperationException;
-import com.cloud.exception.InsufficientCapacityException;
-import com.cloud.exception.InvalidParameterValueException;
-import com.cloud.exception.ResourceAllocationException;
-import com.cloud.exception.ResourceInUseException;
-import com.cloud.exception.ResourceUnavailableException;
-import com.cloud.netapp.NetappManager;
-import com.cloud.server.ManagementService;
-import com.cloud.server.api.response.netapp.DeleteLUNCmdResponse;
-import com.cloud.utils.component.ComponentLocator;
-
-@Implementation(description="Destroy a LUN", responseObject = DeleteLUNCmdResponse.class)
-public class DestroyLunCmd extends BaseCmd {
-    
-	public static final Logger s_logger = Logger.getLogger(DestroyLunCmd.class.getName());
-    private static final String s_name = "destroylunresponse";
-
-    @Parameter(name=ApiConstants.PATH, type=CommandType.STRING, required = true, description="LUN path.")
-	private String path;
-
-    @Override
-    public void execute() throws ResourceUnavailableException,
-    InsufficientCapacityException, ServerApiException,
-    ConcurrentOperationException, ResourceAllocationException {
-    	ComponentLocator locator = ComponentLocator.getLocator(ManagementService.Name);
-    	NetappManager netappMgr = locator.getManager(NetappManager.class);
-    	try {
-			netappMgr.destroyLunOnFiler(path);
-    		DeleteLUNCmdResponse response = new DeleteLUNCmdResponse();
-    		response.setResponseName(getCommandName());
-    		this.setResponseObject(response);
-    	} catch (InvalidParameterValueException e) {
-    		throw new ServerApiException(BaseCmd.PARAM_ERROR, e.toString());
-    	} catch (ServerException e) {
-    		throw new ServerApiException(BaseCmd.RESOURCE_IN_USE_ERROR, e.toString());
-    	}
-    }
-
-    @Override
-	public String getCommandName() {
-		// TODO Auto-generated method stub
-		return s_name;
-	}
-
-	@Override
-	public long getEntityOwnerId() {
-		// TODO Auto-generated method stub
-		return 0;
-	}
-    
-}

http://git-wip-us.apache.org/repos/asf/incubator-cloudstack/blob/8aa2b55d/server/src/com/cloud/api/commands/netapp/DestroyVolumeOnFilerCmd.java
----------------------------------------------------------------------
diff --git a/server/src/com/cloud/api/commands/netapp/DestroyVolumeOnFilerCmd.java b/server/src/com/cloud/api/commands/netapp/DestroyVolumeOnFilerCmd.java
deleted file mode 100644
index 4bde7f5..0000000
--- a/server/src/com/cloud/api/commands/netapp/DestroyVolumeOnFilerCmd.java
+++ /dev/null
@@ -1,87 +0,0 @@
-// Licensed to the Apache Software Foundation (ASF) under one
-// or more contributor license agreements.  See the NOTICE file
-// distributed with this work for additional information
-// regarding copyright ownership.  The ASF licenses this file
-// to you under the Apache License, Version 2.0 (the
-// "License"); you may not use this file except in compliance
-// with the License.  You may obtain a copy of the License at
-//
-//   http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing,
-// software distributed under the License is distributed on an
-// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
-// KIND, either express or implied.  See the License for the
-// specific language governing permissions and limitations
-// under the License.
-package com.cloud.api.commands.netapp;
-
-import java.rmi.ServerException;
-
-import org.apache.log4j.Logger;
-
-import com.cloud.api.ApiConstants;
-import com.cloud.api.BaseCmd;
-import com.cloud.api.Implementation;
-import com.cloud.api.Parameter;
-import com.cloud.api.ServerApiException;
-import com.cloud.exception.ConcurrentOperationException;
-import com.cloud.exception.InsufficientCapacityException;
-import com.cloud.exception.InvalidParameterValueException;
-import com.cloud.exception.ResourceAllocationException;
-import com.cloud.exception.ResourceInUseException;
-import com.cloud.exception.ResourceUnavailableException;
-import com.cloud.netapp.NetappManager;
-import com.cloud.server.ManagementService;
-import com.cloud.server.api.response.netapp.DeleteVolumeOnFilerCmdResponse;
-import com.cloud.utils.component.ComponentLocator;
-
-@Implementation(description="Destroy a Volume", responseObject = DeleteVolumeOnFilerCmdResponse.class)
-public class DestroyVolumeOnFilerCmd extends BaseCmd {
-	public static final Logger s_logger = Logger.getLogger(DestroyVolumeOnFilerCmd.class.getName());
-    private static final String s_name = "destroyvolumeresponse";
-    
-    @Parameter(name=ApiConstants.AGGREGATE_NAME, type=CommandType.STRING, required = true, description="aggregate name.")
-	private String aggrName;
-    
-    @Parameter(name=ApiConstants.IP_ADDRESS, type=CommandType.STRING, required = true, description="ip address.")
-	private String ipAddr;
-    
-    @Parameter(name=ApiConstants.VOLUME_NAME, type=CommandType.STRING, required = true, description="volume name.")
-	private String volumeName;
-    
-    
-	@Override
-	public void execute() throws ResourceUnavailableException,
-			InsufficientCapacityException, ServerApiException,
-			ConcurrentOperationException, ResourceAllocationException {
-		ComponentLocator locator = ComponentLocator.getLocator(ManagementService.Name);
-    	NetappManager netappMgr = locator.getManager(NetappManager.class);
-    	try {
-    		netappMgr.destroyVolumeOnFiler(ipAddr, aggrName, volumeName);
-    		DeleteVolumeOnFilerCmdResponse response = new DeleteVolumeOnFilerCmdResponse();
-    		response.setResponseName(getCommandName());
-    		this.setResponseObject(response);
-    	} catch (InvalidParameterValueException e) {
-    		throw new ServerApiException(BaseCmd.PARAM_ERROR, e.toString());
-    	} catch (ResourceInUseException e) {
-    		throw new ServerApiException(BaseCmd.RESOURCE_IN_USE_ERROR, e.toString());
-    	} catch (ServerException e) {
-    		throw new ServerApiException(BaseCmd.INTERNAL_ERROR, e.toString());
-		}
-		
-	}
-
-	@Override
-	public String getCommandName() {
-		// TODO Auto-generated method stub
-		return s_name;
-	}
-
-	@Override
-	public long getEntityOwnerId() {
-		// TODO Auto-generated method stub
-		return 0;
-	}
-    
-}
\ No newline at end of file