Skip to content

Commit

Permalink
Merge pull request #1374 from matthiasblaesing/com_latebinding_set_pr…
Browse files Browse the repository at this point in the history
…operty_string

Free BSTR/Variant allocated in COMLateBindingObject#setProperty(String, String)
  • Loading branch information
matthiasblaesing authored Aug 18, 2021
2 parents 6cad6d2 + 1c4c0f6 commit fd6a9a6
Show file tree
Hide file tree
Showing 4 changed files with 130 additions and 14 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -37,11 +37,9 @@
import com.sun.jna.platform.win32.OleAuto;
import com.sun.jna.platform.win32.OleAuto.DISPPARAMS;
import com.sun.jna.platform.win32.Variant.VARIANT;
import com.sun.jna.platform.win32.Variant.VariantArg;
import com.sun.jna.platform.win32.WTypes;
import com.sun.jna.platform.win32.WinDef;
import com.sun.jna.platform.win32.WinDef.LCID;
import com.sun.jna.platform.win32.WinDef.UINT;
import com.sun.jna.platform.win32.WinNT.HRESULT;
import com.sun.jna.ptr.IntByReference;
import com.sun.jna.ptr.PointerByReference;
Expand Down Expand Up @@ -187,8 +185,7 @@ protected HRESULT oleMethod(int nType, VARIANT.ByReference pvResult,

COMUtils.checkRC(hr);

return this
.oleMethod(nType, pvResult, iDispatch, pdispID.getValue(), pArgs);
return this.oleMethod(nType, pvResult, pdispID.getValue(), pArgs);
}

