/* Copyright (c) 2010, 2013 Daniel Doubrovkine, Markus Karg, All Rights Reserved * * This library is free software; you can redistribute it and/or * modify it under the terms of the GNU Lesser General Public * License as published by the Free Software Foundation; either * version 2.1 of the License, or (at your option) any later version. * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU * Lesser General Public License for more details. */ package com.sun.jna.platform.win32; import java.io.BufferedReader; import java.io.BufferedWriter; import java.io.File; import java.io.FileReader; import java.io.FileWriter; import java.io.IOException; import java.io.PrintWriter; import java.util.Collection; import java.util.List; import java.util.Map; import com.sun.jna.Pointer; import com.sun.jna.platform.win32.Tlhelp32.MODULEENTRY32W; import com.sun.jna.platform.win32.WinNT.HANDLE; import com.sun.jna.platform.win32.WinNT.HRESULT; import com.sun.jna.platform.win32.WinNT.LARGE_INTEGER; import junit.framework.TestCase; /** * @author dblock[at]dblock[dot]org * @author markus[at]headcrashing[dot]eu */ public class Kernel32UtilTest extends TestCase { public static void main(String[] args) throws Exception { System.out.println("Computer name: " + Kernel32Util.getComputerName()); System.out.println("Temp path: " + Kernel32Util.getTempPath()); // logical drives System.out.println("Logical drives: "); Collection<String> logicalDrives = Kernel32Util.getLogicalDriveStrings(); for(String logicalDrive : logicalDrives) { // drive type System.out.println(" " + logicalDrive + " (" + Kernel32.INSTANCE.GetDriveType(logicalDrive) + ")"); // free space LARGE_INTEGER.ByReference lpFreeBytesAvailable = new LARGE_INTEGER.ByReference(); LARGE_INTEGER.ByReference lpTotalNumberOfBytes = new LARGE_INTEGER.ByReference(); LARGE_INTEGER.ByReference lpTotalNumberOfFreeBytes = new LARGE_INTEGER.ByReference(); if (Kernel32.INSTANCE.GetDiskFreeSpaceEx(logicalDrive, lpFreeBytesAvailable, lpTotalNumberOfBytes, lpTotalNumberOfFreeBytes)) { System.out.println(" Total: " + formatBytes(lpTotalNumberOfBytes.getValue())); System.out.println(" Free: " + formatBytes(lpTotalNumberOfFreeBytes.getValue())); } } junit.textui.TestRunner.run(Kernel32UtilTest.class); } /** * Format bytes. * @param bytes * Bytes. * @return * Rounded string representation of the byte size. */ private static String formatBytes(long bytes) { if (bytes == 1) { // bytes return String.format("%d byte", bytes); } else if (bytes < 1024) { // bytes return String.format("%d bytes", bytes); } else if (bytes < 1048576 && bytes % 1024 == 0) { // Kb return String.format("%.0f KB", (double) bytes / 1024); } else if (bytes < 1048576) { // Kb return String.format("%.1f KB", (double) bytes / 1024); } else if (bytes % 1048576 == 0 && bytes < 1073741824) { // Mb return String.format("%.0f MB", (double) bytes / 1048576); } else if (bytes < 1073741824) { // Mb return String.format("%.1f MB", (double) bytes / 1048576); } else if (bytes % 1073741824 == 0 && bytes < 1099511627776L) { // GB return String.format("%.0f GB", (double) bytes / 1073741824); } else if (bytes < 1099511627776L ) { return String.format("%.1f GB", (double) bytes / 1073741824); } else if (bytes % 1099511627776L == 0 && bytes < 1125899906842624L) { // TB return String.format("%.0f TB", (double) bytes / 1099511627776L); } else if (bytes < 1125899906842624L ) { return String.format("%.1f TB", (double) bytes / 1099511627776L); } else { return String.format("%d bytes", bytes); } } public void testFreeLocalMemory() { try { Pointer ptr = new Pointer(0xFFFFFFFFFFFFFFFFL); Kernel32Util.freeLocalMemory(ptr); fail("Unexpected success to free bad local memory"); } catch(Win32Exception e) { HRESULT hr = e.getHR(); int code = W32Errors.HRESULT_CODE(hr.intValue()); assertEquals("Mismatched failure reason code", WinError.ERROR_INVALID_HANDLE, code); } } public void testFreeGlobalMemory() { try { Pointer ptr = new Pointer(0xFFFFFFFFFFFFFFFFL); Kernel32Util.freeGlobalMemory(ptr); fail("Unexpected success to free bad global memory"); } catch(Win32Exception e) { HRESULT hr = e.getHR(); int code = W32Errors.HRESULT_CODE(hr.intValue()); assertEquals("Mismatched failure reason code", WinError.ERROR_INVALID_HANDLE, code); } } public void testGetComputerName() { assertTrue(Kernel32Util.getComputerName().length() > 0); } public void testFormatMessageFromLastErrorCode() { if (AbstractWin32TestSupport.isEnglishLocale) { assertEquals("The remote server has been paused or is in the process of being started.", Kernel32Util.formatMessageFromLastErrorCode(W32Errors.ERROR_SHARING_PAUSED)); } else { System.out.println("testFormatMessageFromLastErrorCode Test can only be run on english locale"); } } public void testFormatMessageFromHR() { if(AbstractWin32TestSupport.isEnglishLocale) { assertEquals("The operation completed successfully.", Kernel32Util.formatMessage(W32Errors.S_OK)); } else { System.out.println("testFormatMessageFromHR Test can only be run on english locale"); } } public void testGetTempPath() { assertTrue(Kernel32Util.getTempPath().length() > 0); } public void testGetLogicalDriveStrings() { Collection<String> logicalDrives = Kernel32Util.getLogicalDriveStrings(); assertTrue("No logical drives found", logicalDrives.size() > 0); for(String logicalDrive : logicalDrives) { assertTrue("Empty logical drive name in list", logicalDrive.length() > 0); } } public void testDeleteFile() throws IOException { String filename = Kernel32Util.getTempPath() + "\\FileDoesNotExist.jna"; File f = new File(filename); f.createNewFile(); Kernel32Util.deleteFile(filename); } public void testGetFileAttributes() throws IOException { String filename = Kernel32Util.getTempPath(); int fileAttributes = Kernel32Util.getFileAttributes(filename); assertEquals(WinNT.FILE_ATTRIBUTE_DIRECTORY, fileAttributes & WinNT.FILE_ATTRIBUTE_DIRECTORY); File tempFile = File.createTempFile("jna", "tmp"); tempFile.deleteOnExit(); int fileAttributes2 = Kernel32Util.getFileAttributes(tempFile.getAbsolutePath()); tempFile.delete(); assertEquals(0, fileAttributes2 & WinNT.FILE_ATTRIBUTE_DIRECTORY); } public void testGetEnvironmentVariable() { assertEquals(null, Kernel32Util.getEnvironmentVariable("jna-getenvironment-test")); Kernel32.INSTANCE.SetEnvironmentVariable("jna-getenvironment-test", "42"); assertEquals("42", Kernel32Util.getEnvironmentVariable("jna-getenvironment-test")); } public final void testGetPrivateProfileInt() throws IOException { final File tmp = File.createTempFile("testGetPrivateProfileInt", "ini"); tmp.deleteOnExit(); final PrintWriter writer = new PrintWriter(new BufferedWriter(new FileWriter(tmp))); writer.println("[Section]"); writer.println("existingKey = 123"); writer.close(); assertEquals(123, Kernel32Util.getPrivateProfileInt("Section", "existingKey", 456, tmp.getCanonicalPath())); assertEquals(456, Kernel32Util.getPrivateProfileInt("Section", "missingKey", 456, tmp.getCanonicalPath())); } public final void testGetPrivateProfileString() throws IOException { final File tmp = File.createTempFile("testGetPrivateProfileString", "ini"); tmp.deleteOnExit(); final PrintWriter writer = new PrintWriter(new BufferedWriter(new FileWriter(tmp))); writer.println("[Section]"); writer.println("existingKey = ABC"); writer.close(); assertEquals("ABC", Kernel32Util.getPrivateProfileString("Section", "existingKey", "DEF", tmp.getCanonicalPath())); assertEquals("DEF", Kernel32Util.getPrivateProfileString("Section", "missingKey", "DEF", tmp.getCanonicalPath())); } public final void testWritePrivateProfileString() throws IOException { final File tmp = File.createTempFile("testWritePrivateProfileString", "ini"); tmp.deleteOnExit(); final PrintWriter writer = new PrintWriter(new BufferedWriter(new FileWriter(tmp))); writer.println("[Section]"); writer.println("existingKey = ABC"); writer.println("removedKey = JKL"); writer.close(); Kernel32Util.writePrivateProfileString("Section", "existingKey", "DEF", tmp.getCanonicalPath()); Kernel32Util.writePrivateProfileString("Section", "addedKey", "GHI", tmp.getCanonicalPath()); Kernel32Util.writePrivateProfileString("Section", "removedKey", null, tmp.getCanonicalPath()); final BufferedReader reader = new BufferedReader(new FileReader(tmp)); assertEquals(reader.readLine(), "[Section]"); assertTrue(reader.readLine().matches("existingKey\\s*=\\s*DEF")); assertTrue(reader.readLine().matches("addedKey\\s*=\\s*GHI")); assertEquals(reader.readLine(), null); reader.close(); } public final void testGetPrivateProfileSection() throws IOException { final File tmp = File.createTempFile("testGetPrivateProfileSection", ".ini"); tmp.deleteOnExit(); final PrintWriter writer = new PrintWriter(new BufferedWriter(new FileWriter(tmp))); try { writer.println("[X]"); writer.println("A=1"); writer.println("foo=bar"); } finally { writer.close(); } final String[] lines = Kernel32Util.getPrivateProfileSection("X", tmp.getCanonicalPath()); assertEquals(lines.length, 2); assertEquals(lines[0], "A=1"); assertEquals(lines[1], "foo=bar"); } public final void testGetPrivateProfileSectionNames() throws IOException { final File tmp = File.createTempFile("testGetPrivateProfileSectionNames", "ini"); tmp.deleteOnExit(); final PrintWriter writer = new PrintWriter(new BufferedWriter(new FileWriter(tmp))); try { writer.println("[S1]"); writer.println("A=1"); writer.println("B=X"); writer.println("[S2]"); writer.println("C=2"); writer.println("D=Y"); } finally { writer.close(); } String[] sectionNames = Kernel32Util.getPrivateProfileSectionNames(tmp.getCanonicalPath()); assertEquals(sectionNames.length, 2); assertEquals(sectionNames[0], "S1"); assertEquals(sectionNames[1], "S2"); } public final void testWritePrivateProfileSection() throws IOException { final File tmp = File.createTempFile("testWritePrivateProfileSecion", "ini"); tmp.deleteOnExit(); final PrintWriter writer = new PrintWriter(new BufferedWriter(new FileWriter(tmp))); try { writer.println("[S1]"); writer.println("A=1"); writer.println("B=X"); writer.println("[S2]"); writer.println("C=2"); writer.println("foo=bar"); } finally { writer.close(); } Kernel32Util.writePrivateProfileSection("S1", new String[] { "A=3", "E=Z" }, tmp.getCanonicalPath()); final BufferedReader reader = new BufferedReader(new FileReader(tmp)); try { assertEquals(reader.readLine(), "[S1]"); assertEquals(reader.readLine(), "A=3"); assertEquals(reader.readLine(), "E=Z"); assertEquals(reader.readLine(), "[S2]"); assertEquals(reader.readLine(), "C=2"); assertEquals(reader.readLine(), "foo=bar"); } finally { reader.close(); } } public final void testQueryFullProcessImageName() { HANDLE h = Kernel32.INSTANCE.OpenProcess(WinNT.PROCESS_QUERY_INFORMATION, false, Kernel32.INSTANCE.GetCurrentProcessId()); assertNotNull("Failed (" + Kernel32.INSTANCE.GetLastError() + ") to get process handle", h); try { String name = Kernel32Util.QueryFullProcessImageName(h, 0); assertTrue("Failed to query process image name, empty path returned", name.length() > 0); } finally { Kernel32Util.closeHandle(h); } } public void testGetResource() { String winDir = Kernel32Util.getEnvironmentVariable("WINDIR"); assertNotNull("No WINDIR value returned", winDir); assertTrue("Specified WINDIR does not exist: " + winDir, new File(winDir).exists()); // On Windows 7, "14" is the type assigned to the "My Computer" icon // (which is named "ICO_MYCOMPUTER") byte[] results = Kernel32Util.getResource(new File(winDir, "explorer.exe").getAbsolutePath(), "14", "ICO_MYCOMPUTER"); assertNotNull("The 'ICO_MYCOMPUTER' resource in explorer.exe should have some content.", results); assertTrue("The 'ICO_MYCOMPUTER' resource in explorer.exe should have some content.", results.length > 0); } public void testGetResourceNames() { String winDir = Kernel32Util.getEnvironmentVariable("WINDIR"); assertNotNull("No WINDIR value returned", winDir); assertTrue("Specified WINDIR does not exist: " + winDir, new File(winDir).exists()); // On Windows 7, "14" is the type assigned to the "My Computer" icon // (which is named "ICO_MYCOMPUTER") Map<String, List<String>> names = Kernel32Util.getResourceNames(new File(winDir, "explorer.exe").getAbsolutePath()); assertNotNull("explorer.exe should contain some resources in it.", names); assertTrue("explorer.exe should contain some resource types in it.", names.size() > 0); assertTrue("explorer.exe should contain a resource of type '14' in it.", names.containsKey("14")); assertTrue("resource type 14 should have a name named ICO_MYCOMPUTER associated with it.", names.get("14").contains("ICO_MYCOMPUTER")); } public void testGetModules() { List<MODULEENTRY32W> results = Kernel32Util.getModules(Kernel32.INSTANCE.GetCurrentProcessId()); // not sure if this will be run against java.exe or javaw.exe but these checks should work with both assertNotNull("There should be some modules returned from this helper", results); assertTrue("The first module in this process should be java.exe or javaw.exe", results.get(0).szModule().startsWith("java")); // since this is supposed to return all the modules in a process, there should be an EXE and at least 1 Windows DLL // so assert total count is at least two assertTrue("This is supposed to return all the modules in a process, so there should be an EXE and at least 1 Windows API DLL.", results.size() > 2); } }