Change the prototypes of the JNA library interface in order to take
advantage of the CString class.
This removes a fair amount of code in the org.libvirt.Library class
and puts the decoding of C string data into a single place.
---
src/main/java/org/libvirt/Connect.java | 20 +++++++-------
src/main/java/org/libvirt/Device.java | 7 +++--
src/main/java/org/libvirt/Domain.java | 6 ++--
src/main/java/org/libvirt/Library.java | 44 ++++++++----------------------
src/main/java/org/libvirt/StoragePool.java | 7 +++--
src/main/java/org/libvirt/jna/Libvirt.java | 26 +++++++++---------
6 files changed, 46 insertions(+), 64 deletions(-)
diff --git a/src/main/java/org/libvirt/Connect.java
b/src/main/java/org/libvirt/Connect.java
index 437f423..1d37c22 100644
--- a/src/main/java/org/libvirt/Connect.java
+++ b/src/main/java/org/libvirt/Connect.java
@@ -1183,7 +1183,7 @@ public class Connect {
public String[] listDefinedDomains() throws LibvirtException {
int maxnames = numOfDefinedDomains();
if (maxnames > 0) {
- final Pointer[] names = new Pointer[maxnames];
+ final CString[] names = new CString[maxnames];
final int n = processError(libvirt.virConnectListDefinedDomains(VCP, names,
maxnames));
return Library.toStringArray(names, n);
} else {
@@ -1201,7 +1201,7 @@ public class Connect {
public String[] listDefinedInterfaces() throws LibvirtException {
final int max = numOfDefinedInterfaces();
if (max > 0) {
- final Pointer[] ifs = new Pointer[max];
+ final CString[] ifs = new CString[max];
final int n = processError(libvirt.virConnectListDefinedInterfaces(VCP, ifs,
max));
return Library.toStringArray(ifs, n);
} else {
@@ -1219,7 +1219,7 @@ public class Connect {
public String[] listDefinedNetworks() throws LibvirtException {
int maxnames = numOfDefinedNetworks();
if (maxnames > 0) {
- final Pointer[] names = new Pointer[maxnames];
+ final CString[] names = new CString[maxnames];
final int n = processError(libvirt.virConnectListDefinedNetworks(VCP, names,
maxnames));
return Library.toStringArray(names, n);
} else {
@@ -1237,7 +1237,7 @@ public class Connect {
public String[] listDefinedStoragePools() throws LibvirtException {
int num = numOfDefinedStoragePools();
if (num > 0) {
- Pointer[] pools = new Pointer[num];
+ CString[] pools = new CString[num];
final int n = processError(libvirt.virConnectListDefinedStoragePools(VCP,
pools, num));
return Library.toStringArray(pools, n);
} else {
@@ -1254,7 +1254,7 @@ public class Connect {
public String[] listDevices(String capabilityName) throws LibvirtException {
int maxDevices = numOfDevices(capabilityName);
if (maxDevices > 0) {
- Pointer[] names = new Pointer[maxDevices];
+ CString[] names = new CString[maxDevices];
final int n = processError(libvirt.virNodeListDevices(VCP, capabilityName,
names, maxDevices, 0));
return Library.toStringArray(names, n);
} else {
@@ -1288,7 +1288,7 @@ public class Connect {
public String[] listInterfaces() throws LibvirtException {
int num = numOfInterfaces();
if (num > 0) {
- Pointer[] ifs = new Pointer[num];
+ CString[] ifs = new CString[num];
final int n = processError(libvirt.virConnectListInterfaces(VCP, ifs, num));
return Library.toStringArray(ifs, n);
} else {
@@ -1305,7 +1305,7 @@ public class Connect {
public String[] listNetworkFilters() throws LibvirtException {
int maxnames = numOfNetworkFilters();
if (maxnames > 0) {
- Pointer[] names = new Pointer[maxnames];
+ CString[] names = new CString[maxnames];
final int n = processError(libvirt.virConnectListNWFilters(VCP, names,
maxnames));
return Library.toStringArray(names, n);
} else {
@@ -1323,7 +1323,7 @@ public class Connect {
public String[] listNetworks() throws LibvirtException {
int maxnames = numOfNetworks();
if (maxnames > 0) {
- Pointer[] names = new Pointer[maxnames];
+ CString[] names = new CString[maxnames];
final int n = processError(libvirt.virConnectListNetworks(VCP, names,
maxnames));
return Library.toStringArray(names, n);
} else {
@@ -1340,7 +1340,7 @@ public class Connect {
public String[] listSecrets() throws LibvirtException {
int num = numOfSecrets();
if (num > 0) {
- Pointer[] returnValue = new Pointer[num];
+ CString[] returnValue = new CString[num];
final int n = processError(libvirt.virConnectListSecrets(VCP, returnValue,
num));
return Library.toStringArray(returnValue, n);
} else {
@@ -1358,7 +1358,7 @@ public class Connect {
public String[] listStoragePools() throws LibvirtException {
int num = numOfStoragePools();
if (num > 0) {
- Pointer[] returnValue = new Pointer[num];
+ CString[] returnValue = new CString[num];
final int n = processError(libvirt.virConnectListStoragePools(VCP,
returnValue, num));
return Library.toStringArray(returnValue, n);
} else {
diff --git a/src/main/java/org/libvirt/Device.java
b/src/main/java/org/libvirt/Device.java
index 04f373e..6becbca 100644
--- a/src/main/java/org/libvirt/Device.java
+++ b/src/main/java/org/libvirt/Device.java
@@ -1,5 +1,6 @@
package org.libvirt;
+import org.libvirt.jna.CString;
import org.libvirt.jna.DevicePointer;
import static org.libvirt.Library.libvirt;
import static org.libvirt.ErrorHandler.processError;
@@ -130,10 +131,10 @@ public class Device {
int maxCaps = getNumberOfCapabilities();
if (maxCaps > 0) {
- Pointer[] ptrs = new Pointer[maxCaps];
- int got = processError(libvirt.virNodeDeviceListCaps(VDP, ptrs, maxCaps));
+ CString[] strings = new CString[maxCaps];
+ int got = processError(libvirt.virNodeDeviceListCaps(VDP, strings,
maxCaps));
- return Library.toStringArray(ptrs, got);
+ return Library.toStringArray(strings, got);
} else {
return Library.NO_STRINGS;
}
diff --git a/src/main/java/org/libvirt/Domain.java
b/src/main/java/org/libvirt/Domain.java
index 087a06f..ed6690c 100644
--- a/src/main/java/org/libvirt/Domain.java
+++ b/src/main/java/org/libvirt/Domain.java
@@ -1437,10 +1437,10 @@ public class Domain {
public String[] snapshotListNames(int flags) throws LibvirtException {
int num = snapshotNum();
if (num > 0) {
- Pointer[] ptrs = new Pointer[num];
- int got = processError(libvirt.virDomainSnapshotListNames(VDP, ptrs, num,
flags));
+ CString[] names = new CString[num];
+ int got = processError(libvirt.virDomainSnapshotListNames(VDP, names, num,
flags));
- return Library.toStringArray(ptrs, got);
+ return Library.toStringArray(names, got);
} else {
return Library.NO_STRINGS;
}
diff --git a/src/main/java/org/libvirt/Library.java
b/src/main/java/org/libvirt/Library.java
index ac89de4..7ce986d 100644
--- a/src/main/java/org/libvirt/Library.java
+++ b/src/main/java/org/libvirt/Library.java
@@ -2,6 +2,7 @@ package org.libvirt;
import org.libvirt.jna.Libvirt;
import org.libvirt.jna.Libvirt.VirEventTimeoutCallback;
+import org.libvirt.jna.CString;
import static org.libvirt.ErrorHandler.processError;
import com.sun.jna.Native;
@@ -71,46 +72,25 @@ public final class Library {
}
/**
- * Convert the data pointed to by {@code ptr} to a String.
- */
- static String getString(Pointer ptr) {
- final long len = ptr.indexOf(0, (byte)0);
- assert (len != -1): "C-Strings must be \\0 terminated.";
-
- final byte[] data = ptr.getByteArray(0, (int)len);
- try {
- return new String(data, "utf-8");
- } catch (java.io.UnsupportedEncodingException e) {
- throw new RuntimeException("Libvirt problem: UTF-8 decoding
error.", e);
- }
- }
-
- /**
- * Calls {@link #toStringArray(Pointer[], int)}.
- */
- static String[] toStringArray(Pointer[] ptrArr) {
- return toStringArray(ptrArr, ptrArr.length);
- }
-
- /**
- * Convert the given array of native pointers to "char" in
- * UTF-8 encoding to an array of Strings.
+ * Convert the given array of UTF-8 encoded C-Strings to an array
+ * of Strings.
*
* \note The memory used by the elements of the original array
- * is freed and ptrArr is modified.
+ * is freed.
*/
- static String[] toStringArray(Pointer[] ptrArr, final int size) {
+ static String[] toStringArray(CString[] cstrarr, final int size) {
+ int i = 0;
try {
final String[] result = new String[size];
- for (int i = 0; i < size; ++i) {
- result[i] = Library.getString(ptrArr[i]);
+ for (; i < size; ++i) {
+ result[i] = cstrarr[i].toString();
}
return result;
- } finally {
- for (int i = 0; i < size; ++i) {
- Library.free(ptrArr[i]);
- ptrArr[i] = null;
+ } catch (Exception e) {
+ for (; i < size; ++i) {
+ if (cstrarr[i] != null) cstrarr[i].free();
}
+ throw e;
}
}
diff --git a/src/main/java/org/libvirt/StoragePool.java
b/src/main/java/org/libvirt/StoragePool.java
index 8caf9f5..04870bf 100644
--- a/src/main/java/org/libvirt/StoragePool.java
+++ b/src/main/java/org/libvirt/StoragePool.java
@@ -1,5 +1,6 @@
package org.libvirt;
+import org.libvirt.jna.CString;
import org.libvirt.jna.Libvirt;
import org.libvirt.jna.StoragePoolPointer;
import org.libvirt.jna.StorageVolPointer;
@@ -247,11 +248,11 @@ public class StoragePool {
public String[] listVolumes() throws LibvirtException {
int num = numOfVolumes();
if (num > 0) {
- Pointer[] ptrs = new Pointer[num];
+ CString[] names = new CString[num];
- int got = processError(libvirt.virStoragePoolListVolumes(VSPP, ptrs, num));
+ int got = processError(libvirt.virStoragePoolListVolumes(VSPP, names, num));
- return Library.toStringArray(ptrs, got);
+ return Library.toStringArray(names, got);
} else {
return Library.NO_STRINGS;
}
diff --git a/src/main/java/org/libvirt/jna/Libvirt.java
b/src/main/java/org/libvirt/jna/Libvirt.java
index c6b7153..3589525 100644
--- a/src/main/java/org/libvirt/jna/Libvirt.java
+++ b/src/main/java/org/libvirt/jna/Libvirt.java
@@ -184,16 +184,16 @@ public interface Libvirt extends Library {
String virConnectGetType(ConnectionPointer virConnectPtr);
CString virConnectGetURI(ConnectionPointer virConnectPtr);
int virConnectGetVersion(ConnectionPointer virConnectPtr, LongByReference hvVer);
- int virConnectListDefinedDomains(ConnectionPointer virConnectPtr, Pointer[] name, int
maxnames);
- int virConnectListDefinedNetworks(ConnectionPointer virConnectPtr, Pointer[] name,
int maxnames);
- int virConnectListDefinedStoragePools(ConnectionPointer virConnectPtr, Pointer[]
names, int maxnames);
- int virConnectListDefinedInterfaces(ConnectionPointer virConnectPtr, Pointer[] name,
int maxNames);
+ int virConnectListDefinedDomains(ConnectionPointer virConnectPtr, CString[] name, int
maxnames);
+ int virConnectListDefinedNetworks(ConnectionPointer virConnectPtr, CString[] name,
int maxnames);
+ int virConnectListDefinedStoragePools(ConnectionPointer virConnectPtr, CString[]
names, int maxnames);
+ int virConnectListDefinedInterfaces(ConnectionPointer virConnectPtr, CString[] name,
int maxNames);
int virConnectListDomains(ConnectionPointer virConnectPtr, int[] ids, int maxnames);
- int virConnectListInterfaces(ConnectionPointer virConnectPtr, Pointer[] name, int
maxNames);
- int virConnectListNetworks(ConnectionPointer virConnectPtr, Pointer[] name, int
maxnames);
- int virConnectListNWFilters(ConnectionPointer virConnectPtr, Pointer[] name, int
maxnames);
- int virConnectListSecrets(ConnectionPointer virConnectPtr, Pointer[] uids, int
maxUids);
- int virConnectListStoragePools(ConnectionPointer virConnectPtr, Pointer[] names, int
maxnames);
+ int virConnectListInterfaces(ConnectionPointer virConnectPtr, CString[] name, int
maxNames);
+ int virConnectListNetworks(ConnectionPointer virConnectPtr, CString[] name, int
maxnames);
+ int virConnectListNWFilters(ConnectionPointer virConnectPtr, CString[] name, int
maxnames);
+ int virConnectListSecrets(ConnectionPointer virConnectPtr, CString[] uids, int
maxUids);
+ int virConnectListStoragePools(ConnectionPointer virConnectPtr, CString[] names, int
maxnames);
int virConnectNumOfDefinedDomains(ConnectionPointer virConnectPtr);
int virConnectNumOfDefinedNetworks(ConnectionPointer virConnectPtr);
int virConnectNumOfDefinedInterfaces(ConnectionPointer virConnectPtr);
@@ -343,13 +343,13 @@ public interface Libvirt extends Library {
// Node/Device functions
int virNodeNumOfDevices(ConnectionPointer virConnectPtr, String capabilityName, int
flags);
- int virNodeListDevices(ConnectionPointer virConnectPtr, String capabilityName,
Pointer[] names, int maxnames,
+ int virNodeListDevices(ConnectionPointer virConnectPtr, String capabilityName,
CString[] names, int maxnames,
int flags);
DevicePointer virNodeDeviceLookupByName(ConnectionPointer virConnectPtr, String
name);
String virNodeDeviceGetName(DevicePointer virDevicePointer);
String virNodeDeviceGetParent(DevicePointer virDevicePointer);
int virNodeDeviceNumOfCaps(DevicePointer virDevicePointer);
- int virNodeDeviceListCaps(DevicePointer virDevicePointer, Pointer[] names, int
maxNames);
+ int virNodeDeviceListCaps(DevicePointer virDevicePointer, CString[] names, int
maxNames);
CString virNodeDeviceGetXMLDesc(DevicePointer virDevicePointer, int flags);
int virNodeDeviceFree(DevicePointer virDevicePointer);
int virNodeDeviceDettach(DevicePointer virDevicePointer);
@@ -372,7 +372,7 @@ public interface Libvirt extends Library {
int virStoragePoolGetUUID(StoragePoolPointer storagePoolPtr, byte[] uuidString);
int virStoragePoolGetUUIDString(StoragePoolPointer storagePoolPtr, byte[]
uuidString);
CString virStoragePoolGetXMLDesc(StoragePoolPointer storagePoolPtr, int flags);
- int virStoragePoolListVolumes(StoragePoolPointer storagePoolPtr, Pointer[] names, int
maxnames);
+ int virStoragePoolListVolumes(StoragePoolPointer storagePoolPtr, CString[] names, int
maxnames);
int virStoragePoolIsActive(StoragePoolPointer storagePoolPtr);
int virStoragePoolIsPersistent(StoragePoolPointer storagePoolPtr);
StoragePoolPointer virStoragePoolLookupByName(ConnectionPointer virConnectPtr, String
name);
@@ -450,7 +450,7 @@ public interface Libvirt extends Library {
int virDomainSnapshotDelete(DomainSnapshotPointer virDomainSnapshotPtr, int flags);
CString virDomainSnapshotGetXMLDesc(DomainSnapshotPointer virDomainSnapshotPtr, int
flags);
int virDomainSnapshotFree(DomainSnapshotPointer virDomainSnapshotPtr);
- int virDomainSnapshotListNames(DomainPointer virDomainPtr, Pointer[] names, int
nameslen, int flags);
+ int virDomainSnapshotListNames(DomainPointer virDomainPtr, CString[] names, int
nameslen, int flags);
DomainSnapshotPointer virDomainSnapshotLookupByName(DomainPointer virDomainPtr,
String name, int flags);
int virDomainSnapshotNum(DomainPointer virDomainPtr, int flags);
--
2.2.2