コード例 #1
0
enum esif_rc esif_get_action_systemio(
	const struct esif_lp *lp_ptr,
	const struct esif_lp_primitive *primitive_ptr,
	const struct esif_lp_action *action_ptr,
	struct esif_data *req_data_ptr,
	struct esif_data *rsp_data_ptr
	)
{
	enum esif_rc rc = ESIF_OK;
	u32 val         = 1234;

	UNREFERENCED_PARAMETER(lp_ptr);
	UNREFERENCED_PARAMETER(primitive_ptr);
	UNREFERENCED_PARAMETER(action_ptr);
	UNREFERENCED_PARAMETER(req_data_ptr);

	if (NULL == rsp_data_ptr) {
		    rc = ESIF_E_PARAMETER_IS_NULL;
		    goto exit;
	}

	ESIF_TRACE_DYN_GET("val = %d\n", val);

	switch (rsp_data_ptr->type) {
	case ESIF_DATA_UINT8:
		rsp_data_ptr->data_len = sizeof(u8);
		if (rsp_data_ptr->buf_len >= sizeof(u8))
			*((u8 *)rsp_data_ptr->buf_ptr) = (u8)val;
		else
			rc = ESIF_E_OVERFLOWED_RESULT_TYPE;
		break;

	case ESIF_DATA_UINT16:
		rsp_data_ptr->data_len = sizeof(u16);
		if (rsp_data_ptr->buf_len >= sizeof(u16))
			*((u16 *)rsp_data_ptr->buf_ptr) = (u16)val;
		else
			rc = ESIF_E_OVERFLOWED_RESULT_TYPE;
		break;

	case ESIF_DATA_UINT32:
		rsp_data_ptr->data_len = sizeof(u32);
		if (rsp_data_ptr->buf_len >= sizeof(u32))
			*((u32 *)rsp_data_ptr->buf_ptr) = (u32)val;
		else
			rc = ESIF_E_OVERFLOWED_RESULT_TYPE;
		break;

	default:
		ESIF_TRACE_DYN_GET("Data Type Not Implemented = %s\n",
				   esif_data_type_str(rsp_data_ptr->type));
		rc = ESIF_E_NOT_IMPLEMENTED;
		break;
	}
exit:
	ESIF_TRACE_DYN_GET("RC: %s(%d)\n", esif_rc_str(rc), rc);
	return rc;
}
コード例 #2
0
ファイル: esif_lib_eqlcmd.c プロジェクト: naitaku/dptf
// Debug Output
void EqlCmd_DebugDump (EqlCmdPtr self)
{
	if (self) {
		int i;
		CMD_DEBUG(
			"\n"
			"EQLCMD:\n"
			"  adapter       = %s\n"
			"  subtype       = %s\n"
			"  action        = %s\n",
			String_Get(self->adapter),
			String_Get(self->subtype),
			String_Get(self->action));

		for (i = 0; i < self->messages->items; i++)
			CMD_DEBUG(
				"  messages[%d]   = %s\n",
				i, self->messages->list[i]);
		for (i = 0; i < self->parameters->items; i++)
			CMD_DEBUG(
				"  parameters[%d] = %s\n",
				i, self->parameters->list[i]);
		for (i = 0; i < self->values->items; i++)
			CMD_DEBUG(
				"  values[%d]     = %s (%s)\n",
				i, self->datatypes->list[i], self->values->list[i]);
		for (i = 0; i < self->options->items; i++)
			CMD_DEBUG(
				"  options[%d]    = %s\n",
				i, self->options->list[i]);
		for (i = 0; i < self->results->size; i++) {
			EsifDataPtr data = &self->results->elements[i];
			char *strdata    = EsifData_ToString(data);
			if (strdata) {
				CMD_DEBUG(
					"  results[%d]    = %s (buf_len=%d data_len=%d)\n"
					"%s\n",
					i, esif_data_type_str(self->results->elements[i].type),
					self->results->elements[i].buf_len, self->results->elements[i].data_len,
					strdata);
				esif_ccb_free(strdata);
			}
		}
		CMD_DEBUG("\n");
	}
}
コード例 #3
0
ファイル: esif_lib_eqlcmd.c プロジェクト: naitaku/dptf
// Bind Optional Binary Arguments to the Command
eEsifError EqlCmd_BindArguments (
	EqlCmdPtr self,
	EsifDataPtr *arguments
	)
{
	eEsifError rc = ESIF_OK;
	int bin = 0, val = 0;

	// Replace Binary Values with parameters
	for (val = 0; val < self->values->items; val++)
		if (strcmp(self->datatypes->list[val], "%") == 0) {
			if (arguments && arguments[bin]) {
				self->datatypes->list[val] = esif_data_type_str(arguments[bin]->type);
				esif_ccb_free(self->values->list[val]);
				self->values->list[val]    = EsifData_ToString(arguments[bin]);	// temp hack: convert to string
				bin++;
			} else {
				return ESIF_E_PARAMETER_IS_NULL;
			}
		}
	return rc;
}
コード例 #4
0
eEsifError ESIF_CALLCONV EsifEventMgr_RegisterEventByGuid(
	esif_guid_t *guidPtr,
	UInt8 participantId,
	UInt16 domainId,
	EVENT_OBSERVER_CALLBACK eventCallback,
	void *contextPtr
	)
{
	eEsifError rc = ESIF_OK;
	EsifFpcEventPtr fpcEventPtr = NULL;
	EsifUpPtr upPtr = NULL;
	char guidStr[ESIF_GUID_PRINT_SIZE];

	UNREFERENCED_PARAMETER(guidStr);

	if((NULL == guidPtr) || (NULL == eventCallback)) {
		rc = ESIF_E_PARAMETER_IS_NULL;
		goto exit;
	}

	/* Find Our Participant */
	upPtr = EsifUpPm_GetAvailableParticipantByInstance(participantId);
	if (NULL == upPtr) {
		rc = ESIF_E_PARTICIPANT_NOT_FOUND;
		goto exit;
	}

	/* Find the event associated with the participant */
	fpcEventPtr = EsifUp_GetFpcEventByGuid(upPtr, guidPtr);
	if (NULL == fpcEventPtr) {
		rc = ESIF_E_EVENT_NOT_FOUND;
		goto exit;
	}

	ESIF_TRACE_DEBUG(
		"Registering event\n"
		"  Alias: %s\n"
		"  GUID: %s\n"
		"  Type: %s(%d)\n"
		"  Data: %s(%d)\n"
		"  Key: %s\n"
		"  Group: %s\n",
		fpcEventPtr->event_name,
		esif_guid_print((esif_guid_t *)fpcEventPtr->event_guid, guidStr),
		esif_event_type_str(fpcEventPtr->esif_event), fpcEventPtr->esif_event,
		esif_data_type_str(fpcEventPtr->esif_group_data_type), fpcEventPtr->esif_group_data_type,
		esif_guid_print((esif_guid_t *)fpcEventPtr->event_key, guidStr),
		esif_event_group_enum_str(fpcEventPtr->esif_group));

	rc = EsifEventMgr_AddEntry(
		fpcEventPtr,
		participantId,
		domainId,
		eventCallback,
		contextPtr);

exit:
	if (upPtr != NULL) {
		EsifUp_PutRef(upPtr);
	}
	return rc;
}
コード例 #5
0
static eEsifError EsifEventMgr_ProcessEvent(
	UInt8 participantId,
	UInt16 domainId,
	eEsifEventType eventType,
	EsifDataPtr eventDataPtr
	)
{
	eEsifError rc = ESIF_OK;
	EsifLinkListPtr listPtr = NULL;
	EsifLinkListNodePtr nodePtr = NULL;
	EsifLinkListNodePtr nextNodePtr = NULL;
	EventMgrEntryPtr entryPtr = NULL;
	char domain_str[8] = "";
	atomic_t refCount = 0;
	UInt8 shouldDumpGarbage = ESIF_FALSE;

	UNREFERENCED_PARAMETER(domain_str);

	if (NULL == eventDataPtr) {
		ESIF_TRACE_DEBUG("APPLICATION_EVENT_NO_DATA:\n"
			"  ParticipantID: %u\n"
			"  Domain:        %s(%04X)\n"
			"  EventType:     %s(%d)\n",
			participantId,
			esif_primitive_domain_str(domainId, domain_str, sizeof(domain_str)),
			domainId,
			esif_event_type_str(eventType), eventType);
	} else {
		ESIF_TRACE_DEBUG("APPLICATION_EVENT\n"
						 "  ParticipantID: %u\n"
						 "  Domain:        %s(%04X)\n"
						 "  EventType:     %s(%d)\n"
						 "  EventDataType: %s(%d)\n"
						 "  EventData:     %p\n"
						 "    buf_ptr      %p\n"
						 "    buf_len      %d\n"
						 "    data_len     %d\n",
						 participantId,
						 esif_primitive_domain_str(domainId, domain_str, 8),
						 domainId,
						 esif_event_type_str(eventType), eventType,
						 esif_data_type_str(eventDataPtr->type), eventDataPtr->type,
						 eventDataPtr,
						 eventDataPtr->buf_ptr, eventDataPtr->buf_len, eventDataPtr->data_len
						 );

		if ((ESIF_DATA_STRING == eventDataPtr->type) && (NULL != eventDataPtr->buf_ptr)) {
			ESIF_TRACE_DEBUG(
				"  Data Length:   %d\n"
				"  Data:          %s\n",
				eventDataPtr->data_len,
				(EsifString)eventDataPtr->buf_ptr);
		}
	}

	esif_ccb_write_lock(&g_EsifEventMgr.listLock);

	listPtr = g_EsifEventMgr.observerLists[(unsigned)eventType % NUM_EVENT_LISTS];
	if(NULL == listPtr) {
		rc = ESIF_E_UNSPECIFIED;
		esif_ccb_write_unlock(&g_EsifEventMgr.listLock);
		goto exit;
	}

	nodePtr = listPtr->head_ptr;
	while (NULL != nodePtr) {
		nextNodePtr = nodePtr->next_ptr;

		entryPtr = (EventMgrEntryPtr)nodePtr->data_ptr;
		ESIF_ASSERT(entryPtr != NULL);

		if ((eventType == entryPtr->fpcEvent.esif_event) &&
			((entryPtr->participantId == participantId) || (entryPtr->participantId == EVENT_MGR_MATCH_ANY)) &&
			((entryPtr->domainId == domainId) || (entryPtr->domainId == EVENT_MGR_MATCH_ANY) || (domainId == EVENT_MGR_DOMAIN_NA)) &&
			(entryPtr->refCount > 0)) {

			/*
			 * Increment the reference count so that the node is not removed while in use,
			 * then release the lock so that we avoid a deadlock condition
			 */
			atomic_inc(&entryPtr->refCount);
			esif_ccb_write_unlock(&g_EsifEventMgr.listLock);

			entryPtr->callback(entryPtr->contextPtr,
				participantId,
				domainId,
				&entryPtr->fpcEvent,
				eventDataPtr);

			/* 
			 * Get the lock back and decrement the reference count.  Remove the node now
			 * if the reference count is 0
			 */
			esif_ccb_write_lock(&g_EsifEventMgr.listLock);

			nextNodePtr = nodePtr->next_ptr;

			refCount = atomic_dec(&entryPtr->refCount);
			if (refCount <= 0) {
				EsifEventMgr_MoveEntryToGarbage(entryPtr);
				esif_link_list_node_remove(listPtr, nodePtr);
				shouldDumpGarbage = ESIF_TRUE;
			}
		}
		nodePtr = nextNodePtr;
	}

	esif_ccb_write_unlock(&g_EsifEventMgr.listLock);

	if (shouldDumpGarbage) {
		EsifEventMgr_DumpGarbage();
	}

exit:
	return rc;
}
コード例 #6
0
ファイル: esif_uf_dspmgr.c プロジェクト: 01org/dptf
eEsifError esif_fpc_load(
	EsifFpcPtr fpcPtr,
	EsifDspPtr dspPtr
	)
{
	eEsifError rc = ESIF_OK;
	EsifFpcDomainPtr domainPtr;
	EsifFpcPrimitivePtr primitivePtr;
	EsifFpcAlgorithmPtr algoPtr;
	EsifFpcEventPtr eventPtr;
	unsigned long offset = 0;
	UInt8 *basePtr    = (UInt8 *)fpcPtr;
	UInt32 numPrim    = 0;
	UInt32 i;
	UInt32 j;

	if ((fpcPtr == NULL) || (dspPtr == NULL))
	{
		ESIF_TRACE_ERROR("The fpc pointer or dsp pointer is NULL\n");
		rc = ESIF_E_PARAMETER_IS_NULL;
		goto exit;
	}

	if (fpcPtr->number_of_domains < 1) {
		ESIF_TRACE_WARN("No domain error, number_of_domain = %d (less than 1)\n",
			fpcPtr->number_of_domains);
		rc = ESIF_E_PARAMETER_IS_NULL;
		goto exit;
	}
	dspPtr->domain_count = &fpcPtr->number_of_domains;

	/* Allocate Hash and List. Hash Size 31 Is Hard-Coded And Chosen By DSP Compiler */
	dspPtr->ht_ptr     = esif_ht_create(ESIF_DSP_HASHTABLE_SIZE);
	dspPtr->algo_ptr   = esif_link_list_create();
	dspPtr->domain_ptr = esif_link_list_create();
	dspPtr->cap_ptr    = esif_link_list_create();
	dspPtr->evt_ptr    = esif_link_list_create();

	if (!dspPtr->ht_ptr || !dspPtr->algo_ptr || !dspPtr->domain_ptr || !dspPtr->cap_ptr || !dspPtr->evt_ptr) {
		ESIF_TRACE_ERROR("Fail to allocate linked list or hash table\n");
		rc = ESIF_E_NO_MEMORY;
		goto exit;
	}

	ESIF_TRACE_DEBUG("<fpc @ %p> FPC name '%s' ver %x,%x desc '%s' size %u num_domains %d num_algorithms %d num_events %d",
					 fpcPtr,
					 fpcPtr->header.name,
					 fpcPtr->header.ver_major,
					 fpcPtr->header.ver_minor,
					 fpcPtr->header.description,
					 fpcPtr->size,
					 fpcPtr->number_of_domains,
					 fpcPtr->number_of_algorithms,
					 fpcPtr->number_of_events);

	/* First Domain, Ok To Have Zero Primitive Of A Domain */
	domainPtr = (EsifFpcDomainPtr)(fpcPtr + 1);
	for (i = 0; i < fpcPtr->number_of_domains; i++) {
		offset = (unsigned long)((UInt8 *)domainPtr - basePtr);
		ESIF_TRACE_DEBUG("<%04lu> Domain[%d] name %s size %d num_of_primitives %d  "
						 "num_of_capabilites %u (0x%x)",
						 offset, i, domainPtr->descriptor.name, domainPtr->size,
						 domainPtr->number_of_primitives,
						 domainPtr->capability_for_domain.number_of_capability_flags,
						 domainPtr->capability_for_domain.capability_flags);

		/* Insert Domain Into Linked List */
		rc = dspPtr->insert_domain(dspPtr, domainPtr);
		if (ESIF_OK != rc) {
			ESIF_TRACE_ERROR("Fail to insert domain #%d\n", i);
			goto exit;
		}

		/* Capability */
		for (j = 0; j < domainPtr->capability_for_domain.number_of_capability_flags; j++) {
			offset = (unsigned long)(((UInt8 *)&domainPtr->capability_for_domain) - basePtr);
			ESIF_TRACE_DEBUG("<%04lu> Capability[%d] 0x%x", offset, j,
							 domainPtr->capability_for_domain.capability_mask[j]);
		}

		/* First Primtive */
		primitivePtr = (EsifFpcPrimitivePtr)(domainPtr + 1);
		for (j = 0; j < domainPtr->number_of_primitives; j++, numPrim++) {
			offset = (unsigned long)(((UInt8 *)primitivePtr) - basePtr);
			ESIF_TRACE_DEBUG("<%04lu> Primitive[%03d]: size %3d tuple_id <%03u %03u %03u> "
							 "operation %u(%s) req_type %u(%s) res_type %u(%s) num_actions %u",
							 offset, j,
							 primitivePtr->size,
							 primitivePtr->tuple.id,
							 primitivePtr->tuple.domain,
							 primitivePtr->tuple.instance,
							 primitivePtr->operation,
							 esif_primitive_opcode_str(primitivePtr->operation),
							 primitivePtr->request_type,
							 esif_data_type_str(primitivePtr->request_type),
							 primitivePtr->result_type,
							 esif_data_type_str(primitivePtr->result_type),
							 primitivePtr->num_actions);
			/* Insert Primitive Into Hash */
			rc = dspPtr->insert_primitive(dspPtr, primitivePtr);
			if (ESIF_OK != rc) {
				ESIF_TRACE_ERROR("Fail to insert primitive (id = %d)\n", primitivePtr->tuple.id);
				goto exit;
			}
			/* Next Primitive */
			primitivePtr = (EsifFpcPrimitivePtr)((UInt8 *)primitivePtr + primitivePtr->size);
		}
		/* Next Domain */
		domainPtr = (EsifFpcDomainPtr)((UInt8 *)domainPtr + domainPtr->size);
	}

	/* First Algorithm (Laid After The Last Domain) */
	algoPtr = (EsifFpcAlgorithmPtr)domainPtr;
	for (i = 0; i < fpcPtr->number_of_algorithms; i++) {
		offset = (unsigned long)((UInt8 *)algoPtr - basePtr);
		ESIF_TRACE_DEBUG("<%04lu> Algorithm[%03d]:  action_type %u(%s) temp_xform %u "
						 "tempC1 %u percent_xform %u size %u",
						 offset, i,
						 algoPtr->action_type,
						 esif_action_type_str(algoPtr->action_type),
						 algoPtr->temp_xform,
						 algoPtr->tempC1,
						 algoPtr->percent_xform,
						 algoPtr->size);

		/* Insert Algorithm Into Linked List */
		rc = dspPtr->insert_algorithm(dspPtr, algoPtr);
		if (ESIF_OK != rc) {
			ESIF_TRACE_ERROR("Fail to insert algorithm - %s\n", esif_action_type_str(algoPtr->action_type));
			goto exit;
		}

		/* Next Algorithm */
		algoPtr = (EsifFpcAlgorithmPtr)(algoPtr + 1);
	}

	/* First Event (Laid After The Last Algorithm) */
	eventPtr = (EsifFpcEventPtr)algoPtr;
	for (i = 0; i < fpcPtr->number_of_events; i++) {
		offset = (unsigned long)((UInt8 *)eventPtr - basePtr);
		ESIF_TRACE_DEBUG("<%04lu> Event [%03d] type %s(%d)\n",
						 offset, i, esif_event_type_str(eventPtr->esif_event), eventPtr->esif_event);

		/* Insert Algorithm Into Linked List */
		rc = dspPtr->insert_event(dspPtr, eventPtr);
		if (ESIF_OK != rc) {
			ESIF_TRACE_ERROR("Fail to insert event - %s\n", esif_event_type_str(eventPtr->esif_event));
			goto exit;
		}

		/* Next Event */
		eventPtr = (EsifFpcEventPtr)(eventPtr + 1);
	}

exit:
	if (fpcPtr != NULL) {
		ESIF_TRACE_DEBUG("%u domains, %u primitives and %u algorithms %u events inserted! status %s",
						 fpcPtr->number_of_domains, numPrim, fpcPtr->number_of_algorithms, fpcPtr->number_of_events,
						 esif_rc_str(rc));
	}
	return rc;
}
コード例 #7
0
ファイル: esif_lf_command.c プロジェクト: naitaku/dptf
/* Dispatch */
struct esif_ipc *esif_execute_ipc_command(
	struct esif_ipc *ipc_ptr
	)
{
	struct esif_ipc_command *command_ptr =
		(struct esif_ipc_command *)(ipc_ptr + 1);
	u32 data_size = 0;

	command_ptr->return_code = ESIF_E_COMMAND_DATA_INVALID;

	if (ESIF_COMMAND_VERSION != command_ptr->version)
		goto exit;

	data_size = ipc_ptr->data_len - sizeof(*command_ptr);

	if(((command_ptr->req_data_offset + command_ptr->req_data_len) > 
	     data_size) ||
	   ((command_ptr->rsp_data_offset + command_ptr->rsp_data_len) > 
	     data_size))
		goto exit;

	ESIF_TRACE_DYN_COMMAND("%s: COMMAND Received: ipc %p\n",
			       ESIF_FUNC,
			       ipc_ptr);
	ESIF_TRACE_DYN_DECODE("  Version:              %d\n"
			      "  Type:                 %s(%d)\n"
			      "  Priority:             %s(%d)\n"
			      "  Payload Length:       %d\n"
			      "  Request  Data Type:   %s(%d)\n"
			      "  Request  Data Offset: %d\n"
			      "  Request  Data Length: %d\n"
			      "  Response Data Type:   %s(%d)\n"
			      "  Response Data Offset: %d\n"
			      "  Response Data Length: %d\n",
			      (int)command_ptr->version,
			      esif_command_type_str(command_ptr->type),
			      (int)command_ptr->type,
			      esif_command_priority_str(command_ptr->priority),
			      (int)command_ptr->priority,
			      (int)command_ptr->payload_len,
			      esif_data_type_str(command_ptr->req_data_type),
			      (int)command_ptr->req_data_type,
			      (int)command_ptr->req_data_offset,
			      (int)command_ptr->req_data_len,
			      esif_data_type_str(command_ptr->rsp_data_type),
			      (int)command_ptr->rsp_data_type,
			      (int)command_ptr->rsp_data_offset,
			      (int)command_ptr->rsp_data_len);

	switch (command_ptr->type) {
	case ESIF_COMMAND_TYPE_SET_DEBUG_MODULES:
		esif_execute_ipc_command_set_debug_modules(command_ptr);
		break;

	case ESIF_COMMAND_TYPE_SET_DEBUG_MODULE_LEVEL:
		esif_execute_ipc_command_set_debug_module_level(command_ptr);
		break;

	case ESIF_COMMAND_TYPE_GET_DEBUG_MODULE_LEVEL:
		esif_execute_ipc_command_get_debug_module_level(command_ptr);
		break;

	case ESIF_COMMAND_TYPE_GET_KERNEL_INFO:
		esif_execute_ipc_command_get_kernel_info(command_ptr);
		break;

	case ESIF_COMMAND_TYPE_GET_MEMORY_STATS:
		esif_execute_ipc_command_get_memory_stats(command_ptr);
		break;

	case ESIF_COMMAND_TYPE_GET_PARTICIPANTS:
		esif_execute_ipc_command_get_participants(command_ptr);
		break;

	case ESIF_COMMAND_TYPE_GET_PARTICIPANT_DETAIL:
		esif_execute_ipc_command_get_participant_detail(command_ptr);
		break;

	default:
		ESIF_TRACE_DYN_COMMAND("%s: Unknown Command Type %d:\n",
				       ESIF_FUNC, command_ptr->type);
		break;
	}
	ESIF_TRACE_DYN_COMMAND("%s: COMMAND return result: %s(%d)\n", ESIF_FUNC,
			       esif_rc_str(
				       command_ptr->return_code),
			       command_ptr->return_code);
exit:
	/* Send To User */
	return ipc_ptr;
}
コード例 #8
0
/* Copy/Merge Keys from one NameSpace to Another */
eEsifError EsifConfigCopy(
	EsifDataPtr nameSpaceFrom,	// Source DV
	EsifDataPtr nameSpaceTo,	// Target DV
	EsifDataPtr keyspecs,		// Tab-separated Keyspec List (wildcards OK)
	esif_flags_t flags,			// Item Flags
	Bool replaceKeys,			// TRUE=COPY Keys (Replace if exists), FALSE=MERGE Keys (Do Not Replace)
	UInt32 *keycount)			// Optional pointer to variable to hold Key Count copied/merged
{
	eEsifError rc = ESIF_OK;
	EsifConfigFindContext context = NULL;
	EsifDataPtr data_key = NULL;
	EsifDataPtr data_value = NULL;
	esif_string keylist = NULL;
	esif_string keyspec = NULL;
	esif_string keyspec_context = NULL;
	char **keyset = NULL;
	size_t keyset_count = 0;
	UInt32 exported = 0;
	esif_context_t qsort_ctx = 0;
	size_t key = 0;

	ESIF_ASSERT(nameSpaceFrom && nameSpaceTo && keyspecs && nameSpaceFrom->buf_ptr && nameSpaceTo->buf_ptr && keyspecs->buf_ptr);

	// Parse Key List (optionally Tab-separated)
	keylist = esif_ccb_strdup((esif_string)keyspecs->buf_ptr);
	if (keylist == NULL) {
		rc = ESIF_E_NO_MEMORY;
		goto exit;
	}

	// Create sorted keyset with exclude keyspecs ("!keyspec") listed first
	keyspec = esif_ccb_strtok(keylist, "\t", &keyspec_context);
	while (keyspec != NULL) {
		char **new_keyset = (char **)esif_ccb_realloc(keyset, sizeof(char *) * (keyset_count + 1));
		if (new_keyset == NULL) {
			rc = ESIF_E_NO_MEMORY;
			goto exit;
		}
		keyset = new_keyset;
		keyset[keyset_count++] = keyspec;
		keyspec = esif_ccb_strtok(NULL, "\t", &keyspec_context);
	}
	esif_ccb_qsort(keyset, keyset_count, sizeof(char *), esif_ccb_qsort_stricmp, qsort_ctx);

	// Enumerate Each Matching keyspec
	for (key = 0; (rc == ESIF_OK && key < keyset_count); key++) {

		// Skip excludes for now so we can compare to each maching keyspec later
		if (keyset[key][0] == '!') {
			continue;
		}

		EsifData_Destroy(data_key);
		data_key = EsifData_CreateAs(ESIF_DATA_STRING, keyset[key], 0, ESIFAUTOLEN);
		if (data_key == NULL) {
			rc = ESIF_E_NO_MEMORY;
			goto exit;
		}
		if ((rc = EsifConfigFindFirst(nameSpaceFrom, data_key, NULL, &context)) == ESIF_OK) {
			do {
				// Skip if matching key matches any exclude keyspecs
				Bool skip_key = ESIF_FALSE;
				size_t ex = 0;
				for (ex = 0; (ex < key && keyset[ex][0] == '!'); ex++) {
					if (esif_ccb_strmatch((esif_string)data_key->buf_ptr, &keyset[ex][1])) {
						skip_key = ESIF_TRUE;
						break;
					}
				}

				// copy  = always replace existing key in target if it already exists
				// merge = never replace existing key in target if it already exists
				if ((skip_key == ESIF_FALSE) &&
					(replaceKeys == ESIF_TRUE || DataBank_KeyExists(g_DataBankMgr, (esif_string)nameSpaceTo->buf_ptr, (esif_string)data_key->buf_ptr) == ESIF_FALSE)) {

					EsifData_Destroy(data_value);
					data_value = EsifData_CreateAs(ESIF_DATA_AUTO, NULL, ESIF_DATA_ALLOCATE, 0);
					if (data_value == NULL) {
						rc = ESIF_E_NO_MEMORY;
						break;
					}
					rc = EsifConfigGet(nameSpaceFrom, data_key, data_value);
					if (rc != ESIF_OK) {
						break;
					}
					rc = EsifConfigSet(nameSpaceTo, data_key, flags, data_value);
					if (rc != ESIF_OK) {
						break;
					}

					ESIF_TRACE_DEBUG("DV %s: @%s => @%s [%s] {%s, %u bytes}\n",
						(replaceKeys ? "Copy" : "Merge"),
						(esif_string)nameSpaceFrom->buf_ptr,
						(esif_string)nameSpaceTo->buf_ptr,
						(esif_string)data_key->buf_ptr,
						esif_data_type_str(data_value->type),
						data_value->data_len);

					exported++;
				}

				// Reset Key for next search
				EsifData_Set(data_key, ESIF_DATA_STRING, keyset[key], 0, ESIFAUTOLEN);
			} while ((rc = EsifConfigFindNext(nameSpaceFrom, data_key, NULL, &context)) == ESIF_OK);

			EsifConfigFindClose(&context);
		}
		if (rc == ESIF_E_ITERATION_DONE || rc == ESIF_E_NOT_FOUND) {
			rc = ESIF_OK;
		}
	}

exit:
	if (rc == ESIF_OK && keycount != NULL) {
		*keycount = exported;
	}
	EsifData_Destroy(data_key);
	EsifData_Destroy(data_value);
	esif_ccb_free(keylist);
	esif_ccb_free(keyset);
	return rc;
}
コード例 #9
0
ファイル: esif_lib_datavault.c プロジェクト: qbbian/dptf
// Retrieve a single value from a DataVault
eEsifError DataVault_GetValue (
	DataVaultPtr self,
	EsifDataPtr path,
	EsifDataPtr value
	)
{
	eEsifError rc = ESIF_E_NOT_FOUND;
	DataCacheEntryPtr keypair = NULL;

	if (!self)
		return ESIF_E_PARAMETER_IS_NULL;

	// TODO: Locking

	// Debug: Dump Entire Contents of DataVault if path="*"
	if (strcmp((esif_string)path->buf_ptr, "*") == 0) {
		UInt32 context = 0;
		EsifDataPtr nameSpace = EsifData_CreateAs(ESIF_DATA_STRING, esif_ccb_strdup(self->name), ESIFAUTOLEN, ESIFAUTOLEN);
		EsifDataPtr key       = EsifData_CreateAs(ESIF_DATA_AUTO, NULL, ESIF_DATA_ALLOCATE, 0);
		EsifDataPtr value     = EsifData_CreateAs(ESIF_DATA_AUTO, NULL, ESIF_DATA_ALLOCATE, 0);

#ifdef _DEBUG
		// Dump DataCache if Debug Mode
		UInt32 i;
		for (i = 0; i < self->cache->size; i++) {
			DataCacheEntryPtr keypair = &self->cache->elements[i];
			CMD_DEBUG("\n"
					  "id=%d\n"
					  "key=%s\n"
					  "flags=%08X\n"
					  "value.type = %s (%d)\n"
					  "value.buf_ptr = %p %s\n"
					  "value.buf_len = %d\n"
					  "value.data_len= %d\n",
					  i,
					  (char*)keypair->key.buf_ptr,
					  keypair->flags,
					  esif_data_type_str(keypair->value.type), keypair->value.type,
					  keypair->value.buf_ptr,
					  ((keypair->flags & (ESIF_SERVICE_CONFIG_FILELINK | ESIF_SERVICE_CONFIG_REGLINK)) ? (esif_string)keypair->value.buf_ptr : ""),
					  keypair->value.buf_len,
					  keypair->value.data_len
					  );
		}
		if (i > 0) {
			CMD_DEBUG("*****************\n");
		}
#endif
		// Iterate the Contents of the Data Cache
		if ((rc = EsifConfigFindFirst(nameSpace, key, value, &context)) == ESIF_OK) {
			do {
				StringPtr valuestr = EsifData_ToString(value);
				CMD_DEBUG("\n"
						  "EsifFind%s(\"%s\",%d):\n"
						  "  path = %s\n"
						  "  value= %s%s%s\n"
						  "  type = %s, len=%d\n",
						  (context <= 1 ? "First" : "Next"), (char*)nameSpace->buf_ptr, context - 1,
						  (char*)key->buf_ptr,
						  (value->type == ESIF_DATA_STRING ? "\"" : ""), (valuestr ? valuestr : ""), (value->type == ESIF_DATA_STRING ? "\"" : ""),
						  esif_data_type_str(value->type), value->data_len
						  );
				esif_ccb_free(valuestr);
				EsifData_Set(key, ESIF_DATA_AUTO, NULL, ESIF_DATA_ALLOCATE, 0);
				EsifData_Set(value, ESIF_DATA_AUTO, NULL, ESIF_DATA_ALLOCATE, 0);
			} while ((rc = EsifConfigFindNext(nameSpace, key, value, &context)) == ESIF_OK);
			if (rc == ESIF_E_NOT_FOUND) {
				rc = ESIF_OK;
			}
		}
		EsifData_Destroy(nameSpace);
		EsifData_Destroy(key);
		EsifData_Destroy(value);
		return ESIF_OK;
	}

	// Write to Log before retrieval if AUTO
	if (value->type == ESIF_DATA_AUTO || value->buf_len == ESIF_DATA_ALLOCATE) {
		DataVault_WriteLog(self, "AUTO", (esif_string)(self->name), path, 0, value);
	}

	keypair = DataCache_GetValue(self->cache, (esif_string)path->buf_ptr);
	
	if (NULL != keypair) {
		UInt32 data_len = keypair->value.data_len;
		void *buf_ptr   = keypair->value.buf_ptr;

		// File Redirect?
		if (keypair->flags & ESIF_SERVICE_CONFIG_FILELINK) {
			if (DataVault_ReadFile(self, (esif_string)buf_ptr, &buf_ptr, &data_len) != ESIF_OK) {
				value->data_len = 0;
				if (value->type == ESIF_DATA_AUTO) {
					value->type = keypair->value.type;
				}
				if (value->buf_len == ESIF_DATA_ALLOCATE) {
					value->buf_len = 0;
					value->buf_ptr = 0;
				}
				return ESIF_OK;	// return OK and a blank buffer if file not found/error
			}
		}

#ifdef ESIF_ATTR_OS_WINDOWS
		// Registry Redirect?
		else if (keypair->flags & ESIF_SERVICE_CONFIG_REGLINK) {
			if (DataVault_ReadRegistry(self, (esif_string)buf_ptr, &buf_ptr, &data_len) != ESIF_OK) {
				value->data_len = 0;
				if (value->type == ESIF_DATA_AUTO) {
					value->type = keypair->value.type;
				}
				if (value->buf_len == ESIF_DATA_ALLOCATE) {
					value->buf_len = 0;
					value->buf_ptr = 0;
				}
				return ESIF_OK;	// return OK and a blank buffer if Registry value not found/error
			}
		}
#endif
		// Match Found. Verify Data Type matches unless AUTO
		if (value->type != keypair->value.type && value->type != ESIF_DATA_AUTO) {
			rc = ESIF_E_UNSUPPORTED_RESULT_DATA_TYPE;	// TODO: ESIF_E_INVALID_DATA_TYPE
		}
		// Verify Data Buffer is large enough unless Auto-Allocate
		else if (value->buf_len < data_len && value->buf_len != ESIF_DATA_ALLOCATE) {
			value->buf_len = data_len;
			rc = ESIF_E_NEED_LARGER_BUFFER;
		}
		// Return pointer to static contents if this is a static vault
		else if ((self->flags & ESIF_SERVICE_CONFIG_STATIC) &&
				 (value->type == ESIF_DATA_AUTO) &&
				 (value->buf_len == ESIF_DATA_ALLOCATE)) {
			value->type     = keypair->value.type;
			value->data_len = data_len;
			value->buf_len  = 0;	// Caller MUST NOT Free!
			value->buf_ptr  = buf_ptr;
			rc = ESIF_OK;
		} else {
			// Set Data Type and Auto-Allocate Buffer?
			if (value->type == ESIF_DATA_AUTO) {
				value->type = keypair->value.type;
			}
			if (ESIF_DATA_ALLOCATE == value->buf_len) {
				value->buf_len = data_len;
				value->buf_ptr = esif_ccb_malloc(value->buf_len);
				if (!value->buf_ptr) {
					return ESIF_E_NO_MEMORY;
				}
			}

			// Read from file if NOCACHE option
			if ((keypair->flags & ESIF_SERVICE_CONFIG_NOCACHE) && keypair->value.buf_len == 0) {
				size_t offset = (size_t)keypair->value.buf_ptr;
				if (DataVault_ReadBlock(self, (esif_string)value->buf_ptr, data_len, offset) != ESIF_OK) {
					data_len = 0;
					return ESIF_E_NOT_FOUND;
				}
				// Decrypt?
				if (keypair->flags & ESIF_SERVICE_CONFIG_ENCRYPT) {
					UInt32 byte;
					for (byte = 0; byte < data_len; byte++)
						((UInt8*)(value->buf_ptr))[byte] = ~((UInt8*)(value->buf_ptr))[byte];
				}
			} else {
				esif_ccb_memcpy(value->buf_ptr, buf_ptr, data_len);
			}
			value->data_len = data_len;
			rc = ESIF_OK;
		}
	}
	// Write to Log
	DataVault_WriteLog(self, "GET", (esif_string)self->name, path, 0, value);
	return rc;
}