Esempio n. 1
0
static int
sysev_evc_handler(sysevent_t *ev, void *cookie)
{
  char *name, *zonename, *oldstate, *newstate;
  nvlist_t *nvlist;
  nvpair_t *curr, *next;

  cookie = cookie; // SILENCE!

  if (sysevent_get_attr_list(ev, &nvlist) != 0) {
    // XXX Error
    return (1);
  }

  // loop through event nvpairs to get our interesting values
  curr = nvlist_next_nvpair(nvlist, NULL);
  while (curr != NULL) {
    // all fields we're interested in are strings
    if (nvpair_type(curr) == DATA_TYPE_STRING) {
      name = nvpair_name(curr);

      if (strcmp(name, ZONE_CB_NAME) == 0) {
        nvpair_value_string(curr, &zonename);
      } else if (strcmp(name, ZONE_CB_NEWSTATE) == 0) {
        nvpair_value_string(curr, &newstate);
      } else if (strcmp(name, ZONE_CB_OLDSTATE) == 0) {
        nvpair_value_string(curr, &oldstate);
      }
    }

    next = nvlist_next_nvpair(nvlist, curr);
    curr = next;
  }

  // if it is a boot into running we need to enable the gate
  if (strcmp(oldstate, ZONE_EVENT_READY) == 0 &&
      strcmp(newstate, ZONE_EVENT_RUNNING) == 0) {
    gate_attach(zonename);
  }

  // ignore multiple shutting_down -> shutting_down transitions
  if (strcmp(oldstate, newstate) != 0) {
    char zonebrand[MAXNAMELEN];

    // get brand for zone
    if (zone_get_brand(zonename, zonebrand, sizeof (zonebrand)) == Z_OK) {
      request_send_state_event(zonename, zonebrand, oldstate, newstate);
    } else {
      request_send_state_event(zonename, NULL, oldstate, newstate);
    }
  }

  return (0);
}
Esempio n. 2
0
static int
probe_event(sysevent_t *ev, void *arg)
{
	nvlist_t *nvl;
	uint32_t state;
	uint32_t version;
	ipmpstat_probe_state_t *psp = arg;

	if (strcmp(sysevent_get_subclass_name(ev), ESC_IPMP_PROBE_STATE) != 0)
		return (0);

	if (sysevent_get_attr_list(ev, &nvl) != 0) {
		warn("sysevent_get_attr_list failed; dropping event");
		return (0);
	}

	if (nvlist_lookup_uint32(nvl, IPMP_EVENT_VERSION, &version) != 0) {
		warn("dropped event with no IPMP_EVENT_VERSION\n");
		goto out;
	}

	if (version != IPMP_EVENT_CUR_VERSION) {
		warn("dropped event with unsupported IPMP_EVENT_VERSION %d\n",
		    version);
		goto out;
	}

	if (nvlist_lookup_uint32(nvl, IPMP_PROBE_STATE, &state) != 0) {
		warn("dropped event with no IPMP_PROBE_STATE\n");
		goto out;
	}

	if (state == IPMP_PROBE_ACKED || state == IPMP_PROBE_LOST)
		ofmt_output(psp->ps_ofmt, psp->ps_ih, nvl);
out:
	nvlist_free(nvl);
	return (0);
}
Esempio n. 3
0
/* Calls the client callback function, if one is registered */
static void
notifyClient(sysevent_t *ev)
{
	nvlist_t *attr_list = NULL;

	uint64_t *val = NULL;
	int32_t  *instance = NULL;
	int32_t  *major = NULL;

	int valAllocated = 0;

	uint_t nelem = 0;

	int i = 0;
	int eventType = 0;
	int index = -1;

	void *pCallerData = NULL;

	char subClassName[256];

	MP_BOOL becomingVisible = MP_FALSE;

	MP_OID_LIST *oidList = NULL;


	log(LOG_INFO, "notifyClient()", "- enter");


	(void) strncpy(subClassName, sysevent_get_subclass_name(ev), 256);

	if (strstr(subClassName, "change")) {

		eventType = PROP_CHANGE;

		log(LOG_INFO, "notifyClient()", "- got a change event");
		log(LOG_INFO, "notifyClient()", ": [%s]",
		    subClassName);

		if (strncmp(subClassName, ESC_SUN_MP_PLUGIN_CHANGE, 255)
		    == 0) {

			index = MP_OBJECT_TYPE_PLUGIN;

		} else if (strncmp(subClassName, ESC_SUN_MP_LU_CHANGE, 255)
		    == 0) {

			index = MP_OBJECT_TYPE_MULTIPATH_LU;

		} else if (strncmp(subClassName, ESC_SUN_MP_PATH_CHANGE, 255)
		    == 0) {

			index = MP_OBJECT_TYPE_PATH_LU;

		} else if (strncmp(subClassName, ESC_SUN_MP_INIT_PORT_CHANGE,
		    255) == 0) {

			index = MP_OBJECT_TYPE_INITIATOR_PORT;

		} else if (strncmp(subClassName, ESC_SUN_MP_TPG_CHANGE, 255)
		    == 0) {

			index = MP_OBJECT_TYPE_TARGET_PORT_GROUP;

		} else if (strncmp(subClassName, ESC_SUN_MP_TARGET_PORT_CHANGE,
		    255) == 0) {

			index = MP_OBJECT_TYPE_TARGET_PORT;

		} else if (strncmp(subClassName, ESC_SUN_MP_DEV_PROD_CHANGE,
		    255) == 0) {

			index = MP_OBJECT_TYPE_DEVICE_PRODUCT;
		}

	} else if ((strstr(subClassName, "add")) ||
	    (strstr(subClassName, "initiator_register"))) {

		eventType = VISA_CHANGE;
		becomingVisible = MP_TRUE;

		log(LOG_INFO, "notifyClient()", "- got a visibility"
		    " add event");
		log(LOG_INFO, "notifyClient()", ": [%s]",
		    subClassName);

		if (strncmp(subClassName, ESC_SUN_MP_LU_ADD, 255) == 0) {

			index = MP_OBJECT_TYPE_MULTIPATH_LU;

		} else if (strncmp(subClassName, ESC_SUN_MP_PATH_ADD, 255)
		    == 0) {

			index = MP_OBJECT_TYPE_PATH_LU;

		} else if (strncmp(subClassName, ESC_DDI_INITIATOR_REGISTER,
		    244) == 0) {

			index = MP_OBJECT_TYPE_INITIATOR_PORT;

		} else if (strncmp(subClassName, ESC_SUN_MP_TPG_ADD,
		    255) == 0) {

			index = MP_OBJECT_TYPE_TARGET_PORT_GROUP;

		} else if (strncmp(subClassName, ESC_SUN_MP_TARGET_PORT_ADD,
		    255) == 0) {

			index = MP_OBJECT_TYPE_TARGET_PORT;

		} else if (strncmp(subClassName, ESC_SUN_MP_DEV_PROD_ADD, 255)
		    == 0) {

			index = MP_OBJECT_TYPE_DEVICE_PRODUCT;
		}


	} else if ((strstr(subClassName, "remove")) ||
	    (strstr(subClassName, "initiator_unregister"))) {

		eventType = VISA_CHANGE;
		becomingVisible = MP_FALSE;

		log(LOG_INFO, "notifyClient()", "- got a visibility"
		    " remove event");
		log(LOG_INFO, "notifyClient()", ": [%s]",
		    subClassName);

		if (strncmp(subClassName, ESC_SUN_MP_LU_REMOVE, 255) == 0) {

			index = MP_OBJECT_TYPE_MULTIPATH_LU;

		} else if (strncmp(subClassName, ESC_SUN_MP_PATH_REMOVE, 255)
		    == 0) {

			index = MP_OBJECT_TYPE_PATH_LU;

		} else if (strncmp(subClassName, ESC_DDI_INITIATOR_UNREGISTER,
		    255) == 0) {

			index = MP_OBJECT_TYPE_INITIATOR_PORT;

		} else if (strncmp(subClassName, ESC_SUN_MP_TPG_REMOVE, 255)
		    == 0) {

			index = MP_OBJECT_TYPE_TARGET_PORT_GROUP;

		} else if (strncmp(subClassName, ESC_SUN_MP_TARGET_PORT_REMOVE,
		    255) == 0) {

			index = MP_OBJECT_TYPE_TARGET_PORT;

		} else if (strncmp(subClassName, ESC_SUN_MP_DEV_PROD_REMOVE,
		    255) == 0) {

			index = MP_OBJECT_TYPE_DEVICE_PRODUCT;
		}


	} else {
		log(LOG_INFO, "notifyClient()", "- got an unsupported event");
		return;
	}

	if (index < 0) {

		log(LOG_INFO, "notifyClient()", "- index is less than zero");
		return;
	}

	if (eventType == VISA_CHANGE) {

		(void) pthread_mutex_lock(&g_visa_mutex);

		if (NULL == g_Visibility_Callback_List[index].pClientFn) {

			log(LOG_INFO, "notifyClient()",
			    "- no visibility change callback to notify");

			(void) pthread_mutex_unlock(&g_visa_mutex);

			return;
		}

		(void) pthread_mutex_unlock(&g_visa_mutex);
	}

	if (eventType == PROP_CHANGE) {

		(void) pthread_mutex_lock(&g_prop_mutex);

		if (NULL == g_Property_Callback_List[index].pClientFn) {

			log(LOG_INFO, "notifyClient()",
			    "- no property change callback to notify");

			(void) pthread_mutex_unlock(&g_prop_mutex);

			return;
		}

		(void) pthread_mutex_unlock(&g_prop_mutex);
	}

	(void) sysevent_get_attr_list(ev, &attr_list);
	if (NULL != attr_list) {

		if ((VISA_CHANGE == eventType) &&
		    (MP_OBJECT_TYPE_PLUGIN == index)) {

			val = (uint64_t *)malloc(sizeof (uint64_t));
			valAllocated = 1;

			/*
			 * We have no well-defined way to determine our OSN.
			 * Currently the common library uses 0 as OSN for every
			 * plugin, so just use 0. If the OSN assigned by the
			 * common library changed, this code would have to be
			 * updated.
			 */
			*val = 0;
			nelem = 1;

		} else if ((VISA_CHANGE == eventType) &&
		    (MP_OBJECT_TYPE_INITIATOR_PORT == index)) {

			(void) nvlist_lookup_int32_array(attr_list,
			    DDI_INSTANCE, &instance, &nelem);

			log(LOG_INFO, "notifyClient()",
			    "- event (PHCI_INSTANCE) has [%d] elements",
			    nelem);

			(void) nvlist_lookup_int32_array(attr_list,
			    DDI_DRIVER_MAJOR, &major, &nelem);

			log(LOG_INFO, "notifyClient()",
			    "- event (PHCI_DRIVER_MAJOR) has [%d] elements",
			    nelem);

			if ((NULL != instance) & (NULL != major)) {

				val = (uint64_t *)malloc(sizeof (uint64_t));

				valAllocated = 1;

				*val = 0;
				*val = MP_STORE_INST_TO_ID(*instance, *val);
				*val = MP_STORE_MAJOR_TO_ID(*major, *val);

				nelem = 1;

			} else {

				nelem = 0;
			}

		} else {

			(void) nvlist_lookup_uint64_array(attr_list, OIDLIST,
			    &val, &nelem);

			log(LOG_INFO, "notifyClient()",
			    "- event has [%d] elements",
			    nelem);
		}

		if (nelem > 0) {

			for (i = 0; i < nelem; i++) {

				log(LOG_INFO, "notifyClient()",
				    "- event [%d] = %llx",
				    i, val[i]);
			}

			oidList = createOidList(nelem);
			if (NULL == oidList) {

				log(LOG_INFO, "notifyClient()",
				    "- unable to create MP_OID_LIST");

				log(LOG_INFO, "notifyClient()",
				    "- error exit");

				nvlist_free(attr_list);

				return;
			}

			oidList->oidCount = nelem;

			for (i = 0; i < nelem; i++) {

				oidList->oids[i].objectType = index;
				oidList->oids[i].ownerId = g_pluginOwnerID;
				oidList->oids[i].objectSequenceNumber = val[i];
			}

			if (valAllocated) {

				free(val);
			}

			for (i = 0; i < oidList->oidCount; i++) {

				log(LOG_INFO, "notifyClient()",
				    "oidList->oids[%d].objectType"
				    "           = %d",
				    i, oidList->oids[i].objectType);
				log(LOG_INFO, "notifyClient()",
				    "oidList->oids[%d].ownerId"
				    "              = %d",
				    i, oidList->oids[i].ownerId);
				log(LOG_INFO, "notifyClient()",
				    "oidList->oids[%d].objectSequenceNumber"
				    " = %llx",
				    i, oidList->oids[i].objectSequenceNumber);
			}

			if (eventType == PROP_CHANGE) {

				(void) pthread_mutex_lock(&g_prop_mutex);

				pCallerData = g_Property_Callback_List[index].
				    pCallerData;

				(g_Property_Callback_List[index].pClientFn)
				    (oidList, pCallerData);

				(void) pthread_mutex_unlock(&g_prop_mutex);

			} else if (eventType == VISA_CHANGE) {

				(void) pthread_mutex_lock(&g_visa_mutex);

				pCallerData = g_Visibility_Callback_List[index].
				    pCallerData;

				(g_Visibility_Callback_List[index].pClientFn)
				    (becomingVisible, oidList, pCallerData);

				(void) pthread_mutex_unlock(&g_visa_mutex);

			}
		}

		nvlist_free(attr_list);
	}


	log(LOG_INFO, "notifyClient()", "- exit");
}
Esempio n. 4
0
/* Event handler called by system */
static void
syseventHandler(sysevent_t *ev)
{

	const char	ROUTINE[] = "syseventHandler";
	nvlist_t 	*attrList = NULL;
	char		*eventStr, *portAddrStr, *charptr;
	int		update;
	uint64_t 	addr;
	uint8_t		phyId, linkRate;
	HBA_WWN		portAddr;

	/* Is the event one of ours? */
	if (strncmp(EC_HBA, sysevent_get_class_name(ev), strlen(EC_HBA)) == 0) {
		/* handle phy events */
		if (strncmp(ESC_SAS_PHY_EVENT, sysevent_get_subclass_name(ev),
		    strlen(ESC_SAS_PHY_EVENT)) == 0) {
			if (sysevent_get_attr_list(ev, &attrList) != 0) {
				log(LOG_DEBUG, ROUTINE,
				    "Failed to get event attributes on %s/%s",
				    EC_HBA, ESC_SAS_PHY_EVENT);
				return;
			} else {
				if (nvlist_lookup_string(attrList,
				    "event_type", &eventStr) != 0) {
					log(LOG_DEBUG, ROUTINE,
					    "Event type not found");
					return;
				} else {
					if (strncmp(eventStr, "phy_online",
					    sizeof (eventStr)) == 0) {
						update = ONLINE;
						if (nvlist_lookup_uint8(
						    attrList, "link_rate",
						    &linkRate) != 0) {
							log(LOG_DEBUG, ROUTINE,
							    "Link Rate not \
							    found");
							return;
						}
					} else if (strncmp(eventStr,
					    "phy_offline",
					    sizeof (eventStr)) == 0) {
						update = OFFLINE;
					} else if (strncmp(eventStr,
					    "phy_remove",
					    sizeof (eventStr)) == 0) {
						update = REMOVED;
					} else {
						log(LOG_DEBUG, ROUTINE,
						    "Invalid event type");
						return;
					}
				}
				if (nvlist_lookup_string(attrList,
				    "port_address", &portAddrStr) != 0) {
					log(LOG_DEBUG, ROUTINE,
					    "Port SAS address not found");
					return;
				} else {
					for (charptr = portAddrStr;
					    charptr != NULL; charptr++) {
						if (isxdigit(*charptr)) {
							break;
						}
					}
					addr = htonll(strtoll(charptr,
					    NULL, 16));
					(void) memcpy(portAddr.wwn, &addr, 8);
				}
				if (nvlist_lookup_uint8(attrList,
				    "PhyIdentifier", &phyId) != 0) {
					log(LOG_DEBUG, ROUTINE,
					    "Port SAS address not found");
					return;
				}
			}