Przeglądaj źródła

stateless calls work again

Stasik0 9 lat temu
rodzic
commit
3d110a6720

+ 9 - 2
CMakeLists.txt

@@ -246,6 +246,9 @@ if(EXTENSION_UDP)
   endif()
 endif()
 
+option(LEGACY "Enable LEGACY code" OFF)
+mark_as_advanced(LEGACY)
+
 option(EXTENSION_STATELESS "Enable stateless extension" OFF)
 if(EXTENSION_STATELESS)
 	message(STATUS "Extensions: enabling stateless")
@@ -367,12 +370,16 @@ if(BUILD_EXAMPLECLIENT)
         target_link_libraries(client_static urcu-cds urcu urcu-common pthread)
         target_link_libraries(client urcu-cds urcu urcu-common pthread)
     endif()
-    if(EXTENSION_STATELESS)
+    if(EXTENSION_STATELESS AND NOT ENABLE_AMALGAMATION)
         add_executable(client_stateless examples/client_stateless.c ${client_source})
         if(ENABLE_MULTITHREADING)
             target_link_libraries(client_stateless urcu-cds urcu urcu-common pthread)
         endif()
     endif()
+    if(LEGACY AND NOT ENABLE_AMALGAMATION)
+    	add_executable(client_legacy ${PROJECT_SOURCE_DIR}/examples/client_legacy.c $<TARGET_OBJECTS:open62541-object>)
+		target_link_libraries(client_legacy ${LIBS})
+	endif()
 endif()
 
 # build unit tests
@@ -400,7 +407,7 @@ if(BUILD_EXAMPLES)
 	if(ENABLE_MULTITHREADING)
 		list(APPEND LIBS urcu-cds urcu urcu-common)
 	endif(ENABLE_MULTITHREADING)
-
+	
     add_executable(server_variable ${PROJECT_SOURCE_DIR}/examples/server_variable.c $<TARGET_OBJECTS:open62541-object>)
 	target_link_libraries(server_variable ${LIBS})
 

+ 47 - 22
examples/client_legacy.c

@@ -11,13 +11,10 @@
 #include <unistd.h> // for close
 #include <stdlib.h> // pulls in declaration of malloc, free
 