protected HRESULT oleMethod(int nType, VARIANT.ByReference pvResult,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -559,21 +559,19 @@ protected void setProperty(String propertyName, short value) {

/**
* Sets the property.
* <p>
* <i>Implementation note:</i> the string is wrapped as a BSTR value, that is
* allocated using {@link com.sun.jna.platform.win32.OleAuto#SysAllocString} and
* will no longer be accessible to the user to free using
* {@link com.sun.jna.platform.win32.OleAuto#SysFreeString}. Consider using
* {@link #setProperty(String, VARIANT)} to allow later clearing of the VARIANT.
* </p>
*
* @param propertyName
* the property name
* @param value
* the value
*/
protected void setProperty(String propertyName, String value) {
this.oleMethod(OleAuto.DISPATCH_PROPERTYPUT, null, propertyName, new VARIANT(value));
VARIANT wrappedValue = new VARIANT(value);
try {
this.oleMethod(OleAuto.DISPATCH_PROPERTYPUT, null, propertyName, wrappedValue);
} finally {
OleAuto.INSTANCE.VariantClear(wrappedValue);
}
}

/**
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,123 @@
/* Copyright (c) 2021 Matthias Bläsing, All Rights Reserved
*
* The contents of this file is dual-licensed under 2
* alternative Open Source/Free licenses: LGPL 2.1 or later and
* Apache License 2.0. (starting with JNA version 4.0.0).
*
* You can freely decide which license you want to apply to
* the project.
*
* You may obtain a copy of the LGPL License at:
*
* http://www.gnu.org/licenses/licenses.html
*
* A copy is also included in the downloadable source code package
* containing JNA, in file "LGPL2.1".
*
* You may obtain a copy of the Apache License at:
*
* http://www.apache.org/licenses/
*
* A copy is also included in the downloadable source code package
* containing JNA, in file "AL2.0".
*/
package com.sun.jna.platform.win32.COM;

import com.sun.jna.WString;
import com.sun.jna.platform.win32.AbstractWin32TestSupport;
import com.sun.jna.platform.win32.Guid;
import com.sun.jna.platform.win32.Guid.CLSID;
import com.sun.jna.platform.win32.Guid.REFIID;
import com.sun.jna.platform.win32.OaIdl.DISPIDByReference;
import com.sun.jna.platform.win32.OaIdl.EXCEPINFO;
import com.sun.jna.platform.win32.Ole32;
import com.sun.jna.platform.win32.OleAuto;
import com.sun.jna.platform.win32.OleAuto.DISPPARAMS;
import com.sun.jna.platform.win32.Variant.VARIANT;
import com.sun.jna.platform.win32.WTypes;
import com.sun.jna.platform.win32.WinDef;
import com.sun.jna.platform.win32.WinDef.LCID;
import com.sun.jna.platform.win32.WinNT.HRESULT;
import com.sun.jna.ptr.IntByReference;
import com.sun.jna.ptr.PointerByReference;
import org.junit.After;
import org.junit.Before;
import org.junit.Test;

import static org.junit.Assert.*;

public class COMLateBindingObjectTest {

static {
ClassLoader.getSystemClassLoader().setDefaultAssertionStatus(true);
}

private final CLSID CLSID_InternetExplorer = new CLSID("{0002DF01-0000-0000-C000-000000000046}");
private final LCID lcid = new LCID(0x0409); // LCID for english locale
private final WinDef.WORD methodFlags = new WinDef.WORD(OleAuto.DISPATCH_METHOD);

private final REFIID niid = new REFIID(Guid.IID_NULL);
private final DISPIDByReference dispIdQuit = new DISPIDByReference();

private PointerByReference ieApp;
private Dispatch ieDispatch;

public COMLateBindingObjectTest() {
}

@Before
public void before() {
AbstractWin32TestSupport.killProcessByName("iexplore.exe");
try {
Thread.sleep(5 * 1000);
} catch (InterruptedException ex) {
}

HRESULT hr = Ole32.INSTANCE.CoInitializeEx(null, Ole32.COINIT_MULTITHREADED);
COMUtils.checkRC(hr);

// Create InternetExplorer object
ieApp = new PointerByReference();
hr = Ole32.INSTANCE
.CoCreateInstance(CLSID_InternetExplorer, null, WTypes.CLSCTX_SERVER, IDispatch.IID_IDISPATCH, ieApp);
COMUtils.checkRC(hr);

ieDispatch = new Dispatch(ieApp.getValue());
ieDispatch.AddRef();
hr = ieDispatch.GetIDsOfNames(new REFIID(Guid.IID_NULL), new WString[]{new WString("Quit")}, 1, lcid, dispIdQuit);
COMUtils.checkRC(hr);
}

@After
public void after() {
// Shutdown Internet Explorer
DISPPARAMS.ByReference pDispParams = new DISPPARAMS.ByReference();
VARIANT.ByReference pVarResult = new VARIANT.ByReference();
IntByReference puArgErr = new IntByReference();
EXCEPINFO.ByReference pExcepInfo = new EXCEPINFO.ByReference();

HRESULT hr = ieDispatch.Invoke(dispIdQuit.getValue(), niid, lcid, methodFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
COMUtils.checkRC(hr, pExcepInfo, puArgErr);

ieDispatch.Release();
Ole32.INSTANCE.CoUninitialize();
}

@Test
public void testPropertyAccessor() throws InterruptedException {
final String testString = "Hallo Welt";
COMLateBindingObject ieBinding = new COMLateBindingObject(ieDispatch);
ieBinding.setProperty("Visible", true);
assertTrue(ieBinding.getBooleanProperty("Visible"));
boolean statusBarInitial = ieBinding.getBooleanProperty("StatusBar");
ieBinding.setProperty("StatusBar", true);
assertTrue(ieBinding.getBooleanProperty("StatusBar"));
ieBinding.setProperty("StatusText", testString);
assertEquals(testString, ieBinding.getStringProperty("StatusText"));
ieBinding.setProperty("StatusBar", false);
assertFalse(ieBinding.getBooleanProperty("StatusBar"));
ieBinding.setProperty("StatusBar", statusBarInitial);
ieBinding.setProperty("Visible", false);
assertFalse(ieBinding.getBooleanProperty("Visible"));
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -55,8 +55,6 @@
import com.sun.jna.platform.win32.WinNT.HRESULT;
import com.sun.jna.ptr.IntByReference;
import com.sun.jna.ptr.PointerByReference;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.junit.Assert;

public class ComEventCallbacks_Test {
Expand Down

0 comments on commit fd6a9a6

Please sign in to comment.