UWP Brokered Component Restart/Stop DLL - c#

so I'm implementing printing for my UWP app following this guide https://learn.microsoft.com/en-us/windows/uwp/winrt-components/brokered-windows-runtime-components-for-side-loaded-windows-store-apps#creating-and-deploying-the-windows-runtime-proxy
I have a bug where the printer stops working and I realized one fix is to go into task manager and delete the COM Surrogate associated with a dll. I'm not sure how to find out what dll this is, has anyone ran into this issue before?
I would think the fix is to relink the component somehow but am not sure how.

The proper way to print from a UWP is using the Windows.Graphics.Printing, Windows.UI.Xaml.Printing, PrintDocument APIs as documented here:
https://learn.microsoft.com/en-us/windows/uwp/devices-sensors/print-from-your-app
One thing to note is that this approach currently does not support silent/unattended print scenarios. For those you would have to work around using classic Win32 printing API, either from a brokered component (as you tried) or using a desktop extension to your UWP. The latter is the preferred route (brokered components is Win8 era tech). I have a quick tutorial on desktop extensions here: https://stefanwick.com/2018/04/06/uwp-with-desktop-extension-part-1/ and a very simple silent printing sample here: 1drv.ms/u/s!AovTwKUMywTNnOsbzlRfghOikDy8Dw

I have used this technique (Brokered Windows Runtime Components) in an LOB app for several years, and it is always a PITA for the maintenance.
Every time I have made an update to Brokered Windows Runtime Component I will need to register it again using regsvr32.exe. If I have run the app and COM Surrogate is already running, the registration will fail. I will need to reboot the system, or I have to kill the running "dllhost.exe" in task manager - there might be several instances of dllhost.exe, and I just kill the ones that run under the current logon user, and leave those run as SYSTEM.
One of the dllhost.exe instances hosts the DLL you created and registered. It is not clear why printer stops working so I can't give an answer. To help investigation, add some logs to these points.
When the app code is calling the Brokered Windows Runtime Component, check the return value of the call, and try and catch any exception.
Inside the Brokered Windows Runtime Component, at the entry and exit of the method that is being called by the App.
Check the code that uses printer, is it working correctly? or is it being called at all?

Related

Is Memory-mapped-files as ipc between uwp app and win32 process supported

The official docs doesn't properly state if ipc via memory-mapped-files is supported in uwp. I was working on a scenario for ipc between an uwp app and its desktop extension. While I can create memory-mapped-files using System.IO.MemoryMappedFiles from uwp app with codeGeneration capability but opening from win32 process fails with message Unable to find the specified file.. Is ipc via memory-mapped-files supported in uwp, if yes, what is the proper way to do it??
Minimal reproduceable sample.
Update 1
Updated sample implementing answer from #Peter Torr - MSFT.
Update 2
Working sample in which memory-mapped-file created from uwp app can be read by win32 process. Reading memory-mapped-file in uwp app created by win32 process still isn't working.
Yes it is supported, but if you're creating the object in a UWP context and opening it from a Desktop context then the Desktop process needs to explicitly use the namespace of the named object.
From within your UWP process, call GetAppContainerNamedObjectPath(nullptr, nullptr, ...) to determine what that namespace is, and then add a backslash and your mapped file name to the end. It will be something like AppContainerNamedObjects\S-1-15-2-xxxxxxx\YourMappedName
You should only need to do this once, unless you change your package name (including the publisher hash). So once you have generated it, you can hard-code the value into your desktop app and forget about it.
Note that if you do it the other way around - Desktop creates the object, and UWP opens it - then you don't need to worry about the namespace, but you have to modify the access control instead, which is trickier.

DwmRegisterThumbnail for UWP app

I'm working on a UWP app that provides task-switching capabilities for users with complex physical limitations. This question is related to trying to provide the live thumbnails like alt-tab and the taskbar do. So far, much of the functionality has been made possible through an in-process full-trust component making the necessary (winapi) calls and passing information back to the UWP app.
I made a test WPF app utilizing DwmRegisterThumbnail and DwmUpdateThumbnailProperties and it works fine.
However, when I attempt to implement this in the UWP/full-trust app, registration fails with E_INVALIDARG. According to MSDN, this can be because the source or destination windows are not top-level windows. In this case, the destination window is the window handle for the UWP app, and the source window is explorer.exe (file explorer, in this case). Both are enumerated by EnumWindows and aren't children of other windows.
Is the problem that the full-trust side is calling DwmRegisterThumbnail? I tried making the calls from the UWP side as well, but got the same result. I wouldn't really expect to be able to make those calls from the UWP side anyway, since it would seem to violate the sandboxed nature of it. Is there any way to do this?
Edit:
I tried doing a C++ UWP proof-of-concept, but couldn't reference anything DWM-related. Then I found this. Looks like DWM isn't available at all to UWP.
I'm guessing the full-trust component can't register the UWP app to be drawn to because, according to this:
The window designated by hwndDestination must either be the desktop
window itself or be owned by the process that is calling
DwmRegisterThumbnail. This is required to prevent applications from
affecting the content of other applications.
As stated above, I tried having the full-trust component call DwmRegisterThumbnail, using the handle of the host UWP app, but it doesn't appear to work, presumably because it isn't owned by the UWP process?
Does anyone know of alternative methods that could be used to accomplish a thumbnail/window preview?

