|  | @@ -611,44 +611,114 @@ cJSON* cJSONUtils_GeneratePatches(cJSON *from, cJSON *to)
 | 
	
		
			
				|  |  |      return patches;
 | 
	
		
			
				|  |  |  }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | +/* sort lists using mergesort */
 | 
	
		
			
				|  |  |  static cJSON *cJSONUtils_SortList(cJSON *list)
 | 
	
		
			
				|  |  |  {
 | 
	
		
			
				|  |  | -	cJSON *first=list,*second=list,*ptr=list;
 | 
	
		
			
				|  |  | +    cJSON *first = list;
 | 
	
		
			
				|  |  | +    cJSON *second = list;
 | 
	
		
			
				|  |  | +    cJSON *ptr = list;
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -	if (!list || !list->next) return list;	/* One entry is sorted already. */
 | 
	
		
			
				|  |  | -	
 | 
	
		
			
				|  |  | -	while (ptr && ptr->next && cJSONUtils_strcasecmp(ptr->string,ptr->next->string)<0) ptr=ptr->next;	/* Test for list sorted. */
 | 
	
		
			
				|  |  | -	if (!ptr || !ptr->next) return list;	/* Leave sorted lists unmodified. */
 | 
	
		
			
				|  |  | -	ptr=list;
 | 
	
		
			
				|  |  | +    if (!list || !list->next)
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +        /* One entry is sorted already. */
 | 
	
		
			
				|  |  | +        return list;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -	while (ptr) {second=second->next;ptr=ptr->next;if (ptr) ptr=ptr->next;}	/* Walk two pointers to find the middle. */
 | 
	
		
			
				|  |  | -	if (second && second->prev) second->prev->next=0;	/* Split the lists */
 | 
	
		
			
				|  |  | +    while (ptr && ptr->next && (cJSONUtils_strcasecmp(ptr->string, ptr->next->string) < 0))
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +        /* Test for list sorted. */
 | 
	
		
			
				|  |  | +        ptr = ptr->next;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +    if (!ptr || !ptr->next)
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +        /* Leave sorted lists unmodified. */
 | 
	
		
			
				|  |  | +        return list;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +    /* reset ptr to the beginning */
 | 
	
		
			
				|  |  | +    ptr = list;
 | 
	
		
			
				|  |  | +    while (ptr)
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +        /* Walk two pointers to find the middle. */
 | 
	
		
			
				|  |  | +        second = second->next;
 | 
	
		
			
				|  |  | +        ptr = ptr->next;
 | 
	
		
			
				|  |  | +        /* advances ptr two steps at a time */
 | 
	
		
			
				|  |  | +        if (ptr)
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +            ptr = ptr->next;
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +    if (second && second->prev)
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +        /* Split the lists */
 | 
	
		
			
				|  |  | +        second->prev->next = 0;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -	first=cJSONUtils_SortList(first);	/* Recursively sort the sub-lists. */
 | 
	
		
			
				|  |  | -	second=cJSONUtils_SortList(second);
 | 
	
		
			
				|  |  | -	list=ptr=0;
 | 
	
		
			
				|  |  | +    /* Recursively sort the sub-lists. */
 | 
	
		
			
				|  |  | +    first = cJSONUtils_SortList(first);
 | 
	
		
			
				|  |  | +    second = cJSONUtils_SortList(second);
 | 
	
		
			
				|  |  | +    list = ptr = 0;
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -	while (first && second)	/* Merge the sub-lists */
 | 
	
		
			
				|  |  | -	{		
 | 
	
		
			
				|  |  | -		if (cJSONUtils_strcasecmp(first->string,second->string)<0)
 | 
	
		
			
				|  |  | -		{
 | 
	
		
			
				|  |  | -			if (!list) list=ptr=first;
 | 
	
		
			
				|  |  | -			else	{ptr->next=first;first->prev=ptr;ptr=first;}
 | 
	
		
			
				|  |  | -			first=first->next;
 | 
	
		
			
				|  |  | -		}
 | 
	
		
			
				|  |  | -		else 
 | 
	
		
			
				|  |  | -		{
 | 
	
		
			
				|  |  | -			if (!list) list=ptr=second;
 | 
	
		
			
				|  |  | -			else	{ptr->next=second;second->prev=ptr;ptr=second;}
 | 
	
		
			
				|  |  | -			second=second->next;
 | 
	
		
			
				|  |  | -		}
 | 
	
		
			
				|  |  | -	}
 | 
	
		
			
				|  |  | -	if (first)	{	if (!list) return first;	ptr->next=first;	first->prev=ptr;	}	/* Append any tails. */
 | 
	
		
			
				|  |  | -	if (second)	{	if (!list) return second;	ptr->next=second;	second->prev=ptr;	}
 | 
	
		
			
				|  |  | +    while (first && second) /* Merge the sub-lists */
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +        if (cJSONUtils_strcasecmp(first->string, second->string) < 0)
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +            if (!list)
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +                /* start merged list with the first element of the first list */
 | 
	
		
			
				|  |  | +                list = ptr = first;
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +            else
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +                /* add first element of first list to merged list */
 | 
	
		
			
				|  |  | +                ptr->next = first;
 | 
	
		
			
				|  |  | +                first->prev = ptr;
 | 
	
		
			
				|  |  | +                ptr = first;
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +            first = first->next;
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +        else
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +            if (!list)
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +                /* start merged list with the first element of the second list */
 | 
	
		
			
				|  |  | +                list = ptr = second;
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +            else
 | 
	
		
			
				|  |  | +            {
 | 
	
		
			
				|  |  | +                /* add first element of second list to merged list */
 | 
	
		
			
				|  |  | +                ptr->next = second;
 | 
	
		
			
				|  |  | +                second->prev = ptr;
 | 
	
		
			
				|  |  | +                ptr = second;
 | 
	
		
			
				|  |  | +            }
 | 
	
		
			
				|  |  | +            second = second->next;
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +    if (first)
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +        /* Append rest of first list. */
 | 
	
		
			
				|  |  | +        if (!list)
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +            return first;
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +        ptr->next = first;
 | 
	
		
			
				|  |  | +        first->prev = ptr;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  | +    if (second)
 | 
	
		
			
				|  |  | +    {
 | 
	
		
			
				|  |  | +        /* Append rest of second list */
 | 
	
		
			
				|  |  | +        if (!list)
 | 
	
		
			
				|  |  | +        {
 | 
	
		
			
				|  |  | +            return second;
 | 
	
		
			
				|  |  | +        }
 | 
	
		
			
				|  |  | +        ptr->next = second;
 | 
	
		
			
				|  |  | +        second->prev = ptr;
 | 
	
		
			
				|  |  | +    }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -	return list;
 | 
	
		
			
				|  |  | +    return list;
 | 
	
		
			
				|  |  |  }
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  |  void cJSONUtils_SortObject(cJSON *object)	{object->child=cJSONUtils_SortList(object->child);}
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |  cJSON* cJSONUtils_MergePatch(cJSON *target, cJSON *patch)
 |