Allow using IRPC functions on the messaging bus from Python.
authorJelmer Vernooij <jelmer@samba.org>
Mon, 26 May 2008 02:14:28 +0000 (04:14 +0200)
committerJelmer Vernooij <jelmer@samba.org>
Mon, 26 May 2008 02:14:28 +0000 (04:14 +0200)
(This used to be commit 6ecf81ae13dffa05356c1177c617206c120fb7d7)

source4/lib/messaging/config.mk
source4/lib/messaging/pymessaging.c [moved from source4/lib/messaging/pyirpc.c with 87% similarity]
source4/librpc/config.mk
source4/librpc/rpc/pyrpc.h
source4/pidl/lib/Parse/Pidl/Samba4/Python.pm
source4/scripting/bin/smbstatus

index f330ed7cabf5b6a8663e5987095bc3bb58912a8c..e92f78c8e368b99127d41aae26ebf556f3b93d49 100644 (file)
@@ -11,8 +11,8 @@ PUBLIC_DEPENDENCIES = \
 
 MESSAGING_OBJ_FILES = $(libmessagingsrcdir)/messaging.o
 
-[PYTHON::python_irpc]
-LIBRARY_REALNAME = samba/irpc.$(SHLIBEXT)
-PRIVATE_DEPENDENCIES = MESSAGING LIBEVENTS
+[PYTHON::python_messaging]
+LIBRARY_REALNAME = samba/messaging.$(SHLIBEXT)
+PRIVATE_DEPENDENCIES = MESSAGING LIBEVENTS python_irpc
 
-python_irpc_OBJ_FILES = $(libmessagingsrcdir)/pyirpc.o
+python_messaging_OBJ_FILES = $(libmessagingsrcdir)/pymessaging.o
similarity index 87%
rename from source4/lib/messaging/pyirpc.c
rename to source4/lib/messaging/pymessaging.c
index 41475daaffa2fb9e163d7923a25fec06337ca8ef..e05d5eb1f1ac54fae7c2d2a3a39e6253739a561b 100644 (file)
@@ -31,7 +31,7 @@
 #include "librpc/gen_ndr/py_irpc.h"
 
 PyAPI_DATA(PyTypeObject) messaging_Type;
-PyAPI_DATA(PyTypeObject) irpc_InterfaceType;
+PyAPI_DATA(PyTypeObject) irpc_ClientConnectionType;
 
 static bool server_id_from_py(PyObject *object, struct server_id *server_id)
 {
@@ -65,7 +65,7 @@ PyObject *py_messaging_connect(PyTypeObject *self, PyObject *args, PyObject *kwa
        const char *messaging_path = NULL;
        messaging_Object *ret;
 
-       if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|Os:connect", 
+       if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|Oz:connect", 
                discard_const_p(char *, kwnames), &own_id, &messaging_path)) {
                return NULL;
        }
@@ -280,6 +280,9 @@ PyTypeObject messaging_Type = {
        .tp_dealloc = py_messaging_dealloc,
        .tp_methods = py_messaging_methods,
        .tp_getset = py_messaging_getset,
+       .tp_doc = "Messaging(own_id=None, messaging_path=None)\n" \
+                 "Create a new object that can be used to communicate with the peers in the specified messaging path.\n" \
+                 "If no path is specified, the default path from smb.conf will be used."
 };
 
 
