diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/lockdown.c | 184 | ||||
| -rw-r--r-- | src/plist.c | 67 | ||||
| -rw-r--r-- | src/plist.h | 1 | 
3 files changed, 155 insertions, 97 deletions
| diff --git a/src/lockdown.c b/src/lockdown.c index 1782d45..3d39fbd 100644 --- a/src/lockdown.c +++ b/src/lockdown.c @@ -91,7 +91,6 @@ iphone_lckd_client_t new_lockdownd_client(iphone_device_t phone)  	return control;  } -  /** Closes the lockdownd client and does the necessary housekeeping.   *   * @param control The lockdown client @@ -436,10 +435,9 @@ iphone_error_t iphone_lckd_new_client(iphone_device_t device, iphone_lckd_client  iphone_error_t lockdownd_pair_device(iphone_lckd_client_t control, char *uid, char *host_id)  {  	iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR; -	xmlDocPtr plist = new_plist(); -	xmlNode *dict = NULL; -	xmlNode *dictRecord = NULL; -	char **dictionary = NULL; +	plist_t plist = NULL; +	dict_t dict = NULL; +	dict_t dict_record = NULL;  	int bytes = 0, i = 0;  	char *XML_content = NULL;  	uint32_t length = 0; @@ -462,24 +460,23 @@ iphone_error_t lockdownd_pair_device(iphone_lckd_client_t control, char *uid, ch  	}  	/* Setup Pair request plist */ -	dict = add_child_to_plist(plist, "dict", "\n", NULL, 0); -	dictRecord = add_key_dict_node(plist, dict, "PairRecord", "\n", 1); -	//dictRecord = add_child_to_plist(plist, "dict", "\n", NULL, 1); -	add_key_data_dict_element(plist, dictRecord, "DeviceCertificate", device_cert_b64, 2); -	add_key_data_dict_element(plist, dictRecord, "HostCertificate", host_cert_b64, 2); -	add_key_str_dict_element(plist, dictRecord, "HostID", host_id, 2); -	add_key_data_dict_element(plist, dictRecord, "RootCertificate", root_cert_b64, 2); -	add_key_str_dict_element(plist, dict, "Request", "Pair", 1); - -	xmlDocDumpMemory(plist, (xmlChar **) & XML_content, &length); - -	printf("XML Pairing request : %s\n", XML_content); +	plist_new_plist(&plist); +	plist_new_dict_in_plist(plist, &dict); +	plist_add_dict_element(dict, "PairRecord", PLIST_DICT, NULL); +	dict_record = g_node_last_child(dict); +	plist_add_dict_element(dict_record, "DeviceCertificate", PLIST_DATA, (void *) device_cert_b64); +	plist_add_dict_element(dict_record, "HostCertificate", PLIST_DATA, (void *) host_cert_b64); +	plist_add_dict_element(dict_record, "HostID", PLIST_STRING, (void *) host_id); +	plist_add_dict_element(dict_record, "RootCertificate", PLIST_DATA, (void *) root_cert_b64); +	plist_add_dict_element(dict, "Request", PLIST_STRING, (void *) "Pair"); +	plist_to_xml(plist, &XML_content, &length); +	log_debug_msg("XML Pairing request :\nsize : %i\nxml :\n %s", length, XML_content);  	/* send to iPhone */  	ret = iphone_lckd_send(control, XML_content, length, &bytes);  	xmlFree(XML_content); -	xmlFreeDoc(plist); +	plist_free(plist);  	plist = NULL;  	if (ret != IPHONE_E_SUCCESS) @@ -495,40 +492,29 @@ iphone_error_t lockdownd_pair_device(iphone_lckd_client_t control, char *uid, ch  	log_debug_msg(XML_content);  	log_debug_msg("\n\n"); -	plist = xmlReadMemory(XML_content, bytes, NULL, NULL, 0); -	if (!plist) { -		free(public_key_b64); +	xml_to_plist(XML_content, bytes, &plist); +	if (!plist)  		return IPHONE_E_PLIST_ERROR; -	} -	dict = xmlDocGetRootElement(plist); -	for (dict = dict->children; dict; dict = dict->next) { -		if (!xmlStrcmp(dict->name, "dict")) -			break; -	} -	if (!dict) { -		free(public_key_b64); -		return IPHONE_E_DICT_ERROR; -	} -	/* Parse xml to check success and to find public key */ -	dictionary = read_dict_element_strings(dict); -	xmlFreeDoc(plist); -	free(XML_content); +	plist_t query_node = find_query_node(plist, "Request", "Pair"); +	plist_t result_key_node = g_node_next_sibling(query_node); +	plist_t result_value_node = g_node_next_sibling(result_key_node); -	int success = 0; -	for (i = 0; dictionary[i]; i += 2) { -		if (!strcmp(dictionary[i], "Result") && !strcmp(dictionary[i + 1], "Success")) { -			success = 1; -		} -	} +	plist_type result_key_type; +	plist_type result_value_type; +	char *result_key = NULL; +	char *result_value = NULL; -	if (dictionary) { -		free_dictionary(dictionary); -		dictionary = NULL; +	get_type_and_value(result_key_node, &result_key_type, (void *) (&result_key)); +	get_type_and_value(result_value_node, &result_value_type, (void *) (&result_value)); + +	if (result_key_type == PLIST_KEY && +		result_value_type == PLIST_STRING && !strcmp(result_key, "Result") && !strcmp(result_value, "Success")) { +		ret = IPHONE_E_SUCCESS;  	}  	/* store public key in config if pairing succeeded */ -	if (success) { +	if (ret == IPHONE_E_SUCCESS) {  		log_debug_msg("lockdownd_pair_device: pair success\n");  		store_device_public_key(uid, public_key_b64);  		ret = IPHONE_E_SUCCESS; @@ -914,81 +900,85 @@ iphone_error_t iphone_lckd_start_service(iphone_lckd_client_t client, const char  	if (!client->in_SSL && !lockdownd_start_SSL_session(client, host_id))  		return IPHONE_E_SSL_ERROR; -	char *XML_query, **dictionary; + +	plist_t plist = NULL; +	dict_t dict = NULL; +	char *XML_content = NULL;  	uint32_t length, i = 0, port_loc = 0, bytes = 0; -	uint8_t result = 0;  	iphone_error_t ret = IPHONE_E_UNKNOWN_ERROR;  	free(host_id);  	host_id = NULL; -	xmlDocPtr plist = new_plist(); -	xmlNode *dict = add_child_to_plist(plist, "dict", "\n", NULL, 0); -	xmlNode *key; -	key = add_key_str_dict_element(plist, dict, "Request", "StartService", 1); -	if (!key) { -		xmlFreeDoc(plist); -		return IPHONE_E_UNKNOWN_ERROR; -	} -	key = add_key_str_dict_element(plist, dict, "Service", service, 1); -	if (!key) { -		xmlFreeDoc(plist); -		return IPHONE_E_UNKNOWN_ERROR; -	} +	plist_new_plist(&plist); +	plist_new_dict_in_plist(plist, &dict); +	plist_add_dict_element(dict, "Request", PLIST_STRING, (void *) "StartService"); +	plist_add_dict_element(dict, "Service", PLIST_STRING, (void *) service); +	plist_to_xml(plist, &XML_content, &length); + +	/* send to iPhone */ +	log_debug_msg("Send msg :\nsize : %i\nxml : %s", length, XML_content); +	ret = iphone_lckd_send(client, XML_content, length, &bytes); -	xmlDocDumpMemory(plist, (xmlChar **) & XML_query, &length); +	xmlFree(XML_content); +	XML_content = NULL; +	plist_free(plist); +	plist = NULL; -	ret = iphone_lckd_send(client, XML_query, length, &bytes); -	free(XML_query);  	if (IPHONE_E_SUCCESS != ret)  		return ret; -	ret = iphone_lckd_recv(client, &XML_query, &bytes); -	xmlFreeDoc(plist); +	ret = iphone_lckd_recv(client, &XML_content, &bytes); +  	if (IPHONE_E_SUCCESS != ret)  		return ret; +	xml_to_plist(XML_content, bytes, &plist); +	if (!plist) +		return IPHONE_E_PLIST_ERROR; + +  	if (bytes <= 0)  		return IPHONE_E_NOT_ENOUGH_DATA;  	else { -		plist = xmlReadMemory(XML_query, bytes, NULL, NULL, 0); -		if (!plist) -			return IPHONE_E_UNKNOWN_ERROR; -		dict = xmlDocGetRootElement(plist); -		if (!dict) -			return IPHONE_E_UNKNOWN_ERROR; -		for (dict = dict->children; dict; dict = dict->next) { -			if (!xmlStrcmp(dict->name, "dict")) -				break; -		} -		if (!dict) -			return IPHONE_E_UNKNOWN_ERROR; -		dictionary = read_dict_element_strings(dict); - -		for (i = 0; dictionary[i]; i += 2) { -			log_debug_msg("lockdownd_start_service() dictionary %s: %s\n", dictionary[i], dictionary[i + 1]); - -			if (!xmlStrcmp(dictionary[i], "Port")) { -				port_loc = atoi(dictionary[i + 1]); -				log_debug_msg("lockdownd_start_service() atoi'd port: %i\n", port); -			} - -			if (!xmlStrcmp(dictionary[i], "Result")) { -				if (!xmlStrcmp(dictionary[i + 1], "Success")) { -					result = 1; -				} -			} +		plist_t query_node = find_query_node(plist, "Request", "StartService"); +		plist_t result_key_node = g_node_next_sibling(query_node); +		plist_t result_value_node = g_node_next_sibling(result_key_node); + +		plist_t port_key_node = find_node(plist, PLIST_KEY, "Port"); +		plist_t port_value_node = g_node_next_sibling(port_key_node); + +		plist_type result_key_type; +		plist_type result_value_type; +		plist_type port_key_type; +		plist_type port_value_type; +		char *result_key = NULL; +		char *result_value = NULL; +		char *port_key = NULL; +		uint64_t port_value = 0; + +		get_type_and_value(result_key_node, &result_key_type, (void *) (&result_key)); +		get_type_and_value(result_value_node, &result_value_type, (void *) (&result_value)); +		get_type_and_value(port_key_node, &port_key_type, (void *) (&port_key)); +		get_type_and_value(port_value_node, &port_value_type, (void *) (&port_value)); + +		if (result_key_type == PLIST_KEY && +			result_value_type == PLIST_STRING && +			port_key_type == PLIST_KEY && +			port_value_type == PLIST_UINT64 && +			!strcmp(result_key, "Result") && !strcmp(result_value, "Success") && !strcmp(port_key, "Port")) { +			port_loc = port_value; +			ret = IPHONE_E_SUCCESS;  		}  		log_debug_msg("lockdownd_start_service(): DATA RECEIVED:\n\n"); -		log_debug_msg(XML_query); +		log_debug_msg(XML_content);  		log_debug_msg("end data received by lockdownd_start_service()\n"); -		free(XML_query); -		xmlFreeDoc(plist); -		free_dictionary(dictionary); -		if (port && result) { +		free(XML_content); +		plist_free(plist); +		if (port && ret == IPHONE_E_SUCCESS) {  			*port = port_loc;  			return IPHONE_E_SUCCESS;  		} else diff --git a/src/plist.c b/src/plist.c index 5b61570..1c00cc6 100644 --- a/src/plist.c +++ b/src/plist.c @@ -946,6 +946,73 @@ GNode *find_query_node(plist_t plist, char *key, char *request)  	return NULL;  } +char compare_node_value(plist_type type, struct plist_data *data, void *value) +{ +	char res = FALSE; +	switch (type) { +	case PLIST_BOOLEAN: +		res = data->boolval == *((char *) value) ? TRUE : FALSE; +		break; +	case PLIST_UINT8: +		res = data->intval8 == *((uint8_t *) value) ? TRUE : FALSE; +		break; +	case PLIST_UINT16: +		res = data->intval16 == *((uint16_t *) value) ? TRUE : FALSE; +		break; +	case PLIST_UINT32: +		res = data->intval32 == *((uint32_t *) value) ? TRUE : FALSE; +		break; +	case PLIST_UINT64: +		res = data->intval64 == *((uint64_t *) value) ? TRUE : FALSE; +		break; +	case PLIST_FLOAT32: +		res = data->realval32 == *((float *) value) ? TRUE : FALSE; +		break; +	case PLIST_FLOAT64: +		res = data->realval64 == *((double *) value) ? TRUE : FALSE; +		break; +	case PLIST_KEY: +	case PLIST_STRING: +		res = !strcmp(data->strval, ((char *) value)); +		break; +	case PLIST_UNICODE: +		res = !wcscmp(data->unicodeval, ((wchar_t *) value)); +		break; +	case PLIST_DATA: +		res = !strcmp(data->buff, ((char *) value)); +		break; +	case PLIST_ARRAY: +	case PLIST_DICT: +	case PLIST_DATE: +	case PLIST_PLIST: +	default: +		break; +	} +	return res; +} + +GNode *find_node(plist_t plist, plist_type type, void *value) +{ +	if (!plist) +		return NULL; + +	GNode *current = NULL; +	for (current = plist->children; current; current = current->next) { + +		struct plist_data *data = (struct plist_data *) current->data; + +		if (data->type == type && compare_node_value(type, data, value)) { +			return current; +		} +		if (data->type == PLIST_DICT || data->type == PLIST_ARRAY || data->type == PLIST_PLIST) { +			GNode *sub = find_node(current, type, value); +			if (sub) +				return sub; +		} +	} +	return NULL; +} +  void get_type_and_value(GNode * node, plist_type * type, void *value)  {  	if (!node) diff --git a/src/plist.h b/src/plist.h index ffc00e4..34e3934 100644 --- a/src/plist.h +++ b/src/plist.h @@ -84,5 +84,6 @@ void xml_to_plist(const char *plist_xml, uint32_t length, plist_t * plist);  void bin_to_plist(const char *plist_bin, uint32_t length, plist_t * plist);  GNode *find_query_node(plist_t plist, char *key, char *request); +GNode *find_node(plist_t plist, plist_type type, void *value);  void get_type_and_value(GNode * node, plist_type * type, void *value);  #endif | 