Including C# ConsoleApplication in UWA

Does anybody of you guys have experiences with including a C#-based Console Application in a C#-based Universal Windows App?
The reason why I'm asking: I've an already exsisting Console Application developed by another developer. This Application includes a database with all the queries which I need for my App.
The problem: When I try to include the CA in my UWA project many commands like
private global::System.Runtime.InteropServices.HandleRef
throw new global::System.ApplicationException
don't get identified by VS2015.
Is there a way to let the UWA project identify CA commands? For example with adding an external CA-library or something like that.
Thank you!
You can't combine full .NET (console, winforms, WPF) assemblies with an UWP app, as they're different .NET frameworks. For more details, please read this reply. Part of the code is shareable in a Portable Class Library (PCL), but most likely not all of the code you've written.
Possible solutions:
Create an API (yourself or with the other developer) to expose the functionality needed over a (preferably) REST api.
Find a way to cheat the system. Example: launch a file (associated to the console application) with the Launcher api and output the results to a text file on disk, which you then read from your UWP app.
The first one is guaranteed to work. You might find a way to cheat the system for the second 'solution', but there's no guarantee that it won't break in the future when Windows 10 gets updated (experienced that myself for another 'hack' on the upgrade between Windows 8 and 8.1).

Compile and run a external Java program in WinRT?

I am making windows 8 , c#/xaml app. Is it possible to compile and run a java console program like " hello world"?
Since winRt apps cannot use System.Diagnostics.Process then it cannot figure how to compile and run it. Or if compile is not possible, just being able to run a .class file is fine.
I have tried useing System.Diagnostics.Process to open cmd to compile but that class isn't supported.
Thanks for any advice.
There's certainly not an elegant or intended (& documented) way to launch a process like you describe from a Windows Store application (it's intentionally locked down and there is no "command prompt for the new Windows store UI apps). There are some that suggest that there may be a way via CoCreateInstanceFromApp, but the documentation now reads as if that API only works for a limited number of Microsoft built COM objects.
While you can launch other installed Windows Store applications, the Java compiler will definitely not be one of those without a significant and unusual repackaging by Oracle (or some third party). While it's possible that someone is working on that, it would seem unlikely (given the limited need for such functionality).
Depending on the nature of the Java code, you may want to look for a Java interpreters that could be embedded within your application, and call it directly, especially if the Java code is trivial.
Your application requirements would suggest that a traditional Windows desktop application would be a better fit.

Toolbar on windows xp and vista taskbar

I have made a toolbar that I want to enable from a systray application written in C#, the actual toolbar enabling is done from a C++ part using [DLLImport].
Current I use:
SHLoadInProc(__uuidof(MyBandLoader))
but this fails on vista (SHLoadInProc is not implemented any more), and on Windows XP SP2 with IE6 (the quick launch toolbar vanishes after reboot).
On Vista I have tried to with: CocreateInstance() and BandSite->AddBand(), but using the guid of the toolbar dll gave me either a segmentation fault or the address bar.
Is there another way to enable a toolbar from another program on XP and Vista?
On Vista there's a new poorly-documented interface called ITrayDeskBand.
Create an instance of this via CoCreateInstance, and then call ShowDeskBand([CLSID of your toolbar]) on the returned pointer (in C++ - I'm not sure how you create all the relevant bits for PInvoke in C# - might be easier to write a simple C++ dll to expose this function)
That only works on Vista though, on XP you need to continue with the SHLoadInProc method above, so you need to test the OS version and do the appropriate thing.
Be careful if you're lifting code from that codeproject article - it's full of subtle bugs, although many of them are discussed in the comments
I have used that one, but it only tells you have to make a toolbar, not how to enable it from another program.
One should never use .Net to create any COM objects inside the Explorer process. This will just not work if there is another .net component using a different framework version already loaded into the explorers process. Only one .net framework for each process. MS should have never propaged samples about developing deskbands in any .net language.
The only way on Vista an up is to use the ITrayDeskBand interface to display the toolbar. However, this will display a confirmation box to the user and he can refuse the toolbar to be shown.

Categories