@@ -292,7 +295,7 @@ typedef struct {
        struct server_id *dest_ids;
        struct messaging_context *msg_ctx;
        TALLOC_CTX *mem_ctx;
-} irpc_InterfaceObject;
+} irpc_ClientConnectionObject;
 
 /*
   setup a context for talking to a irpc server
@@ -307,14 +310,14 @@ PyObject *py_irpc_connect(PyTypeObject *self, PyObject *args, PyObject *kwargs)
        char *server;
        const char *messaging_path = NULL;
        PyObject *own_id = Py_None;
-       irpc_InterfaceObject *ret;
+       irpc_ClientConnectionObject *ret;
 
-       if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s|Os:connect", 
+       if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s|Oz:connect", 
                discard_const_p(char *, kwnames), &server, &own_id, &messaging_path)) {
                return NULL;
        }
 
-       ret = PyObject_New(irpc_InterfaceObject, &irpc_InterfaceType);
+       ret = PyObject_New(irpc_ClientConnectionObject, &irpc_ClientConnectionType);
        if (ret == NULL)
                return NULL;
 
@@ -326,6 +329,8 @@ PyObject *py_irpc_connect(PyTypeObject *self, PyObject *args, PyObject *kwargs)
 
        if (messaging_path == NULL) {
                messaging_path = lp_messaging_path(ret, global_loadparm);
+       } else {
+               messaging_path = talloc_strdup(ret->mem_ctx, messaging_path);
        }
 
        if (own_id != Py_None) {
@@ -413,12 +418,13 @@ PyTypeObject irpc_ResultIteratorType = {
        .tp_name = "irpc.ResultIterator",
        .tp_basicsize = sizeof(irpc_ResultObject),
        .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE,
-       .tp_iter = (iternextfunc)irpc_result_next,
+       .tp_iternext = (iternextfunc)irpc_result_next,
+       .tp_iter = PyObject_SelfIter,
        .tp_methods = irpc_result_methods,
        .tp_dealloc = irpc_result_dealloc,
 };
 
-static PyObject *py_irpc_call(irpc_InterfaceObject *p, struct PyNdrRpcMethodDef *method_def, PyObject *args, PyObject *kwargs)
+static PyObject *py_irpc_call(irpc_ClientConnectionObject *p, struct PyNdrRpcMethodDef *method_def, PyObject *args, PyObject *kwargs)
 {
        void *ptr;
        struct irpc_request **reqs;
@@ -476,7 +482,7 @@ done:
 
 static PyObject *py_irpc_call_wrapper(PyObject *self, PyObject *args, void *wrapped, PyObject *kwargs)
 {      
-       irpc_InterfaceObject *iface = (irpc_InterfaceObject *)self;
+       irpc_ClientConnectionObject *iface = (irpc_ClientConnectionObject *)self;
        struct PyNdrRpcMethodDef *md = wrapped;
 
        return py_irpc_call(iface, md, args, kwargs);
@@ -484,21 +490,24 @@ static PyObject *py_irpc_call_wrapper(PyObject *self, PyObject *args, void *wrap
 
 static void py_irpc_dealloc(PyObject *self)
 {
-       irpc_InterfaceObject *iface = (irpc_InterfaceObject *)self;
+       irpc_ClientConnectionObject *iface = (irpc_ClientConnectionObject *)self;
        talloc_free(iface->mem_ctx);
        PyObject_Del(self);
 }
 
-PyTypeObject irpc_InterfaceType = {
+PyTypeObject irpc_ClientConnectionType = {
        PyObject_HEAD_INIT(NULL) 0,
        .tp_name = "irpc.ClientConnection",
-       .tp_basicsize = sizeof(irpc_InterfaceObject),
+       .tp_basicsize = sizeof(irpc_ClientConnectionObject),
        .tp_flags = Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE,
        .tp_new = py_irpc_connect,
        .tp_dealloc = py_irpc_dealloc,
+       .tp_doc = "ClientConnection(server, own_id=None, messaging_path=None)\n" \
+                 "Create a new IRPC client connection to communicate with the servers in the specified path.\n" \
+                 "If no path is specified, the default path from smb.conf will be used."
 };
 
-static bool irpc_AddNdrRpcMethods(PyTypeObject *ifacetype, struct PyNdrRpcMethodDef *mds)
+static bool irpc_AddNdrRpcMethods(PyTypeObject *ifacetype, const struct PyNdrRpcMethodDef *mds)
 {
        int i;
        for (i = 0; mds[i].name; i++) {
@@ -510,7 +519,7 @@ static bool irpc_AddNdrRpcMethods(PyTypeObject *ifacetype, struct PyNdrRpcMethod
                wb->wrapper = (wrapperfunc)py_irpc_call_wrapper;
                wb->doc = discard_const_p(char, mds[i].doc);
                
-               ret = PyDescr_NewWrapper(ifacetype, wb, &mds[i]);
+               ret = PyDescr_NewWrapper(ifacetype, wb, discard_const_p(void, &mds[i]));
 
                PyDict_SetItemString(ifacetype->tp_dict, mds[i].name, 
                                     (PyObject *)ret);
@@ -519,11 +528,11 @@ static bool irpc_AddNdrRpcMethods(PyTypeObject *ifacetype, struct PyNdrRpcMethod
        return true;
 }
 
-void initirpc(void)
+void initmessaging(void)
 {
        PyObject *mod;
 
-       if (PyType_Ready(&irpc_InterfaceType) < 0)
+       if (PyType_Ready(&irpc_ClientConnectionType) < 0)
                return;
 
        if (PyType_Ready(&messaging_Type) < 0)
@@ -532,15 +541,15 @@ void initirpc(void)
        if (PyType_Ready(&irpc_ResultIteratorType) < 0) 
                return;
 
-       if (!irpc_AddNdrRpcMethods(&irpc_InterfaceType, py_ndr_irpc_methods))
+       if (!irpc_AddNdrRpcMethods(&irpc_ClientConnectionType, py_ndr_irpc_methods))
                return;
 
-       mod = Py_InitModule3("irpc", NULL, "Internal RPC");
+       mod = Py_InitModule3("messaging", NULL, "Internal RPC");
        if (mod == NULL)
                return;
 
-       Py_INCREF((PyObject *)&irpc_InterfaceType);
-       PyModule_AddObject(mod, "ClientConnection", (PyObject *)&irpc_InterfaceType);
+       Py_INCREF((PyObject *)&irpc_ClientConnectionType);
+       PyModule_AddObject(mod, "ClientConnection", (PyObject *)&irpc_ClientConnectionType);
 
        Py_INCREF((PyObject *)&messaging_Type);
        PyModule_AddObject(mod, "Messaging", (PyObject *)&messaging_Type);
index 2943c7b516cbe0ca89b488a8bf014f6032f5ae9a..ab25921ef88ac889e1d4e98a7a2c817347cb551e 100644 (file)
@@ -434,6 +434,11 @@ PUBLIC_DEPENDENCIES = dcerpc NDR_UNIXINFO
 
 RPC_NDR_UNIXINFO_OBJ_FILES = $(gen_ndrsrcdir)/ndr_unixinfo_c.o
 
+[SUBSYSTEM::RPC_NDR_IRPC]
+PUBLIC_DEPENDENCIES = dcerpc NDR_IRPC
+
+RPC_NDR_IRPC_OBJ_FILES = $(gen_ndrsrcdir)/ndr_irpc_c.o
+
 [LIBRARY::dcerpc_samr]
 PUBLIC_DEPENDENCIES = dcerpc NDR_SAMR 
 
@@ -658,6 +663,12 @@ PRIVATE_DEPENDENCIES = dcerpc_atsvc PYTALLOC param swig_credentials  python_dcer
 
 python_atsvc_OBJ_FILES = $(gen_ndrsrcdir)/py_atsvc.o
 
+[PYTHON::python_nbt]
+LIBRARY_REALNAME = samba/nbt.$(SHLIBEXT)
+PRIVATE_DEPENDENCIES = NDR_NBT PYTALLOC param swig_credentials python_dcerpc
+
+python_nbt_OBJ_FILES = $(gen_ndrsrcdir)/py_nbt.o
+
 [PYTHON::python_samr]
 LIBRARY_REALNAME = samba/dcerpc/samr.$(SHLIBEXT)
 PRIVATE_DEPENDENCIES = dcerpc_samr PYTALLOC python_dcerpc_security python_lsa python_dcerpc_misc swig_credentials param python_dcerpc
@@ -694,6 +705,12 @@ PRIVATE_DEPENDENCIES = RPC_NDR_UNIXINFO PYTALLOC param swig_credentials python_d
 
 python_unixinfo_OBJ_FILES = $(gen_ndrsrcdir)/py_unixinfo.o
 
+[PYTHON::python_irpc]
+LIBRARY_REALNAME = samba/irpc.$(SHLIBEXT)
+PRIVATE_DEPENDENCIES = RPC_NDR_IRPC PYTALLOC param swig_credentials python_dcerpc_security python_dcerpc_misc python_dcerpc python_nbt
+
+python_irpc_OBJ_FILES = $(gen_ndrsrcdir)/py_irpc.o
+
 [PYTHON::python_drsuapi]
 LIBRARY_REALNAME = samba/dcerpc/drsuapi.$(SHLIBEXT)
 PRIVATE_DEPENDENCIES = RPC_NDR_DRSUAPI PYTALLOC param swig_credentials python_dcerpc_misc python_dcerpc_security python_dcerpc
index 989aeecc7b9d678a4ebe2894029ff5cc0ccc8b75..af9ca728d8ed666b880115b140e28941c4d08f06 100644 (file)
                fail; \
        }
 
+#define dom_sid0_Type dom_sid_Type
 #define dom_sid2_Type dom_sid_Type
 #define dom_sid28_Type dom_sid_Type
+#define dom_sid0_Check dom_sid_Check
 #define dom_sid2_Check dom_sid_Check
 #define dom_sid28_Check dom_sid_Check
 
index 055ee13b108d31127f15188f93a37d597f90d6da..b5ae801ff8276ac7e136792db93014b5210628d3 100644 (file)
@@ -651,7 +651,7 @@ sub Interface($$$)
                }
 
                $self->pidl("const struct PyNdrRpcMethodDef py_ndr_$interface->{NAME}\_methods[] = {");
-               $self->pidl_hdr("const struct PyNdrRpcMethodDef py_ndr_$interface->{NAME}\_methods[];");
+               $self->pidl_hdr("extern const struct PyNdrRpcMethodDef py_ndr_$interface->{NAME}\_methods[];");
                $self->indent;
                foreach my $d (@fns) {
                        my ($infn, $outfn, $callfn, $prettyname, $docstring, $opnum) = @$d;
index 782e83e4cf68a6c449cefd5f6a3098ed372f57bb..6d852c279cd63f2156292310995f08827170f323 100755 (executable)
@@ -15,11 +15,12 @@ sys.path.insert(0, "bin/python")
 
 import optparse
 import samba.getopt as options
-import samba.irpc
+from samba import messaging, irpc
 
-def show_sessions():
+def show_sessions(conn):
        """show open sessions"""
-       sessions = smbsrv_sessions()
+       conn = open_connection("smb_server")
+       sessions = conn.smbsrv_information(irpc.SMBSRV_INFO_SESSIONS).next()
        print "User                                  Client      Connected at"
        print "-------------------------------------------------------------------------------"
        for session in sessions:
@@ -27,37 +28,43 @@ def show_sessions():
                print "%-30s %16s   %s" % (fulluser, session.client_ip, sys.httptime(session.connect_time))
        print ""
 
-def show_tcons():
+def show_tcons(open_connection):
        """show open tree connects"""
-       tcons = smbsrv_tcons()
+       conn = open_connection("smb_server")
+       tcons = conn.smbsrv_information(irpc.SMBSRV_INFO_TCONS).next()
        print "Share                                 Client      Connected at"
        print "-------------------------------------------------------------------------------"
        for tcon in tcons:
                print "%-30s %16s   %s\n" % (tcon.share_name, tcon.client_ip, sys.httptime(tcon.connect_time))
 
 
-def show_nbt():
+def show_nbt(open_connection):
        """show nbtd information"""
-       stats = nbtd_statistics()
-       print "NBT server statistics:",
+       conn = open_connection("nbt_server")
+       stats = conn.nbtd_information(irpc.NBTD_INFO_STATISTICS).next()
+       print "NBT server statistics:"
        for r in stats:
-               print "\t" + r + ":\t" + stats[r] + "\n"
+               print "\t" + r + ":\t" + getattr(stats, r) + "\n"
        print ""
 
 parser = optparse.OptionParser("%s [options]" % sys.argv[0])
 sambaopts = options.SambaOptions(parser)
 parser.add_option_group(sambaopts)
-parser.add_option("--nbt", type="string", metavar="NBT", 
-        help="show NetBIOS status")
+parser.add_option("--messaging-path", type="string", metavar="PATH",
+                         help="messaging path")
+parser.add_option("--nbt", help="show NetBIOS status", action="store_true")
+
+opts, args = parser.parse_args()
 
 lp = sambaopts.get_loadparm()
 
 print "%s\n\n" % lp.get("server string")
 
+def open_connection(name):
+       return messaging.ClientConnection(name, messaging_path=opts.messaging_path)
+
 if opts.nbt:
-       show_nbt()
+       show_nbt(open_connection)
 else:
-       show_sessions()
-       show_tcons()
-
-return 0
+       show_sessions(open_connection)
+       show_tcons(open_connection)