# HG changeset patch # User Edouard Tisserant # Date 1730127767 -3600 # Node ID 1ffff67678adb3ec2d72111b96377e99cc3cf9b9 # Parent a89ed401fbc69d781a6b37bfa9d5d402f19bdc06 Add ExtendedCall to PLCObject as a replacement of RemoteExec and reflect it in eRPC interface. ExtendedCall is a generic remote procedure call that runtime code can register to and that IDE extensions can call. For example a fieldbus extension can use ExtendedCall to browse the fieldbus devices connected to the runtime. diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/PLCObject.cpp --- a/C_runtime/PLCObject.cpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/PLCObject.cpp Mon Oct 28 16:02:47 2024 +0100 @@ -675,3 +675,13 @@ "TraceThreadProc ended normally"); } +uint32_t PLCObject::ExtendedCall(const char * method, const binary_t * argument, binary_t * answer) +{ + // TODO + + answer->data = (uint8_t*)""; + answer->dataLength = 0; + + return 0; +} + diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/PLCObject.hpp --- a/C_runtime/PLCObject.hpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/PLCObject.hpp Mon Oct 28 16:02:47 2024 +0100 @@ -71,6 +71,7 @@ uint32_t SetTraceVariablesList(const list_trace_order_1_t * orders, int32_t * debugtoken); uint32_t StartPLC(void); uint32_t StopPLC(bool * success); + uint32_t ExtendedCall(const char * method, const binary_t * argument, binary_t * answer); // Public interface used by runtime uint32_t AutoLoad(); diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/c_erpc_PLCObject_client.cpp --- a/C_runtime/c_erpc_PLCObject_client.cpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/c_erpc_PLCObject_client.cpp Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ @@ -132,6 +132,14 @@ return result; } +uint32_t ExtendedCall(const char * method, const binary_t * argument, binary_t * answer) +{ + uint32_t result; + result = s_BeremizPLCObjectService_client->ExtendedCall(method, argument, answer); + + return result; +} + void initBeremizPLCObjectService_client(erpc_client_t client) { #if ERPC_ALLOCATION_POLICY == ERPC_ALLOCATION_POLICY_DYNAMIC diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/c_erpc_PLCObject_client.h --- a/C_runtime/c_erpc_PLCObject_client.h Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/c_erpc_PLCObject_client.h Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ @@ -38,6 +38,7 @@ kBeremizPLCObjectService_SetTraceVariablesList_id = 12, kBeremizPLCObjectService_StartPLC_id = 13, kBeremizPLCObjectService_StopPLC_id = 14, + kBeremizPLCObjectService_ExtendedCall_id = 15, }; //! @name BeremizPLCObjectService @@ -69,6 +70,8 @@ uint32_t StartPLC(void); uint32_t StopPLC(bool * success); + +uint32_t ExtendedCall(const char * method, const binary_t * argument, binary_t * answer); //@} #endif // ERPC_FUNCTIONS_DEFINITIONS diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/c_erpc_PLCObject_server.cpp --- a/C_runtime/c_erpc_PLCObject_server.cpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/c_erpc_PLCObject_server.cpp Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ @@ -132,6 +132,14 @@ return result; } + + uint32_t ExtendedCall(const char * method, const binary_t * argument, binary_t * answer) + { + uint32_t result; + result = ::ExtendedCall(method, argument, answer); + + return result; + } }; ERPC_MANUALLY_CONSTRUCTED_STATIC(BeremizPLCObjectService_service, s_BeremizPLCObjectService_service); diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/c_erpc_PLCObject_server.h --- a/C_runtime/c_erpc_PLCObject_server.h Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/c_erpc_PLCObject_server.h Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ @@ -39,6 +39,7 @@ kBeremizPLCObjectService_SetTraceVariablesList_id = 12, kBeremizPLCObjectService_StartPLC_id = 13, kBeremizPLCObjectService_StopPLC_id = 14, + kBeremizPLCObjectService_ExtendedCall_id = 15, }; //! @name BeremizPLCObjectService @@ -70,6 +71,8 @@ uint32_t StartPLC(void); uint32_t StopPLC(bool * success); + +uint32_t ExtendedCall(const char * method, const binary_t * argument, binary_t * answer); //@} diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/erpc_PLCObject_client.cpp --- a/C_runtime/erpc_PLCObject_client.cpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/erpc_PLCObject_client.cpp Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ @@ -1213,3 +1213,74 @@ return result; } + +// BeremizPLCObjectService interface ExtendedCall function client shim. +uint32_t BeremizPLCObjectService_client::ExtendedCall(const char * method, const binary_t * argument, binary_t * answer) +{ + erpc_status_t err = kErpcStatus_Success; + + uint32_t result; + +#if ERPC_PRE_POST_ACTION + pre_post_action_cb preCB = m_clientManager->getPreCB(); + if (preCB) + { + preCB(); + } +#endif + + // Get a new request. + RequestContext request = m_clientManager->createRequest(false); + + // Encode the request. + Codec * codec = request.getCodec(); + + if (codec == NULL) + { + err = kErpcStatus_MemoryError; + } + else + { + codec->startWriteMessage(message_type_t::kInvocationMessage, m_serviceId, m_ExtendedCallId, request.getSequence()); + + { + uint32_t method_len = strlen((const char*)method); + + codec->writeString(method_len, (const char*)method); + } + + write_binary_t_struct(codec, argument); + + // Send message to server + // Codec status is checked inside this function. + m_clientManager->performRequest(request); + + read_binary_t_struct(codec, answer); + + codec->read(result); + + err = codec->getStatus(); + } + + // Dispose of the request. + m_clientManager->releaseRequest(request); + + // Invoke error handler callback function + m_clientManager->callErrorHandler(err, m_ExtendedCallId); + +#if ERPC_PRE_POST_ACTION + pre_post_action_cb postCB = m_clientManager->getPostCB(); + if (postCB) + { + postCB(); + } +#endif + + + if (err != kErpcStatus_Success) + { + result = 0xFFFFFFFFU; + } + + return result; +} diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/erpc_PLCObject_client.hpp --- a/C_runtime/erpc_PLCObject_client.hpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/erpc_PLCObject_client.hpp Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ @@ -50,6 +50,8 @@ virtual uint32_t StopPLC(bool * success); + virtual uint32_t ExtendedCall(const char * method, const binary_t * argument, binary_t * answer); + protected: erpc::ClientManager *m_clientManager; }; diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/erpc_PLCObject_common.h --- a/C_runtime/erpc_PLCObject_common.h Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/erpc_PLCObject_common.h Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/erpc_PLCObject_common.hpp --- a/C_runtime/erpc_PLCObject_common.hpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/erpc_PLCObject_common.hpp Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/erpc_PLCObject_interface.cpp --- a/C_runtime/erpc_PLCObject_interface.cpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/erpc_PLCObject_interface.cpp Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/erpc_PLCObject_interface.hpp --- a/C_runtime/erpc_PLCObject_interface.hpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/erpc_PLCObject_interface.hpp Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ @@ -33,6 +33,7 @@ static const uint8_t m_SetTraceVariablesListId = 12; static const uint8_t m_StartPLCId = 13; static const uint8_t m_StopPLCId = 14; + static const uint8_t m_ExtendedCallId = 15; virtual ~BeremizPLCObjectService_interface(void); @@ -63,6 +64,8 @@ virtual uint32_t StartPLC(void) = 0; virtual uint32_t StopPLC(bool * success) = 0; + + virtual uint32_t ExtendedCall(const char * method, const binary_t * argument, binary_t * answer) = 0; private: }; } // erpcShim diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/erpc_PLCObject_server.cpp --- a/C_runtime/erpc_PLCObject_server.cpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/erpc_PLCObject_server.cpp Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ @@ -501,6 +501,12 @@ break; } + case BeremizPLCObjectService_interface::m_ExtendedCallId: + { + erpcStatus = ExtendedCall_shim(codec, messageFactory, transport, sequence); + break; + } + default: { erpcStatus = kErpcStatus_InvalidArgument; @@ -1313,3 +1319,92 @@ return err; } + +// Server shim for ExtendedCall of BeremizPLCObjectService interface. +erpc_status_t BeremizPLCObjectService_service::ExtendedCall_shim(Codec * codec, MessageBufferFactory *messageFactory, Transport * transport, uint32_t sequence) +{ + erpc_status_t err = kErpcStatus_Success; + + char * method = NULL; + binary_t *argument = NULL; + argument = (binary_t *) erpc_malloc(sizeof(binary_t)); + if (argument == NULL) + { + codec->updateStatus(kErpcStatus_MemoryError); + } + binary_t *answer = NULL; + uint32_t result; + + // startReadMessage() was already called before this shim was invoked. + + { + uint32_t method_len; + char * method_local; + codec->readString(method_len, &method_local); + method = (char*) erpc_malloc((method_len + 1) * sizeof(char)); + if ((method == NULL) || (method_local == NULL)) + { + codec->updateStatus(kErpcStatus_MemoryError); + } + else + { + memcpy(method, method_local, method_len); + (method)[method_len] = 0; + } + } + + read_binary_t_struct(codec, argument); + + answer = (binary_t *) erpc_malloc(sizeof(binary_t)); + if (answer == NULL) + { + codec->updateStatus(kErpcStatus_MemoryError); + } + + err = codec->getStatus(); + if (err == kErpcStatus_Success) + { + // Invoke the actual served function. +#if ERPC_NESTED_CALLS_DETECTION + nestingDetection = true; +#endif + result = m_handler->ExtendedCall(method, argument, answer); +#if ERPC_NESTED_CALLS_DETECTION + nestingDetection = false; +#endif + + // preparing MessageBuffer for serializing data + err = messageFactory->prepareServerBufferForSend(codec->getBufferRef(), transport->reserveHeaderSize()); + } + + if (err == kErpcStatus_Success) + { + // preparing codec for serializing data + codec->reset(transport->reserveHeaderSize()); + + // Build response message. + codec->startWriteMessage(message_type_t::kReplyMessage, BeremizPLCObjectService_interface::m_serviceId, BeremizPLCObjectService_interface::m_ExtendedCallId, sequence); + + write_binary_t_struct(codec, answer); + + codec->write(result); + + err = codec->getStatus(); + } + + erpc_free(method); + + if (argument) + { + free_binary_t_struct(argument); + } + erpc_free(argument); + + if (answer) + { + free_binary_t_struct(answer); + } + erpc_free(answer); + + return err; +} diff -r a89ed401fbc6 -r 1ffff67678ad C_runtime/erpc_PLCObject_server.hpp --- a/C_runtime/erpc_PLCObject_server.hpp Fri Oct 25 14:51:38 2024 +0200 +++ b/C_runtime/erpc_PLCObject_server.hpp Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ /* - * Generated by erpcgen 1.12.0 on Mon May 20 17:54:19 2024. + * Generated by erpcgen 1.12.0 on Mon Oct 28 15:10:14 2024. * * AUTOGENERATED - DO NOT EDIT */ @@ -80,6 +80,9 @@ /*! @brief Server shim for StopPLC of BeremizPLCObjectService interface. */ erpc_status_t StopPLC_shim(erpc::Codec * codec, erpc::MessageBufferFactory *messageFactory, erpc::Transport * transport, uint32_t sequence); + + /*! @brief Server shim for ExtendedCall of BeremizPLCObjectService interface. */ + erpc_status_t ExtendedCall_shim(erpc::Codec * codec, erpc::MessageBufferFactory *messageFactory, erpc::Transport * transport, uint32_t sequence); }; } // erpcShim diff -r a89ed401fbc6 -r 1ffff67678ad ProjectController.py --- a/ProjectController.py Fri Oct 25 14:51:38 2024 +0200 +++ b/ProjectController.py Mon Oct 28 16:02:47 2024 +0100 @@ -1919,6 +1919,9 @@ # Oups. self.logger.write_error(_("Connection failed to %s!\n") % uri) else: + VersionsInfoBytes = self._connector.ExtendedCall("GetVersions", bytes()) + VersionsInfo = VersionsInfoBytes.decode() + self.logger.write(f"Version string: {VersionsInfo}\n") self.CompareLocalAndRemotePLC() # Init with actual PLC status and print it diff -r a89ed401fbc6 -r 1ffff67678ad connectors/ERPC/__init__.py --- a/connectors/ERPC/__init__.py Fri Oct 25 14:51:38 2024 +0200 +++ b/connectors/ERPC/__init__.py Mon Oct 28 16:02:47 2024 +0100 @@ -61,6 +61,7 @@ "SeedBlob":ReturnAsLastOutput, "SetTraceVariablesList": ReturnAsLastOutput, "StopPLC":ReturnAsLastOutput, + "ExtendedCall":ReturnAsLastOutput, } ArgsWrappers = { diff -r a89ed401fbc6 -r 1ffff67678ad erpc_interface/__init__.py --- a/erpc_interface/__init__.py Fri Oct 25 14:51:38 2024 +0200 +++ b/erpc_interface/__init__.py Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ # -# Generated by erpcgen 1.12.0 on Mon May 20 17:53:37 2024. +# Generated by erpcgen 1.12.0 on Mon Oct 28 11:30:03 2024. # # AUTOGENERATED - DO NOT EDIT # diff -r a89ed401fbc6 -r 1ffff67678ad erpc_interface/erpc_PLCObject.erpc --- a/erpc_interface/erpc_PLCObject.erpc Fri Oct 25 14:51:38 2024 +0200 +++ b/erpc_interface/erpc_PLCObject.erpc Mon Oct 28 16:02:47 2024 +0100 @@ -61,11 +61,11 @@ MatchMD5(in string MD5, out bool match) -> uint32 NewPLC(in string md5sum, in binary plcObjectBlobID, in list extrafiles, out bool success) -> uint32 PurgeBlobs() -> uint32 - /* NOT TO DO : RemoteExec(in ) -> uint32 */ RepairPLC() -> uint32 ResetLogCount() -> uint32 SeedBlob(in binary seed, out binary blobID) -> uint32 SetTraceVariablesList(in list orders, out int32 debugtoken) -> uint32 StartPLC() -> uint32 StopPLC(out bool success) -> uint32 + ExtendedCall(in string method, in binary argument, out binary answer ) -> uint32 } diff -r a89ed401fbc6 -r 1ffff67678ad erpc_interface/erpc_PLCObject/__init__.py --- a/erpc_interface/erpc_PLCObject/__init__.py Fri Oct 25 14:51:38 2024 +0200 +++ b/erpc_interface/erpc_PLCObject/__init__.py Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ # -# Generated by erpcgen 1.12.0 on Mon May 20 17:53:37 2024. +# Generated by erpcgen 1.12.0 on Mon Oct 28 11:30:03 2024. # # AUTOGENERATED - DO NOT EDIT # diff -r a89ed401fbc6 -r 1ffff67678ad erpc_interface/erpc_PLCObject/client.py --- a/erpc_interface/erpc_PLCObject/client.py Fri Oct 25 14:51:38 2024 +0200 +++ b/erpc_interface/erpc_PLCObject/client.py Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ # -# Generated by erpcgen 1.12.0 on Mon May 20 17:53:37 2024. +# Generated by erpcgen 1.12.0 on Mon Oct 28 11:30:03 2024. # # AUTOGENERATED - DO NOT EDIT # @@ -292,4 +292,28 @@ _result = codec.read_uint32() return _result - + def ExtendedCall(self, method, argument, answer): + assert type(answer) is erpc.Reference, "out parameter must be a Reference object" + + # Build remote function invocation message. + request = self._clientManager.create_request() + codec = request.codec + codec.start_write_message(erpc.codec.MessageInfo( + type=erpc.codec.MessageType.kInvocationMessage, + service=self.SERVICE_ID, + request=self.EXTENDEDCALL_ID, + sequence=request.sequence)) + if method is None: + raise ValueError("method is None") + codec.write_string(method) + if argument is None: + raise ValueError("argument is None") + codec.write_binary(argument) + + # Send request and process reply. + self._clientManager.perform_request(request) + answer.value = codec.read_binary() + _result = codec.read_uint32() + return _result + + diff -r a89ed401fbc6 -r 1ffff67678ad erpc_interface/erpc_PLCObject/common.py --- a/erpc_interface/erpc_PLCObject/common.py Fri Oct 25 14:51:38 2024 +0200 +++ b/erpc_interface/erpc_PLCObject/common.py Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ # -# Generated by erpcgen 1.12.0 on Mon May 20 17:53:37 2024. +# Generated by erpcgen 1.12.0 on Mon Oct 28 11:30:03 2024. # # AUTOGENERATED - DO NOT EDIT # diff -r a89ed401fbc6 -r 1ffff67678ad erpc_interface/erpc_PLCObject/interface.py --- a/erpc_interface/erpc_PLCObject/interface.py Fri Oct 25 14:51:38 2024 +0200 +++ b/erpc_interface/erpc_PLCObject/interface.py Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ # -# Generated by erpcgen 1.12.0 on Mon May 20 17:53:37 2024. +# Generated by erpcgen 1.12.0 on Mon Oct 28 11:30:03 2024. # # AUTOGENERATED - DO NOT EDIT # @@ -21,6 +21,7 @@ SETTRACEVARIABLESLIST_ID = 12 STARTPLC_ID = 13 STOPPLC_ID = 14 + EXTENDEDCALL_ID = 15 def AppendChunkToBlob(self, data, blobID, newBlobID): raise NotImplementedError() @@ -64,4 +65,7 @@ def StopPLC(self, success): raise NotImplementedError() + def ExtendedCall(self, method, argument, answer): + raise NotImplementedError() + diff -r a89ed401fbc6 -r 1ffff67678ad erpc_interface/erpc_PLCObject/server.py --- a/erpc_interface/erpc_PLCObject/server.py Fri Oct 25 14:51:38 2024 +0200 +++ b/erpc_interface/erpc_PLCObject/server.py Mon Oct 28 16:02:47 2024 +0100 @@ -1,5 +1,5 @@ # -# Generated by erpcgen 1.12.0 on Mon May 20 17:53:37 2024. +# Generated by erpcgen 1.12.0 on Mon Oct 28 11:30:03 2024. # # AUTOGENERATED - DO NOT EDIT # @@ -27,6 +27,7 @@ interface.IBeremizPLCObjectService.SETTRACEVARIABLESLIST_ID: self._handle_SetTraceVariablesList, interface.IBeremizPLCObjectService.STARTPLC_ID: self._handle_StartPLC, interface.IBeremizPLCObjectService.STOPPLC_ID: self._handle_StopPLC, + interface.IBeremizPLCObjectService.EXTENDEDCALL_ID: self._handle_ExtendedCall, } def _handle_AppendChunkToBlob(self, sequence, codec): @@ -348,4 +349,29 @@ codec.write_bool(success.value) codec.write_uint32(_result) - + def _handle_ExtendedCall(self, sequence, codec): + # Create reference objects to pass into handler for out/inout parameters. + answer = erpc.Reference() + + # Read incoming parameters. + method = codec.read_string() + argument = codec.read_binary() + + # Invoke user implementation of remote function. + _result = self._handler.ExtendedCall(method, argument, answer) + + # Prepare codec for reply message. + codec.reset() + + # Construct reply message. + codec.start_write_message(erpc.codec.MessageInfo( + type=erpc.codec.MessageType.kReplyMessage, + service=interface.IBeremizPLCObjectService.SERVICE_ID, + request=interface.IBeremizPLCObjectService.EXTENDEDCALL_ID, + sequence=sequence)) + if answer.value is None: + raise ValueError("answer.value is None") + codec.write_binary(answer.value) + codec.write_uint32(_result) + + diff -r a89ed401fbc6 -r 1ffff67678ad runtime/PLCObject.py --- a/runtime/PLCObject.py Fri Oct 25 14:51:38 2024 +0200 +++ b/runtime/PLCObject.py Mon Oct 28 16:02:47 2024 +0100 @@ -103,6 +103,9 @@ self.PlcStopped.set() self._init_blobs() + + # initialize extended calls with GetVersions call, ignoring arguments + self.extended_calls = {"GetVersions":lambda *_args:self.GetVersions().encode()} # First task of worker -> no @RunInMain def AutoLoad(self, autostart): @@ -818,16 +821,17 @@ self.TraceThread = None - def RemoteExec(self, script, *kwargs): - try: - exec(script, kwargs) - except Exception: - _e_type, e_value, e_traceback = sys.exc_info() - line_no = traceback.tb_lineno(get_last_traceback(e_traceback)) - return (-1, "RemoteExec script failed!\n\nLine %d: %s\n\t%s" % - (line_no, e_value, script.splitlines()[line_no - 1])) - return (0, kwargs.get("returnVal", None)) - def GetVersions(self): return platform_module.system() + " " + platform_module.release() + @RunInMain + def ExtendedCall(self, method, argument): + """ Dispatch argument to registered service """ + return self.extended_calls[method](argument) + + def RegisterExtendedCall(method, callback): + self.extended_calls[method] = callback + + def UnregisterExtendedCall(method): + del self.extended_calls[method] + diff -r a89ed401fbc6 -r 1ffff67678ad runtime/eRPCServer.py --- a/runtime/eRPCServer.py Fri Oct 25 14:51:38 2024 +0200 +++ b/runtime/eRPCServer.py Mon Oct 28 16:02:47 2024 +0100 @@ -47,6 +47,7 @@ "SeedBlob":ReturnAsLastOutput, "SetTraceVariablesList": ReturnAsLastOutput, "StopPLC":ReturnAsLastOutput, + "ExtendedCall":ReturnAsLastOutput, } ArgsWrappers = {