ua_session.c 5.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144
  1. #include "ua_session.h"
  2. #include "ua_util.h"
  3. #include "ua_statuscodes.h"
  4. #ifdef UA_MULTITHREADING
  5. #include <urcu/uatomic.h>
  6. #endif
  7. UA_Session anonymousSession = {
  8. .clientDescription = {.applicationUri = {-1, UA_NULL},
  9. .productUri = {-1, UA_NULL},
  10. .applicationName = {.locale = {-1, UA_NULL}, .text = {-1, UA_NULL}},
  11. .applicationType = UA_APPLICATIONTYPE_CLIENT,
  12. .gatewayServerUri = {-1, UA_NULL},
  13. .discoveryProfileUri = {-1, UA_NULL},
  14. .discoveryUrlsSize = -1,
  15. .discoveryUrls = UA_NULL},
  16. .sessionName = {sizeof("Anonymous Session")-1, (UA_Byte*)"Anonymous Session"},
  17. .authenticationToken = {.namespaceIndex = 0, .identifierType = UA_NODEIDTYPE_NUMERIC, .identifier.numeric = 0}, // is never used, as this session is not stored in the sessionmanager
  18. .sessionId = {.namespaceIndex = 0, .identifierType = UA_NODEIDTYPE_NUMERIC, .identifier.numeric = 0},
  19. .maxRequestMessageSize = UA_UINT32_MAX,
  20. .maxResponseMessageSize = UA_UINT32_MAX,
  21. .timeout = UA_INT64_MAX,
  22. .validTill = UA_INT64_MAX,
  23. .channel = UA_NULL};
  24. UA_Session adminSession = {
  25. .clientDescription = {.applicationUri = {-1, UA_NULL},
  26. .productUri = {-1, UA_NULL},
  27. .applicationName = {.locale = {-1, UA_NULL}, .text = {-1, UA_NULL}},
  28. .applicationType = UA_APPLICATIONTYPE_CLIENT,
  29. .gatewayServerUri = {-1, UA_NULL},
  30. .discoveryProfileUri = {-1, UA_NULL},
  31. .discoveryUrlsSize = -1,
  32. .discoveryUrls = UA_NULL},
  33. .sessionName = {sizeof("Administrator Session")-1, (UA_Byte*)"Administrator Session"},
  34. .authenticationToken = {.namespaceIndex = 0, .identifierType = UA_NODEIDTYPE_NUMERIC, .identifier.numeric = 1}, // is never used, as this session is not stored in the sessionmanager
  35. .sessionId = {.namespaceIndex = 0, .identifierType = UA_NODEIDTYPE_NUMERIC, .identifier.numeric = 1},
  36. .maxRequestMessageSize = UA_UINT32_MAX,
  37. .maxResponseMessageSize = UA_UINT32_MAX,
  38. .timeout = UA_INT64_MAX,
  39. .validTill = UA_INT64_MAX,
  40. .channel = UA_NULL};
  41. UA_Session * UA_Session_new(void) {
  42. UA_Session *s = UA_malloc(sizeof(UA_Session));
  43. if(s) UA_Session_init(s);
  44. return s;
  45. }
  46. /* TODO: Nobody seems to call this function right now */
  47. static UA_StatusCode UA_Session_generateToken(UA_NodeId *newToken, UA_UInt32 *seed) {
  48. newToken->namespaceIndex = 0; // where else?
  49. newToken->identifierType = UA_NODEIDTYPE_GUID;
  50. newToken->identifier.guid = UA_Guid_random(seed);
  51. return UA_STATUSCODE_GOOD;
  52. }
  53. void UA_Session_init(UA_Session *session) {
  54. if(!session) return;
  55. UA_ApplicationDescription_init(&session->clientDescription);
  56. UA_NodeId_init(&session->authenticationToken);
  57. UA_NodeId_init(&session->sessionId);
  58. UA_String_init(&session->sessionName);
  59. session->maxRequestMessageSize = 0;
  60. session->maxResponseMessageSize = 0;
  61. session->timeout = 0;
  62. UA_DateTime_init(&session->validTill);
  63. session->channel = UA_NULL;
  64. }
  65. void UA_Session_deleteMembers(UA_Session *session) {
  66. UA_ApplicationDescription_deleteMembers(&session->clientDescription);
  67. UA_NodeId_deleteMembers(&session->authenticationToken);
  68. UA_NodeId_deleteMembers(&session->sessionId);
  69. UA_String_deleteMembers(&session->sessionName);
  70. session->channel = UA_NULL;
  71. }
  72. void UA_Session_delete(UA_Session *session) {
  73. UA_Session_deleteMembers(session);
  74. UA_free(session);
  75. }
  76. UA_Boolean UA_Session_compare(UA_Session *session1, UA_Session *session2) {
  77. if(session1 && session2 && UA_NodeId_equal(&session1->sessionId, &session2->sessionId))
  78. return UA_TRUE;
  79. return UA_FALSE;
  80. }
  81. UA_StatusCode UA_Session_setExpirationDate(UA_Session *session) {
  82. if(!session)
  83. return UA_STATUSCODE_BADINTERNALERROR;
  84. session->validTill = UA_DateTime_now() + session->timeout * 100000; //timeout in ms
  85. return UA_STATUSCODE_GOOD;
  86. }
  87. UA_StatusCode UA_Session_getPendingLifetime(UA_Session *session, UA_Double *pendingLifetime_ms) {
  88. if(!session)
  89. return UA_STATUSCODE_BADINTERNALERROR;
  90. *pendingLifetime_ms = (session->validTill - UA_DateTime_now())/10000000; //difference in ms
  91. return UA_STATUSCODE_GOOD;
  92. }
  93. void UA_SecureChannel_detachSession(UA_SecureChannel *channel) {
  94. #ifdef UA_MULTITHREADING
  95. UA_Session *session = channel->session;
  96. if(session)
  97. uatomic_cmpxchg(&session->channel, channel, UA_NULL);
  98. uatomic_set(&channel->session, UA_NULL);
  99. #else
  100. if(channel->session)
  101. channel->session->channel = UA_NULL;
  102. channel->session = UA_NULL;
  103. #endif
  104. }
  105. void UA_SecureChannel_attachSession(UA_SecureChannel *channel, UA_Session *session) {
  106. #ifdef UA_MULTITHREADING
  107. if(uatomic_cmpxchg(&session->channel, UA_NULL, channel) == UA_NULL)
  108. uatomic_set(&channel->session, session);
  109. #else
  110. if(session->channel != UA_NULL)
  111. return;
  112. session->channel = channel;
  113. channel->session = session;
  114. #endif
  115. }
  116. void UA_Session_detachSecureChannel(UA_Session *session) {
  117. #ifdef UA_MULTITHREADING
  118. UA_SecureChannel *channel = session->channel;
  119. if(channel)
  120. uatomic_cmpxchg(&channel->session, session, UA_NULL);
  121. uatomic_set(&session->channel, UA_NULL);
  122. #else
  123. if(session->channel)
  124. session->channel->session = UA_NULL;
  125. session->channel = UA_NULL;
  126. #endif
  127. }