Przeglądaj źródła

Common service create added,
CipCallback added in class struct

micsat 4 lat temu
rodzic
commit
c129f55c7b
3 zmienionych plików z 82 dodań i 0 usunięć
  1. 39 0
      source/src/cip/cipcommon.c
  2. 21 0
      source/src/cip/cipcommon.h
  3. 22 0
      source/src/cip/ciptypes.h

+ 39 - 0
source/src/cip/cipcommon.c

@@ -1264,6 +1264,45 @@ int DecodePaddedEPath(CipEpath *epath,
   return number_of_decoded_elements * 2 + 1; /* number_of_decoded_elements times 2 as every encoding uses 2 bytes */
 }
 
+EipStatus Create(CipInstance *RESTRICT const instance,
+                             CipMessageRouterRequest *const message_router_request,
+                             CipMessageRouterResponse *const message_router_response,
+                             const struct sockaddr *originator_address,
+                             const int encapsulation_session) {
+
+  InitializeENIPMessage(&message_router_response->message);
+  message_router_response->reply_service =
+      (0x80 | message_router_request->service);
+  message_router_response->general_status = kCipErrorSuccess;
+  message_router_response->size_of_additional_status = 0;
+
+  CipClass *class = GetCipClass(message_router_request->request_path.class_id);
+
+  EipStatus internal_state = kEipStatusOk;
+
+  /* Call the PreCreateCallback if the class provides one. */
+  if( NULL != class->PreCreateCallback) {
+    internal_state = class->PreCreateCallback(instance, message_router_request, message_router_response);
+  }
+
+  if (kEipStatusOk == internal_state) {
+    CipInstance *new_instance = AddCipInstances(class, 1); /* add 1 instance to class*/
+    // TODO: handle possible error of "AddCipInstances", instance!=0
+
+    /* Call the PostSetCallback if the class provides one. */
+    if (NULL != class->PostSetCallback) {
+      class->PostSetCallback(new_instance, message_router_request,
+                             message_router_response);
+    }
+    OPENER_TRACE_INFO("Instance number %d created\n",
+                      new_instance->instance_number);
+  }
+  return kEipStatusOkSend;
+}
+
+
+//TODO: add delete service
+
 void AllocateAttributeMasks(CipClass *target_class) {
   unsigned size = 1 + CalculateIndex(target_class->highest_attribute_number);
   OPENER_TRACE_INFO(

+ 21 - 0
source/src/cip/cipcommon.h

@@ -145,4 +145,25 @@ EipStatus SetAttributeList(CipInstance *instance,
 int DecodePaddedEPath(CipEpath *epath,
                       const EipUint8 **message);
 
+/** @brief Generic implementation of the Create CIP service
+ *
+ *  Creates dynamically allocated object instance within the specified class.
+ *
+ * @param instance pointer to instance.
+ * @param message_router_request pointer to request.
+ * @param message_router_response pointer to response.
+ * @param originator_address address struct of the originator as received
+ * @param encapsulation_session associated encapsulation session of the explicit message
+ * @return status  >0 .. success
+ *          -1 .. requested attribute not set
+ */
+EipStatus Create(
+    CipInstance *RESTRICT const instance,
+    CipMessageRouterRequest *const
+        message_router_request,
+    CipMessageRouterResponse *const
+        message_router_response,
+    const struct sockaddr *originator_address,
+    const int encapsulation_session);
+
 #endif /* OPENER_CIPCOMMON_H_ */

+ 22 - 0
source/src/cip/ciptypes.h

@@ -333,6 +333,23 @@ typedef EipStatus (*CipGetSetCallback)(CipInstance *const instance,
                                        CipAttributeStruct *const attribute,
                                        CipByte service);
 
+/** @ingroup CIP_API
+ *  @typedef EipStatus (*CipCallback)(
+ *    CipInstance *const instance,
+ *    CipMessageRouterRequest *message_router_request,
+ *    CipMessageRouterResponse *message_router_response
+ *  )
+ *  @brief Signature definition of callback functions for CIP services
+ *
+ *  @param  instance  CIP instance involved in common services
+ *  @param  message_router_request pointer to request.
+ *  @param  message_router_response pointer to response.
+ *  @return           status of kEipStatusOk or kEipStatusError on failure
+ */
+typedef EipStatus (*CipCallback)(CipInstance *const instance,
+                const CipMessageRouterRequest *const message_router_request,
+		CipMessageRouterResponse *const message_router_response);
+
 /** @brief Type definition of CipClass that is a subclass of CipInstance */
 typedef struct cip_class {
   CipInstance class_instance;   /**< This is the instance that contains the
@@ -365,6 +382,11 @@ typedef struct cip_class {
   /** Is called in SetAttributeSingle* after the received data was set
    * in the object's attributes. */
   CipGetSetCallback PostSetCallback;
+
+  /** Is called in Create before the instance is created. */
+  CipCallback PreCreateCallback;
+  /** Is called in Create after the instance has been created. */
+  CipCallback PostCreateCallback;
 } CipClass;
 
 /** @ingroup CIP_API