~ubuntu-core-dev/eucalyptus/ubuntu-karmic

« back to all changes in this revision

Viewing changes to clc/modules/storage-manager/src/edu/ucsb/eucalyptus/storage/fs/FileSystemStorageManager.java

  • Committer: Dmitrii Zagorodnov
  • Date: 2009-01-27 21:53:41 UTC
  • mfrom: (25.1.112 eucalyptus-main)
  • Revision ID: dmitrii@cs.ucsb.edu-20090127215341-i0f0v6cmbpljmg02
merged with current main

Show diffs side-by-side

added added

removed removed

Lines of Context:
34
34
 
35
35
package edu.ucsb.eucalyptus.storage.fs;
36
36
 
 
37
import edu.ucsb.eucalyptus.cloud.EucalyptusCloudException;
 
38
import edu.ucsb.eucalyptus.keys.Hashes;
37
39
import edu.ucsb.eucalyptus.storage.StorageManager;
38
 
import edu.ucsb.eucalyptus.util.WalrusProperties;
39
40
 
40
41
import java.io.*;
 
42
import java.util.ArrayList;
 
43
import java.util.List;
41
44
 
42
45
public class FileSystemStorageManager implements StorageManager {
43
46
 
44
47
    public static final String FILE_SEPARATOR = "/";
45
 