-#ifdef NOT_AMALGATED
-    #include "ua_transport_generated.h"
-    #include "ua_types_encoding_binary.h"
-    #include "ua_util.h"
-#else
-    #include "open62541.h"
-#endif
+//this legacy stuff can not be build with amalgamation options, since it need internal APIs
+#include "ua_util.h"
+#include "ua_transport_generated_encoding_binary.h"
+#include "ua_types_generated_encoding_binary.h"
 
 typedef struct ConnectionInfo {
 	UA_Int32 socket;
@@ -40,14 +37,17 @@ static UA_Int32 sendHello(UA_Int32 sock, UA_String *endpointURL) {
 	hello.receiveBufferSize = 65536;
 	hello.sendBufferSize = 65536;
 
-	messageHeader.messageSize = UA_TcpHelloMessage_calcSizeBinary((UA_TcpHelloMessage const*) &hello) +
-                                UA_TcpMessageHeader_calcSizeBinary((UA_TcpMessageHeader const*) &messageHeader);
 	UA_ByteString message;
-	UA_ByteString_newMembers(&message, messageHeader.messageSize);
+	UA_ByteString_newMembers(&message, 1024);
 
 	size_t offset = 0;
 	UA_TcpMessageHeader_encodeBinary((UA_TcpMessageHeader const*) &messageHeader, &message, &offset);
 	UA_TcpHelloMessage_encodeBinary((UA_TcpHelloMessage const*) &hello, &message, &offset);
+    messageHeader.messageSize = offset;
+
+	offset = 0;
+    UA_TcpMessageHeader_encodeBinary((UA_TcpMessageHeader const*) &messageHeader, &message, &offset);
+    UA_TcpHelloMessage_encodeBinary((UA_TcpHelloMessage const*) &hello, &message, &offset);
 
 	UA_Int32 sendret = send(sock, message.data, offset, 0);
 
@@ -112,7 +112,7 @@ static int sendOpenSecureChannel(UA_Int32 sock) {
 	UA_OpenSecureChannelRequest_encodeBinary(&opnSecRq, &message, &offset);
 
     UA_OpenSecureChannelRequest_deleteMembers(&opnSecRq);
-	UA_String_deleteMembers(&securityPolicy);
+	//UA_String_deleteMembers(&securityPolicy);
 
 	UA_Int32 sendret = send(sock, message.data, offset, 0);
 	UA_ByteString_deleteMembers(&message);
@@ -154,8 +154,13 @@ static UA_Int32 sendCreateSession(UA_Int32 sock, UA_UInt32 channelId, UA_UInt32
 	rq.requestedSessionTimeout = 1200000;
 	rq.maxResponseMessageSize = UA_INT32_MAX;
 
-	msghdr.messageSize = 16 + UA_TcpMessageHeader_calcSizeBinary(&msghdr) + UA_NodeId_calcSizeBinary(&type) +
-                         UA_CreateSessionRequest_calcSizeBinary(&rq);
+	//workaround to get length calculated
+	offset = 0;
+	UA_CreateSessionRequest_encodeBinary(&rq, &message, &offset);
+	UA_TcpMessageHeader_encodeBinary(&msghdr, &message, &offset);
+	UA_NodeId_encodeBinary(&type, &message, &offset);
+	msghdr.messageSize = 16 + offset;
+	offset = 0;
 
 	UA_TcpMessageHeader_encodeBinary(&msghdr, &message, &offset);
 	UA_UInt32_encodeBinary(&tmpChannelId, &message, &offset);
@@ -167,7 +172,8 @@ static UA_Int32 sendCreateSession(UA_Int32 sock, UA_UInt32 channelId, UA_UInt32
 
 	UA_Int32 sendret = send(sock, message.data, offset, 0);
 	UA_ByteString_deleteMembers(&message);
-	UA_CreateSessionRequest_deleteMembers(&rq);
+	//fixme: potential leak
+	//UA_CreateSessionRequest_deleteMembers(&rq);
 	if (sendret < 0) {
 		printf("send opensecurechannel failed");
 		return 1;
@@ -200,8 +206,13 @@ static UA_Int32 closeSession(ConnectionInfo *connectionInfo) {
 	type.identifierType = UA_NODEIDTYPE_NUMERIC;
 	type.namespaceIndex = 0;
 
-	msghdr.messageSize = 16 + UA_TcpMessageHeader_calcSizeBinary(&msghdr) + UA_NodeId_calcSizeBinary(&type) +
-                         UA_CloseSessionRequest_calcSizeBinary(&rq);
+    //workaround to get length calculated
+    offset = 0;
+    UA_CloseSessionRequest_encodeBinary(&rq, &message, &offset);
+    UA_TcpMessageHeader_encodeBinary(&msghdr, &message, &offset);
+    UA_NodeId_encodeBinary(&type, &message, &offset);
+    msghdr.messageSize = 16 + offset;
+    offset = 0;
 
 	UA_TcpMessageHeader_encodeBinary(&msghdr, &message, &offset);
 	UA_UInt32_encodeBinary(&connectionInfo->channelId, &message, &offset);
@@ -241,8 +252,12 @@ static UA_Int32 closeSecureChannel(ConnectionInfo *connectionInfo) {
 	UA_TcpMessageHeader msghdr;
 	msghdr.messageTypeAndFinal = UA_MESSAGETYPEANDFINAL_CLOF;
 
-	msghdr.messageSize = 4 + UA_TcpMessageHeader_calcSizeBinary(&msghdr) +
-                         UA_CloseSecureChannelRequest_calcSizeBinary(&rq);
+	//workaround to get length calculated
+	offset = 0;
+	UA_CloseSecureChannelRequest_encodeBinary(&rq, &message, &offset);
+	UA_TcpMessageHeader_encodeBinary(&msghdr, &message, &offset);
+	msghdr.messageSize = 4 + offset;
+	offset = 0;
 
 	UA_TcpMessageHeader_encodeBinary(&msghdr, &message, &offset);
 	UA_UInt32_encodeBinary(&connectionInfo->channelId, &message, &offset);
@@ -282,8 +297,13 @@ static UA_Int32 sendActivateSession(UA_Int32 sock, UA_UInt32 channelId, UA_UInt3
 	rq.requestHeader.timestamp = UA_DateTime_now();
 	rq.requestHeader.timeoutHint = 10000;
     
-	msghdr.messageSize  = 16 + UA_TcpMessageHeader_calcSizeBinary(&msghdr) + UA_NodeId_calcSizeBinary(&type) +
-                          UA_ActivateSessionRequest_calcSizeBinary(&rq);
+    //workaround to get length calculated
+    offset = 0;
+    UA_ActivateSessionRequest_encodeBinary(&rq, message, &offset);
+    UA_TcpMessageHeader_encodeBinary(&msghdr, message, &offset);
+    UA_NodeId_encodeBinary(&type, message, &offset);
+    msghdr.messageSize = 16 + offset;
+    offset = 0;
 
 	UA_TcpMessageHeader_encodeBinary(&msghdr, message, &offset);
 	UA_UInt32_encodeBinary(&tmpChannelId, message, &offset);
@@ -339,8 +359,13 @@ static UA_Int64 sendReadRequest(ConnectionInfo *connectionInfo, UA_Int32 nodeIds
 	rq.timestampsToReturn = 0x03;
 	rq.requestHeader.requestHandle = 1 + connectionInfo->sequenceHdr.requestId;
 
-	msghdr.messageSize = 16 + UA_TcpMessageHeader_calcSizeBinary(&msghdr) + UA_NodeId_calcSizeBinary(&type) +
-                         UA_ReadRequest_calcSizeBinary(&rq);
+    //workaround to get length calculated
+    offset = 0;
+    UA_ReadRequest_encodeBinary(&rq, message, &offset);
+    UA_TcpMessageHeader_encodeBinary(&msghdr, message, &offset);
+    UA_NodeId_encodeBinary(&type, message, &offset);
+    msghdr.messageSize = 16 + offset;
+    offset = 0;
 
 	UA_TcpMessageHeader_encodeBinary(&msghdr,message,&offset);
 	UA_UInt32_encodeBinary(&tmpChannelId, message, &offset);

+ 4 - 2
examples/client_stateless.c

@@ -8,9 +8,11 @@
 #include <unistd.h> // for close
 #include <stdlib.h> // pulls in declaration of malloc, free
 
+//this stuff can not be build with amalgamation options, since it need internal APIs
 #include "ua_util.h"
-#include "ua_types_encoding_binary.h"
-#include "ua_transport_generated.h"
+#include "ua_transport_generated_encoding_binary.h"
+#include "ua_types_generated_encoding_binary.h"
+
 
 int main(int argc , char *argv[])
 {

+ 11 - 7
src/server/ua_server_binary.c

@@ -157,6 +157,16 @@ static void invoke_service(UA_Server *server, UA_SecureChannel *channel, UA_UInt
     init_response_header(request, response);
     /* try to get the session from the securechannel first */
     UA_Session *session = UA_SecureChannel_getSession(channel, &request->authenticationToken);
+#ifdef EXTENSION_STATELESS
+    if(request->authenticationToken.namespaceIndex == 0
+            && request->authenticationToken.identifierType == UA_NODEIDTYPE_NUMERIC
+            && request->authenticationToken.identifier.numeric == 0
+    && (responseType->typeIndex == UA_TYPES_READRESPONSE
+            || responseType->typeIndex == UA_TYPES_WRITERESPONSE
+            || responseType->typeIndex == UA_TYPES_BROWSERESPONSE)
+    ){
+        session = &anonymousSession;
+#else
     if(!session || session->channel != channel) {
         response->serviceResult = UA_STATUSCODE_BADSESSIONIDINVALID;
     } else if(session->activated == UA_FALSE) {
@@ -165,6 +175,7 @@ static void invoke_service(UA_Server *server, UA_SecureChannel *channel, UA_UInt
         UA_SessionManager_removeSession(&server->sessionManager, server, &request->authenticationToken);
     } else {
         UA_Session_updateLifetime(session);
+#endif
         service(server, session, request, response);
     }
     UA_StatusCode retval = UA_SecureChannel_sendBinaryMessage(channel, requestId, response, responseType);
@@ -202,9 +213,6 @@ static void processMSG(UA_Connection *connection, UA_Server *server, const UA_By
         UA_SecureChannel_init(&anonymousChannel);
         anonymousChannel.connection = connection;
         clientChannel = &anonymousChannel;
-#ifdef EXTENSION_STATELESS
-        UA_SecureChannel_attachSession(&anonymousChannel, &anonymousSession);
-#endif
     }
 
     /* Read the security header */
@@ -374,10 +382,6 @@ static void processMSG(UA_Connection *connection, UA_Server *server, const UA_By
         UA_ServiceFault_init(&r);
         init_response_header(&p, &r.responseHeader);
         r.responseHeader.serviceResult = UA_STATUSCODE_BADSERVICEUNSUPPORTED;
-#ifdef EXTENSION_STATELESS
-        if(retval != UA_STATUSCODE_GOOD)
-            r.responseHeader.serviceResult = retval;
-#endif
         UA_SecureChannel_sendBinaryMessage(clientChannel, sequenceHeader.requestId, &r,
                                            &UA_TYPES[UA_TYPES_SERVICEFAULT]);
         UA_RequestHeader_deleteMembers(&p);

+ 8 - 10
src/server/ua_services_attribute.c

@@ -393,12 +393,11 @@ void Service_Read(UA_Server *server, UA_Session *session, const UA_ReadRequest *
 		/* expiry header */
 		UA_ExtensionObject additionalHeader;
 		UA_ExtensionObject_init(&additionalHeader);
+		additionalHeader.typeId = UA_TYPES[UA_TYPES_VARIANT].typeId;
 		additionalHeader.encoding = UA_EXTENSIONOBJECT_ENCODINGMASK_BODYISBYTESTRING;
 
 		UA_Variant variant;
 		UA_Variant_init(&variant);
-		variant.type = &UA_TYPES[UA_TYPES_DATETIME];
-		variant.arrayLength = request->nodesToReadSize;
 
 		UA_DateTime* expireArray = UA_NULL;
 		expireArray = UA_Array_new(&UA_TYPES[UA_TYPES_DATETIME], request->nodesToReadSize);
@@ -408,22 +407,21 @@ void Service_Read(UA_Server *server, UA_Session *session, const UA_ReadRequest *
 		for(UA_Int32 i = 0;i < response->resultsSize;i++) {
 			expireArray[i] = UA_DateTime_now() + 20 * 100 * 1000 * 1000;
 		}
+		UA_Variant_setArray(&variant, expireArray, request->nodesToReadSize, &UA_TYPES[UA_TYPES_DATETIME]);
+
 		size_t offset = 0;
-        UA_Connection *c = UA_NULL;
-        UA_SecureChannel *sc = session->channel;
-        if(!sc) {
-            response->responseHeader.serviceResult = UA_STATUSCODE_BADINTERNALERROR;
-            return;
-        }
 		UA_ByteString str;
-        UA_ByteString_newMembers(&str, c->remoteConf.maxMessageSize);
+        UA_ByteString_newMembers(&str, 65536);
 		UA_Variant_encodeBinary(&variant, &str, &offset);
+
+        UA_Array_delete(expireArray, &UA_TYPES[UA_TYPES_DATETIME], request->nodesToReadSize);
+
 		additionalHeader.body = str;
+		additionalHeader.body.length = offset;
 		response->responseHeader.additionalHeader = additionalHeader;
     }
 #endif
 }
-
 #define SETATTRIBUTE_IF_DATATYPE_IS(EXP_DT)                                                                             \
 /* The Userspace setAttribute expects the value being passed being the correct type and has no own means for checking   \
    We need to check for setAttribute if the dataType is correct                                                         \