How to use dbus in CentOS without Desktop Environment - x11

My system is a centos with no gui. I have a server application which "listens" for a method call in a session dbus. It apparently works fine. I have pydbus and python3-gobject installed fine, I also have dbus-launch working. This is the server application:
from pydbus import SessionBus
from gi.repository import GLib
import time
# Variables / Constants / Instantiation...
bus = SessionBus()
BUS = "org.mybus.demo.test"
loop = GLib.MainLoop()
message_count = 0
class DBusService_XML():
"""
DBus Service XML Definition.
type = "i" for integer, "s" for string, "d" for double, "as" list of string data.
"""
dbus = """
<node>
<interface name="{}">
<method name='greeting'>
<arg type="s" name="input" direction="in">
</arg>
<arg type="s" name="output" direction="out">
</arg>
</method>
</interface>
</node>
""".format(BUS)
def greeting(self, clientName):
"Receive and send arg"
print("{} is asking for name".format(clientName))
return "Hello {}, Im Kyle".format(clientName)
if __name__ == "__main__":
bus.publish(BUS, DBusService_XML())
loop.run()
Now in order to call that server method, from another terminal (same user) I tried to use my client application, which failed, then I tried gdbus application which failed with the same error as below:
# dbus-launch gdbus call --session --dest org.mybus.demo.test --object-path /org/mybus/demo/test --method org.mybus.demo.test.greeting "Julia"
Error: GDBus.Error:org.freedesktop.DBus.Error.ServiceUnknown: The name org.mybus.demo.test was not provided by any .service files
From another machine with Desktop Environment everything works fine. I searched around but couldn't find a way to use dbus in that situation. Can anyone help?

Unless your service is already running when you call that method from the client, you will need to enable service activation for it, which involves writing a org.mybus.demo.test.service file and putting it in /usr/share/dbus-1/services. See the specification. It would probably look something like:
[D-BUS Service]
Name=org.mybus.demo.test
Exec=/path/to/your/application.py

Related

Settings schema 'com.github.Suzie97.epoch' is not installed

This is the gschema.xml code for my app:
<?xml version="1.0" encoding="UTF-8"?>
<schemalist>
<schema path="/com/github/Suzie97/epoch"
id="com.github.Suzie97.epoch"
gettext-domain - "com.github.Suzie97.epoch">
<key name="pos-x" type="i">
<default>360</default>
<summary>Most recent x position of Epoch</summary>
<description>Most recent x position of Epoch</description>
</key>
<key name="pos-y" type="i">
<default>360</default>
<summary>Most recent y position of Epoch</summary>
<description>Most recent y position of Epoch</description>
</key>
</schema>
</schemalist>
This is the meson.build file to install the gschema:
install_data(
'gschema.xml',
install_dir: join_paths (get_option ('datadir'), 'glib-2.0', 'schemas'),
rename: meson.project_name() + '.gschema.xml'
)
When I compile this error is displayed:
Settings schema 'com.github.Suzie97.epoch' is not installed
This is the post_install.py script:
#!/usr/bin/env python3
import os
import subprocess
install_prefix = os.environ['MESON_INSTALL_PREFIX']
schemadir = os.path.join(install_prefix, 'share/glib-2.0/schemas')
if not os.environ.get('DESTDIR'):
print('Compiling the gsettings schemas ... ')
subprocess.call(['glib-compile-schemas', schemadir])
Why is this happening?
There are various issues at play:
the name of the schema file should match your application's identifier—in this case, it would be com.github.Suzie97.epoch.gschema.xml
you should not rename the file on installation; just installing it under the glib-2.0/schemas data directory is enough
you should call glib-compile-schemas $datadir/glib-2.0/schemas to "compile" all the schemas once you installed your application; this is typically done as a post-installation script in Meson, using meson.add_install_script().
GSettings does not use the XML per se: the glib-compile-schemas tool will generate a cache file that will be shared by all applications using GSettings, and will be fast to load. This is why GSettings will warn you that the schema is not installed: you are missing that last compilation step.

Calling VBS CreateObject("someapp.someapp", "remote PC") for a COM interface on another machine?

