+typedef struct cb_info {
+ const CMPIContext *context;
+ const CMPIObjectPath *obj_path;
+} *cb_info_ptr;
+
+static const CMPIBroker *_BROKER;
+
+#define CAI_NUM_PLATFORMS 3
+enum CAI_PLATFORMS {CAI_XEN,
+ CAI_KVM,
+ CAI_LXC,
+};
+static int active_filters[CAI_NUM_PLATFORMS];
+
+static pthread_mutex_t cb_reg_mutex = PTHREAD_MUTEX_INITIALIZER;
+
+static void set_alert_ind_props(const CMPIBroker *broker,
+ const char *prefix,
+ const CMPIContext *ctx,
+ CMPIInstance *ind)
+{
+ CMPIStatus s;
+ CMPIString *str = NULL;
+ CMPIUint16 val;
+ CMPIArray *array = NULL;
+ char *charsptr = NULL;
+ int rc;
+
+
+ //CMSetProperty(ind, "Description", &str, CMPI_string);
+
+
+ // val 1
+ val = 1;
+ CMSetProperty(ind, "AlertType", &val, CMPI_uint16);
+
+ str = CMNewString(broker, "Virtual guest crash", &s);
+ CMSetProperty(ind, "OtherAlertType", &str, CMPI_string);
+
+ val = 7;
+ CMSetProperty(ind, "PerceivedSeverity", &val, CMPI_uint16);
+
+ // val 48
+ val = 48;
+ CMSetProperty(ind, "ProbableCause", &val, CMPI_uint16);
+
+ //CMSetProperty(ind, "ProbableCauseDescription", &str,
CMPI_string);
+
+ // val 1
+ val = 1;
+ CMSetProperty(ind, "Trending", &val, CMPI_uint16);
+
+ // This is an array
+ // CMSetProperty(ind, "RecommendedActions", &str, CMPI_string);
+
+
+ // Must find how to fill it
+ //CMSetProperty(ind, "EventTime", &, CMPI_dateTime);
+
+ // Won't use it
+ //CMSetProperty(ind, "SystemCreationClassName", &str,
CMPI_string);
+
+ // Won't use it
+ // CMSetProperty(ind, "SystemName", &str, CMPI_string);
+
+ // Combine GuestCrashAlertIndication with prefix
+ rc = asprintf(&charsptr, "%s%s", prefix,
"_GuestCrashAlertIndication");
Instead of hardcoding the name of the provider in two places, I would
have this function take a const char * argument and then pass in the value.
+ str = CMNewString(broker, charsptr, &s);
+ CMSetProperty(ind, "ProviderName", &str, CMPI_string);
+ free(charsptr);
+
+ str = CMNewString(broker, "DTMF", &s);
+ CMSetProperty(ind, "OwningEntity", &str, CMPI_string);
+
+ str = CMNewString(broker, "PLAT0002", &s);
+ CMSetProperty(ind, "MessageID", &str, CMPI_string);
+
+ //CMSetProperty(ind, "Message", &str, CMPI_string);
+
+ // This is an string array
+ array = CMNewArray(broker, 1, CMPI_stringA, &s);
+ str = CMNewString(broker,
+ "Virtual machine execution ended "
+ "unexpectly",
+ &s);
+ s = CMSetArrayElementAt(array, 0, &str, CMPI_string);
+ CMSetProperty(ind, "MessageArguments", &array, CMPI_string);
+}
+
+static CMPIStatus create_and_deliver_ind(const CMPIBroker *broker,
+ const CMPIContext *ctx,
+ struct ind_args *args)
+{
+ const char *ind_type_name = "GuestCrashAlertIndication";
You set the name of the provider here - so you can pass this to
set_alert_ind_props(). This keeps you from having to change the name in
multiple locations if the name changes.
+ CMPIObjectPath *ind_op;
+ CMPIInstance *ind;
+ CMPIStatus s;
+ char *prefix = NULL;
+
+ prefix = class_prefix_name(args->classname);
+
+ ind = get_typed_instance(broker,
+ prefix,
+ ind_type_name,
+ args->ns);
You shouldn't need to create another indication here. You've already
created one in guest_crashed_cb(). If you create a new one here, you
overwrite the one created in guest_crashed_cb(). You lose the values of
the attributes you set in guest_crashed_cb().
+
+ if (ind == NULL) {
+ cu_statusf(broker,
+ &s,
+ CMPI_RC_ERR_FAILED,
+ "Failed to create ind, type '%s:%s_%s'",
+ args->ns,
+ prefix,
+ ind_type_name);
+ goto out;
+ }
+
+ ind_op = CMGetObjectPath(ind, &s);
+ if (s.rc != CMPI_RC_OK) {
+ //CU_DEBUG("Failed to get ind_op. Error: '%s'",
s.msg);
+ goto out;
+ }
+ CMSetNameSpace(ind_op, args->ns);
+
+ set_alert_ind_props(broker, prefix, ctx, ind);
+
+ CU_DEBUG("Delivering Indication: %s",
+ CMGetCharPtr(CMObjectPathToString(ind_op, NULL)));
+
+ s = stdi_deliver(broker, ctx, args, ind);
+ if (s.rc == CMPI_RC_OK) {
+ CU_DEBUG("Indication delivered");
+ } else {
+ CU_DEBUG("Not delivered: %s", CMGetCharPtr(s.msg));
+ }
+
+ out:
+ free(prefix);
+
+ return s;
+}
+
+
+static void preset_alert_ind_props(CMPIInstance *ind, virDomainPtr dom)
+{
+ CMPIStatus s;
+ CMPIString *str = NULL;
+ char *dom_name = (char *)virDomainGetName(dom);
+ char *counter = NULL;
+
+ if (dom_name == NULL) {
+ CU_DEBUG("Could not retrieve name of guest responsible for "
+ "crash");
+ dom_name = "Guest name not available";
+ }
+
+ str = CMNewString(_BROKER, dom_name, &s);
+ CMSetProperty(ind, "AlertingManagedElement", &str, CMPI_string);
+
+ // This property must be unique, retrieve a counter from infostore
+ counter = inc_counter(dom);
It seems like you'd want to use a mutex around this call to ensure that
you're note reading from the info store as it's being written to.
That'll ensure that each indication gets its own value.
+ if (counter == NULL) {
+ CU_DEBUG("Could not retrieve counter");
+ } else {
+ str = CMNewString(_BROKER, counter, &s);
+ CMSetProperty(ind, "EventID", &str, CMPI_string);
+ free(counter);
+ }
+}
+
--
Kaitlin Rupert
IBM Linux Technology Center
kaitlin(a)linux.vnet.ibm.com