    public FileSystemStorageManager() {
46
 
    }
 
48
    public static final String lvmRootDirectory = "/dev";
 
49
    private static boolean initialized = false;
 
50
 
 
51
    private String rootDirectory;
 
52
    public FileSystemStorageManager(String rootDirectory) {
 
53
        this.rootDirectory = rootDirectory;
 
54
    }
 
55
 
 
56
    public void initialize() {
 
57
        if(!initialized) {
 
58
            System.loadLibrary("fsstorage");
 
59
            initialized = true;
 
60
        }
 
61
    }
 
62
 
 
63
    public void setRootDirectory(String rootDirectory) {
 
64
        this.rootDirectory = rootDirectory;
 
65
    }
 
66
 
47
67
 
48
68
    public void createBucket(String bucket) throws IOException {
49
 
        File bukkit = new File (WalrusProperties.bucketRootDirectory + FILE_SEPARATOR + bucket);
 
69
        File bukkit = new File (rootDirectory + FILE_SEPARATOR + bucket);
50
70
        if(!bukkit.exists()) {
51
71
            if(!bukkit.mkdirs()) {
52
72
                throw new IOException(bucket);
54
74
        }
55
75
    }
56
76
 
57
 
 
58
 
    public boolean isEmpty(String bucket) {
59
 
        return true;  //To change body of implemented methods use File | Settings | File Templates.
 
77
    public long getSize(String bucket, String object) {
 
78
        File objectFile = new File (rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object);
 
79
        if(objectFile.exists())
 
80
            return objectFile.length();
 
81
        return -1;
60
82
    }
61
83
 
62
84
    public void deleteBucket(String bucket) throws IOException {
63
 
        File bukkit = new File (WalrusProperties.bucketRootDirectory + FILE_SEPARATOR + bucket);
 
85
        File bukkit = new File (rootDirectory + FILE_SEPARATOR + bucket);
64
86
        if(!bukkit.delete()) {
65
87
            throw new IOException(bucket);
66
88
        }
67
89
    }
68
90
 
69
91
    public void createObject(String bucket, String object) throws IOException {
70
 
        File objectFile = new File (WalrusProperties.bucketRootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object);
 
92
        File objectFile = new File (rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object);
71
93
        if (!objectFile.exists()) {
72
94
            if (!objectFile.createNewFile()) {
73
95
                throw new IOException(object);
76
98
    }
77
99
 
78
100
    public int readObject(String bucket, String object, byte[] bytes, long offset) throws IOException {
79
 
        return readObject(WalrusProperties.bucketRootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object, bytes, offset);
 
101
        return readObject(rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object, bytes, offset);
80
102
    }
81
103
 
82
104
    public int readObject(String path, byte[] bytes, long offset) throws IOException {
94
116
    }
95
117
 
96
118
    public void deleteObject(String bucket, String object) throws IOException {
97
 
        File objectFile = new File (WalrusProperties.bucketRootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object);
 
119
        File objectFile = new File (rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object);
98
120
        if (objectFile.exists()) {
99
121
            if(!objectFile.delete()) {
100
122
                throw new IOException(object);
112
134
    }
113
135
 
114
136
    public void putObject(String bucket, String object, byte[] base64Data, boolean append) throws IOException {
115
 
        File objectFile = new File (WalrusProperties.bucketRootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object);
 
137
        File objectFile = new File (rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object);
116
138
        if (!objectFile.exists()) {
117
139
            objectFile.createNewFile();
118
140
        }
122
144
    }
123
145
 
124
146
    public void renameObject(String bucket, String oldName, String newName) throws IOException {
125
 
        File oldObjectFile = new File (WalrusProperties.bucketRootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + oldName);
126
 
        File newObjectFile = new File (WalrusProperties.bucketRootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + newName);
127
 
        if (!oldObjectFile.renameTo(newObjectFile)) {
128
 
            throw new IOException(oldName);
 
147
        File oldObjectFile = new File (rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + oldName);
 
148
        File newObjectFile = new File (rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + newName);
 
149
        if(oldObjectFile.exists()) {
 
150
            if (!oldObjectFile.renameTo(newObjectFile)) {
 
151
                throw new IOException(oldName);
 
152
            }
129
153
        }
130
154
    }
131
155
 
132
156
    public String getObjectPath(String bucket, String object) {
133
 
        return WalrusProperties.bucketRootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object;
 
157
        return rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + object;
 
158
    }
 
159
 
 
160
    public native String removeLoopback(String loDevName);
 
161
 
 
162
    public native String createLoopback(String fileName);
 
163
 
 
164
    public native String removeLogicalVolume(String lvName);
 
165
 
 
166
    public native String reduceVolumeGroup(String vgName, String pvName);
 
167
 
 
168
    public native String removePhysicalVolume(String loDevName);
 
169
 
 
170
    public native String createVolumeFromLv(String lvName, String volumeKey);
 
171
 
 
172
    public native String enableLogicalVolume(String lvName);
 
173
 
 
174
    public native String disableLogicalVolume(String lvName);
 
175
 
 
176
    public void deleteSnapshot(String bucket, String snapshotId, String vgName, String lvName, List<String> snapshotSet) throws EucalyptusCloudException {
 
177
        //load the snapshot set
 
178
        ArrayList<String> loDevices = new ArrayList<String>();
 
179
        String snapshotLoDev = null;
 
180
        String snapshotFileName = null;
 
181
        for(String snapshot : snapshotSet) {
 
182
            String fileName = rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + snapshot;
 
183
            String loDevName = createLoopback(fileName);
 
184
            if(loDevName.length() == 0)
 
185
                throw new EucalyptusCloudException("could not create loopback device for " + snapshot);
 
186
            if(snapshot.equals(snapshotId)) {
 
187
                snapshotLoDev = loDevName;
 
188
                snapshotFileName = fileName;
 
189
            }
 
190
            loDevices.add(loDevName);
 
191
        }
 
192
        //now remove the snapshot
 
193
        String absoluteLVName = lvmRootDirectory + FILE_SEPARATOR + vgName + FILE_SEPARATOR + lvName;
 
194
        String returnValue = removeLogicalVolume(absoluteLVName);
 
195
        if(returnValue.length() == 0) {
 
196
            throw new EucalyptusCloudException("Unable to remove logical volume " + absoluteLVName);
 
197
        }
 
198
        returnValue = reduceVolumeGroup(vgName, snapshotLoDev);
 
199
        if(returnValue.length() == 0) {
 
200
            throw new EucalyptusCloudException("Unable to remove volume group " + vgName);
 
201
        }
 
202
        returnValue = removePhysicalVolume(snapshotLoDev);
 
203
        if(returnValue.length() == 0) {
 
204
            throw new EucalyptusCloudException("Unable to remove physical volume " + snapshotLoDev);
 
205
        }
 
206
 
 
207
        //unload the snapshots
 
208
        for(String loDevice : loDevices) {
 
209
            returnValue = removeLoopback(loDevice);
 
210
        }
 
211
 
 
212
        //remove the snapshot backing store
 
213
        try {
 
214
            deleteObject("", snapshotFileName);
 
215
        } catch(Exception ex) {
 
216
            throw new EucalyptusCloudException("could not delete snapshot file " + snapshotFileName);
 
217
        }
 
218
    }
 
219
 
 
220
    public String createVolume(String bucket, List<String> snapshotSet, List<String> vgNames, List<String> lvNames, String snapshotId, String snapshotVgName, String snapshotLvName) throws EucalyptusCloudException {
 
221
        String snapshotLoDev = null;
 
222
        ArrayList<String> loDevices = new ArrayList<String>();
 
223
        for(String snapshot : snapshotSet) {
 
224
            String loDevName = createLoopback(rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + snapshot);
 
225
            if(loDevName.length() == 0)
 
226
                throw new EucalyptusCloudException("could not create loopback device for " + snapshot);
 
227
            if(snapshot.equals(snapshotId))
 
228
                snapshotLoDev = loDevName;
 
229
            loDevices.add(loDevName);
 
230
        }
 
231
 
 
232
        //enable them
 
233
        int i = 0;
 
234
        ArrayList<String> absoluteLvNames = new ArrayList<String>();
 
235
        String snapshotAbsoluteLvName = null;
 
236
        for(String snapshot : snapshotSet) {
 
237
            String absoluteLvName = lvmRootDirectory + FILE_SEPARATOR + vgNames.get(i) + FILE_SEPARATOR + lvNames.get(i);
 
238
            if(i == 0)
 
239
                enableLogicalVolume(absoluteLvName);
 
240
            if(snapshotId.equals(snapshot))
 
241
                snapshotAbsoluteLvName = absoluteLvName;
 
242
            absoluteLvNames.add(absoluteLvName);
 
243
            ++i;
 
244
        }
 
245
 
 
246
        String volumeKey = "walrusvol-" + Hashes.getRandom(16);
 
247
        String volumePath = rootDirectory + FILE_SEPARATOR + bucket + FILE_SEPARATOR + volumeKey;
 
248
        createVolumeFromLv(snapshotAbsoluteLvName, volumePath);
 
249
        if(!(new File(volumePath).exists()))
 
250
            throw new EucalyptusCloudException("Unable to create file " + volumePath);
 
251
 
 
252
        for(String absoluteLvName : absoluteLvNames) {
 
253
            String returnValue = disableLogicalVolume(absoluteLvName);
 
254
        }
 
255
 
 
256
        //unload the snapshots
 
257
        for(String loDevice : loDevices) {
 
258
            String returnValue = removeLoopback(loDevice);
 
259
        }
 
260
        return volumeKey;
134
261
    }
135
262
}
 
 
b'\\ No newline at end of file'