Disclaimer: Yes, I think this questions boils down to understanding some DCOM basics and what VBS CreateObject actually does/needs:
I have a 3rd party application that offers an automation interface via (D?)COM.
The interface is automatically registered when we install the application and it works fine when running simple VBS scripts locally:
This works fine on the same machine:
Dim oAppApi
WScript.Echo "Hello, try to connect ..."
Set oAppApi = CreateObject("theapp.theapp") ' Note that this will either start the application or connect to an already started instance
WScript.Echo oAppApi.APIVersion
oAppApi.DisconnectFromTool
This also works on the same machine:
Dim oAppApi
WScript.Echo "Hello, try to connect ..."
Set oAppApi = CreateObject("theapp.theapp", "localhost")
WScript.Echo oAppApi.APIVersion
oAppApi.DisconnectFromTool
This will fail when run on another PC in the same network:
Dim oAppApi
WScript.Echo "Hello, try to connect ..."
Set oAppApi = CreateObject("theapp.theapp", "machineNameWithAppInstalled") ' FAIL: ActiveX component can't create object
What would be neccessary to make this simple VBScript work from the remote machine?
Would anything need to be installed on the client machine? (COM proxy DLL or somesuch?)
Does the ServerName.TypeNameof CreateObject need to be known on the client side?
Do we have to do some DMCOMCnfg magic on the server?
Additional Details:
Since, from what I know of COM, this might depend on how the stuff is registered, here's my "trace" through the registry for "TheApp.TheApp" on the application PC:
[HKEY_CLASSES_ROOT\TheApp.TheApp]
#="com.company.toolAPI.theapp.theapp"
[HKEY_CLASSES_ROOT\TheApp.TheApp\CLSID]
#="{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}"
[HKEY_CLASSES_ROOT\TheApp.TheApp\CurVer]
#="TheApp.TheApp.7.2"
...
[HKEY_CLASSES_ROOT\TheApp.TheApp.7.2]
#="TheApp.TheApp"
[HKEY_CLASSES_ROOT\TheApp.TheApp.7.2\CLSID]
#="{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}"
...
[HKEY_CLASSES_ROOT\AppID\{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}]
#="THEAPP72 Server"
"DllSurrogate"=""
"RunAs"="Interactive User"
...
[HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}]
#="com.company.toolAPI.theapp.theapp"
"AppID"="{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}"
[HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}\Implemented Categories]
[HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}\Implemented Categories\{62C8FE65-4EBB-45e7-B440-6E39B2CDBF29}]
[HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}\InprocServer32]
#="mscoree.dll"
"ThreadingModel"="Both"
"Class"="com.company.toolAPI.theapp.theapp"
"Assembly"="TheAppCOM, Version=11.0.0.0, Culture=neutral, PublicKeyToken=c9b6e760b808c9f9"
"RuntimeVersion"="v2.0.50727"
"CodeBase"="file:///C:/Company/THEAPP7.2/interface/TheAppCOM.DLL"
[HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}\InprocServer32\11.0.0.0]
"Class"="com.company.toolAPI.theapp.theapp"
"Assembly"="TheAppCOM, Version=11.0.0.0, Culture=neutral, PublicKeyToken=c9b6e760b808c9f9"
"RuntimeVersion"="v2.0.50727"
"CodeBase"="file:///C:/Company/THEAPP7.2/interface/TheAppCOM.DLL"
[HKEY_CLASSES_ROOT\Wow6432Node\CLSID\{0CBEA087-0CC7-4D15-A659-8B3AC68B82E1}\ProgId]
#="TheApp.TheApp"
I used RDS.DataSpace to access a 'middle-tier' dcom server.
Example: http://www.oblique.ch/ms/rds25.html#_Toc483670219

Xposed - hook MTP method running in android.process.media method

I wish to hook a MTP method bool MtpDevice::openSession() in MtpDevice.cpp, this method should be running in android.process.media.
When I try to hook package name android.process.media, it do not being hit at all.(Maybe this process name is not a package name at all).
Since this process is launched by system bootup, I do not know how can I hook it.
The package name of android.process.media should be com.android.providers.media. refer to this file.
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.android.providers.media"
android:sharedUserId="android.media"
android:sharedUserLabel="#string/uid_label"
android:versionCode="1023">

Under what conditions does RmGetList return 2 for the lpdwRebootReasons output parameter?

Background
I am designing an Inno Setup installer to install a Cygwin service, and I am puzzled by the behavior I'm seeing from the Windows Restart Manager APIs.
Specifically, when the service is running (started using the cygrunsrv utility), the RmGetList API function returns 2 (RmRebootReasonSessionMismatch) for its lpdwRebootReasons output parameter. This output parameter is an enumeration of type RM_REBOOT_REASON, and the description on MSDN for the RmRebootReasonSessionMismatch value is:
One or more processes are running in another Terminal Services session.
The Inno Setup log file contains lines like the following:
RestartManager found an application using one of our files: <executable name>
RestartManager found an application using one of our files: <service name>
Can use RestartManager to avoid reboot? No (2: Session Mismatch)
Inno Setup then proceeds trying to replace in-use files, as if Restart Manager was not used at all.
I am puzzled by this output value, because on two different machines I tested (Windows 10 1909 x64 and Windows Server 2012 R2), no terminal server/remote desktop users are logged on.
If I stop the service and start another executable (in the set of files to be replaced by the installer), RmGetList returns 0 (RmRebootReasonNone) for lpdwRebootReasons, and Inno Setup displays the normal dialog for in-use files and allows the user to select to automatically close them.
Process Explorer shows both processes (cygrunsrv.exe and the process it starts) running in session 0 and at System integrity level. Both are console subsystem executables.
Questions
Under what conditions does RmGetList return 2 (RmRebootReasonSessionMismatch) for its lpdwRebootReasons output parameter? (I'm trying to understand why this happens when the service is running.)
Does this value cause the entire Restart Manager session to fail, or can Restart Manager proceed even though it thinks applications are running in one or more different sessions?
For question 2, in the document RM_PROCESS_INFO
bRestartable
TRUE if the application can be restarted by the Restart Manager;
otherwise, FALSE. This member is always TRUE if the process is a
service. This member is always FALSE if the process is a critical
system process.
This value indicates if the application can be restarted by the Restart Manager.
For question 1, Note that services are running in session 0. If the process occupying the resource (registered in RmRegisterResources) is a service A, the RmGetList function which also running in the service process B will return lpdwRebootReasons = RmRebootReasonNone, bRestartable = TRUE.
But if A is not a service, then A & B are running in different sessions, lpdwRebootReasons = RmRebootReasonSessionMismatch and bRestartable = FALSE
other results:(B run with elevated privileges)
A & B is a console and in the same session:lpdwRebootReasons = RmRebootReasonNone, bRestartable = TRUE, ApplicationType = RmConsole.
A & B is a console and in the different session:lpdwRebootReasons = RmRebootReasonSessionMismatch, bRestartable = FALSE, ApplicationType = RmConsole.
A: service, B: console: lpdwRebootReasons = RmRebootReasonNone, bRestartable = TRUE, ApplicationType = RmService
(B not run with elevated privileges):
A & B is a console and in the different session:lpdwRebootReasons = RmRebootReasonCriticalProcess, bRestartable = FALSE, ApplicationType = RmCritical.
A: service, B: console: lpdwRebootReasons = RmRebootReasonPermissionDenied, bRestartable = FALSE, ApplicationType = RmCritical
According the document bRestartable depends on ApplicationType. And then, we can see that if the bRestartable = TRUE, then the lpdwRebootReasons = RmRebootReasonNone. But when bRestartable = FALSE, It depends on the other members RM_PROCESS_INFO.
A Clue from the RestartManager PowerShell Module
The RestartManager PowerShell module (special thanks to Heath Stewart) provides a simple PowerShell interface for the Restart Manager. My commands are as follows:
Set-Location <path to Cygwin root directory>
Start-RestartManagerSession
Get-ChildItem . -File -Include *.exe,*.dll -Recurse | RegisterRestartManagerResource
Get-RestartManagerProcess
Stop-RestartManagerProcess
These commands produce the following output:
Id : <process ID>
StartTime : <process start time>
Description : <executable started by cygrunsrv>
ServiceName :
ApplicationType : Console
ApplicationStatus : Running
IsRestartable : False
RebootReason : SessionMismatch
Id : <cygrunsrv process id>
StartTime : <cygrunsrv process start time>
Description : <description of service>
ServiceName : <service name>
ApplicationType : Service
ApplicationStatus : Running
IsRestartable : True
RebootReason : SessionMismatch
For some reason, Restart Manager sees the cygrunsrv.exe service process as restartable, but the executable it spawns as not restartable. (I am still curious about why this happens in the first place.)
An Imperfect Workaround Attempt
Based on this observed behavior, I first attempted the following workaround:
In the Inno Setup script's [Setup] section, set the following:
CloseApplications=yes
CloseApplicationsFilter=*.chm,*.pdf
RestartApplications=yes
The CloseApplicationsFilter directive specifies what files get registered with the Restart Manager. Note I do not specify *.exe or *.dll here; I want to manually specify only certain .exe files in the [Code] section.
Call the Inno Setup RegisterExtraCloseApplicationsResource function once for each .exe file in the setup that will NOT be spawned by cygrunsrv and put them in the RegisterExtraCloseApplicationsResources event procedure. Example:
[Code]
procedure RegisterExtraCloseApplicationsResources();
begin
RegisterExtraCloseApplicationsResource(false, ExpandConstant('{app}\bin\cygrunsrv.exe'));
end;
It's important not to register any executable spawned by cygrunsrv.exe or any of the Cygwin DLL files, because this will prevent the Restart Manager from taking effect in Inno Setup.
This solution is far from perfect, because executables normally started by cygrunsrv, if started separately, are not detected by Restart Manager (e.g., sshd.exe). For example, new SSH sessions are spawned in executables that the Restart Manager are not restartable.
A Better Solution
I've decided that a better solution is to detect any running executables from code and prompt the user apart from the Restart Manager functionality (which, simply put, doesn't work for Cygwin services).

Windows command line access denied to install service, and I'm the administrator

I'm attempting to install a windows service with Python (3.4). Upon installation I intend to run it. It doesn't perform any function other than demo a service running in Windows.
I'm getting the following access permission when installing the service:
I'm the admin for the computer therefore I should have the permission to do this.
Perhaps its because the command line is attempting install the service with a Python. Does Python have permission to do this through the command line?
How can I get past this issue. Is there a specific file with permissions that I need to change?
I've included the code from the service just in case.
The help is appreciated.
#Run a Windows Service
import win32serviceutil
import win32service
import win32event
import os
import sys
import time
from threading import Thread
import http.server
class ServiceLauncher(win32serviceutil.ServiceFramework):
_svc_name_ = "PythonService"
_svc_display_name_ = "Python based win32 service"
_svc_description_ = ""
def __init__(self, args):
win32serviceutil.ServiceFramework.__init__(self, args)
self.hWaitStop = win32event.CreateEvent(None, 0, 0, None)
def SvcStop(self):
self.ReportServiceStatus(win32service.SERVICE_STOP_PENDING)
win32event.SetEvent(self.hWaitStop)
def SvcDoRun(self):
thread = Thread(target = httpserver.run_httpserver)
thread.daemon = True
thread.start()
while (1):
rc = win32event.WaitForSingleObject(self.hWaitStop, 1000)
if rc==win32event.WAIT_OBJECT_0:
# Stop event
break
if __name__ == '__main__':
win32serviceutil.HandleCommandLine(ServiceLauncher)
The solution involves running the command line as an administrator. This is performed by right clicking the command prompt and selecting to run the command line as an administrator.
In Windows, the user logged into the computer may be a Windows administrator but the rights do not automatically extend to the command line. The user with administrator rights has to choose to run the command line as an administrator in order to perform the commands reserved to administrators such as performing an install of a Windows service.

Resources